diff --git a/media/src/DataTables.js b/media/src/DataTables.js
index 0810bcda..f5de7dd7 100644
--- a/media/src/DataTables.js
+++ b/media/src/DataTables.js
@@ -21,7 +21,7 @@
  */
 
 /*jslint evil: true, undef: true, browser: true */
-/*globals $,require,jQuery,define,_fnExternApiFunc,_fnInitialise,_fnInitComplete,_fnLanguageCompat,_fnAddColumn,_fnColumnOptions,_fnAddData,_fnCreateTr,_fnGatherData,_fnBuildHead,_fnDrawHead,_fnDraw,_fnReDraw,_fnAjaxUpdate,_fnAjaxParameters,_fnAjaxUpdateDraw,_fnAddOptionsHtml,_fnFeatureHtmlTable,_fnScrollDraw,_fnAdjustColumnSizing,_fnFeatureHtmlFilter,_fnFilterComplete,_fnFilterCustom,_fnFilterColumn,_fnFilter,_fnBuildSearchArray,_fnBuildSearchRow,_fnFilterCreateSearch,_fnDataToSearch,_fnSort,_fnSortAttachListener,_fnSortingClasses,_fnFeatureHtmlPaginate,_fnPageChange,_fnFeatureHtmlInfo,_fnUpdateInfo,_fnFeatureHtmlLength,_fnFeatureHtmlProcessing,_fnProcessingDisplay,_fnVisibleToColumnIndex,_fnColumnIndexToVisible,_fnNodeToDataIndex,_fnVisbleColumns,_fnCalculateEnd,_fnConvertToWidth,_fnCalculateColumnWidths,_fnScrollingWidthAdjust,_fnGetWidestNode,_fnGetMaxLenString,_fnStringToCss,_fnDetectType,_fnSettingsFromNode,_fnGetDataMaster,_fnGetTrNodes,_fnGetTdNodes,_fnEscapeRegex,_fnDeleteIndex,_fnColumnOrdering,_fnLog,_fnClearTable,_fnSaveState,_fnLoadState,_fnDetectHeader,_fnGetUniqueThs,_fnScrollBarWidth,_fnApplyToChildren,_fnMap,_fnGetRowData,_fnGetCellData,_fnSetCellData,_fnGetObjectDataFn,_fnSetObjectDataFn,_fnApplyColumnDefs,_fnBindAction,_fnCallbackReg,_fnCallbackFire,_fnNodeToColumnIndex,_fnInfoMacros,_fnBrowserDetect,_fnGetColumns,_fnHungarianMap,_fnCamelToHungarian,_fnBuildAjax,_fnAjaxDataSrc*/
+/*globals $,require,jQuery,define,_fnExternApiFunc,_fnInitialise,_fnInitComplete,_fnLanguageCompat,_fnAddColumn,_fnColumnOptions,_fnAddData,_fnCreateTr,_fnGatherData,_fnBuildHead,_fnDrawHead,_fnDraw,_fnReDraw,_fnAjaxUpdate,_fnAjaxParameters,_fnAjaxUpdateDraw,_fnAddOptionsHtml,_fnFeatureHtmlTable,_fnScrollDraw,_fnAdjustColumnSizing,_fnFeatureHtmlFilter,_fnFilterComplete,_fnFilterCustom,_fnFilterColumn,_fnFilter,_fnBuildSearchArray,_fnBuildSearchRow,_fnFilterCreateSearch,_fnDataToSearch,_fnSort,_fnSortAttachListener,_fnSortingClasses,_fnFeatureHtmlPaginate,_fnPageChange,_fnFeatureHtmlInfo,_fnUpdateInfo,_fnFeatureHtmlLength,_fnFeatureHtmlProcessing,_fnProcessingDisplay,_fnVisibleToColumnIndex,_fnColumnIndexToVisible,_fnNodeToDataIndex,_fnVisbleColumns,_fnConvertToWidth,_fnCalculateColumnWidths,_fnScrollingWidthAdjust,_fnGetWidestNode,_fnGetMaxLenString,_fnStringToCss,_fnDetectType,_fnSettingsFromNode,_fnGetDataMaster,_fnGetTrNodes,_fnGetTdNodes,_fnEscapeRegex,_fnDeleteIndex,_fnColumnOrdering,_fnLog,_fnClearTable,_fnSaveState,_fnLoadState,_fnDetectHeader,_fnGetUniqueThs,_fnScrollBarWidth,_fnApplyToChildren,_fnMap,_fnGetRowData,_fnGetCellData,_fnSetCellData,_fnGetObjectDataFn,_fnSetObjectDataFn,_fnApplyColumnDefs,_fnBindAction,_fnCallbackReg,_fnCallbackFire,_fnNodeToColumnIndex,_fnInfoMacros,_fnBrowserDetect,_fnGetColumns,_fnHungarianMap,_fnCamelToHungarian,_fnBuildAjax,_fnAjaxDataSrc*/
 
 (/** @lends <global> */function( window, document, undefined ) {
 
diff --git a/media/src/api/api.internal.js b/media/src/api/api.internal.js
index cea9ba27..5201063d 100644
--- a/media/src/api/api.internal.js
+++ b/media/src/api/api.internal.js
@@ -72,7 +72,6 @@ this.oApi = {
 	"_fnColumnIndexToVisible": _fnColumnIndexToVisible,
 	"_fnNodeToDataIndex": _fnNodeToDataIndex,
 	"_fnVisbleColumns": _fnVisbleColumns,
-	"_fnCalculateEnd": _fnCalculateEnd,
 	"_fnConvertToWidth": _fnConvertToWidth,
 	"_fnCalculateColumnWidths": _fnCalculateColumnWidths,
 	"_fnScrollingWidthAdjust": _fnScrollingWidthAdjust,
diff --git a/media/src/api/api.methods.js b/media/src/api/api.methods.js
index a0dd8bde..1609edb5 100644
--- a/media/src/api/api.methods.js
+++ b/media/src/api/api.methods.js
@@ -454,7 +454,6 @@ this.fnDeleteRow = function( mTarget, fnCallBack, bRedraw )
 	
 	if ( bRedraw === undefined || bRedraw )
 	{
-		_fnCalculateEnd( oSettings );
 		_fnDraw( oSettings );
 	}
 	
@@ -626,7 +625,6 @@ this.fnDraw = function( bComplete )
 		// also re-sort and re-filter. Do we need this kind of draw at all
 		// in the new API - I can't see why you'd want to do a draw which
 		// doesn't take into account the latest data.
-		_fnCalculateEnd( oSettings );
 		_fnDraw( oSettings );
 	}
 	else
@@ -726,7 +724,6 @@ this.fnFilter = function( sInput, iColumn, bRegex, bSmart, bShowGlobal, bCaseIns
 
 	// tmp hack during transition to new API
 	oSettings._iDisplayStart = 0;
-	_fnCalculateEnd( oSettings );
 	_fnDraw( oSettings );
 };
 
@@ -1006,8 +1003,7 @@ this.fnPageChange = function ( mAction, bRedraw )
 {
 	var oSettings = _fnSettingsFromNode( this[DataTable.ext.iApiIndex] );
 	_fnPageChange( oSettings, mAction );
-	_fnCalculateEnd( oSettings );
-	
+
 	if ( bRedraw === undefined || bRedraw )
 	{
 		_fnDraw( oSettings );
diff --git a/media/src/api/api.page.js b/media/src/api/api.page.js
index 1076b14e..d7a3cafa 100644
--- a/media/src/api/api.page.js
+++ b/media/src/api/api.page.js
@@ -32,14 +32,13 @@ _Api.register( 'page()', function ( action ) {
 	// else, have an action to take on all tables
 	return this.tables( function ( settings ) {
 		_fnPageChange( settings, action );
-		_fnCalculateEnd( settings );
 	} );
 } );
 
 
 /**
  * Paging information for the first table in the current context.
- * 
+ *
  * If you require paging information for another table, use the `table()` method
  * with a suitable selector.
  *
@@ -103,7 +102,6 @@ _Api.register( 'page.len()', function ( len ) {
 	// else, set the page length
 	return this.tables( function ( settings ) {
 		_fnLengthChange( settings, len );
-		_fnCalculateEnd( settings );
 	} );
 } );
 
diff --git a/media/src/core/core.data.js b/media/src/core/core.data.js
index c1a9c56b..e0eaf086 100644
--- a/media/src/core/core.data.js
+++ b/media/src/core/core.data.js
@@ -494,7 +494,6 @@ function _fnClearTable( oSettings )
 	oSettings.aoData.splice( 0, oSettings.aoData.length );
 	oSettings.aiDisplayMaster.splice( 0, oSettings.aiDisplayMaster.length );
 	oSettings.aiDisplay.splice( 0, oSettings.aiDisplay.length );
-	_fnCalculateEnd( oSettings );
 }
 
 
diff --git a/media/src/core/core.draw.js b/media/src/core/core.draw.js
index d038a97f..38fcc824 100644
--- a/media/src/core/core.draw.js
+++ b/media/src/core/core.draw.js
@@ -320,25 +320,27 @@ function _fnDraw( oSettings )
 	var i, iLen, n;
 	var anRows = [];
 	var iRowCount = 0;
-	var iStripes = oSettings.asStripeClasses.length;
+	var asStripeClasses = oSettings.asStripeClasses;
+	var iStripes = asStripeClasses.length;
 	var iOpenRows = oSettings.aoOpenRows.length;
+	var oLang = oSettings.oLanguage;
+	var iInitDisplayStart = oSettings.iInitDisplayStart;
+	var iDisplayStart = oSettings._iDisplayStart;
+	var bServerSide = oSettings.oFeatures.bServerSide;
 	
 	oSettings.bDrawing = true;
+
 	
 	/* Check and see if we have an initial draw position from state saving */
-	if ( oSettings.iInitDisplayStart !== undefined && oSettings.iInitDisplayStart != -1 )
+	if ( iInitDisplayStart !== undefined && iInitDisplayStart !== -1 )
 	{
-		if ( oSettings.oFeatures.bServerSide )
-		{
-			oSettings._iDisplayStart = oSettings.iInitDisplayStart;
-		}
-		else
-		{
-			oSettings._iDisplayStart = (oSettings.iInitDisplayStart >= oSettings.fnRecordsDisplay()) ?
-				0 : oSettings.iInitDisplayStart;
-		}
+		iDisplayStart = bServerSide ?
+			iInitDisplayStart :
+			iInitDisplayStart >= oSettings.fnRecordsDisplay() ?
+				0 :
+				iInitDisplayStart;
+
 		oSettings.iInitDisplayStart = -1;
-		_fnCalculateEnd( oSettings );
 	}
 	
 	/* Server-side processing draw intercept */
@@ -347,7 +349,7 @@ function _fnDraw( oSettings )
 		oSettings.bDeferLoading = false;
 		oSettings.iDraw++;
 	}
-	else if ( !oSettings.oFeatures.bServerSide )
+	else if ( !bServerSide )
 	{
 		oSettings.iDraw++;
 	}
@@ -358,10 +360,10 @@ function _fnDraw( oSettings )
 	
 	if ( oSettings.aiDisplay.length !== 0 )
 	{
-		var iStart = oSettings._iDisplayStart;
-		var iEnd = oSettings._iDisplayEnd;
+		var iStart = iDisplayStart;
+		var iEnd = oSettings.fnDisplayEnd();
 		
-		if ( oSettings.oFeatures.bServerSide )
+		if ( bServerSide )
 		{
 			iStart = 0;
 			iEnd = oSettings.aoData.length;
@@ -380,7 +382,7 @@ function _fnDraw( oSettings )
 			/* Remove the old striping classes and then add the new one */
 			if ( iStripes !== 0 )
 			{
-				var sStripe = oSettings.asStripeClasses[ iRowCount % iStripes ];
+				var sStripe = asStripeClasses[ iRowCount % iStripes ];
 				if ( aoData._sRowStripe != sStripe )
 				{
 					$(nRow).removeClass( aoData._sRowStripe ).addClass( sStripe );
@@ -409,16 +411,8 @@ function _fnDraw( oSettings )
 	else
 	{
 		/* Table is empty - create a row with an empty message in it */
-		anRows[ 0 ] = document.createElement( 'tr' );
-		
-		if ( oSettings.asStripeClasses[0] )
-		{
-			anRows[ 0 ].className = oSettings.asStripeClasses[0];
-		}
-
-		var oLang = oSettings.oLanguage;
 		var sZero = oLang.sZeroRecords;
-		if ( oSettings.iDraw == 1 && oSettings.sAjaxSource !== null && !oSettings.oFeatures.bServerSide )
+		if ( oSettings.iDraw == 1 && oSettings.sAjaxSource !== null && !bServerSide )
 		{
 			sZero = oLang.sLoadingRecords;
 		}
@@ -427,21 +421,20 @@ function _fnDraw( oSettings )
 			sZero = oLang.sEmptyTable;
 		}
 
-		var nTd = document.createElement( 'td' );
-		nTd.setAttribute( 'valign', "top" );
-		nTd.colSpan = _fnVisbleColumns( oSettings );
-		nTd.className = oSettings.oClasses.sRowEmpty;
-		nTd.innerHTML = _fnInfoMacros( oSettings, sZero );
-		
-		anRows[ iRowCount ].appendChild( nTd );
+		anRows[ 0 ] = $( '<tr/>', { 'class': iStripes ? asStripeClasses[0] : '' } )
+			.append( $('<td>'+sZero+'</td>', {
+				'valign':  'top',
+				'colspan': _fnVisbleColumns( oSettings ),
+				'class':   oSettings.oClasses.sRowEmpty
+			} ) )[0];
 	}
 	
 	/* Header and footer callbacks */
 	_fnCallbackFire( oSettings, 'aoHeaderCallback', 'header', [ $(oSettings.nTHead).children('tr')[0],
-		_fnGetDataMaster( oSettings ), oSettings._iDisplayStart, oSettings.fnDisplayEnd(), oSettings.aiDisplay ] );
+		_fnGetDataMaster( oSettings ), iDisplayStart, oSettings.fnDisplayEnd(), oSettings.aiDisplay ] );
 	
 	_fnCallbackFire( oSettings, 'aoFooterCallback', 'footer', [ $(oSettings.nTFoot).children('tr')[0],
-		_fnGetDataMaster( oSettings ), oSettings._iDisplayStart, oSettings.fnDisplayEnd(), oSettings.aiDisplay ] );
+		_fnGetDataMaster( oSettings ), iDisplayStart, oSettings.fnDisplayEnd(), oSettings.aiDisplay ] );
 	
 	/*
 	 * Need to remove any old row from the display - note we can't just empty the tbody using
@@ -523,7 +516,6 @@ function _fnReDraw( settings, holdPosition )
 		settings._iDisplayStart = 0;
 	}
 
-	_fnCalculateEnd( settings );
 	_fnDraw( settings );
 }
 
diff --git a/media/src/core/core.filter.js b/media/src/core/core.filter.js
index ccfad17d..ef28e6e2 100644
--- a/media/src/core/core.filter.js
+++ b/media/src/core/core.filter.js
@@ -54,7 +54,6 @@ function _fnFeatureHtmlFilter ( oSettings )
 
 			// Need to redraw, without resorting
 			oSettings._iDisplayStart = 0;
-			_fnCalculateEnd( oSettings );
 			_fnDraw( oSettings );
 		}
 	} );
diff --git a/media/src/core/core.length.js b/media/src/core/core.length.js
index e53876aa..288cddad 100644
--- a/media/src/core/core.length.js
+++ b/media/src/core/core.length.js
@@ -9,7 +9,6 @@ function _fnLengthChange ( settings, val )
 
 	/* Redraw the table */
 	settings._iDisplayLength = len;
-	_fnCalculateEnd( settings );
 
 	end = settings.fnDisplayEnd();
 	
@@ -86,21 +85,3 @@ function _fnFeatureHtmlLength ( settings )
 	return div[0];
 }
 
-
-/**
- * Recalculate the end point based on the start point
- *  @param {object} settings dataTables settings object
- *  @memberof DataTable#oApi
- */
-function _fnCalculateEnd( settings )
-{
-	var
-		len     = settings._iDisplayLength,
-		calc    = settings._iDisplayStart + len,
-		records = settings.aiDisplay.length;
-
-	settings._iDisplayEnd = ! settings.oFeatures.bPaginate || calc>records || len===-1 ?
-		records :
-		calc;
-}
-
diff --git a/media/src/core/core.page.js b/media/src/core/core.page.js
index e1f0899a..bc63e51b 100644
--- a/media/src/core/core.page.js
+++ b/media/src/core/core.page.js
@@ -22,7 +22,6 @@ function _fnFeatureHtmlPaginate ( settings )
 		type   = settings.sPaginationType,
 		plugin = DataTable.ext.oPagination[ type ],
 		redraw = function( settings ) {
-			_fnCalculateEnd( settings );
 			_fnDraw( settings );
 		},
 		node = $('<div/>').addClass( settings.oClasses.sPaging + type )[0];
diff --git a/media/src/core/core.scrolling.js b/media/src/core/core.scrolling.js
index bcdfe166..68ab76c7 100644
--- a/media/src/core/core.scrolling.js
+++ b/media/src/core/core.scrolling.js
@@ -155,7 +155,6 @@ function _fnFeatureHtmlTable ( oSettings )
 					if ( oSettings.fnDisplayEnd() < oSettings.fnRecordsDisplay() )
 					{
 						_fnPageChange( oSettings, 'next' );
-						_fnCalculateEnd( oSettings );
 						_fnDraw( oSettings );
 					}
 				}
