From owner-dev-commits-src-all@freebsd.org Fri Jan 29 11:24:07 2021 Return-Path: Delivered-To: dev-commits-src-all@mailman.nyi.freebsd.org Received: from mx1.freebsd.org (mx1.freebsd.org [IPv6:2610:1c1:1:606c::19:1]) by mailman.nyi.freebsd.org (Postfix) with ESMTP id 456144E7E91; Fri, 29 Jan 2021 11:24:07 +0000 (UTC) (envelope-from git@FreeBSD.org) Received: from mxrelay.nyi.freebsd.org (mxrelay.nyi.freebsd.org [IPv6:2610:1c1:1:606c::19:3]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature RSA-PSS (4096 bits) server-digest SHA256 client-signature RSA-PSS (4096 bits) client-digest SHA256) (Client CN "mxrelay.nyi.freebsd.org", Issuer "R3" (verified OK)) by mx1.freebsd.org (Postfix) with ESMTPS id 4DRw2v1TTMz4lZr; Fri, 29 Jan 2021 11:24:07 +0000 (UTC) (envelope-from git@FreeBSD.org) Received: from gitrepo.freebsd.org (gitrepo.freebsd.org [IPv6:2610:1c1:1:6068::e6a:5]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature RSA-PSS (4096 bits) server-digest SHA256) (Client did not present a certificate) by mxrelay.nyi.freebsd.org (Postfix) with ESMTPS id 25C3421BBC; Fri, 29 Jan 2021 11:24:07 +0000 (UTC) (envelope-from git@FreeBSD.org) Received: from gitrepo.freebsd.org ([127.0.1.44]) by gitrepo.freebsd.org (8.16.1/8.16.1) with ESMTP id 10TBO7Ld054697; Fri, 29 Jan 2021 11:24:07 GMT (envelope-from git@gitrepo.freebsd.org) Received: (from git@localhost) by gitrepo.freebsd.org (8.16.1/8.16.1/Submit) id 10TBO7HW054696; Fri, 29 Jan 2021 11:24:07 GMT (envelope-from git) Date: Fri, 29 Jan 2021 11:24:07 GMT Message-Id: <202101291124.10TBO7HW054696@gitrepo.freebsd.org> To: src-committers@FreeBSD.org, dev-commits-src-all@FreeBSD.org, dev-commits-src-main@FreeBSD.org From: Mateusz Guzik Subject: git: 6affe1b71238 - main - select: employ fget_only_user MIME-Version: 1.0 Content-Type: text/plain; charset=utf-8 Content-Transfer-Encoding: 8bit X-Git-Committer: mjg X-Git-Repository: src X-Git-Refname: refs/heads/main X-Git-Reftype: branch X-Git-Commit: 6affe1b71238df7bbbca6e2059e5494d91e68d2d Auto-Submitted: auto-generated X-BeenThere: dev-commits-src-all@freebsd.org X-Mailman-Version: 2.1.34 Precedence: list List-Id: Commit messages for all branches of the src repository List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Fri, 29 Jan 2021 11:24:07 -0000 The branch main has been updated by mjg: URL: https://cgit.FreeBSD.org/src/commit/?id=6affe1b71238df7bbbca6e2059e5494d91e68d2d commit 6affe1b71238df7bbbca6e2059e5494d91e68d2d Author: Mateusz Guzik AuthorDate: 2021-01-28 23:33:46 +0000 Commit: Mateusz Guzik CommitDate: 2021-01-29 11:23:44 +0000 select: employ fget_only_user Since most select users are single-threaded this avoid a lot of work in the common case. For example select of 16 fds (ops/s): before: 2114536 after: 2991010 --- sys/kern/sys_generic.c | 35 ++++++++++++++++++++++------------- 1 file changed, 22 insertions(+), 13 deletions(-) diff --git a/sys/kern/sys_generic.c b/sys/kern/sys_generic.c index a055f4a9b597..dc2cd56f5077 100644 --- a/sys/kern/sys_generic.c +++ b/sys/kern/sys_generic.c @@ -1304,13 +1304,6 @@ selsetbits(fd_mask **ibits, fd_mask **obits, int idx, fd_mask bit, int events) return (n); } -static __inline int -getselfd_cap(struct filedesc *fdp, int fd, struct file **fpp) -{ - - return (fget_unlocked(fdp, fd, &cap_event_rights, fpp)); -} - /* * Traverse the list of fds attached to this thread's seltd and check for * completion. @@ -1327,10 +1320,12 @@ selrescan(struct thread *td, fd_mask **ibits, fd_mask **obits) fd_mask bit; int fd, ev, n, idx; int error; + bool only_user; fdp = td->td_proc->p_fd; stp = td->td_sel; n = 0; + only_user = FILEDESC_IS_ONLY_USER(fdp); STAILQ_FOREACH_SAFE(sfp, &stp->st_selq, sf_link, sfn) { fd = (int)(uintptr_t)sfp->sf_cookie; si = sfp->sf_si; @@ -1338,13 +1333,19 @@ selrescan(struct thread *td, fd_mask **ibits, fd_mask **obits) /* If the selinfo wasn't cleared the event didn't fire. */ if (si != NULL) continue; - error = getselfd_cap(fdp, fd, &fp); - if (error) + if (only_user) + error = fget_only_user(fdp, fd, &cap_event_rights, &fp); + else + error = fget_unlocked(fdp, fd, &cap_event_rights, &fp); + if (__predict_false(error != 0)) return (error); idx = fd / NFDBITS; bit = (fd_mask)1 << (fd % NFDBITS); ev = fo_poll(fp, selflags(ibits, idx, bit), td->td_ucred, td); - fdrop(fp, td); + if (only_user) + fput_only_user(fdp, fp); + else + fdrop(fp, td); if (ev != 0) n += selsetbits(ibits, obits, idx, bit, ev); } @@ -1366,9 +1367,11 @@ selscan(struct thread *td, fd_mask **ibits, fd_mask **obits, int nfd) int ev, flags, end, fd; int n, idx; int error; + bool only_user; fdp = td->td_proc->p_fd; n = 0; + only_user = FILEDESC_IS_ONLY_USER(fdp); for (idx = 0, fd = 0; fd < nfd; idx++) { end = imin(fd + NFDBITS, nfd); for (bit = 1; fd < end; bit <<= 1, fd++) { @@ -1376,12 +1379,18 @@ selscan(struct thread *td, fd_mask **ibits, fd_mask **obits, int nfd) flags = selflags(ibits, idx, bit); if (flags == 0) continue; - error = getselfd_cap(fdp, fd, &fp); - if (error) + if (only_user) + error = fget_only_user(fdp, fd, &cap_event_rights, &fp); + else + error = fget_unlocked(fdp, fd, &cap_event_rights, &fp); + if (__predict_false(error != 0)) return (error); selfdalloc(td, (void *)(uintptr_t)fd); ev = fo_poll(fp, flags, td->td_ucred, td); - fdrop(fp, td); + if (only_user) + fput_only_user(fdp, fp); + else + fdrop(fp, td); if (ev != 0) n += selsetbits(ibits, obits, idx, bit, ev); }