Contributing to GHC

via Phabricator

About two weeks ago I gave a talk on “Contriubting to GHC via Phabricator” at the local haskell.sg Meetup. Sadly the microphone died after a few minutes into the recording, and as such the video has no audio for most of the talk and is pretty useless. As the topic might be of interest to those who could not attend, I’ll write down the content of the talk as good as I can.

Phabricator?!

Let’s start with what Phabricator is, Phabricator is the code review tool GHC uses. It was originally developed at Facebook by Evan Priestley, who has since founded Phacility, Inc where the development of Phabricator continues.

Phabricator is not just used at GHC, it is also used for other projects like LLVM, the Wikimedia Foundation, FreeBSD, and a many more.

I will now try to demonstrate the usage of Phabricator for a simple change (with many pictures!).

Creating an account

When visiting phabricator.haskell.org, this is the first screen you will be greeted with. We will proceed to open an account so we can do something useful.

Upon clicking the “Log in” button you will reach the Log In form. While you can register a new account, I would suggest to use on of the available alternative account connectors.

For this example, we’ll use GitHub.

It will pull some username and Real Name from GitHub, but you will still be required to provide an email address.

With the account we could not start reviewing other peoples code, or even submit our own code for review. So let’s do this next.

I have a change in my tree

Phabricator is not really concerned how your local tree looks like. It essentially only cares about differences. So you can go wild with your local branch management; use git however you like.

For Phabricator try to think in patches (differences) instead of commits.

For the following example, I’ve been working on cross compiler related issues and while doing so, I usually accumulate lots of different fixes in my branch.

As such I now have some commit ( c93b5bbf1c adds -latomic to ghc-prim ) somewhere in my history, which I’d like to get into GHC proper.

Let’s go ahead and create a new branch from origin/master and cherry-pick the relevant commit onto it. You could do this however you like. Just make sure you have a handle on the range for your patch.

Let’s ask git what the actual patch looks like. git diff origin/master should tell us. Note the stupid white space!

Enter arcanist

Phabricator has a companion tool called arc anist:

“arc — arcanist, a code review and revision management utility”

To install it, we need to clone the following two repositories:



$ git clone $ git clone https://github.com/phacility/libphutil.git $ git clone https://github.com/phacility/arcanist.git

Then add arcanist/bin to your PATH .

Link arc with your phabricator account

Next we’ll need to tell connect arc with our phabricator account on phabricator.haskell.org. To do this we need to run the follwing command from within the ghc repository

ghc $ arc install-certificate

arc will request an API Token, and tells us where we can get it from.

Navigating to the URL arcanist gave us, presents us with the following page. Simply copying the API Token …

… and pasting it into the terminal should be enough for arc to properly link your haskell phabricator account with your ghc repository. This needs to be done only once!

Let’s send the patch for review. I like to be explicit about the offset, but usually arc should figure out the origin/master offset on its own.

Next we might be greeted with this. What is this?! arc wants to be helpful here and tell us that we have lots of untracked files in our repository. If you are sure you have committed everything you want to submit for review, it’s safe to say y here.

Alright, so now your $EDITOR will open, and you will be asked to fill out some metadata about your patch.

Here’s an example of the filled out metadata. I’ve added a summary and added Ben Gamari as a reviewer. Let’s hope he’s not too busy!

Upon existing your editor, arc will run a few linters over the patch. And of course it found the stupid white space from before. It is however helpful enough to ask us if we just want to have this change (removal of white space) applied.

Removing the white space seems reasonable. So let’s have arc apply the patch. Next it wants to know if we want to amend HEAD. And yes it makes sense to just amend this into the last commit. So I’ll go with y here.

Alright and we are done. arc has sent the patch to phabricator; and we got a Differential identifier back D4253 in this case.

Navigating to the URL of the Differential will present us with this page.

A bit further down we’ll see the summary we entered and the Reviewer(s) we specified.

And even further down we can see the patch we submitted.

Now those lines look suspicious, why is this only for linux? Let’s do a self-review here.

After adding our comment to the line range we selected, it is displayed but not the gray dashed border. It is not submitted. I think phabricator UI could be a bit better.

We still need to scroll to the bottom and hit “Submit” so that our remarks are actually submitted and others can see them.

At the top, Phabricator will now show the added comment in the timeline.

Let’s go back to our source and change the patch. Adding a comment probably doesn’t hurt and might help the next one reading the “code”.

Next, create a new commit and let’s take a look at the new patch.

Here we now see the new patch. Note that not much from the previous patch is left, because we essentially rewrote everything. The second commit reversed everything from the first after all.

Time for arc diff origin/master again.

And again we are greeted with the untracked files screen.

However the $EDITOR now has a slightly different template because we are updating a differential and are not creating a new one. Here we can specify what we changed. By default it will pull information from the commit messages.

After exiting the $EDITOR arc tells us it has updated the Differential.

Looking at the timeline we see the new update item as well.

Of course the patch now looks different and our new patch is displayed. We’ll mark the comment as Done…

… and again we’ll need to hit Submit for this to be actually submitted.

The marking of the comment as done is now also reflected in the timeline.

Where to go from here?