Am 13.04.2018 um 13:05 hat Paolo Bonzini geschrieben: > On 13/04/2018 10:01, Kevin Wolf wrote: > >> Or bs->quiescent, for the sake of bikeshedding. > > Yes, that sounds better. > > > > The only problem with the proposal as I made it is that it's wrong. We > > can't keep bs->quiescent until bdrv_do_drained_end() because the caller > > can issue new requests and then have a nested drained section that needs > > to wait for all requests again instead of deciding that everything is > > already quiescent. > > > > Maybe where we should really reset it is in the initial recursion of > > bdrv_do_drained_begin(), specifically in bdrv_do_drained_begin_quiesce() > > which is called by both the parent and the child recursion. > > > > There don't seem to be completely obviously correct solutions (can't an > > I/O thread be draining a specific node while the main loop runs > > drain_all?), but this would probably be the most obvious one. > > Or use a hash table?
I don't think it would be any more obvious, but it would bring in quite a bit of additional complexity (structural, not computational), with multiple places that create a hash table and then it would have to be passed down to all functions involved in the recursion etc. The fundamental question would stay the same as with bool quiescent: When do you have to enter a node in the hash table, and when do you have to remove it again? The first question is easy, you mark it quiescent when bdrv_drain_poll() returns false. The second is a bit harder, but reseting the quiescent state in bdrv_do_drained_begin_quiesce() feels like the best place. It's much simpler than recursively resetting it in all places that start new activity (which would include BlockBackend users, not only nodes). Kevin