Kaynağa Gözat

* Fix to TObjectOpenAddressingLP in generics.collections where SetValue
would free the object if the current value is the same as the new value
(fixes #40024)

(cherry picked from commit 663ee7bc2007a22c48f97927afd4086cc8e56490)

J. Gareth "Curious Kit" Moreton 2 yıl önce
ebeveyn
işleme
5d878ac342

+ 14 - 0
packages/rtl-generics/src/inc/generics.dictionaries.inc

@@ -2233,6 +2233,20 @@ begin
   FOwnerships := AOwnerships;
 end;
 
+procedure TObjectOpenAddressingLP<OPEN_ADDRESSING_CONSTRAINTS>.SetValue(var AValue: TValue; constref ANewValue: TValue);
+var
+  LOldValue: TValue;
+begin
+  if TObject((@AValue)^) <> TObject((@ANewValue)^) then
+  begin
+    LOldValue := AValue;
+    AValue := ANewValue;
+
+    ValueNotify(LOldValue, cnRemoved);
+    ValueNotify(ANewValue, cnAdded);
+  end;
+end;
+
 procedure TObjectOpenAddressingLP<OPEN_ADDRESSING_CONSTRAINTS>.KeyNotify(
   constref AKey: TKey; ACollectionNotification: TCollectionNotification);
 begin

+ 2 - 1
packages/rtl-generics/src/inc/generics.dictionariesh.inc

@@ -98,7 +98,7 @@ type
     procedure KeyNotify(constref AKey: TKey; ACollectionNotification: TCollectionNotification); virtual;
     procedure ValueNotify(constref AValue: TValue; ACollectionNotification: TCollectionNotification); virtual;
     procedure PairNotify(constref APair: TDictionaryPair; ACollectionNotification: TCollectionNotification); inline;
-    procedure SetValue(var AValue: TValue; constref ANewValue: TValue);
+    procedure SetValue(var AValue: TValue; constref ANewValue: TValue); dynamic;
   public
     property OnKeyNotify: TCollectionNotifyEvent<TKey> read FOnKeyNotify write FOnKeyNotify;
     property OnValueNotify: TCollectionNotifyEvent<TValue> read FOnValueNotify write FOnValueNotify;
@@ -597,6 +597,7 @@ type
   private
     FOwnerships: TDictionaryOwnerships;
   protected
+    procedure SetValue(var AValue: TValue; constref ANewValue: TValue); override;
     procedure KeyNotify(constref AKey: TKey; ACollectionNotification: TCollectionNotification); override;
     procedure ValueNotify(constref AValue: TValue; ACollectionNotification: TCollectionNotification); override;
   public