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

Side by Side Diff: src/x87/macro-assembler-x87.h

Issue 1474993004: X87: [debugger] flood function for stepping before calling it. (Closed) Base URL: https://chromium.googlesource.com/v8/v8.git@master
Patch Set: Created 5 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
« no previous file with comments | « src/x87/builtins-x87.cc ('k') | src/x87/macro-assembler-x87.cc » ('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 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #ifndef V8_X87_MACRO_ASSEMBLER_X87_H_ 5 #ifndef V8_X87_MACRO_ASSEMBLER_X87_H_
6 #define V8_X87_MACRO_ASSEMBLER_X87_H_ 6 #define V8_X87_MACRO_ASSEMBLER_X87_H_
7 7
8 #include "src/assembler.h" 8 #include "src/assembler.h"
9 #include "src/bailout-reason.h" 9 #include "src/bailout-reason.h"
10 #include "src/frames.h" 10 #include "src/frames.h"
(...skipping 23 matching lines...) Expand all
34 // distinguish memory operands from other operands on ia32. 34 // distinguish memory operands from other operands on ia32.
35 typedef Operand MemOperand; 35 typedef Operand MemOperand;
36 36
37 enum RememberedSetAction { EMIT_REMEMBERED_SET, OMIT_REMEMBERED_SET }; 37 enum RememberedSetAction { EMIT_REMEMBERED_SET, OMIT_REMEMBERED_SET };
38 enum SmiCheck { INLINE_SMI_CHECK, OMIT_SMI_CHECK }; 38 enum SmiCheck { INLINE_SMI_CHECK, OMIT_SMI_CHECK };
39 enum PointersToHereCheck { 39 enum PointersToHereCheck {
40 kPointersToHereMaybeInteresting, 40 kPointersToHereMaybeInteresting,
41 kPointersToHereAreAlwaysInteresting 41 kPointersToHereAreAlwaysInteresting
42 }; 42 };
43 43
44 44 enum RegisterValueType { REGISTER_VALUE_IS_SMI, REGISTER_VALUE_IS_INT32 };
45 enum RegisterValueType {
46 REGISTER_VALUE_IS_SMI,
47 REGISTER_VALUE_IS_INT32
48 };
49
50 45
51 #ifdef DEBUG 46 #ifdef DEBUG
52 bool AreAliased(Register reg1, 47 bool AreAliased(Register reg1, Register reg2, Register reg3 = no_reg,
53 Register reg2, 48 Register reg4 = no_reg, Register reg5 = no_reg,
54 Register reg3 = no_reg, 49 Register reg6 = no_reg, Register reg7 = no_reg,
55 Register reg4 = no_reg,
56 Register reg5 = no_reg,
57 Register reg6 = no_reg,
58 Register reg7 = no_reg,
59 Register reg8 = no_reg); 50 Register reg8 = no_reg);
60 #endif 51 #endif
61 52
62
63 // MacroAssembler implements a collection of frequently used macros. 53 // MacroAssembler implements a collection of frequently used macros.
64 class MacroAssembler: public Assembler { 54 class MacroAssembler: public Assembler {
65 public: 55 public:
66 MacroAssembler(Isolate* isolate, void* buffer, int size, 56 MacroAssembler(Isolate* isolate, void* buffer, int size,
67 CodeObjectRequired create_code_object); 57 CodeObjectRequired create_code_object);
68 58
69 void Load(Register dst, const Operand& src, Representation r); 59 void Load(Register dst, const Operand& src, Representation r);
70 void Store(Register src, const Operand& dst, Representation r); 60 void Store(Register src, const Operand& dst, Representation r);
71 61
72 // Load a register with a long value as efficiently as possible. 62 // Load a register with a long value as efficiently as possible.
(...skipping 26 matching lines...) Expand all
99 // Compare the object in a register to a value and jump if they are not equal. 89 // Compare the object in a register to a value and jump if they are not equal.
100 void JumpIfNotRoot(Register with, Heap::RootListIndex index, 90 void JumpIfNotRoot(Register with, Heap::RootListIndex index,
101 Label* if_not_equal, 91 Label* if_not_equal,
102 Label::Distance if_not_equal_distance = Label::kNear) { 92 Label::Distance if_not_equal_distance = Label::kNear) {
103 CompareRoot(with, index); 93 CompareRoot(with, index);
104 j(not_equal, if_not_equal, if_not_equal_distance); 94 j(not_equal, if_not_equal, if_not_equal_distance);
105 } 95 }
106 96
107 // --------------------------------------------------------------------------- 97 // ---------------------------------------------------------------------------
108 // GC Support 98 // GC Support
109 enum RememberedSetFinalAction { 99 enum RememberedSetFinalAction { kReturnAtEnd, kFallThroughAtEnd };
110 kReturnAtEnd,
111 kFallThroughAtEnd
112 };
113 100
114 // Record in the remembered set the fact that we have a pointer to new space 101 // Record in the remembered set the fact that we have a pointer to new space
115 // at the address pointed to by the addr register. Only works if addr is not 102 // at the address pointed to by the addr register. Only works if addr is not
116 // in new space. 103 // in new space.
117 void RememberedSetHelper(Register object, // Used for debug code. 104 void RememberedSetHelper(Register object, // Used for debug code.
118 Register addr, Register scratch, 105 Register addr, Register scratch,
119 SaveFPRegsMode save_fp, 106 SaveFPRegsMode save_fp,
120 RememberedSetFinalAction and_then); 107 RememberedSetFinalAction and_then);
121 108
122 void CheckPageFlag(Register object, 109 void CheckPageFlag(Register object, Register scratch, int mask, Condition cc,
123 Register scratch,
124 int mask,
125 Condition cc,
126 Label* condition_met, 110 Label* condition_met,
127 Label::Distance condition_met_distance = Label::kFar); 111 Label::Distance condition_met_distance = Label::kFar);
128 112
129 void CheckPageFlagForMap( 113 void CheckPageFlagForMap(
130 Handle<Map> map, 114 Handle<Map> map, int mask, Condition cc, Label* condition_met,
131 int mask,
132 Condition cc,
133 Label* condition_met,
134 Label::Distance condition_met_distance = Label::kFar); 115 Label::Distance condition_met_distance = Label::kFar);
135 116
136 // Check if object is in new space. Jumps if the object is not in new space. 117 // Check if object is in new space. Jumps if the object is not in new space.
137 // The register scratch can be object itself, but scratch will be clobbered. 118 // The register scratch can be object itself, but scratch will be clobbered.
138 void JumpIfNotInNewSpace(Register object, 119 void JumpIfNotInNewSpace(Register object, Register scratch, Label* branch,
139 Register scratch,
140 Label* branch,
141 Label::Distance distance = Label::kFar) { 120 Label::Distance distance = Label::kFar) {
142 InNewSpace(object, scratch, zero, branch, distance); 121 InNewSpace(object, scratch, zero, branch, distance);
143 } 122 }
144 123
145 // Check if object is in new space. Jumps if the object is in new space. 124 // Check if object is in new space. Jumps if the object is in new space.
146 // The register scratch can be object itself, but it will be clobbered. 125 // The register scratch can be object itself, but it will be clobbered.
147 void JumpIfInNewSpace(Register object, 126 void JumpIfInNewSpace(Register object, Register scratch, Label* branch,
148 Register scratch,
149 Label* branch,
150 Label::Distance distance = Label::kFar) { 127 Label::Distance distance = Label::kFar) {
151 InNewSpace(object, scratch, not_zero, branch, distance); 128 InNewSpace(object, scratch, not_zero, branch, distance);
152 } 129 }
153 130
154 // Check if an object has a given incremental marking color. Also uses ecx! 131 // Check if an object has a given incremental marking color. Also uses ecx!
155 void HasColor(Register object, 132 void HasColor(Register object, Register scratch0, Register scratch1,
156 Register scratch0, 133 Label* has_color, Label::Distance has_color_distance,
157 Register scratch1, 134 int first_bit, int second_bit);
158 Label* has_color,
159 Label::Distance has_color_distance,
160 int first_bit,
161 int second_bit);
162 135
163 void JumpIfBlack(Register object, 136 void JumpIfBlack(Register object, Register scratch0, Register scratch1,
164 Register scratch0,
165 Register scratch1,
166 Label* on_black, 137 Label* on_black,
167 Label::Distance on_black_distance = Label::kFar); 138 Label::Distance on_black_distance = Label::kFar);
168 139
169 // Checks the color of an object. If the object is already grey or black 140 // Checks the color of an object. If the object is already grey or black
170 // then we just fall through, since it is already live. If it is white and 141 // then we just fall through, since it is already live. If it is white and
171 // we can determine that it doesn't need to be scanned, then we just mark it 142 // we can determine that it doesn't need to be scanned, then we just mark it
172 // black and fall through. For the rest we jump to the label so the 143 // black and fall through. For the rest we jump to the label so the
173 // incremental marker can fix its assumptions. 144 // incremental marker can fix its assumptions.
174 void EnsureNotWhite(Register object, 145 void EnsureNotWhite(Register object, Register scratch1, Register scratch2,
175 Register scratch1,
176 Register scratch2,
177 Label* object_is_white_and_not_data, 146 Label* object_is_white_and_not_data,
178 Label::Distance distance); 147 Label::Distance distance);
179 148
180 // Notify the garbage collector that we wrote a pointer into an object. 149 // Notify the garbage collector that we wrote a pointer into an object.
181 // |object| is the object being stored into, |value| is the object being 150 // |object| is the object being stored into, |value| is the object being
182 // stored. value and scratch registers are clobbered by the operation. 151 // stored. value and scratch registers are clobbered by the operation.
183 // The offset is the offset from the start of the object, not the offset from 152 // The offset is the offset from the start of the object, not the offset from
184 // the tagged HeapObject pointer. For use with FieldOperand(reg, off). 153 // the tagged HeapObject pointer. For use with FieldOperand(reg, off).
185 void RecordWriteField( 154 void RecordWriteField(
186 Register object, int offset, Register value, Register scratch, 155 Register object, int offset, Register value, Register scratch,
(...skipping 77 matching lines...) Expand 10 before | Expand all | Expand 10 after
264 // Find the function context up the context chain. 233 // Find the function context up the context chain.
265 void LoadContext(Register dst, int context_chain_length); 234 void LoadContext(Register dst, int context_chain_length);
266 235
267 // Load the global proxy from the current context. 236 // Load the global proxy from the current context.
268 void LoadGlobalProxy(Register dst); 237 void LoadGlobalProxy(Register dst);
269 238
270 // Conditionally load the cached Array transitioned map of type 239 // Conditionally load the cached Array transitioned map of type
271 // transitioned_kind from the native context if the map in register 240 // transitioned_kind from the native context if the map in register
272 // map_in_out is the cached Array map in the native context of 241 // map_in_out is the cached Array map in the native context of
273 // expected_kind. 242 // expected_kind.
274 void LoadTransitionedArrayMapConditional( 243 void LoadTransitionedArrayMapConditional(ElementsKind expected_kind,
275 ElementsKind expected_kind, 244 ElementsKind transitioned_kind,
276 ElementsKind transitioned_kind, 245 Register map_in_out,
277 Register map_in_out, 246 Register scratch,
278 Register scratch, 247 Label* no_map_match);
279 Label* no_map_match);
280 248
281 // Load the global function with the given index. 249 // Load the global function with the given index.
282 void LoadGlobalFunction(int index, Register function); 250 void LoadGlobalFunction(int index, Register function);
283 251
284 // Load the initial map from the global function. The registers 252 // Load the initial map from the global function. The registers
285 // function and map can be the same. 253 // function and map can be the same.
286 void LoadGlobalFunctionInitialMap(Register function, Register map); 254 void LoadGlobalFunctionInitialMap(Register function, Register map);
287 255
288 // Push and pop the registers that can hold pointers. 256 // Push and pop the registers that can hold pointers.
289 void PushSafepointRegisters() { pushad(); } 257 void PushSafepointRegisters() { pushad(); }
(...skipping 27 matching lines...) Expand all
317 } 285 }
318 286
319 void CmpWeakValue(Register value, Handle<WeakCell> cell, Register scratch); 287 void CmpWeakValue(Register value, Handle<WeakCell> cell, Register scratch);
320 void GetWeakValue(Register value, Handle<WeakCell> cell); 288 void GetWeakValue(Register value, Handle<WeakCell> cell);
321 void LoadWeakValue(Register value, Handle<WeakCell> cell, Label* miss); 289 void LoadWeakValue(Register value, Handle<WeakCell> cell, Label* miss);
322 290
323 // --------------------------------------------------------------------------- 291 // ---------------------------------------------------------------------------
324 // JavaScript invokes 292 // JavaScript invokes
325 293
326 // Invoke the JavaScript function code by either calling or jumping. 294 // Invoke the JavaScript function code by either calling or jumping.
327 void InvokeCode(Register code,
328 const ParameterCount& expected,
329 const ParameterCount& actual,
330 InvokeFlag flag,
331 const CallWrapper& call_wrapper) {
332 InvokeCode(Operand(code), no_reg, expected, actual, flag, call_wrapper);
333 }
334 295
335 void InvokeCode(const Operand& code, Register new_target, 296 void InvokeFunctionCode(Register function, Register new_target,
336 const ParameterCount& expected, const ParameterCount& actual, 297 const ParameterCount& expected,
337 InvokeFlag flag, const CallWrapper& call_wrapper); 298 const ParameterCount& actual, InvokeFlag flag,
299 const CallWrapper& call_wrapper);
338 300
339 // Invoke the JavaScript function in the given register. Changes the 301 // Invoke the JavaScript function in the given register. Changes the
340 // current context to the context in the function before invoking. 302 // current context to the context in the function before invoking.
341 void InvokeFunction(Register function, Register new_target, 303 void InvokeFunction(Register function, Register new_target,
342 const ParameterCount& actual, InvokeFlag flag, 304 const ParameterCount& actual, InvokeFlag flag,
343 const CallWrapper& call_wrapper); 305 const CallWrapper& call_wrapper);
344 306
345 void InvokeFunction(Register function, 307 void InvokeFunction(Register function, const ParameterCount& expected,
346 const ParameterCount& expected, 308 const ParameterCount& actual, InvokeFlag flag,
347 const ParameterCount& actual,
348 InvokeFlag flag,
349 const CallWrapper& call_wrapper); 309 const CallWrapper& call_wrapper);
350 310
351 void InvokeFunction(Handle<JSFunction> function, 311 void InvokeFunction(Handle<JSFunction> function,
352 const ParameterCount& expected, 312 const ParameterCount& expected,
353 const ParameterCount& actual, 313 const ParameterCount& actual, InvokeFlag flag,
354 InvokeFlag flag,
355 const CallWrapper& call_wrapper); 314 const CallWrapper& call_wrapper);
356 315
357 // Invoke specified builtin JavaScript function. 316 // Invoke specified builtin JavaScript function.
358 void InvokeBuiltin(int native_context_index, InvokeFlag flag, 317 void InvokeBuiltin(int native_context_index, InvokeFlag flag,
359 const CallWrapper& call_wrapper = NullCallWrapper()); 318 const CallWrapper& call_wrapper = NullCallWrapper());
360 319
361 // Store the function for the given builtin in the target register. 320 // Store the function for the given builtin in the target register.
362 void GetBuiltinFunction(Register target, int native_context_index); 321 void GetBuiltinFunction(Register target, int native_context_index);
363 322
364 // Store the code object for the given builtin in the target register.
365 void GetBuiltinEntry(Register target, int native_context_index);
366 323
367 // Expression support 324 // Expression support
368 // Support for constant splitting. 325 // Support for constant splitting.
369 bool IsUnsafeImmediate(const Immediate& x); 326 bool IsUnsafeImmediate(const Immediate& x);
370 void SafeMove(Register dst, const Immediate& x); 327 void SafeMove(Register dst, const Immediate& x);
371 void SafePush(const Immediate& x); 328 void SafePush(const Immediate& x);
372 329
373 // Compare object type for heap object. 330 // Compare object type for heap object.
374 // Incoming register is heap_object and outgoing register is map. 331 // Incoming register is heap_object and outgoing register is map.
375 void CmpObjectType(Register heap_object, InstanceType type, Register map); 332 void CmpObjectType(Register heap_object, InstanceType type, Register map);
376 333
377 // Compare instance type for map. 334 // Compare instance type for map.
378 void CmpInstanceType(Register map, InstanceType type); 335 void CmpInstanceType(Register map, InstanceType type);
379 336
380 // Check if a map for a JSObject indicates that the object has fast elements. 337 // Check if a map for a JSObject indicates that the object has fast elements.
381 // Jump to the specified label if it does not. 338 // Jump to the specified label if it does not.
382 void CheckFastElements(Register map, 339 void CheckFastElements(Register map, Label* fail,
383 Label* fail,
384 Label::Distance distance = Label::kFar); 340 Label::Distance distance = Label::kFar);
385 341
386 // Check if a map for a JSObject indicates that the object can have both smi 342 // Check if a map for a JSObject indicates that the object can have both smi
387 // and HeapObject elements. Jump to the specified label if it does not. 343 // and HeapObject elements. Jump to the specified label if it does not.
388 void CheckFastObjectElements(Register map, 344 void CheckFastObjectElements(Register map, Label* fail,
389 Label* fail,
390 Label::Distance distance = Label::kFar); 345 Label::Distance distance = Label::kFar);
391 346
392 // Check if a map for a JSObject indicates that the object has fast smi only 347 // Check if a map for a JSObject indicates that the object has fast smi only
393 // elements. Jump to the specified label if it does not. 348 // elements. Jump to the specified label if it does not.
394 void CheckFastSmiElements(Register map, 349 void CheckFastSmiElements(Register map, Label* fail,
395 Label* fail,
396 Label::Distance distance = Label::kFar); 350 Label::Distance distance = Label::kFar);
397 351
398 // Check to see if maybe_number can be stored as a double in 352 // Check to see if maybe_number can be stored as a double in
399 // FastDoubleElements. If it can, store it at the index specified by key in 353 // FastDoubleElements. If it can, store it at the index specified by key in
400 // the FastDoubleElements array elements, otherwise jump to fail. 354 // the FastDoubleElements array elements, otherwise jump to fail.
401 void StoreNumberToDoubleElements(Register maybe_number, 355 void StoreNumberToDoubleElements(Register maybe_number, Register elements,
402 Register elements, 356 Register key, Register scratch, Label* fail,
403 Register key,
404 Register scratch,
405 Label* fail,
406 int offset = 0); 357 int offset = 0);
407 358
408 // Compare an object's map with the specified map. 359 // Compare an object's map with the specified map.
409 void CompareMap(Register obj, Handle<Map> map); 360 void CompareMap(Register obj, Handle<Map> map);
410 361
411 // Check if the map of an object is equal to a specified map and branch to 362 // Check if the map of an object is equal to a specified map and branch to
412 // label if not. Skip the smi check if not required (object is known to be a 363 // label if not. Skip the smi check if not required (object is known to be a
413 // heap object). If mode is ALLOW_ELEMENT_TRANSITION_MAPS, then also match 364 // heap object). If mode is ALLOW_ELEMENT_TRANSITION_MAPS, then also match
414 // against maps that are ElementsKind transition maps of the specified map. 365 // against maps that are ElementsKind transition maps of the specified map.
415 void CheckMap(Register obj, 366 void CheckMap(Register obj, Handle<Map> map, Label* fail,
416 Handle<Map> map,
417 Label* fail,
418 SmiCheckType smi_check_type); 367 SmiCheckType smi_check_type);
419 368
420 // Check if the map of an object is equal to a specified weak map and branch 369 // Check if the map of an object is equal to a specified weak map and branch
421 // to a specified target if equal. Skip the smi check if not required 370 // to a specified target if equal. Skip the smi check if not required
422 // (object is known to be a heap object) 371 // (object is known to be a heap object)
423 void DispatchWeakMap(Register obj, Register scratch1, Register scratch2, 372 void DispatchWeakMap(Register obj, Register scratch1, Register scratch2,
424 Handle<WeakCell> cell, Handle<Code> success, 373 Handle<WeakCell> cell, Handle<Code> success,
425 SmiCheckType smi_check_type); 374 SmiCheckType smi_check_type);
426 375
427 // Check if the object in register heap_object is a string. Afterwards the 376 // Check if the object in register heap_object is a string. Afterwards the
428 // register map contains the object map and the register instance_type 377 // register map contains the object map and the register instance_type
429 // contains the instance_type. The registers map and instance_type can be the 378 // contains the instance_type. The registers map and instance_type can be the
430 // same in which case it contains the instance type afterwards. Either of the 379 // same in which case it contains the instance type afterwards. Either of the
431 // registers map and instance_type can be the same as heap_object. 380 // registers map and instance_type can be the same as heap_object.
432 Condition IsObjectStringType(Register heap_object, 381 Condition IsObjectStringType(Register heap_object, Register map,
433 Register map,
434 Register instance_type); 382 Register instance_type);
435 383
436 // Check if the object in register heap_object is a name. Afterwards the 384 // Check if the object in register heap_object is a name. Afterwards the
437 // register map contains the object map and the register instance_type 385 // register map contains the object map and the register instance_type
438 // contains the instance_type. The registers map and instance_type can be the 386 // contains the instance_type. The registers map and instance_type can be the
439 // same in which case it contains the instance type afterwards. Either of the 387 // same in which case it contains the instance type afterwards. Either of the
440 // registers map and instance_type can be the same as heap_object. 388 // registers map and instance_type can be the same as heap_object.
441 Condition IsObjectNameType(Register heap_object, 389 Condition IsObjectNameType(Register heap_object, Register map,
442 Register map,
443 Register instance_type); 390 Register instance_type);
444 391
445 // FCmp is similar to integer cmp, but requires unsigned 392 // FCmp is similar to integer cmp, but requires unsigned
446 // jcc instructions (je, ja, jae, jb, jbe, je, and jz). 393 // jcc instructions (je, ja, jae, jb, jbe, je, and jz).
447 void FCmp(); 394 void FCmp();
448 void FXamMinusZero(); 395 void FXamMinusZero();
449 void FXamSign(); 396 void FXamSign();
450 void X87CheckIA(); 397 void X87CheckIA();
451 void X87SetRC(int rc); 398 void X87SetRC(int rc);
452 void X87SetFPUCW(int cw); 399 void X87SetFPUCW(int cw);
(...skipping 28 matching lines...) Expand all
481 STATIC_ASSERT(kSmiTag == 0); 428 STATIC_ASSERT(kSmiTag == 0);
482 j(not_carry, is_smi); 429 j(not_carry, is_smi);
483 } 430 }
484 431
485 void LoadUint32NoSSE2(Register src) { 432 void LoadUint32NoSSE2(Register src) {
486 LoadUint32NoSSE2(Operand(src)); 433 LoadUint32NoSSE2(Operand(src));
487 } 434 }
488 void LoadUint32NoSSE2(const Operand& src); 435 void LoadUint32NoSSE2(const Operand& src);
489 436
490 // Jump the register contains a smi. 437 // Jump the register contains a smi.
491 inline void JumpIfSmi(Register value, 438 inline void JumpIfSmi(Register value, Label* smi_label,
492 Label* smi_label,
493 Label::Distance distance = Label::kFar) { 439 Label::Distance distance = Label::kFar) {
494 test(value, Immediate(kSmiTagMask)); 440 test(value, Immediate(kSmiTagMask));
495 j(zero, smi_label, distance); 441 j(zero, smi_label, distance);
496 } 442 }
497 // Jump if the operand is a smi. 443 // Jump if the operand is a smi.
498 inline void JumpIfSmi(Operand value, 444 inline void JumpIfSmi(Operand value, Label* smi_label,
499 Label* smi_label,
500 Label::Distance distance = Label::kFar) { 445 Label::Distance distance = Label::kFar) {
501 test(value, Immediate(kSmiTagMask)); 446 test(value, Immediate(kSmiTagMask));
502 j(zero, smi_label, distance); 447 j(zero, smi_label, distance);
503 } 448 }
504 // Jump if register contain a non-smi. 449 // Jump if register contain a non-smi.
505 inline void JumpIfNotSmi(Register value, 450 inline void JumpIfNotSmi(Register value, Label* not_smi_label,
506 Label* not_smi_label,
507 Label::Distance distance = Label::kFar) { 451 Label::Distance distance = Label::kFar) {
508 test(value, Immediate(kSmiTagMask)); 452 test(value, Immediate(kSmiTagMask));
509 j(not_zero, not_smi_label, distance); 453 j(not_zero, not_smi_label, distance);
510 } 454 }
511 455
512 void LoadInstanceDescriptors(Register map, Register descriptors); 456 void LoadInstanceDescriptors(Register map, Register descriptors);
513 void EnumLength(Register dst, Register map); 457 void EnumLength(Register dst, Register map);
514 void NumberOfOwnDescriptors(Register dst, Register map); 458 void NumberOfOwnDescriptors(Register dst, Register map);
515 void LoadAccessor(Register dst, Register holder, int accessor_index, 459 void LoadAccessor(Register dst, Register holder, int accessor_index,
516 AccessorComponent accessor); 460 AccessorComponent accessor);
(...skipping 52 matching lines...) Expand 10 before | Expand all | Expand 10 after
569 513
570 // Unlink the stack handler on top of the stack from the stack handler chain. 514 // Unlink the stack handler on top of the stack from the stack handler chain.
571 void PopStackHandler(); 515 void PopStackHandler();
572 516
573 // --------------------------------------------------------------------------- 517 // ---------------------------------------------------------------------------
574 // Inline caching support 518 // Inline caching support
575 519
576 // Generate code for checking access rights - used for security checks 520 // Generate code for checking access rights - used for security checks
577 // on access to global objects across environments. The holder register 521 // on access to global objects across environments. The holder register
578 // is left untouched, but the scratch register is clobbered. 522 // is left untouched, but the scratch register is clobbered.
579 void CheckAccessGlobalProxy(Register holder_reg, 523 void CheckAccessGlobalProxy(Register holder_reg, Register scratch1,
580 Register scratch1, 524 Register scratch2, Label* miss);
581 Register scratch2,
582 Label* miss);
583 525
584 void GetNumberHash(Register r0, Register scratch); 526 void GetNumberHash(Register r0, Register scratch);
585 527
586 void LoadFromNumberDictionary(Label* miss, 528 void LoadFromNumberDictionary(Label* miss, Register elements, Register key,
587 Register elements, 529 Register r0, Register r1, Register r2,
588 Register key,
589 Register r0,
590 Register r1,
591 Register r2,
592 Register result); 530 Register result);
593 531
594
595 // --------------------------------------------------------------------------- 532 // ---------------------------------------------------------------------------
596 // Allocation support 533 // Allocation support
597 534
598 // Allocate an object in new space or old space. If the given space 535 // Allocate an object in new space or old space. If the given space
599 // is exhausted control continues at the gc_required label. The allocated 536 // is exhausted control continues at the gc_required label. The allocated
600 // object is returned in result and end of the new object is returned in 537 // object is returned in result and end of the new object is returned in
601 // result_end. The register scratch can be passed as no_reg in which case 538 // result_end. The register scratch can be passed as no_reg in which case
602 // an additional object reference will be added to the reloc info. The 539 // an additional object reference will be added to the reloc info. The
603 // returned pointers in result and result_end have not yet been tagged as 540 // returned pointers in result and result_end have not yet been tagged as
604 // heap objects. If result_contains_top_on_entry is true the content of 541 // heap objects. If result_contains_top_on_entry is true the content of
605 // result is known to be the allocation top on entry (could be result_end 542 // result is known to be the allocation top on entry (could be result_end
606 // from a previous call). If result_contains_top_on_entry is true scratch 543 // from a previous call). If result_contains_top_on_entry is true scratch
607 // should be no_reg as it is never used. 544 // should be no_reg as it is never used.
608 void Allocate(int object_size, 545 void Allocate(int object_size, Register result, Register result_end,
609 Register result, 546 Register scratch, Label* gc_required, AllocationFlags flags);
610 Register result_end,
611 Register scratch,
612 Label* gc_required,
613 AllocationFlags flags);
614 547
615 void Allocate(int header_size, 548 void Allocate(int header_size, ScaleFactor element_size,
616 ScaleFactor element_size, 549 Register element_count, RegisterValueType element_count_type,
617 Register element_count, 550 Register result, Register result_end, Register scratch,
618 RegisterValueType element_count_type, 551 Label* gc_required, AllocationFlags flags);
619 Register result,
620 Register result_end,
621 Register scratch,
622 Label* gc_required,
623 AllocationFlags flags);
624 552
625 void Allocate(Register object_size, 553 void Allocate(Register object_size, Register result, Register result_end,
626 Register result, 554 Register scratch, Label* gc_required, AllocationFlags flags);
627 Register result_end,
628 Register scratch,
629 Label* gc_required,
630 AllocationFlags flags);
631 555
632 // Allocate a heap number in new space with undefined value. The 556 // Allocate a heap number in new space with undefined value. The
633 // register scratch2 can be passed as no_reg; the others must be 557 // register scratch2 can be passed as no_reg; the others must be
634 // valid registers. Returns tagged pointer in result register, or 558 // valid registers. Returns tagged pointer in result register, or
635 // jumps to gc_required if new space is full. 559 // jumps to gc_required if new space is full.
636 void AllocateHeapNumber(Register result, 560 void AllocateHeapNumber(Register result, Register scratch1, Register scratch2,
637 Register scratch1, 561 Label* gc_required, MutableMode mode = IMMUTABLE);
638 Register scratch2,
639 Label* gc_required,
640 MutableMode mode = IMMUTABLE);
641 562
642 // Allocate a sequential string. All the header fields of the string object 563 // Allocate a sequential string. All the header fields of the string object
643 // are initialized. 564 // are initialized.
644 void AllocateTwoByteString(Register result, 565 void AllocateTwoByteString(Register result, Register length,
645 Register length, 566 Register scratch1, Register scratch2,
646 Register scratch1, 567 Register scratch3, Label* gc_required);
647 Register scratch2,
648 Register scratch3,
649 Label* gc_required);
650 void AllocateOneByteString(Register result, Register length, 568 void AllocateOneByteString(Register result, Register length,
651 Register scratch1, Register scratch2, 569 Register scratch1, Register scratch2,
652 Register scratch3, Label* gc_required); 570 Register scratch3, Label* gc_required);
653 void AllocateOneByteString(Register result, int length, Register scratch1, 571 void AllocateOneByteString(Register result, int length, Register scratch1,
654 Register scratch2, Label* gc_required); 572 Register scratch2, Label* gc_required);
655 573
656 // Allocate a raw cons string object. Only the map field of the result is 574 // Allocate a raw cons string object. Only the map field of the result is
657 // initialized. 575 // initialized.
658 void AllocateTwoByteConsString(Register result, 576 void AllocateTwoByteConsString(Register result, Register scratch1,
659 Register scratch1, 577 Register scratch2, Label* gc_required);
660 Register scratch2,
661 Label* gc_required);
662 void AllocateOneByteConsString(Register result, Register scratch1, 578 void AllocateOneByteConsString(Register result, Register scratch1,
663 Register scratch2, Label* gc_required); 579 Register scratch2, Label* gc_required);
664 580
665 // Allocate a raw sliced string object. Only the map field of the result is 581 // Allocate a raw sliced string object. Only the map field of the result is
666 // initialized. 582 // initialized.
667 void AllocateTwoByteSlicedString(Register result, 583 void AllocateTwoByteSlicedString(Register result, Register scratch1,
668 Register scratch1, 584 Register scratch2, Label* gc_required);
669 Register scratch2,
670 Label* gc_required);
671 void AllocateOneByteSlicedString(Register result, Register scratch1, 585 void AllocateOneByteSlicedString(Register result, Register scratch1,
672 Register scratch2, Label* gc_required); 586 Register scratch2, Label* gc_required);
673 587
674 // Copy memory, byte-by-byte, from source to destination. Not optimized for 588 // Copy memory, byte-by-byte, from source to destination. Not optimized for
675 // long or aligned copies. 589 // long or aligned copies.
676 // The contents of index and scratch are destroyed. 590 // The contents of index and scratch are destroyed.
677 void CopyBytes(Register source, 591 void CopyBytes(Register source, Register destination, Register length,
678 Register destination,
679 Register length,
680 Register scratch); 592 Register scratch);
681 593
682 // Initialize fields with filler values. Fields starting at |current_address| 594 // Initialize fields with filler values. Fields starting at |current_address|
683 // not including |end_address| are overwritten with the value in |filler|. At 595 // not including |end_address| are overwritten with the value in |filler|. At
684 // the end the loop, |current_address| takes the value of |end_address|. 596 // the end the loop, |current_address| takes the value of |end_address|.
685 void InitializeFieldsWithFiller(Register current_address, 597 void InitializeFieldsWithFiller(Register current_address,
686 Register end_address, Register filler); 598 Register end_address, Register filler);
687 599
688 // --------------------------------------------------------------------------- 600 // ---------------------------------------------------------------------------
689 // Support functions. 601 // Support functions.
(...skipping 53 matching lines...) Expand 10 before | Expand all | Expand 10 after
743 CallRuntime(Runtime::FunctionForId(id), num_arguments, save_doubles); 655 CallRuntime(Runtime::FunctionForId(id), num_arguments, save_doubles);
744 } 656 }
745 657
746 // Convenience function: call an external reference. 658 // Convenience function: call an external reference.
747 void CallExternalReference(ExternalReference ref, int num_arguments); 659 void CallExternalReference(ExternalReference ref, int num_arguments);
748 660
749 // Tail call of a runtime routine (jump). 661 // Tail call of a runtime routine (jump).
750 // Like JumpToExternalReference, but also takes care of passing the number 662 // Like JumpToExternalReference, but also takes care of passing the number
751 // of parameters. 663 // of parameters.
752 void TailCallExternalReference(const ExternalReference& ext, 664 void TailCallExternalReference(const ExternalReference& ext,
753 int num_arguments, 665 int num_arguments, int result_size);
754 int result_size);
755 666
756 // Convenience function: tail call a runtime routine (jump). 667 // Convenience function: tail call a runtime routine (jump).
757 void TailCallRuntime(Runtime::FunctionId fid, 668 void TailCallRuntime(Runtime::FunctionId fid, int num_arguments,
758 int num_arguments,
759 int result_size); 669 int result_size);
760 670
761 // Before calling a C-function from generated code, align arguments on stack. 671 // Before calling a C-function from generated code, align arguments on stack.
762 // After aligning the frame, arguments must be stored in esp[0], esp[4], 672 // After aligning the frame, arguments must be stored in esp[0], esp[4],
763 // etc., not pushed. The argument count assumes all arguments are word sized. 673 // etc., not pushed. The argument count assumes all arguments are word sized.
764 // Some compilers/platforms require the stack to be aligned when calling 674 // Some compilers/platforms require the stack to be aligned when calling
765 // C++ code. 675 // C++ code.
766 // Needs a scratch register to do some arithmetic. This register will be 676 // Needs a scratch register to do some arithmetic. This register will be
767 // trashed. 677 // trashed.
768 void PrepareCallCFunction(int num_arguments, Register scratch); 678 void PrepareCallCFunction(int num_arguments, Register scratch);
(...skipping 73 matching lines...) Expand 10 before | Expand all | Expand 10 after
842 752
843 // --------------------------------------------------------------------------- 753 // ---------------------------------------------------------------------------
844 // StatsCounter support 754 // StatsCounter support
845 755
846 void SetCounter(StatsCounter* counter, int value); 756 void SetCounter(StatsCounter* counter, int value);
847 void IncrementCounter(StatsCounter* counter, int value); 757 void IncrementCounter(StatsCounter* counter, int value);
848 void DecrementCounter(StatsCounter* counter, int value); 758 void DecrementCounter(StatsCounter* counter, int value);
849 void IncrementCounter(Condition cc, StatsCounter* counter, int value); 759 void IncrementCounter(Condition cc, StatsCounter* counter, int value);
850 void DecrementCounter(Condition cc, StatsCounter* counter, int value); 760 void DecrementCounter(Condition cc, StatsCounter* counter, int value);
851 761
852
853 // --------------------------------------------------------------------------- 762 // ---------------------------------------------------------------------------
854 // Debugging 763 // Debugging
855 764
856 // Calls Abort(msg) if the condition cc is not satisfied. 765 // Calls Abort(msg) if the condition cc is not satisfied.
857 // Use --debug_code to enable. 766 // Use --debug_code to enable.
858 void Assert(Condition cc, BailoutReason reason); 767 void Assert(Condition cc, BailoutReason reason);
859 768
860 void AssertFastElements(Register elements); 769 void AssertFastElements(Register elements);
861 770
862 // Like Assert(), but always enabled. 771 // Like Assert(), but always enabled.
(...skipping 30 matching lines...) Expand all
893 802
894 // Checks if the given register or operand is a unique name 803 // Checks if the given register or operand is a unique name
895 void JumpIfNotUniqueNameInstanceType(Register reg, Label* not_unique_name, 804 void JumpIfNotUniqueNameInstanceType(Register reg, Label* not_unique_name,
896 Label::Distance distance = Label::kFar) { 805 Label::Distance distance = Label::kFar) {
897 JumpIfNotUniqueNameInstanceType(Operand(reg), not_unique_name, distance); 806 JumpIfNotUniqueNameInstanceType(Operand(reg), not_unique_name, distance);
898 } 807 }
899 808
900 void JumpIfNotUniqueNameInstanceType(Operand operand, Label* not_unique_name, 809 void JumpIfNotUniqueNameInstanceType(Operand operand, Label* not_unique_name,
901 Label::Distance distance = Label::kFar); 810 Label::Distance distance = Label::kFar);
902 811
903 void EmitSeqStringSetCharCheck(Register string, 812 void EmitSeqStringSetCharCheck(Register string, Register index,
904 Register index, 813 Register value, uint32_t encoding_mask);
905 Register value,
906 uint32_t encoding_mask);
907 814
908 static int SafepointRegisterStackIndex(Register reg) { 815 static int SafepointRegisterStackIndex(Register reg) {
909 return SafepointRegisterStackIndex(reg.code()); 816 return SafepointRegisterStackIndex(reg.code());
910 } 817 }
911 818
912 // Load the type feedback vector from a JavaScript frame. 819 // Load the type feedback vector from a JavaScript frame.
913 void EmitLoadTypeFeedbackVector(Register vector); 820 void EmitLoadTypeFeedbackVector(Register vector);
914 821
915 // Activation support. 822 // Activation support.
916 void EnterFrame(StackFrame::Type type); 823 void EnterFrame(StackFrame::Type type);
(...skipping 34 matching lines...) Expand 10 before | Expand all | Expand 10 after
951 // This handle will be patched with the code object on installation. 858 // This handle will be patched with the code object on installation.
952 Handle<Object> code_object_; 859 Handle<Object> code_object_;
953 860
954 // Helper functions for generating invokes. 861 // Helper functions for generating invokes.
955 void InvokePrologue(const ParameterCount& expected, 862 void InvokePrologue(const ParameterCount& expected,
956 const ParameterCount& actual, Label* done, 863 const ParameterCount& actual, Label* done,
957 bool* definitely_mismatches, InvokeFlag flag, 864 bool* definitely_mismatches, InvokeFlag flag,
958 Label::Distance done_distance, 865 Label::Distance done_distance,
959 const CallWrapper& call_wrapper); 866 const CallWrapper& call_wrapper);
960 867
868 void FloodFunctionIfStepping(Register fun, Register new_target,
869 const ParameterCount& expected,
870 const ParameterCount& actual);
871
961 void EnterExitFramePrologue(); 872 void EnterExitFramePrologue();
962 void EnterExitFrameEpilogue(int argc, bool save_doubles); 873 void EnterExitFrameEpilogue(int argc, bool save_doubles);
963 874
964 void LeaveExitFrameEpilogue(bool restore_context); 875 void LeaveExitFrameEpilogue(bool restore_context);
965 876
966 // Allocation support helpers. 877 // Allocation support helpers.
967 void LoadAllocationTopHelper(Register result, 878 void LoadAllocationTopHelper(Register result, Register scratch,
968 Register scratch,
969 AllocationFlags flags); 879 AllocationFlags flags);
970 880
971 void UpdateAllocationTopHelper(Register result_end, 881 void UpdateAllocationTopHelper(Register result_end, Register scratch,
972 Register scratch,
973 AllocationFlags flags); 882 AllocationFlags flags);
974 883
975 // Helper for implementing JumpIfNotInNewSpace and JumpIfInNewSpace. 884 // Helper for implementing JumpIfNotInNewSpace and JumpIfInNewSpace.
976 void InNewSpace(Register object, 885 void InNewSpace(Register object, Register scratch, Condition cc,
977 Register scratch,
978 Condition cc,
979 Label* condition_met, 886 Label* condition_met,
980 Label::Distance condition_met_distance = Label::kFar); 887 Label::Distance condition_met_distance = Label::kFar);
981 888
982 // Helper for finding the mark bits for an address. Afterwards, the 889 // Helper for finding the mark bits for an address. Afterwards, the
983 // bitmap register points at the word with the mark bits and the mask 890 // bitmap register points at the word with the mark bits and the mask
984 // the position of the first bit. Uses ecx as scratch and leaves addr_reg 891 // the position of the first bit. Uses ecx as scratch and leaves addr_reg
985 // unchanged. 892 // unchanged.
986 inline void GetMarkBits(Register addr_reg, 893 inline void GetMarkBits(Register addr_reg, Register bitmap_reg,
987 Register bitmap_reg,
988 Register mask_reg); 894 Register mask_reg);
989 895
990 // Compute memory operands for safepoint stack slots. 896 // Compute memory operands for safepoint stack slots.
991 Operand SafepointRegisterSlot(Register reg); 897 Operand SafepointRegisterSlot(Register reg);
992 static int SafepointRegisterStackIndex(int reg_code); 898 static int SafepointRegisterStackIndex(int reg_code);
993 899
994 // Needs access to SafepointRegisterStackIndex for compiled frame 900 // Needs access to SafepointRegisterStackIndex for compiled frame
995 // traversal. 901 // traversal.
996 friend class StandardFrame; 902 friend class StandardFrame;
997 }; 903 };
998 904
999
1000 // The code patcher is used to patch (typically) small parts of code e.g. for 905 // The code patcher is used to patch (typically) small parts of code e.g. for
1001 // debugging and other types of instrumentation. When using the code patcher 906 // debugging and other types of instrumentation. When using the code patcher
1002 // the exact number of bytes specified must be emitted. Is not legal to emit 907 // the exact number of bytes specified must be emitted. Is not legal to emit
1003 // relocation information. If any of these constraints are violated it causes 908 // relocation information. If any of these constraints are violated it causes
1004 // an assertion. 909 // an assertion.
1005 class CodePatcher { 910 class CodePatcher {
1006 public: 911 public:
1007 CodePatcher(byte* address, int size); 912 CodePatcher(byte* address, int size);
1008 ~CodePatcher(); 913 ~CodePatcher();
1009 914
1010 // Macro assembler to emit code. 915 // Macro assembler to emit code.
1011 MacroAssembler* masm() { return &masm_; } 916 MacroAssembler* masm() { return &masm_; }
1012 917
1013 private: 918 private:
1014 byte* address_; // The address of the code being patched. 919 byte* address_; // The address of the code being patched.
1015 int size_; // Number of bytes of the expected patch size. 920 int size_; // Number of bytes of the expected patch size.
1016 MacroAssembler masm_; // Macro assembler used to generate the code. 921 MacroAssembler masm_; // Macro assembler used to generate the code.
1017 }; 922 };
1018 923
1019
1020 // ----------------------------------------------------------------------------- 924 // -----------------------------------------------------------------------------
1021 // Static helper functions. 925 // Static helper functions.
1022 926
1023 // Generate an Operand for loading a field from an object. 927 // Generate an Operand for loading a field from an object.
1024 inline Operand FieldOperand(Register object, int offset) { 928 inline Operand FieldOperand(Register object, int offset) {
1025 return Operand(object, offset - kHeapObjectTag); 929 return Operand(object, offset - kHeapObjectTag);
1026 } 930 }
1027 931
1028
1029 // Generate an Operand for loading an indexed field from an object. 932 // Generate an Operand for loading an indexed field from an object.
1030 inline Operand FieldOperand(Register object, 933 inline Operand FieldOperand(Register object, Register index, ScaleFactor scale,
1031 Register index,
1032 ScaleFactor scale,
1033 int offset) { 934 int offset) {
1034 return Operand(object, index, scale, offset - kHeapObjectTag); 935 return Operand(object, index, scale, offset - kHeapObjectTag);
1035 } 936 }
1036 937
1037 938 inline Operand FixedArrayElementOperand(Register array, Register index_as_smi,
1038 inline Operand FixedArrayElementOperand(Register array,
1039 Register index_as_smi,
1040 int additional_offset = 0) { 939 int additional_offset = 0) {
1041 int offset = FixedArray::kHeaderSize + additional_offset * kPointerSize; 940 int offset = FixedArray::kHeaderSize + additional_offset * kPointerSize;
1042 return FieldOperand(array, index_as_smi, times_half_pointer_size, offset); 941 return FieldOperand(array, index_as_smi, times_half_pointer_size, offset);
1043 } 942 }
1044 943
1045
1046 inline Operand ContextOperand(Register context, int index) { 944 inline Operand ContextOperand(Register context, int index) {
1047 return Operand(context, Context::SlotOffset(index)); 945 return Operand(context, Context::SlotOffset(index));
1048 } 946 }
1049 947
1050
1051 inline Operand ContextOperand(Register context, Register index) { 948 inline Operand ContextOperand(Register context, Register index) {
1052 return Operand(context, index, times_pointer_size, Context::SlotOffset(0)); 949 return Operand(context, index, times_pointer_size, Context::SlotOffset(0));
1053 } 950 }
1054 951
1055
1056 inline Operand GlobalObjectOperand() { 952 inline Operand GlobalObjectOperand() {
1057 return ContextOperand(esi, Context::GLOBAL_OBJECT_INDEX); 953 return ContextOperand(esi, Context::GLOBAL_OBJECT_INDEX);
1058 } 954 }
1059 955
1060
1061 #ifdef GENERATED_CODE_COVERAGE 956 #ifdef GENERATED_CODE_COVERAGE
1062 extern void LogGeneratedCodeCoverage(const char* file_line); 957 extern void LogGeneratedCodeCoverage(const char* file_line);
1063 #define CODE_COVERAGE_STRINGIFY(x) #x 958 #define CODE_COVERAGE_STRINGIFY(x) #x
1064 #define CODE_COVERAGE_TOSTRING(x) CODE_COVERAGE_STRINGIFY(x) 959 #define CODE_COVERAGE_TOSTRING(x) CODE_COVERAGE_STRINGIFY(x)
1065 #define __FILE_LINE__ __FILE__ ":" CODE_COVERAGE_TOSTRING(__LINE__) 960 #define __FILE_LINE__ __FILE__ ":" CODE_COVERAGE_TOSTRING(__LINE__)
1066 #define ACCESS_MASM(masm) { \ 961 #define ACCESS_MASM(masm) { \
1067 byte* ia32_coverage_function = \ 962 byte* ia32_coverage_function = \
1068 reinterpret_cast<byte*>(FUNCTION_ADDR(LogGeneratedCodeCoverage)); \ 963 reinterpret_cast<byte*>(FUNCTION_ADDR(LogGeneratedCodeCoverage)); \
1069 masm->pushfd(); \ 964 masm->pushfd(); \
1070 masm->pushad(); \ 965 masm->pushad(); \
1071 masm->push(Immediate(reinterpret_cast<int>(&__FILE_LINE__))); \ 966 masm->push(Immediate(reinterpret_cast<int>(&__FILE_LINE__))); \
1072 masm->call(ia32_coverage_function, RelocInfo::RUNTIME_ENTRY); \ 967 masm->call(ia32_coverage_function, RelocInfo::RUNTIME_ENTRY); \
1073 masm->pop(eax); \ 968 masm->pop(eax); \
1074 masm->popad(); \ 969 masm->popad(); \
1075 masm->popfd(); \ 970 masm->popfd(); \
1076 } \ 971 } \
1077 masm-> 972 masm->
1078 #else 973 #else
1079 #define ACCESS_MASM(masm) masm-> 974 #define ACCESS_MASM(masm) masm->
1080 #endif 975 #endif
1081 976
1082
1083 } // namespace internal 977 } // namespace internal
1084 } // namespace v8 978 } // namespace v8
1085 979
1086 #endif // V8_X87_MACRO_ASSEMBLER_X87_H_ 980 #endif // V8_X87_MACRO_ASSEMBLER_X87_H_
OLDNEW
« no previous file with comments | « src/x87/builtins-x87.cc ('k') | src/x87/macro-assembler-x87.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698