In Linux, according to the Filesystem Hierarchy Standard, /opt is the designated location for add-on application software packages. Thus, when developing my own software package, which is not a dependency for anything else, I would place that in /opt/somepackage, with a hierarchy of my choice underneath.

FreeBSD, according to the link above, does not strictly follow the FHS but installs third-party packages into /usr/local. OPNsense, which is based on FreeBSD, installs its own code (at least in part) into /usr/local/opnsense. The hier manpage on FreeBSD makes no mention of /opt – thus a package installing itself in that location would be unlikely to collide with anything else, but would introduce a top-level path that is almost as exotic as installing straight to /somepackage.

What would be the appropriate installation location in FreeBSD? /usr/local/somepackage instead of /opt/somepackage, again with a hierarchy of my choice underneath?

Note that I have seen the following posts, which provide some insight but don’t fully answer my question:

3 Answers 3


You install user programs in /usr/local/. There is no /opt in the standard install or mentioned in the hier man page.

From the man page:

/usr/ contains the majority of user utilities and applications


local/ local executables, libraries, etc. Also used as the default destination for the ports(7) framework. Within local/, the general layout sketched out by hier for /usr should be used.



 This manual page documents the default FreeBSD file system layout, but
 the actual hierarchy on a given system is defined at the system
 administrator's discretion.  A well-maintained installation will include
 a customized version of this document.

If you are installing an executable that includes other things like documentation, data, helper files, etc., I would put this in /usr/local/$package because it's a package of things. If it's the executable alone, it should go in /usr/local/bin cause it's a binary.

  • Which leaves me with the question: /usr/local/{bin,sbin,man,lib} or /usr/local/$PACKAGE? I don’t see that answered here – except that the notes state I can drop my code basically anywhere, even straight in the root dir (/$PACKAGE), as long as I provide a customized version of hier in some form. The latter could be just a text file placed in a location of my choice.
    – user149408
    Commented May 5 at 11:43
  • @user149408 Edited my answer with more detail
    – Rob
    Commented May 5 at 11:48
  • Thanks, that is also in line with what OPNsense does for its own opnsense package. Seems there isn’t a clearly designated place, but of all the proposals made so far this looks cleanest.
    – user149408
    Commented May 5 at 15:13

At least on OpenBSD (and I'm guessing the same applies to FreeBSD), /usr/local is essentially managed by the OS' package system. If your "custom software package" will not be handled by the package system, there is a possibility of conflicts - e.g. files with the same name - with other packages that are. So, unless, you are building a package to be installed via the OS's package system, I'd stick to putting it under /opt, to make sure it doesn't interfere with other packages (or be interfered with).

  • What’s the standard hierarchy for /usr/local in FreeBSD? /usr/local/{bin,sbin,man,lib} or usr/local/$PACKAGE? In the first case, conflicts are likely and I wouldn’t feel comfortable placing anything in there. In the latter case, there should be no conflicts as long as the name of my package doesn’t collide with anything in the repos, which shouldn’t be that hard to avoid. Installing two packages with the same name (one from the repo, one custom) but different contents will probably cause other issues as well, so I’m not too worried about file collisions in that case.
    – user149408
    Commented Apr 28 at 18:21
  • Here's the canonical answer: FreeBSD's man page for hier. Its bin, sbin, etc. Note the absence of /opt, although that obviously doesn't mean it can't exist.
    – Zé Loff
    Commented Apr 28 at 21:14
  • I see hier (7) mentions neither /opt nor /usr/local/$PACKAGE (which another answer mentions). As per hier (7) and ports (7), BSD ports go in /usr/local/ports/$CATEGORY/$PORT, e.g. /usr/local/ports/sysutils/fooadmin for fooadmin from the sysutils category. As in FreeBSD terminology, port and package are pretty much synonyms, that would imply installing your own package into /usr/local/ports/$CATEGORY/$PACKAGE, even if it’s not strictly part of the FreeBSD Ports Collection. You’d run into issues only if the latter has a package of the same name in the same category.
    – user149408
    Commented Apr 29 at 18:57
  • 1
    /usr/ports is not for installing packages. It is where the porting infrastructure is stored, i.e., the "recipes" for building the packages themselves. You can, of course, create a port of your own software, and then you can install the resulting package file with the OS's package management tools.
    – Zé Loff
    Commented Apr 29 at 19:02
  • Indeed, I should have read this more thoroughly, /usr/ports is for source code, patches and build recipes, not executable binaries.
    – user149408
    Commented Apr 29 at 19:21

The use of /usr/local vs. /opt/ transcends BSD and predates linux.

Typically both directories are used for installing software that doesn't come with the operating system. The quote about software "not installed by the package manager" really means not from the repos and packages supplied by the OS. Many third party package managers and repos will install into /opt.

Historically, all locally installed (non-distro) packages were dumped into /usr/local usually in the {bin,sbin,man,lib} kind of hierarchy.

But this gets messy fast, since files from multiple packages will all be jumbled together, possibly stepping on each other, and making update paths unclear.

So a practice was started for installing things in /usr/local/$packagename/{bin,lib,man} which was better but still messy. To fix this, using /opt was encouraged for this, leaving /usr/local/ to still be a mess, but at least some of the packages were outside of that mess.

But really, in the end, you can install software anywhere, including $HOME/mysillyapps/$package/{bin,man,lib} and the only requirement is that you add bin to $PATH (although other envs help too) so using /usr/local/ or /opt is kind of an agnostic thing, this works anywhere.

The hope is that by adding $packagename (or $packagename-$version ) to the directory name, the risk of collisions with package manager installed apps is reduced no matter where it gets installed. (Surely you're not hand installing and package manager installing the same package!)

The only OS flavor relevant thing here is that /usr/local/bin may already be added to PATH by default.

  • Sure, I can create a directory named $package right underneath root, install my package files there and make sure it is on $PATH, but that would be a highly unexpected location. I was wondering if there is some kind of de-facto standard for installing to a location which includes the package name.
    – user149408
    Commented Apr 29 at 19:27

You must log in to answer this question.

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