// if (val != null)
// val = ((PersistenceCapable) val).pcFetchObjectId();
int pc = code.getNextLocalsIndex();
code.astore().setLocal(pc);
code.aload().setLocal(pc);
JumpInstruction ifnull1 = code.ifnull();
code.aload().setLocal(pc);
code.checkcast().setType(PersistenceCapable.class);
if (!pk.getTypeMetaData().isOpenJPAIdentity())
code.invokeinterface().setMethod(PersistenceCapable.class,
PRE + "FetchObjectId", Object.class, null);
else
code.invokeinterface().setMethod(PersistenceCapable.class,
PRE + "NewObjectIdInstance", Object.class, null);
int oid = code.getNextLocalsIndex();
code.astore().setLocal(oid);
code.aload().setLocal(oid);
JumpInstruction ifnull2 = code.ifnull();
// for datastore / single-field identity:
// if (val != null)
// val = ((OpenJPAId) val).getId();
ClassMetaData pkmeta = pk.getDeclaredTypeMetaData();
int pkcode = pk.getObjectIdFieldTypeCode();
Class pktype = pk.getObjectIdFieldType();
if (pkmeta.getIdentityType() == ClassMetaData.ID_DATASTORE
&& pkcode == JavaTypes.LONG) {
code.aload().setLocal(oid);
code.checkcast().setType(Id.class);
code.invokevirtual().setMethod(Id.class, "getId",
long.class, null);
} else if (pkmeta.getIdentityType() == ClassMetaData.ID_DATASTORE) {
code.aload().setLocal(oid);
} else if (pkmeta.isOpenJPAIdentity()) {
switch (pkcode) {
case JavaTypes.BYTE_OBJ:
code.anew().setType(Byte.class);
code.dup();
// no break
case JavaTypes.BYTE:
code.aload().setLocal(oid);
code.checkcast().setType(ByteId.class);
code.invokevirtual().setMethod(ByteId.class, "getId",
byte.class, null);
if (pkcode == JavaTypes.BYTE_OBJ)
code.invokespecial().setMethod(Byte.class, "<init>",
void.class, new Class[] {byte.class});
break;
case JavaTypes.CHAR_OBJ:
code.anew().setType(Character.class);
code.dup();
// no break
case JavaTypes.CHAR:
code.aload().setLocal(oid);
code.checkcast().setType(CharId.class);
code.invokevirtual().setMethod(CharId.class, "getId",
char.class, null);
if (pkcode == JavaTypes.CHAR_OBJ)
code.invokespecial().setMethod(Character.class,
"<init>", void.class, new Class[] {char.class});
break;
case JavaTypes.DOUBLE_OBJ:
code.anew().setType(Double.class);
code.dup();
// no break
case JavaTypes.DOUBLE:
code.aload().setLocal(oid);
code.checkcast().setType(DoubleId.class);
code.invokevirtual().setMethod(DoubleId.class, "getId",
double.class, null);
if (pkcode == JavaTypes.DOUBLE_OBJ)
code.invokespecial().setMethod(Double.class, "<init>",
void.class, new Class[]{double.class});
break;
case JavaTypes.FLOAT_OBJ:
code.anew().setType(Float.class);
code.dup();
// no break
case JavaTypes.FLOAT:
code.aload().setLocal(oid);
code.checkcast().setType(FloatId.class);
code.invokevirtual().setMethod(FloatId.class, "getId",
float.class, null);
if (pkcode == JavaTypes.FLOAT_OBJ)
code.invokespecial().setMethod(Float.class, "<init>",
void.class, new Class[]{float.class});
break;
case JavaTypes.INT_OBJ:
code.anew().setType(Integer.class);
code.dup();
// no break
case JavaTypes.INT:
code.aload().setLocal(oid);
code.checkcast().setType(IntId.class);
code.invokevirtual().setMethod(IntId.class, "getId",
int.class, null);
if (pkcode == JavaTypes.INT_OBJ)
code.invokespecial().setMethod(Integer.class, "<init>",
void.class, new Class[] {int.class});
break;
case JavaTypes.LONG_OBJ:
code.anew().setType(Long.class);
code.dup();
// no break
case JavaTypes.LONG:
code.aload().setLocal(oid);
code.checkcast().setType(LongId.class);
code.invokevirtual().setMethod(LongId.class, "getId",
long.class, null);
if (pkcode == JavaTypes.LONG_OBJ)
code.invokespecial().setMethod(Long.class, "<init>",
void.class, new Class[] {long.class});
break;
case JavaTypes.SHORT_OBJ:
code.anew().setType(Short.class);
code.dup();
// no break
case JavaTypes.SHORT:
code.aload().setLocal(oid);
code.checkcast().setType(ShortId.class);
code.invokevirtual().setMethod(ShortId.class, "getId",
short.class, null);
if (pkcode == JavaTypes.SHORT_OBJ)
code.invokespecial().setMethod(Short.class, "<init>",
void.class, new Class[]{short.class});
break;
case JavaTypes.DATE:
code.aload().setLocal(oid);
code.checkcast().setType(DateId.class);
code.invokevirtual().setMethod(DateId.class, "getId",
Date.class, null);
if (pktype != Date.class) {
// java.sql.Date.class
code.checkcast().setType(pktype);
}
break;
case JavaTypes.STRING:
code.aload().setLocal(oid);
code.checkcast().setType(StringId.class);
code.invokevirtual().setMethod(StringId.class, "getId",
String.class, null);
break;
case JavaTypes.BIGDECIMAL:
code.aload().setLocal(oid);
code.checkcast().setType(BigDecimalId.class);
code.invokevirtual().setMethod(BigDecimalId.class, "getId",
BigDecimal.class, null);
break;
case JavaTypes.BIGINTEGER:
code.aload().setLocal(oid);
code.checkcast().setType(BigIntegerId.class);
code.invokevirtual().setMethod(BigIntegerId.class, "getId",
BigInteger.class, null);
break;
default:
code.aload().setLocal(oid);
code.checkcast().setType(ObjectId.class);
code.invokevirtual().setMethod(ObjectId.class, "getId",
Object.class, null);
}
} else if (pkmeta.getObjectIdType() != null) {
code.aload().setLocal(oid);
if (pkcode == JavaTypes.OBJECT) {
code.checkcast().setType(ObjectId.class);
code.invokevirtual().setMethod(ObjectId.class, "getId",
Object.class, null);
}
code.checkcast().setType(pktype);
} else
code.aload().setLocal(oid);
JumpInstruction go2 = code.go2();
// if (val == null)
// val = <default>;
Instruction def;
switch (pkcode) {
case JavaTypes.BOOLEAN:
def = code.constant().setValue(false);
break;
case JavaTypes.BYTE:
def = code.constant().setValue((byte) 0);
break;
case JavaTypes.CHAR:
def = code.constant().setValue((char) 0);
break;
case JavaTypes.DOUBLE:
def = code.constant().setValue(0D);
break;
case JavaTypes.FLOAT:
def = code.constant().setValue(0F);
break;
case JavaTypes.INT:
def = code.constant().setValue(0);
break;
case JavaTypes.LONG:
def = code.constant().setValue(0L);
break;
case JavaTypes.SHORT:
def = code.constant().setValue((short) 0);
break;
default:
def = code.constant().setNull();
}
ifnull1.setTarget(def);
ifnull2.setTarget(def);
go2.setTarget(code.nop());
}