OK. The author pushed it to a branch - https://git1-us-west.apache.org/repos/asf?p=logging-log4j2.git;a=commit;h=64bfd314 <https://git1-us-west.apache.org/repos/asf?p=logging-log4j2.git;a=commit;h=64bfd314>.
Ralph > On Oct 5, 2018, at 1:45 PM, Luke Hutchison <luke.hu...@gmail.com> wrote: > > On Fri, Oct 5, 2018 at 1:58 PM Ralph Goers <rgo...@apache.org > <mailto:rgo...@apache.org>> wrote: > I didn’t write this particular test. I will have to find it. > > I'm curious to see the test as well, especially to see what the > "defaultJava8" test is. Is that a method for getting the stack frames using > Exception::getStackTrace or something? > > On Fri, Oct 5, 2018 at 11:55 AM David Lloyd <david.ll...@redhat.com > <mailto:david.ll...@redhat.com>> wrote: > Something to consider is _how_ the StackWalker is used. It's > potentially quite expensive in that it produces a Stream in its full > usage mode. Have you compared using the stream + lambda approach > versus extracting the stream iterator and iterating in the classic > Java fashion? I doubt it would make the benchmark competitive, but it > might help a little bit. > > In my own code, I used StackWalker::forEach rather than StalkWalker::walk, > since the stream API has such high overhead. Even lambdas have a high startup > overhead for some reason (I think it was 20ms of incurred latency when you > first use a lambda, last time I measured it?), but at least forEach should > deliver much higher throughput than walk. > > The code I'm using currently is below. I have a few questions: > > (1) Is it correct to try both StackWalker and SecurityManager first with > doPrivileged, and then if that fails, without doPrivileged? (i.e. I think it > is possible for doPrivileged to fail when non-doPrivileged doesn't fail, *or* > vice versa, depending on the security configuration?) -- sorry for the newbie > question re. JVM security, I'm having a hard time getting my head around it... > > (2) Is it reasonable to fail over from StackWalker to SecurityManager? Or if > StackWalker fails due to security limitations, will SecurityManager always > fail due to the same security limitations? (Are their security models a 1:1 > match?) > > (3) Under what circumstances can StackWalker and/or SecurityManager obtain > more information about a stacktrace than Exception::getStackTrace? > > > ---- > > > private static final class CallerResolver extends SecurityManager { > @Override > protected Class<?>[] getClassContext() { > return super.getClassContext(); > } > } > > private static Class<?>[] getCallStack() { > // Try StackWalker (JDK 9+) > PrivilegedAction<Object> stackWalkerAction = new > PrivilegedAction<Object>() { > @Override > public Object run() { > List<Class<?>> stackFrameClasses = new ArrayList<>(); > StackWalker.getInstance(Option.RETAIN_CLASS_REFERENCE) > .forEach(sf -> > stackFrameClasses.add(sf.getDeclaringClass())); > return stackFrameClasses.toArray(new Class<?>[0]); > } > }; > try { > // Try with doPrivileged() > return (Class<?>[]) AccessController.doPrivileged(stackWalkerAction); > } catch (Exception e) { > } > try { > // Try without doPrivileged() > return (Class<?>[]) stackWalkerAction.run(); > } catch (Exception e) { > } > > // Try SecurityManager > PrivilegedAction<Object> callerResolverAction = new > PrivilegedAction<Object>() { > @Override > public Object run() { > return new CallerResolver().getClassContext(); > } > }; > try { > // Try with doPrivileged() > return (Class<?>[]) > AccessController.doPrivileged(callerResolverAction); > } catch (Exception e) { > } > try { > // Try without doPrivileged() > return (Class<?>[]) callerResolverAction.run(); > } catch (Exception e) { > } > > // As a fallback, use getStackTrace() to try to get the call stack > try { > throw new Exception(); > } catch (final Exception e) { > final List<Class<?>> classes = new ArrayList<>(); > for (final StackTraceElement elt : e.getStackTrace()) { > try { > classes.add(Class.forName(elt.getClassName())); > } catch (final Throwable e2) { > // Ignore > } > } > if (classes.size() > 0) { > return classes.toArray(new Class<?>[0]); > } else { > // Last-ditch effort -- include just this class in the call stack > return new Class<?>[] { Java9Scanner.class }; > } > } > } > > > > >