Browse Source

Fix bytecode generation for SpEL OpPlus

Without this change the plus operator would fail to
include a CHECKCAST in generated bytecode when it
was compiled in cases where one of the operands
has a runtime type of String but a statically
declared type that was not String (i.e. Object).

Issue: SPR-12426
pull/694/head
Andy Clement 10 years ago
parent
commit
94ee763bc8
  1. 3
      spring-expression/src/main/java/org/springframework/expression/spel/ast/OpPlus.java
  2. 29
      spring-expression/src/test/java/org/springframework/expression/spel/SpelCompilationCoverageTests.java

3
spring-expression/src/main/java/org/springframework/expression/spel/ast/OpPlus.java

@ -206,6 +206,9 @@ public class OpPlus extends Operator { @@ -206,6 +206,9 @@ public class OpPlus extends Operator {
else {
cf.enterCompilationScope();
operand.generateCode(mv,cf);
if (cf.lastDescriptor() != "Ljava/lang/String") {
mv.visitTypeInsn(CHECKCAST, "java/lang/String");
}
cf.exitCompilationScope();
mv.visitMethodInsn(INVOKEVIRTUAL, "java/lang/StringBuilder", "append", "(Ljava/lang/String;)Ljava/lang/StringBuilder;", false);
}

29
spring-expression/src/test/java/org/springframework/expression/spel/SpelCompilationCoverageTests.java

@ -1683,12 +1683,41 @@ public class SpelCompilationCoverageTests extends AbstractExpressionTests { @@ -1683,12 +1683,41 @@ public class SpelCompilationCoverageTests extends AbstractExpressionTests {
expression = parse("'hello' + 3 + ' spring'");
assertEquals("hello3 spring",expression.getValue(new Greeter()));
assertCantCompile(expression);
expression = parse("object + 'a'");
assertEquals("objecta",expression.getValue(new Greeter()));
assertCanCompile(expression);
assertEquals("objecta",expression.getValue(new Greeter()));
expression = parse("'a'+object");
assertEquals("aobject",expression.getValue(new Greeter()));
assertCanCompile(expression);
assertEquals("aobject",expression.getValue(new Greeter()));
expression = parse("'a'+object+'a'");
assertEquals("aobjecta",expression.getValue(new Greeter()));
assertCanCompile(expression);
assertEquals("aobjecta",expression.getValue(new Greeter()));
expression = parse("object+'a'+object");
assertEquals("objectaobject",expression.getValue(new Greeter()));
assertCanCompile(expression);
assertEquals("objectaobject",expression.getValue(new Greeter()));
expression = parse("object+object");
assertEquals("objectobject",expression.getValue(new Greeter()));
assertCanCompile(expression);
assertEquals("objectobject",expression.getValue(new Greeter()));
}
public static class Greeter {
public String getWorld() {
return "world";
}
public Object getObject() {
return "object";
}
}
@Test

Loading…
Cancel
Save