diff --git a/inc/lib_base.php b/inc/lib_base.php
index e5ae5b4779e055080e1ca5e817a478c8efc52e82..01c54766fc587971da98fe3ed9eb43439faee6f7 100644
--- a/inc/lib_base.php
+++ b/inc/lib_base.php
@@ -94,29 +94,7 @@ if(!isset($CONFIG_BACKEND)){
 }
 OC_USER::setBackend($CONFIG_BACKEND);
 
-if(!is_dir($CONFIG_DATADIRECTORY_ROOT)){
-	@mkdir($CONFIG_DATADIRECTORY_ROOT) or die("Can't create data directory ($CONFIG_DATADIRECTORY_ROOT), you can usually fix this by setting the owner of '$SERVERROOT' to the user that the web server uses (www-data for debian/ubuntu)");
-}
-if(OC_USER::isLoggedIn()){
-	//jail the user in a seperate data folder
-	$CONFIG_DATADIRECTORY=$CONFIG_DATADIRECTORY_ROOT.'/'.$_SESSION['username_clean'];
-	if(!is_dir($CONFIG_DATADIRECTORY)){
-		mkdir($CONFIG_DATADIRECTORY);
-	}
-	$rootStorage=new OC_FILESTORAGE_LOCAL(array('datadir'=>$CONFIG_DATADIRECTORY));
-	if($CONFIG_ENABLEBACKUP){
-		if(!is_dir($CONFIG_BACKUPDIRECTORY)){
-			mkdir($CONFIG_BACKUPDIRECTORY);
-		}
-		if(!is_dir($CONFIG_BACKUPDIRECTORY.'/'.$_SESSION['username_clean'])){
-			mkdir($CONFIG_BACKUPDIRECTORY.'/'.$_SESSION['username_clean']);
-		}
-		$backupStorage=new OC_FILESTORAGE_LOCAL(array('datadir'=>$CONFIG_BACKUPDIRECTORY.'/'.$_SESSION['username_clean']));
-		$backup=new OC_FILEOBSERVER_BACKUP(array('storage'=>$backupStorage));
-		$rootStorage->addObserver($backup);
-	}
-	OC_FILESYSTEM::mount($rootStorage,'/');
-}
+OC_UTIL::setupFS();
 
 
 
