From owner-svn-src-head@FreeBSD.ORG Fri May 15 14:41:45 2009 Return-Path: Delivered-To: svn-src-head@freebsd.org Received: from mx1.freebsd.org (mx1.freebsd.org [IPv6:2001:4f8:fff6::34]) by hub.freebsd.org (Postfix) with ESMTP id B0E061065670; Fri, 15 May 2009 14:41:45 +0000 (UTC) (envelope-from kib@FreeBSD.org) Received: from svn.freebsd.org (svn.freebsd.org [IPv6:2001:4f8:fff6::2c]) by mx1.freebsd.org (Postfix) with ESMTP id 84BCA8FC0A; Fri, 15 May 2009 14:41:45 +0000 (UTC) (envelope-from kib@FreeBSD.org) Received: from svn.freebsd.org (localhost [127.0.0.1]) by svn.freebsd.org (8.14.3/8.14.3) with ESMTP id n4FEfjsu026330; Fri, 15 May 2009 14:41:45 GMT (envelope-from kib@svn.freebsd.org) Received: (from kib@localhost) by svn.freebsd.org (8.14.3/8.14.3/Submit) id n4FEfjvC026328; Fri, 15 May 2009 14:41:45 GMT (envelope-from kib@svn.freebsd.org) Message-Id: <200905151441.n4FEfjvC026328@svn.freebsd.org> From: Konstantin Belousov Date: Fri, 15 May 2009 14:41:45 +0000 (UTC) To: src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org X-SVN-Group: head MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Cc: Subject: svn commit: r192144 - head/sys/kern X-BeenThere: svn-src-head@freebsd.org X-Mailman-Version: 2.1.5 Precedence: list List-Id: SVN commit messages for the src tree for head/-current List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Fri, 15 May 2009 14:41:46 -0000 Author: kib Date: Fri May 15 14:41:44 2009 New Revision: 192144 URL: http://svn.freebsd.org/changeset/base/192144 Log: Revert r192094. The revision caused problems for sysctl(3) consumers that expect that oldlen is filled with required buffer length even when supplied buffer is too short and returned error is ENOMEM. Redo the fix for kern.proc.filedesc, by reverting the req->oldidx when remaining buffer space is too short for the current kinfo_file structure. Also, only ignore ENOMEM. We have to convert ENOMEM to no error condition to keep existing interface for the sysctl, though. Reported by: ed, Florian Smeets Tested by: pho Modified: head/sys/kern/kern_descrip.c head/sys/kern/kern_sysctl.c Modified: head/sys/kern/kern_descrip.c ============================================================================== --- head/sys/kern/kern_descrip.c Fri May 15 14:30:37 2009 (r192143) +++ head/sys/kern/kern_descrip.c Fri May 15 14:41:44 2009 (r192144) @@ -2883,6 +2883,7 @@ sysctl_kern_proc_filedesc(SYSCTL_HANDLER struct proc *p; struct tty *tp; int vfslocked; + size_t oldidx; name = (int *)arg1; if ((p = pfind((pid_t)name[0])) == NULL) @@ -3061,14 +3062,26 @@ sysctl_kern_proc_filedesc(SYSCTL_HANDLER strlen(kif->kf_path) + 1; kif->kf_structsize = roundup(kif->kf_structsize, sizeof(uint64_t)); + oldidx = req->oldidx; error = SYSCTL_OUT(req, kif, kif->kf_structsize); - if (error) + if (error) { + if (error == ENOMEM) { + /* + * The hack to keep the ABI of sysctl + * kern.proc.filedesc intact, but not + * to account a partially copied + * kinfo_file into the oldidx. + */ + req->oldidx = oldidx; + error = 0; + } break; + } } FILEDESC_SUNLOCK(fdp); fddrop(fdp); free(kif, M_TEMP); - return (0); + return (error); } static SYSCTL_NODE(_kern_proc, KERN_PROC_FILEDESC, filedesc, CTLFLAG_RD, Modified: head/sys/kern/kern_sysctl.c ============================================================================== --- head/sys/kern/kern_sysctl.c Fri May 15 14:30:37 2009 (r192143) +++ head/sys/kern/kern_sysctl.c Fri May 15 14:41:44 2009 (r192144) @@ -1223,9 +1223,9 @@ sysctl_old_kernel(struct sysctl_req *req if (i > 0) bcopy(p, (char *)req->oldptr + req->oldidx, i); } + req->oldidx += l; if (req->oldptr && i != l) return (ENOMEM); - req->oldidx += l; return (0); } @@ -1322,10 +1322,9 @@ sysctl_old_user(struct sysctl_req *req, size_t i, len, origidx; origidx = req->oldidx; - if (req->oldptr == NULL) { - req->oldidx += l; + req->oldidx += l; + if (req->oldptr == NULL) return (0); - } /* * If we have not wired the user supplied buffer and we are currently * holding locks, drop a witness warning, as it's possible that @@ -1347,7 +1346,6 @@ sysctl_old_user(struct sysctl_req *req, return (error); if (i < l) return (ENOMEM); - req->oldidx += l; return (0); }