Index: kioslave/ftp/ftp.cc =================================================================== --- kioslave/ftp/ftp.cc.orig +++ kioslave/ftp/ftp.cc @@ -1275,6 +1275,16 @@ bool Ftp::ftpRename( const QString & src return false; } + // Must check if dst already exists, RNFR+RNTO overwrites by default (#127793). + if (ftpFileExists(dst)) { + error(ERR_FILE_ALREADY_EXIST, dst); + return false; + } + if (ftpFolder(dst, false)) { + error(ERR_DIR_ALREADY_EXIST, dst); + return false; + } + int pos = src.findRev("/"); if( !ftpFolder(src.left(pos+1), false) ) return false; @@ -2406,6 +2416,19 @@ bool Ftp::ftpSize( const QString & path, return true; } +bool Ftp::ftpFileExists(const QString& path) +{ + QCString buf; + buf = "SIZE "; + buf += remoteEncoding()->encode(path); + if( !ftpSendCmd( buf ) || (m_iRespType != 2) ) + return false; + + // skip leading "213 " (response code) + const char* psz = ftpResponse(4); + return psz != 0; +} + // Today the differences between ASCII and BINARY are limited to // CR or CR/LF line terminators. Many servers ignore ASCII (like // win2003 -or- vsftp with default config). In the early days of Index: kioslave/ftp/ftp.h =================================================================== --- kioslave/ftp/ftp.h.orig +++ kioslave/ftp/ftp.h @@ -350,6 +350,11 @@ private: /** * Set the current working directory, but only if not yet current */ + bool ftpFileExists(const QString& path); + + /** + * Set the current working directory, but only if not yet current + */ bool ftpFolder(const QString& path, bool bReportError); /**