mrpetrov
Posts: 19
Joined: Sun Mar 08, 2015 3:44 pm

[HOWTO] Using BTRFS root on stock Raspbian with Pi 2

Sun Mar 15, 2015 11:07 am

Raspberry Pi 2 Model B with BTRFS root (for live system backups)

NOTE: Using swap file is not possible on BTRFS filesystem yet. If you want to use swap file - you will have to make another partition either swap or some filesystem which supports swap files.

1. Go to http://www.raspberrypi.org/downloads/ and get the latest Raspbian image. Find the relevant instructions on how to write the image on your microSD card.
DO NOT RESIZE THE ROOT PARTITION TO MAX SIZE.
2. Have your Pi up and running, with networking working - I did this

Code: Select all

sudo nano /etc/wpa_supplicant/wpa_supplicant.conf
and put at the end of the file my wifi details, as shown here: http://www.raspberrypi.org/documentatio ... ess-cli.md
NOTE: I used the D-LINK DWA-125 USB wireless adapter, which runs on the Pi out of the box.
3. Update your Pi:

Code: Select all

sudo apt-get update
sudo apt-get upgrade
4. Get the btrfs-tools package installed

Code: Select all

sudo apt-get install btrfs-tools
5. Add "btrfs" to your "/etc/initramfs-tools/modules" file:

Code: Select all

nano /etc/initramfs-tools/modules
Add "btrfs" at the very end of the file so the btrfs module gets loaded by the stock kernel, allowing for the use of BTRFS root FS.
6. Update kernel image

Code: Select all

sudo rpi-update
The above updates your firmware and kernel to the latest stable versions and creates a backup of /boot. [Need to confirm this...it may be config dependent]
7. Reboot
8. Update the initramfs

Code: Select all

update-initramfs -c -k `uname -r`
9. Edit /boot/config.txt by adding "initramfs initrd.img-3.xx.yy+" to the end of the file, replacing xx.yy with the correct numbers - see the exact numbers like so:

Code: Select all

