1 29 30 package com.caucho.quercus.program; 31 32 import com.caucho.quercus.Location; 33 import com.caucho.quercus.QuercusExecutionException; 34 import com.caucho.quercus.env.Env; 35 import com.caucho.quercus.env.Value; 36 37 import java.util.IdentityHashMap ; 38 import java.util.logging.Level ; 39 import java.util.logging.Logger ; 40 41 44 abstract public class Statement { 45 private static final Logger log = Logger.getLogger(Statement.class.getName()); 46 47 public static final int FALL_THROUGH = 0; 48 public static final int BREAK_FALL_THROUGH = 0x1; 49 public static final int RETURN = 0x2; 50 51 private final Location _location; 52 53 protected Statement() 54 { 55 _location = Location.UNKNOWN; 56 } 57 58 protected Statement(Location location) 59 { 60 _location = location; 61 } 62 63 public Location getLocation() 64 { 65 return _location; 66 } 67 68 abstract public Value execute(Env env); 69 70 73 public int fallThrough() 74 { 75 return FALL_THROUGH; 76 } 77 78 final protected void rethrow(Throwable t) 79 throws Throwable 80 { 81 rethrow(t, Throwable .class); 82 } 83 84 final protected <E extends Throwable > void rethrow(Throwable t, Class <E> cl) 85 throws E 86 { 87 E typedT; 88 89 if (!cl.isAssignableFrom(t.getClass())) { 90 try { 91 typedT = cl.newInstance(); 92 typedT.initCause(t); 93 } 94 catch (InstantiationException e) { 95 log.log(Level.WARNING, t.toString(), t); 96 throw new RuntimeException (e); 97 } 98 catch (IllegalAccessException e) { 99 log.log(Level.WARNING, t.toString(), t); 100 throw new RuntimeException (e); 101 } 102 } 103 else 104 typedT = (E) t; 105 106 Throwable rootCause = t; 107 108 IdentityHashMap <Throwable , Boolean > causes = new IdentityHashMap <Throwable , Boolean >(); 110 111 causes.put(rootCause, Boolean.TRUE); 112 113 while (rootCause.getCause() != null) { 114 Throwable cause = rootCause.getCause(); 115 116 if (causes.containsKey(cause)) 117 break; 118 119 causes.put(cause, Boolean.TRUE); 120 121 rootCause = cause; 122 } 123 124 if (!(rootCause instanceof QuercusExecutionException)) { 125 String rootCauseName = rootCause.getClass().getName(); 126 String rootCauseMessage = rootCause.getMessage(); 127 128 StringBuilder quercusExMessage = new StringBuilder (); 129 130 quercusExMessage.append(rootCauseName); 131 132 if (rootCauseMessage != null && rootCauseMessage.length() > 0) { 133 quercusExMessage.append(" "); 134 quercusExMessage.append(rootCauseMessage); 135 } 136 137 QuercusExecutionException quercusEx 138 = new QuercusExecutionException(quercusExMessage.toString()); 139 140 StackTraceElement [] quercusExStackTrace = quercusEx.getStackTrace(); 141 StackTraceElement [] rootCauseStackTrace = rootCause.getStackTrace(); 142 143 int quercusExIndex = quercusExStackTrace.length - 1; 144 int rootCauseIndex = rootCauseStackTrace.length - 1; 145 146 while (rootCauseIndex >= 0 && quercusExIndex >= 0) { 147 StackTraceElement rootCauseElement = rootCauseStackTrace[rootCauseIndex]; 148 StackTraceElement quercusExElement = quercusExStackTrace[quercusExIndex]; 149 150 if (! quercusExElement.equals(rootCauseElement)) 151 break; 152 153 rootCauseIndex--; 154 quercusExIndex--; 155 } 156 157 int len = rootCauseIndex + 1; 158 159 StackTraceElement [] trimmedElements = new StackTraceElement [len]; 160 System.arraycopy(rootCauseStackTrace, 0, trimmedElements, 0, len); 161 162 quercusEx.setStackTrace(trimmedElements); 163 rootCause.initCause(quercusEx); 164 rootCause = quercusEx; 165 } 166 167 String className = _location.getClassName(); 168 String functionName = _location.getFunctionName(); 169 String fileName = _location.getFileName(); 170 int lineNumber = _location.getLineNumber(); 171 172 if (className == null) 173 className = ""; 174 175 if (functionName == null) 176 functionName = ""; 177 178 StackTraceElement [] existingElements = rootCause.getStackTrace(); 179 int len = existingElements.length; 180 StackTraceElement lastElement; 181 182 if (len > 1) 183 lastElement = existingElements[len - 1]; 184 else 185 lastElement = null; 186 187 if (lastElement != null 189 && (functionName.equals(lastElement.getMethodName())) 190 && (className.equals(lastElement.getClassName()))) 191 { 192 throw typedT; 193 } 194 195 StackTraceElement [] elements = new StackTraceElement [len + 1]; 196 197 System.arraycopy(existingElements, 0, elements, 0, len); 198 199 elements[len] = new StackTraceElement (className, 200 functionName, 201 fileName, 202 lineNumber); 203 204 rootCause.setStackTrace(elements); 205 206 throw typedT; 207 } 208 209 public String toString() 210 { 211 return getClass().getSimpleName() + "[]"; 212 } 213 } 214 215 | Popular Tags |