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

Side by Side Diff: src/arm/builtins-arm.cc

Issue 184009: First step in allocating objects in generated code on ARM (Closed) Base URL: http://v8.googlecode.com/svn/branches/bleeding_edge/
Patch Set: '' Created 11 years, 3 months 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 | « no previous file | src/arm/codegen-arm.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 2006-2008 the V8 project authors. All rights reserved. 1 // Copyright 2006-2008 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 70 matching lines...) Expand 10 before | Expand all | Expand 10 after
81 __ GetBuiltinEntry(r3, Builtins::CALL_NON_FUNCTION_AS_CONSTRUCTOR); 81 __ GetBuiltinEntry(r3, Builtins::CALL_NON_FUNCTION_AS_CONSTRUCTOR);
82 __ Jump(Handle<Code>(builtin(ArgumentsAdaptorTrampoline)), 82 __ Jump(Handle<Code>(builtin(ArgumentsAdaptorTrampoline)),
83 RelocInfo::CODE_TARGET); 83 RelocInfo::CODE_TARGET);
84 } 84 }
85 85
86 86
87 void Builtins::Generate_JSConstructStubGeneric(MacroAssembler* masm) { 87 void Builtins::Generate_JSConstructStubGeneric(MacroAssembler* masm) {
88 // Enter a construct frame. 88 // Enter a construct frame.
89 __ EnterConstructFrame(); 89 __ EnterConstructFrame();
90 90
91 // Preserve the two incoming parameters 91 // Preserve the two incoming parameters on the stack.
92 __ mov(r0, Operand(r0, LSL, kSmiTagSize)); 92 __ mov(r0, Operand(r0, LSL, kSmiTagSize));
93 __ push(r0); // smi-tagged arguments count 93 __ push(r0); // Smi-tagged arguments count.
94 __ push(r1); // constructor function 94 __ push(r1); // Constructor function.
95 95
96 // Allocate the new receiver object. 96 // Use r7 for holding undefined which is used in several places below.
97 __ LoadRoot(r7, Heap::kUndefinedValueRootIndex);
98
99 // Try to allocate the object without transitioning into C code. If any of the
100 // preconditions is not met, the code bails out to the runtime call.
101 Label rt_call, allocated;
102 if (FLAG_inline_new) {
103 Label undo_allocation;
104 #ifdef ENABLE_DEBUGGER_SUPPORT
105 ExternalReference debug_step_in_fp =
106 ExternalReference::debug_step_in_fp_address();
107 __ mov(r2, Operand(debug_step_in_fp));
108 __ ldr(r2, MemOperand(r2));
109 __ tst(r2, r2);
110 __ b(nz, &rt_call);
111 #endif
112
113 // Load the initial map and verify that it is in fact a map.
114 // r1: constructor function
115 // r7: undefined
116 __ ldr(r2, FieldMemOperand(r1, JSFunction::kPrototypeOrInitialMapOffset));
117 __ tst(r2, Operand(kSmiTagMask));
118 __ b(eq, &rt_call);
119 __ CompareObjectType(r2, r3, r4, MAP_TYPE);
120 __ b(ne, &rt_call);
121
122 // Check that the constructor is not constructing a JSFunction (see comments
123 // in Runtime_NewObject in runtime.cc). In which case the initial map's
124 // instance type would be JS_FUNCTION_TYPE.
125 // r1: constructor function
126 // r2: initial map
127 // r7: undefined
128 __ CompareInstanceType(r2, r3, JS_FUNCTION_TYPE);
129 __ b(eq, &rt_call);
130
131 // Now allocate the JSObject on the heap.
132 // r1: constructor function
133 // r2: initial map
134 // r7: undefined
135 __ ldrb(r3, FieldMemOperand(r2, Map::kInstanceSizeOffset));
136 // Make sure that the maximum heap object size will never cause us
137 // problem here, because it is always greater than the maximum
138 // instance size that can be represented in a byte.
139 ASSERT(Heap::MaxObjectSizeInPagedSpace() >= JSObject::kMaxInstanceSize);
140 __ AllocateObjectInNewSpace(r3, r4, r5, r6, &rt_call, false);
141
142 // Allocated the JSObject, now initialize the fields. Map is set to initial
143 // map and properties and elements are set to empty fixed array.
144 // r1: constructor function
145 // r2: initial map
146 // r3: object size
147 // r4: JSObject (not tagged)
148 // r7: undefined
149 __ LoadRoot(r6, Heap::kEmptyFixedArrayRootIndex);
150 __ mov(r5, r4);
151 ASSERT_EQ(0 * kPointerSize, JSObject::kMapOffset);
152 __ str(r2, MemOperand(r5, kPointerSize, PostIndex));
153 ASSERT_EQ(1 * kPointerSize, JSObject::kPropertiesOffset);
154 __ str(r6, MemOperand(r5, kPointerSize, PostIndex));
155 ASSERT_EQ(2 * kPointerSize, JSObject::kElementsOffset);
156 __ str(r6, MemOperand(r5, kPointerSize, PostIndex));
157
158 // Fill all the in-object properties with undefined.
159 // r1: constructor function
160 // r2: initial map
161 // r3: object size (in words)
162 // r4: JSObject (not tagged)
163 // r5: First in-object property of JSObject (not tagged)
164 // r7: undefined
165 __ add(r6, r4, Operand(r3, LSL, kPointerSizeLog2)); // End of object.
166 ASSERT_EQ(12, JSObject::kHeaderSize);
167 { Label loop, entry;
168 __ b(&entry);
169 __ bind(&loop);
170 __ str(r7, MemOperand(r5, kPointerSize, PostIndex));
171 __ bind(&entry);
172 __ cmp(r5, Operand(r6));
173 __ b(lt, &loop);
174 }
175
176 // Add the object tag to make the JSObject real, so that we can continue and
177 // jump into the continuation code at any time from now on. Any failures
178 // need to undo the allocation, so that the heap is in a consistent state
179 // and verifiable.
180 __ add(r4, r4, Operand(kHeapObjectTag));
181
182 // Check if a non-empty properties array is needed. Continue with allocated
183 // object if not fall through to runtime call if it is.
184 // r1: constructor function
185 // r2: initial map
186 // r4: JSObject
187 // r5: start of next object (not tagged)
188 // r7: undefined
189 __ ldrb(r3, FieldMemOperand(r2, Map::kUnusedPropertyFieldsOffset));
190 // The field instance sizes contains both pre-allocated property fields and
191 // in-object properties.
192 __ ldr(r0, FieldMemOperand(r2, Map::kInstanceSizesOffset));
193 __ and_(r6,
194 r0,
195 Operand(0x000000FF << Map::kPreAllocatedPropertyFieldsByte * 8));
196 __ add(r3, r3, Operand(r6, LSR, Map::kPreAllocatedPropertyFieldsByte * 8));
197 __ and_(r6, r0, Operand(0x000000FF << Map::kInObjectPropertiesByte * 8));
198 __ sub(r3, r3, Operand(r6, LSR, Map::kInObjectPropertiesByte * 8), SetCC);
199
200 // Done if no extra properties are to be allocated.
201 __ b(eq, &allocated);
202 __ Assert(al, "Property allocation count failed.");
203
204 // Undo the setting of the new top so that the heap is verifiable. For
205 // example, the map's unused properties potentially do not match the
206 // allocated objects unused properties.
207 // r4: JSObject (previous new top)
208 __ bind(&undo_allocation);
209 __ UndoAllocationInNewSpace(r4, r5);
210 }
211
212 // Allocate the new receiver object using the runtime call.
213 __ bind(&rt_call);
97 __ push(r1); // argument for Runtime_NewObject 214 __ push(r1); // argument for Runtime_NewObject
98 __ CallRuntime(Runtime::kNewObject, 1); 215 __ CallRuntime(Runtime::kNewObject, 1);
99 __ push(r0); // save the receiver 216 __ mov(r4, r0);
217
218 // Receiver for constructor call allocated.
219 // r4: JSObject
220 __ bind(&allocated);
221 __ push(r4);
100 222
101 // Push the function and the allocated receiver from the stack. 223 // Push the function and the allocated receiver from the stack.
102 // sp[0]: receiver (newly allocated object) 224 // sp[0]: receiver (newly allocated object)
103 // sp[1]: constructor function 225 // sp[1]: constructor function
104 // sp[2]: number of arguments (smi-tagged) 226 // sp[2]: number of arguments (smi-tagged)
105 __ ldr(r1, MemOperand(sp, kPointerSize)); 227 __ ldr(r1, MemOperand(sp, kPointerSize));
106 __ push(r1); // function 228 __ push(r1); // Constructor function.
107 __ push(r0); // receiver 229 __ push(r4); // Receiver.
108 230
109 // Reload the number of arguments from the stack. 231 // Reload the number of arguments from the stack.
110 // r1: constructor function 232 // r1: constructor function
111 // sp[0]: receiver 233 // sp[0]: receiver
112 // sp[1]: constructor function 234 // sp[1]: constructor function
113 // sp[2]: receiver 235 // sp[2]: receiver
114 // sp[3]: constructor function 236 // sp[3]: constructor function
115 // sp[4]: number of arguments (smi-tagged) 237 // sp[4]: number of arguments (smi-tagged)
116 __ ldr(r3, MemOperand(sp, 4 * kPointerSize)); 238 __ ldr(r3, MemOperand(sp, 4 * kPointerSize));
117 239
(...skipping 69 matching lines...) Expand 10 before | Expand all | Expand 10 after
187 // return. 309 // return.
188 __ bind(&exit); 310 __ bind(&exit);
189 // r0: result 311 // r0: result
190 // sp[0]: receiver (newly allocated object) 312 // sp[0]: receiver (newly allocated object)
191 // sp[1]: constructor function 313 // sp[1]: constructor function
192 // sp[2]: number of arguments (smi-tagged) 314 // sp[2]: number of arguments (smi-tagged)
193 __ ldr(r1, MemOperand(sp, 2 * kPointerSize)); 315 __ ldr(r1, MemOperand(sp, 2 * kPointerSize));
194 __ LeaveConstructFrame(); 316 __ LeaveConstructFrame();
195 __ add(sp, sp, Operand(r1, LSL, kPointerSizeLog2 - 1)); 317 __ add(sp, sp, Operand(r1, LSL, kPointerSizeLog2 - 1));
196 __ add(sp, sp, Operand(kPointerSize)); 318 __ add(sp, sp, Operand(kPointerSize));
319 __ IncrementCounter(&Counters::constructed_objects, 1, r1, r2);
197 __ Jump(lr); 320 __ Jump(lr);
198 } 321 }
199 322
200 323
201 static void Generate_JSEntryTrampolineHelper(MacroAssembler* masm, 324 static void Generate_JSEntryTrampolineHelper(MacroAssembler* masm,
202 bool is_construct) { 325 bool is_construct) {
203 // Called from Generate_JS_Entry 326 // Called from Generate_JS_Entry
204 // r0: code entry 327 // r0: code entry
205 // r1: function 328 // r1: function
206 // r2: receiver 329 // r2: receiver
(...skipping 486 matching lines...) Expand 10 before | Expand all | Expand 10 after
693 // Dont adapt arguments. 816 // Dont adapt arguments.
694 // ------------------------------------------- 817 // -------------------------------------------
695 __ bind(&dont_adapt_arguments); 818 __ bind(&dont_adapt_arguments);
696 __ Jump(r3); 819 __ Jump(r3);
697 } 820 }
698 821
699 822
700 #undef __ 823 #undef __
701 824
702 } } // namespace v8::internal 825 } } // namespace v8::internal
OLDNEW
« no previous file with comments | « no previous file | src/arm/codegen-arm.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698