Infrastructure de sécurité : validation des entrées | Mesures d’atténuation
Désactiver les scripts XSLT pour toutes les transformations à l’aide de feuilles de style non approuvées
Intitulé | Détails |
---|---|
Composant | Application Web |
Phase SDL | Build |
Technologies applicables | Générique |
Attributs | N/A |
Informations de référence | Sécurité XSLT, Propriété XsltSettings.EnableScript |
Étapes | XSLT prend en charge les scripts dans les feuilles de style à l’aide de l’élément <msxml:script> . Cela permet d’utiliser des fonctions personnalisées dans une transformation XSLT. Le script est exécuté dans le cadre du processus exécutant la transformation. Le script XSLT doit être désactivé dans les environnements non approuvés afin d’empêcher l’exécution de code non approuvé. Si vous utilisez .NET : les scripts XSLT sont désactivés par défaut. Cependant, vous devez vous assurer qu’ils n’ont pas été explicitement activés par le biais de la propriété XsltSettings.EnableScript . |
Exemple
XsltSettings settings = new XsltSettings();
settings.EnableScript = true; // WRONG: THIS SHOULD BE SET TO false
Exemple
Si vous utilisez MSXML 6.0, les scripts XSLT sont désactivés par défaut. Cependant, vous devez vous assurer qu’ils n’ont pas été explicitement activés par le biais de la propriété d’objet DOM XML AllowXsltScript.
doc.setProperty("AllowXsltScript", true); // WRONG: THIS SHOULD BE SET TO false
Exemple
Si vous utilisez MSXML 5 ou une version antérieure, les scripts XSLT sont activés par défaut et vous devez les désactiver explicitement. Définissez la propriété de l’objet XML DOM AllowXsltScript sur false.
doc.setProperty("AllowXsltScript", false); // CORRECT. Setting to false disables XSLT scripting.
S’assurer que chaque page susceptible de comporter du contenu contrôlable par l’utilisateur refuse la détection MIME automatique
Intitulé | Détails |
---|---|
Composant | Application Web |
Phase SDL | Build |
Technologies applicables | Générique |
Attributs | N/A |
Informations de référence | IE8 Security Part V - Comprehensive Protection (Sécurité IE8 Partie V - Protection complète) |
Étapes | Pour chaque page susceptible de comporter du contenu contrôlable par l’utilisateur, vous devez utiliser l’en-tête HTTP Chaque type de fichier provenant d’un serveur web est associé à un type MIME (également appelé type de contenu) qui décrit la nature du contenu (image, texte, application, etc.) L’en-tête X-Content-Type-Options est un en-tête HTTP permettant aux développeurs de spécifier que leur contenu ne doit pas être détecté par MIME. Cet en-tête est conçu pour limiter les attaques par détection MIME. La prise en charge de cet en-tête a été ajoutée dans Internet Explorer 8 (IE8). Seuls les utilisateurs d’Internet Explorer 8 (IE8) bénéficient de l’en-tête X-Content-Type-Options. À l’heure actuelle, les versions antérieures d’Internet Explorer ne prennent pas en charge l’en-tête X-Content-Type-Options Internet Explorer 8 (et les versions ultérieures) constitue le seul navigateur majeur permettant d’implémenter une fonctionnalité de refus de la détection MIME. Si d’autres navigateurs majeurs (Firefox, Safari, Chrome) implémentent des fonctionnalités similaires, cette recommandation sera mise à jour afin d’inclure également la syntaxe de ces navigateurs |
Exemple
Pour activer l’en-tête requis sur toutes les pages de l’application, vous pouvez effectuer l’une des opérations suivantes :
- Ajoutez l’en-tête dans le fichier web.config si l’application est hébergée par Internet Information Services (IIS) 7
<system.webServer>
<httpProtocol>
<customHeaders>
<add name=""X-Content-Type-Options"" value=""nosniff""/>
</customHeaders>
</httpProtocol>
</system.webServer>
- Ajoutez l’en-tête par le biais de la méthode globale Application_BeginRequest
void Application_BeginRequest(object sender, EventArgs e)
{
this.Response.Headers[""X-Content-Type-Options""] = ""nosniff"";
}
- Implémentez le module HTTP personnalisé
public class XContentTypeOptionsModule : IHttpModule
{
#region IHttpModule Members
public void Dispose()
{
}
public void Init(HttpApplication context)
{
context.PreSendRequestHeaders += newEventHandler(context_PreSendRequestHeaders);
}
#endregion
void context_PreSendRequestHeaders(object sender, EventArgs e)
{
HttpApplication application = sender as HttpApplication;
if (application == null)
return;
if (application.Response.Headers[""X-Content-Type-Options ""] != null)
return;
application.Response.Headers.Add(""X-Content-Type-Options "", ""nosniff"");
}
}
- Vous pouvez activer l’en-tête requis uniquement pour des pages spécifiques en l’ajoutant à des réponses individuelles :
this.Response.Headers[""X-Content-Type-Options""] = ""nosniff"";
Renforcer ou désactiver la résolution d’entité XML
Intitulé | Détails |
---|---|
Composant | Application Web |
Phase SDL | Build |
Technologies applicables | Générique |
Attributs | N/A |
Informations de référence | XML Entity Expansion (Extension d’entité XML), Attaques par déni de service XML et moyens de défense, Vue d’ensemble de la sécurité MSXML, Meilleures pratiques pour la sécurisation du Code MSXML, Référence de protocole NSXMLParserDelegate, Résolution des ressources externes |
Étapes | Bien qu’elle soit peu utilisée, une fonctionnalité XML permet à l’analyseur XML d’étendre des entités de macro avec des valeurs définies dans le document lui-même ou à partir de sources externes. Par exemple, le document peut définir une entité « companyname » avec la valeur « Microsoft », afin que chaque fois que le texte « &companyname ; » apparaisse dans le document, il est automatiquement remplacé par le texte Microsoft. Autre solution : le document peut définir une entité « StockMSFT » qui fait référence à un service web externe permettant d’extraire la valeur actuelle du stock Microsoft. Ensuite, chaque fois que « &MSFTStock » apparaît dans le document, il est automatiquement remplacé par le cours actuel des actions. Cependant, cette fonctionnalité peut être utilisée abusivement afin de générer un déni de service (DoS). Une personne malveillante peut imbriquer plusieurs entités pour créer une bombe XML à extension exponentielle, qui consomme toute la mémoire disponible sur le système. Elle peut également créer une référence externe qui diffuse en continu une quantité infinie de données ou bloque simplement le thread. Par conséquent, toutes les équipes doivent entièrement désactiver la résolution d’entité XML interne et/ou externe si leur application ne l’utilise pas, ou limiter manuellement la quantité de mémoire et de temps que l’application peut utiliser pour la résolution d’entité si cette fonctionnalité est indispensable. Si la résolution d’entité n’est pas requise par votre application, désactivez-la. |
Exemple
Pour le code .NET Framework, vous pouvez utiliser les méthodes suivantes :
XmlTextReader reader = new XmlTextReader(stream);
reader.ProhibitDtd = true;
XmlReaderSettings settings = new XmlReaderSettings();
settings.ProhibitDtd = true;
XmlReader reader = XmlReader.Create(stream, settings);
// for .NET 4
XmlReaderSettings settings = new XmlReaderSettings();
settings.DtdProcessing = DtdProcessing.Prohibit;
XmlReader reader = XmlReader.Create(stream, settings);
La valeur par défaut de ProhibitDtd
dans XmlReaderSettings
est true, mais elle est false dans XmlTextReader
. Si vous utilisez XmlReaderSettings, vous n’êtes pas obligé de définir explicitement ProhibitDtd sur true, mais ce paramétrage est recommandé pour des raisons de sécurité. La classe XmlDocument autorise également la résolution d’entité par défaut.
Exemple
Pour désactiver la résolution d’entité relative à XmlDocument, utilisez la surcharge XmlDocument.Load(XmlReader)
de la méthode Load et définissez les propriétés concernées dans l’argument XmlReader, comme illustré dans le code suivant :
XmlReaderSettings settings = new XmlReaderSettings();
settings.ProhibitDtd = true;
XmlReader reader = XmlReader.Create(stream, settings);
XmlDocument doc = new XmlDocument();
doc.Load(reader);
Exemple
S’il est impossible de désactiver la résolution d’entité pour votre application, définissez la propriété XmlReaderSettings.MaxCharactersFromEntities sur une valeur raisonnable en fonction des besoins de votre application. Cela limitera l’impact des attaques DoS potentielles d’extension exponentielle. Le code suivant propose un exemple d’approche :
XmlReaderSettings settings = new XmlReaderSettings();
settings.ProhibitDtd = false;
settings.MaxCharactersFromEntities = 1000;
XmlReader reader = XmlReader.Create(stream, settings);
Exemple
Si vous devez résoudre les entités incorporées, mais pas les entités externes, définissez la propriété XmlReaderSettings.XmlResolver sur null. Par exemple :
XmlReaderSettings settings = new XmlReaderSettings();
settings.ProhibitDtd = false;
settings.MaxCharactersFromEntities = 1000;
settings.XmlResolver = null;
XmlReader reader = XmlReader.Create(stream, settings);
Dans MSXML6, la valeur ProhibitDTD est définie sur true (ce qui désactive le traitement DTD) par défaut. Pour le code Apple OSX/iOS, vous pouvez utiliser deux analyseurs XML : NSXMLParser et libXML2.
Les applications utilisant http.sys doivent procéder à la vérification de la canonisation des URL
Intitulé | Détails |
---|---|
Composant | Application Web |
Phase SDL | Build |
Technologies applicables | Générique |
Attributs | N/A |
Informations de référence | N/A |
Étapes | Toutes les applications utilisant http.sys doivent suivre ces instructions :
|
S’assurer que les contrôles appropriés sont en place lors de l’acceptation de fichiers provenant d’utilisateurs
Intitulé | Détails |
---|---|
Composant | Application Web |
Phase SDL | Build |
Technologies applicables | Générique |
Attributs | N/A |
Informations de référence | Unrestricted File Upload (Chargement de fichiers sans restriction), File Signature Table (Table de signatures de fichier) |
Étapes | Les fichiers téléchargés constituent un risque significatif pour les applications. La première étape de nombreuses attaques consiste à obtenir un code permettant d’attaquer le système. Il suffit ensuite que l’attaque trouve un moyen d’exécuter le code. Un téléchargement de fichier permet aux personnes malveillantes d’accomplir la première étape. Les conséquences d’un téléchargement de fichier sans restriction peuvent varier, de la prise de contrôle totale du système à la surcharge d’un système de fichiers ou d’une base de données, en passant par le transfert d’attaques vers les systèmes back-end ou la simple dégradation. Tout dépend de ce que l’application fait du fichier téléchargé, et surtout de l’emplacement de stockage du fichier. Il manque la validation des téléchargements de fichiers côté serveur. Le suivi des contrôles de sécurité doit être implémenté pour la fonctionnalité de téléchargement de fichiers :
|
Exemple
Concernant la validation de la signature de format de fichier, reportez-vous à la classe ci-dessous pour plus d’informations :
private static Dictionary<string, List<byte[]>> fileSignature = new Dictionary<string, List<byte[]>>
{
{ ".DOC", new List<byte[]> { new byte[] { 0xD0, 0xCF, 0x11, 0xE0, 0xA1, 0xB1, 0x1A, 0xE1 } } },
{ ".DOCX", new List<byte[]> { new byte[] { 0x50, 0x4B, 0x03, 0x04 } } },
{ ".PDF", new List<byte[]> { new byte[] { 0x25, 0x50, 0x44, 0x46 } } },
{ ".ZIP", new List<byte[]>
{
new byte[] { 0x50, 0x4B, 0x03, 0x04 },
new byte[] { 0x50, 0x4B, 0x4C, 0x49, 0x54, 0x55 },
new byte[] { 0x50, 0x4B, 0x53, 0x70, 0x58 },
new byte[] { 0x50, 0x4B, 0x05, 0x06 },
new byte[] { 0x50, 0x4B, 0x07, 0x08 },
new byte[] { 0x57, 0x69, 0x6E, 0x5A, 0x69, 0x70 }
}
},
{ ".PNG", new List<byte[]> { new byte[] { 0x89, 0x50, 0x4E, 0x47, 0x0D, 0x0A, 0x1A, 0x0A } } },
{ ".JPG", new List<byte[]>
{
new byte[] { 0xFF, 0xD8, 0xFF, 0xE0 },
new byte[] { 0xFF, 0xD8, 0xFF, 0xE1 },
new byte[] { 0xFF, 0xD8, 0xFF, 0xE8 }
}
},
{ ".JPEG", new List<byte[]>
{
new byte[] { 0xFF, 0xD8, 0xFF, 0xE0 },
new byte[] { 0xFF, 0xD8, 0xFF, 0xE2 },
new byte[] { 0xFF, 0xD8, 0xFF, 0xE3 }
}
},
{ ".XLS", new List<byte[]>
{
new byte[] { 0xD0, 0xCF, 0x11, 0xE0, 0xA1, 0xB1, 0x1A, 0xE1 },
new byte[] { 0x09, 0x08, 0x10, 0x00, 0x00, 0x06, 0x05, 0x00 },
new byte[] { 0xFD, 0xFF, 0xFF, 0xFF }
}
},
{ ".XLSX", new List<byte[]> { new byte[] { 0x50, 0x4B, 0x03, 0x04 } } },
{ ".GIF", new List<byte[]> { new byte[] { 0x47, 0x49, 0x46, 0x38 } } }
};
public static bool IsValidFileExtension(string fileName, byte[] fileData, byte[] allowedChars)
{
if (string.IsNullOrEmpty(fileName) || fileData == null || fileData.Length == 0)
{
return false;
}
bool flag = false;
string ext = Path.GetExtension(fileName);
if (string.IsNullOrEmpty(ext))
{
return false;
}
ext = ext.ToUpperInvariant();
if (ext.Equals(".TXT") || ext.Equals(".CSV") || ext.Equals(".PRN"))
{
foreach (byte b in fileData)
{
if (b > 0x7F)
{
if (allowedChars != null)
{
if (!allowedChars.Contains(b))
{
return false;
}
}
else
{
return false;
}
}
}
return true;
}
if (!fileSignature.ContainsKey(ext))
{
return true;
}
List<byte[]> sig = fileSignature[ext];
foreach (byte[] b in sig)
{
var curFileSig = new byte[b.Length];
Array.Copy(fileData, curFileSig, b.Length);
if (curFileSig.SequenceEqual(b))
{
flag = true;
break;
}
}
return flag;
}
S’assurer que des paramètres de type sécurisé sont utilisés dans une application web pour l’accès aux données
Intitulé | Détails |
---|---|
Composant | Application Web |
Phase SDL | Build |
Technologies applicables | Générique |
Attributs | N/A |
Informations de référence | N/A |
Étapes | Si vous utilisez la collection Parameters, SQL traite l’entrée comme une valeur littérale et non comme du code exécutable. La collection Parameters peut être utilisée pour appliquer des contraintes de type et de longueur sur les données d’entrée. Les valeurs situées en dehors de la plage déclenchent une exception. En l’absence de paramètres SQL de type sécurisé, des personnes malveillantes peuvent exécuter des attaques par injection, incorporées dans les entrées non filtrées. Utilisez des paramètres de type sécurisé lors de la création de requêtes SQL afin d’éviter des attaques par injection de code SQL susceptibles de se produire avec des entrées non filtrées. Vous pouvez utiliser des paramètres de type sécurisé avec des procédures stockées et des instructions SQL dynamiques. Les paramètres sont traités comme des valeurs littérales par la base de données, et non comme du code exécutable. Le type et la longueur sont également vérifiés pour les paramètres. |
Exemple
Le code suivant montre comment utiliser les paramètres de type sécurisé avec SqlParameterCollection lors de l’appel d’une procédure stockée.
using System.Data;
using System.Data.SqlClient;
using (SqlConnection connection = new SqlConnection(connectionString))
{
DataSet userDataset = new DataSet();
SqlDataAdapter myCommand = new SqlDataAdapter("LoginStoredProcedure", connection);
myCommand.SelectCommand.CommandType = CommandType.StoredProcedure;
myCommand.SelectCommand.Parameters.Add("@au_id", SqlDbType.VarChar, 11);
myCommand.SelectCommand.Parameters["@au_id"].Value = SSN.Text;
myCommand.Fill(userDataset);
}
Dans l’exemple de code précédent, la valeur d’entrée ne peut pas être supérieure à 11 caractères. Si les données ne sont pas conformes au type ou à la longueur définis par le paramètre, la classe SqlParameter renvoie une exception.
Utiliser des classes de liaison de modèle ou des listes de filtre de liaison distinctes pour empêcher une vulnérabilité d’attribution collective MVC
Intitulé | Détails |
---|---|
Composant | Application Web |
Phase SDL | Build |
Technologies applicables | MVC5, MVC6 |
Attributs | N/A |
Informations de référence | Metadata Attributes (Classe MetadataTypeAttribute), Public Key Security Vulnerability And Mitigation (Failles de sécurité des clés publiques et mesures de correction), Complete Guide to Mass Assignment in ASP.NET MVC (Guide complet d’attribution collective dans ASP.NET MVC), Getting Started with EF using MVC (Prise en main d’EF à l’aide de MVC) |
Étapes |
|
Encoder une sortie web non approuvée avant le rendu
Intitulé | Détails |
---|---|
Composant | Application Web |
Phase SDL | Build |
Technologies applicables | Générique, Web Forms, MVC5, MVC6 |
Attributs | N/A |
Informations de référence | How to prevent Cross-site scripting in ASP.NET (Comment éviter les scripts intersites dans ASP.NET), Cross-site Scripting (Scripts intersites), XSS (Cross Site Scripting) Prevention Cheat Sheet (Aide-mémoire sur la prévention des scripts intersites) |
Étapes | Les scripts intersites (XSS, Cross Site Scripting) sont un vecteur d’attaque pour les services en ligne ou toute application/tout composant qui utilise des entrées tirées du web. Les vulnérabilités XSS permettent à une personne malveillante d’exécuter un script sur l’ordinateur d’un autre utilisateur par le biais d’une application web vulnérable. Les scripts malveillants peuvent servir à dérober des cookies ou à manipuler un ordinateur cible par le biais de JavaScript. Pour empêcher les scripts intersites, il faut procéder à la validation des entrées utilisateur, en s’assurant que la forme et l’encodage sont corrects avant le rendu sur une page web. La validation des entrées et l’encodage des sorties peuvent se faire au moyen de Web Protection Library. Pour le code managé (C#, VB.NET, etc.), utilisez une ou plusieurs méthodes d’encodage appropriées, tirées de Web Protection (Anti-XSS) Library, en fonction du contexte dans lequel les entrées utilisateur se manifestent : |
Exemple
* Encoder.HtmlEncode
* Encoder.HtmlAttributeEncode
* Encoder.JavaScriptEncode
* Encoder.UrlEncode
* Encoder.VisualBasicScriptEncode
* Encoder.XmlEncode
* Encoder.XmlAttributeEncode
* Encoder.CssEncode
* Encoder.LdapEncode
Procéder à la validation et au filtrage des entrées sur les propriétés de modèle de tous types de chaînes
Intitulé | Détails |
---|---|
Composant | Application Web |
Phase SDL | Build |
Technologies applicables | Générique, MVC5, MVC6 |
Attributs | N/A |
Informations de référence | Adding Validation (Ajout d’une validation), Validating Model Data in an MVC Application (Validation des données de modèle dans une application MVC), Principes directeurs pour vos applications ASP.NET MVC |
Étapes | Tous les paramètres d’entrée doivent être validés avant d’être utilisés dans l’application afin de vous assurer que l’application est protégée contre les entrées utilisateur malveillantes. Validez les valeurs d’entrée en recourant à la validation d’expressions régulières côté serveur au moyen d’une stratégie de validation par liste autorisée. Les entrées utilisateur/paramètres non nettoyés et transmis aux méthodes peuvent engendrer des vulnérabilités par injection de code. Pour les applications web, les points d’entrée peuvent également inclure des champs de formulaire, des chaînes de requête, des cookies, des en-têtes HTTP et des paramètres de service web. Les contrôles de validation des entrées suivants doivent être effectués lors de la liaison de modèle :
|
Les champs de formulaire acceptant tous les caractères, par exemple dans un éditeur de texte enrichi, doivent être nettoyés
Intitulé | Détails |
---|---|
Composant | Application Web |
Phase SDL | Build |
Technologies applicables | Générique |
Attributs | N/A |
Informations de référence | Encode Unsafe Input (Encodage d’entrées à risque), HTML Sanitizer |
Étapes | Identifiez toutes les balises statiques que vous souhaitez utiliser. Une pratique courante consiste à limiter la mise en forme des éléments HTML sécurisés, comme Avant d’écrire les données, encodez-les au format HTML. Cela sécurise n’importe quel script malveillant en le traitant comme du texte, et non comme du code exécutable.
La page dans les références désactive la validation de requête ASP.NET en définissant HtmlSanitizer est une bibliothèque .NET destinée au nettoyage des documents et fragments HTML provenant de constructions susceptibles d’aboutir à des attaques XSS. Elle utilise AngleSharp pour analyser, manipuler et réaliser le rendu HTML et CSS. HtmlSanitizer peut être installée en tant que package NuGet, et les entrées utilisateur peuvent être transmises par le biais de méthodes de nettoyage HTML ou CSS appropriées, le cas échéant, côté serveur. Dans le cadre du contrôle de sécurité, le nettoyage doit être envisagé uniquement en dernier recours. La validation des entrées et l’encodage des sorties sont considérés comme de meilleurs contrôles de sécurité. |
Ne pas attribuer d’éléments DOM à des récepteurs sans codage intégré
Intitulé | Détails |
---|---|
Composant | Application Web |
Phase SDL | Build |
Technologies applicables | Générique |
Attributs | N/A |
Informations de référence | N/A |
Étapes | De nombreuses fonctions JavaScript ne procèdent pas à l’encodage par défaut. L’attribution d’entrées non approuvées à des éléments DOM par le biais de ces fonctions risque d’entraîner l’exécution de scripts intersites (XSS). |
Exemple
Voici quelques exemples non sécurisés :
document.getElementByID("div1").innerHtml = value;
$("#userName").html(res.Name);
return $('<div/>').html(value)
$('body').append(resHTML);
N’utilisez pas innerHtml
. Utilisez plutôt innerText
. De même, au lieu de $("#elm").html()
, utilisez$("#elm").text()
Valider la sécurité de la fermeture ou de l’exécution de toutes les redirections au sein de l’application
Intitulé | Détails |
---|---|
Composant | Application Web |
Phase SDL | Build |
Technologies applicables | Générique |
Attributs | N/A |
Informations de référence | The OAuth 2.0 Authorization Framework - Open Redirectors (Infrastructure d’autorisation OAuth 2.0 : Redirecteurs ouverts) |
Étapes | La conception d’applications nécessitant une redirection vers un emplacement fourni par l’utilisateur doit limiter les cibles possibles de redirection à une liste prédéfinie « sécurisée » de sites ou de domaines. Toutes les redirections au sein de l’application doivent être fermées/sécurisées. Pour ce faire :
|
Implémenter la validation des entrées sur tous les paramètres de type de chaîne acceptés par les méthodes de contrôleur
Intitulé | Détails |
---|---|
Composant | Application Web |
Phase SDL | Build |
Technologies applicables | Générique, MVC5, MVC6 |
Attributs | N/A |
Informations de référence | Validating Model Data in an MVC Application (Validation des données de modèle dans une application MVC), Principes directeurs pour vos applications ASP.NET MVC |
Étapes | Pour les méthodes qui acceptent uniquement un type de données primitif, et non les modèles en tant qu’argument, la validation des entrées doit être effectuée à l’aide d’expressions régulières. Dans le cas présent, Regex.IsMatch doit être utilisé avec un modèle d’expression régulière valide. Si l’entrée ne correspond pas à l’expression régulière spécifiée, le contrôle ne doit pas se poursuivre, et un avertissement approprié indiquant l’échec de la validation doit s’afficher. |
Définir le seuil supérieur du délai d’expiration pour le traitement des expressions régulières afin d’empêcher un déni de service en raison d’expressions régulières incorrectes
Intitulé | Détails |
---|---|
Composant | Application Web |
Phase SDL | Build |
Technologies applicables | Générique, Web Forms, MVC5, MVC6 |
Attributs | N/A |
Informations de référence | Propriété DefaultRegexMatchTimeout |
Étapes | Pour empêcher les attaques par déni de service contre les expressions régulières incorrectes, qui suscitent de nombreux retours sur trace, définissez le délai d’attente global par défaut. Si le temps de traitement excède la limite supérieure définie, une exception d’expiration est générée. Si rien n’est configuré, le délai d’attente est infini. |
Exemple
Par exemple, la configuration suivante génère une exception RegexMatchTimeoutException, si le traitement prend plus de 5 secondes :
<httpRuntime targetFramework="4.5" defaultRegexMatchTimeout="00:00:05" />
Éviter l’utilisation de Html.Raw dans les vues Razor
Intitulé | Détails |
---|---|
Composant | Application Web |
Phase SDL | Build |
Technologies applicables | MVC5, MVC6 |
Attributs | N/A |
Informations de référence | N/A |
Étape | Pages Web ASP.NET (Razor) procède à un encodage HTML automatique. Toutes les chaînes imprimées par des pépites, ou nuggets, de code (blocs @) sont automatiquement encodées au format HTML. Toutefois, lorsque la méthode HtmlHelper.Raw est appelée, elle renvoie un balisage qui n’est pas encodé au format HTML. Si la méthode d’assistance Html.Raw() est utilisée, elle ignore la protection par encodage automatique fournie par Razor. |
Exemple
Voici un exemple non sécurisé :
<div class="form-group">
@Html.Raw(Model.AccountConfirmText)
</div>
<div class="form-group">
@Html.Raw(Model.PaymentConfirmText)
</div>
</div>
N’utilisez pas Html.Raw()
sauf si vous devez afficher le balisage. Cette méthode n’effectue pas de codage implicite en sortie. Utilisez d’autres aides ASP.NET, comme @Html.DisplayFor()
Ne pas utiliser les requêtes dynamiques dans les procédures stockées
Intitulé | Détails |
---|---|
Composant | Base de données |
Phase SDL | Build |
Technologies applicables | Générique |
Attributs | N/A |
Informations de référence | N/A |
Étapes | Une attaque par injection de code SQL exploite les vulnérabilités de la validation des entrées afin d’exécuter des commandes arbitraires dans la base de données. Cela peut se produire lorsque votre application utilise des entrées pour créer des instructions SQL dynamiques afin d’accéder à la base de données. Cela peut également se produire si votre code utilise des procédures stockées contenant des chaînes transmises qui comportent des entrées utilisateur brutes. Grâce aux attaques par injection de code SQL, une personne malveillante peut exécuter des commandes arbitraires dans la base de données. Toutes les instructions SQL (y compris les instructions SQL des procédures stockées) doivent être paramétrables. Les instructions SQL paramétrables acceptent les caractères ayant une signification particulière pour SQL (par exemple, les guillemets simples) sans problème, car ils sont fortement typés. |
Exemple
Voici un exemple de procédure stockée dynamique non sécurisée :
CREATE PROCEDURE [dbo].[uspGetProductsByCriteria]
(
@productName nvarchar(200) = NULL,
@startPrice float = NULL,
@endPrice float = NULL
)
AS
BEGIN
DECLARE @sql nvarchar(max)
SELECT @sql = ' SELECT ProductID, ProductName, Description, UnitPrice, ImagePath' +
' FROM dbo.Products WHERE 1 = 1 '
PRINT @sql
IF @productName IS NOT NULL
SELECT @sql = @sql + ' AND ProductName LIKE ''%' + @productName + '%'''
IF @startPrice IS NOT NULL
SELECT @sql = @sql + ' AND UnitPrice > ''' + CONVERT(VARCHAR(10),@startPrice) + ''''
IF @endPrice IS NOT NULL
SELECT @sql = @sql + ' AND UnitPrice < ''' + CONVERT(VARCHAR(10),@endPrice) + ''''
PRINT @sql
EXEC(@sql)
END
Exemple
Voici la même procédure stockée, implémentée de façon sécurisée :
CREATE PROCEDURE [dbo].[uspGetProductsByCriteriaSecure]
(
@productName nvarchar(200) = NULL,
@startPrice float = NULL,
@endPrice float = NULL
)
AS
BEGIN
SELECT ProductID, ProductName, Description, UnitPrice, ImagePath
FROM dbo.Products where
(@productName IS NULL or ProductName like '%'+ @productName +'%')
AND
(@startPrice IS NULL or UnitPrice > @startPrice)
AND
(@endPrice IS NULL or UnitPrice < @endPrice)
END
S’assurer que la validation du modèle est effectuée sur les méthodes d’API Web
Intitulé | Détails |
---|---|
Composant | API Web |
Phase SDL | Build |
Technologies applicables | MVC5, MVC6 |
Attributs | N/A |
Informations de référence | Validation du modèle dans l’API web ASP.NET |
Étapes | Lorsqu’un client envoie des données vers une API Web, les données doivent être validées avant tout traitement. Pour les API Web ASP.NET qui acceptent les modèles en tant qu’entrée, utilisez des annotations de données sur les modèles afin de définir des règles de validation sur les propriétés du modèle. |
Exemple
Le code suivant illustre le même cas :
using System.ComponentModel.DataAnnotations;
namespace MyApi.Models
{
public class Product
{
public int Id { get; set; }
[Required]
[RegularExpression(@"^[a-zA-Z0-9]*$", ErrorMessage="Only alphanumeric characters are allowed.")]
public string Name { get; set; }
public decimal Price { get; set; }
[Range(0, 999)]
public double Weight { get; set; }
}
}
Exemple
Dans la méthode d’action des contrôleurs d’API, la validité du modèle doit être vérifiée explicitement comme indiqué ci-dessous :
namespace MyApi.Controllers
{
public class ProductsController : ApiController
{
public HttpResponseMessage Post(Product product)
{
if (ModelState.IsValid)
{
// Do something with the product (not shown).
return new HttpResponseMessage(HttpStatusCode.OK);
}
else
{
return Request.CreateErrorResponse(HttpStatusCode.BadRequest, ModelState);
}
}
}
}
Implémenter la validation des entrées sur tous les paramètres de type de chaîne acceptés par les méthodes d’API Web
Intitulé | Détails |
---|---|
Composant | API Web |
Phase SDL | Build |
Technologies applicables | Générique, MVC 5, MVC 6 |
Attributs | N/A |
Informations de référence | Validating Model Data in an MVC Application (Validation des données de modèle dans une application MVC), Principes directeurs pour vos applications ASP.NET MVC |
Étapes | Pour les méthodes qui acceptent uniquement un type de données primitif, et non les modèles en tant qu’argument, la validation des entrées doit être effectuée à l’aide d’expressions régulières. Dans le cas présent, Regex.IsMatch doit être utilisé avec un modèle d’expression régulière valide. Si l’entrée ne correspond pas à l’expression régulière spécifiée, le contrôle ne doit pas se poursuivre, et un avertissement approprié indiquant l’échec de la validation doit s’afficher. |
S’assurer que les paramètres de type sécurisé sont utilisés dans une API Web pour l’accès aux données
Intitulé | Détails |
---|---|
Composant | API Web |
Phase SDL | Build |
Technologies applicables | Générique |
Attributs | N/A |
Informations de référence | N/A |
Étapes | Si vous utilisez la collection Parameters, SQL traite l’entrée comme une valeur littérale et non comme du code exécutable. La collection Parameters peut être utilisée pour appliquer des contraintes de type et de longueur sur les données d’entrée. Les valeurs situées en dehors de la plage déclenchent une exception. En l’absence de paramètres SQL de type sécurisé, des personnes malveillantes peuvent exécuter des attaques par injection, incorporées dans les entrées non filtrées. Utilisez des paramètres de type sécurisé lors de la création de requêtes SQL afin d’éviter des attaques par injection de code SQL susceptibles de se produire avec des entrées non filtrées. Vous pouvez utiliser des paramètres de type sécurisé avec des procédures stockées et des instructions SQL dynamiques. Les paramètres sont traités comme des valeurs littérales par la base de données, et non comme du code exécutable. Le type et la longueur sont également vérifiés pour les paramètres. |
Exemple
Le code suivant montre comment utiliser les paramètres de type sécurisé avec SqlParameterCollection lors de l’appel d’une procédure stockée.
using System.Data;
using System.Data.SqlClient;
using (SqlConnection connection = new SqlConnection(connectionString))
{
DataSet userDataset = new DataSet();
SqlDataAdapter myCommand = new SqlDataAdapter("LoginStoredProcedure", connection);
myCommand.SelectCommand.CommandType = CommandType.StoredProcedure;
myCommand.SelectCommand.Parameters.Add("@au_id", SqlDbType.VarChar, 11);
myCommand.SelectCommand.Parameters["@au_id"].Value = SSN.Text;
myCommand.Fill(userDataset);
}
Dans l’exemple de code précédent, la valeur d’entrée ne peut pas être supérieure à 11 caractères. Si les données ne sont pas conformes au type ou à la longueur définis par le paramètre, la classe SqlParameter renvoie une exception.
Utiliser des requêtes SQL paramétrables pour Azure Cosmos DB
Intitulé | Détails |
---|---|
Composant | Azure Document DB |
Phase SDL | Build |
Technologies applicables | Générique |
Attributs | N/A |
Informations de référence | Annonce de paramétrage SQL dans Azure Cosmos DB |
Étapes | Bien qu’Azure Cosmos DB ne prenne en charge que les requêtes en lecture seule, l’injection de code SQL reste possible si les requêtes sont construites par concaténation avec les entrées utilisateur. Un utilisateur peut parfois accéder à des données auxquelles il ne devrait pas accéder dans la même collection en créant des requêtes SQL malveillantes. Utilisez des requêtes SQL paramétrables si les requêtes sont créées à partir d’entrées utilisateur. |
Validation des entrées WCF par le biais de la liaison de schéma
Intitulé | Détails |
---|---|
Composant | WCF |
Phase SDL | Build |
Technologies applicables | Générique, NET Framework 3 |
Attributs | N/A |
Informations de référence | MSDN |
Étapes | Une absence de validation peut entraîner différentes attaques par injection de code. La validation des messages représente une ligne de défense spécifique dans la protection de votre application WCF. Avec cette approche, vous validez des messages à l’aide de schémas pour protéger les opérations de service WCF contre les attaques de clients malveillants. Validez tous les messages reçus par le client pour protéger le client contre des attaques effectuées par un service malveillant. La validation des messages permet de valider les messages lorsque les opérations utilisent des contrats de messages ou de données, ce qui ne peut pas être fait avec la validation des paramètres. La validation des messages vous permet de créer une logique de validation dans les schémas, offrant ainsi plus de flexibilité et réduisant le temps de développement. Les schémas peuvent être réutilisés dans plusieurs applications de l’organisation, ce qui crée des normes de représentation des données. En outre, la validation des messages vous permet de protéger les opérations lorsqu’elles utilisent des types de données plus complexes impliquant des contrats de logique métier. Pour procéder à la validation des messages, commencez par créer un schéma qui représente les opérations de votre service et les types de données utilisées par ces opérations. Créez ensuite une classe .NET qui implémente un inspecteur de messages client personnalisé et un inspecteur de messages de répartition personnalisé afin de valider les messages envoyés/reçus à destination/en provenance du service. Puis implémentez un comportement de point de terminaison personnalisé afin d’activer la validation des messages sur le client et le service. Enfin, implémentez un élément de configuration personnalisé sur la classe afin d’exposer le comportement de point de terminaison personnalisé étendu dans le fichier de configuration du service ou le client. |
WCF - Validation des entrées par le biais des inspecteurs de paramètres
Intitulé | Détails |
---|---|
Composant | WCF |
Phase SDL | Build |
Technologies applicables | Générique, NET Framework 3 |
Attributs | N/A |
Informations de référence | MSDN |
Étapes | La validation des données et des entrées représente une ligne de défense importante de la protection de votre application WCF. Vous devez valider tous les paramètres exposés dans les opérations de service WCF pour protéger le service des attaques menées par un client malveillant. Inversement, vous devez aussi valider toutes les valeurs de retour reçues par le client pour protéger le client contre les attaques menées par un service malveillant WCF fournit différents points d’extension qui vous permettent de personnaliser le comportement d’exécution WCF en créant des extensions personnalisées. Les inspecteurs de messages et les inspecteurs de paramètres sont deux mécanismes d’extension facilitant le contrôle des données échangées entre un client et un service. Vous devez utiliser les inspecteurs de paramètres pour la validation des entrées, et les inspecteurs de messages uniquement lorsque vous devez inspecter l’intégralité des messages entrant et sortant d’un service. Pour procéder à la validation des entrées, créez une classe .NET et implémentez un inspecteur de paramètres personnalisé afin de valider les paramètres sur les opérations dans votre service. Implémentez ensuite un comportement de point de terminaison personnalisé afin d’activer la validation sur le client et le service. Enfin, implémentez un élément de configuration personnalisé sur la classe afin d’exposer le comportement de point de terminaison personnalisé étendu dans le fichier de configuration du service ou le client |