vala r1947 - in trunk: . gobject vala



Author: juergbi
Date: Sat Nov  1 14:03:41 2008
New Revision: 1947
URL: http://svn.gnome.org/viewvc/vala?rev=1947&view=rev

Log:
2008-11-01  JÃrg Billeter  <j bitron ch>

	* vala/Makefile.am:
	* vala/valacfgbuilder.vala:
	* vala/valacodevisitor.vala:
	* vala/valamethod.vala:
	* vala/valanullchecker.vala:
	* vala/valaparser.vala:
	* vala/valascanner.vala:
	* vala/valasemanticanalyzer.vala:
	* vala/valasymbolresolver.vala:
	* vala/valatokentype.vala:
	* vala/valayieldstatement.vala:
	* gobject/valaccodegenerator.vala:

	Parse yield statements


Added:
   trunk/vala/valayieldstatement.vala
Modified:
   trunk/ChangeLog
   trunk/gobject/valaccodegenerator.vala
   trunk/vala/Makefile.am
   trunk/vala/valacfgbuilder.vala
   trunk/vala/valacodevisitor.vala
   trunk/vala/valamethod.vala
   trunk/vala/valanullchecker.vala
   trunk/vala/valaparser.vala
   trunk/vala/valascanner.vala
   trunk/vala/valasemanticanalyzer.vala
   trunk/vala/valasymbolresolver.vala
   trunk/vala/valatokentype.vala

Modified: trunk/gobject/valaccodegenerator.vala
==============================================================================
--- trunk/gobject/valaccodegenerator.vala	(original)
+++ trunk/gobject/valaccodegenerator.vala	Sat Nov  1 14:03:41 2008
@@ -2680,6 +2680,57 @@
 		}
 	}
 
+	public override void visit_yield_statement (YieldStatement stmt) {
+		if (stmt.yield_expression == null) {
+			stmt.ccodenode = new CCodeFragment ();
+			return;
+		}
+
+		stmt.accept_children (this);
+
+		if (stmt.yield_expression.error) {
+			stmt.error = true;
+			return;
+		}
+
+		stmt.ccodenode = new CCodeExpressionStatement ((CCodeExpression) stmt.yield_expression.ccodenode);
+
+		if (stmt.tree_can_fail && stmt.yield_expression.tree_can_fail) {
+			// simple case, no node breakdown necessary
+
+			var cfrag = new CCodeFragment ();
+
+			cfrag.append (stmt.ccodenode);
+
+			add_simple_check (stmt.yield_expression, cfrag);
+
+			stmt.ccodenode = cfrag;
+		}
+
+		/* free temporary objects */
+
+		if (((Gee.List<LocalVariable>) temp_vars).size == 0) {
+			/* nothing to do without temporary variables */
+			return;
+		}
+		
+		var cfrag = new CCodeFragment ();
+		append_temp_decl (cfrag, temp_vars);
+		
+		cfrag.append (stmt.ccodenode);
+		
+		foreach (LocalVariable local in temp_ref_vars) {
+			var ma = new MemberAccess.simple (local.name);
+			ma.symbol_reference = local;
+			cfrag.append (new CCodeExpressionStatement (get_unref_expression (new CCodeIdentifier (local.name), local.variable_type, ma)));
+		}
+		
+		stmt.ccodenode = cfrag;
+		
+		temp_vars.clear ();
+		temp_ref_vars.clear ();
+	}
+
 	public override void visit_throw_statement (ThrowStatement stmt) {
 		stmt.accept_children (this);
 

Modified: trunk/vala/Makefile.am
==============================================================================
--- trunk/vala/Makefile.am	(original)
+++ trunk/vala/Makefile.am	Sat Nov  1 14:03:41 2008
@@ -144,6 +144,7 @@
 	valavaluetype.vala \
 	valavoidtype.vala \
 	valawhilestatement.vala \
+	valayieldstatement.vala \
 	$(NULL)
 
 libvalacore_la_SOURCES = \

Modified: trunk/vala/valacfgbuilder.vala
==============================================================================
--- trunk/vala/valacfgbuilder.vala	(original)
+++ trunk/vala/valacfgbuilder.vala	Sat Nov  1 14:03:41 2008
@@ -579,6 +579,14 @@
 		}
 	}
 
