\section{Questions}
\subsection{Point of Assignment}
The main point of this assignment was to gain experience working with device drivers and the Linux kernel crypto API. To accomplish this, a lot of research was necessary. Learning how to perform research and finding good sources for the future are also benefits of this assignment. Finally, the assignment provided experience working with module parameters.

\subsection{Problem Approach}
We approached this problem by first reading through the Homework 3 page on Canvas. Then we separated the assignment into three main concepts, the device driver, crypto, and the module. 

First we decided to implement the device driver. As suggested on the Canvas page, "SBD" was researched and an example of a sample block device was found at http://blog.superpat.com/2010/05/04/a-simple-block-driver-for-linux-kernel-2-6-31/. After some adjustments to ensure it was compatible with the version of the kernel we are using, the device driver was tested. After ensuring correct functionality of the device driver, the Linux kernel crypto API was researched. This mainly involved looking through the crypto.h file to find the functions that are available. After finding the functions we wished to use, the device driver was adapted to encrypt and decrypt data at the time that it is read or written. Finally, we added the cipher key as a module parameter. While performing the crypto development,the module was loaded as a built-in module at boot time. Once kernel parameters were added, the driver was compiled as an add-in module, scp'd to the virtual machine, installed into the kernel directories, and loaded with varying parameters as needed for testing.

\subsection{Correctness}
We know that the end result was correct by first using the output of printk function calls to look at the cipher key, the current state (reading or writing), the encrypted bytes, and the unencrypted bytes. This allowed us to see what the encrypted data looked like and ensure that the encryption and decryption was being done correctly. Then we moved our block device to a module to test the module parameter. To test this, we used different cipher keys with the same input data to show that the output data changes with the different cipher keys. Lastly, we were able to verify that the driver was working correctly by directly reading data from the /dev/sdb0 device. Reading from the device directly always returned garbage encrypted data unlike when reading from the mounted directory using our driver.

\subsection{What Was Learned}
We again learned that documentation is extremely important to code development as it allows readers to more easily use code that has already been written. We also learned the basics of how to use the Linux kernel crypto API as well as the basics of writing device drivers. 

\subsection{How to Evaluate}
After applying the patch file using patch -p1 $<$ homework3.patch from the root of the kernel directory, building the kernel, and launching the vm, you should immediately see printk statements showing the output of the driver. Once booted, a filesystem can be made per the assignment instructions and mounted to a folder using the mount command. By reading and writing data to the mounted drive and watching printk output, you will easily be able to see that the encrypted data is different than the unencrypted data. For more in depth evaluation, a boot time kernel parameter can be set with the command "encrypted\_boot\_device.custom\_cipher\_key=yourkey" to change the module parameter. Then, by following the process above with identical data input as before, you can see the printk statements for encrypted data output differing data than with the default key.
