This is an automated email from the ASF dual-hosted git repository.

joshtynjala pushed a commit to branch develop
in repository https://gitbox.apache.org/repos/asf/royale-compiler.git


The following commit(s) were added to refs/heads/develop by this push:
     new 6a0222755 IdentifierNode, DefinitionBase: Fixed rare race condition 
where certain cached values are detected as non-null but become null before the 
method returns.
6a0222755 is described below

commit 6a022275568f98d9dc76bcd91308b8c336adb8fb
Author: Josh Tynjala <[email protected]>
AuthorDate: Mon Jun 1 13:08:07 2026 -0700

    IdentifierNode, DefinitionBase: Fixed rare race condition where certain 
cached values are detected as non-null but become null before the method 
returns.
---
 RELEASE_NOTES.md                                             |  1 +
 .../royale/compiler/internal/definitions/DefinitionBase.java |  8 ++++++--
 .../royale/compiler/internal/tree/as/IdentifierNode.java     | 12 +++++++++---
 3 files changed, 16 insertions(+), 5 deletions(-)

diff --git a/RELEASE_NOTES.md b/RELEASE_NOTES.md
index 191ab60d0..05d4a0427 100644
--- a/RELEASE_NOTES.md
+++ b/RELEASE_NOTES.md
@@ -81,6 +81,7 @@ Apache Royale Compiler 1.0.0
 - compiler: Fixed JavaScript code generation for E4X wildcard (.*) syntax.
 - compiler: Added `[JSDynamicOverride]`, `[JSForInOverride]`, and 
`[JSForEachOverride]` to customize the behavior of certain syntax when 
targeting JavaScript. Useful for emulating the full features of `Dictionary` 
and `ByteArray` from SWF.
 - compiler: Support resource bundles with `JS` target, similar to `JSRoyale`.
+- compiler: Fixed rare race condition where certain cached values are detected 
as non-null but become null before the method returns.
 - debugger: Added missing isolate ID to SWF load and unload events.
 - debugger: Fixed debugger targeting the current JDK version instead of the 
intended minimum JDK version.
 - debugger: Fixed localized messages appearing as unprocessed tokens.
diff --git 
a/compiler/src/main/java/org/apache/royale/compiler/internal/definitions/DefinitionBase.java
 
b/compiler/src/main/java/org/apache/royale/compiler/internal/definitions/DefinitionBase.java
index 60bca1baa..18f9f72b1 100644
--- 
a/compiler/src/main/java/org/apache/royale/compiler/internal/definitions/DefinitionBase.java
+++ 
b/compiler/src/main/java/org/apache/royale/compiler/internal/definitions/DefinitionBase.java
@@ -258,8 +258,12 @@ public abstract class DefinitionBase implements 
IDocumentableDefinition, IDefini
     @Override
     public IDefinition getParent()
     {
-       if (getPerformanceCachingEnabled() && parentDef != null)
-               return parentDef;
+        // use a local reference to the cached parent definition because the
+        // member variable might change in another thread between checking for
+        // null and returning the value
+        IDefinition cachedParentDef = parentDef;
+       if (getPerformanceCachingEnabled() && cachedParentDef != null)
+               return cachedParentDef;
        
         IASScope scope = getContainingScope();
 
diff --git 
a/compiler/src/main/java/org/apache/royale/compiler/internal/tree/as/IdentifierNode.java
 
b/compiler/src/main/java/org/apache/royale/compiler/internal/tree/as/IdentifierNode.java
index df434c321..05378f962 100644
--- 
a/compiler/src/main/java/org/apache/royale/compiler/internal/tree/as/IdentifierNode.java
+++ 
b/compiler/src/main/java/org/apache/royale/compiler/internal/tree/as/IdentifierNode.java
@@ -308,6 +308,7 @@ public class IdentifierNode extends ExpressionNodeBase 
implements IIdentifierNod
     }
 
     private IDefinition idDef = null;
+
     //
     // ExpressionNodeBase overrides
     //
@@ -315,8 +316,12 @@ public class IdentifierNode extends ExpressionNodeBase 
implements IIdentifierNod
     @Override
     public IDefinition resolve(ICompilerProject project)
     {
-       if (DefinitionBase.getPerformanceCachingEnabled() && idDef != null)
-               return idDef;
+        // use a local reference to the cached identifier definition because 
the
+        // member variable might change in another thread between checking for
+        // null and returning the value
+        IDefinition cachedIdDef = idDef;
+       if (DefinitionBase.getPerformanceCachingEnabled() && cachedIdDef != 
null)
+               return cachedIdDef;
        
         ASScope asScope = getASScope();
 
@@ -451,7 +456,8 @@ public class IdentifierNode extends ExpressionNodeBase 
implements IIdentifierNod
                        ((RoyaleProject)project).addToAPIReport(result);
         }
         
-        idDef = result;
+        if (DefinitionBase.getPerformanceCachingEnabled())
+            idDef = result;
         return result;
     }
 

Reply via email to