This patch adds a new Static Analyzer checker for the correct use of mutexes in the Magenta kernel.The checker analyzes uses of mutex_init, mutex_acquire, mutex_release, and mutex_destroy. It performs the core checks on usage of these APIs on mutex to make sure they are correct. For instance, we want to make sure mutexes are always initialized in the constructor and destroyed in the destructor. Also, we do not want to have paths where a mutex is released while not having been acquired first.
The checker was authored by Farid Molazem Tabrizi.
Before i forget: this API is a bit tricky, and there's a common but completely unobvious mistake that you're making here. reportMutexError(..., false) is producing a transition to a non-fatal error node. The whole point of the non-fatal error node is that analysis continues past this node. After adding the transition on this line, you effectively split the analysis into two paths, one following the non-fatal error node, another containing the MutexMap change.
This doubles up the time it takes to analyze the rest of the code (growing exponentially if encountered multiple times; probably rises to the node limit very soon, destroying coverage), and the additional path through the error node is not expected here (but it might be for some checkers, so the API is not quite at fault) - the behavior of the checker on this path might also be unexpected (it essentially skips the initialization of the mutex).
The right way to do this is to remember the exploded node generated by generateNonFatalErrorNode(), and put the new transition on top of that node (if the report has actually been thrown) by using the addTransition(St, N) override (or make the transition normally if it isn't).
I really wish there was a good and universal solution to make the transition API more obvious, feel sorry about that every time i see one of those problems.