Index: twisted/test/test_ftp.py
===================================================================
--- twisted/test/test_ftp.py	(revision 30839)
+++ twisted/test/test_ftp.py	(working copy)
@@ -422,7 +422,34 @@
         d2.addErrback(eb)
         return defer.gatherResults([d1, d2])
 
+    def test_STORwriteError(self):
+        """
+        Any errors during writing a file inside a STOR should be returned to
+        the client.
+        """
+        # Make a failing file writer.
+        class FailingFileWriter(ftp._FileWriter):
+            def receive(self):
+                return defer.fail(ftp.IsNotADirectoryError("blah"))
 
+        def failing_stor(a, b):
+            return defer.succeed(FailingFileWriter(None))
+
+        # Monkey patch the shell so it returns a file writer that will
+        # fail.
+        self.patch(ftp.FTPAnonymousShell, 'openForWriting', failing_stor)
+
+        def eb(res):
+            self.flushLoggedErrors()
+            res.trap(ftp.CommandFailed)
+            self.assertEquals(
+                res.value.args[0][0],
+                "550 Cannot rmd, ('blah',) is not a directory")
+        d1, d2 = self.client.storeFile('failing_file')
+        d2.addErrback(eb)
+        return defer.gatherResults([d1, d2])
+
+
 class FTPServerPasvDataConnectionTestCase(FTPServerTestCase):
     def _makeDataConnection(self, ignored=None):
         # Establish a passive data connection (i.e. client connecting to
Index: twisted/protocols/ftp.py
===================================================================
--- twisted/protocols/ftp.py	(revision 30839)
+++ twisted/protocols/ftp.py	(working copy)
@@ -1112,6 +1112,8 @@
         def ebSent(err):
             log.msg("Unexpected error receiving file from client:")
             log.err(err)
+            if err.check(FTPCmdError):
+                return (err.value.errorCode, err.value.errorMessage)
             return (CNX_CLOSED_TXFR_ABORTED,)
 
         def cbConsumer(cons):
Index: twisted/topfiles/4909.feature
===================================================================
--- twisted/topfiles/4909.feature	(revision 0)
+++ twisted/topfiles/4909.feature	(revision 0)
@@ -0,0 +1,2 @@
+twisted.protocols.ftp.FTP.ftp_STOR now catches `FTPCmdError`s raised by
+the file writer, and returns the error back to the client.
