You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
119 lines
3.3 KiB
119 lines
3.3 KiB
<?php
|
|
|
|
/**
|
|
*
|
|
* @package Duplicator
|
|
* @copyright (c) 2021, Snapcreek LLC
|
|
*/
|
|
|
|
namespace Duplicator\Libs\DupArchive\Headers;
|
|
|
|
use Duplicator\Libs\Snap\SnapIO;
|
|
use Exception;
|
|
|
|
/**
|
|
* File header
|
|
*/
|
|
class DupArchiveFileHeader extends DupArchiveReaderFileHeader
|
|
{
|
|
const MAX_SIZE_FOR_HASHING = 1000000000;
|
|
|
|
public $fileSize = 0;
|
|
public $mtime = 0;
|
|
public $permissions = '';
|
|
public $hash = '';
|
|
public $relativePathLength = 0;
|
|
public $relativePath = '';
|
|
|
|
/**
|
|
* create header from file
|
|
*
|
|
* @param string $filepath file path
|
|
* @param string $relativeFilePath relative file path in archive
|
|
*
|
|
* @return static
|
|
*/
|
|
public static function createFromFile($filepath, $relativeFilePath)
|
|
{
|
|
$instance = new static();
|
|
|
|
|
|
$instance->fileSize = SnapIO::filesize($filepath);
|
|
$instance->permissions = substr(sprintf('%o', fileperms($filepath)), -4);
|
|
$instance->mtime = SnapIO::filemtime($filepath);
|
|
|
|
if ($instance->fileSize > self::MAX_SIZE_FOR_HASHING) {
|
|
$instance->hash = "00000000000000000000000000000000";
|
|
} else {
|
|
$instance->hash = hash_file('crc32b', $filepath);
|
|
}
|
|
|
|
$instance->relativePath = $relativeFilePath;
|
|
$instance->relativePathLength = strlen($instance->relativePath);
|
|
|
|
return $instance;
|
|
}
|
|
|
|
/**
|
|
* create header from src
|
|
*
|
|
* @param string $src source string
|
|
* @param string $relativeFilePath relative path in archvie
|
|
* @param int $forceSize if 0 size is auto of content is filled of \0 char to size
|
|
*
|
|
* @return static
|
|
*/
|
|
public static function createFromSrc($src, $relativeFilePath, $forceSize = 0)
|
|
{
|
|
$instance = new static();
|
|
|
|
$instance->fileSize = strlen($src);
|
|
$instance->permissions = '0644';
|
|
$instance->mtime = time();
|
|
|
|
$srcLen = strlen($src);
|
|
|
|
if ($forceSize > 0 && $srcLen < $forceSize) {
|
|
$charsToAdd = $forceSize - $srcLen;
|
|
$src .= str_repeat("\0", $charsToAdd);
|
|
}
|
|
|
|
if ($instance->fileSize > self::MAX_SIZE_FOR_HASHING) {
|
|
$instance->hash = "00000000000000000000000000000000";
|
|
} else {
|
|
$instance->hash = hash('crc32b', $src);
|
|
}
|
|
|
|
$instance->relativePath = $relativeFilePath;
|
|
$instance->relativePathLength = strlen($instance->relativePath);
|
|
|
|
return $instance;
|
|
}
|
|
|
|
/**
|
|
* Write header in archive
|
|
*
|
|
* @param resource $archiveHandle archive resource
|
|
*
|
|
* @return int bytes written
|
|
*/
|
|
public function writeToArchive($archiveHandle)
|
|
{
|
|
$headerString = '<F><FS>' .
|
|
$this->fileSize . '</FS><MT>' .
|
|
$this->mtime . '</MT><P>' .
|
|
$this->permissions . '</P><HA>' .
|
|
$this->hash . '</HA><RPL>' .
|
|
$this->relativePathLength . '</RPL><RP>' .
|
|
$this->relativePath . '</RP></F>';
|
|
|
|
//SnapIO::fwrite($archiveHandle, $headerString);
|
|
$bytes_written = @fwrite($archiveHandle, $headerString);
|
|
|
|
if ($bytes_written === false) {
|
|
throw new Exception('Error writing to file.');
|
|
} else {
|
|
return $bytes_written;
|
|
}
|
|
}
|
|
}
|
|
|