diff --git a/src/java.base/share/classes/java/io/ObjectInputFilter.java b/src/java.base/share/classes/java/io/ObjectInputFilter.java
index 9a04e1f58e3..9232111de07 100644
--- a/src/java.base/share/classes/java/io/ObjectInputFilter.java
+++ b/src/java.base/share/classes/java/io/ObjectInputFilter.java
@@ -29,8 +29,6 @@ import jdk.internal.access.SharedSecrets;
 import jdk.internal.util.StaticProperty;
 
 import java.lang.reflect.InvocationTargetException;
-import java.security.AccessController;
-import java.security.PrivilegedAction;
 import java.security.Security;
 import java.util.ArrayList;
 import java.util.List;
@@ -630,17 +628,13 @@ public interface ObjectInputFilter {
             configLog = System.getLogger("java.io.serialization");
 
             // Get the values of the system properties, if they are defined
-            @SuppressWarnings("removal")
             String factoryClassName = StaticProperty.jdkSerialFilterFactory() != null
                     ? StaticProperty.jdkSerialFilterFactory()
-                    : AccessController.doPrivileged((PrivilegedAction<String>) () ->
-                        Security.getProperty(SERIAL_FILTER_FACTORY_PROPNAME));
+                    : Security.getProperty(SERIAL_FILTER_FACTORY_PROPNAME);
 
-            @SuppressWarnings("removal")
             String filterString = StaticProperty.jdkSerialFilter() != null
                     ? StaticProperty.jdkSerialFilter()
-                    : AccessController.doPrivileged((PrivilegedAction<String>) () ->
-                        Security.getProperty(SERIAL_FILTER_PROPNAME));
+                    : Security.getProperty(SERIAL_FILTER_PROPNAME);
 
             // Initialize the static filter if the jdk.serialFilter is present
             String filterMessage = null;
@@ -734,11 +728,6 @@ public interface ObjectInputFilter {
          */
         public static void setSerialFilter(ObjectInputFilter filter) {
             Objects.requireNonNull(filter, "filter");
-            @SuppressWarnings("removal")
-            SecurityManager sm = System.getSecurityManager();
-            if (sm != null) {
-                sm.checkPermission(ObjectStreamConstants.SERIAL_FILTER_PERMISSION);
-            }
             if (invalidFilterMessage != null) {
                 throw new IllegalStateException(invalidFilterMessage);
             }
@@ -831,11 +820,6 @@ public interface ObjectInputFilter {
          */
         public static void setSerialFilterFactory(BinaryOperator<ObjectInputFilter> filterFactory) {
             Objects.requireNonNull(filterFactory, "filterFactory");
-            @SuppressWarnings("removal")
-            SecurityManager sm = System.getSecurityManager();
-            if (sm != null) {
-                sm.checkPermission(ObjectStreamConstants.SERIAL_FILTER_PERMISSION);
-            }
             if (filterFactoryNoReplace.getAndSet(true)) {
                 final String msg = serialFilterFactory != null
                         ? "Cannot replace filter factory: " + serialFilterFactory.getClass().getName()
diff --git a/src/java.base/share/classes/java/io/ObjectInputStream.java b/src/java.base/share/classes/java/io/ObjectInputStream.java
index 60d8cadf6a3..31d0aecf831 100644
--- a/src/java.base/share/classes/java/io/ObjectInputStream.java
+++ b/src/java.base/share/classes/java/io/ObjectInputStream.java
@@ -34,13 +34,7 @@ import java.lang.reflect.InvocationHandler;
 import java.lang.reflect.Modifier;
 import java.lang.reflect.Proxy;
 import java.nio.charset.StandardCharsets;
-import java.security.AccessControlContext;
-import java.security.AccessController;
-import java.security.PrivilegedAction;
-import java.security.PrivilegedActionException;
-import java.security.PrivilegedExceptionAction;
 import java.util.Arrays;
-import java.util.Map;
 import java.util.Objects;
 
 import jdk.internal.access.JavaLangAccess;
@@ -49,8 +43,6 @@ import jdk.internal.event.DeserializationEvent;
 import jdk.internal.misc.Unsafe;
 import jdk.internal.util.ByteArray;
 import sun.reflect.misc.ReflectUtil;
-import sun.security.action.GetBooleanAction;
-import sun.security.action.GetIntegerAction;
 
 /**
  * An ObjectInputStream deserializes primitive data and objects previously
@@ -278,8 +270,8 @@ public class ObjectInputStream
          * have been read.
          * See {@link #setObjectInputFilter(ObjectInputFilter)}
          */
-        static final boolean SET_FILTER_AFTER_READ = GetBooleanAction
-                .privilegedGetProperty("jdk.serialSetFilterAfterRead");
+        static final boolean SET_FILTER_AFTER_READ =
+                Boolean.getBoolean("jdk.serialSetFilterAfterRead");
 
         /**
          * Property to control {@link GetField#get(String, Object)} conversion of
@@ -287,8 +279,8 @@ public class ObjectInputStream
          * {@link GetField#get(String, Object)} returns null otherwise
          * throwing {@link ClassNotFoundException}.
          */
-        private static final boolean GETFIELD_CNFE_RETURNS_NULL = GetBooleanAction
-                .privilegedGetProperty("jdk.serialGetFieldCnfeReturnsNull");
+        private static final boolean GETFIELD_CNFE_RETURNS_NULL =
+                Boolean.getBoolean("jdk.serialGetFieldCnfeReturnsNull");
 
         /**
          * Property to override the implementation limit on the number
@@ -296,8 +288,8 @@ public class ObjectInputStream
          * The maximum number of interfaces allowed for a proxy is limited to 65535 by
          * {@link java.lang.reflect.Proxy#newProxyInstance(ClassLoader, Class[], InvocationHandler)}.
          */
-        static final int PROXY_INTERFACE_LIMIT = Math.clamp(GetIntegerAction
-                .privilegedGetProperty("jdk.serialProxyInterfaceLimit", 65535), 0, 65535);
+        static final int PROXY_INTERFACE_LIMIT =
+                Math.clamp(Integer.getInteger("jdk.serialProxyInterfaceLimit", 65535), 0, 65535);
     }
 
     /*
@@ -386,7 +378,6 @@ public class ObjectInputStream
      */
     @SuppressWarnings("this-escape")
     public ObjectInputStream(InputStream in) throws IOException {
-        verifySubclass();
         bin = new BlockDataInputStream(in);
         handles = new HandleTable(10);
         vlist = new ValidationList();
@@ -416,11 +407,6 @@ public class ObjectInputStream
      *      fails due to invalid serial filter or serial filter factory properties.
      */
     protected ObjectInputStream() throws IOException {
-        @SuppressWarnings("removal")
-        SecurityManager sm = System.getSecurityManager();
-        if (sm != null) {
-            sm.checkPermission(SUBCLASS_IMPLEMENTATION_PERMISSION);
-        }
         bin = null;
         handles = null;
         vlist = null;
@@ -907,13 +893,6 @@ public class ObjectInputStream
         if (enable == enableResolve) {
             return enable;
         }
-        if (enable) {
-            @SuppressWarnings("removal")
-            SecurityManager sm = System.getSecurityManager();
-            if (sm != null) {
-                sm.checkPermission(SUBSTITUTION_PERMISSION);
-            }
-        }
         enableResolve = enable;
         return !enableResolve;
     }
@@ -1309,11 +1288,6 @@ public class ObjectInputStream
      * @since 9
      */
     public final void setObjectInputFilter(ObjectInputFilter filter) {
-        @SuppressWarnings("removal")
-        SecurityManager sm = System.getSecurityManager();
-        if (sm != null) {
-            sm.checkPermission(ObjectStreamConstants.SERIAL_FILTER_PERMISSION);
-        }
         if (totalObjectRefs > 0 && !Caches.SET_FILTER_AFTER_READ) {
             throw new IllegalStateException(
                     "filter can not be set after an object has been read");
@@ -1571,58 +1545,29 @@ public class ObjectInputStream
         public abstract Object get(String name, Object val) throws IOException, ClassNotFoundException;
     }
 
-    /**
-     * Verifies that this (possibly subclass) instance can be constructed
-     * without violating security constraints: the subclass must not override
-     * security-sensitive non-final methods, or else the
-     * "enableSubclassImplementation" SerializablePermission is checked.
-     */
-    private void verifySubclass() {
-        Class<?> cl = getClass();
-        if (cl == ObjectInputStream.class) {
-            return;
-        }
-        @SuppressWarnings("removal")
-        SecurityManager sm = System.getSecurityManager();
-        if (sm == null) {
-            return;
-        }
-        boolean result = Caches.subclassAudits.get(cl);
-        if (!result) {
-            sm.checkPermission(SUBCLASS_IMPLEMENTATION_PERMISSION);
-        }
-    }
-
     /**
      * Performs reflective checks on given subclass to verify that it doesn't
      * override security-sensitive non-final methods.  Returns TRUE if subclass
      * is "safe", FALSE otherwise.
      */
-    @SuppressWarnings("removal")
     private static Boolean auditSubclass(Class<?> subcl) {
-        return AccessController.doPrivileged(
-            new PrivilegedAction<Boolean>() {
-                public Boolean run() {
-                    for (Class<?> cl = subcl;
-                         cl != ObjectInputStream.class;
-                         cl = cl.getSuperclass())
-                    {
-                        try {
-                            cl.getDeclaredMethod(
-                                "readUnshared", (Class[]) null);
-                            return Boolean.FALSE;
-                        } catch (NoSuchMethodException ex) {
-                        }
-                        try {
-                            cl.getDeclaredMethod("readFields", (Class[]) null);
-                            return Boolean.FALSE;
-                        } catch (NoSuchMethodException ex) {
-                        }
-                    }
-                    return Boolean.TRUE;
-                }
+        for (Class<?> cl = subcl;
+             cl != ObjectInputStream.class;
+             cl = cl.getSuperclass())
+        {
+            try {
+                cl.getDeclaredMethod(
+                    "readUnshared", (Class[]) null);
+                return Boolean.FALSE;
+            } catch (NoSuchMethodException ex) {
             }
-        );
+            try {
+                cl.getDeclaredMethod("readFields", (Class[]) null);
+                return Boolean.FALSE;
+            } catch (NoSuchMethodException ex) {
+            }
+        }
+        return Boolean.TRUE;
     }
 
     /**
@@ -2702,16 +2647,11 @@ public class ObjectInputStream
             final ObjectInputValidation obj;
             final int priority;
             Callback next;
-            @SuppressWarnings("removal")
-            final AccessControlContext acc;
 
-            Callback(ObjectInputValidation obj, int priority, Callback next,
-                @SuppressWarnings("removal") AccessControlContext acc)
-            {
+            Callback(ObjectInputValidation obj, int priority, Callback next) {
                 this.obj = obj;
                 this.priority = priority;
                 this.next = next;
-                this.acc = acc;
             }
         }
 
@@ -2740,12 +2680,10 @@ public class ObjectInputStream
                 prev = cur;
                 cur = cur.next;
             }
-            @SuppressWarnings("removal")
-            AccessControlContext acc = AccessController.getContext();
             if (prev != null) {
-                prev.next = new Callback(obj, priority, cur, acc);
+                prev.next = new Callback(obj, priority, cur);
             } else {
-                list = new Callback(obj, priority, list, acc);
+                list = new Callback(obj, priority, list);
             }
         }
 
@@ -2756,23 +2694,15 @@ public class ObjectInputStream
          * throws an InvalidObjectException, the callback process is terminated
          * and the exception propagated upwards.
          */
-        @SuppressWarnings("removal")
         void doCallbacks() throws InvalidObjectException {
             try {
                 while (list != null) {
-                    AccessController.doPrivileged(
-                        new PrivilegedExceptionAction<Void>()
-                    {
-                        public Void run() throws InvalidObjectException {
-                            list.obj.validateObject();
-                            return null;
-                        }
-                    }, list.acc);
+                    list.obj.validateObject();
                     list = list.next;
                 }
-            } catch (PrivilegedActionException ex) {
+            } catch (InvalidObjectException ex) {
                 list = null;
-                throw (InvalidObjectException) ex.getException();
+                throw ex;
             }
         }
 
diff --git a/src/java.base/share/classes/java/io/ObjectOutputStream.java b/src/java.base/share/classes/java/io/ObjectOutputStream.java
index 429c91ab673..5225c673705 100644
--- a/src/java.base/share/classes/java/io/ObjectOutputStream.java
+++ b/src/java.base/share/classes/java/io/ObjectOutputStream.java
@@ -26,8 +26,6 @@
 
 package java.io;
 
-import java.security.AccessController;
-import java.security.PrivilegedAction;
 import java.util.ArrayList;
 import java.util.Arrays;
 import java.util.List;
@@ -224,11 +222,8 @@ public class ObjectOutputStream
      * value of "sun.io.serialization.extendedDebugInfo" property,
      * as true or false for extended information about exception's place
      */
-    @SuppressWarnings("removal")
     private static final boolean extendedDebugInfo =
-        java.security.AccessController.doPrivileged(
-            new sun.security.action.GetBooleanAction(
-                "sun.io.serialization.extendedDebugInfo")).booleanValue();
+            Boolean.getBoolean("sun.io.serialization.extendedDebugInfo");
 
     /**
      * Creates an ObjectOutputStream that writes to the specified OutputStream.
@@ -247,7 +242,6 @@ public class ObjectOutputStream
      */
     @SuppressWarnings("this-escape")
     public ObjectOutputStream(OutputStream out) throws IOException {
-        verifySubclass();
         bout = new BlockDataOutputStream(out);
         handles = new HandleTable(10, (float) 3.00);
         subs = new ReplaceTable(10, (float) 3.00);
@@ -269,11 +263,6 @@ public class ObjectOutputStream
      * @throws  IOException if an I/O error occurs while creating this stream
      */
     protected ObjectOutputStream() throws IOException {
-        @SuppressWarnings("removal")
-        SecurityManager sm = System.getSecurityManager();
-        if (sm != null) {
-            sm.checkPermission(SUBCLASS_IMPLEMENTATION_PERMISSION);
-        }
         bout = null;
         handles = null;
         subs = null;
@@ -595,13 +584,6 @@ public class ObjectOutputStream
         if (enable == enableReplace) {
             return enable;
         }
-        if (enable) {
-            @SuppressWarnings("removal")
-            SecurityManager sm = System.getSecurityManager();
-            if (sm != null) {
-                sm.checkPermission(SUBSTITUTION_PERMISSION);
-            }
-        }
         enableReplace = enable;
         return !enableReplace;
     }
@@ -625,8 +607,8 @@ public class ObjectOutputStream
      * stream.  Subclasses of ObjectOutputStream may override this method to
      * customize the way in which class descriptors are written to the
      * serialization stream.  The corresponding method in ObjectInputStream,
-     * {@link ObjectInputStream#readClassDescriptor readClassDescriptor}, should then be overridden to
-     * reconstitute the class descriptor from its custom stream representation.
+     * {@link ObjectInputStream#readClassDescriptor readClassDescriptor}, should then be
+     * overridden to reconstitute the class descriptor from its custom stream representation.
      * By default, this method writes class descriptors according to the format
      * defined in the <a href="{@docRoot}/../specs/serialization/index.html">
      * <cite>Java Object Serialization Specification</cite></a>.
@@ -1022,58 +1004,29 @@ public class ObjectOutputStream
         }
     }
 
-    /**
-     * Verifies that this (possibly subclass) instance can be constructed
-     * without violating security constraints: the subclass must not override
-     * security-sensitive non-final methods, or else the
-     * "enableSubclassImplementation" SerializablePermission is checked.
-     */
-    private void verifySubclass() {
-        Class<?> cl = getClass();
-        if (cl == ObjectOutputStream.class) {
-            return;
-        }
-        @SuppressWarnings("removal")
-        SecurityManager sm = System.getSecurityManager();
-        if (sm == null) {
-            return;
-        }
-        boolean result = Caches.subclassAudits.get(cl);
-        if (!result) {
-            sm.checkPermission(SUBCLASS_IMPLEMENTATION_PERMISSION);
-        }
-    }
-
     /**
      * Performs reflective checks on given subclass to verify that it doesn't
      * override security-sensitive non-final methods.  Returns TRUE if subclass
      * is "safe", FALSE otherwise.
      */
-    @SuppressWarnings("removal")
     private static Boolean auditSubclass(Class<?> subcl) {
-        return AccessController.doPrivileged(
-            new PrivilegedAction<>() {
-                public Boolean run() {
-                    for (Class<?> cl = subcl;
-                         cl != ObjectOutputStream.class;
-                         cl = cl.getSuperclass())
-                    {
-                        try {
-                            cl.getDeclaredMethod(
-                                "writeUnshared", new Class<?>[] { Object.class });
-                            return Boolean.FALSE;
-                        } catch (NoSuchMethodException ex) {
-                        }
-                        try {
-                            cl.getDeclaredMethod("putFields", (Class<?>[]) null);
-                            return Boolean.FALSE;
-                        } catch (NoSuchMethodException ex) {
-                        }
-                    }
-                    return Boolean.TRUE;
-                }
+        for (Class<?> cl = subcl;
+             cl != ObjectOutputStream.class;
+             cl = cl.getSuperclass())
+        {
+            try {
+                cl.getDeclaredMethod(
+                    "writeUnshared", new Class<?>[] { Object.class });
+                return Boolean.FALSE;
+            } catch (NoSuchMethodException ex) {
             }
-        );
+            try {
+                cl.getDeclaredMethod("putFields", (Class<?>[]) null);
+                return Boolean.FALSE;
+            } catch (NoSuchMethodException ex) {
+            }
+        }
+        return Boolean.TRUE;
     }
 
     /**
diff --git a/src/java.base/share/classes/java/io/ObjectStreamClass.java b/src/java.base/share/classes/java/io/ObjectStreamClass.java
index 73bb162e843..4fb9847a4e8 100644
--- a/src/java.base/share/classes/java/io/ObjectStreamClass.java
+++ b/src/java.base/share/classes/java/io/ObjectStreamClass.java
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1996, 2023, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1996, 2024, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -32,21 +32,12 @@ import java.lang.reflect.Constructor;
 import java.lang.reflect.Field;
 import java.lang.reflect.InvocationTargetException;
 import java.lang.reflect.RecordComponent;
-import java.lang.reflect.UndeclaredThrowableException;
 import java.lang.reflect.Member;
 import java.lang.reflect.Method;
 import java.lang.reflect.Modifier;
 import java.lang.reflect.Proxy;
-import java.security.AccessControlContext;
-import java.security.AccessController;
 import java.security.MessageDigest;
 import java.security.NoSuchAlgorithmException;
-import java.security.PermissionCollection;
-import java.security.Permissions;
-import java.security.PrivilegedAction;
-import java.security.PrivilegedActionException;
-import java.security.PrivilegedExceptionAction;
-import java.security.ProtectionDomain;
 import java.util.ArrayList;
 import java.util.Arrays;
 import java.util.Collections;
@@ -58,13 +49,8 @@ import java.util.concurrent.ConcurrentHashMap;
 
 import jdk.internal.event.SerializationMisdeclarationEvent;
 import jdk.internal.misc.Unsafe;
-import jdk.internal.reflect.CallerSensitive;
-import jdk.internal.reflect.Reflection;
 import jdk.internal.reflect.ReflectionFactory;
-import jdk.internal.access.SharedSecrets;
-import jdk.internal.access.JavaSecurityAccess;
 import jdk.internal.util.ByteArray;
-import sun.reflect.misc.ReflectUtil;
 
 /**
  * Serialization's descriptor for classes.  It contains the name and
@@ -98,12 +84,6 @@ public final class ObjectStreamClass implements Serializable {
     private static final ObjectStreamField[] serialPersistentFields =
         NO_FIELDS;
 
-    /** reflection factory for obtaining serialization constructors */
-    @SuppressWarnings("removal")
-    private static final ReflectionFactory reflFactory =
-        AccessController.doPrivileged(
-            new ReflectionFactory.GetReflectionFactoryAction());
-
     private static class Caches {
         /** cache mapping local classes -> descriptors */
         static final ClassCache<ObjectStreamClass> localDescs =
@@ -206,8 +186,6 @@ public final class ObjectStreamClass implements Serializable {
     /** session-cache of record deserialization constructor
      * (in de-serialized OSC only), or null */
     private MethodHandle deserializationCtr;
-    /** protection domains that need to be checked when calling the constructor */
-    private ProtectionDomain[] domains;
 
     /** class-defined writeObject method, or null if none */
     private Method writeObjectMethod;
@@ -280,20 +258,13 @@ public final class ObjectStreamClass implements Serializable {
      *
      * @return  the SUID of the class described by this descriptor
      */
-    @SuppressWarnings("removal")
     public long getSerialVersionUID() {
         // REMIND: synchronize instead of relying on volatile?
         if (suid == null) {
             if (isRecord)
                 return 0L;
 
-            suid = AccessController.doPrivileged(
-                new PrivilegedAction<Long>() {
-                    public Long run() {
-                        return computeDefaultSUID(cl);
-                    }
-                }
-            );
+            suid = computeDefaultSUID(cl);
         }
         return suid.longValue();
     }
@@ -304,19 +275,11 @@ public final class ObjectStreamClass implements Serializable {
      *
      * @return  the {@code Class} instance that this descriptor represents
      */
-    @SuppressWarnings("removal")
-    @CallerSensitive
     public Class<?> forClass() {
         if (cl == null) {
             return null;
         }
         requireInitialized();
-        if (System.getSecurityManager() != null) {
-            Class<?> caller = Reflection.getCallerClass();
-            if (ReflectUtil.needsPackageAccessCheck(caller.getClassLoader(), cl.getClassLoader())) {
-                ReflectUtil.checkPackageAccess(cl);
-            }
-        }
         return cl;
     }
 
@@ -369,7 +332,6 @@ public final class ObjectStreamClass implements Serializable {
     /**
      * Creates local class descriptor representing given class.
      */
-    @SuppressWarnings("removal")
     private ObjectStreamClass(final Class<?> cl) {
         this.cl = cl;
         name = cl.getName();
@@ -384,53 +346,44 @@ public final class ObjectStreamClass implements Serializable {
         localDesc = this;
 
         if (serializable) {
-            AccessController.doPrivileged(new PrivilegedAction<>() {
-                public Void run() {
-                    if (isEnum) {
-                        suid = 0L;
-                        fields = NO_FIELDS;
-                        return null;
-                    }
-                    if (cl.isArray()) {
-                        fields = NO_FIELDS;
-                        return null;
-                    }
-
-                    suid = getDeclaredSUID(cl);
-                    try {
-                        fields = getSerialFields(cl);
-                        computeFieldOffsets();
-                    } catch (InvalidClassException e) {
-                        serializeEx = deserializeEx =
+            if (isEnum) {
+                suid = 0L;
+                fields = NO_FIELDS;
+            } else if (cl.isArray()) {
+                fields = NO_FIELDS;
+            } else {
+                suid = getDeclaredSUID(cl);
+                try {
+                    fields = getSerialFields(cl);
+                    computeFieldOffsets();
+                } catch (InvalidClassException e) {
+                    serializeEx = deserializeEx =
                             new ExceptionInfo(e.classname, e.getMessage());
-                        fields = NO_FIELDS;
-                    }
-
-                    if (isRecord) {
-                        canonicalCtr = canonicalRecordCtr(cl);
-                        deserializationCtrs = new DeserializationConstructorsCache();
-                    } else if (externalizable) {
-                        cons = getExternalizableConstructor(cl);
-                    } else {
-                        cons = getSerializableConstructor(cl);
-                        writeObjectMethod = getPrivateMethod(cl, "writeObject",
-                            new Class<?>[] { ObjectOutputStream.class },
-                            Void.TYPE);
-                        readObjectMethod = getPrivateMethod(cl, "readObject",
-                            new Class<?>[] { ObjectInputStream.class },
-                            Void.TYPE);
-                        readObjectNoDataMethod = getPrivateMethod(
-                            cl, "readObjectNoData", null, Void.TYPE);
-                        hasWriteObjectData = (writeObjectMethod != null);
-                    }
-                    domains = getProtectionDomains(cons, cl);
-                    writeReplaceMethod = getInheritableMethod(
-                        cl, "writeReplace", null, Object.class);
-                    readResolveMethod = getInheritableMethod(
-                        cl, "readResolve", null, Object.class);
-                    return null;
+                    fields = NO_FIELDS;
                 }
-            });
+
+                if (isRecord) {
+                    canonicalCtr = canonicalRecordCtr(cl);
+                    deserializationCtrs = new DeserializationConstructorsCache();
+                } else if (externalizable) {
+                    cons = getExternalizableConstructor(cl);
+                } else {
+                    cons = getSerializableConstructor(cl);
+                    writeObjectMethod = getPrivateMethod(cl, "writeObject",
+                            new Class<?>[]{ObjectOutputStream.class},
+                            Void.TYPE);
+                    readObjectMethod = getPrivateMethod(cl, "readObject",
+                            new Class<?>[]{ObjectInputStream.class},
+                            Void.TYPE);
+                    readObjectNoDataMethod = getPrivateMethod(
+                            cl, "readObjectNoData", null, Void.TYPE);
+                    hasWriteObjectData = (writeObjectMethod != null);
+                }
+                writeReplaceMethod = getInheritableMethod(
+                        cl, "writeReplace", null, Object.class);
+                readResolveMethod = getInheritableMethod(
+                        cl, "readResolve", null, Object.class);
+            }
         } else {
             suid = 0L;
             fields = NO_FIELDS;
@@ -474,66 +427,6 @@ public final class ObjectStreamClass implements Serializable {
     ObjectStreamClass() {
     }
 
-    /**
-     * Creates a PermissionDomain that grants no permission.
-     */
-    private ProtectionDomain noPermissionsDomain() {
-        PermissionCollection perms = new Permissions();
-        perms.setReadOnly();
-        return new ProtectionDomain(null, perms);
-    }
-
-    /**
-     * Aggregate the ProtectionDomains of all the classes that separate
-     * a concrete class {@code cl} from its ancestor's class declaring
-     * a constructor {@code cons}.
-     *
-     * If {@code cl} is defined by the boot loader, or the constructor
-     * {@code cons} is declared by {@code cl}, or if there is no security
-     * manager, then this method does nothing and {@code null} is returned.
-     *
-     * @param cons A constructor declared by {@code cl} or one of its
-     *             ancestors.
-     * @param cl A concrete class, which is either the class declaring
-     *           the constructor {@code cons}, or a serializable subclass
-     *           of that class.
-     * @return An array of ProtectionDomain representing the set of
-     *         ProtectionDomain that separate the concrete class {@code cl}
-     *         from its ancestor's declaring {@code cons}, or {@code null}.
-     */
-    @SuppressWarnings("removal")
-    private ProtectionDomain[] getProtectionDomains(Constructor<?> cons,
-                                                    Class<?> cl) {
-        ProtectionDomain[] domains = null;
-        if (cons != null && cl.getClassLoader() != null
-                && System.getSecurityManager() != null) {
-            Class<?> cls = cl;
-            Class<?> fnscl = cons.getDeclaringClass();
-            Set<ProtectionDomain> pds = null;
-            while (cls != fnscl) {
-                ProtectionDomain pd = cls.getProtectionDomain();
-                if (pd != null) {
-                    if (pds == null) pds = new HashSet<>();
-                    pds.add(pd);
-                }
-                cls = cls.getSuperclass();
-                if (cls == null) {
-                    // that's not supposed to happen
-                    // make a ProtectionDomain with no permission.
-                    // should we throw instead?
-                    if (pds == null) pds = new HashSet<>();
-                    else pds.clear();
-                    pds.add(noPermissionsDomain());
-                    break;
-                }
-            }
-            if (pds != null) {
-                domains = pds.toArray(new ProtectionDomain[0]);
-            }
-        }
-        return domains;
-    }
-
     /**
      * Initializes class descriptor representing a proxy class.
      */
@@ -564,7 +457,6 @@ public final class ObjectStreamClass implements Serializable {
             writeReplaceMethod = localDesc.writeReplaceMethod;
             readResolveMethod = localDesc.readResolveMethod;
             deserializeEx = localDesc.deserializeEx;
-            domains = localDesc.domains;
             cons = localDesc.cons;
         }
         fieldRefl = getReflector(fields, localDesc);
@@ -656,7 +548,6 @@ public final class ObjectStreamClass implements Serializable {
             if (deserializeEx == null) {
                 deserializeEx = localDesc.deserializeEx;
             }
-            domains = localDesc.domains;
             assert cl.isRecord() ? localDesc.cons == null : true;
             cons = localDesc.cons;
         }
@@ -1013,7 +904,6 @@ public final class ObjectStreamClass implements Serializable {
      * class is non-serializable or if the appropriate no-arg constructor is
      * inaccessible/unavailable.
      */
-    @SuppressWarnings("removal")
     Object newInstance()
         throws InstantiationException, InvocationTargetException,
                UnsupportedOperationException
@@ -1021,35 +911,7 @@ public final class ObjectStreamClass implements Serializable {
         requireInitialized();
         if (cons != null) {
             try {
-                if (domains == null || domains.length == 0) {
-                    return cons.newInstance();
-                } else {
-                    JavaSecurityAccess jsa = SharedSecrets.getJavaSecurityAccess();
-                    PrivilegedAction<?> pea = () -> {
-                        try {
-                            return cons.newInstance();
-                        } catch (InstantiationException
-                                 | InvocationTargetException
-                                 | IllegalAccessException x) {
-                            throw new UndeclaredThrowableException(x);
-                        }
-                    }; // Can't use PrivilegedExceptionAction with jsa
-                    try {
-                        return jsa.doIntersectionPrivilege(pea,
-                                   AccessController.getContext(),
-                                   new AccessControlContext(domains));
-                    } catch (UndeclaredThrowableException x) {
-                        Throwable cause = x.getCause();
-                        if (cause instanceof InstantiationException ie)
-                            throw ie;
-                        if (cause instanceof InvocationTargetException ite)
-                            throw ite;
-                        if (cause instanceof IllegalAccessException iae)
-                            throw iae;
-                        // not supposed to happen
-                        throw x;
-                    }
-                }
+                return cons.newInstance();
             } catch (IllegalAccessException ex) {
                 // should not occur, as access checks have been suppressed
                 throw new InternalError(ex);
@@ -1454,7 +1316,7 @@ public final class ObjectStreamClass implements Serializable {
      * returned constructor (if any).
      */
     private static Constructor<?> getSerializableConstructor(Class<?> cl) {
-        return reflFactory.newConstructorForSerialization(cl);
+        return ReflectionFactory.getReflectionFactory().newConstructorForSerialization(cl);
     }
 
     /**
@@ -1462,22 +1324,18 @@ public final class ObjectStreamClass implements Serializable {
      * the not found ( which should never happen for correctly generated record
      * classes ).
      */
-    @SuppressWarnings("removal")
     private static MethodHandle canonicalRecordCtr(Class<?> cls) {
         assert cls.isRecord() : "Expected record, got: " + cls;
-        PrivilegedAction<MethodHandle> pa = () -> {
-            Class<?>[] paramTypes = Arrays.stream(cls.getRecordComponents())
-                                          .map(RecordComponent::getType)
-                                          .toArray(Class<?>[]::new);
-            try {
-                Constructor<?> ctr = cls.getDeclaredConstructor(paramTypes);
-                ctr.setAccessible(true);
-                return MethodHandles.lookup().unreflectConstructor(ctr);
-            } catch (IllegalAccessException | NoSuchMethodException e) {
-                return null;
-            }
-        };
-        return AccessController.doPrivileged(pa);
+        Class<?>[] paramTypes = Arrays.stream(cls.getRecordComponents())
+                                      .map(RecordComponent::getType)
+                                      .toArray(Class<?>[]::new);
+        try {
+            Constructor<?> ctr = cls.getDeclaredConstructor(paramTypes);
+            ctr.setAccessible(true);
+            return MethodHandles.lookup().unreflectConstructor(ctr);
+        } catch (IllegalAccessException | NoSuchMethodException e) {
+            return null;
+        }
     }
 
     /**
@@ -2358,7 +2216,6 @@ public final class ObjectStreamClass implements Serializable {
          * and return
          * {@code Object}
          */
-        @SuppressWarnings("removal")
         static MethodHandle deserializationCtr(ObjectStreamClass desc) {
             // check the cached value 1st
             MethodHandle mh = desc.deserializationCtr;
@@ -2367,14 +2224,7 @@ public final class ObjectStreamClass implements Serializable {
             if (mh != null) return desc.deserializationCtr = mh;
 
             // retrieve record components
-            RecordComponent[] recordComponents;
-            try {
-                Class<?> cls = desc.forClass();
-                PrivilegedExceptionAction<RecordComponent[]> pa = cls::getRecordComponents;
-                recordComponents = AccessController.doPrivileged(pa);
-            } catch (PrivilegedActionException e) {
-                throw new InternalError(e.getCause());
-            }
+            RecordComponent[] recordComponents = desc.forClass().getRecordComponents();
 
             // retrieve the canonical constructor
             // (T1, T2, ..., Tn):TR
diff --git a/src/java.base/share/classes/java/io/ObjectStreamField.java b/src/java.base/share/classes/java/io/ObjectStreamField.java
index 75c955440c1..465c29c101c 100644
--- a/src/java.base/share/classes/java/io/ObjectStreamField.java
+++ b/src/java.base/share/classes/java/io/ObjectStreamField.java
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1996, 2022, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1996, 2024, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -26,9 +26,6 @@
 package java.io;
 
 import java.lang.reflect.Field;
-import jdk.internal.reflect.CallerSensitive;
-import jdk.internal.reflect.Reflection;
-import sun.reflect.misc.ReflectUtil;
 
 /**
  * A description of a Serializable field from a Serializable class.  An array
@@ -161,15 +158,7 @@ public class ObjectStreamField
      * @return  a {@code Class} object representing the type of the
      *          serializable field
      */
-    @SuppressWarnings("removal")
-    @CallerSensitive
     public Class<?> getType() {
-        if (System.getSecurityManager() != null) {
-            Class<?> caller = Reflection.getCallerClass();
-            if (ReflectUtil.needsPackageAccessCheck(caller.getClassLoader(), type.getClassLoader())) {
-                ReflectUtil.checkPackageAccess(type);
-            }
-        }
         return type;
     }
 
diff --git a/src/java.base/share/classes/java/io/SerializationMisdeclarationChecker.java b/src/java.base/share/classes/java/io/SerializationMisdeclarationChecker.java
index 5eae83e80f7..5a9a6f02ab4 100644
--- a/src/java.base/share/classes/java/io/SerializationMisdeclarationChecker.java
+++ b/src/java.base/share/classes/java/io/SerializationMisdeclarationChecker.java
@@ -29,8 +29,6 @@ import java.lang.reflect.Field;
 import java.lang.reflect.Member;
 import java.lang.reflect.Method;
 import java.lang.reflect.Proxy;
-import java.security.AccessController;
-import java.security.PrivilegedAction;
 import java.util.Arrays;
 
 import static jdk.internal.event.SerializationMisdeclarationEvent.*;
@@ -75,7 +73,7 @@ final class SerializationMisdeclarationChecker {
     }
 
     private static void checkSerialVersionUID(Class<?> cl) {
-        Field f = privilegedDeclaredField(cl, SUID_NAME);
+        Field f = declaredField(cl, SUID_NAME);
         if (f == null) {
             if (isOrdinaryClass(cl)) {
                 commitEvent(cl, SUID_NAME + " should be declared explicitly" +
@@ -101,7 +99,7 @@ final class SerializationMisdeclarationChecker {
     }
 
     private static void checkSerialPersistentFields(Class<?> cl) {
-        Field f = privilegedDeclaredField(cl, SERIAL_PERSISTENT_FIELDS_NAME);
+        Field f = declaredField(cl, SERIAL_PERSISTENT_FIELDS_NAME);
         if (f == null) {
             return;
         }
@@ -142,7 +140,7 @@ final class SerializationMisdeclarationChecker {
 
     private static void checkPrivateMethod(Class<?> cl,
             String name, Class<?>[] paramTypes, Class<?> retType) {
-        for (Method m : privilegedDeclaredMethods(cl)) {
+        for (Method m : cl.getDeclaredMethods()) {
             if (m.getName().equals(name)) {
                 checkPrivateMethod(cl, m, paramTypes, retType);
             }
@@ -173,7 +171,7 @@ final class SerializationMisdeclarationChecker {
     private static void checkAccessibleMethod(Class<?> cl,
             String name, Class<?>[] paramTypes, Class<?> retType) {
         for (Class<?> superCl = cl; superCl != null; superCl = superCl.getSuperclass()) {
-            for (Method m : privilegedDeclaredMethods(superCl)) {
+            for (Method m : superCl.getDeclaredMethods()) {
                 if (m.getName().equals(name)) {
                     checkAccessibleMethod(cl, superCl, m, paramTypes, retType);
                 }
@@ -236,14 +234,6 @@ final class SerializationMisdeclarationChecker {
         return (m.getModifiers() & STATIC) != 0;
     }
 
-    @SuppressWarnings("removal")
-    private static Field privilegedDeclaredField(Class<?> cl, String name) {
-        if (System.getSecurityManager() == null) {
-            return declaredField(cl, name);
-        }
-        return AccessController.doPrivileged((PrivilegedAction<Field>) () ->
-                declaredField(cl, name));
-    }
 
     private static Field declaredField(Class<?> cl, String name) {
         try {
@@ -253,14 +243,6 @@ final class SerializationMisdeclarationChecker {
         return null;
     }
 
-    @SuppressWarnings("removal")
-    private static Method[] privilegedDeclaredMethods(Class<?> cl) {
-        if (System.getSecurityManager() == null) {
-            return cl.getDeclaredMethods();
-        }
-        return AccessController.doPrivileged(
-                (PrivilegedAction<Method[]>) cl::getDeclaredMethods);
-    }
 
     private static Object objectFromStatic(Field f) {
         try {
diff --git a/test/jdk/jdk/internal/reflect/CallerSensitive/CheckCSMs.java b/test/jdk/jdk/internal/reflect/CallerSensitive/CheckCSMs.java
index ee4d2021b87..6b63ce122a3 100644
--- a/test/jdk/jdk/internal/reflect/CallerSensitive/CheckCSMs.java
+++ b/test/jdk/jdk/internal/reflect/CallerSensitive/CheckCSMs.java
@@ -70,8 +70,7 @@ public class CheckCSMs {
     // The goal is to remove this list of Non-final instance @CS methods
     // over time.  Do not add any new one to this list.
     private static final Set<String> KNOWN_NON_FINAL_CSMS =
-        Set.of("java/io/ObjectStreamField#getType ()Ljava/lang/Class;",
-               "java/lang/Runtime#load (Ljava/lang/String;)V",
+        Set.of("java/lang/Runtime#load (Ljava/lang/String;)V",
                "java/lang/Runtime#loadLibrary (Ljava/lang/String;)V",
                "javax/sql/rowset/serial/SerialJavaObject#getFields ()[Ljava/lang/reflect/Field;"
         );