diff --git a/t3lib/class.t3lib_befunc.php b/t3lib/class.t3lib_befunc.php
index 0c12b2b..2319e24 100644
--- t3lib/class.t3lib_befunc.php
+++ t3lib/class.t3lib_befunc.php
@@ -1755,6 +1755,21 @@ final class t3lib_BEfunc {
 		$uploaddir = (is_null($uploaddir)) ? $TCA[$table]['columns'][$field]['config']['uploadfolder'] : $uploaddir;
 		$uploaddir = preg_replace('#/$#','', $uploaddir);
 
+		/**
+		 * FAL stuff
+		 */
+		if (t3lib_extMgm::isLoaded('fal')) {
+			if (isset($GLOBALS['TYPO3_CONF_VARS']['SC_OPTIONS']['fal']['tableAndFieldMapping'][$table])) {
+				$repo = t3lib_div::makeInstance('t3lib_file_Repository');
+				foreach ($GLOBALS['TYPO3_CONF_VARS']['SC_OPTIONS']['fal']['tableAndFieldMapping'][$table] as $overlayField => $fieldName) {
+					$references = $repo->getFilesFromRelation($fieldName, $table, intval($row['uid']));
+					$references = t3lib_file_Helper::createCsvListOfFilepaths($references);
+					$row[$fieldName] = $references;
+					$row[$overlayField] = $references;
+				};			
+			}
+			$uploaddir = '';
+		}
 			// Set thumbs-script:
 		if (!$GLOBALS['TYPO3_CONF_VARS']['GFX']['thumbnails']) {
 			$thumbScript = 'gfx/notfound_thumb.gif';
diff --git a/t3lib/class.t3lib_div.php b/t3lib/class.t3lib_div.php
index 87c2a3d..f998d23 100644
--- t3lib/class.t3lib_div.php
+++ t3lib/class.t3lib_div.php
@@ -3212,7 +3212,13 @@ final class t3lib_div {
 				if ($OK)	{ $OK = rmdir($path); }
 
 			} else {	// If $dirname is a file, simply remove it
-				$OK = unlink($path);
+				if (t3lib_extMgm::isLoaded('fal')) {
+					$fileRepository = t3lib_div::makeInstance('t3lib_file_Repository');
+					$fileRecord = $fileRepository->getFileByPath($path);
+					$OK = $fileRecord->delete();
+				} else {
+					$OK = unlink($path);
+				}
 			}
 
 			clearstatcache();
diff --git a/t3lib/class.t3lib_extfilefunc.php b/t3lib/class.t3lib_extfilefunc.php
index 838d256..942bc63 100644
--- t3lib/class.t3lib_extfilefunc.php
+++ t3lib/class.t3lib_extfilefunc.php
@@ -424,9 +424,11 @@ class t3lib_extFileFunctions extends t3lib_basicFileFunctions	{
 			return TRUE;
 		} elseif ($this->useRecycler != 2) {	// if $this->useRecycler==2 then we cannot delete for real!!
 			if (@is_file($theFile))	{	// If we are deleting a file...
+				$fileRepository = t3lib_div::makeInstance('t3lib_file_Repository');
+				$file = $fileRepository->getFileByPath($theFile);
 				if ($this->actionPerms['deleteFile'])	{
 					if ($this->checkPathAgainstMounts($theFile))	{
-						if (@unlink($theFile))	{
+						if ($file->delete())	{
 							$this->writelog(4,0,1,'File "%s" deleted',Array($theFile));
 							return TRUE;
 						} else $this->writelog(4,1,110,'Could not delete file "%s". Write-permission problem?', Array($theFile));
@@ -803,7 +805,7 @@ class t3lib_extFileFunctions extends t3lib_basicFileFunctions	{
 			$theFile = $_FILES['upload_'.$id]['tmp_name'];				// filename of the uploaded file
 			$theFileSize = $_FILES['upload_'.$id]['size'];				// filesize of the uploaded file
 			$theName = $this->cleanFileName(stripslashes($_FILES['upload_'.$id]['name']), (isset($cmds['charset']) ? $cmds['charset'] : ''));	// The original filename
-			if (is_uploaded_file($theFile) && $theName)	{	// Check the file
+			if (is_file($theFile) && $theName)	{	// Check the file
 				if ($this->actionPerms['uploadFile'])	{
 					if ($theFileSize<($this->maxUploadFileSize*1024))	{
 						$fI = t3lib_div::split_fileref($theName);
diff --git a/t3lib/class.t3lib_extmgm.php b/t3lib/class.t3lib_extmgm.php
index 53f40e6..13478a7 100644
--- t3lib/class.t3lib_extmgm.php
+++ t3lib/class.t3lib_extmgm.php
@@ -1060,6 +1060,44 @@ final class t3lib_extMgm {
 			$TCA[$content_table]['columns'][$content_field]['config']['allowed'].=','.$table;
 		}
 	}
+	
+	/**
+	 * Get field TCA configuration (only "config" part) for File Abstraction Layer
+	 * fields.
+	 *
+	 * @param	string		$fieldName Field name
+	 * @param	string		$allowedFileTypes Comma list of allowed file extensions (e.g. "jpg,gif,png"). By default, it's allowing TYPO3_CONF_VARS[GFX][imagefile_ext].
+	 * @param	array		$overrideArray Array to override or add configuration options
+	 * @return	array		Field TCA configuration "config" section for the field
+	 */
+	public static function getFileFieldTCAConfig($fieldName, $allowedFileTypes = '', array $overrideArray = array()) {
+		if(!$allowedFileTypes) {
+			$allowedFileTypes = $GLOBALS['TYPO3_CONF_VARS']['GFX']['imagefile_ext'];
+		}
+		$TCAFieldConfig = t3lib_div::array_merge_recursive_overrule(array(
+			'type' => 'group',	
+			'internal_type' => 'db',	
+			'allowed' => 'sys_files',
+			'internal_subtype' => 'file_record',
+			'internal_subtype_allowed' => $allowedFileTypes,
+			'prepend_tname' => 1,
+			'show_thumbs' => 0,
+			'size' => 5,	
+			'minitems' => 0,
+			#'maxitems' => 100,
+			'MM_opposite_field' => 'file_usage',
+			'MM' => 'sys_files_usage_mm',
+			'MM_match_fields' => array('ident' => $fieldName),
+			'wizards' => array(
+				'falrendering' => array(
+					'type' => 'userFunc',
+					'userFunc' => 'tx_fal_tceforms_wizard->tx_fal_fieldwizard',
+				),
+			),
+		), $overrideArray);
+		
+		return $TCAFieldConfig;
+	}
 
 	/**
 	 * Add PlugIn to Static Template #43
diff --git a/t3lib/class.t3lib_page.php b/t3lib/class.t3lib_page.php
index 71e7cfa..8adf063 100644
--- t3lib/class.t3lib_page.php
+++ t3lib/class.t3lib_page.php
@@ -324,7 +324,6 @@ class t3lib_pageSelect {
 	 * @return	array		Page row which is overlayed with language_overlay record (or the overlay record alone)
 	 */
 	function getPageOverlay($pageInput,$lUid=-1)	{
-
 			// Initialize:
 		if ($lUid<0)	$lUid = $this->sys_language_uid;
 		$row = NULL;
@@ -375,6 +374,7 @@ class t3lib_pageSelect {
 
 				if (is_array($row))	{
 					$row['_PAGES_OVERLAY'] = TRUE;
+					$row['_PAGES_OVERLAY_UID'] = $row['uid'];
 
 						// Unset vital fields that are NOT allowed to be overlaid:
 					unset($row['uid']);
@@ -654,6 +654,10 @@ class t3lib_pageSelect {
 		}
 
 			// Initialize:
+		// add FAL media field to the rootline
+		if (t3lib_extMgm::isLoaded('fal')) {
+			$GLOBALS['TYPO3_CONF_VARS']['FE']['addRootLineFields'] .= ', media_rel';
+		}
 		$selFields = t3lib_div::uniqueList('pid,uid,t3ver_oid,t3ver_wsid,t3ver_state,t3ver_swapmode,title,alias,nav_title,media,layout,hidden,starttime,endtime,fe_group,extendToSubpages,doktype,TSconfig,storage_pid,is_siteroot,mount_pid,mount_pid_ol,fe_login_mode,'.$GLOBALS['TYPO3_CONF_VARS']['FE']['addRootLineFields']);
 		$this->error_getRootLine = '';
 		$this->error_getRootLine_failPid = 0;
diff --git a/t3lib/class.t3lib_tceforms.php b/t3lib/class.t3lib_tceforms.php
index 3ed52b5..d056c29 100644
--- t3lib/class.t3lib_tceforms.php
+++ t3lib/class.t3lib_tceforms.php
@@ -2361,7 +2361,7 @@ class t3lib_TCEforms	{
 					'noBrowser' => $noList || (isset($config['disable_controls']) && t3lib_div::inList($config['disable_controls'], 'browser')),
 					'noList' => $noList,
 				);
-				$item.= $this->dbFileIcons($PA['itemFormElName'],'db',implode(',',$tempFT),$itemArray,'',$params,$PA['onFocus'],$table,$field,$row['uid']);
+				$item.= $this->dbFileIcons($PA['itemFormElName'], 'db', implode(',',$tempFT), $itemArray,'',$params,$PA['onFocus'],$table,$field,$row['uid'], $config['internal_subtype'], $config['internal_subtype_allowed']);
 
 			break;
 		}
@@ -3612,9 +3612,18 @@ class t3lib_TCEforms	{
 	 * @param	string		$uid:	(optional) uid of table record processing for
 	 * @return	string		The form fields for the selection.
 	 */
-	function dbFileIcons($fName,$mode,$allowed,$itemArray,$selector='',$params=array(),$onFocus='',$table='',$field='',$uid='')	{
-
-
+	function dbFileIcons($fName,$mode,$allowed,$itemArray,$selector='',$params=array(),$onFocus='',$table='',$field='',$uid='', $subtype='', $subtype_allowed='')	{
+		
+		if($mode === 'db' && $subtype === 'file_record') {
+			$elementBrowserMode = 'file';
+			$elementBrowserAllowed = $subtype_allowed;
+			$isFalMode = 1;
+		} else {
+			$elementBrowserMode = $mode;
+			$elementBrowserAllowed = $allowed;
+			$isFalMode = 0;
+		}
+		
 		$disabled = '';
 		if($this->renderReadonly || $params['readOnly'])  {
 			$disabled = ' disabled="disabled"';
@@ -3691,11 +3700,24 @@ class t3lib_TCEforms	{
 						$rOnClickInline = 'inline.revertUnique(\''.$objectPrefix.'\',null,\''.$uid.'\');';
 					}
 				}
-				$aOnClick='setFormValueOpenBrowser(\''.$mode.'\',\''.($fName.'|||'.$allowed.'|'.$aOnClickInline).'\'); return false;';
+				$aOnClick='setFormValueOpenBrowser(\''.$elementBrowserMode.'\',\''.($fName.'|||'.$elementBrowserAllowed.'|'.$aOnClickInline).'||||'.($isFalMode?1:0).'\'); return false;';
 				$icons['R'][]='<a href="#" onclick="'.htmlspecialchars($aOnClick).'">'.
-						t3lib_iconWorks::getSpriteIcon('actions-insert-record', array('title' => htmlspecialchars($this->getLL('l_browse_' . ($mode == 'db' ? 'db' : 'file'))))) .
+						t3lib_iconWorks::getSpriteIcon('actions-insert-record', array('title' => htmlspecialchars($this->getLL('l_browse_' . $elementBrowserMode)))) .
+				'</a>';
+			}
+			if($elementBrowserMode === 'file' && $isFalMode === 1){
+				$pageRenderer = $GLOBALS['SOBE']->doc->getPageRenderer(); 
+				$pageRenderer->addExtOnReadyCode("
+					Ext.get(Ext.getDom('".$fName."_uploadButton')).on('click',function(e){
+						e.stopEvent();
+						top.TYPO3.FileUploadWindow.showFalTceFormsUploadDialog('" . $fName . "','" . $elementBrowserAllowed . "');
+					});
+				");
+				$icons['R'][]= '<a id="'.$fName.'_uploadButton" title="'.$GLOBALS['LANG']->makeEntities($GLOBALS['LANG']->sL('LLL:EXT:lang/locallang_core.xml:cm.upload',1)).'">' .
+					t3lib_iconWorks::getSpriteIcon('actions-edit-upload') .
 				'</a>';
 			}
+			
 			if (!$params['dontShowMoveIcons'])	{
 				if ($sSize>=5)	{
 					$icons['L'][]='<a href="#" onclick="setFormValueManipulate(\''.$fName.'\',\'Top\'); return false;">'.
@@ -3894,7 +3916,7 @@ class t3lib_TCEforms	{
 					}
 
 						//
-					switch((string)$wConf['type'])	{
+					switch((string)$wConf['type'])	{						
 						case 'userFunc':
 						case 'script':
 						case 'popup':
diff --git a/t3lib/core_autoload.php b/t3lib/core_autoload.php
index 142086c..83f2cb0 100644
--- t3lib/core_autoload.php
+++ t3lib/core_autoload.php
@@ -1,9 +1,9 @@
 <?php
 // DO NOT CHANGE THIS FILE! It is automatically generated by extdeveval::buildAutoloadRegistry.
-// This file was generated on 2009-11-25 23:05
+// This file was generated on 2010-11-12 13:23
 
 
-$t3libClasses = array(
+return array(
 	'gzip_encode' => PATH_t3lib . 'class.gzip_encode.php',
 	't3lib_admin' => PATH_t3lib . 'class.t3lib_admin.php',
 	't3lib_ajax' => PATH_t3lib . 'class.t3lib_ajax.php',
@@ -20,7 +20,6 @@ $t3libClasses = array(
 	't3lib_compressor' => PATH_t3lib . 'class.t3lib_compressor.php',
 	't3lib_cs' => PATH_t3lib . 'class.t3lib_cs.php',
 	't3lib_db' => PATH_t3lib . 'class.t3lib_db.php',
-	't3lib_db_preparedstatement' => PATH_t3lib . 'db/class.t3lib_db_preparedstatement.php',
 	't3lib_diff' => PATH_t3lib . 'class.t3lib_diff.php',
 	't3lib_div' => PATH_t3lib . 'class.t3lib_div.php',
 	't3lib_exception' => PATH_t3lib . 'class.t3lib_exception.php',
@@ -50,6 +49,7 @@ $t3libClasses = array(
 	't3lib_pagetree' => PATH_t3lib . 'class.t3lib_pagetree.php',
 	't3lib_parsehtml' => PATH_t3lib . 'class.t3lib_parsehtml.php',
 	't3lib_parsehtml_proc' => PATH_t3lib . 'class.t3lib_parsehtml_proc.php',
+	't3lib_pdohelper' => PATH_t3lib . 'class.t3lib_pdohelper.php',
 	't3lib_positionmap' => PATH_t3lib . 'class.t3lib_positionmap.php',
 	't3lib_querygenerator' => PATH_t3lib . 'class.t3lib_querygenerator.php',
 	't3lib_readmail' => PATH_t3lib . 'class.t3lib_readmail.php',
@@ -59,6 +59,7 @@ $t3libClasses = array(
 	't3lib_rteapi' => PATH_t3lib . 'class.t3lib_rteapi.php',
 	't3lib_scbase' => PATH_t3lib . 'class.t3lib_scbase.php',
 	't3lib_softrefproc' => PATH_t3lib . 'class.t3lib_softrefproc.php',
+	't3lib_spritemanager' => PATH_t3lib . 'class.t3lib_spritemanager.php',
 	't3lib_sqlengine' => PATH_t3lib . 'class.t3lib_sqlengine.php',
 	't3lib_sqlengine_resultobj' => PATH_t3lib . 'class.t3lib_sqlengine.php',
 	't3lib_sqlparser' => PATH_t3lib . 'class.t3lib_sqlparser.php',
@@ -109,6 +110,7 @@ $t3libClasses = array(
 	't3lib_cache_frontend_stringfrontend' => PATH_t3lib . 'cache/frontend/class.t3lib_cache_frontend_stringfrontend.php',
 	't3lib_cache_frontend_variablefrontend' => PATH_t3lib . 'cache/frontend/class.t3lib_cache_frontend_variablefrontend.php',
 	't3lib_cache_frontend_frontend' => PATH_t3lib . 'cache/frontend/interfaces/interface.t3lib_cache_frontend_frontend.php',
+	't3lib_db_preparedstatement' => PATH_t3lib . 'db/class.t3lib_db_preparedstatement.php',
 	't3lib_error_abstractexceptionhandler' => PATH_t3lib . 'error/class.t3lib_error_abstractexceptionhandler.php',
 	't3lib_error_debugexceptionhandler' => PATH_t3lib . 'error/class.t3lib_error_debugexceptionhandler.php',
 	't3lib_error_errorhandler' => PATH_t3lib . 'error/class.t3lib_error_errorhandler.php',
@@ -116,25 +118,44 @@ $t3libClasses = array(
 	't3lib_error_productionexceptionhandler' => PATH_t3lib . 'error/class.t3lib_error_productionexceptionhandler.php',
 	't3lib_error_errorhandlerinterface' => PATH_t3lib . 'error/interface.t3lib_error_errorhandlerinterface.php',
 	't3lib_error_exceptionhandlerinterface' => PATH_t3lib . 'error/interface.t3lib_error_exceptionhandlerinterface.php',
+	't3lib_extjs_extdirectapi' => PATH_t3lib . 'extjs/class.t3lib_extjs_extdirectapi.php',
+	't3lib_extjs_extdirectdebug' => PATH_t3lib . 'extjs/class.t3lib_extjs_extdirectdebug.php',
+	't3lib_extjs_extdirectrouter' => PATH_t3lib . 'extjs/class.t3lib_extjs_extdirectrouter.php',
+	't3lib_file_collection' => PATH_t3lib . 'file/class.t3lib_file_Collection.php',
+	't3lib_file_file' => PATH_t3lib . 'file/class.t3lib_file_File.php',
+	't3lib_file_frontendaccess' => PATH_t3lib . 'file/class.t3lib_file_frontendaccess.php',
+	't3lib_file_indexer' => PATH_t3lib . 'file/class.t3lib_file_Indexer.php',
+	't3lib_file_helper' => PATH_t3lib . 'file/class.t3lib_file_Helper.php',
+	't3lib_file_mount' => PATH_t3lib . 'file/class.t3lib_file_Mount.php',
+	't3lib_file_repository' => PATH_t3lib . 'file/class.t3lib_file_Repository.php',
+	't3lib_file_backend_fileadminbackend' => PATH_t3lib . 'file/backend/class.t3lib_file_backend_FileadminBackend.php',
+	't3lib_file_backend_interface' => PATH_t3lib . 'file/backend/interface.t3lib_file_backend_Interface.php',
+	't3lib_file_storage_filesystemstorage' => PATH_t3lib . 'file/storage/class.t3lib_file_storage_filesystemstorage.php',
+	't3lib_file_storage_interface' => PATH_t3lib . 'file/storage/interface.t3lib_file_storage_interface.php',
+	't3lib_file_streams_streamwrapperinterface' => PATH_t3lib . 'file/streams/interface.t3lib_file_streams_streamwrapperinterface.php',
+	't3lib_file_streams_streamwrapperadapter' => PATH_t3lib . 'file/streams/class.t3lib_file_streams_streamwrapperadapter.php',
+	't3lib_file_exception_filenotfound' => PATH_t3lib . 'file/exception/class.t3lib_file_exception_filenotfound.php',
 	't3lib_browselinkshook' => PATH_t3lib . 'interfaces/interface.t3lib_browselinkshook.php',
 	't3lib_extfilefunctions_processdatahook' => PATH_t3lib . 'interfaces/interface.t3lib_extfilefunctions_processdatahook.php',
 	't3lib_localrecordlistgettablehook' => PATH_t3lib . 'interfaces/interface.t3lib_localrecordlistgettablehook.php',
 	't3lib_pageselect_getpagehook' => PATH_t3lib . 'interfaces/interface.t3lib_pageselect_getpagehook.php',
-	't3lib_pageselect_getrecordoverlayhook' => PATH_t3lib . 'interfaces/interface.t3lib_pageselect_getrecordoverlayhook.php',
 	't3lib_pageselect_getpageoverlayhook' => PATH_t3lib . 'interfaces/interface.t3lib_pageselect_getpageoverlayhook.php',
+	't3lib_pageselect_getrecordoverlayhook' => PATH_t3lib . 'interfaces/interface.t3lib_pageselect_getrecordoverlayhook.php',
 	't3lib_singleton' => PATH_t3lib . 'interfaces/interface.t3lib_singleton.php',
+	't3lib_spritemanager_spriteicongenerator' => PATH_t3lib . 'interfaces/interface.t3lib_spritemanager_spriteicongenerator.php',
 	't3lib_tceformsinlinehook' => PATH_t3lib . 'interfaces/interface.t3lib_tceformsinlinehook.php',
 	't3lib_tcemain_checkmodifyaccesslisthook' => PATH_t3lib . 'interfaces/interface.t3lib_tcemain_checkmodifyaccesslisthook.php',
 	't3lib_tcemain_processuploadhook' => PATH_t3lib . 'interfaces/interface.t3lib_tcemain_processuploadhook.php',
-	't3lib_mail_message' => PATH_t3lib . 'mail/class.t3lib_mail_message.php',
-	't3lib_mail_mailer' => PATH_t3lib . 'mail/class.t3lib_mail_mailer.php',
 	't3lib_matchcondition_abstract' => PATH_t3lib . 'matchcondition/class.t3lib_matchcondition_abstract.php',
 	't3lib_matchcondition_backend' => PATH_t3lib . 'matchcondition/class.t3lib_matchcondition_backend.php',
 	't3lib_matchcondition_frontend' => PATH_t3lib . 'matchcondition/class.t3lib_matchcondition_frontend.php',
-	't3lib_pdohelper' => PATH_t3lib . 'class.t3lib_pdohelper.php',
+	't3lib_message_abstractmessage' => PATH_t3lib . 'message/class.t3lib_message_abstractmessage.php',
+	't3lib_spritemanager_simplehandler' => PATH_t3lib . 'spritemanager/class.t3lib_spritemanager_simplehandler.php',
+	't3lib_spritemanager_spritegenerator' => PATH_t3lib . 'spritemanager/class.t3lib_spritemanager_spritegenerator.php',
 	't3lib_tceforms_suggest' => PATH_t3lib . 'tceforms/class.t3lib_tceforms_suggest.php',
 	't3lib_tceforms_suggest_defaultreceiver' => PATH_t3lib . 'tceforms/class.t3lib_tceforms_suggest_defaultreceiver.php',
 	't3lib_utility_client' => PATH_t3lib . 'utility/class.t3lib_utility_client.php',
+	't3lib_utility_debug' => PATH_t3lib . 'utility/class.t3lib_utility_debug.php',
 	't3lib_utility_http' => PATH_t3lib . 'utility/class.t3lib_utility_http.php',
 	't3lib_utility_mail' => PATH_t3lib . 'utility/class.t3lib_utility_mail.php',
 	't3lib_utility_phpoptions' => PATH_t3lib . 'utility/class.t3lib_utility_phpoptions.php',
@@ -172,9 +193,42 @@ $t3libClasses = array(
 	't3lib_tree_tca_databasetreedataprovider' => PATH_t3lib . 'tree/tca/class.t3lib_tree_tca_databasetreedataprovider.php',
 	't3lib_tree_tca_dataproviderfactory' => PATH_t3lib . 'tree/tca/class.t3lib_tree_tca_dataproviderfactory.php',
 	't3lib_tree_tca_tcatree' => PATH_t3lib . 'tree/tca/class.t3lib_tree_tca_tcatree.php',
+	'tslib_adminpanel' => PATH_tslib . 'class.tslib_adminpanel.php',
+	'tslib_cobj' => PATH_tslib . 'class.tslib_content.php',
+	'tslib_frameset' => PATH_tslib . 'class.tslib_content.php',
+	'tslib_tableoffset' => PATH_tslib . 'class.tslib_content.php',
+	'tslib_controltable' => PATH_tslib . 'class.tslib_content.php',
+	'tslib_eidtools' => PATH_tslib . 'class.tslib_eidtools.php',
+	'tslib_extdirecteid' => PATH_tslib . 'class.tslib_extdirecteid.php',
+	'tslib_fe' => PATH_tslib . 'class.tslib_fe.php',
+	'tslib_fecompression' => PATH_tslib . 'class.tslib_fecompression.php',
+	'tslib_fetce' => PATH_tslib . 'class.tslib_fetce.php',
+	'tslib_feuserauth' => PATH_tslib . 'class.tslib_feuserauth.php',
+	'tslib_gifbuilder' => PATH_tslib . 'class.tslib_gifbuilder.php',
+	'tslib_mediawizardcoreprovider' => PATH_tslib . 'class.tslib_mediawizardcoreprovider.php',
+	'tslib_mediawizardmanager' => PATH_tslib . 'class.tslib_mediawizardmanager.php',
+	'tslib_menu' => PATH_tslib . 'class.tslib_menu.php',
+	'tslib_tmenu' => PATH_tslib . 'class.tslib_menu.php',
+	'tslib_gmenu' => PATH_tslib . 'class.tslib_menu.php',
+	'tslib_imgmenu' => PATH_tslib . 'class.tslib_menu.php',
+	'tslib_jsmenu' => PATH_tslib . 'class.tslib_menu.php',
+	'tspagegen' => PATH_tslib . 'class.tslib_pagegen.php',
+	'fe_loaddbgroup' => PATH_tslib . 'class.tslib_pagegen.php',
+	'tslib_pibase' => PATH_tslib . 'class.tslib_pibase.php',
+	'tslib_search' => PATH_tslib . 'class.tslib_search.php',
+	'sc_tslib_showpic' => PATH_tslib . 'showpic.php',
+	'tx_cms_mediaitems' => PATH_tslib . 'hooks/class.tx_cms_mediaitems.php',
+	'tx_cms_treelistcacheupdate' => PATH_tslib . 'hooks/class.tx_cms_treelistcacheupdate.php',
+	'tslib_content_cobjgetsinglehook' => PATH_tslib . 'interfaces/interface.tslib_content_cobjgetsinglehook.php',
+	'tslib_content_getdatahook' => PATH_tslib . 'interfaces/interface.tslib_content_getdatahook.php',
+	'tslib_cobj_getimgresourcehook' => PATH_tslib . 'interfaces/interface.tslib_content_getimgresourcehook.php',
+	'tslib_content_postinithook' => PATH_tslib . 'interfaces/interface.tslib_content_postinithook.php',
+	'tslib_content_stdwraphook' => PATH_tslib . 'interfaces/interface.tslib_content_stdwraphook.php',
+	'tslib_mediawizardprovider' => PATH_tslib . 'interfaces/interface.tslib_mediawizardprovider.php',
+	'tslib_menu_filtermenupageshook' => PATH_tslib . 'interfaces/interface.tslib_menu_filterMenuPagesHook.php',
+	'user_various' => PATH_tslib . 'media/scripts/example_callfunction.php',
+	'tslib_gmenu_foldout' => PATH_tslib . 'media/scripts/gmenu_foldout.php',
+	'tslib_gmenu_layers' => PATH_tslib . 'media/scripts/gmenu_layers.php',
+	'tslib_tmenu_layers' => PATH_tslib . 'media/scripts/tmenu_layers.php',
 );
-
-$tslibClasses = require(PATH_typo3 . 'sysext/cms/ext_autoload.php');
-
-return array_merge($t3libClasses, $tslibClasses);
 ?>
diff --git a/t3lib/file/class.t3lib_file_Collection.php b/t3lib/file/class.t3lib_file_Collection.php
new file mode 100644
index 0000000..168a7a5
--- /dev/null
+++ t3lib/file/class.t3lib_file_Collection.php
@@ -0,0 +1,39 @@
+<?php
+/***************************************************************
+*  Copyright notice
+*
+*  (c) 1999-2010 Kasper Skårhøj (kasperYYYY@typo3.com)
+*  All rights reserved
+*
+*  This script is part of the TYPO3 project. The TYPO3 project is
+*  free software; you can redistribute it and/or modify
+*  it under the terms of the GNU General Public License as published by
+*  the Free Software Foundation; either version 2 of the License, or
+*  (at your option) any later version.
+*
+*  The GNU General Public License can be found at
+*  http://www.gnu.org/copyleft/gpl.html.
+*  A copy is found in the textfile GPL.txt and important notices to the license
+*  from the author is found in LICENSE.txt distributed with these scripts.
+*
+*
+*  This script 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 General Public License for more details.
+*
+*  This copyright notice MUST APPEAR in all copies of the script!
+***************************************************************/
+
+
+/**
+ * Probably safe to ignore at this time
+ */
+class t3lib_file_Collection {
+	private $backend;
+	
+	public function  __construct(t3lib_file_backend_Interface $backend) {
+		$this->backend = $backend;
+	}
+}
+?>
diff --git a/t3lib/file/class.t3lib_file_File.php b/t3lib/file/class.t3lib_file_File.php
new file mode 100644
index 0000000..bd03cb3
--- /dev/null
+++ t3lib/file/class.t3lib_file_File.php
@@ -0,0 +1,155 @@
+<?php
+/***************************************************************
+*  Copyright notice
+*
+*  (c) 1999-2010 Kasper Skårhøj (kasperYYYY@typo3.com)
+*  All rights reserved
+*
+*  This script is part of the TYPO3 project. The TYPO3 project is
+*  free software; you can redistribute it and/or modify
+*  it under the terms of the GNU General Public License as published by
+*  the Free Software Foundation; either version 2 of the License, or
+*  (at your option) any later version.
+*
+*  The GNU General Public License can be found at
+*  http://www.gnu.org/copyleft/gpl.html.
+*  A copy is found in the textfile GPL.txt and important notices to the license
+*  from the author is found in LICENSE.txt distributed with these scripts.
+*
+*
+*  This script 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 General Public License for more details.
+*
+*  This copyright notice MUST APPEAR in all copies of the script!
+***************************************************************/
+
+class t3lib_file_File {
+	/**
+	 * The uid of this file's record
+	 *
+	 * @var integer
+	 */
+	protected $uid;
+
+	/**
+	 * The name of this file. This is only the filename without the path
+	 *
+	 * @var string
+	 */
+	protected $filename;
+
+	/**
+	 * The mount this file is located in
+	 *
+	 * @var t3lib_file_Mount
+	 */
+	protected $mount;
+
+	/**
+	 * The path to this file (inside the file mount)
+	 *
+	 * @var string
+	 */
+	protected $path = NULL;
+
+	/**
+	 * The file size
+	 *
+	 * @var integer
+	 */
+	protected $size;
+
+	/**
+	 * The SHA-1 hash sum of the file
+	 *
+	 * @var string
+	 */
+	protected $hash;
+
+	public function  __construct(t3lib_file_Mount $mount, array $fileData) {
+		$this->mount = $mount;
+		$this->uid = $fileData['uid'];
+		$this->name = $fileData['file_name'];
+		$this->path = $fileData['file_path'];
+		$this->size = $fileData['file_size'];
+		$this->hash = $fileData['file_hash'];
+	}
+
+	public function getThumbnail() {
+		/** @todo: Implement */
+	}
+
+	public function getThumbnailUrl() {
+		/** @todo: Implement */
+	}
+
+	/**
+	 * @param string $table
+	 * @param integer $uid
+	 * @param string $field
+	 * @param string $flexFormStructurePath Optional.
+	 * @return void
+	 */
+	public function addRelation($table, $uid, $field, $flexFormStructurePath = NULL) {
+		/** @todo: Implement */
+	}
+
+	public function getRelatedRecords($table = '') {
+		/** @todo: Implement */
+	}
+
+	public function getUrl() {
+		return $this->mount->getUrlForPath($this->path);
+	}
+
+	public function writeFile($content) {
+		/** @todo: Implement */
+	}
+
+	public function getUid() {
+		return $this->uid;
+	}
+
+	public function getName() {
+		return $this->name;
+	}
+
+	public function getPath() {
+		return $this->path;
+	}
+
+	public function getSize() {
+		return $this->size;
+	}
+
+	public function getHash() {
+		return $this->hash;
+	}
+
+	public function replaceWithLocalFile($filePath) {
+	}
+
+	public function getFileCopyForLocalProcessing() {
+	}
+
+	public function copyInsideMount($newPath) {
+	}
+
+	public function copyToMount(t3lib_file_Mount $mount, $newPath) {
+	}
+
+	public function moveInsideMount($newPath) {
+	}
+
+	public function moveToMount(t3lib_file_Mount $mount, $newPath) {
+	}
+
+	public function getContents() {
+	}
+
+	public function getFileHandle($mode) {
+	}
+}
+?>
\ No newline at end of file
diff --git a/t3lib/file/class.t3lib_file_Helper.php b/t3lib/file/class.t3lib_file_Helper.php
new file mode 100644
index 0000000..e7c1d90
--- /dev/null
+++ t3lib/file/class.t3lib_file_Helper.php
@@ -0,0 +1,58 @@
+<?php
+
+class t3lib_file_Helper {
+	public static function getOrCreateFileObjectFromPath($fileNameAndPath) {
+		/** @var $fileRepository t3lib_file_Repository */
+		$fileRepository = t3lib_div::makeInstance('t3lib_file_Repository');
+		$relativePath = substr($fileNameAndPath, strlen(PATH_site));
+
+		try {
+			return $fileRepository->getFileByPath($relativePath);
+		} catch(t3lib_file_exception_FileNotFound $e) {
+
+			$mount = self::getMountFromFilePath($relativePath);
+			$fileUid = t3lib_file_Indexer::addFileToIndex($mount, $relativePath);
+
+			return $fileRepository->getFileById($fileUid);
+		}
+	}
+
+	/**
+	 * Creates a comma separated list of file paths from a list of file objects
+	 *
+	 * @param array $fileObjects The file objects to iterate over
+	 * @return string A comma separated list of paths to the files.
+	 * @static
+	 * @author Andreas Wolf <andreas.wolf@ikt-werk.de>
+	 *
+	 * TODO: check how this will work for remote files
+	 */
+	public static function createCsvListOfFilepaths(array $fileObjects) {
+		$csv = array();
+		foreach ($fileObjects as $file) {
+			$csv[] = $file->getPath() . $file->getName();
+		}
+
+		return implode(',', $csv);
+	}
+
+	/**
+	 * Extracts the mount from a FAL file path (<mount>/path/to/file/inside/mount)
+	 *
+	 * @param string $filePath The path to the file
+	 * @static
+	 * @return t3lib_file_Mount|boolean FALSE if the mount could not be resolved 
+	 */
+	public static function getMountFromFilePath($filePath) {
+		$pathParts = explode('/', $filePath, 2);
+		$mountAlias = array_shift($pathParts);
+		$mount = t3lib_file_Mount::getInstanceForAlias($mountAlias);
+
+		if (!is_object($mount)) {
+			return FALSE;
+		}
+		return $mount;
+	}
+}
+
+?>
\ No newline at end of file
diff --git a/t3lib/file/class.t3lib_file_Indexer.php b/t3lib/file/class.t3lib_file_Indexer.php
new file mode 100644
index 0000000..3d92177
--- /dev/null
+++ t3lib/file/class.t3lib_file_Indexer.php
@@ -0,0 +1,82 @@
+<?php
+/***************************************************************
+*  Copyright notice
+*
+*  (c) 1999-2010 Kasper Skårhøj (kasperYYYY@typo3.com)
+*  All rights reserved
+*
+*  This script is part of the TYPO3 project. The TYPO3 project is
+*  free software; you can redistribute it and/or modify
+*  it under the terms of the GNU General Public License as published by
+*  the Free Software Foundation; either version 2 of the License, or
+*  (at your option) any later version.
+*
+*  The GNU General Public License can be found at
+*  http://www.gnu.org/copyleft/gpl.html.
+*  A copy is found in the textfile GPL.txt and important notices to the license
+*  from the author is found in LICENSE.txt distributed with these scripts.
+*
+*
+*  This script 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 General Public License for more details.
+*
+*  This copyright notice MUST APPEAR in all copies of the script!
+***************************************************************/
+
+class t3lib_file_Indexer {
+
+	public function indexDirectory() {
+
+	}
+
+	/**
+	 * Add a file to the index. This only works for files that already reside in the virtual
+	 * file system we use; so you have to move the file to a mount manually.
+	 *
+	 * @param t3lib_file_Mount The mount the file resides in.
+	 * @param string Path to the file, relative to the mount root
+	 * @return t3lib_file_File The file record, if the file could be successfully indexed
+	 *
+	 * TODO check if file exists
+	 */
+	public static function addFileToIndex(t3lib_file_Mount $mount, $filePath) {
+		$fileName = basename($filePath);
+		$folder = dirname($filePath) . '/';
+		$backend = $mount->getStorageBackend();
+
+		$success = $GLOBALS['TYPO3_DB']->exec_INSERTquery('sys_files', array(
+			'file_name' => $fileName,
+			'file_path' => $folder,
+			'file_size' => $backend->getSize($filePath),
+			'file_mtime' => $backend->getModificationTime($filePath),
+			'file_hash' => $backend->getFileHash($filePath),
+			'mount' => $mount->getUid(),
+			'crdate' => $GLOBALS['EXEC_TIME'],
+			'tstamp' => $GLOBALS['EXEC_TIME']
+		));
+
+		/** @var $repo t3lib_file_Repository */
+		return $GLOBALS['TYPO3_DB']->sql_insert_id();
+		//$repo = t3lib_div::makeInstance('t3lib_file_Repository');
+		//return $repo->getFileById($GLOBALS['TYPO3_DB']->sql_insert_id());
+	}
+
+	public function updateFileIndex(t3lib_file_File $file) {
+		/** @todo: Implement */
+	}
+
+	/**
+	 * Delete a file from index
+	 *
+	 * @param		integer		UID of the file record to remove from index
+	 * @return		void
+	 */
+	public static function deleteFileFromIndex($file) {
+		$sucess = $GLOBALS['TYPO3_DB']->exec_UPDATEquery('sys_files', 'uid=' . $file,
+			array('deleted' => 1)
+		);
+	}
+}
+?>
diff --git a/t3lib/file/class.t3lib_file_Mount.php b/t3lib/file/class.t3lib_file_Mount.php
new file mode 100644
index 0000000..c71dd31
--- /dev/null
+++ t3lib/file/class.t3lib_file_Mount.php
@@ -0,0 +1,214 @@
+<?php
+/***************************************************************
+*  Copyright notice
+*
+*  (c) 1999-2010 Kasper Skårhøj (kasperYYYY@typo3.com)
+*  All rights reserved
+*
+*  This script is part of the TYPO3 project. The TYPO3 project is
+*  free software; you can redistribute it and/or modify
+*  it under the terms of the GNU General Public License as published by
+*  the Free Software Foundation; either version 2 of the License, or
+*  (at your option) any later version.
+*
+*  The GNU General Public License can be found at
+*  http://www.gnu.org/copyleft/gpl.html.
+*  A copy is found in the textfile GPL.txt and important notices to the license
+*  from the author is found in LICENSE.txt distributed with these scripts.
+*
+*
+*  This script 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 General Public License for more details.
+*
+*  This copyright notice MUST APPEAR in all copies of the script!
+***************************************************************/
+
+class t3lib_file_Mount {
+	/**
+	 * The backend this mount uses
+	 *
+	 * @var t3lib_file_storage_Interface
+	 */
+	protected $storageBackend;
+
+	/**
+	 * The base url for this file mount
+	 *
+	 * @var string
+	 */
+	protected $baseUrl;
+
+	protected $uid;
+
+	/**
+	 * @var array<t3lib_file_Mount>
+	 */
+	private static $instances = array();
+
+
+	public function __construct($mountInformation) {
+		$this->uid = $mountInformation['uid'];
+		$this->alias = $mountInformation['alias'];
+	}
+
+	public static function getInstanceForUid($mountUid) {
+		if (count(self::$instances) == 0) {
+			self::loadMountsFromDatabase();
+		}
+
+		if (self::$instances[$mountUid]) {
+			return self::$instances[$mountUid];
+		}
+
+		throw new RuntimeException("Mount with uid $mountUid was not found.");
+	}
+
+	/**
+	 * Returns an instance of a file mount by its alias
+	 *
+	 * @param string $alias
+	 * @return void
+	 * @static
+	 */
+	public static function getInstanceForAlias($alias) {
+		if (count(self::$instances) == 0) {
+			self::loadMountsFromDatabase();
+		}
+
+		foreach (self::$instances as $instance) {
+			if ($instance->getAlias() == $alias) {
+				return $instance;
+			}
+		}
+
+		throw new RuntimeException("FAL mount $alias was not found.");
+	}
+
+	/**
+	 * Loads all existing FAL mounts from the database and initializes them for later use.
+	 *
+	 * @return void
+	 * @static
+	 */
+	protected static function loadMountsFromDatabase() {
+		$mountRecord = array('alias' => 'fileadmin', 'uid' => 0, 'storage_backend' => 't3lib_file_storage_FileSystemStorage');
+		$storageConfiguration = array('relative' => TRUE, 'path' => 'fileadmin/');
+
+		self::$instances[0] = self::mountObjectFactory($mountRecord, $storageConfiguration); 
+
+		$mountRecords = $GLOBALS['TYPO3_DB']->exec_SELECTgetRows('*', 'sys_files_mounts');
+		foreach ($mountRecords as $mountRecord) {
+			$storageConfiguration = t3lib_div::xml2array($mountRecord['backend_configuration']);
+			$storageConfiguration = self::extractValuesFromFlexformArray($storageConfiguration['data']);
+
+			self::$instances[$mountRecord['uid']] = self::mountObjectFactory($mountRecord, $storageConfiguration);
+		}
+	}
+
+	/**
+	 * Factory method for mount objects.
+	 *
+	 * @param  $mountRecord
+	 * @param  $storageConfiguration
+	 *
+	 * @throws RuntimeException
+	 * @return void
+	 * @static
+	 */
+	protected static function mountObjectFactory($mountRecord, $storageConfiguration) {
+		$storageBackendClass = $mountRecord['storage_backend'];
+		if (!class_exists($storageBackendClass)) {
+			throw new RuntimeException("Class $storageBackendClass does not exist.");
+		}
+		$storageBackend = t3lib_div::makeInstance($storageBackendClass, $storageConfiguration);
+
+		$mountObject = new t3lib_file_Mount($mountRecord);
+		$mountObject->setStorageBackend($storageBackend);
+
+		return $mountObject;
+	}
+
+	/**
+	 * Helper function to ease unit testing. Ignore in normal operation.
+	 *
+	 * @param array $instances
+	 * @return void
+	 * @static
+	 */
+	public static function _setInstances(array $instances) {
+		self::$instances = $instances;
+	}
+
+
+	/**
+	 * Helper method for extracting values from a single-language FlexForm. This method does not care about double
+	 * field names, so use with caution (in FlexForms, the same field name may be used in different sheets)
+	 *
+	 * @param  $flexformArray
+	 * @return array
+	 * @static
+	 */
+	protected static function extractValuesFromFlexformArray(array $flexformArray) {
+		foreach ($flexformArray as $sheet) {
+			foreach ($sheet as $language) {
+				foreach ($language as $fieldName => $fieldValue) {
+					$values[$fieldName] = $fieldValue['vDEF'];
+				}
+			}
+		}
+
+		return $values;
+	}
+
+	/**
+	 * @param t3lib_file_storage_Interface $storageBackend The backend to use
+	 *
+	 */
+	public function setStorageBackend(t3lib_file_storage_Interface $storageBackend) {
+		$this->storageBackend = $storageBackend;
+
+		$this->baseUrl = $this->storageBackend->getBaseUrl();
+	}
+
+	/**
+	 * Returns the storage backend used by this file mount.
+	 *
+	 * @return t3lib_file_storage_Interface
+	 */
+	public function getStorageBackend() {
+		return $this->storageBackend;
+	}
+
+	/**
+	 * Creates a directory inside this mount. Success of this operation depends - among other things - on the directory
+	 * support by the backend.
+	 *
+	 * @param  $path The path to create the directory in
+	 * @param  $directoryName The directory to create
+	 * @return boolean TRUE if the directory could be created
+	 */
+	public function createDirectory($path, $directoryName) {
+		return $this->storageBackend->createDirectory($path, $directoryName);
+	}
+
+	/**
+	 * Returns a URL for a path in this mount
+	 *
+	 * @param  $path
+	 * @return string
+	 */
+	public function getUrlForPath($path) {
+		return $this->baseUrl . $path;
+	}
+
+	public function getUid() {
+		return $this->uid;
+	}
+
+	public function getAlias() {
+		return $this->alias;
+	}
+}
+?>
diff --git a/t3lib/file/class.t3lib_file_Repository.php b/t3lib/file/class.t3lib_file_Repository.php
new file mode 100644
index 0000000..f6a7859
--- /dev/null
+++ t3lib/file/class.t3lib_file_Repository.php
@@ -0,0 +1,156 @@
+<?php
+/***************************************************************
+*  Copyright notice
+*
+*  (c) 1999-2010 Kasper Skårhøj (kasperYYYY@typo3.com)
+*  All rights reserved
+*
+*  This script is part of the TYPO3 project. The TYPO3 project is
+*  free software; you can redistribute it and/or modify
+*  it under the terms of the GNU General Public License as published by
+*  the Free Software Foundation; either version 2 of the License, or
+*  (at your option) any later version.
+*
+*  The GNU General Public License can be found at
+*  http://www.gnu.org/copyleft/gpl.html.
+*  A copy is found in the textfile GPL.txt and important notices to the license
+*  from the author is found in LICENSE.txt distributed with these scripts.
+*
+*
+*  This script 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 General Public License for more details.
+*
+*  This copyright notice MUST APPEAR in all copies of the script!
+***************************************************************/
+
+class t3lib_file_Repository implements t3lib_Singleton {
+
+	/**
+	 * Get the file by ID
+	 *
+	 * @param integer UID of the file record
+	 * @return t3lib_file_File A file object instance
+	 */
+	public function getFileById($uid) {
+		$recordData = $GLOBALS['TYPO3_DB']->exec_SELECTgetRows('*', 'sys_files', 'uid=' . $uid);
+		$mount = $this->getMountForFile($recordData);
+
+		if (count($recordData) == 0) {
+			throw new t3lib_file_exception_FileNotFound();
+		}
+
+		return new t3lib_file_File($mount, $recordData[0]);
+	}
+
+	/**
+	 * 
+	 */
+	public function getFilesFromRelation($field, $table, $recordUid) {
+		if(TYPO3_MODE === 'FE') { // @TODO: Check if constant name and value TYPO3_MODE === 'FE' are correct for checking for FE.
+			$GLOBALS['TSFE']->includeTCA();
+		}
+		t3lib_div::loadTCA($table);
+
+		$assetObjects = array();
+
+		// get column definition
+		$MMfieldTCA = $GLOBALS['TCA'][$table]['columns'][$field]['config'];
+
+		$dbGroup = t3lib_div::makeInstance('t3lib_loadDBGroup');
+		$dbGroup->start($recordUid, 'sys_files', $MMfieldTCA['MM'], intval($recordUid), $table, $MMfieldTCA);
+		$assetIds = $dbGroup->tableArray['sys_files'];
+		if (is_array($assetIds)) {
+			foreach ($assetIds as $key => $uid) {
+				$assetObjects[] = $this->getFileById($uid);
+			}
+		}
+		return $assetObjects;
+	}
+
+	/**
+	 * Returns a file object by the file's complete path.
+	 *
+	 * @param string $filePath The path to the file. May contain the alias of the mount if this is not given as the second parameter.
+	 * @param t3lib_file_Mount $mount The mount the file is located in (optional). If this is not given, the mount is extracted from the first part of the path.
+	 * @return t3lib_file_File
+	 *
+	 * @throws t3lib_file_exception_FileNotFound
+	 *
+	 * TODO: respect file mount (extract it from the path or take it as parameter - both ways should be supported)
+	 */
+	public function getFileByPath($filePath, $mount = NULL) {
+		if ($mount == NULL) {
+			$pathParts = explode('/', $filePath, 2);
+			$mountAlias = array_shift($pathParts);
+			$mount = t3lib_file_Mount::getInstanceForAlias($mountAlias);
+		}
+
+		$fileName = substr($filePath, strrpos($filePath, '/') + 1);
+		$folderPath = substr($filePath, 0, strrpos($filePath, '/') + 1);
+
+		$recordData = $GLOBALS['TYPO3_DB']->exec_SELECTgetRows('*', 'sys_files',
+			'file_path = "' . $folderPath . '" AND file_name = "' . $fileName . '" AND mount = ' . intval($mount->getUid));
+
+		if (count($recordData) == 0) {
+			throw new t3lib_file_exception_FileNotFound();
+		}
+		$mount = $this->getMountForFile($recordData);
+
+		return new t3lib_file_File($mount, $recordData[0]);
+	}
+
+	/**
+	 * Returns all files that are related to a certain field in a certain record.
+	 *
+	 * @param string $table The table
+	 * @param integer $recordUid The record uid
+	 * @param string $fieldName The field name
+	 * @param string $structurePath The structure path in FlexForm data inside $field (optional)
+	 * @return array
+	 *
+	 * TODO: define what is returned by this method (a list of file uids or complete file records)
+	 */
+	public function getReferencedFilesForRecordField($table, $recordUid, $fieldName, $structurePath = '') {
+		//
+	}
+
+	/**
+	 * Returns the mount record for a specified file.
+	 *
+	 * @param array $fileRecord
+	 * @return void
+	 */
+	protected function getMountForFile(array $fileRecord) {
+		$mount = $fileRecord['mount'];
+
+		return t3lib_file_Mount::getInstanceForUid($mount);
+	}
+
+	/**
+	 * @throws t3lib_file_exception_FileNotFound
+	 * @param  $filePath
+	 * @return array
+	 *
+	 * TODO: respect file mount (extract it from the path or take it as parameter - both ways should be supported)
+	 */
+	public function getAllInPath($filePath) {
+		$recordData = $GLOBALS['TYPO3_DB']->exec_SELECTgetRows('*', 'sys_files',
+			'file_path = "' . $filePath . '"');
+
+		if (count($recordData) == 0) {
+			throw new t3lib_file_exception_FileNotFound();
+		}
+		$mount = $this->getMountForFile($recordData[0]);
+
+		$files = array();
+		foreach ($recordData as $data) {
+			$files[] = new t3lib_file_File($mount, $data);
+		}
+
+		return $files;
+	}
+}
+
+?>
diff --git a/t3lib/file/exception/class.t3lib_file_exception_filenotfound.php b/t3lib/file/exception/class.t3lib_file_exception_filenotfound.php
new file mode 100644
index 0000000..418e4b4
--- /dev/null
+++ t3lib/file/exception/class.t3lib_file_exception_filenotfound.php
@@ -0,0 +1,4 @@
+<?php
+
+class t3lib_file_exception_FileNotFound extends RuntimeException {
+}
\ No newline at end of file
diff --git a/t3lib/file/storage/class.t3lib_file_storage_filesystemstorage.php b/t3lib/file/storage/class.t3lib_file_storage_filesystemstorage.php
new file mode 100644
index 0000000..460f93d
--- /dev/null
+++ t3lib/file/storage/class.t3lib_file_storage_filesystemstorage.php
@@ -0,0 +1,141 @@
+<?php
+
+class t3lib_file_storage_FileSystemStorage implements t3lib_file_storage_Interface {
+
+	/**
+	 * @var array The configuration for this backend
+	 */
+	protected $configuration;
+
+	/**
+	 * @var string
+	 */
+	protected $basePath;
+
+	/**
+	 * @param array $configuration The configuration for the backend
+	 */
+	public function __construct($configuration) {
+		$this->configuration = $configuration;
+
+		if ($configuration['relative']) {
+			$this->basePath = t3lib_div::resolveBackPath(PATH_site . $configuration['path']);
+		} else {
+			$this->basePath = $configuration['path'];
+		}
+		$this->basePath = rtrim($this->basePath, '/') . '/';
+
+		// TODO: throw exception if $this->basePath does not exist
+	}
+
+	public function read($path) {
+		return file_get_contents($path);
+	}
+
+	public function write($path, $content) {
+		return file_put_contents($path, $content);
+	}
+
+	public function delete($path) {
+		if ($this->exists($path)) {
+			unlink($path);
+		}
+	}
+
+	public function exists($path) {
+		return file_exists($path);
+	}
+
+	public function getModificationTime($path) {
+		if ($this->exists($path)) {
+			return filemtime($path);
+		}
+	}
+
+	public function getFileHash($path) {
+		if ($this->exists($path)) {
+			return sha1_file($path);
+		}
+	}
+
+	public function getSize($path) {
+		if ($this->exists($path)) {
+			return filesize($path);
+		}
+	}
+
+	public function getBasePath() {
+		return $this->basePath;
+	}
+
+	public function getBaseUrl() {
+		if ($this->configuration['relative']) {
+			return $this->configuration['path'];
+		}
+	}
+
+	public function open($path, $mode) {}
+
+	/**
+	 * Copies a file inside this storage. All parameters are relative to the base of this storage
+	 *
+	 * @param  $path
+	 * @param  $newPath
+	 * @return void
+	 */
+	public function copyFile($path, $newPath) {
+		$path = $this->basePath . $path;
+		$newPath = $this->basePath . $newPath;
+		if (!file_exists($path)) {
+			throw new InvalidArgumentException('Source file does not exist.');
+		}
+
+		if (!copy($path, $newPath)) {
+			throw new RuntimeException("Copying file '$path' to '$newPath' failed.");
+		}
+	}
+
+	/**
+	 * Moves a file inside this storage.
+	 *
+	 * @param string $oldPath The file to move
+	 * @param string $newPath The location to move to
+	 * @return void
+	 *
+	 * @throws InvalidArgumentException If the file does not exist or there is a file at the new location
+	 */
+	public function moveFile($oldPath, $newPath) {
+		$oldPath = $this->basePath . $oldPath;
+		$newPath = $this->basePath . $newPath;
+
+		if (!file_exists($oldPath)) {
+			throw new InvalidArgumentException('Source file does not exist.');
+		}
+		if (file_exists($newPath)) {
+			throw new InvalidArgumentException('Target file already exists.');
+		}
+
+		rename($oldPath, $newPath);
+	}
+
+	/**
+	 * Creates a directory inside a path
+	 *
+	 * @return boolean
+	 */
+	public function createDirectory($path, $directoryName) {
+		$path = rtrim($this->basePath . $path, '/') . '/';
+
+		return mkdir($path . $directoryName);
+	}
+
+	/**
+	 * Returns a list of all files and directories inside a path
+	 *
+	 * @param string $path
+	 * @return void
+	 */
+	public function getListing($path) {}
+}
+
+?>
\ No newline at end of file
diff --git a/t3lib/file/storage/interface.t3lib_file_storage_interface.php b/t3lib/file/storage/interface.t3lib_file_storage_interface.php
new file mode 100644
index 0000000..cac26ba
--- /dev/null
+++ t3lib/file/storage/interface.t3lib_file_storage_interface.php
@@ -0,0 +1,118 @@
+<?php
+/***************************************************************
+*  Copyright notice
+*
+*  (c) 1999-2010 Kasper Skårhøj (kasperYYYY@typo3.com)
+*  All rights reserved
+*
+*  This script is part of the TYPO3 project. The TYPO3 project is
+*  free software; you can redistribute it and/or modify
+*  it under the terms of the GNU General Public License as published by
+*  the Free Software Foundation; either version 2 of the License, or
+*  (at your option) any later version.
+*
+*  The GNU General Public License can be found at
+*  http://www.gnu.org/copyleft/gpl.html.
+*  A copy is found in the textfile GPL.txt and important notices to the license
+*  from the author is found in LICENSE.txt distributed with these scripts.
+*
+*
+*  This script 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 General Public License for more details.
+*
+*  This copyright notice MUST APPEAR in all copies of the script!
+***************************************************************/
+
+interface t3lib_file_storage_Interface {
+	public function getBasePath();
+
+	public function getBaseUrl();
+
+	public function open($path, $mode);
+
+	/**
+	 * Read the contents of a file
+	 *
+	 * @param		string		Absolute path to the file
+	 * @return		string		File contents
+	 */
+	public function read($path);
+
+	/**
+	 * Write data into a file
+	 *
+	 * @param		string		Absolute path to the file
+	 * @param		string		File contents
+	 * @return		boolean		Success of operation
+	 */
+	public function write($path, $content);
+
+	/**
+	 * Delete the file
+	 *
+	 * @param		string		Absolute path to the file
+	 * @return		void
+	 */
+	public function delete($path);
+
+	/**
+	 * Check if file or directory exists
+	 *
+	 * @param		string		Absolute path to the file
+	 * @return		boolean		True if the file or folder exists, false otherwise
+	 */
+	public function exists($path);
+
+	/**
+	 * Get timestamp of when the file was last modified
+	 *
+	 * @param		string		Absolute path to the file
+	 * @return		integer		Timestamp
+	 */
+	public function getModificationTime($path);
+
+	/**
+	 * Get the sha1 hash of the file
+	 *
+	 * @param		string		Absolute path to the file
+	 * @return		string		Hash of the content
+	 */
+	public function getFileHash($path);
+
+	/**
+	 * Get the file size of the content
+	 *
+	 * @param		string		Absolute path to the file
+	 * @return		integer		Size of the file in bytes
+	 */
+	public function getSize($path);
+
+	/**
+	 * Copies a file inside this storage. All parameters are relative to the base of this storage
+	 *
+	 * @param  $path
+	 * @param  $newPath
+	 * @return void
+	 */
+	public function copyFile($path, $newPath);
+
+	public function moveFile($oldPath, $newPath);
+
+	/**
+	 * Creates a directory inside a path
+	 *
+	 * @return boolean TRUE if the directory could be created
+	 */
+	public function createDirectory($path, $directoryName);
+
+	/**
+	 * Returns a list of all files and directories inside a path
+	 *
+	 * @param string $path
+	 * @return void
+	 */
+	public function getListing($path);
+}
+?>
diff --git a/t3lib/file_bak_Andreas/class.t3lib_file_file.php b/t3lib/file_bak_Andreas/class.t3lib_file_file.php
new file mode 100644
index 0000000..30670b0
--- /dev/null
+++ t3lib/file_bak_Andreas/class.t3lib_file_file.php
@@ -0,0 +1,76 @@
+<?php
+
+/**
+ * The file class of the TYPO3 File Abstraction Layer
+ */
+class t3lib_file_File {
+	
+	/**
+	 * The uid of this node
+	 *
+	 * @var integer
+	 */
+	protected $uid;
+
+	/**
+	 * The name of this node. This is only the name on the current leve, no path
+	 *
+	 * @var string
+	 */
+	protected $name;
+
+	/**
+	 * The parent node of this node
+	 *
+	 * @var t3lib_file_Mount
+	 */
+	protected $mount;
+
+	/**
+	 * The path to this file (inside the file mount)
+	 *
+	 * @var string
+	 */
+	protected $path = NULL;
+
+	/**
+	 * The file size
+	 * 
+	 * @var integer
+	 */
+	protected $size;
+
+	/**
+	 * The hash sum of the file
+	 * TODO: decide on a hashing algorithm
+	 *
+	 * @var string
+	 */
+	protected $hash;
+
+	public function __construct($fileData) {
+		$this->uid = $fileData['uid'];
+		$this->name = $fileData['name'];
+		$this->path = $fileData['path'];
+		$this->size = $fileData['size'];
+	}
+
+	public function getUid() {
+		return $this->uid;
+	}
+
+	public function getName() {
+		return $this->name;
+	}
+
+	public function getPath() {
+		return $this->path;
+	}
+
+	public function getSize() {
+		return $this->size;
+	}
+
+}
+
+?>
\ No newline at end of file
diff --git a/t3lib/file_bak_Andreas/class.t3lib_file_repository.php b/t3lib/file_bak_Andreas/class.t3lib_file_repository.php
new file mode 100644
index 0000000..8ae05a9
--- /dev/null
+++ t3lib/file_bak_Andreas/class.t3lib_file_repository.php
@@ -0,0 +1,66 @@
+<?php
+
+/**
+ * Repository class for files.
+ *
+ * @TODO add support for file mounts
+ *
+ */
+class t3lib_file_Repository {
+	/**
+	 * @static
+	 * @throws t3lib_file_exception_FileNotFound
+	 * @param  integer $uid
+	 * @return t3lib_file_File
+	 *
+	 * @TODO define how to handle more than one match (which would point to an error in the database structure)
+	 */
+	public static function getByUid($uid) {
+		$recordData = $GLOBALS['TYPO3_DB']->exec_SELECTgetRows('*', 'sys_files', 'uid=' . $uid);
+
+		if (count($recordData) == 0) {
+			throw new t3lib_file_exception_FileNotFound();
+		}
+
+		return new t3lib_file_File($recordData[0]);
+	}
+
+	/**
+	 * Returns a file object by the file's complete path.
+	 *
+	 * @static
+	 * @throws t3lib_file_exception_FileNotFound
+	 * @param  string  $filePath
+	 * @return t3lib_file_File
+	 */
+	public static function getByFilepath($filePath) {
+		$fileName = substr($filePath, strrpos($filePath, '/') + 1);
+		$folderPath = substr($filePath, 0, strrpos($filePath, '/') + 1);
+
+		$recordData = $GLOBALS['TYPO3_DB']->exec_SELECTgetRows('*', 'sys_files',
+			'file_path = "' . $folderPath . '" AND file_name = "' . $fileName . '"');
+
+		if (count($recordData) == 0) {
+			throw new t3lib_file_exception_FileNotFound();
+		}
+
+		return new t3lib_file_File($recordData[0]);
+	}
+
+	public static function getAllInPath($path) {
+		$recordData = $GLOBALS['TYPO3_DB']->exec_SELECTgetRows('*', 'sys_files',
+			'file_path = "' . $path . '"');
+
+		if (count($recordData) == 0) {
+			throw new t3lib_file_exception_FileNotFound();
+		}
+
+		foreach ($recordData as $record) {
+			$fileObjects[] = new t3lib_file_File($record); 
+		}
+
+		return $fileObjects;
+	}
+}
+
+?>
\ No newline at end of file
diff --git a/t3lib/js/extjs/ux/ext.ux.plupload.css b/t3lib/js/extjs/ux/ext.ux.plupload.css
new file mode 100644
index 0000000..16da211
--- /dev/null
+++ t3lib/js/extjs/ux/ext.ux.plupload.css
@@ -0,0 +1,43 @@
+.x-plupload-body {
+    overflow-x: hidden;
+    overflow-y: auto;
+}
+
+.x-plupload-body dl {
+    padding: 5px;     
+    border-bottom: 1px solid #D0D0D0;
+    font: normal 11px arial,tahoma,verdana,helvetica;
+    width: 100%;
+}
+
+.x-plupload-body dt {
+    float: left;
+    cursor: pointer;
+    display: block;
+    overflow: hidden;
+    white-space: nowrap;
+}
+
+.plupload_over {
+    background-color: #EFF5FB;
+}
+
+.plupload_selected {
+    background-color: #EFF5FB;
+}
+
+.plupload_emptytext {
+    font: 11px Arial,Helvetica,sans-serif; 
+    vertical-align: middle; 
+    text-align: center;
+}
+
+.plupload_emptytext span {
+    line-height: 100px;
+}
+
+.silk-accept { background-image: url(../../../../typo3/sysext/t3skin/images/icons/status/dialog-ok.png) !important; background-repeat: no-repeat; }
+.silk-add { background-image: url(../../../../typo3/sysext/t3skin/images/icons/actions/edit-add.png) !important; background-repeat: no-repeat; }
+.silk-cross { background-image: url(../../../../typo3/sysext/t3skin/images/icons/status/status-icon-missing.png) !important; background-repeat: no-repeat; }
+.silk-stop { background-image: url(../../../../typo3/sysext/t3skin/images/icons/status/status-permission-denied.png) !important; background-repeat: no-repeat; }
+.silk-arrow-up { background-image: url(../../../../typo3/sysext/t3skin/images/icons/actions/edit-upload.png) !important; background-repeat: no-repeat; }
diff --git a/t3lib/js/extjs/ux/ext.ux.plupload.js b/t3lib/js/extjs/ux/ext.ux.plupload.js
new file mode 100644
index 0000000..9155194
--- /dev/null
+++ t3lib/js/extjs/ux/ext.ux.plupload.js
@@ -0,0 +1,422 @@
+/*!
+ * Ext.ux.PluploadPanel
+ * Ext.ux.PluploadButton
+ * (c) http://adtim.ru/extjs/ux_plupload
+ * 2010-04-28 v0.1
+ */
+
+Ext.ux.PluploadPanel = Ext.extend(Ext.Panel, {
+    constructor: function(config) {
+
+        this.autoScroll = false;
+        this.bodyCssClass = 'x-plupload-body';
+
+        this.success = [];
+        this.failed = [];
+
+        this.viewTpl = new Ext.XTemplate(
+            '<tpl for=".">',
+                '<dl id="{id}">',
+                    '<dt style="width: 50%">{name}</dt>',
+                    '<dt style="width: 15%">{size:fileSize}</dt>',
+                    '<tpl exec="this.statusValue(status, percent, msg)"></tpl><dt style="width: 35%">{this.statusText}</dt>',
+                    '<div class="x-clear"></div>',
+                '</dl>',
+            '</tpl>',
+            {   compiled: true,
+                statusText: '-',
+                statusTextQueued: config.statusQueuedText || 'Queued',
+                statusTextUploading: config.statusUploadingText || 'Uploaded ({0}%)',
+                statusTextFailed: config.statusFailedText || 'FAILED',
+                statusTextDone: config.statusDoneText || 'DONE',
+                statusValue: function (status, percent, msg) {
+                    if ( status == 1 ) {
+                        this.statusText = this.statusTextQueued;
+                    }
+                    else if ( status == 2 ) {
+                        this.statusText = String.format( this.statusTextUploading, percent );
+                    }
+                    else if ( status == 4 ) {
+                        this.statusText = msg || this.statusTextFailed;
+                    }
+                    else if ( status == 5 ) {
+                        this.statusText = this.statusTextDone;
+                    }
+                }
+            }
+        );
+
+        this.store = new Ext.data.JsonStore({
+            fields: [ 'id', 'loaded', 'name', 'size', 'percent', 'status', 'msg' ],
+            listeners: {
+                load: this.onStoreLoad,
+                remove: this.onStoreRemove,
+                update: this.onStoreUpdate,
+                scope: this
+            }
+        });
+
+        this.pbar = new Ext.ProgressBar({ flex: 1 });
+
+        this.bbar = new Ext.Toolbar({
+            layout: 'hbox',
+            style: { paddingLeft: '5px' },
+            items: [
+                this.pbar,
+                new Ext.Toolbar.TextItem({
+                    text: '<i>uploader not initialized</i>',
+                    itemId: 'status'
+                })
+            ]
+        });
+    
+        this.tbar = new Ext.Toolbar({
+            enableOverflow: true,
+              items: [
+                new Ext.Button({
+                    text: config.addButtonText || 'Add files',
+                    itemId: 'addButton',
+                    iconCls: config.addButtonCls,
+                    disabled: true
+                }),
+                new Ext.Button({
+                    text: config.uploadButtonText || 'Upload',
+                    handler: this.onStart,
+                    scope: this,
+                    disabled: true,
+                    itemId: 'start',
+                    iconCls: config.uploadButtonCls
+                }),
+                new Ext.Button({
+                    text: config.cancelButtonText || 'Cancel',
+                    handler: this.onCancel,
+                    scope: this,
+                    disabled: true,
+                    itemId: 'cancel',
+                    iconCls: config.cancelButtonCls
+                }),
+                new Ext.SplitButton({
+                    text: config.deleteButtonText || 'Remove',
+                    handler: this.onDeleteSelected,
+                    menu: new Ext.menu.Menu({
+                        items: [
+                            {text: config.deleteSelectedText || '<b>Remove selected</b>', handler: this.onDeleteSelected, scope: this },
+                            '-',
+                            {text: config.deleteUploadedText || 'Remove uploaded', handler: this.onDeleteUploaded, scope: this },
+                            '-',
+                            {text: config.deleteAllText || 'Remove all', handler: this.onDeleteAll, scope: this }
+                        ]
+                    }),
+                    scope: this,
+                    disabled: true,
+                    itemId: 'delete',
+                    iconCls: config.deleteButtonCls
+                })
+            ]
+        });
+
+        this.view = new Ext.DataView({
+            store: this.store,
+            tpl: this.viewTpl,
+            multiSelect: true,
+            overClass: 'plupload_over',
+            selectedClass: 'plupload_selected',
+            itemSelector: 'dl',
+            emptyText: config.emptyText || '<div class="plupload_emptytext"><span>Queue is empty</span></div>',
+            emptyDropText: config.emptyDropText || '<div class="plupload_emptytext"><span>Drop files here</span></div>',
+            deferEmptyText: false,
+            plugins: Ext.DataView.DragSelector ? new Ext.DataView.DragSelector() : ''
+        });
+
+        this.items = this.view;
+
+        Ext.ux.PluploadPanel.superclass.constructor.apply(this, arguments);
+    },
+    initComponent: function() {
+        Ext.ux.PluploadPanel.superclass.initComponent.apply(this, arguments);
+    },
+    afterRender: function() {
+        Ext.ux.PluploadPanel.superclass.afterRender.apply(this, arguments);
+
+        this.initialize_uploader();
+    },
+    onDeleteSelected: function () {
+        Ext.each( this.view.getSelectedRecords(), 
+            function (record) {
+                this.remove_file( record.get( 'id' ) );
+            }, this
+        );
+    },
+    onDeleteAll: function () {
+        this.store.each(
+            function (record) {
+                this.remove_file( record.get( 'id' ) );
+            }, this
+        );
+    },
+    onDeleteUploaded: function () {
+        this.store.each(
+            function (record) {
+                if ( record.get( 'status' ) == 5 ) {
+                    this.remove_file( record.get( 'id' ) );
+                }
+            }, this
+        );
+    },
+    onCancel: function () {
+        this.uploader.stop();
+    },
+    onStart: function () {
+        this.fireEvent('beforestart', this);
+        if ( this.multipart_params ) {
+            this.uploader.settings.multipart_params = this.multipart_params;
+        }
+        this.uploader.start();
+    },
+    initialize_uploader: function () {
+        var runtimes = 'gears,browserplus,html5';
+        if ( this.flash_swf_url ) {
+            runtimes = "flash," + runtimes; 
+        }
+        if ( this.silverlight_xap_url ) {
+            runtimes = "silverlight," + runtimes; 
+        }
+        this.uploader = new plupload.Uploader({
+            url: this.url,
+            runtimes: this.runtimes || runtimes,
+            browse_button: this.getTopToolbar().getComponent('addButton').getEl().dom.id,
+            container: this.getTopToolbar().getEl().dom.id,
+            max_file_size: this.max_file_size || '10mb',
+            resize: this.resize || '',
+            flash_swf_url: this.flash_swf_url || '',
+            silverlight_xap_url: this.silverlight_xap_url || '',
+            filters : this.filters || [],
+            chunk_size: this.chunk_size,
+            unique_names: this.unique_names,
+            multipart: this.multipart,
+            multipart_params: this.multipart_params,
+            file_data_name: this.file_data_name,
+            drop_element: this.body.dom.id,
+            required_features: this.required_features
+        });
+        Ext.each(['Init', 'ChunkUploaded', 'FilesAdded', 'FilesRemoved', 'FileUploaded', 'PostInit',
+                  'QueueChanged', 'Refresh', 'StateChanged', 'UploadFile', 'UploadProgress', 'Error',  ],
+                 function (v) { this.uploader.bind(v, eval("this." + v), this); }, this
+                );
+        this.uploader.init();
+    },
+    remove_file: function (id) {
+        var fileObj = this.uploader.getFile( id );
+        if ( fileObj ) {
+            this.uploader.removeFile( fileObj );
+        }
+        else {
+            this.store.remove( this.store.getById( id ) );
+        }
+    },
+    update_pbar: function () {
+        var t = this.uploader.total;
+        var speed = Ext.util.Format.fileSize(t.bytesPerSec);
+        var total = this.store.data.length;
+        var failed = this.failed.length; 
+        var success = this.success.length;
+        var sent = failed + success;
+        var queued = total - success - failed;
+//console.log('Sent', sent, 'Total', total, 'Success', success, 'Failed', failed, 'Queued', queued, 'Speed', speed);
+        if ( total ) {
+            this.progressText = '';
+            var pbarText = String.format( this.progressText || '{2} of {1} uploaded ({5}/s)', sent, total, success, failed, queued, speed );
+            var percent = t.percent / 100;
+
+            // flash and html4 runtime fix (uploader.total contains outdated info about queue)
+            if ( this.runtime == 'flash' || this.runtime == 'html4' ) { 
+                if ( total == sent || this.store.find('status', /1|2/) == -1 ) { //find queued or uploading status
+                    percent = 1  
+                }
+            }
+            // end fix
+
+            this.pbar.updateProgress(percent, pbarText);
+        }
+        else {
+            this.pbar.updateProgress(0, ' ');
+        }
+    },
+    update_store: function (v) {
+        if ( !v.msg ) { v.msg = ''; }
+        var data = this.store.getById(v.id);
+        if ( data ) {
+            data.data = v;
+            data.commit();
+        }
+        else {
+            this.store.loadData(v, true);
+        }
+    },
+    onStoreLoad: function (store, record, operation) {
+        this.update_pbar();
+    },
+    onStoreRemove: function (store, record, operation) {
+        if ( ! store.data.length ) {
+            this.getTopToolbar().getComponent('delete').setDisabled(true);
+            this.getTopToolbar().getComponent('start').setDisabled(true);
+            this.uploader.total.reset();
+        }
+        var id = record.get( 'id' );
+
+        Ext.each( this.success, 
+            function (v) {
+                if ( v && v.id == id ) {
+                    this.success.remove(v);
+                }
+            }, this
+        );
+
+        Ext.each( this.failed, 
+            function (v) {
+                if ( v && v.id == id ) {
+                    this.failed.remove(v);
+                }
+            }, this
+        );
+        this.update_pbar();
+    },
+    onStoreUpdate: function (store, record, operation) {
+        this.update_pbar();
+    },
+    Init: function(uploader, data) {
+        var bbar = this.getBottomToolbar();
+        var statusCmp = bbar.getComponent('status');
+        this.runtime = data.runtime;
+        if ( this.runtime_visible == true ) {
+            statusCmp.setText(" Uploader runtime: " + this.runtime);
+        }
+        else {
+            statusCmp.setText('');
+        }
+
+        bbar.syncSize();
+
+        if ( this.uploader.features.dragdrop ) {
+            var v = this.view;
+            v.emptyText = this.emptyDropText;
+            if ( v.rendered ) {
+                v.refresh();
+            }
+        }
+        this.getTopToolbar().getComponent('addButton').setDisabled(false);
+    },
+    ChunkUploaded: function() {
+    },
+    FilesAdded: function(uploader, files) {
+        this.getTopToolbar().getComponent('delete').setDisabled(false);
+        this.getTopToolbar().getComponent('start').setDisabled(false);
+        Ext.each(files, 
+            function (v) {
+                this.update_store( v );
+            }, this
+        );
+    },
+    FilesRemoved: function(uploader, files) {
+        Ext.each(files, 
+            function (file) {
+                this.store.remove( this.store.getById( file.id ) );
+            }, this
+        );
+    },
+    FileUploaded: function(uploader, file, status) {
+        var response = Ext.util.JSON.decode( status.response );
+        if ( response.success == true ) {
+            file.server_error = 0;
+            this.success.push(file);
+        }
+        else {
+            if ( response.message ) {
+                file.msg = '<span style="color: red">' + response.message + '</span>';
+            }
+            file.server_error = 1;
+            this.failed.push(file);
+        }
+        this.update_store( file );
+    },
+    PostInit: function() {
+
+    },
+    QueueChanged: function(uploader) {
+    },
+    Refresh: function(uploader) {
+        Ext.each(uploader.files, 
+            function (v) {
+                this.update_store( v );
+            }, this
+        );
+    },
+    StateChanged: function(uploader) {
+        if ( uploader.state == 2 ) {
+            this.fireEvent('uploadstarted', this);
+            this.getTopToolbar().getComponent('cancel').setDisabled(false);
+            this.getTopToolbar().getComponent('start').setDisabled(true);
+        }
+        else {
+            this.fireEvent('uploadcomplete', this, this.success, this.failed);
+            this.getTopToolbar().getComponent('cancel').setDisabled(true);
+            this.getTopToolbar().getComponent('start').setDisabled(false);
+        }
+    },
+    UploadFile: function(uploader, file) {
+        this.fireEvent('uploadfile', this, uploader, file);
+    },
+    UploadProgress: function(uploader, file) {
+        if ( file.server_error ) {
+            file.status = 4;
+        }
+        this.update_store( file );
+    },
+    Error: function (uploader, data) {
+        data.file.status = 4;
+        if ( data.code == -600 ) {
+            data.file.msg = String.format( '<span style="color: red">{0}</span>', this.statusInvalidSizeText || 'Too big' );
+        }
+        else if ( data.code == -700 ) {
+            data.file.msg = String.format( '<span style="color: red">{0}</span>', this.statusInvalidExtensionText || 'Invalid file type' );
+        }
+        else {
+            data.file.msg = String.format( '<span style="color: red">{2} ({0}: {1})</span>', data.code, data.details, data.message );
+        }
+        this.update_store( data.file );
+    }
+});
+
+Ext.reg('pluploadpanel', Ext.ux.PluploadPanel);
+
+Ext.ux.PluploadButton = Ext.extend(Ext.Button, {
+    constructor: function(config) {
+
+        this.uploadpanel = new Ext.ux.PluploadPanel(config.upload_config);
+
+        this.window = new Ext.Window({ 
+            title: config.window_title || config.text || 'Upload files',
+            width: config.window_width || 640, 
+            height: config.window_height || 380, 
+            layout: 'fit', 
+            items: this.uploadpanel, 
+            closeAction: 'hide',
+            listeners: {
+                hide: function (window) {
+                    if ( this.clearOnClose ) {
+                        this.uploadpanel.onDeleteAll();
+                    }
+                },
+                scope: this
+            }
+        });
+
+        this.handler = function () { 
+            this.window.show(); 
+            this.uploadpanel.doLayout();
+        };
+        
+        Ext.ux.PluploadButton.superclass.constructor.apply(this, arguments);
+    }
+});
+Ext.reg('pluploadbutton', Ext.ux.PluploadButton);
diff --git a/t3lib/js/extjs/ux/ext.ux.plupload.min.js b/t3lib/js/extjs/ux/ext.ux.plupload.min.js
new file mode 100644
index 0000000..d68ec47
--- /dev/null
+++ t3lib/js/extjs/ux/ext.ux.plupload.min.js
@@ -0,0 +1,7 @@
+/*
+ * Ext.ux.PluploadPanel
+ * Ext.ux.PluploadButton
+ * (c) http://adtim.ru/extjs/ux_plupload
+ * 2010-04-28 v0.1
+ */
+Ext.ux.PluploadPanel=Ext.extend(Ext.Panel,{constructor:function(a){this.autoScroll=false;this.bodyCssClass="x-plupload-body";this.success=[];this.failed=[];this.viewTpl=new Ext.XTemplate('<tpl for=".">','<dl id="{id}">','<dt style="width: 50%">{name}</dt>','<dt style="width: 15%">{size:fileSize}</dt>','<tpl exec="this.statusValue(status, percent, msg)"></tpl><dt style="width: 35%">{this.statusText}</dt>','<div class="x-clear"></div>',"</dl>","</tpl>",{compiled:true,statusText:"-",statusTextQueued:a.statusQueuedText||"Queued",statusTextUploading:a.statusUploadingText||"Uploaded ({0}%)",statusTextFailed:a.statusFailedText||"FAILED",statusTextDone:a.statusDoneText||"DONE",statusValue:function(b,c,d){if(b==1){this.statusText=this.statusTextQueued}else{if(b==2){this.statusText=String.format(this.statusTextUploading,c)}else{if(b==4){this.statusText=d||this.statusTextFailed}else{if(b==5){this.statusText=this.statusTextDone}}}}}});this.store=new Ext.data.JsonStore({fields:["id","loaded","name","size","percent","status","msg"],listeners:{load:this.onStoreLoad,remove:this.onStoreRemove,update:this.onStoreUpdate,scope:this}});this.pbar=new Ext.ProgressBar({flex:1});this.bbar=new Ext.Toolbar({layout:"hbox",style:{paddingLeft:"5px"},items:[this.pbar,new Ext.Toolbar.TextItem({text:"<i>uploader not initialized</i>",itemId:"status"})]});this.tbar=new Ext.Toolbar({enableOverflow:true,items:[new Ext.Button({text:a.addButtonText||"Add files",itemId:"addButton",iconCls:a.addButtonCls,disabled:true}),new Ext.Button({text:a.uploadButtonText||"Upload",handler:this.onStart,scope:this,disabled:true,itemId:"start",iconCls:a.uploadButtonCls}),new Ext.Button({text:a.cancelButtonText||"Cancel",handler:this.onCancel,scope:this,disabled:true,itemId:"cancel",iconCls:a.cancelButtonCls}),new Ext.SplitButton({text:a.deleteButtonText||"Remove",handler:this.onDeleteSelected,menu:new Ext.menu.Menu({items:[{text:a.deleteSelectedText||"<b>Remove selected</b>",handler:this.onDeleteSelected,scope:this},"-",{text:a.deleteUploadedText||"Remove uploaded",handler:this.onDeleteUploaded,scope:this},"-",{text:a.deleteAllText||"Remove all",handler:this.onDeleteAll,scope:this}]}),scope:this,disabled:true,itemId:"delete",iconCls:a.deleteButtonCls})]});this.view=new Ext.DataView({store:this.store,tpl:this.viewTpl,multiSelect:true,overClass:"plupload_over",selectedClass:"plupload_selected",itemSelector:"dl",emptyText:a.emptyText||'<div class="plupload_emptytext"><span>Queue is empty</span></div>',emptyDropText:a.emptyDropText||'<div class="plupload_emptytext"><span>Drop files here</span></div>',deferEmptyText:false,plugins:Ext.DataView.DragSelector?new Ext.DataView.DragSelector():""});this.items=this.view;Ext.ux.PluploadPanel.superclass.constructor.apply(this,arguments)},initComponent:function(){Ext.ux.PluploadPanel.superclass.initComponent.apply(this,arguments)},afterRender:function(){Ext.ux.PluploadPanel.superclass.afterRender.apply(this,arguments);this.initialize_uploader()},onDeleteSelected:function(){Ext.each(this.view.getSelectedRecords(),function(a){this.remove_file(a.get("id"))},this)},onDeleteAll:function(){this.store.each(function(a){this.remove_file(a.get("id"))},this)},onDeleteUploaded:function(){this.store.each(function(a){if(a.get("status")==5){this.remove_file(a.get("id"))}},this)},onCancel:function(){this.uploader.stop()},onStart:function(){this.fireEvent("beforestart",this);if(this.multipart_params){this.uploader.settings.multipart_params=this.multipart_params}this.uploader.start()},initialize_uploader:function(){var runtimes="gears,browserplus,html5";if(this.flash_swf_url){runtimes="flash,"+runtimes}if(this.silverlight_xap_url){runtimes="silverlight,"+runtimes}this.uploader=new plupload.Uploader({url:this.url,runtimes:this.runtimes||runtimes,browse_button:this.getTopToolbar().getComponent("addButton").getEl().dom.id,container:this.getTopToolbar().getEl().dom.id,max_file_size:this.max_file_size||"10mb",resize:this.resize||"",flash_swf_url:this.flash_swf_url||"",silverlight_xap_url:this.silverlight_xap_url||"",filters:this.filters||[],chunk_size:this.chunk_size,unique_names:this.unique_names,multipart:this.multipart,multipart_params:this.multipart_params,drop_element:this.body.dom.id,required_features:this.required_features});Ext.each(["Init","ChunkUploaded","FilesAdded","FilesRemoved","FileUploaded","PostInit","QueueChanged","Refresh","StateChanged","UploadFile","UploadProgress","Error"],function(v){this.uploader.bind(v,eval("this."+v),this)},this);this.uploader.init()},remove_file:function(b){var a=this.uploader.getFile(b);if(a){this.uploader.removeFile(a)}else{this.store.remove(this.store.getById(b))}},update_pbar:function(){var i=this.uploader.total;var c=Ext.util.Format.fileSize(i.bytesPerSec);var g=this.store.data.length;var d=this.failed.length;var h=this.success.length;var f=d+h;var a=g-h-d;if(g){this.progressText="";var b=String.format(this.progressText||"{2} of {1} uploaded ({5}/s)",f,g,h,d,a,c);var e=i.percent/100;if(this.runtime=="flash"||this.runtime=="html4"){if(g==f||this.store.find("status",/1|2/)==-1){e=1}}this.pbar.updateProgress(e,b)}else{this.pbar.updateProgress(0," ")}},update_store:function(a){if(!a.msg){a.msg=""}var b=this.store.getById(a.id);if(b){b.data=a;b.commit()}else{this.store.loadData(a,true)}},onStoreLoad:function(c,a,b){this.update_pbar()},onStoreRemove:function(c,a,b){if(!c.data.length){this.getTopToolbar().getComponent("delete").setDisabled(true);this.getTopToolbar().getComponent("start").setDisabled(true);this.uploader.total.reset()}var d=a.get("id");Ext.each(this.success,function(e){if(e&&e.id==d){this.success.remove(e)}},this);Ext.each(this.failed,function(e){if(e&&e.id==d){this.failed.remove(e)}},this);this.update_pbar()},onStoreUpdate:function(c,a,b){this.update_pbar()},Init:function(d,c){var e=this.getBottomToolbar();var b=e.getComponent("status");this.runtime=c.runtime;if(this.runtime_visible==true){b.setText(" Uploader runtime: "+this.runtime)}else{b.setText("")}e.syncSize();if(this.uploader.features.dragdrop){var a=this.view;a.emptyText=this.emptyDropText;if(a.rendered){a.refresh()}}this.getTopToolbar().getComponent("addButton").setDisabled(false)},ChunkUploaded:function(){},FilesAdded:function(b,a){this.getTopToolbar().getComponent("delete").setDisabled(false);this.getTopToolbar().getComponent("start").setDisabled(false);Ext.each(a,function(c){this.update_store(c)},this)},FilesRemoved:function(b,a){Ext.each(a,function(c){this.store.remove(this.store.getById(c.id))},this)},FileUploaded:function(d,c,a){var b=Ext.util.JSON.decode(a.response);if(b.success==true){c.server_error=0;this.success.push(c)}else{if(b.message){c.msg='<span style="color: red">'+b.message+"</span>"}c.server_error=1;this.failed.push(c)}this.update_store(c)},PostInit:function(){},QueueChanged:function(a){},Refresh:function(a){Ext.each(a.files,function(b){this.update_store(b)},this)},StateChanged:function(a){if(a.state==2){this.fireEvent("uploadstarted",this);this.getTopToolbar().getComponent("cancel").setDisabled(false);this.getTopToolbar().getComponent("start").setDisabled(true)}else{this.fireEvent("uploadcomplete",this,this.success,this.failed);this.getTopToolbar().getComponent("cancel").setDisabled(true);this.getTopToolbar().getComponent("start").setDisabled(false)}},UploadFile:function(){},UploadProgress:function(b,a){if(a.server_error){a.status=4}this.update_store(a)},Error:function(b,a){a.file.status=4;if(a.code==-600){a.file.msg=String.format('<span style="color: red">{0}</span>',this.statusInvalidSizeText||"Too big")}else{if(a.code==-700){a.file.msg=String.format('<span style="color: red">{0}</span>',this.statusInvalidExtensionText||"Invalid file type")}else{a.file.msg=String.format('<span style="color: red">{2} ({0}: {1})</span>',a.code,a.details,a.message)}}this.update_store(a.file)}});Ext.reg("pluploadpanel",Ext.ux.PluploadPanel);Ext.ux.PluploadButton=Ext.extend(Ext.Button,{constructor:function(a){this.uploadpanel=new Ext.ux.PluploadPanel(a.upload_config);this.window=new Ext.Window({title:a.window_title||a.text||"Upload files",width:a.window_width||640,height:a.window_height||380,layout:"fit",items:this.uploadpanel,closeAction:"hide",listeners:{hide:function(b){if(this.clearOnClose){this.uploadpanel.onDeleteAll()}},scope:this}});this.handler=function(){this.window.show();this.uploadpanel.doLayout()};Ext.ux.PluploadButton.superclass.constructor.apply(this,arguments)}});Ext.reg("pluploadbutton",Ext.ux.PluploadButton);
\ No newline at end of file
diff --git a/tests/t3lib/file/storage/t3lib_file_storage_filesystemstorageTest.php b/tests/t3lib/file/storage/t3lib_file_storage_filesystemstorageTest.php
new file mode 100644
index 0000000..d3225ca
--- /dev/null
+++ tests/t3lib/file/storage/t3lib_file_storage_filesystemstorageTest.php
@@ -0,0 +1,123 @@
+<?php
+
+include_once 'vfsStream/vfsStreamWrapper.php';
+include_once 'vfsStream/vfsStream.php';
+
+class t3lib_file_storage_FileSystemStorageTest extends tx_phpunit_testcase {
+	/**
+	 * @test
+	 */
+	public function basePathAlwaysEndsWithSlash() {
+		$storageConfiguration = array('relative' => TRUE, 'path' => 'relative/path');
+
+		$storageBackend = new t3lib_file_storage_FileSystemStorage($storageConfiguration);
+		$this->assertEquals(PATH_site . $storageConfiguration['path'] . '/', $storageBackend->getBasePath());
+
+		$storageConfiguration = array('relative' => FALSE, 'path' => '/absolute/path');
+
+		$storageBackend = new t3lib_file_storage_FileSystemStorage($storageConfiguration);
+		$this->assertEquals($storageConfiguration['path'] . '/', $storageBackend->getBasePath());
+	}
+
+	/**
+	 * @test
+	 */
+	public function relativePathIsResolvedCorrectly() {
+		$storageConfiguration = array('relative' => 1, 'path' => 'relative/path/');
+
+		$storageBackend = new t3lib_file_storage_FileSystemStorage($storageConfiguration);
+		$this->assertEquals(PATH_site . $storageConfiguration['path'], $storageBackend->getBasePath());
+	}
+
+	/**
+	 * @test
+	 */
+	public function relativePathWithDotsIsResolvedCorrectly() {
+		$storageConfiguration = array('relative' => 1, 'path' => '../a/relative/path/outside/the/typo3/site/directory/');
+
+		$storageBackend = new t3lib_file_storage_FileSystemStorage($storageConfiguration);
+		$expectedPath = substr(PATH_site, 0, strrpos(PATH_site, '/', -2)) . substr($storageConfiguration['path'], strpos($storageConfiguration['path'], '/'));
+		$this->assertEquals($expectedPath, $storageBackend->getBasePath());
+	}
+
+	/**
+	 * @test
+	 */
+	public function copyCopiesFileToCorrectLocation() {
+		$root = vfsStream::setup('root');
+		$subdir = vfsStream::newDirectory('somedir')->at($root);
+		$file = vfsStream::newFile('source.txt')->at($subdir);
+		$storageBackend = new t3lib_file_storage_FileSystemStorage(array('path' => vfsStream::url('root'), 'relative' => FALSE));
+		$storageBackend->copyFile('somedir/source.txt', 'somedir/target.txt');
+
+		$this->assertTrue($subdir->hasChild('target.txt'));
+	}
+
+	/**
+	 * @test
+	 */
+	public function copyThrowsExceptionIfSourceFileIsNotFound() {
+		$this->setExpectedException('InvalidArgumentException');
+
+		$root = vfsStream::setup('root');
+		$subdir = vfsStream::newDirectory('somedir')->at($root);
+		$storageBackend = new t3lib_file_storage_FileSystemStorage(array('path' => vfsStream::url('root'), 'relative' => FALSE));
+		$storageBackend->copyFile('somedir/source.txt', 'somedir/target.txt');
+	}
+
+	/**
+	 * @test
+	 */
+	public function moveFileMovesToCorrectLocation() {
+		$root = vfsStream::setup('root');
+		$subdir = vfsStream::newDirectory('somedir')->at($root);
+		$file = vfsStream::newFile('source.txt')->at($subdir);
+		$storageBackend = new t3lib_file_storage_FileSystemStorage(array('path' => vfsStream::url('root'), 'relative' => FALSE));
+		$storageBackend->moveFile('somedir/source.txt', 'somedir/target.txt');
+
+		$this->assertFalse($subdir->hasChild('source.txt'));
+		$this->assertTrue($subdir->hasChild('target.txt'));
+	}
+
+	/**
+	 * @test
+	 */
+	public function moveFileThrowsExceptionIfSourceFileDoesNotExist() {
+		$this->setExpectedException('InvalidArgumentException');
+
+		$root = vfsStream::setup('root');
+		$subdir = vfsStream::newDirectory('somedir')->at($root);
+		$storageBackend = new t3lib_file_storage_FileSystemStorage(array('path' => vfsStream::url('root'), 'relative' => FALSE));
+		$storageBackend->moveFile('somedir/source.txt', 'somedir/target.txt');
+	}
+
+	/**
+	 * @test
+	 */
+	public function moveFileThrowsExceptionIfDestinationFileExists() {
+		$this->setExpectedException('InvalidArgumentException');
+
+		$root = vfsStream::setup('root');
+		$subdir = vfsStream::newDirectory('somedir')->at($root);
+		vfsStream::newFile('source.txt')->at($subdir);
+		vfsStream::newFile('target.txt')->at($subdir);
+		$storageBackend = new t3lib_file_storage_FileSystemStorage(array('path' => vfsStream::url('root'), 'relative' => FALSE));
+		$storageBackend->moveFile('somedir/source.txt', 'somedir/target.txt');
+	}
+
+	/**
+	 * @test
+	 */
+	public function createDirectoryCreatesDirectory() {
+		$root = vfsStream::setup('root');
+		$storageBackend = new t3lib_file_storage_FileSystemStorage(array('path' => vfsStream::url('root'), 'relative' => FALSE));
+
+		$storageBackend->createDirectory('', 'aDirOnTheFirstLevel');
+		$this->assertTrue($root->hasChild('aDirOnTheFirstLevel'));
+
+		$subdir = vfsStream::newDirectory('someDir')->at($root);
+		$storageBackend->createDirectory('someDir', 'anotherDir');
+
+		$this->assertTrue($subdir->hasChild('anotherDir'));
+	}
+}
\ No newline at end of file
diff --git a/tests/t3lib/file/t3lib_file_fileTest.php b/tests/t3lib/file/t3lib_file_fileTest.php
new file mode 100644
index 0000000..3e04cda
--- /dev/null
+++ tests/t3lib/file/t3lib_file_fileTest.php
@@ -0,0 +1,58 @@
+<?php
+/***************************************************************
+* Copyright notice
+*
+* (c) 2010 Andreas Wolf <andreas.wolf@ikt-werk.de>
+* All rights reserved
+*
+* This script is part of the TYPO3 project. The TYPO3 project is
+* free software; you can redistribute it and/or modify
+* it under the terms of the GNU General Public License as published by
+* the Free Software Foundation; either version 2 of the License, or
+* (at your option) any later version.
+*
+* The GNU General Public License can be found at
+* http://www.gnu.org/copyleft/gpl.html.
+*
+* This script 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 General Public License for more details.
+*
+* This copyright notice MUST APPEAR in all copies of the script!
+***************************************************************/
+
+/**
+ * Testcase for the t3lib_file_File class in the TYPO3 Core.
+ *
+ * @package TYPO3
+ * @subpackage t3lib
+ *
+ * @author Andreas Wolf <andreas.wolf@ikt-werk.de>
+ */
+class t3lib_file_fileTest extends tx_phpunit_testcase {
+
+	/**
+	 * @test
+	 */
+	public function constructorStoresFileData() {
+		// pseudo file data from the database
+		$fileData = array(
+			'uid' => 1,
+			'file_name' => 'test.jpg',
+			'file_path' => 'just/a/random/testfolder/',
+			'file_size' => 1234,
+			'file_hash' => sha1(uniqid())
+		);
+		$mockMount = $this->getMock('t3lib_file_Mount');
+
+		$fileObject = new t3lib_file_File($mockMount, $fileData);
+
+		$this->assertEquals($fileData['uid'], $fileObject->getUid(), 'File uid was not stored correctly.');
+		$this->assertEquals($fileData['file_name'], $fileObject->getName(), 'File name was not stored correctly.');
+		$this->assertEquals($fileData['file_size'], $fileObject->getSize(), 'File size was not stored correctly.');
+		$this->assertEquals($fileData['file_path'], $fileObject->getPath(), 'Node path was not stored correctly.');
+		$this->assertEquals($fileData['file_hash'], $fileObject->getHash(), 'Node path was not stored correctly.');
+	}
+}
+?>
\ No newline at end of file
diff --git a/tests/t3lib/file/t3lib_file_indexerTest.php b/tests/t3lib/file/t3lib_file_indexerTest.php
new file mode 100644
index 0000000..e9c99ec
--- /dev/null
+++ tests/t3lib/file/t3lib_file_indexerTest.php
@@ -0,0 +1,92 @@
+<?php
+
+class t3lib_file_IndexerTest extends tx_phpunit_testcase {
+
+	private $_dbConnectionBackup;
+
+	/**
+	 * @var t3lib_file_Mount
+	 */
+	private $mockedMount;
+
+	/**
+	 * @var t3lib_file_storage_Interface
+	 */
+	private $mockedStorage;
+
+	/**
+	 * @var t3lib_DB
+	 */
+	private $mockedDatabase;
+
+	public function setUp() {
+		$this->mockedStorage = $this->getMock('t3lib_file_storage_Interface');
+		$this->mockedStorage->expects($this->any())->method('exists')->will($this->returnValue(TRUE));
+		$this->mockedMount = $this->getMock('t3lib_file_Mount');
+		$this->mockedMount->expects($this->any())->method('getUid')->will($this->returnValue(1));
+		$this->mockedMount->expects($this->any())->method('getStorageBackend')->will($this->returnValue($this->mockedStorage));
+
+		$this->mockedDatabase = $this->getMock('t3lib_DB');
+
+		$this->_dbConnectionBackup = $GLOBALS['TYPO3_DB'];
+		$GLOBALS['TYPO3_DB'] = $this->mockedDatabase;
+	}
+
+	public function tearDown() {
+		$GLOBALS['TYPO3_DB'] = $this->_dbConnectionBackup;
+		$this->mockedMount = NULL;
+		$this->mockedStorage = NULL;
+	}
+
+	/**
+	 * @test
+	 */
+	public function indexerCorrectlyResolvesFilePath() {
+		$fakedPath = 'someFolder/' . uniqid() . 'with/someFileInIt_' . uniqid() . '.ext';
+
+		$this->mockedMount->expects($this->any())->method('getStorageBackend')->will($this->returnValue($this->mockedStorage));
+		$this->mockedDatabase->expects($this->any())->method('exec_INSERTquery')->with(
+			$this->anything(),
+			$this->logicalAnd($this->contains(basename($fakedPath)), $this->contains(dirname($fakedPath) . '/'))
+		);
+
+		t3lib_file_Indexer::addFileToIndex($this->mockedMount, $fakedPath);
+	}
+
+	/**
+	 * @test
+	 */
+	public function indexerStoresTimesWithNewFileRecords() {
+		$fakedPath = 'someFolder/' . uniqid() . 'with/someFileInIt_' . uniqid() . '.ext';
+
+		$this->mockedMount->expects($this->any())->method('getStorageBackend')->will($this->returnValue($this->mockedStorage));
+		$this->mockedDatabase->expects($this->any())->method('exec_INSERTquery')->with(
+			$this->anything(),
+			$this->logicalAnd($this->contains($GLOBALS['EXEC_TIME']))
+		);
+
+		t3lib_file_Indexer::addFileToIndex($this->mockedMount, $fakedPath);
+	}
+
+	/**
+	 * @test
+	 */
+	public function indexerQueriesBackendForFileData() {
+		$fakedPath = 'someFolder/' . uniqid() . 'with/someFileInIt_' . uniqid() . '.ext';
+
+		$modificationTime = time();
+		$hash = uniqid();
+		$size = rand(1, 1048576);
+		$this->mockedStorage->expects($this->any())->method('getSize')->will($this->returnValue($size));
+		$this->mockedStorage->expects($this->any())->method('getFileHash')->will($this->returnValue($hash));
+		$this->mockedStorage->expects($this->any())->method('getModificationTime')->will($this->returnValue($modificationTime));
+		$this->mockedMount->expects($this->any())->method('getStorageBackend')->will($this->returnValue($this->mockedStorage));
+
+		$this->mockedDatabase->expects($this->atLeastOnce())->method('exec_INSERTquery')->with(
+			'sys_files',
+			$this->logicalAnd($this->contains($hash), $this->contains($size), $this->contains($modificationTime))
+		);
+
+		t3lib_file_Indexer::addFileToIndex($this->mockedMount, $fakedPath);
+	}
+}
\ No newline at end of file
diff --git a/tests/t3lib/file/t3lib_file_mountTest.php b/tests/t3lib/file/t3lib_file_mountTest.php
new file mode 100644
index 0000000..6e65883
--- /dev/null
+++ tests/t3lib/file/t3lib_file_mountTest.php
@@ -0,0 +1,49 @@
+<?php
+
+class t3lib_file_mountTest extends tx_phpunit_testcase {
+
+	/**
+	 * @test
+	 */
+	public function getInstanceReturnsInstanceForUidZero() {
+		$mountObject = t3lib_file_Mount::getInstanceForUid(0);
+
+		$this->assertType('t3lib_file_Mount', $mountObject);
+	}
+
+	/**
+	 * @test
+	 */
+	public function backendInInstanceForUidZeroPointsToCorrectLocation() {
+		$mountObject = t3lib_file_Mount::getInstanceForUid(0);
+		$backend = $mountObject->getStorageBackend();
+
+		$this->assertEquals(PATH_site . 'fileadmin/', $backend->getBasePath());
+	}
+
+	/**
+	 * @test
+	 */
+	public function getUrlForPathUsesBaseUrlFromBackend() {
+		$baseUrl = 'protocol://some-host/some/path/to/a/mount/';
+		$filePath = 'a/file/inside/the/mount.ext';
+
+		$mountObject = new t3lib_file_Mount();
+		$backendObject = $this->getMock('t3lib_file_storage_filesystemstorage', array('getBaseUrl'));
+		$backendObject->expects($this->any())->method('getBaseUrl')->will($this->returnValue($baseUrl));
+		$mountObject->setStorageBackend($backendObject);
+
+		$this->assertEquals($baseUrl . $filePath, $mountObject->getUrlForPath($filePath));
+	}
+
+	/**
+	 * @test
+	 */
+	public function getInstanceForAliasReturnsCorrectMount() {
+		$mount = t3lib_file_Mount::getInstanceForAlias('fileadmin');
+
+		$this->assertEquals(0, $mount->getUid());
+		$this->assertEquals('fileadmin', $mount->getAlias());
+	}
+}
+?>
\ No newline at end of file
diff --git a/tests/t3lib/file/t3lib_file_repositoryTest.php b/tests/t3lib/file/t3lib_file_repositoryTest.php
new file mode 100644
index 0000000..ce82a1a
--- /dev/null
+++ tests/t3lib/file/t3lib_file_repositoryTest.php
@@ -0,0 +1,195 @@
+<?php
+
+class t3lib_file_repositoryTest extends tx_phpunit_testcase {
+
+	protected function _getFakedMount($uid, $alias) {
+		return new t3lib_file_Mount(array('uid' => $uid, 'alias' => $alias));
+	}
+
+	/**
+	 * @test
+	 */
+	public function getByIdFetchesCorrectRecordFromDatabase() {
+		$fakeRecord = array(
+			'uid' => 1,
+			'file_name' => 'test.jpg',
+			'file_path' => 'just/a/testfolder/somewhere/',
+			'file_size' => 1234,
+			'mount' => 0
+		);
+		$databaseMock = $this->getMock('t3lib_DB', array('exec_SELECTgetRows'));
+		$databaseMock->expects($this->at(0))->method('exec_SELECTgetRows')->with(
+			$this->anything(),
+			$this->equalTo('sys_files'),
+			$this->stringEndsWith($fakeRecord['uid'])
+		)->will($this->returnValue(array($fakeRecord)));
+
+		$fakedMount = $this->_getFakedMount(0, 'fileadmin');
+
+		$GLOBALS['TYPO3_DB'] = $databaseMock;
+		$repository = $this->getMock('t3lib_file_Repository', array('getMountForFile'));
+		$repository->expects($this->any())->method('getMountForFile')->will($this->returnValue($fakedMount));
+
+		$fileObject = $repository->getFileById($fakeRecord['uid']);
+		$this->assertType('t3lib_file_File', $fileObject);
+		$this->assertEquals($fakeRecord['uid'], $fileObject->getUid());
+	}
+
+	/**
+	 * @test
+	 */
+	public function getByIdThrowsExceptionIfRecordDoesNotExist() {
+		$databaseMock = $this->getMock('t3lib_DB', array('exec_SELECTgetRows'));
+		$databaseMock->expects($this->once())->method('exec_SELECTgetRows')->with(
+				$this->anything(),
+				$this->equalTo('sys_files'),
+				$this->anything()
+			)->will($this->returnValue(array()));
+
+		$fakedMount = $this->_getFakedMount(0, 'fileadmin');
+
+		$GLOBALS['TYPO3_DB'] = $databaseMock;
+		$repository = $this->getMock('t3lib_file_Repository', array('getMountForFile'));
+		$repository->expects($this->any())->method('getMountForFile')->will($this->returnValue($fakedMount));
+
+		$this->setExpectedException('t3lib_file_exception_FileNotFound');
+		$repository->getFileById(1);
+	}
+
+	/**
+	 * @test
+	 */
+	public function getFileByPathFetchesCorrectRecordFromDatabase() {
+		$fakeRecord = array(
+			'uid' => 1,
+			'file_name' => 'test.jpg',
+			'file_path' => 'fileadmin/just/a/testfolder/somewhere/',
+			'file_size' => 1234,
+			'mount' => 0
+		);
+		$databaseMock = $this->getMock('t3lib_DB', array('exec_SELECTgetRows'));
+		$databaseMock->expects($this->once())->method('exec_SELECTgetRows')->with(
+			$this->anything(),
+			$this->equalTo('sys_files'),
+			$this->logicalAnd($this->stringContains('"' . $fakeRecord['file_name'] . '"'), $this->stringContains('"' . $fakeRecord['file_path'] . '"'))
+		)->will($this->returnValue(array($fakeRecord)));
+
+		$fakedMount = $this->_getFakedMount(0, 'fileadmin');
+
+		$GLOBALS['TYPO3_DB'] = $databaseMock;
+		$repository = $this->getMock('t3lib_file_Repository', array('getMountForFile'));
+		$repository->expects($this->any())->method('getMountForFile')->will($this->returnValue($fakedMount));
+
+		$fileObject = $repository->getFileByPath($fakeRecord['file_path'] . $fakeRecord['file_name']);
+		$this->assertType('t3lib_file_File', $fileObject);
+	}
+
+	/**
+	 * @test
+	 */
+	public function getAllInPathFetchesAllRecordsFromPath() {
+		$fakePath = 'just/a/testfolder/somewhere/';
+		$fakeRecords = array(
+			array(
+				'uid' => 1,
+				'file_name' => 'test.jpg',
+				'file_path' => $fakePath,
+				'file_size' => 1234,
+				'mount' => 0
+			),
+			array(
+				'uid' => 2,
+				'file_name' => 'test.odt',
+				'file_path' => $fakePath,
+				'file_size' => 321,
+				'mount' => 0
+			)
+		);
+		$databaseMock = $this->getMock('t3lib_DB', array('exec_SELECTgetRows'));
+		$databaseMock->expects($this->once())->method('exec_SELECTgetRows')->with(
+			$this->anything(),
+			$this->equalTo('sys_files'),
+			$this->stringContains('"' . $fakePath . '"')
+		)->will($this->returnValue($fakeRecords));
+
+		$GLOBALS['TYPO3_DB'] = $databaseMock;
+		// TODO: use the real mount here
+		$mount = t3lib_file_Mount::getInstanceForUid(0);
+
+		$repository = new t3lib_file_Repository();
+
+		$fileObjects = $repository->getAllInPath($fakePath);
+		$this->assertType('array', $fileObjects);
+		$this->assertEquals(2, count($fileObjects));
+		$this->assertType('t3lib_file_File', $fileObjects[0]);
+		$this->assertType('t3lib_file_File', $fileObjects[1]);
+		$this->assertEquals($fileObjects[0], new t3lib_file_File($mount, $fakeRecords[0]));
+		$this->assertEquals($fileObjects[1], new t3lib_file_File($mount, $fakeRecords[1]));
+	}
+
+	/**
+	 * @test
+	 */
+	public function getFilesFromRelation() {
+		t3lib_div::loadTCA('tx_test');
+		$fakePath = 'just/a/testfolder/somewhere/';
+		$fakeRecords = array(
+			array(
+				'uid' => 1,
+				'file_name' => 'test.jpg',
+				'file_path' => $fakePath,
+				'file_size' => 1234,
+				'mount' => 0
+			),
+			array(
+				'uid' => 2,
+				'file_name' => 'test.odt',
+				'file_path' => $fakePath,
+				'file_size' => 321,
+				'mount' => 0
+			)
+		);
+		$fakeRelations = array(
+			array(
+				'tablenames' => 'sys_files_usage_mm',
+				'uid_foreign' => '8',
+				'uid_local' => '1',
+				'table' => 'tx_test',
+				'ident' => 'testField'
+			)
+		);
+
+		$GLOBALS['TCA']['tx_test']['columns']['testField']['config'] = array(
+			'type' => 'group',
+			'internal_type' => 'db',
+			'allowed' => 'sys_files',
+			'internal_subtype' => 'file_record',
+			'internal_subtype_allowed' => 'gif,jpg,jpeg,tif,tiff,bmp,pcx,tga,png,pdf,ai',
+			'prepend_tname' => 1,
+			'size' => 5,
+			'minitems' => 0,
+			'MM_opposite_field' => 'file_usage',
+			'MM' => 'sys_files_usage_mm',
+			'MM_match_fields' => array(
+				'ident' => 'testField'
+			)
+		);
+
+		$databaseMock = $this->getMock('t3lib_DB', array('exec_SELECTgetRows'));
+		$databaseMock->expects($this->once())->method('exec_SELECTgetRows')->will($this->returnValue(array($fakeRecords[0])));
+		$databaseMock->expects($this->once())->method('exec_SELECTgetRows')->with(
+			$this->anything(),
+			$this->equalTo('sys_files_usage_mm')
+		)->will($this->returnValue($fakeRelations));
+
+		$GLOBALS['TYPO3_DB'] = $databaseMock;
+
+		$repository = new t3lib_file_Repository();
+
+		$fileObjects = $repository->getFilesFromRelation('testField', 'tx_test', 1);
+		$this->assertType('array', $fileObjects);
+		$this->assertEquals(1, count($fileObjects));
+	}
+}
+
+?>
\ No newline at end of file
diff --git a/typo3/backend.php b/typo3/backend.php
index 29acdad..91173ea 100644
--- typo3/backend.php
+++ typo3/backend.php
@@ -128,7 +128,11 @@ class TYPO3backend {
 			'toolbarmanager'        => 'js/toolbarmanager.js',
 			'modulemenu'            => 'js/modulemenu.js',
 			'iecompatibility'       => 'js/iecompatibility.js',
-			'flashupload'           => 'js/flashupload.js',
+			'plupload_gears'        => 'contrib/plupload/js/gears_init.js',
+			'plupload_browserplus'  => 'contrib/yahooapis/browserplus-min.js',
+			'plupload_full'         => 'contrib/plupload/js/plupload.full.min.js',
+			'plupload_extjs'        => '../t3lib/js/extjs/ux/ext.ux.plupload.js',
+		    'plupload'              => 'js/plupload.js',
 			'evalfield'             => '../t3lib/jsfunc.evalfield.js',
 			'flashmessages'         => '../t3lib/js/extjs/ux/flashmessages.js',
 			'tabclosemenu'          => '../t3lib/js/extjs/ux/ext.ux.tabclosemenu.js',
@@ -628,8 +632,13 @@ class TYPO3backend {
 	public function addJavascriptFile($javascriptFile) {
 		$jsFileAdded = false;
 
+		$checkFile = $javascriptFile;
+		$queryStarts = strpos($checkFile,'?');
+		if ($queryStarts !== false){
+			$checkFile = substr($checkFile,0,$queryStarts);
+		} 
 			//TODO add more checks if neccessary
-		if(file_exists(t3lib_div::resolveBackPath(PATH_typo3.$javascriptFile))) {
+		if(file_exists(t3lib_div::resolveBackPath(PATH_typo3.$checkFile))) {
 			$this->jsFiles[] = $javascriptFile;
 			$jsFileAdded     = true;
 		}
diff --git a/typo3/class.browse_links.php b/typo3/class.browse_links.php
index d32d66d..50da974 100644
--- typo3/class.browse_links.php
+++ typo3/class.browse_links.php
@@ -653,6 +653,7 @@ class browse_links {
 	var $setTitle;      		// title (RTE specific)
 	var $doc;			// Backend template object
 	var $elements = array();	// Holds information about files
+	protected $isFileAbstractionLayerMode = false; // Determines if the element browser is in the File Abstraction Layer (FAL) mode. This means it will return sys_file UIDs instead of paths to files even when it's running in the "file" mode.
 
 		// GPvars:	(Input variables from outside)
 	/**
@@ -704,6 +705,7 @@ class browse_links {
 	 * 5: IRRE uniqueness: name of function in opener window that checks if element is already used, eg. "inline.checkUniqueElement"
 	 * 6: IRRE uniqueness: name of function in opener window that performs some additional(!) action, eg. "inline.setUniqueElement"
 	 * 7: IRRE uniqueness: name of function in opener window that performs action instead of using addElement/insertElement, eg. "inline.importElement"
+	 * 8: FAL mode: Determines if the file browser is used in the File Abstraction Layer (FAL) mode (zero or one)
 	 *
 	 * $pArr = explode('|',$this->bparams);
 	 * $formFieldName = $pArr[0];
@@ -778,12 +780,26 @@ class browse_links {
 		if (!$this->mode)	{
 			$this->mode = 'rte';
 		}
+		
+		/**
+		 * Splits parts of $this->bparams
+		 * @see $bparams
+		 */
+		$pArr = explode('|',$this->bparams);
+		$this->isFileAbstractionLayerMode = (bool)$pArr[8];
+
 			// Creating backend template object:
 		$this->doc = t3lib_div::makeInstance('template');
 		$this->doc->backPath = $GLOBALS['BACK_PATH'];
 			// Load the Prototype library and browse_links.js
 		$this->doc->getPageRenderer()->loadPrototype();
 		$this->doc->loadJavascriptLib('js/browse_links.js');
+		
+		if($this->isFileAbstractionLayerMode) {
+			$this->doc->getPageRenderer()->loadExtJS();
+			$this->doc->getPageRenderer()->addJSFile($this->doc->backPath.'ajax.php?ajaxID=ExtDirect::getAPI&namespace=TYPO3.FAL', NULL, false);
+			$this->doc->getPageRenderer()->addExtDirectCode();
+		}
 
 			// init hook objects:
 		$this->hookObjects = array();
@@ -1047,12 +1063,6 @@ class browse_links {
 		';
 
 
-		/**
-		 * Splits parts of $this->bparams
-		 * @see $bparams
-		 */
-		$pArr = explode('|',$this->bparams);
-
 			// This is JavaScript especially for the TBE Element Browser!
 		$formFieldName = 'data['.$pArr[0].']['.$pArr[1].']['.$pArr[2].']';
 
@@ -1084,10 +1094,11 @@ class browse_links {
 					}
 			';
 		}
+		$JScodeAction = '';
 			// insertElement - perform action commands:
 		if ($pArr[4] && $pArr[7]) {
 				// Call user defined action function:
-			$JScodeAction = '
+			$JScodeAction .= '
 					if (parent.window.opener) {
 						parent.window.opener.'.$pArr[7].'("'.addslashes($pArr[4]).'",table,uid,type);
 						focusOpenerAndClose(close);
@@ -1097,11 +1108,21 @@ class browse_links {
 					}
 			';
 		} else if ($pArr[0] && !$pArr[1] && !$pArr[2]) {
-			$JScodeAction = '
-					addElement(filename,table+"_"+uid,fp,close);
-			';
+			
+			if($this->isFileAbstractionLayerMode) {
+				$JScodeAction .= '
+					TYPO3.FAL.ExtDirect.test(fp, function(response) {
+						addElement(filename,table+"_"+uid,response,close);
+					});
+				';
+			} else {
+				$JScodeAction .= '
+						addElement(filename,table+"_"+uid,fp,close);
+				';
+			}
+
 		} else {
-			$JScodeAction = '
+			$JScodeAction .= '
 					if (setReferences()) {
 						parent.window.opener.group_change("add","'.$pArr[0].'","'.$pArr[1].'","'.$pArr[2].'",elRef,targetDoc);
 					} else {
@@ -1153,7 +1174,8 @@ class browse_links {
 				BrowseLinks.focusOpenerAndClose(close);
 			}
 		';
-
+		
+		
 			// Finally, add the accumulated JavaScript to the template object:
 		$this->doc->JScode.= $this->doc->wrapScriptTags($JScode);
 
@@ -1170,9 +1192,16 @@ class browse_links {
 			'expandPage' => $this->expandPage,
 			'expandFolder' => $this->expandFolder,
 			'PM' => $this->PM,
+			'isFileAbstractionLayerMode' => $this->isFileAbstractionLayerMode,
 		),'Internal variables of Script Class:');
 	}
-
+	
+	
+	function initExtDirect() {
+		
+	}
+	
+	
 
 	/**
 	 * Session data for this class can be set from outside with this method.
diff --git a/typo3/classes/class.typo3_tcefile.php b/typo3/classes/class.typo3_tcefile.php
index 39cdaab..f31988e 100644
--- typo3/classes/class.typo3_tcefile.php
+++ typo3/classes/class.typo3_tcefile.php
@@ -164,16 +164,64 @@ class TYPO3_tcefile {
 	 */
 	public function processAjaxRequest(array $params, TYPO3AJAX $ajaxObj) {
 		$this->init();
+		$this->checkRawRequest($params, $ajaxObj);
 		$this->main();
-		$errors = $this->fileProcessor->getErrorMessages();
-		if (count($errors)) {
-			$ajaxObj->setError(implode(',', $errors));
+		
+		$response = array();
+		$error = null;
+		foreach ($this->fileData['upload'] as $uploaded) {
+			// $uploaded would contain the absolute file path, if it worked
+			if ($uploaded === null) {
+				$error = $this->fileProcessor->lastError;
+				break;
+			}
+		}
+		if (strlen($error)) {
+			$response['message'] = $error;
+			$response['success'] = FALSE;
 		} else {
-			$ajaxObj->addContent('result', $this->fileData);
+			$response['result'] = $this->fileData;
 			if ($this->redirect) {
-				$ajaxObj->addContent('redirect', $this->redirect);
+				$response['redirect'] = $this->redirect;
 			}
-			$ajaxObj->setContentFormat('json');
+			$response['success'] = TRUE;
+		}
+		$ajaxObj->setContentFormat('plain');
+		$ajaxObj->setContent(array(json_encode($response)));
+	}
+	
+	protected function checkRawRequest(array $params, TYPO3AJAX $ajaxObj) {
+
+		// Look for the content type header
+		if (isset($_SERVER["HTTP_CONTENT_TYPE"]))
+			$contentType = $_SERVER["HTTP_CONTENT_TYPE"];
+
+		if (isset($_SERVER["CONTENT_TYPE"]))
+			$contentType = $_SERVER["CONTENT_TYPE"];
+
+		if (strpos($contentType, "multipart") === false) {
+			$tempFile = tempnam('/tmp', 'upload');
+
+			// Open temp file
+			$out = fopen($tempFile, 'wb');
+			if ($out) {
+				// Read binary input stream and append it to temp file
+				$in = fopen("php://input", "rb");
+
+				if ($in) {
+					while ($buff = fread($in, 4096))
+						fwrite($out, $buff);
+				} else
+					die('{"jsonrpc" : "2.0", "error" : {"code": 101, "message": "Failed to open input stream."}, "id" : "id"}');
+				fclose($out);
+				$_FILES['upload_1'] = array(
+					'name' => $_GET['file']['upload']['1']['name'],
+					'tmp_name' => $tempFile,
+					'size' => filesize($tempFile),
+					'target' => $_GET['file']['upload']['1']['target'],
+				);
+			} else
+				die('{"jsonrpc" : "2.0", "error" : {"code": 102, "message": "Failed to open output stream."}, "id" : "id"}');
 		}
 	}
 }
diff --git a/typo3/contrib/plupload/changelog.txt b/typo3/contrib/plupload/changelog.txt
new file mode 100644
index 0000000..b2b5dfd
diff --git a/typo3/contrib/plupload/js/gears_init.js b/typo3/contrib/plupload/js/gears_init.js
new file mode 100644
index 0000000..5f44f09
diff --git a/typo3/contrib/plupload/js/jquery.plupload.queue.min.js b/typo3/contrib/plupload/js/jquery.plupload.queue.min.js
new file mode 100644
index 0000000..2ef814c
diff --git a/typo3/contrib/plupload/js/plupload.browserplus.min.js b/typo3/contrib/plupload/js/plupload.browserplus.min.js
new file mode 100644
index 0000000..19f3fc9
diff --git a/typo3/contrib/plupload/js/plupload.flash.min.js b/typo3/contrib/plupload/js/plupload.flash.min.js
new file mode 100644
index 0000000..d8a06a0
diff --git a/typo3/contrib/plupload/js/plupload.flash.swf b/typo3/contrib/plupload/js/plupload.flash.swf
new file mode 100644
index 0000000..b5ab53d
Binary files /dev/null and b/typo3/contrib/plupload/js/plupload.flash.swf differ
diff --git a/typo3/contrib/plupload/js/plupload.full.min.js b/typo3/contrib/plupload/js/plupload.full.min.js
new file mode 100644
index 0000000..304321c
diff --git a/typo3/contrib/plupload/js/plupload.full.tmp.js b/typo3/contrib/plupload/js/plupload.full.tmp.js
new file mode 100644
index 0000000..0e17539
diff --git a/typo3/contrib/plupload/js/plupload.gears.min.js b/typo3/contrib/plupload/js/plupload.gears.min.js
new file mode 100644
index 0000000..517e8db
diff --git a/typo3/contrib/plupload/js/plupload.html4.min.js b/typo3/contrib/plupload/js/plupload.html4.min.js
new file mode 100644
index 0000000..6a809ed
diff --git a/typo3/contrib/plupload/js/plupload.html5.min.js b/typo3/contrib/plupload/js/plupload.html5.min.js
new file mode 100644
index 0000000..3592fb9
diff --git a/typo3/contrib/plupload/js/plupload.min.js b/typo3/contrib/plupload/js/plupload.min.js
new file mode 100644
index 0000000..d762ad1
diff --git a/typo3/contrib/plupload/js/plupload.silverlight.min.js b/typo3/contrib/plupload/js/plupload.silverlight.min.js
new file mode 100644
index 0000000..ed5b7e4
diff --git a/typo3/contrib/plupload/license.txt b/typo3/contrib/plupload/license.txt
new file mode 100644
index 0000000..82fa1da
diff --git a/typo3/contrib/plupload/readme.md b/typo3/contrib/plupload/readme.md
new file mode 100644
index 0000000..85f8111
diff --git a/typo3/contrib/plupload/readme.txt b/typo3/contrib/plupload/readme.txt
new file mode 100644
index 0000000..bb8685d
diff --git a/typo3/contrib/yahooapis/browserplus-min.js b/typo3/contrib/yahooapis/browserplus-min.js
new file mode 100644
index 0000000..47fbf32
diff --git a/typo3/js/browse_links.js b/typo3/js/browse_links.js
index f39aa86..d426c71 100755
--- typo3/js/browse_links.js
+++ typo3/js/browse_links.js
@@ -43,10 +43,12 @@ var BrowseLinks = {
 };
 
 BrowseLinks.File = {
-	insertElement: function(index, close) {
+	insertElement: function(index, close, mode) {
+	
 		var result = false;
 		if (typeof BrowseLinks.elements[index] !== undefined) {
 			var element = BrowseLinks.elements[index];
+						
 			result = insertElement(
 				'', element.md5, element.type,
 				element.fileName, element.filePath, element.fileExt,
diff --git a/typo3/js/common.js b/typo3/js/common.js
index 863e388..f8e6f29 100644
--- typo3/js/common.js
+++ typo3/js/common.js
@@ -77,7 +77,9 @@ T3AJAX.showError = function(xhr, json) {
 };
 
 // common storage and global object, could later hold more information about the current user etc.
-var TYPO3 = {
+if (!TYPO3) TYPO3 = {}
+
+TYPO3 = Ext.extend(TYPO3, {
 	// store instances that only should be running once
 	_instances: {},
 	getInstance: function(className) {
@@ -99,4 +101,4 @@ var TYPO3 = {
 			return res;
 		}
 	}
-};
+});
diff --git a/typo3/js/plupload.js b/typo3/js/plupload.js
new file mode 100644
index 0000000..7bbec2e
--- /dev/null
+++ typo3/js/plupload.js
@@ -0,0 +1,186 @@
+Ext.ns('TYPO3.Components','TYPO3.Components.filelist');
+
+Ext.onReady(function() {
+	var plp = new Ext.ux.PluploadPanel({
+	    region: 'center',
+	    split: true,
+	    width: 500,
+	    height: 350,
+	    url: TYPO3.configuration.PATH_typo3 + 'ajax.php',
+	    runtimes: 'html5,flash,silverlight,browserplus,gears,html4',
+	    multipart: false,
+	    multipart_params: { },
+	    file_data_name: 'upload_1',
+	
+	    max_file_size: '100mb',
+	
+	    /* image resizing */
+	    /*resize: {width : 640, height : 480, quality : 60},*/
+	
+	    flash_swf_url : '/typo3/contrib/plupload/js/plupload.flash.swf',
+	    silverlight_xap_url : '/typo3/contrib/plupload/js/plupload.silverlight.xap',
+	
+	    /*filters: [  {title : "Image files", extensions : "jpg,JPG,gif,GIF,png,PNG"},
+	                {title : "Zip files", extensions : "zip,ZIP"},
+	                {title : "Text files", extensions : "txt,TXT"}
+	             ],*/
+	
+	    runtime_visible: true,
+	
+	    addButtonCls: 'silk-add',
+	    uploadButtonCls: 'silk-arrow-up',
+	    cancelButtonCls: 'silk-stop',
+	    deleteButtonCls: 'silk-cross',
+	
+	    addButtonText: 'Add files',
+	    uploadButtonText: 'Upload',
+	    cancelButtonText: 'Cancel upload',
+	    deleteButtonText: 'Remove',
+	    deleteSelectedText: '<b>Remove selected</b>',
+	    deleteUploadedText: 'Remove uploaded',
+	    deleteAllText: 'Remove ALL',
+	
+	    statusQueuedText: 'Queued',
+	    statusUploadingText: 'Uploading ({0}%)',
+	    statusFailedText: '<span style="color: red">FAILED</span>',
+	    statusDoneText: '<span style="color: green">DONE</span>',
+	
+	    statusInvalidSizeText: 'Too big',
+	    statusInvalidExtensionText: 'Invalid file type',
+	
+	    emptyText: '<div class="plupload_emptytext"><span>Upload queue is empty</span></div>',
+	    emptyDropText: '<div class="plupload_emptytext"><span>Drop files here</span></div>',
+	
+	    progressText: '{0}/{1} ({3} failed) ({5}/s)',
+	
+	    listeners: {
+	        beforestart: function(uploadpanel) {
+	            // As TYPO3_tcefile::process expects this parameter dependent on the file (because of the parameter name)
+	            // we have to update the upload url for every single file (and not in "beforestart" as in the original file
+	            var parameters = {
+	                "file": "upload_1",
+	                "file[upload][1][name]": uploadpanel.uploader.files[0].name,
+	                "file[upload][1][target]": top.TYPO3.configuration.FileUpload.targetDirectory,
+	                "file[upload][1][data]": 1,
+	                "file[upload][1][charset]": "utf-8",
+	                "ajaxID": "TYPO3_tcefile::process",
+	                "vC": top.TYPO3.configuration.veriCode
+	            };
+	    
+	            uploadpanel.uploader.settings.url = this.url + '?' + Ext.urlEncode(parameters);
+	        },
+	        uploadfile: function(uploadpanel, uploader, file) {
+	
+	            // As TYPO3_tcefile::process expects this parameter dependent on the file (because of the parameter name)
+	            // we have to update the upload url for every single file (and not in "beforestart" as in the original file
+	            var parameters = {
+	                "file": "upload_1",
+	                "file[upload][1][name]": file.name,
+	                "file[upload][1][target]": top.TYPO3.configuration.FileUpload.targetDirectory,
+	                "file[upload][1][data]": 1,
+	                "file[upload][1][charset]": "utf-8",
+	                "ajaxID": "TYPO3_tcefile::process",
+	                "vC": top.TYPO3.configuration.veriCode
+	            };
+	            uploader.settings.url = this.url + '?' + Ext.urlEncode(parameters);
+	        },
+	        uploadstarted: function(uploadpanel) {
+	
+	        },
+	        uploadcomplete: function(uploadpanel, success, failures) {
+/*
+	            if ( success.length && failures.length == 0) {
+	                Ext.Msg.alert('success!', 'all worked');
+	            } else if (success.length) {
+		            Ext.Msg.alert('partly..', 'some worked, some not');
+	            } else {
+		            Ext.Msg.alert('nothing?', 'seems like nothing worked this time');
+	            }
+*/
+	        }
+	    }
+	});
+	
+	var tree = {region:'west', hidden:true};
+	if(TYPO3.Components.filelist.FolderTree){
+		tree = new TYPO3.Components.filelist.FolderTree({
+			id: 't3-upload-window-tree',
+			region: 'west',
+			layout: 'fit',
+			width: 180,
+			minWidth: 20,
+			floatable: true,
+			animCollapse: false,
+			split: true,
+			collapsible: true,
+			collapseMode: 'mini',
+			hideCollapseTool: true,
+			stateful:true,
+			autoScroll: true,
+			border: false,
+			hidden:true,
+			listeners:{
+				click: {
+					fn: function(){
+						
+					}
+				}
+			}
+		});
+	}
+	
+	TYPO3.FileUploadWindow = new Ext.Window({
+	    width: 600,
+	    height: 350,
+		center: true,
+		modal: true,
+		id: 't3-upload-window',
+		layout:'border',
+		title: String.format(TYPO3.LLL.fileUpload.windowTitle),
+		shadow: false,
+		hideBorders: true,
+		closeAction:'hide',
+		maximizable:true,
+		items:[tree,plp],
+		listeners:{
+			hide:{
+				fn: function(){
+					plp.onDeleteAll();
+				}
+			}
+		},
+		bbar:['->',{
+			text:'Upload',
+			disabled:true
+		},{
+			text:'Cancel',
+			handler: function(){
+				TYPO3.FileUploadWindow.hide();
+			}
+		}],
+		showFilelistUploadDialog: function(target){
+			top.TYPO3.configuration.FileUpload = {targetDirectory:target};
+			var tree = Ext.getCmp('t3-upload-window-tree');
+			if (tree) {
+				tree.hide();
+			}
+			TYPO3.FileUploadWindow.show();
+			return false;
+		},
+		showFalTceFormsUploadDialog: function(field,allowed){
+			if(!top.TYPO3.configuration.FileUpload){
+				top.TYPO3.configuration.FileUpload = {targetDirectory:'fileadmin/_temp_/'};
+			}
+			var tree = Ext.getCmp('t3-upload-window-tree');
+			if (tree) {
+				tree.show();
+			}
+			TYPO3.FileUploadWindow.show();
+			return false;
+		}
+	});
+});
+Ext.onReady(function(){
+	Ext.QuickTips.init();
+	Ext.state.Manager.setProvider(new Ext.state.CookieProvider());
+});
diff --git a/typo3/sysext/cms/ext_localconf.php b/typo3/sysext/cms/ext_localconf.php
index cf9ef9e..cfaf065 100755
diff --git a/typo3/sysext/cms/tslib/class.tslib_content.php b/typo3/sysext/cms/tslib/class.tslib_content.php
index 1a1611e..bb6ce37 100644
diff --git a/typo3/sysext/cms/tslib/class.tslib_fe.php b/typo3/sysext/cms/tslib/class.tslib_fe.php
index d8a4d22..870f0df 100644
diff --git a/typo3/sysext/cms/tslib/content/class.tslib_content_content.php b/typo3/sysext/cms/tslib/content/class.tslib_content_content.php
index c3fc3d7..15b03db 100644
diff --git a/typo3/sysext/css_styled_content/pi1/class.tx_cssstyledcontent_pi1.php b/typo3/sysext/css_styled_content/pi1/class.tx_cssstyledcontent_pi1.php
index e7dcba7..9054c6e 100755
diff --git a/typo3/sysext/fal/ChangeLog b/typo3/sysext/fal/ChangeLog
new file mode 100644
index 0000000..6dae3ff
diff --git a/typo3/sysext/fal/README.txt b/typo3/sysext/fal/README.txt
new file mode 100644
index 0000000..2b9aebe
diff --git a/typo3/sysext/fal/classes/controller/class.tx_fal_migrationcontroller.php b/typo3/sysext/fal/classes/controller/class.tx_fal_migrationcontroller.php
new file mode 100644
index 0000000..4881e2b
diff --git a/typo3/sysext/fal/classes/dataprovider/class.tx_fal_dataprovider.php b/typo3/sysext/fal/classes/dataprovider/class.tx_fal_dataprovider.php
new file mode 100644
index 0000000..2ea125d
diff --git a/typo3/sysext/fal/classes/hooks/class.tx_fal_examplehook.php b/typo3/sysext/fal/classes/hooks/class.tx_fal_examplehook.php
new file mode 100644
index 0000000..a6be072
diff --git a/typo3/sysext/fal/classes/iterator/class.tx_fal_databasefieldnameiterator.php b/typo3/sysext/fal/classes/iterator/class.tx_fal_databasefieldnameiterator.php
new file mode 100644
index 0000000..20473c1
diff --git a/typo3/sysext/fal/classes/iterator/class.tx_fal_recorditerator.php b/typo3/sysext/fal/classes/iterator/class.tx_fal_recorditerator.php
new file mode 100644
index 0000000..0ff497d
diff --git a/typo3/sysext/fal/classes/tceforms_wizard.php b/typo3/sysext/fal/classes/tceforms_wizard.php
new file mode 100644
index 0000000..2d61d12
diff --git a/typo3/sysext/fal/doc/wizard_form.dat b/typo3/sysext/fal/doc/wizard_form.dat
new file mode 100644
index 0000000..ef63b07
diff --git a/typo3/sysext/fal/doc/wizard_form.html b/typo3/sysext/fal/doc/wizard_form.html
new file mode 100644
index 0000000..655031b
diff --git a/typo3/sysext/fal/ds_filesystemstorage.xml b/typo3/sysext/fal/ds_filesystemstorage.xml
new file mode 100644
index 0000000..82aaa91
diff --git a/typo3/sysext/fal/ext_autoload.php b/typo3/sysext/fal/ext_autoload.php
new file mode 100755
index 0000000..c2fbb39
diff --git a/typo3/sysext/fal/ext_emconf.php b/typo3/sysext/fal/ext_emconf.php
new file mode 100644
index 0000000..04ea455
diff --git a/typo3/sysext/fal/ext_icon.gif b/typo3/sysext/fal/ext_icon.gif
new file mode 100644
index 0000000..b993e8a
Binary files /dev/null and b/typo3/sysext/fal/ext_icon.gif differ
diff --git a/typo3/sysext/fal/ext_localconf.php b/typo3/sysext/fal/ext_localconf.php
new file mode 100755
index 0000000..2131a81
diff --git a/typo3/sysext/fal/ext_tables.php b/typo3/sysext/fal/ext_tables.php
new file mode 100644
index 0000000..4b77390
diff --git a/typo3/sysext/fal/ext_tables.sql b/typo3/sysext/fal/ext_tables.sql
new file mode 100644
index 0000000..11ea55c
diff --git a/typo3/sysext/fal/icon_tx_fal_contentimages.gif b/typo3/sysext/fal/icon_tx_fal_contentimages.gif
new file mode 100644
index 0000000..eb01f27
Binary files /dev/null and b/typo3/sysext/fal/icon_tx_fal_contentimages.gif differ
diff --git a/typo3/sysext/fal/icon_tx_fal_sys_files.gif b/typo3/sysext/fal/icon_tx_fal_sys_files.gif
new file mode 100644
index 0000000..eb01f27
Binary files /dev/null and b/typo3/sysext/fal/icon_tx_fal_sys_files.gif differ
diff --git a/typo3/sysext/fal/locallang.xml b/typo3/sysext/fal/locallang.xml
new file mode 100755
index 0000000..d552fc0
diff --git a/typo3/sysext/fal/locallang_db.xml b/typo3/sysext/fal/locallang_db.xml
new file mode 100644
index 0000000..7c02adf
diff --git a/typo3/sysext/fal/tasks/class.tx_fal_migrationtask.php b/typo3/sysext/fal/tasks/class.tx_fal_migrationtask.php
new file mode 100755
index 0000000..8bb283b
diff --git a/typo3/sysext/fal/tasks/class.tx_fal_migrationtask_additionalfieldprovider.php b/typo3/sysext/fal/tasks/class.tx_fal_migrationtask_additionalfieldprovider.php
new file mode 100755
index 0000000..2fcaa40
diff --git a/typo3/sysext/fal/tca.php b/typo3/sysext/fal/tca.php
new file mode 100644
index 0000000..6b853a8
diff --git a/typo3/sysext/filelist/classes/class.tx_filelist_backendhook.php b/typo3/sysext/filelist/classes/class.tx_filelist_backendhook.php
new file mode 100644
index 0000000..d7d16ee
diff --git a/typo3/sysext/filelist/classes/class.tx_filelist_dataprovider.php b/typo3/sysext/filelist/classes/class.tx_filelist_dataprovider.php
new file mode 100644
index 0000000..b161b91
diff --git a/typo3/sysext/filelist/classes/class.tx_filelist_registry.php b/typo3/sysext/filelist/classes/class.tx_filelist_registry.php
new file mode 100644
index 0000000..fdf3371
diff --git a/typo3/sysext/filelist/ext_autoload.php b/typo3/sysext/filelist/ext_autoload.php
new file mode 100644
index 0000000..1f9c657
diff --git a/typo3/sysext/filelist/ext_conf_template.txt b/typo3/sysext/filelist/ext_conf_template.txt
new file mode 100644
index 0000000..fab7fe8
diff --git a/typo3/sysext/filelist/ext_localconf.php b/typo3/sysext/filelist/ext_localconf.php
new file mode 100644
index 0000000..c3e27f8
diff --git a/typo3/sysext/filelist/ext_tables.php b/typo3/sysext/filelist/ext_tables.php
index f820920..4557699 100644
diff --git a/typo3/sysext/filelist/mod1/file_list.php b/typo3/sysext/filelist/mod1/file_list.php
index 4aa8a33..4428656 100644
diff --git a/typo3/sysext/filelist/mod_extjs/conf.php b/typo3/sysext/filelist/mod_extjs/conf.php
new file mode 100644
index 0000000..04e4bd0
diff --git a/typo3/sysext/filelist/mod_extjs/index.php b/typo3/sysext/filelist/mod_extjs/index.php
new file mode 100644
index 0000000..89fa8a1
diff --git a/typo3/sysext/filelist/mod_extjs/list.gif b/typo3/sysext/filelist/mod_extjs/list.gif
new file mode 100644
index 0000000..85a4ea0
Binary files /dev/null and b/typo3/sysext/filelist/mod_extjs/list.gif differ
diff --git a/typo3/sysext/filelist/mod_extjs/locallang.xml b/typo3/sysext/filelist/mod_extjs/locallang.xml
new file mode 100644
index 0000000..6831bb4
diff --git a/typo3/sysext/filelist/mod_extjs/locallang_mod.xml b/typo3/sysext/filelist/mod_extjs/locallang_mod.xml
new file mode 100644
index 0000000..0b8d7a3
diff --git a/typo3/sysext/filelist/mod_extjs/mod_template.html b/typo3/sysext/filelist/mod_extjs/mod_template.html
new file mode 100644
index 0000000..e36e1a0
diff --git a/typo3/sysext/filelist/res/js/Application.js b/typo3/sysext/filelist/res/js/Application.js
new file mode 100644
index 0000000..b20f526
diff --git a/typo3/sysext/filelist/res/js/ComponentRegistry.js b/typo3/sysext/filelist/res/js/ComponentRegistry.js
new file mode 100644
index 0000000..b5d33b5
diff --git a/typo3/sysext/filelist/res/js/DetailView/Bootstrap.js b/typo3/sysext/filelist/res/js/DetailView/Bootstrap.js
new file mode 100644
index 0000000..c0c4f60
diff --git a/typo3/sysext/filelist/res/js/DetailView/DetailView.js b/typo3/sysext/filelist/res/js/DetailView/DetailView.js
new file mode 100644
index 0000000..73cdaad
diff --git a/typo3/sysext/filelist/res/js/FileList/Bootstrap.js b/typo3/sysext/filelist/res/js/FileList/Bootstrap.js
new file mode 100644
index 0000000..b3932d0
diff --git a/typo3/sysext/filelist/res/js/FileList/FileList.js b/typo3/sysext/filelist/res/js/FileList/FileList.js
new file mode 100644
index 0000000..b31e588
diff --git a/typo3/sysext/filelist/res/js/FolderTree/Bootstrap.js b/typo3/sysext/filelist/res/js/FolderTree/Bootstrap.js
new file mode 100644
index 0000000..1b3065e
diff --git a/typo3/sysext/filelist/res/js/FolderTree/FolderTree.js b/typo3/sysext/filelist/res/js/FolderTree/FolderTree.js
new file mode 100644
index 0000000..26017e9
diff --git a/typo3/sysext/filelist/res/js/Ui/Bootstrap.js b/typo3/sysext/filelist/res/js/Ui/Bootstrap.js
new file mode 100644
index 0000000..b8b4df8
diff --git a/typo3/sysext/filelist/res/js/Ui/Ui.js b/typo3/sysext/filelist/res/js/Ui/Ui.js
new file mode 100644
index 0000000..c1df524
diff --git a/typo3/sysext/t3skin/stylesheets/structure/element_file_plupload.css b/typo3/sysext/t3skin/stylesheets/structure/element_file_plupload.css
new file mode 100644
index 0000000..4a479da
diff --git a/typo3/sysext/t3skin/stylesheets/visual/element_file_plupload.css b/typo3/sysext/t3skin/stylesheets/visual/element_file_plupload.css
new file mode 100644
index 0000000..cd0cab2
