src/share/vm/opto/escape.cpp
Index Unified diffs Context diffs Sdiffs Wdiffs Patch New Old Previous File Next File 7146442 Sdiff src/share/vm/opto

src/share/vm/opto/escape.cpp

Print this page




2018           // Ignore array length load
2019         }
2020 #ifdef ASSERT
2021       } else {
2022         // Raw pointers are used for initializing stores so skip it
2023         // since it should be recorded already
2024         Node* base = get_addp_base(ptn->_node);
2025         assert(adr_type->isa_rawptr() && base->is_Proj() &&
2026                (base->in(0) == alloc),"unexpected pointer type");
2027 #endif
2028       }
2029       if (basic_field_type == T_OBJECT ||
2030           basic_field_type == T_NARROWOOP ||
2031           basic_field_type == T_ARRAY) {
2032         Node* value = NULL;
2033         if (ini != NULL) {
2034           BasicType ft = UseCompressedOops ? T_NARROWOOP : T_OBJECT;
2035           Node* store = ini->find_captured_store(offset, type2aelembytes(ft), phase);
2036           if (store != NULL && store->is_Store()) {
2037             value = store->in(MemNode::ValueIn);
2038           } else if (ptn->edge_count() > 0) { // Are there oop stores?
2039             // Check for a store which follows allocation without branches.
2040             // For example, a volatile field store is not collected
2041             // by Initialize node. TODO: it would be nice to use idom() here.
2042             //
2043             // Search all references to the same field which use different
2044             // AddP nodes, for example, in the next case:
2045             //
2046             //    Point p[] = new Point[1];
2047             //    if ( x ) { p[0] = new Point(); p[0].x = x; }
2048             //    if ( p[0] != null ) { y = p[0].x; } // has CastPP
2049             //
2050             for (uint next = ei; (next < ae_cnt) && (value == NULL); next++) {
2051               uint fpi = pta->edge_target(next); // Field (AddP)
2052               PointsToNode *ptf = ptnode_adr(fpi);
2053               if (ptf->offset() == offset) {
2054                 Node* nf = ptf->_node;
2055                 for (DUIterator_Fast imax, i = nf->fast_outs(imax); i < imax; i++) {
2056                   store = nf->fast_out(i);
2057                   if (store->is_Store() && store->in(0) != NULL) {
2058                     Node* ctrl = store->in(0);
2059                     while(!(ctrl == ini || ctrl == alloc || ctrl == NULL ||
2060                             ctrl == C->root() || ctrl == C->top() || ctrl->is_Region() ||
2061                             ctrl->is_IfTrue() || ctrl->is_IfFalse())) {
2062                        ctrl = ctrl->in(0);
2063                     }
2064                     if (ctrl == ini || ctrl == alloc) {
2065                       value = store->in(MemNode::ValueIn);
2066                       break;
2067                     }
2068                   }
2069                 }
2070               }
2071             }
2072           }
2073         }
2074         if (value == NULL || value != ptnode_adr(value->_idx)->_node) {
2075           // A field's initializing value was not recorded. Add NULL.
2076           add_edge_from_fields(alloc->_idx, null_idx, offset);
2077         }
2078       }
2079     }
2080   }
2081 }
2082 
2083 // Adjust escape state after Connection Graph is built.
2084 void ConnectionGraph::adjust_escape_state(Node* n) {
2085   PointsToNode* ptn = ptnode_adr(n->_idx);
2086   assert(n->is_AddP(), "Should be called for AddP nodes only");
2087   // Search for objects which are not scalar replaceable
2088   // and mark them to propagate the state to referenced objects.
2089   //
2090 
2091   int offset = ptn->offset();
2092   Node* base = get_addp_base(n);
2093   VectorSet* ptset = PointsTo(base);




2018           // Ignore array length load
2019         }
2020 #ifdef ASSERT
2021       } else {
2022         // Raw pointers are used for initializing stores so skip it
2023         // since it should be recorded already
2024         Node* base = get_addp_base(ptn->_node);
2025         assert(adr_type->isa_rawptr() && base->is_Proj() &&
2026                (base->in(0) == alloc),"unexpected pointer type");
2027 #endif
2028       }
2029       if (basic_field_type == T_OBJECT ||
2030           basic_field_type == T_NARROWOOP ||
2031           basic_field_type == T_ARRAY) {
2032         Node* value = NULL;
2033         if (ini != NULL) {
2034           BasicType ft = UseCompressedOops ? T_NARROWOOP : T_OBJECT;
2035           Node* store = ini->find_captured_store(offset, type2aelembytes(ft), phase);
2036           if (store != NULL && store->is_Store()) {
2037             value = store->in(MemNode::ValueIn);
2038           } else {
2039             // There could be initializing stores which follow allocation.
2040             // For example, a volatile field store is not collected
2041             // by Initialize node.
2042             //
2043             // Need to check for dependent loads to separate such stores from
2044             // stores which follow loads. For now, add initial value NULL so
2045             // that compare pointers optimization works correctly.

















2046           }



2047         }






2048         if (value == NULL || value != ptnode_adr(value->_idx)->_node) {
2049           // A field's initializing value was not recorded. Add NULL.
2050           add_edge_from_fields(alloc->_idx, null_idx, offset);
2051         }
2052       }
2053     }
2054   }
2055 }
2056 
2057 // Adjust escape state after Connection Graph is built.
2058 void ConnectionGraph::adjust_escape_state(Node* n) {
2059   PointsToNode* ptn = ptnode_adr(n->_idx);
2060   assert(n->is_AddP(), "Should be called for AddP nodes only");
2061   // Search for objects which are not scalar replaceable
2062   // and mark them to propagate the state to referenced objects.
2063   //
2064 
2065   int offset = ptn->offset();
2066   Node* base = get_addp_base(n);
2067   VectorSet* ptset = PointsTo(base);


src/share/vm/opto/escape.cpp
Index Unified diffs Context diffs Sdiffs Wdiffs Patch New Old Previous File Next File