18

I'm writing a custom automated install using AIF (Arch Installation Framework), and I need to find the filesystem on a partition given a partition.

So far I have this:

grok_partitions () {
    local partitions=
    for label in `ls /dev/disk/by-label | grep "Arch"`
    do
        if [ $label == "Arch" ]
        then
            mount_point="/"
        else
            IFS="-" read base mount <<< "${label}"
            mount_point="/${mount}"
        fi

        local partition=$(readlink -f /dev/disk/by-label/${label})
        local part_no=$(echo ${partition} | grep -Po '\d+')
        local fs=$(parted -mls | grep "^${part_no}" | cut -d: -f5)
        partitions+="${partition} raw ${label} ${fs};yes;${mount_point};target;no_opts;${label};no_params\n"
    done

    # do the swap
    if [ -e /dev/disk/by-label/swap ]
    then
        local partition=$(readlink -f /dev/disk/by-label/swap)
        partitions+="$partition raw swap swap;yes;no_mountpoint;target;no_opts;swap;no_params"
    else
        # if there's no labeled swap, use the first one we find
        local partition=$(fdisk -l | grep -m1 swap | awk '{ print $1 }')
        if [ ! -e $partition ]
        then
            echo "No swap detected. Giving up."
            exit 1
        fi
        partitions+="$partition raw no_label swap;yes;no_mountpoint;target;no_opts;no_label;no_params"
    fi

    echo -n ${partitions}
}

This worked fine on my machine with only one hard drive, but it failed (obviously) when running in my VM running on a LiveCD (the LiveCD was being picked up as another drive, /dev/sr0).

I've thought of a couple of hacks I could try:

  • mount $partition; grep $partition /etc/mtab | awk ...
  • use parted -mls, but pull out the partition I care about with clever scripting, then parse as I already do in the scriptt

Is there a better, simpler way of doing this? I already have the partitions I'm interested in, and I only need to find their filesystems (as well as find available swap).

1
  • 3
    @Mikel No, that question looks at a mounted filesystem. While you can mount the filesystem then see what type it's mounted as, this is slow, not robust, doesn't work for swap, only works for filesystems supported by the running kernel... Jul 17, 2012 at 23:39

4 Answers 4

18

I think I found the answer: blkid

From the man page:

The blkid program is the command-line interface to working with the libblkid(3) library. It can determine the type of content (e.g. filesystem or swap) that a block device holds, and also attributes (tokens, NAME=value pairs) from the content metadata (e.g. LABEL or UUID fields).

Apparently it prints the device name along with the filesystem type (along with some other useful information). To get a list of all devices with their types:

blkid | sed 's!\(.*\):.*TYPE="\(.*\)".*!\1: \2!'

To find all /dev/sd*/ devices, just add in a grep:

blkid | grep "/dev/sd.*" | sed 's!\(.*\):.*TYPE="\(.*\)".*!\1: \2!'

Then just cut or awk to get what you need.

4
  • 14
    blkid can filter what you need on its own - no need for sed/grep/awk magic: blkid -s TYPE -o value /dev/sda3
    – Petr Uzel
    Jul 17, 2012 at 8:28
  • @PetrUzel - Awesome! That's exactly what I was looking for!
    – beatgammit
    Jul 18, 2012 at 17:51
  • 2
    Remember to run with sudo if you are not root! This one caught me out because blkid does not print any error messages and exits with status code 0 if it cannot access block devices... Aug 24, 2015 at 10:46
  • There's rarely a need to pipe grep to sed. grep foo | sed 's/pattern/repl/' is more cleanly written sed '/foo/s/pattern/repl/' Aug 31, 2019 at 1:29
9

file -s /path/to/device will identify the filesystem on a disk/partition/slice.

A la:

[root@node2 ~]# file -s /dev/mapper/VolGroup00-LogVol00
/dev/mapper/VolGroup00-LogVol00: Linux rev 1.0 ext3 filesystem data (needs journa recovery) (large files)
[root@node2 ~]# file -s /dev/mapper/coraid--pool-coraid--lv1 
/dev/mapper/coraid--pool-coraid--lv1: Linux GFS2 Filesystem (blocksize 4096, lockproto lock_dlm)
[root@node2 ~]# file -s /dev/mapper/coraid--pool-coraid--lv2 
/dev/mapper/coraid--pool-coraid--lv2: SGI XFS filesystem data (blksz 4096, inosz 256, v2 dirs)

at least, on Linux it does.

2
  • Is there a way to reliably filter out the filesystem type from a script?
    – beatgammit
    Jul 18, 2012 at 17:50
  • depends on whether you consider the full name of the filesystem filtered enough, as in | cut -d: -f2 | cut -d( -f1 or something. It's not as pretty as blkid, that's for sure. :) Jul 20, 2012 at 1:56
8

Show only the block device's TYPE tag, and only output its value:

blkid -s TYPE -o value "$device"

Example:

$ blkid -s TYPE -o value /dev/mapper/vg_svelte-home 
btrfs
1

A secondary option that works with many filesystems and has the benefit of working even with filesystems that have damaged structures is testdisk. (You can run sudo apt install testdisk to install it on Debian-based systems.)

Script it to return just the filesystem type like this:

$ testdisk /list "$path_to_partition" | awk '$1 == "P" {print $2}'

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .