This article is targeted for MFC developers with understanding of the Crypto++ code library.
For the sake of clarity and introducing Crypto++ to those who are not familiar with it, I added the following paragraph.
From the Crypto++ website: "Crypto++ Library is a free C++ class library of cryptographic schemes".
Written and maintained by Wei Dai, this is a powerful library that contains modern cryptography algorithms.
To understand Crypto++, you should have (at least) basic understanding of cryptography concepts.
The World-Wide-Web offers a lot of information, and so does CodeProject (e.g.: See Jeffery Walton's valuable articles in this field).
For an in-depth reading, I found the book Applied Cryptography to be very enlightening. Beyond being very informative, it is written almost like an espionage/conspiracy novel, which makes reading it a lot more fun.
Back to Crypto++, the website contains valuable information and you may also want to visit the Crypto++ Wiki pages to get started.
I should point out that, to me, the learning curve was kinda slower than, oh, let's say, the time it took Trinity to learn how to fly that Bell 212 helicopter... (Note: I am not the geek you might think I am at this point in the article!)
Anyway, it will take a while to get used to the concepts and design patterns of the library (on a personal note, I really enjoyed reading Crypto++'s source code).
So, if you're going for it - don't get discouraged - once you get the hang of things, everything will fall into place and it'll all become clear.
While integrating cryptography abilities into an MFC application I'm working on, I needed to use
CFile(s) with Crypto++'s code instead of its built-in
fstream file handling implementation.
Not being able to find such an implementation, I decided to write one.
This implementation will enable you to use an MFC
CFile as a Source / Sink element in conjunction with Crypto++'s data transport design pattern. It is pretty straightforward - I used Crypto++'s files.h/.cpp as a baseline, and made the necessary modifications for the code to work with a
The code is based on Crypto++ v5.5.2 (but I believe it may work with earlier versions) and was tested on Visual C++ 6.0 and Visual Studio 2005.
The source code won't run on its own. You will have to integrate it into a working Crypto++ environment.
Crypto++ source code may be downloaded from Crypto++'s download section.
You'll probably want to review the Compiling and Integrating Crypto++ into the Microsoft Visual C++ Environment page, which will help you get started with Crypto++ on your version of Microsoft Visual Studio.
You may also have a look at the Crypto++ FAQ and the Crypto++ Wiki for a user reference, some useful examples and more information.
Using the Code
I'll use a simple file-copy operation to demonstrate the code.
void CopyFile( CFile* fin, CFile* fout )
MfcCFileSource( fin, true, new MfcCFileSink( fout ) );
This code will create an
MfcCFileSource wrapper for the input file, create a
MfcCFileSink wrapper for the output file, and pump all bytes from the input file to the output file.
Preserving the Output File Pointer
In the above example,
MfcCFileSink will be deleted somewhere during
MfcCFileSource's destruction sequence. Effectively, this means that
MfcCFileSink, in its turn, will delete the
fout file pointer (this will be done implicitly by a smart pointer that wraps
In order to overcome this hurdle, I added a boolean parameter to
MfcCFileSink( CFile* out, bool bAutoDelete = true );
The default value of
bAutoDelete will be to auto-delete the
out file pointer, which is the default behavior of having
fout wrapped in a smart pointer. In order to keep
out alive and unharmed, you should pass
false as the second parameter to
Here's the revised file-copy example:
void CopyFile( CFile* fin, CFile* fout, bool bAutoDeleteFOut )
MfcCFileSource( fin, true, new MfcCFileSink( fout, bAutoDeleteFOut ) );
Using this version of
CopyFile, it is possible to pass
bAutoDeleteFOut and thus preserve
fout for consecutive operations (e.g., appending several files one after the other into a single output file).
No Auto-delete Option for a Filename Constructor
While we're on the subject, I'll just add the filename related constructor:
MfcCFileSink(LPCTSTR filename, bool binary=true);
CFile pointer in this case is maintained internally in this case, I'd like to keep it that way. That is why there is no
bAutoDeleteFOut parameter here. If you really need the
CFile* - open a file in advance and pass it to the appropriate constructor.
A Real-Life Example
Of course, any transformation filter may be applied before
MfcCFileSink in order to manipulate the bytes on their way from the source to the sink.
In order to see the code in action, here's a real-life example of compressing and encrypting an input file:
void EncryptFileDemo( CFile* fin, CFile* fout, const char* sPassPhrase )
MfcCFileSource( fin, true,
new DefaultEncryptorWithMAC( sPassPhrase,
new MfcCFileSink( fout )
In the example, we pass the input file bytes through a compression filter and an encryption (with password) filter all the way out to the output file.
Filter is a Crypto++ data manipulation mechanism.
- Explaining filters is beyond the scope of this article.
The client code may look like this:
new CFile(File, CFile::modeRead),
new CFile(sOutFile, CFile::modeWrite | CFile::modeCreate),
Hope you'll find this helpful.
Comments / suggestions are most welcome.
- 3rd March, 2009
- 7th March, 2009
- Added Crypto++ Background and Code Integration info (thanks to Hans Dietrich)
- Fixed a minor compatibility issue with VC7 version and above