RFS file system support for linux

From SamyGO
Jump to: navigation, search

RFS file system support for linux

File systems are storage formats for data on e.g., a disk or a pendrive. On a linux box, EXT3 (3rd extended file system) is very popular, just as NTFS is for Windows. and FAT12, FAT16 and FAT32 were for DOS and earlier Windows versions.

Samsung TV's have their file systems for user space applications formatted as RFS (Robust File System). RFS is a FAT 16/32 based file system with a sort of journalling system on it. The code to build and use the RFS file system is proprietary and only used in Samsung equipment, such as TV's, BluRay players and cellphones.

What are the possibilities?

Well, Samsung firmware upgrades are delivered as a set of file system images that are flashed over the existing flash file systems, typically in the RFS format. Until now it was not possible to use these images on a desktop or notebook computer, so if you need to change something in the firmware, you would have to use a hex-editor to patch the file system image directly. That is a cumbersome way of doing things, and offers only limited patching possibilities. When you have the code for Samsung's file system, in theory it can be made to work and eventually be used on other equipment than Samsung's.

And that's exactly what happened. Some time ago, Samsung (accidentally?) posted the firmware source code for one of the A-series TV's on their global open source download site, with the code for the rfs.ko kernel module still in it. There's no need to check it out, it's not there any more. arris69 downloaded it, patched it to make it work on x86-based computers and hey presto! a working RFS file system module for desktop use.

Practical use

You can use the RFS file system support for two things:

  1. You can change things in the firmware of your TV a LOT easier than before. Just mount the file system images, change whatever you want, unmount again, repack into the firmware and flash, or, flash the image directly onto your TV using the internal flashing software (using bml.restore bml.dump and the likes).
  2. You can build newer kernels for your TV to add extra functionality and still use the proprietary file systems and firmware images for your TV.

Warning: make sure your self made image is not bigger than the partition where you want to flash it!!!

How do I make it work on my computer?

First of all, this method works on Linux only. If you have no (root) access to a Linux box, stop reading, go and do something else, this is not for you. Linux users, read on!

What you need

  1. You will need root access to an intel compatible linux machine. The code has been tested so far on both i386 and x86_64 platforms. Since the code only comprises the file system driver, it will probably work on other platforms as well. ARM and MIPS-based platforms should be no problem, since that's what it is being used for most by Samsung.
  2. The machine needs to be configured for development purposes, i.e., you have to have a working toolchain installed (gcc, binutils and glibc library headers, make, bison and some other development tools).
  3. Basic knowledge of unix (bash) command line interface commands. Typically, tar, ls, cd, rm, ln and some others. If you don't know any of these, try and open a terminal and type man <command name> to get help.
  4. A little experience in kernel configuration and compilation is a plus.
  5. Internet access, but you are probably reading this on the internet, so that's not a problem.

What you do

( This will be automated probably, at least partly)

  • Download a vanilla kernel source from www.kernel.org. (compatible versions will follow later) You will need this to build a new kernel from. Kernel sources as used by popular distro's are heavily patched throughout the source tree, making it hard to patch them without errors, with a single patch, built for a non-patched kernel. If you insist you can try, but you're on your own.
  • Download the RFS patch from (original version from samsung sources?) and save it as <a-path-to/RFS.patch>.
  • Download the RFS fix patch version 1.2.2p1-rc2 or version 1.3.1_b070 prepared for xattr support and save it as <a-path-to/RFS-fix.patch>.
  • Unpack the kernel source. On Debian and Slackware based machines (Debian, Ubuntu, Gentoo, Slackware) this normally is done in /usr/src. On RedHat based machines (Fedora, CentOS, Mandriva, RedHat) the kernel sources typically go in /usr/src/kernels. If you do not want to mess up your standard source tree, any other directory will do just as well.
  • Open a terminal as root and enter the top-level kernel source directory. Patch the kernel by issuing the following command(s):
patch -p1 < <a-path-to/RFS.patch>
patch -p1 < <a-path-to/RFS-fix.patch>
  • Integrate the RFS Configuration in kernels Build-System with following commands:
sed -i -e 's#\(obj-$(CONFIG_JFFS2.*\)#\1\nobj-$(CONFIG_RFS_FS)\t\t+= rfs/#' fs/Makefile
sed -i -e 's#\(source "fs/nls/Kconfig"\)#\1\nsource "fs/rfs/Kconfig"#' fs/Kconfig
  • Configure the kernel by

