2
0
Эх сурвалжийг харах

[js] save caught exception in haxe.CallStack so we can use it for exceptionStack later.

Dan Korostelev 10 жил өмнө
parent
commit
2bddad82ab
2 өөрчлөгдсөн 40 нэмэгдсэн , 23 устгасан
  1. 6 0
      genjs.ml
  2. 34 23
      std/haxe/CallStack.hx

+ 6 - 0
genjs.ml

@@ -663,6 +663,12 @@ and gen_expr ctx e =
 		let bend = open_block ctx in
 		let last = ref false in
 		let else_block = ref false in
+
+		if (has_feature ctx "haxe.CallStack.exceptionStack") then begin
+			newline ctx;
+			print ctx "%s.lastException = %s" (ctx.type_accessor (TClassDecl { null_class with cl_path = ["haxe"],"CallStack" })) vname
+		end;
+
 		if (has_feature ctx "js.Boot.HaxeError") then begin
 			newline ctx;
 			print ctx "if (%s instanceof %s) %s = %s.val" vname (ctx.type_accessor (TClassDecl { null_class with cl_path = ["js";"_Boot"],"HaxeError" })) vname vname;

+ 34 - 23
std/haxe/CallStack.hx

@@ -36,6 +36,34 @@ enum StackItem {
 	Get informations about the call stack.
 **/
 class CallStack {
+	#if js
+	static var lastException:js.Error;
+
+	static function getStack(e:js.Error):Array<StackItem> {
+		// https://code.google.com/p/v8/wiki/JavaScriptStackTraceApi
+		var oldValue = (untyped Error).prepareStackTrace;
+		(untyped Error).prepareStackTrace = function (error, callsites :Array<Dynamic>) {
+			var stack = [];
+			for (site in callsites) {
+				var method = null;
+				var fullName :String = site.getFunctionName();
+				if (fullName != null) {
+					var idx = fullName.lastIndexOf(".");
+					if (idx >= 0) {
+						var className = fullName.substr(0, idx);
+						var methodName = fullName.substr(idx+1);
+						method = Method(className, methodName);
+					}
+				}
+				stack.push(FilePos(method, site.getFileName(), site.getLineNumber()));
+			}
+			return stack;
+		}
+		var a = makeStack(e.stack);
+		(untyped Error).prepareStackTrace = oldValue;
+		return a;
+	}
+	#end
 
 	/**
 		Return the call stack elements, or an empty array if not available.
@@ -55,33 +83,14 @@ class CallStack {
 			var s:Array<String> = untyped __global__.__hxcpp_get_call_stack(true);
 			return makeStack(s);
 		#elseif js
-			// https://code.google.com/p/v8/wiki/JavaScriptStackTraceApi
-			var oldValue = (untyped Error).prepareStackTrace;
-			(untyped Error).prepareStackTrace = function (error, callsites :Array<Dynamic>) {
-				var stack = [];
-				for (site in callsites) {
-					var method = null;
-					var fullName :String = site.getFunctionName();
-					if (fullName != null) {
-						var idx = fullName.lastIndexOf(".");
-						if (idx >= 0) {
-							var className = fullName.substr(0, idx);
-							var methodName = fullName.substr(idx+1);
-							method = Method(className, methodName);
-						}
-					}
-					stack.push(FilePos(method, site.getFileName(), site.getLineNumber()));
-				}
-				return stack;
-			}
 			try {
-				throw untyped __new__("Error");
+				throw new js.Error();
 			} catch( e : Dynamic ) {
-				var a = makeStack(e.stack);
-				if( a != null ) a.shift(); // remove Stack.callStack()
-				(untyped Error).prepareStackTrace = oldValue;
+				var a = getStack(e);
+				a.shift(); // remove Stack.callStack()
 				return a;
 			}
+
 		#elseif java
 			var stack = [];
 			for ( el in java.lang.Thread.currentThread().getStackTrace() ) {
@@ -178,6 +187,8 @@ class CallStack {
 					stack.push(FilePos(null, elem._1, elem._2));
 			}
 			return stack;
+		#elseif js
+			return untyped __define_feature__("haxe.CallStack.exceptionStack", getStack(lastException));
 		#else
 			return []; // Unsupported
 		#end