1 /*
2 * Copyright (C) 2009, Google Inc.
3 * and other copyright owners as documented in the project's IP log.
4 *
5 * This program and the accompanying materials are made available
6 * under the terms of the Eclipse Distribution License v1.0 which
7 * accompanies this distribution, is reproduced below, and is
8 * available at http://www.eclipse.org/org/documents/edl-v10.php
9 *
10 * All rights reserved.
11 *
12 * Redistribution and use in source and binary forms, with or
13 * without modification, are permitted provided that the following
14 * conditions are met:
15 *
16 * - Redistributions of source code must retain the above copyright
17 * notice, this list of conditions and the following disclaimer.
18 *
19 * - Redistributions in binary form must reproduce the above
20 * copyright notice, this list of conditions and the following
21 * disclaimer in the documentation and/or other materials provided
22 * with the distribution.
23 *
24 * - Neither the name of the Eclipse Foundation, Inc. nor the
25 * names of its contributors may be used to endorse or promote
26 * products derived from this software without specific prior
27 * written permission.
28 *
29 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND
30 * CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES,
31 * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
32 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
33 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
34 * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
35 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
36 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
37 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
38 * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
39 * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
40 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
41 * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
42 */
43
44 package org.eclipse.jgit.storage.file;
45
46 import org.eclipse.jgit.internal.storage.file.WindowCache;
47 import org.eclipse.jgit.lib.Config;
48 import org.eclipse.jgit.storage.pack.PackConfig;
49
50 /**
51 * Configuration parameters for JVM-wide buffer cache used by JGit.
52 */
53 public class WindowCacheConfig {
54 /** 1024 (number of bytes in one kibibyte/kilobyte) */
55 public static final int KB = 1024;
56
57 /** 1024 {@link #KB} (number of bytes in one mebibyte/megabyte) */
58 public static final int MB = 1024 * KB;
59
60 private int packedGitOpenFiles;
61
62 private long packedGitLimit;
63
64 private int packedGitWindowSize;
65
66 private boolean packedGitMMAP;
67
68 private int deltaBaseCacheLimit;
69
70 private int streamFileThreshold;
71
72 /**
73 * Create a default configuration.
74 */
75 public WindowCacheConfig() {
76 packedGitOpenFiles = 128;
77 packedGitLimit = 10 * MB;
78 packedGitWindowSize = 8 * KB;
79 packedGitMMAP = false;
80 deltaBaseCacheLimit = 10 * MB;
81 streamFileThreshold = PackConfig.DEFAULT_BIG_FILE_THRESHOLD;
82 }
83
84 /**
85 * Get maximum number of streams to open at a time.
86 *
87 * @return maximum number of streams to open at a time. Open packs count
88 * against the process limits. <b>Default is 128.</b>
89 */
90 public int getPackedGitOpenFiles() {
91 return packedGitOpenFiles;
92 }
93
94 /**
95 * Set maximum number of streams to open at a time.
96 *
97 * @param fdLimit
98 * maximum number of streams to open at a time. Open packs count
99 * against the process limits
100 */
101 public void setPackedGitOpenFiles(final int fdLimit) {
102 packedGitOpenFiles = fdLimit;
103 }
104
105 /**
106 * Get maximum number bytes of heap memory to dedicate to caching pack file
107 * data.
108 *
109 * @return maximum number bytes of heap memory to dedicate to caching pack
110 * file data. <b>Default is 10 MB.</b>
111 */
112 public long getPackedGitLimit() {
113 return packedGitLimit;
114 }
115
116 /**
117 * Set maximum number bytes of heap memory to dedicate to caching pack file
118 * data.
119 *
120 * @param newLimit
121 * maximum number bytes of heap memory to dedicate to caching
122 * pack file data.
123 */
124 public void setPackedGitLimit(final long newLimit) {
125 packedGitLimit = newLimit;
126 }
127
128 /**
129 * Get size in bytes of a single window mapped or read in from the pack
130 * file.
131 *
132 * @return size in bytes of a single window mapped or read in from the pack
133 * file. <b>Default is 8 KB.</b>
134 */
135 public int getPackedGitWindowSize() {
136 return packedGitWindowSize;
137 }
138
139 /**
140 * Set size in bytes of a single window read in from the pack file.
141 *
142 * @param newSize
143 * size in bytes of a single window read in from the pack file.
144 */
145 public void setPackedGitWindowSize(final int newSize) {
146 packedGitWindowSize = newSize;
147 }
148
149 /**
150 * Whether to use Java NIO virtual memory mapping for windows
151 *
152 * @return {@code true} enables use of Java NIO virtual memory mapping for
153 * windows; false reads entire window into a byte[] with standard
154 * read calls. <b>Default false.</b>
155 */
156 public boolean isPackedGitMMAP() {
157 return packedGitMMAP;
158 }
159
160 /**
161 * Set whether to enable use of Java NIO virtual memory mapping for windows
162 *
163 * @param usemmap
164 * {@code true} enables use of Java NIO virtual memory mapping
165 * for windows; false reads entire window into a byte[] with
166 * standard read calls.
167 */
168 public void setPackedGitMMAP(final boolean usemmap) {
169 packedGitMMAP = usemmap;
170 }
171
172 /**
173 * Get maximum number of bytes to cache in delta base cache for inflated,
174 * recently accessed objects, without delta chains.
175 *
176 * @return maximum number of bytes to cache in delta base cache for
177 * inflated, recently accessed objects, without delta chains.
178 * <b>Default 10 MB.</b>
179 */
180 public int getDeltaBaseCacheLimit() {
181 return deltaBaseCacheLimit;
182 }
183
184 /**
185 * Set maximum number of bytes to cache in delta base cache for inflated,
186 * recently accessed objects, without delta chains.
187 *
188 * @param newLimit
189 * maximum number of bytes to cache in delta base cache for
190 * inflated, recently accessed objects, without delta chains.
191 */
192 public void setDeltaBaseCacheLimit(final int newLimit) {
193 deltaBaseCacheLimit = newLimit;
194 }
195
196 /**
197 * Get the size threshold beyond which objects must be streamed.
198 *
199 * @return the size threshold beyond which objects must be streamed.
200 */
201 public int getStreamFileThreshold() {
202 return streamFileThreshold;
203 }
204
205 /**
206 * Set new byte limit for objects that must be streamed.
207 *
208 * @param newLimit
209 * new byte limit for objects that must be streamed. Objects
210 * smaller than this size can be obtained as a contiguous byte
211 * array, while objects bigger than this size require using an
212 * {@link org.eclipse.jgit.lib.ObjectStream}.
213 */
214 public void setStreamFileThreshold(final int newLimit) {
215 streamFileThreshold = newLimit;
216 }
217
218 /**
219 * Update properties by setting fields from the configuration.
220 * <p>
221 * If a property is not defined in the configuration, then it is left
222 * unmodified.
223 *
224 * @param rc
225 * configuration to read properties from.
226 * @return {@code this}.
227 * @since 3.0
228 */
229 public WindowCacheConfig fromConfig(final Config rc) {
230 setPackedGitOpenFiles(rc.getInt(
231 "core", null, "packedgitopenfiles", getPackedGitOpenFiles())); //$NON-NLS-1$ //$NON-NLS-2$
232 setPackedGitLimit(rc.getLong(
233 "core", null, "packedgitlimit", getPackedGitLimit())); //$NON-NLS-1$ //$NON-NLS-2$
234 setPackedGitWindowSize(rc.getInt(
235 "core", null, "packedgitwindowsize", getPackedGitWindowSize())); //$NON-NLS-1$ //$NON-NLS-2$
236 setPackedGitMMAP(rc.getBoolean(
237 "core", null, "packedgitmmap", isPackedGitMMAP())); //$NON-NLS-1$ //$NON-NLS-2$
238 setDeltaBaseCacheLimit(rc.getInt(
239 "core", null, "deltabasecachelimit", getDeltaBaseCacheLimit())); //$NON-NLS-1$ //$NON-NLS-2$
240
241 long maxMem = Runtime.getRuntime().maxMemory();
242 long sft = rc.getLong(
243 "core", null, "streamfilethreshold", getStreamFileThreshold()); //$NON-NLS-1$ //$NON-NLS-2$
244 sft = Math.min(sft, maxMem / 4); // don't use more than 1/4 of the heap
245 sft = Math.min(sft, Integer.MAX_VALUE); // cannot exceed array length
246 setStreamFileThreshold((int) sft);
247 return this;
248 }
249
250 /**
251 * Install this configuration as the live settings.
252 * <p>
253 * The new configuration is applied immediately. If the new limits are
254 * smaller than what what is currently cached, older entries will be purged
255 * as soon as possible to allow the cache to meet the new limit.
256 *
257 * @since 3.0
258 */
259 @SuppressWarnings("deprecation")
260 public void install() {
261 WindowCache.reconfigure(this);
262 }
263 }