Take the 2-minute tour ×
Unix & Linux Stack Exchange is a question and answer site for users of Linux, FreeBSD and other Un*x-like operating systems.. It's 100% free, no registration required.

I'm trying to design a firmware update system for an embedded Linux system. My plan is to send an image that can be mounted on the target system, so I don't need to unpack the entire file. I also want to encrypt the image, and optionally compress it as well. Since the build system for creating this image is going to be deployed on several computers I also want the build system to require minimal amount of setup, i.e., avoid avoid requiring root privileges.

I've created a working model where I mount an image file using losetup as such:

dd if=/dev/zero of=image_file bs=1M count=10
losetup -e aes loop0 image_file
mkfs.ext2 /dev/loop0
losetup -d loop0
mount -t ext2 -o loop,encryption=aes image_file some_working_folder/
# Add files to some_working_folder
umount some_working_folder
# Send encrypted image to the target system

Now, since this is a bit cumbersome to set up on some machines, and I want to avoid creating fixed sized images. So I want to replace the losetup commands with something else. I found the command virt-make-fs, which can create a mountable image with the ext2 filesystem. So now I only need to encrypt the image file in a way that is decryptable by the linux kernel. I've tried to use OpenSSL, but I haven't been able to find the correct algorithm, or maybe I'm missing something. Does anybody know how to do this? Basically I want something like the script below.

tar -cf archive.tar some files
virt-make-fs archive.tar image.ext2
# the below command need to be fixed/replaced
openssl enc -aes192 -in image.ext2 -out image.ext2.aes

On the target system I want be able to use the following command, or at least something similar.

# The next command should be done on the target
mount -t ext2 -o loop,encryption=aes image.ext2.aes /mnt/upgrade
# work with files in /mnt/upgrade

So, just to clarify: How can I create an encrypted mountable image file without being root?

Feel free to comment if I'm trying to reinvent the wheel, or if there is some other well established solution for this problem. Even though there are better solutions, I'm still interested in the command to solve the encryption problem.


Edit: As been pointed out cryptoloop is unsecure, see http://lwn.net/Articles/67216/. So I will probably look around for another solution as well. I've found to util aespipe, which I might be able to use.


Edit 2: I've dug into the source code in the AES module of the Linux kernel, and I've concluded that it is probably the hashing of the password that is causing the problem. Both aespipe and the AES module are using an AES-256-CBC encryption. As far as I can see the linux kernel uses the given password as key, and aespipe hashes the incoming password. Since the "no root" part is very important to me I've started looking for other solutions, and my current plan is to use something like the following on the development computer:

tar -cf - file0 file1 ... | gzip -c | aespipe -e aes256 > arhive_file

And then on the target system run

rm -rf /tmp/update ; mkdir -p /tmp/update
aespipe -d -e aes256 < archive.mbl | gzip -cd | tar -C /tmp/update -xf -
share|improve this question
    
It's not fixed size if you use resize2fs -M. –  frostschutz May 26 '13 at 21:43
    
True, but I would prefer to have an image that is of the correct size from the beginning. –  Kotte May 27 '13 at 6:23

3 Answers 3

up vote 1 down vote accepted

Despiting the weak security of cryptloop according to this.

You can use usermode FS creator like: buildroot genext2fs.sh or android make_ext4fs. with combination with aespipe tool for host creation of your encrypted image without root/superuser privilege.

But you need to patch the losetup(at least or mount) with loop-aes and activate cryptoloop (as module or builtin) for the Linux kernel of your target, to be able to mount such encrypted image directly.

The following shows how to do that in case of encrypted ext4 filesystem image (for ext2 FS you can just replace the first 2 commands with the buildroot genext2fs.sh[3]):

HOST $ make_ext4fs -s -l 512M -a data yourimage.simg folder/
HOST $ simg2img yourimage.simg yourimage.img
HOST $ cat yourimage.img | aespipe -e aes256 > yourimage.crypt

TARGET # modprobe cryptoloop #in case of cryptoloop as module.
TARGET # losetup.patched -e aes-256 /dev/loop0 yourimage.crypt
TARGET # mount -t ext4 /dev/loop0 /mnt/uncrypt
share|improve this answer

