powershell ftps upload causing error "DATA connection terminated without ssl shutdown" on stream close

1.7k Views Asked by At

I have the following code I have built upon something I found online (can't remember where)

$Server = XXXXX
$port = XXX
$remotepath='/'
$username = 'XXXX'
#$passward = ConvertTo-SecureString -AsPlainText 'XXXX' -Force 
$password = 'XXXXX'
$file = "path-to-file"

$f = Get-Item $File
$remote_url = "ftp://$Server`:$Port$RemotePath"

[System.Net.FtpWebRequest]$req = [System.Net.FtpWebRequest]::Create($remote_url + $f.Name)
# [System.Net.FtpWebRequest]$req = [System.Net.WebRequest]::Create($remote_url + $f.Name)
$req.Credentials = New-Object System.Net.NetworkCredential($Username, $Password)
$req.Method = [System.Net.WebRequestMethods+Ftp]::UploadFile
$req.EnableSsl = $true
$req.UseBinary = $true
$req.UsePassive = $true
$req.KeepAlive = $true
$req.ConnectionGroupName = "FTPS_$Username"
[System.Net.ServicePointManager]::ServerCertificateValidationCallback = {return $true}
$fs = New-Object IO.FileStream $f.FullName, 'Open', 'Read'
$req.ContentLength = $f.Length
$ftpStream = $req.GetRequestStream()

$b = New-Object Byte[](10000)

do {
   $ftpStream.Write($b, 0, $r)
   $r = $fs.Read($b, 0, 10000)
} while ($r -ne 0)

if ($fs -ne $null) { $fs.Dispose() }
$ftpStream.Close()    
$resp = $req.GetResponse()
$resp.StatusDescription
$resp.Close()

the file is uploaded fine, however when the following line is tiggered:

$ftpStream.Close() 

it causes on the server (vsftp on ubuntu) the following error:

Sun Mar 31 13:58:13 2019 [pid 3779] [XXXX] DEBUG: Client "XXX.XXX.XXX.XXX", "DATA connection terminated without SSL shutdown. Buggy client! Integrity of upload cannot be asserted."
Sun Mar 31 13:58:13 2019 [pid 3780] [XXXX] FTP response: Client "XXX.XXX.XXX.XXX", "426 Failure reading network stream."
Sun Mar 31 13:58:13 2019 [pid 3780] [XXXX] FAIL UPLOAD: Client "XXX.XXX.XXX.XXX", "/file-path", 36851 bytes, 0.21Kbyte/sec
Sun Mar 31 13:58:13 2019 [pid 3779] [XXXX] DEBUG: Client "XXX.XXX.XXX.XXX", "Control connection terminated without SSL shutdown."

which in return causes the following line in my code:

$resp = $req.GetResponse()

to fail with:

Exception calling "GetResponse" with "0" argument(s): "The remote server returned an error: (426) Connection closed; transfer aborted."
At line:3 char:13
+             $resp = $req.GetResponse()
+             ~~~~~~~~~~~~~~~~~~~~~~~~~~
    + CategoryInfo          : NotSpecified: (:) [], MethodInvocationException
    + FullyQualifiedErrorId : WebException

all help will be very much appreciated as it is really important that the script will reliably be able to alert if the upload failed or succeeded.

============= UPDATE =============

well I am not posting this update as an answer (at least not yet) because it is more of a workaround than a proper solution.

I found this post in Chinese: https://blog.yuwu.me/?p=1159 which I understood nothing from (It was literally Chinese to me) but he did quota part of vsftpd documentation:

strict_ssl_read_eof If enabled, SSL data uploads are required to terminate via SSL, not an EOF on the socket. This option is required to be sure that an attacker did not terminate an upload prematurely with a faked TCP FIN. Unfortu‐ nately, it is not enabled by default because so few clients get it right. (New in v2.0.7).

Default: NO

I added this setting to my config, and lo and behold - my script managed to complete successfully. However, server continues to throw an error of "DATA connection terminated without SSL shutdown. Buggy client! Integrity of upload cannot be asserted." but at least it isn't terminating my control channel any more.

obviously a real solution would be terminating the data connection properly, so hopefully someone will be able to successfully solve this issue.

0

There are 0 best solutions below