• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /* libs/pixelflinger/codeflinger/CodeCache.h
2 **
3 ** Copyright 2006, The Android Open Source Project
4 **
5 ** Licensed under the Apache License, Version 2.0 (the "License");
6 ** you may not use this file except in compliance with the License.
7 ** You may obtain a copy of the License at
8 **
9 **     http://www.apache.org/licenses/LICENSE-2.0
10 **
11 ** Unless required by applicable law or agreed to in writing, software
12 ** distributed under the License is distributed on an "AS IS" BASIS,
13 ** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 ** See the License for the specific language governing permissions and
15 ** limitations under the License.
16 */
17 
18 
19 #ifndef ANDROID_CODECACHE_H
20 #define ANDROID_CODECACHE_H
21 
22 #include <stdint.h>
23 #include <pthread.h>
24 #include <sys/types.h>
25 #include <cutils/mspace.h>
26 
27 #include "tinyutils/KeyedVector.h"
28 #include "tinyutils/smartpointer.h"
29 
30 namespace android {
31 
32 // ----------------------------------------------------------------------------
33 
34 class AssemblyKeyBase {
35 public:
~AssemblyKeyBase()36     virtual ~AssemblyKeyBase() { }
37     virtual int compare_type(const AssemblyKeyBase& key) const = 0;
38 };
39 
40 template  <typename T>
41 class AssemblyKey : public AssemblyKeyBase
42 {
43 public:
AssemblyKey(const T & rhs)44     AssemblyKey(const T& rhs) : mKey(rhs) { }
compare_type(const AssemblyKeyBase & key)45     virtual int compare_type(const AssemblyKeyBase& key) const {
46         const T& rhs = static_cast<const AssemblyKey&>(key).mKey;
47         return android::compare_type(mKey, rhs);
48     }
49 private:
50     T mKey;
51 };
52 
53 // ----------------------------------------------------------------------------
54 
55 class Assembly
56 {
57 public:
58                 Assembly(size_t size);
59     virtual     ~Assembly();
60 
61     ssize_t     size() const;
62     uint32_t*   base() const;
63     ssize_t     resize(size_t size);
64 
65     // protocol for sp<>
66             void    incStrong(const void* id) const;
67             void    decStrong(const void* id) const;
68     typedef void    weakref_type;
69 
70 private:
71     static  mspace  getMspace();
72             void    ensureMbaseExecutable();
73 
74     mutable int32_t     mCount;
75             uint32_t*   mBase;
76             size_t      mSize;
77 };
78 
79 // ----------------------------------------------------------------------------
80 
81 class CodeCache
82 {
83 public:
84 // pretty simple cache API...
85                 CodeCache(size_t size);
86                 ~CodeCache();
87 
88             sp<Assembly>        lookup(const AssemblyKeyBase& key) const;
89 
90             int                 cache(  const AssemblyKeyBase& key,
91                                         const sp<Assembly>& assembly);
92 
93 private:
94     // nothing to see here...
95     struct cache_entry_t {
cache_entry_tcache_entry_t96         inline cache_entry_t() { }
cache_entry_tcache_entry_t97         inline cache_entry_t(const sp<Assembly>& a, int64_t w)
98                 : entry(a), when(w) { }
99         sp<Assembly>            entry;
100         mutable int64_t         when;
101     };
102 
103     class key_t {
104         friend int compare_type(
105             const key_value_pair_t<key_t, cache_entry_t>&,
106             const key_value_pair_t<key_t, cache_entry_t>&);
107         const AssemblyKeyBase* mKey;
108     public:
key_t()109         key_t() { };
key_t(const AssemblyKeyBase & k)110         key_t(const AssemblyKeyBase& k) : mKey(&k)  { }
111     };
112 
113     mutable pthread_mutex_t             mLock;
114     mutable int64_t                     mWhen;
115     size_t                              mCacheSize;
116     size_t                              mCacheInUse;
117     KeyedVector<key_t, cache_entry_t>   mCacheData;
118 
119     friend int compare_type(
120         const key_value_pair_t<key_t, cache_entry_t>&,
121         const key_value_pair_t<key_t, cache_entry_t>&);
122 };
123 
124 // KeyedVector uses compare_type(), which is more efficient, than
125 // just using operator < ()
compare_type(const key_value_pair_t<CodeCache::key_t,CodeCache::cache_entry_t> & lhs,const key_value_pair_t<CodeCache::key_t,CodeCache::cache_entry_t> & rhs)126 inline int compare_type(
127     const key_value_pair_t<CodeCache::key_t, CodeCache::cache_entry_t>& lhs,
128     const key_value_pair_t<CodeCache::key_t, CodeCache::cache_entry_t>& rhs)
129 {
130     return lhs.key.mKey->compare_type(*(rhs.key.mKey));
131 }
132 
133 // ----------------------------------------------------------------------------
134 
135 }; // namespace android
136 
137 #endif //ANDROID_CODECACHE_H
138