1205 |
1205 |
1206 { |
1206 { |
1207 __ pusha(); // push registers (overkill) |
1207 __ pusha(); // push registers (overkill) |
1208 // must compute element count unless barrier set interface is changed (other platforms supply count) |
1208 // must compute element count unless barrier set interface is changed (other platforms supply count) |
1209 assert_different_registers(start, end, scratch); |
1209 assert_different_registers(start, end, scratch); |
1210 __ lea(scratch, Address(end, wordSize)); |
1210 __ lea(scratch, Address(end, BytesPerHeapOop)); |
1211 __ subptr(scratch, start); |
1211 __ subptr(scratch, start); // subtract start to get #bytes |
1212 __ shrptr(scratch, LogBytesPerWord); |
1212 __ shrptr(scratch, LogBytesPerHeapOop); // convert to element count |
1213 __ mov(c_rarg0, start); |
1213 __ mov(c_rarg0, start); |
1214 __ mov(c_rarg1, scratch); |
1214 __ mov(c_rarg1, scratch); |
1215 __ call(RuntimeAddress(CAST_FROM_FN_PTR(address, BarrierSet::static_write_ref_array_post))); |
1215 __ call(RuntimeAddress(CAST_FROM_FN_PTR(address, BarrierSet::static_write_ref_array_post))); |
1216 __ popa(); |
1216 __ popa(); |
1217 } |
1217 } |
1223 assert(sizeof(*ct->byte_map_base) == sizeof(jbyte), "adjust this code"); |
1223 assert(sizeof(*ct->byte_map_base) == sizeof(jbyte), "adjust this code"); |
1224 |
1224 |
1225 Label L_loop; |
1225 Label L_loop; |
1226 |
1226 |
1227 __ shrptr(start, CardTableModRefBS::card_shift); |
1227 __ shrptr(start, CardTableModRefBS::card_shift); |
|
1228 __ addptr(end, BytesPerHeapOop); |
1228 __ shrptr(end, CardTableModRefBS::card_shift); |
1229 __ shrptr(end, CardTableModRefBS::card_shift); |
1229 __ subptr(end, start); // number of bytes to copy |
1230 __ subptr(end, start); // number of bytes to copy |
1230 |
1231 |
1231 intptr_t disp = (intptr_t) ct->byte_map_base; |
1232 intptr_t disp = (intptr_t) ct->byte_map_base; |
1232 if (__ is_simm32(disp)) { |
1233 if (__ is_simm32(disp)) { |
2249 // Register rdx = -1 * number of *remaining* oops, r14 = *total* oops. |
2250 // Register rdx = -1 * number of *remaining* oops, r14 = *total* oops. |
2250 // Emit GC store barriers for the oops we have copied (r14 + rdx), |
2251 // Emit GC store barriers for the oops we have copied (r14 + rdx), |
2251 // and report their number to the caller. |
2252 // and report their number to the caller. |
2252 assert_different_registers(rax, r14_length, count, to, end_to, rcx); |
2253 assert_different_registers(rax, r14_length, count, to, end_to, rcx); |
2253 __ lea(end_to, to_element_addr); |
2254 __ lea(end_to, to_element_addr); |
|
2255 __ addptr(end_to, -heapOopSize); // make an inclusive end pointer |
2254 gen_write_ref_array_post_barrier(to, end_to, rscratch1); |
2256 gen_write_ref_array_post_barrier(to, end_to, rscratch1); |
2255 __ movptr(rax, r14_length); // original oops |
2257 __ movptr(rax, r14_length); // original oops |
2256 __ addptr(rax, count); // K = (original - remaining) oops |
2258 __ addptr(rax, count); // K = (original - remaining) oops |
2257 __ notptr(rax); // report (-1^K) to caller |
2259 __ notptr(rax); // report (-1^K) to caller |
2258 __ jmp(L_done); |
2260 __ jmp(L_done); |
2259 |
2261 |
2260 // Come here on success only. |
2262 // Come here on success only. |
2261 __ BIND(L_do_card_marks); |
2263 __ BIND(L_do_card_marks); |
2262 __ addptr(end_to, -wordSize); // make an inclusive end pointer |
2264 __ addptr(end_to, -heapOopSize); // make an inclusive end pointer |
2263 gen_write_ref_array_post_barrier(to, end_to, rscratch1); |
2265 gen_write_ref_array_post_barrier(to, end_to, rscratch1); |
2264 __ xorptr(rax, rax); // return 0 on success |
2266 __ xorptr(rax, rax); // return 0 on success |
2265 |
2267 |
2266 // Common exit point (success or failure). |
2268 // Common exit point (success or failure). |
2267 __ BIND(L_done); |
2269 __ BIND(L_done); |