Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

Merge tag 'fuse-fixes-4.20-rc3' of git://git.kernel.org/pub/scm/linux/kernel/git/mszeredi/fuse

Pull fuse fixes from Miklos Szeredi:
"A couple of fixes, all bound for -stable (i.e. not regressions in this
cycle)"

* tag 'fuse-fixes-4.20-rc3' of git://git.kernel.org/pub/scm/linux/kernel/git/mszeredi/fuse:
fuse: fix use-after-free in fuse_direct_IO()
fuse: fix possibly missed wake-up after abort
fuse: fix leaked notify reply

+15 -5
+12 -4
fs/fuse/dev.c
··· 165 165 166 166 static void fuse_drop_waiting(struct fuse_conn *fc) 167 167 { 168 - if (fc->connected) { 169 - atomic_dec(&fc->num_waiting); 170 - } else if (atomic_dec_and_test(&fc->num_waiting)) { 168 + /* 169 + * lockess check of fc->connected is okay, because atomic_dec_and_test() 170 + * provides a memory barrier mached with the one in fuse_wait_aborted() 171 + * to ensure no wake-up is missed. 172 + */ 173 + if (atomic_dec_and_test(&fc->num_waiting) && 174 + !READ_ONCE(fc->connected)) { 171 175 /* wake up aborters */ 172 176 wake_up_all(&fc->blocked_waitq); 173 177 } ··· 1772 1768 req->in.args[1].size = total_len; 1773 1769 1774 1770 err = fuse_request_send_notify_reply(fc, req, outarg->notify_unique); 1775 - if (err) 1771 + if (err) { 1776 1772 fuse_retrieve_end(fc, req); 1773 + fuse_put_request(fc, req); 1774 + } 1777 1775 1778 1776 return err; 1779 1777 } ··· 2225 2219 2226 2220 void fuse_wait_aborted(struct fuse_conn *fc) 2227 2221 { 2222 + /* matches implicit memory barrier in fuse_drop_waiting() */ 2223 + smp_mb(); 2228 2224 wait_event(fc->blocked_waitq, atomic_read(&fc->num_waiting) == 0); 2229 2225 } 2230 2226
+3 -1
fs/fuse/file.c
··· 2924 2924 } 2925 2925 2926 2926 if (io->async) { 2927 + bool blocking = io->blocking; 2928 + 2927 2929 fuse_aio_complete(io, ret < 0 ? ret : 0, -1); 2928 2930 2929 2931 /* we have a non-extending, async request, so return */ 2930 - if (!io->blocking) 2932 + if (!blocking) 2931 2933 return -EIOCBQUEUED; 2932 2934 2933 2935 wait_for_completion(&wait);