Index: java/engine/org/apache/derby/impl/sql/compile/sqlgrammar.jj
===================================================================
--- java/engine/org/apache/derby/impl/sql/compile/sqlgrammar.jj	(revision 152676)
+++ java/engine/org/apache/derby/impl/sql/compile/sqlgrammar.jj	(working copy)
@@ -6585,7 +6585,7 @@
 	orderCol = sortKey() /* [ collateClause() ] */ [ orderingSpecification(orderCol) ]
 	{
 		orderCols.addOrderByColumn(orderCol);
-	}
+	} 
 }
 
 OrderByColumn
@@ -6598,6 +6598,7 @@
 	String correlationName = null;
 	String schemaName = null;
 	int columnPosition;
+	ValueNode columnExpression;
 } 
 {
 	firstName = identifier(DB2Limit.DB2_MAX_IDENTIFIER_LENGTH128, false)
@@ -6652,6 +6653,15 @@
 								ReuseFactory.getInteger(columnPosition),
 								getContextManager());
 	}
+|
+	columnExpression = additiveExpression(null,0,true)
+	{
+		return (OrderByColumn) nodeFactory.getNode(
+								C_NodeTypes.ORDER_BY_COLUMN,
+								columnExpression,
+								null,
+								getContextManager());
+	}
 }
 
 
Index: java/engine/org/apache/derby/impl/sql/compile/OrderByColumn.java
===================================================================
--- java/engine/org/apache/derby/impl/sql/compile/OrderByColumn.java	(revision 152676)
+++ java/engine/org/apache/derby/impl/sql/compile/OrderByColumn.java	(working copy)
@@ -46,7 +46,9 @@
 	private	String			correlationName;
 	private String	schemaName;
 	private boolean			ascending = true;
+	private ValueNode expression;
 
+
 	/**
 	 * Initializer.
 	 *
@@ -63,13 +65,25 @@
 		this.schemaName = (String) schemaName;
 	}
 
-	/**
+    	/**
 	 * Initializer.
 	 *
+	 * @param expression            Expression of this column
+	 * @param dummy                 Dummy to distinguish from init with one parameter
+	 */
+	public void init(Object expression,
+			 Object dummy)
+	{
+		this.expression = (ValueNode)expression;
+	}
+	
+	/**
+	 *I nitializer.
+	 *
 	 * @param columnPosition	The position of the column being referenced
 	 */
 	public void init(Object columnPosition) {
-		this.columnPosition = ((Integer) columnPosition).intValue();
+	    this.columnPosition = ((Integer) columnPosition).intValue();
 	}
 
 	/**
@@ -236,8 +250,20 @@
 				throw StandardException.newException(SQLState.LANG_ORDER_BY_COLUMN_NOT_FOUND, errString);
 			}
 			columnPosition = resultCol.getColumnPosition();
-		}
-		else {
+		}else if(expression != null){
+		    
+			int i = 0;
+			for(i = 0;
+			    i < targetCols.size();
+			    i  ++){
+				ResultColumn col = targetCols.getOrderByColumn(i);
+				if(col != null && 
+				   col.getExpression() == expression){
+					break;
+				}
+			}
+			columnPosition = i;
+		}else {
 			resultCol = targetCols.getOrderByColumn(columnPosition);
 			if (resultCol == null) {
 				throw StandardException.newException(SQLState.LANG_COLUMN_OUT_OF_RANGE, String.valueOf(columnPosition));
@@ -295,6 +321,15 @@
 				targetCols.addResultColumn(resultCol);
 				targetCols.incOrderBySelect();
 			}
+
+		}else if(expression != null){
+			ResultColumnList	targetCols = target.getResultColumns();
+			resultCol = (ResultColumn) getNodeFactory().getNode(C_NodeTypes.RESULT_COLUMN,
+									    null,
+									    expression,
+									    getContextManager());
+			targetCols.addResultColumn(resultCol);
+			targetCols.incOrderBySelect();
 		}
 	}
 
