Commit: a93a462dcefd62e07963dd2da506fbb3409c88b5
Author: Andreas Streichardt <andreas.streicha...@gmail.com> Fri, 12
Oct 2012 11:02:33 +0200
Committer: Stanislav Malyshev <s...@php.net> Sun, 4 Aug 2013 19:31:30 -0700
Parents: 8d86597d7368460383a33a4399ea7a8b244cd6fa
Branches: PHP-5.4 PHP-5.5 master
Link:
http://git.php.net/?p=php-src.git;a=commitdiff;h=a93a462dcefd62e07963dd2da506fbb3409c88b5
Log:
First fixes for a 64bit compatible ftp extension
Changed paths:
M ext/ftp/ftp.c
M ext/ftp/ftp.h
M ext/ftp/php_ftp.c
A ext/ftp/tests/filesize_large.phpt
A ext/ftp/tests/ftp_nb_get_large.phpt
M ext/ftp/tests/server.inc
diff --git a/ext/ftp/ftp.c b/ext/ftp/ftp.c
index dd41f02..0d6704f 100644
--- a/ext/ftp/ftp.c
+++ b/ext/ftp/ftp.c
@@ -612,7 +612,7 @@ ftp_chmod(ftpbuf_t *ftp, const int mode, const char
*filename, const int filenam
/* {{{ ftp_alloc
*/
int
-ftp_alloc(ftpbuf_t *ftp, const int size, char **response)
+ftp_alloc(ftpbuf_t *ftp, const long size, char **response)
{
char buffer[64];
@@ -620,8 +620,8 @@ ftp_alloc(ftpbuf_t *ftp, const int size, char **response)
return 0;
}
- snprintf(buffer, sizeof(buffer) - 1, "%d", size);
-
+ snprintf(buffer, sizeof(buffer) - 1, "%ld", size);
+
if (!ftp_putcmd(ftp, "ALLO", buffer)) {
return 0;
}
@@ -787,7 +787,7 @@ ftp_pasv(ftpbuf_t *ftp, int pasv)
/* {{{ ftp_get
*/
int
-ftp_get(ftpbuf_t *ftp, php_stream *outstream, const char *path, ftptype_t
type, int resumepos TSRMLS_DC)
+ftp_get(ftpbuf_t *ftp, php_stream *outstream, const char *path, ftptype_t
type, long resumepos TSRMLS_DC)
{
databuf_t *data = NULL;
int lastch;
@@ -808,11 +808,7 @@ ftp_get(ftpbuf_t *ftp, php_stream *outstream, const char
*path, ftptype_t type,
ftp->data = data;
if (resumepos > 0) {
- if (resumepos > 2147483647) {
- php_error_docref(NULL TSRMLS_CC, E_WARNING, "PHP cannot
handle files greater than 2147483647 bytes.");
- goto bail;
- }
- snprintf(arg, sizeof(arg), "%u", resumepos);
+ snprintf(arg, sizeof(arg), "%ld", resumepos);
if (!ftp_putcmd(ftp, "REST", arg)) {
goto bail;
}
@@ -885,10 +881,10 @@ bail:
/* {{{ ftp_put
*/
int
-ftp_put(ftpbuf_t *ftp, const char *path, php_stream *instream, ftptype_t type,
int startpos TSRMLS_DC)
+ftp_put(ftpbuf_t *ftp, const char *path, php_stream *instream, ftptype_t type,
long startpos TSRMLS_DC)
{
databuf_t *data = NULL;
- int size;
+ long size;
char *ptr;
int ch;
char arg[11];
@@ -905,11 +901,7 @@ ftp_put(ftpbuf_t *ftp, const char *path, php_stream
*instream, ftptype_t type, i
ftp->data = data;
if (startpos > 0) {
- if (startpos > 2147483647) {
- php_error_docref(NULL TSRMLS_CC, E_WARNING, "PHP cannot
handle files with a size greater than 2147483647 bytes.");
- goto bail;
- }
- snprintf(arg, sizeof(arg), "%u", startpos);
+ snprintf(arg, sizeof(arg), "%ld", startpos);
if (!ftp_putcmd(ftp, "REST", arg)) {
goto bail;
}
@@ -966,7 +958,7 @@ bail:
/* {{{ ftp_size
*/
-int
+long
ftp_size(ftpbuf_t *ftp, const char *path)
{
if (ftp == NULL) {
@@ -981,7 +973,7 @@ ftp_size(ftpbuf_t *ftp, const char *path)
if (!ftp_getresp(ftp) || ftp->resp != 213) {
return -1;
}
- return atoi(ftp->inbuf);
+ return atol(ftp->inbuf);
}
/* }}} */
@@ -1143,7 +1135,7 @@ ftp_putcmd(ftpbuf_t *ftp, const char *cmd, const char
*args)
int
ftp_readline(ftpbuf_t *ftp)
{
- int size, rcvd;
+ long size, rcvd;
char *data, *eol;
/* shift the extra to the front */
@@ -1236,7 +1228,8 @@ ftp_getresp(ftpbuf_t *ftp)
int
my_send(ftpbuf_t *ftp, php_socket_t s, void *buf, size_t len)
{
- int n, size, sent;
+ long size, sent;
+ int n;
size = len;
while (size) {
@@ -1719,7 +1712,7 @@ bail:
/* {{{ ftp_nb_get
*/
int
-ftp_nb_get(ftpbuf_t *ftp, php_stream *outstream, const char *path, ftptype_t
type, int resumepos TSRMLS_DC)
+ftp_nb_get(ftpbuf_t *ftp, php_stream *outstream, const char *path, ftptype_t
type, long resumepos TSRMLS_DC)
{
databuf_t *data = NULL;
char arg[11];
@@ -1737,14 +1730,7 @@ ftp_nb_get(ftpbuf_t *ftp, php_stream *outstream, const
char *path, ftptype_t typ
}
if (resumepos>0) {
- /* We are working on an architecture that supports 64-bit
integers
- * since php is 32 bit by design, we bail out with warning
- */
- if (resumepos > 2147483647) {
- php_error_docref(NULL TSRMLS_CC, E_WARNING, "PHP cannot
handle files greater than 2147483648 bytes.");
- goto bail;
- }
- snprintf(arg, sizeof(arg), "%u", resumepos);
+ snprintf(arg, sizeof(arg), "%ld", resumepos);
if (!ftp_putcmd(ftp, "REST", arg)) {
goto bail;
}
@@ -1843,7 +1829,7 @@ bail:
/* {{{ ftp_nb_put
*/
int
-ftp_nb_put(ftpbuf_t *ftp, const char *path, php_stream *instream, ftptype_t
type, int startpos TSRMLS_DC)
+ftp_nb_put(ftpbuf_t *ftp, const char *path, php_stream *instream, ftptype_t
type, long startpos TSRMLS_DC)
{
databuf_t *data = NULL;
char arg[11];
@@ -1858,11 +1844,7 @@ ftp_nb_put(ftpbuf_t *ftp, const char *path, php_stream
*instream, ftptype_t type
goto bail;
}
if (startpos > 0) {
- if (startpos > 2147483647) {
- php_error_docref(NULL TSRMLS_CC, E_WARNING, "PHP cannot
handle files with a size greater than 2147483647 bytes.");
- goto bail;
- }
- snprintf(arg, sizeof(arg), "%u", startpos);
+ snprintf(arg, sizeof(arg), "%ld", startpos);
if (!ftp_putcmd(ftp, "REST", arg)) {
goto bail;
}
@@ -1899,7 +1881,7 @@ bail:
int
ftp_nb_continue_write(ftpbuf_t *ftp TSRMLS_DC)
{
- int size;
+ long size;
char *ptr;
int ch;
diff --git a/ext/ftp/ftp.h b/ext/ftp/ftp.h
index c7db457..69de7db 100644
--- a/ext/ftp/ftp.h
+++ b/ext/ftp/ftp.h
@@ -146,7 +146,7 @@ int ftp_chmod(ftpbuf_t *ftp, const int mode, const
char *filename, const int fi
* however some servers will not accept STOR or APPE until ALLO is confirmed.
* If response is passed, it is estrdup()ed from ftp->inbuf and must be freed
* or assigned to a zval returned to the user */
-int ftp_alloc(ftpbuf_t *ftp, const int size, char **response);
+int ftp_alloc(ftpbuf_t *ftp, const long size, char **response);
/* returns a NULL-terminated array of filenames in the given path
* or NULL on error. the return array must be freed (but don't
@@ -169,15 +169,15 @@ int ftp_pasv(ftpbuf_t *ftp, int pasv);
/* retrieves a file and saves its contents to outfp
* returns true on success, false on error
*/
-int ftp_get(ftpbuf_t *ftp, php_stream *outstream, const char *path,
ftptype_t type, int resumepos TSRMLS_DC);
+int ftp_get(ftpbuf_t *ftp, php_stream *outstream, const char *path,
ftptype_t type, long resumepos TSRMLS_DC);
/* stores the data from a file, socket, or process as a file on the remote
server
* returns true on success, false on error
*/
-int ftp_put(ftpbuf_t *ftp, const char *path, php_stream *instream,
ftptype_t type, int startpos TSRMLS_DC);
+int ftp_put(ftpbuf_t *ftp, const char *path, php_stream *instream,
ftptype_t type, long startpos TSRMLS_DC);
/* returns the size of the given file, or -1 on error */
-int ftp_size(ftpbuf_t *ftp, const char *path);
+long ftp_size(ftpbuf_t *ftp, const char *path);
/* returns the last modified time of the given file, or -1 on error */
time_t ftp_mdtm(ftpbuf_t *ftp, const char *path);
@@ -194,12 +194,12 @@ int ftp_site(ftpbuf_t *ftp, const char
*cmd);
/* retrieves part of a file and saves its contents to outfp
* returns true on success, false on error
*/
-int ftp_nb_get(ftpbuf_t *ftp, php_stream *outstream, const char
*path, ftptype_t type, int resumepos TSRMLS_DC);
+int ftp_nb_get(ftpbuf_t *ftp, php_stream *outstream, const char
*path, ftptype_t type, long resumepos TSRMLS_DC);
/* stores the data from a file, socket, or process as a file on the remote
server
* returns true on success, false on error
*/
-int ftp_nb_put(ftpbuf_t *ftp, const char *path, php_stream
*instream, ftptype_t type, int startpos TSRMLS_DC);
+int ftp_nb_put(ftpbuf_t *ftp, const char *path, php_stream
*instream, ftptype_t type, long startpos TSRMLS_DC);
/* continues a previous nb_(f)get command
*/
diff --git a/ext/ftp/php_ftp.c b/ext/ftp/php_ftp.c
index 7307193..da22e0b 100644
--- a/ext/ftp/php_ftp.c
+++ b/ext/ftp/php_ftp.c
@@ -784,8 +784,8 @@ PHP_FUNCTION(ftp_nb_fget)
ftptype_t xtype;
php_stream *stream;
char *file;
- int file_len, ret;
- long mode, resumepos=0;
+ int file_len;
+ long mode, resumepos=0, ret;
if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "rrsl|l", &z_ftp,
&z_file, &file, &file_len, &mode, &resumepos) == FAILURE) {
return;
@@ -968,9 +968,7 @@ PHP_FUNCTION(ftp_nb_get)
RETURN_LONG(PHP_FTP_FAILED);
}
- if (ret == PHP_FTP_FINISHED) {
- php_stream_close(outstream);
- }
+ php_stream_close(outstream);
RETURN_LONG(ret);
}
@@ -982,7 +980,7 @@ PHP_FUNCTION(ftp_nb_continue)
{
zval *z_ftp;
ftpbuf_t *ftp;
- int ret;
+ long ret;
if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "r", &z_ftp) ==
FAILURE) {
return;
@@ -1120,7 +1118,7 @@ PHP_FUNCTION(ftp_put)
ftpbuf_t *ftp;
ftptype_t xtype;
char *remote, *local;
- int remote_len, local_len;
+ long remote_len, local_len;
long mode, startpos=0;
php_stream *instream;
@@ -1173,8 +1171,8 @@ PHP_FUNCTION(ftp_nb_put)
ftpbuf_t *ftp;
ftptype_t xtype;
char *remote, *local;
- int remote_len, local_len, ret;
- long mode, startpos=0;
+ int remote_len, local_len;
+ long mode, startpos=0, ret;
php_stream *instream;
if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "rppl|l", &z_ftp,
&remote, &remote_len, &local, &local_len, &mode, &startpos) == FAILURE) {
diff --git a/ext/ftp/tests/filesize_large.phpt
b/ext/ftp/tests/filesize_large.phpt
new file mode 100644
index 0000000..05f12a3
--- /dev/null
+++ b/ext/ftp/tests/filesize_large.phpt
@@ -0,0 +1,23 @@
+--TEST--
+Verify php can handle filesizes >32bit
+--SKIPIF--
+<?php
+require 'skipif.inc';
+if (2147483647 == PHP_INT_MAX) {
+ die('skip 64-bit only');
+}
+?>
+--FILE--
+<?php
+require 'server.inc';
+
+$ftp = ftp_connect('127.0.0.1', $port);
+if (!$ftp) die("Couldn't connect to the server");
+
+ftp_login($ftp, 'user', 'pass');
+var_dump(ftp_size($ftp, 'largefile'));
+
+ftp_close($ftp);
+?>
+--EXPECT--
+int(5368709120)
diff --git a/ext/ftp/tests/ftp_nb_get_large.phpt
b/ext/ftp/tests/ftp_nb_get_large.phpt
new file mode 100644
index 0000000..3fbf2a4
--- /dev/null
+++ b/ext/ftp/tests/ftp_nb_get_large.phpt
@@ -0,0 +1,36 @@
+--TEST--
+Testing ftp_nb_fget can handle large files incl. resume
+--SKIPIF--
+<?php
+require 'skipif.inc';
+if (2147483647 == PHP_INT_MAX) {
+ die('skip ot supported on this system');
+}
+if (disk_free_space(__DIR__) < 10*1024*1024*1024) {
+ die('not enough disk space');
+}
+?>
+--FILE--
+<?php
+require 'server.inc';
+
+$ftp = ftp_connect('127.0.0.1', $port);
+ftp_login($ftp, 'user', 'pass');
+if (!$ftp) die("Couldn't connect to the server");
+
+$local_file = dirname(__FILE__) . DIRECTORY_SEPARATOR . "localfile.txt";
+touch($local_file);
+ftp_nb_get($ftp, $local_file, 'fget_large.txt', FTP_BINARY, 5368709119);
+$fp = fopen($local_file, 'r');
+fseek($fp, 5368709119);
+var_dump(fread($fp, 1));
+var_dump(filesize($local_file));
+fclose($fp);
+?>
+--CLEAN--
+<?php
+@unlink(dirname(__FILE__) . DIRECTORY_SEPARATOR . "localfile.txt");
+?>
+--EXPECT--
+string(1) "X"
+int(5368709120)
diff --git a/ext/ftp/tests/server.inc b/ext/ftp/tests/server.inc
index 8617880..7dc8fa0 100644
--- a/ext/ftp/tests/server.inc
+++ b/ext/ftp/tests/server.inc
@@ -357,7 +357,17 @@ if ($pid) {
$transfer_type = $ascii? 'ASCII' :
'BINARY' ;
fputs($fs, "Bar\r\n");
fputs($s, "226 Closing data
Connection.\r\n");
- break;
+ break;
+ case "fget_large":
+ fputs($s, "150 File status okay; about
to open data connection.\r\n");
+ $transfer_type = $ascii? 'ASCII' :
'BINARY' ;
+ if ($GLOBALS['rest_pos'] ==
'5368709119') {
+ fputs($fs, "X");
+ } else {
+ fputs($fs, "Y");
+ }
+ fputs($s, "226 Closing data
Connection.\r\n");
+ break;
default:
fputs($s, "550 {$matches[1]}: No such
file or directory \r\n");
break;
@@ -393,11 +403,12 @@ if ($pid) {
}elseif (preg_match('/^LIST no_exists\//', $buf, $matches)) {
fputs($s, "425 Error establishing connection\r\n");
- }elseif (preg_match('/^REST \d+/', $buf, $matches)) {
+ }elseif (preg_match('/^REST (\d+)/', $buf, $matches)) {
+ $GLOBALS['rest_pos'] = $matches[1];
fputs($s, "350 OK\r\n");
- }
-
- else {
+ }elseif (preg_match('/^SIZE largefile/', $buf)) {
+ fputs($s, "213 5368709120\r\n");
+ }else {
fputs($s, "500 Syntax error, command
unrecognized.\r\n");
dump_and_exit($buf);
}
@@ -407,4 +418,4 @@ if ($pid) {
}
fclose($socket);
-?>
\ No newline at end of file
+?>
--
PHP CVS Mailing List (http://www.php.net/)
To unsubscribe, visit: http://www.php.net/unsub.php