+	public override void visit_yield_statement (YieldStatement stmt) {
+		if (unreachable (stmt)) {
+			return;
+		}
+
+		stmt.accept_children (this);
+	}
+
 	public override void visit_throw_statement (ThrowStatement stmt) {
 		if (unreachable (stmt)) {
 			return;

Modified: trunk/vala/valacodevisitor.vala
==============================================================================
--- trunk/vala/valacodevisitor.vala	(original)
+++ trunk/vala/valacodevisitor.vala	Sat Nov  1 14:03:41 2008
@@ -356,6 +356,14 @@
 	}
 
 	/**
+	 * Visit operation called for yield statement.
+	 *
+	 * @param y a yield statement
+	 */
+	public virtual void visit_yield_statement (YieldStatement y) {
+	}
+
+	/**
 	 * Visit operation called for throw statements.
 	 *
 	 * @param stmt a throw statement

Modified: trunk/vala/valamethod.vala
==============================================================================
--- trunk/vala/valamethod.vala	(original)
+++ trunk/vala/valamethod.vala	Sat Nov  1 14:03:41 2008
@@ -200,6 +200,8 @@
 	 */
 	public bool has_construct_function { get; set; default = true; }
 
+	public bool coroutine { get; set; }
+
 	private Gee.List<FormalParameter> parameters = new ArrayList<FormalParameter> ();
 	private string cname;
 	private string _vfunc_name;

Modified: trunk/vala/valanullchecker.vala
==============================================================================
--- trunk/vala/valanullchecker.vala	(original)
+++ trunk/vala/valanullchecker.vala	Sat Nov  1 14:03:41 2008
@@ -176,6 +176,10 @@
 		}
 	}
 
+	public override void visit_yield_statement (YieldStatement stmt) {
+		stmt.accept_children (this);
+	}
+
 	public override void visit_throw_statement (ThrowStatement stmt) {
 		stmt.accept_children (this);
 

Modified: trunk/vala/valaparser.vala
==============================================================================
--- trunk/vala/valaparser.vala	(original)
+++ trunk/vala/valaparser.vala	Sat Nov  1 14:03:41 2008
@@ -232,6 +232,8 @@
 		case TokenType.VOLATILE:
 		case TokenType.WEAK:
 		case TokenType.WHILE:
+		case TokenType.YIELD:
+		case TokenType.YIELDS:
 			next ();
 			return;
 		}
@@ -1205,6 +1207,9 @@
 				case TokenType.RETURN:
 					stmt = parse_return_statement ();
 					break;
+				case TokenType.YIELD:
+					stmt = parse_yield_statement ();
+					break;
 				case TokenType.THROW:
 					stmt = parse_throw_statement ();
 					break;
@@ -1325,6 +1330,7 @@
 		case TokenType.BREAK:     return parse_break_statement ();
 		case TokenType.CONTINUE:  return parse_continue_statement ();
 		case TokenType.RETURN:    return parse_return_statement ();
+		case TokenType.YIELD:     return parse_yield_statement ();
 		case TokenType.THROW:     return parse_throw_statement ();
 		case TokenType.TRY:       return parse_try_statement ();
 		case TokenType.LOCK:      return parse_lock_statement ();
@@ -1584,6 +1590,17 @@
 		return new ReturnStatement (expr, get_src_com (begin));
 	}
 
+	Statement parse_yield_statement () throws ParseError {
+		var begin = get_location ();
+		expect (TokenType.YIELD);
+		Expression expr = null;
+		if (current () != TokenType.SEMICOLON) {
+			expr = parse_expression ();
+		}
+		expect (TokenType.SEMICOLON);
+		return new YieldStatement (expr, get_src (begin));
+	}
+
 	Statement parse_throw_statement () throws ParseError {
 		var begin = get_location ();
 		expect (TokenType.THROW);
@@ -1841,6 +1858,7 @@
 			case TokenType.TRY:
 			case TokenType.VAR:
 			case TokenType.WHILE:
+			case TokenType.YIELD:
 				return RecoveryState.STATEMENT_BEGIN;
 			default:
 				next ();
@@ -2157,6 +2175,9 @@
 			} while (accept (TokenType.COMMA));
 		}
 		expect (TokenType.CLOSE_PARENS);
+		if (accept (TokenType.YIELDS)) {
+			method.coroutine = true;
+		}
 		if (accept (TokenType.THROWS)) {
 			do {
 				method.add_error_type (parse_type ());
@@ -2730,6 +2751,9 @@
 			} while (accept (TokenType.COMMA));
 		}
 		expect (TokenType.CLOSE_PARENS);
+		if (accept (TokenType.YIELDS)) {
+			method.coroutine = true;
+		}
 		if (accept (TokenType.THROWS)) {
 			do {
 				method.add_error_type (parse_type ());

Modified: trunk/vala/valascanner.vala
==============================================================================
--- trunk/vala/valascanner.vala	(original)
+++ trunk/vala/valascanner.vala	Sat Nov  1 14:03:41 2008
@@ -175,6 +175,9 @@
 			case 'w':
 				if (matches (begin, "while")) return TokenType.WHILE;
 				break;
+			case 'y':
+				if (matches (begin, "yield")) return TokenType.YIELD;
+				break;
 			}
 			break;
 		case 6:
@@ -231,6 +234,9 @@
 					break;
 				}
 				break;
