From 520741cc565d09791208aa28dbf23fcb3d74da9b Mon Sep 17 00:00:00 2001 From: JinhangZhang Date: Mon, 11 Nov 2024 14:18:22 -0500 Subject: [PATCH] Update doPrivilegedWithCombinerHelper function When we try to invoke doPrivilegedWithCombiner function to perform a privileged action under an existing context environment, we are used to construct a new context but ignore the parent context. We should take consideration of a combination of the current and parent context, rather than just choose either the current or the parent. This patch solves a failed case in issue #19499. Issue: #19499 Signed-off-by: Jinhang Zhang --- .../java/security/AccessControlContext.java | 36 +++++++++++++++++++ .../java/security/AccessController.java | 10 ++---- 2 files changed, 39 insertions(+), 7 deletions(-) diff --git a/jcl/src/java.base/share/classes/java/security/AccessControlContext.java b/jcl/src/java.base/share/classes/java/security/AccessControlContext.java index de86aff22a6..245aa87da58 100644 --- a/jcl/src/java.base/share/classes/java/security/AccessControlContext.java +++ b/jcl/src/java.base/share/classes/java/security/AccessControlContext.java @@ -353,6 +353,42 @@ public AccessControlContext(ProtectionDomain[] fromContext) { this.containPrivilegedContext = true; } +AccessControlContext(ProtectionDomain[] pdArray, AccessControlContext parentAcc, AccessControlContext context, int authorizeState) { + super(); + switch (authorizeState) { + default: + // authorizeState can't be STATE_UNKNOWN, callerPD always is NULL + throw new IllegalArgumentException(); + case STATE_AUTHORIZED: + if (context != null) { + if (parentAcc == null) { + // inherit the domain combiner when authorized + this.domainCombiner = context.domainCombiner; + } else { + // when parent combiner is not null, use parent combiner to combine the current context + DomainCombiner parentAccCombiner = parentAcc.getCombiner(); + if (parentAccCombiner != null) { + this.context = parentAccCombiner.combine(pdArray, context.context); + this.domainCombiner = parentAccCombiner; + } else { + this.context = combinePDObjs(pdArray, context.context); + this.domainCombiner = context.domainCombiner; + } + } + } else { + this.domainCombiner = parentAcc.domainCombiner; + this.context = pdArray; + this.nextStackAcc = parentAcc; + } + break; + case STATE_NOT_AUTHORIZED: + break; + } + this.doPrivilegedAcc = context; + this.authorizeState = authorizeState; + this.containPrivilegedContext = true; +} + /** * Constructs a new instance of this class given a context * and a DomainCombiner diff --git a/jcl/src/java.base/share/classes/java/security/AccessController.java b/jcl/src/java.base/share/classes/java/security/AccessController.java index 8bb613bccbb..1d6d133d90d 100644 --- a/jcl/src/java.base/share/classes/java/security/AccessController.java +++ b/jcl/src/java.base/share/classes/java/security/AccessController.java @@ -1096,13 +1096,9 @@ public static T doPrivilegedWithCombiner(PrivilegedExceptionAction action private static AccessControlContext doPrivilegedWithCombinerHelper(AccessControlContext context) { ProtectionDomain domain = getCallerPD(2); ProtectionDomain[] pdArray = (domain == null) ? null : new ProtectionDomain[] { domain }; - AccessControlContext fixedContext = new AccessControlContext(context, pdArray, getNewAuthorizedState(context, domain)); - if (context == null) { - AccessControlContext parentContext = getContextHelper(true); - fixedContext.domainCombiner = parentContext.domainCombiner; - fixedContext.nextStackAcc = parentContext; - } - return fixedContext; + AccessControlContext parentContext = getContextHelper(context == null); + + return new AccessControlContext(pdArray, parentContext, context, getNewAuthorizedState(context, domain)); } /*[ENDIF] JAVA_SPEC_VERSION < 24 */