ls -l /boot/initrd*
10. After verifying everything works, halt your Pi so you can power it down and take the microSD card out.
11. Change the filesystem to BTRFS. The aim is to make a snapshot archive of /dev/mmcblk0p2 part (Pi's root), make changes, and then trasfer the archive contents back to /dev/mmcblk0p2 as BTRFS.
I used PartitionMagic for this. Make an extra partition on the SD card and copy /dev/mmcblk0p2 to /dev/mmcblk0p3. Re-formatted the p2 part to btrfs:

Code: Select all

mkfs.btrfs -f /dev/mmcblk0p2
Afterwords - mount /dev/mmcblk0p2 with the compress option (to save space), mount /dev/mmcblk0p3 as read-only and then transfer /dev/mmcblk0p3 contents back to /dev/mmcblk0p2.
Stock Raspbian is like 3GB, so this takes a while. At the end of the copy process, find /etc/fstab on the /dev/mmcblk0p2 part and change this:

Code: Select all

/dev/mmcblk0p2  /               ext4    defaults,noatime  0       1
to this:

Code: Select all

/dev/mmcblk0p2  /               btrfs   compress          0       1
Maybe add the third partition so it gets mounted? You can do this later, too.
12. While still in PartitionMagic, mount /dev/mmcblk0p1 and edit /boot/cmdline.txt changing

Code: Select all

rootfstype=ext4
to

Code: Select all

rootfstype=btrfs
13. Unmount everything, take the SD card back in the Pi, power it up and enjoy!

The above is tried to work with The Raspberry Pi 2 Model B and
RASPBIAN
Debian Wheezy
Version:February 2015
Release date:2015-02-16
All of the above enables Pi users to do online backups given there are enough resources:

To back the BTRFS root filesystem up - I use this script:

Code: Select all

#!/bin/bash
# ver 2.0
# Now naming each archive with the hostname and date it was created.
# Just make sure it is run only once a day!

backupfilename=$(hostname)-$(date +%F).tar.bz2

if [ -e "/root/snapshots" ] && [ -d "/root/snapshots" ]; then
        printf "/root/snapshots folder found. Moving on.\n"
else
        printf "/root/snapshots folder does not exist - creating it..."
        mkdir /root/snapshots
        if [ "$?" -eq "0" ]; then
            printf "done.\n"
        else
            printf "error!\nFailed to create folder /root/snapshots. Aborting snapshotting.\n"
            exit 1
        fi
fi

printf "btrfs: "
btrfs subvolume snapshot -r / /root/snapshots/snap001

if [ "$?" -eq "0" ]; then
        printf "Snapshot created.\n"
else
        printf "Failed to create snapshot. Aborting operation.\n"
        exit 1
fi

cd /root/snapshots/snap001

printf "Beginning to tar.bz2 contents of snapshoted /. Please, be patient.\nWorking..."
tar --one-file-system -cjf /root/$backupfilename .

if ! [ "$?" -eq "0" ]; then
    printf "Failure during compression with tar -cj. Continuing to clean up.\n"
fi
cd /root
printf "compressing done.\n"

printf "btrfs: "
btrfs subvolume delete /root/snapshots/snap001

if [ "$?" -eq "0" ]; then
        printf "Snapshot removed.\n"
else
        printf "Failed to remove the snapshot of / btrfs filesystem.\n"
fi

printf "Creating MD5 checksum of archive (binary mode)..."
md5sum -b $backupfilename > $backupfilename.md5
printf "done!\n"

backupfilename=
I have the above code in an executable file named "backup-root.sh" in root's home dir, so on the Pi I did:

Code: Select all

sudo -i
and then, as root in root's home dir, I ran

Code: Select all

nano backup-root.sh
and used copy-paste.

To start the script on the Pi run:

Code: Select all

sudo -i
time ./backup-root.sh
and wait until it finishes. While it is running, you can do other stuff too - the tasks will simply run side by side. I use my Pi to collect sensor data, and while its backing up in one ssh window, I can open another ssh session to it to watch my live sensor data.

Stock Raspbian on Pi 2 takes 1 hour to backup and the .tar.bz2 archive is 1GB. The system is usable during the backup.

Thanks to scott.mckenzie for pointing out a mistake in guide revision 2!

Guide revision 3, date: 2015-05-13.

Comments and suggestions are welcome.
Last edited by mrpetrov on Wed May 13, 2015 3:38 pm, edited 1 time in total.

scott.mckenzie
Posts: 3
Joined: Mon May 11, 2015 10:51 am

Re: [HOWTO] Using BTRFS root on stock Raspbian with Pi 2

Wed May 13, 2015 9:02 am

Thanks for posting these instructions.

I did have some problems which I think came from running 'sudo rpi-update' after generating the initrd. I think this command may have downloaded a new kernel version which did not match the version of the running kernel or the initrd. This meant my pi would not load the initrd and therefore was not able to boot. Once I figured that out I was able to generate another initrd matching the kernel version, copied that to the sdcard and it booted.

I choose to use btrfs-convert to convert the existing ext4 partition to btrfs rather than using copy. If going with the copy option I would recommend copying the files to another device rather than using the sdcard as it would be much faster.

Thanks again for taking the time to write this up :)

mrpetrov
Posts: 19
Joined: Sun Mar 08, 2015 3:44 pm

Re: [HOWTO] Using BTRFS root on stock Raspbian with Pi 2

Wed May 13, 2015 3:35 pm

Thanks for your comment.

My aim in using BTRFS is snapshotting and space saving, so by going the route

Code: Select all

backup->format to btrfs->mount with compress->restore
I believe I achieve the compression I desire, which I am not sure btrfs-convert would provide, but this needs to be checked further.

As for your troubles with 'sudo rpi-update' - your notes here are 100% correct: one is supposed to first update the kernel with 'sudo rpi-update', and then proceed with the initrd boot image creation. I will fix my first post.

Needless to say - nice suggestions.

Thanks!

scott.mckenzie
Posts: 3
Joined: Mon May 11, 2015 10:51 am

Re: [HOWTO] Using BTRFS root on stock Raspbian with Pi 2

Thu May 14, 2015 12:43 am

