将对象序列化为加密的 std::fstream (C++)

Kha*_*tur 4 c++ std

有没有办法创建加密的文件流?

我想做这样的事情:

string myString;
fstream myStream;

myStream.create("my path", "my password", cipherAlgorithm);
myStream.write(myString); - this code saves my string to an encrypted stream
myStream.close();
Run Code Online (Sandbox Code Playgroud)

谢谢。

Ben*_*n J 5

我建议有一个接收器对象,一种您写入的设备。接收器可以包裹在升压流中。然后可以像任何“标准”输出流一样写入流

#ifndef ENCRYPTION_SINK_HPP__
#define ENCRYPTION_SINK_HPP__

#include <boost/iostreams/categories.hpp>  // sink_tag
#include <iosfwd>                          // streamsize    
#include <string>
#include <iostream>

class EncryptionSink
{
  public:
    typedef char                          char_type;
    typedef boost::iostreams::sink_tag    category;

    /**
     * @param underlyingStream where the data is actually written
     * @param key the key to use during encryption 
     * @note we could pass in a path rather than a stream and construct the
     * underlying stream internally. But doing it this way affords the 
     * flexibility of using any ostream type e.g. ofstream, ostringstream, 
     * cout etc.
     */ 
    EncryptionSink(std::ostream &underlyingStream, std::string const &key);

    /**
     * @param buf the data that you write
     * @param n number of bytes to write
     * @return the number of bytes written
     */
    std::streamsize write(char_type const * const buf, std::streamsize const n) const;
    ~EncryptionSink();

    private:
        std::ostream &m_underlyingStream;
        std::string const m_key;
};

#endif // ENCRYPTION_SINK_HPP__
Run Code Online (Sandbox Code Playgroud)

上面的类采用底层流(或 FILE 句柄,如果您愿意)并使用您的加密算法所需的任何转换在 write 的实际“.cpp”实现中写入它。例如,以下实现应用了 XOR 转换(我认为这是 XOR,我的知识充其量是生疏的):

EncryptionSink::EncryptionSink(std::ostream &underlyingStream, std::string const &key)
    : m_underlyingStream(underlyingStream)
    , m_key(key)
{}

std::streamsize 
EncryptionSink::write(char_type const * const buf, std::streamsize const n) const
{
    std::stringstream ss;
    std::string::size_type t = 0;
    for(unsigned long i = 0; i < n ; ++i) {
        long result = buf[i] ^ m_key[t];
        std::stringstream ss;
        ss << (unsigned char)result;
        m_underlyingStream.write(ss.str().c_str(), 1);
        ++t;
        if(t >= m_key.length()) t = 0;
    }

    return n;

}

// etc.
Run Code Online (Sandbox Code Playgroud)

在代码的其他地方,接收器的实例化可能如下所示:

std::fstream underlyingStream(path, std::ios::out | std::ios::binary);
EncryptionSink sink(underlyingStream, std::string("theEncryptionKey"));
boost::iostreams::stream<EncryptionSink> outputStream(sink);
outputStream << "some data!";
outputStream.flush();
Run Code Online (Sandbox Code Playgroud)

我想您可能需要一个随附的 DecryptionSink 来反转操作,使用流复制器将加密数据复制回纯文本。请注意,使用 XOR 您不需要这样做,因为重新应用“XOR”将转换回原始数据

编辑:除此之外,我编写了一个简单的 c++ api,演示如何更有效地使用此类代码:cryptex