http://git-wip-us.apache.org/repos/asf/freemarker/blob/81b48221/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/string-builtins-regexps.f3ac
----------------------------------------------------------------------
diff --git 
a/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/string-builtins-regexps.f3ac
 
b/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/string-builtins-regexps.f3ac
new file mode 100644
index 0000000..f3a4a9f
--- /dev/null
+++ 
b/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/string-builtins-regexps.f3ac
@@ -0,0 +1,136 @@
+<#--
+  Licensed to the Apache Software Foundation (ASF) under one
+  or more contributor license agreements.  See the NOTICE file
+  distributed with this work for additional information
+  regarding copyright ownership.  The ASF licenses this file
+  to you under the Apache License, Version 2.0 (the
+  "License"); you may not use this file except in compliance
+  with the License.  You may obtain a copy of the License at
+
+    http://www.apache.org/licenses/LICENSE-2.0
+
+  Unless required by applicable law or agreed to in writing,
+  software distributed under the License is distributed on an
+  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+  KIND, either express or implied.  See the License for the
+  specific language governing permissions and limitations
+  under the License.
+-->
+${"test"?matches('test')?string} == true
+${"test"?matches('test', '')?string} == true
+
+${"TEST"?matches('test')?string} == false
+${"TEST"?matches('test', 'i')?string} == true
+
+${"test\nfoo"?matches('.*^foo')?string} == false
+${"test\nfoo"?matches(r'.*\n^foo', 'm')?string} == true
+
+${"test\nfoo"?matches('test.foo')?string} == false
+${"test\nfoo"?matches('test.foo', 's')?string} == true
+
+${"test\nFoo"?matches('.*foo', 's')?string} == false
+${"test\nFoo"?matches('.*foo', 'i')?string} == false
+${"test\nFoo"?matches('.*foo', 'im')?string} == false
+${"test\nFoo"?matches('.*foo', 'si')?string} == true
+${"test\nFoo"?matches('.*foo', 'is')?string} == true
+${"test\nFoo"?matches('.*foo', 'mis')?string} == true
+
+${"test\nFoo"?matches('.*\n^foo', 'm')?string} == false
+${"test\nFoo"?matches('.*\n^foo', 'i')?string} == false
+${"test\nFoo"?matches('.*\n^foo', 'im')?string} == true
+${"test\nFoo"?matches('.*\n^foo', 'mi')?string} == true
+${"test\nFoo"?matches('.*^foo', 'ism')?string} == true
+${"test\nFoo"?matches('.*^foo', 'smi')?string} == true
+<#setting booleanFormat="True,False">
+<@assert false?matches('[eslaF]+') />
+<@assert 'False'?matches('[eslaF]+') />
+
+<#assign s = "Code without test coverage\nis considered to be BROKEN">
+
+Lower 'c'-words:
+<#list s?matches('c[a-z]*') as m>
+- ${m}
+</#list>
+
+Any 'c'-words:
+<#list s?matches('c[a-z]*', 'i') as m>
+- ${m}
+</#list>  
+
+Lower line-last words:
+<#list s?matches('[a-z]+$', 'm') as m>
+- ${m}
+</#list>  
+
+Any line-last words:
+<#list s?matches('[a-z]+$', 'mi') as m>
+- ${m}
+</#list>
+
+Any last words:
+<#list s?matches('[a-z]+$', 'i') as m>
+- ${m}
+</#list>
+
+c-word with follower:
+<#list s?matches('(c[a-z]*+).([a-z]++)', 'is') as m>
+- "${m?jString}"
+  Groups: <#list m?groups as g>"${g?jString}"<#if g_has_next>, </#if></#list>
+</#list>
+
+c-word with follower in the same line:
+<#list s?matches('c[a-z]*+.[a-z]++', 'i') as m>
+- ${m}
+</#list>
+
+Lower c-word with follower in the same line:
+<#list s?matches('c[a-z]*+.[a-z]++', '') as m>
+- ${m}
+</#list>
+
+<#attempt>
+  Ignored but logged in 2.3: ${s?matches('broken', 'I')?string} == False
+<#recover>
+  Fails in 2.4
+</#attempt>
+<#attempt>
+  Ignored but logged in 2.3: ${s?matches('broken', 'f')?string} == False
+<#recover>
+  Fails in 2.4
+</#attempt>
+
+${"foobar"?replace("foo", "FOO")} == FOObar
+${"Foobar"?replace("foo", "FOO", "")} == Foobar
+${"Foobar"?replace("foo", "FOO", "i")} == FOObar
+${"FoobarfOO"?replace("foo", "FOO", "i")} == FOObarFOO
+${"FoobarfOO"?replace("foo", "FOO", "if")} == FOObarfOO
+${"FoobarfOO"?replace("foo", "FOO", "fi")} == FOObarfOO
+${"Foobar"?replace("foo", "FOO", "r")} == Foobar
+${"Foobar"?replace("foo", "FOO", "ri")} == FOObar
+${"FoobarfOO"?replace("foo", "FOO", "ri")} == FOObarFOO
+${"FoobarfOO"?replace("foo", "FOO", "rif")} == FOObarfOO
+${"FoobarfOO"?replace("foo", "FOO", "fri")} == FOObarfOO
+${"foobar"?replace("fo+", "FOO")} == foobar
+${"foobar"?replace("fo+", "FOO", "")} == foobar
+${"foobar"?replace("fo+", "FOO", "r")} == FOObar
+${"foobarfOo"?replace("fo+", "FOO", "ri")} == FOObarFOO
+${"foobarfOo"?replace("fo+", "FOO", "rif")} == FOObarfOo
+${false?replace('a', 'A')} == FAlse
+${false?replace('[abc]', 'A', 'r')} == FAlse
+
+<#attempt>
+  Ignored but logged in 2.3: ${"foobar"?replace("foo", "FOO", "c")}
+<#recover>
+  Fails in 2.4
+</#attempt>
+
+<#macro dumpList xs{positional}>[<#list xs as x>${x}<#if x_has_next>, 
</#if></#list>]</#macro>
+<@dumpList "fooXbarxbaaz"?split("X") /> == [foo, barxbaaz]
+<@dumpList "fooXbarxbaaz"?split("X", "") /> == [foo, barxbaaz]
+<@dumpList "fooXbarxbaaz"?split("X", "i") /> == [foo, bar, baaz]
+<@dumpList "fooXbarxbaaz"?split("X", "r") /> == [foo, barxbaaz]
+<@dumpList "fooXbarxbaaz"?split("X", "ri") /> == [foo, bar, baaz]
+<@dumpList "fooXXbarxxbaaz"?split("X+", "i") /> == [fooXXbarxxbaaz]
+<@dumpList "fooXXbarxxbaaz"?split("X+", "ri") /> == [foo, bar, baaz]
+<@dumpList false?split("[ae]", "r") /> == [F, ls]
+<@dumpList false?split("e") /> == [Fals, ]
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/freemarker/blob/81b48221/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/string-builtins-regexps.ftl
----------------------------------------------------------------------
diff --git 
a/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/string-builtins-regexps.ftl
 
b/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/string-builtins-regexps.ftl
deleted file mode 100644
index f3a4a9f..0000000
--- 
a/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/string-builtins-regexps.ftl
+++ /dev/null
@@ -1,136 +0,0 @@
-<#--
-  Licensed to the Apache Software Foundation (ASF) under one
-  or more contributor license agreements.  See the NOTICE file
-  distributed with this work for additional information
-  regarding copyright ownership.  The ASF licenses this file
-  to you under the Apache License, Version 2.0 (the
-  "License"); you may not use this file except in compliance
-  with the License.  You may obtain a copy of the License at
-
-    http://www.apache.org/licenses/LICENSE-2.0
-
-  Unless required by applicable law or agreed to in writing,
-  software distributed under the License is distributed on an
-  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
-  KIND, either express or implied.  See the License for the
-  specific language governing permissions and limitations
-  under the License.
--->
-${"test"?matches('test')?string} == true
-${"test"?matches('test', '')?string} == true
-
-${"TEST"?matches('test')?string} == false
-${"TEST"?matches('test', 'i')?string} == true
-
-${"test\nfoo"?matches('.*^foo')?string} == false
-${"test\nfoo"?matches(r'.*\n^foo', 'm')?string} == true
-
-${"test\nfoo"?matches('test.foo')?string} == false
-${"test\nfoo"?matches('test.foo', 's')?string} == true
-
-${"test\nFoo"?matches('.*foo', 's')?string} == false
-${"test\nFoo"?matches('.*foo', 'i')?string} == false
-${"test\nFoo"?matches('.*foo', 'im')?string} == false
-${"test\nFoo"?matches('.*foo', 'si')?string} == true
-${"test\nFoo"?matches('.*foo', 'is')?string} == true
-${"test\nFoo"?matches('.*foo', 'mis')?string} == true
-
-${"test\nFoo"?matches('.*\n^foo', 'm')?string} == false
-${"test\nFoo"?matches('.*\n^foo', 'i')?string} == false
-${"test\nFoo"?matches('.*\n^foo', 'im')?string} == true
-${"test\nFoo"?matches('.*\n^foo', 'mi')?string} == true
-${"test\nFoo"?matches('.*^foo', 'ism')?string} == true
-${"test\nFoo"?matches('.*^foo', 'smi')?string} == true
-<#setting booleanFormat="True,False">
-<@assert false?matches('[eslaF]+') />
-<@assert 'False'?matches('[eslaF]+') />
-
-<#assign s = "Code without test coverage\nis considered to be BROKEN">
-
-Lower 'c'-words:
-<#list s?matches('c[a-z]*') as m>
-- ${m}
-</#list>
-
-Any 'c'-words:
-<#list s?matches('c[a-z]*', 'i') as m>
-- ${m}
-</#list>  
-
-Lower line-last words:
-<#list s?matches('[a-z]+$', 'm') as m>
-- ${m}
-</#list>  
-
-Any line-last words:
-<#list s?matches('[a-z]+$', 'mi') as m>
-- ${m}
-</#list>
-
-Any last words:
-<#list s?matches('[a-z]+$', 'i') as m>
-- ${m}
-</#list>
-
-c-word with follower:
-<#list s?matches('(c[a-z]*+).([a-z]++)', 'is') as m>
-- "${m?jString}"
-  Groups: <#list m?groups as g>"${g?jString}"<#if g_has_next>, </#if></#list>
-</#list>
-
-c-word with follower in the same line:
-<#list s?matches('c[a-z]*+.[a-z]++', 'i') as m>
-- ${m}
-</#list>
-
-Lower c-word with follower in the same line:
-<#list s?matches('c[a-z]*+.[a-z]++', '') as m>
-- ${m}
-</#list>
-
-<#attempt>
-  Ignored but logged in 2.3: ${s?matches('broken', 'I')?string} == False
-<#recover>
-  Fails in 2.4
-</#attempt>
-<#attempt>
-  Ignored but logged in 2.3: ${s?matches('broken', 'f')?string} == False
-<#recover>
-  Fails in 2.4
-</#attempt>
-
-${"foobar"?replace("foo", "FOO")} == FOObar
-${"Foobar"?replace("foo", "FOO", "")} == Foobar
-${"Foobar"?replace("foo", "FOO", "i")} == FOObar
-${"FoobarfOO"?replace("foo", "FOO", "i")} == FOObarFOO
-${"FoobarfOO"?replace("foo", "FOO", "if")} == FOObarfOO
-${"FoobarfOO"?replace("foo", "FOO", "fi")} == FOObarfOO
-${"Foobar"?replace("foo", "FOO", "r")} == Foobar
-${"Foobar"?replace("foo", "FOO", "ri")} == FOObar
-${"FoobarfOO"?replace("foo", "FOO", "ri")} == FOObarFOO
-${"FoobarfOO"?replace("foo", "FOO", "rif")} == FOObarfOO
-${"FoobarfOO"?replace("foo", "FOO", "fri")} == FOObarfOO
-${"foobar"?replace("fo+", "FOO")} == foobar
-${"foobar"?replace("fo+", "FOO", "")} == foobar
-${"foobar"?replace("fo+", "FOO", "r")} == FOObar
-${"foobarfOo"?replace("fo+", "FOO", "ri")} == FOObarFOO
-${"foobarfOo"?replace("fo+", "FOO", "rif")} == FOObarfOo
-${false?replace('a', 'A')} == FAlse
-${false?replace('[abc]', 'A', 'r')} == FAlse
-
-<#attempt>
-  Ignored but logged in 2.3: ${"foobar"?replace("foo", "FOO", "c")}
-<#recover>
-  Fails in 2.4
-</#attempt>
-
-<#macro dumpList xs{positional}>[<#list xs as x>${x}<#if x_has_next>, 
</#if></#list>]</#macro>
-<@dumpList "fooXbarxbaaz"?split("X") /> == [foo, barxbaaz]
-<@dumpList "fooXbarxbaaz"?split("X", "") /> == [foo, barxbaaz]
-<@dumpList "fooXbarxbaaz"?split("X", "i") /> == [foo, bar, baaz]
-<@dumpList "fooXbarxbaaz"?split("X", "r") /> == [foo, barxbaaz]
-<@dumpList "fooXbarxbaaz"?split("X", "ri") /> == [foo, bar, baaz]
-<@dumpList "fooXXbarxxbaaz"?split("X+", "i") /> == [fooXXbarxxbaaz]
-<@dumpList "fooXXbarxxbaaz"?split("X+", "ri") /> == [foo, bar, baaz]
-<@dumpList false?split("[ae]", "r") /> == [F, ls]
-<@dumpList false?split("e") /> == [Fals, ]
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/freemarker/blob/81b48221/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/string-builtins1.f3ac
----------------------------------------------------------------------
diff --git 
a/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/string-builtins1.f3ac
 
