Skip to content

Commit

Permalink
8259777: Incorrect predication condition generated by ADLC
Browse files Browse the repository at this point in the history
Reviewed-by: vlivanov
  • Loading branch information
jbhateja committed Jan 15, 2021
1 parent 9127e05 commit fef7514
Show file tree
Hide file tree
Showing 2 changed files with 26 additions and 11 deletions.
35 changes: 25 additions & 10 deletions src/hotspot/share/adlc/formssel.cpp
Expand Up @@ -1527,6 +1527,7 @@ Predicate *InstructForm::build_predicate() {
for( DictI i(&names); i.test(); ++i ) {
uintptr_t cnt = (uintptr_t)i._value;
if( cnt > 1 ) { // Need a predicate at all?
int path_bitmask = 0;
assert( cnt == 2, "Unimplemented" );
// Handle many pairs
if( first ) first=0;
Expand All @@ -1537,10 +1538,10 @@ Predicate *InstructForm::build_predicate() {
// Add predicate to working buffer
sprintf(s,"/*%s*/(",(char*)i._key);
s += strlen(s);
mnode->build_instr_pred(s,(char*)i._key,0);
mnode->build_instr_pred(s,(char*)i._key, 0, path_bitmask, 0);
s += strlen(s);
strcpy(s," == "); s += strlen(s);
mnode->build_instr_pred(s,(char*)i._key,1);
mnode->build_instr_pred(s,(char*)i._key, 1, path_bitmask, 0);
s += strlen(s);
strcpy(s,")"); s += strlen(s);
}
Expand Down Expand Up @@ -3426,21 +3427,35 @@ void MatchNode::count_instr_names( Dict &names ) {
//------------------------------build_instr_pred-------------------------------
// Build a path to 'name' in buf. Actually only build if cnt is zero, so we
// can skip some leading instances of 'name'.
int MatchNode::build_instr_pred( char *buf, const char *name, int cnt ) {
int MatchNode::build_instr_pred( char *buf, const char *name, int cnt, int path_bitmask, int level) {
if( _lChild ) {
if( !cnt ) strcpy( buf, "_kids[0]->" );
cnt = _lChild->build_instr_pred( buf+strlen(buf), name, cnt );
if( cnt < 0 ) return cnt; // Found it, all done
cnt = _lChild->build_instr_pred(buf, name, cnt, path_bitmask, level+1);
if( cnt < 0 ) {
return cnt; // Found it, all done
}
}
if( _rChild ) {
if( !cnt ) strcpy( buf, "_kids[1]->" );
cnt = _rChild->build_instr_pred( buf+strlen(buf), name, cnt );
if( cnt < 0 ) return cnt; // Found it, all done
path_bitmask |= 1 << level;
cnt = _rChild->build_instr_pred( buf, name, cnt, path_bitmask, level+1);
if( cnt < 0 ) {
return cnt; // Found it, all done
}
}
if( !_lChild && !_rChild ) { // Found a leaf
// Wrong name? Give up...
if( strcmp(name,_name) ) return cnt;
if( !cnt ) strcpy(buf,"_leaf");
if( !cnt ) {
for(int i = 0; i < level; i++) {
int kid = path_bitmask & (1 << i);
if (0 == kid) {
strcpy( buf, "_kids[0]->" );
} else {
strcpy( buf, "_kids[1]->" );
}
buf += 10;
}
strcpy( buf, "_leaf" );
}
return cnt-1;
}
return cnt;
Expand Down
2 changes: 1 addition & 1 deletion src/hotspot/share/adlc/formssel.hpp
Expand Up @@ -969,7 +969,7 @@ class MatchNode : public Form {

// Help build instruction predicates. Search for operand names.
void count_instr_names( Dict &names );
int build_instr_pred( char *buf, const char *name, int cnt );
int build_instr_pred( char *buf, const char *name, int cnt, int path_bitmask, int level);
void build_internalop( );

// Return the name of the operands associated with reducing to this operand:
Expand Down

0 comments on commit fef7514

Please sign in to comment.