Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(163)

Side by Side Diff: src/messages.js

Issue 11530011: Avoid object layout changes during GC. (Closed) Base URL: https://v8.googlecode.com/svn/branches/bleeding_edge
Patch Set: addressed comment Created 8 years ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
« no previous file with comments | « src/heap.cc ('k') | src/runtime.h » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2012 the V8 project authors. All rights reserved. 1 // Copyright 2012 the V8 project authors. All rights reserved.
2 // Redistribution and use in source and binary forms, with or without 2 // Redistribution and use in source and binary forms, with or without
3 // modification, are permitted provided that the following conditions are 3 // modification, are permitted provided that the following conditions are
4 // met: 4 // met:
5 // 5 //
6 // * Redistributions of source code must retain the above copyright 6 // * Redistributions of source code must retain the above copyright
7 // notice, this list of conditions and the following disclaimer. 7 // notice, this list of conditions and the following disclaimer.
8 // * Redistributions in binary form must reproduce the above 8 // * Redistributions in binary form must reproduce the above
9 // copyright notice, this list of conditions and the following 9 // copyright notice, this list of conditions and the following
10 // disclaimer in the documentation and/or other materials provided 10 // disclaimer in the documentation and/or other materials provided
(...skipping 1070 matching lines...) Expand 10 before | Expand all | Expand 10 after
1081 return constructorName; 1081 return constructorName;
1082 } 1082 }
1083 1083
1084 1084
1085 function captureStackTrace(obj, cons_opt) { 1085 function captureStackTrace(obj, cons_opt) {
1086 var stackTraceLimit = $Error.stackTraceLimit; 1086 var stackTraceLimit = $Error.stackTraceLimit;
1087 if (!stackTraceLimit || !IS_NUMBER(stackTraceLimit)) return; 1087 if (!stackTraceLimit || !IS_NUMBER(stackTraceLimit)) return;
1088 if (stackTraceLimit < 0 || stackTraceLimit > 10000) { 1088 if (stackTraceLimit < 0 || stackTraceLimit > 10000) {
1089 stackTraceLimit = 10000; 1089 stackTraceLimit = 10000;
1090 } 1090 }
1091 var raw_stack = %CollectStackTrace(obj, 1091 var stack = %CollectStackTrace(obj,
1092 cons_opt ? cons_opt : captureStackTrace, 1092 cons_opt ? cons_opt : captureStackTrace,
1093 stackTraceLimit); 1093 stackTraceLimit);
1094 1094
1095 // Don't be lazy if the error stack formatting is custom (observable). 1095 // Don't be lazy if the error stack formatting is custom (observable).
1096 if (IS_FUNCTION($Error.prepareStackTrace)) { 1096 if (IS_FUNCTION($Error.prepareStackTrace)) {
1097 var custom_stacktrace_fun = $Error.prepareStackTrace; 1097 var custom_stacktrace_fun = $Error.prepareStackTrace;
1098 // Use default error formatting for the case that custom formatting throws. 1098 // Use default error formatting for the case that custom formatting throws.
1099 $Error.prepareStackTrace = null; 1099 $Error.prepareStackTrace = null;
1100 var array = []; 1100 var array = [];
1101 %MoveArrayContents(GetStackFrames(raw_stack), array); 1101 %MoveArrayContents(GetStackFrames(stack), array);
1102 obj.stack = custom_stacktrace_fun(obj, array); 1102 obj.stack = custom_stacktrace_fun(obj, array);
1103 $Error.prepareStackTrace = custom_stacktrace_fun; 1103 $Error.prepareStackTrace = custom_stacktrace_fun;
1104 return; 1104 return;
1105 } 1105 }
1106 1106
1107 var error_string = FormatErrorString(obj); 1107 var error_string = FormatErrorString(obj);
1108 // Note that 'obj' and 'this' maybe different when called on objects that 1108 // Note that 'obj' and 'this' maybe different when called on objects that
1109 // have the error object on its prototype chain. The getter replaces itself 1109 // have the error object on its prototype chain. The getter replaces itself
1110 // with a data property as soon as the stack trace has been formatted. 1110 // with a data property as soon as the stack trace has been formatted.
1111 // The getter must not change the object layout as it may be called after GC.
1111 var getter = function() { 1112 var getter = function() {
1112 var value = FormatStackTrace(error_string, GetStackFrames(raw_stack)); 1113 if (IS_STRING(stack)) return stack;
1113 %DefineOrRedefineDataProperty(obj, 'stack', value, NONE); 1114 // Stack is still a raw array awaiting to be formatted.
1114 return value; 1115 stack = FormatStackTrace(error_string, GetStackFrames(stack));
1116 // Release context value.
1117 error_string = void 0;
1118 return stack;
1115 }; 1119 };
1116 %MarkOneShotGetter(getter); 1120 %MarkOneShotGetter(getter);
1117 1121
1118 // The 'stack' property of the receiver is set as data property. If 1122 // The 'stack' property of the receiver is set as data property. If
1119 // the receiver is the same as holder, this accessor pair is replaced. 1123 // the receiver is the same as holder, this accessor pair is replaced.
1120 var setter = function(v) { 1124 var setter = function(v) {
1121 %DefineOrRedefineDataProperty(this, 'stack', v, NONE); 1125 %DefineOrRedefineDataProperty(this, 'stack', v, NONE);
1122 }; 1126 };
1123 1127
1124 %DefineOrRedefineAccessorProperty(obj, 'stack', getter, setter, DONT_ENUM); 1128 %DefineOrRedefineAccessorProperty(obj, 'stack', getter, setter, DONT_ENUM);
(...skipping 131 matching lines...) Expand 10 before | Expand all | Expand 10 after
1256 function SetUpStackOverflowBoilerplate() { 1260 function SetUpStackOverflowBoilerplate() {
1257 var boilerplate = MakeRangeError('stack_overflow', []); 1261 var boilerplate = MakeRangeError('stack_overflow', []);
1258 1262
1259 // The raw stack trace is stored as hidden property of the copy of this 1263 // The raw stack trace is stored as hidden property of the copy of this
1260 // boilerplate error object. Note that the receiver 'this' may not be that 1264 // boilerplate error object. Note that the receiver 'this' may not be that
1261 // error object copy, but can be found on the prototype chain of 'this'. 1265 // error object copy, but can be found on the prototype chain of 'this'.
1262 // When the stack trace is formatted, this accessor property is replaced by 1266 // When the stack trace is formatted, this accessor property is replaced by
1263 // a data property. 1267 // a data property.
1264 var error_string = boilerplate.name + ": " + boilerplate.message; 1268 var error_string = boilerplate.name + ": " + boilerplate.message;
1265 1269
1270 // The getter must not change the object layout as it may be called after GC.
1266 function getter() { 1271 function getter() {
1267 var holder = this; 1272 var holder = this;
1268 while (!IS_ERROR(holder)) { 1273 while (!IS_ERROR(holder)) {
1269 holder = %GetPrototype(holder); 1274 holder = %GetPrototype(holder);
1270 if (holder == null) return MakeSyntaxError('illegal_access', []); 1275 if (holder == null) return MakeSyntaxError('illegal_access', []);
1271 } 1276 }
1272 var raw_stack = %GetOverflowedRawStackTrace(holder); 1277 var stack = %GetOverflowedStackTrace(holder);
1273 var result = IS_ARRAY(raw_stack) 1278 if (IS_STRING(stack)) return stack;
1274 ? FormatStackTrace(error_string, GetStackFrames(raw_stack)) 1279 if (IS_ARRAY(stack)) {
1275 : void 0; 1280 var result = FormatStackTrace(error_string, GetStackFrames(stack));
1276 %DefineOrRedefineDataProperty(holder, 'stack', result, NONE); 1281 %SetOverflowedStackTrace(holder, result);
1277 return result; 1282 return result;
1283 }
1284 return void 0;
1278 } 1285 }
1279 %MarkOneShotGetter(getter); 1286 %MarkOneShotGetter(getter);
1280 1287
1281 // The 'stack' property of the receiver is set as data property. If 1288 // The 'stack' property of the receiver is set as data property. If
1282 // the receiver is the same as holder, this accessor pair is replaced. 1289 // the receiver is the same as holder, this accessor pair is replaced.
1283 function setter(v) { 1290 function setter(v) {
1284 %DefineOrRedefineDataProperty(this, 'stack', v, NONE); 1291 %DefineOrRedefineDataProperty(this, 'stack', v, NONE);
1292 // Release the stack trace that is stored as hidden property, if exists.
1293 %SetOverflowedStackTrace(this, void 0);
1285 } 1294 }
1286 1295
1287 %DefineOrRedefineAccessorProperty( 1296 %DefineOrRedefineAccessorProperty(
1288 boilerplate, 'stack', getter, setter, DONT_ENUM); 1297 boilerplate, 'stack', getter, setter, DONT_ENUM);
1289 1298
1290 return boilerplate; 1299 return boilerplate;
1291 } 1300 }
1292 1301
1293 var kStackOverflowBoilerplate = SetUpStackOverflowBoilerplate(); 1302 var kStackOverflowBoilerplate = SetUpStackOverflowBoilerplate();
OLDNEW
« no previous file with comments | « src/heap.cc ('k') | src/runtime.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698