• Boqun Feng's avatar
    lockdep: Extend __bfs() to work with multiple types of dependencies · 6971c0f3
    Boqun Feng authored
    Now we have four types of dependencies in the dependency graph, and not
    all the pathes carry real dependencies (the dependencies that may cause
    a deadlock), for example:
    
    	Given lock A and B, if we have:
    
    	CPU1			CPU2
    	=============		==============
    	write_lock(A);		read_lock(B);
    	read_lock(B);		write_lock(A);
    
    	(assuming read_lock(B) is a recursive reader)
    
    	then we have dependencies A -(ER)-> B, and B -(SN)-> A, and a
    	dependency path A -(ER)-> B -(SN)-> A.
    
    	In lockdep w/o recursive locks, a dependency path from A to A
    	means a deadlock. However, the above case is obviously not a
    	deadlock, because no one holds B exclusively, therefore no one
    	waits for the other to release B, so who get A first in CPU1 and
    	CPU2 will run non-blockingly.
    
    	As a result, dependency path A -(ER)-> B -(SN)-> A is not a
    	real/strong dependency that could cause a deadlock.
    
    From the observation above, we know that for a dependency path to be
    real/strong, no two adjacent dependencies can be as -(*R)-> -(S*)->.
    
    Now our mission is to make __bfs() traverse only the strong dependency
    paths, which is simple: we record whether we only have -(*R)-> for the
    previous lock_list of the path in lock_list::only_xr, and when we pick a
    dependency in the traverse, we 1) filter out -(S*)-> dependency if the
    previous lock_list only has -(*R)-> dependency (i.e. ->only_xr is true)
    and 2) set the next lock_list::only_xr to true if we only have -(*R)->
    left after we filter out dependencies based on 1), otherwise, set it to
    false.
    
    With this extension for __bfs(), we now need to initialize the root of
    __bfs() properly (with a correct ->only_xr), to do so, we introduce some
    helper functions, which also cleans up a little bit for the __bfs() root
    initialization code.
    Signed-off-by: default avatarBoqun Feng <boqun.feng@gmail.com>
    Signed-off-by: default avatarPeter Zijlstra (Intel) <peterz@infradead.org>
    Link: https://lkml.kernel.org/r/20200807074238.1632519-8-boqun.feng@gmail.com
    6971c0f3
lockdep.c 152 KB