Many resources are needed to download a project. Please understand that we have to compensate our server costs. Thank you in advance. Project price only 1 $
You can buy this project and download/modify it how often you want.
/**
* Copyright 2003-2010 Terracotta, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package net.sf.ehcache.pool.sizeof;
import java.lang.ref.SoftReference;
import java.lang.reflect.Array;
import java.lang.reflect.Field;
import java.lang.reflect.Modifier;
import java.text.MessageFormat;
import java.util.ArrayList;
import java.util.Collection;
import java.util.IdentityHashMap;
import java.util.Stack;
import net.sf.ehcache.pool.sizeof.filter.SizeOfFilter;
import net.sf.ehcache.util.WeakIdentityConcurrentMap;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
/**
* This will walk an object graph and let you execute some "function" along the way
*
* @author Alex Snaps
*/
final class ObjectGraphWalker {
private static final Logger LOG = LoggerFactory.getLogger(ObjectGraphWalker.class);
private static final String TC_INTERNAL_FIELD_PREFIX = "$__tc_";
private static final String VERBOSE_DEBUG_LOGGING = "net.sf.ehcache.sizeof.verboseDebugLogging";
private static final String CONTINUE_MESSAGE =
"The configured limit of {0} object references was reached while attempting to calculate the size of the object graph." +
" Severe performance degradation could occur if the sizing operation continues. This can be avoided by setting the CacheManger" +
" or Cache element's maxDepthExceededBehavior to \"abort\" or adding stop points with @IgnoreSizeOf annotations." +
" If performance degradation is NOT an issue at the configured limit, raise the limit value using the CacheManager or Cache" +
" element's maxDepth attribute. For more information, see the Ehcache configuration documentation.";
private static final String ABORT_MESSAGE =
"The configured limit of {0} object references was reached while attempting to calculate the size of the object graph." +
" This can be avoided by adding stop points with @IgnoreSizeOf annotations. Since the CacheManger or Cache " +
" element's maxDepthExceededBehavior is set to \"abort\", the sizing operation has stopped and the reported cache size is not" +
" accurate. If performance degradation is NOT an issue at the configured limit, raise the limit value using the CacheManager" +
" or Cache element's maxDepth attribute. For more information, see the Ehcache configuration documentation.";
private static final boolean USE_VERBOSE_DEBUG_LOGGING;
// Todo this is probably not what we want...
private final WeakIdentityConcurrentMap, SoftReference>> fieldCache =
new WeakIdentityConcurrentMap, SoftReference>>();
private final WeakIdentityConcurrentMap, Boolean> classCache =
new WeakIdentityConcurrentMap, Boolean>();
private final SizeOfFilter sizeOfFilter;
private final Visitor visitor;
static {
USE_VERBOSE_DEBUG_LOGGING = getVerboseSizeOfDebugLogging();
}
/**
* Constructor
*
* @param visitor the visitor to use
* @param filter the filtering
* @see Visitor
* @see SizeOfFilter
*/
ObjectGraphWalker(Visitor visitor, SizeOfFilter filter) {
this.visitor = visitor;
this.sizeOfFilter = filter;
}
private static boolean getVerboseSizeOfDebugLogging() {
String verboseString = System.getProperty(VERBOSE_DEBUG_LOGGING, "false").toLowerCase();
return verboseString.equals("true");
}
/**
* The visitor to execute the function on each node of the graph
* This is only to be used for the sizing of an object graph in memory!
*/
static interface Visitor {
/**
* The visit method executed on each node
*
* @param object the reference at that node
* @return a long for you to do things with...
*/
public long visit(Object object);
}
/**
* Walk the graph and call into the "visitor"
*
* @param maxDepth maximum depth to traverse the object graph
* @param abortWhenMaxDepthExceeded true if the object traversal should be aborted when the max depth is exceeded
* @param root the roots of the objects (a shared graph will only be visited once)
* @return the sum of all Visitor#visit returned values
*/
long walk(int maxDepth, boolean abortWhenMaxDepthExceeded, Object... root) {
StringBuilder traversalDebugMessage = null;
long result = 0;
boolean warned = false;
try {
Stack