+			case 'y':
+				if (matches (begin, "yields")) return TokenType.YIELDS;
+				break;
 			}
 			break;
 		case 7:

Modified: trunk/vala/valasemanticanalyzer.vala
==============================================================================
--- trunk/vala/valasemanticanalyzer.vala	(original)
+++ trunk/vala/valasemanticanalyzer.vala	Sat Nov  1 14:03:41 2008
@@ -1164,6 +1164,10 @@
 		stmt.add_error_types (stmt.return_expression.get_error_types ());
 	}
 
+	public override void visit_yield_statement (YieldStatement stmt) {
+		stmt.check (this);
+	}
+
 	public override void visit_throw_statement (ThrowStatement stmt) {
 		stmt.error_expression.target_type = new ErrorType (null, null, stmt.source_reference);
 		stmt.error_expression.target_type.value_owned = true;
@@ -2094,7 +2098,8 @@
 		if (ret_type is VoidType) {
 			// void return type
 			if (!(expr.parent_node is ExpressionStatement)
-			    && !(expr.parent_node is ForStatement)) {
+			    && !(expr.parent_node is ForStatement)
+			    && !(expr.parent_node is YieldStatement)) {
 				// A void method invocation can be in the initializer or
 				// iterator of a for statement
 				expr.error = true;

Modified: trunk/vala/valasymbolresolver.vala
==============================================================================
--- trunk/vala/valasymbolresolver.vala	(original)
+++ trunk/vala/valasymbolresolver.vala	Sat Nov  1 14:03:41 2008
@@ -354,6 +354,10 @@
 		stmt.accept_children (this);
 	}
 
+	public override void visit_yield_statement (YieldStatement stmt) {
+		stmt.accept_children (this);
+	}
+
 	public override void visit_throw_statement (ThrowStatement stmt) {
 		stmt.accept_children (this);
 	}

Modified: trunk/vala/valatokentype.vala
==============================================================================
--- trunk/vala/valatokentype.vala	(original)
+++ trunk/vala/valatokentype.vala	Sat Nov  1 14:03:41 2008
@@ -139,7 +139,9 @@
 	VOID,
 	VOLATILE,
 	WEAK,
-	WHILE;
+	WHILE,
+	YIELD,
+	YIELDS;
 
 	public weak string to_string () {
 		switch (this) {
@@ -255,6 +257,8 @@
 		case VOLATILE: return "`volatile'";
 		case WEAK: return "`weak'";
 		case WHILE: return "`while'";
+		case YIELD: return "`yield'";
+		case YIELDS: return "`yields'";
 		default: return "unknown token";
 		}
 	}

Added: trunk/vala/valayieldstatement.vala
==============================================================================
--- (empty file)
+++ trunk/vala/valayieldstatement.vala	Sat Nov  1 14:03:41 2008
@@ -0,0 +1,81 @@
+/* valayieldstatement.vala
+ *
+ * Copyright (C) 2008  JÃrg Billeter
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301  USA
+ *
+ * Author:
+ * 	JÃrg Billeter <j bitron ch>
+ */
+
+/**
+ * Represents a yield statement in the source code.
+ */
+public class Vala.YieldStatement : CodeNode, Statement {
+	/**
+	 * The expression to yield or the method call to yield to.
+	 */
+	public Expression? yield_expression {
+		get { return _yield_expression; }
+		set {
+			_yield_expression = value;
+			if (_yield_expression != null) {
+				_yield_expression.parent_node = this;
+			}
+		}
+	}
+
+	private Expression _yield_expression;
+
+	/**
+	 * Creates a new yield statement.
+	 *
+	 * @param yield_expression the yield expression
+	 * @param source_reference reference to source code
+	 * @return                 newly created yield statement
+	 */
+	public YieldStatement (Expression? yield_expression, SourceReference? source_reference = null) {
+		this.yield_expression = yield_expression;
+		this.source_reference = source_reference;
+	}
+
+	public override void accept (CodeVisitor visitor) {
+		visitor.visit_yield_statement (this);
+	}
+
+	public override void accept_children (CodeVisitor visitor) {
+		if (yield_expression != null) {
+			yield_expression.accept (visitor);
+
+			visitor.visit_end_full_expression (yield_expression);
+		}
+	}
+
+	public override void replace_expression (Expression old_node, Expression new_node) {
+		if (yield_expression == old_node) {
+			yield_expression = new_node;
+		}
+	}
+
+	public override bool check (SemanticAnalyzer analyzer) {
+		if (yield_expression != null) {
+			yield_expression.accept (analyzer);
+			error = yield_expression.error;
+		}
+
+		return !error;
+	}
+}
+



[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]