1/*
2 * Copyright (C) 2006 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 *      http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17package android.app;
18
19import android.os.Trace;
20import android.util.ArrayMap;
21import dalvik.system.PathClassLoader;
22
23class ApplicationLoaders
24{
25    public static ApplicationLoaders getDefault()
26    {
27        return gApplicationLoaders;
28    }
29
30    public ClassLoader getClassLoader(String zip, String libPath, ClassLoader parent)
31    {
32        /*
33         * This is the parent we use if they pass "null" in.  In theory
34         * this should be the "system" class loader; in practice we
35         * don't use that and can happily (and more efficiently) use the
36         * bootstrap class loader.
37         */
38        ClassLoader baseParent = ClassLoader.getSystemClassLoader().getParent();
39
40        synchronized (mLoaders) {
41            if (parent == null) {
42                parent = baseParent;
43            }
44
45            /*
46             * If we're one step up from the base class loader, find
47             * something in our cache.  Otherwise, we create a whole
48             * new ClassLoader for the zip archive.
49             */
50            if (parent == baseParent) {
51                ClassLoader loader = mLoaders.get(zip);
52                if (loader != null) {
53                    return loader;
54                }
55
56                Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, zip);
57                PathClassLoader pathClassloader =
58                    new PathClassLoader(zip, libPath, parent);
59                Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER);
60
61                mLoaders.put(zip, pathClassloader);
62                return pathClassloader;
63            }
64
65            Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, zip);
66            PathClassLoader pathClassloader = new PathClassLoader(zip, parent);
67            Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER);
68            return pathClassloader;
69        }
70    }
71
72    private final ArrayMap<String, ClassLoader> mLoaders = new ArrayMap<String, ClassLoader>();
73
74    private static final ApplicationLoaders gApplicationLoaders
75        = new ApplicationLoaders();
76}
77