Package org.renjin.gcc.translate.var

Source Code of org.renjin.gcc.translate.var.PrimitiveArrayPtrVar

package org.renjin.gcc.translate.var;


import org.renjin.gcc.jimple.JimpleExpr;
import org.renjin.gcc.jimple.JimpleType;
import org.renjin.gcc.translate.FunctionContext;
import org.renjin.gcc.translate.expr.*;
import org.renjin.gcc.translate.type.ImIndirectType;
import org.renjin.gcc.translate.type.ImPrimitiveArrayPtrType;
import org.renjin.gcc.translate.type.ImPrimitiveType;
import org.renjin.gcc.translate.type.ImType;

public class PrimitiveArrayPtrVar extends AbstractImExpr implements Variable,ImIndirectExpr {

  private FunctionContext context;
  private final String jimpleArrayName;
  private final String jimpleStartIndexName;
  private final ImPrimitiveArrayPtrType type;
  private int lowerBound;

  public PrimitiveArrayPtrVar(FunctionContext context, String name, ImPrimitiveArrayPtrType type) {
    this.context = context;
    this.jimpleArrayName = name;
    this.jimpleStartIndexName = name + "_offset";
    this.type = type;
    this.lowerBound = type.baseType().getLowerBound();

    context.getBuilder().addVarDecl(type.baseType().componentType().getArrayClass(), name);
    context.getBuilder().addVarDecl(JimpleType.INT, jimpleStartIndexName);
  }

  @Override
  public void writeAssignment(FunctionContext context, ImExpr rhs) {
    if(rhs.isNull()) {
      context.getBuilder().addStatement(jimpleArrayName + " = null");
    } else if(rhs instanceof ImIndirectExpr) {
      ArrayRef ptr = ((ImIndirectExpr) rhs).translateToArrayRef(context);
      context.getBuilder().addStatement(jimpleArrayName + " = " +  ptr.getArrayExpr());
      context.getBuilder().addStatement(jimpleStartIndexName + " = " + ptr.getIndexExpr());
    } else {
      throw new UnsupportedOperationException(rhs.toString());
    }
  }

  @Override
  public ArrayRef translateToArrayRef(FunctionContext context) {
    return new ArrayRef(jimpleArrayName, jimpleStartIndexName);
  }

  @Override
  public ImIndirectType type() {
    return type;
  }

  @Override
  public ImExpr memref() {
    return new ArrayValue();
  }

  @Override
  public String toString() {
    return jimpleArrayName;
  }

  private JimpleExpr computeIndex(ImExpr index) {
    JimpleExpr indexExpr = index.translateToPrimitive(context, ImPrimitiveType.INT);
    JimpleExpr finalIndex = context.declareTemp(JimpleType.INT,
        JimpleExpr.binaryInfix("+", new JimpleExpr(jimpleStartIndexName), indexExpr));

    if(lowerBound != 0) {
      finalIndex = context.declareTemp(JimpleType.INT,
          JimpleExpr.binaryInfix("-", finalIndex, JimpleExpr.integerConstant(lowerBound)));
    }

    return finalIndex;
  }

  private class ArrayValue extends AbstractImExpr {

    @Override
    public ImExpr addressOf() {
      return PrimitiveArrayPtrVar.this;
    }

    @Override
    public ImExpr elementAt(ImExpr index) {
      return new ArrayElement(index);

    }

    @Override
    public ImType type() {
      return type.baseType();
    }
  }

  private class ArrayElement extends AbstractImExpr implements ImLValue {

    private final ImExpr index;

    public ArrayElement(ImExpr index) {
      this.index = index;
    }

    @Override
    public ImType type() {
      return type.baseType().componentType();
    }

    @Override
    public ImExpr addressOf() {
      return new ArrayElementAddress(index);
    }

    @Override
    public void writeAssignment(FunctionContext context, ImExpr rhs) {
      context.getBuilder().addAssignment(jimpleArrayName + "[" + computeIndex(index) + "]",
          rhs.translateToPrimitive(context, type.baseType().componentType()));
    }

    @Override
    public JimpleExpr translateToPrimitive(FunctionContext context, ImPrimitiveType type) {
      return new JimpleExpr(jimpleArrayName + "[" + computeIndex(index) + "]");
    }
  }

  private class ArrayElementAddress extends AbstractImExpr implements ImIndirectExpr {

    private ImExpr index;

    private ArrayElementAddress(ImExpr index) {
      this.index = index;
    }

    @Override
    public ArrayRef translateToArrayRef(FunctionContext context) {
      return new ArrayRef(jimpleArrayName, computeIndex(index));
    }

    @Override
    public ImIndirectType type() {
      return type.baseType().componentType().pointerType();
    }
  }


}
TOP

Related Classes of org.renjin.gcc.translate.var.PrimitiveArrayPtrVar

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.