# HG changeset patch # User Andreas Woess # Date 1416918110 -3600 # Node ID cb4d5cc2b52b34c0988bee4eb8445d9375beeb86 # Parent 7bf2965140defb27ed6d21eaba193599aa142631 Truffle: clone ConditionProfile and BranchProfile node fields diff -r 7bf2965140de -r cb4d5cc2b52b graal/com.oracle.truffle.api/src/com/oracle/truffle/api/nodes/NodeCloneable.java --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/nodes/NodeCloneable.java Tue Nov 25 13:21:50 2014 +0100 @@ -0,0 +1,32 @@ +/* + * Copyright (c) 2014, 2014, Oracle and/or its affiliates. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. Oracle designates this + * particular file as subject to the "Classpath" exception as provided + * by Oracle in the LICENSE file that accompanied this code. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA + * or visit www.oracle.com if you need additional information or have any + * questions. + */ +package com.oracle.truffle.api.nodes; + +/** + * Declarative interface for node fields that are to be cloned together with the containing node. + */ +public interface NodeCloneable extends Cloneable { + public Object clone(); +} diff -r 7bf2965140de -r cb4d5cc2b52b graal/com.oracle.truffle.api/src/com/oracle/truffle/api/nodes/NodeUtil.java --- a/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/nodes/NodeUtil.java Tue Nov 25 13:21:38 2014 +0100 +++ b/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/nodes/NodeUtil.java Tue Nov 25 13:21:50 2014 +0100 @@ -179,6 +179,7 @@ private final long parentOffset; private final long[] childOffsets; private final long[] childrenOffsets; + private final long[] cloneableOffsets; private final Class clazz; public static NodeClass get(Class clazz) { @@ -190,6 +191,7 @@ long parentFieldOffset = -1; List childOffsetsList = new ArrayList<>(); List childrenOffsetsList = new ArrayList<>(); + List cloneableOffsetsList = new ArrayList<>(); for (Field field : getAllFields(clazz)) { if (Modifier.isStatic(field.getModifiers()) || field.isSynthetic()) { @@ -209,6 +211,9 @@ checkChildrenField(field); kind = NodeFieldKind.CHILDREN; childrenOffsetsList.add(fieldOffsetProvider.objectFieldOffset(field)); + } else if (NodeCloneable.class.isAssignableFrom(field.getType())) { + kind = NodeFieldKind.DATA; + cloneableOffsetsList.add(fieldOffsetProvider.objectFieldOffset(field)); } else { kind = NodeFieldKind.DATA; } @@ -223,6 +228,7 @@ this.parentOffset = parentFieldOffset; this.childOffsets = toLongArray(childOffsetsList); this.childrenOffsets = toLongArray(childrenOffsetsList); + this.cloneableOffsets = toLongArray(cloneableOffsetsList); this.clazz = clazz; } @@ -471,6 +477,12 @@ unsafe.putObject(clone, fieldOffset, clonedChildren); } } + for (long fieldOffset : nodeClass.cloneableOffsets) { + Object cloneable = unsafe.getObject(clone, fieldOffset); + if (cloneable != null && cloneable == unsafe.getObject(orig, fieldOffset)) { + unsafe.putObject(clone, fieldOffset, ((NodeCloneable) cloneable).clone()); + } + } return (T) clone; } diff -r 7bf2965140de -r cb4d5cc2b52b graal/com.oracle.truffle.api/src/com/oracle/truffle/api/utilities/BranchProfile.java --- a/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/utilities/BranchProfile.java Tue Nov 25 13:21:38 2014 +0100 +++ b/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/utilities/BranchProfile.java Tue Nov 25 13:21:50 2014 +0100 @@ -26,6 +26,7 @@ import com.oracle.truffle.api.*; import com.oracle.truffle.api.CompilerDirectives.CompilationFinal; +import com.oracle.truffle.api.nodes.*; /** * Utility class to speculate on branches to be never visited. If the {@link #enter()} method is @@ -36,7 +37,7 @@ * All {@code BranchProfile} instances must be held in {@code final} fields for compiler * optimizations to take effect. */ -public final class BranchProfile { +public final class BranchProfile implements NodeCloneable { @CompilationFinal private boolean visited; @@ -63,4 +64,12 @@ return String.format("%s(%s)@%x", getClass().getSimpleName(), visited ? "visited" : "not-visited", hashCode()); } + @Override + public Object clone() { + try { + return super.clone(); + } catch (CloneNotSupportedException e) { + throw new AssertionError(e); + } + } } diff -r 7bf2965140de -r cb4d5cc2b52b graal/com.oracle.truffle.api/src/com/oracle/truffle/api/utilities/ConditionProfile.java --- a/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/utilities/ConditionProfile.java Tue Nov 25 13:21:38 2014 +0100 +++ b/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/utilities/ConditionProfile.java Tue Nov 25 13:21:50 2014 +0100 @@ -25,6 +25,7 @@ package com.oracle.truffle.api.utilities; import com.oracle.truffle.api.*; +import com.oracle.truffle.api.nodes.*; /** * Abstract utility class to speculate on conditions. Condition profiles are intended to be used as @@ -50,7 +51,7 @@ * @see #createCountingProfile() * @see #createBinaryProfile() */ -public abstract class ConditionProfile { +public abstract class ConditionProfile implements NodeCloneable { public abstract boolean profile(boolean value); @@ -80,4 +81,12 @@ return new BinaryConditionProfile(); } + @Override + public final Object clone() { + try { + return super.clone(); + } catch (CloneNotSupportedException e) { + throw new AssertionError(e); + } + } }