001/*
002 * Copyright (c) 2011, Oracle and/or its affiliates. All rights reserved.
003 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
004 *
005 * This code is free software; you can redistribute it and/or modify it
006 * under the terms of the GNU General Public License version 2 only, as
007 * published by the Free Software Foundation.
008 *
009 * This code is distributed in the hope that it will be useful, but WITHOUT
010 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
011 * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
012 * version 2 for more details (a copy is included in the LICENSE file that
013 * accompanied this code).
014 *
015 * You should have received a copy of the GNU General Public License version
016 * 2 along with this work; if not, write to the Free Software Foundation,
017 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
018 *
019 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
020 * or visit www.oracle.com if you need additional information or have any
021 * questions.
022 */
023package com.oracle.graal.replacements.test;
024
025import jdk.internal.jvmci.meta.*;
026
027import org.junit.*;
028
029import com.oracle.graal.compiler.test.*;
030import com.oracle.graal.nodes.*;
031import com.oracle.graal.nodes.StructuredGraph.AllowAssumptions;
032import com.oracle.graal.replacements.*;
033import com.oracle.graal.word.*;
034
035/**
036 * Tests for the {@link Word} type.
037 */
038public class WordTest extends GraalCompilerTest implements Snippets {
039
040    private final ReplacementsImpl installer;
041
042    public WordTest() {
043        installer = (ReplacementsImpl) getReplacements();
044    }
045
046    @Override
047    protected StructuredGraph parseEager(ResolvedJavaMethod m, AllowAssumptions allowAssumptions) {
048        return installer.makeGraph(m, null, null);
049    }
050
051    @Test
052    public void construction() {
053        long[] words = new long[]{Long.MIN_VALUE, Long.MIN_VALUE + 1, -1L, 0L, 1L, Long.MAX_VALUE - 1, Long.MAX_VALUE, Integer.MAX_VALUE - 1L, Integer.MAX_VALUE, Integer.MAX_VALUE + 1L,
054                        Integer.MIN_VALUE - 1L, Integer.MIN_VALUE, Integer.MIN_VALUE + 1L};
055        for (long word : words) {
056            test("unsignedLong", word);
057            test("unsignedInt", (int) word);
058            test("signedLong", word);
059            test("signedInt", (int) word);
060        }
061    }
062
063    @Test
064    public void testArithmetic() {
065        long[] words = new long[]{Long.MIN_VALUE, Long.MIN_VALUE + 1, -1L, 0L, 1L, Long.MAX_VALUE - 1, Long.MAX_VALUE, Integer.MAX_VALUE - 1L, Integer.MAX_VALUE, Integer.MAX_VALUE + 1L,
066                        Integer.MIN_VALUE - 1L, Integer.MIN_VALUE, Integer.MIN_VALUE + 1L};
067        for (long word : words) {
068            test("unsignedNot", word);
069            test("signedNot", word);
070            for (long addend : words) {
071                test("unsignedPlusInt", word, (int) addend);
072                test("unsignedMinusInt", word, (int) addend);
073                test("unsignedPlusInt", word, -((int) addend));
074                test("unsignedMinusInt", word, -((int) addend));
075                test("unsignedPlusLong", word, addend);
076                test("unsignedMinusLong", word, addend);
077                test("unsignedPlusLong", word, -addend);
078                test("unsignedMinusLong", word, -addend);
079                test("signedPlusInt", word, (int) addend);
080                test("signedMinusInt", word, (int) addend);
081                test("signedPlusInt", word, -((int) addend));
082                test("signedMinusInt", word, -((int) addend));
083                test("signedPlusLong", word, addend);
084                test("signedMinusLong", word, addend);
085                test("signedPlusLong", word, -addend);
086                test("signedMinusLong", word, -addend);
087
088                test("andInt", word, (int) addend);
089                test("orInt", word, (int) addend);
090                test("andInt", word, -((int) addend));
091                test("orInt", word, -((int) addend));
092                test("andLong", word, addend);
093                test("orLong", word, addend);
094                test("andLong", word, -addend);
095                test("orLong", word, -addend);
096            }
097        }
098    }
099
100    @Test
101    public void testCompare() {
102        long[] words = new long[]{Long.MIN_VALUE, Long.MIN_VALUE + 1, -1L, 0L, 1L, Long.MAX_VALUE - 1, Long.MAX_VALUE};
103        for (long word1 : words) {
104            for (long word2 : words) {
105                for (String method : new String[]{"aboveOrEqual", "above", "belowOrEqual", "below"}) {
106                    test(method, word1, word2);
107                    test(method, word2, word1);
108                }
109            }
110        }
111    }
112
113    @Test
114    public void testCast() {
115        test("cast", 1234L);
116    }
117
118    @Snippet
119    public static long cast(long input) {
120        WordBase base = Word.signed(input);
121        Unsigned unsigned = (Unsigned) base;
122        Pointer pointer = (Pointer) unsigned;
123        Word word = (Word) pointer;
124        return word.rawValue();
125    }
126
127    @Snippet
128    public static long unsignedLong(long word) {
129        return Word.unsigned(word).rawValue();
130    }
131
132    @Snippet
133    public static long unsignedInt(int word) {
134        return Word.unsigned(word).rawValue();
135    }
136
137    @Snippet
138    public static long signedLong(long word) {
139        return Word.signed(word).rawValue();
140    }
141
142    @Snippet
143    public static long signedInt(int word) {
144        return Word.signed(word).rawValue();
145    }
146
147    @Snippet
148    public static long unsignedPlusInt(long word, int addend) {
149        return Word.unsigned(word).add(addend).rawValue();
150    }
151
152    @Snippet
153    public static long unsignedMinusInt(long word, int addend) {
154        return Word.unsigned(word).subtract(addend).rawValue();
155    }
156
157    @Snippet
158    public static long unsignedPlusLong(long word, long addend) {
159        return Word.unsigned(word).add(Word.unsigned(addend)).rawValue();
160    }
161
162    @Snippet
163    public static long unsignedMinusLong(long word, long addend) {
164        return Word.unsigned(word).subtract(Word.unsigned(addend)).rawValue();
165    }
166
167    @Snippet
168    public static long signedPlusInt(long word, int addend) {
169        return Word.signed(word).add(addend).rawValue();
170    }
171
172    @Snippet
173    public static long signedMinusInt(long word, int addend) {
174        return Word.signed(word).subtract(addend).rawValue();
175    }
176
177    @Snippet
178    public static long signedPlusLong(long word, long addend) {
179        return Word.signed(word).add(Word.signed(addend)).rawValue();
180    }
181
182    @Snippet
183    public static long signedMinusLong(long word, long addend) {
184        return Word.signed(word).subtract(Word.signed(addend)).rawValue();
185    }
186
187    @Snippet
188    public static long signedNot(long word) {
189        return Word.signed(word).not().rawValue();
190    }
191
192    @Snippet
193    public static long unsignedNot(long word) {
194        return Word.unsigned(word).not().rawValue();
195    }
196
197    @Snippet
198    public static boolean aboveOrEqual(long word1, long word2) {
199        return Word.unsigned(word1).aboveOrEqual(Word.unsigned(word2));
200    }
201
202    @Snippet
203    public static boolean above(long word1, long word2) {
204        return Word.unsigned(word1).aboveThan(Word.unsigned(word2));
205    }
206
207    @Snippet
208    public static boolean belowOrEqual(long word1, long word2) {
209        return Word.unsigned(word1).belowOrEqual(Word.unsigned(word2));
210    }
211
212    @Snippet
213    public static boolean below(long word1, long word2) {
214        return Word.unsigned(word1).belowThan(Word.unsigned(word2));
215    }
216
217    @Snippet
218    public static long andInt(long word, int addend) {
219        return Word.unsigned(word).and(addend).rawValue();
220    }
221
222    @Snippet
223    public static long orInt(long word, int addend) {
224        return Word.unsigned(word).or(addend).rawValue();
225    }
226
227    @Snippet
228    public static long andLong(long word, long addend) {
229        return Word.unsigned(word).and(Word.unsigned(addend)).rawValue();
230    }
231
232    @Snippet
233    public static long orLong(long word, long addend) {
234        return Word.unsigned(word).or(Word.unsigned(addend)).rawValue();
235    }
236}