加密 .txt 文件错误 - 进程无法访问文件

Encrypting .txt File Erroring - Process Cannot Access File

我正在尝试加密在我的应用程序中创建的 .txt 文件。

要创建此文件,我使用以下代码:

Dim fileExists As Boolean = File.Exists(directorypath & "dbpw.txt")
If File.Exists(directorypath & "dbpw.txt") = False Then
   Using sw As New StreamWriter(File.Open(directorypath & "dbpw.txt", FileMode.Create))
         IIf(fileExists, "", "")
         sw.Close()
   End Using
End If

然后,为了写入和加密文件,我使用了以下代码,调用了我根据 Internet 上的示例调整的子例程。

bytKey = CreateKey(txtCode.Text)
bytIV = CreateIV(txtCode.Text)

EncryptOrDecryptFile(directorypath & "dbpw.txt", directorypath & "dbpw.txt", bytKey, bytIV, CryptoAction.ActionEncrypt)

当代码到达最后一行时,调用 EncryptOrDecrypt 子例程,抛出错误

The process cannot access the file 'myDirectoryPath\dbpw.txt' because it is being used by another process

释放文件需要做什么?

我也尝试过将 File.CreateFile.Encrypt 一起使用,但无论哪种方式都会抛出相同的错误。

EncryptOrDecryptFile()

代码
Public Sub EncryptOrDecryptFile(ByVal strInputFile As String, ByVal strOutputFile As String, ByVal bytKey() As Byte, ByVal bytIV() As Byte, ByVal Direction As CryptoAction)

    Try
        fsInput = New System.IO.FileStream(strInputFile, FileMode.Open, FileAccess.Read)
        fsOutput = New System.IO.FileStream(strOutputFile, FileMode.OpenOrCreate, FileAccess.Write)
        fsOutput.SetLength(0)
        ' Currently fails, file not being released for read/write once it's created.

        Dim bytBuffer(4096) As Byte
        Dim lngBytesProcessed As Long = 0
        Dim lngFileLength As Long = fsInput.Length
        Dim intBytesInCurrentBlock As Integer
        Dim csCryptoStream As CryptoStream

        Dim cspRijndael As New System.Security.Cryptography.RijndaelManaged

        Select Case Direction
            Case CryptoAction.ActionEncrypt
                csCryptoStream = New CryptoStream(fsOutput, _
                cspRijndael.CreateEncryptor(bytKey, bytIV), _
                CryptoStreamMode.Write)

            Case CryptoAction.ActionDecrypt
                csCryptoStream = New CryptoStream(fsOutput, _
                cspRijndael.CreateDecryptor(bytKey, bytIV), _
                CryptoStreamMode.Write)
        End Select

        While lngBytesProcessed < lngFileLength
            intBytesInCurrentBlock = fsInput.Read(bytBuffer, 0, 4096)

            csCryptoStream.Write(bytBuffer, 0, intBytesInCurrentBlock)

            lngBytesProcessed = lngBytesProcessed + _
                                    CLng(intBytesInCurrentBlock)
        End While

        csCryptoStream.Close()
        fsInput.Close()
        fsOutput.Close()

    Catch ex As Exception
        errorLog(ex)

    End Try
End Sub

连同您传递给它的参数,在您的 EncryptOrDecryptFile() 方法中,您试图打开同一个文件的两个流(fsInputfsOutput)。一旦你打开 fsInput 它就拥有文件的独占访问权限,使得 fsOutput 无法打开它进行写入。

您唯一的选择是:

  • 重命名输入文件或输出文件,以便两个流打开两个不同的文件,或者:

  • 为文件打开一个 "global" 加密流,每次要向其中写入数据时都会使用它。

注意: 将来有人可能会建议您用 FileShare.Write 打开 fsInput 以允许其他进程打开文件进行写入,因此也允许 fsOutput 流也写入它。 - 不要那样做!

在您读取文件时允许其他进程写入文件可能会导致问题,即使它是您的 fsOutput 流。这是因为您永远无法知道将要写入多少 数据fsOutput。如果加密数据比原始数据长怎么办?这将导致它覆盖 fsInput 接下来要读取的内容,从而损坏文件。