Ipfs Fuse mount allows for symlinks outside the mount directory

Vulnerability Note

1 Summary

Go-ipfs uses fuse for user space mounting of ipfs nodes. It uses the Brazil library for this [2]. Brazil does not provide secure by default settings and assumes that it’s provided with safe input from the code calling into it. This assumption is not valid in IPFS’s case, where the nodes that can be queried are not sanitised. This allows an attacker to create symlinks on an IPFS mount that reference other potentially sensitive files.

This weakness affects any user that leverages the mount functionality to expose access to potentially unsafe IPFS nodes.

2 Details

2.1 Description

IPFS allows users to distribute nodes (representing files, directories and symlinks) on its network. The path name parameters for these nodes are never sanitised and can therefore contain malicious payloads.

go-ipfs allows users to mount ipfs in the filesystem. Once mounted, users can get the content of ipfs nodes by accessing them at /<mountpoint>/<node_hash>. When a user accesses the contents such a file, go-ipfs will fetch the content of the corresponding node and provide them to the user. If the node being accessed is a symlink node, then it will try to resolve the symlink target and fetch it’s data.

Unfortunately, there is no limitation on what the symlink node can point to, and attackers can freely exploit this aspect since there is no other sanitisation.

Attackers can leverage such capabilities to leak infromation from nodes using go-ipfs' fuse mount capabilities.

2.2 Proof of Concept

To reproduce follow the following steps:

vagrant init ubuntu/groovy64
vagrant up
vagrant ssh

$ wget https://dist.ipfs.io/go-ipfs/v0.7.0/go-ipfs_v0.7.0_linux-amd64.tar.gz
$ tar -xvzf go-ipfs_v0.7.0_linux-amd64.tar.gz
$ cd go-ipfs
$ sudo bash install.sh

$ sudo mkdir /ipfs /ipns
$ sudo chown vagrant: /ipfs /ipns

$ echo "secret" > secret_file
$ mkdir poc
$ ln -s /home/vagrant/secret_file ./poc/not_so_secret

$ ipfs init
$ ipfs daemon --mount &
$ ipfs add -r ./poc
$ ipfs pin add <hash of poc node>

$ cat /ipfs/<hash_of_poc_node>/not_so_secret
secret

3 Recommendation

The weakness that’s affecting go-ipfs is not unique and potentially affects other projects too. Unfortunately Brazil doesn’t provide an option to jail symlinks by default.

However fuse implementations such as osxfuse do implement this behaviour (Mount options · osxfuse/osxfuse Wiki · GitHub). I’m planning to communicate with the maintainers of Brazil to see if they are amenable to adding symlink jailing functionality to the Brazil library.

If acceptable, I’d like to share this report with the maintainers of brazil to demonstrate the merit in adding this security control.

Otherwise, it should be sufficient to sanitise node data so that only symlinks pointing within the mount are accepted.

3.1 Timeline

Feb/04/2020	initial disclosure vendor

4 References