use of lucee.transformer.bytecode.BodyBase in project Lucee by lucee.
the class TagFunction method _writeOut.
public void _writeOut(BytecodeContext bc, int type) throws TransformerException {
// private static final Expression EMPTY = LitString.toExprString("");
Body functionBody = new BodyBase(bc.getFactory());
RefBoolean isStatic = new RefBooleanImpl();
Function func = createFunction(bc.getPage(), functionBody, isStatic, bc.getOutput());
// ScriptBody sb=new ScriptBody(bc.getFactory());
func.setParent(getParent());
List<Statement> statements = getBody().getStatements();
Statement stat;
Tag tag;
// suppress WS between cffunction and the last cfargument
Tag last = null;
if (bc.getSupressWSbeforeArg()) {
// check if there is a cfargument at all
Iterator<Statement> it = statements.iterator();
while (it.hasNext()) {
stat = it.next();
if (stat instanceof Tag) {
tag = (Tag) stat;
if (tag.getTagLibTag().getTagClassDefinition().isClassNameEqualTo("lucee.runtime.tag.Argument")) {
last = tag;
}
}
}
// check if there are only literal WS printouts
if (last != null) {
it = statements.iterator();
while (it.hasNext()) {
stat = it.next();
if (stat == last)
break;
if (stat instanceof PrintOut) {
PrintOut po = (PrintOut) stat;
Expression expr = po.getExpr();
if (!(expr instanceof LitString) || !StringUtil.isWhiteSpace(((LitString) expr).getString())) {
last = null;
break;
}
}
}
}
}
Iterator<Statement> it = statements.iterator();
boolean beforeLastArgument = last != null;
while (it.hasNext()) {
stat = it.next();
if (beforeLastArgument) {
if (stat == last) {
beforeLastArgument = false;
} else if (stat instanceof PrintOut) {
PrintOut po = (PrintOut) stat;
Expression expr = po.getExpr();
if (expr instanceof LitString) {
LitString ls = (LitString) expr;
if (StringUtil.isWhiteSpace(ls.getString()))
continue;
}
}
}
if (stat instanceof Tag) {
tag = (Tag) stat;
if (tag.getTagLibTag().getTagClassDefinition().isClassNameEqualTo("lucee.runtime.tag.Argument")) {
addArgument(func, tag);
continue;
}
}
functionBody.addStatement(stat);
}
func._writeOut(bc, type);
}
use of lucee.transformer.bytecode.BodyBase in project Lucee by lucee.
the class AbstrCFMLScriptTransformer method tryStatement.
/**
* Liest eine try Block ein
* <br />
* EBNF:<br />
* <code>;</code>
* @return Try Block
* @throws TemplateException
*/
private final TryCatchFinally tryStatement(ExprData data) throws TemplateException {
if (!data.srcCode.forwardIfCurrent("try", '{') && !data.srcCode.forwardIfCurrent("try ") && !data.srcCode.forwardIfCurrent("try", '/'))
return null;
data.srcCode.previous();
Body body = new BodyBase(data.factory);
TryCatchFinally tryCatchFinally = new TryCatchFinally(data.factory, body, data.srcCode.getPosition(), null);
statement(data, body, CTX_TRY);
comments(data);
// catches
short catchCount = 0;
while (data.srcCode.forwardIfCurrent("catch", '(')) {
catchCount++;
comments(data);
// type
int pos = data.srcCode.getPos();
Position line = data.srcCode.getPosition();
Expression name = null, type = null;
StringBuffer sbType = new StringBuffer();
String id;
while (true) {
id = identifier(data, false);
if (id == null)
break;
sbType.append(id);
data.srcCode.removeSpace();
if (!data.srcCode.forwardIfCurrent('.'))
break;
sbType.append('.');
data.srcCode.removeSpace();
}
if (sbType.length() == 0) {
type = string(data);
if (type == null)
throw new TemplateException(data.srcCode, "a catch statement must begin with the throwing type (query, application ...).");
} else {
type = data.factory.createLitString(sbType.toString());
}
// name = expression();
comments(data);
// name
if (!data.srcCode.isCurrent(')')) {
name = expression(data);
} else {
data.srcCode.setPos(pos);
name = expression(data);
type = data.factory.createLitString("any");
}
comments(data);
Body b = new BodyBase(data.factory);
try {
tryCatchFinally.addCatch(type, name, b, line);
} catch (TransformerException e) {
throw new TemplateException(data.srcCode, e.getMessage());
}
comments(data);
if (!data.srcCode.forwardIfCurrent(')'))
throw new TemplateException(data.srcCode, "invalid catch statement, missing closing )");
statement(data, b, CTX_CATCH);
comments(data);
}
// finally
if (finallyStatement(data, tryCatchFinally)) {
comments(data);
} else if (catchCount == 0)
throw new TemplateException(data.srcCode, "a try statement must have at least one catch statement");
// if(body.isEmpty()) return null;
tryCatchFinally.setEnd(data.srcCode.getPosition());
return tryCatchFinally;
}
use of lucee.transformer.bytecode.BodyBase in project Lucee by lucee.
the class AbstrCFMLScriptTransformer method caseStatement.
/**
* Liest ein Case Statement ein
* @return case Statement
* @throws TemplateException
*/
private final boolean caseStatement(ExprData data, Switch swit) throws TemplateException {
if (!data.srcCode.forwardIfCurrentAndNoWordAfter("case"))
return false;
// int line=data.srcCode.getLine();
comments(data);
Expression expr = super.expression(data);
comments(data);
if (!data.srcCode.forwardIfCurrent(':'))
throw new TemplateException(data.srcCode, "case body must start with [:]");
Body body = new BodyBase(data.factory);
switchBlock(data, body);
swit.addCase(expr, body);
return true;
}
use of lucee.transformer.bytecode.BodyBase in project Lucee by lucee.
the class AbstrCFMLScriptTransformer method elseStatement.
/**
* Liest ein else Statement ein.
* <br />
* EBNF:<br />
* <code>block;</code>
* @return else Statement
* @throws TemplateException
*/
private final boolean elseStatement(ExprData data, Condition cont) throws TemplateException {
if (!data.srcCode.forwardIfCurrent("else", '{') && !data.srcCode.forwardIfCurrent("else ") && !data.srcCode.forwardIfCurrent("else", '/'))
return false;
// start (
data.srcCode.previous();
// ex block
Body body = new BodyBase(data.factory);
Pair p = cont.setElse(body, data.srcCode.getPosition(), null);
statement(data, body, CTX_ELSE);
p.end = data.srcCode.getPosition();
return true;
}
use of lucee.transformer.bytecode.BodyBase in project Lucee by lucee.
the class AbstrCFMLScriptTransformer method doStatement.
/**
* Liest ein do Statement ein.
* <br />
* EBNF:<br />
* <code>block spaces "while" spaces "(" spaces condition spaces ")";</code>
* @return do Statement
* @throws TemplateException
*/
private final DoWhile doStatement(ExprData data) throws TemplateException {
int pos = data.srcCode.getPos();
// id
String id = variableDec(data, false);
if (id == null) {
data.srcCode.setPos(pos);
return null;
}
if (id.equalsIgnoreCase("do")) {
id = null;
if (!data.srcCode.isCurrent('{') && !data.srcCode.isCurrent(' ') && !data.srcCode.isCurrent('/')) {
data.srcCode.setPos(pos);
return null;
}
} else {
data.srcCode.removeSpace();
if (!data.srcCode.forwardIfCurrent(':')) {
data.srcCode.setPos(pos);
return null;
}
data.srcCode.removeSpace();
if (!data.srcCode.forwardIfCurrent("do", '{') && !data.srcCode.forwardIfCurrent("do ") && !data.srcCode.forwardIfCurrent("do", '/')) {
data.srcCode.setPos(pos);
return null;
}
data.srcCode.previous();
}
// if(!data.srcCode.forwardIfCurrent("do",'{') && !data.srcCode.forwardIfCurrent("do ") && !data.srcCode.forwardIfCurrent("do",'/'))
// return null;
Position line = data.srcCode.getPosition();
Body body = new BodyBase(data.factory);
// data.srcCode.previous();
statement(data, body, CTX_DO_WHILE);
comments(data);
if (!data.srcCode.forwardIfCurrent("while", '('))
throw new TemplateException(data.srcCode, "do statement must have a while at the end");
DoWhile doWhile = new DoWhile(condition(data), body, line, data.srcCode.getPosition(), id);
if (!data.srcCode.forwardIfCurrent(')'))
throw new TemplateException(data.srcCode, "do statement must end with a [)]");
return doWhile;
}
Aggregations