From c20319d37701efb9d32c38dd71880739ca75b33f Mon Sep 17 00:00:00 2001 From: Robin Appelman Date: Tue, 21 Feb 2012 20:48:14 +0100 Subject: [PATCH] fix incorrect information in the filecache when using encryption --- apps/files_encryption/lib/cryptstream.php | 5 +-- apps/files_encryption/lib/proxy.php | 31 ++++++++++-------- apps/media/lib_media.php | 1 + files/ajax/upload.php | 3 +- lib/filecache.php | 40 ++++++++++++++++++++--- lib/filesystemview.php | 6 +++- 6 files changed, 62 insertions(+), 24 deletions(-) diff --git a/apps/files_encryption/lib/cryptstream.php b/apps/files_encryption/lib/cryptstream.php index 97e0846187..86583096f1 100644 --- a/apps/files_encryption/lib/cryptstream.php +++ b/apps/files_encryption/lib/cryptstream.php @@ -90,7 +90,6 @@ class OC_CryptStream{ } public function stream_write($data){ - error_log('write to '. $this->path); $length=strlen($data); $written=0; $currentPos=ftell($this->source); @@ -148,9 +147,7 @@ class OC_CryptStream{ } public function stream_close(){ - if(OC_FileCache::inCache($this->path)){ - OC_FileCache::put($this->path,array('encrypted'=>true)); - } + OC_FileCache::put($this->path,array('encrypted'=>true)); return fclose($this->source); } } \ No newline at end of file diff --git a/apps/files_encryption/lib/proxy.php b/apps/files_encryption/lib/proxy.php index c53d567ad1..ed3907cccf 100644 --- a/apps/files_encryption/lib/proxy.php +++ b/apps/files_encryption/lib/proxy.php @@ -38,13 +38,7 @@ class OC_FileProxy_Encryption extends OC_FileProxy{ if(is_null(self::$blackList)){ self::$blackList=explode(',',OC_Appconfig::getValue('files_encryption','type_blacklist','jpg,png,jpeg,avi,mpg,mpeg,mkv,mp3,oga,ogv,ogg')); } - if(isset(self::$metaData[$path])){ - $metadata=self::$metaData[$path]; - }else{ - $metadata=OC_FileCache::get($path); - self::$metaData[$path]=$metadata; - } - if($metadata['encrypted']){ + if(self::isEncrypted($path)){ return true; } $extention=substr($path,strrpos($path,'.')+1); @@ -62,7 +56,7 @@ class OC_FileProxy_Encryption extends OC_FileProxy{ if(isset(self::$metaData[$path])){ $metadata=self::$metaData[$path]; }else{ - $metadata=OC_FileCache::get($path); + $metadata=OC_FileCache::getCached($path); self::$metaData[$path]=$metadata; } return (bool)$metadata['encrypted']; @@ -92,14 +86,19 @@ class OC_FileProxy_Encryption extends OC_FileProxy{ fclose($result); $result=fopen('crypt://'.$path,$meta['mode']); }elseif(self::shouldEncrypt($path) and $meta['mode']!='r'){ - if(OC_Filesystem::file_exists($path)){ + if(OC_Filesystem::file_exists($path) and OC_Filesystem::filesize($path)>0){ //first encrypt the target file so we don't end up with a half encrypted file OC_Log::write('files_encryption','Decrypting '.$path.' before writing',OC_Log::DEBUG); - if($result){ - fclose($result); + $tmp=fopen('php://temp'); + while(!feof($result)){ + $chunk=fread($result,8192); + if($chunk){ + fwrite($tmp,$chunk); + } } - $tmpFile=OC_Filesystem::toTmpFile($path); - OC_Filesystem::fromTmpFile($tmpFile,$path); + fclose($result); + OC_Filesystem::file_put_contents($path,$tmp); + fclose($tmp); } $result=fopen('crypt://'.$path,$meta['mode']); } @@ -117,6 +116,10 @@ class OC_FileProxy_Encryption extends OC_FileProxy{ } public function postGetMimeType($path,$mime){ - return OC_Helper::getMimeType('crypt://'.$path,'w'); + if((!OC_FileCache::inCache($path) and self::shouldEncrypt($path)) or self::isEncrypted($path)){ + return OC_Helper::getMimeType('crypt://'.$path,'w'); + }else{ + return $mime; + } } } diff --git a/apps/media/lib_media.php b/apps/media/lib_media.php index 1bcd0f08c8..a2109c151a 100644 --- a/apps/media/lib_media.php +++ b/apps/media/lib_media.php @@ -56,6 +56,7 @@ class OC_MEDIA{ */ public static function updateFile($params){ $path=$params['path']; + if(!$path) return; require_once 'lib_scanner.php'; require_once 'lib_collection.php'; //fix a bug where there were multiply '/' in front of the path, it should only be one diff --git a/files/ajax/upload.php b/files/ajax/upload.php index 241edc216f..034b891460 100644 --- a/files/ajax/upload.php +++ b/files/ajax/upload.php @@ -48,7 +48,8 @@ if(strpos($dir,'..') === false){ for($i=0;$i<$fileCount;$i++){ $target=stripslashes($dir) . $files['name'][$i]; if(is_uploaded_file($files['tmp_name'][$i]) and OC_Filesystem::fromTmpFile($files['tmp_name'][$i],$target)){ - $result[]=array( "status" => "success", 'mime'=>OC_Filesystem::getMimeType($target),'size'=>OC_Filesystem::filesize($target),'name'=>$files['name'][$i]); + $meta=OC_FileCache::getCached($target); + $result[]=array( "status" => "success", 'mime'=>$meta['mimetype'],'size'=>$meta['size'],'name'=>$files['name'][$i]); } } OC_JSON::encodedPrint($result); diff --git a/lib/filecache.php b/lib/filecache.php index 5d299ff24e..83eaffb171 100644 --- a/lib/filecache.php +++ b/lib/filecache.php @@ -28,6 +28,8 @@ * It will try to keep the data up to date but changes from outside ownCloud can invalidate the cache */ class OC_FileCache{ + private static $savedData=array(); + /** * get the filesystem info from the cache * @param string path @@ -93,6 +95,14 @@ class OC_FileCache{ self::update($id,$data); return; } + if(isset(self::$savedData[$path])){ + $data=array_merge($data,self::$savedData[$path]); + unset(self::$savedData[$path]); + } + if(!isset($data['size']) or !isset($data['mtime'])){//save incomplete data for the next time we write it + self::$savedData[$path]=$data; + return; + } if(!isset($data['encrypted'])){ $data['encrypted']=false; } @@ -101,9 +111,8 @@ class OC_FileCache{ } $mimePart=dirname($data['mimetype']); $user=OC_User::getUser(); - $query=OC_DB::prepare('INSERT INTO *PREFIX*fscache(parent, name, path, size, mtime, ctime, mimetype, mimepart,user,writable) VALUES(?,?,?,?,?,?,?,?,?,?)'); - $query->execute(array($parent,basename($path),$path,$data['size'],$data['mtime'],$data['ctime'],$data['mimetype'],$mimePart,$user,$data['writable'])); - + $query=OC_DB::prepare('INSERT INTO *PREFIX*fscache(parent, name, path, size, mtime, ctime, mimetype, mimepart,user,writable,encrypted,versioned) VALUES(?,?,?,?,?,?,?,?,?,?,?,?)'); + $query->execute(array($parent,basename($path),$path,$data['size'],$data['mtime'],$data['ctime'],$data['mimetype'],$mimePart,$user,$data['writable'],$data['encrypted'],$data['versioned'])); } /** @@ -323,7 +332,29 @@ class OC_FileCache{ } self::increaseSize(dirname($fullPath),$size-$cachedSize); } - + + public static function getCached($path,$root=''){ + if(!$root){ + $root=OC_Filesystem::getRoot(); + }else{ + if($root=='/'){ + $root=''; + } + } + $path=$root.$path; + $query=OC_DB::prepare('SELECT ctime,mtime,mimetype,size,encrypted,versioned,writable FROM *PREFIX*fscache WHERE path=?'); + $result=$query->execute(array($path))->fetchRow(); + if(is_array($result)){ + if(isset(self::$savedData[$path])){ + $result=array_merge($result,self::$savedData[$path]); + } + return $result; + }else{ + OC_Log::write('get(): file not found in cache ('.$path.')','core',OC_Log::DEBUG); + return false; + } + } + private static function getCachedSize($path,$root){ if(!$root){ $root=OC_Filesystem::getRoot(); @@ -332,6 +363,7 @@ class OC_FileCache{ $root=''; } } + $path=$root.$path; $query=OC_DB::prepare('SELECT size FROM *PREFIX*fscache WHERE path=?'); $result=$query->execute(array($path)); if($row=$result->fetchRow()){ diff --git a/lib/filesystemview.php b/lib/filesystemview.php index 58d5b3af71..c4d5ff3514 100644 --- a/lib/filesystemview.php +++ b/lib/filesystemview.php @@ -171,6 +171,7 @@ class OC_FilesystemView { } fclose($target); fclose($data); + OC_Hook::emit( OC_Filesystem::CLASSNAME, OC_Filesystem::signal_post_write, array( OC_Filesystem::signal_param_path => $path)); return true; }else{ return false; @@ -278,6 +279,9 @@ class OC_FilesystemView { } public function fromTmpFile($tmpFile,$path){ if(OC_Filesystem::isValidPath($path)){ + if(!$tmpFile){ + debug_print_backtrace(); + } $source=fopen($tmpFile,'r'); if($source){ $this->file_put_contents($path,$source); @@ -286,7 +290,7 @@ class OC_FilesystemView { }else{ } }else{ - error_log('invalid path'); + return false; } }