b/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/string-builtins1.f3ac
new file mode 100644
index 0000000..be1b19e
--- /dev/null
+++ 
b/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/string-builtins1.f3ac
@@ -0,0 +1,129 @@
+<#--
+  Licensed to the Apache Software Foundation (ASF) under one
+  or more contributor license agreements.  See the NOTICE file
+  distributed with this work for additional information
+  regarding copyright ownership.  The ASF licenses this file
+  to you under the Apache License, Version 2.0 (the
+  "License"); you may not use this file except in compliance
+  with the License.  You may obtain a copy of the License at
+
+    http://www.apache.org/licenses/LICENSE-2.0
+
+  Unless required by applicable law or agreed to in writing,
+  software distributed under the License is distributed on an
+  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+  KIND, either express or implied.  See the License for the
+  specific language governing permissions and limitations
+  under the License.
+-->
+FreeMarker: Encoding string built-in tests
+
+<#assign x = r'  dieBugsDie! * vazzZE 123456 --cdc-- --<<--@ x 
${"kigyo"?upperCase}  '>
+  
+capFirst:   ${x?capFirst};
+uncapFirst: ${x?uncapFirst};
+uncapFirst: ${"Blah"?uncapFirst}
+capitalize: ${x?capitalize};
+html:       ${x?html};
+length:     ${x?length};
+lowerCase:  ${x?lowerCase};
+rtf:        ${x?rtf};
+trim:       ${x?trim};
+trim2:      ${"foo bar"?trim}
+trim3:      ${" foo bar"?trim}
+trim4:      ${"foo bar "?trim}
+upperCase:  ${x?upperCase};
+xml:        ${x?xml};
+xhtml:      ${"\"Blah's is > 1 & < 2\""?xhtml}
+<@assertEquals actual="'"?html expected="&#39;" />
+<@assertEquals actual="'"?xhtml expected="&#39;" />
+<@assertEquals actual="'"?xml expected="&apos;" />
+<#-- ?substring: -->
+<@assertEquals actual="ab"?substring(0) expected="ab" />
+<@assertEquals actual="ab"?substring(1) expected="b" />
+<@assertEquals actual="ab"?substring(2) expected="" />
+<@assertFails message="at least 0">${"ab"?substring(-1)}</@><#t>
+<@assertFails message="greater than the length of the 
string">${"ab"?substring(3)}</@><#t>
+<@assertEquals actual="ab"?substring(0, 0) expected="" />
+<@assertEquals actual="ab"?substring(0, 1) expected="a" />
+<@assertEquals actual="ab"?substring(0, 2) expected="ab" />
+<@assertFails message="at least 0">${"ab"?substring(0, -1)}</@><#t>
+<@assertFails message="greater than the length of the 
string">${"ab"?substring(0, 3)}</@><#t>
+<@assertEquals actual="ab"?substring(1, 1) expected="" />
+<@assertEquals actual="ab"?substring(1, 2) expected="b" />
+<@assertFails message="at least 0">${"ab"?substring(1, -1)}</@><#t>
+<@assertFails message="greater than the length of the 
string">${"ab"?substring(1, 3)}</@><#t>
+<@assertFails message="shouldn't be greater than the end 
index">${"ab"?substring(1, 0)}</@><#t>
+
+word_list:
+<#global words = x?wordList>
+<#list words as w>- ${w}
+</#list>
+
+<#global canufeelitbabe = x?interpret>
+interpret: <@canufeelitbabe></@>
+<#setting locale="es_ES">number: ${"-123.45"?number + 1.1}
+${"1.5e3"?number?c}
+${"0005"?number?c}
+${"+0"?number?c}
+${"-0"?number?c}
+${"NaN"?number?isNan?c}
+${("INF"?number?isInfinite && "INF"?number > 0)?c}
+${("-INF"?number?isInfinite && "-INF"?number < 0)?c}
+${("Infinity"?number?isInfinite && "Infinity"?number > 0)?c}
+${("-Infinity"?number?isInfinite && "-Infinity"?number < 0)?c}
+
+${"org.apache.freemarker.core.templatesuite.models.NewTestModel"?new()}
+${"org.apache.freemarker.core.templatesuite.models.NewTestModel"?new(1)}
+${"org.apache.freemarker.core.templatesuite.models.NewTestModel"?new("xxx")}
+${"org.apache.freemarker.core.templatesuite.models.NewTestModel"?new("xxx", 
"yyy")}
+
+<#assign x = "In the beginning, God created the Heavens and The Earth.">
+
+${x?replace("the", "The Sacred, Holy", "i")} <#-- case insensitive replacement 
-->
+${x?replace("the", "the very", "f")} <#-- replace only the first one -->
+${x?replace("", "|")} <#-- replace empry string -->
+${x?replace("", "|", "f")} <#-- replace first empty string -->
+
+${x?replace("the H[a-z]+", "the sky", "r")} <#-- regexp replacement -->
+
+<#if x?matches(".*Heav..s.*")>matches<#else>Really?</#if>
+
+<#list x?matches("(the) ([a-z]+)", "i") as match>
+  ${match}
+  ${match?groups[1]} sacred ${match?groups[2]}
+</#list>  
+
+<#assign matches = x?matches("In the ([a-z]+), God created (.*)")>
+${matches?groups[0]}
+${matches?groups[1]}
+${matches?groups[2]}
+
+<#assign x="foo, bar;baz,     foobar">
+<#list x?split("[,;] ?", "r") as word>
+   ${word}
+</#list>
+
+
+<#assign a = "foo", b="bar", c="(a+b)?upperCase">
+${c?eval}
+
+[${"a"?jString}] = [a]
+[${"a\\'x'\nb"?jString}] = [a\\'x'\nb]
+[${"\x0001\x001A "?jString}] = [\u0001\u001a ]
+
+[${"a"?jsString}] = [a]
+[${"a\\'x'\nb"?jsString}] = [a\\\'x\'\nb]
+[${"\x0001\x001A "?jsString}] = [\x01\x1A ]
+[${"<![CDATA["?jsString}] = [\x3C![CDATA[]
+[${"]]>"?jsString}] = []]\>]
+
+[${"a"?jsonString}] = [a]
+[${"a\\'x'\nb"?jsonString}] = [a\\'x'\nb]
+[${"\x0001\x001A "?jsonString}] = [\u0001\u001A ]
+[${"\n\r\t\f\b\""?jsonString}] = [\n\r\t\f\b\"]
+[${"/"?jsonString}] = [\/]
+[${"a/b"?jsonString}] = [a/b]
+[${"</script>"?jsonString}] = [<\/script>]
+[${"<![CDATA["?jsonString}] = [\u003C![CDATA[]
+[${"]]>"?jsonString}] = []]\u003E]

http://git-wip-us.apache.org/repos/asf/freemarker/blob/81b48221/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/string-builtins1.ftl
----------------------------------------------------------------------
diff --git 
a/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/string-builtins1.ftl
 
b/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/string-builtins1.ftl
deleted file mode 100644
index be1b19e..0000000
--- 
a/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/string-builtins1.ftl
+++ /dev/null
@@ -1,129 +0,0 @@
-<#--
-  Licensed to the Apache Software Foundation (ASF) under one
-  or more contributor license agreements.  See the NOTICE file
-  distributed with this work for additional information
-  regarding copyright ownership.  The ASF licenses this file
-  to you under the Apache License, Version 2.0 (the
-  "License"); you may not use this file except in compliance
-  with the License.  You may obtain a copy of the License at
-
-    http://www.apache.org/licenses/LICENSE-2.0
-
-  Unless required by applicable law or agreed to in writing,
-  software distributed under the License is distributed on an
-  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
-  KIND, either express or implied.  See the License for the
-  specific language governing permissions and limitations
-  under the License.
--->
-FreeMarker: Encoding string built-in tests
-
-<#assign x = r'  dieBugsDie! * vazzZE 123456 --cdc-- --<<--@ x 
${"kigyo"?upperCase}  '>
-  
-capFirst:   ${x?capFirst};
-uncapFirst: ${x?uncapFirst};
-uncapFirst: ${"Blah"?uncapFirst}
-capitalize: ${x?capitalize};
-html:       ${x?html};
-length:     ${x?length};
-lowerCase:  ${x?lowerCase};
-rtf:        ${x?rtf};
-trim:       ${x?trim};
-trim2:      ${"foo bar"?trim}
-trim3:      ${" foo bar"?trim}
-trim4:      ${"foo bar "?trim}
-upperCase:  ${x?upperCase};
-xml:        ${x?xml};
-xhtml:      ${"\"Blah's is > 1 & < 2\""?xhtml}
-<@assertEquals actual="'"?html expected="&#39;" />
-<@assertEquals actual="'"?xhtml expected="&#39;" />
-<@assertEquals actual="'"?xml expected="&apos;" />
-<#-- ?substring: -->
-<@assertEquals actual="ab"?substring(0) expected="ab" />
-<@assertEquals actual="ab"?substring(1) expected="b" />
-<@assertEquals actual="ab"?substring(2) expected="" />
-<@assertFails message="at least 0">${"ab"?substring(-1)}</@><#t>
-<@assertFails message="greater than the length of the 
string">${"ab"?substring(3)}</@><#t>
-<@assertEquals actual="ab"?substring(0, 0) expected="" />
-<@assertEquals actual="ab"?substring(0, 1) expected="a" />
-<@assertEquals actual="ab"?substring(0, 2) expected="ab" />
-<@assertFails message="at least 0">${"ab"?substring(0, -1)}</@><#t>
-<@assertFails message="greater than the length of the 
string">${"ab"?substring(0, 3)}</@><#t>
-<@assertEquals actual="ab"?substring(1, 1) expected="" />
-<@assertEquals actual="ab"?substring(1, 2) expected="b" />
-<@assertFails message="at least 0">${"ab"?substring(1, -1)}</@><#t>
-<@assertFails message="greater than the length of the 
string">${"ab"?substring(1, 3)}</@><#t>
-<@assertFails message="shouldn't be greater than the end 
index">${"ab"?substring(1, 0)}</@><#t>
-
-word_list:
-<#global words = x?wordList>
-<#list words as w>- ${w}
-</#list>
-
-<#global canufeelitbabe = x?interpret>
-interpret: <@canufeelitbabe></@>
-<#setting locale="es_ES">number: ${"-123.45"?number + 1.1}
-${"1.5e3"?number?c}
-${"0005"?number?c}
-${"+0"?number?c}
-${"-0"?number?c}
-${"NaN"?number?isNan?c}
-${("INF"?number?isInfinite && "INF"?number > 0)?c}
-${("-INF"?number?isInfinite && "-INF"?number < 0)?c}
-${("Infinity"?number?isInfinite && "Infinity"?number > 0)?c}
-${("-Infinity"?number?isInfinite && "-Infinity"?number < 0)?c}
-
-${"org.apache.freemarker.core.templatesuite.models.NewTestModel"?new()}
-${"org.apache.freemarker.core.templatesuite.models.NewTestModel"?new(1)}
-${"org.apache.freemarker.core.templatesuite.models.NewTestModel"?new("xxx")}
-${"org.apache.freemarker.core.templatesuite.models.NewTestModel"?new("xxx", 
"yyy")}
-
-<#assign x = "In the beginning, God created the Heavens and The Earth.">
-
-${x?replace("the", "The Sacred, Holy", "i")} <#-- case insensitive replacement 
-->
-${x?replace("the", "the very", "f")} <#-- replace only the first one -->
-${x?replace("", "|")} <#-- replace empry string -->
-${x?replace("", "|", "f")} <#-- replace first empty string -->
-
-${x?replace("the H[a-z]+", "the sky", "r")} <#-- regexp replacement -->
-
-<#if x?matches(".*Heav..s.*")>matches<#else>Really?</#if>
-
-<#list x?matches("(the) ([a-z]+)", "i") as match>
-  ${match}
-  ${match?groups[1]} sacred ${match?groups[2]}
-</#list>  
-
-<#assign matches = x?matches("In the ([a-z]+), God created (.*)")>
-${matches?groups[0]}
-${matches?groups[1]}
-${matches?groups[2]}
-
-<#assign x="foo, bar;baz,     foobar">
-<#list x?split("[,;] ?", "r") as word>
-   ${word}
-</#list>
-
-
-<#assign a = "foo", b="bar", c="(a+b)?upperCase">
-${c?eval}
-
-[${"a"?jString}] = [a]
-[${"a\\'x'\nb"?jString}] = [a\\'x'\nb]
-[${"\x0001\x001A "?jString}] = [\u0001\u001a ]
-
-[${"a"?jsString}] = [a]
-[${"a\\'x'\nb"?jsString}] = [a\\\'x\'\nb]
-[${"\x0001\x001A "?jsString}] = [\x01\x1A ]
-[${"<![CDATA["?jsString}] = [\x3C![CDATA[]
-[${"]]>"?jsString}] = []]\>]
-
-[${"a"?jsonString}] = [a]
-[${"a\\'x'\nb"?jsonString}] = [a\\'x'\nb]
-[${"\x0001\x001A "?jsonString}] = [\u0001\u001A ]
-[${"\n\r\t\f\b\""?jsonString}] = [\n\r\t\f\b\"]
-[${"/"?jsonString}] = [\/]
-[${"a/b"?jsonString}] = [a/b]
-[${"</script>"?jsonString}] = [<\/script>]
-[${"<![CDATA["?jsonString}] = [\u003C![CDATA[]
-[${"]]>"?jsonString}] = []]\u003E]

http://git-wip-us.apache.org/repos/asf/freemarker/blob/81b48221/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/string-builtins2.f3ac
----------------------------------------------------------------------
diff --git 
a/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/string-builtins2.f3ac
 
b/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/string-builtins2.f3ac
new file mode 100644
index 0000000..b12d149
--- /dev/null
+++ 
b/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/string-builtins2.f3ac
@@ -0,0 +1,135 @@
+<#--
+  Licensed to the Apache Software Foundation (ASF) under one
+  or more contributor license agreements.  See the NOTICE file
+  distributed with this work for additional information
+  regarding copyright ownership.  The ASF licenses this file
+  to you under the Apache License, Version 2.0 (the
+  "License"); you may not use this file except in compliance
+  with the License.  You may obtain a copy of the License at
+
+    http://www.apache.org/licenses/LICENSE-2.0
+
+  Unless required by applicable law or agreed to in writing,
+  software distributed under the License is distributed on an
+  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+  KIND, either express or implied.  See the License for the
+  specific language governing permissions and limitations
+  under the License.
+-->
+--
+<#assign s = "abbcdbb">
+${s?indexOf("bb")} = 1
+${s?indexOf("bb", 2)} = 5
+${s?indexOf("")} = 0
+--
+${s?lastIndexOf("bb")} = 5
+${s?lastIndexOf("bb", 4)} = 1
+${s?lastIndexOf("")} = ${s?length}
+--
+${s?startsWith("abb")?string} = true
+${s?startsWith("bb")?string} = false
+${s?startsWith("")?string} = true
+--
+${s?endsWith("dbb")?string} = true
+${s?endsWith("cbb")?string} = false
+${s?endsWith("")?string} = true
+--
+${s?contains("abb")?string} = true
+${s?contains("bcd")?string} = true
+${s?contains("dbb")?string} = true
+${s?contains("bbx")?string} = false
+${s?contains("")?string} = true
+--
+[${s?chopLinebreak}] = [abbcdbb]
+[${"qwe\n"?chopLinebreak}] = [qwe]
+[${"qwe\r"?chopLinebreak}] = [qwe]
+[${"qwe\r\n"?chopLinebreak}] = [qwe]
+[${"qwe\r\n\r\n"?chopLinebreak}] = [qwe
+]
+[${"qwe\n\n"?chopLinebreak}] = [qwe
+]
+--
+[${s?replace("A", "-")}] = [abbcdbb]
+[${s?replace("c", "-")}] = [abb-dbb]
+[${s?replace("bb", "-=*")}] = [a-=*cd-=*]
+--
+<#assign ls = s?split("b")>
+<#list ls as i>[${i}]</#list> == [a][][cd][][]
+<#list "--die--maggots--!"?split("--") as i>[${i}]</#list> == 
[][die][maggots][!]
+<#list "Die maggots!"?split("--") as i>[${i}]</#list> == [Die maggots!]
+--
+[${""?leftPad(5)}]
+[${"a"?leftPad(5)}]
+[${"ab"?leftPad(5)}]
+[${"abc"?leftPad(5)}]
+[${"abcd"?leftPad(5)}]
+[${"abcde"?leftPad(5)}]
+[${"abcdef"?leftPad(5)}]
+[${"abcdefg"?leftPad(5)}]
+[${"abcdefgh"?leftPad(5)}]
+[${""?leftPad(5, "-")}]
+[${"a"?leftPad(5, "-")}]
+[${"ab"?leftPad(5, "-")}]
+[${"abc"?leftPad(5, "-")}]
+[${"abcd"?leftPad(5, "-")}]
+[${"abcde"?leftPad(5, "-")}]
+[${"abcdef"?leftPad(5, "-")}]
+[${"abcdefg"?leftPad(5, "-")}]
+[${"abcdefgh"?leftPad(5, "-")}]
+[${""?leftPad(8, ".oO")}]
+[${"a"?leftPad(8, ".oO")}]
+[${"ab"?leftPad(8, ".oO")}]
+[${"abc"?leftPad(8, ".oO")}]
+[${"abcd"?leftPad(8, ".oO")}]
+[${"abcde"?leftPad(8, ".oO")}]
+[${"abcdef"?leftPad(8, ".oO")}]
+[${"abcdefg"?leftPad(8, ".oO")}]
+[${"abcdefgh"?leftPad(8, ".oO")}]
+[${"abcdefghi"?leftPad(8, ".oO")}]
+[${"abcdefghij"?leftPad(8, ".oO")}]
+[${""?leftPad(0, r"/\_")}]
+[${""?leftPad(1, r"/\_")}]
+[${""?leftPad(2, r"/\_")}]
+[${""?leftPad(3, r"/\_")}]
+[${""?leftPad(4, r"/\_")}]
+[${""?leftPad(5, r"/\_")}]
+[${""?leftPad(6, r"/\_")}]
+[${""?leftPad(7, r"/\_")}]
+--
+[${""?rightPad(5)}]
+[${"a"?rightPad(5)}]
+[${"ab"?rightPad(5)}]
+[${"abc"?rightPad(5)}]
+[${"abcd"?rightPad(5)}]
+[${"abcde"?rightPad(5)}]
+[${"abcdef"?rightPad(5)}]
+[${"abcdefg"?rightPad(5)}]
+[${"abcdefgh"?rightPad(5)}]
+[${""?rightPad(5, "-")}]
+[${"a"?rightPad(5, "-")}]
+[${"ab"?rightPad(5, "-")}]
+[${"abc"?rightPad(5, "-")}]
+[${"abcd"?rightPad(5, "-")}]
+[${"abcde"?rightPad(5, "-")}]
+[${"abcdef"?rightPad(5, "-")}]
+[${"abcdefg"?rightPad(5, "-")}]
+[${"abcdefgh"?rightPad(5, "-")}]
+[${""?rightPad(8, ".oO")}]
+[${"a"?rightPad(8, ".oO")}]
+[${"ab"?rightPad(8, ".oO")}]
+[${"abc"?rightPad(8, ".oO")}]
+[${"abcd"?rightPad(8, ".oO")}]
+[${"abcde"?rightPad(8, ".oO")}]
+[${"abcdef"?rightPad(8, ".oO")}]
+[${"abcdefg"?rightPad(8, ".oO")}]
+[${"abcdefgh"?rightPad(8, ".oO")}]
+[${"abcdefghi"?rightPad(8, ".oO")}]
+[${"abcdefghij"?rightPad(8, ".oO")}]
+[${""?rightPad(0, r"/\_")}]
+[${""?rightPad(1, r"/\_")}]
+[${""?rightPad(2, r"/\_")}]
+[${""?rightPad(3, r"/\_")}]
+[${""?rightPad(4, r"/\_")}]
+[${""?rightPad(5, r"/\_")}]
+[${""?rightPad(6, r"/\_")}]
+[${""?rightPad(7, r"/\_")}]
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/freemarker/blob/81b48221/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/string-builtins2.ftl
----------------------------------------------------------------------
diff --git 
a/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/string-builtins2.ftl
 
b/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/string-builtins2.ftl
deleted file mode 100644
index b12d149..0000000
--- 
a/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/string-builtins2.ftl
+++ /dev/null
@@ -1,135 +0,0 @@
-<#--
-  Licensed to the Apache Software Foundation (ASF) under one
-  or more contributor license agreements.  See the NOTICE file
-  distributed with this work for additional information
-  regarding copyright ownership.  The ASF licenses this file
-  to you under the Apache License, Version 2.0 (the
-  "License"); you may not use this file except in compliance
-  with the License.  You may obtain a copy of the License at
-
-    http://www.apache.org/licenses/LICENSE-2.0
-
-  Unless required by applicable law or agreed to in writing,
-  software distributed under the License is distributed on an
-  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
-  KIND, either express or implied.  See the License for the
-  specific language governing permissions and limitations
-  under the License.
--->
---
-<#assign s = "abbcdbb">
-${s?indexOf("bb")} = 1
-${s?indexOf("bb", 2)} = 5
-${s?indexOf("")} = 0
---
-${s?lastIndexOf("bb")} = 5
-${s?lastIndexOf("bb", 4)} = 1
-${s?lastIndexOf("")} = ${s?length}
---
-${s?startsWith("abb")?string} = true
-${s?startsWith("bb")?string} = false
-${s?startsWith("")?string} = true
---
-${s?endsWith("dbb")?string} = true
-${s?endsWith("cbb")?string} = false
-${s?endsWith("")?string} = true
---
-${s?contains("abb")?string} = true
-${s?contains("bcd")?string} = true
-${s?contains("dbb")?string} = true
-${s?contains("bbx")?string} = false
-${s?contains("")?string} = true
---
-[${s?chopLinebreak}] = [abbcdbb]
-[${"qwe\n"?chopLinebreak}] = [qwe]
-[${"qwe\r"?chopLinebreak}] = [qwe]
-[${"qwe\r\n"?chopLinebreak}] = [qwe]
-[${"qwe\r\n\r\n"?chopLinebreak}] = [qwe
-]
-[${"qwe\n\n"?chopLinebreak}] = [qwe
-]
---
-[${s?replace("A", "-")}] = [abbcdbb]
-[${s?replace("c", "-")}] = [abb-dbb]
-[${s?replace("bb", "-=*")}] = [a-=*cd-=*]
---
-<#assign ls = s?split("b")>
-<#list ls as i>[${i}]</#list> == [a][][cd][][]
-<#list "--die--maggots--!"?split("--") as i>[${i}]</#list> == 
[][die][maggots][!]
-<#list "Die maggots!"?split("--") as i>[${i}]</#list> == [Die maggots!]
---
-[${""?leftPad(5)}]
-[${"a"?leftPad(5)}]
-[${"ab"?leftPad(5)}]
-[${"abc"?leftPad(5)}]
-[${"abcd"?leftPad(5)}]
-[${"abcde"?leftPad(5)}]
-[${"abcdef"?leftPad(5)}]
-[${"abcdefg"?leftPad(5)}]
-[${"abcdefgh"?leftPad(5)}]
-[${""?leftPad(5, "-")}]
-[${"a"?leftPad(5, "-")}]
-[${"ab"?leftPad(5, "-")}]
-[${"abc"?leftPad(5, "-")}]
-[${"abcd"?leftPad(5, "-")}]
-[${"abcde"?leftPad(5, "-")}]
-[${"abcdef"?leftPad(5, "-")}]
-[${"abcdefg"?leftPad(5, "-")}]
-[${"abcdefgh"?leftPad(5, "-")}]
-[${""?leftPad(8, ".oO")}]
-[${"a"?leftPad(8, ".oO")}]
-[${"ab"?leftPad(8, ".oO")}]
-[${"abc"?leftPad(8, ".oO")}]
-[${"abcd"?leftPad(8, ".oO")}]
-[${"abcde"?leftPad(8, ".oO")}]
-[${"abcdef"?leftPad(8, ".oO")}]
-[${"abcdefg"?leftPad(8, ".oO")}]
-[${"abcdefgh"?leftPad(8, ".oO")}]
-[${"abcdefghi"?leftPad(8, ".oO")}]
-[${"abcdefghij"?leftPad(8, ".oO")}]
-[${""?leftPad(0, r"/\_")}]
-[${""?leftPad(1, r"/\_")}]
-[${""?leftPad(2, r"/\_")}]
-[${""?leftPad(3, r"/\_")}]
-[${""?leftPad(4, r"/\_")}]
-[${""?leftPad(5, r"/\_")}]
-[${""?leftPad(6, r"/\_")}]
-[${""?leftPad(7, r"/\_")}]
---
-[${""?rightPad(5)}]
-[${"a"?rightPad(5)}]
-[${"ab"?rightPad(5)}]
-[${"abc"?rightPad(5)}]
-[${"abcd"?rightPad(5)}]
-[${"abcde"?rightPad(5)}]
-[${"abcdef"?rightPad(5)}]
-[${"abcdefg"?rightPad(5)}]
-[${"abcdefgh"?rightPad(5)}]
-[${""?rightPad(5, "-")}]
-[${"a"?rightPad(5, "-")}]
-[${"ab"?rightPad(5, "-")}]
-[${"abc"?rightPad(5, "-")}]
-[${"abcd"?rightPad(5, "-")}]
-[${"abcde"?rightPad(5, "-")}]
-[${"abcdef"?rightPad(5, "-")}]
-[${"abcdefg"?rightPad(5, "-")}]
-[${"abcdefgh"?rightPad(5, "-")}]
-[${""?rightPad(8, ".oO")}]
-[${"a"?rightPad(8, ".oO")}]
-[${"ab"?rightPad(8, ".oO")}]
-[${"abc"?rightPad(8, ".oO")}]
-[${"abcd"?rightPad(8, ".oO")}]
-[${"abcde"?rightPad(8, ".oO")}]
-[${"abcdef"?rightPad(8, ".oO")}]
-[${"abcdefg"?rightPad(8, ".oO")}]
-[${"abcdefgh"?rightPad(8, ".oO")}]
-[${"abcdefghi"?rightPad(8, ".oO")}]
-[${"abcdefghij"?rightPad(8, ".oO")}]
-[${""?rightPad(0, r"/\_")}]
-[${""?rightPad(1, r"/\_")}]
-[${""?rightPad(2, r"/\_")}]
-[${""?rightPad(3, r"/\_")}]
-[${""?rightPad(4, r"/\_")}]
-[${""?rightPad(5, r"/\_")}]
-[${""?rightPad(6, r"/\_")}]
-[${""?rightPad(7, r"/\_")}]
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/freemarker/blob/81b48221/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/string-builtins3.f3ac
----------------------------------------------------------------------
diff --git 
a/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/string-builtins3.f3ac
 
b/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/string-builtins3.f3ac
new file mode 100644
index 0000000..0a387ce
--- /dev/null
+++ 
b/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/string-builtins3.f3ac
@@ -0,0 +1,225 @@
+<#--
+  Licensed to the Apache Software Foundation (ASF) under one
+  or more contributor license agreements.  See the NOTICE file
+  distributed with this work for additional information
+  regarding copyright ownership.  The ASF licenses this file
+  to you under the Apache License, Version 2.0 (the
+  "License"); you may not use this file except in compliance
+  with the License.  You may obtain a copy of the License at
+
+    http://www.apache.org/licenses/LICENSE-2.0
+
+  Unless required by applicable law or agreed to in writing,
+  software distributed under the License is distributed on an
+  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+  KIND, either express or implied.  See the License for the
+  specific language governing permissions and limitations
+  under the License.
+-->
+<@assertEquals expected='foo' actual='foo'?keepBefore('x') />
+<@assertEquals expected='f' actual='foo'?keepBefore('o') />
+<@assertEquals expected='' actual='foo'?keepBefore('f') />
+<@assertEquals expected='fo' actual='foobar'?keepBefore('ob') />
+<@assertEquals expected='foob' actual='foobar'?keepBefore('ar') />
+<@assertEquals expected='' actual='foobar'?keepBefore('foobar') />
+<@assertEquals expected='' actual='foobar'?keepBefore('') />
+<@assertEquals expected='' actual='foobar'?keepBefore('', 'r') />
+<@assertEquals expected='FOO' actual='FOO'?keepBefore('o') />
+<@assertEquals expected='F' actual='FOO'?keepBefore('o', 'i') />
+<@assertEquals expected='fo' actual='fo.o'?keepBefore('.') />
+<@assertEquals expected='' actual='fo.o'?keepBefore('.', 'r') />
+<@assertEquals expected='FOOb' actual='FOObaar'?keepBefore(r'([a-z])\1', 'r') 
/>
+<@assertEquals expected='F' actual='FOObaar'?keepBefore(r'([a-z])\1', 'ri') />
+<@assertEquals expected='foo' actual="foo : bar"?keepBefore(r"\s*:\s*", "r") />
+<@assertEquals expected='foo' actual="foo:bar"?keepBefore(r"\s*:\s*", "r") />
+<@assertFails message='"m" flag'>
+    ${'x'?keepBefore('x', 'm')}
+</@assertFails>
+<@assertFails message='can only have'>
+    ${'x'?keepBefore('x', 'i', 'x')}
+</@assertFails>
+<@assertFails message='argument'>
+    ${'x'?keepBefore()}
+</@assertFails>
+
+<@assertEquals expected='' actual=''?keepBeforeLast('f') />
+<@assertEquals expected='ff' actual='fff'?keepBeforeLast('f') />
+<@assertEquals expected='' actual='foo'?keepBeforeLast('f') />
+<@assertEquals expected='' actual='f'?keepBeforeLast('f') />
+<@assertEquals expected='a.b' actual='a.b.txt'?keepBeforeLast('.') />
+<@assertEquals expected='ab' actual='ab'?keepBeforeLast('.') />
+<@assertEquals expected='a' actual='ab'?keepBeforeLast('.', 'r') />
+<@assertEquals expected='ab' actual='ab'?keepBeforeLast(r'\.', 'r') />
+<@assertEquals expected='af' actual='afFf'?keepBeforeLast('F') />
+<@assertEquals expected='afF' actual='afFf'?keepBeforeLast('F', 'i') />
+<@assertEquals expected='1a2' actual='1a2b3'?keepBeforeLast('[ab]', 'r') />
+<@assertEquals expected='aa' actual='aaabb'?keepBeforeLast('[ab]{3}', 'r') />
+<@assertEquals expected='aaabbx' actual='aaabbxbabe'?keepBeforeLast('[ab]{3}', 
'r') />
+<@assertEquals expected='xxxaa' actual='xxxaaayyy'?keepBeforeLast('a+', 'r') />
+<@assertEquals expected='foobar' actual='foobar'?keepBeforeLast('') />
+<@assertEquals expected='foobar' actual='foobar'?keepBeforeLast('', 'r') />
+<@assertFails message='"m" flag'>
+    ${'x'?keepBeforeLast('x', 'm')}
+</@assertFails>
+<@assertFails message='can only have'>
+    ${'x'?keepBeforeLast('x', 'i', 'x')}
+</@assertFails>
+<@assertFails message='argument'>
+    ${'x'?keepBeforeLast()}
+</@assertFails>
+
+<@assertEquals expected='' actual='foo'?keepAfter('x') />
+<@assertEquals expected='o' actual='foo'?keepAfter('o') />
+<@assertEquals expected='oo' actual='foo'?keepAfter('f') />
+<@assertEquals expected='ar' actual='foobar'?keepAfter('ob') />
+<@assertEquals expected='' actual='foobar'?keepAfter('ar') />
+<@assertEquals expected='' actual='foobar'?keepAfter('foobar') />
+<@assertEquals expected='foobar' actual='foobar'?keepAfter('') />
+<@assertEquals expected='foobar' actual='foobar'?keepAfter('', 'r') />
+<@assertEquals expected='' actual='FOO'?keepAfter('o') />
+<@assertEquals expected='O' actual='FOO'?keepAfter('o', 'i') />
+<@assertEquals expected='o' actual='fo.o'?keepAfter('.') />
+<@assertEquals expected='o.o' actual='fo.o'?keepAfter('.', 'r') />
+<@assertEquals expected='r' actual='FOObaar'?keepAfter(r'([a-z])\1', 'r') />
+<@assertEquals expected='baar' actual='FOObaar'?keepAfter(r'([a-z])\1', 'ri') 
/>
+<@assertEquals expected='bar' actual="foo : bar"?keepAfter(r"\s*:\s*", "r") />
+<@assertEquals expected='bar' actual="foo:bar"?keepAfter(r"\s*:\s*", "r") />
+<@assertFails message='"m" flag'>
+    ${'x'?keepAfter('x', 'm')}
+</@assertFails>
+<@assertFails message='can only have'>
+    ${'x'?keepAfter('x', 'i', 'x')}
+</@assertFails>
+<@assertFails message='argument'>
+    ${'x'?keepAfter()}
+</@assertFails>
+
+<@assertEquals expected='' actual=''?keepAfterLast('f') />
+<@assertEquals expected='' actual='fff'?keepAfterLast('f') />
+<@assertEquals expected='' actual='oof'?keepAfterLast('f') />
+<@assertEquals expected='' actual='f'?keepAfterLast('f') />
+<@assertEquals expected='txt' actual='a.b.txt'?keepAfterLast('.') />
+<@assertEquals expected='' actual='ab'?keepAfterLast('.') />
+<@assertEquals expected='' actual='ab'?keepAfterLast('.', 'r') />
+<@assertEquals expected='' actual='ab'?keepAfterLast(r'\.', 'r') />
+<@assertEquals expected='fa' actual='fFfa'?keepAfterLast('F') />
+<@assertEquals expected='a' actual='fFfa'?keepAfterLast('F', 'i') />
+<@assertEquals expected='3' actual='1a2b3'?keepAfterLast('[ab]', 'r') />
+<@assertEquals expected='' actual='aaabb'?keepAfterLast('[ab]{3}', 'r') />
+<@assertEquals expected='x' actual='aaabbx'?keepAfterLast('[ab]{3}', 'r') />
+<@assertEquals expected='e' actual='aaabbxbabe'?keepAfterLast('[ab]{3}', 'r') 
/>
+<@assertEquals expected='12345' actual='aaabb12345'?keepAfterLast('[ab]{3}', 
'r') />
+<@assertEquals expected='yyy' actual='xxxaaayyy'?keepAfterLast('a+', 'r') />
+<@assertEquals expected='' actual='foobar'?keepAfterLast('') />
+<@assertEquals expected='' actual='foobar'?keepAfterLast('', 'r') />
+<@assertFails message='"m" flag'>
+    ${'x'?keepAfterLast('x', 'm')}
+</@assertFails>
+<@assertFails message='can only have'>
+    ${'x'?keepAfterLast('x', 'i', 'x')}
+</@assertFails>
+<@assertFails message='argument'>
+    ${'x'?keepAfterLast()}
+</@assertFails>
+
+<@assertEquals expected='foo' actual='foo'?removeBeginning('x') />
+<@assertEquals expected='foo' actual='foo'?removeBeginning('o') />
+<@assertEquals expected='foo' actual='foo'?removeBeginning('fooo') />
+<@assertEquals expected='oo' actual='foo'?removeBeginning('f') />
+<@assertEquals expected='o' actual='foo'?removeBeginning('fo') />
+<@assertEquals expected='' actual='foo'?removeBeginning('foo') />
+<@assertEquals expected='foo' actual='foo'?removeBeginning('') />
+<@assertFails message='can only have'>
+    ${'x'?removeBeginning('x', 'x')}
+</@assertFails>
+<@assertFails message='argument'>
+    ${'x'?removeBeginning()}
+</@assertFails>
+
+<@assertEquals expected='bar' actual='bar'?removeEnding('x') />
+<@assertEquals expected='bar' actual='bar'?removeEnding('a') />
+<@assertEquals expected='bar' actual='bar'?removeEnding('barr') />
+<@assertEquals expected='ba' actual='bar'?removeEnding('r') />
+<@assertEquals expected='b' actual='bar'?removeEnding('ar') />
+<@assertEquals expected='' actual='bar'?removeEnding('bar') />
+<@assertEquals expected='bar' actual='bar'?removeEnding('') />
+<@assertFails message='can only have'>
+    ${'x'?removeEnding('x', 'x')}
+</@assertFails>
+<@assertFails message='argument'>
+    ${'x'?removeEnding()}
+</@assertFails>
+
+<@assertEquals expected='xfoo' actual='foo'?ensureStartsWith('x') />
+<@assertEquals expected='foo' actual='foo'?ensureStartsWith('f') />
+<@assertEquals expected='foo' actual='foo'?ensureStartsWith('foo') />
+<@assertEquals expected='fooofoo' actual='foo'?ensureStartsWith('fooo') />
+<@assertEquals expected='foo' actual='foo'?ensureStartsWith('') />
+<@assertEquals expected='x' actual=''?ensureStartsWith('x') />
+<@assertEquals expected='' actual=''?ensureStartsWith('') />
+<@assertEquals expected='bacdef' actual="bacdef"?ensureStartsWith("[ab]{2}", 
"ab") />
+<@assertEquals expected='bacdef' actual="bacdef"?ensureStartsWith("^[ab]{2}", 
"ab") />
+<@assertEquals expected='abcacdef' actual="cacdef"?ensureStartsWith("[ab]{2}", 
"ab") />
+<@assertEquals expected='abcacdef' 
actual="cacdef"?ensureStartsWith("^[ab]{2}", "ab") />
+<@assertEquals expected='ab!cdef' actual="cdef"?ensureStartsWith("ab", "ab!") 
/>
+<@assertEquals expected='ab!ABcdef' actual="ABcdef"?ensureStartsWith("ab", 
"ab!") />
+<@assertEquals expected='ABcdef' actual="ABcdef"?ensureStartsWith("ab", "ab!", 
'i') />
+<@assertEquals expected='abABcdef' actual="ABcdef"?ensureStartsWith(".b", 
"ab", 'i') />
+<@assertEquals expected='ABcdef' actual="ABcdef"?ensureStartsWith(".b", "ab", 
'ri') />
+<@assertEquals expected='http://example.com' 
actual="example.com"?ensureStartsWith("[a-z]+://", "http://";) />
+<@assertEquals expected='http://example.com' 
actual="http://example.com"?ensureStartsWith("[a-z]+://", "http://";) />
+<@assertEquals expected='https://example.com' 
actual="https://example.com"?ensureStartsWith("[a-z]+://", "http://";) />
+<@assertEquals expected='http://HTTP://example.com' 
actual="HTTP://example.com"?ensureStartsWith("[a-z]+://", "http://";) />
+<@assertEquals expected='HTTP://example.com' 
actual="HTTP://example.com"?ensureStartsWith("[a-z]+://", "http://";, "ir") />
+<@assertFails message='can only have'>
+    ${'x'?ensureStartsWith('x', 'x', 'x', 'x')}
+</@assertFails>
+<@assertFails message='argument'>
+    ${'x'?ensureStartsWith()}
+</@assertFails>
+
+<@assertEquals expected='foox' actual='foo'?ensureEndsWith('x') />
+<@assertEquals expected='foo' actual='foo'?ensureEndsWith('o') />
+<@assertEquals expected='foo' actual='foo'?ensureEndsWith('foo') />
+<@assertEquals expected='foofooo' actual='foo'?ensureEndsWith('fooo') />
+<@assertEquals expected='foo' actual='foo'?ensureEndsWith('') />
+<@assertEquals expected='x' actual=''?ensureEndsWith('x') />
+<@assertEquals expected='' actual=''?ensureEndsWith('') />
+<@assertFails message='can only have'>
+    ${'x'?ensureEndsWith('x', 'x')}
+</@assertFails>
+<@assertFails message='argument'>
+    ${'x'?ensureEndsWith()}
+</@assertFails>
+
+<@assertEquals expected='a' actual=1?lowerAbc />
+<@assertEquals expected='b' actual=2?lowerAbc />
+<@assertEquals expected='z' actual=26?lowerAbc />
+<@assertEquals expected='aa' actual=27?lowerAbc />
+<@assertEquals expected='ab' actual=28?lowerAbc />
+<@assertEquals expected='cv' actual=100?lowerAbc />
+<@assertFails messageRegexp='0|at least 1'>>
+    ${0?lowerAbc}
+</@assertFails>
+<@assertFails messageRegexp='0|at least 1'>
+    ${-1?lowerAbc}
+</@assertFails>
+<@assertFails messageRegexp='1.00001|integer'>
+    ${1.00001?lowerAbc}
+</@assertFails>
+
+<@assertEquals expected='A' actual=1?upperAbc />
+<@assertEquals expected='B' actual=2?upperAbc />
+<@assertEquals expected='Z' actual=26?upperAbc />
+<@assertEquals expected='AA' actual=27?upperAbc />
+<@assertEquals expected='AB' actual=28?upperAbc />
+<@assertEquals expected='CV' actual=100?upperAbc />
+<@assertFails messageRegexp='0|at least 1'>>
+    ${0?upperAbc}
+</@assertFails>
+<@assertFails messageRegexp='0|at least 1'>
+    ${-1?upperAbc}
+</@assertFails>
+<@assertFails messageRegexp='1.00001|integer'>
+    ${1.00001?upperAbc}
+</@assertFails>

http://git-wip-us.apache.org/repos/asf/freemarker/blob/81b48221/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/string-builtins3.ftl
----------------------------------------------------------------------
diff --git 
a/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/string-builtins3.ftl
 
b/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/string-builtins3.ftl
deleted file mode 100644
index 0a387ce..0000000
--- 
a/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/string-builtins3.ftl
+++ /dev/null
@@ -1,225 +0,0 @@
-<#--
-  Licensed to the Apache Software Foundation (ASF) under one
-  or more contributor license agreements.  See the NOTICE file
-  distributed with this work for additional information
-  regarding copyright ownership.  The ASF licenses this file
-  to you under the Apache License, Version 2.0 (the
-  "License"); you may not use this file except in compliance
-  with the License.  You may obtain a copy of the License at
-
-    http://www.apache.org/licenses/LICENSE-2.0
-
-  Unless required by applicable law or agreed to in writing,
-  software distributed under the License is distributed on an
-  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
-  KIND, either express or implied.  See the License for the
-  specific language governing permissions and limitations
-  under the License.
--->
-<@assertEquals expected='foo' actual='foo'?keepBefore('x') />
-<@assertEquals expected='f' actual='foo'?keepBefore('o') />
-<@assertEquals expected='' actual='foo'?keepBefore('f') />
-<@assertEquals expected='fo' actual='foobar'?keepBefore('ob') />
-<@assertEquals expected='foob' actual='foobar'?keepBefore('ar') />
-<@assertEquals expected='' actual='foobar'?keepBefore('foobar') />
-<@assertEquals expected='' actual='foobar'?keepBefore('') />
-<@assertEquals expected='' actual='foobar'?keepBefore('', 'r') />
-<@assertEquals expected='FOO' actual='FOO'?keepBefore('o') />
-<@assertEquals expected='F' actual='FOO'?keepBefore('o', 'i') />
-<@assertEquals expected='fo' actual='fo.o'?keepBefore('.') />
-<@assertEquals expected='' actual='fo.o'?keepBefore('.', 'r') />
-<@assertEquals expected='FOOb' actual='FOObaar'?keepBefore(r'([a-z])\1', 'r') 
/>
-<@assertEquals expected='F' actual='FOObaar'?keepBefore(r'([a-z])\1', 'ri') />
-<@assertEquals expected='foo' actual="foo : bar"?keepBefore(r"\s*:\s*", "r") />
-<@assertEquals expected='foo' actual="foo:bar"?keepBefore(r"\s*:\s*", "r") />
-<@assertFails message='"m" flag'>
-    ${'x'?keepBefore('x', 'm')}
-</@assertFails>
-<@assertFails message='can only have'>
-    ${'x'?keepBefore('x', 'i', 'x')}
-</@assertFails>
-<@assertFails message='argument'>
-    ${'x'?keepBefore()}
-</@assertFails>
-
-<@assertEquals expected='' actual=''?keepBeforeLast('f') />
-<@assertEquals expected='ff' actual='fff'?keepBeforeLast('f') />
-<@assertEquals expected='' actual='foo'?keepBeforeLast('f') />
-<@assertEquals expected='' actual='f'?keepBeforeLast('f') />
-<@assertEquals expected='a.b' actual='a.b.txt'?keepBeforeLast('.') />
-<@assertEquals expected='ab' actual='ab'?keepBeforeLast('.') />
-<@assertEquals expected='a' actual='ab'?keepBeforeLast('.', 'r') />
-<@assertEquals expected='ab' actual='ab'?keepBeforeLast(r'\.', 'r') />
-<@assertEquals expected='af' actual='afFf'?keepBeforeLast('F') />
-<@assertEquals expected='afF' actual='afFf'?keepBeforeLast('F', 'i') />
-<@assertEquals expected='1a2' actual='1a2b3'?keepBeforeLast('[ab]', 'r') />
-<@assertEquals expected='aa' actual='aaabb'?keepBeforeLast('[ab]{3}', 'r') />
-<@assertEquals expected='aaabbx' actual='aaabbxbabe'?keepBeforeLast('[ab]{3}', 
'r') />
-<@assertEquals expected='xxxaa' actual='xxxaaayyy'?keepBeforeLast('a+', 'r') />
-<@assertEquals expected='foobar' actual='foobar'?keepBeforeLast('') />
-<@assertEquals expected='foobar' actual='foobar'?keepBeforeLast('', 'r') />
-<@assertFails message='"m" flag'>
-    ${'x'?keepBeforeLast('x', 'm')}
-</@assertFails>
-<@assertFails message='can only have'>
-    ${'x'?keepBeforeLast('x', 'i', 'x')}
-</@assertFails>
-<@assertFails message='argument'>
-    ${'x'?keepBeforeLast()}
-</@assertFails>
-
-<@assertEquals expected='' actual='foo'?keepAfter('x') />
-<@assertEquals expected='o' actual='foo'?keepAfter('o') />
-<@assertEquals expected='oo' actual='foo'?keepAfter('f') />
-<@assertEquals expected='ar' actual='foobar'?keepAfter('ob') />
-<@assertEquals expected='' actual='foobar'?keepAfter('ar') />
-<@assertEquals expected='' actual='foobar'?keepAfter('foobar') />
-<@assertEquals expected='foobar' actual='foobar'?keepAfter('') />
-<@assertEquals expected='foobar' actual='foobar'?keepAfter('', 'r') />
-<@assertEquals expected='' actual='FOO'?keepAfter('o') />
-<@assertEquals expected='O' actual='FOO'?keepAfter('o', 'i') />
-<@assertEquals expected='o' actual='fo.o'?keepAfter('.') />
-<@assertEquals expected='o.o' actual='fo.o'?keepAfter('.', 'r') />
-<@assertEquals expected='r' actual='FOObaar'?keepAfter(r'([a-z])\1', 'r') />
-<@assertEquals expected='baar' actual='FOObaar'?keepAfter(r'([a-z])\1', 'ri') 
/>
-<@assertEquals expected='bar' actual="foo : bar"?keepAfter(r"\s*:\s*", "r") />
-<@assertEquals expected='bar' actual="foo:bar"?keepAfter(r"\s*:\s*", "r") />
-<@assertFails message='"m" flag'>
-    ${'x'?keepAfter('x', 'm')}
-</@assertFails>
-<@assertFails message='can only have'>
-    ${'x'?keepAfter('x', 'i', 'x')}
-</@assertFails>
-<@assertFails message='argument'>
-    ${'x'?keepAfter()}
-</@assertFails>
-
-<@assertEquals expected='' actual=''?keepAfterLast('f') />
-<@assertEquals expected='' actual='fff'?keepAfterLast('f') />
-<@assertEquals expected='' actual='oof'?keepAfterLast('f') />
-<@assertEquals expected='' actual='f'?keepAfterLast('f') />
-<@assertEquals expected='txt' actual='a.b.txt'?keepAfterLast('.') />
-<@assertEquals expected='' actual='ab'?keepAfterLast('.') />
-<@assertEquals expected='' actual='ab'?keepAfterLast('.', 'r') />
-<@assertEquals expected='' actual='ab'?keepAfterLast(r'\.', 'r') />
-<@assertEquals expected='fa' actual='fFfa'?keepAfterLast('F') />
-<@assertEquals expected='a' actual='fFfa'?keepAfterLast('F', 'i') />
-<@assertEquals expected='3' actual='1a2b3'?keepAfterLast('[ab]', 'r') />
-<@assertEquals expected='' actual='aaabb'?keepAfterLast('[ab]{3}', 'r') />
-<@assertEquals expected='x' actual='aaabbx'?keepAfterLast('[ab]{3}', 'r') />
-<@assertEquals expected='e' actual='aaabbxbabe'?keepAfterLast('[ab]{3}', 'r') 
/>
-<@assertEquals expected='12345' actual='aaabb12345'?keepAfterLast('[ab]{3}', 
'r') />
-<@assertEquals expected='yyy' actual='xxxaaayyy'?keepAfterLast('a+', 'r') />
-<@assertEquals expected='' actual='foobar'?keepAfterLast('') />
-<@assertEquals expected='' actual='foobar'?keepAfterLast('', 'r') />
-<@assertFails message='"m" flag'>
-    ${'x'?keepAfterLast('x', 'm')}
-</@assertFails>
-<@assertFails message='can only have'>
-    ${'x'?keepAfterLast('x', 'i', 'x')}
-</@assertFails>
-<@assertFails message='argument'>
-    ${'x'?keepAfterLast()}
-</@assertFails>
-
-<@assertEquals expected='foo' actual='foo'?removeBeginning('x') />
-<@assertEquals expected='foo' actual='foo'?removeBeginning('o') />
-<@assertEquals expected='foo' actual='foo'?removeBeginning('fooo') />
-<@assertEquals expected='oo' actual='foo'?removeBeginning('f') />
-<@assertEquals expected='o' actual='foo'?removeBeginning('fo') />
-<@assertEquals expected='' actual='foo'?removeBeginning('foo') />
-<@assertEquals expected='foo' actual='foo'?removeBeginning('') />
-<@assertFails message='can only have'>
-    ${'x'?removeBeginning('x', 'x')}
-</@assertFails>
-<@assertFails message='argument'>
-    ${'x'?removeBeginning()}
-</@assertFails>
-
-<@assertEquals expected='bar' actual='bar'?removeEnding('x') />
-<@assertEquals expected='bar' actual='bar'?removeEnding('a') />
-<@assertEquals expected='bar' actual='bar'?removeEnding('barr') />
-<@assertEquals expected='ba' actual='bar'?removeEnding('r') />
-<@assertEquals expected='b' actual='bar'?removeEnding('ar') />
-<@assertEquals expected='' actual='bar'?removeEnding('bar') />
-<@assertEquals expected='bar' actual='bar'?removeEnding('') />
-<@assertFails message='can only have'>
-    ${'x'?removeEnding('x', 'x')}
-</@assertFails>
-<@assertFails message='argument'>
-    ${'x'?removeEnding()}
-</@assertFails>
-
-<@assertEquals expected='xfoo' actual='foo'?ensureStartsWith('x') />
-<@assertEquals expected='foo' actual='foo'?ensureStartsWith('f') />
-<@assertEquals expected='foo' actual='foo'?ensureStartsWith('foo') />
-<@assertEquals expected='fooofoo' actual='foo'?ensureStartsWith('fooo') />
-<@assertEquals expected='foo' actual='foo'?ensureStartsWith('') />
-<@assertEquals expected='x' actual=''?ensureStartsWith('x') />
-<@assertEquals expected='' actual=''?ensureStartsWith('') />
-<@assertEquals expected='bacdef' actual="bacdef"?ensureStartsWith("[ab]{2}", 
"ab") />
-<@assertEquals expected='bacdef' actual="bacdef"?ensureStartsWith("^[ab]{2}", 
"ab") />
-<@assertEquals expected='abcacdef' actual="cacdef"?ensureStartsWith("[ab]{2}", 
"ab") />
-<@assertEquals expected='abcacdef' 
actual="cacdef"?ensureStartsWith("^[ab]{2}", "ab") />
-<@assertEquals expected='ab!cdef' actual="cdef"?ensureStartsWith("ab", "ab!") 
/>
-<@assertEquals expected='ab!ABcdef' actual="ABcdef"?ensureStartsWith("ab", 
"ab!") />
-<@assertEquals expected='ABcdef' actual="ABcdef"?ensureStartsWith("ab", "ab!", 
'i') />
-<@assertEquals expected='abABcdef' actual="ABcdef"?ensureStartsWith(".b", 
"ab", 'i') />
-<@assertEquals expected='ABcdef' actual="ABcdef"?ensureStartsWith(".b", "ab", 
'ri') />
-<@assertEquals expected='http://example.com' 
actual="example.com"?ensureStartsWith("[a-z]+://", "http://";) />
-<@assertEquals expected='http://example.com' 
actual="http://example.com"?ensureStartsWith("[a-z]+://", "http://";) />
-<@assertEquals expected='https://example.com' 
actual="https://example.com"?ensureStartsWith("[a-z]+://", "http://";) />
-<@assertEquals expected='http://HTTP://example.com' 
actual="HTTP://example.com"?ensureStartsWith("[a-z]+://", "http://";) />
-<@assertEquals expected='HTTP://example.com' 
actual="HTTP://example.com"?ensureStartsWith("[a-z]+://", "http://";, "ir") />
-<@assertFails message='can only have'>
-    ${'x'?ensureStartsWith('x', 'x', 'x', 'x')}
-</@assertFails>
-<@assertFails message='argument'>
-    ${'x'?ensureStartsWith()}
-</@assertFails>
-
-<@assertEquals expected='foox' actual='foo'?ensureEndsWith('x') />
-<@assertEquals expected='foo' actual='foo'?ensureEndsWith('o') />
-<@assertEquals expected='foo' actual='foo'?ensureEndsWith('foo') />
-<@assertEquals expected='foofooo' actual='foo'?ensureEndsWith('fooo') />
-<@assertEquals expected='foo' actual='foo'?ensureEndsWith('') />
-<@assertEquals expected='x' actual=''?ensureEndsWith('x') />
-<@assertEquals expected='' actual=''?ensureEndsWith('') />
-<@assertFails message='can only have'>
-    ${'x'?ensureEndsWith('x', 'x')}
-</@assertFails>
-<@assertFails message='argument'>
-    ${'x'?ensureEndsWith()}
-</@assertFails>
-
-<@assertEquals expected='a' actual=1?lowerAbc />
-<@assertEquals expected='b' actual=2?lowerAbc />
-<@assertEquals expected='z' actual=26?lowerAbc />
-<@assertEquals expected='aa' actual=27?lowerAbc />
-<@assertEquals expected='ab' actual=28?lowerAbc />
-<@assertEquals expected='cv' actual=100?lowerAbc />
-<@assertFails messageRegexp='0|at least 1'>>
-    ${0?lowerAbc}
-</@assertFails>
-<@assertFails messageRegexp='0|at least 1'>
-    ${-1?lowerAbc}
-</@assertFails>
-<@assertFails messageRegexp='1.00001|integer'>
-    ${1.00001?lowerAbc}
-</@assertFails>
-
-<@assertEquals expected='A' actual=1?upperAbc />
-<@assertEquals expected='B' actual=2?upperAbc />
-<@assertEquals expected='Z' actual=26?upperAbc />
-<@assertEquals expected='AA' actual=27?upperAbc />
-<@assertEquals expected='AB' actual=28?upperAbc />
-<@assertEquals expected='CV' actual=100?upperAbc />
-<@assertFails messageRegexp='0|at least 1'>>
-    ${0?upperAbc}
-</@assertFails>
-<@assertFails messageRegexp='0|at least 1'>
-    ${-1?upperAbc}
-</@assertFails>
-<@assertFails messageRegexp='1.00001|integer'>
-    ${1.00001?upperAbc}
-</@assertFails>

http://git-wip-us.apache.org/repos/asf/freemarker/blob/81b48221/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/stringbimethods.f3ac
----------------------------------------------------------------------
diff --git 
a/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/stringbimethods.f3ac
 
b/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/stringbimethods.f3ac
new file mode 100644
index 0000000..c3bd460
--- /dev/null
+++ 
b/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/stringbimethods.f3ac
@@ -0,0 +1,32 @@
+<#--
+  Licensed to the Apache Software Foundation (ASF) under one
+  or more contributor license agreements.  See the NOTICE file
+  distributed with this work for additional information
+  regarding copyright ownership.  The ASF licenses this file
+  to you under the Apache License, Version 2.0 (the
+  "License"); you may not use this file except in compliance
+  with the License.  You may obtain a copy of the License at
+
+    http://www.apache.org/licenses/LICENSE-2.0
+
+  Unless required by applicable law or agreed to in writing,
+  software distributed under the License is distributed on an
+  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+  KIND, either express or implied.  See the License for the
+  specific language governing permissions and limitations
+  under the License.
+-->
+<#setting locale="en_US">
+<#assign x = 3>
+${x?string["0.00"]}
+${x?string("0.00")}
+${'01:02:03'?time.iso?string["iso ms nz"]}
+${'01:02:03'?time.iso?string("iso ms nz")}
+---
+${multi}
+<#assign a = true>
+<#assign b = false>
+${a?string} ${b?string}
+${a?string("yes", "no")} ${b?string("yes", "no")}
+<#setting booleanFormat="igen,nem"/>
+${a?string} ${b?string}

http://git-wip-us.apache.org/repos/asf/freemarker/blob/81b48221/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/stringbimethods.ftl
----------------------------------------------------------------------
diff --git 
a/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/stringbimethods.ftl
 
b/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/stringbimethods.ftl
deleted file mode 100644
index c3bd460..0000000
--- 
a/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/stringbimethods.ftl
+++ /dev/null
@@ -1,32 +0,0 @@
-<#--
-  Licensed to the Apache Software Foundation (ASF) under one
-  or more contributor license agreements.  See the NOTICE file
-  distributed with this work for additional information
-  regarding copyright ownership.  The ASF licenses this file
-  to you under the Apache License, Version 2.0 (the
-  "License"); you may not use this file except in compliance
-  with the License.  You may obtain a copy of the License at
-
-    http://www.apache.org/licenses/LICENSE-2.0
-
-  Unless required by applicable law or agreed to in writing,
-  software distributed under the License is distributed on an
-  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
-  KIND, either express or implied.  See the License for the
-  specific language governing permissions and limitations
-  under the License.
--->
-<#setting locale="en_US">
-<#assign x = 3>
-${x?string["0.00"]}
-${x?string("0.00")}
-${'01:02:03'?time.iso?string["iso ms nz"]}
-${'01:02:03'?time.iso?string("iso ms nz")}
----
-${multi}
-<#assign a = true>
-<#assign b = false>
-${a?string} ${b?string}
-${a?string("yes", "no")} ${b?string("yes", "no")}
-<#setting booleanFormat="igen,nem"/>
-${a?string} ${b?string}

http://git-wip-us.apache.org/repos/asf/freemarker/blob/81b48221/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/stringliteral.f3ac
----------------------------------------------------------------------
diff --git 
a/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/stringliteral.f3ac
 
b/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/stringliteral.f3ac
new file mode 100644
index 0000000..436c632
--- /dev/null
+++ 
b/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/stringliteral.f3ac
@@ -0,0 +1,69 @@
+<#--
+  Licensed to the Apache Software Foundation (ASF) under one
+  or more contributor license agreements.  See the NOTICE file
+  distributed with this work for additional information
+  regarding copyright ownership.  The ASF licenses this file
+  to you under the Apache License, Version 2.0 (the
+  "License"); you may not use this file except in compliance
+  with the License.  You may obtain a copy of the License at
+
+    http://www.apache.org/licenses/LICENSE-2.0
+
+  Unless required by applicable law or agreed to in writing,
+  software distributed under the License is distributed on an
+  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+  KIND, either express or implied.  See the License for the
+  specific language governing permissions and limitations
+  under the License.
+-->
+<html>
+<head>
+  <title>FreeMarker: String literal test</title>
+  <meta http-equiv="Content-type" content="text/html; charset=UTF-8">
+</head>
+<body>
+
+<p>A simple test follows:</p>
+
+<#assign x = "Hello", y = "World">
+<#assign message = "${x}, ${y}!">
+
+${message}
+
+<p>
+[${""}] = []<br>
+[${"a"}] = [a]<br>
+[${"abcdef"}] = [abcdef]<br>
+[${"\""}] = ["]<br>
+[${"\"\"\""}] = ["""]<br>
+[${"a\""}] = [a"]<br>
+[${"\"a"}] = ["a]<br>
+[${"a\"b"}] = [a"b]<br>
+[${"a\nb"}] = [a
+b]<br>
+[${"'"}] = [']<br>
+[${"a'a"}] = [a'a]<br>
+[${"\"\'\n\r\f\b\t\l\a\g"}]<br>
+[${"\xA\x0A\x00A\x000A\x0000A"}]<br>
+[${"\x15Bz\x15b"}]<br>
+[${"\x010Cz\x010c"}]<br>
+
+<p>
+[${''}] = []<br>
+[${'a'}] = [a]<br>
+[${'abcdef'}] = [abcdef]<br>
+[${'"'}] = ["]<br>
+[${'"""'}] = ["""]<br>
+[${'a"'}] = [a"]<br>
+[${'"a'}] = ["a]<br>
+[${'a"b'}] = [a"b]<br>
+[${'a\nb'}] = [a
+b]<br>
+[${'\''}] = [']<br>
+[${'a\'a'}] = [a'a]<br>
+[${'\"\'\n\r\f\b\t\l\a\g'}]<br>
+[${'\xA\x0A\x00A\x000A\x0000A'}]<br>
+[${'\x15Bz\x15b'}]<br>
+[${'\x010Cz\x010c'}]<br>
+</body>
+</html>
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/freemarker/blob/81b48221/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/stringliteral.ftl
----------------------------------------------------------------------
diff --git 
a/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/stringliteral.ftl
 
b/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/stringliteral.ftl
deleted file mode 100644
index 436c632..0000000
--- 
a/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/stringliteral.ftl
+++ /dev/null
@@ -1,69 +0,0 @@
-<#--
-  Licensed to the Apache Software Foundation (ASF) under one
-  or more contributor license agreements.  See the NOTICE file
-  distributed with this work for additional information
-  regarding copyright ownership.  The ASF licenses this file
-  to you under the Apache License, Version 2.0 (the
-  "License"); you may not use this file except in compliance
-  with the License.  You may obtain a copy of the License at
-
-    http://www.apache.org/licenses/LICENSE-2.0
-
-  Unless required by applicable law or agreed to in writing,
-  software distributed under the License is distributed on an
-  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
-  KIND, either express or implied.  See the License for the
-  specific language governing permissions and limitations
-  under the License.
--->
-<html>
-<head>
-  <title>FreeMarker: String literal test</title>
-  <meta http-equiv="Content-type" content="text/html; charset=UTF-8">
-</head>
-<body>
-
-<p>A simple test follows:</p>
-
-<#assign x = "Hello", y = "World">
-<#assign message = "${x}, ${y}!">
-
-${message}
-
-<p>
-[${""}] = []<br>
-[${"a"}] = [a]<br>
-[${"abcdef"}] = [abcdef]<br>
-[${"\""}] = ["]<br>
-[${"\"\"\""}] = ["""]<br>
-[${"a\""}] = [a"]<br>
-[${"\"a"}] = ["a]<br>
-[${"a\"b"}] = [a"b]<br>
-[${"a\nb"}] = [a
-b]<br>
-[${"'"}] = [']<br>
-[${"a'a"}] = [a'a]<br>
-[${"\"\'\n\r\f\b\t\l\a\g"}]<br>
-[${"\xA\x0A\x00A\x000A\x0000A"}]<br>
-[${"\x15Bz\x15b"}]<br>
-[${"\x010Cz\x010c"}]<br>
-
-<p>
-[${''}] = []<br>
-[${'a'}] = [a]<br>
-[${'abcdef'}] = [abcdef]<br>
-[${'"'}] = ["]<br>
-[${'"""'}] = ["""]<br>
-[${'a"'}] = [a"]<br>
-[${'"a'}] = ["a]<br>
-[${'a"b'}] = [a"b]<br>
-[${'a\nb'}] = [a
-b]<br>
-[${'\''}] = [']<br>
-[${'a\'a'}] = [a'a]<br>
-[${'\"\'\n\r\f\b\t\l\a\g'}]<br>
-[${'\xA\x0A\x00A\x000A\x0000A'}]<br>
-[${'\x15Bz\x15b'}]<br>
-[${'\x010Cz\x010c'}]<br>
-</body>
-</html>
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/freemarker/blob/81b48221/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/subdir/include-subdir.f3ac
----------------------------------------------------------------------
diff --git 
a/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/subdir/include-subdir.f3ac
 
b/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/subdir/include-subdir.f3ac
new file mode 100644
index 0000000..20a676c
--- /dev/null
+++ 
b/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/subdir/include-subdir.f3ac
@@ -0,0 +1,27 @@
+<#--
+  Licensed to the Apache Software Foundation (ASF) under one
+  or more contributor license agreements.  See the NOTICE file
+  distributed with this work for additional information
+  regarding copyright ownership.  The ASF licenses this file
+  to you under the Apache License, Version 2.0 (the
+  "License"); you may not use this file except in compliance
+  with the License.  You may obtain a copy of the License at
+
+    http://www.apache.org/licenses/LICENSE-2.0
+
+  Unless required by applicable law or agreed to in writing,
+  software distributed under the License is distributed on an
+  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+  KIND, either express or implied.  See the License for the
+  specific language governing permissions and limitations
+  under the License.
+-->
+<p>This is include-subdir.f3ac</p>
+<p>Testing including from same directory</p>
+<#include "include-subdir2.f3ac">
+<p>Testing including from relative parent</p>
+<#include "../included.f3ac">
+<p>Testing including from loader root</p>
+<#include "/included.f3ac">
+<p>Testing including through acquisition</p>
+<#include "*/subdir/include-subdir2.f3ac">
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/freemarker/blob/81b48221/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/subdir/include-subdir.ftl
----------------------------------------------------------------------
diff --git 
a/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/subdir/include-subdir.ftl
 
b/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/subdir/include-subdir.ftl
deleted file mode 100644
index cd24873..0000000
--- 
a/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/subdir/include-subdir.ftl
+++ /dev/null
@@ -1,27 +0,0 @@
-<#--
-  Licensed to the Apache Software Foundation (ASF) under one
-  or more contributor license agreements.  See the NOTICE file
-  distributed with this work for additional information
-  regarding copyright ownership.  The ASF licenses this file
-  to you under the Apache License, Version 2.0 (the
-  "License"); you may not use this file except in compliance
-  with the License.  You may obtain a copy of the License at
-
-    http://www.apache.org/licenses/LICENSE-2.0
-
-  Unless required by applicable law or agreed to in writing,
-  software distributed under the License is distributed on an
-  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
-  KIND, either express or implied.  See the License for the
-  specific language governing permissions and limitations
-  under the License.
--->
-<p>This is include-subdir.ftl</p>
-<p>Testing including from same directory</p>
-<#include "include-subdir2.ftl">
-<p>Testing including from relative parent</p>
-<#include "../included.ftl">
-<p>Testing including from loader root</p>
-<#include "/included.ftl">
-<p>Testing including through acquisition</p>
-<#include "*/subdir/include-subdir2.ftl">
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/freemarker/blob/81b48221/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/subdir/include-subdir2.f3ac
----------------------------------------------------------------------
diff --git 
a/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/subdir/include-subdir2.f3ac
 
b/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/subdir/include-subdir2.f3ac
new file mode 100644
index 0000000..12c458f
--- /dev/null
+++ 
b/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/subdir/include-subdir2.f3ac
@@ -0,0 +1,19 @@
+<#--
+  Licensed to the Apache Software Foundation (ASF) under one
+  or more contributor license agreements.  See the NOTICE file
+  distributed with this work for additional information
+  regarding copyright ownership.  The ASF licenses this file
+  to you under the Apache License, Version 2.0 (the
+  "License"); you may not use this file except in compliance
+  with the License.  You may obtain a copy of the License at
+
+    http://www.apache.org/licenses/LICENSE-2.0
+
+  Unless required by applicable law or agreed to in writing,
+  software distributed under the License is distributed on an
+  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+  KIND, either express or implied.  See the License for the
+  specific language governing permissions and limitations
+  under the License.
+-->
+<p>This is include-subdir2.f3ac</p>

http://git-wip-us.apache.org/repos/asf/freemarker/blob/81b48221/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/subdir/include-subdir2.ftl
----------------------------------------------------------------------
diff --git 
a/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/subdir/include-subdir2.ftl
 
b/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/subdir/include-subdir2.ftl
deleted file mode 100644
index 356fcb2..0000000
--- 
a/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/subdir/include-subdir2.ftl
+++ /dev/null
@@ -1,19 +0,0 @@
-<#--
-  Licensed to the Apache Software Foundation (ASF) under one
-  or more contributor license agreements.  See the NOTICE file
-  distributed with this work for additional information
-  regarding copyright ownership.  The ASF licenses this file
-  to you under the Apache License, Version 2.0 (the
-  "License"); you may not use this file except in compliance
-  with the License.  You may obtain a copy of the License at
-
-    http://www.apache.org/licenses/LICENSE-2.0
-
-  Unless required by applicable law or agreed to in writing,
-  software distributed under the License is distributed on an
-  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
-  KIND, either express or implied.  See the License for the
-  specific language governing permissions and limitations
-  under the License.
--->
-<p>This is include-subdir2.ftl</p>

http://git-wip-us.apache.org/repos/asf/freemarker/blob/81b48221/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/subdir/new-optin-2.f3ac
----------------------------------------------------------------------
diff --git 
a/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/subdir/new-optin-2.f3ac
 
b/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/subdir/new-optin-2.f3ac
new file mode 100644
index 0000000..fafe593
--- /dev/null
+++ 
b/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/subdir/new-optin-2.f3ac
@@ -0,0 +1,24 @@
+<#--
+  Licensed to the Apache Software Foundation (ASF) under one
+  or more contributor license agreements.  See the NOTICE file
+  distributed with this work for additional information
+  regarding copyright ownership.  The ASF licenses this file
+  to you under the Apache License, Version 2.0 (the
+  "License"); you may not use this file except in compliance
+  with the License.  You may obtain a copy of the License at
+
+    http://www.apache.org/licenses/LICENSE-2.0
+
+  Unless required by applicable law or agreed to in writing,
+  software distributed under the License is distributed on an
+  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+  KIND, either express or implied.  See the License for the
+  specific language governing permissions and limitations
+  under the License.
+-->
+${"org.apache.freemarker.core.templatesuite.models.NewTestModel"?new("works")}
+<#attempt>
+${"org.apache.freemarker.core.templatesuite.models.NewTestModel2"?new("works")}
+<#recover>
+fails
+</#attempt>
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/freemarker/blob/81b48221/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/subdir/new-optin-2.ftl
----------------------------------------------------------------------
diff --git 
a/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/subdir/new-optin-2.ftl
 
b/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/subdir/new-optin-2.ftl
deleted file mode 100644
index fafe593..0000000
--- 
a/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/subdir/new-optin-2.ftl
+++ /dev/null
@@ -1,24 +0,0 @@
-<#--
-  Licensed to the Apache Software Foundation (ASF) under one
-  or more contributor license agreements.  See the NOTICE file
-  distributed with this work for additional information
-  regarding copyright ownership.  The ASF licenses this file
-  to you under the Apache License, Version 2.0 (the
-  "License"); you may not use this file except in compliance
-  with the License.  You may obtain a copy of the License at
-
-    http://www.apache.org/licenses/LICENSE-2.0
-
-  Unless required by applicable law or agreed to in writing,
-  software distributed under the License is distributed on an
-  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
-  KIND, either express or implied.  See the License for the
-  specific language governing permissions and limitations
-  under the License.
--->
-${"org.apache.freemarker.core.templatesuite.models.NewTestModel"?new("works")}
-<#attempt>
-${"org.apache.freemarker.core.templatesuite.models.NewTestModel2"?new("works")}
-<#recover>
-fails
-</#attempt>
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/freemarker/blob/81b48221/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/subdir/new-optin.f3ac
----------------------------------------------------------------------
diff --git 
a/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/subdir/new-optin.f3ac
 
b/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/subdir/new-optin.f3ac
new file mode 100644
index 0000000..97d88e8
--- /dev/null
+++ 
b/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/subdir/new-optin.f3ac
@@ -0,0 +1,26 @@
+<#--
+  Licensed to the Apache Software Foundation (ASF) under one
+  or more contributor license agreements.  See the NOTICE file
+  distributed with this work for additional information
+  regarding copyright ownership.  The ASF licenses this file
+  to you under the Apache License, Version 2.0 (the
+  "License"); you may not use this file except in compliance
+  with the License.  You may obtain a copy of the License at
+
+    http://www.apache.org/licenses/LICENSE-2.0
+
+  Unless required by applicable law or agreed to in writing,
+  software distributed under the License is distributed on an
+  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+  KIND, either express or implied.  See the License for the
+  specific language governing permissions and limitations
+  under the License.
+-->
+${"org.apache.freemarker.core.templatesuite.models.NewTestModel"?new("works")}
+<#attempt>
+${"org.apache.freemarker.core.templatesuite.models.NewTestModel2"?new("works")}
+<#recover>
+fails
+</#attempt>
+
+<#include "new-optin-2.f3ac">
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/freemarker/blob/81b48221/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/subdir/new-optin.ftl
----------------------------------------------------------------------
diff --git 
a/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/subdir/new-optin.ftl
 
b/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/subdir/new-optin.ftl
deleted file mode 100644
index cc37004..0000000
--- 
a/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/subdir/new-optin.ftl
+++ /dev/null
@@ -1,26 +0,0 @@
-<#--
-  Licensed to the Apache Software Foundation (ASF) under one
-  or more contributor license agreements.  See the NOTICE file
-  distributed with this work for additional information
-  regarding copyright ownership.  The ASF licenses this file
-  to you under the Apache License, Version 2.0 (the
-  "License"); you may not use this file except in compliance
-  with the License.  You may obtain a copy of the License at
-
-    http://www.apache.org/licenses/LICENSE-2.0
-
-  Unless required by applicable law or agreed to in writing,
-  software distributed under the License is distributed on an
-  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
-  KIND, either express or implied.  See the License for the
-  specific language governing permissions and limitations
-  under the License.
--->
-${"org.apache.freemarker.core.templatesuite.models.NewTestModel"?new("works")}
-<#attempt>
-${"org.apache.freemarker.core.templatesuite.models.NewTestModel2"?new("works")}
-<#recover>
-fails
-</#attempt>
-
-<#include "new-optin-2.ftl">
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/freemarker/blob/81b48221/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/subdir/subsub/new-optin.f3ac
----------------------------------------------------------------------
diff --git 
a/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/subdir/subsub/new-optin.f3ac
 
b/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/subdir/subsub/new-optin.f3ac
new file mode 100644
index 0000000..fafe593
--- /dev/null
+++ 
b/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/subdir/subsub/new-optin.f3ac
@@ -0,0 +1,24 @@
+<#--
+  Licensed to the Apache Software Foundation (ASF) under one
+  or more contributor license agreements.  See the NOTICE file
+  distributed with this work for additional information
+  regarding copyright ownership.  The ASF licenses this file
+  to you under the Apache License, Version 2.0 (the
+  "License"); you may not use this file except in compliance
+  with the License.  You may obtain a copy of the License at
+
+    http://www.apache.org/licenses/LICENSE-2.0
+
+  Unless required by applicable law or agreed to in writing,
+  software distributed under the License is distributed on an
+  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+  KIND, either express or implied.  See the License for the
+  specific language governing permissions and limitations
+  under the License.
+-->
+${"org.apache.freemarker.core.templatesuite.models.NewTestModel"?new("works")}
+<#attempt>
+${"org.apache.freemarker.core.templatesuite.models.NewTestModel2"?new("works")}
+<#recover>
+fails
+</#attempt>
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/freemarker/blob/81b48221/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/subdir/subsub/new-optin.ftl
----------------------------------------------------------------------
diff --git 
a/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/subdir/subsub/new-optin.ftl
 
b/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/subdir/subsub/new-optin.ftl
deleted file mode 100644
index fafe593..0000000
--- 
a/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/subdir/subsub/new-optin.ftl
+++ /dev/null
@@ -1,24 +0,0 @@
-<#--
-  Licensed to the Apache Software Foundation (ASF) under one
-  or more contributor license agreements.  See the NOTICE file
-  distributed with this work for additional information
-  regarding copyright ownership.  The ASF licenses this file
-  to you under the Apache License, Version 2.0 (the
-  "License"); you may not use this file except in compliance
-  with the License.  You may obtain a copy of the License at
-
-    http://www.apache.org/licenses/LICENSE-2.0
-
-  Unless required by applicable law or agreed to in writing,
-  software distributed under the License is distributed on an
-  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
-  KIND, either express or implied.  See the License for the
-  specific language governing permissions and limitations
-  under the License.
--->
-${"org.apache.freemarker.core.templatesuite.models.NewTestModel"?new("works")}
-<#attempt>
-${"org.apache.freemarker.core.templatesuite.models.NewTestModel2"?new("works")}
-<#recover>
-fails
-</#attempt>
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/freemarker/blob/81b48221/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/switch-builtin.f3ac
----------------------------------------------------------------------
diff --git 
a/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/switch-builtin.f3ac
 
b/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/switch-builtin.f3ac
new file mode 100644
index 0000000..f79f639
--- /dev/null
+++ 
b/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/switch-builtin.f3ac
@@ -0,0 +1,54 @@
+<#--
+  Licensed to the Apache Software Foundation (ASF) under one
+  or more contributor license agreements.  See the NOTICE file
+  distributed with this work for additional information
+  regarding copyright ownership.  The ASF licenses this file
+  to you under the Apache License, Version 2.0 (the
+  "License"); you may not use this file except in compliance
+  with the License.  You may obtain a copy of the License at
+
+    http://www.apache.org/licenses/LICENSE-2.0
+
+  Unless required by applicable law or agreed to in writing,
+  software distributed under the License is distributed on an
+  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+  KIND, either express or implied.  See the License for the
+  specific language governing permissions and limitations
+  under the License.
+-->
+<@assertEquals expected="A" actual="a"?switch("a", "A") />
+<@assertFails message="didn't match">${"b"?switch("a", "A")}</@>
+<@assertEquals expected="D" actual="b"?switch("a", "A", "D") />
+<@assertEquals expected="B" actual="b"?switch("a", "A", "b", "B") />
+<@assertFails message="didn't match">${"c"?switch("a", "A", "b", "B")}</@>
+<@assertEquals expected="D" actual="c"?switch("a", "A", "b", "B", "D") />
+
+<#assign out = "">
+<#assign fInvocationCnt = 0>
+<#list 0..5 as x>
+  <#assign out += x?switch(1, f("one"), 2, f("two"), 3, f("three"), 
f("default")) + ";">
+</#list>
+<@assertEquals expected="default;one;two;three;default;default;" actual=out />
+<@assertEquals expected=6 actual=fInvocationCnt />
+
+<#assign out = "">
+<#list 0..5 as x>
+  <#assign out += true?switch(x <= 1, "low", x == 2 || x == 3, "medium", x >= 
3, "high") + ";">
+</#list>
+<@assertEquals expected="low;low;medium;medium;high;high;" actual=out />
+
+<#function f(x)>
+  <#assign fInvocationCnt++>
+  <#return x>
+</#function>
+
+<@assertFails message="noSuchVar1">${1?switch(noSuchVar1, noSuchVar2)}</@>
+<@assertFails message="noSuchVar2">${1?switch(1, noSuchVar2)}</@>
+<@assertFails message="noSuchVar3">${noSuchVar3?switch(1, 1)}</@>
+
+<@assertEquals expected="one" actual=1?switch(1, "one", "2", "two") />
+<@assertFails messageRegexp="Can't compare.+number.+string">${2?switch(1, 
"one", "2", "two")}</@>
+<@assertFails messageRegexp="Can't compare.+number.+string">${2?switch(1, 
"one", "2", "two", "default")}</@>
+
+<#assign out><#escape x as x?switch(2 * x, "zero", 1, "one", x, 
x?string("0.0"))>${0} ${1} ${2}</#escape></#assign>
+<@assertEquals expected="zero one 2.0" actual=out />

http://git-wip-us.apache.org/repos/asf/freemarker/blob/81b48221/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/switch-builtin.ftl
----------------------------------------------------------------------
diff --git 
a/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/switch-builtin.ftl
 
b/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/switch-builtin.ftl
deleted file mode 100644
index f79f639..0000000
--- 
a/freemarker-core-test/src/test/resources/org/apache/freemarker/core/templatesuite/templates/switch-builtin.ftl
+++ /dev/null
@@ -1,54 +0,0 @@
-<#--
-  Licensed to the Apache Software Foundation (ASF) under one
-  or more contributor license agreements.  See the NOTICE file
-  distributed with this work for additional information
-  regarding copyright ownership.  The ASF licenses this file
-  to you under the Apache License, Version 2.0 (the
-  "License"); you may not use this file except in compliance
-  with the License.  You may obtain a copy of the License at
-
-    http://www.apache.org/licenses/LICENSE-2.0
-
-  Unless required by applicable law or agreed to in writing,
-  software distributed under the License is distributed on an
-  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
-  KIND, either express or implied.  See the License for the
-  specific language governing permissions and limitations
-  under the License.
--->
-<@assertEquals expected="A" actual="a"?switch("a", "A") />
-<@assertFails message="didn't match">${"b"?switch("a", "A")}</@>
-<@assertEquals expected="D" actual="b"?switch("a", "A", "D") />
-<@assertEquals expected="B" actual="b"?switch("a", "A", "b", "B") />
-<@assertFails message="didn't match">${"c"?switch("a", "A", "b", "B")}</@>
-<@assertEquals expected="D" actual="c"?switch("a", "A", "b", "B", "D") />
-
-<#assign out = "">
-<#assign fInvocationCnt = 0>
-<#list 0..5 as x>
-  <#assign out += x?switch(1, f("one"), 2, f("two"), 3, f("three"), 
f("default")) + ";">
-</#list>
-<@assertEquals expected="default;one;two;three;default;default;" actual=out />
-<@assertEquals expected=6 actual=fInvocationCnt />
-
-<#assign out = "">
-<#list 0..5 as x>
-  <#assign out += true?switch(x <= 1, "low", x == 2 || x == 3, "medium", x >= 
3, "high") + ";">
-</#list>
-<@assertEquals expected="low;low;medium;medium;high;high;" actual=out />
-
-<#function f(x)>
-  <#assign fInvocationCnt++>
-  <#return x>
-</#function>
-
-<@assertFails message="noSuchVar1">${1?switch(noSuchVar1, noSuchVar2)}</@>
-<@assertFails message="noSuchVar2">${1?switch(1, noSuchVar2)}</@>
-<@assertFails message="noSuchVar3">${noSuchVar3?switch(1, 1)}</@>
-
-<@assertEquals expected="one" actual=1?switch(1, "one", "2", "two") />
-<@assertFails messageRegexp="Can't compare.+number.+string">${2?switch(1, 
"one", "2", "two")}</@>
-<@assertFails messageRegexp="Can't compare.+number.+string">${2?switch(1, 
"one", "2", "two", "default")}</@>
-
-<#assign out><#escape x as x?switch(2 * x, "zero", 1, "one", x, 
x?string("0.0"))>${0} ${1} ${2}</#escape></#assign>
-<@assertEquals expected="zero one 2.0" actual=out />

Reply via email to