private static OptionalService<ThreadAllocatedBytes> createInternal() throws Exception {
   Class<?> sunThreadMXBeanClass;
   try {
     sunThreadMXBeanClass = Class.forName("com.sun.management.ThreadMXBean");
   } catch (ClassNotFoundException e) {
     // log exception at debug level
     logger.debug(e.getMessage(), e);
     return OptionalService.unavailable(
         "Cannot find class com.sun.management.ThreadMXBean"
             + " (introduced in Oracle Java SE 6u25)");
   }
   Method isSupportedMethod =
       Reflections.getMethod(sunThreadMXBeanClass, "isThreadAllocatedMemorySupported");
   Boolean supported =
       (Boolean) Reflections.invoke(isSupportedMethod, ManagementFactory.getThreadMXBean());
   return createInternal(supported, sunThreadMXBeanClass);
 }
 @VisibleForTesting
 static OptionalService<ThreadAllocatedBytes> createInternal(
     @Nullable Boolean supported, Class<?> sunThreadMXBeanClass) throws Exception {
   if (supported == null) {
     return OptionalService.unavailable(
         "ThreadMXBean.isThreadAllocatedMemorySupported() unexpectedly returned null");
   }
   if (!supported) {
     return OptionalService.unavailable(
         "Method com.sun.management.ThreadMXBean"
             + ".isThreadAllocatedMemorySupported() returned false");
   }
   Method getThreadAllocatedBytesMethod =
       Reflections.getMethod(sunThreadMXBeanClass, "getThreadAllocatedBytes", long.class);
   return OptionalService.available(new ThreadAllocatedBytes(getThreadAllocatedBytesMethod));
 }
 public long getThreadAllocatedBytesSafely(long threadId) {
   if (disabledDueToError) {
     // prevent excessive error logging in case there is a problem
     return -1;
   }
   try {
     Long threadAllocatedBytes =
         (Long)
             Reflections.invoke(
                 getThreadAllocatedBytesMethod, ManagementFactory.getThreadMXBean(), threadId);
     if (threadAllocatedBytes == null) {
       logger.error(
           "method unexpectedly returned null:"
               + " com.sun.management.ThreadMXBean.getThreadAllocatedBytes()");
       disabledDueToError = true;
       return -1;
     }
     return threadAllocatedBytes;
   } catch (Exception e) {
     logger.error(e.getMessage(), e);
     disabledDueToError = true;
     return -1;
   }
 }