3050 default: ShouldNotReachHere(); |
3050 default: ShouldNotReachHere(); |
3051 } |
3051 } |
3052 return false; |
3052 return false; |
3053 } |
3053 } |
3054 |
3054 |
3055 // Emit constants grouped in the following order: |
|
3056 static BasicType type_order[] = { |
|
3057 T_FLOAT, // 32-bit |
|
3058 T_OBJECT, // 32 or 64-bit |
|
3059 T_ADDRESS, // 32 or 64-bit |
|
3060 T_DOUBLE, // 64-bit |
|
3061 T_LONG, // 64-bit |
|
3062 T_VOID, // 32 or 64-bit (jump-tables are at the end of the constant table for code emission reasons) |
|
3063 T_ILLEGAL |
|
3064 }; |
|
3065 |
|
3066 static int type_to_size_in_bytes(BasicType t) { |
3055 static int type_to_size_in_bytes(BasicType t) { |
3067 switch (t) { |
3056 switch (t) { |
3068 case T_LONG: return sizeof(jlong ); |
3057 case T_LONG: return sizeof(jlong ); |
3069 case T_FLOAT: return sizeof(jfloat ); |
3058 case T_FLOAT: return sizeof(jfloat ); |
3070 case T_DOUBLE: return sizeof(jdouble); |
3059 case T_DOUBLE: return sizeof(jdouble); |
3071 // We use T_VOID as marker for jump-table entries (labels) which |
3060 // We use T_VOID as marker for jump-table entries (labels) which |
3072 // need an interal word relocation. |
3061 // need an internal word relocation. |
3073 case T_VOID: |
3062 case T_VOID: |
3074 case T_ADDRESS: |
3063 case T_ADDRESS: |
3075 case T_OBJECT: return sizeof(jobject); |
3064 case T_OBJECT: return sizeof(jobject); |
3076 } |
3065 } |
3077 |
3066 |
3078 ShouldNotReachHere(); |
3067 ShouldNotReachHere(); |
3079 return -1; |
3068 return -1; |
3080 } |
3069 } |
3081 |
3070 |
|
3071 int Compile::ConstantTable::qsort_comparator(Constant* a, Constant* b) { |
|
3072 // sort descending |
|
3073 if (a->freq() > b->freq()) return -1; |
|
3074 if (a->freq() < b->freq()) return 1; |
|
3075 return 0; |
|
3076 } |
|
3077 |
3082 void Compile::ConstantTable::calculate_offsets_and_size() { |
3078 void Compile::ConstantTable::calculate_offsets_and_size() { |
3083 int size = 0; |
3079 // First, sort the array by frequencies. |
3084 for (int t = 0; type_order[t] != T_ILLEGAL; t++) { |
3080 _constants.sort(qsort_comparator); |
3085 BasicType type = type_order[t]; |
3081 |
3086 |
3082 #ifdef ASSERT |
3087 for (int i = 0; i < _constants.length(); i++) { |
3083 // Make sure all jump-table entries were sorted to the end of the |
3088 Constant con = _constants.at(i); |
3084 // array (they have a negative frequency). |
3089 if (con.type() != type) continue; // Skip other types. |
3085 bool found_void = false; |
3090 |
3086 for (int i = 0; i < _constants.length(); i++) { |
3091 // Align size for type. |
3087 Constant con = _constants.at(i); |
3092 int typesize = type_to_size_in_bytes(con.type()); |
3088 if (con.type() == T_VOID) |
3093 size = align_size_up(size, typesize); |
3089 found_void = true; // jump-tables |
3094 |
3090 else |
3095 // Set offset. |
3091 assert(!found_void, "wrong sorting"); |
3096 con.set_offset(size); |
3092 } |
3097 _constants.at_put(i, con); |
3093 #endif |
3098 |
3094 |
3099 // Add type size. |
3095 int offset = 0; |
3100 size = size + typesize; |
3096 for (int i = 0; i < _constants.length(); i++) { |
|
3097 Constant* con = _constants.adr_at(i); |
|
3098 |
|
3099 // Align offset for type. |
|
3100 int typesize = type_to_size_in_bytes(con->type()); |
|
3101 offset = align_size_up(offset, typesize); |
|
3102 con->set_offset(offset); // set constant's offset |
|
3103 |
|
3104 if (con->type() == T_VOID) { |
|
3105 MachConstantNode* n = (MachConstantNode*) con->get_jobject(); |
|
3106 offset = offset + typesize * n->outcnt(); // expand jump-table |
|
3107 } else { |
|
3108 offset = offset + typesize; |
3101 } |
3109 } |
3102 } |
3110 } |
3103 |
3111 |
3104 // Align size up to the next section start (which is insts; see |
3112 // Align size up to the next section start (which is insts; see |
3105 // CodeBuffer::align_at_start). |
3113 // CodeBuffer::align_at_start). |
3106 assert(_size == -1, "already set?"); |
3114 assert(_size == -1, "already set?"); |
3107 _size = align_size_up(size, CodeEntryAlignment); |
3115 _size = align_size_up(offset, CodeEntryAlignment); |
3108 |
|
3109 if (Matcher::constant_table_absolute_addressing) { |
|
3110 set_table_base_offset(0); // No table base offset required |
|
3111 } else { |
|
3112 if (UseRDPCForConstantTableBase) { |
|
3113 // table base offset is set in MachConstantBaseNode::emit |
|
3114 } else { |
|
3115 // When RDPC is not used, the table base is set into the middle of |
|
3116 // the constant table. |
|
3117 int half_size = _size / 2; |
|
3118 assert(half_size * 2 == _size, "sanity"); |
|
3119 set_table_base_offset(-half_size); |
|
3120 } |
|
3121 } |
|
3122 } |
3116 } |
3123 |
3117 |
3124 void Compile::ConstantTable::emit(CodeBuffer& cb) { |
3118 void Compile::ConstantTable::emit(CodeBuffer& cb) { |
3125 MacroAssembler _masm(&cb); |
3119 MacroAssembler _masm(&cb); |
3126 for (int t = 0; type_order[t] != T_ILLEGAL; t++) { |
3120 for (int i = 0; i < _constants.length(); i++) { |
3127 BasicType type = type_order[t]; |
3121 Constant con = _constants.at(i); |
3128 |
3122 address constant_addr; |
3129 for (int i = 0; i < _constants.length(); i++) { |
3123 switch (con.type()) { |
3130 Constant con = _constants.at(i); |
3124 case T_LONG: constant_addr = _masm.long_constant( con.get_jlong() ); break; |
3131 if (con.type() != type) continue; // Skip other types. |
3125 case T_FLOAT: constant_addr = _masm.float_constant( con.get_jfloat() ); break; |
3132 |
3126 case T_DOUBLE: constant_addr = _masm.double_constant(con.get_jdouble()); break; |
3133 address constant_addr; |
3127 case T_OBJECT: { |
3134 switch (con.type()) { |
3128 jobject obj = con.get_jobject(); |
3135 case T_LONG: constant_addr = _masm.long_constant( con.get_jlong() ); break; |
3129 int oop_index = _masm.oop_recorder()->find_index(obj); |
3136 case T_FLOAT: constant_addr = _masm.float_constant( con.get_jfloat() ); break; |
3130 constant_addr = _masm.address_constant((address) obj, oop_Relocation::spec(oop_index)); |
3137 case T_DOUBLE: constant_addr = _masm.double_constant(con.get_jdouble()); break; |
3131 break; |
3138 case T_OBJECT: { |
3132 } |
3139 jobject obj = con.get_jobject(); |
3133 case T_ADDRESS: { |
3140 int oop_index = _masm.oop_recorder()->find_index(obj); |
3134 address addr = (address) con.get_jobject(); |
3141 constant_addr = _masm.address_constant((address) obj, oop_Relocation::spec(oop_index)); |
3135 constant_addr = _masm.address_constant(addr); |
3142 break; |
3136 break; |
3143 } |
3137 } |
3144 case T_ADDRESS: { |
3138 // We use T_VOID as marker for jump-table entries (labels) which |
3145 address addr = (address) con.get_jobject(); |
3139 // need an internal word relocation. |
3146 constant_addr = _masm.address_constant(addr); |
3140 case T_VOID: { |
3147 break; |
3141 MachConstantNode* n = (MachConstantNode*) con.get_jobject(); |
3148 } |
3142 // Fill the jump-table with a dummy word. The real value is |
3149 // We use T_VOID as marker for jump-table entries (labels) which |
3143 // filled in later in fill_jump_table. |
3150 // need an interal word relocation. |
3144 address dummy = (address) n; |
3151 case T_VOID: { |
3145 constant_addr = _masm.address_constant(dummy); |
3152 // Write a dummy word. The real value is filled in later |
3146 // Expand jump-table |
3153 // in fill_jump_table_in_constant_table. |
3147 for (uint i = 1; i < n->outcnt(); i++) { |
3154 address addr = (address) con.get_jobject(); |
3148 address temp_addr = _masm.address_constant(dummy + i); |
3155 constant_addr = _masm.address_constant(addr); |
3149 assert(temp_addr, "consts section too small"); |
3156 break; |
3150 } |
3157 } |
3151 break; |
3158 default: ShouldNotReachHere(); |
3152 } |
3159 } |
3153 default: ShouldNotReachHere(); |
3160 assert(constant_addr != NULL, "consts section too small"); |
3154 } |
3161 assert((constant_addr - _masm.code()->consts()->start()) == con.offset(), err_msg("must be: %d == %d", constant_addr - _masm.code()->consts()->start(), con.offset())); |
3155 assert(constant_addr, "consts section too small"); |
3162 } |
3156 assert((constant_addr - _masm.code()->consts()->start()) == con.offset(), err_msg("must be: %d == %d", constant_addr - _masm.code()->consts()->start(), con.offset())); |
3163 } |
3157 } |
3164 } |
3158 } |
3165 |
3159 |
3166 int Compile::ConstantTable::find_offset(Constant& con) const { |
3160 int Compile::ConstantTable::find_offset(Constant& con) const { |
3167 int idx = _constants.find(con); |
3161 int idx = _constants.find(con); |
3173 |
3167 |
3174 void Compile::ConstantTable::add(Constant& con) { |
3168 void Compile::ConstantTable::add(Constant& con) { |
3175 if (con.can_be_reused()) { |
3169 if (con.can_be_reused()) { |
3176 int idx = _constants.find(con); |
3170 int idx = _constants.find(con); |
3177 if (idx != -1 && _constants.at(idx).can_be_reused()) { |
3171 if (idx != -1 && _constants.at(idx).can_be_reused()) { |
|
3172 _constants.adr_at(idx)->inc_freq(con.freq()); // increase the frequency by the current value |
3178 return; |
3173 return; |
3179 } |
3174 } |
3180 } |
3175 } |
3181 (void) _constants.append(con); |
3176 (void) _constants.append(con); |
3182 } |
3177 } |
3183 |
3178 |
3184 Compile::Constant Compile::ConstantTable::add(BasicType type, jvalue value) { |
3179 Compile::Constant Compile::ConstantTable::add(MachConstantNode* n, BasicType type, jvalue value) { |
3185 Constant con(type, value); |
3180 Block* b = Compile::current()->cfg()->_bbs[n->_idx]; |
|
3181 Constant con(type, value, b->_freq); |
3186 add(con); |
3182 add(con); |
3187 return con; |
3183 return con; |
3188 } |
3184 } |
3189 |
3185 |
3190 Compile::Constant Compile::ConstantTable::add(MachOper* oper) { |
3186 Compile::Constant Compile::ConstantTable::add(MachConstantNode* n, MachOper* oper) { |
3191 jvalue value; |
3187 jvalue value; |
3192 BasicType type = oper->type()->basic_type(); |
3188 BasicType type = oper->type()->basic_type(); |
3193 switch (type) { |
3189 switch (type) { |
3194 case T_LONG: value.j = oper->constantL(); break; |
3190 case T_LONG: value.j = oper->constantL(); break; |
3195 case T_FLOAT: value.f = oper->constantF(); break; |
3191 case T_FLOAT: value.f = oper->constantF(); break; |
3196 case T_DOUBLE: value.d = oper->constantD(); break; |
3192 case T_DOUBLE: value.d = oper->constantD(); break; |
3197 case T_OBJECT: |
3193 case T_OBJECT: |
3198 case T_ADDRESS: value.l = (jobject) oper->constant(); break; |
3194 case T_ADDRESS: value.l = (jobject) oper->constant(); break; |
3199 default: ShouldNotReachHere(); |
3195 default: ShouldNotReachHere(); |
3200 } |
3196 } |
3201 return add(type, value); |
3197 return add(n, type, value); |
3202 } |
3198 } |
3203 |
3199 |
3204 Compile::Constant Compile::ConstantTable::allocate_jump_table(MachConstantNode* n) { |
3200 Compile::Constant Compile::ConstantTable::add_jump_table(MachConstantNode* n) { |
3205 jvalue value; |
3201 jvalue value; |
3206 // We can use the node pointer here to identify the right jump-table |
3202 // We can use the node pointer here to identify the right jump-table |
3207 // as this method is called from Compile::Fill_buffer right before |
3203 // as this method is called from Compile::Fill_buffer right before |
3208 // the MachNodes are emitted and the jump-table is filled (means the |
3204 // the MachNodes are emitted and the jump-table is filled (means the |
3209 // MachNode pointers do not change anymore). |
3205 // MachNode pointers do not change anymore). |
3210 value.l = (jobject) n; |
3206 value.l = (jobject) n; |
3211 Constant con(T_VOID, value, false); // Labels of a jump-table cannot be reused. |
3207 Constant con(T_VOID, value, next_jump_table_freq(), false); // Labels of a jump-table cannot be reused. |
3212 for (uint i = 0; i < n->outcnt(); i++) { |
3208 add(con); |
3213 add(con); |
|
3214 } |
|
3215 return con; |
3209 return con; |
3216 } |
3210 } |
3217 |
3211 |
3218 void Compile::ConstantTable::fill_jump_table(CodeBuffer& cb, MachConstantNode* n, GrowableArray<Label*> labels) const { |
3212 void Compile::ConstantTable::fill_jump_table(CodeBuffer& cb, MachConstantNode* n, GrowableArray<Label*> labels) const { |
3219 // If called from Compile::scratch_emit_size do nothing. |
3213 // If called from Compile::scratch_emit_size do nothing. |