You are correct - using btrfs-convert will not compress the files. Mounting the filesystem with the compress option and then running a defrag would compress the files. I suspect this would take a long time to perform on an sdcard but at least it's an online operation.

I have plenty of space on my sdcard so I'm OK with only future files being compressed. I choose lzo compression because it is supposedly faster (uses less CPU) but it does not compress files as much as zlib.

Lot's of options with btrfs which I like. It's now the only filesystem on all my Linux systems.

mrpetrov
Posts: 19
Joined: Sun Mar 08, 2015 3:44 pm

Re: [HOWTO] Using BTRFS root on stock Raspbian with Pi 2

Thu May 14, 2015 9:21 am

You assume that raspbian comes with working defrag - to my amusement, I found out the hard way that the tools for keeping btrfs up to snuff that come with raspbian are in fact ancient - they date to one of the first versions ever released.
To get to this info I had to run my scripts manually to see what was failing and where, and what do you know - stock raspbian btrfs userland tools were saying "unknown parameter" and such...

If someone ever manages to update just btrfs-tools and only them on a stock raspbian - please, let me know how!
Last edited by mrpetrov on Thu Jul 30, 2015 6:31 pm, edited 1 time in total.

scott.mckenzie
Posts: 3
Joined: Mon May 11, 2015 10:51 am

Re: [HOWTO] Using BTRFS root on stock Raspbian with Pi 2

Thu May 14, 2015 8:45 pm

Ancient is right! Looks like an upgrade to jessie is required for a recent btrfs-tools:
https://packages.debian.org/search?keywords=btrfs-tools

jessie is in the raspbian repo's but wheezy-backports is not. I'll test an upgrade over the weekend.

diederik
Posts: 389
Joined: Wed Mar 26, 2014 11:17 pm

Re: [HOWTO] Using BTRFS root on stock Raspbian with Pi 2

Mon Dec 28, 2015 5:05 pm

mrpetrov wrote:As for your troubles with 'sudo rpi-update' - your notes here are 100% correct: one is supposed to first update the kernel with 'sudo rpi-update', and then proceed with the initrd boot image creation. I will fix my first post.
You're actually not supposed to use rpi-update at all anymore (unless specifically instructed to do so by one of the kernel devs).
Just stick to the 'raspberrypi-bootloader' package.

ddurdle
Posts: 59
Joined: Sat May 04, 2013 12:20 am

Re: [HOWTO] Using BTRFS root on stock Raspbian with Pi 2

Sat Mar 26, 2016 2:06 am

The backup script confuses me. I'm a long-time user of BTRFS.

The backup script is creating a snapshot and then creating a tar file backup of the snapshot. Are you storing this backup on the device or moving off to another device? If you are storing the backups on the same device, then why not just keep the snapshots? The tar files are going to take more space, as you are already using compression for the filesystem itself. The snapshots are going to prevent storing duplicate bits, whereas your tars are not.

If you are going to transfer the backups to another device for safe keeping, BTRFS already has that covered. You can send|receive snapshots between devices, while taking advantages of BTRFS (de-duplication, compression, etc).

The setup instructions on BTRFS are very good and thorough.

mrpetrov
Posts: 19
Joined: Sun Mar 08, 2015 3:44 pm

Re: [HOWTO] Using BTRFS root on stock Raspbian with Pi 2

Sat Mar 26, 2016 7:01 am

Your question kind of already contains the answer - I'm using tar to create a tarball archive and then store it on a file server, on another file server and a copy on optical media. So, by having a tar archive of my whole filesystem, I am basically covered for anything, and my only loss would be the service of my device while I get a hold of a new microSD card, Raspberry Pi, whatever... and just extract my arhive on the new card.
And as a bonus, I can use whatever systems I want, because I am working with just a file, as opposed to your suggestion that there is another machine with BTRFS available to use send|receive.

Thanks, and have a good one!

ddurdle
Posts: 59
Joined: Sat May 04, 2013 12:20 am

Re: [HOWTO] Using BTRFS root on stock Raspbian with Pi 2

Sat Mar 26, 2016 1:43 pm

