Chameleon Applications

Chameleon Applications Svn Source Tree

Root/branches/iFabio/i386/libsaio/cache.c

Source at commit 214 created 13 years 5 months ago.
By ifabio, update to chameleon trunk 630, and now the pakage folder is the same as blackosx branch, also add Icon "building" into buildpkg script, and add mint theme info into the English localizable.strings.
1/*
2 * Copyright (c) 2000-2003 Apple Computer, Inc. All rights reserved.
3 *
4 * @APPLE_LICENSE_HEADER_START@
5 *
6 * The contents of this file constitute Original Code as defined in and
7 * are subject to the Apple Public Source License Version 2.0 (the
8 * "License"). You may not use this file except in compliance with the
9 * License. Please obtain a copy of the License at
10 * http://www.apple.com/publicsource and read it before using this file.
11 *
12 * This Original Code and all software distributed under the License are
13 * distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY KIND, EITHER
14 * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES,
15 * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY,
16 * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT. Please see the
17 * License for the specific language governing rights and limitations
18 * under the License.
19 *
20 * @APPLE_LICENSE_HEADER_END@
21 */
22/*
23 * cache.c - A simple cache for file systems meta-data.
24 *
25 * Copyright (c) 2000 Apple Computer, Inc.
26 *
27 * DRI: Josh de Cesare
28 */
29
30#include <sl.h>
31// #include <fs.h>
32
33struct CacheEntry {
34 CICell ih;
35 long time;
36 long long offset;
37};
38typedef struct CacheEntry CacheEntry;
39
40#define kCacheSize (0x100000)
41#define kCacheMinBlockSize (0x200)
42#define kCacheMaxBlockSize (0x8000)
43#define kCacheMaxEntries (kCacheSize / kCacheMinBlockSize)
44
45static CICell gCacheIH;
46static long gCacheBlockSize;
47static long gCacheNumEntries;
48static long gCacheTime;
49
50#ifdef __i386__
51static CacheEntry *gCacheEntries;
52static char *gCacheBuffer;
53#else
54static CacheEntry gCacheEntries[kCacheMaxEntries];
55static char gCacheBuffer[kCacheSize];
56#endif
57
58#if CACHE_STATS
59unsigned long gCacheHits;
60unsigned long gCacheMisses;
61unsigned long gCacheEvicts;
62#endif
63
64void CacheReset()
65{
66 gCacheIH = NULL;
67}
68
69void CacheInit( CICell ih, long blockSize )
70{
71#ifdef __i386__
72 if ((ih == gCacheIH) && (blockSize == gCacheBlockSize))
73 return;
74#endif
75
76 if ((blockSize < kCacheMinBlockSize) ||
77 (blockSize > kCacheMaxBlockSize))
78 return;
79
80 gCacheBlockSize = blockSize;
81 gCacheNumEntries = kCacheSize / gCacheBlockSize;
82 gCacheTime = 0;
83
84#if CACHE_STATS
85 gCacheHits = 0;
86 gCacheMisses = 0;
87 gCacheEvicts = 0;
88#endif
89
90 gCacheIH = ih;
91
92#ifdef __i386__
93 if (!gCacheBuffer) gCacheBuffer = (char *) malloc(kCacheSize);
94 if (!gCacheEntries) gCacheEntries = (CacheEntry *) malloc(kCacheMaxEntries * sizeof(CacheEntry));
95 if ( !gCacheBuffer || !gCacheEntries )
96 {
97 gCacheIH = 0; // invalidate cache
98 return;
99 }
100#endif
101
102 bzero(gCacheEntries, kCacheMaxEntries * sizeof(CacheEntry));
103}
104
105long CacheRead( CICell ih, char * buffer, long long offset,
106 long length, long cache )
107{
108 long cnt, oldestEntry = 0, oldestTime, loadCache = 0;
109 CacheEntry *entry;
110
111 // See if the data can be cached.
112 if (cache && (gCacheIH == ih) && (length == gCacheBlockSize)) {
113 // Look for the data in the cache.
114 for (cnt = 0; cnt < gCacheNumEntries; cnt++) {
115 entry = &gCacheEntries[cnt];
116 if ((entry->ih == ih) && (entry->offset == offset)) {
117 entry->time = ++gCacheTime;
118 break;
119 }
120 }
121
122 // If the data was found copy it to the caller.
123 if (cnt != gCacheNumEntries) {
124 bcopy(gCacheBuffer + cnt * gCacheBlockSize, buffer, gCacheBlockSize);
125#if CACHE_STATS
126 gCacheHits++;
127#endif
128 return gCacheBlockSize;
129 }
130
131 // Could not find the data in the cache.
132 loadCache = 1;
133 }
134
135 // Read the data from the disk.
136 Seek(ih, offset);
137 Read(ih, (long)buffer, length);
138#if CACHE_STATS
139 if (cache) gCacheMisses++;
140#endif
141
142 // Put the data from the disk in the cache if needed.
143 if (loadCache) {
144 // Find a free entry.
145 oldestTime = gCacheTime;
146 for (cnt = 0; cnt < gCacheNumEntries; cnt++) {
147 entry = &gCacheEntries[cnt];
148
149 // Found a free entry.
150 if (entry->ih == 0) break;
151
152 if (entry->time < oldestTime) {
153 oldestTime = entry->time;
154 oldestEntry = cnt;
155 }
156 }
157
158 // If no free entry was found, use the oldest.
159 if (cnt == gCacheNumEntries) {
160 cnt = oldestEntry;
161#if CACHE_STATS
162 gCacheEvicts++;
163#endif
164 }
165
166 // Copy the data from disk to the new entry.
167 entry = &gCacheEntries[cnt];
168 entry->ih = ih;
169 entry->time = ++gCacheTime;
170 entry->offset = offset;
171 bcopy(buffer, gCacheBuffer + cnt * gCacheBlockSize, gCacheBlockSize);
172 }
173
174 return length;
175}
176

Archive Download this file

Revision: 214