2703 // following nodes will have the control of the MemBarCPUOrder inserted at
2704 // the end of this method. So, pushing the load onto the stack at a later
2705 // point is fine.
2706 set_result(p);
2707 } else {
2708 // place effect of store into memory
2709 switch (type) {
2710 case T_DOUBLE:
2711 val = dstore_rounding(val);
2712 break;
2713 case T_ADDRESS:
2714 // Repackage the long as a pointer.
2715 val = ConvL2X(val);
2716 val = _gvn.transform(new CastX2PNode(val));
2717 break;
2718 default:
2719 break;
2720 }
2721
2722 if (type == T_OBJECT) {
2723 store_oop_to_unknown(control(), heap_base_oop, adr, adr_type, val, type, mo, mismatched);
2724 } else {
2725 store_to_memory(control(), adr, val, type, adr_type, mo, requires_atomic_access, unaligned, mismatched);
2726 }
2727 }
2728
2729 switch(kind) {
2730 case Relaxed:
2731 case Opaque:
2732 case Release:
2733 break;
2734 case Acquire:
2735 case Volatile:
2736 if (!is_store) {
2737 insert_mem_bar(Op_MemBarAcquire);
2738 } else {
2739 if (!support_IRIW_for_not_multiple_copy_atomic_cpu) {
2740 insert_mem_bar(Op_MemBarVolatile);
2741 }
2742 }
3052 case LS_cmp_swap_weak:
3053 load_store = _gvn.transform(new WeakCompareAndSwapLNode(control(), mem, adr, newval, oldval, mo));
3054 break;
3055 case LS_cmp_swap:
3056 load_store = _gvn.transform(new CompareAndSwapLNode(control(), mem, adr, newval, oldval, mo));
3057 break;
3058 case LS_cmp_exchange:
3059 load_store = _gvn.transform(new CompareAndExchangeLNode(control(), mem, adr, newval, oldval, adr_type, mo));
3060 break;
3061 default:
3062 ShouldNotReachHere();
3063 }
3064 break;
3065 case T_OBJECT:
3066 // Transformation of a value which could be NULL pointer (CastPP #NULL)
3067 // could be delayed during Parse (for example, in adjust_map_after_if()).
3068 // Execute transformation here to avoid barrier generation in such case.
3069 if (_gvn.type(newval) == TypePtr::NULL_PTR)
3070 newval = _gvn.makecon(TypePtr::NULL_PTR);
3071
3072 // Reference stores need a store barrier.
3073 switch(kind) {
3074 case LS_get_set: {
3075 // If pre-barrier must execute before the oop store, old value will require do_load here.
3076 if (!can_move_pre_barrier()) {
3077 newval = pre_barrier(true /* do_load*/,
3078 control(), base, adr, alias_idx, newval, value_type->make_oopptr(),
3079 NULL /* pre_val*/,
3080 T_OBJECT);
3081 } // Else move pre_barrier to use load_store value, see below.
3082 else {
3083 newval = shenandoah_storeval_barrier(newval);
3084 }
3085 break;
3086 }
3087 case LS_cmp_swap_weak:
3088 case LS_cmp_swap:
3089 case LS_cmp_exchange: {
3090 // Same as for newval above:
3091 if (_gvn.type(oldval) == TypePtr::NULL_PTR) {
3092 oldval = _gvn.makecon(TypePtr::NULL_PTR);
3093 }
3094 // The only known value which might get overwritten is oldval.
3095 newval = pre_barrier(false /* do_load */,
3096 control(), NULL, adr, max_juint, newval, NULL,
3097 oldval /* pre_val */,
3098 T_OBJECT);
3099 break;
3100 }
3101 default:
3102 ShouldNotReachHere();
3103 }
3104
3105 #ifdef _LP64
3106 if (adr->bottom_type()->is_ptr_to_narrowoop()) {
3107 Node *newval_enc = _gvn.transform(new EncodePNode(newval, newval->bottom_type()->make_narrowoop()));
3108
3109 switch(kind) {
3110 case LS_get_set:
3111 load_store = _gvn.transform(new GetAndSetNNode(control(), mem, adr, newval_enc, adr_type, value_type->make_narrowoop()));
3112 break;
3113 case LS_cmp_swap_weak: {
3114 Node *oldval_enc = _gvn.transform(new EncodePNode(oldval, oldval->bottom_type()->make_narrowoop()));
3115 load_store = _gvn.transform(new WeakCompareAndSwapNNode(control(), mem, adr, newval_enc, oldval_enc, mo));
|
2703 // following nodes will have the control of the MemBarCPUOrder inserted at
2704 // the end of this method. So, pushing the load onto the stack at a later
2705 // point is fine.
2706 set_result(p);
2707 } else {
2708 // place effect of store into memory
2709 switch (type) {
2710 case T_DOUBLE:
2711 val = dstore_rounding(val);
2712 break;
2713 case T_ADDRESS:
2714 // Repackage the long as a pointer.
2715 val = ConvL2X(val);
2716 val = _gvn.transform(new CastX2PNode(val));
2717 break;
2718 default:
2719 break;
2720 }
2721
2722 if (type == T_OBJECT) {
2723 val = shenandoah_storeval_barrier(val);
2724 store_oop_to_unknown(control(), heap_base_oop, adr, adr_type, val, type, mo, mismatched);
2725 } else {
2726 store_to_memory(control(), adr, val, type, adr_type, mo, requires_atomic_access, unaligned, mismatched);
2727 }
2728 }
2729
2730 switch(kind) {
2731 case Relaxed:
2732 case Opaque:
2733 case Release:
2734 break;
2735 case Acquire:
2736 case Volatile:
2737 if (!is_store) {
2738 insert_mem_bar(Op_MemBarAcquire);
2739 } else {
2740 if (!support_IRIW_for_not_multiple_copy_atomic_cpu) {
2741 insert_mem_bar(Op_MemBarVolatile);
2742 }
2743 }
3053 case LS_cmp_swap_weak:
3054 load_store = _gvn.transform(new WeakCompareAndSwapLNode(control(), mem, adr, newval, oldval, mo));
3055 break;
3056 case LS_cmp_swap:
3057 load_store = _gvn.transform(new CompareAndSwapLNode(control(), mem, adr, newval, oldval, mo));
3058 break;
3059 case LS_cmp_exchange:
3060 load_store = _gvn.transform(new CompareAndExchangeLNode(control(), mem, adr, newval, oldval, adr_type, mo));
3061 break;
3062 default:
3063 ShouldNotReachHere();
3064 }
3065 break;
3066 case T_OBJECT:
3067 // Transformation of a value which could be NULL pointer (CastPP #NULL)
3068 // could be delayed during Parse (for example, in adjust_map_after_if()).
3069 // Execute transformation here to avoid barrier generation in such case.
3070 if (_gvn.type(newval) == TypePtr::NULL_PTR)
3071 newval = _gvn.makecon(TypePtr::NULL_PTR);
3072
3073 newval = shenandoah_storeval_barrier(newval);
3074
3075 // Reference stores need a store barrier.
3076 switch(kind) {
3077 case LS_get_set: {
3078 // If pre-barrier must execute before the oop store, old value will require do_load here.
3079 if (!can_move_pre_barrier()) {
3080 pre_barrier(true /* do_load*/,
3081 control(), base, adr, alias_idx, newval, value_type->make_oopptr(),
3082 NULL /* pre_val*/,
3083 T_OBJECT);
3084 } // Else move pre_barrier to use load_store value, see below.
3085 break;
3086 }
3087 case LS_cmp_swap_weak:
3088 case LS_cmp_swap:
3089 case LS_cmp_exchange: {
3090 // Same as for newval above:
3091 if (_gvn.type(oldval) == TypePtr::NULL_PTR) {
3092 oldval = _gvn.makecon(TypePtr::NULL_PTR);
3093 }
3094 // The only known value which might get overwritten is oldval.
3095 pre_barrier(false /* do_load */,
3096 control(), NULL, adr, max_juint, newval, NULL,
3097 oldval /* pre_val */,
3098 T_OBJECT);
3099 break;
3100 }
3101 default:
3102 ShouldNotReachHere();
3103 }
3104
3105 #ifdef _LP64
3106 if (adr->bottom_type()->is_ptr_to_narrowoop()) {
3107 Node *newval_enc = _gvn.transform(new EncodePNode(newval, newval->bottom_type()->make_narrowoop()));
3108
3109 switch(kind) {
3110 case LS_get_set:
3111 load_store = _gvn.transform(new GetAndSetNNode(control(), mem, adr, newval_enc, adr_type, value_type->make_narrowoop()));
3112 break;
3113 case LS_cmp_swap_weak: {
3114 Node *oldval_enc = _gvn.transform(new EncodePNode(oldval, oldval->bottom_type()->make_narrowoop()));
3115 load_store = _gvn.transform(new WeakCompareAndSwapNNode(control(), mem, adr, newval_enc, oldval_enc, mo));
|