View Javadoc

1   //////////////////////////////////////////////////////////////////////////////
2   // Clirr: compares two versions of a java library for binary compatibility
3   // Copyright (C) 2003 - 2005  Lars Kühne
4   //
5   // This library is free software; you can redistribute it and/or
6   // modify it under the terms of the GNU Lesser General Public
7   // License as published by the Free Software Foundation; either
8   // version 2.1 of the License, or (at your option) any later version.
9   //
10  // This library is distributed in the hope that it will be useful,
11  // but WITHOUT ANY WARRANTY; without even the implied warranty of
12  // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
13  // Lesser General Public License for more details.
14  //
15  // You should have received a copy of the GNU Lesser General Public
16  // License along with this library; if not, write to the Free Software
17  // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
18  //////////////////////////////////////////////////////////////////////////////
19  
20  package net.sf.clirr.core.internal;
21  
22  import java.lang.reflect.Method;
23  
24  /***
25   * A helper class to initialize the cause of an exception.
26   *
27   * This allows Clirr to be compile time compatible with JDK 1.3
28   * at still taking advantage of the JDK 1.4 chained exceptions feature
29   * if available.
30   *
31   * @author lkuehne
32   */
33  public final class ExceptionUtil
34  {
35      /*** Disallow instantiation. */
36      private ExceptionUtil()
37      {
38      }
39  
40      private static Method initCauseMethod;
41  
42      static
43      {
44          try
45          {
46              initCauseMethod = Throwable.class.getMethod("initCause", new Class[]{Throwable.class});
47          }
48          catch (NoSuchMethodException e)
49          {
50              // we're on JDK < 1.4, no cause data will be available in Exception stacktraces
51              initCauseMethod = null;
52          }
53      }
54  
55      /***
56       * Initializes the chained exception if possible.
57       * Does nothing if chained exceptions are not available on the
58       * current JDK (1.3 or lower).
59       *
60       * @param t the resulting exception (high abstraction level)
61       * @param cause the underlying cause of t (low abstraction level)
62       */
63      public static void initCause(Throwable t, Throwable cause)
64      {
65          if (initCauseMethod == null)
66          {
67              return;
68          }
69  
70          try
71          {
72              initCauseMethod.invoke(t, new Throwable[]{cause});
73          }
74          catch (Exception e)
75          {
76              if (e instanceof RuntimeException)
77              {
78                  throw (RuntimeException) e;
79              }
80              throw new RuntimeException("unable to initCause: " + e.toString());
81          }
82      }
83  }