csharp.lang.security.insecure-deserialization.newtonsoft.insecure-newtonsoft-deserialization

profile photo of returntocorpreturntocorp
Author
5,563
Download Count*

TypeNameHandling $TYPEHANDLER is unsafe and can lead to arbitrary code execution in the context of the process. Use a custom SerializationBinder whenever using a setting other than TypeNameHandling.None.

Run Locally

Run in CI

Defintion

rules:
  - id: insecure-newtonsoft-deserialization
    patterns:
      - pattern-either:
          - pattern: TypeNameHandling = TypeNameHandling.$TYPEHANDLER
          - pattern: |
              $SETTINGS.TypeNameHandling = TypeNameHandling.$TYPEHANDLER;
              ...
              JsonConvert.DeserializeObject<$TYPE>(...,$SETTINGS);
          - pattern: |
              $SETTINGS.TypeNameHandling = TypeNameHandling.$TYPEHANDLER;
              ...
              JsonConvert.DeserializeObject(...,$SETTINGS);
      - pattern-inside: |
          using Newtonsoft.Json;
          ...
      - metavariable-regex:
          metavariable: $TYPEHANDLER
          regex: (All|Auto|Objects|Arrays)
    message: TypeNameHandling $TYPEHANDLER is unsafe and can lead to arbitrary code
      execution in the context of the process.  Use a custom SerializationBinder
      whenever using a setting other than TypeNameHandling.None.
    languages:
      - csharp
    severity: WARNING
    metadata:
      category: security
      cwe:
        - "CWE-502: Deserialization of Untrusted Data"
      owasp:
        - A08:2017 - Insecure Deserialization
        - A08:2021 - Software and Data Integrity Failures
      references:
        - https://www.newtonsoft.com/json/help/html/T_Newtonsoft_Json_TypeNameHandling.htm#remarks
      technology:
        - .net
        - newtonsoft
        - json
      confidence: LOW
      license: MIT
      cwe2022-top25: true
      cwe2021-top25: true
      subcategory:
        - audit
      likelihood: LOW
      impact: HIGH

Examples

newtonsoft.cs

using Newtonsoft.Json;

namespace InsecureDeserialization
{
    public class InsecureNewtonsoftDeserialization
    {
        public void NewtonsoftDeserialization(string json)
        {
            try
            {
                JsonConvert.DeserializeObject<object>(json, new JsonSerializerSettings
                {
                    // ruleid: insecure-newtonsoft-deserialization
                    TypeNameHandling = TypeNameHandling.All
                });
            } catch(Exception e)
            {
                Console.WriteLine(e);
            }
        }

        public void ConverterOverrideSettings(){
            JsonConvert.DefaultSettings = () => 
                //ruleid: insecure-newtonsoft-deserialization
                new JsonSerializerSettings{TypeNameHandling = TypeNameHandling.Auto};
            Bar newBar = JsonConvert.DeserializeObject<Bar>(someJson);
        }

        public void ConverterOverrideSettingsStaggeredInitialize(){
            var settings = new JsonSerializerSettings();
            //ruleid: insecure-newtonsoft-deserialization
            settings.TypeNameHandling = TypeNameHandling.Auto;
            Bar newBar = JsonConvert.DeserializeObject<Bar>(someJson,settings);
        }

        public void ConverterOverrideSettingsMultipleSettingArgs(){
            JsonConvert.DefaultSettings = () => 
                new JsonSerializerSettings{
                    Culture = InvariantCulture,
                    //ruleid: insecure-newtonsoft-deserialization
                    TypeNameHandling = TypeNameHandling.Auto,
                    TraceWriter = traceWriter
                    };
            Bar newBar = JsonConvert.DeserializeObject<Bar>(someJson);
        }

      public void SafeDeserialize(){
        Bar newBar = JsonConvert.DeserializeObject<Bar>(someJson, new JsonSerializerSettings
        {
            //ok: insecure-newtonsoft-deserialization
            TypeNameHandling = TypeNameHandling.None
        });
      }

      public void SafeDefaults(){
        //ok: insecure-newtonsoft-deserialization
        Bar newBar = JsonConvert.DeserializeObject<Bar>(someJson);
      }
    }
}