diff options
| author | The Android Open Source Project <initial-contribution@android.com> | 2008-12-17 18:03:55 -0800 |
|---|---|---|
| committer | The Android Open Source Project <initial-contribution@android.com> | 2008-12-17 18:03:55 -0800 |
| commit | 89c1feb0a69a7707b271086e749975b3f7acacf7 (patch) | |
| tree | 003624a03635e05020a47fc72a2c42934e3f0703 /libcore/security-kernel | |
| parent | 2ad60cfc28e14ee8f0bb038720836a4696c478ad (diff) | |
| download | android_dalvik-89c1feb0a69a7707b271086e749975b3f7acacf7.tar.gz android_dalvik-89c1feb0a69a7707b271086e749975b3f7acacf7.tar.bz2 android_dalvik-89c1feb0a69a7707b271086e749975b3f7acacf7.zip | |
Code drop from //branches/cupcake/...@124589
Diffstat (limited to 'libcore/security-kernel')
| -rw-r--r-- | libcore/security-kernel/src/main/java/java/security/AccessControlContext.java | 150 | ||||
| -rw-r--r-- | libcore/security-kernel/src/main/java/java/security/AccessController.java | 233 |
2 files changed, 298 insertions, 85 deletions
diff --git a/libcore/security-kernel/src/main/java/java/security/AccessControlContext.java b/libcore/security-kernel/src/main/java/java/security/AccessControlContext.java index 22b1a306b..f9d883a71 100644 --- a/libcore/security-kernel/src/main/java/java/security/AccessControlContext.java +++ b/libcore/security-kernel/src/main/java/java/security/AccessControlContext.java @@ -1,31 +1,44 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ /* - * Licensed to the Apache Software Foundation (ASF) under one or more - * contributor license agreements. See the NOTICE file distributed with - * this work for additional information regarding copyright ownership. - * The ASF licenses this file to You under the Apache License, Version 2.0 - * (the "License"); you may not use this file except in compliance with - * the License. You may obtain a copy of the License at + * Copyright (C) 2008 The Android Open Source Project * - * http://www.apache.org/licenses/LICENSE-2.0 + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. */ -/** -* @author Alexander V. Astapchuk -* @version $Revision: 1.1.2.2.4.3 $ -*/ package java.security; -import java.util.ArrayList; import org.apache.harmony.security.fortress.PolicyUtils; +import java.util.ArrayList; + /** - * @com.intel.drl.spec_ref + * {@code AccessControlContext} encapsulates the {@code ProtectionDomain}s on + * which access control decisions are based. */ public final class AccessControlContext { @@ -33,7 +46,7 @@ public final class AccessControlContext { // It has the following characteristics: // - 'context' can not be null // - never contains null(s) - // - all elements are uniq (no dups) + // - all elements are unique (no dups) ProtectionDomain[] context; DomainCombiner combiner; @@ -42,7 +55,25 @@ public final class AccessControlContext { private AccessControlContext inherited; /** - * @com.intel.drl.spec_ref + * Constructs a new instance of {@code AccessControlContext} with the + * specified {@code AccessControlContext} and {@code DomainCombiner}. + * <p> + * If a {@code SecurityManager} is installed, code calling this constructor + * need the {@code SecurityPermission} {@code createAccessControlContext} to + * be granted, otherwise a {@code SecurityException} will be thrown. + * + * @param acc + * the {@code AccessControlContext} related to the given {@code + * DomainCombiner} + * @param combiner + * the {@code DomainCombiner} related to the given {@code + * AccessControlContext} + * @throws SecurityException + * if a {@code SecurityManager} is installed and the caller does + * not have permission to invoke this constructor + * @throws NullPointerException + * if {@code acc} is {@code null} + * @since Android 1.0 */ public AccessControlContext(AccessControlContext acc, DomainCombiner combiner) { @@ -57,7 +88,15 @@ public final class AccessControlContext { } /** - * @com.intel.drl.spec_ref + * Constructs a new instance of {@code AccessControlContext} with the + * specified array of {@code ProtectionDomain}s. + * + * @param context + * the {@code ProtectionDomain}s that are used to perform access + * checks in the context of this {@code AccessControlContext} + * @throws NullPointerException + * if {@code context} is {@code null} + * @since Android 1.0 */ public AccessControlContext(ProtectionDomain[] context) { if (context == null) { @@ -112,7 +151,7 @@ public final class AccessControlContext { * </li> * * @param stack - array of ProtectionDomains - * @param inherited - inherited context, which may be null + * @param combiner - combiner */ AccessControlContext(ProtectionDomain[] stack, DomainCombiner combiner) { @@ -121,7 +160,32 @@ public final class AccessControlContext { } /** - * @com.intel.drl.spec_ref + * Checks the specified permission against the vm's current security policy. + * The check is based on this {@code AccessControlContext} as opposed to the + * {@link AccessController#checkPermission(Permission)} method which + * performs access checks based on the context of the current thread. This + * method returns silently if the permission is granted, otherwise an + * {@code AccessControlException} is thrown. + * <p> + * A permission is considered granted if every {@link ProtectionDomain} in + * this context has been granted the specified permission. + * <p> + * If privileged operations are on the call stack, only the {@code + * ProtectionDomain}s from the last privileged operation are taken into + * account. + * <p> + * If inherited methods are on the call stack, the protection domains of the + * declaring classes are checked, not the protection domains of the classes + * on which the method is invoked. + * + * @param perm + * the permission to check against the policy + * @throws AccessControlException + * if the specified permission is not granted + * @throws NullPointerException + * if the specified permission is {@code null} + * @see AccessController#checkPermission(Permission) + * @since Android 1.0 */ public void checkPermission(Permission perm) throws AccessControlException { if (perm == null) { @@ -138,9 +202,22 @@ public final class AccessControlContext { } } + /** - * @com.intel.drl.spec_ref + * Compares the specified object with this {@code AccessControlContext} for + * equality. Returns {@code true} if the specified object is also an + * instance of {@code AccessControlContext}, and the two contexts + * encapsulate the same {@code ProtectionDomain}s. The order of the {@code + * ProtectionDomain}s is ignored by this method. + * + * @param obj + * object to be compared for equality with this {@code + * AccessControlContext} + * @return {@code true} if the specified object is equal to this {@code + * AccessControlContext}, otherwise {@code false} + * @since Android 1.0 */ + @Override public boolean equals(Object obj) { if (this == obj) { return true; @@ -159,7 +236,19 @@ public final class AccessControlContext { } /** - * @com.intel.drl.spec_ref + * Returns the {@code DomainCombiner} associated with this {@code + * AccessControlContext}. + * <p> + * If a {@code SecurityManager} is installed, code calling this method needs + * the {@code SecurityPermission} {@code getDomainCombiner} to be granted, + * otherwise a {@code SecurityException} will be thrown. + * + * @return the {@code DomainCombiner} associated with this {@code + * AccessControlContext} + * @throws SecurityException + * if a {@code SecurityManager} is installed and the caller does + * not have permission to invoke this method + * @since Android 1.0 */ public DomainCombiner getDomainCombiner() { SecurityManager sm = System.getSecurityManager(); @@ -169,8 +258,17 @@ public final class AccessControlContext { return combiner; } + /** - * @com.intel.drl.spec_ref + * Returns the hash code value for this {@code AccessControlContext}. + * Returns the same hash code for {@code AccessControlContext}s that are + * equal to each other as required by the general contract of + * {@link Object#hashCode}. + * + * @return the hash code value for this {@code AccessControlContext} + * @see Object#equals(Object) + * @see AccessControlContext#equals(Object) + * @since Android 1.0 */ public int hashCode() { int hash = 0; diff --git a/libcore/security-kernel/src/main/java/java/security/AccessController.java b/libcore/security-kernel/src/main/java/java/security/AccessController.java index c504fc86a..5c5bc262d 100644 --- a/libcore/security-kernel/src/main/java/java/security/AccessController.java +++ b/libcore/security-kernel/src/main/java/java/security/AccessController.java @@ -1,18 +1,33 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ /* - * Licensed to the Apache Software Foundation (ASF) under one or more - * contributor license agreements. See the NOTICE file distributed with - * this work for additional information regarding copyright ownership. - * The ASF licenses this file to You under the Apache License, Version 2.0 - * (the "License"); you may not use this file except in compliance with - * the License. You may obtain a copy of the License at + * Copyright (C) 2008 The Android Open Source Project * - * http://www.apache.org/licenses/LICENSE-2.0 + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. */ package java.security; @@ -23,28 +38,44 @@ import java.util.WeakHashMap; import org.apache.harmony.security.fortress.SecurityUtils; /** - * @com.intel.drl.spec_ref + * {@code AccessController} provides static methods to perform access control + * checks and privileged operations. */ public final class AccessController { private AccessController() { throw new Error("statics only."); - }; + } /** * A map used to store a mapping between a given Thread and * AccessControllerContext-s used in successive calls of doPrivileged(). A * WeakHashMap is used to allow automagical wiping of the dead threads from * the map. The thread (normally Thread.currentThread()) is used as a key - * for the map, and a value is ArrayList where all AccessControlContext-s are - * stored. ((ArrayList)contexts.get(Thread.currentThread())).lastElement() - - * is reference to the latest context passed to the doPrivileged() call. + * for the map, and a value is ArrayList where all AccessControlContext-s + * are stored. + * ((ArrayList)contexts.get(Thread.currentThread())).lastElement() - is + * reference to the latest context passed to the doPrivileged() call. */ - private static final WeakHashMap<Thread, ArrayList<AccessControlContext>> - contexts = new WeakHashMap<Thread, ArrayList<AccessControlContext>>(); - + private static final WeakHashMap<Thread, ArrayList<AccessControlContext>> contexts = new WeakHashMap<Thread, ArrayList<AccessControlContext>>(); + /** - * @com.intel.drl.spec_ref + * Returns the result of executing the specified privileged action. Only the + * {@code ProtectionDomain} of the direct caller of this method and the + * {@code ProtectionDomain}s of all subsequent classes in the call chain are + * checked to be granted the necessary permission if access checks are + * performed. + * <p> + * If an instance of {@code RuntimeException} is thrown during the execution + * of the {@code PrivilegedAction#run()} method of the given action, it will + * be propagated through this method. + * + * @param action + * the action to be executed with privileges + * @return the result of executing the privileged action + * @throws NullPointerException + * if the specified action is {@code null} + * @since Android 1.0 */ public static <T> T doPrivileged(PrivilegedAction<T> action) { if (action == null) { @@ -54,7 +85,25 @@ public final class AccessController { } /** - * @com.intel.drl.spec_ref + * Returns the result of executing the specified privileged action. The + * {@code ProtectionDomain} of the direct caller of this method, the {@code + * ProtectionDomain}s of all subsequent classes in the call chain and all + * {@code ProtectionDomain}s of the given context are checked to be granted + * the necessary permission if access checks are performed. + * <p> + * If an instance of {@code RuntimeException} is thrown during the execution + * of the {@code PrivilegedAction#run()} method of the given action, it will + * be propagated through this method. + * + * @param action + * the action to be executed with privileges + * @param context + * the {@code AccessControlContext} whose protection domains are + * checked additionally + * @return the result of executing the privileged action + * @throws NullPointerException + * if the specified action is {@code null} + * @since Android 1.0 */ public static <T> T doPrivileged(PrivilegedAction<T> action, AccessControlContext context) { @@ -65,7 +114,27 @@ public final class AccessController { } /** - * @com.intel.drl.spec_ref + * Returns the result of executing the specified privileged action. Only the + * {@code ProtectionDomain} of the direct caller of this method and the + * {@code ProtectionDomain}s of all subsequent classes in the call chain are + * checked to be granted the necessary permission if access checks are + * performed. + * <p> + * If a checked exception is thrown by the action's run method, it will be + * wrapped and propagated through this method. + * <p> + * If an instance of {@code RuntimeException} is thrown during the execution + * of the {@code PrivilegedAction#run()} method of the given action, it will + * be propagated through this method. + * + * @param action + * the action to be executed with privileges + * @return the result of executing the privileged action + * @throws PrivilegedActionException + * if the action's run method throws any checked exception + * @throws NullPointerException + * if the specified action is {@code null} + * @since Android 1.0 */ public static <T> T doPrivileged(PrivilegedExceptionAction<T> action) throws PrivilegedActionException { @@ -76,7 +145,30 @@ public final class AccessController { } /** - * @com.intel.drl.spec_ref + * Returns the result of executing the specified privileged action. The + * {@code ProtectionDomain} of the direct caller of this method, the {@code + * ProtectionDomain}s of all subsequent classes in the call chain and all + * {@code ProtectionDomain}s of the given context are checked to be granted + * the necessary permission if access checks are performed. + * <p> + * If a checked exception is thrown by the action's run method, it will be + * wrapped and propagated through this method. + * <p> + * If an instance of {@code RuntimeException} is thrown during the execution + * of the {@code PrivilegedAction#run()} method of the given action, it will + * be propagated through this method. + * + * @param action + * the action to be executed with privileges + * @param context + * the {@code AccessControlContext} whose protection domains are + * checked additionally + * @return the result of executing the privileged action + * @throws PrivilegedActionException + * if the action's run method throws any checked exception + * @throws NullPointerException + * if the specified action is {@code null} + * @since Android 1.0 */ public static <T> T doPrivileged(PrivilegedExceptionAction<T> action, AccessControlContext context) throws PrivilegedActionException { @@ -87,11 +179,10 @@ public final class AccessController { } /** - * The real implementation of doPrivileged() method.<br> - * It pushes the passed context into this thread's contexts stack, - * and then invokes <code>action.run()</code>.<br> - * The pushed context is then investigated in the {@link getContext()} - * which is called in the {@link checkPermission}. + * The real implementation of doPrivileged() method. It pushes the passed + * context into this thread's contexts stack, and then invokes + * <code>action.run()</code>. The pushed context is then investigated in the + * {@link #getContext()} which is called in the {@link #checkPermission}. */ private static <T> T doPrivilegedImpl(PrivilegedExceptionAction<T> action, AccessControlContext context) throws PrivilegedActionException { @@ -114,7 +205,7 @@ public final class AccessController { return action.run(); } catch (Exception ex) { - // Errors automagically go throught - they are not catched by this + // Errors automagically go through - they are not catched by this // block // Unchecked exceptions must pass through without modification @@ -126,7 +217,7 @@ public final class AccessController { throw new PrivilegedActionException(ex); } finally { if (currThread != null) { - // No need to sync() here, as each given 'a' will be accessed + // No need to sync() here, as each given 'a' will be accessed // only from one Thread. 'contexts' still need sync() however, // as it's accessed from different threads simultaneously if (a != null) { @@ -139,10 +230,10 @@ public final class AccessController { /** * The real implementation of appropriate doPrivileged() method.<br> - * It pushes the passed context into this thread's stack of contexts and + * It pushes the passed context into this thread's stack of contexts and * then invokes <code>action.run()</code>.<br> - * The pushed context is then investigated in the {@link getContext()} - * which is called in the {@link checkPermission}. + * The pushed context is then investigated in the {@link #getContext()} + * which is called in the {@link #checkPermission}. */ private static <T> T doPrivilegedImpl(PrivilegedAction<T> action, AccessControlContext context) { @@ -151,10 +242,10 @@ public final class AccessController { if (currThread == null || contexts == null) { // Big boom time - VM is starting... No need to check permissions: - // 1st, I do believe there is no malicious code available here for + // 1st, I do believe there is no malicious code available here for // this moment - // 2d, I cant use currentThread() as a key anyway - when it will - // turn into the real Thread, I'll be unable to retrieve the value + // 2d, I cant use currentThread() as a key anyway - when it will + // turn into the real Thread, I'll be unable to retrieve the value // stored with 'currThread==null' as a key. return action.run(); } @@ -173,7 +264,7 @@ public final class AccessController { return action.run(); } finally { - // No need to sync() here, as each given 'a' will be accessed + // No need to sync() here, as each given 'a' will be accessed // only from one Thread. 'contexts' still need sync() however, // as it's accessed from different threads simultaneously if (a != null) { @@ -183,7 +274,30 @@ public final class AccessController { } /** - * @com.intel.drl.spec_ref + * Checks the specified permission against the vm's current security policy. + * The check is performed in the context of the current thread. This method + * returns silently if the permission is granted, otherwise an {@code + * AccessControlException} is thrown. + * <p> + * A permission is considered granted if every {@link ProtectionDomain} in + * the current execution context has been granted the specified permission. + * If privileged operations are on the execution context, only the {@code + * ProtectionDomain}s from the last privileged operation are taken into + * account. + * <p> + * This method delegates the permission check to + * {@link AccessControlContext#checkPermission(Permission)} on the current + * callers' context obtained by {@link #getContext()}. + * + * @param perm + * the permission to check against the policy + * @throws AccessControlException + * if the specified permission is not granted + * @throws NullPointerException + * if the specified permission is {@code null} + * @see AccessControlContext#checkPermission(Permission) + * + * @since Android 1.0 */ public static void checkPermission(Permission perm) throws AccessControlException { @@ -195,25 +309,34 @@ public final class AccessController { } /** - * Returns array of ProtectionDomains from the classes residing - * on the stack of the current thread, up to and including the caller - * of the nearest privileged frame. Reflection frames are skipped. - * The returned array is never null and never contains null elements, - * meaning that bootstrap classes are effectively ignored. + * Returns array of ProtectionDomains from the classes residing on the stack + * of the current thread, up to and including the caller of the nearest + * privileged frame. Reflection frames are skipped. The returned array is + * never null and never contains null elements, meaning that bootstrap + * classes are effectively ignored. */ private static native ProtectionDomain[] getStackDomains(); - + /** - * @com.intel.drl.spec_ref + * Returns the {@code AccessControlContext} for the current {@code Thread} + * including the inherited access control context of the thread that spawned + * the current thread (recursively). + * <p> + * The returned context may be used to perform access checks at a later + * point in time, possibly by another thread. + * + * @return the {@code AccessControlContext} for the current {@code Thread} + * @see Thread#currentThread + * @since Android 1.0 */ public static AccessControlContext getContext() { // duplicates (if any) will be removed in ACC constructor ProtectionDomain[] stack = getStackDomains(); - + Thread currThread = Thread.currentThread(); if (currThread == null || contexts == null) { - // Big boo time. No need to check anything ? + // Big boo time. No need to check anything ? return new AccessControlContext(stack); } @@ -221,7 +344,7 @@ public final class AccessController { synchronized (contexts) { threadContexts = contexts.get(currThread); } - + AccessControlContext that; if ((threadContexts == null) || (threadContexts.size() == 0)) { // We were not in doPrivileged method, so @@ -236,9 +359,8 @@ public final class AccessController { if (that != null && that.combiner != null) { ProtectionDomain[] assigned = null; if (that.context != null && that.context.length != 0) { - assigned = new ProtectionDomain[that.context.length]; - System.arraycopy(that.context, 0, assigned, 0, - assigned.length); + assigned = new ProtectionDomain[that.context.length]; + System.arraycopy(that.context, 0, assigned, 0, assigned.length); } ProtectionDomain[] allpds = that.combiner.combine(stack, assigned); if (allpds == null) { @@ -249,11 +371,4 @@ public final class AccessController { return new AccessControlContext(stack, that); } - - /* - * TEMPORARY, used for testing implementation. - */ - //public static ProtectionDomain[] testStackDomains() { - // return getStackDomains(); - //} } |
