IntType.java revision 1620:7ac82655d829
177957Sbenno/*
277957Sbenno * Copyright (c) 2010, 2013, Oracle and/or its affiliates. All rights reserved.
377957Sbenno * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4139825Simp *
577957Sbenno * This code is free software; you can redistribute it and/or modify it
677957Sbenno * under the terms of the GNU General Public License version 2 only, as
777957Sbenno * published by the Free Software Foundation.  Oracle designates this
877957Sbenno * particular file as subject to the "Classpath" exception as provided
977957Sbenno * by Oracle in the LICENSE file that accompanied this code.
1077957Sbenno *
1177957Sbenno * This code is distributed in the hope that it will be useful, but WITHOUT
1277957Sbenno * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
1377957Sbenno * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
1477957Sbenno * version 2 for more details (a copy is included in the LICENSE file that
1577957Sbenno * accompanied this code).
1677957Sbenno *
1777957Sbenno * You should have received a copy of the GNU General Public License version
1877957Sbenno * 2 along with this work; if not, write to the Free Software Foundation,
1977957Sbenno * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
2077957Sbenno *
2177957Sbenno * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
2277957Sbenno * or visit www.oracle.com if you need additional information or have any
2377957Sbenno * questions.
2477957Sbenno */
2577957Sbenno
2677957Sbennopackage jdk.nashorn.internal.codegen.types;
2777957Sbenno
28139825Simpimport static jdk.internal.org.objectweb.asm.Opcodes.BIPUSH;
2977957Sbennoimport static jdk.internal.org.objectweb.asm.Opcodes.I2D;
3077957Sbennoimport static jdk.internal.org.objectweb.asm.Opcodes.I2L;
3177957Sbennoimport static jdk.internal.org.objectweb.asm.Opcodes.IADD;
3277957Sbennoimport static jdk.internal.org.objectweb.asm.Opcodes.IAND;
3377957Sbennoimport static jdk.internal.org.objectweb.asm.Opcodes.ICONST_0;
3477957Sbennoimport static jdk.internal.org.objectweb.asm.Opcodes.ICONST_1;
3577957Sbennoimport static jdk.internal.org.objectweb.asm.Opcodes.ICONST_2;
3677957Sbennoimport static jdk.internal.org.objectweb.asm.Opcodes.ICONST_3;
3777957Sbennoimport static jdk.internal.org.objectweb.asm.Opcodes.ICONST_4;
3877957Sbennoimport static jdk.internal.org.objectweb.asm.Opcodes.ICONST_5;
3977957Sbennoimport static jdk.internal.org.objectweb.asm.Opcodes.ICONST_M1;
4077957Sbennoimport static jdk.internal.org.objectweb.asm.Opcodes.ILOAD;
4177957Sbennoimport static jdk.internal.org.objectweb.asm.Opcodes.IMUL;
4277957Sbennoimport static jdk.internal.org.objectweb.asm.Opcodes.INEG;
4377957Sbennoimport static jdk.internal.org.objectweb.asm.Opcodes.IOR;
4477957Sbennoimport static jdk.internal.org.objectweb.asm.Opcodes.IRETURN;
4577957Sbennoimport static jdk.internal.org.objectweb.asm.Opcodes.ISHL;
4677957Sbennoimport static jdk.internal.org.objectweb.asm.Opcodes.ISHR;
4777957Sbennoimport static jdk.internal.org.objectweb.asm.Opcodes.ISTORE;
4877957Sbennoimport static jdk.internal.org.objectweb.asm.Opcodes.ISUB;
4977957Sbennoimport static jdk.internal.org.objectweb.asm.Opcodes.IUSHR;
5077957Sbennoimport static jdk.internal.org.objectweb.asm.Opcodes.IXOR;
5177957Sbennoimport static jdk.internal.org.objectweb.asm.Opcodes.SIPUSH;
5277957Sbennoimport static jdk.nashorn.internal.codegen.CompilerConstants.staticCallNoLookup;
5377957Sbennoimport static jdk.nashorn.internal.runtime.JSType.UNDEFINED_INT;
5477957Sbennoimport static jdk.nashorn.internal.runtime.UnwarrantedOptimismException.INVALID_PROGRAM_POINT;
5577957Sbenno
5677957Sbennoimport jdk.internal.org.objectweb.asm.MethodVisitor;
5777957Sbennoimport jdk.nashorn.internal.codegen.CompilerConstants;
5877957Sbennoimport jdk.nashorn.internal.runtime.JSType;
5977957Sbenno
60198723Snwhitehorn/**
6177957Sbenno * Type class: INT
6277957Sbenno */
6377957Sbennoclass IntType extends BitwiseType {
6477957Sbenno    private static final long serialVersionUID = 1L;
6577957Sbenno
6677957Sbenno    private static final CompilerConstants.Call TO_STRING = staticCallNoLookup(Integer.class, "toString", String.class, int.class);
6777957Sbenno    private static final CompilerConstants.Call VALUE_OF  = staticCallNoLookup(Integer.class, "valueOf", Integer.class, int.class);
6877957Sbenno
69178628Smarcel    protected IntType() {
70178628Smarcel        super("int", int.class, 2, 1);
71178628Smarcel    }
72223485Snwhitehorn
73178628Smarcel    @Override
74178628Smarcel    public Type nextWider() {
75178628Smarcel        return NUMBER;
76172887Sgrehan    }
77172887Sgrehan
78172887Sgrehan    @Override
79118893Sgrehan    public Class<?> getBoxedType() {
80118893Sgrehan        return Integer.class;
8177957Sbenno    }
8277957Sbenno
83198723Snwhitehorn    @Override
84198723Snwhitehorn    public char getBytecodeStackType() {
85118893Sgrehan        return 'I';
86118893Sgrehan    }
8791486Sbenno
88198723Snwhitehorn    @Override
8991486Sbenno    public Type ldc(final MethodVisitor method, final Object c) {
90198723Snwhitehorn        assert c instanceof Integer;
91198723Snwhitehorn
9277957Sbenno        final int value = ((Integer) c);
93118893Sgrehan
94223485Snwhitehorn        switch (value) {
95198723Snwhitehorn        case -1:
96198731Snwhitehorn            method.visitInsn(ICONST_M1);
97118893Sgrehan            break;
98198731Snwhitehorn        case 0:
99178628Smarcel            method.visitInsn(ICONST_0);
100198731Snwhitehorn            break;
10186066Smp        case 1:
10286066Smp            method.visitInsn(ICONST_1);
103188860Snwhitehorn            break;
104188860Snwhitehorn        case 2:
105198731Snwhitehorn            method.visitInsn(ICONST_2);
106198731Snwhitehorn            break;
107188860Snwhitehorn        case 3:
108198731Snwhitehorn            method.visitInsn(ICONST_3);
109188860Snwhitehorn            break;
110188860Snwhitehorn        case 4:
111188860Snwhitehorn            method.visitInsn(ICONST_4);
112188860Snwhitehorn            break;
113118893Sgrehan        case 5:
11491486Sbenno            method.visitInsn(ICONST_5);
11591486Sbenno            break;
116234517Snwhitehorn        default:
117198723Snwhitehorn            if (value == (byte) value) {
118198723Snwhitehorn                method.visitIntInsn(BIPUSH, value);
119178628Smarcel            } else if (value == (short) value) {
120198723Snwhitehorn                method.visitIntInsn(SIPUSH, value);
121198723Snwhitehorn            } else {
122198723Snwhitehorn                method.visitLdcInsn(c);
123198723Snwhitehorn            }
124198723Snwhitehorn            break;
125223485Snwhitehorn        }
126198723Snwhitehorn
127235013Snwhitehorn        return Type.INT;
128235013Snwhitehorn    }
129198723Snwhitehorn
130198723Snwhitehorn    @Override
131118893Sgrehan    public Type convert(final MethodVisitor method, final Type to) {
132223485Snwhitehorn        if (to.isEquivalentTo(this)) {
133223485Snwhitehorn            return to;
134118893Sgrehan        }
13577957Sbenno
136223485Snwhitehorn        if (to.isNumber()) {
137183088Smarcel            method.visitInsn(I2D);
138183088Smarcel        } else if (to.isLong()) {
139178628Smarcel            method.visitInsn(I2L);
140178628Smarcel        } else if (to.isBoolean()) {
141118893Sgrehan            //nop
142188860Snwhitehorn        } else if (to.isString()) {
143223485Snwhitehorn            invokestatic(method, TO_STRING);
14486066Smp        } else if (to.isObject()) {
14586066Smp            invokestatic(method, VALUE_OF);
146188860Snwhitehorn        } else {
147188860Snwhitehorn            throw new UnsupportedOperationException("Illegal conversion " + this + " -> " + to);
148188860Snwhitehorn        }
149188860Snwhitehorn
150188860Snwhitehorn        return to;
151223485Snwhitehorn    }
152188860Snwhitehorn
153188860Snwhitehorn    @Override
15499036Sbenno    public Type add(final MethodVisitor method, final int programPoint) {
155188860Snwhitehorn        if(programPoint == INVALID_PROGRAM_POINT) {
156118893Sgrehan            method.visitInsn(IADD);
15799036Sbenno        } else {
15899036Sbenno            method.visitInvokeDynamicInsn("iadd", "(II)I", MATHBOOTSTRAP, programPoint);
15984945Smp        }
16099036Sbenno        return INT;
16191486Sbenno    }
162209975Snwhitehorn
163214607Snwhitehorn    @Override
164105611Sgrehan    public Type shr(final MethodVisitor method) {
165105611Sgrehan        method.visitInsn(IUSHR);
16699036Sbenno        return INT;
167190704Smarcel    }
168190704Smarcel
169190704Smarcel    @Override
170190704Smarcel    public Type sar(final MethodVisitor method) {
171190704Smarcel        method.visitInsn(ISHR);
172190704Smarcel        return INT;
17377957Sbenno    }
17477957Sbenno
17577957Sbenno    @Override
17684945Smp    public Type shl(final MethodVisitor method) {
17784945Smp        method.visitInsn(ISHL);
17877957Sbenno        return INT;
17977957Sbenno    }
18099036Sbenno
18184945Smp    @Override
182197962Snwhitehorn    public Type and(final MethodVisitor method) {
18377957Sbenno        method.visitInsn(IAND);
18491467Sbenno        return INT;
18591467Sbenno    }
18691467Sbenno
18791467Sbenno    @Override
18891467Sbenno    public Type or(final MethodVisitor method) {
18991467Sbenno        method.visitInsn(IOR);
19095719Sbenno        return INT;
19195719Sbenno    }
19295719Sbenno
19391467Sbenno    @Override
194132520Sgrehan    public Type xor(final MethodVisitor method) {
195132520Sgrehan        method.visitInsn(IXOR);
196132520Sgrehan        return INT;
197132520Sgrehan    }
19895719Sbenno
199    @Override
200    public Type load(final MethodVisitor method, final int slot) {
201        assert slot != -1;
202        method.visitVarInsn(ILOAD, slot);
203        return INT;
204    }
205
206    @Override
207    public void store(final MethodVisitor method, final int slot) {
208        assert slot != -1;
209        method.visitVarInsn(ISTORE, slot);
210    }
211
212    @Override
213    public Type sub(final MethodVisitor method, final int programPoint) {
214        if(programPoint == INVALID_PROGRAM_POINT) {
215            method.visitInsn(ISUB);
216        } else {
217            method.visitInvokeDynamicInsn("isub", "(II)I", MATHBOOTSTRAP, programPoint);
218        }
219        return INT;
220    }
221
222    @Override
223    public Type mul(final MethodVisitor method, final int programPoint) {
224        if(programPoint == INVALID_PROGRAM_POINT) {
225            method.visitInsn(IMUL);
226        } else {
227            method.visitInvokeDynamicInsn("imul", "(II)I", MATHBOOTSTRAP, programPoint);
228        }
229        return INT;
230    }
231
232    @Override
233    public Type div(final MethodVisitor method, final int programPoint) {
234        if (programPoint == INVALID_PROGRAM_POINT) {
235            JSType.DIV_ZERO.invoke(method);
236        } else {
237            method.visitInvokeDynamicInsn("idiv", "(II)I", MATHBOOTSTRAP, programPoint);
238        }
239        return INT;
240    }
241
242    @Override
243    public Type rem(final MethodVisitor method, final int programPoint) {
244        if (programPoint == INVALID_PROGRAM_POINT) {
245            JSType.REM_ZERO.invoke(method);
246        } else {
247            method.visitInvokeDynamicInsn("irem", "(II)I", MATHBOOTSTRAP, programPoint);
248        }
249        return INT;
250    }
251
252    @Override
253    public Type neg(final MethodVisitor method, final int programPoint) {
254        if(programPoint == INVALID_PROGRAM_POINT) {
255            method.visitInsn(INEG);
256        } else {
257            method.visitInvokeDynamicInsn("ineg", "(I)I", MATHBOOTSTRAP, programPoint);
258        }
259        return INT;
260    }
261
262    @Override
263    public void _return(final MethodVisitor method) {
264        method.visitInsn(IRETURN);
265    }
266
267    @Override
268    public Type loadUndefined(final MethodVisitor method) {
269        method.visitLdcInsn(UNDEFINED_INT);
270        return INT;
271    }
272
273    @Override
274    public Type loadForcedInitializer(final MethodVisitor method) {
275        method.visitInsn(ICONST_0);
276        return INT;
277    }
278
279    @Override
280    public Type cmp(final MethodVisitor method, final boolean isCmpG) {
281        throw new UnsupportedOperationException("cmp" + (isCmpG ? 'g' : 'l'));
282    }
283
284    @Override
285    public Type cmp(final MethodVisitor method) {
286        throw new UnsupportedOperationException("cmp");
287    }
288
289}
290