mrpetrov wrote:Your question kind of already contains the answer - I'm using tar to create a tarball archive and then store it on a file server, on another file server and a copy on optical media. So, by having a tar archive of my whole filesystem, I am basically covered for anything, and my only loss would be the service of my device while I get a hold of a new microSD card, Raspberry Pi, whatever... and just extract my arhive on the new card.
And as a bonus, I can use whatever systems I want, because I am working with just a file, as opposed to your suggestion that there is another machine with BTRFS available to use send|receive.

Thanks, and have a good one!
Yes, I'm just putting it out there that if people are backing up and using BTRFS, they have the ability to leverage snapshots to achieve backups and benefit from deduplication.

I also found benefit of using subvolumes as opposed to mounting the root BTRFS. I once managed to corrupt my BTRFS by an ill behaving LXC. Because I didn't know any better and was mounting the entire BTRFS volume, even though I had snapshots, I lost the ability to restore using them (since the root volume was corrupt). In this scenario I had to restore from a backup snapshot stored on a backup device (using receive). I've learned from that. I now only mount the subvolumes and only a backup script mounts and unmounts the root (for purposes of backing up subvolumes). I try to keep locally one most recent snapshot backup (in addition to backing up to external devices). If you don't have immediate access to an external backup, you can always restore a local snapshot. I'm only getting started with BTRFS on the pi devices I own, but based on the number of times I've had to restore backups from EXT4 pis,I'll probably end up doing some BTRFS restores.

If anyone is curious how to mount a subvolume on the pi (instructions are hard to come by on the internet, your post is the best BTRFS on pi post), in the fstab you can just add a subvol=subvolume_name to the options for the mount, and in the cmdline.txt, add rootflags=subvol=subvolume_name.

I store the OS components in a subvolume called pi-raspbian and the home directory in a subvolume called home_myname. Snapshots I append .YYYYMMDD to the subvolume name.

wiak
Posts: 7
Joined: Sun Sep 02, 2012 9:57 pm

Re: [HOWTO] Using BTRFS root on stock Raspbian with Pi 2

Tue Apr 05, 2016 10:49 pm

cant we just mount the raspbian image, copy boot to fat32 partition, then format a btrfs parition then copy / ?
the dd image is basicly a disk image, so you can mount it

just thinking out load here :roll:

ddurdle
Posts: 59
Joined: Sat May 04, 2013 12:20 am

Re: [HOWTO] Using BTRFS root on stock Raspbian with Pi 2

Wed Apr 06, 2016 4:07 pm

I had issues before trying to reproduce a bootable SD card from one card to another. The source would be bootable but not the copy. Even if you attempt to flag the vfat partition bootable, I believe there are some bytes in the image (outside of the vfat partition) that provides the system the correct byte offset to locate the bootable partition.

To make things really simple, and generally what I do, keep a simple downloaded img on a system, and when you want to create a card, restore it, and then wipe out the ext4 partition with a btrfs partition, and then copy over the filesystem (as you pointed out).

If you have an existing ext4 install, and you don't want to lose your setup, you can either convert it to BTRFS (which is really simple, tool just creates the BTRFS partition table, you can even rollback the change to put it back to ext4) or you can rsync everything over to somewhere temporary, and then back over. The rsync method is what I generally do, as if you decide to use compression on the volume, your data will be compressed when you rsync it back.

Once you have a good filesystem on BTRFS, you can use send|receive to transfer it. Personally, I keep two external hard drives to "backups" and I send|receive my BTRFS volumes to it. So if I need to restore a system or clone a system (such as make a duplicate raspberry pi device), I simply create the SD card, wipe out the ext4, create a BTRFS partition and send|receive the FS over to the device. Couldn't be easier :)

ygd2013520
Posts: 4
Joined: Tue Jan 26, 2016 3:02 am

Re: [HOWTO] Using BTRFS root on stock Raspbian with Pi 2

Thu May 12, 2016 7:48 am

hello,I use your method to do it ,but when I put the sd back to the pi,it can not go to the desktop or command line.But I use ssh through network ,I can got into the command line ,but can not use "sudo",it shows "sudo: /usr/bin/sudo must be owned by uid 0 and have the setuid bit set" ,please help me ,thanks very much.

Return to “Advanced users”