diff --git a/src/LitJson/JsonMapper.cs b/src/LitJson/JsonMapper.cs index 99946cf..fc10b28 100644 --- a/src/LitJson/JsonMapper.cs +++ b/src/LitJson/JsonMapper.cs @@ -106,11 +106,13 @@ public class JsonMapper private static readonly IDictionary base_exporters_table; private static readonly IDictionary custom_exporters_table; + private static readonly object custom_exporters_table_lock = new Object(); private static readonly IDictionary> base_importers_table; private static readonly IDictionary> custom_importers_table; + private static readonly object custom_importers_table_lock = new Object(); private static readonly IDictionary array_metadata; private static readonly object array_metadata_lock = new Object (); @@ -341,25 +343,19 @@ private static object ReadValue (Type inst_type, JsonReader reader) return reader.Value; // If there's a custom importer that fits, use it - if (custom_importers_table.ContainsKey (json_type) && - custom_importers_table[json_type].ContainsKey ( - value_type)) { + lock (custom_importers_table_lock) { + if (custom_importers_table.TryGetValue(json_type, out IDictionary customImporterTablesValue) && + customImporterTablesValue.TryGetValue(value_type, out ImporterFunc customImporter)) { - ImporterFunc importer = - custom_importers_table[json_type][value_type]; - - return importer (reader.Value); + return customImporter(reader.Value); + } } // Maybe there's a base importer that works - if (base_importers_table.ContainsKey (json_type) && - base_importers_table[json_type].ContainsKey ( - value_type)) { - - ImporterFunc importer = - base_importers_table[json_type][value_type]; + if (base_importers_table.TryGetValue(json_type, out IDictionary baseImporterTablesValue) && + baseImporterTablesValue.TryGetValue(value_type, out ImporterFunc baseImporter)) { - return importer (reader.Value); + return baseImporter(reader.Value); } // Maybe it's an enum @@ -560,6 +556,8 @@ private static void ReadSkip (JsonReader reader) private static void RegisterBaseExporters () { + // This method is only called from the static initializer, + // so there is no need to explicitly lock any static members here base_exporters_table[typeof (byte)] = delegate (object obj, JsonWriter writer) { writer.Write (Convert.ToInt32 ((byte) obj)); @@ -614,6 +612,8 @@ private static void RegisterBaseExporters () private static void RegisterBaseImporters () { + // This method is only called from the static initializer, + // so there is no need to explicitly lock any static members here ImporterFunc importer; importer = delegate (object input) { @@ -810,17 +810,17 @@ private static void WriteValue (object obj, JsonWriter writer, Type obj_type = obj.GetType (); // See if there's a custom exporter for the object - if (custom_exporters_table.ContainsKey (obj_type)) { - ExporterFunc exporter = custom_exporters_table[obj_type]; - exporter (obj, writer); + lock (custom_exporters_table_lock) { + if (custom_exporters_table.TryGetValue(obj_type, out ExporterFunc customExporter)) { + customExporter(obj, writer); - return; + return; + } } // If not, maybe there's a base exporter - if (base_exporters_table.ContainsKey (obj_type)) { - ExporterFunc exporter = base_exporters_table[obj_type]; - exporter (obj, writer); + if (base_exporters_table.TryGetValue(obj_type, out ExporterFunc baseExporter)) { + baseExporter(obj, writer); return; } @@ -959,7 +959,9 @@ public static void RegisterExporter (ExporterFunc exporter) exporter ((T) obj, writer); }; - custom_exporters_table[typeof (T)] = exporter_wrapper; + lock (custom_exporters_table_lock) { + custom_exporters_table[typeof (T)] = exporter_wrapper; + } } public static void RegisterImporter ( @@ -970,18 +972,24 @@ public static void RegisterImporter ( return importer ((TJson) input); }; - RegisterImporter (custom_importers_table, typeof (TJson), - typeof (TValue), importer_wrapper); + lock (custom_importers_table_lock) { + RegisterImporter (custom_importers_table, typeof (TJson), + typeof (TValue), importer_wrapper); + } } public static void UnregisterExporters () { - custom_exporters_table.Clear (); + lock (custom_exporters_table_lock) { + custom_exporters_table.Clear(); + } } public static void UnregisterImporters () { - custom_importers_table.Clear (); + lock (custom_importers_table_lock) { + custom_importers_table.Clear(); + } } } }