* This file is part of the ManageWP Worker plugin.
* (c) ManageWP LLC <contact@managewp.com>
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
class MWP_IncrementalBackup_HashComputer
private $maxChunkByteSize = 102400;
* @param int $maxChunkByteSize
public function setMaxChunkByteSize($maxChunkByteSize)
$this->maxChunkByteSize = $maxChunkByteSize;
public function getMaxChunkByteSize()
return $this->maxChunkByteSize;
* Compute a full md5 file hash or compute a partial hash if $limit is present.
* Returns null on failure.
* @param string $realPath
* @param int $offset in bytes
* @param int $limit in bytes
* @param boolean $forcePartialHashing
public function computeMd5Hash($realPath, $offset = 0, $limit = 0, $forcePartialHashing = false)
if ($limit === 0 && $offset === 0 && !$forcePartialHashing) {
// md5_file is always faster if we don't chunk the file
$hash = md5_file($realPath);
return $hash !== false ? $hash : null;
// Fail to initialize file hashing
// Calculate limit from file size and offset
$limit = filesize($realPath) - $offset;
$fh = @fopen($realPath, "rb");
// Failed opening file, cleanup hash context
// Limit chunk size to either our remaining chunk or max chunk size
$chunkSize = $limit < $this->maxChunkByteSize ? $limit : $this->maxChunkByteSize;
$chunk = fread($fh, $chunkSize);
hash_update($ctx, $chunk);
* Run md5sum process and return file hash, or null in case of error
public function computeUnixMd5Sum($realPath)
$processBuilder = Symfony_Process_ProcessBuilder::create()
if (!mwp_is_shell_available()) {
throw new MWP_Worker_Exception(MWP_Worker_Exception::SHELL_NOT_AVAILABLE, "Shell is not available");
$process = $processBuilder->getProcess();
if (!$process->isSuccessful()) {
throw new Symfony_Process_Exception_ProcessFailedException($process);
// Output is in the format of "md5hash filename"
$output = trim($process->getOutput());
$parts = explode(' ', $output);
// Return only the first part of the output
} catch (Symfony_Process_Exception_ProcessFailedException $e) {
mwp_logger()->error('MD5 command line sum failed', array(
'process' => $e->getProcess(),
mwp_logger()->error('MD5 command line sum failed', array(