Do use dmcrypt, it's the de facto standard disk encryption subsystem in Linux.

On developer machines, install cryptmount and configure it to allow mounting as a non-root user. This is cumbersome as you have to hardcode the path to the image (and the mount point) in /etc/cryptmount/cmtab.

upgrade {
    keyformat=luks
    dev=/home/bob/upgrade/image.enc
    dir=/mnt/upgrade
}

To mount and unmount:

cryptmount -m upgrade
cryptmount -u upgrade

Alternatively, set up sudo rules to allow the developers to run cryptsetup and losetup without a password.

Cmnd_Alias CryptLoop = cryptsetup luksOpen * *, cryptsetup remove *, losetup * *
bob ALL=(ALL) NOPASSWD: CryptLoop
share|improve this answer
    
Yes, but it's not really the disk encryption I am after, the important part is the disk image encryption. I will look into using dmcrypt on the target system. But on having this special configuration on the developers computers is bound to cause problem later on when someone else is taking over this part. That is why I want to have the build system as self contained as possible. –  Kotte May 28 '13 at 11:43
    
@Kotte I understood that you wanted the image to be encrypted on the target device. If you don't want that, forget about encrypting the image on developer machines: encrypt their home directory (with dmcrypt or ecryptfs), as well as whatever repository the images are stored in, instead of encrypting the file. For distribution (which developers don't ordinarily intervene in), use whatever format is appropriate for transmitting to the device. –  Gilles May 28 '13 at 11:50
    
The problem I am trying to solve is the format to use when transmitting the file to the device. I want to have firmware upgrade file that I can send to customers so they can upgrade the firmware in the device in the field, but I don't want to have to worry about the file ending up in the wrong hands. Sorry if the question is a bit confusing. –  Kotte May 28 '13 at 12:15
    
@Kotte In that case there's no need to involve developers in the encryption. You need to encrypt the image at the delivery point, not during development. –  Gilles May 28 '13 at 12:30
    
Yes, but in this case the build system need to be able to create deliverable files as well –  Kotte May 28 '13 at 12:32

If I remember correctly then encryption support has been removed from mount / losetup for security considerations in favor of dmcrypt. Thus I assume you have to use losetup without encryption and put a DM crypto device on top of it.

losetup /dev/loop0 /image/clearfile.img
losetup /dev/loop1 /image/cryptfile.img
cryptsetup create cr_loop /dev/loop1
dd if=/dev/loop0 of=/dev/mapper/cr_loop bs=100M

Then cryptfile.img is encrypted. You can distribute it and make it available by repeating losetup and cryptsetup (and mount the decrypted device afterwards).

You may add the cipher (and so on) to be used to the cryptsetup call in order to avoid problems with changed defaults. Or use LUKS instead. But in that case the encrypted file has to be a bit larger than the cleartext image (5 MiB should be enough); that the file system is probably a bit smaller than the device then does not matter.

share|improve this answer
    
Yes, but the losetup procedure I described works on all the machines I've tested it on. But my problem with that procedure is that it sometimes require root privileges, and I don't want to fix that on all the developers laptops. Do you what kind of security considerations it was? –  Kotte May 27 '13 at 6:52
    
@Kotte It seems to me that avoiding root privileges is not part of your question. If you want to mount something you need root privileges (once) anyway. The closest thing to not needing them is probably FUSE. There should be a crypto module available for it. –  Hauke Laging May 27 '13 at 9:21
    
Well, I want to create the image file on my development computer and then mount the image on the target system. And I want to avoid being root on my development computer. So a bit reformulated my question is: How can I create an encrypted mountable image without being root. –  Kotte May 27 '13 at 9:29
    
@Kotte You should really restate your question then. Instead of adding a comment with a new version of the question. Because that will be the last other readers will notice. –  Hauke Laging May 27 '13 at 9:36
    
I really thought that was clear from the first sentance. But I've updated the question now. Hopefully its clearer now :) –  Kotte May 27 '13 at 10:09

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.