make menuconfig Here is where a little experience comes in handy. To configure the kernel properly, and as lean as possible, you need to know what exactly the hardware is you are using. If you don't know, you can try and use the configuration for your distro, typically available from the distro kernel source packages. The RFS filesystem configuration has been preset, so it should be OK.

  • Build the kernel and modules:

make (-j<number of cores on your machine + 1> )

  • Install the modules:

make modules_install This builds and installs the kernel modules, including the rfs module.

  • Put the kernel (arch/<architecture>/boot/bzImage) in the directory where it belongs, typically /boot
  • Configure the boot loader to enable booting your freshly built kernel.

In grub: add the lines

title SamyGO
root (hd0,2)
kernel /kernel-with-rfs ro root=/dev/sda5 rhgb quiet
initrd /initrd-image

to /boot/grub/grub.conf. Replace kernel image name, initrd name and root device with the right ones for your system. in LILO: (anyone still using this?) add the lines


to /etc/lilo.conf, typically at the far end. Again, choose your names for the kernel and root device.
run /sbin/lilo

  • reboot, pick the right kernel to load.
  • login as root, open a shell (terminal) and load the rfs module:

modprobe rfs.ko

  • Try and mount a file system image from Samsung:

mount -t rfs <image_name, e.g. exe.img> /mnt -o loop

  • Test it by making new files, deleting files, editing, linking etc ...
  • All done.

Making new RFS filesystems

So far we only discussed mounting and editing RFS file systems on linux. In another source package issued by Samsung, the code for a set of tools to build and test RFS filesystems was released. This may come in handy if you want to build your own filesystems (of different size, for other Samsung equipment, ...). The code for this tool resides inside 10_LA32C530_X4.zip, in the package vdlinux-mstar-kernel.tgz, in the subdirectory vdlinux-mstar-kernel/RFS_1.3.1_b070-LinuStoreIII_1.2.0_b032FSR_1.2.1p1_b129_RTM_X4/tools/FSTools/
It is available from the open source server at Samsung's. This package both contains the source code and a working i*86 binary of mkrfs. Unpack it, type ./mkrfs -h in its installation dir and you will see the options it has. Like mksquashfs, it generates a filesystem from an existing directory rather than an empty one with a predefined size. Unlike e.g., mksquashfs, you can set the size of the filesystem to be built.

Fix RFS filesystem images

If you want to manipulate image files extracted from Samsung firmware updates, or play with self-created file system images made by passing the image size to the command mkrfs, you first need to expand such file system images to the correct size. Otherwise you will end up with a damaged image file when you try to write data into it. The next example shows how to do this.

  • readout the data size
sudo fsck.vfat -n -v <orig_image_file>
the output of this command is (for an image with size of 46215168 bytes):
Boot sector contents:
System ID "libFAT  "
Media byte 0xf8 (hard disk)
      4096 bytes per logical sector
      4096 bytes per cluster
         1 reserved sector
First FAT starts at byte 4096 (sector 1)
         2 FATs, 16 bit entries
     24576 bytes per FAT (= 6 sectors)
Root directory starts at byte 53248 (sector 13)
       512 root directory entries
Data area starts at byte 69632 (sector 17)
     11265 data clusters (46141440 bytes)
8 sectors/track, 1 heads
         0 hidden sectors
     11282 sectors total
FATs differ but appear to be intact. Using first FAT.
Checking for unused clusters.
Leaving file system unchanged.
and another example output (for an image from Samsung firmware with size of 41996288 bytes):
Boot sector contents:
System ID "libFAT  "
Media byte 0xf8 (hard disk)
      2048 bytes per logical sector
      8192 bytes per cluster
         2 reserved sectors
First FAT starts at byte 4096 (sector 2)
         2 FATs, 16 bit entries
     16384 bytes per FAT (= 8 sectors)
Root directory starts at byte 36864 (sector 18)
       512 root directory entries
Data area starts at byte 53248 (sector 26)
      7673 data clusters (62857216 bytes)
8 sectors/track, 1 heads
         0 hidden sectors
     30720 sectors total
FATs differ but appear to be intact. Using first FAT.
Got 0 bytes instead of 32 at 45232128
  • now calculate the required image size
sectors total * bytes per logical sector + First FAT starts at byte = 30720 * 2048 + 4096 = 62918656
  • create a new file with the correct size, and copy the file system image into it (use man dd for more information on dd usage)
dd if=/dev/zero of=<fixed_image_file> bs=<size_in_bytes> count=1
dd if=<orig_image_file> of=<fixed_image_file> conv=notrunc

Reference Threads

thnx to Marcel for the article