无法读取Stream中的XML

时间:2016-11-23 16:13:49

标签: vb.net visual-studio stream

我对XML文件和Stream有点问题。我在Stream中创建并保存XML文件,加密Stream,然后将其保存到普通文件中。

我想读取这个XML,但是如果我使用FileStream并将解密文件写入磁盘,我只能这样做。

有没有办法解密并将此文件保存在内存中?

这是我的代码:

XMLDecriptato = New MemoryStream()
Using stream_readerX As New StreamReader(XMLDecriptato, Text.Encoding.UTF8)

    XMLDecriptato.SetLength(0)
    Dim FStreamCrypted As FileStream = File.Open(varTitolo, FileMode.Open, FileAccess.Read)
    FStreamCrypted.Seek(0, SeekOrigin.Begin)
    CryptStream(Pass, FStreamCrypted, XMLDecriptato, Type.Decrypt)

    'try to read the stream
    Dim xDocumentX As New XmlDocument()
    xDocumentX.Load(stream_readerX) 'here is the error
End Using

它一直说Stream已关闭。我也尝试过另一种方式。唯一有效的方法是使用FileStream将流写入硬盘。

那就是加密/解密子:

Public Sub CryptStream(ByVal Psw As String, ByVal IN_Stream As Stream, ByVal OUT_Stream As Stream, ByVal CrtType As CryptType)
    Dim AES_Provider As New AesCryptoServiceProvider()

    Dim Key_Size_Bits As Integer = 0
    For i As Integer = 1024 To 1 Step -1
        If (aes_provider.ValidKeySize(i)) Then
            Key_Size_Bits = i
            Exit For
        End If
    Next i

    Dim Block_Size_Bits As Integer = AES_Provider.BlockSize
    Dim Key() As Byte = Nothing
    Dim IV() As Byte = Nothing
    Dim Salt() As Byte = "//my salt//"
    MakeKeyAndIV(Psw, Salt, Key_Size_Bits, Block_Size_Bits, Key, IV)

    Dim Crypto_Transform As ICryptoTransform = Nothing

    Select Case CrtType
        Case CryptType.Encrypt
            Crypto_Transform = AES_Provider.CreateEncryptor(key, iv)
        Case CryptType.Decrypt
            Crypto_Transform = AES_Provider.CreateDecryptor(key, iv)
    End Select
    If Crypto_Transform Is Nothing Then Exit Sub

    Try
        Using Crypto_Stream As New CryptoStream(OUT_Stream, Crypto_Transform, CryptoStreamMode.Write)
            Const Block_Size As Integer = 1024
            Dim Buffer(Block_Size) As Byte
            Dim Bytes_Read As Integer
            Do
                Bytes_Read = IN_Stream.Read(Buffer, 0, Block_Size)
                If (Bytes_Read = 0) Then Exit Do

                Crypto_Stream.Write(Buffer, 0, Bytes_Read)
            Loop
        End Using
    Catch ex As Exception
    End Try

    Crypto_Transform.Dispose()
End Sub

1 个答案:

答案 0 :(得分:1)

事实证明,当Using/End Using block调用def时, $scope.changeAllValues = function() { angular.forEach($scope.names, function(item) { item["value"] = 1; }) } 也会处理基础流(在本例中为CryptoStream.Dispose())。检查Microsoft's Reference Source

可以确认此行为

由于CryptoStream.NET 4.5 and up以来没有像MemoryStream那样的CryptoStream标记,我删除了LeaveOpen块并写了我自己为你的方法打电话。

变化:

StreamReader

由于数据将被输入Using,其位置将发生变化,因此您在加载XML文档之前也必须重置它:

Public Sub CryptStream(ByVal Psw As String, ByVal IN_Stream As Stream, ByVal OUT_Stream As Stream, ByVal CrtType As CryptType, Optional ByVal LeaveOpen As Boolean = False)
    ...code...

    Try
        Dim Crypto_Stream As New CryptoStream(OUT_Stream, Crypto_Transform, CryptoStreamMode.Write)

        Const Block_Size As Integer = 1024
        Dim Buffer(Block_Size) As Byte
        Dim Bytes_Read As Integer
        Do
            Bytes_Read = IN_Stream.Read(Buffer, 0, Block_Size)
            If (Bytes_Read = 0) Then Exit Do

            Crypto_Stream.Write(Buffer, 0, Bytes_Read)
        Loop

        If Crypto_Stream.HasFlushedFinalBlock = False Then Crypto_Stream.FlushFinalBlock()

        If LeaveOpen = False Then
            Crypto_Stream.Dispose()
        End If
    Catch ex As Exception
    End Try

    ...code...
End Sub

您可能已经注意到我删除了MemoryStream行。这是因为您刚刚打开了流并且没有对其进行任何操作,因此该位置已经为0。

希望这有帮助!