Completed
Branch master (4dc390)
by Fabio
30:44
created

TTarFileExtractor::_extractList()   F

Complexity

Conditions 53
Paths > 20000

Size

Total Lines 206
Code Lines 133

Duplication

Lines 0
Ratio 0 %
Metric Value
dl 0
loc 206
rs 2
cc 53
eloc 133
nc 52948
nop 5

How to fix   Long Method    Complexity   

Long Method

Small methods make your code easier to understand, in particular if combined with a good name. Besides, if your method is small, finding a good name is usually much easier.

For example, if you find yourself adding comments to a method's body, this is usually a good sign to extract the commented part to a new method, and use the comment as a starting point when coming up with a good name for this new method.

Commonly applied refactorings include:

1
<?php
2
/**
3
 * TTarFileExtractor class file
4
 *
5
 * @author Vincent Blavet <[email protected]>
6
 * @copyright Copyright &copy; 1997-2003 The PHP Group
7
 * @package System.IO
8
 */
9
10
/* vim: set ts=4 sw=4: */
11
// +----------------------------------------------------------------------+
12
// | PHP Version 4                                                        |
13
// +----------------------------------------------------------------------+
14
// | Copyright (c) 1997-2003 The PHP Group                                |
15
// +----------------------------------------------------------------------+
16
// | This source file is subject to version 3.0 of the PHP license,       |
17
// | that is bundled with this package in the file LICENSE, and is        |
18
// | available through the world-wide-web at the following url:           |
19
// | http://www.php.net/license/3_0.txt.                                  |
20
// | If you did not receive a copy of the PHP license and are unable to   |
21
// | obtain it through the world-wide-web, please send a note to          |
22
// | [email protected] so we can mail you a copy immediately.               |
23
// +----------------------------------------------------------------------+
24
// | Author: Vincent Blavet <[email protected]>                      |
25
// +----------------------------------------------------------------------+
26
//
27
// $Id: TTarFileExtractor.php 3188 2012-07-12 12:13:23Z ctrlaltca $
28
29
/**
30
 * TTarFileExtractor class
31
 *
32
 * @author Vincent Blavet <[email protected]>
33
 * @package System.IO
34
 * @since 3.0
35
 */
