Permalink
Browse files

MDL-39339 - zip_archive should ignore system files

zip_archive should ignore OSX system files (__MACOSX, .DS_Store) and
Windows thumbnail cache files (Thumbs.db), to avoid issues and confusion.
  • Loading branch information...
pauln committed May 29, 2013
1 parent 81d9f3d commit f384ce26c0c549973e4dd3a155f21715cf18c5c5
Showing with 40 additions and 9 deletions.
  1. +40 −9 lib/filestorage/zip_archive.php
@@ -258,7 +258,8 @@ public function get_info($index) {
return false;
}
- if ($index < 0 or $index >=$this->count()) {
+ // Need to use the ZipArchive's numfiles, as $this->count() relies on this function to count actual files (skipping OSX junk).
+ if ($index < 0 or $index >=$this->za->numFiles) {
return false;
}
@@ -282,6 +283,11 @@ public function get_info($index) {
$info->size = (int)$result['size'];
}
+ if ($this->is_system_file($info)) {
+ // Don't return system files.
+ return false;
+ }
+
return $info;
}
@@ -297,17 +303,32 @@ public function list_files() {
$infos = array();
- for ($i=0; $i<$this->count(); $i++) {
- $info = $this->get_info($i);
- if ($info === false) {
- continue;
- }
- $infos[$i] = $info;
+ foreach ($this as $info) {
+ // Simply iterating over $this will give us info only for files we're interested in.
+ array_push($infos, $info);
}
return $infos;
}
+ public function is_system_file($fileinfo) {
+ if (substr($fileinfo->pathname, 0, 8) === '__MACOSX' or substr($fileinfo->pathname, -9) === '.DS_Store') {
+ // Mac OSX system files.
+ return true;
+ }
+ if (substr($fileinfo->pathname, -9) === 'Thumbs.db') {
+ $stream = $this->za->getStream($fileinfo->pathname);
+ $info = unpack('Nsiga/Nsigb', fread($stream, 8));
+ $signature = fread($stream, 8);
+ fclose($stream);
+ if ($info['siga'] === 0xd0cf11e0 && $info['sigb'] === 0xa1b11ae1) {
+ // It's an OLE Compound File - so it's almost certainly a Windows thumbnail cache.
+ return true;
+ }
+ }
+ return false;
+ }
+
/**
* Returns number of files in archive.
*
@@ -318,7 +339,7 @@ public function count() {
return false;
}
- return $this->za->numFiles;
+ return count($this->list_files());
}
/**
@@ -485,7 +506,17 @@ public function valid() {
return false;
}
- return ($this->pos < $this->count());
+ // Skip over unwanted system files (get_info will return false).
+ while (!$this->get_info($this->pos) && $this->pos < $this->za->numFiles) {
+ $this->next();
+ }
+
+ // No files left - we're at the end.
+ if ($this->pos >= $this->za->numFiles) {
+ return false;
+ }
+
+ return true;
}
/**

0 comments on commit f384ce2

Please sign in to comment.