@@ -132,12 +110,44 @@ $loginresult=OC_USER::loginlisener();
  *
  */
 class OC_UTIL {
-  public static $scripts=array();
-  
-  /**
-  * get the current installed version of ownCloud
-  * @return array
-  */
+	public static $scripts=array();
+	
+	public static function setupFS(){// configure the initial filesystem based on the configuration
+		global $CONFIG_DATADIRECTORY_ROOT;
+		global $CONFIG_DATADIRECTORY;
+		global $CONFIG_BACKUPDIRECTORY;
+		global $CONFIG_ENABLEBACKUP;
+		if(!is_dir($CONFIG_DATADIRECTORY_ROOT)){
+			@mkdir($CONFIG_DATADIRECTORY_ROOT) or die("Can't create data directory ($CONFIG_DATADIRECTORY_ROOT), you can usually fix this by setting the owner of '$SERVERROOT' to the user that the web server uses (www-data for debian/ubuntu)");
+		}
+		if(OC_USER::isLoggedIn()){
+			$rootStorage=new OC_FILESTORAGE_LOCAL(array('datadir'=>$CONFIG_DATADIRECTORY));
+			if($CONFIG_ENABLEBACKUP){
+				if(!is_dir($CONFIG_BACKUPDIRECTORY)){
+					mkdir($CONFIG_BACKUPDIRECTORY);
+				}
+				if(!is_dir($CONFIG_BACKUPDIRECTORY.'/'.$_SESSION['username_clean'])){
+					mkdir($CONFIG_BACKUPDIRECTORY.'/'.$_SESSION['username_clean']);
+				}
+				$backupStorage=new OC_FILESTORAGE_LOCAL(array('datadir'=>$CONFIG_BACKUPDIRECTORY));
+				$backup=new OC_FILEOBSERVER_BACKUP(array('storage'=>$backupStorage));
+				$rootStorage->addObserver($backup);
+			}
+			OC_FILESYSTEM::mount($rootStorage,'/');
+			
+			$CONFIG_DATADIRECTORY=$CONFIG_DATADIRECTORY_ROOT.'/'.$_SESSION['username_clean'];
+			if(!is_dir($CONFIG_DATADIRECTORY)){
+				mkdir($CONFIG_DATADIRECTORY);
+			}
+			
+			OC_FILESYSTEM::chroot('/'.$_SESSION['username_clean']);
+		}
+	}
+	
+	/**
+	* get the current installed version of ownCloud
+	* @return array
+	*/
 	public static function getVersion(){
 		return array(1,0,60);
 	}
diff --git a/inc/lib_filesystem.php b/inc/lib_filesystem.php
index 492e0c5d3825c9ee1f647edb9cc38eaad8c93883..6ba1f05a3104d4f37e223677175c3245f272b600 100644
--- a/inc/lib_filesystem.php
+++ b/inc/lib_filesystem.php
@@ -29,6 +29,32 @@
  */
 class OC_FILESYSTEM{
 	static private $storages=array();
+	static private $fakeRoot='';
+	
+	/**
+	* change the root to a fake toor
+	* @param  string  fakeRoot
+	* @return bool
+	*/
+	static public function chroot($fakeRoot){
+		if($fakeRoot[0]!=='/'){
+			$fakeRoot='/'.$fakeRoot;
+		}
+		self::$fakeRoot=$fakeRoot;
+	}
+	
+	/**
+	* get the part of the path relative to the mountpoint of the storage it's stored in
+	* @param  string  path
+	* @return bool
+	*/
+	static public function getInternalPath($path){
+		$mountPoint=self::getMountPoint($path);
+		$path=self::$fakeRoot.$path;
+		$internalPath=substr($path,strlen($mountPoint));
+		return $internalPath;
+	}
+	
 	/**
 	* check if the current users has the right premissions to read a file
 	* @param  string  path
@@ -67,7 +93,7 @@ class OC_FILESYSTEM{
 		if(substr($mountpoint,0,1)!=='/'){
 			$mountpoint='/'.$mountpoint;
 		}
-		self::$storages[$mountpoint]=$storage;
+		self::$storages[self::$fakeRoot.$mountpoint]=$storage;
 	}
 	
 	/**
@@ -84,6 +110,8 @@ class OC_FILESYSTEM{
 	
 	/**
 	* get the mountpoint of the storage object for a path
+	( note: because a storage is not always mounted inside the fakeroot, the returned mountpoint is relative to the absolute root of the filesystem and doesn't take the chroot into account
+	*
 	* @param string path
 	* @return string
 	*/
@@ -94,6 +122,7 @@ class OC_FILESYSTEM{
 		if(substr($path,0,1)!=='/'){
 			$path='/'.$path;
 		}
+		$path=self::$fakeRoot.$path;
 		$foundMountPoint='';
 		foreach(self::$storages as $mountpoint=>$storage){
 			if($mountpoint==$path){
@@ -109,17 +138,17 @@ class OC_FILESYSTEM{
 	static public function mkdir($path){
 		$parent=substr($path,0,strrpos($path,'/'));
 		if(self::canWrite($parent) and $storage=self::getStorage($path)){
-			return $storage->mkdir(substr($path,strlen(self::getMountPoint($path))));
+			return $storage->mkdir(self::getInternalPath($path));
 		}
 	}
 	static public function rmdir($path){
 		if(self::canWrite($path) and $storage=self::getStorage($path)){
-			return $storage->rmdir(substr($path,strlen(self::getMountPoint($path))));
+			return $storage->rmdir(self::getInternalPath($path));
 		}
 	}
 	static public function opendir($path){
 		if(self::canRead($path) and $storage=self::getStorage($path)){
-			return $storage->opendir(substr($path,strlen(self::getMountPoint($path))));
+			return $storage->opendir(self::getInternalPath($path));
 		}
 	}
 	static public function is_dir($path){
@@ -127,7 +156,7 @@ class OC_FILESYSTEM{
 			return true;
 		}
 		if(self::canRead($path) and $storage=self::getStorage($path)){
-			return $storage->is_dir(substr($path,strlen(self::getMountPoint($path))));
+			return $storage->is_dir(self::getInternalPath($path));
 		}
 	}
 	static public function is_file($path){
@@ -135,38 +164,38 @@ class OC_FILESYSTEM{
 			return false;
 		}
 		if(self::canRead($path) and $storage=self::getStorage($path)){
-			return $storage->is_file(substr($path,strlen(self::getMountPoint($path))));
+			return $storage->is_file(self::getInternalPath($path));
 		}
 	}
 	static public function stat($path){
 		if(self::canRead($path) and $storage=self::getStorage($path)){
-			return $storage->stat(substr($path,strlen(self::getMountPoint($path))));
+			return $storage->stat(self::getInternalPath($path));
 		}
 	}
 	static public function filetype($path){
 		if(self::canRead($path) and $storage=self::getStorage($path)){
-			return $storage->filetype(substr($path,strlen(self::getMountPoint($path))));
+			return $storage->filetype(self::getInternalPath($path));
 		}
 	}
 	static public function filesize($path){
 		if(self::canRead($path) and $storage=self::getStorage($path)){
-			return $storage->filesize(substr($path,strlen(self::getMountPoint($path))));
+			return $storage->filesize(self::getInternalPath($path));
 		}
 	}
 	static public function readfile($path){
 		if(self::canRead($path) and $storage=self::getStorage($path)){
-			return $storage->readfile(substr($path,strlen(self::getMountPoint($path))));
+			return $storage->readfile(self::getInternalPath($path));
 		}
 	}
 	static public function is_readable($path){
 		if(self::canRead($path) and $storage=self::getStorage($path)){
-			return $storage->is_readable(substr($path,strlen(self::getMountPoint($path))));
+			return $storage->is_readable(self::getInternalPath($path));
 		}
 		return false;
 	}
 	static public function is_writeable($path){
 		if(self::canWrite($path) and $storage=self::getStorage($path)){
-			return $storage->is_writeable(substr($path,strlen(self::getMountPoint($path))));
+			return $storage->is_writeable(self::getInternalPath($path));
 		}
 		return false;
 	}
@@ -175,39 +204,39 @@ class OC_FILESYSTEM{
 			return true;
 		}
 		if(self::canWrite($path) and $storage=self::getStorage($path)){
-			return $storage->file_exists(substr($path,strlen(self::getMountPoint($path))));
+			return $storage->file_exists(self::getInternalPath($path));
 		}
 		return false;
 	}
 	static public function filectime($path){
 		if($storage=self::getStorage($path)){
-			return $storage->filectime(substr($path,strlen(self::getMountPoint($path))));
+			return $storage->filectime(self::getInternalPath($path));
 		}
 	}
 	static public function filemtime($path){
 		if($storage=self::getStorage($path)){
-			return $storage->filemtime(substr($path,strlen(self::getMountPoint($path))));
+			return $storage->filemtime(self::getInternalPath($path));
 		}
 	}
 	static public function fileatime($path){
 		if($storage=self::getStorage($path)){
-			return $storage->fileatime(substr($path,strlen(self::getMountPoint($path))));
+			return $storage->fileatime(self::getInternalPath($path));
 		}
 	}
 	static public function file_get_contents($path){
 		if(self::canRead($path) and $storage=self::getStorage($path)){
-			return $storage->file_get_contents(substr($path,strlen(self::getMountPoint($path))));
+			return $storage->file_get_contents(self::getInternalPath($path));
 		}
 	}
 	static public function file_put_contents($path,$data){
 		if(self::canWrite($path) and $storage=self::getStorage($path)){
 			$this->notifyObservers($path,OC_FILEACTION_WRITE | OC_FILEACTION_CREATE);
-			return $storage->file_put_contents(substr($path,strlen(self::getMountPoint($path))));
+			return $storage->file_put_contents(self::getInternalPath($path));
 		}
 	}
 	static public function unlink($path){
 		if(self::canWrite($path) and $storage=self::getStorage($path)){
-			return $storage->unlink(substr($path,strlen(self::getMountPoint($path))));
+			return $storage->unlink(self::getInternalPath($path));
 		}
 	}
 	static public function rename($path1,$path2){
@@ -216,12 +245,12 @@ class OC_FILESYSTEM{
 			$mp2=self::getMountPoint($path2);
 			if($mp1==$mp2){
 				if($storage=self::getStorage($path1)){
-					return $storage->rename(substr($path1,strlen($mp1)),substr($path2,strlen($mp2)));
+					return $storage->rename(self::getInternalPath($path1),self::getInternalPath($path2));
 				}
 			}elseif($storage1=self::getStorage($path1) and $storage2=self::getStorage($path2)){
-				$tmpFile=$storage1->toTmpFile(substr($path1,strlen($mp1)));
-				$result=$storage2->fromTmpFile($tmpFile,substr($path2,strlen($mp2)));
-				$storage1->unlink(substr($path1,strlen($mp1)));
+				$tmpFile=$storage1->toTmpFile(self::getInternalPath($path1));
+				$result=$storage2->fromTmpFile(self::getInternalPath($path2));
+				$storage1->unlink(self::getInternalPath($path1));
 				return $result;
 			}
 		}
@@ -232,11 +261,11 @@ class OC_FILESYSTEM{
 			$mp2=self::getMountPoint($path2);
 			if($mp1==$mp2){
 				if($storage=self::getStorage($path1)){
-					return $storage->copy(substr($path1,strlen($mp1)),substr($path2,strlen($mp2)));
+					return $storage->copy(self::getInternalPath($path1),self::getInternalPath($path2));
 				}
 			}elseif($storage1=self::getStorage($path1) and $storage2=self::getStorage($path2)){
-				$tmpFile=$storage1->toTmpFile(substr($path1,strlen($mp1)));
-				return $storage2->fromTmpFile($tmpFile,substr($path2,strlen($mp2)));
+				$tmpFile=$storage1->toTmpFile(self::getInternalPath($path1));
+				return $storage2->fromTmpFile(self::getInternalPath($path2));
 			}
 		}
 	}
@@ -244,34 +273,34 @@ class OC_FILESYSTEM{
 		$allowed=((strpos($path,'r')===false and strpos($path,'r+')!==false and self::canRead) or self::canWrite($path));
 		if($allowed){
 			if($storage=self::getStorage($path)){
-				return $storage->fopen(substr($path,strlen(self::getMountPoint($path))),$mode);
+				return $storage->fopen(self::getInternalPath($path),$mode);
 			}
 		}
 	}
 	static public function toTmpFile($path){
 		if(self::canRead($path) and $storage=self::getStorage($path)){
-			return $storage->toTmpFile(substr($path,strlen(self::getMountPoint($path))));
+			return $storage->toTmpFile(self::getInternalPath($path));
 		}
 	}
 	static public function fromTmpFile($tmpFile,$path){
 		if(self::canWrite($path) and $storage=self::getStorage($path)){
-			return $storage->fromTmpFile($tmpFile,substr($path,strlen(self::getMountPoint($path))));
+			return $storage->fromTmpFile(self::getInternalPath($path));
 		}
 	}
 	static public function getMimeType($path){
 		if(self::canRead($path) and $storage=self::getStorage($path)){
-			return $storage->getMimeType(substr($path,strlen(self::getMountPoint($path))));
+			return $storage->getMimeType(self::getInternalPath($path));
 		}
 	}
 	static public function delTree($path){
 		if(self::canWrite($path) and $storage=self::getStorage($path)){
-			return $storage->delTree(substr($path,strlen(self::getMountPoint($path))));
+			return $storage->delTree(self::getInternalPath($path));
 		}
 	}
 	static public function find($path){
 		if($storage=self::getStorage($path)){
 			$mp=self::getMountPoint($path);
-			$return=$storage->find(substr($path,strlen($mp)));
+			$return=$storage->find(self::getInternalPath($path));
 			foreach($return as &$file){
 				$file=$mp.$file;
 			}
@@ -281,8 +310,7 @@ class OC_FILESYSTEM{
 	static public function getTree($path){
 		if(self::canRead($path) and $storage=self::getStorage($path)){
 			$mp=self::getMountPoint($path);
-			$return=$storage->getTree(substr($path,strlen($mp)));
-			echo "mp:  $mp";
+			$return=$storage->getTree(self::getInternalPath($path));
 			foreach($return as &$file){
 				if(substr($file,0,1)=='/'){
 					$file=substr($file,1);