36
class TTarFileExtractor
37
{
38
    /**
39
    * @var string Name of the Tar
40
    */
41
    private $_tarname='';
42
43
    /**
44
    * @var file descriptor
45
    */
46
    private $_file=0;
47
48
    /**
49
    * @var string Local Tar name of a remote Tar (http:// or ftp://)
50
    */
51
    private $_temp_tarname='';
52
53
    /**
54
    * Archive_Tar Class constructor. This flavour of the constructor only
55
    * declare a new Archive_Tar object, identifying it by the name of the
56
    * tar file.
57
    *
58
    * @param    string  $p_tarname  The name of the tar archive to create
59
    * @access public
60
    */
61
    public function __construct($p_tarname)
0 ignored issues
show
Coding Style Naming introduced by
The parameter $p_tarname is not named in camelCase.

This check marks parameter names that have not been written in camelCase.

In camelCase names are written without any punctuation, the start of each new word being marked by a capital letter. Thus the name database connection string becomes databaseConnectionString.

Loading history...
62
    {
63
        $this->_tarname = $p_tarname;
64
    }
65
66
    public function __destruct()
67
    {
68
        $this->_close();
69
        // ----- Look for a local copy to delete
70
        if ($this->_temp_tarname != '')
71
            @unlink($this->_temp_tarname);
0 ignored issues
show
Security Best Practice introduced by
It seems like you do not handle an error condition here. This can introduce security issues, and is generally not recommended.

If you suppress an error, we recommend checking for the error condition explicitly:

// For example instead of
@mkdir($dir);

// Better use
if (@mkdir($dir) === false) {
    throw new \RuntimeException('The directory '.$dir.' could not be created.');
}
Loading history...
72
    }
73
74
    public function extract($p_path='')
0 ignored issues
show
Coding Style Naming introduced by
The parameter $p_path is not named in camelCase.

This check marks parameter names that have not been written in camelCase.

In camelCase names are written without any punctuation, the start of each new word being marked by a capital letter. Thus the name database connection string becomes databaseConnectionString.

Loading history...
75
    {
76
        return $this->extractModify($p_path, '');
77
    }
78
79
    /**
80
    * This method extract all the content of the archive in the directory
81
    * indicated by $p_path. When relevant the memorized path of the
82
    * files/dir can be modified by removing the $p_remove_path path at the
83
    * beginning of the file/dir path.
84
    * While extracting a file, if the directory path does not exists it is
85
    * created.
86
    * While extracting a file, if the file already exists it is replaced
87
    * without looking for last modification date.
88
    * While extracting a file, if the file already exists and is write
89
    * protected, the extraction is aborted.
90
    * While extracting a file, if a directory with the same name already
91
    * exists, the extraction is aborted.
92
    * While extracting a directory, if a file with the same name already
93
    * exists, the extraction is aborted.
94
    * While extracting a file/directory if the destination directory exist
95
    * and is write protected, or does not exist but can not be created,
96
    * the extraction is aborted.
97
    * If after extraction an extracted file does not show the correct
98
    * stored file size, the extraction is aborted.
99
    * When the extraction is aborted, a PEAR error text is set and false
100
    * is returned. However the result can be a partial extraction that may
101
    * need to be manually cleaned.
102
    *
103
    * @param string $p_path         The path of the directory where the
104
	*                               files/dir need to by extracted.
105
    * @param string $p_remove_path  Part of the memorized path that can be
106
	*                               removed if present at the beginning of
107
	*                               the file/dir path.
108
    * @return boolean               true on success, false on error.
109
    * @access public
110
    */
111
    protected function extractModify($p_path, $p_remove_path)
0 ignored issues
show
Coding Style Naming introduced by
The parameter $p_path is not named in camelCase.

This check marks parameter names that have not been written in camelCase.

In camelCase names are written without any punctuation, the start of each new word being marked by a capital letter. Thus the name database connection string becomes databaseConnectionString.

Loading history...
Coding Style Naming introduced by
The parameter $p_remove_path is not named in camelCase.

This check marks parameter names that have not been written in camelCase.

In camelCase names are written without any punctuation, the start of each new word being marked by a capital letter. Thus the name database connection string becomes databaseConnectionString.

Loading history...
112
    {
113
        $v_result = true;
0 ignored issues
show
Unused Code introduced by
$v_result is not used, you could remove the assignment.

This check looks for variable assignements that are either overwritten by other assignments or where the variable is not used subsequently.

$myVar = 'Value';
$higher = false;

if (rand(1, 6) > 3) {
    $higher = true;
} else {
    $higher = false;
}

Both the $myVar assignment in line 1 and the $higher assignment in line 2 are dead. The first because $myVar is never used and the second because $higher is always overwritten for every possible time line.

Loading history...
114
        $v_list_detail = array();
115
116
        if ($v_result = $this->_openRead()) {
117
            $v_result = $this->_extractList($p_path, $v_list_detail,
118
			                                "complete", 0, $p_remove_path);
119
            $this->_close();
120
        }
121
122
        return $v_result;
123
    }
124
125
    protected function _error($p_message)
0 ignored issues
show
Coding Style Naming introduced by
The parameter $p_message is not named in camelCase.

This check marks parameter names that have not been written in camelCase.

In camelCase names are written without any punctuation, the start of each new word being marked by a capital letter. Thus the name database connection string becomes databaseConnectionString.

Loading history...
126
    {
127
		throw new Exception($p_message);
128
    }
129
130
    private function _isArchive($p_filename=null)
0 ignored issues
show
Coding Style Naming introduced by
The parameter $p_filename is not named in camelCase.

This check marks parameter names that have not been written in camelCase.

In camelCase names are written without any punctuation, the start of each new word being marked by a capital letter. Thus the name database connection string becomes databaseConnectionString.

Loading history...
131
    {
132
        if ($p_filename == null) {
133
            $p_filename = $this->_tarname;
134
        }
135
        clearstatcache();
136
        return @is_file($p_filename);
137
    }
138
139
    private function _openRead()
140
    {
141
        if (strtolower(substr($this->_tarname, 0, 7)) == 'http://') {
142
143
          // ----- Look if a local copy need to be done
144
          if ($this->_temp_tarname == '') {
145
              $this->_temp_tarname = uniqid('tar').'.tmp';
146
              if (!$v_file_from = @fopen($this->_tarname, 'rb')) {
147
                $this->_error('Unable to open in read mode \''
148
				              .$this->_tarname.'\'');
149
                $this->_temp_tarname = '';
150
                return false;
151
              }
152
              if (!$v_file_to = @fopen($this->_temp_tarname, 'wb')) {
153
                $this->_error('Unable to open in write mode \''
154
				              .$this->_temp_tarname.'\'');
155
                $this->_temp_tarname = '';
156
                return false;
157
              }
158
              while ($v_data = @fread($v_file_from, 1024))
159
                  @fwrite($v_file_to, $v_data);
0 ignored issues
show
Security Best Practice introduced by
It seems like you do not handle an error condition here. This can introduce security issues, and is generally not recommended.

If you suppress an error, we recommend checking for the error condition explicitly:

// For example instead of
@mkdir($dir);

// Better use
if (@mkdir($dir) === false) {
    throw new \RuntimeException('The directory '.$dir.' could not be created.');
}
Loading history...
160
              @fclose($v_file_from);
0 ignored issues
show
Security Best Practice introduced by
It seems like you do not handle an error condition here. This can introduce security issues, and is generally not recommended.

If you suppress an error, we recommend checking for the error condition explicitly:

// For example instead of
@mkdir($dir);

// Better use
if (@mkdir($dir) === false) {
    throw new \RuntimeException('The directory '.$dir.' could not be created.');
}
Loading history...
161
              @fclose($v_file_to);
0 ignored issues
show
Security Best Practice introduced by
It seems like you do not handle an error condition here. This can introduce security issues, and is generally not recommended.

If you suppress an error, we recommend checking for the error condition explicitly:

// For example instead of
@mkdir($dir);

// Better use
if (@mkdir($dir) === false) {
    throw new \RuntimeException('The directory '.$dir.' could not be created.');
}
Loading history...
162
          }
163
164
          // ----- File to open if the local copy
165
          $v_filename = $this->_temp_tarname;
166
167
        } else
168
          // ----- File to open if the normal Tar file
169
          $v_filename = $this->_tarname;
170
171
		$this->_file = @fopen($v_filename, "rb");
172
173
        if ($this->_file == 0) {
174
            $this->_error('Unable to open in read mode \''.$v_filename.'\'');
175
            return false;
176
        }
177
178
        return true;
179
    }
180
181
    private function _close()
182
    {
183
        //if (isset($this->_file)) {
184
        if (is_resource($this->_file))
185
		{
186
               @fclose($this->_file);
0 ignored issues
show
Security Best Practice introduced by
It seems like you do not handle an error condition here. This can introduce security issues, and is generally not recommended.

If you suppress an error, we recommend checking for the error condition explicitly:

// For example instead of
@mkdir($dir);

// Better use
if (@mkdir($dir) === false) {
    throw new \RuntimeException('The directory '.$dir.' could not be created.');
}
Loading history...
187
            $this->_file = 0;
0 ignored issues
show
Documentation Bug introduced by
It seems like 0 of type integer is incompatible with the declared type object<file> of property $_file.

Our type inference engine has found an assignment to a property that is incompatible with the declared type of that property.

Either this assignment is in error or the assigned type should be added to the documentation/type hint for that property..

Loading history...
188
        }
189
190
        // ----- Look if a local copy need to be erase
191
        // Note that it might be interesting to keep the url for a time : ToDo
0 ignored issues
show
Coding Style introduced by
Comment refers to a TODO task

This check looks TODO comments that have been left in the code.

``TODO``s show that something is left unfinished and should be attended to.

Loading history...
192
        if ($this->_temp_tarname != '') {
193
            @unlink($this->_temp_tarname);
0 ignored issues
show
Security Best Practice introduced by
It seems like you do not handle an error condition here. This can introduce security issues, and is generally not recommended.

If you suppress an error, we recommend checking for the error condition explicitly:

// For example instead of
@mkdir($dir);

// Better use
if (@mkdir($dir) === false) {
    throw new \RuntimeException('The directory '.$dir.' could not be created.');
}
Loading history...
194
            $this->_temp_tarname = '';
195
        }
196
197
        return true;
198
    }
199
200
    private function _cleanFile()
0 ignored issues
show
Unused Code introduced by
This method is not used, and could be removed.
Loading history...
201
    {
202
        $this->_close();
203
204
        // ----- Look for a local copy
205
        if ($this->_temp_tarname != '') {
206
            // ----- Remove the local copy but not the remote tarname
207
            @unlink($this->_temp_tarname);
0 ignored issues
show
Security Best Practice introduced by
It seems like you do not handle an error condition here. This can introduce security issues, and is generally not recommended.

If you suppress an error, we recommend checking for the error condition explicitly:

// For example instead of
@mkdir($dir);

// Better use
if (@mkdir($dir) === false) {
    throw new \RuntimeException('The directory '.$dir.' could not be created.');
}
Loading history...
208
            $this->_temp_tarname = '';
209
        } else {
210
            // ----- Remove the local tarname file
211
            @unlink($this->_tarname);
0 ignored issues
show
Security Best Practice introduced by
It seems like you do not handle an error condition here. This can introduce security issues, and is generally not recommended.

If you suppress an error, we recommend checking for the error condition explicitly:

// For example instead of
@mkdir($dir);

// Better use
if (@mkdir($dir) === false) {
    throw new \RuntimeException('The directory '.$dir.' could not be created.');
}
Loading history...
212
        }
213
        $this->_tarname = '';
214
215
        return true;
216
    }
217
218
    private function _readBlock()
219
    {
220
      $v_block = null;
221
      if (is_resource($this->_file)) {
222
              $v_block = @fread($this->_file, 512);
223
      }
224
      return $v_block;
225
    }
226
227
    private function _jumpBlock($p_len=null)
0 ignored issues
show
Coding Style Naming introduced by
The parameter $p_len is not named in camelCase.

This check marks parameter names that have not been written in camelCase.

In camelCase names are written without any punctuation, the start of each new word being marked by a capital letter. Thus the name database connection string becomes databaseConnectionString.

Loading history...
228
    {
229
      if (is_resource($this->_file)) {
230
          if ($p_len === null)
231
              $p_len = 1;
232
233
              @fseek($this->_file, @ftell($this->_file)+($p_len*512));
0 ignored issues
show
Security Best Practice introduced by
It seems like you do not handle an error condition here. This can introduce security issues, and is generally not recommended.

If you suppress an error, we recommend checking for the error condition explicitly:

// For example instead of
@mkdir($dir);

// Better use
if (@mkdir($dir) === false) {
    throw new \RuntimeException('The directory '.$dir.' could not be created.');
}
Loading history...
234
      }
235
      return true;
236
    }
237
238
    private function _readHeader($v_binary_data, &$v_header)
0 ignored issues
show
Coding Style Naming introduced by
The parameter $v_binary_data is not named in camelCase.

This check marks parameter names that have not been written in camelCase.

In camelCase names are written without any punctuation, the start of each new word being marked by a capital letter. Thus the name database connection string becomes databaseConnectionString.

Loading history...
Coding Style Naming introduced by
The parameter $v_header is not named in camelCase.

This check marks parameter names that have not been written in camelCase.

In camelCase names are written without any punctuation, the start of each new word being marked by a capital letter. Thus the name database connection string becomes databaseConnectionString.

Loading history...
239
    {
240
        if (strlen($v_binary_data)==0) {
241
            $v_header['filename'] = '';
242
            return true;
243
        }
244
245
        if (strlen($v_binary_data) != 512) {
246
            $v_header['filename'] = '';
247
            $this->_error('Invalid block size : '.strlen($v_binary_data));
248
            return false;
249
        }
250
251
        // ----- Calculate the checksum
252
        $v_checksum = 0;
253
        // ..... First part of the header
254
        for ($i=0; $i<148; $i++)
255
            $v_checksum+=ord(substr($v_binary_data,$i,1));
256
        // ..... Ignore the checksum value and replace it by ' ' (space)
257
        for ($i=148; $i<156; $i++)
258
            $v_checksum += ord(' ');
259
        // ..... Last part of the header
260
        for ($i=156; $i<512; $i++)
261
           $v_checksum+=ord(substr($v_binary_data,$i,1));
262
263
        $v_data = unpack("a100filename/a8mode/a8uid/a8gid/a12size/a12mtime/"
264
		                 ."a8checksum/a1typeflag/a100link/a6magic/a2version/"
265
						 ."a32uname/a32gname/a8devmajor/a8devminor",
266
						 $v_binary_data);
267
268
        // ----- Extract the checksum
269
        $v_header['checksum'] = OctDec(trim($v_data['checksum']));
270
        if ($v_header['checksum'] != $v_checksum) {
271
            $v_header['filename'] = '';
272
273
            // ----- Look for last block (empty block)
274
            if (($v_checksum == 256) && ($v_header['checksum'] == 0))
275
                return true;
276
277
            $this->_error('Invalid checksum for file "'.$v_data['filename']
278
			              .'" : '.$v_checksum.' calculated, '
279
						  .$v_header['checksum'].' expected');
280
            return false;
281
        }
282
283
        // ----- Extract the properties
284
        $v_header['filename'] = trim($v_data['filename']);
285
        $v_header['mode'] = OctDec(trim($v_data['mode']));
286
        $v_header['uid'] = OctDec(trim($v_data['uid']));
287
        $v_header['gid'] = OctDec(trim($v_data['gid']));
288
        $v_header['size'] = OctDec(trim($v_data['size']));
289
        $v_header['mtime'] = OctDec(trim($v_data['mtime']));
290
        if (($v_header['typeflag'] = $v_data['typeflag']) == "5") {
291
          $v_header['size'] = 0;
292
        }
293
        return true;
294
    }
295
296
    private function _readLongHeader(&$v_header)
0 ignored issues
show
Coding Style Naming introduced by
The parameter $v_header is not named in camelCase.

This check marks parameter names that have not been written in camelCase.

In camelCase names are written without any punctuation, the start of each new word being marked by a capital letter. Thus the name database connection string becomes databaseConnectionString.

Loading history...
297
    {
298
      $v_filename = '';
299
      $n = floor($v_header['size']/512);
300
      for ($i=0; $i<$n; $i++) {
301
        $v_content = $this->_readBlock();
302
        $v_filename .= $v_content;
303
      }
304
      if (($v_header['size'] % 512) != 0) {
305
        $v_content = $this->_readBlock();
306
        $v_filename .= $v_content;
307
      }
308
309
      // ----- Read the next header
310
      $v_binary_data = $this->_readBlock();
311
312
      if (!$this->_readHeader($v_binary_data, $v_header))
313
        return false;
314
315
      $v_header['filename'] = $v_filename;
316
317
      return true;
318
    }
319
320
    protected function _extractList($p_path, &$p_list_detail, $p_mode,
0 ignored issues
show
Coding Style Naming introduced by
The parameter $p_path is not named in camelCase.

This check marks parameter names that have not been written in camelCase.

In camelCase names are written without any punctuation, the start of each new word being marked by a capital letter. Thus the name database connection string becomes databaseConnectionString.

Loading history...
Coding Style Naming introduced by
The parameter $p_list_detail is not named in camelCase.

This check marks parameter names that have not been written in camelCase.

In camelCase names are written without any punctuation, the start of each new word being marked by a capital letter. Thus the name database connection string becomes databaseConnectionString.

Loading history...
Coding Style Naming introduced by
The parameter $p_mode is not named in camelCase.

This check marks parameter names that have not been written in camelCase.

In camelCase names are written without any punctuation, the start of each new word being marked by a capital letter. Thus the name database connection string becomes databaseConnectionString.

Loading history...
Coding Style Naming introduced by
The parameter $p_file_list is not named in camelCase.

This check marks parameter names that have not been written in camelCase.

In camelCase names are written without any punctuation, the start of each new word being marked by a capital letter. Thus the name database connection string becomes databaseConnectionString.

Loading history...
Coding Style Naming introduced by
The parameter $p_remove_path is not named in camelCase.

This check marks parameter names that have not been written in camelCase.

In camelCase names are written without any punctuation, the start of each new word being marked by a capital letter. Thus the name database connection string becomes databaseConnectionString.

Loading history...
321
	                      $p_file_list, $p_remove_path)
322
    {
323
    $v_result=true;
0 ignored issues
show
Unused Code introduced by
$v_result is not used, you could remove the assignment.

This check looks for variable assignements that are either overwritten by other assignments or where the variable is not used subsequently.

$myVar = 'Value';
$higher = false;

if (rand(1, 6) > 3) {
    $higher = true;
} else {
    $higher = false;
}

Both the $myVar assignment in line 1 and the $higher assignment in line 2 are dead. The first because $myVar is never used and the second because $higher is always overwritten for every possible time line.

Loading history...
324
    $v_nb = 0;
325
    $v_extract_all = true;
0 ignored issues
show
Unused Code introduced by
$v_extract_all is not used, you could remove the assignment.

This check looks for variable assignements that are either overwritten by other assignments or where the variable is not used subsequently.

$myVar = 'Value';
$higher = false;

if (rand(1, 6) > 3) {
    $higher = true;
} else {
    $higher = false;
}

Both the $myVar assignment in line 1 and the $higher assignment in line 2 are dead. The first because $myVar is never used and the second because $higher is always overwritten for every possible time line.

Loading history...
326
    $v_listing = false;
0 ignored issues
show
Unused Code introduced by
$v_listing is not used, you could remove the assignment.

This check looks for variable assignements that are either overwritten by other assignments or where the variable is not used subsequently.

$myVar = 'Value';
$higher = false;

if (rand(1, 6) > 3) {
    $higher = true;
} else {
    $higher = false;
}

Both the $myVar assignment in line 1 and the $higher assignment in line 2 are dead. The first because $myVar is never used and the second because $higher is always overwritten for every possible time line.

Loading history...
327
328
    $p_path = $this->_translateWinPath($p_path, false);
329
    if ($p_path == '' || (substr($p_path, 0, 1) != '/'
330
	    && substr($p_path, 0, 3) != "../" && !strpos($p_path, ':'))) {
331
      $p_path = "./".$p_path;
332
    }
333
    $p_remove_path = $this->_translateWinPath($p_remove_path);
334
335
    // ----- Look for path to remove format (should end by /)
336
    if (($p_remove_path != '') && (substr($p_remove_path, -1) != '/'))
337
      $p_remove_path .= '/';
338
    $p_remove_path_size = strlen($p_remove_path);
339
340
    switch ($p_mode) {
341
      case "complete" :
0 ignored issues
show
Coding Style introduced by
There must be no space before the colon in a CASE statement

As per the PSR-2 coding standard, there must not be a space in front of the colon in case statements.

switch ($selector) {
    case "A": //right
        doSomething();
        break;
    case "B" : //wrong
        doSomethingElse();
        break;
}

To learn more about the PSR-2 coding standard, please refer to the PHP-Fig.

Loading history...
342
        $v_extract_all = true;
343
        $v_listing = false;
344
      break;
345
      case "partial" :
0 ignored issues
show
Coding Style introduced by
There must be no space before the colon in a CASE statement

As per the PSR-2 coding standard, there must not be a space in front of the colon in case statements.

switch ($selector) {
    case "A": //right
        doSomething();
        break;
    case "B" : //wrong
        doSomethingElse();
        break;
}

To learn more about the PSR-2 coding standard, please refer to the PHP-Fig.

Loading history...
346
          $v_extract_all = false;
347
          $v_listing = false;
348
      break;
349
      case "list" :
0 ignored issues
show
Coding Style introduced by
There must be no space before the colon in a CASE statement

As per the PSR-2 coding standard, there must not be a space in front of the colon in case statements.

switch ($selector) {
    case "A": //right
        doSomething();
        break;
    case "B" : //wrong
        doSomethingElse();
        break;
}

To learn more about the PSR-2 coding standard, please refer to the PHP-Fig.

Loading history...
350
          $v_extract_all = false;
351
          $v_listing = true;
352
      break;
353
      default :
0 ignored issues
show
Coding Style introduced by
There must be no space before the colon in a DEFAULT statement

As per the PSR-2 coding standard, there must not be a space in front of the colon in the default statement.

switch ($expr) {
    default : //wrong
        doSomething();
        break;
}

switch ($expr) {
    default: //right
        doSomething();
        break;
}

To learn more about the PSR-2 coding standard, please refer to the PHP-Fig.

Loading history...
354
        $this->_error('Invalid extract mode ('.$p_mode.')');
355
        return false;
356
    }
357
358
    clearstatcache();
359
360
    while (strlen($v_binary_data = $this->_readBlock()) != 0)
361
    {
362
      $v_extract_file = false;
0 ignored issues
show
Unused Code introduced by
$v_extract_file is not used, you could remove the assignment.

This check looks for variable assignements that are either overwritten by other assignments or where the variable is not used subsequently.

$myVar = 'Value';
$higher = false;

if (rand(1, 6) > 3) {
    $higher = true;
} else {
    $higher = false;
}

Both the $myVar assignment in line 1 and the $higher assignment in line 2 are dead. The first because $myVar is never used and the second because $higher is always overwritten for every possible time line.

Loading history...
363
      $v_extraction_stopped = 0;
364
365
      if (!$this->_readHeader($v_binary_data, $v_header))
366
        return false;
367
368
      if ($v_header['filename'] == '') {
369
        continue;
370
      }
371
372
      // ----- Look for long filename
373
      if ($v_header['typeflag'] == 'L') {
374
        if (!$this->_readLongHeader($v_header))
375
          return false;
376
      }
377
378
      if ((!$v_extract_all) && (is_array($p_file_list))) {
379
        // ----- By default no unzip if the file is not found
380
        $v_extract_file = false;
381
382
        for ($i=0; $i<sizeof($p_file_list); $i++) {
0 ignored issues
show
Performance Best Practice introduced by
It seems like you are calling the size function sizeof() as part of the test condition. You might want to compute the size beforehand, and not on each iteration.

If the size of the collection does not change during the iteration, it is generally a good practice to compute it beforehand, and not on each iteration:

for ($i=0; $i<count($array); $i++) { // calls count() on each iteration
}

// Better
for ($i=0, $c=count($array); $i<$c; $i++) { // calls count() just once
}
Loading history...
383
          // ----- Look if it is a directory
384
          if (substr($p_file_list[$i], -1) == '/') {
385
            // ----- Look if the directory is in the filename path
386
            if ((strlen($v_header['filename']) > strlen($p_file_list[$i]))
387
			    && (substr($v_header['filename'], 0, strlen($p_file_list[$i]))
388
				    == $p_file_list[$i])) {
389
              $v_extract_file = true;
390
              break;
391
            }
392
          }
393
394
          // ----- It is a file, so compare the file names
395
          elseif ($p_file_list[$i] == $v_header['filename']) {
396
            $v_extract_file = true;
397
            break;
398
          }
399
        }
400
      } else {
401
        $v_extract_file = true;
402
      }
403
404
      // ----- Look if this file need to be extracted
405
      if (($v_extract_file) && (!$v_listing))
406
      {
407
        if (($p_remove_path != '')
408
            && (substr($v_header['filename'], 0, $p_remove_path_size)
409
			    == $p_remove_path))
410
          $v_header['filename'] = substr($v_header['filename'],
411
		                                 $p_remove_path_size);
412
        if (($p_path != './') && ($p_path != '/')) {
413
          while (substr($p_path, -1) == '/')
414
            $p_path = substr($p_path, 0, strlen($p_path)-1);
415
416
          if (substr($v_header['filename'], 0, 1) == '/')
417
              $v_header['filename'] = $p_path.$v_header['filename'];
418
          else
419
            $v_header['filename'] = $p_path.'/'.$v_header['filename'];
420
        }
421
        if (file_exists($v_header['filename'])) {
422
          if (   (@is_dir($v_header['filename']))
423
		      && ($v_header['typeflag'] == '')) {
424
            $this->_error('File '.$v_header['filename']
425
			              .' already exists as a directory');
426
            return false;
427
          }
428
          if (   ($this->_isArchive($v_header['filename']))
429
		      && ($v_header['typeflag'] == "5")) {
430
            $this->_error('Directory '.$v_header['filename']
431
			              .' already exists as a file');
432
            return false;
433
          }
434
          if (!is_writeable($v_header['filename'])) {
435
            $this->_error('File '.$v_header['filename']
436
			              .' already exists and is write protected');
437
            return false;
438
          }
439
          if (filemtime($v_header['filename']) > $v_header['mtime']) {
0 ignored issues
show
Unused Code introduced by
This if statement is empty and can be removed.

This check looks for the bodies of if statements that have no statements or where all statements have been commented out. This may be the result of changes for debugging or the code may simply be obsolete.

These if bodies can be removed. If you have an empty if but statements in the else branch, consider inverting the condition.

if (rand(1, 6) > 3) {
//print "Check failed";
} else {
    print "Check succeeded";
}

could be turned into

if (rand(1, 6) <= 3) {
    print "Check succeeded";
}

This is much more concise to read.

Loading history...
440
            // To be completed : An error or silent no replace ?
441
          }
442
        }
443
444
        // ----- Check the directory availability and create it if necessary
445
        elseif (($v_result
446
		         = $this->_dirCheck(($v_header['typeflag'] == "5"
447
				                    ?$v_header['filename']
448
									:dirname($v_header['filename'])))) != 1) {
449
            $this->_error('Unable to create path for '.$v_header['filename']);
450
            return false;
451
        }
452
453
        if ($v_extract_file) {
454
          if ($v_header['typeflag'] == "5") {
455
            if (!@file_exists($v_header['filename'])) {
456
                if (!@mkdir($v_header['filename'], PRADO_CHMOD)) {
457
                    $this->_error('Unable to create directory {'
458
					              .$v_header['filename'].'}');
459
                    return false;
460
                }
461
                chmod($v_header['filename'], PRADO_CHMOD);
462
            }
463
          } else {
464
              if (($v_dest_file = @fopen($v_header['filename'], "wb")) == 0) {
465
                  $this->_error('Error while opening {'.$v_header['filename']
466
				                .'} in write binary mode');
467
                  return false;
468
              } else {
469
                  $n = floor($v_header['size']/512);
470
                  for ($i=0; $i<$n; $i++) {
471
                      $v_content = $this->_readBlock();
472
                      fwrite($v_dest_file, $v_content, 512);
473
                  }
474
            if (($v_header['size'] % 512) != 0) {
475
              $v_content = $this->_readBlock();
476
              fwrite($v_dest_file, $v_content, ($v_header['size'] % 512));
477
            }
478
479
            @fclose($v_dest_file);
0 ignored issues
show
Security Best Practice introduced by
It seems like you do not handle an error condition here. This can introduce security issues, and is generally not recommended.

If you suppress an error, we recommend checking for the error condition explicitly:

// For example instead of
@mkdir($dir);

// Better use
if (@mkdir($dir) === false) {
    throw new \RuntimeException('The directory '.$dir.' could not be created.');
}
Loading history...
480
481
            // ----- Change the file mode, mtime
482
            @touch($v_header['filename'], $v_header['mtime']);
0 ignored issues
show
Security Best Practice introduced by
It seems like you do not handle an error condition here. This can introduce security issues, and is generally not recommended.

If you suppress an error, we recommend checking for the error condition explicitly:

// For example instead of
@mkdir($dir);

// Better use
if (@mkdir($dir) === false) {
    throw new \RuntimeException('The directory '.$dir.' could not be created.');
}
Loading history...
483
            // To be completed
484
            //chmod($v_header[filename], DecOct($v_header[mode]));
485
          }
486
487
          // ----- Check the file size
488
          clearstatcache();
489
          if (filesize($v_header['filename']) != $v_header['size']) {
490
              $this->_error('Extracted file '.$v_header['filename']
491
			                .' does not have the correct file size \''
492
							.filesize($v_header['filename'])
493
							.'\' ('.$v_header['size']
494
							.' expected). Archive may be corrupted.');
495
              return false;
496
          }
497
          }
498
        } else {
499
          $this->_jumpBlock(ceil(($v_header['size']/512)));
500
        }
501
      } else {
502
          $this->_jumpBlock(ceil(($v_header['size']/512)));
503
      }
504
505
      /* TBC : Seems to be unused ...
506
      if ($this->_compress)
507
        $v_end_of_file = @gzeof($this->_file);
508
      else
509
        $v_end_of_file = @feof($this->_file);
510
        */
511
512
      if ($v_listing || $v_extract_file || $v_extraction_stopped) {
513
        // ----- Log extracted files
514
        if (($v_file_dir = dirname($v_header['filename']))
515
		    == $v_header['filename'])
516
          $v_file_dir = '';
517
        if ((substr($v_header['filename'], 0, 1) == '/') && ($v_file_dir == ''))
518
          $v_file_dir = '/';
0 ignored issues
show
Unused Code introduced by
$v_file_dir is not used, you could remove the assignment.

This check looks for variable assignements that are either overwritten by other assignments or where the variable is not used subsequently.

$myVar = 'Value';
$higher = false;

if (rand(1, 6) > 3) {
    $higher = true;
} else {
    $higher = false;
}

Both the $myVar assignment in line 1 and the $higher assignment in line 2 are dead. The first because $myVar is never used and the second because $higher is always overwritten for every possible time line.

Loading history...
519
520
        $p_list_detail[$v_nb++] = $v_header;
521
      }
522
    }
523
524
        return true;
525
    }
526
527
    /**
528
     * Check if a directory exists and create it (including parent
529
     * dirs) if not.
530
     *
531
     * @param string $p_dir directory to check
532
     *
533
     * @return bool true if the directory exists or was created
534
     */
535
    protected function _dirCheck($p_dir)
0 ignored issues
show
Coding Style Naming introduced by
The parameter $p_dir is not named in camelCase.

This check marks parameter names that have not been written in camelCase.

In camelCase names are written without any punctuation, the start of each new word being marked by a capital letter. Thus the name database connection string becomes databaseConnectionString.

Loading history...
536
    {
537
        if ((@is_dir($p_dir)) || ($p_dir == ''))
538
            return true;
539
540
        $p_parent_dir = dirname($p_dir);
541
542
        if (($p_parent_dir != $p_dir) &&
543
            ($p_parent_dir != '') &&
544
            (!$this->_dirCheck($p_parent_dir)))
545
             return false;
546
547
        if (!@mkdir($p_dir, PRADO_CHMOD)) {
548
            $this->_error("Unable to create directory '$p_dir'");
549
            return false;
550
        }
551
        chmod($p_dir,PRADO_CHMOD);
552
553
        return true;
554
    }
555
556
    protected function _translateWinPath($p_path, $p_remove_disk_letter=true)
0 ignored issues
show
Coding Style Naming introduced by
The parameter $p_path is not named in camelCase.

This check marks parameter names that have not been written in camelCase.

In camelCase names are written without any punctuation, the start of each new word being marked by a capital letter. Thus the name database connection string becomes databaseConnectionString.

Loading history...
Coding Style Naming introduced by
The parameter $p_remove_disk_letter is not named in camelCase.

This check marks parameter names that have not been written in camelCase.

In camelCase names are written without any punctuation, the start of each new word being marked by a capital letter. Thus the name database connection string becomes databaseConnectionString.

Loading history...
557
    {
558
      if (substr(PHP_OS, 0, 3) == 'WIN') {
559
          // ----- Look for potential disk letter
560
          if (   ($p_remove_disk_letter)
561
		      && (($v_position = strpos($p_path, ':')) != false)) {
0 ignored issues
show
Bug Best Practice introduced by
It seems like you are loosely comparing $v_position = strpos($p_path, ':') of type integer to the boolean false. If you are specifically checking for non-zero, consider using something more explicit like > 0 or !== 0 instead.
Loading history...
562
              $p_path = substr($p_path, $v_position+1);
563
          }
564
          // ----- Change potential windows directory separator
565
          if ((strpos($p_path, '\\') > 0) || (substr($p_path, 0,1) == '\\')) {
566
              $p_path = strtr($p_path, '\\', '/');
567
          }
568
      }
569
      return $p_path;
570
    }
571
}
572