diff --git a/media/src/core/core.state.js b/media/src/core/core.state.js
index f97b01bc..661ffa9c 100644
--- a/media/src/core/core.state.js
+++ b/media/src/core/core.state.js
@@ -16,8 +16,7 @@ function _fnSaveState ( oSettings )
 	var i, iLen, bInfinite=oSettings.oScroll.bInfinite;
 	var oState = {
 		"iCreate":      new Date().getTime(),
-		"iStart":       (bInfinite ? 0 : oSettings._iDisplayStart),
-		"iEnd":         (bInfinite ? oSettings._iDisplayLength : oSettings._iDisplayEnd),
+		"iStart":       bInfinite ? 0 : oSettings._iDisplayStart,
 		"iLength":      oSettings._iDisplayLength,
 		"aaSorting":    $.extend( true, [], oSettings.aaSorting ),
 		"oSearch":      $.extend( true, {}, oSettings.oPreviousSearch ),
@@ -75,7 +74,6 @@ function _fnLoadState ( oSettings, oInit )
 	/* Restore key features */
 	oSettings._iDisplayStart    = oData.iStart;
 	oSettings.iInitDisplayStart = oData.iStart;
-	oSettings._iDisplayEnd      = oData.iEnd;
 	oSettings._iDisplayLength   = oData.iLength;
 	oSettings.aaSorting         = oData.aaSorting.slice();
 	oSettings.saved_aaSorting   = oData.aaSorting.slice();
diff --git a/media/src/model/model.settings.js b/media/src/model/model.settings.js
index cc4e34f4..c2d11c3b 100644
--- a/media/src/model/model.settings.js
+++ b/media/src/model/model.settings.js
@@ -705,15 +705,6 @@ DataTable.models.oSettings = {
 	 *  @default 0
 	 */
 	"_iDisplayStart": 0,
-
-	/**
-	 * Paging end point - aiDisplay index. Use fnDisplayEnd rather than
-	 * this property to get the end point
-	 *  @type int
-	 *  @default 10
-	 *  @private
-	 */
-	"_iDisplayEnd": 10,
 	
 	/**
 	 * Server-side processing - number of records in the result set
@@ -804,11 +795,9 @@ DataTable.models.oSettings = {
 	 */
 	"fnRecordsTotal": function ()
 	{
-		if ( this.oFeatures.bServerSide ) {
-			return parseInt(this._iRecordsTotal, 10);
-		} else {
-			return this.aiDisplayMaster.length;
-		}
+		return this.oFeatures.bServerSide ?
+			parseInt(this._iRecordsTotal, 10) :
+			this.aiDisplayMaster.length;
 	},
 	
 	/**
@@ -817,29 +806,34 @@ DataTable.models.oSettings = {
 	 */
 	"fnRecordsDisplay": function ()
 	{
-		if ( this.oFeatures.bServerSide ) {
-			return parseInt(this._iRecordsDisplay, 10);
-		} else {
-			return this.aiDisplay.length;
-		}
+		return this.oFeatures.bServerSide ?
+			parseInt(this._iRecordsDisplay, 10) :
+			this.aiDisplay.length;
 	},
 	
 	/**
-	 * Set the display end point - aiDisplay index
+	 * Get the display end point - aiDisplay index
 	 *  @type function
-	 *  @todo Should do away with _iDisplayEnd and calculate it on-the-fly here
 	 */
 	"fnDisplayEnd": function ()
 	{
-		if ( this.oFeatures.bServerSide ) {
-			if ( this.oFeatures.bPaginate === false || this._iDisplayLength == -1 ) {
-				return this._iDisplayStart+this.aiDisplay.length;
-			} else {
-				return Math.min( this._iDisplayStart+this._iDisplayLength,
-					this._iRecordsDisplay );
-			}
-		} else {
-			return this._iDisplayEnd;
+		var
+			len      = this._iDisplayLength,
+			start    = this._iDisplayStart,
+			calc     = start + len,
+			records  = this.aiDisplay.length,
+			features = this.oFeatures,
+			paginate = features.bPaginate;
+
+		if ( features.bServerSide ) {
+			return paginate === false || len === -1 ?
+				start + records :
+				Math.min( start+len, this._iRecordsDisplay );
+		}
+		else {
+			return ! paginate || calc>records || len===-1 ?
+				records :
+				calc;
 		}
 	},