comparison src/share/vm/adlc/adlparse.cpp @ 14456:abec000618bf

Merge
author kvn
date Tue, 28 Jan 2014 12:25:34 -0800
parents de6a9e811145 318d0622a6d7
children 4ca6dc0799b6
comparison
equal deleted inserted replaced
14269:2a8891e0a082 14456:abec000618bf
217 } 217 }
218 } 218 }
219 else if (!strcmp(ident, "encode")) { 219 else if (!strcmp(ident, "encode")) {
220 parse_err(SYNERR, "Instructions specify ins_encode, not encode\n"); 220 parse_err(SYNERR, "Instructions specify ins_encode, not encode\n");
221 } 221 }
222 else if (!strcmp(ident, "ins_encode")) ins_encode_parse(*instr); 222 else if (!strcmp(ident, "ins_encode")) ins_encode_parse(*instr);
223 else if (!strcmp(ident, "opcode")) instr->_opcode = opcode_parse(instr); 223 // Parse late expand keyword.
224 else if (!strcmp(ident, "size")) instr->_size = size_parse(instr); 224 else if (!strcmp(ident, "postalloc_expand")) postalloc_expand_parse(*instr);
225 else if (!strcmp(ident, "effect")) effect_parse(instr); 225 else if (!strcmp(ident, "opcode")) instr->_opcode = opcode_parse(instr);
226 else if (!strcmp(ident, "expand")) instr->_exprule = expand_parse(instr); 226 else if (!strcmp(ident, "size")) instr->_size = size_parse(instr);
227 else if (!strcmp(ident, "rewrite")) instr->_rewrule = rewrite_parse(); 227 else if (!strcmp(ident, "effect")) effect_parse(instr);
228 else if (!strcmp(ident, "expand")) instr->_exprule = expand_parse(instr);
229 else if (!strcmp(ident, "rewrite")) instr->_rewrule = rewrite_parse();
228 else if (!strcmp(ident, "constraint")) { 230 else if (!strcmp(ident, "constraint")) {
229 parse_err(SYNERR, "Instructions do not specify a constraint\n"); 231 parse_err(SYNERR, "Instructions do not specify a constraint\n");
230 } 232 }
231 else if (!strcmp(ident, "construct")) { 233 else if (!strcmp(ident, "construct")) {
232 parse_err(SYNERR, "Instructions do not specify a construct\n"); 234 parse_err(SYNERR, "Instructions do not specify a construct\n");
233 } 235 }
234 else if (!strcmp(ident, "format")) instr->_format = format_parse(); 236 else if (!strcmp(ident, "format")) instr->_format = format_parse();
235 else if (!strcmp(ident, "interface")) { 237 else if (!strcmp(ident, "interface")) {
236 parse_err(SYNERR, "Instructions do not specify an interface\n"); 238 parse_err(SYNERR, "Instructions do not specify an interface\n");
237 } 239 }
238 else if (!strcmp(ident, "ins_pipe")) ins_pipe_parse(*instr); 240 else if (!strcmp(ident, "ins_pipe")) ins_pipe_parse(*instr);
239 else { // Done with staticly defined parts of instruction definition 241 else { // Done with staticly defined parts of instruction definition
240 // Check identifier to see if it is the name of an attribute 242 // Check identifier to see if it is the name of an attribute
241 const Form *form = _globalNames[ident]; 243 const Form *form = _globalNames[ident];
242 AttributeForm *attr = form ? form->is_attribute() : NULL; 244 AttributeForm *attr = form ? form->is_attribute() : NULL;
243 if( attr && (attr->_atype == INS_ATTR) ) { 245 if (attr && (attr->_atype == INS_ATTR)) {
244 // Insert the new attribute into the linked list. 246 // Insert the new attribute into the linked list.
245 Attribute *temp = attr_parse(ident); 247 Attribute *temp = attr_parse(ident);
246 temp->_next = instr->_attribs; 248 temp->_next = instr->_attribs;
247 instr->_attribs = temp; 249 instr->_attribs = temp;
248 } else { 250 } else {
249 parse_err(SYNERR, "expected one of:\n predicate, match, encode, or the name of an instruction attribute at %s\n", ident); 251 parse_err(SYNERR, "expected one of:\n predicate, match, encode, or the name of"
252 " an instruction attribute at %s\n", ident);
250 } 253 }
251 } 254 }
252 skipws(); 255 skipws();
253 } while(_curchar != '%'); 256 } while(_curchar != '%');
254 next_char(); 257 next_char();
256 parse_err(SYNERR, "missing '%%}' in instruction definition\n"); 259 parse_err(SYNERR, "missing '%%}' in instruction definition\n");
257 return; 260 return;
258 } 261 }
259 // Check for "Set" form of chain rule 262 // Check for "Set" form of chain rule
260 adjust_set_rule(instr); 263 adjust_set_rule(instr);
261 if (_AD._pipeline ) { 264 if (_AD._pipeline) {
262 if( instr->expands() ) { 265 // No pipe required for late expand.
263 if( instr->_ins_pipe ) 266 if (instr->expands() || instr->postalloc_expands()) {
264 parse_err(WARN, "ins_pipe and expand rule both specified for instruction \"%s\"; ins_pipe will be unused\n", instr->_ident); 267 if (instr->_ins_pipe) {
268 parse_err(WARN, "ins_pipe and expand rule both specified for instruction \"%s\";"
269 " ins_pipe will be unused\n", instr->_ident);
270 }
265 } else { 271 } else {
266 if( !instr->_ins_pipe ) 272 if (!instr->_ins_pipe) {
267 parse_err(WARN, "No ins_pipe specified for instruction \"%s\"\n", instr->_ident); 273 parse_err(WARN, "No ins_pipe specified for instruction \"%s\"\n", instr->_ident);
274 }
268 } 275 }
269 } 276 }
270 // Add instruction to tail of instruction list 277 // Add instruction to tail of instruction list
271 _AD.addForm(instr); 278 _AD.addForm(instr);
272 279
2777 while ((param = inst._parameters.iter()) != NULL) { 2784 while ((param = inst._parameters.iter()) != NULL) {
2778 OperandForm* opForm = (OperandForm*) inst._localNames[param]; 2785 OperandForm* opForm = (OperandForm*) inst._localNames[param];
2779 encoding->add_parameter(opForm->_ident, param); 2786 encoding->add_parameter(opForm->_ident, param);
2780 } 2787 }
2781 2788
2782 // Define a MacroAssembler instance for use by the encoding. The 2789 if (!inst._is_postalloc_expand) {
2783 // name is chosen to match the __ idiom used for assembly in other 2790 // Define a MacroAssembler instance for use by the encoding. The
2784 // parts of hotspot and assumes the existence of the standard 2791 // name is chosen to match the __ idiom used for assembly in other
2785 // #define __ _masm. 2792 // parts of hotspot and assumes the existence of the standard
2786 encoding->add_code(" MacroAssembler _masm(&cbuf);\n"); 2793 // #define __ _masm.
2794 encoding->add_code(" MacroAssembler _masm(&cbuf);\n");
2795 }
2787 2796
2788 // Parse the following %{ }% block 2797 // Parse the following %{ }% block
2789 ins_encode_parse_block_impl(inst, encoding, ec_name); 2798 ins_encode_parse_block_impl(inst, encoding, ec_name);
2790 2799
2791 // Build an encoding rule which invokes the encoding rule we just 2800 // Build an encoding rule which invokes the encoding rule we just
2852 skipws(); 2861 skipws();
2853 2862
2854 // Check if this instruct is a MachConstantNode. 2863 // Check if this instruct is a MachConstantNode.
2855 if (strcmp(rep_var, "constanttablebase") == 0) { 2864 if (strcmp(rep_var, "constanttablebase") == 0) {
2856 // This instruct is a MachConstantNode. 2865 // This instruct is a MachConstantNode.
2857 inst.set_is_mach_constant(true); 2866 inst.set_needs_constant_base(true);
2867 if (strncmp("MachCall", inst.mach_base_class(_globalNames), strlen("MachCall")) != 0 ) {
2868 inst.set_is_mach_constant(true);
2869 }
2858 2870
2859 if (_curchar == '(') { 2871 if (_curchar == '(') {
2860 parse_err(SYNERR, "constanttablebase in instruct %s cannot have an argument (only constantaddress and constantoffset)", ec_name); 2872 parse_err(SYNERR, "constanttablebase in instruct %s cannot have an argument "
2873 "(only constantaddress and constantoffset)", ec_name);
2861 return; 2874 return;
2862 } 2875 }
2863 } 2876 }
2864 else if ((strcmp(rep_var, "constantaddress") == 0) || 2877 else if ((strcmp(rep_var, "constantaddress") == 0) ||
2865 (strcmp(rep_var, "constantoffset") == 0)) { 2878 (strcmp(rep_var, "constantoffset") == 0)) {
2953 2966
2954 // Parse the encode method's parameters 2967 // Parse the encode method's parameters
2955 while (_curchar != ')') { 2968 while (_curchar != ')') {
2956 char *param = get_ident_or_literal_constant("encoding operand"); 2969 char *param = get_ident_or_literal_constant("encoding operand");
2957 if ( param != NULL ) { 2970 if ( param != NULL ) {
2958 // Found a parameter: 2971
2959 // Check it is a local name, add it to the list, then check for more 2972 // Check if this instruct is a MachConstantNode.
2960 // New: allow hex constants as parameters to an encode method. 2973 if (strcmp(param, "constanttablebase") == 0) {
2961 // New: allow parenthesized expressions as parameters. 2974 // This instruct is a MachConstantNode.
2962 // New: allow "primary", "secondary", "tertiary" as parameters. 2975 inst.set_needs_constant_base(true);
2963 // New: allow user-defined register name as parameter 2976 if (strncmp("MachCall", inst.mach_base_class(_globalNames), strlen("MachCall")) != 0 ) {
2964 if ( (inst._localNames[param] == NULL) && 2977 inst.set_is_mach_constant(true);
2965 !ADLParser::is_literal_constant(param) && 2978 }
2966 (Opcode::as_opcode_type(param) == Opcode::NOT_AN_OPCODE) && 2979
2967 ((_AD._register == NULL ) || (_AD._register->getRegDef(param) == NULL)) ) { 2980 if (_curchar == '(') {
2968 parse_err(SYNERR, "Using non-locally defined parameter %s for encoding %s.\n", param, ec_name); 2981 parse_err(SYNERR, "constanttablebase in instruct %s cannot have an argument "
2969 return; 2982 "(only constantaddress and constantoffset)", ec_name);
2983 return;
2984 }
2985 } else {
2986 // Found a parameter:
2987 // Check it is a local name, add it to the list, then check for more
2988 // New: allow hex constants as parameters to an encode method.
2989 // New: allow parenthesized expressions as parameters.
2990 // New: allow "primary", "secondary", "tertiary" as parameters.
2991 // New: allow user-defined register name as parameter
2992 if ( (inst._localNames[param] == NULL) &&
2993 !ADLParser::is_literal_constant(param) &&
2994 (Opcode::as_opcode_type(param) == Opcode::NOT_AN_OPCODE) &&
2995 ((_AD._register == NULL ) || (_AD._register->getRegDef(param) == NULL)) ) {
2996 parse_err(SYNERR, "Using non-locally defined parameter %s for encoding %s.\n", param, ec_name);
2997 return;
2998 }
2970 } 2999 }
2971 params->add_entry(param); 3000 params->add_entry(param);
2972 3001
2973 skipws(); 3002 skipws();
2974 if (_curchar == ',' ) { 3003 if (_curchar == ',' ) {
3043 return; 3072 return;
3044 } 3073 }
3045 3074
3046 // Debug Stuff 3075 // Debug Stuff
3047 if (_AD._adl_debug > 1) fprintf(stderr,"Instruction Encode: %s\n", ec_name); 3076 if (_AD._adl_debug > 1) fprintf(stderr,"Instruction Encode: %s\n", ec_name);
3077
3078 // Set encode class of this instruction.
3079 inst._insencode = encrule;
3080 }
3081
3082 //------------------------------postalloc_expand_parse---------------------------
3083 // Encode rules have the form
3084 // postalloc_expand( encode_class_name(parameter_list) );
3085 //
3086 // The "encode_class_name" must be defined in the encode section.
3087 // The parameter list contains $names that are locals.
3088 //
3089 // This is just a copy of ins_encode_parse without the loop.
3090 void ADLParser::postalloc_expand_parse(InstructForm& inst) {
3091 inst._is_postalloc_expand = true;
3092
3093 // Parse encode class name.
3094 skipws(); // Skip whitespace.
3095 if (_curchar != '(') {
3096 // Check for postalloc_expand %{ form
3097 if ((_curchar == '%') && (*(_ptr+1) == '{')) {
3098 next_char(); // Skip '%'
3099 next_char(); // Skip '{'
3100
3101 // Parse the block form of postalloc_expand
3102 ins_encode_parse_block(inst);
3103 return;
3104 }
3105
3106 parse_err(SYNERR, "missing '(' in postalloc_expand definition\n");
3107 return;
3108 }
3109 next_char(); // Move past '('.
3110 skipws();
3111
3112 InsEncode *encrule = new InsEncode(); // Encode class for instruction.
3113 encrule->_linenum = linenum();
3114 char *ec_name = NULL; // String representation of encode rule.
3115 // identifier is optional.
3116 if (_curchar != ')') {
3117 ec_name = get_ident();
3118 if (ec_name == NULL) {
3119 parse_err(SYNERR, "Invalid postalloc_expand class name after 'postalloc_expand('.\n");
3120 return;
3121 }
3122 // Check that encoding is defined in the encode section.
3123 EncClass *encode_class = _AD._encode->encClass(ec_name);
3124
3125 // Get list for encode method's parameters
3126 NameAndList *params = encrule->add_encode(ec_name);
3127
3128 // Parse the parameters to this encode method.
3129 skipws();
3130 if (_curchar == '(') {
3131 next_char(); // Move past '(' for parameters.
3132
3133 // Parse the encode method's parameters.
3134 while (_curchar != ')') {
3135 char *param = get_ident_or_literal_constant("encoding operand");
3136 if (param != NULL) {
3137 // Found a parameter:
3138
3139 // First check for constant table support.
3140
3141 // Check if this instruct is a MachConstantNode.
3142 if (strcmp(param, "constanttablebase") == 0) {
3143 // This instruct is a MachConstantNode.
3144 inst.set_needs_constant_base(true);
3145 if (strncmp("MachCall", inst.mach_base_class(_globalNames), strlen("MachCall")) != 0 ) {
3146 inst.set_is_mach_constant(true);
3147 }
3148
3149 if (_curchar == '(') {
3150 parse_err(SYNERR, "constanttablebase in instruct %s cannot have an argument "
3151 "(only constantaddress and constantoffset)", ec_name);
3152 return;
3153 }
3154 }
3155 else if ((strcmp(param, "constantaddress") == 0) ||
3156 (strcmp(param, "constantoffset") == 0)) {
3157 // This instruct is a MachConstantNode.
3158 inst.set_is_mach_constant(true);
3159
3160 // If the constant keyword has an argument, parse it.
3161 if (_curchar == '(') constant_parse(inst);
3162 }
3163
3164 // Else check it is a local name, add it to the list, then check for more.
3165 // New: allow hex constants as parameters to an encode method.
3166 // New: allow parenthesized expressions as parameters.
3167 // New: allow "primary", "secondary", "tertiary" as parameters.
3168 // New: allow user-defined register name as parameter.
3169 else if ((inst._localNames[param] == NULL) &&
3170 !ADLParser::is_literal_constant(param) &&
3171 (Opcode::as_opcode_type(param) == Opcode::NOT_AN_OPCODE) &&
3172 ((_AD._register == NULL) || (_AD._register->getRegDef(param) == NULL))) {
3173 parse_err(SYNERR, "Using non-locally defined parameter %s for encoding %s.\n", param, ec_name);
3174 return;
3175 }
3176 params->add_entry(param);
3177
3178 skipws();
3179 if (_curchar == ',') {
3180 // More parameters to come.
3181 next_char(); // Move past ',' between parameters.
3182 skipws(); // Skip to next parameter.
3183 } else if (_curchar == ')') {
3184 // Done with parameter list
3185 } else {
3186 // Only ',' or ')' are valid after a parameter name.
3187 parse_err(SYNERR, "expected ',' or ')' after parameter %s.\n", ec_name);
3188 return;
3189 }
3190
3191 } else {
3192 skipws();
3193 // Did not find a parameter.
3194 if (_curchar == ',') {
3195 parse_err(SYNERR, "Expected encode parameter before ',' in postalloc_expand %s.\n", ec_name);
3196 return;
3197 }
3198 if (_curchar != ')') {
3199 parse_err(SYNERR, "Expected ')' after postalloc_expand parameters.\n");
3200 return;
3201 }
3202 }
3203 } // WHILE loop collecting parameters.
3204 next_char(); // Move past ')' at end of parameters.
3205 } // Done with parameter list for encoding.
3206
3207 // Check for ',' or ')' after encoding.
3208 skipws(); // Move to character after parameters.
3209 if (_curchar != ')') {
3210 // Only a ')' is allowed.
3211 parse_err(SYNERR, "Expected ')' after postalloc_expand %s.\n", ec_name);
3212 return;
3213 }
3214 } // Done parsing postalloc_expand method and their parameters.
3215 if (_curchar != ')') {
3216 parse_err(SYNERR, "Missing ')' at end of postalloc_expand description.\n");
3217 return;
3218 }
3219 next_char(); // Move past ')'.
3220 skipws(); // Skip leading whitespace.
3221
3222 if (_curchar != ';') {
3223 parse_err(SYNERR, "Missing ';' at end of postalloc_expand.\n");
3224 return;
3225 }
3226 next_char(); // Move past ';'.
3227 skipws(); // Be friendly to oper_parse().
3228
3229 // Debug Stuff.
3230 if (_AD._adl_debug > 1) fprintf(stderr, "Instruction postalloc_expand: %s\n", ec_name);
3048 3231
3049 // Set encode class of this instruction. 3232 // Set encode class of this instruction.
3050 inst._insencode = encrule; 3233 inst._insencode = encrule;
3051 } 3234 }
3052 3235
3833 } 4016 }
3834 4017
3835 //------------------------------expand_parse----------------------------------- 4018 //------------------------------expand_parse-----------------------------------
3836 ExpandRule* ADLParser::expand_parse(InstructForm *instr) { 4019 ExpandRule* ADLParser::expand_parse(InstructForm *instr) {
3837 char *ident, *ident2; 4020 char *ident, *ident2;
3838 OperandForm *oper;
3839 InstructForm *ins;
3840 NameAndList *instr_and_operands = NULL; 4021 NameAndList *instr_and_operands = NULL;
3841 ExpandRule *exp = new ExpandRule(); 4022 ExpandRule *exp = new ExpandRule();
3842 4023
3843 // Expand is a block containing an ordered list of instructions, each of 4024 // Expand is a block containing an ordered list of operands with initializers,
3844 // which has an ordered list of operands. 4025 // or instructions, each of which has an ordered list of operands.
3845 // Check for block delimiter 4026 // Check for block delimiter
3846 skipws(); // Skip leading whitespace 4027 skipws(); // Skip leading whitespace
3847 if ((_curchar != '%') 4028 if ((_curchar != '%')
3848 || (next_char(), (_curchar != '{')) ) { // If not open block 4029 || (next_char(), (_curchar != '{')) ) { // If not open block
3849 parse_err(SYNERR, "missing '%%{' in expand definition\n"); 4030 parse_err(SYNERR, "missing '%%{' in expand definition\n");
3853 do { 4034 do {
3854 ident = get_ident(); // Grab next identifier 4035 ident = get_ident(); // Grab next identifier
3855 if (ident == NULL) { 4036 if (ident == NULL) {
3856 parse_err(SYNERR, "identifier expected at %c\n", _curchar); 4037 parse_err(SYNERR, "identifier expected at %c\n", _curchar);
3857 continue; 4038 continue;
3858 } // Check that you have a valid instruction 4039 }
4040
4041 // Check whether we should parse an instruction or operand.
3859 const Form *form = _globalNames[ident]; 4042 const Form *form = _globalNames[ident];
3860 ins = form ? form->is_instruction() : NULL; 4043 bool parse_oper = false;
3861 if (ins == NULL) { 4044 bool parse_ins = false;
4045 if (form == NULL) {
4046 skipws();
4047 // Check whether this looks like an instruction specification. If so,
4048 // just parse the instruction. The declaration of the instruction is
4049 // not needed here.
4050 if (_curchar == '(') parse_ins = true;
4051 } else if (form->is_instruction()) {
4052 parse_ins = true;
4053 } else if (form->is_operand()) {
4054 parse_oper = true;
4055 } else {
4056 parse_err(SYNERR, "instruction/operand name expected at %s\n", ident);
4057 continue;
4058 }
4059
4060 if (parse_oper) {
3862 // This is a new operand 4061 // This is a new operand
3863 oper = form ? form->is_operand() : NULL; 4062 OperandForm *oper = form->is_operand();
3864 if (oper == NULL) { 4063 if (oper == NULL) {
3865 parse_err(SYNERR, "instruction/operand name expected at %s\n", ident); 4064 parse_err(SYNERR, "instruction/operand name expected at %s\n", ident);
3866 continue; 4065 continue;
3867 } 4066 }
3868 // Throw the operand on the _newopers list 4067 // Throw the operand on the _newopers list
3893 } 4092 }
3894 else next_char(); // Skip the ; 4093 else next_char(); // Skip the ;
3895 skipws(); 4094 skipws();
3896 } 4095 }
3897 else { 4096 else {
4097 assert(parse_ins, "sanity");
3898 // Add instruction to list 4098 // Add instruction to list
3899 instr_and_operands = new NameAndList(ident); 4099 instr_and_operands = new NameAndList(ident);
3900 // Grab operands, build nameList of them, and then put into dictionary 4100 // Grab operands, build nameList of them, and then put into dictionary
3901 skipws(); 4101 skipws();
3902 if (_curchar != '(') { // Check for parenthesized operand list 4102 if (_curchar != '(') { // Check for parenthesized operand list
3916 const Form *form2 = instr->_localNames[ident2]; 4116 const Form *form2 = instr->_localNames[ident2];
3917 if (!form2) { 4117 if (!form2) {
3918 parse_err(SYNERR, "operand name expected at %s\n", ident2); 4118 parse_err(SYNERR, "operand name expected at %s\n", ident2);
3919 continue; 4119 continue;
3920 } 4120 }
3921 oper = form2->is_operand(); 4121 OperandForm *oper = form2->is_operand();
3922 if (oper == NULL && !form2->is_opclass()) { 4122 if (oper == NULL && !form2->is_opclass()) {
3923 parse_err(SYNERR, "operand name expected at %s\n", ident2); 4123 parse_err(SYNERR, "operand name expected at %s\n", ident2);
3924 continue; 4124 continue;
3925 } // Add operand to list 4125 } // Add operand to list
3926 instr_and_operands->add_entry(ident2); 4126 instr_and_operands->add_entry(ident2);