From gnehzuil.liu@gmail.com Fri Mar 1 03:11:12 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=FREEMAIL_FROM,T_DKIM_INVALID autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id D57137F62 for ; Fri, 1 Mar 2013 03:11:12 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay2.corp.sgi.com (Postfix) with ESMTP id B56F7304048 for ; Fri, 1 Mar 2013 01:11:09 -0800 (PST) X-ASG-Debug-ID: 1362129068-04bdf02297201c0001-NocioJ Received: from mail-pa0-f45.google.com (mail-pa0-f45.google.com [209.85.220.45]) by cuda.sgi.com with ESMTP id GWiz9kbf9aFAbrLW (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Fri, 01 Mar 2013 01:11:08 -0800 (PST) X-Barracuda-Envelope-From: gnehzuil.liu@gmail.com X-Barracuda-Apparent-Source-IP: 209.85.220.45 X-Barracuda-IPDD: Level1 [gmail.com/209.85.220.45] Received: by mail-pa0-f45.google.com with SMTP id kl14so1703913pab.18 for ; Fri, 01 Mar 2013 01:11:08 -0800 (PST) X-Barracuda-IPDD: Level1 [gmail.com/209.85.220.45] X-Barracuda-IPDD: Level1 [gmail.com/209.85.220.45] DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20120113; h=x-received:from:to:cc:subject:date:message-id:x-mailer; bh=STVDlqKY/JoRpsJZ8IyJ/H0+ttrqXgHfUyqdLcjc4uI=; b=vtY5VdPJ4zCT/do+emDGahgN/cFkaf3WVF6/UfJlPF5i321smb3iGAXCToo3henP6d VrfgxbRMCdIgJK2/oUTKwH36D1YFpYpxqv9pqY9PV895JeVfsPgZ30oD8AWANxjr5xG9 9f1utiwIPg+zrsyE1AokvTcp0B8GFPWDdlQF9hCUiIidW5xI6AGTLRFKMmvaq9n0Welu yZ+mq6gjOjILv6rhVkkbXHzGjvCxepDamIAaWlyag5MduDli3FHDwNv34M1jTuAc5kVp 8Cq1ol0YZmPJokVHlv+FX/eKSXn1L2UkPFD8D/o0UtC/j94bKYRTNpOuUlA2kjUukwsg zpkw== X-Received: by 10.68.203.9 with SMTP id km9mr7544220pbc.191.1362129068356; Fri, 01 Mar 2013 01:11:08 -0800 (PST) Received: from lz-desktop.taobao.ali.com ([182.92.247.2]) by mx.google.com with ESMTPS id y9sm12464397paw.1.2013.03.01.01.11.05 (version=TLSv1 cipher=RC4-SHA bits=128/128); Fri, 01 Mar 2013 01:11:07 -0800 (PST) From: Zheng Liu To: xfs@oss.sgi.com Cc: Zheng Liu Subject: [PATCH] xfstests: use right path in _require_defrag() Date: Fri, 1 Mar 2013 17:25:59 +0800 X-ASG-Orig-Subj: [PATCH] xfstests: use right path in _require_defrag() Message-Id: <1362129959-4504-1-git-send-email-wenqing.lz@taobao.com> X-Mailer: git-send-email 1.7.12.rc2.18.g61b472e X-Barracuda-Connect: mail-pa0-f45.google.com[209.85.220.45] X-Barracuda-Start-Time: 1362129068 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=DKIM_SIGNED, DKIM_VERIFIED X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.123929 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature In _require_defrag defragmentation command path is fixed. That will cause that this test case is skipped in some distributions. Signed-off-by: Zheng Liu --- common.defrag | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/common.defrag b/common.defrag index ea6c14c..7be8ad9 100644 --- a/common.defrag +++ b/common.defrag @@ -24,10 +24,10 @@ _require_defrag() { case "$FSTYP" in xfs) - DEFRAG_PROG=/usr/sbin/xfs_fsr + DEFRAG_PROG=`which xfs_fsr` ;; ext4|ext4dev) - DEFRAG_PROG=/usr/bin/e4defrag + DEFRAG_PROG=`which e4defrag` ;; btrfs) DEFRAG_PROG="$BTRFS_UTIL_PROG filesystem defragment" @@ -38,7 +38,7 @@ _require_defrag() esac _require_command $DEFRAG_PROG - _require_command /usr/sbin/filefrag + _require_command `which filefrag` } _extent_count() -- 1.7.12.rc2.18.g61b472e From qcai@redhat.com Fri Mar 1 03:20:33 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 761D37FAB for ; Fri, 1 Mar 2013 03:20:33 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay3.corp.sgi.com (Postfix) with ESMTP id 08B8CAC002 for ; Fri, 1 Mar 2013 01:20:29 -0800 (PST) X-ASG-Debug-ID: 1362129626-04cb6c2b03202b0001-NocioJ Received: from mx3-phx2.redhat.com (mx3-phx2.redhat.com [209.132.183.24]) by cuda.sgi.com with ESMTP id ipolb2r5VtKvGM0z for ; Fri, 01 Mar 2013 01:20:27 -0800 (PST) X-Barracuda-Envelope-From: qcai@redhat.com X-Barracuda-Apparent-Source-IP: 209.132.183.24 Received: from zmail14.collab.prod.int.phx2.redhat.com (zmail14.collab.prod.int.phx2.redhat.com [10.5.83.16]) by mx3-phx2.redhat.com (8.13.8/8.13.8) with ESMTP id r219KIUi030988; Fri, 1 Mar 2013 04:20:19 -0500 Date: Fri, 1 Mar 2013 04:20:18 -0500 (EST) From: CAI Qian To: Dave Chinner Cc: xfs@oss.sgi.com, Steve Best Message-ID: <220575861.7590457.1362129618880.JavaMail.root@redhat.com> In-Reply-To: <20130228115410.GN5551@dastard> Subject: Re: possible fsync02() xfs slowness regression on power7 MIME-Version: 1.0 X-ASG-Orig-Subj: Re: possible fsync02() xfs slowness regression on power7 Content-Type: text/plain; charset=utf-8 Content-Transfer-Encoding: quoted-printable X-Originating-IP: [10.66.13.185] X-Mailer: Zimbra 7.2.0_GA_2669 (ZimbraWebClient - FF3.0 (Linux)/7.2.0_GA_2669) X-Barracuda-Connect: mx3-phx2.redhat.com[209.132.183.24] X-Barracuda-Start-Time: 1362129626 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.11 X-Barracuda-Spam-Status: No, SCORE=0.11 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_SA085, BSF_SC2_SA022a X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.123931 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.01 BSF_SC2_SA022a Custom Rule SA022a 0.10 BSF_SC0_SA085 Custom Rule SA085 ----- =E5=8E=9F=E5=A7=8B=E9=82=AE=E4=BB=B6 ----- > =E5=8F=91=E4=BB=B6=E4=BA=BA: "Dave Chinner" > =E6=94=B6=E4=BB=B6=E4=BA=BA: "CAI Qian" > =E6=8A=84=E9=80=81: xfs@oss.sgi.com, "Steve Best" > =E5=8F=91=E9=80=81=E6=97=B6=E9=97=B4: =E6=98=9F=E6=9C=9F=E5=9B=9B, 2013= =E5=B9=B4 2 =E6=9C=88 28=E6=97=A5 =E4=B8=8B=E5=8D=88 7:54:10 > =E4=B8=BB=E9=A2=98: Re: possible fsync02() xfs slowness regression on pow= er7 >=20 > On Thu, Feb 28, 2013 at 04:28:35AM -0500, CAI Qian wrote: > > This LTP test starting to fail using the latest upstream kernel on > > one of the power7 > > systems here, http://tinyurl.com/bngwouj > >=20 > > # ./fsync02 > > fsync02 1 TFAIL : fsync took too long: 252.000000 seconds; > > max_block: 214 > >=20 > > When it is working, the test is almost returned immediately. The > > bisecting so far > > indicated that one or a few of the following could be culprits. > >=20 > > # git log --pretty=3Doneline > > 498f7f505dc79934c878c7667840c50c64f232fc..b199c8a4ba11879df87daad496cee= e41fdc6aa82 >=20 > They are all patches committed more than 2 years ago, and none of > them are platform specific. This sounds more like a machine specific > issue than a platform specific problem (i.e. lots of RAM, slow, > slow disk). >=20 > In future when reporting a bug, please tell use hardware you are > using as per: >=20 > http://xfs.org/index.php/XFS_FAQ#Q:_What_information_should_I_include_whe= n_reporting_a_problem.3F >=20 > Given that this is a sparse file test that repeatedly extends the > file, this is the likely culprit: >=20 > > 055388a3188f56676c21e92962fc366ac8b5cb72 xfs: dynamic speculative > > EOF preallocation Yes, you are right, just confirmed it. Nice catch! >=20 > And this commit in 3.9-rc1: >=20 > a1e16c2 xfs: limit speculative prealloc size on sparse files Just back-ported it and running at the moment and will let you know. Thanks= Dave. >=20 > should fix the problem. Please confirm these commits are the cause > and the fix respectively.... >=20 > Cheers, >=20 > Dave. > -- > Dave Chinner > david@fromorbit.com >=20 From david@fromorbit.com Fri Mar 1 03:21:24 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 0FA1B7FAF for ; Fri, 1 Mar 2013 03:21:24 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id E3448304039 for ; Fri, 1 Mar 2013 01:21:23 -0800 (PST) X-ASG-Debug-ID: 1362129681-04cbb07dbd23a60001-NocioJ Received: from ipmail07.adl2.internode.on.net (ipmail07.adl2.internode.on.net [150.101.137.131]) by cuda.sgi.com with ESMTP id br7wrChJRftS8q9F for ; Fri, 01 Mar 2013 01:21:22 -0800 (PST) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.131 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: Ao0OAClyMFF5LOvW/2dsb2JhbABFhWa3OIUVfRdzgh8BAQU6HCMQCAMOCgklDwUlAyETiBLBGhWOICI9B4JfYQOWQolkhwiDHA Received: from ppp121-44-235-214.lns20.syd7.internode.on.net (HELO dastard) ([121.44.235.214]) by ipmail07.adl2.internode.on.net with ESMTP; 01 Mar 2013 19:51:20 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UBM9W-0006L7-Vd; Fri, 01 Mar 2013 20:21:19 +1100 Date: Fri, 1 Mar 2013 20:21:18 +1100 From: Dave Chinner To: Zheng Liu Cc: xfs@oss.sgi.com, Zheng Liu Subject: Re: [PATCH] xfstests: use right path in _require_defrag() Message-ID: <20130301092118.GA23616@dastard> X-ASG-Orig-Subj: Re: [PATCH] xfstests: use right path in _require_defrag() References: <1362129959-4504-1-git-send-email-wenqing.lz@taobao.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <1362129959-4504-1-git-send-email-wenqing.lz@taobao.com> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail07.adl2.internode.on.net[150.101.137.131] X-Barracuda-Start-Time: 1362129681 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.123931 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Fri, Mar 01, 2013 at 05:25:59PM +0800, Zheng Liu wrote: > In _require_defrag defragmentation command path is fixed. That will > cause that this test case is skipped in some distributions. > > Signed-off-by: Zheng Liu > --- > common.defrag | 6 +++--- > 1 file changed, 3 insertions(+), 3 deletions(-) > > diff --git a/common.defrag b/common.defrag > index ea6c14c..7be8ad9 100644 > --- a/common.defrag > +++ b/common.defrag > @@ -24,10 +24,10 @@ _require_defrag() > { > case "$FSTYP" in > xfs) > - DEFRAG_PROG=/usr/sbin/xfs_fsr > + DEFRAG_PROG=`which xfs_fsr` > ;; > ext4|ext4dev) > - DEFRAG_PROG=/usr/bin/e4defrag > + DEFRAG_PROG=`which e4defrag` > ;; > btrfs) > DEFRAG_PROG="$BTRFS_UTIL_PROG filesystem defragment" > @@ -38,7 +38,7 @@ _require_defrag() > esac > > _require_command $DEFRAG_PROG > - _require_command /usr/sbin/filefrag > + _require_command `which filefrag` > } $DEFRAG_PROG and $FILEFRAG_PROG should be set up in common.config with set_prog_path, not in _require_defrag. Cheers, Dave. -- Dave Chinner david@fromorbit.com From ole.tange.work@gmail.com Fri Mar 1 03:37:40 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=FREEMAIL_FROM,T_DKIM_INVALID autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id BA3257FAF for ; Fri, 1 Mar 2013 03:37:40 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay3.corp.sgi.com (Postfix) with ESMTP id 4604BAC004 for ; Fri, 1 Mar 2013 01:37:40 -0800 (PST) X-ASG-Debug-ID: 1362130657-04cb6c2b01210a0001-NocioJ Received: from mail-wi0-f174.google.com (mail-wi0-f174.google.com [209.85.212.174]) by cuda.sgi.com with ESMTP id QUDqseexcAxgFqPT (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Fri, 01 Mar 2013 01:37:38 -0800 (PST) X-Barracuda-Envelope-From: ole.tange.work@gmail.com X-Barracuda-Apparent-Source-IP: 209.85.212.174 X-Barracuda-IPDD: Level1 [gmail.com/209.85.212.174] Received: by mail-wi0-f174.google.com with SMTP id hi8so8824102wib.1 for ; Fri, 01 Mar 2013 01:37:37 -0800 (PST) X-Barracuda-IPDD: Level1 [gmail.com/209.85.212.174] X-Barracuda-IPDD: Level1 [gmail.com/209.85.212.174] DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20120113; h=x-received:mime-version:sender:in-reply-to:references:from:date :x-google-sender-auth:message-id:subject:to:cc:content-type; bh=gqCwEJFiyNE67tt//wIDH3HovFBYXs332fjuTzRWsvI=; b=uEQx8FQ6wtsEEEnXeVEonDZtaFfV9XcehwxWFomZVPd7MnJ9V9nU5ToA174CwrzCh9 ydKWhSI80o7nKNSvBauI0p2zbYSDnW4dPjDreg6VBg6Wdt+8yvNCwug0G8wG4RiJMDy3 EV8+AnVCDR4EHslavWPZcfd+xLIkWU/S9yv+FD4EauIKrDVnN5J2l+qKTNYJXr6fcamt dU5EJKOlSt9DucRC5FC7MNNo4Fw0cwzdZJaNKe9FsYlHtf6YxLNDPc/5AWv7mLr0pflJ 0mNJs7PiQGbkWIz5mB9wEoOyHGg+hVCmnDy5IsacAaqh2k2FbyZPMRxQls8bD6YI5zTo tA5A== X-Received: by 10.180.87.98 with SMTP id w2mr2631290wiz.30.1362130657557; Fri, 01 Mar 2013 01:37:37 -0800 (PST) MIME-Version: 1.0 Sender: ole.tange.work@gmail.com Received: by 10.194.166.65 with HTTP; Fri, 1 Mar 2013 01:37:17 -0800 (PST) In-Reply-To: <512FA67D.2090708@sandeen.net> References: <512FA67D.2090708@sandeen.net> From: Ole Tange Date: Fri, 1 Mar 2013 10:37:17 +0100 X-Google-Sender-Auth: 3JNBv3COlz_Mu2YIclD9tv7giew Message-ID: Subject: Re: xfs_repair segfaults To: Eric Sandeen X-ASG-Orig-Subj: Re: xfs_repair segfaults Cc: xfs@oss.sgi.com Content-Type: text/plain; charset=ISO-8859-1 X-Barracuda-Connect: mail-wi0-f174.google.com[209.85.212.174] X-Barracuda-Start-Time: 1362130658 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=DKIM_SIGNED, DKIM_VERIFIED X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.123931 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature On Thu, Feb 28, 2013 at 7:48 PM, Eric Sandeen wrote: > On 2/28/13 9:22 AM, Ole Tange wrote: >> /usr/local/src/xfsprogs-3.1.10/repair# ./xfs_repair -n /dev/md5p1 [...] >> Segmentation fault (core dumped) >> >> Core put in: http://dna.ku.dk/~tange/tmp/xfs_repair.core.bz2 > > We'd need a binary w/ debug symbols to go along with it. http://dna.ku.dk/~tange/tmp/xfs_repair > an xfs_metadump might recreate the problem too. # sudo ./xfs_metadump.sh -g /dev/md5p1 - | pbzip2 > /home/tange/public_html/tmp/metadump.bz2 xfs_metadump: cannot init perag data (117) Copying log http://dna.ku.dk/~tange/tmp/metadump.bz2 Please consider providing an example in the man page for xfs_metadump e.g: xfs_metadump.sh -g /dev/sda2 meta.dump /Ole From david@fromorbit.com Fri Mar 1 05:17:31 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 18A5E7FB9 for ; Fri, 1 Mar 2013 05:17:31 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay2.corp.sgi.com (Postfix) with ESMTP id D84A5304051 for ; Fri, 1 Mar 2013 03:17:30 -0800 (PST) X-ASG-Debug-ID: 1362136648-04bdf022972bc90001-NocioJ Received: from ipmail07.adl2.internode.on.net (ipmail07.adl2.internode.on.net [150.101.137.131]) by cuda.sgi.com with ESMTP id SgMS4Ex9m58RpO6Q for ; Fri, 01 Mar 2013 03:17:29 -0800 (PST) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.131 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: Ao4OAPiNMFF5LOvW/2dsb2JhbABFhWa3OIUVfhdzgh8BAQQBOhwjBQsIAxgJJQ8FJQMhE4gNBcEAFY4gIj0Hgl9hA5ZCiWSHCIMc Received: from ppp121-44-235-214.lns20.syd7.internode.on.net (HELO dastard) ([121.44.235.214]) by ipmail07.adl2.internode.on.net with ESMTP; 01 Mar 2013 21:47:12 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UBNxV-0006Yu-Qr; Fri, 01 Mar 2013 22:17:01 +1100 Date: Fri, 1 Mar 2013 22:17:01 +1100 From: Dave Chinner To: Ole Tange Cc: xfs@oss.sgi.com Subject: Re: xfs_repair segfaults Message-ID: <20130301111701.GB23616@dastard> X-ASG-Orig-Subj: Re: xfs_repair segfaults References: MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail07.adl2.internode.on.net[150.101.137.131] X-Barracuda-Start-Time: 1362136648 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.123937 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Thu, Feb 28, 2013 at 04:22:08PM +0100, Ole Tange wrote: > I forced a RAID online. I have done that before and xfs_repair > normally removes the last hour of data or so, but saves everything > else. Why did you need to force it online? > Today that did not work: > > /usr/local/src/xfsprogs-3.1.10/repair# ./xfs_repair -n /dev/md5p1 > Phase 1 - find and verify superblock... > Phase 2 - using internal log > - scan filesystem freespace and inode maps... > flfirst 232 in agf 91 too large (max = 128) Can you run: # xfs_db -c "agf 91" -c p /dev/md5p1 And post the output? > # cat /proc/partitions |grep md5 > 9 5 125024550912 md5 > 259 0 107521114112 md5p1 > 259 1 17503434752 md5p2 Ouch. > # cat /proc/mdstat > Personalities : [raid0] [raid6] [raid5] [raid4] > md5 : active raid0 md1[0] md4[3] md3[2] md2[1] > 125024550912 blocks super 1.2 512k chunks > > md1 : active raid6 sdd[1] sdi[9] sdq[13] sdau[7] sdt[10] sdg[5] sdf[4] sde[2] > 31256138752 blocks super 1.2 level 6, 128k chunk, algorithm 2 > [10/8] [_UU_UUUUUU] > bitmap: 2/2 pages [8KB], 1048576KB chunk There are 2 failed devices in this RAID6 lun - i.e. no redundancy - and no rebuild in progress. Is this related to why you had to force the RAID online? > md4 : active raid6 sdo[13] sdu[9] sdad[8] sdh[7] sdc[6] sds[11] > sdap[3] sdao[2] sdk[1] > 31256138752 blocks super 1.2 level 6, 128k chunk, algorithm 2 > [10/8] [_UUUU_UUUU] > [>....................] recovery = 2.1% (84781876/3907017344) > finish=2196.4min speed=29003K/sec > bitmap: 2/2 pages [8KB], 1048576KB chunk and 2 failed devices here, too, with a rebuild underway that will take the best part of 2 days to complete... So, before even trying to diagnose the xfs_repair problem, can you tell us what actually went wrong with your md devices? Cheers, Dave. -- Dave Chinner david@fromorbit.com From ole.tange.work@gmail.com Fri Mar 1 06:25:02 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=FREEMAIL_FROM,T_DKIM_INVALID autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id CC9BB7FBC for ; Fri, 1 Mar 2013 06:25:02 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay2.corp.sgi.com (Postfix) with ESMTP id B7D6D304043 for ; Fri, 1 Mar 2013 04:24:59 -0800 (PST) X-ASG-Debug-ID: 1362140697-04cb6c2b042d420001-NocioJ Received: from mail-we0-f172.google.com (mail-we0-f172.google.com [74.125.82.172]) by cuda.sgi.com with ESMTP id aMFDHrRLC2Coz69y (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Fri, 01 Mar 2013 04:24:57 -0800 (PST) X-Barracuda-Envelope-From: ole.tange.work@gmail.com X-Barracuda-Apparent-Source-IP: 74.125.82.172 Received: by mail-we0-f172.google.com with SMTP id x10so2499951wey.17 for ; Fri, 01 Mar 2013 04:24:56 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20120113; h=x-received:mime-version:sender:in-reply-to:references:from:date :x-google-sender-auth:message-id:subject:to:cc:content-type; bh=xvh0KeVuUi0u1BWnhWlFNddZjlkheIzGsNbfLfRbBlY=; b=x36B+UAC6/i4gSGiVZ8F2xQpjRfcTgxItz8j8g50UjuDKEZYEKq6xnlpdJ1kRik6qT oLp7QxeI2nvma9sKgLMMHlsWExrmSXumMCybrk/Yus4Hp5M5qofF/JogRel216EdbOLN y0bnfeXf9ggj/hxynGff/FMlU069QAQIfl7fkRI3sZb8J3XW5UPRg7CbW6MlE7S/wAQo mxufz+cB3GRpNS8aAEaeUUNx1j6GV04Zh7idlalBqnMJ49Yp7uK8t7eDjDRi33PGepWj hxXo2rSdNmkPPc2MTF6UMcOC4ay40+fmU3JyjKcUWBVfyZW9LrtAXyRY3RK9KVeRtXxE /G7g== X-Received: by 10.195.12.133 with SMTP id eq5mr16634363wjd.52.1362140696657; Fri, 01 Mar 2013 04:24:56 -0800 (PST) MIME-Version: 1.0 Sender: ole.tange.work@gmail.com Received: by 10.194.166.65 with HTTP; Fri, 1 Mar 2013 04:24:36 -0800 (PST) In-Reply-To: <20130301111701.GB23616@dastard> References: <20130301111701.GB23616@dastard> From: Ole Tange Date: Fri, 1 Mar 2013 13:24:36 +0100 X-Google-Sender-Auth: -Mm9n5yQOQjq2c-LO2f7NZeuIiE Message-ID: Subject: Re: xfs_repair segfaults To: Dave Chinner X-ASG-Orig-Subj: Re: xfs_repair segfaults Cc: xfs@oss.sgi.com Content-Type: text/plain; charset=ISO-8859-1 X-Barracuda-Connect: mail-we0-f172.google.com[74.125.82.172] X-Barracuda-Start-Time: 1362140697 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=DKIM_SIGNED, DKIM_VERIFIED X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.123942 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature On Fri, Mar 1, 2013 at 12:17 PM, Dave Chinner wrote: > On Thu, Feb 28, 2013 at 04:22:08PM +0100, Ole Tange wrote: : >> I forced a RAID online. I have done that before and xfs_repair >> normally removes the last hour of data or so, but saves everything >> else. > > Why did you need to force it online? More than 2 harddisks went offline. We have seen that before and it is not due to bad harddisks. It may be due to driver/timings/controller. The alternative to forcing it online would be to read back a backup. Since we are talking 100 TB of data reading back the backup can take a week and will set us back to the last backup (which is more than a day old). So it is preferable to force the last failing harddisk online even though that causes us to loose a few hours of work. >> Today that did not work: >> >> /usr/local/src/xfsprogs-3.1.10/repair# ./xfs_repair -n /dev/md5p1 >> Phase 1 - find and verify superblock... >> Phase 2 - using internal log >> - scan filesystem freespace and inode maps... >> flfirst 232 in agf 91 too large (max = 128) > > Can you run: > > # xfs_db -c "agf 91" -c p /dev/md5p1 > > And post the output? # xfs_db -c "agf 91" -c p /dev/md5p1 xfs_db: cannot init perag data (117) magicnum = 0x58414746 versionnum = 1 seqno = 91 length = 268435200 bnoroot = 295199 cntroot = 13451007 bnolevel = 2 cntlevel = 2 flfirst = 232 fllast = 32 flcount = 191 freeblks = 184285136 longest = 84709383 btreeblks = 24 The partition has earlier been mounted with -o inode64. /Ole From gnehzuil.liu@gmail.com Fri Mar 1 08:02:22 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=FREEMAIL_FROM,T_DKIM_INVALID autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 66AD57FB2 for ; Fri, 1 Mar 2013 08:02:22 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay1.corp.sgi.com (Postfix) with ESMTP id 551E88F8033 for ; Fri, 1 Mar 2013 06:02:19 -0800 (PST) X-ASG-Debug-ID: 1362146534-04cb6c2b0333d10001-NocioJ Received: from mail-pa0-f42.google.com (mail-pa0-f42.google.com [209.85.220.42]) by cuda.sgi.com with ESMTP id NEVmiWX9W1r6v8Rp (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Fri, 01 Mar 2013 06:02:15 -0800 (PST) X-Barracuda-Envelope-From: gnehzuil.liu@gmail.com X-Barracuda-Apparent-Source-IP: 209.85.220.42 X-Barracuda-IPDD: Level1 [gmail.com/209.85.220.42] Received: by mail-pa0-f42.google.com with SMTP id kq12so1830402pab.29 for ; Fri, 01 Mar 2013 06:02:14 -0800 (PST) X-Barracuda-IPDD: Level1 [gmail.com/209.85.220.42] X-Barracuda-IPDD: Level1 [gmail.com/209.85.220.42] DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20120113; h=x-received:from:to:cc:subject:date:message-id:x-mailer; bh=t7wHTFNHxOLwCP9NfjkPASq9bUTQbfypGIz38xEOuHs=; b=uAEppYZlPb1yvzuQzDdF9RLircghHo6Wc+ODsdx2c7h3Lc+5NBSIZkpjmKTeBpjS80 Lw1nNd1Kv9i7s2eMwQqJasVzllrQGqOyKa66GRWvSslUVuLDb1fQ4wp7ghpP+9yttnOj Kdjmglb0q+tgaqtF3gtZHk9UxudgAjs0jrl6E9mxL4/b17EzNFRdb19s/j8I3GcB3SBu 3FhMURe4IA7KZtVqnv7Bc9zm3/xJBV5HNkLonaiG8/zDIqZu3/nPh27IDjflnpanWk/o yEMTzHyXX2GjIYyiTdqadSk2pOlSIYoDvX6hISqIgbjV3woZYvTcyOhIbKmZYgRAuTul e2UA== X-Received: by 10.68.240.67 with SMTP id vy3mr14830349pbc.119.1362146534531; Fri, 01 Mar 2013 06:02:14 -0800 (PST) Received: from lz-desktop.taobao.ali.com ([182.92.247.2]) by mx.google.com with ESMTPS id zv5sm11467705pab.2.2013.03.01.06.02.09 (version=TLSv1 cipher=RC4-SHA bits=128/128); Fri, 01 Mar 2013 06:02:13 -0800 (PST) From: Zheng Liu To: xfs@oss.sgi.com Cc: linux-ext4@vger.kernel.org, Zheng Liu , Dave Chinner Subject: [PATCH v2] xfstests: use right defrag program path Date: Fri, 1 Mar 2013 22:17:13 +0800 X-ASG-Orig-Subj: [PATCH v2] xfstests: use right defrag program path Message-Id: <1362147433-5788-1-git-send-email-wenqing.lz@taobao.com> X-Mailer: git-send-email 1.7.12.rc2.18.g61b472e X-Barracuda-Connect: mail-pa0-f42.google.com[209.85.220.42] X-Barracuda-Start-Time: 1362146535 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=DKIM_SIGNED, DKIM_VERIFIED X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.123949 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature From: Zheng Liu In _require_defrag defragmentation command path is fixed. That will cause that this test case is skipped in some distributions. Signed-off-by: Zheng Liu Cc: Dave Chinner --- [*NOTE*: this patch is Cc'ed to linux-ext4 mailing list because after applied it xfstests #218 will fail against 3.8 and dev branch.] v2 <- v1: * Define 'E4DEFRAG_PROG' and 'FILEFRAG_PROG' in common.config with set_prog_path common.config | 2 ++ common.defrag | 10 +++++----- 2 files changed, 7 insertions(+), 5 deletions(-) diff --git a/common.config b/common.config index 7174127..9c99bfe 100644 --- a/common.config +++ b/common.config @@ -160,6 +160,8 @@ export INDENT_PROG="`set_prog_path indent`" export XFS_COPY_PROG="`set_prog_path xfs_copy`" export FSTRIM_PROG="`set_prog_path fstrim`" export DUMPE2FS_PROG="`set_prog_path dumpe2fs`" +export FILEFRAG_PROG="`set_prog_path filefrag`" +export E4DEFRAG_PROG="`set_prog_path e4defrag`" # Generate a comparable xfsprogs version number in the form of # major * 10000 + minor * 100 + release diff --git a/common.defrag b/common.defrag index ea6c14c..9c9eb9b 100644 --- a/common.defrag +++ b/common.defrag @@ -24,10 +24,10 @@ _require_defrag() { case "$FSTYP" in xfs) - DEFRAG_PROG=/usr/sbin/xfs_fsr + DEFRAG_PROG="$XFS_FSR_PROG" ;; ext4|ext4dev) - DEFRAG_PROG=/usr/bin/e4defrag + DEFRAG_PROG="$E4DEFRAG_PROG" ;; btrfs) DEFRAG_PROG="$BTRFS_UTIL_PROG filesystem defragment" @@ -38,13 +38,13 @@ _require_defrag() esac _require_command $DEFRAG_PROG - _require_command /usr/sbin/filefrag + _require_command $FILEFRAG_PROG } _extent_count() { - filefrag $1 | awk '{print $2}' - filefrag -v $1 >> $seq.full 2>&1 + $FILEFRAG_PROG $1 | awk '{print $2}' + $FILEFRAG_PROG -v $1 >> $seq.full 2>&1 } # Defrag file, check it, and remove it. -- 1.7.12.rc2.18.g61b472e From rjohnston@sgi.com Fri Mar 1 09:43:09 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 3DE4B7FBD for ; Fri, 1 Mar 2013 09:43:09 -0600 (CST) Received: from xmail.sgi.com (pv-excas3-dc21-nlb.corp.sgi.com [137.38.102.207]) by relay1.corp.sgi.com (Postfix) with ESMTP id AF0188F8040; Fri, 1 Mar 2013 07:43:08 -0800 (PST) Received: from [128.162.233.55] (128.162.233.55) by xmail.sgi.com (137.38.102.30) with Microsoft SMTP Server (TLS) id 14.2.318.1; Fri, 1 Mar 2013 09:43:08 -0600 Message-ID: <5130CC8E.6090406@sgi.com> Date: Fri, 1 Mar 2013 09:43:10 -0600 From: Rich Johnston User-Agent: Mozilla/5.0 (X11; Linux i686; rv:13.0) Gecko/20120615 Thunderbird/13.0.1 MIME-Version: 1.0 To: Dmitry Monakhov CC: , , , Subject: Re: [PATCH 01/10] xfstests: add fio requirement V2 References: <1361356935-29153-1-git-send-email-dmonakhov@openvz.org> <1361356935-29153-2-git-send-email-dmonakhov@openvz.org> In-Reply-To: <1361356935-29153-2-git-send-email-dmonakhov@openvz.org> Content-Type: text/plain; charset="ISO-8859-1"; format=flowed Content-Transfer-Encoding: 7bit X-Originating-IP: [128.162.233.55] On 02/20/2013 04:42 AM, Dmitry Monakhov wrote: > FIO is very flexible io generator, I would call it IO swiss knife. > Currently we have tonns of hardcoded application which reproduces > some predefined scenario. This approach has obvious dissadvantages > 1) Lack of flexability: one written it is hard to modify it in future > 2) Code base is large, many routines written again and again > > At the same time add new fio based tast is just add simle INI file. > This greatly simplify code review. I do beleve that some day we will > replace most of hardcoded io binaries with fio. > > One who is planning to run $FIO_PROG should first check that system > contains appropriate version which is able to handle jobfile > for example: _require_fio 286-job.fio > > Signed-off-by: Dmitry Monakhov Minor typos in the description, but looks good. Reviewed-by: Rich Johnston From rjohnston@sgi.com Fri Mar 1 09:43:17 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 4B1237FC3 for ; Fri, 1 Mar 2013 09:43:17 -0600 (CST) Received: from xmail.sgi.com (pv-excas3-dc21-nlb.corp.sgi.com [137.38.102.207]) by relay2.corp.sgi.com (Postfix) with ESMTP id 1BA05304051; Fri, 1 Mar 2013 07:43:17 -0800 (PST) Received: from [128.162.233.55] (128.162.233.55) by xmail.sgi.com (137.38.102.30) with Microsoft SMTP Server (TLS) id 14.2.318.1; Fri, 1 Mar 2013 09:43:16 -0600 Message-ID: <5130CC96.7020705@sgi.com> Date: Fri, 1 Mar 2013 09:43:18 -0600 From: Rich Johnston User-Agent: Mozilla/5.0 (X11; Linux i686; rv:13.0) Gecko/20120615 Thunderbird/13.0.1 MIME-Version: 1.0 To: Dmitry Monakhov CC: , , , Subject: Re: [PATCH 02/10] xfstest: add configurable load factors References: <1361356935-29153-1-git-send-email-dmonakhov@openvz.org> <1361356935-29153-3-git-send-email-dmonakhov@openvz.org> In-Reply-To: <1361356935-29153-3-git-send-email-dmonakhov@openvz.org> Content-Type: text/plain; charset="ISO-8859-1"; format=flowed Content-Transfer-Encoding: 7bit X-Originating-IP: [128.162.233.55] On 02/20/2013 04:42 AM, Dmitry Monakhov wrote: > Most stress test has probable behauviour, the longer test run the > larger corner cases will be cover. It is reasonable to allow > user to provide some sort of system load factor. > This patch introduce two global variables > LOAD_FACTOR: Usually means factor number of running tasks > TIME_FACTOR: Usually means factor of run time, or number of operations > If not speficied both variables defined to 1, so original behaviour > preserved. > > TODO: Change all stress tests to use this variables > > Signed-off-by: Dmitry Monakhov Nice addition, looks good. Reviewed-by: Rich Johnston From rjohnston@sgi.com Fri Mar 1 09:43:26 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 91CBE7FBD for ; Fri, 1 Mar 2013 09:43:26 -0600 (CST) Received: from xmail.sgi.com (pv-excas3-dc21-nlb.corp.sgi.com [137.38.102.207]) by relay2.corp.sgi.com (Postfix) with ESMTP id C5FBB304039; Fri, 1 Mar 2013 07:43:25 -0800 (PST) Received: from [128.162.233.55] (128.162.233.55) by xmail.sgi.com (137.38.102.30) with Microsoft SMTP Server (TLS) id 14.2.318.1; Fri, 1 Mar 2013 09:43:25 -0600 Message-ID: <5130CC9F.4090207@sgi.com> Date: Fri, 1 Mar 2013 09:43:27 -0600 From: Rich Johnston User-Agent: Mozilla/5.0 (X11; Linux i686; rv:13.0) Gecko/20120615 Thunderbird/13.0.1 MIME-Version: 1.0 To: Dmitry Monakhov CC: , , , Subject: Re: [PATCH 03/10] xfstests: hardcode fops for determinable fsstests runs References: <1361356935-29153-1-git-send-email-dmonakhov@openvz.org> <1361356935-29153-4-git-send-email-dmonakhov@openvz.org> In-Reply-To: <1361356935-29153-4-git-send-email-dmonakhov@openvz.org> Content-Type: text/plain; charset="ISO-8859-1"; format=flowed Content-Transfer-Encoding: 7bit X-Originating-IP: [128.162.233.55] On 02/20/2013 04:42 AM, Dmitry Monakhov wrote: > 106,107 and 117 are frozen tests which use known seed, it is > reasonable to explicitly hardcode file operations in order to avoid > implicit changes caused by future changes in fsstress. > > NOTE: options genereted like follows: fsstress -S c $ORIG_ARGS > > Signed-off-by: Dmitry Monakhov 106 and 107 are not valid for ext4. They failed the same before and after this patch with xfs. Because 106 and 107 are not in the auto group and 117 is in the auto group and passes for both xfs and ext4, I will say this looks good. Reviewed-by: Rich Johnston > --- > 106 | 33 +++++++++++++++++++++++++++++++-- > 107 | 32 +++++++++++++++++++++++++++++--- > 2 files changed, 60 insertions(+), 5 deletions(-) > > diff --git a/106 b/106 > index 8278691..b351fe5 100755 > --- a/106 > +++ b/106 > @@ -61,8 +61,37 @@ _require_prjquota $SCRATCH_DEV > > # initial populate > target=$SCRATCH_MNT/target > -$FSSTRESS_PROG -s 0xdeed -m8 -w -p4 -n1000 $FSSTRESS_AVOID -d $target > -$FSSTRESS_PROG -s 0xdeed -m8 -z -p4 -n1000 -fsetxattr=500 -fchown=500 -d $target > +$FSSTRESS_PROG -z -s 57069 -m 8 -n 1000 -p 4 \ > +-f allocsp=1 \ > +-f chown=3 \ > +-f creat=4 \ > +-f dwrite=4 \ > +-f fallocate=1 \ > +-f fdatasync=1 \ > +-f fiemap=1 \ > +-f freesp=1 \ > +-f fsync=1 \ > +-f link=1 \ > +-f mkdir=2 \ > +-f mknod=2 \ > +-f punch=1 \ > +-f rename=2 \ > +-f resvsp=1 \ > +-f rmdir=1 \ > +-f setxattr=1 \ > +-f symlink=2 \ > +-f sync=1 \ > +-f truncate=2 \ > +-f unlink=1 \ > +-f unresvsp=1 \ > +-f write=4 \ > +-d $target > + > +$FSSTRESS_PROG -z -s 57069 -m 8 -n 1000 -p 4 \ > +-f chown=500 \ > +-f setxattr=500 \ > +-d $target > + > > # also use space, to be able to go over/under limits easily > uid=255 > diff --git a/107 b/107 > index 74403e6..eaf7e6a 100755 > --- a/107 > +++ b/107 > @@ -78,9 +78,35 @@ echo "6:$target" | tee -a $seq.full > $tmp.projects > > echo "### populate filesystem" > mkdir $target || exit > -FSSTRESS_AVOID="$FSSTRESS_AVOID -fmknod=0 -fsymlink=0" > -$FSSTRESS_PROG -s 0xfeed -m8 -w -p4 -n1000 $FSSTRESS_AVOID -d $target > -$FSSTRESS_PROG -s 0xbabe -m8 -z -p4 -n500 -fsetxattr=250 -fchown=250 -d $target > +$FSSTRESS_PROG -z -s 65261 -m 8 -n 1000 -p 4 \ > +-f allocsp=1 \ > +-f chown=3 \ > +-f creat=4 \ > +-f dwrite=4 \ > +-f fallocate=1 \ > +-f fdatasync=1 \ > +-f fiemap=1 \ > +-f freesp=1 \ > +-f fsync=1 \ > +-f link=1 \ > +-f mkdir=2 \ > +-f punch=1 \ > +-f rename=2 \ > +-f resvsp=1 \ > +-f rmdir=1 \ > +-f setxattr=1 \ > +-f sync=1 \ > +-f truncate=2 \ > +-f unlink=1 \ > +-f unresvsp=1 \ > +-f write=4 \ > +-d $target > + > +$FSSTRESS_PROG -z -s 47806 -m 8 -n 500 -p 4 \ > +-f chown=250 \ > +-f setxattr=250 \ > +-d $target > + > > QARGS="-x -D $tmp.projects -P /dev/null $SCRATCH_MNT" > > From rjohnston@sgi.com Fri Mar 1 09:43:41 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 8B4CD7FCA for ; Fri, 1 Mar 2013 09:43:41 -0600 (CST) Received: from xmail.sgi.com (pv-excas3-dc21.corp.sgi.com [137.38.102.206]) by relay3.corp.sgi.com (Postfix) with ESMTP id E3945AC002; Fri, 1 Mar 2013 07:43:40 -0800 (PST) Received: from [128.162.233.55] (128.162.233.55) by xmail.sgi.com (137.38.102.30) with Microsoft SMTP Server (TLS) id 14.2.318.1; Fri, 1 Mar 2013 09:43:40 -0600 Message-ID: <5130CCAE.2060108@sgi.com> Date: Fri, 1 Mar 2013 09:43:42 -0600 From: Rich Johnston User-Agent: Mozilla/5.0 (X11; Linux i686; rv:13.0) Gecko/20120615 Thunderbird/13.0.1 MIME-Version: 1.0 To: Dmitry Monakhov CC: , , , Subject: Re: [PATCH 04/10] xfstets: fsstress add replace file operation References: <1361356935-29153-1-git-send-email-dmonakhov@openvz.org> <1361356935-29153-5-git-send-email-dmonakhov@openvz.org> In-Reply-To: <1361356935-29153-5-git-send-email-dmonakhov@openvz.org> Content-Type: text/plain; charset="ISO-8859-1"; format=flowed Content-Transfer-Encoding: 7bit X-Originating-IP: [128.162.233.55] On 02/20/2013 04:42 AM, Dmitry Monakhov wrote: > The most common usecase for rename(2) syscall is an atomic replacement > of existing file with newer version. But rename_f() rename some existing > filename to newly generated (non existing) filename. As result the most > important usecase is not covered. Good catch. > Since rename_f() is already exist in fsstress and it has known behavior, > some tests already depends on that behaviour, let's add another operation > (replace_f) which invoke rename(2) for two existing entries. > > OUT_OF_COMMIT_DISCUSSION: > Off course replace_f() break naming convention where fun_name == syscall_f(), > but this is the only way I see to introduce new feature and not break > other tests. May be it is reasonable to call it rename2_f() ? > I think this possible exposes a bug which was not exposed by before when running for example test 076 and test 083 on both ext4 and xfs. Suggest this new function is called rename2_() so that we don't change the existing known tests. Regards --Rich From rjohnston@sgi.com Fri Mar 1 09:43:53 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 5AC017FCA for ; Fri, 1 Mar 2013 09:43:53 -0600 (CST) Received: from xmail.sgi.com (pv-excas3-dc21-nlb.corp.sgi.com [137.38.102.207]) by relay1.corp.sgi.com (Postfix) with ESMTP id 39D948F8033; Fri, 1 Mar 2013 07:43:53 -0800 (PST) Received: from [128.162.233.55] (128.162.233.55) by xmail.sgi.com (137.38.102.30) with Microsoft SMTP Server (TLS) id 14.2.318.1; Fri, 1 Mar 2013 09:43:52 -0600 Message-ID: <5130CCBA.4000307@sgi.com> Date: Fri, 1 Mar 2013 09:43:54 -0600 From: Rich Johnston User-Agent: Mozilla/5.0 (X11; Linux i686; rv:13.0) Gecko/20120615 Thunderbird/13.0.1 MIME-Version: 1.0 To: Dmitry Monakhov CC: , , , Subject: Re: [PATCH 05/10] xfstest: allow fsstress to use load factor where appropriate References: <1361356935-29153-1-git-send-email-dmonakhov@openvz.org> <1361356935-29153-6-git-send-email-dmonakhov@openvz.org> In-Reply-To: <1361356935-29153-6-git-send-email-dmonakhov@openvz.org> Content-Type: text/plain; charset="ISO-8859-1"; format=flowed Content-Transfer-Encoding: 7bit X-Originating-IP: [128.162.233.55] On 02/20/2013 04:42 AM, Dmitry Monakhov wrote: > 1) Add _scale_fsstress_args function which transform argumets according > to load factors > 2) Let all non deterministic fsstress tests to use scaled arguments > > I've able to trigger OOPS on xfs see:https://gist.github.com/dmonakhov/4762653 > I did not see any OOPS. Looks good. Reviewed-by: Rich Johnston From rjohnston@sgi.com Fri Mar 1 09:44:11 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id A19487FC9 for ; Fri, 1 Mar 2013 09:44:11 -0600 (CST) Received: from xmail.sgi.com (pv-excas3-dc21-nlb.corp.sgi.com [137.38.102.207]) by relay1.corp.sgi.com (Postfix) with ESMTP id 71CEF8F8040; Fri, 1 Mar 2013 07:44:11 -0800 (PST) Received: from [128.162.233.55] (128.162.233.55) by xmail.sgi.com (137.38.102.30) with Microsoft SMTP Server (TLS) id 14.2.318.1; Fri, 1 Mar 2013 09:44:11 -0600 Message-ID: <5130CCCD.8010705@sgi.com> Date: Fri, 1 Mar 2013 09:44:13 -0600 From: Rich Johnston User-Agent: Mozilla/5.0 (X11; Linux i686; rv:13.0) Gecko/20120615 Thunderbird/13.0.1 MIME-Version: 1.0 To: Dmitry Monakhov CC: , , , Subject: Re: [PATCH 06/10] xfstest: move run_check to common.rc References: <1361356935-29153-1-git-send-email-dmonakhov@openvz.org> <1361356935-29153-7-git-send-email-dmonakhov@openvz.org> In-Reply-To: <1361356935-29153-7-git-send-email-dmonakhov@openvz.org> Content-Type: text/plain; charset="ISO-8859-1"; format=flowed Content-Transfer-Encoding: 7bit X-Originating-IP: [128.162.233.55] Looks good, will add the following simple description when this is committed Move run_check to common.rc Reviewed-by: Rich Johnston From sandeen@redhat.com Fri Mar 1 09:48:33 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id F01767FCD for ; Fri, 1 Mar 2013 09:48:32 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id CE0D5304059 for ; Fri, 1 Mar 2013 07:48:32 -0800 (PST) X-ASG-Debug-ID: 1362152910-04cbb07dbd3f6a0001-NocioJ Received: from mx1.redhat.com (mx1.redhat.com [209.132.183.28]) by cuda.sgi.com with ESMTP id Pol2U1G2boWAe3wh for ; Fri, 01 Mar 2013 07:48:30 -0800 (PST) X-Barracuda-Envelope-From: sandeen@redhat.com X-Barracuda-Apparent-Source-IP: 209.132.183.28 X-ASG-Whitelist: Client Received: from int-mx12.intmail.prod.int.phx2.redhat.com (int-mx12.intmail.prod.int.phx2.redhat.com [10.5.11.25]) by mx1.redhat.com (8.14.4/8.14.4) with ESMTP id r21FmKwq009444 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=OK); Fri, 1 Mar 2013 10:48:20 -0500 Received: from liberator.sandeen.net (ovpn01.gateway.prod.ext.phx2.redhat.com [10.5.9.1]) by int-mx12.intmail.prod.int.phx2.redhat.com (8.14.4/8.14.4) with ESMTP id r21FmIAQ021082 (version=TLSv1/SSLv3 cipher=DHE-RSA-CAMELLIA256-SHA bits=256 verify=NO); Fri, 1 Mar 2013 10:48:19 -0500 Message-ID: <5130CDC1.8060704@redhat.com> Date: Fri, 01 Mar 2013 09:48:17 -0600 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: Zheng Liu CC: xfs@oss.sgi.com, linux-ext4@vger.kernel.org, Zheng Liu , Dave Chinner Subject: Re: [PATCH v2] xfstests: use right defrag program path References: <1362147433-5788-1-git-send-email-wenqing.lz@taobao.com> X-ASG-Orig-Subj: Re: [PATCH v2] xfstests: use right defrag program path In-Reply-To: <1362147433-5788-1-git-send-email-wenqing.lz@taobao.com> X-Enigmail-Version: 1.5 Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Scanned-By: MIMEDefang 2.68 on 10.5.11.25 X-Barracuda-Connect: mx1.redhat.com[209.132.183.28] X-Barracuda-Start-Time: 1362152910 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 On 3/1/13 8:17 AM, Zheng Liu wrote: > From: Zheng Liu > > In _require_defrag defragmentation command path is fixed. That will > cause that this test case is skipped in some distributions. > > Signed-off-by: Zheng Liu > Cc: Dave Chinner > --- > [*NOTE*: this patch is Cc'ed to linux-ext4 mailing list because after > applied it xfstests #218 will fail against 3.8 and dev branch.] > > v2 <- v1: > * Define 'E4DEFRAG_PROG' and 'FILEFRAG_PROG' in common.config with > set_prog_path Looks good to me, thanks. Reviewed-by: Eric Sandeen > common.config | 2 ++ > common.defrag | 10 +++++----- > 2 files changed, 7 insertions(+), 5 deletions(-) > > diff --git a/common.config b/common.config > index 7174127..9c99bfe 100644 > --- a/common.config > +++ b/common.config > @@ -160,6 +160,8 @@ export INDENT_PROG="`set_prog_path indent`" > export XFS_COPY_PROG="`set_prog_path xfs_copy`" > export FSTRIM_PROG="`set_prog_path fstrim`" > export DUMPE2FS_PROG="`set_prog_path dumpe2fs`" > +export FILEFRAG_PROG="`set_prog_path filefrag`" > +export E4DEFRAG_PROG="`set_prog_path e4defrag`" > > # Generate a comparable xfsprogs version number in the form of > # major * 10000 + minor * 100 + release > diff --git a/common.defrag b/common.defrag > index ea6c14c..9c9eb9b 100644 > --- a/common.defrag > +++ b/common.defrag > @@ -24,10 +24,10 @@ _require_defrag() > { > case "$FSTYP" in > xfs) > - DEFRAG_PROG=/usr/sbin/xfs_fsr > + DEFRAG_PROG="$XFS_FSR_PROG" > ;; > ext4|ext4dev) > - DEFRAG_PROG=/usr/bin/e4defrag > + DEFRAG_PROG="$E4DEFRAG_PROG" > ;; > btrfs) > DEFRAG_PROG="$BTRFS_UTIL_PROG filesystem defragment" > @@ -38,13 +38,13 @@ _require_defrag() > esac > > _require_command $DEFRAG_PROG > - _require_command /usr/sbin/filefrag > + _require_command $FILEFRAG_PROG > } > > _extent_count() > { > - filefrag $1 | awk '{print $2}' > - filefrag -v $1 >> $seq.full 2>&1 > + $FILEFRAG_PROG $1 | awk '{print $2}' > + $FILEFRAG_PROG -v $1 >> $seq.full 2>&1 > } > > # Defrag file, check it, and remove it. > From tinguely@sgi.com Fri Mar 1 09:51:58 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 36F8D7FDF for ; Fri, 1 Mar 2013 09:51:58 -0600 (CST) Received: from eagdhcp-232-136.americas.sgi.com (eagdhcp-232-136.americas.sgi.com [128.162.232.136]) by relay1.corp.sgi.com (Postfix) with ESMTP id 928AA8F8033; Fri, 1 Mar 2013 07:51:57 -0800 (PST) Message-ID: <5130CE9E.9080501@sgi.com> Date: Fri, 01 Mar 2013 09:51:58 -0600 From: Mark Tinguely User-Agent: Mozilla/5.0 (X11; FreeBSD amd64; rv:9.0) Gecko/20120122 Thunderbird/9.0 MIME-Version: 1.0 To: Tony Lu CC: Dave Chinner , Ben Myers , Alex Elder , "linux-kernel@vger.kernel.org" , Chris Metcalf , "xfs@oss.sgi.com" , Dave Chinner , "linux-fsdevel@vger.kernel.org" Subject: Re: [PATCH] xfs: Fix possible truncation of log data in xlog_bread_noalign() References: <20130223000802.GB26081@dastard> <20130223235546.GA5551@dastard> <20130224141017.GC5551@dastard> In-Reply-To: Content-Type: text/plain; charset=ISO-8859-1; format=flowed Content-Transfer-Encoding: 7bit On 02/26/13 01:28, Tony Lu wrote: > I get a reliable way to reproduce this bug. The logprint and metadump are attached. > > Kernel version: 2.6.38.8 > Mkfs.xfs version: xfsprogs-3.1.1 > mkfs.xfs -s size=4096 /dev/sda1 > > Run the following mount-cp-umount script to reproduce: > #!/bin/sh > device=/dev/sda1 > mount_point=/mnt > times=10 > > for ((num=1;num<=$times;num++)) > do > echo "$num mount $device $mount_point" > mount $device $mount_point > > echo "cp -rf /bin $mount_point/$num" > cp -rf /bin $mount_point/$num > > echo "$num umount $device $mount_point" > umount $mount_point > > #num=$(($num + 1)) > done > > After several times of mount/cp/umount, this xfs crashes, and the xfs partition can not be mounted any more. Here is the output of console. > -sh-4.1# ./umount-test > 1 mount /dev/sda1 /mnt > XFS mounting filesystem sda1 > cp -rf /bin /mnt/1 > 1 umount /dev/sda1 /mnt > 2 mount /dev/sda1 /mnt > XFS mounting filesystem sda1 > cp -rf /bin /mnt/2 > 2 umount /dev/sda1 /mnt > 3 mount /dev/sda1 /mnt > XFS mounting filesystem sda1 > cp -rf /bin /mnt/3 > 3 umount /dev/sda1 /mnt > 4 mount /dev/sda1 /mnt > XFS mounting filesystem sda1 > cp -rf /bin /mnt/4 > 4 umount /dev/sda1 /mnt > 5 mount /dev/sda1 /mnt > XFS mounting filesystem sda1 > Starting XFS recovery on filesystem: sda1 (logdev: internal) > Ending XFS recovery on filesystem: sda1 (logdev: internal)cp -rf /bin /mnt/5 > 5 umount /dev/sda1 /mnt > 6 mount /dev/sda1 /mnt > > XFS mounting filesystem sda1 > Starting XFS recovery on filesystem: sda1 (logdev: internal) > Ending XFS recovery on filesystem: sda1 (logdev: internal)Interrupt > cp -rf /bin /mnt/6 > 6 umount /dev/sda1 /mnt > 7 mount /dev/sda1 /mnt > > XFS mounting filesystem sda1 > cp -rf /bin /mnt/7 > 7 umount /dev/sda1 /mnt > Interrupt > 8 mount /dev/sda1 /mnt > XFS mounting filesystem sda1 > Starting XFS recovery on filesystem: sda1 (logdev: internal) > XFS: xlog_recover_process_data: bad clientid > XFS: log mount/recovery failed: error 5 > XFS: log mount failed > > Thanks > -Tony It works fine on a 2.6.32 machine I had sitting around - and I never required log recovery. I think you need to answer Dave's question as to why is your unmounts are requiring recovery? Are there errors in the /var/log/messages? I downloaded the Linux 2.6.38.8 source and take a look if I can recreate the problem. --Mark. From sandeen@sandeen.net Fri Mar 1 10:46:18 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id DB2027F54 for ; Fri, 1 Mar 2013 10:46:18 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay3.corp.sgi.com (Postfix) with ESMTP id 6B2F2AC002 for ; Fri, 1 Mar 2013 08:46:15 -0800 (PST) X-ASG-Debug-ID: 1362156373-04cbb07dbc44ae0001-NocioJ Received: from sandeen.net (sandeen.net [63.231.237.45]) by cuda.sgi.com with ESMTP id fs7HuMFL6w9z7HXQ for ; Fri, 01 Mar 2013 08:46:13 -0800 (PST) X-Barracuda-Envelope-From: sandeen@sandeen.net X-Barracuda-Apparent-Source-IP: 63.231.237.45 Received: from liberator.sandeen.net (liberator.sandeen.net [10.0.0.4]) (using TLSv1 with cipher DHE-RSA-CAMELLIA256-SHA (256/256 bits)) (No client certificate requested) by sandeen.net (Postfix) with ESMTPSA id E4FC963C59BB; Fri, 1 Mar 2013 10:46:12 -0600 (CST) Message-ID: <5130DB54.9030503@sandeen.net> Date: Fri, 01 Mar 2013 10:46:12 -0600 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: Ole Tange CC: xfs@oss.sgi.com Subject: Re: xfs_repair segfaults References: <512FA67D.2090708@sandeen.net> X-ASG-Orig-Subj: Re: xfs_repair segfaults In-Reply-To: X-Enigmail-Version: 1.5 Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: sandeen.net[63.231.237.45] X-Barracuda-Start-Time: 1362156373 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.123958 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On 3/1/13 3:37 AM, Ole Tange wrote: > On Thu, Feb 28, 2013 at 7:48 PM, Eric Sandeen wrote: >> On 2/28/13 9:22 AM, Ole Tange wrote: > >>> /usr/local/src/xfsprogs-3.1.10/repair# ./xfs_repair -n /dev/md5p1 > [...] >>> Segmentation fault (core dumped) >>> >>> Core put in: http://dna.ku.dk/~tange/tmp/xfs_repair.core.bz2 >> >> We'd need a binary w/ debug symbols to go along with it. > > http://dna.ku.dk/~tange/tmp/xfs_repair > >> an xfs_metadump might recreate the problem too. > > # sudo ./xfs_metadump.sh -g /dev/md5p1 - | pbzip2 > > /home/tange/public_html/tmp/metadump.bz2 > xfs_metadump: cannot init perag data (117) > Copying log I'll take a look. May be that the error renders it invalid but we'll see. > http://dna.ku.dk/~tange/tmp/metadump.bz2 > > Please consider providing an example in the man page for xfs_metadump e.g: > > xfs_metadump.sh -g /dev/sda2 meta.dump >From the manpage, SYNOPSIS xfs_metadump [ -efgow ] [ -l logdev ] source target The source argument must be the pathname of the device or file containing the XFS filesystem and the target argument specifies the destination file name. is not enough? Thanks, -Eric > > /Ole > > _______________________________________________ > xfs mailing list > xfs@oss.sgi.com > http://oss.sgi.com/mailman/listinfo/xfs > From enwlinux@gmail.com Fri Mar 1 11:37:09 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=FREEMAIL_FROM,T_DKIM_INVALID autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 2B5AD7FC7 for ; Fri, 1 Mar 2013 11:37:09 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay3.corp.sgi.com (Postfix) with ESMTP id BFB74AC00A for ; Fri, 1 Mar 2013 09:37:08 -0800 (PST) X-ASG-Debug-ID: 1362159423-04bdf022954e1d0001-NocioJ Received: from mail-qe0-f53.google.com (mail-qe0-f53.google.com [209.85.128.53]) by cuda.sgi.com with ESMTP id QTK0UubUeLKA87WM (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Fri, 01 Mar 2013 09:37:04 -0800 (PST) X-Barracuda-Envelope-From: enwlinux@gmail.com X-Barracuda-Apparent-Source-IP: 209.85.128.53 X-Barracuda-IPDD: Level1 [gmail.com/209.85.128.53] Received: by mail-qe0-f53.google.com with SMTP id cz11so2469206qeb.40 for ; Fri, 01 Mar 2013 09:37:03 -0800 (PST) X-Barracuda-IPDD: Level1 [gmail.com/209.85.128.53] X-Barracuda-IPDD: Level1 [gmail.com/209.85.128.53] DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20120113; h=x-received:date:from:to:cc:subject:message-id:references :mime-version:content-type:content-disposition:in-reply-to :user-agent; bh=MQcjAQvXjX+eypTQXiJZaLnPhrjEISvyEelOaG1uEi8=; b=Gl9gvMqWl7fJX66i3ZzP9T6M7gp86USnQFCpbizHVaOs1/NAyg4xhEVgeHtAC5KA06 hl4jADGhJ1Y+4aNwI56s/4ChIqXsosA7oaB1ZpVRH6HmbMYOIwNdbcJfX9VH6sKPNtrp nOPrbJZNQAi84C0G8PhUKjcTk0sJNKCKbX2rRnGalxzMb9dInaQL4iYEFapDPWmSsPSX GimOmHhyTtJ9Cq2/XUa338Q0TVf0qVoW0aycPeFk2g0kJWCPMsLioH7PQvbgKpWitwVr mXQfcV7PCB21nZ25+yIOxJUiUSsA7HMuitvVhsFEIHU9pAYF3yBrzbMeMV/CZlc84z6K WaNw== X-Received: by 10.224.193.200 with SMTP id dv8mr13426293qab.85.1362159423792; Fri, 01 Mar 2013 09:37:03 -0800 (PST) Received: from wallace (c-75-68-62-236.hsd1.nh.comcast.net. [75.68.62.236]) by mx.google.com with ESMTPS id ho10sm15587950qab.13.2013.03.01.09.37.01 (version=TLSv1.2 cipher=RC4-SHA bits=128/128); Fri, 01 Mar 2013 09:37:02 -0800 (PST) Date: Fri, 1 Mar 2013 12:36:59 -0500 From: Eric Whitney To: Eric Whitney Cc: Eric Sandeen , xfs@oss.sgi.com Subject: Re: [PATCH] xfstests: don't remove trailing zeros from integers Message-ID: <20130301173658.GB6449@wallace> X-ASG-Orig-Subj: Re: [PATCH] xfstests: don't remove trailing zeros from integers References: <20130301002637.GB5016@wallace> <51301A92.2080104@redhat.com> <20130301041344.GA3206@rocky> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <20130301041344.GA3206@rocky> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: mail-qe0-f53.google.com[209.85.128.53] X-Barracuda-Start-Time: 1362159424 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.50 X-Barracuda-Spam-Status: No, SCORE=0.50 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_SA_TO_FROM_ADDR_MATCH, DKIM_SIGNED, DKIM_VERIFIED X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.123963 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature 0.50 BSF_SC0_SA_TO_FROM_ADDR_MATCH Sender Address Matches Recipient Address * Eric Whitney : > * Eric Sandeen : > > On 2/28/13 6:26 PM, Eric Whitney wrote: > > > _within_tolerance strips trailing zeros from the min and max range > > > values it outputs. This leads to damage if the min or max value is > > > an integer containing trailing zeros rather than a real number with > > > a fractional part containing trailing zeros. Xfstest 289 can exhibit > > > this problem when its input is out of range. Modify the code so it > > > will only remove trailing zeros found after a decimal point. > > > > whoops, that's not too good. > > > > It's only for the output message in a failure case though, correct? > > But it makes the error output unhelpful. > > Right on both counts. We'd noticed the error output was confusing a few > months ago when you fixed an ext4 free space reporting problem (this is an > IOU) - 1280000 reported as 128 in that case. > > > > > Seems a little weird that it still leaves the trailing decimal: > > > > $ echo 20000.00 | sed -e '/\./s/0*$//' > > 20000. > > > > but that's not a big deal. The patch makes it better and > > the output is understandable even if it has a trailing > > decimal (which it had before anyway) so: > > > > Reviewed-by: Eric Sandeen > > I'd reached the same conclusion, but if preferred I'll take this farther > and eliminate the trailing decimal. > On further consideration, it's easy enough to clean up the trailing decimal and it's just better that way, even for an error case. There's at least one fix that isn't elegant but works. I'll send along a V2 shortly. Regards, Eric > Thanks for the review! > > Eric > > > > > > Signed-off-by: Eric Whitney > > > --- > > > common.filter | 6 ++++-- > > > 1 file changed, 4 insertions(+), 2 deletions(-) > > > > > > diff --git a/common.filter b/common.filter > > > index 9e4c90c..1df2f97 100644 > > > --- a/common.filter > > > +++ b/common.filter > > > @@ -106,8 +106,10 @@ EOF > > > > > > # fix up min, max precision for output > > > # can vary for 5.3, 6.2 > > > - _min=`echo $_min | sed -e 's/0*$//'` # get rid of trailling zeroes > > > - _max=`echo $_max | sed -e 's/0*$//'` # get rid of trailling zeroes > > > + > > > + # remove any trailing zeroes from min, max if they have fractional parts > > > + _min=`echo $_min | sed -e '/\./s/0*$//'` > > > + _max=`echo $_max | sed -e '/\./s/0*$//'` > > > > > > if [ $_in_range -eq 1 ] > > > then > > > > > From rjohnston@sgi.com Fri Mar 1 11:49:34 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 6CF177FB3 for ; Fri, 1 Mar 2013 11:49:34 -0600 (CST) Received: from xmail.sgi.com (pv-excas3-dc21.corp.sgi.com [137.38.102.206]) by relay3.corp.sgi.com (Postfix) with ESMTP id 66CC6AC004; Fri, 1 Mar 2013 09:49:33 -0800 (PST) Received: from [128.162.233.55] (128.162.233.55) by xmail.sgi.com (137.38.102.30) with Microsoft SMTP Server (TLS) id 14.2.318.1; Fri, 1 Mar 2013 11:49:32 -0600 Message-ID: <5130EA2F.9080209@sgi.com> Date: Fri, 1 Mar 2013 11:49:35 -0600 From: Rich Johnston User-Agent: Mozilla/5.0 (X11; Linux i686; rv:13.0) Gecko/20120615 Thunderbird/13.0.1 MIME-Version: 1.0 To: Dmitry Monakhov CC: , , , Subject: Re: [PATCH 07/10] xfstest: add fallocate/truncate vs AIO/DIO stress test References: <1361356935-29153-1-git-send-email-dmonakhov@openvz.org> <1361356935-29153-8-git-send-email-dmonakhov@openvz.org> In-Reply-To: <1361356935-29153-8-git-send-email-dmonakhov@openvz.org> Content-Type: text/plain; charset="ISO-8859-1"; format=flowed Content-Transfer-Encoding: 7bit X-Originating-IP: [128.162.233.55] On 02/20/2013 04:42 AM, Dmitry Monakhov wrote: > Run DIO, fallocate and truncate threads on a common file in parallel. > If race exist old dio request may rewrite blocks after it was allocated > to another file, we will catch that by verifying blocks content. > > this patch known to catch deadlock for ext4 > http://lists.openwall.net/linux-ext4/2012/09/06/3 > > Signed-off-by: Dmitry Monakhov Looks good. Reviewed-by: Rich Johnston From rjohnston@sgi.com Fri Mar 1 11:50:08 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 5D1E07FB3 for ; Fri, 1 Mar 2013 11:50:08 -0600 (CST) Received: from xmail.sgi.com (pv-excas3-dc21.corp.sgi.com [137.38.102.206]) by relay3.corp.sgi.com (Postfix) with ESMTP id 4B7A5AC00A; Fri, 1 Mar 2013 09:50:07 -0800 (PST) Received: from [128.162.233.55] (128.162.233.55) by xmail.sgi.com (137.38.102.30) with Microsoft SMTP Server (TLS) id 14.2.318.1; Fri, 1 Mar 2013 11:50:06 -0600 Message-ID: <5130EA51.7090306@sgi.com> Date: Fri, 1 Mar 2013 11:50:09 -0600 From: Rich Johnston User-Agent: Mozilla/5.0 (X11; Linux i686; rv:13.0) Gecko/20120615 Thunderbird/13.0.1 MIME-Version: 1.0 To: Dmitry Monakhov CC: , , , Subject: Re: [PATCH 08/10] xfstest: add fallocate/punch_hole vs AIO/DIO stress test References: <1361356935-29153-1-git-send-email-dmonakhov@openvz.org> <1361356935-29153-9-git-send-email-dmonakhov@openvz.org> In-Reply-To: <1361356935-29153-9-git-send-email-dmonakhov@openvz.org> Content-Type: text/plain; charset="ISO-8859-1"; format=flowed Content-Transfer-Encoding: 7bit X-Originating-IP: [128.162.233.55] On 02/20/2013 04:42 AM, Dmitry Monakhov wrote: > Run random AIO/DIO activity (fio's job:direct_aio_raicer) > random fallocate activity(fio's job:falloc_raicer) > and random punch_hole activity(punch_hole_raicer) on a common > file in parallel. If race exist old dio request may rewrite > punched block after it was allocated to another file, we will > catch that by verifier fio's job: "aio-dio-verifier". > > Signed-off-by: Dmitry Monakhov Looks good. Reviewed-by: Rich Johnston From enwlinux@gmail.com Fri Mar 1 12:02:13 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=FREEMAIL_FROM,T_DKIM_INVALID autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 8684A7FD5 for ; Fri, 1 Mar 2013 12:02:12 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay3.corp.sgi.com (Postfix) with ESMTP id 09ED7AC002 for ; Fri, 1 Mar 2013 10:02:08 -0800 (PST) X-ASG-Debug-ID: 1362160927-04cb6c2b044b3d0001-NocioJ Received: from mail-qc0-f178.google.com (mail-qc0-f178.google.com [209.85.216.178]) by cuda.sgi.com with ESMTP id jZDBtPqeHJLqlGna (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Fri, 01 Mar 2013 10:02:08 -0800 (PST) X-Barracuda-Envelope-From: enwlinux@gmail.com X-Barracuda-Apparent-Source-IP: 209.85.216.178 X-Barracuda-IPDD: Level1 [gmail.com/209.85.216.178] Received: by mail-qc0-f178.google.com with SMTP id j34so366357qco.37 for ; Fri, 01 Mar 2013 10:02:07 -0800 (PST) X-Barracuda-IPDD: Level1 [gmail.com/209.85.216.178] X-Barracuda-IPDD: Level1 [gmail.com/209.85.216.178] DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20120113; h=x-received:date:from:to:cc:subject:message-id:mime-version :content-type:content-disposition:user-agent; bh=eErL0bQXGqj3OMCrPg1VlJbS8aKsdl/qeS5ibtG9HeQ=; b=BYGwjssR60kvFLcC9xSIaqbvPDcZejdHenZYcocZn2fhc8u0iwUgdSePGnfoHoJcoC b59OFbkx/6f+tYlhuTAwNb23B393L2/QUIP7y25SG/NZWME1rf8Aped2sJ0zxWevFUuO j3YI9LnKzqtsxzDJDC/6ue0tebEdejCWEDGA8OmLK6iMaubxtPG3IoOjct1TCIyyfLu8 DyKtUlczjQ1ltgyjnKIusgiJrR4WgprCs2k+vRqKgLqCgrNhm2rvtd2ofRvRXMPlzarp igkauaoUR+LUT38Eo4wvEvtlLqFFN8wOtOrbM44LVXH1hH8h1dYt4wMTTNFwWWSs+scG EWkA== X-Received: by 10.224.216.9 with SMTP id hg9mr20746673qab.44.1362160921884; Fri, 01 Mar 2013 10:02:01 -0800 (PST) Received: from wallace (c-75-68-62-236.hsd1.nh.comcast.net. [75.68.62.236]) by mx.google.com with ESMTPS id 8sm20598761qed.6.2013.03.01.10.02.00 (version=TLSv1.2 cipher=RC4-SHA bits=128/128); Fri, 01 Mar 2013 10:02:01 -0800 (PST) Date: Fri, 1 Mar 2013 13:01:58 -0500 From: Eric Whitney To: xfs@oss.sgi.com Cc: sandeen@redhat.com Subject: [PATCH V2] xfstests: don't remove trailing zeros from integers Message-ID: <20130301180158.GC6449@wallace> X-ASG-Orig-Subj: [PATCH V2] xfstests: don't remove trailing zeros from integers MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: mail-qc0-f178.google.com[209.85.216.178] X-Barracuda-Start-Time: 1362160927 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=DKIM_SIGNED, DKIM_VERIFIED X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.123965 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature _within_tolerance strips trailing zeros from the min and max range values it outputs. This leads to damage if the min or max value is an integer containing trailing zeros rather than a real number with a fractional part containing trailing zeros. Xfstest 289 can exhibit this problem when its input is out of range. Modify the code so it will only remove trailing zeros found after a decimal point, and remove decimal points not followed by digits. Signed-off-by: Eric Whitney --- common.filter | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/common.filter b/common.filter index 9e4c90c..bfc800b 100644 --- a/common.filter +++ b/common.filter @@ -106,8 +106,11 @@ EOF # fix up min, max precision for output # can vary for 5.3, 6.2 - _min=`echo $_min | sed -e 's/0*$//'` # get rid of trailling zeroes - _max=`echo $_max | sed -e 's/0*$//'` # get rid of trailling zeroes + + # remove any trailing zeroes from min, max if they have fractional parts + # and then remove any decimal points not followed by digits + _min=`echo $_min | sed -e '/\./s/0*$//' | sed -e 's/\.$//'` + _max=`echo $_max | sed -e '/\./s/0*$//' | sed -e 's/\.$//'` if [ $_in_range -eq 1 ] then -- 1.7.10.4 From rjohnston@sgi.com Fri Mar 1 13:23:51 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id A85637FD5 for ; Fri, 1 Mar 2013 13:23:51 -0600 (CST) Received: from xmail.sgi.com (pv-excas3-dc21-nlb.corp.sgi.com [137.38.102.207]) by relay2.corp.sgi.com (Postfix) with ESMTP id 5B2AC304053; Fri, 1 Mar 2013 11:23:48 -0800 (PST) Received: from [128.162.233.55] (128.162.233.55) by xmail.sgi.com (137.38.102.30) with Microsoft SMTP Server (TLS) id 14.2.318.1; Fri, 1 Mar 2013 13:23:47 -0600 Message-ID: <51310046.5090306@sgi.com> Date: Fri, 1 Mar 2013 13:23:50 -0600 From: Rich Johnston User-Agent: Mozilla/5.0 (X11; Linux i686; rv:13.0) Gecko/20120615 Thunderbird/13.0.1 MIME-Version: 1.0 To: Dmitry Monakhov CC: , , , Subject: Re: [PATCH 09/10] xfstest: add defragmentation stress tests for ext4 References: <1361356935-29153-1-git-send-email-dmonakhov@openvz.org> <1361356935-29153-10-git-send-email-dmonakhov@openvz.org> In-Reply-To: <1361356935-29153-10-git-send-email-dmonakhov@openvz.org> Content-Type: text/plain; charset="ISO-8859-1"; format=flowed Content-Transfer-Encoding: 7bit X-Originating-IP: [128.162.233.55] On 02/20/2013 04:42 AM, Dmitry Monakhov wrote: > Perform various regression tests for ext4defrag subsystem > > 299'th Test1: Defragment file while other task does direct AIO > 300'th Test2: Perform defragmentation on file under buffered AIO > while third task does direct AIO to donor file > 301'th Test3: Two defrag tasks use common donor file. > 302'th Test4: Stress defragmentation. Several threads pefrorm typo perform > fragmentation at random position use inplace=1 will > allocate and free blocks inside defrag event improve > load pressure. > > This tests are considered dengerous because 300'th and 301'th are known typo dangerous > to trigger OOPS on recent kernels see:https://gist.github.com/dmonakhov/4770294 > > Signed-off-by: Dmitry Monakhov > --- > 299 | 126 +++++++++++++++++++++++++++++++++++++++++++++++ > 299.out | 4 ++ > 300 | 143 +++++++++++++++++++++++++++++++++++++++++++++++++++++ > 300.out | 4 ++ > 301 | 153 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++ > 301.out | 4 ++ > 302 | 130 ++++++++++++++++++++++++++++++++++++++++++++++++ > 302.out | 4 ++ > common.defrag | 4 +- > group | 6 ++- > 10 files changed, 575 insertions(+), 3 deletions(-) > create mode 100755 299 > create mode 100644 299.out > create mode 100755 300 > create mode 100644 300.out > create mode 100755 301 > create mode 100644 301.out > create mode 100755 302 > create mode 100644 302.out > > diff --git a/299 b/299 > new file mode 100755 > index 0000000..4a7a98c > --- /dev/null > +++ b/299 > @@ -0,0 +1,126 @@ > +#! /bin/bash > +# FSQA Test No. 299 > +# > +# Ext4 defragmentation stress test > +# Defragment file while other task does direct io > +#----------------------------------------------------------------------- > +# (c) 2013 Dmitry Monakhov > +# > +# This program is free software; you can redistribute it and/or > +# modify it under the terms of the GNU General Public License as > +# published by the Free Software Foundation. > +# > +# This program is distributed in the hope that it would be useful, > +# but WITHOUT ANY WARRANTY; without even the implied warranty of > +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the > +# GNU General Public License for more details. > +# > +# You should have received a copy of the GNU General Public License > +# along with this program; if not, write the Free Software Foundation, > +# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA > +# > +#----------------------------------------------------------------------- > +# > +# creator > +owner=dmonakhov@openvz.org > + > +seq=`basename $0` > +echo "QA output created by $seq" > + > +here=`pwd` > +tmp=/tmp/$$ > +status=1 # failure is the default! > +trap "rm -f $tmp.*; exit \$status" 0 1 2 3 15 > + > +# get standard environment, filters and checks > +. ./common.rc > +. ./common.filter > +. ./common.defrag > + > +# real QA test starts here > +_supported_os Linux > +_supported_fs ext4 > +_need_to_be_root > +_require_scratch > +_require_defrag > + I think you meant to set NUM_JOBS here like you did in [Patch 08/10], something like: +NUM_JOBS=$((4*LOAD_FACTOR)) otherwise you get ### [not run] /usr/local/bin/fio too old > +BLK_DEV_SIZE=`blockdev --getsz $SCRATCH_DEV` > +# We need space for 2 files (test file, and donor one) > +# reserve 30% in order to avoid ENOSPC > +FILE_SIZE=$((BLK_DEV_SIZE * (512 / (2 + 1)))) > + > +cat >$tmp-$seq.fio < +# Common e4defrag regression tests > +[global] > +ioengine=ioe_e4defrag > +iodepth=1 > +directory=${SCRATCH_MNT} > +filesize=${FILE_SIZE} > +size=999G > +buffered=0 > +fadvise_hint=0 > +group_reporting > + > +################################# > +# Test1 > +# Defragment file while other task does direct io > + > +# Continious sequential defrag activity > +[defrag-4k] > +ioengine=e4defrag > +iodepth=1 > +bs=128k > +donorname=test1.def > +filename=test1 > +inplace=0 > +rw=write > +numjobs=${NUM_JOBS} > +runtime=30*${TIME_FACTOR} > +time_based > + > +# Verifier > +[aio-dio-verifier] > +ioengine=libaio > +iodepth=128*${LOAD_FACTOR} > +numjobs=1 > +verify=crc32c-intel > +verify_fatal=1 > +verify_dump=1 > +verify_backlog=1024 > +verify_async=1 > +verifysort=1 > +direct=1 > +bs=64k > +rw=randwrite > +filename=test1 > +runtime=30*${TIME_FACTOR} > +time_based > +EOF > + > +_workout() > +{ > + echo "" > + echo " Start defragment activity " git does not like trailing whitespace ^ (same for the other 3 tests) > + echo "" > + cat $tmp-$seq.fio >> $seq.full > + run_check $FIO_PROG $tmp-$seq.fio > +} > + > +_require_fio $tmp-$seq.fio > + > +_scratch_mkfs >> $seq.full 2>&1 > +_scratch_mount > + > +if ! _workout; then > + umount $SCRATCH_DEV 2>/dev/null > + exit > +fi > + > +if ! _scratch_unmount; then > + echo "failed to umount" > + status=1 > + exit > +fi > +_check_scratch_fs > +status=$? > +exit diff --git a/299.out b/299.out new file mode 100644 index 0000000..b215a3f > diff --git a/299.out b/299.out > new file mode 100644 > index 0000000..c2b0b4c > --- /dev/null > +++ b/299.out > @@ -0,0 +1,4 @@ > +QA output created by 299 > + > + Start defragment activity remove trailing whitespace ^ (same for the other 3 tests) Let me know if you agree with these changes and I will make them at commit time. Thanks --Rich From rjohnston@sgi.com Fri Mar 1 14:11:20 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 0EEB97F9A for ; Fri, 1 Mar 2013 14:11:20 -0600 (CST) Received: from xmail.sgi.com (pv-excas3-dc21.corp.sgi.com [137.38.102.206]) by relay3.corp.sgi.com (Postfix) with ESMTP id 53A4EAC002; Fri, 1 Mar 2013 12:11:16 -0800 (PST) Received: from [128.162.233.55] (128.162.233.55) by xmail.sgi.com (137.38.102.30) with Microsoft SMTP Server (TLS) id 14.2.318.1; Fri, 1 Mar 2013 14:11:15 -0600 Message-ID: <51310B63.4070105@sgi.com> Date: Fri, 1 Mar 2013 14:11:15 -0600 From: Rich Johnston User-Agent: Mozilla/5.0 (X11; Linux i686; rv:13.0) Gecko/20120615 Thunderbird/13.0.1 MIME-Version: 1.0 To: Dmitry Monakhov CC: , , , Subject: Re: [PATCH 10/10] xfstests: add disk failure simulation test References: <1361356935-29153-1-git-send-email-dmonakhov@openvz.org> <1361356935-29153-11-git-send-email-dmonakhov@openvz.org> In-Reply-To: <1361356935-29153-11-git-send-email-dmonakhov@openvz.org> Content-Type: text/plain; charset="ISO-8859-1"; format=flowed Content-Transfer-Encoding: 7bit X-Originating-IP: [128.162.233.55] On 02/20/2013 04:42 AM, Dmitry Monakhov wrote: > There are many situations where disk may fail for example > 1) brutal usb dongle unplug > 2) iscsi (or any other netbdev) failure due to network issues > In this situation filesystem which use this blockdevice is > expected to fail(force RO remount, abort, etc) but whole system > should still be operational. In other words: > 1) Kernel should not panic > 2) Memory should not leak > 3) Data integrity operations (sync,fsync,fdatasync, directio) should fail > for affected filesystem > 4) It should be possible to umount broken filesystem > > Later when disk becomes available again we expect(only for journaled filesystems): > 5) It will be possible to mount filesystem w/o explicit fsck (in order to caught typo s/caught/catch/g > issues like https://patchwork.kernel.org/patch/1983981/) > 6) Filesystem should be operational > 7) After mount/umount has being done all errors should be fixed so fsck should > not spot any issues. > > This test use fault enjection (CONFIG_FAIL_MAKE_REQUEST=y config option ) May want to mention all the kernel config options required. i.e. CONFIG_FAULT_INJECTION=y ... are there others? CONFIG_FAULT_INJECTION_DEBUG_FS=y ??? > which force all new IO requests to fail for a given device. Xfs already has to force > XFS_IOC_GOINGDOWN ioctl which provides similar behaviour, but it is fs speciffic typos s/behaviour/behavior/g s/speciffic/specific > and it does it in an easy way because it perform freeze_bdev() before actual > shotdown. typo s/shotdown/shutdown/g > > Test run fsstress in background and then force disk failure. > Once disk failed it check that (1)-(4) is true. Once the disk fails, check that (1)-(4) are true. > Then makes disk available again and check that (5)-(7) is also true make the disk ... are > > BE CAREFUL!! test known to cause memory corruption for XFS > see: https://gist.github.com/dmonakhov/4953045 > From rjohnston@sgi.com Fri Mar 1 14:23:29 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 6FE807FD3 for ; Fri, 1 Mar 2013 14:23:29 -0600 (CST) Received: from xmail.sgi.com (pv-excas3-dc21-nlb.corp.sgi.com [137.38.102.207]) by relay2.corp.sgi.com (Postfix) with ESMTP id 2AFED304043; Fri, 1 Mar 2013 12:23:26 -0800 (PST) Received: from [128.162.233.55] (128.162.233.55) by xmail.sgi.com (137.38.102.30) with Microsoft SMTP Server (TLS) id 14.2.318.1; Fri, 1 Mar 2013 14:23:25 -0600 Message-ID: <51310E40.7070008@sgi.com> Date: Fri, 1 Mar 2013 14:23:28 -0600 From: Rich Johnston User-Agent: Mozilla/5.0 (X11; Linux i686; rv:13.0) Gecko/20120615 Thunderbird/13.0.1 MIME-Version: 1.0 To: Dmitry Monakhov CC: , , , Subject: Re: [PATCH 00/10] xfstests: Stress tests improments v5 References: <1361356935-29153-1-git-send-email-dmonakhov@openvz.org> In-Reply-To: <1361356935-29153-1-git-send-email-dmonakhov@openvz.org> Content-Type: text/plain; charset="ISO-8859-1"; format=flowed Content-Transfer-Encoding: 7bit X-Originating-IP: [128.162.233.55] Committed patches 1-3 and 5-8. Waiting for responses back on patches 4, 9, and 10. Thanks --Rich On 02/20/2013 04:42 AM, Dmitry Monakhov wrote: > 1 add fio requirement V2 > 2 add configurable load factors > 3 hardcode fops for determinable fsstests runs > 4 fsstress add replace file operation > 5 allow fsstress to use load factor where appropriate > 6 move run_check to common.rc > 7 add fallocate/truncate vs AIO/DIO stress test > 8 add fallocate/punch_hole vs AIO/DIO stress test > 9 add defragmentation stress tests for ext4 > 10 add disk failure simulation test > commit 892125a53aac8e82dec99fe4e824c39513d4a17a Author: Dmitry Monakhov Date: Wed Feb 20 10:42:13 2013 +0000 xfstest: add fallocate/punch_hole vs AIO/DIO stress test Run random AIO/DIO activity (fio's job:direct_aio_raicer) random fallocate activity(fio's job:falloc_raicer) and random punch_hole activity(punch_hole_raicer) on a common file in parallel. If a race exists, old dio request may rewrite punched block after it was allocated to another file, we will catch that by verifier fio's job: "aio-dio-verifier". Signed-off-by: Dmitry Monakhov Reviewed-by: Rich Johnston Signed-off-by: Rich Johnston commit 0f88dc26abf55cee39ede490da08ed0d2960cdb2 Author: Dmitry Monakhov Date: Wed Feb 20 10:42:12 2013 +0000 xfstest: add fallocate/truncate vs AIO/DIO stress test Run DIO, fallocate and truncate threads on a common file in parallel. If a race exists, the old dio request may rewrite blocks after it was allocated to another file, we will catch that by verifying blocks content. this patch known to catch deadlock for ext4 http://lists.openwall.net/linux-ext4/2012/09/06/3 Signed-off-by: Dmitry Monakhov Reviewed-by: Rich Johnston Signed-off-by: Rich Johnston commit bb949015a8d3fcf4a5c105b1edd74f27b848a806 Author: Dmitry Monakhov Date: Wed Feb 20 10:42:11 2013 +0000 xfstest: move run_check to common.rc Signed-off-by: Dmitry Monakhov Reviewed-by: Rich Johnston Signed-off-by: Rich Johnston Move run_check to common.rc. commit b84aade2f49f309c44e6c0b029586c9dcb7b1c22 Author: Dmitry Monakhov Date: Wed Feb 20 10:42:10 2013 +0000 xfstest: allow fsstress to use load factor where appropriate 1) Add _scale_fsstress_args function which transform arguments according to load factors 2) Let all non deterministic fsstress tests to use scaled arguments Signed-off-by: Dmitry Monakhov Reviewed-by: Rich Johnston Signed-off-by: Rich Johnston commit d14981fa536ac0106dbe9b3d5088a5a50be49f55 Author: Dmitry Monakhov Date: Wed Feb 20 10:42:08 2013 +0000 xfstests: hardcode fops for determinable fsstests runs 106,107 and 117 are frozen tests which use known seed, it is reasonable to explicitly hardcode file operations in order to avoid implicit changes caused by future changes in fsstress. NOTE: options generated like follows: fsstress -S c $ORIG_ARGS Signed-off-by: Dmitry Monakhov Reviewed-by: Rich Johnston Signed-off-by: Rich Johnston commit 66a98478e3cffecfbd62d3a124b626ddda447c57 Author: Dmitry Monakhov Date: Wed Feb 20 10:42:07 2013 +0000 xfstest: add configurable load factors Most stress test has probable behavior, the longer test run the larger corner cases will be cover. It is reasonable to allow user to provide some sort of system load factor. This patch introduce two global variables LOAD_FACTOR: Usually means factor number of running tasks TIME_FACTOR: Usually means factor of run time, or number of operations If not specified both variables defined to 1, so original behavior preserved. TODO: Change all stress tests to use this variables Signed-off-by: Dmitry Monakhov Reviewed-by: Rich Johnston Signed-off-by: Rich Johnston commit b3db6021fc2df4e99c9e098612446f4c86e70766 Author: Dmitry Monakhov Date: Wed Feb 20 10:42:06 2013 +0000 xfstests: add fio requirement V2 FIO is very flexible io generator, I would call it IO swiss knife. Currently we have tons of hardcoded application which reproduces some predefined scenario. This approach has obvious disadvantages 1) Lack of flexibility: one written it is hard to modify it in future 2) Code base is large, many routines written again and again At the same time add new fio based test, just add simple INI file. This greatly simplifies code review. I do believe that some day we will replace most of hardcoded io binaries with fio. One who is planning to run $FIO_PROG should first check that system contains appropriate version which is able to handle jobfile for example: _require_fio 286-job.fio Signed-off-by: Dmitry Monakhov Reviewed-by: Rich Johnston Signed-off-by: Rich Johnston From tinguely@sgi.com Fri Mar 1 14:24:27 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id EC2147FE7 for ; Fri, 1 Mar 2013 14:24:26 -0600 (CST) Received: from eagdhcp-232-136.americas.sgi.com (eagdhcp-232-136.americas.sgi.com [128.162.232.136]) by relay2.corp.sgi.com (Postfix) with ESMTP id 56A54304043; Fri, 1 Mar 2013 12:24:26 -0800 (PST) Message-ID: <51310E7A.1000905@sgi.com> Date: Fri, 01 Mar 2013 14:24:26 -0600 From: Mark Tinguely User-Agent: Mozilla/5.0 (X11; FreeBSD amd64; rv:9.0) Gecko/20120122 Thunderbird/9.0 MIME-Version: 1.0 To: Tony Lu CC: Alex Elder , "linux-kernel@vger.kernel.org" , Chris Metcalf , "xfs@oss.sgi.com" , Ben Myers , Dave Chinner , "linux-fsdevel@vger.kernel.org" Subject: Re: [PATCH] xfs: Fix possible truncation of log data in xlog_bread_noalign() References: <20130223000802.GB26081@dastard> <20130223235546.GA5551@dastard> <20130224141017.GC5551@dastard> <5130CE9E.9080501@sgi.com> In-Reply-To: <5130CE9E.9080501@sgi.com> Content-Type: text/plain; charset=ISO-8859-1; format=flowed Content-Transfer-Encoding: 7bit On 03/01/13 09:51, Mark Tinguely wrote: > On 02/26/13 01:28, Tony Lu wrote: >> I get a reliable way to reproduce this bug. The logprint and metadump >> are attached. >> >> Kernel version: 2.6.38.8 >> Mkfs.xfs version: xfsprogs-3.1.1 >> mkfs.xfs -s size=4096 /dev/sda1 >> >> Run the following mount-cp-umount script to reproduce: >> #!/bin/sh >> device=/dev/sda1 >> mount_point=/mnt >> times=10 >> >> for ((num=1;num<=$times;num++)) >> do >> echo "$num mount $device $mount_point" >> mount $device $mount_point >> >> echo "cp -rf /bin $mount_point/$num" >> cp -rf /bin $mount_point/$num >> >> echo "$num umount $device $mount_point" >> umount $mount_point >> >> #num=$(($num + 1)) >> done >> >> After several times of mount/cp/umount, this xfs crashes, and the xfs >> partition can not be mounted any more. Here is the output of console. >> -sh-4.1# ./umount-test >> 1 mount /dev/sda1 /mnt >> XFS mounting filesystem sda1 >> cp -rf /bin /mnt/1 >> 1 umount /dev/sda1 /mnt >> 2 mount /dev/sda1 /mnt >> XFS mounting filesystem sda1 >> cp -rf /bin /mnt/2 >> 2 umount /dev/sda1 /mnt >> 3 mount /dev/sda1 /mnt >> XFS mounting filesystem sda1 >> cp -rf /bin /mnt/3 >> 3 umount /dev/sda1 /mnt >> 4 mount /dev/sda1 /mnt >> XFS mounting filesystem sda1 >> cp -rf /bin /mnt/4 >> 4 umount /dev/sda1 /mnt >> 5 mount /dev/sda1 /mnt >> XFS mounting filesystem sda1 >> Starting XFS recovery on filesystem: sda1 (logdev: internal) >> Ending XFS recovery on filesystem: sda1 (logdev: internal)cp -rf /bin >> /mnt/5 >> 5 umount /dev/sda1 /mnt >> 6 mount /dev/sda1 /mnt >> >> XFS mounting filesystem sda1 >> Starting XFS recovery on filesystem: sda1 (logdev: internal) >> Ending XFS recovery on filesystem: sda1 (logdev: internal)Interrupt >> cp -rf /bin /mnt/6 >> 6 umount /dev/sda1 /mnt >> 7 mount /dev/sda1 /mnt >> >> XFS mounting filesystem sda1 >> cp -rf /bin /mnt/7 >> 7 umount /dev/sda1 /mnt >> Interrupt >> 8 mount /dev/sda1 /mnt >> XFS mounting filesystem sda1 >> Starting XFS recovery on filesystem: sda1 (logdev: internal) >> XFS: xlog_recover_process_data: bad clientid >> XFS: log mount/recovery failed: error 5 >> XFS: log mount failed >> >> Thanks >> -Tony > > It works fine on a 2.6.32 machine I had sitting around - and I never > required log recovery. > > I think you need to answer Dave's question as to why is your unmounts > are requiring recovery? > > Are there errors in the /var/log/messages? > > I downloaded the Linux 2.6.38.8 source and take a look if I can recreate > the problem. > > --Mark. I could not reproduce the problem on a vanilla install. XFS shutdown and remounted cleanly running your script (several iterations looping set to 100). I started fsstress on another XFS partition on the same disk to see if I could force a shutdown race. With CONFIG_XFS_DEBUG=y, I could trigger other ASSERTs on the fsstress partition so I never stayed up long enough to cause a shutdown race. Not wanting to patch that version of Linux/XFS, I am bailing here. If you want to turn on the XFS debug it may point out why your filesystem is not shutting down cleanly. --Mark. From david@fromorbit.com Fri Mar 1 14:30:40 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 405AF7FEE for ; Fri, 1 Mar 2013 14:30:40 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay3.corp.sgi.com (Postfix) with ESMTP id CD732AC002 for ; Fri, 1 Mar 2013 12:30:39 -0800 (PST) X-ASG-Debug-ID: 1362169837-04cb6c2b015bcf0001-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id hhPzHqfALtVIbkGQ for ; Fri, 01 Mar 2013 12:30:37 -0800 (PST) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AhwOAIUPMVF5LOvW/2dsb2JhbABEhWa3PoUZfhdzgh8BAQU6HCMQCAMOCgklDwUNGAMhE4gBAw63ZA2JNBWMMIF5Ij0Hgl9hA5RmgVyLVIUYgxw Received: from ppp121-44-235-214.lns20.syd7.internode.on.net (HELO dastard) ([121.44.235.214]) by ipmail05.adl6.internode.on.net with ESMTP; 02 Mar 2013 07:00:28 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UBWb4-0007iQ-4e; Sat, 02 Mar 2013 07:30:26 +1100 Date: Sat, 2 Mar 2013 07:30:26 +1100 From: Dave Chinner To: Eric Whitney Cc: xfs@oss.sgi.com, sandeen@redhat.com Subject: Re: [PATCH V2] xfstests: don't remove trailing zeros from integers Message-ID: <20130301203026.GC23616@dastard> X-ASG-Orig-Subj: Re: [PATCH V2] xfstests: don't remove trailing zeros from integers References: <20130301180158.GC6449@wallace> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <20130301180158.GC6449@wallace> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1362169837 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.123975 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Fri, Mar 01, 2013 at 01:01:58PM -0500, Eric Whitney wrote: > _within_tolerance strips trailing zeros from the min and max range > values it outputs. This leads to damage if the min or max value is > an integer containing trailing zeros rather than a real number with > a fractional part containing trailing zeros. Xfstest 289 can exhibit > this problem when its input is out of range. Modify the code so it > will only remove trailing zeros found after a decimal point, and > remove decimal points not followed by digits. > > Signed-off-by: Eric Whitney > --- > common.filter | 7 +++++-- > 1 file changed, 5 insertions(+), 2 deletions(-) > > diff --git a/common.filter b/common.filter > index 9e4c90c..bfc800b 100644 > --- a/common.filter > +++ b/common.filter > @@ -106,8 +106,11 @@ EOF > > # fix up min, max precision for output > # can vary for 5.3, 6.2 > - _min=`echo $_min | sed -e 's/0*$//'` # get rid of trailling zeroes > - _max=`echo $_max | sed -e 's/0*$//'` # get rid of trailling zeroes > + > + # remove any trailing zeroes from min, max if they have fractional parts > + # and then remove any decimal points not followed by digits > + _min=`echo $_min | sed -e '/\./s/0*$//' | sed -e 's/\.$//'` > + _max=`echo $_max | sed -e '/\./s/0*$//' | sed -e 's/\.$//'` You can do this with a single sed invocation via multiple expressions: $ echo 200.00 | sed -e '/\./s/0*$//' -e 's/\.$//' 200 $ Cheers, Dave. -- Dave Chinner david@fromorbit.com From david@fromorbit.com Fri Mar 1 14:53:08 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id CD2BE7FD5 for ; Fri, 1 Mar 2013 14:53:08 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay1.corp.sgi.com (Postfix) with ESMTP id 9A1B68F8035 for ; Fri, 1 Mar 2013 12:53:08 -0800 (PST) X-ASG-Debug-ID: 1362171186-04bdf022955ffe0001-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id CTvy1TkoLLWT3RBc for ; Fri, 01 Mar 2013 12:53:07 -0800 (PST) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AhwOAJ4TMVF5LOvW/2dsb2JhbABEhWa3P4UZfhdzgh8BAQQBJxMcIwULCAMYCSUPBSUDIROIDQXBGxWOKSI9B4JfYQOWQolkhwiDHA Received: from ppp121-44-235-214.lns20.syd7.internode.on.net (HELO dastard) ([121.44.235.214]) by ipmail05.adl6.internode.on.net with ESMTP; 02 Mar 2013 07:23:06 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UBWwz-0007oA-Ky; Sat, 02 Mar 2013 07:53:05 +1100 Date: Sat, 2 Mar 2013 07:53:05 +1100 From: Dave Chinner To: Ole Tange Cc: xfs@oss.sgi.com Subject: Re: xfs_repair segfaults Message-ID: <20130301205305.GD23616@dastard> X-ASG-Orig-Subj: Re: xfs_repair segfaults References: <20130301111701.GB23616@dastard> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1362171186 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 1.00 X-Barracuda-Spam-Status: No, SCORE=1.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_TG232 X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.123977 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 1.00 BSF_SC0_TG232 BODY: Custom Rule TG232 On Fri, Mar 01, 2013 at 01:24:36PM +0100, Ole Tange wrote: > On Fri, Mar 1, 2013 at 12:17 PM, Dave Chinner wrote: > > On Thu, Feb 28, 2013 at 04:22:08PM +0100, Ole Tange wrote: > : > >> I forced a RAID online. I have done that before and xfs_repair > >> normally removes the last hour of data or so, but saves everything > >> else. > > > > Why did you need to force it online? > > More than 2 harddisks went offline. We have seen that before and it is > not due to bad harddisks. It may be due to driver/timings/controller. I thought that might be the case. What filesystem errors occurred when the srives went offline? > >> /usr/local/src/xfsprogs-3.1.10/repair# ./xfs_repair -n /dev/md5p1 > >> Phase 1 - find and verify superblock... > >> Phase 2 - using internal log > >> - scan filesystem freespace and inode maps... > >> flfirst 232 in agf 91 too large (max = 128) > > > > Can you run: > > > > # xfs_db -c "agf 91" -c p /dev/md5p1 > > > > And post the output? > > # xfs_db -c "agf 91" -c p /dev/md5p1 > xfs_db: cannot init perag data (117) Interesting. It's detecting corrupt AG headers. > magicnum = 0x58414746 > versionnum = 1 > seqno = 91 > length = 268435200 > bnoroot = 295199 > cntroot = 13451007 > bnolevel = 2 > cntlevel = 2 > flfirst = 232 > fllast = 32 > flcount = 191 That implies that the free list is actually 232+191-32 = 391 entries long. That doesn't add up any way I look at it. both the flfirst and flcount fields look wrong here, which rules out a simple bit error as the problem. I can't see how these values would have been written by XFS as they are out of range for 512 byte sector AGFL: be32_add_cpu(&agf->agf_flfirst, 1); xfs_trans_brelse(tp, agflbp); if (be32_to_cpu(agf->agf_flfirst) == XFS_AGFL_SIZE(mp)) agf->agf_flfirst = 0; So I suspect that something more than just disks going off line here went wrong here, as I've never seen this sort of corruption before... Cheers, Dave. -- Dave Chinner david@fromorbit.com From sandeen@sandeen.net Fri Mar 1 16:14:29 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 38BDB7FD5 for ; Fri, 1 Mar 2013 16:14:29 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay1.corp.sgi.com (Postfix) with ESMTP id 283EF8F8040 for ; Fri, 1 Mar 2013 14:14:25 -0800 (PST) X-ASG-Debug-ID: 1362176064-04cb6c2b01628e0001-NocioJ Received: from sandeen.net (sandeen.net [63.231.237.45]) by cuda.sgi.com with ESMTP id uMobwCgf09SoeGqU for ; Fri, 01 Mar 2013 14:14:24 -0800 (PST) X-Barracuda-Envelope-From: sandeen@sandeen.net X-Barracuda-Apparent-Source-IP: 63.231.237.45 Received: from liberator.sandeen.net (liberator.sandeen.net [10.0.0.4]) (using TLSv1 with cipher DHE-RSA-CAMELLIA256-SHA (256/256 bits)) (No client certificate requested) by sandeen.net (Postfix) with ESMTPSA id 5DD8C63C5856; Fri, 1 Mar 2013 16:14:24 -0600 (CST) Message-ID: <5131283F.8030704@sandeen.net> Date: Fri, 01 Mar 2013 16:14:23 -0600 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: Ole Tange CC: xfs@oss.sgi.com Subject: Re: xfs_repair segfaults References: X-ASG-Orig-Subj: Re: xfs_repair segfaults In-Reply-To: X-Enigmail-Version: 1.5 Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: sandeen.net[63.231.237.45] X-Barracuda-Start-Time: 1362176064 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.123981 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On 2/28/13 9:22 AM, Ole Tange wrote: > I forced a RAID online. I have done that before and xfs_repair > normally removes the last hour of data or so, but saves everything > else. > > Today that did not work: > > /usr/local/src/xfsprogs-3.1.10/repair# ./xfs_repair -n /dev/md5p1 > Phase 1 - find and verify superblock... > Phase 2 - using internal log > - scan filesystem freespace and inode maps... > flfirst 232 in agf 91 too large (max = 128) > Segmentation fault (core dumped) FWIW, the fs in question seems to need a log replay, so xfs_repair -n would find it in a worse state... I had forgotten that xfs_repair -n won't complain about a dirty log. Seems like it should. But, the log is corrupt enough that it won't replay: XFS (loop0): Mounting Filesystem XFS (loop0): Starting recovery (logdev: internal) ffff88036e7cd800: 58 41 47 46 00 00 00 01 00 00 00 5b 0f ff ff 00 XAGF.......[.... XFS (loop0): Internal error xfs_alloc_read_agf at line 2146 of file fs/xfs/xfs_alloc.c. Caller 0xffffffffa033d009 so really this'll require xfs_repair -L xfs_repair -L doesn't segfault though, FWIW. I'll try to look into the -n segfault in any case. -Eric > Core put in: http://dna.ku.dk/~tange/tmp/xfs_repair.core.bz2 > > I tried using the git-version, too, but could not get that to compile. > > # uname -a > Linux franklin 3.2.0-0.bpo.4-amd64 #1 SMP Debian 3.2.35-2~bpo60+1 > x86_64 GNU/Linux > > # ./xfs_repair -V > xfs_repair version 3.1.10 > > # cat /proc/cpuinfo |grep MH | wc > 64 256 1280 > > # cat /proc/partitions |grep md5 > 9 5 125024550912 md5 > 259 0 107521114112 md5p1 > 259 1 17503434752 md5p2 > > # cat /proc/mdstat > Personalities : [raid0] [raid6] [raid5] [raid4] > md5 : active raid0 md1[0] md4[3] md3[2] md2[1] > 125024550912 blocks super 1.2 512k chunks > > md1 : active raid6 sdd[1] sdi[9] sdq[13] sdau[7] sdt[10] sdg[5] sdf[4] sde[2] > 31256138752 blocks super 1.2 level 6, 128k chunk, algorithm 2 > [10/8] [_UU_UUUUUU] > bitmap: 2/2 pages [8KB], 1048576KB chunk > > md4 : active raid6 sdo[13] sdu[9] sdad[8] sdh[7] sdc[6] sds[11] > sdap[3] sdao[2] sdk[1] > 31256138752 blocks super 1.2 level 6, 128k chunk, algorithm 2 > [10/8] [_UUUU_UUUU] > [>....................] recovery = 2.1% (84781876/3907017344) > finish=2196.4min speed=29003K/sec > bitmap: 2/2 pages [8KB], 1048576KB chunk > > md2 : active raid6 sdac[0] sdal[9] sdak[8] sdaj[7] sdai[6] sdah[5] > sdag[4] sdaf[3] sdae[2] sdr[10] > 31256138752 blocks super 1.2 level 6, 128k chunk, algorithm 2 > [10/10] [UUUUUUUUUU] > bitmap: 0/2 pages [0KB], 1048576KB chunk > > md3 : active raid6 sdaq[0] sdab[9] sdaa[8] sdb[7] sdy[6] sdx[5] sdw[4] > sdv[3] sdz[10] sdj[1] > 31256138752 blocks super 1.2 level 6, 128k chunk, algorithm 2 > [10/10] [UUUUUUUUUU] > bitmap: 0/2 pages [0KB], 1048576KB chunk > > unused devices: > > # smartctl -a /dev/sdau|grep Model > Device Model: Hitachi HDS724040ALE640 > > # hdparm -W /dev/sdau > /dev/sdau: > write-caching = 0 (off) > > # dmesg > [ 3745.914280] xfs_repair[25300]: segfault at 7f5d9282b000 ip > 000000000042d068 sp 00007f5da3183dd0 error 4 in > xfs_repair[400000+7f000] > > > /Ole > > _______________________________________________ > xfs mailing list > xfs@oss.sgi.com > http://oss.sgi.com/mailman/listinfo/xfs > From david@fromorbit.com Fri Mar 1 16:31:21 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 10D1E7F63 for ; Fri, 1 Mar 2013 16:31:21 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay1.corp.sgi.com (Postfix) with ESMTP id C768F8F8040 for ; Fri, 1 Mar 2013 14:31:20 -0800 (PST) X-ASG-Debug-ID: 1362177078-04bdf0229666140001-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id X9ZhtEZ6Xip9nDQy for ; Fri, 01 Mar 2013 14:31:18 -0800 (PST) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AhwOAJIqMVF5LOvW/2dsb2JhbABEhWa3P4UZfxdzgh8BAQU6HCMQCAMYCSUPBSUDIROIEsEhFY4pIj0Hgl9hA5ZCiWSHCIMc Received: from ppp121-44-235-214.lns20.syd7.internode.on.net (HELO dastard) ([121.44.235.214]) by ipmail05.adl6.internode.on.net with ESMTP; 02 Mar 2013 09:01:17 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UBYU0-0007xz-3J; Sat, 02 Mar 2013 09:31:16 +1100 Date: Sat, 2 Mar 2013 09:31:16 +1100 From: Dave Chinner To: Eric Sandeen Cc: Ole Tange , xfs@oss.sgi.com Subject: Re: xfs_repair segfaults Message-ID: <20130301223116.GE23616@dastard> X-ASG-Orig-Subj: Re: xfs_repair segfaults References: <5131283F.8030704@sandeen.net> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <5131283F.8030704@sandeen.net> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1362177078 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.123983 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Fri, Mar 01, 2013 at 04:14:23PM -0600, Eric Sandeen wrote: > On 2/28/13 9:22 AM, Ole Tange wrote: > > I forced a RAID online. I have done that before and xfs_repair > > normally removes the last hour of data or so, but saves everything > > else. > > > > Today that did not work: > > > > /usr/local/src/xfsprogs-3.1.10/repair# ./xfs_repair -n /dev/md5p1 > > Phase 1 - find and verify superblock... > > Phase 2 - using internal log > > - scan filesystem freespace and inode maps... > > flfirst 232 in agf 91 too large (max = 128) > > Segmentation fault (core dumped) > > FWIW, the fs in question seems to need a log replay, so > xfs_repair -n would find it in a worse state... > I had forgotten that xfs_repair -n won't complain about > a dirty log. Seems like it should. > > But, the log is corrupt enough that it won't replay: > > XFS (loop0): Mounting Filesystem > XFS (loop0): Starting recovery (logdev: internal) > ffff88036e7cd800: 58 41 47 46 00 00 00 01 00 00 00 5b 0f ff ff 00 XAGF.......[.... ^^ It's detecting AGF 91 is corrupt.... Cheers, Dave. -- Dave Chinner david@fromorbit.com From sandeen@sandeen.net Fri Mar 1 16:32:24 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 777F77FF0 for ; Fri, 1 Mar 2013 16:32:24 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id 5D25C304032 for ; Fri, 1 Mar 2013 14:32:20 -0800 (PST) X-ASG-Debug-ID: 1362177139-04cbb07dbf62430001-NocioJ Received: from sandeen.net (sandeen.net [63.231.237.45]) by cuda.sgi.com with ESMTP id SnX2fgD2BF87i9os for ; Fri, 01 Mar 2013 14:32:20 -0800 (PST) X-Barracuda-Envelope-From: sandeen@sandeen.net X-Barracuda-Apparent-Source-IP: 63.231.237.45 Received: from liberator.sandeen.net (liberator.sandeen.net [10.0.0.4]) (using TLSv1 with cipher DHE-RSA-CAMELLIA256-SHA (256/256 bits)) (No client certificate requested) by sandeen.net (Postfix) with ESMTPSA id 9B4EF63C5856; Fri, 1 Mar 2013 16:32:19 -0600 (CST) Message-ID: <51312C73.5060203@sandeen.net> Date: Fri, 01 Mar 2013 16:32:19 -0600 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: Dave Chinner CC: Ole Tange , xfs@oss.sgi.com Subject: Re: xfs_repair segfaults References: <5131283F.8030704@sandeen.net> <20130301223116.GE23616@dastard> X-ASG-Orig-Subj: Re: xfs_repair segfaults In-Reply-To: <20130301223116.GE23616@dastard> X-Enigmail-Version: 1.5 Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: sandeen.net[63.231.237.45] X-Barracuda-Start-Time: 1362177139 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.123983 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On 3/1/13 4:31 PM, Dave Chinner wrote: > On Fri, Mar 01, 2013 at 04:14:23PM -0600, Eric Sandeen wrote: >> On 2/28/13 9:22 AM, Ole Tange wrote: >>> I forced a RAID online. I have done that before and xfs_repair >>> normally removes the last hour of data or so, but saves everything >>> else. >>> >>> Today that did not work: >>> >>> /usr/local/src/xfsprogs-3.1.10/repair# ./xfs_repair -n /dev/md5p1 >>> Phase 1 - find and verify superblock... >>> Phase 2 - using internal log >>> - scan filesystem freespace and inode maps... >>> flfirst 232 in agf 91 too large (max = 128) >>> Segmentation fault (core dumped) >> >> FWIW, the fs in question seems to need a log replay, so >> xfs_repair -n would find it in a worse state... >> I had forgotten that xfs_repair -n won't complain about >> a dirty log. Seems like it should. >> >> But, the log is corrupt enough that it won't replay: >> >> XFS (loop0): Mounting Filesystem >> XFS (loop0): Starting recovery (logdev: internal) >> ffff88036e7cd800: 58 41 47 46 00 00 00 01 00 00 00 5b 0f ff ff 00 XAGF.......[.... > ^^ > It's detecting AGF 91 is corrupt.... Yep and that's what lights up when repair -L runs too. Ole, you can xfs_mdrestore your metadump image and run test repairs on the result, if you want a more realistic "dry run" of what repair would do. -Eric > Cheers, > > Dave. > From bpm@sgi.com Fri Mar 1 17:29:42 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 8959B7FF4 for ; Fri, 1 Mar 2013 17:29:42 -0600 (CST) Received: from whiskey.americas.sgi.com (eagdhcp-232-197.americas.sgi.com [128.162.232.197]) by relay1.corp.sgi.com (Postfix) with ESMTP id 32B0F8F8035; Fri, 1 Mar 2013 15:29:42 -0800 (PST) Received: by whiskey.americas.sgi.com (Postfix, from userid 4600) id F1FC9500B4B; Fri, 1 Mar 2013 17:29:41 -0600 (CST) Date: Fri, 1 Mar 2013 17:29:41 -0600 From: Ben Myers To: stable@vger.kernel.org Cc: xfs@oss.sgi.com, dchinner@redhat.com Subject: [STABLE] [PATCH] xfs: xfs_bmap_add_attrfork_local is too generic Message-ID: <20130301232941.GJ30652@sgi.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline User-Agent: Mutt/1.5.20 (2009-06-14) Hi, Please take this fix for 3.8-stable. It resolves a problem with write verifiers and symlinks which results in a forced unmount. Thanks, Ben From: Dave Chinner Date: Mon, 11 Feb 2013 15:58:13 +1100 Subject: [PATCH] xfs: xfs_bmap_add_attrfork_local is too generic Commit 1e82379b018ceed0f0912327c60d73107dacbcb3 upstream. When we are converting local data to an extent format as a result of adding an attribute, the type of data contained in the local fork determines the behaviour that needs to occur. xfs_bmap_add_attrfork_local() already handles the directory data case specially by using S_ISDIR() and calling out to xfs_dir2_sf_to_block(), but with verifiers we now need to handle each different type of metadata specially and different metadata formats require different verifiers (and eventually block header initialisation). There is only a single place that we add and attribute fork to the inode, but that is in the attribute code and it knows nothing about the specific contents of the data fork. It is only the case of local data that is the issue here, so adding code to hadnle this case in the attribute specific code is wrong. Hence we are really stuck trying to detect the data fork contents in xfs_bmap_add_attrfork_local() and performing the correct callout there. Luckily the current cases can be determined by S_IS* macros, and we can push the work off to data specific callouts, but each of those callouts does a lot of work in common with xfs_bmap_local_to_extents(). The only reason that this fails for symlinks right now is is that xfs_bmap_local_to_extents() assumes the data fork contains extent data, and so attaches a a bmap extent data verifier to the buffer and simply copies the data fork information straight into it. To fix this, allow us to pass a "formatting" callback into xfs_bmap_local_to_extents() which is responsible for setting the buffer type, initialising it and copying the data fork contents over to the new buffer. This allows callers to specify how they want to format the new buffer (which is necessary for the upcoming CRC enabled metadata blocks) and hence make xfs_bmap_local_to_extents() useful for any type of data fork content. Signed-off-by: Dave Chinner Reviewed-by: Mark Tinguely Signed-off-by: Ben Myers --- fs/xfs/xfs_bmap.c | 114 ++++++++++++++++++++++++++++++++++++++++++++---------- 1 file changed, 93 insertions(+), 21 deletions(-) diff --git a/fs/xfs/xfs_bmap.c b/fs/xfs/xfs_bmap.c index cdb2d33..572a858 100644 --- a/fs/xfs/xfs_bmap.c +++ b/fs/xfs/xfs_bmap.c @@ -147,7 +147,10 @@ xfs_bmap_local_to_extents( xfs_fsblock_t *firstblock, /* first block allocated in xaction */ xfs_extlen_t total, /* total blocks needed by transaction */ int *logflagsp, /* inode logging flags */ - int whichfork); /* data or attr fork */ + int whichfork, /* data or attr fork */ + void (*init_fn)(struct xfs_buf *bp, + struct xfs_inode *ip, + struct xfs_ifork *ifp)); /* * Search the extents list for the inode, for the extent containing bno. @@ -357,7 +360,42 @@ xfs_bmap_add_attrfork_extents( } /* - * Called from xfs_bmap_add_attrfork to handle local format files. + * Block initialisation functions for local to extent format conversion. + * As these get more complex, they will be moved to the relevant files, + * but for now they are too simple to worry about. + */ +STATIC void +xfs_bmap_local_to_extents_init_fn( + struct xfs_buf *bp, + struct xfs_inode *ip, + struct xfs_ifork *ifp) +{ + bp->b_ops = &xfs_bmbt_buf_ops; + memcpy(bp->b_addr, ifp->if_u1.if_data, ifp->if_bytes); +} + +STATIC void +xfs_symlink_local_to_remote( + struct xfs_buf *bp, + struct xfs_inode *ip, + struct xfs_ifork *ifp) +{ + /* remote symlink blocks are not verifiable until CRCs come along */ + bp->b_ops = NULL; + memcpy(bp->b_addr, ifp->if_u1.if_data, ifp->if_bytes); +} + +/* + * Called from xfs_bmap_add_attrfork to handle local format files. Each + * different data fork content type needs a different callout to do the + * conversion. Some are basic and only require special block initialisation + * callouts for the data formating, others (directories) are so specialised they + * handle everything themselves. + * + * XXX (dgc): investigate whether directory conversion can use the generic + * formatting callout. It should be possible - it's just a very complex + * formatter. it would also require passing the transaction through to the init + * function. */ STATIC int /* error */ xfs_bmap_add_attrfork_local( @@ -368,25 +406,29 @@ xfs_bmap_add_attrfork_local( int *flags) /* inode logging flags */ { xfs_da_args_t dargs; /* args for dir/attr code */ - int error; /* error return value */ - xfs_mount_t *mp; /* mount structure pointer */ if (ip->i_df.if_bytes <= XFS_IFORK_DSIZE(ip)) return 0; + if (S_ISDIR(ip->i_d.di_mode)) { - mp = ip->i_mount; memset(&dargs, 0, sizeof(dargs)); dargs.dp = ip; dargs.firstblock = firstblock; dargs.flist = flist; - dargs.total = mp->m_dirblkfsbs; + dargs.total = ip->i_mount->m_dirblkfsbs; dargs.whichfork = XFS_DATA_FORK; dargs.trans = tp; - error = xfs_dir2_sf_to_block(&dargs); - } else - error = xfs_bmap_local_to_extents(tp, ip, firstblock, 1, flags, - XFS_DATA_FORK); - return error; + return xfs_dir2_sf_to_block(&dargs); + } + + if (S_ISLNK(ip->i_d.di_mode)) + return xfs_bmap_local_to_extents(tp, ip, firstblock, 1, + flags, XFS_DATA_FORK, + xfs_symlink_local_to_remote); + + return xfs_bmap_local_to_extents(tp, ip, firstblock, 1, flags, + XFS_DATA_FORK, + xfs_bmap_local_to_extents_init_fn); } /* @@ -3221,7 +3263,10 @@ xfs_bmap_local_to_extents( xfs_fsblock_t *firstblock, /* first block allocated in xaction */ xfs_extlen_t total, /* total blocks needed by transaction */ int *logflagsp, /* inode logging flags */ - int whichfork) /* data or attr fork */ + int whichfork, + void (*init_fn)(struct xfs_buf *bp, + struct xfs_inode *ip, + struct xfs_ifork *ifp)) { int error; /* error return value */ int flags; /* logging flags returned */ @@ -3241,12 +3286,12 @@ xfs_bmap_local_to_extents( xfs_buf_t *bp; /* buffer for extent block */ xfs_bmbt_rec_host_t *ep;/* extent record pointer */ + ASSERT((ifp->if_flags & + (XFS_IFINLINE|XFS_IFEXTENTS|XFS_IFEXTIREC)) == XFS_IFINLINE); memset(&args, 0, sizeof(args)); args.tp = tp; args.mp = ip->i_mount; args.firstblock = *firstblock; - ASSERT((ifp->if_flags & - (XFS_IFINLINE|XFS_IFEXTENTS|XFS_IFEXTIREC)) == XFS_IFINLINE); /* * Allocate a block. We know we need only one, since the * file currently fits in an inode. @@ -3262,17 +3307,20 @@ xfs_bmap_local_to_extents( args.mod = args.minleft = args.alignment = args.wasdel = args.isfl = args.minalignslop = 0; args.minlen = args.maxlen = args.prod = 1; - if ((error = xfs_alloc_vextent(&args))) + error = xfs_alloc_vextent(&args); + if (error) goto done; - /* - * Can't fail, the space was reserved. - */ + + /* Can't fail, the space was reserved. */ ASSERT(args.fsbno != NULLFSBLOCK); ASSERT(args.len == 1); *firstblock = args.fsbno; bp = xfs_btree_get_bufl(args.mp, tp, args.fsbno, 0); - bp->b_ops = &xfs_bmbt_buf_ops; - memcpy(bp->b_addr, ifp->if_u1.if_data, ifp->if_bytes); + + /* initialise the block and copy the data */ + init_fn(bp, ip, ifp); + + /* account for the change in fork size and log everything */ xfs_trans_log_buf(tp, bp, 0, ifp->if_bytes - 1); xfs_bmap_forkoff_reset(args.mp, ip, whichfork); xfs_idata_realloc(ip, -ifp->if_bytes, whichfork); @@ -4919,8 +4967,32 @@ xfs_bmapi_write( XFS_STATS_INC(xs_blk_mapw); if (XFS_IFORK_FORMAT(ip, whichfork) == XFS_DINODE_FMT_LOCAL) { + /* + * XXX (dgc): This assumes we are only called for inodes that + * contain content neutral data in local format. Anything that + * contains caller-specific data in local format that needs + * transformation to move to a block format needs to do the + * conversion to extent format itself. + * + * Directory data forks and attribute forks handle this + * themselves, but with the addition of metadata verifiers every + * data fork in local format now contains caller specific data + * and as such conversion through this function is likely to be + * broken. + * + * The only likely user of this branch is for remote symlinks, + * but we cannot overwrite the data fork contents of the symlink + * (EEXIST occurs higher up the stack) and so it will never go + * from local format to extent format here. Hence I don't think + * this branch is ever executed intentionally and we should + * consider removing it and asserting that xfs_bmapi_write() + * cannot be called directly on local format forks. i.e. callers + * are completely responsible for local to extent format + * conversion, not xfs_bmapi_write(). + */ error = xfs_bmap_local_to_extents(tp, ip, firstblock, total, - &bma.logflags, whichfork); + &bma.logflags, whichfork, + xfs_bmap_local_to_extents_init_fn); if (error) goto error0; } -- 1.7.12.4 From sandeen@sandeen.net Fri Mar 1 17:46:51 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 701027FF6 for ; Fri, 1 Mar 2013 17:46:51 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay3.corp.sgi.com (Postfix) with ESMTP id EFF6EAC002 for ; Fri, 1 Mar 2013 15:46:50 -0800 (PST) X-ASG-Debug-ID: 1362181609-04bdf0229869910001-NocioJ Received: from sandeen.net (sandeen.net [63.231.237.45]) by cuda.sgi.com with ESMTP id MB4SHYJnA1LcCmh8 for ; Fri, 01 Mar 2013 15:46:49 -0800 (PST) X-Barracuda-Envelope-From: sandeen@sandeen.net X-Barracuda-Apparent-Source-IP: 63.231.237.45 Received: from liberator.sandeen.net (liberator.sandeen.net [10.0.0.4]) (using TLSv1 with cipher DHE-RSA-CAMELLIA256-SHA (256/256 bits)) (No client certificate requested) by sandeen.net (Postfix) with ESMTPSA id 5C0BC63C5856; Fri, 1 Mar 2013 17:46:49 -0600 (CST) Message-ID: <51313DE8.5080104@sandeen.net> Date: Fri, 01 Mar 2013 17:46:48 -0600 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: xfs-oss CC: Ole Tange Subject: [PATCH] xfs_repair: skip freelist scan of dodgy agf in no-modify mode X-Enigmail-Version: 1.5 X-ASG-Orig-Subj: [PATCH] xfs_repair: skip freelist scan of dodgy agf in no-modify mode Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: sandeen.net[63.231.237.45] X-Barracuda-Start-Time: 1362181609 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.123987 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- In no-modify mode (-n), verify_set_agf doesn't fix up bad freelist blocks that it finds. When we get to scan_freelist, this can wreak havoc if, for example, first > last and the loop never exits; we index agfl->agfl_bno[i] off into the weeds. To fix this, re-check the values in no-modify mode, and if they're off, warn about it and skip the scan. In addition, add a check to verify_set_agf() to ensure that first <= last. Reported-by: Ole Tange Signed-off-by: Eric Sandeen --- diff --git a/repair/agheader.c b/repair/agheader.c index 769022d..68789fe 100644 --- a/repair/agheader.c +++ b/repair/agheader.c @@ -86,6 +86,14 @@ verify_set_agf(xfs_mount_t *mp, xfs_agf_t *agf, xfs_agnumber_t i) * check first/last AGF fields. if need be, lose the free * space in the AGFL, we'll reclaim it later. */ + if (be32_to_cpu(agf->agf_flfirst) > be32_to_cpu(agf->agf_fllast)) { + do_warn(_("flfirst %d in agf %d > fllast %d\n"), + be32_to_cpu(agf->agf_flfirst), + i, be32_to_cpu(agf->agf_fllast)); + if (!no_modify) + agf->agf_fllast = agf->agf_flfirst = cpu_to_be32(0); + } + if (be32_to_cpu(agf->agf_flfirst) >= XFS_AGFL_SIZE(mp)) { do_warn(_("flfirst %d in agf %d too large (max = %zu)\n"), be32_to_cpu(agf->agf_flfirst), diff --git a/repair/scan.c b/repair/scan.c index 5345094..0f83fb4 100644 --- a/repair/scan.c +++ b/repair/scan.c @@ -1067,6 +1067,17 @@ scan_freelist( } agfl = XFS_BUF_TO_AGFL(agflbuf); i = be32_to_cpu(agf->agf_flfirst); + if (no_modify) { + /* agf values not sanitized, so double check */ + if (i >= XFS_AGFL_SIZE(mp) || + be32_to_cpu(agf->agf_fllast) >= XFS_AGFL_SIZE(mp) || + i > be32_to_cpu(agf->agf_fllast)) + do_warn(_("agf %d freelist blocks bad, skipping scan\n"), + i); + return; + } else /* should have been fixed in verify_set_agf() */ + ASSERT(0); + count = 0; for (;;) { bno = be32_to_cpu(agfl->agfl_bno[i]); From greg@kroah.com Fri Mar 1 17:51:11 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=T_DKIM_INVALID autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 67CED7F60 for ; Fri, 1 Mar 2013 17:51:11 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay1.corp.sgi.com (Postfix) with ESMTP id 51D278F8052 for ; Fri, 1 Mar 2013 15:51:11 -0800 (PST) X-ASG-Debug-ID: 1362181869-04cb6c2b0167850001-NocioJ Received: from out1-smtp.messagingengine.com (out1-smtp.messagingengine.com [66.111.4.25]) by cuda.sgi.com with ESMTP id XKvgDujgx4RmTJDd (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO) for ; Fri, 01 Mar 2013 15:51:10 -0800 (PST) X-Barracuda-Envelope-From: greg@kroah.com X-Barracuda-Apparent-Source-IP: 66.111.4.25 Received: from compute1.internal (compute1.nyi.mail.srv.osa [10.202.2.41]) by gateway1.nyi.mail.srv.osa (Postfix) with ESMTP id B4E702064A; Fri, 1 Mar 2013 18:51:09 -0500 (EST) Received: from frontend2.nyi.mail.srv.osa ([10.202.2.161]) by compute1.internal (MEProxy); Fri, 01 Mar 2013 18:51:09 -0500 DKIM-Signature: v=1; a=rsa-sha1; c=relaxed/relaxed; d= messagingengine.com; h=date:from:to:cc:subject:message-id :references:mime-version:content-type:in-reply-to; s=smtpout; bh=5fzCFk5u2aZ68+7PiGONFkhaWiA=; b=I98EgEeb/MExDQTl8ciFB88Rzmli 4NnhbqnsbV5Y2sANyRNnhcQhnP5nmonpeetcdq2JReRid7yBEu0vfuf55KwmVDd2 5522MTz3Uqnfitwuel7Kc5UsYcUHsHHfKYtHEvpQ5hmnBK+kpLxrXRIfiPYmmrN6 wE5lp0lotgZ1FB8= X-Sasl-enc: iPR6xwMzmh4Y3fyuqtSslzbqFeak6Xrg5/j6M1ryrT5H 1362181869 Received: from localhost (unknown [76.28.172.123]) by mail.messagingengine.com (Postfix) with ESMTPA id 502AA201102; Fri, 1 Mar 2013 18:51:09 -0500 (EST) Date: Fri, 1 Mar 2013 15:51:08 -0800 From: Greg KH To: Ben Myers Cc: stable@vger.kernel.org, xfs@oss.sgi.com, dchinner@redhat.com Subject: Re: [STABLE] [PATCH] xfs: xfs_bmap_add_attrfork_local is too generic Message-ID: <20130301235108.GB11455@kroah.com> X-ASG-Orig-Subj: Re: [STABLE] [PATCH] xfs: xfs_bmap_add_attrfork_local is too generic References: <20130301232941.GJ30652@sgi.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <20130301232941.GJ30652@sgi.com> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: out1-smtp.messagingengine.com[66.111.4.25] X-Barracuda-Start-Time: 1362181870 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 2.60 X-Barracuda-Spam-Status: No, SCORE=2.60 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_MV0249, DKIM_SIGNED, DKIM_VERIFIED, MARKETING_SUBJECT X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.123989 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.60 MARKETING_SUBJECT Subject contains popular marketing words -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature 2.00 BSF_SC0_MV0249 Custom rule MV0249 On Fri, Mar 01, 2013 at 05:29:41PM -0600, Ben Myers wrote: > Hi, > > Please take this fix for 3.8-stable. It resolves a problem with write > verifiers and symlinks which results in a forced unmount. Now applied, I've snuck it into 3.8.2. greg k-h From sandeen@sandeen.net Fri Mar 1 17:56:00 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 7AF627FB3 for ; Fri, 1 Mar 2013 17:56:00 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay1.corp.sgi.com (Postfix) with ESMTP id 5536C8F8052 for ; Fri, 1 Mar 2013 15:56:00 -0800 (PST) X-ASG-Debug-ID: 1362182159-04bdf022986a030001-NocioJ Received: from sandeen.net (sandeen.net [63.231.237.45]) by cuda.sgi.com with ESMTP id brBq3HIFXnKh1Xib for ; Fri, 01 Mar 2013 15:55:59 -0800 (PST) X-Barracuda-Envelope-From: sandeen@sandeen.net X-Barracuda-Apparent-Source-IP: 63.231.237.45 Received: from liberator.sandeen.net (liberator.sandeen.net [10.0.0.4]) (using TLSv1 with cipher DHE-RSA-CAMELLIA256-SHA (256/256 bits)) (No client certificate requested) by sandeen.net (Postfix) with ESMTPSA id BF6F163C5856; Fri, 1 Mar 2013 17:55:58 -0600 (CST) Message-ID: <5131400E.5060207@sandeen.net> Date: Fri, 01 Mar 2013 17:55:58 -0600 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: Dave Chinner CC: xfs@oss.sgi.com, Ole Tange Subject: Re: xfs_repair segfaults References: <5131283F.8030704@sandeen.net> <20130301223116.GE23616@dastard> <51312C73.5060203@sandeen.net> X-ASG-Orig-Subj: Re: xfs_repair segfaults In-Reply-To: <51312C73.5060203@sandeen.net> X-Enigmail-Version: 1.5 Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: sandeen.net[63.231.237.45] X-Barracuda-Start-Time: 1362182159 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.123989 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On 3/1/13 4:32 PM, Eric Sandeen wrote: > Ole, you can xfs_mdrestore your metadump image and run test repairs on the result, If you like, test it after applying the patch I just sent. (or wait 'til it's reviewed) :) Anyway, running in non "-n" mode will avoid the segfault you reported. -Eric From bpm@sgi.com Fri Mar 1 17:56:42 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 6DE747FFE for ; Fri, 1 Mar 2013 17:56:42 -0600 (CST) Received: from whiskey.americas.sgi.com (eagdhcp-232-197.americas.sgi.com [128.162.232.197]) by relay3.corp.sgi.com (Postfix) with ESMTP id E011FAC008; Fri, 1 Mar 2013 15:56:41 -0800 (PST) Received: by whiskey.americas.sgi.com (Postfix, from userid 4600) id 98BC9500B4B; Fri, 1 Mar 2013 17:56:41 -0600 (CST) Date: Fri, 1 Mar 2013 17:56:41 -0600 From: Ben Myers To: Dave Chinner Cc: xfs@oss.sgi.com Subject: Re: [PATCH 05/16] xfs: add CRC checks to the AGFL Message-ID: <20130301235641.GE22182@sgi.com> References: <1361755901-12453-1-git-send-email-david@fromorbit.com> <1361755901-12453-6-git-send-email-david@fromorbit.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <1361755901-12453-6-git-send-email-david@fromorbit.com> User-Agent: Mutt/1.5.20 (2009-06-14) Hi Dave, On Mon, Feb 25, 2013 at 12:31:30PM +1100, Dave Chinner wrote: > From: Christoph Hellwig > > Add CRC checks, location information and a magic number to the AGFL. > Previously the AGFL was just a block containing nothing but the > free block pointers. The new AGFL has a real header with the usual > boilerplate instead, so that we can verify it's not corrupted and > written into the right place. > > [dchinner@redhat.com] Added LSN field, reworked significantly to fit > into new verifier structure and growfs structure, enabled full > verifier functionality now there is a header to verify and we can > guarantee an initialised AGFL. > > Signed-off-by: Christoph Hellwig > Signed-off-by: Dave Chinner > --- > fs/xfs/xfs_ag.h | 25 +++++++++- > fs/xfs/xfs_alloc.c | 119 ++++++++++++++++++++++++++++++---------------- > fs/xfs/xfs_buf_item.h | 4 +- > fs/xfs/xfs_fsops.c | 5 ++ > fs/xfs/xfs_log_recover.c | 10 ++++ > 5 files changed, 119 insertions(+), 44 deletions(-) > > diff --git a/fs/xfs/xfs_ag.h b/fs/xfs/xfs_ag.h > index 9f4815e..272ef09 100644 > --- a/fs/xfs/xfs_ag.h > +++ b/fs/xfs/xfs_ag.h > @@ -30,6 +30,7 @@ struct xfs_trans; > > #define XFS_AGF_MAGIC 0x58414746 /* 'XAGF' */ > #define XFS_AGI_MAGIC 0x58414749 /* 'XAGI' */ > +#define XFS_AGFL_MAGIC 0x5841464c /* 'XAFL' */ > #define XFS_AGF_VERSION 1 > #define XFS_AGI_VERSION 1 > > @@ -190,11 +191,31 @@ extern const struct xfs_buf_ops xfs_agi_buf_ops; > */ > #define XFS_AGFL_DADDR(mp) ((xfs_daddr_t)(3 << (mp)->m_sectbb_log)) > #define XFS_AGFL_BLOCK(mp) XFS_HDR_BLOCK(mp, XFS_AGFL_DADDR(mp)) > -#define XFS_AGFL_SIZE(mp) ((mp)->m_sb.sb_sectsize / sizeof(xfs_agblock_t)) > #define XFS_BUF_TO_AGFL(bp) ((xfs_agfl_t *)((bp)->b_addr)) > > +#define XFS_BUF_TO_AGFL_BNO(mp, bp) \ > + (xfs_sb_version_hascrc(&((mp)->m_sb)) ? \ > + &(XFS_BUF_TO_AGFL(bp)->agfl_bno[0]) : \ > + (__be32 *)(bp)->b_addr) > + > +/* > + * Size of the AGFL. For CRC-enabled filesystes we steal a couple of > + * slots in the beginning of the block for a proper header with the > + * location information and CRC. > + */ > +#define XFS_AGFL_SIZE(mp) \ > + (((mp)->m_sb.sb_sectsize - \ > + (xfs_sb_version_hascrc(&((mp)->m_sb)) ? \ > + sizeof(struct xfs_agfl) : 0)) / \ > + sizeof(xfs_agblock_t)) > + > typedef struct xfs_agfl { > - __be32 agfl_bno[1]; /* actually XFS_AGFL_SIZE(mp) */ > + __be32 agfl_magicnum; + __be32 agfl_versionnum; Now would be a good time to add this, and it would be consistent with the AGF and AGI structures. There is no shortage of agfl slots according to my calculation, and this might be helpful for xfsrepair later. -Ben > + __be32 agfl_seqno; > + uuid_t agfl_uuid; > + __be64 agfl_lsn; > + __be32 agfl_crc; > + __be32 agfl_bno[]; /* actually XFS_AGFL_SIZE(mp) */ > } xfs_agfl_t; From david@fromorbit.com Fri Mar 1 19:18:18 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id A19D57FF6 for ; Fri, 1 Mar 2013 19:18:18 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay3.corp.sgi.com (Postfix) with ESMTP id 14C9AAC001 for ; Fri, 1 Mar 2013 17:18:14 -0800 (PST) X-ASG-Debug-ID: 1362187089-04cb6c2b026c2c0001-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id VuTzgb2jElTefWl2 for ; Fri, 01 Mar 2013 17:18:10 -0800 (PST) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AhwOAFRSMVF5LOvW/2dsb2JhbABEhWa3QYUZfxdzgh8BAQUnExwjEAgDGAklDwUlAyETiBLBDhWOKSI9B4JfYQOWQolkhwiDHA Received: from ppp121-44-235-214.lns20.syd7.internode.on.net (HELO dastard) ([121.44.235.214]) by ipmail05.adl6.internode.on.net with ESMTP; 02 Mar 2013 11:48:08 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UBb5S-0008Dm-VS; Sat, 02 Mar 2013 12:18:07 +1100 Date: Sat, 2 Mar 2013 12:18:06 +1100 From: Dave Chinner To: Eric Sandeen Cc: xfs-oss , Ole Tange Subject: Re: [PATCH] xfs_repair: skip freelist scan of dodgy agf in no-modify mode Message-ID: <20130302011806.GF23616@dastard> X-ASG-Orig-Subj: Re: [PATCH] xfs_repair: skip freelist scan of dodgy agf in no-modify mode References: <51313DE8.5080104@sandeen.net> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <51313DE8.5080104@sandeen.net> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1362187089 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.123995 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Fri, Mar 01, 2013 at 05:46:48PM -0600, Eric Sandeen wrote: > In no-modify mode (-n), verify_set_agf doesn't fix up bad > freelist blocks that it finds. When we get to scan_freelist, > this can wreak havoc if, for example, first > last and the loop > never exits; we index agfl->agfl_bno[i] off into the weeds. > > To fix this, re-check the values in no-modify mode, and if > they're off, warn about it and skip the scan. > > In addition, add a check to verify_set_agf() to ensure that > first <= last. > > Reported-by: Ole Tange > Signed-off-by: Eric Sandeen > --- > > diff --git a/repair/agheader.c b/repair/agheader.c > index 769022d..68789fe 100644 > --- a/repair/agheader.c > +++ b/repair/agheader.c > @@ -86,6 +86,14 @@ verify_set_agf(xfs_mount_t *mp, xfs_agf_t *agf, xfs_agnumber_t i) > * check first/last AGF fields. if need be, lose the free > * space in the AGFL, we'll reclaim it later. > */ > + if (be32_to_cpu(agf->agf_flfirst) > be32_to_cpu(agf->agf_fllast)) { > + do_warn(_("flfirst %d in agf %d > fllast %d\n"), > + be32_to_cpu(agf->agf_flfirst), > + i, be32_to_cpu(agf->agf_fllast)); > + if (!no_modify) > + agf->agf_fllast = agf->agf_flfirst = cpu_to_be32(0); > + } I don't think that test is correct. The free list is circular and is indexed as a pair of head/tail pointers. Hence flfirst > fllast can be actually valid. e.g. flcount = 4, flfirst=126, fllast = 2 is a valid free list. > + > if (be32_to_cpu(agf->agf_flfirst) >= XFS_AGFL_SIZE(mp)) { > do_warn(_("flfirst %d in agf %d too large (max = %zu)\n"), > be32_to_cpu(agf->agf_flfirst), > diff --git a/repair/scan.c b/repair/scan.c > index 5345094..0f83fb4 100644 > --- a/repair/scan.c > +++ b/repair/scan.c > @@ -1067,6 +1067,17 @@ scan_freelist( > } > agfl = XFS_BUF_TO_AGFL(agflbuf); > i = be32_to_cpu(agf->agf_flfirst); > + if (no_modify) { > + /* agf values not sanitized, so double check */ > + if (i >= XFS_AGFL_SIZE(mp) || > + be32_to_cpu(agf->agf_fllast) >= XFS_AGFL_SIZE(mp) || > + i > be32_to_cpu(agf->agf_fllast)) > + do_warn(_("agf %d freelist blocks bad, skipping scan\n"), "skipping freelist scan" > + i); > + return; Also, you might be missing a set of {} there - that will always return immediately if no_modify is set.... Cheers, Dave. -- Dave Chinner david@fromorbit.com From sandeen@sandeen.net Fri Mar 1 19:30:37 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=MIME_QP_LONG_LINE autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 3310E7FF6 for ; Fri, 1 Mar 2013 19:30:37 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay3.corp.sgi.com (Postfix) with ESMTP id 93E6CAC001 for ; Fri, 1 Mar 2013 17:30:36 -0800 (PST) X-ASG-Debug-ID: 1362187835-04cb6c2b036cd10001-NocioJ Received: from sandeen.net (sandeen.net [63.231.237.45]) by cuda.sgi.com with ESMTP id qSR5uQwHS1RGvqMH for ; Fri, 01 Mar 2013 17:30:35 -0800 (PST) X-Barracuda-Envelope-From: sandeen@sandeen.net X-Barracuda-Apparent-Source-IP: 63.231.237.45 Received: from [10.170.226.67] (mobile-198-228-232-010.mycingular.net [198.228.232.10]) (using TLSv1 with cipher AES128-SHA (128/128 bits)) (No client certificate requested) by sandeen.net (Postfix) with ESMTPSA id 6426163C59BB; Fri, 1 Mar 2013 19:30:34 -0600 (CST) Content-Type: text/plain; charset=us-ascii Content-Transfer-Encoding: quoted-printable Subject: Re: [PATCH] xfs_repair: skip freelist scan of dodgy agf in no-modify mode References: <51313DE8.5080104@sandeen.net> <20130302011806.GF23616@dastard> X-ASG-Orig-Subj: Re: [PATCH] xfs_repair: skip freelist scan of dodgy agf in no-modify mode From: Eric Sandeen Mime-Version: 1.0 (1.0) In-Reply-To: <20130302011806.GF23616@dastard> Message-Id: <734EB96C-D92F-4F17-BF1A-056FAE063874@sandeen.net> Date: Fri, 1 Mar 2013 19:22:28 -0600 Cc: xfs-oss , Ole Tange To: Dave Chinner X-Mailer: iPhone Mail (10A523) X-Barracuda-Connect: sandeen.net[63.231.237.45] X-Barracuda-Start-Time: 1362187835 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.82 X-Barracuda-Spam-Status: No, SCORE=0.82 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=MIME_QP_LONG_LINE, MIME_QP_LONG_LINE_2 X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.123995 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 MIME_QP_LONG_LINE RAW: Quoted-printable line longer than 76 chars 0.82 MIME_QP_LONG_LINE_2 RAW: Quoted-printable line longer than 76 chars On Mar 1, 2013, at 7:18 PM, Dave Chinner wrote: > On Fri, Mar 01, 2013 at 05:46:48PM -0600, Eric Sandeen wrote: >> In no-modify mode (-n), verify_set_agf doesn't fix up bad >> freelist blocks that it finds. When we get to scan_freelist, >> this can wreak havoc if, for example, first > last and the loop >> never exits; we index agfl->agfl_bno[i] off into the weeds. >>=20 >> To fix this, re-check the values in no-modify mode, and if >> they're off, warn about it and skip the scan. >>=20 >> In addition, add a check to verify_set_agf() to ensure that >> first <=3D last. >>=20 >> Reported-by: Ole Tange >> Signed-off-by: Eric Sandeen >> --- >>=20 >> diff --git a/repair/agheader.c b/repair/agheader.c >> index 769022d..68789fe 100644 >> --- a/repair/agheader.c >> +++ b/repair/agheader.c >> @@ -86,6 +86,14 @@ verify_set_agf(xfs_mount_t *mp, xfs_agf_t *agf, xfs_ag= number_t i) >> * check first/last AGF fields. if need be, lose the free >> * space in the AGFL, we'll reclaim it later. >> */ >> + if (be32_to_cpu(agf->agf_flfirst) > be32_to_cpu(agf->agf_fllast)) { >> + do_warn(_("flfirst %d in agf %d > fllast %d\n"), >> + be32_to_cpu(agf->agf_flfirst), >> + i, be32_to_cpu(agf->agf_fllast)); >> + if (!no_modify) >> + agf->agf_fllast =3D agf->agf_flfirst =3D cpu_to_be32(0); >> + } >=20 > I don't think that test is correct. The free list is circular and is > indexed as a pair of head/tail pointers. Hence flfirst > fllast can > be actually valid. e.g. flcount =3D 4, flfirst=3D126, fllast =3D 2 is a > valid free list. >=20 Doh, ok. Will fix. >> + >> if (be32_to_cpu(agf->agf_flfirst) >=3D XFS_AGFL_SIZE(mp)) { >> do_warn(_("flfirst %d in agf %d too large (max =3D %zu)\n"), >> be32_to_cpu(agf->agf_flfirst), >> diff --git a/repair/scan.c b/repair/scan.c >> index 5345094..0f83fb4 100644 >> --- a/repair/scan.c >> +++ b/repair/scan.c >> @@ -1067,6 +1067,17 @@ scan_freelist( >> } >> agfl =3D XFS_BUF_TO_AGFL(agflbuf); >> i =3D be32_to_cpu(agf->agf_flfirst); >> + if (no_modify) { >> + /* agf values not sanitized, so double check */ >> + if (i >=3D XFS_AGFL_SIZE(mp) || >> + be32_to_cpu(agf->agf_fllast) >=3D XFS_AGFL_SIZE(mp) || >> + i > be32_to_cpu(agf->agf_fllast)) >> + do_warn(_("agf %d freelist blocks bad, skipping scan\n"), >=20 > "skipping freelist scan" >=20 >> + i); >> + return; >=20 > Also, you might be missing a set of {} there - that will always > return immediately if no_modify is set.... >=20 Cripes. 1 demerit for me, sorry. Will fix and resend. Thanks for the embarrassing review. :) -Eric > Cheers, >=20 > Dave. > --=20 > Dave Chinner > david@fromorbit.com >=20 From rjevskiy@gmail.com Fri Mar 1 19:30:51 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=FREEMAIL_FROM,T_DKIM_INVALID autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id AD0237F63 for ; Fri, 1 Mar 2013 19:30:51 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay3.corp.sgi.com (Postfix) with ESMTP id 1F1D4AC001 for ; Fri, 1 Mar 2013 17:30:51 -0800 (PST) X-ASG-Debug-ID: 1362187848-04cb6c2b036cd20001-NocioJ Received: from mail-la0-f47.google.com (mail-la0-f47.google.com [209.85.215.47]) by cuda.sgi.com with ESMTP id tCSH82PqUktUOjpT (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Fri, 01 Mar 2013 17:30:49 -0800 (PST) X-Barracuda-Envelope-From: rjevskiy@gmail.com X-Barracuda-Apparent-Source-IP: 209.85.215.47 X-Barracuda-IPDD: Level1 [gmail.com/209.85.215.47] Received: by mail-la0-f47.google.com with SMTP id fj20so3470606lab.20 for ; Fri, 01 Mar 2013 17:30:47 -0800 (PST) X-Barracuda-IPDD: Level1 [gmail.com/209.85.215.47] X-Barracuda-IPDD: Level1 [gmail.com/209.85.215.47] DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20120113; h=x-received:sender:from:to:cc:subject:in-reply-to:references :user-agent:date:message-id:mime-version:content-type; bh=rAnlwywUBdaidJZfgdc380R8YIPKVeddCqbqzXy7LpU=; b=iQ6UCxH4q3YUk3I2kvlOv6lM+mvRtxr5v136dm2LcA571dHIKCJj4zOLda0VxlMvKd wqtzgg8gUnPzLB0y7Revo+6WDqIgrD3F4ITw3R1+MezQXhcS5m/2n7gn0ARAazJ4l4r4 mrSqSiwLc1VM42o/nY7QU7tG5QtsIXSYiWPoVujqEtZ8ZtEU9cUNev+KA9YdbxLYyqko gP5Gh/fap7xy98hGBNoIyOeHrWD84pGuawDbpd9yGnb+W2RXJ8Pn9MofiTKEFupYaHG0 ERHK//xGgNVD5U6D9E1dJRcusz2iM9WyqfjiMrMX/ZxwTT8GyMrucaZ5wSOuXjY7tBdT C7zw== X-Received: by 10.152.132.170 with SMTP id ov10mr10785941lab.21.1362187847675; Fri, 01 Mar 2013 17:30:47 -0800 (PST) Received: from smtp.gmail.com (swsoft-msk-nat.sw.ru. [195.214.232.10]) by mx.google.com with ESMTPS id v7sm4674372lbg.13.2013.03.01.17.30.45 (version=TLSv1.2 cipher=RC4-SHA bits=128/128); Fri, 01 Mar 2013 17:30:45 -0800 (PST) Sender: Dmitry Monakhov From: Dmitry Monakhov To: Rich Johnston Cc: xfs@oss.sgi.com, linux-fsdevel@vger.kernel.org, linux-ext4@vger.kernel.org, dchinner@redhat.com Subject: Re: [PATCH 09/10] xfstest: add defragmentation stress tests for ext4 In-Reply-To: <51310046.5090306@sgi.com> X-ASG-Orig-Subj: Re: [PATCH 09/10] xfstest: add defragmentation stress tests for ext4 References: <1361356935-29153-1-git-send-email-dmonakhov@openvz.org> <1361356935-29153-10-git-send-email-dmonakhov@openvz.org> <51310046.5090306@sgi.com> User-Agent: Notmuch/0.6.1 (http://notmuchmail.org) Emacs/23.3.1 (x86_64-redhat-linux-gnu) Date: Sat, 02 Mar 2013 05:30:43 +0400 Message-ID: <878v66h9ks.fsf@openvz.org> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii X-Barracuda-Connect: mail-la0-f47.google.com[209.85.215.47] X-Barracuda-Start-Time: 1362187848 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=DKIM_SIGNED, DKIM_VERIFIED X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.123995 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature On Fri, 1 Mar 2013 13:23:50 -0600, Rich Johnston wrote: > On 02/20/2013 04:42 AM, Dmitry Monakhov wrote: > > Perform various regression tests for ext4defrag subsystem > > > > 299'th Test1: Defragment file while other task does direct AIO > > 300'th Test2: Perform defragmentation on file under buffered AIO > > while third task does direct AIO to donor file > > 301'th Test3: Two defrag tasks use common donor file. > > 302'th Test4: Stress defragmentation. Several threads pefrorm > typo perform > > > fragmentation at random position use inplace=1 will > > allocate and free blocks inside defrag event improve > > load pressure. > > > > This tests are considered dengerous because 300'th and 301'th are known > typo dangerous > > > to trigger OOPS on recent kernels see:https://gist.github.com/dmonakhov/4770294 > > > > Signed-off-by: Dmitry Monakhov > > --- > > 299 | 126 +++++++++++++++++++++++++++++++++++++++++++++++ > > 299.out | 4 ++ > > 300 | 143 +++++++++++++++++++++++++++++++++++++++++++++++++++++ > > 300.out | 4 ++ > > 301 | 153 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++ > > 301.out | 4 ++ > > 302 | 130 ++++++++++++++++++++++++++++++++++++++++++++++++ > > 302.out | 4 ++ > > common.defrag | 4 +- > > group | 6 ++- > > 10 files changed, 575 insertions(+), 3 deletions(-) > > create mode 100755 299 > > create mode 100644 299.out > > create mode 100755 300 > > create mode 100644 300.out > > create mode 100755 301 > > create mode 100644 301.out > > create mode 100755 302 > > create mode 100644 302.out > > > > diff --git a/299 b/299 > > new file mode 100755 > > index 0000000..4a7a98c > > --- /dev/null > > +++ b/299 > > @@ -0,0 +1,126 @@ > > +#! /bin/bash > > +# FSQA Test No. 299 > > +# > > +# Ext4 defragmentation stress test > > +# Defragment file while other task does direct io > > +#----------------------------------------------------------------------- > > +# (c) 2013 Dmitry Monakhov > > +# > > +# This program is free software; you can redistribute it and/or > > +# modify it under the terms of the GNU General Public License as > > +# published by the Free Software Foundation. > > +# > > +# This program is distributed in the hope that it would be useful, > > +# but WITHOUT ANY WARRANTY; without even the implied warranty of > > +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the > > +# GNU General Public License for more details. > > +# > > +# You should have received a copy of the GNU General Public License > > +# along with this program; if not, write the Free Software Foundation, > > +# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA > > +# > > +#----------------------------------------------------------------------- > > +# > > +# creator > > +owner=dmonakhov@openvz.org > > + > > +seq=`basename $0` > > +echo "QA output created by $seq" > > + > > +here=`pwd` > > +tmp=/tmp/$$ > > +status=1 # failure is the default! > > +trap "rm -f $tmp.*; exit \$status" 0 1 2 3 15 > > + > > +# get standard environment, filters and checks > > +. ./common.rc > > +. ./common.filter > > +. ./common.defrag > > + > > +# real QA test starts here > > +_supported_os Linux > > +_supported_fs ext4 > > +_need_to_be_root > > +_require_scratch > > +_require_defrag > > + > I think you meant to set NUM_JOBS here like you did in [Patch 08/10], > something like: > > +NUM_JOBS=$((4*LOAD_FACTOR)) Indeed. I've forget to update patch. > > otherwise you get > > ### [not run] /usr/local/bin/fio too old > > > +BLK_DEV_SIZE=`blockdev --getsz $SCRATCH_DEV` > > +# We need space for 2 files (test file, and donor one) > > +# reserve 30% in order to avoid ENOSPC > > +FILE_SIZE=$((BLK_DEV_SIZE * (512 / (2 + 1)))) > > + > > +cat >$tmp-$seq.fio < > +# Common e4defrag regression tests > > +[global] > > +ioengine=ioe_e4defrag > > +iodepth=1 > > +directory=${SCRATCH_MNT} > > +filesize=${FILE_SIZE} > > +size=999G > > +buffered=0 > > +fadvise_hint=0 > > +group_reporting > > + > > +################################# > > +# Test1 > > +# Defragment file while other task does direct io > > + > > +# Continious sequential defrag activity > > +[defrag-4k] > > +ioengine=e4defrag > > +iodepth=1 > > +bs=128k > > +donorname=test1.def > > +filename=test1 > > +inplace=0 > > +rw=write > > +numjobs=${NUM_JOBS} > > +runtime=30*${TIME_FACTOR} > > +time_based > > + > > +# Verifier > > +[aio-dio-verifier] > > +ioengine=libaio > > +iodepth=128*${LOAD_FACTOR} > > +numjobs=1 > > +verify=crc32c-intel > > +verify_fatal=1 > > +verify_dump=1 > > +verify_backlog=1024 > > +verify_async=1 > > +verifysort=1 > > +direct=1 > > +bs=64k > > +rw=randwrite > > +filename=test1 > > +runtime=30*${TIME_FACTOR} > > +time_based > > +EOF > > + > > +_workout() > > +{ > > + echo "" > > + echo " Start defragment activity " > git does not like trailing whitespace ^ > (same for the other 3 tests) > > + echo "" > > + cat $tmp-$seq.fio >> $seq.full > > + run_check $FIO_PROG $tmp-$seq.fio > > +} > > + > > +_require_fio $tmp-$seq.fio > > + > > +_scratch_mkfs >> $seq.full 2>&1 > > +_scratch_mount > > + > > +if ! _workout; then > > + umount $SCRATCH_DEV 2>/dev/null > > + exit > > +fi > > + > > +if ! _scratch_unmount; then > > + echo "failed to umount" > > + status=1 > > + exit > > +fi > > +_check_scratch_fs > > +status=$? > > +exit diff --git a/299.out b/299.out new file mode 100644 index 0000000..b215a3f > > diff --git a/299.out b/299.out > > new file mode 100644 > > index 0000000..c2b0b4c > > --- /dev/null > > +++ b/299.out > > @@ -0,0 +1,4 @@ > > +QA output created by 299 > > + > > + Start defragment activity > remove trailing whitespace ^ > (same for the other 3 tests) > > Let me know if you agree with these changes and I will make them at > commit time. Yes, please do. > > Thanks > --Rich > > -- > To unsubscribe from this list: send the line "unsubscribe linux-fsdevel" in > the body of a message to majordomo@vger.kernel.org > More majordomo info at http://vger.kernel.org/majordomo-info.html From rjevskiy@gmail.com Fri Mar 1 19:49:16 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=FREEMAIL_FROM,T_DKIM_INVALID autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 646717FF6 for ; Fri, 1 Mar 2013 19:49:16 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id 4B30C304032 for ; Fri, 1 Mar 2013 17:49:13 -0800 (PST) X-ASG-Debug-ID: 1362188950-04cbb07dbd6c100001-NocioJ Received: from mail-lb0-f177.google.com (mail-lb0-f177.google.com [209.85.217.177]) by cuda.sgi.com with ESMTP id SIrKRx3GUjef5CKZ (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Fri, 01 Mar 2013 17:49:11 -0800 (PST) X-Barracuda-Envelope-From: rjevskiy@gmail.com X-Barracuda-Apparent-Source-IP: 209.85.217.177 X-Barracuda-IPDD: Level1 [gmail.com/209.85.217.177] Received: by mail-lb0-f177.google.com with SMTP id go11so2635803lbb.8 for ; Fri, 01 Mar 2013 17:49:10 -0800 (PST) X-Barracuda-IPDD: Level1 [gmail.com/209.85.217.177] X-Barracuda-IPDD: Level1 [gmail.com/209.85.217.177] DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20120113; h=x-received:sender:from:to:cc:subject:in-reply-to:references :user-agent:date:message-id:mime-version:content-type; bh=tTKkAvAp6uuQgPU0mzLDA6RLGbSoWJpPQeknWwNHAUk=; b=JGiwlg4VU+RvRiEbzMFs3LYx/DW+4ZRCCO6O1aKHZCCPyWABe+oCP0Dwp1WOK4DBdd P0YuyHzCwrOTrq2OztUMM6ZQNMPM6Enbow0dq8/drlr2jxrLH9fOdMR3yEJ58GbbOB9l MaEY5lGotuCk5p/RrUgaLZi5QTfghSnrMgaCWpe1o7JAfY03muAFcxw+JHN/6NqEgPXJ 2f/sHxzClYQ0ST0pf4Rah7YEZ5P0Y0TT/CTxzBdbUiWsSxNbrnINYClEfKilkJUBAy/J 9mvxl1p7XEiKoMgFm5IHKHX5OJqgXYZqW9aUQt8xGlQvzfQhXscs475oA+Ygo/TvdCLY gtnw== X-Received: by 10.152.125.239 with SMTP id mt15mr10882294lab.26.1362188950419; Fri, 01 Mar 2013 17:49:10 -0800 (PST) Received: from smtp.gmail.com (swsoft-msk-nat.sw.ru. [195.214.232.10]) by mx.google.com with ESMTPS id pk1sm7591961lab.0.2013.03.01.17.49.08 (version=TLSv1.2 cipher=RC4-SHA bits=128/128); Fri, 01 Mar 2013 17:49:09 -0800 (PST) Sender: Dmitry Monakhov From: Dmitry Monakhov To: Rich Johnston Cc: xfs@oss.sgi.com, linux-fsdevel@vger.kernel.org, linux-ext4@vger.kernel.org, dchinner@redhat.com Subject: Re: [PATCH 10/10] xfstests: add disk failure simulation test In-Reply-To: <51310B63.4070105@sgi.com> X-ASG-Orig-Subj: Re: [PATCH 10/10] xfstests: add disk failure simulation test References: <1361356935-29153-1-git-send-email-dmonakhov@openvz.org> <1361356935-29153-11-git-send-email-dmonakhov@openvz.org> <51310B63.4070105@sgi.com> User-Agent: Notmuch/0.6.1 (http://notmuchmail.org) Emacs/23.3.1 (x86_64-redhat-linux-gnu) Date: Sat, 02 Mar 2013 05:49:07 +0400 Message-ID: <87621ah8q4.fsf@openvz.org> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii X-Barracuda-Connect: mail-lb0-f177.google.com[209.85.217.177] X-Barracuda-Start-Time: 1362188951 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=DKIM_SIGNED, DKIM_VERIFIED X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.123997 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature On Fri, 1 Mar 2013 14:11:15 -0600, Rich Johnston wrote: > On 02/20/2013 04:42 AM, Dmitry Monakhov wrote: > > There are many situations where disk may fail for example > > 1) brutal usb dongle unplug > > 2) iscsi (or any other netbdev) failure due to network issues > > In this situation filesystem which use this blockdevice is > > expected to fail(force RO remount, abort, etc) but whole system > > should still be operational. In other words: > > 1) Kernel should not panic > > 2) Memory should not leak > > 3) Data integrity operations (sync,fsync,fdatasync, directio) should fail > > for affected filesystem > > 4) It should be possible to umount broken filesystem > > > > Later when disk becomes available again we expect(only for journaled filesystems): > > 5) It will be possible to mount filesystem w/o explicit fsck (in order to caught > > typo s/caught/catch/g > > > issues like https://patchwork.kernel.org/patch/1983981/) > > 6) Filesystem should be operational > > 7) After mount/umount has being done all errors should be fixed so fsck should > > not spot any issues. > > > > This test use fault enjection (CONFIG_FAIL_MAKE_REQUEST=y config option ) > May want to mention all the kernel config options required. > i.e. CONFIG_FAULT_INJECTION=y ... are there others? > CONFIG_FAULT_INJECTION_DEBUG_FS=y ??? Yes, all three options are required. > > > which force all new IO requests to fail for a given device. Xfs already has > to force > > > XFS_IOC_GOINGDOWN ioctl which provides similar behaviour, but it is fs speciffic > > typos s/behaviour/behavior/g s/speciffic/specific > > and it does it in an easy way > because it perform freeze_bdev() before actual > > shotdown. > typo s/shotdown/shutdown/g Agree with your diagnosis. My gramma is bad and I've forget to call spell check before submission. Should I resend this one or you fix it manually on commit time? > > > > > Test run fsstress in background and then force disk failure. > > Once disk failed it check that (1)-(4) is true. > Once the disk fails, check that (1)-(4) are true. > > > Then makes disk available again and check that (5)-(7) is also true > make the disk ... are > > > > BE CAREFUL!! test known to cause memory corruption for XFS > > see: https://gist.github.com/dmonakhov/4953045 > > > > > > > -- > To unsubscribe from this list: send the line "unsubscribe linux-ext4" in > the body of a message to majordomo@vger.kernel.org > More majordomo info at http://vger.kernel.org/majordomo-info.html From usmyusuf5@gmail.com Sat Mar 2 06:50:39 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: **** X-Spam-Status: No, score=4.3 required=5.0 tests=FREEMAIL_ENVFROM_END_DIGIT, FREEMAIL_FROM,HTML_FONT_FACE_BAD,HTML_MESSAGE,LOTS_OF_MONEY,MONEY_FORM_SHORT, T_DKIM_INVALID,T_FILL_THIS_FORM_SHORT autolearn=no version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 515DD8006 for ; Sat, 2 Mar 2013 06:50:39 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay3.corp.sgi.com (Postfix) with ESMTP id AB331AC001 for ; Sat, 2 Mar 2013 04:50:38 -0800 (PST) X-ASG-Debug-ID: 1362228636-04cbb07dbd8eed0001-NocioJ Received: from mail-la0-f54.google.com (mail-la0-f54.google.com [209.85.215.54]) by cuda.sgi.com with ESMTP id hM25wwmv2MDWlMpA (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Sat, 02 Mar 2013 04:50:37 -0800 (PST) X-Barracuda-Envelope-From: usmyusuf5@gmail.com X-Barracuda-Apparent-Source-IP: 209.85.215.54 X-Barracuda-IPDD: Level1 [gmail.com/209.85.215.54] Received: by mail-la0-f54.google.com with SMTP id gw10so3777141lab.13 for ; Sat, 02 Mar 2013 04:50:35 -0800 (PST) X-Barracuda-IPDD: Level1 [gmail.com/209.85.215.54] X-Barracuda-IPDD: Level1 [gmail.com/209.85.215.54] DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20120113; h=mime-version:x-received:date:message-id:subject:from:to :content-type; bh=bV2i5G/3rngJA4d+WSZy1y3FSxcATblwBwxruBLOMMA=; b=FS0PXYydsGJc7PMC9e8bIQFgvM2w/niiD5WNo6vQmjtYtnUY+t3MLDIAJ3MrRzbEHw n1QJvPIjn/1IW2ka/aSf0o0wsT1eMBvRr002miOKgOqUjiiNcq408yN5xsm7Vi2IHIvt GAf2oSbushK4y9GaUQQa9zj083A44kQaFDFWPkT8Zqcdfqki1WubsL1xT/PuQbhO9rW0 iZ7wBDzRn6nUmwuHNppa9G5+7YX1UzagBUalSmkCTZ4KmAbBe5BfIOfBFi6GjRJQyekk 01oOiEoRQAP1VnZs2o9DW9KjfK1cCBUSoyS+a7xUH6gzooSPBZvXD8zXdEJb1IN7ux7H Iq3w== MIME-Version: 1.0 X-Received: by 10.112.88.72 with SMTP id be8mr2043995lbb.116.1362228635840; Sat, 02 Mar 2013 04:50:35 -0800 (PST) Received: by 10.112.14.41 with HTTP; Sat, 2 Mar 2013 04:50:35 -0800 (PST) Date: Sat, 2 Mar 2013 04:50:35 -0800 Message-ID: Subject: settlement info, From: Usman yusuf X-ASG-Orig-Subj: settlement info, To: undisclosed-recipients:; Content-Type: multipart/alternative; boundary=bcaec554da74f13ea304d6f091ea X-Barracuda-Connect: mail-la0-f54.google.com[209.85.215.54] X-Barracuda-Start-Time: 1362228636 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.61 X-Barracuda-Spam-Status: No, SCORE=0.61 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=DKIM_SIGNED, DKIM_VERIFIED, HTML_FONT_FACE_BAD, HTML_MESSAGE X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124040 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature 0.00 HTML_MESSAGE BODY: HTML included in message 0.61 HTML_FONT_FACE_BAD BODY: HTML font face is not a word --bcaec554da74f13ea304d6f091ea Content-Type: text/plain; charset=ISO-8859-1 *Sir* * * *I wish to inform you that your contract payment has been approved under category (C) you shall receive your payment under Federal Ministry of health.* * * *US$4.2m shall be paid to you as part payment; you are advised to confirm your contact address/telephone number for an immediate payment.* * * * * *Thank you,* *Usman Yusuf* *DEBT MANAGEMENT OFFICE* --bcaec554da74f13ea304d6f091ea Content-Type: text/html; charset=ISO-8859-1 Content-Transfer-Encoding: quoted-printable
I = wish to inform you that your contract payment has been approved under categ= ory (C) you shall receive your payment under Federal Ministry of health.

US$4.2m shall b= e paid to you as part payment; you are advised to confirm your contact addr= ess/telephone number for an immediate payment.
=A0
Thank you,
Usman Yusuf
= DEBT MANAGEMENT OFFICE
--bcaec554da74f13ea304d6f091ea-- From tinguely@sgi.com Sat Mar 2 14:20:09 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id F268B8006 for ; Sat, 2 Mar 2013 14:20:08 -0600 (CST) Received: from eagdhcp-232-136.americas.sgi.com (eagdhcp-232-136.americas.sgi.com [128.162.232.136]) by relay2.corp.sgi.com (Postfix) with ESMTP id CDE48304059 for ; Sat, 2 Mar 2013 12:20:05 -0800 (PST) Received: from eagdhcp-232-136.americas.sgi.com (localhost [127.0.0.1]) by eagdhcp-232-136.americas.sgi.com (8.14.5/8.14.5) with ESMTP id r22KK6GY002665 for ; Sat, 2 Mar 2013 14:20:06 -0600 (CST) (envelope-from tinguely@sgi.com) Received: (from tinguely@localhost) by eagdhcp-232-136.americas.sgi.com (8.14.5/8.14.5/Submit) id r22KK5ts002664; Sat, 2 Mar 2013 14:20:05 -0600 (CST) (envelope-from tinguely@sgi.com) X-Authentication-Warning: eagdhcp-232-136.americas.sgi.com: tinguely set sender to tinguely@sgi.com using -f Message-Id: <20130302201452.236378200@sgi.com> User-Agent: quilt/0.51-1 Date: Sat, 02 Mar 2013 14:14:47 -0600 From: Mark Tinguely To: xfs@oss.sgi.com Subject: [PATCH] xfs: logsunit rounding causes iclog corruption/crash References: <20130302201446.854313570@sgi.com> Content-Disposition: inline; filename=xfs-limit-round-log-buffer-size-to-lsunit.patch When the iclog buffer size and log stripe unit are both defined and the log stripe unit is less the log buffer size then the buffer is rounded up to the log stripe unit size during the xlog_sync(). This rounding can exceed the iclog buffer length and in xlog_data_pack(): 1) Cause corruption inside the iclog buffer because there will not be enough space for the headers in the front of the iclog buffer for the rounding. 2) Cause corruption in memory that follows the iclog buffer when stamping the lsn in each of the rounded blocks. 3) If CONFIG_XFS_DEBUG is defined will cause a crash in xlog_verify_iclog(). 4) Cause page fault crash if the memory after the buffer is not mapped. This has been found in XFS versions at least as far back as Linux 2.6.32. This patch forces the iclog buffer to be a multiple of the log stripe unit when they are both defined. Example: # mkfs.xfs -l su=192k -f /dev/sda2 # mount -o logbsize=256k /dev/sda3 /scratch # io such as fsstress in /scratch will immediately crash a debug xfs kernel and most like a non-debug xfs kernel. Signed-off-by: Mark Tinguely --- fs/xfs/xfs_super.c | 20 ++++++++++++++++---- 1 file changed, 16 insertions(+), 4 deletions(-) Index: b/fs/xfs/xfs_super.c =================================================================== --- a/fs/xfs/xfs_super.c +++ b/fs/xfs/xfs_super.c @@ -1357,11 +1357,23 @@ xfs_finish_flags( if (mp->m_logbsize <= 0 && mp->m_sb.sb_logsunit > XLOG_BIG_RECORD_BSIZE) { mp->m_logbsize = mp->m_sb.sb_logsunit; - } else if (mp->m_logbsize > 0 && - mp->m_logbsize < mp->m_sb.sb_logsunit) { - xfs_warn(mp, + } else if (mp->m_logbsize > 0) { + if (mp->m_logbsize > mp->m_sb.sb_logsunit) { + int logbsize; + /* round up to the next multiple of logsunit */ + logbsize = roundup(mp->m_logbsize, + mp->m_sb.sb_logsunit); + if (logbsize > XLOG_MAX_RECORD_BSIZE) + /* buffer size too large. round down. */ + logbsize -= mp->m_sb.sb_logsunit; + xfs_warn(mp, "log bufsize rounded from %d to %d", + mp->m_logbsize, logbsize); + mp->m_logbsize = logbsize; + } else if (mp->m_logbsize < mp->m_sb.sb_logsunit) { + xfs_warn(mp, "logbuf size must be greater than or equal to log stripe size"); - return XFS_ERROR(EINVAL); + return XFS_ERROR(EINVAL); + } } } else { /* Fail a mount if the logbuf is larger than 32K */ From sandeen@sandeen.net Sat Mar 2 15:23:13 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id D527F8008 for ; Sat, 2 Mar 2013 15:23:13 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay2.corp.sgi.com (Postfix) with ESMTP id ACCE5304059 for ; Sat, 2 Mar 2013 13:23:13 -0800 (PST) X-ASG-Debug-ID: 1362259389-04bdf02295c55f0001-NocioJ Received: from sandeen.net (sandeen.net [63.231.237.45]) by cuda.sgi.com with ESMTP id wCnu4zhtuWAveton for ; Sat, 02 Mar 2013 13:23:09 -0800 (PST) X-Barracuda-Envelope-From: sandeen@sandeen.net X-Barracuda-Apparent-Source-IP: 63.231.237.45 Received: from Liberator-563.local (liberator.sandeen.net [10.0.0.4]) (using TLSv1 with cipher DHE-RSA-CAMELLIA256-SHA (256/256 bits)) (No client certificate requested) by sandeen.net (Postfix) with ESMTPSA id BBF7163C59BB; Sat, 2 Mar 2013 15:23:08 -0600 (CST) Message-ID: <51326DC0.8030403@sandeen.net> Date: Sat, 02 Mar 2013 15:23:12 -0600 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: xfs-oss CC: Ole Tange Subject: [PATCH V2] xfs_repair: skip freelist scan of corrupt agf in no-modify mode References: <51313DE8.5080104@sandeen.net> X-ASG-Orig-Subj: [PATCH V2] xfs_repair: skip freelist scan of corrupt agf in no-modify mode In-Reply-To: <51313DE8.5080104@sandeen.net> X-Enigmail-Version: 1.5 Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: sandeen.net[63.231.237.45] X-Barracuda-Start-Time: 1362259389 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124073 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- In xfs_repair's no-modify mode (-n), verify_set_agf doesn't fix up bad freelist blocks that it finds. When we get to scan_freelist, this can wreak havoc if, for example, first > last and the loop never exits; we index agfl->agfl_bno[i] off into the weeds. To fix this, re-check the values in no-modify mode, and if they're off, warn about it and skip the scan. Reported-by: Ole Tange Signed-off-by: Eric Sandeen --- V2: Remove dumb mistakes :/ diff --git a/repair/scan.c b/repair/scan.c index 5345094..1d39bdc 100644 --- a/repair/scan.c +++ b/repair/scan.c @@ -1066,6 +1066,18 @@ scan_freelist( return; } agfl = XFS_BUF_TO_AGFL(agflbuf); + + if (no_modify) { + /* agf values not fixed in verify_set_agf, so recheck */ + if (be32_to_cpu(agf->agf_flfirst) >= XFS_AGFL_SIZE(mp) || + be32_to_cpu(agf->agf_fllast) >= XFS_AGFL_SIZE(mp)) { + do_warn(_("agf %d freelist blocks bad, skipping " + "freelist scan\n"), i); + return; + } + } else /* should have been fixed in verify_set_agf() */ + ASSERT(0); + i = be32_to_cpu(agf->agf_flfirst); count = 0; for (;;) { From david@fromorbit.com Sat Mar 2 17:05:22 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 814438006 for ; Sat, 2 Mar 2013 17:05:22 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay3.corp.sgi.com (Postfix) with ESMTP id 87C94AC001 for ; Sat, 2 Mar 2013 15:05:18 -0800 (PST) X-ASG-Debug-ID: 1362265516-04cbb07dbece790001-NocioJ Received: from ipmail07.adl2.internode.on.net (ipmail07.adl2.internode.on.net [150.101.137.131]) by cuda.sgi.com with ESMTP id Y8IhEBnBxLvPeRtk for ; Sat, 02 Mar 2013 15:05:17 -0800 (PST) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.131 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: Ar4NAKOEMlF5LFKb/2dsb2JhbABFhWe3TYUZexdzgh8BAQQBJxMcIwULCAMYCSUPBSUDIROIDQXBNhWOKSI9B4NAA5ZFkG2DHA Received: from ppp121-44-82-155.lns20.syd6.internode.on.net (HELO dastard) ([121.44.82.155]) by ipmail07.adl2.internode.on.net with ESMTP; 03 Mar 2013 09:35:15 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UBvUQ-0001os-01; Sun, 03 Mar 2013 10:05:14 +1100 Date: Sun, 3 Mar 2013 10:05:13 +1100 From: Dave Chinner To: Mark Tinguely Cc: xfs@oss.sgi.com Subject: Re: [PATCH] xfs: logsunit rounding causes iclog corruption/crash Message-ID: <20130302230513.GH23616@dastard> X-ASG-Orig-Subj: Re: [PATCH] xfs: logsunit rounding causes iclog corruption/crash References: <20130302201446.854313570@sgi.com> <20130302201452.236378200@sgi.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <20130302201452.236378200@sgi.com> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail07.adl2.internode.on.net[150.101.137.131] X-Barracuda-Start-Time: 1362265516 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124079 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Sat, Mar 02, 2013 at 02:14:47PM -0600, Mark Tinguely wrote: > When the iclog buffer size and log stripe unit are both defined and > the log stripe unit is less the log buffer size then the buffer is > rounded up to the log stripe unit size during the xlog_sync(). > > This rounding can exceed the iclog buffer length and in xlog_data_pack(): > 1) Cause corruption inside the iclog buffer because there will not be > enough space for the headers in the front of the iclog buffer for > the rounding. > 2) Cause corruption in memory that follows the iclog buffer when > stamping the lsn in each of the rounded blocks. > 3) If CONFIG_XFS_DEBUG is defined will cause a crash in xlog_verify_iclog(). > 4) Cause page fault crash if the memory after the buffer is not mapped. > > This has been found in XFS versions at least as far back as > Linux 2.6.32. > > This patch forces the iclog buffer to be a multiple of the log stripe > unit when they are both defined. > > Example: > # mkfs.xfs -l su=192k -f /dev/sda2 $ sudo mkfs.xfs -l sunit=192k /dev/vdb Specify log sunit in 512-byte blocks, no size suffix .... $ > # mount -o logbsize=256k /dev/sda3 /scratch > # io such as fsstress in /scratch will immediately crash a debug xfs > kernel and most like a non-debug xfs kernel. It's definitely not an immediate crash. xfstests runs for several minutes (including through fsstress workloads) before it finally falls over. I'd suggest a targetted xfstest is needed for this... > Index: b/fs/xfs/xfs_super.c > =================================================================== > --- a/fs/xfs/xfs_super.c > +++ b/fs/xfs/xfs_super.c > @@ -1357,11 +1357,23 @@ xfs_finish_flags( > if (mp->m_logbsize <= 0 && > mp->m_sb.sb_logsunit > XLOG_BIG_RECORD_BSIZE) { > mp->m_logbsize = mp->m_sb.sb_logsunit; > - } else if (mp->m_logbsize > 0 && > - mp->m_logbsize < mp->m_sb.sb_logsunit) { > - xfs_warn(mp, > + } else if (mp->m_logbsize > 0) { > + if (mp->m_logbsize > mp->m_sb.sb_logsunit) { > + int logbsize; > + /* round up to the next multiple of logsunit */ > + logbsize = roundup(mp->m_logbsize, > + mp->m_sb.sb_logsunit); > + if (logbsize > XLOG_MAX_RECORD_BSIZE) > + /* buffer size too large. round down. */ > + logbsize -= mp->m_sb.sb_logsunit; > + xfs_warn(mp, "log bufsize rounded from %d to %d", > + mp->m_logbsize, logbsize); > + mp->m_logbsize = logbsize; > + } else if (mp->m_logbsize < mp->m_sb.sb_logsunit) { > + xfs_warn(mp, > "logbuf size must be greater than or equal to log stripe size"); > - return XFS_ERROR(EINVAL); > + return XFS_ERROR(EINVAL); > + } If the user has specified an invalid log buffer size, then reject it with: logbsize XXX is not an integer multiple of the log stripe unit YYY Rounding means that the user isn't getting what they want and they may not realise it. If they make a mistake, they should be informed and forced to fix it before going any further. Cheers, Dave. -- Dave Chinner david@fromorbit.com From richard@nod.at Sat Mar 2 18:06:08 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 8282E800C for ; Sat, 2 Mar 2013 18:06:08 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay1.corp.sgi.com (Postfix) with ESMTP id 639C08F8049 for ; Sat, 2 Mar 2013 16:06:08 -0800 (PST) X-ASG-Debug-ID: 1362269162-04cbb07dbdd1810001-NocioJ Received: from radon.swed.at (a.ns.miles-group.at [95.130.255.143]) by cuda.sgi.com with ESMTP id bvcdqoZm4w1X6n9v (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO) for ; Sat, 02 Mar 2013 16:06:03 -0800 (PST) X-Barracuda-Envelope-From: richard@nod.at X-Barracuda-Apparent-Source-IP: 95.130.255.143 Received: (qmail 31389 invoked by uid 89); 3 Mar 2013 00:06:02 -0000 Received: by simscan 1.3.1 ppid: 31381, pid: 31385, t: 0.2167s scanners: attach: 1.3.1 clamav: 0.96.5/m: Received: from unknown (HELO spider.haslach.nod.at.haslach.nod.at) (richard@nod.at@212.186.22.124) by radon.swed.at with ESMTPA; 3 Mar 2013 00:06:02 -0000 From: Richard Weinberger To: xfs@oss.sgi.com Cc: linux-fsdevel@vger.kernel.org, Richard Weinberger Subject: [PATCH] Do not check ocfs2 Date: Sun, 3 Mar 2013 01:05:50 +0100 X-ASG-Orig-Subj: [PATCH] Do not check ocfs2 Message-Id: <1362269150-21478-1-git-send-email-richard@nod.at> X-Mailer: git-send-email 1.8.1.2 X-Barracuda-Connect: a.ns.miles-group.at[95.130.255.143] X-Barracuda-Start-Time: 1362269163 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124083 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- We cannot run fsck.ocfs2 because the file system is most likely mounted on another node. Signed-off-by: Richard Weinberger --- common.rc | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/common.rc b/common.rc index f5180fe..00c075d 100644 --- a/common.rc +++ b/common.rc @@ -1419,6 +1419,9 @@ _check_test_fs() udf) # do nothing for now ;; + ocfs2) + # other nodes may have mounted the fs + ;; btrfs) _check_btrfs_filesystem $TEST_DEV ;; @@ -1448,6 +1451,9 @@ _check_scratch_fs() nfs*) # Don't know how to check an NFS filesystem, yet. ;; + ocfs2) + # other nodes may have mounted the fs + ;; btrfs) _check_btrfs_filesystem $SCRATCH_DEV ;; -- 1.8.1.2 From david@fromorbit.com Sat Mar 2 19:19:25 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 9EEF0800E for ; Sat, 2 Mar 2013 19:19:25 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay3.corp.sgi.com (Postfix) with ESMTP id 1C9FBAC002 for ; Sat, 2 Mar 2013 17:19:21 -0800 (PST) X-ASG-Debug-ID: 1362273559-04cbb07dbcd4e50001-NocioJ Received: from ipmail07.adl2.internode.on.net (ipmail07.adl2.internode.on.net [150.101.137.131]) by cuda.sgi.com with ESMTP id BW1cVdufErDe9IX7 for ; Sat, 02 Mar 2013 17:19:20 -0800 (PST) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.131 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: Ar0NAJ2jMlF5LFKb/2dsb2JhbABFhWe3UIUZexdzgh8BAQU6HCMQCAMYCSUPBSUDIROIEsElFY4pIj0Hg0ADlkWQbYMc Received: from ppp121-44-82-155.lns20.syd6.internode.on.net (HELO dastard) ([121.44.82.155]) by ipmail07.adl2.internode.on.net with ESMTP; 03 Mar 2013 11:49:19 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UBxa9-000218-Nq; Sun, 03 Mar 2013 12:19:17 +1100 Date: Sun, 3 Mar 2013 12:19:17 +1100 From: Dave Chinner To: Richard Weinberger Cc: xfs@oss.sgi.com, linux-fsdevel@vger.kernel.org Subject: Re: [PATCH] Do not check ocfs2 Message-ID: <20130303011917.GI23616@dastard> X-ASG-Orig-Subj: Re: [PATCH] Do not check ocfs2 References: <1362269150-21478-1-git-send-email-richard@nod.at> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <1362269150-21478-1-git-send-email-richard@nod.at> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail07.adl2.internode.on.net[150.101.137.131] X-Barracuda-Start-Time: 1362273559 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124088 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Sun, Mar 03, 2013 at 01:05:50AM +0100, Richard Weinberger wrote: > We cannot run fsck.ocfs2 because the file system > is most likely mounted on another node. This patch means that ocfs2 filesystems are *never* checked for consistency, even when you are testing them with exclusive local access. That defeats a primary function of xfstests - ensuring that the tests run do no corrupt the filesystem. Besides, why would you be running xfstests on a filesystem that is mounted on multiple nodes? Yes, ocfs2 is a cluster filesystem, but xfstests is designed to test local filesystem behaviour and is completely cluster naive. Hence having multiple nodes mount the filesystem that is being tested by xfstests does not serve any purpose at all. Further, turning off consistency checking for those that are running ocfs2 testing on single nodes means that testing is now mostly wasted as the majority of problems that can occur are no longer detectable.... Cheers, Dave. -- Dave Chinner david@fromorbit.com From info@karaokencasa.com Sat Mar 2 20:58:15 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: *** X-Spam-Status: No, score=3.2 required=5.0 tests=DATE_IN_PAST_24_48, HTML_IMAGE_RATIO_04,HTML_MESSAGE,T_DKIM_INVALID autolearn=no version=3.3.1 X-Original-To: linux-xfs@oss.sgi.com Delivered-To: linux-xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 4ADE18010 for ; Sat, 2 Mar 2013 20:58:15 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay1.corp.sgi.com (Postfix) with ESMTP id 3A50C8F8035 for ; Sat, 2 Mar 2013 18:58:12 -0800 (PST) X-ASG-Debug-ID: 1362279489-04cbb07dbfd9810001-w1Z2WR Received: from emailscampaign.net (static-ip-173-224-115-102.inaddr.ip-pool.com [173.224.115.102]) by cuda.sgi.com with ESMTP id eVV1SHnStA4ogSxk for ; Sat, 02 Mar 2013 18:58:10 -0800 (PST) X-Barracuda-Envelope-From: info@karaokencasa.com X-Barracuda-Apparent-Source-IP: 173.224.115.102 DKIM-Signature: v=1; a=rsa-sha1; c=relaxed/relaxed; s=dkim; d=vm-group.net; h=To:Subject:Message-ID:Date:From:Reply-To:MIME-Version:List-Unsubscribe:Content-Type:Content-Transfer-Encoding; i=info@vm-group.net; bh=jjB0gk5ytl1tQWgZAx0WKrWQ5iM=; b=TvUgPazTZrdkPMx3FlitFvo6aTcRr666SizL3+ULq3Pvot/wth4a1IhM98Sf2h/74rvKebRF++2D wBURBiHu/76+l3g0usulO0cxpT0npdPbafutHp2YlN6jKySFyUX078C33Pxh1gBs7hWDeE1hPejJ pitioof5+wjiyBtSLWE= DomainKey-Signature: a=rsa-sha1; c=nofws; q=dns; s=dkim; d=vm-group.net; b=a+3ydR+59nm5GtgJ7VtyKOHWemp7+wzC/FYqI22UTbCrCe7eBgYCW6nQ3rPlJ28sG6jQeXbXGL41 WOOQimsM50qVFGGVyUn2dCVukp8Vts9bYepgnu5tAiitHRxxjbjFLcAgvfY3ig5TbWZc437KMTFC oC/XTLzHHkF/Qha6FKI=; To: linux-xfs@oss.sgi.com Subject: forma vendedores profesionales Message-ID: <15cbd174578857d1e2d483035493c584@server00017.com> X-ASG-Orig-Subj: forma vendedores profesionales Date: Fri, 01 Mar 2013 11:26:09 -0500 From: "charly vende" Reply-To: info@vm-group.net MIME-Version: 1.0 X-Mailer-LID: 2 List-Unsubscribe: X-Mailer-RecptId: 149687 X-Mailer-SID: 9 X-Mailer-Sent-By: 2 Content-Type: multipart/alternative; charset="UTF-8"; boundary="b1_2618c8149ca5d2ed93c4256fc3f25757" Content-Transfer-Encoding: 8bit X-Barracuda-Connect: static-ip-173-224-115-102.inaddr.ip-pool.com[173.224.115.102] X-Barracuda-Start-Time: 1362279489 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.67 X-Barracuda-Spam-Status: No, SCORE=0.67 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=DATE_IN_PAST_24_48, DATE_IN_PAST_24_48_2, DKIM_SIGNED, HTML_IMAGE_RATIO_04, HTML_MESSAGE X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124094 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.01 DATE_IN_PAST_24_48 Date: is 24 to 48 hours before Received: date 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature 0.17 HTML_IMAGE_RATIO_04 BODY: HTML has a low ratio of text to image area 0.00 HTML_MESSAGE BODY: HTML included in message 0.48 DATE_IN_PAST_24_48_2 DATE_IN_PAST_24_48_2 --b1_2618c8149ca5d2ed93c4256fc3f25757 Content-Type: text/plain; format=flowed; charset="UTF-8" Content-Transfer-Encoding: 8bit Su cliente de correo electronico no puede leer este e-mail. Para ver en linea, por favor haga clic aqui: http://server00017.com/mail/display.php?M=149687&C=3b6a406c48aea73f45c88c2e69e57b20&S=9&L=2&N=2 Para dejar de recibir estos correos electronicos:http://server00017.com/mail/unsubscribe.php?M=149687&C=3b6a406c48aea73f45c88c2e69e57b20&L=2&N=9 --b1_2618c8149ca5d2ed93c4256fc3f25757 Content-Type: text/html; charset="UTF-8" Content-Transfer-Encoding: 8bit Landing Page

“Si Sus Vendedores, o Su Equipo de

Trabajo en General, Están Negociando

Para Beneficio de Su Empresa

¿No Sería Bueno Armarlos Con Técnicas Superiores

de Negociación Comercial?”

Siempre estamos negociando y quien negocia mejor, obtiene los mayores beneficios.

Si usted ha deseado por mucho tiempo tener una fuerza de ventas:

  • Más efectiva a la hora de negociar;
  • Que gane para su empresa los mejores tratos; 
  • Que cierre más ventas (sin ceder a cada petición que realice la otra parte); 
  • Que acelere la toma de decisiones de sus clientes, obteniendo para su empresa más clientes en menos tiempo…

Permítanos presentarle el Programa de Entrenamiento de Ventas mas vendido en el Mundo en manos del mejor entrenador en ventas de habla hispana, ALEX DEY !:

1fh.png
 

Sí… Quiero convertirme en un vendedor profesional:
videooo.jpg

Es un curso en Video 100% práctico que incluye dinámicas, prácticas de negociación en vivo, todo enfocado a maximizar la efectividad de sus vendedores al negociar.

ompraw.png


ELIMINAR SU DIRECCIÓN: Si este mensaje no ha sido de su agrado por favor acepte nuestras disculpas. "Tener en cuenta que responder este correo para solicitar su Baja no tendrá dicho efecto, por favor siga estas instrucciones para garantizar su Baja de la lista"
1) Para darse de Baja definitiva de la lista UD.
Deberá hacer CLICK AQUI

--b1_2618c8149ca5d2ed93c4256fc3f25757-- From richard@nod.at Sun Mar 3 03:03:08 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 1953C8013 for ; Sun, 3 Mar 2013 03:03:08 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id 0701D304032 for ; Sun, 3 Mar 2013 01:03:04 -0800 (PST) X-ASG-Debug-ID: 1362301377-04cbb07dbef16c0001-NocioJ Received: from radon.swed.at (a.ns.miles-group.at [95.130.255.143]) by cuda.sgi.com with ESMTP id C0wd8Xz2bPudHa1U (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO) for ; Sun, 03 Mar 2013 01:02:58 -0800 (PST) X-Barracuda-Envelope-From: richard@nod.at X-Barracuda-Apparent-Source-IP: 95.130.255.143 Received: (qmail 8779 invoked by uid 89); 3 Mar 2013 09:02:57 -0000 Received: by simscan 1.3.1 ppid: 8772, pid: 8775, t: 0.1024s scanners: attach: 1.3.1 clamav: 0.96.5/m: Received: from unknown (HELO spider.haslach.nod.at) (richard@nod.at@212.186.22.124) by radon.swed.at with ESMTPA; 3 Mar 2013 09:02:57 -0000 Date: Sun, 3 Mar 2013 10:02:54 +0100 From: Richard Weinberger To: Dave Chinner Cc: xfs@oss.sgi.com, linux-fsdevel@vger.kernel.org Subject: Re: [PATCH] Do not check ocfs2 Message-ID: <20130303100254.500b076f@spider.haslach.nod.at> X-ASG-Orig-Subj: Re: [PATCH] Do not check ocfs2 In-Reply-To: <20130303011917.GI23616@dastard> References: <1362269150-21478-1-git-send-email-richard@nod.at> <20130303011917.GI23616@dastard> X-Mailer: Claws Mail 3.8.1 (GTK+ 2.24.14; x86_64-suse-linux-gnu) Mime-Version: 1.0 Content-Type: text/plain; charset=US-ASCII Content-Transfer-Encoding: 7bit X-Barracuda-Connect: a.ns.miles-group.at[95.130.255.143] X-Barracuda-Start-Time: 1362301378 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124116 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- Am Sun, 3 Mar 2013 12:19:17 +1100 schrieb Dave Chinner : > On Sun, Mar 03, 2013 at 01:05:50AM +0100, Richard Weinberger wrote: > > We cannot run fsck.ocfs2 because the file system > > is most likely mounted on another node. > > This patch means that ocfs2 filesystems are *never* checked for > consistency, even when you are testing them with exclusive local > access. That defeats a primary function of xfstests - ensuring that > the tests run do no corrupt the filesystem. > > Besides, why would you be running xfstests on a filesystem that is > mounted on multiple nodes? Yes, ocfs2 is a cluster filesystem, but > xfstests is designed to test local filesystem behaviour and is > completely cluster naive. Hence having multiple nodes mount the > filesystem that is being tested by xfstests does not serve any > purpose at all. Further, turning off consistency checking for those > that are running ocfs2 testing on single nodes means that testing is > now mostly wasted as the majority of problems that can occur are no > longer detectable.... Using xfstests I was able to trigger dlm issues in ocfs2. I ran xfstests on one node and other nodes had it mounted too. To ensure that fsck.ocfs2 will not corrupt the filesystem I've applied this patch. If you don't like the patch I'm perfectly fine with that. Maybe it makes more sense to add a feature to xfstests which unmounts the ocfs2 filesystem on all nodes (using SSH), then it is allowed to run fsck.ocfs2. Thanks, //richard From jmv@email.gwu.edu Sun Mar 3 07:41:32 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: * X-Spam-Status: No, score=1.2 required=5.0 tests=FREEMAIL_FORGED_REPLYTO, HTML_MESSAGE autolearn=no version=3.3.1 X-Original-To: linux-xfs@oss.sgi.com Delivered-To: linux-xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 537208015 for ; Sun, 3 Mar 2013 07:41:32 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay3.corp.sgi.com (Postfix) with ESMTP id D58B9AC002 for ; Sun, 3 Mar 2013 05:41:31 -0800 (PST) X-ASG-Debug-ID: 1362318090-04bdf02295100580001-w1Z2WR Received: from na3sys009aob109.obsmtp.com (na3sys009aob109.obsmtp.com [74.125.149.200]) by cuda.sgi.com with SMTP id hN6f0ReU7M2yju0H (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO) for ; Sun, 03 Mar 2013 05:41:30 -0800 (PST) X-Barracuda-Envelope-From: jmv@email.gwu.edu X-Barracuda-RBL-Trusted-Forwarder: 74.125.149.200 Received: from mail-ie0-f199.google.com ([209.85.223.199]) (using TLSv1) by na3sys009aob109.postini.com ([74.125.148.12]) with SMTP ID DSNKUTNTCTygaKv9XZfV7cPs0X0SDaUlHR44@postini.com; Sun, 03 Mar 2013 05:41:30 PST Received: by mail-ie0-f199.google.com with SMTP id c13so27092195ieb.2 for ; Sun, 03 Mar 2013 05:41:29 -0800 (PST) X-Barracuda-BBL-Trusted-Forwarder: 209.85.223.199 X-Barracuda-RBL-Trusted-Forwarder: 209.85.223.199 X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=20120113; h=x-received:mime-version:x-received:reply-to:date:message-id:subject :from:to:content-type:x-gm-message-state; bh=uUeGXPjGyDQTl+8uy7wYZTqXnVrDhUKoMGJNjr8ZjGI=; b=NQJeiyeKIRG0Qu54NW0Yv8UA07X46nb2o3zw9roaw1VsSIrQQQfv8tHu7qpae94jou jp1c92HPd47vkiDuOL8h6B9GNLDHpyd29ISNiON/aK0Q53gN+xWcv2IaRhSZfxxsuKZ6 Rj8J9CehS4E3Tf8koupEyv+FHVpLuyvo3lK9KezXHYSPwLI2gWrv54CMdRa9xa4AO8Jz QU4egYS1P9xx0QItOVHQqtNZvBNwAYo2/xc2WmHgmRpKh1bVkQ0cnNNQ7NqN3/V9vIlY RZxXXR8uQoOEFxEbYJrePaIiUGQvAQz/3PIopcmz2D7l8wmHtB9VZ4aqzzrRhO/QAKS1 VTkA== X-Barracuda-BBL-IP: nil X-Received: by 10.50.13.175 with SMTP id i15mr179119igc.105.1362318089227; Sun, 03 Mar 2013 05:41:29 -0800 (PST) MIME-Version: 1.0 X-Received: by 10.50.13.175 with SMTP id i15mr178781igc.105.1362318088434; Sun, 03 Mar 2013 05:41:28 -0800 (PST) Received: by 10.64.141.115 with HTTP; Sun, 3 Mar 2013 05:41:28 -0800 (PST) Reply-To: smithjonesltd@live.com Date: Sun, 3 Mar 2013 15:41:28 +0200 Message-ID: Subject: Price Quotes... From: Smith Jones Ltd X-ASG-Orig-Subj: Price Quotes... To: undisclosed-recipients:; Content-Type: multipart/alternative; boundary=f46d0447f382bbfbe404d7056534 X-Gm-Message-State: ALoCoQlLQ1STbmHuS3MyOXXIhT20jNeLgi6pRzwrahSIn4qbs2DDipvcY5ioBKhduOPcEV+Iwt3C6U1Ys8iwC+oBnspuAXmeDHHd01OwdSN43RssYq6CAxU6eyLjM7cE8ndrvGH/V+kef2u7SREQNmSrCQiUf7BGJQ== X-Barracuda-Connect: na3sys009aob109.obsmtp.com[74.125.149.200] X-Barracuda-Start-Time: 1362318090 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.50 X-Barracuda-Spam-Status: No, SCORE=0.50 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_SA620a, HTML_MESSAGE X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124133 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 HTML_MESSAGE BODY: HTML included in message 0.50 BSF_SC0_SA620a Custom Rule SA620a --f46d0447f382bbfbe404d7056534 Content-Type: text/plain; charset=ISO-8859-1 Hello, I saw your product and we are interested in purchasing. Kindly send us more detail and price quotes. We await your earliest response. Regard, Smith Jones Ltd. --f46d0447f382bbfbe404d7056534 Content-Type: text/html; charset=ISO-8859-1 Hello,

I saw your product and we are interested in purchasing. Kindly send us more detail and price quotes.

We await your earliest response.

Regard,

Smith Jones Ltd. --f46d0447f382bbfbe404d7056534-- From rovingve@hurricane.hawkhost.com Sun Mar 3 08:41:41 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: **** X-Spam-Status: No, score=4.2 required=5.0 tests=HTML_IMAGE_ONLY_16, HTML_MESSAGE,MIME_HTML_ONLY,T_REMOTE_IMAGE autolearn=no version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 84C298015 for ; Sun, 3 Mar 2013 08:41:41 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay2.corp.sgi.com (Postfix) with ESMTP id 724FF304032 for ; Sun, 3 Mar 2013 06:41:38 -0800 (PST) X-ASG-Debug-ID: 1362321695-04cb6c2b041059a0001-NocioJ Received: from hurricane.hawkhost.com (hurricane.hawkhost.com [174.37.162.44]) by cuda.sgi.com with ESMTP id HpogfWs4Wc8ZAh1p (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO) for ; Sun, 03 Mar 2013 06:41:36 -0800 (PST) X-Barracuda-Envelope-From: rovingve@hurricane.hawkhost.com X-Barracuda-Apparent-Source-IP: 174.37.162.44 Received: from rovingve by hurricane.hawkhost.com with local (Exim 4.80) (envelope-from ) id 1UCA6Z-003xEH-3z for xfs@oss.sgi.com; Sun, 03 Mar 2013 06:41:35 -0800 To: xfs@oss.sgi.com Subject: Important - Personal Information Update Required. X-PHP-Script: rovingvet.com/wp-content/themes/flexibility3/includes/inbox.php for 41.138.177.29 X-ASG-Orig-Subj: Important - Personal Information Update Required. From: Wells Fargo Bank MIME-Version: 1.0 Content-Type: text/html Message-Id: Date: Sun, 03 Mar 2013 06:41:35 -0800 X-AntiAbuse: This header was added to track abuse, please include it with any abuse report X-AntiAbuse: Primary Hostname - hurricane.hawkhost.com X-AntiAbuse: Original Domain - oss.sgi.com X-AntiAbuse: Originator/Caller UID/GID - [615 619] / [47 12] X-AntiAbuse: Sender Address Domain - hurricane.hawkhost.com X-Get-Message-Sender-Via: hurricane.hawkhost.com: authenticated_id: rovingve/only user confirmed/virtual account not confirmed X-Barracuda-Connect: hurricane.hawkhost.com[174.37.162.44] X-Barracuda-Start-Time: 1362321695 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.63 X-Barracuda-Spam-Status: No, SCORE=0.63 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=HTML_IMAGE_ONLY_16, HTML_MESSAGE, MIME_HTML_ONLY X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124137 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 MIME_HTML_ONLY BODY: Message only has text/html MIME parts 0.63 HTML_IMAGE_ONLY_16 BODY: HTML: images with 1200-1600 bytes of words 0.00 HTML_MESSAGE BODY: HTML included in message Wells Fargo Letter

Wells Fargo logo

Dear Valuable Customers,

Your new statement is now available online

The new statement for your account is now available to view online.

To access your statement, go to Stateme nts and Documents.

Keeping your financial information secure is one of our most important responsibilities.


Wells Fargo Security Team
(If you have questions about your account, please refer to the contact information on your statement. )
(For questions about viewing your statements online, Wells Fargo Customer Service is available 24 hours a day, 7 days a week at 1-800-956-4442 or by secure email.)

From gnehzuil.liu@gmail.com Sun Mar 3 10:28:41 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=FREEMAIL_FROM,T_DKIM_INVALID autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 11DF57F93 for ; Sun, 3 Mar 2013 10:28:41 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay2.corp.sgi.com (Postfix) with ESMTP id D7DD3304043 for ; Sun, 3 Mar 2013 08:28:37 -0800 (PST) X-ASG-Debug-ID: 1362328116-04bdf022971101a0001-NocioJ Received: from mail-da0-f49.google.com (mail-da0-f49.google.com [209.85.210.49]) by cuda.sgi.com with ESMTP id DncaROxvNRSpBDcz (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Sun, 03 Mar 2013 08:28:36 -0800 (PST) X-Barracuda-Envelope-From: gnehzuil.liu@gmail.com X-Barracuda-Apparent-Source-IP: 209.85.210.49 X-Barracuda-IPDD: Level1 [gmail.com/209.85.210.49] Received: by mail-da0-f49.google.com with SMTP id t11so2112200daj.8 for ; Sun, 03 Mar 2013 08:28:36 -0800 (PST) X-Barracuda-IPDD: Level1 [gmail.com/209.85.210.49] X-Barracuda-IPDD: Level1 [gmail.com/209.85.210.49] DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20120113; h=x-received:date:from:to:cc:subject:message-id:mail-followup-to :references:mime-version:content-type:content-disposition :in-reply-to:user-agent; bh=vk5wQwsSaMYpZHQUuJkHe3CsC2aX9j3LCnZVJTEnT/A=; b=TlU3ezv8lmBi1GkPD8eBtwcKfi87a7dAsj9DsFbWlfyBsD9gurqYPKFpa1jFOh5Zok UtbG+CtqhBgTTZwexFB+CdXQkBETWForw8SyPtfklVPHHgc/vlnGtJZPXRNLlKYi4Tbj uZMYYS8sfcaO6MJhOzZGFVyqnTG+NbfTaLSLFs0aN/qk6lY0IF9D6DezORpHM34JPG95 bf73XAOVKoLGiM/F5nyTE8WdJOtOQoa6JhUeJ3Vk0zRW9DCnbAdMS6X+9fpojvJj7U2N wzbYyUV6E09VccQj2bxhOCmMl/EVskBXZvwUwqPRQ8C2ExYZ+WstNgOjkPBCpygmDNli xB3Q== X-Received: by 10.68.25.138 with SMTP id c10mr24353143pbg.133.1362328116478; Sun, 03 Mar 2013 08:28:36 -0800 (PST) Received: from gmail.com ([182.92.247.2]) by mx.google.com with ESMTPS id ri1sm19190267pbc.16.2013.03.03.08.28.31 (version=TLSv1 cipher=RC4-SHA bits=128/128); Sun, 03 Mar 2013 08:28:35 -0800 (PST) Date: Mon, 4 Mar 2013 00:43:42 +0800 From: Zheng Liu To: Dmitry Monakhov Cc: xfs@oss.sgi.com, linux-fsdevel@vger.kernel.org, linux-ext4@vger.kernel.org, dchinner@redhat.com Subject: Re: [PATCH 09/10] xfstest: add defragmentation stress tests for ext4 Message-ID: <20130303164342.GB30459@gmail.com> X-ASG-Orig-Subj: Re: [PATCH 09/10] xfstest: add defragmentation stress tests for ext4 Mail-Followup-To: Dmitry Monakhov , xfs@oss.sgi.com, linux-fsdevel@vger.kernel.org, linux-ext4@vger.kernel.org, dchinner@redhat.com References: <1361356935-29153-1-git-send-email-dmonakhov@openvz.org> <1361356935-29153-10-git-send-email-dmonakhov@openvz.org> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <1361356935-29153-10-git-send-email-dmonakhov@openvz.org> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: mail-da0-f49.google.com[209.85.210.49] X-Barracuda-Start-Time: 1362328116 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=DKIM_SIGNED, DKIM_VERIFIED X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124145 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature On Wed, Feb 20, 2013 at 02:42:14PM +0400, Dmitry Monakhov wrote: > Perform various regression tests for ext4defrag subsystem > > 299'th Test1: Defragment file while other task does direct AIO Hi Dmitry, I couldn't run this testcase in my sandbox. I got the following error message. FSTYP -- ext4 PLATFORM -- Linux/x86_64 lz-desktop 3.8.0 MKFS_OPTIONS -- /dev/sda2 MOUNT_OPTIONS -- -o acl,user_xattr /dev/sda2 /mnt/sda2 299 [not run] /usr/local/bin/fio too old Not run: 299 Passed all 0 tests My fio version is fio-2.0.14-23-g9c63. It seems that there are some errors in fio config file. Regards, - Zheng From gnehzuil.liu@gmail.com Sun Mar 3 11:08:24 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=FREEMAIL_FROM,T_DKIM_INVALID autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 21E4F801E for ; Sun, 3 Mar 2013 11:08:24 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id 0FEFB304039 for ; Sun, 3 Mar 2013 09:08:21 -0800 (PST) X-ASG-Debug-ID: 1362330496-04cbb07dbd112110001-NocioJ Received: from mail-pa0-f51.google.com (mail-pa0-f51.google.com [209.85.220.51]) by cuda.sgi.com with ESMTP id 1ySZAo9tbuXuE9bE (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Sun, 03 Mar 2013 09:08:17 -0800 (PST) X-Barracuda-Envelope-From: gnehzuil.liu@gmail.com X-Barracuda-Apparent-Source-IP: 209.85.220.51 X-Barracuda-IPDD: Level1 [gmail.com/209.85.220.51] Received: by mail-pa0-f51.google.com with SMTP id hz1so2683568pad.38 for ; Sun, 03 Mar 2013 09:08:16 -0800 (PST) X-Barracuda-IPDD: Level1 [gmail.com/209.85.220.51] X-Barracuda-IPDD: Level1 [gmail.com/209.85.220.51] DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20120113; h=x-received:date:from:to:subject:message-id:mail-followup-to :references:mime-version:content-type:content-disposition :in-reply-to:user-agent; bh=xe68d/j20pmT++S129Tvi1yIep3pbfX3u3A5xWY/KZI=; b=H7GEZt5vlyOISQXr4BHr0marECPBoaowAkIp19g30jD9s7iSc2aUGEsdvbe7Wn83cE C+xAMwCxLXLXxw3DwZC8oEwj8AiwcV88yof6T0JVI2B5e3QeK0Dyc9sWEfXqOyLIzKur kZjWJdtU48SQGCXL3lIuZjc4UB6A4KGgt7PD6jHy+3kslvHgob4Nfr8gkY+dGu4N2uMv Ukf3i+X0WIxCYv6ShgudP92+rwMncsawcW5IEljaJEAvnZ5vPb/u+B9PNW1CxWhxhW5H PmcSJ3e1IgLMG9LpR+C7elaz4/bpZf0BQjwuSl1TbkC1Hxp7T6lUpKUET9QMV0xpBtI+ befw== X-Received: by 10.68.50.231 with SMTP id f7mr3740445pbo.221.1362330496428; Sun, 03 Mar 2013 09:08:16 -0800 (PST) Received: from gmail.com ([182.92.247.2]) by mx.google.com with ESMTPS id e6sm20694586paw.16.2013.03.03.09.08.11 (version=TLSv1 cipher=RC4-SHA bits=128/128); Sun, 03 Mar 2013 09:08:15 -0800 (PST) Date: Mon, 4 Mar 2013 01:23:21 +0800 From: Zheng Liu To: Dmitry Monakhov , xfs@oss.sgi.com, linux-fsdevel@vger.kernel.org, linux-ext4@vger.kernel.org, dchinner@redhat.com Subject: Re: [PATCH 09/10] xfstest: add defragmentation stress tests for ext4 Message-ID: <20130303172321.GA5608@gmail.com> X-ASG-Orig-Subj: Re: [PATCH 09/10] xfstest: add defragmentation stress tests for ext4 Mail-Followup-To: Dmitry Monakhov , xfs@oss.sgi.com, linux-fsdevel@vger.kernel.org, linux-ext4@vger.kernel.org, dchinner@redhat.com References: <1361356935-29153-1-git-send-email-dmonakhov@openvz.org> <1361356935-29153-10-git-send-email-dmonakhov@openvz.org> <20130303164342.GB30459@gmail.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <20130303164342.GB30459@gmail.com> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: mail-pa0-f51.google.com[209.85.220.51] X-Barracuda-Start-Time: 1362330496 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=DKIM_SIGNED, DKIM_VERIFIED X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124147 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature On Mon, Mar 04, 2013 at 12:43:42AM +0800, Zheng Liu wrote: > On Wed, Feb 20, 2013 at 02:42:14PM +0400, Dmitry Monakhov wrote: > > Perform various regression tests for ext4defrag subsystem > > > > 299'th Test1: Defragment file while other task does direct AIO > > Hi Dmitry, > > I couldn't run this testcase in my sandbox. I got the following error > message. > > FSTYP -- ext4 > PLATFORM -- Linux/x86_64 lz-desktop 3.8.0 > MKFS_OPTIONS -- /dev/sda2 > MOUNT_OPTIONS -- -o acl,user_xattr /dev/sda2 /mnt/sda2 > > 299 [not run] /usr/local/bin/fio too old > Not run: 299 > Passed all 0 tests > > My fio version is fio-2.0.14-23-g9c63. It seems that there are some > errors in fio config file. I just notice Rich's reply. After adding 'NUM_JOBS=$((4*LOAD_FACTOR))', the testcase can run. Sorry for the noisy. Regards, - Zheng From tinguely@sgi.com Sun Mar 3 13:04:43 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 85C80800E for ; Sun, 3 Mar 2013 13:04:43 -0600 (CST) Received: from eagdhcp-232-136.americas.sgi.com (eagdhcp-232-136.americas.sgi.com [128.162.232.136]) by relay2.corp.sgi.com (Postfix) with ESMTP id 657F9304048; Sun, 3 Mar 2013 11:04:40 -0800 (PST) Message-ID: <51339EC7.1000509@sgi.com> Date: Sun, 03 Mar 2013 13:04:39 -0600 From: Mark Tinguely User-Agent: Mozilla/5.0 (X11; FreeBSD amd64; rv:9.0) Gecko/20120122 Thunderbird/9.0 MIME-Version: 1.0 To: Dave Chinner CC: xfs@oss.sgi.com Subject: Re: [PATCH] xfs: logsunit rounding causes iclog corruption/crash References: <20130302201446.854313570@sgi.com> <20130302201452.236378200@sgi.com> <20130302230513.GH23616@dastard> In-Reply-To: <20130302230513.GH23616@dastard> Content-Type: text/plain; charset=ISO-8859-1; format=flowed Content-Transfer-Encoding: 7bit On 03/02/13 17:05, Dave Chinner wrote: > On Sat, Mar 02, 2013 at 02:14:47PM -0600, Mark Tinguely wrote: >> When the iclog buffer size and log stripe unit are both defined and >> the log stripe unit is less the log buffer size then the buffer is >> rounded up to the log stripe unit size during the xlog_sync(). >> >> This rounding can exceed the iclog buffer length and in xlog_data_pack(): >> 1) Cause corruption inside the iclog buffer because there will not be >> enough space for the headers in the front of the iclog buffer for >> the rounding. >> 2) Cause corruption in memory that follows the iclog buffer when >> stamping the lsn in each of the rounded blocks. >> 3) If CONFIG_XFS_DEBUG is defined will cause a crash in xlog_verify_iclog(). >> 4) Cause page fault crash if the memory after the buffer is not mapped. >> >> This has been found in XFS versions at least as far back as >> Linux 2.6.32. >> >> This patch forces the iclog buffer to be a multiple of the log stripe >> unit when they are both defined. >> >> Example: >> # mkfs.xfs -l su=192k -f /dev/sda2 > > $ sudo mkfs.xfs -l sunit=192k /dev/vdb > Specify log sunit in 512-byte blocks, no size suffix > .... > $ > >> # mount -o logbsize=256k /dev/sda3 /scratch >> # io such as fsstress in /scratch will immediately crash a debug xfs >> kernel and most like a non-debug xfs kernel. > > It's definitely not an immediate crash. xfstests runs for several > minutes (including through fsstress workloads) before it finally > falls over. I'd suggest a targetted xfstest is needed for this... > >> Index: b/fs/xfs/xfs_super.c >> =================================================================== >> --- a/fs/xfs/xfs_super.c >> +++ b/fs/xfs/xfs_super.c >> @@ -1357,11 +1357,23 @@ xfs_finish_flags( >> if (mp->m_logbsize<= 0&& >> mp->m_sb.sb_logsunit> XLOG_BIG_RECORD_BSIZE) { >> mp->m_logbsize = mp->m_sb.sb_logsunit; >> - } else if (mp->m_logbsize> 0&& >> - mp->m_logbsize< mp->m_sb.sb_logsunit) { >> - xfs_warn(mp, >> + } else if (mp->m_logbsize> 0) { >> + if (mp->m_logbsize> mp->m_sb.sb_logsunit) { >> + int logbsize; >> + /* round up to the next multiple of logsunit */ >> + logbsize = roundup(mp->m_logbsize, >> + mp->m_sb.sb_logsunit); >> + if (logbsize> XLOG_MAX_RECORD_BSIZE) >> + /* buffer size too large. round down. */ >> + logbsize -= mp->m_sb.sb_logsunit; eeks: if (logbsize != mp->m_logbsize) { >> + xfs_warn(mp, "log bufsize rounded from %d to %d", >> + mp->m_logbsize, logbsize); >> + mp->m_logbsize = logbsize; } >> + } else if (mp->m_logbsize< mp->m_sb.sb_logsunit) { >> + xfs_warn(mp, >> "logbuf size must be greater than or equal to log stripe size"); >> - return XFS_ERROR(EINVAL); >> + return XFS_ERROR(EINVAL); >> + } > > If the user has specified an invalid log buffer size, then reject it > with: > > logbsize XXX is not an integer multiple of the log stripe unit YYY > > Rounding means that the user isn't getting what they want and they > may not realise it. If they make a mistake, they should be informed > and forced to fix it before going any further. > > Cheers, > > Dave. The code already silently changes the log blocksize if mp->m_sb.sb_logsunit > mp->m_logbsize. IMO, it should fix it not a multiple too. --Mark. From jcjohn@gwmail.gwu.edu Sun Mar 3 15:08:35 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: * X-Spam-Status: No, score=1.2 required=5.0 tests=FREEMAIL_FORGED_REPLYTO, HTML_MESSAGE autolearn=no version=3.3.1 X-Original-To: linux-xfs@oss.sgi.com Delivered-To: linux-xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 23B0E801D for ; Sun, 3 Mar 2013 15:08:35 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay3.corp.sgi.com (Postfix) with ESMTP id A50A1AC001 for ; Sun, 3 Mar 2013 13:08:34 -0800 (PST) X-ASG-Debug-ID: 1362344910-04cbb07dbf121540001-w1Z2WR Received: from mail-ie0-f193.google.com (mail-ie0-f193.google.com [209.85.223.193]) by cuda.sgi.com with ESMTP id BGrcLb1bTnVIbvS2 (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Sun, 03 Mar 2013 13:08:30 -0800 (PST) X-Barracuda-Envelope-From: jcjohn@gwmail.gwu.edu X-Barracuda-Apparent-Source-IP: 209.85.223.193 Received: by mail-ie0-f193.google.com with SMTP id 16so1659906iea.0 for ; Sun, 03 Mar 2013 13:08:29 -0800 (PST) X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=20120113; h=mime-version:x-received:reply-to:date:message-id:subject:from:to :content-type:x-gm-message-state; bh=ou2sdHwaC9NuzSeonN9aeLL/C0GPGnqnj0MEPI505QU=; b=RZ7CPuyuZ/9uI73eohht3GV6Q1wIyQ1exIdODqaGztlHzRQfZtfjR8oJPCDX+nRokj 9q50Rdrv/Kltk+wsYMT/NFRIRLmmlB/jJ28P6KKFT9cNdj0wGhxsdLk8H3xaTH4OIILX A3q6Xv5QoqOZHrdvIBG9VoE0Cr7bYkONiV6bvqhW1DNQX4uwZX4J9cCZuLu8uJ/kK8Xx wYpIG4sL3i/k7b5fDi6LOxSSYxlfsq5Q86zYt/vh40yw9CKt60LI4KFXlYm63GT+iBDF sVt8IB5nDzclNGdpWvQ1Wn98Cx5Xcv8KOW3iv/Zb3ruxVFkOHeKlYWRkkVX98UdHXEwV UPfQ== MIME-Version: 1.0 X-Received: by 10.50.41.167 with SMTP id g7mr803609igl.47.1362344909351; Sun, 03 Mar 2013 13:08:29 -0800 (PST) Received: by 10.64.231.40 with HTTP; Sun, 3 Mar 2013 13:08:29 -0800 (PST) Reply-To: smithjonesltd@live.com Date: Sun, 3 Mar 2013 23:08:29 +0200 Message-ID: Subject: price quotes. From: Smith Jones Ltd X-ASG-Orig-Subj: price quotes. To: undisclosed-recipients:; Content-Type: multipart/alternative; boundary=14dae93409b9625c2104d70ba4d0 X-Gm-Message-State: ALoCoQk4X+18FWczlgxnMlgbXdn8tFNarWjtCRFkQM6jw4LezTXQyASurTeabAcaQyQHibepxRC5 X-Barracuda-Connect: mail-ie0-f193.google.com[209.85.223.193] X-Barracuda-Start-Time: 1362344910 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.50 X-Barracuda-Spam-Status: No, SCORE=0.50 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_SA620a, HTML_MESSAGE X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124163 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 HTML_MESSAGE BODY: HTML included in message 0.50 BSF_SC0_SA620a Custom Rule SA620a --14dae93409b9625c2104d70ba4d0 Content-Type: text/plain; charset=ISO-8859-1 Hello, I saw your product and we are interested in purchasing. Kindly send us more detail and price quotes. We await your earliest response. Regard, Smith Jones Ltd. --14dae93409b9625c2104d70ba4d0 Content-Type: text/html; charset=ISO-8859-1
Hello,

I saw your product and we are interested in purchasing. Kindly send us more detail and price quotes.

We await your earliest response.

Regard,

Smith Jones Ltd.
--14dae93409b9625c2104d70ba4d0-- From sandeen@sandeen.net Sun Mar 3 16:04:51 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 6C5BE801D for ; Sun, 3 Mar 2013 16:04:51 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay3.corp.sgi.com (Postfix) with ESMTP id CB264AC001 for ; Sun, 3 Mar 2013 14:04:47 -0800 (PST) X-ASG-Debug-ID: 1362348286-04bdf0229612f440001-NocioJ Received: from sandeen.net (sandeen.net [63.231.237.45]) by cuda.sgi.com with ESMTP id FUHNRFJ0CtbYjVhn for ; Sun, 03 Mar 2013 14:04:46 -0800 (PST) X-Barracuda-Envelope-From: sandeen@sandeen.net X-Barracuda-Apparent-Source-IP: 63.231.237.45 Received: from liberator.sandeen.net (liberator.sandeen.net [10.0.0.4]) (using TLSv1 with cipher DHE-RSA-CAMELLIA256-SHA (256/256 bits)) (No client certificate requested) by sandeen.net (Postfix) with ESMTPSA id 181EF63C58E8; Sun, 3 Mar 2013 16:04:46 -0600 (CST) Message-ID: <5133C900.9050300@sandeen.net> Date: Sun, 03 Mar 2013 16:04:48 -0600 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: Richard Weinberger CC: Dave Chinner , linux-fsdevel@vger.kernel.org, xfs@oss.sgi.com Subject: Re: [PATCH] Do not check ocfs2 References: <1362269150-21478-1-git-send-email-richard@nod.at> <20130303011917.GI23616@dastard> <20130303100254.500b076f@spider.haslach.nod.at> X-ASG-Orig-Subj: Re: [PATCH] Do not check ocfs2 In-Reply-To: <20130303100254.500b076f@spider.haslach.nod.at> X-Enigmail-Version: 1.5 Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: sandeen.net[63.231.237.45] X-Barracuda-Start-Time: 1362348286 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124167 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On 3/3/13 3:02 AM, Richard Weinberger wrote: > Am Sun, 3 Mar 2013 12:19:17 +1100 > schrieb Dave Chinner : > >> On Sun, Mar 03, 2013 at 01:05:50AM +0100, Richard Weinberger wrote: >>> We cannot run fsck.ocfs2 because the file system >>> is most likely mounted on another node. >> >> This patch means that ocfs2 filesystems are *never* checked for >> consistency, even when you are testing them with exclusive local >> access. That defeats a primary function of xfstests - ensuring that >> the tests run do no corrupt the filesystem. >> >> Besides, why would you be running xfstests on a filesystem that is >> mounted on multiple nodes? Yes, ocfs2 is a cluster filesystem, but >> xfstests is designed to test local filesystem behaviour and is >> completely cluster naive. Hence having multiple nodes mount the >> filesystem that is being tested by xfstests does not serve any >> purpose at all. Further, turning off consistency checking for those >> that are running ocfs2 testing on single nodes means that testing is >> now mostly wasted as the majority of problems that can occur are no >> longer detectable.... > > Using xfstests I was able to trigger dlm issues in ocfs2. > I ran xfstests on one node and other nodes had it mounted too. Just for my own education, how does that happen? Were you testing on filesystems already configured into a cluster, or did the cluster somehow pick up your newly-defined test fileystems and mount them? How does fsck.ocfs2 behave when you run it on one node, when the fs is mounted on others? Will it proceed w/ no knowledge of the fact that it's mounted elsewhere? -Eric > To ensure that fsck.ocfs2 will not corrupt the filesystem I've applied > this patch. > > If you don't like the patch I'm perfectly fine with that. > Maybe it makes more sense to add a feature to xfstests which unmounts > the ocfs2 filesystem on all nodes (using SSH), then it is allowed to > run fsck.ocfs2. > > Thanks, > //richard > > _______________________________________________ > xfs mailing list > xfs@oss.sgi.com > http://oss.sgi.com/mailman/listinfo/xfs > From richard@nod.at Sun Mar 3 16:19:16 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 4547C801D for ; Sun, 3 Mar 2013 16:19:16 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay3.corp.sgi.com (Postfix) with ESMTP id 8709DAC002 for ; Sun, 3 Mar 2013 14:19:15 -0800 (PST) X-ASG-Debug-ID: 1362349148-04cbb07dbf125130001-NocioJ Received: from radon.swed.at (a.ns.miles-group.at [95.130.255.143]) by cuda.sgi.com with ESMTP id MTJDcR56Tt815L48 (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO) for ; Sun, 03 Mar 2013 14:19:11 -0800 (PST) X-Barracuda-Envelope-From: richard@nod.at X-Barracuda-Apparent-Source-IP: 95.130.255.143 Received: (qmail 15559 invoked by uid 89); 3 Mar 2013 22:19:12 -0000 Received: by simscan 1.3.1 ppid: 15552, pid: 15555, t: 0.1598s scanners: attach: 1.3.1 clamav: 0.96.5/m: Received: from unknown (HELO spider.haslach.nod.at) (richard@nod.at@212.186.22.124) by radon.swed.at with ESMTPA; 3 Mar 2013 22:19:12 -0000 Date: Sun, 3 Mar 2013 23:19:05 +0100 From: Richard Weinberger To: Eric Sandeen Cc: Dave Chinner , linux-fsdevel@vger.kernel.org, xfs@oss.sgi.com Subject: Re: [PATCH] Do not check ocfs2 Message-ID: <20130303231905.0efd6d08@spider.haslach.nod.at> X-ASG-Orig-Subj: Re: [PATCH] Do not check ocfs2 In-Reply-To: <5133C900.9050300@sandeen.net> References: <1362269150-21478-1-git-send-email-richard@nod.at> <20130303011917.GI23616@dastard> <20130303100254.500b076f@spider.haslach.nod.at> <5133C900.9050300@sandeen.net> X-Mailer: Claws Mail 3.8.1 (GTK+ 2.24.14; x86_64-suse-linux-gnu) Mime-Version: 1.0 Content-Type: text/plain; charset=US-ASCII Content-Transfer-Encoding: quoted-printable X-Barracuda-Connect: a.ns.miles-group.at[95.130.255.143] X-Barracuda-Start-Time: 1362349150 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124169 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- Am Sun, 03 Mar 2013 16:04:48 -0600 schrieb Eric Sandeen : > > Using xfstests I was able to trigger dlm issues in ocfs2. > > I ran xfstests on one node and other nodes had it mounted too. >=20 > Just for my own education, how does that happen? >=20 > Were you testing on filesystems already configured into a cluster, > or did the cluster somehow pick up your newly-defined test > fileystems and mount them? The cluster is already configured. But a single node can mount/unmount the fs as it wants. I know, xfstests is not a perfect test case for ocfs2 but it allowed me to trigger issues... These issues can also be triggered without xfstests. But in my case I found them using xfstests. > How does fsck.ocfs2 behave when you run it on one node, when the > fs is mounted on others? Will it proceed w/ no knowledge of the > fact that it's mounted elsewhere? It refuses to check the fs and exists with an error code !=3D 0. =46rom the manpage: -F By default fsck.ocfs2 will check with the cluster services to ensure that the volume is not in-use (mounted) on any node in the cluster before proceeding. -F skips this check and should only be used when it can be guaranteed that the volume is not mounted on any node in the cluster. WARNING: If the cluster check is disabled and the volume is mounted on one or more nodes, file system corruption is very likely. If unsure, do not use this option. Thanks, //richard From sandeen@sandeen.net Sun Mar 3 16:40:29 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 598708022 for ; Sun, 3 Mar 2013 16:40:29 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay3.corp.sgi.com (Postfix) with ESMTP id 447A6AC003 for ; Sun, 3 Mar 2013 14:40:28 -0800 (PST) X-ASG-Debug-ID: 1362350424-04cb6c2b02123cd0001-NocioJ Received: from sandeen.net (sandeen.net [63.231.237.45]) by cuda.sgi.com with ESMTP id 7IPShHi4QOVtJGmk for ; Sun, 03 Mar 2013 14:40:24 -0800 (PST) X-Barracuda-Envelope-From: sandeen@sandeen.net X-Barracuda-Apparent-Source-IP: 63.231.237.45 Received: from liberator.sandeen.net (liberator.sandeen.net [10.0.0.4]) (using TLSv1 with cipher DHE-RSA-CAMELLIA256-SHA (256/256 bits)) (No client certificate requested) by sandeen.net (Postfix) with ESMTPSA id E4C9963C58E8; Sun, 3 Mar 2013 16:40:23 -0600 (CST) Message-ID: <5133D15A.9010600@sandeen.net> Date: Sun, 03 Mar 2013 16:40:26 -0600 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: Richard Weinberger CC: Dave Chinner , linux-fsdevel@vger.kernel.org, xfs@oss.sgi.com Subject: Re: [PATCH] Do not check ocfs2 References: <1362269150-21478-1-git-send-email-richard@nod.at> <20130303011917.GI23616@dastard> <20130303100254.500b076f@spider.haslach.nod.at> <5133C900.9050300@sandeen.net> <20130303231905.0efd6d08@spider.haslach.nod.at> X-ASG-Orig-Subj: Re: [PATCH] Do not check ocfs2 In-Reply-To: <20130303231905.0efd6d08@spider.haslach.nod.at> X-Enigmail-Version: 1.5 Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: sandeen.net[63.231.237.45] X-Barracuda-Start-Time: 1362350424 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124169 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On 3/3/13 4:19 PM, Richard Weinberger wrote: > Am Sun, 03 Mar 2013 16:04:48 -0600 > schrieb Eric Sandeen : > > > Using xfstests I was able to trigger dlm issues in ocfs2. >>> I ran xfstests on one node and other nodes had it mounted too. >> >> Just for my own education, how does that happen? >> >> Were you testing on filesystems already configured into a cluster, >> or did the cluster somehow pick up your newly-defined test >> fileystems and mount them? > > The cluster is already configured. But a single node can mount/unmount > the fs as it wants. Ok, so: a) your cluster is already configured, and b) other nodes can mount cluster filesystems Sure, but - how *did* other nodes mount your xfstest filesystems? Or did you configure xfstests to use something already configured to be mounted on multiple nodes? Perhaps another related question - did the fs *need* to be mounted on other nodes to expose the problems you found? I'm just trying to understand if this is a common case, or unique to how you have configured things. > I know, xfstests is not a perfect test case for ocfs2 but it allowed me > to trigger issues... > These issues can also be triggered without xfstests. But in my case I > found them using xfstests. I understand, I'm not suggesting that you not run xfstests; I'm sure it is useful. It's supposed to be. :) We just need to keep it useful & not disable the consistency checks unless it's necessary. >> How does fsck.ocfs2 behave when you run it on one node, when the >> fs is mounted on others? Will it proceed w/ no knowledge of the >> fact that it's mounted elsewhere? > > It refuses to check the fs and exists with an error code != 0. Ok, then that confuses me a little, because earlier you said: > To ensure that fsck.ocfs2 will not corrupt the filesystem but just now you said it won't run at all? Anyway... > From the manpage: > -F By default fsck.ocfs2 will check with the cluster > services to ensure that the volume is not in-use (mounted) on any node > in the cluster before proceeding. -F skips this check and should only > be used when it can be guaranteed that the volume is not mounted on any > node in the cluster. WARNING: If the cluster check is disabled and the > volume is mounted on one or more nodes, file system corruption is very > likely. If unsure, do not use this option. Ok, but xfstests wasn't *using* -F was it? Anyway, what if you did something more along the lines of [pseudocode] ocfs2) if mounted.ocfs2 -f $TEST-DEV | frob_as_necessary[1] ; else fsck.ocfs2 $TEST-DEV fi ;; so that *if* it's mounted on some other node, the fsck won't run. That has downsides as Dave mentioned, but for the case where the xfstests node is the only one with it in use, it'll still do the beneficial consistency check. Just tweaking the fsck action bsed on *if* it's mounted (or, maybe, if the node is in a cluster?) might be a more generic solution that is widely applicable to all ocfs2 test environments. Thanks, -Eric [1] I know next to nothing about ocfs2, but presumably one can detect if the device in question is configured into, or mounted in, a cluster? > Thanks, > //richard > From richard@nod.at Sun Mar 3 16:53:46 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 6BE1D8024 for ; Sun, 3 Mar 2013 16:53:46 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id 53EEA304032 for ; Sun, 3 Mar 2013 14:53:46 -0800 (PST) X-ASG-Debug-ID: 1362351224-04cbb07dbd126ad0001-NocioJ Received: from radon.swed.at (a.ns.miles-group.at [95.130.255.143]) by cuda.sgi.com with ESMTP id zPSc37d8dpUsPZqF (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO) for ; Sun, 03 Mar 2013 14:53:44 -0800 (PST) X-Barracuda-Envelope-From: richard@nod.at X-Barracuda-Apparent-Source-IP: 95.130.255.143 Received: (qmail 15685 invoked by uid 89); 3 Mar 2013 22:53:57 -0000 Received: by simscan 1.3.1 ppid: 15678, pid: 15681, t: 0.1723s scanners: attach: 1.3.1 clamav: 0.96.5/m: Received: from unknown (HELO spider.haslach.nod.at) (richard@nod.at@212.186.22.124) by radon.swed.at with ESMTPA; 3 Mar 2013 22:53:57 -0000 Date: Sun, 3 Mar 2013 23:53:41 +0100 From: Richard Weinberger To: Eric Sandeen Cc: Dave Chinner , linux-fsdevel@vger.kernel.org, xfs@oss.sgi.com Subject: Re: [PATCH] Do not check ocfs2 Message-ID: <20130303235341.7470085e@spider.haslach.nod.at> X-ASG-Orig-Subj: Re: [PATCH] Do not check ocfs2 In-Reply-To: <5133D15A.9010600@sandeen.net> References: <1362269150-21478-1-git-send-email-richard@nod.at> <20130303011917.GI23616@dastard> <20130303100254.500b076f@spider.haslach.nod.at> <5133C900.9050300@sandeen.net> <20130303231905.0efd6d08@spider.haslach.nod.at> <5133D15A.9010600@sandeen.net> X-Mailer: Claws Mail 3.8.1 (GTK+ 2.24.14; x86_64-suse-linux-gnu) Mime-Version: 1.0 Content-Type: text/plain; charset=US-ASCII Content-Transfer-Encoding: 7bit X-Barracuda-Connect: a.ns.miles-group.at[95.130.255.143] X-Barracuda-Start-Time: 1362351224 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124171 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- Am Sun, 03 Mar 2013 16:40:26 -0600 schrieb Eric Sandeen : > On 3/3/13 4:19 PM, Richard Weinberger wrote: > > Am Sun, 03 Mar 2013 16:04:48 -0600 > > schrieb Eric Sandeen : > > > > Using xfstests I was able to trigger dlm issues in ocfs2. > >>> I ran xfstests on one node and other nodes had it mounted too. > >> > >> Just for my own education, how does that happen? > >> > >> Were you testing on filesystems already configured into a cluster, > >> or did the cluster somehow pick up your newly-defined test > >> fileystems and mount them? > > > > The cluster is already configured. But a single node can > > mount/unmount the fs as it wants. > > Ok, so: > a) your cluster is already configured, and > b) other nodes can mount cluster filesystems Correct. > Sure, but - how *did* other nodes mount your xfstest filesystems? > Or did you configure xfstests to use something already configured > to be mounted on multiple nodes? > > Perhaps another related question - did the fs *need* to be mounted > on other nodes to expose the problems you found? Yes, seems so. > I'm just trying to understand if this is a common case, or unique to > how you have configured things. > > > I know, xfstests is not a perfect test case for ocfs2 but it > > allowed me to trigger issues... > > These issues can also be triggered without xfstests. But in my case > > I found them using xfstests. > > I understand, I'm not suggesting that you not run xfstests; I'm sure > it is useful. It's supposed to be. :) We just need to keep it > useful & not disable the consistency checks unless it's necessary. Fair point. > >> How does fsck.ocfs2 behave when you run it on one node, when the > >> fs is mounted on others? Will it proceed w/ no knowledge of the > >> fact that it's mounted elsewhere? > > > > It refuses to check the fs and exists with an error code != 0. > > Ok, then that confuses me a little, because earlier you said: > > > To ensure that fsck.ocfs2 will not corrupt the filesystem > > but just now you said it won't run at all? Anyway... In the first test run I faced a filesystem corruption and blamed fsck.ocfs2. After writing the mail I realized that fsck.ocfs2 aborted and the corruption came from another issue. Sorry for being imprecise. > > From the manpage: > > -F By default fsck.ocfs2 will check with the cluster > > services to ensure that the volume is not in-use (mounted) on any > > node in the cluster before proceeding. -F skips this check and > > should only be used when it can be guaranteed that the volume is > > not mounted on any node in the cluster. WARNING: If the cluster > > check is disabled and the volume is mounted on one or more nodes, > > file system corruption is very likely. If unsure, do not use this > > option. > > Ok, but xfstests wasn't *using* -F was it? Correct. > Anyway, what if you did something more along the lines of [pseudocode] > > ocfs2) > if mounted.ocfs2 -f $TEST-DEV | frob_as_necessary[1] > ; > else > fsck.ocfs2 $TEST-DEV > fi > ;; > > so that *if* it's mounted on some other node, the fsck won't run. > That has downsides as Dave mentioned, but for the case where the > xfstests node is the only one with it in use, it'll still do the > beneficial consistency check. > > Just tweaking the fsck action bsed on *if* it's mounted (or, > maybe, if the node is in a cluster?) might be a more generic solution > that is widely applicable to all ocfs2 test environments. Good point. mounted.ocfs2 really makes sense. I'll implement this on my test suite and submit a new patch. > Thanks, > -Eric > > [1] I know next to nothing about ocfs2, but presumably one can detect > if the device in question is configured into, or mounted in, a > cluster? I'll find out! Thanks, //richard From sandeen@sandeen.net Sun Mar 3 16:57:54 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id A475C8024 for ; Sun, 3 Mar 2013 16:57:54 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay3.corp.sgi.com (Postfix) with ESMTP id BB161AC001 for ; Sun, 3 Mar 2013 14:57:53 -0800 (PST) X-ASG-Debug-ID: 1362351473-04bdf022981327a0001-NocioJ Received: from sandeen.net (sandeen.net [63.231.237.45]) by cuda.sgi.com with ESMTP id x1Q3E9mecoCCVHII for ; Sun, 03 Mar 2013 14:57:53 -0800 (PST) X-Barracuda-Envelope-From: sandeen@sandeen.net X-Barracuda-Apparent-Source-IP: 63.231.237.45 Received: from liberator.sandeen.net (liberator.sandeen.net [10.0.0.4]) (using TLSv1 with cipher DHE-RSA-CAMELLIA256-SHA (256/256 bits)) (No client certificate requested) by sandeen.net (Postfix) with ESMTPSA id F30CF63C58E8; Sun, 3 Mar 2013 16:57:52 -0600 (CST) Message-ID: <5133D573.3050106@sandeen.net> Date: Sun, 03 Mar 2013 16:57:55 -0600 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: Richard Weinberger CC: Dave Chinner , linux-fsdevel@vger.kernel.org, xfs@oss.sgi.com Subject: Re: [PATCH] Do not check ocfs2 References: <1362269150-21478-1-git-send-email-richard@nod.at> <20130303011917.GI23616@dastard> <20130303100254.500b076f@spider.haslach.nod.at> <5133C900.9050300@sandeen.net> <20130303231905.0efd6d08@spider.haslach.nod.at> <5133D15A.9010600@sandeen.net> <20130303235341.7470085e@spider.haslach.nod.at> X-ASG-Orig-Subj: Re: [PATCH] Do not check ocfs2 In-Reply-To: <20130303235341.7470085e@spider.haslach.nod.at> X-Enigmail-Version: 1.5 Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: sandeen.net[63.231.237.45] X-Barracuda-Start-Time: 1362351473 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124171 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On 3/3/13 4:53 PM, Richard Weinberger wrote: >> Anyway, what if you did something more along the lines of [pseudocode] >> >> ocfs2) >> if mounted.ocfs2 -f $TEST-DEV | frob_as_necessary[1] >> ; >> else >> fsck.ocfs2 $TEST-DEV >> fi >> ;; >> >> so that *if* it's mounted on some other node, the fsck won't run. >> That has downsides as Dave mentioned, but for the case where the >> xfstests node is the only one with it in use, it'll still do the >> beneficial consistency check. >> >> Just tweaking the fsck action bsed on *if* it's mounted (or, >> maybe, if the node is in a cluster?) might be a more generic solution >> that is widely applicable to all ocfs2 test environments. > > Good point. mounted.ocfs2 really makes sense. I'll implement this on my > test suite and submit a new patch. Sounds good to me. It'd be most preferable to do a cluster-wide unmount and fsck, but if that's unfeasible, then skipping the fsck (with a warning) is still preferable to simply disabling it outright for everyone. Thanks, -Eric From david@fromorbit.com Sun Mar 3 17:36:26 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id AAB87801D for ; Sun, 3 Mar 2013 17:36:26 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay1.corp.sgi.com (Postfix) with ESMTP id 7B2888F8035 for ; Sun, 3 Mar 2013 15:36:23 -0800 (PST) X-ASG-Debug-ID: 1362353777-04bdf022981347a0001-NocioJ Received: from ipmail07.adl2.internode.on.net (ipmail07.adl2.internode.on.net [150.101.137.131]) by cuda.sgi.com with ESMTP id DviYysEvaOXgryiI for ; Sun, 03 Mar 2013 15:36:18 -0800 (PST) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.131 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: Am4OANndM1F5LFKb/2dsb2JhbABFhWe3SoUZexdzgh8BAQUnExwjEAgDGAklDwUlAyETiBLHLRWOKSI9B4NAA5ZFiWWHCIMc Received: from ppp121-44-82-155.lns20.syd6.internode.on.net (HELO dastard) ([121.44.82.155]) by ipmail07.adl2.internode.on.net with ESMTP; 04 Mar 2013 10:06:17 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UCIRz-00042d-GV; Mon, 04 Mar 2013 10:36:15 +1100 Date: Mon, 4 Mar 2013 10:36:15 +1100 From: Dave Chinner To: Eric Sandeen Cc: xfs-oss , Ole Tange Subject: Re: [PATCH V2] xfs_repair: skip freelist scan of corrupt agf in no-modify mode Message-ID: <20130303233615.GK26081@dastard> X-ASG-Orig-Subj: Re: [PATCH V2] xfs_repair: skip freelist scan of corrupt agf in no-modify mode References: <51313DE8.5080104@sandeen.net> <51326DC0.8030403@sandeen.net> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <51326DC0.8030403@sandeen.net> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail07.adl2.internode.on.net[150.101.137.131] X-Barracuda-Start-Time: 1362353778 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124173 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Sat, Mar 02, 2013 at 03:23:12PM -0600, Eric Sandeen wrote: > In xfs_repair's no-modify mode (-n), verify_set_agf doesn't fix up > bad freelist blocks that it finds. When we get to scan_freelist, > this can wreak havoc if, for example, first > last and the loop > never exits; we index agfl->agfl_bno[i] off into the weeds. > > To fix this, re-check the values in no-modify mode, and if > they're off, warn about it and skip the scan. > > Reported-by: Ole Tange > Signed-off-by: Eric Sandeen > --- > > V2: Remove dumb mistakes :/ > > diff --git a/repair/scan.c b/repair/scan.c > index 5345094..1d39bdc 100644 > --- a/repair/scan.c > +++ b/repair/scan.c > @@ -1066,6 +1066,18 @@ scan_freelist( > return; > } > agfl = XFS_BUF_TO_AGFL(agflbuf); > + > + if (no_modify) { > + /* agf values not fixed in verify_set_agf, so recheck */ > + if (be32_to_cpu(agf->agf_flfirst) >= XFS_AGFL_SIZE(mp) || > + be32_to_cpu(agf->agf_fllast) >= XFS_AGFL_SIZE(mp)) { > + do_warn(_("agf %d freelist blocks bad, skipping " > + "freelist scan\n"), i); > + return; > + } > + } else /* should have been fixed in verify_set_agf() */ > + ASSERT(0); > + > i = be32_to_cpu(agf->agf_flfirst); > count = 0; > for (;;) { Looks ok, but IIRC there are overruns in these functions for the same reason (i.e. unchecked use of agf->agf_flfirst as an array index) db/check.c::scan_freelist() db/freesp.c::scan_freelist() I found lots of almost-but-not-quite-exact code duplication like this recenty when doing CRC updates to the userspace code.... Cheers, Dave. -- Dave Chinner david@fromorbit.com From lankolp@nash.com Sun Mar 3 17:54:12 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=HTML_MESSAGE autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id D0E1C802A for ; Sun, 3 Mar 2013 17:54:12 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay1.corp.sgi.com (Postfix) with ESMTP id A4E1B8F8035 for ; Sun, 3 Mar 2013 15:54:12 -0800 (PST) X-ASG-Debug-ID: 1362354849-04cb6c2b04127540001-NocioJ Received: from mailserver.hostland.ru (mail.hostland.ru [77.234.201.83]) by cuda.sgi.com with ESMTP id JUc2lv64S9cT4x19 (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO) for ; Sun, 03 Mar 2013 15:54:11 -0800 (PST) X-Barracuda-Envelope-From: lankolp@nash.com X-Barracuda-Apparent-Source-IP: 77.234.201.83 Received: from Unknown (unknown [183.60.255.203]) (Authenticated sender: info@karpovguitar.ru) by mailserver.hostland.ru (Postfix) with ESMTPA id 59F2F525DF; Mon, 4 Mar 2013 03:54:03 +0400 (GMT-4) Message-ID: Reply-To: =?windows-1251?B?6O3i5fHy7vA=?= From: =?windows-1251?B?6O3i5fHy7vA=?= To: , , , Subject: =?windows-1251?B?7/Du9uXk8/DgIO/u6/P35e3o/yDw4Ofw5fjl?= =?windows-1251?B?7ej/IO3gIPHy8O7o8uXr/PHy4u4=?= Date: Sun, 3 Mar 2013 15:54:06 -0800 X-ASG-Orig-Subj: =?windows-1251?B?7/Du9uXk8/DgIO/u6/P35e3o/yDw4Ofw5fjl?= =?windows-1251?B?7ej/IO3gIPHy8O7o8uXr/PHy4u4=?= MIME-Version: 1.0 Content-Type: multipart/alternative; boundary="----=_NextPart_000_1AEA_01CE1827.55E05740" X-Priority: 3 X-MSMail-Priority: Normal X-Mailer: Microsoft Windows Mail 6.0.6001.18416 X-MimeOLE: Produced By Microsoft MimeOLE V6.0.6001.18645 X-Barracuda-Connect: mail.hostland.ru[77.234.201.83] X-Barracuda-Start-Time: 1362354850 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=HTML_MESSAGE X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124175 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 HTML_MESSAGE BODY: HTML included in message This is a multi-part message in MIME format. ------=_NextPart_000_1AEA_01CE1827.55E05740 Content-Type: text/plain; charset="windows-1251" Content-Transfer-Encoding: quoted-printable =CF=F0=E8=E3=EB=E0=F8=E0=E5=EC =C2=E0=F1 =ED=E0 =F1=E5=EC=E8=ED=E0=F0 =EF= =EE =F1=F2=F0=EE=E8=F2=E5=EB=FC=ED=EE=EC=F3 =ED=E0=E4=E7=EE=F0=F3 =E8 =FD= =EA=F1=EF=E5=F0=F2=E8=E7=E5, =F1=F2=F0=EE=E8=F2=E5=EB=FC=ED=FB=EC =ED=EE=F0= =EC=E0=EC =E8 =EF=F0=E0=E2=E8=EB=E0=EC =E2 =CF=C5=D2=C5=D0=C1=D3=D0=C3=C5= ! =C8=E7=EC=E5=ED=E5=ED=E8=FF =E7=E0=EA=EE=ED=EE=E4=E0=F2=E5=EB=FC=F1=F2=E2= =E0, =F0=E5=E3=F3=EB=E8=F0=F3=FE=F9=E5=E3=EE =E3=F0=E0=E4=EE=F1=F2=F0=EE=E8= =F2=E5=EB=FC=ED=F3=FE =E4=E5=FF=F2=E5=EB=FC=ED=EE=F1=F2=FC, =E7=E0=F2=F0=E0= =E3=E8=E2=E0=FE=F2 =EC=ED=EE=E6=E5=F1=F2=E2=EE =E2=E0=E6=ED=FB=F5 =EF=F0=EE= =F6=E5=E4=F3=F0 =EF=F0=EE=E5=EA=F2=E8=F0=EE=E2=E0=ED=E8=FF, =F1=EE=E3=EB=E0= =F1=EE=E2=E0=ED=E8=FF, =F1=F2=F0=EE=E8=F2=E5=EB=FC=F1=F2=E2=E0 =E8 =E2=E2= =EE=E4=E0 =E2 =FD=EA=F1=EF=EB=F3=E0=F2=E0=F6=E8=FE =EE=E1=FA=E5=EA=F2=EE=E2= =ED=E5=E4=E2=E8=E6=E8=EC=EE=F1=F2=E8. =CD=E0 =F1=E5=EC=E8=ED=E0=F0=E5 =F2=E0=EA=E6=E5 =E1=F3=E4=F3=F2 =EF=EE=E4= =F0=EE=E1=ED=EE =F0=E0=F1=F1=EC=EE=F2=F0=E5=ED=FB =F2=E5=EC=FB =F1=EC=E5=F2= =ED=EE=E3=EE =E4=E5=EB=E0 =E8 =F6=E5=ED=EE=EE=E1=F0=E0=E7=EE=E2=E0=ED=E8=FF= , =F1=F2=F0=EE=E8=F2=E5=EB=FC=ED=FB=F5 =EF=F0=E0=E2=E8=EB =E8 =ED=EE=F0=EC= , =E0 =F2=E0=EA=E6=E5 =E8=E7=F3=F7=E5=ED=FB =F2=E5=F5=ED=E8=F7=E5=F1=EA=E8= =E5 =F0=E5=E3=EB=E0=EC=E5=ED=F2=FB =F2=E0=EC=EE=E6=E5=ED=ED=EE=E3=EE =F1=EE= =FE=E7=E0 =E2 =EE=E1=EB=E0=F1=F2=E8 =F1=F2=F0=EE=E8=F2=E5=EB=FC=F1=F2=E2=E0= =E8 =E1=E5=E7=EE=EF=E0=F1=ED=EE=F1=F2=E8. =CE=E1=F3=F7=E5=ED=E8=E5 =F1=EE=F1=F2=EE=E8=F2=F1=FF =E2 =EF=E5=F0=E8=EE=E4= =F1 25 =EF=EE 26 =EC=E0=F0=F2=E0 2Ol=C7=E3. =E2 =E3.=CF=C5=D2=C5=D0= =C1=D3=D0=C3. =C2=FB =F3=E7=ED=E0=E5=F2=E5: - =F0=F3=EA=EE=E2=EE=E4=FF=F9=E8=E5 =E4=EE=EA=F3=EC=E5=ED=F2=FB: =E3=EE=F1= =F1=F2=F0=EE=E9=ED=E0=E4=E7=EE=F0, =FD=EA=F1=EF=E5=F0=F2=E8=E7=E0; - =D4=C7 N 243-=D4=C7 =EE=F2 18 =E8=FE=EB=FF 2011 =E3=EE=E4=E0; =ED=EE=E2= =FB=E5 =EF=F0=E0=E2=E8=EB=E0 =E0=F0=F5=E8=F2=E5=EA=F2=F3=F0=ED=EE-=F1=F2=F0= =EE=E8=F2=E5=EB=FC=ED=EE=E3=EE =EF=F0=EE=E5=EA=F2=E8=F0=EE=E2=E0=ED=E8=FF= ; - =EF=EE=F0=FF=E4=EE=EA =E2=E7=E0=E8=EC=EE=E4=E5=E9=F1=F2=E2=E8=FF =F1=EB= =F3=E6=E1 =E3=EE=F1=F3=E4=E0=F0=F1=F2=E2=E5=ED=ED=EE=E3=EE =F1=F2=F0=EE=E8= =F2=E5=EB=FC=ED=EE=E3=EE =ED=E0=E4=E7=EE=F0=E0 =E8 =ED=E5=E3=EE=F1=F3=E4=E0= =F0=F1=F2=E2=E5=ED=ED=EE=E9 =FD=EA=F1=EF=E5=F0=F2=E8=E7=FB; - =E0=EB=E3=EE=F0=E8=F2=EC =E2=E7=E0=E8=EC=EE=E4=E5=E9=F1=F2=E2=E8=FF =F1= =FD=EA=F1=EF=E5=F0=F2=E8=E7=EE=E9 =E8 =E3=EE=F1=F1=F2=F0=EE=E9=ED=E0=E4=E7= =EE=F0=EE=EC; - =E8=E7=EC=E5=ED=E5=ED=E8=FF =E2 =C3=F0=E0=E4=EE=F1=F2=F0=EE=E8=F2=E5=EB= =FC=ED=FB=E9 =EA=EE=E4=E5=EA=F1; - =CF=EE=F0=FF=E4=EE=EA =F1=EE=E3=EB=E0=F1=EE=E2=E0=ED=E8=FF =E8 =E2=FB=E4= =E0=F7=E8 =F0=E0=E7=F0=E5=F8=E5=ED=E8=FF =ED=E0 =F1=F2=F0=EE=E8=F2=E5=EB=FC= =F1=F2=E2=EE; - =E0=E4=EC=E8=ED=E8=F1=F2=F0=E0=F2=E8=E2=ED=E0=FF =EE=F2=E2=E5=F2=F1=F2=E2= =E5=ED=ED=EE=F1=F2=FC; - =F1=EC=E5=F2=ED=E0=FF =F7=E0=F1=F2=FC =EF=F0=EE=E5=EA=F2=ED=EE-=F1=EC=E5= =F2=ED=EE=E9 =E4=EE=EA=F3=EC=E5=ED=F2=E0=F6=E8=E8; =D2=E0=EA=E6=E5 =ED=E0 =EA=F3=F0=F1=E5 =C2=E0=F1 =E6=E4=E5=F2 =EF=EE=E4=F0= =EE=E1=ED=FB=E9 =EE=E1=E7=EE=F0 =E8 =F0=E0=E7=E1=EE=F0 =F1=EE=E2=F0=E5=EC= =E5=ED=ED=EE=E9 =E7=E0=EA=EE=ED=EE=E4=E0=F2=E5=EB=FC=ED=EE-=ED=EE=F0=EC=E0= =F2=E8=E2=ED=EE=E9 =E1=E0=E7=FB =E8=ED=E2=E5=F1=F2=E8=F6=E8=EE=ED=ED=EE-=F1= =F2=F0=EE=E8=F2=E5=EB=FC=ED=EE=E3=EE =EF=F0=EE=F6=E5=F1=F1=E0. =D0=E0=F1=EF=E8=F1=E0=ED=E8=E5, =EF=F0=EE=E3=F0=E0=EC=EC=E0, =F0=E5=E3=E8= =F1=F2=F0=E0=F6=E8=FF: 8 * =CF=E5=F2=E5=F0=E1=F3=F0=E3 * 98= =3D7 . 8=C7 - l7 =20 ------=_NextPart_000_1AEA_01CE1827.55E05740 Content-Type: text/html; charset="windows-1251" Content-Transfer-Encoding: quoted-printable

=CF=F0=E8= =E3=EB=E0=F8=E0=E5=EC =C2=E0=F1 =ED=E0 =F1=E5=EC=E8=ED=E0=F0 =EF=EE =F1=F2= =F0=EE=E8=F2=E5=EB=FC=ED=EE=EC=F3 =ED=E0=E4=E7=EE=F0=F3 =E8 =FD=EA=F1=EF=E5= =F0=F2=E8=E7=E5, =F1=F2=F0=EE=E8=F2=E5=EB=FC=ED=FB=EC =ED=EE=F0=EC=E0=EC = =E8 =EF=F0=E0=E2=E8=EB=E0=EC =E2 =CF=C5=D2=C5=D0=C1=D3=D0=C3=C5! <= div> =C8=E7=EC=E5=ED=E5=ED=E8=FF =E7=E0=EA=EE=ED=EE=E4=E0=F2=E5=EB=FC=F1=F2= =E2=E0, =F0=E5=E3=F3=EB=E8=F0=F3=FE=F9=E5=E3=EE =E3=F0=E0=E4=EE=F1=F2=F0=EE= =E8=F2=E5=EB=FC=ED=F3=FE =E4=E5=FF=F2=E5=EB=FC=ED=EE=F1=F2=FC, =E7=E0=F2=F0= =E0=E3=E8=E2=E0=FE=F2 =EC=ED=EE=E6=E5=F1=F2=E2=EE =E2=E0=E6=ED=FB=F5 =EF=F0= =EE=F6=E5=E4=F3=F0 =EF=F0=EE=E5=EA=F2=E8=F0=EE=E2=E0=ED=E8=FF, =F1=EE=E3=EB= =E0=F1=EE=E2=E0=ED=E8=FF, =F1=F2=F0=EE=E8=F2=E5=EB=FC=F1=F2=E2=E0 =E8 =E2= =E2=EE=E4=E0 =E2 =FD=EA=F1=EF=EB=F3=E0=F2=E0=F6=E8=FE =EE=E1=FA=E5=EA=F2=EE= =E2 =ED=E5=E4=E2=E8=E6=E8=EC=EE=F1=F2=E8.

=CD=E0 =F1=E5=EC=E8= =ED=E0=F0=E5 =F2=E0=EA=E6=E5 =E1=F3=E4=F3=F2 =EF=EE=E4=F0=EE=E1=ED=EE =F0= =E0=F1=F1=EC=EE=F2=F0=E5=ED=FB =F2=E5=EC=FB =F1=EC=E5=F2=ED=EE=E3=EE =E4=E5= =EB=E0 =E8 =F6=E5=ED=EE=EE=E1=F0=E0=E7=EE=E2=E0=ED=E8=FF, =F1=F2=F0=EE=E8= =F2=E5=EB=FC=ED=FB=F5 =EF=F0=E0=E2=E8=EB =E8 =ED=EE=F0=EC, =E0 =F2=E0=EA=E6= =E5 =E8=E7=F3=F7=E5=ED=FB =F2=E5=F5=ED=E8=F7=E5=F1=EA=E8=E5 =F0=E5=E3=EB=E0= =EC=E5=ED=F2=FB =F2=E0=EC=EE=E6=E5=ED=ED=EE=E3=EE =F1=EE=FE=E7=E0 =E2 =EE= =E1=EB=E0=F1=F2=E8 =F1=F2=F0=EE=E8=F2=E5=EB=FC=F1=F2=E2=E0 =E8 =E1=E5=E7=EE= =EF=E0=F1=ED=EE=F1=F2=E8.

=CE=E1=F3=F7=E5=ED=E8=E5 =F1=EE=F1=F2=EE=E8=F2= =F1=FF =E2 =EF=E5=F0=E8=EE=E4 =F1 25 =EF=EE 26 =EC=E0=F0=F2=E0 2Ol=C7= =E3. =E2 =E3.=CF=C5=D2=C5=D0=C1=D3=D0=C3.

=C2=FB =F3=E7=ED=E0=E5= =F2=E5:

- =F0=F3=EA=EE=E2=EE=E4=FF=F9=E8=E5 =E4=EE=EA=F3=EC=E5= =ED=F2=FB: =E3=EE=F1=F1=F2=F0=EE=E9=ED=E0=E4=E7=EE=F0, =FD=EA=F1=EF=E5=F0= =F2=E8=E7=E0;
- =D4=C7 N 243-=D4=C7 =EE=F2 18 =E8=FE=EB=FF 2= 011 =E3=EE=E4=E0; =ED=EE=E2=FB=E5 =EF=F0=E0=E2=E8=EB=E0 =E0=F0=F5=E8=F2=E5= =EA=F2=F3=F0=ED=EE-=F1=F2=F0=EE=E8=F2=E5=EB=FC=ED=EE=E3=EE =EF=F0=EE=E5=EA= =F2=E8=F0=EE=E2=E0=ED=E8=FF;
- =EF=EE=F0=FF=E4=EE=EA =E2=E7=E0= =E8=EC=EE=E4=E5=E9=F1=F2=E2=E8=FF =F1=EB=F3=E6=E1 =E3=EE=F1=F3=E4=E0=F0=F1= =F2=E2=E5=ED=ED=EE=E3=EE =F1=F2=F0=EE=E8=F2=E5=EB=FC=ED=EE=E3=EE =ED=E0=E4= =E7=EE=F0=E0 =E8 =ED=E5=E3=EE=F1=F3=E4=E0=F0=F1=F2=E2=E5=ED=ED=EE=E9 =FD=EA= =F1=EF=E5=F0=F2=E8=E7=FB;
- =E0=EB=E3=EE=F0=E8=F2=EC =E2=E7=E0= =E8=EC=EE=E4=E5=E9=F1=F2=E2=E8=FF =F1 =FD=EA=F1=EF=E5=F0=F2=E8=E7=EE=E9 =E8= =E3=EE=F1=F1=F2=F0=EE=E9=ED=E0=E4=E7=EE=F0=EE=EC;
- =E8=E7=EC= =E5=ED=E5=ED=E8=FF =E2 =C3=F0=E0=E4=EE=F1=F2=F0=EE=E8=F2=E5=EB=FC=ED=FB=E9= =EA=EE=E4=E5=EA=F1;
- =CF=EE=F0=FF=E4=EE=EA =F1=EE=E3=EB=E0= =F1=EE=E2=E0=ED=E8=FF =E8 =E2=FB=E4=E0=F7=E8 =F0=E0=E7=F0=E5=F8=E5=ED=E8=FF= =ED=E0 =F1=F2=F0=EE=E8=F2=E5=EB=FC=F1=F2=E2=EE;
- =E0=E4=EC= =E8=ED=E8=F1=F2=F0=E0=F2=E8=E2=ED=E0=FF =EE=F2=E2=E5=F2=F1=F2=E2=E5=ED=ED= =EE=F1=F2=FC;
- =F1=EC=E5=F2=ED=E0=FF =F7=E0=F1=F2=FC =EF=F0= =EE=E5=EA=F2=ED=EE-=F1=EC=E5=F2=ED=EE=E9 =E4=EE=EA=F3=EC=E5=ED=F2=E0=F6=E8= =E8;
=D2=E0=EA=E6=E5 =ED=E0 =EA=F3=F0=F1=E5 =C2=E0=F1 =E6=E4= =E5=F2 =EF=EE=E4=F0=EE=E1=ED=FB=E9 =EE=E1=E7=EE=F0 =E8 =F0=E0=E7=E1=EE=F0= =F1=EE=E2=F0=E5=EC=E5=ED=ED=EE=E9 =E7=E0=EA=EE=ED=EE=E4=E0=F2=E5=EB=FC=ED= =EE-=ED=EE=F0=EC=E0=F2=E8=E2=ED=EE=E9 =E1=E0=E7=FB =E8=ED=E2=E5=F1=F2=E8=F6= =E8=EE=ED=ED=EE-=F1=F2=F0=EE=E8=F2=E5=EB=FC=ED=EE=E3=EE =EF=F0=EE=F6=E5=F1= =F1=E0.

=D0=E0=F1=EF=E8=F1=E0=ED=E8=E5, =EF=F0=EE=E3=F0=E0=EC=EC= =E0, =F0=E5=E3=E8=F1=F2=F0=E0=F6=E8=FF: 8 * =CF=E5=F2=E5=F0=E1=F3= =F0=E3 * 98=3D7 . 8=C7 - l7

------=_NextPart_000_1AEA_01CE1827.55E05740-- From david@fromorbit.com Sun Mar 3 18:31:37 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id D8DE6802C for ; Sun, 3 Mar 2013 18:31:37 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id C00AF304039 for ; Sun, 3 Mar 2013 16:31:37 -0800 (PST) X-ASG-Debug-ID: 1362357095-04cbb07dbf12b2e0001-NocioJ Received: from ipmail07.adl2.internode.on.net (ipmail07.adl2.internode.on.net [150.101.137.131]) by cuda.sgi.com with ESMTP id ZwHXTixqQKdZ28Gf for ; Sun, 03 Mar 2013 16:31:36 -0800 (PST) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.131 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AnAOACHqM1F5LFKb/2dsb2JhbABFhWe3SYUZexdzgh8BAQQBJxMcIwULCAMYCSUPBSUDIRMbh3IFDcclFY1BAQZhIj0Hg0ADlkWQbYMcgVUBHw Received: from ppp121-44-82-155.lns20.syd6.internode.on.net (HELO dastard) ([121.44.82.155]) by ipmail07.adl2.internode.on.net with ESMTP; 04 Mar 2013 11:01:35 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UCJJW-00048O-5L; Mon, 04 Mar 2013 11:31:34 +1100 Date: Mon, 4 Mar 2013 11:31:34 +1100 From: Dave Chinner To: Mark Tinguely Cc: xfs@oss.sgi.com Subject: Re: [PATCH] xfs: logsunit rounding causes iclog corruption/crash Message-ID: <20130304003134.GJ23616@dastard> X-ASG-Orig-Subj: Re: [PATCH] xfs: logsunit rounding causes iclog corruption/crash References: <20130302201446.854313570@sgi.com> <20130302201452.236378200@sgi.com> <20130302230513.GH23616@dastard> <51339EC7.1000509@sgi.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <51339EC7.1000509@sgi.com> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail07.adl2.internode.on.net[150.101.137.131] X-Barracuda-Start-Time: 1362357095 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124177 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Sun, Mar 03, 2013 at 01:04:39PM -0600, Mark Tinguely wrote: > On 03/02/13 17:05, Dave Chinner wrote: > >On Sat, Mar 02, 2013 at 02:14:47PM -0600, Mark Tinguely wrote: > >>When the iclog buffer size and log stripe unit are both defined and > >>the log stripe unit is less the log buffer size then the buffer is > >>rounded up to the log stripe unit size during the xlog_sync(). > >> > >>This rounding can exceed the iclog buffer length and in xlog_data_pack(): > >> 1) Cause corruption inside the iclog buffer because there will not be > >> enough space for the headers in the front of the iclog buffer for > >> the rounding. > >> 2) Cause corruption in memory that follows the iclog buffer when > >> stamping the lsn in each of the rounded blocks. > >> 3) If CONFIG_XFS_DEBUG is defined will cause a crash in xlog_verify_iclog(). > >> 4) Cause page fault crash if the memory after the buffer is not mapped. ... > >If the user has specified an invalid log buffer size, then reject it > >with: > > > >logbsize XXX is not an integer multiple of the log stripe unit YYY > > > >Rounding means that the user isn't getting what they want and they > >may not realise it. If they make a mistake, they should be informed > >and forced to fix it before going any further. > > The code already silently changes the log blocksize if > mp->m_sb.sb_logsunit > mp->m_logbsize. Where? It only changes m_logbsize if it is <= 0, which means the user has not specified the value as a mount option and hence we are free to chose whatever value we want. > IMO, it should fix it not a multiple too. ENOPARSE. :/ FWIW, a further argument against the rounding approach is this: the iclogbuf size supplied to mount is constrainted to be a power of 2 size. if (mp->m_logbsize != -1 && mp->m_logbsize != 0 && (mp->m_logbsize < XLOG_MIN_RECORD_BSIZE || mp->m_logbsize > XLOG_MAX_RECORD_BSIZE || !is_power_of_2(mp->m_logbsize))) { xfs_warn(mp, "invalid logbufsize: %d [not 16k,32k,64k,128k or 256k]", mp->m_logbsize); return XFS_ERROR(EINVAL); } This constraint appears to be a feature of the original log stripe unit code that did only support power-of-2 log stripe units. However, that was removed way back in 2004: http://oss.sgi.com/cgi-bin/gitweb.cgi?p=archive/xfs-import.git;a=commitdiff;h=d3037d91429cc2ea383f8a2736c86ed9f1eec542 That commit introduced the very rounding code in xlog_sync() that is causing the crash you are trying to address right now. i.e. this code: count = XLOG_LSUNITTOB(log, XLOG_BTOLSUNIT(log, count_init)); IOWs, it makes no sense to only allow power-of-2 logbsize options if we then round it to something completely different. The above commit makes it pretty clear that the intent is that logbsize should be an exact integer multiple of the log stripe unit - which it is if no logbsize mount option is given - but our mount option parsing does not reflect this at all. Personally, I'd prefer that logbsize be limited to power-of-2 multiples of the lsunit or XLOG_MIN_RECORD_BSIZE (if lsunit = 0) as allowing arbitrary values to be specified by users leads to a testing and bug triage nightmare. If we are not going to change the power-of-2 logbsize mount option requirement, then I think that the correct solution is to make the log limit the iclogbuf size internally to power-of-2 multiples of the lsunit so that it is not at all externally visible (e.g. /proc/self/mounts shows exactly what came in as a mount option). This problem really has nothing to do with what mount options are specified and passed to the log - the log is separate code with it's own internal constraints and hence should be ensuring that it's setup is consistent with those constraints.... Further, if we really need to know what iclogbuf size the log is using on disk, both the physical iclogbuf size and the size of the current write gets written into every log header block.... Cheers, Dave. -- Dave Chinner david@fromorbit.com From david@fromorbit.com Sun Mar 3 18:46:37 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id C0627802E for ; Sun, 3 Mar 2013 18:46:37 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay3.corp.sgi.com (Postfix) with ESMTP id 4F012AC003 for ; Sun, 3 Mar 2013 16:46:37 -0800 (PST) X-ASG-Debug-ID: 1362357994-04cb6c2b03129820001-NocioJ Received: from ipmail07.adl2.internode.on.net (ipmail07.adl2.internode.on.net [150.101.137.131]) by cuda.sgi.com with ESMTP id 35bThwSScwRS7Z6y for ; Sun, 03 Mar 2013 16:46:35 -0800 (PST) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.131 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: Am4OAO/tM1F5LFKb/2dsb2JhbABFhWe3SYUZexdzgh8BAQU6HCMQCAMYCSUPBSUDIRMbh3fHGRWOKSI9B4NAA5ZFkG2DHA Received: from ppp121-44-82-155.lns20.syd6.internode.on.net (HELO dastard) ([121.44.82.155]) by ipmail07.adl2.internode.on.net with ESMTP; 04 Mar 2013 11:12:30 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UCJU5-00049n-9Y; Mon, 04 Mar 2013 11:42:29 +1100 Date: Mon, 4 Mar 2013 11:42:29 +1100 From: Dave Chinner To: Eric Sandeen Cc: Richard Weinberger , linux-fsdevel@vger.kernel.org, xfs@oss.sgi.com Subject: Re: [PATCH] Do not check ocfs2 Message-ID: <20130304004229.GK23616@dastard> X-ASG-Orig-Subj: Re: [PATCH] Do not check ocfs2 References: <1362269150-21478-1-git-send-email-richard@nod.at> <20130303011917.GI23616@dastard> <20130303100254.500b076f@spider.haslach.nod.at> <5133C900.9050300@sandeen.net> <20130303231905.0efd6d08@spider.haslach.nod.at> <5133D15A.9010600@sandeen.net> <20130303235341.7470085e@spider.haslach.nod.at> <5133D573.3050106@sandeen.net> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <5133D573.3050106@sandeen.net> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail07.adl2.internode.on.net[150.101.137.131] X-Barracuda-Start-Time: 1362357994 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124177 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Sun, Mar 03, 2013 at 04:57:55PM -0600, Eric Sandeen wrote: > On 3/3/13 4:53 PM, Richard Weinberger wrote: > > >> Anyway, what if you did something more along the lines of [pseudocode] > >> > >> ocfs2) > >> if mounted.ocfs2 -f $TEST-DEV | frob_as_necessary[1] > >> ; > >> else > >> fsck.ocfs2 $TEST-DEV > >> fi > >> ;; > >> > >> so that *if* it's mounted on some other node, the fsck won't run. > >> That has downsides as Dave mentioned, but for the case where the > >> xfstests node is the only one with it in use, it'll still do the > >> beneficial consistency check. > >> > >> Just tweaking the fsck action bsed on *if* it's mounted (or, > >> maybe, if the node is in a cluster?) might be a more generic solution > >> that is widely applicable to all ocfs2 test environments. > > > > Good point. mounted.ocfs2 really makes sense. I'll implement this on my > > test suite and submit a new patch. > > Sounds good to me. > > It'd be most preferable to do a cluster-wide unmount and fsck, Which makes no sense to me, because ./check will then do a cluster wide unmount as it runs the test harness initialisation. Hence all the subsequent tests will run with the filesystem only mounted on the local node.... Really, xfstests is not designed for testing cluster filesystems in clustered environments. If we really want to support clustered filesystems and cluster wide operations, then we need to think about how to architect multi-host support into xfstests sanely. Clustered filesystems are not the only people that could make use of such functionality (NFS and CIFS come to mind).... ;) Cheers, Dave/ -- Dave Chinner david@fromorbit.com From qcai@redhat.com Sun Mar 3 22:23:41 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 9E25C8030 for ; Sun, 3 Mar 2013 22:23:41 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay2.corp.sgi.com (Postfix) with ESMTP id 7C7B8304032 for ; Sun, 3 Mar 2013 20:23:38 -0800 (PST) X-ASG-Debug-ID: 1362371014-04cb6c2b02132780001-NocioJ Received: from mx4-phx2.redhat.com (mx4-phx2.redhat.com [209.132.183.25]) by cuda.sgi.com with ESMTP id 3iE7uyXURsGPVPVq for ; Sun, 03 Mar 2013 20:23:34 -0800 (PST) X-Barracuda-Envelope-From: qcai@redhat.com X-Barracuda-Apparent-Source-IP: 209.132.183.25 Received: from zmail14.collab.prod.int.phx2.redhat.com (zmail14.collab.prod.int.phx2.redhat.com [10.5.83.16]) by mx4-phx2.redhat.com (8.13.8/8.13.8) with ESMTP id r244NQvd030846; Sun, 3 Mar 2013 23:23:26 -0500 Date: Sun, 3 Mar 2013 23:23:26 -0500 (EST) From: CAI Qian To: Dave Chinner Cc: xfs@oss.sgi.com Message-ID: <1601552351.8516567.1362371006444.JavaMail.root@redhat.com> In-Reply-To: <220575861.7590457.1362129618880.JavaMail.root@redhat.com> Subject: Re: possible fsync02() xfs slowness regression on power7 MIME-Version: 1.0 X-ASG-Orig-Subj: Re: possible fsync02() xfs slowness regression on power7 Content-Type: text/plain; charset=utf-8 Content-Transfer-Encoding: 7bit X-Originating-IP: [10.66.13.185] X-Mailer: Zimbra 7.2.0_GA_2669 (ZimbraWebClient - FF3.0 (Linux)/7.2.0_GA_2669) X-Barracuda-Connect: mx4-phx2.redhat.com[209.132.183.25] X-Barracuda-Start-Time: 1362371014 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124193 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- > > And this commit in 3.9-rc1: > > > > a1e16c2 xfs: limit speculative prealloc size on sparse files > > should fix the problem. Please confirm these commits are the cause > > and the fix respectively.... Confirmed this fixed the problem. I'd like to request this to be back-ported to stable-3.0, stable-3.4 and stable-3.8. What do you think? Thanks, CAI Qian From david@fromorbit.com Sun Mar 3 23:55:09 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id D44CD8032 for ; Sun, 3 Mar 2013 23:55:09 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay3.corp.sgi.com (Postfix) with ESMTP id 673DBAC002 for ; Sun, 3 Mar 2013 21:55:06 -0800 (PST) X-ASG-Debug-ID: 1362376504-04cb6c2b04137860001-NocioJ Received: from ipmail06.adl6.internode.on.net (ipmail06.adl6.internode.on.net [150.101.137.145]) by cuda.sgi.com with ESMTP id ni68BcFW89ogfGED for ; Sun, 03 Mar 2013 21:55:04 -0800 (PST) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.145 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AhElADQ2NFF5LFKb/2dsb2JhbABFvTSFFQECAXsXc4IfAQEFOhwjEAgDGAklDwUlAyETiBLHHBWNQgYvGB9KB4NAA5ZFkG2DHIFW Received: from ppp121-44-82-155.lns20.syd6.internode.on.net (HELO dastard) ([121.44.82.155]) by ipmail06.adl6.internode.on.net with ESMTP; 04 Mar 2013 16:25:02 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UCOMY-0004pY-2b; Mon, 04 Mar 2013 16:55:02 +1100 Date: Mon, 4 Mar 2013 16:55:02 +1100 From: Dave Chinner To: CAI Qian Cc: xfs@oss.sgi.com Subject: Re: possible fsync02() xfs slowness regression on power7 Message-ID: <20130304055502.GP23616@dastard> X-ASG-Orig-Subj: Re: possible fsync02() xfs slowness regression on power7 References: <220575861.7590457.1362129618880.JavaMail.root@redhat.com> <1601552351.8516567.1362371006444.JavaMail.root@redhat.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <1601552351.8516567.1362371006444.JavaMail.root@redhat.com> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail06.adl6.internode.on.net[150.101.137.145] X-Barracuda-Start-Time: 1362376504 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124199 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Sun, Mar 03, 2013 at 11:23:26PM -0500, CAI Qian wrote: > > > > And this commit in 3.9-rc1: > > > > > > a1e16c2 xfs: limit speculative prealloc size on sparse files > > > should fix the problem. Please confirm these commits are the cause > > > and the fix respectively.... > Confirmed this fixed the problem. I'd like to request this to be back-ported > to stable-3.0, stable-3.4 and stable-3.8. What do you think? IMO, no, it is not a backport candidate. The patch has quite a few dependencies, and at least for 3.0 xfs_bmapi_read() doesn't exist and hence is not a trivial backport. Further, it's take 2 years for this to be noticed, and you haven't explained why the problem exists on your power machine and not any others that it has been tested on. And there's been very few complaints about performance of such workloads over the past 2 years, so either the workload is not important or only your power7 machine is having problems. Hence I don't see any need to back port it - it's not a critical fix and very few people see the problem so there's no real need to do the backport. Maybe someone else has the time and resources to waste on backporting non-critical fixes to stable kernels, but I don't.... Cheers, Dave. -- Dave Chinner david@fromorbit.com From qcai@redhat.com Mon Mar 4 00:14:08 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 93D468034 for ; Mon, 4 Mar 2013 00:14:08 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id 812B3304032 for ; Sun, 3 Mar 2013 22:14:05 -0800 (PST) X-ASG-Debug-ID: 1362377644-04cbb07dbe13e2b0001-NocioJ Received: from mx4-phx2.redhat.com (mx4-phx2.redhat.com [209.132.183.25]) by cuda.sgi.com with ESMTP id LWXlFGhJYx2Gfhf2 for ; Sun, 03 Mar 2013 22:14:04 -0800 (PST) X-Barracuda-Envelope-From: qcai@redhat.com X-Barracuda-Apparent-Source-IP: 209.132.183.25 Received: from zmail14.collab.prod.int.phx2.redhat.com (zmail14.collab.prod.int.phx2.redhat.com [10.5.83.16]) by mx4-phx2.redhat.com (8.13.8/8.13.8) with ESMTP id r246E2g3014835; Mon, 4 Mar 2013 01:14:02 -0500 Date: Mon, 4 Mar 2013 01:14:02 -0500 (EST) From: CAI Qian To: Dave Chinner Cc: xfs@oss.sgi.com Message-ID: <1735762055.8552410.1362377642444.JavaMail.root@redhat.com> In-Reply-To: <20130304055502.GP23616@dastard> Subject: Re: possible fsync02() xfs slowness regression on power7 MIME-Version: 1.0 X-ASG-Orig-Subj: Re: possible fsync02() xfs slowness regression on power7 Content-Type: text/plain; charset=utf-8 Content-Transfer-Encoding: quoted-printable X-Originating-IP: [10.66.13.185] X-Mailer: Zimbra 7.2.0_GA_2669 (ZimbraWebClient - FF3.0 (Linux)/7.2.0_GA_2669) X-Barracuda-Connect: mx4-phx2.redhat.com[209.132.183.25] X-Barracuda-Start-Time: 1362377644 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124199 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- ----- =E5=8E=9F=E5=A7=8B=E9=82=AE=E4=BB=B6 ----- > =E5=8F=91=E4=BB=B6=E4=BA=BA: "Dave Chinner" > =E6=94=B6=E4=BB=B6=E4=BA=BA: "CAI Qian" > =E6=8A=84=E9=80=81: xfs@oss.sgi.com > =E5=8F=91=E9=80=81=E6=97=B6=E9=97=B4: =E6=98=9F=E6=9C=9F=E4=B8=80, 2013= =E5=B9=B4 3 =E6=9C=88 04=E6=97=A5 =E4=B8=8B=E5=8D=88 1:55:02 > =E4=B8=BB=E9=A2=98: Re: possible fsync02() xfs slowness regression on pow= er7 >=20 > On Sun, Mar 03, 2013 at 11:23:26PM -0500, CAI Qian wrote: > >=20 > > > > And this commit in 3.9-rc1: > > > >=20 > > > > a1e16c2 xfs: limit speculative prealloc size on sparse files > > > > should fix the problem. Please confirm these commits are the > > > > cause > > > > and the fix respectively.... > > Confirmed this fixed the problem. I'd like to request this to be > > back-ported > > to stable-3.0, stable-3.4 and stable-3.8. What do you think? >=20 > IMO, no, it is not a backport candidate. The patch has quite a few > dependencies, and at least for 3.0 xfs_bmapi_read() doesn't exist > and hence is not a trivial backport. It is fine to skip the 3.0 then, but the other stable branches can be appli= ed as it iis and build fine. >=20 > Further, it's take 2 years for this to be noticed, and you haven't > explained why the problem exists on your power machine and not any > others that it has been tested on. And there's been very few > complaints about performance of such workloads over the past 2 > years, so either the workload is not important or only your power7 > machine is having problems. Hmm, it could also be possible that it was easy to reproduce now with the new kernel plus new user-spaces as well the new compiler. Also, those syste= ms started to switch to use XFS as root partitions from ext4 only recently, so we have never noticed this in the past when running those LTP tests. XFS could also become more popular than 2-year ago. :) >=20 > Hence I don't see any need to back port it - it's not a critical fix > and very few people see the problem so there's no real need to do > the backport. Maybe someone else has the time and resources to > waste on backporting non-critical fixes to stable kernels, but I > don't.... I have time so I can do the back-port for you guys to review if you don't mind. Thanks for your time. >=20 > Cheers, >=20 > Dave. > -- > Dave Chinner > david@fromorbit.com >=20 From zlu@tilera.com Mon Mar 4 02:33:01 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 518948032 for ; Mon, 4 Mar 2013 02:33:01 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay2.corp.sgi.com (Postfix) with ESMTP id 1AE1D304051 for ; Mon, 4 Mar 2013 00:33:00 -0800 (PST) X-ASG-Debug-ID: 1362385978-04bdf02295153530001-NocioJ Received: from USMAMAIL.TILERA.COM (usmamail.tilera.com [12.216.194.151]) by cuda.sgi.com with ESMTP id JaNn6LU08jdDc1Nv (version=TLSv1 cipher=AES128-SHA bits=128 verify=NO) for ; Mon, 04 Mar 2013 00:32:59 -0800 (PST) X-Barracuda-Envelope-From: zlu@tilera.com X-Barracuda-Apparent-Source-IP: 12.216.194.151 Received: from USMAEXCH1.tad.internal.tilera.com ([fe80::709c:7a3e:ae82:7a6e]) by USMAExch2.tad.internal.tilera.com ([fe80::408c:3921:ab63:6a87%11]) with mapi; Mon, 4 Mar 2013 03:32:58 -0500 From: Tony Lu To: Mark Tinguely CC: Alex Elder , "linux-kernel@vger.kernel.org" , Chris Metcalf , "xfs@oss.sgi.com" , Ben Myers , Dave Chinner , "linux-fsdevel@vger.kernel.org" Subject: RE: [PATCH] xfs: Fix possible truncation of log data in xlog_bread_noalign() Thread-Topic: [PATCH] xfs: Fix possible truncation of log data in xlog_bread_noalign() X-ASG-Orig-Subj: RE: [PATCH] xfs: Fix possible truncation of log data in xlog_bread_noalign() Thread-Index: Ac4Q1GkSs67IJq+zR5aVm2NJSgVsAwAr1ggAACdj+ZYAHdvY9AD+/4OnABP7wQAAcqHZwA== Date: Mon, 4 Mar 2013 08:32:45 +0000 Message-ID: References: <20130223000802.GB26081@dastard> <20130223235546.GA5551@dastard> <20130224141017.GC5551@dastard> <5130CE9E.9080501@sgi.com> <51310E7A.1000905@sgi.com> In-Reply-To: <51310E7A.1000905@sgi.com> Accept-Language: zh-CN, en-US Content-Language: zh-CN X-MS-Has-Attach: X-MS-TNEF-Correlator: Content-Type: text/plain; charset="us-ascii" Content-Transfer-Encoding: quoted-printable MIME-Version: 1.0 X-Barracuda-Connect: usmamail.tilera.com[12.216.194.151] X-Barracuda-Start-Time: 1362385979 X-Barracuda-Encrypted: AES128-SHA X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.02 X-Barracuda-Spam-Status: No, SCORE=0.02 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=THREAD_INDEX, THREAD_TOPIC X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124209 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.01 THREAD_INDEX thread-index: AcO7Y8iR61tzADqsRmmc5wNiFHEOig== 0.01 THREAD_TOPIC Thread-Topic: ...(Japanese Subject)... Thanks for you following up. My apologize that I just found that it is one change I made before that cau= ses this problem. This change forces mkfs.xfs to format xfs partitions whos= e sectorsize were not smaller than 4096 bytes, which was due to a bug that = earlier versions of xfs used (struct *page)->private(long) as a bitmap to r= epresent each block's state within a page (the size of a page could be 64K = or larger, then it needs 128 bit or more to represent each block's state wi= thin a page). This is reproducible on 2.6.38.6 kernel on X86. But I do not get why this c= hange makes the xfs log inconsistent during mount/cp/umount operations. diff -dur xfsprogs-3.1.4.ori/include/xfs_alloc_btree.h xfsprogs-3.1.4/inclu= de/xfs_alloc_btree.h --- xfsprogs-3.1.4.ori/include/xfs_alloc_btree.h 2010-01-30 03:46:13= .000000000 +0800 +++ xfsprogs-3.1.4/include/xfs_alloc_btree.h 2013-03-04 16:11:41.0000000= 00 +0800 @@ -59,7 +59,7 @@ #define XFS_MAX_BLOCKSIZE_LOG 16 /* i.e. 65536 bytes */ #define XFS_MIN_BLOCKSIZE (1 << XFS_MIN_BLOCKSIZE_LOG) #define XFS_MAX_BLOCKSIZE (1 << XFS_MAX_BLOCKSIZE_LOG) -#define XFS_MIN_SECTORSIZE_LOG 9 /* i.e. 512 bytes */ +#define XFS_MIN_SECTORSIZE_LOG 12 /* i.e. 512 bytes */ #define XFS_MAX_SECTORSIZE_LOG 15 /* i.e. 32768 bytes */ #define XFS_MIN_SECTORSIZE (1 << XFS_MIN_SECTORSIZE_LOG) #define XFS_MAX_SECTORSIZE (1 << XFS_MAX_SECTORSIZE_LOG) Thanks -Tony >-----Original Message----- >From: Mark Tinguely [mailto:tinguely@sgi.com] >Sent: Saturday, March 02, 2013 4:24 AM >To: Tony Lu >Cc: Alex Elder; linux-kernel@vger.kernel.org; Chris Metcalf; xfs@oss.sgi.c= om; >Ben Myers; Dave Chinner; linux-fsdevel@vger.kernel.org >Subject: Re: [PATCH] xfs: Fix possible truncation of log data in >xlog_bread_noalign() > >On 03/01/13 09:51, Mark Tinguely wrote: >> On 02/26/13 01:28, Tony Lu wrote: >>> I get a reliable way to reproduce this bug. The logprint and metadump >>> are attached. >>> >>> Kernel version: 2.6.38.8 >>> Mkfs.xfs version: xfsprogs-3.1.1 >>> mkfs.xfs -s size=3D4096 /dev/sda1 >>> >>> Run the following mount-cp-umount script to reproduce: >>> #!/bin/sh >>> device=3D/dev/sda1 >>> mount_point=3D/mnt >>> times=3D10 >>> >>> for ((num=3D1;num<=3D$times;num++)) >>> do >>> echo "$num mount $device $mount_point" >>> mount $device $mount_point >>> >>> echo "cp -rf /bin $mount_point/$num" >>> cp -rf /bin $mount_point/$num >>> >>> echo "$num umount $device $mount_point" >>> umount $mount_point >>> >>> #num=3D$(($num + 1)) >>> done >>> >>> After several times of mount/cp/umount, this xfs crashes, and the xfs >>> partition can not be mounted any more. Here is the output of console. >>> -sh-4.1# ./umount-test >>> 1 mount /dev/sda1 /mnt >>> XFS mounting filesystem sda1 >>> cp -rf /bin /mnt/1 >>> 1 umount /dev/sda1 /mnt >>> 2 mount /dev/sda1 /mnt >>> XFS mounting filesystem sda1 >>> cp -rf /bin /mnt/2 >>> 2 umount /dev/sda1 /mnt >>> 3 mount /dev/sda1 /mnt >>> XFS mounting filesystem sda1 >>> cp -rf /bin /mnt/3 >>> 3 umount /dev/sda1 /mnt >>> 4 mount /dev/sda1 /mnt >>> XFS mounting filesystem sda1 >>> cp -rf /bin /mnt/4 >>> 4 umount /dev/sda1 /mnt >>> 5 mount /dev/sda1 /mnt >>> XFS mounting filesystem sda1 >>> Starting XFS recovery on filesystem: sda1 (logdev: internal) >>> Ending XFS recovery on filesystem: sda1 (logdev: internal)cp -rf /bin >>> /mnt/5 >>> 5 umount /dev/sda1 /mnt >>> 6 mount /dev/sda1 /mnt >>> >>> XFS mounting filesystem sda1 >>> Starting XFS recovery on filesystem: sda1 (logdev: internal) >>> Ending XFS recovery on filesystem: sda1 (logdev: internal)Interrupt >>> cp -rf /bin /mnt/6 >>> 6 umount /dev/sda1 /mnt >>> 7 mount /dev/sda1 /mnt >>> >>> XFS mounting filesystem sda1 >>> cp -rf /bin /mnt/7 >>> 7 umount /dev/sda1 /mnt >>> Interrupt >>> 8 mount /dev/sda1 /mnt >>> XFS mounting filesystem sda1 >>> Starting XFS recovery on filesystem: sda1 (logdev: internal) >>> XFS: xlog_recover_process_data: bad clientid >>> XFS: log mount/recovery failed: error 5 >>> XFS: log mount failed >>> >>> Thanks >>> -Tony >> >> It works fine on a 2.6.32 machine I had sitting around - and I never >> required log recovery. >> >> I think you need to answer Dave's question as to why is your unmounts >> are requiring recovery? >> >> Are there errors in the /var/log/messages? >> >> I downloaded the Linux 2.6.38.8 source and take a look if I can recreate >> the problem. >> >> --Mark. > >I could not reproduce the problem on a vanilla install. XFS shutdown and >remounted cleanly running your script (several iterations looping set to >100). > >I started fsstress on another XFS partition on the same disk to see if I >could force a shutdown race. With CONFIG_XFS_DEBUG=3Dy, I could trigger >other ASSERTs on the fsstress partition so I never stayed up long enough >to cause a shutdown race. > >Not wanting to patch that version of Linux/XFS, I am bailing here. If >you want to turn on the XFS debug it may point out why your filesystem >is not shutting down cleanly. > >--Mark. From qcai@redhat.com Mon Mar 4 02:52:40 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 7D90A8038 for ; Mon, 4 Mar 2013 02:52:40 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay1.corp.sgi.com (Postfix) with ESMTP id 6BBB48F8035 for ; Mon, 4 Mar 2013 00:52:37 -0800 (PST) X-ASG-Debug-ID: 1362387155-04cbb07dbe147790001-NocioJ Received: from mx3-phx2.redhat.com (mx3-phx2.redhat.com [209.132.183.24]) by cuda.sgi.com with ESMTP id jC0vJw35t8Tf5YGg; Mon, 04 Mar 2013 00:52:35 -0800 (PST) X-Barracuda-Envelope-From: qcai@redhat.com X-Barracuda-Apparent-Source-IP: 209.132.183.24 Received: from zmail14.collab.prod.int.phx2.redhat.com (zmail14.collab.prod.int.phx2.redhat.com [10.5.83.16]) by mx3-phx2.redhat.com (8.13.8/8.13.8) with ESMTP id r248qYof014776; Mon, 4 Mar 2013 03:52:35 -0500 Date: Mon, 4 Mar 2013 03:52:34 -0500 (EST) From: CAI Qian To: Dave Chinner , Mark Tinguely , Brian Foster , Ben Myers Cc: xfs@oss.sgi.com, stable@vger.kernel.org Message-ID: <1879117295.8593844.1362387154930.JavaMail.root@redhat.com> In-Reply-To: <426368976.8591643.1362386550488.JavaMail.root@redhat.com> Subject: request for stable inclusion MIME-Version: 1.0 X-ASG-Orig-Subj: request for stable inclusion Content-Type: text/plain; charset=utf-8 Content-Transfer-Encoding: 7bit X-Originating-IP: [10.66.13.185] X-Mailer: Zimbra 7.2.0_GA_2669 (ZimbraWebClient - FF3.0 (Linux)/7.2.0_GA_2669) X-Barracuda-Connect: mx3-phx2.redhat.com[209.132.183.24] X-Barracuda-Start-Time: 1362387155 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.01 X-Barracuda-Spam-Status: No, SCORE=0.01 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_SA_TO_FROM_DOMAIN_MATCH X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124211 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.01 BSF_SC0_SA_TO_FROM_DOMAIN_MATCH Sender Domain Matches Recipient Domain This is to request to apply the below commit for the stable releases in order to fix a regression introduced by 055388a (xfs: dynamic speculative EOF preallocation) that caused fsync() took long time during the sparse file testing. For stable-3.4 and stable-3.8, it can be applied as it is. For stable-3.0, please see the below patch which fixed the context and used xfs_bmapi() instead of xfs_bmapi_read() which yet in the tree. Also tested on the stable-3.0 to confirmed the original fsync() slowness regression is now gone. Please review and ACK. >From a1e16c26660b301cc8423185924cf1b0b16ea92b Mon Sep 17 00:00:00 2001 From: Dave Chinner Date: Mon, 11 Feb 2013 16:05:01 +1100 Subject: [PATCH] xfs: limit speculative prealloc size on sparse files Speculative preallocation based on the current file size works well for contiguous files, but is sub-optimal for sparse files where the EOF preallocation can fill holes and result in large amounts of zeros being written when it is not necessary. The algorithm is modified to prevent EOF speculative preallocation from triggering larger allocations on IO patterns of truncate--to-zero-seek-write-seek-write-.... which results in non-sparse files for large files. This, unfortunately, is the way cp now behaves when copying sparse files and so needs to be fixed. What this code does is that it looks at the existing extent adjacent to the current EOF and if it determines that it is a hole we disable speculative preallocation altogether. To avoid the next write from doing a large prealloc, it takes the size of subsequent preallocations from the current size of the existing EOF extent. IOWs, if you leave a hole in the file, it resets preallocation behaviour to the same as if it was a zero size file. Example new behaviour: $ xfs_io -f -c "pwrite 0 31m" \ -c "pwrite 33m 1m" \ -c "pwrite 128m 1m" \ -c "fiemap -v" /mnt/scratch/blah wrote 32505856/32505856 bytes at offset 0 31 MiB, 7936 ops; 0.0000 sec (1.608 GiB/sec and 421432.7439 ops/sec) wrote 1048576/1048576 bytes at offset 34603008 1 MiB, 256 ops; 0.0000 sec (1.462 GiB/sec and 383233.5329 ops/sec) wrote 1048576/1048576 bytes at offset 134217728 1 MiB, 256 ops; 0.0000 sec (1.719 GiB/sec and 450704.2254 ops/sec) /mnt/scratch/blah: EXT: FILE-OFFSET BLOCK-RANGE TOTAL FLAGS 0: [0..65535]: 96..65631 65536 0x0 1: [65536..67583]: hole 2048 2: [67584..69631]: 67680..69727 2048 0x0 3: [69632..262143]: hole 192512 4: [262144..264191]: 262240..264287 2048 0x1 Signed-off-by: Dave Chinner Reviewed-by: Mark Tinguely Reviewed-by: Brian Foster Signed-off-by: Ben Myers Signed-off-by: CAI Qian diff --git a/fs/xfs/xfs_iomap.c b/fs/xfs/xfs_iomap.c index 091d82b..c5a377c 100644 --- a/fs/xfs/xfs_iomap.c +++ b/fs/xfs/xfs_iomap.c @@ -321,6 +321,63 @@ xfs_iomap_eof_want_preallocate( } /* + * Determine the initial size of the preallocation. We are beyond the current + * EOF here, but we need to take into account whether this is a sparse write or + * an extending write when determining the preallocation size. Hence we need to + * look up the extent that ends at the current write offset and use the result + * to determine the preallocation size. + * + * If the extent is a hole, then preallocation is essentially disabled. + * Otherwise we take the size of the preceeding data extent as the basis for the + * preallocation size. If the size of the extent is greater than half the + * maximum extent length, then use the current offset as the basis. This ensures + * that for large files the preallocation size always extends to MAXEXTLEN + * rather than falling short due to things like stripe unit/width alignment of + * real extents. + */ +STATIC int +xfs_iomap_eof_prealloc_initial_size( + struct xfs_mount *mp, + struct xfs_inode *ip, + xfs_off_t offset, + xfs_bmbt_irec_t *imap, + int nimaps) +{ + xfs_fileoff_t start_fsb; + int imaps = 1; + int error; + + ASSERT(nimaps >= imaps); + + /* if we are using a specific prealloc size, return now */ + if (mp->m_flags & XFS_MOUNT_DFLT_IOSIZE) + return 0; + + /* + * As we write multiple pages, the offset will always align to the + * start of a page and hence point to a hole at EOF. i.e. if the size is + * 4096 bytes, we only have one block at FSB 0, but XFS_B_TO_FSB(4096) + * will return FSB 1. Hence if there are blocks in the file, we want to + * point to the block prior to the EOF block and not the hole that maps + * directly at @offset. + */ + start_fsb = XFS_B_TO_FSB(mp, offset); + if (start_fsb) + start_fsb--; + error = xfs_bmapi(NULL, ip, start_fsb, 1, XFS_BMAPI_ENTIRE, NULL, 0, + imap, &imaps, NULL); + if (error) + return 0; + + ASSERT(imaps == 1); + if (imap[0].br_startblock == HOLESTARTBLOCK) + return 0; + if (imap[0].br_blockcount <= (MAXEXTLEN >> 1)) + return imap[0].br_blockcount; + return XFS_B_TO_FSB(mp, offset); +} + +/* * If we don't have a user specified preallocation size, dynamically increase * the preallocation size as the size of the file grows. Cap the maximum size * at a single extent or less if the filesystem is near full. The closer the @@ -329,20 +386,19 @@ xfs_iomap_eof_want_preallocate( STATIC xfs_fsblock_t xfs_iomap_prealloc_size( struct xfs_mount *mp, - struct xfs_inode *ip) + struct xfs_inode *ip, + xfs_off_t offset, + struct xfs_bmbt_irec *imap, + int nimaps) { xfs_fsblock_t alloc_blocks = 0; - if (!(mp->m_flags & XFS_MOUNT_DFLT_IOSIZE)) { + alloc_blocks = xfs_iomap_eof_prealloc_initial_size(mp, ip, offset, + imap, nimaps); + if (alloc_blocks > 0) { int shift = 0; int64_t freesp; - /* - * rounddown_pow_of_two() returns an undefined result - * if we pass in alloc_blocks = 0. Hence the "+ 1" to - * ensure we always pass in a non-zero value. - */ - alloc_blocks = XFS_B_TO_FSB(mp, ip->i_size) + 1; alloc_blocks = XFS_FILEOFF_MIN(MAXEXTLEN, rounddown_pow_of_two(alloc_blocks)); @@ -401,7 +457,6 @@ xfs_iomap_write_delay( extsz = xfs_get_extsz_hint(ip); offset_fsb = XFS_B_TO_FSBT(mp, offset); - error = xfs_iomap_eof_want_preallocate(mp, ip, offset, count, imap, XFS_WRITE_IMAPS, &prealloc); if (error) @@ -409,7 +464,10 @@ xfs_iomap_write_delay( retry: if (prealloc) { - xfs_fsblock_t alloc_blocks = xfs_iomap_prealloc_size(mp, ip); + xfs_fsblock_t alloc_blocks; + + alloc_blocks = xfs_iomap_prealloc_size(mp, ip, offset, imap, + XFS_WRITE_IMAPS); aligned_offset = XFS_WRITEIO_ALIGN(mp, (offset + count - 1)); ioalign = XFS_B_TO_FSBT(mp, aligned_offset); From ole.tange.work@gmail.com Mon Mar 4 03:00:30 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=FREEMAIL_FROM,T_DKIM_INVALID autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 28BA48038 for ; Mon, 4 Mar 2013 03:00:30 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay1.corp.sgi.com (Postfix) with ESMTP id E88308F8040 for ; Mon, 4 Mar 2013 01:00:29 -0800 (PST) X-ASG-Debug-ID: 1362387628-04bdf02297154e50001-NocioJ Received: from mail-pa0-f49.google.com (mail-pa0-f49.google.com [209.85.220.49]) by cuda.sgi.com with ESMTP id ZswViz9OTyilUFVh (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Mon, 04 Mar 2013 01:00:28 -0800 (PST) X-Barracuda-Envelope-From: ole.tange.work@gmail.com X-Barracuda-Apparent-Source-IP: 209.85.220.49 X-Barracuda-IPDD: Level1 [gmail.com/209.85.220.49] Received: by mail-pa0-f49.google.com with SMTP id kp6so3054779pab.36 for ; Mon, 04 Mar 2013 01:00:28 -0800 (PST) X-Barracuda-IPDD: Level1 [gmail.com/209.85.220.49] X-Barracuda-IPDD: Level1 [gmail.com/209.85.220.49] DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20120113; h=x-received:mime-version:sender:in-reply-to:references:from:date :x-google-sender-auth:message-id:subject:to:cc:content-type; bh=M/HsKJzRpoUkDNFtSjMwgfoh1LBWfNYf5K2eS+Eusgw=; b=mvxVEMMJkGa339plNV2O90PQ+09Hj7bEV3JzTj+dK6Vsao7QXRPZA5ExGhAkqTH7bo ZnSmIWv4FLIwE/h2et+uGhhqp41Apsjwxakwq59Z5onA3lle9ubtHdy7ISLINMIQxtjJ skLtAMeriEC25/CSU8OqRHNEoCYf+qE+NzSWoY+AOeSloMD5dwc8uh0xwET43rlsvnXT 4rbmWDsHiwg863WjA96wJkEUorMSoNfdYroUEv5P2asGI4SIgBABDzp/4Y6jJn7aZkDs 3Wc2xtU3ZKsWpZi5Gy4e1tiFPzdyk1iblORZF8roKotMfGvVLt7u0oslPMgyRyMBEhP5 Bs1w== X-Received: by 10.68.47.39 with SMTP id a7mr27214854pbn.155.1362387628538; Mon, 04 Mar 2013 01:00:28 -0800 (PST) MIME-Version: 1.0 Sender: ole.tange.work@gmail.com Received: by 10.68.7.9 with HTTP; Mon, 4 Mar 2013 01:00:08 -0800 (PST) In-Reply-To: <5130DB54.9030503@sandeen.net> References: <512FA67D.2090708@sandeen.net> <5130DB54.9030503@sandeen.net> From: Ole Tange Date: Mon, 4 Mar 2013 10:00:08 +0100 X-Google-Sender-Auth: aFJ8Bvh91yt_1VidbCBTOledpTY Message-ID: Subject: Re: xfs_repair segfaults To: Eric Sandeen X-ASG-Orig-Subj: Re: xfs_repair segfaults Cc: xfs@oss.sgi.com Content-Type: text/plain; charset=ISO-8859-1 X-Barracuda-Connect: mail-pa0-f49.google.com[209.85.220.49] X-Barracuda-Start-Time: 1362387628 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=DKIM_SIGNED, DKIM_VERIFIED X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124211 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature On Fri, Mar 1, 2013 at 5:46 PM, Eric Sandeen wrote: > On 3/1/13 3:37 AM, Ole Tange wrote: >> Please consider providing an example in the man page for xfs_metadump e.g: >> >> xfs_metadump.sh -g /dev/sda2 meta.dump > > From the manpage, > > SYNOPSIS > xfs_metadump [ -efgow ] [ -l logdev ] source target > > The source argument must be the pathname of > the device or file containing the XFS filesystem > > and > > the target argument specifies the destination file name. > > is not enough? I have never run xfs_metadump before and I am in a state of worry that my filesystem is toast. I would therefore like to be re-assured that what I am doing is correct. I did that by reading and re-reading the manual to make sure I had understood it correctly. By providing me with an example of the right way to do it in the man page, I will feel more confident that what I am about to do it correct and I could probably save time by not having to re-read the manual. So I am not saying the information is not there, what I am saying is that you in a simple way could make it easier to grasp the information. /Ole From ole.tange.work@gmail.com Mon Mar 4 03:03:54 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=FREEMAIL_FROM,T_DKIM_INVALID autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 2F5C3803D for ; Mon, 4 Mar 2013 03:03:54 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay2.corp.sgi.com (Postfix) with ESMTP id 0F01A304043 for ; Mon, 4 Mar 2013 01:03:51 -0800 (PST) X-ASG-Debug-ID: 1362387829-04bdf02298155140001-NocioJ Received: from mail-pb0-f48.google.com (mail-pb0-f48.google.com [209.85.160.48]) by cuda.sgi.com with ESMTP id Zq9bibIHXe1OeHqx (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Mon, 04 Mar 2013 01:03:49 -0800 (PST) X-Barracuda-Envelope-From: ole.tange.work@gmail.com X-Barracuda-Apparent-Source-IP: 209.85.160.48 X-Barracuda-IPDD: Level1 [gmail.com/209.85.160.48] Received: by mail-pb0-f48.google.com with SMTP id wy12so2946456pbc.21 for ; Mon, 04 Mar 2013 01:03:49 -0800 (PST) X-Barracuda-IPDD: Level1 [gmail.com/209.85.160.48] X-Barracuda-IPDD: Level1 [gmail.com/209.85.160.48] DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20120113; h=x-received:mime-version:sender:in-reply-to:references:from:date :x-google-sender-auth:message-id:subject:to:cc:content-type; bh=xh7TAYPp7+q+RkXgcmq71er1zoiF3yXN7mVGDwX5uLw=; b=LPCYN0NmhXLSp+SCqi5dZoXuK/5aIhWgm36jZUXpDGiiIE8d0LBVxSHbb00/rmBt96 1Mj2tmjEEmaGCZtsvq+aoVv+abWDALuCCALIhosMBPxzjb23BMhZG/mLn3JkBPRW1L+v S9/ytQ2c4j3VDHOPLbCrhUksyaZ7aHtAC9qaVL3SwgrPenhcVeqRNzyx7hwNqsC6xJkb vRgbs3lxj7Bgzf+cXQt9l0R8lYjpS6qOYztNd1abJzbBXOqEyQQRpc8SqW/RHKCzSDIb cGp4de48Fc8NwJC8cuvPaujvbY7NM53lI2ScFBpYRfYLzFgyJC4+jyB7Li5vvR6yXagX j7Iw== X-Received: by 10.68.163.68 with SMTP id yg4mr17716095pbb.77.1362387829493; Mon, 04 Mar 2013 01:03:49 -0800 (PST) MIME-Version: 1.0 Sender: ole.tange.work@gmail.com Received: by 10.68.7.9 with HTTP; Mon, 4 Mar 2013 01:03:29 -0800 (PST) In-Reply-To: <20130301205305.GD23616@dastard> References: <20130301111701.GB23616@dastard> <20130301205305.GD23616@dastard> From: Ole Tange Date: Mon, 4 Mar 2013 10:03:29 +0100 X-Google-Sender-Auth: P7ArLkWbTyTrpF8nv43Xa0K4hZE Message-ID: Subject: Re: xfs_repair segfaults To: Dave Chinner X-ASG-Orig-Subj: Re: xfs_repair segfaults Cc: xfs@oss.sgi.com Content-Type: text/plain; charset=ISO-8859-1 X-Barracuda-Connect: mail-pb0-f48.google.com[209.85.160.48] X-Barracuda-Start-Time: 1362387829 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=DKIM_SIGNED, DKIM_VERIFIED X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124211 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature On Fri, Mar 1, 2013 at 9:53 PM, Dave Chinner wrote: : > What filesystem errors occurred > when the srives went offline? See http://dna.ku.dk/~tange/tmp/syslog.3 Feb 26 00:46:52 franklin kernel: [556238.429259] XFS (md5p1): metadata I/O error: block 0x459b8 ("xfs_buf_iodone_callbacks") error 5 buf count 4096 /Ole From margarita.carmenate@uam.es Mon Mar 4 04:28:41 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=T_DKIM_INVALID autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 3C4D8803D for ; Mon, 4 Mar 2013 04:28:41 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay2.corp.sgi.com (Postfix) with ESMTP id 07C1C304039 for ; Mon, 4 Mar 2013 02:28:40 -0800 (PST) X-ASG-Debug-ID: 1362392917-04bdf022961581d0001-NocioJ Received: from eint2.ti.uam.es (eint2.ti.uam.es [150.244.9.161]) by cuda.sgi.com with ESMTP id gveBiACajvje3cUx for ; Mon, 04 Mar 2013 02:28:38 -0800 (PST) X-Barracuda-Envelope-From: margarita.carmenate@uam.es X-Barracuda-Apparent-Source-IP: 150.244.9.161 Received: from imsvain1.ti.uam.es (pip9.ti.uam.es [150.244.8.254]) by postfix.imss70 (Postfix) with ESMTP id 12C39300DF; Mon, 4 Mar 2013 11:28:36 +0100 (CET) Received: from imsvain1.ti.uam.es (unknown [127.0.0.1]) by IMSVA (Postfix) with ESMTP id 208CE4C0036; Mon, 4 Mar 2013 11:28:36 +0100 (CET) Received: from localhost (unknown [150.244.8.254]) by imsvain1.ti.uam.es (Postfix) with ESMTP id 054114C003D; Mon, 4 Mar 2013 11:28:36 +0100 (CET) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=uam.es; h= content-transfer-encoding:content-disposition:mime-version :content-type:content-type:user-agent:subject:subject:from:from :message-id:date:date:received:received:received:received; s= uam; t=1362392915; bh=50An93IRp8hNpIkNbj74jtq+rbHHizrg9fTUvZrUwn A=; b=kz7MLlECuJlwTuqJEjL34DBcHv0fVq8HXga48RVtJT6iiLkGFvFl0AJw2X RuiX4ahyF1nV6WJTOkgoPHfj9JebGGUTbu6KY5zcxBIvNWGMfjBTDJjIedPAwwt3 CbRfqcP7c88W6ISaakoQjJxcPCFzMe2kf5pGTxQZg1np9vRHI= Received: from eint1.ti.uam.es ([127.0.0.1]) by localhost (eint1.ti.uam.es [127.0.0.1]) (amavisd-new, port 10027) with ESMTP id mGrZWvmJU6dm; Mon, 4 Mar 2013 11:28:35 +0100 (CET) Received: from webmail3.ti.uam.es (pip9.ti.uam.es [150.244.8.254]) by eint1.ti.uam.es (Postfix) with ESMTP id D93E72C00BC; Mon, 4 Mar 2013 11:28:35 +0100 (CET) Received: from localhost (localhost [127.0.0.1]) by webmail3.ti.uam.es (Postfix) with ESMTPA id 4BD5022672; Mon, 4 Mar 2013 11:26:54 +0100 (CET) Received: from 41.206.11.17.vgccl.net (41.206.11.17.vgccl.net [41.206.11.17]) by webmail.uam.es (Horde Framework) with HTTP; Mon, 04 Mar 2013 11:26:54 +0100 Date: Mon, 04 Mar 2013 11:26:54 +0100 Message-ID: <20130304112654.Horde.UoIHFHsco4xRNHbuKybBSYA@webmail.uam.es> From: margarita.carmenate@uam.es To: info@webmail.de Subject: Aktualisieren Sie Ihre Webmail User-Agent: Internet Messaging Program (IMP) H4 (5.0.21) X-ASG-Orig-Subj: Aktualisieren Sie Ihre Webmail Content-Type: text/plain; charset=ISO-8859-1; format=flowed; DelSp=Yes MIME-Version: 1.0 Content-Disposition: inline Content-Transfer-Encoding: quoted-printable X-TM-AS-MML: No X-Barracuda-Connect: eint2.ti.uam.es[150.244.9.161] X-Barracuda-Start-Time: 1362392918 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 1.26 X-Barracuda-Spam-Status: No, SCORE=1.26 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_MISMATCH_TO, DKIM_SIGNED, DKIM_VERIFIED, NO_REAL_NAME, RCVD_NUMERIC_HELO, RCVD_NUMERIC_HELO_2 X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124217 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 NO_REAL_NAME From: does not include a real name 0.00 BSF_SC0_MISMATCH_TO Envelope rcpt doesn't match header 0.00 RCVD_NUMERIC_HELO Received: contains an IP address used for HELO -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature 1.25 RCVD_NUMERIC_HELO_2 Received: contains an IP address used for HELO Sehr geehrter E-Mail-Nutzer Ihre Web-Mail-Kontingent hat die September =FCberschritten 3GB es. Derzeit 3.9GB. in belebt und Steigern Sie Ihren Webmail Zitat klicken Sie den Link unten. https://docs.google.com/a/ucm.es/spreadsheet/viewform?formkey=3DdE5QZEc1T= ktaRmFKbG8zX1dldzJYMEE6MQ Dies kann zu K=FCndigung Ihres Webmail-Konto f=FChren. Vielen Dank und sorry f=FCr die Unannehmlichkeiten Webmaster From noreply.contact@sparkasse.de Mon Mar 4 06:30:08 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=HTML_MESSAGE,T_FRT_CONTACT autolearn=ham version=3.3.1 X-Original-To: linux-xfs@oss.sgi.com Delivered-To: linux-xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id C0C30803D for ; Mon, 4 Mar 2013 06:30:08 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay2.corp.sgi.com (Postfix) with ESMTP id 93F8B304043 for ; Mon, 4 Mar 2013 04:30:05 -0800 (PST) X-ASG-Debug-ID: 1362400202-04bdf0229715cd70001-w1Z2WR Received: from srv01.eventproco.NET (ptp-eventpro-NOC.spidernet.net [194.154.135.146]) by cuda.sgi.com with ESMTP id xiHDPIJINj9NYiwp for ; Mon, 04 Mar 2013 04:30:02 -0800 (PST) X-Barracuda-Envelope-From: noreply.contact@sparkasse.de X-Barracuda-Apparent-Source-IP: 194.154.135.146 X-Brightmail-Tracker: AAAAAhxWjgQHDEsm thread-index: Ac4YwZnn59lBJTQCSuactqUqtLBcsg== Received: from termsrv.mcoc.local ([50.84.104.226]) by srv01.eventproco.NET with Microsoft SMTPSVC(6.0.3790.4675); Mon, 4 Mar 2013 12:18:22 +0200 Content-Transfer-Encoding: 7bit Content-Type: multipart/alternative; boundary="===============1620372624==" MIME-Version: 1.0 Content-Class: urn:content-classes:message Importance: normal Priority: normal X-MimeOLE: Produced By Microsoft MimeOLE V6.00.3790.4721 Subject: wichtiger Hinweis To: "Recipients" X-ASG-Orig-Subj: wichtiger Hinweis From: "SPARKASSE GERMANY " Date: Mon, 04 Mar 2013 04:01:20 -0600 Reply-To: Message-ID: X-OriginalArrivalTime: 04 Mar 2013 10:18:22.0796 (UTC) FILETIME=[99C5E0C0:01CE18C1] X-Barracuda-Connect: ptp-eventpro-NOC.spidernet.net[194.154.135.146] X-Barracuda-Start-Time: 1362400202 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Barracuda-BRTS-Status: 1 X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-Spam-Score: 0.51 X-Barracuda-Spam-Status: No, SCORE=0.51 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_MISMATCH_TO, BSF_SC0_SA_TO_FROM_ADDR_MATCH, HTML_MESSAGE, THREAD_INDEX X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124224 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.01 THREAD_INDEX thread-index: AcO7Y8iR61tzADqsRmmc5wNiFHEOig== 0.00 BSF_SC0_MISMATCH_TO Envelope rcpt doesn't match header 0.00 HTML_MESSAGE BODY: HTML included in message 0.50 BSF_SC0_SA_TO_FROM_ADDR_MATCH Sender Address Matches Recipient Address This is a multi-part message in MIME format. --===============1620372624== Content-Type: text/plain; charset="iso-8859-1" MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable Content-Description: Mail message body Sehr geehrter Kunde, im vergangenen Jahr wurde die Sparkasse, zusammen = mit vielen anderen Schweizer Banken, das Ziel eines weit verbreiteten Inter= net-Betruges. Daher haben wir ein Projekt zur Bekampfung gestartet. Alle = online-Bankkonten sollen auf ein neu entwickeltes Sicherheitssystem verbund= en werden, welches verd=E4chtige Bewegungen und Trends auf Ihrem online-Ban= kkonto schnell aufgesp=FCrt und gel=F6st werden k=F6nnen. Es wurde festgele= gt, dass Ihre online-Sparkassen-Konto noch nicht mit dem neu entwickelten S= icherheitssystem ausgestattet ist und bitten Sie 5-10 Minuten Zeit zu inves= tieren um dieses Sicherheitsupdate/Ma=DFnahmen zu vervollst=E4ndigen. Na= ch dem Update wird sie einer unserer Mitarbeiter kontaktieren, um den gesam= ten Prozess zu vervollstandigen. Wenn der Vorgang abgeschlos john2quest: is= t, werden Sie wie gewohnt, ihr online-Banking mit der Sparkasse verwenden k= =F6nnen. Wir wollen Ihnen im Voraus f=FCr Ihre Mitarbeit danken. SPARKA= SSE/SPARKASSE SPARKASSE GERMANY Mit freundlichen Gr=FC=DFen, Sparkasse. --===============1620372624== Content-Type: text/html; charset="iso-8859-1" MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable Content-Description: Mail message body
Sehr geehrter Kunde,
 
im vergangenen Jahr wurde die Sparkasse, zusammen mit vielen anderen S= chweizer Banken, das Ziel eines weit verbreiteten Internet-Betruges. Daher = haben wir ein Projekt zur Bekampfung gestartet.
 
Alle online-Bankkonten sollen auf ein neu entwickeltes Sicherheitssyst= em verbunden werden, welches verd=E4chtige Bewegungen und Trends auf Ihrem = online-Bankkonto schnell aufgesp=FCrt und gel=F6st werden k=F6nnen.
Es wurde festgelegt, dass Ihre online-Sparkassen-Konto noch nicht mit = dem neu entwickelten Sicherheitssystem ausgestattet ist und bitten Sie 5-10= Minuten Zeit zu investieren um dieses Sicherheitsupdate/Ma=DFnahmen zu ver= vollst=E4ndigen.
 
Nach dem Update wird sie einer unserer Mitarbeiter kontaktieren, um de= n gesamten Prozess zu vervollstandigen. Wenn der Vorgang abgeschlos
john2quest: ist, werden Sie wie gewohnt, ihr online-Banking mit der Sp= arkasse verwenden k=F6nnen.
 
Wir wollen Ihnen im Voraus f=FCr Ihre Mitarbeit danken.
 
Mit freundlichen Gr=FC=DFen,
Sparkasse.
--===============1620372624==-- From ole.tange.work@gmail.com Mon Mar 4 06:47:36 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=FREEMAIL_FROM,T_DKIM_INVALID autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 06E1C803D for ; Mon, 4 Mar 2013 06:47:36 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay1.corp.sgi.com (Postfix) with ESMTP id E975A8F8037 for ; Mon, 4 Mar 2013 04:47:35 -0800 (PST) X-ASG-Debug-ID: 1362401254-04cb6c2b0414b8e0001-NocioJ Received: from mail-da0-f47.google.com (mail-da0-f47.google.com [209.85.210.47]) by cuda.sgi.com with ESMTP id PwWmm40RjtEjt8F3 (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Mon, 04 Mar 2013 04:47:34 -0800 (PST) X-Barracuda-Envelope-From: ole.tange.work@gmail.com X-Barracuda-Apparent-Source-IP: 209.85.210.47 X-Barracuda-IPDD: Level1 [gmail.com/209.85.210.47] Received: by mail-da0-f47.google.com with SMTP id s35so2525728dak.6 for ; Mon, 04 Mar 2013 04:47:34 -0800 (PST) X-Barracuda-IPDD: Level1 [gmail.com/209.85.210.47] X-Barracuda-IPDD: Level1 [gmail.com/209.85.210.47] DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20120113; h=x-received:mime-version:sender:in-reply-to:references:from:date :x-google-sender-auth:message-id:subject:to:cc:content-type; bh=AJjhktc3MuS/c6IN/fTAyY6uxsrMVeY0h8caH1adJMg=; b=jmAkNr5NnoNex+Jp4GEyP8d4pb0cCcHSk/W0co/rsqhlQgSqpRQw4NUXM7r137zNGl SQuv099IWjg4bjJdqJwoNBb7B8ZBqQDeYHk0yVKAX+u+n7DT96Bi1UblYkf6WRSXxrYM QEfOH4oPrF1qLr1wZpgu9s8g0SRJE3232FA/jjEksSzvCHcNbSc6hZ1iOsL5iIQEf8ij E5Ao2PZfsIjXrxyqi1EAVybK5N2qpZre7IEFCSAX0D48pxc+rSGhntDac3wlTH1/x4zs An2OcNCKI4vUH63+hxvCbgt/tY0SCY1vuv2rwstZGzJh5j/zZVBVUMbKv2srhrYGL9dh himQ== X-Received: by 10.68.163.68 with SMTP id yg4mr18539120pbb.77.1362401254244; Mon, 04 Mar 2013 04:47:34 -0800 (PST) MIME-Version: 1.0 Sender: ole.tange.work@gmail.com Received: by 10.68.7.9 with HTTP; Mon, 4 Mar 2013 04:47:14 -0800 (PST) In-Reply-To: <51312C73.5060203@sandeen.net> References: <5131283F.8030704@sandeen.net> <20130301223116.GE23616@dastard> <51312C73.5060203@sandeen.net> From: Ole Tange Date: Mon, 4 Mar 2013 13:47:14 +0100 X-Google-Sender-Auth: 03fGevhrRr5LVOvlKQTZfYJAXZk Message-ID: Subject: Re: xfs_repair segfaults To: Eric Sandeen X-ASG-Orig-Subj: Re: xfs_repair segfaults Cc: Dave Chinner , xfs@oss.sgi.com Content-Type: text/plain; charset=ISO-8859-1 X-Barracuda-Connect: mail-da0-f47.google.com[209.85.210.47] X-Barracuda-Start-Time: 1362401254 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=DKIM_SIGNED, DKIM_VERIFIED X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124227 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature On Fri, Mar 1, 2013 at 11:32 PM, Eric Sandeen wrote: > Ole, you can xfs_mdrestore your metadump image and run test repairs on the result, > if you want a more realistic "dry run" of what repair would do. I have never run xfs_mdrestore before. >From the man page: xfs_mdrestore should not be used to restore metadata onto an existing filesystem unless you are completely certain the target can be destroyed. It is unclear to me if you are suggesting me to do: xfs_mdrestore the-already-created-dump /dev/md5p1 followed by xfs_repair. Or if you want me to restore the metadata on another 100 TB partition (I do not have that available). Maybe you have a trick so that it can be restored on some smaller block device, so I do not need the 100 TB partition, but I will still be able to see how many files are being removed? If you have such a trick, consider including it in the manual. Also I would love if xfs_repair had an option to copy the changed sectors to a file, so it would be easy to revert. E.g: xfs_repair --backup backup.file /dev/sda1 and if the repair did not work out, then you could revert using: xfs_repair --revert backup.file /dev/sda1 and be back at your starting state. /Ole From akinobu.mita@gmail.com Mon Mar 4 06:59:37 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=FREEMAIL_FROM,T_DKIM_INVALID autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 52EB68040 for ; Mon, 4 Mar 2013 06:59:37 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay2.corp.sgi.com (Postfix) with ESMTP id 16A70304051 for ; Mon, 4 Mar 2013 04:59:34 -0800 (PST) X-ASG-Debug-ID: 1362401972-04bdf0229815de90001-NocioJ Received: from mail-da0-f44.google.com (mail-da0-f44.google.com [209.85.210.44]) by cuda.sgi.com with ESMTP id HVFy06Z3VqcTniYv (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Mon, 04 Mar 2013 04:59:32 -0800 (PST) X-Barracuda-Envelope-From: akinobu.mita@gmail.com X-Barracuda-Apparent-Source-IP: 209.85.210.44 X-Barracuda-IPDD: Level1 [gmail.com/209.85.210.44] Received: by mail-da0-f44.google.com with SMTP id z20so2538054dae.17 for ; Mon, 04 Mar 2013 04:59:32 -0800 (PST) X-Barracuda-IPDD: Level1 [gmail.com/209.85.210.44] X-Barracuda-IPDD: Level1 [gmail.com/209.85.210.44] DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20120113; h=x-received:from:to:cc:subject:date:message-id:x-mailer:in-reply-to :references; bh=9GzFHIDQg3HtlDQhfDeN/isLm42aaV64bRQSyaw4wSE=; b=PcdBQ+RsoHr5ZcEx5eX1Qgw149gN/u6C3brtfyt19AE9YCWLPRq+9zIpCLegE5wer/ LADDd1DPoRcPycgEuzGSwqyvEkeotz/Q2gpA9L4YIH42KI7UWV7RWIydQT47Af/kOWca uCTAci2+NX8jWcOJ7/p5JHEZ5vznTK6tcXzem6H7XyP37GYJM+MOmrNgMUfF5WiLrkJP lZUT7/T+cKjgb9vrfKS0s1+iEDfoJaY18E0jGyrsM4ybLL30lXOuxGKuCNJPyB5sYB/r erLKvo35eYpJ5f5TRWVZ4RjuSV4aoUFFWuOYu2Z4uNaaOkX2UMDpztN16UQecywwJ/ca tlKQ== X-Received: by 10.66.218.131 with SMTP id pg3mr32331158pac.89.1362401972068; Mon, 04 Mar 2013 04:59:32 -0800 (PST) Received: from localhost.localdomain (p2126-ipbf3106hodogaya.kanagawa.ocn.ne.jp. [114.149.157.126]) by mx.google.com with ESMTPS id t6sm23836060paz.11.2013.03.04.04.59.29 (version=TLSv1.2 cipher=RC4-SHA bits=128/128); Mon, 04 Mar 2013 04:59:30 -0800 (PST) From: Akinobu Mita To: linux-kernel@vger.kernel.org, akpm@linux-foundation.org Cc: Akinobu Mita , Ben Myers , Alex Elder , xfs@oss.sgi.com Subject: [PATCH -v3 12/23] xfs: rename random32() to prandom_u32() Date: Mon, 4 Mar 2013 21:58:20 +0900 X-ASG-Orig-Subj: [PATCH -v3 12/23] xfs: rename random32() to prandom_u32() Message-Id: <1362401911-14074-13-git-send-email-akinobu.mita@gmail.com> X-Mailer: git-send-email 1.8.1.2 In-Reply-To: <1362401911-14074-1-git-send-email-akinobu.mita@gmail.com> References: <1362401911-14074-1-git-send-email-akinobu.mita@gmail.com> X-Barracuda-Connect: mail-da0-f44.google.com[209.85.210.44] X-Barracuda-Start-Time: 1362401972 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=DKIM_SIGNED, DKIM_VERIFIED X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124227 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature Use more preferable function name which implies using a pseudo-random number generator. Signed-off-by: Akinobu Mita Acked-by: Cc: Ben Myers Cc: Alex Elder Cc: xfs@oss.sgi.com --- * Change from v2 - add Acked-by: line fs/xfs/xfs_alloc.c | 2 +- fs/xfs/xfs_error.c | 2 +- fs/xfs/xfs_ialloc.c | 2 +- fs/xfs/xfs_log.c | 2 +- 4 files changed, 4 insertions(+), 4 deletions(-) diff --git a/fs/xfs/xfs_alloc.c b/fs/xfs/xfs_alloc.c index 0ad2325..a8beb5c 100644 --- a/fs/xfs/xfs_alloc.c +++ b/fs/xfs/xfs_alloc.c @@ -842,7 +842,7 @@ xfs_alloc_ag_vextent_near( */ int dofirst; /* set to do first algorithm */ - dofirst = random32() & 1; + dofirst = prandom_u32() & 1; #endif restart: diff --git a/fs/xfs/xfs_error.c b/fs/xfs/xfs_error.c index 6104560..07bf3b9 100644 --- a/fs/xfs/xfs_error.c +++ b/fs/xfs/xfs_error.c @@ -66,7 +66,7 @@ xfs_error_test(int error_tag, int *fsidp, char *expression, int i; int64_t fsid; - if (random32() % randfactor) + if (prandom_u32() % randfactor) return 0; memcpy(&fsid, fsidp, sizeof(xfs_fsid_t)); diff --git a/fs/xfs/xfs_ialloc.c b/fs/xfs/xfs_ialloc.c index 515bf71..ba62661 100644 --- a/fs/xfs/xfs_ialloc.c +++ b/fs/xfs/xfs_ialloc.c @@ -369,7 +369,7 @@ xfs_ialloc_ag_alloc( * number from being easily guessable. */ error = xfs_ialloc_inode_init(args.mp, tp, agno, args.agbno, - args.len, random32()); + args.len, prandom_u32()); if (error) return error; diff --git a/fs/xfs/xfs_log.c b/fs/xfs/xfs_log.c index eec226f..b345a7c 100644 --- a/fs/xfs/xfs_log.c +++ b/fs/xfs/xfs_log.c @@ -3485,7 +3485,7 @@ xlog_ticket_alloc( tic->t_curr_res = unit_bytes; tic->t_cnt = cnt; tic->t_ocnt = cnt; - tic->t_tid = random32(); + tic->t_tid = prandom_u32(); tic->t_clientid = client; tic->t_flags = XLOG_TIC_INITED; tic->t_trans_type = 0; -- 1.8.1.2 From rdosramo@ivic.gob.ve Mon Mar 4 07:08:01 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.5 required=5.0 tests=HTML_MESSAGE,SUBJ_ALL_CAPS, T_KHOP_FOREIGN_CLICK autolearn=no version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id EF24D8042 for ; Mon, 4 Mar 2013 07:08:00 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay3.corp.sgi.com (Postfix) with ESMTP id 6F109AC002 for ; Mon, 4 Mar 2013 05:07:57 -0800 (PST) X-ASG-Debug-ID: 1362402472-04cb6c2b0314c610001-NocioJ Received: from mail.ivic.gob.ve (mail.ivic.gob.ve [190.170.128.187]) by cuda.sgi.com with ESMTP id TGegJ5NKbmN1AeLw for ; Mon, 04 Mar 2013 05:07:52 -0800 (PST) X-Barracuda-Envelope-From: rdosramo@ivic.gob.ve X-Barracuda-Apparent-Source-IP: 190.170.128.187 Received: from localhost (localhost [127.0.0.1]) by mail.ivic.gob.ve (Postfix) with ESMTP id 49F7027265E; Mon, 4 Mar 2013 08:33:28 -0430 (VET) X-Virus-Scanned: amavisd-new at ivic.gob.ve Received: from mail.ivic.gob.ve ([127.0.0.1]) by localhost (mail.ivic.gob.ve [127.0.0.1]) (amavisd-new, port 10024) with ESMTP id lw2dteD0hebZ; Mon, 4 Mar 2013 08:33:27 -0430 (VET) Received: from mail.ivic.gob.ve (mail.ivic.gob.ve [190.170.128.187]) by mail.ivic.gob.ve (Postfix) with ESMTP id 90DA2272260; Mon, 4 Mar 2013 08:33:26 -0430 (VET) Date: Mon, 04 Mar 2013 08:33:26 -0430 (VET) From: BNP PARIBAS FORTIS Subject: 2013 ACOOUNT NODIG =?utf-8?Q?VEILIGHEIDSMAATREGELEN=E2=80=8F?= Message-ID: X-ASG-Orig-Subj: 2013 ACOOUNT NODIG =?utf-8?Q?VEILIGHEIDSMAATREGELEN=E2=80=8F?= Content-Type: multipart/alternative; boundary="=_cdaaf095-b606-412f-859b-259300a28052" MIME-Version: 1.0 X-Originating-IP: [41.71.188.250] X-Mailer: Zimbra 7.1.2_GA_3268 (zclient/7.1.2_GA_3268) To: undisclosed-recipients:; X-Barracuda-Connect: mail.ivic.gob.ve[190.170.128.187] X-Barracuda-Start-Time: 1362402472 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 1.00 X-Barracuda-Spam-Status: No, SCORE=1.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_MV0224, BSF_SC7_SA578_CH, HTML_MESSAGE X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124227 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 HTML_MESSAGE BODY: HTML included in message 0.50 BSF_SC0_MV0224 FULL: Custom rule MV0224 0.50 BSF_SC7_SA578_CH Custom Rule SA578_CH --=_cdaaf095-b606-412f-859b-259300a28052 Content-Type: text/plain; charset=utf-8 Content-Transfer-Encoding: 7bit Geachte BNP PARIBAS FORTIS Client Houd er rekening mee dat de toegang tot uw online account dreigt te verlopen. Om de toegang tot uw online account actief te houden, vragen wij u dan gelieve om zo snel mogelijk te inloggen. Gebruik de onderstaande link om verder te gaan en toegang te krijgen tot uw account. Na dat u gebruik heeft gemaakt van de onderstaande link zal er door een van onze medewerkers nog contact met u worden opgenomen om het gehele proces te voltooien. Wanneer het gehele proces gereed is zal u weer als vanouds gebruik kunnen maken van uw BNP PARIBAS FORTIS online. Klik hier Met toegang tot uw BNP PARIBAS FORTIS online kunt u het grootste deel van uw bankverrichtingen uitvoeren. Alles wat u nodig hebt is u aanmelden bij internet bankieren. Wij willen u alvast bedanken voor uw medewerking. Hoogachtend, Klantenservice. --=_cdaaf095-b606-412f-859b-259300a28052 Content-Type: text/html; charset=utf-8 Content-Transfer-Encoding: quoted-printable
Geachte BNP PARIBAS FORTIS Client

Houd er rekening mee= dat de toegang tot uw online account dreigt te verlopen.
Om de toegang = tot uw online account actief te houden, vragen wij u dan gelieve
om zo = snel mogelijk te inloggen.

Gebruik de onderstaande link om verder te= gaan en toegang te krijgen tot uw account.
Na dat u gebruik heeft gemaa= kt van de onderstaande link zal er door een van onze medewerkers
nog co= ntact met u worden opgenomen om het gehele proces te voltooien. Wanneer het=
gehele proces gereed is zal u weer als vanouds gebruik kunnen maken va= n uw BNP PARIBAS FORTIS online.

Klik hier

Met toega= ng tot uw BNP PARIBAS FORTIS online kunt u het grootste deel van uw bankver= richtingen uitvoeren.
Alles wat u nodig hebt is u aanmelden bij internet= bankieren.
Wij willen u alvast bedanken voor uw medewerking.
Hoogac= htend,
Klantenservice.
--=_cdaaf095-b606-412f-859b-259300a28052-- From sandeen@sandeen.net Mon Mar 4 09:17:51 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 9414A8042 for ; Mon, 4 Mar 2013 09:17:51 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay1.corp.sgi.com (Postfix) with ESMTP id 7C68C8F8037 for ; Mon, 4 Mar 2013 07:17:51 -0800 (PST) X-ASG-Debug-ID: 1362410270-04cbb07dbf158610001-NocioJ Received: from sandeen.net (sandeen.net [63.231.237.45]) by cuda.sgi.com with ESMTP id k9ZCKuYy56uMkQSh for ; Mon, 04 Mar 2013 07:17:50 -0800 (PST) X-Barracuda-Envelope-From: sandeen@sandeen.net X-Barracuda-Apparent-Source-IP: 63.231.237.45 Received: from liberator.sandeen.net (liberator.sandeen.net [10.0.0.4]) (using TLSv1 with cipher DHE-RSA-CAMELLIA256-SHA (256/256 bits)) (No client certificate requested) by sandeen.net (Postfix) with ESMTPSA id E97BB63C58E8; Mon, 4 Mar 2013 09:17:49 -0600 (CST) Message-ID: <5134BB1F.4020207@sandeen.net> Date: Mon, 04 Mar 2013 09:17:51 -0600 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: Ole Tange CC: Dave Chinner , xfs@oss.sgi.com Subject: Re: xfs_repair segfaults References: <5131283F.8030704@sandeen.net> <20130301223116.GE23616@dastard> <51312C73.5060203@sandeen.net> X-ASG-Orig-Subj: Re: xfs_repair segfaults In-Reply-To: X-Enigmail-Version: 1.5 Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: sandeen.net[63.231.237.45] X-Barracuda-Start-Time: 1362410270 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124235 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On 3/4/13 6:47 AM, Ole Tange wrote: > On Fri, Mar 1, 2013 at 11:32 PM, Eric Sandeen wrote: > >> Ole, you can xfs_mdrestore your metadump image and run test repairs on the result, >> if you want a more realistic "dry run" of what repair would do. > > I have never run xfs_mdrestore before. > > From the man page: > > xfs_mdrestore should not be used to restore metadata onto an > existing filesystem unless you are completely certain the target can > be destroyed. > > It is unclear to me if you are suggesting me to do: > > xfs_mdrestore the-already-created-dump /dev/md5p1 no. definitely not. :) > followed by xfs_repair. Or if you want me to restore the metadata on > another 100 TB partition (I do not have that available). Nope - to a sparse file, on a filesystem which can hold a file with 100T offsets - like xfs. > Maybe you have a trick so that it can be restored on some smaller > block device, so I do not need the 100 TB partition, but I will still > be able to see how many files are being removed? If you have such a > trick, consider including it in the manual. Probably worth doing, or putting in the xfs faq. Basically, if you do: # xfs_mdatadump -o /dev/whatever metadump.file # xfs_mdrestore metadump.file xfsfile.img or # xfs_metadump -o /dev/whatever - | xfs_mdrestore - xfsfile.img then you can xfs_repair xfsfile.img, without the -n, see what happens, mount the image as loopback, see what's changed, etc, to see what xfs_repair really would do with your actual filesystem. (although, if things are so badly corrupted that metadump gets confused, it's not as good a test). The metadump only contains *metadata* so if you read any file on the mounted loopback image, you just get 0s back. > Also I would love if xfs_repair had an option to copy the changed > sectors to a file, so it would be easy to revert. E.g: > > xfs_repair --backup backup.file /dev/sda1 > > and if the repair did not work out, then you could revert using: > > xfs_repair --revert backup.file /dev/sda1 > > and be back at your starting state. That would be nice. But as soon as you have mounted the result and made any change at all to the fs, reverting in this manner wouldn't be safe anymore. -Eric > > /Ole > From sandeen@sandeen.net Mon Mar 4 09:20:08 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 1E84F8045 for ; Mon, 4 Mar 2013 09:20:08 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay1.corp.sgi.com (Postfix) with ESMTP id F03C08F8035 for ; Mon, 4 Mar 2013 07:20:07 -0800 (PST) X-ASG-Debug-ID: 1362410403-04bdf02297164fd0001-NocioJ Received: from sandeen.net (sandeen.net [63.231.237.45]) by cuda.sgi.com with ESMTP id 3imJw6wjHcac4lWW for ; Mon, 04 Mar 2013 07:20:03 -0800 (PST) X-Barracuda-Envelope-From: sandeen@sandeen.net X-Barracuda-Apparent-Source-IP: 63.231.237.45 Received: from liberator.sandeen.net (liberator.sandeen.net [10.0.0.4]) (using TLSv1 with cipher DHE-RSA-CAMELLIA256-SHA (256/256 bits)) (No client certificate requested) by sandeen.net (Postfix) with ESMTPSA id F336B63C58E9; Mon, 4 Mar 2013 09:20:02 -0600 (CST) Message-ID: <5134BBA4.3060305@sandeen.net> Date: Mon, 04 Mar 2013 09:20:04 -0600 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: Ole Tange CC: xfs@oss.sgi.com Subject: Re: xfs_repair segfaults References: <512FA67D.2090708@sandeen.net> <5130DB54.9030503@sandeen.net> X-ASG-Orig-Subj: Re: xfs_repair segfaults In-Reply-To: X-Enigmail-Version: 1.5 Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: sandeen.net[63.231.237.45] X-Barracuda-Start-Time: 1362410403 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124237 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On 3/4/13 3:00 AM, Ole Tange wrote: > On Fri, Mar 1, 2013 at 5:46 PM, Eric Sandeen wrote: >> On 3/1/13 3:37 AM, Ole Tange wrote: > >>> Please consider providing an example in the man page for xfs_metadump e.g: >>> >>> xfs_metadump.sh -g /dev/sda2 meta.dump >> >> From the manpage, >> >> SYNOPSIS >> xfs_metadump [ -efgow ] [ -l logdev ] source target >> >> The source argument must be the pathname of >> the device or file containing the XFS filesystem >> >> and >> >> the target argument specifies the destination file name. >> >> is not enough? > > I have never run xfs_metadump before and I am in a state of worry that > my filesystem is toast. I would therefore like to be re-assured that > what I am doing is correct. I did that by reading and re-reading the > manual to make sure I had understood it correctly. By providing me > with an example of the right way to do it in the man page, I will feel > more confident that what I am about to do it correct and I could > probably save time by not having to re-read the manual. > > So I am not saying the information is not there, what I am saying is > that you in a simple way could make it easier to grasp the > information. Fair enough, maybe a concrete example is warranted. I suggested the meatadump for 2 reasons: 1) to get an image we could look at, to analyze the reason for the segfault, and 2) so you could run a "real" non-"n" xfs_repair on a metadata image as a more realistic dry run xfs_metadump only *reads* your filesystem, so there is nothing dangerous. But I understand your paranoia and worry. :) -Eric > > /Ole > From bpm@sgi.com Mon Mar 4 10:31:52 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 809EF803D for ; Mon, 4 Mar 2013 10:31:52 -0600 (CST) Received: from whiskey.americas.sgi.com (eagdhcp-232-197.americas.sgi.com [128.162.232.197]) by relay3.corp.sgi.com (Postfix) with ESMTP id 0A6DDAC005; Mon, 4 Mar 2013 08:31:48 -0800 (PST) Received: by whiskey.americas.sgi.com (Postfix, from userid 4600) id 90B29500B4A; Mon, 4 Mar 2013 10:31:48 -0600 (CST) Date: Mon, 4 Mar 2013 10:31:48 -0600 From: Ben Myers To: Dave Chinner Cc: xfs@oss.sgi.com Subject: Re: [PATCH 2/9] xfs: add support for large btree blocks Message-ID: <20130304163148.GF22182@sgi.com> References: <1358774760-21841-1-git-send-email-david@fromorbit.com> <1358774760-21841-3-git-send-email-david@fromorbit.com> <20130215212015.GO22182@sgi.com> <20130222013456.GN26694@dastard> <20130223022722.GI26081@dastard> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <20130223022722.GI26081@dastard> User-Agent: Mutt/1.5.20 (2009-06-14) Hi Dave, On Sat, Feb 23, 2013 at 01:27:22PM +1100, Dave Chinner wrote: > On Fri, Feb 22, 2013 at 12:34:56PM +1100, Dave Chinner wrote: > > On Fri, Feb 15, 2013 at 03:20:15PM -0600, Ben Myers wrote: > > > On Tue, Jan 22, 2013 at 12:25:53AM +1100, Dave Chinner wrote: > > > > From: Christoph Hellwig > > > > > > > > Add support for larger btree blocks that contains a CRC32C checksum, > > > > a filesystem uuid and block number for detecting filesystem > > > > consistency and out of place writes. > > > > > > > > [dchinner@redhat.com] Also include an owner field to allow reverse > > > > mappings to be implemented for improved repairability and a LSN > > > > field to so that log recovery can easily determine the last > > > > modification that made it to disk for each buffer. > > > > > > > > [dchinner@redhat.com] Add buffer log format flags to indicate the > > > > type of buffer to recovery so that we don't have to do blind magic > > > > number tests to determine what the buffer is. > > > > > > > > [dchinner@redhat.com] Modified to fit into the verifier structure. > > > > > > This patch is far too large for a good review. It needs to be split up into > > > it's various ideas which you outlined in patch 0. If you need to add dead code > > > in each piece and then enable it at the end, that's fine with me. > > > > You want it broken up into 7 or 8 separate patches - what does it > > gain us? It'll take a week for me to do the patch monkeying and to > > retest and validate the resulting stack (i.e. it is bisectable, each > > patch passes xfstests, etc), and in the end the code will be > > identical. > > > > As I've said before, there's a point where the tradeoff for > > splitting patches up doesn't make sense. Asking a developer to do > > days of work to end up with exactly the same code to save the > > reviewer an hour or two is *not* a good tradeoff. Especially for the > > first patch of a much larger 15-20 patch series which contains > > several larger and more complex patches.... > > Ben, reading this back it comes across as unnecessarily negative and > narky. I was just about at the end of the attribute leaf changes and > it's been a mind-numbing slog making mechanical changes to lots of > code. > > This is after having to do the same slog through all the directory > code. The block, leaf, node, freespace and da_btree code all had to > get the same treatment, and it's worn me down. My wrists are > starting to hurt from the last three months of slogging through this > stuff (roughly +20,000/-10,000 lines modified according to a quick > diffstat) and that doesn't make me a happy camper. > > So I'm not meaning to be narky or nasty - I just want to get this > stuff done ASAP before it burns me out. Hence the prospect of having > to go back and redo significant chunks to split out trivial pieces > of code (i.e. a mind-numbing slog making mechanical changes) hit a > bit of a raw nerve. > > All I'm asking is that you take into account the extra load that the > rework you ask me to do adds and whether it is absolutely necessary > to be able to review the code. The last thing I want is be burnt out > by this stuff.... Once I get back to it I'll consider whether to pull it apart myself. I had a hard time keeping track of everything that was going on in that patch. And it seems like whenever that happens I miss something important in my review. Working through the rest of the series may also help to get more comfortable with this patch. -Ben From bpm@sgi.com Mon Mar 4 10:33:43 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 9D21C803D for ; Mon, 4 Mar 2013 10:33:43 -0600 (CST) Received: from whiskey.americas.sgi.com (eagdhcp-232-197.americas.sgi.com [128.162.232.197]) by relay1.corp.sgi.com (Postfix) with ESMTP id 7540F8F8037; Mon, 4 Mar 2013 08:33:40 -0800 (PST) Received: by whiskey.americas.sgi.com (Postfix, from userid 4600) id 51F0C500B4B; Mon, 4 Mar 2013 10:33:40 -0600 (CST) Date: Mon, 4 Mar 2013 10:33:40 -0600 From: Ben Myers To: Dave Chinner Cc: xfs@oss.sgi.com Subject: Re: [PATCH 0/9] xfs: metadata CRCs, kernel, first batch Message-ID: <20130304163340.GG22182@sgi.com> References: <1358774760-21841-1-git-send-email-david@fromorbit.com> <20130222151931.GU22182@sgi.com> <20130222231217.GA26081@dastard> <20130222235029.GA30652@sgi.com> <20130223023818.GJ26081@dastard> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <20130223023818.GJ26081@dastard> User-Agent: Mutt/1.5.20 (2009-06-14) Hi Dave, On Sat, Feb 23, 2013 at 01:38:18PM +1100, Dave Chinner wrote: > On Fri, Feb 22, 2013 at 05:50:29PM -0600, Ben Myers wrote: > > On Sat, Feb 23, 2013 at 10:12:17AM +1100, Dave Chinner wrote: > > > On Fri, Feb 22, 2013 at 09:19:31AM -0600, Ben Myers wrote: > > > This is mentioned in the patch zero description: > > > > > > "This series makes is through to 001-092 in xfstests - there is a > > > problem in the dquot verifier that causes log recovery of dquot > > > buffers to follow a NULL pointer." > > > > > > Basically, mp->m_quotainfo is not initialised until after log > > > recovery occurs, so this has to be detected in the verify/crc > > > routines otherwise it goes splat like above. My current patch series > > > has this fixed. > > > > Cool. Sorry for the extra noise. > > No, that's fine. It tells me that you're actaully looking at the > code and seeing what it does ;) > > I'm close to having a new version of the kernel patchset out. I've > just got to finish debugging the attribute changes I've made and > move the superblock support patch to the end of the series and I'll > post it out. > > All I'm aiming for with the next version of the patch set is that > existing filesystems (i.e. no CRCs) are regression free. I've > actaully done very little CRC enabled testing while doing all the > directory and attribute code changes, mainly because I can't test > them properly until the userspace support is there. However, the > patch set up to the final patch (i.e. everything but the attribute > changes) seems to work just fine with the existing toolchain and > xfstests. > > Put simply, my focus for testing the patch set is currently "no > regressions for existing users", not "CRCs work perfectly". Sounds good. I'll keep that in mind. -Ben From hpj@urpla.net Mon Mar 4 10:40:28 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 84C5B804E for ; Mon, 4 Mar 2013 10:40:28 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay1.corp.sgi.com (Postfix) with ESMTP id 6BE768F804B for ; Mon, 4 Mar 2013 08:40:28 -0800 (PST) X-ASG-Debug-ID: 1362415226-04cb6c2b01157de0001-NocioJ Received: from moutng.kundenserver.de (moutng.kundenserver.de [212.227.17.8]) by cuda.sgi.com with ESMTP id oXc3Ew1OlxgONvSR (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Mon, 04 Mar 2013 08:40:26 -0800 (PST) X-Barracuda-Envelope-From: hpj@urpla.net X-Barracuda-Apparent-Source-IP: 212.227.17.8 Received: from lisa (p5B2A4C2B.dip0.t-ipconnect.de [91.42.76.43]) by mrelayeu.kundenserver.de (node=mreu3) with ESMTP (Nemesis) id 0M2CDg-1V22az2Up2-00s8L3; Mon, 04 Mar 2013 17:40:25 +0100 Received: from localhost (localhost [127.0.0.1]) by tyrex.lisa.loc (Postfix) with ESMTP id 7140F1B971B00 for ; Mon, 4 Mar 2013 17:40:25 +0100 (CET) X-Virus-Scanned: amavisd-new at lisa.loc Received: from tyrex.lisa.loc ([127.0.0.1]) by localhost (tyrex.lisa.loc [127.0.0.1]) (amavisd-new, port 10024) with LMTP id 1hCBpu20T1kh for ; Mon, 4 Mar 2013 17:40:13 +0100 (CET) From: Hans-Peter Jansen To: xfs@oss.sgi.com Subject: strange behavior of a larger xfs directory Date: Mon, 04 Mar 2013 17:40:13 +0100 X-ASG-Orig-Subj: strange behavior of a larger xfs directory Message-ID: <4300208.uZ6HVTycB6@xrated> User-Agent: KMail/4.9.5 (Linux/3.4.28-2.20-desktop; KDE/4.9.5; x86_64; ; ) MIME-Version: 1.0 Content-Transfer-Encoding: 7Bit Content-Type: text/plain; charset="us-ascii" X-Provags-ID: V02:K0:13P12aebZzRWAaq7njB74x5f/jwTk7aSHzUoSnX5O86 M631Db36Q4l88YffvUmhwuHB0haLdAxP/t6dUVRPXxBwOgGrFM JlcGqEe0dmudjYnAvBQWHRUNnGzfOzecuuUKd3ptrjdidy7NwE erqVrg3iZT4UvIv3+2fwY+vFSv3Qtp5DQ4/6PiCrspAwxt9KQd xcBIHlItJMDuB4fHAABGU3KK/ctPL2DdCO5VGG+IFdFQ1ssdY7 krCex7e+x5ugHtWIQ0WOXV3XSrXnRIRxGP+xQsT+RBGYPVNEYJ x5q8KS4QJA4oAvGTuG4pxqE4jznplBCGONayO88MZnGlnIJeQ= = X-Barracuda-Connect: moutng.kundenserver.de[212.227.17.8] X-Barracuda-Start-Time: 1362415226 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124241 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- Hi, after upgrading the kernel on a server from 2.6.34 to 3.8.1 (x86-32), I suffer from a strange behavior of a larger directory, that a downgrade of the kernel cannot repair. The best way to reproduce the problem is cd into that directory and running "vi .". It should display a full directory listing, but it only displays a about dozen entries. Another way is just using bash tab completion (e.g. ls should display a screenful of items, but only shows the very same dozen of entries. Userspace is quite old (openSUSE 11.1/i586, but I cannot upgrade to a newer userspace for a couple of reasons. OTOH, a simple ls displays the full list again, as well as does a simple python script: import os for i in os.listdir("/video/video"): print i, os.lstat(os.path.join("/video/video", i)) As far as I understand Linux, this kind of kernel upgrade should work just fine (minus the usual udev fallout, that isn't an issue for a server (this one at least). Everything is working fine so far, bind, dhcpd, samba, NFS3 (homes are mounted from it), postfix, cyrus imapd, mysql (with many databases), ntp, you name it. It is also serving vdr video streams and records, and its record directory is the one, that shows the issues, resulting in some displeasure in my family. stracing the vi call reveals 27177 open("/video/video/", O_RDONLY|O_NONBLOCK|O_LARGEFILE|O_DIRECTORY|O_CLOEXEC) = 3 27177 fstat64(3, {st_dev=makedev(8, 65), st_ino=357, st_mode=S_IFDIR|0775, st_nlink=350, st_uid=223, st_gid=33, st_blksize=4096, st_blocks=40, st_size=16384, st_atime=2013/03/04-16:12:37, st_mtime=2013/03/04-16:17:52, st_ctime=2013/03/04-16:17:52}) = 0 27177 getdents64(3, { {d_ino=357, d_off=4, d_type=DT_UNKNOWN, d_reclen=24, d_name="."} {d_ino=128, d_off=6, d_type=DT_UNKNOWN, d_reclen=24, d_name=".."} {d_ino=367, d_off=12, d_type=DT_UNKNOWN, d_reclen=56, d_name="%Avatar_-_Aufbruch_nach_Pandora"} {d_ino=368, d_off=18, d_type=DT_UNKNOWN, d_reclen=56, d_name="%Der_Deutsche_Comedy_Preis_2009"} [...] {d_ino=4303329151, d_off=78, d_type=DT_UNKNOWN, d_reclen=32, d_name="Black_Swan"} [...]}) = 4072 # note: including items, that are missing later on, probably all 27177 _llseek(3, 74, [74], SEEK_SET) = 0 # now a couple of stat64 calls of entries that are displayed later 27177 stat64("/video/video/%Avatar_-_Aufbruch_nach_Pandora", {st_dev=makedev(8, 65), st_ino=367, st_mode=S_IFDIR|0755, st_nlink=3, st_uid=223, st_gid=33, st_blksize=4096, st_blocks=0, st_size=39, st_atime=2013/03/04-07:49:20, st_mtime=2011/02/03-23:21:08, st_ctime=2011/09/10-17:55:32}) = 0 27177 stat64("/video/video/%Avatar_-_Aufbruch_nach_Pandora", {st_dev=makedev(8, 65), st_ino=367, st_mode=S_IFDIR|0755, st_nlink=3, st_uid=223, st_gid=33, st_blksize=4096, st_blocks=0, st_size=39, st_atime=2013/03/04-07:49:20, st_mtime=2011/02/03-23:21:08, st_ctime=2011/09/10-17:55:32}) = 0 27177 stat64("/video/video/%Avatar_-_Aufbruch_nach_Pandora", {st_dev=makedev(8, 65), st_ino=367, st_mode=S_IFDIR|0755, st_nlink=3, st_uid=223, st_gid=33, st_blksize=4096, st_blocks=0, st_size=39, st_atime=2013/03/04-07:49:20, st_mtime=2011/02/03-23:21:08, st_ctime=2011/09/10-17:55:32}) = 0 [...] # then it preceeds with getdents64 and fetches already fetched entries 27177 getdents64(3, { {d_ino=4303329151, d_off=78, d_type=DT_UNKNOWN, d_reclen=32, d_name="Black_Swan"} [...]}) = 4088 27177 close(3) = 0 This looks silly. Shouldn't getdent64 only return not yet processed entries? Full trace is available here: ftp://urpla.net/video.trc xfs-info: meta-data=/dev/sde1 isize=256 agcount=5, agsize=268435455 blks = sectsz=512 attr=2 data = bsize=4096 blocks=1098632439, imaxpct=5 = sunit=0 swidth=0 blks naming =version 2 bsize=4096 ascii-ci=0 log =internal bsize=4096 blocks=521728, version=2 = sectsz=512 sunit=0 blks, lazy-count=1 realtime =none extsz=4096 blocks=0, rtextents=0 xfs_repair (3.1.6) doesn't choke on any errors. Could some kind soul with more insight shed some light on this issue? From bpm@sgi.com Mon Mar 4 11:40:15 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id C6DF9803D for ; Mon, 4 Mar 2013 11:40:15 -0600 (CST) Received: from whiskey.americas.sgi.com (eagdhcp-232-197.americas.sgi.com [128.162.232.197]) by relay2.corp.sgi.com (Postfix) with ESMTP id AE097304051; Mon, 4 Mar 2013 09:40:12 -0800 (PST) Received: by whiskey.americas.sgi.com (Postfix, from userid 4600) id 4ED2F500B4A; Mon, 4 Mar 2013 11:40:12 -0600 (CST) Date: Mon, 4 Mar 2013 11:40:12 -0600 From: Ben Myers To: Dave Chinner Cc: xfs@oss.sgi.com Subject: Re: [PATCH 5/9] xfs: add CRC checks to the AGI Message-ID: <20130304174012.GH22182@sgi.com> References: <1358774760-21841-1-git-send-email-david@fromorbit.com> <1358774760-21841-6-git-send-email-david@fromorbit.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <1358774760-21841-6-git-send-email-david@fromorbit.com> User-Agent: Mutt/1.5.20 (2009-06-14) Dave, On Tue, Jan 22, 2013 at 12:25:56AM +1100, Dave Chinner wrote: > From: Dave Chinner > > Same set of changes made to the AGF need to be made to the AGI. > This patch has a similar history to the AGF, hence a similar > sign-off chain. > > Signed-off-by: Dave Chinner > Signed-off-by: Christoph Hellwig > Signed-off-by: Dave Chinner This one looks fine to me. -Ben From bpm@sgi.com Mon Mar 4 11:41:22 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 83C518051 for ; Mon, 4 Mar 2013 11:41:22 -0600 (CST) Received: from whiskey.americas.sgi.com (eagdhcp-232-197.americas.sgi.com [128.162.232.197]) by relay2.corp.sgi.com (Postfix) with ESMTP id 5F440304032; Mon, 4 Mar 2013 09:41:21 -0800 (PST) Received: by whiskey.americas.sgi.com (Postfix, from userid 4600) id B9F84500B4B; Mon, 4 Mar 2013 11:41:21 -0600 (CST) Date: Mon, 4 Mar 2013 11:41:21 -0600 From: Ben Myers To: Dave Chinner Cc: xfs@oss.sgi.com Subject: Re: [PATCH 5/9] xfs: add CRC checks to the AGI Message-ID: <20130304174121.GI22182@sgi.com> References: <1358774760-21841-1-git-send-email-david@fromorbit.com> <1358774760-21841-6-git-send-email-david@fromorbit.com> <20130304174012.GH22182@sgi.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <20130304174012.GH22182@sgi.com> User-Agent: Mutt/1.5.20 (2009-06-14) On Mon, Mar 04, 2013 at 11:40:12AM -0600, Ben Myers wrote: > On Tue, Jan 22, 2013 at 12:25:56AM +1100, Dave Chinner wrote: > > From: Dave Chinner > > > > Same set of changes made to the AGF need to be made to the AGI. > > This patch has a similar history to the AGF, hence a similar > > sign-off chain. > > > > Signed-off-by: Dave Chinner > > Signed-off-by: Christoph Hellwig > > Signed-off-by: Dave Chinner > > This one looks fine to me. Meh. I meant to reply to the v2 posting. -Ben From david@fromorbit.com Mon Mar 4 15:03:19 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 0D969804E for ; Mon, 4 Mar 2013 15:03:19 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay1.corp.sgi.com (Postfix) with ESMTP id EEB308F8064 for ; Mon, 4 Mar 2013 13:03:15 -0800 (PST) X-ASG-Debug-ID: 1362430993-04cb6c2b0416e030001-NocioJ Received: from ipmail06.adl2.internode.on.net (ipmail06.adl2.internode.on.net [150.101.137.129]) by cuda.sgi.com with ESMTP id COEKvkUENUqFpBgK for ; Mon, 04 Mar 2013 13:03:14 -0800 (PST) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.129 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AhshAAsLNVF5Layr/2dsb2JhbABEvTuFFQECAYEIF3OCHwEBBAEnExwjBQsIAw4KCSUPBSUDIROIDQWyPo8xFY12GB9KB4NAA5ZFiWWHCIMc Received: from ppp121-45-172-171.lns20.syd6.internode.on.net (HELO dastard) ([121.45.172.171]) by ipmail06.adl2.internode.on.net with ESMTP; 05 Mar 2013 07:33:13 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UCcXP-0006Yj-2l; Tue, 05 Mar 2013 08:03:11 +1100 Date: Tue, 5 Mar 2013 08:03:11 +1100 From: Dave Chinner To: Tony Lu Cc: Mark Tinguely , Alex Elder , "linux-kernel@vger.kernel.org" , Chris Metcalf , "xfs@oss.sgi.com" , Ben Myers , Dave Chinner , "linux-fsdevel@vger.kernel.org" Subject: Re: [PATCH] xfs: Fix possible truncation of log data in xlog_bread_noalign() Message-ID: <20130304210311.GQ23616@dastard> X-ASG-Orig-Subj: Re: [PATCH] xfs: Fix possible truncation of log data in xlog_bread_noalign() References: <20130223000802.GB26081@dastard> <20130223235546.GA5551@dastard> <20130224141017.GC5551@dastard> <5130CE9E.9080501@sgi.com> <51310E7A.1000905@sgi.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail06.adl2.internode.on.net[150.101.137.129] X-Barracuda-Start-Time: 1362430993 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124259 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Mon, Mar 04, 2013 at 08:32:45AM +0000, Tony Lu wrote: > Thanks for you following up. > > My apologize that I just found that it is one change I made before > that causes this problem. This change forces mkfs.xfs to format > xfs partitions whose sectorsize were not smaller than 4096 bytes, > which was due to a bug that earlier versions of xfs used (struct > *page)->private(long) as a bitmap to represent each block's state > within a page (the size of a page could be 64K or larger, then it > needs 128 bit or more to represent each block's state within a > page). You do realise that bug doesn't affect x86-64 platforms as they don't support 64k pages? > This is reproducible on 2.6.38.6 kernel on X86. But I do not get > why this change makes the xfs log inconsistent during > mount/cp/umount operations. Neither do I, and I don't care to look any further because the problem is of your own making. In future, please check first that the bug you are reporting is reproducable on a current upstream kernel and userspace. Cheers, Dave. -- Dave Chinner david@fromorbit.com From jlbec@ftp.linux.org.uk Mon Mar 4 15:05:43 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id A965D804E for ; Mon, 4 Mar 2013 15:05:43 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay2.corp.sgi.com (Postfix) with ESMTP id 68D25304059 for ; Mon, 4 Mar 2013 13:05:40 -0800 (PST) X-ASG-Debug-ID: 1362431137-04bdf02297180ee0001-NocioJ Received: from ZenIV.linux.org.uk (zeniv.linux.org.uk [195.92.253.2]) by cuda.sgi.com with ESMTP id wcXrzqhxV7GRrDkG (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO) for ; Mon, 04 Mar 2013 13:05:38 -0800 (PST) X-Barracuda-Envelope-From: jlbec@ftp.linux.org.uk X-Barracuda-Apparent-Source-IP: 195.92.253.2 Received: from jlbec by ZenIV.linux.org.uk with local (Exim 4.76 #1 (Red Hat Linux)) id 1UCcZa-0002hl-Mw; Mon, 04 Mar 2013 21:05:26 +0000 Date: Mon, 4 Mar 2013 13:05:23 -0800 From: Joel Becker To: Dave Chinner Cc: Eric Sandeen , Richard Weinberger , linux-fsdevel@vger.kernel.org, xfs@oss.sgi.com Subject: Re: [PATCH] Do not check ocfs2 Message-ID: <20130304210522.GA7783@localhost> X-ASG-Orig-Subj: Re: [PATCH] Do not check ocfs2 Mail-Followup-To: Dave Chinner , Eric Sandeen , Richard Weinberger , linux-fsdevel@vger.kernel.org, xfs@oss.sgi.com References: <1362269150-21478-1-git-send-email-richard@nod.at> <20130303011917.GI23616@dastard> <20130303100254.500b076f@spider.haslach.nod.at> <5133C900.9050300@sandeen.net> <20130303231905.0efd6d08@spider.haslach.nod.at> <5133D15A.9010600@sandeen.net> <20130303235341.7470085e@spider.haslach.nod.at> <5133D573.3050106@sandeen.net> <20130304004229.GK23616@dastard> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <20130304004229.GK23616@dastard> X-Burt-Line: Trees are cool. X-Red-Smith: Ninety feet between bases is perhaps as close as man has ever come to perfection. User-Agent: Mutt/1.5.21 (2010-09-15) Sender: Joel Becker X-Barracuda-Connect: zeniv.linux.org.uk[195.92.253.2] X-Barracuda-Start-Time: 1362431138 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124259 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Mon, Mar 04, 2013 at 11:42:29AM +1100, Dave Chinner wrote: > On Sun, Mar 03, 2013 at 04:57:55PM -0600, Eric Sandeen wrote: > > On 3/3/13 4:53 PM, Richard Weinberger wrote: > > > > >> Anyway, what if you did something more along the lines of [pseudocode] > > >> > > >> ocfs2) > > >> if mounted.ocfs2 -f $TEST-DEV | frob_as_necessary[1] > > >> ; > > >> else > > >> fsck.ocfs2 $TEST-DEV > > >> fi > > >> ;; > > >> > > >> so that *if* it's mounted on some other node, the fsck won't run. > > >> That has downsides as Dave mentioned, but for the case where the > > >> xfstests node is the only one with it in use, it'll still do the > > >> beneficial consistency check. > > >> > > >> Just tweaking the fsck action bsed on *if* it's mounted (or, > > >> maybe, if the node is in a cluster?) might be a more generic solution > > >> that is widely applicable to all ocfs2 test environments. > > > > > > Good point. mounted.ocfs2 really makes sense. I'll implement this on my > > > test suite and submit a new patch. > > > > Sounds good to me. > > > > It'd be most preferable to do a cluster-wide unmount and fsck, > > Which makes no sense to me, because ./check will then do a cluster > wide unmount as it runs the test harness initialisation. Hence all > the subsequent tests will run with the filesystem only mounted on > the local node.... > > Really, xfstests is not designed for testing cluster filesystems in > clustered environments. If we really want to support clustered > filesystems and cluster wide operations, then we need to think > about how to architect multi-host support into xfstests sanely. > Clustered filesystems are not the only people that could make use of > such functionality (NFS and CIFS come to mind).... ;) I'm much happier with the "check for other cluster mounts" approach rather than avoiding fsck entirely. We like xfstests in the local or single-node cases to behave exactly as one would expect. We do run xfstests on multiple nodes in a cluster, but by hand and with our own cleanup. Obviously support for automating that would be awesome :-) Joel > > Cheers, > > Dave/ > -- > Dave Chinner > david@fromorbit.com > -- > To unsubscribe from this list: send the line "unsubscribe linux-fsdevel" in > the body of a message to majordomo@vger.kernel.org > More majordomo info at http://vger.kernel.org/majordomo-info.html -- "Born under a bad sign. I been down since I began to crawl. If it wasn't for bad luck, I wouldn't have no luck at all." http://www.jlbec.org/ jlbec@evilplan.org From richard@nod.at Mon Mar 4 16:09:35 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id BEDA18053 for ; Mon, 4 Mar 2013 16:09:35 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay2.corp.sgi.com (Postfix) with ESMTP id 9E156304039 for ; Mon, 4 Mar 2013 14:09:35 -0800 (PST) X-ASG-Debug-ID: 1362434968-04bdf022971872b0001-NocioJ Received: from radon.swed.at (a.ns.miles-group.at [95.130.255.143]) by cuda.sgi.com with ESMTP id 8dGvH04kOEjXECVE (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO) for ; Mon, 04 Mar 2013 14:09:30 -0800 (PST) X-Barracuda-Envelope-From: richard@nod.at X-Barracuda-Apparent-Source-IP: 95.130.255.143 Received: (qmail 31631 invoked by uid 89); 4 Mar 2013 22:09:31 -0000 Received: by simscan 1.3.1 ppid: 31624, pid: 31627, t: 0.1638s scanners: attach: 1.3.1 clamav: 0.96.5/m: Received: from unknown (HELO spider.haslach.nod.at) (richard@nod.at@212.186.22.124) by radon.swed.at with ESMTPA; 4 Mar 2013 22:09:31 -0000 Date: Mon, 4 Mar 2013 23:09:22 +0100 From: Richard Weinberger To: Joel Becker Cc: Dave Chinner , Eric Sandeen , linux-fsdevel@vger.kernel.org, xfs@oss.sgi.com Subject: Re: [PATCH] Do not check ocfs2 Message-ID: <20130304230922.20f6c05a@spider.haslach.nod.at> X-ASG-Orig-Subj: Re: [PATCH] Do not check ocfs2 In-Reply-To: <20130304210522.GA7783@localhost> References: <1362269150-21478-1-git-send-email-richard@nod.at> <20130303011917.GI23616@dastard> <20130303100254.500b076f@spider.haslach.nod.at> <5133C900.9050300@sandeen.net> <20130303231905.0efd6d08@spider.haslach.nod.at> <5133D15A.9010600@sandeen.net> <20130303235341.7470085e@spider.haslach.nod.at> <5133D573.3050106@sandeen.net> <20130304004229.GK23616@dastard> <20130304210522.GA7783@localhost> X-Mailer: Claws Mail 3.8.1 (GTK+ 2.24.14; x86_64-suse-linux-gnu) Mime-Version: 1.0 Content-Type: text/plain; charset=US-ASCII Content-Transfer-Encoding: 7bit X-Barracuda-Connect: a.ns.miles-group.at[95.130.255.143] X-Barracuda-Start-Time: 1362434969 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124263 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- Am Mon, 4 Mar 2013 13:05:23 -0800 schrieb Joel Becker : > > Really, xfstests is not designed for testing cluster filesystems in > > clustered environments. If we really want to support clustered > > filesystems and cluster wide operations, then we need to think > > about how to architect multi-host support into xfstests sanely. > > Clustered filesystems are not the only people that could make use of > > such functionality (NFS and CIFS come to mind).... ;) > > I'm much happier with the "check for other cluster mounts" approach > rather than avoiding fsck entirely. We like xfstests in the local or > single-node cases to behave exactly as one would expect. > > We do run xfstests on multiple nodes in a cluster, but by hand and > with our own cleanup. Obviously support for automating that would be > awesome :-) Can you share your cleanup code? Thanks, //richard From david@fromorbit.com Mon Mar 4 16:11:08 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 9AD857CBF for ; Mon, 4 Mar 2013 16:11:08 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id 8712C304032 for ; Mon, 4 Mar 2013 14:11:08 -0800 (PST) X-ASG-Debug-ID: 1362435063-04cbb07dbc177fc0001-NocioJ Received: from ipmail06.adl2.internode.on.net (ipmail06.adl2.internode.on.net [150.101.137.129]) by cuda.sgi.com with ESMTP id 0HFIlDUcIMfMo7E9 for ; Mon, 04 Mar 2013 14:11:03 -0800 (PST) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.129 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AhkhADwaNVF5Layr/2dsb2JhbABEvTuFFQECAYEJF3OCHwEBBTocIxAIAxgJJQ8FJQMhE4gSsVuPXRWNdhgfSgeDQAOTA4NCkG2DHA Received: from ppp121-45-172-171.lns20.syd6.internode.on.net (HELO dastard) ([121.45.172.171]) by ipmail06.adl2.internode.on.net with ESMTP; 05 Mar 2013 08:41:02 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UCdb2-0006iB-W0; Tue, 05 Mar 2013 09:11:01 +1100 Date: Tue, 5 Mar 2013 09:11:00 +1100 From: Dave Chinner To: CAI Qian Cc: Dave Chinner , Mark Tinguely , Brian Foster , Ben Myers , stable@vger.kernel.org, xfs@oss.sgi.com Subject: Re: request for stable inclusion Message-ID: <20130304221100.GL26081@dastard> X-ASG-Orig-Subj: Re: request for stable inclusion References: <426368976.8591643.1362386550488.JavaMail.root@redhat.com> <1879117295.8593844.1362387154930.JavaMail.root@redhat.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <1879117295.8593844.1362387154930.JavaMail.root@redhat.com> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail06.adl2.internode.on.net[150.101.137.129] X-Barracuda-Start-Time: 1362435063 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124263 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Mon, Mar 04, 2013 at 03:52:34AM -0500, CAI Qian wrote: > This is to request to apply the below commit for the stable releases > in order to fix a regression introduced by 055388a (xfs: dynamic > speculative EOF preallocation) that caused fsync() took long time during > the sparse file testing. > > For stable-3.4 and stable-3.8, it can be applied as it is. For stable-3.0, > please see the below patch which fixed the context and used xfs_bmapi() > instead of xfs_bmapi_read() which yet in the tree. Also tested on the > stable-3.0 to confirmed the original fsync() slowness regression is now > gone. Please review and ACK. I've already said no to -stable in another discussion thread, and that discussion has not yet played out. please do not try to preempt any discussion by sending patches to @stable before it is even decided if it is something we *need* to fix in 2 year old kernels. Yes, you have input into the discussion, but please do not take it upon yourself to determine what should be backported to -stable and what shouldn't be - that is for the subsystem maintainers to decide. FWIW, is your memory so short that you don't remember what happened a couple of weeks ago with the last XFS bugfix backport you requested directly to @stable and was accepted based on "it applies and builds, so it's OK?" i.e. without proper review, discussion or testing? That's right - it caused a major functional regression and that wasted a heap of time for quite a few people in sorting it out. So right now this request gets a big, fat, loud NACK from me while the aforementioned discussion takes place. Cheers, Dave. -- Dave Chinner david@fromorbit.com From hpj@urpla.net Mon Mar 4 16:55:51 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 2F6097F4C for ; Mon, 4 Mar 2013 16:55:51 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay2.corp.sgi.com (Postfix) with ESMTP id 1B3C9304032 for ; Mon, 4 Mar 2013 14:55:51 -0800 (PST) X-ASG-Debug-ID: 1362437748-04cb6c2b02177360001-NocioJ Received: from moutng.kundenserver.de (moutng.kundenserver.de [212.227.17.10]) by cuda.sgi.com with ESMTP id q9i6Eil4FAZukOEr (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Mon, 04 Mar 2013 14:55:49 -0800 (PST) X-Barracuda-Envelope-From: hpj@urpla.net X-Barracuda-Apparent-Source-IP: 212.227.17.10 Received: from lisa (p5B2A4C2B.dip0.t-ipconnect.de [91.42.76.43]) by mrelayeu.kundenserver.de (node=mrbap1) with ESMTP (Nemesis) id 0LtlI5-1UtRL71Ycn-0110Ti; Mon, 04 Mar 2013 23:55:48 +0100 Received: from localhost (localhost [127.0.0.1]) by tyrex.lisa.loc (Postfix) with ESMTP id 20B651B971B00 for ; Mon, 4 Mar 2013 23:55:48 +0100 (CET) X-Virus-Scanned: amavisd-new at lisa.loc Received: from tyrex.lisa.loc ([127.0.0.1]) by localhost (tyrex.lisa.loc [127.0.0.1]) (amavisd-new, port 10024) with LMTP id r1M05fXDHgWk for ; Mon, 4 Mar 2013 23:55:41 +0100 (CET) From: Hans-Peter Jansen To: xfs@oss.sgi.com Subject: Re: strange behavior of a larger xfs directory Date: Mon, 04 Mar 2013 23:55:40 +0100 X-ASG-Orig-Subj: Re: strange behavior of a larger xfs directory Message-ID: <5347920.zaxHybjLeK@xrated> User-Agent: KMail/4.9.5 (Linux/3.4.28-2.20-desktop; KDE/4.9.5; x86_64; ; ) In-Reply-To: <4300208.uZ6HVTycB6@xrated> References: <4300208.uZ6HVTycB6@xrated> MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable Content-Type: text/plain; charset="iso-8859-1" X-Provags-ID: V02:K0:AO1XGzJ5KmcJEukgA7Lv9s8bX8ZDl/aiIe57+GW++k+ b1jsZxixYEG/jIc69/3sw6gu/tfrYQh/N/zbJF1idpvTJIfrs3 uSVDNJkjuC520M1SpJpop3JbzV+gcfE+GvWq9omQ3A/UBdU3Sa p7Kv/+lKJIeEWRqKLXYtR0L+wrwg/HZDq5Tl9gf7vG5yC9bH5s X4URxTc2+1dNe75oE4158ufKV09CnyAzOcoZeZnCQbEktOfWyD FaMbqO/jDvL51q7rFiWrWaeZMmXdl1Dg+X6nqbvbdrAVf1TAIA c1+NC7nIeTx6GpGFxCqtrOBjlmnGj/VYS0Eytz5LgpqSKRHuw= = X-Barracuda-Connect: moutng.kundenserver.de[212.227.17.10] X-Barracuda-Start-Time: 1362437749 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124267 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- Am Montag, 4. M=E4rz 2013, 17:40:13 schrieb Hans-Peter Jansen: > Hi, >=20 > after upgrading the kernel on a server from 2.6.34 to 3.8.1 (x86-32),= I=20 > suffer from a strange behavior of a larger directory, that a downgrad= e=20 > of the kernel cannot repair. >=20 > The best way to reproduce the problem is cd into that directory and=20= > running "vi .". It should display a full directory listing, but it on= ly=20 > displays a about dozen entries. Another way is just using bash tab=20= > completion (e.g. ls should display a screenful of items, b= ut=20 > only shows the very same dozen of entries. Userspace is quite old=20 > (openSUSE 11.1/i586, but I cannot upgrade to a newer userspace for a=20= > couple of reasons. OTOH, a simple ls displays the full list again,=20= [...] > > # then it preceeds with getdents64 and fetches already fetched entr= ies >=20 > 27177 getdents64(3, { > {d_ino=3D4303329151, d_off=3D78, d_type=3DDT_UNKNOWN, d_= reclen=3D32, d_name=3D"Black_Swan"}=20 Okay, this is the culprit: 0x1007F977F overflows 32 bit, although I=20 *never* mounted anything with inode64 option.=20 For some reason, the intermediate kernel 3.8.0 has used the inode64 ver= sion by *default*. This breaks bash tab completion and vdr. After forcing th= e=20 inode32 option and copying some offenders away and back in place, the i= ssue vanishes.=20 Unlike stated in the XFS FAQs, openSUSE 11.1 *has* issues with inode64,= and even more so, if enabled by default. I will hack up a script now, that copes with this mess. Cheers, Pete From jlbec@ftp.linux.org.uk Mon Mar 4 16:57:38 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id BC3E4805C for ; Mon, 4 Mar 2013 16:57:38 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay3.corp.sgi.com (Postfix) with ESMTP id D5B6CAC003 for ; Mon, 4 Mar 2013 14:57:34 -0800 (PST) X-ASG-Debug-ID: 1362437852-04cb6c2b04177480001-NocioJ Received: from ZenIV.linux.org.uk (zeniv.linux.org.uk [195.92.253.2]) by cuda.sgi.com with ESMTP id lB1hIsls47RV3QH4 (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO) for ; Mon, 04 Mar 2013 14:57:33 -0800 (PST) X-Barracuda-Envelope-From: jlbec@ftp.linux.org.uk X-Barracuda-Apparent-Source-IP: 195.92.253.2 Received: from jlbec by ZenIV.linux.org.uk with local (Exim 4.76 #1 (Red Hat Linux)) id 1UCeK0-0004F8-43; Mon, 04 Mar 2013 22:57:28 +0000 Date: Mon, 4 Mar 2013 14:57:24 -0800 From: Joel Becker To: Richard Weinberger Cc: Dave Chinner , Eric Sandeen , linux-fsdevel@vger.kernel.org, xfs@oss.sgi.com Subject: Re: [PATCH] Do not check ocfs2 Message-ID: <20130304225724.GB7783@localhost> X-ASG-Orig-Subj: Re: [PATCH] Do not check ocfs2 Mail-Followup-To: Richard Weinberger , Dave Chinner , Eric Sandeen , linux-fsdevel@vger.kernel.org, xfs@oss.sgi.com References: <20130303011917.GI23616@dastard> <20130303100254.500b076f@spider.haslach.nod.at> <5133C900.9050300@sandeen.net> <20130303231905.0efd6d08@spider.haslach.nod.at> <5133D15A.9010600@sandeen.net> <20130303235341.7470085e@spider.haslach.nod.at> <5133D573.3050106@sandeen.net> <20130304004229.GK23616@dastard> <20130304210522.GA7783@localhost> <20130304230922.20f6c05a@spider.haslach.nod.at> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <20130304230922.20f6c05a@spider.haslach.nod.at> X-Burt-Line: Trees are cool. X-Red-Smith: Ninety feet between bases is perhaps as close as man has ever come to perfection. User-Agent: Mutt/1.5.21 (2010-09-15) Sender: Joel Becker X-Barracuda-Connect: zeniv.linux.org.uk[195.92.253.2] X-Barracuda-Start-Time: 1362437853 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124267 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Mon, Mar 04, 2013 at 11:09:22PM +0100, Richard Weinberger wrote: > Am Mon, 4 Mar 2013 13:05:23 -0800 > schrieb Joel Becker : > > > Really, xfstests is not designed for testing cluster filesystems in > > > clustered environments. If we really want to support clustered > > > filesystems and cluster wide operations, then we need to think > > > about how to architect multi-host support into xfstests sanely. > > > Clustered filesystems are not the only people that could make use of > > > such functionality (NFS and CIFS come to mind).... ;) > > > > I'm much happier with the "check for other cluster mounts" approach > > rather than avoiding fsck entirely. We like xfstests in the local or > > single-node cases to behave exactly as one would expect. > > > > We do run xfstests on multiple nodes in a cluster, but by hand and > > with our own cleanup. Obviously support for automating that would be > > awesome :-) > > Can you share your cleanup code? It's not code, unless you count DNA and neuron connections... Joel > > Thanks, > //richard > -- > To unsubscribe from this list: send the line "unsubscribe linux-fsdevel" in > the body of a message to majordomo@vger.kernel.org > More majordomo info at http://vger.kernel.org/majordomo-info.html -- Life's Little Instruction Book #139 "Never deprive someone of hope; it might be all they have." http://www.jlbec.org/ jlbec@evilplan.org From david@fromorbit.com Mon Mar 4 17:05:34 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id E66407FE2 for ; Mon, 4 Mar 2013 17:05:33 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay1.corp.sgi.com (Postfix) with ESMTP id CAA748F8035 for ; Mon, 4 Mar 2013 15:05:30 -0800 (PST) X-ASG-Debug-ID: 1362438328-04cbb07dbe17ba40001-NocioJ Received: from ipmail06.adl2.internode.on.net (ipmail06.adl2.internode.on.net [150.101.137.129]) by cuda.sgi.com with ESMTP id 2mYmVCDpJIxEvtlQ for ; Mon, 04 Mar 2013 15:05:28 -0800 (PST) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.129 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AhshAG4nNVF5Layr/2dsb2JhbAAqGr07hRUBAgGBChdzgh8BAQQBOhwjBQsIAxgJJQ8FJQMhExuHcgUNLrBTj2AVjVMjGB9KB4NAA5ZFkG2DHIFX Received: from ppp121-45-172-171.lns20.syd6.internode.on.net (HELO dastard) ([121.45.172.171]) by ipmail06.adl2.internode.on.net with ESMTP; 05 Mar 2013 09:35:28 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UCeRj-0006pF-6b; Tue, 05 Mar 2013 10:05:27 +1100 Date: Tue, 5 Mar 2013 10:05:27 +1100 From: Dave Chinner To: Hans-Peter Jansen Cc: xfs@oss.sgi.com Subject: Re: strange behavior of a larger xfs directory Message-ID: <20130304230527.GM26081@dastard> X-ASG-Orig-Subj: Re: strange behavior of a larger xfs directory References: <4300208.uZ6HVTycB6@xrated> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <4300208.uZ6HVTycB6@xrated> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail06.adl2.internode.on.net[150.101.137.129] X-Barracuda-Start-Time: 1362438328 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.10 X-Barracuda-Spam-Status: No, SCORE=0.10 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_SA085 X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124267 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.10 BSF_SC0_SA085 Custom Rule SA085 On Mon, Mar 04, 2013 at 05:40:13PM +0100, Hans-Peter Jansen wrote: > Hi, > > after upgrading the kernel on a server from 2.6.34 to 3.8.1 (x86-32), I > suffer from a strange behavior of a larger directory, that a downgrade > of the kernel cannot repair. TL;DR: problem with an old userspace and 64 bit inodes. > 27177 open("/video/video/", O_RDONLY|O_NONBLOCK|O_LARGEFILE|O_DIRECTORY|O_CLOEXEC) = 3 > 27177 fstat64(3, {st_dev=makedev(8, 65), st_ino=357, st_mode=S_IFDIR|0775, st_nlink=350, > st_uid=223, st_gid=33, st_blksize=4096, st_blocks=40, st_size=16384, > st_atime=2013/03/04-16:12:37, st_mtime=2013/03/04-16:17:52, > st_ctime=2013/03/04-16:17:52}) = 0 > 27177 getdents64(3, { > {d_ino=357, d_off=4, d_type=DT_UNKNOWN, d_reclen=24, d_name="."} > {d_ino=128, d_off=6, d_type=DT_UNKNOWN, d_reclen=24, d_name=".."} > {d_ino=367, d_off=12, d_type=DT_UNKNOWN, d_reclen=56, d_name="%Avatar_-_Aufbruch_nach_Pandora"} > {d_ino=368, d_off=18, d_type=DT_UNKNOWN, d_reclen=56, d_name="%Der_Deutsche_Comedy_Preis_2009"} > [...] > {d_ino=4303329151, d_off=78, d_type=DT_UNKNOWN, d_reclen=32, d_name="Black_Swan"} That's a 64 bit inode number right there (0x0x1007F977F), and AFAICT it's the only one in the directory. That was created when you were running 3.8.1. > [...]}) = 4072 > # note: including items, that are missing later on, probably all > > 27177 _llseek(3, 74, [74], SEEK_SET) = 0 Smoking gun. That is effectively setting the directory offset to 74 (XFS masks out the upper 32 bits of the directory position because it is invalid) and so XFS will take that offset and walk to the next valid dirent and start filling entries from there on the next getdents64 call. Your filesystem is doing exactly what userspace is asking it to do. Ah, I note that all the stat64() calls that follow stop at the dirent that is at d_off=74. So it appears that userspace is having some kind of problem related to the above entry. > # then it preceeds with getdents64 and fetches already fetched entries > > 27177 getdents64(3, { > {d_ino=4303329151, d_off=78, d_type=DT_UNKNOWN, d_reclen=32, d_name="Black_Swan"} ^^^^^^^^ And the next valid entry in the directory is offset=78. So, what it looks like to me is that whatever is parsing the linux_dirent returned by the getdents64() call is choking on the 64 bit inode number. Now, given that strace is parsing it correctly, this implies that whatever is issuing the getdents64 call is not parsing the linux_dirent64 structure correctly. In fact, I suspect what is happening is that userspace is incorrectly using a struct linux_dirent to parse the results and hence it's seeing d_off/d_type/d_reclen being invalid due to the resultant structure misalignment. Further, this is being seen by multiple different vectors, which indicates that it is probably the readdir() glibc call that is buggy, and not any of the applications. First solution: upgrade to a modern userspace. Second solution: Run 3.8.1, make sure you mount with inode32, and then run the xfs_reno tool mentioned on this page: http://xfs.org/index.php/Unfinished_work to find all the inodes with inode numbers larger than 32 bits and move them to locations with smaller inode numbers. Cheers, Dave. -- Dave Chinner david@fromorbit.com From david@fromorbit.com Mon Mar 4 17:12:06 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id CC8508051 for ; Mon, 4 Mar 2013 17:12:06 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay3.corp.sgi.com (Postfix) with ESMTP id E3976AC003 for ; Mon, 4 Mar 2013 15:12:02 -0800 (PST) X-ASG-Debug-ID: 1362438720-04cbb07dbd17bf60001-NocioJ Received: from ipmail06.adl2.internode.on.net (ipmail06.adl2.internode.on.net [150.101.137.129]) by cuda.sgi.com with ESMTP id 70mKm73WKUAW5Q71 for ; Mon, 04 Mar 2013 15:12:01 -0800 (PST) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.129 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AhkhAMspNVF5Layr/2dsb2JhbABEvTuFFQECAYEKF3OCHwEBBTocIxAIAxgJJQ8FJQMhE4gSDbB4j14VjXYYH0oHg0ADlkWJZYcIgxw Received: from ppp121-45-172-171.lns20.syd6.internode.on.net (HELO dastard) ([121.45.172.171]) by ipmail06.adl2.internode.on.net with ESMTP; 05 Mar 2013 09:41:49 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UCeXr-0006q6-N4; Tue, 05 Mar 2013 10:11:47 +1100 Date: Tue, 5 Mar 2013 10:11:37 +1100 From: Dave Chinner To: Eric Sandeen Cc: Ole Tange , xfs@oss.sgi.com Subject: Re: xfs_repair segfaults Message-ID: <20130304231137.GN26081@dastard> X-ASG-Orig-Subj: Re: xfs_repair segfaults References: <5131283F.8030704@sandeen.net> <20130301223116.GE23616@dastard> <51312C73.5060203@sandeen.net> <5134BB1F.4020207@sandeen.net> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <5134BB1F.4020207@sandeen.net> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail06.adl2.internode.on.net[150.101.137.129] X-Barracuda-Start-Time: 1362438720 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124267 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Mon, Mar 04, 2013 at 09:17:51AM -0600, Eric Sandeen wrote: > On 3/4/13 6:47 AM, Ole Tange wrote: > > On Fri, Mar 1, 2013 at 11:32 PM, Eric Sandeen wrote: > > > >> Ole, you can xfs_mdrestore your metadump image and run test repairs on the result, > >> if you want a more realistic "dry run" of what repair would do. > > > > I have never run xfs_mdrestore before. > > > > From the man page: > > > > xfs_mdrestore should not be used to restore metadata onto an > > existing filesystem unless you are completely certain the target can > > be destroyed. > > > > It is unclear to me if you are suggesting me to do: > > > > xfs_mdrestore the-already-created-dump /dev/md5p1 > > no. definitely not. :) > > > followed by xfs_repair. Or if you want me to restore the metadata on > > another 100 TB partition (I do not have that available). > > Nope - to a sparse file, on a filesystem which can hold a file with > 100T offsets - like xfs. > > > Maybe you have a trick so that it can be restored on some smaller > > block device, so I do not need the 100 TB partition, but I will still > > be able to see how many files are being removed? If you have such a > > trick, consider including it in the manual. > > Probably worth doing, or putting in the xfs faq. Examples of how to do these sorts of operations should go into the xfs users guide here: http://xfs.org/docs/xfsdocs-xml-dev/XFS_User_Guide//tmp/en-US/html/index.html Cheers, Dave. -- Dave Chinner david@fromorbit.com From david@fromorbit.com Mon Mar 4 17:18:56 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 2D55F8057 for ; Mon, 4 Mar 2013 17:18:56 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay3.corp.sgi.com (Postfix) with ESMTP id 5CA9DAC003 for ; Mon, 4 Mar 2013 15:18:55 -0800 (PST) X-ASG-Debug-ID: 1362439134-04bdf0229618c970001-NocioJ Received: from ipmail06.adl2.internode.on.net (ipmail06.adl2.internode.on.net [150.101.137.129]) by cuda.sgi.com with ESMTP id 3Nmln9PdB9vT06qi for ; Mon, 04 Mar 2013 15:18:54 -0800 (PST) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.129 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AhkhAN4qNVF5Layr/2dsb2JhbABEvTuFFQECAYEKF3OCHwEBBTIBIyMQCAMYCSUPBSUDIROIErEBj14VjVMjGB9KB4NAA5ZFkG2DHIFX Received: from ppp121-45-172-171.lns20.syd6.internode.on.net (HELO dastard) ([121.45.172.171]) by ipmail06.adl2.internode.on.net with ESMTP; 05 Mar 2013 09:48:53 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UCeei-0006r2-UV; Tue, 05 Mar 2013 10:18:52 +1100 Date: Tue, 5 Mar 2013 10:18:52 +1100 From: Dave Chinner To: Hans-Peter Jansen Cc: xfs@oss.sgi.com Subject: Re: strange behavior of a larger xfs directory Message-ID: <20130304231852.GO26081@dastard> X-ASG-Orig-Subj: Re: strange behavior of a larger xfs directory References: <4300208.uZ6HVTycB6@xrated> <5347920.zaxHybjLeK@xrated> MIME-Version: 1.0 Content-Type: text/plain; charset=iso-8859-1 Content-Disposition: inline Content-Transfer-Encoding: 8bit In-Reply-To: <5347920.zaxHybjLeK@xrated> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail06.adl2.internode.on.net[150.101.137.129] X-Barracuda-Start-Time: 1362439134 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124267 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Mon, Mar 04, 2013 at 11:55:40PM +0100, Hans-Peter Jansen wrote: > Am Montag, 4. Mrz 2013, 17:40:13 schrieb Hans-Peter Jansen: > > Hi, > > > > after upgrading the kernel on a server from 2.6.34 to 3.8.1 (x86-32), I > > suffer from a strange behavior of a larger directory, that a downgrade > > of the kernel cannot repair. > > > > The best way to reproduce the problem is cd into that directory and > > running "vi .". It should display a full directory listing, but it only > > displays a about dozen entries. Another way is just using bash tab > > completion (e.g. ls should display a screenful of items, but > > only shows the very same dozen of entries. Userspace is quite old > > (openSUSE 11.1/i586, but I cannot upgrade to a newer userspace for a > > couple of reasons. OTOH, a simple ls displays the full list again, > > [...] > > > > # then it preceeds with getdents64 and fetches already fetched entries > > > > 27177 getdents64(3, { > > {d_ino=4303329151, d_off=78, d_type=DT_UNKNOWN, d_reclen=32, d_name="Black_Swan"} > > Okay, this is the culprit: 0x1007F977F overflows 32 bit, although I > *never* mounted anything with inode64 option. > > For some reason, the intermediate kernel 3.8.0 has used the inode64 version > by *default*. This breaks bash tab completion and vdr. After forcing the > inode32 option and copying some offenders away and back in place, the issue > vanishes. > > Unlike stated in the XFS FAQs, openSUSE 11.1 *has* issues with inode64, and > even more so, if enabled by default. Wonderful. Report a bug to OpenSuSE and get userspace fixed. It's only a matter of time before btrfs and ext4 users start reporting the same problem, as they also use 64 bit inode numbers.... Cheers, Dave. -- Dave Chinner david@fromorbit.com From rjohnston@sgi.com Mon Mar 4 17:20:00 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id CD98A8064 for ; Mon, 4 Mar 2013 17:20:00 -0600 (CST) Received: from xmail.sgi.com (pv-excas3-dc21-nlb.corp.sgi.com [137.38.102.207]) by relay2.corp.sgi.com (Postfix) with ESMTP id 58CB7304048; Mon, 4 Mar 2013 15:19:57 -0800 (PST) Received: from [134.15.1.80] (134.15.1.80) by xmail.sgi.com (137.38.102.30) with Microsoft SMTP Server (TLS) id 14.2.318.1; Mon, 4 Mar 2013 17:19:57 -0600 Message-ID: <51352C1C.40409@sgi.com> Date: Mon, 4 Mar 2013 17:19:56 -0600 From: Rich Johnston User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:14.0) Gecko/20120714 Thunderbird/14.0 MIME-Version: 1.0 To: Dmitry Monakhov CC: , , , Subject: Re: [PATCH 09/10] xfstest: add defragmentation stress tests for ext4 References: <1361356935-29153-1-git-send-email-dmonakhov@openvz.org> <1361356935-29153-10-git-send-email-dmonakhov@openvz.org> <51310046.5090306@sgi.com> <878v66h9ks.fsf@openvz.org> In-Reply-To: <878v66h9ks.fsf@openvz.org> Content-Type: text/plain; charset="ISO-8859-1"; format=flowed Content-Transfer-Encoding: 7bit X-Originating-IP: [134.15.1.80] On 03/01/2013 07:30 PM, Dmitry Monakhov wrote: > On Fri, 1 Mar 2013 13:23:50 -0600, Rich Johnston wrote: >> On 02/20/2013 04:42 AM, Dmitry Monakhov wrote: >> >> Let me know if you agree with these changes and I will make them at >> commit time. > Yes, please do. >> >> Thanks >> --Rich commit a3d92a6cbdf9e98d8e256974b50b025d1d4575ec Author: Dmitry Monakhov Date: Wed Feb 20 10:42:14 2013 +0000 xfstest: add defragmentation stress tests for ext4 Perform various regression tests for ext4defrag subsystem 301'th Test1: Defragment file while other task does direct AIO 302'th Test2: Perform defragmentation on file under buffered AIO while third task does direct AIO to donor file 303'th Test3: Two defrag tasks use common donor file. 304'th Test4: Stress defragmentation. Several threads perform fragmentation at random position use inplace=1 will allocate and free blocks inside defrag event improve load pressure. This tests are considered dangerous because 302'th and 303'th are known to trigger OOPS on recent kernels see:https://gist.github.com/dmonakhov/4770 294 From david@fromorbit.com Mon Mar 4 17:23:24 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 41A1A7F52 for ; Mon, 4 Mar 2013 17:23:24 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay2.corp.sgi.com (Postfix) with ESMTP id 12B9D304048 for ; Mon, 4 Mar 2013 15:23:23 -0800 (PST) X-ASG-Debug-ID: 1362439400-04cb6c2b02178b70001-NocioJ Received: from ipmail06.adl2.internode.on.net (ipmail06.adl2.internode.on.net [150.101.137.129]) by cuda.sgi.com with ESMTP id ebYTFHxAyMA3nzAG for ; Mon, 04 Mar 2013 15:23:21 -0800 (PST) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.129 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: Ah8hAN4qNVF5Layr/2dsb2JhbABEFr0lhRUBAgGBChdzgh8BAQQBOhwjEAgDGAklDwUlAyETiA0FDbB0j14VjXYYH0oHg0ADlkWJZYcIgxw Received: from ppp121-45-172-171.lns20.syd6.internode.on.net (HELO dastard) ([121.45.172.171]) by ipmail06.adl2.internode.on.net with ESMTP; 05 Mar 2013 09:53:20 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UCej1-0006rj-PO; Tue, 05 Mar 2013 10:23:19 +1100 Date: Tue, 5 Mar 2013 10:23:19 +1100 From: Dave Chinner To: Ole Tange Cc: xfs@oss.sgi.com Subject: Re: xfs_repair segfaults Message-ID: <20130304232319.GR23616@dastard> X-ASG-Orig-Subj: Re: xfs_repair segfaults References: <20130301111701.GB23616@dastard> <20130301205305.GD23616@dastard> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail06.adl2.internode.on.net[150.101.137.129] X-Barracuda-Start-Time: 1362439400 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124269 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Mon, Mar 04, 2013 at 10:03:29AM +0100, Ole Tange wrote: > On Fri, Mar 1, 2013 at 9:53 PM, Dave Chinner wrote: > : > > What filesystem errors occurred > > when the srives went offline? > > See http://dna.ku.dk/~tange/tmp/syslog.3 You log is full of this: mpt2sas1: log_info(0x31120303): originator(PL), code(0x12), sub_code(0x0303) What's that mean? > > Feb 26 00:46:52 franklin kernel: [556238.429259] XFS (md5p1): metadata > I/O error: block 0x459b8 ("xfs_buf_iodone_callbacks") error 5 buf > count 4096 So, the first IO errors appear at 23:00 on /dev/sdb, and the controller does a full reset and reprobe. Look slike a port failure of some kind. Notable: mpt2sas1: LSISAS2008: FWVersion(07.00.00.00), ChipRevision(0x03), BiosVersion(07.11.10.00) >From a quick google, that firmware looks out of date (current LSISAS2008 firmwares are numbered 10 or 11, and bios versions are at 7.21). So, /dev/md1 reported a failure (/dev/sdb) around 23:01:16, started a rebuild. Looks like it swapped in /dev/sdd and started a rebuild. /dev/md4 had a failure (/dev/sds) around 00:19, no rebuild started. Down to 8 disks in /dev/md4, no rebuild in progress, no redundancy available. /dev/md1 had another failure (/dev/sdj) around 00:46, this time on a SYNCHRONISE CACHE command (i.e. log write). This IO failure caused the shutdown to occur. And this is the result: [556219.292225] end_request: I/O error, dev sdj, sector 10 [556219.292275] md: super_written gets error=-5, uptodate=0 [556219.292283] md/raid:md1: Disk failure on sdj, disabling device. [556219.292286] md/raid:md1: Operation continuing on 7 devices. At this point, /dev/md1 is reporting 7 working disks and has had an EIO on it's superblock write, which means it's probably in an inconsistent state. Further, it's only got 8 disks associated with it and as a rebuild is in progress it means that data loss has occurred with this failure. There's your problem. Essentially, you need to fix your hardware before you do anything else. Get it all back fully online and fix whatever the problems are that are causing IO errors, then you can worry about recovering the filesystem and your data. Until the hardware is stable and not throwing errors, recovery is going to be unreliable (if not impossible). Cheers, Dave. -- Dave Chinner david@fromorbit.com From rjohnston@sgi.com Mon Mar 4 17:44:19 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 2CD19805E for ; Mon, 4 Mar 2013 17:44:19 -0600 (CST) Received: from xmail.sgi.com (pv-excas3-dc21.corp.sgi.com [137.38.102.206]) by relay3.corp.sgi.com (Postfix) with ESMTP id D7BD4AC005; Mon, 4 Mar 2013 15:44:17 -0800 (PST) Received: from [134.15.1.80] (134.15.1.80) by xmail.sgi.com (137.38.102.30) with Microsoft SMTP Server (TLS) id 14.2.318.1; Mon, 4 Mar 2013 17:44:17 -0600 Message-ID: <513531D0.9080409@sgi.com> Date: Mon, 4 Mar 2013 17:44:16 -0600 From: Rich Johnston User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:14.0) Gecko/20120714 Thunderbird/14.0 MIME-Version: 1.0 To: Dmitry Monakhov CC: , , , Subject: Re: [PATCH 10/10] xfstests: add disk failure simulation test References: <1361356935-29153-1-git-send-email-dmonakhov@openvz.org> <1361356935-29153-11-git-send-email-dmonakhov@openvz.org> <51310B63.4070105@sgi.com> <87621ah8q4.fsf@openvz.org> In-Reply-To: <87621ah8q4.fsf@openvz.org> Content-Type: text/plain; charset="ISO-8859-1"; format=flowed Content-Transfer-Encoding: 7bit X-Originating-IP: [134.15.1.80] On 03/01/2013 07:49 PM, Dmitry Monakhov wrote: > On Fri, 1 Mar 2013 14:11:15 -0600, Rich Johnston wrote: >> On 02/20/2013 04:42 AM, Dmitry Monakhov wrote: >>> There are many situations where disk may fail for example >>> 1) brutal usb dongle unplug >>> 2) iscsi (or any other netbdev) failure due to network issues >>> In this situation filesystem which use this blockdevice is >>> expected to fail(force RO remount, abort, etc) but whole system >>> should still be operational. In other words: >>> 1) Kernel should not panic >>> 2) Memory should not leak >>> 3) Data integrity operations (sync,fsync,fdatasync, directio) should fail >>> for affected filesystem >>> 4) It should be possible to umount broken filesystem >>> >>> Later when disk becomes available again we expect(only for journaled filesystems): >>> 5) It will be possible to mount filesystem w/o explicit fsck (in order to caught >> >> typo s/caught/catch/g >> >>> issues like https://patchwork.kernel.org/patch/1983981/) >>> 6) Filesystem should be operational >>> 7) After mount/umount has being done all errors should be fixed so fsck should >>> not spot any issues. >>> >>> This test use fault enjection (CONFIG_FAIL_MAKE_REQUEST=y config option ) >> May want to mention all the kernel config options required. >> i.e. CONFIG_FAULT_INJECTION=y ... are there others? >> CONFIG_FAULT_INJECTION_DEBUG_FS=y ??? > Yes, all three options are required. >> >>> which force all new IO requests to fail for a given device. Xfs already has >> to force >> >>> XFS_IOC_GOINGDOWN ioctl which provides similar behaviour, but it is fs speciffic >> >> typos s/behaviour/behavior/g s/speciffic/specific >> > and it does it in an easy way >> because it perform freeze_bdev() before actual >>> shotdown. >> typo s/shotdown/shutdown/g > Agree with your diagnosis. My gramma is bad and I've forget to call spell check > before submission. Should I resend this one or you fix it manually > on commit time? No worries, I'm sure your English is much better than any of my attempts to write in your native tongue. ;) No need to resend, glad to take care of these minor changes at commit time. commit 02e57e1e3a42856dca9061ff943ba72fa7be8469 Author: Dmitry Monakhov Date: Wed Feb 20 10:42:15 2013 +0000 xfstests: add disk failure simulation test There are many situations where disk may fail for example 1) brutal usb dongle unplug 2) iscsi (or any other netbdev) failure due to network issues In this situation filesystem which use this blockdevice is expected to fail(force RO remount, abort, etc) but whole system should still be operational. In other words: 1) Kernel should not panic 2) Memory should not leak 3) Data integrity operations (sync,fsync,fdatasync, directio) should fail for affected filesystem 4) It should be possible to umount broken filesystem Later when disk becomes available again we expect(only for journaled filesystems): 5) It will be possible to mount filesystem w/o explicit fsck (in order to catch issues like https://patchwork.kernel.org/patch/1983981/) 6) Filesystem should be operational 7) After mount/umount has being done all errors should be fixed so fsck should not spot any issues. This test use fault injection (CONFIG_FAULT_INJECTION=y, CONFIG_FAIL_MAKE_REQUEST=y and CONFIG_FAULT_INJECTION_DEBUG_FS=y config options) to force all new IO requests to fail for a given device. Xfs already has XFS_IOC_GOINGDOWN ioctl which provides similar behavior, but it is fs specific and it does it in an easy way because it performs freeze_bdev() before actual shutdown. Test run fsstress in background and then force disk failure. Once disk failed it check that (1)-(4) is true. Then makes disk available again and check that (5)-(7) is also true BE CAREFUL!! test known to cause memory corruption for XFS see: https://gist.github.com/dmonakhov/4953045 From huucuong989@gmail.com Mon Mar 4 20:03:53 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: * X-Spam-Status: No, score=1.3 required=5.0 tests=FREEMAIL_ENVFROM_END_DIGIT, FREEMAIL_FROM,FREEMAIL_REPLYTO,HTML_MESSAGE,T_DKIM_INVALID autolearn=no version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id D3D458032 for ; Mon, 4 Mar 2013 20:03:53 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay1.corp.sgi.com (Postfix) with ESMTP id ADB1F8F8037 for ; Mon, 4 Mar 2013 18:03:50 -0800 (PST) X-ASG-Debug-ID: 1362449028-04cb6c2b011818c0001-NocioJ Received: from mail-pb0-f53.google.com (mail-pb0-f53.google.com [209.85.160.53]) by cuda.sgi.com with ESMTP id ANpNdDI5BnDiFxqE (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Mon, 04 Mar 2013 18:03:49 -0800 (PST) X-Barracuda-Envelope-From: huucuong989@gmail.com X-Barracuda-Apparent-Source-IP: 209.85.160.53 X-Barracuda-IPDD: Level1 [gmail.com/209.85.160.53] Received: by mail-pb0-f53.google.com with SMTP id un1so3697835pbc.26 for ; Mon, 04 Mar 2013 18:03:48 -0800 (PST) X-Barracuda-IPDD: Level1 [gmail.com/209.85.160.53] X-Barracuda-IPDD: Level1 [gmail.com/209.85.160.53] DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20120113; h=x-received:from:subject:to:content-type:mime-version:reply-to:date :message-id; bh=4qBphRoyX/16oyf/uHcu9Ms9gsT5tjb+90+g0xSDZRE=; b=gQuGP67wrcxIP+0PAvqWFonK0E6EGgRU5z6xMEwFx2tgyvsh7S8MikAfIo0R/EuSs0 dU2/+UhMMOI+CmR3OJBjMJr/llEbLPRUQYQnYMjVnF8cUFtUUeF6M4pem8O6Hl2Ko440 th8gW+jBvyuW1qJzMI5dbHKxZFX2qDZhLJox+jUr8Fotmq15zky5L/S+S0cfaFqYmCXt 71Ut0wx8qVgZ584UFkZEK4CH3dlBuwzfCoZVxBlz9g5X4az1HIsVAUJ5UAnhyeoZsH94 2Qri2rB4tAFbKxwWFiGTI5Y+BFw/irSmaKri3/IjSPeJ7zqDhIIWFJ9M342CXhWcqyUM DRuQ== X-Received: by 10.68.218.100 with SMTP id pf4mr32656820pbc.156.1362449028664; Mon, 04 Mar 2013 18:03:48 -0800 (PST) Received: from USER-VAIO ([113.22.26.192]) by mx.google.com with ESMTPS id qp13sm24409130pbb.3.2013.03.04.18.03.46 (version=TLSv1 cipher=RC4-SHA bits=128/128); Mon, 04 Mar 2013 18:03:47 -0800 (PST) From: "ACC Viet Nam" Subject: ACC - =?UTF-8?B?Q2h1ecOqbiB0aGnhur90IGvhur8sIHPhuqNuIHh14bqldCB2w6AgbOG6r3Ag?= =?UTF-8?B?xJHhurd0IGjhu4cgdGjhu5FuZyBi4bq/cCBjw7RuZyBuZ2hp4buHcCwgYuG6?= =?UTF-8?B?v3AgxINuIHThuq1wIHRo4buD?= cho =?UTF-8?B?bmjDoCBow6BuZywga2jDoWNoIHPhuqFuLCB0csaw4budbmcgaOG7jWMsIGLh?= =?UTF-8?B?u4duaCB2aeG7h24sIG5ow6AgbcOheSwgY8OhYyBsb+G6oWkgbcOheSB0aOG7?= =?UTF-8?B?sWMgcGjhuqlt4oCm?= To: xfs@oss.sgi.com X-ASG-Orig-Subj: ACC - =?UTF-8?B?Q2h1ecOqbiB0aGnhur90IGvhur8sIHPhuqNuIHh14bqldCB2w6AgbOG6r3Ag?= =?UTF-8?B?xJHhurd0IGjhu4cgdGjhu5FuZyBi4bq/cCBjw7RuZyBuZ2hp4buHcCwgYuG6?= =?UTF-8?B?v3AgxINuIHThuq1wIHRo4buD?= cho =?UTF-8?B?bmjDoCBow6BuZywga2jDoWNoIHPhuqFuLCB0csaw4budbmcgaOG7jWMsIGLh?= =?UTF-8?B?u4duaCB2aeG7h24sIG5ow6AgbcOheSwgY8OhYyBsb+G6oWkgbcOheSB0aOG7?= =?UTF-8?B?sWMgcGjhuqlt4oCm?= Content-Type: multipart/alternative; charset="UTF-8"; boundary="iuSvi=_hqI4IHeEt1qhQyx2MIdT5itmX630" MIME-Version: 1.0 Reply-To: huucuong989@gmail.com Date: Tue, 5 Mar 2013 09:03:48 +0700 Message-ID: <57681580726409@user-VAIO> X-Barracuda-Connect: mail-pb0-f53.google.com[209.85.160.53] X-Barracuda-Start-Time: 1362449029 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 2.00 X-Barracuda-Spam-Status: No, SCORE=2.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC3_MV0164, DKIM_SIGNED, DKIM_VERIFIED, HTML_MESSAGE X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124279 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature 0.00 HTML_MESSAGE BODY: HTML included in message 2.00 BSF_SC3_MV0164 Custom rule MV0164 This is a multi-part message in MIME format --iuSvi=_hqI4IHeEt1qhQyx2MIdT5itmX630 Content-Type: text/plain ; charset="UTF-8" Content-Transfer-Encoding: quoted-printable C=C3=A1c thi=E1=BA=BFt b=E1=BB=8B cung c=E1=BA=A5p: M=C3=A1y pha c=C3=A0 ph=C3=AA, m=C3=A1y xay c=C3=A0 ph=C3=AA, m=C3=A1y= tr=E1=BB=99n (=C4=91=C3=A1nh, chia) b=E1=BB=99t, m=C3=A1y c=C3=A1n b=E1= =BB=99t, m=C3=A1y b=C3=A0o =C4=91=C3=A1, m=C3=A1y xay th=E1=BB=8Bt, m=C3= =A1y c=C6=B0a x=C6=B0=C6=A1ng, m=C3=A1y c=E1=BA=AFt (th=C3=A1i) l=C3=A1= t th=E1=BB=8Bt, m=C3=A1y l=C3=A0m kem, m=C3=A1y nh=E1=BB=93i (n=C6=B0=E1= =BB=9Bng, =C4=91=C3=B9n) x=C3=BAc x=C3=ADch, m=C3=A1y r=E1=BB=ADa b=C3= =A1t, m=C3=A1y g=E1=BB=8Dt (th=C3=A1i, c=E1=BA=AFt, r=E1=BB=ADa) rau c= =E1=BB=A7 qu=E1=BA=A3, m=C3=A1y vo g=E1=BA=A1o, m=C3=A1y s=E1=BA=A5y k= h=C4=83n, m=C3=A1y v=E1=BA=B7t l=C3=B4ng g=C3=A0 (v=E1=BB=8Bt), m=C3=A1= y ch=E1=BA=BF bi=E1=BA=BFn, m=C3=A1y l=C3=A0m (s=E1=BA=A3n xu=E1=BA=A5= t) =C4=91=C3=A1, m=C3=A1y l=C3=A0m =C4=91=C3=A1 si=C3=AAu t=E1=BB=91c,= m=C3=A1y =C3=A9p n=C6=B0=E1=BB=9Bc m=C3=ADa, m=C3=A1y t=C3=A1ch (b=C3= =B3c) h=E1=BA=A1t ng=C3=B4, m=C3=A1y b=C3=B3c (t=C3=A1ch) h=C3=A0nh t=E1= =BB=8Fi, m=C3=A1y l=C3=A0m b=C3=A1nh m=E1=BB=B3 Donnekebab, m=C3=A1y t= r=E1=BB=99n salad, m=C3=A1y chi=E1=BA=BFt r=C3=B3t bia, m=C3=A1y (b=C3= =ACnh) l=C3=A0m l=E1=BA=A1nh n=C6=B0=E1=BB=9Bc tr=C3=A1i c=C3=A2y, m=C3= =A1y xay =C4=91=E1=BA=ADu t=C6=B0=C6=A1ng, b=E1=BA=BFp c=C3=B4ng nghi=E1= =BB=87p, b=E1=BA=BFp =C3=A1 =C4=91=C3=B4i, b=E1=BA=BFp =C3=A1 =C4=91=C6= =A1n, b=E1=BA=BFp h=E1=BA=A5p, b=E1=BA=BFp 6 =C3=B4, b=E1=BA=BFp h=E1=BA= =A7m, b=E1=BA=BFp x=C3=A0o, b=E1=BA=BFp =C3=A2u, b=E1=BA=BFp chi=C3=AA= n, b=E1=BA=BFp n=C6=B0=E1=BB=9Bng, b=E1=BA=BFp r=C3=A1n, b=E1=BA=BFp n= h=C3=BAng, b=E1=BA=BFp n=C6=B0=E1=BB=9Bng m=E1=BA=B7t, b=E1=BA=BFp t=E1= =BB=95ng h=E1=BB=A3p, b=E1=BA=BFp nh=E1=BA=ADt, b=E1=BA=BFp l=E1=BA=A9= u, b=E1=BA=BFp n=C6=B0=E1=BB=9Bng barbecue, b=E1=BA=BFp n=E1=BA=A5u c=C6= =A1m ni=C3=AAu =C4=91=E1=BA=A5t, b=E1=BA=BFp n=C6=B0=E1=BB=9Bng than =C4= =91=C3=A1 ho=E1=BA=A1t t=C3=ADnh, b=E1=BA=BFp nh=C3=BAng, l=C3=B2 n=C6= =B0=E1=BB=9Bng b=C3=A1nh m=E1=BB=B3, l=C3=B2 n=C6=B0=E1=BB=9Bng pizza,= l=C3=B2 n=C6=B0=E1=BB=9Bng, l=C3=B2 n=C6=B0=E1=BB=9Bng gia c=E1=BA=A7= m, l=C3=B2 quay, b=C3=A0n (t=E1=BB=A7) h=C3=A2m n=C3=B3ng th=E1=BB=B1c= ph=E1=BA=A9m, t=E1=BB=A7 l=E1=BA=A1nh c=C3=B4ng nghi=E1=BB=87p, t=E1=BB= =A7 b=E1=BA=A3o =C3=B4n, t=E1=BB=A7 tr=C6=B0ng b=E1=BA=A7y salad, t=E1= =BB=A7 s=E1=BA=A5y b=C3=A1t di=E1=BB=87t khu=E1=BA=A9n, t=E1=BB=A7 h=E1= =BA=A5p kh=C4=83n, t=E1=BB=A7 b=E1=BA=A3o qu=E1=BA=A3n ki=E1=BB=83u b=C3= =A0n, t=E1=BB=A7 tr=C6=B0ng b=C3=A0y, t=E1=BB=A7 m=C3=A1t, t=E1=BB=A7 = gi=E1=BB=AF =E1=BA=A5m, t=E1=BB=A7 b=C3=A1nh, t=E1=BB=A7 l=C3=A0m l=E1= =BA=A1nh r=C6=B0=E1=BB=A3u, t=E1=BB=A7 si=C3=AAu th=E1=BB=8B, t=E1=BB=A7= sushi, t=E1=BB=A7 =C4=91=C3=B4ng, t=E1=BB=A7 n=E1=BA=A5u (h=E1=BA=A5p= ) c=C6=A1m, t=E1=BB=A7 h=E1=BA=A5p, t=E1=BB=A7 pizza (sandwich, salad,= sushi), t=E1=BB=A7 inox, t=E1=BB=A7 b=E1=BA=A3o qu=E1=BA=A3n kem c=C3= =A2n, thi=E1=BA=BFt b=E1=BB=8B l=C3=A0m b=C3=A1nh (m=C3=A1y tr=E1=BB=99= n, c=C3=A1n, cu=E1=BB=99n, c=E1=BA=AFt), thi=E1=BA=BFt b=E1=BB=8B ch=E1= =BA=BF bi=E1=BA=BFn, thi=E1=BA=BFt b=E1=BB=8B l=C3=A0m l=E1=BA=A1nh, c= =C3=A1c lo=E1=BA=A1i xe =C4=91=E1=BA=A9y, th=C3=B9ng r=C3=A1c, c=C3=A1= c lo=E1=BA=A1i b=E1=BA=A3ng (bi=E1=BB=83n) th=C3=B4ng tin ch=E1=BB=89 = d=E1=BA=ABn, b=C3=A0n inox, b=C3=A0n gh=E1=BA=BF =C4=83n c=C3=B4ng nh=C3= =A2n, b=C3=A0n ra =C4=91=E1=BB=93, b=C3=A0n ch=E1=BA=BF bi=E1=BA=BFn, = =C4=91=E1=BB=93 d=C3=B9ng buffet, =C3=A2u buffet, =C4=91=E1=BB=93 inox= , khay c=C6=A1m inox, gi=C3=A1 k=E1=BB=87 inox =C4=91=E1=BB=83 =C4=91=E1= =BB=93 th=E1=BB=B1c ph=E1=BA=A9m, ch=E1=BA=ADu (b=E1=BB=93n) r=E1=BB=AD= a, tum (ch=E1=BB=A5p) h=C3=BAt kh=C3=B3i, =E1=BB=91ng d=E1=BA=ABn kh=C3= =B3i, m=C3=B4 t=C6=A1 h=C3=BAt kh=C3=B3i=E2=80=A6=20 M=E1=BB=8Di chi ti=E1=BA=BFt xin li=C3=AAn h=E1=BB=87: C=C3=94NG TY TNHH THI=E1=BA=BET B=E1=BB=8A B=E1=BA=BEP C=C3=94NG NGHI=E1= =BB=86P ACC S=E1=BB=91 68B Tr=E1=BA=A7n Quang Di=E1=BB=87u - Ho=C3=A0ng C=E1=BA=A7= u - =C3=94 Ch=E1=BB=A3 D=E1=BB=ABa - =C4=90=E1=BB=91ng =C4=90a - H=C3=A0= N=E1=BB=99i =C4=90T: 04.35380712 - 04.35380713 - fax: 04.35380712 - 0972498338 Website: www.bepcongnghiepinox.vn Email: anhcuong.co@gmail.com Yahoo: bepacc@yahoo.com =20 =20 =20 --iuSvi=_hqI4IHeEt1qhQyx2MIdT5itmX630 Content-Type: text/html ; charset="UTF-8" Content-Transfer-Encoding: quoted-printable

C= ác thiết bị cung cấp:

Máy pha cà phê, m&aacu= te;y xay cà phê, máy trộn (đánh,= chia) bột, máy cán bột, máy bà= ;o đá, máy xay thịt, máy cưa x= 32;ơng, máy cắt (thái) lát thịt,= máy làm kem, máy nhồi (nướng, &= #273;ùn) xúc xích, máy rửa bá= t, máy gọt (thái, cắt, rửa) rau c̗= 1; quả, máy vo gạo, máy sấy khăn,= máy vặt lông gà (vịt), máy ch&= #7871; biến, máy làm (sản xuất) đ= á, máy làm đá siêu tốc, m= áy ép nước mía, máy tách= (bóc) hạt ngô, máy bóc (tách)= hành tỏi, máy làm bánh mỳ Don= nekebab, máy trộn salad, máy chiết ró= t bia, máy (bình) làm lạnh nước = trái cây, máy xay đậu tương, = bếp công nghiệp, bếp á đôi, b= ếp á đơn, bếp hấp, bếp 6 &oci= rc;, bếp hầm, bếp xào, bếp âu, b&= #7871;p chiên, bếp nướng, bếp rán,= bếp nhúng, bếp nướng mặt, bế= ;p tổng hợp, bếp nhật, bếp lẩu, b&= #7871;p nướng barbecue, bếp nấu cơm ni&eci= rc;u đất, bếp nướng than đá ho= ạt tính, bếp nhúng, lò nướng bánh mỳ, lò = nướng pizza, lò nướng, lò nư&= #7899;ng gia cầm, lò quay, bàn (tủ) hâm nóng thực phẩm= , các loại xe đẩy, = thùng rác, các loại bảng (biển) th&oc= irc;ng tin chỉ dẫn, = bàn inox, bàn ghế ăn công nhân, b= àn ra đồ, bàn chế biến, &#= 273;ồ dùng buffet, âu buffet, đồ inox, k= hay cơm inox, giá kệ inox để đồ= ; thực phẩm, chậu (bồn) rửa, tum (chO= 09;p) hút khói, ống dẫn khói, mô= ; tơ hút khói… 

M= ọi chi tiết xin liên hệ:

CÔNG TY TNHH THIẾT BỊ BẾP CÔNG NGHI&#= 7878;P ACC

Số 68B = Trần Quang Diệu - Hoàng Cầu - Ô Ch̖= 7; Dừa - Đống Đa - Hà Nội

ĐT: 04.3= 5380712 - 04.35380713 - fax: 04.35380712 - 0972498338

Website: www.bepcongnghiepinox.vn

Email: a= nhcuong.co@gmail.com

Yahoo: bepacc= @yahoo.com

 

=  

 

--iuSvi=_hqI4IHeEt1qhQyx2MIdT5itmX630-- From esinvest@sv14.webhost.pl Mon Mar 4 23:48:28 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: * X-Spam-Status: No, score=1.0 required=5.0 tests=FORGED_HOTMAIL_RCVD2, FREEMAIL_FROM,FREEMAIL_REPLYTO,T_FILL_THIS_FORM_SHORT autolearn=no version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 822017F88 for ; Mon, 4 Mar 2013 23:48:28 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay1.corp.sgi.com (Postfix) with ESMTP id 6BBB58F8040 for ; Mon, 4 Mar 2013 21:48:25 -0800 (PST) X-ASG-Debug-ID: 1362462503-04cb6c2b0418d750001-NocioJ Received: from sv14.webhost.pl (sv14.webhost.pl [176.119.33.81]) by cuda.sgi.com with ESMTP id FOfTTfjJSAivXDnB (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO) for ; Mon, 04 Mar 2013 21:48:24 -0800 (PST) X-Barracuda-Envelope-From: esinvest@sv14.webhost.pl X-Barracuda-Apparent-Source-IP: 176.119.33.81 Received: from esinvest by sv14.webhost.pl with local (Exim 4.80) (envelope-from ) id 1UCkjV-00067o-IO for xfs@oss.sgi.com; Tue, 05 Mar 2013 06:48:13 +0100 To: xfs@oss.sgi.com Subject: Purchase Order X-PHP-Script: www.esinvest.pl/administrator/components/msh0p4you.php for 41.138.190.69 X-ASG-Orig-Subj: Purchase Order From: Em, &, Supply, Group, Pty. Reply-To: sales5em@gmail.com MIME-Version: 1.0 Content-Type: text/plain Content-Transfer-Encoding: 8bit Message-Id: Date: Tue, 05 Mar 2013 06:48:13 +0100 X-cPanel-MailScanner-Information: Please contact the ISP for more information X-cPanel-MailScanner-ID: 1UCkjV-00067o-IO X-cPanel-MailScanner: Not scanned: please contact your Internet E-Mail Service Provider for details X-cPanel-MailScanner-SpamCheck: X-cPanel-MailScanner-From: esinvest@sv14.webhost.pl X-AntiAbuse: This header was added to track abuse, please include it with any abuse report X-AntiAbuse: Primary Hostname - sv14.webhost.pl X-AntiAbuse: Original Domain - oss.sgi.com X-AntiAbuse: Originator/Caller UID/GID - [957 32007] / [47 12] X-AntiAbuse: Sender Address Domain - sv14.webhost.pl X-Get-Message-Sender-Via: sv14.webhost.pl: authenticated_id: esinvest/only user confirmed/virtual account not confirmed X-Source: X-Source-Args: X-Source-Dir: X-Barracuda-Connect: sv14.webhost.pl[176.119.33.81] X-Barracuda-Start-Time: 1362462503 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 1.12 X-Barracuda-Spam-Status: No, SCORE=1.12 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=FORGED_HOTMAIL_RCVD2 X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124295 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 1.12 FORGED_HOTMAIL_RCVD2 hotmail.com 'From' address, but no 'Received:' Good day . Thank you for your swift response to my mail in regards to one of your product i saw on a trade website which my company will like to purchase from you. However i saw a similar and latest product design on a trade production design website which i have chosen to be the product design i want,i will need this particular design in large quantities if the price and the quality meets up to our requirements, as we go for the best quality and the best price. To view the picture of the particular product i need you need to click the link below, Log in your email username and password for you to view the picture of the exact product and design that my company has decided to purchase, do get back to me and let me know if you have the design as we are ready to make immediate order in large quantities. Click the Link: http://www.sep.org.pt/modules/mod/sample/Samples.htm Mitchel From gabriel@vlasiu.net Tue Mar 5 07:05:05 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=T_DKIM_INVALID autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 850028022 for ; Tue, 5 Mar 2013 07:05:05 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id 76667304064 for ; Tue, 5 Mar 2013 05:05:02 -0800 (PST) X-ASG-Debug-ID: 1362488698-04cbb07dbe1ac690001-NocioJ Received: from mail.vlasiu.net (mail.vlasiu.net [91.223.50.125]) by cuda.sgi.com with ESMTP id pYg4rFEEb0tFASBw (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO) for ; Tue, 05 Mar 2013 05:04:59 -0800 (PST) X-Barracuda-Envelope-From: gabriel@vlasiu.net X-Barracuda-Apparent-Source-IP: 91.223.50.125 Received: from localhost (localhost [127.0.0.1]) by mail.vlasiu.net (Postfix) with ESMTP id 35BE37E07F for ; Tue, 5 Mar 2013 15:04:57 +0200 (EET) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=vlasiu.net; h= content-type:content-type:mime-version:user-agent:message-id :subject:subject:from:from:date:date:received:received:received; s=default; t=1362488689; x=1362492290; bh=FHdvWwA6g0GbaE+AATR70 xMV+nB9QjNe5FhjYrMbai0=; b=IqA6mgp4QI5SBISqMoS+r4TtTF+UCIslYgpKG nJpZHPxq1tBYK487vrFChslBOVN8mv60eKHsOc+wGgEZnEFjf/boE6d1zPVGvmXj AOKwLblD1wGYTAFcBSOwSTwRXR5j8OM73+fDWuUbBXqfZCusdzr4gWhyufeXsh/G EWhAJM= X-Virus-Scanned: amavisd-new at vlasiu.net Received: from mail.vlasiu.net ([127.0.0.1]) by localhost (mail.vlasiu.net [127.0.0.1]) (amavisd-new, port 10026) with LMTP id twuwcp_6AoYW for ; Tue, 5 Mar 2013 15:04:49 +0200 (EET) Received: by mail.vlasiu.net (Postfix, from userid 500) id B281A7E083; Tue, 5 Mar 2013 15:04:49 +0200 (EET) Received: from localhost (localhost [127.0.0.1]) by mail.vlasiu.net (Postfix) with ESMTP id 8449D7E07F for ; Tue, 5 Mar 2013 15:04:49 +0200 (EET) Date: Tue, 5 Mar 2013 15:04:44 +0200 (EET) From: Gabriel VLASIU To: xfs@oss.sgi.com Subject: xfs with kernel 3.8.1 Message-ID: X-ASG-Orig-Subj: xfs with kernel 3.8.1 User-Agent: Alpine 2.02 (LRH 1266 2009-07-14) X-OpenGPG-KeyID: 44952F15 X-OpenGPG-Fingerprint: 4AC5 7C26 2FE9 02DA 4906 24B2 D32B 7ED7 4495 2F15 X-OpenGPG-URL: http://www.vlasiu.net/public.key MIME-Version: 1.0 Content-Type: TEXT/PLAIN; charset=US-ASCII X-Barracuda-Connect: mail.vlasiu.net[91.223.50.125] X-Barracuda-Start-Time: 1362488699 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=DKIM_SIGNED, DKIM_VERIFIED X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124321 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature -----BEGIN PGP SIGNED MESSAGE----- Hash: SHA512 Hi! I think there is something wrong with xfs in kernel 3.8.1 (x86_64). While compiling kernel 3.8.2 (noarch section: rpmbuild -bb kernel.spec - --target=noarch) I had this error: Mar 5 12:50:21 xxxxxxx kernel: [93088.912705] ffff88010e1bf000: 2f 68 6f 6d 65 2f 67 61 62 72 69 65 6c 2f 77 6f /home/gabriel/wo Mar 5 12:50:21 xxxxxxx kernel: [93088.912713] XFS (loop0): Internal error xfs_bmbt_verify at line 747 of file fs/xfs/xfs_bmap_btree.c. Caller 0xffffffffa005b7fe Mar 5 12:50:21 xxxxxxx kernel: [93088.912713] Mar 5 12:50:21 xxxxxxx kernel: [93088.912716] Pid: 497, comm: xfsaild/loop0 Tainted: GF C O 3.8.1-201.AES.f18g.x86_64 #1 Mar 5 12:50:21 xxxxxxx kernel: [93088.912718] Call Trace: Mar 5 12:50:21 xxxxxxx kernel: [93088.912768] [] xfs_error_report+0x3f/0x50 [xfs] Mar 5 12:50:21 xxxxxxx kernel: [93088.912786] [] ? xfs_bmbt_write_verify+0xe/0x10 [xfs] Mar 5 12:50:21 xxxxxxx kernel: [93088.912799] [] xfs_corruption_error+0x5e/0x90 [xfs] Mar 5 12:50:21 xxxxxxx kernel: [93088.912815] [] ? xfs_bmbt_write_verify+0xe/0x10 [xfs] Mar 5 12:50:21 xxxxxxx kernel: [93088.912831] [] xfs_bmbt_verify+0x76/0x1c0 [xfs] Mar 5 12:50:21 xxxxxxx kernel: [93088.912847] [] ? xfs_bmbt_write_verify+0xe/0x10 [xfs] Mar 5 12:50:21 xxxxxxx kernel: [93088.912860] [] ? xfs_bdstrat_cb+0x65/0xd0 [xfs] Mar 5 12:50:21 xxxxxxx kernel: [93088.912876] [] xfs_bmbt_write_verify+0xe/0x10 [xfs] Mar 5 12:50:21 xxxxxxx kernel: [93088.912889] [] _xfs_buf_ioapply+0x5e/0x370 [xfs] Mar 5 12:50:21 xxxxxxx kernel: [93088.912894] [] ? try_to_wake_up+0x2d0/0x2d0 Mar 5 12:50:21 xxxxxxx kernel: [93088.912907] [] ? xfs_bdstrat_cb+0x65/0xd0 [xfs] Mar 5 12:50:21 xxxxxxx kernel: [93088.912920] [] xfs_buf_iorequest+0x4a/0xa0 [xfs] Mar 5 12:50:21 xxxxxxx kernel: [93088.912933] [] xfs_bdstrat_cb+0x65/0xd0 [xfs] Mar 5 12:50:21 xxxxxxx kernel: [93088.912946] [] __xfs_buf_delwri_submit+0x171/0x1e0 [xfs] Mar 5 12:50:21 xxxxxxx kernel: [93088.912960] [] ? xfs_buf_delwri_submit_nowait+0x20/0x30 [xfs] Mar 5 12:50:21 xxxxxxx kernel: [93088.912979] [] ? xfs_trans_ail_cursor_first+0x80/0xb0 [xfs] Mar 5 12:50:21 xxxxxxx kernel: [93088.912992] [] xfs_buf_delwri_submit_nowait+0x20/0x30 [xfs] Mar 5 12:50:21 xxxxxxx kernel: [93088.913002] [] xfsaild+0x221/0x5d0 [xfs] Mar 5 12:50:21 xxxxxxx kernel: [93088.913047] [] ? xfs_trans_ail_cursor_first+0xb0/0xb0 [xfs] Mar 5 12:50:21 xxxxxxx kernel: [93088.913058] [] kthread+0xc0/0xd0 Mar 5 12:50:21 xxxxxxx kernel: [93088.913063] [] ? ftrace_define_fields_xen_mc_entry+0xa0/0xf0 Mar 5 12:50:21 xxxxxxx kernel: [93088.913065] [] ? kthread_create_on_node+0x120/0x120 Mar 5 12:50:21 xxxxxxx kernel: [93088.913069] [] ret_from_fork+0x7c/0xb0 Mar 5 12:50:21 xxxxxxx kernel: [93088.913072] [] ? kthread_create_on_node+0x120/0x120 Mar 5 12:50:21 xxxxxxx kernel: [93088.913075] XFS (loop0): Corruption detected. Unmount and run xfs_repair Mar 5 12:50:21 xxxxxxx kernel: [93088.913081] XFS (loop0): xfs_do_force_shutdown(0x8) called from line 1358 of file fs/xfs/xfs_buf.c. Return address = 0xffffffffa002f441 Mar 5 12:50:21 xxxxxxx kernel: [93088.913090] XFS (loop0): Corruption of in-memory data detected. Shutting down filesystem Mar 5 12:50:21 xxxxxxx kernel: [93088.913094] XFS (loop0): Please umount the filesystem and rectify the problem(s) Unmounted /home partition: Mar 5 12:50:51 xxxxxxx kernel: [93118.944028] XFS (loop0): xfs_log_force: error 5 returned. Mar 5 12:51:21 xxxxxxx kernel: [93149.024021] XFS (loop0): xfs_log_force: error 5 returned. Mar 5 12:51:34 xxxxxxx kernel: [93162.227404] XFS (loop0): xfs_log_force: error 5 returned. Mar 5 12:51:34 xxxxxxx kernel: [93162.399230] XFS (loop0): xfs_log_force: error 5 returned. Mar 5 12:51:34 xxxxxxx kernel: [93162.484440] XFS (loop0): xfs_log_force: error 5 returned. Mount /home: Mar 5 12:52:15 xxxxxxx kernel: [93203.823908] XFS (loop0): Mounting Filesystem Mar 5 12:52:16 xxxxxxx kernel: [93203.921716] XFS (loop0): Starting recovery (logdev: internal) Mar 5 12:52:16 xxxxxxx kernel: [93203.925106] XFS (loop0): log record CRC mismatch: found 0x73ada7a8, expected 0x707caf70. Mar 5 12:52:16 xxxxxxx kernel: [93203.925106] Mar 5 12:52:16 xxxxxxx kernel: [93203.926284] ffffc90010f80000: 00 00 00 29 00 00 00 60 69 00 00 00 4e 49 a4 81 ...)...`i...NI.. Mar 5 12:52:16 xxxxxxx kernel: [93203.927457] ffffc90010f80010: 02 02 00 00 e8 03 00 00 e8 03 00 00 01 00 00 00 ................ Mar 5 12:52:16 xxxxxxx kernel: [93203.955789] XFS (loop0): log record CRC mismatch: found 0x812d8b74, expected 0x804f4c8f. Mar 5 12:52:16 xxxxxxx kernel: [93203.955789] Mar 5 12:52:16 xxxxxxx kernel: [93203.957064] ffffc90010f80000: 00 00 00 29 00 00 00 00 69 01 00 00 dd a9 1c 1e ...)....i....... Mar 5 12:52:16 xxxxxxx kernel: [93203.958297] ffffc90010f80010: 00 00 00 10 69 00 00 00 4e 41 52 54 2a 00 00 00 ....i...NART*... Mar 5 12:52:16 xxxxxxx kernel: [93203.966873] XFS (loop0): log record CRC mismatch: found 0xfe2b5eb2, expected 0xcf6bdbcf. Mar 5 12:52:16 xxxxxxx kernel: [93203.966873] Mar 5 12:52:16 xxxxxxx kernel: [93203.968220] ffffc90010f80000: 00 00 00 29 00 00 03 60 69 18 00 00 00 00 00 00 ...)...`i....... Mar 5 12:52:16 xxxxxxx kernel: [93203.969436] ffffc90010f80010: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................ Mar 5 12:52:16 xxxxxxx kernel: [93203.973081] XFS (loop0): log record CRC mismatch: found 0x95245555, expected 0x8cbe76ce. Mar 5 12:52:16 xxxxxxx kernel: [93203.973081] Mar 5 12:52:16 xxxxxxx kernel: [93203.974507] ffffc90010f80000: 00 00 00 29 00 00 00 48 69 18 00 00 00 00 00 00 ...)...Hi....... Mar 5 12:52:16 xxxxxxx kernel: [93203.975784] ffffc90010f80010: 00 00 01 00 c7 cd 35 51 e6 fe 0a 16 c7 cd 35 51 ......5Q......5Q Mar 5 12:52:16 xxxxxxx kernel: [93203.983811] XFS (loop0): log record CRC mismatch: found 0x73ada7a8, expected 0x707caf70. Mar 5 12:52:16 xxxxxxx kernel: [93203.983811] Mar 5 12:52:16 xxxxxxx kernel: [93203.985372] ffffc90014c00000: 00 00 00 29 00 00 00 60 69 00 00 00 4e 49 a4 81 ...)...`i...NI.. Mar 5 12:52:16 xxxxxxx kernel: [93203.986759] ffffc90014c00010: 02 02 00 00 e8 03 00 00 e8 03 00 00 01 00 00 00 ................ Mar 5 12:52:16 xxxxxxx kernel: [93203.995116] XFS (loop0): log record CRC mismatch: found 0x812d8b74, expected 0x804f4c8f. Mar 5 12:52:16 xxxxxxx kernel: [93203.995116] Mar 5 12:52:16 xxxxxxx kernel: [93203.996650] ffffc90014c00000: 00 00 00 29 00 00 00 00 69 01 00 00 dd a9 1c 1e ...)....i....... Mar 5 12:52:16 xxxxxxx kernel: [93203.998018] ffffc90014c00010: 00 00 00 10 69 00 00 00 4e 41 52 54 2a 00 00 00 ....i...NART*... Mar 5 12:52:16 xxxxxxx kernel: [93204.006817] XFS (loop0): log record CRC mismatch: found 0xfe2b5eb2, expected 0xcf6bdbcf. Mar 5 12:52:16 xxxxxxx kernel: [93204.006817] Mar 5 12:52:16 xxxxxxx kernel: [93204.008432] ffffc90014c00000: 00 00 00 29 00 00 03 60 69 18 00 00 00 00 00 00 ...)...`i....... Mar 5 12:52:16 xxxxxxx kernel: [93204.009808] ffffc90014c00010: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................ Mar 5 12:52:16 xxxxxxx kernel: [93204.013573] XFS (loop0): log record CRC mismatch: found 0x95245555, expected 0x8cbe76ce. Mar 5 12:52:16 xxxxxxx kernel: [93204.013573] Mar 5 12:52:16 xxxxxxx kernel: [93204.015169] ffffc90014c00000: 00 00 00 29 00 00 00 48 69 18 00 00 00 00 00 00 ...)...Hi....... Mar 5 12:52:16 xxxxxxx kernel: [93204.016560] ffffc90014c00010: 00 00 01 00 c7 cd 35 51 e6 fe 0a 16 c7 cd 35 51 ......5Q......5Q Mar 5 12:52:16 xxxxxxx kernel: [93204.825304] XFS (loop0): Ending recovery (logdev: internal) Umount, xfs_repair, remount: Mar 5 12:53:31 xxxxxxx kernel: [93278.958787] XFS (loop0): Mounting Filesystem Mar 5 12:53:31 xxxxxxx kernel: [93279.063396] XFS (loop0): Ending clean mount 20 minutes later, recompiling kernel 3.8.1 (noarch) and running rsync I had another error: Mar 5 13:10:36 xxxxxxx kernel: [94304.726835] ffff880110756000: 2f 68 6f 6d 65 2f 67 61 62 72 69 65 6c 2f 77 6f /home/gabriel/wo Mar 5 13:10:36 xxxxxxx kernel: [94304.726842] XFS (loop0): Internal error xfs_bmbt_verify at line 747 of file fs/xfs/xfs_bmap_btree.c. Caller 0xffffffffa005b7fe Mar 5 13:10:36 xxxxxxx kernel: [94304.726842] Mar 5 13:10:36 xxxxxxx kernel: [94304.726846] Pid: 25827, comm: xfsaild/loop0 Tainted: GF C O 3.8.1-201.AES.f18g.x86_64 #1 Mar 5 13:10:36 xxxxxxx kernel: [94304.726847] Call Trace: Mar 5 13:10:36 xxxxxxx kernel: [94304.726897] [] xfs_error_report+0x3f/0x50 [xfs] Mar 5 13:10:36 xxxxxxx kernel: [94304.726914] [] ? xfs_bmbt_write_verify+0xe/0x10 [xfs] Mar 5 13:10:36 xxxxxxx kernel: [94304.726927] [] xfs_corruption_error+0x5e/0x90 [xfs] Mar 5 13:10:36 xxxxxxx kernel: [94304.726943] [] ? xfs_bmbt_write_verify+0xe/0x10 [xfs] Mar 5 13:10:36 xxxxxxx kernel: [94304.726959] [] xfs_bmbt_verify+0x76/0x1c0 [xfs] Mar 5 13:10:36 xxxxxxx kernel: [94304.727062] [] ? xfs_bmbt_write_verify+0xe/0x10 [xfs] Mar 5 13:10:36 xxxxxxx kernel: [94304.727075] [] ? xfs_bdstrat_cb+0x65/0xd0 [xfs] Mar 5 13:10:36 xxxxxxx kernel: [94304.727091] [] xfs_bmbt_write_verify+0xe/0x10 [xfs] Mar 5 13:10:36 xxxxxxx kernel: [94304.727104] [] _xfs_buf_ioapply+0x5e/0x370 [xfs] Mar 5 13:10:36 xxxxxxx kernel: [94304.727110] [] ? try_to_wake_up+0x2d0/0x2d0 Mar 5 13:10:36 xxxxxxx kernel: [94304.727123] [] ? xfs_bdstrat_cb+0x65/0xd0 [xfs] Mar 5 13:10:36 xxxxxxx kernel: [94304.727136] [] xfs_buf_iorequest+0x4a/0xa0 [xfs] Mar 5 13:10:36 xxxxxxx kernel: [94304.727149] [] xfs_bdstrat_cb+0x65/0xd0 [xfs] Mar 5 13:10:36 xxxxxxx kernel: [94304.727162] [] __xfs_buf_delwri_submit+0x171/0x1e0 [xfs] Mar 5 13:10:36 xxxxxxx kernel: [94304.727176] [] ? xfs_buf_delwri_submit_nowait+0x20/0x30 [xfs] Mar 5 13:10:36 xxxxxxx kernel: [94304.727195] [] ? xfs_trans_ail_cursor_first+0x81/0xb0 [xfs] Mar 5 13:10:36 xxxxxxx kernel: [94304.727209] [] xfs_buf_delwri_submit_nowait+0x20/0x30 [xfs] Mar 5 13:10:36 xxxxxxx kernel: [94304.727227] [] xfsaild+0x221/0x5d0 [xfs] Mar 5 13:10:36 xxxxxxx kernel: [94304.727246] [] ? xfs_trans_ail_cursor_first+0xb0/0xb0 [xfs] Mar 5 13:10:36 xxxxxxx kernel: [94304.727251] [] kthread+0xc0/0xd0 Mar 5 13:10:36 xxxxxxx kernel: [94304.727256] [] ? ftrace_define_fields_xen_mc_entry+0xa0/0xf0 Mar 5 13:10:36 xxxxxxx kernel: [94304.727258] [] ? kthread_create_on_node+0x120/0x120 Mar 5 13:10:36 xxxxxxx kernel: [94304.727262] [] ret_from_fork+0x7c/0xb0 Mar 5 13:10:36 xxxxxxx kernel: [94304.727265] [] ? kthread_create_on_node+0x120/0x120 Mar 5 13:10:36 xxxxxxx kernel: [94304.727267] XFS (loop0): Corruption detected. Unmount and run xfs_repair Mar 5 13:10:36 xxxxxxx kernel: [94304.727270] XFS (loop0): xfs_do_force_shutdown(0x8) called from line 1358 of file fs/xfs/xfs_buf.c. Return address = 0xffffffffa002f441 Mar 5 13:10:37 xxxxxxx kernel: [94304.982635] XFS (loop0): Corruption of in-memory data detected. Shutting down filesystem Mar 5 13:10:37 xxxxxxx kernel: [94304.982642] XFS (loop0): Please umount the filesystem and rectify the problem(s) Mar 5 13:10:37 xxxxxxx kernel: [94305.036039] XFS (loop0): xfs_log_force: error 5 returned. Mar 5 13:10:37 xxxxxxx kernel: [94305.087970] Buffer I/O error on device loop0, logical block 90997607 Mar 5 13:10:37 xxxxxxx kernel: [94305.087975] lost page write due to I/O error on loop0 Mar 5 13:10:37 xxxxxxx kernel: [94305.087980] Buffer I/O error on device loop0, logical block 90997608 Mar 5 13:10:37 xxxxxxx kernel: [94305.087981] lost page write due to I/O error on loop0 Mar 5 13:10:37 xxxxxxx kernel: [94305.087983] Buffer I/O error on device loop0, logical block 90997609 Mar 5 13:10:37 xxxxxxx kernel: [94305.087984] lost page write due to I/O error on loop0 Mar 5 13:10:37 xxxxxxx kernel: [94305.087986] Buffer I/O error on device loop0, logical block 90997610 Mar 5 13:10:37 xxxxxxx kernel: [94305.087988] lost page write due to I/O error on loop0 Mar 5 13:10:37 xxxxxxx kernel: [94305.087990] Buffer I/O error on device loop0, logical block 90997611 Mar 5 13:10:37 xxxxxxx kernel: [94305.087991] lost page write due to I/O error on loop0 Mar 5 13:10:37 xxxxxxx kernel: [94305.087993] Buffer I/O error on device loop0, logical block 90997612 Mar 5 13:10:37 xxxxxxx kernel: [94305.087994] lost page write due to I/O error on loop0 Mar 5 13:10:37 xxxxxxx kernel: [94305.087996] Buffer I/O error on device loop0, logical block 90997613 Mar 5 13:10:37 xxxxxxx kernel: [94305.087997] lost page write due to I/O error on loop0 Mar 5 13:10:37 xxxxxxx kernel: [94305.087999] Buffer I/O error on device loop0, logical block 90997614 Mar 5 13:10:37 xxxxxxx kernel: [94305.088018] lost page write due to I/O error on loop0 Mar 5 13:10:37 xxxxxxx kernel: [94305.088020] Buffer I/O error on device loop0, logical block 90997615 Mar 5 13:10:37 xxxxxxx kernel: [94305.088021] lost page write due to I/O error on loop0 Mar 5 13:10:37 xxxxxxx kernel: [94305.088023] Buffer I/O error on device loop0, logical block 90997616 Mar 5 13:10:37 xxxxxxx kernel: [94305.088025] lost page write due to I/O error on loop0 Umount /home: Mar 5 13:11:06 xxxxxxx kernel: [94334.816017] XFS (loop0): xfs_log_force: error 5 returned. Mar 5 13:11:37 xxxxxxx kernel: [94364.896026] XFS (loop0): xfs_log_force: error 5 returned. Mar 5 13:12:07 xxxxxxx kernel: [94394.976025] XFS (loop0): xfs_log_force: error 5 returned. Mar 5 13:12:08 xxxxxxx kernel: [94396.397569] XFS (loop0): xfs_log_force: error 5 returned. Mar 5 13:12:08 xxxxxxx kernel: [94396.798331] XFS (loop0): xfs_log_force: error 5 returned. Mar 5 13:12:08 xxxxxxx kernel: [94396.803897] XFS (loop0): xfs_log_force: error 5 returned. Mount /home: Mar 5 13:12:36 xxxxxxx kernel: [94424.276817] XFS (loop0): Mounting Filesystem Mar 5 13:12:36 xxxxxxx kernel: [94424.444206] XFS (loop0): Starting recovery (logdev: internal) Mar 5 13:12:36 xxxxxxx kernel: [94424.454409] XFS (loop0): log record CRC mismatch: found 0xe8dc0331, expected 0xb8afb9f5. Mar 5 13:12:36 xxxxxxx kernel: [94424.454409] Mar 5 13:12:36 xxxxxxx kernel: [94424.454427] ffffc90014440000: 00 00 00 01 00 00 00 00 69 01 00 00 4f 3e 05 16 ........i...O>.. Mar 5 13:12:36 xxxxxxx kernel: [94424.454434] ffffc90014440010: 00 00 00 10 69 00 00 00 4e 41 52 54 2a 00 00 00 ....i...NART*... Mar 5 13:12:36 xxxxxxx kernel: [94424.457657] XFS (loop0): log record CRC mismatch: found 0xca3729fa, expected 0x936285f8. Mar 5 13:12:36 xxxxxxx kernel: [94424.457657] Mar 5 13:12:36 xxxxxxx kernel: [94424.457677] ffffc90014440000: 00 00 00 01 00 00 00 48 69 18 00 00 00 00 00 00 .......Hi....... Mar 5 13:12:36 xxxxxxx kernel: [94424.457685] ffffc90014440010: 00 00 00 00 3e d2 35 51 d3 4c a5 05 3e d2 35 51 ....>.5Q.L..>.5Q Mar 5 13:12:36 xxxxxxx kernel: [94424.459325] XFS (loop0): log record CRC mismatch: found 0x82df5071, expected 0x147787f2. Mar 5 13:12:36 xxxxxxx kernel: [94424.459325] Mar 5 13:12:36 xxxxxxx kernel: [94424.459343] ffffc90014440000: 00 00 00 01 00 00 00 00 69 01 00 00 b6 da 4d 37 ........i.....M7 Mar 5 13:12:36 xxxxxxx kernel: [94424.459351] ffffc90014440010: 00 00 00 10 69 00 00 00 4e 41 52 54 2a 00 00 00 ....i...NART*... Mar 5 13:12:36 xxxxxxx kernel: [94424.459825] XFS (loop0): log record CRC mismatch: found 0x81d60a0c, expected 0xa36fc6cf. Mar 5 13:12:36 xxxxxxx kernel: [94424.459825] Mar 5 13:12:36 xxxxxxx kernel: [94424.459836] ffffc90014440000: 00 00 00 01 00 00 00 00 69 01 00 00 a0 58 d2 ca ........i....X.. Mar 5 13:12:36 xxxxxxx kernel: [94424.459842] ffffc90014440010: 00 00 00 10 69 00 00 00 4e 41 52 54 2a 00 00 00 ....i...NART*... Mar 5 13:12:36 xxxxxxx kernel: [94424.460452] XFS (loop0): log record CRC mismatch: found 0xd5e688af, expected 0x32f0716d. Mar 5 13:12:36 xxxxxxx kernel: [94424.460452] Mar 5 13:12:36 xxxxxxx kernel: [94424.460466] ffffc90014440000: 00 00 00 01 00 00 00 00 69 01 00 00 7d a4 99 70 ........i...}..p Mar 5 13:12:36 xxxxxxx kernel: [94424.460473] ffffc90014440010: 00 00 00 10 69 00 00 00 4e 41 52 54 2a 00 00 00 ....i...NART*... Mar 5 13:12:36 xxxxxxx kernel: [94424.460904] XFS (loop0): log record CRC mismatch: found 0xaa2ac0a7, expected 0x94620a44. Mar 5 13:12:36 xxxxxxx kernel: [94424.460904] Mar 5 13:12:36 xxxxxxx kernel: [94424.460915] ffffc90014440000: 00 00 00 01 00 00 00 00 69 01 00 00 43 53 3a 4f ........i...CS:O Mar 5 13:12:36 xxxxxxx kernel: [94424.460921] ffffc90014440010: 00 00 00 10 69 00 00 00 4e 41 52 54 2a 00 00 00 ....i...NART*... Mar 5 13:12:36 xxxxxxx kernel: [94424.474642] XFS (loop0): log record CRC mismatch: found 0x924e1723, expected 0x89c0a34b. Mar 5 13:12:36 xxxxxxx kernel: [94424.474642] Mar 5 13:12:36 xxxxxxx kernel: [94424.474661] ffffc90014440000: 00 00 00 01 00 00 00 00 69 01 00 00 05 3b b5 68 ........i....;.h Mar 5 13:12:36 xxxxxxx kernel: [94424.474668] ffffc90014440010: 00 00 00 10 69 00 00 00 4e 41 52 54 2a 00 00 00 ....i...NART*... Mar 5 13:12:36 xxxxxxx kernel: [94424.475512] XFS (loop0): log record CRC mismatch: found 0x1b8a4eb7, expected 0xa9b341a6. Mar 5 13:12:36 xxxxxxx kernel: [94424.475512] Mar 5 13:12:36 xxxxxxx kernel: [94424.475529] ffffc90014440000: 00 00 00 01 00 00 00 00 69 01 00 00 1b e8 ad f5 ........i....... Mar 5 13:12:36 xxxxxxx kernel: [94424.475536] ffffc90014440010: 00 00 00 10 69 00 00 00 4e 41 52 54 2a 00 00 00 ....i...NART*... Mar 5 13:12:36 xxxxxxx kernel: [94424.478164] XFS (loop0): log record CRC mismatch: found 0xe7aaf329, expected 0x62577a0d. Mar 5 13:12:36 xxxxxxx kernel: [94424.478164] Mar 5 13:12:36 xxxxxxx kernel: [94424.478181] ffffc90014440000: 00 00 00 01 00 00 00 00 69 01 00 00 5f 1b ed 49 ........i..._..I Mar 5 13:12:36 xxxxxxx kernel: [94424.478190] ffffc90014440010: 00 00 00 10 69 00 00 00 4e 41 52 54 2a 00 00 00 ....i...NART*... Mar 5 13:12:36 xxxxxxx kernel: [94424.478869] XFS (loop0): log record CRC mismatch: found 0x8b024d5d, expected 0xa6ddb6cf. Mar 5 13:12:36 xxxxxxx kernel: [94424.478869] Mar 5 13:12:36 xxxxxxx kernel: [94424.479208] ffffc90014440000: 00 00 00 01 00 00 00 00 69 01 00 00 b1 f5 1e 94 ........i....... Mar 5 13:12:36 xxxxxxx kernel: [94424.480501] ffffc90014440010: 00 00 00 10 69 00 00 00 4e 41 52 54 2a 00 00 00 ....i...NART*... Mar 5 13:12:36 xxxxxxx kernel: [94424.489048] XFS (loop0): log record CRC mismatch: found 0xe8dc0331, expected 0xb8afb9f5. Mar 5 13:12:36 xxxxxxx kernel: [94424.489048] Mar 5 13:12:36 xxxxxxx kernel: [94424.490737] ffffc90014480000: 00 00 00 01 00 00 00 00 69 01 00 00 4f 3e 05 16 ........i...O>.. Mar 5 13:12:36 xxxxxxx kernel: [94424.492209] ffffc90014480010: 00 00 00 10 69 00 00 00 4e 41 52 54 2a 00 00 00 ....i...NART*... Mar 5 13:12:36 xxxxxxx kernel: [94424.496938] XFS (loop0): log record CRC mismatch: found 0xca3729fa, expected 0x936285f8. Mar 5 13:12:36 xxxxxxx kernel: [94424.496938] Mar 5 13:12:36 xxxxxxx kernel: [94424.498729] ffffc90014480000: 00 00 00 01 00 00 00 48 69 18 00 00 00 00 00 00 .......Hi....... Mar 5 13:12:36 xxxxxxx kernel: [94424.500298] ffffc90014480010: 00 00 00 00 3e d2 35 51 d3 4c a5 05 3e d2 35 51 ....>.5Q.L..>.5Q Mar 5 13:12:37 xxxxxxx kernel: [94425.029493] XFS (loop0): log record CRC mismatch: found 0x82df5071, expected 0x147787f2. Mar 5 13:12:37 xxxxxxx kernel: [94425.029493] Mar 5 13:12:37 xxxxxxx kernel: [94425.031376] ffffc90014480000: 00 00 00 01 00 00 00 00 69 01 00 00 b6 da 4d 37 ........i.....M7 Mar 5 13:12:37 xxxxxxx kernel: [94425.032938] ffffc90014480010: 00 00 00 10 69 00 00 00 4e 41 52 54 2a 00 00 00 ....i...NART*... Mar 5 13:12:37 xxxxxxx kernel: [94425.069605] XFS (loop0): log record CRC mismatch: found 0x81d60a0c, expected 0xa36fc6cf. Mar 5 13:12:37 xxxxxxx kernel: [94425.069605] Mar 5 13:12:37 xxxxxxx kernel: [94425.071520] ffffc90014480000: 00 00 00 01 00 00 00 00 69 01 00 00 a0 58 d2 ca ........i....X.. Mar 5 13:12:37 xxxxxxx kernel: [94425.073183] ffffc90014480010: 00 00 00 10 69 00 00 00 4e 41 52 54 2a 00 00 00 ....i...NART*... Mar 5 13:12:37 xxxxxxx kernel: [94425.082249] XFS (loop0): log record CRC mismatch: found 0xd5e688af, expected 0x32f0716d. Mar 5 13:12:37 xxxxxxx kernel: [94425.082249] Mar 5 13:12:37 xxxxxxx kernel: [94425.084292] ffffc90014480000: 00 00 00 01 00 00 00 00 69 01 00 00 7d a4 99 70 ........i...}..p Mar 5 13:12:37 xxxxxxx kernel: [94425.085947] ffffc90014480010: 00 00 00 10 69 00 00 00 4e 41 52 54 2a 00 00 00 ....i...NART*... Mar 5 13:12:37 xxxxxxx kernel: [94425.092165] XFS (loop0): log record CRC mismatch: found 0xaa2ac0a7, expected 0x94620a44. Mar 5 13:12:37 xxxxxxx kernel: [94425.092165] Mar 5 13:12:37 xxxxxxx kernel: [94425.094305] ffffc90014480000: 00 00 00 01 00 00 00 00 69 01 00 00 43 53 3a 4f ........i...CS:O Mar 5 13:12:37 xxxxxxx kernel: [94425.096037] ffffc90014480010: 00 00 00 10 69 00 00 00 4e 41 52 54 2a 00 00 00 ....i...NART*... Mar 5 13:12:37 xxxxxxx kernel: [94425.111936] XFS (loop0): log record CRC mismatch: found 0x924e1723, expected 0x89c0a34b. Mar 5 13:12:37 xxxxxxx kernel: [94425.111936] Mar 5 13:12:37 xxxxxxx kernel: [94425.114115] ffffc90014480000: 00 00 00 01 00 00 00 00 69 01 00 00 05 3b b5 68 ........i....;.h Mar 5 13:12:37 xxxxxxx kernel: [94425.115816] ffffc90014480010: 00 00 00 10 69 00 00 00 4e 41 52 54 2a 00 00 00 ....i...NART*... Mar 5 13:12:37 xxxxxxx kernel: [94425.527549] XFS (loop0): log record CRC mismatch: found 0x1b8a4eb7, expected 0xa9b341a6. Mar 5 13:12:37 xxxxxxx kernel: [94425.527549] Mar 5 13:12:37 xxxxxxx kernel: [94425.529738] ffffc90014480000: 00 00 00 01 00 00 00 00 69 01 00 00 1b e8 ad f5 ........i....... Mar 5 13:12:37 xxxxxxx kernel: [94425.531521] ffffc90014480010: 00 00 00 10 69 00 00 00 4e 41 52 54 2a 00 00 00 ....i...NART*... Mar 5 13:12:37 xxxxxxx kernel: [94425.539719] XFS (loop0): log record CRC mismatch: found 0xe7aaf329, expected 0x62577a0d. Mar 5 13:12:37 xxxxxxx kernel: [94425.539719] Mar 5 13:12:37 xxxxxxx kernel: [94425.541902] ffffc90014480000: 00 00 00 01 00 00 00 00 69 01 00 00 5f 1b ed 49 ........i..._..I Mar 5 13:12:37 xxxxxxx kernel: [94425.543659] ffffc90014480010: 00 00 00 10 69 00 00 00 4e 41 52 54 2a 00 00 00 ....i...NART*... Mar 5 13:12:38 xxxxxxx kernel: [94425.890080] XFS (loop0): log record CRC mismatch: found 0x8b024d5d, expected 0xa6ddb6cf. Mar 5 13:12:38 xxxxxxx kernel: [94425.890080] Mar 5 13:12:38 xxxxxxx kernel: [94425.892186] ffffc90014480000: 00 00 00 01 00 00 00 00 69 01 00 00 b1 f5 1e 94 ........i....... Mar 5 13:12:38 xxxxxxx kernel: [94425.893932] ffffc90014480010: 00 00 00 10 69 00 00 00 4e 41 52 54 2a 00 00 00 ....i...NART*... Mar 5 13:12:38 xxxxxxx kernel: [94425.911651] XFS (loop0): Ending recovery (logdev: internal) Umount, xfs_repair, mount. Reboot with 3.7.9 (x86_64) - full resync for whole directory tree (196Gb): no problems - kernel re-compilation: no problems Seems to be related to kernel tree directory: Mar 5 12:50:21 xxxxxxx kernel: [93088.912705] ffff88010e1bf000: 2f 68 6f 6d 65 2f 67 61 62 72 69 65 6c 2f 77 6f /home/gabriel/wo I think the actual directory is /home/gabriel/work/rpm/BUILD/kernel-3.8.f18g/ ... Is there any way I can debug this? Additional info: * kernel: 3.8.1 (x86_64) * xfs_repair version: 3.1.10 * 1 cpu # cat /proc/mounts | grep xfs | grep ^/dev /dev/sda2 / xfs rw,seclabel,relatime,attr2,inode64,noquota 0 0 /dev/sdc1 /saves xfs rw,seclabel,nosuid,nodev,relatime,attr2,inode64,logbufs=8,logbsize=256k,noquota 0 0 /dev/sdb1 /export xfs rw,seclabel,nosuid,nodev,relatime,attr2,inode64,logbufs=8,logbsize=256k,noquota 0 0 /dev/loop6 /tmp xfs rw,seclabel,nosuid,nodev,noexec,relatime,attr2,inode64,noquota 0 0 /dev/loop6 /var/tmp xfs rw,seclabel,nosuid,nodev,noexec,relatime,attr2,inode64,noquota 0 0 /dev/loop0 /home xfs rw,seclabel,nosuid,nodev,relatime,attr2,inode64,logbufs=8,logbsize=256k,noquota 0 0 # cat /proc/partitions major minor #blocks name 8 0 488386584 sda 8 1 512000 sda1 8 2 20971520 sda2 8 3 2097152 sda3 8 4 1 sda4 8 5 462707712 sda5 8 6 2095104 sda6 11 0 1048575 sr0 8 32 312571224 sdc 8 33 312570200 sdc1 8 16 156290904 sdb 8 17 156289880 sdb1 7 0 462707704 loop0 7 6 2095104 loop6 7 7 2097148 loop7 # xfs_info /home meta-data=/dev/loop0 isize=256 agcount=4, agsize=28919232 blks = sectsz=512 attr=2 data = bsize=4096 blocks=115676926, imaxpct=25 = sunit=0 swidth=0 blks naming =version 2 bsize=4096 ascii-ci=0 log =internal bsize=4096 blocks=56482, version=2 = sectsz=512 sunit=0 blks, lazy-count=1 realtime =none extsz=4096 blocks=0, rtextents=0 Sincerely, Gabriel - -- // Gabriel VLASIU // // OpenGPG-KeyID : 44952F15 // OpenGPG-Fingerprint: 4AC5 7C26 2FE9 02DA 4906 24B2 D32B 7ED7 4495 2F15 // OpenGPG-URL : http://www.vlasiu.net/public.key -----BEGIN PGP SIGNATURE----- Version: GnuPG v1.4.13 (GNU/Linux) iQIcBAEBCgAGBQJRNe1sAAoJENMrftdElS8Vrt8QALOWM3Gzph6TDWkGwcqyxTos o6X0jXfJxEn+pYdcMWh+h8x8poxfLFNxCn4yVqO5WdX4xqYq23BYO1VR0qqFueTT dNerqxQcvKn+HRi+hsME/GabDjI5RInvotZ2QVWjuqWk72F2qlIVnmvQtCXOm1lX 6Mkf18b0+voCgZG6eYHSftbRxc+Jme2lPl5fbUcGDeiANkkZbq0+YrfAp6u9KEOu CX5Pzss7oSDqTCVzy0X85Xw9f1txKEdjPbzZkMcTLFmVgB7zc/muViEmEiLljGjS DLtoONDoHU6cVTkfr7Uzjuv49vwSKNL/5qrtX05+GidUOAKQqGs90FR3wgMC9SHR Vo5RSbNVOEeRUkbhWa2mBemscD6teNujBnVkvVsWeeA9qdf4F5CldshfCdZocLhe Zy8qD/ZmoVJTgEzv5iksd4WzkpVnT5Vz0w59ETW3SkvIdceGwEFCE3PUS19Yb6Gr /OWj8bna+QtgtrEijbwdOPDDx6JrXXcYTtJk7m2R0LMRC3GymPeOiJSbrxFe8XTn s6o4QGZQczPkwL/+wQIDiijAQxBn/t9tRC36iunIA7hXRzmYhtgj9s6iXTmiLLJk NkdZ9jlg82RFenXaDDOMMdki2tgEmGZGpYDH81V/Nfi4VHDBjM0ZIjP0/2wWoUnA 9GYY2qWSGY3MNw28hlu9 =RjjN -----END PGP SIGNATURE----- From bpm@sgi.com Tue Mar 5 09:43:29 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 129BC7F81 for ; Tue, 5 Mar 2013 09:43:29 -0600 (CST) Received: from whiskey.americas.sgi.com (eagdhcp-232-197.americas.sgi.com [128.162.232.197]) by relay1.corp.sgi.com (Postfix) with ESMTP id C1E898F8033; Tue, 5 Mar 2013 07:43:25 -0800 (PST) Received: by whiskey.americas.sgi.com (Postfix, from userid 4600) id 6C37D500B4A; Tue, 5 Mar 2013 09:43:25 -0600 (CST) Date: Tue, 5 Mar 2013 09:43:25 -0600 From: Ben Myers To: Gabriel VLASIU Cc: xfs@oss.sgi.com Subject: Re: xfs with kernel 3.8.1 Message-ID: <20130305154325.GJ22182@sgi.com> References: MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: User-Agent: Mutt/1.5.20 (2009-06-14) Hi Gabriel, This is fixed in 3.8.2, by commit 2cd182d6f0f xfs: xfs_bmap_add_attrfork_local is too generic commit 1e82379b018ceed0f0912327c60d73107dacbcb3 upstream. -Ben On Tue, Mar 05, 2013 at 03:04:44PM +0200, Gabriel VLASIU wrote: > -----BEGIN PGP SIGNED MESSAGE----- > Hash: SHA512 > > Hi! > > I think there is something wrong with xfs in kernel 3.8.1 (x86_64). > > While compiling kernel 3.8.2 (noarch section: rpmbuild -bb kernel.spec > - --target=noarch) I had this error: > > Mar 5 12:50:21 xxxxxxx kernel: [93088.912705] ffff88010e1bf000: 2f 68 6f 6d 65 2f 67 61 62 72 69 65 6c 2f 77 6f /home/gabriel/wo > Mar 5 12:50:21 xxxxxxx kernel: [93088.912713] XFS (loop0): Internal error xfs_bmbt_verify at line 747 of file fs/xfs/xfs_bmap_btree.c. Caller 0xffffffffa005b7fe > Mar 5 12:50:21 xxxxxxx kernel: [93088.912713] > Mar 5 12:50:21 xxxxxxx kernel: [93088.912716] Pid: 497, comm: xfsaild/loop0 Tainted: GF C O 3.8.1-201.AES.f18g.x86_64 #1 > Mar 5 12:50:21 xxxxxxx kernel: [93088.912718] Call Trace: > Mar 5 12:50:21 xxxxxxx kernel: [93088.912768] [] xfs_error_report+0x3f/0x50 [xfs] > Mar 5 12:50:21 xxxxxxx kernel: [93088.912786] [] ? xfs_bmbt_write_verify+0xe/0x10 [xfs] > Mar 5 12:50:21 xxxxxxx kernel: [93088.912799] [] xfs_corruption_error+0x5e/0x90 [xfs] > Mar 5 12:50:21 xxxxxxx kernel: [93088.912815] [] ? xfs_bmbt_write_verify+0xe/0x10 [xfs] > Mar 5 12:50:21 xxxxxxx kernel: [93088.912831] [] xfs_bmbt_verify+0x76/0x1c0 [xfs] > Mar 5 12:50:21 xxxxxxx kernel: [93088.912847] [] ? xfs_bmbt_write_verify+0xe/0x10 [xfs] > Mar 5 12:50:21 xxxxxxx kernel: [93088.912860] [] ? xfs_bdstrat_cb+0x65/0xd0 [xfs] > Mar 5 12:50:21 xxxxxxx kernel: [93088.912876] [] xfs_bmbt_write_verify+0xe/0x10 [xfs] > Mar 5 12:50:21 xxxxxxx kernel: [93088.912889] [] _xfs_buf_ioapply+0x5e/0x370 [xfs] > Mar 5 12:50:21 xxxxxxx kernel: [93088.912894] [] ? try_to_wake_up+0x2d0/0x2d0 > Mar 5 12:50:21 xxxxxxx kernel: [93088.912907] [] ? xfs_bdstrat_cb+0x65/0xd0 [xfs] > Mar 5 12:50:21 xxxxxxx kernel: [93088.912920] [] xfs_buf_iorequest+0x4a/0xa0 [xfs] > Mar 5 12:50:21 xxxxxxx kernel: [93088.912933] [] xfs_bdstrat_cb+0x65/0xd0 [xfs] > Mar 5 12:50:21 xxxxxxx kernel: [93088.912946] [] __xfs_buf_delwri_submit+0x171/0x1e0 [xfs] > Mar 5 12:50:21 xxxxxxx kernel: [93088.912960] [] ? xfs_buf_delwri_submit_nowait+0x20/0x30 [xfs] > Mar 5 12:50:21 xxxxxxx kernel: [93088.912979] [] ? xfs_trans_ail_cursor_first+0x80/0xb0 [xfs] > Mar 5 12:50:21 xxxxxxx kernel: [93088.912992] [] xfs_buf_delwri_submit_nowait+0x20/0x30 [xfs] > Mar 5 12:50:21 xxxxxxx kernel: [93088.913002] [] xfsaild+0x221/0x5d0 [xfs] > Mar 5 12:50:21 xxxxxxx kernel: [93088.913047] [] ? xfs_trans_ail_cursor_first+0xb0/0xb0 [xfs] > Mar 5 12:50:21 xxxxxxx kernel: [93088.913058] [] kthread+0xc0/0xd0 > Mar 5 12:50:21 xxxxxxx kernel: [93088.913063] [] ? ftrace_define_fields_xen_mc_entry+0xa0/0xf0 > Mar 5 12:50:21 xxxxxxx kernel: [93088.913065] [] ? kthread_create_on_node+0x120/0x120 > Mar 5 12:50:21 xxxxxxx kernel: [93088.913069] [] ret_from_fork+0x7c/0xb0 > Mar 5 12:50:21 xxxxxxx kernel: [93088.913072] [] ? kthread_create_on_node+0x120/0x120 > Mar 5 12:50:21 xxxxxxx kernel: [93088.913075] XFS (loop0): Corruption detected. Unmount and run xfs_repair > Mar 5 12:50:21 xxxxxxx kernel: [93088.913081] XFS (loop0): xfs_do_force_shutdown(0x8) called from line 1358 of file fs/xfs/xfs_buf.c. Return address = 0xffffffffa002f441 > Mar 5 12:50:21 xxxxxxx kernel: [93088.913090] XFS (loop0): Corruption of in-memory data detected. Shutting down filesystem > Mar 5 12:50:21 xxxxxxx kernel: [93088.913094] XFS (loop0): Please umount the filesystem and rectify the problem(s) > > Unmounted /home partition: > > Mar 5 12:50:51 xxxxxxx kernel: [93118.944028] XFS (loop0): xfs_log_force: error 5 returned. > Mar 5 12:51:21 xxxxxxx kernel: [93149.024021] XFS (loop0): xfs_log_force: error 5 returned. > Mar 5 12:51:34 xxxxxxx kernel: [93162.227404] XFS (loop0): xfs_log_force: error 5 returned. > Mar 5 12:51:34 xxxxxxx kernel: [93162.399230] XFS (loop0): xfs_log_force: error 5 returned. > Mar 5 12:51:34 xxxxxxx kernel: [93162.484440] XFS (loop0): xfs_log_force: error 5 returned. > > Mount /home: > > Mar 5 12:52:15 xxxxxxx kernel: [93203.823908] XFS (loop0): Mounting Filesystem > Mar 5 12:52:16 xxxxxxx kernel: [93203.921716] XFS (loop0): Starting recovery (logdev: internal) > Mar 5 12:52:16 xxxxxxx kernel: [93203.925106] XFS (loop0): log record CRC mismatch: found 0x73ada7a8, expected 0x707caf70. > Mar 5 12:52:16 xxxxxxx kernel: [93203.925106] > Mar 5 12:52:16 xxxxxxx kernel: [93203.926284] ffffc90010f80000: 00 00 00 29 00 00 00 60 69 00 00 00 4e 49 a4 81 ...)...`i...NI.. > Mar 5 12:52:16 xxxxxxx kernel: [93203.927457] ffffc90010f80010: 02 02 00 00 e8 03 00 00 e8 03 00 00 01 00 00 00 ................ > Mar 5 12:52:16 xxxxxxx kernel: [93203.955789] XFS (loop0): log record CRC mismatch: found 0x812d8b74, expected 0x804f4c8f. > Mar 5 12:52:16 xxxxxxx kernel: [93203.955789] > Mar 5 12:52:16 xxxxxxx kernel: [93203.957064] ffffc90010f80000: 00 00 00 29 00 00 00 00 69 01 00 00 dd a9 1c 1e ...)....i....... > Mar 5 12:52:16 xxxxxxx kernel: [93203.958297] ffffc90010f80010: 00 00 00 10 69 00 00 00 4e 41 52 54 2a 00 00 00 ....i...NART*... > Mar 5 12:52:16 xxxxxxx kernel: [93203.966873] XFS (loop0): log record CRC mismatch: found 0xfe2b5eb2, expected 0xcf6bdbcf. > Mar 5 12:52:16 xxxxxxx kernel: [93203.966873] > Mar 5 12:52:16 xxxxxxx kernel: [93203.968220] ffffc90010f80000: 00 00 00 29 00 00 03 60 69 18 00 00 00 00 00 00 ...)...`i....... > Mar 5 12:52:16 xxxxxxx kernel: [93203.969436] ffffc90010f80010: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................ > Mar 5 12:52:16 xxxxxxx kernel: [93203.973081] XFS (loop0): log record CRC mismatch: found 0x95245555, expected 0x8cbe76ce. > Mar 5 12:52:16 xxxxxxx kernel: [93203.973081] > Mar 5 12:52:16 xxxxxxx kernel: [93203.974507] ffffc90010f80000: 00 00 00 29 00 00 00 48 69 18 00 00 00 00 00 00 ...)...Hi....... > Mar 5 12:52:16 xxxxxxx kernel: [93203.975784] ffffc90010f80010: 00 00 01 00 c7 cd 35 51 e6 fe 0a 16 c7 cd 35 51 ......5Q......5Q > Mar 5 12:52:16 xxxxxxx kernel: [93203.983811] XFS (loop0): log record CRC mismatch: found 0x73ada7a8, expected 0x707caf70. > Mar 5 12:52:16 xxxxxxx kernel: [93203.983811] > Mar 5 12:52:16 xxxxxxx kernel: [93203.985372] ffffc90014c00000: 00 00 00 29 00 00 00 60 69 00 00 00 4e 49 a4 81 ...)...`i...NI.. > Mar 5 12:52:16 xxxxxxx kernel: [93203.986759] ffffc90014c00010: 02 02 00 00 e8 03 00 00 e8 03 00 00 01 00 00 00 ................ > Mar 5 12:52:16 xxxxxxx kernel: [93203.995116] XFS (loop0): log record CRC mismatch: found 0x812d8b74, expected 0x804f4c8f. > Mar 5 12:52:16 xxxxxxx kernel: [93203.995116] > Mar 5 12:52:16 xxxxxxx kernel: [93203.996650] ffffc90014c00000: 00 00 00 29 00 00 00 00 69 01 00 00 dd a9 1c 1e ...)....i....... > Mar 5 12:52:16 xxxxxxx kernel: [93203.998018] ffffc90014c00010: 00 00 00 10 69 00 00 00 4e 41 52 54 2a 00 00 00 ....i...NART*... > Mar 5 12:52:16 xxxxxxx kernel: [93204.006817] XFS (loop0): log record CRC mismatch: found 0xfe2b5eb2, expected 0xcf6bdbcf. > Mar 5 12:52:16 xxxxxxx kernel: [93204.006817] > Mar 5 12:52:16 xxxxxxx kernel: [93204.008432] ffffc90014c00000: 00 00 00 29 00 00 03 60 69 18 00 00 00 00 00 00 ...)...`i....... > Mar 5 12:52:16 xxxxxxx kernel: [93204.009808] ffffc90014c00010: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................ > Mar 5 12:52:16 xxxxxxx kernel: [93204.013573] XFS (loop0): log record CRC mismatch: found 0x95245555, expected 0x8cbe76ce. > Mar 5 12:52:16 xxxxxxx kernel: [93204.013573] > Mar 5 12:52:16 xxxxxxx kernel: [93204.015169] ffffc90014c00000: 00 00 00 29 00 00 00 48 69 18 00 00 00 00 00 00 ...)...Hi....... > Mar 5 12:52:16 xxxxxxx kernel: [93204.016560] ffffc90014c00010: 00 00 01 00 c7 cd 35 51 e6 fe 0a 16 c7 cd 35 51 ......5Q......5Q > Mar 5 12:52:16 xxxxxxx kernel: [93204.825304] XFS (loop0): Ending recovery (logdev: internal) > > Umount, xfs_repair, remount: > > Mar 5 12:53:31 xxxxxxx kernel: [93278.958787] XFS (loop0): Mounting Filesystem > Mar 5 12:53:31 xxxxxxx kernel: [93279.063396] XFS (loop0): Ending clean mount > > 20 minutes later, recompiling kernel 3.8.1 (noarch) and running rsync > I had another error: > > Mar 5 13:10:36 xxxxxxx kernel: [94304.726835] ffff880110756000: 2f 68 6f 6d 65 2f 67 61 62 72 69 65 6c 2f 77 6f /home/gabriel/wo > Mar 5 13:10:36 xxxxxxx kernel: [94304.726842] XFS (loop0): Internal error xfs_bmbt_verify at line 747 of file fs/xfs/xfs_bmap_btree.c. Caller 0xffffffffa005b7fe > Mar 5 13:10:36 xxxxxxx kernel: [94304.726842] > Mar 5 13:10:36 xxxxxxx kernel: [94304.726846] Pid: 25827, comm: xfsaild/loop0 Tainted: GF C O 3.8.1-201.AES.f18g.x86_64 #1 > Mar 5 13:10:36 xxxxxxx kernel: [94304.726847] Call Trace: > Mar 5 13:10:36 xxxxxxx kernel: [94304.726897] [] xfs_error_report+0x3f/0x50 [xfs] > Mar 5 13:10:36 xxxxxxx kernel: [94304.726914] [] ? xfs_bmbt_write_verify+0xe/0x10 [xfs] > Mar 5 13:10:36 xxxxxxx kernel: [94304.726927] [] xfs_corruption_error+0x5e/0x90 [xfs] > Mar 5 13:10:36 xxxxxxx kernel: [94304.726943] [] ? xfs_bmbt_write_verify+0xe/0x10 [xfs] > Mar 5 13:10:36 xxxxxxx kernel: [94304.726959] [] xfs_bmbt_verify+0x76/0x1c0 [xfs] > Mar 5 13:10:36 xxxxxxx kernel: [94304.727062] [] ? xfs_bmbt_write_verify+0xe/0x10 [xfs] > Mar 5 13:10:36 xxxxxxx kernel: [94304.727075] [] ? xfs_bdstrat_cb+0x65/0xd0 [xfs] > Mar 5 13:10:36 xxxxxxx kernel: [94304.727091] [] xfs_bmbt_write_verify+0xe/0x10 [xfs] > Mar 5 13:10:36 xxxxxxx kernel: [94304.727104] [] _xfs_buf_ioapply+0x5e/0x370 [xfs] > Mar 5 13:10:36 xxxxxxx kernel: [94304.727110] [] ? try_to_wake_up+0x2d0/0x2d0 > Mar 5 13:10:36 xxxxxxx kernel: [94304.727123] [] ? xfs_bdstrat_cb+0x65/0xd0 [xfs] > Mar 5 13:10:36 xxxxxxx kernel: [94304.727136] [] xfs_buf_iorequest+0x4a/0xa0 [xfs] > Mar 5 13:10:36 xxxxxxx kernel: [94304.727149] [] xfs_bdstrat_cb+0x65/0xd0 [xfs] > Mar 5 13:10:36 xxxxxxx kernel: [94304.727162] [] __xfs_buf_delwri_submit+0x171/0x1e0 [xfs] > Mar 5 13:10:36 xxxxxxx kernel: [94304.727176] [] ? xfs_buf_delwri_submit_nowait+0x20/0x30 [xfs] > Mar 5 13:10:36 xxxxxxx kernel: [94304.727195] [] ? xfs_trans_ail_cursor_first+0x81/0xb0 [xfs] > Mar 5 13:10:36 xxxxxxx kernel: [94304.727209] [] xfs_buf_delwri_submit_nowait+0x20/0x30 [xfs] > Mar 5 13:10:36 xxxxxxx kernel: [94304.727227] [] xfsaild+0x221/0x5d0 [xfs] > Mar 5 13:10:36 xxxxxxx kernel: [94304.727246] [] ? xfs_trans_ail_cursor_first+0xb0/0xb0 [xfs] > Mar 5 13:10:36 xxxxxxx kernel: [94304.727251] [] kthread+0xc0/0xd0 > Mar 5 13:10:36 xxxxxxx kernel: [94304.727256] [] ? ftrace_define_fields_xen_mc_entry+0xa0/0xf0 > Mar 5 13:10:36 xxxxxxx kernel: [94304.727258] [] ? kthread_create_on_node+0x120/0x120 > Mar 5 13:10:36 xxxxxxx kernel: [94304.727262] [] ret_from_fork+0x7c/0xb0 > Mar 5 13:10:36 xxxxxxx kernel: [94304.727265] [] ? kthread_create_on_node+0x120/0x120 > Mar 5 13:10:36 xxxxxxx kernel: [94304.727267] XFS (loop0): Corruption detected. Unmount and run xfs_repair > Mar 5 13:10:36 xxxxxxx kernel: [94304.727270] XFS (loop0): xfs_do_force_shutdown(0x8) called from line 1358 of file fs/xfs/xfs_buf.c. Return address = 0xffffffffa002f441 > Mar 5 13:10:37 xxxxxxx kernel: [94304.982635] XFS (loop0): Corruption of in-memory data detected. Shutting down filesystem > Mar 5 13:10:37 xxxxxxx kernel: [94304.982642] XFS (loop0): Please umount the filesystem and rectify the problem(s) > Mar 5 13:10:37 xxxxxxx kernel: [94305.036039] XFS (loop0): xfs_log_force: error 5 returned. > Mar 5 13:10:37 xxxxxxx kernel: [94305.087970] Buffer I/O error on device loop0, logical block 90997607 > Mar 5 13:10:37 xxxxxxx kernel: [94305.087975] lost page write due to I/O error on loop0 > Mar 5 13:10:37 xxxxxxx kernel: [94305.087980] Buffer I/O error on device loop0, logical block 90997608 > Mar 5 13:10:37 xxxxxxx kernel: [94305.087981] lost page write due to I/O error on loop0 > Mar 5 13:10:37 xxxxxxx kernel: [94305.087983] Buffer I/O error on device loop0, logical block 90997609 > Mar 5 13:10:37 xxxxxxx kernel: [94305.087984] lost page write due to I/O error on loop0 > Mar 5 13:10:37 xxxxxxx kernel: [94305.087986] Buffer I/O error on device loop0, logical block 90997610 > Mar 5 13:10:37 xxxxxxx kernel: [94305.087988] lost page write due to I/O error on loop0 > Mar 5 13:10:37 xxxxxxx kernel: [94305.087990] Buffer I/O error on device loop0, logical block 90997611 > Mar 5 13:10:37 xxxxxxx kernel: [94305.087991] lost page write due to I/O error on loop0 > Mar 5 13:10:37 xxxxxxx kernel: [94305.087993] Buffer I/O error on device loop0, logical block 90997612 > Mar 5 13:10:37 xxxxxxx kernel: [94305.087994] lost page write due to I/O error on loop0 > Mar 5 13:10:37 xxxxxxx kernel: [94305.087996] Buffer I/O error on device loop0, logical block 90997613 > Mar 5 13:10:37 xxxxxxx kernel: [94305.087997] lost page write due to I/O error on loop0 > Mar 5 13:10:37 xxxxxxx kernel: [94305.087999] Buffer I/O error on device loop0, logical block 90997614 > Mar 5 13:10:37 xxxxxxx kernel: [94305.088018] lost page write due to I/O error on loop0 > Mar 5 13:10:37 xxxxxxx kernel: [94305.088020] Buffer I/O error on device loop0, logical block 90997615 > Mar 5 13:10:37 xxxxxxx kernel: [94305.088021] lost page write due to I/O error on loop0 > Mar 5 13:10:37 xxxxxxx kernel: [94305.088023] Buffer I/O error on device loop0, logical block 90997616 > Mar 5 13:10:37 xxxxxxx kernel: [94305.088025] lost page write due to I/O error on loop0 > > Umount /home: > > Mar 5 13:11:06 xxxxxxx kernel: [94334.816017] XFS (loop0): xfs_log_force: error 5 returned. > Mar 5 13:11:37 xxxxxxx kernel: [94364.896026] XFS (loop0): xfs_log_force: error 5 returned. > Mar 5 13:12:07 xxxxxxx kernel: [94394.976025] XFS (loop0): xfs_log_force: error 5 returned. > Mar 5 13:12:08 xxxxxxx kernel: [94396.397569] XFS (loop0): xfs_log_force: error 5 returned. > Mar 5 13:12:08 xxxxxxx kernel: [94396.798331] XFS (loop0): xfs_log_force: error 5 returned. > Mar 5 13:12:08 xxxxxxx kernel: [94396.803897] XFS (loop0): xfs_log_force: error 5 returned. > > Mount /home: > > Mar 5 13:12:36 xxxxxxx kernel: [94424.276817] XFS (loop0): Mounting Filesystem > Mar 5 13:12:36 xxxxxxx kernel: [94424.444206] XFS (loop0): Starting recovery (logdev: internal) > Mar 5 13:12:36 xxxxxxx kernel: [94424.454409] XFS (loop0): log record CRC mismatch: found 0xe8dc0331, expected 0xb8afb9f5. > Mar 5 13:12:36 xxxxxxx kernel: [94424.454409] > Mar 5 13:12:36 xxxxxxx kernel: [94424.454427] ffffc90014440000: 00 00 00 01 00 00 00 00 69 01 00 00 4f 3e 05 16 ........i...O>.. > Mar 5 13:12:36 xxxxxxx kernel: [94424.454434] ffffc90014440010: 00 00 00 10 69 00 00 00 4e 41 52 54 2a 00 00 00 ....i...NART*... > Mar 5 13:12:36 xxxxxxx kernel: [94424.457657] XFS (loop0): log record CRC mismatch: found 0xca3729fa, expected 0x936285f8. > Mar 5 13:12:36 xxxxxxx kernel: [94424.457657] > Mar 5 13:12:36 xxxxxxx kernel: [94424.457677] ffffc90014440000: 00 00 00 01 00 00 00 48 69 18 00 00 00 00 00 00 .......Hi....... > Mar 5 13:12:36 xxxxxxx kernel: [94424.457685] ffffc90014440010: 00 00 00 00 3e d2 35 51 d3 4c a5 05 3e d2 35 51 ....>.5Q.L..>.5Q > Mar 5 13:12:36 xxxxxxx kernel: [94424.459325] XFS (loop0): log record CRC mismatch: found 0x82df5071, expected 0x147787f2. > Mar 5 13:12:36 xxxxxxx kernel: [94424.459325] > Mar 5 13:12:36 xxxxxxx kernel: [94424.459343] ffffc90014440000: 00 00 00 01 00 00 00 00 69 01 00 00 b6 da 4d 37 ........i.....M7 > Mar 5 13:12:36 xxxxxxx kernel: [94424.459351] ffffc90014440010: 00 00 00 10 69 00 00 00 4e 41 52 54 2a 00 00 00 ....i...NART*... > Mar 5 13:12:36 xxxxxxx kernel: [94424.459825] XFS (loop0): log record CRC mismatch: found 0x81d60a0c, expected 0xa36fc6cf. > Mar 5 13:12:36 xxxxxxx kernel: [94424.459825] > Mar 5 13:12:36 xxxxxxx kernel: [94424.459836] ffffc90014440000: 00 00 00 01 00 00 00 00 69 01 00 00 a0 58 d2 ca ........i....X.. > Mar 5 13:12:36 xxxxxxx kernel: [94424.459842] ffffc90014440010: 00 00 00 10 69 00 00 00 4e 41 52 54 2a 00 00 00 ....i...NART*... > Mar 5 13:12:36 xxxxxxx kernel: [94424.460452] XFS (loop0): log record CRC mismatch: found 0xd5e688af, expected 0x32f0716d. > Mar 5 13:12:36 xxxxxxx kernel: [94424.460452] > Mar 5 13:12:36 xxxxxxx kernel: [94424.460466] ffffc90014440000: 00 00 00 01 00 00 00 00 69 01 00 00 7d a4 99 70 ........i...}..p > Mar 5 13:12:36 xxxxxxx kernel: [94424.460473] ffffc90014440010: 00 00 00 10 69 00 00 00 4e 41 52 54 2a 00 00 00 ....i...NART*... > Mar 5 13:12:36 xxxxxxx kernel: [94424.460904] XFS (loop0): log record CRC mismatch: found 0xaa2ac0a7, expected 0x94620a44. > Mar 5 13:12:36 xxxxxxx kernel: [94424.460904] > Mar 5 13:12:36 xxxxxxx kernel: [94424.460915] ffffc90014440000: 00 00 00 01 00 00 00 00 69 01 00 00 43 53 3a 4f ........i...CS:O > Mar 5 13:12:36 xxxxxxx kernel: [94424.460921] ffffc90014440010: 00 00 00 10 69 00 00 00 4e 41 52 54 2a 00 00 00 ....i...NART*... > Mar 5 13:12:36 xxxxxxx kernel: [94424.474642] XFS (loop0): log record CRC mismatch: found 0x924e1723, expected 0x89c0a34b. > Mar 5 13:12:36 xxxxxxx kernel: [94424.474642] > Mar 5 13:12:36 xxxxxxx kernel: [94424.474661] ffffc90014440000: 00 00 00 01 00 00 00 00 69 01 00 00 05 3b b5 68 ........i....;.h > Mar 5 13:12:36 xxxxxxx kernel: [94424.474668] ffffc90014440010: 00 00 00 10 69 00 00 00 4e 41 52 54 2a 00 00 00 ....i...NART*... > Mar 5 13:12:36 xxxxxxx kernel: [94424.475512] XFS (loop0): log record CRC mismatch: found 0x1b8a4eb7, expected 0xa9b341a6. > Mar 5 13:12:36 xxxxxxx kernel: [94424.475512] > Mar 5 13:12:36 xxxxxxx kernel: [94424.475529] ffffc90014440000: 00 00 00 01 00 00 00 00 69 01 00 00 1b e8 ad f5 ........i....... > Mar 5 13:12:36 xxxxxxx kernel: [94424.475536] ffffc90014440010: 00 00 00 10 69 00 00 00 4e 41 52 54 2a 00 00 00 ....i...NART*... > Mar 5 13:12:36 xxxxxxx kernel: [94424.478164] XFS (loop0): log record CRC mismatch: found 0xe7aaf329, expected 0x62577a0d. > Mar 5 13:12:36 xxxxxxx kernel: [94424.478164] > Mar 5 13:12:36 xxxxxxx kernel: [94424.478181] ffffc90014440000: 00 00 00 01 00 00 00 00 69 01 00 00 5f 1b ed 49 ........i..._..I > Mar 5 13:12:36 xxxxxxx kernel: [94424.478190] ffffc90014440010: 00 00 00 10 69 00 00 00 4e 41 52 54 2a 00 00 00 ....i...NART*... > Mar 5 13:12:36 xxxxxxx kernel: [94424.478869] XFS (loop0): log record CRC mismatch: found 0x8b024d5d, expected 0xa6ddb6cf. > Mar 5 13:12:36 xxxxxxx kernel: [94424.478869] > Mar 5 13:12:36 xxxxxxx kernel: [94424.479208] ffffc90014440000: 00 00 00 01 00 00 00 00 69 01 00 00 b1 f5 1e 94 ........i....... > Mar 5 13:12:36 xxxxxxx kernel: [94424.480501] ffffc90014440010: 00 00 00 10 69 00 00 00 4e 41 52 54 2a 00 00 00 ....i...NART*... > Mar 5 13:12:36 xxxxxxx kernel: [94424.489048] XFS (loop0): log record CRC mismatch: found 0xe8dc0331, expected 0xb8afb9f5. > Mar 5 13:12:36 xxxxxxx kernel: [94424.489048] > Mar 5 13:12:36 xxxxxxx kernel: [94424.490737] ffffc90014480000: 00 00 00 01 00 00 00 00 69 01 00 00 4f 3e 05 16 ........i...O>.. > Mar 5 13:12:36 xxxxxxx kernel: [94424.492209] ffffc90014480010: 00 00 00 10 69 00 00 00 4e 41 52 54 2a 00 00 00 ....i...NART*... > Mar 5 13:12:36 xxxxxxx kernel: [94424.496938] XFS (loop0): log record CRC mismatch: found 0xca3729fa, expected 0x936285f8. > Mar 5 13:12:36 xxxxxxx kernel: [94424.496938] > Mar 5 13:12:36 xxxxxxx kernel: [94424.498729] ffffc90014480000: 00 00 00 01 00 00 00 48 69 18 00 00 00 00 00 00 .......Hi....... > Mar 5 13:12:36 xxxxxxx kernel: [94424.500298] ffffc90014480010: 00 00 00 00 3e d2 35 51 d3 4c a5 05 3e d2 35 51 ....>.5Q.L..>.5Q > Mar 5 13:12:37 xxxxxxx kernel: [94425.029493] XFS (loop0): log record CRC mismatch: found 0x82df5071, expected 0x147787f2. > Mar 5 13:12:37 xxxxxxx kernel: [94425.029493] > Mar 5 13:12:37 xxxxxxx kernel: [94425.031376] ffffc90014480000: 00 00 00 01 00 00 00 00 69 01 00 00 b6 da 4d 37 ........i.....M7 > Mar 5 13:12:37 xxxxxxx kernel: [94425.032938] ffffc90014480010: 00 00 00 10 69 00 00 00 4e 41 52 54 2a 00 00 00 ....i...NART*... > Mar 5 13:12:37 xxxxxxx kernel: [94425.069605] XFS (loop0): log record CRC mismatch: found 0x81d60a0c, expected 0xa36fc6cf. > Mar 5 13:12:37 xxxxxxx kernel: [94425.069605] > Mar 5 13:12:37 xxxxxxx kernel: [94425.071520] ffffc90014480000: 00 00 00 01 00 00 00 00 69 01 00 00 a0 58 d2 ca ........i....X.. > Mar 5 13:12:37 xxxxxxx kernel: [94425.073183] ffffc90014480010: 00 00 00 10 69 00 00 00 4e 41 52 54 2a 00 00 00 ....i...NART*... > Mar 5 13:12:37 xxxxxxx kernel: [94425.082249] XFS (loop0): log record CRC mismatch: found 0xd5e688af, expected 0x32f0716d. > Mar 5 13:12:37 xxxxxxx kernel: [94425.082249] > Mar 5 13:12:37 xxxxxxx kernel: [94425.084292] ffffc90014480000: 00 00 00 01 00 00 00 00 69 01 00 00 7d a4 99 70 ........i...}..p > Mar 5 13:12:37 xxxxxxx kernel: [94425.085947] ffffc90014480010: 00 00 00 10 69 00 00 00 4e 41 52 54 2a 00 00 00 ....i...NART*... > Mar 5 13:12:37 xxxxxxx kernel: [94425.092165] XFS (loop0): log record CRC mismatch: found 0xaa2ac0a7, expected 0x94620a44. > Mar 5 13:12:37 xxxxxxx kernel: [94425.092165] > Mar 5 13:12:37 xxxxxxx kernel: [94425.094305] ffffc90014480000: 00 00 00 01 00 00 00 00 69 01 00 00 43 53 3a 4f ........i...CS:O > Mar 5 13:12:37 xxxxxxx kernel: [94425.096037] ffffc90014480010: 00 00 00 10 69 00 00 00 4e 41 52 54 2a 00 00 00 ....i...NART*... > Mar 5 13:12:37 xxxxxxx kernel: [94425.111936] XFS (loop0): log record CRC mismatch: found 0x924e1723, expected 0x89c0a34b. > Mar 5 13:12:37 xxxxxxx kernel: [94425.111936] > Mar 5 13:12:37 xxxxxxx kernel: [94425.114115] ffffc90014480000: 00 00 00 01 00 00 00 00 69 01 00 00 05 3b b5 68 ........i....;.h > Mar 5 13:12:37 xxxxxxx kernel: [94425.115816] ffffc90014480010: 00 00 00 10 69 00 00 00 4e 41 52 54 2a 00 00 00 ....i...NART*... > Mar 5 13:12:37 xxxxxxx kernel: [94425.527549] XFS (loop0): log record CRC mismatch: found 0x1b8a4eb7, expected 0xa9b341a6. > Mar 5 13:12:37 xxxxxxx kernel: [94425.527549] > Mar 5 13:12:37 xxxxxxx kernel: [94425.529738] ffffc90014480000: 00 00 00 01 00 00 00 00 69 01 00 00 1b e8 ad f5 ........i....... > Mar 5 13:12:37 xxxxxxx kernel: [94425.531521] ffffc90014480010: 00 00 00 10 69 00 00 00 4e 41 52 54 2a 00 00 00 ....i...NART*... > Mar 5 13:12:37 xxxxxxx kernel: [94425.539719] XFS (loop0): log record CRC mismatch: found 0xe7aaf329, expected 0x62577a0d. > Mar 5 13:12:37 xxxxxxx kernel: [94425.539719] > Mar 5 13:12:37 xxxxxxx kernel: [94425.541902] ffffc90014480000: 00 00 00 01 00 00 00 00 69 01 00 00 5f 1b ed 49 ........i..._..I > Mar 5 13:12:37 xxxxxxx kernel: [94425.543659] ffffc90014480010: 00 00 00 10 69 00 00 00 4e 41 52 54 2a 00 00 00 ....i...NART*... > Mar 5 13:12:38 xxxxxxx kernel: [94425.890080] XFS (loop0): log record CRC mismatch: found 0x8b024d5d, expected 0xa6ddb6cf. > Mar 5 13:12:38 xxxxxxx kernel: [94425.890080] > Mar 5 13:12:38 xxxxxxx kernel: [94425.892186] ffffc90014480000: 00 00 00 01 00 00 00 00 69 01 00 00 b1 f5 1e 94 ........i....... > Mar 5 13:12:38 xxxxxxx kernel: [94425.893932] ffffc90014480010: 00 00 00 10 69 00 00 00 4e 41 52 54 2a 00 00 00 ....i...NART*... > Mar 5 13:12:38 xxxxxxx kernel: [94425.911651] XFS (loop0): Ending recovery (logdev: internal) > > Umount, xfs_repair, mount. > > Reboot with 3.7.9 (x86_64) > - full resync for whole directory tree (196Gb): no problems > - kernel re-compilation: no problems > > Seems to be related to kernel tree directory: > > Mar 5 12:50:21 xxxxxxx kernel: [93088.912705] ffff88010e1bf000: 2f 68 6f 6d 65 2f 67 61 62 72 69 65 6c 2f 77 6f /home/gabriel/wo > > I think the actual directory is /home/gabriel/work/rpm/BUILD/kernel-3.8.f18g/ ... > > Is there any way I can debug this? > > > Additional info: > * kernel: 3.8.1 (x86_64) > * xfs_repair version: 3.1.10 > * 1 cpu > > # cat /proc/mounts | grep xfs | grep ^/dev > /dev/sda2 / xfs rw,seclabel,relatime,attr2,inode64,noquota 0 0 > /dev/sdc1 /saves xfs rw,seclabel,nosuid,nodev,relatime,attr2,inode64,logbufs=8,logbsize=256k,noquota 0 0 > /dev/sdb1 /export xfs rw,seclabel,nosuid,nodev,relatime,attr2,inode64,logbufs=8,logbsize=256k,noquota 0 0 > /dev/loop6 /tmp xfs rw,seclabel,nosuid,nodev,noexec,relatime,attr2,inode64,noquota 0 0 > /dev/loop6 /var/tmp xfs rw,seclabel,nosuid,nodev,noexec,relatime,attr2,inode64,noquota 0 0 > /dev/loop0 /home xfs rw,seclabel,nosuid,nodev,relatime,attr2,inode64,logbufs=8,logbsize=256k,noquota 0 0 > > # cat /proc/partitions > major minor #blocks name > > 8 0 488386584 sda > 8 1 512000 sda1 > 8 2 20971520 sda2 > 8 3 2097152 sda3 > 8 4 1 sda4 > 8 5 462707712 sda5 > 8 6 2095104 sda6 > 11 0 1048575 sr0 > 8 32 312571224 sdc > 8 33 312570200 sdc1 > 8 16 156290904 sdb > 8 17 156289880 sdb1 > 7 0 462707704 loop0 > 7 6 2095104 loop6 > 7 7 2097148 loop7 > > # xfs_info /home > meta-data=/dev/loop0 isize=256 agcount=4, agsize=28919232 blks > = sectsz=512 attr=2 > data = bsize=4096 blocks=115676926, imaxpct=25 > = sunit=0 swidth=0 blks > naming =version 2 bsize=4096 ascii-ci=0 > log =internal bsize=4096 blocks=56482, version=2 > = sectsz=512 sunit=0 blks, lazy-count=1 > realtime =none extsz=4096 blocks=0, rtextents=0 > > > Sincerely, > Gabriel > > - -- > > // Gabriel VLASIU > // > // OpenGPG-KeyID : 44952F15 > // OpenGPG-Fingerprint: 4AC5 7C26 2FE9 02DA 4906 24B2 D32B 7ED7 4495 2F15 > // OpenGPG-URL : http://www.vlasiu.net/public.key > > > -----BEGIN PGP SIGNATURE----- > Version: GnuPG v1.4.13 (GNU/Linux) > > iQIcBAEBCgAGBQJRNe1sAAoJENMrftdElS8Vrt8QALOWM3Gzph6TDWkGwcqyxTos > o6X0jXfJxEn+pYdcMWh+h8x8poxfLFNxCn4yVqO5WdX4xqYq23BYO1VR0qqFueTT > dNerqxQcvKn+HRi+hsME/GabDjI5RInvotZ2QVWjuqWk72F2qlIVnmvQtCXOm1lX > 6Mkf18b0+voCgZG6eYHSftbRxc+Jme2lPl5fbUcGDeiANkkZbq0+YrfAp6u9KEOu > CX5Pzss7oSDqTCVzy0X85Xw9f1txKEdjPbzZkMcTLFmVgB7zc/muViEmEiLljGjS > DLtoONDoHU6cVTkfr7Uzjuv49vwSKNL/5qrtX05+GidUOAKQqGs90FR3wgMC9SHR > Vo5RSbNVOEeRUkbhWa2mBemscD6teNujBnVkvVsWeeA9qdf4F5CldshfCdZocLhe > Zy8qD/ZmoVJTgEzv5iksd4WzkpVnT5Vz0w59ETW3SkvIdceGwEFCE3PUS19Yb6Gr > /OWj8bna+QtgtrEijbwdOPDDx6JrXXcYTtJk7m2R0LMRC3GymPeOiJSbrxFe8XTn > s6o4QGZQczPkwL/+wQIDiijAQxBn/t9tRC36iunIA7hXRzmYhtgj9s6iXTmiLLJk > NkdZ9jlg82RFenXaDDOMMdki2tgEmGZGpYDH81V/Nfi4VHDBjM0ZIjP0/2wWoUnA > 9GYY2qWSGY3MNw28hlu9 > =RjjN > -----END PGP SIGNATURE----- > > _______________________________________________ > xfs mailing list > xfs@oss.sgi.com > http://oss.sgi.com/mailman/listinfo/xfs From gabriel@vlasiu.net Tue Mar 5 09:46:58 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=T_DKIM_INVALID autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id BC5F47F63 for ; Tue, 5 Mar 2013 09:46:58 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay3.corp.sgi.com (Postfix) with ESMTP id 5BC6DAC007 for ; Tue, 5 Mar 2013 07:46:55 -0800 (PST) X-ASG-Debug-ID: 1362498412-04bdf022961cc540001-NocioJ Received: from mail.vlasiu.net (mail.vlasiu.net [91.223.50.125]) by cuda.sgi.com with ESMTP id 91wYeCEFseuAWUDM (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO) for ; Tue, 05 Mar 2013 07:46:54 -0800 (PST) X-Barracuda-Envelope-From: gabriel@vlasiu.net X-Barracuda-Apparent-Source-IP: 91.223.50.125 Received: from localhost (localhost [127.0.0.1]) by mail.vlasiu.net (Postfix) with ESMTP id 43DEE7E07F; Tue, 5 Mar 2013 17:46:52 +0200 (EET) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=vlasiu.net; h= content-type:content-type:mime-version:user-agent:references :message-id:in-reply-to:subject:subject:from:from:date:date :received:received:received; s=default; t=1362498408; x= 1362502009; bh=G2BJuRyQpIk+h8xZTcSXzfkh4sOV7KDpcIPGAUJG1Dw=; b=z 6C7nYkCSz1XB7BkiCzs0MtHXehQulpefGGtJeRxyBK4iwAu3HPcePWUYYnQH3n9c xDcz9WiD+S9521NcoRG08OOSmS1BZUvFWZ5Ew4ROFgQfEJjgi5+DWFWqX9yFpEiG 1CXgu67ux0hhrLjCY2lJY3mTrpfsBEa5FXtHdFacxY= X-Virus-Scanned: amavisd-new at vlasiu.net Received: from mail.vlasiu.net ([127.0.0.1]) by localhost (mail.vlasiu.net [127.0.0.1]) (amavisd-new, port 10026) with LMTP id RyUOQlZDGA4m; Tue, 5 Mar 2013 17:46:48 +0200 (EET) Received: by mail.vlasiu.net (Postfix, from userid 500) id ACEB87E083; Tue, 5 Mar 2013 17:46:48 +0200 (EET) Received: from localhost (localhost [127.0.0.1]) by mail.vlasiu.net (Postfix) with ESMTP id 873937E07F; Tue, 5 Mar 2013 17:46:48 +0200 (EET) Date: Tue, 5 Mar 2013 17:46:42 +0200 (EET) From: Gabriel VLASIU To: Ben Myers cc: xfs@oss.sgi.com Subject: Re: xfs with kernel 3.8.1 In-Reply-To: <20130305154325.GJ22182@sgi.com> X-ASG-Orig-Subj: Re: xfs with kernel 3.8.1 Message-ID: References: <20130305154325.GJ22182@sgi.com> User-Agent: Alpine 2.02 (LRH 1266 2009-07-14) X-OpenGPG-KeyID: 44952F15 X-OpenGPG-Fingerprint: 4AC5 7C26 2FE9 02DA 4906 24B2 D32B 7ED7 4495 2F15 X-OpenGPG-URL: http://www.vlasiu.net/public.key MIME-Version: 1.0 Content-Type: TEXT/PLAIN; charset=US-ASCII X-Barracuda-Connect: mail.vlasiu.net[91.223.50.125] X-Barracuda-Start-Time: 1362498413 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=DKIM_SIGNED, DKIM_VERIFIED X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124331 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature -----BEGIN PGP SIGNED MESSAGE----- Hash: SHA512 Hi! On Tue, 5 Mar 2013, Ben Myers wrote: > This is fixed in 3.8.2, by > > commit 2cd182d6f0f > > xfs: xfs_bmap_add_attrfork_local is too generic > commit 1e82379b018ceed0f0912327c60d73107dacbcb3 upstream. Thank you! Sincerely, Gabriel - -- // Gabriel VLASIU // // OpenGPG-KeyID : 44952F15 // OpenGPG-Fingerprint: 4AC5 7C26 2FE9 02DA 4906 24B2 D32B 7ED7 4495 2F15 // OpenGPG-URL : http://www.vlasiu.net/public.key -----BEGIN PGP SIGNATURE----- Version: GnuPG v1.4.13 (GNU/Linux) iQIcBAEBCgAGBQJRNhNiAAoJENMrftdElS8VbeMP/Rl1IpHc9WmqxVN8FwnsyD+0 JJfeR1cJXnl7Yl+ATw3yaM7p2v1te6mPwevaltRGQFHpRc8XiGkkEBIYRVaqjU+x P3OA+N0R4/N1mykDa+xGSGPjq0i4crKJtHXSyFhIJvty/HwildejyNkN/NdOsM8r gRhBvESu0z4pSivIpRR6JghS1DRvpAM6l2DcWJuHibznOgW8CXxda4Ly3v74GXZM wpEsDWUdUeow59duaTf6vc9K6Oxhiybw00wify/+xYEgg5ESjQ/XoyVigd2NR1sT d9xd8Z8IxLlHEJPFAyZn/pa8AfuEWjmUVwm9BMnFt7qWmIPFzjv60dBzpssHlVFY bt7sStqAdXpeODh5AVcxvpI2Muij4oxCPZ0x5nIm8FHpChXWDjorgTYkHp0a2RZn qTu70jGUniM8NZo244XgqO/3LLCMh5S7T8Sg3GW+oOG+AvDD63I+AOe4LH3e1sJC 7+uG/2uuvTSUvLLQZcoSvUPvQm2p26i9WZ7OEJ++v6NcH9JD9jCgTvfroDEt0RWO R6ulSG9msJnKK4olIzBLuaJRTFcPXieJQFXQWpxniEzWg08NpBPNEDySLK1+7Q/N KJr0BRsH/EDgt1p0VqGkmlg4+BzHdZhkwFkYHIqyH0FEGsnbbthaqbafsp70mMkf L2OmqQYJK60JJ8U7vinB =aQa3 -----END PGP SIGNATURE----- From rjohnston@sgi.com Tue Mar 5 09:58:08 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id DF8A07FD3 for ; Tue, 5 Mar 2013 09:58:08 -0600 (CST) Received: from xmail.sgi.com (pv-excas3-dc21-nlb.corp.sgi.com [137.38.102.207]) by relay1.corp.sgi.com (Postfix) with ESMTP id 9D8558F8033; Tue, 5 Mar 2013 07:58:08 -0800 (PST) Received: from [128.162.233.55] (128.162.233.55) by xmail.sgi.com (137.38.102.30) with Microsoft SMTP Server (TLS) id 14.2.318.1; Tue, 5 Mar 2013 09:55:30 -0600 Message-ID: <5136157C.5080404@sgi.com> Date: Tue, 5 Mar 2013 09:55:40 -0600 From: Rich Johnston User-Agent: Mozilla/5.0 (X11; Linux i686; rv:13.0) Gecko/20120615 Thunderbird/13.0.1 MIME-Version: 1.0 To: Eric Sandeen CC: Zheng Liu , , Zheng Liu , Subject: Re: [PATCH v2] xfstests: use right defrag program path References: <1362147433-5788-1-git-send-email-wenqing.lz@taobao.com> <5130CDC1.8060704@redhat.com> In-Reply-To: <5130CDC1.8060704@redhat.com> Content-Type: text/plain; charset="ISO-8859-1"; format=flowed Content-Transfer-Encoding: 7bit X-Originating-IP: [128.162.233.55] This patch has been committed. commit 08557e219c12e573be459407033495899f46967a Author: Zheng Liu Date: Fri Mar 1 14:17:13 2013 +0000 xfstests: use right defrag program path In _require_defrag defragmentation command path is fixed. That will cause that this test case is skipped in some distributions. Signed-off-by: Zheng Liu Reviewed-by: Eric Sandeen Signed-off-by: Rich Johnston From bpm@oss.sgi.com Tue Mar 5 10:01:24 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=-0.0 required=5.0 tests=NO_RELAYS autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: by oss.sgi.com (Postfix, from userid 46323) id ECE63803B; Tue, 5 Mar 2013 10:01:23 -0600 (CST) From: xfs@oss.sgi.com To: xfs@oss.sgi.com Subject: [XFS updates] XFS development tree branch, master, updated. for-linus-v3.9-rc1-12693-g6dbe51c X-Git-Refname: refs/heads/master X-Git-Reftype: branch X-Git-Oldrev: 1e82379b018ceed0f0912327c60d73107dacbcb3 X-Git-Newrev: 6dbe51c251a327e012439c4772097a13df43c5b8 Message-Id: <20130305160123.ECE63803B@oss.sgi.com> Date: Tue, 5 Mar 2013 10:01:22 -0600 (CST) This is an automated email from the git hooks/post-receive script. It was generated because a ref change was pushed to the repository containing the project "XFS development tree". The branch, master has been updated b67bfe0 hlist: drop the node parameter from iterators d895cb1 Merge branch 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/viro/vfs 94e07a75 fs: encode_fh: return FILEID_INVALID if invalid fid_type 496ad9a new helper: file_inode(file) 06991c2 Merge tag 'driver-core-3.9-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/driver-core 65e3aa7 xfs: Fix xfs_swap_extents() after removal of xfs_flushinval_pages() 4b05d09 xfs: Fix possible use-after-free with AIO 9f87832 xfs: fix shutdown hang on invalid inode during create f2a4595 xfs: limit speculative prealloc near ENOSPC thresholds eb17861 xfs: fix _xfs_buf_find oops on blocks beyond the filesystem end d26978d xfs: pull up stack_switch check into xfs_bmapi_write 1bee12b xfs: Do not return EFSCORRUPTED when filesystem probe finds no XFS magic ed408f7 Merge 3.9-rc4 into driver-core-next 37f1356 xfs: recalculate leaf entry pointer after compacting a dir2 block ab7eac2 xfs: remove int casts from debug dquot soft limit timer asserts 91e4bac xfs: fix the multi-segment log buffer format 2d0e9df xfs: fix segment in xfs_buf_item_format_segment 0f22f9d xfs: rename bli_format to avoid confusion with bli_formats d44d9bc xfs: use b_maps[] for discontiguous buffers d9777b8 fs/xfs: remove depends on CONFIG_EXPERIMENTAL from 1e82379b018ceed0f0912327c60d73107dacbcb3 (commit) Those revisions listed above that are new to this repository have not appeared on any other notification email; so we list those revisions in full, below. - Log ----------------------------------------------------------------- commit b67bfe0d42cac56c512dd5da4b1b347a23f4b70a Author: Sasha Levin Date: Wed Feb 27 17:06:00 2013 -0800 hlist: drop the node parameter from iterators I'm not sure why, but the hlist for each entry iterators were conceived list_for_each_entry(pos, head, member) The hlist ones were greedy and wanted an extra parameter: hlist_for_each_entry(tpos, pos, head, member) Why did they need an extra pos parameter? I'm not quite sure. Not only they don't really need it, it also prevents the iterator from looking exactly like the list iterator, which is unfortunate. Besides the semantic patch, there was some manual work required: - Fix up the actual hlist iterators in linux/list.h - Fix up the declaration of other iterators based on the hlist ones. - A very small amount of places were using the 'node' parameter, this was modified to use 'obj->member' instead. - Coccinelle didn't handle the hlist_for_each_entry_safe iterator properly, so those had to be fixed up manually. The semantic patch which is mostly the work of Peter Senna Tschudin is here: @@ iterator name hlist_for_each_entry, hlist_for_each_entry_continue, hlist_for_each_entry_from, hlist_for_each_entry_rcu, hlist_for_each_entry_rcu_bh, hlist_for_each_entry_continue_rcu_bh, for_each_busy_worker, ax25_uid_for_each, ax25_for_each, inet_bind_bucket_for_each, sctp_for_each_hentry, sk_for_each, sk_for_each_rcu, sk_for_each_from, sk_for_each_safe, sk_for_each_bound, hlist_for_each_entry_safe, hlist_for_each_entry_continue_rcu, nr_neigh_for_each, nr_neigh_for_each_safe, nr_node_for_each, nr_node_for_each_safe, for_each_gfn_indirect_valid_sp, for_each_gfn_sp, for_each_host; type T; expression a,c,d,e; identifier b; statement S; @@ -T b; <+... when != b ( hlist_for_each_entry(a, - b, c, d) S | hlist_for_each_entry_continue(a, - b, c) S | hlist_for_each_entry_from(a, - b, c) S | hlist_for_each_entry_rcu(a, - b, c, d) S | hlist_for_each_entry_rcu_bh(a, - b, c, d) S | hlist_for_each_entry_continue_rcu_bh(a, - b, c) S | for_each_busy_worker(a, c, - b, d) S | ax25_uid_for_each(a, - b, c) S | ax25_for_each(a, - b, c) S | inet_bind_bucket_for_each(a, - b, c) S | sctp_for_each_hentry(a, - b, c) S | sk_for_each(a, - b, c) S | sk_for_each_rcu(a, - b, c) S | sk_for_each_from -(a, b) +(a) S + sk_for_each_from(a) S | sk_for_each_safe(a, - b, c, d) S | sk_for_each_bound(a, - b, c) S | hlist_for_each_entry_safe(a, - b, c, d, e) S | hlist_for_each_entry_continue_rcu(a, - b, c) S | nr_neigh_for_each(a, - b, c) S | nr_neigh_for_each_safe(a, - b, c, d) S | nr_node_for_each(a, - b, c) S | nr_node_for_each_safe(a, - b, c, d) S | - for_each_gfn_sp(a, c, d, b) S + for_each_gfn_sp(a, c, d) S | - for_each_gfn_indirect_valid_sp(a, c, d, b) S + for_each_gfn_indirect_valid_sp(a, c, d) S | for_each_host(a, - b, c) S | for_each_host_safe(a, - b, c, d) S | for_each_mesh_entry(a, - b, c, d) S ) ...+> [akpm@linux-foundation.org: drop bogus change from net/ipv4/raw.c] [akpm@linux-foundation.org: drop bogus hunk from net/ipv6/raw.c] [akpm@linux-foundation.org: checkpatch fixes] [akpm@linux-foundation.org: fix warnings] [akpm@linux-foudnation.org: redo intrusive kvm changes] Tested-by: Peter Senna Tschudin Acked-by: Paul E. McKenney Signed-off-by: Sasha Levin Cc: Wu Fengguang Cc: Marcelo Tosatti Cc: Gleb Natapov Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds commit d895cb1af15c04c522a25c79cc429076987c089b Merge: 9626357 d3d009c Author: Linus Torvalds Date: Tue Feb 26 20:16:07 2013 -0800 Merge branch 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/viro/vfs Pull vfs pile (part one) from Al Viro: "Assorted stuff - cleaning namei.c up a bit, fixing ->d_name/->d_parent locking violations, etc. The most visible changes here are death of FS_REVAL_DOT (replaced with "has ->d_weak_revalidate()") and a new helper getting from struct file to inode. Some bits of preparation to xattr method interface changes. Misc patches by various people sent this cycle *and* ocfs2 fixes from several cycles ago that should've been upstream right then. PS: the next vfs pile will be xattr stuff." * 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/viro/vfs: (46 commits) saner proc_get_inode() calling conventions proc: avoid extra pde_put() in proc_fill_super() fs: change return values from -EACCES to -EPERM fs/exec.c: make bprm_mm_init() static ocfs2/dlm: use GFP_ATOMIC inside a spin_lock ocfs2: fix possible use-after-free with AIO ocfs2: Fix oops in ocfs2_fast_symlink_readpage() code path get_empty_filp()/alloc_file() leave both ->f_pos and ->f_version zero target: writev() on single-element vector is pointless export kernel_write(), convert open-coded instances fs: encode_fh: return FILEID_INVALID if invalid fid_type kill f_vfsmnt vfs: kill FS_REVAL_DOT by adding a d_weak_revalidate dentry op nfsd: handle vfs_getattr errors in acl protocol switch vfs_getattr() to struct path default SET_PERSONALITY() in linux/elf.h ceph: prepopulate inodes only when request is aborted d_hash_and_lookup(): export, switch open-coded instances 9p: switch v9fs_set_create_acl() to inode+fid, do it before d_instantiate() 9p: split dropping the acls from v9fs_set_create_acl() ... commit 94e07a7590ae855bae0536c42b3086fadc7c83a8 Author: Namjae Jeon Date: Sun Feb 17 15:48:11 2013 +0900 fs: encode_fh: return FILEID_INVALID if invalid fid_type This patch is a follow up on below patch: [PATCH] exportfs: add FILEID_INVALID to indicate invalid fid_type commit: 216b6cbdcbd86b1db0754d58886b466ae31f5a63 Signed-off-by: Namjae Jeon Signed-off-by: Vivek Trivedi Acked-by: Steven Whitehouse Acked-by: Sage Weil Signed-off-by: Al Viro commit 496ad9aa8ef448058e36ca7a787c61f2e63f0f54 Author: Al Viro Date: Wed Jan 23 17:07:38 2013 -0500 new helper: file_inode(file) Signed-off-by: Al Viro commit 06991c28f37ad68e5c03777f5c3b679b56e3dac1 Merge: 460dc1e 74fef7a Author: Linus Torvalds Date: Thu Feb 21 12:05:51 2013 -0800 Merge tag 'driver-core-3.9-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/driver-core Pull driver core patches from Greg Kroah-Hartman: "Here is the big driver core merge for 3.9-rc1 There are two major series here, both of which touch lots of drivers all over the kernel, and will cause you some merge conflicts: - add a new function called devm_ioremap_resource() to properly be able to check return values. - remove CONFIG_EXPERIMENTAL Other than those patches, there's not much here, some minor fixes and updates" Fix up trivial conflicts * tag 'driver-core-3.9-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/driver-core: (221 commits) base: memory: fix soft/hard_offline_page permissions drivercore: Fix ordering between deferred_probe and exiting initcalls backlight: fix class_find_device() arguments TTY: mark tty_get_device call with the proper const values driver-core: constify data for class_find_device() firmware: Ignore abort check when no user-helper is used firmware: Reduce ifdef CONFIG_FW_LOADER_USER_HELPER firmware: Make user-mode helper optional firmware: Refactoring for splitting user-mode helper code Driver core: treat unregistered bus_types as having no devices watchdog: Convert to devm_ioremap_resource() thermal: Convert to devm_ioremap_resource() spi: Convert to devm_ioremap_resource() power: Convert to devm_ioremap_resource() mtd: Convert to devm_ioremap_resource() mmc: Convert to devm_ioremap_resource() mfd: Convert to devm_ioremap_resource() media: Convert to devm_ioremap_resource() iommu: Convert to devm_ioremap_resource() drm: Convert to devm_ioremap_resource() ... commit 65e3aa77f1b0269720660a6879f6f28d158f54c8 Author: Torsten Kaiser Date: Sun Jan 20 10:24:49 2013 +0100 xfs: Fix xfs_swap_extents() after removal of xfs_flushinval_pages() Commit fb59581404ab7ec5075299065c22cb211a9262a9 removed xfs_flushinval_pages() and changed its callers to use filemap_write_and_wait() and truncate_pagecache_range() directly. But in xfs_swap_extents() this change accidental switched the argument for 'tip' to 'ip'. This patch switches it back to 'tip' Signed-off-by: Torsten Kaiser Reviewed-by: Ben Myers Signed-off-by: Ben Myers commit 4b05d09c18d9aa62d2e7fb4b057f54e5a38963f5 Author: Jan Kara Date: Wed Jan 23 13:56:18 2013 +0100 xfs: Fix possible use-after-free with AIO Running AIO is pinning inode in memory using file reference. Once AIO is completed using aio_complete(), file reference is put and inode can be freed from memory. So we have to be sure that calling aio_complete() is the last thing we do with the inode. CC: xfs@oss.sgi.com CC: Ben Myers CC: stable@vger.kernel.org Signed-off-by: Jan Kara Reviewed-by: Ben Myers Signed-off-by: Ben Myers commit 9f87832a82923943aaab38b8d53658af134bbfa4 Author: Dave Chinner Date: Mon Jan 21 23:53:55 2013 +1100 xfs: fix shutdown hang on invalid inode during create When the new inode verify in xfs_iread() fails, the create transaction is aborted and a shutdown occurs. The subsequent unmount then hangs in xfs_wait_buftarg() on a buffer that has an elevated hold count. Debug showed that it was an AGI buffer getting stuck: [ 22.576147] XFS (vdb): buffer 0x2/0x1, hold 0x2 stuck [ 22.976213] XFS (vdb): buffer 0x2/0x1, hold 0x2 stuck [ 23.376206] XFS (vdb): buffer 0x2/0x1, hold 0x2 stuck [ 23.776325] XFS (vdb): buffer 0x2/0x1, hold 0x2 stuck The trace of this buffer leading up to the shutdown (trimmed for brevity) looks like: xfs_buf_init: bno 0x2 nblks 0x1 hold 1 caller xfs_buf_get_map xfs_buf_get: bno 0x2 len 0x200 hold 1 caller xfs_buf_read_map xfs_buf_read: bno 0x2 len 0x200 hold 1 caller xfs_trans_read_buf_map xfs_buf_iorequest: bno 0x2 nblks 0x1 hold 1 caller _xfs_buf_read xfs_buf_hold: bno 0x2 nblks 0x1 hold 1 caller xfs_buf_iorequest xfs_buf_rele: bno 0x2 nblks 0x1 hold 2 caller xfs_buf_iorequest xfs_buf_iowait: bno 0x2 nblks 0x1 hold 1 caller _xfs_buf_read xfs_buf_ioerror: bno 0x2 len 0x200 hold 1 caller xfs_buf_bio_end_io xfs_buf_iodone: bno 0x2 nblks 0x1 hold 1 caller _xfs_buf_ioend xfs_buf_iowait_done: bno 0x2 nblks 0x1 hold 1 caller _xfs_buf_read xfs_buf_hold: bno 0x2 nblks 0x1 hold 1 caller xfs_buf_item_init xfs_trans_read_buf: bno 0x2 len 0x200 hold 2 recur 0 refcount 1 xfs_trans_brelse: bno 0x2 len 0x200 hold 2 recur 0 refcount 1 xfs_buf_item_relse: bno 0x2 nblks 0x1 hold 2 caller xfs_trans_brelse xfs_buf_rele: bno 0x2 nblks 0x1 hold 2 caller xfs_buf_item_relse xfs_buf_unlock: bno 0x2 nblks 0x1 hold 1 caller xfs_trans_brelse xfs_buf_rele: bno 0x2 nblks 0x1 hold 1 caller xfs_trans_brelse xfs_buf_trylock: bno 0x2 nblks 0x1 hold 2 caller _xfs_buf_find xfs_buf_find: bno 0x2 len 0x200 hold 2 caller xfs_buf_get_map xfs_buf_get: bno 0x2 len 0x200 hold 2 caller xfs_buf_read_map xfs_buf_read: bno 0x2 len 0x200 hold 2 caller xfs_trans_read_buf_map xfs_buf_hold: bno 0x2 nblks 0x1 hold 2 caller xfs_buf_item_init xfs_trans_read_buf: bno 0x2 len 0x200 hold 3 recur 0 refcount 1 xfs_trans_log_buf: bno 0x2 len 0x200 hold 3 recur 0 refcount 1 xfs_buf_item_unlock: bno 0x2 len 0x200 hold 3 flags DIRTY liflags ABORTED xfs_buf_unlock: bno 0x2 nblks 0x1 hold 3 caller xfs_buf_item_unlock xfs_buf_rele: bno 0x2 nblks 0x1 hold 3 caller xfs_buf_item_unlock And that is the AGI buffer from cold cache read into memory to transaction abort. You can see at transaction abort the bli is dirty and only has a single reference. The item is not pinned, and it's not in the AIL. Hence the only reference to it is this transaction. The problem is that the xfs_buf_item_unlock() call is dropping the last reference to the xfs_buf_log_item attached to the buffer (which holds a reference to the buffer), but it is not freeing the xfs_buf_log_item. Hence nothing will ever release the buffer, and the unmount hangs waiting for this reference to go away. The fix is simple - xfs_buf_item_unlock needs to detect the last reference going away in this case and free the xfs_buf_log_item to release the reference it holds on the buffer. Signed-off-by: Dave Chinner Reviewed-by: Ben Myers Signed-off-by: Ben Myers commit f2a459565b02b60408f3f2e5ca992a031319712b Author: Dave Chinner Date: Mon Jan 21 23:53:54 2013 +1100 xfs: limit speculative prealloc near ENOSPC thresholds There is a window on small filesytsems where specualtive preallocation can be larger than that ENOSPC throttling thresholds, resulting in specualtive preallocation trying to reserve more space than there is space available. This causes immediate ENOSPC to be triggered, prealloc to be turned off and flushing to occur. One the next write (i.e. next 4k page), we do exactly the same thing, and so effective drive into synchronous 4k writes by triggering ENOSPC flushing on every page while in the window between the prealloc size and the ENOSPC prealloc throttle threshold. Fix this by checking to see if the prealloc size would consume all free space, and throttle it appropriately to avoid premature ENOSPC... Signed-off-by: Dave Chinner Reviewed-by: Brian Foster Signed-off-by: Ben Myers commit eb178619f930fa2ba2348de332a1ff1c66a31424 Author: Dave Chinner Date: Mon Jan 21 23:53:52 2013 +1100 xfs: fix _xfs_buf_find oops on blocks beyond the filesystem end When _xfs_buf_find is passed an out of range address, it will fail to find a relevant struct xfs_perag and oops with a null dereference. This can happen when trying to walk a filesystem with a metadata inode that has a partially corrupted extent map (i.e. the block number returned is corrupt, but is otherwise intact) and we try to read from the corrupted block address. In this case, just fail the lookup. If it is readahead being issued, it will simply not be done, but if it is real read that fails we will get an error being reported. Ideally this case should result in an EFSCORRUPTED error being reported, but we cannot return an error through xfs_buf_read() or xfs_buf_get() so this lookup failure may result in ENOMEM or EIO errors being reported instead. Signed-off-by: Dave Chinner Reviewed-by: Brian Foster Reviewed-by: Ben Myers Signed-off-by: Ben Myers commit d26978dd866dbb3b3a9690f3655a5e735055de89 Author: Brian Foster Date: Thu Jan 17 13:11:29 2013 -0500 xfs: pull up stack_switch check into xfs_bmapi_write The stack_switch check currently occurs in __xfs_bmapi_allocate, which means the stack switch only occurs when xfs_bmapi_allocate() is called in a loop. Pull the check up before the loop in xfs_bmapi_write() such that the first iteration of the loop has consistent behavior. Signed-off-by: Brian Foster Reviewed-by: Dave Chinner Signed-off-by: Ben Myers commit 1bee12b8c44d825fb45cd6a13e76c185ed6888b8 Author: Eric Sandeen Date: Wed Jan 16 17:33:53 2013 -0600 xfs: Do not return EFSCORRUPTED when filesystem probe finds no XFS magic 9802182 changed the return value from EWRONGFS (aka EINVAL) to EFSCORRUPTED which doesn't seem to be handled properly by the root filesystem probe. Signed-off-by: Eric Sandeen Tested-by: Sergei Trofimovich Reviewed-by: Ben Myers Signed-off-by: Ben Myers commit ed408f7c0fab7ecc72f94f204f0d2607b2749f69 Merge: 52f7a82 7d1f9ae Author: Greg Kroah-Hartman Date: Thu Jan 17 19:48:18 2013 -0800 Merge 3.9-rc4 into driver-core-next This is to fix up a build problem with a wireless driver due to the dynamic-debug patches in this branch. Signed-off-by: Greg Kroah-Hartman commit 37f13561de6039b3a916d1510086030d097dea0f Author: Eric Sandeen Date: Thu Jan 10 10:41:48 2013 -0600 xfs: recalculate leaf entry pointer after compacting a dir2 block Dave Jones hit this assert when doing a compile on recent git, with CONFIG_XFS_DEBUG enabled: XFS: Assertion failed: (char *)dup - (char *)hdr == be16_to_cpu(*xfs_dir2_data_unused_tag_p(dup)), file: fs/xfs/xfs_dir2_data.c, line: 828 Upon further digging, the tag found by xfs_dir2_data_unused_tag_p(dup) contained "2" and not the proper offset, and I found that this value was changed after the memmoves under "Use a stale leaf for our new entry." in xfs_dir2_block_addname(), i.e. memmove(&blp[mid + 1], &blp[mid], (highstale - mid) * sizeof(*blp)); overwrote it. What has happened is that the previous call to xfs_dir2_block_compact() has rearranged things; it changes btp->count as well as the blp array. So after we make that call, we must recalculate the proper pointer to the leaf entries by making another call to xfs_dir2_block_leaf_p(). Dave provided a metadump image which led to a simple reproducer (create a particular filename in the affected directory) and this resolves the testcase as well as the bug on his live system. Thanks also to dchinner for looking at this one with me. Signed-off-by: Eric Sandeen Tested-by: Dave Jones Reviewed-by: Dave Chinner Reviewed-by: Mark Tinguely Signed-off-by: Ben Myers commit ab7eac22008f044631c0a3f4be344ebc2cb0e266 Author: Brian Foster Date: Fri Dec 21 10:45:17 2012 -0500 xfs: remove int casts from debug dquot soft limit timer asserts The int casts here make it easy to trigger an assert with a large soft limit. For example, set a >4TB soft limit on an empty volume to reproduce a (0 > -x) comparison due to an overflow of d_blk_softlimit. Signed-off-by: Brian Foster Reviewed-by: Ben Myers Signed-off-by: Ben Myers commit 91e4bac0b72736410c88632906953f14259144b1 Author: Mark Tinguely Date: Tue Dec 4 17:18:05 2012 -0600 xfs: fix the multi-segment log buffer format Per Dave Chinner suggestion, this patch: 1) Corrects the detection of whether a multi-segment buffer is still tracking data. 2) Clears all the buffer log formats for a multi-segment buffer. Signed-off-by: Mark Tinguely Reviewed-by: Christoph Hellwig Reviewed-by: Dave Chinner Signed-off-by: Ben Myers commit 2d0e9df579029b62adc72b50977182757cc04cd5 Author: Mark Tinguely Date: Tue Dec 4 17:18:04 2012 -0600 xfs: fix segment in xfs_buf_item_format_segment Not every segment in a multi-segment buffer is dirty in a transaction and they will not be outputted. The assert in xfs_buf_item_format_segment() that checks for the at least one chunk of data in the segment to be used is not necessary true for multi-segmented buffers. Signed-off-by: Mark Tinguely Reviewed-by: Dave Chinner Signed-off-by: Ben Myers commit 0f22f9d0cd8a630b40a9ccc07a8844345b185aae Author: Mark Tinguely Date: Tue Dec 4 17:18:03 2012 -0600 xfs: rename bli_format to avoid confusion with bli_formats Rename the bli_format structure to __bli_format to avoid accidently confusing them with the bli_formats pointer. Signed-off-by: Mark Tinguely Reviewed-by: Christoph Hellwig Reviewed-by: Dave Chinner Signed-off-by: Ben Myers commit d44d9bc68e32ad5881b105f82bd259d261d1ef74 Author: Mark Tinguely Date: Tue Dec 4 17:18:02 2012 -0600 xfs: use b_maps[] for discontiguous buffers Commits starting at 77c1a08 introduced a multiple segment support to xfs_buf. xfs_trans_buf_item_match() could not find a multi-segment buffer in the transaction because it was looking at the single segment block number rather than the multi-segment b_maps[0].bm.bn. This results on a recursive buffer lock that can never be satisfied. This patch: 1) Changed the remaining b_map accesses to be b_maps[0] accesses. 2) Renames the single segment b_map structure to __b_map to avoid future confusion. Signed-off-by: Mark Tinguely Reviewed-by: Dave Chinner Reviewed-by: Christoph Hellwig Signed-off-by: Ben Myers commit d9777b8de415f2e699dcc4ce8825732ba8af732a Author: Kees Cook Date: Tue Oct 2 11:19:27 2012 -0700 fs/xfs: remove depends on CONFIG_EXPERIMENTAL The CONFIG_EXPERIMENTAL config item has not carried much meaning for a while now and is almost always enabled by default. As agreed during the Linux kernel summit, remove it from any "depends on" lines in Kconfigs. CC: Ben Myers CC: Alex Elder Signed-off-by: Kees Cook Acked-by: Ben Myers ----------------------------------------------------------------------- Summary of changes: fs/xfs/Kconfig | 4 ++-- fs/xfs/xfs_dfrag.c | 8 ++++---- fs/xfs/xfs_export.c | 4 ++-- fs/xfs/xfs_file.c | 4 ++-- fs/xfs/xfs_ioctl.c | 6 +++--- fs/xfs/xfs_ioctl32.c | 2 +- fs/xfs/xfs_log_recover.c | 3 +-- 7 files changed, 15 insertions(+), 16 deletions(-) hooks/post-receive -- XFS development tree From bpm@oss.sgi.com Tue Mar 5 10:02:24 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=-0.0 required=5.0 tests=NO_RELAYS autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: by oss.sgi.com (Postfix, from userid 46323) id 1579B8046; Tue, 5 Mar 2013 10:02:24 -0600 (CST) From: xfs@oss.sgi.com To: xfs@oss.sgi.com Subject: [XFS updates] XFS development tree branch, for-next, updated. for-linus-v3.9-rc1-12693-g6dbe51c X-Git-Refname: refs/heads/for-next X-Git-Reftype: branch X-Git-Oldrev: 1e82379b018ceed0f0912327c60d73107dacbcb3 X-Git-Newrev: 6dbe51c251a327e012439c4772097a13df43c5b8 Message-Id: <20130305160224.1579B8046@oss.sgi.com> Date: Tue, 5 Mar 2013 10:02:23 -0600 (CST) This is an automated email from the git hooks/post-receive script. It was generated because a ref change was pushed to the repository containing the project "XFS development tree". The branch, for-next has been updated b67bfe0 hlist: drop the node parameter from iterators d895cb1 Merge branch 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/viro/vfs 94e07a75 fs: encode_fh: return FILEID_INVALID if invalid fid_type 496ad9a new helper: file_inode(file) 06991c2 Merge tag 'driver-core-3.9-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/driver-core 65e3aa7 xfs: Fix xfs_swap_extents() after removal of xfs_flushinval_pages() 4b05d09 xfs: Fix possible use-after-free with AIO 9f87832 xfs: fix shutdown hang on invalid inode during create f2a4595 xfs: limit speculative prealloc near ENOSPC thresholds eb17861 xfs: fix _xfs_buf_find oops on blocks beyond the filesystem end d26978d xfs: pull up stack_switch check into xfs_bmapi_write 1bee12b xfs: Do not return EFSCORRUPTED when filesystem probe finds no XFS magic ed408f7 Merge 3.9-rc4 into driver-core-next 37f1356 xfs: recalculate leaf entry pointer after compacting a dir2 block ab7eac2 xfs: remove int casts from debug dquot soft limit timer asserts 91e4bac xfs: fix the multi-segment log buffer format 2d0e9df xfs: fix segment in xfs_buf_item_format_segment 0f22f9d xfs: rename bli_format to avoid confusion with bli_formats d44d9bc xfs: use b_maps[] for discontiguous buffers d9777b8 fs/xfs: remove depends on CONFIG_EXPERIMENTAL from 1e82379b018ceed0f0912327c60d73107dacbcb3 (commit) Those revisions listed above that are new to this repository have not appeared on any other notification email; so we list those revisions in full, below. - Log ----------------------------------------------------------------- commit b67bfe0d42cac56c512dd5da4b1b347a23f4b70a Author: Sasha Levin Date: Wed Feb 27 17:06:00 2013 -0800 hlist: drop the node parameter from iterators I'm not sure why, but the hlist for each entry iterators were conceived list_for_each_entry(pos, head, member) The hlist ones were greedy and wanted an extra parameter: hlist_for_each_entry(tpos, pos, head, member) Why did they need an extra pos parameter? I'm not quite sure. Not only they don't really need it, it also prevents the iterator from looking exactly like the list iterator, which is unfortunate. Besides the semantic patch, there was some manual work required: - Fix up the actual hlist iterators in linux/list.h - Fix up the declaration of other iterators based on the hlist ones. - A very small amount of places were using the 'node' parameter, this was modified to use 'obj->member' instead. - Coccinelle didn't handle the hlist_for_each_entry_safe iterator properly, so those had to be fixed up manually. The semantic patch which is mostly the work of Peter Senna Tschudin is here: @@ iterator name hlist_for_each_entry, hlist_for_each_entry_continue, hlist_for_each_entry_from, hlist_for_each_entry_rcu, hlist_for_each_entry_rcu_bh, hlist_for_each_entry_continue_rcu_bh, for_each_busy_worker, ax25_uid_for_each, ax25_for_each, inet_bind_bucket_for_each, sctp_for_each_hentry, sk_for_each, sk_for_each_rcu, sk_for_each_from, sk_for_each_safe, sk_for_each_bound, hlist_for_each_entry_safe, hlist_for_each_entry_continue_rcu, nr_neigh_for_each, nr_neigh_for_each_safe, nr_node_for_each, nr_node_for_each_safe, for_each_gfn_indirect_valid_sp, for_each_gfn_sp, for_each_host; type T; expression a,c,d,e; identifier b; statement S; @@ -T b; <+... when != b ( hlist_for_each_entry(a, - b, c, d) S | hlist_for_each_entry_continue(a, - b, c) S | hlist_for_each_entry_from(a, - b, c) S | hlist_for_each_entry_rcu(a, - b, c, d) S | hlist_for_each_entry_rcu_bh(a, - b, c, d) S | hlist_for_each_entry_continue_rcu_bh(a, - b, c) S | for_each_busy_worker(a, c, - b, d) S | ax25_uid_for_each(a, - b, c) S | ax25_for_each(a, - b, c) S | inet_bind_bucket_for_each(a, - b, c) S | sctp_for_each_hentry(a, - b, c) S | sk_for_each(a, - b, c) S | sk_for_each_rcu(a, - b, c) S | sk_for_each_from -(a, b) +(a) S + sk_for_each_from(a) S | sk_for_each_safe(a, - b, c, d) S | sk_for_each_bound(a, - b, c) S | hlist_for_each_entry_safe(a, - b, c, d, e) S | hlist_for_each_entry_continue_rcu(a, - b, c) S | nr_neigh_for_each(a, - b, c) S | nr_neigh_for_each_safe(a, - b, c, d) S | nr_node_for_each(a, - b, c) S | nr_node_for_each_safe(a, - b, c, d) S | - for_each_gfn_sp(a, c, d, b) S + for_each_gfn_sp(a, c, d) S | - for_each_gfn_indirect_valid_sp(a, c, d, b) S + for_each_gfn_indirect_valid_sp(a, c, d) S | for_each_host(a, - b, c) S | for_each_host_safe(a, - b, c, d) S | for_each_mesh_entry(a, - b, c, d) S ) ...+> [akpm@linux-foundation.org: drop bogus change from net/ipv4/raw.c] [akpm@linux-foundation.org: drop bogus hunk from net/ipv6/raw.c] [akpm@linux-foundation.org: checkpatch fixes] [akpm@linux-foundation.org: fix warnings] [akpm@linux-foudnation.org: redo intrusive kvm changes] Tested-by: Peter Senna Tschudin Acked-by: Paul E. McKenney Signed-off-by: Sasha Levin Cc: Wu Fengguang Cc: Marcelo Tosatti Cc: Gleb Natapov Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds commit d895cb1af15c04c522a25c79cc429076987c089b Merge: 9626357 d3d009c Author: Linus Torvalds Date: Tue Feb 26 20:16:07 2013 -0800 Merge branch 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/viro/vfs Pull vfs pile (part one) from Al Viro: "Assorted stuff - cleaning namei.c up a bit, fixing ->d_name/->d_parent locking violations, etc. The most visible changes here are death of FS_REVAL_DOT (replaced with "has ->d_weak_revalidate()") and a new helper getting from struct file to inode. Some bits of preparation to xattr method interface changes. Misc patches by various people sent this cycle *and* ocfs2 fixes from several cycles ago that should've been upstream right then. PS: the next vfs pile will be xattr stuff." * 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/viro/vfs: (46 commits) saner proc_get_inode() calling conventions proc: avoid extra pde_put() in proc_fill_super() fs: change return values from -EACCES to -EPERM fs/exec.c: make bprm_mm_init() static ocfs2/dlm: use GFP_ATOMIC inside a spin_lock ocfs2: fix possible use-after-free with AIO ocfs2: Fix oops in ocfs2_fast_symlink_readpage() code path get_empty_filp()/alloc_file() leave both ->f_pos and ->f_version zero target: writev() on single-element vector is pointless export kernel_write(), convert open-coded instances fs: encode_fh: return FILEID_INVALID if invalid fid_type kill f_vfsmnt vfs: kill FS_REVAL_DOT by adding a d_weak_revalidate dentry op nfsd: handle vfs_getattr errors in acl protocol switch vfs_getattr() to struct path default SET_PERSONALITY() in linux/elf.h ceph: prepopulate inodes only when request is aborted d_hash_and_lookup(): export, switch open-coded instances 9p: switch v9fs_set_create_acl() to inode+fid, do it before d_instantiate() 9p: split dropping the acls from v9fs_set_create_acl() ... commit 94e07a7590ae855bae0536c42b3086fadc7c83a8 Author: Namjae Jeon Date: Sun Feb 17 15:48:11 2013 +0900 fs: encode_fh: return FILEID_INVALID if invalid fid_type This patch is a follow up on below patch: [PATCH] exportfs: add FILEID_INVALID to indicate invalid fid_type commit: 216b6cbdcbd86b1db0754d58886b466ae31f5a63 Signed-off-by: Namjae Jeon Signed-off-by: Vivek Trivedi Acked-by: Steven Whitehouse Acked-by: Sage Weil Signed-off-by: Al Viro commit 496ad9aa8ef448058e36ca7a787c61f2e63f0f54 Author: Al Viro Date: Wed Jan 23 17:07:38 2013 -0500 new helper: file_inode(file) Signed-off-by: Al Viro commit 06991c28f37ad68e5c03777f5c3b679b56e3dac1 Merge: 460dc1e 74fef7a Author: Linus Torvalds Date: Thu Feb 21 12:05:51 2013 -0800 Merge tag 'driver-core-3.9-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/driver-core Pull driver core patches from Greg Kroah-Hartman: "Here is the big driver core merge for 3.9-rc1 There are two major series here, both of which touch lots of drivers all over the kernel, and will cause you some merge conflicts: - add a new function called devm_ioremap_resource() to properly be able to check return values. - remove CONFIG_EXPERIMENTAL Other than those patches, there's not much here, some minor fixes and updates" Fix up trivial conflicts * tag 'driver-core-3.9-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/driver-core: (221 commits) base: memory: fix soft/hard_offline_page permissions drivercore: Fix ordering between deferred_probe and exiting initcalls backlight: fix class_find_device() arguments TTY: mark tty_get_device call with the proper const values driver-core: constify data for class_find_device() firmware: Ignore abort check when no user-helper is used firmware: Reduce ifdef CONFIG_FW_LOADER_USER_HELPER firmware: Make user-mode helper optional firmware: Refactoring for splitting user-mode helper code Driver core: treat unregistered bus_types as having no devices watchdog: Convert to devm_ioremap_resource() thermal: Convert to devm_ioremap_resource() spi: Convert to devm_ioremap_resource() power: Convert to devm_ioremap_resource() mtd: Convert to devm_ioremap_resource() mmc: Convert to devm_ioremap_resource() mfd: Convert to devm_ioremap_resource() media: Convert to devm_ioremap_resource() iommu: Convert to devm_ioremap_resource() drm: Convert to devm_ioremap_resource() ... commit 65e3aa77f1b0269720660a6879f6f28d158f54c8 Author: Torsten Kaiser Date: Sun Jan 20 10:24:49 2013 +0100 xfs: Fix xfs_swap_extents() after removal of xfs_flushinval_pages() Commit fb59581404ab7ec5075299065c22cb211a9262a9 removed xfs_flushinval_pages() and changed its callers to use filemap_write_and_wait() and truncate_pagecache_range() directly. But in xfs_swap_extents() this change accidental switched the argument for 'tip' to 'ip'. This patch switches it back to 'tip' Signed-off-by: Torsten Kaiser Reviewed-by: Ben Myers Signed-off-by: Ben Myers commit 4b05d09c18d9aa62d2e7fb4b057f54e5a38963f5 Author: Jan Kara Date: Wed Jan 23 13:56:18 2013 +0100 xfs: Fix possible use-after-free with AIO Running AIO is pinning inode in memory using file reference. Once AIO is completed using aio_complete(), file reference is put and inode can be freed from memory. So we have to be sure that calling aio_complete() is the last thing we do with the inode. CC: xfs@oss.sgi.com CC: Ben Myers CC: stable@vger.kernel.org Signed-off-by: Jan Kara Reviewed-by: Ben Myers Signed-off-by: Ben Myers commit 9f87832a82923943aaab38b8d53658af134bbfa4 Author: Dave Chinner Date: Mon Jan 21 23:53:55 2013 +1100 xfs: fix shutdown hang on invalid inode during create When the new inode verify in xfs_iread() fails, the create transaction is aborted and a shutdown occurs. The subsequent unmount then hangs in xfs_wait_buftarg() on a buffer that has an elevated hold count. Debug showed that it was an AGI buffer getting stuck: [ 22.576147] XFS (vdb): buffer 0x2/0x1, hold 0x2 stuck [ 22.976213] XFS (vdb): buffer 0x2/0x1, hold 0x2 stuck [ 23.376206] XFS (vdb): buffer 0x2/0x1, hold 0x2 stuck [ 23.776325] XFS (vdb): buffer 0x2/0x1, hold 0x2 stuck The trace of this buffer leading up to the shutdown (trimmed for brevity) looks like: xfs_buf_init: bno 0x2 nblks 0x1 hold 1 caller xfs_buf_get_map xfs_buf_get: bno 0x2 len 0x200 hold 1 caller xfs_buf_read_map xfs_buf_read: bno 0x2 len 0x200 hold 1 caller xfs_trans_read_buf_map xfs_buf_iorequest: bno 0x2 nblks 0x1 hold 1 caller _xfs_buf_read xfs_buf_hold: bno 0x2 nblks 0x1 hold 1 caller xfs_buf_iorequest xfs_buf_rele: bno 0x2 nblks 0x1 hold 2 caller xfs_buf_iorequest xfs_buf_iowait: bno 0x2 nblks 0x1 hold 1 caller _xfs_buf_read xfs_buf_ioerror: bno 0x2 len 0x200 hold 1 caller xfs_buf_bio_end_io xfs_buf_iodone: bno 0x2 nblks 0x1 hold 1 caller _xfs_buf_ioend xfs_buf_iowait_done: bno 0x2 nblks 0x1 hold 1 caller _xfs_buf_read xfs_buf_hold: bno 0x2 nblks 0x1 hold 1 caller xfs_buf_item_init xfs_trans_read_buf: bno 0x2 len 0x200 hold 2 recur 0 refcount 1 xfs_trans_brelse: bno 0x2 len 0x200 hold 2 recur 0 refcount 1 xfs_buf_item_relse: bno 0x2 nblks 0x1 hold 2 caller xfs_trans_brelse xfs_buf_rele: bno 0x2 nblks 0x1 hold 2 caller xfs_buf_item_relse xfs_buf_unlock: bno 0x2 nblks 0x1 hold 1 caller xfs_trans_brelse xfs_buf_rele: bno 0x2 nblks 0x1 hold 1 caller xfs_trans_brelse xfs_buf_trylock: bno 0x2 nblks 0x1 hold 2 caller _xfs_buf_find xfs_buf_find: bno 0x2 len 0x200 hold 2 caller xfs_buf_get_map xfs_buf_get: bno 0x2 len 0x200 hold 2 caller xfs_buf_read_map xfs_buf_read: bno 0x2 len 0x200 hold 2 caller xfs_trans_read_buf_map xfs_buf_hold: bno 0x2 nblks 0x1 hold 2 caller xfs_buf_item_init xfs_trans_read_buf: bno 0x2 len 0x200 hold 3 recur 0 refcount 1 xfs_trans_log_buf: bno 0x2 len 0x200 hold 3 recur 0 refcount 1 xfs_buf_item_unlock: bno 0x2 len 0x200 hold 3 flags DIRTY liflags ABORTED xfs_buf_unlock: bno 0x2 nblks 0x1 hold 3 caller xfs_buf_item_unlock xfs_buf_rele: bno 0x2 nblks 0x1 hold 3 caller xfs_buf_item_unlock And that is the AGI buffer from cold cache read into memory to transaction abort. You can see at transaction abort the bli is dirty and only has a single reference. The item is not pinned, and it's not in the AIL. Hence the only reference to it is this transaction. The problem is that the xfs_buf_item_unlock() call is dropping the last reference to the xfs_buf_log_item attached to the buffer (which holds a reference to the buffer), but it is not freeing the xfs_buf_log_item. Hence nothing will ever release the buffer, and the unmount hangs waiting for this reference to go away. The fix is simple - xfs_buf_item_unlock needs to detect the last reference going away in this case and free the xfs_buf_log_item to release the reference it holds on the buffer. Signed-off-by: Dave Chinner Reviewed-by: Ben Myers Signed-off-by: Ben Myers commit f2a459565b02b60408f3f2e5ca992a031319712b Author: Dave Chinner Date: Mon Jan 21 23:53:54 2013 +1100 xfs: limit speculative prealloc near ENOSPC thresholds There is a window on small filesytsems where specualtive preallocation can be larger than that ENOSPC throttling thresholds, resulting in specualtive preallocation trying to reserve more space than there is space available. This causes immediate ENOSPC to be triggered, prealloc to be turned off and flushing to occur. One the next write (i.e. next 4k page), we do exactly the same thing, and so effective drive into synchronous 4k writes by triggering ENOSPC flushing on every page while in the window between the prealloc size and the ENOSPC prealloc throttle threshold. Fix this by checking to see if the prealloc size would consume all free space, and throttle it appropriately to avoid premature ENOSPC... Signed-off-by: Dave Chinner Reviewed-by: Brian Foster Signed-off-by: Ben Myers commit eb178619f930fa2ba2348de332a1ff1c66a31424 Author: Dave Chinner Date: Mon Jan 21 23:53:52 2013 +1100 xfs: fix _xfs_buf_find oops on blocks beyond the filesystem end When _xfs_buf_find is passed an out of range address, it will fail to find a relevant struct xfs_perag and oops with a null dereference. This can happen when trying to walk a filesystem with a metadata inode that has a partially corrupted extent map (i.e. the block number returned is corrupt, but is otherwise intact) and we try to read from the corrupted block address. In this case, just fail the lookup. If it is readahead being issued, it will simply not be done, but if it is real read that fails we will get an error being reported. Ideally this case should result in an EFSCORRUPTED error being reported, but we cannot return an error through xfs_buf_read() or xfs_buf_get() so this lookup failure may result in ENOMEM or EIO errors being reported instead. Signed-off-by: Dave Chinner Reviewed-by: Brian Foster Reviewed-by: Ben Myers Signed-off-by: Ben Myers commit d26978dd866dbb3b3a9690f3655a5e735055de89 Author: Brian Foster Date: Thu Jan 17 13:11:29 2013 -0500 xfs: pull up stack_switch check into xfs_bmapi_write The stack_switch check currently occurs in __xfs_bmapi_allocate, which means the stack switch only occurs when xfs_bmapi_allocate() is called in a loop. Pull the check up before the loop in xfs_bmapi_write() such that the first iteration of the loop has consistent behavior. Signed-off-by: Brian Foster Reviewed-by: Dave Chinner Signed-off-by: Ben Myers commit 1bee12b8c44d825fb45cd6a13e76c185ed6888b8 Author: Eric Sandeen Date: Wed Jan 16 17:33:53 2013 -0600 xfs: Do not return EFSCORRUPTED when filesystem probe finds no XFS magic 9802182 changed the return value from EWRONGFS (aka EINVAL) to EFSCORRUPTED which doesn't seem to be handled properly by the root filesystem probe. Signed-off-by: Eric Sandeen Tested-by: Sergei Trofimovich Reviewed-by: Ben Myers Signed-off-by: Ben Myers commit ed408f7c0fab7ecc72f94f204f0d2607b2749f69 Merge: 52f7a82 7d1f9ae Author: Greg Kroah-Hartman Date: Thu Jan 17 19:48:18 2013 -0800 Merge 3.9-rc4 into driver-core-next This is to fix up a build problem with a wireless driver due to the dynamic-debug patches in this branch. Signed-off-by: Greg Kroah-Hartman commit 37f13561de6039b3a916d1510086030d097dea0f Author: Eric Sandeen Date: Thu Jan 10 10:41:48 2013 -0600 xfs: recalculate leaf entry pointer after compacting a dir2 block Dave Jones hit this assert when doing a compile on recent git, with CONFIG_XFS_DEBUG enabled: XFS: Assertion failed: (char *)dup - (char *)hdr == be16_to_cpu(*xfs_dir2_data_unused_tag_p(dup)), file: fs/xfs/xfs_dir2_data.c, line: 828 Upon further digging, the tag found by xfs_dir2_data_unused_tag_p(dup) contained "2" and not the proper offset, and I found that this value was changed after the memmoves under "Use a stale leaf for our new entry." in xfs_dir2_block_addname(), i.e. memmove(&blp[mid + 1], &blp[mid], (highstale - mid) * sizeof(*blp)); overwrote it. What has happened is that the previous call to xfs_dir2_block_compact() has rearranged things; it changes btp->count as well as the blp array. So after we make that call, we must recalculate the proper pointer to the leaf entries by making another call to xfs_dir2_block_leaf_p(). Dave provided a metadump image which led to a simple reproducer (create a particular filename in the affected directory) and this resolves the testcase as well as the bug on his live system. Thanks also to dchinner for looking at this one with me. Signed-off-by: Eric Sandeen Tested-by: Dave Jones Reviewed-by: Dave Chinner Reviewed-by: Mark Tinguely Signed-off-by: Ben Myers commit ab7eac22008f044631c0a3f4be344ebc2cb0e266 Author: Brian Foster Date: Fri Dec 21 10:45:17 2012 -0500 xfs: remove int casts from debug dquot soft limit timer asserts The int casts here make it easy to trigger an assert with a large soft limit. For example, set a >4TB soft limit on an empty volume to reproduce a (0 > -x) comparison due to an overflow of d_blk_softlimit. Signed-off-by: Brian Foster Reviewed-by: Ben Myers Signed-off-by: Ben Myers commit 91e4bac0b72736410c88632906953f14259144b1 Author: Mark Tinguely Date: Tue Dec 4 17:18:05 2012 -0600 xfs: fix the multi-segment log buffer format Per Dave Chinner suggestion, this patch: 1) Corrects the detection of whether a multi-segment buffer is still tracking data. 2) Clears all the buffer log formats for a multi-segment buffer. Signed-off-by: Mark Tinguely Reviewed-by: Christoph Hellwig Reviewed-by: Dave Chinner Signed-off-by: Ben Myers commit 2d0e9df579029b62adc72b50977182757cc04cd5 Author: Mark Tinguely Date: Tue Dec 4 17:18:04 2012 -0600 xfs: fix segment in xfs_buf_item_format_segment Not every segment in a multi-segment buffer is dirty in a transaction and they will not be outputted. The assert in xfs_buf_item_format_segment() that checks for the at least one chunk of data in the segment to be used is not necessary true for multi-segmented buffers. Signed-off-by: Mark Tinguely Reviewed-by: Dave Chinner Signed-off-by: Ben Myers commit 0f22f9d0cd8a630b40a9ccc07a8844345b185aae Author: Mark Tinguely Date: Tue Dec 4 17:18:03 2012 -0600 xfs: rename bli_format to avoid confusion with bli_formats Rename the bli_format structure to __bli_format to avoid accidently confusing them with the bli_formats pointer. Signed-off-by: Mark Tinguely Reviewed-by: Christoph Hellwig Reviewed-by: Dave Chinner Signed-off-by: Ben Myers commit d44d9bc68e32ad5881b105f82bd259d261d1ef74 Author: Mark Tinguely Date: Tue Dec 4 17:18:02 2012 -0600 xfs: use b_maps[] for discontiguous buffers Commits starting at 77c1a08 introduced a multiple segment support to xfs_buf. xfs_trans_buf_item_match() could not find a multi-segment buffer in the transaction because it was looking at the single segment block number rather than the multi-segment b_maps[0].bm.bn. This results on a recursive buffer lock that can never be satisfied. This patch: 1) Changed the remaining b_map accesses to be b_maps[0] accesses. 2) Renames the single segment b_map structure to __b_map to avoid future confusion. Signed-off-by: Mark Tinguely Reviewed-by: Dave Chinner Reviewed-by: Christoph Hellwig Signed-off-by: Ben Myers commit d9777b8de415f2e699dcc4ce8825732ba8af732a Author: Kees Cook Date: Tue Oct 2 11:19:27 2012 -0700 fs/xfs: remove depends on CONFIG_EXPERIMENTAL The CONFIG_EXPERIMENTAL config item has not carried much meaning for a while now and is almost always enabled by default. As agreed during the Linux kernel summit, remove it from any "depends on" lines in Kconfigs. CC: Ben Myers CC: Alex Elder Signed-off-by: Kees Cook Acked-by: Ben Myers ----------------------------------------------------------------------- Summary of changes: fs/xfs/Kconfig | 4 ++-- fs/xfs/xfs_dfrag.c | 8 ++++---- fs/xfs/xfs_export.c | 4 ++-- fs/xfs/xfs_file.c | 4 ++-- fs/xfs/xfs_ioctl.c | 6 +++--- fs/xfs/xfs_ioctl32.c | 2 +- fs/xfs/xfs_log_recover.c | 3 +-- 7 files changed, 15 insertions(+), 16 deletions(-) hooks/post-receive -- XFS development tree From tytso@thunk.org Tue Mar 5 11:59:49 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 42986802C for ; Tue, 5 Mar 2013 11:59:49 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id 2E63F304066 for ; Tue, 5 Mar 2013 09:59:45 -0800 (PST) X-ASG-Debug-ID: 1362506384-04cbb07dbc1bdd90001-NocioJ Received: from imap.thunk.org (li9-11.members.linode.com [67.18.176.11]) by cuda.sgi.com with ESMTP id mOWYyTYm3ZNevDyE (version=TLSv1 cipher=AES128-SHA bits=128 verify=NO) for ; Tue, 05 Mar 2013 09:59:45 -0800 (PST) X-Barracuda-Envelope-From: tytso@thunk.org X-Barracuda-Apparent-Source-IP: 67.18.176.11 Received: from root (helo=closure.thunk.org) by imap.thunk.org with local-esmtp (Exim 4.80) (envelope-from ) id 1UCw9P-0008Jj-AW; Tue, 05 Mar 2013 17:59:43 +0000 Received: by closure.thunk.org (Postfix, from userid 15806) id 333392406A8; Tue, 5 Mar 2013 12:59:42 -0500 (EST) From: Theodore Ts'o To: xfs@oss.sgi.com Cc: Ext4 Developers List , Theodore Ts'o Subject: [PATCH] xfstests: don't assume that falloc_punch implies falloc in test 255 Date: Tue, 5 Mar 2013 12:59:42 -0500 X-ASG-Orig-Subj: [PATCH] xfstests: don't assume that falloc_punch implies falloc in test 255 Message-Id: <1362506382-26974-1-git-send-email-tytso@mit.edu> X-Mailer: git-send-email 1.7.12.rc0.22.gcdd159b X-SA-Exim-Connect-IP: X-SA-Exim-Mail-From: tytso@thunk.org X-SA-Exim-Scanned: No (on imap.thunk.org); SAEximRunCond expanded to false X-Barracuda-Connect: li9-11.members.linode.com[67.18.176.11] X-Barracuda-Start-Time: 1362506385 X-Barracuda-Encrypted: AES128-SHA X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124341 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- As of Linux 3.9-rc1, ext4 will support the punch operation on file systems using indirect blocks, but it can not support the fallocate operation (since there is no way to mark a block as uninitialized using indirect block scheme). This caused test 255 to fail, since it only used _require_xfS_io_falloc_punch assuming that all file systems which supported punch can also support fallocate. Fix this. Signed-off-by: "Theodore Ts'o" --- 255 | 1 + 1 file changed, 1 insertion(+) diff --git a/255 b/255 index 0083963..ae1d8e0 100755 --- a/255 +++ b/255 @@ -48,6 +48,7 @@ _supported_fs generic _supported_os Linux _require_xfs_io_falloc_punch +_require_xfs_io_falloc _require_xfs_io_fiemap testfile=$TEST_DIR/255.$$ -- 1.7.12.rc0.22.gcdd159b From rjohnston@sgi.com Tue Mar 5 12:43:44 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 7937D7FE6 for ; Tue, 5 Mar 2013 12:43:44 -0600 (CST) Received: from xmail.sgi.com (pv-excas3-dc21-nlb.corp.sgi.com [137.38.102.207]) by relay1.corp.sgi.com (Postfix) with ESMTP id 152918F8073; Tue, 5 Mar 2013 10:43:40 -0800 (PST) Received: from [128.162.233.55] (128.162.233.55) by xmail.sgi.com (137.38.102.30) with Microsoft SMTP Server (TLS) id 14.2.318.1; Tue, 5 Mar 2013 12:43:40 -0600 Message-ID: <51363CE6.1010807@sgi.com> Date: Tue, 5 Mar 2013 12:43:50 -0600 From: Rich Johnston User-Agent: Mozilla/5.0 (X11; Linux i686; rv:13.0) Gecko/20120615 Thunderbird/13.0.1 MIME-Version: 1.0 To: Wang Sheng-Hui CC: xfstests , , Subject: Re: [PATCH] xfstests 276: fix error 'FIBMAP: Invalid argument' References: <512DB284.1090806@gmail.com> In-Reply-To: <512DB284.1090806@gmail.com> Content-Type: text/plain; charset="ISO-8859-1"; format=flowed Content-Transfer-Encoding: 7bit X-Originating-IP: [128.162.233.55] This patch has been committed. --Rich commit eba3a5206cd7f8df73d6e6dbf2bb0afca677fca8 Author: Wang Sheng-Hui Date: Thu Feb 28 02:05:56 2013 +0000 xfstests 276: fix error 'FIBMAP: Invalid argument' Commit 05dadc0 ("Btrfs: add fiemap's flag check") added validity checks to the fiemap flags and hence invalid flags are now being rejected. Test 276 passes an invalid fiemap flag to btrfs, and so that test fails since this commit was added. Btrfs doesn't support FIEMAP_FLAG_XATTR, which is enabled by -x option of filefrag, and will fail with 'FIBMAP: Invalid argument' for 'filefrag -vx'. 'filefrag -vx' fails on btrfs with 'FIEMAP failed with unsupported flags 2' Remove the '-x' option. From rjohnston@sgi.com Tue Mar 5 12:51:48 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 233A98015 for ; Tue, 5 Mar 2013 12:51:48 -0600 (CST) Received: from xmail.sgi.com (pv-excas3-dc21-nlb.corp.sgi.com [137.38.102.207]) by relay2.corp.sgi.com (Postfix) with ESMTP id A2C65304048; Tue, 5 Mar 2013 10:51:44 -0800 (PST) Received: from [128.162.233.55] (128.162.233.55) by xmail.sgi.com (137.38.102.30) with Microsoft SMTP Server (TLS) id 14.2.318.1; Tue, 5 Mar 2013 12:51:44 -0600 Message-ID: <51363ECA.3090909@sgi.com> Date: Tue, 5 Mar 2013 12:51:54 -0600 From: Rich Johnston User-Agent: Mozilla/5.0 (X11; Linux i686; rv:13.0) Gecko/20120615 Thunderbird/13.0.1 MIME-Version: 1.0 To: Theodore Ts'o CC: , Ext4 Developers List Subject: Re: [PATCH] xfstests: don't assume that falloc_punch implies falloc in test 255 References: <1362506382-26974-1-git-send-email-tytso@mit.edu> In-Reply-To: <1362506382-26974-1-git-send-email-tytso@mit.edu> Content-Type: text/plain; charset="ISO-8859-1"; format=flowed Content-Transfer-Encoding: 7bit X-Originating-IP: [128.162.233.55] On 03/05/2013 11:59 AM, Theodore Ts'o wrote: > As of Linux 3.9-rc1, ext4 will support the punch operation on file > systems using indirect blocks, but it can not support the fallocate > operation (since there is no way to mark a block as uninitialized > using indirect block scheme). This caused test 255 to fail, since it > only used _require_xfS_io_falloc_punch assuming that all file systems > which supported punch can also support fallocate. Fix this. > > Signed-off-by: "Theodore Ts'o" > --- > 255 | 1 + > 1 file changed, 1 insertion(+) > > diff --git a/255 b/255 > index 0083963..ae1d8e0 100755 > --- a/255 > +++ b/255 > @@ -48,6 +48,7 @@ _supported_fs generic > _supported_os Linux > > _require_xfs_io_falloc_punch > +_require_xfs_io_falloc #rcj looks reasonable to me to add this requirement > _require_xfs_io_fiemap > > testfile=$TEST_DIR/255.$$ > Reviewed-by: Rich Johnston From rjohnston@sgi.com Tue Mar 5 13:08:54 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 46B857F72 for ; Tue, 5 Mar 2013 13:08:54 -0600 (CST) Received: from xmail.sgi.com (pv-excas3-dc21-nlb.corp.sgi.com [137.38.102.207]) by relay1.corp.sgi.com (Postfix) with ESMTP id 0D5138F8087; Tue, 5 Mar 2013 11:08:50 -0800 (PST) Received: from [128.162.233.55] (128.162.233.55) by xmail.sgi.com (137.38.102.30) with Microsoft SMTP Server (TLS) id 14.2.318.1; Tue, 5 Mar 2013 13:07:46 -0600 Message-ID: <5136428C.3020604@sgi.com> Date: Tue, 5 Mar 2013 13:07:56 -0600 From: Rich Johnston User-Agent: Mozilla/5.0 (X11; Linux i686; rv:13.0) Gecko/20120615 Thunderbird/13.0.1 MIME-Version: 1.0 To: Theodore Ts'o CC: , Ext4 Developers List Subject: Re: [PATCH] xfstests: don't assume that falloc_punch implies falloc in test 255 References: <1362506382-26974-1-git-send-email-tytso@mit.edu> In-Reply-To: <1362506382-26974-1-git-send-email-tytso@mit.edu> Content-Type: text/plain; charset="ISO-8859-1"; format=flowed Content-Transfer-Encoding: 7bit X-Originating-IP: [128.162.233.55] This patch has been committed. Thanks --Rich commit 864688d368d6781c3f6d60bc55b5e3591953e462 Author: Theodore Ts'o Date: Tue Mar 5 17:59:42 2013 +0000 xfstests: don't assume that falloc_punch implies falloc in test 255 As of Linux 3.9-rc1, ext4 will support the punch operation on file systems using indirect blocks, but it can not support the fallocate operation (since there is no way to mark a block as uninitialized using indirect block scheme). This caused test 255 to fail, since it only used _require_xfS_io_falloc_punch assuming that all file systems which supported punch can also support fallocate. Fix this. From enwlinux@gmail.com Tue Mar 5 13:17:57 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=FREEMAIL_FROM,T_DKIM_INVALID autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 5ED4E802C for ; Tue, 5 Mar 2013 13:17:57 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay2.corp.sgi.com (Postfix) with ESMTP id 4942330405F for ; Tue, 5 Mar 2013 11:17:57 -0800 (PST) X-ASG-Debug-ID: 1362511073-04cb6c2b041c1eb0001-NocioJ Received: from mail-qe0-f44.google.com (mail-qe0-f44.google.com [209.85.128.44]) by cuda.sgi.com with ESMTP id HcZ0MeCZwIeVwvai (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Tue, 05 Mar 2013 11:17:53 -0800 (PST) X-Barracuda-Envelope-From: enwlinux@gmail.com X-Barracuda-Apparent-Source-IP: 209.85.128.44 X-Barracuda-IPDD: Level1 [gmail.com/209.85.128.44] Received: by mail-qe0-f44.google.com with SMTP id x7so4960831qeu.3 for ; Tue, 05 Mar 2013 11:17:53 -0800 (PST) X-Barracuda-IPDD: Level1 [gmail.com/209.85.128.44] X-Barracuda-IPDD: Level1 [gmail.com/209.85.128.44] DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20120113; h=x-received:date:from:to:cc:subject:message-id:mime-version :content-type:content-disposition:user-agent; bh=a3h5wodbU6o8zQeC3dV9ZLKcep8wsOU1cHJrFEbvUxc=; b=QMi7fRpamlviIIvIhcvBaF7aNdY5BDUryWdLSJPIqlusmfyzDuV3LHzh8TpNpcf2d5 SdL8cIG1SLfsiCjcVWPlQI1CiRaRIpGKLU0VNrhXly4R3xLPK/RI3BuCF2d9cnhLiDlL Ag+fgIO9nSDimZdXttOJTzLuec2fquqJBjK7V2PRVWkW9CtSf2MSe7a9vBZPsisQRPek 2oCL6LAsILwVJZTLxNjYT2Ee1PlhoO4IflVCPa08nH6VEzK5XQZZ07G8KQV5tVtEBo27 qvVKh1MoY4pxr/ncxy2NfwH6mWBVD8N4F3k7fRx9JsstJ9OG5fb9xbhCn5ZTdQLMUleQ Vo/w== X-Received: by 10.224.110.1 with SMTP id l1mr41139042qap.21.1362511072934; Tue, 05 Mar 2013 11:17:52 -0800 (PST) Received: from wallace (c-75-68-62-236.hsd1.nh.comcast.net. [75.68.62.236]) by mx.google.com with ESMTPS id j6sm33349605qek.8.2013.03.05.11.17.51 (version=TLSv1.2 cipher=RC4-SHA bits=128/128); Tue, 05 Mar 2013 11:17:52 -0800 (PST) Date: Tue, 5 Mar 2013 14:17:48 -0500 From: Eric Whitney To: xfs@oss.sgi.com Cc: sandeen@redhat.com Subject: [PATCH V3] xfstests: don't remove trailing zeros from integers Message-ID: <20130305191748.GB3930@wallace> X-ASG-Orig-Subj: [PATCH V3] xfstests: don't remove trailing zeros from integers MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: mail-qe0-f44.google.com[209.85.128.44] X-Barracuda-Start-Time: 1362511073 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=DKIM_SIGNED, DKIM_VERIFIED X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124345 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature _within_tolerance strips trailing zeros from the min and max range values it outputs. This leads to damage if the min or max value is an integer containing trailing zeros rather than a real number with a fractional part containing trailing zeros. Xfstest 289 can exhibit this problem when its input is out of range. Modify the code so it will only remove trailing zeros found after a decimal point. V1->V2: Remove decimal points not followed by digits V2->V3: Per Dave Chinner, simplify by using multiple sed expressions Signed-off-by: Eric Whitney --- common.filter | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/common.filter b/common.filter index 9e4c90c..c854a98 100644 --- a/common.filter +++ b/common.filter @@ -106,8 +106,10 @@ EOF # fix up min, max precision for output # can vary for 5.3, 6.2 - _min=`echo $_min | sed -e 's/0*$//'` # get rid of trailling zeroes - _max=`echo $_max | sed -e 's/0*$//'` # get rid of trailling zeroes + + # remove any trailing zeroes from min, max if they have fractional parts + _min=`echo $_min | sed -e '/\./s/0*$//' -e 's/\.$//'` + _max=`echo $_max | sed -e '/\./s/0*$//' -e 's/\.$//'` if [ $_in_range -eq 1 ] then -- 1.7.10.4 From rjohnston@sgi.com Tue Mar 5 13:20:37 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 1596E802C for ; Tue, 5 Mar 2013 13:20:37 -0600 (CST) Received: from xmail.sgi.com (pv-excas3-dc21-nlb.corp.sgi.com [137.38.102.207]) by relay2.corp.sgi.com (Postfix) with ESMTP id DE4FC304059; Tue, 5 Mar 2013 11:20:36 -0800 (PST) Received: from [128.162.233.55] (128.162.233.55) by xmail.sgi.com (137.38.102.30) with Microsoft SMTP Server (TLS) id 14.2.318.1; Tue, 5 Mar 2013 13:20:36 -0600 Message-ID: <5136458D.4070803@sgi.com> Date: Tue, 5 Mar 2013 13:20:45 -0600 From: Rich Johnston User-Agent: Mozilla/5.0 (X11; Linux i686; rv:13.0) Gecko/20120615 Thunderbird/13.0.1 MIME-Version: 1.0 To: Dave Chinner CC: Eric Whitney , , Subject: Re: [PATCH V2] xfstests: don't remove trailing zeros from integers References: <20130301180158.GC6449@wallace> <20130301203026.GC23616@dastard> In-Reply-To: <20130301203026.GC23616@dastard> Content-Type: text/plain; charset="ISO-8859-1"; format=flowed Content-Transfer-Encoding: 7bit X-Originating-IP: [128.162.233.55] On 03/01/2013 02:30 PM, Dave Chinner wrote: > On Fri, Mar 01, 2013 at 01:01:58PM -0500, Eric Whitney wrote: >> _within_tolerance strips trailing zeros from the min and max range >> values it outputs. This leads to damage if the min or max value is >> an integer containing trailing zeros rather than a real number with >> a fractional part containing trailing zeros. Xfstest 289 can exhibit >> this problem when its input is out of range. Modify the code so it >> will only remove trailing zeros found after a decimal point, and >> remove decimal points not followed by digits. >> >> Signed-off-by: Eric Whitney >> --- >> common.filter | 7 +++++-- >> 1 file changed, 5 insertions(+), 2 deletions(-) >> >> diff --git a/common.filter b/common.filter >> index 9e4c90c..bfc800b 100644 >> --- a/common.filter >> +++ b/common.filter >> @@ -106,8 +106,11 @@ EOF >> >> # fix up min, max precision for output >> # can vary for 5.3, 6.2 >> - _min=`echo $_min | sed -e 's/0*$//'` # get rid of trailling zeroes >> - _max=`echo $_max | sed -e 's/0*$//'` # get rid of trailling zeroes >> + >> + # remove any trailing zeroes from min, max if they have fractional parts >> + # and then remove any decimal points not followed by digits >> + _min=`echo $_min | sed -e '/\./s/0*$//' | sed -e 's/\.$//'` >> + _max=`echo $_max | sed -e '/\./s/0*$//' | sed -e 's/\.$//'` I like Dave's suggestion to change it to the following, what do you think Eric? + _min=`echo $_min | sed -e '/\./s/0*$//' -e 's/\.$//'` # get rid of trailing zeros + _max=`echo $_max | sed -e '/\./s/0*$//' -e 's/\.$//'` # get rid of trailing zeros Regards --Rich > > You can do this with a single sed invocation via multiple > expressions: > > $ echo 200.00 | sed -e '/\./s/0*$//' -e 's/\.$//' > 200 > $ > > Cheers, > > Dave. > From sandeen@redhat.com Tue Mar 5 13:26:07 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 43A17803D for ; Tue, 5 Mar 2013 13:26:07 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay1.corp.sgi.com (Postfix) with ESMTP id 269D18F8070 for ; Tue, 5 Mar 2013 11:26:07 -0800 (PST) X-ASG-Debug-ID: 1362511566-04cb6c2b021c2670001-NocioJ Received: from mx1.redhat.com (mx1.redhat.com [209.132.183.28]) by cuda.sgi.com with ESMTP id P7Fn0J6BFNKQjm6z; Tue, 05 Mar 2013 11:26:06 -0800 (PST) X-Barracuda-Envelope-From: sandeen@redhat.com X-Barracuda-Apparent-Source-IP: 209.132.183.28 X-ASG-Whitelist: Client Received: from int-mx11.intmail.prod.int.phx2.redhat.com (int-mx11.intmail.prod.int.phx2.redhat.com [10.5.11.24]) by mx1.redhat.com (8.14.4/8.14.4) with ESMTP id r25JPvik020080 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=OK); Tue, 5 Mar 2013 14:25:57 -0500 Received: from liberator.sandeen.net (ovpn01.gateway.prod.ext.phx2.redhat.com [10.5.9.1]) by int-mx11.intmail.prod.int.phx2.redhat.com (8.14.4/8.14.4) with ESMTP id r25JPucK004938 (version=TLSv1/SSLv3 cipher=DHE-RSA-CAMELLIA256-SHA bits=256 verify=NO); Tue, 5 Mar 2013 14:25:57 -0500 Message-ID: <513646C4.2090504@redhat.com> Date: Tue, 05 Mar 2013 13:25:56 -0600 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: Rich Johnston CC: Dave Chinner , Eric Whitney , xfs@oss.sgi.com Subject: Re: [PATCH V2] xfstests: don't remove trailing zeros from integers References: <20130301180158.GC6449@wallace> <20130301203026.GC23616@dastard> <5136458D.4070803@sgi.com> X-ASG-Orig-Subj: Re: [PATCH V2] xfstests: don't remove trailing zeros from integers In-Reply-To: <5136458D.4070803@sgi.com> X-Enigmail-Version: 1.5.1 Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Scanned-By: MIMEDefang 2.68 on 10.5.11.24 X-Barracuda-Connect: mx1.redhat.com[209.132.183.28] X-Barracuda-Start-Time: 1362511566 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 On 3/5/13 1:20 PM, Rich Johnston wrote: > On 03/01/2013 02:30 PM, Dave Chinner wrote: >> On Fri, Mar 01, 2013 at 01:01:58PM -0500, Eric Whitney wrote: >>> _within_tolerance strips trailing zeros from the min and max range >>> values it outputs. This leads to damage if the min or max value is >>> an integer containing trailing zeros rather than a real number with >>> a fractional part containing trailing zeros. Xfstest 289 can exhibit >>> this problem when its input is out of range. Modify the code so it >>> will only remove trailing zeros found after a decimal point, and >>> remove decimal points not followed by digits. >>> >>> Signed-off-by: Eric Whitney >>> --- >>> common.filter | 7 +++++-- >>> 1 file changed, 5 insertions(+), 2 deletions(-) >>> >>> diff --git a/common.filter b/common.filter >>> index 9e4c90c..bfc800b 100644 >>> --- a/common.filter >>> +++ b/common.filter >>> @@ -106,8 +106,11 @@ EOF >>> >>> # fix up min, max precision for output >>> # can vary for 5.3, 6.2 >>> - _min=`echo $_min | sed -e 's/0*$//'` # get rid of trailling zeroes >>> - _max=`echo $_max | sed -e 's/0*$//'` # get rid of trailling zeroes >>> + >>> + # remove any trailing zeroes from min, max if they have fractional parts >>> + # and then remove any decimal points not followed by digits >>> + _min=`echo $_min | sed -e '/\./s/0*$//' | sed -e 's/\.$//'` >>> + _max=`echo $_max | sed -e '/\./s/0*$//' | sed -e 's/\.$//'` > > I like Dave's suggestion to change it to the following, what do you think Eric? > > + _min=`echo $_min | sed -e '/\./s/0*$//' -e 's/\.$//'` # get rid of trailing zeros > + _max=`echo $_max | sed -e '/\./s/0*$//' -e 's/\.$//'` # get rid of trailing zeros looks awesome. Don't much care. Better to just fix than to dither for too long, aiming for the best sed ever ;) -Eric > Regards > --Rich > >> >> You can do this with a single sed invocation via multiple >> expressions: >> >> $ echo 200.00 | sed -e '/\./s/0*$//' -e 's/\.$//' >> 200 >> $ >> >> Cheers, >> >> Dave. >> > > From sandeen@sandeen.net Tue Mar 5 13:30:48 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 8504E8004 for ; Tue, 5 Mar 2013 13:30:48 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay3.corp.sgi.com (Postfix) with ESMTP id 1507BAC005 for ; Tue, 5 Mar 2013 11:30:44 -0800 (PST) X-ASG-Debug-ID: 1362511843-04cb6c2b041c2b20001-NocioJ Received: from sandeen.net (sandeen.net [63.231.237.45]) by cuda.sgi.com with ESMTP id vOtSL6A30LDD5tvL for ; Tue, 05 Mar 2013 11:30:43 -0800 (PST) X-Barracuda-Envelope-From: sandeen@sandeen.net X-Barracuda-Apparent-Source-IP: 63.231.237.45 Received: from liberator.sandeen.net (liberator.sandeen.net [10.0.0.4]) (using TLSv1 with cipher DHE-RSA-CAMELLIA256-SHA (256/256 bits)) (No client certificate requested) by sandeen.net (Postfix) with ESMTPSA id 731D863C59BB; Tue, 5 Mar 2013 13:30:43 -0600 (CST) Message-ID: <513647E2.1020200@sandeen.net> Date: Tue, 05 Mar 2013 13:30:42 -0600 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: Eric Whitney CC: xfs@oss.sgi.com, sandeen@redhat.com Subject: Re: [PATCH V3] xfstests: don't remove trailing zeros from integers References: <20130305191748.GB3930@wallace> X-ASG-Orig-Subj: Re: [PATCH V3] xfstests: don't remove trailing zeros from integers In-Reply-To: <20130305191748.GB3930@wallace> X-Enigmail-Version: 1.5.1 Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: sandeen.net[63.231.237.45] X-Barracuda-Start-Time: 1362511843 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124347 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On 3/5/13 1:17 PM, Eric Whitney wrote: > _within_tolerance strips trailing zeros from the min and max range > values it outputs. This leads to damage if the min or max value is > an integer containing trailing zeros rather than a real number with > a fractional part containing trailing zeros. Xfstest 289 can exhibit > this problem when its input is out of range. Modify the code so it > will only remove trailing zeros found after a decimal point. > > V1->V2: Remove decimal points not followed by digits > V2->V3: Per Dave Chinner, simplify by using multiple sed expressions > > Signed-off-by: Eric Whitney Reviewed-by: Eric Sandeen > --- > common.filter | 6 ++++-- > 1 file changed, 4 insertions(+), 2 deletions(-) > > diff --git a/common.filter b/common.filter > index 9e4c90c..c854a98 100644 > --- a/common.filter > +++ b/common.filter > @@ -106,8 +106,10 @@ EOF > > # fix up min, max precision for output > # can vary for 5.3, 6.2 > - _min=`echo $_min | sed -e 's/0*$//'` # get rid of trailling zeroes > - _max=`echo $_max | sed -e 's/0*$//'` # get rid of trailling zeroes > + > + # remove any trailing zeroes from min, max if they have fractional parts > + _min=`echo $_min | sed -e '/\./s/0*$//' -e 's/\.$//'` > + _max=`echo $_max | sed -e '/\./s/0*$//' -e 's/\.$//'` > > if [ $_in_range -eq 1 ] > then > From enwlinux@gmail.com Tue Mar 5 13:31:49 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=FREEMAIL_FROM,T_DKIM_INVALID autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 5DC1C805A for ; Tue, 5 Mar 2013 13:31:49 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay1.corp.sgi.com (Postfix) with ESMTP id 429FE8F8071 for ; Tue, 5 Mar 2013 11:31:49 -0800 (PST) X-ASG-Debug-ID: 1362511907-04cbb07dbd1c6680001-NocioJ Received: from mail-qe0-f52.google.com (mail-qe0-f52.google.com [209.85.128.52]) by cuda.sgi.com with ESMTP id 9xuJ5HG0lVKFmkEZ (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Tue, 05 Mar 2013 11:31:48 -0800 (PST) X-Barracuda-Envelope-From: enwlinux@gmail.com X-Barracuda-Apparent-Source-IP: 209.85.128.52 X-Barracuda-IPDD: Level1 [gmail.com/209.85.128.52] Received: by mail-qe0-f52.google.com with SMTP id s14so4496225qeb.39 for ; Tue, 05 Mar 2013 11:31:47 -0800 (PST) X-Barracuda-IPDD: Level1 [gmail.com/209.85.128.52] X-Barracuda-IPDD: Level1 [gmail.com/209.85.128.52] DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20120113; h=x-received:date:from:to:cc:subject:message-id:references :mime-version:content-type:content-disposition:in-reply-to :user-agent; bh=MShdQetjwyS6lKxvvOtGve/uspO9O7WBnq1cPJFBckA=; b=AKLL1xA1eNHDiwypK+A4uUTYM4V67ZyvMpEpWveqRrow+tiwgmcYKqrHSO58e/JGyT X53YLSXTEQDXxG0GVTBsxvbzQQV2gOA8Bo48I5bvoIXvMMpEW47EdWzie+oyXjUKv6XH vemvY3+8sbr1Rg4TYoYuQmxl2MGeAasctWRL7a7W+4J92Kg6PhTLCSgG4r31Dr6i5isN f9wH3n7J4/yDPcdYIorvgY1VezkpTHY3ybaPXjDZX+g91HccgxOiEV7dFw+e0r2mPP3o 5zs92o2e/XLYCeZk4HkD5VCT8+OQfM7g+Al4ydbCWVpSkepgDtPLC5PKUl91BIuOp9il p88g== X-Received: by 10.49.24.194 with SMTP id w2mr42906052qef.24.1362511907683; Tue, 05 Mar 2013 11:31:47 -0800 (PST) Received: from wallace (c-75-68-62-236.hsd1.nh.comcast.net. [75.68.62.236]) by mx.google.com with ESMTPS id dt10sm44319892qab.0.2013.03.05.11.31.46 (version=TLSv1.2 cipher=RC4-SHA bits=128/128); Tue, 05 Mar 2013 11:31:46 -0800 (PST) Date: Tue, 5 Mar 2013 14:31:43 -0500 From: Eric Whitney To: Rich Johnston Cc: Dave Chinner , Eric Whitney , sandeen@redhat.com, xfs@oss.sgi.com Subject: Re: [PATCH V2] xfstests: don't remove trailing zeros from integers Message-ID: <20130305193143.GA13545@wallace> X-ASG-Orig-Subj: Re: [PATCH V2] xfstests: don't remove trailing zeros from integers References: <20130301180158.GC6449@wallace> <20130301203026.GC23616@dastard> <5136458D.4070803@sgi.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <5136458D.4070803@sgi.com> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: mail-qe0-f52.google.com[209.85.128.52] X-Barracuda-Start-Time: 1362511908 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=DKIM_SIGNED, DKIM_VERIFIED X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124347 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature * Rich Johnston : > On 03/01/2013 02:30 PM, Dave Chinner wrote: > >On Fri, Mar 01, 2013 at 01:01:58PM -0500, Eric Whitney wrote: > >>_within_tolerance strips trailing zeros from the min and max range > >>values it outputs. This leads to damage if the min or max value is > >>an integer containing trailing zeros rather than a real number with > >>a fractional part containing trailing zeros. Xfstest 289 can exhibit > >>this problem when its input is out of range. Modify the code so it > >>will only remove trailing zeros found after a decimal point, and > >>remove decimal points not followed by digits. > >> > >>Signed-off-by: Eric Whitney > >>--- > >> common.filter | 7 +++++-- > >> 1 file changed, 5 insertions(+), 2 deletions(-) > >> > >>diff --git a/common.filter b/common.filter > >>index 9e4c90c..bfc800b 100644 > >>--- a/common.filter > >>+++ b/common.filter > >>@@ -106,8 +106,11 @@ EOF > >> > >> # fix up min, max precision for output > >> # can vary for 5.3, 6.2 > >>- _min=`echo $_min | sed -e 's/0*$//'` # get rid of trailling zeroes > >>- _max=`echo $_max | sed -e 's/0*$//'` # get rid of trailling zeroes > >>+ > >>+ # remove any trailing zeroes from min, max if they have fractional parts > >>+ # and then remove any decimal points not followed by digits > >>+ _min=`echo $_min | sed -e '/\./s/0*$//' | sed -e 's/\.$//'` > >>+ _max=`echo $_max | sed -e '/\./s/0*$//' | sed -e 's/\.$//'` > > I like Dave's suggestion to change it to the following, what do you > think Eric? I just posted a V3 containing Dave's simplification. I'd hoped there would be something like that, and much appreciate the suggestion. Thanks, Eric > > + _min=`echo $_min | sed -e '/\./s/0*$//' -e 's/\.$//'` # get rid > of trailing zeros > + _max=`echo $_max | sed -e '/\./s/0*$//' -e 's/\.$//'` # get rid > of trailing zeros > > Regards > --Rich > > > > >You can do this with a single sed invocation via multiple > >expressions: > > > >$ echo 200.00 | sed -e '/\./s/0*$//' -e 's/\.$//' > >200 > >$ > > > >Cheers, > > > >Dave. > > > > From rjohnston@sgi.com Tue Mar 5 13:49:13 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id B8AE58034 for ; Tue, 5 Mar 2013 13:49:13 -0600 (CST) Received: from xmail.sgi.com (pv-excas3-dc21-nlb.corp.sgi.com [137.38.102.207]) by relay2.corp.sgi.com (Postfix) with ESMTP id 705F3304051; Tue, 5 Mar 2013 11:49:13 -0800 (PST) Received: from [128.162.233.55] (128.162.233.55) by xmail.sgi.com (137.38.102.30) with Microsoft SMTP Server (TLS) id 14.2.318.1; Tue, 5 Mar 2013 13:49:12 -0600 Message-ID: <51364C42.6030307@sgi.com> Date: Tue, 5 Mar 2013 13:49:22 -0600 From: Rich Johnston User-Agent: Mozilla/5.0 (X11; Linux i686; rv:13.0) Gecko/20120615 Thunderbird/13.0.1 MIME-Version: 1.0 To: Eric Whitney CC: , Subject: Re: [PATCH V3] xfstests: don't remove trailing zeros from integers References: <20130305191748.GB3930@wallace> In-Reply-To: <20130305191748.GB3930@wallace> Content-Type: text/plain; charset="ISO-8859-1"; format=flowed Content-Transfer-Encoding: 7bit X-Originating-IP: [128.162.233.55] This patch has been committed. Thanks --Rich commit edce9e677fda49ca20d6059248937ab4af65d053 Author: Eric Whitney Date: Tue Mar 5 19:17:48 2013 +0000 xfstests: don't remove trailing zeros from integers _within_tolerance strips trailing zeros from the min and max range values it outputs. This leads to damage if the min or max value is an integer containing trailing zeros rather than a real number with a fractional part containing trailing zeros. Xfstest 289 can exhibit this problem when its input is out of range. Modify the code so it will only remove trailing zeros found after a decimal point. V1->V2: Remove decimal points not followed by digits V2->V3: Per Dave Chinner, simplify by using multiple sed expressions Signed-off-by: Eric Whitney Reviewed-by: Eric Sandeen Signed-off-by: Rich Johnston From daviddonihue10001@gmail.com Tue Mar 5 13:59:37 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.3 required=5.0 tests=FREEMAIL_ENVFROM_END_DIGIT, FREEMAIL_FROM,HTML_MESSAGE,T_DKIM_INVALID autolearn=no version=3.3.1 X-Original-To: linux-xfs@oss.sgi.com Delivered-To: linux-xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 913A2804E for ; Tue, 5 Mar 2013 13:59:37 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay2.corp.sgi.com (Postfix) with ESMTP id 5B47B304064 for ; Tue, 5 Mar 2013 11:59:37 -0800 (PST) X-ASG-Debug-ID: 1362513572-04bdf022961e30a0001-w1Z2WR Received: from mail-pb0-f50.google.com (mail-pb0-f50.google.com [209.85.160.50]) by cuda.sgi.com with ESMTP id kFA6WmWjglZpTF0J (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Tue, 05 Mar 2013 11:59:33 -0800 (PST) X-Barracuda-Envelope-From: daviddonihue10001@gmail.com X-Barracuda-Apparent-Source-IP: 209.85.160.50 X-Barracuda-IPDD: Level1 [gmail.com/209.85.160.50] Received: by mail-pb0-f50.google.com with SMTP id up1so4851682pbc.23 for ; Tue, 05 Mar 2013 11:59:32 -0800 (PST) X-Barracuda-IPDD: Level1 [gmail.com/209.85.160.50] X-Barracuda-IPDD: Level1 [gmail.com/209.85.160.50] DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20120113; h=x-received:date:subject:message-id:mime-version:from:to :content-type; bh=dRNCpvUOjAXf6htuC24W8t8v1gkzsH+3sjvc4n/0jx8=; b=dleu6k0hRIxryE9DJLEVsXFUHCEUqs+uWiRqPf7lRS2Jek/6dLXTZtZFhcq9Xbox8J +uGdQ3hK37P1PybJ8lnYX/HA+qOu89S7PyJCy6f3IEj26IV+Y4fi3mRP3XkAnHi7Deye 2SaLcbd8hOme85MuyeiXMxcknrPlQhCYk1zBRasbLk2ioXz/BAphhAiuLmX7IqwAEzK3 E5LxhGTmTmrbKyVKpu6UOpy3rFeXTRCxUEMpZHuEkDLK/amBu8zPAAsUD9GBEis14iYU ThG6fDTaBQNM/bERgmwno7F1ZjQ9QRVbYQpz5Y4z9a1IVqIwdJM8JrQEJB40KdJkiNiR tv5Q== X-Received: by 10.68.117.104 with SMTP id kd8mr40360601pbb.1.1362513572564; Tue, 05 Mar 2013 11:59:32 -0800 (PST) Received: from localhost.localdomain (108-90-121-38.lightspeed.irvnca.sbcglobal.net. [108.90.121.38]) by mx.google.com with ESMTPS id hu2sm27949852pbc.38.2013.03.05.11.59.30 (version=TLSv1 cipher=RC4-SHA bits=128/128); Tue, 05 Mar 2013 11:59:31 -0800 (PST) Date: Tue, 05 Mar 2013 11:58:18 -0800 Subject: Music Videos as low as $2000 for cool acts Message-ID: <3845faa174589a206e08ffc54c76ca68@unknowne091f59e44fe.att.net> X-ASG-Orig-Subj: Music Videos as low as $2000 for cool acts MIME-Version: 1.0 (Generated by Pantomime 1.2.0) From: Super Rad Motion Picture Group To: linux-xfs@oss.sgi.com Content-Type: multipart/alternative; boundary="=_64f036179837090ffb3f7698c74d51f6" X-Barracuda-Connect: mail-pb0-f50.google.com[209.85.160.50] X-Barracuda-Start-Time: 1362513573 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Barracuda-BRTS-Status: 1 X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=DKIM_SIGNED, DKIM_VERIFIED, HTML_MESSAGE X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124349 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature 0.00 HTML_MESSAGE BODY: HTML included in message --=_64f036179837090ffb3f7698c74d51f6 Content-Type: text/plain; charset="us-ascii"; format="flowed" Starting as low as $2500 (if you provide the location). We also offer lyrics and mash up videos that have been known to rule the youtube world. 2 NEW VIDEOS ADDED! CHECK EM OUT! I've had work run on MTV, BET, M2, etc. My recent music video did 160,000 views when it dropped and launched the career of it's young star onto Nickalodean. http://www.superradfilms.com/music-videos.html Donihue directed the underground mini-hit The Weathered Underground staring Brea Grant from Heroes as well as the upcoming film The Bang Bang Brokers. His past music videos include Computer Killer (featuring Gas Lamp Killer and Computer Jay) The Lashes, Sirens Sister, Rocket, Pinehurst Kids, Mar Mar, Rick Shaffer, Aaron Manino and many others. He has cut promos for Guitar Heroes Soundgarden launch party, Wii's Just dance campaign, Groundworks Pearl Jam and many more. David Donihue 323 363 0562 info@superradfilms.com --=_64f036179837090ffb3f7698c74d51f6 Content-Type: text/html; charset="us-ascii"; format="flowed"

Starting as low as $2500 (if you provide the location). We also offer lyrics and mash up videos that have been known to rule the youtube world. 2 NEW VIDEOS ADDED! CHECK EM OUT! I've had work run on MTV, BET, M2, etc. My recent music video did 160,000 views when it dropped and launched the career of it's young star onto Nickalodean.


http://www.superradfilms.com/music-videos.html


Donihue directed the underground mini-hit The Weathered Underground staring Brea Grant from Heroes as well as the upcoming film The Bang Bang Brokers. His past music videos include Computer Killer (featuring Gas Lamp Killer and Computer Jay) The Lashes, Sirens Sister, Rocket, Pinehurst Kids, Mar Mar, Rick Shaffer, Aaron Manino and many others. He has cut promos for Guitar Heroes Soundgarden launch party, Wii's Just dance campaign, Groundworks Pearl Jam and many more.



David Donihue

323 363 0562

info@superradfilms.com




--=_64f036179837090ffb3f7698c74d51f6-- From daviddonihue10001@gmail.com Tue Mar 5 13:59:43 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: *** X-Spam-Status: No, score=3.2 required=5.0 tests=FREEMAIL_ENVFROM_END_DIGIT, FREEMAIL_FROM,HTML_IMAGE_ONLY_32,HTML_MESSAGE,PLING_QUERY,T_DKIM_INVALID autolearn=no version=3.3.1 X-Original-To: linux-xfs@oss.sgi.com Delivered-To: linux-xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 6EA168067 for ; Tue, 5 Mar 2013 13:59:43 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay2.corp.sgi.com (Postfix) with ESMTP id 1A9D230406B for ; Tue, 5 Mar 2013 11:59:43 -0800 (PST) X-ASG-Debug-ID: 1362513581-04bdf022981e30d0001-w1Z2WR Received: from mail-pb0-f43.google.com (mail-pb0-f43.google.com [209.85.160.43]) by cuda.sgi.com with ESMTP id RN82lfkr2dTCH4hi (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Tue, 05 Mar 2013 11:59:41 -0800 (PST) X-Barracuda-Envelope-From: daviddonihue10001@gmail.com X-Barracuda-Apparent-Source-IP: 209.85.160.43 X-Barracuda-IPDD: Level1 [gmail.com/209.85.160.43] Received: by mail-pb0-f43.google.com with SMTP id md12so4952097pbc.30 for ; Tue, 05 Mar 2013 11:59:41 -0800 (PST) X-Barracuda-IPDD: Level1 [gmail.com/209.85.160.43] X-Barracuda-IPDD: Level1 [gmail.com/209.85.160.43] DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20120113; h=x-received:date:subject:message-id:mime-version:from:to :content-type; bh=x05Dv3qD+muV4JfPu5U78DPrrg0T/22NNvE0LGDhOx0=; b=aqK7yaMgn4/QKb04/9BtZhE54kMvZ4EP5Cbu1FiNvGdK2IIZLc2BQS7HckUNSC4+Np lrZY7F/w8L0Nv515NyywvwL/Gw3EkqHXC6T2bRa2qJd9iAjEPqPZVQgMjg4qyDSGVN3L aADcuGhquMUHXTeUVgvYK1Ar/H4ukBbUvHiOu8+dtypoAj+QW+njwxAUDrGisWOOw3gx 0+Tibz+8SU1136DH/1x02FZnClsI+SiSKGkOYnaGFLNy8CIGId7oAcpi8II+xsX4Aoko tnwT008U4h/y2+07Pb7XmPsZ4GM+68jlIEKKXCxMKCC9BIZ68Qoa1FtMt5UGh0fBLkUw 3Xkg== X-Received: by 10.68.163.68 with SMTP id yg4mr30186466pbb.77.1362513581301; Tue, 05 Mar 2013 11:59:41 -0800 (PST) Received: from localhost.localdomain (108-90-121-38.lightspeed.irvnca.sbcglobal.net. [108.90.121.38]) by mx.google.com with ESMTPS id pg6sm27980156pbb.0.2013.03.05.11.59.38 (version=TLSv1 cipher=RC4-SHA bits=128/128); Tue, 05 Mar 2013 11:59:39 -0800 (PST) Date: Tue, 05 Mar 2013 11:58:26 -0800 Subject: Need a Web Commercial? As low as $2500! Message-ID: <6541da7e4b00792d6a5592c59a17cb93@unknowne091f59e44fe.att.net> X-ASG-Orig-Subj: Need a Web Commercial? As low as $2500! MIME-Version: 1.0 (Generated by Pantomime 1.2.0) From: Super Rad Motion Picture Group To: linux-xfs@oss.sgi.com Content-Type: multipart/related; type="multipart/alternative"; boundary="=_851d4a64bfa46ccb58b964e4134e0975" X-Barracuda-Connect: mail-pb0-f43.google.com[209.85.160.43] X-Barracuda-Start-Time: 1362513581 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 1.34 X-Barracuda-Spam-Status: No, SCORE=1.34 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=DKIM_SIGNED, DKIM_VERIFIED, EXTRA_MPART_TYPE, HTML_IMAGE_ONLY_32, HTML_MESSAGE, PLING_QUERY X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124349 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 EXTRA_MPART_TYPE Header has extraneous Content-type:...type= entry -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature 0.00 HTML_IMAGE_ONLY_32 BODY: HTML: images with 2800-3200 bytes of words 0.00 HTML_MESSAGE BODY: HTML included in message 1.33 PLING_QUERY Subject has exclamation mark and question mark --=_851d4a64bfa46ccb58b964e4134e0975 Content-Type: multipart/alternative; boundary="=_f57c9177d5d8a74f2ee868368086fe32" --=_f57c9177d5d8a74f2ee868368086fe32 Content-Type: text/plain; charset="us-ascii"; format="flowed" Hey guys, According to MSN and Google, Web Videos increase sales by 72%. We're currently doing LA based TV and Web Commercials (yet we work clients all over the globe) for as low as $2500 for spots that look amazing! Use ua for fashion, cars or food. As you know, the higher the production value, the more people take you seriously. Checkout our work! Let us help you generate a whole new line of customers! We also do music videos and corporate training videos as well! http://www.superradfilms.com Sincerly, David Donihue 323 363 0562 info@superradfilms.com --=_f57c9177d5d8a74f2ee868368086fe32 Content-Transfer-Encoding: quoted-printable Content-Type: text/html; charset="iso-8859-1"


Hey guys,


According to MSN and Google= , Web Videos increase sales by 72%.


We're currently doing LA based= TV and Web Commercials (yet we work clients all over the globe) for as = low as $2500 for spots that look amazing! Use ua for fashion, cars or fo= od. As you know, the higher the production value, the more people take y= ou seriously.


Checkout our work! Let us help= you generate a whole new line of customers! We also do music videos and= corporate training videos as well!


http://www.superradfilms.com


3D"9438144.jpg"


Sincerly,


David Donihue =A0

323 363 0562

info@superradfilms.com<= /p>

--=_f57c9177d5d8a74f2ee868368086fe32-- --=_851d4a64bfa46ccb58b964e4134e0975 Content-Transfer-Encoding: base64 Content-ID: <61ae4150-c1d6-4766-a195-0b7ae26cb0c7@local> Content-Type: image/jpeg; name="9438144.jpg" /9j/4AAQSkZJRgABAQEASABIAAD/2wBDAAIBAQIBAQICAgICAgICAwUDAwMDAwYEBAMFBwYH BwcGBwcICQsJCAgKCAcHCg0KCgsMDAwMBwkODw0MDgsMDAz/2wBDAQICAgMDAwYDAwYMCAcI DAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAz/wAAR CABkAYsDAREAAhEBAxEB/8QAHgAAAAYDAQEAAAAAAAAAAAAAAAQFBgcJAwgKAQL/xABnEAAB AwMCAwQFAgoQEQoHAQABAgMEBQYRAAcIEiEJEzFBChQiUWFx0RUWIzJSgZG0tdMaJDM2OUJy dHWChKGxs9LUFyU0NThHV2JjZGVmdpKUlcEYKDdzg4WGo6ThGUNERVaWwtX/xAAcAQEBAQEA AwEBAAAAAAAAAAAAAQIDBAUHCAb/xABCEQACAQIEAwQGBA0DBQAAAAAAAQIDEQQFEjEGIUEH UXGBFCIyYZGxEzVS0hY0QlRyc4KSoaLB0fAVYrIXJCUzU//aAAwDAQACEQMRAD8A3Y7e/th7 v7I+1tsJ9p2hbF2LvqbUoslNYkSWhGEVqMtJR3Khkq75Wc/YjHidEdZyaditv8mc7x/3Hdrv 9vqX4zQzrkfQ9M13jV/ad2t/3hUv5eg1syI9Mt3jWf8Aoc2t/wB41L+XoNbMzfpkm8i/7Tm1 v+8ql/K0Gtmdv0xneZf9pzaz/edS/laDW+8Ms+mFbyO+Oz21v+86l/K0Gthtj0vreF3GdoNr xn/KdS/laDWw2z6XTvA6eu0W2H+86j8+g1sOMelsbuuf2pNsh/3lUfn0JqYdj+libtPeO022 Yz/lKo/Poa1MPx/Ssd2HvHanbUfJUah8+g1MOx/Snd1nsZ2r24BPuqNQ+fQjkw/H9KH3TeIz tbt0P+8J/wA+hdTD0b0nLdB3x2w28H/eE/59BqYoRvSXNzXh12y2/HyVCd8+guxQjekiblP/ ANrawR+753z6F1MPxvSLtx5GM7cWGP3dN+fQXYoxfSFdw5Hjt3Yoz/js359CXYoRu3+3AfHX b6yBn/HZvz6Fuw/G7ee/ZA62BZQB/wAdmfPoNTFKL25t9P8AjYlmj92S/n0F2KEbttr3exmx rQH7rl/PoNTFGN2z16SD1sm0h+65Xz6C7FGN2wt4v4zZlqj91Svn0FxRjdrddz2M2fa4z7pM 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 ANADQA0ANADQA0ANADQA0ANADQH/2Q== --=_851d4a64bfa46ccb58b964e4134e0975-- From rjohnston@sgi.com Tue Mar 5 14:09:34 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 257E88067 for ; Tue, 5 Mar 2013 14:09:34 -0600 (CST) Received: from xmail.sgi.com (pv-excas3-dc21.corp.sgi.com [137.38.102.206]) by relay3.corp.sgi.com (Postfix) with ESMTP id 82A42AC00A; Tue, 5 Mar 2013 12:09:30 -0800 (PST) Received: from [128.162.233.55] (128.162.233.55) by xmail.sgi.com (137.38.102.30) with Microsoft SMTP Server (TLS) id 14.2.318.1; Tue, 5 Mar 2013 14:09:12 -0600 Message-ID: <513650F2.8060406@sgi.com> Date: Tue, 5 Mar 2013 14:09:22 -0600 From: Rich Johnston User-Agent: Mozilla/5.0 (X11; Linux i686; rv:13.0) Gecko/20120615 Thunderbird/13.0.1 MIME-Version: 1.0 To: Eric Whitney CC: , Subject: Re: [PATCH] xfstests: use native definition of O_DIRECT flag References: <20130226210322.GB5275@wallace> In-Reply-To: <20130226210322.GB5275@wallace> Content-Type: text/plain; charset="ISO-8859-1"; format=flowed Content-Transfer-Encoding: 7bit X-Originating-IP: [128.162.233.55] This patch has been committed. Thanks --Rich commit 5825ecd3b99ed8c177895d5e6a830133fed384ea Author: Eric Whitney Date: Tue Feb 26 21:03:22 2013 +0000 xfstests: use native definition of O_DIRECT flag The definition of O_DIRECT in src/trunc.c causes xfstest 125 to fail when run on a Pandaboard. On ARM, the value used (0x040000) is O_DIRECTORY rather than O_DIRECT as it is on x86. Prefer the platform's native definition of O_DIRECT supplied by fcntl.h if available. Also, fix a couple of error messages to properly reflect their context. Signed-off-by: Eric Whitney Reviewed-by: Dave Chinner Signed-off-by: Rich Johnston From rjohnston@sgi.com Tue Mar 5 14:23:31 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 05682806B for ; Tue, 5 Mar 2013 14:23:31 -0600 (CST) Received: from xmail.sgi.com (pv-excas3-dc21.corp.sgi.com [137.38.102.206]) by relay3.corp.sgi.com (Postfix) with ESMTP id 1A7A8AC005; Tue, 5 Mar 2013 12:23:30 -0800 (PST) Received: from [128.162.233.55] (128.162.233.55) by xmail.sgi.com (137.38.102.30) with Microsoft SMTP Server (TLS) id 14.2.318.1; Tue, 5 Mar 2013 14:23:29 -0600 Message-ID: <5136544B.2030004@sgi.com> Date: Tue, 5 Mar 2013 14:23:39 -0600 From: Rich Johnston User-Agent: Mozilla/5.0 (X11; Linux i686; rv:13.0) Gecko/20120615 Thunderbird/13.0.1 MIME-Version: 1.0 To: Eric Sandeen CC: xfs-oss , linux-btrfs , Stefan Behrens Subject: Re: [PATCH] xfstests: handle new mkfs.btrfs -f option cleanly References: <512D1E3E.9050907@redhat.com> In-Reply-To: <512D1E3E.9050907@redhat.com> Content-Type: text/plain; charset="ISO-8859-1"; format=flowed Content-Transfer-Encoding: 7bit X-Originating-IP: [128.162.233.55] Looks good. Reviewed-by: Rich Johnston This patch has been committed. Thanks --Rich commit 24fef70ef3fa0be047264b7a40b0bcf86533ec22 Author: Eric Sandeen Date: Tue Feb 26 20:42:38 2013 +0000 xfstests: handle new mkfs.btrfs -f option cleanly I added an "-f" option to mkfs.btrfs to force overwrite of an existing filesystem. Now on an xfstests run, new mkfs.btrfs requires it, and old mkfs.btrfs cannot accept it. So, add a helper which works out whether -f is needed, and add it to the MKFS_BTRFS_PROG env. var as necessary, so that it is an always-included option during the tests. Signed-off-by: Eric Sandeen Reviewed-by: Rich Johnston Signed-off-by: Rich Johnston From hpj@urpla.net Tue Mar 5 14:32:32 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 6C5938074 for ; Tue, 5 Mar 2013 14:32:32 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay1.corp.sgi.com (Postfix) with ESMTP id 0A6288F807A for ; Tue, 5 Mar 2013 12:32:28 -0800 (PST) X-ASG-Debug-ID: 1362515544-04bdf022961e55e0001-NocioJ Received: from moutng.kundenserver.de (moutng.kundenserver.de [212.227.126.171]) by cuda.sgi.com with ESMTP id zPbi8Zo53hSdDP6H (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Tue, 05 Mar 2013 12:32:25 -0800 (PST) X-Barracuda-Envelope-From: hpj@urpla.net X-Barracuda-Apparent-Source-IP: 212.227.126.171 Received: from lisa (p5B2A4BB3.dip0.t-ipconnect.de [91.42.75.179]) by mrelayeu.kundenserver.de (node=mreu0) with ESMTP (Nemesis) id 0MIAsE-1UDWl70JRu-003yr2; Tue, 05 Mar 2013 21:32:15 +0100 Received: from localhost (localhost [127.0.0.1]) by tyrex.lisa.loc (Postfix) with ESMTP id A20111B971B00; Tue, 5 Mar 2013 21:32:14 +0100 (CET) X-Virus-Scanned: amavisd-new at lisa.loc Received: from tyrex.lisa.loc ([127.0.0.1]) by localhost (tyrex.lisa.loc [127.0.0.1]) (amavisd-new, port 10024) with LMTP id EbjcLku25IL0; Tue, 5 Mar 2013 21:32:04 +0100 (CET) From: Hans-Peter Jansen To: Dave Chinner Cc: xfs@oss.sgi.com Subject: Re: strange behavior of a larger xfs directory Date: Tue, 05 Mar 2013 21:32:02 +0100 X-ASG-Orig-Subj: Re: strange behavior of a larger xfs directory Message-ID: <8026381.3dEJ1E4pzL@xrated> User-Agent: KMail/4.9.5 (Linux/3.4.28-2.20-desktop; KDE/4.9.5; x86_64; ; ) In-Reply-To: <20130304230527.GM26081@dastard> References: <4300208.uZ6HVTycB6@xrated> <20130304230527.GM26081@dastard> MIME-Version: 1.0 Content-Type: multipart/mixed; boundary="nextPart5192251.cl8ZghraCZ" Content-Transfer-Encoding: 7Bit X-Provags-ID: V02:K0:ODY+jGbyLPscfrIfiMRU1F/u9jELtBP/uRmvyM/n/rR ldN0Z4daVPs6DLCWhn796vd/sPnzlKumuFiTiqnoYE3c8hAkhw pFmItLXiBFNJlYUjqXBLf1RN7jx7hnm2HOmocueb+Mwwlgv69a QI4mEu8RKF3TQ+RT0r69K+5UrdAV0LeBcZeUR6pQdZWuhRx6Um b+Hr0/SaLUekFmbysbBdJYdGDUb3tZ1YWZzu7bckimJOEbS0Z7 vpXAuYTgPCNZ7EHqBMk7tc5bHxNdr+xGXJfhFxgTXA362GvLmp 5ESo0iyF/Zyg4vt9FL20m98hHDTezuZu9FfPoWP6AM2QZEYEw= = X-Barracuda-Connect: moutng.kundenserver.de[212.227.126.171] X-Barracuda-Start-Time: 1362515544 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.10 X-Barracuda-Spam-Status: No, SCORE=0.10 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_SA085 X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124351 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.10 BSF_SC0_SA085 Custom Rule SA085 This is a multi-part message in MIME format. --nextPart5192251.cl8ZghraCZ Content-Transfer-Encoding: quoted-printable Content-Type: text/plain; charset="iso-8859-1" Hi Dave, thanks for the helpful hints. Am Dienstag, 5. M=E4rz 2013, 10:05:27 schrieb Dave Chinner: > On Mon, Mar 04, 2013 at 05:40:13PM +0100, Hans-Peter Jansen wrote: > > Hi, > >=20 > > after upgrading the kernel on a server from 2.6.34 to 3.8.1 (x86-32= ), I > > suffer from a strange behavior of a larger directory, that a downgr= ade > > of the kernel cannot repair. >=20 > TL;DR: problem with an old userspace and 64 bit inodes. >=20 [...] >=20 > > # then it preceeds with getdents64 and fetches already fetched entr= ies > >=20 > > 27177 getdents64(3, { > >=20 > > {d_ino=3D4303329151, d_off=3D78, d_type=3DDT_UNKNOWN, = d_reclen=3D32, > > d_name=3D"Black_Swan"} > ^^^^^^^^ >=20 > And the next valid entry in the directory is offset=3D78. >=20 > So, what it looks like to me is that whatever is parsing the > linux_dirent returned by the getdents64() call is choking on the 64 > bit inode number. >=20 > Now, given that strace is parsing it correctly, this implies that > whatever is issuing the getdents64 call is not parsing the > linux_dirent64 structure correctly. In fact, I suspect what is > happening is that userspace is incorrectly using a struct > linux_dirent to parse the results and hence it's seeing > d_off/d_type/d_reclen being invalid due to the resultant structure > misalignment. >=20 > Further, this is being seen by multiple different vectors, which > indicates that it is probably the readdir() glibc call that is > buggy, and not any of the applications. Well, than the python script and ls should fall flat on their faces, wh= ich=20 they do not.. Also such a blatant misinterpretation should cause more h= avoc,=20 but most other stat values seem to match expectations.=20 Some kind of subtle wreckage happens here.. > First solution: upgrade to a modern userspace. I wish, but I cannot ATM. > Second solution: Run 3.8.1, make sure you mount with inode32, and > then run the xfs_reno tool mentioned on this page: > > http://xfs.org/index.php/Unfinished_work >=20 > to find all the inodes with inode numbers larger than 32 > bits and move them to locations with smaller inode numbers. Okay, I would like to take that route. I've updated the xfsprogs, xfsdump and xfstests packages in my openSUSE= build=20 service repo home:frispete:tools to current versions today, and plan to= submit=20 them to Factory. openSUSE is always lagging in this area. I've tried to include a build of the xfs_reno tool in xfsprogs, since, = as you=20 mentioned, others might have a similar need soon. Unfortunately I faile= d so=20 far, because it is using some attr_multi and attr_list interfaces, that= aren't=20 part of the xfsprogs visible API anymore. Only the handle(3) man page r= efers=20 to them. Attached is my current state: I've relocated the patch to xfsprogs 3.1.= 9,=20 because it already carries all the necessary headers (apart from attr_m= ulti=20 and attr_list). The attr interfaces seem to be collected in libhandle n= ow,=20 hence I've added it to the build.=20 But now I'm stuck. It's not obvious for me, how the attr_multi_by_handl= e and=20 attr_list_by_handle are supposed to replace the ones that xfs_reno uses= , and=20 documentation of this stuff is, hmm, sparse.. Could somebody with deeper insight have a look? TIA && cheers, Pete --nextPart5192251.cl8ZghraCZ Content-Disposition: attachment; filename="xfs_reno.patch" Content-Transfer-Encoding: 7Bit Content-Type: text/x-patch; charset="UTF-8"; name="xfs_reno.patch" From: "Barry Naujok" Date: 2007-10-04 4:25:16 Message-ID: op.tznnweh23jf8g2 () pc-bnaujok ! melbourne ! sgi ! com The attached tool allows an inode64 filesystem to be converted to inode32. For this to work, the filesystem has to be mounted inode32 before it's run. Relocated to xfsprogs by H.P. Jansen Index: b/man/man8/xfs_reno.8 =================================================================== --- /dev/null +++ b/man/man8/xfs_reno.8 @@ -0,0 +1,117 @@ +.TH xfs_reno 8 +.SH NAME +xfs_reno \- renumber XFS inodes +.SH SYNOPSIS +.B xfs_reno +[ +.B \-fnpqv +] [ +.B \-P +.I interval +] +.I path +.br +.B xfs_reno \-r +.I recover_file +.SH DESCRIPTION +.B xfs_reno +is applicable only to XFS filesystems. +.PP +.B xfs_reno +renumbers inodes. XFS supports 64-bit inode numbers, although by +default it will avoid creating inodes with numbers greater than +what can be contained within a 32-bit number. If a filesystem does +contain inode numbers greater than 32-bits, then this can conflict with +applications that do not support them. +To recover from this situation previously, affected files would need +to be copied (and so get a new inode number) and the old version +removed. This can be time consuming and impractical for very large +files and filesystems. +.B xfs_reno +can be used to renumber such inodes quickly. +.B xfs_reno +will copy the inodes of affected files and move the data from the old +inode to the new without having to copy the data. +.B xfs_reno +relies on XFS in the kernel to allocate a new inode number, so if the +filesystem has been mounted with the +.I inode64 +mount option, the new inodes will quite possibly have inode numbers +greater than 32-bits. +.PP +.B xfs_reno +should only be used on a filesystem where it is necessary to +renumber inodes. Use of +.B xfs_reno +on a regular basis is +.IR "not recommended" . +Apart from application compatibility, there is no particular advantage +to be had from renumbering inodes. +.PP +.B xfs_reno +works by traversing a directory tree, scanning all the directories +and noting which files require renumbering. Once the scanning phase +is done, it will process the appropriate files and directories. The +directory's absolute pathname must be given to +.BR xfs_reno . +The following options are accepted by +.BR xfs_reno . +.TP +.B \-f +Force conversion on all inodes, rather than just those with a 64-bit +inode number. This is not particularly useful except for debugging +purposes. +.TP +.B \-n +Do nothing, perform a trial run. +.TP +.B \-v +Increases the verbosity of progress and error messages. Additional +.BR \-v 's +can be used to further increase verbosity. +.TP +.B \-q +Do not report progress, only errors. +.TP +.B \-p +Show progress status. +.TP +.BI \-P " seconds" +Set the interval for the progress status in seconds. The default is 1 +second. +.TP +.B \-r +Recover from an interrupted run. If +.B xfs_reno +is interrupted, it will leave a file called +.I xfs_reno.recover +in the directory specified on the command line. This file will +contain enough information so that +.B xfs_reno +can either finish processing the file it was working on when +interrupted or back out the last change it made, depending on how far +through the process it had progressed. +.B xfs_reno +will only recover the single file it was working on so it will need +to be run again on the directory to be sure that all the appropriate +inodes have been converted. +.SH EXAMPLES +To renumber inodes with 64-bit inode numbers: +.IP +.B # xfs_reno -p /path/to/directory +.PP +To recover from an interrupted run: +.IP +.B # xfs_reno -r /path/to/directory/xfs_reno.recover +.PP +.SH FILES +.PD +.TP +.I /path/xfs_reno.recover +records the state where renumbering was interrupted. +.PD +.SH SEE ALSO +.BR xfs_fsr (8), +.BR xfs_ncheck (8), +.BR fstab (5), +.BR xfs (5). Index: b/reno/Makefile =================================================================== --- /dev/null +++ b/reno/Makefile @@ -0,0 +1,19 @@ +# +# Copyright (c) 2007 Silicon Graphics, Inc. All Rights Reserved. +# + +TOPDIR = .. +include $(TOPDIR)/include/builddefs + +LTCOMMAND = xfs_reno +CFILES = xfs_reno.c +LLDLIBS = $(LIBATTR) + +default: $(LTCOMMAND) + +include $(BUILDRULES) + +install: default + $(INSTALL) -m 755 -d $(PKG_SBIN_DIR) + $(LTINSTALL) -m 755 $(LTCOMMAND) $(PKG_SBIN_DIR) +install-dev: Index: b/reno/xfs_reno.c =================================================================== --- /dev/null +++ b/reno/xfs_reno.c @@ -0,0 +1,2040 @@ +/* + * Copyright (c) 2007 Silicon Graphics, Inc. + * All Rights Reserved. + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License as + * published by the Free Software Foundation. + * + * This program is distributed in the hope that it would be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + */ + +/* + * xfs_reno - renumber 64-bit inodes + * + * xfs_reno [-f] [-n] [-p] [-q] [-v] [-P seconds] path ... + * xfs_reno [-r] path ... + * + * Renumbers all inodes > 32 bits into 32 bit space. Requires the filesytem + * to be mounted with inode32. + * + * -f force conversion on all inodes rather than just + * those with a 64bit inode number. + * -n nothing, do not renumber inodes + * -p show progress status. + * -q quiet, do not report progress, only errors. + * -v verbose, more -v's more verbose. + * -P seconds set the interval for the progress status in seconds. + * -r recover from an interrupted run. + */ + +#include + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#define ATTRBUFSIZE 1024 + +#define SCAN_PHASE 0x00 +#define DIR_PHASE 0x10 /* nothing done or all done */ +#define DIR_PHASE_1 0x11 /* target dir created */ +#define DIR_PHASE_2 0x12 /* temp dir created */ +#define DIR_PHASE_3 0x13 /* attributes backed up to temp */ +#define DIR_PHASE_4 0x14 /* dirents moved to target dir */ +#define DIR_PHASE_5 0x15 /* attributes applied to target dir */ +#define DIR_PHASE_6 0x16 /* src dir removed */ +#define DIR_PHASE_7 0x17 /* temp dir removed */ +#define DIR_PHASE_MAX 0x17 +#define FILE_PHASE 0x20 /* nothing done or all done */ +#define FILE_PHASE_1 0x21 /* temp file created */ +#define FILE_PHASE_2 0x22 /* swapped extents */ +#define FILE_PHASE_3 0x23 /* unlinked source */ +#define FILE_PHASE_4 0x24 /* renamed temp to source name */ +#define FILE_PHASE_MAX 0x24 +#define SLINK_PHASE 0x30 /* nothing done or all done */ +#define SLINK_PHASE_1 0x31 /* temp symlink created */ +#define SLINK_PHASE_2 0x32 /* symlink attrs copied */ +#define SLINK_PHASE_3 0x33 /* unlinked source */ +#define SLINK_PHASE_4 0x34 /* renamed temp to source name */ +#define SLINK_PHASE_MAX 0x34 + +static void update_recoverfile(void); +#define SET_PHASE(x) (cur_phase = x, update_recoverfile()) + +#define LOG_ERR 0 +#define LOG_NORMAL 1 +#define LOG_INFO 2 +#define LOG_DEBUG 3 +#define LOG_NITTY 4 + +#define NH_BUCKETS 65536 +#define NH_HASH(ino) (nodehash + ((ino) % NH_BUCKETS)) + +typedef struct { + xfs_ino_t ino; + int ftw_flags; + nlink_t numpaths; + char **paths; +} bignode_t; + +typedef struct { + bignode_t *nodes; + uint64_t listlen; + uint64_t lastnode; +} nodelist_t; + +static const char *cmd_prefix = "xfs_reno_"; + +static char *progname; +static int log_level = LOG_NORMAL; +static int force_all; +static nodelist_t *nodehash; +static int realuid; +static uint64_t numdirnodes; +static uint64_t numfilenodes; +static uint64_t numslinknodes; +static uint64_t numdirsdone; +static uint64_t numfilesdone; +static uint64_t numslinksdone; +static int poll_interval; +static time_t starttime; +static bignode_t *cur_node; +static char *cur_target; +static char *cur_temp; +static int cur_phase; +static int highest_numpaths; +static char *recover_file; +static int recover_fd; +static volatile int poll_output; +static int global_rval; + +/* + * message handling + */ +static void +log_message( + int level, + char *fmt, ...) +{ + char buf[1024]; + va_list ap; + + if (log_level < level) + return; + + va_start(ap, fmt); + vsnprintf(buf, 1024, fmt, ap); + va_end(ap); + + printf("%c%s: %s\n", poll_output ? '\n' : '\r', progname, buf); + poll_output = 0; +} + +static void +err_message( + char *fmt, ...) +{ + char buf[1024]; + va_list ap; + + va_start(ap, fmt); + vsnprintf(buf, 1024, fmt, ap); + va_end(ap); + + fprintf(stderr, "%c%s: %s\n", poll_output ? '\n' : '\r', progname, buf); + poll_output = 0; +} + +static void +err_nomem(void) +{ + err_message(_("Out of memory")); +} + +static void +err_open( + const char *s) +{ + err_message(_("Cannot open %s: %s"), s, strerror(errno)); +} + +static void +err_not_xfs( + const char *s) +{ + err_message(_("%s is not on an XFS filesystem"), s); +} + +static void +err_stat( + const char *s) +{ + err_message(_("Cannot stat %s: %s\n"), s, strerror(errno)); +} + +/* + * usage message + */ +static void +usage(void) +{ + fprintf(stderr, _("%s [-fnpqv] [-P ] [-r] \n"), + progname); + exit(1); +} + + +/* + * XFS interface functions + */ + +static int +xfs_bulkstat_single(int fd, xfs_ino_t *lastip, xfs_bstat_t *ubuffer) +{ + xfs_fsop_bulkreq_t bulkreq; + + bulkreq.lastip = (__u64 *)lastip; + bulkreq.icount = 1; + bulkreq.ubuffer = ubuffer; + bulkreq.ocount = NULL; + return ioctl(fd, XFS_IOC_FSBULKSTAT_SINGLE, &bulkreq); +} + +static int +xfs_swapext(int fd, xfs_swapext_t *sx) +{ + return ioctl(fd, XFS_IOC_SWAPEXT, sx); +} + +static int +xfs_getxattr(int fd, struct fsxattr *attr) +{ + return ioctl(fd, XFS_IOC_FSGETXATTR, attr); +} + +static int +xfs_setxattr(int fd, struct fsxattr *attr) +{ + return ioctl(fd, XFS_IOC_FSSETXATTR, attr); +} + +/* + * A hash table of inode numbers and associated paths. + */ +static nodelist_t * +init_nodehash(void) +{ + int i; + + nodehash = calloc(NH_BUCKETS, sizeof(nodelist_t)); + if (nodehash == NULL) { + err_nomem(); + return NULL; + } + + for (i = 0; i < NH_BUCKETS; i++) { + nodehash[i].nodes = NULL; + nodehash[i].lastnode = 0; + nodehash[i].listlen = 0; + } + + return nodehash; +} + +static void +free_nodehash(void) +{ + int i, j, k; + + for (i = 0; i < NH_BUCKETS; i++) { + bignode_t *nodes = nodehash[i].nodes; + + for (j = 0; j < nodehash[i].lastnode; j++) { + for (k = 0; k < nodes[j].numpaths; k++) { + free(nodes[j].paths[k]); + } + free(nodes[j].paths); + } + + free(nodes); + } + free(nodehash); +} + +static nlink_t +add_path( + bignode_t *node, + const char *path) +{ + node->paths = realloc(node->paths, + sizeof(char *) * (node->numpaths + 1)); + if (node->paths == NULL) { + err_nomem(); + exit(1); + } + + node->paths[node->numpaths] = strdup(path); + if (node->paths[node->numpaths] == NULL) { + err_nomem(); + exit(1); + } + + node->numpaths++; + if (node->numpaths > highest_numpaths) + highest_numpaths = node->numpaths; + + return node->numpaths; +} + +static bignode_t * +add_node( + nodelist_t *list, + xfs_ino_t ino, + int ftw_flags, + const char *path) +{ + bignode_t *node; + + if (list->lastnode >= list->listlen) { + list->listlen += 500; + list->nodes = realloc(list->nodes, + sizeof(bignode_t) * list->listlen); + if (list->nodes == NULL) { + err_nomem(); + return NULL; + } + } + + node = list->nodes + list->lastnode; + + node->ino = ino; + node->ftw_flags = ftw_flags; + node->paths = NULL; + node->numpaths = 0; + add_path(node, path); + + list->lastnode++; + + return node; +} + +static bignode_t * +find_node( + xfs_ino_t ino) +{ + int i; + nodelist_t *nodelist; + bignode_t *nodes; + + nodelist = NH_HASH(ino); + nodes = nodelist->nodes; + + for(i = 0; i < nodelist->lastnode; i++) { + if (nodes[i].ino == ino) { + return &nodes[i]; + } + } + + return NULL; +} + +static bignode_t * +add_node_path( + xfs_ino_t ino, + int ftw_flags, + const char *path) +{ + nodelist_t *nodelist; + bignode_t *node; + + log_message(LOG_NITTY, "add_node_path: ino %llu, path %s", ino, path); + + node = find_node(ino); + if (node == NULL) { + nodelist = NH_HASH(ino); + return add_node(nodelist, ino, ftw_flags, path); + } + + add_path(node, path); + return node; +} + +static void +dump_node( + char *msg, + bignode_t *node) +{ + int k; + + if (log_level < LOG_DEBUG) + return; + + log_message(LOG_DEBUG, "%s: %llu %llu %s", msg, node->ino, + node->numpaths, node->paths[0]); + + for (k = 1; k < node->numpaths; k++) + log_message(LOG_DEBUG, "\t%s", node->paths[k]); +} + +static void +dump_nodehash(void) +{ + int i, j; + + if (log_level < LOG_NITTY) + return; + + for (i = 0; i < NH_BUCKETS; i++) { + bignode_t *nodes = nodehash[i].nodes; + for (j = 0; j < nodehash[i].lastnode; j++, nodes++) + dump_node("nodehash", nodes); + } +} + +static int +for_all_nodes( + int (*fn)(bignode_t *node), + int ftw_flags, + int quit_on_error) +{ + int i; + int j; + int rval = 0; + + for (i = 0; i < NH_BUCKETS; i++) { + bignode_t *nodes = nodehash[i].nodes; + + for (j = 0; j < nodehash[i].lastnode; j++, nodes++) { + if (nodes->ftw_flags == ftw_flags) { + rval = fn(nodes); + if (rval && quit_on_error) + goto quit; + } + } + } + +quit: + return rval; +} + +/* + * Adds appropriate files to the inode hash table + */ +static int +nftw_addnodes( + const char *path, + const struct stat64 *st, + int flags, + struct FTW *sntfw) +{ + if (st->st_ino <= XFS_MAXINUMBER_32 && !force_all) + return 0; + + if (flags == FTW_F) + numfilenodes++; + else if (flags == FTW_D) + numdirnodes++; + else if (flags == FTW_SL) + numslinknodes++; + else + return 0; + + add_node_path(st->st_ino, flags, path); + + return 0; +} + +/* + * Attribute cloning code - most of this is here because attr_copy does not + * let us pick and choose which attributes we want to copy. + */ + +attr_multiop_t attr_ops[ATTR_MAX_MULTIOPS]; + +/* + * Grab attributes specified in attr_ops from source file and write them + * out on the destination file. + */ + +static int +attr_replicate( + char *source, + char *target, + int count) +{ + int j, k; + + if (attr_multi(source, attr_ops, count, ATTR_DONTFOLLOW) < 0) + return -1; + + for (k = 0; k < count; k++) { + if (attr_ops[k].am_error) { + err_message(_("Error %d getting attribute"), + attr_ops[k].am_error); + break; + } + attr_ops[k].am_opcode = ATTR_OP_SET; + } + if (attr_multi(target, attr_ops, k, ATTR_DONTFOLLOW) < 0) + err_message("on attr_multif set"); + for (j = 0; j < k; j++) { + if (attr_ops[j].am_error) { + err_message(_("Error %d setting attribute"), + attr_ops[j].am_error); + return -1; + } + } + + return 0; +} + +/* + * Copy all the attributes specified from src to dst. + */ + +static int +attr_clone_copy( + char *source, + char *target, + char *list_buf, + char *attr_buf, + int buf_len, + int flags) +{ + attrlist_t *alist; + attrlist_ent_t *attr; + attrlist_cursor_t cursor; + int space, i, j; + char *ptr; + + bzero((char *)&cursor, sizeof(cursor)); + do { + if (attr_list(source, list_buf, ATTRBUFSIZE, + flags | ATTR_DONTFOLLOW, &cursor) < 0) { + err_message("on attr_listf"); + return -1; + } + + alist = (attrlist_t *)list_buf; + + space = buf_len; + ptr = attr_buf; + for (j = 0, i = 0; i < alist->al_count; i++) { + attr = ATTR_ENTRY(list_buf, i); + if (space < attr->a_valuelen) { + if (attr_replicate(source, target, j) < 0) + return -1; + j = 0; + space = buf_len; + ptr = attr_buf; + } + attr_ops[j].am_opcode = ATTR_OP_GET; + attr_ops[j].am_attrname = attr->a_name; + attr_ops[j].am_attrvalue = ptr; + attr_ops[j].am_length = (int) attr->a_valuelen; + attr_ops[j].am_flags = flags; + attr_ops[j].am_error = 0; + j++; + ptr += attr->a_valuelen; + space -= attr->a_valuelen; + } + + log_message(LOG_NITTY, "copying attribute %d", i); + + if (j) { + if (attr_replicate(source, target, j) < 0) + return -1; + } + + } while (alist->al_more); + + return 0; +} + +static int +clone_attribs( + char *source, + char *target) +{ + char list_buf[ATTRBUFSIZE]; + char *attr_buf; + int rval; + + attr_buf = malloc(ATTR_MAX_VALUELEN * 2); + if (attr_buf == NULL) { + err_nomem(); + return -1; + } + rval = attr_clone_copy(source, target, list_buf, attr_buf, + ATTR_MAX_VALUELEN * 2, 0); + if (rval == 0) + rval = attr_clone_copy(source, target, list_buf, attr_buf, + ATTR_MAX_VALUELEN * 2, ATTR_ROOT); + if (rval == 0) + rval = attr_clone_copy(source, target, list_buf, attr_buf, + ATTR_MAX_VALUELEN * 2, ATTR_SECURE); + free(attr_buf); + return rval; +} + +static int +dup_attributes( + char *source, + int sfd, + char *target, + int tfd) +{ + struct stat64 st; + struct timeval tv[2]; + struct fsxattr fsx; + + if (fstat64(sfd, &st) < 0) { + err_stat(source); + return -1; + } + + if (xfs_getxattr(sfd, &fsx) < 0) { + err_stat(source); + return -1; + } + + tv[0].tv_sec = st.st_atim.tv_sec; + tv[0].tv_usec = st.st_atim.tv_nsec / 1000; + tv[1].tv_sec = st.st_mtim.tv_sec; + tv[1].tv_usec = st.st_mtim.tv_nsec / 1000; + + if (futimes(tfd, tv) < 0) + err_message(_("%s: Cannot update target times"), target); + + if (fchown(tfd, st.st_uid, st.st_gid) < 0) { + err_message(_("%s: Cannot change target ownership to " + "uid(%d) gid(%d)"), target, + st.st_uid, st.st_gid); + + if (fchmod(tfd, st.st_mode & ~(S_ISUID | S_ISGID)) < 0) + err_message(_("%s: Cannot change target mode " + "to (%o)"), target, st.st_mode); + } else if (fchmod(tfd, st.st_mode) < 0) + err_message(_("%s: Cannot change target mode to (%o)"), + target, st.st_mode); + + if (xfs_setxattr(tfd, &fsx) < 0) + err_message(_("%s: Cannet set target extended " + "attributes"), target); + + return clone_attribs(source, target); +} + +static int +move_dirents( + char *srcpath, + char *targetpath, + int *move_count) +{ + int rval = 0; + DIR *srcd; + struct dirent64 *dp; + char srcname[PATH_MAX]; + char targetname[PATH_MAX]; + + *move_count = 0; + + srcd = opendir(srcpath); + if (srcd == NULL) { + err_open(srcpath); + return 1; + } + + while ((dp = readdir64(srcd)) != NULL) { + if (dp->d_ino == 0 || !strcmp(dp->d_name, ".") || + !strcmp(dp->d_name, "..")) + continue; + + if (strlen(srcpath) + 1 + strlen(dp->d_name) >= + sizeof(srcname) - 1) { + + err_message(_("%s/%s: Name too long"), srcpath, + dp->d_name); + rval = 1; + goto quit; + } + + sprintf(srcname, "%s/%s", srcpath, dp->d_name); + sprintf(targetname, "%s/%s", targetpath, dp->d_name); + + rval = rename(srcname, targetname); + if (rval != 0) { + err_message(_("failed to rename: \'%s\' to \'%s\'"), + srcname, targetname); + goto quit; + } + + log_message(LOG_DEBUG, "rename %s -> %s", srcname, targetname); + + (*move_count)++; + } + +quit: + closedir(srcd); + return rval; +} + +static int +process_dir( + bignode_t *node) +{ + int sfd = -1; + int tfd = -1; + int targetfd = -1; + int rval = 0; + int move_count = 0; + char *srcname = NULL; + char *pname = NULL; + struct stat64 s1; + struct fsxattr fsx; + char target[PATH_MAX] = ""; + + SET_PHASE(DIR_PHASE); + + dump_node("directory", node); + + cur_node = node; + srcname = node->paths[0]; + + if (stat64(srcname, &s1) < 0) { + if (errno != ENOENT) { + err_stat(srcname); + global_rval |= 2; + } + goto quit; + } + if (s1.st_ino <= XFS_MAXINUMBER_32 && !force_all) { + /* + * This directory has already changed ino's, probably due + * to being moved during processing of a parent directory. + */ + log_message(LOG_DEBUG, "process_dir: skipping %s", srcname); + goto quit; + } + + rval = 1; + + sfd = open(srcname, O_RDONLY); + if (sfd < 0) { + err_open(srcname); + goto quit; + } + + if (!platform_test_xfs_fd(sfd)) { + err_not_xfs(srcname); + goto quit; + } + + if (xfs_getxattr(sfd, &fsx) < 0) { + err_message(_("failed to get inode attrs: %s"), srcname); + goto quit; + } + if (fsx.fsx_xflags & (XFS_XFLAG_IMMUTABLE | XFS_XFLAG_APPEND)) { + err_message(_("%s: immutable/append, ignoring"), srcname); + global_rval |= 2; + rval = 0; + goto quit; + } + + /* mkdir parent/target */ + pname = strdup(srcname); + if (pname == NULL) { + err_nomem(); + goto quit; + } + dirname(pname); + sprintf(target, "%s/%sXXXXXX", pname, cmd_prefix); + if (mkdtemp(target) == NULL) { + err_message(_("Unable to create directory copy: %s"), srcname); + goto quit; + } + SET_PHASE(DIR_PHASE_1); + + cur_target = strdup(target); + if (!cur_target) { + err_nomem(); + goto quit; + } + + sprintf(target, "%s/%sXXXXXX", pname, cmd_prefix); + if (mkdtemp(target) == NULL) { + err_message(_("unable to create tmp directory copy")); + goto quit; + } + SET_PHASE(DIR_PHASE_2); + + cur_temp = strdup(target); + if (!cur_temp) { + err_nomem(); + goto quit; + } + + tfd = open(cur_temp, O_RDONLY); + if (tfd < 0) { + err_open(cur_temp); + goto quit; + } + + targetfd = open(cur_target, O_RDONLY); + if (tfd < 0) { + err_open(cur_target); + goto quit; + } + + + /* copy timestamps, attribs and EAs, to cur_temp */ + rval = dup_attributes(srcname, sfd, cur_temp, tfd); + if (rval != 0) { + err_message(_("unable to duplicate directory attributes: %s"), + srcname); + goto quit_unlink; + } + + SET_PHASE(DIR_PHASE_3); + + /* move src dirents to cur_target (this changes timestamps on src) */ + rval = move_dirents(srcname, cur_target, &move_count); + if (rval != 0) { + err_message(_("unable to move directory contents: %s to %s"), + srcname, cur_target); + /* uh oh, move everything back... */ + if (move_count > 0) + goto quit_undo; + } + + SET_PHASE(DIR_PHASE_4); + + /* copy timestamps, attribs and EAs from cur_temp to cur_target */ + rval = dup_attributes(cur_temp, tfd, cur_target, targetfd); + if (rval != 0) { + err_message(_("unable to duplicate directory attributes: %s"), + cur_temp); + goto quit_unlink; + } + + SET_PHASE(DIR_PHASE_5); + + /* rmdir src */ + rval = rmdir(srcname); + if (rval != 0) { + err_message(_("unable to remove directory: %s"), srcname); + goto quit_undo; + } + + SET_PHASE(DIR_PHASE_6); + + rval = rmdir(cur_temp); + if (rval != 0) + err_message(_("unable to remove tmp directory: %s"), cur_temp); + + SET_PHASE(DIR_PHASE_7); + + /* rename cur_target src */ + rval = rename(cur_target, srcname); + if (rval != 0) { + /* + * we can't abort since the src dir is now gone. + * let the admin clean this one up + */ + err_message(_("unable to rename directory: %s to %s"), + cur_target, srcname); + } + goto quit; + + quit_undo: + if (move_dirents(cur_target, srcname, &move_count) != 0) { + /* oh, dear lord... let the admin clean this one up */ + err_message(_("unable to move directory contents back: %s to %s"), + cur_target, srcname); + goto quit; + } + SET_PHASE(DIR_PHASE_3); + + quit_unlink: + rmdir(cur_target); + rmdir(cur_temp); + + quit: + + SET_PHASE(DIR_PHASE); + + if (sfd >= 0) + close(sfd); + if (tfd >= 0) + close(tfd); + if (targetfd >= 0) + close(targetfd); + + free(pname); + free(cur_target); + free(cur_temp); + + cur_target = NULL; + cur_temp = NULL; + cur_node = NULL; + numdirsdone++; + return rval; +} + +static int +process_file( + bignode_t *node) +{ + int sfd = -1; + int tfd = -1; + int i = 0; + int rval = 0; + struct stat64 s1; + char *srcname = NULL; + char *pname = NULL; + xfs_swapext_t sx; + xfs_bstat_t bstatbuf; + struct fsxattr fsx; + char target[PATH_MAX] = ""; + + SET_PHASE(FILE_PHASE); + + dump_node("file", node); + + cur_node = node; + srcname = node->paths[0]; + + bzero(&s1, sizeof(s1)); + bzero(&bstatbuf, sizeof(bstatbuf)); + bzero(&sx, sizeof(sx)); + + if (stat64(srcname, &s1) < 0) { + if (errno != ENOENT) { + err_stat(srcname); + global_rval |= 2; + } + goto quit; + } + if (s1.st_ino <= XFS_MAXINUMBER_32 && !force_all) + /* this file has changed, and no longer needs processing */ + goto quit; + + /* open and sync source */ + sfd = open(srcname, O_RDWR | O_DIRECT); + if (sfd < 0) { + err_open(srcname); + rval = 1; + goto quit; + } + if (!platform_test_xfs_fd(sfd)) { + err_not_xfs(srcname); + rval = 1; + goto quit; + } + if (fsync(sfd) < 0) { + err_message(_("sync failed: %s: %s"), + srcname, strerror(errno)); + rval = 1; + goto quit; + } + + + /* + * Check if a mandatory lock is set on the file to try and + * avoid blocking indefinitely on the reads later. Note that + * someone could still set a mandatory lock after this check + * but before all reads have completed to block xfs_reno reads. + * This change just closes the window a bit. + */ + if ((s1.st_mode & S_ISGID) && !(s1.st_mode & S_IXGRP)) { + struct flock fl; + + fl.l_type = F_RDLCK; + fl.l_whence = SEEK_SET; + fl.l_start = (off_t)0; + fl.l_len = 0; + if (fcntl(sfd, F_GETLK, &fl) < 0 ) { + if (log_level >= LOG_DEBUG) + err_message("locking check failed: %s", + srcname); + global_rval |= 2; + goto quit; + } + if (fl.l_type != F_UNLCK) { + if (log_level >= LOG_DEBUG) + err_message("mandatory lock: %s: ignoring", + srcname); + global_rval |= 2; + goto quit; + } + } + + if (xfs_getxattr(sfd, &fsx) < 0) { + err_message(_("failed to get inode attrs: %s"), srcname); + rval = 1; + goto quit; + } + if (fsx.fsx_xflags & (XFS_XFLAG_IMMUTABLE | XFS_XFLAG_APPEND)) { + err_message(_("%s: immutable/append, ignoring"), srcname); + global_rval |= 2; + goto quit; + } + + rval = 1; + + if (realuid != 0 && realuid != s1.st_uid) { + errno = EACCES; + err_open(srcname); + goto quit; + } + + /* creat target */ + pname = strdup(srcname); + if (pname == NULL) { + err_nomem(); + goto quit; + } + dirname(pname); + sprintf(target, "%s/%sXXXXXX", pname, cmd_prefix); + tfd = mkstemp(target); + if (tfd < 0) { + err_message("unable to create file copy"); + goto quit; + } + cur_target = strdup(target); + if (cur_target == NULL) { + err_nomem(); + goto quit; + } + + SET_PHASE(FILE_PHASE_1); + + /* Setup direct I/O */ + if (fcntl(tfd, F_SETFL, O_DIRECT) < 0 ) { + err_message(_("could not set O_DIRECT for %s on tmp: %s"), + srcname, target); + unlink(target); + goto quit; + } + + /* copy attribs & EAs to target */ + if (dup_attributes(srcname, sfd, target, tfd) != 0) { + err_message(_("unable to duplicate file attributes: %s"), + srcname); + unlink(target); + goto quit; + } + + if (xfs_bulkstat_single(sfd, &s1.st_ino, &bstatbuf) < 0) { + err_message(_("unable to bulkstat source file: %s"), + srcname); + unlink(target); + goto quit; + } + + if (bstatbuf.bs_ino != s1.st_ino) { + err_message(_("bulkstat of source file returned wrong inode: %s"), + srcname); + unlink(target); + goto quit; + } + + ftruncate64(tfd, bstatbuf.bs_size); + + /* swapextents src target */ + sx.sx_stat = bstatbuf; /* struct copy */ + sx.sx_version = XFS_SX_VERSION; + sx.sx_fdtarget = sfd; + sx.sx_fdtmp = tfd; + sx.sx_offset = 0; + sx.sx_length = bstatbuf.bs_size; + + /* Swap the extents */ + rval = xfs_swapext(sfd, &sx); + if (rval < 0) { + if (log_level >= LOG_DEBUG) { + switch (errno) { + case ENOTSUP: + err_message("%s: file type not supported", + srcname); + break; + case EFAULT: + /* The file has changed since we started the copy */ + err_message("%s: file modified, " + "inode renumber aborted: %ld", + srcname, bstatbuf.bs_size); + break; + case EBUSY: + /* Timestamp has changed or mmap'ed file */ + err_message("%s: file busy", srcname); + break; + default: + err_message(_("Swap extents failed: %s: %s"), + srcname, strerror(errno)); + break; + } + } else + err_message(_("Swap extents failed: %s: %s"), + srcname, strerror(errno)); + goto quit; + } + + if (bstatbuf.bs_dmevmask | bstatbuf.bs_dmstate) { + struct fsdmidata fssetdm; + + /* Set the DMAPI Fields. */ + fssetdm.fsd_dmevmask = bstatbuf.bs_dmevmask; + fssetdm.fsd_padding = 0; + fssetdm.fsd_dmstate = bstatbuf.bs_dmstate; + + if (ioctl(tfd, XFS_IOC_FSSETDM, (void *)&fssetdm ) < 0) + err_message(_("attempt to set DMI attributes " + "of %s failed"), target); + } + + SET_PHASE(FILE_PHASE_2); + + /* unlink src */ + rval = unlink(srcname); + if (rval != 0) { + err_message(_("unable to remove file: %s"), srcname); + goto quit; + } + + SET_PHASE(FILE_PHASE_3); + + /* rename target src */ + rval = rename(target, srcname); + if (rval != 0) { + /* + * we can't abort since the src file is now gone. + * let the admin clean this one up + */ + err_message(_("unable to rename file: %s to %s"), + target, srcname); + goto quit; + } + + SET_PHASE(FILE_PHASE_4); + + /* for each hardlink, unlink and creat pointing to target */ + for (i = 1; i < node->numpaths; i++) { + /* unlink src */ + rval = unlink(node->paths[i]); + if (rval != 0) { + err_message(_("unable to remove file: %s"), + node->paths[i]); + goto quit; + } + + rval = link(srcname, node->paths[i]); + if (rval != 0) { + err_message("unable to link to file: %s", srcname); + goto quit; + } + numfilesdone++; + } + + quit: + cur_node = NULL; + + SET_PHASE(FILE_PHASE); + + if (sfd >= 0) + close(sfd); + if (tfd >= 0) + close(tfd); + + free(pname); + free(cur_target); + + cur_target = NULL; + + numfilesdone++; + return rval; +} + + +static int +process_slink( + bignode_t *node) +{ + int i = 0; + int rval = 0; + struct stat64 st; + char *srcname = NULL; + char *pname = NULL; + char target[PATH_MAX] = ""; + char linkbuf[PATH_MAX]; + + SET_PHASE(SLINK_PHASE); + + dump_node("symlink", node); + + cur_node = node; + srcname = node->paths[0]; + + if (lstat64(srcname, &st) < 0) { + if (errno != ENOENT) { + err_stat(srcname); + global_rval |= 2; + } + goto quit; + } + if (st.st_ino <= XFS_MAXINUMBER_32 && !force_all) + /* this file has changed, and no longer needs processing */ + goto quit; + + rval = 1; + + i = readlink(srcname, linkbuf, sizeof(linkbuf) - 1); + if (i < 0) { + err_message(_("unable to read symlink: %s"), srcname); + goto quit; + } + linkbuf[i] = '\0'; + + if (realuid != 0 && realuid != st.st_uid) { + errno = EACCES; + err_open(srcname); + goto quit; + } + + /* create target */ + pname = strdup(srcname); + if (pname == NULL) { + err_nomem(); + goto quit; + } + dirname(pname); + + sprintf(target, "%s/%sXXXXXX", pname, cmd_prefix); + if (mktemp(target) == NULL) { + err_message(_("unable to create temp symlink name")); + goto quit; + } + cur_target = strdup(target); + if (cur_target == NULL) { + err_nomem(); + goto quit; + } + + if (symlink(linkbuf, target) != 0) { + err_message(_("unable to create symlink: %s"), target); + goto quit; + } + + SET_PHASE(SLINK_PHASE_1); + + /* copy ownership & EAs to target */ + if (lchown(target, st.st_uid, st.st_gid) < 0) { + err_message(_("%s: Cannot change target ownership to " + "uid(%d) gid(%d)"), target, + st.st_uid, st.st_gid); + unlink(target); + goto quit; + } + + if (clone_attribs(srcname, target) != 0) { + err_message(_("unable to duplicate symlink attributes: %s"), + srcname); + unlink(target); + goto quit; + } + + SET_PHASE(SLINK_PHASE_2); + + /* unlink src */ + rval = unlink(srcname); + if (rval != 0) { + err_message(_("unable to remove symlink: %s"), srcname); + goto quit; + } + + SET_PHASE(SLINK_PHASE_3); + + /* rename target src */ + rval = rename(target, srcname); + if (rval != 0) { + /* + * we can't abort since the src file is now gone. + * let the admin clean this one up + */ + err_message(_("unable to rename symlink: %s to %s"), + target, srcname); + goto quit; + } + + SET_PHASE(SLINK_PHASE_4); + + /* for each hardlink, unlink and creat pointing to target */ + for (i = 1; i < node->numpaths; i++) { + /* unlink src */ + rval = unlink(node->paths[i]); + if (rval != 0) { + err_message(_("unable to remove symlink: %s"), + node->paths[i]); + goto quit; + } + + rval = link(srcname, node->paths[i]); + if (rval != 0) { + err_message("unable to link to symlink: %s", srcname); + goto quit; + } + numslinksdone++; + } + + quit: + cur_node = NULL; + + SET_PHASE(SLINK_PHASE); + + free(pname); + free(cur_target); + + cur_target = NULL; + + numslinksdone++; + return rval; +} + +static int +open_recoverfile(void) +{ + recover_fd = open(recover_file, O_RDWR | O_SYNC | O_CREAT | O_EXCL, + 0600); + if (recover_fd < 0) { + if (errno == EEXIST) + err_message(_("Recovery file already exists, either " + "run '%s -r %s' or remove the file."), + progname, recover_file); + else + err_open(recover_file); + return 1; + } + + if (!platform_test_xfs_fd(recover_fd)) { + err_not_xfs(recover_file); + close(recover_fd); + return 1; + } + + return 0; +} + +static void +update_recoverfile(void) +{ + static const char null_file[] = "0\n0\n0\n\ntarget: \ntemp: \nend\n"; + static size_t buf_size = 0; + static char *buf = NULL; + int i, len; + + if (recover_fd <= 0) + return; + + if (cur_node == NULL || cur_phase == 0) { + /* inbetween processing or still scanning */ + lseek(recover_fd, 0, SEEK_SET); + write(recover_fd, null_file, sizeof(null_file)); + return; + } + + ASSERT(highest_numpaths > 0); + if (buf == NULL) { + buf_size = (highest_numpaths + 3) * PATH_MAX; + buf = malloc(buf_size); + if (buf == NULL) { + err_nomem(); + exit(1); + } + } + + len = sprintf(buf, "%d\n%llu\n%d\n", cur_phase, + (long long)cur_node->ino, cur_node->ftw_flags); + + for (i = 0; i < cur_node->numpaths; i++) + len += sprintf(buf + len, "%s\n", cur_node->paths[i]); + + len += sprintf(buf + len, "target: %s\ntemp: %s\nend\n", + cur_target, cur_temp); + + ASSERT(len < buf_size); + + lseek(recover_fd, 0, SEEK_SET); + ftruncate(recover_fd, 0); + write(recover_fd, buf, len); +} + +static void +cleanup(void) +{ + log_message(LOG_NORMAL, _("Interrupted -- cleaning up...")); + + free_nodehash(); + + log_message(LOG_NORMAL, _("Done.")); +} + +static void +sighandler(int sig) +{ + static char cycle[4] = "-\\|/"; + static uint64_t cur_cycle = 0; + double percent; + char *typename; + uint64_t nodes, done; + + alarm(0); + + if (sig != SIGALRM) { + cleanup(); + exit(1); + } + + if (cur_phase == SCAN_PHASE) { + if (log_level >= LOG_INFO) + fprintf(stderr, _("\r%llu files, %llu dirs and %llu " + "symlinks to renumber found... %c"), + (long long)numfilenodes, + (long long)numdirnodes, + (long long)numslinknodes, + cycle[cur_cycle % 4]); + else + fprintf(stderr, "\r%c", + cycle[cur_cycle % 4]); + cur_cycle++; + } else { + if (cur_phase >= DIR_PHASE && cur_phase <= DIR_PHASE_MAX) { + nodes = numdirnodes; + done = numdirsdone; + typename = _("dirs"); + } else + if (cur_phase >= FILE_PHASE && cur_phase <= FILE_PHASE_MAX) { + nodes = numfilenodes; + done = numfilesdone; + typename = _("files"); + } else { + nodes = numslinknodes; + done = numslinksdone; + typename = _("symlinks"); + } + percent = 100.0 * (double)done / (double)nodes; + if (percent > 100.0) + percent = 100.0; + if (log_level >= LOG_INFO) + fprintf(stderr, _("\r%.1f%%, %llu of %llu %s, " + "%u seconds elapsed"), percent, + (long long)done, (long long)nodes, + typename, (int)(time(0) - starttime)); + else + fprintf(stderr, "\r%.1f%%", percent); + } + poll_output = 1; + signal(SIGALRM, sighandler); + + if (poll_interval) + alarm(poll_interval); +} + +static int +read_recover_file( + char *recover_file, + bignode_t **node, + char **target, + char **temp, + int *phase) +{ + FILE *file; + int rval = 1; + ino_t ino; + int ftw_flags; + char buf[PATH_MAX + 10]; /* path + "target: " */ + struct stat64 s; + int first_path; + + /* + + A recovery file should look like: + + + + + + + target: + temp: + end + */ + + file = fopen(recover_file, "r"); + if (file == NULL) { + err_open(recover_file); + return 1; + } + + /* read phase */ + *phase = 0; + if (fgets(buf, PATH_MAX + 10, file) == NULL) { + err_message("Recovery failed: unable to read phase"); + goto quit; + } + buf[strlen(buf) - 1] = '\0'; + *phase = atoi(buf); + if (*phase == SCAN_PHASE) { + fclose(file); + return 0; + } + if ((*phase < DIR_PHASE || *phase > DIR_PHASE_MAX) && + (*phase < FILE_PHASE || *phase > FILE_PHASE_MAX)) { + err_message("Recovery failed: failed to read valid recovery phase"); + goto quit; + } + + /* read inode number */ + if (fgets(buf, PATH_MAX + 10, file) == NULL) { + err_message("Recovery failed: unable to read inode number"); + goto quit; + } + buf[strlen(buf) - 1] = '\0'; + ino = strtoull(buf, NULL, 10); + if (ino == 0) { + err_message("Recovery failed: unable to read inode number"); + goto quit; + } + + /* read ftw_flags */ + if (fgets(buf, PATH_MAX + 10, file) == NULL) { + err_message("Recovery failed: unable to read flags"); + goto quit; + } + buf[strlen(buf) - 1] = '\0'; + if (buf[1] != '\0' || (buf[0] != '0' && buf[0] != '1')) { + err_message("Recovery failed: unable to read flags: '%s'", buf); + goto quit; + } + ftw_flags = atoi(buf); + + /* read paths and target path */ + *node = NULL; + *target = NULL; + first_path = 1; + while (fgets(buf, PATH_MAX + 10, file) != NULL) { + buf[strlen(buf) - 1] = '\0'; + + log_message(LOG_DEBUG, "path: '%s'", buf); + + if (buf[0] == '/') { + if (stat64(buf, &s) < 0) { + err_message(_("Recovery failed: cannot " + "stat '%s'"), buf); + goto quit; + } + if (s.st_ino != ino) { + err_message(_("Recovery failed: inode " + "number for '%s' does not " + "match recorded number"), buf); + goto quit; + } + + if (first_path) { + first_path = 0; + *node = add_node_path(ino, ftw_flags, buf); + } + else { + add_path(*node, buf); + } + } + else if (strncmp(buf, "target: ", 8) == 0) { + *target = strdup(buf + 8); + if (*target == NULL) { + err_nomem(); + goto quit; + } + if (stat64(*target, &s) < 0) { + err_message(_("Recovery failed: cannot " + "stat '%s'"), *target); + goto quit; + } + } + else if (strncmp(buf, "temp: ", 6) == 0) { + *temp = strdup(buf + 6); + if (*temp == NULL) { + err_nomem(); + goto quit; + } + } + else if (strcmp(buf, "end") == 0) { + rval = 0; + goto quit; + } + else { + err_message(_("Recovery failed: unrecognised " + "string: '%s'"), buf); + goto quit; + } + } + + err_message(_("Recovery failed: end of recovery file not found")); + + quit: + if (*node == NULL) { + err_message(_("Recovery failed: no valid inode or paths " + "specified")); + rval = 1; + } + + if (*target == NULL) { + err_message(_("Recovery failed: no inode target specified")); + rval = 1; + } + + fclose(file); + + return rval; +} + +int +recover( + bignode_t *node, + char *target, + char *tname, + int phase) +{ + int tfd = -1; + int targetfd = -1; + char *srcname = NULL; + int rval = 0; + int i; + int move_count = 0; + + dump_node("recover", node); + log_message(LOG_DEBUG, "target: %s, phase: %x", target, phase); + + if (node) + srcname = node->paths[0]; + + switch (phase) { + + case DIR_PHASE_2: +rmtemps: + log_message(LOG_NORMAL, _("Removing temporary directory: '%s'"), + tname); + if (rmdir(tname) < 0 && errno != ENOENT) { + err_message(_("unable to remove directory: %s"), tname); + rval = 1; + } + /* FALL THRU */ + case DIR_PHASE_1: + log_message(LOG_NORMAL, _("Removing target directory: '%s'"), + target); + if (rmdir(target) < 0 && errno != ENOENT) { + err_message(_("unable to remove directory: %s"), + target); + rval = 1; + } + break; + + case DIR_PHASE_3: + log_message(LOG_NORMAL, _("Completing moving directory " + "contents: '%s' to '%s'"), srcname, target); + if (move_dirents(srcname, target, &move_count) != 0) { + err_message(_("unable to move directory contents: " + "%s to %s"), srcname, target); + /* uh oh, move everything back... */ + if (move_count > 0) { + if (move_dirents(target, srcname, + &move_count) != 0) { + /* oh, dear lord... let the admin + * clean this one up */ + err_message(_("unable to move directory " + "contents back: %s to %s"), + target, srcname); + exit(1); + } + } + goto rmtemps; + } + /* FALL THRU */ + case DIR_PHASE_4: + log_message(LOG_NORMAL, _("Setting attributes for target " + "directory: \'%s\'"), target); + tfd = open(tname, O_RDONLY); + if (tfd < 0) { + err_open(tname); + rval = 1; + break; + } + targetfd = open(target, O_RDONLY); + if (targetfd < 0) { + err_open(target); + rval = 1; + break; + } + rval = dup_attributes(tname, tfd, target, targetfd); + if (rval != 0) { + err_message(_("unable to duplicate directory " + "attributes: %s"), tname); + break; + } + close(tfd); + close(targetfd); + /* FALL THRU */ + case DIR_PHASE_6: + log_message(LOG_NORMAL, _("Removing temporary directory: \'%s\'"), + tname); + if (rmdir(tname) < 0 && errno != ENOENT) { + err_message(_("unable to remove directory: %s"), + tname); + rval = 1; + break; + } + /* FALL THRU */ + case DIR_PHASE_5: + log_message(LOG_NORMAL, _("Removing old directory: \'%s\'"), + srcname); + if (rmdir(srcname) < 0 && errno != ENOENT) { + err_message(_("unable to remove directory: %s"), + srcname); + rval = 1; + break; + } + /* FALL THRU */ + case DIR_PHASE_7: + log_message(LOG_NORMAL, _("Renaming new directory to old " + "directory: \'%s\' -> \'%s\'"), target, srcname); + rval = rename(target, srcname); + if (rval != 0) { + /* we can't abort since the src dir is now gone. + * let the admin clean this one up + */ + err_message(_("unable to rename directory: %s to %s"), + target, srcname); + break; + } + break; + + + case FILE_PHASE_1: + case SLINK_PHASE_1: + log_message(LOG_NORMAL, _("Unlinking temporary file: \'%s\'"), + target); + unlink(target); + break; + + case FILE_PHASE_2: + case SLINK_PHASE_2: + log_message(LOG_NORMAL, _("Unlinking old file: \'%s\'"), + srcname); + rval = unlink(srcname); + if (rval != 0) { + err_message(_("unable to remove file: %s"), srcname); + break; + } + /* FALL THRU */ + case FILE_PHASE_3: + case SLINK_PHASE_3: + log_message(LOG_NORMAL, _("Renaming new file to old file: " + "\'%s\' -> \'%s\'"), target, srcname); + rval = rename(target, srcname); + if (rval != 0) { + /* we can't abort since the src file is now gone. + * let the admin clean this one up + */ + err_message(_("unable to rename file: %s to %s"), + target, srcname); + break; + } + /* FALL THRU */ + case FILE_PHASE_4: + case SLINK_PHASE_4: + /* for each hardlink, unlink and creat pointing to target */ + for (i = 1; i < node->numpaths; i++) { + if (i == 1) + log_message(LOG_NORMAL, _("Resetting hardlinks " + "to new file")); + + rval = unlink(node->paths[i]); + if (rval != 0) { + err_message(_("unable to remove file: %s"), + node->paths[i]); + break; + } + rval = link(srcname, node->paths[i]); + if (rval != 0) { + err_message(_("unable to link to file: %s"), + srcname); + break; + } + } + break; + } + + if (rval == 0) { + log_message(LOG_NORMAL, _("Removing recover file: \'%s\'"), + recover_file); + unlink(recover_file); + log_message(LOG_NORMAL, _("Recovery done.")); + } + else { + log_message(LOG_NORMAL, _("Leaving recover file: \'%s\'"), + recover_file); + log_message(LOG_NORMAL, _("Recovery failed.")); + } + + return rval; +} + +int +main( + int argc, + char *argv[]) +{ + int c = 0; + int rval = 0; + int q_opt = 0; + int v_opt = 0; + int p_opt = 0; + int n_opt = 0; + char pathname[PATH_MAX]; + struct stat64 st; + + progname = basename(argv[0]); + + setlocale(LC_ALL, ""); + bindtextdomain(PACKAGE, LOCALEDIR); + textdomain(PACKAGE); + + while ((c = getopt(argc, argv, "fnpqvP:r:")) != -1) { + switch (c) { + case 'f': + force_all = 1; + break; + case 'n': + n_opt++; + break; + case 'p': + p_opt++; + break; + case 'q': + if (v_opt) + err_message(_("'q' option incompatible " + "with 'v' option")); + q_opt++; + log_level=0; + break; + case 'v': + if (q_opt) + err_message(_("'v' option incompatible " + "with 'q' option")); + v_opt++; + log_level++; + break; + case 'P': + poll_interval = atoi(optarg); + break; + case 'r': + recover_file = optarg; + break; + default: + err_message(_("%s: illegal option -- %c\n"), c); + usage(); + /* NOTREACHED */ + break; + } + } + + if (optind != argc - 1 && recover_file == NULL) { + usage(); + exit(1); + } + + realuid = getuid(); + starttime = time(0); + + init_nodehash(); + + signal(SIGALRM, sighandler); + signal(SIGABRT, sighandler); + signal(SIGHUP, sighandler); + signal(SIGINT, sighandler); + signal(SIGQUIT, sighandler); + signal(SIGTERM, sighandler); + + if (p_opt && poll_interval == 0) { + poll_interval = 1; + } + if (poll_interval) + alarm(poll_interval); + + if (recover_file) { + bignode_t *node = NULL; + char *target = NULL; + char *tname = NULL; + int phase = 0; + + if (n_opt) + goto quit; + + /* read node info from recovery file */ + if (read_recover_file(recover_file, &node, &target, + &tname, &phase) != 0) + exit(1); + + rval = recover(node, target, tname, phase); + + free(target); + free(tname); + + return rval; + } + + recover_file = malloc(PATH_MAX); + if (recover_file == NULL) { + err_nomem(); + exit(1); + } + recover_file[0] = '\0'; + + strcpy(pathname, argv[optind]); + if (pathname[0] != '/') { + err_message(_("pathname must begin with a slash ('/')")); + exit(1); + } + + if (stat64(pathname, &st) < 0) { + err_stat(pathname); + exit(1); + } + if (S_ISREG(st.st_mode)) { + /* single file specified */ + if (st.st_nlink > 1) { + err_message(_("cannot process single file with a " + "link count greater than 1")); + exit(1); + } + + strcpy(recover_file, pathname); + dirname(recover_file); + + strcpy(recover_file + strlen(recover_file), "/xfs_reno.recover"); + if (!n_opt) { + if (open_recoverfile() != 0) + exit(1); + } + add_node_path(st.st_ino, FTW_F, pathname); + } + else if (S_ISDIR(st.st_mode)) { + /* directory tree specified */ + strcpy(recover_file, pathname); + + strcpy(recover_file + strlen(recover_file), "/xfs_reno.recover"); + if (!n_opt) { + if (open_recoverfile() != 0) + exit(1); + } + + /* directory scan */ + log_message(LOG_INFO, _("\rScanning directory tree...")); + SET_PHASE(SCAN_PHASE); + nftw64(pathname, nftw_addnodes, 100, FTW_PHYS | FTW_MOUNT); + } + else { + err_message(_("pathname must be either a regular file " + "or directory")); + exit(1); + } + + dump_nodehash(); + + if (n_opt) { + /* n flag set, don't do anything */ + if (numdirnodes) + log_message(LOG_NORMAL, "\rWould process %d %s", + numdirnodes, numdirnodes == 1 ? + "directory" : "directories"); + else + log_message(LOG_NORMAL, "\rNo directories to process"); + + if (numfilenodes) + /* process files */ + log_message(LOG_NORMAL, "\rWould process %d %s", + numfilenodes, numfilenodes == 1 ? + "file" : "files"); + else + log_message(LOG_NORMAL, "\rNo files to process"); + if (numslinknodes) + /* process files */ + log_message(LOG_NORMAL, "\rWould process %d %s", + numslinknodes, numslinknodes == 1 ? + "symlinx" : "symlinks"); + else + log_message(LOG_NORMAL, "\rNo symlinks to process"); + } else { + /* process directories */ + if (numdirnodes) { + log_message(LOG_INFO, _("\rProcessing %d %s..."), + numdirnodes, numdirnodes == 1 ? + _("directory") : _("directories")); + cur_phase = DIR_PHASE; + rval = for_all_nodes(process_dir, FTW_D, 1); + if (rval != 0) + goto quit; + } + else + log_message(LOG_INFO, _("\rNo directories to process...")); + + if (numfilenodes) { + /* process files */ + log_message(LOG_INFO, _("\rProcessing %d %s..."), + numfilenodes, numfilenodes == 1 ? + _("file") : _("files")); + cur_phase = FILE_PHASE; + for_all_nodes(process_file, FTW_F, 0); + } + else + log_message(LOG_INFO, _("\rNo files to process...")); + + if (numslinknodes) { + /* process symlinks */ + log_message(LOG_INFO, _("\rProcessing %d %s..."), + numslinknodes, numslinknodes == 1 ? + _("symlink") : _("symlinks")); + cur_phase = SLINK_PHASE; + for_all_nodes(process_slink, FTW_SL, 0); + } + else + log_message(LOG_INFO, _("\rNo symlinks to process...")); + + } +quit: + free_nodehash(); + + close(recover_fd); + + if (rval == 0) + unlink(recover_file); + + log_message(LOG_DEBUG, "\r%u seconds elapsed", time(0) - starttime); + log_message(LOG_INFO, _("\rDone. ")); + + return rval | global_rval; +} Index: b/Makefile =================================================================== --- a/Makefile +++ b/Makefile @@ -41,7 +41,7 @@ endif LIB_SUBDIRS = libxfs libxlog libxcmd libhandle libdisk TOOL_SUBDIRS = copy db estimate fsck fsr growfs io logprint mkfs quota \ - mdrestore repair rtcp m4 man doc po debian + mdrestore repair reno rtcp m4 man doc po debian SUBDIRS = include $(LIB_SUBDIRS) $(TOOL_SUBDIRS) --nextPart5192251.cl8ZghraCZ Content-Disposition: attachment; filename="xfs_reno_fix.diff" Content-Transfer-Encoding: 7Bit Content-Type: text/x-patch; charset="UTF-8"; name="xfs_reno_fix.diff" Index: b/Makefile =================================================================== --- a/Makefile +++ b/Makefile @@ -56,7 +56,7 @@ endif $(LIB_SUBDIRS) $(TOOL_SUBDIRS): include copy mdrestore: libxfs db logprint: libxfs libxlog -fsr: libhandle +fsr reno: libhandle growfs: libxfs libxcmd io: libxcmd libhandle mkfs: libxfs Index: b/reno/Makefile =================================================================== --- a/reno/Makefile +++ b/reno/Makefile @@ -7,7 +7,7 @@ include $(TOPDIR)/include/builddefs LTCOMMAND = xfs_reno CFILES = xfs_reno.c -LLDLIBS = $(LIBATTR) +LLDLIBS = $(LIBATTR) $(LIBHANDLE) default: $(LTCOMMAND) Index: b/reno/xfs_reno.c =================================================================== --- a/reno/xfs_reno.c +++ b/reno/xfs_reno.c @@ -49,6 +49,7 @@ #include #include #include +#include #define ATTRBUFSIZE 1024 --nextPart5192251.cl8ZghraCZ-- From bpm@sgi.com Tue Mar 5 14:36:15 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id AE2DE8068 for ; Tue, 5 Mar 2013 14:36:15 -0600 (CST) Received: from whiskey.americas.sgi.com (eagdhcp-232-197.americas.sgi.com [128.162.232.197]) by relay1.corp.sgi.com (Postfix) with ESMTP id 7DB7E8F808F; Tue, 5 Mar 2013 12:36:15 -0800 (PST) Received: by whiskey.americas.sgi.com (Postfix, from userid 4600) id 199B1500B4A; Tue, 5 Mar 2013 14:36:15 -0600 (CST) Date: Tue, 5 Mar 2013 14:36:15 -0600 From: Ben Myers To: Dave Chinner Cc: xfs@oss.sgi.com Subject: Re: [PATCH 07/16] xfs: add CRC checks for quota blocks Message-ID: <20130305203615.GK22182@sgi.com> References: <1361755901-12453-1-git-send-email-david@fromorbit.com> <1361755901-12453-8-git-send-email-david@fromorbit.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <1361755901-12453-8-git-send-email-david@fromorbit.com> User-Agent: Mutt/1.5.20 (2009-06-14) Hi Dave, On Mon, Feb 25, 2013 at 12:31:32PM +1100, Dave Chinner wrote: > From: Christoph Hellwig > > Use the reserved space in struct xfs_dqblk to store a UUID and a crc > for the quota blocks. > > [dchinner@redhat.com] Add a LSN field and update for current verifier > infrastructure. > > Signed-off-by: Christoph Hellwig > Signed-off-by: Dave Chinner Been over this and it looks fine. > @@ -897,6 +910,10 @@ xfs_qm_dqiter_bufs( > if (error) > break; > > + /* > + * XXX(hch): need to figure out if it makes sense to validate > + * the CRC here. > + */ What's you're opinion on this? -Ben From bpm@sgi.com Tue Mar 5 15:32:27 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 2531B8045 for ; Tue, 5 Mar 2013 15:32:27 -0600 (CST) Received: from whiskey.americas.sgi.com (eagdhcp-232-197.americas.sgi.com [128.162.232.197]) by relay1.corp.sgi.com (Postfix) with ESMTP id DDA8C8F8040; Tue, 5 Mar 2013 13:32:23 -0800 (PST) Received: by whiskey.americas.sgi.com (Postfix, from userid 4600) id 951FD500B4A; Tue, 5 Mar 2013 15:32:23 -0600 (CST) Date: Tue, 5 Mar 2013 15:32:23 -0600 From: Ben Myers To: CAI Qian Cc: Mark Tinguely , Brian Foster , stable@vger.kernel.org, xfs@oss.sgi.com, Dave Chinner , Dave Chinner Subject: Re: request for stable inclusion Message-ID: <20130305213223.GL22182@sgi.com> References: <426368976.8591643.1362386550488.JavaMail.root@redhat.com> <1879117295.8593844.1362387154930.JavaMail.root@redhat.com> <20130304221100.GL26081@dastard> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <20130304221100.GL26081@dastard> User-Agent: Mutt/1.5.20 (2009-06-14) Hi CAI, On Tue, Mar 05, 2013 at 09:11:00AM +1100, Dave Chinner wrote: > On Mon, Mar 04, 2013 at 03:52:34AM -0500, CAI Qian wrote: > > This is to request to apply the below commit for the stable releases > > in order to fix a regression introduced by 055388a (xfs: dynamic > > speculative EOF preallocation) that caused fsync() took long time during > > the sparse file testing. > > > > For stable-3.4 and stable-3.8, it can be applied as it is. For stable-3.0, > > please see the below patch which fixed the context and used xfs_bmapi() > > instead of xfs_bmapi_read() which yet in the tree. Also tested on the > > stable-3.0 to confirmed the original fsync() slowness regression is now > > gone. Please review and ACK. > > I've already said no to -stable in another discussion thread, and > that discussion has not yet played out. please do not try to preempt > any discussion by sending patches to @stable before it is even > decided if it is something we *need* to fix in 2 year old kernels. > Yes, you have input into the discussion, but please do not take it > upon yourself to determine what should be backported to -stable and > what shouldn't be - that is for the subsystem maintainers to decide. > > FWIW, is your memory so short that you don't remember what happened > a couple of weeks ago with the last XFS bugfix backport you > requested directly to @stable and was accepted based on "it applies > and builds, so it's OK?" i.e. without proper review, discussion or > testing? > > That's right - it caused a major functional regression and that > wasted a heap of time for quite a few people in sorting it out. > > So right now this request gets a big, fat, loud NACK from me while > the aforementioned discussion takes place. I appreciate that you've been willing to do the legwork on this. That's really nice work, but I agree with Dave that it needs a closer look before we request that it be picked up in -stable. Lets get this reviewed and tested on xfs@oss.sgi.com before bringing it to the attention of the -stable folk. We can continue to work through this in the other thread. Thanks for spending the time! ;) Regards, Ben From david@fromorbit.com Tue Mar 5 16:30:10 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 8FFA48038 for ; Tue, 5 Mar 2013 16:30:10 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay2.corp.sgi.com (Postfix) with ESMTP id 7AE60304048 for ; Tue, 5 Mar 2013 14:30:07 -0800 (PST) X-ASG-Debug-ID: 1362522603-04cb6c2b031cd370001-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id HzkZQrH1qx98KGPt for ; Tue, 05 Mar 2013 14:30:04 -0800 (PST) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AlogAH1xNlF5Layr/2dsb2JhbAAqGod+t1aFEgECAYFwF3OCKwEBBTIBIxESEAgDGAklDwUlAyETG4d3DS68GhWNdxgfSgeDQAOWSYEfj1CDHA Received: from ppp121-45-172-171.lns20.syd6.internode.on.net (HELO dastard) ([121.45.172.171]) by ipmail05.adl6.internode.on.net with ESMTP; 06 Mar 2013 08:59:45 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UD0Mf-000157-2p; Wed, 06 Mar 2013 09:29:41 +1100 Date: Wed, 6 Mar 2013 09:29:41 +1100 From: Dave Chinner To: Hans-Peter Jansen Cc: xfs@oss.sgi.com Subject: Re: strange behavior of a larger xfs directory Message-ID: <20130305222941.GP26081@dastard> X-ASG-Orig-Subj: Re: strange behavior of a larger xfs directory References: <4300208.uZ6HVTycB6@xrated> <20130304230527.GM26081@dastard> <8026381.3dEJ1E4pzL@xrated> MIME-Version: 1.0 Content-Type: text/plain; charset=iso-8859-1 Content-Disposition: inline Content-Transfer-Encoding: 8bit In-Reply-To: <8026381.3dEJ1E4pzL@xrated> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1362522603 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.10 X-Barracuda-Spam-Status: No, SCORE=0.10 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_SA085 X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124359 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.10 BSF_SC0_SA085 Custom Rule SA085 On Tue, Mar 05, 2013 at 09:32:02PM +0100, Hans-Peter Jansen wrote: > Am Dienstag, 5. Mrz 2013, 10:05:27 schrieb Dave Chinner: > > On Mon, Mar 04, 2013 at 05:40:13PM +0100, Hans-Peter Jansen wrote: > > Second solution: Run 3.8.1, make sure you mount with inode32, and > > then run the xfs_reno tool mentioned on this page: > > > > http://xfs.org/index.php/Unfinished_work > > > > to find all the inodes with inode numbers larger than 32 > > bits and move them to locations with smaller inode numbers. > > Okay, I would like to take that route. > > I've updated the xfsprogs, xfsdump and xfstests packages in my openSUSE build > service repo home:frispete:tools to current versions today, and plan to submit > them to Factory. openSUSE is always lagging in this area. > > I've tried to include a build of the xfs_reno tool in xfsprogs, since, as you > mentioned, others might have a similar need soon. Unfortunately I failed so > far, because it is using some attr_multi and attr_list interfaces, that aren't > part of the xfsprogs visible API anymore. Only the handle(3) man page refers > to them. > > Attached is my current state: I've relocated the patch to xfsprogs 3.1.9, > because it already carries all the necessary headers (apart from attr_multi > and attr_list). The attr interfaces seem to be collected in libhandle now, > hence I've added it to the build. attr_list and attr_multi are supplied by libattr, you should not need the *by_handle variants at all - they are special sauce used by xfsdump, not xfs_reno.... ..... > +TOPDIR = .. > +include $(TOPDIR)/include/builddefs > + > +LTCOMMAND = xfs_reno > +CFILES = xfs_reno.c > +LLDLIBS = $(LIBATTR) The patch assumes that libattr has been found by autoconf and set up in $(LIBATTR), but xfsprogs does not currently use libattr and hence that variable isn't set up. Therefore this line is a no-op: +LLDLIBS = $(LIBATTR) Change it to: LLDLIBS = -lattr And the xfs_reno should then link. BTW, if you want extra points and add the autoconf magic to the patch, copy it from the xfsdump tree. The places you need to copy from are: $ git grep -l LIBATTR |grep -v Makefile configure.ac include/builddefs.in m4/package_attrdev.m4 $ And for even more bonus points, you could write a basic xfstest that creates a bunch of 64 bit inodes and then runs xfs_reno on it and checks that they get moved to 32 bit inodes. At that point, we could probably pull the xfs_reno patch into xfsprogs and ship it.... Cheers, Dave. -- Dave Chinner david@fromorbit.com From sandeen@sandeen.net Tue Mar 5 16:41:55 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id D7C798053 for ; Tue, 5 Mar 2013 16:41:55 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id C1049304066 for ; Tue, 5 Mar 2013 14:41:55 -0800 (PST) X-ASG-Debug-ID: 1362523314-04cbb07dbc1d6550001-NocioJ Received: from sandeen.net (sandeen.net [63.231.237.45]) by cuda.sgi.com with ESMTP id prCuE6ikuIoLlOOR for ; Tue, 05 Mar 2013 14:41:54 -0800 (PST) X-Barracuda-Envelope-From: sandeen@sandeen.net X-Barracuda-Apparent-Source-IP: 63.231.237.45 Received: from liberator.sandeen.net (liberator.sandeen.net [10.0.0.4]) (using TLSv1 with cipher DHE-RSA-CAMELLIA256-SHA (256/256 bits)) (No client certificate requested) by sandeen.net (Postfix) with ESMTPSA id 7B10163C59BB; Tue, 5 Mar 2013 16:41:54 -0600 (CST) Message-ID: <513674B2.9030900@sandeen.net> Date: Tue, 05 Mar 2013 16:41:54 -0600 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: Eric Sandeen CC: xfs-oss , linux-btrfs , Stefan Behrens Subject: [PATCH] xfstests: Fix hang when mkfs.btrfs isn't present References: <512D1E3E.9050907@redhat.com> X-ASG-Orig-Subj: [PATCH] xfstests: Fix hang when mkfs.btrfs isn't present In-Reply-To: <512D1E3E.9050907@redhat.com> X-Enigmail-Version: 1.5.1 Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: sandeen.net[63.231.237.45] X-Barracuda-Start-Time: 1362523314 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124359 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- My earlier patch (xfstests: handle new mkfs.btrfs -f option cleanly) had a flaw in that if set_prog_path mkfs.btrfs returns nothing, the grep will hang. Test for that case to avoid it, and just return the empty string in that case. Reported-by: Rich Johnston Signed-off-by: Eric Sandeen --- diff --git a/common.config b/common.config index c10163a..a0b017d 100644 --- a/common.config +++ b/common.config @@ -108,7 +108,7 @@ set_prog_path() set_btrfs_mkfs_prog_path_with_opts() { p=`set_prog_path mkfs.btrfs` - if grep -q 'force overwrite' $p; then + if [ "$p" != "" ] && grep -q 'force overwrite' $p; then echo "$p -f" else echo $p From rjohnston@sgi.com Tue Mar 5 16:48:28 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id C60958053 for ; Tue, 5 Mar 2013 16:48:28 -0600 (CST) Received: from xmail.sgi.com (pv-excas3-dc21.corp.sgi.com [137.38.102.206]) by relay3.corp.sgi.com (Postfix) with ESMTP id 16A1CAC007; Tue, 5 Mar 2013 14:48:25 -0800 (PST) Received: from [128.162.233.55] (128.162.233.55) by xmail.sgi.com (137.38.102.30) with Microsoft SMTP Server (TLS) id 14.2.318.1; Tue, 5 Mar 2013 16:47:34 -0600 Message-ID: <51367610.3070804@sgi.com> Date: Tue, 5 Mar 2013 16:47:44 -0600 From: Rich Johnston User-Agent: Mozilla/5.0 (X11; Linux i686; rv:13.0) Gecko/20120615 Thunderbird/13.0.1 MIME-Version: 1.0 To: Eric Sandeen CC: Eric Sandeen , Stefan Behrens , linux-btrfs , xfs-oss Subject: Re: [PATCH] xfstests: Fix hang when mkfs.btrfs isn't present References: <512D1E3E.9050907@redhat.com> <513674B2.9030900@sandeen.net> In-Reply-To: <513674B2.9030900@sandeen.net> Content-Type: text/plain; charset="ISO-8859-1"; format=flowed Content-Transfer-Encoding: 7bit X-Originating-IP: [128.162.233.55] Yup looks good, thanks for fixing it Eric. Reviewed-by: Rich Johnston Having some network issues, will pull this in tomorrow. Thanks --Rich From david@fromorbit.com Tue Mar 5 16:50:33 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 096E88063 for ; Tue, 5 Mar 2013 16:50:33 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay3.corp.sgi.com (Postfix) with ESMTP id 89D7CAC005 for ; Tue, 5 Mar 2013 14:50:32 -0800 (PST) X-ASG-Debug-ID: 1362523830-04cbb07dbf1d6cf0001-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id 6SMfYdFZ670LF6ZG for ; Tue, 05 Mar 2013 14:50:30 -0800 (PST) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AlkgABV2NlF5Layr/2dsb2JhbABEh363VoUSAQIBgXAXc4IrAQEFOhwjEAgDDgcDCSUPBSUDIROIErxYFY1JLhgfPwsHg0ADlkmQb4McgVYBHgY Received: from ppp121-45-172-171.lns20.syd6.internode.on.net (HELO dastard) ([121.45.172.171]) by ipmail05.adl6.internode.on.net with ESMTP; 06 Mar 2013 09:19:37 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UD0fw-000189-Ru; Wed, 06 Mar 2013 09:49:36 +1100 Date: Wed, 6 Mar 2013 09:49:36 +1100 From: Dave Chinner To: Ben Myers Cc: xfs@oss.sgi.com Subject: Re: [PATCH 07/16] xfs: add CRC checks for quota blocks Message-ID: <20130305224936.GQ26081@dastard> X-ASG-Orig-Subj: Re: [PATCH 07/16] xfs: add CRC checks for quota blocks References: <1361755901-12453-1-git-send-email-david@fromorbit.com> <1361755901-12453-8-git-send-email-david@fromorbit.com> <20130305203615.GK22182@sgi.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <20130305203615.GK22182@sgi.com> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1362523830 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124361 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Tue, Mar 05, 2013 at 02:36:15PM -0600, Ben Myers wrote: > Hi Dave, > > On Mon, Feb 25, 2013 at 12:31:32PM +1100, Dave Chinner wrote: > > From: Christoph Hellwig > > > > Use the reserved space in struct xfs_dqblk to store a UUID and a crc > > for the quota blocks. > > > > [dchinner@redhat.com] Add a LSN field and update for current verifier > > infrastructure. > > > > Signed-off-by: Christoph Hellwig > > Signed-off-by: Dave Chinner > > Been over this and it looks fine. > > > @@ -897,6 +910,10 @@ xfs_qm_dqiter_bufs( > > if (error) > > break; > > > > + /* > > + * XXX(hch): need to figure out if it makes sense to validate > > + * the CRC here. > > + */ > > What's you're opinion on this? I did actually change the code to validate the CRC here via the call to xfs_trans_read_buf(.... &xfs_dquot_buf_ops) above. i.e. the read verifier will do CRC validation of the buffer. The comment is still relevant, however, because it's not exactly clear what the best approach to do here if we get a CRC failure. That would indicate some kind of corruption that we weren't expecting, and quite possibly a corruption that rewriting the dquot can't fix. So without knowing what kind of corruption is typical here, I don't know what the best approach to take here is. So effectively what I've done is add CRC validation so that we'll get people telling us about problems (because the quotacheck will abort and there will be a stack trace in the log). If it turns out that corrupted quota files is a common problem that quotacheck encounters we can gather the corpses, do post-mortem analysis of the failures and then revisit the code appropriately with that knowledge in hand. Cheers, Dave. -- Dave Chinner david@fromorbit.com From rechas001@gmail.com Tue Mar 5 17:32:54 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: **** X-Spam-Status: No, score=4.7 required=5.0 tests=FREEMAIL_ENVFROM_END_DIGIT, FREEMAIL_FROM,HTML_FONT_SIZE_LARGE,HTML_MESSAGE,MIME_HTML_ONLY,MPART_ALT_DIFF autolearn=no version=3.3.1 X-Original-To: linux-xfs@oss.sgi.com Delivered-To: linux-xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 895AD800C for ; Tue, 5 Mar 2013 17:32:53 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay3.corp.sgi.com (Postfix) with ESMTP id 2618DAC005 for ; Tue, 5 Mar 2013 15:32:50 -0800 (PST) X-ASG-Debug-ID: 1362526364-04bdf022981f0140001-w1Z2WR Received: from india213.startdedicated.com (static-ip-85-25-13-96.inaddr.ip-pool.com [85.25.13.96]) by cuda.sgi.com with ESMTP id iiAgssSRhxFJAbwJ (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO) for ; Tue, 05 Mar 2013 15:32:45 -0800 (PST) X-Barracuda-Envelope-From: rechas001@gmail.com X-Barracuda-Apparent-Source-IP: 85.25.13.96 Received: by india213.startdedicated.com (Postfix, from userid 48) id D50E2AF9620; Wed, 6 Mar 2013 00:32:40 +0100 (CET) To: Subject: Toner originales Max - Color X-PHP-Originating-Script: 500:MailSend.php X-ASG-Orig-Subj: Toner originales Max - Color From: Marketing y Publicidad Reply-To: Digital - Print Date: Wed, 06 Mar 2013 00:32:39 +0100 X-LibVersion: 3.3.2_4 MIME-Version: 1.0 Content-Type: multipart/related; boundary="_=_swift-200363721551368097e51ca9.49483358_=_" Content-Transfer-Encoding: 7bit X-Priority: 3 X-MSMail-Priority: Normal X-MimeOLE: Produced by SwiftMailer 3.3.2_4 X-Mailer: Administration X-Mailer-MsgId: bGludXgteGZzQG9zcy5zZ2kuY29t X-Mailer-CSID: NjVfNDE= Message-ID: <20130305233240.31039.645715483.swift@marketingypublicidadbolivia.com> X-Barracuda-Connect: static-ip-85-25-13-96.inaddr.ip-pool.com[85.25.13.96] X-Barracuda-Start-Time: 1362526365 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.15 X-Barracuda-Spam-Status: No, SCORE=0.15 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=HTML_FONT_SIZE_LARGE, HTML_MESSAGE, MAILTO_TO_SPAM_ADDR, MIME_HTML_ONLY, MPART_ALT_DIFF X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124363 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 MAILTO_TO_SPAM_ADDR URI: Includes a link to a likely spammer email 0.00 HTML_FONT_SIZE_LARGE BODY: HTML font size is large 0.00 MIME_HTML_ONLY BODY: Message only has text/html MIME parts 0.00 HTML_MESSAGE BODY: HTML included in message 0.14 MPART_ALT_DIFF BODY: HTML and text parts are different This is a message in multipart MIME format. Your mail client should not be displaying this. Consider upgrading your mail client to view this message correctly. --_=_swift-200363721551368097e51ca9.49483358_=_ Content-Type: multipart/alternative; boundary="_=_swift-9834447185136809807ea89.96665306_=_" Content-Transfer-Encoding: 7bit --_=_swift-9834447185136809807ea89.96665306_=_ Content-Type: text/html; charset=us-ascii Content-Transfer-Encoding: 7bit
TONERS COLOR PARA IMPRESORAS HP
Distribuidor Exclusivo para Bolivia Digital Print
Si no puede visualizar correctamente este mensaje por favor pulse Aqui
Comparte esta publicidad con tus amigos en: Facebook  Twitter 

  

BENEFICIOS PARA NUESTROS CLIENTE
• Atención personalizada; le llevamos el pedido hasta su establecimiento.
• Productos y servicios de calidad.
• Garantía al 100% con todos nuestros productos, trabajos y servicios.
• Ante cualquier falla de nuestros tóner, le remplazamos al instante por uno nuevo.
Impresoras en calidad de comodato. Nosótros le ponemos la impresora y usted solo nos consume el tóner.

* Nuestros pruductos cuentan con certificación internacional ISO 9001-2000   iso 14001 - 2004

• Todos nuestros precios incluyen impuestos de ley.
• Al comprar nuestros productos, usted obtiene un considerable ahorro monetario.

Con todos estos beneficios, queremos que nos dé la oportunidad de demostrarle nuestra capacidad de servicio que, estamos seguros, logrará superar sus expectativas.
Sin otro particular, me despido con las consideraciones más distinguidas.

Para mayor información e inscripciones:

Teléfono: 3-485719 Cel.: 747-05000 Email: digitalprintsc@hotmail.com
Teléfono: 710-12899 Cel.: 721-89286 Email: manuel_sof@hotmail.com
Dirección: Santa Cruz: Av. Paragua No. 3840 Of. No. 8
 
 
 
 
 
 
Santa Cruz - Bolivia
 
 
 
 

 

Siguenos en:

 

 

 

 

 

 

 
 
 
 
Para dejar de recibir este servicio por favor responda este mismo correo con el Asunto o Subject: Baja a rechas001@gmail.com
Ley 26.032: La búsqueda, recepción y difusión de información e ideas de toda índole, a través del servicio de Internet, se considera comprendido dentro de la garantía constitucional que ampara la libertad de expresión.
© 2006 - 2013
--- --_=_swift-9834447185136809807ea89.96665306_=_-- --_=_swift-200363721551368097e51ca9.49483358_=_ Content-Type: image/png; name=face.png Content-Transfer-Encoding: base64 Content-Disposition: inline; filename=face.png Content-ID: iVBORw0KGgoAAAANSUhEUgAAABAAAAAQCAYAAAAf8/9hAAAACXBIWXMAAAsTAAALEwEAmpwY AAAAIGNIUk0AAHolAACAgwAA+f8AAIDpAAB1MAAA6mAAADqYAAAXb5JfxUYAAANZSURBVHja fJJdSN11GMc//xeP891zPOpysznfjqJG0GoUtLEyRrIyt110MWddjCiIutiIXbi6KShHLAhr i6JgjMaaoqPaiGmtQEW3fElj6lLnUeyo//P++v///r8uTpHd9IXn6uH5PN8vz6NIKdmqT7q7 c48ePnRmYXGlp6Kycthv+HG5XAQCAQqdTkLBIE6nE7/foGzHTtStw293du4+3tExPD4bOqU7 HD9MTU683FBf7+D/JKVESkl/X9+BeCIpXzrVI8ufPCffPdcrQ8Z9OTU5ufjNlSstGmg+n4/5 uTk2NzaYn5slFoulHTy+d29RS8uzA890fMXE76s0VLvovbnC4LCX0mLnrrq6um/H7twZ/uzC hXpPTY2y1YCqK4ry/Y0bPa909rO+EcHlzEJYNrbiwLueQtMVyneWsr3UvefwkbaZkdHR/rbW VreipDlq37VrHiOY3Hf91hxuVxamaROOJvDszue14/tRM7L5ZXSBpdUgD5YVU1e741Dv1Uvr xqav++Gmpky9obGxrW/gLra0saUEIQhFkyRNC4DTZ3/ii6vjFLscPOByUJjnYMUXpq255tWb A98l1ayszOoFrx9NVbCEIJpIUeLO5usPj4I06X7nIBe7nkdTdRIig0WfycqGhXfdQlh2qWrb IqkokLIEliWwhU0oFGdw5B4oGsPjKwyNe1FVQLHJ1EHT0qUopNRQKHq7sdpNLJbEEhKpSnxG lPfO/wyofHr5Nucvj5GbrSNMkXYZS+KpKESq8jf1YHPzpeee8qDpKrFEEmFZoEjycjIAyM/W ycnSsYTAEjaJZLr/wtMefhwcuqguLt+PRyKh919vf5R79w0sS2BaFgrpF9c0BdMUmCK9fWnZ z4kjTWzL5OP29mNrum3b1FZVnYnEAy9O3/1zV+/1GVzuXDaDcUZ/nWVpNYCmKcTjJqteg+b9 VXSdPLCWV1B2MmGmUIRIn8uh6TnByObIR18ONXzw+RDBtTBEk5C3DTJUcgoyefPYY5w+8cRs QeH2RxJmKgL8C/gb4piYmnijpKTorVtjy0Uzf2wgbUlthYt9e8oD4XDwbEPdQ12JlJlCSUf8 DyAYCFCQn8309Eyl2+1stYWoBRRVVecMI9hXU1s9b/jDuN2l/AP4awAvqaE3niQlYAAAAABJ RU5ErkJggg== --_=_swift-200363721551368097e51ca9.49483358_=_ Content-Type: image/png; name=twi.png Content-Transfer-Encoding: base64 Content-Disposition: inline; filename=twi.png Content-ID: iVBORw0KGgoAAAANSUhEUgAAABAAAAAQCAYAAAAf8/9hAAAACXBIWXMAAAsTAAALEwEAmpwY AAAAIGNIUk0AAHolAACAgwAA+f8AAIDpAAB1MAAA6mAAADqYAAAXb5JfxUYAAANpSURBVHja fJJtTNR1AMc////9747jQe6OA6wDTyiEG49FzjVRZ1kK0zFqqy2ZrtWLeuWrVm+yXtRqy2Wb pQ3baq0aDnMDpEKbpY0NxDDAOOLQsaDB3XHc8+P/4dcLZ9mbPu+/n31efCUhBP8iOHP6TPGz h/YfX1oJXNhaUzMeicVwOpxEo1HsDgfxWAyHw0EsssFmdxXyfWveevN4zZGjR8dn4tbXTBbr 5dmZmRcbG7wW/g8hBEIIhgYH92ZyefHSt7dF/aeL4sTIlIgs+cTMzPTS+YGBLhOYgsEgi34/ 4fV17vgXSKfTdwse37GjrLPzwJWnzs4xHUzjLjUzvGHnRlhQW1Hq8Xq9IzempsbP9vV56+vq pPsDZEWSpO9HRy+83D/PWjyHTZZ4Y7udk10efgwW8J0/SUN1OZUu+2PP9PTMTUxODvV0d7uQ 7nrkweHh+nBa7B6ZDVGgwB53AfPCyqPnV3llp4cvfRqnri7zV1Rlc9kmGj0VB4fOfRGKhAKn 25qbrUpjU1PPwM1V8qpKLptDMTSWUwYIg1N/JOjaW08oa7Aqp+g9OUGpWWc5mOS5R8pf/enS xZxisykP+wNJZN0gm8mTzaqYTYBF5sOpBOhxSAv6Dm+hze1ixBciGTNxJy6j63qlYhhGTugG mXQWswL5rEqBJIFq8MluByXo6JKEdXmFS741CiVBUstjMlRkibwSj6d+bXHbyMUz5MwyiVSG UrMJNKiymaiVVPIGfD0fIBJLY7cpkMjifaAQTZJuyfv3Pf3N89sfBE1FzeUYvbVGd6UMhWa6 fwjTfCVL+2iGXQfb6dhSTDSSAlXlyM5qfv5l/CtTNBbRAoGATchyx9jYMjFNR4sn+OxwE0qJ Da+rgIaqIjrLTHx07jrp2+u8cKiWA63Oj/d07BqQdE3DoiiWZCa8sO/tq56xa39CsYVKdwk9 7W5KbVaEEHx+bZHQ5Aotez1cf/eJtSKne2tWzeckXdMAsChKUSwZmHinf67x/f5ZWM9AXgfD gLwGrkKO9TbxXm/rQonT3Z7V1CRC8I8ABBbFbJmevXms0lX++uXptbLflqIIIWip3sSTrRXR eCp2orGh7YNsPpe/98T/CGLxKPYiG7/7fLVlTns3urENkCST5N+IJAbrtj20uB5OUF5RwT3B 3wMAPuibzO4+nh8AAAAASUVORK5CYII= --_=_swift-200363721551368097e51ca9.49483358_=_ Content-Type: image/jpeg; name=arteenviodp.jpg Content-Transfer-Encoding: base64 Content-Disposition: inline; filename=arteenviodp.jpg Content-ID: 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 C4bOG41SbxrXsGZodjsKkhppmNAOspt4zimFOhceLh5K8lbWWCNWsoKZ8Mf5bexR3wsGxo7F ayxKO+Gq+mcSqdG33R2JssaNwU18eU0TT2IUiFoG5c2JZGK4UAgkHaPOuFw3BBqkva6MFz2O aB7w29SgEmhXWERva/gQewpIdm3Eda4/YEB6W1wcA4bDiuqHpcj5bWNzxQlv/RTFDQIQhAM2 szZ4myMNQQE8srGy60Rx5IMtv7u8K3tdctbketld7rsFAWaE22eN+IcD5UrmN4jtVApCTzG8 R2o5jeI7UApCTzG8R2o5jeI7UApCTzG8R2o5jeI7UApCTzG8R2o5jeI7UApCTzG8R2o5jeI7 UApCTzG8R2o5jeI7UApCTzG8R2o5jeI7UApCTzG8R2o5jeI7UApCTzG8R2o5jeI7UApCTzG8 R2o5jeI7UApCTzG8R2o5jeI7UApCTzG8R2o5jeI7UApCTzG8R2o5jeI7UApCTzG8R2o5jeI7 UApCTzG8R2o5jeI7UApCTzG8R2o5jeI7UApCTzG8R2o5jeI7UApCTzG8R2o5jeI7UApCTzG8 R2o5jeI7UApCTzG8R2o5jeI7UApCTzG8R2o5jeI7UApCTzG8R2o5jeI7UApCTzG8R2o5jeI7 UAPFQVjdVipKajBbLO3iO1V93ZRTgmoqoypw5MewBnq0CczJd3bG3eabE0WyUBbQ12rz243O B76e4q19WDFhyMyZrN7oRWb3Qs9u2h071NR/MV0Epkc3g1FZgagBNltB3qaj9F0BMcyb3Qu5 5uATt20HepqPgJVKqPnmG5vnSRPNWhACbLaE71H1Jgal5cFDbLOcKNXebcHc1VUYfJVdSaE6 1tRiqwyzt3NShcXA2ZPOrtZnuVfUscM23amX0DhwUXxF1XAN7EF9y/blR0toRctV1JEu3Dgm LmpjPkSSLl22nYkSsmDCX0p1LfFS2+r8UY5uWj47pP8Ai/6Gs0H/AGMf+L/MVZKt0H/Yx/4v 8xVkvRf7rfM+fT7a/IEiXNkdk9ahy9e5LQsmzzxxL3OdIe8XHN1pBzDBri3qU69idbPLZKB2 YmgNTjiFE5sbngY1I3iipmBbbmRjSxpo07QkNbU7UusXEJ9j4KHj1IRJIrTexA7+xHzCPdXs V0xmnUxtiT1/pToj07/i/vIUohqUY49iebrEbfZKuhFYf8QfEEvlWAw8IO0ICobr0Q9kqRF9 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 QgBCEIAQhCAEIQgBCEIAQhCA/9k= --_=_swift-200363721551368097e51ca9.49483358_=_ Content-Type: image/png; name=facebook.png Content-Transfer-Encoding: base64 Content-Disposition: inline; filename=facebook.png Content-ID: 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 ANUi444x1g2bAAAAAElFTkSuQmCC --_=_swift-200363721551368097e51ca9.49483358_=_ Content-Type: image/png; name=twitter.png Content-Transfer-Encoding: base64 Content-Disposition: inline; filename=twitter.png Content-ID: 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 Twy/uv3fANiVDxWvAoVaAAAAAElFTkSuQmCC --_=_swift-200363721551368097e51ca9.49483358_=_ Content-Type: image/png; name=youtube.png Content-Transfer-Encoding: base64 Content-Disposition: inline; filename=youtube.png Content-ID: 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 --_=_swift-200363721551368097e51ca9.49483358_=_-- From hpj@urpla.net Tue Mar 5 17:48:53 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id C6F7F8064 for ; Tue, 5 Mar 2013 17:48:53 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay1.corp.sgi.com (Postfix) with ESMTP id B04708F8074 for ; Tue, 5 Mar 2013 15:48:50 -0800 (PST) X-ASG-Debug-ID: 1362527325-04cbb07dbf1da4f0001-NocioJ Received: from moutng.kundenserver.de (moutng.kundenserver.de [212.227.17.9]) by cuda.sgi.com with ESMTP id Ecqqer5gwAKh9yMB (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Tue, 05 Mar 2013 15:48:46 -0800 (PST) X-Barracuda-Envelope-From: hpj@urpla.net X-Barracuda-Apparent-Source-IP: 212.227.17.9 Received: from lisa (p5B2A4BB3.dip0.t-ipconnect.de [91.42.75.179]) by mrelayeu.kundenserver.de (node=mreu2) with ESMTP (Nemesis) id 0M8M5O-1Uyp3W2nfm-00vMZY; Wed, 06 Mar 2013 00:48:36 +0100 Received: from localhost (localhost [127.0.0.1]) by tyrex.lisa.loc (Postfix) with ESMTP id 55D861B971B00; Wed, 6 Mar 2013 00:48:36 +0100 (CET) X-Virus-Scanned: amavisd-new at lisa.loc Received: from tyrex.lisa.loc ([127.0.0.1]) by localhost (tyrex.lisa.loc [127.0.0.1]) (amavisd-new, port 10024) with LMTP id zfBeF8RV1o9y; Wed, 6 Mar 2013 00:48:27 +0100 (CET) From: Hans-Peter Jansen To: Dave Chinner Cc: xfs@oss.sgi.com Subject: Re: strange behavior of a larger xfs directory Date: Wed, 06 Mar 2013 00:48:25 +0100 X-ASG-Orig-Subj: Re: strange behavior of a larger xfs directory Message-ID: <1517139.CltWl8VXzZ@xrated> User-Agent: KMail/4.9.5 (Linux/3.4.28-2.20-desktop; KDE/4.9.5; x86_64; ; ) In-Reply-To: <20130305222941.GP26081@dastard> References: <4300208.uZ6HVTycB6@xrated> <8026381.3dEJ1E4pzL@xrated> <20130305222941.GP26081@dastard> MIME-Version: 1.0 Content-Type: multipart/mixed; boundary="nextPart2973599.LGyd7z4d3N" Content-Transfer-Encoding: 7Bit X-Provags-ID: V02:K0:Qv183VLIYxytZFBuZZzG45FMSTce8dZSNTS5n++m0R6 RLjgIdvBgQtXleaNPcrTBpz/Vp/n3Q+aOU2eCEW4d/YcEYFQ99 Dv4XZcnhTFJFghIXms4PIMsHY4f6qfEFq8TfRcJcgQlDXNbzSa 88vuvDyyWBD2tbioXBZxrjjBDgJUXeQxOQYIUpB+KDNhRr8ERY dE/s2SBHJSRbFhu1SyjrDlLRbljxK3EPOPjbphI0KXT/pTYBli 4i8sTFqj3TCm4dLJp59Q50+CHYkIcXAi40BOIMpqP4Hnc4kNiX 2tgmHYsOBzCIylmb6ezoeEIUtgmp7IvwYy/Isr3YZYDlBroCw= = X-Barracuda-Connect: moutng.kundenserver.de[212.227.17.9] X-Barracuda-Start-Time: 1362527325 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.10 X-Barracuda-Spam-Status: No, SCORE=0.10 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_SA085 X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124365 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.10 BSF_SC0_SA085 Custom Rule SA085 This is a multi-part message in MIME format. --nextPart2973599.LGyd7z4d3N Content-Transfer-Encoding: quoted-printable Content-Type: text/plain; charset="iso-8859-1" Am Mittwoch, 6. M=E4rz 2013, 09:29:41 schrieb Dave Chinner: > On Tue, Mar 05, 2013 at 09:32:02PM +0100, Hans-Peter Jansen wrote: > > Am Dienstag, 5. M=E4rz 2013, 10:05:27 schrieb Dave Chinner: > > > On Mon, Mar 04, 2013 at 05:40:13PM +0100, Hans-Peter Jansen wrote= : > > > Second solution: Run 3.8.1, make sure you mount with inode32, and= > > > then run the xfs_reno tool mentioned on this page: > > >=20 > > > http://xfs.org/index.php/Unfinished_work > > >=20 > > > to find all the inodes with inode numbers larger than 32 > > > bits and move them to locations with smaller inode numbers. > >=20 > > Okay, I would like to take that route. > >=20 > > I've updated the xfsprogs, xfsdump and xfstests packages in my open= SUSE > > build service repo home:frispete:tools to current versions today, a= nd > > plan to submit them to Factory. openSUSE is always lagging in this = area. > >=20 > > I've tried to include a build of the xfs_reno tool in xfsprogs, sin= ce, as > > you mentioned, others might have a similar need soon. Unfortunately= I > > failed so far, because it is using some attr_multi and attr_list > > interfaces, that aren't part of the xfsprogs visible API anymore. O= nly > > the handle(3) man page refers to them. > >=20 > > Attached is my current state: I've relocated the patch to xfsprogs = 3.1.9, > > because it already carries all the necessary headers (apart from > > attr_multi > > and attr_list). The attr interfaces seem to be collected in libhand= le now, > > hence I've added it to the build. >=20 > attr_list and attr_multi are supplied by libattr, you should not > need the *by_handle variants at all - they are special sauce used by > xfsdump, not xfs_reno.... Ahh, I see. These interfaces cannot be exercised much, given that googl= e=20 didn't relate them to libattr prominently.. > ..... >=20 > > +TOPDIR =3D .. > > +include $(TOPDIR)/include/builddefs > > + > > +LTCOMMAND =3D xfs_reno > > +CFILES =3D xfs_reno.c > > +LLDLIBS =3D $(LIBATTR) >=20 > The patch assumes that libattr has been found by autoconf and set up > in $(LIBATTR), but xfsprogs does not currently use libattr and hence > that variable isn't set up. Therefore this line is a no-op: >=20 > +LLDLIBS =3D $(LIBATTR) >=20 > Change it to: >=20 > LLDLIBS =3D -lattr >=20 > And the xfs_reno should then link. >=20 > BTW, if you want extra points and add the autoconf magic to the > patch, copy it from the xfsdump tree. The places you need to copy > from are: >=20 > $ git grep -l LIBATTR |grep -v Makefile > configure.ac > include/builddefs.in > m4/package_attrdev.m4 > $ Done that up to this point ;-) Nice and easy.=20 Committed, attached, and public build is on the way. Dave, you made my day, ahem, night. Thank you very much. To a casual consumer of this thread: go, grab the xfs_reno.patch in the= =20 preceding mail, and the attached patch, apply both to a current version= of=20 xfsprogs, build, and read man xfs_reno. Seriously. > And for even more bonus points, you could write a basic xfstest that > creates a bunch of 64 bit inodes and then runs xfs_reno on it and > checks that they get moved to 32 bit inodes. At that point, we could > probably pull the xfs_reno patch into xfsprogs and ship it.... Hmm, any idea on how xfs can be tricked into generating 64 bit inodes w= ithout=20 the need to create an excessive big test fs, or is this an accepted pra= ctice? Note to myself: xfs_reno could use some mount option check. Forgot to r= emount=20 one partition with inode32 and, consequently, moved the offending inode= s to=20 another 64 bit value.. Cheers, Pete --nextPart2973599.LGyd7z4d3N Content-Disposition: attachment; filename="xfs_reno_fix.diff" Content-Transfer-Encoding: 7Bit Content-Type: text/x-patch; charset="UTF-8"; name="xfs_reno_fix.diff" Index: b/configure.ac =================================================================== --- a/configure.ac +++ b/configure.ac @@ -101,6 +101,10 @@ AC_PACKAGE_NEED_UUIDCOMPARE AC_PACKAGE_NEED_PTHREAD_H AC_PACKAGE_NEED_PTHREADMUTEXINIT +AC_PACKAGE_NEED_ATTRIBUTES_H +AC_PACKAGE_NEED_ATTRIBUTES_MACROS +AC_PACKAGE_NEED_ATTRGET_LIBATTR + AC_HAVE_FADVISE AC_HAVE_MADVISE AC_HAVE_MINCORE Index: b/include/builddefs.in =================================================================== --- a/include/builddefs.in +++ b/include/builddefs.in @@ -34,6 +34,7 @@ LIBTERMCAP = @libtermcap@ LIBEDITLINE = @libeditline@ LIBREADLINE = @libreadline@ LIBBLKID = @libblkid@ +LIBATTR = @libattr@ LIBXFS = $(TOPDIR)/libxfs/libxfs.la LIBXCMD = $(TOPDIR)/libxcmd/libxcmd.la LIBXLOG = $(TOPDIR)/libxlog/libxlog.la Index: b/m4/package_attrdev.m4 =================================================================== --- /dev/null +++ b/m4/package_attrdev.m4 @@ -0,0 +1,79 @@ +AC_DEFUN([AC_PACKAGE_NEED_ATTR_XATTR_H], + [ AC_CHECK_HEADERS([attr/xattr.h]) + if test "$ac_cv_header_attr_xattr_h" != "yes"; then + echo + echo 'FATAL ERROR: attr/xattr.h does not exist.' + echo 'Install the extended attributes (attr) development package.' + echo 'Alternatively, run "make install-dev" from the attr source.' + exit 1 + fi + ]) + +AC_DEFUN([AC_PACKAGE_NEED_ATTR_ERROR_H], + [ AC_CHECK_HEADERS([attr/error_context.h]) + if test "$ac_cv_header_attr_error_context_h" != "yes"; then + echo + echo 'FATAL ERROR: attr/error_context.h does not exist.' + echo 'Install the extended attributes (attr) development package.' + echo 'Alternatively, run "make install-dev" from the attr source.' + exit 1 + fi + ]) + +AC_DEFUN([AC_PACKAGE_NEED_ATTRIBUTES_H], + [ have_attributes_h=false + AC_CHECK_HEADERS([attr/attributes.h sys/attributes.h], [have_attributes_h=true], ) + if test "$have_attributes_h" = "false"; then + echo + echo 'FATAL ERROR: attributes.h does not exist.' + echo 'Install the extended attributes (attr) development package.' + echo 'Alternatively, run "make install-dev" from the attr source.' + exit 1 + fi + ]) + +AC_DEFUN([AC_PACKAGE_WANT_ATTRLIST_LIBATTR], + [ AC_CHECK_LIB(attr, attr_list, [have_attr_list=true], [have_attr_list=false]) + AC_SUBST(have_attr_list) + ]) + +AC_DEFUN([AC_PACKAGE_NEED_GETXATTR_LIBATTR], + [ AC_CHECK_LIB(attr, getxattr,, [ + echo + echo 'FATAL ERROR: could not find a valid Extended Attributes library.' + echo 'Install the extended attributes (attr) development package.' + echo 'Alternatively, run "make install-lib" from the attr source.' + exit 1 + ]) + libattr="-lattr" + test -f ${libexecdir}${libdirsuffix}/libattr.la && \ + libattr="${libexecdir}${libdirsuffix}/libattr.la" + AC_SUBST(libattr) + ]) + +AC_DEFUN([AC_PACKAGE_NEED_ATTRGET_LIBATTR], + [ AC_CHECK_LIB(attr, attr_get,, [ + echo + echo 'FATAL ERROR: could not find a valid Extended Attributes library.' + echo 'Install the extended attributes (attr) development package.' + echo 'Alternatively, run "make install-lib" from the attr source.' + exit 1 + ]) + libattr="-lattr" + test -f ${libexecdir}${libdirsuffix}/libattr.la && \ + libattr="${libexecdir}${libdirsuffix}/libattr.la" + AC_SUBST(libattr) + ]) + +AC_DEFUN([AC_PACKAGE_NEED_ATTRIBUTES_MACROS], + [ AC_MSG_CHECKING([macros in attr/attributes.h]) + AC_TRY_LINK([ +#include +#include ], + [ int x = ATTR_SECURE; ], [ echo ok ], [ + echo + echo 'FATAL ERROR: could not find a current attributes header.' + echo 'Upgrade the extended attributes (attr) development package.' + echo 'Alternatively, run "make install-dev" from the attr source.' + exit 1 ]) + ]) --nextPart2973599.LGyd7z4d3N-- From david@fromorbit.com Tue Mar 5 18:57:52 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 6EEEF804D for ; Tue, 5 Mar 2013 18:57:52 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay2.corp.sgi.com (Postfix) with ESMTP id 4BF03304067 for ; Tue, 5 Mar 2013 16:57:49 -0800 (PST) X-ASG-Debug-ID: 1362531467-04bdf022981f3f60001-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id utn6WS1WD2pHC0re for ; Tue, 05 Mar 2013 16:57:47 -0800 (PST) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AlogAKWTNlF5Layr/2dsb2JhbABEh363WIUSAQIBgXEXc4IrAQEEATIBIyMFCwgDGAklDwUlAyETiA0FvBoVjXcYHxczB4JfYQOWSYEfj1CDHA Received: from ppp121-45-172-171.lns20.syd6.internode.on.net (HELO dastard) ([121.45.172.171]) by ipmail05.adl6.internode.on.net with ESMTP; 06 Mar 2013 11:27:46 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UD2fx-0001MT-1x; Wed, 06 Mar 2013 11:57:45 +1100 Date: Wed, 6 Mar 2013 11:57:45 +1100 From: Dave Chinner To: Hans-Peter Jansen Cc: xfs@oss.sgi.com Subject: Re: strange behavior of a larger xfs directory Message-ID: <20130306005744.GA4549@dastard> X-ASG-Orig-Subj: Re: strange behavior of a larger xfs directory References: <4300208.uZ6HVTycB6@xrated> <8026381.3dEJ1E4pzL@xrated> <20130305222941.GP26081@dastard> <1517139.CltWl8VXzZ@xrated> MIME-Version: 1.0 Content-Type: text/plain; charset=iso-8859-1 Content-Disposition: inline Content-Transfer-Encoding: 8bit In-Reply-To: <1517139.CltWl8VXzZ@xrated> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1362531467 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124369 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Wed, Mar 06, 2013 at 12:48:25AM +0100, Hans-Peter Jansen wrote: > Am Mittwoch, 6. Mrz 2013, 09:29:41 schrieb Dave Chinner: > > On Tue, Mar 05, 2013 at 09:32:02PM +0100, Hans-Peter Jansen wrote: > > attr_list and attr_multi are supplied by libattr, you should not > > need the *by_handle variants at all - they are special sauce used by > > xfsdump, not xfs_reno.... > > Ahh, I see. These interfaces cannot be exercised much, given that google > didn't relate them to libattr prominently.. Attributes are not widely used by applications for some reason... > Hmm, any idea on how xfs can be tricked into generating 64 bit inodes without > the need to create an excessive big test fs, or is this an accepted practice? The usual trick is to use a sparse loopback device and create the filesystem on that. see, for example, xfstests 078, where it is testing growfs on filesystems up to 16TB in size on a loopback device... > Note to myself: xfs_reno could use some mount option check. Forgot to remount > one partition with inode32 and, consequently, moved the offending inodes to > another 64 bit value.. I'd just use a wrapper script that checked /proc/mounts for the inode64 flag being set first.... .... > Index: b/configure.ac > =================================================================== > --- a/configure.ac > +++ b/configure.ac .... The patch looks sane - can you add a commit description and s Signed-off-by line to it, and then we can use it directly.... Cheers, Dave. -- Dave Chinner david@fromorbit.com From steve@adailyzone.com Wed Mar 6 00:23:49 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=HTML_MESSAGE,T_REMOTE_IMAGE autolearn=ham version=3.3.1 X-Original-To: linux-xfs@oss.sgi.com Delivered-To: linux-xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 1D94E802C for ; Wed, 6 Mar 2013 00:23:49 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay1.corp.sgi.com (Postfix) with ESMTP id E18F98F8078 for ; Tue, 5 Mar 2013 22:23:44 -0800 (PST) X-ASG-Debug-ID: 1362551023-04bdf02298202170001-w1Z2WR Received: from sm-mail2.lunarbreeze.com (sm-mail2.lunarbreeze.com [209.200.245.224]) by cuda.sgi.com with ESMTP id gElbgfkSixGeN26A for ; Tue, 05 Mar 2013 22:23:43 -0800 (PST) X-Barracuda-Envelope-From: steve@adailyzone.com X-Barracuda-Apparent-Source-IP: 209.200.245.224 Received: from italypc (UnknownHost [122.245.199.228]) by sm-mail2.lunarbreeze.com with SMTP; Tue, 5 Mar 2013 22:23:27 -0800 From: "steve" To: linux-xfs@oss.sgi.com Subject: RE: custom machined turned parts Date: Wed, 6 Mar 2013 14:23:22 +0800 X-ASG-Orig-Subj: RE: custom machined turned parts Message-Id: MIME-Version: 1.0 Content-Type: multipart/alternative; boundary="----=_NextPart_13012315472903111501463_002" X-Priority: 3 X-Mailer: DreamMail 4.6.9.2 Disposition-Notification-To: cutom@cixiyuhang.com X-Barracuda-Connect: sm-mail2.lunarbreeze.com[209.200.245.224] X-Barracuda-Start-Time: 1362551023 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.55 X-Barracuda-Spam-Status: No, SCORE=0.55 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=HTML_FONT_LOW_CONTRAST, HTML_MESSAGE, NO_REAL_NAME X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124390 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 NO_REAL_NAME From: does not include a real name 0.54 HTML_FONT_LOW_CONTRAST BODY: HTML font color similar to background 0.00 HTML_MESSAGE BODY: HTML included in message ------=_NextPart_13012315472903111501463_002 Content-Type: text/plain; charset="GB2312" Content-Transfer-Encoding: base64 RGVhciBsaW51eC14ZnOjrA0KR29vZCBkYXkgIQ0KIA0KVGhhbmtzICBmb3IgeW91ciB0aW1lICB0 byByZWFkIG15IGVtYWlsIDsgIA0KDQogSSBhbSBzdGV2ZSB3dQ0KIGZyb20gQ0lYSSBZVUhBTkcg SEFSRFdBUkUgQ09QT05FTlRTIEZBQ1RPUlkgLA0KV2UgYXJlIGZhY3Rvcnkgb2YgICBicmFzcyAv U3RhaW5sZXNzIGNvbXBvbmVudHMsIHN1Y2ggYXMgOg0KQWx1bWludW0gQ2FtICYgR3Jvb3ZlIFF1 aWNrIENvbm5lY3RvcnMgDQoNCiANCg0KQnJvbnplIEZsYW5nZXMsDQpIVkFDIEZpdHRpbmdzLA0K Q2FzdGluZ3MsU2NyZXdlZCBmaXR0aW5ncywNClZhbHZlIGNvbXBvbmVudHMsTW90b3Igc2hhZnQg LA0KDQpDdXN0b20gbWFjaGluZSAgY29tcG9uZW50cyxhbmQgc28gb24uDQpIZXJlIGlzIHRoZSB3 ZWIgc2l0ZSBvZiBvdXIgZ2FsbGVyeSAuIHlvdSBjYW4gdmlldyBpdA0KR2FsbGVyeToNCmh0dHA6 Ly93d3cuYS1kaC5jb20vc3RhaW5sZXNzLWNvbXBvbmVudHMvICANCmh0dHA6Ly9tYWNoaW5lZC1j b21wb25lbnRzLmEtZGguY29tOyANCmlmIHlvdSBoYXZlIGFueSBpZGVhcyAgUGxlYXNlIGZlZWwg ZnJlZSB0byBsZXQgdXMga25vdyAudGhhbmsgeW91IQ0KTVNOOmZvcnR1bmVmYXVjZXRAaG90bWFp bC5jb207DQpDZWxsIHBob25lIDo4Ni0xMzczODgwMTk1MDsNCkZBWDo4Ni01NzQtNjM0NTkzNDY7 DQpQT1NUQ09ERTozMTUzMjYNCg0KQWRkcmVzczpDSVhJIENJVFkgLFRJQU5ZVUFOIFRPV04sIFpI RUpJQU5HIFBST1ZJQ0UgQ0hJTkEuDQo= ------=_NextPart_13012315472903111501463_002 Content-Type: text/html; charset="GB2312" Content-Transfer-Encoding: base64 PEhUTUw+PEhFQUQ+DQo8TUVUQSBjb250ZW50PSJLc0RIVE1MRURMaWIub2N4LCBGcmVlV2FyZSBI VE1MIEVkaXRvciAxLjE2NC4yLCA/S3VydCBTZW5mZXIiIA0KbmFtZT1HRU5FUkFUT1I+DQo8TUVU QSBodHRwLWVxdWl2PUNvbnRlbnQtVHlwZSBjb250ZW50PSJ0ZXh0L2h0bWw7IGNoYXJzZXQ9R0Iy MzEyIj48L0hFQUQ+DQo8Qk9EWSANCnN0eWxlPSJCQUNLR1JPVU5ELVBPU0lUSU9OOiByaWdodCAw cHg7IFNDUk9MTEJBUi1GQUNFLUNPTE9SOiAjYzNkM2ZkOyBGT05ULVNJWkU6IDlwdDsgTUFSR0lO OiAxMHB4OyBTQ1JPTExCQVItSElHSExJR0hULUNPTE9SOiAjZmZmZmZmOyBTQ1JPTExCQVItU0hB RE9XLUNPTE9SOiAjMjYxZmJhOyBDT0xPUjogIzAwMDA2NjsgU0NST0xMQkFSLTNETElHSFQtQ09M T1I6ICM3YjllZDY7IFNDUk9MTEJBUi1BUlJPVy1DT0xPUjogIzRhNjE4NDsgQkFDS0dST1VORC1S RVBFQVQ6IHJlcGVhdDsgRk9OVC1GQU1JTFk6IFZlcmRhbmE7IFNDUk9MTEJBUi1EQVJLU0hBRE9X LUNPTE9SOiAjYmViZWJlIiANCmFMaW5rPSNlYzc2MDAgbGluaz0jZWM3NjAwIGJnUHJvcGVydGll cz1maXhlZCBiZ0NvbG9yPSMwMDAwNjAgDQpiYWNrZ3JvdW5kPWh0dHA6Ly9hLWRoLmNvbS8xMjUu Z2lmIHNjcm9sbD15ZXMgT1JHWVBPUz0iMCIgU0lHQ09MT1I9IjY1NTM1Ij4NCjxESVY+PEZPTlQg Y29sb3I9IzAwMDAwMCBzaXplPTM+PC9GT05UPiZuYnNwOzwvRElWPg0KPERJVj48Rk9OVCBjb2xv cj0jMDAwMDAwIHNpemU9Mz5EZWFyIGxpbnV4LXhmc6OsPC9GT05UPjwvRElWPg0KPERJVj48Rk9O VCBjb2xvcj0jMDAwMDAwIHNpemU9Mz5Hb29kIGRheSAhPC9GT05UPjwvRElWPg0KPERJVj48Rk9O VCBjb2xvcj0jMDAwMDAwIHNpemU9Mz48L0ZPTlQ+Jm5ic3A7PC9ESVY+DQo8RElWPjxGT05UIGNv bG9yPSMwMDAwMDAgc2l6ZT0zPlRoYW5rcyZuYnNwOyBmb3IgeW91ciB0aW1lJm5ic3A7IHRvIHJl YWQgbXkgDQplbWFpbCA7Jm5ic3A7IDwvRk9OVD48L0RJVj4NCjxESVY+PEZPTlQgY29sb3I9IzAw MDAwMCBzaXplPTM+PC9GT05UPjwvRElWPg0KPERJVj48Rk9OVCBjb2xvcj0jMDAwMDAwIHNpemU9 Mz4mbmJzcDtJIGFtIHN0ZXZlIHd1PC9GT05UPjwvRElWPg0KPERJVj48Rk9OVCBjb2xvcj0jMDAw MDAwIHNpemU9Mz4mbmJzcDtmcm9tIENJWEkgWVVIQU5HIEhBUkRXQVJFIENPUE9ORU5UUyANCkZB Q1RPUlkgLDwvRk9OVD48L0RJVj4NCjxESVY+PEZPTlQgY29sb3I9IzAwMDAwMCBzaXplPTM+V2Ug YXJlIGZhY3Rvcnkgb2YmbmJzcDsmbmJzcDsgYnJhc3MgL1N0YWlubGVzcyANCmNvbXBvbmVudHMs IHN1Y2ggYXMgOjwvRk9OVD48L0RJVj4NCjxESVY+PEZPTlQgY29sb3I9IzAwMDAwMCBzaXplPTM+ QWx1bWludW0gQ2FtICZhbXA7IEdyb292ZSBRdWljayBDb25uZWN0b3JzIA0KPC9GT05UPg0KPFA+ Jm5ic3A7PC9QPjwvRElWPg0KPERJVj48QSBocmVmPSJodHRwOi8vd3d3LmEtZGguY29tL3N0YWlu bGVzcy1jb21wb25lbnRzLyI+PEZPTlQgY29sb3I9IzAwMDAwMCANCnNpemU9Mz48SU1HIGFsdD1o dHRwOi8vbWFjaGluZWQtY29tcG9uZW50cy5hLWRoLmNvbSANCnNyYz0iaHR0cDovL2EtZGguY29t L2VtYWlsLmpwZyIgYm9yZGVyPTA+PC9GT05UPjwvQT48L0RJVj4NCjxESVY+PEZPTlQgY29sb3I9 IzAwMDAwMCBzaXplPTM+QnJvbnplIEZsYW5nZXMsPC9GT05UPjwvRElWPg0KPERJVj48Rk9OVCBj b2xvcj0jMDAwMDAwIHNpemU9Mz5IVkFDIEZpdHRpbmdzLDwvRk9OVD48L0RJVj4NCjxESVY+PEZP TlQgY29sb3I9IzAwMDAwMCBzaXplPTM+Q2FzdGluZ3MsU2NyZXdlZCBmaXR0aW5ncyw8L0ZPTlQ+ PC9ESVY+DQo8RElWPjxGT05UIGNvbG9yPSMwMDAwMDAgc2l6ZT0zPlZhbHZlIGNvbXBvbmVudHMs TW90b3Igc2hhZnQgLDwvRk9OVD48L0RJVj4NCjxESVY+PEEgaHJlZj0iaHR0cDovL3d3dy5hLWRo LmNvbS9zdGFpbmxlc3MtY29tcG9uZW50cy8iPjxGT05UIGNvbG9yPSMwMDAwMDAgDQpzaXplPTM+ PC9GT05UPjwvQT48L0RJVj4NCjxESVY+PEZPTlQgY29sb3I9IzAwMDAwMCBzaXplPTM+Q3VzdG9t IG1hY2hpbmUmbmJzcDsgY29tcG9uZW50cyxhbmQgc28gDQpvbi48L0ZPTlQ+PC9ESVY+DQo8RElW PjxGT05UIGNvbG9yPSMwMDAwMDAgc2l6ZT0zPkhlcmUgaXMgdGhlIHdlYiBzaXRlIG9mIG91ciBn YWxsZXJ5IC4geW91IGNhbiANCnZpZXcgaXQ8L0ZPTlQ+PC9ESVY+DQo8RElWPjxGT05UIGNvbG9y PSMwMDAwMDAgc2l6ZT0zPkdhbGxlcnk6PC9GT05UPjwvRElWPg0KPERJVj48QSBocmVmPSJodHRw Oi8vd3d3LmEtZGguY29tL3N0YWlubGVzcy1jb21wb25lbnRzLyI+PEZPTlQgY29sb3I9IzAwMDAw MCANCnNpemU9Mz5odHRwOi8vd3d3LmEtZGguY29tL3N0YWlubGVzcy1jb21wb25lbnRzLzwvRk9O VD48L0E+PEZPTlQgY29sb3I9IzAwMDAwMCANCnNpemU9Mz4gJm5ic3A7PC9GT05UPjwvRElWPg0K PERJVj48QSBocmVmPSJodHRwOi8vbWFjaGluZWQtY29tcG9uZW50cy5hLWRoLmNvbSI+PEZPTlQg Y29sb3I9IzAwMDAwMCANCnNpemU9Mz5odHRwOi8vbWFjaGluZWQtY29tcG9uZW50cy5hLWRoLmNv bTwvRk9OVD48L0E+PEZPTlQgY29sb3I9IzAwMDAwMCANCnNpemU9Mz47IDwvRk9OVD48L0RJVj4N CjxESVY+PEZPTlQgY29sb3I9IzAwMDBmZiBzaXplPTM+PEVNPmlmIHlvdSBoYXZlIGFueSBpZGVh cyZuYnNwOyBQbGVhc2UgZmVlbCBmcmVlIA0KdG8gbGV0IHVzIGtub3cgLnRoYW5rIHlvdSE8L0VN PjwvRk9OVD48L0RJVj4NCjxESVY+PEZPTlQgY29sb3I9IzAwMDAwMCBzaXplPTM+TVNOOmZvcnR1 bmVmYXVjZXRAaG90bWFpbC5jb207PC9GT05UPjwvRElWPg0KPERJVj48Rk9OVCBjb2xvcj0jMDAw MDAwIHNpemU9Mz5DZWxsIHBob25lIDo4Ni0xMzczODgwMTk1MDs8L0ZPTlQ+PC9ESVY+DQo8RElW PjxGT05UIGNvbG9yPSMwMDAwMDAgc2l6ZT0zPkZBWDo4Ni01NzQtNjM0NTkzNDY7PC9GT05UPjwv RElWPg0KPERJVj48Rk9OVCBjb2xvcj0jMDAwMDAwIHNpemU9Mz5QT1NUQ09ERTozMTUzMjY8L0ZP TlQ+PC9ESVY+DQo8RElWPjxGT05UIGNvbG9yPSMwMDAwMDAgc2l6ZT0zPjxJTUcgYWx0PVByb2R1 Y3RzIGhzcGFjZT0wIA0Kc3JjPSJodHRwOi8vYS1kaC5jb20vZW1haWw3LmpwZyIgYWxpZ249YmFz ZWxpbmUgYm9yZGVyPTA+PC9GT05UPjwvRElWPg0KPERJVj48Rk9OVCBjb2xvcj0jMDAwMDAwIHNp emU9Mz5BZGRyZXNzOkNJWEkgQ0lUWSAsVElBTllVQU4gVE9XTiwgWkhFSklBTkcgDQpQUk9WSUNF IENISU5BLjwvRk9OVD48L0RJVj4NCjxESVY+PEZPTlQgY29sb3I9IzAwMDAwMCBzaXplPTM+PElN RyBhbHQ9UHJvZHVjdHMgaHNwYWNlPTAgDQpzcmM9Imh0dHA6Ly9hLWRoLmNvbS9lbWFpbDMuanBn IiBhbGlnbj1iYXNlbGluZSBib3JkZXI9MD48L0ZPTlQ+PC9ESVY+DQo8RElWPjxGT05UIGNvbG9y PSMwMDAwMDAgc2l6ZT0zPjwvRk9OVD4mbmJzcDs8L0RJVj4NCjxESVY+PEZPTlQgY29sb3I9IzAw MDAwMCBzaXplPTM+PC9GT05UPiZuYnNwOzwvRElWPjwvQk9EWT48L0hUTUw+DQo= ------=_NextPart_13012315472903111501463_002-- From shrinath.m@webyog.com Wed Mar 6 02:08:10 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=HTML_FONT_FACE_BAD, HTML_MESSAGE,T_DKIM_INVALID autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id B8E208038 for ; Wed, 6 Mar 2013 02:08:10 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id A2290304039 for ; Wed, 6 Mar 2013 00:08:07 -0800 (PST) X-ASG-Debug-ID: 1362557284-04cbb07dbf1f25f0001-NocioJ Received: from mail-ia0-f171.google.com (mail-ia0-f171.google.com [209.85.210.171]) by cuda.sgi.com with ESMTP id eC7O5KOlxR0rA4an (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Wed, 06 Mar 2013 00:08:04 -0800 (PST) X-Barracuda-Envelope-From: shrinath.m@webyog.com X-Barracuda-Apparent-Source-IP: 209.85.210.171 Received: by mail-ia0-f171.google.com with SMTP id z13so7135774iaz.2 for ; Wed, 06 Mar 2013 00:08:04 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=webyog.com; s=google; h=x-received:mime-version:from:date:message-id:subject:to:cc :content-type; bh=SwCFaLiFMfK/1xkNTAv23IhjBQ3tNMV4WfSvPsJpi1I=; b=ZiN6a8Nb1+DGGZqitAgMj1pcnZwSFFqtTl9PJO5yVu+W/ynNkhqW6yEeEjGE/Uyf5H Ki9JxO6nETDcSXpEGoHz3JsRQTUe54tekKbViwzZ/6vMd6F17VgDEe/AlONEwPDPBMMS /tdA0xt0N1apwo25EOPp6uGFFj5vat67iNAOM= X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=20120113; h=x-received:mime-version:from:date:message-id:subject:to:cc :content-type:x-gm-message-state; bh=SwCFaLiFMfK/1xkNTAv23IhjBQ3tNMV4WfSvPsJpi1I=; b=R3MXpb1K++otx3YXLC98IPKMzRST1+acPm7nZwnKrWLwHIJr7O8SRQLjJjFTfqt+a7 RtjS0lH4RRVuxrfT2SPwth4mTbp93qhjytHI3lvA1RatgTy6r39EUbeSPImkNmrs/kYq gC68A1hmv7qEMnThsoDmIbKK8TBWp/DMRtwMwvpod1L89vVgy25U/8T0d5oo/jelGBZm s7vuvDN8jX4Wt5CLpNGd1uWH0uy1KO9a8o4xhMPCIgNVWwvwHgSSGnltJN9fw786SqUx E/Iu/C0X7XyFCxRLXmj5S8o8y8EPtZqHyUmdvI4mHjLt5SRkv+xK8roBEoUDAAXLdoek EEVg== X-Received: by 10.50.194.164 with SMTP id hx4mr9719069igc.35.1362557283784; Wed, 06 Mar 2013 00:08:03 -0800 (PST) MIME-Version: 1.0 Received: by 10.43.1.132 with HTTP; Wed, 6 Mar 2013 00:07:43 -0800 (PST) From: Shrinath M Date: Wed, 6 Mar 2013 13:37:43 +0530 Message-ID: Subject: XFS filesystem on EC2 instance corrupts and shuts down To: xfs@oss.sgi.com X-ASG-Orig-Subj: XFS filesystem on EC2 instance corrupts and shuts down Cc: Sabyasachi Ruj , Vivek Goel Content-Type: multipart/mixed; boundary=14dae9340de1e2fa7104d73d1633 X-Gm-Message-State: ALoCoQm2IzmY3IyRVIM4sLxMSL4G44eBEC+LvlsELqhsS7sCdm0lX+WpYs7bEwDBx2lCb02oUzUP X-Barracuda-Connect: mail-ia0-f171.google.com[209.85.210.171] X-Barracuda-Start-Time: 1362557284 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.61 X-Barracuda-Spam-Status: No, SCORE=0.61 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=DKIM_SIGNED, DKIM_VERIFIED, HTML_FONT_FACE_BAD, HTML_MESSAGE X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124396 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature 0.00 HTML_MESSAGE BODY: HTML included in message 0.61 HTML_FONT_FACE_BAD BODY: HTML font face is not a word --14dae9340de1e2fa7104d73d1633 Content-Type: multipart/alternative; boundary=14dae9340de1e2fa6c04d73d1631 --14dae9340de1e2fa6c04d73d1631 Content-Type: text/plain; charset=UTF-8 We are experiencing a strange XFS corruption issue. If we look in /var/log/messages, it simply says - Mar 5 01:14:33 ip-100-0-100-1 kernel: [14139930.248619] XFS (md0): Corruption detected. Unmount and run xfs_repair It shuts down the filesystem after this. On rebooting, it calls xfs_repair automatically and everything comes back to normal. We have had 2 such occurrences till now, I am attaching the relevant parts of /var/log/messages here, assuming someone can enlighten me on whats going wrong. Machine details are as follows - We are using Amazon AMI version: Amazon Linux AMI release 2012.09 We are running 8 EBS volumes of 512 MB each, in RAID 0 Array. $~: uname -a Linux ip-100-0-100-1 3.2.34-55.46.amzn1.x86_64 #1 SMP Tue Nov 20 10:06:15 UTC 2012 x86_64 x86_64 x86_64 GNU/Linux Ask me if anyone wants any more details -- Regards *Shrinath.M* --14dae9340de1e2fa6c04d73d1631 Content-Type: text/html; charset=UTF-8 Content-Transfer-Encoding: quoted-printable
We are experiencing a strange XFS corruption issue. If we = look in /var/log/messages, it simply says -=C2=A0

=C2=A0 =C2=A0 Mar =C2=A05 01:14:33 ip-100-0-= 100-1 kernel: [14139930.248619] XFS (md0): Corruption detected. Unmount and= run xfs_repair

It s= huts down the filesystem after this. On rebooting, it calls xfs_repair auto= matically and everything comes back to normal.=C2=A0
We hav= e had 2 such=C2=A0occurrences=C2=A0till now, I am attaching the relevant pa= rts of /var/log/messages here, assuming someone can enlighten me on whats g= oing wrong.

Machine details are as follows -=C2=A0

We are using Amazo= n AMI version: Amazon Linux AMI release 2012.09 We are running 8 EBS volumes of 512 MB each, in RAID 0 Array.=20 $~: uname -a Linux ip-100-0-100-1 3.2.34-55.46.amzn1.x86_64 #1 SMP Tue Nov 20 10:06:15 U= TC 2012 x86_64 x86_64 x86_64 GNU/Linux


Ask me if anyone wants any more details

--
Regards
Shrinath.M

--14dae9340de1e2fa6c04d73d1631-- --14dae9340de1e2fa7104d73d1633 Content-Type: text/plain; charset=US-ASCII; name="xfs_corruption_logs.txt" Content-Disposition: attachment; filename="xfs_corruption_logs.txt" Content-Transfer-Encoding: base64 X-Attachment-Id: f_hdy7cecz0 RmViIDEyIDE5OjQ3OjE4IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWzI1NDExNjguMDE0MjQxXSBY RlMgKG1kMCk6IENvcnJ1cHRpb24gZGV0ZWN0ZWQuIFVubW91bnQgYW5kIHJ1biB4ZnNfcmVwYWly CkZlYiAxMiAxOTo0NzoxOCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsyNTQxMTY4LjAxNDI1OV0g WEZTIChtZDApOiB4ZnNfaXVubGlua19yZW1vdmU6IHhmc19pdG9icCgpIHJldHVybmVkIGVycm9y IDExNy4KRmViIDEyIDE5OjQ3OjE4IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWzI1NDExNjguMDE0 MjY3XSBYRlMgKG1kMCk6IHhmc19pbmFjdGl2ZTogeGZzX2lmcmVlIHJldHVybmVkIGVycm9yIDEx NwpGZWIgMTIgMTk6NDc6MTggaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbMjU0MTE2OC4wMTQyNzRd IFhGUyAobWQwKTogeGZzX2RvX2ZvcmNlX3NodXRkb3duKDB4MSkgY2FsbGVkIGZyb20gbGluZSA3 NDUgb2YgZmlsZSBmcy94ZnMveGZzX3Zub2Rlb3BzLmMuICBSZXR1cm4gYWRkcmVzcyA9IDB4ZmZm ZmZmZmZhMDIxNDEwZgpGZWIgMTIgMTk6NDc6MTggaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbMjU0 MTE2OC4wMjM2MzhdIFhGUyAobWQwKTogSS9PIEVycm9yIERldGVjdGVkLiBTaHV0dGluZyBkb3du IGZpbGVzeXN0ZW0KRmViIDEyIDE5OjQ3OjE4IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWzI1NDEx NjguMDIzNjU0XSBYRlMgKG1kMCk6IFBsZWFzZSB1bW91bnQgdGhlIGZpbGVzeXN0ZW0gYW5kIHJl Y3RpZnkgdGhlIHByb2JsZW0ocykKRmViIDEyIDE5OjQ3OjQzIGlwLTEwMC0wLTEwMC0xIGtlcm5l bDogWzI1NDExOTMuMDUyMDQxXSBYRlMgKG1kMCk6IHhmc19sb2dfZm9yY2U6IGVycm9yIDUgcmV0 dXJuZWQuCkZlYiAxMiAxOTo0ODoxMyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsyNTQxMjIzLjEz MjAzOF0gWEZTIChtZDApOiB4ZnNfbG9nX2ZvcmNlOiBlcnJvciA1IHJldHVybmVkLgpGZWIgMTIg MTk6NDg6NDMgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbMjU0MTI1My4yMTIwMzBdIFhGUyAobWQw KTogeGZzX2xvZ19mb3JjZTogZXJyb3IgNSByZXR1cm5lZC4KRmViIDEyIDE5OjQ5OjEzIGlwLTEw MC0wLTEwMC0xIGtlcm5lbDogWzI1NDEyODMuMjkyMDM0XSBYRlMgKG1kMCk6IHhmc19sb2dfZm9y Y2U6IGVycm9yIDUgcmV0dXJuZWQuCkZlYiAxMiAxOTo0OTo0MyBpcC0xMDAtMC0xMDAtMSBrZXJu ZWw6IFsyNTQxMzEzLjM3MjAzNl0gWEZTIChtZDApOiB4ZnNfbG9nX2ZvcmNlOiBlcnJvciA1IHJl dHVybmVkLgpGZWIgMTIgMTk6NTA6MTQgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbMjU0MTM0My40 NTIwMzRdIFhGUyAobWQwKTogeGZzX2xvZ19mb3JjZTogZXJyb3IgNSByZXR1cm5lZC4KRmViIDEy IDE5OjUwOjQ0IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWzI1NDEzNzMuNTMyMDQ2XSBYRlMgKG1k MCk6IHhmc19sb2dfZm9yY2U6IGVycm9yIDUgcmV0dXJuZWQuCkZlYiAxMiAxOTo1MToxNCBpcC0x MDAtMC0xMDAtMSBrZXJuZWw6IFsyNTQxNDAzLjYxMjAzMV0gWEZTIChtZDApOiB4ZnNfbG9nX2Zv cmNlOiBlcnJvciA1IHJldHVybmVkLgpGZWIgMTIgMTk6NTE6NDQgaXAtMTAwLTAtMTAwLTEga2Vy bmVsOiBbMjU0MTQzMy42OTIwMzddIFhGUyAobWQwKTogeGZzX2xvZ19mb3JjZTogZXJyb3IgNSBy ZXR1cm5lZC4KRmViIDEyIDE5OjUyOjE0IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWzI1NDE0NjMu NzcyMDM1XSBYRlMgKG1kMCk6IHhmc19sb2dfZm9yY2U6IGVycm9yIDUgcmV0dXJuZWQuCkZlYiAx MiAxOTo1Mjo0NCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsyNTQxNDkzLjg1MjAzNF0gWEZTICht ZDApOiB4ZnNfbG9nX2ZvcmNlOiBlcnJvciA1IHJldHVybmVkLgpGZWIgMTIgMTk6NTM6MTQgaXAt MTAwLTAtMTAwLTEga2VybmVsOiBbMjU0MTUyMy45MzIwNDNdIFhGUyAobWQwKTogeGZzX2xvZ19m b3JjZTogZXJyb3IgNSByZXR1cm5lZC4KRmViIDEyIDE5OjUzOjQ0IGlwLTEwMC0wLTEwMC0xIGtl cm5lbDogWzI1NDE1NTQuMDEyMDMyXSBYRlMgKG1kMCk6IHhmc19sb2dfZm9yY2U6IGVycm9yIDUg cmV0dXJuZWQuCkZlYiAxMiAxOTo1NDoxNCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsyNTQxNTg0 LjA5MjAzN10gWEZTIChtZDApOiB4ZnNfbG9nX2ZvcmNlOiBlcnJvciA1IHJldHVybmVkLgpGZWIg MTIgMTk6NTQ6NDQgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbMjU0MTYxNC4xNzIwMzddIFhGUyAo bWQwKTogeGZzX2xvZ19mb3JjZTogZXJyb3IgNSByZXR1cm5lZC4KRmViIDEyIDE5OjU1OjE0IGlw LTEwMC0wLTEwMC0xIGtlcm5lbDogWzI1NDE2NDQuMjUyMDQ2XSBYRlMgKG1kMCk6IHhmc19sb2df Zm9yY2U6IGVycm9yIDUgcmV0dXJuZWQuCkZlYiAxMiAxOTo1NTo0NCBpcC0xMDAtMC0xMDAtMSBr ZXJuZWw6IFsyNTQxNjc0LjMzNjAzNF0gWEZTIChtZDApOiB4ZnNfbG9nX2ZvcmNlOiBlcnJvciA1 IHJldHVybmVkLgpGZWIgMTIgMTk6NTY6MTQgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbMjU0MTcw NC40MTIwMzRdIFhGUyAobWQwKTogeGZzX2xvZ19mb3JjZTogZXJyb3IgNSByZXR1cm5lZC4KRmVi IDEyIDE5OjU2OjQ1IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWzI1NDE3MzQuNDkyMDM5XSBYRlMg KG1kMCk6IHhmc19sb2dfZm9yY2U6IGVycm9yIDUgcmV0dXJuZWQuCkZlYiAxMiAxOTo1NzoxNSBp cC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsyNTQxNzY0LjU3MjA0NV0gWEZTIChtZDApOiB4ZnNfbG9n X2ZvcmNlOiBlcnJvciA1IHJldHVybmVkLgpGZWIgMTIgMTk6NTc6NDUgaXAtMTAwLTAtMTAwLTEg a2VybmVsOiBbMjU0MTc5NC42NTIwNDVdIFhGUyAobWQwKTogeGZzX2xvZ19mb3JjZTogZXJyb3Ig NSByZXR1cm5lZC4KRmViIDEyIDE5OjU4OjE1IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWzI1NDE4 MjQuNzMyMDM3XSBYRlMgKG1kMCk6IHhmc19sb2dfZm9yY2U6IGVycm9yIDUgcmV0dXJuZWQuCkZl YiAxMiAxOTo1ODo0NSBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsyNTQxODU0LjgxMjAzNF0gWEZT IChtZDApOiB4ZnNfbG9nX2ZvcmNlOiBlcnJvciA1IHJldHVybmVkLgpGZWIgMTIgMTk6NTk6MTUg aXAtMTAwLTAtMTAwLTEga2VybmVsOiBbMjU0MTg4NC44OTIxMjRdIFhGUyAobWQwKTogeGZzX2xv Z19mb3JjZTogZXJyb3IgNSByZXR1cm5lZC4KRmViIDEyIDE5OjU5OjQ1IGlwLTEwMC0wLTEwMC0x IGtlcm5lbDogWzI1NDE5MTQuOTcyMDMxXSBYRlMgKG1kMCk6IHhmc19sb2dfZm9yY2U6IGVycm9y IDUgcmV0dXJuZWQuCkZlYiAxMiAyMDowMDoxNSBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsyNTQx OTQ1LjA1NjAzNl0gWEZTIChtZDApOiB4ZnNfbG9nX2ZvcmNlOiBlcnJvciA1IHJldHVybmVkLgpG ZWIgMTIgMjA6MDA6NDUgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbMjU0MTk3NS4xMzIwMzddIFhG UyAobWQwKTogeGZzX2xvZ19mb3JjZTogZXJyb3IgNSByZXR1cm5lZC4KRmViIDEyIDIwOjAxOjE1 IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWzI1NDIwMDUuMjEyMDUxXSBYRlMgKG1kMCk6IHhmc19s b2dfZm9yY2U6IGVycm9yIDUgcmV0dXJuZWQuCkZlYiAxMiAyMDowMTo0NSBpcC0xMDAtMC0xMDAt MSBrZXJuZWw6IFsyNTQyMDM1LjI5MjAzNV0gWEZTIChtZDApOiB4ZnNfbG9nX2ZvcmNlOiBlcnJv ciA1IHJldHVybmVkLgpGZWIgMTIgMjA6MDI6MTUgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbMjU0 MjA2NS4zNzIwMzhdIFhGUyAobWQwKTogeGZzX2xvZ19mb3JjZTogZXJyb3IgNSByZXR1cm5lZC4K RmViIDEyIDIwOjAyOjQ2IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWzI1NDIwOTUuNDUyMDM1XSBY RlMgKG1kMCk6IHhmc19sb2dfZm9yY2U6IGVycm9yIDUgcmV0dXJuZWQuCkZlYiAxMiAyMDowMzox NiBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsyNTQyMTI1LjUzMjAzOV0gWEZTIChtZDApOiB4ZnNf bG9nX2ZvcmNlOiBlcnJvciA1IHJldHVybmVkLgpGZWIgMTIgMjA6MDM6NDYgaXAtMTAwLTAtMTAw LTEga2VybmVsOiBbMjU0MjE1NS42MTIwNTBdIFhGUyAobWQwKTogeGZzX2xvZ19mb3JjZTogZXJy b3IgNSByZXR1cm5lZC4KRmViIDEyIDIwOjA0OjE2IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWzI1 NDIxODUuNjkyMDMyXSBYRlMgKG1kMCk6IHhmc19sb2dfZm9yY2U6IGVycm9yIDUgcmV0dXJuZWQu CkZlYiAxMiAyMDowNDo0NiBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsyNTQyMjE1Ljc3MjA0Nl0g WEZTIChtZDApOiB4ZnNfbG9nX2ZvcmNlOiBlcnJvciA1IHJldHVybmVkLgpGZWIgMTIgMjA6MDU6 MTYgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbMjU0MjI0NS44NTIwMzZdIFhGUyAobWQwKTogeGZz X2xvZ19mb3JjZTogZXJyb3IgNSByZXR1cm5lZC4KRmViIDEyIDIwOjA1OjQ2IGlwLTEwMC0wLTEw MC0xIGtlcm5lbDogWzI1NDIyNzUuOTMyMDQ3XSBYRlMgKG1kMCk6IHhmc19sb2dfZm9yY2U6IGVy cm9yIDUgcmV0dXJuZWQuCkZlYiAxMiAyMDowNjoxNiBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsy NTQyMzA2LjAxMjAzMl0gWEZTIChtZDApOiB4ZnNfbG9nX2ZvcmNlOiBlcnJvciA1IHJldHVybmVk LgpGZWIgMTIgMjA6MDY6NDYgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbMjU0MjMzNi4wOTIwMjhd IFhGUyAobWQwKTogeGZzX2xvZ19mb3JjZTogZXJyb3IgNSByZXR1cm5lZC4KRmViIDEyIDIwOjA3 OjE2IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWzI1NDIzNjYuMTcyMDMwXSBYRlMgKG1kMCk6IHhm c19sb2dfZm9yY2U6IGVycm9yIDUgcmV0dXJuZWQuCkZlYiAxMiAyMDowNzo0NiBpcC0xMDAtMC0x MDAtMSBrZXJuZWw6IFsyNTQyMzk2LjI1MjAzNl0gWEZTIChtZDApOiB4ZnNfbG9nX2ZvcmNlOiBl cnJvciA1IHJldHVybmVkLgpGZWIgMTIgMjA6MDg6MTYgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBb MjU0MjQyNi4zMzIwMzJdIFhGUyAobWQwKTogeGZzX2xvZ19mb3JjZTogZXJyb3IgNSByZXR1cm5l ZC4KRmViIDEyIDIwOjA4OjQ2IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWzI1NDI0NTYuNDEyMDMz XSBYRlMgKG1kMCk6IHhmc19sb2dfZm9yY2U6IGVycm9yIDUgcmV0dXJuZWQuCkZlYiAxMiAyMDow OToxNyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsyNTQyNDg2LjQ5MjA5Nl0gWEZTIChtZDApOiB4 ZnNfbG9nX2ZvcmNlOiBlcnJvciA1IHJldHVybmVkLgpGZWIgMTIgMjA6MDk6NDcgaXAtMTAwLTAt MTAwLTEga2VybmVsOiBbMjU0MjUxNi41NzIwMzddIFhGUyAobWQwKTogeGZzX2xvZ19mb3JjZTog ZXJyb3IgNSByZXR1cm5lZC4KRmViIDEyIDIwOjEwOjE3IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDog WzI1NDI1NDYuNjUyMDMwXSBYRlMgKG1kMCk6IHhmc19sb2dfZm9yY2U6IGVycm9yIDUgcmV0dXJu ZWQuCkZlYiAxMiAyMDoxMDo0NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsyNTQyNTc2LjczMjAz Ml0gWEZTIChtZDApOiB4ZnNfbG9nX2ZvcmNlOiBlcnJvciA1IHJldHVybmVkLgpGZWIgMTIgMjA6 MTE6MTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbMjU0MjYwNi44MTIwNDJdIFhGUyAobWQwKTog eGZzX2xvZ19mb3JjZTogZXJyb3IgNSByZXR1cm5lZC4KRmViIDEyIDIwOjExOjQ3IGlwLTEwMC0w LTEwMC0xIGtlcm5lbDogWzI1NDI2MzYuODkyMTM3XSBYRlMgKG1kMCk6IHhmc19sb2dfZm9yY2U6 IGVycm9yIDUgcmV0dXJuZWQuCkZlYiAxMiAyMDoxMjoxNyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6 IFsyNTQyNjY2Ljk3MjAzMV0gWEZTIChtZDApOiB4ZnNfbG9nX2ZvcmNlOiBlcnJvciA1IHJldHVy bmVkLgpGZWIgMTIgMjA6MTI6NDcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbMjU0MjY5Ny4wNTIw MzddIFhGUyAobWQwKTogeGZzX2xvZ19mb3JjZTogZXJyb3IgNSByZXR1cm5lZC4KRmViIDEyIDIw OjEzOjE3IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWzI1NDI3MjcuMTMyMDQyXSBYRlMgKG1kMCk6 IHhmc19sb2dfZm9yY2U6IGVycm9yIDUgcmV0dXJuZWQuCkZlYiAxMiAyMDoxMzo0NyBpcC0xMDAt MC0xMDAtMSBrZXJuZWw6IFsyNTQyNzU3LjIxMjA1Nl0gWEZTIChtZDApOiB4ZnNfbG9nX2ZvcmNl OiBlcnJvciA1IHJldHVybmVkLgpGZWIgMTIgMjA6MTQ6MTcgaXAtMTAwLTAtMTAwLTEga2VybmVs OiBbMjU0Mjc4Ny4yOTIwMzNdIFhGUyAobWQwKTogeGZzX2xvZ19mb3JjZTogZXJyb3IgNSByZXR1 cm5lZC4KRmViIDEyIDIwOjE0OjQ3IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWzI1NDI4MTcuMzcy MDUzXSBYRlMgKG1kMCk6IHhmc19sb2dfZm9yY2U6IGVycm9yIDUgcmV0dXJuZWQuCkZlYiAxMiAy MDoxNToxOCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsyNTQyODQ3LjQ1MjA3N10gWEZTIChtZDAp OiB4ZnNfbG9nX2ZvcmNlOiBlcnJvciA1IHJldHVybmVkLgpGZWIgMTIgMjA6MTU6NDggaXAtMTAw LTAtMTAwLTEga2VybmVsOiBbMjU0Mjg3Ny41MzIwNDRdIFhGUyAobWQwKTogeGZzX2xvZ19mb3Jj ZTogZXJyb3IgNSByZXR1cm5lZC4KRmViIDEyIDIwOjE2OjE4IGlwLTEwMC0wLTEwMC0xIGtlcm5l bDogWzI1NDI5MDcuNjEyMDQwXSBYRlMgKG1kMCk6IHhmc19sb2dfZm9yY2U6IGVycm9yIDUgcmV0 dXJuZWQuCkZlYiAxMiAyMDoxNjo0OCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsyNTQyOTM3LjY5 MjAzNl0gWEZTIChtZDApOiB4ZnNfbG9nX2ZvcmNlOiBlcnJvciA1IHJldHVybmVkLgpGZWIgMTIg MjA6MTc6MTcgaXAtMTAwLTAtMTAwLTEgaW5pdDogc2VyaWFsIChodmMwKSBtYWluIHByb2Nlc3Mg KDE3NjMpIGtpbGxlZCBieSBURVJNIHNpZ25hbApGZWIgMTIgMjA6MTc6MTcgaXAtMTAwLTAtMTAw LTEgaW5pdDogdHR5ICgvZGV2L3R0eTEpIG1haW4gcHJvY2VzcyAoMTc2NCkga2lsbGVkIGJ5IFRF Uk0gc2lnbmFsCkZlYiAxMiAyMDoxNzoxNyBpcC0xMDAtMC0xMDAtMSBpbml0OiB0dHkgKC9kZXYv dHR5MikgbWFpbiBwcm9jZXNzICgxNzY3KSBraWxsZWQgYnkgVEVSTSBzaWduYWwKRmViIDEyIDIw OjE3OjE3IGlwLTEwMC0wLTEwMC0xIGluaXQ6IHR0eSAoL2Rldi90dHkzKSBtYWluIHByb2Nlc3Mg KDE3NzApIGtpbGxlZCBieSBURVJNIHNpZ25hbApGZWIgMTIgMjA6MTc6MTcgaXAtMTAwLTAtMTAw LTEgaW5pdDogdHR5ICgvZGV2L3R0eTQpIG1haW4gcHJvY2VzcyAoMTc3Mykga2lsbGVkIGJ5IFRF Uk0gc2lnbmFsCkZlYiAxMiAyMDoxNzoxNyBpcC0xMDAtMC0xMDAtMSBpbml0OiB0dHkgKC9kZXYv dHR5NSkgbWFpbiBwcm9jZXNzICgxNzc1KSBraWxsZWQgYnkgVEVSTSBzaWduYWwKRmViIDEyIDIw OjE3OjE3IGlwLTEwMC0wLTEwMC0xIGluaXQ6IHR0eSAoL2Rldi90dHk2KSBtYWluIHByb2Nlc3Mg KDE3NzcpIGtpbGxlZCBieSBURVJNIHNpZ25hbApGZWIgMTIgMjA6MTc6MTcgaXAtMTAwLTAtMTAw LTEgaW5pdDogcGx5bW91dGgtc2h1dGRvd24gbWFpbiBwcm9jZXNzICgxMzUzNCkgdGVybWluYXRl ZCB3aXRoIHN0YXR1cyAxCkZlYiAxMiAyMDoxNzoxNyBpcC0xMDAtMC0xMDAtMSBpbml0OiBzcGxh c2gtbWFuYWdlciBtYWluIHByb2Nlc3MgKDEzNTMwKSB0ZXJtaW5hdGVkIHdpdGggc3RhdHVzIDEK RmViIDEyIDIwOjE3OjE4IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWzI1NDI5NjcuNzcyMDQ2XSBY RlMgKG1kMCk6IHhmc19sb2dfZm9yY2U6IGVycm9yIDUgcmV0dXJuZWQuCkZlYiAxMiAyMDoxNzox OSBpcC0xMDAtMC0xMDAtMSBudHBkWzE0MTVdOiBudHBkIGV4aXRpbmcgb24gc2lnbmFsIDE1CkZl YiAxMiAyMDoxNzoyMCBpcC0xMDAtMC0xMDAtMSBpbml0OiBEaXNjb25uZWN0ZWQgZnJvbSBzeXN0 ZW0gYnVzCkZlYiAxMiAyMDoxNzoyMCBpcC0xMDAtMC0xMDAtMSBhdWRpdGRbMTMwMV06IFRoZSBh dWRpdCBkYWVtb24gaXMgZXhpdGluZy4KRmViIDEyIDIwOjE3OjIwIGlwLTEwMC0wLTEwMC0xIGtl cm5lbDogWzI1NDI5NjkuNTQwODYwXSB0eXBlPTEzMDUgYXVkaXQoMTM2MDcwMDI0MC4xMDk6MzYx NjcwKTogYXVkaXRfcGlkPTAgb2xkPTEzMDEgYXVpZD00Mjk0OTY3Mjk1IHNlcz00Mjk0OTY3Mjk1 IHJlcz0xCkZlYiAxMiAyMDoxNzoyMCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsyNTQyOTY5LjY0 NDUwOF0gdHlwZT0xMzA1IGF1ZGl0KDEzNjA3MDAyNDAuMjEzOjM2MTY3MSk6IGF1ZGl0X2VuYWJs ZWQ9MCBvbGQ9MSBhdWlkPTQyOTQ5NjcyOTUgc2VzPTQyOTQ5NjcyOTUgcmVzPTEKRmViIDEyIDIw OjE3OjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogS2VybmVsIGxvZ2dpbmcgKHByb2MpIHN0b3Bw ZWQuCkZlYiAxMiAyMDoxNzoyMCBpcC0xMDAtMC0xMDAtMSByc3lzbG9nZDogW29yaWdpbiBzb2Z0 d2FyZT0icnN5c2xvZ2QiIHN3VmVyc2lvbj0iNS44LjEwIiB4LXBpZD0iMTMxNiIgeC1pbmZvPSJo dHRwOi8vd3d3LnJzeXNsb2cuY29tIl0gZXhpdGluZyBvbiBzaWduYWwgMTUuCkZlYiAxMiAyMDox OTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IGlta2xvZyA1LjguMTAsIGxvZyBzb3VyY2UgPSAv cHJvYy9rbXNnIHN0YXJ0ZWQuCkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSByc3lzbG9n ZDogW29yaWdpbiBzb2Z0d2FyZT0icnN5c2xvZ2QiIHN3VmVyc2lvbj0iNS44LjEwIiB4LXBpZD0i MTMzNSIgeC1pbmZvPSJodHRwOi8vd3d3LnJzeXNsb2cuY29tIl0gc3RhcnQKRmViIDEyIDIwOjE5 OjU3IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjAwMDAwMF0gSW5pdGlhbGl6aW5nIGNn cm91cCBzdWJzeXMgY3B1c2V0CkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6 IFsgICAgMC4wMDAwMDBdIEluaXRpYWxpemluZyBjZ3JvdXAgc3Vic3lzIGNwdQpGZWIgMTIgMjA6 MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMDAwMDAwXSBMaW51eCB2ZXJzaW9u IDMuMi4zNC01NS40Ni5hbXpuMS54ODZfNjQgKG1vY2tidWlsZEBnb2JpLWJ1aWxkLTMxMDAzKSAo Z2NjIHZlcnNpb24gNC42LjIgMjAxMTEwMjcgKFJlZCBIYXQgNC42LjItMikgKEdDQykgKSAjMSBT TVAgVHVlIE5vdiAyMCAxMDowNjoxNSBVVEMgMjAxMgpGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAt MTAwLTEga2VybmVsOiBbICAgIDAuMDAwMDAwXSBDb21tYW5kIGxpbmU6IHJvb3Q9TEFCRUw9LyBj b25zb2xlPWh2YzAgTEFORz1lbl9VUy5VVEYtOCBLRVlUQUJMRT11cwpGZWIgMTIgMjA6MTk6NTcg aXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMDAwMDAwXSBNYXJraW5nIFRTQyB1bnN0YWJs ZSBkdWUgdG8gWGVuIGRvbWFpbgpGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVs OiBbICAgIDAuMDAwMDAwXSBBQ1BJIGluIHVucHJpdmlsZWdlZCBkb21haW4gZGlzYWJsZWQKRmVi IDEyIDIwOjE5OjU3IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjAwMDAwMF0gUmVsZWFz ZWQgMCBwYWdlcyBvZiB1bnVzZWQgbWVtb3J5CkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAt MSBrZXJuZWw6IFsgICAgMC4wMDAwMDBdIFNldCAwIHBhZ2UocykgdG8gMS0xIG1hcHBpbmcKRmVi IDEyIDIwOjE5OjU3IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjAwMDAwMF0gQklPUy1w cm92aWRlZCBwaHlzaWNhbCBSQU0gbWFwOgpGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEg a2VybmVsOiBbICAgIDAuMDAwMDAwXSAgWGVuOiAwMDAwMDAwMDAwMDAwMDAwIC0gMDAwMDAwMDAw MDBhMDAwMCAodXNhYmxlKQpGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBb ICAgIDAuMDAwMDAwXSAgWGVuOiAwMDAwMDAwMDAwMGEwMDAwIC0gMDAwMDAwMDAwMDEwMDAwMCAo cmVzZXJ2ZWQpCkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4w MDAwMDBdICBYZW46IDAwMDAwMDAwMDAxMDAwMDAgLSAwMDAwMDAwMWUwODAwMDAwICh1c2FibGUp CkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4wMDAwMDBdIE5Y IChFeGVjdXRlIERpc2FibGUpIHByb3RlY3Rpb246IGFjdGl2ZQpGZWIgMTIgMjA6MTk6NTcgaXAt MTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMDAwMDAwXSBETUkgbm90IHByZXNlbnQgb3IgaW52 YWxpZC4KRmViIDEyIDIwOjE5OjU3IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjAwMDAw MF0gTm8gQUdQIGJyaWRnZSBmb3VuZApGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2Vy bmVsOiBbICAgIDAuMDAwMDAwXSBsYXN0X3BmbiA9IDB4MWUwODAwIG1heF9hcmNoX3BmbiA9IDB4 NDAwMDAwMDAwCkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4w MDAwMDBdIGxhc3RfcGZuID0gMHgxMDAwMDAgbWF4X2FyY2hfcGZuID0gMHg0MDAwMDAwMDAKRmVi IDEyIDIwOjE5OjU3IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjAwMDAwMF0gaW5pdF9t ZW1vcnlfbWFwcGluZzogMDAwMDAwMDAwMDAwMDAwMC0wMDAwMDAwMTAwMDAwMDAwCkZlYiAxMiAy MDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4wMDAwMDBdIGluaXRfbWVtb3J5 X21hcHBpbmc6IDAwMDAwMDAxMDAwMDAwMDAtMDAwMDAwMDFlMDgwMDAwMApGZWIgMTIgMjA6MTk6 NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMDAwMDAwXSBSQU1ESVNLOiAwMTlhMjAw MCAtIDAyZDc0MDAwCkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAg MC4wMDAwMDBdIE5VTUEgdHVybmVkIG9mZgpGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEg a2VybmVsOiBbICAgIDAuMDAwMDAwXSBGYWtpbmcgYSBub2RlIGF0IDAwMDAwMDAwMDAwMDAwMDAt MDAwMDAwMDFlMDgwMDAwMApGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBb ICAgIDAuMDAwMDAwXSBJbml0bWVtIHNldHVwIG5vZGUgMCAwMDAwMDAwMDAwMDAwMDAwLTAwMDAw MDAxZTA4MDAwMDAKRmViIDEyIDIwOjE5OjU3IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAw LjAwMDAwMF0gICBOT0RFX0RBVEEgWzAwMDAwMDAxZGZmZmIwMDAgLSAwMDAwMDAwMWRmZmZmZmZm XQpGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMDAwMDAwXSBa b25lIFBGTiByYW5nZXM6CkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsg ICAgMC4wMDAwMDBdICAgRE1BICAgICAgMHgwMDAwMDAxMCAtPiAweDAwMDAxMDAwCkZlYiAxMiAy MDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4wMDAwMDBdICAgRE1BMzIgICAg MHgwMDAwMTAwMCAtPiAweDAwMTAwMDAwCkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBr ZXJuZWw6IFsgICAgMC4wMDAwMDBdICAgTm9ybWFsICAgMHgwMDEwMDAwMCAtPiAweDAwMWUwODAw CkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4wMDAwMDBdIE1v dmFibGUgem9uZSBzdGFydCBQRk4gZm9yIGVhY2ggbm9kZQpGZWIgMTIgMjA6MTk6NTcgaXAtMTAw LTAtMTAwLTEga2VybmVsOiBbICAgIDAuMDAwMDAwXSBlYXJseV9ub2RlX21hcFsyXSBhY3RpdmUg UEZOIHJhbmdlcwpGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAu MDAwMDAwXSAgICAgMDogMHgwMDAwMDAxMCAtPiAweDAwMDAwMGEwCkZlYiAxMiAyMDoxOTo1NyBp cC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4wMDAwMDBdICAgICAwOiAweDAwMDAwMTAwIC0+ IDB4MDAxZTA4MDAKRmViIDEyIDIwOjE5OjU3IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAw LjAwMDAwMF0gU01QOiBBbGxvd2luZyAyIENQVXMsIDAgaG90cGx1ZyBDUFVzCkZlYiAxMiAyMDox OTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4wMDAwMDBdIE5vIGxvY2FsIEFQSUMg cHJlc2VudApGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMDAw MDAwXSBBUElDOiBkaXNhYmxlIGFwaWMgZmFjaWxpdHkKRmViIDEyIDIwOjE5OjU3IGlwLTEwMC0w LTEwMC0xIGtlcm5lbDogWyAgICAwLjAwMDAwMF0gQVBJQzogc3dpdGNoZWQgdG8gYXBpYyBOT09Q CkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4wMDAwMDBdIFBN OiBSZWdpc3RlcmVkIG5vc2F2ZSBtZW1vcnk6IDAwMDAwMDAwMDAwYTAwMDAgLSAwMDAwMDAwMDAw MTAwMDAwCkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4wMDAw MDBdIFBDSTogV2FybmluZzogQ2Fubm90IGZpbmQgYSBnYXAgaW4gdGhlIDMyYml0IGFkZHJlc3Mg cmFuZ2UKRmViIDEyIDIwOjE5OjU3IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjAwMDAw MF0gUENJOiBVbmFzc2lnbmVkIGRldmljZXMgd2l0aCAzMmJpdCByZXNvdXJjZSByZWdpc3RlcnMg bWF5IGJyZWFrIQpGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAu MDAwMDAwXSBBbGxvY2F0aW5nIFBDSSByZXNvdXJjZXMgc3RhcnRpbmcgYXQgMWUwOTAwMDAwIChn YXA6IDFlMDkwMDAwMDo0MDAwMDApCkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJu ZWw6IFsgICAgMC4wMDAwMDBdIEJvb3RpbmcgcGFyYXZpcnR1YWxpemVkIGtlcm5lbCBvbiBYZW4K RmViIDEyIDIwOjE5OjU3IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjAwMDAwMF0gWGVu IHZlcnNpb246IDMuNC4zLTIuNi4xOCAocHJlc2VydmUtQUQpCkZlYiAxMiAyMDoxOTo1NyBpcC0x MDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4wMDAwMDBdIHNldHVwX3BlcmNwdTogTlJfQ1BVUzoz MiBucl9jcHVtYXNrX2JpdHM6MzIgbnJfY3B1X2lkczoyIG5yX25vZGVfaWRzOjEKRmViIDEyIDIw OjE5OjU3IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjAwMDAwMF0gUEVSQ1BVOiBFbWJl ZGRlZCAyNyBwYWdlcy9jcHUgQGZmZmY4ODAxZGZjMDAwMDAgczgwNTEyIHI4MTkyIGQyMTg4OCB1 MTA0ODU3NgpGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMDAw MDAwXSBCdWlsdCAxIHpvbmVsaXN0cyBpbiBOb2RlIG9yZGVyLCBtb2JpbGl0eSBncm91cGluZyBv bi4gIFRvdGFsIHBhZ2VzOiAxOTM1MjQ0CkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBr ZXJuZWw6IFsgICAgMC4wMDAwMDBdIFBvbGljeSB6b25lOiBOb3JtYWwKRmViIDEyIDIwOjE5OjU3 IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjAwMDAwMF0gS2VybmVsIGNvbW1hbmQgbGlu ZTogcm9vdD1MQUJFTD0vIGNvbnNvbGU9aHZjMCBMQU5HPWVuX1VTLlVURi04IEtFWVRBQkxFPXVz CkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4wMDAwMDBdIFBJ RCBoYXNoIHRhYmxlIGVudHJpZXM6IDQwOTYgKG9yZGVyOiAzLCAzMjc2OCBieXRlcykKRmViIDEy IDIwOjE5OjU3IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjAwMDAwMF0gQ2hlY2tpbmcg YXBlcnR1cmUuLi4KRmViIDEyIDIwOjE5OjU3IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAw LjAwMDAwMF0gTm8gQUdQIGJyaWRnZSBmb3VuZApGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAw LTEga2VybmVsOiBbICAgIDAuMDAwMDAwXSBNZW1vcnk6IDc2MTIzMTZrLzc4NzI1MTJrIGF2YWls YWJsZSAoMzg0NGsga2VybmVsIGNvZGUsIDQ0OGsgYWJzZW50LCAyNTk3NDhrIHJlc2VydmVkLCAy OTcxayBkYXRhLCA1NTZrIGluaXQpCkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJu ZWw6IFsgICAgMC4wMDAwMDBdIFNMVUI6IEdlbnNsYWJzPTE1LCBIV2FsaWduPTY0LCBPcmRlcj0w LTMsIE1pbk9iamVjdHM9MCwgQ1BVcz0yLCBOb2Rlcz0xCkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAt MC0xMDAtMSBrZXJuZWw6IFsgICAgMC4wMDAwMDBdIEhpZXJhcmNoaWNhbCBSQ1UgaW1wbGVtZW50 YXRpb24uCkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4wMDAw MDBdIE5SX0lSUVM6NDM1MiBucl9pcnFzOjI4OCAxNgpGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAt MTAwLTEga2VybmVsOiBbICAgIDAuMDAwMDAwXSBDb25zb2xlOiBjb2xvdXIgZHVtbXkgZGV2aWNl IDgweDI1CkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4wMDAw MDBdIGNvbnNvbGUgW3R0eTBdIGVuYWJsZWQKRmViIDEyIDIwOjE5OjU3IGlwLTEwMC0wLTEwMC0x IGtlcm5lbDogWyAgICAwLjAwMDAwMF0gY29uc29sZSBbaHZjMF0gZW5hYmxlZApGZWIgMTIgMjA6 MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMDAwMDAwXSBpbnN0YWxsaW5nIFhl biB0aW1lciBmb3IgQ1BVIDAKRmViIDEyIDIwOjE5OjU3IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDog WyAgICAwLjAwMDAwMF0gRGV0ZWN0ZWQgMjI2Ni43NDYgTUh6IHByb2Nlc3Nvci4KRmViIDEyIDIw OjE5OjU3IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjAwNDAwMF0gQ2FsaWJyYXRpbmcg ZGVsYXkgbG9vcCAoc2tpcHBlZCksIHZhbHVlIGNhbGN1bGF0ZWQgdXNpbmcgdGltZXIgZnJlcXVl bmN5Li4gNDUzMy40OSBCb2dvTUlQUyAobHBqPTkwNjY5ODQpCkZlYiAxMiAyMDoxOTo1NyBpcC0x MDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4wMDQwMDBdIHBpZF9tYXg6IGRlZmF1bHQ6IDMyNzY4 IG1pbmltdW06IDMwMQpGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAg IDAuMDA0MDAwXSBTZWN1cml0eSBGcmFtZXdvcmsgaW5pdGlhbGl6ZWQKRmViIDEyIDIwOjE5OjU3 IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjAwNDAwMF0gRGVudHJ5IGNhY2hlIGhhc2gg dGFibGUgZW50cmllczogMTA0ODU3NiAob3JkZXI6IDExLCA4Mzg4NjA4IGJ5dGVzKQpGZWIgMTIg MjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMDA1MDY4XSBJbm9kZS1jYWNo ZSBoYXNoIHRhYmxlIGVudHJpZXM6IDUyNDI4OCAob3JkZXI6IDEwLCA0MTk0MzA0IGJ5dGVzKQpG ZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMDA2MTI5XSBNb3Vu dC1jYWNoZSBoYXNoIHRhYmxlIGVudHJpZXM6IDI1NgpGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAt MTAwLTEga2VybmVsOiBbICAgIDAuMDA2MzkzXSBJbml0aWFsaXppbmcgY2dyb3VwIHN1YnN5cyBj cHVhY2N0CkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4wMDY0 MDVdIEluaXRpYWxpemluZyBjZ3JvdXAgc3Vic3lzIGRldmljZXMKRmViIDEyIDIwOjE5OjU3IGlw LTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjAwNjQxMV0gSW5pdGlhbGl6aW5nIGNncm91cCBz dWJzeXMgZnJlZXplcgpGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAg IDAuMDA2NDE2XSBJbml0aWFsaXppbmcgY2dyb3VwIHN1YnN5cyBibGtpbwpGZWIgMTIgMjA6MTk6 NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMDA2NDI5XSBJbml0aWFsaXppbmcgY2dy b3VwIHN1YnN5cyBwZXJmX2V2ZW50CkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJu ZWw6IFsgICAgMC4wMDY1MzRdIENQVTogUGh5c2ljYWwgUHJvY2Vzc29yIElEOiAwCkZlYiAxMiAy MDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4wMDY1NDBdIENQVTogUHJvY2Vz c29yIENvcmUgSUQ6IDAKRmViIDEyIDIwOjE5OjU3IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAg ICAwLjAwNjYyMF0gU01QIGFsdGVybmF0aXZlczogc3dpdGNoaW5nIHRvIFVQIGNvZGUKRmViIDEy IDIwOjE5OjU3IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjAyODE3NF0gY3B1IDAgc3Bp bmxvY2sgZXZlbnQgaXJxIDE3CkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6 IFsgICAgMC4wMjgyMDRdIFBlcmZvcm1hbmNlIEV2ZW50czogdW5zdXBwb3J0ZWQgcDYgQ1BVIG1v ZGVsIDI2IG5vIFBNVSBkcml2ZXIsIHNvZnR3YXJlIGV2ZW50cyBvbmx5LgpGZWIgMTIgMjA6MTk6 NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMDI4NDA5XSBpbnN0YWxsaW5nIFhlbiB0 aW1lciBmb3IgQ1BVIDEKRmViIDEyIDIwOjE5OjU3IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAg ICAwLjAyODQyNV0gY3B1IDEgc3BpbmxvY2sgZXZlbnQgaXJxIDIzCkZlYiAxMiAyMDoxOTo1NyBp cC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4wMjg0NTZdIFNNUCBhbHRlcm5hdGl2ZXM6IHN3 aXRjaGluZyB0byBTTVAgY29kZQpGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVs OiBbICAgIDAuMDQ5Mjg2XSBCcm91Z2h0IHVwIDIgQ1BVcwpGZWIgMTIgMjA6MTk6NTcgaXAtMTAw LTAtMTAwLTEga2VybmVsOiBbICAgIDAuMDQ5MzQ5XSBkZXZ0bXBmczogaW5pdGlhbGl6ZWQKRmVi IDEyIDIwOjE5OjU3IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjA0OTM0OV0gR3JhbnQg dGFibGUgaW5pdGlhbGl6ZWQKRmViIDEyIDIwOjE5OjU3IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDog WyAgICAwLjA0OTM0OV0gTkVUOiBSZWdpc3RlcmVkIHByb3RvY29sIGZhbWlseSAxNgpGZWIgMTIg MjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMDUyNDcxXSBQQ0k6IHNldHRp bmcgdXAgWGVuIFBDSSBmcm9udGVuZCBzdHViCkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAt MSBrZXJuZWw6IFsgICAgMC4wNTYwNDNdIGJpbzogY3JlYXRlIHNsYWIgPGJpby0wPiBhdCAwCkZl YiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4wNTYwNThdIEFDUEk6 IEludGVycHJldGVyIGRpc2FibGVkLgpGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2Vy bmVsOiBbICAgIDAuMDU2MTMyXSB4ZW4vYmFsbG9vbjogSW5pdGlhbGlzaW5nIGJhbGxvb24gZHJp dmVyLgpGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMDYwMTI0 XSB4ZW4tYmFsbG9vbjogSW5pdGlhbGlzaW5nIGJhbGxvb24gZHJpdmVyLgpGZWIgMTIgMjA6MTk6 NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMDYwMTU4XSB2Z2FhcmI6IGxvYWRlZApG ZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMDYwMTU4XSBQQ0k6 IFN5c3RlbSBkb2VzIG5vdCBzdXBwb3J0IFBDSQpGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAw LTEga2VybmVsOiBbICAgIDAuMDYwMTU4XSBQQ0k6IFN5c3RlbSBkb2VzIG5vdCBzdXBwb3J0IFBD SQpGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMDYwMzAxXSBO ZXRMYWJlbDogSW5pdGlhbGl6aW5nCkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJu ZWw6IFsgICAgMC4wNjAzMDddIE5ldExhYmVsOiAgZG9tYWluIGhhc2ggc2l6ZSA9IDEyOApGZWIg MTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMDYwMzExXSBOZXRMYWJl bDogIHByb3RvY29scyA9IFVOTEFCRUxFRCBDSVBTT3Y0CkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAt MC0xMDAtMSBrZXJuZWw6IFsgICAgMC4wNjAzMjZdIE5ldExhYmVsOiAgdW5sYWJlbGVkIHRyYWZm aWMgYWxsb3dlZCBieSBkZWZhdWx0CkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJu ZWw6IFsgICAgMC4wNjAzMzRdIFN3aXRjaGluZyB0byBjbG9ja3NvdXJjZSB4ZW4KRmViIDEyIDIw OjE5OjU3IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjA2NjkxNF0gcG5wOiBQblAgQUNQ STogZGlzYWJsZWQKRmViIDEyIDIwOjE5OjU3IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAw LjA3NDMxNl0gTkVUOiBSZWdpc3RlcmVkIHByb3RvY29sIGZhbWlseSAyCkZlYiAxMiAyMDoxOTo1 NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4wNzQ4NjJdIElQIHJvdXRlIGNhY2hlIGhh c2ggdGFibGUgZW50cmllczogMjYyMTQ0IChvcmRlcjogOSwgMjA5NzE1MiBieXRlcykKRmViIDEy IDIwOjE5OjU3IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjA3NzI0Ml0gVENQIGVzdGFi bGlzaGVkIGhhc2ggdGFibGUgZW50cmllczogNTI0Mjg4IChvcmRlcjogMTEsIDgzODg2MDggYnl0 ZXMpCkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4wNzk0NzVd IFRDUCBiaW5kIGhhc2ggdGFibGUgZW50cmllczogNjU1MzYgKG9yZGVyOiA4LCAxMDQ4NTc2IGJ5 dGVzKQpGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMDc5NzIw XSBUQ1A6IEhhc2ggdGFibGVzIGNvbmZpZ3VyZWQgKGVzdGFibGlzaGVkIDUyNDI4OCBiaW5kIDY1 NTM2KQpGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMDc5NzI2 XSBUQ1AgcmVubyByZWdpc3RlcmVkCkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJu ZWw6IFsgICAgMC4wNzk3NjZdIFVEUCBoYXNoIHRhYmxlIGVudHJpZXM6IDQwOTYgKG9yZGVyOiA1 LCAxMzEwNzIgYnl0ZXMpCkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsg ICAgMC4wNzk4MzVdIFVEUC1MaXRlIGhhc2ggdGFibGUgZW50cmllczogNDA5NiAob3JkZXI6IDUs IDEzMTA3MiBieXRlcykKRmViIDEyIDIwOjE5OjU3IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAg ICAwLjA3OTk2MV0gTkVUOiBSZWdpc3RlcmVkIHByb3RvY29sIGZhbWlseSAxCkZlYiAxMiAyMDox OTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4wODAxMTVdIFVucGFja2luZyBpbml0 cmFtZnMuLi4KRmViIDEyIDIwOjE5OjU3IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjEw NDEyNV0gRnJlZWluZyBpbml0cmQgbWVtb3J5OiAyMDI5NmsgZnJlZWQKRmViIDEyIDIwOjE5OjU3 IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjExMDYzN10gUENJLURNQTogVXNpbmcgc29m dHdhcmUgYm91bmNlIGJ1ZmZlcmluZyBmb3IgSU8gKFNXSU9UTEIpCkZlYiAxMiAyMDoxOTo1NyBp cC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4xMTA2NTZdIFBsYWNpbmcgNjRNQiBzb2Z0d2Fy ZSBJTyBUTEIgYmV0d2VlbiBmZmZmODgwMGZiMGYzMDAwIC0gZmZmZjg4MDBmZjBmMzAwMApGZWIg MTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMTEwNjYyXSBzb2Z0d2Fy ZSBJTyBUTEIgYXQgcGh5cyAweGZiMGYzMDAwIC0gMHhmZjBmMzAwMApGZWIgMTIgMjA6MTk6NTcg aXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMTEwODcwXSBwbGF0Zm9ybSBydGNfY21vczog cmVnaXN0ZXJlZCBwbGF0Zm9ybSBSVEMgZGV2aWNlIChubyBQTlAgZGV2aWNlIGZvdW5kKQpGZWIg MTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMTEyNTczXSBhdWRpdDog aW5pdGlhbGl6aW5nIG5ldGxpbmsgc29ja2V0IChkaXNhYmxlZCkKRmViIDEyIDIwOjE5OjU3IGlw LTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjExMjU5Ml0gdHlwZT0yMDAwIGF1ZGl0KDEzNjA3 MDAzNzkuNzc0OjEpOiBpbml0aWFsaXplZApGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEg a2VybmVsOiBbICAgIDAuMTM2MjQ1XSBWRlM6IERpc2sgcXVvdGFzIGRxdW90XzYuNS4yCkZlYiAx MiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4xMzYzNDJdIERxdW90LWNh Y2hlIGhhc2ggdGFibGUgZW50cmllczogNTEyIChvcmRlciAwLCA0MDk2IGJ5dGVzKQpGZWIgMTIg MjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMTM2Mzk1XSBtc2dtbmkgaGFz IGJlZW4gc2V0IHRvIDE0OTA3CkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6 IFsgICAgMC4xMzY4MDBdIGFsZzogTm8gdGVzdCBmb3Igc3Rkcm5nIChrcm5nKQpGZWIgMTIgMjA6 MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMTM2OTU0XSBCbG9jayBsYXllciBT Q1NJIGdlbmVyaWMgKGJzZykgZHJpdmVyIHZlcnNpb24gMC40IGxvYWRlZCAobWFqb3IgMjU0KQpG ZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMTM2OTk4XSBpbyBz Y2hlZHVsZXIgbm9vcCByZWdpc3RlcmVkIChkZWZhdWx0KQpGZWIgMTIgMjA6MTk6NTcgaXAtMTAw LTAtMTAwLTEga2VybmVsOiBbICAgIDAuMTM4MDc5XSBTZXJpYWw6IDgyNTAvMTY1NTAgZHJpdmVy LCA0IHBvcnRzLCBJUlEgc2hhcmluZyBkaXNhYmxlZApGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAt MTAwLTEga2VybmVsOiBbICAgIDAuMjU0MDQzXSBsb29wOiBtb2R1bGUgbG9hZGVkCkZlYiAxMiAy MDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4yNTg4ODhdIGJsa2Zyb250OiB4 dmRhMTogYmFycmllciBvciBmbHVzaDogZGlzYWJsZWQKRmViIDEyIDIwOjE5OjU3IGlwLTEwMC0w LTEwMC0xIGtlcm5lbDogWyAgICAwLjI2MjQxOF0gYmxrZnJvbnQ6IHh2ZGI6IGJhcnJpZXIgb3Ig Zmx1c2g6IGRpc2FibGVkCkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsg ICAgMC4yNzI0NjVdICB4dmRiOiB1bmtub3duIHBhcnRpdGlvbiB0YWJsZQpGZWIgMTIgMjA6MTk6 NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMjczODc4XSBTZXR0aW5nIGNhcGFjaXR5 IHRvIDg4MDczMjE2MApGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAg IDAuMjczODkzXSB4dmRiOiBkZXRlY3RlZCBjYXBhY2l0eSBjaGFuZ2UgZnJvbSAwIHRvIDQ1MDkz NDg2NTkyMApGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMjc1 NDA1XSBibGtmcm9udDogeHZkYzogYmFycmllciBvciBmbHVzaDogZGlzYWJsZWQKRmViIDEyIDIw OjE5OjU3IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjI3OTE3N10gIHh2ZGM6IHVua25v d24gcGFydGl0aW9uIHRhYmxlCkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6 IFsgICAgMC4yODQyOTJdIGJsa2Zyb250OiB4dmRmOiBiYXJyaWVyIG9yIGZsdXNoOiBkaXNhYmxl ZApGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMjg2NzI4XSAg eHZkZjogdW5rbm93biBwYXJ0aXRpb24gdGFibGUKRmViIDEyIDIwOjE5OjU3IGlwLTEwMC0wLTEw MC0xIGtlcm5lbDogWyAgICAwLjI4Nzc3OF0gU2V0dGluZyBjYXBhY2l0eSB0byA4ODA3MzIxNjAK RmViIDEyIDIwOjE5OjU3IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjI4Nzc5MF0geHZk YzogZGV0ZWN0ZWQgY2FwYWNpdHkgY2hhbmdlIGZyb20gMCB0byA0NTA5MzQ4NjU5MjAKRmViIDEy IDIwOjE5OjU3IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjI4OTEzOF0gYmxrZnJvbnQ6 IHh2ZGc6IGJhcnJpZXIgb3IgZmx1c2g6IGRpc2FibGVkCkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAt MC0xMDAtMSBrZXJuZWw6IFsgICAgMC4yOTEwNjNdICB4dmRnOiB1bmtub3duIHBhcnRpdGlvbiB0 YWJsZQpGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMjkxNTcz XSBTZXR0aW5nIGNhcGFjaXR5IHRvIDEwNzM3NDE4MjQKRmViIDEyIDIwOjE5OjU3IGlwLTEwMC0w LTEwMC0xIGtlcm5lbDogWyAgICAwLjI5MTU4Nl0geHZkZjogZGV0ZWN0ZWQgY2FwYWNpdHkgY2hh bmdlIGZyb20gMCB0byA1NDk3NTU4MTM4ODgKRmViIDEyIDIwOjE5OjU3IGlwLTEwMC0wLTEwMC0x IGtlcm5lbDogWyAgICAwLjI5MzI4Nl0gYmxrZnJvbnQ6IHh2ZGg6IGJhcnJpZXIgb3IgZmx1c2g6 IGRpc2FibGVkCkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4y OTUyMDddICB4dmRoOiB1bmtub3duIHBhcnRpdGlvbiB0YWJsZQpGZWIgMTIgMjA6MTk6NTcgaXAt MTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMjk2MDcyXSBJbml0aWFsaXNpbmcgWGVuIHZpcnR1 YWwgZXRoZXJuZXQgZHJpdmVyLgpGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVs OiBbICAgIDAuMjk2MTYwXSBTZXR0aW5nIGNhcGFjaXR5IHRvIDEwNzM3NDE4MjQKRmViIDEyIDIw OjE5OjU3IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjI5NjE2OF0geHZkZzogZGV0ZWN0 ZWQgY2FwYWNpdHkgY2hhbmdlIGZyb20gMCB0byA1NDk3NTU4MTM4ODgKRmViIDEyIDIwOjE5OjU3 IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjI5NjU4M10gU2V0dGluZyBjYXBhY2l0eSB0 byAxMDczNzQxODI0CkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAg MC4yOTY1OThdIHh2ZGg6IGRldGVjdGVkIGNhcGFjaXR5IGNoYW5nZSBmcm9tIDAgdG8gNTQ5NzU1 ODEzODg4CkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4yOTc5 NTNdIGJsa2Zyb250OiB4dmRpOiBiYXJyaWVyIG9yIGZsdXNoOiBkaXNhYmxlZApGZWIgMTIgMjA6 MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMjk4NTg5XSBpODA0MjogUE5QOiBO byBQUy8yIGNvbnRyb2xsZXIgZm91bmQuIFByb2JpbmcgcG9ydHMgZGlyZWN0bHkuCkZlYiAxMiAy MDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4yOTk2MTNdIG1vdXNlZGV2OiBQ Uy8yIG1vdXNlIGRldmljZSBjb21tb24gZm9yIGFsbCBtaWNlCkZlYiAxMiAyMDoxOTo1NyBpcC0x MDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4yOTk5MjJdIFRDUCBjdWJpYyByZWdpc3RlcmVkCkZl YiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4yOTk5MzBdIE5FVDog UmVnaXN0ZXJlZCBwcm90b2NvbCBmYW1pbHkgMTcKRmViIDEyIDIwOjE5OjU3IGlwLTEwMC0wLTEw MC0xIGtlcm5lbDogWyAgICAwLjI5OTk0Ml0gUmVnaXN0ZXJpbmcgdGhlIGRuc19yZXNvbHZlciBr ZXkgdHlwZQpGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMzAw MDU1XSAgeHZkaTogdW5rbm93biBwYXJ0aXRpb24gdGFibGUKRmViIDEyIDIwOjE5OjU3IGlwLTEw MC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjMwMDQwOF0gU2V0dGluZyBjYXBhY2l0eSB0byAxMDcz NzQxODI0CkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4zMDA0 MTddIHh2ZGk6IGRldGVjdGVkIGNhcGFjaXR5IGNoYW5nZSBmcm9tIDAgdG8gNTQ5NzU1ODEzODg4 CkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4zMDA0NTldIHJl Z2lzdGVyZWQgdGFza3N0YXRzIHZlcnNpb24gMQpGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAw LTEga2VybmVsOiBbICAgIDAuMzAxMjU3XSBibGtmcm9udDogeHZkajogYmFycmllciBvciBmbHVz aDogZGlzYWJsZWQKRmViIDEyIDIwOjE5OjU3IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAw LjMwMzAxNF0gIHh2ZGo6IHVua25vd24gcGFydGl0aW9uIHRhYmxlCkZlYiAxMiAyMDoxOTo1NyBp cC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4zMDM0MTVdIFNldHRpbmcgY2FwYWNpdHkgdG8g MTA3Mzc0MTgyNApGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAu MzAzNDI3XSB4dmRqOiBkZXRlY3RlZCBjYXBhY2l0eSBjaGFuZ2UgZnJvbSAwIHRvIDU0OTc1NTgx Mzg4OApGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMzA0NDEz XSBibGtmcm9udDogeHZkazogYmFycmllciBvciBmbHVzaDogZGlzYWJsZWQKRmViIDEyIDIwOjE5 OjU3IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjMwNjI5NF0gIHh2ZGs6IHVua25vd24g cGFydGl0aW9uIHRhYmxlCkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsg ICAgMC4zMDY1NDhdIFNldHRpbmcgY2FwYWNpdHkgdG8gMTA3Mzc0MTgyNApGZWIgMTIgMjA6MTk6 NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMzA2NTYxXSB4dmRrOiBkZXRlY3RlZCBj YXBhY2l0eSBjaGFuZ2UgZnJvbSAwIHRvIDU0OTc1NTgxMzg4OApGZWIgMTIgMjA6MTk6NTcgaXAt MTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMzA3MzAyXSBibGtmcm9udDogeHZkbDogYmFycmll ciBvciBmbHVzaDogZGlzYWJsZWQKRmViIDEyIDIwOjE5OjU3IGlwLTEwMC0wLTEwMC0xIGtlcm5l bDogWyAgICAwLjMwOTE1MF0gIHh2ZGw6IHVua25vd24gcGFydGl0aW9uIHRhYmxlCkZlYiAxMiAy MDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4zMDk0MDddIFNldHRpbmcgY2Fw YWNpdHkgdG8gMTA3Mzc0MTgyNApGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVs OiBbICAgIDAuMzA5NDIwXSB4dmRsOiBkZXRlY3RlZCBjYXBhY2l0eSBjaGFuZ2UgZnJvbSAwIHRv IDU0OTc1NTgxMzg4OApGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAg IDAuMzEwMjAzXSBibGtmcm9udDogeHZkbTogYmFycmllciBvciBmbHVzaDogZGlzYWJsZWQKRmVi IDEyIDIwOjE5OjU3IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjMxMTYyNl0gIHh2ZG06 IHVua25vd24gcGFydGl0aW9uIHRhYmxlCkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBr ZXJuZWw6IFsgICAgMC4zMTE5MjNdIFNldHRpbmcgY2FwYWNpdHkgdG8gMTA3Mzc0MTgyNApGZWIg MTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMzExOTMzXSB4dmRtOiBk ZXRlY3RlZCBjYXBhY2l0eSBjaGFuZ2UgZnJvbSAwIHRvIDU0OTc1NTgxMzg4OApGZWIgMTIgMjA6 MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuNDAwMDQzXSBYRU5CVVM6IERldmlj ZSB3aXRoIG5vIGRyaXZlcjogZGV2aWNlL2NvbnNvbGUvMApGZWIgMTIgMjA6MTk6NTcgaXAtMTAw LTAtMTAwLTEga2VybmVsOiBbICAgIDAuNDAwNDU5XSBGcmVlaW5nIHVudXNlZCBrZXJuZWwgbWVt b3J5OiA1NTZrIGZyZWVkCkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsg ICAgMC40MDA2NjFdIFdyaXRlIHByb3RlY3RpbmcgdGhlIGtlcm5lbCByZWFkLW9ubHkgZGF0YTog NjE0NGsKRmViIDEyIDIwOjE5OjU3IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjQwMzE3 OF0gRnJlZWluZyB1bnVzZWQga2VybmVsIG1lbW9yeTogMjMyayBmcmVlZApGZWIgMTIgMjA6MTk6 NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuNDAzNDgyXSBGcmVlaW5nIHVudXNlZCBr ZXJuZWwgbWVtb3J5OiA0NjhrIGZyZWVkCkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBr ZXJuZWw6IFsgICAgMC40NDI0ODldIGRldmljZS1tYXBwZXI6IHVldmVudDogdmVyc2lvbiAxLjAu MwpGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuNDQyNzM4XSBk ZXZpY2UtbWFwcGVyOiBpb2N0bDogNC4yMi4wLWlvY3RsICgyMDExLTEwLTE5KSBpbml0aWFsaXNl ZDogZG0tZGV2ZWxAcmVkaGF0LmNvbQpGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2Vy bmVsOiBbICAgIDAuNjEzMjU4XSBtZDogYmluZDx4dmRoPgpGZWIgMTIgMjA6MTk6NTcgaXAtMTAw LTAtMTAwLTEga2VybmVsOiBbICAgIDAuNjE3MTkyXSBtZDogYmluZDx4dmRpPgpGZWIgMTIgMjA6 MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuNjIyNzUzXSBtZDogYmluZDx4dmRn PgpGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuNjI5MDY0XSBt ZDogYmluZDx4dmRqPgpGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAg IDAuNjM2NDI3XSBtZDogYmluZDx4dmRsPgpGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEg a2VybmVsOiBbICAgIDAuNjQ0MzQ4XSBtZDogYmluZDx4dmRmPgpGZWIgMTIgMjA6MTk6NTcgaXAt MTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuNjUyMDY1XSBtZDogYmluZDx4dmRtPgpGZWIgMTIg MjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuNjYxNTEyXSBtZDogYmluZDx4 dmRrPgpGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuNjcwMTU3 XSBtZDogcmFpZDAgcGVyc29uYWxpdHkgcmVnaXN0ZXJlZCBmb3IgbGV2ZWwgMApGZWIgMTIgMjA6 MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuNjcwNjk4XSBiaW86IGNyZWF0ZSBz bGFiIDxiaW8tMT4gYXQgMQpGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBb ICAgIDAuNjcwNzE2XSBtZC9yYWlkMDptZDEyNzogbWRfc2l6ZSBpcyA4NTg5OTMwNDk2IHNlY3Rv cnMuCkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC42NzA3Mjdd IG1kOiBSQUlEMCBjb25maWd1cmF0aW9uIGZvciBtZDEyNyAtIDEgem9uZQpGZWIgMTIgMjA6MTk6 NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuNjcwNzMxXSBtZDogem9uZTA9W3h2ZGYv eHZkZy94dmRoL3h2ZGkveHZkai94dmRrL3h2ZGwveHZkbV0KRmViIDEyIDIwOjE5OjU3IGlwLTEw MC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjY3MTEzMl0gICAgICAgem9uZS1vZmZzZXQ9ICAgICAg ICAgMEtCLCBkZXZpY2Utb2Zmc2V0PSAgICAgICAgIDBLQiwgc2l6ZT00Mjk0OTY1MjQ4S0IKRmVi IDEyIDIwOjE5OjU3IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjY3MTEzOV0gCkZlYiAx MiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC42NzExNjNdIG1kMTI3OiBk ZXRlY3RlZCBjYXBhY2l0eSBjaGFuZ2UgZnJvbSAwIHRvIDQzOTgwNDQ0MTM5NTIKRmViIDEyIDIw OjE5OjU3IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjY4MDE1Ml0gIG1kMTI3OiB1bmtu b3duIHBhcnRpdGlvbiB0YWJsZQpGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVs OiBbICAgIDEuMDEyMzM0XSBFWFQ0LWZzICh4dmRhMSk6IElORk86IHJlY292ZXJ5IHJlcXVpcmVk IG9uIHJlYWRvbmx5IGZpbGVzeXN0ZW0KRmViIDEyIDIwOjE5OjU3IGlwLTEwMC0wLTEwMC0xIGtl cm5lbDogWyAgICAxLjAxMjM0OV0gRVhUNC1mcyAoeHZkYTEpOiB3cml0ZSBhY2Nlc3Mgd2lsbCBi ZSBlbmFibGVkIGR1cmluZyByZWNvdmVyeQpGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEg a2VybmVsOiBbICAgIDIuNDk4NTk5XSBFWFQ0LWZzICh4dmRhMSk6IG9ycGhhbiBjbGVhbnVwIG9u IHJlYWRvbmx5IGZzCkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAg Mi42NDMxNThdIEVYVDQtZnMgKHh2ZGExKTogMTggb3JwaGFuIGlub2RlcyBkZWxldGVkCkZlYiAx MiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMi42NDMxNjhdIEVYVDQtZnMg KHh2ZGExKTogcmVjb3ZlcnkgY29tcGxldGUKRmViIDEyIDIwOjE5OjU3IGlwLTEwMC0wLTEwMC0x IGtlcm5lbDogWyAgICAyLjY1ODkyM10gRVhUNC1mcyAoeHZkYTEpOiBtb3VudGVkIGZpbGVzeXN0 ZW0gd2l0aCBvcmRlcmVkIGRhdGEgbW9kZS4gT3B0czogKG51bGwpCkZlYiAxMiAyMDoxOTo1NyBp cC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMi42ODQ3NzddIGRyYWN1dDogUmVtb3VudGluZyAv ZGV2L2Rpc2svYnktbGFiZWwvXHgyZiB3aXRoIC1vIG5vYXRpbWUscm8KRmViIDEyIDIwOjE5OjU3 IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAyLjY5NzAyMF0gRVhUNC1mcyAoeHZkYTEpOiBt b3VudGVkIGZpbGVzeXN0ZW0gd2l0aCBvcmRlcmVkIGRhdGEgbW9kZS4gT3B0czogKG51bGwpCkZl YiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMi43MTk0NjhdIGRyYWN1 dDogTW91bnRlZCByb290IGZpbGVzeXN0ZW0gL2Rldi94dmRhMQpGZWIgMTIgMjA6MTk6NTcgaXAt MTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDIuNzY2NTg5XSBkcmFjdXQ6IExvYWRpbmcgU0VMaW51 eCBwb2xpY3kKRmViIDEyIDIwOjE5OjU3IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAyLjg2 NjcwMV0gZHJhY3V0OiAvc2Jpbi9sb2FkX3BvbGljeTogQ2FuJ3QgbG9hZCBwb2xpY3k6IE5vIHN1 Y2ggZGV2aWNlCkZlYiAxMiAyMDoxOTo1NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMi45 NzU1NjBdIGRyYWN1dDogU3dpdGNoaW5nIHJvb3QKRmViIDEyIDIwOjE5OjU3IGlwLTEwMC0wLTEw MC0xIGtlcm5lbDogWyAgICA3LjkwMTM3M10gbmZfY29ubnRyYWNrIHZlcnNpb24gMC41LjAgKDE2 Mzg0IGJ1Y2tldHMsIDY1NTM2IG1heCkKRmViIDEyIDIwOjE5OjU3IGlwLTEwMC0wLTEwMC0xIGtl cm5lbDogWyAgICA3Ljk4MzI2OF0gU0NTSSBzdWJzeXN0ZW0gaW5pdGlhbGl6ZWQKRmViIDEyIDIw OjE5OjU3IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgIDExLjY1OTY4NF0gRVhUNC1mcyAoeHZk YTEpOiByZS1tb3VudGVkLiBPcHRzOiAobnVsbCkKRmViIDEyIDIwOjE5OjU3IGlwLTEwMC0wLTEw MC0xIGtlcm5lbDogWyAgIDExLjgwMTMyOF0ga2pvdXJuYWxkIHN0YXJ0aW5nLiAgQ29tbWl0IGlu dGVydmFsIDUgc2Vjb25kcwpGZWIgMTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBb ICAgMTEuODAxNjU0XSBFWFQzLWZzICh4dmRiKTogdXNpbmcgaW50ZXJuYWwgam91cm5hbApGZWIg MTIgMjA6MTk6NTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgMTEuODAxNjY0XSBFWFQzLWZz ICh4dmRiKTogbW91bnRlZCBmaWxlc3lzdGVtIHdpdGggb3JkZXJlZCBkYXRhIG1vZGUKRmViIDEy IDIwOjE5OjU3IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgIDEyLjM2OTE4OV0gTkVUOiBSZWdp c3RlcmVkIHByb3RvY29sIGZhbWlseSAxMApGZWIgMTIgMjA6MjA6MDQgaXAtMTAwLTAtMTAwLTEg bnRwZGF0ZVsxNDA5XTogc3RlcCB0aW1lIHNlcnZlciAxMzguMjM2LjEyOC4xMTIgb2Zmc2V0IDAu MDEyMjczIHNlYwpGZWIgMTIgMjA6MjA6MDQgaXAtMTAwLTAtMTAwLTEgbnRwZFsxNDE1XTogbnRw ZCA0LjIuNnA1QDEuMjM0OS1vIE1vbiBOb3YgMjYgMTc6Mjk6MzggVVRDIDIwMTIgKDEpCkZlYiAx MiAyMDoyMDowNCBpcC0xMDAtMC0xMDAtMSBudHBkWzE0MTZdOiBwcm90bzogcHJlY2lzaW9uID0g MC45MTAgdXNlYwpGZWIgMTIgMjA6MjA6MDQgaXAtMTAwLTAtMTAwLTEgbnRwZFsxNDE2XTogMC4w LjAuMCBjMDFkIDBkIGtlcm4ga2VybmVsIHRpbWUgc3luYyBlbmFibGVkCkZlYiAxMiAyMDoyMDow NCBpcC0xMDAtMC0xMDAtMSBudHBkWzE0MTZdOiBMaXN0ZW4gYW5kIGRyb3Agb24gMCB2NHdpbGRj YXJkIDAuMC4wLjAgVURQIDEyMwpGZWIgMTIgMjA6MjA6MDQgaXAtMTAwLTAtMTAwLTEgbnRwZFsx NDE2XTogTGlzdGVuIG5vcm1hbGx5IG9uIDEgbG8gMTI3LjAuMC4xIFVEUCAxMjMKRmViIDEyIDIw OjIwOjA0IGlwLTEwMC0wLTEwMC0xIG50cGRbMTQxNl06IExpc3RlbiBub3JtYWxseSBvbiAyIGV0 aDAgMTAuMC4xLjQ4IFVEUCAxMjMKRmViIDEyIDIwOjIwOjA0IGlwLTEwMC0wLTEwMC0xIG50cGRb MTQxNl06IHBlZXJzIHJlZnJlc2hlZApGZWIgMTIgMjA6MjA6MDQgaXAtMTAwLTAtMTAwLTEgbnRw ZFsxNDE2XTogTGlzdGVuaW5nIG9uIHJvdXRpbmcgc29ja2V0IG9uIGZkICMxOSBmb3IgaW50ZXJm YWNlIHVwZGF0ZXMKRmViIDEyIDIwOjIyOjA5IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgMTUw LjEyNzcyMF0gbWQxMjc6IGRldGVjdGVkIGNhcGFjaXR5IGNoYW5nZSBmcm9tIDQzOTgwNDQ0MTM5 NTIgdG8gMApGZWIgMTIgMjA6MjI6MDkgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAxNTAuMTI3 NzM4XSBtZDogbWQxMjcgc3RvcHBlZC4KRmViIDEyIDIwOjIyOjA5IGlwLTEwMC0wLTEwMC0xIGtl cm5lbDogWyAgMTUwLjEyNzc0N10gbWQ6IHVuYmluZDx4dmRrPgpGZWIgMTIgMjA6MjI6MDkgaXAt MTAwLTAtMTAwLTEga2VybmVsOiBbICAxNTAuMTM2MDU1XSBtZDogZXhwb3J0X3JkZXYoeHZkaykK RmViIDEyIDIwOjIyOjA5IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgMTUwLjEzNjEyMl0gbWQ6 IHVuYmluZDx4dmRtPgpGZWIgMTIgMjA6MjI6MDkgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAx NTAuMTQ4MDM5XSBtZDogZXhwb3J0X3JkZXYoeHZkbSkKRmViIDEyIDIwOjIyOjA5IGlwLTEwMC0w LTEwMC0xIGtlcm5lbDogWyAgMTUwLjE0ODEwOF0gbWQ6IHVuYmluZDx4dmRmPgpGZWIgMTIgMjA6 MjI6MDkgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAxNTAuMTY4MDMzXSBtZDogZXhwb3J0X3Jk ZXYoeHZkZikKRmViIDEyIDIwOjIyOjA5IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgMTUwLjE2 ODM3MV0gbWQ6IHVuYmluZDx4dmRsPgpGZWIgMTIgMjA6MjI6MDkgaXAtMTAwLTAtMTAwLTEga2Vy bmVsOiBbICAxNTAuMjA0MDQ4XSBtZDogZXhwb3J0X3JkZXYoeHZkbCkKRmViIDEyIDIwOjIyOjA5 IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgMTUwLjIwNDExMV0gbWQ6IHVuYmluZDx4dmRqPgpG ZWIgMTIgMjA6MjI6MDkgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAxNTAuMjQwMDI5XSBtZDog ZXhwb3J0X3JkZXYoeHZkaikKRmViIDEyIDIwOjIyOjA5IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDog WyAgMTUwLjI0MDA4MF0gbWQ6IHVuYmluZDx4dmRnPgpGZWIgMTIgMjA6MjI6MDkgaXAtMTAwLTAt MTAwLTEga2VybmVsOiBbICAxNTAuMzA0MDMwXSBtZDogZXhwb3J0X3JkZXYoeHZkZykKRmViIDEy IDIwOjIyOjA5IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgMTUwLjMwNDA4MV0gbWQ6IHVuYmlu ZDx4dmRpPgpGZWIgMTIgMjA6MjI6MTAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAxNTAuMzQw MDI2XSBtZDogZXhwb3J0X3JkZXYoeHZkaSkKRmViIDEyIDIwOjIyOjEwIGlwLTEwMC0wLTEwMC0x IGtlcm5lbDogWyAgMTUwLjM0MDA4MF0gbWQ6IHVuYmluZDx4dmRoPgpGZWIgMTIgMjA6MjI6MTAg aXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAxNTAuMzc2MDUzXSBtZDogZXhwb3J0X3JkZXYoeHZk aCkKRmViIDEyIDIwOjIyOjEwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgMTUwLjQ2NzgxNV0g bWQ6IG1kMCBzdG9wcGVkLgpGZWIgMTIgMjA6MjI6MTAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBb ICAxNTAuNDc2NzE0XSBtZDogYmluZDx4dmRnPgpGZWIgMTIgMjA6MjI6MTAgaXAtMTAwLTAtMTAw LTEga2VybmVsOiBbICAxNTAuNDc4MDAzXSBtZDogYmluZDx4dmRoPgpGZWIgMTIgMjA6MjI6MTAg aXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAxNTAuNDc5MTAxXSBtZDogYmluZDx4dmRpPgpGZWIg MTIgMjA6MjI6MTAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAxNTAuNDgwMTYzXSBtZDogYmlu ZDx4dmRqPgpGZWIgMTIgMjA6MjI6MTAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAxNTAuNDgx MzEyXSBtZDogYmluZDx4dmRrPgpGZWIgMTIgMjA6MjI6MTAgaXAtMTAwLTAtMTAwLTEga2VybmVs OiBbICAxNTAuNDgyNDk4XSBtZDogYmluZDx4dmRsPgpGZWIgMTIgMjA6MjI6MTAgaXAtMTAwLTAt MTAwLTEga2VybmVsOiBbICAxNTAuNDgzMzQ4XSBtZDogYmluZDx4dmRtPgpGZWIgMTIgMjA6MjI6 MTAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAxNTAuNDg0MDk0XSBtZDogYmluZDx4dmRmPgpG ZWIgMTIgMjA6MjI6MTAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAxNTAuNTAyNjk3XSBtZC9y YWlkMDptZDA6IG1kX3NpemUgaXMgODU4OTkzMDQ5NiBzZWN0b3JzLgpGZWIgMTIgMjA6MjI6MTAg aXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAxNTAuNTAyNzEyXSBtZDogUkFJRDAgY29uZmlndXJh dGlvbiBmb3IgbWQwIC0gMSB6b25lCkZlYiAxMiAyMDoyMjoxMCBpcC0xMDAtMC0xMDAtMSBrZXJu ZWw6IFsgIDE1MC41MDI3MTZdIG1kOiB6b25lMD1beHZkZi94dmRnL3h2ZGgveHZkaS94dmRqL3h2 ZGsveHZkbC94dmRtXQpGZWIgMTIgMjA6MjI6MTAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAx NTAuNTAyNzI4XSAgICAgICB6b25lLW9mZnNldD0gICAgICAgICAwS0IsIGRldmljZS1vZmZzZXQ9 ICAgICAgICAgMEtCLCBzaXplPTQyOTQ5NjUyNDhLQgpGZWIgMTIgMjA6MjI6MTAgaXAtMTAwLTAt MTAwLTEga2VybmVsOiBbICAxNTAuNTAyNzMzXSAKRmViIDEyIDIwOjIyOjEwIGlwLTEwMC0wLTEw MC0xIGtlcm5lbDogWyAgMTUwLjUwMjc1OV0gbWQwOiBkZXRlY3RlZCBjYXBhY2l0eSBjaGFuZ2Ug ZnJvbSAwIHRvIDQzOTgwNDQ0MTM5NTIKRmViIDEyIDIwOjIyOjEwIGlwLTEwMC0wLTEwMC0xIGtl cm5lbDogWyAgMTUwLjUxOTk5NV0gIG1kMDogdW5rbm93biBwYXJ0aXRpb24gdGFibGUKRmViIDEy IDIwOjIyOjEwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgMTUwLjg1MTE0MF0gU0dJIFhGUyB3 aXRoIEFDTHMsIHNlY3VyaXR5IGF0dHJpYnV0ZXMsIHJlYWx0aW1lLCBsYXJnZSBibG9jay9pbm9k ZSBudW1iZXJzLCBubyBkZWJ1ZyBlbmFibGVkCkZlYiAxMiAyMDoyMjoxMCBpcC0xMDAtMC0xMDAt MSBrZXJuZWw6IFsgIDE1MC44NTM5ODBdIFNHSSBYRlMgUXVvdGEgTWFuYWdlbWVudCBzdWJzeXN0 ZW0KRmViIDEyIDIwOjIyOjEwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgMTUwLjg2Mzg5MF0g WEZTIChtZDApOiBNb3VudGluZyBGaWxlc3lzdGVtCkZlYiAxMiAyMDoyMjoxMCBpcC0xMDAtMC0x MDAtMSBrZXJuZWw6IFsgIDE1MS4xODc4MjddIFhGUyAobWQwKTogU3RhcnRpbmcgcmVjb3Zlcnkg KGxvZ2RldjogaW50ZXJuYWwpCkZlYiAxMiAyMDoyMjoxMiBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6 IFsgIDE1Mi45NTA5NjNdIFhGUyAobWQwKTogRW5kaW5nIHJlY292ZXJ5IChsb2dkZXY6IGludGVy bmFsKQo= --14dae9340de1e2fa7104d73d1633 Content-Type: text/plain; charset=US-ASCII; name="xfs_corruption_logs2.txt" Content-Disposition: attachment; filename="xfs_corruption_logs2.txt" Content-Transfer-Encoding: base64 X-Attachment-Id: f_hdy7cjhd1 TWFyICA1IDAxOjE0OjMzIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWzE0MTM5OTMwLjI0ODYxOV0g WEZTIChtZDApOiBDb3JydXB0aW9uIGRldGVjdGVkLiBVbm1vdW50IGFuZCBydW4geGZzX3JlcGFp cgpNYXIgIDUgMDE6MTQ6MzMgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbMTQxMzk5MzAuMjQ4NjQx XSBYRlMgKG1kMCk6IEludGVybmFsIGVycm9yIHhmc190cmFuc19jYW5jZWwgYXQgbGluZSAxOTI1 IG9mIGZpbGUgZnMveGZzL3hmc190cmFucy5jLiAgQ2FsbGVyIDB4ZmZmZmZmZmZhMDIxNzM4ZgpN YXIgIDUgMDE6MTQ6MzMgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbMTQxMzk5MzAuMjQ4NjQyXSAK TWFyICA1IDAxOjE0OjMzIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWzE0MTM5OTMwLjI0ODY1NF0g UGlkOiA4MTQwLCBjb21tOiBjbS1zcWwtc2VydmVyIE5vdCB0YWludGVkIDMuMi4yOC00NS42My5h bXpuMS54ODZfNjQgIzEKTWFyICA1IDAxOjE0OjMzIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWzE0 MTM5OTMwLjI0ODY4MV0gQ2FsbCBUcmFjZToKTWFyICA1IDAxOjE0OjMzIGlwLTEwMC0wLTEwMC0x IGtlcm5lbDogWzE0MTM5OTMwLjI0ODcxOV0gIFs8ZmZmZmZmZmZhMDIwMzkwYT5dIHhmc19lcnJv cl9yZXBvcnQrMHgzYS8weDQwIFt4ZnNdCk1hciAgNSAwMToxNDozMyBpcC0xMDAtMC0xMDAtMSBr ZXJuZWw6IFsxNDEzOTkzMC4yNDg3NDRdICBbPGZmZmZmZmZmYTAyMTczOGY+XSA/IHhmc19jcmVh dGUrMHgxZGYvMHg2NDAgW3hmc10KTWFyICA1IDAxOjE0OjMzIGlwLTEwMC0wLTEwMC0xIGtlcm5l bDogWzE0MTM5OTMwLjI0ODc3Ml0gIFs8ZmZmZmZmZmZhMDI1MWE0OT5dIHhmc190cmFuc19jYW5j ZWwrMHhlOS8weDExMCBbeGZzXQpNYXIgIDUgMDE6MTQ6MzMgaXAtMTAwLTAtMTAwLTEga2VybmVs OiBbMTQxMzk5MzAuMjQ4Nzk0XSAgWzxmZmZmZmZmZmEwMjE3MzhmPl0geGZzX2NyZWF0ZSsweDFk Zi8weDY0MCBbeGZzXQpNYXIgIDUgMDE6MTQ6MzMgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbMTQx Mzk5MzAuMjQ4ODE0XSAgWzxmZmZmZmZmZmEwMjA3YmUyPl0gPyB4ZnNfaXVubG9jaysweDYyLzB4 ZjAgW3hmc10KTWFyICA1IDAxOjE0OjMzIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWzE0MTM5OTMw LjI0ODgzNV0gIFs8ZmZmZmZmZmZhMDIwYmU3MT5dIHhmc192bl9ta25vZCsweGExLzB4MWEwIFt4 ZnNdCk1hciAgNSAwMToxNDozMyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsxNDEzOTkzMC4yNDg4 NTZdICBbPGZmZmZmZmZmYTAyMGJmOGI+XSB4ZnNfdm5fY3JlYXRlKzB4Yi8weDEwIFt4ZnNdCk1h ciAgNSAwMToxNDozMyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsxNDEzOTkzMC4yNDg4NzFdICBb PGZmZmZmZmZmODExNGY4ZDA+XSB2ZnNfY3JlYXRlKzB4YTAvMHhjMApNYXIgIDUgMDE6MTQ6MzMg aXAtMTAwLTAtMTAwLTEga2VybmVsOiBbMTQxMzk5MzAuMjQ4ODc4XSAgWzxmZmZmZmZmZjgxMTUx MzRhPl0gZG9fbGFzdCsweDU3YS8weDc5MApNYXIgIDUgMDE6MTQ6MzMgaXAtMTAwLTAtMTAwLTEg a2VybmVsOiBbMTQxMzk5MzAuMjQ4ODg1XSAgWzxmZmZmZmZmZjgxMTUxZWEwPl0gcGF0aF9vcGVu YXQrMHhkMC8weDNmMApNYXIgIDUgMDE6MTQ6MzMgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbMTQx Mzk5MzAuMjQ4ODkzXSAgWzxmZmZmZmZmZjgxMTUzN2VlPl0gPyB1c2VyX3BhdGhfYXRfZW1wdHkr MHg1ZS8weGEwCk1hciAgNSAwMToxNDozMyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsxNDEzOTkz MC4yNDg4OTldICBbPGZmZmZmZmZmODExNTIyZDQ+XSBkb19maWxwX29wZW4rMHg0NC8weGEwCk1h ciAgNSAwMToxNDozMyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsxNDEzOTkzMC4yNDg5MDddICBb PGZmZmZmZmZmODExNWYyZDI+XSA/IGFsbG9jX2ZkKzB4MTAyLzB4MTUwCk1hciAgNSAwMToxNDoz MyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsxNDEzOTkzMC4yNDg5MTZdICBbPGZmZmZmZmZmODEx NDJmNDI+XSBkb19zeXNfb3BlbisweDEwMi8weDFlMApNYXIgIDUgMDE6MTQ6MzMgaXAtMTAwLTAt MTAwLTEga2VybmVsOiBbMTQxMzk5MzAuMjQ4OTI3XSAgWzxmZmZmZmZmZjgxMGJhNDRlPl0gPyBh dWRpdF9zeXNjYWxsX2VudHJ5KzB4MWJlLzB4MWUwCk1hciAgNSAwMToxNDozMyBpcC0xMDAtMC0x MDAtMSBrZXJuZWw6IFsxNDEzOTkzMC4yNDg5MzVdICBbPGZmZmZmZmZmODExNDMwNGI+XSBzeXNf b3BlbisweDFiLzB4MjAKTWFyICA1IDAxOjE0OjMzIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWzE0 MTM5OTMwLjI0ODk0NV0gIFs8ZmZmZmZmZmY4MTNiOTAxMj5dIHN5c3RlbV9jYWxsX2Zhc3RwYXRo KzB4MTYvMHgxYgpNYXIgIDUgMDE6MTQ6MzMgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbMTQxMzk5 MzAuMjQ4OTUzXSBYRlMgKG1kMCk6IHhmc19kb19mb3JjZV9zaHV0ZG93bigweDgpIGNhbGxlZCBm cm9tIGxpbmUgMTkyNiBvZiBmaWxlIGZzL3hmcy94ZnNfdHJhbnMuYy4gIFJldHVybiBhZGRyZXNz ID0gMHhmZmZmZmZmZmEwMjUxYTYyCk1hciAgNSAwMToxNDozMyBpcC0xMDAtMC0xMDAtMSBrZXJu ZWw6IFsxNDEzOTkzMC4yNTU5OTldIFhGUyAobWQwKTogQ29ycnVwdGlvbiBvZiBpbi1tZW1vcnkg ZGF0YSBkZXRlY3RlZC4gIFNodXR0aW5nIGRvd24gZmlsZXN5c3RlbQpNYXIgIDUgMDE6MTQ6MzMg aXAtMTAwLTAtMTAwLTEga2VybmVsOiBbMTQxMzk5MzAuMjU2MDMxXSBYRlMgKG1kMCk6IFBsZWFz ZSB1bW91bnQgdGhlIGZpbGVzeXN0ZW0gYW5kIHJlY3RpZnkgdGhlIHByb2JsZW0ocykKTWFyICA1 IDAxOjE0OjQ2IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWzE0MTM5OTQzLjkwNDA1NF0gWEZTICht ZDApOiB4ZnNfbG9nX2ZvcmNlOiBlcnJvciA1IHJldHVybmVkLgpNYXIgIDUgMDE6MTU6MTYgaXAt MTAwLTAtMTAwLTEga2VybmVsOiBbMTQxMzk5NzMuOTg0MDM3XSBYRlMgKG1kMCk6IHhmc19sb2df Zm9yY2U6IGVycm9yIDUgcmV0dXJuZWQuCk1hciAgNSAwMToxNTo0NiBpcC0xMDAtMC0xMDAtMSBr ZXJuZWw6IFsxNDE0MDAwNC4wNjQwNDddIFhGUyAobWQwKTogeGZzX2xvZ19mb3JjZTogZXJyb3Ig NSByZXR1cm5lZC4KTWFyICA1IDAxOjE2OjE2IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWzE0MTQw MDM0LjE0NDAzNV0gWEZTIChtZDApOiB4ZnNfbG9nX2ZvcmNlOiBlcnJvciA1IHJldHVybmVkLgpN YXIgIDUgMDE6MTY6NDYgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbMTQxNDAwNjQuMjI0MDMzXSBY RlMgKG1kMCk6IHhmc19sb2dfZm9yY2U6IGVycm9yIDUgcmV0dXJuZWQuCk1hciAgNSAwMToxNzox NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsxNDE0MDA5NC4zMDQwNDRdIFhGUyAobWQwKTogeGZz X2xvZ19mb3JjZTogZXJyb3IgNSByZXR1cm5lZC4KTWFyICA1IDAxOjE3OjQ3IGlwLTEwMC0wLTEw MC0xIGtlcm5lbDogWzE0MTQwMTI0LjM4NDA4OV0gWEZTIChtZDApOiB4ZnNfbG9nX2ZvcmNlOiBl cnJvciA1IHJldHVybmVkLgpNYXIgIDUgMDE6MTg6MTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBb MTQxNDAxNTQuNDY0MDQ2XSBYRlMgKG1kMCk6IHhmc19sb2dfZm9yY2U6IGVycm9yIDUgcmV0dXJu ZWQuCk1hciAgNSAwMToxODo0NyBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsxNDE0MDE4NC41NDQw NDhdIFhGUyAobWQwKTogeGZzX2xvZ19mb3JjZTogZXJyb3IgNSByZXR1cm5lZC4KTWFyICA1IDAx OjE5OjE3IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWzE0MTQwMjE0LjYyNDA0Ml0gWEZTIChtZDAp OiB4ZnNfbG9nX2ZvcmNlOiBlcnJvciA1IHJldHVybmVkLgpNYXIgIDUgMDE6MTk6NDcgaXAtMTAw LTAtMTAwLTEga2VybmVsOiBbMTQxNDAyNDQuNzA0MDUzXSBYRlMgKG1kMCk6IHhmc19sb2dfZm9y Y2U6IGVycm9yIDUgcmV0dXJuZWQuCk1hciAgNSAwMToyMDoxNyBpcC0xMDAtMC0xMDAtMSBrZXJu ZWw6IFsxNDE0MDI3NC43ODQwMzddIFhGUyAobWQwKTogeGZzX2xvZ19mb3JjZTogZXJyb3IgNSBy ZXR1cm5lZC4KTWFyICA1IDAxOjIwOjQ3IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWzE0MTQwMzA0 Ljg2NDA1M10gWEZTIChtZDApOiB4ZnNfbG9nX2ZvcmNlOiBlcnJvciA1IHJldHVybmVkLgpNYXIg IDUgMDE6MjE6MTcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbMTQxNDAzMzQuOTQ0MDQ3XSBYRlMg KG1kMCk6IHhmc19sb2dfZm9yY2U6IGVycm9yIDUgcmV0dXJuZWQuCk1hciAgNSAwMToyMTo0NyBp cC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsxNDE0MDM2NS4wMjQwMzldIFhGUyAobWQwKTogeGZzX2xv Z19mb3JjZTogZXJyb3IgNSByZXR1cm5lZC4KTWFyICA1IDAxOjIyOjE3IGlwLTEwMC0wLTEwMC0x IGtlcm5lbDogWzE0MTQwMzk1LjEwNDA0OF0gWEZTIChtZDApOiB4ZnNfbG9nX2ZvcmNlOiBlcnJv ciA1IHJldHVybmVkLgpNYXIgIDUgMDE6MjI6NDcgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbMTQx NDA0MjUuMTg0MDU5XSBYRlMgKG1kMCk6IHhmc19sb2dfZm9yY2U6IGVycm9yIDUgcmV0dXJuZWQu Ck1hciAgNSAwMToyMzoxOCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsxNDE0MDQ1NS4yNjgwMzJd IFhGUyAobWQwKTogeGZzX2xvZ19mb3JjZTogZXJyb3IgNSByZXR1cm5lZC4KTWFyICA1IDAxOjIz OjQ4IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWzE0MTQwNDg1LjM0NDA1N10gWEZTIChtZDApOiB4 ZnNfbG9nX2ZvcmNlOiBlcnJvciA1IHJldHVybmVkLgpNYXIgIDUgMDE6MjQ6MTggaXAtMTAwLTAt MTAwLTEga2VybmVsOiBbMTQxNDA1MTUuNDI0MDQ5XSBYRlMgKG1kMCk6IHhmc19sb2dfZm9yY2U6 IGVycm9yIDUgcmV0dXJuZWQuCk1hciAgNSAwMToyNDo0OCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6 IFsxNDE0MDU0NS41MDQwMzZdIFhGUyAobWQwKTogeGZzX2xvZ19mb3JjZTogZXJyb3IgNSByZXR1 cm5lZC4KTWFyICA1IDAxOjI1OjE4IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWzE0MTQwNTc1LjU4 NDA1MF0gWEZTIChtZDApOiB4ZnNfbG9nX2ZvcmNlOiBlcnJvciA1IHJldHVybmVkLgpNYXIgIDUg MDE6MjU6NDggaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbMTQxNDA2MDUuNjY0MDY2XSBYRlMgKG1k MCk6IHhmc19sb2dfZm9yY2U6IGVycm9yIDUgcmV0dXJuZWQuCk1hciAgNSAwMToyNjoxOCBpcC0x MDAtMC0xMDAtMSBrZXJuZWw6IFsxNDE0MDYzNS43NDQwMzldIFhGUyAobWQwKTogeGZzX2xvZ19m b3JjZTogZXJyb3IgNSByZXR1cm5lZC4KTWFyICA1IDAxOjI2OjQ4IGlwLTEwMC0wLTEwMC0xIGtl cm5lbDogWzE0MTQwNjY1LjgyNDA0Nl0gWEZTIChtZDApOiB4ZnNfbG9nX2ZvcmNlOiBlcnJvciA1 IHJldHVybmVkLgpNYXIgIDUgMDE6Mjc6MTggaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbMTQxNDA2 OTUuOTA0MDMyXSBYRlMgKG1kMCk6IHhmc19sb2dfZm9yY2U6IGVycm9yIDUgcmV0dXJuZWQuCk1h ciAgNSAwMToyNzo0OCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsxNDE0MDcyNS45ODQwNTBdIFhG UyAobWQwKTogeGZzX2xvZ19mb3JjZTogZXJyb3IgNSByZXR1cm5lZC4KTWFyICA1IDAxOjI4OjE4 IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWzE0MTQwNzU2LjA2NDAzMV0gWEZTIChtZDApOiB4ZnNf bG9nX2ZvcmNlOiBlcnJvciA1IHJldHVybmVkLgpNYXIgIDUgMDE6Mjg6NDggaXAtMTAwLTAtMTAw LTEga2VybmVsOiBbMTQxNDA3ODYuMTQ0MDQzXSBYRlMgKG1kMCk6IHhmc19sb2dfZm9yY2U6IGVy cm9yIDUgcmV0dXJuZWQuCk1hciAgNSAwMToyOToxOCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsx NDE0MDgxNi4yMjQwNTJdIFhGUyAobWQwKTogeGZzX2xvZ19mb3JjZTogZXJyb3IgNSByZXR1cm5l ZC4KTWFyICA1IDAxOjI5OjQ5IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWzE0MTQwODQ2LjMwNDA1 NV0gWEZTIChtZDApOiB4ZnNfbG9nX2ZvcmNlOiBlcnJvciA1IHJldHVybmVkLgpNYXIgIDUgMDE6 MzA6MTMgaXAtMTAwLTAtMTAwLTEgaW5pdDogdHR5ICgvZGV2L3R0eTEpIG1haW4gcHJvY2VzcyAo MTc0NSkga2lsbGVkIGJ5IFRFUk0gc2lnbmFsCk1hciAgNSAwMTozMDoxMyBpcC0xMDAtMC0xMDAt MSBpbml0OiBzZXJpYWwgKGh2YzApIG1haW4gcHJvY2VzcyAoMTc0OCkga2lsbGVkIGJ5IFRFUk0g c2lnbmFsCk1hciAgNSAwMTozMDoxMyBpcC0xMDAtMC0xMDAtMSBpbml0OiB0dHkgKC9kZXYvdHR5 MikgbWFpbiBwcm9jZXNzICgxNzUwKSBraWxsZWQgYnkgVEVSTSBzaWduYWwKTWFyICA1IDAxOjMw OjEzIGlwLTEwMC0wLTEwMC0xIGluaXQ6IHR0eSAoL2Rldi90dHkzKSBtYWluIHByb2Nlc3MgKDE3 NTMpIGtpbGxlZCBieSBURVJNIHNpZ25hbApNYXIgIDUgMDE6MzA6MTMgaXAtMTAwLTAtMTAwLTEg aW5pdDogdHR5ICgvZGV2L3R0eTQpIG1haW4gcHJvY2VzcyAoMTc1NSkga2lsbGVkIGJ5IFRFUk0g c2lnbmFsCk1hciAgNSAwMTozMDoxMyBpcC0xMDAtMC0xMDAtMSBpbml0OiB0dHkgKC9kZXYvdHR5 NSkgbWFpbiBwcm9jZXNzICgxNzU3KSBraWxsZWQgYnkgVEVSTSBzaWduYWwKTWFyICA1IDAxOjMw OjEzIGlwLTEwMC0wLTEwMC0xIGluaXQ6IHR0eSAoL2Rldi90dHk2KSBtYWluIHByb2Nlc3MgKDE3 NTkpIGtpbGxlZCBieSBURVJNIHNpZ25hbApNYXIgIDUgMDE6MzA6MTMgaXAtMTAwLTAtMTAwLTEg aW5pdDogcGx5bW91dGgtc2h1dGRvd24gbWFpbiBwcm9jZXNzICgyODc0OSkgdGVybWluYXRlZCB3 aXRoIHN0YXR1cyAxCk1hciAgNSAwMTozMDoxMyBpcC0xMDAtMC0xMDAtMSBpbml0OiBzcGxhc2gt bWFuYWdlciBtYWluIHByb2Nlc3MgKDI4NzQ1KSB0ZXJtaW5hdGVkIHdpdGggc3RhdHVzIDEKTWFy ICA1IDAxOjMwOjE0IGlwLTEwMC0wLTEwMC0xIG50cGRbMTM5N106IG50cGQgZXhpdGluZyBvbiBz aWduYWwgMTUKTWFyICA1IDAxOjMwOjE1IGlwLTEwMC0wLTEwMC0xIGluaXQ6IERpc2Nvbm5lY3Rl ZCBmcm9tIHN5c3RlbSBidXMKTWFyICA1IDAxOjMwOjE1IGlwLTEwMC0wLTEwMC0xIGF1ZGl0ZFsx Mjk5XTogVGhlIGF1ZGl0IGRhZW1vbiBpcyBleGl0aW5nLgpNYXIgIDUgMDE6MzA6MTUgaXAtMTAw LTAtMTAwLTEga2VybmVsOiBbMTQxNDA4NzIuMzk0Njc2XSB0eXBlPTEzMDUgYXVkaXQoMTM2MjQ0 NzAxNS4xNTk6OTAzNzg2KTogYXVkaXRfcGlkPTAgb2xkPTEyOTkgYXVpZD00Mjk0OTY3Mjk1IHNl cz00Mjk0OTY3Mjk1IHJlcz0xCk1hciAgNSAwMTozMDoxNSBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6 IFsxNDE0MDg3Mi41MDQwNjZdIHR5cGU9MTMwNSBhdWRpdCgxMzYyNDQ3MDE1LjI3MTo5MDM3ODcp OiBhdWRpdF9lbmFibGVkPTAgb2xkPTEgYXVpZD00Mjk0OTY3Mjk1IHNlcz00Mjk0OTY3Mjk1IHJl cz0xCk1hciAgNSAwMTozMDoxNSBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IEtlcm5lbCBsb2dnaW5n IChwcm9jKSBzdG9wcGVkLgpNYXIgIDUgMDE6MzA6MTUgaXAtMTAwLTAtMTAwLTEgcnN5c2xvZ2Q6 IFtvcmlnaW4gc29mdHdhcmU9InJzeXNsb2dkIiBzd1ZlcnNpb249IjUuOC4xMCIgeC1waWQ9IjEz MTQiIHgtaW5mbz0iaHR0cDovL3d3dy5yc3lzbG9nLmNvbSJdIGV4aXRpbmcgb24gc2lnbmFsIDE1 LgpNYXIgIDUgMDE6MzE6MjAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBpbWtsb2cgNS44LjEwLCBs b2cgc291cmNlID0gL3Byb2Mva21zZyBzdGFydGVkLgpNYXIgIDUgMDE6MzE6MjAgaXAtMTAwLTAt MTAwLTEgcnN5c2xvZ2Q6IFtvcmlnaW4gc29mdHdhcmU9InJzeXNsb2dkIiBzd1ZlcnNpb249IjUu OC4xMCIgeC1waWQ9IjEzMTAiIHgtaW5mbz0iaHR0cDovL3d3dy5yc3lzbG9nLmNvbSJdIHN0YXJ0 Ck1hciAgNSAwMTozMToyMCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4wMDAwMDBdIElu aXRpYWxpemluZyBjZ3JvdXAgc3Vic3lzIGNwdXNldApNYXIgIDUgMDE6MzE6MjAgaXAtMTAwLTAt MTAwLTEga2VybmVsOiBbICAgIDAuMDAwMDAwXSBJbml0aWFsaXppbmcgY2dyb3VwIHN1YnN5cyBj cHUKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjAwMDAwMF0g TGludXggdmVyc2lvbiAzLjIuMjgtNDUuNjMuYW16bjEueDg2XzY0IChtb2NrYnVpbGRAZ29iaS1i dWlsZC0zMTAwNCkgKGdjYyB2ZXJzaW9uIDQuNC42IDIwMTEwNzMxIChSZWQgSGF0IDQuNC42LTMp IChHQ0MpICkgIzEgU01QIEZyaSBBdWcgMjQgMDU6MzQ6NDkgVVRDIDIwMTIKTWFyICA1IDAxOjMx OjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjAwMDAwMF0gQ29tbWFuZCBsaW5lOiBy b290PUxBQkVMPS8gY29uc29sZT1odmMwIExBTkc9ZW5fVVMuVVRGLTggS0VZVEFCTEU9dXMKTWFy ICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjAwMDAwMF0gTWFya2lu ZyBUU0MgdW5zdGFibGUgZHVlIHRvIFhlbiBkb21haW4KTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0w LTEwMC0xIGtlcm5lbDogWyAgICAwLjAwMDAwMF0gQUNQSSBpbiB1bnByaXZpbGVnZWQgZG9tYWlu IGRpc2FibGVkCk1hciAgNSAwMTozMToyMCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4w MDAwMDBdIFJlbGVhc2VkIDAgcGFnZXMgb2YgdW51c2VkIG1lbW9yeQpNYXIgIDUgMDE6MzE6MjAg aXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMDAwMDAwXSBTZXQgMCBwYWdlKHMpIHRvIDEt MSBtYXBwaW5nCk1hciAgNSAwMTozMToyMCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4w MDAwMDBdIEJJT1MtcHJvdmlkZWQgcGh5c2ljYWwgUkFNIG1hcDoKTWFyICA1IDAxOjMxOjIwIGlw LTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjAwMDAwMF0gIFhlbjogMDAwMDAwMDAwMDAwMDAw MCAtIDAwMDAwMDAwMDAwYTAwMDAgKHVzYWJsZSkKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEw MC0xIGtlcm5lbDogWyAgICAwLjAwMDAwMF0gIFhlbjogMDAwMDAwMDAwMDBhMDAwMCAtIDAwMDAw MDAwMDAxMDAwMDAgKHJlc2VydmVkKQpNYXIgIDUgMDE6MzE6MjAgaXAtMTAwLTAtMTAwLTEga2Vy bmVsOiBbICAgIDAuMDAwMDAwXSAgWGVuOiAwMDAwMDAwMDAwMTAwMDAwIC0gMDAwMDAwMDFlMDgw MDAwMCAodXNhYmxlKQpNYXIgIDUgMDE6MzE6MjAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAg IDAuMDAwMDAwXSBOWCAoRXhlY3V0ZSBEaXNhYmxlKSBwcm90ZWN0aW9uOiBhY3RpdmUKTWFyICA1 IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjAwMDAwMF0gRE1JIG5vdCBw cmVzZW50IG9yIGludmFsaWQuCk1hciAgNSAwMTozMToyMCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6 IFsgICAgMC4wMDAwMDBdIE5vIEFHUCBicmlkZ2UgZm91bmQKTWFyICA1IDAxOjMxOjIwIGlwLTEw MC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjAwMDAwMF0gbGFzdF9wZm4gPSAweDFlMDgwMCBtYXhf YXJjaF9wZm4gPSAweDQwMDAwMDAwMApNYXIgIDUgMDE6MzE6MjAgaXAtMTAwLTAtMTAwLTEga2Vy bmVsOiBbICAgIDAuMDAwMDAwXSBsYXN0X3BmbiA9IDB4MTAwMDAwIG1heF9hcmNoX3BmbiA9IDB4 NDAwMDAwMDAwCk1hciAgNSAwMTozMToyMCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4w MDAwMDBdIGluaXRfbWVtb3J5X21hcHBpbmc6IDAwMDAwMDAwMDAwMDAwMDAtMDAwMDAwMDEwMDAw MDAwMApNYXIgIDUgMDE6MzE6MjAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMDAwMDAw XSBpbml0X21lbW9yeV9tYXBwaW5nOiAwMDAwMDAwMTAwMDAwMDAwLTAwMDAwMDAxZTA4MDAwMDAK TWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjAwMDAwMF0gUkFN RElTSzogMDE5YTUwMDAgLSAwMmQ2MzAwMApNYXIgIDUgMDE6MzE6MjAgaXAtMTAwLTAtMTAwLTEg a2VybmVsOiBbICAgIDAuMDAwMDAwXSBObyBOVU1BIGNvbmZpZ3VyYXRpb24gZm91bmQKTWFyICA1 IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjAwMDAwMF0gRmFraW5nIGEg bm9kZSBhdCAwMDAwMDAwMDAwMDAwMDAwLTAwMDAwMDAxZTA4MDAwMDAKTWFyICA1IDAxOjMxOjIw IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjAwMDAwMF0gSW5pdG1lbSBzZXR1cCBub2Rl IDAgMDAwMDAwMDAwMDAwMDAwMC0wMDAwMDAwMWUwODAwMDAwCk1hciAgNSAwMTozMToyMCBpcC0x MDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4wMDAwMDBdICAgTk9ERV9EQVRBIFswMDAwMDAwMWRm ZmZiMDAwIC0gMDAwMDAwMDFkZmZmZmZmZl0KTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0x IGtlcm5lbDogWyAgICAwLjAwMDAwMF0gWm9uZSBQRk4gcmFuZ2VzOgpNYXIgIDUgMDE6MzE6MjAg aXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMDAwMDAwXSAgIERNQSAgICAgIDB4MDAwMDAw MTAgLT4gMHgwMDAwMTAwMApNYXIgIDUgMDE6MzE6MjAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBb ICAgIDAuMDAwMDAwXSAgIERNQTMyICAgIDB4MDAwMDEwMDAgLT4gMHgwMDEwMDAwMApNYXIgIDUg MDE6MzE6MjAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMDAwMDAwXSAgIE5vcm1hbCAg IDB4MDAxMDAwMDAgLT4gMHgwMDFlMDgwMApNYXIgIDUgMDE6MzE6MjAgaXAtMTAwLTAtMTAwLTEg a2VybmVsOiBbICAgIDAuMDAwMDAwXSBNb3ZhYmxlIHpvbmUgc3RhcnQgUEZOIGZvciBlYWNoIG5v ZGUKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjAwMDAwMF0g ZWFybHlfbm9kZV9tYXBbMl0gYWN0aXZlIFBGTiByYW5nZXMKTWFyICA1IDAxOjMxOjIwIGlwLTEw MC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjAwMDAwMF0gICAgIDA6IDB4MDAwMDAwMTAgLT4gMHgw MDAwMDBhMApNYXIgIDUgMDE6MzE6MjAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMDAw MDAwXSAgICAgMDogMHgwMDAwMDEwMCAtPiAweDAwMWUwODAwCk1hciAgNSAwMTozMToyMCBpcC0x MDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4wMDAwMDBdIFNNUDogQWxsb3dpbmcgMiBDUFVzLCAw IGhvdHBsdWcgQ1BVcwpNYXIgIDUgMDE6MzE6MjAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAg IDAuMDAwMDAwXSBObyBsb2NhbCBBUElDIHByZXNlbnQKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0w LTEwMC0xIGtlcm5lbDogWyAgICAwLjAwMDAwMF0gQVBJQzogZGlzYWJsZSBhcGljIGZhY2lsaXR5 Ck1hciAgNSAwMTozMToyMCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4wMDAwMDBdIEFQ SUM6IHN3aXRjaGVkIHRvIGFwaWMgTk9PUApNYXIgIDUgMDE6MzE6MjAgaXAtMTAwLTAtMTAwLTEg a2VybmVsOiBbICAgIDAuMDAwMDAwXSBQTTogUmVnaXN0ZXJlZCBub3NhdmUgbWVtb3J5OiAwMDAw MDAwMDAwMGEwMDAwIC0gMDAwMDAwMDAwMDEwMDAwMApNYXIgIDUgMDE6MzE6MjAgaXAtMTAwLTAt MTAwLTEga2VybmVsOiBbICAgIDAuMDAwMDAwXSBQQ0k6IFdhcm5pbmc6IENhbm5vdCBmaW5kIGEg Z2FwIGluIHRoZSAzMmJpdCBhZGRyZXNzIHJhbmdlCk1hciAgNSAwMTozMToyMCBpcC0xMDAtMC0x MDAtMSBrZXJuZWw6IFsgICAgMC4wMDAwMDBdIFBDSTogVW5hc3NpZ25lZCBkZXZpY2VzIHdpdGgg MzJiaXQgcmVzb3VyY2UgcmVnaXN0ZXJzIG1heSBicmVhayEKTWFyICA1IDAxOjMxOjIwIGlwLTEw MC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjAwMDAwMF0gQWxsb2NhdGluZyBQQ0kgcmVzb3VyY2Vz IHN0YXJ0aW5nIGF0IDFlMDkwMDAwMCAoZ2FwOiAxZTA5MDAwMDA6NDAwMDAwKQpNYXIgIDUgMDE6 MzE6MjAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMDAwMDAwXSBCb290aW5nIHBhcmF2 aXJ0dWFsaXplZCBrZXJuZWwgb24gWGVuCk1hciAgNSAwMTozMToyMCBpcC0xMDAtMC0xMDAtMSBr ZXJuZWw6IFsgICAgMC4wMDAwMDBdIFhlbiB2ZXJzaW9uOiAzLjQuMy0yLjYuMTggKHByZXNlcnZl LUFEKQpNYXIgIDUgMDE6MzE6MjAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMDAwMDAw XSBzZXR1cF9wZXJjcHU6IE5SX0NQVVM6MzIgbnJfY3B1bWFza19iaXRzOjMyIG5yX2NwdV9pZHM6 MiBucl9ub2RlX2lkczoxCk1hciAgNSAwMTozMToyMCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsg ICAgMC4wMDAwMDBdIFBFUkNQVTogRW1iZWRkZWQgMjcgcGFnZXMvY3B1IEBmZmZmODgwMWRmYzAw MDAwIHM4MDUxMiByODE5MiBkMjE4ODggdTEwNDg1NzYKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0w LTEwMC0xIGtlcm5lbDogWyAgICAwLjAwMDAwMF0gQnVpbHQgMSB6b25lbGlzdHMgaW4gTm9kZSBv cmRlciwgbW9iaWxpdHkgZ3JvdXBpbmcgb24uICBUb3RhbCBwYWdlczogMTkzNTI0NApNYXIgIDUg MDE6MzE6MjAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMDAwMDAwXSBQb2xpY3kgem9u ZTogTm9ybWFsCk1hciAgNSAwMTozMToyMCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4w MDAwMDBdIEtlcm5lbCBjb21tYW5kIGxpbmU6IHJvb3Q9TEFCRUw9LyBjb25zb2xlPWh2YzAgTEFO Rz1lbl9VUy5VVEYtOCBLRVlUQUJMRT11cwpNYXIgIDUgMDE6MzE6MjAgaXAtMTAwLTAtMTAwLTEg a2VybmVsOiBbICAgIDAuMDAwMDAwXSBQSUQgaGFzaCB0YWJsZSBlbnRyaWVzOiA0MDk2IChvcmRl cjogMywgMzI3NjggYnl0ZXMpCk1hciAgNSAwMTozMToyMCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6 IFsgICAgMC4wMDAwMDBdIENoZWNraW5nIGFwZXJ0dXJlLi4uCk1hciAgNSAwMTozMToyMCBpcC0x MDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4wMDAwMDBdIE5vIEFHUCBicmlkZ2UgZm91bmQKTWFy ICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjAwMDAwMF0gTWVtb3J5 OiA3NjEyMzg0ay83ODcyNTEyayBhdmFpbGFibGUgKDM4MzFrIGtlcm5lbCBjb2RlLCA0NDhrIGFi c2VudCwgMjU5NjgwayByZXNlcnZlZCwgMjk4NmsgZGF0YSwgNTY0ayBpbml0KQpNYXIgIDUgMDE6 MzE6MjAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMDAwMDAwXSBTTFVCOiBHZW5zbGFi cz0xNSwgSFdhbGlnbj02NCwgT3JkZXI9MC0zLCBNaW5PYmplY3RzPTAsIENQVXM9MiwgTm9kZXM9 MQpNYXIgIDUgMDE6MzE6MjAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMDAwMDAwXSBI aWVyYXJjaGljYWwgUkNVIGltcGxlbWVudGF0aW9uLgpNYXIgIDUgMDE6MzE6MjAgaXAtMTAwLTAt MTAwLTEga2VybmVsOiBbICAgIDAuMDAwMDAwXSBOUl9JUlFTOjQzNTIgbnJfaXJxczoyODggMTYK TWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjAwMDAwMF0gQ29u c29sZTogY29sb3VyIGR1bW15IGRldmljZSA4MHgyNQpNYXIgIDUgMDE6MzE6MjAgaXAtMTAwLTAt MTAwLTEga2VybmVsOiBbICAgIDAuMDAwMDAwXSBjb25zb2xlIFt0dHkwXSBlbmFibGVkCk1hciAg NSAwMTozMToyMCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4wMDAwMDBdIGNvbnNvbGUg W2h2YzBdIGVuYWJsZWQKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAg ICAwLjAwMDAwMF0gaW5zdGFsbGluZyBYZW4gdGltZXIgZm9yIENQVSAwCk1hciAgNSAwMTozMToy MCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4wMDAwMDBdIERldGVjdGVkIDIyNjYuNzQ2 IE1IeiBwcm9jZXNzb3IuCk1hciAgNSAwMTozMToyMCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsg ICAgMC4wMDQwMDBdIENhbGlicmF0aW5nIGRlbGF5IGxvb3AgKHNraXBwZWQpLCB2YWx1ZSBjYWxj dWxhdGVkIHVzaW5nIHRpbWVyIGZyZXF1ZW5jeS4uIDQ1MzMuNDkgQm9nb01JUFMgKGxwaj05MDY2 OTg0KQpNYXIgIDUgMDE6MzE6MjAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMDA0MDAw XSBwaWRfbWF4OiBkZWZhdWx0OiAzMjc2OCBtaW5pbXVtOiAzMDEKTWFyICA1IDAxOjMxOjIwIGlw LTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjAwNDAwMF0gU2VjdXJpdHkgRnJhbWV3b3JrIGlu aXRpYWxpemVkCk1hciAgNSAwMTozMToyMCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4w MDQwMDBdIERlbnRyeSBjYWNoZSBoYXNoIHRhYmxlIGVudHJpZXM6IDEwNDg1NzYgKG9yZGVyOiAx MSwgODM4ODYwOCBieXRlcykKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDog WyAgICAwLjAwNDg3OV0gSW5vZGUtY2FjaGUgaGFzaCB0YWJsZSBlbnRyaWVzOiA1MjQyODggKG9y ZGVyOiAxMCwgNDE5NDMwNCBieXRlcykKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtl cm5lbDogWyAgICAwLjAwNTg3Nl0gTW91bnQtY2FjaGUgaGFzaCB0YWJsZSBlbnRyaWVzOiAyNTYK TWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjAwNjA4OV0gSW5p dGlhbGl6aW5nIGNncm91cCBzdWJzeXMgY3B1YWNjdApNYXIgIDUgMDE6MzE6MjAgaXAtMTAwLTAt MTAwLTEga2VybmVsOiBbICAgIDAuMDA2MDk5XSBJbml0aWFsaXppbmcgY2dyb3VwIHN1YnN5cyBk ZXZpY2VzCk1hciAgNSAwMTozMToyMCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4wMDYx MDVdIEluaXRpYWxpemluZyBjZ3JvdXAgc3Vic3lzIGZyZWV6ZXIKTWFyICA1IDAxOjMxOjIwIGlw LTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjAwNjExMF0gSW5pdGlhbGl6aW5nIGNncm91cCBz dWJzeXMgYmxraW8KTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAw LjAwNjEyM10gSW5pdGlhbGl6aW5nIGNncm91cCBzdWJzeXMgcGVyZl9ldmVudApNYXIgIDUgMDE6 MzE6MjAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMDA2MjA0XSBDUFU6IFBoeXNpY2Fs IFByb2Nlc3NvciBJRDogMApNYXIgIDUgMDE6MzE6MjAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBb ICAgIDAuMDA2MjA5XSBDUFU6IFByb2Nlc3NvciBDb3JlIElEOiAwCk1hciAgNSAwMTozMToyMCBp cC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4wMDYyOTNdIFNNUCBhbHRlcm5hdGl2ZXM6IHN3 aXRjaGluZyB0byBVUCBjb2RlCk1hciAgNSAwMTozMToyMCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6 IFsgICAgMC4wMzE4MjhdIGNwdSAwIHNwaW5sb2NrIGV2ZW50IGlycSAxNwpNYXIgIDUgMDE6MzE6 MjAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMDMxOTcwXSBQZXJmb3JtYW5jZSBFdmVu dHM6IHVuc3VwcG9ydGVkIHA2IENQVSBtb2RlbCAyNiBubyBQTVUgZHJpdmVyLCBzb2Z0d2FyZSBl dmVudHMgb25seS4KTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAw LjAzMjMyN10gaW5zdGFsbGluZyBYZW4gdGltZXIgZm9yIENQVSAxCk1hciAgNSAwMTozMToyMCBp cC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4wMzIzNDJdIGNwdSAxIHNwaW5sb2NrIGV2ZW50 IGlycSAyMwpNYXIgIDUgMDE6MzE6MjAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMDMy MzczXSBTTVAgYWx0ZXJuYXRpdmVzOiBzd2l0Y2hpbmcgdG8gU01QIGNvZGUKTWFyICA1IDAxOjMx OjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjA1MjMxMV0gQnJvdWdodCB1cCAyIENQ VXMKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjA1MjYxMF0g ZGV2dG1wZnM6IGluaXRpYWxpemVkCk1hciAgNSAwMTozMToyMCBpcC0xMDAtMC0xMDAtMSBrZXJu ZWw6IFsgICAgMC4wNTY0MTBdIEdyYW50IHRhYmxlIGluaXRpYWxpemVkCk1hciAgNSAwMTozMToy MCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4wNTY0NDVdIE5FVDogUmVnaXN0ZXJlZCBw cm90b2NvbCBmYW1pbHkgMTYKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDog WyAgICAwLjA1ODE3Nl0gUENJOiBzZXR0aW5nIHVwIFhlbiBQQ0kgZnJvbnRlbmQgc3R1YgpNYXIg IDUgMDE6MzE6MjAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMDYwMTQ4XSBiaW86IGNy ZWF0ZSBzbGFiIDxiaW8tMD4gYXQgMApNYXIgIDUgMDE6MzE6MjAgaXAtMTAwLTAtMTAwLTEga2Vy bmVsOiBbICAgIDAuMDYwMTQ4XSBBQ1BJOiBJbnRlcnByZXRlciBkaXNhYmxlZC4KTWFyICA1IDAx OjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjA2MDQxMV0geGVuL2JhbGxvb246 IEluaXRpYWxpc2luZyBiYWxsb29uIGRyaXZlci4KTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEw MC0xIGtlcm5lbDogWyAgICAwLjA2NDEyNl0geGVuLWJhbGxvb246IEluaXRpYWxpc2luZyBiYWxs b29uIGRyaXZlci4KTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAw LjA2NDE5Nl0gdmdhYXJiOiBsb2FkZWQKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtl cm5lbDogWyAgICAwLjA2NDE5Nl0gUENJOiBTeXN0ZW0gZG9lcyBub3Qgc3VwcG9ydCBQQ0kKTWFy ICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjA2NDE5Nl0gUENJOiBT eXN0ZW0gZG9lcyBub3Qgc3VwcG9ydCBQQ0kKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0x IGtlcm5lbDogWyAgICAwLjA2NDE5Nl0gTmV0TGFiZWw6IEluaXRpYWxpemluZwpNYXIgIDUgMDE6 MzE6MjAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMDY0MTk2XSBOZXRMYWJlbDogIGRv bWFpbiBoYXNoIHNpemUgPSAxMjgKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5l bDogWyAgICAwLjA2NDE5Nl0gTmV0TGFiZWw6ICBwcm90b2NvbHMgPSBVTkxBQkVMRUQgQ0lQU092 NApNYXIgIDUgMDE6MzE6MjAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMDY0MTk2XSBO ZXRMYWJlbDogIHVubGFiZWxlZCB0cmFmZmljIGFsbG93ZWQgYnkgZGVmYXVsdApNYXIgIDUgMDE6 MzE6MjAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMDY0MTk2XSBTd2l0Y2hpbmcgdG8g Y2xvY2tzb3VyY2UgeGVuCk1hciAgNSAwMTozMToyMCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsg ICAgMC4wNzEwNjJdIHBucDogUG5QIEFDUEk6IGRpc2FibGVkCk1hciAgNSAwMTozMToyMCBpcC0x MDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4wNzc5NjddIE5FVDogUmVnaXN0ZXJlZCBwcm90b2Nv bCBmYW1pbHkgMgpNYXIgIDUgMDE6MzE6MjAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAu MDc4NTE5XSBJUCByb3V0ZSBjYWNoZSBoYXNoIHRhYmxlIGVudHJpZXM6IDI2MjE0NCAob3JkZXI6 IDksIDIwOTcxNTIgYnl0ZXMpCk1hciAgNSAwMTozMToyMCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6 IFsgICAgMC4wODA5MTRdIFRDUCBlc3RhYmxpc2hlZCBoYXNoIHRhYmxlIGVudHJpZXM6IDUyNDI4 OCAob3JkZXI6IDExLCA4Mzg4NjA4IGJ5dGVzKQpNYXIgIDUgMDE6MzE6MjAgaXAtMTAwLTAtMTAw LTEga2VybmVsOiBbICAgIDAuMDgzMDYxXSBUQ1AgYmluZCBoYXNoIHRhYmxlIGVudHJpZXM6IDY1 NTM2IChvcmRlcjogOCwgMTA0ODU3NiBieXRlcykKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEw MC0xIGtlcm5lbDogWyAgICAwLjA4MzMwMl0gVENQOiBIYXNoIHRhYmxlcyBjb25maWd1cmVkIChl c3RhYmxpc2hlZCA1MjQyODggYmluZCA2NTUzNikKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEw MC0xIGtlcm5lbDogWyAgICAwLjA4MzMwOF0gVENQIHJlbm8gcmVnaXN0ZXJlZApNYXIgIDUgMDE6 MzE6MjAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMDgzMzQ4XSBVRFAgaGFzaCB0YWJs ZSBlbnRyaWVzOiA0MDk2IChvcmRlcjogNSwgMTMxMDcyIGJ5dGVzKQpNYXIgIDUgMDE6MzE6MjAg aXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMDgzNDE1XSBVRFAtTGl0ZSBoYXNoIHRhYmxl IGVudHJpZXM6IDQwOTYgKG9yZGVyOiA1LCAxMzEwNzIgYnl0ZXMpCk1hciAgNSAwMTozMToyMCBp cC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4wODM1MzldIE5FVDogUmVnaXN0ZXJlZCBwcm90 b2NvbCBmYW1pbHkgMQpNYXIgIDUgMDE6MzE6MjAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAg IDAuMDgzNjExXSBVbnBhY2tpbmcgaW5pdHJhbWZzLi4uCk1hciAgNSAwMTozMToyMCBpcC0xMDAt MC0xMDAtMSBrZXJuZWw6IFsgICAgMC4xMDc0OTVdIEZyZWVpbmcgaW5pdHJkIG1lbW9yeTogMjAy MTZrIGZyZWVkCk1hciAgNSAwMTozMToyMCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4x MTQzNjBdIFBDSS1ETUE6IFVzaW5nIHNvZnR3YXJlIGJvdW5jZSBidWZmZXJpbmcgZm9yIElPIChT V0lPVExCKQpNYXIgIDUgMDE6MzE6MjAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMTE0 MzgyXSBQbGFjaW5nIDY0TUIgc29mdHdhcmUgSU8gVExCIGJldHdlZW4gZmZmZjg4MDBmYjBmMzAw MCAtIGZmZmY4ODAwZmYwZjMwMDAKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5l bDogWyAgICAwLjExNDM4OV0gc29mdHdhcmUgSU8gVExCIGF0IHBoeXMgMHhmYjBmMzAwMCAtIDB4 ZmYwZjMwMDAKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjEx NDU5M10gcGxhdGZvcm0gcnRjX2Ntb3M6IHJlZ2lzdGVyZWQgcGxhdGZvcm0gUlRDIGRldmljZSAo bm8gUE5QIGRldmljZSBmb3VuZCkKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5l bDogWyAgICAwLjExNjI1NF0gYXVkaXQ6IGluaXRpYWxpemluZyBuZXRsaW5rIHNvY2tldCAoZGlz YWJsZWQpCk1hciAgNSAwMTozMToyMCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4xNDA4 OTddIHR5cGU9MjAwMCBhdWRpdCgxMzYyNDQ3MDY5LjAwMDoxKTogaW5pdGlhbGl6ZWQKTWFyICA1 IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjE2Nzk2NV0gVkZTOiBEaXNr IHF1b3RhcyBkcXVvdF82LjUuMgpNYXIgIDUgMDE6MzE6MjAgaXAtMTAwLTAtMTAwLTEga2VybmVs OiBbICAgIDAuMTY4MTQyXSBEcXVvdC1jYWNoZSBoYXNoIHRhYmxlIGVudHJpZXM6IDUxMiAob3Jk ZXIgMCwgNDA5NiBieXRlcykKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDog WyAgICAwLjE2ODM1M10gbXNnbW5pIGhhcyBiZWVuIHNldCB0byAxNDkwNwpNYXIgIDUgMDE6MzE6 MjAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMTY4ODQ3XSBhbGc6IE5vIHRlc3QgZm9y IHN0ZHJuZyAoa3JuZykKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAg ICAwLjE2OTEwOV0gQmxvY2sgbGF5ZXIgU0NTSSBnZW5lcmljIChic2cpIGRyaXZlciB2ZXJzaW9u IDAuNCBsb2FkZWQgKG1ham9yIDI1NCkKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtl cm5lbDogWyAgICAwLjE2OTE4NV0gaW8gc2NoZWR1bGVyIG5vb3AgcmVnaXN0ZXJlZCAoZGVmYXVs dCkKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjE3MDExMV0g U2VyaWFsOiA4MjUwLzE2NTUwIGRyaXZlciwgNCBwb3J0cywgSVJRIHNoYXJpbmcgZGlzYWJsZWQK TWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjIzMzg4OV0gbG9v cDogbW9kdWxlIGxvYWRlZApNYXIgIDUgMDE6MzE6MjAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBb ICAgIDAuMjM5NjYxXSBibGtmcm9udDogeHZkYTE6IGJhcnJpZXIgb3IgZmx1c2g6IGRpc2FibGVk Ck1hciAgNSAwMTozMToyMCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4yNDY4MTFdIGJs a2Zyb250OiB4dmRiOiBiYXJyaWVyIG9yIGZsdXNoOiBkaXNhYmxlZApNYXIgIDUgMDE6MzE6MjAg aXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMjU2NjgyXSAgeHZkYjogdW5rbm93biBwYXJ0 aXRpb24gdGFibGUKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAw LjI2MjgwNl0gU2V0dGluZyBjYXBhY2l0eSB0byA4ODA3MzIxNjAKTWFyICA1IDAxOjMxOjIwIGlw LTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjI2MjgxOF0geHZkYjogZGV0ZWN0ZWQgY2FwYWNp dHkgY2hhbmdlIGZyb20gMCB0byA0NTA5MzQ4NjU5MjAKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0w LTEwMC0xIGtlcm5lbDogWyAgICAwLjI2ODI1N10gYmxrZnJvbnQ6IHh2ZGM6IGJhcnJpZXIgb3Ig Zmx1c2g6IGRpc2FibGVkCk1hciAgNSAwMTozMToyMCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsg ICAgMC4yNjk1NDNdIEluaXRpYWxpc2luZyBYZW4gdmlydHVhbCBldGhlcm5ldCBkcml2ZXIuCk1h ciAgNSAwMTozMToyMCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4yNzE3NjFdIGk4MDQy OiBQTlA6IE5vIFBTLzIgY29udHJvbGxlciBmb3VuZC4gUHJvYmluZyBwb3J0cyBkaXJlY3RseS4K TWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjI3MjkwM10gbW91 c2VkZXY6IFBTLzIgbW91c2UgZGV2aWNlIGNvbW1vbiBmb3IgYWxsIG1pY2UKTWFyICA1IDAxOjMx OjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjI3MzExN10gVENQIGN1YmljIHJlZ2lz dGVyZWQKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjI3MzEy NF0gTkVUOiBSZWdpc3RlcmVkIHByb3RvY29sIGZhbWlseSAxNwpNYXIgIDUgMDE6MzE6MjAgaXAt MTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMjczMTM2XSBSZWdpc3RlcmluZyB0aGUgZG5zX3Jl c29sdmVyIGtleSB0eXBlCk1hciAgNSAwMTozMToyMCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsg ICAgMC4yNzM0MTRdIHJlZ2lzdGVyZWQgdGFza3N0YXRzIHZlcnNpb24gMQpNYXIgIDUgMDE6MzE6 MjAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMjc4MjIyXSAgeHZkYzogdW5rbm93biBw YXJ0aXRpb24gdGFibGUKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAg ICAwLjI3ODUyMV0gU2V0dGluZyBjYXBhY2l0eSB0byA4ODA3MzIxNjAKTWFyICA1IDAxOjMxOjIw IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjI3ODUyOV0geHZkYzogZGV0ZWN0ZWQgY2Fw YWNpdHkgY2hhbmdlIGZyb20gMCB0byA0NTA5MzQ4NjU5MjAKTWFyICA1IDAxOjMxOjIwIGlwLTEw MC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjI3OTA5MF0gYmxrZnJvbnQ6IHh2ZGY6IGJhcnJpZXIg b3IgZmx1c2g6IGRpc2FibGVkCk1hciAgNSAwMTozMToyMCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6 IFsgICAgMC4yODA2OTRdICB4dmRmOiB1bmtub3duIHBhcnRpdGlvbiB0YWJsZQpNYXIgIDUgMDE6 MzE6MjAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMjgwOTQ2XSBTZXR0aW5nIGNhcGFj aXR5IHRvIDEwNzM3NDE4MjQKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDog WyAgICAwLjI4MDk1NV0geHZkZjogZGV0ZWN0ZWQgY2FwYWNpdHkgY2hhbmdlIGZyb20gMCB0byA1 NDk3NTU4MTM4ODgKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAw LjI4MTU3MF0gYmxrZnJvbnQ6IHh2ZGc6IGJhcnJpZXIgb3IgZmx1c2g6IGRpc2FibGVkCk1hciAg NSAwMTozMToyMCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4yODMyMzVdICB4dmRnOiB1 bmtub3duIHBhcnRpdGlvbiB0YWJsZQpNYXIgIDUgMDE6MzE6MjAgaXAtMTAwLTAtMTAwLTEga2Vy bmVsOiBbICAgIDAuMjgzNDY2XSBTZXR0aW5nIGNhcGFjaXR5IHRvIDEwNzM3NDE4MjQKTWFyICA1 IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjI4MzQ3NF0geHZkZzogZGV0 ZWN0ZWQgY2FwYWNpdHkgY2hhbmdlIGZyb20gMCB0byA1NDk3NTU4MTM4ODgKTWFyICA1IDAxOjMx OjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjI4NDA2NV0gYmxrZnJvbnQ6IHh2ZGg6 IGJhcnJpZXIgb3IgZmx1c2g6IGRpc2FibGVkCk1hciAgNSAwMTozMToyMCBpcC0xMDAtMC0xMDAt MSBrZXJuZWw6IFsgICAgMC4yODU4NTRdICB4dmRoOiB1bmtub3duIHBhcnRpdGlvbiB0YWJsZQpN YXIgIDUgMDE6MzE6MjAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMjg2MDc5XSBTZXR0 aW5nIGNhcGFjaXR5IHRvIDEwNzM3NDE4MjQKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0x IGtlcm5lbDogWyAgICAwLjI4NjA4OF0geHZkaDogZGV0ZWN0ZWQgY2FwYWNpdHkgY2hhbmdlIGZy b20gMCB0byA1NDk3NTU4MTM4ODgKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5l bDogWyAgICAwLjI4NjY0OF0gYmxrZnJvbnQ6IHh2ZGk6IGJhcnJpZXIgb3IgZmx1c2g6IGRpc2Fi bGVkCk1hciAgNSAwMTozMToyMCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4yODgyNzhd ICB4dmRpOiB1bmtub3duIHBhcnRpdGlvbiB0YWJsZQpNYXIgIDUgMDE6MzE6MjAgaXAtMTAwLTAt MTAwLTEga2VybmVsOiBbICAgIDAuMjg4NTA3XSBTZXR0aW5nIGNhcGFjaXR5IHRvIDEwNzM3NDE4 MjQKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjI4ODUxNl0g eHZkaTogZGV0ZWN0ZWQgY2FwYWNpdHkgY2hhbmdlIGZyb20gMCB0byA1NDk3NTU4MTM4ODgKTWFy ICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjI4OTA5M10gYmxrZnJv bnQ6IHh2ZGo6IGJhcnJpZXIgb3IgZmx1c2g6IGRpc2FibGVkCk1hciAgNSAwMTozMToyMCBpcC0x MDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4yOTA3NDRdICB4dmRqOiB1bmtub3duIHBhcnRpdGlv biB0YWJsZQpNYXIgIDUgMDE6MzE6MjAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMjkw OTc2XSBTZXR0aW5nIGNhcGFjaXR5IHRvIDEwNzM3NDE4MjQKTWFyICA1IDAxOjMxOjIwIGlwLTEw MC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjI5MDk4NV0geHZkajogZGV0ZWN0ZWQgY2FwYWNpdHkg Y2hhbmdlIGZyb20gMCB0byA1NDk3NTU4MTM4ODgKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEw MC0xIGtlcm5lbDogWyAgICAwLjI5MTU1MV0gYmxrZnJvbnQ6IHh2ZGs6IGJhcnJpZXIgb3IgZmx1 c2g6IGRpc2FibGVkCk1hciAgNSAwMTozMToyMCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAg MC4yOTMyNDldICB4dmRrOiB1bmtub3duIHBhcnRpdGlvbiB0YWJsZQpNYXIgIDUgMDE6MzE6MjAg aXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMjkzNDc1XSBTZXR0aW5nIGNhcGFjaXR5IHRv IDEwNzM3NDE4MjQKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAw LjI5MzQ4NF0geHZkazogZGV0ZWN0ZWQgY2FwYWNpdHkgY2hhbmdlIGZyb20gMCB0byA1NDk3NTU4 MTM4ODgKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjI5NDA4 MF0gYmxrZnJvbnQ6IHh2ZGw6IGJhcnJpZXIgb3IgZmx1c2g6IGRpc2FibGVkCk1hciAgNSAwMToz MToyMCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC4yOTU3NjBdICB4dmRsOiB1bmtub3du IHBhcnRpdGlvbiB0YWJsZQpNYXIgIDUgMDE6MzE6MjAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBb ICAgIDAuMjk1OTkyXSBTZXR0aW5nIGNhcGFjaXR5IHRvIDEwNzM3NDE4MjQKTWFyICA1IDAxOjMx OjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjI5NjAwMV0geHZkbDogZGV0ZWN0ZWQg Y2FwYWNpdHkgY2hhbmdlIGZyb20gMCB0byA1NDk3NTU4MTM4ODgKTWFyICA1IDAxOjMxOjIwIGlw LTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjM0MTU2NF0gYmxrZnJvbnQ6IHh2ZG06IGJhcnJp ZXIgb3IgZmx1c2g6IGRpc2FibGVkCk1hciAgNSAwMTozMToyMCBpcC0xMDAtMC0xMDAtMSBrZXJu ZWw6IFsgICAgMC4zNDM1MzddICB4dmRtOiB1bmtub3duIHBhcnRpdGlvbiB0YWJsZQpNYXIgIDUg MDE6MzE6MjAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMzQzODExXSBTZXR0aW5nIGNh cGFjaXR5IHRvIDEwNzM3NDE4MjQKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5l bDogWyAgICAwLjM0MzgyMF0geHZkbTogZGV0ZWN0ZWQgY2FwYWNpdHkgY2hhbmdlIGZyb20gMCB0 byA1NDk3NTU4MTM4ODgKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAg ICAwLjM3NjAzNl0gWEVOQlVTOiBEZXZpY2Ugd2l0aCBubyBkcml2ZXI6IGRldmljZS9jb25zb2xl LzAKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjM3NjQ5N10g RnJlZWluZyB1bnVzZWQga2VybmVsIG1lbW9yeTogNTY0ayBmcmVlZApNYXIgIDUgMDE6MzE6MjAg aXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuMzc2NjY3XSBXcml0ZSBwcm90ZWN0aW5nIHRo ZSBrZXJuZWwgcmVhZC1vbmx5IGRhdGE6IDYxNDRrCk1hciAgNSAwMTozMToyMCBpcC0xMDAtMC0x MDAtMSBrZXJuZWw6IFsgICAgMC4zNzkyMTVdIEZyZWVpbmcgdW51c2VkIGtlcm5lbCBtZW1vcnk6 IDI0OGsgZnJlZWQKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAw LjM3OTQ5OF0gRnJlZWluZyB1bnVzZWQga2VybmVsIG1lbW9yeTogNDc2ayBmcmVlZApNYXIgIDUg MDE6MzE6MjAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDAuNDI0NjQwXSBkZXZpY2UtbWFw cGVyOiB1ZXZlbnQ6IHZlcnNpb24gMS4wLjMKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0x IGtlcm5lbDogWyAgICAwLjQyNDkzOF0gZGV2aWNlLW1hcHBlcjogaW9jdGw6IDQuMjIuMC1pb2N0 bCAoMjAxMS0xMC0xOSkgaW5pdGlhbGlzZWQ6IGRtLWRldmVsQHJlZGhhdC5jb20KTWFyICA1IDAx OjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjU0NjE2N10gbWQ6IGJpbmQ8eHZk aD4KTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjU1MDUzNV0g bWQ6IGJpbmQ8eHZkZz4KTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAg ICAwLjU1NTE4Ml0gbWQ6IGJpbmQ8eHZkZj4KTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0x IGtlcm5lbDogWyAgICAwLjU2NDI0Ml0gbWQ6IGJpbmQ8eHZkbD4KTWFyICA1IDAxOjMxOjIwIGlw LTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjYzNDg3OF0gbWQ6IGJpbmQ8eHZkaj4KTWFyICA1 IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjY0Mzg1NV0gbWQ6IGJpbmQ8 eHZkaz4KTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjY1Mjc4 Ml0gbWQ6IGJpbmQ8eHZkaT4KTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDog WyAgICAwLjY2MjEwNV0gbWQ6IGJpbmQ8eHZkbT4KTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEw MC0xIGtlcm5lbDogWyAgICAwLjY3MDA2Nl0gbWQ6IHJhaWQwIHBlcnNvbmFsaXR5IHJlZ2lzdGVy ZWQgZm9yIGxldmVsIDAKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAg ICAwLjY3MDI2OF0gYmlvOiBjcmVhdGUgc2xhYiA8YmlvLTE+IGF0IDEKTWFyICA1IDAxOjMxOjIw IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAwLjY3MDI4M10gbWQvcmFpZDA6bWQxMjc6IG1k X3NpemUgaXMgODU4OTkxODIwOCBzZWN0b3JzLgpNYXIgIDUgMDE6MzE6MjAgaXAtMTAwLTAtMTAw LTEga2VybmVsOiBbICAgIDAuNjcwMjkyXSBtZDogUkFJRDAgY29uZmlndXJhdGlvbiBmb3IgbWQx MjcgLSAxIHpvbmUKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAw LjY3MDI5OF0gbWQ6IHpvbmUwPVt4dmRmL3h2ZGcveHZkaC94dmRpL3h2ZGoveHZkay94dmRsL3h2 ZG1dCk1hciAgNSAwMTozMToyMCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMC42NzAzMTJd ICAgICAgIHpvbmUtb2Zmc2V0PSAgICAgICAgIDBLQiwgZGV2aWNlLW9mZnNldD0gICAgICAgICAw S0IsIHNpemU9NDI5NDk1OTEwNEtCCk1hciAgNSAwMTozMToyMCBpcC0xMDAtMC0xMDAtMSBrZXJu ZWw6IFsgICAgMC42NzAzMThdIApNYXIgIDUgMDE6MzE6MjAgaXAtMTAwLTAtMTAwLTEga2VybmVs OiBbICAgIDAuNjcwMzM5XSBtZDEyNzogZGV0ZWN0ZWQgY2FwYWNpdHkgY2hhbmdlIGZyb20gMCB0 byA0Mzk4MDM4MTIyNDk2Ck1hciAgNSAwMTozMToyMCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsg ICAgMC42NzI3MTFdICBtZDEyNzogdW5rbm93biBwYXJ0aXRpb24gdGFibGUKTWFyICA1IDAxOjMx OjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAxLjAzMjE0N10gRVhUNC1mcyAoeHZkYTEp OiBtb3VudGVkIGZpbGVzeXN0ZW0gd2l0aCBvcmRlcmVkIGRhdGEgbW9kZS4gT3B0czogKG51bGwp Ck1hciAgNSAwMTozMToyMCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgICAgMS4wNjQ1NjFdIGRy YWN1dDogUmVtb3VudGluZyAvZGV2L2Rpc2svYnktbGFiZWwvXHgyZiB3aXRoIC1vIG5vYXRpbWUs cm8KTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICAxLjA5MzAwN10g RVhUNC1mcyAoeHZkYTEpOiBtb3VudGVkIGZpbGVzeXN0ZW0gd2l0aCBvcmRlcmVkIGRhdGEgbW9k ZS4gT3B0czogKG51bGwpCk1hciAgNSAwMTozMToyMCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsg ICAgMS4wOTc2NDFdIGRyYWN1dDogTW91bnRlZCByb290IGZpbGVzeXN0ZW0gL2Rldi94dmRhMQpN YXIgIDUgMDE6MzE6MjAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAgIDEuMjAxNTgzXSBkcmFj dXQ6IExvYWRpbmcgU0VMaW51eCBwb2xpY3kKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0x IGtlcm5lbDogWyAgICAxLjM2NzkyMF0gZHJhY3V0OiAvc2Jpbi9sb2FkX3BvbGljeTogQ2FuJ3Qg bG9hZCBwb2xpY3k6IE5vIHN1Y2ggZGV2aWNlCk1hciAgNSAwMTozMToyMCBpcC0xMDAtMC0xMDAt MSBrZXJuZWw6IFsgICAgMS40NjE5ODRdIGRyYWN1dDogU3dpdGNoaW5nIHJvb3QKTWFyICA1IDAx OjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICA2Ljc1NzYzMV0gbmZfY29ubnRyYWNr IHZlcnNpb24gMC41LjAgKDE2Mzg0IGJ1Y2tldHMsIDY1NTM2IG1heCkKTWFyICA1IDAxOjMxOjIw IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICA2Ljg4MDAzOF0gU0NTSSBzdWJzeXN0ZW0gaW5p dGlhbGl6ZWQKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICA3LjMy ODUxMV0gRVhUNC1mcyAoeHZkYTEpOiByZS1tb3VudGVkLiBPcHRzOiAobnVsbCkKTWFyICA1IDAx OjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICA3LjU1NDQwN10ga2pvdXJuYWxkIHN0 YXJ0aW5nLiAgQ29tbWl0IGludGVydmFsIDUgc2Vjb25kcwpNYXIgIDUgMDE6MzE6MjAgaXAtMTAw LTAtMTAwLTEga2VybmVsOiBbICAgIDcuNTU0NzU0XSBFWFQzLWZzICh4dmRiKTogdXNpbmcgaW50 ZXJuYWwgam91cm5hbApNYXIgIDUgMDE6MzE6MjAgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAg IDcuNTU0NzYzXSBFWFQzLWZzICh4dmRiKTogbW91bnRlZCBmaWxlc3lzdGVtIHdpdGggb3JkZXJl ZCBkYXRhIG1vZGUKTWFyICA1IDAxOjMxOjIwIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgICA4 LjQ1NTEyMV0gTkVUOiBSZWdpc3RlcmVkIHByb3RvY29sIGZhbWlseSAxMApNYXIgIDUgMDE6MzM6 MzQgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAxNDUuMjQ0MjQwXSBtZDEyNzogZGV0ZWN0ZWQg Y2FwYWNpdHkgY2hhbmdlIGZyb20gNDM5ODAzODEyMjQ5NiB0byAwCk1hciAgNSAwMTozMzozNCBp cC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgIDE0NS4yNDQyNTddIG1kOiBtZDEyNyBzdG9wcGVkLgpN YXIgIDUgMDE6MzM6MzQgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAxNDUuMjQ0MjY1XSBtZDog dW5iaW5kPHh2ZG0+Ck1hciAgNSAwMTozMzozNCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgIDE0 NS4yNjAwNjJdIG1kOiBleHBvcnRfcmRldih4dmRtKQpNYXIgIDUgMDE6MzM6MzQgaXAtMTAwLTAt MTAwLTEga2VybmVsOiBbICAxNDUuMjYwMTk5XSBtZDogdW5iaW5kPHh2ZGk+Ck1hciAgNSAwMToz MzozNCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgIDE0NS4yNzIwNzRdIG1kOiBleHBvcnRfcmRl dih4dmRpKQpNYXIgIDUgMDE6MzM6MzQgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAxNDUuMjcy MTMyXSBtZDogdW5iaW5kPHh2ZGs+Ck1hciAgNSAwMTozMzozNCBpcC0xMDAtMC0xMDAtMSBrZXJu ZWw6IFsgIDE0NS4yODQwNjFdIG1kOiBleHBvcnRfcmRldih4dmRrKQpNYXIgIDUgMDE6MzM6MzQg aXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAxNDUuMjg0MTIxXSBtZDogdW5iaW5kPHh2ZGo+Ck1h ciAgNSAwMTozMzozNCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgIDE0NS4zNDAwODVdIG1kOiBl eHBvcnRfcmRldih4dmRqKQpNYXIgIDUgMDE6MzM6MzQgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBb ICAxNDUuMzQwMzc0XSBtZDogdW5iaW5kPHh2ZGw+Ck1hciAgNSAwMTozMzozNCBpcC0xMDAtMC0x MDAtMSBrZXJuZWw6IFsgIDE0NS4zNjgwNzVdIG1kOiBleHBvcnRfcmRldih4dmRsKQpNYXIgIDUg MDE6MzM6MzQgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAxNDUuMzY4MTQwXSBtZDogdW5iaW5k PHh2ZGY+Ck1hciAgNSAwMTozMzozNCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgIDE0NS4zODAw NjBdIG1kOiBleHBvcnRfcmRldih4dmRmKQpNYXIgIDUgMDE6MzM6MzQgaXAtMTAwLTAtMTAwLTEg a2VybmVsOiBbICAxNDUuMzgwMTI4XSBtZDogdW5iaW5kPHh2ZGc+Ck1hciAgNSAwMTozMzozNCBp cC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgIDE0NS40MDgwNTldIG1kOiBleHBvcnRfcmRldih4dmRn KQpNYXIgIDUgMDE6MzM6MzQgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAxNDUuNDA4MTIyXSBt ZDogdW5iaW5kPHh2ZGg+Ck1hciAgNSAwMTozMzozNCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsg IDE0NS40NDAwNThdIG1kOiBleHBvcnRfcmRldih4dmRoKQpNYXIgIDUgMDE6MzM6MzQgaXAtMTAw LTAtMTAwLTEga2VybmVsOiBbICAxNDUuNDY2MjcyXSBtZDogbWQwIHN0b3BwZWQuCk1hciAgNSAw MTozMzozNCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgIDE0NS40NzQxNTRdIG1kOiBiaW5kPHh2 ZGc+Ck1hciAgNSAwMTozMzozNCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgIDE0NS40NzUyMDdd IG1kOiBiaW5kPHh2ZGg+Ck1hciAgNSAwMTozMzozNCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsg IDE0NS40NzYxMTVdIG1kOiBiaW5kPHh2ZGk+Ck1hciAgNSAwMTozMzozNCBpcC0xMDAtMC0xMDAt MSBrZXJuZWw6IFsgIDE0NS40NzY5OTNdIG1kOiBiaW5kPHh2ZGo+Ck1hciAgNSAwMTozMzozNCBp cC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgIDE0NS40NzgxNDhdIG1kOiBiaW5kPHh2ZGs+Ck1hciAg NSAwMTozMzozNCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgIDE0NS40Nzg5ODRdIG1kOiBiaW5k PHh2ZGw+Ck1hciAgNSAwMTozMzozNCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgIDE0NS40Nzk5 NzVdIG1kOiBiaW5kPHh2ZG0+Ck1hciAgNSAwMTozMzozNCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6 IFsgIDE0NS40ODA4MzddIG1kOiBiaW5kPHh2ZGY+Ck1hciAgNSAwMTozMzozNCBpcC0xMDAtMC0x MDAtMSBrZXJuZWw6IFsgIDE0NS40OTU2ODBdIG1kL3JhaWQwOm1kMDogbWRfc2l6ZSBpcyA4NTg5 OTE4MjA4IHNlY3RvcnMuCk1hciAgNSAwMTozMzozNCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsg IDE0NS40OTU2OTNdIG1kOiBSQUlEMCBjb25maWd1cmF0aW9uIGZvciBtZDAgLSAxIHpvbmUKTWFy ICA1IDAxOjMzOjM0IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgMTQ1LjQ5NTY5N10gbWQ6IHpv bmUwPVt4dmRmL3h2ZGcveHZkaC94dmRpL3h2ZGoveHZkay94dmRsL3h2ZG1dCk1hciAgNSAwMToz MzozNCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgIDE0NS40OTU3MDldICAgICAgIHpvbmUtb2Zm c2V0PSAgICAgICAgIDBLQiwgZGV2aWNlLW9mZnNldD0gICAgICAgICAwS0IsIHNpemU9NDI5NDk1 OTEwNEtCCk1hciAgNSAwMTozMzozNCBpcC0xMDAtMC0xMDAtMSBrZXJuZWw6IFsgIDE0NS40OTU3 MTVdIApNYXIgIDUgMDE6MzM6MzQgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAxNDUuNDk1NzQw XSBtZDA6IGRldGVjdGVkIGNhcGFjaXR5IGNoYW5nZSBmcm9tIDAgdG8gNDM5ODAzODEyMjQ5NgpN YXIgIDUgMDE6MzM6MzQgaXAtMTAwLTAtMTAwLTEga2VybmVsOiBbICAxNDUuNTE2NzM3XSAgbWQw OiB1bmtub3duIHBhcnRpdGlvbiB0YWJsZQpNYXIgIDUgMDE6MzM6MzQgaXAtMTAwLTAtMTAwLTEg a2VybmVsOiBbICAxNDUuNzg2ODg1XSBTR0kgWEZTIHdpdGggQUNMcywgc2VjdXJpdHkgYXR0cmli dXRlcywgcmVhbHRpbWUsIGxhcmdlIGJsb2NrL2lub2RlIG51bWJlcnMsIG5vIGRlYnVnIGVuYWJs ZWQKTWFyICA1IDAxOjMzOjM0IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgMTQ1Ljc4NzI5M10g U0dJIFhGUyBRdW90YSBNYW5hZ2VtZW50IHN1YnN5c3RlbQpNYXIgIDUgMDE6MzM6MzQgaXAtMTAw LTAtMTAwLTEga2VybmVsOiBbICAxNDUuNzg5NDQyXSBYRlMgKG1kMCk6IE1vdW50aW5nIEZpbGVz eXN0ZW0KTWFyICA1IDAxOjMzOjM1IGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgMTQ2LjI3NDQ2 NF0gWEZTIChtZDApOiBTdGFydGluZyByZWNvdmVyeSAobG9nZGV2OiBpbnRlcm5hbCkKTWFyICA1 IDAxOjMzOjQyIGlwLTEwMC0wLTEwMC0xIGtlcm5lbDogWyAgMTUzLjI3NDY2N10gWEZTIChtZDAp OiBFbmRpbmcgcmVjb3ZlcnkgKGxvZ2RldjogaW50ZXJuYWwpCg== --14dae9340de1e2fa7104d73d1633-- From info@labsend.net Wed Mar 6 04:12:17 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: **** X-Spam-Status: No, score=4.4 required=5.0 tests=HTML_FONT_SIZE_LARGE, HTML_IMAGE_RATIO_02,HTML_MESSAGE,MIME_HTML_ONLY,MIME_QP_LONG_LINE, T_KHOP_FOREIGN_CLICK autolearn=no version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 735527FB0 for ; Wed, 6 Mar 2013 04:12:16 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay3.corp.sgi.com (Postfix) with ESMTP id EA2E8AC001 for ; Wed, 6 Mar 2013 02:12:12 -0800 (PST) X-ASG-Debug-ID: 1362564730-04cb6c2b021eeb70001-NocioJ Received: from labsend.com (184-106-136-180.labsend.net [184.106.136.180]) by cuda.sgi.com with ESMTP id bwA7HKcZ32owxC0v (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO) for ; Wed, 06 Mar 2013 02:12:10 -0800 (PST) X-Barracuda-Envelope-From: info@labsend.net X-Barracuda-Apparent-Source-IP: 184.106.136.180 Received: from transito (184-106-237-74.static.cloud-ips.com [184.106.237.74]) (using TLSv1 with cipher ADH-AES256-SHA (256/256 bits)) (No client certificate requested) by labsend.com (Postfix) with ESMTPS id D0AFB914A3 for ; Wed, 6 Mar 2013 11:09:05 +0100 (CET) Received: from nas-2A-E3-B6 (host31-177-static.9-188-b.business.telecomitalia.it [188.9.177.31]) (Authenticated sender: newsletter) by transito (Postfix) with ESMTPA id 127DC60854 for ; Wed, 6 Mar 2013 11:32:36 +0100 (CET) Received: from default (unknown [192.168.1.5]) by nas-2A-E3-B6 (Postfix) with ESMTP id 4D8A6CE7 for ; Wed, 6 Mar 2013 11:12:03 +0100 (CET) MIME-Version: 1.0 From: "Cucine Noventa" To: xfs@oss.sgi.com Date: 6 Mar 2013 11:12:07 +0100 Subject: L'Arredamento per la tua casa! Content-Type: text/html; charset=us-ascii X-ASG-Orig-Subj: L'Arredamento per la tua casa! Content-Transfer-Encoding: quoted-printable X-Antivirus: avast! (VPS 130305-1, 05/03/2013), Outbound message X-Antivirus-Status: Clean Message-Id: <20130306101203.4D8A6CE7@nas-2A-E3-B6> X-Barracuda-Connect: 184-106-136-180.labsend.net[184.106.136.180] X-Barracuda-Start-Time: 1362564730 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 1.97 X-Barracuda-Spam-Status: No, SCORE=1.97 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC5_MJ1963, HTML_FONT_SIZE_LARGE, HTML_IMAGE_RATIO_02, HTML_MESSAGE, MIME_HTML_ONLY, MIME_QP_LONG_LINE, MIME_QP_LONG_LINE_2, RDNS_DYNAMIC X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124404 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 HTML_FONT_SIZE_LARGE BODY: HTML font size is large 0.00 MIME_HTML_ONLY BODY: Message only has text/html MIME parts 0.55 HTML_IMAGE_RATIO_02 BODY: HTML has a low ratio of text to image area 0.00 HTML_MESSAGE BODY: HTML included in message 0.00 MIME_QP_LONG_LINE RAW: Quoted-printable line longer than 76 chars 0.82 MIME_QP_LONG_LINE_2 RAW: Quoted-printable line longer than 76 chars 0.10 RDNS_DYNAMIC Delivered to trusted network by host with dynamic-looking rDNS 0.50 BSF_SC5_MJ1963 Custom Rule MJ1963 =0D=0A=0D=0A=0D=0A=0D=0A=0D=0A=0D=0A =0D=0A= =0D=0A =0D=0A =0D=0A  =0D=0A =0D=0A = =0D=0A =0D=0A =0D=0A =0D=0A =
Se non visualizzi correttamente= le =0D=0A immagini = =0D=0A clicca qui.
=0D=0A =0D=0A= =0D=0A =0D=0A = =0D=0A =0D=0A =0D=0A= =0D=0A =0D=0A= =0D=0A =0D=0A =0D=0A =0D=0A= =0D=0A =0D=0A = =0D=0A =0D=0A =0D=0A =0D=0A
=0D=0A = =0D=0A =0D=0A =0D=0A =0D=0A = =0D=0A =0D=0A =0D=0A =0D=0A = =0D=0A = =0D=0A =0D=0A =0D=0A =0D=0A=
=0D=0A =0D=0A= =0D=0A =0D=0A = =0D=0A
=0D=0A =0D=0A =0D=0A =0D=0A =0D=0A=
=0D=0A =0D=0A =0D=0A =0D=0A = =0D=0A =0D=0A = =0D=0A
= =0D=0A=0D=0A=0D=0A = =0D=0A =0D=0A = =0D=0A =0D=0A =0D=0A =0D=0A = =0D=0A
=0D=0A =0D=0A Dalla Fabbrica,
=0D=0A=

=0D=0A =0D=0A    =0D=0A= =0D=0A = direttamente a casa Vostra!

=0D=0A

 

= =0D=0A =0D=0A= =0D=0A =0D=0A = =0D=0A =0D=0A = =0D=0A =0D=0A = =0D=0A =0D=0A = =0D=0A =0D=0A
   
 Cucine Noventa S.r.l
= =0D=0A Strada del Mobile 10
=0D=0A33087= Pasiano (Pn)
=0D=0ATel. 0434 625290
 
=0D=0A=    = =0D=0A www.cucinenoventa.com
=0D=0A
=0D=0A = =0D=0A =0D=0A = =0D=0A =0D=0A =0D=0A =0D=0A =0D=0A = =0D=0A =0D=0A = =0D=0A =0D=0A
=0D=0A

=0D=0A NON RISPONDERE a= questa Newsletter perche'  la comunicazione non =0D=0A verra' = letta, ma invia =0D=0A a: info@cucinenoventa.com

=0D=0A = =0D=0A
=0D=0A =0D=0A 3D"cn1"
=0D=0A  
=0D=0A
=0D=0A
=0D=0A =0D=0A =0D=0A= =0D=0A =0D=0A = =0D=0A =0D=0A =0D=0A = =0D=0A =0D=0A =0D=0A =
=0D=0A   =0D=0A =0D=0A =0D=0A Piu' valore= alla tua casa!

 

=0D=0A = =0D=0A =0D=0A = =0D=0A =0D=0A =0D=0A=
=0D=0A

= =0D=0A - Mobili =0D=0A = prodotti in Italia
=0D=0A  - Un professionista al tuo fianco
= =0D=0A - I migliori marchi Nazionali
=0D=0A -= Prezzi tra i piu' bassi del =0D=0A mercato
=0D=0A  -= Trasporto e montaggio gratuiti
=0D=0A - 10 anni di garanzia
= =0D=0A - Pagamenti rateali
=0D=0A - Zero sorprese

 
=0D=0A
=0D=0A  
=0D=0A
=0D=0A 3D"cn1"
=0D=0A =0D=0A =0D=0A =0D=0A = =0D=0A =0D=0A = =0D=0A =0D=0A = =0D=0A =0D=0A =0D=0A = =0D=0A =0D=0A = =0D=0A = =0D=0A =0D=0A = =0D=0A =0D=0A =0D=0A = =0D=0A =0D=0A = =0D=0A = =0D=0A
= =0D=0A=0D=0A=0D=0A= =0D=0A =0D=0A=0D=0A=

=0D=0A= =0D=0A

  
=0D=0A= =0D=0A=0D=0A=0D=0A
  
=0D=0A= =0D=0A=0D=0A

=0D=0A= =0D=0A

=0D=0A
=0D=0A
3D"1"
=0D=0A =0D=0A =0D=0A= =0D=0A =0D=0A = =0D=0A =0D=0A = =0D=0A =0D=0A =0D=0A = =0D=0A =0D=0A =0D=0A =0D=0A = =0D=0A =0D=0A= =0D=0A
=0D=0A =0D=0A
=0D=0A =0D=0A =0D=0A = =0D=0A =0D=0A =0D=0A= =0D=0A = =0D=0A =0D=0A =0D=0A= =0D=0A = =0D=0A
=0D=0A = =0D=0A =0D=0A =0D=0A =0D=0A =0D=0A =0D=0A =0D=0A
=0D=0ASamoa
=0D=0AKios
=0D=0AMoretti Compact
= =0D=0ASanta Lucia
=0D=0ATomasella
=0D=0AArros Group
=0D=0AMistral
= =0D=0AColombini
=0D=0AAlberta
=0D=0ADitre Italia
=0D=0AFelis= Felix
=0D=0AEurosedia
= =0D=0AInfiniti
=0D=0AIngenia
=0D=0AEurobagni
= =0D=0AEdmo
= =0D=0A
=0D=0A =0D=0A
=0D=0A =0D=0A
=0D=0A


=0D=0ASCONTO 45% =0D=0A- PAGAMENTO 12= MESI senza interessi
=0D=0A
=0D=0A

=0D=0A
=0D=0A =0D=0A
=0D=0A =0D=0A =0D=0A = =0D=0A =0D=0A=
=0D=0A = =0D=0A =0D=0A =0D=0A =0D=0A =0D=0A= =0D=0A = =0D=0A
=0D=0A = =0D=0A = =0D=0A =0D=0A
=0D=0A
=0D=0A
=0D=0A =0D=0A =0D=0A =0D=0A =0D=0A = =0D=0A =0D=0A= =0D=0A
= =0D=0AIdea group
=0D=0ACalligaris
= =0D=0AGruppo Santarossa
=0D=0AZanette
=0D=0APavanello
=0D=0ALa= Primavera
=0D=0AEuropeo
=0D=0AMD House
=0D=0ASan Giacomo
= =0D=0AMorfeus
=0D=0AMab
=0D=0AMaretto Marflex
=0D=0ARosini
= =0D=0AArmobil
=0D=0ARossetto Arred.ti
=0D=0ABirex
=0D=0A Pintdecor
= =0D=0APoletti Design
=0D=0ACorazzin
=0D=0ADhesja
=0D=0ADoimo Idea
= =0D=0ADomitalia
=0D=0ARCR Bagno
=0D=0ARoberti Rattan
=0D=0A
=0D=0A  
=0D=0A

= =0D=0A =0D=0A= ...e molto altro ancora!

=0D=0A  
=0D=0A

200

= =0D=0A
=0D=0A =0D=0A =0D=0A = =0D=0A =0D=0A =0D=0A =0D=0A =0D=0A =0D=0A= =0D=0A = =0D=0A =0D=0A =0D=0A

=0D=0A =0D=0A Gentile utente, il suo= indirizzo e-mail proviene da =0D=0A elenchi di distribuzione ai quali= e' stata data esplicita autorizzazione =0D=0A all'invio di comunicazioni= promozionali, richieste di iscrizione a =0D=0A mailing =0D=0A list e/o newsletter.= Per rimuovere i suoi dati personali clicchi= qui.

=0D=0A = =0D=0A=0D=0A=0D=0A=0D=0A=0D=0A From rwheeler@redhat.com Wed Mar 6 06:59:40 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id AA6648004 for ; Wed, 6 Mar 2013 06:59:40 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id 915EF304048 for ; Wed, 6 Mar 2013 04:59:40 -0800 (PST) X-ASG-Debug-ID: 1362574779-04cbb07dbd202880001-NocioJ Received: from mx1.redhat.com (mx1.redhat.com [209.132.183.28]) by cuda.sgi.com with ESMTP id MwEtDyaiu7zR6ZPW for ; Wed, 06 Mar 2013 04:59:39 -0800 (PST) X-Barracuda-Envelope-From: rwheeler@redhat.com X-Barracuda-Apparent-Source-IP: 209.132.183.28 X-ASG-Whitelist: Client Received: from int-mx12.intmail.prod.int.phx2.redhat.com (int-mx12.intmail.prod.int.phx2.redhat.com [10.5.11.25]) by mx1.redhat.com (8.14.4/8.14.4) with ESMTP id r26Cxdb7001740 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=OK); Wed, 6 Mar 2013 07:59:39 -0500 Received: from tunkums.home (ovpn-112-33.phx2.redhat.com [10.3.112.33]) by int-mx12.intmail.prod.int.phx2.redhat.com (8.14.4/8.14.4) with ESMTP id r26CxbV7007903; Wed, 6 Mar 2013 07:59:38 -0500 Message-ID: <51373DB8.2020707@redhat.com> Date: Wed, 06 Mar 2013 07:59:36 -0500 From: Ric Wheeler User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:17.0) Gecko/20130219 Thunderbird/17.0.3 MIME-Version: 1.0 To: Shrinath M CC: xfs@oss.sgi.com, Sabyasachi Ruj , Vivek Goel Subject: Re: XFS filesystem on EC2 instance corrupts and shuts down References: X-ASG-Orig-Subj: Re: XFS filesystem on EC2 instance corrupts and shuts down In-Reply-To: Content-Type: text/plain; charset=ISO-8859-1; format=flowed Content-Transfer-Encoding: 7bit X-Scanned-By: MIMEDefang 2.68 on 10.5.11.25 X-Barracuda-Connect: mx1.redhat.com[209.132.183.28] X-Barracuda-Start-Time: 1362574779 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 On 03/06/2013 03:07 AM, Shrinath M wrote: > We are experiencing a strange XFS corruption issue. If we look in > /var/log/messages, it simply says - > > Mar 5 01:14:33 ip-100-0-100-1 kernel: [14139930.248619] XFS (md0): > Corruption detected. Unmount and run xfs_repair > > It shuts down the filesystem after this. On rebooting, it calls xfs_repair > automatically and everything comes back to normal. > We have had 2 such occurrences till now, I am attaching the relevant parts of > /var/log/messages here, assuming someone can enlighten me on whats going wrong. > > Machine details are as follows - > > We are using Amazon AMI version: Amazon Linux AMI release 2012.09 We are > running 8 EBS volumes of 512 MB each, in RAID 0 Array. $~: uname -a Linux > ip-100-0-100-1 3.2.34-55.46.amzn1.x86_64 #1 SMP Tue Nov 20 10:06:15 UTC 2012 > x86_64 x86_64 x86_64 GNU/Linux > > > Ask me if anyone wants any more details > I think that you would need to verify that the Amazon storage is not throwing errors - do your logs show IO errors or issues before XFS hits an issue? Thanks! Ric From rjohnston@sgi.com Wed Mar 6 07:02:55 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 5340F8004 for ; Wed, 6 Mar 2013 07:02:55 -0600 (CST) Received: from xmail.sgi.com (pv-excas3-dc21-nlb.corp.sgi.com [137.38.102.207]) by relay2.corp.sgi.com (Postfix) with ESMTP id 881B5304059; Wed, 6 Mar 2013 05:02:51 -0800 (PST) Received: from [128.162.233.55] (128.162.233.55) by xmail.sgi.com (137.38.102.30) with Microsoft SMTP Server (TLS) id 14.2.318.1; Wed, 6 Mar 2013 07:02:50 -0600 Message-ID: <51373E85.9050408@sgi.com> Date: Wed, 6 Mar 2013 07:03:01 -0600 From: Rich Johnston User-Agent: Mozilla/5.0 (X11; Linux i686; rv:13.0) Gecko/20120615 Thunderbird/13.0.1 MIME-Version: 1.0 To: Eric Sandeen CC: Eric Sandeen , Stefan Behrens , linux-btrfs , xfs-oss Subject: Re: [PATCH] xfstests: Fix hang when mkfs.btrfs isn't present References: <512D1E3E.9050907@redhat.com> <513674B2.9030900@sandeen.net> In-Reply-To: <513674B2.9030900@sandeen.net> Content-Type: text/plain; charset="ISO-8859-1"; format=flowed Content-Transfer-Encoding: 7bit X-Originating-IP: [128.162.233.55] This patch has been committed. Thanks --Rich commit 52f4953ac4a377f9f7fc870d2a81f30c3e5d3c7f Author: Eric Sandeen Date: Tue Mar 5 22:41:54 2013 +0000 xfstests: Fix hang when mkfs.btrfs isn't present My earlier patch (xfstests: handle new mkfs.btrfs -f option cleanly) had a flaw in that if set_prog_path mkfs.btrfs returns nothing, the grep will hang. Test for that case to avoid it, and just return the empty string in that case. Reported-by: Rich Johnston Signed-off-by: Eric Sandeen Reviewed-by: Rich Johnston Signed-off-by: Rich Johnston From shrinath.m@webyog.com Wed Mar 6 07:03:32 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=HTML_FONT_FACE_BAD, HTML_MESSAGE,T_DKIM_INVALID autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 69FF28004 for ; Wed, 6 Mar 2013 07:03:32 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay3.corp.sgi.com (Postfix) with ESMTP id EF31BAC005 for ; Wed, 6 Mar 2013 05:03:28 -0800 (PST) X-ASG-Debug-ID: 1362575006-04cb6c2b011fa080001-NocioJ Received: from mail-la0-f45.google.com (mail-la0-f45.google.com [209.85.215.45]) by cuda.sgi.com with ESMTP id QxbwjZvEAzHfH3nE (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Wed, 06 Mar 2013 05:03:27 -0800 (PST) X-Barracuda-Envelope-From: shrinath.m@webyog.com X-Barracuda-Apparent-Source-IP: 209.85.215.45 Received: by mail-la0-f45.google.com with SMTP id er20so7365854lab.18 for ; Wed, 06 Mar 2013 05:03:25 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=webyog.com; s=google; h=x-received:mime-version:in-reply-to:references:from:date:message-id :subject:to:cc:content-type; bh=FfvZGBAkcL3KSpEK3ddLJb+MciYSS6MQVT/9TKM3slg=; b=E6ARuEFLV76DMuI1s9tHSb/LKqglMkdQrVjw4DEgpOyqf5d21A/nbTf/meKoS6iiV4 C1UtEMOv/wxZou04UKP4G6WFi4Sy9d3Munqdp39lFU8Yi2L0X/84R1wtu4gfkQU32KAs 5BAhhe6lKPPCfMMgwQUpl3UwoXx4mA9tASpQ0= X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=20120113; h=x-received:mime-version:in-reply-to:references:from:date:message-id :subject:to:cc:content-type:x-gm-message-state; bh=FfvZGBAkcL3KSpEK3ddLJb+MciYSS6MQVT/9TKM3slg=; b=nnzlHSAjaMQikHJoocnxiIxY4m3OwcXkM9GE7MLDpmRDu0c/LcJY/l5HTeMpHFvQpL hzkz2WsMK5h7Wy1N4hsvIXmZQYohtV+YskNidAQIDuDgrHNWtiQDEYsgqR86r9d3qv+s nW18kYimxcbMmmBzSzfUOd9Vka0l8FF4yJlcYNSgbh2js+Jv4sLfT5liVxGhxmqiULJU 8LWNi4/HvSZMvCYbQmw58ireAOGKfasq8ReNtHMgzH4+AW7SAURTaMjVD6AtlOLXqE02 1Tmvezpi6IOyC9cAQsoUdUGlGZgQN3pwCN2V+hBr4nxHhYXgHo8izlqilhLrTkutIY3p 2kSw== X-Received: by 10.112.9.231 with SMTP id d7mr7485814lbb.8.1362575005592; Wed, 06 Mar 2013 05:03:25 -0800 (PST) MIME-Version: 1.0 Received: by 10.112.7.42 with HTTP; Wed, 6 Mar 2013 05:03:05 -0800 (PST) In-Reply-To: <51373DB8.2020707@redhat.com> References: <51373DB8.2020707@redhat.com> From: Shrinath M Date: Wed, 6 Mar 2013 18:33:05 +0530 Message-ID: Subject: Re: XFS filesystem on EC2 instance corrupts and shuts down To: Ric Wheeler , Supratik Goswami X-ASG-Orig-Subj: Re: XFS filesystem on EC2 instance corrupts and shuts down Cc: xfs@oss.sgi.com, Sabyasachi Ruj , Vivek Goel Content-Type: multipart/alternative; boundary=e0cb4efe29d230549c04d7413786 X-Gm-Message-State: ALoCoQn4o6HAXMZuaMAUtOo9fzwRLtFGXNkRPSo8DjsXl80J6dQIXBTrqB6csQ81VPMGKeExTiU5 X-Barracuda-Connect: mail-la0-f45.google.com[209.85.215.45] X-Barracuda-Start-Time: 1362575006 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.61 X-Barracuda-Spam-Status: No, SCORE=0.61 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=DKIM_SIGNED, DKIM_VERIFIED, HTML_FONT_FACE_BAD, HTML_MESSAGE X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124416 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature 0.00 HTML_MESSAGE BODY: HTML included in message 0.61 HTML_FONT_FACE_BAD BODY: HTML font face is not a word --e0cb4efe29d230549c04d7413786 Content-Type: text/plain; charset=UTF-8 On Wed, Mar 6, 2013 at 6:29 PM, Ric Wheeler wrote: > I think that you would need to verify that the Amazon storage is not > throwing errors - do your logs show IO errors or issues before XFS hits an > issue? No IO errors in /var/log/messages. Where else should I be looking? -- Regards *Shrinath.M* --e0cb4efe29d230549c04d7413786 Content-Type: text/html; charset=UTF-8 Content-Transfer-Encoding: quoted-printable

On Wed, Mar 6, 2013 at 6:29 PM, Ric Wheele= r <rwheeler@redhat.com> wrote:
I think that you would need to verify that the Amazon stor= age is not throwing errors - do your logs show IO errors or issues before X= FS hits an issue?

No IO errors in /var/log/message= s.=C2=A0
Where else should I be looking?



--
<= font face=3D"'courier new', monospace" color=3D"#666666">Regards
Shrina= th.M

--e0cb4efe29d230549c04d7413786-- From rwheeler@redhat.com Wed Mar 6 07:08:21 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id C8B7E8013 for ; Wed, 6 Mar 2013 07:08:21 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay2.corp.sgi.com (Postfix) with ESMTP id 91CC5304059 for ; Wed, 6 Mar 2013 05:08:21 -0800 (PST) X-ASG-Debug-ID: 1362575300-04bdf02298214e10001-NocioJ Received: from mx1.redhat.com (mx1.redhat.com [209.132.183.28]) by cuda.sgi.com with ESMTP id nL1KuiHpZ5WLcihy for ; Wed, 06 Mar 2013 05:08:20 -0800 (PST) X-Barracuda-Envelope-From: rwheeler@redhat.com X-Barracuda-Apparent-Source-IP: 209.132.183.28 X-ASG-Whitelist: Client Received: from int-mx01.intmail.prod.int.phx2.redhat.com (int-mx01.intmail.prod.int.phx2.redhat.com [10.5.11.11]) by mx1.redhat.com (8.14.4/8.14.4) with ESMTP id r26D8KdQ020525 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=OK); Wed, 6 Mar 2013 08:08:20 -0500 Received: from tunkums.home (ovpn-112-33.phx2.redhat.com [10.3.112.33]) by int-mx01.intmail.prod.int.phx2.redhat.com (8.13.8/8.13.8) with ESMTP id r26D8IP0024439; Wed, 6 Mar 2013 08:08:18 -0500 Message-ID: <51373FC1.6010101@redhat.com> Date: Wed, 06 Mar 2013 08:08:17 -0500 From: Ric Wheeler User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:17.0) Gecko/20130219 Thunderbird/17.0.3 MIME-Version: 1.0 To: Shrinath M CC: Supratik Goswami , Sabyasachi Ruj , Vivek Goel , xfs@oss.sgi.com Subject: Re: XFS filesystem on EC2 instance corrupts and shuts down References: <51373DB8.2020707@redhat.com> X-ASG-Orig-Subj: Re: XFS filesystem on EC2 instance corrupts and shuts down In-Reply-To: Content-Type: text/plain; charset=ISO-8859-1; format=flowed Content-Transfer-Encoding: 7bit X-Scanned-By: MIMEDefang 2.67 on 10.5.11.11 X-Barracuda-Connect: mx1.redhat.com[209.132.183.28] X-Barracuda-Start-Time: 1362575300 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 On 03/06/2013 08:03 AM, Shrinath M wrote: > > On Wed, Mar 6, 2013 at 6:29 PM, Ric Wheeler > wrote: > > I think that you would need to verify that the Amazon storage is not > throwing errors - do your logs show IO errors or issues before XFS hits an > issue? > > > No IO errors in /var/log/messages. > Where else should I be looking? > > Feb 12 19:47:18 ip-100-0-100-1 kernel: [2541168.023638] XFS (md0): I/O Error Detected. Shutting down filesystem Is an IO error from MD. I would suggest trying to reproduce without MD in the picture first - always best to try to reproduce with the simplest setup first and work your way up the complexity ladder, Ric From supratik.goswami@webyog.com Wed Mar 6 07:12:50 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=HTML_FONT_FACE_BAD, HTML_MESSAGE,T_DKIM_INVALID autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 28FD88012 for ; Wed, 6 Mar 2013 07:12:50 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay1.corp.sgi.com (Postfix) with ESMTP id ED9DB8F8092 for ; Wed, 6 Mar 2013 05:12:46 -0800 (PST) X-ASG-Debug-ID: 1362575564-04bdf02296215140001-NocioJ Received: from mail-ee0-f52.google.com (mail-ee0-f52.google.com [74.125.83.52]) by cuda.sgi.com with ESMTP id 9jZn9gsiTPQO5w4l (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Wed, 06 Mar 2013 05:12:45 -0800 (PST) X-Barracuda-Envelope-From: supratik.goswami@webyog.com X-Barracuda-Apparent-Source-IP: 74.125.83.52 Received: by mail-ee0-f52.google.com with SMTP id b15so5527696eek.11 for ; Wed, 06 Mar 2013 05:12:44 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=webyog.com; s=google; h=x-received:mime-version:in-reply-to:references:from:date:message-id :subject:to:content-type; bh=lKR17cPg1l6nORUnO70KjNuQOe9kcc9TJnfR6n2HciQ=; b=HHa7HmW4gK4O9WOQ6AZzBvGDky8pJb7L77N7D7QFpo7wcKouPISaXW7QaC1pTsTyu2 FSUBqWK4DWADdTuIf0Pc5rKxoMfVLUGWYCvoqsRsOgo2HFcUF4R5On3Qm4fkoa4IiO95 V/Igy40fqowhm+ryw56jppWIC421CZi1uAtAY= X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=20120113; h=x-received:mime-version:in-reply-to:references:from:date:message-id :subject:to:content-type:x-gm-message-state; bh=lKR17cPg1l6nORUnO70KjNuQOe9kcc9TJnfR6n2HciQ=; b=X8eJ1wvbeGK0RatjGlogKWXS/aA9bwQF5zFOw7JrMSRYcFqZVQB4/3rZfk1eiygGQh WMStuw9n8R7c6Dhul1Qiv0QwBY7cZG9s+91wXjRgYwvS2Mz66V01i/Z8NLGch4kstaLd nCujQTTK/zXDFITTJzjZXPLDr0rUsQJ70fGavA7wlmIKiMB1jWh5s0tHlMN2yoEWjf5z CWyxvcBnPxIFEqXB31o71DEZxVDRCGHA4naO221MuK/BjuI2NKS6c5j3DAyTZ/wONoFJ cSZDaNYvkaSvAulwMkR4lhJ0VJ6GRrFtvc8t1FXdUQY48aLfprIfAMmn61ThBzS3Mdu7 M2TQ== X-Received: by 10.14.183.67 with SMTP id p43mr81438118eem.10.1362575564071; Wed, 06 Mar 2013 05:12:44 -0800 (PST) MIME-Version: 1.0 Received: by 10.14.215.132 with HTTP; Wed, 6 Mar 2013 05:12:23 -0800 (PST) In-Reply-To: <51373FC1.6010101@redhat.com> References: <51373DB8.2020707@redhat.com> <51373FC1.6010101@redhat.com> From: Supratik Goswami Date: Wed, 6 Mar 2013 18:42:23 +0530 Message-ID: Subject: Re: XFS filesystem on EC2 instance corrupts and shuts down To: Shrinath M , Sabyasachi Ruj , Vivek Goel , xfs@oss.sgi.com X-ASG-Orig-Subj: Re: XFS filesystem on EC2 instance corrupts and shuts down Content-Type: multipart/alternative; boundary=047d7b3a805e7a19e404d7415844 X-Gm-Message-State: ALoCoQlWozaSEvx6wonr7u27qko4LnqdGBxN996NimQwLDtgia39+2KiduR6qJ62I2m1zy8Iqjpe X-Barracuda-Connect: mail-ee0-f52.google.com[74.125.83.52] X-Barracuda-Start-Time: 1362575565 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.62 X-Barracuda-Spam-Status: No, SCORE=0.62 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_SA_TO_FROM_DOMAIN_MATCH, DKIM_SIGNED, DKIM_VERIFIED, HTML_FONT_FACE_BAD, HTML_MESSAGE X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124416 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature 0.00 HTML_MESSAGE BODY: HTML included in message 0.61 HTML_FONT_FACE_BAD BODY: HTML font face is not a word 0.01 BSF_SC0_SA_TO_FROM_DOMAIN_MATCH Sender Domain Matches Recipient Domain --047d7b3a805e7a19e404d7415844 Content-Type: text/plain; charset=UTF-8 Have we created a ticket with AWS ? It could be an EBS issue who knows, we need to confirm that first. -- Warm Regards Supratik On Wed, Mar 6, 2013 at 6:38 PM, Ric Wheeler wrote: > On 03/06/2013 08:03 AM, Shrinath M wrote: > > >> On Wed, Mar 6, 2013 at 6:29 PM, Ric Wheeler > rwheeler@redhat.com>> wrote: >> >> I think that you would need to verify that the Amazon storage is not >> throwing errors - do your logs show IO errors or issues before XFS >> hits an >> issue? >> >> >> No IO errors in /var/log/messages. >> Where else should I be looking? >> >> >> > Feb 12 19:47:18 ip-100-0-100-1 kernel: [2541168.023638] XFS (md0): I/O > Error Detected. Shutting down filesystem > > Is an IO error from MD. > > I would suggest trying to reproduce without MD in the picture first - > always best to try to reproduce with the simplest setup first and work your > way up the complexity ladder, > > Ric > > --047d7b3a805e7a19e404d7415844 Content-Type: text/html; charset=UTF-8 Content-Transfer-Encoding: quoted-printable Have we created a ticket with AW= S ?

It could be a= n EBS issue who knows, we need to confirm that first.
--
Warm Regards

Supratik


On Wed, Mar 6, 2013 at 6:38 PM, Ric Whee= ler <rwheeler@redhat.com> wrote:
On 03/06/2013 08:03 AM, Shrinath M wrote:


On Wed, Mar 6, 2013 at 6:29 PM, Ric Wheeler <rwheeler@redhat.com <mailto:rwheeler@redhat.com>&= gt; wrote:

=C2=A0 =C2=A0 I think that you would need to verify that the Amazon storage= is not
=C2=A0 =C2=A0 throwing errors - do your logs show IO errors or issues befor= e XFS hits an
=C2=A0 =C2=A0 issue?


No IO errors in /var/log/messages.
Where else should I be looking?



Feb 12 19:47:18 ip-100-0-100-1 kernel: [2541168.023638] XFS (md0): I/O Erro= r Detected. Shutting down filesystem

Is an IO error from MD.

I would suggest trying to reproduce without MD in the picture first - alway= s best to try to reproduce with the simplest setup first and work your way = up the complexity ladder,

Ric


--047d7b3a805e7a19e404d7415844-- From supratik.goswami@webyog.com Wed Mar 6 07:15:33 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=HTML_FONT_FACE_BAD, HTML_MESSAGE,T_DKIM_INVALID autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id D59278015 for ; Wed, 6 Mar 2013 07:15:33 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay1.corp.sgi.com (Postfix) with ESMTP id 8F6148F8094 for ; Wed, 6 Mar 2013 05:15:33 -0800 (PST) X-ASG-Debug-ID: 1362575731-04bdf02298215340001-NocioJ Received: from mail-ee0-f54.google.com (mail-ee0-f54.google.com [74.125.83.54]) by cuda.sgi.com with ESMTP id yzSwLwFxSE1zNN1I (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Wed, 06 Mar 2013 05:15:32 -0800 (PST) X-Barracuda-Envelope-From: supratik.goswami@webyog.com X-Barracuda-Apparent-Source-IP: 74.125.83.54 Received: by mail-ee0-f54.google.com with SMTP id c41so5768007eek.13 for ; Wed, 06 Mar 2013 05:15:30 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=webyog.com; s=google; h=x-received:mime-version:in-reply-to:references:from:date:message-id :subject:to:content-type; bh=uLUPNNVUmbZylG6/1U/6/kfNF/A0m7WpCQCPGYL6kGg=; b=m9J0ZDY1wiRWUWIZMu2Er7/r81ytmApsHFMskc1f7Y3uENgf492axuFJy2fOfzQItP flTAA27p6mgalbOUMrttcyDgbyegpfZ8SH3m8fenvFX7wDKs0/CQNOVUiD+lvkPLoFfG dDk30vsjXKCNkrDh1nUtOc4dX18/gebRJ2Ysk= X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=20120113; h=x-received:mime-version:in-reply-to:references:from:date:message-id :subject:to:content-type:x-gm-message-state; bh=uLUPNNVUmbZylG6/1U/6/kfNF/A0m7WpCQCPGYL6kGg=; b=kvMkG7lUvTs0XIYmsIlTz6AneKwKlABDX2M7wGx+pe6HpaJIEvFvO82GR+YDUw5/jw daMnEe71+TXYCTGLLSjfXuPtb/za8+WU6+dilftzKf+u2hHFEQyRlgTFKAfI1nAQYq6d G7ImZ3qwSoOJ0J+eNz4k0Te3Nt+2L4oPMq9bUqho7XPiI+RWVyNfrmVSa5cR+/3yB8AA LGg8viEsxX1ij2dnZbqPubf2Z/eFFkI4KfnaW0Nz7I4i8yh2HURNTzEVFZfG5crVQihi OSB0pXyAWTB72GKYTCJAg/Xz5yb46nuPwh50Ybl+ty3SzEJj3kT7JoQ0yOepxiK/k62y 7oiQ== X-Received: by 10.14.207.200 with SMTP id n48mr82249015eeo.4.1362575730659; Wed, 06 Mar 2013 05:15:30 -0800 (PST) MIME-Version: 1.0 Received: by 10.14.215.132 with HTTP; Wed, 6 Mar 2013 05:15:10 -0800 (PST) In-Reply-To: References: <51373DB8.2020707@redhat.com> <51373FC1.6010101@redhat.com> From: Supratik Goswami Date: Wed, 6 Mar 2013 18:45:10 +0530 Message-ID: Subject: Re: XFS filesystem on EC2 instance corrupts and shuts down To: Shrinath M , Sabyasachi Ruj , Vivek Goel , xfs@oss.sgi.com X-ASG-Orig-Subj: Re: XFS filesystem on EC2 instance corrupts and shuts down Content-Type: multipart/alternative; boundary=047d7b343b1c68147504d7416243 X-Gm-Message-State: ALoCoQkX+6AMz7UFa+PlQ3MmkC1ui/0ts3rQ8TeNqxkKTvQRFTXxnvcBnmwtizistWAWSWUwAgRj X-Barracuda-Connect: mail-ee0-f54.google.com[74.125.83.54] X-Barracuda-Start-Time: 1362575731 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.62 X-Barracuda-Spam-Status: No, SCORE=0.62 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_SA_TO_FROM_DOMAIN_MATCH, DKIM_SIGNED, DKIM_VERIFIED, HTML_FONT_FACE_BAD, HTML_MESSAGE X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124416 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature 0.00 HTML_MESSAGE BODY: HTML included in message 0.61 HTML_FONT_FACE_BAD BODY: HTML font face is not a word 0.01 BSF_SC0_SA_TO_FROM_DOMAIN_MATCH Sender Domain Matches Recipient Domain --047d7b343b1c68147504d7416243 Content-Type: text/plain; charset=UTF-8 Please ignore my previous mail. -- Warm Regards Supratik On Wed, Mar 6, 2013 at 6:42 PM, Supratik Goswami < supratik.goswami@webyog.com> wrote: > Have we created a ticket with AWS ? > > It could be an EBS issue who knows, we need to confirm that first. > > -- > Warm Regards > > Supratik > > > On Wed, Mar 6, 2013 at 6:38 PM, Ric Wheeler wrote: > >> On 03/06/2013 08:03 AM, Shrinath M wrote: >> >> >>> On Wed, Mar 6, 2013 at 6:29 PM, Ric Wheeler >> rwheeler@redhat.com>> wrote: >>> >>> I think that you would need to verify that the Amazon storage is not >>> throwing errors - do your logs show IO errors or issues before XFS >>> hits an >>> issue? >>> >>> >>> No IO errors in /var/log/messages. >>> Where else should I be looking? >>> >>> >>> >> Feb 12 19:47:18 ip-100-0-100-1 kernel: [2541168.023638] XFS (md0): I/O >> Error Detected. Shutting down filesystem >> >> Is an IO error from MD. >> >> I would suggest trying to reproduce without MD in the picture first - >> always best to try to reproduce with the simplest setup first and work your >> way up the complexity ladder, >> >> Ric >> >> > --047d7b343b1c68147504d7416243 Content-Type: text/html; charset=UTF-8 Content-Transfer-Encoding: quoted-printable Please ignore my previous mail.<= br clear=3D"all">

--
Warm Regards

Supratik


On Wed, Mar 6, 2013 at 6:42 PM, Supratik= Goswami <supratik.goswami@webyog.com> wrote:
<= blockquote class=3D"gmail_quote" style=3D"margin:0 0 0 .8ex;border-left:1px= #ccc solid;padding-left:1ex"> Have we created a ticket with AW= S ?

It could be a= n EBS issue who knows, we need to confirm that first.
--
Warm Regards

Supratik


On Wed, Mar 6, 2013 at 6:38 PM, Ric Whee= ler <rwheeler@redhat.com> wrote:
On 03/06/2013 08:03 AM, Shrinath M wrote:


On Wed, Mar 6, 2013 at 6:29 PM, Ric Wheeler <rwheeler@redhat.com <mailto:rwheeler@redhat.com>&= gt; wrote:

=C2=A0 =C2=A0 I think that you would need to verify that the Amazon storage= is not
=C2=A0 =C2=A0 throwing errors - do your logs show IO errors or issues befor= e XFS hits an
=C2=A0 =C2=A0 issue?


No IO errors in /var/log/messages.
Where else should I be looking?



Feb 12 19:47:18 ip-100-0-100-1 kernel: [2541168.023638] XFS (md0): I/O Erro= r Detected. Shutting down filesystem

Is an IO error from MD.

I would suggest trying to reproduce without MD in the picture first - alway= s best to try to reproduce with the simplest setup first and work your way = up the complexity ladder,

Ric



--047d7b343b1c68147504d7416243-- From dennis.kaarsemaker@booking.com Wed Mar 6 07:52:53 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=T_DKIM_INVALID autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id D5F2E8004 for ; Wed, 6 Mar 2013 07:52:53 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id AF828304051 for ; Wed, 6 Mar 2013 05:52:53 -0800 (PST) X-ASG-Debug-ID: 1362577967-04cbb07dbe204bf0001-NocioJ Received: from mail-out2.booking.com (mail-out2.booking.com [62.190.24.21]) by cuda.sgi.com with ESMTP id q29HheejmQQeoOkS (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO) for ; Wed, 06 Mar 2013 05:52:49 -0800 (PST) X-Barracuda-Envelope-From: dennis.kaarsemaker@booking.com X-Barracuda-Apparent-Source-IP: 62.190.24.21 DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=booking.com; s=bk; h=Mime-Version:Content-Type:References:In-Reply-To:Date:To:From:Subject:Message-ID; bh=+w4+YyGqzUR9vNOHfvw0+E9AyqwVDaQU4AhnPlRMPxM=; b=DU+4efAWaKwyQAldTEZfNAz50tV6Hm8dDJdzzKGog9PGMIpqUTLJZyCMB6UuJXAgWWYpgm4pKC+o9bPuvkRK2xx4ZtYt88IY91mmRcz+emuc3SdB6/qb/gmzIWMn8YNvgwCX9pHYbw6Ngh0XmfUH0AqtvLt0CljtOPOP11vp/R4=; Received: from corpds-202.lhr4.corp.booking.com ([10.186.68.14]:46159) by mtx-06.prod.lhr1.booking.com with esmtps (TLSv1:DHE-RSA-AES256-SHA:256) (Exim 4.80.1) (envelope-from ) id 1UDEly-0006WE-TF for xfs@oss.sgi.com; Wed, 06 Mar 2013 14:52:46 +0100 Received: from [10.155.73.64] (port=51823) by corpds-202.lhr4.corp.booking.com with esmtpsa (TLSv1:DHE-RSA-CAMELLIA256-SHA:256) (Exim 4.80.1) (envelope-from ) id 1UDEly-0005xU-N0 for xfs@oss.sgi.com; Wed, 06 Mar 2013 14:52:46 +0100 Message-ID: <1362577992.1247.84.camel@seahawk> Subject: Re: XFS IO multiplication problem on centos/rhel 6 using hp p420i raid controllers From: Dennis Kaarsemaker X-ASG-Orig-Subj: Re: XFS IO multiplication problem on centos/rhel 6 using hp p420i raid controllers To: xfs@oss.sgi.com Date: Wed, 06 Mar 2013 14:53:12 +0100 In-Reply-To: <20130228194023.GQ5551@dastard> References: <1362060736.1247.30.camel@seahawk> <20130228194023.GQ5551@dastard> Organization: Booking.com Content-Type: multipart/mixed; boundary="=-2o1faoBEooenegpWZfdA" X-Mailer: Evolution 3.2.3-0ubuntu6 Mime-Version: 1.0 X-Barracuda-Connect: mail-out2.booking.com[62.190.24.21] X-Barracuda-Start-Time: 1362577969 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.10 X-Barracuda-Spam-Status: No, SCORE=0.10 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_SA085, DKIM_SIGNED, DKIM_VERIFIED X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124420 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature 0.10 BSF_SC0_SA085 Custom Rule SA085 --=-2o1faoBEooenegpWZfdA Content-Type: text/plain; charset="UTF-8" Content-Transfer-Encoding: 7bit On Fri, 2013-03-01 at 06:40 +1100, Dave Chinner wrote: > On Thu, Feb 28, 2013 at 03:12:16PM +0100, Dennis Kaarsemaker wrote: > > Hello XFS developers, > > > > I have a problem as described in the subject. If I read the xfs website > > correctly, this would be a place to ask for support with that problem. > > Before I spam you all with details, please confirm if this is true or > > direct me to a better place. Thanks! > > CentOS/RHEL problems can be triaged up to a point here. i.e. we will > make an effort to pinpoint the problem, but we give no guarantees > and we definitely can't fix it. If you want a btter triage guarantee > and to talk to someone who is able to fix the problem, you need to > work through the problem with your RHEL support contact. Hi Dave, Thanks for responding. We have filed support tickets with HP and Red Hat as well, I was trying to parallelize the search for an answer as the problem is really getting in the way here. So much so that I've offered a bottle of $favourite_drink on a serverfault question to the one who solves it, that offer applies here too :) > Either way: > > http://xfs.org/index.php/XFS_FAQ#Q:_What_information_should_I_include_when_reporting_a_problem.3F A summary of the problem is this: [root@bc290bprdb-01 ~]# collectl #<----CPU[HYPER]-----><----------Disks-----------><----------Network----------> #cpu sys inter ctxsw KBRead Reads KBWrit Writes KBIn PktIn KBOut PktOut 1 0 1636 4219 16 1 2336 313 184 195 12 133 1 0 1654 2804 64 3 2919 432 391 352 20 208 [root@bc291bprdb-01 ~]# collectl #<----CPU[HYPER]-----><----------Disks-----------><----------Network----------> #cpu sys inter ctxsw KBRead Reads KBWrit Writes KBIn PktIn KBOut PktOut 1 0 2220 3691 332 13 39992 331 112 122 6 92 0 0 1354 2708 0 0 39836 335 103 125 9 99 0 0 1563 3023 120 6 44036 369 399 317 13 188 Notice the KBWrit difference. These are two identical hp gen 8 machines, doing the same thing (replicating the same mysql schema). The one writing ten times as many bytes in the same amount of transactions is running centos 6 (and was running rhel 6). Changing to gen7 hardware (hp p410 controller instead of p420), or to centos 5 on newer hardware (older xfs version obviously) or using ext3 instead of xfs on either makes the writes "normal sized" again. We're most likely doing something wrong with XFS but can't figure out what. Any hint to get us moving in the right direction would be most helpful. Now all the info asked for in that wikipage: uname -a: Linux bc291bprdb-01.lhr4.prod.booking.com 2.6.32-279.1.1.el6.x86_64 #1 SMP Tue Jul 10 13:47:21 UTC 2012 x86_64 x86_64 x86_64 GNU/Linux xfsprogs version: xfs_repair version 3.1.1 number of CPU's: 2 x 8-core hyperthreaded Intel(R) Xeon(R) CPU E5-2670 0 @ 2.60GHz meminfo: MemTotal: 99026008 kB MemFree: 502692 kB Buffers: 176964 kB Cached: 44630620 kB SwapCached: 0 kB Active: 71178012 kB Inactive: 24698980 kB Active(anon): 48478524 kB Inactive(anon): 2591228 kB Active(file): 22699488 kB Inactive(file): 22107752 kB Unevictable: 0 kB Mlocked: 0 kB SwapTotal: 1048312 kB SwapFree: 1048312 kB Dirty: 4740 kB Writeback: 0 kB AnonPages: 51069600 kB Mapped: 32992 kB Shmem: 184 kB Slab: 1517096 kB SReclaimable: 1444392 kB SUnreclaim: 72704 kB KernelStack: 6152 kB PageTables: 105940 kB NFS_Unstable: 0 kB Bounce: 0 kB WritebackTmp: 0 kB CommitLimit: 50561316 kB Committed_AS: 87014212 kB VmallocTotal: 34359738367 kB VmallocUsed: 483464 kB VmallocChunk: 34308527752 kB HardwareCorrupted: 0 kB AnonHugePages: 49096704 kB HugePages_Total: 0 HugePages_Free: 0 HugePages_Rsvd: 0 HugePages_Surp: 0 Hugepagesize: 2048 kB DirectMap4k: 8120 kB DirectMap2M: 3102720 kB DirectMap1G: 97517568 kB mounts: rootfs / rootfs rw 0 0 proc /proc proc rw,relatime 0 0 sysfs /sys sysfs rw,relatime 0 0 devtmpfs /dev devtmpfs rw,relatime,size=49503776k,nr_inodes=12375944,mode=755 0 0 devpts /dev/pts devpts rw,relatime,gid=5,mode=620,ptmxmode=000 0 0 tmpfs /dev/shm tmpfs rw,relatime 0 0 /dev/mapper/sysvm-root / ext4 rw,relatime,barrier=1,stripe=192,data=ordered 0 0 /proc/bus/usb /proc/bus/usb usbfs rw,relatime 0 0 /dev/sda1 /boot ext4 rw,relatime,barrier=1,stripe=768,data=ordered 0 0 none /proc/sys/fs/binfmt_misc binfmt_misc rw,relatime 0 0 debugfs /sys/kernel/debug debugfs rw,relatime 0 0 /dev/mapper/sysvm-mysqlVol /mysql/bp xfs rw,relatime,attr2,delaylog,allocsize=1024k,logbsize=256k,sunit=512,swidth=1536,noquota 0 0 raid layout: hp p420i raid controller 7 x 600 GB SAS disk (HP EG0600FBLSH) raid 1+0 with one hot spare LVM: default red hat config (lvm.conf attached) The raid array is partitioned into /boot swap and a PV for LVM One volume group containing that PV 2 LV's: root and mysql. Root is ext4, mysql xfs [root@bc291bprdb-01 ~]# lvdisplay --- Logical volume --- LV Path /dev/sysvm/root LV Name root VG Name sysvm LV UUID 2xXk8Q-gor3-Ql0S-EKI3-dA20-E9el-FH8eDX LV Write Access read/write LV Creation host, time bc291bprdb-01.lhr4.prod.booking.com, 2013-02-28 09:36:01 +0100 LV Status available # open 1 LV Size 39.06 GiB Current LE 1250 Segments 1 Allocation inherit Read ahead sectors auto - currently set to 256 Block device 253:0 --- Logical volume --- LV Path /dev/sysvm/mysqlVol LV Name mysqlVol VG Name sysvm LV UUID v2yezw-Ry8i-wy2d-PjZD-QHeJ-refb-96oAH8 LV Write Access read/write LV Creation host, time bc291bprdb-01.lhr4.prod.booking.com, 2013-02-28 09:49:58 +0100 LV Status available # open 1 LV Size 300.00 GiB Current LE 9600 Segments 1 Allocation inherit Read ahead sectors auto - currently set to 256 Block device 253:1 type of disks: see raid config write cache status: no disk write cache but raid controller cache size of bbwc and mode: Cache Board Present: True Cache Status: OK Accelerator Ratio: 10% Read / 90% Write Cache Backup Power Source: Capacitors Battery/Capacitor Count: 1 Battery/Capacitor Status: OK xfs_info: [root@bc291bprdb-01 ~]# xfs_info /mysql/bp/ meta-data=/dev/mapper/sysvm-mysqlVol isize=256 agcount=16, agsize=4915136 blks = sectsz=512 attr=2 data = bsize=4096 blocks=78642176, imaxpct=25 = sunit=64 swidth=192 blks naming =version 2 bsize=4096 ascii-ci=0 log =internal bsize=4096 blocks=38400, version=2 = sectsz=512 sunit=64 blks, lazy-count=1 realtime =none extsz=4096 blocks=0, rtextents=0 And for reference, xfs_info on centos 5: [root@bc290bprdb-01 ~]# xfs_info /mysql/bp/ meta-data=/dev/sysvm/mysqlVol isize=256 agcount=22, agsize=4915200 blks = sectsz=512 attr=0 data = bsize=4096 blocks=104857600, imaxpct=25 = sunit=0 swidth=0 blks, unwritten=1 naming =version 2 bsize=4096 log =internal bsize=4096 blocks=32768, version=1 = sectsz=512 sunit=0 blks, lazy-count=0 realtime =none extsz=4096 blocks=0, rtextents=0 dmesg output: there are no errors on the filesystem or in dmesg iostat/vmstat output: attached -- Dennis Kaarsemaker, Systems Architect Booking.com Herengracht 597, 1017 CE Amsterdam Tel external +31 (0) 20 715 3409 Tel internal (7207) 3409 --=-2o1faoBEooenegpWZfdA Content-Disposition: attachment; filename="lvm.conf" Content-Type: text/plain; name="lvm.conf"; charset="UTF-8" Content-Transfer-Encoding: 7bit # This is an example configuration file for the LVM2 system. # It contains the default settings that would be used if there was no # /etc/lvm/lvm.conf file. # # Refer to 'man lvm.conf' for further information including the file layout. # # To put this file in a different directory and override /etc/lvm set # the environment variable LVM_SYSTEM_DIR before running the tools. # # N.B. Take care that each setting only appears once if uncommenting # example settings in this file. # This section allows you to configure which block devices should # be used by the LVM system. devices { # Where do you want your volume groups to appear ? dir = "/dev" # An array of directories that contain the device nodes you wish # to use with LVM2. scan = [ "/dev" ] # If set, the cache of block device nodes with all associated symlinks # will be constructed out of the existing udev database content. # This avoids using and opening any inapplicable non-block devices or # subdirectories found in the device directory. This setting is applied # to udev-managed device directory only, other directories will be scanned # fully. LVM2 needs to be compiled with udev support for this setting to # take effect. N.B. Any device node or symlink not managed by udev in # udev directory will be ignored with this setting on. obtain_device_list_from_udev = 1 # If several entries in the scanned directories correspond to the # same block device and the tools need to display a name for device, # all the pathnames are matched against each item in the following # list of regular expressions in turn and the first match is used. # preferred_names = [ ] # Try to avoid using undescriptive /dev/dm-N names, if present. preferred_names = [ "^/dev/mpath/", "^/dev/mapper/mpath", "^/dev/[hs]d" ] # A filter that tells LVM2 to only use a restricted set of devices. # The filter consists of an array of regular expressions. These # expressions can be delimited by a character of your choice, and # prefixed with either an 'a' (for accept) or 'r' (for reject). # The first expression found to match a device name determines if # the device will be accepted or rejected (ignored). Devices that # don't match any patterns are accepted. # Be careful if there there are symbolic links or multiple filesystem # entries for the same device as each name is checked separately against # the list of patterns. The effect is that if the first pattern in the # list to match a name is an 'a' pattern for any of the names, the device # is accepted; otherwise if the first pattern in the list to match a name # is an 'r' pattern for any of the names it is rejected; otherwise it is # accepted. # Don't have more than one filter line active at once: only one gets used. # Run vgscan after you change this parameter to ensure that # the cache file gets regenerated (see below). # If it doesn't do what you expect, check the output of 'vgscan -vvvv'. # By default we accept every block device: filter = [ "a/.*/" ] # Exclude the cdrom drive # filter = [ "r|/dev/cdrom|" ] # When testing I like to work with just loopback devices: # filter = [ "a/loop/", "r/.*/" ] # Or maybe all loops and ide drives except hdc: # filter =[ "a|loop|", "r|/dev/hdc|", "a|/dev/ide|", "r|.*|" ] # Use anchors if you want to be really specific # filter = [ "a|^/dev/hda8$|", "r/.*/" ] # The results of the filtering are cached on disk to avoid # rescanning dud devices (which can take a very long time). # By default this cache is stored in the /etc/lvm/cache directory # in a file called '.cache'. # It is safe to delete the contents: the tools regenerate it. # (The old setting 'cache' is still respected if neither of # these new ones is present.) cache_dir = "/etc/lvm/cache" cache_file_prefix = "" # You can turn off writing this cache file by setting this to 0. write_cache_state = 1 # Advanced settings. # List of pairs of additional acceptable block device types found # in /proc/devices with maximum (non-zero) number of partitions. # types = [ "fd", 16 ] # If sysfs is mounted (2.6 kernels) restrict device scanning to # the block devices it believes are valid. # 1 enables; 0 disables. sysfs_scan = 1 # By default, LVM2 will ignore devices used as component paths # of device-mapper multipath devices. # 1 enables; 0 disables. multipath_component_detection = 1 # By default, LVM2 will ignore devices used as components of # software RAID (md) devices by looking for md superblocks. # 1 enables; 0 disables. md_component_detection = 1 # By default, if a PV is placed directly upon an md device, LVM2 # will align its data blocks with the md device's stripe-width. # 1 enables; 0 disables. md_chunk_alignment = 1 # Default alignment of the start of a data area in MB. If set to 0, # a value of 64KB will be used. Set to 1 for 1MiB, 2 for 2MiB, etc. # default_data_alignment = 1 # By default, the start of a PV's data area will be a multiple of # the 'minimum_io_size' or 'optimal_io_size' exposed in sysfs. # - minimum_io_size - the smallest request the device can perform # w/o incurring a read-modify-write penalty (e.g. MD's chunk size) # - optimal_io_size - the device's preferred unit of receiving I/O # (e.g. MD's stripe width) # minimum_io_size is used if optimal_io_size is undefined (0). # If md_chunk_alignment is enabled, that detects the optimal_io_size. # This setting takes precedence over md_chunk_alignment. # 1 enables; 0 disables. data_alignment_detection = 1 # Alignment (in KB) of start of data area when creating a new PV. # md_chunk_alignment and data_alignment_detection are disabled if set. # Set to 0 for the default alignment (see: data_alignment_default) # or page size, if larger. data_alignment = 0 # By default, the start of the PV's aligned data area will be shifted by # the 'alignment_offset' exposed in sysfs. This offset is often 0 but # may be non-zero; e.g.: certain 4KB sector drives that compensate for # windows partitioning will have an alignment_offset of 3584 bytes # (sector 7 is the lowest aligned logical block, the 4KB sectors start # at LBA -1, and consequently sector 63 is aligned on a 4KB boundary). # But note that pvcreate --dataalignmentoffset will skip this detection. # 1 enables; 0 disables. data_alignment_offset_detection = 1 # If, while scanning the system for PVs, LVM2 encounters a device-mapper # device that has its I/O suspended, it waits for it to become accessible. # Set this to 1 to skip such devices. This should only be needed # in recovery situations. ignore_suspended_devices = 0 # During each LVM operation errors received from each device are counted. # If the counter of a particular device exceeds the limit set here, no # further I/O is sent to that device for the remainder of the respective # operation. Setting the parameter to 0 disables the counters altogether. disable_after_error_count = 0 # Allow use of pvcreate --uuid without requiring --restorefile. require_restorefile_with_uuid = 1 # Minimum size (in KB) of block devices which can be used as PVs. # In a clustered environment all nodes must use the same value. # Any value smaller than 512KB is ignored. # Ignore devices smaller than 2MB such as floppy drives. pv_min_size = 2048 # The original built-in setting was 512 up to and including version 2.02.84. # pv_min_size = 512 # Issue discards to a logical volumes's underlying physical volume(s) when # the logical volume is no longer using the physical volumes' space (e.g. # lvremove, lvreduce, etc). Discards inform the storage that a region is # no longer in use. Storage that supports discards advertise the protocol # specific way discards should be issued by the kernel (TRIM, UNMAP, or # WRITE SAME with UNMAP bit set). Not all storage will support or benefit # from discards but SSDs and thinly provisioned LUNs generally do. If set # to 1, discards will only be issued if both the storage and kernel provide # support. # 1 enables; 0 disables. issue_discards = 0 } # This section allows you to configure the way in which LVM selects # free space for its Logical Volumes. #allocation { # When searching for free space to extend an LV, the "cling" # allocation policy will choose space on the same PVs as the last # segment of the existing LV. If there is insufficient space and a # list of tags is defined here, it will check whether any of them are # attached to the PVs concerned and then seek to match those PV tags # between existing extents and new extents. # Use the special tag "@*" as a wildcard to match any PV tag. # # Example: LVs are mirrored between two sites within a single VG. # PVs are tagged with either @site1 or @site2 to indicate where # they are situated. # # cling_tag_list = [ "@site1", "@site2" ] # cling_tag_list = [ "@*" ] # # Changes made in version 2.02.85 extended the reach of the 'cling' # policies to detect more situations where data can be grouped # onto the same disks. Set this to 0 to revert to the previous # algorithm. # # maximise_cling = 1 # # Set to 1 to guarantee that mirror logs will always be placed on # different PVs from the mirror images. This was the default # until version 2.02.85. # # mirror_logs_require_separate_pvs = 0 # # Set to 1 to guarantee that thin pool metadata will always # be placed on different PVs from the pool data. # # thin_pool_metadata_require_separate_pvs = 0 #} # This section that allows you to configure the nature of the # information that LVM2 reports. log { # Controls the messages sent to stdout or stderr. # There are three levels of verbosity, 3 being the most verbose. verbose = 0 # Should we send log messages through syslog? # 1 is yes; 0 is no. syslog = 1 # Should we log error and debug messages to a file? # By default there is no log file. #file = "/var/log/lvm2.log" # Should we overwrite the log file each time the program is run? # By default we append. overwrite = 0 # What level of log messages should we send to the log file and/or syslog? # There are 6 syslog-like log levels currently in use - 2 to 7 inclusive. # 7 is the most verbose (LOG_DEBUG). level = 0 # Format of output messages # Whether or not (1 or 0) to indent messages according to their severity indent = 1 # Whether or not (1 or 0) to display the command name on each line output command_names = 0 # A prefix to use before the message text (but after the command name, # if selected). Default is two spaces, so you can see/grep the severity # of each message. prefix = " " # To make the messages look similar to the original LVM tools use: # indent = 0 # command_names = 1 # prefix = " -- " # Set this if you want log messages during activation. # Don't use this in low memory situations (can deadlock). # activation = 0 } # Configuration of metadata backups and archiving. In LVM2 when we # talk about a 'backup' we mean making a copy of the metadata for the # *current* system. The 'archive' contains old metadata configurations. # Backups are stored in a human readeable text format. backup { # Should we maintain a backup of the current metadata configuration ? # Use 1 for Yes; 0 for No. # Think very hard before turning this off! backup = 1 # Where shall we keep it ? # Remember to back up this directory regularly! backup_dir = "/etc/lvm/backup" # Should we maintain an archive of old metadata configurations. # Use 1 for Yes; 0 for No. # On by default. Think very hard before turning this off. archive = 1 # Where should archived files go ? # Remember to back up this directory regularly! archive_dir = "/etc/lvm/archive" # What is the minimum number of archive files you wish to keep ? retain_min = 10 # What is the minimum time you wish to keep an archive file for ? retain_days = 30 } # Settings for the running LVM2 in shell (readline) mode. shell { # Number of lines of history to store in ~/.lvm_history history_size = 100 } # Miscellaneous global LVM2 settings global { # The file creation mask for any files and directories created. # Interpreted as octal if the first digit is zero. umask = 077 # Allow other users to read the files #umask = 022 # Enabling test mode means that no changes to the on disk metadata # will be made. Equivalent to having the -t option on every # command. Defaults to off. test = 0 # Default value for --units argument units = "h" # Since version 2.02.54, the tools distinguish between powers of # 1024 bytes (e.g. KiB, MiB, GiB) and powers of 1000 bytes (e.g. # KB, MB, GB). # If you have scripts that depend on the old behaviour, set this to 0 # temporarily until you update them. si_unit_consistency = 1 # Whether or not to communicate with the kernel device-mapper. # Set to 0 if you want to use the tools to manipulate LVM metadata # without activating any logical volumes. # If the device-mapper kernel driver is not present in your kernel # setting this to 0 should suppress the error messages. activation = 1 # If we can't communicate with device-mapper, should we try running # the LVM1 tools? # This option only applies to 2.4 kernels and is provided to help you # switch between device-mapper kernels and LVM1 kernels. # The LVM1 tools need to be installed with .lvm1 suffices # e.g. vgscan.lvm1 and they will stop working after you start using # the new lvm2 on-disk metadata format. # The default value is set when the tools are built. # fallback_to_lvm1 = 0 # The default metadata format that commands should use - "lvm1" or "lvm2". # The command line override is -M1 or -M2. # Defaults to "lvm2". # format = "lvm2" # Location of proc filesystem proc = "/proc" # Type of locking to use. Defaults to local file-based locking (1). # Turn locking off by setting to 0 (dangerous: risks metadata corruption # if LVM2 commands get run concurrently). # Type 2 uses the external shared library locking_library. # Type 3 uses built-in clustered locking. # Type 4 uses read-only locking which forbids any operations that might # change metadata. locking_type = 1 # Set to 0 to fail when a lock request cannot be satisfied immediately. wait_for_locks = 1 # If using external locking (type 2) and initialisation fails, # with this set to 1 an attempt will be made to use the built-in # clustered locking. # If you are using a customised locking_library you should set this to 0. fallback_to_clustered_locking = 1 # If an attempt to initialise type 2 or type 3 locking failed, perhaps # because cluster components such as clvmd are not running, with this set # to 1 an attempt will be made to use local file-based locking (type 1). # If this succeeds, only commands against local volume groups will proceed. # Volume Groups marked as clustered will be ignored. fallback_to_local_locking = 1 # Local non-LV directory that holds file-based locks while commands are # in progress. A directory like /tmp that may get wiped on reboot is OK. locking_dir = "/var/lock/lvm" # Whenever there are competing read-only and read-write access requests for # a volume group's metadata, instead of always granting the read-only # requests immediately, delay them to allow the read-write requests to be # serviced. Without this setting, write access may be stalled by a high # volume of read-only requests. # NB. This option only affects locking_type = 1 viz. local file-based # locking. prioritise_write_locks = 1 # Other entries can go here to allow you to load shared libraries # e.g. if support for LVM1 metadata was compiled as a shared library use # format_libraries = "liblvm2format1.so" # Full pathnames can be given. # Search this directory first for shared libraries. # library_dir = "/lib" # The external locking library to load if locking_type is set to 2. # locking_library = "liblvm2clusterlock.so" # Treat any internal errors as fatal errors, aborting the process that # encountered the internal error. Please only enable for debugging. abort_on_internal_errors = 0 # Check whether CRC is matching when parsed VG is used multiple times. # This is useful to catch unexpected internal cached volume group # structure modification. Please only enable for debugging. detect_internal_vg_cache_corruption = 0 # If set to 1, no operations that change on-disk metadata will be permitted. # Additionally, read-only commands that encounter metadata in need of repair # will still be allowed to proceed exactly as if the repair had been # performed (except for the unchanged vg_seqno). # Inappropriate use could mess up your system, so seek advice first! metadata_read_only = 0 # 'mirror_segtype_default' defines which segtype will be used when the # shorthand '-m' option is used for mirroring. The possible options are: # # "mirror" - The original RAID1 implementation provided by LVM2/DM. It is # characterized by a flexible log solution (core, disk, mirrored) # and by the necessity to block I/O while reconfiguring in the # event of a failure. # # There is an inherent race in the dmeventd failure handling # logic with snapshots of devices using this type of RAID1 that # in the worst case could cause a deadlock. # Ref: https://bugzilla.redhat.com/show_bug.cgi?id=817130#c10 # # "raid1" - This implementation leverages MD's RAID1 personality through # device-mapper. It is characterized by a lack of log options. # (A log is always allocated for every device and they are placed # on the same device as the image - no separate devices are # required.) This mirror implementation does not require I/O # to be blocked in the kernel in the event of a failure. # This mirror implementation is not cluster-aware and cannot be # used in a shared (active/active) fashion in a cluster. # # Specify the '--type ' option to override this default # setting. mirror_segtype_default = "mirror" # The default format for displaying LV names in lvdisplay was changed # in version 2.02.89 to show the LV name and path separately. # Previously this was always shown as /dev/vgname/lvname even when that # was never a valid path in the /dev filesystem. # Set to 1 to reinstate the previous format. # # lvdisplay_shows_full_device_path = 0 # Whether to use (trust) a running instance of lvmetad. If this is set to # 0, all commands fall back to the usual scanning mechanisms. When set to 1 # *and* when lvmetad is running (it is not auto-started), the volume group # metadata and PV state flags are obtained from the lvmetad instance and no # scanning is done by the individual commands. In a setup with lvmetad, # lvmetad udev rules *must* be set up for LVM to work correctly. Without # proper udev rules, all changes in block device configuration will be # *ignored* until a manual 'vgscan' is performed. use_lvmetad = 0 } activation { # Set to 1 to perform internal checks on the operations issued to # libdevmapper. Useful for debugging problems with activation. # Some of the checks may be expensive, so it's best to use this # only when there seems to be a problem. checks = 0 # Set to 0 to disable udev synchronisation (if compiled into the binaries). # Processes will not wait for notification from udev. # They will continue irrespective of any possible udev processing # in the background. You should only use this if udev is not running # or has rules that ignore the devices LVM2 creates. # The command line argument --nodevsync takes precedence over this setting. # If set to 1 when udev is not running, and there are LVM2 processes # waiting for udev, run 'dmsetup udevcomplete_all' manually to wake them up. udev_sync = 1 # Set to 0 to disable the udev rules installed by LVM2 (if built with # --enable-udev_rules). LVM2 will then manage the /dev nodes and symlinks # for active logical volumes directly itself. # N.B. Manual intervention may be required if this setting is changed # while any logical volumes are active. udev_rules = 1 # Set to 1 for LVM2 to verify operations performed by udev. This turns on # additional checks (and if necessary, repairs) on entries in the device # directory after udev has completed processing its events. # Useful for diagnosing problems with LVM2/udev interactions. verify_udev_operations = 0 # If set to 1 and if deactivation of an LV fails, perhaps because # a process run from a quick udev rule temporarily opened the device, # retry the operation for a few seconds before failing. retry_deactivation = 1 # How to fill in missing stripes if activating an incomplete volume. # Using "error" will make inaccessible parts of the device return # I/O errors on access. You can instead use a device path, in which # case, that device will be used to in place of missing stripes. # But note that using anything other than "error" with mirrored # or snapshotted volumes is likely to result in data corruption. missing_stripe_filler = "error" # The linear target is an optimised version of the striped target # that only handles a single stripe. Set this to 0 to disable this # optimisation and always use the striped target. use_linear_target = 1 # How much stack (in KB) to reserve for use while devices suspended # Prior to version 2.02.89 this used to be set to 256KB reserved_stack = 64 # How much memory (in KB) to reserve for use while devices suspended reserved_memory = 8192 # Nice value used while devices suspended process_priority = -18 # If volume_list is defined, each LV is only activated if there is a # match against the list. # "vgname" and "vgname/lvname" are matched exactly. # "@tag" matches any tag set in the LV or VG. # "@*" matches if any tag defined on the host is also set in the LV or VG # # volume_list = [ "vg1", "vg2/lvol1", "@tag1", "@*" ] # If read_only_volume_list is defined, each LV that is to be activated # is checked against the list, and if it matches, it as activated # in read-only mode. (This overrides '--permission rw' stored in the # metadata.) # "vgname" and "vgname/lvname" are matched exactly. # "@tag" matches any tag set in the LV or VG. # "@*" matches if any tag defined on the host is also set in the LV or VG # # read_only_volume_list = [ "vg1", "vg2/lvol1", "@tag1", "@*" ] # Size (in KB) of each copy operation when mirroring mirror_region_size = 512 # Setting to use when there is no readahead value stored in the metadata. # # "none" - Disable readahead. # "auto" - Use default value chosen by kernel. readahead = "auto" # 'raid_fault_policy' defines how a device failure in a RAID logical # volume is handled. This includes logical volumes that have the following # segment types: raid1, raid4, raid5*, and raid6*. # # In the event of a failure, the following policies will determine what # actions are performed during the automated response to failures (when # dmeventd is monitoring the RAID logical volume) and when 'lvconvert' is # called manually with the options '--repair' and '--use-policies'. # # "warn" - Use the system log to warn the user that a device in the RAID # logical volume has failed. It is left to the user to run # 'lvconvert --repair' manually to remove or replace the failed # device. As long as the number of failed devices does not # exceed the redundancy of the logical volume (1 device for # raid4/5, 2 for raid6, etc) the logical volume will remain # usable. # # "allocate" - Attempt to use any extra physical volumes in the volume # group as spares and replace faulty devices. # raid_fault_policy = "warn" # 'mirror_image_fault_policy' and 'mirror_log_fault_policy' define # how a device failure affecting a mirror (of "mirror" segment type) is # handled. A mirror is composed of mirror images (copies) and a log. # A disk log ensures that a mirror does not need to be re-synced # (all copies made the same) every time a machine reboots or crashes. # # In the event of a failure, the specified policy will be used to determine # what happens. This applies to automatic repairs (when the mirror is being # monitored by dmeventd) and to manual lvconvert --repair when # --use-policies is given. # # "remove" - Simply remove the faulty device and run without it. If # the log device fails, the mirror would convert to using # an in-memory log. This means the mirror will not # remember its sync status across crashes/reboots and # the entire mirror will be re-synced. If a # mirror image fails, the mirror will convert to a # non-mirrored device if there is only one remaining good # copy. # # "allocate" - Remove the faulty device and try to allocate space on # a new device to be a replacement for the failed device. # Using this policy for the log is fast and maintains the # ability to remember sync state through crashes/reboots. # Using this policy for a mirror device is slow, as it # requires the mirror to resynchronize the devices, but it # will preserve the mirror characteristic of the device. # This policy acts like "remove" if no suitable device and # space can be allocated for the replacement. # # "allocate_anywhere" - Not yet implemented. Useful to place the log device # temporarily on same physical volume as one of the mirror # images. This policy is not recommended for mirror devices # since it would break the redundant nature of the mirror. This # policy acts like "remove" if no suitable device and space can # be allocated for the replacement. mirror_log_fault_policy = "allocate" mirror_image_fault_policy = "remove" # 'snapshot_autoextend_threshold' and 'snapshot_autoextend_percent' define # how to handle automatic snapshot extension. The former defines when the # snapshot should be extended: when its space usage exceeds this many # percent. The latter defines how much extra space should be allocated for # the snapshot, in percent of its current size. # # For example, if you set snapshot_autoextend_threshold to 70 and # snapshot_autoextend_percent to 20, whenever a snapshot exceeds 70% usage, # it will be extended by another 20%. For a 1G snapshot, using up 700M will # trigger a resize to 1.2G. When the usage exceeds 840M, the snapshot will # be extended to 1.44G, and so on. # # Setting snapshot_autoextend_threshold to 100 disables automatic # extensions. The minimum value is 50 (A setting below 50 will be treated # as 50). snapshot_autoextend_threshold = 100 snapshot_autoextend_percent = 20 # 'thin_pool_autoextend_threshold' and 'thin_pool_autoextend_percent' define # how to handle automatic pool extension. The former defines when the # pool should be extended: when its space usage exceeds this many # percent. The latter defines how much extra space should be allocated for # the pool, in percent of its current size. # # For example, if you set thin_pool_autoextend_threshold to 70 and # thin_pool_autoextend_percent to 20, whenever a pool exceeds 70% usage, # it will be extended by another 20%. For a 1G pool, using up 700M will # trigger a resize to 1.2G. When the usage exceeds 840M, the pool will # be extended to 1.44G, and so on. # # Setting thin_pool_autoextend_threshold to 100 disables automatic # extensions. The minimum value is 50 (A setting below 50 will be treated # as 50). thin_pool_autoextend_threshold = 100 thin_pool_autoextend_percent = 20 # Full path of the utility called to check that a thin metadata device # is in a state that allows it to be used. # Each time a thin pool needs to be activated, this utility is executed. # The activation will only proceed if the utility has an exit status of 0. # Set to "" to skip this check. (Not recommended.) # The thin tools are available as part of the device-mapper-persistent-data # package from https://github.com/jthornber/thin-provisioning-tools. # thin_check_executable = "/usr/sbin/thin_check" # String with options passed with thin_check command. By default, # option '-q' is for quiet output. thin_check_options = [ "-q" ] # While activating devices, I/O to devices being (re)configured is # suspended, and as a precaution against deadlocks, LVM2 needs to pin # any memory it is using so it is not paged out. Groups of pages that # are known not to be accessed during activation need not be pinned # into memory. Each string listed in this setting is compared against # each line in /proc/self/maps, and the pages corresponding to any # lines that match are not pinned. On some systems locale-archive was # found to make up over 80% of the memory used by the process. # mlock_filter = [ "locale/locale-archive", "gconv/gconv-modules.cache" ] # Set to 1 to revert to the default behaviour prior to version 2.02.62 # which used mlockall() to pin the whole process's memory while activating # devices. use_mlockall = 0 # Monitoring is enabled by default when activating logical volumes. # Set to 0 to disable monitoring or use the --ignoremonitoring option. monitoring = 1 # When pvmove or lvconvert must wait for the kernel to finish # synchronising or merging data, they check and report progress # at intervals of this number of seconds. The default is 15 seconds. # If this is set to 0 and there is only one thing to wait for, there # are no progress reports, but the process is awoken immediately the # operation is complete. polling_interval = 15 } #################### # Advanced section # #################### # Metadata settings # # metadata { # Default number of copies of metadata to hold on each PV. 0, 1 or 2. # You might want to override it from the command line with 0 # when running pvcreate on new PVs which are to be added to large VGs. # pvmetadatacopies = 1 # Default number of copies of metadata to maintain for each VG. # If set to a non-zero value, LVM automatically chooses which of # the available metadata areas to use to achieve the requested # number of copies of the VG metadata. If you set a value larger # than the the total number of metadata areas available then # metadata is stored in them all. # The default value of 0 ("unmanaged") disables this automatic # management and allows you to control which metadata areas # are used at the individual PV level using 'pvchange # --metadataignore y/n'. # vgmetadatacopies = 0 # Approximate default size of on-disk metadata areas in sectors. # You should increase this if you have large volume groups or # you want to retain a large on-disk history of your metadata changes. # pvmetadatasize = 255 # List of directories holding live copies of text format metadata. # These directories must not be on logical volumes! # It's possible to use LVM2 with a couple of directories here, # preferably on different (non-LV) filesystems, and with no other # on-disk metadata (pvmetadatacopies = 0). Or this can be in # addition to on-disk metadata areas. # The feature was originally added to simplify testing and is not # supported under low memory situations - the machine could lock up. # # Never edit any files in these directories by hand unless you # you are absolutely sure you know what you are doing! Use # the supplied toolset to make changes (e.g. vgcfgrestore). # dirs = [ "/etc/lvm/metadata", "/mnt/disk2/lvm/metadata2" ] #} # Event daemon # dmeventd { # mirror_library is the library used when monitoring a mirror device. # # "libdevmapper-event-lvm2mirror.so" attempts to recover from # failures. It removes failed devices from a volume group and # reconfigures a mirror as necessary. If no mirror library is # provided, mirrors are not monitored through dmeventd. mirror_library = "libdevmapper-event-lvm2mirror.so" # snapshot_library is the library used when monitoring a snapshot device. # # "libdevmapper-event-lvm2snapshot.so" monitors the filling of # snapshots and emits a warning through syslog when the use of # the snapshot exceeds 80%. The warning is repeated when 85%, 90% and # 95% of the snapshot is filled. snapshot_library = "libdevmapper-event-lvm2snapshot.so" # thin_library is the library used when monitoring a thin device. # # "libdevmapper-event-lvm2thin.so" monitors the filling of # pool and emits a warning through syslog when the use of # the pool exceeds 80%. The warning is repeated when 85%, 90% and # 95% of the pool is filled. thin_library = "libdevmapper-event-lvm2thin.so" # Full path of the dmeventd binary. # # executable = "/sbin/dmeventd" } --=-2o1faoBEooenegpWZfdA Content-Disposition: attachment; filename="vmstat.rh5.txt" Content-Type: text/plain; name="vmstat.rh5.txt"; charset="UTF-8" Content-Transfer-Encoding: 7bit procs -----------memory---------- ---swap-- -----io---- --system-- -----cpu------ r b swpd free buff cache si so bi bo in cs us sy id wa st 1 0 12 260348 44008 10917540 0 0 8 124 0 0 8 1 90 0 0 0 0 12 259000 44020 10920880 0 0 22 4308 1747 4974 1 1 98 0 0 0 0 12 258808 44024 10922932 0 0 3 3419 1687 4453 1 0 99 0 0 0 0 12 254744 44036 10925876 0 0 37 3237 1545 2962 1 0 99 0 0 0 0 12 253172 44044 10927272 0 0 3 2401 1686 4460 1 0 99 0 0 0 0 12 251724 44052 10929436 0 0 48 3643 1545 3113 0 0 99 0 0 0 0 12 251680 44060 10930668 0 0 19 2130 1673 4354 1 0 99 0 0 1 0 12 248208 44076 10932328 0 0 18 2879 1544 3201 1 1 98 0 0 1 0 12 245156 44088 10935136 0 0 19 12653 1794 4943 5 0 95 0 0 0 0 12 243324 44092 10938956 0 0 38 3929 1575 2785 1 0 98 1 0 0 0 12 250824 44076 10930140 0 0 22 3346 1670 4509 1 0 99 0 0 0 0 12 250964 44092 10932452 0 0 85 4113 1591 2816 0 0 99 0 0 --=-2o1faoBEooenegpWZfdA Content-Disposition: attachment; filename="iostat.rh5.txt" Content-Type: text/plain; name="iostat.rh5.txt"; charset="UTF-8" Content-Transfer-Encoding: 7bit Linux 2.6.18-308.el5 (bc290bprdb-01.lhr4.prod.booking.com) 03/06/2013 Device: rrqm/s wrqm/s r/s w/s rMB/s wMB/s avgrq-sz avgqu-sz await svctm %util cciss/c0d0 6.95 27.09 7.72 270.96 0.19 2.90 22.71 0.07 0.25 0.22 6.00 cciss/c0d0p1 0.00 0.00 0.00 0.00 0.00 0.00 47.62 0.00 1.69 1.61 0.00 cciss/c0d0p2 0.00 0.00 0.00 0.00 0.00 0.00 14.40 0.00 4.07 4.06 0.00 cciss/c0d0p3 6.94 27.09 7.72 270.96 0.19 2.90 22.71 0.07 0.25 0.22 6.00 dm-0 0.00 0.00 0.45 32.85 0.01 0.13 8.34 0.02 0.49 0.07 0.24 dm-1 0.00 0.00 6.97 264.13 0.15 2.77 22.10 0.07 0.24 0.22 5.93 Device: rrqm/s wrqm/s r/s w/s rMB/s wMB/s avgrq-sz avgqu-sz await svctm %util cciss/c0d0 0.00 22.40 0.80 334.40 0.01 2.75 16.89 0.02 0.06 0.06 2.02 cciss/c0d0p1 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 cciss/c0d0p2 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 cciss/c0d0p3 0.00 22.40 0.80 334.40 0.01 2.75 16.89 0.02 0.06 0.06 2.02 dm-0 0.00 0.00 0.00 27.20 0.00 0.11 8.00 0.00 0.03 0.01 0.04 dm-1 0.00 0.00 0.80 329.60 0.01 2.65 16.47 0.02 0.06 0.06 1.96 Device: rrqm/s wrqm/s r/s w/s rMB/s wMB/s avgrq-sz avgqu-sz await svctm %util cciss/c0d0 0.00 25.80 0.60 275.60 0.01 2.13 15.89 0.02 0.06 0.05 1.44 cciss/c0d0p1 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 cciss/c0d0p2 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 cciss/c0d0p3 0.00 25.80 0.60 275.60 0.01 2.13 15.89 0.02 0.06 0.05 1.44 dm-0 0.00 0.00 0.00 28.80 0.00 0.11 8.00 0.00 0.10 0.03 0.08 dm-1 0.00 0.00 0.60 272.60 0.01 2.02 15.23 0.01 0.05 0.05 1.36 Device: rrqm/s wrqm/s r/s w/s rMB/s wMB/s avgrq-sz avgqu-sz await svctm %util cciss/c0d0 0.00 89.22 13.37 389.82 0.21 3.26 17.60 0.10 0.25 0.24 9.72 cciss/c0d0p1 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 cciss/c0d0p2 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 cciss/c0d0p3 0.00 89.22 13.37 389.82 0.21 3.26 17.60 0.10 0.25 0.24 9.72 dm-0 0.00 0.00 0.00 122.95 0.00 0.48 8.00 0.03 0.25 0.02 0.22 dm-1 0.00 0.00 13.37 356.09 0.21 2.78 16.54 0.10 0.26 0.26 9.68 Device: rrqm/s wrqm/s r/s w/s rMB/s wMB/s avgrq-sz avgqu-sz await svctm %util cciss/c0d0 0.00 14.80 1.20 303.60 0.02 2.88 19.48 0.02 0.07 0.06 1.76 cciss/c0d0p1 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 cciss/c0d0p2 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 cciss/c0d0p3 0.00 14.80 1.20 303.60 0.02 2.88 19.48 0.02 0.07 0.06 1.76 dm-0 0.00 0.00 0.00 18.40 0.00 0.07 8.00 0.00 0.21 0.05 0.10 dm-1 0.00 0.00 1.20 300.00 0.02 2.81 19.22 0.02 0.07 0.06 1.74 Device: rrqm/s wrqm/s r/s w/s rMB/s wMB/s avgrq-sz avgqu-sz await svctm %util cciss/c0d0 0.00 38.20 1.00 339.80 0.02 2.91 17.55 0.02 0.05 0.05 1.82 cciss/c0d0p1 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 cciss/c0d0p2 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 cciss/c0d0p3 0.00 38.20 1.00 339.80 0.02 2.91 17.55 0.02 0.05 0.05 1.82 dm-0 0.00 0.00 0.00 43.00 0.00 0.17 8.00 0.01 0.33 0.02 0.08 dm-1 0.00 0.00 1.00 335.00 0.02 2.74 16.78 0.02 0.05 0.05 1.80 Device: rrqm/s wrqm/s r/s w/s rMB/s wMB/s avgrq-sz avgqu-sz await svctm %util cciss/c0d0 0.00 17.20 0.20 296.40 0.00 2.16 14.96 0.01 0.05 0.04 1.22 cciss/c0d0p1 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 cciss/c0d0p2 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 cciss/c0d0p3 0.00 17.20 0.20 296.40 0.00 2.16 14.96 0.01 0.05 0.04 1.22 dm-0 0.00 0.00 0.00 20.80 0.00 0.08 8.00 0.02 0.92 0.06 0.12 dm-1 0.00 0.00 0.20 292.80 0.00 2.08 14.58 0.01 0.04 0.04 1.18 Device: rrqm/s wrqm/s r/s w/s rMB/s wMB/s avgrq-sz avgqu-sz await svctm %util cciss/c0d0 0.00 16.80 1.60 309.20 0.02 2.62 17.42 0.02 0.07 0.06 1.90 cciss/c0d0p1 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 cciss/c0d0p2 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 cciss/c0d0p3 0.00 16.80 1.60 309.20 0.02 2.62 17.42 0.02 0.07 0.06 1.90 dm-0 0.00 0.00 0.00 21.00 0.00 0.08 8.00 0.00 0.14 0.03 0.06 dm-1 0.00 0.00 1.60 305.00 0.02 2.54 17.11 0.02 0.06 0.06 1.78 Device: rrqm/s wrqm/s r/s w/s rMB/s wMB/s avgrq-sz avgqu-sz await svctm %util cciss/c0d0 0.00 35.20 3.00 309.20 0.05 2.27 15.20 0.03 0.11 0.10 3.20 cciss/c0d0p1 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 cciss/c0d0p2 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 cciss/c0d0p3 0.00 35.20 3.00 309.20 0.05 2.27 15.20 0.03 0.11 0.10 3.20 dm-0 0.00 0.00 0.00 40.20 0.00 0.16 8.00 0.02 0.48 0.02 0.10 dm-1 0.00 0.00 3.00 304.20 0.05 2.11 14.40 0.03 0.10 0.10 3.16 Device: rrqm/s wrqm/s r/s w/s rMB/s wMB/s avgrq-sz avgqu-sz await svctm %util cciss/c0d0 0.00 29.80 0.80 325.60 0.01 2.76 17.37 0.01 0.04 0.04 1.44 cciss/c0d0p1 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 cciss/c0d0p2 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 cciss/c0d0p3 0.00 29.80 0.80 325.60 0.01 2.76 17.37 0.01 0.04 0.04 1.44 dm-0 0.00 0.00 0.00 35.60 0.00 0.14 8.00 0.00 0.02 0.01 0.04 dm-1 0.00 0.00 0.80 319.80 0.01 2.62 16.79 0.01 0.05 0.05 1.48 Device: rrqm/s wrqm/s r/s w/s rMB/s wMB/s avgrq-sz avgqu-sz await svctm %util cciss/c0d0 0.00 81.00 1.40 311.40 0.02 2.53 16.73 0.03 0.10 0.10 3.00 cciss/c0d0p1 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 cciss/c0d0p2 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 cciss/c0d0p3 0.00 81.00 1.40 311.40 0.02 2.53 16.73 0.03 0.10 0.10 3.00 dm-0 0.00 0.00 0.00 114.00 0.00 0.45 8.00 0.04 0.34 0.01 0.16 dm-1 0.00 0.00 1.40 278.40 0.02 2.09 15.45 0.03 0.11 0.11 2.94 Device: rrqm/s wrqm/s r/s w/s rMB/s wMB/s avgrq-sz avgqu-sz await svctm %util cciss/c0d0 0.00 39.00 15.40 334.80 0.24 3.38 21.17 0.11 0.31 0.28 9.72 cciss/c0d0p1 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 cciss/c0d0p2 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 cciss/c0d0p3 0.00 39.00 15.40 334.80 0.24 3.38 21.17 0.11 0.31 0.28 9.72 dm-0 0.00 0.00 0.00 43.80 0.00 0.17 8.00 0.02 0.41 0.04 0.16 dm-1 0.00 0.00 15.40 330.00 0.24 3.21 20.45 0.11 0.31 0.28 9.56 --=-2o1faoBEooenegpWZfdA Content-Disposition: attachment; filename="vmstat.rh6.txt" Content-Type: text/plain; name="vmstat.rh6.txt"; charset="UTF-8" Content-Transfer-Encoding: 7bit procs -----------memory---------- ---swap-- -----io---- --system-- -----cpu----- r b swpd free buff cache si so bi bo in cs us sy id wa st 2 0 0 502436 176348 44540116 0 0 10 1223 5 1 1 0 99 0 0 1 0 0 497348 176352 44541280 0 0 142 58031 2661 4424 3 0 97 0 0 1 0 0 486996 176360 44543584 0 0 105 43446 2563 3963 1 0 98 0 0 0 0 0 487388 176364 44545004 0 0 144 47756 1235 2889 0 0 99 0 0 0 0 0 481700 176372 44546044 0 0 87 40935 1719 3091 0 0 99 0 0 0 0 0 483400 176376 44546948 0 0 95 44988 1366 3021 0 0 99 0 0 0 0 0 484440 176376 44547944 0 0 16 33223 929 2255 0 0 100 0 0 0 0 0 483852 176380 44549140 0 0 186 40805 1288 2661 0 0 99 0 0 0 0 0 487676 176380 44544424 0 0 134 36696 2530 3300 0 1 99 0 0 2 0 0 487456 176380 44545240 0 0 40 35708 1589 3353 2 0 98 0 0 1 0 0 486604 176380 44546864 0 0 106 56364 1855 3779 2 0 98 0 0 0 0 0 485236 176380 44547916 0 0 63 41737 1310 2801 0 0 99 0 0 --=-2o1faoBEooenegpWZfdA Content-Disposition: attachment; filename="iostat.rh6.txt" Content-Type: text/plain; name="iostat.rh6.txt"; charset="UTF-8" Content-Transfer-Encoding: 7bit Linux 2.6.32-279.1.1.el6.x86_64 (bc291bprdb-01.lhr4.prod.booking.com) 03/06/2013 _x86_64_ (32 CPU) Device: rrqm/s wrqm/s r/s w/s rMB/s wMB/s avgrq-sz avgqu-sz await svctm %util sda 0.06 355.36 14.52 337.78 0.32 38.17 223.75 0.28 0.81 0.28 9.79 dm-0 0.00 0.00 0.39 17.27 0.01 0.07 8.86 0.03 1.50 0.07 0.13 dm-1 0.00 0.00 14.14 675.89 0.31 38.11 114.01 1.41 2.04 0.14 9.76 Device: rrqm/s wrqm/s r/s w/s rMB/s wMB/s avgrq-sz avgqu-sz await svctm %util sda 0.00 3.60 6.00 374.40 0.06 44.18 238.17 0.11 0.28 0.16 6.08 dm-0 0.00 0.00 0.00 4.40 0.00 0.02 8.00 0.00 0.27 0.18 0.08 dm-1 0.00 0.00 6.00 373.20 0.06 44.11 238.56 0.11 0.28 0.16 6.04 Device: rrqm/s wrqm/s r/s w/s rMB/s wMB/s avgrq-sz avgqu-sz await svctm %util sda 0.00 1.80 8.40 307.00 0.07 35.49 230.89 0.11 0.33 0.18 5.58 dm-0 0.00 0.00 0.00 5.20 0.00 0.02 8.00 0.00 0.04 0.04 0.02 dm-1 0.00 0.00 8.40 304.00 0.07 35.52 233.31 0.11 0.34 0.18 5.64 Device: rrqm/s wrqm/s r/s w/s rMB/s wMB/s avgrq-sz avgqu-sz await svctm %util sda 0.00 36.60 1.80 339.60 0.02 39.29 235.83 0.08 0.23 0.16 5.54 dm-0 0.00 0.00 0.00 40.60 0.00 0.16 8.00 0.25 6.11 0.03 0.14 dm-1 0.00 0.00 1.80 335.20 0.02 39.08 237.64 0.06 0.18 0.16 5.44 Device: rrqm/s wrqm/s r/s w/s rMB/s wMB/s avgrq-sz avgqu-sz await svctm %util sda 0.00 11.20 7.20 297.20 0.07 34.37 231.68 0.08 0.25 0.15 4.66 dm-0 0.00 0.00 0.00 13.60 0.00 0.05 8.00 0.01 0.51 0.03 0.04 dm-1 0.00 0.00 7.20 294.80 0.07 34.31 233.16 0.08 0.25 0.16 4.70 Device: rrqm/s wrqm/s r/s w/s rMB/s wMB/s avgrq-sz avgqu-sz await svctm %util sda 0.00 21.80 72.20 401.20 0.90 46.25 203.97 0.64 1.35 0.34 15.86 dm-0 0.00 0.00 0.00 24.60 0.00 0.10 8.00 0.01 0.27 0.02 0.04 dm-1 0.00 0.00 72.20 398.40 0.90 46.15 204.77 0.64 1.36 0.34 15.96 Device: rrqm/s wrqm/s r/s w/s rMB/s wMB/s avgrq-sz avgqu-sz await svctm %util sda 0.00 8.60 0.80 314.60 0.01 36.05 234.19 0.05 0.17 0.15 4.80 dm-0 0.00 0.00 0.00 13.80 0.00 0.05 8.00 0.00 0.23 0.01 0.02 dm-1 0.00 0.00 0.80 309.40 0.01 36.00 237.76 0.05 0.16 0.16 4.82 Device: rrqm/s wrqm/s r/s w/s rMB/s wMB/s avgrq-sz avgqu-sz await svctm %util sda 0.00 8.40 11.60 326.20 0.08 38.22 232.19 0.19 0.56 0.23 7.62 dm-0 0.00 0.00 0.00 16.80 0.00 0.07 8.00 0.00 0.01 0.01 0.02 dm-1 0.00 0.00 11.60 318.40 0.08 38.21 237.62 0.19 0.58 0.23 7.70 Device: rrqm/s wrqm/s r/s w/s rMB/s wMB/s avgrq-sz avgqu-sz await svctm %util sda 0.00 3.20 1.80 304.00 0.03 34.85 233.55 0.05 0.18 0.15 4.54 dm-0 0.00 0.00 0.00 6.20 0.00 0.02 8.00 0.00 0.26 0.16 0.10 dm-1 0.00 0.00 1.80 300.40 0.03 34.77 235.79 0.05 0.18 0.15 4.56 Device: rrqm/s wrqm/s r/s w/s rMB/s wMB/s avgrq-sz avgqu-sz await svctm %util sda 0.00 5.60 15.00 354.60 0.18 41.34 230.08 0.17 0.47 0.26 9.64 dm-0 0.00 0.00 0.00 7.00 0.00 0.03 8.00 0.00 0.23 0.17 0.12 dm-1 0.00 0.00 15.00 353.20 0.18 41.31 230.81 0.18 0.48 0.26 9.62 Device: rrqm/s wrqm/s r/s w/s rMB/s wMB/s avgrq-sz avgqu-sz await svctm %util sda 0.00 47.00 4.20 315.40 0.02 36.54 234.33 0.09 0.29 0.19 6.08 dm-0 0.00 0.00 0.00 52.60 0.00 0.21 8.00 0.01 0.26 0.01 0.06 dm-1 0.00 0.00 4.20 309.80 0.02 36.34 237.17 0.09 0.29 0.19 6.08 Device: rrqm/s wrqm/s r/s w/s rMB/s wMB/s avgrq-sz avgqu-sz await svctm %util sda 0.00 6.00 7.40 337.60 0.15 38.87 231.63 0.11 0.31 0.23 7.96 dm-0 0.00 0.00 0.00 8.40 0.00 0.03 8.00 0.00 0.02 0.02 0.02 dm-1 0.00 0.00 7.40 335.20 0.15 38.84 233.06 0.11 0.31 0.23 8.00 --=-2o1faoBEooenegpWZfdA-- From rwheeler@redhat.com Wed Mar 6 08:26:03 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 131DB7F69 for ; Wed, 6 Mar 2013 08:26:03 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay1.corp.sgi.com (Postfix) with ESMTP id E7E428F8037 for ; Wed, 6 Mar 2013 06:25:59 -0800 (PST) X-ASG-Debug-ID: 1362579958-04cbb07dbe206140001-NocioJ Received: from mx1.redhat.com (mx1.redhat.com [209.132.183.28]) by cuda.sgi.com with ESMTP id lzM8HXqFQ7KbJR0z for ; Wed, 06 Mar 2013 06:25:59 -0800 (PST) X-Barracuda-Envelope-From: rwheeler@redhat.com X-Barracuda-Apparent-Source-IP: 209.132.183.28 X-ASG-Whitelist: Client Received: from int-mx10.intmail.prod.int.phx2.redhat.com (int-mx10.intmail.prod.int.phx2.redhat.com [10.5.11.23]) by mx1.redhat.com (8.14.4/8.14.4) with ESMTP id r26EPw4J021363 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=OK); Wed, 6 Mar 2013 09:25:58 -0500 Received: from tunkums.home (ovpn-112-33.phx2.redhat.com [10.3.112.33]) by int-mx10.intmail.prod.int.phx2.redhat.com (8.14.4/8.14.4) with ESMTP id r26EPtpv025558; Wed, 6 Mar 2013 09:25:56 -0500 Message-ID: <513751F2.2060109@redhat.com> Date: Wed, 06 Mar 2013 09:25:54 -0500 From: Ric Wheeler User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:17.0) Gecko/20130219 Thunderbird/17.0.3 MIME-Version: 1.0 To: Supratik Goswami CC: Shrinath M , Sabyasachi Ruj , Vivek Goel , xfs@oss.sgi.com Subject: Re: XFS filesystem on EC2 instance corrupts and shuts down References: <51373DB8.2020707@redhat.com> <51373FC1.6010101@redhat.com> X-ASG-Orig-Subj: Re: XFS filesystem on EC2 instance corrupts and shuts down In-Reply-To: Content-Type: text/plain; charset=ISO-8859-1; format=flowed Content-Transfer-Encoding: 7bit X-Scanned-By: MIMEDefang 2.68 on 10.5.11.23 X-Barracuda-Connect: mx1.redhat.com[209.132.183.28] X-Barracuda-Start-Time: 1362579959 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 I would suggest contacting Amazon's customer support channel (or the vendor you paid for the Linux instance you are running). XFS developer list is probably not the correct forum to help you debug this :) Good luck! Ric On 03/06/2013 08:12 AM, Supratik Goswami wrote: > Have we created a ticket with AWS ? > > It could be an EBS issue who knows, we need to confirm that first. > > -- > Warm Regards > > Supratik > > > On Wed, Mar 6, 2013 at 6:38 PM, Ric Wheeler > wrote: > > On 03/06/2013 08:03 AM, Shrinath M wrote: > > > On Wed, Mar 6, 2013 at 6:29 PM, Ric Wheeler >> wrote: > > I think that you would need to verify that the Amazon storage is not > throwing errors - do your logs show IO errors or issues before XFS > hits an > issue? > > > No IO errors in /var/log/messages. > Where else should I be looking? > > > > Feb 12 19:47:18 ip-100-0-100-1 kernel: [2541168.023638] XFS (md0): I/O > Error Detected. Shutting down filesystem > > Is an IO error from MD. > > I would suggest trying to reproduce without MD in the picture first - > always best to try to reproduce with the simplest setup first and work > your way up the complexity ladder, > > Ric > > > > > _______________________________________________ > xfs mailing list > xfs@oss.sgi.com > http://oss.sgi.com/mailman/listinfo/xfs From hpj@urpla.net Wed Mar 6 08:55:52 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 157BF7F3F for ; Wed, 6 Mar 2013 08:55:52 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay1.corp.sgi.com (Postfix) with ESMTP id E278F8F80A1 for ; Wed, 6 Mar 2013 06:55:51 -0800 (PST) X-ASG-Debug-ID: 1362581746-04cb6c2b021feed0001-NocioJ Received: from moutng.kundenserver.de (moutng.kundenserver.de [212.227.17.9]) by cuda.sgi.com with ESMTP id t6l6ltbWA0fxGkJy (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Wed, 06 Mar 2013 06:55:47 -0800 (PST) X-Barracuda-Envelope-From: hpj@urpla.net X-Barracuda-Apparent-Source-IP: 212.227.17.9 Received: from lisa (p5B2A49B7.dip0.t-ipconnect.de [91.42.73.183]) by mrelayeu.kundenserver.de (node=mrbap0) with ESMTP (Nemesis) id 0Lf0SV-1UZgCN3p4J-00qWVu; Wed, 06 Mar 2013 15:55:45 +0100 Received: from localhost (localhost [127.0.0.1]) by tyrex.lisa.loc (Postfix) with ESMTP id 7E3151B971B00; Wed, 6 Mar 2013 15:55:37 +0100 (CET) X-Virus-Scanned: amavisd-new at lisa.loc Received: from tyrex.lisa.loc ([127.0.0.1]) by localhost (tyrex.lisa.loc [127.0.0.1]) (amavisd-new, port 10024) with LMTP id sOxW4iPjCDAW; Wed, 6 Mar 2013 15:55:21 +0100 (CET) From: Hans-Peter Jansen To: david@fromorbit.com Cc: xfs@oss.sgi.com Subject: Fwd: xfs_reno Date: Wed, 06 Mar 2013 15:55:19 +0100 X-ASG-Orig-Subj: Fwd: xfs_reno Message-ID: <20351675.Zy117sIl8Z@xrated> User-Agent: KMail/4.9.5 (Linux/3.4.28-2.20-desktop; KDE/4.9.5; x86_64; ; ) MIME-Version: 1.0 Content-Type: multipart/mixed; boundary="nextPart1386822.l1ojNFhaiW" Content-Transfer-Encoding: 7Bit X-Provags-ID: V02:K0:FRVTgXptI8h+cMSR+gJjamNpF7WGe4r5lrry/izXCSP wxQBol6kVCFISLwWA4twpqZ6G72Bu+in59ZrpJ67/KiCz6hRdk WO22pMMktJnT2ZEudzNqbTWYrMsQWfY2JVW1xyVhPn0koc/vqT W6l6b6+Ddhkzss9GBlQ64AMHC3AKvkKlOq3+zbvLhrHRiqWBL1 h5R4t877nifIXEVC1im0UdEkcyU2HFGwu3N4VmtlJupVMjk/L6 M38vNDaWbN5Md/rDnjbxgyXSQAtQ09BudBwDadLVbQs7Cy4LY9 x0MULKjvV6RxKaJjVz8fJes5jgO7adKELIhmfg5ydlTgrL/iQ= = X-Barracuda-Connect: moutng.kundenserver.de[212.227.17.9] X-Barracuda-Start-Time: 1362581747 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_MISMATCH_TO, INFO_TLD X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124424 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 BSF_SC0_MISMATCH_TO Envelope rcpt doesn't match header 0.00 INFO_TLD URI: Contains an URL in the INFO top-level domain This is a multi-part message in MIME format. --nextPart1386822.l1ojNFhaiW Content-Transfer-Encoding: quoted-printable Content-Type: text/plain; charset="utf-8" Hi Dave, I tried to gather Barrys SOB, but failed so far. His trace ends in 2009= google=20 wise. How is this case usually handled? Here's the current state of things. Cheers, Pete ---------- Weitergeleitete Nachricht ---------- Betreff: xfs_reno Datum: Mittwoch, 6. M=C3=A4rz 2013, 12:52:19 Von: Hans-Peter Jansen An: bnaujok@sgi.com Hi Barry, attached is a slightly mangled version of your xfs_reno tool, that I ba= dly=20 needed recently. While at it, I plan to submit it, as it saved my *ss. = Thanks. Apart from relocation to xfsprogs, I just changed this + log_message(LOG_DEBUG, "%s: %llu %lu %s", msg, node->ino, + node->numpaths, node->paths[0]); from %llu to %lu for the node->numpaths argument. It might still be wro= ng, as=20 numpath is defined as nlink_t which is a __u32 type, but the %s printed= =20 garbage like this: Scanning directory tree... xfs_reno: add_node_path: ino 8611163235, path=20 /work/dlbase/hosts/11.2/pico/var/run/screens xfs_reno: add_node_path: ino 8611163233, path=20 /work/dlbase/hosts/11.2/pico/var/run/pcscd/pcscd.events xfs_reno: add_node_path: ino 8611163234, path=20 /work/dlbase/hosts/11.2/pico/var/run/uscreens xfs_reno: nodehash: 8611163233 692488159933497345 =EF=BF=BD=EF=BF=BD]=EF= =BF=BD=EF=BF=BDf=EF=BF=BDe=EF=BF=BD xfs_reno: nodehash: 8611163234 692366801337581569 =EF=BF=BD=EF=BF=BD]=EF= =BF=BD=EF=BF=BDf=EF=BF=BDe=EF=BF=BD xfs_reno: nodehash: 8611163235 692223830466232321 =EF=BF=BD=EF=BF=BD]=EF= =BF=BD=EF=BF=BDf=EF=BF=BDe=EF=BF=BD I guess, gcc is smart enough to see, that the struct members overlap he= re, and=20 prints the paths[0] argument as a %llu value. What do you think? Anyway, I will revise this during the course of creating a xlstests tes= t for=20 xfs_reno... Do you allow me to add your Signed-off-by to this patch? If you want to build this, apply both patches to xfsprogs. TIA, Pete ------------------------------------------------------------- --nextPart1386822.l1ojNFhaiW Content-Disposition: attachment; filename="xfsprogs-xfs_reno.diff" Content-Transfer-Encoding: 7Bit Content-Type: text/x-patch; charset="utf-8"; name="xfsprogs-xfs_reno.diff" From: "Barry Naujok" Date: 2007-10-04 4:25:16 Message-ID: op.tznnweh23jf8g2 () pc-bnaujok ! melbourne ! sgi ! com The attached tool allows an inode64 filesystem to be converted to inode32. For this to work, the filesystem has to be mounted inode32 before it's run. Second version including these changes: - Major one is that symlinks are now supported, but only owner, group and extended attributes are copied for them (not times or inode attributes). - Man page! See: http://marc.info/?l=linux-xfs&m=119130906204596&w=2 http://marc.info/?l=linux-xfs&m=119147190705051&w=2 Relocated to xfsprogs and other minor adjustments by H.P. Jansen. Tested-by: Hans-Peter Jansen Index: b/man/man8/xfs_reno.8 =================================================================== --- /dev/null +++ b/man/man8/xfs_reno.8 @@ -0,0 +1,117 @@ +.TH xfs_reno 8 +.SH NAME +xfs_reno \- renumber XFS inodes +.SH SYNOPSIS +.B xfs_reno +[ +.B \-fnpqv +] [ +.B \-P +.I interval +] +.I path +.br +.B xfs_reno \-r +.I recover_file +.SH DESCRIPTION +.B xfs_reno +is applicable only to XFS filesystems. +.PP +.B xfs_reno +renumbers inodes. XFS supports 64-bit inode numbers, although by +default it will avoid creating inodes with numbers greater than +what can be contained within a 32-bit number. If a filesystem does +contain inode numbers greater than 32-bits, then this can conflict with +applications that do not support them. +To recover from this situation previously, affected files would need +to be copied (and so get a new inode number) and the old version +removed. This can be time consuming and impractical for very large +files and filesystems. +.B xfs_reno +can be used to renumber such inodes quickly. +.B xfs_reno +will copy the inodes of affected files and move the data from the old +inode to the new without having to copy the data. +.B xfs_reno +relies on XFS in the kernel to allocate a new inode number, so if the +filesystem has been mounted with the +.I inode64 +mount option, the new inodes will quite possibly have inode numbers +greater than 32-bits. +.PP +.B xfs_reno +should only be used on a filesystem where it is necessary to +renumber inodes. Use of +.B xfs_reno +on a regular basis is +.IR "not recommended" . +Apart from application compatibility, there is no particular advantage +to be had from renumbering inodes. +.PP +.B xfs_reno +works by traversing a directory tree, scanning all the directories +and noting which files require renumbering. Once the scanning phase +is done, it will process the appropriate files and directories. The +directory's absolute pathname must be given to +.BR xfs_reno . +The following options are accepted by +.BR xfs_reno . +.TP +.B \-f +Force conversion on all inodes, rather than just those with a 64-bit +inode number. This is not particularly useful except for debugging +purposes. +.TP +.B \-n +Do nothing, perform a trial run. +.TP +.B \-v +Increases the verbosity of progress and error messages. Additional +.BR \-v 's +can be used to further increase verbosity. +.TP +.B \-q +Do not report progress, only errors. +.TP +.B \-p +Show progress status. +.TP +.BI \-P " seconds" +Set the interval for the progress status in seconds. The default is 1 +second. +.TP +.B \-r +Recover from an interrupted run. If +.B xfs_reno +is interrupted, it will leave a file called +.I xfs_reno.recover +in the directory specified on the command line. This file will +contain enough information so that +.B xfs_reno +can either finish processing the file it was working on when +interrupted or back out the last change it made, depending on how far +through the process it had progressed. +.B xfs_reno +will only recover the single file it was working on so it will need +to be run again on the directory to be sure that all the appropriate +inodes have been converted. +.SH EXAMPLES +To renumber inodes with 64-bit inode numbers: +.IP +.B # xfs_reno -p /path/to/directory +.PP +To recover from an interrupted run: +.IP +.B # xfs_reno -r /path/to/directory/xfs_reno.recover +.PP +.SH FILES +.PD +.TP +.I /path/xfs_reno.recover +records the state where renumbering was interrupted. +.PD +.SH SEE ALSO +.BR xfs_fsr (8), +.BR xfs_ncheck (8), +.BR fstab (5), +.BR xfs (5). Index: b/reno/Makefile =================================================================== --- /dev/null +++ b/reno/Makefile @@ -0,0 +1,19 @@ +# +# Copyright (c) 2007 Silicon Graphics, Inc. All Rights Reserved. +# + +TOPDIR = .. +include $(TOPDIR)/include/builddefs + +LTCOMMAND = xfs_reno +CFILES = xfs_reno.c +LLDLIBS = $(LIBATTR) + +default: $(LTCOMMAND) + +include $(BUILDRULES) + +install: default + $(INSTALL) -m 755 -d $(PKG_SBIN_DIR) + $(LTINSTALL) -m 755 $(LTCOMMAND) $(PKG_SBIN_DIR) +install-dev: Index: b/reno/xfs_reno.c =================================================================== --- /dev/null +++ b/reno/xfs_reno.c @@ -0,0 +1,2040 @@ +/* + * Copyright (c) 2007 Silicon Graphics, Inc. + * All Rights Reserved. + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License as + * published by the Free Software Foundation. + * + * This program is distributed in the hope that it would be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + */ + +/* + * xfs_reno - renumber 64-bit inodes + * + * xfs_reno [-f] [-n] [-p] [-q] [-v] [-P seconds] path ... + * xfs_reno [-r] path ... + * + * Renumbers all inodes > 32 bits into 32 bit space. Requires the filesytem + * to be mounted with inode32. + * + * -f force conversion on all inodes rather than just + * those with a 64bit inode number. + * -n nothing, do not renumber inodes + * -p show progress status. + * -q quiet, do not report progress, only errors. + * -v verbose, more -v's more verbose. + * -P seconds set the interval for the progress status in seconds. + * -r recover from an interrupted run. + */ + +#include + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#define ATTRBUFSIZE 1024 + +#define SCAN_PHASE 0x00 +#define DIR_PHASE 0x10 /* nothing done or all done */ +#define DIR_PHASE_1 0x11 /* target dir created */ +#define DIR_PHASE_2 0x12 /* temp dir created */ +#define DIR_PHASE_3 0x13 /* attributes backed up to temp */ +#define DIR_PHASE_4 0x14 /* dirents moved to target dir */ +#define DIR_PHASE_5 0x15 /* attributes applied to target dir */ +#define DIR_PHASE_6 0x16 /* src dir removed */ +#define DIR_PHASE_7 0x17 /* temp dir removed */ +#define DIR_PHASE_MAX 0x17 +#define FILE_PHASE 0x20 /* nothing done or all done */ +#define FILE_PHASE_1 0x21 /* temp file created */ +#define FILE_PHASE_2 0x22 /* swapped extents */ +#define FILE_PHASE_3 0x23 /* unlinked source */ +#define FILE_PHASE_4 0x24 /* renamed temp to source name */ +#define FILE_PHASE_MAX 0x24 +#define SLINK_PHASE 0x30 /* nothing done or all done */ +#define SLINK_PHASE_1 0x31 /* temp symlink created */ +#define SLINK_PHASE_2 0x32 /* symlink attrs copied */ +#define SLINK_PHASE_3 0x33 /* unlinked source */ +#define SLINK_PHASE_4 0x34 /* renamed temp to source name */ +#define SLINK_PHASE_MAX 0x34 + +static void update_recoverfile(void); +#define SET_PHASE(x) (cur_phase = x, update_recoverfile()) + +#define LOG_ERR 0 +#define LOG_NORMAL 1 +#define LOG_INFO 2 +#define LOG_DEBUG 3 +#define LOG_NITTY 4 + +#define NH_BUCKETS 65536 +#define NH_HASH(ino) (nodehash + ((ino) % NH_BUCKETS)) + +typedef struct { + xfs_ino_t ino; + int ftw_flags; + nlink_t numpaths; + char **paths; +} bignode_t; + +typedef struct { + bignode_t *nodes; + uint64_t listlen; + uint64_t lastnode; +} nodelist_t; + +static const char *cmd_prefix = "xfs_reno_"; + +static char *progname; +static int log_level = LOG_NORMAL; +static int force_all; +static nodelist_t *nodehash; +static int realuid; +static uint64_t numdirnodes; +static uint64_t numfilenodes; +static uint64_t numslinknodes; +static uint64_t numdirsdone; +static uint64_t numfilesdone; +static uint64_t numslinksdone; +static int poll_interval; +static time_t starttime; +static bignode_t *cur_node; +static char *cur_target; +static char *cur_temp; +static int cur_phase; +static int highest_numpaths; +static char *recover_file; +static int recover_fd; +static volatile int poll_output; +static int global_rval; + +/* + * message handling + */ +static void +log_message( + int level, + char *fmt, ...) +{ + char buf[1024]; + va_list ap; + + if (log_level < level) + return; + + va_start(ap, fmt); + vsnprintf(buf, 1024, fmt, ap); + va_end(ap); + + printf("%c%s: %s\n", poll_output ? '\n' : '\r', progname, buf); + poll_output = 0; +} + +static void +err_message( + char *fmt, ...) +{ + char buf[1024]; + va_list ap; + + va_start(ap, fmt); + vsnprintf(buf, 1024, fmt, ap); + va_end(ap); + + fprintf(stderr, "%c%s: %s\n", poll_output ? '\n' : '\r', progname, buf); + poll_output = 0; +} + +static void +err_nomem(void) +{ + err_message(_("Out of memory")); +} + +static void +err_open( + const char *s) +{ + err_message(_("Cannot open %s: %s"), s, strerror(errno)); +} + +static void +err_not_xfs( + const char *s) +{ + err_message(_("%s is not on an XFS filesystem"), s); +} + +static void +err_stat( + const char *s) +{ + err_message(_("Cannot stat %s: %s\n"), s, strerror(errno)); +} + +/* + * usage message + */ +static void +usage(void) +{ + fprintf(stderr, _("%s [-fnpqv] [-P ] [-r] \n"), + progname); + exit(1); +} + + +/* + * XFS interface functions + */ + +static int +xfs_bulkstat_single(int fd, xfs_ino_t *lastip, xfs_bstat_t *ubuffer) +{ + xfs_fsop_bulkreq_t bulkreq; + + bulkreq.lastip = (__u64 *)lastip; + bulkreq.icount = 1; + bulkreq.ubuffer = ubuffer; + bulkreq.ocount = NULL; + return ioctl(fd, XFS_IOC_FSBULKSTAT_SINGLE, &bulkreq); +} + +static int +xfs_swapext(int fd, xfs_swapext_t *sx) +{ + return ioctl(fd, XFS_IOC_SWAPEXT, sx); +} + +static int +xfs_getxattr(int fd, struct fsxattr *attr) +{ + return ioctl(fd, XFS_IOC_FSGETXATTR, attr); +} + +static int +xfs_setxattr(int fd, struct fsxattr *attr) +{ + return ioctl(fd, XFS_IOC_FSSETXATTR, attr); +} + +/* + * A hash table of inode numbers and associated paths. + */ +static nodelist_t * +init_nodehash(void) +{ + int i; + + nodehash = calloc(NH_BUCKETS, sizeof(nodelist_t)); + if (nodehash == NULL) { + err_nomem(); + return NULL; + } + + for (i = 0; i < NH_BUCKETS; i++) { + nodehash[i].nodes = NULL; + nodehash[i].lastnode = 0; + nodehash[i].listlen = 0; + } + + return nodehash; +} + +static void +free_nodehash(void) +{ + int i, j, k; + + for (i = 0; i < NH_BUCKETS; i++) { + bignode_t *nodes = nodehash[i].nodes; + + for (j = 0; j < nodehash[i].lastnode; j++) { + for (k = 0; k < nodes[j].numpaths; k++) { + free(nodes[j].paths[k]); + } + free(nodes[j].paths); + } + + free(nodes); + } + free(nodehash); +} + +static nlink_t +add_path( + bignode_t *node, + const char *path) +{ + node->paths = realloc(node->paths, + sizeof(char *) * (node->numpaths + 1)); + if (node->paths == NULL) { + err_nomem(); + exit(1); + } + + node->paths[node->numpaths] = strdup(path); + if (node->paths[node->numpaths] == NULL) { + err_nomem(); + exit(1); + } + + node->numpaths++; + if (node->numpaths > highest_numpaths) + highest_numpaths = node->numpaths; + + return node->numpaths; +} + +static bignode_t * +add_node( + nodelist_t *list, + xfs_ino_t ino, + int ftw_flags, + const char *path) +{ + bignode_t *node; + + if (list->lastnode >= list->listlen) { + list->listlen += 500; + list->nodes = realloc(list->nodes, + sizeof(bignode_t) * list->listlen); + if (list->nodes == NULL) { + err_nomem(); + return NULL; + } + } + + node = list->nodes + list->lastnode; + + node->ino = ino; + node->ftw_flags = ftw_flags; + node->paths = NULL; + node->numpaths = 0; + add_path(node, path); + + list->lastnode++; + + return node; +} + +static bignode_t * +find_node( + xfs_ino_t ino) +{ + int i; + nodelist_t *nodelist; + bignode_t *nodes; + + nodelist = NH_HASH(ino); + nodes = nodelist->nodes; + + for(i = 0; i < nodelist->lastnode; i++) { + if (nodes[i].ino == ino) { + return &nodes[i]; + } + } + + return NULL; +} + +static bignode_t * +add_node_path( + xfs_ino_t ino, + int ftw_flags, + const char *path) +{ + nodelist_t *nodelist; + bignode_t *node; + + log_message(LOG_NITTY, "add_node_path: ino %llu, path %s", ino, path); + + node = find_node(ino); + if (node == NULL) { + nodelist = NH_HASH(ino); + return add_node(nodelist, ino, ftw_flags, path); + } + + add_path(node, path); + return node; +} + +static void +dump_node( + char *msg, + bignode_t *node) +{ + int k; + + if (log_level < LOG_DEBUG) + return; + + log_message(LOG_DEBUG, "%s: %llu %lu %s", msg, node->ino, + node->numpaths, node->paths[0]); + + for (k = 1; k < node->numpaths; k++) + log_message(LOG_DEBUG, "\t%s", node->paths[k]); +} + +static void +dump_nodehash(void) +{ + int i, j; + + if (log_level < LOG_NITTY) + return; + + for (i = 0; i < NH_BUCKETS; i++) { + bignode_t *nodes = nodehash[i].nodes; + for (j = 0; j < nodehash[i].lastnode; j++, nodes++) + dump_node("nodehash", nodes); + } +} + +static int +for_all_nodes( + int (*fn)(bignode_t *node), + int ftw_flags, + int quit_on_error) +{ + int i; + int j; + int rval = 0; + + for (i = 0; i < NH_BUCKETS; i++) { + bignode_t *nodes = nodehash[i].nodes; + + for (j = 0; j < nodehash[i].lastnode; j++, nodes++) { + if (nodes->ftw_flags == ftw_flags) { + rval = fn(nodes); + if (rval && quit_on_error) + goto quit; + } + } + } + +quit: + return rval; +} + +/* + * Adds appropriate files to the inode hash table + */ +static int +nftw_addnodes( + const char *path, + const struct stat64 *st, + int flags, + struct FTW *sntfw) +{ + if (st->st_ino <= XFS_MAXINUMBER_32 && !force_all) + return 0; + + if (flags == FTW_F) + numfilenodes++; + else if (flags == FTW_D) + numdirnodes++; + else if (flags == FTW_SL) + numslinknodes++; + else + return 0; + + add_node_path(st->st_ino, flags, path); + + return 0; +} + +/* + * Attribute cloning code - most of this is here because attr_copy does not + * let us pick and choose which attributes we want to copy. + */ + +attr_multiop_t attr_ops[ATTR_MAX_MULTIOPS]; + +/* + * Grab attributes specified in attr_ops from source file and write them + * out on the destination file. + */ + +static int +attr_replicate( + char *source, + char *target, + int count) +{ + int j, k; + + if (attr_multi(source, attr_ops, count, ATTR_DONTFOLLOW) < 0) + return -1; + + for (k = 0; k < count; k++) { + if (attr_ops[k].am_error) { + err_message(_("Error %d getting attribute"), + attr_ops[k].am_error); + break; + } + attr_ops[k].am_opcode = ATTR_OP_SET; + } + if (attr_multi(target, attr_ops, k, ATTR_DONTFOLLOW) < 0) + err_message("on attr_multif set"); + for (j = 0; j < k; j++) { + if (attr_ops[j].am_error) { + err_message(_("Error %d setting attribute"), + attr_ops[j].am_error); + return -1; + } + } + + return 0; +} + +/* + * Copy all the attributes specified from src to dst. + */ + +static int +attr_clone_copy( + char *source, + char *target, + char *list_buf, + char *attr_buf, + int buf_len, + int flags) +{ + attrlist_t *alist; + attrlist_ent_t *attr; + attrlist_cursor_t cursor; + int space, i, j; + char *ptr; + + bzero((char *)&cursor, sizeof(cursor)); + do { + if (attr_list(source, list_buf, ATTRBUFSIZE, + flags | ATTR_DONTFOLLOW, &cursor) < 0) { + err_message("on attr_listf"); + return -1; + } + + alist = (attrlist_t *)list_buf; + + space = buf_len; + ptr = attr_buf; + for (j = 0, i = 0; i < alist->al_count; i++) { + attr = ATTR_ENTRY(list_buf, i); + if (space < attr->a_valuelen) { + if (attr_replicate(source, target, j) < 0) + return -1; + j = 0; + space = buf_len; + ptr = attr_buf; + } + attr_ops[j].am_opcode = ATTR_OP_GET; + attr_ops[j].am_attrname = attr->a_name; + attr_ops[j].am_attrvalue = ptr; + attr_ops[j].am_length = (int) attr->a_valuelen; + attr_ops[j].am_flags = flags; + attr_ops[j].am_error = 0; + j++; + ptr += attr->a_valuelen; + space -= attr->a_valuelen; + } + + log_message(LOG_NITTY, "copying attribute %d", i); + + if (j) { + if (attr_replicate(source, target, j) < 0) + return -1; + } + + } while (alist->al_more); + + return 0; +} + +static int +clone_attribs( + char *source, + char *target) +{ + char list_buf[ATTRBUFSIZE]; + char *attr_buf; + int rval; + + attr_buf = malloc(ATTR_MAX_VALUELEN * 2); + if (attr_buf == NULL) { + err_nomem(); + return -1; + } + rval = attr_clone_copy(source, target, list_buf, attr_buf, + ATTR_MAX_VALUELEN * 2, 0); + if (rval == 0) + rval = attr_clone_copy(source, target, list_buf, attr_buf, + ATTR_MAX_VALUELEN * 2, ATTR_ROOT); + if (rval == 0) + rval = attr_clone_copy(source, target, list_buf, attr_buf, + ATTR_MAX_VALUELEN * 2, ATTR_SECURE); + free(attr_buf); + return rval; +} + +static int +dup_attributes( + char *source, + int sfd, + char *target, + int tfd) +{ + struct stat64 st; + struct timeval tv[2]; + struct fsxattr fsx; + + if (fstat64(sfd, &st) < 0) { + err_stat(source); + return -1; + } + + if (xfs_getxattr(sfd, &fsx) < 0) { + err_stat(source); + return -1; + } + + tv[0].tv_sec = st.st_atim.tv_sec; + tv[0].tv_usec = st.st_atim.tv_nsec / 1000; + tv[1].tv_sec = st.st_mtim.tv_sec; + tv[1].tv_usec = st.st_mtim.tv_nsec / 1000; + + if (futimes(tfd, tv) < 0) + err_message(_("%s: Cannot update target times"), target); + + if (fchown(tfd, st.st_uid, st.st_gid) < 0) { + err_message(_("%s: Cannot change target ownership to " + "uid(%d) gid(%d)"), target, + st.st_uid, st.st_gid); + + if (fchmod(tfd, st.st_mode & ~(S_ISUID | S_ISGID)) < 0) + err_message(_("%s: Cannot change target mode " + "to (%o)"), target, st.st_mode); + } else if (fchmod(tfd, st.st_mode) < 0) + err_message(_("%s: Cannot change target mode to (%o)"), + target, st.st_mode); + + if (xfs_setxattr(tfd, &fsx) < 0) + err_message(_("%s: Cannet set target extended " + "attributes"), target); + + return clone_attribs(source, target); +} + +static int +move_dirents( + char *srcpath, + char *targetpath, + int *move_count) +{ + int rval = 0; + DIR *srcd; + struct dirent64 *dp; + char srcname[PATH_MAX]; + char targetname[PATH_MAX]; + + *move_count = 0; + + srcd = opendir(srcpath); + if (srcd == NULL) { + err_open(srcpath); + return 1; + } + + while ((dp = readdir64(srcd)) != NULL) { + if (dp->d_ino == 0 || !strcmp(dp->d_name, ".") || + !strcmp(dp->d_name, "..")) + continue; + + if (strlen(srcpath) + 1 + strlen(dp->d_name) >= + sizeof(srcname) - 1) { + + err_message(_("%s/%s: Name too long"), srcpath, + dp->d_name); + rval = 1; + goto quit; + } + + sprintf(srcname, "%s/%s", srcpath, dp->d_name); + sprintf(targetname, "%s/%s", targetpath, dp->d_name); + + rval = rename(srcname, targetname); + if (rval != 0) { + err_message(_("failed to rename: \'%s\' to \'%s\'"), + srcname, targetname); + goto quit; + } + + log_message(LOG_DEBUG, "rename %s -> %s", srcname, targetname); + + (*move_count)++; + } + +quit: + closedir(srcd); + return rval; +} + +static int +process_dir( + bignode_t *node) +{ + int sfd = -1; + int tfd = -1; + int targetfd = -1; + int rval = 0; + int move_count = 0; + char *srcname = NULL; + char *pname = NULL; + struct stat64 s1; + struct fsxattr fsx; + char target[PATH_MAX] = ""; + + SET_PHASE(DIR_PHASE); + + dump_node("directory", node); + + cur_node = node; + srcname = node->paths[0]; + + if (stat64(srcname, &s1) < 0) { + if (errno != ENOENT) { + err_stat(srcname); + global_rval |= 2; + } + goto quit; + } + if (s1.st_ino <= XFS_MAXINUMBER_32 && !force_all) { + /* + * This directory has already changed ino's, probably due + * to being moved during processing of a parent directory. + */ + log_message(LOG_DEBUG, "process_dir: skipping %s", srcname); + goto quit; + } + + rval = 1; + + sfd = open(srcname, O_RDONLY); + if (sfd < 0) { + err_open(srcname); + goto quit; + } + + if (!platform_test_xfs_fd(sfd)) { + err_not_xfs(srcname); + goto quit; + } + + if (xfs_getxattr(sfd, &fsx) < 0) { + err_message(_("failed to get inode attrs: %s"), srcname); + goto quit; + } + if (fsx.fsx_xflags & (XFS_XFLAG_IMMUTABLE | XFS_XFLAG_APPEND)) { + err_message(_("%s: immutable/append, ignoring"), srcname); + global_rval |= 2; + rval = 0; + goto quit; + } + + /* mkdir parent/target */ + pname = strdup(srcname); + if (pname == NULL) { + err_nomem(); + goto quit; + } + dirname(pname); + sprintf(target, "%s/%sXXXXXX", pname, cmd_prefix); + if (mkdtemp(target) == NULL) { + err_message(_("Unable to create directory copy: %s"), srcname); + goto quit; + } + SET_PHASE(DIR_PHASE_1); + + cur_target = strdup(target); + if (!cur_target) { + err_nomem(); + goto quit; + } + + sprintf(target, "%s/%sXXXXXX", pname, cmd_prefix); + if (mkdtemp(target) == NULL) { + err_message(_("unable to create tmp directory copy")); + goto quit; + } + SET_PHASE(DIR_PHASE_2); + + cur_temp = strdup(target); + if (!cur_temp) { + err_nomem(); + goto quit; + } + + tfd = open(cur_temp, O_RDONLY); + if (tfd < 0) { + err_open(cur_temp); + goto quit; + } + + targetfd = open(cur_target, O_RDONLY); + if (tfd < 0) { + err_open(cur_target); + goto quit; + } + + + /* copy timestamps, attribs and EAs, to cur_temp */ + rval = dup_attributes(srcname, sfd, cur_temp, tfd); + if (rval != 0) { + err_message(_("unable to duplicate directory attributes: %s"), + srcname); + goto quit_unlink; + } + + SET_PHASE(DIR_PHASE_3); + + /* move src dirents to cur_target (this changes timestamps on src) */ + rval = move_dirents(srcname, cur_target, &move_count); + if (rval != 0) { + err_message(_("unable to move directory contents: %s to %s"), + srcname, cur_target); + /* uh oh, move everything back... */ + if (move_count > 0) + goto quit_undo; + } + + SET_PHASE(DIR_PHASE_4); + + /* copy timestamps, attribs and EAs from cur_temp to cur_target */ + rval = dup_attributes(cur_temp, tfd, cur_target, targetfd); + if (rval != 0) { + err_message(_("unable to duplicate directory attributes: %s"), + cur_temp); + goto quit_unlink; + } + + SET_PHASE(DIR_PHASE_5); + + /* rmdir src */ + rval = rmdir(srcname); + if (rval != 0) { + err_message(_("unable to remove directory: %s"), srcname); + goto quit_undo; + } + + SET_PHASE(DIR_PHASE_6); + + rval = rmdir(cur_temp); + if (rval != 0) + err_message(_("unable to remove tmp directory: %s"), cur_temp); + + SET_PHASE(DIR_PHASE_7); + + /* rename cur_target src */ + rval = rename(cur_target, srcname); + if (rval != 0) { + /* + * we can't abort since the src dir is now gone. + * let the admin clean this one up + */ + err_message(_("unable to rename directory: %s to %s"), + cur_target, srcname); + } + goto quit; + + quit_undo: + if (move_dirents(cur_target, srcname, &move_count) != 0) { + /* oh, dear lord... let the admin clean this one up */ + err_message(_("unable to move directory contents back: %s to %s"), + cur_target, srcname); + goto quit; + } + SET_PHASE(DIR_PHASE_3); + + quit_unlink: + rmdir(cur_target); + rmdir(cur_temp); + + quit: + + SET_PHASE(DIR_PHASE); + + if (sfd >= 0) + close(sfd); + if (tfd >= 0) + close(tfd); + if (targetfd >= 0) + close(targetfd); + + free(pname); + free(cur_target); + free(cur_temp); + + cur_target = NULL; + cur_temp = NULL; + cur_node = NULL; + numdirsdone++; + return rval; +} + +static int +process_file( + bignode_t *node) +{ + int sfd = -1; + int tfd = -1; + int i = 0; + int rval = 0; + struct stat64 s1; + char *srcname = NULL; + char *pname = NULL; + xfs_swapext_t sx; + xfs_bstat_t bstatbuf; + struct fsxattr fsx; + char target[PATH_MAX] = ""; + + SET_PHASE(FILE_PHASE); + + dump_node("file", node); + + cur_node = node; + srcname = node->paths[0]; + + bzero(&s1, sizeof(s1)); + bzero(&bstatbuf, sizeof(bstatbuf)); + bzero(&sx, sizeof(sx)); + + if (stat64(srcname, &s1) < 0) { + if (errno != ENOENT) { + err_stat(srcname); + global_rval |= 2; + } + goto quit; + } + if (s1.st_ino <= XFS_MAXINUMBER_32 && !force_all) + /* this file has changed, and no longer needs processing */ + goto quit; + + /* open and sync source */ + sfd = open(srcname, O_RDWR | O_DIRECT); + if (sfd < 0) { + err_open(srcname); + rval = 1; + goto quit; + } + if (!platform_test_xfs_fd(sfd)) { + err_not_xfs(srcname); + rval = 1; + goto quit; + } + if (fsync(sfd) < 0) { + err_message(_("sync failed: %s: %s"), + srcname, strerror(errno)); + rval = 1; + goto quit; + } + + + /* + * Check if a mandatory lock is set on the file to try and + * avoid blocking indefinitely on the reads later. Note that + * someone could still set a mandatory lock after this check + * but before all reads have completed to block xfs_reno reads. + * This change just closes the window a bit. + */ + if ((s1.st_mode & S_ISGID) && !(s1.st_mode & S_IXGRP)) { + struct flock fl; + + fl.l_type = F_RDLCK; + fl.l_whence = SEEK_SET; + fl.l_start = (off_t)0; + fl.l_len = 0; + if (fcntl(sfd, F_GETLK, &fl) < 0 ) { + if (log_level >= LOG_DEBUG) + err_message("locking check failed: %s", + srcname); + global_rval |= 2; + goto quit; + } + if (fl.l_type != F_UNLCK) { + if (log_level >= LOG_DEBUG) + err_message("mandatory lock: %s: ignoring", + srcname); + global_rval |= 2; + goto quit; + } + } + + if (xfs_getxattr(sfd, &fsx) < 0) { + err_message(_("failed to get inode attrs: %s"), srcname); + rval = 1; + goto quit; + } + if (fsx.fsx_xflags & (XFS_XFLAG_IMMUTABLE | XFS_XFLAG_APPEND)) { + err_message(_("%s: immutable/append, ignoring"), srcname); + global_rval |= 2; + goto quit; + } + + rval = 1; + + if (realuid != 0 && realuid != s1.st_uid) { + errno = EACCES; + err_open(srcname); + goto quit; + } + + /* creat target */ + pname = strdup(srcname); + if (pname == NULL) { + err_nomem(); + goto quit; + } + dirname(pname); + sprintf(target, "%s/%sXXXXXX", pname, cmd_prefix); + tfd = mkstemp(target); + if (tfd < 0) { + err_message("unable to create file copy"); + goto quit; + } + cur_target = strdup(target); + if (cur_target == NULL) { + err_nomem(); + goto quit; + } + + SET_PHASE(FILE_PHASE_1); + + /* Setup direct I/O */ + if (fcntl(tfd, F_SETFL, O_DIRECT) < 0 ) { + err_message(_("could not set O_DIRECT for %s on tmp: %s"), + srcname, target); + unlink(target); + goto quit; + } + + /* copy attribs & EAs to target */ + if (dup_attributes(srcname, sfd, target, tfd) != 0) { + err_message(_("unable to duplicate file attributes: %s"), + srcname); + unlink(target); + goto quit; + } + + if (xfs_bulkstat_single(sfd, &s1.st_ino, &bstatbuf) < 0) { + err_message(_("unable to bulkstat source file: %s"), + srcname); + unlink(target); + goto quit; + } + + if (bstatbuf.bs_ino != s1.st_ino) { + err_message(_("bulkstat of source file returned wrong inode: %s"), + srcname); + unlink(target); + goto quit; + } + + ftruncate64(tfd, bstatbuf.bs_size); + + /* swapextents src target */ + sx.sx_stat = bstatbuf; /* struct copy */ + sx.sx_version = XFS_SX_VERSION; + sx.sx_fdtarget = sfd; + sx.sx_fdtmp = tfd; + sx.sx_offset = 0; + sx.sx_length = bstatbuf.bs_size; + + /* Swap the extents */ + rval = xfs_swapext(sfd, &sx); + if (rval < 0) { + if (log_level >= LOG_DEBUG) { + switch (errno) { + case ENOTSUP: + err_message("%s: file type not supported", + srcname); + break; + case EFAULT: + /* The file has changed since we started the copy */ + err_message("%s: file modified, " + "inode renumber aborted: %ld", + srcname, bstatbuf.bs_size); + break; + case EBUSY: + /* Timestamp has changed or mmap'ed file */ + err_message("%s: file busy", srcname); + break; + default: + err_message(_("Swap extents failed: %s: %s"), + srcname, strerror(errno)); + break; + } + } else + err_message(_("Swap extents failed: %s: %s"), + srcname, strerror(errno)); + goto quit; + } + + if (bstatbuf.bs_dmevmask | bstatbuf.bs_dmstate) { + struct fsdmidata fssetdm; + + /* Set the DMAPI Fields. */ + fssetdm.fsd_dmevmask = bstatbuf.bs_dmevmask; + fssetdm.fsd_padding = 0; + fssetdm.fsd_dmstate = bstatbuf.bs_dmstate; + + if (ioctl(tfd, XFS_IOC_FSSETDM, (void *)&fssetdm ) < 0) + err_message(_("attempt to set DMI attributes " + "of %s failed"), target); + } + + SET_PHASE(FILE_PHASE_2); + + /* unlink src */ + rval = unlink(srcname); + if (rval != 0) { + err_message(_("unable to remove file: %s"), srcname); + goto quit; + } + + SET_PHASE(FILE_PHASE_3); + + /* rename target src */ + rval = rename(target, srcname); + if (rval != 0) { + /* + * we can't abort since the src file is now gone. + * let the admin clean this one up + */ + err_message(_("unable to rename file: %s to %s"), + target, srcname); + goto quit; + } + + SET_PHASE(FILE_PHASE_4); + + /* for each hardlink, unlink and creat pointing to target */ + for (i = 1; i < node->numpaths; i++) { + /* unlink src */ + rval = unlink(node->paths[i]); + if (rval != 0) { + err_message(_("unable to remove file: %s"), + node->paths[i]); + goto quit; + } + + rval = link(srcname, node->paths[i]); + if (rval != 0) { + err_message("unable to link to file: %s", srcname); + goto quit; + } + numfilesdone++; + } + + quit: + cur_node = NULL; + + SET_PHASE(FILE_PHASE); + + if (sfd >= 0) + close(sfd); + if (tfd >= 0) + close(tfd); + + free(pname); + free(cur_target); + + cur_target = NULL; + + numfilesdone++; + return rval; +} + + +static int +process_slink( + bignode_t *node) +{ + int i = 0; + int rval = 0; + struct stat64 st; + char *srcname = NULL; + char *pname = NULL; + char target[PATH_MAX] = ""; + char linkbuf[PATH_MAX]; + + SET_PHASE(SLINK_PHASE); + + dump_node("symlink", node); + + cur_node = node; + srcname = node->paths[0]; + + if (lstat64(srcname, &st) < 0) { + if (errno != ENOENT) { + err_stat(srcname); + global_rval |= 2; + } + goto quit; + } + if (st.st_ino <= XFS_MAXINUMBER_32 && !force_all) + /* this file has changed, and no longer needs processing */ + goto quit; + + rval = 1; + + i = readlink(srcname, linkbuf, sizeof(linkbuf) - 1); + if (i < 0) { + err_message(_("unable to read symlink: %s"), srcname); + goto quit; + } + linkbuf[i] = '\0'; + + if (realuid != 0 && realuid != st.st_uid) { + errno = EACCES; + err_open(srcname); + goto quit; + } + + /* create target */ + pname = strdup(srcname); + if (pname == NULL) { + err_nomem(); + goto quit; + } + dirname(pname); + + sprintf(target, "%s/%sXXXXXX", pname, cmd_prefix); + if (mktemp(target) == NULL) { + err_message(_("unable to create temp symlink name")); + goto quit; + } + cur_target = strdup(target); + if (cur_target == NULL) { + err_nomem(); + goto quit; + } + + if (symlink(linkbuf, target) != 0) { + err_message(_("unable to create symlink: %s"), target); + goto quit; + } + + SET_PHASE(SLINK_PHASE_1); + + /* copy ownership & EAs to target */ + if (lchown(target, st.st_uid, st.st_gid) < 0) { + err_message(_("%s: Cannot change target ownership to " + "uid(%d) gid(%d)"), target, + st.st_uid, st.st_gid); + unlink(target); + goto quit; + } + + if (clone_attribs(srcname, target) != 0) { + err_message(_("unable to duplicate symlink attributes: %s"), + srcname); + unlink(target); + goto quit; + } + + SET_PHASE(SLINK_PHASE_2); + + /* unlink src */ + rval = unlink(srcname); + if (rval != 0) { + err_message(_("unable to remove symlink: %s"), srcname); + goto quit; + } + + SET_PHASE(SLINK_PHASE_3); + + /* rename target src */ + rval = rename(target, srcname); + if (rval != 0) { + /* + * we can't abort since the src file is now gone. + * let the admin clean this one up + */ + err_message(_("unable to rename symlink: %s to %s"), + target, srcname); + goto quit; + } + + SET_PHASE(SLINK_PHASE_4); + + /* for each hardlink, unlink and creat pointing to target */ + for (i = 1; i < node->numpaths; i++) { + /* unlink src */ + rval = unlink(node->paths[i]); + if (rval != 0) { + err_message(_("unable to remove symlink: %s"), + node->paths[i]); + goto quit; + } + + rval = link(srcname, node->paths[i]); + if (rval != 0) { + err_message("unable to link to symlink: %s", srcname); + goto quit; + } + numslinksdone++; + } + + quit: + cur_node = NULL; + + SET_PHASE(SLINK_PHASE); + + free(pname); + free(cur_target); + + cur_target = NULL; + + numslinksdone++; + return rval; +} + +static int +open_recoverfile(void) +{ + recover_fd = open(recover_file, O_RDWR | O_SYNC | O_CREAT | O_EXCL, + 0600); + if (recover_fd < 0) { + if (errno == EEXIST) + err_message(_("Recovery file already exists, either " + "run '%s -r %s' or remove the file."), + progname, recover_file); + else + err_open(recover_file); + return 1; + } + + if (!platform_test_xfs_fd(recover_fd)) { + err_not_xfs(recover_file); + close(recover_fd); + return 1; + } + + return 0; +} + +static void +update_recoverfile(void) +{ + static const char null_file[] = "0\n0\n0\n\ntarget: \ntemp: \nend\n"; + static size_t buf_size = 0; + static char *buf = NULL; + int i, len; + + if (recover_fd <= 0) + return; + + if (cur_node == NULL || cur_phase == 0) { + /* inbetween processing or still scanning */ + lseek(recover_fd, 0, SEEK_SET); + write(recover_fd, null_file, sizeof(null_file)); + return; + } + + ASSERT(highest_numpaths > 0); + if (buf == NULL) { + buf_size = (highest_numpaths + 3) * PATH_MAX; + buf = malloc(buf_size); + if (buf == NULL) { + err_nomem(); + exit(1); + } + } + + len = sprintf(buf, "%d\n%llu\n%d\n", cur_phase, + (long long)cur_node->ino, cur_node->ftw_flags); + + for (i = 0; i < cur_node->numpaths; i++) + len += sprintf(buf + len, "%s\n", cur_node->paths[i]); + + len += sprintf(buf + len, "target: %s\ntemp: %s\nend\n", + cur_target, cur_temp); + + ASSERT(len < buf_size); + + lseek(recover_fd, 0, SEEK_SET); + ftruncate(recover_fd, 0); + write(recover_fd, buf, len); +} + +static void +cleanup(void) +{ + log_message(LOG_NORMAL, _("Interrupted -- cleaning up...")); + + free_nodehash(); + + log_message(LOG_NORMAL, _("Done.")); +} + +static void +sighandler(int sig) +{ + static char cycle[4] = "-\\|/"; + static uint64_t cur_cycle = 0; + double percent; + char *typename; + uint64_t nodes, done; + + alarm(0); + + if (sig != SIGALRM) { + cleanup(); + exit(1); + } + + if (cur_phase == SCAN_PHASE) { + if (log_level >= LOG_INFO) + fprintf(stderr, _("\r%llu files, %llu dirs and %llu " + "symlinks to renumber found... %c"), + (long long)numfilenodes, + (long long)numdirnodes, + (long long)numslinknodes, + cycle[cur_cycle % 4]); + else + fprintf(stderr, "\r%c", + cycle[cur_cycle % 4]); + cur_cycle++; + } else { + if (cur_phase >= DIR_PHASE && cur_phase <= DIR_PHASE_MAX) { + nodes = numdirnodes; + done = numdirsdone; + typename = _("dirs"); + } else + if (cur_phase >= FILE_PHASE && cur_phase <= FILE_PHASE_MAX) { + nodes = numfilenodes; + done = numfilesdone; + typename = _("files"); + } else { + nodes = numslinknodes; + done = numslinksdone; + typename = _("symlinks"); + } + percent = 100.0 * (double)done / (double)nodes; + if (percent > 100.0) + percent = 100.0; + if (log_level >= LOG_INFO) + fprintf(stderr, _("\r%.1f%%, %llu of %llu %s, " + "%u seconds elapsed"), percent, + (long long)done, (long long)nodes, + typename, (int)(time(0) - starttime)); + else + fprintf(stderr, "\r%.1f%%", percent); + } + poll_output = 1; + signal(SIGALRM, sighandler); + + if (poll_interval) + alarm(poll_interval); +} + +static int +read_recover_file( + char *recover_file, + bignode_t **node, + char **target, + char **temp, + int *phase) +{ + FILE *file; + int rval = 1; + ino_t ino; + int ftw_flags; + char buf[PATH_MAX + 10]; /* path + "target: " */ + struct stat64 s; + int first_path; + + /* + + A recovery file should look like: + + + + + + + target: + temp: + end + */ + + file = fopen(recover_file, "r"); + if (file == NULL) { + err_open(recover_file); + return 1; + } + + /* read phase */ + *phase = 0; + if (fgets(buf, PATH_MAX + 10, file) == NULL) { + err_message("Recovery failed: unable to read phase"); + goto quit; + } + buf[strlen(buf) - 1] = '\0'; + *phase = atoi(buf); + if (*phase == SCAN_PHASE) { + fclose(file); + return 0; + } + if ((*phase < DIR_PHASE || *phase > DIR_PHASE_MAX) && + (*phase < FILE_PHASE || *phase > FILE_PHASE_MAX)) { + err_message("Recovery failed: failed to read valid recovery phase"); + goto quit; + } + + /* read inode number */ + if (fgets(buf, PATH_MAX + 10, file) == NULL) { + err_message("Recovery failed: unable to read inode number"); + goto quit; + } + buf[strlen(buf) - 1] = '\0'; + ino = strtoull(buf, NULL, 10); + if (ino == 0) { + err_message("Recovery failed: unable to read inode number"); + goto quit; + } + + /* read ftw_flags */ + if (fgets(buf, PATH_MAX + 10, file) == NULL) { + err_message("Recovery failed: unable to read flags"); + goto quit; + } + buf[strlen(buf) - 1] = '\0'; + if (buf[1] != '\0' || (buf[0] != '0' && buf[0] != '1')) { + err_message("Recovery failed: unable to read flags: '%s'", buf); + goto quit; + } + ftw_flags = atoi(buf); + + /* read paths and target path */ + *node = NULL; + *target = NULL; + first_path = 1; + while (fgets(buf, PATH_MAX + 10, file) != NULL) { + buf[strlen(buf) - 1] = '\0'; + + log_message(LOG_DEBUG, "path: '%s'", buf); + + if (buf[0] == '/') { + if (stat64(buf, &s) < 0) { + err_message(_("Recovery failed: cannot " + "stat '%s'"), buf); + goto quit; + } + if (s.st_ino != ino) { + err_message(_("Recovery failed: inode " + "number for '%s' does not " + "match recorded number"), buf); + goto quit; + } + + if (first_path) { + first_path = 0; + *node = add_node_path(ino, ftw_flags, buf); + } + else { + add_path(*node, buf); + } + } + else if (strncmp(buf, "target: ", 8) == 0) { + *target = strdup(buf + 8); + if (*target == NULL) { + err_nomem(); + goto quit; + } + if (stat64(*target, &s) < 0) { + err_message(_("Recovery failed: cannot " + "stat '%s'"), *target); + goto quit; + } + } + else if (strncmp(buf, "temp: ", 6) == 0) { + *temp = strdup(buf + 6); + if (*temp == NULL) { + err_nomem(); + goto quit; + } + } + else if (strcmp(buf, "end") == 0) { + rval = 0; + goto quit; + } + else { + err_message(_("Recovery failed: unrecognised " + "string: '%s'"), buf); + goto quit; + } + } + + err_message(_("Recovery failed: end of recovery file not found")); + + quit: + if (*node == NULL) { + err_message(_("Recovery failed: no valid inode or paths " + "specified")); + rval = 1; + } + + if (*target == NULL) { + err_message(_("Recovery failed: no inode target specified")); + rval = 1; + } + + fclose(file); + + return rval; +} + +int +recover( + bignode_t *node, + char *target, + char *tname, + int phase) +{ + int tfd = -1; + int targetfd = -1; + char *srcname = NULL; + int rval = 0; + int i; + int move_count = 0; + + dump_node("recover", node); + log_message(LOG_DEBUG, "target: %s, phase: %x", target, phase); + + if (node) + srcname = node->paths[0]; + + switch (phase) { + + case DIR_PHASE_2: +rmtemps: + log_message(LOG_NORMAL, _("Removing temporary directory: '%s'"), + tname); + if (rmdir(tname) < 0 && errno != ENOENT) { + err_message(_("unable to remove directory: %s"), tname); + rval = 1; + } + /* FALL THRU */ + case DIR_PHASE_1: + log_message(LOG_NORMAL, _("Removing target directory: '%s'"), + target); + if (rmdir(target) < 0 && errno != ENOENT) { + err_message(_("unable to remove directory: %s"), + target); + rval = 1; + } + break; + + case DIR_PHASE_3: + log_message(LOG_NORMAL, _("Completing moving directory " + "contents: '%s' to '%s'"), srcname, target); + if (move_dirents(srcname, target, &move_count) != 0) { + err_message(_("unable to move directory contents: " + "%s to %s"), srcname, target); + /* uh oh, move everything back... */ + if (move_count > 0) { + if (move_dirents(target, srcname, + &move_count) != 0) { + /* oh, dear lord... let the admin + * clean this one up */ + err_message(_("unable to move directory " + "contents back: %s to %s"), + target, srcname); + exit(1); + } + } + goto rmtemps; + } + /* FALL THRU */ + case DIR_PHASE_4: + log_message(LOG_NORMAL, _("Setting attributes for target " + "directory: \'%s\'"), target); + tfd = open(tname, O_RDONLY); + if (tfd < 0) { + err_open(tname); + rval = 1; + break; + } + targetfd = open(target, O_RDONLY); + if (targetfd < 0) { + err_open(target); + rval = 1; + break; + } + rval = dup_attributes(tname, tfd, target, targetfd); + if (rval != 0) { + err_message(_("unable to duplicate directory " + "attributes: %s"), tname); + break; + } + close(tfd); + close(targetfd); + /* FALL THRU */ + case DIR_PHASE_6: + log_message(LOG_NORMAL, _("Removing temporary directory: \'%s\'"), + tname); + if (rmdir(tname) < 0 && errno != ENOENT) { + err_message(_("unable to remove directory: %s"), + tname); + rval = 1; + break; + } + /* FALL THRU */ + case DIR_PHASE_5: + log_message(LOG_NORMAL, _("Removing old directory: \'%s\'"), + srcname); + if (rmdir(srcname) < 0 && errno != ENOENT) { + err_message(_("unable to remove directory: %s"), + srcname); + rval = 1; + break; + } + /* FALL THRU */ + case DIR_PHASE_7: + log_message(LOG_NORMAL, _("Renaming new directory to old " + "directory: \'%s\' -> \'%s\'"), target, srcname); + rval = rename(target, srcname); + if (rval != 0) { + /* we can't abort since the src dir is now gone. + * let the admin clean this one up + */ + err_message(_("unable to rename directory: %s to %s"), + target, srcname); + break; + } + break; + + + case FILE_PHASE_1: + case SLINK_PHASE_1: + log_message(LOG_NORMAL, _("Unlinking temporary file: \'%s\'"), + target); + unlink(target); + break; + + case FILE_PHASE_2: + case SLINK_PHASE_2: + log_message(LOG_NORMAL, _("Unlinking old file: \'%s\'"), + srcname); + rval = unlink(srcname); + if (rval != 0) { + err_message(_("unable to remove file: %s"), srcname); + break; + } + /* FALL THRU */ + case FILE_PHASE_3: + case SLINK_PHASE_3: + log_message(LOG_NORMAL, _("Renaming new file to old file: " + "\'%s\' -> \'%s\'"), target, srcname); + rval = rename(target, srcname); + if (rval != 0) { + /* we can't abort since the src file is now gone. + * let the admin clean this one up + */ + err_message(_("unable to rename file: %s to %s"), + target, srcname); + break; + } + /* FALL THRU */ + case FILE_PHASE_4: + case SLINK_PHASE_4: + /* for each hardlink, unlink and creat pointing to target */ + for (i = 1; i < node->numpaths; i++) { + if (i == 1) + log_message(LOG_NORMAL, _("Resetting hardlinks " + "to new file")); + + rval = unlink(node->paths[i]); + if (rval != 0) { + err_message(_("unable to remove file: %s"), + node->paths[i]); + break; + } + rval = link(srcname, node->paths[i]); + if (rval != 0) { + err_message(_("unable to link to file: %s"), + srcname); + break; + } + } + break; + } + + if (rval == 0) { + log_message(LOG_NORMAL, _("Removing recover file: \'%s\'"), + recover_file); + unlink(recover_file); + log_message(LOG_NORMAL, _("Recovery done.")); + } + else { + log_message(LOG_NORMAL, _("Leaving recover file: \'%s\'"), + recover_file); + log_message(LOG_NORMAL, _("Recovery failed.")); + } + + return rval; +} + +int +main( + int argc, + char *argv[]) +{ + int c = 0; + int rval = 0; + int q_opt = 0; + int v_opt = 0; + int p_opt = 0; + int n_opt = 0; + char pathname[PATH_MAX]; + struct stat64 st; + + progname = basename(argv[0]); + + setlocale(LC_ALL, ""); + bindtextdomain(PACKAGE, LOCALEDIR); + textdomain(PACKAGE); + + while ((c = getopt(argc, argv, "fnpqvP:r:")) != -1) { + switch (c) { + case 'f': + force_all = 1; + break; + case 'n': + n_opt++; + break; + case 'p': + p_opt++; + break; + case 'q': + if (v_opt) + err_message(_("'q' option incompatible " + "with 'v' option")); + q_opt++; + log_level=0; + break; + case 'v': + if (q_opt) + err_message(_("'v' option incompatible " + "with 'q' option")); + v_opt++; + log_level++; + break; + case 'P': + poll_interval = atoi(optarg); + break; + case 'r': + recover_file = optarg; + break; + default: + err_message(_("%s: illegal option -- %c\n"), c); + usage(); + /* NOTREACHED */ + break; + } + } + + if (optind != argc - 1 && recover_file == NULL) { + usage(); + exit(1); + } + + realuid = getuid(); + starttime = time(0); + + init_nodehash(); + + signal(SIGALRM, sighandler); + signal(SIGABRT, sighandler); + signal(SIGHUP, sighandler); + signal(SIGINT, sighandler); + signal(SIGQUIT, sighandler); + signal(SIGTERM, sighandler); + + if (p_opt && poll_interval == 0) { + poll_interval = 1; + } + if (poll_interval) + alarm(poll_interval); + + if (recover_file) { + bignode_t *node = NULL; + char *target = NULL; + char *tname = NULL; + int phase = 0; + + if (n_opt) + goto quit; + + /* read node info from recovery file */ + if (read_recover_file(recover_file, &node, &target, + &tname, &phase) != 0) + exit(1); + + rval = recover(node, target, tname, phase); + + free(target); + free(tname); + + return rval; + } + + recover_file = malloc(PATH_MAX); + if (recover_file == NULL) { + err_nomem(); + exit(1); + } + recover_file[0] = '\0'; + + strcpy(pathname, argv[optind]); + if (pathname[0] != '/') { + err_message(_("pathname must begin with a slash ('/')")); + exit(1); + } + + if (stat64(pathname, &st) < 0) { + err_stat(pathname); + exit(1); + } + if (S_ISREG(st.st_mode)) { + /* single file specified */ + if (st.st_nlink > 1) { + err_message(_("cannot process single file with a " + "link count greater than 1")); + exit(1); + } + + strcpy(recover_file, pathname); + dirname(recover_file); + + strcpy(recover_file + strlen(recover_file), "/xfs_reno.recover"); + if (!n_opt) { + if (open_recoverfile() != 0) + exit(1); + } + add_node_path(st.st_ino, FTW_F, pathname); + } + else if (S_ISDIR(st.st_mode)) { + /* directory tree specified */ + strcpy(recover_file, pathname); + + strcpy(recover_file + strlen(recover_file), "/xfs_reno.recover"); + if (!n_opt) { + if (open_recoverfile() != 0) + exit(1); + } + + /* directory scan */ + log_message(LOG_INFO, _("\rScanning directory tree...")); + SET_PHASE(SCAN_PHASE); + nftw64(pathname, nftw_addnodes, 100, FTW_PHYS | FTW_MOUNT); + } + else { + err_message(_("pathname must be either a regular file " + "or directory")); + exit(1); + } + + dump_nodehash(); + + if (n_opt) { + /* n flag set, don't do anything */ + if (numdirnodes) + log_message(LOG_NORMAL, "\rWould process %d %s", + numdirnodes, numdirnodes == 1 ? + "directory" : "directories"); + else + log_message(LOG_NORMAL, "\rNo directories to process"); + + if (numfilenodes) + /* process files */ + log_message(LOG_NORMAL, "\rWould process %d %s", + numfilenodes, numfilenodes == 1 ? + "file" : "files"); + else + log_message(LOG_NORMAL, "\rNo files to process"); + if (numslinknodes) + /* process files */ + log_message(LOG_NORMAL, "\rWould process %d %s", + numslinknodes, numslinknodes == 1 ? + "symlinx" : "symlinks"); + else + log_message(LOG_NORMAL, "\rNo symlinks to process"); + } else { + /* process directories */ + if (numdirnodes) { + log_message(LOG_INFO, _("\rProcessing %d %s..."), + numdirnodes, numdirnodes == 1 ? + _("directory") : _("directories")); + cur_phase = DIR_PHASE; + rval = for_all_nodes(process_dir, FTW_D, 1); + if (rval != 0) + goto quit; + } + else + log_message(LOG_INFO, _("\rNo directories to process...")); + + if (numfilenodes) { + /* process files */ + log_message(LOG_INFO, _("\rProcessing %d %s..."), + numfilenodes, numfilenodes == 1 ? + _("file") : _("files")); + cur_phase = FILE_PHASE; + for_all_nodes(process_file, FTW_F, 0); + } + else + log_message(LOG_INFO, _("\rNo files to process...")); + + if (numslinknodes) { + /* process symlinks */ + log_message(LOG_INFO, _("\rProcessing %d %s..."), + numslinknodes, numslinknodes == 1 ? + _("symlink") : _("symlinks")); + cur_phase = SLINK_PHASE; + for_all_nodes(process_slink, FTW_SL, 0); + } + else + log_message(LOG_INFO, _("\rNo symlinks to process...")); + + } +quit: + free_nodehash(); + + close(recover_fd); + + if (rval == 0) + unlink(recover_file); + + log_message(LOG_DEBUG, "\r%u seconds elapsed", time(0) - starttime); + log_message(LOG_INFO, _("\rDone. ")); + + return rval | global_rval; +} Index: b/Makefile =================================================================== --- a/Makefile +++ b/Makefile @@ -41,7 +41,7 @@ endif LIB_SUBDIRS = libxfs libxlog libxcmd libhandle libdisk TOOL_SUBDIRS = copy db estimate fsck fsr growfs io logprint mkfs quota \ - mdrestore repair rtcp m4 man doc po debian + mdrestore repair reno rtcp m4 man doc po debian SUBDIRS = include $(LIB_SUBDIRS) $(TOOL_SUBDIRS) --nextPart1386822.l1ojNFhaiW Content-Disposition: attachment; filename="xfsprogs-libattr-ac.diff" Content-Transfer-Encoding: 7Bit Content-Type: text/x-patch; charset="utf-8"; name="xfsprogs-libattr-ac.diff" Add the necessary autoconf magic in order to be able to compile anything dependent from libattr, e.g. xfs_reno. Shamelessly stolen from xfsdump. Thanks to Dave Chinner for advice. Signed-off-by: Hans-Peter Jansen Index: b/configure.ac =================================================================== --- a/configure.ac +++ b/configure.ac @@ -101,6 +101,10 @@ AC_PACKAGE_NEED_UUIDCOMPARE AC_PACKAGE_NEED_PTHREAD_H AC_PACKAGE_NEED_PTHREADMUTEXINIT +AC_PACKAGE_NEED_ATTRIBUTES_H +AC_PACKAGE_NEED_ATTRIBUTES_MACROS +AC_PACKAGE_NEED_ATTRGET_LIBATTR + AC_HAVE_FADVISE AC_HAVE_MADVISE AC_HAVE_MINCORE Index: b/include/builddefs.in =================================================================== --- a/include/builddefs.in +++ b/include/builddefs.in @@ -34,6 +34,7 @@ LIBTERMCAP = @libtermcap@ LIBEDITLINE = @libeditline@ LIBREADLINE = @libreadline@ LIBBLKID = @libblkid@ +LIBATTR = @libattr@ LIBXFS = $(TOPDIR)/libxfs/libxfs.la LIBXCMD = $(TOPDIR)/libxcmd/libxcmd.la LIBXLOG = $(TOPDIR)/libxlog/libxlog.la Index: b/m4/package_attrdev.m4 =================================================================== --- /dev/null +++ b/m4/package_attrdev.m4 @@ -0,0 +1,79 @@ +AC_DEFUN([AC_PACKAGE_NEED_ATTR_XATTR_H], + [ AC_CHECK_HEADERS([attr/xattr.h]) + if test "$ac_cv_header_attr_xattr_h" != "yes"; then + echo + echo 'FATAL ERROR: attr/xattr.h does not exist.' + echo 'Install the extended attributes (attr) development package.' + echo 'Alternatively, run "make install-dev" from the attr source.' + exit 1 + fi + ]) + +AC_DEFUN([AC_PACKAGE_NEED_ATTR_ERROR_H], + [ AC_CHECK_HEADERS([attr/error_context.h]) + if test "$ac_cv_header_attr_error_context_h" != "yes"; then + echo + echo 'FATAL ERROR: attr/error_context.h does not exist.' + echo 'Install the extended attributes (attr) development package.' + echo 'Alternatively, run "make install-dev" from the attr source.' + exit 1 + fi + ]) + +AC_DEFUN([AC_PACKAGE_NEED_ATTRIBUTES_H], + [ have_attributes_h=false + AC_CHECK_HEADERS([attr/attributes.h sys/attributes.h], [have_attributes_h=true], ) + if test "$have_attributes_h" = "false"; then + echo + echo 'FATAL ERROR: attributes.h does not exist.' + echo 'Install the extended attributes (attr) development package.' + echo 'Alternatively, run "make install-dev" from the attr source.' + exit 1 + fi + ]) + +AC_DEFUN([AC_PACKAGE_WANT_ATTRLIST_LIBATTR], + [ AC_CHECK_LIB(attr, attr_list, [have_attr_list=true], [have_attr_list=false]) + AC_SUBST(have_attr_list) + ]) + +AC_DEFUN([AC_PACKAGE_NEED_GETXATTR_LIBATTR], + [ AC_CHECK_LIB(attr, getxattr,, [ + echo + echo 'FATAL ERROR: could not find a valid Extended Attributes library.' + echo 'Install the extended attributes (attr) development package.' + echo 'Alternatively, run "make install-lib" from the attr source.' + exit 1 + ]) + libattr="-lattr" + test -f ${libexecdir}${libdirsuffix}/libattr.la && \ + libattr="${libexecdir}${libdirsuffix}/libattr.la" + AC_SUBST(libattr) + ]) + +AC_DEFUN([AC_PACKAGE_NEED_ATTRGET_LIBATTR], + [ AC_CHECK_LIB(attr, attr_get,, [ + echo + echo 'FATAL ERROR: could not find a valid Extended Attributes library.' + echo 'Install the extended attributes (attr) development package.' + echo 'Alternatively, run "make install-lib" from the attr source.' + exit 1 + ]) + libattr="-lattr" + test -f ${libexecdir}${libdirsuffix}/libattr.la && \ + libattr="${libexecdir}${libdirsuffix}/libattr.la" + AC_SUBST(libattr) + ]) + +AC_DEFUN([AC_PACKAGE_NEED_ATTRIBUTES_MACROS], + [ AC_MSG_CHECKING([macros in attr/attributes.h]) + AC_TRY_LINK([ +#include +#include ], + [ int x = ATTR_SECURE; ], [ echo ok ], [ + echo + echo 'FATAL ERROR: could not find a current attributes header.' + echo 'Upgrade the extended attributes (attr) development package.' + echo 'Alternatively, run "make install-dev" from the attr source.' + exit 1 ]) + ]) --nextPart1386822.l1ojNFhaiW-- From jferrero06@gmail.com Wed Mar 6 09:09:06 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.3 required=5.0 tests=FREEMAIL_ENVFROM_END_DIGIT, FREEMAIL_FROM,T_DKIM_INVALID autolearn=no version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 2AC8F7FD0 for ; Wed, 6 Mar 2013 09:09:06 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay3.corp.sgi.com (Postfix) with ESMTP id BB83DAC001 for ; Wed, 6 Mar 2013 07:09:02 -0800 (PST) X-ASG-Debug-ID: 1362582540-04bdf0229821a490001-NocioJ Received: from mail-bk0-f66.google.com (mail-bk0-f66.google.com [209.85.214.66]) by cuda.sgi.com with ESMTP id LwSFQzSf0IFSgk5J (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Wed, 06 Mar 2013 07:09:01 -0800 (PST) X-Barracuda-Envelope-From: jferrero06@gmail.com X-Barracuda-Apparent-Source-IP: 209.85.214.66 X-Barracuda-IPDD: Level1 [gmail.com/209.85.214.66] Received: by mail-bk0-f66.google.com with SMTP id jk7so170490bkc.1 for ; Wed, 06 Mar 2013 07:08:59 -0800 (PST) X-Barracuda-IPDD: Level1 [gmail.com/209.85.214.66] X-Barracuda-IPDD: Level1 [gmail.com/209.85.214.66] DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20120113; h=mime-version:x-received:date:message-id:subject:from:to :content-type; bh=kDyzgUrHPvT5FcmYpjShBuXFm+C2LZOheAo6iEezCWE=; b=GXAPUnBlMSCA/YnOX/iZGHp2BuYkXLtd9zZWkTpJeo66sIn2kA/ZZyHFV6sP55Icej c4gg/0cSBD9A99K8qFFOihSzcLS9118woZviWQxjvZnv7b6A9Xkk4FK3r0cU8xyRGGAj gvZ5omZ8ly5WjRrWxnWn3cUCkJbQegXD0DWenLGTt0UhCafdqJajWYqezDiXpOwF91zW 4Ii9/3ByeX/zlqgn2Qa5NXi6kP6iiWr6Bq9vZGj8j7u+NkFo4kKkwvv45UmE8ZKE2JK6 qPioCmMZ2TblCD9Km7nZGKNQJANR2ENBsEmHgiJOKgPnjvvTP0hR1vRGPZsMKXYMVCi4 +rwA== MIME-Version: 1.0 X-Received: by 10.205.120.133 with SMTP id fy5mr11496600bkc.87.1362582539685; Wed, 06 Mar 2013 07:08:59 -0800 (PST) Received: by 10.204.228.133 with HTTP; Wed, 6 Mar 2013 07:08:59 -0800 (PST) Date: Wed, 6 Mar 2013 16:08:59 +0100 Message-ID: Subject: XFS filesystem corruption From: Julien FERRERO X-ASG-Orig-Subj: XFS filesystem corruption To: xfs@oss.sgi.com Content-Type: text/plain; charset=ISO-8859-1 X-Barracuda-Connect: mail-bk0-f66.google.com[209.85.214.66] X-Barracuda-Start-Time: 1362582540 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Barracuda-BRTS-Status: 1 X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=DKIM_SIGNED, DKIM_VERIFIED X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124424 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature Hi, I am migrating a video streaming server from Linux kernel 2.6.18 (8 years old kernel...) to 2.6.35 (2 years old...). Unfortunately, I don't have the choice of the kernel version since some proprietary external modules require this specific kernel version. We use XFS for filesystem and the layout is the following: H/W RAID 5 (/dev/sda) > mdadm Linear RAID (/dev/md0) > XFS filesystem (/mountpoint). The allocated size of the fs is 1.5 TB. Since we have migrated to 2.6.35, we start to experience some very rare and random filesystem corruption. Some file or directory suddenly become no longer accessible. For instance, the /bin/ls command returns: ?????????? ? ? ? ? ? 4988d60d-2ee5-4ee6-9a16-6f7f5f28f412.xml and I cannot open the file (No such file or directory). I had a look to the FAQ and I did try to remount the fs with the option "inode64" but it did not change anything. I have the exact same result. If I run "xfs_repair" on my system I have the following output: --------------8<--------------8<-------------- # xfs_repair -n /dev/md0 Phase 1 - find and verify superblock... Phase 2 - using internal log - scan filesystem freespace and inode maps... agi unlinked bucket 62 is 190 in ag 1 (inode=134217918) - found root inode chunk Phase 3 - for each AG... - scan (but don't clear) agi unlinked lists... - process known inodes and perform inode discovery... - agno = 0 b52feb70: Badness in key lookup (length) bp=(bno 60387336, len 16384 bytes) key=(bno 60387336, len 8192 bytes) - agno = 1 imap claims a free inode 134217858 is in use, would correct imap and clear inode imap claims a free inode 134217859 is in use, would correct imap and clear inode imap claims a free inode 134217860 is in use, would correct imap and clear inode imap claims a free inode 134217863 is in use, would correct imap and clear inode imap claims a free inode 134217864 is in use, would correct imap and clear inode imap claims a free inode 134217866 is in use, would correct imap and clear inode imap claims a free inode 134217867 is in use, would correct imap and clear inode imap claims a free inode 134217869 is in use, would correct imap and clear inode imap claims a free inode 134217915 is in use, would correct imap and clear inode imap claims a free inode 134217916 is in use, would correct imap and clear inode imap claims a free inode 140493888 is in use, would correct imap and clear inode imap claims a free inode 140493894 is in use, would correct imap and clear inode imap claims a free inode 140493896 is in use, would correct imap and clear inode imap claims a free inode 140493897 is in use, would correct imap and clear inode imap claims a free inode 140493898 is in use, would correct imap and clear inode imap claims a free inode 140493899 is in use, would correct imap and clear inode - agno = 2 - agno = 3 - agno = 4 - agno = 5 - agno = 6 - agno = 7 - agno = 8 - agno = 9 - agno = 10 - agno = 11 - agno = 12 - agno = 13 - agno = 14 - agno = 15 - agno = 16 - agno = 17 - agno = 18 - agno = 19 - agno = 20 - agno = 21 - agno = 22 - agno = 23 - agno = 24 - agno = 25 - agno = 26 - agno = 27 - agno = 28 - agno = 29 - agno = 30 - agno = 31 - process newly discovered inodes... Phase 4 - check for duplicate blocks... - setting up duplicate extent list... - check for inodes claiming duplicate blocks... - agno = 0 - agno = 1 entry "10fdb8cd-b48a-4d2a-8ff4-19516e6a3b06.xml" at block 0 offset 544 in directory inode 134217856 references free inode 140493896 would clear inode number in entry at offset 544... entry "9e6727ff-9fd6-466a-aa30-c7aabdd67646.xml" at block 0 offset 600 in directory inode 134217856 references free inode 140493898 entry "tmp" at block 0 offset 112 in directory inode 128 references free inode 140493888 would clear inode number in entry at offset 600... would clear inode number in entry at offset 112... entry "5ff59379-e982-4d4e-b87a-cb194ea6cfd8.xml" at block 0 offset 632 in directory inode 134217856 references free inode 140493899 entry "tmp" at block 0 offset 3984 in directory inode 128 references free inode 135 would clear inode number in entry at offset 632... would clear inode number in entry at offset 3984... entry "b8078379-d8ee-4af0-9ed4-2c94479a7a51.xml" in shortform directory 131 references free inode 135 would have junked entry "b8078379-d8ee-4af0-9ed4-2c94479a7a51.xml" in directory inode 131 entry "4988d60d-2ee5-4ee6-9a16-6f7f5f28f412.xml" in shortform directory 131 references free inode 135 would have junked entry "4988d60d-2ee5-4ee6-9a16-6f7f5f28f412.xml" in directory inode 131 - agno = 2 entry "87280c00-3b60-46ec-9d65-937db364a7b9" at block 2 offset 16 in directory inode 268435584 references free inode 135 would clear inode number in entry at offset 16... - agno = 3 - agno = 4 - agno = 5 - agno = 6 - agno = 7 - agno = 8 - agno = 9 - agno = 10 - agno = 11 - agno = 12 - agno = 13 - agno = 14 - agno = 15 - agno = 16 - agno = 17 - agno = 18 - agno = 19 - agno = 20 - agno = 21 - agno = 22 - agno = 23 - agno = 24 - agno = 25 - agno = 26 - agno = 27 - agno = 28 - agno = 29 - agno = 30 entry "up2" in shortform directory 4026531968 references free inode 135 would have junked entry "up2" in directory inode 4026531968 - agno = 31 No modify flag set, skipping phase 5 Phase 6 - check inode connectivity... - traversing filesystem ... entry "tmp" in directory inode 128 points to free inode 140493888, would junk entry entry "tmp" in directory inode 128 points to free inode 135, would junk entry bad hash table for directory inode 128 (no data entry): would rebuild entry "56b3f51e-4912-4e43-99ed-2204aa8a68f2.xml" in shortform directory inode 131 points to free inode 135would junk entry entry "4988d60d-2ee5-4ee6-9a16-6f7f5f28f412.xml" in shortform directory inode 131 points to free inode 135would junk entry entry "ca073ec3-5d59-4306-a8a6-67c2e0d79c81.xml" in directory inode 134217856 points to free inode 140493896, would junk entry entry "ea5dd270-06a0-4e25-8cbf-0a37b2dad755.xml" in directory inode 134217856 points to free inode 140493898, would junk entry entry "dd745300-48fa-46e5-b5c7-a4ba5e820353.xml" in directory inode 134217856 points to free inode 140493899, would junk entry entry "3a092246-f8ea-4cb6-9758-f0d73253f368.xml" in dir 134217856 points to an already connected directory inode 140493909 would clear entry "3a092246-f8ea-4cb6-9758-f0d73253f368.xml" bad hash table for directory inode 134217856 (no data entry): would rebuild entry "87280c00-3b60-46ec-9d65-937db364a7b9" in directory inode 268435584 points to free inode 135, would junk entry bad hash table for directory inode 268435584 (no data entry): would rebuild entry "up2" in shortform directory inode 4026531968 points to free inode 135would junk entry - traversal finished ... - moving disconnected inodes to lost+found ... disconnected dir inode 134217861, would move to lost+found disconnected inode 134217865, would move to lost+found disconnected inode 134217868, would move to lost+found disconnected inode 134217918, would move to lost+found disconnected inode 134217919, would move to lost+found disconnected inode 140493900, would move to lost+found Phase 7 - verify link counts... would have reset inode 128 nlinks from 12 to 8 would have reset inode 134217918 nlinks from -1 to 1 would have reset inode 268435584 nlinks from 192 to 191 would have reset inode 4026531968 nlinks from 4 to 3 No modify flag set, skipping filesystem flush and exiting. --------------8<--------------8<-------------- The filesystem was originally created with the command: # mkfs.xfs -f -l size=32m /dev/md0 and the mount option in fstab are "defaults" (rw,relatime,attr2,noquota). We know the problem is not related to the RAID H/W. We also have an unit with corrupted fs on a single drive (the RAID Linear is still there though). I am totally stuck and I really don't know how to duplicate the corruption. I only know that units are used to be power cycle by operator while the fs is still mounted (no proper shutdown / reboot). My guess is the fs journal shall handle this case and avoid such corruption. Any help would be appreciated. Thank you. -- Julian From eflorac@intellique.com Wed Mar 6 09:15:43 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 0977C7F52 for ; Wed, 6 Mar 2013 09:15:43 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay1.corp.sgi.com (Postfix) with ESMTP id DDEFA8F80A6 for ; Wed, 6 Mar 2013 07:15:39 -0800 (PST) X-ASG-Debug-ID: 1362582936-04cbb07dbe2084f0001-NocioJ Received: from smtp3-g21.free.fr (smtp3-g21.free.fr [212.27.42.3]) by cuda.sgi.com with ESMTP id 5FvW0CWVFIL1J7tH for ; Wed, 06 Mar 2013 07:15:37 -0800 (PST) X-Barracuda-Envelope-From: eflorac@intellique.com X-Barracuda-Apparent-Source-IP: 212.27.42.3 Received: from galadriel.home (unknown [82.235.234.79]) by smtp3-g21.free.fr (Postfix) with ESMTP id 18938A619A; Wed, 6 Mar 2013 16:15:31 +0100 (CET) Date: Wed, 6 Mar 2013 16:15:19 +0100 From: Emmanuel Florac To: Julien FERRERO Cc: xfs@oss.sgi.com Subject: Re: XFS filesystem corruption Message-ID: <20130306161519.2c28d911@galadriel.home> X-ASG-Orig-Subj: Re: XFS filesystem corruption In-Reply-To: References: Organization: Intellique X-Mailer: Claws Mail 3.7.8 (GTK+ 2.24.4; i686-pc-linux-gnu) Mime-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: quoted-printable X-Barracuda-Connect: smtp3-g21.free.fr[212.27.42.3] X-Barracuda-Start-Time: 1362582936 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124424 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- Le Wed, 6 Mar 2013 16:08:59 +0100 vous =C3=A9criviez: > I am totally stuck and I really don't know how to duplicate the > corruption. I only know that units are used to be power cycle by > operator while the fs is still mounted (no proper shutdown / reboot). > My guess is the fs journal shall handle this case and avoid such > corruption. Wrong guess. It may work or not, depending upon a long list of parameters, but basically not turning it off properly is asking for problems and corruptions. The problem will be tragically aggravated if your hardware RAID doesn't have a battery backed-up cache. --=20 ------------------------------------------------------------------------ Emmanuel Florac | Direction technique | Intellique | | +33 1 78 94 84 02 ------------------------------------------------------------------------ From jferrero06@gmail.com Wed Mar 6 10:16:40 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.3 required=5.0 tests=FREEMAIL_ENVFROM_END_DIGIT, FREEMAIL_FROM,T_DKIM_INVALID autolearn=no version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 86FA27CBF for ; Wed, 6 Mar 2013 10:16:40 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay1.corp.sgi.com (Postfix) with ESMTP id 472688F8074 for ; Wed, 6 Mar 2013 08:16:37 -0800 (PST) X-ASG-Debug-ID: 1362586591-04bdf0229721f340001-NocioJ Received: from mail-bk0-f44.google.com (mail-bk0-f44.google.com [209.85.214.44]) by cuda.sgi.com with ESMTP id mYdwCZr0mTuNMnOF (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Wed, 06 Mar 2013 08:16:32 -0800 (PST) X-Barracuda-Envelope-From: jferrero06@gmail.com X-Barracuda-Apparent-Source-IP: 209.85.214.44 X-Barracuda-IPDD: Level1 [gmail.com/209.85.214.44] Received: by mail-bk0-f44.google.com with SMTP id j4so369083bkw.17 for ; Wed, 06 Mar 2013 08:16:31 -0800 (PST) X-Barracuda-IPDD: Level1 [gmail.com/209.85.214.44] X-Barracuda-IPDD: Level1 [gmail.com/209.85.214.44] DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20120113; h=mime-version:x-received:in-reply-to:references:date:message-id :subject:from:to:cc:content-type:content-transfer-encoding; bh=7LBgWZE+ZvCtBx46uj4A+ctqRSSBTjQUs7Ozo4s7lTg=; b=Ew6Vo1HF6t5kpPtqqrAffAgU7OjBUc893mdIvbPO8spz3qAwrf+zYUoSco+4CIJtts 8oTopi24cU+JdF0TZOfMpQ45gU06GxQZb2uVR7MO88z+Mbt2OpvI47ZWWd6QYDRymmHf vMB0HMcdajSD3hMJlEApqBtXIU0pRAIlwA4CAQf2n3TkYLcaF0Grgyo2QdH+s028HLRU ijziIayC6KtxpEj9kgEcAAuKLLfNFiOX0FHNgQpwe1KqrHmY+45dyHzh6RY1CgzgBKSP gsQziClFTxCsReDaMgC6fqQWOLw9BeH0x2wkBgviRDuJZQTKQs4QBwqrsbPFJwWJh5Z8 AggQ== MIME-Version: 1.0 X-Received: by 10.204.11.87 with SMTP id s23mr11575444bks.113.1362586591471; Wed, 06 Mar 2013 08:16:31 -0800 (PST) Received: by 10.204.228.133 with HTTP; Wed, 6 Mar 2013 08:16:31 -0800 (PST) In-Reply-To: <20130306161519.2c28d911@galadriel.home> References: <20130306161519.2c28d911@galadriel.home> Date: Wed, 6 Mar 2013 17:16:31 +0100 Message-ID: Subject: Re: XFS filesystem corruption From: Julien FERRERO X-ASG-Orig-Subj: Re: XFS filesystem corruption To: Emmanuel Florac Cc: xfs@oss.sgi.com Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: quoted-printable X-Barracuda-Connect: mail-bk0-f44.google.com[209.85.214.44] X-Barracuda-Start-Time: 1362586592 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=DKIM_SIGNED, DKIM_VERIFIED X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124428 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature Hi Emmanuel 2013/3/6 Emmanuel Florac : > Le Wed, 6 Mar 2013 16:08:59 +0100 vous =E9criviez: > >> I am totally stuck and I really don't know how to duplicate the >> corruption. I only know that units are used to be power cycle by >> operator while the fs is still mounted (no proper shutdown / reboot). >> My guess is the fs journal shall handle this case and avoid such >> corruption. > > Wrong guess. It may work or not, depending upon a long list of > parameters, but basically not turning it off properly is asking for > problems and corruptions. The problem will be tragically aggravated if > your hardware RAID doesn't have a battery backed-up cache. > OK but our server is 95% of the time reading data and 5% of the time writing data. We have a case of a server that did not write anything at the time of failure (and during all the uptime session). Moreover, failure occurs to files that were opened in read-only or weren't accessed at all at the time of failure. I don't think the H/W RAID is the issue since we have the same corruption with other setup without H/W RAID. Does the "ls" output with "???" looks like a fs corruption ? From sandeen@redhat.com Wed Mar 6 10:24:01 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 675E87F63 for ; Wed, 6 Mar 2013 10:24:01 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay2.corp.sgi.com (Postfix) with ESMTP id 47CC8304043 for ; Wed, 6 Mar 2013 08:23:58 -0800 (PST) X-ASG-Debug-ID: 1362587037-04bdf0229821f7f0001-NocioJ Received: from mx1.redhat.com (mx1.redhat.com [209.132.183.28]) by cuda.sgi.com with ESMTP id 6hjFm13CdKYOuPyL for ; Wed, 06 Mar 2013 08:23:57 -0800 (PST) X-Barracuda-Envelope-From: sandeen@redhat.com X-Barracuda-Apparent-Source-IP: 209.132.183.28 X-ASG-Whitelist: Client Received: from int-mx11.intmail.prod.int.phx2.redhat.com (int-mx11.intmail.prod.int.phx2.redhat.com [10.5.11.24]) by mx1.redhat.com (8.14.4/8.14.4) with ESMTP id r26GNtuD017695 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=OK); Wed, 6 Mar 2013 11:23:56 -0500 Received: from liberator.sandeen.net (ovpn01.gateway.prod.ext.phx2.redhat.com [10.5.9.1]) by int-mx11.intmail.prod.int.phx2.redhat.com (8.14.4/8.14.4) with ESMTP id r26GA917023995 (version=TLSv1/SSLv3 cipher=DHE-RSA-CAMELLIA256-SHA bits=256 verify=NO); Wed, 6 Mar 2013 11:10:10 -0500 Message-ID: <51376A61.6060807@redhat.com> Date: Wed, 06 Mar 2013 10:10:09 -0600 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: "Theodore Ts'o" CC: xfs@oss.sgi.com, Ext4 Developers List Subject: Re: [PATCH] xfstests: don't assume that falloc_punch implies falloc in test 255 References: <1362506382-26974-1-git-send-email-tytso@mit.edu> X-ASG-Orig-Subj: Re: [PATCH] xfstests: don't assume that falloc_punch implies falloc in test 255 In-Reply-To: <1362506382-26974-1-git-send-email-tytso@mit.edu> X-Enigmail-Version: 1.5.1 Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Scanned-By: MIMEDefang 2.68 on 10.5.11.24 X-Barracuda-Connect: mx1.redhat.com[209.132.183.28] X-Barracuda-Start-Time: 1362587037 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 On 3/5/13 11:59 AM, Theodore Ts'o wrote: > As of Linux 3.9-rc1, ext4 will support the punch operation on file > systems using indirect blocks, but it can not support the fallocate > operation (since there is no way to mark a block as uninitialized > using indirect block scheme). This caused test 255 to fail, since it > only used _require_xfS_io_falloc_punch assuming that all file systems > which supported punch can also support fallocate. Fix this. Seems fine to avoid the incorrect failure, so as far as that goes: Reviewed-by: Eric Sandeen But we probably can & should still test punch in this situation, so we need a new test to exercise that I guess. -Eric > Signed-off-by: "Theodore Ts'o" > --- > 255 | 1 + > 1 file changed, 1 insertion(+) > > diff --git a/255 b/255 > index 0083963..ae1d8e0 100755 > --- a/255 > +++ b/255 > @@ -48,6 +48,7 @@ _supported_fs generic > _supported_os Linux > > _require_xfs_io_falloc_punch > +_require_xfs_io_falloc > _require_xfs_io_fiemap > > testfile=$TEST_DIR/255.$$ > From gnehzuil.liu@gmail.com Wed Mar 6 10:37:18 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=FREEMAIL_FROM,T_DKIM_INVALID autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id CCDA67F72 for ; Wed, 6 Mar 2013 10:37:18 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay2.corp.sgi.com (Postfix) with ESMTP id B386D304070 for ; Wed, 6 Mar 2013 08:37:18 -0800 (PST) X-ASG-Debug-ID: 1362587837-04cb6c2b032051e0001-NocioJ Received: from mail-pb0-f44.google.com (mail-pb0-f44.google.com [209.85.160.44]) by cuda.sgi.com with ESMTP id gRGZ1Q4GSCrWBhDd (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Wed, 06 Mar 2013 08:37:17 -0800 (PST) X-Barracuda-Envelope-From: gnehzuil.liu@gmail.com X-Barracuda-Apparent-Source-IP: 209.85.160.44 X-Barracuda-IPDD: Level1 [gmail.com/209.85.160.44] Received: by mail-pb0-f44.google.com with SMTP id wz12so6252035pbc.3 for ; Wed, 06 Mar 2013 08:37:16 -0800 (PST) X-Barracuda-IPDD: Level1 [gmail.com/209.85.160.44] X-Barracuda-IPDD: Level1 [gmail.com/209.85.160.44] DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20120113; h=x-received:date:from:to:cc:subject:message-id:mail-followup-to :references:mime-version:content-type:content-disposition :in-reply-to:user-agent; bh=JIFKxSE3dmLI7DpGuH7/7j534oiVLBmI9fqRKC1pink=; b=SeDRON9IrwdcTfVOZwG9wQ/RQPNI0K9N+TRaTVj7O5lPYBflswsaO13ZD4kmY/744I TrS49yLFv3AuYUfuLXO/avKu1EGQfJWGtfpPAWd/gZ5Z3Wk2zQwCap/14o3lq0mjXtSW AjywdGJA4vwZyn+aRXCb9/ApiNuXIevQs18yqXnk81r7+kalFUtUGM84fPk98TZYJbg3 HA1oUnFHTNh/MC/lwGby5L2yUiZKPeVjYcOKU2MHkkFoo4Y//reMMe5CZHt1HbMTVBBl sS28jB1BpOhgin4x6srPcs6fpp6+pQ+epzdek2QJwa1YDbGGMxJQYQ02/JEH1uS3i2/v vD6g== X-Received: by 10.68.242.41 with SMTP id wn9mr8305879pbc.156.1362587836812; Wed, 06 Mar 2013 08:37:16 -0800 (PST) Received: from gmail.com ([182.92.247.2]) by mx.google.com with ESMTPS id c8sm32005112pbq.10.2013.03.06.08.37.10 (version=TLSv1 cipher=RC4-SHA bits=128/128); Wed, 06 Mar 2013 08:37:15 -0800 (PST) Date: Thu, 7 Mar 2013 00:52:26 +0800 From: Zheng Liu To: Eric Sandeen Cc: Theodore Ts'o , Ext4 Developers List , xfs@oss.sgi.com Subject: Re: [PATCH] xfstests: don't assume that falloc_punch implies falloc in test 255 Message-ID: <20130306165226.GA3454@gmail.com> X-ASG-Orig-Subj: Re: [PATCH] xfstests: don't assume that falloc_punch implies falloc in test 255 Mail-Followup-To: Eric Sandeen , Theodore Ts'o , Ext4 Developers List , xfs@oss.sgi.com References: <1362506382-26974-1-git-send-email-tytso@mit.edu> <51376A61.6060807@redhat.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <51376A61.6060807@redhat.com> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: mail-pb0-f44.google.com[209.85.160.44] X-Barracuda-Start-Time: 1362587837 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=DKIM_SIGNED, DKIM_VERIFIED X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124429 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature On Wed, Mar 06, 2013 at 10:10:09AM -0600, Eric Sandeen wrote: > On 3/5/13 11:59 AM, Theodore Ts'o wrote: > > As of Linux 3.9-rc1, ext4 will support the punch operation on file > > systems using indirect blocks, but it can not support the fallocate > > operation (since there is no way to mark a block as uninitialized > > using indirect block scheme). This caused test 255 to fail, since it > > only used _require_xfS_io_falloc_punch assuming that all file systems > > which supported punch can also support fallocate. Fix this. > > Seems fine to avoid the incorrect failure, so as far as that goes: > > Reviewed-by: Eric Sandeen > > But we probably can & should still test punch in this situation, > so we need a new test to exercise that I guess. Hi Eric, I have sent a patch set to add a test case for punching hole. You can find it in this link [1]. Sorry I don't finish the second version according to Mark's comment. 1. http://www.spinics.net/lists/xfs/msg16234.html Regards, - Zheng From rwheeler@redhat.com Wed Mar 6 10:47:46 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 213CB7F7E for ; Wed, 6 Mar 2013 10:47:46 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay1.corp.sgi.com (Postfix) with ESMTP id 596CB8F80A1 for ; Wed, 6 Mar 2013 08:47:45 -0800 (PST) X-ASG-Debug-ID: 1362588464-04cb6c2b03205820001-NocioJ Received: from mx1.redhat.com (mx1.redhat.com [209.132.183.28]) by cuda.sgi.com with ESMTP id jUKCI1aLVbmGqNvi for ; Wed, 06 Mar 2013 08:47:44 -0800 (PST) X-Barracuda-Envelope-From: rwheeler@redhat.com X-Barracuda-Apparent-Source-IP: 209.132.183.28 X-ASG-Whitelist: Client Received: from int-mx11.intmail.prod.int.phx2.redhat.com (int-mx11.intmail.prod.int.phx2.redhat.com [10.5.11.24]) by mx1.redhat.com (8.14.4/8.14.4) with ESMTP id r26Glfjs019195 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=OK); Wed, 6 Mar 2013 11:47:41 -0500 Received: from tunkums.home (ovpn-112-33.phx2.redhat.com [10.3.112.33]) by int-mx11.intmail.prod.int.phx2.redhat.com (8.14.4/8.14.4) with ESMTP id r26Gldtb009758; Wed, 6 Mar 2013 11:47:40 -0500 Message-ID: <5137732B.3010703@redhat.com> Date: Wed, 06 Mar 2013 11:47:39 -0500 From: Ric Wheeler User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:17.0) Gecko/20130219 Thunderbird/17.0.3 MIME-Version: 1.0 To: Julien FERRERO CC: Emmanuel Florac , xfs@oss.sgi.com Subject: Re: XFS filesystem corruption References: <20130306161519.2c28d911@galadriel.home> X-ASG-Orig-Subj: Re: XFS filesystem corruption In-Reply-To: Content-Type: text/plain; charset=ISO-8859-1; format=flowed Content-Transfer-Encoding: 8bit X-Scanned-By: MIMEDefang 2.68 on 10.5.11.24 X-Barracuda-Connect: mx1.redhat.com[209.132.183.28] X-Barracuda-Start-Time: 1362588464 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 On 03/06/2013 11:16 AM, Julien FERRERO wrote: > Hi Emmanuel > > 2013/3/6 Emmanuel Florac : >> Le Wed, 6 Mar 2013 16:08:59 +0100 vous criviez: >> >>> I am totally stuck and I really don't know how to duplicate the >>> corruption. I only know that units are used to be power cycle by >>> operator while the fs is still mounted (no proper shutdown / reboot). >>> My guess is the fs journal shall handle this case and avoid such >>> corruption. >> Wrong guess. It may work or not, depending upon a long list of >> parameters, but basically not turning it off properly is asking for >> problems and corruptions. The problem will be tragically aggravated if >> your hardware RAID doesn't have a battery backed-up cache. >> > OK but our server is 95% of the time reading data and 5% of the time > writing data. We have a case of a server that did not write anything > at the time of failure (and during all the uptime session). Moreover, > failure occurs to files that were opened in read-only or weren't > accessed at all at the time of failure. I don't think the H/W RAID is > the issue since we have the same corruption with other setup without > H/W RAID. > > Does the "ls" output with "???" looks like a fs corruption ? > Caching can hold dirty data in volatile cache for a very long time. Even if you open a file in "read-only" mode, you still do a fair amount of writes to storage. You can use blktrace or similar tool to see just how much data is written. As mentioned earlier, you always must unmount cleanly as a best practice. An operator that powers off with mounted file systems need educated or let go :) Ric From rjohnston@sgi.com Wed Mar 6 12:31:38 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id AEA567F76 for ; Wed, 6 Mar 2013 12:31:38 -0600 (CST) Received: from xmail.sgi.com (pv-excas3-dc21-nlb.corp.sgi.com [137.38.102.207]) by relay2.corp.sgi.com (Postfix) with ESMTP id 52BAE30407B; Wed, 6 Mar 2013 10:31:35 -0800 (PST) Received: from [128.162.233.55] (128.162.233.55) by xmail.sgi.com (137.38.102.30) with Microsoft SMTP Server (TLS) id 14.2.318.1; Wed, 6 Mar 2013 12:31:16 -0600 Message-ID: <51378B7F.9090103@sgi.com> Date: Wed, 6 Mar 2013 12:31:27 -0600 From: Rich Johnston User-Agent: Mozilla/5.0 (X11; Linux i686; rv:13.0) Gecko/20120615 Thunderbird/13.0.1 MIME-Version: 1.0 To: David Sterba CC: Subject: Re: [PATCH] xfstests: enhance ltp/fsx with a timeout option References: <1358944851-14336-1-git-send-email-dsterba@suse.cz> In-Reply-To: <1358944851-14336-1-git-send-email-dsterba@suse.cz> Content-Type: text/plain; charset="ISO-8859-1"; format=flowed Content-Transfer-Encoding: 7bit X-Originating-IP: [128.162.233.55] David, Thanks for submitting this patch. I like the addition of the -T option. I used test 263 to verify that fsx works as expected with the new -T and the existing -N options. With the -T option of course, test 263 will fail. I don't suggest that we change existing tests but add new tests which use the new -T option. Do you have a new test which you intend to use the -T option that can be submitted with this patch? Thanks --Rich From comunicado@receita.fazenda.gov.br Wed Mar 6 12:41:01 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.2 required=5.0 tests=HTML_MESSAGE,NORMAL_HTTP_TO_IP, T_KHOP_FOREIGN_CLICK autolearn=no version=3.3.1 X-Original-To: linux-xfs@oss.sgi.com Delivered-To: linux-xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id D29B47F51 for ; Wed, 6 Mar 2013 12:41:01 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay1.corp.sgi.com (Postfix) with ESMTP id C0F9A8F8094 for ; Wed, 6 Mar 2013 10:40:58 -0800 (PST) X-ASG-Debug-ID: 1362595255-04cbb07dbd212640001-w1Z2WR Received: from fw01.delpozo.com.br (mailserver.delpozo.com.br [201.72.78.130]) by cuda.sgi.com with ESMTP id m3kIY1jOwR0VqHC5 (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO) for ; Wed, 06 Mar 2013 10:40:56 -0800 (PST) X-Barracuda-Envelope-From: comunicado@receita.fazenda.gov.br X-Barracuda-Apparent-Source-IP: 201.72.78.130 Received: from localhost (localhost.localdomain [127.0.0.1]) by fw01.delpozo.com.br (Postfix) with ESMTP id 5F3A2C68E0A; Wed, 6 Mar 2013 15:35:19 -0300 (BRT) X-Virus-Scanned: amavisd-new at delpozo.com.br Received: from fw01.delpozo.com.br ([127.0.0.1]) by localhost (fw01.delpozo.com.br [127.0.0.1]) (amavisd-new, port 10024) with ESMTP id SR1Rrxc1lyjD; Wed, 6 Mar 2013 15:35:11 -0300 (BRT) Received: from [69.162.95.58] (unknown [69.162.95.58]) by fw01.delpozo.com.br (Postfix) with ESMTPSA id 11277C693A0; Wed, 6 Mar 2013 15:19:19 -0300 (BRT) Content-Type: multipart/alternative; boundary="===============1163291352==" MIME-Version: 1.0 Subject: =?utf-8?q?Notifica=C3=A7=C3=A3o_de_Irregularidades_na_Declara=C3=A7=C3=A3?= =?utf-8?q?o_de_Imposto_de_Renda_Base_2012=2E?= To: Recipients X-ASG-Orig-Subj: =?utf-8?q?Notifica=C3=A7=C3=A3o_de_Irregularidades_na_Declara=C3=A7=C3=A3?= =?utf-8?q?o_de_Imposto_de_Renda_Base_2012=2E?= From: "Receita Federal" Date: Wed, 06 Mar 2013 15:21:18 -0300 Message-Id: <20130306181920.11277C693A0@fw01.delpozo.com.br> X-Barracuda-Connect: mailserver.delpozo.com.br[201.72.78.130] X-Barracuda-Start-Time: 1362595256 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 1.00 X-Barracuda-Spam-Status: No, SCORE=1.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_SA_TO_FROM_ADDR_MATCH, BSF_SC7_SA578_CH, HTML_MESSAGE, NORMAL_HTTP_TO_IP X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124438 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 NORMAL_HTTP_TO_IP URI: Uses a dotted-decimal IP address in URL 0.00 HTML_MESSAGE BODY: HTML included in message 0.50 BSF_SC0_SA_TO_FROM_ADDR_MATCH Sender Address Matches Recipient Address 0.50 BSF_SC7_SA578_CH Custom Rule SA578_CH You will not see this in a MIME-aware mail reader. --===============1163291352== Content-Type: text/plain; charset="iso-8859-1" MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable Content-Description: Mail message body Sr. Contribuinte, Constatamos que h- irregularidades na sua declara--o de Imposto de Renda = exerc-cio 2011 base 2012, favor conferi-l- para que n-o haja problemas ao realizar a Declara--o de I= mposto de Renda base 2013. Para visualiz--la acesse o link a seguir: = Clique Aqui.. = = = =20 --===============1163291352== Content-Type: text/html; charset="iso-8859-1" MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable Content-Description: Mail message body Untitled Document

Sr. Contribuinte,

Constatamos que há irregularidades na sua declaraçã= ;o de Imposto de Renda exercício 2011 base 2012,
favor conferi-lá para que não haja problemas ao realizar a De= claração de Imposto de Renda base 2013.

Para visualizá-la acesse o link a seguir:
Clique Aqui..

 

--===============1163291352==-- From jack@suse.cz Wed Mar 6 14:22:17 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 28EEA7F5D for ; Wed, 6 Mar 2013 14:22:17 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay3.corp.sgi.com (Postfix) with ESMTP id B7C8CAC004 for ; Wed, 6 Mar 2013 12:22:13 -0800 (PST) X-ASG-Debug-ID: 1362601331-04cb6c2b0320f580001-NocioJ Received: from mx2.suse.de (cantor2.suse.de [195.135.220.15]) by cuda.sgi.com with ESMTP id KPZ92lezO7n0U3Pc for ; Wed, 06 Mar 2013 12:22:12 -0800 (PST) X-Barracuda-Envelope-From: jack@suse.cz X-Barracuda-Apparent-Source-IP: 195.135.220.15 Received: from relay2.suse.de (unknown [195.135.220.254]) by mx2.suse.de (Postfix) with ESMTP id 601CCA3E1C for ; Wed, 6 Mar 2013 21:22:11 +0100 (CET) Received: by quack.suse.cz (Postfix, from userid 1000) id 94DF82067D; Wed, 6 Mar 2013 21:22:10 +0100 (CET) Date: Wed, 6 Mar 2013 21:22:10 +0100 From: Jan Kara To: xfs@oss.sgi.com Subject: Pathological allocation pattern with direct IO Message-ID: <20130306202210.GA1318@quack.suse.cz> X-ASG-Orig-Subj: Pathological allocation pattern with direct IO MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline User-Agent: Mutt/1.5.20 (2009-06-14) X-Barracuda-Connect: cantor2.suse.de[195.135.220.15] X-Barracuda-Start-Time: 1362601331 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124446 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- Hello, one of our customers has application that write large (tens of GB) files using direct IO done in 16 MB chunks. They keep the fs around 80% full deleting oldest files when they need to store new ones. Usually the file can be stored in under 10 extents but from time to time a pathological case is triggered and the file has few thousands extents (which naturally has impact on performance). The customer actually uses 2.6.32-based kernel but I reproduced the issue with 3.8.2 kernel as well. I was analyzing why this happens and the filefrag for the file looks like: Filesystem type is: 58465342 File size of /raw_data/ex.20130302T121135/ov.s1a1.wb is 186294206464 (45481984 blocks, blocksize 4096) ext logical physical expected length flags 0 0 13 4550656 1 4550656 188136807 4550668 12562432 2 17113088 200699240 200699238 622592 3 17735680 182046055 201321831 4096 4 17739776 182041959 182050150 4096 5 17743872 182037863 182046054 4096 6 17747968 182033767 182041958 4096 7 17752064 182029671 182037862 4096 ... 6757 45400064 154381644 154389835 4096 6758 45404160 154377548 154385739 4096 6759 45408256 252951571 154381643 73728 eof /raw_data/ex.20130302T121135/ov.s1a1.wb: 6760 extents found So we see that at one moment, the allocator starts giving us 16 MB chunks backwards. This seems to be caused by XFS_ALLOCTYPE_NEAR_BNO allocation. For two cases I was able to track down the logic: 1) We start allocating blocks for file. We want to allocate in the same AG as the inode is. First we try exact allocation which fails so we try XFS_ALLOCTYPE_NEAR_BNO allocation which finds large enough free extent before the inode. So we start allocating 16 MB chunks from the end of that free extent. From this moment on we are basically bound to continue allocating backwards using XFS_ALLOCTYPE_NEAR_BNO allocation until we exhaust the whole free extent. 2) Similar situation happens when we cannot further grow current extent but there is large free space somewhere before this extent in the AG. So I was wondering is this known? Is XFS_ALLOCTYPE_NEAR_BNO so beneficial it outweights pathological cases like the above? Or shouldn't it maybe be disabled for larger files or for direct IO? Honza -- Jan Kara SUSE Labs, CR From sandeen@sandeen.net Wed Mar 6 14:37:42 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 0C9C97F9A for ; Wed, 6 Mar 2013 14:37:42 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay1.corp.sgi.com (Postfix) with ESMTP id ED23D8F8074 for ; Wed, 6 Mar 2013 12:37:38 -0800 (PST) X-ASG-Debug-ID: 1362602257-04cbb07dbf217cc0001-NocioJ Received: from sandeen.net (sandeen.net [63.231.237.45]) by cuda.sgi.com with ESMTP id smVCVnmJNLlceVpj for ; Wed, 06 Mar 2013 12:37:37 -0800 (PST) X-Barracuda-Envelope-From: sandeen@sandeen.net X-Barracuda-Apparent-Source-IP: 63.231.237.45 Received: from liberator.sandeen.net (liberator.sandeen.net [10.0.0.4]) (using TLSv1 with cipher DHE-RSA-CAMELLIA256-SHA (256/256 bits)) (No client certificate requested) by sandeen.net (Postfix) with ESMTPSA id 7C44063C3E25; Wed, 6 Mar 2013 14:37:37 -0600 (CST) Message-ID: <5137A910.7090404@sandeen.net> Date: Wed, 06 Mar 2013 14:37:36 -0600 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: Hans-Peter Jansen CC: david@fromorbit.com, xfs@oss.sgi.com Subject: Re: Fwd: xfs_reno References: <20351675.Zy117sIl8Z@xrated> X-ASG-Orig-Subj: Re: Fwd: xfs_reno In-Reply-To: <20351675.Zy117sIl8Z@xrated> X-Enigmail-Version: 1.5.1 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit X-Barracuda-Connect: sandeen.net[63.231.237.45] X-Barracuda-Start-Time: 1362602257 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124446 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On 3/6/13 8:55 AM, Hans-Peter Jansen wrote: > Hi Dave, > > I tried to gather Barrys SOB, but failed so far. His trace ends in 2009 google > wise. I've got him. ;) I asked him to chime in here or maybe email you personally. Thanks, -Eric > How is this case usually handled? > > Here's the current state of things. > > Cheers, > Pete > > > ---------- Weitergeleitete Nachricht ---------- > > Betreff: xfs_reno > Datum: Mittwoch, 6. März 2013, 12:52:19 > Von: Hans-Peter Jansen > An: bnaujok@sgi.com > > Hi Barry, > > attached is a slightly mangled version of your xfs_reno tool, that I badly > needed recently. While at it, I plan to submit it, as it saved my *ss. Thanks. > > Apart from relocation to xfsprogs, I just changed this > > + log_message(LOG_DEBUG, "%s: %llu %lu %s", msg, node->ino, > + node->numpaths, node->paths[0]); > > from %llu to %lu for the node->numpaths argument. It might still be wrong, as > numpath is defined as nlink_t which is a __u32 type, but the %s printed > garbage like this: > > Scanning directory tree... > xfs_reno: add_node_path: ino 8611163235, path > /work/dlbase/hosts/11.2/pico/var/run/screens > xfs_reno: add_node_path: ino 8611163233, path > /work/dlbase/hosts/11.2/pico/var/run/pcscd/pcscd.events > xfs_reno: add_node_path: ino 8611163234, path > /work/dlbase/hosts/11.2/pico/var/run/uscreens > xfs_reno: nodehash: 8611163233 692488159933497345 ��]��f�e� > xfs_reno: nodehash: 8611163234 692366801337581569 ��]��f�e� > xfs_reno: nodehash: 8611163235 692223830466232321 ��]��f�e� > > I guess, gcc is smart enough to see, that the struct members overlap here, and > prints the paths[0] argument as a %llu value. What do you think? > > Anyway, I will revise this during the course of creating a xlstests test for > xfs_reno... > > Do you allow me to add your Signed-off-by to this patch? > > If you want to build this, apply both patches to xfsprogs. > > TIA, > Pete > > ------------------------------------------------------------- > > > > _______________________________________________ > xfs mailing list > xfs@oss.sgi.com > http://oss.sgi.com/mailman/listinfo/xfs > From bpm@sgi.com Wed Mar 6 16:01:59 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 228907F77 for ; Wed, 6 Mar 2013 16:01:59 -0600 (CST) Received: from whiskey.americas.sgi.com (eagdhcp-232-197.americas.sgi.com [128.162.232.197]) by relay1.corp.sgi.com (Postfix) with ESMTP id EE5A08F8092; Wed, 6 Mar 2013 14:01:55 -0800 (PST) Received: by whiskey.americas.sgi.com (Postfix, from userid 4600) id C1315500B4B; Wed, 6 Mar 2013 16:01:55 -0600 (CST) Date: Wed, 6 Mar 2013 16:01:55 -0600 From: Ben Myers To: Jan Kara Cc: xfs@oss.sgi.com Subject: Re: Pathological allocation pattern with direct IO Message-ID: <20130306220155.GM22182@sgi.com> References: <20130306202210.GA1318@quack.suse.cz> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <20130306202210.GA1318@quack.suse.cz> User-Agent: Mutt/1.5.20 (2009-06-14) Hi Jan, On Wed, Mar 06, 2013 at 09:22:10PM +0100, Jan Kara wrote: > one of our customers has application that write large (tens of GB) files > using direct IO done in 16 MB chunks. They keep the fs around 80% full > deleting oldest files when they need to store new ones. Usually the file > can be stored in under 10 extents but from time to time a pathological case > is triggered and the file has few thousands extents (which naturally has > impact on performance). The customer actually uses 2.6.32-based kernel but > I reproduced the issue with 3.8.2 kernel as well. > > I was analyzing why this happens and the filefrag for the file looks like: > Filesystem type is: 58465342 > File size of /raw_data/ex.20130302T121135/ov.s1a1.wb is 186294206464 > (45481984 blocks, blocksize 4096) > ext logical physical expected length flags > 0 0 13 4550656 > 1 4550656 188136807 4550668 12562432 > 2 17113088 200699240 200699238 622592 > 3 17735680 182046055 201321831 4096 > 4 17739776 182041959 182050150 4096 > 5 17743872 182037863 182046054 4096 > 6 17747968 182033767 182041958 4096 > 7 17752064 182029671 182037862 4096 > ... > 6757 45400064 154381644 154389835 4096 > 6758 45404160 154377548 154385739 4096 > 6759 45408256 252951571 154381643 73728 eof > /raw_data/ex.20130302T121135/ov.s1a1.wb: 6760 extents found > > So we see that at one moment, the allocator starts giving us 16 MB chunks > backwards. This seems to be caused by XFS_ALLOCTYPE_NEAR_BNO allocation. For > two cases I was able to track down the logic: > > 1) We start allocating blocks for file. We want to allocate in the same AG > as the inode is. First we try exact allocation which fails so we try > XFS_ALLOCTYPE_NEAR_BNO allocation which finds large enough free extent > before the inode. So we start allocating 16 MB chunks from the end of that > free extent. From this moment on we are basically bound to continue > allocating backwards using XFS_ALLOCTYPE_NEAR_BNO allocation until we > exhaust the whole free extent. > > 2) Similar situation happens when we cannot further grow current extent but > there is large free space somewhere before this extent in the AG. > > So I was wondering is this known? Is XFS_ALLOCTYPE_NEAR_BNO so beneficial > it outweights pathological cases like the above? Or shouldn't it maybe be > disabled for larger files or for direct IO? I believe we've seen something similar to #2 before: # xfs_bmap -v /data/dbench.dat /data/dbench.dat: EXT: FILE-OFFSET BLOCK-RANGE AG AG-OFFSET TOTAL FLAGS 0: [0..150994943]: 2343559168..2494554111 5 (2048..150996991) 150994944 00011 1: [150994944..468582399]: 2494556160..2812143615 5 (150999040..468586495) 317587456 00011 2: [468582400..670957567]: 3078479872..3280855039 6 (266211328..468586495) 202375168 00011 3: [670957568..671088639]: 3078346752..3078477823 6 (266078208..266209279) 131072 00011 4: [671088640..671219711]: 3078215680..3078346751 6 (265947136..266078207) 131072 00011 5: [671219712..671350783]: 3078084608..3078215679 6 (265816064..265947135) 131072 00011 6: [671350784..671481855]: 3077953536..3078084607 6 (265684992..265816063) 131072 00011 7: [671481856..671612927]: 3077822464..3077953535 6 (265553920..265684991) 131072 00011 8: [671612928..671743999]: 3077691392..3077822463 6 (265422848..265553919) 131072 00011 9: [671744000..671875071]: 3077560320..3077691391 6 (265291776..265422847) 131072 00011 ... 2040: [4216979456..4502192127]: 6562093056..6847305727 14 (133120..285345791) 285212672 00011 2041: [4502192128..4685430783]: 6847307776..7030546431 14 (285347840..468586495) 183238656 00011 2042: [4685430784..4876402687]: 9183129600..9374101503 19 (277612544..468584447) 190971904 00011 2043: [4876402688..5344985087]: 9374230528..9842812927 20 (2048..468584447) 468582400 00011 2044: [5344985088..5813567487]: 9842941952..10311524351 21 (2048..468584447) 468582400 00011 2045: [5813567488..6282149887]: 10311653376..10780235775 22 (2048..468584447) 468582400 00011 2046: [6282149888..6750732287]: 10780364800..11248947199 23 (2048..468584447) 468582400 00011 2047: [6750732288..6767501311]: 11249076224..11265845247 24 (2048..16771071) 16769024 00011 2048: [6767501312..7219314687]: 11265845248..11717658623 24 (16771072..468584447) 451813376 00011 2049: [7219314688..7687766015]: 11717918720..12186370047 25 (133120..468584447) 468451328 2050: [7687766016..8156348415]: 12186499072..12655081471 26 (2048..468584447) 468582400 00011 2051: [8156348416..8449425407]: 12655210496..12948287487 27 (2048..293079039) 293076992 00011 In this case, the allocation in AG 6 starts near the middle of the AG and runs through the end. At that point we began to march backward through the AG until it was exhausted. Not ideal. Maybe it would be better if XFS_ALLOCTYPE_NEAR_BNO would move on to the next AG if it reached the end of the current one. We need to be careful though. What is good for this workload may have unintended consequences for another. Could you post geometry information for the filesystem in question? xfs_growfs -n /dev/sda Thanks, Ben From eflorac@intellique.com Wed Mar 6 16:21:25 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 184B67FAF for ; Wed, 6 Mar 2013 16:21:25 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay3.corp.sgi.com (Postfix) with ESMTP id 990A6AC004 for ; Wed, 6 Mar 2013 14:21:21 -0800 (PST) X-ASG-Debug-ID: 1362608477-04cb6c2b01215220001-NocioJ Received: from smtp3-g21.free.fr (smtp3-g21.free.fr [212.27.42.3]) by cuda.sgi.com with ESMTP id lTDL5E91WeuMjuXQ for ; Wed, 06 Mar 2013 14:21:18 -0800 (PST) X-Barracuda-Envelope-From: eflorac@intellique.com X-Barracuda-Apparent-Source-IP: 212.27.42.3 Received: from galadriel.home (unknown [82.235.234.79]) by smtp3-g21.free.fr (Postfix) with ESMTP id F23FDA611A; Wed, 6 Mar 2013 23:21:13 +0100 (CET) Date: Wed, 6 Mar 2013 23:21:00 +0100 From: Emmanuel Florac To: Julien FERRERO Cc: xfs@oss.sgi.com Subject: Re: XFS filesystem corruption Message-ID: <20130306232100.6286f640@galadriel.home> X-ASG-Orig-Subj: Re: XFS filesystem corruption In-Reply-To: References: <20130306161519.2c28d911@galadriel.home> Organization: Intellique X-Mailer: Claws Mail 3.7.8 (GTK+ 2.24.4; i686-pc-linux-gnu) Mime-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: quoted-printable X-Barracuda-Connect: smtp3-g21.free.fr[212.27.42.3] X-Barracuda-Start-Time: 1362608477 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124454 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- Le Wed, 6 Mar 2013 17:16:31 +0100 vous =C3=A9criviez: > I don't think the H/W RAID is > the issue since we have the same corruption with other setup without > H/W RAID. HW RAID may exacerbate the problem. XFS is absolutely, definitely not "brutal power off" safe. All linux systems from this century are perfectly able to turn themselves off properly at a single press of the power button; the only safe options are educating the users or mounting the filesystem read-only. And yes, the ls garbled output is caracteristic of a filesystem corruption. --=20 ------------------------------------------------------------------------ Emmanuel Florac | Direction technique | Intellique | | +33 1 78 94 84 02 ------------------------------------------------------------------------ From rwheeler@redhat.com Wed Mar 6 17:12:15 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id C84DA7F69 for ; Wed, 6 Mar 2013 17:12:15 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay1.corp.sgi.com (Postfix) with ESMTP id 98FA28F8078 for ; Wed, 6 Mar 2013 15:12:12 -0800 (PST) X-ASG-Debug-ID: 1362611531-04bdf02295232e80001-NocioJ Received: from mx1.redhat.com (mx1.redhat.com [209.132.183.28]) by cuda.sgi.com with ESMTP id xLczGGbMLEotYbZW for ; Wed, 06 Mar 2013 15:12:11 -0800 (PST) X-Barracuda-Envelope-From: rwheeler@redhat.com X-Barracuda-Apparent-Source-IP: 209.132.183.28 X-ASG-Whitelist: Client Received: from int-mx01.intmail.prod.int.phx2.redhat.com (int-mx01.intmail.prod.int.phx2.redhat.com [10.5.11.11]) by mx1.redhat.com (8.14.4/8.14.4) with ESMTP id r26NC85h031066 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=OK); Wed, 6 Mar 2013 18:12:08 -0500 Received: from tunkums.home (ovpn-112-33.phx2.redhat.com [10.3.112.33]) by int-mx01.intmail.prod.int.phx2.redhat.com (8.13.8/8.13.8) with ESMTP id r26NC7UN028039; Wed, 6 Mar 2013 18:12:07 -0500 Message-ID: <5137CD46.6070909@redhat.com> Date: Wed, 06 Mar 2013 18:12:06 -0500 From: Ric Wheeler User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:17.0) Gecko/20130219 Thunderbird/17.0.3 MIME-Version: 1.0 To: Emmanuel Florac CC: Julien FERRERO , xfs@oss.sgi.com Subject: Re: XFS filesystem corruption References: <20130306161519.2c28d911@galadriel.home> <20130306232100.6286f640@galadriel.home> X-ASG-Orig-Subj: Re: XFS filesystem corruption In-Reply-To: <20130306232100.6286f640@galadriel.home> Content-Type: text/plain; charset=UTF-8; format=flowed Content-Transfer-Encoding: 8bit X-Scanned-By: MIMEDefang 2.67 on 10.5.11.11 X-Barracuda-Connect: mx1.redhat.com[209.132.183.28] X-Barracuda-Start-Time: 1362611531 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 On 03/06/2013 05:21 PM, Emmanuel Florac wrote: > Le Wed, 6 Mar 2013 17:16:31 +0100 vous écriviez: > >> I don't think the H/W RAID is >> the issue since we have the same corruption with other setup without >> H/W RAID. > HW RAID may exacerbate the problem. XFS is absolutely, definitely not > "brutal power off" safe. All linux systems from this century are > perfectly able to turn themselves off properly at a single press of the > power button; the only safe options are educating the users or mounting > the filesystem read-only. > > And yes, the ls garbled output is caracteristic of a filesystem > corruption. > We actually test brutal "Power off" for xfs, ext4 and other file systems. If your storage is configured properly and you have barriers enabled, they all pass without corruption. What hardware raid cards can do is to hide a volatile write cache. Either on the raid HBA itself or, even worse, on the backend disks behind the card. S-ata disks tend to default to write cache enabled and need to be checked especially careful (sas drives tend to be write cache disabled by default). ric From dsterba@suse.cz Wed Mar 6 17:22:28 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 95E7A7FB1 for ; Wed, 6 Mar 2013 17:22:28 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id 79570304067 for ; Wed, 6 Mar 2013 15:22:25 -0800 (PST) X-ASG-Debug-ID: 1362612144-04cbb07dbc220120001-NocioJ Received: from mx2.suse.de (cantor2.suse.de [195.135.220.15]) by cuda.sgi.com with ESMTP id BGE2wAd4VcSlYHxQ for ; Wed, 06 Mar 2013 15:22:24 -0800 (PST) X-Barracuda-Envelope-From: dsterba@suse.cz X-Barracuda-Apparent-Source-IP: 195.135.220.15 Received: from relay1.suse.de (unknown [195.135.220.254]) by mx2.suse.de (Postfix) with ESMTP id 06AE5A39D2; Thu, 7 Mar 2013 00:22:24 +0100 (CET) Received: by ds.suse.cz (Postfix, from userid 10065) id 311CDDA800; Thu, 7 Mar 2013 00:22:22 +0100 (CET) Date: Thu, 7 Mar 2013 00:22:22 +0100 From: David Sterba To: Wang Sheng-Hui Cc: xfs@oss.sgi.com Subject: Re: [PATCH] xfstests 273: fix a typo Message-ID: <20130306232222.GF21081@twin.jikos.cz> X-ASG-Orig-Subj: Re: [PATCH] xfstests 273: fix a typo Reply-To: dsterba@suse.cz Mail-Followup-To: dsterba@suse.cz, Wang Sheng-Hui , xfs@oss.sgi.com References: <512DAC1A.2040601@gmail.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <512DAC1A.2040601@gmail.com> User-Agent: Mutt/1.5.21 (2011-07-01) X-Barracuda-Connect: cantor2.suse.de[195.135.220.15] X-Barracuda-Start-Time: 1362612144 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124458 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Wed, Feb 27, 2013 at 02:47:54PM +0800, Wang Sheng-Hui wrote: > Make the porter log cp failure into $seq.full by appending, not overwriting, > which can help debug. > > Signed-off-by: Wang Sheng-Hui > --- > 273 | 2 +- > 1 file changed, 1 insertion(+), 1 deletion(-) > > diff --git a/273 b/273 > index 67f3d6b..639e280 100755 > --- a/273 > +++ b/273 > @@ -92,7 +92,7 @@ _porter() > exit > fi > > - cp -r $SCRATCH_MNT/origin $SCRATCH_MNT/sub_$_suffix >$seq.full 2>&1 > + cp -r $SCRATCH_MNT/origin $SCRATCH_MNT/sub_$_suffix >>$seq.full 2>&1 This gives me 273 154s ... [20:05:00] [20:05:01] - output mismatch (see 273.out.bad) --- 273.out 2011-11-11 15:13:46.000000000 +0100 +++ 273.out.bad 2013-03-06 20:05:01.000000000 +0100 @@ -1,4 +1,4 @@ QA output created by 273 ------------------------------- -start the workload ------------------------------- +./273: line 95: syntax error near unexpected token `&' +./273: line 95: ` cp -r $SCRATCH_MNT/origin $SCRATCH_MNT/sub_$_suffix >$seq.full 2>>&1' +umount: /dev/sda9: not mounted ... (Run 'diff -u 273.out 273.out.bad' to see the entire diff) --- The script calls /bin/bash, my version says GNU bash, version 4.1.10(1)-release david From kj13yw@gwmail.gwu.edu Wed Mar 6 20:05:08 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=FREEMAIL_FROM,HTML_MESSAGE autolearn=ham version=3.3.1 X-Original-To: linux-xfs@oss.sgi.com Delivered-To: linux-xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 9A5447FA3 for ; Wed, 6 Mar 2013 20:05:08 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay2.corp.sgi.com (Postfix) with ESMTP id 771C4304048 for ; Wed, 6 Mar 2013 18:05:05 -0800 (PST) X-ASG-Debug-ID: 1362621902-04bdf0229523ba10001-w1Z2WR Received: from mail-la0-f42.google.com (mail-la0-f42.google.com [209.85.215.42]) by cuda.sgi.com with ESMTP id Rhbzo0FJOElHezgR (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Wed, 06 Mar 2013 18:05:03 -0800 (PST) X-Barracuda-Envelope-From: kj13yw@gwmail.gwu.edu X-Barracuda-Apparent-Source-IP: 209.85.215.42 Received: by mail-la0-f42.google.com with SMTP id fe20so8186879lab.15 for ; Wed, 06 Mar 2013 18:05:02 -0800 (PST) X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=20120113; h=mime-version:x-received:sender:date:x-google-sender-auth:message-id :subject:from:to:content-type:x-gm-message-state; bh=ACvrSAUZlLP3R4azRpB7hpowhmnfHpu45mIboBa/Hk4=; b=id6BbQJQOAe2+u/vZ2zzg2Bf4dJv/qYHmlEV36Y+OsJSle8hQ9MNnbtp/swrioDm/l Iry22OcP2WpVEkaKkJXh1FlD/izSiels+U09IjEf/rTRjlM5DyWzHBsgnI/+SkFjPri4 vJCH4I3yW0SrGLRqPvm1HoANp7qU3eug1yTA+/bbjAja3n7yN72vEs8DWpzTdZZlfPO3 aU7s98o1y3LmrQJBgYZnp7W1ZpI2ZrRKP4OKg3VbCOStdF5QfdH9ybxYz3DqqLdlvM33 rFIDS7apI9oSRVHUEkK9miu0tKzSDKP2fjURCTaHsdgfhzKVj85JR/ZmQUnlHb8bln6N RA4w== MIME-Version: 1.0 X-Received: by 10.112.28.169 with SMTP id c9mr8490910lbh.84.1362621900807; Wed, 06 Mar 2013 18:05:00 -0800 (PST) Sender: kj13yw@gwmail.gwu.edu Received: by 10.112.45.39 with HTTP; Wed, 6 Mar 2013 18:05:00 -0800 (PST) Date: Thu, 7 Mar 2013 03:05:00 +0100 X-Google-Sender-Auth: dMmz_PdXOpZdcIa17Frd1w3FWes Message-ID: Subject: Partnership From: "CHUO MALLEABLE IRON CO., LTD" X-ASG-Orig-Subj: Partnership To: undisclosed-recipients:; Content-Type: multipart/alternative; boundary=bcaec554d8325e646004d74c22cb X-Gm-Message-State: ALoCoQn4hIdoVWVGBP3OPTdmwD0kZLvsS5KQws3ZmMuQRfsnpc114MvDTBM9iNND4g5rMbnCK+kl X-Barracuda-Connect: mail-la0-f42.google.com[209.85.215.42] X-Barracuda-Start-Time: 1362621903 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=HTML_MESSAGE X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124468 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 HTML_MESSAGE BODY: HTML included in message --bcaec554d8325e646004d74c22cb Content-Type: text/plain; charset=ISO-8859-1 We need your partnership in our company. Sincerely, Hisao Takeyama --bcaec554d8325e646004d74c22cb Content-Type: text/html; charset=ISO-8859-1 We need your partnership in our company.

Sincerely,
Hisao Takeyama
--bcaec554d8325e646004d74c22cb-- From david@fromorbit.com Wed Mar 6 21:39:06 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 392877FA2 for ; Wed, 6 Mar 2013 21:39:06 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay3.corp.sgi.com (Postfix) with ESMTP id C7548AC001 for ; Wed, 6 Mar 2013 19:39:05 -0800 (PST) X-ASG-Debug-ID: 1362627543-04bdf0229723f690001-NocioJ Received: from ipmail06.adl2.internode.on.net (ipmail06.adl2.internode.on.net [150.101.137.129]) by cuda.sgi.com with ESMTP id gmCkOC4K7WtUOrbi for ; Wed, 06 Mar 2013 19:39:04 -0800 (PST) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.129 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: ArckAAkLOFF5LAvR/2dsb2JhbABDvyyFFgECAYFjF3OCKwEBBTocMwgDGAklDwUNGAMhARKIAQMOsWYNiVoVjC+BBUIYH1GCX2EDlGuBX4tZhRiDHYFV Received: from ppp121-44-11-209.lns20.syd6.internode.on.net (HELO dastard) ([121.44.11.209]) by ipmail06.adl2.internode.on.net with ESMTP; 07 Mar 2013 14:08:50 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UDRfN-0004MX-TR; Thu, 07 Mar 2013 14:38:49 +1100 Date: Thu, 7 Mar 2013 14:38:49 +1100 From: Dave Chinner To: dsterba@suse.cz, Wang Sheng-Hui , xfs@oss.sgi.com Subject: Re: [PATCH] xfstests 273: fix a typo Message-ID: <20130307033849.GB6369@dastard> X-ASG-Orig-Subj: Re: [PATCH] xfstests 273: fix a typo References: <512DAC1A.2040601@gmail.com> <20130306232222.GF21081@twin.jikos.cz> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <20130306232222.GF21081@twin.jikos.cz> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail06.adl2.internode.on.net[150.101.137.129] X-Barracuda-Start-Time: 1362627543 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124474 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Thu, Mar 07, 2013 at 12:22:22AM +0100, David Sterba wrote: > On Wed, Feb 27, 2013 at 02:47:54PM +0800, Wang Sheng-Hui wrote: > > Make the porter log cp failure into $seq.full by appending, not overwriting, > > which can help debug. > > > > Signed-off-by: Wang Sheng-Hui > > --- > > 273 | 2 +- > > 1 file changed, 1 insertion(+), 1 deletion(-) > > > > diff --git a/273 b/273 > > index 67f3d6b..639e280 100755 > > --- a/273 > > +++ b/273 > > @@ -92,7 +92,7 @@ _porter() > > exit > > fi > > > > - cp -r $SCRATCH_MNT/origin $SCRATCH_MNT/sub_$_suffix >$seq.full 2>&1 > > + cp -r $SCRATCH_MNT/origin $SCRATCH_MNT/sub_$_suffix >>$seq.full 2>&1 > > This gives me > > 273 154s ... [20:05:00] [20:05:01] - output mismatch (see 273.out.bad) > --- 273.out 2011-11-11 15:13:46.000000000 +0100 > +++ 273.out.bad 2013-03-06 20:05:01.000000000 +0100 > @@ -1,4 +1,4 @@ > QA output created by 273 > ------------------------------- > -start the workload > ------------------------------- > +./273: line 95: syntax error near unexpected token `&' > +./273: line 95: ` cp -r $SCRATCH_MNT/origin $SCRATCH_MNT/sub_$_suffix >$seq.full 2>>&1' > +umount: /dev/sda9: not mounted that seems rather strange. The patch does this: ....sub_$_suffix >>$seq.full 2>&1 and the error output you see is ....sub_$_suffix >$seq.full 2>>&1 So it doesn't look lie you are running with the change that is actually in the patch... > ... > (Run 'diff -u 273.out 273.out.bad' to see the entire diff) > --- > > The script calls /bin/bash, my version says > GNU bash, version 4.1.10(1)-release Wroks fine here, with: GNU bash, version 4.2.37(1)-release Cheers, Dave. -- Dave Chinner david@fromorbit.com From stan@hardwarefreak.com Wed Mar 6 21:56:08 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 468027F63 for ; Wed, 6 Mar 2013 21:56:08 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay1.corp.sgi.com (Postfix) with ESMTP id 164718F8073 for ; Wed, 6 Mar 2013 19:56:04 -0800 (PST) X-ASG-Debug-ID: 1362628563-04bdf02297240280001-NocioJ Received: from greer.hardwarefreak.com (mo-65-41-216-221.sta.embarqhsd.net [65.41.216.221]) by cuda.sgi.com with ESMTP id R5wdKNg6F5b7DRDK for ; Wed, 06 Mar 2013 19:56:03 -0800 (PST) X-Barracuda-Envelope-From: stan@hardwarefreak.com X-Barracuda-Apparent-Source-IP: 65.41.216.221 X-Barracuda-User-Whitelist: xfs@oss.sgi.com Received: from [192.168.100.53] (gffx.hardwarefreak.com [192.168.100.53]) by greer.hardwarefreak.com (Postfix) with ESMTP id 7139C6C159; Wed, 6 Mar 2013 21:56:03 -0600 (CST) Message-ID: <51380FD3.5010302@hardwarefreak.com> Date: Wed, 06 Mar 2013 21:56:03 -0600 From: Stan Hoeppner Reply-To: stan@hardwarefreak.com User-Agent: Mozilla/5.0 (Windows NT 5.1; rv:17.0) Gecko/20130215 Thunderbird/17.0.3 MIME-Version: 1.0 To: Julien FERRERO CC: xfs@oss.sgi.com Subject: Re: XFS filesystem corruption References: X-ASG-Orig-Subj: Re: XFS filesystem corruption In-Reply-To: Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: mo-65-41-216-221.sta.embarqhsd.net[65.41.216.221] X-Barracuda-Start-Time: 1362628563 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 On 3/6/2013 9:08 AM, Julien FERRERO wrote: > The filesystem was originally created with the command: > # mkfs.xfs -f -l size=32m /dev/md0 It may be unrelated to your corruption, problem but I'm curious why you are specifying a 32MB log section instead of letting mkfs.xfs make the log size decision. > corruption. I only know that units are used to be power cycle by > operator while the fs is still mounted (no proper shutdown / reboot). > My guess is the fs journal shall handle this case and avoid such > corruption. As others have stated, this operator needs to be flogged and educated. A computer based video ingestion/playback system with disk storage and a complex filesystem is not a tape deck. You can't can't simply power it off as if it were a tape deck. I would assume based on your description that this is a mobile storage system, often moved from one location to another, probably in a van, and this is why the operator simply hits the power switch? Live news crew type application or similar? -- Stan From david@fromorbit.com Wed Mar 6 21:57:41 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id B2E157FA5 for ; Wed, 6 Mar 2013 21:57:41 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay1.corp.sgi.com (Postfix) with ESMTP id 9CB448F8073 for ; Wed, 6 Mar 2013 19:57:41 -0800 (PST) X-ASG-Debug-ID: 1362628658-04cb6c2b032249e0001-NocioJ Received: from ipmail06.adl2.internode.on.net (ipmail06.adl2.internode.on.net [150.101.137.129]) by cuda.sgi.com with ESMTP id PbOWtQ47Azbrt4CM for ; Wed, 06 Mar 2013 19:57:39 -0800 (PST) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.129 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: ArkkAMkOOFF5LAvR/2dsb2JhbAApGr8shRYBAgGBYxdzgisBAQQBJxMcIwULCAMYCSUPBSUDIROIDQUNLrsUFY1QJhgfSgeCX2EDlkqQcYFTgUo Received: from ppp121-44-11-209.lns20.syd6.internode.on.net (HELO dastard) ([121.44.11.209]) by ipmail06.adl2.internode.on.net with ESMTP; 07 Mar 2013 14:27:38 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UDRxZ-0004P1-4v; Thu, 07 Mar 2013 14:57:37 +1100 Date: Thu, 7 Mar 2013 14:57:37 +1100 From: Dave Chinner To: Dennis Kaarsemaker Cc: xfs@oss.sgi.com Subject: Re: XFS IO multiplication problem on centos/rhel 6 using hp p420i raid controllers Message-ID: <20130307035737.GC6369@dastard> X-ASG-Orig-Subj: Re: XFS IO multiplication problem on centos/rhel 6 using hp p420i raid controllers References: <1362060736.1247.30.camel@seahawk> <20130228194023.GQ5551@dastard> <1362577992.1247.84.camel@seahawk> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <1362577992.1247.84.camel@seahawk> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail06.adl2.internode.on.net[150.101.137.129] X-Barracuda-Start-Time: 1362628658 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.60 X-Barracuda-Spam-Status: No, SCORE=0.60 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_SA085, BSF_SC1_TG070, BSF_SC5_SA210e X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124476 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.10 BSF_SC0_SA085 Custom Rule SA085 0.00 BSF_SC5_SA210e Custom Rule SA210e 0.50 BSF_SC1_TG070 Custom Rule TG070 On Wed, Mar 06, 2013 at 02:53:12PM +0100, Dennis Kaarsemaker wrote: > On Fri, 2013-03-01 at 06:40 +1100, Dave Chinner wrote: > > On Thu, Feb 28, 2013 at 03:12:16PM +0100, Dennis Kaarsemaker wrote: > > > Hello XFS developers, > > > > > > I have a problem as described in the subject. If I read the xfs website > > > correctly, this would be a place to ask for support with that problem. > > > Before I spam you all with details, please confirm if this is true or > > > direct me to a better place. Thanks! > > > > CentOS/RHEL problems can be triaged up to a point here. i.e. we will > > make an effort to pinpoint the problem, but we give no guarantees > > and we definitely can't fix it. If you want a btter triage guarantee > > and to talk to someone who is able to fix the problem, you need to > > work through the problem with your RHEL support contact. > > Hi Dave, > > Thanks for responding. We have filed support tickets with HP and Red Hat > as well, I was trying to parallelize the search for an answer as the > problem is really getting in the way here. So much so that I've offered > a bottle of $favourite_drink on a serverfault question to the one who > solves it, that offer applies here too :) > > > Either way: > > > > http://xfs.org/index.php/XFS_FAQ#Q:_What_information_should_I_include_when_reporting_a_problem.3F > > A summary of the problem is this: > > [root@bc290bprdb-01 ~]# collectl > #<----CPU[HYPER]-----><----------Disks-----------><----------Network----------> > #cpu sys inter ctxsw KBRead Reads KBWrit Writes KBIn PktIn KBOut PktOut > 1 0 1636 4219 16 1 2336 313 184 195 12 133 > 1 0 1654 2804 64 3 2919 432 391 352 20 208 > > [root@bc291bprdb-01 ~]# collectl > #<----CPU[HYPER]-----><----------Disks-----------><----------Network----------> > #cpu sys inter ctxsw KBRead Reads KBWrit Writes KBIn PktIn KBOut PktOut > 1 0 2220 3691 332 13 39992 331 112 122 6 92 > 0 0 1354 2708 0 0 39836 335 103 125 9 99 > 0 0 1563 3023 120 6 44036 369 399 317 13 188 > > Notice the KBWrit difference. These are two identical hp gen 8 machines, > doing the same thing (replicating the same mysql schema). The one > writing ten times as many bytes in the same amount of transactions is > running centos 6 (and was running rhel 6). So what is the problem? it is writing too much on the on the centos 6 machine? Either way, this doesn't sound like a filesystem problem - the size and amount of data writes is entirely determined by the application. > /dev/mapper/sysvm-mysqlVol /mysql/bp xfs rw,relatime,attr2,delaylog,allocsize=1024k,logbsize=256k,sunit=512,swidth=1536,noquota 0 0 What is the reason for using allocsize, sunit/swidth? Are you using them on other machines? And if you remove the allocsize mount option, does the behaviour on centos6.3 change? What happens if you set allocsize=4k? > xfs_info: > > [root@bc291bprdb-01 ~]# xfs_info /mysql/bp/ > meta-data=/dev/mapper/sysvm-mysqlVol isize=256 agcount=16, agsize=4915136 blks > = sectsz=512 attr=2 > data = bsize=4096 blocks=78642176, imaxpct=25 > = sunit=64 swidth=192 blks > naming =version 2 bsize=4096 ascii-ci=0 > log =internal bsize=4096 blocks=38400, version=2 > = sectsz=512 sunit=64 blks, lazy-count=1 > realtime =none extsz=4096 blocks=0, rtextents=0 > > > And for reference, xfs_info on centos 5: > > [root@bc290bprdb-01 ~]# xfs_info /mysql/bp/ > meta-data=/dev/sysvm/mysqlVol isize=256 agcount=22, agsize=4915200 blks > = sectsz=512 attr=0 > data = bsize=4096 blocks=104857600, imaxpct=25 > = sunit=0 swidth=0 blks, unwritten=1 > naming =version 2 bsize=4096 > log =internal bsize=4096 blocks=32768, version=1 > = sectsz=512 sunit=0 blks, lazy-count=0 > realtime =none extsz=4096 blocks=0, rtextents=0 The only difference is that the centos 6 filesystem is configured with sunit/swidth. That affects allocation alignment, but nothing else. It won't affect IO sizes. > Linux 2.6.18-308.el5 (bc290bprdb-01.lhr4.prod.booking.com) 03/06/2013 > > Device: rrqm/s wrqm/s r/s w/s rMB/s wMB/s avgrq-sz avgqu-sz await svctm %util > cciss/c0d0 6.95 27.09 7.72 270.96 0.19 2.90 22.71 0.07 0.25 0.22 6.00 > cciss/c0d0p1 0.00 0.00 0.00 0.00 0.00 0.00 47.62 0.00 1.69 1.61 0.00 > cciss/c0d0p2 0.00 0.00 0.00 0.00 0.00 0.00 14.40 0.00 4.07 4.06 0.00 > cciss/c0d0p3 6.94 27.09 7.72 270.96 0.19 2.90 22.71 0.07 0.25 0.22 6.00 > dm-0 0.00 0.00 0.45 32.85 0.01 0.13 8.34 0.02 0.49 0.07 0.24 > dm-1 0.00 0.00 6.97 264.13 0.15 2.77 22.10 0.07 0.24 0.22 5.93 So, 8k IOs on centos 5... > Linux 2.6.32-279.1.1.el6.x86_64 (bc291bprdb-01.lhr4.prod.booking.com) 03/06/2013 _x86_64_ (32 CPU) > > Device: rrqm/s wrqm/s r/s w/s rMB/s wMB/s avgrq-sz avgqu-sz await svctm %util > sda 0.00 3.60 6.00 374.40 0.06 44.18 238.17 0.11 0.28 0.16 6.08 > dm-0 0.00 0.00 0.00 4.40 0.00 0.02 8.00 0.00 0.27 0.18 0.08 > dm-1 0.00 0.00 6.00 373.20 0.06 44.11 238.56 0.11 0.28 0.16 6.04 And 128k IOs on centos 6. Unless there's a massive difference in file layouts, nothing in the filesystem would cause such a dramatic change in IO size or thoughput. Cheers, Dave. -- Dave Chinner david@fromorbit.com From david@fromorbit.com Wed Mar 6 22:13:54 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 87C5C7FA8 for ; Wed, 6 Mar 2013 22:13:54 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay2.corp.sgi.com (Postfix) with ESMTP id 67CF230405F for ; Wed, 6 Mar 2013 20:13:51 -0800 (PST) X-ASG-Debug-ID: 1362629629-04cb6c2b022256a0001-NocioJ Received: from ipmail06.adl2.internode.on.net (ipmail06.adl2.internode.on.net [150.101.137.129]) by cuda.sgi.com with ESMTP id TSeejl75L8czR2np for ; Wed, 06 Mar 2013 20:13:49 -0800 (PST) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.129 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: ArckAHwSOFF5LAvR/2dsb2JhbABDvyyFFgECAYFjF3OCKwEBBTocIxAIAxgJJQ8FJQMhE4gSDbtIFY02QBgfSgeCX2EDlkqJZ4cKgx2BXg Received: from ppp121-44-11-209.lns20.syd6.internode.on.net (HELO dastard) ([121.44.11.209]) by ipmail06.adl2.internode.on.net with ESMTP; 07 Mar 2013 14:43:49 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UDSDE-0004RD-E3; Thu, 07 Mar 2013 15:13:48 +1100 Date: Thu, 7 Mar 2013 15:13:48 +1100 From: Dave Chinner To: Hans-Peter Jansen Cc: xfs@oss.sgi.com Subject: Re: Fwd: xfs_reno Message-ID: <20130307041348.GD6369@dastard> X-ASG-Orig-Subj: Re: Fwd: xfs_reno References: <20351675.Zy117sIl8Z@xrated> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <20351675.Zy117sIl8Z@xrated> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail06.adl2.internode.on.net[150.101.137.129] X-Barracuda-Start-Time: 1362629629 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124476 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Wed, Mar 06, 2013 at 03:55:19PM +0100, Hans-Peter Jansen wrote: > Hi Dave, > > I tried to gather Barrys SOB, but failed so far. His trace ends in 2009 google > wise. > > How is this case usually handled? > > Here's the current state of things. He was working for SGI at the time, so you should be able to get anyone from SGI provide a valid S-O-B if needed. As it is, I can probably verify the patch origins sufficiently to add a SOB to it as: http://oss.sgi.com/archives/xfs/2007-11/msg00769.html It's pretty clear that the code was released under the GPL and free from any tainted code by SGI. The post I'm pointing to above is one I made while an SGI employee, and it effectively verifies the origin of the code in the same way a S-O-B does. So, you probably don't even need to chase a S-O-B from SGI if you just point at that email and attribute the code correctly. i.e. retaining al the SGI copyright notices in the code and saying inteh patch description that the code was originally authored by SGI and released under the same license as the rest of the xfs userspace code. Cheers, Dave. -- Dave Chinner david@fromorbit.com From david@fromorbit.com Wed Mar 6 23:03:33 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id C0D9E7FAA for ; Wed, 6 Mar 2013 23:03:33 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay3.corp.sgi.com (Postfix) with ESMTP id 42B4CAC005 for ; Wed, 6 Mar 2013 21:03:30 -0800 (PST) X-ASG-Debug-ID: 1362632607-04cbb07dbf22e700001-NocioJ Received: from ipmail06.adl2.internode.on.net (ipmail06.adl2.internode.on.net [150.101.137.129]) by cuda.sgi.com with ESMTP id rqODy6kEUHkWhk1j for ; Wed, 06 Mar 2013 21:03:28 -0800 (PST) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.129 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: ArgkAFAeOFF5LAvR/2dsb2JhbABDvyyFFgECAYFjF3OCKwEBBTocIxAIAw4KCSUPBSUDIRMbh3e7TRWNdhgfSgeDQAOWSpBxgx0 Received: from ppp121-44-11-209.lns20.syd6.internode.on.net (HELO dastard) ([121.44.11.209]) by ipmail06.adl2.internode.on.net with ESMTP; 07 Mar 2013 15:33:27 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UDSzF-0004Ww-S2; Thu, 07 Mar 2013 16:03:25 +1100 Date: Thu, 7 Mar 2013 16:03:25 +1100 From: Dave Chinner To: Jan Kara Cc: xfs@oss.sgi.com Subject: Re: Pathological allocation pattern with direct IO Message-ID: <20130307050325.GS23616@dastard> X-ASG-Orig-Subj: Re: Pathological allocation pattern with direct IO References: <20130306202210.GA1318@quack.suse.cz> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <20130306202210.GA1318@quack.suse.cz> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail06.adl2.internode.on.net[150.101.137.129] X-Barracuda-Start-Time: 1362632607 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124480 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Wed, Mar 06, 2013 at 09:22:10PM +0100, Jan Kara wrote: > Hello, > > one of our customers has application that write large (tens of GB) files > using direct IO done in 16 MB chunks. They keep the fs around 80% full > deleting oldest files when they need to store new ones. Usually the file > can be stored in under 10 extents but from time to time a pathological case > is triggered and the file has few thousands extents (which naturally has > impact on performance). The customer actually uses 2.6.32-based kernel but > I reproduced the issue with 3.8.2 kernel as well. > > I was analyzing why this happens and the filefrag for the file looks like: > Filesystem type is: 58465342 > File size of /raw_data/ex.20130302T121135/ov.s1a1.wb is 186294206464 > (45481984 blocks, blocksize 4096) > ext logical physical expected length flags > 0 0 13 4550656 > 1 4550656 188136807 4550668 12562432 > 2 17113088 200699240 200699238 622592 > 3 17735680 182046055 201321831 4096 > 4 17739776 182041959 182050150 4096 > 5 17743872 182037863 182046054 4096 > 6 17747968 182033767 182041958 4096 > 7 17752064 182029671 182037862 4096 > ... > 6757 45400064 154381644 154389835 4096 > 6758 45404160 154377548 154385739 4096 > 6759 45408256 252951571 154381643 73728 eof > /raw_data/ex.20130302T121135/ov.s1a1.wb: 6760 extents found > > So we see that at one moment, the allocator starts giving us 16 MB chunks > backwards. This seems to be caused by XFS_ALLOCTYPE_NEAR_BNO allocation. For > two cases I was able to track down the logic: > > 1) We start allocating blocks for file. We want to allocate in the same AG > as the inode is. First we try exact allocation which fails so we try > XFS_ALLOCTYPE_NEAR_BNO allocation which finds large enough free extent > before the inode. So we start allocating 16 MB chunks from the end of that > free extent. From this moment on we are basically bound to continue > allocating backwards using XFS_ALLOCTYPE_NEAR_BNO allocation until we > exhaust the whole free extent. > > 2) Similar situation happens when we cannot further grow current extent but > there is large free space somewhere before this extent in the AG. > > So I was wondering is this known? Is XFS_ALLOCTYPE_NEAR_BNO so beneficial > it outweights pathological cases like the above? Or shouldn't it maybe be > disabled for larger files or for direct IO? Well known issue, first diagnosed about 15 years ago, IIRC. Simple solution: use extent size hints. Cheers, Dave. -- Dave Chinner david@fromorbit.com From bartz7rz@gmail.com Wed Mar 6 23:52:17 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=FREEMAIL_FROM,HTML_MESSAGE, T_DKIM_INVALID autolearn=ham version=3.3.1 X-Original-To: linux-xfs@oss.sgi.com Delivered-To: linux-xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 4070C7FAD for ; Wed, 6 Mar 2013 23:52:17 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay1.corp.sgi.com (Postfix) with ESMTP id 0A7138F8073 for ; Wed, 6 Mar 2013 21:52:16 -0800 (PST) X-ASG-Debug-ID: 1362635535-04bdf022952453d0001-w1Z2WR Received: from mail-oa0-f44.google.com (mail-oa0-f44.google.com [209.85.219.44]) by cuda.sgi.com with ESMTP id rtxbwA78kfw07Dd5 (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Wed, 06 Mar 2013 21:52:15 -0800 (PST) X-Barracuda-Envelope-From: bartz7rz@gmail.com X-Barracuda-Apparent-Source-IP: 209.85.219.44 X-Barracuda-IPDD: Level1 [gmail.com/209.85.219.44] Received: by mail-oa0-f44.google.com with SMTP id h1so130054oag.3 for ; Wed, 06 Mar 2013 21:52:15 -0800 (PST) X-Barracuda-IPDD: Level1 [gmail.com/209.85.219.44] X-Barracuda-IPDD: Level1 [gmail.com/209.85.219.44] DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20120113; h=mime-version:x-received:date:message-id:subject:from:to :content-type; bh=2LMZJLxDcid+YA1rdjyiFt0Q/iPd4Iw/Uw5OhTynIYs=; b=xToKGVbngIr+Igod6Q9FiYw9V3dvL2LXvIFDZNvxDzh5PLPBrYVBd6RY/SrRC2yEO1 Lfsdt2yxklBgvfZCtsZEVnnKsrcpA5XIsCXuSi49K4x//D50mMfXhqhR+A2xEpM1hd4C xzY8+/SWO2YCPWZYyBkBS0UeD8QU8mF2Oge3G6DhFh7VuWO8UQCU6yMfGpwzVdb//Qrs /uKYpmKvMg3zyLhHuQrx1po3h47rdHXUZ1EkzVvbY+0mFXGGREg3B8HbzRbZQ7PTzqSf sooW3rqSn/ROBT/TPUd/dXR2Ih1+9Fd/jlFv8rJCgGlKByJXR43Nqj+ozJLvlkRIzeKw ocdA== MIME-Version: 1.0 X-Received: by 10.60.22.137 with SMTP id d9mr25078858oef.91.1362635534676; Wed, 06 Mar 2013 21:52:14 -0800 (PST) Received: by 10.60.55.4 with HTTP; Wed, 6 Mar 2013 21:52:14 -0800 (PST) Date: Thu, 7 Mar 2013 13:52:14 +0800 Message-ID: Subject: dog supply From: 3U Pet Supply X-ASG-Orig-Subj: dog supply To: undisclosed-recipients:; Content-Type: multipart/alternative; boundary=e89a8f838cff00d42104d74f4f27 X-Barracuda-Connect: mail-oa0-f44.google.com[209.85.219.44] X-Barracuda-Start-Time: 1362635535 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=DKIM_SIGNED, DKIM_VERIFIED, HTML_MESSAGE X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124484 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature 0.00 HTML_MESSAGE BODY: HTML included in message --e89a8f838cff00d42104d74f4f27 Content-Type: text/plain; charset=ISO-8859-1 Hi, this is Jeff Wu from China. We are a factory which produces pet clothes, pet harness, pet leash and pet toys. Please let me know if you are interested to buy from us, thanks! Best regards, Jeff Wu --e89a8f838cff00d42104d74f4f27 Content-Type: text/html; charset=ISO-8859-1
Hi, this is Jeff Wu from China.
We are a factory which produces pet clothes, pet harness, pet leash and pet toys.
Please let me know if you are interested to buy from us, thanks!

Best regards,
Jeff Wu
--e89a8f838cff00d42104d74f4f27-- From dennis.kaarsemaker@booking.com Thu Mar 7 04:11:53 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=T_DKIM_INVALID autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 3C7CB7FAA for ; Thu, 7 Mar 2013 04:11:53 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay2.corp.sgi.com (Postfix) with ESMTP id 089A830405F for ; Thu, 7 Mar 2013 02:11:49 -0800 (PST) X-ASG-Debug-ID: 1362651102-04bdf02296254190001-NocioJ Received: from mail-out3.booking.com (mail-out3.booking.com [91.195.237.20]) by cuda.sgi.com with ESMTP id AIQ8yFDc9JslwhkB (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO) for ; Thu, 07 Mar 2013 02:11:44 -0800 (PST) X-Barracuda-Envelope-From: dennis.kaarsemaker@booking.com X-Barracuda-Apparent-Source-IP: 91.195.237.20 DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=booking.com; s=bk; h=Mime-Version:Content-Transfer-Encoding:Content-Type:References:In-Reply-To:Date:Cc:To:From:Subject:Message-ID; bh=PDCqUNp3Ck2FvclYott+3XVitc8Qo+nkH37vKdM6Ms8=; b=WP6DMu37yLLX8XJxEWhqnJ9y8ZKnDV65p/qgui2s35p7GypjJ86KFbqzCAsQRiH46veWrRiFYQcEH+tFW+XSJS2bRYP7tqyXxwmIxKH7Hc1KhtlEMIawVPSd3qOaF0xM4jRD5w7RlTHvysUTQF1cmBAFWTxIeoCCs010xbP6kDU=; Received: from corpds-102.ams4.corp.booking.com ([10.196.68.83]:38940) by mtx-101.ams4.prod.booking.com with esmtps (TLSv1:DHE-RSA-AES256-SHA:256) (Exim 4.80.1) (envelope-from ) id 1UDXna-0007hX-CB; Thu, 07 Mar 2013 11:11:42 +0100 Received: from [10.155.73.64] (port=41639) by corpds-102.ams4.corp.booking.com with esmtpsa (TLSv1:DHE-RSA-CAMELLIA256-SHA:256) (Exim 4.80.1) (envelope-from ) id 1UDXna-0003xC-7v; Thu, 07 Mar 2013 11:11:42 +0100 Message-ID: <1362651128.16657.13.camel@seahawk> Subject: Re: XFS IO multiplication problem on centos/rhel 6 using hp p420i raid controllers From: Dennis Kaarsemaker X-ASG-Orig-Subj: Re: XFS IO multiplication problem on centos/rhel 6 using hp p420i raid controllers To: Dave Chinner Cc: xfs@oss.sgi.com Date: Thu, 07 Mar 2013 11:12:08 +0100 In-Reply-To: <20130307035737.GC6369@dastard> References: <1362060736.1247.30.camel@seahawk> <20130228194023.GQ5551@dastard> <1362577992.1247.84.camel@seahawk> <20130307035737.GC6369@dastard> Organization: Booking.com Content-Type: text/plain; charset="UTF-8" X-Mailer: Evolution 3.2.3-0ubuntu6 Content-Transfer-Encoding: 7bit Mime-Version: 1.0 X-Barracuda-Connect: mail-out3.booking.com[91.195.237.20] X-Barracuda-Start-Time: 1362651103 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.10 X-Barracuda-Spam-Status: No, SCORE=0.10 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_SA085, BSF_SC5_SA210e, DKIM_SIGNED, DKIM_VERIFIED X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124500 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature 0.10 BSF_SC0_SA085 Custom Rule SA085 0.00 BSF_SC5_SA210e Custom Rule SA210e On Thu, 2013-03-07 at 14:57 +1100, Dave Chinner wrote: > On Wed, Mar 06, 2013 at 02:53:12PM +0100, Dennis Kaarsemaker wrote: > > On Fri, 2013-03-01 at 06:40 +1100, Dave Chinner wrote: > > > On Thu, Feb 28, 2013 at 03:12:16PM +0100, Dennis Kaarsemaker wrote: > > > > Hello XFS developers, > > > > > > > > I have a problem as described in the subject. If I read the xfs website > > > > correctly, this would be a place to ask for support with that problem. > > > > Before I spam you all with details, please confirm if this is true or > > > > direct me to a better place. Thanks! > > > > > > CentOS/RHEL problems can be triaged up to a point here. i.e. we will > > > make an effort to pinpoint the problem, but we give no guarantees > > > and we definitely can't fix it. If you want a btter triage guarantee > > > and to talk to someone who is able to fix the problem, you need to > > > work through the problem with your RHEL support contact. > > > > Hi Dave, > > > > Thanks for responding. We have filed support tickets with HP and Red Hat > > as well, I was trying to parallelize the search for an answer as the > > problem is really getting in the way here. So much so that I've offered > > a bottle of $favourite_drink on a serverfault question to the one who > > solves it, that offer applies here too :) > > > > > Either way: > > > > > > http://xfs.org/index.php/XFS_FAQ#Q:_What_information_should_I_include_when_reporting_a_problem.3F > > > > A summary of the problem is this: > > > > [root@bc290bprdb-01 ~]# collectl > > #<----CPU[HYPER]-----><----------Disks-----------><----------Network----------> > > #cpu sys inter ctxsw KBRead Reads KBWrit Writes KBIn PktIn KBOut PktOut > > 1 0 1636 4219 16 1 2336 313 184 195 12 133 > > 1 0 1654 2804 64 3 2919 432 391 352 20 208 > > > > [root@bc291bprdb-01 ~]# collectl > > #<----CPU[HYPER]-----><----------Disks-----------><----------Network----------> > > #cpu sys inter ctxsw KBRead Reads KBWrit Writes KBIn PktIn KBOut PktOut > > 1 0 2220 3691 332 13 39992 331 112 122 6 92 > > 0 0 1354 2708 0 0 39836 335 103 125 9 99 > > 0 0 1563 3023 120 6 44036 369 399 317 13 188 > > > > Notice the KBWrit difference. These are two identical hp gen 8 machines, > > doing the same thing (replicating the same mysql schema). The one > > writing ten times as many bytes in the same amount of transactions is > > running centos 6 (and was running rhel 6). > > So what is the problem? it is writing too much on the on the centos > 6 machine? Either way, this doesn't sound like a filesystem problem > - the size and amount of data writes is entirely determined by the > application. For performing the same amount of work (processing the same mysql transactions, the same amount of IO transactions resulting from them), the 'broken' case writes ten-ish times as many bytes. > > /dev/mapper/sysvm-mysqlVol /mysql/bp xfs rw,relatime,attr2,delaylog,allocsize=1024k,logbsize=256k,sunit=512,swidth=1536,noquota 0 0 > > What is the reason for using allocsize, sunit/swidth? Are you using > them on other machines? xfs autodetects them from the hpsa driver. They seem to be correct for the raid layout (256 strips, 3 drives per mirror pool) and I don't seem to be able to override them. > And if you remove the allocsize mount option, does the behaviour on > centos6.3 change? What happens if you set allocsize=4k? The allocsize parameter has no effect. It was put in place to correct a monitoring issue: due to mysql's access patterns, using the default large allocsize on rhel 6 makes our monitoring report the filesystem as much fuller than it actually is. > > xfs_info: > > > > [root@bc291bprdb-01 ~]# xfs_info /mysql/bp/ > > meta-data=/dev/mapper/sysvm-mysqlVol isize=256 agcount=16, agsize=4915136 blks > > = sectsz=512 attr=2 > > data = bsize=4096 blocks=78642176, imaxpct=25 > > = sunit=64 swidth=192 blks > > naming =version 2 bsize=4096 ascii-ci=0 > > log =internal bsize=4096 blocks=38400, version=2 > > = sectsz=512 sunit=64 blks, lazy-count=1 > > realtime =none extsz=4096 blocks=0, rtextents=0 > > > > > > And for reference, xfs_info on centos 5: > > > > [root@bc290bprdb-01 ~]# xfs_info /mysql/bp/ > > meta-data=/dev/sysvm/mysqlVol isize=256 agcount=22, agsize=4915200 blks > > = sectsz=512 attr=0 > > data = bsize=4096 blocks=104857600, imaxpct=25 > > = sunit=0 swidth=0 blks, unwritten=1 > > naming =version 2 bsize=4096 > > log =internal bsize=4096 blocks=32768, version=1 > > = sectsz=512 sunit=0 blks, lazy-count=0 > > realtime =none extsz=4096 blocks=0, rtextents=0 > > The only difference is that the centos 6 filesystem is configured > with sunit/swidth. That affects allocation alignment, but nothing > else. It won't affect IO sizes. > > > Linux 2.6.18-308.el5 (bc290bprdb-01.lhr4.prod.booking.com) 03/06/2013 > > > > Device: rrqm/s wrqm/s r/s w/s rMB/s wMB/s avgrq-sz avgqu-sz await svctm %util > > cciss/c0d0 6.95 27.09 7.72 270.96 0.19 2.90 22.71 0.07 0.25 0.22 6.00 > > cciss/c0d0p1 0.00 0.00 0.00 0.00 0.00 0.00 47.62 0.00 1.69 1.61 0.00 > > cciss/c0d0p2 0.00 0.00 0.00 0.00 0.00 0.00 14.40 0.00 4.07 4.06 0.00 > > cciss/c0d0p3 6.94 27.09 7.72 270.96 0.19 2.90 22.71 0.07 0.25 0.22 6.00 > > dm-0 0.00 0.00 0.45 32.85 0.01 0.13 8.34 0.02 0.49 0.07 0.24 > > dm-1 0.00 0.00 6.97 264.13 0.15 2.77 22.10 0.07 0.24 0.22 5.93 > > So, 8k IOs on centos 5... > > > Linux 2.6.32-279.1.1.el6.x86_64 (bc291bprdb-01.lhr4.prod.booking.com) 03/06/2013 _x86_64_ (32 CPU) > > > > Device: rrqm/s wrqm/s r/s w/s rMB/s wMB/s avgrq-sz avgqu-sz await svctm %util > > sda 0.00 3.60 6.00 374.40 0.06 44.18 238.17 0.11 0.28 0.16 6.08 > > dm-0 0.00 0.00 0.00 4.40 0.00 0.02 8.00 0.00 0.27 0.18 0.08 > > dm-1 0.00 0.00 6.00 373.20 0.06 44.11 238.56 0.11 0.28 0.16 6.04 > > And 128k IOs on centos 6. Unless there's a massive difference in > file layouts, nothing in the filesystem would cause such a > dramatic change in IO size or thoughput. I see, so now I need to find out what's causing the larger average request size. Would you happen to know a list of common causes? -- Dennis Kaarsemaker, Systems Architect Booking.com Herengracht 597, 1017 CE Amsterdam Tel external +31 (0) 20 715 3409 Tel internal (7207) 3409 From jack@suse.cz Thu Mar 7 04:24:11 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id E22337FB1 for ; Thu, 7 Mar 2013 04:24:10 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay3.corp.sgi.com (Postfix) with ESMTP id 6D1A6AC003 for ; Thu, 7 Mar 2013 02:24:10 -0800 (PST) X-ASG-Debug-ID: 1362651848-04cb6c2b0223b550001-NocioJ Received: from mx2.suse.de (cantor2.suse.de [195.135.220.15]) by cuda.sgi.com with ESMTP id keRwvNkXs6vUxyVa for ; Thu, 07 Mar 2013 02:24:08 -0800 (PST) X-Barracuda-Envelope-From: jack@suse.cz X-Barracuda-Apparent-Source-IP: 195.135.220.15 Received: from relay2.suse.de (unknown [195.135.220.254]) by mx2.suse.de (Postfix) with ESMTP id 08E85A398F; Thu, 7 Mar 2013 11:24:07 +0100 (CET) Received: by quack.suse.cz (Postfix, from userid 1000) id 0103B2067D; Thu, 7 Mar 2013 11:24:06 +0100 (CET) Date: Thu, 7 Mar 2013 11:24:06 +0100 From: Jan Kara To: Dave Chinner Cc: Jan Kara , xfs@oss.sgi.com Subject: Re: Pathological allocation pattern with direct IO Message-ID: <20130307102406.GA6723@quack.suse.cz> X-ASG-Orig-Subj: Re: Pathological allocation pattern with direct IO References: <20130306202210.GA1318@quack.suse.cz> <20130307050325.GS23616@dastard> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <20130307050325.GS23616@dastard> User-Agent: Mutt/1.5.20 (2009-06-14) X-Barracuda-Connect: cantor2.suse.de[195.135.220.15] X-Barracuda-Start-Time: 1362651848 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124502 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Thu 07-03-13 16:03:25, Dave Chinner wrote: > On Wed, Mar 06, 2013 at 09:22:10PM +0100, Jan Kara wrote: > > Hello, > > > > one of our customers has application that write large (tens of GB) files > > using direct IO done in 16 MB chunks. They keep the fs around 80% full > > deleting oldest files when they need to store new ones. Usually the file > > can be stored in under 10 extents but from time to time a pathological case > > is triggered and the file has few thousands extents (which naturally has > > impact on performance). The customer actually uses 2.6.32-based kernel but > > I reproduced the issue with 3.8.2 kernel as well. > > > > I was analyzing why this happens and the filefrag for the file looks like: > > Filesystem type is: 58465342 > > File size of /raw_data/ex.20130302T121135/ov.s1a1.wb is 186294206464 > > (45481984 blocks, blocksize 4096) > > ext logical physical expected length flags > > 0 0 13 4550656 > > 1 4550656 188136807 4550668 12562432 > > 2 17113088 200699240 200699238 622592 > > 3 17735680 182046055 201321831 4096 > > 4 17739776 182041959 182050150 4096 > > 5 17743872 182037863 182046054 4096 > > 6 17747968 182033767 182041958 4096 > > 7 17752064 182029671 182037862 4096 > > ... > > 6757 45400064 154381644 154389835 4096 > > 6758 45404160 154377548 154385739 4096 > > 6759 45408256 252951571 154381643 73728 eof > > /raw_data/ex.20130302T121135/ov.s1a1.wb: 6760 extents found > > > > So we see that at one moment, the allocator starts giving us 16 MB chunks > > backwards. This seems to be caused by XFS_ALLOCTYPE_NEAR_BNO allocation. For > > two cases I was able to track down the logic: > > > > 1) We start allocating blocks for file. We want to allocate in the same AG > > as the inode is. First we try exact allocation which fails so we try > > XFS_ALLOCTYPE_NEAR_BNO allocation which finds large enough free extent > > before the inode. So we start allocating 16 MB chunks from the end of that > > free extent. From this moment on we are basically bound to continue > > allocating backwards using XFS_ALLOCTYPE_NEAR_BNO allocation until we > > exhaust the whole free extent. > > > > 2) Similar situation happens when we cannot further grow current extent but > > there is large free space somewhere before this extent in the AG. > > > > So I was wondering is this known? Is XFS_ALLOCTYPE_NEAR_BNO so beneficial > > it outweights pathological cases like the above? Or shouldn't it maybe be > > disabled for larger files or for direct IO? > > Well known issue, first diagnosed about 15 years ago, IIRC. Simple > solution: use extent size hints. I thought someone must have hit it before. But I wasn't successful in googling... I suggested using fallocate to the customer since they have a good idea of the final file size in advance and in testing it gave better results than extent size hints (plus it works for other filesystems as well). But really I was wondering about usefulness of XFS_ALLOCTYPE_NEAR_BNO heuristic. Sure the seek time depends on the distance so if we are speaking about allocating single extent then XFS_ALLOCTYPE_NEAR_BNO is useful but once that strategy would allocate two or three consecutive extents you've lost all the benefit and you would be better off if you started allocating from the start of the free space. Obviously we don't know the future in advance but this resembles a classical problem from approximations algorithms theory (rent-or-buy problem where renting corresponds to allocating from the end of free space and taking the smaller cost while buying corresponds to allocation from the beginning, taking the higher cost, but expecting you won't have to pay anything in future). And the theory of approximation algorithms tells us that once we pay for renting as much as buying will cost us, then at that moment it is advantageous to buy and that gives you 2-approximation algorithm (you can do even better - factor 1.58 approximation - if you use randomization but I don't think we want to go that way). So from this I'd say that switching off XFS_ALLOCTYPE_NEAR_BNO allocation once you've allocated 2-3 extents backwards would work of better on average. Honza -- Jan Kara SUSE Labs, CR From dsterba@suse.cz Thu Mar 7 05:06:10 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 258657FAF for ; Thu, 7 Mar 2013 05:06:10 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay3.corp.sgi.com (Postfix) with ESMTP id A9170AC004 for ; Thu, 7 Mar 2013 03:06:06 -0800 (PST) X-ASG-Debug-ID: 1362654361-04cb6c2b0423dc10001-NocioJ Received: from mx2.suse.de (cantor2.suse.de [195.135.220.15]) by cuda.sgi.com with ESMTP id V5YC0VKTIjxalmAj for ; Thu, 07 Mar 2013 03:06:02 -0800 (PST) X-Barracuda-Envelope-From: dsterba@suse.cz X-Barracuda-Apparent-Source-IP: 195.135.220.15 Received: from relay1.suse.de (unknown [195.135.220.254]) by mx2.suse.de (Postfix) with ESMTP id C0FA5A3E1C; Thu, 7 Mar 2013 12:06:01 +0100 (CET) Received: by ds.suse.cz (Postfix, from userid 10065) id 41D3EDA800; Thu, 7 Mar 2013 12:06:01 +0100 (CET) Date: Thu, 7 Mar 2013 12:06:01 +0100 From: David Sterba To: Dave Chinner Cc: dsterba@suse.cz, Wang Sheng-Hui , xfs@oss.sgi.com Subject: Re: [PATCH] xfstests 273: fix a typo Message-ID: <20130307110600.GJ21081@twin.jikos.cz> X-ASG-Orig-Subj: Re: [PATCH] xfstests 273: fix a typo Reply-To: dsterba@suse.cz Mail-Followup-To: dsterba@suse.cz, Dave Chinner , Wang Sheng-Hui , xfs@oss.sgi.com References: <512DAC1A.2040601@gmail.com> <20130306232222.GF21081@twin.jikos.cz> <20130307033849.GB6369@dastard> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <20130307033849.GB6369@dastard> User-Agent: Mutt/1.5.21 (2011-07-01) X-Barracuda-Connect: cantor2.suse.de[195.135.220.15] X-Barracuda-Start-Time: 1362654361 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124504 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Thu, Mar 07, 2013 at 02:38:49PM +1100, Dave Chinner wrote: > On Thu, Mar 07, 2013 at 12:22:22AM +0100, David Sterba wrote: > > On Wed, Feb 27, 2013 at 02:47:54PM +0800, Wang Sheng-Hui wrote: > > > - cp -r $SCRATCH_MNT/origin $SCRATCH_MNT/sub_$_suffix >$seq.full 2>&1 > > > + cp -r $SCRATCH_MNT/origin $SCRATCH_MNT/sub_$_suffix >>$seq.full 2>&1 This is quote from the mail, but the merged patch does something else. > > +./273: line 95: syntax error near unexpected token `&' > > +./273: line 95: ` cp -r $SCRATCH_MNT/origin $SCRATCH_MNT/sub_$_suffix >$seq.full 2>>&1' > > +umount: /dev/sda9: not mounted > that seems rather strange. The patch does this: > > ....sub_$_suffix >>$seq.full 2>&1 http://oss.sgi.com/cgi-bin/gitweb.cgi?p=xfs/cmds/xfstests.git;a=commitdiff;h=0c5e67e46e476b70290033efc7feb784f7ecbab1;hp=08557e219c12e573be459407033495899f46967a --- a/273 +++ b/273 @@ -92,7 +92,7 @@ _porter() exit fi - cp -r $SCRATCH_MNT/origin $SCRATCH_MNT/sub_$_suffix >$seq.full 2>&1 + cp -r $SCRATCH_MNT/origin $SCRATCH_MNT/sub_$_suffix >$seq.full 2>>&1 if [ $? -ne 0 ] then echo "_porter $_suffix not complete" --- > and the error output you see is > > ....sub_$_suffix >$seq.full 2>>&1 > > So it doesn't look lie you are running with the change that is > actually in the patch... There's a difference between the patch in mail and what has been merged, that can happen, but I wonder why it works on your side. Minimal reproducer that I used on machines with never bash: --- touch origin cp -r origin target >seq.full 2>>&1 --- bash --version: GNU bash, version 4.2.24(1)-release and fails the same way. > GNU bash, version 4.2.37(1)-release I've checked bash sources (no git, just tar + context diff patches), there's no apparent fix between 24-37 for that. (Also tried to build a git tree, but filterdiff did not produce 1:1 unified format of the separate patches and there are lots of conflicts). If possible, I'd like avoid forcing a minimal version of bash, as the enterprise distros do not always ship the latest ones, and this break the tests unnecessarily. david From dsterba@suse.cz Thu Mar 7 05:22:38 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 344BE7FAF for ; Thu, 7 Mar 2013 05:22:38 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id 19D65304059 for ; Thu, 7 Mar 2013 03:22:37 -0800 (PST) X-ASG-Debug-ID: 1362655356-04cbb07dbe248f10001-NocioJ Received: from mx2.suse.de (cantor2.suse.de [195.135.220.15]) by cuda.sgi.com with ESMTP id EZ3frZ6jSQVy2YJp for ; Thu, 07 Mar 2013 03:22:36 -0800 (PST) X-Barracuda-Envelope-From: dsterba@suse.cz X-Barracuda-Apparent-Source-IP: 195.135.220.15 Received: from relay1.suse.de (unknown [195.135.220.254]) by mx2.suse.de (Postfix) with ESMTP id 67A46A4F28; Thu, 7 Mar 2013 12:22:36 +0100 (CET) Received: by ds.suse.cz (Postfix, from userid 10065) id B06ADDA800; Thu, 7 Mar 2013 12:22:35 +0100 (CET) Date: Thu, 7 Mar 2013 12:22:35 +0100 From: David Sterba To: dsterba@suse.cz, Dave Chinner , Wang Sheng-Hui , xfs@oss.sgi.com Subject: Re: [PATCH] xfstests 273: fix a typo Message-ID: <20130307112235.GK21081@twin.jikos.cz> X-ASG-Orig-Subj: Re: [PATCH] xfstests 273: fix a typo Reply-To: dsterba@suse.cz Mail-Followup-To: dsterba@suse.cz, Dave Chinner , Wang Sheng-Hui , xfs@oss.sgi.com References: <512DAC1A.2040601@gmail.com> <20130306232222.GF21081@twin.jikos.cz> <20130307033849.GB6369@dastard> <20130307110600.GJ21081@twin.jikos.cz> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <20130307110600.GJ21081@twin.jikos.cz> User-Agent: Mutt/1.5.21 (2011-07-01) X-Barracuda-Connect: cantor2.suse.de[195.135.220.15] X-Barracuda-Start-Time: 1362655356 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.50 X-Barracuda-Spam-Status: No, SCORE=0.50 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_SA_TO_FROM_ADDR_MATCH X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124506 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.50 BSF_SC0_SA_TO_FROM_ADDR_MATCH Sender Address Matches Recipient Address On Thu, Mar 07, 2013 at 12:06:01PM +0100, David Sterba wrote: > (Also tried to build a git tree, but filterdiff did not produce 1:1 unified > format of the separate patches and there are lots of conflicts). I'm too git-centric and wanted to use 'git apply', but the 'patch' utility is able to apply context diffs just fine, so now tested with "GNU bash, version 4.2.42(2)-release" $ bash-4.2/bash 273 273: line 4: syntax error near unexpected token `&' 273: line 4: `cp -r origin target >seq.full 2>>&1' http://www.gnu.org/software/bash/manual/html_node/Redirections.html does not list the syntactic construct as valid. david From athena@fftw.org Thu Mar 7 06:13:42 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 98E257FB6 for ; Thu, 7 Mar 2013 06:13:42 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay3.corp.sgi.com (Postfix) with ESMTP id 27A83AC004 for ; Thu, 7 Mar 2013 04:13:39 -0800 (PST) X-ASG-Debug-ID: 1362658417-04cb6c2b04241fa0001-NocioJ Received: from fftw.org (216.119.142.145.static.a2webhosting.com [216.119.142.145]) by cuda.sgi.com with ESMTP id v4ig3bM99sEpOMnP (version=TLSv1 cipher=AES128-SHA bits=128 verify=NO) for ; Thu, 07 Mar 2013 04:13:37 -0800 (PST) X-Barracuda-Envelope-From: athena@fftw.org X-Barracuda-Apparent-Source-IP: 216.119.142.145 Received: from c-24-62-102-245.hsd1.ma.comcast.net ([24.62.102.245] helo=amd) by fftw.org with esmtpsa (TLS1.2:DHE_RSA_AES_128_CBC_SHA1:128) (Exim 4.80) (envelope-from ) id 1UDZhW-0007K4-6R; Thu, 07 Mar 2013 07:13:34 -0500 Received: from athena by amd with local (Exim 4.80) (envelope-from ) id 1UDZhQ-0007vz-2L; Thu, 07 Mar 2013 07:13:28 -0500 From: Matteo Frigo To: Dave Chinner Cc: dm-devel@redhat.com, xfs@oss.sgi.com Subject: Re: [dm-devel] [BUG] pvmove corrupting XFS filesystems (was Re: [BUG] Internal error xfs_dir2_data_reada_verify) References: <87d2vnc34r.fsf@fftw.org> <20130226044039.GM5551@dastard> <20130227010414.GD1514@agk.fab.redhat.com> <20130227014900.GY5551@dastard> <87y5eah4xz.fsf@fftw.org> X-ASG-Orig-Subj: Re: [dm-devel] [BUG] pvmove corrupting XFS filesystems (was Re: [BUG] Internal error xfs_dir2_data_reada_verify) Date: Thu, 07 Mar 2013 07:13:27 -0500 In-Reply-To: <87y5eah4xz.fsf@fftw.org> (Matteo Frigo's message of "Tue, 26 Feb 2013 21:21:44 -0500") Message-ID: <87k3pjs908.fsf@fftw.org> User-Agent: Gnus/5.13 (Gnus v5.13) Emacs/24.1 (gnu/linux) MIME-Version: 1.0 Content-Type: text/plain X-Barracuda-Connect: 216.119.142.145.static.a2webhosting.com[216.119.142.145] X-Barracuda-Start-Time: 1362658417 X-Barracuda-Encrypted: AES128-SHA X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124508 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- Matteo Frigo writes: > Well, I don't really know anything about this topic, so I may be > completely off the mark, but dm-raid1.c:mirror_map() does indeed return > EWOULDBLOCK, and EWOULDBLOCK is #define'd to be EAGAIN, so it seems to > me that dm-raid1 does indeed return EAGAIN for "rw == READA" (which I > assume is read-ahead) if the "region is not in-sync": > > /* > * If region is not in-sync queue the bio. > */ > if (!r || (r == -EWOULDBLOCK)) { > if (rw == READA) > return -EWOULDBLOCK; > > queue_bio(ms, bio, rw); > return DM_MAPIO_SUBMITTED; > } Dave (and others), do you have any suggestion on what should be done to fix this bug? I have tried returning -EIO instead of -EWOULDBLOCK, but xfs does not like that. dm-zero.c:zero_map() appears to return -EIO too, so this is another potential issue. I have verified that removing the READA special case, treating READA like READ, fixes the problem: if(0) if (rw == READA) return -EWOULDBLOCK; Of course this "fix" throws away the baby with the bath water. I am willing to write and submit a patch, but I would appreciate directions as to what the correct protocol between xfs and dm is supposed to be. Regards, MF From jferrero06@gmail.com Thu Mar 7 07:04:37 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.3 required=5.0 tests=FREEMAIL_ENVFROM_END_DIGIT, FREEMAIL_FROM,T_DKIM_INVALID autolearn=no version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id BF7F27FB8 for ; Thu, 7 Mar 2013 07:04:37 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay2.corp.sgi.com (Postfix) with ESMTP id 9D77C304059 for ; Thu, 7 Mar 2013 05:04:34 -0800 (PST) X-ASG-Debug-ID: 1362661472-04cb6c2b042455e0001-NocioJ Received: from mail-bk0-f44.google.com (mail-bk0-f44.google.com [209.85.214.44]) by cuda.sgi.com with ESMTP id zWDOkTZp57Lp37Iv (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Thu, 07 Mar 2013 05:04:33 -0800 (PST) X-Barracuda-Envelope-From: jferrero06@gmail.com X-Barracuda-Apparent-Source-IP: 209.85.214.44 X-Barracuda-IPDD: Level1 [gmail.com/209.85.214.44] Received: by mail-bk0-f44.google.com with SMTP id j4so206286bkw.3 for ; Thu, 07 Mar 2013 05:04:32 -0800 (PST) X-Barracuda-IPDD: Level1 [gmail.com/209.85.214.44] X-Barracuda-IPDD: Level1 [gmail.com/209.85.214.44] DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20120113; h=mime-version:x-received:in-reply-to:references:date:message-id :subject:from:to:cc:content-type; bh=0U5W7zIDPL6aPM6JyzMNMWZAHCgu+rQJAEzouN8Qjm4=; b=KtqntBsDbXksETq3AKfBa5iOLc3CF17K9FmEGWUPaC2CLyOjp1r5BMPVBhnAy2b3fV eCKsbY1yqyUvGegsTeLUaR8/P1AWrIJOPiy4DUuMTyO+xhRxLSZHb6mO+qKRpHH81zOC wo7FrqIyvfime8pchl6vS+Db8EaCL6yJgCOWKua1xweLfqXbo2ucrY/Tzc+IfFlXCjsT PrqsoJjSt/U8qJzFQbcmyftaoSpAIN69+SnM6KqrnH7+At121J0xlt/NDPVxW8CJ1QXQ OjKGPWhmrp6BroNzRqdAb4O7+1NREiZLMbF/P8QFXbz8xOcwVK7C97JTWnR/n/8IzkcF vs8Q== MIME-Version: 1.0 X-Received: by 10.204.147.81 with SMTP id k17mr13081471bkv.70.1362661472218; Thu, 07 Mar 2013 05:04:32 -0800 (PST) Received: by 10.204.228.133 with HTTP; Thu, 7 Mar 2013 05:04:32 -0800 (PST) In-Reply-To: <51380FD3.5010302@hardwarefreak.com> References: <51380FD3.5010302@hardwarefreak.com> Date: Thu, 7 Mar 2013 14:04:32 +0100 Message-ID: Subject: Re: XFS filesystem corruption From: Julien FERRERO X-ASG-Orig-Subj: Re: XFS filesystem corruption To: stan@hardwarefreak.com Cc: xfs@oss.sgi.com Content-Type: text/plain; charset=ISO-8859-1 X-Barracuda-Connect: mail-bk0-f44.google.com[209.85.214.44] X-Barracuda-Start-Time: 1362661473 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_MISMATCH_TO, DKIM_SIGNED, DKIM_VERIFIED X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124512 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 BSF_SC0_MISMATCH_TO Envelope rcpt doesn't match header -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature > It may be unrelated to your corruption, problem but I'm curious why you > are specifying a 32MB log section instead of letting mkfs.xfs make the > log size decision. I honestly don' know, the rebuild script was written 8 years ago by an engineer that since left the company. Is 32MB a short log space for a 1.5 TB of data ? > > I would assume based on your description that this is a mobile storage > system, often moved from one location to another, probably in a van, and > this is why the operator simply hits the power switch? Live news crew > type application or similar? > Correct. Moreover, the common usage is to power off all the equipment (included ours) from a general power switch. From stan@hardwarefreak.com Thu Mar 7 07:10:41 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 98BDE7FBA for ; Thu, 7 Mar 2013 07:10:41 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay3.corp.sgi.com (Postfix) with ESMTP id 44F5AAC001 for ; Thu, 7 Mar 2013 05:10:38 -0800 (PST) X-ASG-Debug-ID: 1362661837-04bdf02297260cd0001-NocioJ Received: from greer.hardwarefreak.com (mo-65-41-216-221.sta.embarqhsd.net [65.41.216.221]) by cuda.sgi.com with ESMTP id 9j56iuP4aM2huRap for ; Thu, 07 Mar 2013 05:10:37 -0800 (PST) X-Barracuda-Envelope-From: stan@hardwarefreak.com X-Barracuda-Apparent-Source-IP: 65.41.216.221 X-Barracuda-User-Whitelist: xfs@oss.sgi.com Received: from [192.168.100.53] (gffx.hardwarefreak.com [192.168.100.53]) by greer.hardwarefreak.com (Postfix) with ESMTP id F04436C0AC; Thu, 7 Mar 2013 07:10:36 -0600 (CST) Message-ID: <513891D7.4060801@hardwarefreak.com> Date: Thu, 07 Mar 2013 07:10:47 -0600 From: Stan Hoeppner Reply-To: stan@hardwarefreak.com User-Agent: Mozilla/5.0 (Windows NT 5.1; rv:17.0) Gecko/20130215 Thunderbird/17.0.3 MIME-Version: 1.0 To: Dennis Kaarsemaker CC: Dave Chinner , xfs@oss.sgi.com Subject: Re: XFS IO multiplication problem on centos/rhel 6 using hp p420i raid controllers References: <1362060736.1247.30.camel@seahawk> <20130228194023.GQ5551@dastard> <1362577992.1247.84.camel@seahawk> <20130307035737.GC6369@dastard> <1362651128.16657.13.camel@seahawk> X-ASG-Orig-Subj: Re: XFS IO multiplication problem on centos/rhel 6 using hp p420i raid controllers In-Reply-To: <1362651128.16657.13.camel@seahawk> Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: mo-65-41-216-221.sta.embarqhsd.net[65.41.216.221] X-Barracuda-Start-Time: 1362661837 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 On 3/7/2013 4:12 AM, Dennis Kaarsemaker wrote: > I see, so now I need to find out what's causing the larger average > request size. Would you happen to know a list of common causes? Given that mysql is doing the writes, that's the first place to look. Is the mysql version the same on all machines? If not, what changed between versions? How about the config? How about the sql code driving the IO, is it the same? Is this host using a different mysql log or db file format? Is the logging method the same? Is it writing the same total amount of data to the filesystem, but just in larger chunks? Etc, etc. -- Stan From jferrero06@gmail.com Thu Mar 7 07:15:34 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.3 required=5.0 tests=FREEMAIL_ENVFROM_END_DIGIT, FREEMAIL_FROM,T_DKIM_INVALID autolearn=no version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id EED6A7FBA for ; Thu, 7 Mar 2013 07:15:33 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id C774C30405F for ; Thu, 7 Mar 2013 05:15:33 -0800 (PST) X-ASG-Debug-ID: 1362662131-04cbb07dbe2503d0001-NocioJ Received: from mail-bk0-f54.google.com (mail-bk0-f54.google.com [209.85.214.54]) by cuda.sgi.com with ESMTP id ctrWvHOMsjDaGEU4 (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Thu, 07 Mar 2013 05:15:32 -0800 (PST) X-Barracuda-Envelope-From: jferrero06@gmail.com X-Barracuda-Apparent-Source-IP: 209.85.214.54 X-Barracuda-IPDD: Level1 [gmail.com/209.85.214.54] Received: by mail-bk0-f54.google.com with SMTP id w5so214206bku.13 for ; Thu, 07 Mar 2013 05:15:31 -0800 (PST) X-Barracuda-IPDD: Level1 [gmail.com/209.85.214.54] X-Barracuda-IPDD: Level1 [gmail.com/209.85.214.54] DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20120113; h=mime-version:x-received:in-reply-to:references:date:message-id :subject:from:to:cc:content-type; bh=mZzQgOJVJoZUbELv9aYvm7mC5Z+CvSbL/dj9vnaCjO8=; b=QzDG/vppeDpaLidbG2R8ud/MN8plP4+5sv65xHk+Eu4Nz/m0/W6GiT8ptkFOfQb0cV ZHzsarn/PSf54PFvMCi+okP5K3nwf7gALcx0t4MBRXp5a6Nyfn8AfWxhR0YFnJF97j5z UjFQPKpiw37kRGXaNgeyhhLnaEgpgBz/FHx0dsOX9GNDwm9oh1yQYw2CjF9NI6hypgDL 3OLRHBs3FNjfWn7iEA872Eyg8HIb3mgmiGeAAv+xd2X1xu1pMyf1bgBY5wi/6HVCUSZp +QkE94WLehaHH8M3F9hQVtHQOVTh/eHIE+s7XpolcbzUuGGVZTdMPCd9Peq7WNyzNv2Y bUZg== MIME-Version: 1.0 X-Received: by 10.204.136.197 with SMTP id s5mr13053139bkt.125.1362662131466; Thu, 07 Mar 2013 05:15:31 -0800 (PST) Received: by 10.204.228.133 with HTTP; Thu, 7 Mar 2013 05:15:31 -0800 (PST) In-Reply-To: <5137CD46.6070909@redhat.com> References: <20130306161519.2c28d911@galadriel.home> <20130306232100.6286f640@galadriel.home> <5137CD46.6070909@redhat.com> Date: Thu, 7 Mar 2013 14:15:31 +0100 Message-ID: Subject: Re: XFS filesystem corruption From: Julien FERRERO X-ASG-Orig-Subj: Re: XFS filesystem corruption To: Ric Wheeler Cc: Emmanuel Florac , xfs@oss.sgi.com Content-Type: text/plain; charset=ISO-8859-1 X-Barracuda-Connect: mail-bk0-f54.google.com[209.85.214.54] X-Barracuda-Start-Time: 1362662132 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=DKIM_SIGNED, DKIM_VERIFIED X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124512 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature > We actually test brutal "Power off" for xfs, ext4 and other file systems. If > your storage is configured properly and you have barriers enabled, they all > pass without corruption. > > What hardware raid cards can do is to hide a volatile write cache. Either on > the raid HBA itself or, even worse, on the backend disks behind the card. > S-ata disks tend to default to write cache enabled and need to be checked > especially careful (sas drives tend to be write cache disabled by default). Write cache is supposed to be disabled on the H/W RAID (according to hdparm) and barrier are correctly enabled since xfs does not report any warning at mount. The odd thing is we never see this with kernel 2.6.18 where barriers weren't yet available. An other difference is the "unwritten extend" that was used to set to 0 by default. Now we cannot change this setting according to an old thread I've found: "unwritten extents on linux are generally a bad idea, this option should not be used.". Unfortunately, the engineer that chose this setting is no longer working with us... From stan@hardwarefreak.com Thu Mar 7 07:32:05 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id EFD257FBE for ; Thu, 7 Mar 2013 07:32:05 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay2.corp.sgi.com (Postfix) with ESMTP id D5F3D304039 for ; Thu, 7 Mar 2013 05:32:05 -0800 (PST) X-ASG-Debug-ID: 1362663125-04cb6c2b03247880001-NocioJ Received: from greer.hardwarefreak.com (mo-65-41-216-221.sta.embarqhsd.net [65.41.216.221]) by cuda.sgi.com with ESMTP id CfqGOgHPTcdzn3KO for ; Thu, 07 Mar 2013 05:32:05 -0800 (PST) X-Barracuda-Envelope-From: stan@hardwarefreak.com X-Barracuda-Apparent-Source-IP: 65.41.216.221 X-Barracuda-User-Whitelist: xfs@oss.sgi.com Received: from [192.168.100.53] (gffx.hardwarefreak.com [192.168.100.53]) by greer.hardwarefreak.com (Postfix) with ESMTP id DC6606C0AC; Thu, 7 Mar 2013 07:32:04 -0600 (CST) Message-ID: <513896DF.7010609@hardwarefreak.com> Date: Thu, 07 Mar 2013 07:32:15 -0600 From: Stan Hoeppner Reply-To: stan@hardwarefreak.com User-Agent: Mozilla/5.0 (Windows NT 5.1; rv:17.0) Gecko/20130215 Thunderbird/17.0.3 MIME-Version: 1.0 To: Julien FERRERO CC: xfs@oss.sgi.com Subject: Re: XFS filesystem corruption References: <51380FD3.5010302@hardwarefreak.com> X-ASG-Orig-Subj: Re: XFS filesystem corruption In-Reply-To: Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: mo-65-41-216-221.sta.embarqhsd.net[65.41.216.221] X-Barracuda-Start-Time: 1362663125 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 On 3/7/2013 7:04 AM, Julien FERRERO wrote: >> It may be unrelated to your corruption, problem but I'm curious why you >> are specifying a 32MB log section instead of letting mkfs.xfs make the >> log size decision. > > I honestly don' know, the rebuild script was written 8 years ago by an > engineer that since left the company. > > Is 32MB a short log space for a 1.5 TB of data ? The log is for journal metadata. So if you're capturing a frame of video per file, or 24 or 60 frames per file, and thus are writing lots of files, 32MB may be too small. I'm not an expert here. Dave C. would be better able to answer this. But this is a very minor problem compared to... > Moreover, the common usage is to power off all the equipment (included > ours) from a general power switch. this. Have the crews been hard cutting power to these XFS boxen for the 8 years you mention above? And this filesystem corruption problem and/or corrupted files, is just now cropping up? That's hard to believe. There may be a bug in 2.6.35 that exacerbates this that's been fixed in later versions--2.6.35 is not a long term stable kernel--odd that a vendor would choose it for long term use. If you never had this problem before, I can only guess that previously you were using hardware RAID controllers with BBWC having sufficient battery hours of cache power to survive until the next power on, at which point the BBWC RAID dumped the data to the disks. If you switched from that solution to non BBWC RAID, or to Linux software RAID, that might explain why you're seeing corruption now and did not previously. And even with BBWC RAID, hard cutting power to the system is still not a smart thing to do. For this kind of environment, if field techs are going to hard cut power no matter what you tell them, then you simply MUST get LSI (or possibly other) RAID cards with the flash backed write cache. This doesn't rely on batteries so the cache is never volatile, and can sit overnight, or for days or weeks, without losing the data in the write cache. -- Stan From dennis.kaarsemaker@booking.com Thu Mar 7 07:32:46 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=T_DKIM_INVALID autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id AB2B47FBE for ; Thu, 7 Mar 2013 07:32:46 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay1.corp.sgi.com (Postfix) with ESMTP id 9271E8F8068 for ; Thu, 7 Mar 2013 05:32:46 -0800 (PST) X-ASG-Debug-ID: 1362663163-04cb6c2b01247930001-NocioJ Received: from mail-out1.booking.com (mail-out1.booking.com [62.190.24.20]) by cuda.sgi.com with ESMTP id fiCXwnRGcaFHUx8j (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO) for ; Thu, 07 Mar 2013 05:32:45 -0800 (PST) X-Barracuda-Envelope-From: dennis.kaarsemaker@booking.com X-Barracuda-Apparent-Source-IP: 62.190.24.20 DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=booking.com; s=bk; h=Mime-Version:Content-Transfer-Encoding:Content-Type:References:In-Reply-To:Date:Cc:To:From:Subject:Message-ID; bh=nTqLCk4hVI9OOsUvV3ZhT6qW/ZPyWW5FbEFi5tiXCH8=; b=GXFdxG9Xxp9oyDUW1zLuUG77ErkRHeuAlxO8jg2HRgwh30R/n1TrlyJsZewtbzxkMFZmWi85C+0fl+CpRHAsreAjmP8f/0Aa66OOoxjJtVyYUE1lgHPyIJ6VGf+AXVVrLGMGcXvxE7+hlH0/47D3+p8HhkKFI2f78y7Vog2z8ro=; Received: from corpds-204.lhr4.corp.booking.com ([10.186.69.9]:41085) by mtx-05.prod.lhr1.booking.com with esmtps (TLSv1:DHE-RSA-AES256-SHA:256) (Exim 4.80.1) (envelope-from ) id 1UDaw6-00077m-CQ; Thu, 07 Mar 2013 14:32:42 +0100 Received: from [10.155.73.64] (port=59970) by corpds-204.lhr4.corp.booking.com with esmtpsa (TLSv1:DHE-RSA-CAMELLIA256-SHA:256) (Exim 4.80.1) (envelope-from ) id 1UDaw6-0005zN-7L; Thu, 07 Mar 2013 14:32:42 +0100 Message-ID: <1362663188.16657.20.camel@seahawk> Subject: Re: XFS IO multiplication problem on centos/rhel 6 using hp p420i raid controllers From: Dennis Kaarsemaker X-ASG-Orig-Subj: Re: XFS IO multiplication problem on centos/rhel 6 using hp p420i raid controllers To: stan@hardwarefreak.com Cc: Dave Chinner , xfs@oss.sgi.com Date: Thu, 07 Mar 2013 14:33:08 +0100 In-Reply-To: <513891D7.4060801@hardwarefreak.com> References: <1362060736.1247.30.camel@seahawk> <20130228194023.GQ5551@dastard> <1362577992.1247.84.camel@seahawk> <20130307035737.GC6369@dastard> <1362651128.16657.13.camel@seahawk> <513891D7.4060801@hardwarefreak.com> Organization: Booking.com Content-Type: text/plain; charset="UTF-8" X-Mailer: Evolution 3.2.3-0ubuntu6 Content-Transfer-Encoding: 7bit Mime-Version: 1.0 X-Barracuda-Connect: mail-out1.booking.com[62.190.24.20] X-Barracuda-Start-Time: 1362663165 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_MISMATCH_TO, DKIM_SIGNED, DKIM_VERIFIED X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124513 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 BSF_SC0_MISMATCH_TO Envelope rcpt doesn't match header -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature On Thu, 2013-03-07 at 07:10 -0600, Stan Hoeppner wrote: > On 3/7/2013 4:12 AM, Dennis Kaarsemaker wrote: > > > I see, so now I need to find out what's causing the larger average > > request size. Would you happen to know a list of common causes? > > Given that mysql is doing the writes, that's the first place to look. That is indeed where we started, but MySQL is configured exactly the same on both thanks to puppet. > Is the mysql version the same on all machines? Yes. > How about the config? All that's different is server_id and prompt. > How about the sql code driving the IO, is it the same? They're replicating the same set of data. > Is this host using a different mysql log or db file format? Is the logging method the same? All the same > Is it writing the same > total amount of data to the filesystem, but just in larger chunks? Etc, The "ten times as many bytes" is constant, so it is constantly writing ten times as much data. -- Dennis Kaarsemaker, Systems Architect Booking.com Herengracht 597, 1017 CE Amsterdam Tel external +31 (0) 20 715 3409 Tel internal (7207) 3409 From rwheeler@redhat.com Thu Mar 7 07:40:44 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 4E0577F5D for ; Thu, 7 Mar 2013 07:40:44 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id 26EB830405F for ; Thu, 7 Mar 2013 05:40:43 -0800 (PST) X-ASG-Debug-ID: 1362663643-04cbb07dbc252700001-NocioJ Received: from mx1.redhat.com (mx1.redhat.com [209.132.183.28]) by cuda.sgi.com with ESMTP id Els2XKrerIClCMfm for ; Thu, 07 Mar 2013 05:40:43 -0800 (PST) X-Barracuda-Envelope-From: rwheeler@redhat.com X-Barracuda-Apparent-Source-IP: 209.132.183.28 X-ASG-Whitelist: Client Received: from int-mx10.intmail.prod.int.phx2.redhat.com (int-mx10.intmail.prod.int.phx2.redhat.com [10.5.11.23]) by mx1.redhat.com (8.14.4/8.14.4) with ESMTP id r27DedlY028011 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=OK); Thu, 7 Mar 2013 08:40:39 -0500 Received: from tunkums.home (ovpn-112-33.phx2.redhat.com [10.3.112.33]) by int-mx10.intmail.prod.int.phx2.redhat.com (8.14.4/8.14.4) with ESMTP id r27Debtb029828; Thu, 7 Mar 2013 08:40:38 -0500 Message-ID: <513898D4.6030502@redhat.com> Date: Thu, 07 Mar 2013 08:40:36 -0500 From: Ric Wheeler User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:17.0) Gecko/20130219 Thunderbird/17.0.3 MIME-Version: 1.0 To: Julien FERRERO CC: Emmanuel Florac , xfs@oss.sgi.com Subject: Re: XFS filesystem corruption References: <20130306161519.2c28d911@galadriel.home> <20130306232100.6286f640@galadriel.home> <5137CD46.6070909@redhat.com> X-ASG-Orig-Subj: Re: XFS filesystem corruption In-Reply-To: Content-Type: text/plain; charset=ISO-8859-1; format=flowed Content-Transfer-Encoding: 7bit X-Scanned-By: MIMEDefang 2.68 on 10.5.11.23 X-Barracuda-Connect: mx1.redhat.com[209.132.183.28] X-Barracuda-Start-Time: 1362663643 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 On 03/07/2013 08:15 AM, Julien FERRERO wrote: >> We actually test brutal "Power off" for xfs, ext4 and other file systems. If >> your storage is configured properly and you have barriers enabled, they all >> pass without corruption. >> >> What hardware raid cards can do is to hide a volatile write cache. Either on >> the raid HBA itself or, even worse, on the backend disks behind the card. >> S-ata disks tend to default to write cache enabled and need to be checked >> especially careful (sas drives tend to be write cache disabled by default). > Write cache is supposed to be disabled on the H/W RAID (according to > hdparm) and barrier are correctly enabled since xfs does not report > any warning at mount. hdparm shows you the devices that the card shows, not the state of the write cache on the drives behind them. You need special vendor tools to do.... The LSI controllers for example have megaraid tools. Until your IO stack is properly configured, you really don't need to worry about the file system options :) ric > > The odd thing is we never see this with kernel 2.6.18 where barriers > weren't yet available. An other difference is the "unwritten extend" > that was used to set to 0 by default. Now we cannot change this > setting according to an old thread I've found: "unwritten extents on > linux are generally a bad idea, this option should not be used.". > Unfortunately, the engineer that chose this setting is no longer > working with us... From stan@hardwarefreak.com Thu Mar 7 07:44:41 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id E124F7FB6 for ; Thu, 7 Mar 2013 07:44:41 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay1.corp.sgi.com (Postfix) with ESMTP id CA16B8F8066 for ; Thu, 7 Mar 2013 05:44:41 -0800 (PST) X-ASG-Debug-ID: 1362663881-04cb6c2b01248940001-NocioJ Received: from greer.hardwarefreak.com (mo-65-41-216-221.sta.embarqhsd.net [65.41.216.221]) by cuda.sgi.com with ESMTP id mHGlM9g0WKyAC1G0 for ; Thu, 07 Mar 2013 05:44:41 -0800 (PST) X-Barracuda-Envelope-From: stan@hardwarefreak.com X-Barracuda-Apparent-Source-IP: 65.41.216.221 X-Barracuda-User-Whitelist: xfs@oss.sgi.com Received: from [192.168.100.53] (gffx.hardwarefreak.com [192.168.100.53]) by greer.hardwarefreak.com (Postfix) with ESMTP id 1DC946C0AC; Thu, 7 Mar 2013 07:44:41 -0600 (CST) Message-ID: <513899D3.80907@hardwarefreak.com> Date: Thu, 07 Mar 2013 07:44:51 -0600 From: Stan Hoeppner Reply-To: stan@hardwarefreak.com User-Agent: Mozilla/5.0 (Windows NT 5.1; rv:17.0) Gecko/20130215 Thunderbird/17.0.3 MIME-Version: 1.0 To: Dennis Kaarsemaker CC: xfs@oss.sgi.com Subject: Re: XFS IO multiplication problem on centos/rhel 6 using hp p420i raid controllers References: <1362060736.1247.30.camel@seahawk> <20130228194023.GQ5551@dastard> <1362577992.1247.84.camel@seahawk> <20130307035737.GC6369@dastard> <1362651128.16657.13.camel@seahawk> <513891D7.4060801@hardwarefreak.com> <1362663188.16657.20.camel@seahawk> X-ASG-Orig-Subj: Re: XFS IO multiplication problem on centos/rhel 6 using hp p420i raid controllers In-Reply-To: <1362663188.16657.20.camel@seahawk> Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: mo-65-41-216-221.sta.embarqhsd.net[65.41.216.221] X-Barracuda-Start-Time: 1362663881 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 On 3/7/2013 7:33 AM, Dennis Kaarsemaker wrote: > The "ten times as many bytes" is constant, so it is constantly writing > ten times as much data. Where in the IO stack are you counting the bytes? Are 10x as many bytes actually hitting the AGs? I.e. are you consuming 10x more (real--not counting preallocation) space in the filesystem? Or are you simply seeing larger IOs in flight per unit time, but the same total amount of IO bytes? -- Stan From dennis.kaarsemaker@booking.com Thu Mar 7 07:52:34 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=T_DKIM_INVALID autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 502DC7FC6 for ; Thu, 7 Mar 2013 07:52:34 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id 3583F304048 for ; Thu, 7 Mar 2013 05:52:33 -0800 (PST) X-ASG-Debug-ID: 1362664351-04cbb07dbd253630001-NocioJ Received: from mail-out1.booking.com (mail-out1.booking.com [62.190.24.20]) by cuda.sgi.com with ESMTP id IUwhqqOlMtJqEnI3 (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO) for ; Thu, 07 Mar 2013 05:52:32 -0800 (PST) X-Barracuda-Envelope-From: dennis.kaarsemaker@booking.com X-Barracuda-Apparent-Source-IP: 62.190.24.20 DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=booking.com; s=bk; h=Mime-Version:Content-Transfer-Encoding:Content-Type:References:In-Reply-To:Date:Cc:To:From:Subject:Message-ID; bh=1PU8X6dO3390c3WdTD1cIim1JyEcflpEsA5dO0E51c0=; b=ot370Hc5XAzfePHVFZitqVKE8hO7+19vXkWxw2zj0x3UbWDx1FupPP1zHu4fVKUp9elLfiUqW61gy8p0eQt0mINRB3olqg/Co3ux7g3/MJb++cwLR54/M+fAJ/+hzYRVc8IFPoaY2i2sdcMrPM6fkVncx6SOCkmEu2J742Jaslw=; Received: from corpds-204.lhr4.corp.booking.com ([10.186.69.9]:34002) by mtx-05.prod.lhr1.booking.com with esmtps (TLSv1:DHE-RSA-AES256-SHA:256) (Exim 4.80.1) (envelope-from ) id 1UDbFG-00058h-Rg; Thu, 07 Mar 2013 14:52:30 +0100 Received: from [10.155.73.64] (port=60208) by corpds-204.lhr4.corp.booking.com with esmtpsa (TLSv1:DHE-RSA-CAMELLIA256-SHA:256) (Exim 4.80.1) (envelope-from ) id 1UDbFG-0003ez-Lw; Thu, 07 Mar 2013 14:52:30 +0100 Message-ID: <1362664376.16657.26.camel@seahawk> Subject: Re: XFS IO multiplication problem on centos/rhel 6 using hp p420i raid controllers From: Dennis Kaarsemaker X-ASG-Orig-Subj: Re: XFS IO multiplication problem on centos/rhel 6 using hp p420i raid controllers To: stan@hardwarefreak.com Cc: xfs@oss.sgi.com Date: Thu, 07 Mar 2013 14:52:56 +0100 In-Reply-To: <513899D3.80907@hardwarefreak.com> References: <1362060736.1247.30.camel@seahawk> <20130228194023.GQ5551@dastard> <1362577992.1247.84.camel@seahawk> <20130307035737.GC6369@dastard> <1362651128.16657.13.camel@seahawk> <513891D7.4060801@hardwarefreak.com> <1362663188.16657.20.camel@seahawk> <513899D3.80907@hardwarefreak.com> Organization: Booking.com Content-Type: text/plain; charset="UTF-8" X-Mailer: Evolution 3.2.3-0ubuntu6 Content-Transfer-Encoding: 7bit Mime-Version: 1.0 X-Barracuda-Connect: mail-out1.booking.com[62.190.24.20] X-Barracuda-Start-Time: 1362664352 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_MISMATCH_TO, DKIM_SIGNED, DKIM_VERIFIED X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124516 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 BSF_SC0_MISMATCH_TO Envelope rcpt doesn't match header -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature On Thu, 2013-03-07 at 07:44 -0600, Stan Hoeppner wrote: > On 3/7/2013 7:33 AM, Dennis Kaarsemaker wrote: > > > The "ten times as many bytes" is constant, so it is constantly writing > > ten times as much data. > > Where in the IO stack are you counting the bytes? Are 10x as many bytes > actually hitting the AGs? I.e. are you consuming 10x more (real--not > counting preallocation) space in the filesystem? Or are you simply > seeing larger IOs in flight per unit time, but the same total amount of > IO bytes? I'm counting them with vmstat, iostat and collectl as can be seen in the various outputs I've sent. I hope that answers your question as I have no idea how to see what's hitting the AG's. I am not using ten times as much space, as that wouldn't fit on the volume. -- Dennis Kaarsemaker, Systems Architect Booking.com Herengracht 597, 1017 CE Amsterdam Tel external +31 (0) 20 715 3409 Tel internal (7207) 3409 From tinguely@sgi.com Thu Mar 7 07:58:35 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 95B727FC6 for ; Thu, 7 Mar 2013 07:58:35 -0600 (CST) Received: from eagdhcp-232-136.americas.sgi.com (eagdhcp-232-136.americas.sgi.com [128.162.232.136]) by relay1.corp.sgi.com (Postfix) with ESMTP id 4570F8F8074; Thu, 7 Mar 2013 05:58:35 -0800 (PST) Message-ID: <51389D0B.4020000@sgi.com> Date: Thu, 07 Mar 2013 07:58:35 -0600 From: Mark Tinguely User-Agent: Mozilla/5.0 (X11; FreeBSD amd64; rv:9.0) Gecko/20120122 Thunderbird/9.0 MIME-Version: 1.0 To: Jan Kara CC: Dave Chinner , xfs@oss.sgi.com Subject: Re: Pathological allocation pattern with direct IO References: <20130306202210.GA1318@quack.suse.cz> <20130307050325.GS23616@dastard> <20130307102406.GA6723@quack.suse.cz> In-Reply-To: <20130307102406.GA6723@quack.suse.cz> Content-Type: text/plain; charset=ISO-8859-1; format=flowed Content-Transfer-Encoding: 7bit On 03/07/13 04:24, Jan Kara wrote: > On Thu 07-03-13 16:03:25, Dave Chinner wrote: >> On Wed, Mar 06, 2013 at 09:22:10PM +0100, Jan Kara wrote: >>> Hello, >>> >>> one of our customers has application that write large (tens of GB) files >>> using direct IO done in 16 MB chunks. They keep the fs around 80% full >>> deleting oldest files when they need to store new ones. Usually the file >>> can be stored in under 10 extents but from time to time a pathological case >>> is triggered and the file has few thousands extents (which naturally has >>> impact on performance). The customer actually uses 2.6.32-based kernel but >>> I reproduced the issue with 3.8.2 kernel as well. >>> >>> I was analyzing why this happens and the filefrag for the file looks like: >>> Filesystem type is: 58465342 >>> File size of /raw_data/ex.20130302T121135/ov.s1a1.wb is 186294206464 >>> (45481984 blocks, blocksize 4096) >>> ext logical physical expected length flags >>> 0 0 13 4550656 >>> 1 4550656 188136807 4550668 12562432 >>> 2 17113088 200699240 200699238 622592 >>> 3 17735680 182046055 201321831 4096 >>> 4 17739776 182041959 182050150 4096 >>> 5 17743872 182037863 182046054 4096 >>> 6 17747968 182033767 182041958 4096 >>> 7 17752064 182029671 182037862 4096 >>> ... >>> 6757 45400064 154381644 154389835 4096 >>> 6758 45404160 154377548 154385739 4096 >>> 6759 45408256 252951571 154381643 73728 eof >>> /raw_data/ex.20130302T121135/ov.s1a1.wb: 6760 extents found >>> >>> So we see that at one moment, the allocator starts giving us 16 MB chunks >>> backwards. This seems to be caused by XFS_ALLOCTYPE_NEAR_BNO allocation. For >>> two cases I was able to track down the logic: >>> >>> 1) We start allocating blocks for file. We want to allocate in the same AG >>> as the inode is. First we try exact allocation which fails so we try >>> XFS_ALLOCTYPE_NEAR_BNO allocation which finds large enough free extent >>> before the inode. So we start allocating 16 MB chunks from the end of that >>> free extent. From this moment on we are basically bound to continue >>> allocating backwards using XFS_ALLOCTYPE_NEAR_BNO allocation until we >>> exhaust the whole free extent. >>> >>> 2) Similar situation happens when we cannot further grow current extent but >>> there is large free space somewhere before this extent in the AG. >>> >>> So I was wondering is this known? Is XFS_ALLOCTYPE_NEAR_BNO so beneficial >>> it outweights pathological cases like the above? Or shouldn't it maybe be >>> disabled for larger files or for direct IO? >> >> Well known issue, first diagnosed about 15 years ago, IIRC. Simple >> solution: use extent size hints. > I thought someone must have hit it before. But I wasn't successful in > googling... I suggested using fallocate to the customer since they have a > good idea of the final file size in advance and in testing it gave better > results than extent size hints (plus it works for other filesystems as > well). > > But really I was wondering about usefulness of XFS_ALLOCTYPE_NEAR_BNO > heuristic. Sure the seek time depends on the distance so if we are speaking > about allocating single extent then XFS_ALLOCTYPE_NEAR_BNO is useful but > once that strategy would allocate two or three consecutive extents you've > lost all the benefit and you would be better off if you started allocating > from the start of the free space. Obviously we don't know the future in > advance but this resembles a classical problem from approximations > algorithms theory (rent-or-buy problem where renting corresponds to > allocating from the end of free space and taking the smaller cost while > buying corresponds to allocation from the beginning, taking the higher > cost, but expecting you won't have to pay anything in future). And the > theory of approximation algorithms tells us that once we pay for renting as > much as buying will cost us, then at that moment it is advantageous to buy > and that gives you 2-approximation algorithm (you can do even better - > factor 1.58 approximation - if you use randomization but I don't think we > want to go that way). So from this I'd say that switching off > XFS_ALLOCTYPE_NEAR_BNO allocation once you've allocated 2-3 extents > backwards would work of better on average. > > Honza Sounds like a candidate for a dynamic allocation policy, http://oss.sgi.com/archives/xfs/2013-01/msg00611.html --Mark. From rjohnston@sgi.com Thu Mar 7 07:59:49 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id AE4BD7FCC for ; Thu, 7 Mar 2013 07:59:49 -0600 (CST) Received: from gulag1.americas.sgi.com (gulag1.americas.sgi.com [128.162.236.41]) by relay1.corp.sgi.com (Postfix) with ESMTP id 7EF1F8F8074; Thu, 7 Mar 2013 05:59:49 -0800 (PST) Received: by gulag1.americas.sgi.com (Postfix, from userid 48222) id 628CE8580BCF; Thu, 7 Mar 2013 07:59:49 -0600 (CST) Message-Id: <20130307124125.435047948@sgi.com> User-Agent: quilt/0.47-15.17.1 Date: Thu, 07 Mar 2013 06:41:03 -0600 From: rjohnston@sgi.com To: xfs@oss.sgi.com Cc: shhuiw@gmail.com Subject: [PATCH] Fix typo from commit 0c5e67e4 "xfstests 273: fix a typo" References: <20130307124102.821208303@sgi.com> Content-Disposition: inline; filename=fix-typo-273.patch When updating the patch, the redirect was incorrect. Reported-by: Wang Sheng-Hui Signed-off-by: Rich Johnston --- 273 | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) Index: b/273 =================================================================== --- a/273 +++ b/273 @@ -92,7 +92,7 @@ _porter() exit fi - cp -r $SCRATCH_MNT/origin $SCRATCH_MNT/sub_$_suffix >$seq.full 2>>&1 + cp -r $SCRATCH_MNT/origin $SCRATCH_MNT/sub_$_suffix >>$seq.full 2>&1 if [ $? -ne 0 ] then echo "_porter $_suffix not complete" From tinguely@sgi.com Thu Mar 7 08:56:37 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 2900F7FC8 for ; Thu, 7 Mar 2013 08:56:37 -0600 (CST) Received: from eagdhcp-232-136.americas.sgi.com (eagdhcp-232-136.americas.sgi.com [128.162.232.136]) by relay2.corp.sgi.com (Postfix) with ESMTP id E5B3F304039; Thu, 7 Mar 2013 06:56:33 -0800 (PST) Message-ID: <5138AAA2.70308@sgi.com> Date: Thu, 07 Mar 2013 08:56:34 -0600 From: Mark Tinguely User-Agent: Mozilla/5.0 (X11; FreeBSD amd64; rv:9.0) Gecko/20120122 Thunderbird/9.0 MIME-Version: 1.0 To: rjohnston@sgi.com CC: xfs@oss.sgi.com, shhuiw@gmail.com Subject: Re: [PATCH] Fix typo from commit 0c5e67e4 "xfstests 273: fix a typo" References: <20130307124102.821208303@sgi.com> <20130307124125.435047948@sgi.com> In-Reply-To: <20130307124125.435047948@sgi.com> Content-Type: text/plain; charset=ISO-8859-1; format=flowed Content-Transfer-Encoding: 7bit On 03/07/13 06:41, rjohnston@sgi.com wrote: > When updating the patch, the redirect was incorrect. > > Reported-by: Wang Sheng-Hui > Signed-off-by: Rich Johnston > > --- > > 273 | 2 +- > 1 file changed, 1 insertion(+), 1 deletion(-) > > Index: b/273 > =================================================================== > --- a/273 > +++ b/273 > @@ -92,7 +92,7 @@ _porter() > exit > fi > > - cp -r $SCRATCH_MNT/origin $SCRATCH_MNT/sub_$_suffix>$seq.full 2>>&1 > + cp -r $SCRATCH_MNT/origin $SCRATCH_MNT/sub_$_suffix>>$seq.full 2>&1 > if [ $? -ne 0 ] > then > echo "_porter $_suffix not complete" > The original patch looked okay: http://oss.sgi.com/archives/xfs/2013-02/msg00518.html Should the bad patch be reverted and the original one put in? --Mark. From rjohnston@sgi.com Thu Mar 7 09:48:55 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id C909A7FC8 for ; Thu, 7 Mar 2013 09:48:55 -0600 (CST) Received: from xmail.sgi.com (pv-excas2-dc21.corp.sgi.com [137.38.102.196]) by relay2.corp.sgi.com (Postfix) with ESMTP id 9A081304059; Thu, 7 Mar 2013 07:48:52 -0800 (PST) Received: from [134.15.0.114] (134.15.0.114) by xmail.sgi.com (137.38.102.30) with Microsoft SMTP Server (TLS) id 14.2.318.1; Thu, 7 Mar 2013 09:48:52 -0600 Message-ID: <5138B6E3.5010903@sgi.com> Date: Thu, 7 Mar 2013 09:48:51 -0600 From: Rich Johnston User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:14.0) Gecko/20120714 Thunderbird/14.0 MIME-Version: 1.0 To: Mark Tinguely CC: , , , Dave Chinner Subject: Re: [PATCH] Fix typo from commit 0c5e67e4 "xfstests 273: fix a typo" References: <20130307124102.821208303@sgi.com> <20130307124125.435047948@sgi.com> <5138AAA2.70308@sgi.com> In-Reply-To: <5138AAA2.70308@sgi.com> Content-Type: text/plain; charset="ISO-8859-1"; format=flowed Content-Transfer-Encoding: 7bit X-Originating-IP: [134.15.0.114] On 03/07/2013 08:56 AM, Mark Tinguely wrote: > On 03/07/13 06:41, rjohnston@sgi.com wrote: >> When updating the patch, the redirect was incorrect. >> >> Reported-by: Wang Sheng-Hui >> Signed-off-by: Rich Johnston >> >> --- >> >> 273 | 2 +- >> 1 file changed, 1 insertion(+), 1 deletion(-) >> >> Index: b/273 >> =================================================================== >> --- a/273 >> +++ b/273 >> @@ -92,7 +92,7 @@ _porter() >> exit >> fi >> >> - cp -r $SCRATCH_MNT/origin $SCRATCH_MNT/sub_$_suffix>$seq.full 2>>&1 >> + cp -r $SCRATCH_MNT/origin $SCRATCH_MNT/sub_$_suffix>>$seq.full 2>&1 >> if [ $? -ne 0 ] >> then >> echo "_porter $_suffix not complete" >> > > > The original patch looked okay: > > http://oss.sgi.com/archives/xfs/2013-02/msg00518.html > > Should the bad patch be reverted and the original one put in? > > --Mark. Yes the patch would not apply to top of tree and I placed the redirect in the incorrect position when I updated the and committed the patch. I have reverted and applied the patch correctly this time. :) commit a1f6dd481218cd95c8d48ed684070cc2b0f62db2 Author: Wang Sheng-Hui Date: Wed Feb 27 06:47:54 2013 +0000 xfstests 273: fix a typo Make the porter log cp failure into $seq.full by appending, not overwriting, which can help debug. Signed-off-by: Wang Sheng-Hui Reviewed-by: Dave Chinner Signed-off-by: Rich Johnston diff --git a/273 b/273 index 67f3d6b..639e280 100755 --- a/273 +++ b/273 @@ -92,7 +92,7 @@ _porter() exit fi - cp -r $SCRATCH_MNT/origin $SCRATCH_MNT/sub_$_suffix >$seq.full 2>&1 + cp -r $SCRATCH_MNT/origin $SCRATCH_MNT/sub_$_suffix >>$seq.full 2>&1 if [ $? -ne 0 ] then echo "_porter $_suffix not complete" commit 2a599a54aba600c299b8209d802f97c51a164dcb Author: Rich Johnston Date: Thu Mar 7 09:21:30 2013 -0600 Revert "xfstests 273: fix a typo" This reverts commit 0c5e67e46e476b70290033efc7feb784f7ecbab1. Will re-apply the correct patch. From dsterba@suse.cz Thu Mar 7 12:25:31 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id A90657FC4 for ; Thu, 7 Mar 2013 12:25:31 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay2.corp.sgi.com (Postfix) with ESMTP id 8830E304071 for ; Thu, 7 Mar 2013 10:25:28 -0800 (PST) X-ASG-Debug-ID: 1362680727-04bdf0229827fb20001-NocioJ Received: from mx2.suse.de (cantor2.suse.de [195.135.220.15]) by cuda.sgi.com with ESMTP id gTZCAA5aZQbnDTnz for ; Thu, 07 Mar 2013 10:25:27 -0800 (PST) X-Barracuda-Envelope-From: dsterba@suse.cz X-Barracuda-Apparent-Source-IP: 195.135.220.15 Received: from relay2.suse.de (unknown [195.135.220.254]) by mx2.suse.de (Postfix) with ESMTP id A2F2FA3A78; Thu, 7 Mar 2013 19:25:26 +0100 (CET) Received: by ds.suse.cz (Postfix, from userid 10065) id DD655DA801; Thu, 7 Mar 2013 19:25:25 +0100 (CET) Date: Thu, 7 Mar 2013 19:25:25 +0100 From: David Sterba To: Rich Johnston Cc: xfs@oss.sgi.com Subject: Re: [PATCH] xfstests: enhance ltp/fsx with a timeout option Message-ID: <20130307182525.GA29541@suse.cz> X-ASG-Orig-Subj: Re: [PATCH] xfstests: enhance ltp/fsx with a timeout option Reply-To: dsterba@suse.cz Mail-Followup-To: dsterba@suse.cz, Rich Johnston , xfs@oss.sgi.com References: <1358944851-14336-1-git-send-email-dsterba@suse.cz> <51378B7F.9090103@sgi.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <51378B7F.9090103@sgi.com> User-Agent: Mutt/1.5.21 (2011-07-01) X-Barracuda-Connect: cantor2.suse.de[195.135.220.15] X-Barracuda-Start-Time: 1362680727 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124534 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- Hi, On Wed, Mar 06, 2013 at 12:31:27PM -0600, Rich Johnston wrote: > I used test 263 to verify that fsx works as expected with the new -T and the > existing -N options. With the -T option of course, test 263 will fail. I > don't suggest that we change existing tests but add new tests which use the > new -T option. Do you have a new test which you intend to use the -T option > that can be submitted with this patch? I understand that changing behaviour of existing checks is not desirable. The -T option to fsx was inspired by the test we used to hunt a bug at 3.8-rc time where 50 concurrent direct io fsx jobs triggered the bug in about 10 minutes or it was considered fine. fsx -q xxxf$x -Z -R -W -r 4096 -w 4096 (http://permalink.gmane.org/gmane.comp.file-systems.btrfs/22447) I'll send this test integrated into xfstests harness. david From bpm@oss.sgi.com Thu Mar 7 12:42:07 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=-0.0 required=5.0 tests=NO_RELAYS autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: by oss.sgi.com (Postfix, from userid 46323) id 5E5537FC6; Thu, 7 Mar 2013 12:42:07 -0600 (CST) From: xfs@oss.sgi.com To: xfs@oss.sgi.com Subject: [XFS updates] XFS development tree branch, master, updated. v3.9-rc1-6-g9e5987a X-Git-Refname: refs/heads/master X-Git-Reftype: branch X-Git-Oldrev: 6dbe51c251a327e012439c4772097a13df43c5b8 X-Git-Newrev: 9e5987a7792194ec338f53643237150c0db5f5e0 Message-Id: <20130307184207.5E5537FC6@oss.sgi.com> Date: Thu, 7 Mar 2013 12:42:07 -0600 (CST) This is an automated email from the git hooks/post-receive script. It was generated because a ref change was pushed to the repository containing the project "XFS development tree". The branch, master has been updated 9e5987a xfs: rearrange some code in xfs_bmap for better locality ecb3403 xfs: rename random32() to prandom_u32() d5929de xfs: don't verify buffers after IO errors e8108ce xfs: fix xfs_iomap_eof_prealloc_initial_size type e114b5f xfs: increase prealloc size to double that of the previous extent e78c420 xfs: fix potential infinite loop in xfs_iomap_prealloc_size() from 6dbe51c251a327e012439c4772097a13df43c5b8 (commit) Those revisions listed above that are new to this repository have not appeared on any other notification email; so we list those revisions in full, below. - Log ----------------------------------------------------------------- commit 9e5987a7792194ec338f53643237150c0db5f5e0 Author: Dave Chinner Date: Mon Feb 25 12:31:26 2013 +1100 xfs: rearrange some code in xfs_bmap for better locality xfs_bmap.c is a big file, and some of the related code is spread all throughout the file requiring function prototypes for static function and jumping all through the file to follow a single call path. Rearrange the code so that: a) related functionality is grouped together; and b) functions are grouped in call dependency order While the diffstat is large, there are no code changes in the patch; it is just moving the functionality around and removing the function prototypes at the top of the file. The resulting layout of the code is as follows (top of file to bottom): - miscellaneous helper functions - extent tree block counting routines - debug/sanity checking code - bmap free list manipulation functions - inode fork format manipulation functions - internal/external extent tree seach functions - extent tree manipulation functions used during allocation - functions used during extent read/allocate/removal operations (i.e. xfs_bmapi_write, xfs_bmapi_read, xfs_bunmapi and xfs_getbmap) This means that following logic paths through the bmapi code is much simpler - most of the code relevant to a specific operation is now clustered together rather than spread all over the file.... Signed-off-by: Dave Chinner Reviewed-by: Mark Tinguely Signed-off-by: Ben Myers commit ecb3403de1efb56f78d9093376aec0a8af76b316 Author: Akinobu Mita Date: Mon Mar 4 21:58:20 2013 +0900 xfs: rename random32() to prandom_u32() Use more preferable function name which implies using a pseudo-random number generator. Signed-off-by: Akinobu Mita Acked-by: Cc: Ben Myers Cc: Alex Elder Cc: xfs@oss.sgi.com Signed-off-by: Ben Myers commit d5929de8337fef46f3e307914ed0f3cb845e66c1 Author: Dave Chinner Date: Wed Feb 27 13:25:54 2013 +1100 xfs: don't verify buffers after IO errors When we read a buffer, we might get an error from the underlying block device and not the real data. Hence if we get an IO error, we shouldn't run the verifier but instead just pass the IO error straight through. Signed-off-by: Dave Chinner Reviewed-by: Mark Tinguely Signed-off-by: Ben Myers commit e8108cedb1c5d1dc359690d18ca997e97a0061d2 Author: Mark Tinguely Date: Sun Feb 24 13:04:37 2013 -0600 xfs: fix xfs_iomap_eof_prealloc_initial_size type Fix the return type of xfs_iomap_eof_prealloc_initial_size() to xfs_fsblock_t to reflect the fact that the return value may be an unsigned 64 bits if XFS_BIG_BLKNOS is defined. Signed-off-by: Mark Tinguely Reviewed-by: Dave Chinner Signed-off-by: Ben Myers commit e114b5fce6befb8fa345d7cf1a4de8ce5a211910 Author: Brian Foster Date: Tue Feb 19 10:24:41 2013 -0500 xfs: increase prealloc size to double that of the previous extent The updated speculative preallocation algorithm for handling sparse files can becomes less effective in situations with a high number of concurrent, sequential writers. The number of writers and amount of available RAM affect the writeback bandwidth slicing algorithm, which in turn affects the block allocation pattern of XFS. For example, running 32 sequential writers on a system with 32GB RAM, preallocs become fixed at a value of around 128MB (instead of steadily increasing to the 8GB maximum as sequential writes proceed). Update the speculative prealloc heuristic to base the size of the next prealloc on double the size of the preceding extent. This preserves the original aggressive speculative preallocation behavior and continues to accomodate sparse files at a slight cost of increasing the size of preallocated data regions following holes of sparse files. Signed-off-by: Brian Foster Reviewed-by: Dave Chinner Signed-off-by: Ben Myers commit e78c420bfc2608bb5f9a0b9165b1071c1e31166a Author: Brian Foster Date: Fri Feb 22 13:32:56 2013 -0500 xfs: fix potential infinite loop in xfs_iomap_prealloc_size() If freesp == 0, we could end up in an infinite loop while squashing the preallocation. Break the loop when we've killed the prealloc entirely. Signed-off-by: Brian Foster Reviewed-by: Dave Chinner Signed-off-by: Ben Myers ----------------------------------------------------------------------- Summary of changes: fs/xfs/xfs_alloc.c | 2 +- fs/xfs/xfs_bmap.c | 10659 +++++++++++++++++++++++++------------------------- fs/xfs/xfs_buf.c | 4 +- fs/xfs/xfs_error.c | 2 +- fs/xfs/xfs_ialloc.c | 2 +- fs/xfs/xfs_iomap.c | 6 +- fs/xfs/xfs_log.c | 2 +- 7 files changed, 5271 insertions(+), 5406 deletions(-) hooks/post-receive -- XFS development tree From bpm@oss.sgi.com Thu Mar 7 12:42:20 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=-0.0 required=5.0 tests=NO_RELAYS autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: by oss.sgi.com (Postfix, from userid 46323) id A32687FD1; Thu, 7 Mar 2013 12:42:20 -0600 (CST) From: xfs@oss.sgi.com To: xfs@oss.sgi.com Subject: [XFS updates] XFS development tree branch, for-next, updated. v3.9-rc1-6-g9e5987a X-Git-Refname: refs/heads/for-next X-Git-Reftype: branch X-Git-Oldrev: 6dbe51c251a327e012439c4772097a13df43c5b8 X-Git-Newrev: 9e5987a7792194ec338f53643237150c0db5f5e0 Message-Id: <20130307184220.A32687FD1@oss.sgi.com> Date: Thu, 7 Mar 2013 12:42:20 -0600 (CST) This is an automated email from the git hooks/post-receive script. It was generated because a ref change was pushed to the repository containing the project "XFS development tree". The branch, for-next has been updated 9e5987a xfs: rearrange some code in xfs_bmap for better locality ecb3403 xfs: rename random32() to prandom_u32() d5929de xfs: don't verify buffers after IO errors e8108ce xfs: fix xfs_iomap_eof_prealloc_initial_size type e114b5f xfs: increase prealloc size to double that of the previous extent e78c420 xfs: fix potential infinite loop in xfs_iomap_prealloc_size() from 6dbe51c251a327e012439c4772097a13df43c5b8 (commit) Those revisions listed above that are new to this repository have not appeared on any other notification email; so we list those revisions in full, below. - Log ----------------------------------------------------------------- commit 9e5987a7792194ec338f53643237150c0db5f5e0 Author: Dave Chinner Date: Mon Feb 25 12:31:26 2013 +1100 xfs: rearrange some code in xfs_bmap for better locality xfs_bmap.c is a big file, and some of the related code is spread all throughout the file requiring function prototypes for static function and jumping all through the file to follow a single call path. Rearrange the code so that: a) related functionality is grouped together; and b) functions are grouped in call dependency order While the diffstat is large, there are no code changes in the patch; it is just moving the functionality around and removing the function prototypes at the top of the file. The resulting layout of the code is as follows (top of file to bottom): - miscellaneous helper functions - extent tree block counting routines - debug/sanity checking code - bmap free list manipulation functions - inode fork format manipulation functions - internal/external extent tree seach functions - extent tree manipulation functions used during allocation - functions used during extent read/allocate/removal operations (i.e. xfs_bmapi_write, xfs_bmapi_read, xfs_bunmapi and xfs_getbmap) This means that following logic paths through the bmapi code is much simpler - most of the code relevant to a specific operation is now clustered together rather than spread all over the file.... Signed-off-by: Dave Chinner Reviewed-by: Mark Tinguely Signed-off-by: Ben Myers commit ecb3403de1efb56f78d9093376aec0a8af76b316 Author: Akinobu Mita Date: Mon Mar 4 21:58:20 2013 +0900 xfs: rename random32() to prandom_u32() Use more preferable function name which implies using a pseudo-random number generator. Signed-off-by: Akinobu Mita Acked-by: Cc: Ben Myers Cc: Alex Elder Cc: xfs@oss.sgi.com Signed-off-by: Ben Myers commit d5929de8337fef46f3e307914ed0f3cb845e66c1 Author: Dave Chinner Date: Wed Feb 27 13:25:54 2013 +1100 xfs: don't verify buffers after IO errors When we read a buffer, we might get an error from the underlying block device and not the real data. Hence if we get an IO error, we shouldn't run the verifier but instead just pass the IO error straight through. Signed-off-by: Dave Chinner Reviewed-by: Mark Tinguely Signed-off-by: Ben Myers commit e8108cedb1c5d1dc359690d18ca997e97a0061d2 Author: Mark Tinguely Date: Sun Feb 24 13:04:37 2013 -0600 xfs: fix xfs_iomap_eof_prealloc_initial_size type Fix the return type of xfs_iomap_eof_prealloc_initial_size() to xfs_fsblock_t to reflect the fact that the return value may be an unsigned 64 bits if XFS_BIG_BLKNOS is defined. Signed-off-by: Mark Tinguely Reviewed-by: Dave Chinner Signed-off-by: Ben Myers commit e114b5fce6befb8fa345d7cf1a4de8ce5a211910 Author: Brian Foster Date: Tue Feb 19 10:24:41 2013 -0500 xfs: increase prealloc size to double that of the previous extent The updated speculative preallocation algorithm for handling sparse files can becomes less effective in situations with a high number of concurrent, sequential writers. The number of writers and amount of available RAM affect the writeback bandwidth slicing algorithm, which in turn affects the block allocation pattern of XFS. For example, running 32 sequential writers on a system with 32GB RAM, preallocs become fixed at a value of around 128MB (instead of steadily increasing to the 8GB maximum as sequential writes proceed). Update the speculative prealloc heuristic to base the size of the next prealloc on double the size of the preceding extent. This preserves the original aggressive speculative preallocation behavior and continues to accomodate sparse files at a slight cost of increasing the size of preallocated data regions following holes of sparse files. Signed-off-by: Brian Foster Reviewed-by: Dave Chinner Signed-off-by: Ben Myers commit e78c420bfc2608bb5f9a0b9165b1071c1e31166a Author: Brian Foster Date: Fri Feb 22 13:32:56 2013 -0500 xfs: fix potential infinite loop in xfs_iomap_prealloc_size() If freesp == 0, we could end up in an infinite loop while squashing the preallocation. Break the loop when we've killed the prealloc entirely. Signed-off-by: Brian Foster Reviewed-by: Dave Chinner Signed-off-by: Ben Myers ----------------------------------------------------------------------- Summary of changes: fs/xfs/xfs_alloc.c | 2 +- fs/xfs/xfs_bmap.c | 10659 +++++++++++++++++++++++++------------------------- fs/xfs/xfs_buf.c | 4 +- fs/xfs/xfs_error.c | 2 +- fs/xfs/xfs_ialloc.c | 2 +- fs/xfs/xfs_iomap.c | 6 +- fs/xfs/xfs_log.c | 2 +- 7 files changed, 5271 insertions(+), 5406 deletions(-) hooks/post-receive -- XFS development tree From bpm@sgi.com Thu Mar 7 12:43:09 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 1E1C07FA1 for ; Thu, 7 Mar 2013 12:43:09 -0600 (CST) Received: from whiskey.americas.sgi.com (eagdhcp-232-197.americas.sgi.com [128.162.232.197]) by relay3.corp.sgi.com (Postfix) with ESMTP id 7CEEFAC004; Thu, 7 Mar 2013 10:43:08 -0800 (PST) Received: by whiskey.americas.sgi.com (Postfix, from userid 4600) id 2EE8D500B4A; Thu, 7 Mar 2013 12:43:08 -0600 (CST) Date: Thu, 7 Mar 2013 12:43:08 -0600 From: Ben Myers To: Brian Foster Cc: xfs@oss.sgi.com Subject: Re: [PATCH] xfs: fix potential infinite loop in xfs_iomap_prealloc_size() Message-ID: <20130307184308.GN22182@sgi.com> References: <1361557976-54981-1-git-send-email-bfoster@redhat.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <1361557976-54981-1-git-send-email-bfoster@redhat.com> User-Agent: Mutt/1.5.20 (2009-06-14) On Fri, Feb 22, 2013 at 01:32:56PM -0500, Brian Foster wrote: > If freesp == 0, we could end up in an infinite loop while squashing > the preallocation. Break the loop when we've killed the prealloc > entirely. > > Signed-off-by: Brian Foster Applied. -Ben From bpm@sgi.com Thu Mar 7 12:43:54 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id B4DB07FA1 for ; Thu, 7 Mar 2013 12:43:54 -0600 (CST) Received: from whiskey.americas.sgi.com (eagdhcp-232-197.americas.sgi.com [128.162.232.197]) by relay1.corp.sgi.com (Postfix) with ESMTP id 8FDC98F8049; Thu, 7 Mar 2013 10:43:54 -0800 (PST) Received: by whiskey.americas.sgi.com (Postfix, from userid 4600) id 6CC6A500B4B; Thu, 7 Mar 2013 12:43:54 -0600 (CST) Date: Thu, 7 Mar 2013 12:43:54 -0600 From: Ben Myers To: Brian Foster Cc: xfs@oss.sgi.com Subject: Re: [PATCH] xfs: increase prealloc size to double that of the previous extent Message-ID: <20130307184354.GO22182@sgi.com> References: <1361231827-58766-1-git-send-email-bfoster@redhat.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <1361231827-58766-1-git-send-email-bfoster@redhat.com> User-Agent: Mutt/1.5.20 (2009-06-14) On Mon, Feb 18, 2013 at 06:57:07PM -0500, Brian Foster wrote: > The updated speculative preallocation algorithm becomes less > effective in situations with a high number of concurrent, > sequential writers. In running 32 sequential writers on a system > with 32GB RAM, preallocs become fixed at a value of around 128MB. > Update the heuristic to base the size of the prealloc on double > the size of the preceding extent. This preserves the original > aggressive speculative preallocation behavior at a slight cost of > increasing the size of preallocated data regions following holes of > sparse files. > > Signed-off-by: Brian Foster Applied. -Ben From bpm@sgi.com Thu Mar 7 12:45:05 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 3CBF67FA1 for ; Thu, 7 Mar 2013 12:45:05 -0600 (CST) Received: from whiskey.americas.sgi.com (eagdhcp-232-197.americas.sgi.com [128.162.232.197]) by relay3.corp.sgi.com (Postfix) with ESMTP id 50259AC009; Thu, 7 Mar 2013 10:45:04 -0800 (PST) Received: by whiskey.americas.sgi.com (Postfix, from userid 4600) id 170D7500B4A; Thu, 7 Mar 2013 12:45:04 -0600 (CST) Date: Thu, 7 Mar 2013 12:45:04 -0600 From: Ben Myers To: Brian Foster Cc: xfs@oss.sgi.com Subject: Re: [PATCH v2] xfs: increase prealloc size to double that of the previous extent Message-ID: <20130307184504.GP22182@sgi.com> References: <1361287481-9649-1-git-send-email-bfoster@redhat.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <1361287481-9649-1-git-send-email-bfoster@redhat.com> User-Agent: Mutt/1.5.20 (2009-06-14) On Tue, Feb 19, 2013 at 10:24:41AM -0500, Brian Foster wrote: > The updated speculative preallocation algorithm for handling sparse > files can becomes less effective in situations with a high number of > concurrent, sequential writers. The number of writers and amount of > available RAM affect the writeback bandwidth slicing algorithm, > which in turn affects the block allocation pattern of XFS. For > example, running 32 sequential writers on a system with 32GB RAM, > preallocs become fixed at a value of around 128MB (instead of > steadily increasing to the 8GB maximum as sequential writes > proceed). > > Update the speculative prealloc heuristic to base the size of the > next prealloc on double the size of the preceding extent. This > preserves the original aggressive speculative preallocation > behavior and continues to accomodate sparse files at a slight cost > of increasing the size of preallocated data regions following holes > of sparse files. > > Signed-off-by: Brian Foster > Reviewed-by: Dave Chinner Excuse me. This is the version I applied. Not v1. -Ben From bpm@sgi.com Thu Mar 7 12:45:39 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 858AF7FA1 for ; Thu, 7 Mar 2013 12:45:39 -0600 (CST) Received: from whiskey.americas.sgi.com (eagdhcp-232-197.americas.sgi.com [128.162.232.197]) by relay2.corp.sgi.com (Postfix) with ESMTP id 605A3304081; Thu, 7 Mar 2013 10:45:39 -0800 (PST) Received: by whiskey.americas.sgi.com (Postfix, from userid 4600) id 2E6C5500B4B; Thu, 7 Mar 2013 12:45:39 -0600 (CST) Date: Thu, 7 Mar 2013 12:45:39 -0600 From: Ben Myers To: Mark Tinguely Cc: xfs@oss.sgi.com Subject: Re: [PATCH] xfs: fix xfs_iomap_eof_prealloc_initial_size type Message-ID: <20130307184539.GQ22182@sgi.com> References: <20130224190436.906161932@sgi.com> <20130224190441.937509860@sgi.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <20130224190441.937509860@sgi.com> User-Agent: Mutt/1.5.20 (2009-06-14) On Sun, Feb 24, 2013 at 01:04:37PM -0600, Mark Tinguely wrote: > Fix the return type of xfs_iomap_eof_prealloc_initial_size() to > xfs_fsblock_t to reflect the fact that the return value may be an > unsigned 64 bits if XFS_BIG_BLKNOS is defined. > > Signed-off-by: Mark Tinguely Applied. From bpm@sgi.com Thu Mar 7 12:46:24 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 9D27D7FA1 for ; Thu, 7 Mar 2013 12:46:24 -0600 (CST) Received: from whiskey.americas.sgi.com (eagdhcp-232-197.americas.sgi.com [128.162.232.197]) by relay1.corp.sgi.com (Postfix) with ESMTP id 86C478F8066; Thu, 7 Mar 2013 10:46:24 -0800 (PST) Received: by whiskey.americas.sgi.com (Postfix, from userid 4600) id 6736D500B4A; Thu, 7 Mar 2013 12:46:24 -0600 (CST) Date: Thu, 7 Mar 2013 12:46:24 -0600 From: Ben Myers To: Dave Chinner Cc: xfs@oss.sgi.com Subject: Re: [PATCH] xfs: don't verify buffers after IO errors Message-ID: <20130307184624.GR22182@sgi.com> References: <1361931954-11105-1-git-send-email-david@fromorbit.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <1361931954-11105-1-git-send-email-david@fromorbit.com> User-Agent: Mutt/1.5.20 (2009-06-14) On Wed, Feb 27, 2013 at 01:25:54PM +1100, Dave Chinner wrote: > From: Dave Chinner > > When we read a buffer, we might get an error from the underlying > block device and not the real data. Hence if we get an IO error, we > shouldn't run the verifier but instead just pass the IO error > straight through. > > Signed-off-by: Dave Chinner Applied. -Ben From bpm@sgi.com Thu Mar 7 12:48:00 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id BDF1D7FE9 for ; Thu, 7 Mar 2013 12:48:00 -0600 (CST) Received: from whiskey.americas.sgi.com (eagdhcp-232-197.americas.sgi.com [128.162.232.197]) by relay2.corp.sgi.com (Postfix) with ESMTP id 5C5B630406B; Thu, 7 Mar 2013 10:48:00 -0800 (PST) Received: by whiskey.americas.sgi.com (Postfix, from userid 4600) id 2F201500B4A; Thu, 7 Mar 2013 12:48:00 -0600 (CST) Date: Thu, 7 Mar 2013 12:48:00 -0600 From: Ben Myers To: Akinobu Mita Cc: linux-kernel@vger.kernel.org, akpm@linux-foundation.org, Alex Elder , xfs@oss.sgi.com Subject: Re: [PATCH -v3 12/23] xfs: rename random32() to prandom_u32() Message-ID: <20130307184800.GW30652@sgi.com> References: <1362401911-14074-1-git-send-email-akinobu.mita@gmail.com> <1362401911-14074-13-git-send-email-akinobu.mita@gmail.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <1362401911-14074-13-git-send-email-akinobu.mita@gmail.com> User-Agent: Mutt/1.5.20 (2009-06-14) Akinobu, On Mon, Mar 04, 2013 at 09:58:20PM +0900, Akinobu Mita wrote: > Use more preferable function name which implies using a pseudo-random > number generator. > > Signed-off-by: Akinobu Mita > Acked-by: > Cc: Ben Myers > Cc: Alex Elder > Cc: xfs@oss.sgi.com Applied this to git://oss.sgi.com/xfs/xfs.git, master branch. Thanks! -Ben From bpm@sgi.com Thu Mar 7 12:48:49 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 769AB7FEF for ; Thu, 7 Mar 2013 12:48:49 -0600 (CST) Received: from whiskey.americas.sgi.com (eagdhcp-232-197.americas.sgi.com [128.162.232.197]) by relay3.corp.sgi.com (Postfix) with ESMTP id 04F01AC001; Thu, 7 Mar 2013 10:48:48 -0800 (PST) Received: by whiskey.americas.sgi.com (Postfix, from userid 4600) id AD2E1500B4A; Thu, 7 Mar 2013 12:48:48 -0600 (CST) Date: Thu, 7 Mar 2013 12:48:48 -0600 From: Ben Myers To: Dave Chinner Cc: xfs@oss.sgi.com Subject: Re: [PATCH 01/16] xfs: rearrange some code in xfs_bmap for better locality Message-ID: <20130307184848.GS22182@sgi.com> References: <1361755901-12453-1-git-send-email-david@fromorbit.com> <1361755901-12453-2-git-send-email-david@fromorbit.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <1361755901-12453-2-git-send-email-david@fromorbit.com> User-Agent: Mutt/1.5.20 (2009-06-14) On Mon, Feb 25, 2013 at 12:31:26PM +1100, Dave Chinner wrote: > From: Dave Chinner > > xfs_bmap.c is a big file, and some of the related code is spread all > throughout the file requiring function prototypes for static > function and jumping all through the file to follow a single call > path. Rearrange the code so that: > > a) related functionality is grouped together; and > b) functions are grouped in call dependency order > > While the diffstat is large, there are no code changes in the patch; > it is just moving the functionality around and removing the function > prototypes at the top of the file. The resulting layout of the code > is as follows (top of file to bottom): > > - miscellaneous helper functions > - extent tree block counting routines > - debug/sanity checking code > - bmap free list manipulation functions > - inode fork format manipulation functions > - internal/external extent tree seach functions > - extent tree manipulation functions used during allocation > - functions used during extent read/allocate/removal > operations (i.e. xfs_bmapi_write, xfs_bmapi_read, > xfs_bunmapi and xfs_getbmap) > > This means that following logic paths through the bmapi code is much > simpler - most of the code relevant to a specific operation is now > clustered together rather than spread all over the file.... > > Signed-off-by: Dave Chinner Applied. -Ben From bpm@sgi.com Thu Mar 7 14:16:22 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id EB01E7F9B for ; Thu, 7 Mar 2013 14:16:21 -0600 (CST) Received: from whiskey.americas.sgi.com (eagdhcp-232-197.americas.sgi.com [128.162.232.197]) by relay3.corp.sgi.com (Postfix) with ESMTP id 3A48CAC003; Thu, 7 Mar 2013 12:16:18 -0800 (PST) Received: by whiskey.americas.sgi.com (Postfix, from userid 4600) id D8E68500B4A; Thu, 7 Mar 2013 14:16:17 -0600 (CST) Date: Thu, 7 Mar 2013 14:16:17 -0600 From: Ben Myers To: Hans-Peter Jansen Cc: Dave Chinner , xfs@oss.sgi.com Subject: Re: Fwd: xfs_reno Message-ID: <20130307201617.GT22182@sgi.com> References: <20351675.Zy117sIl8Z@xrated> <20130307041348.GD6369@dastard> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <20130307041348.GD6369@dastard> User-Agent: Mutt/1.5.20 (2009-06-14) Hi Pete, On Thu, Mar 07, 2013 at 03:13:48PM +1100, Dave Chinner wrote: > On Wed, Mar 06, 2013 at 03:55:19PM +0100, Hans-Peter Jansen wrote: > > Hi Dave, > > > > I tried to gather Barrys SOB, but failed so far. His trace ends in 2009 google > > wise. > > > > How is this case usually handled? > > > > Here's the current state of things. > > He was working for SGI at the time, so you should be able to get > anyone from SGI provide a valid S-O-B if needed. > > As it is, I can probably verify the patch origins sufficiently > to add a SOB to it as: > > http://oss.sgi.com/archives/xfs/2007-11/msg00769.html > > It's pretty clear that the code was released under the GPL and free > from any tainted code by SGI. The post I'm pointing to above is one > I made while an SGI employee, and it effectively verifies the origin > of the code in the same way a S-O-B does. > > So, you probably don't even need to chase a S-O-B from SGI if you > just point at that email and attribute the code correctly. i.e. > retaining al the SGI copyright notices in the code and saying inteh > patch description that the code was originally authored by SGI and > released under the same license as the rest of the xfs userspace > code. Looks good to me as is. Links and attribution are in the header, copyright notices, etc. We'll clean up that copyright header in the Makefile with a separate commit authored by a current SGI employee. You can add a Signed-off-by: Ben Myers if you want. No need to repost just for that. Thanks for spending the time! Regards, Ben From pg_mh@mh.to.sabi.co.uk Thu Mar 7 15:04:45 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 334197F78 for ; Thu, 7 Mar 2013 15:04:45 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay1.corp.sgi.com (Postfix) with ESMTP id 103268F804B for ; Thu, 7 Mar 2013 13:04:41 -0800 (PST) X-ASG-Debug-ID: 1362690280-04cbb07dbe2820a0001-NocioJ Received: from honeysuckle.london.02.net (honeysuckle.london.02.net [87.194.255.144]) by cuda.sgi.com with ESMTP id pI8ajD6IDvjX8nHx for ; Thu, 07 Mar 2013 13:04:40 -0800 (PST) X-Barracuda-Envelope-From: pg_mh@mh.to.sabi.co.UK X-Barracuda-Apparent-Source-IP: 87.194.255.144 Received: from ty.sabi.co.UK (78.86.80.54) by honeysuckle.london.02.net (8.5.140) id 50D1042B04BC0EAA for xfs@oss.sgi.com; Thu, 7 Mar 2013 21:04:39 +0000 Received: from from [127.0.0.1] (helo=tree.ty.sabi.co.uk) by ty.sabi.co.UK with esmtp(Exim 4.76 #1) id 1UDhzK-0007NZ-Gq for ; Thu, 07 Mar 2013 21:04:30 +0000 Resent-Message-ID: <20793.222.376461.229641@tree.ty.sabi.co.uk> Resent-Date: Thu, 7 Mar 2013 21:04:30 +0000 Resent-To: xfs@oss.sgi.com Content-Transfer-Encoding: 7bit X-Face: SMJE]JPYVBO-9UR%/8d'mG.F!@.,l@c[f'[%S8'BZIcbQc3/">GrXDwb#;fTRGNmHr^JFb SAptvwWc,0+z+~p~"Gdr4H$(|N(yF(wwCM2bW0~U?HPEE^fkPGx^u[*[yV.gyB!hDOli}EF[\cW*S H&spRGFL}{`bj1TaD^l/"[ msn( /TH#THs{Hpj>)]f> Message-ID: <20791.50126.796065.137158@tree.ty.sabi.co.uk> References: <20130306202210.GA1318@quack.suse.cz> In-Reply-To: <20130306202210.GA1318@quack.suse.cz> X-Barracuda-Connect: honeysuckle.london.02.net[87.194.255.144] X-Barracuda-Start-Time: 1362690280 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124544 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- Resent-From: pg_mh@mh.to.sabi.co.UK > [ ... ] application that write large (tens of GB) files using > direct IO done in 16 MB chunks. They keep the fs around 80% > full deleting oldest files when they need to store new ones. > Usually the file can be stored in under 10 extents but from > time to time a pathological case is triggered and the file has > few thousands extents (which naturally has impact on > performance). [ ... ] They just want *guaranteed* (not just nearly-always) contiguity, without preallocating, with incremental writes with direct IO, while keeping the filesystem full at 80%. And a pony! :-) From david@fromorbit.com Thu Mar 7 16:27:53 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 3B1D77F95 for ; Thu, 7 Mar 2013 16:27:53 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay3.corp.sgi.com (Postfix) with ESMTP id BACDBAC001 for ; Thu, 7 Mar 2013 14:27:49 -0800 (PST) X-ASG-Debug-ID: 1362695267-04cb6c2b0427be60001-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id fFAqCpiVi3DubKxi for ; Thu, 07 Mar 2013 14:27:47 -0800 (PST) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AtgjAGkTOVF5LAvR/2dsb2JhbABDvz2FFgECAYFjF3SCLAEBBAE6HCgLCAMYCSUPBSUDIQESiA0FDbtBFY12GB9Rg0ADlkqBH49Tgx0 Received: from ppp121-44-11-209.lns20.syd6.internode.on.net (HELO dastard) ([121.44.11.209]) by ipmail05.adl6.internode.on.net with ESMTP; 08 Mar 2013 08:57:46 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UDjHt-0006Z6-3x; Fri, 08 Mar 2013 09:27:45 +1100 Date: Fri, 8 Mar 2013 09:27:45 +1100 From: Dave Chinner To: dsterba@suse.cz, Rich Johnston , xfs@oss.sgi.com Subject: Re: [PATCH] xfstests: enhance ltp/fsx with a timeout option Message-ID: <20130307222745.GT23616@dastard> X-ASG-Orig-Subj: Re: [PATCH] xfstests: enhance ltp/fsx with a timeout option References: <1358944851-14336-1-git-send-email-dsterba@suse.cz> <51378B7F.9090103@sgi.com> <20130307182525.GA29541@suse.cz> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <20130307182525.GA29541@suse.cz> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1362695267 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124550 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Thu, Mar 07, 2013 at 07:25:25PM +0100, David Sterba wrote: > Hi, > > On Wed, Mar 06, 2013 at 12:31:27PM -0600, Rich Johnston wrote: > > I used test 263 to verify that fsx works as expected with the new -T and the > > existing -N options. With the -T option of course, test 263 will fail. I > > don't suggest that we change existing tests but add new tests which use the > > new -T option. Do you have a new test which you intend to use the -T option > > that can be submitted with this patch? > > I understand that changing behaviour of existing checks is not desirable. > > The -T option to fsx was inspired by the test we used to hunt a bug at > 3.8-rc time where 50 concurrent direct io fsx jobs triggered the bug in > about 10 minutes or it was considered fine. > > fsx -q xxxf$x -Z -R -W -r 4096 -w 4096 > (http://permalink.gmane.org/gmane.comp.file-systems.btrfs/22447) fsx is already run with those exact parameters as part of test 091. > I'll send this test integrated into xfstests harness. There's little point in adding duplicate tests that only differ in runtime. It does not improve test coverage at all and only increases the overall test harness run time. If you want to run 091 for longer, add support for the new LOAD_FACTOR variable so you can increase the number of ops it runs for. Alternatively, make fsx use both -N ops and -T time simultaneously, and stop the execution whenever the first criteria expires. That way you can bound the test run time, and just use LOAD_FACTOR to make sure it runs for the desired amount out time.... Cheers, Dave. -- Dave Chinner david@fromorbit.com From david@fromorbit.com Thu Mar 7 16:31:44 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id C03927FC1 for ; Thu, 7 Mar 2013 16:31:44 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay2.corp.sgi.com (Postfix) with ESMTP id A8698304059 for ; Thu, 7 Mar 2013 14:31:44 -0800 (PST) X-ASG-Debug-ID: 1362695501-04cb6c2b0227c3c0001-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id HBGvB9qCKIzxMdlh for ; Thu, 07 Mar 2013 14:31:43 -0800 (PST) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AtgjAMYUOVF5LAvR/2dsb2JhbABDvz2FFgECAYFjF3SCLAEBBTocIxAIAw4KCRoLDwUlAyETiBK7TBWNdhgfSgeDQAOWSolnhwuBU4FK Received: from ppp121-44-11-209.lns20.syd6.internode.on.net (HELO dastard) ([121.44.11.209]) by ipmail05.adl6.internode.on.net with ESMTP; 08 Mar 2013 09:01:41 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UDjLg-0006Zc-Jx; Fri, 08 Mar 2013 09:31:40 +1100 Date: Fri, 8 Mar 2013 09:31:40 +1100 From: Dave Chinner To: Matteo Frigo Cc: dm-devel@redhat.com, xfs@oss.sgi.com Subject: Re: [dm-devel] [BUG] pvmove corrupting XFS filesystems (was Re: [BUG] Internal error xfs_dir2_data_reada_verify) Message-ID: <20130307223140.GU23616@dastard> X-ASG-Orig-Subj: Re: [dm-devel] [BUG] pvmove corrupting XFS filesystems (was Re: [BUG] Internal error xfs_dir2_data_reada_verify) References: <87d2vnc34r.fsf@fftw.org> <20130226044039.GM5551@dastard> <20130227010414.GD1514@agk.fab.redhat.com> <20130227014900.GY5551@dastard> <87y5eah4xz.fsf@fftw.org> <87k3pjs908.fsf@fftw.org> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <87k3pjs908.fsf@fftw.org> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1362695501 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124550 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Thu, Mar 07, 2013 at 07:13:27AM -0500, Matteo Frigo wrote: > Matteo Frigo writes: > > > Well, I don't really know anything about this topic, so I may be > > completely off the mark, but dm-raid1.c:mirror_map() does indeed return > > EWOULDBLOCK, and EWOULDBLOCK is #define'd to be EAGAIN, so it seems to > > me that dm-raid1 does indeed return EAGAIN for "rw == READA" (which I > > assume is read-ahead) if the "region is not in-sync": > > > > /* > > * If region is not in-sync queue the bio. > > */ > > if (!r || (r == -EWOULDBLOCK)) { > > if (rw == READA) > > return -EWOULDBLOCK; > > > > queue_bio(ms, bio, rw); > > return DM_MAPIO_SUBMITTED; > > } > > Dave (and others), > > do you have any suggestion on what should be done to fix this bug? > > I have tried returning -EIO instead of -EWOULDBLOCK, but xfs does not > like that. dm-zero.c:zero_map() appears to return -EIO too, so this is > another potential issue. You need the XFS patch I posted so that readahead buffer verification is avoided in the case of an error being returned from the readahead. Cheers, Dave. -- Dave Chinner david@fromorbit.com From bounce2@uygunundan.com Thu Mar 7 16:42:07 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: * X-Spam-Status: No, score=1.7 required=5.0 tests=DATE_IN_PAST_06_12, HTML_MESSAGE,T_DKIM_INVALID autolearn=no version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id E5B6C7FC4 for ; Thu, 7 Mar 2013 16:42:07 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay2.corp.sgi.com (Postfix) with ESMTP id AFB8D30406A for ; Thu, 7 Mar 2013 14:42:07 -0800 (PST) X-ASG-Debug-ID: 1362696124-04bdf0229829def0001-NocioJ Received: from server1.uygunundan.com (server-176.53.34.57.as42926.net [176.53.34.57]) by cuda.sgi.com with ESMTP id 5HzOVHxXascphkT6 for ; Thu, 07 Mar 2013 14:42:04 -0800 (PST) X-Barracuda-Envelope-From: bounce2@uygunundan.com X-Barracuda-Apparent-Source-IP: 176.53.34.57 DKIM-Signature: v=1; a=rsa-sha1; c=relaxed/relaxed; s=key1; d=uygunundan.com; h=To:Subject:Message-ID:Date:From:Reply-To:MIME-Version:List-Unsubscribe:Content-Type:Content-Transfer-Encoding; i=duyuru@uygunundan.com; bh=FiH/TN0iMDQ+1Tana2yNb1yD5ww=; b=GY/W+O84F/uS2T6OS7a/TN9/kVEa3fXGtwUfep85tYEHwZnJ2Zj/2kkx9FsL8bDjwugAaxtZH9Q/ CzVN6/TwLuYncLWz80gAWCdoJ1WkAiDIG45AxyXwFVnJKzj+/sz9GbGNHU7nA6dpp/XzEzFL3/xC dbfYswYNJ5yH63UW56U= DomainKey-Signature: a=rsa-sha1; c=nofws; q=dns; s=key1; d=uygunundan.com; b=V4DfHRl7eBo1q1dZ0DY+Ku5GrjUuPJl+ATA75KBQU63k4tbLPvnj6gZN39N7BWnRfXABRYZG+iLE ACxVqSAe38nlsWuv0VqhvLF6W9u8EETWl8IiRNvQLMBbCs3pYq2n8/9CMiwwFDBtwddxwOp8Z4tg aqJhN1HveGt8UYs/jLY=; To: xfs@oss.sgi.com Subject: =?UTF-8?B?TWFzcmFmc2l6IEtvbWlzeW9uc3V6IEthcGlkYSBLcmVkaSDDnHN0ZWxpayBEZXYgU2Ftc3VuZyBMZWQgVFYgRmlyc2F0aXlsYQ==?= Message-ID: X-ASG-Orig-Subj: =?UTF-8?B?TWFzcmFmc2l6IEtvbWlzeW9uc3V6IEthcGlkYSBLcmVkaSDDnHN0ZWxpayBEZXYgU2Ftc3VuZyBMZWQgVFYgRmlyc2F0aXlsYQ==?= Date: Thu, 07 Mar 2013 07:53:13 -0500 From: "BankPozitif" Reply-To: duyuru@uygunundan.com MIME-Version: 1.0 X-Mailer-LID: 5 List-Unsubscribe: X-Mailer-RecptId: 956282 X-Mailer-SID: 6 X-Mailer-Sent-By: 1 Content-Type: multipart/alternative; charset="UTF-8"; boundary="b1_ace712576f21b05610df178290bee2bf" Content-Transfer-Encoding: 8bit X-Barracuda-Connect: server-176.53.34.57.as42926.net[176.53.34.57] X-Barracuda-Start-Time: 1362696124 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 1.91 X-Barracuda-Spam-Status: No, SCORE=1.91 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_SA038b, BSF_SC5_MJ1963, DATE_IN_PAST_06_12, DATE_IN_PAST_06_12_2, DKIM_SIGNED, DKIM_VERIFIED, HTML_MESSAGE, RDNS_DYNAMIC X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124550 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.01 DATE_IN_PAST_06_12 Date: is 6 to 12 hours before Received: date -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature 0.00 HTML_MESSAGE BODY: HTML included in message 0.20 BSF_SC0_SA038b Custom Rule SA038b 1.10 DATE_IN_PAST_06_12_2 DATE_IN_PAST_06_12_2 0.10 RDNS_DYNAMIC Delivered to trusted network by host with dynamic-looking rDNS 0.50 BSF_SC5_MJ1963 Custom Rule MJ1963 --b1_ace712576f21b05610df178290bee2bf Content-Type: text/plain; format=flowed; charset="UTF-8" Content-Transfer-Encoding: 8bit BankPozitiften 30Mart 2013 e kadar kredi kullanan herkes 189 Ekran Samsung LED Tv yada 10 Ipad Mini'den birini kazanma f?rsat?n? yakal?yor. Ba?vurunuzu online yap?n banka yetkililerimiz sizin kap?n?za kadar gelip imza i?lemlerini yaps?nlar... Üstelik BankPozitif Kredi masraflar?n? ve komisyonlar?n?da kald?rd?. Daha detayl? bilgi ve ba?vuru için; http://uygunundan.com/link.php?M=956282&N=6&L=1&F=T http://uygunundan.com/unsubscribe.php?M=956282&C=4bb72257f3c93f85b3d9c86d6ee83fb0&L=5&N=6 --b1_ace712576f21b05610df178290bee2bf Content-Type: text/html; charset="UTF-8" Content-Transfer-Encoding: 8bit
BankPozitif
BankPozitif
BankPozitif
Bu e-Posta BankPozitif'in sundu?u kampanyalar, avantajlar ve ürünler hakk?nda bilgilendirmek amac?yla haz?rlanm??t?r.
BankPozitif e-posta üyeli?inden ç?kmak için Unsubscribe me from this list
Sizlere daha iyi hizmet sunabilmemiz ve tüm sorular?n?z için,
bize Mesaj Merkezimiz üzerinden ula?abilirsiniz.
Bizi takip edin:
Bu E-posta mesaj? gizlidir. Ayr?ca sadece yukar?da ad? geçen ki?iye özel bilgi içeriyor olabilir. Mesaj?n gönderilmek istendi?i ki?i siz de?ilseniz hiçbir k?sm?n? kopyalayamaz ba?kas?na gönderemez ba?kas?na aç?klayamaz veya kullanamazs?n?z. E?er bu mesaj size yanl??l?kla ula?m??sa lütfen mesaj? ve tüm kopyalar?n? sisteminizden silin ve gönderen ki?iyi E-posta yolu ile bilgilendirin. ?nternet ileti?iminde zaman?nda güvenli hatas?z ya da virüssüz gönderim garanti edilemez. Gönderen taraf hata veya unutmalardan sorumluluk kabul etmez.
--b1_ace712576f21b05610df178290bee2bf-- From david@fromorbit.com Thu Mar 7 16:48:36 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id DBFEF7FC4 for ; Thu, 7 Mar 2013 16:48:36 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay3.corp.sgi.com (Postfix) with ESMTP id 70C11AC009 for ; Thu, 7 Mar 2013 14:48:36 -0800 (PST) X-ASG-Debug-ID: 1362696513-04cbb07dbe28cce0001-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id YpIrJk0DBFTCmuEE for ; Thu, 07 Mar 2013 14:48:34 -0800 (PST) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AtcjAP0XOVF5LAvR/2dsb2JhbABDvz2FFgECAYFjF3SCLAEBBTocMwgDGAklDwUlAyEBEogSDbs8FY1GMBgfUYNAA5ZKkHKDHYFe Received: from ppp121-44-11-209.lns20.syd6.internode.on.net (HELO dastard) ([121.44.11.209]) by ipmail05.adl6.internode.on.net with ESMTP; 08 Mar 2013 09:18:33 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UDjc0-0006bc-KP; Fri, 08 Mar 2013 09:48:32 +1100 Date: Fri, 8 Mar 2013 09:48:32 +1100 From: Dave Chinner To: dsterba@suse.cz, Wang Sheng-Hui , xfs@oss.sgi.com Subject: Re: [PATCH] xfstests 273: fix a typo Message-ID: <20130307224832.GV23616@dastard> X-ASG-Orig-Subj: Re: [PATCH] xfstests 273: fix a typo References: <512DAC1A.2040601@gmail.com> <20130306232222.GF21081@twin.jikos.cz> <20130307033849.GB6369@dastard> <20130307110600.GJ21081@twin.jikos.cz> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <20130307110600.GJ21081@twin.jikos.cz> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1362696513 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124552 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Thu, Mar 07, 2013 at 12:06:01PM +0100, David Sterba wrote: > On Thu, Mar 07, 2013 at 02:38:49PM +1100, Dave Chinner wrote: > > On Thu, Mar 07, 2013 at 12:22:22AM +0100, David Sterba wrote: > > > On Wed, Feb 27, 2013 at 02:47:54PM +0800, Wang Sheng-Hui wrote: > > > > - cp -r $SCRATCH_MNT/origin $SCRATCH_MNT/sub_$_suffix >$seq.full 2>&1 > > > > + cp -r $SCRATCH_MNT/origin $SCRATCH_MNT/sub_$_suffix >>$seq.full 2>&1 > > This is quote from the mail, but the merged patch does something else. > > > > +./273: line 95: syntax error near unexpected token `&' > > > +./273: line 95: ` cp -r $SCRATCH_MNT/origin $SCRATCH_MNT/sub_$_suffix >$seq.full 2>>&1' > > > +umount: /dev/sda9: not mounted > > > that seems rather strange. The patch does this: > > > > ....sub_$_suffix >>$seq.full 2>&1 > > http://oss.sgi.com/cgi-bin/gitweb.cgi?p=xfs/cmds/xfstests.git;a=commitdiff;h=0c5e67e46e476b70290033efc7feb784f7ecbab1;hp=08557e219c12e573be459407033495899f46967a Oh.... > --- > > > and the error output you see is > > > > ....sub_$_suffix >$seq.full 2>>&1 > > > > So it doesn't look lie you are running with the change that is > > actually in the patch... > > There's a difference between the patch in mail and what has been merged, that > can happen, but I wonder why it works on your side. .... because I haven't updated to the latest xfstests master branch yet - I'm running with the patch from the list applied. I didn't realise you were running from the main repo, and that the commit was busted... Cheers, Dave. -- Dave Chinner david@fromorbit.com From david@fromorbit.com Thu Mar 7 16:50:05 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id EF2627FD0 for ; Thu, 7 Mar 2013 16:50:04 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay3.corp.sgi.com (Postfix) with ESMTP id 86289AC004 for ; Thu, 7 Mar 2013 14:50:04 -0800 (PST) X-ASG-Debug-ID: 1362696602-04bdf0229529ea50001-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id ZuaN1JFygOZJPmCW for ; Thu, 07 Mar 2013 14:50:02 -0800 (PST) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AtgjADAZOVF5LAvR/2dsb2JhbABDvz2FFgECAYFjF3SCLAEBBTocIxAIAw4KCRoLDwUlAyETiBINu0IVjXYYH0oHg0ADlkqJZ4cLgVOBSg Received: from ppp121-44-11-209.lns20.syd6.internode.on.net (HELO dastard) ([121.44.11.209]) by ipmail05.adl6.internode.on.net with ESMTP; 08 Mar 2013 09:20:01 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UDjdR-0006bl-Gz; Fri, 08 Mar 2013 09:50:01 +1100 Date: Fri, 8 Mar 2013 09:50:01 +1100 From: Dave Chinner To: Matteo Frigo Cc: dm-devel@redhat.com, xfs@oss.sgi.com Subject: Re: [dm-devel] [BUG] pvmove corrupting XFS filesystems (was Re: [BUG] Internal error xfs_dir2_data_reada_verify) Message-ID: <20130307225001.GW23616@dastard> X-ASG-Orig-Subj: Re: [dm-devel] [BUG] pvmove corrupting XFS filesystems (was Re: [BUG] Internal error xfs_dir2_data_reada_verify) References: <87d2vnc34r.fsf@fftw.org> <20130226044039.GM5551@dastard> <20130227010414.GD1514@agk.fab.redhat.com> <20130227014900.GY5551@dastard> <87y5eah4xz.fsf@fftw.org> <87k3pjs908.fsf@fftw.org> <20130307223140.GU23616@dastard> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <20130307223140.GU23616@dastard> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1362696602 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124552 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Fri, Mar 08, 2013 at 09:31:40AM +1100, Dave Chinner wrote: > On Thu, Mar 07, 2013 at 07:13:27AM -0500, Matteo Frigo wrote: > > Matteo Frigo writes: > > > > > Well, I don't really know anything about this topic, so I may be > > > completely off the mark, but dm-raid1.c:mirror_map() does indeed return > > > EWOULDBLOCK, and EWOULDBLOCK is #define'd to be EAGAIN, so it seems to > > > me that dm-raid1 does indeed return EAGAIN for "rw == READA" (which I > > > assume is read-ahead) if the "region is not in-sync": > > > > > > /* > > > * If region is not in-sync queue the bio. > > > */ > > > if (!r || (r == -EWOULDBLOCK)) { > > > if (rw == READA) > > > return -EWOULDBLOCK; > > > > > > queue_bio(ms, bio, rw); > > > return DM_MAPIO_SUBMITTED; > > > } > > > > Dave (and others), > > > > do you have any suggestion on what should be done to fix this bug? > > > > I have tried returning -EIO instead of -EWOULDBLOCK, but xfs does not > > like that. dm-zero.c:zero_map() appears to return -EIO too, so this is > > another potential issue. > > You need the XFS patch I posted so that readahead buffer > verification is avoided in the case of an error being returned from > the readahead. I don't recall if that patch was sent to this thread, so here it is: http://oss.sgi.com/archives/xfs/2013-02/msg00516.html Cheers, Dave. -- Dave Chinner david@fromorbit.com From david@fromorbit.com Thu Mar 7 17:00:50 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id F09D27CBF for ; Thu, 7 Mar 2013 17:00:49 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay3.corp.sgi.com (Postfix) with ESMTP id 83ACCAC001 for ; Thu, 7 Mar 2013 15:00:49 -0800 (PST) X-ASG-Debug-ID: 1362697247-04bdf0229629fc30001-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id AsFGfnga7AdoSDVE for ; Thu, 07 Mar 2013 15:00:48 -0800 (PST) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AtgjANkbOVF5LAvR/2dsb2JhbABDvz2FFgECAYFjF3SCLAEBBAEnExwjEAgDGAklDwUlAyETiA0Fu08VjXYYH0oHg0ADlkqQcoFTgUo Received: from ppp121-44-11-209.lns20.syd6.internode.on.net (HELO dastard) ([121.44.11.209]) by ipmail05.adl6.internode.on.net with ESMTP; 08 Mar 2013 09:30:20 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UDjnQ-0006d6-4l; Fri, 08 Mar 2013 10:00:20 +1100 Date: Fri, 8 Mar 2013 10:00:20 +1100 From: Dave Chinner To: Dennis Kaarsemaker Cc: xfs@oss.sgi.com Subject: Re: XFS IO multiplication problem on centos/rhel 6 using hp p420i raid controllers Message-ID: <20130307230020.GX23616@dastard> X-ASG-Orig-Subj: Re: XFS IO multiplication problem on centos/rhel 6 using hp p420i raid controllers References: <1362060736.1247.30.camel@seahawk> <20130228194023.GQ5551@dastard> <1362577992.1247.84.camel@seahawk> <20130307035737.GC6369@dastard> <1362651128.16657.13.camel@seahawk> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <1362651128.16657.13.camel@seahawk> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1362697247 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.50 X-Barracuda-Spam-Status: No, SCORE=0.50 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC1_TG070 X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124552 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.50 BSF_SC1_TG070 Custom Rule TG070 On Thu, Mar 07, 2013 at 11:12:08AM +0100, Dennis Kaarsemaker wrote: > On Thu, 2013-03-07 at 14:57 +1100, Dave Chinner wrote: > > On Wed, Mar 06, 2013 at 02:53:12PM +0100, Dennis Kaarsemaker wrote: .... > > > #<----CPU[HYPER]-----><----------Disks-----------><----------Network----------> > > > #cpu sys inter ctxsw KBRead Reads KBWrit Writes KBIn PktIn KBOut PktOut > > > 1 0 1636 4219 16 1 2336 313 184 195 12 133 > > > 1 0 1654 2804 64 3 2919 432 391 352 20 208 > > > > > > [root@bc291bprdb-01 ~]# collectl > > > #<----CPU[HYPER]-----><----------Disks-----------><----------Network----------> > > > #cpu sys inter ctxsw KBRead Reads KBWrit Writes KBIn PktIn KBOut PktOut > > > 1 0 2220 3691 332 13 39992 331 112 122 6 92 > > > 0 0 1354 2708 0 0 39836 335 103 125 9 99 > > > 0 0 1563 3023 120 6 44036 369 399 317 13 188 > > > > > > Notice the KBWrit difference. These are two identical hp gen 8 machines, > > > doing the same thing (replicating the same mysql schema). The one > > > writing ten times as many bytes in the same amount of transactions is > > > running centos 6 (and was running rhel 6). > > > > So what is the problem? it is writing too much on the on the centos > > 6 machine? Either way, this doesn't sound like a filesystem problem > > - the size and amount of data writes is entirely determined by the > > application. > > For performing the same amount of work (processing the same mysql > transactions, the same amount of IO transactions resulting from them), > the 'broken' case writes ten-ish times as many bytes. Thanks for clarifying. > > > /dev/mapper/sysvm-mysqlVol /mysql/bp xfs rw,relatime,attr2,delaylog,allocsize=1024k,logbsize=256k,sunit=512,swidth=1536,noquota 0 0 > > > > What is the reason for using allocsize, sunit/swidth? Are you using > > them on other machines? > > xfs autodetects them from the hpsa driver. They seem to be correct for > the raid layout (256 strips, 3 drives per mirror pool) and I don't seem > to be able to override them. That's fine, they're set correctly. I'd forgotten that the number are emitted in /proc/mounts even when they are not specified as mount options. > > And if you remove the allocsize mount option, does the behaviour on > > centos6.3 change? What happens if you set allocsize=4k? > > The allocsize parameter has no effect. It was put in place to correct a > monitoring issue: due to mysql's access patterns, using the default > large allocsize on rhel 6 makes our monitoring report the filesystem as > much fuller than it actually is. Which is due to speculative EOF preallocation, and so it is only set on the CentOS box that is showing the larger write behaviour? Have you tried setting it to 4k? If not, please do - EOF preallocation for sparse extending writes can result in extra zeroing occurring, and so if it is anything related to the filesystem, this is the likely culprit. Setting it to 4k sets it back to the default value used on older versions of Linux.... Cheers, Dave. -- Dave Chinner david@fromorbit.com From david@fromorbit.com Thu Mar 7 17:22:21 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 2B4707F98 for ; Thu, 7 Mar 2013 17:22:21 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay1.corp.sgi.com (Postfix) with ESMTP id 0A2CB8F8035 for ; Thu, 7 Mar 2013 15:22:17 -0800 (PST) X-ASG-Debug-ID: 1362698536-04cbb07dbc28f820001-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id ZmtqfIgI2CqLJNby for ; Thu, 07 Mar 2013 15:22:16 -0800 (PST) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AtgjAI4gOVF5LAvR/2dsb2JhbABDvz2FFgECAYFjF3SCLAEBBAE6HCMFCwgDGAklDwUlAyETiA0Fu04VjUcFKhgfSgeDQAOWSpBygx2BVg Received: from ppp121-44-11-209.lns20.syd6.internode.on.net (HELO dastard) ([121.44.11.209]) by ipmail05.adl6.internode.on.net with ESMTP; 08 Mar 2013 09:52:15 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UDk8c-0006ft-CQ; Fri, 08 Mar 2013 10:22:14 +1100 Date: Fri, 8 Mar 2013 10:22:14 +1100 From: Dave Chinner To: Julien FERRERO Cc: Ric Wheeler , xfs@oss.sgi.com Subject: Re: XFS filesystem corruption Message-ID: <20130307232214.GY23616@dastard> X-ASG-Orig-Subj: Re: XFS filesystem corruption References: <20130306161519.2c28d911@galadriel.home> <20130306232100.6286f640@galadriel.home> <5137CD46.6070909@redhat.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1362698536 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124554 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Thu, Mar 07, 2013 at 02:15:31PM +0100, Julien FERRERO wrote: > > We actually test brutal "Power off" for xfs, ext4 and other file systems. If > > your storage is configured properly and you have barriers enabled, they all > > pass without corruption. > > > > What hardware raid cards can do is to hide a volatile write cache. Either on > > the raid HBA itself or, even worse, on the backend disks behind the card. > > S-ata disks tend to default to write cache enabled and need to be checked > > especially careful (sas drives tend to be write cache disabled by default). > > Write cache is supposed to be disabled on the H/W RAID (according to > hdparm) and barrier are correctly enabled since xfs does not report > any warning at mount. > > The odd thing is we never see this with kernel 2.6.18 where barriers > weren't yet available. Yes they were. XFS had barrier support added in 2.6.15. > An other difference is the "unwritten extend" > that was used to set to 0 by default. Now we cannot change this > setting according to an old thread I've found: "unwritten extents on > linux are generally a bad idea, this option should not be used.". Yes, that would have been me that said that. I started seeing lots of boy-racer "tweak your filesystem to go faster" blogs recommending that unwritten extents should be turned off high up in google results, with numbers to prove that it improved performance. There were two common things wrong with these blogs: 1. None of them mentioned that turning off unwritten extents exposes stale data to users. i.e. a whopping great big security hole. 2. they reported significant performance improvements for workloads that *didn't use unwritten extents* when they set this flag. i.e. they mistook run-to-run variablity of the benchmark for a performance improvement. i.e. Benchmarking 101 Fail. When you get people who do not understand what they are doing and giving bad advice as the first 10 hits for a google search about optimising/tuning XFS filesystems, it's a major concern, and so I took steps to ensure you can't turn off unwritten extents with mkfs... > Unfortunately, the engineer that chose this setting is no longer > working with us... It sounds like he read one too many of these blogs, because if mysql is triggering speculative preallocation, it is not using unwritten extents.... Cheers, Dave. -- Dave Chinner david@fromorbit.com From athena@fftw.org Thu Mar 7 18:09:44 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id C52697FC4 for ; Thu, 7 Mar 2013 18:09:44 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay1.corp.sgi.com (Postfix) with ESMTP id A39F28F8059 for ; Thu, 7 Mar 2013 16:09:44 -0800 (PST) X-ASG-Debug-ID: 1362701380-04cb6c2b042847c0001-NocioJ Received: from fftw.org (216.119.142.145.static.a2webhosting.com [216.119.142.145]) by cuda.sgi.com with ESMTP id RVIFBpknJePV1VDq (version=TLSv1 cipher=AES128-SHA bits=128 verify=NO) for ; Thu, 07 Mar 2013 16:09:40 -0800 (PST) X-Barracuda-Envelope-From: athena@fftw.org X-Barracuda-Apparent-Source-IP: 216.119.142.145 Received: from c-24-62-102-245.hsd1.ma.comcast.net ([24.62.102.245] helo=amd) by fftw.org with esmtpsa (TLS1.2:DHE_RSA_AES_128_CBC_SHA1:128) (Exim 4.80) (envelope-from ) id 1UDksU-0001HP-6O; Thu, 07 Mar 2013 19:09:38 -0500 Received: from athena by amd with local (Exim 4.80) (envelope-from ) id 1UDksN-0008Ro-Rt; Thu, 07 Mar 2013 19:09:31 -0500 From: Matteo Frigo To: Dave Chinner Cc: dm-devel@redhat.com, xfs@oss.sgi.com Subject: Re: [dm-devel] [BUG] pvmove corrupting XFS filesystems (was Re: [BUG] Internal error xfs_dir2_data_reada_verify) References: <87d2vnc34r.fsf@fftw.org> <20130226044039.GM5551@dastard> <20130227010414.GD1514@agk.fab.redhat.com> <20130227014900.GY5551@dastard> <87y5eah4xz.fsf@fftw.org> <87k3pjs908.fsf@fftw.org> <20130307223140.GU23616@dastard> X-ASG-Orig-Subj: Re: [dm-devel] [BUG] pvmove corrupting XFS filesystems (was Re: [BUG] Internal error xfs_dir2_data_reada_verify) Date: Thu, 07 Mar 2013 19:09:31 -0500 In-Reply-To: <20130307223140.GU23616@dastard> (Dave Chinner's message of "Fri, 8 Mar 2013 09:31:40 +1100") Message-ID: <87hakmpxac.fsf@fftw.org> User-Agent: Gnus/5.13 (Gnus v5.13) Emacs/24.1 (gnu/linux) MIME-Version: 1.0 Content-Type: text/plain X-Barracuda-Connect: 216.119.142.145.static.a2webhosting.com[216.119.142.145] X-Barracuda-Start-Time: 1362701380 X-Barracuda-Encrypted: AES128-SHA X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124556 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- Dave Chinner writes: > You need the XFS patch I posted so that readahead buffer > verification is avoided in the case of an error being returned from > the readahead. I apologize if I was not clear in my previous post. I mean to say that returning -EIO from dm, even in conjunction with your patch, is not sufficient to fix the problem. Specifically, I repeated the experiment with v3.8.2 patched as discussed below, running my original script (repeated here for completeness): pvcreate /dev/vd[bc] vgcreate test /dev/vd[bc] lvcreate -L 8G -n vol test /dev/vdb mkfs.xfs -f /dev/mapper/test-vol mount -o noatime /dev/mapper/test-vol /mnt cd /mnt git clone ~/linux-stable cd / umount /mnt mount -o noatime /dev/mapper/test-vol /mnt pvmove -b /dev/vdb /dev/vdc sleep 2 rm -rf /mnt/linux-stable I obtained a string of errors that starts with this: [ 166.596574] XFS (dm-1): metadata I/O error: block 0x805060 ("xfs_trans_read_buf_map") error 5 numblks 8 [ 166.599556] XFS (dm-1): metadata I/O error: block 0x805060 ("xfs_trans_read_buf_map") error 5 numblks 8 [ 166.604845] XFS (dm-1): metadata I/O error: block 0x5285b8 ("xfs_trans_read_buf_map") error 5 numblks 8 [ 166.607894] XFS (dm-1): metadata I/O error: block 0x5285b8 ("xfs_trans_read_buf_map") error 5 numblks 8 [ 166.614242] XFS (dm-1): metadata I/O error: block 0x54f2b0 ("xfs_trans_read_buf_map") error 5 numblks 8 [ 166.617307] XFS (dm-1): metadata I/O error: block 0x54f2b0 ("xfs_trans_read_buf_map") error 5 numblks 8 [ 166.651373] XFS (dm-1): Corruption detected. Unmount and run xfs_repair [ 166.653517] XFS (dm-1): Corruption detected. Unmount and run xfs_repair [ 166.655545] XFS (dm-1): Corruption detected. Unmount and run xfs_repair [ 166.657614] XFS (dm-1): Corruption detected. Unmount and run xfs_repair [ 166.659685] XFS (dm-1): Corruption detected. Unmount and run xfs_repair [ 166.661731] XFS (dm-1): Corruption detected. Unmount and run xfs_repair [ 166.663761] XFS (dm-1): Corruption detected. Unmount and run xfs_repair I used v3.8.2 with the following diff, including both your xfs patch and my attempt to patch dm-raid1 to return EIO: diff --git a/drivers/md/dm-raid1.c b/drivers/md/dm-raid1.c index fa51918..88903e3 100644 --- a/drivers/md/dm-raid1.c +++ b/drivers/md/dm-raid1.c @@ -1169,7 +1169,7 @@ static int mirror_map(struct dm_target *ti, struct bio *bio) */ if (!r || (r == -EWOULDBLOCK)) { if (rw == READA) - return -EWOULDBLOCK; + return -EIO; queue_bio(ms, bio, rw); return DM_MAPIO_SUBMITTED; diff --git a/fs/xfs/xfs_buf.c b/fs/xfs/xfs_buf.c index fbbb9eb..c961dd4 100644 --- a/fs/xfs/xfs_buf.c +++ b/fs/xfs/xfs_buf.c @@ -1024,7 +1024,9 @@ xfs_buf_iodone_work( bool read = !!(bp->b_flags & XBF_READ); bp->b_flags &= ~(XBF_READ | XBF_WRITE | XBF_READ_AHEAD); - if (read && bp->b_ops) + + /* only validate buffers that were read without errors */ + if (read && bp->b_ops && !bp->b_error && (bp->b_flags & XBF_DONE)) bp->b_ops->verify_read(bp); if (bp->b_iodone) So your patch is not sufficient to fix the problem, even if dm returns -EIO instead of -EAGAIN. My question is, what is dm supposed to return? Regards, MF From david@fromorbit.com Thu Mar 7 19:35:34 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 829A87F77 for ; Thu, 7 Mar 2013 19:35:34 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay2.corp.sgi.com (Postfix) with ESMTP id 434D7304032 for ; Thu, 7 Mar 2013 17:35:31 -0800 (PST) X-ASG-Debug-ID: 1362706528-04bdf022962ac290001-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id guMWy5A8P1MThgkx for ; Thu, 07 Mar 2013 17:35:29 -0800 (PST) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AngZALc/OVF5LAvR/2dsb2JhbABEhz23eYUWAQIBgV4XdIIsAQEEATocIwULCAMOCgkMGQ8FJQMhExuHcgW7YxWNTCoYH0oHCoM2A5ZKkHKDHYFW Received: from ppp121-44-11-209.lns20.syd6.internode.on.net (HELO dastard) ([121.44.11.209]) by ipmail05.adl6.internode.on.net with ESMTP; 08 Mar 2013 12:05:27 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UDmDV-0006td-UC; Fri, 08 Mar 2013 12:35:25 +1100 Date: Fri, 8 Mar 2013 12:35:25 +1100 From: Dave Chinner To: Jan Kara Cc: xfs@oss.sgi.com Subject: Re: Pathological allocation pattern with direct IO Message-ID: <20130308013525.GZ23616@dastard> X-ASG-Orig-Subj: Re: Pathological allocation pattern with direct IO References: <20130306202210.GA1318@quack.suse.cz> <20130307050325.GS23616@dastard> <20130307102406.GA6723@quack.suse.cz> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <20130307102406.GA6723@quack.suse.cz> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1362706528 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124561 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Thu, Mar 07, 2013 at 11:24:06AM +0100, Jan Kara wrote: > On Thu 07-03-13 16:03:25, Dave Chinner wrote: > > On Wed, Mar 06, 2013 at 09:22:10PM +0100, Jan Kara wrote: > > > Hello, > > > > > > one of our customers has application that write large (tens of GB) files > > > using direct IO done in 16 MB chunks. They keep the fs around 80% full > > > deleting oldest files when they need to store new ones. Usually the file > > > can be stored in under 10 extents but from time to time a pathological case > > > is triggered and the file has few thousands extents (which naturally has > > > impact on performance). The customer actually uses 2.6.32-based kernel but > > > I reproduced the issue with 3.8.2 kernel as well. ..... > > > 1) We start allocating blocks for file. We want to allocate in the same AG > > > as the inode is. First we try exact allocation which fails so we try > > > XFS_ALLOCTYPE_NEAR_BNO allocation which finds large enough free extent > > > before the inode. So we start allocating 16 MB chunks from the end of that > > > free extent. From this moment on we are basically bound to continue > > > allocating backwards using XFS_ALLOCTYPE_NEAR_BNO allocation until we > > > exhaust the whole free extent. > > > > > > 2) Similar situation happens when we cannot further grow current extent but > > > there is large free space somewhere before this extent in the AG. > > > > > > So I was wondering is this known? Is XFS_ALLOCTYPE_NEAR_BNO so beneficial > > > it outweights pathological cases like the above? Or shouldn't it maybe be > > > disabled for larger files or for direct IO? > > > > Well known issue, first diagnosed about 15 years ago, IIRC. Simple > > solution: use extent size hints. > I thought someone must have hit it before. But I wasn't successful in > googling... I suggested using fallocate to the customer since they have a > good idea of the final file size in advance and in testing it gave better > results than extent size hints (plus it works for other filesystems as > well). Extent size hints have the advantage of being effective when the file size is not known ahead of time, or the application cannot be modified to do preallocation. And they can be applied immediately to any existing filesystem without needing downtime or code changes, so the problem can be mitigated immediately without impacting ongoing production.... > But really I was wondering about usefulness of XFS_ALLOCTYPE_NEAR_BNO > heuristic. Sure the seek time depends on the distance so if we are speaking > about allocating single extent then XFS_ALLOCTYPE_NEAR_BNO is useful but > once that strategy would allocate two or three consecutive extents you've > lost all the benefit and you would be better off if you started allocating > from the start of the free space. Sorry, I gave quick answer because I didn't have time yesterday to answer in depth. The thing is, this backwards allocation is a low level allocator primitive, and it's behaviour is supposed to find the nearest free extent to a target block number. What you are seeing is exactly the expected beahviour of XFS_ALLOCTYPE_NEAR_BNO. An because it is a low level primitive, it is not designed to take into account high level allocation requirements or do pattern detection. It just finds the nearest free extent to the target block number, and that happens to be at the end of a free extent when it is at a lower block number than the target being asked for. This allocator behaviour is desirable for metadata in btree format, because it means that the btree clusters locally around both sides of the parent object rather than spreading out over an entire AG with blocks getting further and further apart as free space on the ascending side of the inode gets used up. In this case, it's far better to keep seek distances short by maintaining locality to the parent object by allocating on the descending side of the object. And backwards seeks are handled pretty well by the XFS metadata code - it uses readahead in the btree/dirent traversals to allow the elevator to optimise the resultant IO when walking the metadata, and hence backwards seeks are not really a problem at all. For data, random write workloads into sparse files really want this behaviour as well as it results in physical locality of extents. The backwards allocation simply doesn't matter because the extents are being randomly accessed anyway, because physical locality ultimately determines random IO performance. Further, high end storage arrays are capable of detecting backwards read patterns and issue readahead for them, so this backwards allocation doesn't always result in measurable performance problems... Hence repeated backwards allocation is, in many cases, desirable behaviour, and in others it doesn't make any difference. And with it being easy to work around for the few cases where it is tripped over on aging filesystems, there hasn't been a great deal of need to change the behaviour. > Obviously we don't know the future in > advance but this resembles a classical problem from approximations > algorithms theory (rent-or-buy problem where renting corresponds to > allocating from the end of free space and taking the smaller cost while > buying corresponds to allocation from the beginning, taking the higher > cost, but expecting you won't have to pay anything in future). And the > theory of approximation algorithms tells us that once we pay for renting as > much as buying will cost us, then at that moment it is advantageous to buy > and that gives you 2-approximation algorithm (you can do even better - > factor 1.58 approximation - if you use randomization but I don't think we > want to go that way). Way too mathematical for me, because... > So from this I'd say that switching off > XFS_ALLOCTYPE_NEAR_BNO allocation once you've allocated 2-3 extents > backwards would work of better on average. .... common sense says that this is true. I haven't looked to solve this problem in the past 5 years because extent size hints are such a simple way of mitigating the problem. However, given that I know how this allocation code works whole lot better than I did 5 years ago, I think I can see an easy way to avoid this repeated backwards allocation pattern when extending files. What we have right now is this used space/free space layout with the allocation context prev/want when extending the file: free extent free extent +-----------------+ prev ...... +--------------+ +------+ +------+ want This is what we'll ask for as a XFS_ALLOCTYPE_THIS_BNO allocation, but that is going to fail because there is no free space at wantbno. This then falls back to XFS_ALLOCTYPE_NEAR_BNO with the same wantbno target, and it selects the free extent before prev. If we then we look at what is happening xfs_alloc_compute_diff(), we have wantbno > freebno, and wantbno > freeend, so we end up in either of these two cases: } else if (alignment > 1) { newbno1 = roundup(freeend - wantlen, alignment); if (newbno1 > freeend - wantlen && newbno1 - alignment >= freebno) newbno1 -= alignment; else if (newbno1 >= freeend) newbno1 = NULLAGBLOCK; } else newbno1 = freeend - wantlen; Either way, the resultant extent that is cut out of the free extent is this: free extent +-----------------+ prev +------+ +------+ +------+ want got And hence we end up in a backwards allocation pattern. After repeated iterations of this, we end up this a pattern like this: free extent +-----------------+ prev prev-1 prev-2 +------+------+------+ +------+ +------+ want got and so is likely to lead to an extended run of backwards allocation for sequential ascending offsets. So, we would need to detect this pattern in xfs_bmap_adjacent, where the wantbno is determined for EOF allocation. That's a bit complex - we'll need to do extent tree lookups because we need more information than we've got from the initial lookup. I do not want to get this information from the initial lookup and pass it up to xfs_bmap_adjacent() because we are already using lots of stack through this path and adding another 70-odd bytes for another couple of extent maps is not going to fly. So to detect backwards allocation, we'd have to take the CPU hit of doing another lookup and then analysing the results for backwards allocation. That can be done, but I'm wondering if we even need to detect this case... I suspect we don't even need to detect the backwards allocation pattern at all - if we are falling back from an XFS_ALLOCTYPE_THIS_BNO allocation, we know that the target cannot be allocated and so we *might* end up doing a backwards allocation. Hence I don't think it will not hurt at all to simply say "select the start of the next candidate free extent" for a file data allocations in this case. That would completely avoid needing to detect repeated backwards allocations and ensure that subsequent allocations after the backwards jump to the start of the large free extent then go forwards as intended... And because we only do XFS_ALLOCTYPE_THIS_BNO allocations on data allocations when extending file, adding such a flag won't affect random write or metadata allocation patterns.... So, once we've decided that backward allocation is possible, all we need to do is inform XFS_ALLOCTYPE_NEAR_BNO/xfs_alloc_compute_diff() to select the start of the free extent it finds rather than select the tail of it. That will mean that rather than consume the entire free extent in small chunks via backwards allocation, we'll do one large backwards step and then consume the free extent in the forwards direction instead. Cheers, Dave. -- Dave Chinner david@fromorbit.com From david@fromorbit.com Thu Mar 7 19:57:54 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id BDD6F7FD5 for ; Thu, 7 Mar 2013 19:57:54 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay3.corp.sgi.com (Postfix) with ESMTP id 49739AC001 for ; Thu, 7 Mar 2013 17:57:54 -0800 (PST) X-ASG-Debug-ID: 1362707871-04cb6c2b0228b6f0001-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id 65KGiHctchCpEbpt for ; Thu, 07 Mar 2013 17:57:52 -0800 (PST) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AngZABxEOVF5LAvR/2dsb2JhbABEhz23eYUWAQIBgV4XdIIsAQEFJxMcIxAIAw4HAwkaCw8FJQMhE4gSu2YVjXYYH0oHgl9hA5ZKiWeHC4FTgUo Received: from ppp121-44-11-209.lns20.syd6.internode.on.net (HELO dastard) ([121.44.11.209]) by ipmail05.adl6.internode.on.net with ESMTP; 08 Mar 2013 12:27:50 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UDmYl-0006vo-P7; Fri, 08 Mar 2013 12:57:23 +1100 Date: Fri, 8 Mar 2013 12:57:23 +1100 From: Dave Chinner To: Matteo Frigo Cc: dm-devel@redhat.com, xfs@oss.sgi.com Subject: Re: [dm-devel] [BUG] pvmove corrupting XFS filesystems (was Re: [BUG] Internal error xfs_dir2_data_reada_verify) Message-ID: <20130308015723.GA23616@dastard> X-ASG-Orig-Subj: Re: [dm-devel] [BUG] pvmove corrupting XFS filesystems (was Re: [BUG] Internal error xfs_dir2_data_reada_verify) References: <87d2vnc34r.fsf@fftw.org> <20130226044039.GM5551@dastard> <20130227010414.GD1514@agk.fab.redhat.com> <20130227014900.GY5551@dastard> <87y5eah4xz.fsf@fftw.org> <87k3pjs908.fsf@fftw.org> <20130307223140.GU23616@dastard> <87hakmpxac.fsf@fftw.org> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <87hakmpxac.fsf@fftw.org> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1362707871 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124563 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Thu, Mar 07, 2013 at 07:09:31PM -0500, Matteo Frigo wrote: > Dave Chinner writes: > > > You need the XFS patch I posted so that readahead buffer > > verification is avoided in the case of an error being returned from > > the readahead. > > I apologize if I was not clear in my previous post. I mean to say that > returning -EIO from dm, even in conjunction with your patch, is not > sufficient to fix the problem. > > Specifically, I repeated the experiment with v3.8.2 patched as discussed > below, running my original script (repeated here for completeness): > > pvcreate /dev/vd[bc] > vgcreate test /dev/vd[bc] > lvcreate -L 8G -n vol test /dev/vdb > mkfs.xfs -f /dev/mapper/test-vol > mount -o noatime /dev/mapper/test-vol /mnt > cd /mnt > git clone ~/linux-stable > cd / > umount /mnt > > mount -o noatime /dev/mapper/test-vol /mnt > pvmove -b /dev/vdb /dev/vdc > sleep 2 > rm -rf /mnt/linux-stable > > I obtained a string of errors that starts with this: > > [ 166.596574] XFS (dm-1): metadata I/O error: block 0x805060 ("xfs_trans_read_buf_map") error 5 numblks 8 > [ 166.599556] XFS (dm-1): metadata I/O error: block 0x805060 ("xfs_trans_read_buf_map") error 5 numblks 8 > [ 166.604845] XFS (dm-1): metadata I/O error: block 0x5285b8 ("xfs_trans_read_buf_map") error 5 numblks 8 > [ 166.607894] XFS (dm-1): metadata I/O error: block 0x5285b8 ("xfs_trans_read_buf_map") error 5 numblks 8 > [ 166.614242] XFS (dm-1): metadata I/O error: block 0x54f2b0 ("xfs_trans_read_buf_map") error 5 numblks 8 > [ 166.617307] XFS (dm-1): metadata I/O error: block 0x54f2b0 ("xfs_trans_read_buf_map") error 5 numblks 8 > [ 166.651373] XFS (dm-1): Corruption detected. Unmount and run xfs_repair > [ 166.653517] XFS (dm-1): Corruption detected. Unmount and run xfs_repair > [ 166.655545] XFS (dm-1): Corruption detected. Unmount and run xfs_repair > [ 166.657614] XFS (dm-1): Corruption detected. Unmount and run xfs_repair > [ 166.659685] XFS (dm-1): Corruption detected. Unmount and run xfs_repair > [ 166.661731] XFS (dm-1): Corruption detected. Unmount and run xfs_repair > [ 166.663761] XFS (dm-1): Corruption detected. Unmount and run xfs_repair Add the the patch below. If you still see errors, then they are real IO errors from the block device. Cheers, Dave. -- Dave Chinner david@fromorbit.com xfs: ensure we capture IO errors correctly From: Dave Chinner Failed buffer readahead can leave the buffer in the cache marked with an error. Most callers that then issue a subsequent read on the buffer do not zero the b_error field out, and so we may incorectly detect an error during IO completion due to the stale error value left on the buffer. Avoid this problem by zeroing the error before IO submission. This ensures that the only IO errors that are detected those captured from are those captured from bio submission or completion. Signed-off-by: Dave Chinner --- fs/xfs/xfs_buf.c | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/fs/xfs/xfs_buf.c b/fs/xfs/xfs_buf.c index 50eb603..82b70bd 100644 --- a/fs/xfs/xfs_buf.c +++ b/fs/xfs/xfs_buf.c @@ -1336,6 +1336,12 @@ _xfs_buf_ioapply( int size; int i; + /* + * Make sure we capture only current IO errors rather than stale errors + * left over from previous use of the buffer (e.g. failed readahead). + */ + bp->b_error = 0; + if (bp->b_flags & XBF_WRITE) { if (bp->b_flags & XBF_SYNCIO) rw = WRITE_SYNC; From dave@fromorbit.com Thu Mar 7 20:01:20 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 8F91B7FDA for ; Thu, 7 Mar 2013 20:01:20 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay2.corp.sgi.com (Postfix) with ESMTP id 7D3B6304059 for ; Thu, 7 Mar 2013 18:01:17 -0800 (PST) X-ASG-Debug-ID: 1362708075-04cb6c2b0228bae0001-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id gR7vku7IMTGMhF1P for ; Thu, 07 Mar 2013 18:01:16 -0800 (PST) X-Barracuda-Envelope-From: dave@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AgwKAHpFOVF5LAvR/2dsb2JhbABExEwDgV8XdIIsAS0vOxhqAzSIEpp1oG2OC4EegyoDpzyDHQ Received: from ppp121-44-11-209.lns20.syd6.internode.on.net (HELO dastard) ([121.44.11.209]) by ipmail05.adl6.internode.on.net with ESMTP; 08 Mar 2013 12:31:15 +1030 Received: from disappointment ([192.168.1.1]) by dastard with esmtp (Exim 4.76) (envelope-from ) id 1UDmcU-0006x5-PL for xfs@oss.sgi.com; Fri, 08 Mar 2013 13:01:14 +1100 Received: from dave by disappointment with local (Exim 4.80) (envelope-from ) id 1UDmcU-0003uH-GS for xfs@oss.sgi.com; Fri, 08 Mar 2013 13:01:14 +1100 From: Dave Chinner To: xfs@oss.sgi.com Subject: [PATCH] xfs: ensure we capture IO errors correctly Date: Fri, 8 Mar 2013 13:01:14 +1100 X-ASG-Orig-Subj: [PATCH] xfs: ensure we capture IO errors correctly Message-Id: <1362708074-14987-1-git-send-email-david@fromorbit.com> X-Mailer: git-send-email 1.7.10.4 X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1362708075 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124563 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- From: Dave Chinner Failed buffer readahead can leave the buffer in the cache marked with an error. Most callers that then issue a subsequent read on the buffer do not zero the b_error field out, and so we may incorectly detect an error during IO completion due to the stale error value left on the buffer. Avoid this problem by zeroing the error before IO submission. This ensures that the only IO errors that are detected those captured from are those captured from bio submission or completion. Signed-off-by: Dave Chinner --- fs/xfs/xfs_buf.c | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/fs/xfs/xfs_buf.c b/fs/xfs/xfs_buf.c index 50eb603..82b70bd 100644 --- a/fs/xfs/xfs_buf.c +++ b/fs/xfs/xfs_buf.c @@ -1336,6 +1336,12 @@ _xfs_buf_ioapply( int size; int i; + /* + * Make sure we capture only current IO errors rather than stale errors + * left over from previous use of the buffer (e.g. failed readahead). + */ + bp->b_error = 0; + if (bp->b_flags & XBF_WRITE) { if (bp->b_flags & XBF_SYNCIO) rw = WRITE_SYNC; -- 1.7.10.4 From stan@hardwarefreak.com Fri Mar 8 02:39:11 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id C06137F4C for ; Fri, 8 Mar 2013 02:39:11 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id A049A304066 for ; Fri, 8 Mar 2013 00:39:08 -0800 (PST) X-ASG-Debug-ID: 1362731947-04cbb07dbc2babb0001-NocioJ Received: from greer.hardwarefreak.com (mo-65-41-216-221.sta.embarqhsd.net [65.41.216.221]) by cuda.sgi.com with ESMTP id ZkZ6Miv3jYJkt92L for ; Fri, 08 Mar 2013 00:39:07 -0800 (PST) X-Barracuda-Envelope-From: stan@hardwarefreak.com X-Barracuda-Apparent-Source-IP: 65.41.216.221 X-Barracuda-User-Whitelist: xfs@oss.sgi.com Received: from [192.168.100.53] (gffx.hardwarefreak.com [192.168.100.53]) by greer.hardwarefreak.com (Postfix) with ESMTP id 1897D6C0AC; Fri, 8 Mar 2013 02:39:07 -0600 (CST) Message-ID: <5139A3B6.3040805@hardwarefreak.com> Date: Fri, 08 Mar 2013 02:39:18 -0600 From: Stan Hoeppner Reply-To: stan@hardwarefreak.com User-Agent: Mozilla/5.0 (Windows NT 5.1; rv:17.0) Gecko/20130215 Thunderbird/17.0.3 MIME-Version: 1.0 To: Ric Wheeler CC: Emmanuel Florac , Julien FERRERO , xfs@oss.sgi.com Subject: Re: XFS filesystem corruption References: <20130306161519.2c28d911@galadriel.home> <20130306232100.6286f640@galadriel.home> <5137CD46.6070909@redhat.com> X-ASG-Orig-Subj: Re: XFS filesystem corruption In-Reply-To: <5137CD46.6070909@redhat.com> Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: mo-65-41-216-221.sta.embarqhsd.net[65.41.216.221] X-Barracuda-Start-Time: 1362731947 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 On 3/6/2013 5:12 PM, Ric Wheeler wrote: > We actually test brutal "Power off" for xfs, ext4 and other file > systems. If your storage is configured properly and you have barriers > enabled, they all pass without corruption. Something that none of us mentioned WRT write barriers is that while the filesystem structure may avoid corruption when the power is cut, files may still be corrupted, in conditions such as any/all of these: 1. unwritten data still in buffer cache 2. drive caches are enabled 3. BBWC not working properly If the techs are determined to hard cut power because they don't have the time or the knowledge to do a clean shutdown, it may be well worth your time/effort to write a script and teach the field techs to execute it, before flipping the master switch. Your simple script would run as root, or you'd need to do some sudo foo within, and would contain something like: #! /bin/sh sync echo 2 > /proc/sys/vm/drop_caches echo "Ready for power down." This will flush pending writes in buffer cache to disk, and assumes of course that drive caches are disabled, and/or that BBWC, if present, is functioning properly. It also assumes no applications are still actively writing files, in which case you're screwed regardless. It's not a perfect solution and there's no guarantee you won't suffer file corruption, but this greatly increases your odds against it. -- Stan From dennis.kaarsemaker@booking.com Fri Mar 8 03:08:49 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=T_DKIM_INVALID autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id C21BE7FAA for ; Fri, 8 Mar 2013 03:08:49 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay3.corp.sgi.com (Postfix) with ESMTP id 1A048AC003 for ; Fri, 8 Mar 2013 01:08:45 -0800 (PST) X-ASG-Debug-ID: 1362733723-04cb6c2b012a6240001-NocioJ Received: from mail-out4.booking.com (mail-out4.booking.com [91.195.237.21]) by cuda.sgi.com with ESMTP id uCkuAaMcV0SdmkhM (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO) for ; Fri, 08 Mar 2013 01:08:44 -0800 (PST) X-Barracuda-Envelope-From: dennis.kaarsemaker@booking.com X-Barracuda-Apparent-Source-IP: 91.195.237.21 DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=booking.com; s=bk; h=Mime-Version:Content-Transfer-Encoding:Content-Type:References:In-Reply-To:Date:Cc:To:From:Subject:Message-ID; bh=ct+OXoM0duKIbN4Tj2Odk2NejoXVsbMUsKbB2qme6dw=; b=Nl/Kzm0Zf81MT9xX9wJ+VC/3vTbYEK5gIUbCOridOHfVgvYkZ98ne8+7toj3vJKycXtGNa4nMnkCjeLEWML6mxdzs+wMJGrJmkBa9NtT3YXAdPzpMJ4e9aqa4cz7kBduJHZtOif+9g4XplrZE4l8uIbrwS3YVvpoV3zpcvc//Z8=; Received: from corpds-102.ams4.corp.booking.com ([10.196.68.83]:40901) by mtx-102.ams4.prod.booking.com with esmtps (TLSv1:DHE-RSA-AES256-SHA:256) (Exim 4.80.1) (envelope-from ) id 1UDtIA-0001oZ-RP; Fri, 08 Mar 2013 10:08:42 +0100 Received: from [10.155.73.64] (port=36013) by corpds-102.ams4.corp.booking.com with esmtpsa (TLSv1:DHE-RSA-CAMELLIA256-SHA:256) (Exim 4.80.1) (envelope-from ) id 1UDtIA-0007XL-N7; Fri, 08 Mar 2013 10:08:42 +0100 Message-ID: <1362733748.20926.6.camel@seahawk> Subject: Re: XFS IO multiplication problem on centos/rhel 6 using hp p420i raid controllers From: Dennis Kaarsemaker X-ASG-Orig-Subj: Re: XFS IO multiplication problem on centos/rhel 6 using hp p420i raid controllers To: Dave Chinner Cc: xfs@oss.sgi.com Date: Fri, 08 Mar 2013 10:09:08 +0100 In-Reply-To: <20130307230020.GX23616@dastard> References: <1362060736.1247.30.camel@seahawk> <20130228194023.GQ5551@dastard> <1362577992.1247.84.camel@seahawk> <20130307035737.GC6369@dastard> <1362651128.16657.13.camel@seahawk> <20130307230020.GX23616@dastard> Organization: Booking.com Content-Type: text/plain; charset="UTF-8" X-Mailer: Evolution 3.2.3-0ubuntu6 Content-Transfer-Encoding: 7bit Mime-Version: 1.0 X-Barracuda-Connect: mail-out4.booking.com[91.195.237.21] X-Barracuda-Start-Time: 1362733724 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=DKIM_SIGNED, DKIM_VERIFIED X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124591 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature On Fri, 2013-03-08 at 10:00 +1100, Dave Chinner wrote: > On Thu, Mar 07, 2013 at 11:12:08AM +0100, Dennis Kaarsemaker wrote: > > On Thu, 2013-03-07 at 14:57 +1100, Dave Chinner wrote: > > > On Wed, Mar 06, 2013 at 02:53:12PM +0100, Dennis Kaarsemaker wrote: > .... > > > > #<----CPU[HYPER]-----><----------Disks-----------><----------Network----------> > > > > #cpu sys inter ctxsw KBRead Reads KBWrit Writes KBIn PktIn KBOut PktOut > > > > 1 0 1636 4219 16 1 2336 313 184 195 12 133 > > > > 1 0 1654 2804 64 3 2919 432 391 352 20 208 > > > > > > > > [root@bc291bprdb-01 ~]# collectl > > > > #<----CPU[HYPER]-----><----------Disks-----------><----------Network----------> > > > > #cpu sys inter ctxsw KBRead Reads KBWrit Writes KBIn PktIn KBOut PktOut > > > > 1 0 2220 3691 332 13 39992 331 112 122 6 92 > > > > 0 0 1354 2708 0 0 39836 335 103 125 9 99 > > > > 0 0 1563 3023 120 6 44036 369 399 317 13 188 > > > > > > > > Notice the KBWrit difference. These are two identical hp gen 8 machines, > > > > doing the same thing (replicating the same mysql schema). The one > > > > writing ten times as many bytes in the same amount of transactions is > > > > running centos 6 (and was running rhel 6). > > > > > > So what is the problem? it is writing too much on the on the centos > > > 6 machine? Either way, this doesn't sound like a filesystem problem > > > - the size and amount of data writes is entirely determined by the > > > application. > > > > For performing the same amount of work (processing the same mysql > > transactions, the same amount of IO transactions resulting from them), > > the 'broken' case writes ten-ish times as many bytes. > > Thanks for clarifying. > > > > > /dev/mapper/sysvm-mysqlVol /mysql/bp xfs rw,relatime,attr2,delaylog,allocsize=1024k,logbsize=256k,sunit=512,swidth=1536,noquota 0 0 > > > > > > What is the reason for using allocsize, sunit/swidth? Are you using > > > them on other machines? > > > > xfs autodetects them from the hpsa driver. They seem to be correct for > > the raid layout (256 strips, 3 drives per mirror pool) and I don't seem > > to be able to override them. > > That's fine, they're set correctly. I'd forgotten that the number > are emitted in /proc/mounts even when they are not specified as > mount options. > > > > And if you remove the allocsize mount option, does the behaviour on > > > centos6.3 change? What happens if you set allocsize=4k? > > > > The allocsize parameter has no effect. It was put in place to correct a > > monitoring issue: due to mysql's access patterns, using the default > > large allocsize on rhel 6 makes our monitoring report the filesystem as > > much fuller than it actually is. > > Which is due to speculative EOF preallocation, and so it is only set > on the CentOS box that is showing the larger write behaviour? Have > you tried setting it to 4k? If not, please do - EOF preallocation for > sparse extending writes can result in extra zeroing occurring, and > so if it is anything related to the filesystem, this is the likely > culprit. Setting it to 4k sets it back to the default value used > on older versions of Linux.... I've set it to 4k, but no change, though I haven't rebuilt the files yet with this setting (doing that as we speak, takes 90 minutes). I'm also wondering how this could cause the increasing bytes out as reported by vmstat, should zeroing do that? -- Dennis Kaarsemaker, Systems Architect Booking.com Herengracht 597, 1017 CE Amsterdam Tel external +31 (0) 20 715 3409 Tel internal (7207) 3409 From ole.tange.work@gmail.com Fri Mar 8 04:10:06 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=FREEMAIL_FROM,T_DKIM_INVALID autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 154B17FDF for ; Fri, 8 Mar 2013 04:10:06 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay3.corp.sgi.com (Postfix) with ESMTP id A4C51AC003 for ; Fri, 8 Mar 2013 02:10:02 -0800 (PST) X-ASG-Debug-ID: 1362737400-04bdf022952d1700001-NocioJ Received: from mail-pa0-f54.google.com (mail-pa0-f54.google.com [209.85.220.54]) by cuda.sgi.com with ESMTP id L82JRf6rLtovK2Y7 (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Fri, 08 Mar 2013 02:10:01 -0800 (PST) X-Barracuda-Envelope-From: ole.tange.work@gmail.com X-Barracuda-Apparent-Source-IP: 209.85.220.54 X-Barracuda-IPDD: Level1 [gmail.com/209.85.220.54] Received: by mail-pa0-f54.google.com with SMTP id fa10so1204454pad.27 for ; Fri, 08 Mar 2013 02:10:00 -0800 (PST) X-Barracuda-IPDD: Level1 [gmail.com/209.85.220.54] X-Barracuda-IPDD: Level1 [gmail.com/209.85.220.54] DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20120113; h=x-received:mime-version:sender:in-reply-to:references:from:date :x-google-sender-auth:message-id:subject:to:cc:content-type; bh=LZTXXx67E0G4rUoM3I6683aNEqTY7fLy7m9f0frb0fw=; b=w+R3G3l9UGdcn989/NWSyKIaT4EKVEvbXasI/YmlqAJJh6f0nYEKnuff1vfXnAIe1f kddvxnXwfcFJQreDoOgZF2wcU61DbT0NzCSJbpqUNeCRJZHmRb2Yryr0Npoi1H3PiwUZ W8Cz+/FC05EnCaFZ2QltgaCd1+bCFLtr4+vn9jnHQliRKeNjTIVYq9njb0x+GoeZIXZ2 O1lr5kSX2vOHrhjZ1s7ntki3+OcGaOEqQdKHDVxUg9aQ6s0dOQa7/GkQdhqXngwwO1lx t6dhB64MO931QkkfLc0euHg9o8PMDQyCv6mrepLQnRmfG1oxy218incQaaG/V1S1Q1zS CQ1w== X-Received: by 10.66.216.231 with SMTP id ot7mr3129788pac.155.1362737400812; Fri, 08 Mar 2013 02:10:00 -0800 (PST) MIME-Version: 1.0 Sender: ole.tange.work@gmail.com Received: by 10.68.7.9 with HTTP; Fri, 8 Mar 2013 02:09:40 -0800 (PST) In-Reply-To: <20130304232319.GR23616@dastard> References: <20130301111701.GB23616@dastard> <20130301205305.GD23616@dastard> <20130304232319.GR23616@dastard> From: Ole Tange Date: Fri, 8 Mar 2013 11:09:40 +0100 X-Google-Sender-Auth: qyImTszlE_qvR1GUwguG8gFKGzU Message-ID: Subject: Re: xfs_repair segfaults To: Dave Chinner X-ASG-Orig-Subj: Re: xfs_repair segfaults Cc: xfs@oss.sgi.com Content-Type: text/plain; charset=ISO-8859-1 X-Barracuda-Connect: mail-pa0-f54.google.com[209.85.220.54] X-Barracuda-Start-Time: 1362737401 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=DKIM_SIGNED, DKIM_VERIFIED X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124595 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature On Tue, Mar 5, 2013 at 12:23 AM, Dave Chinner wrote: > On Mon, Mar 04, 2013 at 10:03:29AM +0100, Ole Tange wrote: >> On Fri, Mar 1, 2013 at 9:53 PM, Dave Chinner wrote: >> : >> > What filesystem errors occurred >> > when the srives went offline? >> >> See http://dna.ku.dk/~tange/tmp/syslog.3 > > You log is full of this: > > mpt2sas1: log_info(0x31120303): originator(PL), code(0x12), sub_code(0x0303) > > What's that mean? We do not know, but it is something we are continually trying to find out. We have 5 other systems using the same setup and they experience the same. 1 of these 5 systems drop disks off the RAID but the rest work fine. In other words: we do not experience data corruption - only disk dropping of the RAID. That leads me to believe it is some kind of timeout error. >> Feb 26 00:46:52 franklin kernel: [556238.429259] XFS (md5p1): metadata >> I/O error: block 0x459b8 ("xfs_buf_iodone_callbacks") error 5 buf >> count 4096 > > So, the first IO errors appear at 23:00 on /dev/sdb, and the > controller does a full reset and reprobe. Look slike a port failure > of some kind. Notable: > > mpt2sas1: LSISAS2008: FWVersion(07.00.00.00), ChipRevision(0x03), BiosVersion(07.11.10.00) > > From a quick google, that firmware looks out of date (current > LSISAS2008 firmwares are numbered 10 or 11, and bios versions are at > 7.21). We have tried updating the firmware using LSIs own tool. That fails as LSI tools says the firmware is not signed correctly. > /dev/md4 had a failure (/dev/sds) around 00:19, no rebuild started. The rebuild of md4 is now complete. > /dev/md1 had another failure (/dev/sdj) around 00:46, this time on a > SYNCHRONISE CACHE command (i.e. log write). This IO failure caused > the shutdown to occur. And this is the result: > > [556219.292225] end_request: I/O error, dev sdj, sector 10 > [556219.292275] md: super_written gets error=-5, uptodate=0 > [556219.292283] md/raid:md1: Disk failure on sdj, disabling device. > [556219.292286] md/raid:md1: Operation continuing on 7 devices. > > At this point, /dev/md1 is reporting 7 working disks and has had an > EIO on it's superblock write, which means it's probably in an > inconsistent state. Further, it's only got 8 disks associated with > it and as a rebuild is in progress it means that data loss has > occurred with this failure. There's your problem. Yep. What I would like to see from xfs_repair is salvaging the part that is not affected - which ought to be the primary part of the 100 TB. > Essentially, you need to fix your hardware before you do anything > else. Get it all back fully online and fix whatever the problems are > that are causing IO errors, then you can worry about recovering the > filesystem and your data. Until the hardware is stable and not > throwing errors, recovery is going to be unreliable (if not > impossible). As that has been an ongoing effort it is unlikely to be solved within a short timeframe. /Ole From jferrero06@gmail.com Fri Mar 8 04:16:32 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.3 required=5.0 tests=FREEMAIL_ENVFROM_END_DIGIT, FREEMAIL_FROM,T_DKIM_INVALID autolearn=no version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 33E377FE1 for ; Fri, 8 Mar 2013 04:16:32 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay1.corp.sgi.com (Postfix) with ESMTP id 1E2678F8035 for ; Fri, 8 Mar 2013 02:16:32 -0800 (PST) X-ASG-Debug-ID: 1362737787-04cb6c2b032aad00001-NocioJ Received: from mail-qe0-f53.google.com (mail-qe0-f53.google.com [209.85.128.53]) by cuda.sgi.com with ESMTP id TJ1uBuChkuE0dyZa (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Fri, 08 Mar 2013 02:16:28 -0800 (PST) X-Barracuda-Envelope-From: jferrero06@gmail.com X-Barracuda-Apparent-Source-IP: 209.85.128.53 X-Barracuda-IPDD: Level1 [gmail.com/209.85.128.53] Received: by mail-qe0-f53.google.com with SMTP id cz11so891820qeb.12 for ; Fri, 08 Mar 2013 02:16:27 -0800 (PST) X-Barracuda-IPDD: Level1 [gmail.com/209.85.128.53] X-Barracuda-IPDD: Level1 [gmail.com/209.85.128.53] DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20120113; h=mime-version:x-received:in-reply-to:references:date:message-id :subject:from:to:cc:content-type; bh=9Te38zzIThv7dLXdDUDTl1O6I97UeoJSktKiQrgPHoQ=; b=O2OmYaNEvHyTWXngvMy6SKRnmlmJ2eN7yhgfn6hhEVEFl8BV5FeZPJL6PVCuhSXFbf r7pxkB7DsPZozcE/UfPuEp0Rg2NiHkj0mrTAHWMcL3m1YoUnUOF/5JfHU0hwFlwUIjde czS4tTTAdu+ZXl6HG5ql4yhH61V0rQfGrfzJv6H3rh3VVjXYzSGFyUjIq1skAubwrRxB /MMyb7od7O2pgne0MCcLna/l251xEVxLiYDE2BQUDDyWiSK/IUuPTCicIM3ECFvV0wYA 1iOxU7/xwMtzCFDFV6twweEETrDS3QkhtXEmCpn+IEzCTjHQX+jRnnbw6S7FVY5jUFuN nQ/g== MIME-Version: 1.0 X-Received: by 10.224.27.77 with SMTP id h13mr2997878qac.23.1362737787734; Fri, 08 Mar 2013 02:16:27 -0800 (PST) Received: by 10.49.13.10 with HTTP; Fri, 8 Mar 2013 02:16:27 -0800 (PST) In-Reply-To: <20130307232214.GY23616@dastard> References: <20130306161519.2c28d911@galadriel.home> <20130306232100.6286f640@galadriel.home> <5137CD46.6070909@redhat.com> <20130307232214.GY23616@dastard> Date: Fri, 8 Mar 2013 11:16:27 +0100 Message-ID: Subject: Re: XFS filesystem corruption From: Julien FERRERO X-ASG-Orig-Subj: Re: XFS filesystem corruption To: Dave Chinner Cc: Ric Wheeler , xfs@oss.sgi.com Content-Type: text/plain; charset=ISO-8859-1 X-Barracuda-Connect: mail-qe0-f53.google.com[209.85.128.53] X-Barracuda-Start-Time: 1362737788 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=DKIM_SIGNED, DKIM_VERIFIED X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124595 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature > > Yes they were. XFS had barrier support added in 2.6.15. > The XFS was running over a software RAID0 or software RAID5 depending on the product. In both case, my understanding is that either software RAID0 or software RAID5 did not support barrier in 2.6.18. > Yes, that would have been me that said that. I started seeing lots > of boy-racer "tweak your filesystem to go faster" blogs recommending > that unwritten extents should be turned off high up in google > results, with numbers to prove that it improved performance. > > There were two common things wrong with these blogs: > > 1. None of them mentioned that turning off unwritten extents > exposes stale data to users. i.e. a whopping great big > security hole. > > 2. they reported significant performance improvements for > workloads that *didn't use unwritten extents* when they set > this flag. i.e. they mistook run-to-run variablity of the > benchmark for a performance improvement. i.e. Benchmarking > 101 Fail. > > When you get people who do not understand what they are doing and > giving bad advice as the first 10 hits for a google search about > optimising/tuning XFS filesystems, it's a major concern, and so I > took steps to ensure you can't turn off unwritten extents with > mkfs... Thanks for the explanation. From jferrero06@gmail.com Fri Mar 8 04:17:44 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.3 required=5.0 tests=FREEMAIL_ENVFROM_END_DIGIT, FREEMAIL_FROM,T_DKIM_INVALID autolearn=no version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 5933C7FE7 for ; Fri, 8 Mar 2013 04:17:44 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id 4244B304066 for ; Fri, 8 Mar 2013 02:17:44 -0800 (PST) X-ASG-Debug-ID: 1362737863-04cbb07dbc2c3ce0001-NocioJ Received: from mail-qe0-f46.google.com (mail-qe0-f46.google.com [209.85.128.46]) by cuda.sgi.com with ESMTP id 1LHYr6IcyhCqBeKZ (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Fri, 08 Mar 2013 02:17:43 -0800 (PST) X-Barracuda-Envelope-From: jferrero06@gmail.com X-Barracuda-Apparent-Source-IP: 209.85.128.46 X-Barracuda-IPDD: Level1 [gmail.com/209.85.128.46] Received: by mail-qe0-f46.google.com with SMTP id a11so888981qen.33 for ; Fri, 08 Mar 2013 02:17:43 -0800 (PST) X-Barracuda-IPDD: Level1 [gmail.com/209.85.128.46] X-Barracuda-IPDD: Level1 [gmail.com/209.85.128.46] DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20120113; h=mime-version:x-received:in-reply-to:references:date:message-id :subject:from:to:cc:content-type; bh=hjg1ThwYW8WZCIwPFh1Dk4WQFMMawcBK9pE2jHdyUq8=; b=TkmV11p4Gf18BbZ8OtL1t9lIa5FlgrkYIzgh/WTITcvHNQB+9M+OJm/uxQmWRcsnRP xRxNkiN+yXkB5TTgkQra2v2HJWpGPGSsrdITHnA2ySINnhCRQ30g1w9R3jgbgn6vykVI wiqCY/h+W59bWCqU0soPkkZwfGyEq7JlRh/xDkzGBbnIjRw6QpZv2Hg7fdlW/Nuk0Ly1 y9xwAYLj3z7VCStzq2wWyPhw/qRB6ufXlpoeSLJ/I0dNyOlZ+5duiNbh5DrR89z5WikR roWtiIoBfxC3qvwt65cujjkQQd1a8I9mTS6UDp1CWf93/myv57F+YtpqvmTk3QAy/5tm /iXA== MIME-Version: 1.0 X-Received: by 10.224.27.77 with SMTP id h13mr3002574qac.23.1362737863013; Fri, 08 Mar 2013 02:17:43 -0800 (PST) Received: by 10.49.13.10 with HTTP; Fri, 8 Mar 2013 02:17:42 -0800 (PST) In-Reply-To: <5139A3B6.3040805@hardwarefreak.com> References: <20130306161519.2c28d911@galadriel.home> <20130306232100.6286f640@galadriel.home> <5137CD46.6070909@redhat.com> <5139A3B6.3040805@hardwarefreak.com> Date: Fri, 8 Mar 2013 11:17:42 +0100 Message-ID: Subject: Re: XFS filesystem corruption From: Julien FERRERO X-ASG-Orig-Subj: Re: XFS filesystem corruption To: stan@hardwarefreak.com Cc: Ric Wheeler , Emmanuel Florac , xfs@oss.sgi.com Content-Type: text/plain; charset=ISO-8859-1 X-Barracuda-Connect: mail-qe0-f46.google.com[209.85.128.46] X-Barracuda-Start-Time: 1362737863 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_MISMATCH_TO, DKIM_SIGNED, DKIM_VERIFIED X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124595 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 BSF_SC0_MISMATCH_TO Envelope rcpt doesn't match header -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature > Something that none of us mentioned WRT write barriers is that while the > filesystem structure may avoid corruption when the power is cut, files > may still be corrupted, in conditions such as any/all of these: > > 1. unwritten data still in buffer cache > 2. drive caches are enabled > 3. BBWC not working properly > > If the techs are determined to hard cut power because they don't have > the time or the knowledge to do a clean shutdown, it may be well worth > your time/effort to write a script and teach the field techs to execute > it, before flipping the master switch. Your simple script would run as > root, or you'd need to do some sudo foo within, and would contain > something like: > > #! /bin/sh > sync > echo 2 > /proc/sys/vm/drop_caches > echo "Ready for power down." > > This will flush pending writes in buffer cache to disk, and assumes of > course that drive caches are disabled, and/or that BBWC, if present, is > functioning properly. It also assumes no applications are still > actively writing files, in which case you're screwed regardless. It's > not a perfect solution and there's no guarantee you won't suffer file > corruption, but this greatly increases your odds against it. Thank you, that's the plan indeed. Educating our customer, and minimize failure with such script / recommendation. From ole.tange.work@gmail.com Fri Mar 8 04:21:21 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=FREEMAIL_FROM,T_DKIM_INVALID autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id A4F7D7FEC for ; Fri, 8 Mar 2013 04:21:21 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay1.corp.sgi.com (Postfix) with ESMTP id 859888F8033 for ; Fri, 8 Mar 2013 02:21:21 -0800 (PST) X-ASG-Debug-ID: 1362738080-04cbb07dbe2c41f0001-NocioJ Received: from mail-pa0-f44.google.com (mail-pa0-f44.google.com [209.85.220.44]) by cuda.sgi.com with ESMTP id IeZ55i2wZQYVhTlU (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Fri, 08 Mar 2013 02:21:20 -0800 (PST) X-Barracuda-Envelope-From: ole.tange.work@gmail.com X-Barracuda-Apparent-Source-IP: 209.85.220.44 X-Barracuda-IPDD: Level1 [gmail.com/209.85.220.44] Received: by mail-pa0-f44.google.com with SMTP id kp1so1218753pab.3 for ; Fri, 08 Mar 2013 02:21:20 -0800 (PST) X-Barracuda-IPDD: Level1 [gmail.com/209.85.220.44] X-Barracuda-IPDD: Level1 [gmail.com/209.85.220.44] DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20120113; h=x-received:mime-version:sender:in-reply-to:references:from:date :x-google-sender-auth:message-id:subject:to:cc:content-type; bh=Ax7MJHNdD+q3BVegMKTRIUOPbdsigQIDboQU83Fw3NI=; b=mLdbL+f7Bj3Fvho8ZB0ez2/pKjuz/Z6TDrEwtJcK0ywzW/r4Op/4y84u40K/Uyazzi 0goiHub1epd78MgaAfuaRwzYuNRQY+RtgDEuTv+sl6BYqZRoJov5rq2xwM6Xx9PPdVRt 4ySvk9CX5Nt1ElHpepr9+KBIpg8nrRVyXTbE8nIBhSqm+/d9KKILYtN1SIVtVbkGGJ0S 3SKRHr0xhY3WX5qLBGyLbmj9ZjZTLj+00Gy3S8boJ5sUmyHstfp4TOkSaQ7Rr2BXy0Rl kEb12f5yLQ7hHaXyZsAFMt8ny7oNjD5T2MeZe6jsDFfq+3PjnMCKj5k+H8fGhbIGcdm/ ZlgA== X-Received: by 10.68.7.163 with SMTP id k3mr2404486pba.141.1362738080091; Fri, 08 Mar 2013 02:21:20 -0800 (PST) MIME-Version: 1.0 Sender: ole.tange.work@gmail.com Received: by 10.68.7.9 with HTTP; Fri, 8 Mar 2013 02:21:00 -0800 (PST) In-Reply-To: <5134BBA4.3060305@sandeen.net> References: <512FA67D.2090708@sandeen.net> <5130DB54.9030503@sandeen.net> <5134BBA4.3060305@sandeen.net> From: Ole Tange Date: Fri, 8 Mar 2013 11:21:00 +0100 X-Google-Sender-Auth: Ye1YKasTzwQEsXd1E807hG4N178 Message-ID: Subject: Re: xfs_repair segfaults To: Eric Sandeen X-ASG-Orig-Subj: Re: xfs_repair segfaults Cc: xfs@oss.sgi.com Content-Type: text/plain; charset=ISO-8859-1 X-Barracuda-Connect: mail-pa0-f44.google.com[209.85.220.44] X-Barracuda-Start-Time: 1362738080 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=DKIM_SIGNED, DKIM_VERIFIED X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124597 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature On Mon, Mar 4, 2013 at 4:20 PM, Eric Sandeen wrote: > 2) so you could run a "real" non-"n" xfs_repair on a metadata image as a more realistic dry run I have now done a 'xfs_repair' using the code in GIT. It failed, and I then did 'xfs_repair -L' which succeeded. Am I correct that I should now be able to mount the sparse disk-image file and see all the filenames? In that case I am quite worried. I get filenames like: /mnt/disk/??5?z+hEOgl/?7?Psr1?aIHS??+??z=ozK/8_0/???d) 5JCG?eiBd?EVsNF'A?v?m?f;Fi6v)d>/?M%?A??J?)B X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 010227FDA for ; Fri, 8 Mar 2013 05:39:16 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay3.corp.sgi.com (Postfix) with ESMTP id 80911AC003 for ; Fri, 8 Mar 2013 03:39:12 -0800 (PST) X-ASG-Debug-ID: 1362742751-04cbb07dbf2cb130001-NocioJ Received: from fftw.org (216.119.142.145.static.a2webhosting.com [216.119.142.145]) by cuda.sgi.com with ESMTP id yFg3EeuKU3C8siQZ (version=TLSv1 cipher=AES128-SHA bits=128 verify=NO) for ; Fri, 08 Mar 2013 03:39:11 -0800 (PST) X-Barracuda-Envelope-From: athena@fftw.org X-Barracuda-Apparent-Source-IP: 216.119.142.145 Received: from c-24-62-102-245.hsd1.ma.comcast.net ([24.62.102.245] helo=amd) by fftw.org with esmtpsa (TLS1.2:DHE_RSA_AES_128_CBC_SHA1:128) (Exim 4.80) (envelope-from ) id 1UDvdk-0003Fb-2L; Fri, 08 Mar 2013 06:39:09 -0500 Received: from athena by amd with local (Exim 4.80) (envelope-from ) id 1UDvdY-0002ef-Jc; Fri, 08 Mar 2013 06:38:56 -0500 From: Matteo Frigo To: Dave Chinner Cc: dm-devel@redhat.com, xfs@oss.sgi.com Subject: Re: [dm-devel] [BUG] pvmove corrupting XFS filesystems (was Re: [BUG] Internal error xfs_dir2_data_reada_verify) References: <87d2vnc34r.fsf@fftw.org> <20130226044039.GM5551@dastard> <20130227010414.GD1514@agk.fab.redhat.com> <20130227014900.GY5551@dastard> <87y5eah4xz.fsf@fftw.org> <87k3pjs908.fsf@fftw.org> <20130307223140.GU23616@dastard> <87hakmpxac.fsf@fftw.org> <20130308015723.GA23616@dastard> X-ASG-Orig-Subj: Re: [dm-devel] [BUG] pvmove corrupting XFS filesystems (was Re: [BUG] Internal error xfs_dir2_data_reada_verify) Date: Fri, 08 Mar 2013 06:38:56 -0500 In-Reply-To: <20130308015723.GA23616@dastard> (Dave Chinner's message of "Fri, 8 Mar 2013 12:57:23 +1100") Message-ID: <87ppza5df3.fsf@fftw.org> User-Agent: Gnus/5.13 (Gnus v5.13) Emacs/24.1 (gnu/linux) MIME-Version: 1.0 Content-Type: text/plain X-Barracuda-Connect: 216.119.142.145.static.a2webhosting.com[216.119.142.145] X-Barracuda-Start-Time: 1362742751 X-Barracuda-Encrypted: AES128-SHA X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124601 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- Dave Chinner writes: > Add the the patch below. If you still see errors, then they are real > IO errors from the block device. This patch fixes the problem for me. The patch works both when dm-raid1 returns -EIO and when it returns -EWOULDBLOCK. Thanks for your help. Cheers, Matteo From dennis.kaarsemaker@booking.com Fri Mar 8 05:48:39 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=T_DKIM_INVALID autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 75BA57FDF for ; Fri, 8 Mar 2013 05:48:39 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay3.corp.sgi.com (Postfix) with ESMTP id F3BF1AC003 for ; Fri, 8 Mar 2013 03:48:38 -0800 (PST) X-ASG-Debug-ID: 1362743315-04cbb07dbe2cbb60001-NocioJ Received: from mail-out2.booking.com (mail-out2.booking.com [62.190.24.21]) by cuda.sgi.com with ESMTP id tmdBEoKjXdmxBNCV (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO) for ; Fri, 08 Mar 2013 03:48:37 -0800 (PST) X-Barracuda-Envelope-From: dennis.kaarsemaker@booking.com X-Barracuda-Apparent-Source-IP: 62.190.24.21 DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=booking.com; s=bk; h=Mime-Version:Content-Transfer-Encoding:Content-Type:References:In-Reply-To:Date:Cc:To:From:Subject:Message-ID; bh=lFIUVizvh9Gh1gKxAOXPvxr0xazVi+PWYvFNUtkE7Is=; b=YwNPXWQy6O/Anwsn+Uh75MIjAdFmmJqDUuU3SF99pynXxxseAWs0+q+ZpPqhEeoXIn/xYYCRijK9buL9YmYmfH3062n/wtsuSqYq7GH4J+eiSBQwRIP0Z90DkUk6dSGeXVt9IDlYChJdMKL9ZMt+ezqwvFIyyDiPSVC0kcvC2oo=; Received: from corpds-202.lhr4.corp.booking.com ([10.186.68.14]:55198) by mtx-06.prod.lhr1.booking.com with esmtps (TLSv1:DHE-RSA-AES256-SHA:256) (Exim 4.80.1) (envelope-from ) id 1UDvmt-0000MX-9g; Fri, 08 Mar 2013 12:48:35 +0100 Received: from [10.155.73.64] (port=60085) by corpds-202.lhr4.corp.booking.com with esmtpsa (TLSv1:DHE-RSA-CAMELLIA256-SHA:256) (Exim 4.80.1) (envelope-from ) id 1UDvmt-0007yq-4D; Fri, 08 Mar 2013 12:48:35 +0100 Message-ID: <1362743340.20926.15.camel@seahawk> Subject: Re: XFS IO multiplication problem on centos/rhel 6 using hp p420i raid controllers From: Dennis Kaarsemaker X-ASG-Orig-Subj: Re: XFS IO multiplication problem on centos/rhel 6 using hp p420i raid controllers To: Dave Chinner Cc: xfs@oss.sgi.com Date: Fri, 08 Mar 2013 12:49:00 +0100 In-Reply-To: <1362733748.20926.6.camel@seahawk> References: <1362060736.1247.30.camel@seahawk> <20130228194023.GQ5551@dastard> <1362577992.1247.84.camel@seahawk> <20130307035737.GC6369@dastard> <1362651128.16657.13.camel@seahawk> <20130307230020.GX23616@dastard> <1362733748.20926.6.camel@seahawk> Organization: Booking.com Content-Type: text/plain; charset="UTF-8" X-Mailer: Evolution 3.2.3-0ubuntu6 Content-Transfer-Encoding: 7bit Mime-Version: 1.0 X-Barracuda-Connect: mail-out2.booking.com[62.190.24.21] X-Barracuda-Start-Time: 1362743316 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=DKIM_SIGNED, DKIM_VERIFIED X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124603 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature On Fri, 2013-03-08 at 10:09 +0100, Dennis Kaarsemaker wrote: > On Fri, 2013-03-08 at 10:00 +1100, Dave Chinner wrote: > > On Thu, Mar 07, 2013 at 11:12:08AM +0100, Dennis Kaarsemaker wrote: > > > On Thu, 2013-03-07 at 14:57 +1100, Dave Chinner wrote: > > > > On Wed, Mar 06, 2013 at 02:53:12PM +0100, Dennis Kaarsemaker wrote: > > .... > > > > > #<----CPU[HYPER]-----><----------Disks-----------><----------Network----------> > > > > > #cpu sys inter ctxsw KBRead Reads KBWrit Writes KBIn PktIn KBOut PktOut > > > > > 1 0 1636 4219 16 1 2336 313 184 195 12 133 > > > > > 1 0 1654 2804 64 3 2919 432 391 352 20 208 > > > > > > > > > > [root@bc291bprdb-01 ~]# collectl > > > > > #<----CPU[HYPER]-----><----------Disks-----------><----------Network----------> > > > > > #cpu sys inter ctxsw KBRead Reads KBWrit Writes KBIn PktIn KBOut PktOut > > > > > 1 0 2220 3691 332 13 39992 331 112 122 6 92 > > > > > 0 0 1354 2708 0 0 39836 335 103 125 9 99 > > > > > 0 0 1563 3023 120 6 44036 369 399 317 13 188 > > > > > > > > > > Notice the KBWrit difference. These are two identical hp gen 8 machines, > > > > > doing the same thing (replicating the same mysql schema). The one > > > > > writing ten times as many bytes in the same amount of transactions is > > > > > running centos 6 (and was running rhel 6). > > > > > > > > So what is the problem? it is writing too much on the on the centos > > > > 6 machine? Either way, this doesn't sound like a filesystem problem > > > > - the size and amount of data writes is entirely determined by the > > > > application. > > > > > > For performing the same amount of work (processing the same mysql > > > transactions, the same amount of IO transactions resulting from them), > > > the 'broken' case writes ten-ish times as many bytes. > > > > Thanks for clarifying. > > > > > > > /dev/mapper/sysvm-mysqlVol /mysql/bp xfs rw,relatime,attr2,delaylog,allocsize=1024k,logbsize=256k,sunit=512,swidth=1536,noquota 0 0 > > > > > > > > What is the reason for using allocsize, sunit/swidth? Are you using > > > > them on other machines? > > > > > > xfs autodetects them from the hpsa driver. They seem to be correct for > > > the raid layout (256 strips, 3 drives per mirror pool) and I don't seem > > > to be able to override them. > > > > That's fine, they're set correctly. I'd forgotten that the number > > are emitted in /proc/mounts even when they are not specified as > > mount options. > > > > > > And if you remove the allocsize mount option, does the behaviour on > > > > centos6.3 change? What happens if you set allocsize=4k? > > > > > > The allocsize parameter has no effect. It was put in place to correct a > > > monitoring issue: due to mysql's access patterns, using the default > > > large allocsize on rhel 6 makes our monitoring report the filesystem as > > > much fuller than it actually is. > > > > Which is due to speculative EOF preallocation, and so it is only set > > on the CentOS box that is showing the larger write behaviour? Have > > you tried setting it to 4k? If not, please do - EOF preallocation for > > sparse extending writes can result in extra zeroing occurring, and > > so if it is anything related to the filesystem, this is the likely > > culprit. Setting it to 4k sets it back to the default value used > > on older versions of Linux.... > > I've set it to 4k, but no change, though I haven't rebuilt the files yet > with this setting (doing that as we speak, takes 90 minutes). I'm also > wondering how this could cause the increasing bytes out as reported by > vmstat, should zeroing do that? Unfortunately, even on a rebuilt filesystem, the symptoms did not change. -- Dennis Kaarsemaker, Systems Architect Booking.com Herengracht 597, 1017 CE Amsterdam Tel external +31 (0) 20 715 3409 Tel internal (7207) 3409 From rwheeler@redhat.com Fri Mar 8 06:20:48 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 1E83B7F4C for ; Fri, 8 Mar 2013 06:20:48 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay1.corp.sgi.com (Postfix) with ESMTP id 053048F8033 for ; Fri, 8 Mar 2013 04:20:44 -0800 (PST) X-ASG-Debug-ID: 1362745241-04cb6c2b032b45d0001-NocioJ Received: from mx1.redhat.com (mx1.redhat.com [209.132.183.28]) by cuda.sgi.com with ESMTP id DpTDzSgFibME4zz7 for ; Fri, 08 Mar 2013 04:20:41 -0800 (PST) X-Barracuda-Envelope-From: rwheeler@redhat.com X-Barracuda-Apparent-Source-IP: 209.132.183.28 X-ASG-Whitelist: Client Received: from int-mx02.intmail.prod.int.phx2.redhat.com (int-mx02.intmail.prod.int.phx2.redhat.com [10.5.11.12]) by mx1.redhat.com (8.14.4/8.14.4) with ESMTP id r28CKbHD016230 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=OK); Fri, 8 Mar 2013 07:20:37 -0500 Received: from tunkums.home (ovpn-112-33.phx2.redhat.com [10.3.112.33]) by int-mx02.intmail.prod.int.phx2.redhat.com (8.13.8/8.13.8) with ESMTP id r28CKYFg009366; Fri, 8 Mar 2013 07:20:35 -0500 Message-ID: <5139D792.4090304@redhat.com> Date: Fri, 08 Mar 2013 07:20:34 -0500 From: Ric Wheeler User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:17.0) Gecko/20130219 Thunderbird/17.0.3 MIME-Version: 1.0 To: stan@hardwarefreak.com CC: Emmanuel Florac , Julien FERRERO , xfs@oss.sgi.com Subject: Re: XFS filesystem corruption References: <20130306161519.2c28d911@galadriel.home> <20130306232100.6286f640@galadriel.home> <5137CD46.6070909@redhat.com> <5139A3B6.3040805@hardwarefreak.com> X-ASG-Orig-Subj: Re: XFS filesystem corruption In-Reply-To: <5139A3B6.3040805@hardwarefreak.com> Content-Type: text/plain; charset=ISO-8859-1; format=flowed Content-Transfer-Encoding: 7bit X-Scanned-By: MIMEDefang 2.67 on 10.5.11.12 X-Barracuda-Connect: mx1.redhat.com[209.132.183.28] X-Barracuda-Start-Time: 1362745241 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 On 03/08/2013 03:39 AM, Stan Hoeppner wrote: > On 3/6/2013 5:12 PM, Ric Wheeler wrote: > >> We actually test brutal "Power off" for xfs, ext4 and other file >> systems. If your storage is configured properly and you have barriers >> enabled, they all pass without corruption. > Something that none of us mentioned WRT write barriers is that while the > filesystem structure may avoid corruption when the power is cut, files > may still be corrupted, in conditions such as any/all of these: > > 1. unwritten data still in buffer cache This is true only for user data, not the file system metadata. We should always be able to drop power without seeing corruption (like the garbled ls output). > 2. drive caches are enabled Write barriers will take care of drives with write cache enabled, as long as the hardware RAID card is not in the middle and misleading us. > 3. BBWC not working properly This should not be a worry. If the battery (or in more modern cards, flash backed) is not working, a good card will flip into write through caching. Should be slow, but safe. Note that the write cache state on the drives is still a question mark - that needs to be disabled normally. > > If the techs are determined to hard cut power because they don't have > the time or the knowledge to do a clean shutdown, it may be well worth > your time/effort to write a script and teach the field techs to execute > it, before flipping the master switch. Your simple script would run as > root, or you'd need to do some sudo foo within, and would contain > something like: > > #! /bin/sh > sync > echo 2 > /proc/sys/vm/drop_caches > echo "Ready for power down." > > This will flush pending writes in buffer cache to disk, and assumes of > course that drive caches are disabled, and/or that BBWC, if present, is > functioning properly. It also assumes no applications are still > actively writing files, in which case you're screwed regardless. It's > not a perfect solution and there's no guarantee you won't suffer file > corruption, but this greatly increases your odds against it. > For file system *metadata* consistency, you should not have to do this ever if the stack is properly configured. The application data will still be lost. Also, if there are active writers, this is inherently racy. A better script would unmount the file systems :) Ric From hpj@urpla.net Fri Mar 8 07:07:12 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 2A7777FD0 for ; Fri, 8 Mar 2013 07:07:12 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay3.corp.sgi.com (Postfix) with ESMTP id BB2ACAC003 for ; Fri, 8 Mar 2013 05:07:11 -0800 (PST) X-ASG-Debug-ID: 1362748025-04bdf022962e3d60001-NocioJ Received: from moutng.kundenserver.de (moutng.kundenserver.de [212.227.17.9]) by cuda.sgi.com with ESMTP id B7PpdDJxrBb9kkF4 (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Fri, 08 Mar 2013 05:07:07 -0800 (PST) X-Barracuda-Envelope-From: hpj@urpla.net X-Barracuda-Apparent-Source-IP: 212.227.17.9 Received: from lisa (p5B2A479D.dip0.t-ipconnect.de [91.42.71.157]) by mrelayeu.kundenserver.de (node=mrbap1) with ESMTP (Nemesis) id 0M4khh-1UynX21eLl-00yn93; Fri, 08 Mar 2013 14:07:05 +0100 Received: from localhost (localhost [127.0.0.1]) by tyrex.lisa.loc (Postfix) with ESMTP id 19D631B971B00 for ; Fri, 8 Mar 2013 14:07:01 +0100 (CET) X-Virus-Scanned: amavisd-new at lisa.loc Received: from tyrex.lisa.loc ([127.0.0.1]) by localhost (tyrex.lisa.loc [127.0.0.1]) (amavisd-new, port 10024) with LMTP id jofqQcjkj2wJ for ; Fri, 8 Mar 2013 14:06:52 +0100 (CET) From: Hans-Peter Jansen To: xfs@oss.sgi.com Subject: Re: [PATCH] xfs: ensure we capture IO errors correctly Date: Fri, 08 Mar 2013 14:06:52 +0100 X-ASG-Orig-Subj: Re: [PATCH] xfs: ensure we capture IO errors correctly Message-ID: <1407262.RNsTtTSyZy@xrated> User-Agent: KMail/4.9.5 (Linux/3.4.28-2.20-desktop; KDE/4.9.5; x86_64; ; ) In-Reply-To: <1362708074-14987-1-git-send-email-david@fromorbit.com> References: <1362708074-14987-1-git-send-email-david@fromorbit.com> MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable Content-Type: text/plain; charset="iso-8859-1" X-Provags-ID: V02:K0:H2tvvMbM0RZm/QQ9kNFwycITUg+jgPIBvVHq1FlwVLO AHuTDZ1MgWjlybU0LpJWS+1VJSjkDBgMbMECaXWDiPkNbLXt78 G2++GAAUliAh9QMn56ESx93OBcvKypNjlmkyB7hP3vJN/p9aLk 2Xakx26cowjvD7JkMTGTmMWP5hh/ooKWx7cMJDC/oyW1w3NFsk Tff2+ETXbmeNlzL9Vjk5Is8XAWAWcOa6Lya9xkOOfJLq34UMBf zt0n2+yINnvUfXqjMWjAvNkiDiIHZTb70nhvcgfimnx+dcEwPj cRb+ehjPb1LHNP3hG5FMr35xoifBUCMiDcQvtfsDbESqX/8Mw= = X-Barracuda-Connect: moutng.kundenserver.de[212.227.17.9] X-Barracuda-Start-Time: 1362748026 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124607 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- Hi,=20 this sounds like stable material after a little simmering.. Cheers, Pete Am Freitag, 8. M=E4rz 2013, 13:01:14 schrieb Dave Chinner: > From: Dave Chinner >=20 > Failed buffer readahead can leave the buffer in the cache marked > with an error. Most callers that then issue a subsequent read on the > buffer do not zero the b_error field out, and so we may incorectly > detect an error during IO completion due to the stale error value > left on the buffer. >=20 > Avoid this problem by zeroing the error before IO submission. This > ensures that the only IO errors that are detected those captured > from are those captured from bio submission or completion. >=20 > Signed-off-by: Dave Chinner > --- > fs/xfs/xfs_buf.c | 6 ++++++ > 1 file changed, 6 insertions(+) >=20 > diff --git a/fs/xfs/xfs_buf.c b/fs/xfs/xfs_buf.c > index 50eb603..82b70bd 100644 > --- a/fs/xfs/xfs_buf.c > +++ b/fs/xfs/xfs_buf.c > @@ -1336,6 +1336,12 @@ _xfs_buf_ioapply( > =09int=09=09size; > =09int=09=09i; >=20 > +=09/* > +=09 * Make sure we capture only current IO errors rather than stale = errors > +=09 * left over from previous use of the buffer (e.g. failed readahe= ad). > +=09 */ > +=09bp->b_error =3D 0; > + > =09if (bp->b_flags & XBF_WRITE) { > =09=09if (bp->b_flags & XBF_SYNCIO) > =09=09=09rw =3D WRITE_SYNC; From stan@hardwarefreak.com Fri Mar 8 12:59:11 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id EC1597F95 for ; Fri, 8 Mar 2013 12:59:11 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay2.corp.sgi.com (Postfix) with ESMTP id D75B7304048 for ; Fri, 8 Mar 2013 10:59:11 -0800 (PST) X-ASG-Debug-ID: 1362769150-04cb6c2b032dc120001-NocioJ Received: from greer.hardwarefreak.com (mo-65-41-216-221.sta.embarqhsd.net [65.41.216.221]) by cuda.sgi.com with ESMTP id oJ7V6WtTdznQoWaM for ; Fri, 08 Mar 2013 10:59:11 -0800 (PST) X-Barracuda-Envelope-From: stan@hardwarefreak.com X-Barracuda-Apparent-Source-IP: 65.41.216.221 X-Barracuda-User-Whitelist: xfs@oss.sgi.com Received: from [192.168.100.53] (gffx.hardwarefreak.com [192.168.100.53]) by greer.hardwarefreak.com (Postfix) with ESMTP id AFA0C6C150; Fri, 8 Mar 2013 12:59:10 -0600 (CST) Message-ID: <513A350A.508@hardwarefreak.com> Date: Fri, 08 Mar 2013 12:59:22 -0600 From: Stan Hoeppner Reply-To: stan@hardwarefreak.com User-Agent: Mozilla/5.0 (Windows NT 5.1; rv:17.0) Gecko/20130215 Thunderbird/17.0.3 MIME-Version: 1.0 To: Ric Wheeler CC: Emmanuel Florac , Julien FERRERO , xfs@oss.sgi.com Subject: Re: XFS filesystem corruption References: <20130306161519.2c28d911@galadriel.home> <20130306232100.6286f640@galadriel.home> <5137CD46.6070909@redhat.com> <5139A3B6.3040805@hardwarefreak.com> <5139D792.4090304@redhat.com> X-ASG-Orig-Subj: Re: XFS filesystem corruption In-Reply-To: <5139D792.4090304@redhat.com> Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: mo-65-41-216-221.sta.embarqhsd.net[65.41.216.221] X-Barracuda-Start-Time: 1362769151 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 On 3/8/2013 6:20 AM, Ric Wheeler wrote: > On 03/08/2013 03:39 AM, Stan Hoeppner wrote: >> On 3/6/2013 5:12 PM, Ric Wheeler wrote: >> >>> We actually test brutal "Power off" for xfs, ext4 and other file >>> systems. If your storage is configured properly and you have barriers >>> enabled, they all pass without corruption. I think you missed the context. Please reread this: >> Something that none of us mentioned WRT write barriers is that while the >> filesystem structure may avoid corruption when the power is cut, files >> may still be corrupted, in conditions such as any/all of these: I made it very clear I was discussing file corruption here, not filesystem corruption. You already covered that base. I was specifically addressing the fact that XFS performs barriers on metadata writes but not file data writes. >> 1. unwritten data still in buffer cache > > This is true only for user data, not the file system metadata. We should > always be able to drop power without seeing corruption (like the garbled > ls output). > >> 2. drive caches are enabled > > Write barriers will take care of drives with write cache enabled, as > long as the hardware RAID card is not in the middle and misleading us. > >> 3. BBWC not working properly > > This should not be a worry. If the battery (or in more modern cards, > flash backed) is not working, a good card will flip into write through > caching. Should be slow, but safe. > > Note that the write cache state on the drives is still a question mark - > that needs to be disabled normally. > >> >> If the techs are determined to hard cut power because they don't have >> the time or the knowledge to do a clean shutdown, it may be well worth >> your time/effort to write a script and teach the field techs to execute >> it, before flipping the master switch. Your simple script would run as >> root, or you'd need to do some sudo foo within, and would contain >> something like: >> >> #! /bin/sh >> sync >> echo 2 > /proc/sys/vm/drop_caches >> echo "Ready for power down." >> >> This will flush pending writes in buffer cache to disk, and assumes of >> course that drive caches are disabled, and/or that BBWC, if present, is >> functioning properly. It also assumes no applications are still >> actively writing files, in which case you're screwed regardless. It's >> not a perfect solution and there's no guarantee you won't suffer file >> corruption, but this greatly increases your odds against it. >> > > For file system *metadata* consistency, you should not have to do this > ever if the stack is properly configured. The application data will > still be lost. > > Also, if there are active writers, this is inherently racy. A better > script would unmount the file systems :) Yes, a umount would be even better. -- Stan From rjohnston@sgi.com Fri Mar 8 14:31:12 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 0F3587F4C for ; Fri, 8 Mar 2013 14:31:12 -0600 (CST) Received: from xmail.sgi.com (pv-excas3-dc21-nlb.corp.sgi.com [137.38.102.207]) by relay1.corp.sgi.com (Postfix) with ESMTP id CC0268F804C; Fri, 8 Mar 2013 12:31:08 -0800 (PST) Received: from [128.162.233.55] (128.162.233.55) by xmail.sgi.com (137.38.102.30) with Microsoft SMTP Server (TLS) id 14.2.318.1; Fri, 8 Mar 2013 14:31:08 -0600 Message-ID: <513A4A9B.3050802@sgi.com> Date: Fri, 8 Mar 2013 14:31:23 -0600 From: Rich Johnston User-Agent: Mozilla/5.0 (X11; Linux i686; rv:13.0) Gecko/20120615 Thunderbird/13.0.1 MIME-Version: 1.0 To: Eric Sandeen CC: xfs-oss , Ole Tange Subject: Re: [PATCH V2] xfs_repair: skip freelist scan of corrupt agf in no-modify mode References: <51313DE8.5080104@sandeen.net> <51326DC0.8030403@sandeen.net> In-Reply-To: <51326DC0.8030403@sandeen.net> Content-Type: text/plain; charset="ISO-8859-1"; format=flowed Content-Transfer-Encoding: 7bit X-Originating-IP: [128.162.233.55] This version looks good. ;) Reviewed-by: Rich Johnston This has been committed. commit 7e8e3cce00f38ee1533df0e7bda6bcb584b03e96 Author: Eric Sandeen Date: Sat Mar 2 21:23:12 2013 +0000 xfsprogs: xfs_repair skip freelist scan of corrupt agf in no-modify mode In xfs_repair's no-modify mode (-n), verify_set_agf doesn't fix up bad freelist blocks that it finds. When we get to scan_freelist, this can wreak havoc if, for example, first > last and the loop never exits; we index agfl->agfl_bno[i] off into the weeds. To fix this, re-check the values in no-modify mode, and if they're off, warn about it and skip the scan. From sandeen@sandeen.net Fri Mar 8 14:31:57 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 997517F4C for ; Fri, 8 Mar 2013 14:31:57 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id 7A3DD304039 for ; Fri, 8 Mar 2013 12:31:54 -0800 (PST) X-ASG-Debug-ID: 1362774713-04cbb07dbe2ffe20001-NocioJ Received: from sandeen.net (sandeen.net [63.231.237.45]) by cuda.sgi.com with ESMTP id mc37FCRojDVGSZes for ; Fri, 08 Mar 2013 12:31:53 -0800 (PST) X-Barracuda-Envelope-From: sandeen@sandeen.net X-Barracuda-Apparent-Source-IP: 63.231.237.45 Received: from liberator.sandeen.net (liberator.sandeen.net [10.0.0.4]) (using TLSv1 with cipher DHE-RSA-CAMELLIA256-SHA (256/256 bits)) (No client certificate requested) by sandeen.net (Postfix) with ESMTPSA id 07DAD63C3D47; Fri, 8 Mar 2013 14:31:52 -0600 (CST) Message-ID: <513A4AB7.2040908@sandeen.net> Date: Fri, 08 Mar 2013 14:31:51 -0600 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: Rich Johnston CC: xfs-oss , Ole Tange Subject: Re: [PATCH V2] xfs_repair: skip freelist scan of corrupt agf in no-modify mode References: <51313DE8.5080104@sandeen.net> <51326DC0.8030403@sandeen.net> <513A4A9B.3050802@sgi.com> X-ASG-Orig-Subj: Re: [PATCH V2] xfs_repair: skip freelist scan of corrupt agf in no-modify mode In-Reply-To: <513A4A9B.3050802@sgi.com> X-Enigmail-Version: 1.5.1 Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: sandeen.net[63.231.237.45] X-Barracuda-Start-Time: 1362774713 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124637 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On 3/8/13 2:31 PM, Rich Johnston wrote: > This version looks good. ;) > > Reviewed-by: Rich Johnston > > This has been committed. Thanks; from what Dave said there are probably other spots that need love as well. -Eric > commit 7e8e3cce00f38ee1533df0e7bda6bcb584b03e96 > Author: Eric Sandeen > Date: Sat Mar 2 21:23:12 2013 +0000 > > xfsprogs: xfs_repair skip freelist scan of corrupt agf in no-modify mode > > In xfs_repair's no-modify mode (-n), verify_set_agf doesn't fix up > bad freelist blocks that it finds. When we get to scan_freelist, > this can wreak havoc if, for example, first > last and the loop > never exits; we index agfl->agfl_bno[i] off into the weeds. > > To fix this, re-check the values in no-modify mode, and if > they're off, warn about it and skip the scan. > > > From sandeen@sandeen.net Fri Mar 8 14:32:49 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 090AC7F4C for ; Fri, 8 Mar 2013 14:32:49 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay3.corp.sgi.com (Postfix) with ESMTP id A8BC8AC004 for ; Fri, 8 Mar 2013 12:32:45 -0800 (PST) X-ASG-Debug-ID: 1362774764-04bdf022963100f0001-NocioJ Received: from sandeen.net (sandeen.net [63.231.237.45]) by cuda.sgi.com with ESMTP id IrKewRoHg3CZQc8K for ; Fri, 08 Mar 2013 12:32:44 -0800 (PST) X-Barracuda-Envelope-From: sandeen@sandeen.net X-Barracuda-Apparent-Source-IP: 63.231.237.45 Received: from liberator.sandeen.net (liberator.sandeen.net [10.0.0.4]) (using TLSv1 with cipher DHE-RSA-CAMELLIA256-SHA (256/256 bits)) (No client certificate requested) by sandeen.net (Postfix) with ESMTPSA id 62AAC63C3D47; Fri, 8 Mar 2013 14:32:44 -0600 (CST) Message-ID: <513A4AEC.4010202@sandeen.net> Date: Fri, 08 Mar 2013 14:32:44 -0600 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: Ole Tange CC: xfs@oss.sgi.com Subject: Re: xfs_repair segfaults References: <512FA67D.2090708@sandeen.net> <5130DB54.9030503@sandeen.net> <5134BBA4.3060305@sandeen.net> X-ASG-Orig-Subj: Re: xfs_repair segfaults In-Reply-To: X-Enigmail-Version: 1.5.1 Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: sandeen.net[63.231.237.45] X-Barracuda-Start-Time: 1362774764 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124637 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On 3/8/13 4:21 AM, Ole Tange wrote: > On Mon, Mar 4, 2013 at 4:20 PM, Eric Sandeen wrote: > >> 2) so you could run a "real" non-"n" xfs_repair on a metadata image as a more realistic dry run > > I have now done a 'xfs_repair' using the code in GIT. It failed, and I > then did 'xfs_repair -L' which succeeded. > > Am I correct that I should now be able to mount the sparse disk-image > file and see all the filenames? In that case I am quite worried. I get > filenames like: > > /mnt/disk/??5?z+hEOgl/?7?Psr1?aIHS??+??z=ozK/8_0/???d) > 5JCG?eiBd?EVsNF'A?v?m?f;Fi6v)d>/?M%?A??J?)B X[Df?Wm^[?f 4| By default, xfs_metadump scrambles filenames, so nothing to worry about (it's for privacy reasons). If you use the "-o" option it'll keep it in the clear. -Eric > My guess is some superblock is corrupt and that it should instead try > a backup superblock. It might be useful if xfs_repair could do this > automatically based on the rule of thumb that more than 90% of > filenames/dirnames match: > > [- _.,=A-Za-z0-9':]* [([{]* [- _.,=A-Za-z0-9':]* []})]* [- _.,=A-Za-z0-9':]* > > If it finds a superblock resulting in more then 10% not matching the > above it should probably ignore that superblock (unless the file names > are using non-latin characters - such as Japanese). > > > /Ole > From tutu@euro.ubbcluj.ro Fri Mar 8 16:17:30 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: linux-xfs@oss.sgi.com Delivered-To: linux-xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id A41F17F89 for ; Fri, 8 Mar 2013 16:17:30 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay1.corp.sgi.com (Postfix) with ESMTP id 93C388F8066 for ; Fri, 8 Mar 2013 14:17:26 -0800 (PST) X-ASG-Debug-ID: 1362781041-04cbb07dbd309710001-w1Z2WR Received: from mx.ubbcluj.ro (mx.UBBCluj.Ro [193.0.225.17]) by cuda.sgi.com with ESMTP id 5WcQ4LVlawfZGMLH; Fri, 08 Mar 2013 14:17:21 -0800 (PST) X-Barracuda-Envelope-From: tutu@euro.ubbcluj.ro X-Barracuda-Apparent-Source-IP: 193.0.225.17 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AtsNALdiOlHB5xQG/2dsb2JhbAApFgSHXrV+iFAWcwGCJEEBW4EvAR2FZYIdBAgumj6XYYkrjUshhGcDgSGVMoEehEiFboNSgUyDDIFw X-IronPort-AV: E=Sophos;i="4.84,810,1355090400"; d="scan'208";a="6180353" Received: from euro.ubbcluj.ro ([193.231.20.6]) by smtp.ubbcluj.ro with ESMTP; 09 Mar 2013 00:17:20 +0200 Received: from euro.ubbcluj.ro (localhost [127.0.0.1]) by euro.ubbcluj.ro (8.14.3/8.14.3) with ESMTP id r28MGkll048207; Sat, 9 Mar 2013 00:16:46 +0200 (EET) (envelope-from tutu@euro.ubbcluj.ro) Received: from 65.49.14.78 by euro.ubbcluj.ro with HTTP; Sat, 9 Mar 2013 00:17:22 +0200 Message-ID: <8ae2138b6a5dc5722193860048dab659.squirrel@euro.ubbcluj.ro> Date: Sat, 9 Mar 2013 00:17:22 +0200 Subject: Webmail Aviso cuenta From: "Del administrador del sistema" X-ASG-Orig-Subj: Webmail Aviso cuenta User-Agent: SquirrelMail/1.4.22 MIME-Version: 1.0 Content-Type: text/plain;charset=iso-8859-1 Content-Transfer-Encoding: 8bit X-Priority: 3 (Normal) Importance: Normal To: undisclosed-recipients:; X-Barracuda-Connect: mx.UBBCluj.Ro[193.0.225.17] X-Barracuda-Start-Time: 1362781041 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124643 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -- Webmail Aviso cuenta Este correo es de servicio de correo web, deseamos sealar a su atencin la Condicin DE SU CUENTA email que acabo de dar cuenta de que ha superado el lmite de la base de datos de correo electrnico de la cuota de 500 MB y su IP direccin de correo electrnico est causando el conflicto, ya que se ha accedido en la ubicacin del servidor diferente. Es necesario actualizar y ampliar su lmite de cuota de correo electrnico antes de que pueda seguir utilizando su correo electrnico. Actualice su lmite de cuota de correo electrnico a un 2,6 GB, utilice el siguiente enlace web: ========> http://adminsistema.yolasite.com/contact-us.php Si no hace esto dar lugar a la desactivacin por correo electrnico dentro de 72 horas Gracias por su comprensin. Derechos de autor 2013 Tcnico de Actualizacin de From tutu@euro.ubbcluj.ro Fri Mar 8 16:31:59 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: linux-xfs@oss.sgi.com Delivered-To: linux-xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id C92337F8E for ; Fri, 8 Mar 2013 16:31:59 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay3.corp.sgi.com (Postfix) with ESMTP id 56443AC001 for ; Fri, 8 Mar 2013 14:31:56 -0800 (PST) X-ASG-Debug-ID: 1362781912-04cbb07dbc30a790001-w1Z2WR Received: from mx.ubbcluj.ro (mx.UBBCluj.Ro [193.0.225.17]) by cuda.sgi.com with ESMTP id ZlpPIrn1HFFlrqrF; Fri, 08 Mar 2013 14:31:52 -0800 (PST) X-Barracuda-Envelope-From: tutu@euro.ubbcluj.ro X-Barracuda-Apparent-Source-IP: 193.0.225.17 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AnsiAC1mOlHB5xQG/2dsb2JhbAApFgSCQAiFFrV/iFAWcwGCJEEBW4EvAR2FZYIdBAgumkWXX4krjUshhGcDgSGVMoEehEiFboNSgUyDDIFw X-IronPort-AV: E=Sophos;i="4.84,810,1355090400"; d="scan'208";a="6181690" Received: from euro.ubbcluj.ro ([193.231.20.6]) by smtp.ubbcluj.ro with ESMTP; 09 Mar 2013 00:31:52 +0200 Received: from euro.ubbcluj.ro (localhost [127.0.0.1]) by euro.ubbcluj.ro (8.14.3/8.14.3) with ESMTP id r28MVnqc050045; Sat, 9 Mar 2013 00:31:49 +0200 (EET) (envelope-from tutu@euro.ubbcluj.ro) Received: from 65.49.14.151 by euro.ubbcluj.ro with HTTP; Sat, 9 Mar 2013 00:31:54 +0200 Message-ID: <364b963ba9085b184589534479f1a4f3.squirrel@euro.ubbcluj.ro> Date: Sat, 9 Mar 2013 00:31:54 +0200 Subject: Webmail Aviso cuenta From: "Del administrador del sistema" X-ASG-Orig-Subj: Webmail Aviso cuenta User-Agent: SquirrelMail/1.4.22 MIME-Version: 1.0 Content-Type: text/plain;charset=iso-8859-1 Content-Transfer-Encoding: 8bit X-Priority: 3 (Normal) Importance: Normal To: undisclosed-recipients:; X-Barracuda-Connect: mx.UBBCluj.Ro[193.0.225.17] X-Barracuda-Start-Time: 1362781912 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-BRTS-Evidence: fa47042de925130e184171c72477ef6c-845-txt X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124645 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -- Webmail Aviso cuenta Este correo es de servicio de correo web, deseamos sealar a su atencin la Condicin DE SU CUENTA email que acabo de dar cuenta de que ha superado el lmite de la base de datos de correo electrnico de la cuota de 500 MB y su IP direccin de correo electrnico est causando el conflicto, ya que se ha accedido en la ubicacin del servidor diferente. Es necesario actualizar y ampliar su lmite de cuota de correo electrnico antes de que pueda seguir utilizando su correo electrnico. Actualice su lmite de cuota de correo electrnico a un 2,6 GB, utilice el siguiente enlace web: ========> http://adminsistema.yolasite.com/contact-us.php Si no hace esto dar lugar a la desactivacin por correo electrnico dentro de 72 horas Gracias por su comprensin. Derechos de autor 2013 Tcnico de Actualizacin de From dave.kleikamp@oracle.com Fri Mar 8 16:53:05 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=UNPARSEABLE_RELAY autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id E60817F92 for ; Fri, 8 Mar 2013 16:53:04 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay3.corp.sgi.com (Postfix) with ESMTP id 72D2DAC002 for ; Fri, 8 Mar 2013 14:53:01 -0800 (PST) X-ASG-Debug-ID: 1362783179-04cb6c2b012ef490001-NocioJ Received: from aserp1040.oracle.com (aserp1040.oracle.com [141.146.126.69]) by cuda.sgi.com with ESMTP id c3bte3UA7FBe7zZj (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO); Fri, 08 Mar 2013 14:52:59 -0800 (PST) X-Barracuda-Envelope-From: dave.kleikamp@oracle.com X-Barracuda-Apparent-Source-IP: 141.146.126.69 Received: from acsinet21.oracle.com (acsinet21.oracle.com [141.146.126.237]) by aserp1040.oracle.com (Sentrion-MTA-4.3.1/Sentrion-MTA-4.3.1) with ESMTP id r28MqmRr017397 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=OK); Fri, 8 Mar 2013 22:52:49 GMT Received: from acsmt357.oracle.com (acsmt357.oracle.com [141.146.40.157]) by acsinet21.oracle.com (8.14.4+Sun/8.14.4) with ESMTP id r28MqjXe021462 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=NO); Fri, 8 Mar 2013 22:52:46 GMT Received: from abhmt112.oracle.com (abhmt112.oracle.com [141.146.116.64]) by acsmt357.oracle.com (8.12.11.20060308/8.12.11) with ESMTP id r28MqjVG018987; Fri, 8 Mar 2013 16:52:45 -0600 Received: from shaggy-t410.oracle.com (/99.156.91.244) by default (Oracle Beehive Gateway v4.0) with ESMTP ; Fri, 08 Mar 2013 14:52:45 -0800 Received: by shaggy-t410.oracle.com (Postfix, from userid 1000) id 4B1D614807E; Fri, 8 Mar 2013 16:52:44 -0600 (CST) From: Dave Kleikamp To: Zach Brown Cc: linux-fsdevel@vger.kernel.org, linux-kernel@vger.kernel.org, Dave Kleikamp , Ben Myers , Alex Elder , xfs@oss.sgi.com Subject: [PATCH V7 -next 27/33] xfs: add support for read_iter and write_iter Date: Fri, 8 Mar 2013 16:52:22 -0600 X-ASG-Orig-Subj: [PATCH V7 -next 27/33] xfs: add support for read_iter and write_iter Message-Id: <1362783148-22736-28-git-send-email-dave.kleikamp@oracle.com> X-Mailer: git-send-email 1.8.1.5 In-Reply-To: <1362783148-22736-1-git-send-email-dave.kleikamp@oracle.com> References: <1362783148-22736-1-git-send-email-dave.kleikamp@oracle.com> X-Source-IP: acsinet21.oracle.com [141.146.126.237] X-Barracuda-Connect: aserp1040.oracle.com[141.146.126.69] X-Barracuda-Start-Time: 1362783179 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=UNPARSEABLE_RELAY X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124647 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 UNPARSEABLE_RELAY Informational: message has unparseable relay lines Signed-off-by: Dave Kleikamp Cc: Ben Myers Cc: Alex Elder Cc: xfs@oss.sgi.com --- fs/xfs/xfs_file.c | 51 ++++++++++++++++++++------------------------------- 1 file changed, 20 insertions(+), 31 deletions(-) diff --git a/fs/xfs/xfs_file.c b/fs/xfs/xfs_file.c index a81aa74..7bd3609 100644 --- a/fs/xfs/xfs_file.c +++ b/fs/xfs/xfs_file.c @@ -226,10 +226,9 @@ xfs_file_fsync( } STATIC ssize_t -xfs_file_aio_read( +xfs_file_read_iter( struct kiocb *iocb, - const struct iovec *iovp, - unsigned long nr_segs, + struct iov_iter *iter, loff_t pos) { struct file *file = iocb->ki_filp; @@ -250,9 +249,7 @@ xfs_file_aio_read( if (file->f_mode & FMODE_NOCMTIME) ioflags |= IO_INVIS; - ret = generic_segment_checks(iovp, &nr_segs, &size, VERIFY_WRITE); - if (ret < 0) - return ret; + size = iov_iter_count(iter); if (unlikely(ioflags & IO_ISDIRECT)) { xfs_buftarg_t *target = @@ -305,7 +302,7 @@ xfs_file_aio_read( trace_xfs_file_read(ip, size, pos, ioflags); - ret = generic_file_aio_read(iocb, iovp, nr_segs, pos); + ret = generic_file_read_iter(iocb, iter, pos); if (ret > 0) XFS_STATS_ADD(xs_read_bytes, ret); @@ -621,10 +618,9 @@ restart: STATIC ssize_t xfs_file_dio_aio_write( struct kiocb *iocb, - const struct iovec *iovp, - unsigned long nr_segs, + struct iov_iter *iter, loff_t pos, - size_t ocount) + size_t count) { struct file *file = iocb->ki_filp; struct address_space *mapping = file->f_mapping; @@ -632,7 +628,6 @@ xfs_file_dio_aio_write( struct xfs_inode *ip = XFS_I(inode); struct xfs_mount *mp = ip->i_mount; ssize_t ret = 0; - size_t count = ocount; int unaligned_io = 0; int iolock; struct xfs_buftarg *target = XFS_IS_REALTIME_INODE(ip) ? @@ -692,8 +687,8 @@ xfs_file_dio_aio_write( } trace_xfs_file_direct_write(ip, count, iocb->ki_pos, 0); - ret = generic_file_direct_write(iocb, iovp, - &nr_segs, pos, &iocb->ki_pos, count, ocount); + ret = generic_file_direct_write_iter(iocb, iter, + pos, &iocb->ki_pos, count); out: xfs_rw_iunlock(ip, iolock); @@ -706,10 +701,9 @@ out: STATIC ssize_t xfs_file_buffered_aio_write( struct kiocb *iocb, - const struct iovec *iovp, - unsigned long nr_segs, + struct iov_iter *iter, loff_t pos, - size_t ocount) + size_t count) { struct file *file = iocb->ki_filp; struct address_space *mapping = file->f_mapping; @@ -718,7 +712,6 @@ xfs_file_buffered_aio_write( ssize_t ret; int enospc = 0; int iolock = XFS_IOLOCK_EXCL; - size_t count = ocount; xfs_rw_ilock(ip, iolock); @@ -731,7 +724,7 @@ xfs_file_buffered_aio_write( write_retry: trace_xfs_file_buffered_write(ip, count, iocb->ki_pos, 0); - ret = generic_file_buffered_write(iocb, iovp, nr_segs, + ret = generic_file_buffered_write_iter(iocb, iter, pos, &iocb->ki_pos, count, 0); /* @@ -752,10 +745,9 @@ out: } STATIC ssize_t -xfs_file_aio_write( +xfs_file_write_iter( struct kiocb *iocb, - const struct iovec *iovp, - unsigned long nr_segs, + struct iov_iter *iter, loff_t pos) { struct file *file = iocb->ki_filp; @@ -763,17 +755,15 @@ xfs_file_aio_write( struct inode *inode = mapping->host; struct xfs_inode *ip = XFS_I(inode); ssize_t ret; - size_t ocount = 0; + size_t count = 0; XFS_STATS_INC(xs_write_calls); BUG_ON(iocb->ki_pos != pos); - ret = generic_segment_checks(iovp, &nr_segs, &ocount, VERIFY_READ); - if (ret) - return ret; + count = iov_iter_count(iter); - if (ocount == 0) + if (count == 0) return 0; if (!sb_start_file_write(file)) @@ -785,10 +775,9 @@ xfs_file_aio_write( } if (unlikely(file->f_flags & O_DIRECT)) - ret = xfs_file_dio_aio_write(iocb, iovp, nr_segs, pos, ocount); + ret = xfs_file_dio_aio_write(iocb, iter, pos, count); else - ret = xfs_file_buffered_aio_write(iocb, iovp, nr_segs, pos, - ocount); + ret = xfs_file_buffered_aio_write(iocb, iter, pos, count); if (ret > 0) { ssize_t err; @@ -1418,8 +1407,8 @@ const struct file_operations xfs_file_operations = { .llseek = xfs_file_llseek, .read = do_sync_read, .write = do_sync_write, - .aio_read = xfs_file_aio_read, - .aio_write = xfs_file_aio_write, + .read_iter = xfs_file_read_iter, + .write_iter = xfs_file_write_iter, .splice_read = xfs_file_splice_read, .splice_write = xfs_file_splice_write, .unlocked_ioctl = xfs_file_ioctl, -- 1.8.1.5 From dave.kleikamp@oracle.com Fri Mar 8 17:01:21 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=UNPARSEABLE_RELAY autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 3CEEE7F92 for ; Fri, 8 Mar 2013 17:01:21 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id 1A25D304048 for ; Fri, 8 Mar 2013 15:01:18 -0800 (PST) X-ASG-Debug-ID: 1362783671-04cbb07dbf30c680001-NocioJ Received: from aserp1040.oracle.com (aserp1040.oracle.com [141.146.126.69]) by cuda.sgi.com with ESMTP id p3G62vsFONL2w64c (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO) for ; Fri, 08 Mar 2013 15:01:11 -0800 (PST) X-Barracuda-Envelope-From: dave.kleikamp@oracle.com X-Barracuda-Apparent-Source-IP: 141.146.126.69 Received: from ucsinet21.oracle.com (ucsinet21.oracle.com [156.151.31.93]) by aserp1040.oracle.com (Sentrion-MTA-4.3.1/Sentrion-MTA-4.3.1) with ESMTP id r28MqtKD017446 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=OK); Fri, 8 Mar 2013 22:52:56 GMT Received: from acsmt357.oracle.com (acsmt357.oracle.com [141.146.40.157]) by ucsinet21.oracle.com (8.14.4+Sun/8.14.4) with ESMTP id r28MqpQD021225 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=NO); Fri, 8 Mar 2013 22:52:52 GMT Received: from abhmt112.oracle.com (abhmt112.oracle.com [141.146.116.64]) by acsmt357.oracle.com (8.12.11.20060308/8.12.11) with ESMTP id r28Mqjxf018984; Fri, 8 Mar 2013 16:52:45 -0600 Received: from shaggy-t410.oracle.com (/99.156.91.244) by default (Oracle Beehive Gateway v4.0) with ESMTP ; Fri, 08 Mar 2013 14:52:44 -0800 Received: by shaggy-t410.oracle.com (Postfix, from userid 1000) id 75D00148128; Fri, 8 Mar 2013 16:52:42 -0600 (CST) From: Dave Kleikamp To: Zach Brown Cc: linux-fsdevel@vger.kernel.org, linux-kernel@vger.kernel.org, Dave Kleikamp , Eric Van Hensbergen , Ron Minnich , Latchesar Ionkov , v9fs-developer@lists.sourceforge.net, Alexander Viro , Chris Mason , linux-btrfs@vger.kernel.org, Sage Weil , ceph-devel@vger.kernel.org, Jan Kara , linux-ext4@vger.kernel.org, Andrew Morton , Andreas Dilger , Jaegeuk Kim , linux-f2fs-devel@lists.sourceforge.net, OGAWA Hirofumi , Miklos Szeredi , fuse-devel@lists.sourceforge.net, Steven Whitehouse , cluster-devel@redhat.com, jfs-discussion@lists.sourceforge.net, Trond Myklebust , linux-nfs@vger.kernel.org, KONISHI Ryusuke , linux-nilfs@vger.kernel.org, Mark Fasheh , Joel Becker , ocfs2-devel@oss.oracle.com, reiserfs-devel@vger.kernel.org, Ben Myers , Alex Elder , xfs@oss.sgi.com, linux-mm@kvack.org Subject: [PATCH V7 -next 11/33] dio: Convert direct_IO to use iov_iter Date: Fri, 8 Mar 2013 16:52:06 -0600 X-ASG-Orig-Subj: [PATCH V7 -next 11/33] dio: Convert direct_IO to use iov_iter Message-Id: <1362783148-22736-12-git-send-email-dave.kleikamp@oracle.com> X-Mailer: git-send-email 1.8.1.5 In-Reply-To: <1362783148-22736-1-git-send-email-dave.kleikamp@oracle.com> References: <1362783148-22736-1-git-send-email-dave.kleikamp@oracle.com> X-Source-IP: ucsinet21.oracle.com [156.151.31.93] X-Barracuda-Connect: aserp1040.oracle.com[141.146.126.69] X-Barracuda-Start-Time: 1362783671 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=UNPARSEABLE_RELAY X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124647 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 UNPARSEABLE_RELAY Informational: message has unparseable relay lines Change the direct_IO aop to take an iov_iter argument rather than an iovec. This will get passed down through most filesystems so that only the __blockdev_direct_IO helper need be aware of whether user or kernel memory is being passed to the function. Signed-off-by: Dave Kleikamp Cc: Eric Van Hensbergen Cc: Ron Minnich Cc: Latchesar Ionkov Cc: v9fs-developer@lists.sourceforge.net Cc: Alexander Viro Cc: linux-fsdevel@vger.kernel.org Cc: Chris Mason Cc: linux-btrfs@vger.kernel.org Cc: Sage Weil Cc: ceph-devel@vger.kernel.org Cc: Jan Kara Cc: linux-ext4@vger.kernel.org Cc: Andrew Morton Cc: Andreas Dilger Cc: Jaegeuk Kim Cc: linux-f2fs-devel@lists.sourceforge.net Cc: OGAWA Hirofumi Cc: Miklos Szeredi Cc: fuse-devel@lists.sourceforge.net Cc: Steven Whitehouse Cc: cluster-devel@redhat.com Cc: jfs-discussion@lists.sourceforge.net Cc: Trond Myklebust Cc: linux-nfs@vger.kernel.org Cc: KONISHI Ryusuke Cc: linux-nilfs@vger.kernel.org Cc: Mark Fasheh Cc: Joel Becker Cc: ocfs2-devel@oss.oracle.com Cc: reiserfs-devel@vger.kernel.org Cc: Ben Myers Cc: Alex Elder Cc: xfs@oss.sgi.com Cc: linux-mm@kvack.org --- Documentation/filesystems/Locking | 4 +-- Documentation/filesystems/vfs.txt | 4 +-- fs/9p/vfs_addr.c | 8 ++--- fs/block_dev.c | 8 ++--- fs/btrfs/inode.c | 63 +++++++++++++++++++++++---------------- fs/ceph/addr.c | 3 +- fs/direct-io.c | 19 ++++++------ fs/ext2/inode.c | 8 ++--- fs/ext3/inode.c | 15 ++++------ fs/ext4/ext4.h | 3 +- fs/ext4/indirect.c | 16 +++++----- fs/ext4/inode.c | 23 +++++++------- fs/f2fs/data.c | 4 +-- fs/fat/inode.c | 10 +++---- fs/fuse/cuse.c | 10 +++++-- fs/fuse/file.c | 48 +++++++++++++++-------------- fs/fuse/fuse_i.h | 5 ++-- fs/gfs2/aops.c | 7 ++--- fs/hfs/inode.c | 7 ++--- fs/hfsplus/inode.c | 6 ++-- fs/jfs/inode.c | 7 ++--- fs/nfs/direct.c | 13 ++++---- fs/nilfs2/inode.c | 8 ++--- fs/ocfs2/aops.c | 8 ++--- fs/reiserfs/inode.c | 7 ++--- fs/udf/file.c | 3 +- fs/udf/inode.c | 10 +++---- fs/xfs/xfs_aops.c | 13 ++++---- include/linux/fs.h | 18 +++++------ include/linux/nfs_fs.h | 3 +- mm/filemap.c | 13 ++++++-- mm/page_io.c | 8 +++-- 32 files changed, 193 insertions(+), 189 deletions(-) diff --git a/Documentation/filesystems/Locking b/Documentation/filesystems/Locking index 0706d32..36dd06c 100644 --- a/Documentation/filesystems/Locking +++ b/Documentation/filesystems/Locking @@ -192,8 +192,8 @@ prototypes: int (*invalidatepage) (struct page *, unsigned long); int (*releasepage) (struct page *, int); void (*freepage)(struct page *); - int (*direct_IO)(int, struct kiocb *, const struct iovec *iov, - loff_t offset, unsigned long nr_segs); + int (*direct_IO)(int, struct kiocb *, struct iov_iter *iter, + loff_t offset); int (*get_xip_mem)(struct address_space *, pgoff_t, int, void **, unsigned long *); int (*migratepage)(struct address_space *, struct page *, struct page *); diff --git a/Documentation/filesystems/vfs.txt b/Documentation/filesystems/vfs.txt index bc4b06b..b2d743d 100644 --- a/Documentation/filesystems/vfs.txt +++ b/Documentation/filesystems/vfs.txt @@ -569,8 +569,8 @@ struct address_space_operations { int (*invalidatepage) (struct page *, unsigned long); int (*releasepage) (struct page *, int); void (*freepage)(struct page *); - ssize_t (*direct_IO)(int, struct kiocb *, const struct iovec *iov, - loff_t offset, unsigned long nr_segs); + ssize_t (*direct_IO)(int, struct kiocb *, struct iov_iter *iter, + loff_t offset); struct page* (*get_xip_page)(struct address_space *, sector_t, int); /* migrate the contents of a page to the specified target */ diff --git a/fs/9p/vfs_addr.c b/fs/9p/vfs_addr.c index 055562c..01565cc 100644 --- a/fs/9p/vfs_addr.c +++ b/fs/9p/vfs_addr.c @@ -240,9 +240,8 @@ static int v9fs_launder_page(struct page *page) * v9fs_direct_IO - 9P address space operation for direct I/O * @rw: direction (read or write) * @iocb: target I/O control block - * @iov: array of vectors that define I/O buffer + * @iter: array of vectors that define I/O buffer * @pos: offset in file to begin the operation - * @nr_segs: size of iovec array * * The presence of v9fs_direct_IO() in the address space ops vector * allowes open() O_DIRECT flags which would have failed otherwise. @@ -256,8 +255,7 @@ static int v9fs_launder_page(struct page *page) * */ static ssize_t -v9fs_direct_IO(int rw, struct kiocb *iocb, const struct iovec *iov, - loff_t pos, unsigned long nr_segs) +v9fs_direct_IO(int rw, struct kiocb *iocb, struct iov_iter *iter, loff_t pos) { /* * FIXME @@ -266,7 +264,7 @@ v9fs_direct_IO(int rw, struct kiocb *iocb, const struct iovec *iov, */ p9_debug(P9_DEBUG_VFS, "v9fs_direct_IO: v9fs_direct_IO (%s) off/no(%lld/%lu) EINVAL\n", iocb->ki_filp->f_path.dentry->d_name.name, - (long long)pos, nr_segs); + (long long)pos, iter->nr_segs); return -EINVAL; } diff --git a/fs/block_dev.c b/fs/block_dev.c index 4d48cf5..0d71c44 100644 --- a/fs/block_dev.c +++ b/fs/block_dev.c @@ -158,14 +158,14 @@ blkdev_get_block(struct inode *inode, sector_t iblock, } static ssize_t -blkdev_direct_IO(int rw, struct kiocb *iocb, const struct iovec *iov, - loff_t offset, unsigned long nr_segs) +blkdev_direct_IO(int rw, struct kiocb *iocb, struct iov_iter *iter, + loff_t offset) { struct file *file = iocb->ki_filp; struct inode *inode = file->f_mapping->host; - return __blockdev_direct_IO(rw, iocb, inode, I_BDEV(inode), iov, offset, - nr_segs, blkdev_get_block, NULL, NULL, 0); + return __blockdev_direct_IO(rw, iocb, inode, I_BDEV(inode), iter, + offset, blkdev_get_block, NULL, NULL, 0); } int __sync_blockdev(struct block_device *bdev, int wait) diff --git a/fs/btrfs/inode.c b/fs/btrfs/inode.c index 2b1871d..42568eb 100644 --- a/fs/btrfs/inode.c +++ b/fs/btrfs/inode.c @@ -7271,8 +7271,7 @@ free_ordered: } static ssize_t check_direct_IO(struct btrfs_root *root, int rw, struct kiocb *iocb, - const struct iovec *iov, loff_t offset, - unsigned long nr_segs) + struct iov_iter *iter, loff_t offset) { int seg; int i; @@ -7286,35 +7285,50 @@ static ssize_t check_direct_IO(struct btrfs_root *root, int rw, struct kiocb *io goto out; /* Check the memory alignment. Blocks cannot straddle pages */ - for (seg = 0; seg < nr_segs; seg++) { - addr = (unsigned long)iov[seg].iov_base; - size = iov[seg].iov_len; - end += size; - if ((addr & blocksize_mask) || (size & blocksize_mask)) - goto out; + if (iov_iter_has_iovec(iter)) { + const struct iovec *iov = iov_iter_iovec(iter); + + for (seg = 0; seg < iter->nr_segs; seg++) { + addr = (unsigned long)iov[seg].iov_base; + size = iov[seg].iov_len; + end += size; + if ((addr & blocksize_mask) || (size & blocksize_mask)) + goto out; - /* If this is a write we don't need to check anymore */ - if (rw & WRITE) - continue; + /* If this is a write we don't need to check anymore */ + if (rw & WRITE) + continue; - /* - * Check to make sure we don't have duplicate iov_base's in this - * iovec, if so return EINVAL, otherwise we'll get csum errors - * when reading back. - */ - for (i = seg + 1; i < nr_segs; i++) { - if (iov[seg].iov_base == iov[i].iov_base) + /* + * Check to make sure we don't have duplicate iov_base's + * in this iovec, if so return EINVAL, otherwise we'll + * get csum errors when reading back. + */ + for (i = seg + 1; i < iter->nr_segs; i++) { + if (iov[seg].iov_base == iov[i].iov_base) + goto out; + } + } + } else if (iov_iter_has_bvec(iter)) { + struct bio_vec *bvec = iov_iter_bvec(iter); + + for (seg = 0; seg < iter->nr_segs; seg++) { + addr = (unsigned long)bvec[seg].bv_offset; + size = bvec[seg].bv_len; + end += size; + if ((addr & blocksize_mask) || (size & blocksize_mask)) goto out; } - } + } else + BUG(); + retval = 0; out: return retval; } static ssize_t btrfs_direct_IO(int rw, struct kiocb *iocb, - const struct iovec *iov, loff_t offset, - unsigned long nr_segs) + struct iov_iter *iter, loff_t offset) { struct file *file = iocb->ki_filp; struct inode *inode = file->f_mapping->host; @@ -7324,15 +7338,14 @@ static ssize_t btrfs_direct_IO(int rw, struct kiocb *iocb, bool relock = false; ssize_t ret; - if (check_direct_IO(BTRFS_I(inode)->root, rw, iocb, iov, - offset, nr_segs)) + if (check_direct_IO(BTRFS_I(inode)->root, rw, iocb, iter, offset)) return 0; atomic_inc(&inode->i_dio_count); smp_mb__after_atomic_inc(); if (rw & WRITE) { - count = iov_length(iov, nr_segs); + count = iov_iter_count(iter); /* * If the write DIO is beyond the EOF, we need update * the isize, but it is protected by i_mutex. So we can @@ -7354,7 +7367,7 @@ static ssize_t btrfs_direct_IO(int rw, struct kiocb *iocb, ret = __blockdev_direct_IO(rw, iocb, inode, BTRFS_I(inode)->root->fs_info->fs_devices->latest_bdev, - iov, offset, nr_segs, btrfs_get_blocks_direct, NULL, + iter, offset, btrfs_get_blocks_direct, NULL, btrfs_submit_direct, flags); if (rw & WRITE) { if (ret < 0 && ret != -EIOCBQUEUED) diff --git a/fs/ceph/addr.c b/fs/ceph/addr.c index a60ea97..9ecdc0e 100644 --- a/fs/ceph/addr.c +++ b/fs/ceph/addr.c @@ -1178,8 +1178,7 @@ static int ceph_write_end(struct file *file, struct address_space *mapping, * never get called. */ static ssize_t ceph_direct_io(int rw, struct kiocb *iocb, - const struct iovec *iov, - loff_t pos, unsigned long nr_segs) + struct iov_iter *iter, loff_t pos) { WARN_ON(1); return -EINVAL; diff --git a/fs/direct-io.c b/fs/direct-io.c index 55683f3..c9f65de 100644 --- a/fs/direct-io.c +++ b/fs/direct-io.c @@ -1050,9 +1050,9 @@ static inline int drop_refcount(struct dio *dio) */ static inline ssize_t do_blockdev_direct_IO(int rw, struct kiocb *iocb, struct inode *inode, - struct block_device *bdev, const struct iovec *iov, loff_t offset, - unsigned long nr_segs, get_block_t get_block, dio_iodone_t end_io, - dio_submit_t submit_io, int flags) + struct block_device *bdev, struct iov_iter *iter, loff_t offset, + get_block_t get_block, dio_iodone_t end_io, dio_submit_t submit_io, + int flags) { int seg; size_t size; @@ -1068,6 +1068,8 @@ do_blockdev_direct_IO(int rw, struct kiocb *iocb, struct inode *inode, size_t bytes; struct buffer_head map_bh = { 0, }; struct blk_plug plug; + const struct iovec *iov = iov_iter_iovec(iter); + unsigned long nr_segs = iter->nr_segs; if (rw & WRITE) rw = WRITE_ODIRECT; @@ -1286,9 +1288,9 @@ out: ssize_t __blockdev_direct_IO(int rw, struct kiocb *iocb, struct inode *inode, - struct block_device *bdev, const struct iovec *iov, loff_t offset, - unsigned long nr_segs, get_block_t get_block, dio_iodone_t end_io, - dio_submit_t submit_io, int flags) + struct block_device *bdev, struct iov_iter *iter, loff_t offset, + get_block_t get_block, dio_iodone_t end_io, dio_submit_t submit_io, + int flags) { /* * The block device state is needed in the end to finally @@ -1302,9 +1304,8 @@ __blockdev_direct_IO(int rw, struct kiocb *iocb, struct inode *inode, prefetch(bdev->bd_queue); prefetch((char *)bdev->bd_queue + SMP_CACHE_BYTES); - return do_blockdev_direct_IO(rw, iocb, inode, bdev, iov, offset, - nr_segs, get_block, end_io, - submit_io, flags); + return do_blockdev_direct_IO(rw, iocb, inode, bdev, iter, offset, + get_block, end_io, submit_io, flags); } EXPORT_SYMBOL(__blockdev_direct_IO); diff --git a/fs/ext2/inode.c b/fs/ext2/inode.c index 43d72d0..b8933ec 100644 --- a/fs/ext2/inode.c +++ b/fs/ext2/inode.c @@ -846,18 +846,16 @@ static sector_t ext2_bmap(struct address_space *mapping, sector_t block) } static ssize_t -ext2_direct_IO(int rw, struct kiocb *iocb, const struct iovec *iov, - loff_t offset, unsigned long nr_segs) +ext2_direct_IO(int rw, struct kiocb *iocb, struct iov_iter *iter, loff_t offset) { struct file *file = iocb->ki_filp; struct address_space *mapping = file->f_mapping; struct inode *inode = mapping->host; ssize_t ret; - ret = blockdev_direct_IO(rw, iocb, inode, iov, offset, nr_segs, - ext2_get_block); + ret = blockdev_direct_IO(rw, iocb, inode, iter, offset, ext2_get_block); if (ret < 0 && (rw & WRITE)) - ext2_write_failed(mapping, offset + iov_length(iov, nr_segs)); + ext2_write_failed(mapping, offset + iov_iter_count(iter)); return ret; } diff --git a/fs/ext3/inode.c b/fs/ext3/inode.c index eac4f04..72804bd 100644 --- a/fs/ext3/inode.c +++ b/fs/ext3/inode.c @@ -1860,8 +1860,7 @@ static int ext3_releasepage(struct page *page, gfp_t wait) * VFS code falls back into buffered path in that case so we are safe. */ static ssize_t ext3_direct_IO(int rw, struct kiocb *iocb, - const struct iovec *iov, loff_t offset, - unsigned long nr_segs) + struct iov_iter *iter, loff_t offset) { struct file *file = iocb->ki_filp; struct inode *inode = file->f_mapping->host; @@ -1869,10 +1868,10 @@ static ssize_t ext3_direct_IO(int rw, struct kiocb *iocb, handle_t *handle; ssize_t ret; int orphan = 0; - size_t count = iov_length(iov, nr_segs); + size_t count = iov_iter_count(iter); int retries = 0; - trace_ext3_direct_IO_enter(inode, offset, iov_length(iov, nr_segs), rw); + trace_ext3_direct_IO_enter(inode, offset, count, rw); if (rw == WRITE) { loff_t final_size = offset + count; @@ -1896,15 +1895,14 @@ static ssize_t ext3_direct_IO(int rw, struct kiocb *iocb, } retry: - ret = blockdev_direct_IO(rw, iocb, inode, iov, offset, nr_segs, - ext3_get_block); + ret = blockdev_direct_IO(rw, iocb, inode, iter, offset, ext3_get_block); /* * In case of error extending write may have instantiated a few * blocks outside i_size. Trim these off again. */ if (unlikely((rw & WRITE) && ret < 0)) { loff_t isize = i_size_read(inode); - loff_t end = offset + iov_length(iov, nr_segs); + loff_t end = offset + count; if (end > isize) ext3_truncate_failed_direct_write(inode); @@ -1947,8 +1945,7 @@ retry: ret = err; } out: - trace_ext3_direct_IO_exit(inode, offset, - iov_length(iov, nr_segs), rw, ret); + trace_ext3_direct_IO_exit(inode, offset, count, rw, ret); return ret; } diff --git a/fs/ext4/ext4.h b/fs/ext4/ext4.h index 4a01ba3..b05618a 100644 --- a/fs/ext4/ext4.h +++ b/fs/ext4/ext4.h @@ -2104,8 +2104,7 @@ extern void ext4_da_update_reserve_space(struct inode *inode, extern int ext4_ind_map_blocks(handle_t *handle, struct inode *inode, struct ext4_map_blocks *map, int flags); extern ssize_t ext4_ind_direct_IO(int rw, struct kiocb *iocb, - const struct iovec *iov, loff_t offset, - unsigned long nr_segs); + struct iov_iter *iter, loff_t offset); extern int ext4_ind_calc_metadata_amount(struct inode *inode, sector_t lblock); extern int ext4_ind_trans_blocks(struct inode *inode, int nrblocks, int chunk); extern void ext4_ind_truncate(struct inode *inode); diff --git a/fs/ext4/indirect.c b/fs/ext4/indirect.c index 21de123..de8e9de 100644 --- a/fs/ext4/indirect.c +++ b/fs/ext4/indirect.c @@ -775,8 +775,7 @@ out: * VFS code falls back into buffered path in that case so we are safe. */ ssize_t ext4_ind_direct_IO(int rw, struct kiocb *iocb, - const struct iovec *iov, loff_t offset, - unsigned long nr_segs) + struct iov_iter *iter, loff_t offset) { struct file *file = iocb->ki_filp; struct inode *inode = file->f_mapping->host; @@ -784,7 +783,7 @@ ssize_t ext4_ind_direct_IO(int rw, struct kiocb *iocb, handle_t *handle; ssize_t ret; int orphan = 0; - size_t count = iov_length(iov, nr_segs); + size_t count = iov_iter_count(iter); int retries = 0; if (rw == WRITE) { @@ -828,18 +827,17 @@ retry: goto locked; } ret = __blockdev_direct_IO(rw, iocb, inode, - inode->i_sb->s_bdev, iov, - offset, nr_segs, - ext4_get_block, NULL, NULL, 0); + inode->i_sb->s_bdev, iter, + offset, ext4_get_block, NULL, NULL, 0); inode_dio_done(inode); } else { locked: - ret = blockdev_direct_IO(rw, iocb, inode, iov, - offset, nr_segs, ext4_get_block); + ret = blockdev_direct_IO(rw, iocb, inode, iter, + offset, ext4_get_block); if (unlikely((rw & WRITE) && ret < 0)) { loff_t isize = i_size_read(inode); - loff_t end = offset + iov_length(iov, nr_segs); + loff_t end = offset + iov_iter_count(iter); if (end > isize) ext4_truncate_failed_write(inode); diff --git a/fs/ext4/inode.c b/fs/ext4/inode.c index f513f3d..c820273 100644 --- a/fs/ext4/inode.c +++ b/fs/ext4/inode.c @@ -2999,13 +2999,12 @@ out: * */ static ssize_t ext4_ext_direct_IO(int rw, struct kiocb *iocb, - const struct iovec *iov, loff_t offset, - unsigned long nr_segs) + struct iov_iter *iter, loff_t offset) { struct file *file = iocb->ki_filp; struct inode *inode = file->f_mapping->host; ssize_t ret; - size_t count = iov_length(iov, nr_segs); + size_t count = iov_iter_count(iter); int overwrite = 0; get_block_t *get_block_func = NULL; int dio_flags = 0; @@ -3013,7 +3012,7 @@ static ssize_t ext4_ext_direct_IO(int rw, struct kiocb *iocb, /* Use the old path for reads and writes beyond i_size. */ if (rw != WRITE || final_size > inode->i_size) - return ext4_ind_direct_IO(rw, iocb, iov, offset, nr_segs); + return ext4_ind_direct_IO(rw, iocb, iter, offset); BUG_ON(iocb->private == NULL); @@ -3071,8 +3070,8 @@ static ssize_t ext4_ext_direct_IO(int rw, struct kiocb *iocb, dio_flags = DIO_LOCKING; } ret = __blockdev_direct_IO(rw, iocb, inode, - inode->i_sb->s_bdev, iov, - offset, nr_segs, + inode->i_sb->s_bdev, iter, + offset, get_block_func, ext4_end_io_dio, NULL, @@ -3123,8 +3122,7 @@ retake_lock: } static ssize_t ext4_direct_IO(int rw, struct kiocb *iocb, - const struct iovec *iov, loff_t offset, - unsigned long nr_segs) + struct iov_iter *iter, loff_t offset) { struct file *file = iocb->ki_filp; struct inode *inode = file->f_mapping->host; @@ -3140,13 +3138,12 @@ static ssize_t ext4_direct_IO(int rw, struct kiocb *iocb, if (ext4_has_inline_data(inode)) return 0; - trace_ext4_direct_IO_enter(inode, offset, iov_length(iov, nr_segs), rw); + trace_ext4_direct_IO_enter(inode, offset, iov_iter_count(iter), rw); if (ext4_test_inode_flag(inode, EXT4_INODE_EXTENTS)) - ret = ext4_ext_direct_IO(rw, iocb, iov, offset, nr_segs); + ret = ext4_ext_direct_IO(rw, iocb, iter, offset); else - ret = ext4_ind_direct_IO(rw, iocb, iov, offset, nr_segs); - trace_ext4_direct_IO_exit(inode, offset, - iov_length(iov, nr_segs), rw, ret); + ret = ext4_ind_direct_IO(rw, iocb, iter, offset); + trace_ext4_direct_IO_exit(inode, offset, iov_iter_count(iter), rw, ret); return ret; } diff --git a/fs/f2fs/data.c b/fs/f2fs/data.c index d0ed4ba..1531379 100644 --- a/fs/f2fs/data.c +++ b/fs/f2fs/data.c @@ -655,7 +655,7 @@ static int f2fs_write_begin(struct file *file, struct address_space *mapping, } static ssize_t f2fs_direct_IO(int rw, struct kiocb *iocb, - const struct iovec *iov, loff_t offset, unsigned long nr_segs) + struct iov_iter *iter, loff_t offset) { struct file *file = iocb->ki_filp; struct inode *inode = file->f_mapping->host; @@ -664,7 +664,7 @@ static ssize_t f2fs_direct_IO(int rw, struct kiocb *iocb, return 0; /* Needs synchronization with the cleaner */ - return blockdev_direct_IO(rw, iocb, inode, iov, offset, nr_segs, + return blockdev_direct_IO(rw, iocb, inode, iter, offset, get_data_block_ro); } diff --git a/fs/fat/inode.c b/fs/fat/inode.c index d1d502a..300d883 100644 --- a/fs/fat/inode.c +++ b/fs/fat/inode.c @@ -186,8 +186,7 @@ static int fat_write_end(struct file *file, struct address_space *mapping, } static ssize_t fat_direct_IO(int rw, struct kiocb *iocb, - const struct iovec *iov, - loff_t offset, unsigned long nr_segs) + struct iov_iter *iter, loff_t offset) { struct file *file = iocb->ki_filp; struct address_space *mapping = file->f_mapping; @@ -204,7 +203,7 @@ static ssize_t fat_direct_IO(int rw, struct kiocb *iocb, * * Return 0, and fallback to normal buffered write. */ - loff_t size = offset + iov_length(iov, nr_segs); + loff_t size = offset + iov_iter_count(iter); if (MSDOS_I(inode)->mmu_private < size) return 0; } @@ -213,10 +212,9 @@ static ssize_t fat_direct_IO(int rw, struct kiocb *iocb, * FAT need to use the DIO_LOCKING for avoiding the race * condition of fat_get_block() and ->truncate(). */ - ret = blockdev_direct_IO(rw, iocb, inode, iov, offset, nr_segs, - fat_get_block); + ret = blockdev_direct_IO(rw, iocb, inode, iter, offset, fat_get_block); if (ret < 0 && (rw & WRITE)) - fat_write_failed(mapping, offset + iov_length(iov, nr_segs)); + fat_write_failed(mapping, offset + iov_iter_count(iter)); return ret; } diff --git a/fs/fuse/cuse.c b/fs/fuse/cuse.c index 06b5e08..53dc8d8 100644 --- a/fs/fuse/cuse.c +++ b/fs/fuse/cuse.c @@ -93,8 +93,11 @@ static ssize_t cuse_read(struct file *file, char __user *buf, size_t count, { loff_t pos = 0; struct iovec iov = { .iov_base = buf, .iov_len = count }; + struct iov_iter ii; - return fuse_direct_io(file, &iov, 1, count, &pos, 0); + iov_iter_init(&ii, &iov, 1, count, 0); + + return fuse_direct_io(file, &ii, count, &pos, 0); } static ssize_t cuse_write(struct file *file, const char __user *buf, @@ -102,12 +105,15 @@ static ssize_t cuse_write(struct file *file, const char __user *buf, { loff_t pos = 0; struct iovec iov = { .iov_base = (void __user *)buf, .iov_len = count }; + struct iov_iter ii; + + iov_iter_init(&ii, &iov, 1, count, 0); /* * No locking or generic_write_checks(), the server is * responsible for locking and sanity checks. */ - return fuse_direct_io(file, &iov, 1, count, &pos, 1); + return fuse_direct_io(file, &ii, count, &pos, 1); } static int cuse_open(struct inode *inode, struct file *file) diff --git a/fs/fuse/file.c b/fs/fuse/file.c index a359fe0..89855c8 100644 --- a/fs/fuse/file.c +++ b/fs/fuse/file.c @@ -1151,9 +1151,8 @@ static inline int fuse_iter_npages(const struct iov_iter *ii_p) return min(npages, FUSE_MAX_PAGES_PER_REQ); } -ssize_t fuse_direct_io(struct file *file, const struct iovec *iov, - unsigned long nr_segs, size_t count, loff_t *ppos, - int write) +ssize_t fuse_direct_io(struct file *file, struct iov_iter *ii, + size_t count, loff_t *ppos, int write) { struct fuse_file *ff = file->private_data; struct fuse_conn *fc = ff->fc; @@ -1161,11 +1160,8 @@ ssize_t fuse_direct_io(struct file *file, const struct iovec *iov, loff_t pos = *ppos; ssize_t res = 0; struct fuse_req *req; - struct iov_iter ii; - - iov_iter_init(&ii, iov, nr_segs, count, 0); - req = fuse_get_req(fc, fuse_iter_npages(&ii)); + req = fuse_get_req(fc, fuse_iter_npages(ii)); if (IS_ERR(req)) return PTR_ERR(req); @@ -1173,7 +1169,7 @@ ssize_t fuse_direct_io(struct file *file, const struct iovec *iov, size_t nres; fl_owner_t owner = current->files; size_t nbytes = min(count, nmax); - int err = fuse_get_user_pages(req, &ii, &nbytes, write); + int err = fuse_get_user_pages(req, ii, &nbytes, write); if (err) { res = err; break; @@ -1200,7 +1196,7 @@ ssize_t fuse_direct_io(struct file *file, const struct iovec *iov, break; if (count) { fuse_put_request(fc, req); - req = fuse_get_req(fc, fuse_iter_npages(&ii)); + req = fuse_get_req(fc, fuse_iter_npages(ii)); if (IS_ERR(req)) break; } @@ -1214,8 +1210,8 @@ ssize_t fuse_direct_io(struct file *file, const struct iovec *iov, } EXPORT_SYMBOL_GPL(fuse_direct_io); -static ssize_t __fuse_direct_read(struct file *file, const struct iovec *iov, - unsigned long nr_segs, loff_t *ppos) +static ssize_t __fuse_direct_read(struct file *file, struct iov_iter *ii, + loff_t *ppos) { ssize_t res; struct inode *inode = file_inode(file); @@ -1223,8 +1219,7 @@ static ssize_t __fuse_direct_read(struct file *file, const struct iovec *iov, if (is_bad_inode(inode)) return -EIO; - res = fuse_direct_io(file, iov, nr_segs, iov_length(iov, nr_segs), - ppos, 0); + res = fuse_direct_io(file, ii, iov_iter_count(ii), ppos, 0); fuse_invalidate_attr(inode); @@ -1235,19 +1230,23 @@ static ssize_t fuse_direct_read(struct file *file, char __user *buf, size_t count, loff_t *ppos) { struct iovec iov = { .iov_base = buf, .iov_len = count }; - return __fuse_direct_read(file, &iov, 1, ppos); + struct iov_iter ii; + + iov_iter_init(&ii, &iov, 1, count, 0); + + return __fuse_direct_read(file, &ii, ppos); } -static ssize_t __fuse_direct_write(struct file *file, const struct iovec *iov, - unsigned long nr_segs, loff_t *ppos) +static ssize_t __fuse_direct_write(struct file *file, struct iov_iter *ii, + loff_t *ppos) { struct inode *inode = file_inode(file); - size_t count = iov_length(iov, nr_segs); + size_t count = iov_iter_count(ii); ssize_t res; res = generic_write_checks(file, ppos, &count, 0); if (!res) { - res = fuse_direct_io(file, iov, nr_segs, count, ppos, 1); + res = fuse_direct_io(file, ii, count, ppos, 1); if (res > 0) fuse_write_update_size(inode, *ppos); } @@ -1261,15 +1260,18 @@ static ssize_t fuse_direct_write(struct file *file, const char __user *buf, size_t count, loff_t *ppos) { struct iovec iov = { .iov_base = (void __user *)buf, .iov_len = count }; + struct iov_iter ii; struct inode *inode = file_inode(file); ssize_t res; if (is_bad_inode(inode)) return -EIO; + iov_iter_init(&ii, &iov, 1, count, 0); + /* Don't allow parallel writes to the same file */ mutex_lock(&inode->i_mutex); - res = __fuse_direct_write(file, &iov, 1, ppos); + res = __fuse_direct_write(file, &ii, ppos); mutex_unlock(&inode->i_mutex); return res; @@ -2219,8 +2221,8 @@ int fuse_notify_poll_wakeup(struct fuse_conn *fc, } static ssize_t -fuse_direct_IO(int rw, struct kiocb *iocb, const struct iovec *iov, - loff_t offset, unsigned long nr_segs) +fuse_direct_IO(int rw, struct kiocb *iocb, struct iov_iter *ii, + loff_t offset) { ssize_t ret = 0; struct file *file = NULL; @@ -2230,9 +2232,9 @@ fuse_direct_IO(int rw, struct kiocb *iocb, const struct iovec *iov, pos = offset; if (rw == WRITE) - ret = __fuse_direct_write(file, iov, nr_segs, &pos); + ret = __fuse_direct_write(file, ii, &pos); else - ret = __fuse_direct_read(file, iov, nr_segs, &pos); + ret = __fuse_direct_read(file, ii, &pos); return ret; } diff --git a/fs/fuse/fuse_i.h b/fs/fuse/fuse_i.h index 6aeba86..1b5e2cb 100644 --- a/fs/fuse/fuse_i.h +++ b/fs/fuse/fuse_i.h @@ -823,9 +823,8 @@ int fuse_reverse_inval_entry(struct super_block *sb, u64 parent_nodeid, int fuse_do_open(struct fuse_conn *fc, u64 nodeid, struct file *file, bool isdir); -ssize_t fuse_direct_io(struct file *file, const struct iovec *iov, - unsigned long nr_segs, size_t count, loff_t *ppos, - int write); +ssize_t fuse_direct_io(struct file *file, struct iov_iter *ii, + size_t count, loff_t *ppos, int write); long fuse_do_ioctl(struct file *file, unsigned int cmd, unsigned long arg, unsigned int flags); long fuse_ioctl_common(struct file *file, unsigned int cmd, diff --git a/fs/gfs2/aops.c b/fs/gfs2/aops.c index 371bd14..a17f676 100644 --- a/fs/gfs2/aops.c +++ b/fs/gfs2/aops.c @@ -994,8 +994,7 @@ static int gfs2_ok_for_dio(struct gfs2_inode *ip, int rw, loff_t offset) static ssize_t gfs2_direct_IO(int rw, struct kiocb *iocb, - const struct iovec *iov, loff_t offset, - unsigned long nr_segs) + struct iov_iter *iter, loff_t offset) { struct file *file = iocb->ki_filp; struct inode *inode = file->f_mapping->host; @@ -1019,8 +1018,8 @@ static ssize_t gfs2_direct_IO(int rw, struct kiocb *iocb, if (rv != 1) goto out; /* dio not valid, fall back to buffered i/o */ - rv = __blockdev_direct_IO(rw, iocb, inode, inode->i_sb->s_bdev, iov, - offset, nr_segs, gfs2_get_block_direct, + rv = __blockdev_direct_IO(rw, iocb, inode, inode->i_sb->s_bdev, iter, + offset, gfs2_get_block_direct, NULL, NULL, 0); out: gfs2_glock_dq(&gh); diff --git a/fs/hfs/inode.c b/fs/hfs/inode.c index a9d60d4..a129743 100644 --- a/fs/hfs/inode.c +++ b/fs/hfs/inode.c @@ -125,15 +125,14 @@ static int hfs_releasepage(struct page *page, gfp_t mask) } static ssize_t hfs_direct_IO(int rw, struct kiocb *iocb, - const struct iovec *iov, loff_t offset, unsigned long nr_segs) + struct iov_iter *iter, loff_t offset) { struct file *file = iocb->ki_filp; struct address_space *mapping = file->f_mapping; struct inode *inode = file_inode(file)->i_mapping->host; ssize_t ret; - ret = blockdev_direct_IO(rw, iocb, inode, iov, offset, nr_segs, - hfs_get_block); + ret = blockdev_direct_IO(rw, iocb, inode, iter, offset, hfs_get_block); /* * In case of error extending write may have instantiated a few @@ -141,7 +140,7 @@ static ssize_t hfs_direct_IO(int rw, struct kiocb *iocb, */ if (unlikely((rw & WRITE) && ret < 0)) { loff_t isize = i_size_read(inode); - loff_t end = offset + iov_length(iov, nr_segs); + loff_t end = offset + iov_iter_count(iter); if (end > isize) hfs_write_failed(mapping, end); diff --git a/fs/hfsplus/inode.c b/fs/hfsplus/inode.c index cdd181d..f082b4d 100644 --- a/fs/hfsplus/inode.c +++ b/fs/hfsplus/inode.c @@ -122,14 +122,14 @@ static int hfsplus_releasepage(struct page *page, gfp_t mask) } static ssize_t hfsplus_direct_IO(int rw, struct kiocb *iocb, - const struct iovec *iov, loff_t offset, unsigned long nr_segs) + struct iov_iter *iter, loff_t offset) { struct file *file = iocb->ki_filp; struct address_space *mapping = file->f_mapping; struct inode *inode = file_inode(file)->i_mapping->host; ssize_t ret; - ret = blockdev_direct_IO(rw, iocb, inode, iov, offset, nr_segs, + ret = blockdev_direct_IO(rw, iocb, inode, iter, offset, hfsplus_get_block); /* @@ -138,7 +138,7 @@ static ssize_t hfsplus_direct_IO(int rw, struct kiocb *iocb, */ if (unlikely((rw & WRITE) && ret < 0)) { loff_t isize = i_size_read(inode); - loff_t end = offset + iov_length(iov, nr_segs); + loff_t end = offset + iov_iter_count(iter); if (end > isize) hfsplus_write_failed(mapping, end); diff --git a/fs/jfs/inode.c b/fs/jfs/inode.c index 1781f06..c65977f 100644 --- a/fs/jfs/inode.c +++ b/fs/jfs/inode.c @@ -331,15 +331,14 @@ static sector_t jfs_bmap(struct address_space *mapping, sector_t block) } static ssize_t jfs_direct_IO(int rw, struct kiocb *iocb, - const struct iovec *iov, loff_t offset, unsigned long nr_segs) + struct iov_iter *iter, loff_t offset) { struct file *file = iocb->ki_filp; struct address_space *mapping = file->f_mapping; struct inode *inode = file->f_mapping->host; ssize_t ret; - ret = blockdev_direct_IO(rw, iocb, inode, iov, offset, nr_segs, - jfs_get_block); + ret = blockdev_direct_IO(rw, iocb, inode, iter, offset, jfs_get_block); /* * In case of error extending write may have instantiated a few @@ -347,7 +346,7 @@ static ssize_t jfs_direct_IO(int rw, struct kiocb *iocb, */ if (unlikely((rw & WRITE) && ret < 0)) { loff_t isize = i_size_read(inode); - loff_t end = offset + iov_length(iov, nr_segs); + loff_t end = offset + iov_iter_count(iter); if (end > isize) jfs_write_failed(mapping, end); diff --git a/fs/nfs/direct.c b/fs/nfs/direct.c index 0bd7a55..bceb47e 100644 --- a/fs/nfs/direct.c +++ b/fs/nfs/direct.c @@ -112,7 +112,7 @@ static inline int put_dreq(struct nfs_direct_req *dreq) * nfs_direct_IO - NFS address space operation for direct I/O * @rw: direction (read or write) * @iocb: target I/O control block - * @iov: array of vectors that define I/O buffer + * @iter: array of vectors that define I/O buffer * @pos: offset in file to begin the operation * @nr_segs: size of iovec array * @@ -121,22 +121,25 @@ static inline int put_dreq(struct nfs_direct_req *dreq) * shunt off direct read and write requests before the VFS gets them, * so this method is only ever called for swap. */ -ssize_t nfs_direct_IO(int rw, struct kiocb *iocb, const struct iovec *iov, loff_t pos, unsigned long nr_segs) +ssize_t nfs_direct_IO(int rw, struct kiocb *iocb, struct iov_iter *iter, + loff_t pos) { #ifndef CONFIG_NFS_SWAP dprintk("NFS: nfs_direct_IO (%s) off/no(%Ld/%lu) EINVAL\n", iocb->ki_filp->f_path.dentry->d_name.name, - (long long) pos, nr_segs); + (long long) pos, iter->nr_segs); return -EINVAL; #else + const struct iovec *iov = iov_iter_iovec(iter); + VM_BUG_ON(iocb->ki_left != PAGE_SIZE); VM_BUG_ON(iocb->ki_nbytes != PAGE_SIZE); if (rw == READ || rw == KERNEL_READ) - return nfs_file_direct_read(iocb, iov, nr_segs, pos, + return nfs_file_direct_read(iocb, iov, iter->nr_segs, pos, rw == READ ? true : false); - return nfs_file_direct_write(iocb, iov, nr_segs, pos, + return nfs_file_direct_write(iocb, iov, iter->nr_segs, pos, rw == WRITE ? true : false); #endif /* CONFIG_NFS_SWAP */ } diff --git a/fs/nilfs2/inode.c b/fs/nilfs2/inode.c index 1e92930..3b5d64d 100644 --- a/fs/nilfs2/inode.c +++ b/fs/nilfs2/inode.c @@ -262,8 +262,8 @@ static int nilfs_write_end(struct file *file, struct address_space *mapping, } static ssize_t -nilfs_direct_IO(int rw, struct kiocb *iocb, const struct iovec *iov, - loff_t offset, unsigned long nr_segs) +nilfs_direct_IO(int rw, struct kiocb *iocb, struct iov_iter *iter, + loff_t offset) { struct file *file = iocb->ki_filp; struct address_space *mapping = file->f_mapping; @@ -274,7 +274,7 @@ nilfs_direct_IO(int rw, struct kiocb *iocb, const struct iovec *iov, return 0; /* Needs synchronization with the cleaner */ - size = blockdev_direct_IO(rw, iocb, inode, iov, offset, nr_segs, + size = blockdev_direct_IO(rw, iocb, inode, iter, offset, nilfs_get_block); /* @@ -283,7 +283,7 @@ nilfs_direct_IO(int rw, struct kiocb *iocb, const struct iovec *iov, */ if (unlikely((rw & WRITE) && size < 0)) { loff_t isize = i_size_read(inode); - loff_t end = offset + iov_length(iov, nr_segs); + loff_t end = offset + iov_iter_count(iter); if (end > isize) nilfs_write_failed(mapping, end); diff --git a/fs/ocfs2/aops.c b/fs/ocfs2/aops.c index 20dfec7..6406dd9 100644 --- a/fs/ocfs2/aops.c +++ b/fs/ocfs2/aops.c @@ -621,9 +621,8 @@ static int ocfs2_releasepage(struct page *page, gfp_t wait) static ssize_t ocfs2_direct_IO(int rw, struct kiocb *iocb, - const struct iovec *iov, - loff_t offset, - unsigned long nr_segs) + struct iov_iter *iter, + loff_t offset) { struct file *file = iocb->ki_filp; struct inode *inode = file_inode(file)->i_mapping->host; @@ -640,8 +639,7 @@ static ssize_t ocfs2_direct_IO(int rw, return 0; return __blockdev_direct_IO(rw, iocb, inode, inode->i_sb->s_bdev, - iov, offset, nr_segs, - ocfs2_direct_IO_get_blocks, + iter, offset, ocfs2_direct_IO_get_blocks, ocfs2_dio_end_io, NULL, 0); } diff --git a/fs/reiserfs/inode.c b/fs/reiserfs/inode.c index 77d6d47..dcfd260 100644 --- a/fs/reiserfs/inode.c +++ b/fs/reiserfs/inode.c @@ -3068,14 +3068,13 @@ static int reiserfs_releasepage(struct page *page, gfp_t unused_gfp_flags) /* We thank Mingming Cao for helping us understand in great detail what to do in this section of the code. */ static ssize_t reiserfs_direct_IO(int rw, struct kiocb *iocb, - const struct iovec *iov, loff_t offset, - unsigned long nr_segs) + struct iov_iter *iter, loff_t offset) { struct file *file = iocb->ki_filp; struct inode *inode = file->f_mapping->host; ssize_t ret; - ret = blockdev_direct_IO(rw, iocb, inode, iov, offset, nr_segs, + ret = blockdev_direct_IO(rw, iocb, inode, iter, offset, reiserfs_get_blocks_direct_io); /* @@ -3084,7 +3083,7 @@ static ssize_t reiserfs_direct_IO(int rw, struct kiocb *iocb, */ if (unlikely((rw & WRITE) && ret < 0)) { loff_t isize = i_size_read(inode); - loff_t end = offset + iov_length(iov, nr_segs); + loff_t end = offset + iov_iter_count(iter); if ((end > isize) && inode_newsize_ok(inode, isize) == 0) { truncate_setsize(inode, isize); diff --git a/fs/udf/file.c b/fs/udf/file.c index 29569dd..339df8b 100644 --- a/fs/udf/file.c +++ b/fs/udf/file.c @@ -119,8 +119,7 @@ static int udf_adinicb_write_end(struct file *file, } static ssize_t udf_adinicb_direct_IO(int rw, struct kiocb *iocb, - const struct iovec *iov, - loff_t offset, unsigned long nr_segs) + struct iov_iter *iter, loff_t offset) { /* Fallback to buffered I/O. */ return 0; diff --git a/fs/udf/inode.c b/fs/udf/inode.c index b6d15d3..fad32d5 100644 --- a/fs/udf/inode.c +++ b/fs/udf/inode.c @@ -216,19 +216,17 @@ static int udf_write_begin(struct file *file, struct address_space *mapping, return ret; } -static ssize_t udf_direct_IO(int rw, struct kiocb *iocb, - const struct iovec *iov, - loff_t offset, unsigned long nr_segs) +static ssize_t udf_direct_IO(int rw, struct kiocb *iocb, struct iov_iter *iter, + loff_t offset) { struct file *file = iocb->ki_filp; struct address_space *mapping = file->f_mapping; struct inode *inode = mapping->host; ssize_t ret; - ret = blockdev_direct_IO(rw, iocb, inode, iov, offset, nr_segs, - udf_get_block); + ret = blockdev_direct_IO(rw, iocb, inode, iter, offset, udf_get_block); if (unlikely(ret < 0 && (rw & WRITE))) - udf_write_failed(mapping, offset + iov_length(iov, nr_segs)); + udf_write_failed(mapping, offset + iov_iter_count(iter)); return ret; } diff --git a/fs/xfs/xfs_aops.c b/fs/xfs/xfs_aops.c index c24ce0e..08e6c93 100644 --- a/fs/xfs/xfs_aops.c +++ b/fs/xfs/xfs_aops.c @@ -1410,9 +1410,8 @@ STATIC ssize_t xfs_vm_direct_IO( int rw, struct kiocb *iocb, - const struct iovec *iov, - loff_t offset, - unsigned long nr_segs) + struct iov_iter *iter, + loff_t offset) { struct inode *inode = iocb->ki_filp->f_mapping->host; struct block_device *bdev = xfs_find_bdev_for_inode(inode); @@ -1420,7 +1419,7 @@ xfs_vm_direct_IO( ssize_t ret; if (rw & WRITE) { - size_t size = iov_length(iov, nr_segs); + size_t size = iov_iter_count(iter); /* * We cannot preallocate a size update transaction here as we @@ -1432,15 +1431,13 @@ xfs_vm_direct_IO( if (offset + size > XFS_I(inode)->i_d.di_size) ioend->io_isdirect = 1; - ret = __blockdev_direct_IO(rw, iocb, inode, bdev, iov, - offset, nr_segs, + ret = __blockdev_direct_IO(rw, iocb, inode, bdev, iter, offset, xfs_get_blocks_direct, xfs_end_io_direct_write, NULL, 0); if (ret != -EIOCBQUEUED && iocb->private) goto out_destroy_ioend; } else { - ret = __blockdev_direct_IO(rw, iocb, inode, bdev, iov, - offset, nr_segs, + ret = __blockdev_direct_IO(rw, iocb, inode, bdev, iter, offset, xfs_get_blocks_direct, NULL, NULL, 0); } diff --git a/include/linux/fs.h b/include/linux/fs.h index 53a1016..e5e881e 100644 --- a/include/linux/fs.h +++ b/include/linux/fs.h @@ -461,8 +461,8 @@ struct address_space_operations { void (*invalidatepage) (struct page *, unsigned long); int (*releasepage) (struct page *, gfp_t); void (*freepage)(struct page *); - ssize_t (*direct_IO)(int, struct kiocb *, const struct iovec *iov, - loff_t offset, unsigned long nr_segs); + ssize_t (*direct_IO)(int, struct kiocb *, struct iov_iter *iter, + loff_t offset); int (*get_xip_mem)(struct address_space *, pgoff_t, int, void **, unsigned long *); /* @@ -2544,16 +2544,16 @@ enum { void dio_end_io(struct bio *bio, int error); ssize_t __blockdev_direct_IO(int rw, struct kiocb *iocb, struct inode *inode, - struct block_device *bdev, const struct iovec *iov, loff_t offset, - unsigned long nr_segs, get_block_t get_block, dio_iodone_t end_io, - dio_submit_t submit_io, int flags); + struct block_device *bdev, struct iov_iter *iter, loff_t offset, + get_block_t get_block, dio_iodone_t end_io, dio_submit_t submit_io, + int flags); static inline ssize_t blockdev_direct_IO(int rw, struct kiocb *iocb, - struct inode *inode, const struct iovec *iov, loff_t offset, - unsigned long nr_segs, get_block_t get_block) + struct inode *inode, struct iov_iter *iter, loff_t offset, + get_block_t get_block) { - return __blockdev_direct_IO(rw, iocb, inode, inode->i_sb->s_bdev, iov, - offset, nr_segs, get_block, NULL, NULL, + return __blockdev_direct_IO(rw, iocb, inode, inode->i_sb->s_bdev, iter, + offset, get_block, NULL, NULL, DIO_LOCKING | DIO_SKIP_HOLES); } #endif diff --git a/include/linux/nfs_fs.h b/include/linux/nfs_fs.h index 1cc2568..4913e3c 100644 --- a/include/linux/nfs_fs.h +++ b/include/linux/nfs_fs.h @@ -444,8 +444,7 @@ extern int nfs3_removexattr (struct dentry *, const char *name); /* * linux/fs/nfs/direct.c */ -extern ssize_t nfs_direct_IO(int, struct kiocb *, const struct iovec *, loff_t, - unsigned long); +extern ssize_t nfs_direct_IO(int, struct kiocb *, struct iov_iter *, loff_t); extern ssize_t nfs_file_direct_read(struct kiocb *iocb, const struct iovec *iov, unsigned long nr_segs, loff_t pos, bool uio); diff --git a/mm/filemap.c b/mm/filemap.c index 0798e25..28eeb6c 100644 --- a/mm/filemap.c +++ b/mm/filemap.c @@ -1414,11 +1414,15 @@ generic_file_aio_read(struct kiocb *iocb, const struct iovec *iov, goto out; /* skip atime */ size = i_size_read(inode); if (pos < size) { + size_t bytes = iov_length(iov, nr_segs); retval = filemap_write_and_wait_range(mapping, pos, - pos + iov_length(iov, nr_segs) - 1); + pos + bytes - 1); if (!retval) { + struct iov_iter iter; + + iov_iter_init(&iter, iov, nr_segs, bytes, 0); retval = mapping->a_ops->direct_IO(READ, iocb, - iov, pos, nr_segs); + &iter, pos); } if (retval > 0) { *ppos = pos + retval; @@ -2043,6 +2047,7 @@ generic_file_direct_write(struct kiocb *iocb, const struct iovec *iov, ssize_t written; size_t write_len; pgoff_t end; + struct iov_iter iter; if (count != ocount) *nr_segs = iov_shorten((struct iovec *)iov, *nr_segs, count); @@ -2074,7 +2079,9 @@ generic_file_direct_write(struct kiocb *iocb, const struct iovec *iov, } } - written = mapping->a_ops->direct_IO(WRITE, iocb, iov, pos, *nr_segs); + iov_iter_init(&iter, iov, *nr_segs, write_len, 0); + + written = mapping->a_ops->direct_IO(WRITE, iocb, &iter, pos); /* * Finally, try again to invalidate clean pages which might have been diff --git a/mm/page_io.c b/mm/page_io.c index c535d39..bfc8d4f 100644 --- a/mm/page_io.c +++ b/mm/page_io.c @@ -209,6 +209,9 @@ int swap_writepage(struct page *page, struct writeback_control *wbc) .iov_base = kmap(page), .iov_len = PAGE_SIZE, }; + struct iov_iter iter; + + iov_iter_init(&iter, &iov, 1, PAGE_SIZE, 0); init_sync_kiocb(&kiocb, swap_file); kiocb.ki_pos = page_file_offset(page); @@ -216,9 +219,8 @@ int swap_writepage(struct page *page, struct writeback_control *wbc) kiocb.ki_nbytes = PAGE_SIZE; unlock_page(page); - ret = mapping->a_ops->direct_IO(KERNEL_WRITE, - &kiocb, &iov, - kiocb.ki_pos, 1); + ret = mapping->a_ops->direct_IO(KERNEL_WRITE, &kiocb, &iter, + kiocb.ki_pos); kunmap(page); if (ret == PAGE_SIZE) { count_vm_event(PSWPOUT); -- 1.8.1.5 From tutu@euro.ubbcluj.ro Fri Mar 8 17:28:31 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: linux-xfs@oss.sgi.com Delivered-To: linux-xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id C975A7F81 for ; Fri, 8 Mar 2013 17:28:31 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay1.corp.sgi.com (Postfix) with ESMTP id B1EDC8F8059 for ; Fri, 8 Mar 2013 15:28:28 -0800 (PST) X-ASG-Debug-ID: 1362785306-04cb6c2b022f1680001-w1Z2WR Received: from mx.ubbcluj.ro (mx.UBBCluj.Ro [193.0.225.17]) by cuda.sgi.com with ESMTP id XVgntEBDCq0YUzpR; Fri, 08 Mar 2013 15:28:26 -0800 (PST) X-Barracuda-Envelope-From: tutu@euro.ubbcluj.ro X-Barracuda-Apparent-Source-IP: 193.0.225.17 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AnsiAINzOlHB5xQG/2dsb2JhbAApFgSCQAiFFrYJiFAWcwGCJEEBW4EvAR2FZYIdBAgumlSXYYkrjUshhGcDgSGVMoEehEiFboNSgUyDDIFw X-IronPort-AV: E=Sophos;i="4.84,810,1355090400"; d="scan'208";a="6187010" Received: from euro.ubbcluj.ro ([193.231.20.6]) by smtp.ubbcluj.ro with ESMTP; 09 Mar 2013 01:28:26 +0200 Received: from euro.ubbcluj.ro (localhost [127.0.0.1]) by euro.ubbcluj.ro (8.14.3/8.14.3) with ESMTP id r28NSIa9056485; Sat, 9 Mar 2013 01:28:18 +0200 (EET) (envelope-from tutu@euro.ubbcluj.ro) Received: from 65.49.14.149 by euro.ubbcluj.ro with HTTP; Sat, 9 Mar 2013 01:28:28 +0200 Message-ID: Date: Sat, 9 Mar 2013 01:28:28 +0200 Subject: Webmail Aviso cuenta From: "Del administrador del sistema" X-ASG-Orig-Subj: Webmail Aviso cuenta User-Agent: SquirrelMail/1.4.22 MIME-Version: 1.0 Content-Type: text/plain;charset=iso-8859-1 Content-Transfer-Encoding: 8bit X-Priority: 3 (Normal) Importance: Normal To: undisclosed-recipients:; X-Barracuda-Connect: mx.UBBCluj.Ro[193.0.225.17] X-Barracuda-Start-Time: 1362785306 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124649 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -- Webmail Aviso cuenta Este correo es de servicio de correo web, deseamos sealar a su atencin la Condicin DE SU CUENTA email que acabo de dar cuenta de que ha superado el lmite de la base de datos de correo electrnico de la cuota de 500 MB y su IP direccin de correo electrnico est causando el conflicto, ya que se ha accedido en la ubicacin del servidor diferente. Es necesario actualizar y ampliar su lmite de cuota de correo electrnico antes de que pueda seguir utilizando su correo electrnico. Actualice su lmite de cuota de correo electrnico a un 2,6 GB, utilice el siguiente enlace web: ========> http://adminsistema.yolasite.com/contact-us.php Si no hace esto dar lugar a la desactivacin por correo electrnico dentro de 72 horas Gracias por su comprensin. Derechos de autor 2013 Tcnico de Actualizacin de From david@fromorbit.com Sat Mar 9 03:01:07 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 89DAB7F87 for ; Sat, 9 Mar 2013 03:01:07 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay3.corp.sgi.com (Postfix) with ESMTP id 172A7AC001 for ; Sat, 9 Mar 2013 01:01:06 -0800 (PST) X-ASG-Debug-ID: 1362819661-04cbb07dbf32e6e0001-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id XKygqm80xA1Bt8le for ; Sat, 09 Mar 2013 01:01:02 -0800 (PST) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AlsaAPn5OlF5LH9g/2dsb2JhbABCh0G4B4UWAQIBgV4XdIIsAQEFOhwjEAgDDgoJJQ8FJQMhE4gSu1QVjXYYH0oHg0ADllOJaIcMgx4 Received: from ppp121-44-127-96.lns20.syd6.internode.on.net (HELO dastard) ([121.44.127.96]) by ipmail05.adl6.internode.on.net with ESMTP; 09 Mar 2013 19:30:42 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UEFdx-0001nM-4f; Sat, 09 Mar 2013 20:00:41 +1100 Date: Sat, 9 Mar 2013 20:00:41 +1100 From: Dave Chinner To: Rich Johnston Cc: Eric Sandeen , Ole Tange , xfs-oss Subject: Re: [PATCH V2] xfs_repair: skip freelist scan of corrupt agf in no-modify mode Message-ID: <20130309090041.GG23616@dastard> X-ASG-Orig-Subj: Re: [PATCH V2] xfs_repair: skip freelist scan of corrupt agf in no-modify mode References: <51313DE8.5080104@sandeen.net> <51326DC0.8030403@sandeen.net> <513A4A9B.3050802@sgi.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <513A4A9B.3050802@sgi.com> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1362819661 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124687 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Fri, Mar 08, 2013 at 02:31:23PM -0600, Rich Johnston wrote: > This version looks good. ;) > > Reviewed-by: Rich Johnston > > This has been committed. Except that all review comments have not been addressed. i.e there are two places that have the same bug and they haven't been fixed. It's great that you want to commit quickly, but commits should not happen while there are unaddressed issues still outstanding.... Cheers, Dave. -- Dave Chinner david@fromorbit.com From david@fromorbit.com Sat Mar 9 03:12:23 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 84EBD7F87 for ; Sat, 9 Mar 2013 03:12:23 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay3.corp.sgi.com (Postfix) with ESMTP id 2DB67AC002 for ; Sat, 9 Mar 2013 01:12:23 -0800 (PST) X-ASG-Debug-ID: 1362820341-04bdf0229833fce0001-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id gQTxls91ncv4r6CV for ; Sat, 09 Mar 2013 01:12:22 -0800 (PST) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AlsaAJb8OlF5LH9g/2dsb2JhbABDh0G4B4UWAQIBgV4XdIIsAQEEATocIxAIAxgJJQ8FJQMhE4gNBbtEFY1HBSoYH0oHg0ADllOQdIMegVUBHwM Received: from ppp121-44-127-96.lns20.syd6.internode.on.net (HELO dastard) ([121.44.127.96]) by ipmail05.adl6.internode.on.net with ESMTP; 09 Mar 2013 19:41:53 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UEFom-0001oa-DA; Sat, 09 Mar 2013 20:11:52 +1100 Date: Sat, 9 Mar 2013 20:11:52 +1100 From: Dave Chinner To: Stan Hoeppner Cc: Ric Wheeler , Julien FERRERO , xfs@oss.sgi.com Subject: Re: XFS filesystem corruption Message-ID: <20130309091152.GH23616@dastard> X-ASG-Orig-Subj: Re: XFS filesystem corruption References: <20130306161519.2c28d911@galadriel.home> <20130306232100.6286f640@galadriel.home> <5137CD46.6070909@redhat.com> <5139A3B6.3040805@hardwarefreak.com> <5139D792.4090304@redhat.com> <513A350A.508@hardwarefreak.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <513A350A.508@hardwarefreak.com> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1362820341 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Barracuda-BRTS-Status: 1 X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124687 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Fri, Mar 08, 2013 at 12:59:22PM -0600, Stan Hoeppner wrote: > On 3/8/2013 6:20 AM, Ric Wheeler wrote: > > On 03/08/2013 03:39 AM, Stan Hoeppner wrote: > >> On 3/6/2013 5:12 PM, Ric Wheeler wrote: > >> > >>> We actually test brutal "Power off" for xfs, ext4 and other file > >>> systems. If your storage is configured properly and you have barriers > >>> enabled, they all pass without corruption. > > I think you missed the context. Please reread this: > > >> Something that none of us mentioned WRT write barriers is that while the > >> filesystem structure may avoid corruption when the power is cut, files > >> may still be corrupted, in conditions such as any/all of these: > > I made it very clear I was discussing file corruption here, not > filesystem corruption. You already covered that base. I was > specifically addressing the fact that XFS performs barriers on metadata > writes but not file data writes. Actually, you're not correct there, either, Stan. ;) XFS only issues cache flushes/FUA writes for log IO. Metadata IO is done exactly the same way that data IO is done - without barriers. It's because metadata lost in drive caches at the time of a crash is rewritten by journal replay that filesystem corruption does not occur. As it is, if the application uses direct IO (likely, as it sounds like video capture/editing/playout here) then log IO will also ensure that the data written by the app is on disk (i.e. that's ithe mechanism by which fsync works). Hence even assumptions that there will be data loss are dependent on how the application is doing it's IO.... > > Also, if there are active writers, this is inherently racy. A better > > script would unmount the file systems :) > > Yes, a umount would be even better. Change the bios so that the power button does not cause a power down so the OS can capture the button event and trigger an orderly shutdown. Laptops use power button events for all sorts of different things (e.g. suspend rather than shutdown) and you can do exactly the same sort of event triggered shutdown for any server or desktop... Cheers, Dave. -- Dave Chinner david@fromorbit.com From sandeen@sandeen.net Sat Mar 9 09:00:58 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 5C1BF7F37 for ; Sat, 9 Mar 2013 09:00:58 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay1.corp.sgi.com (Postfix) with ESMTP id 3C7AB8F8049 for ; Sat, 9 Mar 2013 07:00:58 -0800 (PST) X-ASG-Debug-ID: 1362841256-04cbb07dbd346350001-NocioJ Received: from sandeen.net (sandeen.net [63.231.237.45]) by cuda.sgi.com with ESMTP id 93p7rk4ftzmxP0Hg for ; Sat, 09 Mar 2013 07:00:57 -0800 (PST) X-Barracuda-Envelope-From: sandeen@sandeen.net X-Barracuda-Apparent-Source-IP: 63.231.237.45 Received: from liberator.sandeen.net (liberator.sandeen.net [10.0.0.4]) (using TLSv1 with cipher DHE-RSA-CAMELLIA256-SHA (256/256 bits)) (No client certificate requested) by sandeen.net (Postfix) with ESMTPSA id 99C1F63C3D47; Sat, 9 Mar 2013 09:00:56 -0600 (CST) Message-ID: <513B4EA7.4060908@sandeen.net> Date: Sat, 09 Mar 2013 09:00:55 -0600 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: Rich Johnston CC: Ole Tange , xfs-oss Subject: Re: [PATCH V2] xfs_repair: skip freelist scan of corrupt agf in no-modify mode References: <51313DE8.5080104@sandeen.net> <51326DC0.8030403@sandeen.net> <513A4A9B.3050802@sgi.com> X-ASG-Orig-Subj: Re: [PATCH V2] xfs_repair: skip freelist scan of corrupt agf in no-modify mode In-Reply-To: <513A4A9B.3050802@sgi.com> X-Enigmail-Version: 1.5.1 Content-Type: text/plain; charset=windows-1252 Content-Transfer-Encoding: 8bit X-Barracuda-Connect: sandeen.net[63.231.237.45] X-Barracuda-Start-Time: 1362841256 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124711 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On 3/8/13 2:31 PM, Rich Johnston wrote: > This version looks good. ;) Actually it's not quite: scan.c: In function scan_freelist: scan.c:1074: warning: i may be used uninitialized in this function I don't know what's wrong with my brain these days. :/ I will send a patch to fix that along w/ the other scan_freelists shortly. Sorry :/ -Eric > Reviewed-by: Rich Johnston > > This has been committed. > > commit 7e8e3cce00f38ee1533df0e7bda6bcb584b03e96 > Author: Eric Sandeen > Date: Sat Mar 2 21:23:12 2013 +0000 > > xfsprogs: xfs_repair skip freelist scan of corrupt agf in no-modify mode > > In xfs_repair's no-modify mode (-n), verify_set_agf doesn't fix up > bad freelist blocks that it finds. When we get to scan_freelist, > this can wreak havoc if, for example, first > last and the loop > never exits; we index agfl->agfl_bno[i] off into the weeds. > > To fix this, re-check the values in no-modify mode, and if > they're off, warn about it and skip the scan. > > > > _______________________________________________ > xfs mailing list > xfs@oss.sgi.com > http://oss.sgi.com/mailman/listinfo/xfs > From sandeen@sandeen.net Sat Mar 9 09:22:02 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 656217F6B for ; Sat, 9 Mar 2013 09:22:02 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay1.corp.sgi.com (Postfix) with ESMTP id 44E778F8035 for ; Sat, 9 Mar 2013 07:21:59 -0800 (PST) X-ASG-Debug-ID: 1362842518-04cb6c2b0233a5d0001-NocioJ Received: from sandeen.net (sandeen.net [63.231.237.45]) by cuda.sgi.com with ESMTP id 2RpkbLhkUe90etLV for ; Sat, 09 Mar 2013 07:21:58 -0800 (PST) X-Barracuda-Envelope-From: sandeen@sandeen.net X-Barracuda-Apparent-Source-IP: 63.231.237.45 Received: from liberator.sandeen.net (liberator.sandeen.net [10.0.0.4]) (using TLSv1 with cipher DHE-RSA-CAMELLIA256-SHA (256/256 bits)) (No client certificate requested) by sandeen.net (Postfix) with ESMTPSA id 288A363C3D47 for ; Sat, 9 Mar 2013 09:21:58 -0600 (CST) Message-ID: <513B5393.4000203@sandeen.net> Date: Sat, 09 Mar 2013 09:21:55 -0600 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: xfs-oss Subject: [PATCH] xfsprogs: skip freelist scans of corrupt agf X-Enigmail-Version: 1.5.1 X-ASG-Orig-Subj: [PATCH] xfsprogs: skip freelist scans of corrupt agf Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: sandeen.net[63.231.237.45] X-Barracuda-Start-Time: 1362842518 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124713 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- If an agf has bad values in the freelist, this can wreak havoc if, for example, first > last and the loop never exits; we index agfl->agfl_bno[i] off into the weeds. If they're off, warn about it and skip the scan. Thisis done both in xfs_check and xfs_db's freespace cmd. Also fix uninit'd variable "i" from previous, similar fix for xfs_repair. Signed-off-by: Eric Sandeen --- diff --git a/db/check.c b/db/check.c index e601e0a..35325b7 100644 --- a/db/check.c +++ b/db/check.c @@ -4112,6 +4112,16 @@ scan_freelist( return; } i = be32_to_cpu(agf->agf_flfirst); + + /* verify agf values before proceeding */ + if (be32_to_cpu(agf->agf_flfirst) >= XFS_AGFL_SIZE(mp) || + be32_to_cpu(agf->agf_fllast) >= XFS_AGFL_SIZE(mp)) { + dbprintf(_("agf %d freelist blocks bad, skipping " + "freelist scan\n"), i); + pop_cur(); + return; + } + count = 0; for (;;) { bno = be32_to_cpu(agfl->agfl_bno[i]); diff --git a/db/freesp.c b/db/freesp.c index c4dabad..472b1f7 100644 --- a/db/freesp.c +++ b/db/freesp.c @@ -239,6 +239,16 @@ scan_freelist( XFS_FSS_TO_BB(mp, 1), DB_RING_IGN, NULL); agfl = iocur_top->data; i = be32_to_cpu(agf->agf_flfirst); + + /* verify agf values before proceeding */ + if (be32_to_cpu(agf->agf_flfirst) >= XFS_AGFL_SIZE(mp) || + be32_to_cpu(agf->agf_fllast) >= XFS_AGFL_SIZE(mp)) { + dbprintf(_("agf %d freelist blocks bad, skipping " + "freelist scan\n"), i); + pop_cur(); + return; + } + for (;;) { bno = be32_to_cpu(agfl->agfl_bno[i]); addtohist(seqno, bno, 1); diff --git a/repair/scan.c b/repair/scan.c index 1d39bdc..6a62dff 100644 --- a/repair/scan.c +++ b/repair/scan.c @@ -1066,6 +1066,7 @@ scan_freelist( return; } agfl = XFS_BUF_TO_AGFL(agflbuf); + i = be32_to_cpu(agf->agf_flfirst); if (no_modify) { /* agf values not fixed in verify_set_agf, so recheck */ @@ -1078,7 +1079,6 @@ scan_freelist( } else /* should have been fixed in verify_set_agf() */ ASSERT(0); - i = be32_to_cpu(agf->agf_flfirst); count = 0; for (;;) { bno = be32_to_cpu(agfl->agfl_bno[i]); From sandeen@sandeen.net Sat Mar 9 11:22:27 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id EFE647F6A for ; Sat, 9 Mar 2013 11:22:27 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay2.corp.sgi.com (Postfix) with ESMTP id B210630405F for ; Sat, 9 Mar 2013 09:22:24 -0800 (PST) X-ASG-Debug-ID: 1362849742-04bdf02297364530001-NocioJ Received: from sandeen.net (sandeen.net [63.231.237.45]) by cuda.sgi.com with ESMTP id ZgNAaVkmJQshnPFB for ; Sat, 09 Mar 2013 09:22:23 -0800 (PST) X-Barracuda-Envelope-From: sandeen@sandeen.net X-Barracuda-Apparent-Source-IP: 63.231.237.45 Received: from liberator.sandeen.net (liberator.sandeen.net [10.0.0.4]) (using TLSv1 with cipher DHE-RSA-CAMELLIA256-SHA (256/256 bits)) (No client certificate requested) by sandeen.net (Postfix) with ESMTPSA id 7496E63C3D47; Sat, 9 Mar 2013 11:22:22 -0600 (CST) Message-ID: <513B6FCD.5080103@sandeen.net> Date: Sat, 09 Mar 2013 11:22:21 -0600 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: Koen De Wit CC: xfs@oss.sgi.com, linux-btrfs Subject: Re: xfstests: 297: simple sparse copy testcase for btrfs References: <50F9C313.1000903@oracle.com> X-ASG-Orig-Subj: Re: xfstests: 297: simple sparse copy testcase for btrfs In-Reply-To: <50F9C313.1000903@oracle.com> X-Enigmail-Version: 1.5.1 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: sandeen.net[63.231.237.45] X-Barracuda-Start-Time: 1362849742 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124721 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On 1/18/13 3:48 PM, Koen De Wit wrote: > Signed-off-by: Koen De Wit Sorry for the late review. Better late than never? cc'ing linux-btrfs - in general a good idea so btrfs experts can evaluate the test as well. > --- > 297 | 75 > +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ > 297.out | 10 ++++++++ > 2 files changed, 85 insertions(+), 0 deletions(-) > create mode 100644 297 > create mode 100644 297.out > > diff --git a/297 b/297 > new file mode 100644 > index 0000000..0851b57 > --- /dev/null > +++ b/297 > @@ -0,0 +1,75 @@ > +#! /bin/bash > +# FS QA Test No. 297 > +# > +# Tests file clone functionality of btrfs ("reflinks"): > +# - Reflink a file > +# - Reflink the reflinked file > +# - Modify the original file > +# - Modify the reflinked file > +# > +#----------------------------------------------------------------------- > +# Copyright (c) 2013, Oracle and/or its affiliates. All Rights Reserved. > +# > +# This program is free software; you can redistribute it and/or > +# modify it under the terms of the GNU General Public License as > +# published by the Free Software Foundation. > +# > +# This program is distributed in the hope that it would be useful, > +# but WITHOUT ANY WARRANTY; without even the implied warranty of > +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the > +# GNU General Public License for more details. > +# > +# You should have received a copy of the GNU General Public License > +# along with this program; if not, write the Free Software Foundation, > +# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA > +#----------------------------------------------------------------------- > +# > +# creator > +owner=koen.de.wit@oracle.com > + > +seq=`basename $0` > +echo "QA output created by $seq" > + > +here=`pwd` > +tmp=/tmp/$$ > +status=1 # failure is the default! > +trap "_cleanup; exit \$status" 0 1 2 3 15 > + > +_cleanup() > +{ > + cd / > + rm -f $tmp.* > +} > + > +# get standard environment, filters and checks > +. ./common.rc > +. ./common.filter > + > +# real QA test starts here > +_supported_fs btrfs I wonder if it'd be nice to make the test generic, but test whether the filesystem supports reflinks, and bail if not. > +_supported_os Linux > + > +_require_cp_reflink where does _require_cp_reflink come from? Also, as for missing bits, need to add new tests to the group with each patch (I see you added them all in the last patch you sent). > + > +TESTDIR1=$TEST_DIR/test-$seq.$$ > +mkdir $TESTDIR1 This has some remote possibility of failure, right, if we happen to run across the same pid. How about: +TESTDIR1=$TEST_DIR/test-$seq +rm -rf TESTDIR1=$TEST_DIR/test-$seq +mkdir $TESTDIR1 > + > +_catfiles() { > + for F in original copy1 copy2 > + do > + md5sum $TESTDIR1/$F | $AWK_PROG 'END {print $1}' > + done > +} Just a nitpick I guess but maybe _checksum_files would be more accurate. It'd also be nicer to provide more context in the output - what file is the checksum for? What are we testing? So maybe: +_checksum_files() { + for F in original copy1 copy2 + do + md5sum $TESTDIR1/$F | _filter_test_dir + done +} so then we'll have the filenames in the output. And then, putting echos in make both the test and the output more self-documenting: +echo "Create the original file filled with 0x61" > +$XFS_IO_PROG -f -c 'pwrite -S 0x61 0 9000' $TESTDIR1/original > /dev/null +echo "And make 2 reflink copies to it" > +cp --reflink $TESTDIR1/original $TESTDIR1/copy1 > +cp --reflink $TESTDIR1/copy1 $TESTDIR1/copy2 +# Ensure that they all have the same md5sums at this point +echo "Original md5sums:" > +_catfiles +echo "Overwrite original file with 0x62" > +$XFS_IO_PROG -c 'pwrite -S 0x62 0 9000' $TESTDIR1/original > /dev/null +echo "md5sums after overwriting original" > +_catfiles +echo "Overwrite copy1 with 0x63" > +$XFS_IO_PROG -c 'pwrite -S 0x63 0 9000' $TESTDIR1/copy1 > /dev/null +echo "md5sums after overwriting copy1:" > +_catfiles > + > +# success, all done > +status=0 > +exit Then the test output looks like: Create the original file filled with 0x61 And make 2 reflink copies to it Original md5sums: 42d69d1a6d333a7ebdf64792a555e392 TEST_DIR/test-307/original 42d69d1a6d333a7ebdf64792a555e392 TEST_DIR/test-307/copy1 42d69d1a6d333a7ebdf64792a555e392 TEST_DIR/test-307/copy2 Overwrite original file with 0x62 md5sums after overwriting original: 4a847a25439532bf48b68c9e9536ed5b TEST_DIR/test-307/original 42d69d1a6d333a7ebdf64792a555e392 TEST_DIR/test-307/copy1 42d69d1a6d333a7ebdf64792a555e392 TEST_DIR/test-307/copy2 Overwrite copy1 with 0x63 md5sums after overwriting copy1: 4a847a25439532bf48b68c9e9536ed5b TEST_DIR/test-307/original e271cd47d9f62ebc96cb4e67ae4d16db TEST_DIR/test-307/copy1 42d69d1a6d333a7ebdf64792a555e392 TEST_DIR/test-307/copy2 so if anything goes wrong, we'll have more context in the output. What do you think? Thanks, -Eric > diff --git a/297.out b/297.out > new file mode 100644 > index 0000000..39c498b > --- /dev/null > +++ b/297.out > @@ -0,0 +1,10 @@ > +QA output created by 297 > +42d69d1a6d333a7ebdf64792a555e392 > +42d69d1a6d333a7ebdf64792a555e392 > +42d69d1a6d333a7ebdf64792a555e392 > +4a847a25439532bf48b68c9e9536ed5b > +42d69d1a6d333a7ebdf64792a555e392 > +42d69d1a6d333a7ebdf64792a555e392 > +4a847a25439532bf48b68c9e9536ed5b > +e271cd47d9f62ebc96cb4e67ae4d16db > +42d69d1a6d333a7ebdf64792a555e392 > From sandeen@sandeen.net Sat Mar 9 11:46:44 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id C48A47F6A for ; Sat, 9 Mar 2013 11:46:44 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay3.corp.sgi.com (Postfix) with ESMTP id 458CBAC001 for ; Sat, 9 Mar 2013 09:46:41 -0800 (PST) X-ASG-Debug-ID: 1362851199-04cbb07dbe3538d0001-NocioJ Received: from sandeen.net (sandeen.net [63.231.237.45]) by cuda.sgi.com with ESMTP id KkaOnjT3TtnovNHS for ; Sat, 09 Mar 2013 09:46:39 -0800 (PST) X-Barracuda-Envelope-From: sandeen@sandeen.net X-Barracuda-Apparent-Source-IP: 63.231.237.45 Received: from liberator.sandeen.net (liberator.sandeen.net [10.0.0.4]) (using TLSv1 with cipher DHE-RSA-CAMELLIA256-SHA (256/256 bits)) (No client certificate requested) by sandeen.net (Postfix) with ESMTPSA id ECFDB63C3D47; Sat, 9 Mar 2013 11:46:38 -0600 (CST) Message-ID: <513B757E.9070803@sandeen.net> Date: Sat, 09 Mar 2013 11:46:38 -0600 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: Koen De Wit CC: xfs@oss.sgi.com, linux-btrfs Subject: Re: xfstests: 298: sparse copy of a directory tree on btrfs References: <50F9C31B.20203@oracle.com> X-ASG-Orig-Subj: Re: xfstests: 298: sparse copy of a directory tree on btrfs In-Reply-To: <50F9C31B.20203@oracle.com> X-Enigmail-Version: 1.5.1 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: sandeen.net[63.231.237.45] X-Barracuda-Start-Time: 1362851199 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124721 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On 1/18/13 3:48 PM, Koen De Wit wrote: > Signed-off-by: Koen De Wit same basic comments as for the previous test: need definition of _require_cp_reflink somewhere need to add test to groups file remove & recreate testdir to avoid collisions (or mktemp maybe?) use _filter_test_dir in md5sum output to get more context add test context to output file also, the patch wrapped when sending, FWIW. Oh, and thanks for writing these! -Eric > --- > 298 | 82 > +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ > 298.out | 19 ++++++++++++++ > 2 files changed, 101 insertions(+), 0 deletions(-) > create mode 100644 298 > create mode 100644 298.out > > diff --git a/298 b/298 > new file mode 100644 > index 0000000..47ac55d > --- /dev/null > +++ b/298 > @@ -0,0 +1,82 @@ > +#! /bin/bash > +# FS QA Test No. 298 > +# > +# Tests file clone functionality of btrfs ("reflinks") on directory trees. > +# - Create directory and subdirectory, each having one file > +# - Create 2 reflinked copies of the tree > +# - Modify the original files > +# - Modify one of the copies adding these as echos at the appropriate places adds context to the output file. > +# > +#----------------------------------------------------------------------- > +# Copyright (c) 2013, Oracle and/or its affiliates. All Rights Reserved. > +# > +# This program is free software; you can redistribute it and/or > +# modify it under the terms of the GNU General Public License as > +# published by the Free Software Foundation. > +# > +# This program is distributed in the hope that it would be useful, > +# but WITHOUT ANY WARRANTY; without even the implied warranty of > +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the > +# GNU General Public License for more details. > +# > +# You should have received a copy of the GNU General Public License > +# along with this program; if not, write the Free Software Foundation, > +# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA > +#----------------------------------------------------------------------- > +# > +# creator > +owner=koen.de.wit@oracle.com > + > +seq=`basename $0` > +echo "QA output created by $seq" > + > +here=`pwd` > +tmp=/tmp/$$ > +status=1 # failure is the default! > +trap "_cleanup; exit \$status" 0 1 2 3 15 > + > +_cleanup() > +{ > + cd / > + rm -f $tmp.* > +} > + > +# get standard environment, filters and checks > +. ./common.rc > +. ./common.filter > + > +# real QA test starts here > +_supported_fs btrfs > +_supported_os Linux > + > +_require_cp_reflink > + > +TESTDIR1=$TEST_DIR/test-$seq.$$ > +mkdir $TESTDIR1 > + > +_catfiles() { > + for F in original/file1 original/subdir/file2 \ > + copy1/file1 copy1/subdir/file2 \ > + copy2/file1 copy2/subdir/file2 > + do > + md5sum $TESTDIR1/$F | $AWK_PROG 'END {print $1}' > + done > +} > + > +mkdir $TESTDIR1/original > +mkdir $TESTDIR1/original/subdir > +$XFS_IO_PROG -f -c 'pwrite -S 0x61 0 9000' $TESTDIR1/original/file1 > /dev/null > +$XFS_IO_PROG -f -c 'pwrite -S 0x62 0 11000' $TESTDIR1/original/subdir/file2 > /dev/null > +cp --recursive --reflink $TESTDIR1/original $TESTDIR1/copy1 > +cp --recursive --reflink $TESTDIR1/copy1 $TESTDIR1/copy2 > +_catfiles > +$XFS_IO_PROG -c 'pwrite -S 0x63 0 13000' $TESTDIR1/original/file1 > /dev/null > +$XFS_IO_PROG -c 'pwrite -S 0x64 5000 1000' > $TESTDIR1/original/subdir/file2 > /dev/null > +_catfiles > +$XFS_IO_PROG -c 'pwrite -S 0x65 0 9000' $TESTDIR1/copy1/file1 > /dev/null > +$XFS_IO_PROG -c 'pwrite -S 0x66 5000 25000' $TESTDIR1/copy1/subdir/file2 > /dev/null > +_catfiles > + > +# success, all done > +status=0 > +exit > diff --git a/298.out b/298.out > new file mode 100644 > index 0000000..f8b6b70 > --- /dev/null > +++ b/298.out > @@ -0,0 +1,19 @@ > +QA output created by 298 > +42d69d1a6d333a7ebdf64792a555e392 > +ca390545f0aedb54b808d6128c56a7dd > +42d69d1a6d333a7ebdf64792a555e392 > +ca390545f0aedb54b808d6128c56a7dd > +42d69d1a6d333a7ebdf64792a555e392 > +ca390545f0aedb54b808d6128c56a7dd > +260f6785c0537fd12582dcae28a3c1a9 > +b8d91fb600f6f2191f2ba66665374860 > +42d69d1a6d333a7ebdf64792a555e392 > +ca390545f0aedb54b808d6128c56a7dd > +42d69d1a6d333a7ebdf64792a555e392 > +ca390545f0aedb54b808d6128c56a7dd > +260f6785c0537fd12582dcae28a3c1a9 > +b8d91fb600f6f2191f2ba66665374860 > +b20229a003e3985c4b0e6806abcd6642 > +b815b24069db14e0a3a07169fd563e93 > +42d69d1a6d333a7ebdf64792a555e392 > +ca390545f0aedb54b808d6128c56a7dd > From sandeen@sandeen.net Sat Mar 9 11:48:02 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id D498B7F6A for ; Sat, 9 Mar 2013 11:48:02 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay1.corp.sgi.com (Postfix) with ESMTP id BD5A28F8037 for ; Sat, 9 Mar 2013 09:48:02 -0800 (PST) X-ASG-Debug-ID: 1362851277-04cb6c2b02349dc0001-NocioJ Received: from sandeen.net (sandeen.net [63.231.237.45]) by cuda.sgi.com with ESMTP id efbTcKtHOsdM66zo for ; Sat, 09 Mar 2013 09:47:57 -0800 (PST) X-Barracuda-Envelope-From: sandeen@sandeen.net X-Barracuda-Apparent-Source-IP: 63.231.237.45 Received: from liberator.sandeen.net (liberator.sandeen.net [10.0.0.4]) (using TLSv1 with cipher DHE-RSA-CAMELLIA256-SHA (256/256 bits)) (No client certificate requested) by sandeen.net (Postfix) with ESMTPSA id 6EFFA63C3D47; Sat, 9 Mar 2013 11:47:57 -0600 (CST) Message-ID: <513B75CD.2050400@sandeen.net> Date: Sat, 09 Mar 2013 11:47:57 -0600 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: Koen De Wit CC: xfs@oss.sgi.com Subject: Re: xfstests: 299: moving and deleting sparse copies on btrfs References: <50F9C324.5010502@oracle.com> X-ASG-Orig-Subj: Re: xfstests: 299: moving and deleting sparse copies on btrfs In-Reply-To: <50F9C324.5010502@oracle.com> X-Enigmail-Version: 1.5.1 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: sandeen.net[63.231.237.45] X-Barracuda-Start-Time: 1362851277 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124723 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On 1/18/13 3:48 PM, Koen De Wit wrote: > Signed-off-by: Koen De Wit same comments as the others; looks good otherwise. -Eric > --- > 299 | 69 > +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ > 299.out | 4 +++ > 2 files changed, 73 insertions(+), 0 deletions(-) > create mode 100644 299 > create mode 100644 299.out > > diff --git a/299 b/299 > new file mode 100644 > index 0000000..0ddb022 > --- /dev/null > +++ b/299 > @@ -0,0 +1,69 @@ > +#! /bin/bash > +# FS QA Test No. 299 > +# > +# Moving and deleting cloned ("reflinked") files on btrfs: > +# - Create a file and a reflink > +# - Move both to a directory > +# - Delete the original (moved) file, check that the copy still exists. > +# > +#----------------------------------------------------------------------- > +# Copyright (c) 2013, Oracle and/or its affiliates. All Rights Reserved. > +# > +# This program is free software; you can redistribute it and/or > +# modify it under the terms of the GNU General Public License as > +# published by the Free Software Foundation. > +# > +# This program is distributed in the hope that it would be useful, > +# but WITHOUT ANY WARRANTY; without even the implied warranty of > +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the > +# GNU General Public License for more details. > +# > +# You should have received a copy of the GNU General Public License > +# along with this program; if not, write the Free Software Foundation, > +# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA > +#----------------------------------------------------------------------- > +# > +# creator > +owner=koen.de.wit@oracle.com > + > +seq=`basename $0` > +echo "QA output created by $seq" > + > +here=`pwd` > +tmp=/tmp/$$ > +status=1 # failure is the default! > +trap "_cleanup; exit \$status" 0 1 2 3 15 > + > +_cleanup() > +{ > + cd / > + rm -f $tmp.* > +} > + > +# get standard environment, filters and checks > +. ./common.rc > +. ./common.filter > + > +# real QA test starts here > +_supported_fs btrfs > +_supported_os Linux > + > +_require_cp_reflink > + > +TESTDIR1=$TEST_DIR/test-$seq.$$ > +mkdir $TESTDIR1 > + > +$XFS_IO_PROG -f -c 'pwrite -S 0x61 0 9000' $TESTDIR1/original > /dev/null > +cp --reflink $TESTDIR1/original $TESTDIR1/copy > +mkdir $TESTDIR1/subdir > +mv $TESTDIR1/original $TESTDIR1/subdir/original_moved > +mv $TESTDIR1/copy $TESTDIR1/subdir/copy_moved > +md5sum $TESTDIR1/subdir/original_moved | $AWK_PROG 'END {print $1}' > +md5sum $TESTDIR1/subdir/copy_moved | $AWK_PROG 'END {print $1}' > +rm $TESTDIR1/subdir/original_moved > +md5sum $TESTDIR1/subdir/copy_moved | $AWK_PROG 'END {print $1}' > +rm -rf $TESTDIR1/subdir > + > +# success, all done > +status=0 > +exit > diff --git a/299.out b/299.out > new file mode 100644 > index 0000000..f06eb2b > --- /dev/null > +++ b/299.out > @@ -0,0 +1,4 @@ > +QA output created by 299 > +42d69d1a6d333a7ebdf64792a555e392 > +42d69d1a6d333a7ebdf64792a555e392 > +42d69d1a6d333a7ebdf64792a555e392 > From sandeen@sandeen.net Sat Mar 9 11:48:50 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id D2A2C7F6A for ; Sat, 9 Mar 2013 11:48:50 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id BD62630405F for ; Sat, 9 Mar 2013 09:48:50 -0800 (PST) X-ASG-Debug-ID: 1362851323-04cbb07dbf353b90001-NocioJ Received: from sandeen.net (sandeen.net [63.231.237.45]) by cuda.sgi.com with ESMTP id YQorTPJzJCYXzwUc for ; Sat, 09 Mar 2013 09:48:44 -0800 (PST) X-Barracuda-Envelope-From: sandeen@sandeen.net X-Barracuda-Apparent-Source-IP: 63.231.237.45 Received: from liberator.sandeen.net (liberator.sandeen.net [10.0.0.4]) (using TLSv1 with cipher DHE-RSA-CAMELLIA256-SHA (256/256 bits)) (No client certificate requested) by sandeen.net (Postfix) with ESMTPSA id DBF2F63C3D47; Sat, 9 Mar 2013 11:48:43 -0600 (CST) Message-ID: <513B75FB.7050905@sandeen.net> Date: Sat, 09 Mar 2013 11:48:43 -0600 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: Koen De Wit CC: xfs@oss.sgi.com, linux-btrfs Subject: Re: xfstests: 299: moving and deleting sparse copies on btrfs References: <50F9C324.5010502@oracle.com> <513B75CD.2050400@sandeen.net> X-ASG-Orig-Subj: Re: xfstests: 299: moving and deleting sparse copies on btrfs In-Reply-To: <513B75CD.2050400@sandeen.net> X-Enigmail-Version: 1.5.1 Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: sandeen.net[63.231.237.45] X-Barracuda-Start-Time: 1362851323 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124723 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On 3/9/13 11:47 AM, Eric Sandeen wrote: > On 1/18/13 3:48 PM, Koen De Wit wrote: >> Signed-off-by: Koen De Wit > > same comments as the others; looks good otherwise. (whoops, cc: btrfs list) > -Eric > >> --- >> 299 | 69 >> +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ >> 299.out | 4 +++ >> 2 files changed, 73 insertions(+), 0 deletions(-) >> create mode 100644 299 >> create mode 100644 299.out >> >> diff --git a/299 b/299 >> new file mode 100644 >> index 0000000..0ddb022 >> --- /dev/null >> +++ b/299 >> @@ -0,0 +1,69 @@ >> +#! /bin/bash >> +# FS QA Test No. 299 >> +# >> +# Moving and deleting cloned ("reflinked") files on btrfs: >> +# - Create a file and a reflink >> +# - Move both to a directory >> +# - Delete the original (moved) file, check that the copy still exists. >> +# >> +#----------------------------------------------------------------------- >> +# Copyright (c) 2013, Oracle and/or its affiliates. All Rights Reserved. >> +# >> +# This program is free software; you can redistribute it and/or >> +# modify it under the terms of the GNU General Public License as >> +# published by the Free Software Foundation. >> +# >> +# This program is distributed in the hope that it would be useful, >> +# but WITHOUT ANY WARRANTY; without even the implied warranty of >> +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the >> +# GNU General Public License for more details. >> +# >> +# You should have received a copy of the GNU General Public License >> +# along with this program; if not, write the Free Software Foundation, >> +# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA >> +#----------------------------------------------------------------------- >> +# >> +# creator >> +owner=koen.de.wit@oracle.com >> + >> +seq=`basename $0` >> +echo "QA output created by $seq" >> + >> +here=`pwd` >> +tmp=/tmp/$$ >> +status=1 # failure is the default! >> +trap "_cleanup; exit \$status" 0 1 2 3 15 >> + >> +_cleanup() >> +{ >> + cd / >> + rm -f $tmp.* >> +} >> + >> +# get standard environment, filters and checks >> +. ./common.rc >> +. ./common.filter >> + >> +# real QA test starts here >> +_supported_fs btrfs >> +_supported_os Linux >> + >> +_require_cp_reflink >> + >> +TESTDIR1=$TEST_DIR/test-$seq.$$ >> +mkdir $TESTDIR1 >> + >> +$XFS_IO_PROG -f -c 'pwrite -S 0x61 0 9000' $TESTDIR1/original > /dev/null >> +cp --reflink $TESTDIR1/original $TESTDIR1/copy >> +mkdir $TESTDIR1/subdir >> +mv $TESTDIR1/original $TESTDIR1/subdir/original_moved >> +mv $TESTDIR1/copy $TESTDIR1/subdir/copy_moved >> +md5sum $TESTDIR1/subdir/original_moved | $AWK_PROG 'END {print $1}' >> +md5sum $TESTDIR1/subdir/copy_moved | $AWK_PROG 'END {print $1}' >> +rm $TESTDIR1/subdir/original_moved >> +md5sum $TESTDIR1/subdir/copy_moved | $AWK_PROG 'END {print $1}' >> +rm -rf $TESTDIR1/subdir >> + >> +# success, all done >> +status=0 >> +exit >> diff --git a/299.out b/299.out >> new file mode 100644 >> index 0000000..f06eb2b >> --- /dev/null >> +++ b/299.out >> @@ -0,0 +1,4 @@ >> +QA output created by 299 >> +42d69d1a6d333a7ebdf64792a555e392 >> +42d69d1a6d333a7ebdf64792a555e392 >> +42d69d1a6d333a7ebdf64792a555e392 >> > > _______________________________________________ > xfs mailing list > xfs@oss.sgi.com > http://oss.sgi.com/mailman/listinfo/xfs > From sandeen@sandeen.net Sat Mar 9 12:08:11 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id EBFD97F6A for ; Sat, 9 Mar 2013 12:08:10 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay3.corp.sgi.com (Postfix) with ESMTP id 8A18AAC001 for ; Sat, 9 Mar 2013 10:08:07 -0800 (PST) X-ASG-Debug-ID: 1362852485-04bdf02296368e80001-NocioJ Received: from sandeen.net (sandeen.net [63.231.237.45]) by cuda.sgi.com with ESMTP id fM3rNYCRg2T4nDKM for ; Sat, 09 Mar 2013 10:08:06 -0800 (PST) X-Barracuda-Envelope-From: sandeen@sandeen.net X-Barracuda-Apparent-Source-IP: 63.231.237.45 Received: from liberator.sandeen.net (liberator.sandeen.net [10.0.0.4]) (using TLSv1 with cipher DHE-RSA-CAMELLIA256-SHA (256/256 bits)) (No client certificate requested) by sandeen.net (Postfix) with ESMTPSA id C588163C3D47; Sat, 9 Mar 2013 12:08:05 -0600 (CST) Message-ID: <513B7A85.6070606@sandeen.net> Date: Sat, 09 Mar 2013 12:08:05 -0600 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: Koen De Wit CC: xfs@oss.sgi.com, linux-btrfs Subject: Re: xfstests: 300: diskspace consumption of cloned files on btrfs References: <50F9C32A.6000600@oracle.com> X-ASG-Orig-Subj: Re: xfstests: 300: diskspace consumption of cloned files on btrfs In-Reply-To: <50F9C32A.6000600@oracle.com> X-Enigmail-Version: 1.5.1 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: sandeen.net[63.231.237.45] X-Barracuda-Start-Time: 1362852485 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124723 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On 1/18/13 3:48 PM, Koen De Wit wrote: > Signed-off-by: Koen De Wit > > --- > 300 | 84 > +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ > 300.out | 4 +++ > 2 files changed, 88 insertions(+), 0 deletions(-) > create mode 100644 300 > create mode 100644 300.out > > diff --git a/300 b/300 > new file mode 100644 > index 0000000..a6f706c > --- /dev/null > +++ b/300 > @@ -0,0 +1,84 @@ > +#! /bin/bash > +# FS QA Test No. 300 > +# > +# Diskspace consumption of sparse file clones ("reflinks") on btrfs > +# - Check that a reflink does not consume space > +# - Check that a reflink starts to consume space when the original file > +# is modified > +# - Check that diskspace is freed up after deleting all files > +# > +#----------------------------------------------------------------------- > +# Copyright (c) 2013, Oracle and/or its affiliates. All Rights Reserved. > +# > +# This program is free software; you can redistribute it and/or > +# modify it under the terms of the GNU General Public License as > +# published by the Free Software Foundation. > +# > +# This program is distributed in the hope that it would be useful, > +# but WITHOUT ANY WARRANTY; without even the implied warranty of > +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the > +# GNU General Public License for more details. > +# > +# You should have received a copy of the GNU General Public License > +# along with this program; if not, write the Free Software Foundation, > +# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA > +#----------------------------------------------------------------------- > +# > +# creator > +owner=koen.de.wit@oracle.com > + > +seq=`basename $0` > +echo "QA output created by $seq" > + > +here=`pwd` > +tmp=/tmp/$$ > +status=1 # failure is the default! > +trap "_cleanup; exit \$status" 0 1 2 3 15 > + > +_cleanup() > +{ > + cd / > + rm -f $tmp.* > +} > + > +# get standard environment, filters and checks > +. ./common.rc > +. ./common.filter > + > +# real QA test starts here > +_supported_fs btrfs > +_supported_os Linux > + > +_require_cp_reflink need def'n > +TESTDIR1=$TEST_DIR/test-$seq.$$ > +mkdir $TESTDIR1 possible clash if pids cycle? > +_free() { > + _df_dir $TEST_DIR | $AWK_PROG '{ print $5 }' > +} > + > +free_before=`_free` > +$XFS_IO_PROG -f -c "pwrite -S 0x61 0 10m" -c "fsync" $TESTDIR1/original > > /dev/null patch wrapped. FWIW sometimes redirecting to $seq.full rather than /dev/null makes it easier to see what's happened if anything goes wrong. > +cp --reflink=always $TESTDIR1/original $TESTDIR1/copy1 > +cp --reflink=auto $TESTDIR1/copy1 $TESTDIR1/copy2 > +btrfs filesystem sync $TEST_DIR > /dev/null > +free_after_creating_reflinks=`_free` > +_within_tolerance "free space after creating 1 file and 2 reflinks" \ > + `expr $free_before - $free_after_creating_reflinks` 10252 512 -v > + A comment about what's being checked here might help, unfortunately the _within_tolerance helper is a little cryptic. why should the difference be 10252, out of curiosity? Does that depend on block size or anything? > +$XFS_IO_PROG -c "pwrite -S 0x62 3m 5m" -c "fsync" $TESTDIR1/original > > /dev/null patch wrapped :) > +btrfs filesystem sync $TEST_DIR > /dev/null > +free_after_overwriting=`_free` > +_within_tolerance "free space after overwriting original file" \ > + `expr $free_before - $free_after_overwriting` 15376 512 -v Ok, so you overwrote 5 megs of the original 10 meg file now. So this is checking that the difference is within 512 bytes newly-consumed space against . . . 15376 what? It'd just be nice to have a comment for future readers. I wonder if comparing to $free_after_creating_reflinks would be clearer, so the space used is just that space used for the new data? > +rm $TESTDIR1/original $TESTDIR1/copy1 $TESTDIR1/copy2 > +btrfs filesystem sync $TEST_DIR > /dev/null > +free_after_removing=`_free` > +_within_tolerance "free space after removing all files" \ > + `expr $free_before - $free_after_removing` 0 128 -v This makes sense, make sure we're back to the original. Is the 128 slop even necessary? Need to add this test to groups as well. Thanks, -Eric > + > +# success, all done > +status=0 > +exit > diff --git a/300.out b/300.out > new file mode 100644 > index 0000000..bbb94f4 > --- /dev/null > +++ b/300.out > @@ -0,0 +1,4 @@ > +QA output created by 300 > +free space after creating 1 file and 2 reflinks is in range > +free space after overwriting original file is in range > +free space after removing all files is in range > From stan@hardwarefreak.com Sat Mar 9 12:51:30 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=T_FRT_PROFILE2 autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 388847F67 for ; Sat, 9 Mar 2013 12:51:30 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay2.corp.sgi.com (Postfix) with ESMTP id 18BA1304032 for ; Sat, 9 Mar 2013 10:51:26 -0800 (PST) X-ASG-Debug-ID: 1362855085-04cb6c2b013501c0001-NocioJ Received: from greer.hardwarefreak.com (mo-65-41-216-221.sta.embarqhsd.net [65.41.216.221]) by cuda.sgi.com with ESMTP id Jr9mDQ34TWqppfh1 for ; Sat, 09 Mar 2013 10:51:26 -0800 (PST) X-Barracuda-Envelope-From: stan@hardwarefreak.com X-Barracuda-Apparent-Source-IP: 65.41.216.221 X-Barracuda-User-Whitelist: xfs@oss.sgi.com Received: from [192.168.100.53] (gffx.hardwarefreak.com [192.168.100.53]) by greer.hardwarefreak.com (Postfix) with ESMTP id B39236C068; Sat, 9 Mar 2013 12:51:25 -0600 (CST) Message-ID: <513B84AD.2000603@hardwarefreak.com> Date: Sat, 09 Mar 2013 12:51:25 -0600 From: Stan Hoeppner Reply-To: stan@hardwarefreak.com User-Agent: Mozilla/5.0 (Windows NT 5.1; rv:17.0) Gecko/20130215 Thunderbird/17.0.3 MIME-Version: 1.0 To: Dave Chinner CC: Ric Wheeler , Julien FERRERO , xfs@oss.sgi.com Subject: Re: XFS filesystem corruption References: <20130306161519.2c28d911@galadriel.home> <20130306232100.6286f640@galadriel.home> <5137CD46.6070909@redhat.com> <5139A3B6.3040805@hardwarefreak.com> <5139D792.4090304@redhat.com> <513A350A.508@hardwarefreak.com> <20130309091152.GH23616@dastard> X-ASG-Orig-Subj: Re: XFS filesystem corruption In-Reply-To: <20130309091152.GH23616@dastard> Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: mo-65-41-216-221.sta.embarqhsd.net[65.41.216.221] X-Barracuda-Start-Time: 1362855086 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 On 3/9/2013 3:11 AM, Dave Chinner wrote: > On Fri, Mar 08, 2013 at 12:59:22PM -0600, Stan Hoeppner wrote: >> On 3/8/2013 6:20 AM, Ric Wheeler wrote: >>> On 03/08/2013 03:39 AM, Stan Hoeppner wrote: >>>> On 3/6/2013 5:12 PM, Ric Wheeler wrote: >>>> >>>>> We actually test brutal "Power off" for xfs, ext4 and other file >>>>> systems. If your storage is configured properly and you have barriers >>>>> enabled, they all pass without corruption. >> >> I think you missed the context. Please reread this: >> >>>> Something that none of us mentioned WRT write barriers is that while the >>>> filesystem structure may avoid corruption when the power is cut, files >>>> may still be corrupted, in conditions such as any/all of these: >> >> I made it very clear I was discussing file corruption here, not >> filesystem corruption. You already covered that base. I was >> specifically addressing the fact that XFS performs barriers on metadata >> writes but not file data writes. > > Actually, you're not correct there, either, Stan. ;) With "either" you're implying I was incorrect twice, and I wasn't, not in whole anyway, maybe in part. ;) > XFS only issues cache flushes/FUA writes for log IO. Metadata IO is > done exactly the same way that data IO is done - without barriers. > It's because metadata lost in drive caches at the time of a crash is > rewritten by journal replay that filesystem corruption does not > occur. Technical semantics. Geeze, give the non dev a break now and then. ;) Does everyone remember the transitive property of equality from math class decades ago? It states "If A=B and B=C then A=C". Thus if barrier writes to the journal protect the journal, and the journal protects metadata, then barrier writes to the journal protect metadata. I had a detail incorrect, but not the big picture. And I'd bet the OP is more interested in the big picture. So surely I'd get a B or a C here, but certainly not an F. > As it is, if the application uses direct IO (likely, as it > sounds like video capture/editing/playout here) then log IO > will also ensure that the data written by the app is on disk (i.e. > that's ithe mechanism by which fsync works). So this would be an interesting upside down case for XFS, as the file data may be intact, but the filesystem gets corrupted, the opposite of the design point. > Hence even assumptions that there will be data loss are dependent on > how the application is doing it's IO.... I didn't assume there _will_ be data loss. I'm simply trying to help the guy think about covering all the bases, which is the smart thing to do, is it not? I've never designed any system with the "assumption" that pulling the plug is the standard mode of system shutdown. ;) I doubt anyone else here has either. So we're all working a bit "outside the box" here, yes? >>> Also, if there are active writers, this is inherently racy. A better >>> script would unmount the file systems :) >> >> Yes, a umount would be even better. > > Change the bios so that the power button does not cause a power down > so the OS can capture the button event and trigger an orderly > shutdown. Dare I say "Dave you're incorrect". ;) The OP already stated that all the gear, whatever that is, in the vans is controlled by a master switch, probably something like an 8 outlet surge protector/power strip, and the techs power down all the gear by this one switch. So this solution doesn't work either. I think someone already suggested this upstream in the thread. This is one of those classic cases of computers being injected into a field application where the users are so used to dumb/analog devices that they simply can't/won't adapt, resist, or simply take a long time to assimilate. Reminds me of a similar case some time ago... When I ordered my first aDSL circuit back in ~2000 it took SW Bell 6 weeks to get it working. The field techs had been trained and worked in the analog phone world for 70+ years and these guys are the antithesis of technical folks. In my case the port on the brand new Alcatel DSLAM was defective. Took 4 weeks and a dozen different techs to finally diagnose it, and another 2 weeks of "paperwork" to reassign my circuit to another DSLAM port, though the bureaucracy issue wasn't the techs' fault. From what I understand it took about 2 years for these guys to become proficient with DSL installations. Let's hope for OP's sake that it doesn't take two years for his guys to learn and adapt to this "new" digital recording system. I put "new" in quotes, as having worked for SGI Dave you know this direct to disk recording technology has been around for over a decade. -- Stan From sgi-linux-xfs@m.gmane.org Sat Mar 9 14:54:52 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=FREEMAIL_FROM autolearn=ham version=3.3.1 X-Original-To: linux-xfs@oss.sgi.com Delivered-To: linux-xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id DE1237F5A for ; Sat, 9 Mar 2013 14:54:52 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay1.corp.sgi.com (Postfix) with ESMTP id BC1E48F8037 for ; Sat, 9 Mar 2013 12:54:49 -0800 (PST) X-ASG-Debug-ID: 1362862483-04cbb07dbc3644b0001-w1Z2WR Received: from plane.gmane.org (plane.gmane.org [80.91.229.3]) by cuda.sgi.com with ESMTP id YLFhQ23TZygrGL6b (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO) for ; Sat, 09 Mar 2013 12:54:45 -0800 (PST) X-Barracuda-Envelope-From: sgi-linux-xfs@m.gmane.org X-Barracuda-Apparent-Source-IP: 80.91.229.3 Received: from list by plane.gmane.org with local (Exim 4.69) (envelope-from ) id 1UEQnI-0007bw-29 for linux-xfs@oss.sgi.com; Sat, 09 Mar 2013 21:55:04 +0100 Received: from blfd-4db017aa.pool.mediaways.net ([77.176.23.170]) by main.gmane.org with esmtp (Gmexim 0.1 (Debian)) id 1AlnuQ-0007hv-00 for ; Sat, 09 Mar 2013 21:55:04 +0100 Received: from pa5ca1 by blfd-4db017aa.pool.mediaways.net with local (Gmexim 0.1 (Debian)) id 1AlnuQ-0007hv-00 for ; Sat, 09 Mar 2013 21:55:04 +0100 X-Injected-Via-Gmane: http://gmane.org/ To: linux-xfs@oss.sgi.com From: Pascal Subject: Maximum file system size of XFS? Date: Sat, 9 Mar 2013 21:51:21 +0100 X-ASG-Orig-Subj: Maximum file system size of XFS? Lines: 24 Message-ID: <20130309215121.0e614ef8@thinky> Mime-Version: 1.0 Content-Type: text/plain; charset=US-ASCII Content-Transfer-Encoding: 7bit X-Complaints-To: usenet@ger.gmane.org X-Gmane-NNTP-Posting-Host: blfd-4db017aa.pool.mediaways.net X-Newsreader: Claws Mail 3.8.0 (GTK+ 2.24.10; x86_64-pc-linux-gnu) X-Barracuda-Connect: plane.gmane.org[80.91.229.3] X-Barracuda-Start-Time: 1362862484 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124734 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- Hello, I am asking you because I am insecure about the correct answer and different sources give me different numbers. My question is: What is the maximum file system size of XFS? The official page says: 2^63 = 9 x 10^18 = 9 exabytes Source: http://oss.sgi.com/projects/xfs/ Wikipedia says 16 exabytes. Source: https://en.wikipedia.org/wiki/XFS Another reference books says 8 exabytes (2^63). Can anyone tell me and explain what is the maximum file system size for XFS? Thank you in advance! Pascal From rwheeler@redhat.com Sat Mar 9 16:29:36 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: linux-xfs@oss.sgi.com Delivered-To: linux-xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 062297F56 for ; Sat, 9 Mar 2013 16:29:36 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay1.corp.sgi.com (Postfix) with ESMTP id CB7938F8059 for ; Sat, 9 Mar 2013 14:29:32 -0800 (PST) X-ASG-Debug-ID: 1362868171-04bdf0229837dbf0001-w1Z2WR Received: from mx1.redhat.com (mx1.redhat.com [209.132.183.28]) by cuda.sgi.com with ESMTP id q9Mcpf6MnEfdvlFB for ; Sat, 09 Mar 2013 14:29:32 -0800 (PST) X-Barracuda-Envelope-From: rwheeler@redhat.com X-Barracuda-Apparent-Source-IP: 209.132.183.28 X-ASG-Whitelist: Client Received: from int-mx12.intmail.prod.int.phx2.redhat.com (int-mx12.intmail.prod.int.phx2.redhat.com [10.5.11.25]) by mx1.redhat.com (8.14.4/8.14.4) with ESMTP id r29MTPTa003485 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=OK); Sat, 9 Mar 2013 17:29:26 -0500 Received: from tunkums.home ([10.3.112.7]) by int-mx12.intmail.prod.int.phx2.redhat.com (8.14.4/8.14.4) with ESMTP id r29MTOS7023519; Sat, 9 Mar 2013 17:29:25 -0500 Message-ID: <513BB7C3.4050009@redhat.com> Date: Sat, 09 Mar 2013 17:29:23 -0500 From: Ric Wheeler User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:17.0) Gecko/20130219 Thunderbird/17.0.3 MIME-Version: 1.0 To: Pascal CC: linux-xfs@oss.sgi.com Subject: Re: Maximum file system size of XFS? References: <20130309215121.0e614ef8@thinky> X-ASG-Orig-Subj: Re: Maximum file system size of XFS? In-Reply-To: <20130309215121.0e614ef8@thinky> Content-Type: text/plain; charset=ISO-8859-1; format=flowed Content-Transfer-Encoding: 7bit X-Scanned-By: MIMEDefang 2.68 on 10.5.11.25 X-Barracuda-Connect: mx1.redhat.com[209.132.183.28] X-Barracuda-Start-Time: 1362868172 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 On 03/09/2013 03:51 PM, Pascal wrote: > Hello, > > I am asking you because I am insecure about the correct answer and > different sources give me different numbers. > > > My question is: What is the maximum file system size of XFS? > > The official page says: 2^63 = 9 x 10^18 = 9 exabytes > Source: http://oss.sgi.com/projects/xfs/ > > Wikipedia says 16 exabytes. > Source: https://en.wikipedia.org/wiki/XFS > > Another reference books says 8 exabytes (2^63). > > > Can anyone tell me and explain what is the maximum file system size for > XFS? > > > Thank you in advance! > > Pascal > The maximum size that XFS can address (which is what most people post in things like wikipedia) is kind of a fantasy number. What is a better question is what is the maximum size XFS file system people have in production (even better, people who have your same work load). Lots and lots of tiny files are more challenging than very large video files for example. I think that you can easily find people with 100's of terabytes in production use. For Red Hat, we support production use of 100TB per XFS instance in RHEL6 for example since that is what we test at (and have been know to officially support larger instances by exception). Some of the things to watch out for in very large file systems is how much DRAM you have in the server. If you ever need to xfs_repair a 1PB file system, you will need a very beefy box :) Ric From pa5ca1@gmx.de Sat Mar 9 16:39:44 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.3 required=5.0 tests=FREEMAIL_ENVFROM_END_DIGIT, FREEMAIL_FROM autolearn=no version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id C618F7F56 for ; Sat, 9 Mar 2013 16:39:44 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay1.corp.sgi.com (Postfix) with ESMTP id A61B68F8035 for ; Sat, 9 Mar 2013 14:39:44 -0800 (PST) X-ASG-Debug-ID: 1362868782-04cb6c2b03362450001-NocioJ Received: from mout.gmx.net (mout.gmx.net [212.227.15.15]) by cuda.sgi.com with ESMTP id cm0y7MxaYUKuUvP0 for ; Sat, 09 Mar 2013 14:39:43 -0800 (PST) X-Barracuda-Envelope-From: pa5ca1@gmx.de X-Barracuda-Apparent-Source-IP: 212.227.15.15 Received: from mailout-de.gmx.net ([10.1.76.12]) by mrigmx.server.lan (mrigmx002) with ESMTP (Nemesis) id 0MDjZQ-1TzYBM2Kzu-00H3jB for ; Sat, 09 Mar 2013 23:39:42 +0100 Received: (qmail invoked by alias); 09 Mar 2013 22:39:42 -0000 Received: from blfd-4db017aa.pool.mediaWays.net (EHLO thinky) [77.176.23.170] by mail.gmx.net (mp012) with SMTP; 09 Mar 2013 23:39:42 +0100 X-Authenticated: #135750480 X-Provags-ID: V01U2FsdGVkX19u38FrZZJu2z3Dm9yxyoiHaYQD1b9p75I09cdl2x jMB0nXaK0gfAQm Date: Sat, 9 Mar 2013 23:39:40 +0100 From: Pascal To: xfs@oss.sgi.com Subject: Re: Maximum file system size of XFS? Message-ID: <20130309233940.3b7c0910@thinky> X-ASG-Orig-Subj: Re: Maximum file system size of XFS? In-Reply-To: <513BB7C3.4050009@redhat.com> References: <20130309215121.0e614ef8@thinky> <513BB7C3.4050009@redhat.com> X-Mailer: Claws Mail 3.8.0 (GTK+ 2.24.10; x86_64-pc-linux-gnu) Mime-Version: 1.0 Content-Type: text/plain; charset=US-ASCII Content-Transfer-Encoding: 7bit X-Y-GMX-Trusted: 0 X-Barracuda-Connect: mout.gmx.net[212.227.15.15] X-Barracuda-Start-Time: 1362868783 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124740 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- Am Sat, 09 Mar 2013 17:29:23 -0500 schrieb Ric Wheeler : > On 03/09/2013 03:51 PM, Pascal wrote: > > Hello, > > > > I am asking you because I am insecure about the correct answer and > > different sources give me different numbers. > > > > > > My question is: What is the maximum file system size of XFS? > > > > The official page says: 2^63 = 9 x 10^18 = 9 exabytes > > Source: http://oss.sgi.com/projects/xfs/ > > > > Wikipedia says 16 exabytes. > > Source: https://en.wikipedia.org/wiki/XFS > > > > Another reference books says 8 exabytes (2^63). > > > > > > Can anyone tell me and explain what is the maximum file system size > > for XFS? > > > > > > Thank you in advance! > > > > Pascal > > > > The maximum size that XFS can address (which is what most people post > in things like wikipedia) is kind of a fantasy number. > > What is a better question is what is the maximum size XFS file system > people have in production (even better, people who have your same > work load). Lots and lots of tiny files are more challenging than > very large video files for example. > > I think that you can easily find people with 100's of terabytes in > production use. For Red Hat, we support production use of 100TB per > XFS instance in RHEL6 for example since that is what we test at (and > have been know to officially support larger instances by exception). > > Some of the things to watch out for in very large file systems is how > much DRAM you have in the server. If you ever need to xfs_repair a > 1PB file system, you will need a very beefy box :) > > Ric > > _______________________________________________ > xfs mailing list > xfs@oss.sgi.com > http://oss.sgi.com/mailman/listinfo/xfs > Hello Ric, thank you for your answer. I am aware that there is a difference between the maximum size under practical conditions and the theoretical maximum. But I am looking for this theoretical number to use in within in my thesis comparing file systems. From sandeen@sandeen.net Sat Mar 9 18:24:53 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id B60727F51 for ; Sat, 9 Mar 2013 18:24:53 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay2.corp.sgi.com (Postfix) with ESMTP id 88C45304043 for ; Sat, 9 Mar 2013 16:24:50 -0800 (PST) X-ASG-Debug-ID: 1362875088-04bdf02298383e40001-NocioJ Received: from sandeen.net (sandeen.net [63.231.237.45]) by cuda.sgi.com with ESMTP id Iqjps7bKI8VfBS19 for ; Sat, 09 Mar 2013 16:24:48 -0800 (PST) X-Barracuda-Envelope-From: sandeen@sandeen.net X-Barracuda-Apparent-Source-IP: 63.231.237.45 Received: from liberator.sandeen.net (liberator.sandeen.net [10.0.0.4]) (using TLSv1 with cipher DHE-RSA-CAMELLIA256-SHA (256/256 bits)) (No client certificate requested) by sandeen.net (Postfix) with ESMTPSA id 4D653602D818; Sat, 9 Mar 2013 18:24:48 -0600 (CST) Message-ID: <513BD2CF.5020204@sandeen.net> Date: Sat, 09 Mar 2013 18:24:47 -0600 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: Koen De Wit CC: xfs@oss.sgi.com, linux-btrfs Subject: Re: xfstests: 301: sparse copy between different filesystems/mountpoints on btrfs References: <50F9C331.9000501@oracle.com> X-ASG-Orig-Subj: Re: xfstests: 301: sparse copy between different filesystems/mountpoints on btrfs In-Reply-To: <50F9C331.9000501@oracle.com> X-Enigmail-Version: 1.5.1 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: sandeen.net[63.231.237.45] X-Barracuda-Start-Time: 1362875088 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124748 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On 1/18/13 3:48 PM, Koen De Wit wrote: > Signed-off-by: Koen De Wit > > --- > 301 | 95 > +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ > 301.out | 7 ++++ > 2 files changed, 102 insertions(+), 0 deletions(-) > create mode 100644 301 > create mode 100644 301.out > Invalid cross-device link > +0 Seems like the above lines should be at the end of the patch (?) > diff --git a/301 b/301 > new file mode 100644 > index 0000000..05b9b39 > --- /dev/null > +++ b/301 > @@ -0,0 +1,95 @@ > +#! /bin/bash > +# FS QA Test No. 301 > +# > +# Check if creating a sparse copy ("reflink") of a file on btrfs > +# expectedly fails when it's done betweeen different filesystems or > +# different mount points of the same filesystem. > +# > +# For both situations, these actions are executed: > +# - Copy a file with the reflink=auto option. > +# A normal copy should be created. > +# - Copy a file with the reflink=always option. Should result in error, > +# no file should be created. > +# > +#----------------------------------------------------------------------- > +# Copyright (c) 2013, Oracle and/or its affiliates. All Rights Reserved. > +# > +# This program is free software; you can redistribute it and/or > +# modify it under the terms of the GNU General Public License as > +# published by the Free Software Foundation. > +# > +# This program is distributed in the hope that it would be useful, > +# but WITHOUT ANY WARRANTY; without even the implied warranty of > +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the > +# GNU General Public License for more details. > +# > +# You should have received a copy of the GNU General Public License > +# along with this program; if not, write the Free Software Foundation, > +# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA > +#----------------------------------------------------------------------- > +# > +# creator > +owner=koen.de.wit@oracle.com > + > +seq=`basename $0` > +echo "QA output created by $seq" > + > +here=`pwd` > +tmp=/tmp/$$ > +status=1 # failure is the default! > +trap "_cleanup; exit \$status" 0 1 2 3 15 > + > +_cleanup() > +{ > + cd / > + rm -f $tmp.* > +} > + > +# get standard environment, filters and checks > +. ./common.rc > +. ./common.filter > + > +# real QA test starts here > +_supported_fs btrfs > +_supported_os Linux > + > +_require_scratch > +_require_cp_reflink same deal, need thisdefinition > + > +TESTDIR1=$TEST_DIR/test-$seq.$$ > +TESTDIR2=$SCRATCH_MNT/test-$seq.$$ > +TESTDIR3=$SCRATCH_MNT/test-bis-$seq.$$ I might drop the .$$ for reasons stated earlier, etc. You might also consider not naming something on $SCRATCH_MNT as $TESTDIR when there's another standard variable named $TEST_DIR - it's confusing. Maybe name them as TEST_SOURCEDIR, SCRATCH_TARGETDIR1, or similar, to make it easier to keep it straight when reading the test. > + > +mkdir $TESTDIR1 > +_scratch_mkfs > +$XFS_IO_PROG -f -c 'pwrite -S 0x61 0 9000' $TESTDIR1/original > /dev/null > + > +_filter_testdirs() > +{ > + sed -e "s,$TESTDIR1,TESTDIR1,g" \ > + -e "s,$TESTDIR2,TESTDIR2,g" \ > + -e "s,$TESTDIR3,TESTDIR3,g" > +} > + > +_create_reflinks_to() > +{ > + mkdir $1 > + cp --reflink=auto $TESTDIR1/original $1/copy > + md5sum $1/copy | $AWK_PROG 'END {print $1}' for more output context: md5sum $1/copy | _filter_testdirs > + rm -rf $1 > + mkdir $1 > + cp --reflink=always $TESTDIR1/original $1/copyfail 2>&1 | > _filter_testdirs patch wrapped > + ls $1/copyfail | wc -l Here if you dropped the $$ from the filename and did: ls $1/copyfail | _filter_testdirs the output might be more informative on a failure? > +} > + > +_scratch_mount > +_create_reflinks_to $TESTDIR2 > +_scratch_unmount > + > +mount $TEST_DEV $SCRATCH_MNT > +_create_reflinks_to $TESTDIR3 > +umount $SCRATCH_MNT TBH this confuses me, not that it's necessarily wrong (?) You mount TEST_DEV on $SCRATCH_MNT which makes my brain hurt a little. Then _create_reflinks_to $TESTDIR3 and at that point, um, what's going on, what's linking what to where? Some comments about what is being tested & the expected result, maybe w/ echos like mentioned before, and descriptive var names would help me, at least. > + > +# success, all done > +status=0 > +exit > diff --git a/301.out b/301.out > new file mode 100644 > index 0000000..3b66682 > --- /dev/null > +++ b/301.out > @@ -0,0 +1,7 @@ > +QA output created by 301 > +42d69d1a6d333a7ebdf64792a555e392 > +cp: failed to clone `TESTDIR2/copyfail' from `TESTDIR1/original': Invalid cross-device link Hm, my cp fails like: +cp: failed to clone `TESTDIR3/copyfail': Invalid cross-device link so might need a special filter to catch both variants. > +0 > +42d69d1a6d333a7ebdf64792a555e392 > +cp: failed to clone `TESTDIR3/copyfail' from `TESTDIR1/original': malformed patch, supposed to be 7 new lines but only 6. Thanks, -Eric From sandeen@sandeen.net Sat Mar 9 18:25:02 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 104567F55 for ; Sat, 9 Mar 2013 18:25:02 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay3.corp.sgi.com (Postfix) with ESMTP id 83653AC001 for ; Sat, 9 Mar 2013 16:24:58 -0800 (PST) X-ASG-Debug-ID: 1362875096-04cbb07dbc372930001-NocioJ Received: from sandeen.net (sandeen.net [63.231.237.45]) by cuda.sgi.com with ESMTP id m5OI35nEmvAB6Mx0 for ; Sat, 09 Mar 2013 16:24:56 -0800 (PST) X-Barracuda-Envelope-From: sandeen@sandeen.net X-Barracuda-Apparent-Source-IP: 63.231.237.45 Received: from liberator.sandeen.net (liberator.sandeen.net [10.0.0.4]) (using TLSv1 with cipher DHE-RSA-CAMELLIA256-SHA (256/256 bits)) (No client certificate requested) by sandeen.net (Postfix) with ESMTPSA id 5CBFB63C3D47; Sat, 9 Mar 2013 18:24:56 -0600 (CST) Message-ID: <513BD2D8.2030404@sandeen.net> Date: Sat, 09 Mar 2013 18:24:56 -0600 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: Koen De Wit CC: xfs@oss.sgi.com, linux-btrfs Subject: Re: xfstests: 303: send/receive functionality of btrfs References: <50F9C340.5050309@oracle.com> X-ASG-Orig-Subj: Re: xfstests: 303: send/receive functionality of btrfs In-Reply-To: <50F9C340.5050309@oracle.com> X-Enigmail-Version: 1.5.1 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: sandeen.net[63.231.237.45] X-Barracuda-Start-Time: 1362875096 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124748 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On 1/18/13 3:48 PM, Koen De Wit wrote: > Signed-off-by: Koen De Wit > > --- > 303 | 127 > +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ > 303.out | 72 +++++++++++++++++++++++++++++++++++ > group | 7 +++ > 3 files changed, 206 insertions(+), 0 deletions(-) > create mode 100644 303 > create mode 100644 303.out > > diff --git a/303 b/303 > new file mode 100644 > index 0000000..6a5628d > --- /dev/null > +++ b/303 > @@ -0,0 +1,127 @@ > +#! /bin/bash > +# FS QA Test No. 303 > +# > +# Tests btrfs send/receive functionality > +# > +#----------------------------------------------------------------------- > +# Copyright (c) 2013, Oracle and/or its affiliates. All Rights Reserved. > +# > +# This program is free software; you can redistribute it and/or > +# modify it under the terms of the GNU General Public License as > +# published by the Free Software Foundation. > +# > +# This program is distributed in the hope that it would be useful, > +# but WITHOUT ANY WARRANTY; without even the implied warranty of > +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the > +# GNU General Public License for more details. > +# > +# You should have received a copy of the GNU General Public License > +# along with this program; if not, write the Free Software Foundation, > +# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA > +#----------------------------------------------------------------------- > +# > +# creator > +owner=koen.de.wit@oracle.com > + > +seq=`basename $0` > +echo "QA output created by $seq" > + > +here=`pwd` > +tmp=/tmp/$$ > +status=1 # failure is the default! > +trap "_cleanup; exit \$status" 0 1 2 3 15 > + > +_cleanup() > +{ > + rm -f $tmp.* > + btrfs subvolume delete $MAINPATH | _filter_test_dir > + btrfs subvolume delete $TEST_DIR/snap1 | _filter_test_dir > + btrfs subvolume delete $TEST_DIR/snap2 | _filter_test_dir > + btrfs subvolume delete $TEST_DIR/snap3 | _filter_test_dir > + btrfs subvolume delete $TEST_DIR/snap4 | _filter_test_dir > +} > + > +# get standard environment, filters and checks > +. ./common.rc > +. ./common.filter > + > +# real QA test starts here > + > +# Modify as appropriate. > +_supported_fs btrfs > +_supported_os Linux > + > +_compare_to_main() { > + # Compare file contents > + diff -r $MAINPATH $1 > + # Compare file attributes nitpick but can you get consistent indentation here? > + ls -lR $MAINPATH | _filter_test_dir > $TEST_DIR/main-files > + ls -lR $1 | _filter_scratch > $TEST_DIR/compare-files > + diff $TEST_DIR/main-files $TEST_DIR/compare-files > +} > + > +# Setup main subvolume > +MAINPATH=$TEST_DIR/main > +btrfs subvolume create $MAINPATH > + > +# Create btrfs filesystem on scratch disk > +_scratch_mkfs > + > +# Create a directory and three files in the main subvolume. Changing these comments to echos adds context to output > +xfs_io -f -c 'pwrite -S 0x61 0 9000' $MAINPATH/file1 > /dev/null > +xfs_io -f -c 'pwrite -S 0x62 0 11000' $MAINPATH/file2 > /dev/null > +mkdir $MAINPATH/dir1 > +xfs_io -f -c 'pwrite -S 0x63 0 13000' $MAINPATH/dir1/file3 > /dev/null > +xfs_io -f -c 'pwrite -S 0x64 0 15000' $MAINPATH/dir1/file4 > /dev/null > +mkdir $MAINPATH/dir2 > +xfs_io -f -c 'pwrite -S 0x65 0 17000' $MAINPATH/dir1/file5 > /dev/null > + > +# Create a snapshot of main and replay on the scratch disk. > +btrfs subvolume snapshot -r $MAINPATH $TEST_DIR/snap1 | _filter_test_dir > +btrfs send $TEST_DIR/snap1 > $TEST_DIR/snap1.send | _filter_test_dir > +btrfs receive -f $TEST_DIR/snap1.send $SCRATCH_MNT > +_compare_to_main $SCRATCH_MNT/snap1 > + > +# Change, add and delete files in the main subvolume. > +xfs_io -c 'pwrite -S 0x66 5000 19000' $MAINPATH/dir1/file3 > /dev/null > +rm $MAINPATH/file2 > +mkdir $MAINPATH/dir1/dir3 > +xfs_io -f -c 'pwrite -S 0x67 0 21000' $MAINPATH/dir1/dir3/file6 > /dev/null > +chmod +x $MAINPATH/dir1/file4 > + > +# Create a snapshot of main, the first snapshot being the parent. > +btrfs subvolume snapshot -r $MAINPATH $TEST_DIR/snap2 | _filter_test_dir > +btrfs send -p $TEST_DIR/snap1 $TEST_DIR/snap2 \ > + > $TEST_DIR/snap2.send | _filter_test_dir > +btrfs receive -f $TEST_DIR/snap2.send $SCRATCH_MNT > +_compare_to_main $SCRATCH_MNT/snap2 > + > +# Reflink a new file and a file existing on another subvolume > +cp --reflink $TEST_DIR/snap1/file2 $MAINPATH/dir1/dir3 > +xfs_io -f -c 'pwrite -S 0x68 0 23000' $TEST_DIR/file7 > /dev/null > +cp --reflink $TEST_DIR/file7 $MAINPATH/dir2 > + > +# Create a snapshot with a parent and clone source. > +btrfs subvolume snapshot -r $MAINPATH $TEST_DIR/snap3 | _filter_test_dir > +btrfs send -p $TEST_DIR/snap2 -i $TEST_DIR/snap1 $TEST_DIR/snap3 \ > + > $TEST_DIR/snap3.send | _filter_test_dir > +btrfs receive -f $TEST_DIR/snap3.send $SCRATCH_MNT > +_compare_to_main $SCRATCH_MNT/snap3 > + > +# Error scenario: clone source does not exist on target disk > +btrfs subvolume delete $SCRATCH_MNT/snap1 | _filter_scratch > +btrfs subvolume delete $SCRATCH_MNT/snap3 | _filter_scratch > +btrfs receive -f $TEST_DIR/snap3.send $SCRATCH_MNT 2>&1 | _filter_scratch > + > +# Error scenario: parent source does not exist on target disk > +btrfs subvolume delete $SCRATCH_MNT/snap2 | _filter_scratch > +btrfs receive -f $TEST_DIR/snap2.send $SCRATCH_MNT 2>&1 | _filter_scratch > + > +# Error scenario: snapshotting a writable subvolume > +btrfs subvolume snapshot $MAINPATH $TEST_DIR/snap4 | _filter_test_dir > +btrfs send $TEST_DIR/snap4 2>&1 | _filter_test_dir > + > +# success, all done > +status=0 > +exit > diff --git a/303.out b/303.out > new file mode 100644 > index 0000000..da4bec8 > --- /dev/null > +++ b/303.out > @@ -0,0 +1,72 @@ > +QA output created by 303 > +Create subvolume '/mnt/diskb/main' > +/dev/sdf1 is mounted Not sure what generated that devicename, but if it's expected output it needs to be filtered. > +Create a readonly snapshot of 'TEST_DIR/main' in 'TEST_DIR/snap1' > +At subvol /mnt/diskb/snap1 > +At subvol snap1 > +1c1 > +< TEST_DIR/main: > +--- > +> SCRATCH_MNT/snap1: > +8c8 > +< TEST_DIR/main/dir1: > +--- > +> SCRATCH_MNT/snap1/dir1: > +14c14 > +< TEST_DIR/main/dir2: > +--- > +> SCRATCH_MNT/snap1/dir2: > +Create a readonly snapshot of 'TEST_DIR/main' in 'TEST_DIR/snap2' > +At subvol /mnt/diskb/snap2 > +At snapshot snap2 > +1c1 > +< TEST_DIR/main: > +--- > +> SCRATCH_MNT/snap2: > +7,8c7,8 > +< TEST_DIR/main/dir1: > +< total 60 > +--- > +> SCRATCH_MNT/snap2/dir1: > +> total 72 > +14c14 > +< TEST_DIR/main/dir1/dir3: > +--- > +> SCRATCH_MNT/snap2/dir1/dir3: > +18c18 > +< TEST_DIR/main/dir2: > +--- > +> SCRATCH_MNT/snap2/dir2: > +Create a readonly snapshot of 'TEST_DIR/main' in 'TEST_DIR/snap3' > +At subvol /mnt/diskb/snap3 > +At snapshot snap3 > +1c1 > +< TEST_DIR/main: > +--- > +> SCRATCH_MNT/snap3: > +7c7 > +< TEST_DIR/main/dir1: > +--- > +> SCRATCH_MNT/snap3/dir1: > +14c14 > +< TEST_DIR/main/dir1/dir3: > +--- > +> SCRATCH_MNT/snap3/dir1/dir3: > +19c19 > +< TEST_DIR/main/dir2: > +--- > +> SCRATCH_MNT/snap3/dir2: > +Delete subvolume 'SCRATCH_MNT/snap1' > +Delete subvolume 'SCRATCH_MNT/snap3' > +ERROR: Failed to lookup path for root 0 - No such file or directory > +ERROR: unable to resolve path for root 257 > +Delete subvolume 'SCRATCH_MNT/snap2' > +At snapshot snap2 > +ERROR: could not find parent subvolume > +Create a snapshot of 'TEST_DIR/main' in 'TEST_DIR/snap4' > +ERROR: TEST_DIR/snap4 is not read-only. > +Delete subvolume 'TEST_DIR/main' > +Delete subvolume 'TEST_DIR/snap1' > +Delete subvolume 'TEST_DIR/snap2' > +Delete subvolume 'TEST_DIR/snap3' > +Delete subvolume 'TEST_DIR/snap4' > diff --git a/group b/group > index 1fdae31..af5356d 100644 > --- a/group > +++ b/group > @@ -412,3 +412,10 @@ deprecated > 291 repair > 292 auto mkfs quick > 293 auto quick > +297 auto rw > +298 auto rw > +299 auto rw > +300 auto rw > +301 auto rw > +302 auto rw > +303 auto > From sandeen@sandeen.net Sat Mar 9 18:25:03 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 660847F58 for ; Sat, 9 Mar 2013 18:25:03 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id 560F5304048 for ; Sat, 9 Mar 2013 16:25:03 -0800 (PST) X-ASG-Debug-ID: 1362875101-04cbb07dbc372940001-NocioJ Received: from sandeen.net (sandeen.net [63.231.237.45]) by cuda.sgi.com with ESMTP id f41tO59dG7X1BoDU for ; Sat, 09 Mar 2013 16:25:02 -0800 (PST) X-Barracuda-Envelope-From: sandeen@sandeen.net X-Barracuda-Apparent-Source-IP: 63.231.237.45 Received: from liberator.sandeen.net (liberator.sandeen.net [10.0.0.4]) (using TLSv1 with cipher DHE-RSA-CAMELLIA256-SHA (256/256 bits)) (No client certificate requested) by sandeen.net (Postfix) with ESMTPSA id C253963C3D47; Sat, 9 Mar 2013 18:25:01 -0600 (CST) Message-ID: <513BD2DD.6050609@sandeen.net> Date: Sat, 09 Mar 2013 18:25:01 -0600 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: Koen De Wit CC: xfs@oss.sgi.com, linux-btrfs Subject: Re: xfstests: 302: cross-subvolume sparse copies on btrfs References: <50F9C339.6010000@oracle.com> X-ASG-Orig-Subj: Re: xfstests: 302: cross-subvolume sparse copies on btrfs In-Reply-To: <50F9C339.6010000@oracle.com> X-Enigmail-Version: 1.5.1 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: sandeen.net[63.231.237.45] X-Barracuda-Start-Time: 1362875101 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124748 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On 1/18/13 3:48 PM, Koen De Wit wrote: > Signed-off-by: Koen De Wit > > --- > 302 | 108 > +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ > 302.out | 28 ++++++++++++++++ > 2 files changed, 136 insertions(+), 0 deletions(-) > create mode 100644 302 > create mode 100644 302.out > > diff --git a/302 b/302 > new file mode 100644 > index 0000000..b7f7507 > --- /dev/null > +++ b/302 > @@ -0,0 +1,108 @@ > +#! /bin/bash > +# FS QA Test No. 302 > +# > +# Testing cross-subvolume sparse copy on btrfs > +# - Create two subvolumes, mount one of them > +# - Create a file on each (sub/root)volume, > +# reflink them on the other volumes > +# - Change one original and two reflinked files > +# - Move and delete files > +# > +#----------------------------------------------------------------------- > +# Copyright (c) 2013, Oracle and/or its affiliates. All Rights Reserved. > +# > +# This program is free software; you can redistribute it and/or > +# modify it under the terms of the GNU General Public License as > +# published by the Free Software Foundation. > +# > +# This program is distributed in the hope that it would be useful, > +# but WITHOUT ANY WARRANTY; without even the implied warranty of > +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the > +# GNU General Public License for more details. > +# > +# You should have received a copy of the GNU General Public License > +# along with this program; if not, write the Free Software Foundation, > +# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA > +#----------------------------------------------------------------------- > +# > +# creator > +owner=koen.de.wit@oracle.com > + > +seq=`basename $0` > +echo "QA output created by $seq" > + > +here=`pwd` > +tmp=/tmp/$$ > +status=1 # failure is the default! > +trap "_cleanup; exit \$status" 0 1 2 3 15 > + > +_cleanup() > +{ > + cd / > + rm -f $tmp.* should cleanup delete created subvols? > +} > + > +# get standard environment, filters and checks > +. ./common.rc > +. ./common.filter > + > +# real QA test starts here > +_supported_fs btrfs > +_supported_os Linux > + > +_require_scratch > +_require_cp_reflink same basic stuff, need the above deifined somewehre, add to groups, add some context to output & comments if you would, to make it easier for future testers. > + > +_catfiles() { _checksum_files > + for D in $TESTDIR1 $SCRATCH_MNT $SUBVOL2 > + do > + for F in file1 file2 file3 > + do > + md5sum $D/$F | $AWK_PROG 'END {print $1}' md5sum $D/$F | _filter_testdirs to get filenames? > + done > + done > +} > + > +_scratch_unmount 2>/dev/null > +TESTDIR1=$TEST_DIR/test-$seq.$$-1 > +TESTDIR2=$TEST_DIR/test-$seq.$$-2 > +SUBVOL1=$TEST_DIR/subvol-$seq.$$-1 > +SUBVOL2=$TEST_DIR/subvol-$seq.$$-2 same mild concern w/ using pids. > + > +mkdir $TESTDIR1 > +mkdir $TESTDIR2 > +btrfs subvolume create $SUBVOL1 > /dev/null > +btrfs subvolume create $SUBVOL2 > /dev/null > +mount -t btrfs -o subvol=subvol-$seq.$$-1 $TEST_DEV $SCRATCH_MNT eek, $TEST_DEV on $SCRATCH_MNT again ;) I guess we need some more btrfs-aware basic infrastructure. > + > +$XFS_IO_PROG -f -c 'pwrite -S 0x61 0 9000' $TESTDIR1/file1 > /dev/null > +$XFS_IO_PROG -f -c 'pwrite -S 0x62 0 13000' $SCRATCH_MNT/file2 > /dev/null > +$XFS_IO_PROG -f -c 'pwrite -S 0x63 0 17000' $SUBVOL2/file3 > /dev/null echos & things to add context to the output file would help. > +cp --reflink $TESTDIR1/file1 $SUBVOL1 > +cp --reflink $TESTDIR1/file1 $SUBVOL2 > +cp --reflink $SUBVOL1/file2 $TESTDIR1/ > +cp --reflink $SUBVOL1/file2 $SUBVOL2 > +cp --reflink $SUBVOL2/file3 $TESTDIR1/ > +cp --reflink $SUBVOL2/file3 $SUBVOL1 > +_catfiles > + > +$XFS_IO_PROG -c 'pwrite -S 0x64 0 9000' $TESTDIR1/file1 > /dev/null > +$XFS_IO_PROG -c 'pwrite -S 0x66 7000 21000' $SUBVOL2/file2 > /dev/null > +$XFS_IO_PROG -c 'pwrite -S 0x65 5000 5000' $SCRATCH_MNT/file3 > /dev/null > +_catfiles > + > +mv $TESTDIR1/file* $TESTDIR2 > +mv $SCRATCH_MNT/file* $TESTDIR1/ > +mv $SUBVOL2/file* $SCRATCH_MNT/ > +mv $TESTDIR2/file* $SUBVOL2/ > +_catfiles > + > +rm -rf $TESTDIR1 > +rm -rf $TESTDIR2 > +umount $SCRATCH_MNT > +btrfs subvolume delete $SUBVOL1 > /dev/null > +btrfs subvolume delete $SUBVOL2 > /dev/null > + > +# success, all done > +status=0 > +exit > diff --git a/302.out b/302.out > new file mode 100644 > index 0000000..a4bc12e > --- /dev/null > +++ b/302.out > @@ -0,0 +1,28 @@ > +QA output created by 302 you can imagine the problem here if, say, the 12th md5sum is wrong in the output. What's a tester to think? ;) > +42d69d1a6d333a7ebdf64792a555e392 > +d7402b46310fbbfbc5e466b1dccb043b > +5a95800e4c04b11117aa4e4de057721f > +42d69d1a6d333a7ebdf64792a555e392 > +d7402b46310fbbfbc5e466b1dccb043b > +5a95800e4c04b11117aa4e4de057721f > +42d69d1a6d333a7ebdf64792a555e392 > +d7402b46310fbbfbc5e466b1dccb043b > +5a95800e4c04b11117aa4e4de057721f > +2e26ad0e8b8e123d18c2d20c81cab0a8 > +d7402b46310fbbfbc5e466b1dccb043b > +5a95800e4c04b11117aa4e4de057721f > +42d69d1a6d333a7ebdf64792a555e392 > +d7402b46310fbbfbc5e466b1dccb043b > +b9f275cd638cb784c9e61def94c622a8 > +42d69d1a6d333a7ebdf64792a555e392 > +a229d0159dad76eecec390d9b1db16d3 > +5a95800e4c04b11117aa4e4de057721f > +42d69d1a6d333a7ebdf64792a555e392 > +d7402b46310fbbfbc5e466b1dccb043b > +b9f275cd638cb784c9e61def94c622a8 > +42d69d1a6d333a7ebdf64792a555e392 > +a229d0159dad76eecec390d9b1db16d3 > +5a95800e4c04b11117aa4e4de057721f > +2e26ad0e8b8e123d18c2d20c81cab0a8 > +d7402b46310fbbfbc5e466b1dccb043b > +5a95800e4c04b11117aa4e4de057721f > From sandeen@sandeen.net Sat Mar 9 19:10:11 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 7AE1F7F53 for ; Sat, 9 Mar 2013 19:10:11 -0600 (CST) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay2.corp.sgi.com (Postfix) with ESMTP id 5B221304032 for ; Sat, 9 Mar 2013 17:10:08 -0800 (PST) X-ASG-Debug-ID: 1362877806-04bdf02296386450001-NocioJ Received: from sandeen.net (sandeen.net [63.231.237.45]) by cuda.sgi.com with ESMTP id IC9nUFn0euw3UrGH for ; Sat, 09 Mar 2013 17:10:06 -0800 (PST) X-Barracuda-Envelope-From: sandeen@sandeen.net X-Barracuda-Apparent-Source-IP: 63.231.237.45 Received: from liberator.sandeen.net (liberator.sandeen.net [10.0.0.4]) (using TLSv1 with cipher DHE-RSA-CAMELLIA256-SHA (256/256 bits)) (No client certificate requested) by sandeen.net (Postfix) with ESMTPSA id 70A6663C3D47; Sat, 9 Mar 2013 19:10:06 -0600 (CST) Message-ID: <513BDD6E.7010507@sandeen.net> Date: Sat, 09 Mar 2013 19:10:06 -0600 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: Pascal CC: xfs@oss.sgi.com Subject: Re: Maximum file system size of XFS? References: <20130309215121.0e614ef8@thinky> <513BB7C3.4050009@redhat.com> <20130309233940.3b7c0910@thinky> X-ASG-Orig-Subj: Re: Maximum file system size of XFS? In-Reply-To: <20130309233940.3b7c0910@thinky> X-Enigmail-Version: 1.5.1 Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: sandeen.net[63.231.237.45] X-Barracuda-Start-Time: 1362877806 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124750 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On 3/9/13 4:39 PM, Pascal wrote: > Hello Ric, > > thank you for your answer. I am aware that there is a difference > between the maximum size under practical conditions and the theoretical > maximum. But I am looking for this theoretical number to use in within > in my thesis comparing file systems. A thesis comparing actual scalability would be much more interesting than one comparing, essentially, the container size chosen for a disk block. One could quickly write a filesystem which "can" be as large as a yottabyte, but it wouldn't really *mean* anything. -Eric From sandeen@sandeen.net Sat Mar 9 20:50:18 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 3D6B07F50 for ; Sat, 9 Mar 2013 20:50:18 -0600 (CST) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay2.corp.sgi.com (Postfix) with ESMTP id 2D10B304048 for ; Sat, 9 Mar 2013 18:50:15 -0800 (PST) X-ASG-Debug-ID: 1362883813-04cb6c2b04370800001-NocioJ Received: from sandeen.net (sandeen.net [63.231.237.45]) by cuda.sgi.com with ESMTP id xBavuboEMYa4fFAc for ; Sat, 09 Mar 2013 18:50:14 -0800 (PST) X-Barracuda-Envelope-From: sandeen@sandeen.net X-Barracuda-Apparent-Source-IP: 63.231.237.45 Received: from liberator.sandeen.net (liberator.sandeen.net [10.0.0.4]) (using TLSv1 with cipher DHE-RSA-CAMELLIA256-SHA (256/256 bits)) (No client certificate requested) by sandeen.net (Postfix) with ESMTPSA id ABB5B63C3D47; Sat, 9 Mar 2013 20:50:13 -0600 (CST) Message-ID: <513BF4E5.8080006@sandeen.net> Date: Sat, 09 Mar 2013 20:50:13 -0600 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: Julien FERRERO CC: stan@hardwarefreak.com, xfs@oss.sgi.com Subject: Re: XFS filesystem corruption References: <51380FD3.5010302@hardwarefreak.com> X-ASG-Orig-Subj: Re: XFS filesystem corruption In-Reply-To: X-Enigmail-Version: 1.5.1 Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: sandeen.net[63.231.237.45] X-Barracuda-Start-Time: 1362883813 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124758 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On 3/7/13 7:04 AM, Julien FERRERO wrote: >> It may be unrelated to your corruption, problem but I'm curious why you >> are specifying a 32MB log section instead of letting mkfs.xfs make the >> log size decision. > > I honestly don' know, the rebuild script was written 8 years ago by an > engineer that since left the company. > > Is 32MB a short log space for a 1.5 TB of data ? $ mkfs.xfs -dfile,name=fsfile,size=1536g meta-data=fsfile isize=256 agcount=4, agsize=100663296 blks = sectsz=512 attr=2, projid32bit=0 data = bsize=4096 blocks=402653184, imaxpct=5 = sunit=0 swidth=0 blks naming =version 2 bsize=4096 ascii-ci=0 log =internal log bsize=4096 blocks=196608, version=2 = sectsz=512 sunit=0 blks, lazy-count=1 realtime =none extsz=4096 blocks=0, rtextents=0 Default would be 768M w/ current xfsprogs. So I'd say yes it's short. You might do well to re-examine any old, crufty "engineer left a while ago" tunings. Defaults are defaults for a reason, if you don't know why you're tuning something it may well be the wrong choice. -Eric From stan@hardwarefreak.com Sun Mar 10 01:54:46 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id EB4537F3F for ; Sun, 10 Mar 2013 01:54:46 -0600 (CST) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id CA66B304048 for ; Sat, 9 Mar 2013 23:54:43 -0800 (PST) X-ASG-Debug-ID: 1362902082-04cbb07dbe3866f0001-NocioJ Received: from greer.hardwarefreak.com (mo-65-41-216-221.sta.embarqhsd.net [65.41.216.221]) by cuda.sgi.com with ESMTP id j142eyUNZXYKnpRs for ; Sat, 09 Mar 2013 23:54:42 -0800 (PST) X-Barracuda-Envelope-From: stan@hardwarefreak.com X-Barracuda-Apparent-Source-IP: 65.41.216.221 X-Barracuda-User-Whitelist: xfs@oss.sgi.com Received: from [192.168.100.53] (gffx.hardwarefreak.com [192.168.100.53]) by greer.hardwarefreak.com (Postfix) with ESMTP id 7AFA66C11A; Sun, 10 Mar 2013 01:54:42 -0600 (CST) Message-ID: <513C3C43.7080104@hardwarefreak.com> Date: Sun, 10 Mar 2013 01:54:43 -0600 From: Stan Hoeppner Reply-To: stan@hardwarefreak.com User-Agent: Mozilla/5.0 (Windows NT 5.1; rv:17.0) Gecko/20130215 Thunderbird/17.0.3 MIME-Version: 1.0 To: Eric Sandeen CC: Pascal , xfs@oss.sgi.com Subject: Re: Maximum file system size of XFS? References: <20130309215121.0e614ef8@thinky> <513BB7C3.4050009@redhat.com> <20130309233940.3b7c0910@thinky> <513BDD6E.7010507@sandeen.net> X-ASG-Orig-Subj: Re: Maximum file system size of XFS? In-Reply-To: <513BDD6E.7010507@sandeen.net> Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: mo-65-41-216-221.sta.embarqhsd.net[65.41.216.221] X-Barracuda-Start-Time: 1362902082 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 On 3/9/2013 7:10 PM, Eric Sandeen wrote: > On 3/9/13 4:39 PM, Pascal wrote: > >> Hello Ric, >> >> thank you for your answer. I am aware that there is a difference >> between the maximum size under practical conditions and the theoretical >> maximum. But I am looking for this theoretical number to use in within >> in my thesis comparing file systems. > > A thesis comparing actual scalability would be much more interesting > than one comparing, essentially, the container size chosen for a disk > block. One could quickly write a filesystem which "can" be as large > as a yottabyte, but it wouldn't really *mean* anything. Agreed. But if the OP must have the theoretical maximum, I think what's in the SGI doc is the correct number. Down below what the OP quoted from the Features section, down in the Technical Specifications, we find: " Maximum Filesystem Size For Linux 2.4, 2 TB. For Linux 2.6 and beyond, when using 64 bit addressing in the block devices layer (CONFIG_LBD) and a 64 bit platform, filesystem size limit increases to 9 million terabytes (or the device limits). For these later kernels on 32 bit platforms, 16TB is the current limit even with 64 bit addressing enabled in the block layer." I assume the OP's paper deals with the far distant future where individual rusty disk drives have 1PB capacity, thus requiring 'only' 9,000 disk drives for a RAW 9EB XFS without redundancy, or 18,000 drives for RAID10. With today's largest drives at 4TB, it would take 2.25 million disk drives for a RAW 9EB capacity, 4.5 million for RAID10. All of this assuming my math is correct. I don't regularly deal with 16 digit decimal numbers. ;) I'm also assuming in this distant future that rusty drives still lead SSD in price/capacity. That may be an incorrect assumption. Dave can beat up on me in a couple of decades if my assumption proves incorrect. ;) For a 9EB XFS to become remotely practical, I'd say disk drive capacity would have to reach 10 petabytes per drive. This yields 1800 drives for 9EB in RAID10, or 3x 42U racks each housing 10x 4U 60 drive FC RAID chassis, 600 drives per rack. I keep saying RAID10 instead of RAID6 because I don't think anyone would want to attempt a RAID6 parity rebuild of even a small 4+2 array of 10PB drives, if the sustained interface rate continues to increase at the snails pace it has in relation to aerial density. Peak interface sustained data rate today is about 200MB/s for the fastest rusty drives. If we are lucky the 10PB drives of the future will have a sustained interface rate of 20GB/s, or 100x today's fastest, which will allow for a mirroring operation to complete in about 14 hours, which is still slower than with today's 4TB drives, which take about 8 hours. Note that a 20GB/s one way data rate of such a 10PB drive would saturate a 16 lane PCI Express v3.0 slot (15GB/s), and eat 2/3rds of a v4.0 x16 slot's bandwidth (31GB/s, but won't ship until ~2016). And since current PCIe controller to processor interconnects are limited to about 12-20GB/s one way, PCIe b/w doesn't matter. Thus, the throughput of our our peripheral and system level interconnects much increase many fold as well to facilitate the hardware that would enable an EB sized XFS. And as Ric mentioned, the memory capacity requirements for executing xfs_repair on a 9EB XFS would likely require a host machine with many hundreds of times the memory capacity of system available today. That and/or a rewrite of xfs_repair to make more efficient use of RAM. So in summary, an Exabyte scale XFS is simply not practical today, and won't be for at least another couple of decades, or more, if ever. The same holds true for some of the other filesystems you're going to be writing about. Some of the cluster and/or distributed filesystems you're looking at could probably scale to Exabytes today. That is, if someone had the budget for half a million hard drives, host systems, switches, etc, the facilities to house it all, and the budget for power and cooling. That's 834 racks for drives alone, just under 1/3rd of a mile long if installed in a single row. -- Stan From deals-st@stocklottrading.net Sun Mar 10 04:42:01 2013 Return-Path: X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 486EE7CBF for ; Sun, 10 Mar 2013 04:42:01 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay1.corp.sgi.com (Postfix) with ESMTP id 2980D8F8049 for ; Sun, 10 Mar 2013 01:42:00 -0800 (PST) X-ASG-Debug-ID: 1362908509-04cbb07dbf38c6b0001-NocioJ Received: from mail-vc0-f169.google.com (mail-vc0-f169.google.com [209.85.220.169]) by cuda.sgi.com with ESMTP id 6wTbA1UqyD4voCJu (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Sun, 10 Mar 2013 01:41:49 -0800 (PST) X-Barracuda-Envelope-From: deals-st@stocklottrading.net X-Barracuda-Apparent-Source-IP: 209.85.220.169 Received: by mail-vc0-f169.google.com with SMTP id n10so1626083vcn.28 for ; Sun, 10 Mar 2013 01:41:49 -0800 (PST) X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=20120113; h=mime-version:x-received:in-reply-to:references:date:message-id :subject:from:to:content-type:x-gm-message-state; bh=V7yJjfT9xeybeSIPaN+YMeVIRLOFAMKEZd+V4S9PchM=; b=EJ5pf4r5BvzQp6yJS2zmBxwz+MWcVkZMJvTj7XSHtjulWffEhjCiwRPlOU/tR8HAVb R+5Ar4iLgBlV/OAhyteFMeXZcupGvOrKKrUQqxm2hSKbvO8EOlgLC5k5vuLYmuK1E+8E u7/8+3jtQwTzjwIMU4aLV08nG5hbOm0Z41YMyx7li054CsxznEF3Qd1sqmA+eWv6Eztw hgs9M+h+IIpaBEbOMt5j42dAg5rsTYF5WV5YprNzafa20sOrZUqVdtTQYQyqNPq7CDyw OOPBpq2fIljzLXAGNK40L4p1jWNvDqZKA4xXwaKdUS2kA0qVjw8d67/1pLChsObTNUMK uLZg== MIME-Version: 1.0 X-Received: by 10.52.34.102 with SMTP id y6mr2917620vdi.19.1362908507466; Sun, 10 Mar 2013 01:41:47 -0800 (PST) Received: by 10.58.164.72 with HTTP; Sun, 10 Mar 2013 01:41:46 -0800 (PST) In-Reply-To: References: Date: Sun, 10 Mar 2013 16:41:46 +0700 Message-ID: Subject: Special Offer Thailand From: Stocklot Trading X-ASG-Orig-Subj: Special Offer Thailand To: Stocklot Trading Content-Type: multipart/mixed; boundary=20cf30780d6273481304d78edd22 X-Gm-Message-State: ALoCoQmP90BJktZI7mYCcY5aHfAIYon2YWobnzWMIxYMXUqQWkmOa3cEzUmWPJQKhinDbbeWPKxA X-Barracuda-Connect: mail-vc0-f169.google.com[209.85.220.169] X-Barracuda-Start-Time: 1362908509 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Barracuda-BRTS-Status: 1 X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-Spam-Score: -1001.00 X-Barracuda-Spam-Status: No, SCORE=-1001.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 --20cf30780d6273481304d78edd22 Content-Type: multipart/related; boundary=20cf30780d6273481104d78edd21 --20cf30780d6273481104d78edd21 Content-Type: multipart/alternative; boundary=20cf30780d6273480e04d78edd20 --20cf30780d6273480e04d78edd20 Content-Type: text/plain; charset=ISO-8859-1 *Stocklot Fashion Jewelry* *Made in India* *80% Neckless* *Quantity : 500.000 Pieces* *Price Take All : 8.75 Baht per Piece / FOB Thailand* *Minimum Order Quantity : 50.000 Pieces* *Price : 9 Baht per Piece / FOB Thailand* [image: Inline image 1] *Liquidation Fashion Carpets Quantity : 40.000 Kilo Price Take All : 115.00 Baht per Kilo / FOB Thailand* [image: Inline image 2] -- *FEEL FREE TO CONTACT US >>>>>>>>* info@stocklottrading.net ------------------------------------------------------------------------------------------------------------------- *Stocklot Trading Co., Ltd* *Contact: Damian Baumler* *Tel: 0847241028* *info@stocklottrading.net* *www.stocklottrading.net * * * * * --20cf30780d6273480e04d78edd20 Content-Type: text/html; charset=ISO-8859-1 Content-Transfer-Encoding: quoted-printable
= Stocklot Fashion Jewelry

Made in India

80% Neckless
=
Quantity : 500.0= 00 Pieces
Price Take All : 8.7= 5 Baht per Piece / FOB Thailand

Minimum Order Quantity : 50.000 Pieces
Price : 9 Baht per P= iece / FOB Thailand
<= br>

3D"Inline


Liquidation Fashion Carpets

Quantity : 40.000= Kilo

Price Take All : 115.00 Baht per Kilo / FOB Thailand



3D"Inline


<= /span>
--
FEEL= FREE TO CONTACT US >>>>>>>>=A0info@stocklottrading.net

----------------------------------------------------------------------= ---------------------------------------------
Stocklot Trading Co., Ltd
Contact: Damian= Baumler
<= i>Tel: 0847241028





--20cf30780d6273480e04d78edd20-- --20cf30780d6273481104d78edd21 Content-Type: image/png; name="image.png" Content-Transfer-Encoding: base64 Content-ID: X-Attachment-Id: ii_13d401f31cd29d3d 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 LC3NhEjrNXAv0HbvXiAy6vHuBelb1ejVuAkGIQhrgE1+hARV157pXgQbsFKYRH+pGaZAF1BPdUhk bRHeiDwy8WhGov3JDPfDIDznOc+JKvMC8GTW/1jqygtA/t2CLYaEipPfP+Ntk4NR4+2c7lp1ms5g GXkDfTQLSrWclequfre+xnfjrhYa02dYqwTP1fI/mm8SBy95yUuKb/3Wby2+/du/vbj33nuDSM/4 aYSpWodp3DwlnITVYJx5cv6cPpdj+u1ITL76q786bg79z//8z0j7Qz/0Q0UvJ2Lf/M3fHFlyeTn/ o/2twuPzbpwD6G/c41RhynA1wpvra/zuey7TNI3POZ+/OW017mrPjXXltI3lNKbL3/Nvzlf9rX6r PpvGdwmJD/uwDys+8zM/s/i3f/u34i//8i+Lg6hNfu3Xfm3xoz/6o4GvzJQ3luv7avirpl3t2foN K5XRCKvpjHMc+XfHHXcgPNpSnDx5sjjCEbxBOCX6LK9a5mplNaaxDOPcbL1M8/bbbw+i97777osN PK9JpsuhsWzfDdWyc9rVfnOeR5JPHHzu535uMYAE8hd/8RcDJ41zpwpbfvZX5kAC+Ou+7uuKr/iK r4j3z/u8zyv+93//dxlBbBtyvkbYjXd9ktA27Nmzp7jtttu4V6g/8PcwKrfize+ZKM3lmT7jx3Jy qMY5Lg32pyF/ixf+qebLcY1pjG+E33L37dtX/Mqv/ErxG7/xG8Xf//3f1+vIZdr/n//5n1986qd+ avHlX/7l3D47XF8bG8ur1pHzC4ftdjxWBRLGW7/x7mdVeKvlVsuplu+zoZo2xSzhw7613J/5mZ/B 5/1U8b3f+72R/tM//dOLm1FjdqzYPuuvlpOf828ud7X6qt+v9Vwts/q8Uj6/G2xDfvbddjnmHUvV cK3yqmlvhGdx/w//8A/FJ3zCJ1wXOAqXbeMQAmtvVfYuraUZc11FPC7adbvGAAAgAElEQVSJ7I95 CPpmmI0qZesJh7YQKwWZihCCQ8utnGKlXMvjmrx4bBrD4D4uTIPaCI5Ii2j9/u8f2BUSdupBWj8f noZUP/IisXfce3fxnDvuLHZ4exxAnsWF6BATuRtDie3btqKfz5EGHI7W1gZVeUS0jIeNNEjYX4Sr igva4JQy4o03nZbidoocDRfcx8mGulUl3zRM1tBkGFjU1/K+hjPojnlMsrNvi8VHUIEivBHB1dk+ 6/YUwBMHPRd5dXWcQjBh5co8ChKxzbhbFR5tMrRqFwaZD/XK5P668PBku09gjG3+EdSjWCbqbYjK nyb/5MUgL24uYi996UtjE8uLhBJnCZYf+ZEfWVVittpiYXyWbq2WZiVU5bqFL4fqc/7ut2p8Tutv NY3v1XSN33z3e2YMMqNgvsc7WIfExcd8zMcUP/mTPxkLcK5DGBphy9/8Na/EvhuQjMbV0uayXNwl IL7zO78zNsi3vvWtUeSHfMiHFLt27VqGl/jAP7ncKs7yt2v9mtc/F+QP/dAPDUJAIvhNb3pTMJ8Z x1crJ9drObkdpm98zmXkdL77vFLIZVa/VeOqZVTjc/pqXH7OvzmNv9VyqrBU451v4uGFL3xh8dzn Prf4iI/4iOLP//zPi+dxEvnRH/3R0VeNRGcuO9dVLdu4lWDJaVf7rcJ0tTQStRII3/Ed31HsRW9V ws0x/M53vrMYHBwMRuHQoUNB8FXhyjDlON/9y+/VOiXsXvCCFwThLDMpMdfFnvJrv/Zrxf/8z//E yZfpV8pbLeeRPGf4rjeP/ebfV33VV4VQ6A/+4A+CUcrS7lzOauU6Zz/7sz+7+Lmf+7m4xfc973lP MM9VojHnzb+5zPxrvLg6cOBAEKGOHYU3F1CVcK3eyc2ux1HJ/c3f/M3iT//0TwOP4rIaxGFj+cbZ zzJj/mWBUDWfz+ZbKX9jusZ38SZ8rntveMMbAo+N5Vj2LbfcUnzSJ31S8Q3f8A0xR3J9jeVV33Ma 4ddG0t98CZrp/C5TK5OgRD/PLes35N9cjnH5OcPoew6Ncfnd7x/5kR8ZAjXnt+GLv/iLi5e97GXF H//xH2O3eazOuOQ6TVN9rr5nGPKv3wxVWFLM0r8rlWX6q+VZqfzcJn/dc5S0u5c8kXvjUiuemCfV zQ2hhYLE3B61fafOnAkadw+2BUr+VS2X5tOl6eCJwbB93QmDkIOnCqrvaLMqPtRkmdVOFlUhNd2b OU3oIa94VRp/yVtnqScc21BpMycBvvvNy4a9T2xbfy8aO63hVegktG47Jwmb0IS5hPtTzYbbOpNH JW0mjpwcjGsA9jPXpWudW3r11C7C8MBDDxWnsZN90bOfSxx3KTDudR7kKcZu7HO1vfWmZulXTyo0 MzDvIvDKUHja0CTh7m3FEsGG41SqTtZ+jCa8oc1jESwjUDm6GPpOehs6jRHGGQyTn3nrbZFHQvk0 ulAiZxfI9ehEol9jDm+m05WThhpOTJak4jJHNCL/3PmhYgu2DLu376gT1hLosxDqMgcbmlmsaLS2 CE7hKcoawnDZDWOeyT8FYzDKn3YI/Vib28H6kc3c0hxpRqcm4hY7J6ruUvVEpDG0cF1kgdVS3SMW B8IRpC4uop3YGsg5qj7UR7lWrl/b2dl5DEy4ZZrenwNGF3Tx4RFQM3Hgk1kbKHna/ZMXj7wQnD59 uvjBH/zBmDgOfv+UciuRyYuGjRSveWExTTUYbzC9Ib/Hy3X8k9Pn+pwAGZac3U3AdPaF33yu5jOd +YTT76ZrDNX0+dk01uufeXP+XEdjGdfzblnCkusQdhdbfw053jpyu3wW59ZvfgluJZff9V3fVXzy J39y8RCLgBtuNeQ6cl/5TcJOAutjP/ZjiwcffDDKtA430OxZIZdhndaXNwLfH02wDMOXfumXFmeY m29/+9tjftnOXGZu80rlV3FvW2y7ZVZVsqppLNO/XKbffK7Wt1I91TjTWoe/5ne8+JxDtb6rfTd9 rt9fg+XmZ3+F1d/f+Z3fCcLlAz7gA4pXvvKVcar0Uz/1U9HeLDU3Xe7XxjGcy6yWHxWu8o/pTWt5 jWXlLI1l+e76/Y3f+I3F13zN1wRTa596eiDjJ/Hz8pe/PNaIfIpgWRk2n6t49N2Q8eyv5Xua9du/ /dtR7r9iSGi9z3rWs4rf+q3fCqnyPffcU5ey+y2Po1RaKi+XmeOu5/dquGjML86s+yu/8itDRcg9 KTMHuW7hynPYsZvjzWf4rM/6rGijEnLrFmcZb6bN6cRfYxuNk8CV8Zb4dz47x971rnfFXBYWCeHP +IzPKH7+538+GFBPCJ3PwmKwjFyPdRlvPaZxD/yLv/iL4n3ve1+cbua2rZTPPI1zJCqo1WHZ/lXb 4bu4sa4cMjzCZHAseElVzuv3ajC/cY3j1zVCocfv/d7vxenDW97ylmB0jJdo99TC0xqZWtfNXJ9l W571VYNxuR9Xa6vx9mHO67vCG9dWg7gV/zIt7qtZCm/duV05v+0xv98ybDmN5Rvn9xxXhbXxubF8 3y3fvLnsah7j8hjJaaxThlahwKd8yqcUH/dxHxftymvwSuVUy7wRnxX2GqQBJbTFpyrjei7a6gkc tJ5qPgqR+1AB7OaS3YdgArQ1yGGK8TnGHQczCNJBZv3+raSujx0C9HIvdyfINAyPYbh86jQ2ux3Y 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 AAAASUVORK5CYII= --20cf30780d6273481104d78edd21 Content-Type: image/png; name="image.png" Content-Transfer-Encoding: base64 Content-ID: X-Attachment-Id: ii_13d401e7e4b79d87 iVBORw0KGgoAAAANSUhEUgAAAxIAAAFyCAYAAABhr+y4AAAgAElEQVR4AeydB4BlV1n4z3vzps/s zu7MtmzJbEkhnST0ntA7AhaaAQRFAUXsBVHAhigKIk1FhL+IYEFBOoGEEEI6KbvZ3nubPvPmzfx/ v+++M/t2sptmQoJydu/c+8495Tvt6+fc0pkf++D03J6edO6q1alSqaTv3XZrKpWb0vIFfamUUpqa mkrViYl4PjQ6miaI62huTssWLkrlpnKq1WqpNllL4yMjqYnf8+bNTwPDQ6m5pSX1dc9JLeVymqag vYcOpU27dqUx0k9PT6elvb2pq6MjbdixI01M1dKG716TJjZtTh3nnpNOO+usVK1WU/ucOYnEacWC BWnBnJ60bc+utOfoUcorpWnKmdvRmRbM60lNLa1pXmcHcVPp0BB1A19fV1dqou4SaYfGxtJRYC/z OwJl7ti7Jx0dGU5d7R3prGXLgWd+GhqfSNMkGCTthu3b0ghtHxg4mrZs2ZKmJqpp6fLladHixamL 8vcNDKS57e1p4bx5qRs4N2/dmnbv359a5s5N+z7+/9LBz/5HauL9Qz2UaHCpXEplxr6Zq4VxqzAu bZ2dqaWrO5W7OtLInPY03js3nbVgcTpj3oK0lDbO75yTuts6U2d7a2ph3Jvp25n+pdH2+//l4Bx/ KIbGcRHCB2SU6m0/WQ/Mjp9m1bHU0hQvqtO1NDE5mcarE2m8xn1yIk2AC8YmuViDE1XjeCYu7qQd I+0o8aPEDXMNcg2Rb4y4icmp1DYxnjp5biZt08RkmqpVU4nf0+CtGnmneJ7iXeJeq1+T3omrUU7g OPEcl/jw/2JonDe5/Q/VOZ7h+998dzxy//tc5mpqqqSm5iboeHOqtIjPW/ndAn1sLq5KU0o8l1qb 0zTx0y1NaQqcP0K6CfD+FHSti7g5xHW3tqYOrk7i2snT0dya2istqY107cS1Eue7Nspp5WqjTu+t 1NHUxFWCHpxkAIQ35lPGkfyG0J8k9b2PnhKRPMgh2leHgdbWEe3/BK57galzv0b99yRfI1z19Nzy /Mpd2dimGK560qnpqVSjzknw42B1PB0dGk4HBofStsMH0+17dqZ1+3annoODqQleamJwOI0fGU6j Y4NpfAzcCp6dBqdKAxqhyHU+FO41+MHOh5+fHvVX70n9fX1pEN5vM/yjvKxdIO+zBD6wFX60tbUl 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 M7yf5wLGcqMYm0xgk7B7d0+2E4JgDhWlQUQxSjsQmWQXyDc5PpEtIY2Q4tNIehIbh3L0zfQypeRC A+t9u3ujf4sQLYYiN8idBIdSh4G+s9kSNhEawUw3NWAHMcGgjgVBZJ1SeAJcvbUTJ04FYTRG+SmI Dw1gBs8PRXwEAfws0SqNe1FIBQgUIFCAQAECBQhcDwgkm7ekZnM96izUUYBAAQKvDAFx6DkYygcP HACHrc72421J3PcsyPowiH4tkgHjiY2AgGt3MAWTeggG/CkIC2NAGKxPnLcRDv/uzh0RnFmmvMbK oxOTQSCMYJvbd6Y/u0B94tbG8Jog2JtaOjoh0s5B76dq7hyFWDgEQ1s75pbmJnDTC+FtVK2a0+DG avQ8/cLzxLOYzLp27cxmwFUj1AG2HapEVUMAzFHH8RPHw7hDL6c+V2tH4kaXrsa0gArJTvANp0+c CMJGmwgJiXLq0Zhc+2nNEl46cjQr4gPWjOUwDaBydgBEgAYBXyWDiHEfYo4GKKhWVHpkxSsx0LhW N1g2rKrPECIOKZnt2D/4WAxcOwWNqZU2SJj4TH+16n8JRJFtJRPboNAQN4SIxMAWGllrLKKFufFI +qCSNJrejj2DVuhGtB6CEqvCfiPiP0C9aUmv9yWRegfW+g0IsmwQIYDUwjsDxil10RhFo/EIIsKA uTEbY8J267GirySwmu1NI2nQl+4IBEUxFu+d6LGF0RVElEFDrGuKoHjajWiYrZ9g6yiGEPrYR/57 9t9/7/dCiiM03khJilVRV74OqNfpIPNbvBduySbk1X6fZVMd+e1cSz2pP/6mereqJ73z15Tazb9P 16l8fp50nd5dj9/UXqrbe3UpNW4yropqe+ndK7Vn2ZQ3Xaffy5X1vcn5a1mdGTimznNdu5leOehS ZHvV/6S+5fc59Sc921xpKpOe5+fPf5d/nfL6m57nl9vqeX4Zr1N/rlQu5ckvm9rb/CzVmerLf289 qZy/+WPh+PjM8fJXKXFqN5WxrnTtr2mrPPHiMv+k8lu9TnX6LtWbny+V9Z1/3qe//Pxb1ZOepXzp PtWf/9xr96SUnLfm35wn1eHzdG2ZlC+Vf6Xf/LpfKa/vrd8+pfXsWnZNX6ndzW14r1fDFA/I++T+ 8Wr6kF+f1yZhZn0JdvYrH3b5ZVIbWz1L776Zv7ab9qZ8+KX++GuSm2p6NXtVqsNy+dfeXy6lfOn3 cvm2em4Z01bj7xp3nqh+4nea/G5T+qbU5lb15L+z/nQfFVzlP6les2/Vx62qebXtvNr8W7X5rXjm WDzw0EPZ//l//UvWDK7cgLRA/E9vSqozNYPcq/KkREHNlXoY3uLSMp/TeDq+tWrGNDaHfbGMcAkJ NXPk7OvAaBJ8UrzXOG4G7K3BziLUpWjfIIaaEnQR2VrNIY2cxYfFeQ3JoMcmCZgKnhnF2nAE5eDA atcYFVv3r4F/Y0BdggmD/ZNZvx3mfS1tqzK1xDcweSIMg3PR8AlHkGqoOtVMRO6YW9xok7wIju7u q/0xNhGqXVk6l1RnilgO/OamvYF7EIuA6F8u2UHfp/yXy7f5uYYgWkmo73W9k26xNCKpr6oJq/br Xf8r1fd7EBG/8Ru/8YYkJPK/zYUvUutG5zSJicQzfz18Qs+P37wpFMXTprT5+ea6vTePf6lMfp7N 1/kbUbpO5a6mrdTe5nq3uk/1p3f57Wy+vlLbqfzlfvPbEdY9PT3ZD/zAD2Sf/OQns0OHDgXycbmy m5+nfljnlfqY3lnesbXNXYhMv/71rwcBoVOEH//xH8+eeeaZ7Ctf+UqMc2orv7/p2bX8Wo8Ijd+8 GSG2vvQt+XXn99v3/jkPU/7Ut835Uh3pvff51/nv03X+b35fUrn0az6vU0p50/utfs1rvvTO+/zr dO/YeBB98IMfhNEznX3mM5+Jcu973/tC1/Xxxx+/7PzYXF+qM/XP+6tJm+vxPqXNdaV3InZxEHGo eu0h6jvHSkTYcvllN7eR6t/8m5/Pw902DKhkG84l6/ZZQpJT+VTO35Ty20/PrvR7LWUdvzZUau+6 667sG9/4RiAD9s+2X6k+3/tN5v/pn/7p7J3vfGf22GOPZX/8x3+8gfjn12Hft/om8/jcdWZ9pnY4 qnWMjeoSw0j8HR+T6zDlT3WnOjffyjhZEgAAIABJREFUmz/l3fw9vstPqWz+s1Rv/rNUX3pmnx94 4IHsbW97W/a3f/u32QiIj2dOas9xNs/3fd/3Edy2JfL4TIItpc3tpDbyfx0n79NfKuOvf46BKT33 2ry2lb//+Dw/mceUynmfrlM+x2Q7jl9+7Md+LPvsZz+bPfvss9Ge363WxIsvvrjR/lblUz35v1eb L5W5Uv70zn57/UopP4/wsdzmOb8ZBq9U57f6vXvNe9/7vuw///Mzr6orItajSBVKcQ4kk/yVofeq qr/qzCL84tuYgr+sD9o1awi+VdKugqELomer95uflU5i1FxejCcjEG/dspavG2poTDLAJtMEUtEW 7qVAOqCgmE0bhMWRkycz6ZI7du+JehVz6BfXDaoNl7ERtAIJRC2cfsuZNM4wYb4cv+kfuh2XL/9U FiFPI4idmwYfrqNX3auOIgpS4tEKNajqkQbWw4h4lCiMIkVQJNTUm+tXakOreDee+AYoK1W0DC8e mw8blFb3GpjHRKdh7R5KML6WUMoHugYs6rG5YUmpmaQwtbRvxvuUdiZv5JQ2A8fxLW95S/Y7v/M7 ccgkjpobg4fPz/zMzwSyK1WcNhy/O206+c98nupNG8nl8pn3cmlznZvrSG1YPrWzua5XypPep9/8 enyWf59/vbmdV7rfXJeHys0335x95CMfyc7gW/qFF17YODita6v+pOeW9S9xre2X+VMb6df86Z3z XsnDb//2b2c/+IM/mL35zW/OnnjiifCu9vu///vZH/7hH2b/9V//9TLJSCr7Wr/bdpuRFP4tCMI/ /uM/Zv/wD//wMoLCfm5O+W2nbzNPOtBTn/Lz5deRnvssXacy+fDJL7PVtXnzU35dm+tJ9W/+zS+f rjeXFUZvf/vbs5/6qZ/K9u/fn/3kT/5kEBO/+7u/m/3N3/xN9rWvfe2K8yP182raTn3I/03l8/uV 6krv8vM7Du4ZIn4/8iM/EvNGROvTn/50EKQiqv3Y1uUjevnlU52pjfx36dp3tvGOd7wj+6Ef+qEN jt9//ud/Zv/0T/8UHLqE3KX68st6vfl5en+l3yv16XLl3CN/9md/NvvN3/zNWF///M///LL1uVU5 +2ZbwlIE92Mf+1j2y7/8y7EOJUqEnWdYgmHq15W+SURIzrbz54d/+IfDK6F1CyfLS6D+1V/9VXYa teC0f2zuW2onPU/tWbfXjq3pcvm2ehcF1v9J353/zP3sXe96V/bhD384GCuDqJIk1emUT1j8xE/8 RHbPPffEXmL7/qX60q/5vU7JPH6/a8w60nenssLHdz73WX5K9ST4bfXOMo5hypufx+v03LZ34trT PV/C4cknn8w64BJ/7nOfy5577rnsrW99a/Rv83en8taV+peepfv8dvLzeX2llF9Pqis926qc71I+ f71P8BM3SM/Sb37+req7MZ/l5oASApnri4ytrl2N/qyavuEFmsAFHXM1XPR06vdq+7Crqwts92Js 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 --20cf30780d6273481104d78edd21-- --20cf30780d6273481304d78edd22 Content-Type: image/jpeg; name="ST 1.jpg" Content-Disposition: attachment; filename="ST 1.jpg" Content-Transfer-Encoding: base64 X-Attachment-Id: f_hdyl84p12 /9j/4AAQSkZJRgABAQEAYABgAAD/2wBDAAIBAQIBAQICAgICAgICAwUDAwMDAwYEBAMFBwYHBwcG BwcICQsJCAgKCAcHCg0KCgsMDAwMBwkODw0MDgsMDAz/2wBDAQICAgMDAwYDAwYMCAcIDAwMDAwM DAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAz/wAARCAJVBT0DASIA AhEBAxEB/8QAHwAAAQUBAQEBAQEAAAAAAAAAAAECAwQFBgcICQoL/8QAtRAAAgEDAwIEAwUFBAQA AAF9AQIDAAQRBRIhMUEGE1FhByJxFDKBkaEII0KxwRVS0fAkM2JyggkKFhcYGRolJicoKSo0NTY3 ODk6Q0RFRkdISUpTVFVWV1hZWmNkZWZnaGlqc3R1dnd4eXqDhIWGh4iJipKTlJWWl5iZmqKjpKWm p6ipqrKztLW2t7i5usLDxMXGx8jJytLT1NXW19jZ2uHi4+Tl5ufo6erx8vP09fb3+Pn6/8QAHwEA AwEBAQEBAQEBAQAAAAAAAAECAwQFBgcICQoL/8QAtREAAgECBAQDBAcFBAQAAQJ3AAECAxEEBSEx BhJBUQdhcRMiMoEIFEKRobHBCSMzUvAVYnLRChYkNOEl8RcYGRomJygpKjU2Nzg5OkNERUZHSElK U1RVVldYWVpjZGVmZ2hpanN0dXZ3eHl6goOEhYaHiImKkpOUlZaXmJmaoqOkpaanqKmqsrO0tba3 uLm6wsPExcbHyMnK0tPU1dbX2Nna4uPk5ebn6Onq8vP09fb3+Pn6/9oADAMBAAIRAxEAPwD51PxU 1V9MimOp6vLeXFyDNHI7eWwVcKnynPA/h4wKbqXirX9fh+zJJfW+2LyRFayyQKFcnLE7s55yDzWn pHwQ+Ca2a2NrpHi7y7e1wt/Lq775HZQJJFQfxMwOMk4GOa5v4t+G/g5pOgmDRfAXjW2gfU7Wyid/ Estxc33mTBCRGFGOO27Ar7R4t21X4/8AAP4/jw7BzShKW/8AKu/+P9fmavif4jSaeLHR7TVr+2uI l2LBDqMkox0IznJYnn6mqo1vVplvLmw1W8RLCJGeWa7bdLLu4Owk9Gwec9K7jVvgn8Jvhz46v7C0 8A+LdHt/Dt2+jyyz6uZZ7qXbuMnK8EdBzge9cinwm+BelaXoUF14Z8X6jcTXxF/J/bDRRRqSzbAo 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 DSXuHihjJZy+04U7jwoPWuc1NtU1FtKsrnRPFXhPwlbBgu3SZml1Vh1OMck85OcAcdax9asH1XxR tuvDfi82dtH5ljZJYSRrKi/NuaMDIABySeMUwOpvPhfoMNlZafZ/FXUbizZzJHFD4fYTyO7bd+0N leOSzGq/iL4Jad4fvdJ8P2/xE199U8Vaillb2J09444LfzQvnztv5IGTtUZ/CszRbfxTfeK7fU7r wv4oWyliLw29roc5jC9FYsVLMo65HpVjwpaamPi/4Z8Tar4Q8VWug6FqIuLy4SwlZ2iDDohGQScD n1oGa2t/s0+HNS8R6RomifEjUfE3iG9vxptnbvpTW6j5iMKzlsEsMg4wADmn6D+yxFrXi1bbWPG1 xothp1ztEio83lKp/euZM43ZBxjNXfBHjsj4+wa+/gzW7BX1SN0lGl3Mk0URlyFzjgsvXA6ZxXLa 8niC/wDEUZg8K+J2imvH3mTRbnEY3EkKoGSQO1IRPY/AnQpJr6U/ESa1sE8xEj+wNe3NwxbYoWPP ykqxJOe9dV4j+F2iajFZ+HLj4s63NcaVYJFbW1n4YZY7dOySSIwyMAnBz/OvPtJsp9I8UXc114Z8 YvfJcb0M2mSFLa3YYaQREZBAxjPqKVPFWpjT9XXRtN8SvIsxhYR2UpUKDj5ynQ89KYXOq0b4G+Fd Hc6hH8WtRW5jHmMv/CPuUGPujDMVz04xX9sdfw/6XpXiS6SOL/hFfFM94+HFvbaJdMypjhjuXnJz yOOK/uApAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFF FABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUU AFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQB/Fd4b+JPiSSC9ttN1nxvBpejBPt0rX8z JNKw+RWl3BmPPC9AB0rivF+t6tp3gzw/Y6l4rvp73XL6Ka9gupSLW0UYHzqv3ieMkjOPrXoH/Cqv hnKiRQn4hDT0CQsraoiR3VyOXmOVwoAIUDngetV774W/Cjw1qg1F9M8ZX32W3E8VnY6tC4WdW4Z3 dDudsDgcCqsyXNHU/G34g+LrL446nHF4s1PSNDsbow2S2rMjmAoPlhQ/6sNxyADjvXB6x8QNb0Xw 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 UUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRR RQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFF ABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUA FFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAU UUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRR RQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFF ABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUA FFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAU UUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRR RQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFF ABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUA FFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAU UUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRR RQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFF ABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUA FFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAU UUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRR RQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFF ABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUA FFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAU UUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRR RQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFF ABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUA FFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAU UUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRR RQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFF ABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUA FFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAU UUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRR RQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFF ABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUA FFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAU UUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRR RQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFF ABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUA FFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAU UUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRR RQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFF ABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUA FFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAU UUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRR RQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFF ABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUA FFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAU UUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRR RQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFF ABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUA FFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAU UUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRR RQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFF ABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUA FFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAU UUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRR RQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFF ABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUA FFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAU UUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRR RQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFF ABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUA FFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAU UUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRR RQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFF ABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUA FFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAU UUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRR RQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFF ABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUA FFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAU UUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRR RQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFF ABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUA FFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAU UUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRR RQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFF ABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUA FFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAU UUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRR RQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFF ABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUA FFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAU UUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRR RQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFF ABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUA FFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAU UUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRR RQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFF ABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUA FFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAU UUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFAH//2Q== --20cf30780d6273481304d78edd22 Content-Type: image/jpeg; name="ST2.jpg" Content-Disposition: attachment; filename="ST2.jpg" Content-Transfer-Encoding: base64 X-Attachment-Id: f_hdyl88xz3 /9j/4AAQSkZJRgABAQEAYABgAAD/2wBDAAIBAQIBAQICAgICAgICAwUDAwMDAwYEBAMFBwYHBwcG BwcICQsJCAgKCAcHCg0KCgsMDAwMBwkODw0MDgsMDAz/2wBDAQICAgMDAwYDAwYMCAcIDAwMDAwM DAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAz/wAARCAJVBT0DASIA AhEBAxEB/8QAHwAAAQUBAQEBAQEAAAAAAAAAAAECAwQFBgcICQoL/8QAtRAAAgEDAwIEAwUFBAQA AAF9AQIDAAQRBRIhMUEGE1FhByJxFDKBkaEII0KxwRVS0fAkM2JyggkKFhcYGRolJicoKSo0NTY3 ODk6Q0RFRkdISUpTVFVWV1hZWmNkZWZnaGlqc3R1dnd4eXqDhIWGh4iJipKTlJWWl5iZmqKjpKWm p6ipqrKztLW2t7i5usLDxMXGx8jJytLT1NXW19jZ2uHi4+Tl5ufo6erx8vP09fb3+Pn6/8QAHwEA AwEBAQEBAQEBAQAAAAAAAAECAwQFBgcICQoL/8QAtREAAgECBAQDBAcFBAQAAQJ3AAECAxEEBSEx BhJBUQdhcRMiMoEIFEKRobHBCSMzUvAVYnLRChYkNOEl8RcYGRomJygpKjU2Nzg5OkNERUZHSElK U1RVVldYWVpjZGVmZ2hpanN0dXZ3eHl6goOEhYaHiImKkpOUlZaXmJmaoqOkpaanqKmqsrO0tba3 uLm6wsPExcbHyMnK0tPU1dbX2Nna4uPk5ebn6Onq8vP09fb3+Pn6/9oADAMBAAIRAxEAPwDw2P8A aG8TS6ZcSHxJqNq1kPIs7ZWZY4Mt+8ZD0U9iR1pk37Qfii5SNrfVtXs50fzRcR308kzgAgqCSdoI JPHFRWP7NngWa+H2/wCJXjO81LVrlrq5jskVbWHEhKQhmxhQuCcAD61W8SfCL4beDNGuVHxJ+K2p 6xbWEt3NNDDAlja4jZmVGdw3GBzjtX231ryP45/1fXSf4M24Pjf4t8L+D/NuPF/i+2vryTzvNudS Z2Zskoq8/KoBxzWf/wALi8b+Jb6wmHizxPqWsSy4jd7+RzAoGQdzH154rK0H9n/4X6r4J8M6jN43 +JWtaxr2nR6/vuLdXtoLbeyEAswySV4OMDnFaOr/AAC+HBu9f1e6+JXjm0jtreMWFvYQqJpAEA2o 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 MKQxWqTtcs6XmDzkjG3GR2Y1+yGqfs7Xt3e/Zf8AhZVvaXNzefarsppcJUIgxFBECMADBLdya/Hf /gz1+Ilj4H0L4/reXOrI7XWjXKQ2Vs0iybIb0bpHAIRVLDgkZz7V+uXhH48aD4csI7qG91Dxd4uv ZGW0tBZTNFbksS53FAgwCOQTWi2OKs1zu5peG/AVv4z02XV7X4n6jqccN1JYK40tYlilBzjYgGMD oWqfRPgrrtv4Ome4+Ml3OZJAWA06HyYupIK43Enjk+lV/hR4ptvgd+zfrN34pvBFf3GuXWoCC1gk nkAnmPlRgBck4IGTxVcfGoX/AIJBtvD1wIEKsiC3aIBycfvmYds8gZ607mTSW63L/wAIP2bk8IeL PDfjHU/iFLrf9hveNaxvpkdsJXuF2OWIwxwuMA8VpeF/gpq1h8QI9UvviCb86FCr2dnDpKLZ2SE5 bJQAMSSD1zxWQfijodlq9rba/wCMpEur2NJ/sa6ZPJFDHnaY4lVDySB8x9arp8eNOgmv3isdbe2s EDzGG2kVwNwAXaRjJJAxyeaAutNCfQPgAPEY1bUX+Kmuai+oXgl1S8bThaiRd3yxR4ACqOnGfWo9 R/Zq1mwhFza/GC6sbTTommEa6NBdrgMxDF3yScHH4Vcuvj/4c1XSE05dU1ecIzrMH06dUR84IUhM ELnGa5jXfiv4R8dXj2dwfEs2m6ZYTQ/ZbW0lSO/bYcKWwDjORkDrRqGnY1PD/wAANW8VaPp+v6l8 Zb6/gvVE1mttYW6QkAgElouWwOMZwD1zXr/7P3w9TwGNYMfiabxJHetEUeaTzJIgu/7x7E5PHbbX k2jfFjRfBfwK+HdveadPpV7d6LD9j0fT7eW4KBnCKowvB9c4716z+z54gttVhv7eK3ezmtoLeSS3 eIo8SuZdu49Ccq3QnFJvQ0pW51/XQ9HooorM7gooooAKKKKACiiigAooooAKKKKACiiigAooooAK KKKACiiigAooooAKKKKACiiigAooooAKKKKACiiigAooooAKKKKACiiigAooooAKKKKACiiigAoo ooAKKKKACiiigAooooAKKKKACiiigAooooAKKKKACiiigAooooAKKKKACiiigDhtV8VXvh7Sg19f n7WGM8sEdqrtEhXcIhj72Ome9ZeheIPFD+F7UzLaNq1/EZfJNsqGJCTtDgdtvrWPq/wo1iO0k1HU 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 /Et7pM+lpLPpuuDUBDHdrI2ba5k8vZ5qj5sbt/GcGv1Kt/hj4utxFNJ40F7eQRybHm0xFTzG6MVD cKB/CPzr0GinclwT1PNdH+EHiuO/a/1XxoNVvLU7rCIaalva27YxuZFbLHk9+9SaL8GvEFtDaDUv Gd7qk29nvJXtlj88bgVRVBwqjkY5r0aii4vZxPMtF+CviGx8dXniK68S2N3fyLJDZq2lAR2MRPyq uHBJxjJ781P4O+EHiPwxqsF1P4rgvih3Tr/ZaQtdHk4LByQMnsOlejUUXD2cTlb/AMF61fSsBrkV vGbby8RWSh3lLZLls5xjgKK5/S/grruleKLrU08UB5pYPKid7MO8fsATgLnBOOTXpVFFwdNHlemf Bjxc8/8AaupeL4NQ11XX7PI+lxxw2ScbgqKxyxGeSetdb8PvCniDw1eai+teIxrsFx5YtIhYrbfY wu7dyCS5bK8npt966eihsaglqgooopFBRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFF FFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUU UAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQ AUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFAB RRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFF FFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUU UAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQ AUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFAB RRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFF FFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUU UAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQ AUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFAB RRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFF FFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUU UAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQ AUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFAB RRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFF FFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUU UAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQ AUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFAB RRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFF FFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUU UAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQ AUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFAB RRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFF FFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUU UAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQ AUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFAB RRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFF FFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUU UAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQ AUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFAB RRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFF FFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUU UAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQ AUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFAB RRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFF FFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUU UAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQ AUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFAB RRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFF FFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUU UAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQ AUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFAB RRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFF FFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUU UAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQ AUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFAB RRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFF FFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUU UAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQ AUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFAB RRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFF FFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUU UAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQ AUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFAB RRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFF FFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUU UAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQ AUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFAB RRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFF FFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUU UAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQ AUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFAB RRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFF FFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUU UAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQ AUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFAB RRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFF FFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUU UAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQ AUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFAB RRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFF FFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUU UAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQ AUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFAB RRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFF FFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUU UAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQ AUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFAB RRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFF FFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUU UAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQ AUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFAB RRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFFFFABRRRQAUUUUAFF FFABRRRQAUUUUAFFFFAH/9k= --20cf30780d6273481304d78edd22-- From jwollrath@web.de Sun Mar 10 09:49:06 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=FREEMAIL_FROM autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 3B5887CBF for ; Sun, 10 Mar 2013 09:49:06 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay1.corp.sgi.com (Postfix) with ESMTP id 286A28F8066 for ; Sun, 10 Mar 2013 07:49:05 -0700 (PDT) X-ASG-Debug-ID: 1362926943-04cb6c2b013a2f30001-NocioJ Received: from mout.web.de (mout.web.de [212.227.15.3]) by cuda.sgi.com with ESMTP id gKpSVMKG8L35tB04 for ; Sun, 10 Mar 2013 07:49:03 -0700 (PDT) X-Barracuda-Envelope-From: jwollrath@web.de X-Barracuda-Apparent-Source-IP: 212.227.15.3 Received: from ilfaris ([84.133.43.234]) by smtp.web.de (mrweb003) with ESMTPSA (Nemesis) id 0Le4PE-1UXGew3fXo-00qG1t for ; Sun, 10 Mar 2013 15:49:03 +0100 Date: Sun, 10 Mar 2013 15:49:00 +0100 From: Julian Wollrath To: xfs@oss.sgi.com Subject: Null pointer dereference and following traces on 3.9-rc1 Message-ID: <20130310154900.673deee0@ilfaris> X-ASG-Orig-Subj: Null pointer dereference and following traces on 3.9-rc1 X-Mailer: Claws Mail 3.8.1 (GTK+ 2.24.10; x86_64-pc-linux-gnu) Mime-Version: 1.0 Content-Type: text/plain; charset=US-ASCII Content-Transfer-Encoding: 7bit X-Provags-ID: V02:K0:O7ssq6bEqDVPXS9xUT+4qxIFVpuQCDgg6XtsA+C+xp+ zPatpLtstRFMhKPhxFPaPwz3ZApNWEnAPamu8CHCdQ05H1dlS7 lOrOb7uUQp14HjciDjHgr2svpnRP7kjIDo9o4fROJTm1XjYWNK h0CtyearztSREnyix5oTsw/vILuwxVqrAGc4atw3q/GxGV/ne5 zQfJdYl1AN552F+TlB4eg== X-Barracuda-Connect: mout.web.de[212.227.15.3] X-Barracuda-Start-Time: 1362926943 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124803 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- Hello, after a xfs_fsr run I found the following in my syslog: Mar 10 14:56:05 ilfaris kernel: [ 472.865406] BUG: unable to handle kernel NULL pointer dereference at 0000000000000018 Mar 10 14:56:05 ilfaris kernel: [ 472.865585] IP: [] xfs_trans_log_inode+0x8/0x30 Mar 10 14:56:05 ilfaris kernel: [ 472.865711] PGD 11645b067 PUD 11a7cd067 PMD 0 Mar 10 14:56:05 ilfaris kernel: [ 472.865811] Oops: 0000 [#1] SMP Mar 10 14:56:05 ilfaris kernel: [ 472.865880] Modules linked in: uvcvideo rtl8192ce rtlwifi mac80211 ohci_hcd ehci_pci ehci_hcd psmouse deflate zlib_deflate des_generic ecb sha512_generic sha1_generic hmac af_key xfrm_algo loop fuse btusb arc4 bluetooth crc16 snd_hda_codec_conexant radeon i2c_algo_bit drm_kms_helper snd_hda_codec_hdmi cfg80211 ttm snd_hda_intel drm videobuf2_vmalloc snd_hda_codec videobuf2_memops videobuf2_core snd_hwdep snd_pcm videodev snd_page_alloc agpgart thinkpad_acpi nvram acpi_cpufreq i2c_piix4 serio_raw rtl8192c_common snd_timer rfkill mperf pcspkr i2c_core k10temp evdev battery ac snd video wmi processor button soundcore sha256_generic twofish_x86_64_3way xts lrw gf128mul glue_helper twofish_x86_64 twofish_common cbc dm_crypt dm_mod sd_mod crc_t10dif rtsx_pci_sdmmc mmc_core microcode thermal thermal_sys ahci libahci rtsx_pci mfd_core usbcore usb_common libata scsi_mod [last unloaded: uvcvideo] Mar 10 14:56:05 ilfaris kernel: [ 472.867709] CPU 1 Mar 10 14:56:05 ilfaris kernel: [ 472.867755] Pid: 4694, comm: xfs_fsr Not tainted 3.9.0-rc1+ #1 LENOVO 30515YG/30515YG Mar 10 14:56:05 ilfaris kernel: [ 472.867898] RIP: 0010:[] [] xfs_trans_log_inode+0x8/0x30 Mar 10 14:56:05 ilfaris kernel: [ 472.868058] RSP: 0018:ffff880119c0bc80 EFLAGS: 00010202 Mar 10 14:56:05 ilfaris kernel: [ 472.868154] RAX: 0000000000000000 RBX: 0000000000000000 RCX: 0000000000000000 Mar 10 14:56:05 ilfaris kernel: [ 472.868280] RDX: 0000000000000005 RSI: ffff8800a5a367c0 RDI: ffff8800b33063b0 Mar 10 14:56:05 ilfaris kernel: [ 472.868406] RBP: ffff8800a5a367c0 R08: ffffffff00000001 R09: ffff8800a5a36838 Mar 10 14:56:05 ilfaris kernel: [ 472.868530] R10: 0000000000000005 R11: ffff8800aca17e78 R12: 0000000000000005 Mar 10 14:56:05 ilfaris kernel: [ 472.868655] R13: 0000000000000000 R14: ffff8800a5a367f8 R15: 0000000000000000 Mar 10 14:56:05 ilfaris kernel: [ 472.868782] FS: 00007f603b1e2700(0000) GS:ffff88011ed00000(0000) knlGS:0000000000000000 Mar 10 14:56:05 ilfaris kernel: [ 472.868923] CS: 0010 DS: 0000 ES: 0000 CR0: 000000008005003b Mar 10 14:56:05 ilfaris kernel: [ 472.869025] CR2: 0000000000000018 CR3: 000000010997e000 CR4: 00000000000007e0 Mar 10 14:56:05 ilfaris kernel: [ 472.869149] DR0: 0000000000000000 DR1: 0000000000000000 DR2: 0000000000000000 Mar 10 14:56:05 ilfaris kernel: [ 472.869274] DR3: 0000000000000000 DR6: 00000000ffff0ff0 DR7: 0000000000000400 Mar 10 14:56:05 ilfaris kernel: [ 472.869400] Process xfs_fsr (pid: 4694, threadinfo ffff880119c0a000, task ffff8800a0240190) Mar 10 14:56:05 ilfaris kernel: [ 472.869543] Stack: Mar 10 14:56:05 ilfaris kernel: [ 472.869584] ffffffff811bedc3 ffff880100000000 ffffffff811968aa ffff880000000000 Mar 10 14:56:05 ilfaris kernel: [ 472.869733] ffff8801196df000 0000000200000000 ffff8800b33063b0 ffff8800a5a367c0 Mar 10 14:56:05 ilfaris kernel: [ 472.869881] 0000000000000000 0000000500000000 0000000000000000 0000000000000000 Mar 10 14:56:05 ilfaris kernel: [ 472.870030] Call Trace: Mar 10 14:56:05 ilfaris kernel: [ 472.870086] [] ? xfs_bunmapi+0x633/0x7f0 Mar 10 14:56:05 ilfaris kernel: [ 472.870192] [] ? xfs_swapext+0x22a/0x800 Mar 10 14:56:05 ilfaris kernel: [ 472.870297] [] ? xfs_itruncate_extents+0xe3/0x2a0 Mar 10 14:56:05 ilfaris kernel: [ 472.870416] [] ? xfs_inactive+0x306/0x410 Mar 10 14:56:05 ilfaris kernel: [ 472.870523] [] ? xfs_fs_evict_inode+0x2a/0xb0 Mar 10 14:56:05 ilfaris kernel: [ 472.870634] [] ? evict+0xa2/0x190 Mar 10 14:56:05 ilfaris kernel: [ 472.870729] [] ? d_kill+0xe0/0x130 Mar 10 14:56:05 ilfaris kernel: [ 472.870825] [] ? dput+0xd9/0x1a0 Mar 10 14:56:05 ilfaris kernel: [ 472.870917] [] ? __fput+0x15c/0x240 Mar 10 14:56:05 ilfaris kernel: [ 472.871017] [] ? task_work_run+0x8f/0xd0 Mar 10 14:56:05 ilfaris kernel: [ 472.871122] [] ? int_signal+0x12/0x17 Mar 10 14:56:05 ilfaris kernel: [ 472.871217] Code: 38 c3 90 48 3b 93 b0 01 00 00 75 cd eb e5 0f 1f 44 00 00 48 3b 93 a0 01 00 00 75 95 eb ad 0f 1f 44 00 00 83 4f 68 01 48 8b 46 78 <48> 8b 40 18 80 48 18 01 48 8b 4e 78 8b 81 90 00 00 00 0b 81 8c Mar 10 14:56:05 ilfaris kernel: [ 472.871897] RIP [] xfs_trans_log_inode+0x8/0x30 Mar 10 14:56:05 ilfaris kernel: [ 472.872016] RSP Mar 10 14:56:05 ilfaris kernel: [ 472.872081] CR2: 0000000000000018 Mar 10 14:56:05 ilfaris kernel: [ 472.895316] ---[ end trace 5ee27f6cb3453334 ]--- Mar 10 14:56:05 ilfaris kernel: [ 472.897470] ------------[ cut here ]------------ Mar 10 14:56:05 ilfaris kernel: [ 472.897583] kernel BUG at fs/xfs/xfs_icache.c:323! Mar 10 14:56:05 ilfaris kernel: [ 472.902476] invalid opcode: 0000 [#2] SMP Mar 10 14:56:05 ilfaris kernel: [ 472.907309] Modules linked in: uvcvideo rtl8192ce rtlwifi mac80211 ohci_hcd ehci_pci ehci_hcd psmouse deflate zlib_deflate des_generic ecb sha512_generic sha1_generic hmac af_key xfrm_algo loop fuse btusb arc4 bluetooth crc16 snd_hda_codec_conexant radeon i2c_algo_bit drm_kms_helper snd_hda_codec_hdmi cfg80211 ttm snd_hda_intel drm videobuf2_vmalloc snd_hda_codec videobuf2_memops videobuf2_core snd_hwdep snd_pcm videodev snd_page_alloc agpgart thinkpad_acpi nvram acpi_cpufreq i2c_piix4 serio_raw rtl8192c_common snd_timer rfkill mperf pcspkr i2c_core k10temp evdev battery ac snd video wmi processor button soundcore sha256_generic twofish_x86_64_3way xts lrw gf128mul glue_helper twofish_x86_64 twofish_common cbc dm_crypt dm_mod sd_mod crc_t10dif rtsx_pci_sdmmc mmc_core microcode thermal thermal_sys ahci libahci rtsx_pci mfd_core usbcore usb_common libata scsi_mod [last unloaded: uvcvideo] Mar 10 14:56:05 ilfaris kernel: [ 472.939548] CPU 1 Mar 10 14:56:05 ilfaris kernel: [ 472.939594] Pid: 4695, comm: xfs_fsr Tainted: G D 3.9.0-rc1+ #1 LENOVO 30515YG/30515YG Mar 10 14:56:05 ilfaris kernel: [ 472.949484] RIP: 0010:[] [] xfs_iget+0x6be/0x6c0 Mar 10 14:56:05 ilfaris kernel: [ 472.954492] RSP: 0018:ffff880103db7c28 EFLAGS: 00010246 Mar 10 14:56:05 ilfaris kernel: [ 472.959435] RAX: 0000000000000000 RBX: ffff8800a5a36818 RCX: 0000000000000002 Mar 10 14:56:05 ilfaris kernel: [ 472.964384] RDX: ffffffff00000001 RSI: 0000000000000004 RDI: ffff8800a5a36898 Mar 10 14:56:05 ilfaris kernel: [ 472.969302] RBP: ffff8800a0aae180 R08: 0000000000000000 R09: ffff8800a6218f90 Mar 10 14:56:05 ilfaris kernel: [ 472.974185] R10: 0000000000000005 R11: 0000000000000004 R12: 00000000000675e0 Mar 10 14:56:05 ilfaris kernel: [ 472.979059] R13: ffff880116576890 R14: 0000000000000011 R15: 0000000000000000 Mar 10 14:56:05 ilfaris kernel: [ 472.983914] FS: 00007f603b1e2700(0000) GS:ffff88011ed00000(0000) knlGS:0000000000000000 Mar 10 14:56:05 ilfaris kernel: [ 472.988815] CS: 0010 DS: 0000 ES: 0000 CR0: 0000000080050033 Mar 10 14:56:05 ilfaris kernel: [ 472.993748] CR2: 00007f603aa95de0 CR3: 000000010997e000 CR4: 00000000000007e0 Mar 10 14:56:05 ilfaris kernel: [ 472.998700] DR0: 0000000000000000 DR1: 0000000000000000 DR2: 0000000000000000 Mar 10 14:56:05 ilfaris kernel: [ 473.003605] DR3: 0000000000000000 DR6: 00000000ffff0ff0 DR7: 0000000000000400 Mar 10 14:56:05 ilfaris kernel: [ 473.008458] Process xfs_fsr (pid: 4695, threadinfo ffff880103db6000, task ffff8800a0283210) Mar 10 14:56:05 ilfaris kernel: [ 473.013401] Stack: Mar 10 14:56:05 ilfaris kernel: [ 473.018335] ffff880117159800 0000000100000080 ffff8800a0aae180 ffff880103db7cf0 Mar 10 14:56:05 ilfaris kernel: [ 473.023363] 00000000000075e0 ffffffff811d5863 000000000000f3a0 ffff880117159800 Mar 10 14:56:05 ilfaris kernel: [ 473.028363] ffff880116576840 000000000000f3a0 000675e000000004 000000000000f3a0 Mar 10 14:56:05 ilfaris kernel: [ 473.033349] Call Trace: Mar 10 14:56:05 ilfaris kernel: [ 473.038283] [] ? xfs_dialloc+0x53/0x320 Mar 10 14:56:05 ilfaris kernel: [ 473.043258] [] ? xfs_ialloc+0xcf/0x630 Mar 10 14:56:05 ilfaris kernel: [ 473.048171] [] ? xfs_trans_add_item+0x25/0x70 Mar 10 14:56:05 ilfaris kernel: [ 473.053071] [] ? _xfs_trans_bjoin+0x49/0x70 Mar 10 14:56:05 ilfaris kernel: [ 473.057988] [] ? xfs_dir_ialloc+0x230/0x2f0 Mar 10 14:56:05 ilfaris kernel: [ 473.062902] [] ? xfs_create+0x25e/0x520 Mar 10 14:56:05 ilfaris kernel: [ 473.067804] [] ? __lookup_hash+0x1d/0x50 Mar 10 14:56:05 ilfaris kernel: [ 473.072710] [] ? xfs_vn_mknod+0xa6/0x1a0 Mar 10 14:56:05 ilfaris kernel: [ 473.077613] [] ? vfs_mkdir+0x7f/0x100 Mar 10 14:56:05 ilfaris kernel: [ 473.082513] [] ? sys_mkdirat+0x56/0xd0 Mar 10 14:56:05 ilfaris kernel: [ 473.087418] [] ? system_call_fastpath+0x16/0x1b Mar 10 14:56:05 ilfaris kernel: [ 473.092342] Code: 08 49 83 c6 10 48 89 de ff d2 49 8b 16 48 85 d2 75 eb e9 6e ff ff ff 8b 74 24 50 48 89 df e8 da 94 03 00 85 c0 0f 85 9a fe ff ff <0f> 0b 41 57 48 8d 87 93 01 00 00 49 89 f7 41 56 41 89 d6 41 55 Mar 10 14:56:05 ilfaris kernel: [ 473.103145] RIP [] xfs_iget+0x6be/0x6c0 Mar 10 14:56:05 ilfaris kernel: [ 473.108277] RSP Mar 10 14:56:05 ilfaris kernel: [ 473.113401] ---[ end trace 5ee27f6cb3453335 ]--- Mar 10 15:08:20 ilfaris kernel: [ 1207.707090] BUG: unable to handle kernel paging request at 0000000000026f80 Mar 10 15:08:20 ilfaris kernel: [ 1207.712172] IP: [] xfs_iflush_cluster+0x153/0x3e0 Mar 10 15:08:20 ilfaris kernel: [ 1207.717214] PGD a0183067 PUD a6f67067 PMD 0 Mar 10 15:08:20 ilfaris kernel: [ 1207.722272] Oops: 0000 [#3] SMP Mar 10 15:08:20 ilfaris kernel: [ 1207.727283] Modules linked in: uvcvideo rtl8192ce rtlwifi mac80211 ohci_hcd ehci_pci ehci_hcd psmouse deflate zlib_deflate des_generic ecb sha512_generic sha1_generic hmac af_key xfrm_algo loop fuse btusb arc4 bluetooth crc16 snd_hda_codec_conexant radeon i2c_algo_bit drm_kms_helper snd_hda_codec_hdmi cfg80211 ttm snd_hda_intel drm videobuf2_vmalloc snd_hda_codec videobuf2_memops videobuf2_core snd_hwdep snd_pcm videodev snd_page_alloc agpgart thinkpad_acpi nvram acpi_cpufreq i2c_piix4 serio_raw rtl8192c_common snd_timer rfkill mperf pcspkr i2c_core k10temp evdev battery ac snd video wmi processor button soundcore sha256_generic twofish_x86_64_3way xts lrw gf128mul glue_helper twofish_x86_64 twofish_common cbc dm_crypt dm_mod sd_mod crc_t10dif rtsx_pci_sdmmc mmc_core microcode thermal thermal_sys ahci libahci rtsx_pci mfd_core usbcore usb_common libata scsi_mod [last unloaded: uvcvideo] Mar 10 15:08:20 ilfaris kernel: [ 1207.760676] CPU 1 Mar 10 15:08:20 ilfaris kernel: [ 1207.760724] Pid: 288, comm: xfsaild/dm-1 Tainted: G D 3.9.0-rc1+ #1 LENOVO 30515YG/30515YG Mar 10 15:08:20 ilfaris kernel: [ 1207.771023] RIP: 0010:[] [] xfs_iflush_cluster+0x153/0x3e0 Mar 10 15:08:20 ilfaris kernel: [ 1207.776251] RSP: 0018:ffff8801195f9ce8 EFLAGS: 00010206 Mar 10 15:08:20 ilfaris kernel: [ 1207.781419] RAX: 0000000000026ef0 RBX: ffff8800a88cd600 RCX: 000000000000001d Mar 10 15:08:20 ilfaris kernel: [ 1207.786586] RDX: 000000000000000e RSI: ffff8801195f9ca8 RDI: ffff8800a88cd6c4 Mar 10 15:08:20 ilfaris kernel: [ 1207.791719] RBP: ffff8801156d7080 R08: ffff88003773db80 R09: 0000000000000000 Mar 10 15:08:20 ilfaris kernel: [ 1207.796839] R10: 00000000000004bf R11: 0000000000000210 R12: 0000000000000038 Mar 10 15:08:20 ilfaris kernel: [ 1207.801943] R13: ffff8801196df000 R14: ffff8800a88cd6c4 R15: ffff8800a5a367c0 Mar 10 15:08:20 ilfaris kernel: [ 1207.807084] FS: 00007f5850b83700(0000) GS:ffff88011ed00000(0000) knlGS:0000000000000000 Mar 10 15:08:20 ilfaris kernel: [ 1207.812287] CS: 0010 DS: 0000 ES: 0000 CR0: 000000008005003b Mar 10 15:08:20 ilfaris kernel: [ 1207.817501] CR2: 0000000000026f80 CR3: 00000000a610b000 CR4: 00000000000007e0 Mar 10 15:08:20 ilfaris kernel: [ 1207.822721] DR0: 0000000000000000 DR1: 0000000000000000 DR2: 0000000000000000 Mar 10 15:08:20 ilfaris kernel: [ 1207.827884] DR3: 0000000000000000 DR6: 00000000ffff0ff0 DR7: 0000000000000400 Mar 10 15:08:20 ilfaris kernel: [ 1207.832982] Process xfsaild/dm-1 (pid: 288, threadinfo ffff8801195f8000, task ffff880119504d90) Mar 10 15:08:20 ilfaris kernel: [ 1207.838173] Stack: Mar 10 15:08:20 ilfaris kernel: [ 1207.843341] ffff8801195f9d90 0000000000000100 00000000000002c0 ffffffffffffffe0 Mar 10 15:08:20 ilfaris kernel: [ 1207.848611] ffff88011988c180 0000000081622f80 ffff88011a4c0380 ffffffff811d8fab Mar 10 15:08:20 ilfaris kernel: [ 1207.853821] 0000000009316960 ffff8800a88cd600 ffff8800a88cd6c4 ffff8801196df000 Mar 10 15:08:20 ilfaris kernel: [ 1207.859012] Call Trace: Mar 10 15:08:20 ilfaris kernel: [ 1207.864128] [] ? xfs_iflush_int+0x2fb/0x340 Mar 10 15:08:20 ilfaris kernel: [ 1207.869290] [] ? xfs_iflush+0x112/0x200 Mar 10 15:08:20 ilfaris kernel: [ 1207.874381] [] ? down_trylock+0x2b/0x40 Mar 10 15:08:20 ilfaris kernel: [ 1207.879444] [] ? up+0xd/0x40 Mar 10 15:08:20 ilfaris kernel: [ 1207.884497] [] ? xfs_inode_item_push+0xdb/0x130 Mar 10 15:08:20 ilfaris kernel: [ 1207.889586] [] ? xfsaild+0x2b7/0x5c0 Mar 10 15:08:20 ilfaris kernel: [ 1207.894657] [] ? dequeue_task_fair+0xcc/0xf0 Mar 10 15:08:20 ilfaris kernel: [ 1207.899749] [] ? xfs_trans_ail_cursor_first+0x90/0x90 Mar 10 15:08:20 ilfaris kernel: [ 1207.904874] [] ? kthread+0xb3/0xc0 Mar 10 15:08:20 ilfaris kernel: [ 1207.909994] [] ? kthread_create_on_node+0x110/0x110 Mar 10 15:08:20 ilfaris kernel: [ 1207.915144] [] ? ret_from_fork+0x7c/0xb0 Mar 10 15:08:20 ilfaris kernel: [ 1207.920292] [] ? kthread_create_on_node+0x110/0x110 Mar 10 15:08:20 ilfaris kernel: [ 1207.925483] Code: 93 01 00 00 b8 01 00 00 00 48 d3 e0 ff c8 41 23 47 18 48 23 44 24 18 48 3b 44 24 10 75 b2 41 80 06 01 49 8b 47 78 48 85 c0 74 0c 80 90 00 00 00 ff 41 00 00 75 0b 41 8b 87 c0 00 00 00 85 c0 Mar 10 15:08:20 ilfaris kernel: [ 1207.936618] RIP [] xfs_iflush_cluster+0x153/0x3e0 Mar 10 15:08:20 ilfaris kernel: [ 1207.941852] RSP Mar 10 15:08:20 ilfaris kernel: [ 1207.947024] CR2: 0000000000026f80 Mar 10 15:08:20 ilfaris kernel: [ 1207.952262] ---[ end trace 5ee27f6cb3453336 ]--- Similar traces were already seen with a 3.7 kernel [1]. If you need further information please do not hestitate to ask. With best regards, Julian Wollrath [1] http://article.gmane.org/gmane.comp.file-systems.xfs.general/48998 From mozart.corretorimobiliario@gmail.com Sun Mar 10 15:29:31 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=FREEMAIL_FROM,HTML_MESSAGE, T_DKIM_INVALID autolearn=ham version=3.3.1 X-Original-To: linux-xfs@oss.sgi.com Delivered-To: linux-xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 229517CBF for ; Sun, 10 Mar 2013 15:29:31 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay2.corp.sgi.com (Postfix) with ESMTP id EF4B3304059 for ; Sun, 10 Mar 2013 13:29:30 -0700 (PDT) X-ASG-Debug-ID: 1362947369-04bdf022953de100001-w1Z2WR Received: from mail-ia0-f195.google.com (mail-ia0-f195.google.com [209.85.210.195]) by cuda.sgi.com with ESMTP id rvZjHDybiYkjFFRS (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Sun, 10 Mar 2013 13:29:29 -0700 (PDT) X-Barracuda-Envelope-From: mozart.corretorimobiliario@gmail.com X-Barracuda-Apparent-Source-IP: 209.85.210.195 X-Barracuda-IPDD: Level1 [gmail.com/209.85.210.195] Received: by mail-ia0-f195.google.com with SMTP id i18so772721iac.10 for ; Sun, 10 Mar 2013 13:29:29 -0700 (PDT) X-Barracuda-IPDD: Level1 [gmail.com/209.85.210.195] X-Barracuda-IPDD: Level1 [gmail.com/209.85.210.195] DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20120113; h=mime-version:x-received:in-reply-to:references:date:message-id :subject:from:to:content-type; bh=moBtPRwcB2sCrRfRE3Yt+SLwJLBkyuCBkKoUjN4L4SI=; b=FcJUneMvRek67oOOA34zvdJwLVZUSA2uXs+FNiBGS/3XKpCJfHrfr0vvO4BUn8SXFq nbSeZ9i5VgC/pU7bwrkiRqQRA2XqE3K7vFV/TnsRaEn7HK5oTVeb0Vm1SiFYTKIbqZiU hLHncMVBbvUz3In+itG90MgS9rqXRDYCljAjOS0ddxpfPjeRiZONvGQpRJpSvQyxnqP+ e429UJTfZ3X5Ya3XQRIU4mThPnYHH3O9m9RVaZdaIS+eYLTIpIJPrrkaDIMB3GXUkXpt ixfnRiHnz54Um+MKsliOkEcyjIPvWqnVDnOMpx/BLi1O0jRFk+Pgui1S6rZs45l8qFp4 PIzw== MIME-Version: 1.0 X-Received: by 10.50.194.164 with SMTP id hx4mr5341438igc.35.1362947369260; Sun, 10 Mar 2013 13:29:29 -0700 (PDT) Received: by 10.43.105.4 with HTTP; Sun, 10 Mar 2013 13:29:28 -0700 (PDT) In-Reply-To: References: Date: Sun, 10 Mar 2013 16:29:28 -0400 Message-ID: Subject: Fwd: Residencial Bela Vista-Programa Minha Casa Minha Vida From: Mozart Faria X-ASG-Orig-Subj: Fwd: Residencial Bela Vista-Programa Minha Casa Minha Vida To: "manaus.imoveis@hotmail.com" Content-Type: multipart/alternative; boundary=14dae9340de1caf4c504d797e9a4 X-Barracuda-Connect: mail-ia0-f195.google.com[209.85.210.195] X-Barracuda-Start-Time: 1362947369 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_MISMATCH_TO, DKIM_SIGNED, DKIM_VERIFIED, HTML_MESSAGE X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124827 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 BSF_SC0_MISMATCH_TO Envelope rcpt doesn't match header -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature 0.00 HTML_MESSAGE BODY: HTML included in message --14dae9340de1caf4c504d797e9a4 Content-Type: text/plain; charset=ISO-8859-1 --14dae9340de1caf4c504d797e9a4 Content-Type: text/html; charset=ISO-8859-1
--14dae9340de1caf4c504d797e9a4-- From david@fromorbit.com Sun Mar 10 17:11:53 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 559717CBF for ; Sun, 10 Mar 2013 17:11:53 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay1.corp.sgi.com (Postfix) with ESMTP id 41B8A8F8035 for ; Sun, 10 Mar 2013 15:11:50 -0700 (PDT) X-ASG-Debug-ID: 1362953508-04cb6c2b043c7c80001-NocioJ Received: from ipmail07.adl2.internode.on.net (ipmail07.adl2.internode.on.net [150.101.137.131]) by cuda.sgi.com with ESMTP id P2Wt8OTRbFORYiU0 for ; Sun, 10 Mar 2013 15:11:48 -0700 (PDT) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.131 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AngcAG0DPVF5LaFk/2dsb2JhbABChzG3eYUWAQIBgUoXdIImAQEFOhwjEAgDGAklDwUlAyETiBK7axWNeBgfSgeDQAOWVJB2gx4o Received: from ppp121-45-161-100.lns20.syd6.internode.on.net (HELO dastard) ([121.45.161.100]) by ipmail07.adl2.internode.on.net with ESMTP; 11 Mar 2013 08:41:47 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UEoT3-0005Fn-J9; Mon, 11 Mar 2013 09:11:45 +1100 Date: Mon, 11 Mar 2013 09:11:45 +1100 From: Dave Chinner To: Julien FERRERO Cc: stan@hardwarefreak.com, xfs@oss.sgi.com Subject: Re: XFS filesystem corruption Message-ID: <20130310221145.GJ23616@dastard> X-ASG-Orig-Subj: Re: XFS filesystem corruption References: <51380FD3.5010302@hardwarefreak.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail07.adl2.internode.on.net[150.101.137.131] X-Barracuda-Start-Time: 1362953508 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124834 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Thu, Mar 07, 2013 at 02:04:32PM +0100, Julien FERRERO wrote: > > It may be unrelated to your corruption, problem but I'm curious why you > > are specifying a 32MB log section instead of letting mkfs.xfs make the > > log size decision. > > I honestly don' know, the rebuild script was written 8 years ago by an > engineer that since left the company. > > Is 32MB a short log space for a 1.5 TB of data ? Depends on your workload. And to tell the truth, the tiny log is probably the only reason that your filesystems have gone this long without corruption, as the small size will force frequent log writes and hence issue cache flushes regularly.... Cheers, Dave. -- Dave Chinner david@fromorbit.com From david@fromorbit.com Sun Mar 10 17:45:43 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id A7A6C7CBF for ; Sun, 10 Mar 2013 17:45:43 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay2.corp.sgi.com (Postfix) with ESMTP id 77F17304053 for ; Sun, 10 Mar 2013 15:45:40 -0700 (PDT) X-ASG-Debug-ID: 1362955538-04bdf022973eae60001-NocioJ Received: from ipmail07.adl2.internode.on.net (ipmail07.adl2.internode.on.net [150.101.137.131]) by cuda.sgi.com with ESMTP id zTY7Pz5gzxrNwCR5 for ; Sun, 10 Mar 2013 15:45:38 -0700 (PDT) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.131 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AtgeACIMPVF5LaFk/2dsb2JhbABChzG3eYUWAQIBgUoXdIImAQEEATocIwULCAMYCSUPBSUDIROIDQW7cBWNSS8YH0oHg0ADllSQdoMeKA Received: from ppp121-45-161-100.lns20.syd6.internode.on.net (HELO dastard) ([121.45.161.100]) by ipmail07.adl2.internode.on.net with ESMTP; 11 Mar 2013 09:15:37 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UEozo-0005Is-PO; Mon, 11 Mar 2013 09:45:36 +1100 Date: Mon, 11 Mar 2013 09:45:36 +1100 From: Dave Chinner To: Stan Hoeppner Cc: Ric Wheeler , Julien FERRERO , xfs@oss.sgi.com Subject: Re: XFS filesystem corruption Message-ID: <20130310224536.GK23616@dastard> X-ASG-Orig-Subj: Re: XFS filesystem corruption References: <20130306161519.2c28d911@galadriel.home> <20130306232100.6286f640@galadriel.home> <5137CD46.6070909@redhat.com> <5139A3B6.3040805@hardwarefreak.com> <5139D792.4090304@redhat.com> <513A350A.508@hardwarefreak.com> <20130309091152.GH23616@dastard> <513B84AD.2000603@hardwarefreak.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <513B84AD.2000603@hardwarefreak.com> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail07.adl2.internode.on.net[150.101.137.131] X-Barracuda-Start-Time: 1362955538 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124836 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Sat, Mar 09, 2013 at 12:51:25PM -0600, Stan Hoeppner wrote: > On 3/9/2013 3:11 AM, Dave Chinner wrote: > > On Fri, Mar 08, 2013 at 12:59:22PM -0600, Stan Hoeppner wrote: > >> On 3/8/2013 6:20 AM, Ric Wheeler wrote: > >>>> Something that none of us mentioned WRT write barriers is that while the > >>>> filesystem structure may avoid corruption when the power is cut, files > >>>> may still be corrupted, in conditions such as any/all of these: > >> > >> I made it very clear I was discussing file corruption here, not > >> filesystem corruption. You already covered that base. I was > >> specifically addressing the fact that XFS performs barriers on metadata > >> writes but not file data writes. > > > > Actually, you're not correct there, either, Stan. ;) > > With "either" you're implying I was incorrect twice, and I wasn't, not > in whole anyway, maybe in part. ;) The "either" was in reference to you correcting someone else... > > XFS only issues cache flushes/FUA writes for log IO. Metadata IO is > > done exactly the same way that data IO is done - without barriers. > > It's because metadata lost in drive caches at the time of a crash is > > rewritten by journal replay that filesystem corruption does not > > occur. > > Technical semantics. Geeze, give the non dev a break now and then. ;) It's the technical semantics that matter when it comes to behaviour at power loss. That's why I pick on "technical semantics" - it's makes your analysis and understanding of problems better, and that means there's less for me to do in future ;) > Does everyone remember the transitive property of equality from math > class decades ago? It states "If A=B and B=C then A=C". Thus if > barrier writes to the journal protect the journal, and the journal > protects metadata, then barrier writes to the journal protect metadata. Yup, but the devil is in the detail - we don't protect individual metadata writes at all and that difference is significant enough to comment on.... :P > I had a detail incorrect, but not the big picture. And I'd bet the OP > is more interested in the big picture. So surely I'd get a B or a C > here, but certainly not an F. Certainly a B+ - like I said, I'm being picky because you seem to understand the details once explained... :) > > As it is, if the application uses direct IO (likely, as it > > sounds like video capture/editing/playout here) then log IO > > will also ensure that the data written by the app is on disk (i.e. > > that's ithe mechanism by which fsync works). > > So this would be an interesting upside down case for XFS, as the file > data may be intact, but the filesystem gets corrupted, the opposite of > the design point. Well, if barriers are working correctly, then there won't be any filesystem corruption, either... > >>> Also, if there are active writers, this is inherently racy. A better > >>> script would unmount the file systems :) > >> > >> Yes, a umount would be even better. > > > > Change the bios so that the power button does not cause a power down > > so the OS can capture the button event and trigger an orderly > > shutdown. > > Dare I say "Dave you're incorrect". ;) Heh. Not so much incorrect as "unaware of the entire scope". I browsed the thread and didn't pick up on this little detail... Cheers, Dave. -- Dave Chinner david@fromorbit.com From david@fromorbit.com Sun Mar 10 17:56:03 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id DD5207CBF for ; Sun, 10 Mar 2013 17:56:03 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay1.corp.sgi.com (Postfix) with ESMTP id AB01C8F8035 for ; Sun, 10 Mar 2013 15:56:03 -0700 (PDT) X-ASG-Debug-ID: 1362956161-04bdf022983ebb40001-NocioJ Received: from ipmail07.adl2.internode.on.net (ipmail07.adl2.internode.on.net [150.101.137.131]) by cuda.sgi.com with ESMTP id SEEG05Uw1xt9bVS7 for ; Sun, 10 Mar 2013 15:56:01 -0700 (PDT) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.131 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AtgeABkPPVF5LaFk/2dsb2JhbAAoGocxt3mFFgECAYFKF3SCJgEBBTocIxAIAw4KCSUPBSUDIROIEg0uuzwVjXgYH0oHg0ADllSQdoMeKA Received: from ppp121-45-161-100.lns20.syd6.internode.on.net (HELO dastard) ([121.45.161.100]) by ipmail07.adl2.internode.on.net with ESMTP; 11 Mar 2013 09:26:01 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UEp9s-0005K7-Kc; Mon, 11 Mar 2013 09:56:00 +1100 Date: Mon, 11 Mar 2013 09:56:00 +1100 From: Dave Chinner To: Julian Wollrath Cc: xfs@oss.sgi.com Subject: Re: Null pointer dereference and following traces on 3.9-rc1 Message-ID: <20130310225600.GL23616@dastard> X-ASG-Orig-Subj: Re: Null pointer dereference and following traces on 3.9-rc1 References: <20130310154900.673deee0@ilfaris> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <20130310154900.673deee0@ilfaris> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail07.adl2.internode.on.net[150.101.137.131] X-Barracuda-Start-Time: 1362956161 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.10 X-Barracuda-Spam-Status: No, SCORE=0.10 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_SA085 X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124838 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.10 BSF_SC0_SA085 Custom Rule SA085 On Sun, Mar 10, 2013 at 03:49:00PM +0100, Julian Wollrath wrote: > Hello, > > after a xfs_fsr run I found the following in my syslog: If you can reproduce this, please run an event trace gathering the xfs_swap_extent* trace points while xfs_fsr is running so I can determine if/why the swap extents code is corrupting inodes. # trace-cmd record -e xfs_swap_extents\* xfs_fsr ..... # trace-cmd report > trace_report.txt Read here for a bit more detail on trace-cmd: http://xfs.org/index.php/XFS_FAQ#Q:_What_information_should_I_include_when_reporting_a_problem.3F Cheers, Dave. -- Dave Chinner david@fromorbit.com From david@fromorbit.com Sun Mar 10 18:03:32 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 316F77CBF for ; Sun, 10 Mar 2013 18:03:32 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay1.corp.sgi.com (Postfix) with ESMTP id 0FB4D8F804C for ; Sun, 10 Mar 2013 16:03:28 -0700 (PDT) X-ASG-Debug-ID: 1362956606-04cbb07dbc3c6670001-NocioJ Received: from ipmail07.adl2.internode.on.net (ipmail07.adl2.internode.on.net [150.101.137.131]) by cuda.sgi.com with ESMTP id b0BPzugf1RbuWPNb for ; Sun, 10 Mar 2013 16:03:27 -0700 (PDT) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.131 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AtceAFoQPVF5LaFk/2dsb2JhbABChzG3eoUWAQIBgUoXdIImAQEFOhwjEAgDGAklDwUlAyETiBK7exWNeBgfSgeDQAOWVJB2gVSBSig Received: from ppp121-45-161-100.lns20.syd6.internode.on.net (HELO dastard) ([121.45.161.100]) by ipmail07.adl2.internode.on.net with ESMTP; 11 Mar 2013 09:33:26 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UEpH3-0005Lc-NE; Mon, 11 Mar 2013 10:03:25 +1100 Date: Mon, 11 Mar 2013 10:03:25 +1100 From: Dave Chinner To: Eric Sandeen Cc: Koen De Wit , xfs@oss.sgi.com, linux-btrfs Subject: Re: xfstests: 301: sparse copy between different filesystems/mountpoints on btrfs Message-ID: <20130310230325.GM23616@dastard> X-ASG-Orig-Subj: Re: xfstests: 301: sparse copy between different filesystems/mountpoints on btrfs References: <50F9C331.9000501@oracle.com> <513BD2CF.5020204@sandeen.net> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <513BD2CF.5020204@sandeen.net> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail07.adl2.internode.on.net[150.101.137.131] X-Barracuda-Start-Time: 1362956607 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124838 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Sat, Mar 09, 2013 at 06:24:47PM -0600, Eric Sandeen wrote: > On 1/18/13 3:48 PM, Koen De Wit wrote: > > +} > > + > > +_scratch_mount > > +_create_reflinks_to $TESTDIR2 > > +_scratch_unmount > > + > > +mount $TEST_DEV $SCRATCH_MNT > > +_create_reflinks_to $TESTDIR3 > > +umount $SCRATCH_MNT > > TBH this confuses me, not that it's necessarily wrong (?) > You mount TEST_DEV on $SCRATCH_MNT which makes my brain hurt a little. > Then _create_reflinks_to $TESTDIR3 and at that point, um, what's going on, > what's linking what to where? Mounting the TEST_DEV on SCRATCH_MNT is almost always a bad thing to do. The test harness expects TEST_DEV to be mounted on TEST_DIR, not anywhere else. If you need multiple scratch filesystems to test cross-device linkage errors, use loopback devices or make use of the btrfs scratch device pool... Cheers, Dave. -- Dave Chinner david@fromorbit.com From stan@hardwarefreak.com Sun Mar 10 18:55:00 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 68D567CBF for ; Sun, 10 Mar 2013 18:55:00 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay2.corp.sgi.com (Postfix) with ESMTP id 2AC18304053 for ; Sun, 10 Mar 2013 16:54:57 -0700 (PDT) X-ASG-Debug-ID: 1362959695-04bdf022973f0bd0001-NocioJ Received: from greer.hardwarefreak.com (mo-65-41-216-221.sta.embarqhsd.net [65.41.216.221]) by cuda.sgi.com with ESMTP id gyL1qe01voxY7ywX for ; Sun, 10 Mar 2013 16:54:56 -0700 (PDT) X-Barracuda-Envelope-From: stan@hardwarefreak.com X-Barracuda-Apparent-Source-IP: 65.41.216.221 X-Barracuda-User-Whitelist: xfs@oss.sgi.com Received: from [192.168.100.53] (gffx.hardwarefreak.com [192.168.100.53]) by greer.hardwarefreak.com (Postfix) with ESMTP id 912BE6C162; Sun, 10 Mar 2013 18:54:55 -0500 (CDT) Message-ID: <513D1D51.7010905@hardwarefreak.com> Date: Sun, 10 Mar 2013 18:54:57 -0500 From: Stan Hoeppner Reply-To: stan@hardwarefreak.com User-Agent: Mozilla/5.0 (Windows NT 5.1; rv:17.0) Gecko/20130215 Thunderbird/17.0.3 MIME-Version: 1.0 To: Dave Chinner CC: Ric Wheeler , Julien FERRERO , xfs@oss.sgi.com Subject: Re: XFS filesystem corruption References: <20130306161519.2c28d911@galadriel.home> <20130306232100.6286f640@galadriel.home> <5137CD46.6070909@redhat.com> <5139A3B6.3040805@hardwarefreak.com> <5139D792.4090304@redhat.com> <513A350A.508@hardwarefreak.com> <20130309091152.GH23616@dastard> <513B84AD.2000603@hardwarefreak.com> <20130310224536.GK23616@dastard> X-ASG-Orig-Subj: Re: XFS filesystem corruption In-Reply-To: <20130310224536.GK23616@dastard> Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: mo-65-41-216-221.sta.embarqhsd.net[65.41.216.221] X-Barracuda-Start-Time: 1362959695 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Barracuda-BRTS-Status: 1 X-Virus-Scanned: by bsmtpd at sgi.com On 3/10/2013 5:45 PM, Dave Chinner wrote: > On Sat, Mar 09, 2013 at 12:51:25PM -0600, Stan Hoeppner wrote: >> On 3/9/2013 3:11 AM, Dave Chinner wrote: >>> On Fri, Mar 08, 2013 at 12:59:22PM -0600, Stan Hoeppner wrote: >>>> On 3/8/2013 6:20 AM, Ric Wheeler wrote: >>>>>> Something that none of us mentioned WRT write barriers is that while the >>>>>> filesystem structure may avoid corruption when the power is cut, files >>>>>> may still be corrupted, in conditions such as any/all of these: >>>> >>>> I made it very clear I was discussing file corruption here, not >>>> filesystem corruption. You already covered that base. I was >>>> specifically addressing the fact that XFS performs barriers on metadata >>>> writes but not file data writes. >>> >>> Actually, you're not correct there, either, Stan. ;) >> >> With "either" you're implying I was incorrect twice, and I wasn't, not >> in whole anyway, maybe in part. ;) > > The "either" was in reference to you correcting someone else... I wasn't attempting to correct Ric on the technicals, as that's simply not really possible, me being a user talking to a dev. That would be really presumptuous on my part, not to mention dumb. I had made a point about file data corruption, and he replied talking about metadata corruption. My "correction" was simply to clarify I was talking about file data not metadata. >>> XFS only issues cache flushes/FUA writes for log IO. Metadata IO is >>> done exactly the same way that data IO is done - without barriers. >>> It's because metadata lost in drive caches at the time of a crash is >>> rewritten by journal replay that filesystem corruption does not >>> occur. >> >> Technical semantics. Geeze, give the non dev a break now and then. ;) > > It's the technical semantics that matter when it comes to behaviour > at power loss. That's why I pick on "technical semantics" - it's > makes your analysis and understanding of problems better, and that > means there's less for me to do in future ;) I do my best to grab the low hanging fruit when I can so you guys can concentrate on more important stuff. >> Does everyone remember the transitive property of equality from math >> class decades ago? It states "If A=B and B=C then A=C". Thus if >> barrier writes to the journal protect the journal, and the journal >> protects metadata, then barrier writes to the journal protect metadata. > > Yup, but the devil is in the detail - we don't protect individual > metadata writes at all and that difference is significant enough to > comment on.... :P Elaborate on this a bit, if you have time. I was under the impression that all directory updates were journaled first. >> I had a detail incorrect, but not the big picture. And I'd bet the OP >> is more interested in the big picture. So surely I'd get a B or a C >> here, but certainly not an F. > > Certainly a B+ - like I said, I'm being picky because you seem to > understand the details once explained... :) Usually. ;) Sometimes it takes a couple of sessions before it fully sinks in. I must say I've learned a tremendous amount from the devs on this list, and I'm grateful that you specifically Dave have taken the time to 'tutor' me, and others, over the last couple of years. >>> As it is, if the application uses direct IO (likely, as it >>> sounds like video capture/editing/playout here) then log IO >>> will also ensure that the data written by the app is on disk (i.e. >>> that's ithe mechanism by which fsync works). >> >> So this would be an interesting upside down case for XFS, as the file >> data may be intact, but the filesystem gets corrupted, the opposite of >> the design point. > > Well, if barriers are working correctly, then there won't be any > filesystem corruption, either... Ok, see, this is odd part here. The OP didn't seem to have this metadata corruption issue with the old 2.6.18 kernel, at least I think that's the one he mentioned. Then he switched to 2.6.35. IIRC there were a number of commits around that time and some regressions. I also recall 2.6.35 is not a long term stable kernel. I'd guess there were reasons for that. So, I'm wondering if there was a bug/regression relating to XFS metadata in 2.6.35 corrected in .36 or later and simply not backported. Seems to ring a bell, vaguely. I have no idea where/how to search for such information. >>>>> Also, if there are active writers, this is inherently racy. A better >>>>> script would unmount the file systems :) >>>> >>>> Yes, a umount would be even better. >>> >>> Change the bios so that the power button does not cause a power down >>> so the OS can capture the button event and trigger an orderly >>> shutdown. >> >> Dare I say "Dave you're incorrect". ;) > > Heh. Not so much incorrect as "unaware of the entire scope". I > browsed the thread and didn't pick up on this little detail... I know. That was a bit of a cheap shot, hence the judicious use of quotes and winkies. ;) I knew you'd missed it or you'd not have mentioned the ACPI soft power switch option. -- Stan From david@fromorbit.com Sun Mar 10 19:50:32 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 36DE67F4C for ; Sun, 10 Mar 2013 19:50:32 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay2.corp.sgi.com (Postfix) with ESMTP id 25CE4304039 for ; Sun, 10 Mar 2013 17:50:28 -0700 (PDT) X-ASG-Debug-ID: 1362963026-04cb6c2b043d5e30001-NocioJ Received: from ipmail07.adl2.internode.on.net (ipmail07.adl2.internode.on.net [150.101.137.131]) by cuda.sgi.com with ESMTP id 4L5LQp82DKagt9v6 for ; Sun, 10 Mar 2013 17:50:27 -0700 (PDT) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.131 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AtceACopPVF5LaFk/2dsb2JhbABDhzO3eoUWAQIBgUsXdIIlAQEFOhwjEAgDGAklDwUlAyETiBK7dhWNSS8YH0oHgl9hA5MQg0SQdoMeKA Received: from ppp121-45-161-100.lns20.syd6.internode.on.net (HELO dastard) ([121.45.161.100]) by ipmail07.adl2.internode.on.net with ESMTP; 11 Mar 2013 11:20:26 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UEqwa-0005WK-Vi; Mon, 11 Mar 2013 11:50:25 +1100 Date: Mon, 11 Mar 2013 11:50:24 +1100 From: Dave Chinner To: Stan Hoeppner Cc: Ric Wheeler , Julien FERRERO , xfs@oss.sgi.com Subject: Re: XFS filesystem corruption Message-ID: <20130311005024.GC20565@dastard> X-ASG-Orig-Subj: Re: XFS filesystem corruption References: <20130306232100.6286f640@galadriel.home> <5137CD46.6070909@redhat.com> <5139A3B6.3040805@hardwarefreak.com> <5139D792.4090304@redhat.com> <513A350A.508@hardwarefreak.com> <20130309091152.GH23616@dastard> <513B84AD.2000603@hardwarefreak.com> <20130310224536.GK23616@dastard> <513D1D51.7010905@hardwarefreak.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <513D1D51.7010905@hardwarefreak.com> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail07.adl2.internode.on.net[150.101.137.131] X-Barracuda-Start-Time: 1362963026 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124846 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Sun, Mar 10, 2013 at 06:54:57PM -0500, Stan Hoeppner wrote: > On 3/10/2013 5:45 PM, Dave Chinner wrote: > >> Does everyone remember the transitive property of equality from math > >> class decades ago? It states "If A=B and B=C then A=C". Thus if > >> barrier writes to the journal protect the journal, and the journal > >> protects metadata, then barrier writes to the journal protect metadata. > > > > Yup, but the devil is in the detail - we don't protect individual > > metadata writes at all and that difference is significant enough to > > comment on.... :P > > Elaborate on this a bit, if you have time. I was under the impression > that all directory updates were journaled first. That's correct - they are all journalled. But journalling is done at the transactional level, not that of individual metadata changes. IOWs, journalled changes do not contain the same information as a metadata buffer write - they contain both more and less information than a metadata buffer write. They contain more information in that there is change atomicity information in the journal information for recovery purposes. i.e. how the individual change relates to changes in other related metadata objects. This information is needed in the journal so that log recovery knows to either apply all the changes in a checkpoint or none of them if this journal checkpoint (or a previous one) is incomplete. They contain less information in that the changes to a metadata object is stored as a diff in the journal rather than as a complete copy of the object. This is done to reduce the amount of journal space and memory required to track and store all of the changes in the checkpoint. Hence what is written to the journal is quite different to what is written during metadata writeback in both contents ad method. It is the atomicity information in the journal that we know got synchronised to disk (via the FUA/cache flush) that enables us to get away with being lazy writing back metadata buffers in any order we please without needing FUA/cache flushes... So, yes you are correct in that the journalling protects metadata. However, the distinction I'm making is that the journal writes contain different information and have different constraints compared to individual metadata object writeback, and therefore are not the "same thing" and do not require the same protection from power loss/crash events... Cheers, Dave. -- Dave Chinner david@fromorbit.com From sandeen@sandeen.net Sun Mar 10 20:40:33 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 38E1E7F3F for ; Sun, 10 Mar 2013 20:40:33 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay1.corp.sgi.com (Postfix) with ESMTP id 248518F8049 for ; Sun, 10 Mar 2013 18:40:32 -0700 (PDT) X-ASG-Debug-ID: 1362966031-04cbb07dbd3d3a50001-NocioJ Received: from sandeen.net (sandeen.net [63.231.237.45]) by cuda.sgi.com with ESMTP id EZ5oC2IGehjJPK8t for ; Sun, 10 Mar 2013 18:40:31 -0700 (PDT) X-Barracuda-Envelope-From: sandeen@sandeen.net X-Barracuda-Apparent-Source-IP: 63.231.237.45 Received: from liberator.sandeen.net (liberator.sandeen.net [10.0.0.4]) (using TLSv1 with cipher DHE-RSA-CAMELLIA256-SHA (256/256 bits)) (No client certificate requested) by sandeen.net (Postfix) with ESMTPSA id 61DAF63C59BB; Sun, 10 Mar 2013 20:40:31 -0500 (CDT) Message-ID: <513D360F.4060309@sandeen.net> Date: Sun, 10 Mar 2013 20:40:31 -0500 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: Dave Chinner CC: Koen De Wit , linux-btrfs , xfs@oss.sgi.com Subject: Re: xfstests: 301: sparse copy between different filesystems/mountpoints on btrfs References: <50F9C331.9000501@oracle.com> <513BD2CF.5020204@sandeen.net> <20130310230325.GM23616@dastard> X-ASG-Orig-Subj: Re: xfstests: 301: sparse copy between different filesystems/mountpoints on btrfs In-Reply-To: <20130310230325.GM23616@dastard> X-Enigmail-Version: 1.5.1 Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: sandeen.net[63.231.237.45] X-Barracuda-Start-Time: 1362966031 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124848 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On 3/10/13 6:03 PM, Dave Chinner wrote: > On Sat, Mar 09, 2013 at 06:24:47PM -0600, Eric Sandeen wrote: >> On 1/18/13 3:48 PM, Koen De Wit wrote: >>> +} >>> + >>> +_scratch_mount >>> +_create_reflinks_to $TESTDIR2 >>> +_scratch_unmount >>> + >>> +mount $TEST_DEV $SCRATCH_MNT >>> +_create_reflinks_to $TESTDIR3 >>> +umount $SCRATCH_MNT >> >> TBH this confuses me, not that it's necessarily wrong (?) >> You mount TEST_DEV on $SCRATCH_MNT which makes my brain hurt a little. >> Then _create_reflinks_to $TESTDIR3 and at that point, um, what's going on, >> what's linking what to where? > > Mounting the TEST_DEV on SCRATCH_MNT is almost always a bad thing to > do. The test harness expects TEST_DEV to be mounted on TEST_DIR, not > anywhere else. > > If you need multiple scratch filesystems to test cross-device > linkage errors, use loopback devices or make use of the btrfs > scratch device pool... Actually, looking at it again - does this wind up with TEST_DEV mounted on both TEST_DIR and SCRATCH_MNT? Maybe what the test wants is more mountpoints, not more devices? -Eric > Cheers, > > Dave. > From david@fromorbit.com Sun Mar 10 20:55:49 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 40A3F7F4C for ; Sun, 10 Mar 2013 20:55:49 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay2.corp.sgi.com (Postfix) with ESMTP id 2F56A304039 for ; Sun, 10 Mar 2013 18:55:46 -0700 (PDT) X-ASG-Debug-ID: 1362966944-04cb6c2b043dcdf0001-NocioJ Received: from ipmail07.adl2.internode.on.net (ipmail07.adl2.internode.on.net [150.101.137.131]) by cuda.sgi.com with ESMTP id ZXiB1JeqiaoqbjKS for ; Sun, 10 Mar 2013 18:55:44 -0700 (PDT) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.131 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AtceAFU4PVF5LaFk/2dsb2JhbABDhzS3eoUWAQIBgUwXdIIkAQEFOhwjEAgDGAklDwUlAyETiBK8ERWNeBgfSgeCX2EDllSQdoMeKA Received: from ppp121-45-161-100.lns20.syd6.internode.on.net (HELO dastard) ([121.45.161.100]) by ipmail07.adl2.internode.on.net with ESMTP; 11 Mar 2013 12:25:43 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UErxm-0005dl-9K; Mon, 11 Mar 2013 12:55:42 +1100 Date: Mon, 11 Mar 2013 12:55:42 +1100 From: Dave Chinner To: Pascal Cc: xfs@oss.sgi.com Subject: Re: Maximum file system size of XFS? Message-ID: <20130311015542.GA21651@dastard> X-ASG-Orig-Subj: Re: Maximum file system size of XFS? References: <20130309215121.0e614ef8@thinky> <513BB7C3.4050009@redhat.com> <20130309233940.3b7c0910@thinky> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <20130309233940.3b7c0910@thinky> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail07.adl2.internode.on.net[150.101.137.131] X-Barracuda-Start-Time: 1362966944 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124850 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Sat, Mar 09, 2013 at 11:39:40PM +0100, Pascal wrote: > thank you for your answer. I am aware that there is a difference > between the maximum size under practical conditions and the theoretical > maximum. But I am looking for this theoretical number to use in within > in my thesis comparing file systems. Out of curiousity, what apsect of file systems are you comparing? Cheers, Dave. -- Dave Chinner david@fromorbit.com From david@fromorbit.com Sun Mar 10 21:00:33 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id DB8267F4C for ; Sun, 10 Mar 2013 21:00:33 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay1.corp.sgi.com (Postfix) with ESMTP id C21958F8050 for ; Sun, 10 Mar 2013 19:00:33 -0700 (PDT) X-ASG-Debug-ID: 1362967231-04cb6c2b033dd650001-NocioJ Received: from ipmail07.adl2.internode.on.net (ipmail07.adl2.internode.on.net [150.101.137.131]) by cuda.sgi.com with ESMTP id ibuGVsZXNarVfx7g for ; Sun, 10 Mar 2013 19:00:32 -0700 (PDT) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.131 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AtweAKI5PVF5LaFk/2dsb2JhbABDhzS3eoUTAwECAYFMF3SCJAEBBTocIxAIAxgJJQ8FJQMhE4gSvBgVjXgYH0oHgl9hA5ZUkHaDHig Received: from ppp121-45-161-100.lns20.syd6.internode.on.net (HELO dastard) ([121.45.161.100]) by ipmail07.adl2.internode.on.net with ESMTP; 11 Mar 2013 12:30:31 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UEs2Q-0005eY-S2; Mon, 11 Mar 2013 13:00:30 +1100 Date: Mon, 11 Mar 2013 13:00:30 +1100 From: Dave Chinner To: Hans-Peter Jansen Cc: xfs@oss.sgi.com Subject: Re: [PATCH] xfs: ensure we capture IO errors correctly Message-ID: <20130311020030.GB21651@dastard> X-ASG-Orig-Subj: Re: [PATCH] xfs: ensure we capture IO errors correctly References: <1362708074-14987-1-git-send-email-david@fromorbit.com> <1407262.RNsTtTSyZy@xrated> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <1407262.RNsTtTSyZy@xrated> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail07.adl2.internode.on.net[150.101.137.131] X-Barracuda-Start-Time: 1362967231 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124850 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Fri, Mar 08, 2013 at 02:06:52PM +0100, Hans-Peter Jansen wrote: > Hi, > > this sounds like stable material after a little simmering.. Yes, it probably is a candidate for 3.8.x Cheers, Dave. -- Dave Chinner david@fromorbit.com From david@fromorbit.com Sun Mar 10 21:02:11 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 570227F3F for ; Sun, 10 Mar 2013 21:02:11 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay1.corp.sgi.com (Postfix) with ESMTP id 2668B8F8050 for ; Sun, 10 Mar 2013 19:02:07 -0700 (PDT) X-ASG-Debug-ID: 1362967326-04bdf022983fbe20001-NocioJ Received: from ipmail07.adl2.internode.on.net (ipmail07.adl2.internode.on.net [150.101.137.131]) by cuda.sgi.com with ESMTP id ioLnwonGmUquy8Sw for ; Sun, 10 Mar 2013 19:02:06 -0700 (PDT) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.131 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AtceAKI5PVF5LaFk/2dsb2JhbABDhzS3eoUWAQIBgUwXdIIkAQEFJxMcIxAIAxgJJQ8FJQMhE4gSvBgVjXgYH0oHgl9hA5ZUkHaDHig Received: from ppp121-45-161-100.lns20.syd6.internode.on.net (HELO dastard) ([121.45.161.100]) by ipmail07.adl2.internode.on.net with ESMTP; 11 Mar 2013 12:32:05 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UEs3x-0005ex-BP; Mon, 11 Mar 2013 13:02:05 +1100 Date: Mon, 11 Mar 2013 13:02:05 +1100 From: Dave Chinner To: Eric Sandeen Cc: xfs-oss Subject: Re: [PATCH] xfsprogs: skip freelist scans of corrupt agf Message-ID: <20130311020205.GC21651@dastard> X-ASG-Orig-Subj: Re: [PATCH] xfsprogs: skip freelist scans of corrupt agf References: <513B5393.4000203@sandeen.net> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <513B5393.4000203@sandeen.net> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail07.adl2.internode.on.net[150.101.137.131] X-Barracuda-Start-Time: 1362967326 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124850 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Sat, Mar 09, 2013 at 09:21:55AM -0600, Eric Sandeen wrote: > If an agf has bad values in the freelist, this can wreak > havoc if, for example, first > last and the loop > never exits; we index agfl->agfl_bno[i] off into the weeds. > > If they're off, warn about it and skip the scan. > > Thisis done both in xfs_check and xfs_db's freespace cmd. > > Also fix uninit'd variable "i" from previous, similar fix > for xfs_repair. Looks good. Reviewed-by: Dave Chinner -- Dave Chinner david@fromorbit.com From wangwushizhu1234@yahoo.com Mon Mar 11 00:36:28 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: ** X-Spam-Status: No, score=2.6 required=5.0 tests=FORGED_YAHOO_RCVD, FREEMAIL_ENVFROM_END_DIGIT,FREEMAIL_FROM autolearn=no version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id D3F617CBF for ; Mon, 11 Mar 2013 00:36:28 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay3.corp.sgi.com (Postfix) with ESMTP id 62423AC005 for ; Sun, 10 Mar 2013 22:36:25 -0700 (PDT) X-ASG-Debug-ID: 1362980182-04cb6c2b013f6130001-NocioJ Received: from sam.nabble.com (sam.nabble.com [216.139.236.26]) by cuda.sgi.com with ESMTP id oyRzsDr34YV013rv (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO) for ; Sun, 10 Mar 2013 22:36:22 -0700 (PDT) X-Barracuda-Envelope-From: wangwushizhu1234@yahoo.com X-Barracuda-Apparent-Source-IP: 216.139.236.26 Received: from tom.nabble.com ([192.168.236.105]) by sam.nabble.com with esmtp (Exim 4.72) (envelope-from ) id 1UEvPK-0000S6-1I for xfs@oss.sgi.com; Sun, 10 Mar 2013 22:36:22 -0700 Date: Sun, 10 Mar 2013 22:36:22 -0700 (PDT) From: panpan2523 To: xfs@oss.sgi.com Message-ID: <1362980181921-34995.post@n7.nabble.com> In-Reply-To: References: Subject: Re: Concours MIME-Version: 1.0 X-ASG-Orig-Subj: Re: Concours Content-Type: text/plain; charset=us-ascii Content-Transfer-Encoding: 7bit X-Barracuda-Connect: sam.nabble.com[216.139.236.26] X-Barracuda-Start-Time: 1362980182 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 1.41 X-Barracuda-Spam-Status: No, SCORE=1.41 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=FORGED_YAHOO_RCVD, FORGED_YAHOO_RCVD_2 X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124864 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 FORGED_YAHOO_RCVD 'From' yahoo.com does not match 'Received' headers 1.41 FORGED_YAHOO_RCVD_2 'From' yahoo.com does not match 'Received' headers In the second, you can definitely find the ideal pair of shoes according to your preference and taste from the huge collection of shoes available from Ash. Visit have global appeal and are acknowledged by various well-known fashion industry publications. The brand, however, continues to create its excellent designs that impress a large number of fashion conscious people.

So you can select anyone that you prefer. Consider the height in the wedge when you are trying to select the proper size. In our society you will find lots of individuals who spend nearly all their own time seated, christian louboutin black nappa mamanouk ankle boots and often this indicates seated inside a single chair. Significantly much more information about delicate and fashion ASH is on our online store , you are able to possess an attempt and not shed such an opportunity.

This logo has already established a global presence. Ash has attracted worldwide customers with boots and shoes that are fabulous in design and made with top quality craftsmanship and materials. prada bags discounted >From the Ash headquarters in Northern Italy, their shoes and boots have spread to European centres and have gained a foothold in the markets of USA. Customers realise now that the Ash boots and Ash shoes that they wear are an amalgam of fashion, comfort, style and durability.
-- View this message in context: http://xfs.9218.n7.nabble.com/Concours-tp25692p34995.html Sent from the Xfs - General mailing list archive at Nabble.com. From jeff.liu@oracle.com Mon Mar 11 01:31:22 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id CE31D7F37 for ; Mon, 11 Mar 2013 01:31:22 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay2.corp.sgi.com (Postfix) with ESMTP id 9C367304039 for ; Sun, 10 Mar 2013 23:31:19 -0700 (PDT) X-ASG-Debug-ID: 1362983478-04bdf02296417090001-NocioJ Received: from aserp1040.oracle.com (aserp1040.oracle.com [141.146.126.69]) by cuda.sgi.com with ESMTP id IGM0lXT3A7DXU2Xy (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO) for ; Sun, 10 Mar 2013 23:31:18 -0700 (PDT) X-Barracuda-Envelope-From: jeff.liu@oracle.com X-Barracuda-Apparent-Source-IP: 141.146.126.69 Received: from acsinet22.oracle.com (acsinet22.oracle.com [141.146.126.238]) by aserp1040.oracle.com (Sentrion-MTA-4.3.1/Sentrion-MTA-4.3.1) with ESMTP id r2B6VH6L010292 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=OK); Mon, 11 Mar 2013 06:31:17 GMT Received: from acsmt357.oracle.com (acsmt357.oracle.com [141.146.40.157]) by acsinet22.oracle.com (8.14.4+Sun/8.14.4) with ESMTP id r2B6VGXQ015702 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=NO); Mon, 11 Mar 2013 06:31:16 GMT Received: from abhmt109.oracle.com (abhmt109.oracle.com [141.146.116.61]) by acsmt357.oracle.com (8.12.11.20060308/8.12.11) with ESMTP id r2B6VGc8017370; Mon, 11 Mar 2013 01:31:16 -0500 Received: from [192.168.1.103] (/114.248.193.130) by default (Oracle Beehive Gateway v4.0) with ESMTP ; Sun, 10 Mar 2013 23:31:16 -0700 Message-ID: <513D7A26.3030401@oracle.com> Date: Mon, 11 Mar 2013 14:31:02 +0800 From: Jeff Liu User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:16.0) Gecko/20121028 Thunderbird/16.0.2 MIME-Version: 1.0 To: "xfs@oss.sgi.com" CC: dchinner@redhat.com Subject: [PATCH] xfs: Remove obsoleted m_inode_shrink from xfs_mount structure Content-Type: text/plain; charset=ISO-8859-1 X-ASG-Orig-Subj: [PATCH] xfs: Remove obsoleted m_inode_shrink from xfs_mount structure Content-Transfer-Encoding: 7bit X-Source-IP: acsinet22.oracle.com [141.146.126.238] X-Barracuda-Connect: aserp1040.oracle.com[141.146.126.69] X-Barracuda-Start-Time: 1362983478 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124868 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- Looks the old m_inode_shrink is obsoleted as we perform inodes reclaim per AG via m_reclaim_workqueue, this patch remove it from the xfs_mount structure if so. Signed-off-by: Jie Liu Cc: Dave Chinner --- fs/xfs/xfs_mount.h | 1 - 1 file changed, 1 deletion(-) diff --git a/fs/xfs/xfs_mount.h b/fs/xfs/xfs_mount.h index bc90706..687c171 100644 --- a/fs/xfs/xfs_mount.h +++ b/fs/xfs/xfs_mount.h @@ -207,7 +207,6 @@ typedef struct xfs_mount { trimming */ __int64_t m_update_flags; /* sb flags we need to update on the next remount,rw */ - struct shrinker m_inode_shrink; /* inode reclaim shrinker */ int64_t m_low_space[XFS_LOWSP_MAX]; /* low free space thresholds */ -- 1.7.9.5 From jferrero06@gmail.com Mon Mar 11 04:25:19 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.3 required=5.0 tests=FREEMAIL_ENVFROM_END_DIGIT, FREEMAIL_FROM,T_DKIM_INVALID autolearn=no version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 1DEF57F37 for ; Mon, 11 Mar 2013 04:25:19 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay2.corp.sgi.com (Postfix) with ESMTP id 0C224304032 for ; Mon, 11 Mar 2013 02:25:15 -0700 (PDT) X-ASG-Debug-ID: 1362993914-04cb6c2b02407c90001-NocioJ Received: from mail-bk0-f43.google.com (mail-bk0-f43.google.com [209.85.214.43]) by cuda.sgi.com with ESMTP id zX1txrAJ4ImizsyI (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Mon, 11 Mar 2013 02:25:15 -0700 (PDT) X-Barracuda-Envelope-From: jferrero06@gmail.com X-Barracuda-Apparent-Source-IP: 209.85.214.43 X-Barracuda-IPDD: Level1 [gmail.com/209.85.214.43] Received: by mail-bk0-f43.google.com with SMTP id jm19so1557409bkc.2 for ; Mon, 11 Mar 2013 02:25:13 -0700 (PDT) X-Barracuda-IPDD: Level1 [gmail.com/209.85.214.43] X-Barracuda-IPDD: Level1 [gmail.com/209.85.214.43] DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20120113; h=mime-version:x-received:in-reply-to:references:date:message-id :subject:from:to:cc:content-type; bh=UwRG4UhdAuwVIB4HAsa+vsifzmDz0VJiSDNXgZGAM0I=; b=sQLhkzfueKn9ZHzlBGd8SV8kdA+Nr1EKWvS4blkatFNAEJYbERJXSmwCrbL154Kwb5 Z38MY25JWtQfVZdiFBfKqb6I/RlsgryaBWRoncin0+96UqWsDinpaZnjOVZ0JcwlOT/6 SKyfnVnxory2n3d1rTCEztRx0cfRPXuMJcNhAKzm9CHtmV5UGab0qnwlMHoD8M2QYqhf 3erftsXqB4oBsBhQ1REhxHzFtGd4xzownJTv+O9mqSyyurVPff8CVpVJsLXXXnJ+5ZND HfTPx5iTIBLQRhKs9hfuG++ODeBOKvGZEma6IF55IUMhJDXiR4Td0mNhdPAPGbt3APKz JPpg== MIME-Version: 1.0 X-Received: by 10.205.17.197 with SMTP id qd5mr4205870bkb.125.1362993913724; Mon, 11 Mar 2013 02:25:13 -0700 (PDT) Received: by 10.204.228.133 with HTTP; Mon, 11 Mar 2013 02:25:13 -0700 (PDT) In-Reply-To: <513D1D51.7010905@hardwarefreak.com> References: <20130306161519.2c28d911@galadriel.home> <20130306232100.6286f640@galadriel.home> <5137CD46.6070909@redhat.com> <5139A3B6.3040805@hardwarefreak.com> <5139D792.4090304@redhat.com> <513A350A.508@hardwarefreak.com> <20130309091152.GH23616@dastard> <513B84AD.2000603@hardwarefreak.com> <20130310224536.GK23616@dastard> <513D1D51.7010905@hardwarefreak.com> Date: Mon, 11 Mar 2013 10:25:13 +0100 Message-ID: Subject: Re: XFS filesystem corruption From: Julien FERRERO X-ASG-Orig-Subj: Re: XFS filesystem corruption To: stan@hardwarefreak.com Cc: Dave Chinner , Ric Wheeler , xfs@oss.sgi.com Content-Type: text/plain; charset=ISO-8859-1 X-Barracuda-Connect: mail-bk0-f43.google.com[209.85.214.43] X-Barracuda-Start-Time: 1362993914 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_MISMATCH_TO, DKIM_SIGNED, DKIM_VERIFIED X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124880 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 BSF_SC0_MISMATCH_TO Envelope rcpt doesn't match header -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature > > Ok, see, this is odd part here. The OP didn't seem to have this > metadata corruption issue with the old 2.6.18 kernel, at least I think > that's the one he mentioned. Then he switched to 2.6.35. IIRC there > were a number of commits around that time and some regressions. I also > recall 2.6.35 is not a long term stable kernel. I'd guess there were > reasons for that. So, I'm wondering if there was a bug/regression > relating to XFS metadata in 2.6.35 corrected in .36 or later and simply > not backported. Seems to ring a bell, vaguely. I have no idea > where/how to search for such information. > That is the main reason I asked. I google for regression / issue with XFS in 2.6.35 but I didn't find anything. My hope was that someone from this mailing list would remember it (if such a regression did exist of course). From stan@hardwarefreak.com Mon Mar 11 04:29:49 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 8D06A7F3F for ; Mon, 11 Mar 2013 04:29:49 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay1.corp.sgi.com (Postfix) with ESMTP id 7B2C28F8049 for ; Mon, 11 Mar 2013 02:29:49 -0700 (PDT) X-ASG-Debug-ID: 1362994185-04cb6c2b034080d0001-NocioJ Received: from greer.hardwarefreak.com (mo-65-41-216-221.sta.embarqhsd.net [65.41.216.221]) by cuda.sgi.com with ESMTP id hOsbt94zxc7ZWrg8 for ; Mon, 11 Mar 2013 02:29:45 -0700 (PDT) X-Barracuda-Envelope-From: stan@hardwarefreak.com X-Barracuda-Apparent-Source-IP: 65.41.216.221 X-Barracuda-User-Whitelist: xfs@oss.sgi.com Received: from [192.168.100.53] (gffx.hardwarefreak.com [192.168.100.53]) by greer.hardwarefreak.com (Postfix) with ESMTP id 6D53F6C162; Mon, 11 Mar 2013 04:29:45 -0500 (CDT) Message-ID: <513DA40B.6050903@hardwarefreak.com> Date: Mon, 11 Mar 2013 04:29:47 -0500 From: Stan Hoeppner Reply-To: stan@hardwarefreak.com User-Agent: Mozilla/5.0 (Windows NT 5.1; rv:17.0) Gecko/20130215 Thunderbird/17.0.3 MIME-Version: 1.0 To: Dave Chinner CC: Ric Wheeler , Julien FERRERO , xfs@oss.sgi.com Subject: Re: XFS filesystem corruption References: <20130306232100.6286f640@galadriel.home> <5137CD46.6070909@redhat.com> <5139A3B6.3040805@hardwarefreak.com> <5139D792.4090304@redhat.com> <513A350A.508@hardwarefreak.com> <20130309091152.GH23616@dastard> <513B84AD.2000603@hardwarefreak.com> <20130310224536.GK23616@dastard> <513D1D51.7010905@hardwarefreak.com> <20130311005024.GC20565@dastard> X-ASG-Orig-Subj: Re: XFS filesystem corruption In-Reply-To: <20130311005024.GC20565@dastard> Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: mo-65-41-216-221.sta.embarqhsd.net[65.41.216.221] X-Barracuda-Start-Time: 1362994185 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 On 3/10/2013 7:50 PM, Dave Chinner wrote: > On Sun, Mar 10, 2013 at 06:54:57PM -0500, Stan Hoeppner wrote: >> On 3/10/2013 5:45 PM, Dave Chinner wrote: >>>> Does everyone remember the transitive property of equality from math >>>> class decades ago? It states "If A=B and B=C then A=C". Thus if >>>> barrier writes to the journal protect the journal, and the journal >>>> protects metadata, then barrier writes to the journal protect metadata. >>> >>> Yup, but the devil is in the detail - we don't protect individual >>> metadata writes at all and that difference is significant enough to >>> comment on.... :P >> >> Elaborate on this a bit, if you have time. I was under the impression >> that all directory updates were journaled first. > > That's correct - they are all journalled. > > But journalling is done at the transactional level, not that of > individual metadata changes. IOWs, journalled changes do not > contain the same information as a metadata buffer write - they > contain both more and less information than a metadata buffer write. > > They contain more information in that there is change atomicity > information in the journal information for recovery purposes. i.e. > how the individual change relates to changes in other related > metadata objects. This information is needed in the journal so that > log recovery knows to either apply all the changes in a checkpoint > or none of them if this journal checkpoint (or a previous one) is > incomplete. > > They contain less information in that the changes to a metadata > object is stored as a diff in the journal rather than as a complete > copy of the object. This is done to reduce the amount of journal > space and memory required to track and store all of the changes in > the checkpoint. Forget the power loss issue for a moment. If I'm digesting this correctly, it's seems quite an accomplishment that you got delaylog working, at all, let alone extremely well as it does. Given what you state above, it would seem there is quite a bit of complexity involved in tracking these metadata change relationships and modifying the checkpoint information accordingly. I would think as you merge multiple traditional XFS log writes into a single write that the relationship information would also need to be modified as well. Or do I lack sufficient understanding at this point to digest this? > Hence what is written to the journal is quite different to what is > written during metadata writeback in both contents ad method. It is > the atomicity information in the journal that we know got > synchronised to disk (via the FUA/cache flush) that enables us to > get away with being lazy writing back metadata buffers in any order > we please without needing FUA/cache flushes... This makes me wonder... for a given metadata write into an AG, is the amount of data in the corresponding journal write typically greater or less? You stated above it is both more and less but I don't know if you meant that qualitatively or quantitatively, or both. I'm wondering that if log write bytes is typically significantly lower, and we know we can recreate a lost metadata write from the journal data during a recovery.... Given that CPU is so much faster than disk, would it be plausible to do all metadata writes in a lazy fashion through the relevant sections of the recovery code, or something along these lines? Make 'recovery' the standard method for metadata writes? I'm not talking about replacing the log journal, but replacing the metadata write method with something akin to a portion of the the journal recovery routine. In other words, could we make use of the delaylog concept of doing more work with fewer IOs to achieve a similar performance gain for metadata writeback? Or is XFS metadata writeback already fully optimized WRT IOs and bandwidth, latency, etc? Or is this simply a crazy idea from a member of the peanut gallery who has just enough knowledge to be a nuisance, but lacks enough to make real contributions? Probably the latter. ;) > So, yes you are correct in that the journalling protects metadata. > However, the distinction I'm making is that the journal writes > contain different information and have different constraints > compared to individual metadata object writeback, and therefore are > not the "same thing" and do not require the same protection from > power loss/crash events... Thanks Dave for continuing to take time to teach. I've passed on much of what I've learned from you to many others outside of this list. -- Stan From stan@hardwarefreak.com Mon Mar 11 06:02:28 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 86F5F7F37 for ; Mon, 11 Mar 2013 06:02:28 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay2.corp.sgi.com (Postfix) with ESMTP id 71539304039 for ; Mon, 11 Mar 2013 04:02:25 -0700 (PDT) X-ASG-Debug-ID: 1362999744-04cb6c2b0140e590001-NocioJ Received: from greer.hardwarefreak.com (mo-65-41-216-221.sta.embarqhsd.net [65.41.216.221]) by cuda.sgi.com with ESMTP id qMEKLuWDH9g1wfLV for ; Mon, 11 Mar 2013 04:02:24 -0700 (PDT) X-Barracuda-Envelope-From: stan@hardwarefreak.com X-Barracuda-Apparent-Source-IP: 65.41.216.221 X-Barracuda-User-Whitelist: xfs@oss.sgi.com Received: from [192.168.100.53] (gffx.hardwarefreak.com [192.168.100.53]) by greer.hardwarefreak.com (Postfix) with ESMTP id 51CCD6C11C; Mon, 11 Mar 2013 06:02:24 -0500 (CDT) Message-ID: <513DB9C2.3050408@hardwarefreak.com> Date: Mon, 11 Mar 2013 06:02:26 -0500 From: Stan Hoeppner Reply-To: stan@hardwarefreak.com User-Agent: Mozilla/5.0 (Windows NT 5.1; rv:17.0) Gecko/20130215 Thunderbird/17.0.3 MIME-Version: 1.0 To: stan@hardwarefreak.com CC: Eric Sandeen , xfs@oss.sgi.com, Pascal Subject: Re: Maximum file system size of XFS? References: <20130309215121.0e614ef8@thinky> <513BB7C3.4050009@redhat.com> <20130309233940.3b7c0910@thinky> <513BDD6E.7010507@sandeen.net> <513C3C43.7080104@hardwarefreak.com> X-ASG-Orig-Subj: Re: Maximum file system size of XFS? In-Reply-To: <513C3C43.7080104@hardwarefreak.com> Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: mo-65-41-216-221.sta.embarqhsd.net[65.41.216.221] X-Barracuda-Start-Time: 1362999744 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 On 3/10/2013 1:54 AM, Stan Hoeppner wrote: > So in summary, an Exabyte scale XFS is simply not practical today, and > won't be for at least another couple of decades, or more, if ever. The > same holds true for some of the other filesystems you're going to be > writing about. Some of the cluster and/or distributed filesystems > you're looking at could probably scale to Exabytes today. That is, if > someone had the budget for half a million hard drives, host systems, > switches, etc, the facilities to house it all, and the budget for power > and cooling. That's 834 racks for drives alone, just under 1/3rd of a > mile long if installed in a single row. Jet lag due to time travel caused a math error above. With today's 4TB drives it would require 2.25 million units for a raw 9EB capacity. That's 3,750 racks of 600 drives each. These would stretch 1.42 miles, 7500 ft. -- Stan From rjohnston@sgi.com Mon Mar 11 07:16:41 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 085917F3F for ; Mon, 11 Mar 2013 07:16:41 -0500 (CDT) Received: from xmail.sgi.com (pv-excas3-dc21.corp.sgi.com [137.38.102.206]) by relay3.corp.sgi.com (Postfix) with ESMTP id 44D7CAC002; Mon, 11 Mar 2013 05:16:37 -0700 (PDT) Received: from [128.162.233.55] (128.162.233.55) by xmail.sgi.com (137.38.102.30) with Microsoft SMTP Server (TLS) id 14.2.318.1; Mon, 11 Mar 2013 07:16:16 -0500 Message-ID: <513DCB25.6000701@sgi.com> Date: Mon, 11 Mar 2013 07:16:37 -0500 From: Rich Johnston User-Agent: Mozilla/5.0 (X11; Linux i686; rv:13.0) Gecko/20120615 Thunderbird/13.0.1 MIME-Version: 1.0 To: Eric Sandeen CC: xfs-oss Subject: Re: [PATCH] xfsprogs: skip freelist scans of corrupt agf References: <513B5393.4000203@sandeen.net> In-Reply-To: <513B5393.4000203@sandeen.net> Content-Type: text/plain; charset="ISO-8859-1"; format=flowed Content-Transfer-Encoding: 7bit X-Originating-IP: [128.162.233.55] This has been commited. Thanks --Rich commit a529cc7f0e5bd1632e5169d015c54e3a6122ee0f Author: Eric Sandeen Date: Sat Mar 9 15:21:55 2013 +0000 xfsprogs: skip freelist scans of corrupt agf If an agf has bad values in the freelist, this can wreak havoc if, for example, first > last and the loop never exits; we index agfl->agfl_bno[i] off into the weeds. If they're off, warn about it and skip the scan. This is done both in xfs_check and xfs_db's freespace cmd. Also fix uninit'd variable "i" from previous, similar fix for xfs_repair. Signed-off-by: Eric Sandeen Reviewed-by: Dave Chinner Signed-off-by: Rich Johnston From rjohnston@sgi.com Mon Mar 11 07:20:19 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 196397F3F for ; Mon, 11 Mar 2013 07:20:19 -0500 (CDT) Received: from xmail.sgi.com (pv-excas3-dc21-nlb.corp.sgi.com [137.38.102.207]) by relay2.corp.sgi.com (Postfix) with ESMTP id DC4A8304048; Mon, 11 Mar 2013 05:20:15 -0700 (PDT) Received: from [128.162.233.55] (128.162.233.55) by xmail.sgi.com (137.38.102.30) with Microsoft SMTP Server (TLS) id 14.2.318.1; Mon, 11 Mar 2013 07:20:15 -0500 Message-ID: <513DCC13.6050800@sgi.com> Date: Mon, 11 Mar 2013 07:20:35 -0500 From: Rich Johnston User-Agent: Mozilla/5.0 (X11; Linux i686; rv:13.0) Gecko/20120615 Thunderbird/13.0.1 MIME-Version: 1.0 To: Dave Chinner CC: Eric Sandeen , Ole Tange , xfs-oss Subject: Re: [PATCH V2] xfs_repair: skip freelist scan of corrupt agf in no-modify mode References: <51313DE8.5080104@sandeen.net> <51326DC0.8030403@sandeen.net> <513A4A9B.3050802@sgi.com> <20130309090041.GG23616@dastard> In-Reply-To: <20130309090041.GG23616@dastard> Content-Type: text/plain; charset="ISO-8859-1"; format=flowed Content-Transfer-Encoding: 7bit X-Originating-IP: [128.162.233.55] On 03/09/2013 03:00 AM, Dave Chinner wrote: > On Fri, Mar 08, 2013 at 02:31:23PM -0600, Rich Johnston wrote: >> This version looks good. ;) >> >> Reviewed-by: Rich Johnston >> >> This has been committed. > > Except that all review comments have not been addressed. i.e there > are two places that have the same bug and they haven't been fixed. > > It's great that you want to commit quickly, but commits should not > happen while there are unaddressed issues still outstanding.... Sorry Dave I misunderstood your comments. I took them to mean you were going to make those changes with your CRC patch. I will make sure to clarify before committing. > > Cheers, > > Dave. > From rjohnston@sgi.com Mon Mar 11 08:19:24 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id F3F1B7F37 for ; Mon, 11 Mar 2013 08:19:23 -0500 (CDT) Received: from xmail.sgi.com (pv-excas3-dc21-nlb.corp.sgi.com [137.38.102.207]) by relay1.corp.sgi.com (Postfix) with ESMTP id D685E8F8052; Mon, 11 Mar 2013 06:19:20 -0700 (PDT) Received: from [128.162.233.55] (128.162.233.55) by xmail.sgi.com (137.38.102.30) with Microsoft SMTP Server (TLS) id 14.2.318.1; Mon, 11 Mar 2013 08:19:20 -0500 Message-ID: <513DD9EC.5080303@sgi.com> Date: Mon, 11 Mar 2013 08:19:40 -0500 From: Rich Johnston User-Agent: Mozilla/5.0 (X11; Linux i686; rv:13.0) Gecko/20120615 Thunderbird/13.0.1 MIME-Version: 1.0 To: Jeff Moyer CC: Subject: Re: xfstests, aio-dio-extend-stat.c: fix error reporting References: In-Reply-To: Content-Type: text/plain; charset="ISO-8859-1"; format=flowed Content-Transfer-Encoding: 7bit X-Originating-IP: [128.162.233.55] Jeff thanks for submitting this patch. Looks good. Reviewed-by: Rich Johnston This has been committed. --Rich commit 06166c2dbaedce9db77b9c6325e21ddf760a7623 Author: Jeff Moyer Date: Fri Jan 18 22:01:57 2013 +0000 xfstests, aio-dio-extend-stat.c: fix error reporting If we receive an unexpected result from an async write, the error reporting does not tell the actual number of bytes written. Fix that, and also a couple of typos in printf's. From tinguely@sgi.com Mon Mar 11 10:00:48 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 212AA7F37 for ; Mon, 11 Mar 2013 10:00:48 -0500 (CDT) Received: from eagdhcp-232-136.americas.sgi.com (eagdhcp-232-136.americas.sgi.com [128.162.232.136]) by relay2.corp.sgi.com (Postfix) with ESMTP id D6DD7304059; Mon, 11 Mar 2013 08:00:44 -0700 (PDT) Message-ID: <513DE38D.9000901@sgi.com> Date: Mon, 11 Mar 2013 09:00:45 -0500 From: Mark Tinguely User-Agent: Mozilla/5.0 (X11; FreeBSD amd64; rv:9.0) Gecko/20120122 Thunderbird/9.0 MIME-Version: 1.0 To: Dave Chinner CC: xfs@oss.sgi.com Subject: Re: [PATCH] xfs: ensure we capture IO errors correctly References: <1362708074-14987-1-git-send-email-david@fromorbit.com> In-Reply-To: <1362708074-14987-1-git-send-email-david@fromorbit.com> Content-Type: text/plain; charset=ISO-8859-1; format=flowed Content-Transfer-Encoding: 7bit On 03/07/13 20:01, Dave Chinner wrote: > From: Dave Chinner > > Failed buffer readahead can leave the buffer in the cache marked > with an error. Most callers that then issue a subsequent read on the > buffer do not zero the b_error field out, and so we may incorectly > detect an error during IO completion due to the stale error value > left on the buffer. > > Avoid this problem by zeroing the error before IO submission. This > ensures that the only IO errors that are detected those captured > from are those captured from bio submission or completion. > > Signed-off-by: Dave Chinner > --- Looks good. Reviewed-by: Mark Tinguely From hpj@urpla.net Mon Mar 11 11:15:38 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 09C147F37 for ; Mon, 11 Mar 2013 11:15:38 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay2.corp.sgi.com (Postfix) with ESMTP id EB41B30406B for ; Mon, 11 Mar 2013 09:15:34 -0700 (PDT) X-ASG-Debug-ID: 1363018529-04cb6c2b04429ee0001-NocioJ Received: from moutng.kundenserver.de (moutng.kundenserver.de [212.227.126.171]) by cuda.sgi.com with ESMTP id 6sP15nateqCB4iv8 (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Mon, 11 Mar 2013 09:15:30 -0700 (PDT) X-Barracuda-Envelope-From: hpj@urpla.net X-Barracuda-Apparent-Source-IP: 212.227.126.171 Received: from lisa (p5B2A4CCE.dip0.t-ipconnect.de [91.42.76.206]) by mrelayeu.kundenserver.de (node=mreu2) with ESMTP (Nemesis) id 0M21V9-1V3cVA0XU3-00tPpZ; Mon, 11 Mar 2013 17:15:19 +0100 Received: from localhost (localhost [127.0.0.1]) by tyrex.lisa.loc (Postfix) with ESMTP id 9DAFE1B971B00; Mon, 11 Mar 2013 17:15:18 +0100 (CET) X-Virus-Scanned: amavisd-new at lisa.loc Received: from tyrex.lisa.loc ([127.0.0.1]) by localhost (tyrex.lisa.loc [127.0.0.1]) (amavisd-new, port 10024) with LMTP id jlr71l8Rdu1a; Mon, 11 Mar 2013 17:15:10 +0100 (CET) From: Hans-Peter Jansen To: xfs@oss.sgi.com, stan@hardwarefreak.com Cc: Pascal , Eric Sandeen Subject: Re: Maximum file system size of XFS? Date: Mon, 11 Mar 2013 17:15:08 +0100 X-ASG-Orig-Subj: Re: Maximum file system size of XFS? Message-ID: <4238234.1XBMaocpAb@xrated> User-Agent: KMail/4.9.5 (Linux/3.4.28-2.20-desktop; KDE/4.9.5; x86_64; ; ) In-Reply-To: <513DB9C2.3050408@hardwarefreak.com> References: <20130309215121.0e614ef8@thinky> <513C3C43.7080104@hardwarefreak.com> <513DB9C2.3050408@hardwarefreak.com> MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable Content-Type: text/plain; charset="iso-8859-1" X-Provags-ID: V02:K0:JohVJVRMdxxn9yDhB3419B6bb2piFtLzY6ivoup4oXr rRPi4jsdx3AUMNGRln1eH1UIuKzb/wl8lywtqVLxHr4LexxLoF xK2DNRQs2+H4DuljLXsZCbLw8gNkOE/GZEO/QU2GW0zPkJFb+9 JuOvg0Jc+nqgksNTP2jAmtzFej686azeF6gN6E3i7r2AVEmjot oIgBT9MAfEGEP0qK3bZwj2wdOClT/GSvB1Uvitv7cD5sZnwvbl o/bOCcpy+XcOko5RiEr1xqZFWrTocAHtilBZkZp0KtfZaJFhze AxX/Vx+XtfU0iEZxQyWyglQTPDB1/UenCR2NVtLWadBS/nc2g= = X-Barracuda-Connect: moutng.kundenserver.de[212.227.126.171] X-Barracuda-Start-Time: 1363018530 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124906 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- Am Montag, 11. M=E4rz 2013, 06:02:26 schrieb Stan Hoeppner: > On 3/10/2013 1:54 AM, Stan Hoeppner wrote: > > So in summary, an Exabyte scale XFS is simply not practical today, = and > > won't be for at least another couple of decades, or more, if ever. = The > > same holds true for some of the other filesystems you're going to b= e > > writing about. Some of the cluster and/or distributed filesystems > > you're looking at could probably scale to Exabytes today. That is,= if > > someone had the budget for half a million hard drives, host systems= , > > switches, etc, the facilities to house it all, and the budget for p= ower > > and cooling. That's 834 racks for drives alone, just under 1/3rd o= f a > > mile long if installed in a single row. >=20 > Jet lag due to time travel caused a math error above. With today's 4= TB > drives it would require 2.25 million units for a raw 9EB capacity. > That's 3,750 racks of 600 drives each. These would stretch 1.42 mile= s, > 7500 ft. And I just acknowledged the building plans for our new datacenter, base= d on=20 your former calculations. The question is, who carries the costs of the= now=20 needed 4 other floors of that building..=20 Are you well-insured, Stan? Cheers, Pete From eflorac@intellique.com Mon Mar 11 11:22:24 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id DFAF27F37 for ; Mon, 11 Mar 2013 11:22:24 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay2.corp.sgi.com (Postfix) with ESMTP id B8A40304064 for ; Mon, 11 Mar 2013 09:22:24 -0700 (PDT) X-ASG-Debug-ID: 1363018941-04cb6c2b0142b0a0001-NocioJ Received: from smtp4-g21.free.fr (smtp4-g21.free.fr [212.27.42.4]) by cuda.sgi.com with ESMTP id sn2GFGBzRLEBKyeF for ; Mon, 11 Mar 2013 09:22:22 -0700 (PDT) X-Barracuda-Envelope-From: eflorac@intellique.com X-Barracuda-Apparent-Source-IP: 212.27.42.4 Received: from harpe.intellique.com (unknown [82.225.196.72]) by smtp4-g21.free.fr (Postfix) with ESMTP id B11B94C8224; Mon, 11 Mar 2013 17:22:16 +0100 (CET) Date: Mon, 11 Mar 2013 17:22:18 +0100 From: Emmanuel Florac To: Hans-Peter Jansen Cc: xfs@oss.sgi.com, stan@hardwarefreak.com, Eric Sandeen , Pascal Subject: Re: Maximum file system size of XFS? Message-ID: <20130311172218.3a3b600b@harpe.intellique.com> X-ASG-Orig-Subj: Re: Maximum file system size of XFS? In-Reply-To: <4238234.1XBMaocpAb@xrated> References: <20130309215121.0e614ef8@thinky> <513C3C43.7080104@hardwarefreak.com> <513DB9C2.3050408@hardwarefreak.com> <4238234.1XBMaocpAb@xrated> Organization: Intellique X-Mailer: Claws Mail 3.9.0 (GTK+ 2.24.10; i486-slackware-linux-gnu) Mime-Version: 1.0 Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: quoted-printable X-Barracuda-Connect: smtp4-g21.free.fr[212.27.42.4] X-Barracuda-Start-Time: 1363018941 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124908 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- Le Mon, 11 Mar 2013 17:15:08 +0100 Hans-Peter Jansen =E9crivait: > And I just acknowledged the building plans for our new datacenter, > based on your former calculations. Don't be afraid, there are 80 drives 4U chassis available, and 5TB drives are around the corner. That's 800 drives and a raw capacity of 4 PB per 42U rack. --=20 ------------------------------------------------------------------------ Emmanuel Florac | Direction technique | Intellique | | +33 1 78 94 84 02 ------------------------------------------------------------------------ From relatsdeficcio@telefonica.net Mon Mar 11 11:33:45 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=FREEMAIL_FROM, HTML_FONT_SIZE_HUGE,HTML_MESSAGE autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 69D487F3F for ; Mon, 11 Mar 2013 11:33:45 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay3.corp.sgi.com (Postfix) with ESMTP id E450CAC005 for ; Mon, 11 Mar 2013 09:33:41 -0700 (PDT) X-ASG-Debug-ID: 1363019616-04cb6c2b0442c690001-NocioJ Received: from telefonica.net (impaqm1.telefonica.net [213.4.138.17]) by cuda.sgi.com with ESMTP id 6cLHvuWg6QZTceko for ; Mon, 11 Mar 2013 09:33:37 -0700 (PDT) X-Barracuda-Envelope-From: relatsdeficcio@telefonica.net X-Barracuda-Apparent-Source-IP: 213.4.138.17 Received: from IMPmailhost2.adm.correo ([10.20.102.39]) by IMPaqm1.telefonica.net with bizsmtp id A7TN1l00o0r0BT63MGZcc3; Mon, 11 Mar 2013 17:33:36 +0100 Received: from FIX ([83.33.95.83]) by IMPmailhost2.adm.correo with BIZ IMP id AGZY1l00V1nvfpf1iGZYbv; Mon, 11 Mar 2013 17:33:36 +0100 X-CMAE-Analysis: v=1.1 cv=+rCLaL1cwipid4BSNuJMvapUMluAq4Fj6WizCAFN7xA= c=1 sm=1 a=BHJCkJAZKfQA:10 a=VY-2JVJxNB4A:10 a=jPJDawAOAc8A:10 a=8nJEP1OIZ-IA:10 a=srCUf73/RkSr9Rjcrh0uHw==:17 a=Rs18TvwyITVLWpBW4FkA:9 a=wPNLvfGTeEIA:10 a=FhPdoIInAAAA:8 a=Fw5ZCecaTCjffAo7-wEA:9 a=_W_S_7VecoQA:10 a=X2T6blWgQvQA:10 a=6ZNAxG575vDUnHsB:21 a=srCUf73/RkSr9Rjcrh0uHw==:117 X-original-sender: relatsdeficcio@telefonica.net From: "La Lluna en un Cove" Subject: =?iso-8859-1?B?UHJvY+lzIGRlIHNlbGVjY2nzIE9CRVJU?= To: "xfs" X-ASG-Orig-Subj: =?iso-8859-1?B?UHJvY+lzIGRlIHNlbGVjY2nzIE9CRVJU?= Content-Type: multipart/alternative; charset="iso-8859-1"; boundary="NHy2aqLDllybg=_4OVXEIFt3FGbQvIkfvc" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit Organization: LLEUC Date: Mon, 11 Mar 2013 17:33:35 +0100 X-Confirm-Reading-To: relatsdeficcio@telefonica.net Return-Receipt-To: relatsdeficcio@telefonica.net Disposition-Notification-To: relatsdeficcio@telefonica.net X-Barracuda-Connect: impaqm1.telefonica.net[213.4.138.17] X-Barracuda-Start-Time: 1363019617 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 1.53 X-Barracuda-Spam-Status: No, SCORE=1.53 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_MV0224, BSF_SC0_SA074, HTML_FONT_SIZE_HUGE, HTML_MESSAGE, MISSING_MID X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124908 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.14 MISSING_MID Missing Message-Id: header 0.50 BSF_SC0_SA074 URI: Custom Rule SA074 0.39 HTML_FONT_SIZE_HUGE BODY: HTML font size is huge 0.00 HTML_MESSAGE BODY: HTML included in message 0.50 BSF_SC0_MV0224 FULL: Custom rule MV0224 Message-Id: <20130311163341.2092F129611D@cuda.sgi.com> This is a multi-part message in MIME format --NHy2aqLDllybg=_4OVXEIFt3FGbQvIkfvc Content-Type: text/plain ; charset="iso-8859-1" Content-Transfer-Encoding: quoted-printable "La Lluna en un Cove =B7 Revista de Relats en Catal=E0" convoca un nou proc=E9s de selecci=F3 Visita la web oficial de "La Lluna en un Cove" i informa-te'n. Clau de cerca: la lluna en un cove revista de relats en catal=E0 Nova secci=F3: "Una imatge, un text" "La Lluna en un Cove" us proposa un interessant joc literari que inter= relaciona dues disciplines art=EDstiques: l'art visual i l'art verbal.= A partir d'una determinada obra gr=E0fica, seleccionada per la nostra= redacci=F3, els participants hauran d'escriure un relat de tem=E0tica= lliure, que estigui, aix=F2 s=ED, inspirat o basat en l'obra proposad= a. Si voleu participar, consulteu la fitxa informativa de la secci=F3 = "Una imatge, un text", on veureu l'obra gr=E0fica que us proposem. "La Lluna en un Cove =B7 Revista de Relats en Catal=E0" Si no voleu rebre m=E9s butlletins, heu de respondre aquest missatge p= osant "Baixa" en l'encap=E7alament. --NHy2aqLDllybg=_4OVXEIFt3FGbQvIkfvc Content-Type: text/html ; charset="iso-8859-1" Content-Transfer-Encoding: quoted-printable

"La Lluna en un Cove =B7 Revista de Relats en Catal=E0= "

convoca un nou proc=E9s de= selecci=F3

Visita la web oficial de "La Lluna en un Cove" i inf= orma-te'n.

 


Clau de cerca:

la lluna en un cove revista d= e relats en catal=E0


 

 

Nova secci=F3:

"Una imatge, un text"

"La Lluna en un Cove" us proposa un = interessant joc literari que interrelaciona dues disciplines art=EDsti= ques: l'art visual i l'art verbal. A partir d'una determinada obra gr=E0= fica, seleccionada per la nostra redacci=F3, els participants hauran d= 'escriure un relat de tem=E0tica lliure, que estigui, aix=F2 s=ED, ins= pirat o basat en l'obra proposada. Si voleu participar, consulteu la f= itxa informativa de la secci=F3 "Una imatge, un text", on veure= u l'obra gr=E0fica que us proposem.


 

"La Lluna en un Cove =B7 Revista de Relats en Catal=E0= "

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 


Si no voleu rebre m=E9s butlletins, h= eu de respondre aquest missatge posant "Baixa" en l'encap=E7alament.

--NHy2aqLDllybg=_4OVXEIFt3FGbQvIkfvc-- From tinguely@sgi.com Mon Mar 11 12:59:17 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id A0F187F37 for ; Mon, 11 Mar 2013 12:59:17 -0500 (CDT) Received: from eagdhcp-232-136.americas.sgi.com (eagdhcp-232-136.americas.sgi.com [128.162.232.136]) by relay2.corp.sgi.com (Postfix) with ESMTP id 4D5BA30405F; Mon, 11 Mar 2013 10:59:17 -0700 (PDT) Message-ID: <513E1B76.2090808@sgi.com> Date: Mon, 11 Mar 2013 12:59:18 -0500 From: Mark Tinguely User-Agent: Mozilla/5.0 (X11; FreeBSD amd64; rv:9.0) Gecko/20120122 Thunderbird/9.0 MIME-Version: 1.0 To: Jeff Liu CC: "xfs@oss.sgi.com" , dchinner@redhat.com Subject: Re: [PATCH] xfs: Remove obsoleted m_inode_shrink from xfs_mount structure References: <513D7A26.3030401@oracle.com> In-Reply-To: <513D7A26.3030401@oracle.com> Content-Type: text/plain; charset=ISO-8859-1; format=flowed Content-Transfer-Encoding: 7bit On 03/11/13 01:31, Jeff Liu wrote: > Looks the old m_inode_shrink is obsoleted as we perform inodes reclaim per AG via > m_reclaim_workqueue, this patch remove it from the xfs_mount structure if so. > > Signed-off-by: Jie Liu > Cc: Dave Chinner > --- > fs/xfs/xfs_mount.h | 1 - > 1 file changed, 1 deletion(-) > > diff --git a/fs/xfs/xfs_mount.h b/fs/xfs/xfs_mount.h > index bc90706..687c171 100644 > --- a/fs/xfs/xfs_mount.h > +++ b/fs/xfs/xfs_mount.h > @@ -207,7 +207,6 @@ typedef struct xfs_mount { > trimming */ > __int64_t m_update_flags; /* sb flags we need to update > on the next remount,rw */ > - struct shrinker m_inode_shrink; /* inode reclaim shrinker */ > int64_t m_low_space[XFS_LOWSP_MAX]; > /* low free space thresholds */ > Obsoleted in commit: commit 8daaa83145ef1f0a146680618328dbbd0fa76939 Author: Dave Chinner Date: Fri Jul 8 14:14:46 2011 +1000 xfs: make use of new shrinker callout for the inode cache Looks good. Reviewed-by: Mark Tinguely From Martin@lichtvoll.de Mon Mar 11 16:45:47 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 60D027F37 for ; Mon, 11 Mar 2013 16:45:47 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay1.corp.sgi.com (Postfix) with ESMTP id 4E88C8F8040 for ; Mon, 11 Mar 2013 14:45:44 -0700 (PDT) X-ASG-Debug-ID: 1363038341-04cbb07dbd443870001-NocioJ Received: from mail.lichtvoll.de (mondschein.lichtvoll.de [194.150.191.11]) by cuda.sgi.com with ESMTP id 5QanBbY79Sxs1vOW for ; Mon, 11 Mar 2013 14:45:42 -0700 (PDT) X-Barracuda-Envelope-From: Martin@lichtvoll.de X-Barracuda-Apparent-Source-IP: 194.150.191.11 Received: from merkaba.localnet (ppp-88-217-125-92.dynamic.mnet-online.de [88.217.125.92]) by mail.lichtvoll.de (Postfix) with ESMTPSA id 5AC59A9; Mon, 11 Mar 2013 22:45:23 +0100 (CET) From: Martin Steigerwald To: xfs@oss.sgi.com Subject: Re: Maximum file system size of XFS? Date: Mon, 11 Mar 2013 22:45:40 +0100 X-ASG-Orig-Subj: Re: Maximum file system size of XFS? User-Agent: KMail/1.13.7 (Linux/3.9.0-rc2-tp520; KDE/4.9.5; x86_64; ; ) Cc: Pascal References: <20130309215121.0e614ef8@thinky> (sfid-20130310_104346_965248_A63DAA41) In-Reply-To: <20130309215121.0e614ef8@thinky> MIME-Version: 1.0 Content-Type: Text/Plain; charset="iso-8859-1" Content-Transfer-Encoding: quoted-printable Message-Id: <201303112245.40522.Martin@lichtvoll.de> X-Barracuda-Connect: mondschein.lichtvoll.de[194.150.191.11] X-Barracuda-Start-Time: 1363038342 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124928 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- Am Samstag, 9. M=E4rz 2013 schrieb Pascal: > Hello, Hi Pascal, > I am asking you because I am insecure about the correct answer and > different sources give me different numbers. >=20 >=20 > My question is: What is the maximum file system size of XFS? >=20 > The official page says: 2^63 =3D 9 x 10^18 =3D 9 exabytes > Source: http://oss.sgi.com/projects/xfs/ >=20 > Wikipedia says 16 exabytes. > Source: https://en.wikipedia.org/wiki/XFS >=20 > Another reference books says 8 exabytes (2^63). >=20 >=20 > Can anyone tell me and explain what is the maximum file system size for > XFS? You can test it. The theoretical limit. Whether such a filesystem will work= =20 nicely with a real workload is, as pointed out, a different question. 1) Use a big enough XFS filesystem (yes, it has to be XFS for anything else= =20 that can carry a exabyte big sparse file) merkaba:~> LANG=3DC mkfs.xfs -L justcrazy /dev/merkaba/zeit meta-data=3D/dev/merkaba/zeit isize=3D256 agcount=3D4, agsize=3D131= 0720 blks =3D sectsz=3D512 attr=3D2, projid32bit=3D0 data =3D bsize=3D4096 blocks=3D5242880, imaxpct= =3D25 =3D sunit=3D0 swidth=3D0 blks naming =3Dversion 2 bsize=3D4096 ascii-ci=3D0 log =3Dinternal log bsize=3D4096 blocks=3D2560, version=3D2 =3D sectsz=3D512 sunit=3D0 blks, lazy-coun= t=3D1 realtime =3Dnone extsz=3D4096 blocks=3D0, rtextents=3D0 2) Create a insanely big sparse file merkaba:~> truncate -s1E /mnt/zeit/evenmorecrazy.img merkaba:~> ls -lh /mnt/zeit/evenmorecrazy.img =2Drw-r--r-- 1 root root 1,0E M=E4r 11 22:37 /mnt/zeit/evenmorecrazy.img (No, this won=B4t work with Ext4.) 3) Make a XFS file system into it: merkaba:~> mkfs.xfs -L /mnt/zeit/evenmorecrazy.img I won=B4t today. I tried that for gag during a linux performance and analys= is=20 training I held on a ThinkPad T520 with Sandybridge i5 2,50 GhZ, Intel SSD= =20 320 on an about 20 GiB XFS filesystem. The mkfs command run for something like one or two hours. It was using quit= e=20 some CPU and quite some SSD, but did not max out one of it. The host XFS filesystem was almost full, so the image took just about those= =20 20 GiB. 4) Mount it and enjoy the output of df -hT. 5) Write to if it you dare. I did it, until the Linux kernel told something= =20 about "lost buffer writes". What I found strange is, that the dd writing to= =20 the 1E filesystem did not quit then with input/output error. It just ran on. I didn=B4t test this with any larger size, but if size and time usage scale= s=20 linearily it might be possible to create a 10EiB filesystem within 200 GiB= =20 host XFS and hum about a day of waiting :). No, I do not suggest to use anything even just remotely like this in=20 production. And no, my test didn=B4t show that an 1EiB filesystem will work nicely with= =20 any real life workload. Am I crazy for trying this? I might be :) Thanks, =2D-=20 Martin 'Helios' Steigerwald - http://www.Lichtvoll.de GPG: 03B0 0D6C 0040 0710 4AFA B82F 991B EAAC A599 84C7 From tinguely@sgi.com Mon Mar 11 16:48:05 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id C88C07F3F for ; Mon, 11 Mar 2013 16:48:05 -0500 (CDT) Received: from eagdhcp-232-136.americas.sgi.com (eagdhcp-232-136.americas.sgi.com [128.162.232.136]) by relay2.corp.sgi.com (Postfix) with ESMTP id 90BF7304048; Mon, 11 Mar 2013 14:48:02 -0700 (PDT) Message-ID: <513E5113.60508@sgi.com> Date: Mon, 11 Mar 2013 16:48:03 -0500 From: Mark Tinguely User-Agent: Mozilla/5.0 (X11; FreeBSD amd64; rv:9.0) Gecko/20120122 Thunderbird/9.0 MIME-Version: 1.0 To: Hans-Peter Jansen CC: david@fromorbit.com, xfs@oss.sgi.com Subject: Re: Fwd: xfs_reno References: <20351675.Zy117sIl8Z@xrated> In-Reply-To: <20351675.Zy117sIl8Z@xrated> Content-Type: text/plain; charset=UTF-8; format=flowed Content-Transfer-Encoding: 8bit On 03/06/13 08:55, Hans-Peter Jansen wrote: > Hi Dave, > > I tried to gather Barrys SOB, but failed so far. His trace ends in 2009 google > wise. > > How is this case usually handled? > > Here's the current state of things. > > Cheers, > Pete > > > ---------- Weitergeleitete Nachricht ---------- > > Betreff: xfs_reno > Datum: Mittwoch, 6. März 2013, 12:52:19 > Von: Hans-Peter Jansen > An: bnaujok@sgi.com > > Hi Barry, > > attached is a slightly mangled version of your xfs_reno tool, that I badly > needed recently. While at it, I plan to submit it, as it saved my *ss. Thanks. > > Apart from relocation to xfsprogs, I just changed this > > + log_message(LOG_DEBUG, "%s: %llu %lu %s", msg, node->ino, > + node->numpaths, node->paths[0]); > > from %llu to %lu for the node->numpaths argument. It might still be wrong, as > numpath is defined as nlink_t which is a __u32 type, but the %s printed > garbage like this: > > Scanning directory tree... > xfs_reno: add_node_path: ino 8611163235, path > /work/dlbase/hosts/11.2/pico/var/run/screens > xfs_reno: add_node_path: ino 8611163233, path > /work/dlbase/hosts/11.2/pico/var/run/pcscd/pcscd.events > xfs_reno: add_node_path: ino 8611163234, path > /work/dlbase/hosts/11.2/pico/var/run/uscreens > xfs_reno: nodehash: 8611163233 692488159933497345 ��]��f�e� > xfs_reno: nodehash: 8611163234 692366801337581569 ��]��f�e� > xfs_reno: nodehash: 8611163235 692223830466232321 ��]��f�e� > > I guess, gcc is smart enough to see, that the struct members overlap here, and > prints the paths[0] argument as a %llu value. What do you think? > > Anyway, I will revise this during the course of creating a xlstests test for > xfs_reno... > > Do you allow me to add your Signed-off-by to this patch? > > If you want to build this, apply both patches to xfsprogs. > > TIA, > Pete > Have you been getting "Out of memory" warnings on your runs? I am. Compiling, I get the warnings about having "\r" in the strings. For example: reno/xfs_reno.c:1415: internationalized messages should not contain the `\r' escape sequence ---------- I wonder if we should add a temp directory option. It seems to want to use the parent directory of the directory as a temporary. Below is the result of running xfs_reno on the target directory is "/mnt/xxx (changing the \r to <^M>\n for the email): xfs_reno: directory: 128 1 /mn<^M> xfs_reno: /mnt/xfs_reno_epdaJc: Cannet set target extended attributes<^M> xfs_reno: failed to rename: '/mnt/xxx/origin' to '/mnt/xfs_reno_NXQLWI/origin' <^M> xfs_reno: unable to move directory contents: /mnt/xxx to /mnt/xfs_reno_NXQLWI <^M> xfs_reno: Cannot stat /mnt/xfs_reno_epdaJc: Inappropriate ioctl for device <^M> xfs_reno: unable to duplicate directory attributes: /mnt/xfs_reno_epdaJc t/xxx ------ /mnt is not an XFS filesystem. When mounting on the root, say /mnt, the message look like: xfs_reno: Cannot stat //xfs_reno_epdaJc: Inappropriate ioctl for device Thank-you, --Mark Tinguely. From Martin@lichtvoll.de Mon Mar 11 16:57:03 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 5A1357F37 for ; Mon, 11 Mar 2013 16:57:03 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id 42761304067 for ; Mon, 11 Mar 2013 14:57:03 -0700 (PDT) X-ASG-Debug-ID: 1363039021-04cbb07dbf444480001-NocioJ Received: from mail.lichtvoll.de (mondschein.lichtvoll.de [194.150.191.11]) by cuda.sgi.com with ESMTP id 1JDoX88LZJsGtXKM for ; Mon, 11 Mar 2013 14:57:02 -0700 (PDT) X-Barracuda-Envelope-From: Martin@lichtvoll.de X-Barracuda-Apparent-Source-IP: 194.150.191.11 Received: from merkaba.localnet (ppp-88-217-125-92.dynamic.mnet-online.de [88.217.125.92]) by mail.lichtvoll.de (Postfix) with ESMTPSA id 995B4A9; Mon, 11 Mar 2013 22:56:43 +0100 (CET) From: Martin Steigerwald To: xfs@oss.sgi.com Subject: Re: Maximum file system size of XFS? Date: Mon, 11 Mar 2013 22:57:00 +0100 X-ASG-Orig-Subj: Re: Maximum file system size of XFS? User-Agent: KMail/1.13.7 (Linux/3.9.0-rc2-tp520; KDE/4.9.5; x86_64; ; ) Cc: Pascal References: <20130309215121.0e614ef8@thinky> <201303112245.40522.Martin@lichtvoll.de> (sfid-20130311_224628_172977_9582C9EE) In-Reply-To: <201303112245.40522.Martin@lichtvoll.de> MIME-Version: 1.0 Content-Type: Text/Plain; charset="iso-8859-1" Content-Transfer-Encoding: quoted-printable Message-Id: <201303112257.00798.Martin@lichtvoll.de> X-Barracuda-Connect: mondschein.lichtvoll.de[194.150.191.11] X-Barracuda-Start-Time: 1363039021 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124930 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- Am Montag, 11. M=E4rz 2013 schrieb Martin Steigerwald: > 2) Create a insanely big sparse file >=20 > merkaba:~> truncate -s1E /mnt/zeit/evenmorecrazy.img > merkaba:~> ls -lh /mnt/zeit/evenmorecrazy.img > -rw-r--r-- 1 root root 1,0E M=E4r 11 22:37 /mnt/zeit/evenmorecrazy.img >=20 > (No, this won=B4t work with Ext4.) Okay, you can=B4t go beyond 8 EiB for a single file which is about what I h= ave=20 read somewhere: merkaba:/mnt/zeit> ls -lh insgesamt 0 =2Drw-r--r-- 1 root root 1,0E M=E4r 11 22:37 evenmorecrazy.img merkaba:/mnt/zeit> truncate -s2E /mnt/zeit/evenmorecrazy.img merkaba:/mnt/zeit> truncate -s3E /mnt/zeit/evenmorecrazy.img merkaba:/mnt/zeit> truncate -s4E /mnt/zeit/evenmorecrazy.img merkaba:/mnt/zeit> truncate -s5E /mnt/zeit/evenmorecrazy.img merkaba:/mnt/zeit> truncate -s6E /mnt/zeit/evenmorecrazy.img merkaba:/mnt/zeit> truncate -s7E /mnt/zeit/evenmorecrazy.img merkaba:/mnt/zeit> LANG=3DC truncate -s8E /mnt/zeit/evenmorecrazy.img truncate: invalid number '8E': Value too large for defined data type merkaba:/mnt/zeit#1> ls -lh =20 insgesamt 0 =2Drw-r--r-- 1 root root 7,0E M=E4r 11 22:49 evenmorecrazy.img So so tests stops there, until you concatenate two of those files with LVM= =20 or SoftRAID 0 (if that works). Like this (I just had to try it): merkaba:/mnt/zeit> ls -lh =20 insgesamt 0 =2Drw-r--r-- 1 root root 7,0E M=E4r 11 22:49 evenmorecrazy.img =2Drw-r--r-- 1 root root 7,0E M=E4r 11 22:52 evenmorecrazy.img2 merkaba:/mnt/zeit> losetup /dev/loop0 evenmorecrazy.img merkaba:/mnt/zeit> losetup /dev/loop1 evenmorecrazy.img2 merkaba:/mnt/zeit#5> pvcreate /dev/loop0 =20 Physical volume "/dev/loop0" successfully created merkaba:/mnt/zeit> pvcreate /dev/loop1 Physical volume "/dev/loop1" successfully created merkaba:/mnt/zeit> vgcreate justinsane /dev/loop0 /dev/loop1 PV /dev/loop0 too large for extent size 4,00 MiB. Format-specific setup of physical volume '/dev/loop0' failed. Unable to add physical volume '/dev/loop0' to volume group 'justinsane'. merkaba:/mnt/zeit#5> vgcreate --physicalextentsize 16M justinsane=20 /dev/loop0 /dev/loop1 PV /dev/loop0 too large for extent size 16,00 MiB. Format-specific setup of physical volume '/dev/loop0' failed. Unable to add physical volume '/dev/loop0' to volume group 'justinsane'. merkaba:/mnt/zeit#5> vgcreate --physicalextentsize 128M justinsane=20 /dev/loop0 /dev/loop1 PV /dev/loop0 too large for extent size 128,00 MiB. Format-specific setup of physical volume '/dev/loop0' failed. Unable to add physical volume '/dev/loop0' to volume group 'justinsane'. merkaba:/mnt/zeit#5> vgcreate --physicalextentsize 1G justinsane /dev/loop= 0=20 /dev/loop1 PV /dev/loop0 too large for extent size 1,00 GiB. Format-specific setup of physical volume '/dev/loop0' failed. Unable to add physical volume '/dev/loop0' to volume group 'justinsane'. merkaba:/mnt/zeit#5> vgcreate --physicalextentsize 4G justinsane /dev/loop= 0=20 /dev/loop1 Volume group "justinsane" successfully created merkaba:/mnt/zeit> vgs = =20 VG #PV #LV #SN Attr VSize VFree=20 justinsane 2 0 0 wz--n- 14,00e 14,00e merkaba 1 4 0 wz--n- 278,99g 4,85g merkaba:/mnt/zeit> merkaba:/mnt/zeit> vgdisplay justinsane --- Volume group --- VG Name justinsane System ID =20 Format lvm2 Metadata Areas 2 Metadata Sequence No 1 VG Access read/write VG Status resizable MAX LV 0 Cur LV 0 Open LV 0 Max PV 0 Cur PV 2 Act PV 2 VG Size 14,00 EiB PE Size 4,00 GiB Total PE 3758096382 Alloc PE / Size 0 / 0 =20 Free PE / Size 3758096382 / 14,00 EiB VG UUID z8JP5s-lfRw-uKo8-DXAP-XWGe-aKra-xug9Nn Enough insanity for today :) I won=B4t mkfs.xfs on it, the 20 GiB of the just filesystem wouldn=B4t be=20 enough. Thanks, =2D-=20 Martin 'Helios' Steigerwald - http://www.Lichtvoll.de GPG: 03B0 0D6C 0040 0710 4AFA B82F 991B EAAC A599 84C7 From Martin@lichtvoll.de Mon Mar 11 17:01:57 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 3F3C77F3F for ; Mon, 11 Mar 2013 17:01:57 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay2.corp.sgi.com (Postfix) with ESMTP id 1DD19304059 for ; Mon, 11 Mar 2013 15:01:53 -0700 (PDT) X-ASG-Debug-ID: 1363039312-04cb6c2b0444fce0001-NocioJ Received: from mail.lichtvoll.de (mondschein.lichtvoll.de [194.150.191.11]) by cuda.sgi.com with ESMTP id uQpRxHOyyH2BtdVv for ; Mon, 11 Mar 2013 15:01:52 -0700 (PDT) X-Barracuda-Envelope-From: Martin@lichtvoll.de X-Barracuda-Apparent-Source-IP: 194.150.191.11 Received: from merkaba.localnet (ppp-88-217-125-92.dynamic.mnet-online.de [88.217.125.92]) by mail.lichtvoll.de (Postfix) with ESMTPSA id 5593FA9; Mon, 11 Mar 2013 23:01:34 +0100 (CET) From: Martin Steigerwald To: xfs@oss.sgi.com Subject: Re: Maximum file system size of XFS? Date: Mon, 11 Mar 2013 23:01:51 +0100 X-ASG-Orig-Subj: Re: Maximum file system size of XFS? User-Agent: KMail/1.13.7 (Linux/3.9.0-rc2-tp520; KDE/4.9.5; x86_64; ; ) Cc: Pascal References: <20130309215121.0e614ef8@thinky> <201303112245.40522.Martin@lichtvoll.de> <201303112257.00798.Martin@lichtvoll.de> (sfid-20130311_225800_849624_DAB614D4) In-Reply-To: <201303112257.00798.Martin@lichtvoll.de> MIME-Version: 1.0 Content-Type: Text/Plain; charset="utf-8" Content-Transfer-Encoding: quoted-printable Message-Id: <201303112301.51715.Martin@lichtvoll.de> X-Barracuda-Connect: mondschein.lichtvoll.de[194.150.191.11] X-Barracuda-Start-Time: 1363039312 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124930 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- Am Montag, 11. M=C3=A4rz 2013 schrieb Martin Steigerwald: > Am Montag, 11. M=C3=A4rz 2013 schrieb Martin Steigerwald: > > 2) Create a insanely big sparse file > >=20 > > merkaba:~> truncate -s1E /mnt/zeit/evenmorecrazy.img > > merkaba:~> ls -lh /mnt/zeit/evenmorecrazy.img > > -rw-r--r-- 1 root root 1,0E M=C3=A4r 11 22:37 /mnt/zeit/evenmorecrazy.i= mg > >=20 > > (No, this won=C2=B4t work with Ext4.) >=20 > Okay, you can=C2=B4t go beyond 8 EiB for a single file which is about wha= t I > have read somewhere: [=E2=80=A6] > merkaba:/mnt/zeit> truncate -s7E /mnt/zeit/evenmorecrazy.img > merkaba:/mnt/zeit> LANG=3DC truncate -s8E /mnt/zeit/evenmorecrazy.img > truncate: invalid number '8E': Value too large for defined data type > merkaba:/mnt/zeit#1> ls -lh > insgesamt 0 > -rw-r--r-- 1 root root 7,0E M=C3=A4r 11 22:49 evenmorecrazy.img >=20 > So so tests stops there, until you concatenate two of those files with > LVM or SoftRAID 0 (if that works). Like this (I just had to try it): >=20 >=20 > merkaba:/mnt/zeit> ls -lh > insgesamt 0 > -rw-r--r-- 1 root root 7,0E M=C3=A4r 11 22:49 evenmorecrazy.img > -rw-r--r-- 1 root root 7,0E M=C3=A4r 11 22:52 evenmorecrazy.img2 > merkaba:/mnt/zeit> losetup /dev/loop0 evenmorecrazy.img > merkaba:/mnt/zeit> losetup /dev/loop1 evenmorecrazy.img2 >=20 > merkaba:/mnt/zeit#5> pvcreate /dev/loop0 > Physical volume "/dev/loop0" successfully created > merkaba:/mnt/zeit> pvcreate /dev/loop1 > Physical volume "/dev/loop1" successfully created > merkaba:/mnt/zeit> vgcreate justinsane /dev/loop0 /dev/loop1 > PV /dev/loop0 too large for extent size 4,00 MiB. > Format-specific setup of physical volume '/dev/loop0' failed. > Unable to add physical volume '/dev/loop0' to volume group > 'justinsane'. [=E2=80=A6] > merkaba:/mnt/zeit#5> vgcreate --physicalextentsize 4G justinsane > /dev/loop0 /dev/loop1 > Volume group "justinsane" successfully created >=20 > merkaba:/mnt/zeit> vgs > VG #PV #LV #SN Attr VSize VFree > justinsane 2 0 0 wz--n- 14,00e 14,00e > merkaba 1 4 0 wz--n- 278,99g 4,85g > merkaba:/mnt/zeit> >=20 > merkaba:/mnt/zeit> vgdisplay justinsane [=E2=80=A6] > Enough insanity for today :) Not quite: > I won=C2=B4t mkfs.xfs on it, the 20 GiB of the just filesystem wouldn=C2= =B4t be > enough. Ok, there seems to be another limit involved: merkaba:/mnt/zeit> lvcreate -n yourbiggiexfs -L14E justinsane Volume group "justinsane" has insufficient free space (3758096382=20 extents): 3758096384 required. merkaba:/mnt/zeit#5> LANG=3DC lvcreate -n yourbiggiexfs -L14E justinsane Volume group "justinsane" has insufficient free space (3758096382=20 extents): 3758096384 required. merkaba:/mnt/zeit#5> LANG=3DC lvcreate -n yourbiggiexfs -L13E justinsane /dev/justinsane/yourbiggiexfs: lseek 0 failed: Invalid argument /dev/justinsane/yourbiggiexfs: lseek 0 failed: Invalid argument Logical volume "yourbiggiexfs" created merkaba:/mnt/zeit> LANG=3DC lvs =20 /dev/justinsane/yourbiggiexfs: lseek 14987979559888945152 failed: Invalid= =20 argument /dev/justinsane/yourbiggiexfs: lseek 14987979559889002496 failed: Invalid= =20 argument /dev/justinsane/yourbiggiexfs: lseek 0 failed: Invalid argument /dev/justinsane/yourbiggiexfs: lseek 4096 failed: Invalid argument /dev/justinsane/yourbiggiexfs: lseek 0 failed: Invalid argument LV VG Attr LSize Pool Origin Data% Move Log=20 Copy% Convert yourbiggiexfs justinsane -wi-a---- 13.00e=20 So testing with 9 EiB might become some issue :) Thanks, =2D-=20 Martin 'Helios' Steigerwald - http://www.Lichtvoll.de GPG: 03B0 0D6C 0040 0710 4AFA B82F 991B EAAC A599 84C7 From Martin@lichtvoll.de Mon Mar 11 17:04:20 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id BFD9F7F4E for ; Mon, 11 Mar 2013 17:04:20 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay1.corp.sgi.com (Postfix) with ESMTP id 905998F8040 for ; Mon, 11 Mar 2013 15:04:17 -0700 (PDT) X-ASG-Debug-ID: 1363039455-04bdf022954825c0001-NocioJ Received: from mail.lichtvoll.de (mondschein.lichtvoll.de [194.150.191.11]) by cuda.sgi.com with ESMTP id JHQNQwAsi738nEfs for ; Mon, 11 Mar 2013 15:04:16 -0700 (PDT) X-Barracuda-Envelope-From: Martin@lichtvoll.de X-Barracuda-Apparent-Source-IP: 194.150.191.11 Received: from merkaba.localnet (ppp-88-217-125-92.dynamic.mnet-online.de [88.217.125.92]) by mail.lichtvoll.de (Postfix) with ESMTPSA id 8A3C6A9 for ; Mon, 11 Mar 2013 23:03:57 +0100 (CET) From: Martin Steigerwald To: xfs@oss.sgi.com Subject: Re: Maximum file system size of XFS? Date: Mon, 11 Mar 2013 23:04:14 +0100 X-ASG-Orig-Subj: Re: Maximum file system size of XFS? User-Agent: KMail/1.13.7 (Linux/3.9.0-rc2-tp520; KDE/4.9.5; x86_64; ; ) References: <20130309215121.0e614ef8@thinky> <201303112257.00798.Martin@lichtvoll.de> <201303112301.51715.Martin@lichtvoll.de> (sfid-20130311_230306_047422_F9446F7E) In-Reply-To: <201303112301.51715.Martin@lichtvoll.de> MIME-Version: 1.0 Content-Type: Text/Plain; charset="utf-8" Content-Transfer-Encoding: quoted-printable Message-Id: <201303112304.14945.Martin@lichtvoll.de> X-Barracuda-Connect: mondschein.lichtvoll.de[194.150.191.11] X-Barracuda-Start-Time: 1363039455 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124930 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- Am Montag, 11. M=C3=A4rz 2013 schrieb Martin Steigerwald: > Am Montag, 11. M=C3=A4rz 2013 schrieb Martin Steigerwald: > > Am Montag, 11. M=C3=A4rz 2013 schrieb Martin Steigerwald: > > > 2) Create a insanely big sparse file > > >=20 > > > merkaba:~> truncate -s1E /mnt/zeit/evenmorecrazy.img > > > merkaba:~> ls -lh /mnt/zeit/evenmorecrazy.img > > > -rw-r--r-- 1 root root 1,0E M=C3=A4r 11 22:37 /mnt/zeit/evenmorecrazy= =2Eimg > > >=20 > > > (No, this won=C2=B4t work with Ext4.) > >=20 > > Okay, you can=C2=B4t go beyond 8 EiB for a single file which is about w= hat I >=20 > > have read somewhere: > [=E2=80=A6] >=20 > > merkaba:/mnt/zeit> truncate -s7E /mnt/zeit/evenmorecrazy.img > > merkaba:/mnt/zeit> LANG=3DC truncate -s8E /mnt/zeit/evenmorecrazy.img > > truncate: invalid number '8E': Value too large for defined data type > > merkaba:/mnt/zeit#1> ls -lh > > insgesamt 0 > > -rw-r--r-- 1 root root 7,0E M=C3=A4r 11 22:49 evenmorecrazy.img > >=20 > > So so tests stops there, until you concatenate two of those files with > > LVM or SoftRAID 0 (if that works). Like this (I just had to try it): > >=20 > >=20 > > merkaba:/mnt/zeit> ls -lh > > insgesamt 0 > > -rw-r--r-- 1 root root 7,0E M=C3=A4r 11 22:49 evenmorecrazy.img > > -rw-r--r-- 1 root root 7,0E M=C3=A4r 11 22:52 evenmorecrazy.img2 > > merkaba:/mnt/zeit> losetup /dev/loop0 evenmorecrazy.img > > merkaba:/mnt/zeit> losetup /dev/loop1 evenmorecrazy.img2 > >=20 > > merkaba:/mnt/zeit#5> pvcreate /dev/loop0 > >=20 > > Physical volume "/dev/loop0" successfully created > >=20 > > merkaba:/mnt/zeit> pvcreate /dev/loop1 > >=20 > > Physical volume "/dev/loop1" successfully created > >=20 > > merkaba:/mnt/zeit> vgcreate justinsane /dev/loop0 /dev/loop1 > >=20 > > PV /dev/loop0 too large for extent size 4,00 MiB. > > Format-specific setup of physical volume '/dev/loop0' failed. > > Unable to add physical volume '/dev/loop0' to volume group > >=20 > > 'justinsane'. >=20 > [=E2=80=A6] >=20 > > merkaba:/mnt/zeit#5> vgcreate --physicalextentsize 4G justinsane > > /dev/loop0 /dev/loop1 > >=20 > > Volume group "justinsane" successfully created > >=20 > > merkaba:/mnt/zeit> vgs > >=20 > > VG #PV #LV #SN Attr VSize VFree > > justinsane 2 0 0 wz--n- 14,00e 14,00e > > merkaba 1 4 0 wz--n- 278,99g 4,85g > >=20 > > merkaba:/mnt/zeit> > >=20 > > merkaba:/mnt/zeit> vgdisplay justinsane >=20 > [=E2=80=A6] >=20 > > Enough insanity for today :) >=20 > Not quite: > > I won=C2=B4t mkfs.xfs on it, the 20 GiB of the just filesystem wouldn= =C2=B4t be > > enough. >=20 > Ok, there seems to be another limit involved: >=20 > merkaba:/mnt/zeit> lvcreate -n yourbiggiexfs -L14E justinsane > Volume group "justinsane" has insufficient free space (3758096382 > extents): 3758096384 required. [=E2=80=A6] > merkaba:/mnt/zeit#5> LANG=3DC lvcreate -n yourbiggiexfs -L13E justinsane > /dev/justinsane/yourbiggiexfs: lseek 0 failed: Invalid argument > /dev/justinsane/yourbiggiexfs: lseek 0 failed: Invalid argument > Logical volume "yourbiggiexfs" created > merkaba:/mnt/zeit> LANG=3DC lvs > /dev/justinsane/yourbiggiexfs: lseek 14987979559888945152 failed: > Invalid argument > /dev/justinsane/yourbiggiexfs: lseek 14987979559889002496 failed: > Invalid argument Well, merkaba:/mnt/zeit> LANG=3DC ls -l total 24 =2Drw-r--r-- 1 root root 8070450532247928832 Mar 11 23:02 evenmorecrazy.img =2Drw-r--r-- 1 root root 8070450532247928832 Mar 11 23:02 evenmorecrazy.img2 looks crazy enough for me already. (Ok, I really stop this now :) Thanks, =2D-=20 Martin 'Helios' Steigerwald - http://www.Lichtvoll.de GPG: 03B0 0D6C 0040 0710 4AFA B82F 991B EAAC A599 84C7 From Martin@lichtvoll.de Mon Mar 11 17:10:57 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 15F0C7F37 for ; Mon, 11 Mar 2013 17:10:57 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay3.corp.sgi.com (Postfix) with ESMTP id 7F933AC002 for ; Mon, 11 Mar 2013 15:10:53 -0700 (PDT) X-ASG-Debug-ID: 1363039851-04cb6c2b01450710001-NocioJ Received: from mail.lichtvoll.de (mondschein.lichtvoll.de [194.150.191.11]) by cuda.sgi.com with ESMTP id 6bo8VYFLKyNZGZZC for ; Mon, 11 Mar 2013 15:10:51 -0700 (PDT) X-Barracuda-Envelope-From: Martin@lichtvoll.de X-Barracuda-Apparent-Source-IP: 194.150.191.11 Received: from merkaba.localnet (ppp-88-217-125-92.dynamic.mnet-online.de [88.217.125.92]) by mail.lichtvoll.de (Postfix) with ESMTPSA id 57C98A9; Mon, 11 Mar 2013 23:10:33 +0100 (CET) From: Martin Steigerwald To: xfs@oss.sgi.com Subject: Re: Maximum file system size of XFS? Date: Mon, 11 Mar 2013 23:10:50 +0100 X-ASG-Orig-Subj: Re: Maximum file system size of XFS? User-Agent: KMail/1.13.7 (Linux/3.9.0-rc2-tp520; KDE/4.9.5; x86_64; ; ) Cc: Pascal References: <20130309215121.0e614ef8@thinky> <201303112245.40522.Martin@lichtvoll.de> (sfid-20130311_224628_172977_9582C9EE) In-Reply-To: <201303112245.40522.Martin@lichtvoll.de> MIME-Version: 1.0 Content-Type: Text/Plain; charset="utf-8" Content-Transfer-Encoding: quoted-printable Message-Id: <201303112310.50523.Martin@lichtvoll.de> X-Barracuda-Connect: mondschein.lichtvoll.de[194.150.191.11] X-Barracuda-Start-Time: 1363039851 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.20 X-Barracuda-Spam-Status: No, SCORE=0.20 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_SA074b X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124930 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.20 BSF_SC0_SA074b Custom Rule SA074b Am Montag, 11. M=C3=A4rz 2013 schrieb Martin Steigerwald: > Am Samstag, 9. M=C3=A4rz 2013 schrieb Pascal: > > Hello, >=20 > Hi Pascal, >=20 > > I am asking you because I am insecure about the correct answer and > > different sources give me different numbers. > > > >=20 > >=20 > > > > My question is: What is the maximum file system size of XFS? > > > >=20 > > > > The official page says: 2^63 =3D 9 x 10^18 =3D 9 exabytes > > Source: http://oss.sgi.com/projects/xfs/ > > > >=20 > > > > Wikipedia says 16 exabytes. > > Source: https://en.wikipedia.org/wiki/XFS > > > >=20 > > > > Another reference books says 8 exabytes (2^63). > > > >=20 > >=20 > > > > Can anyone tell me and explain what is the maximum file system size for > > XFS? >=20 > You can test it. The theoretical limit. Whether such a filesystem will > work nicely with a real workload is, as pointed out, a different > question. Well, as I just demonstrated, you can=C2=B4t. At least not with XFS within = XFS.=20 You can only test for maximum filesize. If XFS can be larger than that, you= =20 need a filesystem which can carry an even larger file. Maybe ZFS on Linux o= r=20 so? BTRFS doesn=C2=B4t go beyond 8 EiB per file as well: merkaba:/mnt#1> mkfs.btrfs -n 16384 -l 16384 /dev/merkaba/zeit WARNING! - Btrfs Btrfs v0.19 IS EXPERIMENTAL WARNING! - see http://btrfs.wiki.kernel.org before using fs created label (null) on /dev/merkaba/zeit nodesize 16384 leafsize 16384 sectorsize 4096 size 20.00GB Btrfs Btrfs v0.19 merkaba:/mnt> mount /dev/merkaba/zeit zeit merkaba:/mnt> cd zeit merkaba:/mnt/zeit> truncate -s1E canitgetcrazierthanthat.img merkaba:/mnt/zeit> truncate -s2E canitgetcrazierthanthat.img merkaba:/mnt/zeit> truncate -s3E canitgetcrazierthanthat.img merkaba:/mnt/zeit> truncate -s4E canitgetcrazierthanthat.img merkaba:/mnt/zeit> truncate -s5E canitgetcrazierthanthat.img merkaba:/mnt/zeit> truncate -s6E canitgetcrazierthanthat.img merkaba:/mnt/zeit> truncate -s7E canitgetcrazierthanthat.img merkaba:/mnt/zeit> truncate -s8E canitgetcrazierthanthat.img truncate: ung=C3=BCltige Zahl =E2=80=9E8E=E2=80=9C: Der Wert ist zu gro=C3= =9F f=C3=BCr den definierten=20 Datentyp merkaba:/mnt/zeit#1> LANG=3DC truncate -s8E canitgetcrazierthanthat.im truncate: invalid number '8E': Value too large for defined data type merkaba:/mnt/zeit#1> ls -lh insgesamt 0 =2Drw-r--r-- 1 root root 7,0E M=C3=A4r 11 23:09 canitgetcrazierthanthat.img Thanks, =2D-=20 Martin 'Helios' Steigerwald - http://www.Lichtvoll.de GPG: 03B0 0D6C 0040 0710 4AFA B82F 991B EAAC A599 84C7 From david@fromorbit.com Mon Mar 11 17:19:41 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 36EC77F37 for ; Mon, 11 Mar 2013 17:19:41 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id 10DE1304059 for ; Mon, 11 Mar 2013 15:19:40 -0700 (PDT) X-ASG-Debug-ID: 1363040378-04cbb07dbd446260001-NocioJ Received: from ipmail06.adl6.internode.on.net (ipmail06.adl6.internode.on.net [150.101.137.145]) by cuda.sgi.com with ESMTP id 29XdECiWGi6qccM2 for ; Mon, 11 Mar 2013 15:19:38 -0700 (PDT) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.145 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AqYdAMhXPlF5LKiV/2dsb2JhbABDv0qFFgECAYFcF3SCKQEBBAEyASMjBQsIAxgJJQ8FJQMhEx+HbgWvXZAbFY14GB9KB4JfYQOWVJB2gx4o Received: from ppp121-44-168-149.lns20.syd7.internode.on.net (HELO dastard) ([121.44.168.149]) by ipmail06.adl6.internode.on.net with ESMTP; 12 Mar 2013 08:49:37 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UFB4C-0008BA-8g; Tue, 12 Mar 2013 09:19:36 +1100 Date: Tue, 12 Mar 2013 09:19:36 +1100 From: Dave Chinner To: Martin Steigerwald Cc: xfs@oss.sgi.com, Pascal Subject: Re: Maximum file system size of XFS? Message-ID: <20130311221936.GD21651@dastard> X-ASG-Orig-Subj: Re: Maximum file system size of XFS? References: <20130309215121.0e614ef8@thinky> <201303112245.40522.Martin@lichtvoll.de> <201303112257.00798.Martin@lichtvoll.de> MIME-Version: 1.0 Content-Type: text/plain; charset=iso-8859-1 Content-Disposition: inline Content-Transfer-Encoding: 8bit In-Reply-To: <201303112257.00798.Martin@lichtvoll.de> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail06.adl6.internode.on.net[150.101.137.145] X-Barracuda-Start-Time: 1363040378 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124932 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Mon, Mar 11, 2013 at 10:57:00PM +0100, Martin Steigerwald wrote: > Am Montag, 11. Mrz 2013 schrieb Martin Steigerwald: > > 2) Create a insanely big sparse file > > > > merkaba:~> truncate -s1E /mnt/zeit/evenmorecrazy.img > > merkaba:~> ls -lh /mnt/zeit/evenmorecrazy.img > > -rw-r--r-- 1 root root 1,0E Mr 11 22:37 /mnt/zeit/evenmorecrazy.img > > > > (No, this wont work with Ext4.) > > Okay, you cant go beyond 8 EiB for a single file which is about what I have > read somewhere: Right - file size offsets max out at 2^63 bytes. .... > merkaba:/mnt/zeit#5> vgcreate --physicalextentsize 4G justinsane /dev/loop0 > /dev/loop1 > Volume group "justinsane" successfully created > > merkaba:/mnt/zeit> vgs > VG #PV #LV #SN Attr VSize VFree > justinsane 2 0 0 wz--n- 14,00e 14,00e > merkaba 1 4 0 wz--n- 278,99g 4,85g > merkaba:/mnt/zeit> .... > Enough insanity for today :) > > I wont mkfs.xfs on it, the 20 GiB of the just filesystem wouldnt be > enough. Right - I did a mkfs.xfs on a (8EB - 1GB) file a couple of days ago just to check it worked. I killed it after a short while, because I didn't feel like needlessly subjecting the SSDs the file was physically located on to the 25 million sparse sector sized writes needed for mkfs to complete. And you can double that number of writes needed for a 16EB filesystem to be initialised by mkfs. So, theory be damned, even mkfs.xfs doesn't scale to supporting exabyte filesystems... Cheers, Dave. -- Dave Chinner david@fromorbit.com From david@fromorbit.com Mon Mar 11 17:45:41 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 23C347F37 for ; Mon, 11 Mar 2013 17:45:41 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay1.corp.sgi.com (Postfix) with ESMTP id DF5E08F8050 for ; Mon, 11 Mar 2013 15:45:40 -0700 (PDT) X-ASG-Debug-ID: 1363041938-04bdf022984868e0001-NocioJ Received: from ipmail06.adl6.internode.on.net (ipmail06.adl6.internode.on.net [150.101.137.145]) by cuda.sgi.com with ESMTP id CmCuz49X4CKJjYWV for ; Mon, 11 Mar 2013 15:45:38 -0700 (PDT) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.145 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AqgdAAJdPlF5LKiV/2dsb2JhbABDv0mFFgECAYFcF3SCKQEBAwEBOhwWBgQDBQsIAxgJJQ8FJQMhE4gNBQ2vS5AcFY1JLxgfSgeCX2EDkxCDRJB2gx4o Received: from ppp121-44-168-149.lns20.syd7.internode.on.net (HELO dastard) ([121.44.168.149]) by ipmail06.adl6.internode.on.net with ESMTP; 12 Mar 2013 09:15:37 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UFBTM-0008Dg-N3; Tue, 12 Mar 2013 09:45:36 +1100 Date: Tue, 12 Mar 2013 09:45:36 +1100 From: Dave Chinner To: Stan Hoeppner Cc: Ric Wheeler , Julien FERRERO , xfs@oss.sgi.com Subject: Re: XFS filesystem corruption Message-ID: <20130311224536.GE21651@dastard> X-ASG-Orig-Subj: Re: XFS filesystem corruption References: <5137CD46.6070909@redhat.com> <5139A3B6.3040805@hardwarefreak.com> <5139D792.4090304@redhat.com> <513A350A.508@hardwarefreak.com> <20130309091152.GH23616@dastard> <513B84AD.2000603@hardwarefreak.com> <20130310224536.GK23616@dastard> <513D1D51.7010905@hardwarefreak.com> <20130311005024.GC20565@dastard> <513DA40B.6050903@hardwarefreak.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <513DA40B.6050903@hardwarefreak.com> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail06.adl6.internode.on.net[150.101.137.145] X-Barracuda-Start-Time: 1363041938 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124932 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Mon, Mar 11, 2013 at 04:29:47AM -0500, Stan Hoeppner wrote: > On 3/10/2013 7:50 PM, Dave Chinner wrote: > > On Sun, Mar 10, 2013 at 06:54:57PM -0500, Stan Hoeppner wrote: > >> On 3/10/2013 5:45 PM, Dave Chinner wrote: > >>>> Does everyone remember the transitive property of equality from math > >>>> class decades ago? It states "If A=B and B=C then A=C". Thus if > >>>> barrier writes to the journal protect the journal, and the journal > >>>> protects metadata, then barrier writes to the journal protect metadata. > >>> > >>> Yup, but the devil is in the detail - we don't protect individual > >>> metadata writes at all and that difference is significant enough to > >>> comment on.... :P > >> > >> Elaborate on this a bit, if you have time. I was under the impression > >> that all directory updates were journaled first. > > > > That's correct - they are all journalled. > > > > But journalling is done at the transactional level, not that of > > individual metadata changes. IOWs, journalled changes do not > > contain the same information as a metadata buffer write - they > > contain both more and less information than a metadata buffer write. > > > > They contain more information in that there is change atomicity > > information in the journal information for recovery purposes. i.e. > > how the individual change relates to changes in other related > > metadata objects. This information is needed in the journal so that > > log recovery knows to either apply all the changes in a checkpoint > > or none of them if this journal checkpoint (or a previous one) is > > incomplete. > > > > They contain less information in that the changes to a metadata > > object is stored as a diff in the journal rather than as a complete > > copy of the object. This is done to reduce the amount of journal > > space and memory required to track and store all of the changes in > > the checkpoint. > > Forget the power loss issue for a moment. If I'm digesting this > correctly, it's seems quite an accomplishment that you got delaylog > working, at all, let alone extremely well as it does. Given what you > state above, it would seem there is quite a bit of complexity involved > in tracking these metadata change relationships and modifying the > checkpoint information accordingly. Yes, there is. > I would think as you merge multiple > traditional XFS log writes into a single write that the relationship > information would also need to be modified as well. Or do I lack > sufficient understanding at this point to digest this? Relationship information is inherent in the checkpoint method due to a feature that has been built into the XFS transaction/journalling code from day-zero: relogging. This is described in all it's glory in Documentation/filesystems/xfs-delayed-logging-design.txt.... > > Hence what is written to the journal is quite different to what is > > written during metadata writeback in both contents ad method. It is > > the atomicity information in the journal that we know got > > synchronised to disk (via the FUA/cache flush) that enables us to > > get away with being lazy writing back metadata buffers in any order > > we please without needing FUA/cache flushes... > > This makes me wonder... for a given metadata write into an AG, is the > amount of data in the corresponding journal write typically greater or > less? Typically less - buffer changes are logged into a dirty bitmap with a resolution of 128 bytes. hence a single byte change will record a single dirty bit, which means 128 bytes will be logged. Both the dirty bitmap and the 128 byte regions are written to the journal. So inthis case, less is written to the journal. However, because of relogging, the more a buffer gets modified, then larger the number of dirty regions, and so for buffers that are repeatedly modified we typically end up logging them entirely, including the bitmap and other information. In this case, more is written to the journal than would be written by metadata writeback... The difference with delayed logging is that the frequency of journal writes goes way down, so the fact that we typically log more per object into the journal is greatly outweighed by the fact that the objects are logged orders of magnitude less often.... > You stated above it is both more and less but I don't know if you > meant that qualitatively or quantitatively, or both. I'm > wondering that if log write bytes is typically significantly > lower, and we know we can recreate a lost metadata write from the > journal data during a recovery.... Given that CPU is so much > faster than disk, would it be plausible to do all metadata writes > in a lazy fashion through the relevant sections of the recovery > code, or something along these lines? We already do that. > Make 'recovery' the > standard method for metadata writes? I'm not talking about > replacing the log journal, but replacing the metadata write method > with something akin to a portion of the the journal recovery > routine. To do that, you need an unbound log size. i.e. you are talking about a log structured filesystem rather than a traditional journalled filesystem. The problem with log structured filesystem is that you trade off write side speed and latency for read side speed and latency. When you get large data sets or frequently modified data sets larger than can be cached in memory, log structured filesystems perform teribly because the metadata needs reconstructing or regathering every time it is read. IOWs, log structured filesystems simply don't scale to large sizes or large scale data sets effectively. > In other words, could we make use of the delaylog concept of doing > more work with fewer IOs to achieve a similar performance gain for > metadata writeback? Or is XFS metadata writeback already fully > optimized WRT IOs and bandwidth, latency, etc? I wouldn't say it's fully optimised (nothing ever is), but metadata writeback is almost completely decoupled from the transactional modification side of the filesystem and so we can do far larger scale optimisation of writback order than othe filesystems. Hence there are relatively few latency/bandwidth/IOPS issued with metadata writeback. For example: have a look at slide 24 of this presentation: http://xfs.org/images/d/d1/Xfs-scalability-lca2012.pdf and note how much IO XFS is doing for metadata writeback for the given metadata performance compared to ext4. Take away message: "XFS has the lowest IOPS rate at a given modification rate - both ext4 and BTRFS are IO bound at higher thread counts." Cheers, Dave. -- Dave Chinner david@fromorbit.com From dsterba@suse.cz Mon Mar 11 18:36:59 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id BA6C17F37 for ; Mon, 11 Mar 2013 18:36:59 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay3.corp.sgi.com (Postfix) with ESMTP id 6616EAC002 for ; Mon, 11 Mar 2013 16:36:56 -0700 (PDT) X-ASG-Debug-ID: 1363045014-04bdf0229748c530001-NocioJ Received: from mx2.suse.de (cantor2.suse.de [195.135.220.15]) by cuda.sgi.com with ESMTP id CNYDhIKVpFzI4WkL for ; Mon, 11 Mar 2013 16:36:55 -0700 (PDT) X-Barracuda-Envelope-From: dsterba@suse.cz X-Barracuda-Apparent-Source-IP: 195.135.220.15 Received: from relay2.suse.de (unknown [195.135.220.254]) by mx2.suse.de (Postfix) with ESMTP id 126E7A3A78 for ; Tue, 12 Mar 2013 00:36:54 +0100 (CET) Received: by ds.suse.cz (Postfix, from userid 10065) id 6DC71DA802; Tue, 12 Mar 2013 00:36:53 +0100 (CET) From: David Sterba To: xfs@oss.sgi.com Cc: David Sterba Subject: [PATCH] xfstests: determine path of logger Date: Tue, 12 Mar 2013 00:36:52 +0100 X-ASG-Orig-Subj: [PATCH] xfstests: determine path of logger Message-Id: <1363045012-21119-1-git-send-email-dsterba@suse.cz> X-Mailer: git-send-email 1.8.1.4 X-Barracuda-Connect: cantor2.suse.de[195.135.220.15] X-Barracuda-Start-Time: 1363045014 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124936 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- The path of the syslog writer utility 'logger' is hardcoded and not always correct, use set_prog_path. Signed-off-by: David Sterba --- check | 2 +- common.config | 1 + 2 files changed, 2 insertions(+), 1 deletion(-) diff --git a/check b/check index c20179c..9a5b256 100755 --- a/check +++ b/check @@ -243,7 +243,7 @@ do start=`_wallclock` $timestamp && echo -n " ["`date "+%T"`"]" [ ! -x $seq ] && chmod u+x $seq # ensure we can run it - [ -x /usr/bin/logger ] && /usr/bin/logger "run xfstest $seq" + $LOGGER_PROG "run xfstest $seq" ./$seq >$tmp.rawout 2>&1 sts=$? $timestamp && _timestamp diff --git a/common.config b/common.config index a0b017d..ed0f44c 100644 --- a/common.config +++ b/common.config @@ -177,6 +177,7 @@ export DUMPE2FS_PROG="`set_prog_path dumpe2fs`" export FIO_PROG="`set_prog_path fio`" export FILEFRAG_PROG="`set_prog_path filefrag`" export E4DEFRAG_PROG="`set_prog_path e4defrag`" +export LOGGER_PROG="`set_prog_path logger`" # Generate a comparable xfsprogs version number in the form of # major * 10000 + minor * 100 + release -- 1.8.1.4 From david@fromorbit.com Mon Mar 11 20:22:14 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 0EABB7F37 for ; Mon, 11 Mar 2013 20:22:14 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay1.corp.sgi.com (Postfix) with ESMTP id E396C8F8035 for ; Mon, 11 Mar 2013 18:22:13 -0700 (PDT) X-ASG-Debug-ID: 1363051331-04bdf02295494380001-NocioJ Received: from ipmail06.adl6.internode.on.net (ipmail06.adl6.internode.on.net [150.101.137.145]) by cuda.sgi.com with ESMTP id 9EJbzSuhMkTukFb4 for ; Mon, 11 Mar 2013 18:22:12 -0700 (PDT) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.145 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AqUdAJGCPlF5LKiV/2dsb2JhbABDv0yFFgECAYFeF3SCKQEBBTocIxAIAw4KCSUPBSUDIROIEq9akCAVjTZCGB9KB4NAA5ZUkHaDHiiBLg Received: from ppp121-44-168-149.lns20.syd7.internode.on.net (HELO dastard) ([121.44.168.149]) by ipmail06.adl6.internode.on.net with ESMTP; 12 Mar 2013 11:51:53 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UFDua-0008W0-6B; Tue, 12 Mar 2013 12:21:52 +1100 Date: Tue, 12 Mar 2013 12:21:52 +1100 From: Dave Chinner To: David Sterba Cc: xfs@oss.sgi.com Subject: Re: [PATCH] xfstests: determine path of logger Message-ID: <20130312012152.GG21651@dastard> X-ASG-Orig-Subj: Re: [PATCH] xfstests: determine path of logger References: <1363045012-21119-1-git-send-email-dsterba@suse.cz> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <1363045012-21119-1-git-send-email-dsterba@suse.cz> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail06.adl6.internode.on.net[150.101.137.145] X-Barracuda-Start-Time: 1363051331 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124944 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Tue, Mar 12, 2013 at 12:36:52AM +0100, David Sterba wrote: > The path of the syslog writer utility 'logger' is hardcoded and not > always correct, use set_prog_path. > > Signed-off-by: David Sterba > --- > check | 2 +- > common.config | 1 + > 2 files changed, 2 insertions(+), 1 deletion(-) > > diff --git a/check b/check > index c20179c..9a5b256 100755 > --- a/check > +++ b/check > @@ -243,7 +243,7 @@ do > start=`_wallclock` > $timestamp && echo -n " ["`date "+%T"`"]" > [ ! -x $seq ] && chmod u+x $seq # ensure we can run it > - [ -x /usr/bin/logger ] && /usr/bin/logger "run xfstest $seq" > + $LOGGER_PROG "run xfstest $seq" > ./$seq >$tmp.rawout 2>&1 > sts=$? > $timestamp && _timestamp > diff --git a/common.config b/common.config > index a0b017d..ed0f44c 100644 > --- a/common.config > +++ b/common.config > @@ -177,6 +177,7 @@ export DUMPE2FS_PROG="`set_prog_path dumpe2fs`" > export FIO_PROG="`set_prog_path fio`" > export FILEFRAG_PROG="`set_prog_path filefrag`" > export E4DEFRAG_PROG="`set_prog_path e4defrag`" > +export LOGGER_PROG="`set_prog_path logger`" > > # Generate a comparable xfsprogs version number in the form of > # major * 10000 + minor * 100 + release Looks good. Reviewed-by: Dave Chinner -- Dave Chinner david@fromorbit.com From qcai@redhat.com Mon Mar 11 23:32:34 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 5617C7F4E for ; Mon, 11 Mar 2013 23:32:34 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay3.corp.sgi.com (Postfix) with ESMTP id BAEFAAC002 for ; Mon, 11 Mar 2013 21:32:30 -0700 (PDT) X-ASG-Debug-ID: 1363062748-04cb6c2b02470b60001-NocioJ Received: from mx4-phx2.redhat.com (mx4-phx2.redhat.com [209.132.183.25]) by cuda.sgi.com with ESMTP id lcTroT9RJXVu0N2I for ; Mon, 11 Mar 2013 21:32:28 -0700 (PDT) X-Barracuda-Envelope-From: qcai@redhat.com X-Barracuda-Apparent-Source-IP: 209.132.183.25 Received: from zmail14.collab.prod.int.phx2.redhat.com (zmail14.collab.prod.int.phx2.redhat.com [10.5.83.16]) by mx4-phx2.redhat.com (8.13.8/8.13.8) with ESMTP id r2C4WS6b012270 for ; Tue, 12 Mar 2013 00:32:28 -0400 Date: Tue, 12 Mar 2013 00:32:28 -0400 (EDT) From: CAI Qian To: xfs@oss.sgi.com Message-ID: <782268481.12604851.1363062748244.JavaMail.root@redhat.com> In-Reply-To: <1868681549.12603593.1363061997919.JavaMail.root@redhat.com> Subject: 3.9-rc2 xfs panic MIME-Version: 1.0 X-ASG-Orig-Subj: 3.9-rc2 xfs panic Content-Type: text/plain; charset=utf-8 Content-Transfer-Encoding: 7bit X-Originating-IP: [10.66.13.149] X-Mailer: Zimbra 7.2.0_GA_2669 (ZimbraWebClient - FF3.0 (Linux)/7.2.0_GA_2669) X-Barracuda-Connect: mx4-phx2.redhat.com[209.132.183.25] X-Barracuda-Start-Time: 1363062748 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124956 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- Just came across when running xfstests using 3.9-rc2 kernel on a power7 box with addition of this patch which fixed a known issue, http://people.redhat.com/qcai/stable/01-fix-double-fetch-hlist.patch The log shows it was happened around test case 370 with TEST_PARAM_BLKSIZE = 2048 Some more information: xfsprogs version = 3.1.10 number of CPUs = 32 Swap Size = 4047 MB Mem Size = 4046 M Still reproducing and bisecting, so this is just a head-up to see if helps. CAI Qian [31797.113368] XFS (loop1): xfs_trans_ail_delete_bulk: attempting to delete a log item that is not in the AIL [31797.113383] XFS (loop1): xfs_do_force_shutdown(0x2) called from line 743 of file fs/xfs/xfs_trans_ail.c. Return address = 0xd000000000f22838 [31797.113430] Buffer I/O error on device loop1, logical block 66965 [31797.113440] lost page write due to I/O error on loop1 [31797.113446] Buffer I/O error on device loop1, logical block 66966 [31797.113450] lost page write due to I/O error on loop1 [31797.113456] Buffer I/O error on device loop1, logical block 66967 [31797.113461] lost page write due to I/O error on loop1 [31797.113466] Buffer I/O error on device loop1, logical block 66968 [31797.113472] lost page write due to I/O error on loop1 [31797.113477] Buffer I/O error on device loop1, logical block 66969 [31797.113482] lost page write due to I/O error on loop1 [31797.113881] XFS (loop1): Log I/O Error Detected. Shutting down filesystem [31797.113887] XFS (loop1): Please umount the filesystem and rectify the problem(s) [31797.114000] XFS (loop1): metadata I/O error: block 0xc0002 ("xfs_trans_read_buf_map") error 5 numblks 1 [31797.114048] XFS (loop1): metadata I/O error: block 0xc0002 ("xfs_trans_read_buf_map") error 5 numblks 1 [31797.150364] Buffer I/O error on device loop1, logical block 33940 [31797.150380] lost page write due to I/O error on loop1 [31797.150389] Buffer I/O error on device loop1, logical block 33941 [31797.150395] lost page write due to I/O error on loop1 [31797.150403] Buffer I/O error on device loop1, logical block 33942 [31797.150408] lost page write due to I/O error on loop1 [31797.150415] Buffer I/O error on device loop1, logical block 33943 [31797.150421] lost page write due to I/O error on loop1 [31797.150429] Buffer I/O error on device loop1, logical block 33944 [31797.150436] lost page write due to I/O error on loop1 [-- MARK -- Mon Mar 11 14:15:00 2013] [31817.159550] XFS (loop1): xfs_log_force: error 5 returned. [31817.166204] XFS (loop1): xfs_log_force: error 5 returned. [31817.166551] XFS (loop1): xfs_log_force: error 5 returned. [31817.508411] XFS (loop0): Mounting Filesystem [31817.566235] XFS (loop0): Ending clean mount [31819.094713] XFS (loop0): Mounting Filesystem [31819.152248] XFS (loop0): Ending clean mount [31819.348238] XFS (loop1): Mounting Filesystem [31819.349879] XFS (loop1): Ending clean mount [31819.561366] XFS (loop0): Mounting Filesystem [31819.616607] XFS (loop0): Ending clean mount [31819.990833] XFS (loop1): Mounting Filesystem [31819.992652] XFS (loop1): Ending clean mount [31819.992768] XFS (loop1): Quotacheck needed: Please wait. [31820.051134] XFS (loop1): Quotacheck: Done. [31832.534868] Unable to handle kernel paging request for data at address 0x5841474900000001 [31832.534881] Faulting instruction address: 0xc0000000001f8070 [31832.534888] Oops: Kernel access of bad area, sig: 11 [#1] [31832.534891] SMP NR_CPUS=1024 NUMA pSeries [31832.534899] Modules linked in: tun(F) binfmt_misc(F) hidp(F) cmtp(F) kernelcapi(F) rfcomm(F) l2tp_ppp(F) l2tp_netlink(F) l2tp_core(F) bnep(F) nfc(F) af_802154(F) pppoe(F) pppox(F) ppp_generic(F) slhc(F) rds(F) af_key(F) atm(F) sctp(F) ip6table_filter(F) ip6_tables(F) iptable_filter(F) ip_tables(F) btrfs(F) raid6_pq(F) xor(F) vfat(F) fat(F) nfsv3(F) nfs_acl(F) nfnetlink_log(F) nfnetlink(F) bluetooth(F) rfkill(F) nfsv2(F) nfs(F) dns_resolver(F) lockd(F) sunrpc(F) fscache(F) nf_tproxy_core(F) nls_koi8_u(F) nls_cp932(F) ts_kmp(F) fuse(F) sg(F) ibmveth(F) xfs(F) libcrc32c(F) sd_mod(F) crc_t10dif(F) ibmvscsi(F) scsi_transport_srp(F) scsi_tgt(F) dm_mirror(F) dm_region_hash(F) dm_log(F) dm_mod(F) [last unloaded: ipt_REJECT] [31832.534978] NIP: c0000000001f8070 LR: c000000000192f6c CTR: c000000000192f50 [31832.534984] REGS: c0000000f1c125f0 TRAP: 0300 Tainted: GF W (3.9.0-rc2+) [31832.534989] MSR: 8000000000009032 CR: 24022024 XER: 20000001 [31832.535003] SOFTE: 0 [31832.535006] CFAR: c000000000005f1c [31832.535009] DAR: 5841474900000001, DSISR: 40000000 [31832.535013] TASK = c00000003f0111c0[16795] 'loop1' THREAD: c0000000f1c10000 CPU: 30 GPR00: c000000000192f6c c0000000f1c12870 c0000000010f3a48 c0000000fe015a00 GPR04: 0000000000011220 0000000000000080 00000000000f3aaf c0000000018d5840 GPR08: 0000000000000000 0000000000000000 0000000000000000 c0000000004e3300 GPR12: 0000000044024024 c00000000f247800 c0000000010d01b0 0000000000000000 GPR16: 0000000000000001 0000000000000000 c0000000009d9020 c0000000009d9060 GPR20: c0000000009d9048 0000000000000020 000000000000007f 0000000000000000 GPR24: 0000000000000fe0 c0000000010d1020 c0000000fe015a00 0000000000000000 GPR28: c000000000192f6c 0000000000011220 5841474900000001 c0000000fe015a00 [31832.535086] NIP [c0000000001f8070] .kmem_cache_alloc+0xb0/0x2d0 [31832.535092] LR [c000000000192f6c] .mempool_alloc_slab+0x1c/0x30 [31832.535096] Call Trace: [31832.535101] [c0000000f1c12870] [0000000000016ac3] 0x16ac3 (unreliable) [31832.535108] [c0000000f1c12920] [c000000000192f6c] .mempool_alloc_slab+0x1c/0x30 [31832.535114] [c0000000f1c12990] [c000000000193108] .mempool_alloc+0x88/0x1c0 [31832.535122] [c0000000f1c12a80] [c0000000004e1824] .scsi_sg_alloc+0x64/0xc0 [31832.535129] [c0000000f1c12af0] [c0000000003e09f8] .__sg_alloc_table+0xa8/0x190 [31832.535135] [c0000000f1c12bc0] [c0000000004e15f0] .scsi_alloc_sgtable+0x40/0x90 [31832.535142] [c0000000f1c12c40] [c0000000004e1668] .scsi_init_sgtable+0x28/0x90 [31832.535148] [c0000000f1c12cc0] [c0000000004e19e0] .scsi_init_io+0x40/0x1a0 [31832.535157] [c0000000f1c12d60] [d000000000c02e78] .sd_prep_fn+0x128/0xac0 [sd_mod] [31832.535164] [c0000000f1c12e20] [c0000000003a611c] .blk_peek_request+0xfc/0x2d0 [31832.535171] [c0000000f1c12eb0] [c0000000004e2c08] .scsi_request_fn+0xb8/0x6d0 [31832.535178] [c0000000f1c12fa0] [c00000000039d7c0] .__blk_run_queue+0x50/0x80 [31832.535184] [c0000000f1c13020] [c0000000003a2184] .queue_unplugged+0xe4/0x100 [31832.535190] [c0000000f1c130c0] [c0000000003a67d8] .blk_flush_plug_list+0x248/0x2e0 [31832.535197] [c0000000f1c13180] [c0000000003a6bcc] .blk_queue_bio+0x2fc/0x490 [31832.535203] [c0000000f1c13230] [c0000000003a436c] .generic_make_request+0x11c/0x180 [31832.535210] [c0000000f1c132c0] [c0000000003a4484] .submit_bio+0xb4/0x1e0 [31832.535245] [c0000000f1c13380] [d000000000eaffa0] .xfs_submit_ioend_bio.isra.10+0x70/0x90 [xfs] [31832.535286] [c0000000f1c133f0] [d000000000eb00f0] .xfs_submit_ioend+0x130/0x190 [xfs] [31832.535343] [c0000000f1c134a0] [d000000000eb045c] .xfs_vm_writepage+0x30c/0x670 [xfs] [31832.535349] [c0000000f1c135d0] [c00000000019d050] .__writepage+0x30/0x90 [31832.535356] [c0000000f1c13650] [c00000000019d728] .write_cache_pages+0x208/0x4f0 [31832.535362] [c0000000f1c137e0] [c00000000019da5c] .generic_writepages+0x4c/0xa0 [31832.535395] [c0000000f1c138a0] [d000000000eaea10] .xfs_vm_writepages+0x60/0x90 [xfs] [31832.535411] [c0000000f1c13930] [c00000000019ee7c] .do_writepages+0x3c/0x70 [31832.535424] [c0000000f1c139a0] [c0000000001914b8] .__filemap_fdatawrite_range+0x68/0x80 [31832.535430] [c0000000f1c13a40] [c000000000191610] .filemap_write_and_wait_range+0x70/0xc0 [31832.535463] [c0000000f1c13ad0] [d000000000eb7970] .xfs_file_fsync+0x60/0x250 [xfs] [31832.535479] [c0000000f1c13b90] [c00000000024c278] .vfs_fsync+0x48/0x70 [31832.535497] [c0000000f1c13c00] [c0000000004d299c] .loop_thread+0x3ec/0x5b0 [31832.535503] [c0000000f1c13d30] [c0000000000b58c8] .kthread+0xe8/0xf0 [31832.535510] [c0000000f1c13e30] [c000000000009f64] .ret_from_kernel_thread+0x64/0x80 [31832.535516] Instruction dump: [31832.535519] 4be17f11 60000000 e93f0000 e94d0040 7ce95214 e8c70008 7fc9502a 2fbe0000 [31832.535532] 41de01fc e95f0022 e93f0000 79290720 <7f3e502a> 0b090000 0b1b0000 39200000 [31832.535557] ---[ end trace 8bfd449aae38f917 ]--- [31832.536965] [31892.635116] INFO: rcu_sched detected stalls on CPUs/tasks: { 30 31} (detected by 28, t=6002 jiffies, g=390021, c=390020, q=417) [31892.635141] Task dump for CPU 30: [31892.635146] loop1 R running task 0 16795 2 0x00000884 [31892.635155] Call Trace: [31892.635176] [c0000000f1c12f10] [0000000000000001] 0x1 (unreliable) [31892.635183] Task dump for CPU 31: [31892.635187] swapper/31 R running task 0 0 1 0x00000804 [31892.635194] Call Trace: [32072.684667] INFO: rcu_sched detected stalls on CPUs/tasks: { 30 31} (detected by 28, t=24007 jiffies, g=390021, c=390020, q=580) [32072.684694] Task dump for CPU 30: [32072.684700] loop1 R running task 0 16795 2 0x00000884 [32072.684708] Call Trace: [32072.684729] [c0000000f1c12f10] [0000000000000001] 0x1 (unreliable) [32072.684737] Task dump for CPU 31: [32072.684741] swapper/31 R running task 0 0 1 0x00000804 [32072.684748] Call Trace: [-- MARK -- Mon Mar 11 14:20:00 2013] [32252.734223] INFO: rcu_sched detected stalls on CPUs/tasks: { 30 31} (detected by 22, t=42012 jiffies, g=390021, c=390020, q=619) [32252.734248] Task dump for CPU 30: [32252.734254] loop1 R running task 0 16795 2 0x00000884 [32252.734262] Call Trace: [32252.734282] [c0000000f1c12f10] [0000000000000001] 0x1 (unreliable) [32252.734289] Task dump for CPU 31: [32252.734293] swapper/31 R running task 0 0 1 0x00000804 [32252.734300] Call Trace: [-- MARK -- Mon Mar 11 14:25:00 2013] [32432.783781] INFO: rcu_sched detected stalls on CPUs/tasks: { 30 31} (detected by 28, t=60017 jiffies, g=390021, c=390020, q=630) [32432.783809] Task dump for CPU 30: [32432.783815] loop1 R running task 0 16795 2 0x00000884 [32432.783823] Call Trace: [32432.783845] [c0000000f1c12f10] [0000000000000001] 0x1 (unreliable) [32432.783852] Task dump for CPU 31: [32432.783856] swapper/31 R running task 0 0 1 0x00000804 [32432.783864] Call Trace: From david@fromorbit.com Tue Mar 12 01:07:10 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 399D87F51 for ; Tue, 12 Mar 2013 01:07:10 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id 283B2304039 for ; Mon, 11 Mar 2013 23:07:07 -0700 (PDT) X-ASG-Debug-ID: 1363068424-04cbb07dbf46a420001-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id rv6wDFl1b2NOKP1p for ; Mon, 11 Mar 2013 23:07:04 -0700 (PDT) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AhIcABnFPlF5LKiV/2dsb2JhbABDh0a4DYUWAQIBgWIXdIIpAQEEATocIwULCAMYCSUPBSUDIROIDQUNsA6QIhWNdxgfSgeDQAOWVIEfj1eBL4FvKA Received: from ppp121-44-168-149.lns20.syd7.internode.on.net (HELO dastard) ([121.44.168.149]) by ipmail05.adl6.internode.on.net with ESMTP; 12 Mar 2013 16:37:03 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UFIMX-0000bb-AL; Tue, 12 Mar 2013 17:07:01 +1100 Date: Tue, 12 Mar 2013 17:07:01 +1100 From: Dave Chinner To: CAI Qian Cc: xfs@oss.sgi.com Subject: Re: 3.9-rc2 xfs panic Message-ID: <20130312060701.GI21651@dastard> X-ASG-Orig-Subj: Re: 3.9-rc2 xfs panic References: <1868681549.12603593.1363061997919.JavaMail.root@redhat.com> <782268481.12604851.1363062748244.JavaMail.root@redhat.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <782268481.12604851.1363062748244.JavaMail.root@redhat.com> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1363068424 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124962 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Tue, Mar 12, 2013 at 12:32:28AM -0400, CAI Qian wrote: > Just came across when running xfstests using 3.9-rc2 kernel on a power7 > box with addition of this patch which fixed a known issue, > http://people.redhat.com/qcai/stable/01-fix-double-fetch-hlist.patch > > The log shows it was happened around test case 370 with > TEST_PARAM_BLKSIZE = 2048 That doesn't sound like xfstests. it only has 305 tests, and no parameters like TEST_PARAM_BLKSIZE.... > Some more information: > xfsprogs version = 3.1.10 > number of CPUs = 32 > Swap Size = 4047 MB > Mem Size = 4046 M > > Still reproducing and bisecting, so this is just a head-up to see if > helps. > > CAI Qian > > [31797.113368] XFS (loop1): xfs_trans_ail_delete_bulk: attempting to delete a log item that is not in the AIL > [31797.113383] XFS (loop1): xfs_do_force_shutdown(0x2) called from line 743 of file fs/xfs/xfs_trans_ail.c. Return address = 0xd000000000f22838 Shutdown for an in-memory problem of some kind.... > [31817.508411] XFS (loop0): Mounting Filesystem > [31817.566235] XFS (loop0): Ending clean mount > [31819.094713] XFS (loop0): Mounting Filesystem > [31819.152248] XFS (loop0): Ending clean mount > [31819.348238] XFS (loop1): Mounting Filesystem > [31819.349879] XFS (loop1): Ending clean mount > [31819.561366] XFS (loop0): Mounting Filesystem > [31819.616607] XFS (loop0): Ending clean mount > [31819.990833] XFS (loop1): Mounting Filesystem > [31819.992652] XFS (loop1): Ending clean mount > [31819.992768] XFS (loop1): Quotacheck needed: Please wait. > [31820.051134] XFS (loop1): Quotacheck: Done. > [31832.534868] Unable to handle kernel paging request for data at address 0x5841474900000001 And after remounting the filesystemi a couple of times, it's tried to follow an AGI buffer header (magic # XAGI, seqno = 1) as though it was a pointer. I can't think of why that would be executed.... > [31832.534881] Faulting instruction address: 0xc0000000001f8070 > [31832.534888] Oops: Kernel access of bad area, sig: 11 [#1] > [31832.534891] SMP NR_CPUS=1024 NUMA pSeries > [31832.534899] Modules linked in: tun(F) binfmt_misc(F) hidp(F) cmtp(F) kernelcapi(F) rfcomm(F) l2tp_ppp(F) l2tp_netlink(F) l2tp_core(F) bnep(F) nfc(F) af_802154(F) pppoe(F) pppox(F) ppp_generic(F) slhc(F) rds(F) af_key(F) atm(F) sctp(F) ip6table_filter(F) ip6_tables(F) iptable_filter(F) ip_tables(F) btrfs(F) raid6_pq(F) xor(F) vfat(F) fat(F) nfsv3(F) nfs_acl(F) nfnetlink_log(F) nfnetlink(F) bluetooth(F) rfkill(F) nfsv2(F) nfs(F) dns_resolver(F) lockd(F) sunrpc(F) fscache(F) nf_tproxy_core(F) nls_koi8_u(F) nls_cp932(F) ts_kmp(F) fuse(F) sg(F) ibmveth(F) xfs(F) libcrc32c(F) sd_mod(F) crc_t10dif(F) ibmvscsi(F) scsi_transport_srp(F) scsi_tgt(F) dm_mirror(F) dm_region_hash(F) dm_log(F) dm_mod(F) [last unloaded: ipt_REJECT] > [31832.534978] NIP: c0000000001f8070 LR: c000000000192f6c CTR: c000000000192f50 > [31832.534984] REGS: c0000000f1c125f0 TRAP: 0300 Tainted: GF W (3.9.0-rc2+) > [31832.534989] MSR: 8000000000009032 CR: 24022024 XER: 20000001 > [31832.535003] SOFTE: 0 > [31832.535006] CFAR: c000000000005f1c > [31832.535009] DAR: 5841474900000001, DSISR: 40000000 > [31832.535013] TASK = c00000003f0111c0[16795] 'loop1' THREAD: c0000000f1c10000 CPU: 30 > GPR00: c000000000192f6c c0000000f1c12870 c0000000010f3a48 c0000000fe015a00 > GPR04: 0000000000011220 0000000000000080 00000000000f3aaf c0000000018d5840 > GPR08: 0000000000000000 0000000000000000 0000000000000000 c0000000004e3300 > GPR12: 0000000044024024 c00000000f247800 c0000000010d01b0 0000000000000000 > GPR16: 0000000000000001 0000000000000000 c0000000009d9020 c0000000009d9060 > GPR20: c0000000009d9048 0000000000000020 000000000000007f 0000000000000000 > GPR24: 0000000000000fe0 c0000000010d1020 c0000000fe015a00 0000000000000000 > GPR28: c000000000192f6c 0000000000011220 5841474900000001 c0000000fe015a00 > [31832.535086] NIP [c0000000001f8070] .kmem_cache_alloc+0xb0/0x2d0 > [31832.535092] LR [c000000000192f6c] .mempool_alloc_slab+0x1c/0x30 > [31832.535096] Call Trace: > [31832.535101] [c0000000f1c12870] [0000000000016ac3] 0x16ac3 (unreliable) > [31832.535108] [c0000000f1c12920] [c000000000192f6c] .mempool_alloc_slab+0x1c/0x30 > [31832.535114] [c0000000f1c12990] [c000000000193108] .mempool_alloc+0x88/0x1c0 > [31832.535122] [c0000000f1c12a80] [c0000000004e1824] .scsi_sg_alloc+0x64/0xc0 > [31832.535129] [c0000000f1c12af0] [c0000000003e09f8] .__sg_alloc_table+0xa8/0x190 > [31832.535135] [c0000000f1c12bc0] [c0000000004e15f0] .scsi_alloc_sgtable+0x40/0x90 > [31832.535142] [c0000000f1c12c40] [c0000000004e1668] .scsi_init_sgtable+0x28/0x90 > [31832.535148] [c0000000f1c12cc0] [c0000000004e19e0] .scsi_init_io+0x40/0x1a0 > [31832.535157] [c0000000f1c12d60] [d000000000c02e78] .sd_prep_fn+0x128/0xac0 [sd_mod] > [31832.535164] [c0000000f1c12e20] [c0000000003a611c] .blk_peek_request+0xfc/0x2d0 > [31832.535171] [c0000000f1c12eb0] [c0000000004e2c08] .scsi_request_fn+0xb8/0x6d0 > [31832.535178] [c0000000f1c12fa0] [c00000000039d7c0] .__blk_run_queue+0x50/0x80 > [31832.535184] [c0000000f1c13020] [c0000000003a2184] .queue_unplugged+0xe4/0x100 > [31832.535190] [c0000000f1c130c0] [c0000000003a67d8] .blk_flush_plug_list+0x248/0x2e0 > [31832.535197] [c0000000f1c13180] [c0000000003a6bcc] .blk_queue_bio+0x2fc/0x490 > [31832.535203] [c0000000f1c13230] [c0000000003a436c] .generic_make_request+0x11c/0x180 > [31832.535210] [c0000000f1c132c0] [c0000000003a4484] .submit_bio+0xb4/0x1e0 > [31832.535245] [c0000000f1c13380] [d000000000eaffa0] .xfs_submit_ioend_bio.isra.10+0x70/0x90 [xfs] > [31832.535286] [c0000000f1c133f0] [d000000000eb00f0] .xfs_submit_ioend+0x130/0x190 [xfs] > [31832.535343] [c0000000f1c134a0] [d000000000eb045c] .xfs_vm_writepage+0x30c/0x670 [xfs] > [31832.535349] [c0000000f1c135d0] [c00000000019d050] .__writepage+0x30/0x90 > [31832.535356] [c0000000f1c13650] [c00000000019d728] .write_cache_pages+0x208/0x4f0 > [31832.535362] [c0000000f1c137e0] [c00000000019da5c] .generic_writepages+0x4c/0xa0 > [31832.535395] [c0000000f1c138a0] [d000000000eaea10] .xfs_vm_writepages+0x60/0x90 [xfs] > [31832.535411] [c0000000f1c13930] [c00000000019ee7c] .do_writepages+0x3c/0x70 > [31832.535424] [c0000000f1c139a0] [c0000000001914b8] .__filemap_fdatawrite_range+0x68/0x80 > [31832.535430] [c0000000f1c13a40] [c000000000191610] .filemap_write_and_wait_range+0x70/0xc0 > [31832.535463] [c0000000f1c13ad0] [d000000000eb7970] .xfs_file_fsync+0x60/0x250 [xfs] > [31832.535479] [c0000000f1c13b90] [c00000000024c278] .vfs_fsync+0x48/0x70 > [31832.535497] [c0000000f1c13c00] [c0000000004d299c] .loop_thread+0x3ec/0x5b0 > [31832.535503] [c0000000f1c13d30] [c0000000000b58c8] .kthread+0xe8/0xf0 > [31832.535510] [c0000000f1c13e30] [c000000000009f64] .ret_from_kernel_thread+0x64/0x80 So, looks like memory corruption - a corrupted slab, perhaps? Can you turn on memory poisoning, debugging, etc? Cheers, Dave. -- Dave Chinner david@fromorbit.com From david@fromorbit.com Tue Mar 12 01:20:14 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 616537F56 for ; Tue, 12 Mar 2013 01:20:14 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay1.corp.sgi.com (Postfix) with ESMTP id 2FA9F8F8035 for ; Mon, 11 Mar 2013 23:20:13 -0700 (PDT) X-ASG-Debug-ID: 1363069202-04bdf022984abcd0001-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id TpkSnytZCwDQt3bx for ; Mon, 11 Mar 2013 23:20:03 -0700 (PDT) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AggcAIvHPlF5LKiV/2dsb2JhbABDh0C4DYUWAQKBXBd0glYTHDskDyUFJQM0iBKeaJEVkCQVjXcYH2mDKAOWVJB2gS+Bbyg Received: from ppp121-44-168-149.lns20.syd7.internode.on.net (HELO dastard) ([121.44.168.149]) by ipmail05.adl6.internode.on.net with ESMTP; 12 Mar 2013 16:50:02 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UFIZ8-0000cu-1O for xfs@oss.sgi.com; Tue, 12 Mar 2013 17:20:02 +1100 Date: Tue, 12 Mar 2013 17:20:02 +1100 From: Dave Chinner To: xfs@oss.sgi.com Subject: [ASSERT failure] transaction reservations changes bad? Message-ID: <20130312062001.GJ21651@dastard> X-ASG-Orig-Subj: [ASSERT failure] transaction reservations changes bad? MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1363069203 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124964 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- Folks, I just got this ASSERT failure running xfstests on a 3.1.8 xfsprogs and a 3.9-rc1 kernel running test 297: [ 2593.733005] XFS: Assertion failed: BTOBB(need_bytes) < log->l_logBBsize, file: fs/xfs/xfs_log.c, line: 1451 [ 2593.736988] ------------[ cut here ]------------ [ 2593.738177] kernel BUG at fs/xfs/xfs_message.c:100! [ 2593.739192] invalid opcode: 0000 [#1] SMP [ 2593.740081] Modules linked in: [ 2593.740786] CPU 0 [ 2593.741221] Pid: 1385, comm: mkdir Not tainted 3.8.0-dgc+ #472 Bochs Bochs [ 2593.742630] RIP: 0010:[] [] assfail+0x22/0x30 [ 2593.744173] RSP: 0018:ffff880038c23c98 EFLAGS: 00010292 [ 2593.745234] RAX: 000000000000005f RBX: ffff88003cfec800 RCX: 0000000000005251 [ 2593.746635] RDX: 0000000000005151 RSI: 0000000000000096 RDI: 0000000000000246 [ 2593.748048] RBP: ffff880038c23c98 R08: 000000000000000a R09: 0000000000000889 [ 2593.749471] R10: 0000000000000000 R11: 0000000000000888 R12: 0000000000000dcb [ 2593.750862] R13: ffff88003cfec800 R14: 0000000000000003 R15: 0000000000000001 [ 2593.752276] FS: 00007f0e64cb97a0(0000) GS:ffff88003fc00000(0000) knlGS:0000000000000000 [ 2593.753895] CS: 0010 DS: 0000 ES: 0000 CR0: 000000008005003b [ 2593.755039] CR2: 000000000066c004 CR3: 000000003cf26000 CR4: 00000000000006f0 [ 2593.756472] DR0: 0000000000000000 DR1: 0000000000000000 DR2: 0000000000000000 [ 2593.757877] DR3: 0000000000000000 DR6: 00000000ffff0ff0 DR7: 0000000000000400 [ 2593.759285] Process mkdir (pid: 1385, threadinfo ffff880038c22000, task ffff88003cb483c0) [ 2593.760914] Stack: [ 2593.761345] ffff880038c23cb8 ffffffff814c9a11 ffff88002fa170a8 ffff880007ac7420 [ 2593.762881] ffff880038c23d18 ffffffff814cb608 0000000000000000 000111b838c23fd8 [ 2593.764429] ffff880038c23fd8 ffff8800055733d0 ffff880005573000 0000000000000000 [ 2593.765964] Call Trace: [ 2593.766449] [] xlog_grant_push_ail+0x41/0xf0 [ 2593.767577] [] xfs_log_reserve+0xe8/0x270 [ 2593.768676] [] xfs_trans_reserve+0x2ee/0x300 [ 2593.769832] [] ? _xfs_trans_alloc+0x37/0xa0 [ 2593.770950] [] xfs_create+0x185/0x660 [ 2593.771975] [] ? lookup_real+0x1d/0x60 [ 2593.773028] [] xfs_vn_mknod+0xa6/0x1b0 [ 2593.774093] [] xfs_vn_mkdir+0x16/0x20 [ 2593.775112] [] vfs_mkdir+0x9e/0xf0 [ 2593.776092] [] sys_mkdirat+0x62/0xe0 [ 2593.777111] [] sys_mkdir+0x19/0x20 [ 2593.778084] [] system_call_fastpath+0x16/0x1b [ 2593.779233] Code: e8 f4 fb ff ff 0f 0b 66 90 0f 1f 44 00 00 55 48 89 f1 41 89 d0 48 89 e5 48 89 fa 48 c7 c6 40 f9 f2 81 31 ff 31 c0 e8 1e fc ff ff <0f> 0b 66 66 66 [ 2593.784186] RIP [] assfail+0x22/0x30 [ 2593.785224] RSP [ 2593.786366] ---[ end trace bf0cb9ec29b256a6 ]--- This implies that the permanent transaction reservation ended up larger than the log itself: $ sudo xfs_info /mnt/scratch/ [sudo] password for dave: meta-data=/dev/vdb isize=256 agcount=16, agsize=1441792 blks = sectsz=512 attr=2 data = bsize=512 blocks=23068672, imaxpct=25 = sunit=512 swidth=6144 blks naming =version 2 bsize=4096 ascii-ci=0 log =internal bsize=512 blocks=2560, version=2 = sectsz=512 sunit=512 blks, lazy-count=1 realtime =none extsz=4096 blocks=0, rtextents=0 Can someone please check that the before/after mkdir transaction reservation sizes are unchanged for such a configuration? Cheers, Dave. -- Dave Chinner david@fromorbit.com From david@fromorbit.com Tue Mar 12 01:25:35 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 4AA5A7F51 for ; Tue, 12 Mar 2013 01:25:35 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id 37215304048 for ; Mon, 11 Mar 2013 23:25:35 -0700 (PDT) X-ASG-Debug-ID: 1363069533-04cbb07dbe46be70001-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id myCvVdH3MPUZgRLe for ; Mon, 11 Mar 2013 23:25:33 -0700 (PDT) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AhQcABnJPlF5LKiV/2dsb2JhbABDhz64DYUWAQIBgVkXdIIoAQEBBAEBASQTHBgbCAMYCQ8WDwUTEgM0iBINr3OQJhWNdxgfURiDKAOWVJB2gx4o Received: from ppp121-44-168-149.lns20.syd7.internode.on.net (HELO dastard) ([121.44.168.149]) by ipmail05.adl6.internode.on.net with ESMTP; 12 Mar 2013 16:55:32 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UFIeR-0000dW-W9 for xfs@oss.sgi.com; Tue, 12 Mar 2013 17:25:32 +1100 Date: Tue, 12 Mar 2013 17:25:31 +1100 From: Dave Chinner To: xfs@oss.sgi.com Subject: Re: [ASSERT failure] transaction reservations changes bad? Message-ID: <20130312062531.GK21651@dastard> X-ASG-Orig-Subj: Re: [ASSERT failure] transaction reservations changes bad? References: <20130312062001.GJ21651@dastard> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <20130312062001.GJ21651@dastard> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1363069533 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124964 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Tue, Mar 12, 2013 at 05:20:02PM +1100, Dave Chinner wrote: > Folks, > > I just got this ASSERT failure running xfstests on a 3.1.8 xfsprogs > and a 3.9-rc1 kernel running test 297: FYI, it's 100% reproducable here with: # sudo MKFS_OPTIONS="-b size=512" ./check 297 (reproduced on multiple VMs now with the same command line) Cheers, Dave. > > [ 2593.733005] XFS: Assertion failed: BTOBB(need_bytes) < log->l_logBBsize, file: fs/xfs/xfs_log.c, line: 1451 > [ 2593.736988] ------------[ cut here ]------------ > [ 2593.738177] kernel BUG at fs/xfs/xfs_message.c:100! > [ 2593.739192] invalid opcode: 0000 [#1] SMP > [ 2593.740081] Modules linked in: > [ 2593.740786] CPU 0 > [ 2593.741221] Pid: 1385, comm: mkdir Not tainted 3.8.0-dgc+ #472 Bochs Bochs > [ 2593.742630] RIP: 0010:[] [] assfail+0x22/0x30 > [ 2593.744173] RSP: 0018:ffff880038c23c98 EFLAGS: 00010292 > [ 2593.745234] RAX: 000000000000005f RBX: ffff88003cfec800 RCX: 0000000000005251 > [ 2593.746635] RDX: 0000000000005151 RSI: 0000000000000096 RDI: 0000000000000246 > [ 2593.748048] RBP: ffff880038c23c98 R08: 000000000000000a R09: 0000000000000889 > [ 2593.749471] R10: 0000000000000000 R11: 0000000000000888 R12: 0000000000000dcb > [ 2593.750862] R13: ffff88003cfec800 R14: 0000000000000003 R15: 0000000000000001 > [ 2593.752276] FS: 00007f0e64cb97a0(0000) GS:ffff88003fc00000(0000) knlGS:0000000000000000 > [ 2593.753895] CS: 0010 DS: 0000 ES: 0000 CR0: 000000008005003b > [ 2593.755039] CR2: 000000000066c004 CR3: 000000003cf26000 CR4: 00000000000006f0 > [ 2593.756472] DR0: 0000000000000000 DR1: 0000000000000000 DR2: 0000000000000000 > [ 2593.757877] DR3: 0000000000000000 DR6: 00000000ffff0ff0 DR7: 0000000000000400 > [ 2593.759285] Process mkdir (pid: 1385, threadinfo ffff880038c22000, task ffff88003cb483c0) > [ 2593.760914] Stack: > [ 2593.761345] ffff880038c23cb8 ffffffff814c9a11 ffff88002fa170a8 ffff880007ac7420 > [ 2593.762881] ffff880038c23d18 ffffffff814cb608 0000000000000000 000111b838c23fd8 > [ 2593.764429] ffff880038c23fd8 ffff8800055733d0 ffff880005573000 0000000000000000 > [ 2593.765964] Call Trace: > [ 2593.766449] [] xlog_grant_push_ail+0x41/0xf0 > [ 2593.767577] [] xfs_log_reserve+0xe8/0x270 > [ 2593.768676] [] xfs_trans_reserve+0x2ee/0x300 > [ 2593.769832] [] ? _xfs_trans_alloc+0x37/0xa0 > [ 2593.770950] [] xfs_create+0x185/0x660 > [ 2593.771975] [] ? lookup_real+0x1d/0x60 > [ 2593.773028] [] xfs_vn_mknod+0xa6/0x1b0 > [ 2593.774093] [] xfs_vn_mkdir+0x16/0x20 > [ 2593.775112] [] vfs_mkdir+0x9e/0xf0 > [ 2593.776092] [] sys_mkdirat+0x62/0xe0 > [ 2593.777111] [] sys_mkdir+0x19/0x20 > [ 2593.778084] [] system_call_fastpath+0x16/0x1b > [ 2593.779233] Code: e8 f4 fb ff ff 0f 0b 66 90 0f 1f 44 00 00 55 48 89 f1 41 89 d0 48 89 e5 48 89 fa 48 c7 c6 40 f9 f2 81 31 ff 31 c0 e8 1e fc ff ff <0f> 0b 66 66 66 > [ 2593.784186] RIP [] assfail+0x22/0x30 > [ 2593.785224] RSP > [ 2593.786366] ---[ end trace bf0cb9ec29b256a6 ]--- > > This implies that the permanent transaction reservation ended up > larger than the log itself: > > $ sudo xfs_info /mnt/scratch/ > [sudo] password for dave: > meta-data=/dev/vdb isize=256 agcount=16, agsize=1441792 blks > = sectsz=512 attr=2 > data = bsize=512 blocks=23068672, imaxpct=25 > = sunit=512 swidth=6144 blks > naming =version 2 bsize=4096 ascii-ci=0 > log =internal bsize=512 blocks=2560, version=2 > = sectsz=512 sunit=512 blks, lazy-count=1 > realtime =none extsz=4096 blocks=0, rtextents=0 > > Can someone please check that the before/after mkdir transaction > reservation sizes are unchanged for such a configuration? > > Cheers, > > Dave. > -- > Dave Chinner > david@fromorbit.com > > _______________________________________________ > xfs mailing list > xfs@oss.sgi.com > http://oss.sgi.com/mailman/listinfo/xfs > > -- > This message has been scanned for viruses and > dangerous content by MailScanner, and is > believed to be clean. > > -- Dave Chinner david@fromorbit.com From qcai@redhat.com Tue Mar 12 01:34:16 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 90C2C7F67 for ; Tue, 12 Mar 2013 01:34:16 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay2.corp.sgi.com (Postfix) with ESMTP id 5E804304053 for ; Mon, 11 Mar 2013 23:34:16 -0700 (PDT) X-ASG-Debug-ID: 1363070054-04bdf022974acb60001-NocioJ Received: from mx3-phx2.redhat.com (mx3-phx2.redhat.com [209.132.183.24]) by cuda.sgi.com with ESMTP id GDiBrbJRulilZNBF for ; Mon, 11 Mar 2013 23:34:14 -0700 (PDT) X-Barracuda-Envelope-From: qcai@redhat.com X-Barracuda-Apparent-Source-IP: 209.132.183.24 Received: from zmail14.collab.prod.int.phx2.redhat.com (zmail14.collab.prod.int.phx2.redhat.com [10.5.83.16]) by mx3-phx2.redhat.com (8.13.8/8.13.8) with ESMTP id r2C6Y7eQ003533; Tue, 12 Mar 2013 02:34:07 -0400 Date: Tue, 12 Mar 2013 02:34:07 -0400 (EDT) From: CAI Qian To: Dave Chinner Cc: xfs@oss.sgi.com Message-ID: <1032405745.12626044.1363070047355.JavaMail.root@redhat.com> In-Reply-To: <20130312060701.GI21651@dastard> Subject: Re: 3.9-rc2 xfs panic MIME-Version: 1.0 X-ASG-Orig-Subj: Re: 3.9-rc2 xfs panic Content-Type: text/plain; charset=utf-8 Content-Transfer-Encoding: 7bit X-Originating-IP: [10.66.13.149] X-Mailer: Zimbra 7.2.0_GA_2669 (ZimbraWebClient - FF3.0 (Linux)/7.2.0_GA_2669) X-Barracuda-Connect: mx3-phx2.redhat.com[209.132.183.24] X-Barracuda-Start-Time: 1363070054 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124964 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- ----- Original Message ----- > From: "Dave Chinner" > To: "CAI Qian" > Cc: xfs@oss.sgi.com > Sent: Tuesday, March 12, 2013 2:07:01 PM > Subject: Re: 3.9-rc2 xfs panic > > On Tue, Mar 12, 2013 at 12:32:28AM -0400, CAI Qian wrote: > > Just came across when running xfstests using 3.9-rc2 kernel on a > > power7 > > box with addition of this patch which fixed a known issue, > > http://people.redhat.com/qcai/stable/01-fix-double-fetch-hlist.patch > > > > The log shows it was happened around test case 370 with > > TEST_PARAM_BLKSIZE = 2048 > > That doesn't sound like xfstests. it only has 305 tests, and no > parameters like TEST_PARAM_BLKSIZE.... Sorry, it is a typo, test case 270 not 370. TEST_PARAM_BLKSIZE was from an internal wrapper to be used to create new filessytem not from the original xfstests. Apologize for that, Dave. > > > Some more information: > > xfsprogs version = 3.1.10 > > number of CPUs = 32 > > Swap Size = 4047 MB > > Mem Size = 4046 M > > > > Still reproducing and bisecting, so this is just a head-up to see > > if > > helps. > > > > CAI Qian > > > > [31797.113368] XFS (loop1): xfs_trans_ail_delete_bulk: attempting > > to delete a log item that is not in the AIL > > [31797.113383] XFS (loop1): xfs_do_force_shutdown(0x2) called from > > line 743 of file fs/xfs/xfs_trans_ail.c. Return address = > > 0xd000000000f22838 > > Shutdown for an in-memory problem of some kind.... > > > [31817.508411] XFS (loop0): Mounting Filesystem > > [31817.566235] XFS (loop0): Ending clean mount > > [31819.094713] XFS (loop0): Mounting Filesystem > > [31819.152248] XFS (loop0): Ending clean mount > > [31819.348238] XFS (loop1): Mounting Filesystem > > [31819.349879] XFS (loop1): Ending clean mount > > [31819.561366] XFS (loop0): Mounting Filesystem > > [31819.616607] XFS (loop0): Ending clean mount > > [31819.990833] XFS (loop1): Mounting Filesystem > > [31819.992652] XFS (loop1): Ending clean mount > > [31819.992768] XFS (loop1): Quotacheck needed: Please wait. > > [31820.051134] XFS (loop1): Quotacheck: Done. > > [31832.534868] Unable to handle kernel paging request for data at > > address 0x5841474900000001 > > And after remounting the filesystemi a couple of times, it's tried > to follow an AGI buffer header (magic # XAGI, seqno = 1) as though > it was a pointer. I can't think of why that would be > executed.... > > > [31832.534881] Faulting instruction address: 0xc0000000001f8070 > > [31832.534888] Oops: Kernel access of bad area, sig: 11 [#1] > > [31832.534891] SMP NR_CPUS=1024 NUMA pSeries > > [31832.534899] Modules linked in: tun(F) binfmt_misc(F) hidp(F) > > cmtp(F) kernelcapi(F) rfcomm(F) l2tp_ppp(F) l2tp_netlink(F) > > l2tp_core(F) bnep(F) nfc(F) af_802154(F) pppoe(F) pppox(F) > > ppp_generic(F) slhc(F) rds(F) af_key(F) atm(F) sctp(F) > > ip6table_filter(F) ip6_tables(F) iptable_filter(F) ip_tables(F) > > btrfs(F) raid6_pq(F) xor(F) vfat(F) fat(F) nfsv3(F) nfs_acl(F) > > nfnetlink_log(F) nfnetlink(F) bluetooth(F) rfkill(F) nfsv2(F) > > nfs(F) dns_resolver(F) lockd(F) sunrpc(F) fscache(F) > > nf_tproxy_core(F) nls_koi8_u(F) nls_cp932(F) ts_kmp(F) fuse(F) > > sg(F) ibmveth(F) xfs(F) libcrc32c(F) sd_mod(F) crc_t10dif(F) > > ibmvscsi(F) scsi_transport_srp(F) scsi_tgt(F) dm_mirror(F) > > dm_region_hash(F) dm_log(F) dm_mod(F) [last unloaded: ipt_REJECT] > > [31832.534978] NIP: c0000000001f8070 LR: c000000000192f6c CTR: > > c000000000192f50 > > [31832.534984] REGS: c0000000f1c125f0 TRAP: 0300 Tainted: GF > > W (3.9.0-rc2+) > > [31832.534989] MSR: 8000000000009032 CR: > > 24022024 XER: 20000001 > > [31832.535003] SOFTE: 0 > > [31832.535006] CFAR: c000000000005f1c > > [31832.535009] DAR: 5841474900000001, DSISR: 40000000 > > [31832.535013] TASK = c00000003f0111c0[16795] 'loop1' THREAD: > > c0000000f1c10000 CPU: 30 > > GPR00: c000000000192f6c c0000000f1c12870 c0000000010f3a48 > > c0000000fe015a00 > > GPR04: 0000000000011220 0000000000000080 00000000000f3aaf > > c0000000018d5840 > > GPR08: 0000000000000000 0000000000000000 0000000000000000 > > c0000000004e3300 > > GPR12: 0000000044024024 c00000000f247800 c0000000010d01b0 > > 0000000000000000 > > GPR16: 0000000000000001 0000000000000000 c0000000009d9020 > > c0000000009d9060 > > GPR20: c0000000009d9048 0000000000000020 000000000000007f > > 0000000000000000 > > GPR24: 0000000000000fe0 c0000000010d1020 c0000000fe015a00 > > 0000000000000000 > > GPR28: c000000000192f6c 0000000000011220 5841474900000001 > > c0000000fe015a00 > > [31832.535086] NIP [c0000000001f8070] .kmem_cache_alloc+0xb0/0x2d0 > > [31832.535092] LR [c000000000192f6c] .mempool_alloc_slab+0x1c/0x30 > > [31832.535096] Call Trace: > > [31832.535101] [c0000000f1c12870] [0000000000016ac3] 0x16ac3 > > (unreliable) > > [31832.535108] [c0000000f1c12920] [c000000000192f6c] > > .mempool_alloc_slab+0x1c/0x30 > > [31832.535114] [c0000000f1c12990] [c000000000193108] > > .mempool_alloc+0x88/0x1c0 > > [31832.535122] [c0000000f1c12a80] [c0000000004e1824] > > .scsi_sg_alloc+0x64/0xc0 > > [31832.535129] [c0000000f1c12af0] [c0000000003e09f8] > > .__sg_alloc_table+0xa8/0x190 > > [31832.535135] [c0000000f1c12bc0] [c0000000004e15f0] > > .scsi_alloc_sgtable+0x40/0x90 > > [31832.535142] [c0000000f1c12c40] [c0000000004e1668] > > .scsi_init_sgtable+0x28/0x90 > > [31832.535148] [c0000000f1c12cc0] [c0000000004e19e0] > > .scsi_init_io+0x40/0x1a0 > > [31832.535157] [c0000000f1c12d60] [d000000000c02e78] > > .sd_prep_fn+0x128/0xac0 [sd_mod] > > [31832.535164] [c0000000f1c12e20] [c0000000003a611c] > > .blk_peek_request+0xfc/0x2d0 > > [31832.535171] [c0000000f1c12eb0] [c0000000004e2c08] > > .scsi_request_fn+0xb8/0x6d0 > > [31832.535178] [c0000000f1c12fa0] [c00000000039d7c0] > > .__blk_run_queue+0x50/0x80 > > [31832.535184] [c0000000f1c13020] [c0000000003a2184] > > .queue_unplugged+0xe4/0x100 > > [31832.535190] [c0000000f1c130c0] [c0000000003a67d8] > > .blk_flush_plug_list+0x248/0x2e0 > > [31832.535197] [c0000000f1c13180] [c0000000003a6bcc] > > .blk_queue_bio+0x2fc/0x490 > > [31832.535203] [c0000000f1c13230] [c0000000003a436c] > > .generic_make_request+0x11c/0x180 > > [31832.535210] [c0000000f1c132c0] [c0000000003a4484] > > .submit_bio+0xb4/0x1e0 > > [31832.535245] [c0000000f1c13380] [d000000000eaffa0] > > .xfs_submit_ioend_bio.isra.10+0x70/0x90 [xfs] > > [31832.535286] [c0000000f1c133f0] [d000000000eb00f0] > > .xfs_submit_ioend+0x130/0x190 [xfs] > > [31832.535343] [c0000000f1c134a0] [d000000000eb045c] > > .xfs_vm_writepage+0x30c/0x670 [xfs] > > [31832.535349] [c0000000f1c135d0] [c00000000019d050] > > .__writepage+0x30/0x90 > > [31832.535356] [c0000000f1c13650] [c00000000019d728] > > .write_cache_pages+0x208/0x4f0 > > [31832.535362] [c0000000f1c137e0] [c00000000019da5c] > > .generic_writepages+0x4c/0xa0 > > [31832.535395] [c0000000f1c138a0] [d000000000eaea10] > > .xfs_vm_writepages+0x60/0x90 [xfs] > > [31832.535411] [c0000000f1c13930] [c00000000019ee7c] > > .do_writepages+0x3c/0x70 > > [31832.535424] [c0000000f1c139a0] [c0000000001914b8] > > .__filemap_fdatawrite_range+0x68/0x80 > > [31832.535430] [c0000000f1c13a40] [c000000000191610] > > .filemap_write_and_wait_range+0x70/0xc0 > > [31832.535463] [c0000000f1c13ad0] [d000000000eb7970] > > .xfs_file_fsync+0x60/0x250 [xfs] > > [31832.535479] [c0000000f1c13b90] [c00000000024c278] > > .vfs_fsync+0x48/0x70 > > [31832.535497] [c0000000f1c13c00] [c0000000004d299c] > > .loop_thread+0x3ec/0x5b0 > > [31832.535503] [c0000000f1c13d30] [c0000000000b58c8] > > .kthread+0xe8/0xf0 > > [31832.535510] [c0000000f1c13e30] [c000000000009f64] > > .ret_from_kernel_thread+0x64/0x80 > > So, looks like memory corruption - a corrupted slab, perhaps? Can > you turn on memory poisoning, debugging, etc? > > Cheers, > > Dave. > -- > Dave Chinner > david@fromorbit.com > From david@fromorbit.com Tue Mar 12 02:46:13 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 1AF277F3F for ; Tue, 12 Mar 2013 02:46:13 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay3.corp.sgi.com (Postfix) with ESMTP id A54EEAC002 for ; Tue, 12 Mar 2013 00:46:12 -0700 (PDT) X-ASG-Debug-ID: 1363074370-04bdf022964b2540001-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id 7uwaokqq9zpfZZZS for ; Tue, 12 Mar 2013 00:46:11 -0700 (PDT) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AhUcAJncPlF5LKiV/2dsb2JhbABDhze4DYUWAQIBgVQXdIIoAQEEATocIwwECAMRBAEBAQklDwUlAxMOE4gNBQ2vbZAzFY13GB9KBwaDOgOWVIEfj1eBL4FvKA Received: from ppp121-44-168-149.lns20.syd7.internode.on.net (HELO dastard) ([121.44.168.149]) by ipmail05.adl6.internode.on.net with ESMTP; 12 Mar 2013 18:16:10 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UFJuS-0000p4-FS; Tue, 12 Mar 2013 18:46:08 +1100 Date: Tue, 12 Mar 2013 18:46:08 +1100 From: Dave Chinner To: CAI Qian Cc: xfs@oss.sgi.com Subject: Re: 3.9-rc2 xfs panic Message-ID: <20130312074608.GL21651@dastard> X-ASG-Orig-Subj: Re: 3.9-rc2 xfs panic References: <20130312060701.GI21651@dastard> <1032405745.12626044.1363070047355.JavaMail.root@redhat.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <1032405745.12626044.1363070047355.JavaMail.root@redhat.com> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1363074370 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124968 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Tue, Mar 12, 2013 at 02:34:07AM -0400, CAI Qian wrote: > > > ----- Original Message ----- > > From: "Dave Chinner" > > To: "CAI Qian" > > Cc: xfs@oss.sgi.com > > Sent: Tuesday, March 12, 2013 2:07:01 PM > > Subject: Re: 3.9-rc2 xfs panic > > > > On Tue, Mar 12, 2013 at 12:32:28AM -0400, CAI Qian wrote: > > > Just came across when running xfstests using 3.9-rc2 kernel on a > > > power7 > > > box with addition of this patch which fixed a known issue, > > > http://people.redhat.com/qcai/stable/01-fix-double-fetch-hlist.patch > > > > > > The log shows it was happened around test case 370 with > > > TEST_PARAM_BLKSIZE = 2048 > > > > That doesn't sound like xfstests. it only has 305 tests, and no > > parameters like TEST_PARAM_BLKSIZE.... > Sorry, it is a typo, test case 270 not 370. TEST_PARAM_BLKSIZE was > from an internal wrapper to be used to create new filessytem not from the > original xfstests. OK, so that means you're testing 2k filesystem block size on a 64k page size machine? Are you running with CONFIG_XFS_DEBUG=y? > > So, looks like memory corruption - a corrupted slab, perhaps? Can > > you turn on memory poisoning, debugging, etc? Does this turn anything up? Cheers, Dave. -- Dave Chinner david@fromorbit.com From qcai@redhat.com Tue Mar 12 03:04:23 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 5193C7F3F for ; Tue, 12 Mar 2013 03:04:23 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id 416FE304059 for ; Tue, 12 Mar 2013 01:04:23 -0700 (PDT) X-ASG-Debug-ID: 1363075458-04cbb07dbf473110001-NocioJ Received: from mx4-phx2.redhat.com (mx4-phx2.redhat.com [209.132.183.25]) by cuda.sgi.com with ESMTP id qhNylVaajHq9EH2Y for ; Tue, 12 Mar 2013 01:04:19 -0700 (PDT) X-Barracuda-Envelope-From: qcai@redhat.com X-Barracuda-Apparent-Source-IP: 209.132.183.25 Received: from zmail14.collab.prod.int.phx2.redhat.com (zmail14.collab.prod.int.phx2.redhat.com [10.5.83.16]) by mx4-phx2.redhat.com (8.13.8/8.13.8) with ESMTP id r2C84Bms012265; Tue, 12 Mar 2013 04:04:11 -0400 Date: Tue, 12 Mar 2013 04:04:11 -0400 (EDT) From: CAI Qian To: Dave Chinner Cc: xfs@oss.sgi.com Message-ID: <924669527.12643828.1363075451534.JavaMail.root@redhat.com> In-Reply-To: <20130312074608.GL21651@dastard> Subject: Re: 3.9-rc2 xfs panic MIME-Version: 1.0 X-ASG-Orig-Subj: Re: 3.9-rc2 xfs panic Content-Type: text/plain; charset=utf-8 Content-Transfer-Encoding: 7bit X-Originating-IP: [10.66.13.149] X-Mailer: Zimbra 7.2.0_GA_2669 (ZimbraWebClient - FF3.0 (Linux)/7.2.0_GA_2669) X-Barracuda-Connect: mx4-phx2.redhat.com[209.132.183.25] X-Barracuda-Start-Time: 1363075458 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124970 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- ----- Original Message ----- > From: "Dave Chinner" > To: "CAI Qian" > Cc: xfs@oss.sgi.com > Sent: Tuesday, March 12, 2013 3:46:08 PM > Subject: Re: 3.9-rc2 xfs panic > > On Tue, Mar 12, 2013 at 02:34:07AM -0400, CAI Qian wrote: > > > > > > ----- Original Message ----- > > > From: "Dave Chinner" > > > To: "CAI Qian" > > > Cc: xfs@oss.sgi.com > > > Sent: Tuesday, March 12, 2013 2:07:01 PM > > > Subject: Re: 3.9-rc2 xfs panic > > > > > > On Tue, Mar 12, 2013 at 12:32:28AM -0400, CAI Qian wrote: > > > > Just came across when running xfstests using 3.9-rc2 kernel on > > > > a > > > > power7 > > > > box with addition of this patch which fixed a known issue, > > > > http://people.redhat.com/qcai/stable/01-fix-double-fetch-hlist.patch > > > > > > > > The log shows it was happened around test case 370 with > > > > TEST_PARAM_BLKSIZE = 2048 > > > > > > That doesn't sound like xfstests. it only has 305 tests, and no > > > parameters like TEST_PARAM_BLKSIZE.... > > Sorry, it is a typo, test case 270 not 370. TEST_PARAM_BLKSIZE was > > from an internal wrapper to be used to create new filessytem not > > from the > > original xfstests. > > OK, so that means you're testing 2k filesystem block size on a 64k > page size machine? Looks like so. Would that be a problem? TEST_PARAM_TEST_DEV not specified; using loopback file TEST_PARAM_SCRATCH_DEV not specified; using loopback file meta-data=/dev/loop0 isize=256 agcount=4, agsize=655360 blks = sectsz=512 attr=2, projid32bit=0 data = bsize=2048 blocks=2621440, imaxpct=25 = sunit=0 swidth=0 blks naming =version 2 bsize=4096 ascii-ci=0 log =internal log bsize=2048 blocks=5120, version=2 = sectsz=512 sunit=0 blks, lazy-count=1 realtime =none extsz=4096 blocks=0, rtextents=0 TEST_DEV=/dev/loop0 # device containing TEST PARTITION TEST_DIR=/mnt/testarea/test # mount point of TEST PARTITION SCRATCH_DEV=/dev/loop1 # device containing SCRATCH PARTITION SCRATCH_MNT=/mnt/testarea/scratch # mount point for SCRATCH PARTITION SCRATCH_LOGDEV= # optional external log for SCRATCH PARTITION SCRATCH_RTDEV= # optional realtime device for SCRATCH PARTITION TMPFS_MOUNT_OPTIONS="" # scratch mount options for tmpfs TEST_FS_MOUNT_OPTS="" # test mount options for tmpfs > Are you running with CONFIG_XFS_DEBUG=y? # CONFIG_XFS_DEBUG is not set I can enable this if I can reproduce it. > > > > So, looks like memory corruption - a corrupted slab, perhaps? Can > > > you turn on memory poisoning, debugging, etc? > > Does this turn anything up? It is still running. Unsure if it is reproducible at this point. CAI Qian > > Cheers, > > Dave. > -- > Dave Chinner > david@fromorbit.com > From jeff.liu@oracle.com Tue Mar 12 03:08:40 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 0B9D07F54 for ; Tue, 12 Mar 2013 03:08:40 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay3.corp.sgi.com (Postfix) with ESMTP id AC0FCAC004 for ; Tue, 12 Mar 2013 01:08:36 -0700 (PDT) X-ASG-Debug-ID: 1363075715-04bdf022984b3f90001-NocioJ Received: from userp1040.oracle.com (userp1040.oracle.com [156.151.31.81]) by cuda.sgi.com with ESMTP id szTpKpCOTGgv6F3L (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO) for ; Tue, 12 Mar 2013 01:08:35 -0700 (PDT) X-Barracuda-Envelope-From: jeff.liu@oracle.com X-Barracuda-Apparent-Source-IP: 156.151.31.81 Received: from ucsinet22.oracle.com (ucsinet22.oracle.com [156.151.31.94]) by userp1040.oracle.com (Sentrion-MTA-4.3.1/Sentrion-MTA-4.3.1) with ESMTP id r2C88QCe001903 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=OK); Tue, 12 Mar 2013 08:08:27 GMT Received: from acsmt358.oracle.com (acsmt358.oracle.com [141.146.40.158]) by ucsinet22.oracle.com (8.14.4+Sun/8.14.4) with ESMTP id r2C88QtR006164 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=NO); Tue, 12 Mar 2013 08:08:26 GMT Received: from abhmt115.oracle.com (abhmt115.oracle.com [141.146.116.67]) by acsmt358.oracle.com (8.12.11.20060308/8.12.11) with ESMTP id r2C88QdO027239; Tue, 12 Mar 2013 03:08:26 -0500 Received: from [192.168.1.103] (/114.248.196.15) by default (Oracle Beehive Gateway v4.0) with ESMTP ; Tue, 12 Mar 2013 01:08:25 -0700 Message-ID: <513EE274.6090808@oracle.com> Date: Tue, 12 Mar 2013 16:08:20 +0800 From: Jeff Liu User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:16.0) Gecko/20121028 Thunderbird/16.0.2 MIME-Version: 1.0 To: Dave Chinner CC: xfs@oss.sgi.com Subject: Re: [ASSERT failure] transaction reservations changes bad? References: <20130312062001.GJ21651@dastard> <20130312062531.GK21651@dastard> X-ASG-Orig-Subj: Re: [ASSERT failure] transaction reservations changes bad? In-Reply-To: <20130312062531.GK21651@dastard> Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Source-IP: ucsinet22.oracle.com [156.151.31.94] X-Barracuda-Connect: userp1040.oracle.com[156.151.31.81] X-Barracuda-Start-Time: 1363075715 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124970 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- Hi Dave, On 03/12/2013 02:25 PM, Dave Chinner wrote: > On Tue, Mar 12, 2013 at 05:20:02PM +1100, Dave Chinner wrote: >> Folks, >> >> I just got this ASSERT failure running xfstests on a 3.1.8 xfsprogs >> and a 3.9-rc1 kernel running test 297: > > FYI, it's 100% reproducable here with: > > # sudo MKFS_OPTIONS="-b size=512" ./check 297 > > (reproduced on multiple VMs now with the same command line) > > Cheers, > > Dave. > >> >> [ 2593.733005] XFS: Assertion failed: BTOBB(need_bytes) < log->l_logBBsize, file: fs/xfs/xfs_log.c, line: 1451 >> [ 2593.736988] ------------[ cut here ]------------ >> [ 2593.738177] kernel BUG at fs/xfs/xfs_message.c:100! >> [ 2593.739192] invalid opcode: 0000 [#1] SMP >> [ 2593.740081] Modules linked in: >> [ 2593.740786] CPU 0 >> [ 2593.741221] Pid: 1385, comm: mkdir Not tainted 3.8.0-dgc+ #472 Bochs Bochs >> [ 2593.742630] RIP: 0010:[] [] assfail+0x22/0x30 >> [ 2593.744173] RSP: 0018:ffff880038c23c98 EFLAGS: 00010292 >> [ 2593.745234] RAX: 000000000000005f RBX: ffff88003cfec800 RCX: 0000000000005251 >> [ 2593.746635] RDX: 0000000000005151 RSI: 0000000000000096 RDI: 0000000000000246 >> [ 2593.748048] RBP: ffff880038c23c98 R08: 000000000000000a R09: 0000000000000889 >> [ 2593.749471] R10: 0000000000000000 R11: 0000000000000888 R12: 0000000000000dcb >> [ 2593.750862] R13: ffff88003cfec800 R14: 0000000000000003 R15: 0000000000000001 >> [ 2593.752276] FS: 00007f0e64cb97a0(0000) GS:ffff88003fc00000(0000) knlGS:0000000000000000 >> [ 2593.753895] CS: 0010 DS: 0000 ES: 0000 CR0: 000000008005003b >> [ 2593.755039] CR2: 000000000066c004 CR3: 000000003cf26000 CR4: 00000000000006f0 >> [ 2593.756472] DR0: 0000000000000000 DR1: 0000000000000000 DR2: 0000000000000000 >> [ 2593.757877] DR3: 0000000000000000 DR6: 00000000ffff0ff0 DR7: 0000000000000400 >> [ 2593.759285] Process mkdir (pid: 1385, threadinfo ffff880038c22000, task ffff88003cb483c0) >> [ 2593.760914] Stack: >> [ 2593.761345] ffff880038c23cb8 ffffffff814c9a11 ffff88002fa170a8 ffff880007ac7420 >> [ 2593.762881] ffff880038c23d18 ffffffff814cb608 0000000000000000 000111b838c23fd8 >> [ 2593.764429] ffff880038c23fd8 ffff8800055733d0 ffff880005573000 0000000000000000 >> [ 2593.765964] Call Trace: >> [ 2593.766449] [] xlog_grant_push_ail+0x41/0xf0 >> [ 2593.767577] [] xfs_log_reserve+0xe8/0x270 >> [ 2593.768676] [] xfs_trans_reserve+0x2ee/0x300 >> [ 2593.769832] [] ? _xfs_trans_alloc+0x37/0xa0 >> [ 2593.770950] [] xfs_create+0x185/0x660 >> [ 2593.771975] [] ? lookup_real+0x1d/0x60 >> [ 2593.773028] [] xfs_vn_mknod+0xa6/0x1b0 >> [ 2593.774093] [] xfs_vn_mkdir+0x16/0x20 >> [ 2593.775112] [] vfs_mkdir+0x9e/0xf0 >> [ 2593.776092] [] sys_mkdirat+0x62/0xe0 >> [ 2593.777111] [] sys_mkdir+0x19/0x20 >> [ 2593.778084] [] system_call_fastpath+0x16/0x1b >> [ 2593.779233] Code: e8 f4 fb ff ff 0f 0b 66 90 0f 1f 44 00 00 55 48 89 f1 41 89 d0 48 89 e5 48 89 fa 48 c7 c6 40 f9 f2 81 31 ff 31 c0 e8 1e fc ff ff <0f> 0b 66 66 66 >> [ 2593.784186] RIP [] assfail+0x22/0x30 >> [ 2593.785224] RSP >> [ 2593.786366] ---[ end trace bf0cb9ec29b256a6 ]--- >> >> This implies that the permanent transaction reservation ended up >> larger than the log itself: >> >> $ sudo xfs_info /mnt/scratch/ >> [sudo] password for dave: >> meta-data=/dev/vdb isize=256 agcount=16, agsize=1441792 blks >> = sectsz=512 attr=2 >> data = bsize=512 blocks=23068672, imaxpct=25 >> = sunit=512 swidth=6144 blks >> naming =version 2 bsize=4096 ascii-ci=0 >> log =internal bsize=512 blocks=2560, version=2 >> = sectsz=512 sunit=512 blks, lazy-count=1 >> realtime =none extsz=4096 blocks=0, rtextents=0 >> >> Can someone please check that the before/after mkdir transaction >> reservation sizes are unchanged for such a configuration? I just did a quick verification. # mkfs.xfs -V mkfs.xfs version 3.1.8 # uname -a Linux koala 3.9.0-rc1 #80 SMP Tue Mar 12 15:06:39 CST 2013 x86_64 x86_64 x86_64 GNU/Linux # mkfs.xfs -f -b size=512 /dev/sda6 meta-data=/dev/sda6 isize=256 agcount=4, agsize=5242880 blks = sectsz=512 attr=2, projid32bit=0 data = bsize=512 blocks=20971520, imaxpct=25 = sunit=0 swidth=0 blks naming =version 2 bsize=4096 ascii-ci=0 log =internal log bsize=512 blocks=20480, version=2 = sectsz=512 sunit=0 blks, lazy-count=1 realtime =none extsz=4096 blocks=0, rtextents=0 The reservation size does not changed, both are 70072 bytes: [ 230.905092] xfs_calc_mkdir_reservation: res=70072 bytes. However, I can always reproducing this issue with '"MKFS_OPTIONS=-b size=512" ./check 297' as well. Thanks, -Jeff From hpj@urpla.net Tue Mar 12 04:02:34 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 8B6587F54 for ; Tue, 12 Mar 2013 04:02:34 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id 7AAB5304043 for ; Tue, 12 Mar 2013 02:02:31 -0700 (PDT) X-ASG-Debug-ID: 1363078948-04cbb07dbe4774a0001-NocioJ Received: from moutng.kundenserver.de (moutng.kundenserver.de [212.227.17.9]) by cuda.sgi.com with ESMTP id UoBu2Pv2ej3TBEJt (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Tue, 12 Mar 2013 02:02:29 -0700 (PDT) X-Barracuda-Envelope-From: hpj@urpla.net X-Barracuda-Apparent-Source-IP: 212.227.17.9 Received: from lisa (p5B2A4BF5.dip0.t-ipconnect.de [91.42.75.245]) by mrelayeu.kundenserver.de (node=mreu0) with ESMTP (Nemesis) id 0LuYSK-1Ux6431xOi-00zl1z; Tue, 12 Mar 2013 10:02:19 +0100 Received: from localhost (localhost [127.0.0.1]) by tyrex.lisa.loc (Postfix) with ESMTP id 090161B971B00; Tue, 12 Mar 2013 10:02:19 +0100 (CET) X-Virus-Scanned: amavisd-new at lisa.loc Received: from tyrex.lisa.loc ([127.0.0.1]) by localhost (tyrex.lisa.loc [127.0.0.1]) (amavisd-new, port 10024) with LMTP id RD4gbegDE6TG; Tue, 12 Mar 2013 10:02:10 +0100 (CET) From: Hans-Peter Jansen To: Mark Tinguely Cc: david@fromorbit.com, xfs@oss.sgi.com Subject: Re: Fwd: xfs_reno Date: Tue, 12 Mar 2013 10:02:09 +0100 X-ASG-Orig-Subj: Re: Fwd: xfs_reno Message-ID: <5202910.jIRzyplXT6@xrated> User-Agent: KMail/4.10.1 (Linux/3.4.33-2.24-desktop; KDE/4.10.1; x86_64; ; ) In-Reply-To: <513E5113.60508@sgi.com> References: <20351675.Zy117sIl8Z@xrated> <513E5113.60508@sgi.com> MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable Content-Type: text/plain; charset="utf-8" X-Provags-ID: V02:K0:kT/T+9j0gvkoAZ3ca9pexkC7SaEVMyvPm2P2KieStjf rvVXeYijVKiXy+EkI1NMd2fN5YKEWVZ+wBg7CWiSUiUx9eIMX7 lEZiV7JjTDUe6+ZysmD6k6bb9tNQrafZplZJUWG7nB9oH1tpVm SGwoyOvToJiMfa6fW78p+qgMbQLbB7/8WOFBpe789tvPJRBklR YLB/4JRxvhwpFhUAw5NLGEixUnUynqvM0NLOZK0VVGFH3V6L65 UgHcGeBylns6zFlbH9cDtWTrXG22KZzw/ZFht3SjiGBvHKbGYN JfIqmiyNT/hwOnQuxsHMKkziUGZYEEEjgPIk/p31svKDRcaiQ= = X-Barracuda-Connect: moutng.kundenserver.de[212.227.17.9] X-Barracuda-Start-Time: 1363078949 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124974 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- Am Montag, 11. M=C3=A4rz 2013, 16:48:03 schrieb Mark Tinguely: > On 03/06/13 08:55, Hans-Peter Jansen wrote: > > Hi Dave, > >=20 > > I tried to gather Barrys SOB, but failed so far. His trace ends in = 2009 > > google wise. > >=20 > > How is this case usually handled? > >=20 > > Here's the current state of things. > >=20 > > Cheers, > > Pete > >=20 > >=20 > > ---------- Weitergeleitete Nachricht ---------- > >=20 > > Betreff: xfs_reno > > Datum: Mittwoch, 6. M=C3=A4rz 2013, 12:52:19 > > Von: Hans-Peter Jansen > > An: bnaujok@sgi.com > >=20 > > Hi Barry, > >=20 > > attached is a slightly mangled version of your xfs_reno tool, that = I badly > > needed recently. While at it, I plan to submit it, as it saved my *= ss. > > Thanks. > >=20 > > Apart from relocation to xfsprogs, I just changed this > >=20 > > + log_message(LOG_DEBUG, "%s: %llu %lu %s", msg, node->ino, > > + node->numpaths, node->paths[0]); > >=20 > > from %llu to %lu for the node->numpaths argument. It might still be= wrong, > > as numpath is defined as nlink_t which is a __u32 type, but the %s > > printed garbage like this: > >=20 > > Scanning directory tree... > > xfs_reno: add_node_path: ino 8611163235, path > > /work/dlbase/hosts/11.2/pico/var/run/screens > > xfs_reno: add_node_path: ino 8611163233, path > > /work/dlbase/hosts/11.2/pico/var/run/pcscd/pcscd.events > > xfs_reno: add_node_path: ino 8611163234, path > > /work/dlbase/hosts/11.2/pico/var/run/uscreens > > xfs_reno: nodehash: 8611163233 692488159933497345 =EF=BF=BD=EF=BF=BD= ]=EF=BF=BD=EF=BF=BDf=EF=BF=BDe=EF=BF=BD > > xfs_reno: nodehash: 8611163234 692366801337581569 =EF=BF=BD=EF=BF=BD= ]=EF=BF=BD=EF=BF=BDf=EF=BF=BDe=EF=BF=BD > > xfs_reno: nodehash: 8611163235 692223830466232321 =EF=BF=BD=EF=BF=BD= ]=EF=BF=BD=EF=BF=BDf=EF=BF=BDe=EF=BF=BD > >=20 > > I guess, gcc is smart enough to see, that the struct members overla= p here, > > and prints the paths[0] argument as a %llu value. What do you think= ? > >=20 > > Anyway, I will revise this during the course of creating a xlstests= test > > for xfs_reno... > >=20 > > Do you allow me to add your Signed-off-by to this patch? > >=20 > > If you want to build this, apply both patches to xfsprogs. > >=20 > > TIA, > > Pete >=20 > Have you been getting "Out of memory" warnings on your runs? I am. No, I would have mentioned them. But I guess, my file systems are tiny=20= compared to yours. The affected FS have 2.8T and 4.1T, with former with= many=20 small files and directories, the latter with many 2G files. =20 > Compiling, I get the warnings about having "\r" in the strings. For e= xample: >=20 > reno/xfs_reno.c:1415: internationalized messages should not contain t= he > `\r' escape sequence Well, that's for the spin wheel, that might have interesting effects, w= hen=20 localized to right-to-left languages... > ---------- > I wonder if we should add a temp directory option. It seems to want t= o > use the parent directory of the directory as a temporary.=20 Without digging into this, I can only guess, but the whole point of xfs= _reno=20 is relocating the inodes on the FS in question *without* copying files = around.=20 Using a separate TEMP defeats this purpose, don't it? It might be in order to add a note to the man page to not try to use it= in "cross mount operation" scenarios. > Below is the > result of running xfs_reno on the target directory is "/mnt/xxx > (changing the \r to <^M>\n for the email): >=20 > xfs_reno: directory: 128 1 /mn<^M> > xfs_reno: /mnt/xfs_reno_epdaJc: Cannet set target extended attributes= <^M> > xfs_reno: failed to rename: '/mnt/xxx/origin' to > '/mnt/xfs_reno_NXQLWI/origin' > <^M> > xfs_reno: unable to move directory contents: /mnt/xxx to > /mnt/xfs_reno_NXQLWI > <^M> > xfs_reno: Cannot stat /mnt/xfs_reno_epdaJc: Inappropriate ioctl for d= evice >=20 > <^M> > xfs_reno: unable to duplicate directory attributes: /mnt/xfs_reno_epd= aJc > t/xxx > ------ > /mnt is not an XFS filesystem. When mounting on the root, say /mnt, t= he > message look like: >=20 > xfs_reno: Cannot stat //xfs_reno_epdaJc: Inappropriate ioctl for devi= ce You lost me here. What I can say, is that using eg. "xfs_reno -vpn /wor= k",=20 hence on the mount point directly, did as advertised. Cheers, Pete From Martin@lichtvoll.de Tue Mar 12 04:58:04 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 13A4D7F55 for ; Tue, 12 Mar 2013 04:58:04 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay3.corp.sgi.com (Postfix) with ESMTP id 96DE6AC006 for ; Tue, 12 Mar 2013 02:58:03 -0700 (PDT) X-ASG-Debug-ID: 1363082278-04cb6c2b04486eb0001-NocioJ Received: from mail.lichtvoll.de (mondschein.lichtvoll.de [194.150.191.11]) by cuda.sgi.com with ESMTP id iGJYUJJDJBuM62BC for ; Tue, 12 Mar 2013 02:57:58 -0700 (PDT) X-Barracuda-Envelope-From: Martin@lichtvoll.de X-Barracuda-Apparent-Source-IP: 194.150.191.11 Received: from merkaba.localnet (blackhole.teamix.net [194.150.191.251]) by mail.lichtvoll.de (Postfix) with ESMTPSA id 47EC5C5; Tue, 12 Mar 2013 10:57:39 +0100 (CET) From: Martin Steigerwald To: xfs@oss.sgi.com Subject: Re: XFS filesystem corruption Date: Tue, 12 Mar 2013 10:57:51 +0100 X-ASG-Orig-Subj: Re: XFS filesystem corruption User-Agent: KMail/1.13.7 (Linux/3.9.0-rc2-tp520; KDE/4.9.5; x86_64; ; ) Cc: Dave Chinner , Julien FERRERO , Ric Wheeler References: <20130307232214.GY23616@dastard> (sfid-20130308_003651_720717_B9D6B992) In-Reply-To: <20130307232214.GY23616@dastard> MIME-Version: 1.0 Content-Type: Text/Plain; charset="iso-8859-1" Content-Transfer-Encoding: quoted-printable Message-Id: <201303121057.52092.Martin@lichtvoll.de> X-Barracuda-Connect: mondschein.lichtvoll.de[194.150.191.11] X-Barracuda-Start-Time: 1363082278 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124978 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- Am Freitag, 8. M=E4rz 2013 schrieb Dave Chinner: > On Thu, Mar 07, 2013 at 02:15:31PM +0100, Julien FERRERO wrote: > > > We actually test brutal "Power off" for xfs, ext4 and other file > > > systems. If your storage is configured properly and you have > > > barriers enabled, they all pass without corruption. > > >=20 > > > What hardware raid cards can do is to hide a volatile write cache. > > > Either on the raid HBA itself or, even worse, on the backend disks > > > behind the card. S-ata disks tend to default to write cache enabled > > > and need to be checked especially careful (sas drives tend to be > > > write cache disabled by default). > > > >=20 > > > > Write cache is supposed to be disabled on the H/W RAID (according to > > hdparm) and barrier are correctly enabled since xfs does not report > > any warning at mount. > > > >=20 > > > > The odd thing is we never see this with kernel 2.6.18 where barriers > > weren't yet available. >=20 > Yes they were. XFS had barrier support added in 2.6.15. I thought this was 2.6.16? Or was that the kernel where it became usable du= e=20 to the generic write barrier part being merged while the XFS one was ready= =20 earlier? I still remember the XFS filesystem crashes I had back then that went away= =20 with disabling the write cache of the drive in my ThinkPad T42 back then an= d=20 where solved with 2.6.17, whereas 2.6.17.7 solved a directory corruption=20 issue introduced with 2.6.17. Thus I always recommended at least 2.6.17.7 i= n=20 case of write barrier usage with XFS. Thanks, =2D-=20 Martin 'Helios' Steigerwald - http://www.Lichtvoll.de GPG: 03B0 0D6C 0040 0710 4AFA B82F 991B EAAC A599 84C7 From david@fromorbit.com Tue Mar 12 05:23:43 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 2D6457F5A for ; Tue, 12 Mar 2013 05:23:43 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay3.corp.sgi.com (Postfix) with ESMTP id BF450AC004 for ; Tue, 12 Mar 2013 03:23:39 -0700 (PDT) X-ASG-Debug-ID: 1363083817-04bdf022964bf4f0001-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id FqZfstGlHj6fSPIl for ; Tue, 12 Mar 2013 03:23:38 -0700 (PDT) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AhQcACYBP1F5LKiV/2dsb2JhbABDhyu4G4UWAQIBgUgXdIIoAQEFOhwjDAQIAxEEAQEBCSUPBSUDEw4TiBINr0uQKRWNdxgfSgcGgzoDllSBH49XgS+Bbyg Received: from ppp121-44-168-149.lns20.syd7.internode.on.net (HELO dastard) ([121.44.168.149]) by ipmail05.adl6.internode.on.net with ESMTP; 12 Mar 2013 20:53:37 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UFMMp-00017V-Ux; Tue, 12 Mar 2013 21:23:35 +1100 Date: Tue, 12 Mar 2013 21:23:35 +1100 From: Dave Chinner To: CAI Qian Cc: xfs@oss.sgi.com Subject: Re: 3.9-rc2 xfs panic Message-ID: <20130312102335.GM21651@dastard> X-ASG-Orig-Subj: Re: 3.9-rc2 xfs panic References: <20130312074608.GL21651@dastard> <924669527.12643828.1363075451534.JavaMail.root@redhat.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <924669527.12643828.1363075451534.JavaMail.root@redhat.com> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1363083817 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124980 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Tue, Mar 12, 2013 at 04:04:11AM -0400, CAI Qian wrote: > > > ----- Original Message ----- > > From: "Dave Chinner" > > To: "CAI Qian" > > Cc: xfs@oss.sgi.com > > Sent: Tuesday, March 12, 2013 3:46:08 PM > > Subject: Re: 3.9-rc2 xfs panic > > > > On Tue, Mar 12, 2013 at 02:34:07AM -0400, CAI Qian wrote: > > > > > > > > > ----- Original Message ----- > > > > From: "Dave Chinner" > > > > To: "CAI Qian" > > > > Cc: xfs@oss.sgi.com > > > > Sent: Tuesday, March 12, 2013 2:07:01 PM > > > > Subject: Re: 3.9-rc2 xfs panic > > > > > > > > On Tue, Mar 12, 2013 at 12:32:28AM -0400, CAI Qian wrote: > > > > > Just came across when running xfstests using 3.9-rc2 kernel on > > > > > a > > > > > power7 > > > > > box with addition of this patch which fixed a known issue, > > > > > http://people.redhat.com/qcai/stable/01-fix-double-fetch-hlist.patch > > > > > > > > > > The log shows it was happened around test case 370 with > > > > > TEST_PARAM_BLKSIZE = 2048 > > > > > > > > That doesn't sound like xfstests. it only has 305 tests, and no > > > > parameters like TEST_PARAM_BLKSIZE.... > > > Sorry, it is a typo, test case 270 not 370. TEST_PARAM_BLKSIZE was > > > from an internal wrapper to be used to create new filessytem not > > > from the > > > original xfstests. > > > > OK, so that means you're testing 2k filesystem block size on a 64k > > page size machine? > Looks like so. Would that be a problem? It shouldn't be a problem, but nobody else is testing with that config and so you could be seeing problems nobody sees. Cheers, Dave. -- Dave Chinner david@fromorbit.com From david@fromorbit.com Tue Mar 12 05:31:45 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 70F297F3F for ; Tue, 12 Mar 2013 05:31:45 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay2.corp.sgi.com (Postfix) with ESMTP id 4E448304039 for ; Tue, 12 Mar 2013 03:31:42 -0700 (PDT) X-ASG-Debug-ID: 1363084299-04cb6c2b04489340001-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id eliRcM5opp2kpRQL for ; Tue, 12 Mar 2013 03:31:40 -0700 (PDT) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AhMcAG4CP1F5LKiV/2dsb2JhbABDhyu4G4UWAQIBgUgXdIIoAQEEATocIwULCAMYCQwDFg8FJQMhE4gNBa9ikCUVjVEmGB9KBwoOgygDllSQdoMeKA Received: from ppp121-44-168-149.lns20.syd7.internode.on.net (HELO dastard) ([121.44.168.149]) by ipmail05.adl6.internode.on.net with ESMTP; 12 Mar 2013 21:01:39 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UFMUc-00018G-Il; Tue, 12 Mar 2013 21:31:38 +1100 Date: Tue, 12 Mar 2013 21:31:38 +1100 From: Dave Chinner To: Jeff Liu Cc: xfs@oss.sgi.com Subject: Re: [ASSERT failure] transaction reservations changes bad? Message-ID: <20130312103138.GN21651@dastard> X-ASG-Orig-Subj: Re: [ASSERT failure] transaction reservations changes bad? References: <20130312062001.GJ21651@dastard> <20130312062531.GK21651@dastard> <513EE274.6090808@oracle.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <513EE274.6090808@oracle.com> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1363084299 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124980 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Tue, Mar 12, 2013 at 04:08:20PM +0800, Jeff Liu wrote: > Hi Dave, > > On 03/12/2013 02:25 PM, Dave Chinner wrote: > > On Tue, Mar 12, 2013 at 05:20:02PM +1100, Dave Chinner wrote: > >> Folks, > >> > >> I just got this ASSERT failure running xfstests on a 3.1.8 xfsprogs > >> and a 3.9-rc1 kernel running test 297: > > > > FYI, it's 100% reproducable here with: > > > > # sudo MKFS_OPTIONS="-b size=512" ./check 297 > > > > (reproduced on multiple VMs now with the same command line) .... > >> This implies that the permanent transaction reservation ended up > >> larger than the log itself: > >> > >> $ sudo xfs_info /mnt/scratch/ > >> [sudo] password for dave: > >> meta-data=/dev/vdb isize=256 agcount=16, agsize=1441792 blks > >> = sectsz=512 attr=2 > >> data = bsize=512 blocks=23068672, imaxpct=25 > >> = sunit=512 swidth=6144 blks > >> naming =version 2 bsize=4096 ascii-ci=0 > >> log =internal bsize=512 blocks=2560, version=2 > >> = sectsz=512 sunit=512 blks, lazy-count=1 > >> realtime =none extsz=4096 blocks=0, rtextents=0 > >> > >> Can someone please check that the before/after mkdir transaction > >> reservation sizes are unchanged for such a configuration? > I just did a quick verification. > > # mkfs.xfs -V > mkfs.xfs version 3.1.8 > > # uname -a > Linux koala 3.9.0-rc1 #80 SMP Tue Mar 12 15:06:39 CST 2013 x86_64 x86_64 x86_64 GNU/Linux > > # mkfs.xfs -f -b size=512 /dev/sda6 > meta-data=/dev/sda6 isize=256 agcount=4, agsize=5242880 blks > = sectsz=512 attr=2, projid32bit=0 > data = bsize=512 blocks=20971520, imaxpct=25 > = sunit=0 swidth=0 blks > naming =version 2 bsize=4096 ascii-ci=0 > log =internal log bsize=512 blocks=20480, version=2 > = sectsz=512 sunit=0 blks, lazy-count=1 > realtime =none extsz=4096 blocks=0, rtextents=0 That's a different mkfs.xfs config to what test 297 is using. Different log size, different AG count, no log stripe unit, etc. 297 is using: scratch_mkfs_xfs -d agcount=16,su=256k,sw=12 -l su=256k,size=2560b And when I add the extra MKFS_OPTIONS in it actually is: # mkfs.xfs -b size=512 -d agcount=16,su=256k,sw=12 -l su=256k,size=2560b > The reservation size does not changed, both are 70072 bytes: > > [ 230.905092] xfs_calc_mkdir_reservation: res=70072 bytes. And it's not just the calculation that I'm worried about here - it's the actual reservation that ends up in the ticket that matters as that is fed into the code that has triggered the assert. The value in the ticket takes into account log stripe units and other roundings, so it's typically much larger than just the reservation calculation itself... > However, I can always reproducing this issue with > '"MKFS_OPTIONS=-b size=512" ./check 297' as well. Can you check that it also fails on kernels prior to the reservation changes? That will rule out it being a recent regression... Cheers, Dave. -- Dave Chinner david@fromorbit.com From ole.tange.work@gmail.com Tue Mar 12 05:41:50 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=FREEMAIL_FROM,T_DKIM_INVALID autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 673A07F61 for ; Tue, 12 Mar 2013 05:41:50 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay1.corp.sgi.com (Postfix) with ESMTP id 55C2F8F8033 for ; Tue, 12 Mar 2013 03:41:47 -0700 (PDT) X-ASG-Debug-ID: 1363084905-04cbb07dbc47e0f0001-NocioJ Received: from mail-da0-f51.google.com (mail-da0-f51.google.com [209.85.210.51]) by cuda.sgi.com with ESMTP id IeBYlqC2YdCZWE37 (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Tue, 12 Mar 2013 03:41:46 -0700 (PDT) X-Barracuda-Envelope-From: ole.tange.work@gmail.com X-Barracuda-Apparent-Source-IP: 209.85.210.51 X-Barracuda-IPDD: Level1 [gmail.com/209.85.210.51] Received: by mail-da0-f51.google.com with SMTP id z17so1210348dal.24 for ; Tue, 12 Mar 2013 03:41:45 -0700 (PDT) X-Barracuda-IPDD: Level1 [gmail.com/209.85.210.51] X-Barracuda-IPDD: Level1 [gmail.com/209.85.210.51] DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20120113; h=x-received:mime-version:sender:in-reply-to:references:from:date :x-google-sender-auth:message-id:subject:to:cc:content-type; bh=z/o7Q+cXpH1EPDjBUw3U+MZ5/s4FxLqu/4FIyEiNisE=; b=UkFcdT7jQlz/ImiGl/fo04G19t4+nRjYbPMIkPNAK6PQ/iAuyeoxMKQc2riXupk1wJ Up3IIp/fMTA2IIE3CaG/UCc/iYUGZVz0LcVTUjSIQtmd5aGEaSw7Q8mkNFmzpdEPU6CL S1zYp+7t6tjKqd75qK+4ooj2bKe1uVT4GubRx4F/icyVCU+xQB4UkQKZlURhCQiCyPeh 1rCuuX6V/yRKn//sX+pdRZy+1je+kH7bGYk/rQXZd+CTmZvd8oWCHeBnQ25mGmYJ5mnh F/Yx0zX5MwPEZJz0Yi9BjfFDLUzphih3QkE2pYLAa3hMl5++ilBaKUi3yShWm48XcbCd 8BvA== X-Received: by 10.68.241.102 with SMTP id wh6mr37277405pbc.150.1363084905243; Tue, 12 Mar 2013 03:41:45 -0700 (PDT) MIME-Version: 1.0 Sender: ole.tange.work@gmail.com Received: by 10.68.51.226 with HTTP; Tue, 12 Mar 2013 03:41:25 -0700 (PDT) In-Reply-To: <513A4AEC.4010202@sandeen.net> References: <512FA67D.2090708@sandeen.net> <5130DB54.9030503@sandeen.net> <5134BBA4.3060305@sandeen.net> <513A4AEC.4010202@sandeen.net> From: Ole Tange Date: Tue, 12 Mar 2013 11:41:25 +0100 X-Google-Sender-Auth: MptTTvIMIWDyX_z84YNHFZVhiSI Message-ID: Subject: Re: xfs_repair segfaults To: Eric Sandeen X-ASG-Orig-Subj: Re: xfs_repair segfaults Cc: xfs@oss.sgi.com Content-Type: text/plain; charset=ISO-8859-1 X-Barracuda-Connect: mail-da0-f51.google.com[209.85.210.51] X-Barracuda-Start-Time: 1363084906 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=DKIM_SIGNED, DKIM_VERIFIED X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124980 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature On Fri, Mar 8, 2013 at 9:32 PM, Eric Sandeen wrote: > On 3/8/13 4:21 AM, Ole Tange wrote: >> On Mon, Mar 4, 2013 at 4:20 PM, Eric Sandeen wrote: >> >>> 2) so you could run a "real" non-"n" xfs_repair on a metadata image as a more realistic dry run : >> I get >> filenames like: >> >> /mnt/disk/??5?z+hEOgl/?7?Psr1?aIHS??+??z=ozK/8_0/???d) >> 5JCG?eiBd?EVsNF'A?v?m?f;Fi6v)d>/?M%?A??J?)B> X[Df?Wm^[?f 4| > > By default, xfs_metadump scrambles filenames, so nothing to worry > about (it's for privacy reasons). If you use the "-o" option it'll keep > it in the clear. Ahh. To me that does not conform to Principle of Least Astonishment - especially since some of the filenames were not obfuscated. I would have been less surprised if the files were named: Use_-o_for_real_file_names_XXXXXXXX Use_-o_for_real_dir_names_XXXXXXXX where XXXXXXXX is just a unique number. /Ole From Martin@lichtvoll.de Tue Mar 12 05:42:21 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 2897A7F61 for ; Tue, 12 Mar 2013 05:42:21 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay1.corp.sgi.com (Postfix) with ESMTP id 085CA8F8040 for ; Tue, 12 Mar 2013 03:42:20 -0700 (PDT) X-ASG-Debug-ID: 1363084939-04cbb07dbc47e170001-NocioJ Received: from mail.lichtvoll.de (mondschein.lichtvoll.de [194.150.191.11]) by cuda.sgi.com with ESMTP id rH7GPGhvEtJZszRJ for ; Tue, 12 Mar 2013 03:42:19 -0700 (PDT) X-Barracuda-Envelope-From: Martin@lichtvoll.de X-Barracuda-Apparent-Source-IP: 194.150.191.11 Received: from merkaba.localnet (blackhole.teamix.net [194.150.191.251]) by mail.lichtvoll.de (Postfix) with ESMTPSA id 868AAC5; Tue, 12 Mar 2013 11:42:00 +0100 (CET) From: Martin Steigerwald To: xfs@oss.sgi.com, stan@hardwarefreak.com Subject: Re: XFS filesystem corruption Date: Tue, 12 Mar 2013 11:42:13 +0100 X-ASG-Orig-Subj: Re: XFS filesystem corruption User-Agent: KMail/1.13.7 (Linux/3.9.0-rc2-tp520; KDE/4.9.5; x86_64; ; ) Cc: Ric Wheeler , Julien FERRERO References: <5137CD46.6070909@redhat.com> <5139A3B6.3040805@hardwarefreak.com> (sfid-20130308_132012_037479_915CAB49) In-Reply-To: <5139A3B6.3040805@hardwarefreak.com> MIME-Version: 1.0 Content-Type: Text/Plain; charset="iso-8859-1" Content-Transfer-Encoding: quoted-printable Message-Id: <201303121142.13980.Martin@lichtvoll.de> X-Barracuda-Connect: mondschein.lichtvoll.de[194.150.191.11] X-Barracuda-Start-Time: 1363084939 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124980 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- Am Freitag, 8. M=E4rz 2013 schrieb Stan Hoeppner: > If the techs are determined to hard cut power because they don't have > the time or the knowledge to do a clean shutdown, it may be well worth > your time/effort to write a script and teach the field techs to execute > it, before flipping the master switch. Your simple script would run as > root, or you'd need to do some sudo foo within, and would contain > something like: >=20 > #! /bin/sh > sync > echo 2 > /proc/sys/vm/drop_caches > echo "Ready for power down." mount -o remount,ro /your/mount/point One can at least try. Maybe some "service stop" commands before that. But then, if using a script like this, why not just type "halt"? Heck, Linux kernel / userspace / distro developers prepared safe shutdown=20 already, so why not use it? Another idea: On Debian Usually on Ctrl-Alt-Delete on a TTY get a shutdown: # What to do when CTRL-ALT-DEL is pressed. ca:12345:ctrlaltdel:/sbin/shutdown -t1 -a -r now Then you plug a keyboard to the server and tell the local admins to just=20 press Ctrl-Alt-Del in order to shutdown the server instead of the power=20 button. But heck, even just pressing the power button for a short period of time=20 should work. In Debian it does. So you can just tip the power button. So, I do see not much of a reason to not shutdown the server properly. Ciao, =2D-=20 Martin 'Helios' Steigerwald - http://www.Lichtvoll.de GPG: 03B0 0D6C 0040 0710 4AFA B82F 991B EAAC A599 84C7 From eflorac@intellique.com Tue Mar 12 05:54:59 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 22D1F7F54 for ; Tue, 12 Mar 2013 05:54:59 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay2.corp.sgi.com (Postfix) with ESMTP id 0CA03304053 for ; Tue, 12 Mar 2013 03:54:59 -0700 (PDT) X-ASG-Debug-ID: 1363085695-04cb6c2b0348ab90001-NocioJ Received: from smtp3-g21.free.fr (smtp3-g21.free.fr [212.27.42.3]) by cuda.sgi.com with ESMTP id z6psu6xeGyQzpsgj for ; Tue, 12 Mar 2013 03:54:56 -0700 (PDT) X-Barracuda-Envelope-From: eflorac@intellique.com X-Barracuda-Apparent-Source-IP: 212.27.42.3 Received: from galadriel.home (unknown [82.235.234.79]) by smtp3-g21.free.fr (Postfix) with ESMTP id 23AA9A6280; Tue, 12 Mar 2013 11:54:50 +0100 (CET) Date: Tue, 12 Mar 2013 11:54:42 +0100 From: Emmanuel Florac To: Julien FERRERO Cc: stan@hardwarefreak.com, Ric Wheeler , xfs@oss.sgi.com Subject: Re: XFS filesystem corruption Message-ID: <20130312115442.1918d592@galadriel.home> X-ASG-Orig-Subj: Re: XFS filesystem corruption In-Reply-To: References: <20130306161519.2c28d911@galadriel.home> <20130306232100.6286f640@galadriel.home> <5137CD46.6070909@redhat.com> <5139A3B6.3040805@hardwarefreak.com> <5139D792.4090304@redhat.com> <513A350A.508@hardwarefreak.com> <20130309091152.GH23616@dastard> <513B84AD.2000603@hardwarefreak.com> <20130310224536.GK23616@dastard> <513D1D51.7010905@hardwarefreak.com> Organization: Intellique X-Mailer: Claws Mail 3.7.8 (GTK+ 2.24.4; i686-pc-linux-gnu) Mime-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: quoted-printable X-Barracuda-Connect: smtp3-g21.free.fr[212.27.42.3] X-Barracuda-Start-Time: 1363085695 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124982 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- Le Mon, 11 Mar 2013 10:25:13 +0100 vous =C3=A9criviez: > That is the main reason I asked. I google for regression / issue with > XFS in 2.6.35 but I didn't find anything. My hope was that someone > from this mailing list would remember it (if such a regression did > exist of course). I don't, but I had at last one serious corruption under 2.6.35.13 (though it was related to hard drive woes). --=20 ------------------------------------------------------------------------ Emmanuel Florac | Direction technique | Intellique | | +33 1 78 94 84 02 ------------------------------------------------------------------------ From jack@suse.cz Tue Mar 12 06:01:07 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id ABF6B7F67 for ; Tue, 12 Mar 2013 06:01:07 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay1.corp.sgi.com (Postfix) with ESMTP id 992118F804B for ; Tue, 12 Mar 2013 04:01:04 -0700 (PDT) X-ASG-Debug-ID: 1363086062-04cbb07dbd47f7e0001-NocioJ Received: from mx2.suse.de (cantor2.suse.de [195.135.220.15]) by cuda.sgi.com with ESMTP id oT9WEu2QmJ3p8vAY for ; Tue, 12 Mar 2013 04:01:02 -0700 (PDT) X-Barracuda-Envelope-From: jack@suse.cz X-Barracuda-Apparent-Source-IP: 195.135.220.15 Received: from relay1.suse.de (unknown [195.135.220.254]) by mx2.suse.de (Postfix) with ESMTP id 21726A4F01; Tue, 12 Mar 2013 12:01:01 +0100 (CET) Received: by quack.suse.cz (Postfix, from userid 1000) id B2A582067D; Tue, 12 Mar 2013 12:01:00 +0100 (CET) Date: Tue, 12 Mar 2013 12:01:00 +0100 From: Jan Kara To: Dave Chinner Cc: Jan Kara , xfs@oss.sgi.com Subject: Re: Pathological allocation pattern with direct IO Message-ID: <20130312110100.GC13152@quack.suse.cz> X-ASG-Orig-Subj: Re: Pathological allocation pattern with direct IO References: <20130306202210.GA1318@quack.suse.cz> <20130307050325.GS23616@dastard> <20130307102406.GA6723@quack.suse.cz> <20130308013525.GZ23616@dastard> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <20130308013525.GZ23616@dastard> User-Agent: Mutt/1.5.20 (2009-06-14) X-Barracuda-Connect: cantor2.suse.de[195.135.220.15] X-Barracuda-Start-Time: 1363086062 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124982 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Fri 08-03-13 12:35:25, Dave Chinner wrote: > On Thu, Mar 07, 2013 at 11:24:06AM +0100, Jan Kara wrote: > > But really I was wondering about usefulness of XFS_ALLOCTYPE_NEAR_BNO > > heuristic. Sure the seek time depends on the distance so if we are speaking > > about allocating single extent then XFS_ALLOCTYPE_NEAR_BNO is useful but > > once that strategy would allocate two or three consecutive extents you've > > lost all the benefit and you would be better off if you started allocating > > from the start of the free space. > Hence repeated backwards allocation is, in many cases, desirable > behaviour, and in others it doesn't make any difference. And with it > being easy to work around for the few cases where it is tripped over > on aging filesystems, there hasn't been a great deal of need to > change the behaviour. Thanks for explanation! > > Obviously we don't know the future in > > advance but this resembles a classical problem from approximations > > algorithms theory (rent-or-buy problem where renting corresponds to > > allocating from the end of free space and taking the smaller cost while > > buying corresponds to allocation from the beginning, taking the higher > > cost, but expecting you won't have to pay anything in future). And the > > theory of approximation algorithms tells us that once we pay for renting as > > much as buying will cost us, then at that moment it is advantageous to buy > > and that gives you 2-approximation algorithm (you can do even better - > > factor 1.58 approximation - if you use randomization but I don't think we > > want to go that way). > > Way too mathematical for me, because... > > > So from this I'd say that switching off > > XFS_ALLOCTYPE_NEAR_BNO allocation once you've allocated 2-3 extents > > backwards would work of better on average. > > .... common sense says that this is true. > > I haven't looked to solve this problem in the past 5 years because > extent size hints are such a simple way of mitigating the problem. > However, given that I know how this allocation code works whole lot > better than I did 5 years ago, I think I can see an easy way to > avoid this repeated backwards allocation pattern when extending > files. > > What we have right now is this used space/free space layout > with the allocation context prev/want when extending the file: > > > free extent free extent > +-----------------+ prev ...... +--------------+ > +------+ > +------+ > want > > This is what we'll ask for as a XFS_ALLOCTYPE_THIS_BNO allocation, > but that is going to fail because there is no free space at wantbno. > This then falls back to XFS_ALLOCTYPE_NEAR_BNO with the same wantbno > target, and it selects the free extent before prev. > > If we then we look at what is happening xfs_alloc_compute_diff(), we > have wantbno > freebno, and wantbno > freeend, so we end up in > either of these two cases: > > } else if (alignment > 1) { > newbno1 = roundup(freeend - wantlen, alignment); > if (newbno1 > freeend - wantlen && > newbno1 - alignment >= freebno) > newbno1 -= alignment; > else if (newbno1 >= freeend) > newbno1 = NULLAGBLOCK; > } else > newbno1 = freeend - wantlen; > > > Either way, the resultant extent that is cut out of the free extent > is this: > > free extent > +-----------------+ prev > +------+ > +------+ > +------+ want > got > > And hence we end up in a backwards allocation pattern. After > repeated iterations of this, we end up this a pattern like this: > > free extent > +-----------------+ prev prev-1 prev-2 > +------+------+------+ > +------+ > +------+ want > got > > and so is likely to lead to an extended run of backwards allocation > for sequential ascending offsets. So, we would need to detect this Yup, that's what I understood in the code and saw in my experiments... > pattern in xfs_bmap_adjacent, where the wantbno is determined for > EOF allocation. That's a bit complex - we'll need to do extent tree > lookups because we need more information than we've got from the > initial lookup. > > I do not want to get this information from the initial lookup and > pass it up to xfs_bmap_adjacent() because we are already using lots > of stack through this path and adding another 70-odd bytes for > another couple of extent maps is not going to fly. So to detect > backwards allocation, we'd have to take the CPU hit of doing another > lookup and then analysing the results for backwards allocation. That > can be done, but I'm wondering if we even need to detect this > case... > > I suspect we don't even need to detect the backwards allocation > pattern at all - if we are falling back from an > XFS_ALLOCTYPE_THIS_BNO allocation, we know that the target cannot be > allocated and so we *might* end up doing a backwards allocation. > Hence I don't think it will not hurt at all to simply say "select > the start of the next candidate free extent" for a file data > allocations in this case. That would completely avoid needing to > detect repeated backwards allocations and ensure that subsequent > allocations after the backwards jump to the start of the large free > extent then go forwards as intended... Yes, I was wondering about whether this strategy won't be good enough as well. But there's one case I'm afraid of: Suppose you have a small file so that it gets written out in one request and fits in a single extent of blocks. Then it is somewhat advantageous to allocate from the end of the free extent because that is closer to the inode and thus reduces inode-to-data seek time. That's why I was suggesting maybe we could use this logic only for larger files or something like that. Hum, maybe if we didn't use this strategy for initial file extent, it would be enough. That's already handled specially in the allocator so it shouldn't be a problem to detect. What do you think? > And because we only do XFS_ALLOCTYPE_THIS_BNO allocations on data > allocations when extending file, adding such a flag won't affect > random write or metadata allocation patterns.... > > So, once we've decided that backward allocation is possible, all we > need to do is inform XFS_ALLOCTYPE_NEAR_BNO/xfs_alloc_compute_diff() > to select the start of the free extent it finds rather than select > the tail of it. That will mean that rather than consume the entire > free extent in small chunks via backwards allocation, we'll do one > large backwards step and then consume the free extent in the > forwards direction instead. Yes, this would work great for me. Honza -- Jan Kara SUSE Labs, CR From jeff.liu@oracle.com Tue Mar 12 06:06:02 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id CE6957F69 for ; Tue, 12 Mar 2013 06:06:01 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay3.corp.sgi.com (Postfix) with ESMTP id 5DFD7AC007 for ; Tue, 12 Mar 2013 04:05:58 -0700 (PDT) X-ASG-Debug-ID: 1363086356-04cb6c2b0348b950001-NocioJ Received: from aserp1040.oracle.com (aserp1040.oracle.com [141.146.126.69]) by cuda.sgi.com with ESMTP id vtnjjUTmAOWNbewI (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO) for ; Tue, 12 Mar 2013 04:05:57 -0700 (PDT) X-Barracuda-Envelope-From: jeff.liu@oracle.com X-Barracuda-Apparent-Source-IP: 141.146.126.69 Received: from ucsinet22.oracle.com (ucsinet22.oracle.com [156.151.31.94]) by aserp1040.oracle.com (Sentrion-MTA-4.3.1/Sentrion-MTA-4.3.1) with ESMTP id r2CB5nww013918 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=OK); Tue, 12 Mar 2013 11:05:49 GMT Received: from acsmt356.oracle.com (acsmt356.oracle.com [141.146.40.156]) by ucsinet22.oracle.com (8.14.4+Sun/8.14.4) with ESMTP id r2CB5mw9009625 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=NO); Tue, 12 Mar 2013 11:05:48 GMT Received: from abhmt103.oracle.com (abhmt103.oracle.com [141.146.116.55]) by acsmt356.oracle.com (8.12.11.20060308/8.12.11) with ESMTP id r2CB5mT7028532; Tue, 12 Mar 2013 06:05:48 -0500 Received: from [192.168.1.103] (/114.248.196.15) by default (Oracle Beehive Gateway v4.0) with ESMTP ; Tue, 12 Mar 2013 04:05:47 -0700 Message-ID: <513F0C07.1060000@oracle.com> Date: Tue, 12 Mar 2013 19:05:43 +0800 From: Jeff Liu User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:16.0) Gecko/20121028 Thunderbird/16.0.2 MIME-Version: 1.0 To: Dave Chinner CC: xfs@oss.sgi.com Subject: Re: [ASSERT failure] transaction reservations changes bad? References: <20130312062001.GJ21651@dastard> <20130312062531.GK21651@dastard> <513EE274.6090808@oracle.com> <20130312103138.GN21651@dastard> X-ASG-Orig-Subj: Re: [ASSERT failure] transaction reservations changes bad? In-Reply-To: <20130312103138.GN21651@dastard> Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Source-IP: ucsinet22.oracle.com [156.151.31.94] X-Barracuda-Connect: aserp1040.oracle.com[141.146.126.69] X-Barracuda-Start-Time: 1363086357 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124982 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On 03/12/2013 06:31 PM, Dave Chinner wrote: > On Tue, Mar 12, 2013 at 04:08:20PM +0800, Jeff Liu wrote: >> Hi Dave, >> >> On 03/12/2013 02:25 PM, Dave Chinner wrote: >>> On Tue, Mar 12, 2013 at 05:20:02PM +1100, Dave Chinner wrote: >>>> Folks, >>>> >>>> I just got this ASSERT failure running xfstests on a 3.1.8 xfsprogs >>>> and a 3.9-rc1 kernel running test 297: >>> >>> FYI, it's 100% reproducable here with: >>> >>> # sudo MKFS_OPTIONS="-b size=512" ./check 297 >>> >>> (reproduced on multiple VMs now with the same command line) > .... >>>> This implies that the permanent transaction reservation ended up >>>> larger than the log itself: >>>> >>>> $ sudo xfs_info /mnt/scratch/ >>>> [sudo] password for dave: >>>> meta-data=/dev/vdb isize=256 agcount=16, agsize=1441792 blks >>>> = sectsz=512 attr=2 >>>> data = bsize=512 blocks=23068672, imaxpct=25 >>>> = sunit=512 swidth=6144 blks >>>> naming =version 2 bsize=4096 ascii-ci=0 >>>> log =internal bsize=512 blocks=2560, version=2 >>>> = sectsz=512 sunit=512 blks, lazy-count=1 >>>> realtime =none extsz=4096 blocks=0, rtextents=0 >>>> >>>> Can someone please check that the before/after mkdir transaction >>>> reservation sizes are unchanged for such a configuration? >> I just did a quick verification. >> >> # mkfs.xfs -V >> mkfs.xfs version 3.1.8 >> >> # uname -a >> Linux koala 3.9.0-rc1 #80 SMP Tue Mar 12 15:06:39 CST 2013 x86_64 x86_64 x86_64 GNU/Linux >> >> # mkfs.xfs -f -b size=512 /dev/sda6 >> meta-data=/dev/sda6 isize=256 agcount=4, agsize=5242880 blks >> = sectsz=512 attr=2, projid32bit=0 >> data = bsize=512 blocks=20971520, imaxpct=25 >> = sunit=0 swidth=0 blks >> naming =version 2 bsize=4096 ascii-ci=0 >> log =internal log bsize=512 blocks=20480, version=2 >> = sectsz=512 sunit=0 blks, lazy-count=1 >> realtime =none extsz=4096 blocks=0, rtextents=0 > > That's a different mkfs.xfs config to what test 297 is using. > Different log size, different AG count, no log stripe unit, etc. > 297 is using: > > scratch_mkfs_xfs -d agcount=16,su=256k,sw=12 -l su=256k,size=2560b > > And when I add the extra MKFS_OPTIONS in it actually is: > > # mkfs.xfs -b size=512 -d agcount=16,su=256k,sw=12 -l su=256k,size=2560b > >> The reservation size does not changed, both are 70072 bytes: >> >> [ 230.905092] xfs_calc_mkdir_reservation: res=70072 bytes. > > And it's not just the calculation that I'm worried about here - it's > the actual reservation that ends up in the ticket that matters as > that is fed into the code that has triggered the assert. The value > in the ticket takes into account log stripe units and other > roundings, so it's typically much larger than just the reservation > calculation itself... > >> However, I can always reproducing this issue with >> '"MKFS_OPTIONS=-b size=512" ./check 297' as well. > > Can you check that it also fails on kernels prior to the reservation > changes? That will rule out it being a recent regression... Sure, verified against a new built 3.8.0 kernel, so this should be a regression issue. $ uname -a Linux koala 3.8.0 #81 SMP Tue Mar 12 18:03:44 CST 2013 x86_64 x86_64 x86_64 GNU/Linux commit 19f949f52599ba7c3f67a5897ac6be14bfcb1200 Author: Linus Torvalds Date: Mon Feb 18 15:58:34 2013 -0800 Thanks, -Jeff From ole.tange.work@gmail.com Tue Mar 12 06:38:10 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=FREEMAIL_FROM,T_DKIM_INVALID autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 2B05F7F73 for ; Tue, 12 Mar 2013 06:38:10 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay3.corp.sgi.com (Postfix) with ESMTP id 9B451AC004 for ; Tue, 12 Mar 2013 04:38:09 -0700 (PDT) X-ASG-Debug-ID: 1363088287-04cb6c2b0148ee50001-NocioJ Received: from mail-pb0-f41.google.com (mail-pb0-f41.google.com [209.85.160.41]) by cuda.sgi.com with ESMTP id 50CuC0dYO2bOpMqq (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Tue, 12 Mar 2013 04:38:07 -0700 (PDT) X-Barracuda-Envelope-From: ole.tange.work@gmail.com X-Barracuda-Apparent-Source-IP: 209.85.160.41 X-Barracuda-IPDD: Level1 [gmail.com/209.85.160.41] Received: by mail-pb0-f41.google.com with SMTP id um15so4914545pbc.0 for ; Tue, 12 Mar 2013 04:38:07 -0700 (PDT) X-Barracuda-IPDD: Level1 [gmail.com/209.85.160.41] X-Barracuda-IPDD: Level1 [gmail.com/209.85.160.41] DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20120113; h=x-received:mime-version:sender:in-reply-to:references:from:date :x-google-sender-auth:message-id:subject:to:cc:content-type; bh=ckxfuHmxhU7MJY3vhrXzNAHaNkSEbb8cpnB6mQ5joIQ=; b=CqHrsAyOg8dCT4NyZh7Q80sl63rH2QYaqmd+nLLPCX9pHgztTCInTtsuE7f0VhnIid mATJJrFZpRjPO3aVX1k6Je5HHTcNgHFmKM6GUpaDlfBXMhEdUEc4g4B9stRjMEJidX/o nmaxl1NIRnHytJ+IVRYz001RTQM+roTsj4cni5gcGJe9CsH/bMTnZo/MkIk7I4j+ror/ qpT/a8hdcPPeC/hIMNx77IZR2mlI6/YXpOmB6uTUU/+gBBVY3nFe6A4OM99cqdcQbssz Vv0wBQOfFJP6V3aJUeLWd9zGY2P2OmckRIf/UqsQtVBMaxYcsJf65B1IF7Ih0bI7+H/L a9IQ== X-Received: by 10.68.47.39 with SMTP id a7mr37049362pbn.155.1363088287066; Tue, 12 Mar 2013 04:38:07 -0700 (PDT) MIME-Version: 1.0 Sender: ole.tange.work@gmail.com Received: by 10.68.51.226 with HTTP; Tue, 12 Mar 2013 04:37:46 -0700 (PDT) In-Reply-To: References: <512FA67D.2090708@sandeen.net> <5130DB54.9030503@sandeen.net> <5134BBA4.3060305@sandeen.net> From: Ole Tange Date: Tue, 12 Mar 2013 12:37:46 +0100 X-Google-Sender-Auth: 5p6VAM6v9zrZGN23VeH5C5qbwrs Message-ID: Subject: Re: xfs_repair segfaults To: Eric Sandeen X-ASG-Orig-Subj: Re: xfs_repair segfaults Cc: xfs@oss.sgi.com Content-Type: text/plain; charset=ISO-8859-1 X-Barracuda-Connect: mail-pb0-f41.google.com[209.85.160.41] X-Barracuda-Start-Time: 1363088287 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=DKIM_SIGNED, DKIM_VERIFIED X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124983 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature (Forgot CC-to list) On Fri, Mar 8, 2013 at 11:21 AM, Ole Tange wrote: > On Mon, Mar 4, 2013 at 4:20 PM, Eric Sandeen wrote: > >> 2) so you could run a "real" non-"n" xfs_repair on a metadata image as a more realistic dry run So I made a new metadata image using xfs_metadump.sh from git: ./xfs_metadump.sh -o /dev/md123p1 franklin.xfs.metadump pbzip2 franklin.xfs.metadump Then I restored it: pbzip2 -dc < franklin.xfs.noobfuscate.metadump.bz2 | time ~/work/xfsprogs/mdrestore/xfs_mdrestore - franklin.img Then I ran git version of xfs_repair (first with -n, then no option, then with -L): $ ~/work/xfsprogs/repair/xfs_repair -n franklin.img # Load of output. Completes OK. $ ~/work/xfsprogs/repair/xfs_repair franklin.img Phase 1 - find and verify superblock... Phase 2 - using internal log - zero log... ERROR: The filesystem has valuable metadata changes in a log which needs to be replayed. Mount the filesystem to replay the log, and unmount it before re-running xfs_repair. If you are unable to mount the filesystem, then use the -L option to destroy the log and attempt a repair. Note that destroying the log may cause corruption -- please attempt a mount of the filesystem before doing this. $ ~/work/xfsprogs/repair/xfs_repair -L franklin.img Phase 1 - find and verify superblock... Phase 2 - using internal log - zero log... ALERT: The filesystem has valuable metadata changes in a log which is being destroyed because the -L option was used. - scan filesystem freespace and inode maps... xfs_repair: scan.c:1080: scan_freelist: Assertion `0' failed. Aborted (core dumped) Then I restored the metadata: pbzip2 -dc < franklin.xfs.noobfuscate.metadump.bz2 | time ~/work/xfsprogs/mdrestore/xfs_mdrestore - franklin.img Then I ran xfs_repair version 3.1.7. This gave a lot of output but completed without core dumping. The resulting filesystem was mountable and contained at least some of the filenames I expected. I believe either there is a new bug in the git version, or it simply discovers a bug that 3.1.7 does not. metadata, xfs_repair binary, core: http://dna.ku.dk/~tange/xfs/ /Ole From jeff.liu@oracle.com Tue Mar 12 06:56:48 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id E9CC87F74 for ; Tue, 12 Mar 2013 06:56:48 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id C8B03304059 for ; Tue, 12 Mar 2013 04:56:45 -0700 (PDT) X-ASG-Debug-ID: 1363089404-04cbb07dbf485250001-NocioJ Received: from userp1040.oracle.com (userp1040.oracle.com [156.151.31.81]) by cuda.sgi.com with ESMTP id RaGZDsUr9Gadc1Bu (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO) for ; Tue, 12 Mar 2013 04:56:44 -0700 (PDT) X-Barracuda-Envelope-From: jeff.liu@oracle.com X-Barracuda-Apparent-Source-IP: 156.151.31.81 Received: from acsinet21.oracle.com (acsinet21.oracle.com [141.146.126.237]) by userp1040.oracle.com (Sentrion-MTA-4.3.1/Sentrion-MTA-4.3.1) with ESMTP id r2CBughQ017611 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=OK); Tue, 12 Mar 2013 11:56:42 GMT Received: from acsmt357.oracle.com (acsmt357.oracle.com [141.146.40.157]) by acsinet21.oracle.com (8.14.4+Sun/8.14.4) with ESMTP id r2CBufko006239 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=NO); Tue, 12 Mar 2013 11:56:41 GMT Received: from abhmt112.oracle.com (abhmt112.oracle.com [141.146.116.64]) by acsmt357.oracle.com (8.12.11.20060308/8.12.11) with ESMTP id r2CBufBT005251; Tue, 12 Mar 2013 06:56:41 -0500 Received: from [192.168.1.102] (/114.248.196.15) by default (Oracle Beehive Gateway v4.0) with ESMTP ; Tue, 12 Mar 2013 04:56:41 -0700 Message-ID: <513F17F3.1010204@oracle.com> Date: Tue, 12 Mar 2013 19:56:35 +0800 From: Jeff Liu User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:16.0) Gecko/20121028 Thunderbird/16.0.2 MIME-Version: 1.0 To: Dave Chinner CC: xfs@oss.sgi.com Subject: Re: [ASSERT failure] transaction reservations changes bad? References: <20130312062001.GJ21651@dastard> <20130312062531.GK21651@dastard> <513EE274.6090808@oracle.com> <20130312103138.GN21651@dastard> <513F0C07.1060000@oracle.com> X-ASG-Orig-Subj: Re: [ASSERT failure] transaction reservations changes bad? In-Reply-To: <513F0C07.1060000@oracle.com> Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Source-IP: acsinet21.oracle.com [141.146.126.237] X-Barracuda-Connect: userp1040.oracle.com[156.151.31.81] X-Barracuda-Start-Time: 1363089404 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124986 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On 03/12/2013 07:05 PM, Jeff Liu wrote: > On 03/12/2013 06:31 PM, Dave Chinner wrote: >> On Tue, Mar 12, 2013 at 04:08:20PM +0800, Jeff Liu wrote: >>> Hi Dave, >>> >>> On 03/12/2013 02:25 PM, Dave Chinner wrote: >>>> On Tue, Mar 12, 2013 at 05:20:02PM +1100, Dave Chinner wrote: >>>>> Folks, >>>>> >>>>> I just got this ASSERT failure running xfstests on a 3.1.8 xfsprogs >>>>> and a 3.9-rc1 kernel running test 297: >>>> >>>> FYI, it's 100% reproducable here with: >>>> >>>> # sudo MKFS_OPTIONS="-b size=512" ./check 297 >>>> >>>> (reproduced on multiple VMs now with the same command line) >> .... >>>>> This implies that the permanent transaction reservation ended up >>>>> larger than the log itself: >>>>> >>>>> $ sudo xfs_info /mnt/scratch/ >>>>> [sudo] password for dave: >>>>> meta-data=/dev/vdb isize=256 agcount=16, agsize=1441792 blks >>>>> = sectsz=512 attr=2 >>>>> data = bsize=512 blocks=23068672, imaxpct=25 >>>>> = sunit=512 swidth=6144 blks >>>>> naming =version 2 bsize=4096 ascii-ci=0 >>>>> log =internal bsize=512 blocks=2560, version=2 >>>>> = sectsz=512 sunit=512 blks, lazy-count=1 >>>>> realtime =none extsz=4096 blocks=0, rtextents=0 >>>>> >>>>> Can someone please check that the before/after mkdir transaction >>>>> reservation sizes are unchanged for such a configuration? >>> I just did a quick verification. >>> >>> # mkfs.xfs -V >>> mkfs.xfs version 3.1.8 >>> >>> # uname -a >>> Linux koala 3.9.0-rc1 #80 SMP Tue Mar 12 15:06:39 CST 2013 x86_64 x86_64 x86_64 GNU/Linux >>> >>> # mkfs.xfs -f -b size=512 /dev/sda6 >>> meta-data=/dev/sda6 isize=256 agcount=4, agsize=5242880 blks >>> = sectsz=512 attr=2, projid32bit=0 >>> data = bsize=512 blocks=20971520, imaxpct=25 >>> = sunit=0 swidth=0 blks >>> naming =version 2 bsize=4096 ascii-ci=0 >>> log =internal log bsize=512 blocks=20480, version=2 >>> = sectsz=512 sunit=0 blks, lazy-count=1 >>> realtime =none extsz=4096 blocks=0, rtextents=0 >> >> That's a different mkfs.xfs config to what test 297 is using. >> Different log size, different AG count, no log stripe unit, etc. >> 297 is using: >> >> scratch_mkfs_xfs -d agcount=16,su=256k,sw=12 -l su=256k,size=2560b >> >> And when I add the extra MKFS_OPTIONS in it actually is: >> >> # mkfs.xfs -b size=512 -d agcount=16,su=256k,sw=12 -l su=256k,size=2560b >> >>> The reservation size does not changed, both are 70072 bytes: >>> >>> [ 230.905092] xfs_calc_mkdir_reservation: res=70072 bytes. >> >> And it's not just the calculation that I'm worried about here - it's >> the actual reservation that ends up in the ticket that matters as >> that is fed into the code that has triggered the assert. The value >> in the ticket takes into account log stripe units and other >> roundings, so it's typically much larger than just the reservation >> calculation itself... >> >>> However, I can always reproducing this issue with >>> '"MKFS_OPTIONS=-b size=512" ./check 297' as well. >> >> Can you check that it also fails on kernels prior to the reservation >> changes? That will rule out it being a recent regression... > Sure, verified against a new built 3.8.0 kernel, so this should be a > regression issue. > $ uname -a > Linux koala 3.8.0 #81 SMP Tue Mar 12 18:03:44 CST 2013 x86_64 x86_64 > x86_64 GNU/Linux > > commit 19f949f52599ba7c3f67a5897ac6be14bfcb1200 > Author: Linus Torvalds > Date: Mon Feb 18 15:58:34 2013 -0800 More info, 3.7.0 is the oldest kernel on my environment, I ran into the same problem. Thanks, -Jeff From david@fromorbit.com Tue Mar 12 07:05:54 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 3E5457F74 for ; Tue, 12 Mar 2013 07:05:54 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id 1D054304048 for ; Tue, 12 Mar 2013 05:05:50 -0700 (PDT) X-ASG-Debug-ID: 1363089948-04cbb07dbc485d30001-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id ojfVEsE8GLVV9OH2 for ; Tue, 12 Mar 2013 05:05:49 -0700 (PDT) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AhEcABgZP1F5LKiV/2dsb2JhbABDhyy4G4UWAQIBgUkXdIIoAQEFOhwjEAgDGAklDwUlAyETiBKvfZAiFY13GB9KB4NAA5ZUkHaBL4FvKA Received: from ppp121-44-168-149.lns20.syd7.internode.on.net (HELO dastard) ([121.44.168.149]) by ipmail05.adl6.internode.on.net with ESMTP; 12 Mar 2013 22:35:47 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UFNxh-0001Or-PJ; Tue, 12 Mar 2013 23:05:45 +1100 Date: Tue, 12 Mar 2013 23:05:45 +1100 From: Dave Chinner To: Jeff Liu Cc: xfs@oss.sgi.com Subject: Re: [ASSERT failure] transaction reservations changes bad? Message-ID: <20130312120545.GO21651@dastard> X-ASG-Orig-Subj: Re: [ASSERT failure] transaction reservations changes bad? References: <20130312062001.GJ21651@dastard> <20130312062531.GK21651@dastard> <513EE274.6090808@oracle.com> <20130312103138.GN21651@dastard> <513F0C07.1060000@oracle.com> <513F17F3.1010204@oracle.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <513F17F3.1010204@oracle.com> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1363089948 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124986 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Tue, Mar 12, 2013 at 07:56:35PM +0800, Jeff Liu wrote: > More info, 3.7.0 is the oldest kernel on my environment, I ran into the > same problem. Thanks for following up so quickly, Jeff. So the problem is that a new test is tripping over a bug that has been around for a while, not that it is a new regression. OK, so I'll expunge that from my testing for the moment as I don't ahve time to dig in and find out what the cause is right now. If anyone else wants to.... :) Cheers, Dave. -- Dave Chinner david@fromorbit.com From dave@fromorbit.com Tue Mar 12 07:31:02 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id CD0A17F78 for ; Tue, 12 Mar 2013 07:31:02 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id B4E1C304048 for ; Tue, 12 Mar 2013 05:31:02 -0700 (PDT) X-ASG-Debug-ID: 1363091460-04cbb07dbd487e60001-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id FlPWGAZdqThkPgrg for ; Tue, 12 Mar 2013 05:31:00 -0700 (PDT) X-Barracuda-Envelope-From: dave@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AgsKAKEfP1F5LKiV/2dsb2JhbABDxF0DgUoXdIMFO4ECA4hGDZ5gkRWQH41iKoRIA6dKgx4ogS8 Received: from ppp121-44-168-149.lns20.syd7.internode.on.net (HELO dastard) ([121.44.168.149]) by ipmail05.adl6.internode.on.net with ESMTP; 12 Mar 2013 23:00:58 +1030 Received: from disappointment ([192.168.1.1]) by dastard with esmtp (Exim 4.76) (envelope-from ) id 1UFOM6-0001RY-02 for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:30:58 +1100 Received: from dave by disappointment with local (Exim 4.80) (envelope-from ) id 1UFOM5-0002Ld-Rs for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:30:57 +1100 From: Dave Chinner To: xfs@oss.sgi.com Subject: [PATCH 00/21] xfs: metadata CRCs, third version Date: Tue, 12 Mar 2013 23:30:33 +1100 X-ASG-Orig-Subj: [PATCH 00/21] xfs: metadata CRCs, third version Message-Id: <1363091454-8852-1-git-send-email-david@fromorbit.com> X-Mailer: git-send-email 1.7.10.4 X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1363091460 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124988 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- Hi Folks, Another week, another version. Previous versions: http://oss.sgi.com/archives/xfs/2013-01/msg00328.html http://oss.sgi.com/archives/xfs/2013-02/msg00451.html This version is based on 3.9-rc2 + TOT xfsdev. I've just forward ported it from a 3.8.0 base where I've been working on it and testing for some time. Bugs that show up are likely to be a result of the forward porting, because I'm posting this before I've even run a full test cycle on 3.9-rc2. I'll probably send delta patches as followup bug fixes rather than reposting full patches, I think... The first patch is an outstanding bug fix, the second is a change in corruption event output to make it output the entire headers of the corrupted buffer to make it easier to triage problems. This new version contains: - numerous bug fixes, mostly in the directory and attribute code. - support for remote attributes - directory/attribute buffer type tracking for log recovery - some cleanup of rough corners in the dir/attr code. Still to do: - DT_* type fields in the directory entries - storage of attributes larger than 256 bytes in shortform attribute forks. - extended superblock feature field checking (i.e. reject anything that is not zero) - add mount warnings about CRC support being experimental - Documentation (half written, not in series) In terms of testing, this patch set seems quite robust running on non-CRC enabled filesystems with existing tool chains. There are no regressions from xfstests, fsmark, dbench and other worklaods I've thrown at it, nor does there appear to be any significant performance impact from the modified code. The CRC enabled code has been smoke tested. I haven't finished the userspace port so there is no repair/check functionality which means I cannot run xfstests on it yet. The attribute code is pretty much untested, but everything else seems to work fine. I can run it through my 50-million inode fsmark test (which creates, walks and removes 50 million inodes) without any problems occurring, so directory growing and shrinking is not obviously broken like it was last time. To run with CRCs enabled, however, you need a mkfs.xfs patch to change the offsets of entries in short form directories. I'l post an updated patch set in the morning that at least enables this in userspace. Comments, flames and questions welcome. -Dave. $ git diff --stat -C -M --summary 929724d.. fs/xfs/Makefile | 6 +- fs/xfs/xfs_ag.h | 56 +- fs/xfs/xfs_alloc.c | 199 ++++-- fs/xfs/xfs_alloc_btree.c | 105 ++- fs/xfs/xfs_alloc_btree.h | 12 +- fs/xfs/xfs_attr.c | 456 +++--------- fs/xfs/xfs_attr.h | 1 - fs/xfs/xfs_attr_leaf.c | 1780 +++++++++++++++++++++++++++-------------------- fs/xfs/xfs_attr_leaf.h | 122 +++- fs/xfs/xfs_attr_remote.c | 550 +++++++++++++++ fs/xfs/xfs_attr_remote.h | 46 ++ fs/xfs/xfs_bmap.c | 71 +- fs/xfs/xfs_bmap_btree.c | 110 ++- fs/xfs/xfs_bmap_btree.h | 19 +- fs/xfs/xfs_btree.c | 256 +++++-- fs/xfs/xfs_btree.h | 64 +- fs/xfs/xfs_buf.c | 6 + fs/xfs/xfs_buf_item.h | 52 +- fs/xfs/xfs_da_btree.c | 1500 ++++++++++++++++++++++++--------------- fs/xfs/xfs_da_btree.h | 130 +++- fs/xfs/xfs_dinode.h | 43 +- fs/xfs/xfs_dir2_block.c | 179 +++-- fs/xfs/xfs_dir2_data.c | 266 ++++--- fs/xfs/xfs_dir2_format.h | 290 +++++++- fs/xfs/xfs_dir2_leaf.c | 891 +++++++++++++++--------- fs/xfs/xfs_dir2_node.c | 992 ++++++++++++++++---------- fs/xfs/xfs_dir2_priv.h | 50 +- fs/xfs/xfs_dir2_sf.c | 12 +- fs/xfs/xfs_dquot.c | 112 ++- fs/xfs/xfs_error.c | 2 +- fs/xfs/xfs_file.c | 2 +- fs/xfs/xfs_fsops.c | 34 +- fs/xfs/xfs_ialloc.c | 80 ++- fs/xfs/xfs_ialloc_btree.c | 87 ++- fs/xfs/xfs_ialloc_btree.h | 9 +- fs/xfs/xfs_inode.c | 212 ++++-- fs/xfs/xfs_inode.h | 31 +- fs/xfs/xfs_inode_item.c | 2 +- fs/xfs/xfs_log_recover.c | 219 +++++- fs/xfs/xfs_mount.c | 97 ++- fs/xfs/xfs_mount.h | 1 + fs/xfs/xfs_qm.c | 23 +- fs/xfs/xfs_qm.h | 2 + fs/xfs/xfs_quota.h | 11 +- fs/xfs/xfs_sb.h | 100 ++- fs/xfs/xfs_symlink.c | 719 +++++++++++++++++++ fs/xfs/xfs_symlink.h | 53 ++ fs/xfs/xfs_trace.c | 2 +- fs/xfs/xfs_trans.h | 4 + fs/xfs/xfs_trans_buf.c | 51 +- fs/xfs/xfs_vnodeops.c | 480 +------------ 51 files changed, 7034 insertions(+), 3563 deletions(-) create mode 100644 fs/xfs/xfs_attr_remote.c create mode 100644 fs/xfs/xfs_attr_remote.h create mode 100644 fs/xfs/xfs_symlink.c create mode 100644 fs/xfs/xfs_symlink.h From dave@fromorbit.com Tue Mar 12 07:31:04 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id AD14A7F83 for ; Tue, 12 Mar 2013 07:31:04 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id 79121304048 for ; Tue, 12 Mar 2013 05:31:04 -0700 (PDT) X-ASG-Debug-ID: 1363091460-04cbb07dbd487e60002-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id fBt2FCYpEzfDwqEJ for ; Tue, 12 Mar 2013 05:31:02 -0700 (PDT) X-Barracuda-Envelope-From: dave@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: Ag0KAKEfP1F5LKiV/2dsb2JhbABDxF0DgUoXdIIoAQEFJy8zCBgxOQMbGYgSsAKQH44MhEgDp0qDHiiBMCQ Received: from ppp121-44-168-149.lns20.syd7.internode.on.net (HELO dastard) ([121.44.168.149]) by ipmail05.adl6.internode.on.net with ESMTP; 12 Mar 2013 23:00:59 +1030 Received: from disappointment ([192.168.1.1]) by dastard with esmtp (Exim 4.76) (envelope-from ) id 1UFOM6-0001Rl-8R for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:30:58 +1100 Received: from dave by disappointment with local (Exim 4.80) (envelope-from ) id 1UFOM6-0002M8-58 for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:30:58 +1100 From: Dave Chinner To: xfs@oss.sgi.com Subject: [PATCH 07/21] xfs: add CRC checks to the AGI Date: Tue, 12 Mar 2013 23:30:40 +1100 X-ASG-Orig-Subj: [PATCH 07/21] xfs: add CRC checks to the AGI Message-Id: <1363091454-8852-8-git-send-email-david@fromorbit.com> X-Mailer: git-send-email 1.7.10.4 In-Reply-To: <1363091454-8852-1-git-send-email-david@fromorbit.com> References: <1363091454-8852-1-git-send-email-david@fromorbit.com> X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1363091461 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124988 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- From: Dave Chinner Same set of changes made to the AGF need to be made to the AGI. This patch has a similar history to the AGF, hence a similar sign-off chain. Signed-off-by: Dave Chinner Signed-off-by: Christoph Hellwig Signed-off-by: Dave Chinner --- fs/xfs/xfs_ag.h | 8 +++++++ fs/xfs/xfs_buf_item.h | 4 +++- fs/xfs/xfs_fsops.c | 3 +++ fs/xfs/xfs_ialloc.c | 57 ++++++++++++++++++++++++++++++++++------------ fs/xfs/xfs_log_recover.c | 8 +++++++ 5 files changed, 65 insertions(+), 15 deletions(-) diff --git a/fs/xfs/xfs_ag.h b/fs/xfs/xfs_ag.h index 272ef09..317aa86 100644 --- a/fs/xfs/xfs_ag.h +++ b/fs/xfs/xfs_ag.h @@ -152,6 +152,7 @@ typedef struct xfs_agi { __be32 agi_root; /* root of inode btree */ __be32 agi_level; /* levels in inode btree */ __be32 agi_freecount; /* number of free inodes */ + __be32 agi_newino; /* new inode just allocated */ __be32 agi_dirino; /* last directory inode chunk */ /* @@ -159,6 +160,13 @@ typedef struct xfs_agi { * still being referenced. */ __be32 agi_unlinked[XFS_AGI_UNLINKED_BUCKETS]; + + uuid_t agi_uuid; /* uuid of filesystem */ + __be32 agi_crc; /* crc of agi sector */ + __be32 agi_pad32; + __be64 agi_lsn; /* last write sequence */ + + /* structure must be padded to 64 bit alignment */ } xfs_agi_t; #define XFS_AGI_MAGICNUM 0x00000001 diff --git a/fs/xfs/xfs_buf_item.h b/fs/xfs/xfs_buf_item.h index 067d5f0..c256606 100644 --- a/fs/xfs/xfs_buf_item.h +++ b/fs/xfs/xfs_buf_item.h @@ -47,6 +47,7 @@ extern kmem_zone_t *xfs_buf_item_zone; #define XFS_BLF_BTREE_BUF (1<<5) #define XFS_BLF_AGF_BUF (1<<6) #define XFS_BLF_AGFL_BUF (1<<7) +#define XFS_BLF_AGI_BUF (1<<8) #define XFS_BLF_TYPE_MASK \ (XFS_BLF_UDQUOT_BUF | \ @@ -54,7 +55,8 @@ extern kmem_zone_t *xfs_buf_item_zone; XFS_BLF_GDQUOT_BUF | \ XFS_BLF_BTREE_BUF | \ XFS_BLF_AGF_BUF | \ - XFS_BLF_AGFL_BUF) + XFS_BLF_AGFL_BUF | \ + XFS_BLF_AGI_BUF) #define XFS_BLF_CHUNK 128 #define XFS_BLF_SHIFT 7 diff --git a/fs/xfs/xfs_fsops.c b/fs/xfs/xfs_fsops.c index a693a54..87595b2 100644 --- a/fs/xfs/xfs_fsops.c +++ b/fs/xfs/xfs_fsops.c @@ -304,8 +304,11 @@ xfs_growfs_data_private( agi->agi_freecount = 0; agi->agi_newino = cpu_to_be32(NULLAGINO); agi->agi_dirino = cpu_to_be32(NULLAGINO); + if (xfs_sb_version_hascrc(&mp->m_sb)) + uuid_copy(&agi->agi_uuid, &mp->m_sb.sb_uuid); for (bucket = 0; bucket < XFS_AGI_UNLINKED_BUCKETS; bucket++) agi->agi_unlinked[bucket] = cpu_to_be32(NULLAGINO); + error = xfs_bwrite(bp); xfs_buf_relse(bp); if (error) diff --git a/fs/xfs/xfs_ialloc.c b/fs/xfs/xfs_ialloc.c index ba62661..6d0a495 100644 --- a/fs/xfs/xfs_ialloc.c +++ b/fs/xfs/xfs_ialloc.c @@ -36,6 +36,8 @@ #include "xfs_rtalloc.h" #include "xfs_error.h" #include "xfs_bmap.h" +#include "xfs_cksum.h" +#include "xfs_buf_item.h" /* @@ -1453,6 +1455,7 @@ xfs_ialloc_log_agi( /* * Log the allocation group inode header buffer. */ + xfs_trans_buf_set_type(tp, bp, XFS_BLF_AGI_BUF); xfs_trans_log_buf(tp, bp, first, last); } @@ -1470,19 +1473,23 @@ xfs_check_agi_unlinked( #define xfs_check_agi_unlinked(agi) #endif -static void +static bool xfs_agi_verify( struct xfs_buf *bp) { struct xfs_mount *mp = bp->b_target->bt_mount; struct xfs_agi *agi = XFS_BUF_TO_AGI(bp); - int agi_ok; + if (xfs_sb_version_hascrc(&mp->m_sb) && + !uuid_equal(&agi->agi_uuid, &mp->m_sb.sb_uuid)) + return false; /* * Validate the magic number of the agi block. */ - agi_ok = agi->agi_magicnum == cpu_to_be32(XFS_AGI_MAGIC) && - XFS_AGI_GOOD_VERSION(be32_to_cpu(agi->agi_versionnum)); + if (agi->agi_magicnum != cpu_to_be32(XFS_AGI_MAGIC)) + return false; + if (!XFS_AGI_GOOD_VERSION(be32_to_cpu(agi->agi_versionnum))) + return false; /* * during growfs operations, the perag is not fully initialised, @@ -1490,30 +1497,52 @@ xfs_agi_verify( * use it by using uncached buffers that don't have the perag attached * so we can detect and avoid this problem. */ - if (bp->b_pag) - agi_ok = agi_ok && be32_to_cpu(agi->agi_seqno) == - bp->b_pag->pag_agno; + if (bp->b_pag && be32_to_cpu(agi->agi_seqno) != bp->b_pag->pag_agno) + return false; - if (unlikely(XFS_TEST_ERROR(!agi_ok, mp, XFS_ERRTAG_IALLOC_READ_AGI, - XFS_RANDOM_IALLOC_READ_AGI))) { - XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, mp, agi); - xfs_buf_ioerror(bp, EFSCORRUPTED); - } xfs_check_agi_unlinked(agi); + return true; } static void xfs_agi_read_verify( struct xfs_buf *bp) { - xfs_agi_verify(bp); + struct xfs_mount *mp = bp->b_target->bt_mount; + int agi_ok = 1; + + if (xfs_sb_version_hascrc(&mp->m_sb)) + agi_ok = xfs_verify_cksum(bp->b_addr, BBTOB(bp->b_length), + offsetof(struct xfs_agi, agi_crc)); + agi_ok = agi_ok && xfs_agi_verify(bp); + + if (unlikely(XFS_TEST_ERROR(!agi_ok, mp, XFS_ERRTAG_IALLOC_READ_AGI, + XFS_RANDOM_IALLOC_READ_AGI))) { + XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, mp, bp->b_addr); + xfs_buf_ioerror(bp, EFSCORRUPTED); + } } static void xfs_agi_write_verify( struct xfs_buf *bp) { - xfs_agi_verify(bp); + struct xfs_mount *mp = bp->b_target->bt_mount; + struct xfs_buf_log_item *bip = bp->b_fspriv; + + if (!xfs_agi_verify(bp)) { + XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, mp, bp->b_addr); + xfs_buf_ioerror(bp, EFSCORRUPTED); + return; + } + + if (!xfs_sb_version_hascrc(&mp->m_sb)) + return; + + if (bip) + XFS_BUF_TO_AGI(bp)->agi_lsn = cpu_to_be64(bip->bli_item.li_lsn); + xfs_update_cksum(bp->b_addr, BBTOB(bp->b_length), + offsetof(struct xfs_agi, agi_crc)); } const struct xfs_buf_ops xfs_agi_buf_ops = { diff --git a/fs/xfs/xfs_log_recover.c b/fs/xfs/xfs_log_recover.c index 8fefbc5..8f70c4e 100644 --- a/fs/xfs/xfs_log_recover.c +++ b/fs/xfs/xfs_log_recover.c @@ -1971,6 +1971,14 @@ xlog_recover_do_reg_buffer( } bp->b_ops = &xfs_agfl_buf_ops; break; + case XFS_BLF_AGI_BUF: + if (*(__be32 *)bp->b_addr != cpu_to_be32(XFS_AGI_MAGIC)) { + xfs_warn(mp, "Bad AGI block magic!"); + ASSERT(0); + break; + } + bp->b_ops = &xfs_agi_buf_ops; + break; default: break; } -- 1.7.10.4 From dave@fromorbit.com Tue Mar 12 07:31:06 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 3699D7F83 for ; Tue, 12 Mar 2013 07:31:06 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id 1F863304048 for ; Tue, 12 Mar 2013 05:31:06 -0700 (PDT) X-ASG-Debug-ID: 1363091464-04cbb07dbd487e80001-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id 57vIReQsPJyQXRAe for ; Tue, 12 Mar 2013 05:31:04 -0700 (PDT) X-Barracuda-Envelope-From: dave@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: Ag0KAKEfP1F5LKiV/2dsb2JhbABDxF0DgUoXdIIoAQEFVjMIGDE5AxsZiBKwApAfjUpCgR6DKgOgPocMgx4ogS4 Received: from ppp121-44-168-149.lns20.syd7.internode.on.net (HELO dastard) ([121.44.168.149]) by ipmail05.adl6.internode.on.net with ESMTP; 12 Mar 2013 23:01:03 +1030 Received: from disappointment ([192.168.1.1]) by dastard with esmtp (Exim 4.76) (envelope-from ) id 1UFOMB-0001Ra-2p for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:31:03 +1100 Received: from dave by disappointment with local (Exim 4.80) (envelope-from ) id 1UFOM5-0002Lk-Ut for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:30:57 +1100 From: Dave Chinner To: xfs@oss.sgi.com Subject: [PATCH 02/21] xfs: increase hexdump output in xfs_corruption_error Date: Tue, 12 Mar 2013 23:30:35 +1100 X-ASG-Orig-Subj: [PATCH 02/21] xfs: increase hexdump output in xfs_corruption_error Message-Id: <1363091454-8852-3-git-send-email-david@fromorbit.com> X-Mailer: git-send-email 1.7.10.4 In-Reply-To: <1363091454-8852-1-git-send-email-david@fromorbit.com> References: <1363091454-8852-1-git-send-email-david@fromorbit.com> X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1363091464 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124988 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- From: Dave Chinner Currently xfs_corruption_error() dumps the first 16 bytes of the buffer that is passed to it when a corruption occurs. This is not large enough to see the entire state of the header of the block that was determined to be corrupt. increase the output to 64 bytes to capture the majority of all headers in all types of metadata blocks. Signed-off-by: Dave Chinner --- fs/xfs/xfs_error.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/fs/xfs/xfs_error.c b/fs/xfs/xfs_error.c index 07bf3b9..35d3f5b 100644 --- a/fs/xfs/xfs_error.c +++ b/fs/xfs/xfs_error.c @@ -178,7 +178,7 @@ xfs_corruption_error( inst_t *ra) { if (level <= xfs_error_level) - xfs_hex_dump(p, 16); + xfs_hex_dump(p, 64); xfs_error_report(tag, level, mp, filename, linenum, ra); xfs_alert(mp, "Corruption detected. Unmount and run xfs_repair"); } -- 1.7.10.4 From dave@fromorbit.com Tue Mar 12 07:31:10 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id B43DE7F88 for ; Tue, 12 Mar 2013 07:31:10 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay1.corp.sgi.com (Postfix) with ESMTP id 915998F8035 for ; Tue, 12 Mar 2013 05:31:10 -0700 (PDT) X-ASG-Debug-ID: 1363091468-04bdf022974cb070001-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id Jpdxvt4Zd5FVbYqZ for ; Tue, 12 Mar 2013 05:31:09 -0700 (PDT) X-Barracuda-Envelope-From: dave@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: Ag0KAKEfP1F5LKiV/2dsb2JhbABDxF0DgUoXdIIoAQEFJy8zCBgxOQMbGYgSsAKQH44MgR6DKgOnSoMeKA Received: from ppp121-44-168-149.lns20.syd7.internode.on.net (HELO dastard) ([121.44.168.149]) by ipmail05.adl6.internode.on.net with ESMTP; 12 Mar 2013 23:01:08 +1030 Received: from disappointment ([192.168.1.1]) by dastard with esmtp (Exim 4.76) (envelope-from ) id 1UFOM6-0001RZ-0m for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:30:58 +1100 Received: from dave by disappointment with local (Exim 4.80) (envelope-from ) id 1UFOM5-0002Lg-T6 for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:30:57 +1100 From: Dave Chinner To: xfs@oss.sgi.com Subject: [PATCH 01/21] xfs: ensure we capture IO errors correctly Date: Tue, 12 Mar 2013 23:30:34 +1100 X-ASG-Orig-Subj: [PATCH 01/21] xfs: ensure we capture IO errors correctly Message-Id: <1363091454-8852-2-git-send-email-david@fromorbit.com> X-Mailer: git-send-email 1.7.10.4 In-Reply-To: <1363091454-8852-1-git-send-email-david@fromorbit.com> References: <1363091454-8852-1-git-send-email-david@fromorbit.com> X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1363091468 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124988 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- From: Dave Chinner Failed buffer readahead can leave the buffer in the cache marked with an error. Most callers that then issue a subsequent read on the buffer do not zero the b_error field out, and so we may incorectly detect an error during IO completion due to the stale error value left on the buffer. Avoid this problem by zeroing the error before IO submission. This ensures that the only IO errors that are detected those captured from are those captured from bio submission or completion. Signed-off-by: Dave Chinner --- fs/xfs/xfs_buf.c | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/fs/xfs/xfs_buf.c b/fs/xfs/xfs_buf.c index 50eb603..82b70bd 100644 --- a/fs/xfs/xfs_buf.c +++ b/fs/xfs/xfs_buf.c @@ -1336,6 +1336,12 @@ _xfs_buf_ioapply( int size; int i; + /* + * Make sure we capture only current IO errors rather than stale errors + * left over from previous use of the buffer (e.g. failed readahead). + */ + bp->b_error = 0; + if (bp->b_flags & XBF_WRITE) { if (bp->b_flags & XBF_SYNCIO) rw = WRITE_SYNC; -- 1.7.10.4 From dave@fromorbit.com Tue Mar 12 07:31:12 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 147FB7F88 for ; Tue, 12 Mar 2013 07:31:12 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay1.corp.sgi.com (Postfix) with ESMTP id C81A38F8035 for ; Tue, 12 Mar 2013 05:31:11 -0700 (PDT) X-ASG-Debug-ID: 1363091468-04bdf022974cb070002-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id EPcU6PaXxKl7UuZq for ; Tue, 12 Mar 2013 05:31:10 -0700 (PDT) X-Barracuda-Envelope-From: dave@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: Ag0KAKEfP1F5LKiV/2dsb2JhbABDxF0DgUoXdIIoAQEFJy8zCBgYGTkDGxmIErACkB+ODIESgzYDoD6HDIMeKA Received: from ppp121-44-168-149.lns20.syd7.internode.on.net (HELO dastard) ([121.44.168.149]) by ipmail05.adl6.internode.on.net with ESMTP; 12 Mar 2013 23:01:08 +1030 Received: from disappointment ([192.168.1.1]) by dastard with esmtp (Exim 4.76) (envelope-from ) id 1UFOM6-0001Rb-2b for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:30:58 +1100 Received: from dave by disappointment with local (Exim 4.80) (envelope-from ) id 1UFOM5-0002Lp-Vr for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:30:57 +1100 From: Dave Chinner To: xfs@oss.sgi.com Subject: [PATCH 03/21] xfs: take inode version into account in XFS_LITINO Date: Tue, 12 Mar 2013 23:30:36 +1100 X-ASG-Orig-Subj: [PATCH 03/21] xfs: take inode version into account in XFS_LITINO Message-Id: <1363091454-8852-4-git-send-email-david@fromorbit.com> X-Mailer: git-send-email 1.7.10.4 In-Reply-To: <1363091454-8852-1-git-send-email-david@fromorbit.com> References: <1363091454-8852-1-git-send-email-david@fromorbit.com> X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1363091469 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124988 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- From: Christoph Hellwig Add a version argument to XFS_LITINO so that it can return different values depending on the inode version. This is required for the upcoming v3 inodes with a larger fixed layout dinode. Signed-off-by: Christoph Hellwig Signed-off-by: Dave Chinner Reviewed-by: Ben Myers --- fs/xfs/xfs_attr_leaf.c | 6 ++++-- fs/xfs/xfs_bmap.c | 4 ++-- fs/xfs/xfs_dinode.h | 6 +++--- fs/xfs/xfs_inode.h | 5 +++-- fs/xfs/xfs_vnodeops.c | 2 +- 5 files changed, 13 insertions(+), 10 deletions(-) diff --git a/fs/xfs/xfs_attr_leaf.c b/fs/xfs/xfs_attr_leaf.c index ee24993..f96a734 100644 --- a/fs/xfs/xfs_attr_leaf.c +++ b/fs/xfs/xfs_attr_leaf.c @@ -172,7 +172,8 @@ xfs_attr_shortform_bytesfit(xfs_inode_t *dp, int bytes) int dsize; xfs_mount_t *mp = dp->i_mount; - offset = (XFS_LITINO(mp) - bytes) >> 3; /* rounded down */ + /* rounded down */ + offset = (XFS_LITINO(mp, dp->i_d.di_version) - bytes) >> 3; switch (dp->i_d.di_format) { case XFS_DINODE_FMT_DEV: @@ -243,7 +244,8 @@ xfs_attr_shortform_bytesfit(xfs_inode_t *dp, int bytes) minforkoff = roundup(minforkoff, 8) >> 3; /* attr fork btree root can have at least this many key/ptr pairs */ - maxforkoff = XFS_LITINO(mp) - XFS_BMDR_SPACE_CALC(MINABTPTRS); + maxforkoff = XFS_LITINO(mp, dp->i_d.di_version) - + XFS_BMDR_SPACE_CALC(MINABTPTRS); maxforkoff = maxforkoff >> 3; /* rounded down */ if (offset >= maxforkoff) diff --git a/fs/xfs/xfs_bmap.c b/fs/xfs/xfs_bmap.c index d490fe8..20efb39 100644 --- a/fs/xfs/xfs_bmap.c +++ b/fs/xfs/xfs_bmap.c @@ -228,13 +228,13 @@ xfs_default_attroffset( uint offset; if (mp->m_sb.sb_inodesize == 256) { - offset = XFS_LITINO(mp) - + offset = XFS_LITINO(mp, ip->i_d.di_version) - XFS_BMDR_SPACE_CALC(MINABTPTRS); } else { offset = XFS_BMDR_SPACE_CALC(6 * MINABTPTRS); } - ASSERT(offset < XFS_LITINO(mp)); + ASSERT(offset < XFS_LITINO(mp, ip->i_d.di_version)); return offset; } diff --git a/fs/xfs/xfs_dinode.h b/fs/xfs/xfs_dinode.h index 1d9643b..88a3368 100644 --- a/fs/xfs/xfs_dinode.h +++ b/fs/xfs/xfs_dinode.h @@ -104,7 +104,7 @@ typedef enum xfs_dinode_fmt { /* * Inode size for given fs. */ -#define XFS_LITINO(mp) \ +#define XFS_LITINO(mp, version) \ ((int)(((mp)->m_sb.sb_inodesize) - sizeof(struct xfs_dinode))) #define XFS_BROOT_SIZE_ADJ \ @@ -119,10 +119,10 @@ typedef enum xfs_dinode_fmt { #define XFS_DFORK_DSIZE(dip,mp) \ (XFS_DFORK_Q(dip) ? \ XFS_DFORK_BOFF(dip) : \ - XFS_LITINO(mp)) + XFS_LITINO(mp, (dip)->di_version)) #define XFS_DFORK_ASIZE(dip,mp) \ (XFS_DFORK_Q(dip) ? \ - XFS_LITINO(mp) - XFS_DFORK_BOFF(dip) : \ + XFS_LITINO(mp, (dip)->di_version) - XFS_DFORK_BOFF(dip) : \ 0) #define XFS_DFORK_SIZE(dip,mp,w) \ ((w) == XFS_DATA_FORK ? \ diff --git a/fs/xfs/xfs_inode.h b/fs/xfs/xfs_inode.h index 237e7f6..b8520b5 100644 --- a/fs/xfs/xfs_inode.h +++ b/fs/xfs/xfs_inode.h @@ -180,10 +180,11 @@ typedef struct xfs_icdinode { #define XFS_IFORK_DSIZE(ip) \ (XFS_IFORK_Q(ip) ? \ XFS_IFORK_BOFF(ip) : \ - XFS_LITINO((ip)->i_mount)) + XFS_LITINO((ip)->i_mount, (ip)->i_d.di_version)) #define XFS_IFORK_ASIZE(ip) \ (XFS_IFORK_Q(ip) ? \ - XFS_LITINO((ip)->i_mount) - XFS_IFORK_BOFF(ip) : \ + XFS_LITINO((ip)->i_mount, (ip)->i_d.di_version) - \ + XFS_IFORK_BOFF(ip) : \ 0) #define XFS_IFORK_SIZE(ip,w) \ ((w) == XFS_DATA_FORK ? \ diff --git a/fs/xfs/xfs_vnodeops.c b/fs/xfs/xfs_vnodeops.c index 77ad748..aa0c066 100644 --- a/fs/xfs/xfs_vnodeops.c +++ b/fs/xfs/xfs_vnodeops.c @@ -1420,7 +1420,7 @@ xfs_symlink( * The symlink will fit into the inode data fork? * There can't be any attributes so we get the whole variable part. */ - if (pathlen <= XFS_LITINO(mp)) + if (pathlen <= XFS_LITINO(mp, dp->i_d.di_version)) fs_blocks = 0; else fs_blocks = XFS_B_TO_FSB(mp, pathlen); -- 1.7.10.4 From dave@fromorbit.com Tue Mar 12 07:31:12 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id E6B3A7F88 for ; Tue, 12 Mar 2013 07:31:12 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay1.corp.sgi.com (Postfix) with ESMTP id C51488F804C for ; Tue, 12 Mar 2013 05:31:12 -0700 (PDT) X-ASG-Debug-ID: 1363091470-04cbb07dbe487eb0001-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id Zd0CQHd2Q4cJQXaj for ; Tue, 12 Mar 2013 05:31:10 -0700 (PDT) X-Barracuda-Envelope-From: dave@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: Ag8KAKEfP1F5LKiV/2dsb2JhbAA5CsRdAwGBSRd0gigBAQUnLzMIGDE5AxsZiBKwApAfjVI6doNSA6dKgx4o Received: from ppp121-44-168-149.lns20.syd7.internode.on.net (HELO dastard) ([121.44.168.149]) by ipmail05.adl6.internode.on.net with ESMTP; 12 Mar 2013 23:01:08 +1030 Received: from disappointment ([192.168.1.1]) by dastard with esmtp (Exim 4.76) (envelope-from ) id 1UFOMG-0001Ry-5W for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:31:08 +1100 Received: from dave by disappointment with local (Exim 4.80) (envelope-from ) id 1UFOM6-0002M0-1m for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:30:58 +1100 From: Dave Chinner To: xfs@oss.sgi.com Subject: [PATCH 05/21] xfs: add CRC checks to the AGF Date: Tue, 12 Mar 2013 23:30:38 +1100 X-ASG-Orig-Subj: [PATCH 05/21] xfs: add CRC checks to the AGF Message-Id: <1363091454-8852-6-git-send-email-david@fromorbit.com> X-Mailer: git-send-email 1.7.10.4 In-Reply-To: <1363091454-8852-1-git-send-email-david@fromorbit.com> References: <1363091454-8852-1-git-send-email-david@fromorbit.com> X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1363091470 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124988 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- From: Dave Chinner The AGF already has some self identifying fields (e.g. the sequence number) so we only need to add the uuid to it to identify the filesystem it belongs to. The location is fixed based on the sequence number, so there's no need to add a block number, either. Hence the only additional fields are the CRC and LSN fields. These are unlogged, so place some space between the end of the logged fields and them so that future expansion of the AGF for logged fields can be placed adjacent to the existing logged fields and hence not complicate the field-derived range based logging we currently have. Based originally on a patch from myself, modified further by Christoph Hellwig and then modified again to fit into the verifier structure with additional fields by myself. The multiple signed-off-by tags indicate the age and history of this patch. Signed-off-by: Dave Chinner Signed-off-by: Christoph Hellwig Signed-off-by: Dave Chinner --- fs/xfs/xfs_ag.h | 23 +++++++++++-- fs/xfs/xfs_alloc.c | 80 ++++++++++++++++++++++++++++++++-------------- fs/xfs/xfs_buf_item.h | 4 ++- fs/xfs/xfs_fsops.c | 3 ++ fs/xfs/xfs_log_recover.c | 8 +++++ 5 files changed, 91 insertions(+), 27 deletions(-) diff --git a/fs/xfs/xfs_ag.h b/fs/xfs/xfs_ag.h index f2aeedb..9f4815e 100644 --- a/fs/xfs/xfs_ag.h +++ b/fs/xfs/xfs_ag.h @@ -63,12 +63,29 @@ typedef struct xfs_agf { __be32 agf_spare0; /* spare field */ __be32 agf_levels[XFS_BTNUM_AGF]; /* btree levels */ __be32 agf_spare1; /* spare field */ + __be32 agf_flfirst; /* first freelist block's index */ __be32 agf_fllast; /* last freelist block's index */ __be32 agf_flcount; /* count of blocks in freelist */ __be32 agf_freeblks; /* total free blocks */ + __be32 agf_longest; /* longest free space */ __be32 agf_btreeblks; /* # of blocks held in AGF btrees */ + uuid_t agf_uuid; /* uuid of filesystem */ + + /* + * reserve some contiguous space for future logged fields before we add + * the unlogged fields. This makes the range logging via flags and + * structure offsets much simpler. + */ + __be64 agf_spare64[16]; + + /* unlogged fields, written during buffer writeback. */ + __be64 agf_lsn; /* last write sequence */ + __be32 agf_crc; /* crc of agf sector */ + __be32 agf_spare2; + + /* structure must be padded to 64 bit alignment */ } xfs_agf_t; #define XFS_AGF_MAGICNUM 0x00000001 @@ -83,7 +100,8 @@ typedef struct xfs_agf { #define XFS_AGF_FREEBLKS 0x00000200 #define XFS_AGF_LONGEST 0x00000400 #define XFS_AGF_BTREEBLKS 0x00000800 -#define XFS_AGF_NUM_BITS 12 +#define XFS_AGF_UUID 0x00001000 +#define XFS_AGF_NUM_BITS 13 #define XFS_AGF_ALL_BITS ((1 << XFS_AGF_NUM_BITS) - 1) #define XFS_AGF_FLAGS \ @@ -98,7 +116,8 @@ typedef struct xfs_agf { { XFS_AGF_FLCOUNT, "FLCOUNT" }, \ { XFS_AGF_FREEBLKS, "FREEBLKS" }, \ { XFS_AGF_LONGEST, "LONGEST" }, \ - { XFS_AGF_BTREEBLKS, "BTREEBLKS" } + { XFS_AGF_BTREEBLKS, "BTREEBLKS" }, \ + { XFS_AGF_UUID, "UUID" } /* disk block (xfs_daddr_t) in the AG */ #define XFS_AGF_DADDR(mp) ((xfs_daddr_t)(1 << (mp)->m_sectbb_log)) diff --git a/fs/xfs/xfs_alloc.c b/fs/xfs/xfs_alloc.c index a8beb5c..c34f799 100644 --- a/fs/xfs/xfs_alloc.c +++ b/fs/xfs/xfs_alloc.c @@ -33,7 +33,9 @@ #include "xfs_alloc.h" #include "xfs_extent_busy.h" #include "xfs_error.h" +#include "xfs_cksum.h" #include "xfs_trace.h" +#include "xfs_buf_item.h" struct workqueue_struct *xfs_alloc_wq; @@ -2058,11 +2060,14 @@ xfs_alloc_log_agf( offsetof(xfs_agf_t, agf_freeblks), offsetof(xfs_agf_t, agf_longest), offsetof(xfs_agf_t, agf_btreeblks), + offsetof(xfs_agf_t, agf_uuid), sizeof(xfs_agf_t) }; trace_xfs_agf(tp->t_mountp, XFS_BUF_TO_AGF(bp), fields, _RET_IP_); + xfs_trans_buf_set_type(tp, bp, XFS_BLF_AGF_BUF); + xfs_btree_offsets(fields, offsets, XFS_AGF_NUM_BITS, &first, &last); xfs_trans_log_buf(tp, bp, (uint)first, (uint)last); } @@ -2143,22 +2148,24 @@ xfs_alloc_put_freelist( return 0; } -static void +static bool xfs_agf_verify( + struct xfs_mount *mp, struct xfs_buf *bp) { - struct xfs_mount *mp = bp->b_target->bt_mount; - struct xfs_agf *agf; - int agf_ok; + struct xfs_agf *agf = XFS_BUF_TO_AGF(bp); - agf = XFS_BUF_TO_AGF(bp); + if (xfs_sb_version_hascrc(&mp->m_sb) && + !uuid_equal(&agf->agf_uuid, &mp->m_sb.sb_uuid)) + return false; - agf_ok = agf->agf_magicnum == cpu_to_be32(XFS_AGF_MAGIC) && - XFS_AGF_GOOD_VERSION(be32_to_cpu(agf->agf_versionnum)) && - be32_to_cpu(agf->agf_freeblks) <= be32_to_cpu(agf->agf_length) && - be32_to_cpu(agf->agf_flfirst) < XFS_AGFL_SIZE(mp) && - be32_to_cpu(agf->agf_fllast) < XFS_AGFL_SIZE(mp) && - be32_to_cpu(agf->agf_flcount) <= XFS_AGFL_SIZE(mp); + if (!(agf->agf_magicnum == cpu_to_be32(XFS_AGF_MAGIC) && + XFS_AGF_GOOD_VERSION(be32_to_cpu(agf->agf_versionnum)) && + be32_to_cpu(agf->agf_freeblks) <= be32_to_cpu(agf->agf_length) && + be32_to_cpu(agf->agf_flfirst) < XFS_AGFL_SIZE(mp) && + be32_to_cpu(agf->agf_fllast) < XFS_AGFL_SIZE(mp) && + be32_to_cpu(agf->agf_flcount) <= XFS_AGFL_SIZE(mp))) + return false; /* * during growfs operations, the perag is not fully initialised, @@ -2166,33 +2173,58 @@ xfs_agf_verify( * use it by using uncached buffers that don't have the perag attached * so we can detect and avoid this problem. */ - if (bp->b_pag) - agf_ok = agf_ok && be32_to_cpu(agf->agf_seqno) == - bp->b_pag->pag_agno; + if (bp->b_pag && be32_to_cpu(agf->agf_seqno) != bp->b_pag->pag_agno) + return false; - if (xfs_sb_version_haslazysbcount(&mp->m_sb)) - agf_ok = agf_ok && be32_to_cpu(agf->agf_btreeblks) <= - be32_to_cpu(agf->agf_length); + if (xfs_sb_version_haslazysbcount(&mp->m_sb) && + be32_to_cpu(agf->agf_btreeblks) > be32_to_cpu(agf->agf_length)) + return false; + + return true;; - if (unlikely(XFS_TEST_ERROR(!agf_ok, mp, XFS_ERRTAG_ALLOC_READ_AGF, - XFS_RANDOM_ALLOC_READ_AGF))) { - XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, mp, agf); - xfs_buf_ioerror(bp, EFSCORRUPTED); - } } static void xfs_agf_read_verify( struct xfs_buf *bp) { - xfs_agf_verify(bp); + struct xfs_mount *mp = bp->b_target->bt_mount; + int agf_ok = 1; + + if (xfs_sb_version_hascrc(&mp->m_sb)) + agf_ok = xfs_verify_cksum(bp->b_addr, BBTOB(bp->b_length), + offsetof(struct xfs_agf, agf_crc)); + + agf_ok = agf_ok && xfs_agf_verify(mp, bp); + + if (unlikely(XFS_TEST_ERROR(!agf_ok, mp, XFS_ERRTAG_ALLOC_READ_AGF, + XFS_RANDOM_ALLOC_READ_AGF))) { + XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, mp, bp->b_addr); + xfs_buf_ioerror(bp, EFSCORRUPTED); + } } static void xfs_agf_write_verify( struct xfs_buf *bp) { - xfs_agf_verify(bp); + struct xfs_mount *mp = bp->b_target->bt_mount; + struct xfs_buf_log_item *bip = bp->b_fspriv; + + if (!xfs_agf_verify(mp, bp)) { + XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, mp, bp->b_addr); + xfs_buf_ioerror(bp, EFSCORRUPTED); + return; + } + + if (!xfs_sb_version_hascrc(&mp->m_sb)) + return; + + if (bip) + XFS_BUF_TO_AGF(bp)->agf_lsn = cpu_to_be64(bip->bli_item.li_lsn); + + xfs_update_cksum(bp->b_addr, BBTOB(bp->b_length), + offsetof(struct xfs_agf, agf_crc)); } const struct xfs_buf_ops xfs_agf_buf_ops = { diff --git a/fs/xfs/xfs_buf_item.h b/fs/xfs/xfs_buf_item.h index 101ef83..76bd7a1 100644 --- a/fs/xfs/xfs_buf_item.h +++ b/fs/xfs/xfs_buf_item.h @@ -45,12 +45,14 @@ extern kmem_zone_t *xfs_buf_item_zone; * once the changes have been replayed into the buffer. */ #define XFS_BLF_BTREE_BUF (1<<5) +#define XFS_BLF_AGF_BUF (1<<6) #define XFS_BLF_TYPE_MASK \ (XFS_BLF_UDQUOT_BUF | \ XFS_BLF_PDQUOT_BUF | \ XFS_BLF_GDQUOT_BUF | \ - XFS_BLF_BTREE_BUF) + XFS_BLF_BTREE_BUF | \ + XFS_BLF_AGF_BUF) #define XFS_BLF_CHUNK 128 #define XFS_BLF_SHIFT 7 diff --git a/fs/xfs/xfs_fsops.c b/fs/xfs/xfs_fsops.c index 6fe286a..b6cca27 100644 --- a/fs/xfs/xfs_fsops.c +++ b/fs/xfs/xfs_fsops.c @@ -247,6 +247,9 @@ xfs_growfs_data_private( tmpsize = agsize - XFS_PREALLOC_BLOCKS(mp); agf->agf_freeblks = cpu_to_be32(tmpsize); agf->agf_longest = cpu_to_be32(tmpsize); + if (xfs_sb_version_hascrc(&mp->m_sb)) + uuid_copy(&agf->agf_uuid, &mp->m_sb.sb_uuid); + error = xfs_bwrite(bp); xfs_buf_relse(bp); if (error) diff --git a/fs/xfs/xfs_log_recover.c b/fs/xfs/xfs_log_recover.c index 10b9854..2943d53 100644 --- a/fs/xfs/xfs_log_recover.c +++ b/fs/xfs/xfs_log_recover.c @@ -1953,6 +1953,14 @@ xlog_recover_do_reg_buffer( break; } break; + case XFS_BLF_AGF_BUF: + if (*(__be32 *)bp->b_addr != cpu_to_be32(XFS_AGF_MAGIC)) { + xfs_warn(mp, "Bad AGF block magic!"); + ASSERT(0); + break; + } + bp->b_ops = &xfs_agf_buf_ops; + break; default: break; } -- 1.7.10.4 From dave@fromorbit.com Tue Mar 12 07:31:15 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 8A3507F95 for ; Tue, 12 Mar 2013 07:31:13 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay1.corp.sgi.com (Postfix) with ESMTP id 599D08F804C for ; Tue, 12 Mar 2013 05:31:13 -0700 (PDT) X-ASG-Debug-ID: 1363091468-04bdf022974cb070003-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id AQqOLH55lyo5047A for ; Tue, 12 Mar 2013 05:31:11 -0700 (PDT) X-Barracuda-Envelope-From: dave@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: Ag8KAKEfP1F5LKiV/2dsb2JhbABDxF0DAYFJF3SCKAEBBScvMwgYMTkDGxmIErACkB+ODHYGg0wDp0qDHig Received: from ppp121-44-168-149.lns20.syd7.internode.on.net (HELO dastard) ([121.44.168.149]) by ipmail05.adl6.internode.on.net with ESMTP; 12 Mar 2013 23:01:09 +1030 Received: from disappointment ([192.168.1.1]) by dastard with esmtp (Exim 4.76) (envelope-from ) id 1UFOMG-0001Rv-7S for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:31:08 +1100 Received: from dave by disappointment with local (Exim 4.80) (envelope-from ) id 1UFOM6-0002M4-2h for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:30:58 +1100 From: Dave Chinner To: xfs@oss.sgi.com Subject: [PATCH 06/21] xfs: add CRC checks to the AGFL Date: Tue, 12 Mar 2013 23:30:39 +1100 X-ASG-Orig-Subj: [PATCH 06/21] xfs: add CRC checks to the AGFL Message-Id: <1363091454-8852-7-git-send-email-david@fromorbit.com> X-Mailer: git-send-email 1.7.10.4 In-Reply-To: <1363091454-8852-1-git-send-email-david@fromorbit.com> References: <1363091454-8852-1-git-send-email-david@fromorbit.com> X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1363091471 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Barracuda-BRTS-Status: 1 X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124988 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- From: Christoph Hellwig Add CRC checks, location information and a magic number to the AGFL. Previously the AGFL was just a block containing nothing but the free block pointers. The new AGFL has a real header with the usual boilerplate instead, so that we can verify it's not corrupted and written into the right place. [dchinner@redhat.com] Added LSN field, reworked significantly to fit into new verifier structure and growfs structure, enabled full verifier functionality now there is a header to verify and we can guarantee an initialised AGFL. Signed-off-by: Christoph Hellwig Signed-off-by: Dave Chinner --- fs/xfs/xfs_ag.h | 25 +++++++++- fs/xfs/xfs_alloc.c | 119 ++++++++++++++++++++++++++++++---------------- fs/xfs/xfs_buf_item.h | 4 +- fs/xfs/xfs_fsops.c | 5 ++ fs/xfs/xfs_log_recover.c | 10 ++++ 5 files changed, 119 insertions(+), 44 deletions(-) diff --git a/fs/xfs/xfs_ag.h b/fs/xfs/xfs_ag.h index 9f4815e..272ef09 100644 --- a/fs/xfs/xfs_ag.h +++ b/fs/xfs/xfs_ag.h @@ -30,6 +30,7 @@ struct xfs_trans; #define XFS_AGF_MAGIC 0x58414746 /* 'XAGF' */ #define XFS_AGI_MAGIC 0x58414749 /* 'XAGI' */ +#define XFS_AGFL_MAGIC 0x5841464c /* 'XAFL' */ #define XFS_AGF_VERSION 1 #define XFS_AGI_VERSION 1 @@ -190,11 +191,31 @@ extern const struct xfs_buf_ops xfs_agi_buf_ops; */ #define XFS_AGFL_DADDR(mp) ((xfs_daddr_t)(3 << (mp)->m_sectbb_log)) #define XFS_AGFL_BLOCK(mp) XFS_HDR_BLOCK(mp, XFS_AGFL_DADDR(mp)) -#define XFS_AGFL_SIZE(mp) ((mp)->m_sb.sb_sectsize / sizeof(xfs_agblock_t)) #define XFS_BUF_TO_AGFL(bp) ((xfs_agfl_t *)((bp)->b_addr)) +#define XFS_BUF_TO_AGFL_BNO(mp, bp) \ + (xfs_sb_version_hascrc(&((mp)->m_sb)) ? \ + &(XFS_BUF_TO_AGFL(bp)->agfl_bno[0]) : \ + (__be32 *)(bp)->b_addr) + +/* + * Size of the AGFL. For CRC-enabled filesystes we steal a couple of + * slots in the beginning of the block for a proper header with the + * location information and CRC. + */ +#define XFS_AGFL_SIZE(mp) \ + (((mp)->m_sb.sb_sectsize - \ + (xfs_sb_version_hascrc(&((mp)->m_sb)) ? \ + sizeof(struct xfs_agfl) : 0)) / \ + sizeof(xfs_agblock_t)) + typedef struct xfs_agfl { - __be32 agfl_bno[1]; /* actually XFS_AGFL_SIZE(mp) */ + __be32 agfl_magicnum; + __be32 agfl_seqno; + uuid_t agfl_uuid; + __be64 agfl_lsn; + __be32 agfl_crc; + __be32 agfl_bno[]; /* actually XFS_AGFL_SIZE(mp) */ } xfs_agfl_t; /* diff --git a/fs/xfs/xfs_alloc.c b/fs/xfs/xfs_alloc.c index c34f799..40d3d57 100644 --- a/fs/xfs/xfs_alloc.c +++ b/fs/xfs/xfs_alloc.c @@ -432,53 +432,84 @@ xfs_alloc_fixup_trees( return 0; } -static void +static bool xfs_agfl_verify( struct xfs_buf *bp) { -#ifdef WHEN_CRCS_COME_ALONG - /* - * we cannot actually do any verification of the AGFL because mkfs does - * not initialise the AGFL to zero or NULL. Hence the only valid part of - * the AGFL is what the AGF says is active. We can't get to the AGF, so - * we can't verify just those entries are valid. - * - * This problem goes away when the CRC format change comes along as that - * requires the AGFL to be initialised by mkfs. At that point, we can - * verify the blocks in the agfl -active or not- lie within the bounds - * of the AG. Until then, just leave this check ifdef'd out. - */ struct xfs_mount *mp = bp->b_target->bt_mount; struct xfs_agfl *agfl = XFS_BUF_TO_AGFL(bp); - int agfl_ok = 1; - int i; + if (!uuid_equal(&agfl->agfl_uuid, &mp->m_sb.sb_uuid)) + return false; + if (be32_to_cpu(agfl->agfl_magicnum) != XFS_AGFL_MAGIC) + return false; + /* + * during growfs operations, the perag is not fully initialised, + * so we can't use it for any useful checking. growfs ensures we can't + * use it by using uncached buffers that don't have the perag attached + * so we can detect and avoid this problem. + */ + if (bp->b_pag && be32_to_cpu(agfl->agfl_seqno) != bp->b_pag->pag_agno) + return false; + for (i = 0; i < XFS_AGFL_SIZE(mp); i++) { - if (be32_to_cpu(agfl->agfl_bno[i]) == NULLAGBLOCK || + if (be32_to_cpu(agfl->agfl_bno[i]) != NULLAGBLOCK && be32_to_cpu(agfl->agfl_bno[i]) >= mp->m_sb.sb_agblocks) - agfl_ok = 0; + return false; } + return true; +} + +static void +xfs_agfl_read_verify( + struct xfs_buf *bp) +{ + struct xfs_mount *mp = bp->b_target->bt_mount; + int agfl_ok = 1; + + /* + * There is no verification of non-crc AGFLs because mkfs does not + * initialise the AGFL to zero or NULL. Hence the only valid part of the + * AGFL is what the AGF says is active. We can't get to the AGF, so we + * can't verify just those entries are valid. + */ + if (!xfs_sb_version_hascrc(&mp->m_sb)) + return; + + agfl_ok = xfs_verify_cksum(bp->b_addr, BBTOB(bp->b_length), + offsetof(struct xfs_agfl, agfl_crc)); + + agfl_ok = agfl_ok && xfs_agfl_verify(bp); if (!agfl_ok) { - XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, mp, agfl); + XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, mp, bp->b_addr); xfs_buf_ioerror(bp, EFSCORRUPTED); } -#endif } static void xfs_agfl_write_verify( struct xfs_buf *bp) { - xfs_agfl_verify(bp); -} + struct xfs_mount *mp = bp->b_target->bt_mount; + struct xfs_buf_log_item *bip = bp->b_fspriv; -static void -xfs_agfl_read_verify( - struct xfs_buf *bp) -{ - xfs_agfl_verify(bp); + /* no verification of non-crc AGFLs */ + if (!xfs_sb_version_hascrc(&mp->m_sb)) + return; + + if (!xfs_agfl_verify(bp)) { + XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, mp, bp->b_addr); + xfs_buf_ioerror(bp, EFSCORRUPTED); + return; + } + + if (bip) + XFS_BUF_TO_AGFL(bp)->agfl_lsn = cpu_to_be64(bip->bli_item.li_lsn); + + xfs_update_cksum(bp->b_addr, BBTOB(bp->b_length), + offsetof(struct xfs_agfl, agfl_crc)); } const struct xfs_buf_ops xfs_agfl_buf_ops = { @@ -1984,18 +2015,18 @@ xfs_alloc_get_freelist( int btreeblk) /* destination is a AGF btree */ { xfs_agf_t *agf; /* a.g. freespace structure */ - xfs_agfl_t *agfl; /* a.g. freelist structure */ xfs_buf_t *agflbp;/* buffer for a.g. freelist structure */ xfs_agblock_t bno; /* block number returned */ + __be32 *agfl_bno; int error; int logflags; - xfs_mount_t *mp; /* mount structure */ + xfs_mount_t *mp = tp->t_mountp; xfs_perag_t *pag; /* per allocation group data */ - agf = XFS_BUF_TO_AGF(agbp); /* * Freelist is empty, give up. */ + agf = XFS_BUF_TO_AGF(agbp); if (!agf->agf_flcount) { *bnop = NULLAGBLOCK; return 0; @@ -2003,15 +2034,17 @@ xfs_alloc_get_freelist( /* * Read the array of free blocks. */ - mp = tp->t_mountp; - if ((error = xfs_alloc_read_agfl(mp, tp, - be32_to_cpu(agf->agf_seqno), &agflbp))) + error = xfs_alloc_read_agfl(mp, tp, be32_to_cpu(agf->agf_seqno), + &agflbp); + if (error) return error; - agfl = XFS_BUF_TO_AGFL(agflbp); + + /* * Get the block number and update the data structures. */ - bno = be32_to_cpu(agfl->agfl_bno[be32_to_cpu(agf->agf_flfirst)]); + agfl_bno = XFS_BUF_TO_AGFL_BNO(mp, agflbp); + bno = be32_to_cpu(agfl_bno[be32_to_cpu(agf->agf_flfirst)]); be32_add_cpu(&agf->agf_flfirst, 1); xfs_trans_brelse(tp, agflbp); if (be32_to_cpu(agf->agf_flfirst) == XFS_AGFL_SIZE(mp)) @@ -2104,12 +2137,13 @@ xfs_alloc_put_freelist( int btreeblk) /* block came from a AGF btree */ { xfs_agf_t *agf; /* a.g. freespace structure */ - xfs_agfl_t *agfl; /* a.g. free block array */ __be32 *blockp;/* pointer to array entry */ int error; int logflags; xfs_mount_t *mp; /* mount structure */ xfs_perag_t *pag; /* per allocation group data */ + __be32 *agfl_bno; + int startoff; agf = XFS_BUF_TO_AGF(agbp); mp = tp->t_mountp; @@ -2117,7 +2151,6 @@ xfs_alloc_put_freelist( if (!agflbp && (error = xfs_alloc_read_agfl(mp, tp, be32_to_cpu(agf->agf_seqno), &agflbp))) return error; - agfl = XFS_BUF_TO_AGFL(agflbp); be32_add_cpu(&agf->agf_fllast, 1); if (be32_to_cpu(agf->agf_fllast) == XFS_AGFL_SIZE(mp)) agf->agf_fllast = 0; @@ -2138,13 +2171,17 @@ xfs_alloc_put_freelist( xfs_alloc_log_agf(tp, agbp, logflags); ASSERT(be32_to_cpu(agf->agf_flcount) <= XFS_AGFL_SIZE(mp)); - blockp = &agfl->agfl_bno[be32_to_cpu(agf->agf_fllast)]; + + agfl_bno = XFS_BUF_TO_AGFL_BNO(mp, agflbp); + blockp = &agfl_bno[be32_to_cpu(agf->agf_fllast)]; *blockp = cpu_to_be32(bno); + startoff = (char *)blockp - (char *)agflbp->b_addr; + xfs_alloc_log_agf(tp, agbp, logflags); - xfs_trans_log_buf(tp, agflbp, - (int)((xfs_caddr_t)blockp - (xfs_caddr_t)agfl), - (int)((xfs_caddr_t)blockp - (xfs_caddr_t)agfl + - sizeof(xfs_agblock_t) - 1)); + + xfs_trans_buf_set_type(tp, agflbp, XFS_BLF_AGFL_BUF); + xfs_trans_log_buf(tp, agflbp, startoff, + startoff + sizeof(xfs_agblock_t) - 1); return 0; } diff --git a/fs/xfs/xfs_buf_item.h b/fs/xfs/xfs_buf_item.h index 76bd7a1..067d5f0 100644 --- a/fs/xfs/xfs_buf_item.h +++ b/fs/xfs/xfs_buf_item.h @@ -46,13 +46,15 @@ extern kmem_zone_t *xfs_buf_item_zone; */ #define XFS_BLF_BTREE_BUF (1<<5) #define XFS_BLF_AGF_BUF (1<<6) +#define XFS_BLF_AGFL_BUF (1<<7) #define XFS_BLF_TYPE_MASK \ (XFS_BLF_UDQUOT_BUF | \ XFS_BLF_PDQUOT_BUF | \ XFS_BLF_GDQUOT_BUF | \ XFS_BLF_BTREE_BUF | \ - XFS_BLF_AGF_BUF) + XFS_BLF_AGF_BUF | \ + XFS_BLF_AGFL_BUF) #define XFS_BLF_CHUNK 128 #define XFS_BLF_SHIFT 7 diff --git a/fs/xfs/xfs_fsops.c b/fs/xfs/xfs_fsops.c index b6cca27..a693a54 100644 --- a/fs/xfs/xfs_fsops.c +++ b/fs/xfs/xfs_fsops.c @@ -268,6 +268,11 @@ xfs_growfs_data_private( } agfl = XFS_BUF_TO_AGFL(bp); + if (xfs_sb_version_hascrc(&mp->m_sb)) { + agfl->agfl_magicnum = cpu_to_be32(XFS_AGFL_MAGIC); + agfl->agfl_seqno = cpu_to_be32(agno); + uuid_copy(&agfl->agfl_uuid, &mp->m_sb.sb_uuid); + } for (bucket = 0; bucket < XFS_AGFL_SIZE(mp); bucket++) agfl->agfl_bno[bucket] = cpu_to_be32(NULLAGBLOCK); diff --git a/fs/xfs/xfs_log_recover.c b/fs/xfs/xfs_log_recover.c index 2943d53..8fefbc5 100644 --- a/fs/xfs/xfs_log_recover.c +++ b/fs/xfs/xfs_log_recover.c @@ -1961,6 +1961,16 @@ xlog_recover_do_reg_buffer( } bp->b_ops = &xfs_agf_buf_ops; break; + case XFS_BLF_AGFL_BUF: + if (!xfs_sb_version_hascrc(&mp->m_sb)) + break; + if (*(__be32 *)bp->b_addr != cpu_to_be32(XFS_AGFL_MAGIC)) { + xfs_warn(mp, "Bad AGFL block magic!"); + ASSERT(0); + break; + } + bp->b_ops = &xfs_agfl_buf_ops; + break; default: break; } -- 1.7.10.4 From dave@fromorbit.com Tue Mar 12 07:31:17 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 0B97B7F88 for ; Tue, 12 Mar 2013 07:31:16 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay3.corp.sgi.com (Postfix) with ESMTP id 7E775AC004 for ; Tue, 12 Mar 2013 05:31:15 -0700 (PDT) X-ASG-Debug-ID: 1363091470-04cbb07dbe487eb0002-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id dErOtUZxAZZvrpb6 for ; Tue, 12 Mar 2013 05:31:12 -0700 (PDT) X-Barracuda-Envelope-From: dave@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: Ag8KAKEfP1F5LKiV/2dsb2JhbAA7CMRdAwGBSRd0gigBAQUnLzMIGDE5AxsZiBKwApAfjVg0dgaDTAOLdJFNigmDHiiBMCQ Received: from ppp121-44-168-149.lns20.syd7.internode.on.net (HELO dastard) ([121.44.168.149]) by ipmail05.adl6.internode.on.net with ESMTP; 12 Mar 2013 23:01:09 +1030 Received: from disappointment ([192.168.1.1]) by dastard with esmtp (Exim 4.76) (envelope-from ) id 1UFOM6-0001Rp-Az for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:30:58 +1100 Received: from dave by disappointment with local (Exim 4.80) (envelope-from ) id 1UFOM6-0002MG-7e for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:30:58 +1100 From: Dave Chinner To: xfs@oss.sgi.com Subject: [PATCH 09/21] xfs: add version 3 inode format with CRCs Date: Tue, 12 Mar 2013 23:30:42 +1100 X-ASG-Orig-Subj: [PATCH 09/21] xfs: add version 3 inode format with CRCs Message-Id: <1363091454-8852-10-git-send-email-david@fromorbit.com> X-Mailer: git-send-email 1.7.10.4 In-Reply-To: <1363091454-8852-1-git-send-email-david@fromorbit.com> References: <1363091454-8852-1-git-send-email-david@fromorbit.com> X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1363091472 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124988 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- From: Christoph Hellwig Add a new inode version with a larger core. The primary objective is to allow for a crc of the inode, and location information (uuid and ino) to verify it was written in the right place. We also extend it by: a creation time (for Samba); a changecount (for NFSv4); a flush sequence (in LSN format for recovery); an additional inode flags field; and some additional padding. These additional fields are not implemented yet, but already laid out in the structure. [dchinner@redhat.com] Added LSN and flags field, some factoring and rework to capture all the necessary information in the crc calculation. Signed-off-by: Christoph Hellwig Signed-off-by: Dave Chinner --- fs/xfs/xfs_buf_item.h | 4 +- fs/xfs/xfs_dinode.h | 33 +++++++-- fs/xfs/xfs_ialloc.c | 23 +++++- fs/xfs/xfs_inode.c | 179 ++++++++++++++++++++++++++++++++-------------- fs/xfs/xfs_inode.h | 26 +++++++ fs/xfs/xfs_inode_item.c | 2 +- fs/xfs/xfs_log_recover.c | 35 +++++++-- fs/xfs/xfs_trans_buf.c | 5 +- 8 files changed, 237 insertions(+), 70 deletions(-) diff --git a/fs/xfs/xfs_buf_item.h b/fs/xfs/xfs_buf_item.h index c256606..abae8c8 100644 --- a/fs/xfs/xfs_buf_item.h +++ b/fs/xfs/xfs_buf_item.h @@ -48,6 +48,7 @@ extern kmem_zone_t *xfs_buf_item_zone; #define XFS_BLF_AGF_BUF (1<<6) #define XFS_BLF_AGFL_BUF (1<<7) #define XFS_BLF_AGI_BUF (1<<8) +#define XFS_BLF_DINO_BUF (1<<9) #define XFS_BLF_TYPE_MASK \ (XFS_BLF_UDQUOT_BUF | \ @@ -56,7 +57,8 @@ extern kmem_zone_t *xfs_buf_item_zone; XFS_BLF_BTREE_BUF | \ XFS_BLF_AGF_BUF | \ XFS_BLF_AGFL_BUF | \ - XFS_BLF_AGI_BUF) + XFS_BLF_AGI_BUF | \ + XFS_BLF_DINO_BUF) #define XFS_BLF_CHUNK 128 #define XFS_BLF_SHIFT 7 diff --git a/fs/xfs/xfs_dinode.h b/fs/xfs/xfs_dinode.h index 6b5bd17..bdc946a 100644 --- a/fs/xfs/xfs_dinode.h +++ b/fs/xfs/xfs_dinode.h @@ -19,7 +19,7 @@ #define __XFS_DINODE_H__ #define XFS_DINODE_MAGIC 0x494e /* 'IN' */ -#define XFS_DINODE_GOOD_VERSION(v) (((v) == 1 || (v) == 2)) +#define XFS_DINODE_GOOD_VERSION(v) ((v) >= 1 && (v) <= 3) typedef struct xfs_timestamp { __be32 t_sec; /* timestamp seconds */ @@ -70,11 +70,36 @@ typedef struct xfs_dinode { /* di_next_unlinked is the only non-core field in the old dinode */ __be32 di_next_unlinked;/* agi unlinked list ptr */ -} __attribute__((packed)) xfs_dinode_t; + + /* start of the extended dinode, writable fields */ + __be32 di_crc; /* CRC of the inode */ + __be64 di_changecount; /* number of attribute changes */ + __be64 di_lsn; /* flush sequence */ + __be64 di_flags2; /* more random flags */ + __u8 di_pad2[16]; /* more padding for future expansion */ + + /* fields only written to during inode creation */ + xfs_timestamp_t di_crtime; /* time created */ + __be64 di_ino; /* inode number */ + uuid_t di_uuid; /* UUID of the filesystem */ + + /* structure must be padded to 64 bit alignment */ +} xfs_dinode_t; #define DI_MAX_FLUSH 0xffff /* + * Size of the core inode on disk. Version 1 and 2 inodes have + * the same size, but version 3 has grown a few additional fields. + */ +static inline uint xfs_dinode_size(int version) +{ + if (version == 3) + return sizeof(struct xfs_dinode); + return offsetof(struct xfs_dinode, di_crc); +} + +/* * The 32 bit link count in the inode theoretically maxes out at UINT_MAX. * Since the pathconf interface is signed, we use 2^31 - 1 instead. * The old inode format had a 16 bit link count, so its maximum is USHRT_MAX. @@ -105,7 +130,7 @@ typedef enum xfs_dinode_fmt { * Inode size for given fs. */ #define XFS_LITINO(mp, version) \ - ((int)(((mp)->m_sb.sb_inodesize) - sizeof(struct xfs_dinode))) + ((int)(((mp)->m_sb.sb_inodesize) - xfs_dinode_size(version))) #define XFS_BROOT_SIZE_ADJ(ip) \ (XFS_BMBT_BLOCK_LEN((ip)->i_mount) - sizeof(xfs_bmdr_block_t)) @@ -133,7 +158,7 @@ typedef enum xfs_dinode_fmt { * Return pointers to the data or attribute forks. */ #define XFS_DFORK_DPTR(dip) \ - ((char *)(dip) + sizeof(struct xfs_dinode)) + ((char *)dip + xfs_dinode_size(dip->di_version)) #define XFS_DFORK_APTR(dip) \ (XFS_DFORK_DPTR(dip) + XFS_DFORK_BOFF(dip)) #define XFS_DFORK_PTR(dip,w) \ diff --git a/fs/xfs/xfs_ialloc.c b/fs/xfs/xfs_ialloc.c index 6d0a495..8ceaa11 100644 --- a/fs/xfs/xfs_ialloc.c +++ b/fs/xfs/xfs_ialloc.c @@ -167,6 +167,7 @@ xfs_ialloc_inode_init( int version; int i, j; xfs_daddr_t d; + xfs_ino_t ino = 0; /* * Loop over the new block(s), filling in the inodes. @@ -190,8 +191,18 @@ xfs_ialloc_inode_init( * the new inode format, then use the new inode version. Otherwise * use the old version so that old kernels will continue to be * able to use the file system. + * + * For v3 inodes, we also need to write the inode number into the inode, + * so calculate the first inode number of the chunk here as + * XFS_OFFBNO_TO_AGINO() only works on filesystem block boundaries, not + * cluster boundaries and so cannot be used in the cluster buffer loop + * below. */ - if (xfs_sb_version_hasnlink(&mp->m_sb)) + if (xfs_sb_version_hascrc(&mp->m_sb)) { + version = 3; + ino = XFS_AGINO_TO_INO(mp, agno, + XFS_OFFBNO_TO_AGINO(mp, agbno, 0)); + } else if (xfs_sb_version_hasnlink(&mp->m_sb)) version = 2; else version = 1; @@ -217,13 +228,21 @@ xfs_ialloc_inode_init( xfs_buf_zero(fbuf, 0, ninodes << mp->m_sb.sb_inodelog); for (i = 0; i < ninodes; i++) { int ioffset = i << mp->m_sb.sb_inodelog; - uint isize = sizeof(struct xfs_dinode); + uint isize = xfs_dinode_size(version); free = xfs_make_iptr(mp, fbuf, i); free->di_magic = cpu_to_be16(XFS_DINODE_MAGIC); free->di_version = version; free->di_gen = cpu_to_be32(gen); free->di_next_unlinked = cpu_to_be32(NULLAGINO); + + if (version == 3) { + free->di_ino = cpu_to_be64(ino); + ino++; + uuid_copy(&free->di_uuid, &mp->m_sb.sb_uuid); + xfs_dinode_calc_crc(mp, free); + } + xfs_trans_log_buf(tp, fbuf, ioffset, ioffset + isize - 1); } xfs_trans_inode_alloc_buf(tp, fbuf); diff --git a/fs/xfs/xfs_inode.c b/fs/xfs/xfs_inode.c index 202ce37..558ef49 100644 --- a/fs/xfs/xfs_inode.c +++ b/fs/xfs/xfs_inode.c @@ -44,6 +44,7 @@ #include "xfs_quota.h" #include "xfs_filestream.h" #include "xfs_vnodeops.h" +#include "xfs_cksum.h" #include "xfs_trace.h" #include "xfs_icache.h" @@ -866,6 +867,17 @@ xfs_dinode_from_disk( to->di_dmstate = be16_to_cpu(from->di_dmstate); to->di_flags = be16_to_cpu(from->di_flags); to->di_gen = be32_to_cpu(from->di_gen); + + if (to->di_version == 3) { + to->di_changecount = be64_to_cpu(from->di_changecount); + to->di_crtime.t_sec = be32_to_cpu(from->di_crtime.t_sec); + to->di_crtime.t_nsec = be32_to_cpu(from->di_crtime.t_nsec); + to->di_flags2 = be64_to_cpu(from->di_flags2); + to->di_ino = be64_to_cpu(from->di_ino); + to->di_lsn = be64_to_cpu(from->di_lsn); + memcpy(to->di_pad2, from->di_pad2, sizeof(to->di_pad2)); + uuid_copy(&to->di_uuid, &from->di_uuid); + } } void @@ -902,6 +914,17 @@ xfs_dinode_to_disk( to->di_dmstate = cpu_to_be16(from->di_dmstate); to->di_flags = cpu_to_be16(from->di_flags); to->di_gen = cpu_to_be32(from->di_gen); + + if (from->di_version == 3) { + to->di_changecount = cpu_to_be64(from->di_changecount); + to->di_crtime.t_sec = cpu_to_be32(from->di_crtime.t_sec); + to->di_crtime.t_nsec = cpu_to_be32(from->di_crtime.t_nsec); + to->di_flags2 = cpu_to_be64(from->di_flags2); + to->di_ino = cpu_to_be64(from->di_ino); + to->di_lsn = cpu_to_be64(from->di_lsn); + memcpy(to->di_pad2, from->di_pad2, sizeof(to->di_pad2)); + uuid_copy(&to->di_uuid, &from->di_uuid); + } } STATIC uint @@ -962,6 +985,47 @@ xfs_dic2xflags( (XFS_DFORK_Q(dip) ? XFS_XFLAG_HASATTR : 0); } +static bool +xfs_dinode_verify( + struct xfs_mount *mp, + struct xfs_inode *ip, + struct xfs_dinode *dip) +{ + if (dip->di_magic != cpu_to_be16(XFS_DINODE_MAGIC)) + return false; + + /* only version 3 or greater inodes are extensively verified here */ + if (dip->di_version < 3) + return true; + + if (!xfs_sb_version_hascrc(&mp->m_sb)) + return false; + if (!xfs_verify_cksum((char *)dip, mp->m_sb.sb_inodesize, + offsetof(struct xfs_dinode, di_crc))) + return false; + if (be64_to_cpu(dip->di_ino) != ip->i_ino) + return false; + if (!uuid_equal(&dip->di_uuid, &mp->m_sb.sb_uuid)) + return false; + return true; +} + +void +xfs_dinode_calc_crc( + struct xfs_mount *mp, + struct xfs_dinode *dip) +{ + __uint32_t crc; + + if (dip->di_version < 3) + return; + + ASSERT(xfs_sb_version_hascrc(&mp->m_sb)); + crc = xfs_start_cksum((char *)dip, mp->m_sb.sb_inodesize, + offsetof(struct xfs_dinode, di_crc)); + dip->di_crc = xfs_end_cksum(crc); +} + /* * Read the disk inode attributes into the in-core inode structure. */ @@ -990,17 +1054,13 @@ xfs_iread( if (error) return error; - /* - * If we got something that isn't an inode it means someone - * (nfs or dmi) has a stale handle. - */ - if (dip->di_magic != cpu_to_be16(XFS_DINODE_MAGIC)) { -#ifdef DEBUG - xfs_alert(mp, - "%s: dip->di_magic (0x%x) != XFS_DINODE_MAGIC (0x%x)", - __func__, be16_to_cpu(dip->di_magic), XFS_DINODE_MAGIC); -#endif /* DEBUG */ - error = XFS_ERROR(EINVAL); + /* even unallocated inodes are verified */ + if (!xfs_dinode_verify(mp, ip, dip)) { + xfs_alert(mp, "%s: validation failed for inode %lld failed", + __func__, ip->i_ino); + + XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, mp, dip); + error = XFS_ERROR(EFSCORRUPTED); goto out_brelse; } @@ -1022,10 +1082,20 @@ xfs_iread( goto out_brelse; } } else { + /* + * Partial initialisation of the in-core inode. Just the bits + * that xfs_ialloc won't overwrite or relies on being correct. + */ ip->i_d.di_magic = be16_to_cpu(dip->di_magic); ip->i_d.di_version = dip->di_version; ip->i_d.di_gen = be32_to_cpu(dip->di_gen); ip->i_d.di_flushiter = be16_to_cpu(dip->di_flushiter); + + if (dip->di_version == 3) { + ip->i_d.di_ino = be64_to_cpu(dip->di_ino); + uuid_copy(&ip->i_d.di_uuid, &dip->di_uuid); + } + /* * Make sure to pull in the mode here as well in * case the inode is released without being used. @@ -1161,6 +1231,7 @@ xfs_ialloc( xfs_buf_t **ialloc_context, xfs_inode_t **ipp) { + struct xfs_mount *mp = tp->t_mountp; xfs_ino_t ino; xfs_inode_t *ip; uint flags; @@ -1187,7 +1258,7 @@ xfs_ialloc( * This is because we're setting fields here we need * to prevent others from looking at until we're done. */ - error = xfs_iget(tp->t_mountp, tp, ino, XFS_IGET_CREATE, + error = xfs_iget(mp, tp, ino, XFS_IGET_CREATE, XFS_ILOCK_EXCL, &ip); if (error) return error; @@ -1208,7 +1279,7 @@ xfs_ialloc( * the inode version number now. This way we only do the conversion * here rather than here and in the flush/logging code. */ - if (xfs_sb_version_hasnlink(&tp->t_mountp->m_sb) && + if (xfs_sb_version_hasnlink(&mp->m_sb) && ip->i_d.di_version == 1) { ip->i_d.di_version = 2; /* @@ -1258,6 +1329,19 @@ xfs_ialloc( ip->i_d.di_dmevmask = 0; ip->i_d.di_dmstate = 0; ip->i_d.di_flags = 0; + + if (ip->i_d.di_version == 3) { + ASSERT(ip->i_d.di_ino == ino); + ASSERT(uuid_equal(&ip->i_d.di_uuid, &mp->m_sb.sb_uuid)); + ip->i_d.di_crc = 0; + ip->i_d.di_changecount = 1; + ip->i_d.di_lsn = 0; + ip->i_d.di_flags2 = 0; + memset(&(ip->i_d.di_pad2[0]), 0, sizeof(ip->i_d.di_pad2)); + ip->i_d.di_crtime = ip->i_d.di_mtime; + } + + flags = XFS_ILOG_CORE; switch (mode & S_IFMT) { case S_IFIFO: @@ -2716,20 +2800,18 @@ abort_out: STATIC int xfs_iflush_int( - xfs_inode_t *ip, - xfs_buf_t *bp) + struct xfs_inode *ip, + struct xfs_buf *bp) { - xfs_inode_log_item_t *iip; - xfs_dinode_t *dip; - xfs_mount_t *mp; + struct xfs_inode_log_item *iip = ip->i_itemp; + struct xfs_dinode *dip; + struct xfs_mount *mp = ip->i_mount; ASSERT(xfs_isilocked(ip, XFS_ILOCK_EXCL|XFS_ILOCK_SHARED)); ASSERT(xfs_isiflocked(ip)); ASSERT(ip->i_d.di_format != XFS_DINODE_FMT_BTREE || ip->i_d.di_nextents > XFS_IFORK_MAXEXT(ip, XFS_DATA_FORK)); - - iip = ip->i_itemp; - mp = ip->i_mount; + ASSERT(iip != NULL && iip->ili_fields != 0); /* set *dip = inode's place in the buffer */ dip = (xfs_dinode_t *)xfs_buf_offset(bp, ip->i_imap.im_boffset); @@ -2790,9 +2872,9 @@ xfs_iflush_int( } /* * bump the flush iteration count, used to detect flushes which - * postdate a log record during recovery. + * postdate a log record during recovery. This is redundant as we now + * log every change and hence this can't happen. Still, it doesn't hurt. */ - ip->i_d.di_flushiter++; /* @@ -2868,41 +2950,30 @@ xfs_iflush_int( * need the AIL lock, because it is a 64 bit value that cannot be read * atomically. */ - if (iip != NULL && iip->ili_fields != 0) { - iip->ili_last_fields = iip->ili_fields; - iip->ili_fields = 0; - iip->ili_logged = 1; + iip->ili_last_fields = iip->ili_fields; + iip->ili_fields = 0; + iip->ili_logged = 1; - xfs_trans_ail_copy_lsn(mp->m_ail, &iip->ili_flush_lsn, - &iip->ili_item.li_lsn); + xfs_trans_ail_copy_lsn(mp->m_ail, &iip->ili_flush_lsn, + &iip->ili_item.li_lsn); - /* - * Attach the function xfs_iflush_done to the inode's - * buffer. This will remove the inode from the AIL - * and unlock the inode's flush lock when the inode is - * completely written to disk. - */ - xfs_buf_attach_iodone(bp, xfs_iflush_done, &iip->ili_item); + /* + * Attach the function xfs_iflush_done to the inode's + * buffer. This will remove the inode from the AIL + * and unlock the inode's flush lock when the inode is + * completely written to disk. + */ + xfs_buf_attach_iodone(bp, xfs_iflush_done, &iip->ili_item); - ASSERT(bp->b_fspriv != NULL); - ASSERT(bp->b_iodone != NULL); - } else { - /* - * We're flushing an inode which is not in the AIL and has - * not been logged. For this case we can immediately drop - * the inode flush lock because we can avoid the whole - * AIL state thing. It's OK to drop the flush lock now, - * because we've already locked the buffer and to do anything - * you really need both. - */ - if (iip != NULL) { - ASSERT(iip->ili_logged == 0); - ASSERT(iip->ili_last_fields == 0); - ASSERT((iip->ili_item.li_flags & XFS_LI_IN_AIL) == 0); - } - xfs_ifunlock(ip); - } + /* update the lsn in the on disk inode if required */ + if (ip->i_d.di_version == 3) + dip->di_lsn = cpu_to_be64(iip->ili_item.li_lsn); + + /* generate the checksum. */ + xfs_dinode_calc_crc(mp, dip); + ASSERT(bp->b_fspriv != NULL); + ASSERT(bp->b_iodone != NULL); return 0; corrupt_out: diff --git a/fs/xfs/xfs_inode.h b/fs/xfs/xfs_inode.h index b8520b5..9112979 100644 --- a/fs/xfs/xfs_inode.h +++ b/fs/xfs/xfs_inode.h @@ -150,13 +150,38 @@ typedef struct xfs_icdinode { __uint16_t di_dmstate; /* DMIG state info */ __uint16_t di_flags; /* random flags, XFS_DIFLAG_... */ __uint32_t di_gen; /* generation number */ + + /* di_next_unlinked is the only non-core field in the old dinode */ + xfs_agino_t di_next_unlinked;/* agi unlinked list ptr */ + + /* start of the extended dinode, writable fields */ + __uint32_t di_crc; /* CRC of the inode */ + __uint64_t di_changecount; /* number of attribute changes */ + xfs_lsn_t di_lsn; /* flush sequence */ + __uint64_t di_flags2; /* more random flags */ + __uint8_t di_pad2[16]; /* more padding for future expansion */ + + /* fields only written to during inode creation */ + xfs_ictimestamp_t di_crtime; /* time created */ + xfs_ino_t di_ino; /* inode number */ + uuid_t di_uuid; /* UUID of the filesystem */ + + /* structure must be padded to 64 bit alignment */ } xfs_icdinode_t; +static inline uint xfs_icdinode_size(int version) +{ + if (version == 3) + return sizeof(struct xfs_icdinode); + return offsetof(struct xfs_icdinode, di_next_unlinked); +} + /* * Flags for xfs_ichgtime(). */ #define XFS_ICHGTIME_MOD 0x1 /* data fork modification timestamp */ #define XFS_ICHGTIME_CHG 0x2 /* inode field change timestamp */ +#define XFS_ICHGTIME_CREATE 0x4 /* inode create timestamp */ /* * Per-fork incore inode flags. @@ -556,6 +581,7 @@ int xfs_imap_to_bp(struct xfs_mount *, struct xfs_trans *, struct xfs_buf **, uint, uint); int xfs_iread(struct xfs_mount *, struct xfs_trans *, struct xfs_inode *, uint); +void xfs_dinode_calc_crc(struct xfs_mount *, struct xfs_dinode *); void xfs_dinode_to_disk(struct xfs_dinode *, struct xfs_icdinode *); void xfs_idestroy_fork(struct xfs_inode *, int); diff --git a/fs/xfs/xfs_inode_item.c b/fs/xfs/xfs_inode_item.c index f034bd1..f76ff52 100644 --- a/fs/xfs/xfs_inode_item.c +++ b/fs/xfs/xfs_inode_item.c @@ -179,7 +179,7 @@ xfs_inode_item_format( nvecs = 1; vecp->i_addr = &ip->i_d; - vecp->i_len = sizeof(struct xfs_icdinode); + vecp->i_len = xfs_icdinode_size(ip->i_d.di_version); vecp->i_type = XLOG_REG_TYPE_ICORE; vecp++; nvecs++; diff --git a/fs/xfs/xfs_log_recover.c b/fs/xfs/xfs_log_recover.c index d750c34..6d08eaa 100644 --- a/fs/xfs/xfs_log_recover.c +++ b/fs/xfs/xfs_log_recover.c @@ -1786,6 +1786,7 @@ xlog_recover_do_inode_buffer( xfs_agino_t *buffer_nextp; trace_xfs_log_recover_buf_inode_buf(mp->m_log, buf_f); + bp->b_ops = &xfs_inode_buf_ops; inodes_per_buf = BBTOB(bp->b_io_length) >> mp->m_sb.sb_inodelog; for (i = 0; i < inodes_per_buf; i++) { @@ -1930,6 +1931,9 @@ xlog_recover_do_reg_buffer( /* Shouldn't be any more regions */ ASSERT(i == item->ri_total); + /* Shouldn't be any more regions */ + ASSERT(i == item->ri_total); + switch (buf_f->blf_flags & XFS_BLF_TYPE_MASK) { case XFS_BLF_BTREE_BUF: switch (be32_to_cpu(*(__be32 *)bp->b_addr)) { @@ -1989,6 +1993,18 @@ xlog_recover_do_reg_buffer( } bp->b_ops = &xfs_dquot_buf_ops; break; + case XFS_BLF_DINO_BUF: + /* + * we get here with inode allocation buffers, not buffers that + * track unlinked list changes. + */ + if (*(__be16 *)bp->b_addr != cpu_to_be16(XFS_DINODE_MAGIC)) { + xfs_warn(mp, "Bad INODE block magic!"); + ASSERT(0); + break; + } + bp->b_ops = &xfs_inode_buf_ops; + break; default: break; } @@ -2277,6 +2293,7 @@ xlog_recover_inode_pass2( int attr_index; uint fields; xfs_icdinode_t *dicp; + uint isize; int need_free = 0; if (item->ri_buf[0].i_len == sizeof(xfs_inode_log_format_t)) { @@ -2302,7 +2319,7 @@ xlog_recover_inode_pass2( trace_xfs_log_recover_inode_recover(log, in_f); bp = xfs_buf_read(mp->m_ddev_targp, in_f->ilf_blkno, in_f->ilf_len, 0, - NULL); + &xfs_inode_buf_ops); if (!bp) { error = ENOMEM; goto error; @@ -2413,7 +2430,8 @@ xlog_recover_inode_pass2( error = EFSCORRUPTED; goto error; } - if (unlikely(item->ri_buf[1].i_len > sizeof(struct xfs_icdinode))) { + isize = xfs_icdinode_size(dicp->di_version); + if (unlikely(item->ri_buf[1].i_len > isize)) { XFS_CORRUPTION_ERROR("xlog_recover_inode_pass2(7)", XFS_ERRLEVEL_LOW, mp, dicp); xfs_buf_relse(bp); @@ -2425,13 +2443,13 @@ xlog_recover_inode_pass2( } /* The core is in in-core format */ - xfs_dinode_to_disk(dip, item->ri_buf[1].i_addr); + xfs_dinode_to_disk(dip, dicp); /* the rest is in on-disk format */ - if (item->ri_buf[1].i_len > sizeof(struct xfs_icdinode)) { - memcpy((xfs_caddr_t) dip + sizeof(struct xfs_icdinode), - item->ri_buf[1].i_addr + sizeof(struct xfs_icdinode), - item->ri_buf[1].i_len - sizeof(struct xfs_icdinode)); + if (item->ri_buf[1].i_len > isize) { + memcpy((char *)dip + isize, + item->ri_buf[1].i_addr + isize, + item->ri_buf[1].i_len - isize); } fields = in_f->ilf_fields; @@ -2515,6 +2533,9 @@ xlog_recover_inode_pass2( } write_inode_buffer: + /* re-generate the checksum. */ + xfs_dinode_calc_crc(log->l_mp, dip); + ASSERT(bp->b_target->bt_mount == mp); bp->b_iodone = xlog_recover_iodone; xfs_buf_delwri_queue(bp, buffer_list); diff --git a/fs/xfs/xfs_trans_buf.c b/fs/xfs/xfs_trans_buf.c index f950edd..8a0f6af 100644 --- a/fs/xfs/xfs_trans_buf.c +++ b/fs/xfs/xfs_trans_buf.c @@ -704,12 +704,13 @@ xfs_trans_inode_buf( ASSERT(atomic_read(&bip->bli_refcount) > 0); bip->bli_flags |= XFS_BLI_INODE_BUF; + xfs_trans_buf_set_type(tp, bp, XFS_BLF_DINO_BUF); } /* * This call is used to indicate that the buffer is going to * be staled and was an inode buffer. This means it gets - * special processing during unpin - where any inodes + * special processing during unpin - where any inodes * associated with the buffer should be removed from ail. * There is also special processing during recovery, * any replay of the inodes in the buffer needs to be @@ -728,6 +729,7 @@ xfs_trans_stale_inode_buf( bip->bli_flags |= XFS_BLI_STALE_INODE; bip->bli_item.li_cb = xfs_buf_iodone; + xfs_trans_buf_set_type(tp, bp, XFS_BLF_DINO_BUF); } /* @@ -751,6 +753,7 @@ xfs_trans_inode_alloc_buf( ASSERT(atomic_read(&bip->bli_refcount) > 0); bip->bli_flags |= XFS_BLI_INODE_ALLOC_BUF; + xfs_trans_buf_set_type(tp, bp, XFS_BLF_DINO_BUF); } /* -- 1.7.10.4 From dave@fromorbit.com Tue Mar 12 07:31:20 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id F2F797F9F for ; Tue, 12 Mar 2013 07:31:17 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay3.corp.sgi.com (Postfix) with ESMTP id 72352AC002 for ; Tue, 12 Mar 2013 05:31:14 -0700 (PDT) X-ASG-Debug-ID: 1363091471-04cb6c2b04493020001-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id uBOf1Z693WoDHoH4 for ; Tue, 12 Mar 2013 05:31:12 -0700 (PDT) X-Barracuda-Envelope-From: dave@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: Ag8KAKEfP1F5LKiV/2dsb2JhbABDxF0DAYFJF3SCKAEBBScvMwgYMTkDGxmIErACkB+NXi52BoNMA6dKgx4ogS8BHgY Received: from ppp121-44-168-149.lns20.syd7.internode.on.net (HELO dastard) ([121.44.168.149]) by ipmail05.adl6.internode.on.net with ESMTP; 12 Mar 2013 23:01:09 +1030 Received: from disappointment ([192.168.1.1]) by dastard with esmtp (Exim 4.76) (envelope-from ) id 1UFOMG-0001Ro-9e for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:31:08 +1100 Received: from dave by disappointment with local (Exim 4.80) (envelope-from ) id 1UFOM6-0002MB-62 for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:30:58 +1100 From: Dave Chinner To: xfs@oss.sgi.com Subject: [PATCH 08/21] xfs: add CRC checks for quota blocks Date: Tue, 12 Mar 2013 23:30:41 +1100 X-ASG-Orig-Subj: [PATCH 08/21] xfs: add CRC checks for quota blocks Message-Id: <1363091454-8852-9-git-send-email-david@fromorbit.com> X-Mailer: git-send-email 1.7.10.4 In-Reply-To: <1363091454-8852-1-git-send-email-david@fromorbit.com> References: <1363091454-8852-1-git-send-email-david@fromorbit.com> X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1363091471 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124988 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- From: Christoph Hellwig Use the reserved space in struct xfs_dqblk to store a UUID and a crc for the quota blocks. [dchinner@redhat.com] Add a LSN field and update for current verifier infrastructure. Signed-off-by: Christoph Hellwig Signed-off-by: Dave Chinner --- fs/xfs/xfs_dquot.c | 112 ++++++++++++++++++++++++++++++++++++++++------ fs/xfs/xfs_log_recover.c | 10 +++++ fs/xfs/xfs_qm.c | 23 ++++++++-- fs/xfs/xfs_qm.h | 2 + fs/xfs/xfs_quota.h | 11 ++++- 5 files changed, 141 insertions(+), 17 deletions(-) diff --git a/fs/xfs/xfs_dquot.c b/fs/xfs/xfs_dquot.c index 8025eb2..aedf29c 100644 --- a/fs/xfs/xfs_dquot.c +++ b/fs/xfs/xfs_dquot.c @@ -36,6 +36,7 @@ #include "xfs_trans_space.h" #include "xfs_trans_priv.h" #include "xfs_qm.h" +#include "xfs_cksum.h" #include "xfs_trace.h" /* @@ -239,6 +240,8 @@ xfs_qm_init_dquot_blk( d->dd_diskdq.d_version = XFS_DQUOT_VERSION; d->dd_diskdq.d_id = cpu_to_be32(curid); d->dd_diskdq.d_flags = type; + if (xfs_sb_version_hascrc(&mp->m_sb)) + uuid_copy(&d->dd_uuid, &mp->m_sb.sb_uuid); } xfs_trans_dquot_buf(tp, bp, @@ -248,25 +251,87 @@ xfs_qm_init_dquot_blk( xfs_trans_log_buf(tp, bp, 0, BBTOB(q->qi_dqchunklen) - 1); } -static void +STATIC void +xfs_dquot_buf_calc_crc( + struct xfs_mount *mp, + struct xfs_buf *bp) +{ + struct xfs_dqblk *d = (struct xfs_dqblk *)bp->b_addr; + int i; + + if (!xfs_sb_version_hascrc(&mp->m_sb)) + return; + + for (i = 0; i < mp->m_quotainfo->qi_dqperchunk; i++, d++) { + xfs_update_cksum((char *)d, sizeof(struct xfs_dqblk), + offsetof(struct xfs_dqblk, dd_crc)); + } +} + +STATIC bool +xfs_dquot_buf_verify_crc( + struct xfs_mount *mp, + struct xfs_buf *bp) +{ + struct xfs_dqblk *d = (struct xfs_dqblk *)bp->b_addr; + int ndquots; + int i; + + if (!xfs_sb_version_hascrc(&mp->m_sb)) + return true; + + /* + * if we are in log recovery, the quota subsystem has not been + * initialised so we have no quotainfo structure. In that case, we need + * to manually calculate the number of dquots in the buffer. + */ + if (mp->m_quotainfo) + ndquots = mp->m_quotainfo->qi_dqperchunk; + else + ndquots = xfs_qm_calc_dquots_per_chunk(mp, + XFS_BB_TO_FSB(mp, bp->b_length)); + + for (i = 0; i < ndquots; i++, d++) { + if (!xfs_verify_cksum((char *)d, sizeof(struct xfs_dqblk), + offsetof(struct xfs_dqblk, dd_crc))) + return false; + if (!uuid_equal(&d->dd_uuid, &mp->m_sb.sb_uuid)) + return false; + } + + return true; +} + +STATIC bool xfs_dquot_buf_verify( + struct xfs_mount *mp, struct xfs_buf *bp) { - struct xfs_mount *mp = bp->b_target->bt_mount; struct xfs_dqblk *d = (struct xfs_dqblk *)bp->b_addr; - struct xfs_disk_dquot *ddq; xfs_dqid_t id = 0; + int ndquots; int i; /* + * if we are in log recovery, the quota subsystem has not been + * initialised so we have no quotainfo structure. In that case, we need + * to manually calculate the number of dquots in the buffer. + */ + if (mp->m_quotainfo) + ndquots = mp->m_quotainfo->qi_dqperchunk; + else + ndquots = xfs_qm_calc_dquots_per_chunk(mp, bp->b_length); + + /* * On the first read of the buffer, verify that each dquot is valid. * We don't know what the id of the dquot is supposed to be, just that * they should be increasing monotonically within the buffer. If the * first id is corrupt, then it will fail on the second dquot in the * buffer so corruptions could point to the wrong dquot in this case. */ - for (i = 0; i < mp->m_quotainfo->qi_dqperchunk; i++) { - int error; + for (i = 0; i < ndquots; i++) { + struct xfs_disk_dquot *ddq; + int error; ddq = &d[i].dd_diskdq; @@ -274,27 +339,37 @@ xfs_dquot_buf_verify( id = be32_to_cpu(ddq->d_id); error = xfs_qm_dqcheck(mp, ddq, id + i, 0, XFS_QMOPT_DOWARN, - "xfs_dquot_read_verify"); - if (error) { - XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, mp, d); - xfs_buf_ioerror(bp, EFSCORRUPTED); - break; - } + "xfs_dquot_buf_verify"); + if (error) + return false; } + return true; } static void xfs_dquot_buf_read_verify( struct xfs_buf *bp) { - xfs_dquot_buf_verify(bp); + struct xfs_mount *mp = bp->b_target->bt_mount; + + if (!xfs_dquot_buf_verify_crc(mp, bp) || !xfs_dquot_buf_verify(mp, bp)) { + XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, mp, bp->b_addr); + xfs_buf_ioerror(bp, EFSCORRUPTED); + } } void xfs_dquot_buf_write_verify( struct xfs_buf *bp) { - xfs_dquot_buf_verify(bp); + struct xfs_mount *mp = bp->b_target->bt_mount; + + if (!xfs_dquot_buf_verify(mp, bp)) { + XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, mp, bp->b_addr); + xfs_buf_ioerror(bp, EFSCORRUPTED); + return; + } + xfs_dquot_buf_calc_crc(mp, bp); } const struct xfs_buf_ops xfs_dquot_buf_ops = { @@ -1035,6 +1110,17 @@ xfs_qm_dqflush( &dqp->q_logitem.qli_item.li_lsn); /* + * copy the lsn into the on-disk dquot now while we have the in memory + * dquot here. This can't be done later in the write verifier as we + * can't get access to the log item at that point in time. + */ + if (xfs_sb_version_hascrc(&mp->m_sb)) { + struct xfs_dqblk *dqb = (struct xfs_dqblk *)ddqp; + + dqb->dd_lsn = cpu_to_be64(dqp->q_logitem.qli_item.li_lsn); + } + + /* * Attach an iodone routine so that we can remove this dquot from the * AIL and release the flush lock once the dquot is synced to disk. */ diff --git a/fs/xfs/xfs_log_recover.c b/fs/xfs/xfs_log_recover.c index 8f70c4e..d750c34 100644 --- a/fs/xfs/xfs_log_recover.c +++ b/fs/xfs/xfs_log_recover.c @@ -1979,6 +1979,16 @@ xlog_recover_do_reg_buffer( } bp->b_ops = &xfs_agi_buf_ops; break; + case XFS_BLF_UDQUOT_BUF: + case XFS_BLF_PDQUOT_BUF: + case XFS_BLF_GDQUOT_BUF: + if (*(__be16 *)bp->b_addr != cpu_to_be16(XFS_DQUOT_MAGIC)) { + xfs_warn(mp, "Bad DQUOT block magic!"); + ASSERT(0); + break; + } + bp->b_ops = &xfs_dquot_buf_ops; + break; default: break; } diff --git a/fs/xfs/xfs_qm.c b/fs/xfs/xfs_qm.c index e5b5cf9..9d00500 100644 --- a/fs/xfs/xfs_qm.c +++ b/fs/xfs/xfs_qm.c @@ -617,6 +617,20 @@ xfs_qm_dqdetach( } } +int +xfs_qm_calc_dquots_per_chunk( + struct xfs_mount *mp, + unsigned int nbblks) /* basic block units */ +{ + unsigned int ndquots; + + ASSERT(nbblks > 0); + ndquots = BBTOB(nbblks); + do_div(ndquots, sizeof(xfs_dqblk_t)); + + return ndquots; +} + /* * This initializes all the quota information that's kept in the * mount structure @@ -656,9 +670,8 @@ xfs_qm_init_quotainfo( /* Precalc some constants */ qinf->qi_dqchunklen = XFS_FSB_TO_BB(mp, XFS_DQUOT_CLUSTER_SIZE_FSB); - ASSERT(qinf->qi_dqchunklen); - qinf->qi_dqperchunk = BBTOB(qinf->qi_dqchunklen); - do_div(qinf->qi_dqperchunk, sizeof(xfs_dqblk_t)); + qinf->qi_dqperchunk = xfs_qm_calc_dquots_per_chunk(mp, + qinf->qi_dqchunklen); mp->m_qflags |= (mp->m_sb.sb_qflags & XFS_ALL_QUOTA_CHKD); @@ -897,6 +910,10 @@ xfs_qm_dqiter_bufs( if (error) break; + /* + * XXX(hch): need to figure out if it makes sense to validate + * the CRC here. + */ xfs_qm_reset_dqcounts(mp, bp, firstid, type); xfs_buf_delwri_queue(bp, buffer_list); xfs_buf_relse(bp); diff --git a/fs/xfs/xfs_qm.h b/fs/xfs/xfs_qm.h index 44b858b..45d1656 100644 --- a/fs/xfs/xfs_qm.h +++ b/fs/xfs/xfs_qm.h @@ -75,6 +75,8 @@ typedef struct xfs_quotainfo { &((qi)->qi_gquota_tree)) +extern int xfs_qm_calc_dquots_per_chunk(struct xfs_mount *mp, + unsigned int nbblks); extern void xfs_trans_mod_dquot(xfs_trans_t *, xfs_dquot_t *, uint, long); extern int xfs_trans_reserve_quota_bydquots(xfs_trans_t *, xfs_mount_t *, xfs_dquot_t *, xfs_dquot_t *, long, long, uint); diff --git a/fs/xfs/xfs_quota.h b/fs/xfs/xfs_quota.h index b50ec5b..c61e31c 100644 --- a/fs/xfs/xfs_quota.h +++ b/fs/xfs/xfs_quota.h @@ -77,7 +77,14 @@ typedef struct xfs_disk_dquot { */ typedef struct xfs_dqblk { xfs_disk_dquot_t dd_diskdq; /* portion that lives incore as well */ - char dd_fill[32]; /* filling for posterity */ + char dd_fill[4]; /* filling for posterity */ + + /* + * These two are only present on filesystems with the CRC bits set. + */ + __be32 dd_crc; /* checksum */ + __be64 dd_lsn; /* last modification in log */ + uuid_t dd_uuid; /* location information */ } xfs_dqblk_t; /* @@ -380,5 +387,7 @@ extern int xfs_qm_dqcheck(struct xfs_mount *, xfs_disk_dquot_t *, xfs_dqid_t, uint, uint, char *); extern int xfs_mount_reset_sbqflags(struct xfs_mount *); +extern const struct xfs_buf_ops xfs_dquot_buf_ops; + #endif /* __KERNEL__ */ #endif /* __XFS_QUOTA_H__ */ -- 1.7.10.4 From dave@fromorbit.com Tue Mar 12 07:31:12 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 9F34C7F8E for ; Tue, 12 Mar 2013 07:31:12 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay1.corp.sgi.com (Postfix) with ESMTP id 8A21E8F804C for ; Tue, 12 Mar 2013 05:31:09 -0700 (PDT) X-ASG-Debug-ID: 1363091460-04cbb07dbd487e60003-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id H6XjgA7PjndAUtv8 for ; Tue, 12 Mar 2013 05:31:04 -0700 (PDT) X-Barracuda-Envelope-From: dave@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AuEKAKEfP1F5LKiV/2dsb2JhbAA5CogVvEcBAwGBSRd0gigBAQUaAQgECwEjMwgYBQIRFQICOQMbGYgSrUKCQJAfgSOMLykRdgYWgiOBEwOnSoMeKA Received: from ppp121-44-168-149.lns20.syd7.internode.on.net (HELO dastard) ([121.44.168.149]) by ipmail05.adl6.internode.on.net with ESMTP; 12 Mar 2013 23:00:58 +1030 Received: from disappointment ([192.168.1.1]) by dastard with esmtp (Exim 4.76) (envelope-from ) id 1UFOM6-0001Rd-3q for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:30:58 +1100 Received: from dave by disappointment with local (Exim 4.80) (envelope-from ) id 1UFOM6-0002Lu-0j for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:30:58 +1100 From: Dave Chinner To: xfs@oss.sgi.com Subject: =?UTF-8?q?=5BPATCH=2004/21=5D=20xfs=3A=20add=20support=20for=20large=20btree=20blocks?= Date: Tue, 12 Mar 2013 23:30:37 +1100 X-ASG-Orig-Subj: =?UTF-8?q?=5BPATCH=2004/21=5D=20xfs=3A=20add=20support=20for=20large=20btree=20blocks?= Message-Id: <1363091454-8852-5-git-send-email-david@fromorbit.com> X-Mailer: git-send-email 1.7.10.4 In-Reply-To: <1363091454-8852-1-git-send-email-david@fromorbit.com> References: <1363091454-8852-1-git-send-email-david@fromorbit.com> MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1363091463 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124988 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- From: Christoph Hellwig Add support for larger btree blocks that contains a CRC32C checksum, a filesystem uuid and block number for detecting filesystem consistency and out of place writes. [dchinner@redhat.com] Also include an owner field to allow reverse mappings to be implemented for improved repairability and a LSN field to so that log recovery can easily determine the last modification that made it to disk for each buffer. [dchinner@redhat.com] Add buffer log format flags to indicate the type of buffer to recovery so that we don't have to do blind magic number tests to determine what the buffer is. [dchinner@redhat.com] Modified to fit into the verifier structure. Signed-off-by: Christoph Hellwig Signed-off-by: Dave Chinner --- fs/xfs/xfs_alloc_btree.c | 105 +++++++++++++------ fs/xfs/xfs_alloc_btree.h | 12 ++- fs/xfs/xfs_attr_leaf.c | 2 +- fs/xfs/xfs_bmap.c | 47 ++++++--- fs/xfs/xfs_bmap_btree.c | 110 +++++++++++++------ fs/xfs/xfs_bmap_btree.h | 19 ++-- fs/xfs/xfs_btree.c | 256 +++++++++++++++++++++++++++++++++++++-------- fs/xfs/xfs_btree.h | 64 ++++++++++-- fs/xfs/xfs_buf_item.h | 24 ++++- fs/xfs/xfs_dinode.h | 4 +- fs/xfs/xfs_fsops.c | 23 +++- fs/xfs/xfs_ialloc_btree.c | 87 ++++++++++----- fs/xfs/xfs_ialloc_btree.h | 9 +- fs/xfs/xfs_inode.c | 33 +++--- fs/xfs/xfs_log_recover.c | 28 +++++ fs/xfs/xfs_trans.h | 2 + fs/xfs/xfs_trans_buf.c | 29 +++-- 17 files changed, 645 insertions(+), 209 deletions(-) diff --git a/fs/xfs/xfs_alloc_btree.c b/fs/xfs/xfs_alloc_btree.c index b1ddef6..30c4c14 100644 --- a/fs/xfs/xfs_alloc_btree.c +++ b/fs/xfs/xfs_alloc_btree.c @@ -33,6 +33,7 @@ #include "xfs_extent_busy.h" #include "xfs_error.h" #include "xfs_trace.h" +#include "xfs_cksum.h" STATIC struct xfs_btree_cur * @@ -272,7 +273,7 @@ xfs_allocbt_key_diff( return (__int64_t)be32_to_cpu(kp->ar_startblock) - rec->ar_startblock; } -static void +static bool xfs_allocbt_verify( struct xfs_buf *bp) { @@ -280,66 +281,103 @@ xfs_allocbt_verify( struct xfs_btree_block *block = XFS_BUF_TO_BLOCK(bp); struct xfs_perag *pag = bp->b_pag; unsigned int level; - int sblock_ok; /* block passes checks */ /* * magic number and level verification * - * During growfs operations, we can't verify the exact level as the - * perag is not fully initialised and hence not attached to the buffer. - * In this case, check against the maximum tree depth. + * During growfs operations, we can't verify the exact level or owner as + * the perag is not fully initialised and hence not attached to the + * buffer. In this case, check against the maximum tree depth. + * + * Similarly, during log recovery we will have a perag structure + * attached, but the agf information will not yet have been initialised + * from the on disk AGF. Again, we can only check against maximum limits + * in this case. */ level = be16_to_cpu(block->bb_level); switch (block->bb_magic) { + case cpu_to_be32(XFS_ABTB_CRC_MAGIC): + if (!xfs_sb_version_hascrc(&mp->m_sb)) + return false; + if (!uuid_equal(&block->bb_u.s.bb_uuid, &mp->m_sb.sb_uuid)) + return false; + if (block->bb_u.s.bb_blkno != cpu_to_be64(bp->b_bn)) + return false; + if (pag && + be32_to_cpu(block->bb_u.s.bb_owner) != pag->pag_agno) + return false; + /* fall through */ case cpu_to_be32(XFS_ABTB_MAGIC): - if (pag) - sblock_ok = level < pag->pagf_levels[XFS_BTNUM_BNOi]; - else - sblock_ok = level < mp->m_ag_maxlevels; + if (pag && pag->pagf_init) { + if (level >= pag->pagf_levels[XFS_BTNUM_BNOi]) + return false; + } else if (level >= mp->m_ag_maxlevels) + return false; break; + case cpu_to_be32(XFS_ABTC_CRC_MAGIC): + if (!xfs_sb_version_hascrc(&mp->m_sb)) + return false; + if (!uuid_equal(&block->bb_u.s.bb_uuid, &mp->m_sb.sb_uuid)) + return false; + if (block->bb_u.s.bb_blkno != cpu_to_be64(bp->b_bn)) + return false; + if (pag && + be32_to_cpu(block->bb_u.s.bb_owner) != pag->pag_agno) + return false; + /* fall through */ case cpu_to_be32(XFS_ABTC_MAGIC): - if (pag) - sblock_ok = level < pag->pagf_levels[XFS_BTNUM_CNTi]; - else - sblock_ok = level < mp->m_ag_maxlevels; + if (pag && pag->pagf_init) { + if (level >= pag->pagf_levels[XFS_BTNUM_CNTi]) + return false; + } else if (level >= mp->m_ag_maxlevels) + return false; break; default: - sblock_ok = 0; - break; + return false; } /* numrecs verification */ - sblock_ok = sblock_ok && - be16_to_cpu(block->bb_numrecs) <= mp->m_alloc_mxr[level != 0]; + if (be16_to_cpu(block->bb_numrecs) > mp->m_alloc_mxr[level != 0]) + return false; /* sibling pointer verification */ - sblock_ok = sblock_ok && - (block->bb_u.s.bb_leftsib == cpu_to_be32(NULLAGBLOCK) || - be32_to_cpu(block->bb_u.s.bb_leftsib) < mp->m_sb.sb_agblocks) && - block->bb_u.s.bb_leftsib && - (block->bb_u.s.bb_rightsib == cpu_to_be32(NULLAGBLOCK) || - be32_to_cpu(block->bb_u.s.bb_rightsib) < mp->m_sb.sb_agblocks) && - block->bb_u.s.bb_rightsib; - - if (!sblock_ok) { - trace_xfs_btree_corrupt(bp, _RET_IP_); - XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, mp, block); - xfs_buf_ioerror(bp, EFSCORRUPTED); - } + if (!block->bb_u.s.bb_leftsib || + (be32_to_cpu(block->bb_u.s.bb_leftsib) >= mp->m_sb.sb_agblocks && + block->bb_u.s.bb_leftsib != cpu_to_be32(NULLAGBLOCK))) + return false; + if (!block->bb_u.s.bb_rightsib || + (be32_to_cpu(block->bb_u.s.bb_rightsib) >= mp->m_sb.sb_agblocks && + block->bb_u.s.bb_rightsib != cpu_to_be32(NULLAGBLOCK))) + return false; + + return true; } static void xfs_allocbt_read_verify( struct xfs_buf *bp) { - xfs_allocbt_verify(bp); + if (!(xfs_btree_sblock_verify_crc(bp) && + xfs_allocbt_verify(bp))) { + trace_xfs_btree_corrupt(bp, _RET_IP_); + XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, + bp->b_target->bt_mount, bp->b_addr); + xfs_buf_ioerror(bp, EFSCORRUPTED); + } } static void xfs_allocbt_write_verify( struct xfs_buf *bp) { - xfs_allocbt_verify(bp); + if (!xfs_allocbt_verify(bp)) { + trace_xfs_btree_corrupt(bp, _RET_IP_); + XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, + bp->b_target->bt_mount, bp->b_addr); + xfs_buf_ioerror(bp, EFSCORRUPTED); + } + xfs_btree_sblock_calc_crc(bp); + } const struct xfs_buf_ops xfs_allocbt_buf_ops = { @@ -444,6 +482,9 @@ xfs_allocbt_init_cursor( cur->bc_private.a.agbp = agbp; cur->bc_private.a.agno = agno; + if (xfs_sb_version_hascrc(&mp->m_sb)) + cur->bc_flags |= XFS_BTREE_CRC_BLOCKS; + return cur; } diff --git a/fs/xfs/xfs_alloc_btree.h b/fs/xfs/xfs_alloc_btree.h index 7e89a2b..e3a3f74 100644 --- a/fs/xfs/xfs_alloc_btree.h +++ b/fs/xfs/xfs_alloc_btree.h @@ -31,8 +31,10 @@ struct xfs_mount; * by blockcount and blockno. All blocks look the same to make the code * simpler; if we have time later, we'll make the optimizations. */ -#define XFS_ABTB_MAGIC 0x41425442 /* 'ABTB' for bno tree */ -#define XFS_ABTC_MAGIC 0x41425443 /* 'ABTC' for cnt tree */ +#define XFS_ABTB_MAGIC 0x41425442 /* 'ABTB' for bno tree */ +#define XFS_ABTB_CRC_MAGIC 0x41423342 /* 'AB3B' */ +#define XFS_ABTC_MAGIC 0x41425443 /* 'ABTC' for cnt tree */ +#define XFS_ABTC_CRC_MAGIC 0x41423343 /* 'AB3C' */ /* * Data record/key structure @@ -59,10 +61,10 @@ typedef __be32 xfs_alloc_ptr_t; /* * Btree block header size depends on a superblock flag. - * - * (not quite yet, but soon) */ -#define XFS_ALLOC_BLOCK_LEN(mp) XFS_BTREE_SBLOCK_LEN +#define XFS_ALLOC_BLOCK_LEN(mp) \ + (xfs_sb_version_hascrc(&((mp)->m_sb)) ? \ + XFS_BTREE_SBLOCK_CRC_LEN : XFS_BTREE_SBLOCK_LEN) /* * Record, key, and pointer address macros for btree blocks. diff --git a/fs/xfs/xfs_attr_leaf.c b/fs/xfs/xfs_attr_leaf.c index f96a734..aa4765f 100644 --- a/fs/xfs/xfs_attr_leaf.c +++ b/fs/xfs/xfs_attr_leaf.c @@ -232,7 +232,7 @@ xfs_attr_shortform_bytesfit(xfs_inode_t *dp, int bytes) return 0; return dp->i_d.di_forkoff; } - dsize = XFS_BMAP_BROOT_SPACE(dp->i_df.if_broot); + dsize = XFS_BMAP_BROOT_SPACE(mp, dp->i_df.if_broot); break; } diff --git a/fs/xfs/xfs_bmap.c b/fs/xfs/xfs_bmap.c index 20efb39..0531cd3 100644 --- a/fs/xfs/xfs_bmap.c +++ b/fs/xfs/xfs_bmap.c @@ -439,11 +439,15 @@ xfs_bmap_sanity_check( { struct xfs_btree_block *block = XFS_BUF_TO_BLOCK(bp); - if (block->bb_magic != cpu_to_be32(XFS_BMAP_MAGIC) || - be16_to_cpu(block->bb_level) != level || + if (block->bb_magic != cpu_to_be32(XFS_BMAP_CRC_MAGIC) && + block->bb_magic != cpu_to_be32(XFS_BMAP_MAGIC)) + return 0; + + if (be16_to_cpu(block->bb_level) != level || be16_to_cpu(block->bb_numrecs) == 0 || be16_to_cpu(block->bb_numrecs) > mp->m_bmap_dmxr[level != 0]) return 0; + return 1; } @@ -1031,6 +1035,7 @@ xfs_bmap_extents_to_btree( xfs_extnum_t nextents; /* number of file extents */ xfs_bmbt_ptr_t *pp; /* root block address pointer */ + mp = ip->i_mount; ifp = XFS_IFORK_PTR(ip, whichfork); ASSERT(XFS_IFORK_FORMAT(ip, whichfork) == XFS_DINODE_FMT_EXTENTS); @@ -1044,16 +1049,18 @@ xfs_bmap_extents_to_btree( * Fill in the root. */ block = ifp->if_broot; - block->bb_magic = cpu_to_be32(XFS_BMAP_MAGIC); - block->bb_level = cpu_to_be16(1); - block->bb_numrecs = cpu_to_be16(1); - block->bb_u.l.bb_leftsib = cpu_to_be64(NULLDFSBNO); - block->bb_u.l.bb_rightsib = cpu_to_be64(NULLDFSBNO); + if (xfs_sb_version_hascrc(&mp->m_sb)) + xfs_btree_init_block_int(mp, block, XFS_BUF_DADDR_NULL, + XFS_BMAP_CRC_MAGIC, 1, 1, ip->i_ino, + XFS_BTREE_LONG_PTRS | XFS_BTREE_CRC_BLOCKS); + else + xfs_btree_init_block_int(mp, block, XFS_BUF_DADDR_NULL, + XFS_BMAP_MAGIC, 1, 1, ip->i_ino, + XFS_BTREE_LONG_PTRS); /* * Need a cursor. Can't allocate until bb_level is filled in. */ - mp = ip->i_mount; cur = xfs_bmbt_init_cursor(mp, tp, ip, whichfork); cur->bc_private.b.firstblock = *firstblock; cur->bc_private.b.flist = flist; @@ -1102,10 +1109,15 @@ xfs_bmap_extents_to_btree( */ abp->b_ops = &xfs_bmbt_buf_ops; ablock = XFS_BUF_TO_BLOCK(abp); - ablock->bb_magic = cpu_to_be32(XFS_BMAP_MAGIC); - ablock->bb_level = 0; - ablock->bb_u.l.bb_leftsib = cpu_to_be64(NULLDFSBNO); - ablock->bb_u.l.bb_rightsib = cpu_to_be64(NULLDFSBNO); + if (xfs_sb_version_hascrc(&mp->m_sb)) + xfs_btree_init_block_int(mp, ablock, abp->b_bn, + XFS_BMAP_CRC_MAGIC, 0, 0, ip->i_ino, + XFS_BTREE_LONG_PTRS | XFS_BTREE_CRC_BLOCKS); + else + xfs_btree_init_block_int(mp, ablock, abp->b_bn, + XFS_BMAP_MAGIC, 0, 0, ip->i_ino, + XFS_BTREE_LONG_PTRS); + arp = XFS_BMBT_REC_ADDR(mp, ablock, 1); nextents = ifp->if_bytes / (uint)sizeof(xfs_bmbt_rec_t); for (cnt = i = 0; i < nextents; i++) { @@ -1155,7 +1167,8 @@ xfs_bmap_local_to_extents( xfs_extlen_t total, /* total blocks needed by transaction */ int *logflagsp, /* inode logging flags */ int whichfork, - void (*init_fn)(struct xfs_buf *bp, + void (*init_fn)(struct xfs_trans *tp, + struct xfs_buf *bp, struct xfs_inode *ip, struct xfs_ifork *ifp)) { @@ -1207,7 +1220,7 @@ xfs_bmap_local_to_extents( bp = xfs_btree_get_bufl(args.mp, tp, args.fsbno, 0); /* initialise the block and copy the data */ - init_fn(bp, ip, ifp); + init_fn(tp, bp, ip, ifp); /* account for the change in fork size and log everything */ xfs_trans_log_buf(tp, bp, 0, ifp->if_bytes - 1); @@ -1314,16 +1327,19 @@ xfs_bmap_add_attrfork_extents( */ STATIC void xfs_bmap_local_to_extents_init_fn( + struct xfs_trans *tp, struct xfs_buf *bp, struct xfs_inode *ip, struct xfs_ifork *ifp) { bp->b_ops = &xfs_bmbt_buf_ops; memcpy(bp->b_addr, ifp->if_u1.if_data, ifp->if_bytes); + xfs_trans_buf_set_type(tp, bp, XFS_BLF_BTREE_BUF); } STATIC void xfs_symlink_local_to_remote( + struct xfs_trans *tp, struct xfs_buf *bp, struct xfs_inode *ip, struct xfs_ifork *ifp) @@ -1342,8 +1358,7 @@ xfs_symlink_local_to_remote( * * XXX (dgc): investigate whether directory conversion can use the generic * formatting callout. It should be possible - it's just a very complex - * formatter. it would also require passing the transaction through to the init - * function. + * formatter. */ STATIC int /* error */ xfs_bmap_add_attrfork_local( diff --git a/fs/xfs/xfs_bmap_btree.c b/fs/xfs/xfs_bmap_btree.c index 061b45c..3a86c3f 100644 --- a/fs/xfs/xfs_bmap_btree.c +++ b/fs/xfs/xfs_bmap_btree.c @@ -37,6 +37,7 @@ #include "xfs_error.h" #include "xfs_quota.h" #include "xfs_trace.h" +#include "xfs_cksum.h" /* * Determine the extent state. @@ -59,24 +60,31 @@ xfs_extent_state( */ void xfs_bmdr_to_bmbt( - struct xfs_mount *mp, + struct xfs_inode *ip, xfs_bmdr_block_t *dblock, int dblocklen, struct xfs_btree_block *rblock, int rblocklen) { + struct xfs_mount *mp = ip->i_mount; int dmxr; xfs_bmbt_key_t *fkp; __be64 *fpp; xfs_bmbt_key_t *tkp; __be64 *tpp; - rblock->bb_magic = cpu_to_be32(XFS_BMAP_MAGIC); + if (xfs_sb_version_hascrc(&mp->m_sb)) + xfs_btree_init_block_int(mp, rblock, XFS_BUF_DADDR_NULL, + XFS_BMAP_CRC_MAGIC, 0, 0, ip->i_ino, + XFS_BTREE_LONG_PTRS | XFS_BTREE_CRC_BLOCKS); + else + xfs_btree_init_block_int(mp, rblock, XFS_BUF_DADDR_NULL, + XFS_BMAP_MAGIC, 0, 0, ip->i_ino, + XFS_BTREE_LONG_PTRS); + rblock->bb_level = dblock->bb_level; ASSERT(be16_to_cpu(rblock->bb_level) > 0); rblock->bb_numrecs = dblock->bb_numrecs; - rblock->bb_u.l.bb_leftsib = cpu_to_be64(NULLDFSBNO); - rblock->bb_u.l.bb_rightsib = cpu_to_be64(NULLDFSBNO); dmxr = xfs_bmdr_maxrecs(mp, dblocklen, 0); fkp = XFS_BMDR_KEY_ADDR(dblock, 1); tkp = XFS_BMBT_KEY_ADDR(mp, rblock, 1); @@ -424,7 +432,13 @@ xfs_bmbt_to_bmdr( xfs_bmbt_key_t *tkp; __be64 *tpp; - ASSERT(rblock->bb_magic == cpu_to_be32(XFS_BMAP_MAGIC)); + if (xfs_sb_version_hascrc(&mp->m_sb)) { + ASSERT(rblock->bb_magic == cpu_to_be32(XFS_BMAP_CRC_MAGIC)); + ASSERT(uuid_equal(&rblock->bb_u.l.bb_uuid, &mp->m_sb.sb_uuid)); + ASSERT(rblock->bb_u.l.bb_blkno == + cpu_to_be64(XFS_BUF_DADDR_NULL)); + } else + ASSERT(rblock->bb_magic == cpu_to_be32(XFS_BMAP_MAGIC)); ASSERT(rblock->bb_u.l.bb_leftsib == cpu_to_be64(NULLDFSBNO)); ASSERT(rblock->bb_u.l.bb_rightsib == cpu_to_be64(NULLDFSBNO)); ASSERT(rblock->bb_level != 0); @@ -708,59 +722,89 @@ xfs_bmbt_key_diff( cur->bc_rec.b.br_startoff; } -static void +static int xfs_bmbt_verify( struct xfs_buf *bp) { struct xfs_mount *mp = bp->b_target->bt_mount; struct xfs_btree_block *block = XFS_BUF_TO_BLOCK(bp); unsigned int level; - int lblock_ok; /* block passes checks */ - /* magic number and level verification. + switch (block->bb_magic) { + case cpu_to_be32(XFS_BMAP_CRC_MAGIC): + if (!xfs_sb_version_hascrc(&mp->m_sb)) + return false; + if (!uuid_equal(&block->bb_u.l.bb_uuid, &mp->m_sb.sb_uuid)) + return false; + if (be64_to_cpu(block->bb_u.l.bb_blkno) != bp->b_bn) + return false; + /* + * XXX: need a better way of verifying the owner here. Right now + * just make sure there has been one set. + */ + if (be64_to_cpu(block->bb_u.l.bb_owner) == 0) + return false; + /* fall through */ + case cpu_to_be32(XFS_BMAP_MAGIC): + break; + default: + return false; + } + + /* + * numrecs and level verification. * - * We don't know waht fork we belong to, so just verify that the level + * We don't know what fork we belong to, so just verify that the level * is less than the maximum of the two. Later checks will be more * precise. */ level = be16_to_cpu(block->bb_level); - lblock_ok = block->bb_magic == cpu_to_be32(XFS_BMAP_MAGIC) && - level < max(mp->m_bm_maxlevels[0], mp->m_bm_maxlevels[1]); - - /* numrecs verification */ - lblock_ok = lblock_ok && - be16_to_cpu(block->bb_numrecs) <= mp->m_bmap_dmxr[level != 0]; + if (level > max(mp->m_bm_maxlevels[0], mp->m_bm_maxlevels[1])) + return false; + if (be16_to_cpu(block->bb_numrecs) > mp->m_bmap_dmxr[level != 0]) + return false; /* sibling pointer verification */ - lblock_ok = lblock_ok && - block->bb_u.l.bb_leftsib && - (block->bb_u.l.bb_leftsib == cpu_to_be64(NULLDFSBNO) || - XFS_FSB_SANITY_CHECK(mp, - be64_to_cpu(block->bb_u.l.bb_leftsib))) && - block->bb_u.l.bb_rightsib && - (block->bb_u.l.bb_rightsib == cpu_to_be64(NULLDFSBNO) || - XFS_FSB_SANITY_CHECK(mp, - be64_to_cpu(block->bb_u.l.bb_rightsib))); - - if (!lblock_ok) { - trace_xfs_btree_corrupt(bp, _RET_IP_); - XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, mp, block); - xfs_buf_ioerror(bp, EFSCORRUPTED); - } + if (!block->bb_u.l.bb_leftsib || + (block->bb_u.l.bb_leftsib != cpu_to_be64(NULLDFSBNO) && + !XFS_FSB_SANITY_CHECK(mp, be64_to_cpu(block->bb_u.l.bb_leftsib)))) + return false; + if (!block->bb_u.l.bb_rightsib || + (block->bb_u.l.bb_rightsib != cpu_to_be64(NULLDFSBNO) && + !XFS_FSB_SANITY_CHECK(mp, be64_to_cpu(block->bb_u.l.bb_rightsib)))) + return false; + + return true; + } static void xfs_bmbt_read_verify( struct xfs_buf *bp) { - xfs_bmbt_verify(bp); + if (!(xfs_btree_lblock_verify_crc(bp) && + xfs_bmbt_verify(bp))) { + trace_xfs_btree_corrupt(bp, _RET_IP_); + XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, + bp->b_target->bt_mount, bp->b_addr); + xfs_buf_ioerror(bp, EFSCORRUPTED); + } + } static void xfs_bmbt_write_verify( struct xfs_buf *bp) { - xfs_bmbt_verify(bp); + if (!xfs_bmbt_verify(bp)) { + xfs_warn(bp->b_target->bt_mount, "bmbt daddr 0x%llx failed", bp->b_bn); + trace_xfs_btree_corrupt(bp, _RET_IP_); + XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, + bp->b_target->bt_mount, bp->b_addr); + xfs_buf_ioerror(bp, EFSCORRUPTED); + return; + } + xfs_btree_lblock_calc_crc(bp); } const struct xfs_buf_ops xfs_bmbt_buf_ops = { @@ -838,6 +882,8 @@ xfs_bmbt_init_cursor( cur->bc_ops = &xfs_bmbt_ops; cur->bc_flags = XFS_BTREE_LONG_PTRS | XFS_BTREE_ROOT_IN_INODE; + if (xfs_sb_version_hascrc(&mp->m_sb)) + cur->bc_flags |= XFS_BTREE_CRC_BLOCKS; cur->bc_private.b.forksize = XFS_IFORK_SIZE(ip, whichfork); cur->bc_private.b.ip = ip; diff --git a/fs/xfs/xfs_bmap_btree.h b/fs/xfs/xfs_bmap_btree.h index 88469ca..70c43d9 100644 --- a/fs/xfs/xfs_bmap_btree.h +++ b/fs/xfs/xfs_bmap_btree.h @@ -18,7 +18,8 @@ #ifndef __XFS_BMAP_BTREE_H__ #define __XFS_BMAP_BTREE_H__ -#define XFS_BMAP_MAGIC 0x424d4150 /* 'BMAP' */ +#define XFS_BMAP_MAGIC 0x424d4150 /* 'BMAP' */ +#define XFS_BMAP_CRC_MAGIC 0x424d4133 /* 'BMA3' */ struct xfs_btree_cur; struct xfs_btree_block; @@ -136,10 +137,10 @@ typedef __be64 xfs_bmbt_ptr_t, xfs_bmdr_ptr_t; /* * Btree block header size depends on a superblock flag. - * - * (not quite yet, but soon) */ -#define XFS_BMBT_BLOCK_LEN(mp) XFS_BTREE_LBLOCK_LEN +#define XFS_BMBT_BLOCK_LEN(mp) \ + (xfs_sb_version_hascrc(&((mp)->m_sb)) ? \ + XFS_BTREE_LBLOCK_CRC_LEN : XFS_BTREE_LBLOCK_LEN) #define XFS_BMBT_REC_ADDR(mp, block, index) \ ((xfs_bmbt_rec_t *) \ @@ -186,12 +187,12 @@ typedef __be64 xfs_bmbt_ptr_t, xfs_bmdr_ptr_t; #define XFS_BMAP_BROOT_PTR_ADDR(mp, bb, i, sz) \ XFS_BMBT_PTR_ADDR(mp, bb, i, xfs_bmbt_maxrecs(mp, sz, 0)) -#define XFS_BMAP_BROOT_SPACE_CALC(nrecs) \ - (int)(XFS_BTREE_LBLOCK_LEN + \ +#define XFS_BMAP_BROOT_SPACE_CALC(mp, nrecs) \ + (int)(XFS_BMBT_BLOCK_LEN(mp) + \ ((nrecs) * (sizeof(xfs_bmbt_key_t) + sizeof(xfs_bmbt_ptr_t)))) -#define XFS_BMAP_BROOT_SPACE(bb) \ - (XFS_BMAP_BROOT_SPACE_CALC(be16_to_cpu((bb)->bb_numrecs))) +#define XFS_BMAP_BROOT_SPACE(mp, bb) \ + (XFS_BMAP_BROOT_SPACE_CALC(mp, be16_to_cpu((bb)->bb_numrecs))) #define XFS_BMDR_SPACE_CALC(nrecs) \ (int)(sizeof(xfs_bmdr_block_t) + \ ((nrecs) * (sizeof(xfs_bmbt_key_t) + sizeof(xfs_bmbt_ptr_t)))) @@ -204,7 +205,7 @@ typedef __be64 xfs_bmbt_ptr_t, xfs_bmdr_ptr_t; /* * Prototypes for xfs_bmap.c to call. */ -extern void xfs_bmdr_to_bmbt(struct xfs_mount *, xfs_bmdr_block_t *, int, +extern void xfs_bmdr_to_bmbt(struct xfs_inode *, xfs_bmdr_block_t *, int, struct xfs_btree_block *, int); extern void xfs_bmbt_get_all(xfs_bmbt_rec_host_t *r, xfs_bmbt_irec_t *s); extern xfs_filblks_t xfs_bmbt_get_blockcount(xfs_bmbt_rec_host_t *r); diff --git a/fs/xfs/xfs_btree.c b/fs/xfs/xfs_btree.c index db01040..ec77036 100644 --- a/fs/xfs/xfs_btree.c +++ b/fs/xfs/xfs_btree.c @@ -30,9 +30,11 @@ #include "xfs_dinode.h" #include "xfs_inode.h" #include "xfs_inode_item.h" +#include "xfs_buf_item.h" #include "xfs_btree.h" #include "xfs_error.h" #include "xfs_trace.h" +#include "xfs_cksum.h" /* * Cursor allocation zone. @@ -42,9 +44,13 @@ kmem_zone_t *xfs_btree_cur_zone; /* * Btree magic numbers. */ -const __uint32_t xfs_magics[XFS_BTNUM_MAX] = { - XFS_ABTB_MAGIC, XFS_ABTC_MAGIC, XFS_BMAP_MAGIC, XFS_IBT_MAGIC +static const __uint32_t xfs_magics[2][XFS_BTNUM_MAX] = { + { XFS_ABTB_MAGIC, XFS_ABTC_MAGIC, XFS_BMAP_MAGIC, XFS_IBT_MAGIC }, + { XFS_ABTB_CRC_MAGIC, XFS_ABTC_CRC_MAGIC, + XFS_BMAP_CRC_MAGIC, XFS_IBT_CRC_MAGIC } }; +#define xfs_btree_magic(cur) \ + xfs_magics[!!((cur)->bc_flags & XFS_BTREE_CRC_BLOCKS)][cur->bc_btnum] STATIC int /* error (0 or EFSCORRUPTED) */ @@ -54,30 +60,38 @@ xfs_btree_check_lblock( int level, /* level of the btree block */ struct xfs_buf *bp) /* buffer for block, if any */ { - int lblock_ok; /* block passes checks */ + int lblock_ok = 1; /* block passes checks */ struct xfs_mount *mp; /* file system mount point */ mp = cur->bc_mp; - lblock_ok = - be32_to_cpu(block->bb_magic) == xfs_magics[cur->bc_btnum] && + + if (xfs_sb_version_hascrc(&mp->m_sb)) { + lblock_ok = lblock_ok && + uuid_equal(&block->bb_u.l.bb_uuid, &mp->m_sb.sb_uuid) && + block->bb_u.l.bb_blkno == cpu_to_be64( + bp ? bp->b_bn : XFS_BUF_DADDR_NULL); + } + + lblock_ok = lblock_ok && + be32_to_cpu(block->bb_magic) == xfs_btree_magic(cur) && be16_to_cpu(block->bb_level) == level && be16_to_cpu(block->bb_numrecs) <= cur->bc_ops->get_maxrecs(cur, level) && block->bb_u.l.bb_leftsib && (block->bb_u.l.bb_leftsib == cpu_to_be64(NULLDFSBNO) || XFS_FSB_SANITY_CHECK(mp, - be64_to_cpu(block->bb_u.l.bb_leftsib))) && + be64_to_cpu(block->bb_u.l.bb_leftsib))) && block->bb_u.l.bb_rightsib && (block->bb_u.l.bb_rightsib == cpu_to_be64(NULLDFSBNO) || XFS_FSB_SANITY_CHECK(mp, - be64_to_cpu(block->bb_u.l.bb_rightsib))); + be64_to_cpu(block->bb_u.l.bb_rightsib))); + if (unlikely(XFS_TEST_ERROR(!lblock_ok, mp, XFS_ERRTAG_BTREE_CHECK_LBLOCK, XFS_RANDOM_BTREE_CHECK_LBLOCK))) { if (bp) trace_xfs_btree_corrupt(bp, _RET_IP_); - XFS_ERROR_REPORT("xfs_btree_check_lblock", XFS_ERRLEVEL_LOW, - mp); + XFS_ERROR_REPORT(__func__, XFS_ERRLEVEL_LOW, mp); return XFS_ERROR(EFSCORRUPTED); } return 0; @@ -90,16 +104,26 @@ xfs_btree_check_sblock( int level, /* level of the btree block */ struct xfs_buf *bp) /* buffer containing block */ { + struct xfs_mount *mp; /* file system mount point */ struct xfs_buf *agbp; /* buffer for ag. freespace struct */ struct xfs_agf *agf; /* ag. freespace structure */ xfs_agblock_t agflen; /* native ag. freespace length */ - int sblock_ok; /* block passes checks */ + int sblock_ok = 1; /* block passes checks */ + mp = cur->bc_mp; agbp = cur->bc_private.a.agbp; agf = XFS_BUF_TO_AGF(agbp); agflen = be32_to_cpu(agf->agf_length); - sblock_ok = - be32_to_cpu(block->bb_magic) == xfs_magics[cur->bc_btnum] && + + if (xfs_sb_version_hascrc(&mp->m_sb)) { + sblock_ok = sblock_ok && + uuid_equal(&block->bb_u.s.bb_uuid, &mp->m_sb.sb_uuid) && + block->bb_u.s.bb_blkno == cpu_to_be64( + bp ? bp->b_bn : XFS_BUF_DADDR_NULL); + } + + sblock_ok = sblock_ok && + be32_to_cpu(block->bb_magic) == xfs_btree_magic(cur) && be16_to_cpu(block->bb_level) == level && be16_to_cpu(block->bb_numrecs) <= cur->bc_ops->get_maxrecs(cur, level) && @@ -109,13 +133,13 @@ xfs_btree_check_sblock( (block->bb_u.s.bb_rightsib == cpu_to_be32(NULLAGBLOCK) || be32_to_cpu(block->bb_u.s.bb_rightsib) < agflen) && block->bb_u.s.bb_rightsib; - if (unlikely(XFS_TEST_ERROR(!sblock_ok, cur->bc_mp, + + if (unlikely(XFS_TEST_ERROR(!sblock_ok, mp, XFS_ERRTAG_BTREE_CHECK_SBLOCK, XFS_RANDOM_BTREE_CHECK_SBLOCK))) { if (bp) trace_xfs_btree_corrupt(bp, _RET_IP_); - XFS_CORRUPTION_ERROR("xfs_btree_check_sblock", - XFS_ERRLEVEL_LOW, cur->bc_mp, block); + XFS_ERROR_REPORT(__func__, XFS_ERRLEVEL_LOW, mp); return XFS_ERROR(EFSCORRUPTED); } return 0; @@ -194,6 +218,72 @@ xfs_btree_check_ptr( #endif /* + * Calculate CRC on the whole btree block and stuff it into the + * long-form btree header. + * + * Prior to calculting the CRC, pull the LSN out of the buffer log item and put + * it into the buffer so recovery knows what the last modifcation was that made + * it to disk. + */ +void +xfs_btree_lblock_calc_crc( + struct xfs_buf *bp) +{ + struct xfs_btree_block *block = XFS_BUF_TO_BLOCK(bp); + struct xfs_buf_log_item *bip = bp->b_fspriv; + + if (!xfs_sb_version_hascrc(&bp->b_target->bt_mount->m_sb)) + return; + if (bip) + block->bb_u.l.bb_lsn = cpu_to_be64(bip->bli_item.li_lsn); + xfs_update_cksum(bp->b_addr, BBTOB(bp->b_length), + XFS_BTREE_LBLOCK_CRC_OFF); +} + +bool +xfs_btree_lblock_verify_crc( + struct xfs_buf *bp) +{ + if (xfs_sb_version_hascrc(&bp->b_target->bt_mount->m_sb)) + return xfs_verify_cksum(bp->b_addr, BBTOB(bp->b_length), + XFS_BTREE_LBLOCK_CRC_OFF); + return true; +} + +/* + * Calculate CRC on the whole btree block and stuff it into the + * short-form btree header. + * + * Prior to calculting the CRC, pull the LSN out of the buffer log item and put + * it into the buffer so recovery knows what the last modifcation was that made + * it to disk. + */ +void +xfs_btree_sblock_calc_crc( + struct xfs_buf *bp) +{ + struct xfs_btree_block *block = XFS_BUF_TO_BLOCK(bp); + struct xfs_buf_log_item *bip = bp->b_fspriv; + + if (!xfs_sb_version_hascrc(&bp->b_target->bt_mount->m_sb)) + return; + if (bip) + block->bb_u.s.bb_lsn = cpu_to_be64(bip->bli_item.li_lsn); + xfs_update_cksum(bp->b_addr, BBTOB(bp->b_length), + XFS_BTREE_SBLOCK_CRC_OFF); +} + +bool +xfs_btree_sblock_verify_crc( + struct xfs_buf *bp) +{ + if (xfs_sb_version_hascrc(&bp->b_target->bt_mount->m_sb)) + return xfs_verify_cksum(bp->b_addr, BBTOB(bp->b_length), + XFS_BTREE_SBLOCK_CRC_OFF); + return true; +} + +/* * Delete the btree cursor. */ void @@ -277,10 +367,8 @@ xfs_btree_dup_cursor( *ncur = NULL; return error; } - new->bc_bufs[i] = bp; - ASSERT(!xfs_buf_geterror(bp)); - } else - new->bc_bufs[i] = NULL; + } + new->bc_bufs[i] = bp; } *ncur = new; return 0; @@ -321,9 +409,14 @@ xfs_btree_dup_cursor( */ static inline size_t xfs_btree_block_len(struct xfs_btree_cur *cur) { - return (cur->bc_flags & XFS_BTREE_LONG_PTRS) ? - XFS_BTREE_LBLOCK_LEN : - XFS_BTREE_SBLOCK_LEN; + if (cur->bc_flags & XFS_BTREE_LONG_PTRS) { + if (cur->bc_flags & XFS_BTREE_CRC_BLOCKS) + return XFS_BTREE_LBLOCK_CRC_LEN; + return XFS_BTREE_LBLOCK_LEN; + } + if (cur->bc_flags & XFS_BTREE_CRC_BLOCKS) + return XFS_BTREE_SBLOCK_CRC_LEN; + return XFS_BTREE_SBLOCK_LEN; } /* @@ -863,43 +956,85 @@ xfs_btree_set_sibling( } void +xfs_btree_init_block_int( + struct xfs_mount *mp, + struct xfs_btree_block *buf, + xfs_daddr_t blkno, + __u32 magic, + __u16 level, + __u16 numrecs, + __u64 owner, + unsigned int flags) +{ + buf->bb_magic = cpu_to_be32(magic); + buf->bb_level = cpu_to_be16(level); + buf->bb_numrecs = cpu_to_be16(numrecs); + + if (flags & XFS_BTREE_LONG_PTRS) { + buf->bb_u.l.bb_leftsib = cpu_to_be64(NULLDFSBNO); + buf->bb_u.l.bb_rightsib = cpu_to_be64(NULLDFSBNO); + if (flags & XFS_BTREE_CRC_BLOCKS) { + buf->bb_u.l.bb_blkno = cpu_to_be64(blkno); + buf->bb_u.l.bb_owner = cpu_to_be64(owner); + uuid_copy(&buf->bb_u.l.bb_uuid, &mp->m_sb.sb_uuid); + buf->bb_u.l.bb_pad = 0; + } + } else { + /* owner is a 32 bit value on short blocks */ + __u32 __owner = (__u32)owner; + + buf->bb_u.s.bb_leftsib = cpu_to_be32(NULLAGBLOCK); + buf->bb_u.s.bb_rightsib = cpu_to_be32(NULLAGBLOCK); + if (flags & XFS_BTREE_CRC_BLOCKS) { + buf->bb_u.s.bb_blkno = cpu_to_be64(blkno); + buf->bb_u.s.bb_owner = cpu_to_be32(__owner); + uuid_copy(&buf->bb_u.s.bb_uuid, &mp->m_sb.sb_uuid); + } + } +} + +void xfs_btree_init_block( struct xfs_mount *mp, struct xfs_buf *bp, __u32 magic, __u16 level, __u16 numrecs, + __u64 owner, unsigned int flags) { - struct xfs_btree_block *new = XFS_BUF_TO_BLOCK(bp); - - new->bb_magic = cpu_to_be32(magic); - new->bb_level = cpu_to_be16(level); - new->bb_numrecs = cpu_to_be16(numrecs); - - if (flags & XFS_BTREE_LONG_PTRS) { - new->bb_u.l.bb_leftsib = cpu_to_be64(NULLDFSBNO); - new->bb_u.l.bb_rightsib = cpu_to_be64(NULLDFSBNO); - } else { - new->bb_u.s.bb_leftsib = cpu_to_be32(NULLAGBLOCK); - new->bb_u.s.bb_rightsib = cpu_to_be32(NULLAGBLOCK); - } + xfs_btree_init_block_int(mp, XFS_BUF_TO_BLOCK(bp), bp->b_bn, + magic, level, numrecs, owner, flags); } STATIC void xfs_btree_init_block_cur( struct xfs_btree_cur *cur, + struct xfs_buf *bp, int level, - int numrecs, - struct xfs_buf *bp) + int numrecs) { - xfs_btree_init_block(cur->bc_mp, bp, xfs_magics[cur->bc_btnum], - level, numrecs, cur->bc_flags); + __u64 owner; + + /* + * we can pull the owner from the cursor right now as the different + * owners align directly with the pointer size of the btree. This may + * change in future, but is safe for current users of the generic btree + * code. + */ + if (cur->bc_flags & XFS_BTREE_LONG_PTRS) + owner = cur->bc_private.b.ip->i_ino; + else + owner = cur->bc_private.a.agno; + + xfs_btree_init_block_int(cur->bc_mp, XFS_BUF_TO_BLOCK(bp), bp->b_bn, + xfs_btree_magic(cur), level, numrecs, + owner, cur->bc_flags); } /* * Return true if ptr is the last record in the btree and - * we need to track updateѕ to this record. The decision + * we need to track updates to this record. The decision * will be further refined in the update_lastrec method. */ STATIC int @@ -1147,6 +1282,7 @@ xfs_btree_log_keys( XFS_BTREE_TRACE_ARGBII(cur, bp, first, last); if (bp) { + xfs_trans_buf_set_type(cur->bc_tp, bp, XFS_BLF_BTREE_BUF); xfs_trans_log_buf(cur->bc_tp, bp, xfs_btree_key_offset(cur, first), xfs_btree_key_offset(cur, last + 1) - 1); @@ -1171,6 +1307,7 @@ xfs_btree_log_recs( XFS_BTREE_TRACE_CURSOR(cur, XBT_ENTRY); XFS_BTREE_TRACE_ARGBII(cur, bp, first, last); + xfs_trans_buf_set_type(cur->bc_tp, bp, XFS_BLF_BTREE_BUF); xfs_trans_log_buf(cur->bc_tp, bp, xfs_btree_rec_offset(cur, first), xfs_btree_rec_offset(cur, last + 1) - 1); @@ -1195,6 +1332,7 @@ xfs_btree_log_ptrs( struct xfs_btree_block *block = XFS_BUF_TO_BLOCK(bp); int level = xfs_btree_get_level(block); + xfs_trans_buf_set_type(cur->bc_tp, bp, XFS_BLF_BTREE_BUF); xfs_trans_log_buf(cur->bc_tp, bp, xfs_btree_ptr_offset(cur, first, level), xfs_btree_ptr_offset(cur, last + 1, level) - 1); @@ -1223,7 +1361,12 @@ xfs_btree_log_block( offsetof(struct xfs_btree_block, bb_numrecs), offsetof(struct xfs_btree_block, bb_u.s.bb_leftsib), offsetof(struct xfs_btree_block, bb_u.s.bb_rightsib), - XFS_BTREE_SBLOCK_LEN + offsetof(struct xfs_btree_block, bb_u.s.bb_blkno), + offsetof(struct xfs_btree_block, bb_u.s.bb_lsn), + offsetof(struct xfs_btree_block, bb_u.s.bb_uuid), + offsetof(struct xfs_btree_block, bb_u.s.bb_owner), + offsetof(struct xfs_btree_block, bb_u.s.bb_crc), + XFS_BTREE_SBLOCK_CRC_LEN }; static const short loffsets[] = { /* table of offsets (long) */ offsetof(struct xfs_btree_block, bb_magic), @@ -1231,17 +1374,40 @@ xfs_btree_log_block( offsetof(struct xfs_btree_block, bb_numrecs), offsetof(struct xfs_btree_block, bb_u.l.bb_leftsib), offsetof(struct xfs_btree_block, bb_u.l.bb_rightsib), - XFS_BTREE_LBLOCK_LEN + offsetof(struct xfs_btree_block, bb_u.l.bb_blkno), + offsetof(struct xfs_btree_block, bb_u.l.bb_lsn), + offsetof(struct xfs_btree_block, bb_u.l.bb_uuid), + offsetof(struct xfs_btree_block, bb_u.l.bb_owner), + offsetof(struct xfs_btree_block, bb_u.l.bb_crc), + offsetof(struct xfs_btree_block, bb_u.l.bb_pad), + XFS_BTREE_LBLOCK_CRC_LEN }; XFS_BTREE_TRACE_CURSOR(cur, XBT_ENTRY); XFS_BTREE_TRACE_ARGBI(cur, bp, fields); if (bp) { + int nbits; + + if (cur->bc_flags & XFS_BTREE_CRC_BLOCKS) { + /* + * We don't log the CRC when updating a btree + * block but instead recreate it during log + * recovery. As the log buffers have checksums + * of their own this is safe and avoids logging a crc + * update in a lot of places. + */ + if (fields == XFS_BB_ALL_BITS) + fields = XFS_BB_ALL_BITS_CRC; + nbits = XFS_BB_NUM_BITS_CRC; + } else { + nbits = XFS_BB_NUM_BITS; + } xfs_btree_offsets(fields, (cur->bc_flags & XFS_BTREE_LONG_PTRS) ? loffsets : soffsets, - XFS_BB_NUM_BITS, &first, &last); + nbits, &first, &last); + xfs_trans_buf_set_type(cur->bc_tp, bp, XFS_BLF_BTREE_BUF); xfs_trans_log_buf(cur->bc_tp, bp, first, last); } else { xfs_trans_log_inode(cur->bc_tp, cur->bc_private.b.ip, @@ -2204,7 +2370,7 @@ xfs_btree_split( goto error0; /* Fill in the btree header for the new right block. */ - xfs_btree_init_block_cur(cur, xfs_btree_get_level(left), 0, rbp); + xfs_btree_init_block_cur(cur, rbp, xfs_btree_get_level(left), 0); /* * Split the entries between the old and the new block evenly. @@ -2513,7 +2679,7 @@ xfs_btree_new_root( nptr = 2; } /* Fill in the new block's btree header and log it. */ - xfs_btree_init_block_cur(cur, cur->bc_nlevels, 2, nbp); + xfs_btree_init_block_cur(cur, nbp, cur->bc_nlevels, 2); xfs_btree_log_block(cur, nbp, XFS_BB_ALL_BITS); ASSERT(!xfs_btree_ptr_is_null(cur, &lptr) && !xfs_btree_ptr_is_null(cur, &rptr)); diff --git a/fs/xfs/xfs_btree.h b/fs/xfs/xfs_btree.h index f932897..6e6c915 100644 --- a/fs/xfs/xfs_btree.h +++ b/fs/xfs/xfs_btree.h @@ -42,11 +42,15 @@ extern kmem_zone_t *xfs_btree_cur_zone; * Generic btree header. * * This is a combination of the actual format used on disk for short and long - * format btrees. The first three fields are shared by both format, but - * the pointers are different and should be used with care. + * format btrees. The first three fields are shared by both format, but the + * pointers are different and should be used with care. * - * To get the size of the actual short or long form headers please use - * the size macros below. Never use sizeof(xfs_btree_block). + * To get the size of the actual short or long form headers please use the size + * macros below. Never use sizeof(xfs_btree_block). + * + * The blkno, crc, lsn, owner and uuid fields are only available in filesystems + * with the crc feature bit, and all accesses to them must be conditional on + * that flag. */ struct xfs_btree_block { __be32 bb_magic; /* magic number for block type */ @@ -56,10 +60,23 @@ struct xfs_btree_block { struct { __be32 bb_leftsib; __be32 bb_rightsib; + + __be64 bb_blkno; + __be64 bb_lsn; + uuid_t bb_uuid; + __be32 bb_owner; + __le32 bb_crc; } s; /* short form pointers */ struct { __be64 bb_leftsib; __be64 bb_rightsib; + + __be64 bb_blkno; + __be64 bb_lsn; + uuid_t bb_uuid; + __be64 bb_owner; + __le32 bb_crc; + __be32 bb_pad; /* padding for alignment */ } l; /* long form pointers */ } bb_u; /* rest */ }; @@ -67,6 +84,16 @@ struct xfs_btree_block { #define XFS_BTREE_SBLOCK_LEN 16 /* size of a short form block */ #define XFS_BTREE_LBLOCK_LEN 24 /* size of a long form block */ +/* sizes of CRC enabled btree blocks */ +#define XFS_BTREE_SBLOCK_CRC_LEN (XFS_BTREE_SBLOCK_LEN + 40) +#define XFS_BTREE_LBLOCK_CRC_LEN (XFS_BTREE_LBLOCK_LEN + 48) + + +#define XFS_BTREE_SBLOCK_CRC_OFF \ + offsetof(struct xfs_btree_block, bb_u.s.bb_crc) +#define XFS_BTREE_LBLOCK_CRC_OFF \ + offsetof(struct xfs_btree_block, bb_u.l.bb_crc) + /* * Generic key, ptr and record wrapper structures. @@ -101,13 +128,11 @@ union xfs_btree_rec { #define XFS_BB_NUMRECS 0x04 #define XFS_BB_LEFTSIB 0x08 #define XFS_BB_RIGHTSIB 0x10 +#define XFS_BB_BLKNO 0x20 #define XFS_BB_NUM_BITS 5 #define XFS_BB_ALL_BITS ((1 << XFS_BB_NUM_BITS) - 1) - -/* - * Magic numbers for btree blocks. - */ -extern const __uint32_t xfs_magics[]; +#define XFS_BB_NUM_BITS_CRC 8 +#define XFS_BB_ALL_BITS_CRC ((1 << XFS_BB_NUM_BITS_CRC) - 1) /* * Generic stats interface @@ -256,6 +281,7 @@ typedef struct xfs_btree_cur #define XFS_BTREE_LONG_PTRS (1<<0) /* pointers are 64bits long */ #define XFS_BTREE_ROOT_IN_INODE (1<<1) /* root may be variable size */ #define XFS_BTREE_LASTREC_UPDATE (1<<2) /* track last rec externally */ +#define XFS_BTREE_CRC_BLOCKS (1<<3) /* uses extended btree blocks */ #define XFS_BTREE_NOERROR 0 @@ -393,8 +419,20 @@ xfs_btree_init_block( __u32 magic, __u16 level, __u16 numrecs, + __u64 owner, unsigned int flags); +void +xfs_btree_init_block_int( + struct xfs_mount *mp, + struct xfs_btree_block *buf, + xfs_daddr_t blkno, + __u32 magic, + __u16 level, + __u16 numrecs, + __u64 owner, + unsigned int flags); + /* * Common btree core entry points. */ @@ -408,6 +446,14 @@ int xfs_btree_delete(struct xfs_btree_cur *, int *); int xfs_btree_get_rec(struct xfs_btree_cur *, union xfs_btree_rec **, int *); /* + * btree block CRC helpers + */ +void xfs_btree_lblock_calc_crc(struct xfs_buf *); +bool xfs_btree_lblock_verify_crc(struct xfs_buf *); +void xfs_btree_sblock_calc_crc(struct xfs_buf *); +bool xfs_btree_sblock_verify_crc(struct xfs_buf *); + +/* * Internal btree helpers also used by xfs_bmap.c. */ void xfs_btree_log_block(struct xfs_btree_cur *, struct xfs_buf *, int); diff --git a/fs/xfs/xfs_buf_item.h b/fs/xfs/xfs_buf_item.h index ee36c88..101ef83 100644 --- a/fs/xfs/xfs_buf_item.h +++ b/fs/xfs/xfs_buf_item.h @@ -24,19 +24,33 @@ extern kmem_zone_t *xfs_buf_item_zone; * This flag indicates that the buffer contains on disk inodes * and requires special recovery handling. */ -#define XFS_BLF_INODE_BUF 0x1 +#define XFS_BLF_INODE_BUF (1<<0) /* * This flag indicates that the buffer should not be replayed * during recovery because its blocks are being freed. */ -#define XFS_BLF_CANCEL 0x2 +#define XFS_BLF_CANCEL (1<<1) + /* * This flag indicates that the buffer contains on disk * user or group dquots and may require special recovery handling. */ -#define XFS_BLF_UDQUOT_BUF 0x4 -#define XFS_BLF_PDQUOT_BUF 0x8 -#define XFS_BLF_GDQUOT_BUF 0x10 +#define XFS_BLF_UDQUOT_BUF (1<<2) +#define XFS_BLF_PDQUOT_BUF (1<<3) +#define XFS_BLF_GDQUOT_BUF (1<<4) + +/* + * all buffers now need flags to tell recovery where the magic number + * is so that it can verify and calculate the CRCs on the buffer correctly + * once the changes have been replayed into the buffer. + */ +#define XFS_BLF_BTREE_BUF (1<<5) + +#define XFS_BLF_TYPE_MASK \ + (XFS_BLF_UDQUOT_BUF | \ + XFS_BLF_PDQUOT_BUF | \ + XFS_BLF_GDQUOT_BUF | \ + XFS_BLF_BTREE_BUF) #define XFS_BLF_CHUNK 128 #define XFS_BLF_SHIFT 7 diff --git a/fs/xfs/xfs_dinode.h b/fs/xfs/xfs_dinode.h index 88a3368..6b5bd17 100644 --- a/fs/xfs/xfs_dinode.h +++ b/fs/xfs/xfs_dinode.h @@ -107,8 +107,8 @@ typedef enum xfs_dinode_fmt { #define XFS_LITINO(mp, version) \ ((int)(((mp)->m_sb.sb_inodesize) - sizeof(struct xfs_dinode))) -#define XFS_BROOT_SIZE_ADJ \ - (XFS_BTREE_LBLOCK_LEN - sizeof(xfs_bmdr_block_t)) +#define XFS_BROOT_SIZE_ADJ(ip) \ + (XFS_BMBT_BLOCK_LEN((ip)->i_mount) - sizeof(xfs_bmdr_block_t)) /* * Inode data & attribute fork sizes, per inode. diff --git a/fs/xfs/xfs_fsops.c b/fs/xfs/xfs_fsops.c index 2866b8c..6fe286a 100644 --- a/fs/xfs/xfs_fsops.c +++ b/fs/xfs/xfs_fsops.c @@ -316,7 +316,13 @@ xfs_growfs_data_private( goto error0; } - xfs_btree_init_block(mp, bp, XFS_ABTB_MAGIC, 0, 1, 0); + if (xfs_sb_version_hascrc(&mp->m_sb)) + xfs_btree_init_block(mp, bp, XFS_ABTB_CRC_MAGIC, 0, 1, + agno, XFS_BTREE_CRC_BLOCKS); + else + xfs_btree_init_block(mp, bp, XFS_ABTB_MAGIC, 0, 1, + agno, 0); + arec = XFS_ALLOC_REC_ADDR(mp, XFS_BUF_TO_BLOCK(bp), 1); arec->ar_startblock = cpu_to_be32(XFS_PREALLOC_BLOCKS(mp)); arec->ar_blockcount = cpu_to_be32( @@ -339,7 +345,13 @@ xfs_growfs_data_private( goto error0; } - xfs_btree_init_block(mp, bp, XFS_ABTC_MAGIC, 0, 1, 0); + if (xfs_sb_version_hascrc(&mp->m_sb)) + xfs_btree_init_block(mp, bp, XFS_ABTC_CRC_MAGIC, 0, 1, + agno, XFS_BTREE_CRC_BLOCKS); + else + xfs_btree_init_block(mp, bp, XFS_ABTC_MAGIC, 0, 1, + agno, 0); + arec = XFS_ALLOC_REC_ADDR(mp, XFS_BUF_TO_BLOCK(bp), 1); arec->ar_startblock = cpu_to_be32(XFS_PREALLOC_BLOCKS(mp)); arec->ar_blockcount = cpu_to_be32( @@ -363,7 +375,12 @@ xfs_growfs_data_private( goto error0; } - xfs_btree_init_block(mp, bp, XFS_IBT_MAGIC, 0, 0, 0); + if (xfs_sb_version_hascrc(&mp->m_sb)) + xfs_btree_init_block(mp, bp, XFS_IBT_CRC_MAGIC, 0, 0, + agno, XFS_BTREE_CRC_BLOCKS); + else + xfs_btree_init_block(mp, bp, XFS_IBT_MAGIC, 0, 0, + agno, 0); error = xfs_bwrite(bp); xfs_buf_relse(bp); diff --git a/fs/xfs/xfs_ialloc_btree.c b/fs/xfs/xfs_ialloc_btree.c index bec344b..c82ac88 100644 --- a/fs/xfs/xfs_ialloc_btree.c +++ b/fs/xfs/xfs_ialloc_btree.c @@ -34,6 +34,7 @@ #include "xfs_alloc.h" #include "xfs_error.h" #include "xfs_trace.h" +#include "xfs_cksum.h" STATIC int @@ -182,52 +183,88 @@ xfs_inobt_key_diff( cur->bc_rec.i.ir_startino; } -void +static int xfs_inobt_verify( struct xfs_buf *bp) { struct xfs_mount *mp = bp->b_target->bt_mount; struct xfs_btree_block *block = XFS_BUF_TO_BLOCK(bp); + struct xfs_perag *pag = bp->b_pag; unsigned int level; - int sblock_ok; /* block passes checks */ - /* magic number and level verification */ - level = be16_to_cpu(block->bb_level); - sblock_ok = block->bb_magic == cpu_to_be32(XFS_IBT_MAGIC) && - level < mp->m_in_maxlevels; + /* + * During growfs operations, we can't verify the exact owner as the + * perag is not fully initialised and hence not attached to the buffer. + * + * Similarly, during log recovery we will have a perag structure + * attached, but the agi information will not yet have been initialised + * from the on disk AGI. We don't currently use any of this information, + * but beware of the landmine (i.e. need to check pag->pagi_init) if we + * ever do. + */ + switch (block->bb_magic) { + case cpu_to_be32(XFS_IBT_CRC_MAGIC): + if (!xfs_sb_version_hascrc(&mp->m_sb)) + return false; + if (!uuid_equal(&block->bb_u.s.bb_uuid, &mp->m_sb.sb_uuid)) + return false; + if (block->bb_u.s.bb_blkno != cpu_to_be64(bp->b_bn)) + return false; + if (pag && + be32_to_cpu(block->bb_u.s.bb_owner) != pag->pag_agno) + return false; + /* fall through */ + case cpu_to_be32(XFS_IBT_MAGIC): + break; + default: + return 0; + } - /* numrecs verification */ - sblock_ok = sblock_ok && - be16_to_cpu(block->bb_numrecs) <= mp->m_inobt_mxr[level != 0]; + /* numrecs and level verification */ + level = be16_to_cpu(block->bb_level); + if (level >= mp->m_in_maxlevels) + return false; + if (be16_to_cpu(block->bb_numrecs) > mp->m_inobt_mxr[level != 0]) + return false; /* sibling pointer verification */ - sblock_ok = sblock_ok && - (block->bb_u.s.bb_leftsib == cpu_to_be32(NULLAGBLOCK) || - be32_to_cpu(block->bb_u.s.bb_leftsib) < mp->m_sb.sb_agblocks) && - block->bb_u.s.bb_leftsib && - (block->bb_u.s.bb_rightsib == cpu_to_be32(NULLAGBLOCK) || - be32_to_cpu(block->bb_u.s.bb_rightsib) < mp->m_sb.sb_agblocks) && - block->bb_u.s.bb_rightsib; - - if (!sblock_ok) { - trace_xfs_btree_corrupt(bp, _RET_IP_); - XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, mp, block); - xfs_buf_ioerror(bp, EFSCORRUPTED); - } + if (!block->bb_u.s.bb_leftsib || + (be32_to_cpu(block->bb_u.s.bb_leftsib) >= mp->m_sb.sb_agblocks && + block->bb_u.s.bb_leftsib != cpu_to_be32(NULLAGBLOCK))) + return false; + if (!block->bb_u.s.bb_rightsib || + (be32_to_cpu(block->bb_u.s.bb_rightsib) >= mp->m_sb.sb_agblocks && + block->bb_u.s.bb_rightsib != cpu_to_be32(NULLAGBLOCK))) + return false; + + return true; } static void xfs_inobt_read_verify( struct xfs_buf *bp) { - xfs_inobt_verify(bp); + if (!(xfs_btree_sblock_verify_crc(bp) && + xfs_inobt_verify(bp))) { + trace_xfs_btree_corrupt(bp, _RET_IP_); + XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, + bp->b_target->bt_mount, bp->b_addr); + xfs_buf_ioerror(bp, EFSCORRUPTED); + } } static void xfs_inobt_write_verify( struct xfs_buf *bp) { - xfs_inobt_verify(bp); + if (!xfs_inobt_verify(bp)) { + trace_xfs_btree_corrupt(bp, _RET_IP_); + XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, + bp->b_target->bt_mount, bp->b_addr); + xfs_buf_ioerror(bp, EFSCORRUPTED); + } + xfs_btree_sblock_calc_crc(bp); + } const struct xfs_buf_ops xfs_inobt_buf_ops = { @@ -301,6 +338,8 @@ xfs_inobt_init_cursor( cur->bc_blocklog = mp->m_sb.sb_blocklog; cur->bc_ops = &xfs_inobt_ops; + if (xfs_sb_version_hascrc(&mp->m_sb)) + cur->bc_flags |= XFS_BTREE_CRC_BLOCKS; cur->bc_private.a.agbp = agbp; cur->bc_private.a.agno = agno; diff --git a/fs/xfs/xfs_ialloc_btree.h b/fs/xfs/xfs_ialloc_btree.h index 25c0239..3ac36b76 100644 --- a/fs/xfs/xfs_ialloc_btree.h +++ b/fs/xfs/xfs_ialloc_btree.h @@ -29,7 +29,8 @@ struct xfs_mount; /* * There is a btree for the inode map per allocation group. */ -#define XFS_IBT_MAGIC 0x49414254 /* 'IABT' */ +#define XFS_IBT_MAGIC 0x49414254 /* 'IABT' */ +#define XFS_IBT_CRC_MAGIC 0x49414233 /* 'IAB3' */ typedef __uint64_t xfs_inofree_t; #define XFS_INODES_PER_CHUNK (NBBY * sizeof(xfs_inofree_t)) @@ -76,10 +77,10 @@ typedef __be32 xfs_inobt_ptr_t; /* * Btree block header size depends on a superblock flag. - * - * (not quite yet, but soon) */ -#define XFS_INOBT_BLOCK_LEN(mp) XFS_BTREE_SBLOCK_LEN +#define XFS_INOBT_BLOCK_LEN(mp) \ + (xfs_sb_version_hascrc(&((mp)->m_sb)) ? \ + XFS_BTREE_SBLOCK_CRC_LEN : XFS_BTREE_SBLOCK_LEN) /* * Record, key, and pointer address macros for btree blocks. diff --git a/fs/xfs/xfs_inode.c b/fs/xfs/xfs_inode.c index 4f20165..202ce37 100644 --- a/fs/xfs/xfs_inode.c +++ b/fs/xfs/xfs_inode.c @@ -786,6 +786,7 @@ xfs_iformat_btree( xfs_dinode_t *dip, int whichfork) { + struct xfs_mount *mp = ip->i_mount; xfs_bmdr_block_t *dfp; xfs_ifork_t *ifp; /* REFERENCED */ @@ -794,7 +795,7 @@ xfs_iformat_btree( ifp = XFS_IFORK_PTR(ip, whichfork); dfp = (xfs_bmdr_block_t *)XFS_DFORK_PTR(dip, whichfork); - size = XFS_BMAP_BROOT_SPACE(dfp); + size = XFS_BMAP_BROOT_SPACE(mp, dfp); nrecs = be16_to_cpu(dfp->bb_numrecs); /* @@ -805,14 +806,14 @@ xfs_iformat_btree( * blocks. */ if (unlikely(XFS_IFORK_NEXTENTS(ip, whichfork) <= - XFS_IFORK_MAXEXT(ip, whichfork) || + XFS_IFORK_MAXEXT(ip, whichfork) || XFS_BMDR_SPACE_CALC(nrecs) > - XFS_DFORK_SIZE(dip, ip->i_mount, whichfork) || + XFS_DFORK_SIZE(dip, mp, whichfork) || XFS_IFORK_NEXTENTS(ip, whichfork) > ip->i_d.di_nblocks)) { - xfs_warn(ip->i_mount, "corrupt inode %Lu (btree).", - (unsigned long long) ip->i_ino); + xfs_warn(mp, "corrupt inode %Lu (btree).", + (unsigned long long) ip->i_ino); XFS_CORRUPTION_ERROR("xfs_iformat_btree", XFS_ERRLEVEL_LOW, - ip->i_mount, dip); + mp, dip); return XFS_ERROR(EFSCORRUPTED); } @@ -823,8 +824,7 @@ xfs_iformat_btree( * Copy and convert from the on-disk structure * to the in-memory structure. */ - xfs_bmdr_to_bmbt(ip->i_mount, dfp, - XFS_DFORK_SIZE(dip, ip->i_mount, whichfork), + xfs_bmdr_to_bmbt(ip, dfp, XFS_DFORK_SIZE(dip, ip->i_mount, whichfork), ifp->if_broot, size); ifp->if_flags &= ~XFS_IFEXTENTS; ifp->if_flags |= XFS_IFBROOT; @@ -2037,7 +2037,7 @@ xfs_iroot_realloc( * allocate it now and get out. */ if (ifp->if_broot_bytes == 0) { - new_size = (size_t)XFS_BMAP_BROOT_SPACE_CALC(rec_diff); + new_size = XFS_BMAP_BROOT_SPACE_CALC(mp, rec_diff); ifp->if_broot = kmem_alloc(new_size, KM_SLEEP | KM_NOFS); ifp->if_broot_bytes = (int)new_size; return; @@ -2051,9 +2051,9 @@ xfs_iroot_realloc( */ cur_max = xfs_bmbt_maxrecs(mp, ifp->if_broot_bytes, 0); new_max = cur_max + rec_diff; - new_size = (size_t)XFS_BMAP_BROOT_SPACE_CALC(new_max); + new_size = XFS_BMAP_BROOT_SPACE_CALC(mp, new_max); ifp->if_broot = kmem_realloc(ifp->if_broot, new_size, - (size_t)XFS_BMAP_BROOT_SPACE_CALC(cur_max), /* old size */ + XFS_BMAP_BROOT_SPACE_CALC(mp, cur_max), KM_SLEEP | KM_NOFS); op = (char *)XFS_BMAP_BROOT_PTR_ADDR(mp, ifp->if_broot, 1, ifp->if_broot_bytes); @@ -2061,7 +2061,7 @@ xfs_iroot_realloc( (int)new_size); ifp->if_broot_bytes = (int)new_size; ASSERT(ifp->if_broot_bytes <= - XFS_IFORK_SIZE(ip, whichfork) + XFS_BROOT_SIZE_ADJ); + XFS_IFORK_SIZE(ip, whichfork) + XFS_BROOT_SIZE_ADJ(ip)); memmove(np, op, cur_max * (uint)sizeof(xfs_dfsbno_t)); return; } @@ -2076,7 +2076,7 @@ xfs_iroot_realloc( new_max = cur_max + rec_diff; ASSERT(new_max >= 0); if (new_max > 0) - new_size = (size_t)XFS_BMAP_BROOT_SPACE_CALC(new_max); + new_size = XFS_BMAP_BROOT_SPACE_CALC(mp, new_max); else new_size = 0; if (new_size > 0) { @@ -2084,7 +2084,8 @@ xfs_iroot_realloc( /* * First copy over the btree block header. */ - memcpy(new_broot, ifp->if_broot, XFS_BTREE_LBLOCK_LEN); + memcpy(new_broot, ifp->if_broot, + XFS_BMBT_BLOCK_LEN(ip->i_mount)); } else { new_broot = NULL; ifp->if_flags &= ~XFS_IFBROOT; @@ -2114,7 +2115,7 @@ xfs_iroot_realloc( ifp->if_broot = new_broot; ifp->if_broot_bytes = (int)new_size; ASSERT(ifp->if_broot_bytes <= - XFS_IFORK_SIZE(ip, whichfork) + XFS_BROOT_SIZE_ADJ); + XFS_IFORK_SIZE(ip, whichfork) + XFS_BROOT_SIZE_ADJ(ip)); return; } @@ -2427,7 +2428,7 @@ xfs_iflush_fork( ASSERT(ifp->if_broot != NULL); ASSERT(ifp->if_broot_bytes <= (XFS_IFORK_SIZE(ip, whichfork) + - XFS_BROOT_SIZE_ADJ)); + XFS_BROOT_SIZE_ADJ(ip))); xfs_bmbt_to_bmdr(mp, ifp->if_broot, ifp->if_broot_bytes, (xfs_bmdr_block_t *)cp, XFS_DFORK_SIZE(dip, mp, whichfork)); diff --git a/fs/xfs/xfs_log_recover.c b/fs/xfs/xfs_log_recover.c index d1dba7c..10b9854 100644 --- a/fs/xfs/xfs_log_recover.c +++ b/fs/xfs/xfs_log_recover.c @@ -29,6 +29,7 @@ #include "xfs_bmap_btree.h" #include "xfs_alloc_btree.h" #include "xfs_ialloc_btree.h" +#include "xfs_btree.h" #include "xfs_dinode.h" #include "xfs_inode.h" #include "xfs_inode_item.h" @@ -1928,6 +1929,33 @@ xlog_recover_do_reg_buffer( /* Shouldn't be any more regions */ ASSERT(i == item->ri_total); + + switch (buf_f->blf_flags & XFS_BLF_TYPE_MASK) { + case XFS_BLF_BTREE_BUF: + switch (be32_to_cpu(*(__be32 *)bp->b_addr)) { + case XFS_ABTB_CRC_MAGIC: + case XFS_ABTC_CRC_MAGIC: + case XFS_ABTB_MAGIC: + case XFS_ABTC_MAGIC: + bp->b_ops = &xfs_allocbt_buf_ops; + break; + case XFS_IBT_CRC_MAGIC: + case XFS_IBT_MAGIC: + bp->b_ops = &xfs_inobt_buf_ops; + break; + case XFS_BMAP_CRC_MAGIC: + case XFS_BMAP_MAGIC: + bp->b_ops = &xfs_bmbt_buf_ops; + break; + default: + xfs_warn(mp, "Bad btree block magic!"); + ASSERT(0); + break; + } + break; + default: + break; + } } /* diff --git a/fs/xfs/xfs_trans.h b/fs/xfs/xfs_trans.h index cd29f61..1b04fe5 100644 --- a/fs/xfs/xfs_trans.h +++ b/fs/xfs/xfs_trans.h @@ -505,6 +505,8 @@ void xfs_trans_inode_buf(xfs_trans_t *, struct xfs_buf *); void xfs_trans_stale_inode_buf(xfs_trans_t *, struct xfs_buf *); void xfs_trans_dquot_buf(xfs_trans_t *, struct xfs_buf *, uint); void xfs_trans_inode_alloc_buf(xfs_trans_t *, struct xfs_buf *); +void xfs_trans_buf_set_type(struct xfs_trans *, struct xfs_buf *, + uint); void xfs_trans_ichgtime(struct xfs_trans *, struct xfs_inode *, int); void xfs_trans_ijoin(struct xfs_trans *, struct xfs_inode *, uint); void xfs_trans_log_buf(xfs_trans_t *, struct xfs_buf *, uint, uint); diff --git a/fs/xfs/xfs_trans_buf.c b/fs/xfs/xfs_trans_buf.c index 3edf5db..f950edd 100644 --- a/fs/xfs/xfs_trans_buf.c +++ b/fs/xfs/xfs_trans_buf.c @@ -659,6 +659,7 @@ xfs_trans_binval( ASSERT(XFS_BUF_ISSTALE(bp)); ASSERT(!(bip->bli_flags & (XFS_BLI_LOGGED | XFS_BLI_DIRTY))); ASSERT(!(bip->__bli_format.blf_flags & XFS_BLF_INODE_BUF)); + ASSERT(!(bip->__bli_format.blf_flags & XFS_BLF_TYPE_MASK)); ASSERT(bip->__bli_format.blf_flags & XFS_BLF_CANCEL); ASSERT(bip->bli_item.li_desc->lid_flags & XFS_LID_DIRTY); ASSERT(tp->t_flags & XFS_TRANS_DIRTY); @@ -671,6 +672,7 @@ xfs_trans_binval( bip->bli_flags &= ~(XFS_BLI_INODE_BUF | XFS_BLI_LOGGED | XFS_BLI_DIRTY); bip->__bli_format.blf_flags &= ~XFS_BLF_INODE_BUF; bip->__bli_format.blf_flags |= XFS_BLF_CANCEL; + bip->__bli_format.blf_flags &= ~XFS_BLF_TYPE_MASK; for (i = 0; i < bip->bli_format_count; i++) { memset(bip->bli_formats[i].blf_data_map, 0, (bip->bli_formats[i].blf_map_size * sizeof(uint))); @@ -751,6 +753,26 @@ xfs_trans_inode_alloc_buf( bip->bli_flags |= XFS_BLI_INODE_ALLOC_BUF; } +/* + * Set the type of the buffer for log recovery so that it can correctly identify + * and hence attach the correct buffer ops to the buffer after replay. + */ +void +xfs_trans_buf_set_type( + struct xfs_trans *tp, + struct xfs_buf *bp, + uint type) +{ + struct xfs_buf_log_item *bip = bp->b_fspriv; + + ASSERT(bp->b_transp == tp); + ASSERT(bip != NULL); + ASSERT(atomic_read(&bip->bli_refcount) > 0); + ASSERT((type & XFS_BLF_TYPE_MASK) != 0); + + bip->__bli_format.blf_flags &= ~XFS_BLF_TYPE_MASK; + bip->__bli_format.blf_flags |= type; +} /* * Similar to xfs_trans_inode_buf(), this marks the buffer as a cluster of @@ -769,14 +791,9 @@ xfs_trans_dquot_buf( xfs_buf_t *bp, uint type) { - xfs_buf_log_item_t *bip = bp->b_fspriv; - - ASSERT(bp->b_transp == tp); - ASSERT(bip != NULL); ASSERT(type == XFS_BLF_UDQUOT_BUF || type == XFS_BLF_PDQUOT_BUF || type == XFS_BLF_GDQUOT_BUF); - ASSERT(atomic_read(&bip->bli_refcount) > 0); - bip->__bli_format.blf_flags |= type; + xfs_trans_buf_set_type(tp, bp, type); } -- 1.7.10.4 From dave@fromorbit.com Tue Mar 12 07:31:21 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 89E1F7F9E for ; Tue, 12 Mar 2013 07:31:18 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay1.corp.sgi.com (Postfix) with ESMTP id 76E768F8035 for ; Tue, 12 Mar 2013 05:31:18 -0700 (PDT) X-ASG-Debug-ID: 1363091470-04cbb07dbe487eb0003-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id 2ovDyMjUyeWE2OJu for ; Tue, 12 Mar 2013 05:31:15 -0700 (PDT) X-Barracuda-Envelope-From: dave@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: Ag8KAKEfP1F5LKiV/2dsb2JhbABDxF0DAYFJF3SCKAEBBRoNLzMIGDE5AxsZiBKwApAfjUFLdoNSA6dKgx4o Received: from ppp121-44-168-149.lns20.syd7.internode.on.net (HELO dastard) ([121.44.168.149]) by ipmail05.adl6.internode.on.net with ESMTP; 12 Mar 2013 23:01:14 +1030 Received: from disappointment ([192.168.1.1]) by dastard with esmtp (Exim 4.76) (envelope-from ) id 1UFOML-0001SC-Ex for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:31:13 +1100 Received: from dave by disappointment with local (Exim 4.80) (envelope-from ) id 1UFOMG-0002MW-BL for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:31:08 +1100 From: Dave Chinner To: xfs@oss.sgi.com Subject: [PATCH 12/21] xfs: add CRC checking to dir2 free blocks Date: Tue, 12 Mar 2013 23:30:45 +1100 X-ASG-Orig-Subj: [PATCH 12/21] xfs: add CRC checking to dir2 free blocks Message-Id: <1363091454-8852-13-git-send-email-david@fromorbit.com> X-Mailer: git-send-email 1.7.10.4 In-Reply-To: <1363091454-8852-1-git-send-email-david@fromorbit.com> References: <1363091454-8852-1-git-send-email-david@fromorbit.com> X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1363091474 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.60 X-Barracuda-Spam-Status: No, SCORE=0.60 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=MARKETING_SUBJECT X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124988 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.60 MARKETING_SUBJECT Subject contains popular marketing words From: Dave Chinner This addition follows the same pattern as the dir2 block CRCs, but with a few differences. The main difference is that the free block header is different between the v2 and v3 formats, so an "in-core" free block header has been added and _todisk/_from_disk functions used to abstract the differences in structure format from the code. This is similar to the on-disk superblock versus the in-core superblock setup. The in-core strucutre is populated when the buffer is read from disk, all the in memory checks and modifications are done on the in-core version of the structure which is written back to the buffer before the buffer is logged. Signed-off-by: Dave Chinner --- fs/xfs/xfs_dir2_format.h | 55 +++++- fs/xfs/xfs_dir2_leaf.c | 15 +- fs/xfs/xfs_dir2_node.c | 476 +++++++++++++++++++++++++++++++--------------- 3 files changed, 384 insertions(+), 162 deletions(-) diff --git a/fs/xfs/xfs_dir2_format.h b/fs/xfs/xfs_dir2_format.h index 7dc26b0..bec058f 100644 --- a/fs/xfs/xfs_dir2_format.h +++ b/fs/xfs/xfs_dir2_format.h @@ -66,6 +66,7 @@ #define XFS_DIR3_BLOCK_MAGIC 0x58444233 /* XDB3: single block dirs */ #define XFS_DIR3_DATA_MAGIC 0x58444433 /* XDD3: multiblock dirs */ +#define XFS_DIR3_FREE_MAGIC 0x58444633 /* XDF3: free index blocks */ /* * Byte offset in data block and shortform entry. @@ -663,19 +664,65 @@ typedef struct xfs_dir2_free { /* unused entries are -1 */ } xfs_dir2_free_t; -static inline int xfs_dir2_free_max_bests(struct xfs_mount *mp) +struct xfs_dir3_free_hdr { + struct xfs_dir3_blk_hdr hdr; + __be32 firstdb; /* db of first entry */ + __be32 nvalid; /* count of valid entries */ + __be32 nused; /* count of used entries */ +}; + +struct xfs_dir3_free { + struct xfs_dir3_free_hdr hdr; + __be16 bests[]; /* best free counts */ + /* unused entries are -1 */ +}; + +#define XFS_DIR3_FREE_CRC_OFF offsetof(struct xfs_dir3_free, hdr.hdr.crc) + +/* + * In core version of the free block header, abstracted away from on-disk format + * differences. Use this in the code, and convert to/from the disk version using + * xfs_dir3_free_hdr_from_disk/xfs_dir3_free_hdr_to_disk. + */ +struct xfs_dir3_icfree_hdr { + __uint32_t magic; + __uint32_t firstdb; + __uint32_t nvalid; + __uint32_t nused; + +}; + +void xfs_dir3_free_hdr_from_disk(struct xfs_dir3_icfree_hdr *to, + struct xfs_dir2_free *from); + +static inline int +xfs_dir3_free_hdr_size(struct xfs_mount *mp) { - return (mp->m_dirblksize - sizeof(struct xfs_dir2_free_hdr)) / + if (xfs_sb_version_hascrc(&mp->m_sb)) + return sizeof(struct xfs_dir3_free_hdr); + return sizeof(struct xfs_dir2_free_hdr); +} + +static inline int +xfs_dir3_free_max_bests(struct xfs_mount *mp) +{ + return (mp->m_dirblksize - xfs_dir3_free_hdr_size(mp)) / sizeof(xfs_dir2_data_off_t); } +static inline __be16 * +xfs_dir3_free_bests_p(struct xfs_mount *mp, struct xfs_dir2_free *free) +{ + return (__be16 *)((char *)free + xfs_dir3_free_hdr_size(mp)); +} + /* * Convert data space db to the corresponding free db. */ static inline xfs_dir2_db_t xfs_dir2_db_to_fdb(struct xfs_mount *mp, xfs_dir2_db_t db) { - return XFS_DIR2_FREE_FIRSTDB(mp) + db / xfs_dir2_free_max_bests(mp); + return XFS_DIR2_FREE_FIRSTDB(mp) + db / xfs_dir3_free_max_bests(mp); } /* @@ -684,7 +731,7 @@ xfs_dir2_db_to_fdb(struct xfs_mount *mp, xfs_dir2_db_t db) static inline int xfs_dir2_db_to_fdindex(struct xfs_mount *mp, xfs_dir2_db_t db) { - return db % xfs_dir2_free_max_bests(mp); + return db % xfs_dir3_free_max_bests(mp); } /* diff --git a/fs/xfs/xfs_dir2_leaf.c b/fs/xfs/xfs_dir2_leaf.c index ef163f0..979735b 100644 --- a/fs/xfs/xfs_dir2_leaf.c +++ b/fs/xfs/xfs_dir2_leaf.c @@ -1881,6 +1881,7 @@ xfs_dir2_node_to_leaf( xfs_mount_t *mp; /* filesystem mount point */ int rval; /* successful free trim? */ xfs_trans_t *tp; /* transaction pointer */ + struct xfs_dir3_icfree_hdr freehdr; /* * There's more than a leaf level in the btree, so there must @@ -1938,15 +1939,15 @@ xfs_dir2_node_to_leaf( if (error) return error; free = fbp->b_addr; - ASSERT(free->hdr.magic == cpu_to_be32(XFS_DIR2_FREE_MAGIC)); - ASSERT(!free->hdr.firstdb); + xfs_dir3_free_hdr_from_disk(&freehdr, free); + + ASSERT(!freehdr.firstdb); /* * Now see if the leafn and free data will fit in a leaf1. * If not, release the buffer and give up. */ - if (xfs_dir2_leaf_size(&leaf->hdr, be32_to_cpu(free->hdr.nvalid)) > - mp->m_dirblksize) { + if (xfs_dir2_leaf_size(&leaf->hdr, freehdr.nvalid) > mp->m_dirblksize) { xfs_trans_brelse(tp, fbp); return 0; } @@ -1967,12 +1968,12 @@ xfs_dir2_node_to_leaf( * Set up the leaf tail from the freespace block. */ ltp = xfs_dir2_leaf_tail_p(mp, leaf); - ltp->bestcount = free->hdr.nvalid; + ltp->bestcount = cpu_to_be32(freehdr.nvalid); /* * Set up the leaf bests table. */ - memcpy(xfs_dir2_leaf_bests_p(ltp), free->bests, - be32_to_cpu(ltp->bestcount) * sizeof(xfs_dir2_data_off_t)); + memcpy(xfs_dir2_leaf_bests_p(ltp), xfs_dir3_free_bests_p(mp, free), + freehdr.nvalid * sizeof(xfs_dir2_data_off_t)); xfs_dir2_leaf_log_bests(tp, lbp, 0, be32_to_cpu(ltp->bestcount) - 1); xfs_dir2_leaf_log_tail(tp, lbp); xfs_dir2_leaf_check(dp, lbp); diff --git a/fs/xfs/xfs_dir2_node.c b/fs/xfs/xfs_dir2_node.c index 985d70b..074fa68 100644 --- a/fs/xfs/xfs_dir2_node.c +++ b/fs/xfs/xfs_dir2_node.c @@ -1,5 +1,6 @@ /* * Copyright (c) 2000-2005 Silicon Graphics, Inc. + * Copyright (c) 2013 Red Hat, Inc. * All Rights Reserved. * * This program is free software; you can redistribute it and/or @@ -32,6 +33,8 @@ #include "xfs_dir2_priv.h" #include "xfs_error.h" #include "xfs_trace.h" +#include "xfs_buf_item.h" +#include "xfs_cksum.h" /* * Function declarations. @@ -55,44 +58,78 @@ static int xfs_dir2_leafn_remove(xfs_da_args_t *args, struct xfs_buf *bp, static int xfs_dir2_node_addname_int(xfs_da_args_t *args, xfs_da_state_blk_t *fblk); -static void -xfs_dir2_free_verify( +static bool +xfs_dir3_free_verify( struct xfs_buf *bp) { struct xfs_mount *mp = bp->b_target->bt_mount; struct xfs_dir2_free_hdr *hdr = bp->b_addr; - int block_ok = 0; - block_ok = hdr->magic == cpu_to_be32(XFS_DIR2_FREE_MAGIC); - if (!block_ok) { - XFS_CORRUPTION_ERROR("xfs_dir2_free_verify magic", - XFS_ERRLEVEL_LOW, mp, hdr); - xfs_buf_ioerror(bp, EFSCORRUPTED); + if (xfs_sb_version_hascrc(&mp->m_sb)) { + struct xfs_dir3_blk_hdr *hdr3 = bp->b_addr; + + if (hdr3->magic != be32_to_cpu(XFS_DIR3_FREE_MAGIC)) + return false; + if (!uuid_equal(&hdr3->uuid, &mp->m_sb.sb_uuid)) + return false; + if (be64_to_cpu(hdr3->blkno) != bp->b_bn) + return false; + } else { + if (hdr->magic != be32_to_cpu(XFS_DIR2_FREE_MAGIC)) + return false; } + + /* XXX: should bounds check the xfs_dir3_icfree_hdr here */ + + return true; } static void -xfs_dir2_free_read_verify( +xfs_dir3_free_read_verify( struct xfs_buf *bp) { - xfs_dir2_free_verify(bp); + struct xfs_mount *mp = bp->b_target->bt_mount; + + if ((xfs_sb_version_hascrc(&mp->m_sb) && + !xfs_verify_cksum(bp->b_addr, BBTOB(bp->b_length), + XFS_DIR3_FREE_CRC_OFF)) || + !xfs_dir3_free_verify(bp)) { + XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, mp, bp->b_addr); + xfs_buf_ioerror(bp, EFSCORRUPTED); + } } static void -xfs_dir2_free_write_verify( +xfs_dir3_free_write_verify( struct xfs_buf *bp) { - xfs_dir2_free_verify(bp); + struct xfs_mount *mp = bp->b_target->bt_mount; + struct xfs_buf_log_item *bip = bp->b_fspriv; + struct xfs_dir3_blk_hdr *hdr3 = bp->b_addr; + + if (!xfs_dir3_free_verify(bp)) { + XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, mp, bp->b_addr); + xfs_buf_ioerror(bp, EFSCORRUPTED); + return; + } + + if (!xfs_sb_version_hascrc(&mp->m_sb)) + return; + + if (bip) + hdr3->lsn = cpu_to_be64(bip->bli_item.li_lsn); + + xfs_update_cksum(bp->b_addr, BBTOB(bp->b_length), XFS_DIR3_FREE_CRC_OFF); } -static const struct xfs_buf_ops xfs_dir2_free_buf_ops = { - .verify_read = xfs_dir2_free_read_verify, - .verify_write = xfs_dir2_free_write_verify, +static const struct xfs_buf_ops xfs_dir3_free_buf_ops = { + .verify_read = xfs_dir3_free_read_verify, + .verify_write = xfs_dir3_free_write_verify, }; static int -__xfs_dir2_free_read( +__xfs_dir3_free_read( struct xfs_trans *tp, struct xfs_inode *dp, xfs_dablk_t fbno, @@ -100,7 +137,7 @@ __xfs_dir2_free_read( struct xfs_buf **bpp) { return xfs_da_read_buf(tp, dp, fbno, mappedbno, bpp, - XFS_DATA_FORK, &xfs_dir2_free_buf_ops); + XFS_DATA_FORK, &xfs_dir3_free_buf_ops); } int @@ -110,7 +147,7 @@ xfs_dir2_free_read( xfs_dablk_t fbno, struct xfs_buf **bpp) { - return __xfs_dir2_free_read(tp, dp, fbno, -1, bpp); + return __xfs_dir3_free_read(tp, dp, fbno, -1, bpp); } static int @@ -120,7 +157,95 @@ xfs_dir2_free_try_read( xfs_dablk_t fbno, struct xfs_buf **bpp) { - return __xfs_dir2_free_read(tp, dp, fbno, -2, bpp); + return __xfs_dir3_free_read(tp, dp, fbno, -2, bpp); +} + + +void +xfs_dir3_free_hdr_from_disk( + struct xfs_dir3_icfree_hdr *to, + struct xfs_dir2_free *from) +{ + if (from->hdr.magic == cpu_to_be32(XFS_DIR2_FREE_MAGIC)) { + to->magic = be32_to_cpu(from->hdr.magic); + to->firstdb = be32_to_cpu(from->hdr.firstdb); + to->nvalid = be32_to_cpu(from->hdr.nvalid); + to->nused = be32_to_cpu(from->hdr.nused); + } else { + struct xfs_dir3_free_hdr *hdr3 = (struct xfs_dir3_free_hdr *)from; + + to->magic = be32_to_cpu(hdr3->hdr.magic); + to->firstdb = be32_to_cpu(hdr3->firstdb); + to->nvalid = be32_to_cpu(hdr3->nvalid); + to->nused = be32_to_cpu(hdr3->nused); + } + + ASSERT(to->magic == XFS_DIR2_FREE_MAGIC || + to->magic == XFS_DIR3_FREE_MAGIC); +} + +static void +xfs_dir3_free_hdr_to_disk( + struct xfs_dir2_free *to, + struct xfs_dir3_icfree_hdr *from) +{ + ASSERT(from->magic == XFS_DIR2_FREE_MAGIC || + from->magic == XFS_DIR3_FREE_MAGIC); + + if (from->magic == XFS_DIR2_FREE_MAGIC) { + to->hdr.magic = cpu_to_be32(from->magic); + to->hdr.firstdb = cpu_to_be32(from->firstdb); + to->hdr.nvalid = cpu_to_be32(from->nvalid); + to->hdr.nused = cpu_to_be32(from->nused); + } else { + struct xfs_dir3_free_hdr *hdr3 = (struct xfs_dir3_free_hdr *)to; + + hdr3->hdr.magic = cpu_to_be32(from->magic); + hdr3->firstdb = cpu_to_be32(from->firstdb); + hdr3->nvalid = cpu_to_be32(from->nvalid); + hdr3->nused = cpu_to_be32(from->nused); + } +} + +static int +xfs_dir3_free_get_buf( + struct xfs_trans *tp, + struct xfs_inode *dp, + xfs_dir2_db_t fbno, + struct xfs_buf **bpp) +{ + struct xfs_mount *mp = dp->i_mount; + struct xfs_buf *bp; + int error; + struct xfs_dir3_icfree_hdr hdr; + + error = xfs_da_get_buf(tp, dp, xfs_dir2_db_to_da(mp, fbno), + -1, &bp, XFS_DATA_FORK); + if (error) + return error; + + bp->b_ops = &xfs_dir3_free_buf_ops;; + + /* + * Initialize the new block to be empty, and remember + * its first slot as our empty slot. + */ + hdr.magic = XFS_DIR2_FREE_MAGIC; + hdr.firstdb = 0; + hdr.nused = 0; + hdr.nvalid = 0; + if (xfs_sb_version_hascrc(&mp->m_sb)) { + struct xfs_dir3_free_hdr *hdr3 = bp->b_addr; + + hdr.magic = XFS_DIR3_FREE_MAGIC; + hdr3->hdr.blkno = cpu_to_be64(bp->b_bn); + hdr3->hdr.owner = cpu_to_be64(dp->i_ino); + uuid_copy(&hdr3->hdr.uuid, &mp->m_sb.sb_uuid); + + } + xfs_dir3_free_hdr_to_disk(bp->b_addr, &hdr); + *bpp = bp; + return 0; } /* @@ -134,13 +259,16 @@ xfs_dir2_free_log_bests( int last) /* last entry to log */ { xfs_dir2_free_t *free; /* freespace structure */ + __be16 *bests; free = bp->b_addr; - ASSERT(free->hdr.magic == cpu_to_be32(XFS_DIR2_FREE_MAGIC)); + bests = xfs_dir3_free_bests_p(tp->t_mountp, free); + ASSERT(free->hdr.magic == cpu_to_be32(XFS_DIR2_FREE_MAGIC) || + free->hdr.magic == cpu_to_be32(XFS_DIR3_FREE_MAGIC)); xfs_trans_log_buf(tp, bp, - (uint)((char *)&free->bests[first] - (char *)free), - (uint)((char *)&free->bests[last] - (char *)free + - sizeof(free->bests[0]) - 1)); + (uint)((char *)&bests[first] - (char *)free), + (uint)((char *)&bests[last] - (char *)free + + sizeof(bests[0]) - 1)); } /* @@ -154,9 +282,9 @@ xfs_dir2_free_log_header( xfs_dir2_free_t *free; /* freespace structure */ free = bp->b_addr; - ASSERT(free->hdr.magic == cpu_to_be32(XFS_DIR2_FREE_MAGIC)); - xfs_trans_log_buf(tp, bp, (uint)((char *)&free->hdr - (char *)free), - (uint)(sizeof(xfs_dir2_free_hdr_t) - 1)); + ASSERT(free->hdr.magic == cpu_to_be32(XFS_DIR2_FREE_MAGIC) || + free->hdr.magic == cpu_to_be32(XFS_DIR3_FREE_MAGIC)); + xfs_trans_log_buf(tp, bp, 0, xfs_dir3_free_hdr_size(tp->t_mountp) - 1); } /* @@ -183,6 +311,7 @@ xfs_dir2_leaf_to_node( xfs_dir2_data_off_t off; /* freespace entry value */ __be16 *to; /* pointer to freespace entry */ xfs_trans_t *tp; /* transaction pointer */ + struct xfs_dir3_icfree_hdr freehdr; trace_xfs_dir2_leaf_to_node(args); @@ -199,43 +328,43 @@ xfs_dir2_leaf_to_node( /* * Get the buffer for the new freespace block. */ - error = xfs_da_get_buf(tp, dp, xfs_dir2_db_to_da(mp, fdb), -1, &fbp, - XFS_DATA_FORK); + error = xfs_dir3_free_get_buf(tp, dp, fdb, &fbp); if (error) return error; - fbp->b_ops = &xfs_dir2_free_buf_ops; free = fbp->b_addr; + xfs_dir3_free_hdr_from_disk(&freehdr, free); leaf = lbp->b_addr; ltp = xfs_dir2_leaf_tail_p(mp, leaf); - /* - * Initialize the freespace block header. - */ - free->hdr.magic = cpu_to_be32(XFS_DIR2_FREE_MAGIC); - free->hdr.firstdb = 0; - ASSERT(be32_to_cpu(ltp->bestcount) <= (uint)dp->i_d.di_size / mp->m_dirblksize); - free->hdr.nvalid = ltp->bestcount; + ASSERT(be32_to_cpu(ltp->bestcount) <= + (uint)dp->i_d.di_size / mp->m_dirblksize); + /* * Copy freespace entries from the leaf block to the new block. * Count active entries. */ - for (i = n = 0, from = xfs_dir2_leaf_bests_p(ltp), to = free->bests; - i < be32_to_cpu(ltp->bestcount); i++, from++, to++) { + from = xfs_dir2_leaf_bests_p(ltp); + to = xfs_dir3_free_bests_p(mp, free); + for (i = n = 0; i < be32_to_cpu(ltp->bestcount); i++, from++, to++) { if ((off = be16_to_cpu(*from)) != NULLDATAOFF) n++; *to = cpu_to_be16(off); } - free->hdr.nused = cpu_to_be32(n); - - lbp->b_ops = &xfs_dir2_leafn_buf_ops; - leaf->hdr.info.magic = cpu_to_be16(XFS_DIR2_LEAFN_MAGIC); /* - * Log everything. + * Now initialize the freespace block header. */ - xfs_dir2_leaf_log_header(tp, lbp); + freehdr.nused = n; + freehdr.nvalid = be32_to_cpu(ltp->bestcount); + + xfs_dir3_free_hdr_to_disk(fbp->b_addr, &freehdr); + xfs_dir2_free_log_bests(tp, fbp, 0, freehdr.nvalid - 1); xfs_dir2_free_log_header(tp, fbp); - xfs_dir2_free_log_bests(tp, fbp, 0, be32_to_cpu(free->hdr.nvalid) - 1); + + /* convert the leaf to a leafnode */ + leaf->hdr.info.magic = cpu_to_be16(XFS_DIR2_LEAFN_MAGIC); + lbp->b_ops = &xfs_dir2_leafn_buf_ops; + xfs_dir2_leaf_log_header(tp, lbp); xfs_dir2_leafn_check(dp, lbp); return 0; } @@ -354,6 +483,23 @@ xfs_dir2_leafn_check( } ASSERT(be16_to_cpu(leaf->hdr.stale) == stale); } + +static void +xfs_dir2_free_hdr_check( + struct xfs_mount *mp, + struct xfs_buf *bp, + xfs_dir2_db_t db) +{ + struct xfs_dir3_icfree_hdr hdr; + + xfs_dir3_free_hdr_from_disk(&hdr, bp->b_addr); + + ASSERT((hdr.firstdb % xfs_dir3_free_max_bests(mp)) == 0); + ASSERT(hdr.firstdb <= db); + ASSERT(db < hdr.firstdb + hdr.nvalid); +} +#else +#define xfs_dir2_free_hdr_check(mp, dp, db) #endif /* DEBUG */ /* @@ -424,7 +570,8 @@ xfs_dir2_leafn_lookup_for_addname( curbp = state->extrablk.bp; curfdb = state->extrablk.blkno; free = curbp->b_addr; - ASSERT(free->hdr.magic == cpu_to_be32(XFS_DIR2_FREE_MAGIC)); + ASSERT(free->hdr.magic == cpu_to_be32(XFS_DIR2_FREE_MAGIC) || + free->hdr.magic == cpu_to_be32(XFS_DIR3_FREE_MAGIC)); } length = xfs_dir2_data_entsize(args->namelen); /* @@ -451,6 +598,8 @@ xfs_dir2_leafn_lookup_for_addname( * in hand, take a look at it. */ if (newdb != curdb) { + __be16 *bests; + curdb = newdb; /* * Convert the data block to the free block @@ -473,13 +622,8 @@ xfs_dir2_leafn_lookup_for_addname( if (error) return error; free = curbp->b_addr; - ASSERT(be32_to_cpu(free->hdr.magic) == - XFS_DIR2_FREE_MAGIC); - ASSERT((be32_to_cpu(free->hdr.firstdb) % - xfs_dir2_free_max_bests(mp)) == 0); - ASSERT(be32_to_cpu(free->hdr.firstdb) <= curdb); - ASSERT(curdb < be32_to_cpu(free->hdr.firstdb) + - be32_to_cpu(free->hdr.nvalid)); + + xfs_dir2_free_hdr_check(mp, curbp, curdb); } /* * Get the index for our entry. @@ -488,8 +632,8 @@ xfs_dir2_leafn_lookup_for_addname( /* * If it has room, return it. */ - if (unlikely(free->bests[fi] == - cpu_to_be16(NULLDATAOFF))) { + bests = xfs_dir3_free_bests_p(mp, free); + if (unlikely(bests[fi] == cpu_to_be16(NULLDATAOFF))) { XFS_ERROR_REPORT("xfs_dir2_leafn_lookup_int", XFS_ERRLEVEL_LOW, mp); if (curfdb != newfdb) @@ -497,7 +641,7 @@ xfs_dir2_leafn_lookup_for_addname( return XFS_ERROR(EFSCORRUPTED); } curfdb = newfdb; - if (be16_to_cpu(free->bests[fi]) >= length) + if (be16_to_cpu(bests[fi]) >= length) goto out; } } @@ -511,6 +655,12 @@ out: state->extrablk.bp = curbp; state->extrablk.index = fi; state->extrablk.blkno = curfdb; + + /* + * Important: this magic number is not in the buffer - it's for + * buffer type information and therefore only the free/data type + * matters here, not whether CRCs are enabled or not. + */ state->extrablk.magic = XFS_DIR2_FREE_MAGIC; } else { state->extravalid = 0; @@ -898,7 +1048,7 @@ xfs_dir2_leafn_rebalance( } static int -xfs_dir2_data_block_free( +xfs_dir3_data_block_free( xfs_da_args_t *args, struct xfs_dir2_data_hdr *hdr, struct xfs_dir2_free *free, @@ -909,59 +1059,68 @@ xfs_dir2_data_block_free( { struct xfs_trans *tp = args->trans; int logfree = 0; + __be16 *bests; + struct xfs_dir3_icfree_hdr freehdr; - if (!hdr) { - /* One less used entry in the free table. */ - be32_add_cpu(&free->hdr.nused, -1); - xfs_dir2_free_log_header(tp, fbp); - /* - * If this was the last entry in the table, we can trim the - * table size back. There might be other entries at the end - * referring to non-existent data blocks, get those too. - */ - if (findex == be32_to_cpu(free->hdr.nvalid) - 1) { - int i; /* free entry index */ + xfs_dir3_free_hdr_from_disk(&freehdr, free); - for (i = findex - 1; i >= 0; i--) { - if (free->bests[i] != cpu_to_be16(NULLDATAOFF)) - break; - } - free->hdr.nvalid = cpu_to_be32(i + 1); - logfree = 0; - } else { - /* Not the last entry, just punch it out. */ - free->bests[findex] = cpu_to_be16(NULLDATAOFF); - logfree = 1; - } + bests = xfs_dir3_free_bests_p(tp->t_mountp, free); + if (hdr) { /* - * If there are no useful entries left in the block, - * get rid of the block if we can. + * Data block is not empty, just set the free entry to the new + * value. */ - if (!free->hdr.nused) { - int error; + bests[findex] = cpu_to_be16(longest); + xfs_dir2_free_log_bests(tp, fbp, findex, findex); + return 0; + } - error = xfs_dir2_shrink_inode(args, fdb, fbp); - if (error == 0) { - fbp = NULL; - logfree = 0; - } else if (error != ENOSPC || args->total != 0) - return error; - /* - * It's possible to get ENOSPC if there is no - * space reservation. In this case some one - * else will eventually get rid of this block. - */ + /* + * One less used entry in the free table. Unused is not converted + * because we only need to know if it zero + */ + freehdr.nused--; + + if (findex == freehdr.nvalid - 1) { + int i; /* free entry index */ + + for (i = findex - 1; i >= 0; i--) { + if (bests[i] != cpu_to_be16(NULLDATAOFF)) + break; } + freehdr.nvalid = i + 1; + logfree = 0; } else { + /* Not the last entry, just punch it out. */ + bests[findex] = cpu_to_be16(NULLDATAOFF); + logfree = 1; + } + + xfs_dir3_free_hdr_to_disk(free, &freehdr); + xfs_dir2_free_log_header(tp, fbp); + + /* + * If there are no useful entries left in the block, get rid of the + * block if we can. + */ + if (!freehdr.nused) { + int error; + + error = xfs_dir2_shrink_inode(args, fdb, fbp); + if (error == 0) { + fbp = NULL; + logfree = 0; + } else if (error != ENOSPC || args->total != 0) + return error; /* - * Data block is not empty, just set the free entry to the new - * value. + * It's possible to get ENOSPC if there is no + * space reservation. In this case some one + * else will eventually get rid of this block. */ - free->bests[findex] = cpu_to_be16(longest); - logfree = 1; } + /* Log the free entry that changed, unless we got rid of it. */ if (logfree) xfs_dir2_free_log_bests(tp, fbp, findex, findex); @@ -1062,10 +1221,15 @@ xfs_dir2_leafn_remove( if (error) return error; free = fbp->b_addr; - ASSERT(free->hdr.magic == cpu_to_be32(XFS_DIR2_FREE_MAGIC)); - ASSERT(be32_to_cpu(free->hdr.firstdb) == - xfs_dir2_free_max_bests(mp) * - (fdb - XFS_DIR2_FREE_FIRSTDB(mp))); +#ifdef DEBUG + { + struct xfs_dir3_icfree_hdr freehdr; + xfs_dir3_free_hdr_from_disk(&freehdr, free); + ASSERT(be32_to_cpu(freehdr.firstdb) == + xfs_dir3_free_max_bests(mp) * + (fdb - XFS_DIR2_FREE_FIRSTDB(mp))); + } +#endif /* * Calculate which entry we need to fix. */ @@ -1096,7 +1260,7 @@ xfs_dir2_leafn_remove( * If we got rid of the data block, we can eliminate that entry * in the free block. */ - error = xfs_dir2_data_block_free(args, hdr, free, + error = xfs_dir3_data_block_free(args, hdr, free, fdb, findex, fbp, longest); if (error) return error; @@ -1447,6 +1611,8 @@ xfs_dir2_node_addname_int( int needscan; /* need to rescan data frees */ __be16 *tagp; /* data entry tag pointer */ xfs_trans_t *tp; /* transaction pointer */ + __be16 *bests; + struct xfs_dir3_icfree_hdr freehdr; dp = args->dp; mp = dp->i_mount; @@ -1464,36 +1630,37 @@ xfs_dir2_node_addname_int( */ ifbno = fblk->blkno; free = fbp->b_addr; - ASSERT(free->hdr.magic == cpu_to_be32(XFS_DIR2_FREE_MAGIC)); findex = fblk->index; + bests = xfs_dir3_free_bests_p(mp, free); + xfs_dir3_free_hdr_from_disk(&freehdr, free); + /* * This means the free entry showed that the data block had * space for our entry, so we remembered it. * Use that data block. */ if (findex >= 0) { - ASSERT(findex < be32_to_cpu(free->hdr.nvalid)); - ASSERT(be16_to_cpu(free->bests[findex]) != NULLDATAOFF); - ASSERT(be16_to_cpu(free->bests[findex]) >= length); - dbno = be32_to_cpu(free->hdr.firstdb) + findex; - } - /* - * The data block looked at didn't have enough room. - * We'll start at the beginning of the freespace entries. - */ - else { + ASSERT(findex < freehdr.nvalid); + ASSERT(be16_to_cpu(bests[findex]) != NULLDATAOFF); + ASSERT(be16_to_cpu(bests[findex]) >= length); + dbno = freehdr.firstdb + findex; + } else { + /* + * The data block looked at didn't have enough room. + * We'll start at the beginning of the freespace entries. + */ dbno = -1; findex = 0; } - } - /* - * Didn't come in with a freespace block, so don't have a data block. - */ - else { + } else { + /* + * Didn't come in with a freespace block, so no data block. + */ ifbno = dbno = -1; fbp = NULL; findex = 0; } + /* * If we don't have a data block yet, we're going to scan the * freespace blocks looking for one. Figure out what the @@ -1547,20 +1714,26 @@ xfs_dir2_node_addname_int( if (!fbp) continue; free = fbp->b_addr; - ASSERT(free->hdr.magic == cpu_to_be32(XFS_DIR2_FREE_MAGIC)); findex = 0; } /* * Look at the current free entry. Is it good enough? + * + * The bests initialisation should be wher eteh bufer is read in + * the above branch. But gcc is too stupid to realise that bests + * iand the freehdr are actually initialised if they are placed + * there, so we have to do it here to avoid warnings. Blech. */ - if (be16_to_cpu(free->bests[findex]) != NULLDATAOFF && - be16_to_cpu(free->bests[findex]) >= length) - dbno = be32_to_cpu(free->hdr.firstdb) + findex; + bests = xfs_dir3_free_bests_p(mp, free); + xfs_dir3_free_hdr_from_disk(&freehdr, free); + if (be16_to_cpu(bests[findex]) != NULLDATAOFF && + be16_to_cpu(bests[findex]) >= length) + dbno = freehdr.firstdb + findex; else { /* * Are we done with the freeblock? */ - if (++findex == be32_to_cpu(free->hdr.nvalid)) { + if (++findex == freehdr.nvalid) { /* * Drop the block. */ @@ -1614,11 +1787,11 @@ xfs_dir2_node_addname_int( * If there wasn't a freespace block, the read will * return a NULL fbp. Allocate and initialize a new one. */ - if( fbp == NULL ) { - if ((error = xfs_dir2_grow_inode(args, XFS_DIR2_FREE_SPACE, - &fbno))) { + if(!fbp) { + error = xfs_dir2_grow_inode(args, XFS_DIR2_FREE_SPACE, + &fbno); + if (error) return error; - } if (unlikely(xfs_dir2_db_to_fdb(mp, dbno) != fbno)) { xfs_alert(mp, @@ -1646,27 +1819,24 @@ xfs_dir2_node_addname_int( /* * Get a buffer for the new block. */ - error = xfs_da_get_buf(tp, dp, - xfs_dir2_db_to_da(mp, fbno), - -1, &fbp, XFS_DATA_FORK); + error = xfs_dir3_free_get_buf(tp, dp, fbno, &fbp); if (error) return error; - fbp->b_ops = &xfs_dir2_free_buf_ops; + free = fbp->b_addr; + bests = xfs_dir3_free_bests_p(mp, free); + xfs_dir3_free_hdr_from_disk(&freehdr, free); /* - * Initialize the new block to be empty, and remember - * its first slot as our empty slot. + * Remember the first slot as our empty slot. */ - free = fbp->b_addr; - free->hdr.magic = cpu_to_be32(XFS_DIR2_FREE_MAGIC); - free->hdr.firstdb = cpu_to_be32( - (fbno - XFS_DIR2_FREE_FIRSTDB(mp)) * - xfs_dir2_free_max_bests(mp)); + freehdr.firstdb = (fbno - XFS_DIR2_FREE_FIRSTDB(mp)) * + xfs_dir3_free_max_bests(mp); free->hdr.nvalid = 0; free->hdr.nused = 0; } else { free = fbp->b_addr; - ASSERT(free->hdr.magic == cpu_to_be32(XFS_DIR2_FREE_MAGIC)); + bests = xfs_dir3_free_bests_p(mp, free); + xfs_dir3_free_hdr_from_disk(&freehdr, free); } /* @@ -1677,20 +1847,21 @@ xfs_dir2_node_addname_int( * If it's after the end of the current entries in the * freespace block, extend that table. */ - if (findex >= be32_to_cpu(free->hdr.nvalid)) { - ASSERT(findex < xfs_dir2_free_max_bests(mp)); - free->hdr.nvalid = cpu_to_be32(findex + 1); + if (findex >= freehdr.nvalid) { + ASSERT(findex < xfs_dir3_free_max_bests(mp)); + freehdr.nvalid = findex + 1; /* * Tag new entry so nused will go up. */ - free->bests[findex] = cpu_to_be16(NULLDATAOFF); + bests[findex] = cpu_to_be16(NULLDATAOFF); } /* * If this entry was for an empty data block * (this should always be true) then update the header. */ - if (free->bests[findex] == cpu_to_be16(NULLDATAOFF)) { - be32_add_cpu(&free->hdr.nused, 1); + if (bests[findex] == cpu_to_be16(NULLDATAOFF)) { + freehdr.nused++; + xfs_dir3_free_hdr_to_disk(fbp->b_addr, &freehdr); xfs_dir2_free_log_header(tp, fbp); } /* @@ -1699,7 +1870,7 @@ xfs_dir2_node_addname_int( * change again. */ hdr = dbp->b_addr; - free->bests[findex] = hdr->bestfree[0].length; + bests[findex] = hdr->bestfree[0].length; logfree = 1; } /* @@ -1758,8 +1929,9 @@ xfs_dir2_node_addname_int( /* * If the freespace entry is now wrong, update it. */ - if (be16_to_cpu(free->bests[findex]) != be16_to_cpu(hdr->bestfree[0].length)) { - free->bests[findex] = hdr->bestfree[0].length; + bests = xfs_dir3_free_bests_p(mp, free); /* gcc is so stupid */ + if (be16_to_cpu(bests[findex]) != be16_to_cpu(hdr->bestfree[0].length)) { + bests[findex] = hdr->bestfree[0].length; logfree = 1; } /* @@ -1995,6 +2167,7 @@ xfs_dir2_node_trim_free( xfs_dir2_free_t *free; /* freespace structure */ xfs_mount_t *mp; /* filesystem mount point */ xfs_trans_t *tp; /* transaction pointer */ + struct xfs_dir3_icfree_hdr freehdr; dp = args->dp; mp = dp->i_mount; @@ -2012,11 +2185,12 @@ xfs_dir2_node_trim_free( if (!bp) return 0; free = bp->b_addr; - ASSERT(free->hdr.magic == cpu_to_be32(XFS_DIR2_FREE_MAGIC)); + xfs_dir3_free_hdr_from_disk(&freehdr, free); + /* * If there are used entries, there's nothing to do. */ - if (be32_to_cpu(free->hdr.nused) > 0) { + if (freehdr.nused > 0) { xfs_trans_brelse(tp, bp); *rvalp = 0; return 0; -- 1.7.10.4 From dave@fromorbit.com Tue Mar 12 07:31:24 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id DF4E17FA2 for ; Tue, 12 Mar 2013 07:31:24 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay1.corp.sgi.com (Postfix) with ESMTP id BDBD48F8035 for ; Tue, 12 Mar 2013 05:31:24 -0700 (PDT) X-ASG-Debug-ID: 1363091470-04cbb07dbe487eb0004-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id rVkaiXc98KbgKdvc for ; Tue, 12 Mar 2013 05:31:20 -0700 (PDT) X-Barracuda-Envelope-From: dave@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AhAKAKEfP1F5LKiV/2dsb2JhbAA7CMRdAwGBSRd0gigBAQUaAQwvFh0IGBgZOQMbGYgSsAKQH41BFwYIJnYGFoM2A6dKgx4ogS4BAQIcBg Received: from ppp121-44-168-149.lns20.syd7.internode.on.net (HELO dastard) ([121.44.168.149]) by ipmail05.adl6.internode.on.net with ESMTP; 12 Mar 2013 23:01:19 +1030 Received: from disappointment ([192.168.1.1]) by dastard with esmtp (Exim 4.76) (envelope-from ) id 1UFOMQ-0001S7-D0 for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:31:18 +1100 Received: from dave by disappointment with local (Exim 4.80) (envelope-from ) id 1UFOM6-0002MK-8k for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:30:58 +1100 From: Dave Chinner To: xfs@oss.sgi.com Subject: [PATCH 10/21] xfs: add CRC checks to remote symlinks Date: Tue, 12 Mar 2013 23:30:43 +1100 X-ASG-Orig-Subj: [PATCH 10/21] xfs: add CRC checks to remote symlinks Message-Id: <1363091454-8852-11-git-send-email-david@fromorbit.com> X-Mailer: git-send-email 1.7.10.4 In-Reply-To: <1363091454-8852-1-git-send-email-david@fromorbit.com> References: <1363091454-8852-1-git-send-email-david@fromorbit.com> X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1363091477 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124988 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- From: Dave Chinner Add a header to the remote symlink block, containing location and owner information, as well as CRCs and LSN fields. This requires verifiers to be added to the remote symlink buffers for CRC enabled filesystems. This also fixes a bug reading multiple block symlinks, where the second block overwrites the first block when copying out the link name. Signed-off-by: Dave Chinner --- fs/xfs/Makefile | 5 +- fs/xfs/xfs_bmap.c | 21 +- fs/xfs/xfs_buf_item.h | 4 +- fs/xfs/xfs_log_recover.c | 9 + fs/xfs/xfs_symlink.c | 719 ++++++++++++++++++++++++++++++++++++++++++++++ fs/xfs/xfs_symlink.h | 53 ++++ fs/xfs/xfs_vnodeops.c | 480 +------------------------------ 7 files changed, 797 insertions(+), 494 deletions(-) create mode 100644 fs/xfs/xfs_symlink.c create mode 100644 fs/xfs/xfs_symlink.h diff --git a/fs/xfs/Makefile b/fs/xfs/Makefile index d02201d..062f25c 100644 --- a/fs/xfs/Makefile +++ b/fs/xfs/Makefile @@ -45,11 +45,11 @@ xfs-y += xfs_aops.o \ xfs_itable.o \ xfs_message.o \ xfs_mru_cache.o \ - xfs_super.o \ - xfs_xattr.o \ xfs_rename.o \ + xfs_super.o \ xfs_utils.o \ xfs_vnodeops.o \ + xfs_xattr.o \ kmem.o \ uuid.o @@ -73,6 +73,7 @@ xfs-y += xfs_alloc.o \ xfs_inode.o \ xfs_log_recover.o \ xfs_mount.o \ + xfs_symlink.o \ xfs_trans.o # low-level transaction/log code diff --git a/fs/xfs/xfs_bmap.c b/fs/xfs/xfs_bmap.c index 0531cd3..0fcb7f4 100644 --- a/fs/xfs/xfs_bmap.c +++ b/fs/xfs/xfs_bmap.c @@ -47,6 +47,7 @@ #include "xfs_filestream.h" #include "xfs_vnodeops.h" #include "xfs_trace.h" +#include "xfs_symlink.h" kmem_zone_t *xfs_bmap_free_item_zone; @@ -1321,9 +1322,10 @@ xfs_bmap_add_attrfork_extents( } /* - * Block initialisation functions for local to extent format conversion. - * As these get more complex, they will be moved to the relevant files, - * but for now they are too simple to worry about. + * Block initialisation function for local to extent format conversion. + * + * This shouldn't actually be called by anyone, so make sure debug kernels cause + * a noticable failure. */ STATIC void xfs_bmap_local_to_extents_init_fn( @@ -1332,23 +1334,12 @@ xfs_bmap_local_to_extents_init_fn( struct xfs_inode *ip, struct xfs_ifork *ifp) { + ASSERT(0); bp->b_ops = &xfs_bmbt_buf_ops; memcpy(bp->b_addr, ifp->if_u1.if_data, ifp->if_bytes); xfs_trans_buf_set_type(tp, bp, XFS_BLF_BTREE_BUF); } -STATIC void -xfs_symlink_local_to_remote( - struct xfs_trans *tp, - struct xfs_buf *bp, - struct xfs_inode *ip, - struct xfs_ifork *ifp) -{ - /* remote symlink blocks are not verifiable until CRCs come along */ - bp->b_ops = NULL; - memcpy(bp->b_addr, ifp->if_u1.if_data, ifp->if_bytes); -} - /* * Called from xfs_bmap_add_attrfork to handle local format files. Each * different data fork content type needs a different callout to do the diff --git a/fs/xfs/xfs_buf_item.h b/fs/xfs/xfs_buf_item.h index abae8c8..09cab4e 100644 --- a/fs/xfs/xfs_buf_item.h +++ b/fs/xfs/xfs_buf_item.h @@ -49,6 +49,7 @@ extern kmem_zone_t *xfs_buf_item_zone; #define XFS_BLF_AGFL_BUF (1<<7) #define XFS_BLF_AGI_BUF (1<<8) #define XFS_BLF_DINO_BUF (1<<9) +#define XFS_BLF_SYMLINK_BUF (1<<10) #define XFS_BLF_TYPE_MASK \ (XFS_BLF_UDQUOT_BUF | \ @@ -58,7 +59,8 @@ extern kmem_zone_t *xfs_buf_item_zone; XFS_BLF_AGF_BUF | \ XFS_BLF_AGFL_BUF | \ XFS_BLF_AGI_BUF | \ - XFS_BLF_DINO_BUF) + XFS_BLF_DINO_BUF | \ + XFS_BLF_SYMLINK_BUF) #define XFS_BLF_CHUNK 128 #define XFS_BLF_SHIFT 7 diff --git a/fs/xfs/xfs_log_recover.c b/fs/xfs/xfs_log_recover.c index 6d08eaa..352d794 100644 --- a/fs/xfs/xfs_log_recover.c +++ b/fs/xfs/xfs_log_recover.c @@ -45,6 +45,7 @@ #include "xfs_cksum.h" #include "xfs_trace.h" #include "xfs_icache.h" +#include "xfs_symlink.h" STATIC int xlog_find_zeroed( @@ -2005,6 +2006,14 @@ xlog_recover_do_reg_buffer( } bp->b_ops = &xfs_inode_buf_ops; break; + case XFS_BLF_SYMLINK_BUF: + if (*(__be32 *)bp->b_addr != cpu_to_be32(XFS_SYMLINK_MAGIC)) { + xfs_warn(mp, "Bad symlink block magic!"); + ASSERT(0); + break; + } + bp->b_ops = &xfs_symlink_buf_ops; + break; default: break; } diff --git a/fs/xfs/xfs_symlink.c b/fs/xfs/xfs_symlink.c new file mode 100644 index 0000000..33e8f13 --- /dev/null +++ b/fs/xfs/xfs_symlink.c @@ -0,0 +1,719 @@ +/* + * Copyright (c) 2000-2006 Silicon Graphics, Inc. + * Copyright (c) 2012-2013 Red Hat, Inc. + * All rights reserved. + */ + +#include "xfs.h" +#include "xfs_fs.h" +#include "xfs_types.h" +#include "xfs_bit.h" +#include "xfs_log.h" +#include "xfs_trans.h" +#include "xfs_sb.h" +#include "xfs_ag.h" +#include "xfs_dir2.h" +#include "xfs_mount.h" +#include "xfs_da_btree.h" +#include "xfs_bmap_btree.h" +#include "xfs_ialloc_btree.h" +#include "xfs_dinode.h" +#include "xfs_inode.h" +#include "xfs_inode_item.h" +#include "xfs_itable.h" +#include "xfs_ialloc.h" +#include "xfs_alloc.h" +#include "xfs_bmap.h" +#include "xfs_error.h" +#include "xfs_quota.h" +#include "xfs_utils.h" +#include "xfs_trans_space.h" +#include "xfs_log_priv.h" +#include "xfs_trace.h" +#include "xfs_symlink.h" +#include "xfs_cksum.h" +#include "xfs_buf_item.h" + + +/* + * Each contiguous block has a header, so it is not just a simple pathlen + * to FSB conversion. + */ +int +xfs_symlink_blocks( + struct xfs_mount *mp, + int pathlen) +{ + int fsblocks = 0; + int len = pathlen; + + do { + fsblocks++; + len -= XFS_SYMLINK_BUF_SPACE(mp, mp->m_sb.sb_blocksize); + } while (len > 0); + + ASSERT(fsblocks <= XFS_SYMLINK_MAPS); + return fsblocks; +} + +static int +xfs_symlink_hdr_set( + struct xfs_mount *mp, + xfs_ino_t ino, + uint32_t offset, + uint32_t size, + struct xfs_buf *bp) +{ + struct xfs_dsymlink_hdr *dsl = bp->b_addr; + + if (!xfs_sb_version_hascrc(&mp->m_sb)) + return 0; + + dsl->sl_magic = cpu_to_be32(XFS_SYMLINK_MAGIC); + dsl->sl_offset = cpu_to_be32(offset); + dsl->sl_bytes = cpu_to_be32(size); + uuid_copy(&dsl->sl_uuid, &mp->m_sb.sb_uuid); + dsl->sl_owner = cpu_to_be64(ino); + dsl->sl_blkno = cpu_to_be64(bp->b_bn); + bp->b_ops = &xfs_symlink_buf_ops; + + return sizeof(struct xfs_dsymlink_hdr); +} + +/* + * Checking of the symlink header is split into two parts. the verifier does + * CRC, location and bounds checking, the unpacking function checks the path + * parameters and owner. + */ +bool +xfs_symlink_hdr_ok( + struct xfs_mount *mp, + xfs_ino_t ino, + uint32_t offset, + uint32_t size, + struct xfs_buf *bp) +{ + struct xfs_dsymlink_hdr *dsl = bp->b_addr; + + if (offset != be32_to_cpu(dsl->sl_offset)) + return false; + if (size != be32_to_cpu(dsl->sl_bytes)) + return false; + if (ino != be64_to_cpu(dsl->sl_owner)) + return false; + + /* ok */ + return true; + +} + +static bool +xfs_symlink_verify( + struct xfs_buf *bp) +{ + struct xfs_mount *mp = bp->b_target->bt_mount; + struct xfs_dsymlink_hdr *dsl = bp->b_addr; + + if (!xfs_sb_version_hascrc(&mp->m_sb)) + return false; + if (dsl->sl_magic != cpu_to_be32(XFS_SYMLINK_MAGIC)) + return false; + if (!uuid_equal(&dsl->sl_uuid, &mp->m_sb.sb_uuid)) + return false; + if (bp->b_bn != be64_to_cpu(dsl->sl_blkno)) + return false; + if (be32_to_cpu(dsl->sl_offset) + + be32_to_cpu(dsl->sl_bytes) >= MAXPATHLEN) + return false; + if (dsl->sl_owner == 0) + return false; + + return true; +} + +static void +xfs_symlink_read_verify( + struct xfs_buf *bp) +{ + struct xfs_mount *mp = bp->b_target->bt_mount; + + /* no verification of non-crc buffers */ + if (!xfs_sb_version_hascrc(&mp->m_sb)) + return; + + if (!xfs_verify_cksum(bp->b_addr, BBTOB(bp->b_length), + offsetof(struct xfs_dsymlink_hdr, sl_crc)) || + !xfs_symlink_verify(bp)) { + XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, mp, bp->b_addr); + xfs_buf_ioerror(bp, EFSCORRUPTED); + } +} + +static void +xfs_symlink_write_verify( + struct xfs_buf *bp) +{ + struct xfs_mount *mp = bp->b_target->bt_mount; + struct xfs_buf_log_item *bip = bp->b_fspriv; + + /* no verification of non-crc buffers */ + if (!xfs_sb_version_hascrc(&mp->m_sb)) + return; + + if (!xfs_symlink_verify(bp)) { + XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, mp, bp->b_addr); + xfs_buf_ioerror(bp, EFSCORRUPTED); + return; + } + + if (bip) { + struct xfs_dsymlink_hdr *dsl = bp->b_addr; + dsl->sl_lsn = cpu_to_be64(bip->bli_item.li_lsn); + } + xfs_update_cksum(bp->b_addr, BBTOB(bp->b_length), + offsetof(struct xfs_dsymlink_hdr, sl_crc)); +} + +const struct xfs_buf_ops xfs_symlink_buf_ops = { + .verify_read = xfs_symlink_read_verify, + .verify_write = xfs_symlink_write_verify, +}; + +void +xfs_symlink_local_to_remote( + struct xfs_trans *tp, + struct xfs_buf *bp, + struct xfs_inode *ip, + struct xfs_ifork *ifp) +{ + struct xfs_mount *mp = ip->i_mount; + char *buf; + + if (!xfs_sb_version_hascrc(&mp->m_sb)) { + bp->b_ops = NULL; + memcpy(bp->b_addr, ifp->if_u1.if_data, ifp->if_bytes); + return; + } + + /* + * As this symlink fits in an inode literal area, it must also fit in + * the smallest buffer the filesystem supports. + */ + ASSERT(BBTOB(bp->b_length) >= + ifp->if_bytes + sizeof(struct xfs_dsymlink_hdr)); + + bp->b_ops = &xfs_symlink_buf_ops; + + buf = bp->b_addr; + buf += xfs_symlink_hdr_set(mp, ip->i_ino, 0, ifp->if_bytes, bp); + memcpy(buf, ifp->if_u1.if_data, ifp->if_bytes); +} + +/* ----- Kernel only functions below ----- */ +STATIC int +xfs_readlink_bmap( + struct xfs_inode *ip, + char *link) +{ + struct xfs_mount *mp = ip->i_mount; + struct xfs_bmbt_irec mval[XFS_SYMLINK_MAPS]; + struct xfs_buf *bp; + xfs_daddr_t d; + char *cur_chunk; + int pathlen = ip->i_d.di_size; + int nmaps = XFS_SYMLINK_MAPS; + int byte_cnt; + int n; + int error = 0; + int fsblocks = 0; + int offset; + + fsblocks = xfs_symlink_blocks(mp, pathlen); + error = xfs_bmapi_read(ip, 0, fsblocks, mval, &nmaps, 0); + if (error) + goto out; + + offset = 0; + for (n = 0; n < nmaps; n++) { + d = XFS_FSB_TO_DADDR(mp, mval[n].br_startblock); + byte_cnt = XFS_FSB_TO_B(mp, mval[n].br_blockcount); + + bp = xfs_buf_read(mp->m_ddev_targp, d, BTOBB(byte_cnt), 0, + &xfs_symlink_buf_ops); + if (!bp) + return XFS_ERROR(ENOMEM); + error = bp->b_error; + if (error) { + xfs_buf_ioerror_alert(bp, __func__); + xfs_buf_relse(bp); + goto out; + } + byte_cnt = XFS_SYMLINK_BUF_SPACE(mp, byte_cnt); + if (pathlen < byte_cnt) + byte_cnt = pathlen; + + cur_chunk = bp->b_addr; + if (xfs_sb_version_hascrc(&mp->m_sb)) { + if (!xfs_symlink_hdr_ok(mp, ip->i_ino, offset, + byte_cnt, bp)) { + error = EFSCORRUPTED; + xfs_alert(mp, +"symlink header does not match required off/len/owner (0x%x/Ox%x,0x%llx)", + offset, byte_cnt, ip->i_ino); + xfs_buf_relse(bp); + goto out; + + } + + cur_chunk += sizeof(struct xfs_dsymlink_hdr); + } + + memcpy(link + offset, bp->b_addr, byte_cnt); + + pathlen -= byte_cnt; + offset += byte_cnt; + + xfs_buf_relse(bp); + } + ASSERT(pathlen == 0); + + link[ip->i_d.di_size] = '\0'; + error = 0; + + out: + return error; +} + +int +xfs_readlink( + struct xfs_inode *ip, + char *link) +{ + struct xfs_mount *mp = ip->i_mount; + xfs_fsize_t pathlen; + int error = 0; + + trace_xfs_readlink(ip); + + if (XFS_FORCED_SHUTDOWN(mp)) + return XFS_ERROR(EIO); + + xfs_ilock(ip, XFS_ILOCK_SHARED); + + pathlen = ip->i_d.di_size; + if (!pathlen) + goto out; + + if (pathlen < 0 || pathlen > MAXPATHLEN) { + xfs_alert(mp, "%s: inode (%llu) bad symlink length (%lld)", + __func__, (unsigned long long) ip->i_ino, + (long long) pathlen); + ASSERT(0); + error = XFS_ERROR(EFSCORRUPTED); + goto out; + } + + + if (ip->i_df.if_flags & XFS_IFINLINE) { + memcpy(link, ip->i_df.if_u1.if_data, pathlen); + link[pathlen] = '\0'; + } else { + error = xfs_readlink_bmap(ip, link); + } + + out: + xfs_iunlock(ip, XFS_ILOCK_SHARED); + return error; +} + +int +xfs_symlink( + struct xfs_inode *dp, + struct xfs_name *link_name, + const char *target_path, + umode_t mode, + struct xfs_inode **ipp) +{ + struct xfs_mount *mp = dp->i_mount; + struct xfs_trans *tp = NULL; + struct xfs_inode *ip = NULL; + int error = 0; + int pathlen; + struct xfs_bmap_free free_list; + xfs_fsblock_t first_block; + bool unlock_dp_on_error = false; + uint cancel_flags; + int committed; + xfs_fileoff_t first_fsb; + xfs_filblks_t fs_blocks; + int nmaps; + struct xfs_bmbt_irec mval[XFS_SYMLINK_MAPS]; + xfs_daddr_t d; + const char *cur_chunk; + int byte_cnt; + int n; + xfs_buf_t *bp; + prid_t prid; + struct xfs_dquot *udqp, *gdqp; + uint resblks; + + *ipp = NULL; + + trace_xfs_symlink(dp, link_name); + + if (XFS_FORCED_SHUTDOWN(mp)) + return XFS_ERROR(EIO); + + /* + * Check component lengths of the target path name. + */ + pathlen = strlen(target_path); + if (pathlen >= MAXPATHLEN) /* total string too long */ + return XFS_ERROR(ENAMETOOLONG); + + udqp = gdqp = NULL; + if (dp->i_d.di_flags & XFS_DIFLAG_PROJINHERIT) + prid = xfs_get_projid(dp); + else + prid = XFS_PROJID_DEFAULT; + + /* + * Make sure that we have allocated dquot(s) on disk. + */ + error = xfs_qm_vop_dqalloc(dp, current_fsuid(), current_fsgid(), prid, + XFS_QMOPT_QUOTALL | XFS_QMOPT_INHERIT, &udqp, &gdqp); + if (error) + goto std_return; + + tp = xfs_trans_alloc(mp, XFS_TRANS_SYMLINK); + cancel_flags = XFS_TRANS_RELEASE_LOG_RES; + /* + * The symlink will fit into the inode data fork? + * There can't be any attributes so we get the whole variable part. + */ + if (pathlen <= XFS_LITINO(mp, dp->i_d.di_version)) + fs_blocks = 0; + else + fs_blocks = XFS_B_TO_FSB(mp, pathlen); + resblks = XFS_SYMLINK_SPACE_RES(mp, link_name->len, fs_blocks); + error = xfs_trans_reserve(tp, resblks, XFS_SYMLINK_LOG_RES(mp), 0, + XFS_TRANS_PERM_LOG_RES, XFS_SYMLINK_LOG_COUNT); + if (error == ENOSPC && fs_blocks == 0) { + resblks = 0; + error = xfs_trans_reserve(tp, 0, XFS_SYMLINK_LOG_RES(mp), 0, + XFS_TRANS_PERM_LOG_RES, XFS_SYMLINK_LOG_COUNT); + } + if (error) { + cancel_flags = 0; + goto error_return; + } + + xfs_ilock(dp, XFS_ILOCK_EXCL | XFS_ILOCK_PARENT); + unlock_dp_on_error = true; + + /* + * Check whether the directory allows new symlinks or not. + */ + if (dp->i_d.di_flags & XFS_DIFLAG_NOSYMLINKS) { + error = XFS_ERROR(EPERM); + goto error_return; + } + + /* + * Reserve disk quota : blocks and inode. + */ + error = xfs_trans_reserve_quota(tp, mp, udqp, gdqp, resblks, 1, 0); + if (error) + goto error_return; + + /* + * Check for ability to enter directory entry, if no space reserved. + */ + error = xfs_dir_canenter(tp, dp, link_name, resblks); + if (error) + goto error_return; + /* + * Initialize the bmap freelist prior to calling either + * bmapi or the directory create code. + */ + xfs_bmap_init(&free_list, &first_block); + + /* + * Allocate an inode for the symlink. + */ + error = xfs_dir_ialloc(&tp, dp, S_IFLNK | (mode & ~S_IFMT), 1, 0, + prid, resblks > 0, &ip, NULL); + if (error) { + if (error == ENOSPC) + goto error_return; + goto error1; + } + + /* + * An error after we've joined dp to the transaction will result in the + * transaction cancel unlocking dp so don't do it explicitly in the + * error path. + */ + xfs_trans_ijoin(tp, dp, XFS_ILOCK_EXCL); + unlock_dp_on_error = false; + + /* + * Also attach the dquot(s) to it, if applicable. + */ + xfs_qm_vop_create_dqattach(tp, ip, udqp, gdqp); + + if (resblks) + resblks -= XFS_IALLOC_SPACE_RES(mp); + /* + * If the symlink will fit into the inode, write it inline. + */ + if (pathlen <= XFS_IFORK_DSIZE(ip)) { + xfs_idata_realloc(ip, pathlen, XFS_DATA_FORK); + memcpy(ip->i_df.if_u1.if_data, target_path, pathlen); + ip->i_d.di_size = pathlen; + + /* + * The inode was initially created in extent format. + */ + ip->i_df.if_flags &= ~(XFS_IFEXTENTS | XFS_IFBROOT); + ip->i_df.if_flags |= XFS_IFINLINE; + + ip->i_d.di_format = XFS_DINODE_FMT_LOCAL; + xfs_trans_log_inode(tp, ip, XFS_ILOG_DDATA | XFS_ILOG_CORE); + + } else { + int offset; + + first_fsb = 0; + nmaps = XFS_SYMLINK_MAPS; + + error = xfs_bmapi_write(tp, ip, first_fsb, fs_blocks, + XFS_BMAPI_METADATA, &first_block, resblks, + mval, &nmaps, &free_list); + if (error) + goto error2; + + if (resblks) + resblks -= fs_blocks; + ip->i_d.di_size = pathlen; + xfs_trans_log_inode(tp, ip, XFS_ILOG_CORE); + + cur_chunk = target_path; + offset = 0; + for (n = 0; n < nmaps; n++) { + char *buf; + + d = XFS_FSB_TO_DADDR(mp, mval[n].br_startblock); + byte_cnt = XFS_FSB_TO_B(mp, mval[n].br_blockcount); + bp = xfs_trans_get_buf(tp, mp->m_ddev_targp, d, + BTOBB(byte_cnt), 0); + if (!bp) { + error = ENOMEM; + goto error2; + } + bp->b_ops = &xfs_symlink_buf_ops; + + byte_cnt = XFS_SYMLINK_BUF_SPACE(mp, byte_cnt); + if (pathlen < byte_cnt) { + byte_cnt = pathlen; + } + + buf = bp->b_addr; + buf += xfs_symlink_hdr_set(mp, ip->i_ino, offset, + byte_cnt, bp); + + memcpy(buf, cur_chunk, byte_cnt); + + cur_chunk += byte_cnt; + pathlen -= byte_cnt; + offset += byte_cnt; + + xfs_trans_log_buf(tp, bp, 0, (buf + byte_cnt - 1) - + (char *)bp->b_addr); + } + } + + /* + * Create the directory entry for the symlink. + */ + error = xfs_dir_createname(tp, dp, link_name, ip->i_ino, + &first_block, &free_list, resblks); + if (error) + goto error2; + xfs_trans_ichgtime(tp, dp, XFS_ICHGTIME_MOD | XFS_ICHGTIME_CHG); + xfs_trans_log_inode(tp, dp, XFS_ILOG_CORE); + + /* + * If this is a synchronous mount, make sure that the + * symlink transaction goes to disk before returning to + * the user. + */ + if (mp->m_flags & (XFS_MOUNT_WSYNC|XFS_MOUNT_DIRSYNC)) { + xfs_trans_set_sync(tp); + } + + error = xfs_bmap_finish(&tp, &free_list, &committed); + if (error) { + goto error2; + } + error = xfs_trans_commit(tp, XFS_TRANS_RELEASE_LOG_RES); + xfs_qm_dqrele(udqp); + xfs_qm_dqrele(gdqp); + + *ipp = ip; + return 0; + + error2: + IRELE(ip); + error1: + xfs_bmap_cancel(&free_list); + cancel_flags |= XFS_TRANS_ABORT; + error_return: + xfs_trans_cancel(tp, cancel_flags); + xfs_qm_dqrele(udqp); + xfs_qm_dqrele(gdqp); + + if (unlock_dp_on_error) + xfs_iunlock(dp, XFS_ILOCK_EXCL); + std_return: + return error; +} + +/* + * Free a symlink that has blocks associated with it. + */ +int +xfs_inactive_symlink_rmt( + xfs_inode_t *ip, + xfs_trans_t **tpp) +{ + xfs_buf_t *bp; + int committed; + int done; + int error; + xfs_fsblock_t first_block; + xfs_bmap_free_t free_list; + int i; + xfs_mount_t *mp; + xfs_bmbt_irec_t mval[XFS_SYMLINK_MAPS]; + int nmaps; + xfs_trans_t *ntp; + int size; + xfs_trans_t *tp; + + tp = *tpp; + mp = ip->i_mount; + ASSERT(ip->i_d.di_size > XFS_IFORK_DSIZE(ip)); + /* + * We're freeing a symlink that has some + * blocks allocated to it. Free the + * blocks here. We know that we've got + * either 1 or 2 extents and that we can + * free them all in one bunmapi call. + */ + ASSERT(ip->i_d.di_nextents > 0 && ip->i_d.di_nextents <= 2); + + /* + * Lock the inode, fix the size, and join it to the transaction. + * Hold it so in the normal path, we still have it locked for + * the second transaction. In the error paths we need it + * held so the cancel won't rele it, see below. + */ + size = (int)ip->i_d.di_size; + ip->i_d.di_size = 0; + xfs_trans_log_inode(tp, ip, XFS_ILOG_CORE); + /* + * Find the block(s) so we can inval and unmap them. + */ + done = 0; + xfs_bmap_init(&free_list, &first_block); + nmaps = ARRAY_SIZE(mval); + error = xfs_bmapi_read(ip, 0, xfs_symlink_blocks(mp, size), + mval, &nmaps, 0); + if (error) + goto error0; + /* + * Invalidate the block(s). No validation is done. + */ + for (i = 0; i < nmaps; i++) { + bp = xfs_trans_get_buf(tp, mp->m_ddev_targp, + XFS_FSB_TO_DADDR(mp, mval[i].br_startblock), + XFS_FSB_TO_BB(mp, mval[i].br_blockcount), 0); + if (!bp) { + error = ENOMEM; + goto error1; + } + xfs_trans_binval(tp, bp); + } + /* + * Unmap the dead block(s) to the free_list. + */ + if ((error = xfs_bunmapi(tp, ip, 0, size, XFS_BMAPI_METADATA, nmaps, + &first_block, &free_list, &done))) + goto error1; + ASSERT(done); + /* + * Commit the first transaction. This logs the EFI and the inode. + */ + if ((error = xfs_bmap_finish(&tp, &free_list, &committed))) + goto error1; + /* + * The transaction must have been committed, since there were + * actually extents freed by xfs_bunmapi. See xfs_bmap_finish. + * The new tp has the extent freeing and EFDs. + */ + ASSERT(committed); + /* + * The first xact was committed, so add the inode to the new one. + * Mark it dirty so it will be logged and moved forward in the log as + * part of every commit. + */ + xfs_trans_ijoin(tp, ip, 0); + xfs_trans_log_inode(tp, ip, XFS_ILOG_CORE); + /* + * Get a new, empty transaction to return to our caller. + */ + ntp = xfs_trans_dup(tp); + /* + * Commit the transaction containing extent freeing and EFDs. + * If we get an error on the commit here or on the reserve below, + * we need to unlock the inode since the new transaction doesn't + * have the inode attached. + */ + error = xfs_trans_commit(tp, 0); + tp = ntp; + if (error) { + ASSERT(XFS_FORCED_SHUTDOWN(mp)); + goto error0; + } + /* + * transaction commit worked ok so we can drop the extra ticket + * reference that we gained in xfs_trans_dup() + */ + xfs_log_ticket_put(tp->t_ticket); + + /* + * Remove the memory for extent descriptions (just bookkeeping). + */ + if (ip->i_df.if_bytes) + xfs_idata_realloc(ip, -ip->i_df.if_bytes, XFS_DATA_FORK); + ASSERT(ip->i_df.if_bytes == 0); + /* + * Put an itruncate log reservation in the new transaction + * for our caller. + */ + if ((error = xfs_trans_reserve(tp, 0, XFS_ITRUNCATE_LOG_RES(mp), 0, + XFS_TRANS_PERM_LOG_RES, XFS_ITRUNCATE_LOG_COUNT))) { + ASSERT(XFS_FORCED_SHUTDOWN(mp)); + goto error0; + } + + xfs_trans_ijoin(tp, ip, 0); + *tpp = tp; + return 0; + + error1: + xfs_bmap_cancel(&free_list); + error0: + return error; +} diff --git a/fs/xfs/xfs_symlink.h b/fs/xfs/xfs_symlink.h new file mode 100644 index 0000000..be20ae1 --- /dev/null +++ b/fs/xfs/xfs_symlink.h @@ -0,0 +1,53 @@ +/* + * Copyright (c) 2012 Red Hat, Inc. All rights reserved. + */ +#ifndef __XFS_SYMLINK_H +#define __XFS_SYMLINK_H 1 + +struct xfs_mount; +struct xfs_trans; +struct xfs_inode; +struct xfs_buf; +struct xfs_ifork; +struct xfs_name; + +#define XFS_SYMLINK_MAGIC 0x58534c4d /* XSLM */ + +struct xfs_dsymlink_hdr { + __be32 sl_magic; + __be32 sl_offset; + __be32 sl_bytes; + __be32 sl_crc; + uuid_t sl_uuid; + __be64 sl_owner; + __be64 sl_blkno; + __be64 sl_lsn; +}; + +/* + * The maximum pathlen is 1024 bytes. Since the minimum file system + * blocksize is 512 bytes, we can get a max of 3 extents back from + * bmapi when crc headers are taken into account. + */ +#define XFS_SYMLINK_MAPS 3 + +#define XFS_SYMLINK_BUF_SPACE(mp, bufsize) \ + ((bufsize) - (xfs_sb_version_hascrc(&(mp)->m_sb) ? \ + sizeof(struct xfs_dsymlink_hdr) : 0)) + +int xfs_symlink_blocks(struct xfs_mount *mp, int pathlen); + +void xfs_symlink_local_to_remote(struct xfs_trans *tp, struct xfs_buf *bp, + struct xfs_inode *ip, struct xfs_ifork *ifp); + +extern const struct xfs_buf_ops xfs_symlink_buf_ops; + +#ifdef __KERNEL__ + +int xfs_symlink(struct xfs_inode *dp, struct xfs_name *link_name, + const char *target_path, umode_t mode, struct xfs_inode **ipp); +int xfs_readlink(struct xfs_inode *ip, char *link); +int xfs_inactive_symlink_rmt(struct xfs_inode *ip, struct xfs_trans **tpp); + +#endif /* __KERNEL__ */ +#endif /* __XFS_SYMLINK_H */ diff --git a/fs/xfs/xfs_vnodeops.c b/fs/xfs/xfs_vnodeops.c index aa0c066..1034440 100644 --- a/fs/xfs/xfs_vnodeops.c +++ b/fs/xfs/xfs_vnodeops.c @@ -1,5 +1,6 @@ /* * Copyright (c) 2000-2006 Silicon Graphics, Inc. + * Copyright (c) 2012 Red Hat, Inc. * All Rights Reserved. * * This program is free software; you can redistribute it and/or @@ -48,103 +49,10 @@ #include "xfs_vnodeops.h" #include "xfs_trace.h" #include "xfs_icache.h" +#include "xfs_symlink.h" +#include "xfs_cksum.h" +#include "xfs_buf_item.h" -/* - * The maximum pathlen is 1024 bytes. Since the minimum file system - * blocksize is 512 bytes, we can get a max of 2 extents back from - * bmapi. - */ -#define SYMLINK_MAPS 2 - -STATIC int -xfs_readlink_bmap( - xfs_inode_t *ip, - char *link) -{ - xfs_mount_t *mp = ip->i_mount; - int pathlen = ip->i_d.di_size; - int nmaps = SYMLINK_MAPS; - xfs_bmbt_irec_t mval[SYMLINK_MAPS]; - xfs_daddr_t d; - int byte_cnt; - int n; - xfs_buf_t *bp; - int error = 0; - - error = xfs_bmapi_read(ip, 0, XFS_B_TO_FSB(mp, pathlen), mval, &nmaps, - 0); - if (error) - goto out; - - for (n = 0; n < nmaps; n++) { - d = XFS_FSB_TO_DADDR(mp, mval[n].br_startblock); - byte_cnt = XFS_FSB_TO_B(mp, mval[n].br_blockcount); - - bp = xfs_buf_read(mp->m_ddev_targp, d, BTOBB(byte_cnt), 0, NULL); - if (!bp) - return XFS_ERROR(ENOMEM); - error = bp->b_error; - if (error) { - xfs_buf_ioerror_alert(bp, __func__); - xfs_buf_relse(bp); - goto out; - } - if (pathlen < byte_cnt) - byte_cnt = pathlen; - pathlen -= byte_cnt; - - memcpy(link, bp->b_addr, byte_cnt); - xfs_buf_relse(bp); - } - - link[ip->i_d.di_size] = '\0'; - error = 0; - - out: - return error; -} - -int -xfs_readlink( - xfs_inode_t *ip, - char *link) -{ - xfs_mount_t *mp = ip->i_mount; - xfs_fsize_t pathlen; - int error = 0; - - trace_xfs_readlink(ip); - - if (XFS_FORCED_SHUTDOWN(mp)) - return XFS_ERROR(EIO); - - xfs_ilock(ip, XFS_ILOCK_SHARED); - - pathlen = ip->i_d.di_size; - if (!pathlen) - goto out; - - if (pathlen < 0 || pathlen > MAXPATHLEN) { - xfs_alert(mp, "%s: inode (%llu) bad symlink length (%lld)", - __func__, (unsigned long long) ip->i_ino, - (long long) pathlen); - ASSERT(0); - error = XFS_ERROR(EFSCORRUPTED); - goto out; - } - - - if (ip->i_df.if_flags & XFS_IFINLINE) { - memcpy(link, ip->i_df.if_u1.if_data, pathlen); - link[pathlen] = '\0'; - } else { - error = xfs_readlink_bmap(ip, link); - } - - out: - xfs_iunlock(ip, XFS_ILOCK_SHARED); - return error; -} /* * This is called by xfs_inactive to free any blocks beyond eof @@ -249,145 +157,6 @@ xfs_free_eofblocks( return error; } -/* - * Free a symlink that has blocks associated with it. - */ -STATIC int -xfs_inactive_symlink_rmt( - xfs_inode_t *ip, - xfs_trans_t **tpp) -{ - xfs_buf_t *bp; - int committed; - int done; - int error; - xfs_fsblock_t first_block; - xfs_bmap_free_t free_list; - int i; - xfs_mount_t *mp; - xfs_bmbt_irec_t mval[SYMLINK_MAPS]; - int nmaps; - xfs_trans_t *ntp; - int size; - xfs_trans_t *tp; - - tp = *tpp; - mp = ip->i_mount; - ASSERT(ip->i_d.di_size > XFS_IFORK_DSIZE(ip)); - /* - * We're freeing a symlink that has some - * blocks allocated to it. Free the - * blocks here. We know that we've got - * either 1 or 2 extents and that we can - * free them all in one bunmapi call. - */ - ASSERT(ip->i_d.di_nextents > 0 && ip->i_d.di_nextents <= 2); - - /* - * Lock the inode, fix the size, and join it to the transaction. - * Hold it so in the normal path, we still have it locked for - * the second transaction. In the error paths we need it - * held so the cancel won't rele it, see below. - */ - size = (int)ip->i_d.di_size; - ip->i_d.di_size = 0; - xfs_trans_log_inode(tp, ip, XFS_ILOG_CORE); - /* - * Find the block(s) so we can inval and unmap them. - */ - done = 0; - xfs_bmap_init(&free_list, &first_block); - nmaps = ARRAY_SIZE(mval); - error = xfs_bmapi_read(ip, 0, XFS_B_TO_FSB(mp, size), - mval, &nmaps, 0); - if (error) - goto error0; - /* - * Invalidate the block(s). - */ - for (i = 0; i < nmaps; i++) { - bp = xfs_trans_get_buf(tp, mp->m_ddev_targp, - XFS_FSB_TO_DADDR(mp, mval[i].br_startblock), - XFS_FSB_TO_BB(mp, mval[i].br_blockcount), 0); - if (!bp) { - error = ENOMEM; - goto error1; - } - xfs_trans_binval(tp, bp); - } - /* - * Unmap the dead block(s) to the free_list. - */ - if ((error = xfs_bunmapi(tp, ip, 0, size, XFS_BMAPI_METADATA, nmaps, - &first_block, &free_list, &done))) - goto error1; - ASSERT(done); - /* - * Commit the first transaction. This logs the EFI and the inode. - */ - if ((error = xfs_bmap_finish(&tp, &free_list, &committed))) - goto error1; - /* - * The transaction must have been committed, since there were - * actually extents freed by xfs_bunmapi. See xfs_bmap_finish. - * The new tp has the extent freeing and EFDs. - */ - ASSERT(committed); - /* - * The first xact was committed, so add the inode to the new one. - * Mark it dirty so it will be logged and moved forward in the log as - * part of every commit. - */ - xfs_trans_ijoin(tp, ip, 0); - xfs_trans_log_inode(tp, ip, XFS_ILOG_CORE); - /* - * Get a new, empty transaction to return to our caller. - */ - ntp = xfs_trans_dup(tp); - /* - * Commit the transaction containing extent freeing and EFDs. - * If we get an error on the commit here or on the reserve below, - * we need to unlock the inode since the new transaction doesn't - * have the inode attached. - */ - error = xfs_trans_commit(tp, 0); - tp = ntp; - if (error) { - ASSERT(XFS_FORCED_SHUTDOWN(mp)); - goto error0; - } - /* - * transaction commit worked ok so we can drop the extra ticket - * reference that we gained in xfs_trans_dup() - */ - xfs_log_ticket_put(tp->t_ticket); - - /* - * Remove the memory for extent descriptions (just bookkeeping). - */ - if (ip->i_df.if_bytes) - xfs_idata_realloc(ip, -ip->i_df.if_bytes, XFS_DATA_FORK); - ASSERT(ip->i_df.if_bytes == 0); - /* - * Put an itruncate log reservation in the new transaction - * for our caller. - */ - if ((error = xfs_trans_reserve(tp, 0, XFS_ITRUNCATE_LOG_RES(mp), 0, - XFS_TRANS_PERM_LOG_RES, XFS_ITRUNCATE_LOG_COUNT))) { - ASSERT(XFS_FORCED_SHUTDOWN(mp)); - goto error0; - } - - xfs_trans_ijoin(tp, ip, 0); - *tpp = tp; - return 0; - - error1: - xfs_bmap_cancel(&free_list); - error0: - return error; -} - int xfs_release( xfs_inode_t *ip) @@ -1353,247 +1122,6 @@ xfs_link( } int -xfs_symlink( - xfs_inode_t *dp, - struct xfs_name *link_name, - const char *target_path, - umode_t mode, - xfs_inode_t **ipp) -{ - xfs_mount_t *mp = dp->i_mount; - xfs_trans_t *tp; - xfs_inode_t *ip; - int error; - int pathlen; - xfs_bmap_free_t free_list; - xfs_fsblock_t first_block; - bool unlock_dp_on_error = false; - uint cancel_flags; - int committed; - xfs_fileoff_t first_fsb; - xfs_filblks_t fs_blocks; - int nmaps; - xfs_bmbt_irec_t mval[SYMLINK_MAPS]; - xfs_daddr_t d; - const char *cur_chunk; - int byte_cnt; - int n; - xfs_buf_t *bp; - prid_t prid; - struct xfs_dquot *udqp, *gdqp; - uint resblks; - - *ipp = NULL; - error = 0; - ip = NULL; - tp = NULL; - - trace_xfs_symlink(dp, link_name); - - if (XFS_FORCED_SHUTDOWN(mp)) - return XFS_ERROR(EIO); - - /* - * Check component lengths of the target path name. - */ - pathlen = strlen(target_path); - if (pathlen >= MAXPATHLEN) /* total string too long */ - return XFS_ERROR(ENAMETOOLONG); - - udqp = gdqp = NULL; - if (dp->i_d.di_flags & XFS_DIFLAG_PROJINHERIT) - prid = xfs_get_projid(dp); - else - prid = XFS_PROJID_DEFAULT; - - /* - * Make sure that we have allocated dquot(s) on disk. - */ - error = xfs_qm_vop_dqalloc(dp, current_fsuid(), current_fsgid(), prid, - XFS_QMOPT_QUOTALL | XFS_QMOPT_INHERIT, &udqp, &gdqp); - if (error) - goto std_return; - - tp = xfs_trans_alloc(mp, XFS_TRANS_SYMLINK); - cancel_flags = XFS_TRANS_RELEASE_LOG_RES; - /* - * The symlink will fit into the inode data fork? - * There can't be any attributes so we get the whole variable part. - */ - if (pathlen <= XFS_LITINO(mp, dp->i_d.di_version)) - fs_blocks = 0; - else - fs_blocks = XFS_B_TO_FSB(mp, pathlen); - resblks = XFS_SYMLINK_SPACE_RES(mp, link_name->len, fs_blocks); - error = xfs_trans_reserve(tp, resblks, XFS_SYMLINK_LOG_RES(mp), 0, - XFS_TRANS_PERM_LOG_RES, XFS_SYMLINK_LOG_COUNT); - if (error == ENOSPC && fs_blocks == 0) { - resblks = 0; - error = xfs_trans_reserve(tp, 0, XFS_SYMLINK_LOG_RES(mp), 0, - XFS_TRANS_PERM_LOG_RES, XFS_SYMLINK_LOG_COUNT); - } - if (error) { - cancel_flags = 0; - goto error_return; - } - - xfs_ilock(dp, XFS_ILOCK_EXCL | XFS_ILOCK_PARENT); - unlock_dp_on_error = true; - - /* - * Check whether the directory allows new symlinks or not. - */ - if (dp->i_d.di_flags & XFS_DIFLAG_NOSYMLINKS) { - error = XFS_ERROR(EPERM); - goto error_return; - } - - /* - * Reserve disk quota : blocks and inode. - */ - error = xfs_trans_reserve_quota(tp, mp, udqp, gdqp, resblks, 1, 0); - if (error) - goto error_return; - - /* - * Check for ability to enter directory entry, if no space reserved. - */ - error = xfs_dir_canenter(tp, dp, link_name, resblks); - if (error) - goto error_return; - /* - * Initialize the bmap freelist prior to calling either - * bmapi or the directory create code. - */ - xfs_bmap_init(&free_list, &first_block); - - /* - * Allocate an inode for the symlink. - */ - error = xfs_dir_ialloc(&tp, dp, S_IFLNK | (mode & ~S_IFMT), 1, 0, - prid, resblks > 0, &ip, NULL); - if (error) { - if (error == ENOSPC) - goto error_return; - goto error1; - } - - /* - * An error after we've joined dp to the transaction will result in the - * transaction cancel unlocking dp so don't do it explicitly in the - * error path. - */ - xfs_trans_ijoin(tp, dp, XFS_ILOCK_EXCL); - unlock_dp_on_error = false; - - /* - * Also attach the dquot(s) to it, if applicable. - */ - xfs_qm_vop_create_dqattach(tp, ip, udqp, gdqp); - - if (resblks) - resblks -= XFS_IALLOC_SPACE_RES(mp); - /* - * If the symlink will fit into the inode, write it inline. - */ - if (pathlen <= XFS_IFORK_DSIZE(ip)) { - xfs_idata_realloc(ip, pathlen, XFS_DATA_FORK); - memcpy(ip->i_df.if_u1.if_data, target_path, pathlen); - ip->i_d.di_size = pathlen; - - /* - * The inode was initially created in extent format. - */ - ip->i_df.if_flags &= ~(XFS_IFEXTENTS | XFS_IFBROOT); - ip->i_df.if_flags |= XFS_IFINLINE; - - ip->i_d.di_format = XFS_DINODE_FMT_LOCAL; - xfs_trans_log_inode(tp, ip, XFS_ILOG_DDATA | XFS_ILOG_CORE); - - } else { - first_fsb = 0; - nmaps = SYMLINK_MAPS; - - error = xfs_bmapi_write(tp, ip, first_fsb, fs_blocks, - XFS_BMAPI_METADATA, &first_block, resblks, - mval, &nmaps, &free_list); - if (error) - goto error2; - - if (resblks) - resblks -= fs_blocks; - ip->i_d.di_size = pathlen; - xfs_trans_log_inode(tp, ip, XFS_ILOG_CORE); - - cur_chunk = target_path; - for (n = 0; n < nmaps; n++) { - d = XFS_FSB_TO_DADDR(mp, mval[n].br_startblock); - byte_cnt = XFS_FSB_TO_B(mp, mval[n].br_blockcount); - bp = xfs_trans_get_buf(tp, mp->m_ddev_targp, d, - BTOBB(byte_cnt), 0); - if (!bp) { - error = ENOMEM; - goto error2; - } - if (pathlen < byte_cnt) { - byte_cnt = pathlen; - } - pathlen -= byte_cnt; - - memcpy(bp->b_addr, cur_chunk, byte_cnt); - cur_chunk += byte_cnt; - - xfs_trans_log_buf(tp, bp, 0, byte_cnt - 1); - } - } - - /* - * Create the directory entry for the symlink. - */ - error = xfs_dir_createname(tp, dp, link_name, ip->i_ino, - &first_block, &free_list, resblks); - if (error) - goto error2; - xfs_trans_ichgtime(tp, dp, XFS_ICHGTIME_MOD | XFS_ICHGTIME_CHG); - xfs_trans_log_inode(tp, dp, XFS_ILOG_CORE); - - /* - * If this is a synchronous mount, make sure that the - * symlink transaction goes to disk before returning to - * the user. - */ - if (mp->m_flags & (XFS_MOUNT_WSYNC|XFS_MOUNT_DIRSYNC)) { - xfs_trans_set_sync(tp); - } - - error = xfs_bmap_finish(&tp, &free_list, &committed); - if (error) { - goto error2; - } - error = xfs_trans_commit(tp, XFS_TRANS_RELEASE_LOG_RES); - xfs_qm_dqrele(udqp); - xfs_qm_dqrele(gdqp); - - *ipp = ip; - return 0; - - error2: - IRELE(ip); - error1: - xfs_bmap_cancel(&free_list); - cancel_flags |= XFS_TRANS_ABORT; - error_return: - xfs_trans_cancel(tp, cancel_flags); - xfs_qm_dqrele(udqp); - xfs_qm_dqrele(gdqp); - - if (unlock_dp_on_error) - xfs_iunlock(dp, XFS_ILOCK_EXCL); - std_return: - return error; -} - -int xfs_set_dmattrs( xfs_inode_t *ip, u_int evmask, -- 1.7.10.4 From dave@fromorbit.com Tue Mar 12 07:31:26 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 688CF7F9C for ; Tue, 12 Mar 2013 07:31:25 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay2.corp.sgi.com (Postfix) with ESMTP id 199B2304048 for ; Tue, 12 Mar 2013 05:31:25 -0700 (PDT) X-ASG-Debug-ID: 1363091481-04bdf022974cb0d0001-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id kFYGFaHnIelTyIeF for ; Tue, 12 Mar 2013 05:31:21 -0700 (PDT) X-Barracuda-Envelope-From: dave@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: Ag8KAKEfP1F5LKiV/2dsb2JhbABDxF0DAYFJF3SCKAEBBRoNLzMIGDE5AxsZiBKwApAfjgx2g1IDp0qDHig Received: from ppp121-44-168-149.lns20.syd7.internode.on.net (HELO dastard) ([121.44.168.149]) by ipmail05.adl6.internode.on.net with ESMTP; 12 Mar 2013 23:01:19 +1030 Received: from disappointment ([192.168.1.1]) by dastard with esmtp (Exim 4.76) (envelope-from ) id 1UFOML-0001SF-Fr for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:31:13 +1100 Received: from dave by disappointment with local (Exim 4.80) (envelope-from ) id 1UFOMG-0002Md-Cg for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:31:08 +1100 From: Dave Chinner To: xfs@oss.sgi.com Subject: [PATCH 13/21] xfs: add CRC checking to dir2 data blocks Date: Tue, 12 Mar 2013 23:30:46 +1100 X-ASG-Orig-Subj: [PATCH 13/21] xfs: add CRC checking to dir2 data blocks Message-Id: <1363091454-8852-14-git-send-email-david@fromorbit.com> X-Mailer: git-send-email 1.7.10.4 In-Reply-To: <1363091454-8852-1-git-send-email-david@fromorbit.com> References: <1363091454-8852-1-git-send-email-david@fromorbit.com> X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1363091481 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124988 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- From: Dave Chinner This addition follows the same pattern as the dir2 block CRCs. Signed-off-by: Dave Chinner --- fs/xfs/xfs_dir2_block.c | 22 +++++----- fs/xfs/xfs_dir2_data.c | 100 ++++++++++++++++++++++++++++++++-------------- fs/xfs/xfs_dir2_format.h | 21 +++++----- fs/xfs/xfs_dir2_leaf.c | 71 ++++++++++++++++++-------------- fs/xfs/xfs_dir2_node.c | 39 ++++++++++-------- fs/xfs/xfs_dir2_priv.h | 12 +++--- fs/xfs/xfs_file.c | 2 +- 7 files changed, 162 insertions(+), 105 deletions(-) diff --git a/fs/xfs/xfs_dir2_block.c b/fs/xfs/xfs_dir2_block.c index 5189606..de2ae38 100644 --- a/fs/xfs/xfs_dir2_block.c +++ b/fs/xfs/xfs_dir2_block.c @@ -77,7 +77,7 @@ xfs_dir3_block_verify( if (hdr3->magic != be32_to_cpu(XFS_DIR2_BLOCK_MAGIC)) return false; } - if (__xfs_dir2_data_check(NULL, bp)) + if (__xfs_dir3_data_check(NULL, bp)) return false; return true; } @@ -553,7 +553,7 @@ xfs_dir2_block_addname( xfs_dir2_data_log_header(tp, bp); xfs_dir2_block_log_tail(tp, bp); xfs_dir2_data_log_entry(tp, bp, dep); - xfs_dir2_data_check(dp, bp); + xfs_dir3_data_check(dp, bp); return 0; } @@ -596,7 +596,7 @@ xfs_dir2_block_getdents( */ wantoff = xfs_dir2_dataptr_to_off(mp, *offset); hdr = bp->b_addr; - xfs_dir2_data_check(dp, bp); + xfs_dir3_data_check(dp, bp); /* * Set up values for the loop. */ @@ -720,7 +720,7 @@ xfs_dir2_block_lookup( dp = args->dp; mp = dp->i_mount; hdr = bp->b_addr; - xfs_dir2_data_check(dp, bp); + xfs_dir3_data_check(dp, bp); btp = xfs_dir2_block_tail_p(mp, hdr); blp = xfs_dir2_block_leaf_p(btp); /* @@ -771,7 +771,7 @@ xfs_dir2_block_lookup_int( return error; hdr = bp->b_addr; - xfs_dir2_data_check(dp, bp); + xfs_dir3_data_check(dp, bp); btp = xfs_dir2_block_tail_p(mp, hdr); blp = xfs_dir2_block_leaf_p(btp); /* @@ -908,7 +908,7 @@ xfs_dir2_block_removename( xfs_dir2_data_freescan(mp, hdr, &needlog); if (needlog) xfs_dir2_data_log_header(tp, bp); - xfs_dir2_data_check(dp, bp); + xfs_dir3_data_check(dp, bp); /* * See if the size as a shortform is good enough. */ @@ -965,7 +965,7 @@ xfs_dir2_block_replace( */ dep->inumber = cpu_to_be64(args->inumber); xfs_dir2_data_log_entry(args->trans, bp, dep); - xfs_dir2_data_check(dp, bp); + xfs_dir3_data_check(dp, bp); return 0; } @@ -1046,12 +1046,14 @@ xfs_dir2_leaf_to_block( * Read the data block if we don't already have it, give up if it fails. */ if (!dbp) { - error = xfs_dir2_data_read(tp, dp, mp->m_dirdatablk, -1, &dbp); + error = xfs_dir3_data_read(tp, dp, mp->m_dirdatablk, -1, &dbp); if (error) return error; } hdr = dbp->b_addr; - ASSERT(hdr->magic == cpu_to_be32(XFS_DIR2_DATA_MAGIC)); + ASSERT(hdr->magic == cpu_to_be32(XFS_DIR2_DATA_MAGIC) || + hdr->magic == cpu_to_be32(XFS_DIR3_DATA_MAGIC)); + /* * Size of the "leaf" area in the block. */ @@ -1329,6 +1331,6 @@ xfs_dir2_sf_to_block( ASSERT(needscan == 0); xfs_dir2_block_log_leaf(tp, bp, 0, be32_to_cpu(btp->count) - 1); xfs_dir2_block_log_tail(tp, bp); - xfs_dir2_data_check(dp, bp); + xfs_dir3_data_check(dp, bp); return 0; } diff --git a/fs/xfs/xfs_dir2_data.c b/fs/xfs/xfs_dir2_data.c index 8484ec4..86ac9c0 100644 --- a/fs/xfs/xfs_dir2_data.c +++ b/fs/xfs/xfs_dir2_data.c @@ -31,6 +31,8 @@ #include "xfs_dir2_format.h" #include "xfs_dir2_priv.h" #include "xfs_error.h" +#include "xfs_buf_item.h" +#include "xfs_cksum.h" STATIC xfs_dir2_data_free_t * xfs_dir2_data_freefind(xfs_dir2_data_hdr_t *hdr, xfs_dir2_data_unused_t *dup); @@ -41,7 +43,7 @@ xfs_dir2_data_freefind(xfs_dir2_data_hdr_t *hdr, xfs_dir2_data_unused_t *dup); * Return 0 is the buffer is good, otherwise an error. */ int -__xfs_dir2_data_check( +__xfs_dir3_data_check( struct xfs_inode *dp, /* incore inode pointer */ struct xfs_buf *bp) /* data block's buffer */ { @@ -76,6 +78,7 @@ __xfs_dir2_data_check( lep = xfs_dir2_block_leaf_p(btp); endp = (char *)lep; break; + case cpu_to_be32(XFS_DIR3_DATA_MAGIC): case cpu_to_be32(XFS_DIR2_DATA_MAGIC): endp = (char *)hdr + mp->m_dirblksize; break; @@ -189,21 +192,27 @@ __xfs_dir2_data_check( return 0; } -static void -xfs_dir2_data_verify( +static bool +xfs_dir3_data_verify( struct xfs_buf *bp) { struct xfs_mount *mp = bp->b_target->bt_mount; - struct xfs_dir2_data_hdr *hdr = bp->b_addr; - int block_ok = 0; + struct xfs_dir3_blk_hdr *hdr3 = bp->b_addr; - block_ok = hdr->magic == cpu_to_be32(XFS_DIR2_DATA_MAGIC); - block_ok = block_ok && __xfs_dir2_data_check(NULL, bp) == 0; - - if (!block_ok) { - XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, mp, hdr); - xfs_buf_ioerror(bp, EFSCORRUPTED); + if (xfs_sb_version_hascrc(&mp->m_sb)) { + if (hdr3->magic != be32_to_cpu(XFS_DIR3_DATA_MAGIC)) + return false; + if (!uuid_equal(&hdr3->uuid, &mp->m_sb.sb_uuid)) + return false; + if (be64_to_cpu(hdr3->blkno) != bp->b_bn) + return false; + } else { + if (hdr3->magic != be32_to_cpu(XFS_DIR2_DATA_MAGIC)) + return false; } + if (__xfs_dir3_data_check(NULL, bp)) + return false; + return true; } /* @@ -212,7 +221,7 @@ xfs_dir2_data_verify( * format buffer or a data format buffer on readahead. */ static void -xfs_dir2_data_reada_verify( +xfs_dir3_data_reada_verify( struct xfs_buf *bp) { struct xfs_mount *mp = bp->b_target->bt_mount; @@ -225,7 +234,8 @@ xfs_dir2_data_reada_verify( bp->b_ops->verify_read(bp); return; case cpu_to_be32(XFS_DIR2_DATA_MAGIC): - xfs_dir2_data_verify(bp); + case cpu_to_be32(XFS_DIR3_DATA_MAGIC): + xfs_dir3_data_verify(bp); return; default: XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, mp, hdr); @@ -235,32 +245,56 @@ xfs_dir2_data_reada_verify( } static void -xfs_dir2_data_read_verify( +xfs_dir3_data_read_verify( struct xfs_buf *bp) { - xfs_dir2_data_verify(bp); + struct xfs_mount *mp = bp->b_target->bt_mount; + + if ((xfs_sb_version_hascrc(&mp->m_sb) && + !xfs_verify_cksum(bp->b_addr, BBTOB(bp->b_length), + XFS_DIR3_DATA_CRC_OFF)) || + !xfs_dir3_data_verify(bp)) { + XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, mp, bp->b_addr); + xfs_buf_ioerror(bp, EFSCORRUPTED); + } } static void -xfs_dir2_data_write_verify( +xfs_dir3_data_write_verify( struct xfs_buf *bp) { - xfs_dir2_data_verify(bp); + struct xfs_mount *mp = bp->b_target->bt_mount; + struct xfs_buf_log_item *bip = bp->b_fspriv; + struct xfs_dir3_blk_hdr *hdr3 = bp->b_addr; + + if (!xfs_dir3_data_verify(bp)) { + XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, mp, bp->b_addr); + xfs_buf_ioerror(bp, EFSCORRUPTED); + return; + } + + if (!xfs_sb_version_hascrc(&mp->m_sb)) + return; + + if (bip) + hdr3->lsn = cpu_to_be64(bip->bli_item.li_lsn); + + xfs_update_cksum(bp->b_addr, BBTOB(bp->b_length), XFS_DIR3_DATA_CRC_OFF); } -const struct xfs_buf_ops xfs_dir2_data_buf_ops = { - .verify_read = xfs_dir2_data_read_verify, - .verify_write = xfs_dir2_data_write_verify, +const struct xfs_buf_ops xfs_dir3_data_buf_ops = { + .verify_read = xfs_dir3_data_read_verify, + .verify_write = xfs_dir3_data_write_verify, }; -static const struct xfs_buf_ops xfs_dir2_data_reada_buf_ops = { - .verify_read = xfs_dir2_data_reada_verify, - .verify_write = xfs_dir2_data_write_verify, +static const struct xfs_buf_ops xfs_dir3_data_reada_buf_ops = { + .verify_read = xfs_dir3_data_reada_verify, + .verify_write = xfs_dir3_data_write_verify, }; int -xfs_dir2_data_read( +xfs_dir3_data_read( struct xfs_trans *tp, struct xfs_inode *dp, xfs_dablk_t bno, @@ -268,18 +302,18 @@ xfs_dir2_data_read( struct xfs_buf **bpp) { return xfs_da_read_buf(tp, dp, bno, mapped_bno, bpp, - XFS_DATA_FORK, &xfs_dir2_data_buf_ops); + XFS_DATA_FORK, &xfs_dir3_data_buf_ops); } int -xfs_dir2_data_readahead( +xfs_dir3_data_readahead( struct xfs_trans *tp, struct xfs_inode *dp, xfs_dablk_t bno, xfs_daddr_t mapped_bno) { return xfs_da_reada_buf(tp, dp, bno, mapped_bno, - XFS_DATA_FORK, &xfs_dir2_data_reada_buf_ops); + XFS_DATA_FORK, &xfs_dir3_data_reada_buf_ops); } /* @@ -309,6 +343,7 @@ xfs_dir2_data_freefind( * one we're looking for it has to be exact. */ ASSERT(hdr->magic == cpu_to_be32(XFS_DIR2_DATA_MAGIC) || + hdr->magic == cpu_to_be32(XFS_DIR3_DATA_MAGIC) || hdr->magic == cpu_to_be32(XFS_DIR2_BLOCK_MAGIC) || hdr->magic == cpu_to_be32(XFS_DIR3_BLOCK_MAGIC)); for (dfp = &bf[0], seenzero = matched = 0; @@ -458,6 +493,7 @@ xfs_dir2_data_freescan( char *p; /* current entry pointer */ ASSERT(hdr->magic == cpu_to_be32(XFS_DIR2_DATA_MAGIC) || + hdr->magic == cpu_to_be32(XFS_DIR3_DATA_MAGIC) || hdr->magic == cpu_to_be32(XFS_DIR2_BLOCK_MAGIC) || hdr->magic == cpu_to_be32(XFS_DIR3_BLOCK_MAGIC)); @@ -534,13 +570,12 @@ xfs_dir3_data_init( XFS_DATA_FORK); if (error) return error; - bp->b_ops = &xfs_dir2_data_buf_ops; + bp->b_ops = &xfs_dir3_data_buf_ops; /* * Initialize the header. */ hdr = bp->b_addr; - if (xfs_sb_version_hascrc(&mp->m_sb)) { struct xfs_dir3_blk_hdr *hdr3 = bp->b_addr; @@ -591,6 +626,7 @@ xfs_dir2_data_log_entry( xfs_dir2_data_hdr_t *hdr = bp->b_addr; ASSERT(hdr->magic == cpu_to_be32(XFS_DIR2_DATA_MAGIC) || + hdr->magic == cpu_to_be32(XFS_DIR3_DATA_MAGIC) || hdr->magic == cpu_to_be32(XFS_DIR2_BLOCK_MAGIC) || hdr->magic == cpu_to_be32(XFS_DIR3_BLOCK_MAGIC)); @@ -610,6 +646,7 @@ xfs_dir2_data_log_header( xfs_dir2_data_hdr_t *hdr = bp->b_addr; ASSERT(hdr->magic == cpu_to_be32(XFS_DIR2_DATA_MAGIC) || + hdr->magic == cpu_to_be32(XFS_DIR3_DATA_MAGIC) || hdr->magic == cpu_to_be32(XFS_DIR2_BLOCK_MAGIC) || hdr->magic == cpu_to_be32(XFS_DIR3_BLOCK_MAGIC)); @@ -628,6 +665,7 @@ xfs_dir2_data_log_unused( xfs_dir2_data_hdr_t *hdr = bp->b_addr; ASSERT(hdr->magic == cpu_to_be32(XFS_DIR2_DATA_MAGIC) || + hdr->magic == cpu_to_be32(XFS_DIR3_DATA_MAGIC) || hdr->magic == cpu_to_be32(XFS_DIR2_BLOCK_MAGIC) || hdr->magic == cpu_to_be32(XFS_DIR3_BLOCK_MAGIC)); @@ -675,7 +713,8 @@ xfs_dir2_data_make_free( /* * Figure out where the end of the data area is. */ - if (hdr->magic == cpu_to_be32(XFS_DIR2_DATA_MAGIC)) + if (hdr->magic == cpu_to_be32(XFS_DIR2_DATA_MAGIC) || + hdr->magic == cpu_to_be32(XFS_DIR3_DATA_MAGIC)) endptr = (char *)hdr + mp->m_dirblksize; else { xfs_dir2_block_tail_t *btp; /* block tail */ @@ -857,6 +896,7 @@ xfs_dir2_data_use_free( hdr = bp->b_addr; ASSERT(hdr->magic == cpu_to_be32(XFS_DIR2_DATA_MAGIC) || + hdr->magic == cpu_to_be32(XFS_DIR3_DATA_MAGIC) || hdr->magic == cpu_to_be32(XFS_DIR2_BLOCK_MAGIC) || hdr->magic == cpu_to_be32(XFS_DIR3_BLOCK_MAGIC)); ASSERT(be16_to_cpu(dup->freetag) == XFS_DIR2_DATA_FREE_TAG); diff --git a/fs/xfs/xfs_dir2_format.h b/fs/xfs/xfs_dir2_format.h index bec058f..dfc8ccf 100644 --- a/fs/xfs/xfs_dir2_format.h +++ b/fs/xfs/xfs_dir2_format.h @@ -283,7 +283,8 @@ struct xfs_dir3_data_hdr { static inline struct xfs_dir2_data_free * xfs_dir3_data_bestfree_p(struct xfs_dir2_data_hdr *hdr) { - if (hdr->magic == cpu_to_be32(XFS_DIR3_BLOCK_MAGIC)) { + if (hdr->magic == cpu_to_be32(XFS_DIR3_DATA_MAGIC) || + hdr->magic == cpu_to_be32(XFS_DIR3_BLOCK_MAGIC)) { struct xfs_dir3_data_hdr *hdr3 = (struct xfs_dir3_data_hdr *)hdr; return hdr3->best_free; } @@ -345,17 +346,6 @@ xfs_dir2_data_unused_tag_p(struct xfs_dir2_data_unused *dup) be16_to_cpu(dup->length) - sizeof(__be16)); } -static inline struct xfs_dir2_data_unused * -xfs_dir3_data_unused_p(struct xfs_dir2_data_hdr *hdr) -{ - if (hdr->magic == cpu_to_be32(XFS_DIR3_BLOCK_MAGIC)) { - return (struct xfs_dir2_data_unused *) - ((char *)hdr + sizeof(struct xfs_dir3_data_hdr)); - } - return (struct xfs_dir2_data_unused *) - ((char *)hdr + sizeof(struct xfs_dir2_data_hdr)); -} - static inline size_t xfs_dir3_data_hdr_size(bool dir3) { @@ -379,6 +369,13 @@ xfs_dir3_data_entry_p(struct xfs_dir2_data_hdr *hdr) ((char *)hdr + xfs_dir3_data_entry_offset(hdr)); } +static inline struct xfs_dir2_data_unused * +xfs_dir3_data_unused_p(struct xfs_dir2_data_hdr *hdr) +{ + return (struct xfs_dir2_data_unused *) + ((char *)hdr + xfs_dir3_data_entry_offset(hdr)); +} + /* * Offsets of . and .. in data space (always block 0) */ diff --git a/fs/xfs/xfs_dir2_leaf.c b/fs/xfs/xfs_dir2_leaf.c index 979735b..c7dca95 100644 --- a/fs/xfs/xfs_dir2_leaf.c +++ b/fs/xfs/xfs_dir2_leaf.c @@ -149,7 +149,7 @@ xfs_dir2_block_to_leaf( int needlog; /* need to log block header */ int needscan; /* need to rescan bestfree */ xfs_trans_t *tp; /* transaction pointer */ - struct xfs_dir2_data_free *bf; + struct xfs_dir2_data_free *bf; trace_xfs_dir2_block_to_leaf(args); @@ -175,7 +175,7 @@ xfs_dir2_block_to_leaf( ASSERT(lbp != NULL); leaf = lbp->b_addr; hdr = dbp->b_addr; - xfs_dir2_data_check(dp, dbp); + xfs_dir3_data_check(dp, dbp); btp = xfs_dir2_block_tail_p(mp, hdr); blp = xfs_dir2_block_leaf_p(btp); bf = xfs_dir3_data_bestfree_p(hdr); @@ -204,8 +204,12 @@ xfs_dir2_block_to_leaf( /* * Fix up the block header, make it a data block. */ - dbp->b_ops = &xfs_dir2_data_buf_ops; - hdr->magic = cpu_to_be32(XFS_DIR2_DATA_MAGIC); + dbp->b_ops = &xfs_dir3_data_buf_ops; + if (hdr->magic == cpu_to_be32(XFS_DIR2_BLOCK_MAGIC)) + hdr->magic = cpu_to_be32(XFS_DIR2_DATA_MAGIC); + else + hdr->magic = cpu_to_be32(XFS_DIR3_DATA_MAGIC); + if (needscan) xfs_dir2_data_freescan(mp, hdr, &needlog); /* @@ -221,7 +225,7 @@ xfs_dir2_block_to_leaf( if (needlog) xfs_dir2_data_log_header(tp, dbp); xfs_dir2_leaf_check(dp, lbp); - xfs_dir2_data_check(dp, dbp); + xfs_dir3_data_check(dp, dbp); xfs_dir2_leaf_log_bests(tp, lbp, 0, 0); return 0; } @@ -385,6 +389,7 @@ xfs_dir2_leaf_addname( __be16 *tagp; /* end of data entry */ xfs_trans_t *tp; /* transaction pointer */ xfs_dir2_db_t use_block; /* data block number */ + struct xfs_dir2_data_free *bf; /* bestfree table */ trace_xfs_dir2_leaf_addname(args); @@ -568,14 +573,15 @@ xfs_dir2_leaf_addname( else xfs_dir2_leaf_log_bests(tp, lbp, use_block, use_block); hdr = dbp->b_addr; - bestsp[use_block] = hdr->bestfree[0].length; + bf = xfs_dir3_data_bestfree_p(hdr); + bestsp[use_block] = bf[0].length; grown = 1; } else { /* * Already had space in some data block. * Just read that one in. */ - error = xfs_dir2_data_read(tp, dp, + error = xfs_dir3_data_read(tp, dp, xfs_dir2_db_to_da(mp, use_block), -1, &dbp); if (error) { @@ -583,13 +589,14 @@ xfs_dir2_leaf_addname( return error; } hdr = dbp->b_addr; + bf = xfs_dir3_data_bestfree_p(hdr); grown = 0; } /* * Point to the biggest freespace in our data block. */ dup = (xfs_dir2_data_unused_t *) - ((char *)hdr + be16_to_cpu(hdr->bestfree[0].offset)); + ((char *)hdr + be16_to_cpu(bf[0].offset)); ASSERT(be16_to_cpu(dup->length) >= length); needscan = needlog = 0; /* @@ -622,8 +629,8 @@ xfs_dir2_leaf_addname( * If the bests table needs to be changed, do it. * Log the change unless we've already done that. */ - if (be16_to_cpu(bestsp[use_block]) != be16_to_cpu(hdr->bestfree[0].length)) { - bestsp[use_block] = hdr->bestfree[0].length; + if (be16_to_cpu(bestsp[use_block]) != be16_to_cpu(bf[0].length)) { + bestsp[use_block] = bf[0].length; if (!grown) xfs_dir2_leaf_log_bests(tp, lbp, use_block, use_block); } @@ -643,7 +650,7 @@ xfs_dir2_leaf_addname( xfs_dir2_leaf_log_header(tp, lbp); xfs_dir2_leaf_log_ents(tp, lbp, lfloglow, lfloghigh); xfs_dir2_leaf_check(dp, lbp); - xfs_dir2_data_check(dp, dbp); + xfs_dir3_data_check(dp, dbp); return 0; } @@ -967,7 +974,7 @@ xfs_dir2_leaf_readbuf( * Read the directory block starting at the first mapping. */ mip->curdb = xfs_dir2_da_to_db(mp, map->br_startoff); - error = xfs_dir2_data_read(NULL, dp, map->br_startoff, + error = xfs_dir3_data_read(NULL, dp, map->br_startoff, map->br_blockcount >= mp->m_dirblkfsbs ? XFS_FSB_TO_DADDR(mp, map->br_startblock) : -1, &bp); @@ -996,7 +1003,7 @@ xfs_dir2_leaf_readbuf( */ if (i > mip->ra_current && map[mip->ra_index].br_blockcount >= mp->m_dirblkfsbs) { - xfs_dir2_data_readahead(NULL, dp, + xfs_dir3_data_readahead(NULL, dp, map[mip->ra_index].br_startoff + mip->ra_offset, XFS_FSB_TO_DADDR(mp, map[mip->ra_index].br_startblock + @@ -1009,7 +1016,7 @@ xfs_dir2_leaf_readbuf( * use our mapping, but this is a very rare case. */ else if (i > mip->ra_current) { - xfs_dir2_data_readahead(NULL, dp, + xfs_dir3_data_readahead(NULL, dp, map[mip->ra_index].br_startoff + mip->ra_offset, -1); mip->ra_current = i; @@ -1135,17 +1142,17 @@ xfs_dir2_leaf_getdents( ASSERT(xfs_dir2_byte_to_db(mp, curoff) == map_info->curdb); hdr = bp->b_addr; - xfs_dir2_data_check(dp, bp); + xfs_dir3_data_check(dp, bp); /* * Find our position in the block. */ - ptr = (char *)(hdr + 1); + ptr = (char *)xfs_dir3_data_entry_p(hdr); byteoff = xfs_dir2_byte_to_off(mp, curoff); /* * Skip past the header. */ if (byteoff == 0) - curoff += (uint)sizeof(*hdr); + curoff += xfs_dir3_data_entry_offset(hdr); /* * Skip past entries until we reach our offset. */ @@ -1481,7 +1488,7 @@ xfs_dir2_leaf_lookup_int( if (newdb != curdb) { if (dbp) xfs_trans_brelse(tp, dbp); - error = xfs_dir2_data_read(tp, dp, + error = xfs_dir3_data_read(tp, dp, xfs_dir2_db_to_da(mp, newdb), -1, &dbp); if (error) { @@ -1522,7 +1529,7 @@ xfs_dir2_leaf_lookup_int( ASSERT(cidb != -1); if (cidb != curdb) { xfs_trans_brelse(tp, dbp); - error = xfs_dir2_data_read(tp, dp, + error = xfs_dir3_data_read(tp, dp, xfs_dir2_db_to_da(mp, cidb), -1, &dbp); if (error) { @@ -1568,6 +1575,7 @@ xfs_dir2_leaf_removename( int needscan; /* need to rescan data frees */ xfs_dir2_data_off_t oldbest; /* old value of best free */ xfs_trans_t *tp; /* transaction pointer */ + struct xfs_dir2_data_free *bf; /* bestfree table */ trace_xfs_dir2_leaf_removename(args); @@ -1582,7 +1590,8 @@ xfs_dir2_leaf_removename( mp = dp->i_mount; leaf = lbp->b_addr; hdr = dbp->b_addr; - xfs_dir2_data_check(dp, dbp); + bf = xfs_dir3_data_bestfree_p(hdr); + xfs_dir3_data_check(dp, dbp); /* * Point to the leaf entry, use that to point to the data entry. */ @@ -1591,7 +1600,7 @@ xfs_dir2_leaf_removename( dep = (xfs_dir2_data_entry_t *) ((char *)hdr + xfs_dir2_dataptr_to_off(mp, be32_to_cpu(lep->address))); needscan = needlog = 0; - oldbest = be16_to_cpu(hdr->bestfree[0].length); + oldbest = be16_to_cpu(bf[0].length); ltp = xfs_dir2_leaf_tail_p(mp, leaf); bestsp = xfs_dir2_leaf_bests_p(ltp); ASSERT(be16_to_cpu(bestsp[db]) == oldbest); @@ -1620,16 +1629,16 @@ xfs_dir2_leaf_removename( * If the longest freespace in the data block has changed, * put the new value in the bests table and log that. */ - if (be16_to_cpu(hdr->bestfree[0].length) != oldbest) { - bestsp[db] = hdr->bestfree[0].length; + if (be16_to_cpu(bf[0].length) != oldbest) { + bestsp[db] = bf[0].length; xfs_dir2_leaf_log_bests(tp, lbp, db, db); } - xfs_dir2_data_check(dp, dbp); + xfs_dir3_data_check(dp, dbp); /* * If the data block is now empty then get rid of the data block. */ - if (be16_to_cpu(hdr->bestfree[0].length) == - mp->m_dirblksize - (uint)sizeof(*hdr)) { + if (be16_to_cpu(bf[0].length) == + mp->m_dirblksize - xfs_dir3_data_entry_offset(hdr)) { ASSERT(db != mp->m_dirdatablk); if ((error = xfs_dir2_shrink_inode(args, db, dbp))) { /* @@ -1809,7 +1818,7 @@ xfs_dir2_leaf_trim_data( /* * Read the offending data block. We need its buffer. */ - error = xfs_dir2_data_read(tp, dp, xfs_dir2_db_to_da(mp, db), -1, &dbp); + error = xfs_dir3_data_read(tp, dp, xfs_dir2_db_to_da(mp, db), -1, &dbp); if (error) return error; @@ -1819,10 +1828,12 @@ xfs_dir2_leaf_trim_data( #ifdef DEBUG { struct xfs_dir2_data_hdr *hdr = dbp->b_addr; + struct xfs_dir2_data_free *bf = xfs_dir3_data_bestfree_p(hdr); - ASSERT(hdr->magic == cpu_to_be32(XFS_DIR2_DATA_MAGIC)); - ASSERT(be16_to_cpu(hdr->bestfree[0].length) == - mp->m_dirblksize - (uint)sizeof(*hdr)); + ASSERT(hdr->magic == cpu_to_be32(XFS_DIR2_DATA_MAGIC) || + hdr->magic == cpu_to_be32(XFS_DIR3_DATA_MAGIC)); + ASSERT(be16_to_cpu(bf[0].length) == + mp->m_dirblksize - xfs_dir3_data_entry_offset(hdr)); ASSERT(db == be32_to_cpu(ltp->bestcount) - 1); } #endif diff --git a/fs/xfs/xfs_dir2_node.c b/fs/xfs/xfs_dir2_node.c index 074fa68..14067a4 100644 --- a/fs/xfs/xfs_dir2_node.c +++ b/fs/xfs/xfs_dir2_node.c @@ -754,13 +754,13 @@ xfs_dir2_leafn_lookup_for_entry( ASSERT(state->extravalid); curbp = state->extrablk.bp; } else { - error = xfs_dir2_data_read(tp, dp, + error = xfs_dir3_data_read(tp, dp, xfs_dir2_db_to_da(mp, newdb), -1, &curbp); if (error) return error; } - xfs_dir2_data_check(dp, curbp); + xfs_dir3_data_check(dp, curbp); curdb = newdb; } /* @@ -788,7 +788,7 @@ xfs_dir2_leafn_lookup_for_entry( state->extrablk.index = (int)((char *)dep - (char *)curbp->b_addr); state->extrablk.magic = XFS_DIR2_DATA_MAGIC; - curbp->b_ops = &xfs_dir2_data_buf_ops; + curbp->b_ops = &xfs_dir3_data_buf_ops; if (cmp == XFS_CMP_EXACT) return XFS_ERROR(EEXIST); } @@ -803,7 +803,7 @@ xfs_dir2_leafn_lookup_for_entry( state->extrablk.index = -1; state->extrablk.blkno = curdb; state->extrablk.magic = XFS_DIR2_DATA_MAGIC; - curbp->b_ops = &xfs_dir2_data_buf_ops; + curbp->b_ops = &xfs_dir3_data_buf_ops; } else { /* If the curbp is not the CI match block, drop it */ if (state->extrablk.bp != curbp) @@ -1153,6 +1153,7 @@ xfs_dir2_leafn_remove( int needlog; /* need to log data header */ int needscan; /* need to rescan data frees */ xfs_trans_t *tp; /* transaction pointer */ + struct xfs_dir2_data_free *bf; /* bestfree table */ trace_xfs_dir2_leafn_remove(args, index); @@ -1187,7 +1188,8 @@ xfs_dir2_leafn_remove( dbp = dblk->bp; hdr = dbp->b_addr; dep = (xfs_dir2_data_entry_t *)((char *)hdr + off); - longest = be16_to_cpu(hdr->bestfree[0].length); + bf = xfs_dir3_data_bestfree_p(hdr); + longest = be16_to_cpu(bf[0].length); needlog = needscan = 0; xfs_dir2_data_make_free(tp, dbp, off, xfs_dir2_data_entsize(dep->namelen), &needlog, &needscan); @@ -1199,12 +1201,12 @@ xfs_dir2_leafn_remove( xfs_dir2_data_freescan(mp, hdr, &needlog); if (needlog) xfs_dir2_data_log_header(tp, dbp); - xfs_dir2_data_check(dp, dbp); + xfs_dir3_data_check(dp, dbp); /* * If the longest data block freespace changes, need to update * the corresponding freeblock entry. */ - if (longest < be16_to_cpu(hdr->bestfree[0].length)) { + if (longest < be16_to_cpu(bf[0].length)) { int error; /* error return value */ struct xfs_buf *fbp; /* freeblock buffer */ xfs_dir2_db_t fdb; /* freeblock block number */ @@ -1234,12 +1236,13 @@ xfs_dir2_leafn_remove( * Calculate which entry we need to fix. */ findex = xfs_dir2_db_to_fdindex(mp, db); - longest = be16_to_cpu(hdr->bestfree[0].length); + longest = be16_to_cpu(bf[0].length); /* * If the data block is now empty we can get rid of it * (usually). */ - if (longest == mp->m_dirblksize - (uint)sizeof(*hdr)) { + if (longest == mp->m_dirblksize - + xfs_dir3_data_entry_offset(hdr)) { /* * Try to punch out the data block. */ @@ -1613,6 +1616,7 @@ xfs_dir2_node_addname_int( xfs_trans_t *tp; /* transaction pointer */ __be16 *bests; struct xfs_dir3_icfree_hdr freehdr; + struct xfs_dir2_data_free *bf; dp = args->dp; mp = dp->i_mount; @@ -1870,7 +1874,8 @@ xfs_dir2_node_addname_int( * change again. */ hdr = dbp->b_addr; - bests[findex] = hdr->bestfree[0].length; + bf = xfs_dir3_data_bestfree_p(hdr); + bests[findex] = bf[0].length; logfree = 1; } /* @@ -1886,19 +1891,20 @@ xfs_dir2_node_addname_int( /* * Read the data block in. */ - error = xfs_dir2_data_read(tp, dp, xfs_dir2_db_to_da(mp, dbno), + error = xfs_dir3_data_read(tp, dp, xfs_dir2_db_to_da(mp, dbno), -1, &dbp); if (error) return error; hdr = dbp->b_addr; + bf = xfs_dir3_data_bestfree_p(hdr); logfree = 0; } - ASSERT(be16_to_cpu(hdr->bestfree[0].length) >= length); + ASSERT(be16_to_cpu(bf[0].length) >= length); /* * Point to the existing unused space. */ dup = (xfs_dir2_data_unused_t *) - ((char *)hdr + be16_to_cpu(hdr->bestfree[0].offset)); + ((char *)hdr + be16_to_cpu(bf[0].offset)); needscan = needlog = 0; /* * Mark the first part of the unused space, inuse for us. @@ -1930,8 +1936,8 @@ xfs_dir2_node_addname_int( * If the freespace entry is now wrong, update it. */ bests = xfs_dir3_free_bests_p(mp, free); /* gcc is so stupid */ - if (be16_to_cpu(bests[findex]) != be16_to_cpu(hdr->bestfree[0].length)) { - bests[findex] = hdr->bestfree[0].length; + if (be16_to_cpu(bests[findex]) != be16_to_cpu(bf[0].length)) { + bests[findex] = bf[0].length; logfree = 1; } /* @@ -2121,7 +2127,8 @@ xfs_dir2_node_replace( * Point to the data entry. */ hdr = state->extrablk.bp->b_addr; - ASSERT(hdr->magic == cpu_to_be32(XFS_DIR2_DATA_MAGIC)); + ASSERT(hdr->magic == cpu_to_be32(XFS_DIR2_DATA_MAGIC) || + hdr->magic == cpu_to_be32(XFS_DIR3_DATA_MAGIC)); dep = (xfs_dir2_data_entry_t *) ((char *)hdr + xfs_dir2_dataptr_to_off(state->mp, be32_to_cpu(lep->address))); diff --git a/fs/xfs/xfs_dir2_priv.h b/fs/xfs/xfs_dir2_priv.h index e6f2e0a..910e644 100644 --- a/fs/xfs/xfs_dir2_priv.h +++ b/fs/xfs/xfs_dir2_priv.h @@ -43,17 +43,17 @@ extern int xfs_dir2_leaf_to_block(struct xfs_da_args *args, /* xfs_dir2_data.c */ #ifdef DEBUG -#define xfs_dir2_data_check(dp,bp) __xfs_dir2_data_check(dp, bp); +#define xfs_dir3_data_check(dp,bp) __xfs_dir3_data_check(dp, bp); #else -#define xfs_dir2_data_check(dp,bp) +#define xfs_dir3_data_check(dp,bp) #endif -extern const struct xfs_buf_ops xfs_dir2_data_buf_ops; +extern const struct xfs_buf_ops xfs_dir3_data_buf_ops; -extern int __xfs_dir2_data_check(struct xfs_inode *dp, struct xfs_buf *bp); -extern int xfs_dir2_data_read(struct xfs_trans *tp, struct xfs_inode *dp, +extern int __xfs_dir3_data_check(struct xfs_inode *dp, struct xfs_buf *bp); +extern int xfs_dir3_data_read(struct xfs_trans *tp, struct xfs_inode *dp, xfs_dablk_t bno, xfs_daddr_t mapped_bno, struct xfs_buf **bpp); -extern int xfs_dir2_data_readahead(struct xfs_trans *tp, struct xfs_inode *dp, +extern int xfs_dir3_data_readahead(struct xfs_trans *tp, struct xfs_inode *dp, xfs_dablk_t bno, xfs_daddr_t mapped_bno); extern struct xfs_dir2_data_free * diff --git a/fs/xfs/xfs_file.c b/fs/xfs/xfs_file.c index 36eb41d..89a32ef 100644 --- a/fs/xfs/xfs_file.c +++ b/fs/xfs/xfs_file.c @@ -915,7 +915,7 @@ xfs_dir_open( */ mode = xfs_ilock_map_shared(ip); if (ip->i_d.di_nextents > 0) - xfs_dir2_data_readahead(NULL, ip, 0, -1); + xfs_dir3_data_readahead(NULL, ip, 0, -1); xfs_iunlock(ip, mode); return 0; } -- 1.7.10.4 From dave@fromorbit.com Tue Mar 12 07:31:31 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 4C4037FB6 for ; Tue, 12 Mar 2013 07:31:31 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay2.corp.sgi.com (Postfix) with ESMTP id 3804A304048 for ; Tue, 12 Mar 2013 05:31:31 -0700 (PDT) X-ASG-Debug-ID: 1363091485-04cb6c2b01493060002-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id 8v5QlpA7d1mIdPPz for ; Tue, 12 Mar 2013 05:31:29 -0700 (PDT) X-Barracuda-Envelope-From: dave@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: Ag0KAKEfP1F5LKiV/2dsb2JhbABDxF0DgUoXdIIoAQEFJy8zCBgYGTkDGxmIErACkB+ODIESgzYDp0qDHig Received: from ppp121-44-168-149.lns20.syd7.internode.on.net (HELO dastard) ([121.44.168.149]) by ipmail05.adl6.internode.on.net with ESMTP; 12 Mar 2013 23:01:29 +1030 Received: from disappointment ([192.168.1.1]) by dastard with esmtp (Exim 4.76) (envelope-from ) id 1UFOMa-0001Sg-Hn for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:31:28 +1100 Received: from dave by disappointment with local (Exim 4.80) (envelope-from ) id 1UFOMQ-0002Mo-Em for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:31:18 +1100 From: Dave Chinner To: xfs@oss.sgi.com Subject: [PATCH 15/21] xfs: shortform directory offsets change for dir3 format Date: Tue, 12 Mar 2013 23:30:48 +1100 X-ASG-Orig-Subj: [PATCH 15/21] xfs: shortform directory offsets change for dir3 format Message-Id: <1363091454-8852-16-git-send-email-david@fromorbit.com> X-Mailer: git-send-email 1.7.10.4 In-Reply-To: <1363091454-8852-1-git-send-email-david@fromorbit.com> References: <1363091454-8852-1-git-send-email-david@fromorbit.com> X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1363091488 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124988 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- From: Dave Chinner Because the header size for the CRC enabled directory blocks is larger, the offset of the first entry into a directory block is different to the dir2 format. The shortform directory stores the dirent's offset so that it doesn't change when moving from shortform to block form and back again, and hence it needs to take into account the different header sizes to maintain the correct offsets. Signed-off-by: Dave Chinner --- fs/xfs/xfs_dir2_format.h | 25 ++++++++++++++----------- fs/xfs/xfs_dir2_sf.c | 10 +++++----- 2 files changed, 19 insertions(+), 16 deletions(-) diff --git a/fs/xfs/xfs_dir2_format.h b/fs/xfs/xfs_dir2_format.h index 8bb4efe..8d33f03 100644 --- a/fs/xfs/xfs_dir2_format.h +++ b/fs/xfs/xfs_dir2_format.h @@ -228,16 +228,6 @@ xfs_dir2_sf_nextentry(struct xfs_dir2_sf_hdr *hdr, xfs_dir2_byte_to_db(mp, XFS_DIR2_DATA_OFFSET) /* - * Offsets of . and .. in data space (always block 0) - */ -#define XFS_DIR2_DATA_DOT_OFFSET \ - ((xfs_dir2_data_aoff_t)sizeof(struct xfs_dir2_data_hdr)) -#define XFS_DIR2_DATA_DOTDOT_OFFSET \ - (XFS_DIR2_DATA_DOT_OFFSET + xfs_dir2_data_entsize(1)) -#define XFS_DIR2_DATA_FIRST_OFFSET \ - (XFS_DIR2_DATA_DOTDOT_OFFSET + xfs_dir2_data_entsize(2)) - -/* * Describe a free area in the data block. * * The freespace will be formatted as a xfs_dir2_data_unused_t. @@ -378,7 +368,20 @@ xfs_dir3_data_unused_p(struct xfs_dir2_data_hdr *hdr) /* * Offsets of . and .. in data space (always block 0) - */ + * + * The macros are used for shortform directories as they have no headers to read + * the magic number out of. Shortform directories need to know the size of the + * data block header because the sfe embeds the block offset of the entry into + * it so that it doesn't change when format conversion occurs. Bad Things Happen + * if we don't follow this rule. + */ +#define XFS_DIR3_DATA_DOT_OFFSET(mp) \ + xfs_dir3_data_hdr_size(xfs_sb_version_hascrc(&(mp)->m_sb)) +#define XFS_DIR3_DATA_DOTDOT_OFFSET(mp) \ + (XFS_DIR3_DATA_DOT_OFFSET(mp) + xfs_dir2_data_entsize(1)) +#define XFS_DIR3_DATA_FIRST_OFFSET(mp) \ + (XFS_DIR3_DATA_DOTDOT_OFFSET(mp) + xfs_dir2_data_entsize(2)) + static inline xfs_dir2_data_aoff_t xfs_dir3_data_dot_offset(struct xfs_dir2_data_hdr *hdr) { diff --git a/fs/xfs/xfs_dir2_sf.c b/fs/xfs/xfs_dir2_sf.c index b975622..6157424 100644 --- a/fs/xfs/xfs_dir2_sf.c +++ b/fs/xfs/xfs_dir2_sf.c @@ -535,7 +535,7 @@ xfs_dir2_sf_addname_hard( * to insert the new entry. * If it's going to end up at the end then oldsfep will point there. */ - for (offset = XFS_DIR2_DATA_FIRST_OFFSET, + for (offset = XFS_DIR3_DATA_FIRST_OFFSET(dp->i_mount), oldsfep = xfs_dir2_sf_firstentry(oldsfp), add_datasize = xfs_dir2_data_entsize(args->namelen), eof = (char *)oldsfep == &buf[old_isize]; @@ -617,7 +617,7 @@ xfs_dir2_sf_addname_pick( sfp = (xfs_dir2_sf_hdr_t *)dp->i_df.if_u1.if_data; size = xfs_dir2_data_entsize(args->namelen); - offset = XFS_DIR2_DATA_FIRST_OFFSET; + offset = XFS_DIR3_DATA_FIRST_OFFSET(mp); sfep = xfs_dir2_sf_firstentry(sfp); holefit = 0; /* @@ -688,7 +688,7 @@ xfs_dir2_sf_check( dp = args->dp; sfp = (xfs_dir2_sf_hdr_t *)dp->i_df.if_u1.if_data; - offset = XFS_DIR2_DATA_FIRST_OFFSET; + offset = XFS_DIR3_DATA_FIRST_OFFSET(dp->i_mount); ino = xfs_dir2_sf_get_parent_ino(sfp); i8count = ino > XFS_DIR2_MAX_SHORT_INUM; @@ -812,9 +812,9 @@ xfs_dir2_sf_getdents( * mp->m_dirdatablk. */ dot_offset = xfs_dir2_db_off_to_dataptr(mp, mp->m_dirdatablk, - XFS_DIR2_DATA_DOT_OFFSET); + XFS_DIR3_DATA_DOT_OFFSET(mp)); dotdot_offset = xfs_dir2_db_off_to_dataptr(mp, mp->m_dirdatablk, - XFS_DIR2_DATA_DOTDOT_OFFSET); + XFS_DIR3_DATA_DOTDOT_OFFSET(mp)); /* * Put . entry unless we're starting past it. -- 1.7.10.4 From dave@fromorbit.com Tue Mar 12 07:31:31 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id CD5197FA2 for ; Tue, 12 Mar 2013 07:31:30 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay3.corp.sgi.com (Postfix) with ESMTP id 3E9D6AC002 for ; Tue, 12 Mar 2013 05:31:30 -0700 (PDT) X-ASG-Debug-ID: 1363091485-04cb6c2b01493060001-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id joCla6qXoSb22RBR for ; Tue, 12 Mar 2013 05:31:26 -0700 (PDT) X-Barracuda-Envelope-From: dave@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AhAKAKEfP1F5LKiV/2dsb2JhbABDxF0DAYFJF3SCKAEBBRoBDC8zCBgxOQMbGYgSsAKQH44MdoNSA6dKgx4ogTAk Received: from ppp121-44-168-149.lns20.syd7.internode.on.net (HELO dastard) ([121.44.168.149]) by ipmail05.adl6.internode.on.net with ESMTP; 12 Mar 2013 23:01:24 +1030 Received: from disappointment ([192.168.1.1]) by dastard with esmtp (Exim 4.76) (envelope-from ) id 1UFOMQ-0001S9-DV for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:31:18 +1100 Received: from dave by disappointment with local (Exim 4.80) (envelope-from ) id 1UFOMB-0002MQ-9z for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:31:03 +1100 From: Dave Chinner To: xfs@oss.sgi.com Subject: [PATCH 11/21] xfs: add CRC checks to block format directory blocks Date: Tue, 12 Mar 2013 23:30:44 +1100 X-ASG-Orig-Subj: [PATCH 11/21] xfs: add CRC checks to block format directory blocks Message-Id: <1363091454-8852-12-git-send-email-david@fromorbit.com> X-Mailer: git-send-email 1.7.10.4 In-Reply-To: <1363091454-8852-1-git-send-email-david@fromorbit.com> References: <1363091454-8852-1-git-send-email-david@fromorbit.com> X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1363091485 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124988 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- From: Dave Chinner Now that directory buffers are made from a single struct xfs_buf, we can add CRC calculation and checking callbacks. While there, add all the fields to the on disk structures for future functionality such as d_type support, uuids, block numbers, owner inode, etc. To distinguish between the different on disk formats, change the magic numbers for the new format directory blocks. Signed-off-by: Dave Chinner --- fs/xfs/xfs_dir2_block.c | 132 +++++++++++++++++++++++++++----------- fs/xfs/xfs_dir2_data.c | 160 ++++++++++++++++++++++++++++------------------ fs/xfs/xfs_dir2_format.h | 155 ++++++++++++++++++++++++++++++++++++++++++-- fs/xfs/xfs_dir2_leaf.c | 6 +- fs/xfs/xfs_dir2_node.c | 2 +- fs/xfs/xfs_dir2_priv.h | 4 +- fs/xfs/xfs_dir2_sf.c | 2 +- fs/xfs/xfs_log_recover.c | 2 + 8 files changed, 352 insertions(+), 111 deletions(-) diff --git a/fs/xfs/xfs_dir2_block.c b/fs/xfs/xfs_dir2_block.c index 12afe07..5189606 100644 --- a/fs/xfs/xfs_dir2_block.c +++ b/fs/xfs/xfs_dir2_block.c @@ -1,5 +1,6 @@ /* * Copyright (c) 2000-2003,2005 Silicon Graphics, Inc. + * Copyright (c) 2013 Red Hat, Inc. * All Rights Reserved. * * This program is free software; you can redistribute it and/or @@ -28,11 +29,13 @@ #include "xfs_dinode.h" #include "xfs_inode.h" #include "xfs_inode_item.h" +#include "xfs_buf_item.h" #include "xfs_dir2.h" #include "xfs_dir2_format.h" #include "xfs_dir2_priv.h" #include "xfs_error.h" #include "xfs_trace.h" +#include "xfs_cksum.h" /* * Local function prototypes. @@ -56,44 +59,74 @@ xfs_dir_startup(void) xfs_dir_hash_dotdot = xfs_da_hashname((unsigned char *)"..", 2); } -static void -xfs_dir2_block_verify( +static bool +xfs_dir3_block_verify( struct xfs_buf *bp) { struct xfs_mount *mp = bp->b_target->bt_mount; - struct xfs_dir2_data_hdr *hdr = bp->b_addr; - int block_ok = 0; - - block_ok = hdr->magic == cpu_to_be32(XFS_DIR2_BLOCK_MAGIC); - block_ok = block_ok && __xfs_dir2_data_check(NULL, bp) == 0; - - if (!block_ok) { - XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, mp, hdr); - xfs_buf_ioerror(bp, EFSCORRUPTED); + struct xfs_dir3_blk_hdr *hdr3 = bp->b_addr; + + if (xfs_sb_version_hascrc(&mp->m_sb)) { + if (hdr3->magic != be32_to_cpu(XFS_DIR3_BLOCK_MAGIC)) + return false; + if (!uuid_equal(&hdr3->uuid, &mp->m_sb.sb_uuid)) + return false; + if (be64_to_cpu(hdr3->blkno) != bp->b_bn) + return false; + } else { + if (hdr3->magic != be32_to_cpu(XFS_DIR2_BLOCK_MAGIC)) + return false; } + if (__xfs_dir2_data_check(NULL, bp)) + return false; + return true; } static void -xfs_dir2_block_read_verify( +xfs_dir3_block_read_verify( struct xfs_buf *bp) { - xfs_dir2_block_verify(bp); + struct xfs_mount *mp = bp->b_target->bt_mount; + + if ((xfs_sb_version_hascrc(&mp->m_sb) && + !xfs_verify_cksum(bp->b_addr, BBTOB(bp->b_length), + XFS_DIR3_DATA_CRC_OFF)) || + !xfs_dir3_block_verify(bp)) { + XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, mp, bp->b_addr); + xfs_buf_ioerror(bp, EFSCORRUPTED); + } } static void -xfs_dir2_block_write_verify( +xfs_dir3_block_write_verify( struct xfs_buf *bp) { - xfs_dir2_block_verify(bp); + struct xfs_mount *mp = bp->b_target->bt_mount; + struct xfs_buf_log_item *bip = bp->b_fspriv; + struct xfs_dir3_blk_hdr *hdr3 = bp->b_addr; + + if (!xfs_dir3_block_verify(bp)) { + XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, mp, bp->b_addr); + xfs_buf_ioerror(bp, EFSCORRUPTED); + return; + } + + if (!xfs_sb_version_hascrc(&mp->m_sb)) + return; + + if (bip) + hdr3->lsn = cpu_to_be64(bip->bli_item.li_lsn); + + xfs_update_cksum(bp->b_addr, BBTOB(bp->b_length), XFS_DIR3_DATA_CRC_OFF); } -const struct xfs_buf_ops xfs_dir2_block_buf_ops = { - .verify_read = xfs_dir2_block_read_verify, - .verify_write = xfs_dir2_block_write_verify, +const struct xfs_buf_ops xfs_dir3_block_buf_ops = { + .verify_read = xfs_dir3_block_read_verify, + .verify_write = xfs_dir3_block_write_verify, }; static int -xfs_dir2_block_read( +xfs_dir3_block_read( struct xfs_trans *tp, struct xfs_inode *dp, struct xfs_buf **bpp) @@ -101,7 +134,29 @@ xfs_dir2_block_read( struct xfs_mount *mp = dp->i_mount; return xfs_da_read_buf(tp, dp, mp->m_dirdatablk, -1, bpp, - XFS_DATA_FORK, &xfs_dir2_block_buf_ops); + XFS_DATA_FORK, &xfs_dir3_block_buf_ops); +} + +static void +xfs_dir3_block_init( + struct xfs_mount *mp, + struct xfs_buf *bp, + struct xfs_inode *dp) +{ + struct xfs_dir3_blk_hdr *hdr3 = bp->b_addr; + + bp->b_ops = &xfs_dir3_block_buf_ops; + + if (xfs_sb_version_hascrc(&mp->m_sb)) { + memset(hdr3, 0, sizeof(*hdr3)); + hdr3->magic = cpu_to_be32(XFS_DIR3_BLOCK_MAGIC); + hdr3->blkno = cpu_to_be64(bp->b_bn); + hdr3->owner = cpu_to_be64(dp->i_ino); + uuid_copy(&hdr3->uuid, &mp->m_sb.sb_uuid); + return; + + } + hdr3->magic = cpu_to_be32(XFS_DIR2_BLOCK_MAGIC); } static void @@ -121,7 +176,7 @@ xfs_dir2_block_need_space( struct xfs_dir2_data_unused *enddup = NULL; *compact = 0; - bf = hdr->bestfree; + bf = xfs_dir3_data_bestfree_p(hdr); /* * If there are stale entries we'll use one for the leaf. @@ -303,7 +358,7 @@ xfs_dir2_block_addname( mp = dp->i_mount; /* Read the (one and only) directory block into bp. */ - error = xfs_dir2_block_read(tp, dp, &bp); + error = xfs_dir3_block_read(tp, dp, &bp); if (error) return error; @@ -531,7 +586,7 @@ xfs_dir2_block_getdents( if (xfs_dir2_dataptr_to_db(mp, *offset) > mp->m_dirdatablk) return 0; - error = xfs_dir2_block_read(NULL, dp, &bp); + error = xfs_dir3_block_read(NULL, dp, &bp); if (error) return error; @@ -546,7 +601,7 @@ xfs_dir2_block_getdents( * Set up values for the loop. */ btp = xfs_dir2_block_tail_p(mp, hdr); - ptr = (char *)(hdr + 1); + ptr = (char *)xfs_dir3_data_entry_p(hdr); endptr = (char *)xfs_dir2_block_leaf_p(btp); /* @@ -711,7 +766,7 @@ xfs_dir2_block_lookup_int( tp = args->trans; mp = dp->i_mount; - error = xfs_dir2_block_read(tp, dp, &bp); + error = xfs_dir3_block_read(tp, dp, &bp); if (error) return error; @@ -974,9 +1029,12 @@ xfs_dir2_leaf_to_block( * These will show up in the leaf bests table. */ while (dp->i_d.di_size > mp->m_dirblksize) { + int hdrsz; + + hdrsz = xfs_dir3_data_hdr_size(xfs_sb_version_hascrc(&mp->m_sb)); bestsp = xfs_dir2_leaf_bests_p(ltp); if (be16_to_cpu(bestsp[be32_to_cpu(ltp->bestcount) - 1]) == - mp->m_dirblksize - (uint)sizeof(*hdr)) { + mp->m_dirblksize - hdrsz) { if ((error = xfs_dir2_leaf_trim_data(args, lbp, (xfs_dir2_db_t)(be32_to_cpu(ltp->bestcount) - 1)))) @@ -1014,8 +1072,8 @@ xfs_dir2_leaf_to_block( /* * Start converting it to block form. */ - dbp->b_ops = &xfs_dir2_block_buf_ops; - hdr->magic = cpu_to_be32(XFS_DIR2_BLOCK_MAGIC); + xfs_dir3_block_init(mp, dbp, dp); + needlog = 1; needscan = 0; /* @@ -1137,16 +1195,16 @@ xfs_dir2_sf_to_block( return error; } /* - * Initialize the data block. + * Initialize the data block, then convert it to block format. */ - error = xfs_dir2_data_init(args, blkno, &bp); + error = xfs_dir3_data_init(args, blkno, &bp); if (error) { kmem_free(sfp); return error; } - bp->b_ops = &xfs_dir2_block_buf_ops; + xfs_dir3_block_init(mp, bp, dp); hdr = bp->b_addr; - hdr->magic = cpu_to_be32(XFS_DIR2_BLOCK_MAGIC); + /* * Compute size of block "tail" area. */ @@ -1156,7 +1214,7 @@ xfs_dir2_sf_to_block( * The whole thing is initialized to free by the init routine. * Say we're using the leaf and tail area. */ - dup = (xfs_dir2_data_unused_t *)(hdr + 1); + dup = xfs_dir3_data_unused_p(hdr); needlog = needscan = 0; xfs_dir2_data_use_free(tp, bp, dup, mp->m_dirblksize - i, i, &needlog, &needscan); @@ -1178,8 +1236,7 @@ xfs_dir2_sf_to_block( /* * Create entry for . */ - dep = (xfs_dir2_data_entry_t *) - ((char *)hdr + XFS_DIR2_DATA_DOT_OFFSET); + dep = xfs_dir3_data_dot_entry_p(hdr); dep->inumber = cpu_to_be64(dp->i_ino); dep->namelen = 1; dep->name[0] = '.'; @@ -1192,8 +1249,7 @@ xfs_dir2_sf_to_block( /* * Create entry for .. */ - dep = (xfs_dir2_data_entry_t *) - ((char *)hdr + XFS_DIR2_DATA_DOTDOT_OFFSET); + dep = xfs_dir3_data_dotdot_entry_p(hdr); dep->inumber = cpu_to_be64(xfs_dir2_sf_get_parent_ino(sfp)); dep->namelen = 2; dep->name[0] = dep->name[1] = '.'; @@ -1203,7 +1259,7 @@ xfs_dir2_sf_to_block( blp[1].hashval = cpu_to_be32(xfs_dir_hash_dotdot); blp[1].address = cpu_to_be32(xfs_dir2_byte_to_dataptr(mp, (char *)dep - (char *)hdr)); - offset = XFS_DIR2_DATA_FIRST_OFFSET; + offset = xfs_dir3_data_first_offset(hdr); /* * Loop over existing entries, stuff them in. */ diff --git a/fs/xfs/xfs_dir2_data.c b/fs/xfs/xfs_dir2_data.c index ffcf177..8484ec4 100644 --- a/fs/xfs/xfs_dir2_data.c +++ b/fs/xfs/xfs_dir2_data.c @@ -1,5 +1,6 @@ /* * Copyright (c) 2000-2002,2005 Silicon Graphics, Inc. + * Copyright (c) 2013 Red Hat, Inc. * All Rights Reserved. * * This program is free software; you can redistribute it and/or @@ -65,10 +66,11 @@ __xfs_dir2_data_check( mp = bp->b_target->bt_mount; hdr = bp->b_addr; - bf = hdr->bestfree; - p = (char *)(hdr + 1); + bf = xfs_dir3_data_bestfree_p(hdr); + p = (char *)xfs_dir3_data_entry_p(hdr); switch (hdr->magic) { + case cpu_to_be32(XFS_DIR3_BLOCK_MAGIC): case cpu_to_be32(XFS_DIR2_BLOCK_MAGIC): btp = xfs_dir2_block_tail_p(mp, hdr); lep = xfs_dir2_block_leaf_p(btp); @@ -148,7 +150,8 @@ __xfs_dir2_data_check( (char *)dep - (char *)hdr); count++; lastfree = 0; - if (hdr->magic == cpu_to_be32(XFS_DIR2_BLOCK_MAGIC)) { + if (hdr->magic == cpu_to_be32(XFS_DIR2_BLOCK_MAGIC) || + hdr->magic == cpu_to_be32(XFS_DIR3_BLOCK_MAGIC)) { addr = xfs_dir2_db_off_to_dataptr(mp, mp->m_dirdatablk, (xfs_dir2_data_aoff_t) ((char *)dep - (char *)hdr)); @@ -168,7 +171,8 @@ __xfs_dir2_data_check( * Need to have seen all the entries and all the bestfree slots. */ XFS_WANT_CORRUPTED_RETURN(freeseen == 7); - if (hdr->magic == cpu_to_be32(XFS_DIR2_BLOCK_MAGIC)) { + if (hdr->magic == cpu_to_be32(XFS_DIR2_BLOCK_MAGIC) || + hdr->magic == cpu_to_be32(XFS_DIR3_BLOCK_MAGIC)) { for (i = stale = 0; i < be32_to_cpu(btp->count); i++) { if (lep[i].address == cpu_to_be32(XFS_DIR2_NULL_DATAPTR)) @@ -216,7 +220,8 @@ xfs_dir2_data_reada_verify( switch (hdr->magic) { case cpu_to_be32(XFS_DIR2_BLOCK_MAGIC): - bp->b_ops = &xfs_dir2_block_buf_ops; + case cpu_to_be32(XFS_DIR3_BLOCK_MAGIC): + bp->b_ops = &xfs_dir3_block_buf_ops; bp->b_ops->verify_read(bp); return; case cpu_to_be32(XFS_DIR2_DATA_MAGIC): @@ -288,12 +293,15 @@ xfs_dir2_data_freefind( { xfs_dir2_data_free_t *dfp; /* bestfree entry */ xfs_dir2_data_aoff_t off; /* offset value needed */ + struct xfs_dir2_data_free *bf; #if defined(DEBUG) && defined(__KERNEL__) int matched; /* matched the value */ int seenzero; /* saw a 0 bestfree entry */ #endif off = (xfs_dir2_data_aoff_t)((char *)dup - (char *)hdr); + bf = xfs_dir3_data_bestfree_p(hdr); + #if defined(DEBUG) && defined(__KERNEL__) /* * Validate some consistency in the bestfree table. @@ -301,9 +309,10 @@ xfs_dir2_data_freefind( * one we're looking for it has to be exact. */ ASSERT(hdr->magic == cpu_to_be32(XFS_DIR2_DATA_MAGIC) || - hdr->magic == cpu_to_be32(XFS_DIR2_BLOCK_MAGIC)); - for (dfp = &hdr->bestfree[0], seenzero = matched = 0; - dfp < &hdr->bestfree[XFS_DIR2_DATA_FD_COUNT]; + hdr->magic == cpu_to_be32(XFS_DIR2_BLOCK_MAGIC) || + hdr->magic == cpu_to_be32(XFS_DIR3_BLOCK_MAGIC)); + for (dfp = &bf[0], seenzero = matched = 0; + dfp < &bf[XFS_DIR2_DATA_FD_COUNT]; dfp++) { if (!dfp->offset) { ASSERT(!dfp->length); @@ -319,7 +328,7 @@ xfs_dir2_data_freefind( else ASSERT(be16_to_cpu(dfp->offset) + be16_to_cpu(dfp->length) <= off); ASSERT(matched || be16_to_cpu(dfp->length) >= be16_to_cpu(dup->length)); - if (dfp > &hdr->bestfree[0]) + if (dfp > &bf[0]) ASSERT(be16_to_cpu(dfp[-1].length) >= be16_to_cpu(dfp[0].length)); } #endif @@ -328,14 +337,12 @@ xfs_dir2_data_freefind( * it can't be there since they're sorted. */ if (be16_to_cpu(dup->length) < - be16_to_cpu(hdr->bestfree[XFS_DIR2_DATA_FD_COUNT - 1].length)) + be16_to_cpu(bf[XFS_DIR2_DATA_FD_COUNT - 1].length)) return NULL; /* * Look at the three bestfree entries for our guy. */ - for (dfp = &hdr->bestfree[0]; - dfp < &hdr->bestfree[XFS_DIR2_DATA_FD_COUNT]; - dfp++) { + for (dfp = &bf[0]; dfp < &bf[XFS_DIR2_DATA_FD_COUNT]; dfp++) { if (!dfp->offset) return NULL; if (be16_to_cpu(dfp->offset) == off) @@ -359,11 +366,12 @@ xfs_dir2_data_freeinsert( xfs_dir2_data_free_t *dfp; /* bestfree table pointer */ xfs_dir2_data_free_t new; /* new bestfree entry */ -#ifdef __KERNEL__ ASSERT(hdr->magic == cpu_to_be32(XFS_DIR2_DATA_MAGIC) || - hdr->magic == cpu_to_be32(XFS_DIR2_BLOCK_MAGIC)); -#endif - dfp = hdr->bestfree; + hdr->magic == cpu_to_be32(XFS_DIR2_BLOCK_MAGIC) || + hdr->magic == cpu_to_be32(XFS_DIR3_DATA_MAGIC) || + hdr->magic == cpu_to_be32(XFS_DIR3_BLOCK_MAGIC)); + + dfp = xfs_dir3_data_bestfree_p(hdr); new.length = dup->length; new.offset = cpu_to_be16((char *)dup - (char *)hdr); @@ -400,32 +408,36 @@ xfs_dir2_data_freeremove( xfs_dir2_data_free_t *dfp, /* bestfree entry pointer */ int *loghead) /* out: log data header */ { -#ifdef __KERNEL__ + struct xfs_dir2_data_free *bf; + ASSERT(hdr->magic == cpu_to_be32(XFS_DIR2_DATA_MAGIC) || - hdr->magic == cpu_to_be32(XFS_DIR2_BLOCK_MAGIC)); -#endif + hdr->magic == cpu_to_be32(XFS_DIR2_BLOCK_MAGIC) || + hdr->magic == cpu_to_be32(XFS_DIR3_DATA_MAGIC) || + hdr->magic == cpu_to_be32(XFS_DIR3_BLOCK_MAGIC)); + /* * It's the first entry, slide the next 2 up. */ - if (dfp == &hdr->bestfree[0]) { - hdr->bestfree[0] = hdr->bestfree[1]; - hdr->bestfree[1] = hdr->bestfree[2]; + bf = xfs_dir3_data_bestfree_p(hdr); + if (dfp == &bf[0]) { + bf[0] = bf[1]; + bf[1] = bf[2]; } /* * It's the second entry, slide the 3rd entry up. */ - else if (dfp == &hdr->bestfree[1]) - hdr->bestfree[1] = hdr->bestfree[2]; + else if (dfp == &bf[1]) + bf[1] = bf[2]; /* * Must be the last entry. */ else - ASSERT(dfp == &hdr->bestfree[2]); + ASSERT(dfp == &bf[2]); /* * Clear the 3rd entry, must be zero now. */ - hdr->bestfree[2].length = 0; - hdr->bestfree[2].offset = 0; + bf[2].length = 0; + bf[2].offset = 0; *loghead = 1; } @@ -441,23 +453,26 @@ xfs_dir2_data_freescan( xfs_dir2_block_tail_t *btp; /* block tail */ xfs_dir2_data_entry_t *dep; /* active data entry */ xfs_dir2_data_unused_t *dup; /* unused data entry */ + struct xfs_dir2_data_free *bf; char *endp; /* end of block's data */ char *p; /* current entry pointer */ -#ifdef __KERNEL__ ASSERT(hdr->magic == cpu_to_be32(XFS_DIR2_DATA_MAGIC) || - hdr->magic == cpu_to_be32(XFS_DIR2_BLOCK_MAGIC)); -#endif + hdr->magic == cpu_to_be32(XFS_DIR2_BLOCK_MAGIC) || + hdr->magic == cpu_to_be32(XFS_DIR3_BLOCK_MAGIC)); + /* * Start by clearing the table. */ - memset(hdr->bestfree, 0, sizeof(hdr->bestfree)); + bf = xfs_dir3_data_bestfree_p(hdr); + memset(bf, 0, sizeof(*bf) * XFS_DIR2_DATA_FD_COUNT); *loghead = 1; /* * Set up pointers. */ - p = (char *)(hdr + 1); - if (hdr->magic == cpu_to_be32(XFS_DIR2_BLOCK_MAGIC)) { + p = (char *)xfs_dir3_data_entry_p(hdr); + if (hdr->magic == cpu_to_be32(XFS_DIR2_BLOCK_MAGIC) || + hdr->magic == cpu_to_be32(XFS_DIR3_BLOCK_MAGIC)) { btp = xfs_dir2_block_tail_p(mp, hdr); endp = (char *)xfs_dir2_block_leaf_p(btp); } else @@ -493,7 +508,7 @@ xfs_dir2_data_freescan( * Give back the buffer for the created block. */ int /* error */ -xfs_dir2_data_init( +xfs_dir3_data_init( xfs_da_args_t *args, /* directory operation args */ xfs_dir2_db_t blkno, /* logical dir block number */ struct xfs_buf **bpp) /* output block buffer */ @@ -502,6 +517,7 @@ xfs_dir2_data_init( xfs_dir2_data_hdr_t *hdr; /* data block header */ xfs_inode_t *dp; /* incore directory inode */ xfs_dir2_data_unused_t *dup; /* unused entry pointer */ + struct xfs_dir2_data_free *bf; int error; /* error return value */ int i; /* bestfree index */ xfs_mount_t *mp; /* filesystem mount point */ @@ -524,21 +540,34 @@ xfs_dir2_data_init( * Initialize the header. */ hdr = bp->b_addr; - hdr->magic = cpu_to_be32(XFS_DIR2_DATA_MAGIC); - hdr->bestfree[0].offset = cpu_to_be16(sizeof(*hdr)); + + if (xfs_sb_version_hascrc(&mp->m_sb)) { + struct xfs_dir3_blk_hdr *hdr3 = bp->b_addr; + + memset(hdr3, 0, sizeof(*hdr3)); + hdr3->magic = cpu_to_be32(XFS_DIR3_DATA_MAGIC); + hdr3->blkno = cpu_to_be64(bp->b_bn); + hdr3->owner = cpu_to_be64(dp->i_ino); + uuid_copy(&hdr3->uuid, &mp->m_sb.sb_uuid); + + } else + hdr->magic = cpu_to_be32(XFS_DIR2_DATA_MAGIC); + + bf = xfs_dir3_data_bestfree_p(hdr); + bf[0].offset = cpu_to_be16(xfs_dir3_data_entry_offset(hdr)); for (i = 1; i < XFS_DIR2_DATA_FD_COUNT; i++) { - hdr->bestfree[i].length = 0; - hdr->bestfree[i].offset = 0; + bf[i].length = 0; + bf[i].offset = 0; } /* * Set up an unused entry for the block's body. */ - dup = (xfs_dir2_data_unused_t *)(hdr + 1); + dup = xfs_dir3_data_unused_p(hdr); dup->freetag = cpu_to_be16(XFS_DIR2_DATA_FREE_TAG); - t = mp->m_dirblksize - (uint)sizeof(*hdr); - hdr->bestfree[0].length = cpu_to_be16(t); + t = mp->m_dirblksize - (uint)xfs_dir3_data_entry_offset(hdr); + bf[0].length = cpu_to_be16(t); dup->length = cpu_to_be16(t); *xfs_dir2_data_unused_tag_p(dup) = cpu_to_be16((char *)dup - (char *)hdr); /* @@ -562,7 +591,8 @@ xfs_dir2_data_log_entry( xfs_dir2_data_hdr_t *hdr = bp->b_addr; ASSERT(hdr->magic == cpu_to_be32(XFS_DIR2_DATA_MAGIC) || - hdr->magic == cpu_to_be32(XFS_DIR2_BLOCK_MAGIC)); + hdr->magic == cpu_to_be32(XFS_DIR2_BLOCK_MAGIC) || + hdr->magic == cpu_to_be32(XFS_DIR3_BLOCK_MAGIC)); xfs_trans_log_buf(tp, bp, (uint)((char *)dep - (char *)hdr), (uint)((char *)(xfs_dir2_data_entry_tag_p(dep) + 1) - @@ -580,9 +610,10 @@ xfs_dir2_data_log_header( xfs_dir2_data_hdr_t *hdr = bp->b_addr; ASSERT(hdr->magic == cpu_to_be32(XFS_DIR2_DATA_MAGIC) || - hdr->magic == cpu_to_be32(XFS_DIR2_BLOCK_MAGIC)); + hdr->magic == cpu_to_be32(XFS_DIR2_BLOCK_MAGIC) || + hdr->magic == cpu_to_be32(XFS_DIR3_BLOCK_MAGIC)); - xfs_trans_log_buf(tp, bp, 0, sizeof(*hdr) - 1); + xfs_trans_log_buf(tp, bp, 0, xfs_dir3_data_entry_offset(hdr) - 1); } /* @@ -597,7 +628,8 @@ xfs_dir2_data_log_unused( xfs_dir2_data_hdr_t *hdr = bp->b_addr; ASSERT(hdr->magic == cpu_to_be32(XFS_DIR2_DATA_MAGIC) || - hdr->magic == cpu_to_be32(XFS_DIR2_BLOCK_MAGIC)); + hdr->magic == cpu_to_be32(XFS_DIR2_BLOCK_MAGIC) || + hdr->magic == cpu_to_be32(XFS_DIR3_BLOCK_MAGIC)); /* * Log the first part of the unused entry. @@ -635,6 +667,7 @@ xfs_dir2_data_make_free( xfs_dir2_data_unused_t *newdup; /* new unused entry */ xfs_dir2_data_unused_t *postdup; /* unused entry after us */ xfs_dir2_data_unused_t *prevdup; /* unused entry before us */ + struct xfs_dir2_data_free *bf; mp = tp->t_mountp; hdr = bp->b_addr; @@ -647,7 +680,8 @@ xfs_dir2_data_make_free( else { xfs_dir2_block_tail_t *btp; /* block tail */ - ASSERT(hdr->magic == cpu_to_be32(XFS_DIR2_BLOCK_MAGIC)); + ASSERT(hdr->magic == cpu_to_be32(XFS_DIR2_BLOCK_MAGIC) || + hdr->magic == cpu_to_be32(XFS_DIR3_BLOCK_MAGIC)); btp = xfs_dir2_block_tail_p(mp, hdr); endptr = (char *)xfs_dir2_block_leaf_p(btp); } @@ -655,7 +689,7 @@ xfs_dir2_data_make_free( * If this isn't the start of the block, then back up to * the previous entry and see if it's free. */ - if (offset > sizeof(*hdr)) { + if (offset > xfs_dir3_data_entry_offset(hdr)) { __be16 *tagp; /* tag just before us */ tagp = (__be16 *)((char *)hdr + offset) - 1; @@ -681,6 +715,7 @@ xfs_dir2_data_make_free( * Previous and following entries are both free, * merge everything into a single free entry. */ + bf = xfs_dir3_data_bestfree_p(hdr); if (prevdup && postdup) { xfs_dir2_data_free_t *dfp2; /* another bestfree pointer */ @@ -695,7 +730,7 @@ xfs_dir2_data_make_free( * since the third bestfree is there, there might be more * entries. */ - needscan = (hdr->bestfree[2].length != 0); + needscan = (bf[2].length != 0); /* * Fix up the new big freespace. */ @@ -711,10 +746,10 @@ xfs_dir2_data_make_free( * Remove entry 1 first then entry 0. */ ASSERT(dfp && dfp2); - if (dfp == &hdr->bestfree[1]) { - dfp = &hdr->bestfree[0]; + if (dfp == &bf[1]) { + dfp = &bf[0]; ASSERT(dfp2 == dfp); - dfp2 = &hdr->bestfree[1]; + dfp2 = &bf[1]; } xfs_dir2_data_freeremove(hdr, dfp2, needlogp); xfs_dir2_data_freeremove(hdr, dfp, needlogp); @@ -722,7 +757,7 @@ xfs_dir2_data_make_free( * Now insert the new entry. */ dfp = xfs_dir2_data_freeinsert(hdr, prevdup, needlogp); - ASSERT(dfp == &hdr->bestfree[0]); + ASSERT(dfp == &bf[0]); ASSERT(dfp->length == prevdup->length); ASSERT(!dfp[1].length); ASSERT(!dfp[2].length); @@ -751,7 +786,7 @@ xfs_dir2_data_make_free( */ else { needscan = be16_to_cpu(prevdup->length) > - be16_to_cpu(hdr->bestfree[2].length); + be16_to_cpu(bf[2].length); } } /* @@ -779,7 +814,7 @@ xfs_dir2_data_make_free( */ else { needscan = be16_to_cpu(newdup->length) > - be16_to_cpu(hdr->bestfree[2].length); + be16_to_cpu(bf[2].length); } } /* @@ -818,10 +853,12 @@ xfs_dir2_data_use_free( xfs_dir2_data_unused_t *newdup; /* new unused entry */ xfs_dir2_data_unused_t *newdup2; /* another new unused entry */ int oldlen; /* old unused entry's length */ + struct xfs_dir2_data_free *bf; hdr = bp->b_addr; ASSERT(hdr->magic == cpu_to_be32(XFS_DIR2_DATA_MAGIC) || - hdr->magic == cpu_to_be32(XFS_DIR2_BLOCK_MAGIC)); + hdr->magic == cpu_to_be32(XFS_DIR2_BLOCK_MAGIC) || + hdr->magic == cpu_to_be32(XFS_DIR3_BLOCK_MAGIC)); ASSERT(be16_to_cpu(dup->freetag) == XFS_DIR2_DATA_FREE_TAG); ASSERT(offset >= (char *)dup - (char *)hdr); ASSERT(offset + len <= (char *)dup + be16_to_cpu(dup->length) - (char *)hdr); @@ -831,7 +868,8 @@ xfs_dir2_data_use_free( */ dfp = xfs_dir2_data_freefind(hdr, dup); oldlen = be16_to_cpu(dup->length); - ASSERT(dfp || oldlen <= be16_to_cpu(hdr->bestfree[2].length)); + bf = xfs_dir3_data_bestfree_p(hdr); + ASSERT(dfp || oldlen <= be16_to_cpu(bf[2].length)); /* * Check for alignment with front and back of the entry. */ @@ -845,7 +883,7 @@ xfs_dir2_data_use_free( */ if (matchfront && matchback) { if (dfp) { - needscan = (hdr->bestfree[2].offset != 0); + needscan = (bf[2].offset != 0); if (!needscan) xfs_dir2_data_freeremove(hdr, dfp, needlogp); } @@ -875,7 +913,7 @@ xfs_dir2_data_use_free( * that means we don't know if there was a better * choice for the last slot, or not. Rescan. */ - needscan = dfp == &hdr->bestfree[2]; + needscan = dfp == &bf[2]; } } /* @@ -902,7 +940,7 @@ xfs_dir2_data_use_free( * that means we don't know if there was a better * choice for the last slot, or not. Rescan. */ - needscan = dfp == &hdr->bestfree[2]; + needscan = dfp == &bf[2]; } } /* @@ -930,7 +968,7 @@ xfs_dir2_data_use_free( * the 2 new will work. */ if (dfp) { - needscan = (hdr->bestfree[2].length != 0); + needscan = (bf[2].length != 0); if (!needscan) { xfs_dir2_data_freeremove(hdr, dfp, needlogp); xfs_dir2_data_freeinsert(hdr, newdup, needlogp); diff --git a/fs/xfs/xfs_dir2_format.h b/fs/xfs/xfs_dir2_format.h index 0727098..7dc26b0 100644 --- a/fs/xfs/xfs_dir2_format.h +++ b/fs/xfs/xfs_dir2_format.h @@ -1,5 +1,6 @@ /* * Copyright (c) 2000-2001,2005 Silicon Graphics, Inc. + * Copyright (c) 2013 Red Hat, Inc. * All Rights Reserved. * * This program is free software; you can redistribute it and/or @@ -36,6 +37,37 @@ #define XFS_DIR2_FREE_MAGIC 0x58443246 /* XD2F: free index blocks */ /* + * Directory Version 3 With CRCs. + * + * The tree formats are the same as for version 2 directories. The difference + * is in the block header and dirent formats. In many cases the v3 structures + * use v2 definitions as they are no different and this makes code sharing much + * easier. + * + * Also, the xfs_dir3_*() functions handle both v2 and v3 formats - if the + * format is v2 then they switch to the existing v2 code, or the format is v3 + * they implement the v3 functionality. This means the existing dir2 is a mix of + * xfs_dir2/xfs_dir3 calls and functions. The xfs_dir3 functions are called + * where there is a difference in the formats, otherwise the code is unchanged. + * + * Where it is possible, the code decides what to do based on the magic numbers + * in the blocks rather than feature bits in the superblock. This means the code + * is as independent of the external XFS code as possible as doesn't require + * passing struct xfs_mount pointers into places where it isn't really + * necessary. + * + * Version 3 includes: + * + * - a larger block header for CRC and identification purposes and so the + * offsets of all the structures inside the blocks are different. + * + * - new magic numbers to be able to detect the v2/v3 types on the fly. + */ + +#define XFS_DIR3_BLOCK_MAGIC 0x58444233 /* XDB3: single block dirs */ +#define XFS_DIR3_DATA_MAGIC 0x58444433 /* XDD3: multiblock dirs */ + +/* * Byte offset in data block and shortform entry. */ typedef __uint16_t xfs_dir2_data_off_t; @@ -117,19 +149,19 @@ static inline int xfs_dir2_sf_hdr_size(int i8count) (sizeof(xfs_dir2_ino8_t) - sizeof(xfs_dir2_ino4_t)); } -static inline xfs_dir2_data_aoff_t + static inline xfs_dir2_data_aoff_t xfs_dir2_sf_get_offset(xfs_dir2_sf_entry_t *sfep) { return get_unaligned_be16(&sfep->offset.i); } -static inline void + static inline void xfs_dir2_sf_put_offset(xfs_dir2_sf_entry_t *sfep, xfs_dir2_data_aoff_t off) { put_unaligned_be16(off, &sfep->offset.i); } -static inline int + static inline int xfs_dir2_sf_entsize(struct xfs_dir2_sf_hdr *hdr, int len) { return sizeof(struct xfs_dir2_sf_entry) + /* namelen + offset */ @@ -139,14 +171,14 @@ xfs_dir2_sf_entsize(struct xfs_dir2_sf_hdr *hdr, int len) sizeof(xfs_dir2_ino4_t)); } -static inline struct xfs_dir2_sf_entry * + static inline struct xfs_dir2_sf_entry * xfs_dir2_sf_firstentry(struct xfs_dir2_sf_hdr *hdr) { return (struct xfs_dir2_sf_entry *) ((char *)hdr + xfs_dir2_sf_hdr_size(hdr->i8count)); } -static inline struct xfs_dir2_sf_entry * + static inline struct xfs_dir2_sf_entry * xfs_dir2_sf_nextentry(struct xfs_dir2_sf_hdr *hdr, struct xfs_dir2_sf_entry *sfep) { @@ -221,11 +253,43 @@ typedef struct xfs_dir2_data_free { */ typedef struct xfs_dir2_data_hdr { __be32 magic; /* XFS_DIR2_DATA_MAGIC or */ - /* XFS_DIR2_BLOCK_MAGIC */ + /* XFS_DIR2_BLOCK_MAGIC */ xfs_dir2_data_free_t bestfree[XFS_DIR2_DATA_FD_COUNT]; } xfs_dir2_data_hdr_t; /* + * define a structure for all the verification fields we are adding to the + * directory block structures. This will be used in several structures. + * The magic number must be the first entry to align with all the dir2 + * structures so we determine how to decode them just by the magic number. + */ +struct xfs_dir3_blk_hdr { + __be32 magic; /* magic number */ + __be32 crc; /* CRC of block */ + __be64 blkno; /* first block of the buffer */ + __be64 lsn; /* sequence number of last write */ + uuid_t uuid; /* filesystem we belong to */ + __be64 owner; /* inode that owns the block */ +}; + +struct xfs_dir3_data_hdr { + struct xfs_dir3_blk_hdr hdr; + xfs_dir2_data_free_t best_free[XFS_DIR2_DATA_FD_COUNT]; +}; + +#define XFS_DIR3_DATA_CRC_OFF offsetof(struct xfs_dir3_data_hdr, hdr.crc) + + static inline struct xfs_dir2_data_free * +xfs_dir3_data_bestfree_p(struct xfs_dir2_data_hdr *hdr) +{ + if (hdr->magic == cpu_to_be32(XFS_DIR3_BLOCK_MAGIC)) { + struct xfs_dir3_data_hdr *hdr3 = (struct xfs_dir3_data_hdr *)hdr; + return hdr3->best_free; + } + return hdr->bestfree; +} + +/* * Active entry in a data block. * * Aligned to 8 bytes. After the variable length name field there is a @@ -280,6 +344,85 @@ xfs_dir2_data_unused_tag_p(struct xfs_dir2_data_unused *dup) be16_to_cpu(dup->length) - sizeof(__be16)); } +static inline struct xfs_dir2_data_unused * +xfs_dir3_data_unused_p(struct xfs_dir2_data_hdr *hdr) +{ + if (hdr->magic == cpu_to_be32(XFS_DIR3_BLOCK_MAGIC)) { + return (struct xfs_dir2_data_unused *) + ((char *)hdr + sizeof(struct xfs_dir3_data_hdr)); + } + return (struct xfs_dir2_data_unused *) + ((char *)hdr + sizeof(struct xfs_dir2_data_hdr)); +} + +static inline size_t +xfs_dir3_data_hdr_size(bool dir3) +{ + if (dir3) + return sizeof(struct xfs_dir3_data_hdr); + return sizeof(struct xfs_dir2_data_hdr); +} + +static inline size_t +xfs_dir3_data_entry_offset(struct xfs_dir2_data_hdr *hdr) +{ + bool dir3 = hdr->magic == cpu_to_be32(XFS_DIR3_DATA_MAGIC) || + hdr->magic == cpu_to_be32(XFS_DIR3_BLOCK_MAGIC); + return xfs_dir3_data_hdr_size(dir3); +} + +static inline struct xfs_dir2_data_entry * +xfs_dir3_data_entry_p(struct xfs_dir2_data_hdr *hdr) +{ + return (struct xfs_dir2_data_entry *) + ((char *)hdr + xfs_dir3_data_entry_offset(hdr)); +} + +/* + * Offsets of . and .. in data space (always block 0) + */ +static inline xfs_dir2_data_aoff_t +xfs_dir3_data_dot_offset(struct xfs_dir2_data_hdr *hdr) +{ + return xfs_dir3_data_entry_offset(hdr); +} + +static inline xfs_dir2_data_aoff_t +xfs_dir3_data_dotdot_offset(struct xfs_dir2_data_hdr *hdr) +{ + return xfs_dir3_data_dot_offset(hdr) + xfs_dir2_data_entsize(1); +} + +static inline xfs_dir2_data_aoff_t +xfs_dir3_data_first_offset(struct xfs_dir2_data_hdr *hdr) +{ + return xfs_dir3_data_dotdot_offset(hdr) + xfs_dir2_data_entsize(2); +} + +/* + * location of . and .. in data space (always block 0) + */ +static inline struct xfs_dir2_data_entry * +xfs_dir3_data_dot_entry_p(struct xfs_dir2_data_hdr *hdr) +{ + return (struct xfs_dir2_data_entry *) + ((char *)hdr + xfs_dir3_data_dot_offset(hdr)); +} + +static inline struct xfs_dir2_data_entry * +xfs_dir3_data_dotdot_entry_p(struct xfs_dir2_data_hdr *hdr) +{ + return (struct xfs_dir2_data_entry *) + ((char *)hdr + xfs_dir3_data_dotdot_offset(hdr)); +} + +static inline struct xfs_dir2_data_entry * +xfs_dir3_data_first_entry_p(struct xfs_dir2_data_hdr *hdr) +{ + return (struct xfs_dir2_data_entry *) + ((char *)hdr + xfs_dir3_data_first_offset(hdr)); +} + /* * Leaf block structures. * diff --git a/fs/xfs/xfs_dir2_leaf.c b/fs/xfs/xfs_dir2_leaf.c index 60cd2fa..ef163f0 100644 --- a/fs/xfs/xfs_dir2_leaf.c +++ b/fs/xfs/xfs_dir2_leaf.c @@ -149,6 +149,7 @@ xfs_dir2_block_to_leaf( int needlog; /* need to log block header */ int needscan; /* need to rescan bestfree */ xfs_trans_t *tp; /* transaction pointer */ + struct xfs_dir2_data_free *bf; trace_xfs_dir2_block_to_leaf(args); @@ -177,6 +178,7 @@ xfs_dir2_block_to_leaf( xfs_dir2_data_check(dp, dbp); btp = xfs_dir2_block_tail_p(mp, hdr); blp = xfs_dir2_block_leaf_p(btp); + bf = xfs_dir3_data_bestfree_p(hdr); /* * Set the counts in the leaf header. */ @@ -212,7 +214,7 @@ xfs_dir2_block_to_leaf( ltp = xfs_dir2_leaf_tail_p(mp, leaf); ltp->bestcount = cpu_to_be32(1); bestsp = xfs_dir2_leaf_bests_p(ltp); - bestsp[0] = hdr->bestfree[0].length; + bestsp[0] = bf[0].length; /* * Log the data header and leaf bests table. */ @@ -544,7 +546,7 @@ xfs_dir2_leaf_addname( /* * Initialize the block. */ - if ((error = xfs_dir2_data_init(args, use_block, &dbp))) { + if ((error = xfs_dir3_data_init(args, use_block, &dbp))) { xfs_trans_brelse(tp, lbp); return error; } diff --git a/fs/xfs/xfs_dir2_node.c b/fs/xfs/xfs_dir2_node.c index 5980f9b..985d70b 100644 --- a/fs/xfs/xfs_dir2_node.c +++ b/fs/xfs/xfs_dir2_node.c @@ -1588,7 +1588,7 @@ xfs_dir2_node_addname_int( if (unlikely((error = xfs_dir2_grow_inode(args, XFS_DIR2_DATA_SPACE, &dbno)) || - (error = xfs_dir2_data_init(args, dbno, &dbp)))) + (error = xfs_dir3_data_init(args, dbno, &dbp)))) return error; /* diff --git a/fs/xfs/xfs_dir2_priv.h b/fs/xfs/xfs_dir2_priv.h index 7da79f6..e6f2e0a 100644 --- a/fs/xfs/xfs_dir2_priv.h +++ b/fs/xfs/xfs_dir2_priv.h @@ -30,7 +30,7 @@ extern int xfs_dir_cilookup_result(struct xfs_da_args *args, const unsigned char *name, int len); /* xfs_dir2_block.c */ -extern const struct xfs_buf_ops xfs_dir2_block_buf_ops; +extern const struct xfs_buf_ops xfs_dir3_block_buf_ops; extern int xfs_dir2_block_addname(struct xfs_da_args *args); extern int xfs_dir2_block_getdents(struct xfs_inode *dp, void *dirent, @@ -61,7 +61,7 @@ xfs_dir2_data_freeinsert(struct xfs_dir2_data_hdr *hdr, struct xfs_dir2_data_unused *dup, int *loghead); extern void xfs_dir2_data_freescan(struct xfs_mount *mp, struct xfs_dir2_data_hdr *hdr, int *loghead); -extern int xfs_dir2_data_init(struct xfs_da_args *args, xfs_dir2_db_t blkno, +extern int xfs_dir3_data_init(struct xfs_da_args *args, xfs_dir2_db_t blkno, struct xfs_buf **bpp); extern void xfs_dir2_data_log_entry(struct xfs_trans *tp, struct xfs_buf *bp, struct xfs_dir2_data_entry *dep); diff --git a/fs/xfs/xfs_dir2_sf.c b/fs/xfs/xfs_dir2_sf.c index 1b9fc3e..b975622 100644 --- a/fs/xfs/xfs_dir2_sf.c +++ b/fs/xfs/xfs_dir2_sf.c @@ -278,7 +278,7 @@ xfs_dir2_block_to_sf( * Set up to loop over the block's entries. */ btp = xfs_dir2_block_tail_p(mp, hdr); - ptr = (char *)(hdr + 1); + ptr = (char *)xfs_dir3_data_entry_p(hdr); endptr = (char *)xfs_dir2_block_leaf_p(btp); sfep = xfs_dir2_sf_firstentry(sfp); /* diff --git a/fs/xfs/xfs_log_recover.c b/fs/xfs/xfs_log_recover.c index 352d794..542aa1e 100644 --- a/fs/xfs/xfs_log_recover.c +++ b/fs/xfs/xfs_log_recover.c @@ -1876,6 +1876,7 @@ xlog_recover_do_reg_buffer( int bit; int nbits; int error; + struct xfs_da_blkinfo *info; trace_xfs_log_recover_buf_reg_buf(mp->m_log, buf_f); @@ -1935,6 +1936,7 @@ xlog_recover_do_reg_buffer( /* Shouldn't be any more regions */ ASSERT(i == item->ri_total); + info = bp->b_addr; switch (buf_f->blf_flags & XFS_BLF_TYPE_MASK) { case XFS_BLF_BTREE_BUF: switch (be32_to_cpu(*(__be32 *)bp->b_addr)) { -- 1.7.10.4 From dave@fromorbit.com Tue Mar 12 07:31:37 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 06FAC7FBE for ; Tue, 12 Mar 2013 07:31:37 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay2.corp.sgi.com (Postfix) with ESMTP id E6CBB304048 for ; Tue, 12 Mar 2013 05:31:36 -0700 (PDT) X-ASG-Debug-ID: 1363091485-04cb6c2b01493060003-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id DuCl8XqTLnvFBew1 for ; Tue, 12 Mar 2013 05:31:34 -0700 (PDT) X-Barracuda-Envelope-From: dave@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: Ag8KAKEfP1F5LKiV/2dsb2JhbABDxF0DAYFJF3SCKAEBBScvMwgYMTkDGxmIErACkB+ODHaDUgOnSoMeKA Received: from ppp121-44-168-149.lns20.syd7.internode.on.net (HELO dastard) ([121.44.168.149]) by ipmail05.adl6.internode.on.net with ESMTP; 12 Mar 2013 23:01:30 +1030 Received: from disappointment ([192.168.1.1]) by dastard with esmtp (Exim 4.76) (envelope-from ) id 1UFOMa-0001SY-Mw for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:31:28 +1100 Received: from dave by disappointment with local (Exim 4.80) (envelope-from ) id 1UFOMQ-0002N1-Jm for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:31:18 +1100 From: Dave Chinner To: xfs@oss.sgi.com Subject: [PATCH 18/21] xfs: split remote attribute code out Date: Tue, 12 Mar 2013 23:30:51 +1100 X-ASG-Orig-Subj: [PATCH 18/21] xfs: split remote attribute code out Message-Id: <1363091454-8852-19-git-send-email-david@fromorbit.com> X-Mailer: git-send-email 1.7.10.4 In-Reply-To: <1363091454-8852-1-git-send-email-david@fromorbit.com> References: <1363091454-8852-1-git-send-email-david@fromorbit.com> X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1363091490 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124988 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- From: Dave Chinner Adding CRC support to remote attributes adds a significant amount of remote attribute specific code. Split the existing remote attribute code out into it's own file so that all the relevant remote attribute code is in a single, easy to find place. Signed-off-by: Dave Chinner --- fs/xfs/Makefile | 1 + fs/xfs/xfs_attr.c | 298 +---------------------------------------- fs/xfs/xfs_attr.h | 1 - fs/xfs/xfs_attr_leaf.c | 1 + fs/xfs/xfs_attr_remote.c | 328 ++++++++++++++++++++++++++++++++++++++++++++++ fs/xfs/xfs_attr_remote.h | 25 ++++ 6 files changed, 356 insertions(+), 298 deletions(-) create mode 100644 fs/xfs/xfs_attr_remote.c create mode 100644 fs/xfs/xfs_attr_remote.h diff --git a/fs/xfs/Makefile b/fs/xfs/Makefile index 062f25c..6313b69 100644 --- a/fs/xfs/Makefile +++ b/fs/xfs/Makefile @@ -58,6 +58,7 @@ xfs-y += xfs_alloc.o \ xfs_alloc_btree.o \ xfs_attr.o \ xfs_attr_leaf.o \ + xfs_attr_remote.o \ xfs_bmap.o \ xfs_bmap_btree.o \ xfs_btree.o \ diff --git a/fs/xfs/xfs_attr.c b/fs/xfs/xfs_attr.c index de4093f..449a240 100644 --- a/fs/xfs/xfs_attr.c +++ b/fs/xfs/xfs_attr.c @@ -35,6 +35,7 @@ #include "xfs_bmap.h" #include "xfs_attr.h" #include "xfs_attr_leaf.h" +#include "xfs_attr_remote.h" #include "xfs_quota.h" #include "xfs_trans_space.h" #include "xfs_vnodeops.h" @@ -73,13 +74,6 @@ STATIC int xfs_attr_node_list(xfs_attr_list_context_t *context); STATIC int xfs_attr_fillstate(xfs_da_state_t *state); STATIC int xfs_attr_refillstate(xfs_da_state_t *state); -/* - * Routines to manipulate out-of-line attribute values. - */ -STATIC int xfs_attr_rmtval_set(xfs_da_args_t *args); -STATIC int xfs_attr_rmtval_remove(xfs_da_args_t *args); - -#define ATTR_RMTVALUE_MAPSIZE 1 /* # of map entries at once */ STATIC int xfs_attr_name_to_xname( @@ -1926,293 +1920,3 @@ xfs_attr_node_list(xfs_attr_list_context_t *context) xfs_trans_brelse(NULL, bp); return 0; } - - -/*======================================================================== - * External routines for manipulating out-of-line attribute values. - *========================================================================*/ - -/* - * Read the value associated with an attribute from the out-of-line buffer - * that we stored it in. - */ -int -xfs_attr_rmtval_get(xfs_da_args_t *args) -{ - xfs_bmbt_irec_t map[ATTR_RMTVALUE_MAPSIZE]; - xfs_mount_t *mp; - xfs_daddr_t dblkno; - void *dst; - xfs_buf_t *bp; - int nmap, error, tmp, valuelen, blkcnt, i; - xfs_dablk_t lblkno; - - trace_xfs_attr_rmtval_get(args); - - ASSERT(!(args->flags & ATTR_KERNOVAL)); - - mp = args->dp->i_mount; - dst = args->value; - valuelen = args->valuelen; - lblkno = args->rmtblkno; - while (valuelen > 0) { - nmap = ATTR_RMTVALUE_MAPSIZE; - error = xfs_bmapi_read(args->dp, (xfs_fileoff_t)lblkno, - args->rmtblkcnt, map, &nmap, - XFS_BMAPI_ATTRFORK); - if (error) - return(error); - ASSERT(nmap >= 1); - - for (i = 0; (i < nmap) && (valuelen > 0); i++) { - ASSERT((map[i].br_startblock != DELAYSTARTBLOCK) && - (map[i].br_startblock != HOLESTARTBLOCK)); - dblkno = XFS_FSB_TO_DADDR(mp, map[i].br_startblock); - blkcnt = XFS_FSB_TO_BB(mp, map[i].br_blockcount); - error = xfs_trans_read_buf(mp, NULL, mp->m_ddev_targp, - dblkno, blkcnt, 0, &bp, NULL); - if (error) - return(error); - - tmp = min_t(int, valuelen, BBTOB(bp->b_length)); - xfs_buf_iomove(bp, 0, tmp, dst, XBRW_READ); - xfs_buf_relse(bp); - dst += tmp; - valuelen -= tmp; - - lblkno += map[i].br_blockcount; - } - } - ASSERT(valuelen == 0); - return(0); -} - -/* - * Write the value associated with an attribute into the out-of-line buffer - * that we have defined for it. - */ -STATIC int -xfs_attr_rmtval_set(xfs_da_args_t *args) -{ - xfs_mount_t *mp; - xfs_fileoff_t lfileoff; - xfs_inode_t *dp; - xfs_bmbt_irec_t map; - xfs_daddr_t dblkno; - void *src; - xfs_buf_t *bp; - xfs_dablk_t lblkno; - int blkcnt, valuelen, nmap, error, tmp, committed; - - trace_xfs_attr_rmtval_set(args); - - dp = args->dp; - mp = dp->i_mount; - src = args->value; - - /* - * Find a "hole" in the attribute address space large enough for - * us to drop the new attribute's value into. - */ - blkcnt = XFS_B_TO_FSB(mp, args->valuelen); - lfileoff = 0; - error = xfs_bmap_first_unused(args->trans, args->dp, blkcnt, &lfileoff, - XFS_ATTR_FORK); - if (error) { - return(error); - } - args->rmtblkno = lblkno = (xfs_dablk_t)lfileoff; - args->rmtblkcnt = blkcnt; - - /* - * Roll through the "value", allocating blocks on disk as required. - */ - while (blkcnt > 0) { - /* - * Allocate a single extent, up to the size of the value. - */ - xfs_bmap_init(args->flist, args->firstblock); - nmap = 1; - error = xfs_bmapi_write(args->trans, dp, (xfs_fileoff_t)lblkno, - blkcnt, - XFS_BMAPI_ATTRFORK | XFS_BMAPI_METADATA, - args->firstblock, args->total, &map, &nmap, - args->flist); - if (!error) { - error = xfs_bmap_finish(&args->trans, args->flist, - &committed); - } - if (error) { - ASSERT(committed); - args->trans = NULL; - xfs_bmap_cancel(args->flist); - return(error); - } - - /* - * bmap_finish() may have committed the last trans and started - * a new one. We need the inode to be in all transactions. - */ - if (committed) - xfs_trans_ijoin(args->trans, dp, 0); - - ASSERT(nmap == 1); - ASSERT((map.br_startblock != DELAYSTARTBLOCK) && - (map.br_startblock != HOLESTARTBLOCK)); - lblkno += map.br_blockcount; - blkcnt -= map.br_blockcount; - - /* - * Start the next trans in the chain. - */ - error = xfs_trans_roll(&args->trans, dp); - if (error) - return (error); - } - - /* - * Roll through the "value", copying the attribute value to the - * already-allocated blocks. Blocks are written synchronously - * so that we can know they are all on disk before we turn off - * the INCOMPLETE flag. - */ - lblkno = args->rmtblkno; - valuelen = args->valuelen; - while (valuelen > 0) { - int buflen; - - /* - * Try to remember where we decided to put the value. - */ - xfs_bmap_init(args->flist, args->firstblock); - nmap = 1; - error = xfs_bmapi_read(dp, (xfs_fileoff_t)lblkno, - args->rmtblkcnt, &map, &nmap, - XFS_BMAPI_ATTRFORK); - if (error) - return(error); - ASSERT(nmap == 1); - ASSERT((map.br_startblock != DELAYSTARTBLOCK) && - (map.br_startblock != HOLESTARTBLOCK)); - - dblkno = XFS_FSB_TO_DADDR(mp, map.br_startblock), - blkcnt = XFS_FSB_TO_BB(mp, map.br_blockcount); - - bp = xfs_buf_get(mp->m_ddev_targp, dblkno, blkcnt, 0); - if (!bp) - return ENOMEM; - - buflen = BBTOB(bp->b_length); - tmp = min_t(int, valuelen, buflen); - xfs_buf_iomove(bp, 0, tmp, src, XBRW_WRITE); - if (tmp < buflen) - xfs_buf_zero(bp, tmp, buflen - tmp); - - error = xfs_bwrite(bp); /* GROT: NOTE: synchronous write */ - xfs_buf_relse(bp); - if (error) - return error; - src += tmp; - valuelen -= tmp; - - lblkno += map.br_blockcount; - } - ASSERT(valuelen == 0); - return(0); -} - -/* - * Remove the value associated with an attribute by deleting the - * out-of-line buffer that it is stored on. - */ -STATIC int -xfs_attr_rmtval_remove(xfs_da_args_t *args) -{ - xfs_mount_t *mp; - xfs_bmbt_irec_t map; - xfs_buf_t *bp; - xfs_daddr_t dblkno; - xfs_dablk_t lblkno; - int valuelen, blkcnt, nmap, error, done, committed; - - trace_xfs_attr_rmtval_remove(args); - - mp = args->dp->i_mount; - - /* - * Roll through the "value", invalidating the attribute value's - * blocks. - */ - lblkno = args->rmtblkno; - valuelen = args->rmtblkcnt; - while (valuelen > 0) { - /* - * Try to remember where we decided to put the value. - */ - nmap = 1; - error = xfs_bmapi_read(args->dp, (xfs_fileoff_t)lblkno, - args->rmtblkcnt, &map, &nmap, - XFS_BMAPI_ATTRFORK); - if (error) - return(error); - ASSERT(nmap == 1); - ASSERT((map.br_startblock != DELAYSTARTBLOCK) && - (map.br_startblock != HOLESTARTBLOCK)); - - dblkno = XFS_FSB_TO_DADDR(mp, map.br_startblock), - blkcnt = XFS_FSB_TO_BB(mp, map.br_blockcount); - - /* - * If the "remote" value is in the cache, remove it. - */ - bp = xfs_incore(mp->m_ddev_targp, dblkno, blkcnt, XBF_TRYLOCK); - if (bp) { - xfs_buf_stale(bp); - xfs_buf_relse(bp); - bp = NULL; - } - - valuelen -= map.br_blockcount; - - lblkno += map.br_blockcount; - } - - /* - * Keep de-allocating extents until the remote-value region is gone. - */ - lblkno = args->rmtblkno; - blkcnt = args->rmtblkcnt; - done = 0; - while (!done) { - xfs_bmap_init(args->flist, args->firstblock); - error = xfs_bunmapi(args->trans, args->dp, lblkno, blkcnt, - XFS_BMAPI_ATTRFORK | XFS_BMAPI_METADATA, - 1, args->firstblock, args->flist, - &done); - if (!error) { - error = xfs_bmap_finish(&args->trans, args->flist, - &committed); - } - if (error) { - ASSERT(committed); - args->trans = NULL; - xfs_bmap_cancel(args->flist); - return(error); - } - - /* - * bmap_finish() may have committed the last trans and started - * a new one. We need the inode to be in all transactions. - */ - if (committed) - xfs_trans_ijoin(args->trans, args->dp, 0); - - /* - * Close out trans and start the next one in the chain. - */ - error = xfs_trans_roll(&args->trans, args->dp); - if (error) - return (error); - } - return(0); -} diff --git a/fs/xfs/xfs_attr.h b/fs/xfs/xfs_attr.h index e920d68..de8dd58 100644 --- a/fs/xfs/xfs_attr.h +++ b/fs/xfs/xfs_attr.h @@ -140,7 +140,6 @@ typedef struct xfs_attr_list_context { * Overall external interface routines. */ int xfs_attr_inactive(struct xfs_inode *dp); -int xfs_attr_rmtval_get(struct xfs_da_args *args); int xfs_attr_list_int(struct xfs_attr_list_context *); #endif /* __XFS_ATTR_H__ */ diff --git a/fs/xfs/xfs_attr_leaf.c b/fs/xfs/xfs_attr_leaf.c index 9c18451..a1cb746 100644 --- a/fs/xfs/xfs_attr_leaf.c +++ b/fs/xfs/xfs_attr_leaf.c @@ -32,6 +32,7 @@ #include "xfs_alloc.h" #include "xfs_btree.h" #include "xfs_attr_sf.h" +#include "xfs_attr_remote.h" #include "xfs_dinode.h" #include "xfs_inode.h" #include "xfs_inode_item.h" diff --git a/fs/xfs/xfs_attr_remote.c b/fs/xfs/xfs_attr_remote.c new file mode 100644 index 0000000..be615d1 --- /dev/null +++ b/fs/xfs/xfs_attr_remote.c @@ -0,0 +1,328 @@ +/* + * Copyright (c) 2000-2005 Silicon Graphics, Inc. + * All Rights Reserved. + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License as + * published by the Free Software Foundation. + * + * This program is distributed in the hope that it would be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + */ +#include "xfs.h" +#include "xfs_fs.h" +#include "xfs_types.h" +#include "xfs_bit.h" +#include "xfs_log.h" +#include "xfs_trans.h" +#include "xfs_sb.h" +#include "xfs_ag.h" +#include "xfs_mount.h" +#include "xfs_error.h" +#include "xfs_da_btree.h" +#include "xfs_bmap_btree.h" +#include "xfs_dinode.h" +#include "xfs_inode.h" +#include "xfs_alloc.h" +#include "xfs_inode_item.h" +#include "xfs_bmap.h" +#include "xfs_attr.h" +#include "xfs_attr_leaf.h" +#include "xfs_attr_remote.h" +#include "xfs_trans_space.h" +#include "xfs_trace.h" + + +#define ATTR_RMTVALUE_MAPSIZE 1 /* # of map entries at once */ + +/* + * Read the value associated with an attribute from the out-of-line buffer + * that we stored it in. + */ +int +xfs_attr_rmtval_get(xfs_da_args_t *args) +{ + xfs_bmbt_irec_t map[ATTR_RMTVALUE_MAPSIZE]; + xfs_mount_t *mp; + xfs_daddr_t dblkno; + void *dst; + xfs_buf_t *bp; + int nmap, error, tmp, valuelen, blkcnt, i; + xfs_dablk_t lblkno; + + trace_xfs_attr_rmtval_get(args); + + ASSERT(!(args->flags & ATTR_KERNOVAL)); + + mp = args->dp->i_mount; + dst = args->value; + valuelen = args->valuelen; + lblkno = args->rmtblkno; + while (valuelen > 0) { + nmap = ATTR_RMTVALUE_MAPSIZE; + error = xfs_bmapi_read(args->dp, (xfs_fileoff_t)lblkno, + args->rmtblkcnt, map, &nmap, + XFS_BMAPI_ATTRFORK); + if (error) + return(error); + ASSERT(nmap >= 1); + + for (i = 0; (i < nmap) && (valuelen > 0); i++) { + ASSERT((map[i].br_startblock != DELAYSTARTBLOCK) && + (map[i].br_startblock != HOLESTARTBLOCK)); + dblkno = XFS_FSB_TO_DADDR(mp, map[i].br_startblock); + blkcnt = XFS_FSB_TO_BB(mp, map[i].br_blockcount); + error = xfs_trans_read_buf(mp, NULL, mp->m_ddev_targp, + dblkno, blkcnt, 0, &bp, NULL); + if (error) + return(error); + + tmp = min_t(int, valuelen, BBTOB(bp->b_length)); + xfs_buf_iomove(bp, 0, tmp, dst, XBRW_READ); + xfs_buf_relse(bp); + dst += tmp; + valuelen -= tmp; + + lblkno += map[i].br_blockcount; + } + } + ASSERT(valuelen == 0); + return(0); +} + +/* + * Write the value associated with an attribute into the out-of-line buffer + * that we have defined for it. + */ +STATIC int +xfs_attr_rmtval_set(xfs_da_args_t *args) +{ + xfs_mount_t *mp; + xfs_fileoff_t lfileoff; + xfs_inode_t *dp; + xfs_bmbt_irec_t map; + xfs_daddr_t dblkno; + void *src; + xfs_buf_t *bp; + xfs_dablk_t lblkno; + int blkcnt, valuelen, nmap, error, tmp, committed; + + trace_xfs_attr_rmtval_set(args); + + dp = args->dp; + mp = dp->i_mount; + src = args->value; + + /* + * Find a "hole" in the attribute address space large enough for + * us to drop the new attribute's value into. + */ + blkcnt = XFS_B_TO_FSB(mp, args->valuelen); + lfileoff = 0; + error = xfs_bmap_first_unused(args->trans, args->dp, blkcnt, &lfileoff, + XFS_ATTR_FORK); + if (error) { + return(error); + } + args->rmtblkno = lblkno = (xfs_dablk_t)lfileoff; + args->rmtblkcnt = blkcnt; + + /* + * Roll through the "value", allocating blocks on disk as required. + */ + while (blkcnt > 0) { + /* + * Allocate a single extent, up to the size of the value. + */ + xfs_bmap_init(args->flist, args->firstblock); + nmap = 1; + error = xfs_bmapi_write(args->trans, dp, (xfs_fileoff_t)lblkno, + blkcnt, + XFS_BMAPI_ATTRFORK | XFS_BMAPI_METADATA, + args->firstblock, args->total, &map, &nmap, + args->flist); + if (!error) { + error = xfs_bmap_finish(&args->trans, args->flist, + &committed); + } + if (error) { + ASSERT(committed); + args->trans = NULL; + xfs_bmap_cancel(args->flist); + return(error); + } + + /* + * bmap_finish() may have committed the last trans and started + * a new one. We need the inode to be in all transactions. + */ + if (committed) + xfs_trans_ijoin(args->trans, dp, 0); + + ASSERT(nmap == 1); + ASSERT((map.br_startblock != DELAYSTARTBLOCK) && + (map.br_startblock != HOLESTARTBLOCK)); + lblkno += map.br_blockcount; + blkcnt -= map.br_blockcount; + + /* + * Start the next trans in the chain. + */ + error = xfs_trans_roll(&args->trans, dp); + if (error) + return (error); + } + + /* + * Roll through the "value", copying the attribute value to the + * already-allocated blocks. Blocks are written synchronously + * so that we can know they are all on disk before we turn off + * the INCOMPLETE flag. + */ + lblkno = args->rmtblkno; + valuelen = args->valuelen; + while (valuelen > 0) { + int buflen; + + /* + * Try to remember where we decided to put the value. + */ + xfs_bmap_init(args->flist, args->firstblock); + nmap = 1; + error = xfs_bmapi_read(dp, (xfs_fileoff_t)lblkno, + args->rmtblkcnt, &map, &nmap, + XFS_BMAPI_ATTRFORK); + if (error) + return(error); + ASSERT(nmap == 1); + ASSERT((map.br_startblock != DELAYSTARTBLOCK) && + (map.br_startblock != HOLESTARTBLOCK)); + + dblkno = XFS_FSB_TO_DADDR(mp, map.br_startblock), + blkcnt = XFS_FSB_TO_BB(mp, map.br_blockcount); + + bp = xfs_buf_get(mp->m_ddev_targp, dblkno, blkcnt, 0); + if (!bp) + return ENOMEM; + + buflen = BBTOB(bp->b_length); + tmp = min_t(int, valuelen, buflen); + xfs_buf_iomove(bp, 0, tmp, src, XBRW_WRITE); + if (tmp < buflen) + xfs_buf_zero(bp, tmp, buflen - tmp); + + error = xfs_bwrite(bp); /* GROT: NOTE: synchronous write */ + xfs_buf_relse(bp); + if (error) + return error; + src += tmp; + valuelen -= tmp; + + lblkno += map.br_blockcount; + } + ASSERT(valuelen == 0); + return(0); +} + +/* + * Remove the value associated with an attribute by deleting the + * out-of-line buffer that it is stored on. + */ +STATIC int +xfs_attr_rmtval_remove(xfs_da_args_t *args) +{ + xfs_mount_t *mp; + xfs_bmbt_irec_t map; + xfs_buf_t *bp; + xfs_daddr_t dblkno; + xfs_dablk_t lblkno; + int valuelen, blkcnt, nmap, error, done, committed; + + trace_xfs_attr_rmtval_remove(args); + + mp = args->dp->i_mount; + + /* + * Roll through the "value", invalidating the attribute value's + * blocks. + */ + lblkno = args->rmtblkno; + valuelen = args->rmtblkcnt; + while (valuelen > 0) { + /* + * Try to remember where we decided to put the value. + */ + nmap = 1; + error = xfs_bmapi_read(args->dp, (xfs_fileoff_t)lblkno, + args->rmtblkcnt, &map, &nmap, + XFS_BMAPI_ATTRFORK); + if (error) + return(error); + ASSERT(nmap == 1); + ASSERT((map.br_startblock != DELAYSTARTBLOCK) && + (map.br_startblock != HOLESTARTBLOCK)); + + dblkno = XFS_FSB_TO_DADDR(mp, map.br_startblock), + blkcnt = XFS_FSB_TO_BB(mp, map.br_blockcount); + + /* + * If the "remote" value is in the cache, remove it. + */ + bp = xfs_incore(mp->m_ddev_targp, dblkno, blkcnt, XBF_TRYLOCK); + if (bp) { + xfs_buf_stale(bp); + xfs_buf_relse(bp); + bp = NULL; + } + + valuelen -= map.br_blockcount; + + lblkno += map.br_blockcount; + } + + /* + * Keep de-allocating extents until the remote-value region is gone. + */ + lblkno = args->rmtblkno; + blkcnt = args->rmtblkcnt; + done = 0; + while (!done) { + xfs_bmap_init(args->flist, args->firstblock); + error = xfs_bunmapi(args->trans, args->dp, lblkno, blkcnt, + XFS_BMAPI_ATTRFORK | XFS_BMAPI_METADATA, + 1, args->firstblock, args->flist, + &done); + if (!error) { + error = xfs_bmap_finish(&args->trans, args->flist, + &committed); + } + if (error) { + ASSERT(committed); + args->trans = NULL; + xfs_bmap_cancel(args->flist); + return(error); + } + + /* + * bmap_finish() may have committed the last trans and started + * a new one. We need the inode to be in all transactions. + */ + if (committed) + xfs_trans_ijoin(args->trans, args->dp, 0); + + /* + * Close out trans and start the next one in the chain. + */ + error = xfs_trans_roll(&args->trans, args->dp); + if (error) + return (error); + } + return(0); +} + diff --git a/fs/xfs/xfs_attr_remote.h b/fs/xfs/xfs_attr_remote.h new file mode 100644 index 0000000..2a34b9a --- /dev/null +++ b/fs/xfs/xfs_attr_remote.h @@ -0,0 +1,25 @@ +/* + * Copyright (c) 2013 Red Hat, Inc. + * All Rights Reserved. + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License as + * published by the Free Software Foundation. + * + * This program is distributed in the hope that it would be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + */ +#ifndef __XFS_ATTR_REMOTE_H__ +#define __XFS_ATTR_REMOTE_H__ + +int xfs_attr_rmtval_get(struct xfs_da_args *args); +int xfs_attr_rmtval_set(struct xfs_da_args *args); +int xfs_attr_rmtval_remove(struct xfs_da_args *args); + +#endif /* __XFS_ATTR_REMOTE_H__ */ -- 1.7.10.4 From dave@fromorbit.com Tue Mar 12 07:31:38 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id BDF487FB0 for ; Tue, 12 Mar 2013 07:31:38 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay1.corp.sgi.com (Postfix) with ESMTP id AB49B8F8035 for ; Tue, 12 Mar 2013 05:31:38 -0700 (PDT) X-ASG-Debug-ID: 1363091485-04cb6c2b01493060004-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id J3gbNNXCalAqaU15 for ; Tue, 12 Mar 2013 05:31:36 -0700 (PDT) X-Barracuda-Envelope-From: dave@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: Ag8KAKEfP1F5LKiV/2dsb2JhbAA5CsRdAwGBSRd0gigBAQUnLzMIGDE5AxsZiBKwApAfjVI6doNSA5xPinuDHig Received: from ppp121-44-168-149.lns20.syd7.internode.on.net (HELO dastard) ([121.44.168.149]) by ipmail05.adl6.internode.on.net with ESMTP; 12 Mar 2013 23:01:30 +1030 Received: from [192.168.1.1] (helo=disappointment) by dastard with esmtp (Exim 4.76) (envelope-from ) id 1UFOMa-0001SZ-Mw for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:31:28 +1100 Received: from dave by disappointment with local (Exim 4.80) (envelope-from ) id 1UFOMQ-0002N5-Ku for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:31:18 +1100 From: Dave Chinner To: xfs@oss.sgi.com Subject: [PATCH 19/21] xfs: add CRC protection to remote attributes Date: Tue, 12 Mar 2013 23:30:52 +1100 X-ASG-Orig-Subj: [PATCH 19/21] xfs: add CRC protection to remote attributes Message-Id: <1363091454-8852-20-git-send-email-david@fromorbit.com> X-Mailer: git-send-email 1.7.10.4 In-Reply-To: <1363091454-8852-1-git-send-email-david@fromorbit.com> References: <1363091454-8852-1-git-send-email-david@fromorbit.com> X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1363091495 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124988 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- From: Dave Chinner There are two ways of doing this - the first is to add a CRC to the remote attribute entry in the attribute block. The second is to treat them similar to the remote symlink, where each fragment has it's own header and identifies fragment location in the attribute. The problem with the CRC in the remote attr entry is that we cannot identify the owner of the metadata from the metadata blocks themselves, or where the blocks fit into the remote attribute. The down side to this approach is that we never know when the attribute has been read from disk or not and so we have to verify it every time it is read, and we must calculate it during the create transaction and log it. We do not log CRCs for any other metadata, and so this creates a unique set of coherency problems that, in general, are best avoided. Adding an identifying header to each allocated block allows us to identify each fragment and where in the attribute it is located. It enables us to rebuild the remote attribute from just the raw blocks containing the attribute. It also provides us to do per-block CRCs verification at IO time rather than during the transaction context that creates it or every time it is read into a user buffer. Hence it avoids all the problems that an external, logged CRC has, and provides all the benefits of self identifying metadata. The only complexity is that we have to add a header per fragment, and we don't know how many fragments will be needed prior to allocations. If we take the symlink example, the header is 56 bytes and hence for a 4k block size filesystem, in the worst case 16 headers requires 1 extra block for the 64k attribute data. For 512 byte filesystems the worst case is an extra block for every 9 fragments (i.e. 16 extra blocks in the worse case). This will be very rare and so it's not really a major concern. Because allocation is done in two steps - the first finds a hole large enough in the attribute file, the second does the allocation - we only need to find a hole big enough for a worst case allocation. We only need to allocate enough extra blocks for number of headers required by the fragments, and we can calculate that as we go.... Hence it really only makes sense to use the same model as for symlinks - it doesn't add that much complexity, does not require an attribute tree format change, and does not require logging calculated CRC values. Signed-off-by: Dave Chinner --- fs/xfs/xfs_attr_remote.c | 324 ++++++++++++++++++++++++++++++++++++++-------- fs/xfs/xfs_attr_remote.h | 19 +++ 2 files changed, 292 insertions(+), 51 deletions(-) diff --git a/fs/xfs/xfs_attr_remote.c b/fs/xfs/xfs_attr_remote.c index be615d1..ec174ff 100644 --- a/fs/xfs/xfs_attr_remote.c +++ b/fs/xfs/xfs_attr_remote.c @@ -1,5 +1,6 @@ /* * Copyright (c) 2000-2005 Silicon Graphics, Inc. + * Copyright (c) 2013 Red Hat, Inc. * All Rights Reserved. * * This program is free software; you can redistribute it and/or @@ -37,63 +38,232 @@ #include "xfs_attr_remote.h" #include "xfs_trans_space.h" #include "xfs_trace.h" - +#include "xfs_cksum.h" +#include "xfs_buf_item.h" #define ATTR_RMTVALUE_MAPSIZE 1 /* # of map entries at once */ /* + * Each contiguous block has a header, so it is not just a simple attribute + * length to FSB conversion. + */ +static int +xfs_attr3_rmt_blocks( + struct xfs_mount *mp, + int attrlen) +{ + int fsblocks = 0; + int len = attrlen; + + do { + fsblocks++; + len -= XFS_ATTR3_RMT_BUF_SPACE(mp, mp->m_sb.sb_blocksize); + } while (len > 0); + + return fsblocks; +} + +static bool +xfs_attr3_rmt_verify( + struct xfs_buf *bp) +{ + struct xfs_mount *mp = bp->b_target->bt_mount; + struct xfs_attr3_rmt_hdr *rmt = bp->b_addr; + + if (!xfs_sb_version_hascrc(&mp->m_sb)) + return false; + if (rmt->rm_magic != cpu_to_be32(XFS_ATTR3_RMT_MAGIC)) + return false; + if (!uuid_equal(&rmt->rm_uuid, &mp->m_sb.sb_uuid)) + return false; + if (bp->b_bn != be64_to_cpu(rmt->rm_blkno)) + return false; + if (be32_to_cpu(rmt->rm_offset) + + be32_to_cpu(rmt->rm_bytes) >= MAXPATHLEN) + return false; + if (rmt->rm_owner == 0) + return false; + + return true; +} + +static void +xfs_attr3_rmt_read_verify( + struct xfs_buf *bp) +{ + struct xfs_mount *mp = bp->b_target->bt_mount; + + /* no verification of non-crc buffers */ + if (!xfs_sb_version_hascrc(&mp->m_sb)) + return; + + if (!xfs_verify_cksum(bp->b_addr, BBTOB(bp->b_length), + XFS_ATTR3_RMT_CRC_OFF) || + !xfs_attr3_rmt_verify(bp)) { + XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, mp, bp->b_addr); + xfs_buf_ioerror(bp, EFSCORRUPTED); + } +} + +static void +xfs_attr3_rmt_write_verify( + struct xfs_buf *bp) +{ + struct xfs_mount *mp = bp->b_target->bt_mount; + struct xfs_buf_log_item *bip = bp->b_fspriv; + + /* no verification of non-crc buffers */ + if (!xfs_sb_version_hascrc(&mp->m_sb)) + return; + + if (!xfs_attr3_rmt_verify(bp)) { + XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, mp, bp->b_addr); + xfs_buf_ioerror(bp, EFSCORRUPTED); + return; + } + + if (bip) { + struct xfs_attr3_rmt_hdr *rmt = bp->b_addr; + rmt->rm_lsn = cpu_to_be64(bip->bli_item.li_lsn); + } + xfs_update_cksum(bp->b_addr, BBTOB(bp->b_length), + XFS_ATTR3_RMT_CRC_OFF); +} + +const struct xfs_buf_ops xfs_attr3_rmt_buf_ops = { + .verify_read = xfs_attr3_rmt_read_verify, + .verify_write = xfs_attr3_rmt_write_verify, +}; + +static int +xfs_attr3_rmt_hdr_set( + struct xfs_mount *mp, + xfs_ino_t ino, + uint32_t offset, + uint32_t size, + struct xfs_buf *bp) +{ + struct xfs_attr3_rmt_hdr *rmt = bp->b_addr; + + if (!xfs_sb_version_hascrc(&mp->m_sb)) + return 0; + + rmt->rm_magic = cpu_to_be32(XFS_ATTR3_RMT_MAGIC); + rmt->rm_offset = cpu_to_be32(offset); + rmt->rm_bytes = cpu_to_be32(size); + uuid_copy(&rmt->rm_uuid, &mp->m_sb.sb_uuid); + rmt->rm_owner = cpu_to_be64(ino); + rmt->rm_blkno = cpu_to_be64(bp->b_bn); + bp->b_ops = &xfs_attr3_rmt_buf_ops; + + return sizeof(struct xfs_attr3_rmt_hdr); +} + +/* + * Checking of the remote attribute header is split into two parts. the verifier + * does CRC, location and bounds checking, the unpacking function checks the + * attribute parameters and owner. + */ +static bool +xfs_attr3_rmt_hdr_ok( + struct xfs_mount *mp, + xfs_ino_t ino, + uint32_t offset, + uint32_t size, + struct xfs_buf *bp) +{ + struct xfs_attr3_rmt_hdr *rmt = bp->b_addr; + + if (offset != be32_to_cpu(rmt->rm_offset)) + return false; + if (size != be32_to_cpu(rmt->rm_bytes)) + return false; + if (ino != be64_to_cpu(rmt->rm_owner)) + return false; + + /* ok */ + return true; + +} + +/* * Read the value associated with an attribute from the out-of-line buffer * that we stored it in. */ int -xfs_attr_rmtval_get(xfs_da_args_t *args) +xfs_attr_rmtval_get( + struct xfs_da_args *args) { - xfs_bmbt_irec_t map[ATTR_RMTVALUE_MAPSIZE]; - xfs_mount_t *mp; - xfs_daddr_t dblkno; - void *dst; - xfs_buf_t *bp; - int nmap, error, tmp, valuelen, blkcnt, i; - xfs_dablk_t lblkno; + struct xfs_bmbt_irec map[ATTR_RMTVALUE_MAPSIZE]; + struct xfs_mount *mp = args->dp->i_mount; + struct xfs_buf *bp; + xfs_daddr_t dblkno; + xfs_dablk_t lblkno = args->rmtblkno; + void *dst = args->value; + int valuelen = args->valuelen; + int nmap; + int error; + int blkcnt; + int i; + int offset = 0; trace_xfs_attr_rmtval_get(args); ASSERT(!(args->flags & ATTR_KERNOVAL)); - mp = args->dp->i_mount; - dst = args->value; - valuelen = args->valuelen; - lblkno = args->rmtblkno; while (valuelen > 0) { nmap = ATTR_RMTVALUE_MAPSIZE; error = xfs_bmapi_read(args->dp, (xfs_fileoff_t)lblkno, args->rmtblkcnt, map, &nmap, XFS_BMAPI_ATTRFORK); if (error) - return(error); + return error; ASSERT(nmap >= 1); for (i = 0; (i < nmap) && (valuelen > 0); i++) { + int byte_cnt; + char *src; + ASSERT((map[i].br_startblock != DELAYSTARTBLOCK) && (map[i].br_startblock != HOLESTARTBLOCK)); dblkno = XFS_FSB_TO_DADDR(mp, map[i].br_startblock); blkcnt = XFS_FSB_TO_BB(mp, map[i].br_blockcount); error = xfs_trans_read_buf(mp, NULL, mp->m_ddev_targp, - dblkno, blkcnt, 0, &bp, NULL); + dblkno, blkcnt, 0, &bp, + &xfs_attr3_rmt_buf_ops); if (error) - return(error); + return error; + + byte_cnt = min_t(int, valuelen, BBTOB(bp->b_length)); + byte_cnt = XFS_ATTR3_RMT_BUF_SPACE(mp, byte_cnt); - tmp = min_t(int, valuelen, BBTOB(bp->b_length)); - xfs_buf_iomove(bp, 0, tmp, dst, XBRW_READ); + src = bp->b_addr; + if (xfs_sb_version_hascrc(&mp->m_sb)) { + if (!xfs_attr3_rmt_hdr_ok(mp, args->dp->i_ino, + offset, byte_cnt, bp)) { + xfs_alert(mp, +"remote attribute header does not match required off/len/owner (0x%x/Ox%x,0x%llx)", + offset, byte_cnt, args->dp->i_ino); + xfs_buf_relse(bp); + return EFSCORRUPTED; + + } + + src += sizeof(struct xfs_attr3_rmt_hdr); + } + + memcpy(dst, src, byte_cnt); xfs_buf_relse(bp); - dst += tmp; - valuelen -= tmp; + + offset += byte_cnt; + dst += byte_cnt; + valuelen -= byte_cnt; lblkno += map[i].br_blockcount; } } ASSERT(valuelen == 0); - return(0); + return 0; } /* @@ -101,35 +271,49 @@ xfs_attr_rmtval_get(xfs_da_args_t *args) * that we have defined for it. */ STATIC int -xfs_attr_rmtval_set(xfs_da_args_t *args) +xfs_attr_rmtval_set( + struct xfs_da_args *args) { - xfs_mount_t *mp; - xfs_fileoff_t lfileoff; - xfs_inode_t *dp; - xfs_bmbt_irec_t map; - xfs_daddr_t dblkno; - void *src; - xfs_buf_t *bp; - xfs_dablk_t lblkno; - int blkcnt, valuelen, nmap, error, tmp, committed; + struct xfs_inode *dp = args->dp; + struct xfs_mount *mp = dp->i_mount; + struct xfs_bmbt_irec map; + struct xfs_buf *bp; + xfs_daddr_t dblkno; + xfs_dablk_t lblkno; + xfs_fileoff_t lfileoff = 0; + void *src = args->value; + int blkcnt; + int valuelen; + int nmap; + int error; + int hdrcnt = 0; + bool crcs = xfs_sb_version_hascrc(&mp->m_sb); + int offset = 0; trace_xfs_attr_rmtval_set(args); - dp = args->dp; - mp = dp->i_mount; - src = args->value; - /* * Find a "hole" in the attribute address space large enough for - * us to drop the new attribute's value into. + * us to drop the new attribute's value into. Because CRC enable + * attributes have headers, we can't just do a straight byte to FSB + * conversion. We calculate the worst case block count in this case + * and we may not need that many, so we have to handle this when + * allocating the blocks below. */ - blkcnt = XFS_B_TO_FSB(mp, args->valuelen); - lfileoff = 0; + if (!crcs) + blkcnt = XFS_B_TO_FSB(mp, args->valuelen); + else + blkcnt = xfs_attr3_rmt_blocks(mp, args->valuelen); + error = xfs_bmap_first_unused(args->trans, args->dp, blkcnt, &lfileoff, XFS_ATTR_FORK); - if (error) { - return(error); - } + if (error) + return error; + + /* Start with the attribute data. We'll allocate the rest afterwards. */ + if (crcs) + blkcnt = XFS_B_TO_FSB(mp, args->valuelen); + args->rmtblkno = lblkno = (xfs_dablk_t)lfileoff; args->rmtblkcnt = blkcnt; @@ -137,6 +321,8 @@ xfs_attr_rmtval_set(xfs_da_args_t *args) * Roll through the "value", allocating blocks on disk as required. */ while (blkcnt > 0) { + int committed; + /* * Allocate a single extent, up to the size of the value. */ @@ -170,6 +356,27 @@ xfs_attr_rmtval_set(xfs_da_args_t *args) (map.br_startblock != HOLESTARTBLOCK)); lblkno += map.br_blockcount; blkcnt -= map.br_blockcount; + hdrcnt++; + + /* + * If we have enough blocks for the attribute data, calculate + * how many extra blocks we need for headers. We might run + * through this multiple times in the case that the additional + * headers in the blocks needed for the data fragments spills + * into requiring more blocks. e.g. for 512 byte blocks, we'll + * spill for another block every 9 headers we require in this + * loop. + */ + + if (crcs && blkcnt == 0) { + int total_len; + + total_len = args->valuelen + + hdrcnt * sizeof(struct xfs_attr3_rmt_hdr); + blkcnt = XFS_B_TO_FSB(mp, total_len); + blkcnt -= args->rmtblkcnt; + args->rmtblkcnt += blkcnt; + } /* * Start the next trans in the chain. @@ -188,7 +395,8 @@ xfs_attr_rmtval_set(xfs_da_args_t *args) lblkno = args->rmtblkno; valuelen = args->valuelen; while (valuelen > 0) { - int buflen; + int byte_cnt; + char *buf; /* * Try to remember where we decided to put the value. @@ -210,24 +418,38 @@ xfs_attr_rmtval_set(xfs_da_args_t *args) bp = xfs_buf_get(mp->m_ddev_targp, dblkno, blkcnt, 0); if (!bp) return ENOMEM; + bp->b_ops = &xfs_attr3_rmt_buf_ops; + + byte_cnt = BBTOB(bp->b_length); + byte_cnt = XFS_ATTR3_RMT_BUF_SPACE(mp, byte_cnt); + if (valuelen < byte_cnt) { + byte_cnt = valuelen; + } + + buf = bp->b_addr; + buf += xfs_attr3_rmt_hdr_set(mp, dp->i_ino, offset, + byte_cnt, bp); + memcpy(buf, src, byte_cnt); - buflen = BBTOB(bp->b_length); - tmp = min_t(int, valuelen, buflen); - xfs_buf_iomove(bp, 0, tmp, src, XBRW_WRITE); - if (tmp < buflen) - xfs_buf_zero(bp, tmp, buflen - tmp); + if (byte_cnt < BBTOB(bp->b_length)) + xfs_buf_zero(bp, byte_cnt, + BBTOB(bp->b_length) - byte_cnt); error = xfs_bwrite(bp); /* GROT: NOTE: synchronous write */ xfs_buf_relse(bp); if (error) return error; - src += tmp; - valuelen -= tmp; + + src += byte_cnt; + valuelen -= byte_cnt; + offset += byte_cnt; + hdrcnt--; lblkno += map.br_blockcount; } ASSERT(valuelen == 0); - return(0); + ASSERT(hdrcnt == 0); + return 0; } /* @@ -306,7 +528,7 @@ xfs_attr_rmtval_remove(xfs_da_args_t *args) ASSERT(committed); args->trans = NULL; xfs_bmap_cancel(args->flist); - return(error); + return error; } /* diff --git a/fs/xfs/xfs_attr_remote.h b/fs/xfs/xfs_attr_remote.h index 2a34b9a..0ca8d9a 100644 --- a/fs/xfs/xfs_attr_remote.h +++ b/fs/xfs/xfs_attr_remote.h @@ -18,6 +18,25 @@ #ifndef __XFS_ATTR_REMOTE_H__ #define __XFS_ATTR_REMOTE_H__ +#define XFS_ATTR3_RMT_MAGIC 0x5841524d /* XARM */ + +struct xfs_attr3_rmt_hdr { + __be32 rm_magic; + __be32 rm_offset; + __be32 rm_bytes; + __be32 rm_crc; + uuid_t rm_uuid; + __be64 rm_owner; + __be64 rm_blkno; + __be64 rm_lsn; +}; + +#define XFS_ATTR3_RMT_CRC_OFF offsetof(struct xfs_attr3_rmt_hdr, rm_crc) + +#define XFS_ATTR3_RMT_BUF_SPACE(mp, bufsize) \ + ((bufsize) - (xfs_sb_version_hascrc(&(mp)->m_sb) ? \ + sizeof(struct xfs_attr3_rmt_hdr) : 0)) + int xfs_attr_rmtval_get(struct xfs_da_args *args); int xfs_attr_rmtval_set(struct xfs_da_args *args); int xfs_attr_rmtval_remove(struct xfs_da_args *args); -- 1.7.10.4 From dave@fromorbit.com Tue Mar 12 07:31:40 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id CB51B7FB3 for ; Tue, 12 Mar 2013 07:31:40 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay1.corp.sgi.com (Postfix) with ESMTP id 8A3478F804B for ; Tue, 12 Mar 2013 05:31:40 -0700 (PDT) X-ASG-Debug-ID: 1363091497-04bdf022984cb130001-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id SPfu7MNLzCcJO1z3 for ; Tue, 12 Mar 2013 05:31:37 -0700 (PDT) X-Barracuda-Envelope-From: dave@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: Ag8KAKEfP1F5LKiV/2dsb2JhbABDxF0DAYFJF3SCKAEBBRoNLzMIGDE5AxsZiBKwApAfjgx2g1IDp0qDHiiBMCQ Received: from ppp121-44-168-149.lns20.syd7.internode.on.net (HELO dastard) ([121.44.168.149]) by ipmail05.adl6.internode.on.net with ESMTP; 12 Mar 2013 23:01:31 +1030 Received: from disappointment ([192.168.1.1]) by dastard with esmtp (Exim 4.76) (envelope-from ) id 1UFOMQ-0001Sa-P4 for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:31:18 +1100 Received: from dave by disappointment with local (Exim 4.80) (envelope-from ) id 1UFOMQ-0002NA-Ls for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:31:18 +1100 From: Dave Chinner To: xfs@oss.sgi.com Subject: [PATCH 20/21] xfs: add buffer types to directory and attribute buffers Date: Tue, 12 Mar 2013 23:30:53 +1100 X-ASG-Orig-Subj: [PATCH 20/21] xfs: add buffer types to directory and attribute buffers Message-Id: <1363091454-8852-21-git-send-email-david@fromorbit.com> X-Mailer: git-send-email 1.7.10.4 In-Reply-To: <1363091454-8852-1-git-send-email-david@fromorbit.com> References: <1363091454-8852-1-git-send-email-david@fromorbit.com> X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1363091497 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Barracuda-BRTS-Status: 1 X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124988 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- From: Dave Chinner Add buffer types to the buffer log items so that log recovery can validate the buffers and calculate CRCs correctly after the buffers are recovered. Signed-off-by: Dave Chinner --- fs/xfs/xfs_attr_leaf.c | 9 +- fs/xfs/xfs_attr_remote.h | 2 + fs/xfs/xfs_buf_item.h | 18 +++- fs/xfs/xfs_da_btree.c | 46 +++++++- fs/xfs/xfs_da_btree.h | 2 + fs/xfs/xfs_dir2_block.c | 12 ++- fs/xfs/xfs_dir2_data.c | 8 +- fs/xfs/xfs_dir2_leaf.c | 26 ++++- fs/xfs/xfs_dir2_node.c | 15 ++- fs/xfs/xfs_dir2_priv.h | 2 + fs/xfs/xfs_log_recover.c | 259 ++++++++++++++++++++++++++++++++-------------- fs/xfs/xfs_trans.h | 2 + fs/xfs/xfs_trans_buf.c | 17 +++ 13 files changed, 323 insertions(+), 95 deletions(-) diff --git a/fs/xfs/xfs_attr_leaf.c b/fs/xfs/xfs_attr_leaf.c index a1cb746..7feaf3c 100644 --- a/fs/xfs/xfs_attr_leaf.c +++ b/fs/xfs/xfs_attr_leaf.c @@ -271,8 +271,13 @@ xfs_attr3_leaf_read( xfs_daddr_t mappedbno, struct xfs_buf **bpp) { - return xfs_da_read_buf(tp, dp, bno, mappedbno, bpp, + int err; + + err = xfs_da_read_buf(tp, dp, bno, mappedbno, bpp, XFS_ATTR_FORK, &xfs_attr3_leaf_buf_ops); + if (!err && tp) + xfs_trans_buf_set_type(tp, *bpp, XFS_BLF_ATTR_LEAF_BUF); + return err; } /*======================================================================== @@ -1078,6 +1083,7 @@ xfs_attr3_leaf_to_node( goto out; /* copy leaf to new buffer, update identifiers */ + xfs_trans_buf_set_type(args->trans, bp2, XFS_BLF_ATTR_LEAF_BUF); bp2->b_ops = bp1->b_ops; memcpy(bp2->b_addr, bp1->b_addr, XFS_LBSIZE(mp)); if (xfs_sb_version_hascrc(&mp->m_sb)) { @@ -1140,6 +1146,7 @@ xfs_attr3_leaf_create( if (error) return error; bp->b_ops = &xfs_attr3_leaf_buf_ops; + xfs_trans_buf_set_type(args->trans, bp, XFS_BLF_ATTR_LEAF_BUF); leaf = bp->b_addr; memset(leaf, 0, XFS_LBSIZE(mp)); diff --git a/fs/xfs/xfs_attr_remote.h b/fs/xfs/xfs_attr_remote.h index 0ca8d9a..c7cca60 100644 --- a/fs/xfs/xfs_attr_remote.h +++ b/fs/xfs/xfs_attr_remote.h @@ -37,6 +37,8 @@ struct xfs_attr3_rmt_hdr { ((bufsize) - (xfs_sb_version_hascrc(&(mp)->m_sb) ? \ sizeof(struct xfs_attr3_rmt_hdr) : 0)) +extern const struct xfs_buf_ops xfs_attr3_rmt_buf_ops; + int xfs_attr_rmtval_get(struct xfs_da_args *args); int xfs_attr_rmtval_set(struct xfs_da_args *args); int xfs_attr_rmtval_remove(struct xfs_da_args *args); diff --git a/fs/xfs/xfs_buf_item.h b/fs/xfs/xfs_buf_item.h index 09cab4e..640adcf 100644 --- a/fs/xfs/xfs_buf_item.h +++ b/fs/xfs/xfs_buf_item.h @@ -50,6 +50,14 @@ extern kmem_zone_t *xfs_buf_item_zone; #define XFS_BLF_AGI_BUF (1<<8) #define XFS_BLF_DINO_BUF (1<<9) #define XFS_BLF_SYMLINK_BUF (1<<10) +#define XFS_BLF_DIR_BLOCK_BUF (1<<11) +#define XFS_BLF_DIR_DATA_BUF (1<<12) +#define XFS_BLF_DIR_FREE_BUF (1<<13) +#define XFS_BLF_DIR_LEAF1_BUF (1<<14) +#define XFS_BLF_DIR_LEAFN_BUF (1<<15) +#define XFS_BLF_DA_NODE_BUF (1<<16) +#define XFS_BLF_ATTR_LEAF_BUF (1<<17) +#define XFS_BLF_ATTR_RMT_BUF (1<<18) #define XFS_BLF_TYPE_MASK \ (XFS_BLF_UDQUOT_BUF | \ @@ -60,7 +68,15 @@ extern kmem_zone_t *xfs_buf_item_zone; XFS_BLF_AGFL_BUF | \ XFS_BLF_AGI_BUF | \ XFS_BLF_DINO_BUF | \ - XFS_BLF_SYMLINK_BUF) + XFS_BLF_SYMLINK_BUF | \ + XFS_BLF_DIR_BLOCK_BUF | \ + XFS_BLF_DIR_DATA_BUF | \ + XFS_BLF_DIR_FREE_BUF | \ + XFS_BLF_DIR_LEAF1_BUF | \ + XFS_BLF_DIR_LEAFN_BUF | \ + XFS_BLF_DA_NODE_BUF | \ + XFS_BLF_ATTR_LEAF_BUF | \ + XFS_BLF_ATTR_RMT_BUF) #define XFS_BLF_CHUNK 128 #define XFS_BLF_SHIFT 7 diff --git a/fs/xfs/xfs_da_btree.c b/fs/xfs/xfs_da_btree.c index 9939764..10bfeaa 100644 --- a/fs/xfs/xfs_da_btree.c +++ b/fs/xfs/xfs_da_btree.c @@ -292,7 +292,6 @@ const struct xfs_buf_ops xfs_da3_node_buf_ops = { .verify_write = xfs_da3_node_write_verify, }; - int xfs_da3_node_read( struct xfs_trans *tp, @@ -302,8 +301,35 @@ xfs_da3_node_read( struct xfs_buf **bpp, int which_fork) { - return xfs_da_read_buf(tp, dp, bno, mappedbno, bpp, + int err; + + err = xfs_da_read_buf(tp, dp, bno, mappedbno, bpp, which_fork, &xfs_da3_node_buf_ops); + if (!err && tp) { + struct xfs_da_blkinfo *info = (*bpp)->b_addr; + int type; + + switch (be16_to_cpu(info->magic)) { + case XFS_DA3_NODE_MAGIC: + case XFS_DA_NODE_MAGIC: + type = XFS_BLF_DA_NODE_BUF; + break; + case XFS_ATTR_LEAF_MAGIC: + case XFS_ATTR3_LEAF_MAGIC: + type = XFS_BLF_ATTR_LEAF_BUF; + break; + case XFS_DIR2_LEAFN_MAGIC: + case XFS_DIR3_LEAFN_MAGIC: + type = XFS_BLF_DIR_LEAFN_BUF; + break; + default: + type = 0; + ASSERT(0); + break; + } + xfs_trans_buf_set_type(tp, *bpp, type); + } + return err; } /*======================================================================== @@ -334,6 +360,8 @@ xfs_da3_node_create( error = xfs_da_get_buf(tp, args->dp, blkno, -1, &bp, whichfork); if (error) return(error); + bp->b_ops = &xfs_da3_node_buf_ops; + xfs_trans_buf_set_type(tp, bp, XFS_BLF_DA_NODE_BUF); node = bp->b_addr; if (xfs_sb_version_hascrc(&mp->m_sb)) { @@ -352,7 +380,6 @@ xfs_da3_node_create( xfs_trans_log_buf(tp, bp, XFS_DA_LOGRANGE(node, &node->hdr, xfs_da3_node_hdr_size(node))); - bp->b_ops = &xfs_da3_node_buf_ops; *bpp = bp; return(0); } @@ -563,6 +590,12 @@ xfs_da3_root_split( btree = xfs_da3_node_tree_p(oldroot); size = (int)((char *)&btree[nodehdr.count] - (char *)oldroot); level = nodehdr.level; + + /* + * we are about to copy oldroot to bp, so set up the type + * of bp while we know exactly what it will be. + */ + xfs_trans_buf_set_type(tp, bp, XFS_BLF_DA_NODE_BUF); } else { struct xfs_dir3_icleaf_hdr leafhdr; struct xfs_dir2_leaf_entry *ents; @@ -575,6 +608,12 @@ xfs_da3_root_split( leafhdr.magic == XFS_DIR3_LEAFN_MAGIC); size = (int)((char *)&ents[leafhdr.count] - (char *)leaf); level = 0; + + /* + * we are about to copy oldroot to bp, so set up the type + * of bp while we know exactly what it will be. + */ + xfs_trans_buf_set_type(tp, bp, XFS_BLF_DIR_LEAFN_BUF); } /* @@ -1090,6 +1129,7 @@ xfs_da3_root_join( */ memcpy(root_blk->bp->b_addr, bp->b_addr, state->blocksize); root_blk->bp->b_ops = bp->b_ops; + xfs_trans_buf_copy_type(root_blk->bp, bp); if (oldroothdr.magic == XFS_DA3_NODE_MAGIC) { struct xfs_da3_blkinfo *da3 = root_blk->bp->b_addr; da3->blkno = cpu_to_be64(root_blk->bp->b_bn); diff --git a/fs/xfs/xfs_da_btree.h b/fs/xfs/xfs_da_btree.h index 0e8182c..6fb3371 100644 --- a/fs/xfs/xfs_da_btree.h +++ b/fs/xfs/xfs_da_btree.h @@ -301,6 +301,8 @@ int xfs_da3_node_read(struct xfs_trans *tp, struct xfs_inode *dp, xfs_dablk_t bno, xfs_daddr_t mappedbno, struct xfs_buf **bpp, int which_fork); +extern const struct xfs_buf_ops xfs_da3_node_buf_ops; + /* * Utility routines. */ diff --git a/fs/xfs/xfs_dir2_block.c b/fs/xfs/xfs_dir2_block.c index dc04537..8c387e4 100644 --- a/fs/xfs/xfs_dir2_block.c +++ b/fs/xfs/xfs_dir2_block.c @@ -132,20 +132,26 @@ xfs_dir3_block_read( struct xfs_buf **bpp) { struct xfs_mount *mp = dp->i_mount; + int err; - return xfs_da_read_buf(tp, dp, mp->m_dirdatablk, -1, bpp, + err = xfs_da_read_buf(tp, dp, mp->m_dirdatablk, -1, bpp, XFS_DATA_FORK, &xfs_dir3_block_buf_ops); + if (!err && tp) + xfs_trans_buf_set_type(tp, *bpp, XFS_BLF_DIR_BLOCK_BUF); + return err; } static void xfs_dir3_block_init( struct xfs_mount *mp, + struct xfs_trans *tp, struct xfs_buf *bp, struct xfs_inode *dp) { struct xfs_dir3_blk_hdr *hdr3 = bp->b_addr; bp->b_ops = &xfs_dir3_block_buf_ops; + xfs_trans_buf_set_type(tp, bp, XFS_BLF_DIR_BLOCK_BUF); if (xfs_sb_version_hascrc(&mp->m_sb)) { memset(hdr3, 0, sizeof(*hdr3)); @@ -1080,7 +1086,7 @@ xfs_dir2_leaf_to_block( /* * Start converting it to block form. */ - xfs_dir3_block_init(mp, dbp, dp); + xfs_dir3_block_init(mp, tp, dbp, dp); needlog = 1; needscan = 0; @@ -1209,7 +1215,7 @@ xfs_dir2_sf_to_block( kmem_free(sfp); return error; } - xfs_dir3_block_init(mp, bp, dp); + xfs_dir3_block_init(mp, tp, bp, dp); hdr = bp->b_addr; /* diff --git a/fs/xfs/xfs_dir2_data.c b/fs/xfs/xfs_dir2_data.c index 86ac9c0..20a4aaf 100644 --- a/fs/xfs/xfs_dir2_data.c +++ b/fs/xfs/xfs_dir2_data.c @@ -301,8 +301,13 @@ xfs_dir3_data_read( xfs_daddr_t mapped_bno, struct xfs_buf **bpp) { - return xfs_da_read_buf(tp, dp, bno, mapped_bno, bpp, + int err; + + err = xfs_da_read_buf(tp, dp, bno, mapped_bno, bpp, XFS_DATA_FORK, &xfs_dir3_data_buf_ops); + if (!err && tp) + xfs_trans_buf_set_type(tp, *bpp, XFS_BLF_DIR_DATA_BUF); + return err; } int @@ -571,6 +576,7 @@ xfs_dir3_data_init( if (error) return error; bp->b_ops = &xfs_dir3_data_buf_ops; + xfs_trans_buf_set_type(tp, bp, XFS_BLF_DIR_DATA_BUF); /* * Initialize the header. diff --git a/fs/xfs/xfs_dir2_leaf.c b/fs/xfs/xfs_dir2_leaf.c index 71b03fc..015c078 100644 --- a/fs/xfs/xfs_dir2_leaf.c +++ b/fs/xfs/xfs_dir2_leaf.c @@ -277,7 +277,7 @@ xfs_dir3_leafn_write_verify( __write_verify(bp, XFS_DIR2_LEAFN_MAGIC); } -static const struct xfs_buf_ops xfs_dir3_leaf1_buf_ops = { +const struct xfs_buf_ops xfs_dir3_leaf1_buf_ops = { .verify_read = xfs_dir3_leaf1_read_verify, .verify_write = xfs_dir3_leaf1_write_verify, }; @@ -295,8 +295,13 @@ xfs_dir3_leaf_read( xfs_daddr_t mappedbno, struct xfs_buf **bpp) { - return xfs_da_read_buf(tp, dp, fbno, mappedbno, bpp, + int err; + + err = xfs_da_read_buf(tp, dp, fbno, mappedbno, bpp, XFS_DATA_FORK, &xfs_dir3_leaf1_buf_ops); + if (!err && tp) + xfs_trans_buf_set_type(tp, *bpp, XFS_BLF_DIR_LEAF1_BUF); + return err; } int @@ -307,8 +312,13 @@ xfs_dir3_leafn_read( xfs_daddr_t mappedbno, struct xfs_buf **bpp) { - return xfs_da_read_buf(tp, dp, fbno, mappedbno, bpp, + int err; + + err = xfs_da_read_buf(tp, dp, fbno, mappedbno, bpp, XFS_DATA_FORK, &xfs_dir3_leafn_buf_ops); + if (!err && tp) + xfs_trans_buf_set_type(tp, *bpp, XFS_BLF_DIR_LEAFN_BUF); + return err; } /* @@ -317,6 +327,7 @@ xfs_dir3_leafn_read( static void xfs_dir3_leaf_init( struct xfs_mount *mp, + struct xfs_trans *tp, struct xfs_buf *bp, xfs_ino_t owner, __uint16_t type) @@ -351,8 +362,11 @@ xfs_dir3_leaf_init( ltp = xfs_dir2_leaf_tail_p(mp, leaf); ltp->bestcount = 0; bp->b_ops = &xfs_dir3_leaf1_buf_ops; - } else + xfs_trans_buf_set_type(tp, bp, XFS_BLF_DIR_LEAF1_BUF); + } else { bp->b_ops = &xfs_dir3_leafn_buf_ops; + xfs_trans_buf_set_type(tp, bp, XFS_BLF_DIR_LEAFN_BUF); + } } int @@ -377,7 +391,7 @@ xfs_dir3_leaf_get_buf( if (error) return error; - xfs_dir3_leaf_init(mp, bp, dp->i_ino, magic); + xfs_dir3_leaf_init(mp, tp, bp, dp->i_ino, magic); xfs_dir3_leaf_log_header(tp, bp); if (magic == XFS_DIR2_LEAF1_MAGIC) xfs_dir3_leaf_log_tail(tp, bp); @@ -473,6 +487,7 @@ xfs_dir2_block_to_leaf( * Fix up the block header, make it a data block. */ dbp->b_ops = &xfs_dir3_data_buf_ops; + xfs_trans_buf_set_type(tp, dbp, XFS_BLF_DIR_DATA_BUF); if (hdr->magic == cpu_to_be32(XFS_DIR2_BLOCK_MAGIC)) hdr->magic = cpu_to_be32(XFS_DIR2_DATA_MAGIC); else @@ -2181,6 +2196,7 @@ xfs_dir2_node_to_leaf( xfs_dir3_leaf_compact(args, &leafhdr, lbp); lbp->b_ops = &xfs_dir3_leaf1_buf_ops; + xfs_trans_buf_set_type(tp, lbp, XFS_BLF_DIR_LEAF1_BUF); leafhdr.magic = (leafhdr.magic == XFS_DIR2_LEAFN_MAGIC) ? XFS_DIR2_LEAF1_MAGIC : XFS_DIR3_LEAFN_MAGIC; diff --git a/fs/xfs/xfs_dir2_node.c b/fs/xfs/xfs_dir2_node.c index 4f9f9cf..7d1ee7d 100644 --- a/fs/xfs/xfs_dir2_node.c +++ b/fs/xfs/xfs_dir2_node.c @@ -144,7 +144,7 @@ xfs_dir3_free_write_verify( xfs_update_cksum(bp->b_addr, BBTOB(bp->b_length), XFS_DIR3_FREE_CRC_OFF); } -static const struct xfs_buf_ops xfs_dir3_free_buf_ops = { +const struct xfs_buf_ops xfs_dir3_free_buf_ops = { .verify_read = xfs_dir3_free_read_verify, .verify_write = xfs_dir3_free_write_verify, }; @@ -158,8 +158,15 @@ __xfs_dir3_free_read( xfs_daddr_t mappedbno, struct xfs_buf **bpp) { - return xfs_da_read_buf(tp, dp, fbno, mappedbno, bpp, + int err; + + err = xfs_da_read_buf(tp, dp, fbno, mappedbno, bpp, XFS_DATA_FORK, &xfs_dir3_free_buf_ops); + + /* try read returns without an error or *bpp if it lands in a hole */ + if (!err && tp && *bpp) + xfs_trans_buf_set_type(tp, *bpp, XFS_BLF_DIR_FREE_BUF); + return err; } int @@ -246,6 +253,7 @@ xfs_dir3_free_get_buf( if (error) return error; + xfs_trans_buf_set_type(tp, bp, XFS_BLF_DIR_FREE_BUF); bp->b_ops = &xfs_dir3_free_buf_ops;; /* @@ -394,6 +402,7 @@ xfs_dir2_leaf_to_node( else leaf->hdr.info.magic = cpu_to_be16(XFS_DIR3_LEAFN_MAGIC); lbp->b_ops = &xfs_dir3_leafn_buf_ops; + xfs_trans_buf_set_type(tp, lbp, XFS_BLF_DIR_LEAFN_BUF); xfs_dir3_leaf_log_header(tp, lbp); xfs_dir3_leaf_check(mp, lbp); return 0; @@ -805,6 +814,7 @@ xfs_dir2_leafn_lookup_for_entry( (char *)curbp->b_addr); state->extrablk.magic = XFS_DIR2_DATA_MAGIC; curbp->b_ops = &xfs_dir3_data_buf_ops; + xfs_trans_buf_set_type(tp, curbp, XFS_BLF_DIR_DATA_BUF); if (cmp == XFS_CMP_EXACT) return XFS_ERROR(EEXIST); } @@ -819,6 +829,7 @@ xfs_dir2_leafn_lookup_for_entry( state->extrablk.blkno = curdb; state->extrablk.magic = XFS_DIR2_DATA_MAGIC; curbp->b_ops = &xfs_dir3_data_buf_ops; + xfs_trans_buf_set_type(tp, curbp, XFS_BLF_DIR_DATA_BUF); } else { /* If the curbp is not the CI match block, drop it */ if (state->extrablk.bp != curbp) diff --git a/fs/xfs/xfs_dir2_priv.h b/fs/xfs/xfs_dir2_priv.h index 932565d..7cf573c 100644 --- a/fs/xfs/xfs_dir2_priv.h +++ b/fs/xfs/xfs_dir2_priv.h @@ -49,6 +49,7 @@ extern int xfs_dir2_leaf_to_block(struct xfs_da_args *args, #endif extern const struct xfs_buf_ops xfs_dir3_data_buf_ops; +extern const struct xfs_buf_ops xfs_dir3_free_buf_ops; extern int __xfs_dir3_data_check(struct xfs_inode *dp, struct xfs_buf *bp); extern int xfs_dir3_data_read(struct xfs_trans *tp, struct xfs_inode *dp, @@ -77,6 +78,7 @@ extern void xfs_dir2_data_use_free(struct xfs_trans *tp, struct xfs_buf *bp, xfs_dir2_data_aoff_t len, int *needlogp, int *needscanp); /* xfs_dir2_leaf.c */ +extern const struct xfs_buf_ops xfs_dir3_leaf1_buf_ops; extern const struct xfs_buf_ops xfs_dir3_leafn_buf_ops; extern int xfs_dir3_leafn_read(struct xfs_trans *tp, struct xfs_inode *dp, diff --git a/fs/xfs/xfs_log_recover.c b/fs/xfs/xfs_log_recover.c index 542aa1e..4cf2cf2 100644 --- a/fs/xfs/xfs_log_recover.c +++ b/fs/xfs/xfs_log_recover.c @@ -45,7 +45,14 @@ #include "xfs_cksum.h" #include "xfs_trace.h" #include "xfs_icache.h" + +/* Need all the magic numbers and buffer ops structures from these headers */ #include "xfs_symlink.h" +#include "xfs_da_btree.h" +#include "xfs_dir2_format.h" +#include "xfs_dir2_priv.h" +#include "xfs_attr_leaf.h" +#include "xfs_attr_remote.h" STATIC int xlog_find_zeroed( @@ -1860,86 +1867,30 @@ xlog_recover_do_inode_buffer( } /* - * Perform a 'normal' buffer recovery. Each logged region of the - * buffer should be copied over the corresponding region in the - * given buffer. The bitmap in the buf log format structure indicates - * where to place the logged data. + * Validate the recovered buffer is of the correct type and attach the + * appropriate buffer operations to them for writeback. Magic numbers are in a + * few places: + * the first 16 bits of the buffer (inode buffer, dquot buffer), + * the first 32 bits of the buffer (most blocks), + * inside a struct xfs_da_blkinfo at the start of the buffer. */ -STATIC void -xlog_recover_do_reg_buffer( +static void +xlog_recovery_validate_buf_type( struct xfs_mount *mp, - xlog_recover_item_t *item, struct xfs_buf *bp, xfs_buf_log_format_t *buf_f) { - int i; - int bit; - int nbits; - int error; - struct xfs_da_blkinfo *info; - - trace_xfs_log_recover_buf_reg_buf(mp->m_log, buf_f); - - bit = 0; - i = 1; /* 0 is the buf format structure */ - while (1) { - bit = xfs_next_bit(buf_f->blf_data_map, - buf_f->blf_map_size, bit); - if (bit == -1) - break; - nbits = xfs_contig_bits(buf_f->blf_data_map, - buf_f->blf_map_size, bit); - ASSERT(nbits > 0); - ASSERT(item->ri_buf[i].i_addr != NULL); - ASSERT(item->ri_buf[i].i_len % XFS_BLF_CHUNK == 0); - ASSERT(BBTOB(bp->b_io_length) >= - ((uint)bit << XFS_BLF_SHIFT) + (nbits << XFS_BLF_SHIFT)); - - /* - * Do a sanity check if this is a dquot buffer. Just checking - * the first dquot in the buffer should do. XXXThis is - * probably a good thing to do for other buf types also. - */ - error = 0; - if (buf_f->blf_flags & - (XFS_BLF_UDQUOT_BUF|XFS_BLF_PDQUOT_BUF|XFS_BLF_GDQUOT_BUF)) { - if (item->ri_buf[i].i_addr == NULL) { - xfs_alert(mp, - "XFS: NULL dquot in %s.", __func__); - goto next; - } - if (item->ri_buf[i].i_len < sizeof(xfs_disk_dquot_t)) { - xfs_alert(mp, - "XFS: dquot too small (%d) in %s.", - item->ri_buf[i].i_len, __func__); - goto next; - } - error = xfs_qm_dqcheck(mp, item->ri_buf[i].i_addr, - -1, 0, XFS_QMOPT_DOWARN, - "dquot_buf_recover"); - if (error) - goto next; - } - - memcpy(xfs_buf_offset(bp, - (uint)bit << XFS_BLF_SHIFT), /* dest */ - item->ri_buf[i].i_addr, /* source */ - nbits<ri_total); - - /* Shouldn't be any more regions */ - ASSERT(i == item->ri_total); - - info = bp->b_addr; + struct xfs_da_blkinfo *info = bp->b_addr; + __uint32_t magic32; + __uint16_t magic16; + __uint16_t magicda; + + magic32 = be32_to_cpu(*(__be32 *)bp->b_addr); + magic16 = be16_to_cpu(*(__be16*)bp->b_addr); + magicda = be16_to_cpu(info->magic); switch (buf_f->blf_flags & XFS_BLF_TYPE_MASK) { case XFS_BLF_BTREE_BUF: - switch (be32_to_cpu(*(__be32 *)bp->b_addr)) { + switch (magic32) { case XFS_ABTB_CRC_MAGIC: case XFS_ABTC_CRC_MAGIC: case XFS_ABTB_MAGIC: @@ -1961,7 +1912,7 @@ xlog_recover_do_reg_buffer( } break; case XFS_BLF_AGF_BUF: - if (*(__be32 *)bp->b_addr != cpu_to_be32(XFS_AGF_MAGIC)) { + if (magic32 != XFS_AGF_MAGIC) { xfs_warn(mp, "Bad AGF block magic!"); ASSERT(0); break; @@ -1971,7 +1922,7 @@ xlog_recover_do_reg_buffer( case XFS_BLF_AGFL_BUF: if (!xfs_sb_version_hascrc(&mp->m_sb)) break; - if (*(__be32 *)bp->b_addr != cpu_to_be32(XFS_AGFL_MAGIC)) { + if (magic32 != XFS_AGFL_MAGIC) { xfs_warn(mp, "Bad AGFL block magic!"); ASSERT(0); break; @@ -1979,7 +1930,7 @@ xlog_recover_do_reg_buffer( bp->b_ops = &xfs_agfl_buf_ops; break; case XFS_BLF_AGI_BUF: - if (*(__be32 *)bp->b_addr != cpu_to_be32(XFS_AGI_MAGIC)) { + if (magic32 != XFS_AGI_MAGIC) { xfs_warn(mp, "Bad AGI block magic!"); ASSERT(0); break; @@ -1989,7 +1940,7 @@ xlog_recover_do_reg_buffer( case XFS_BLF_UDQUOT_BUF: case XFS_BLF_PDQUOT_BUF: case XFS_BLF_GDQUOT_BUF: - if (*(__be16 *)bp->b_addr != cpu_to_be16(XFS_DQUOT_MAGIC)) { + if (magic16 != XFS_DQUOT_MAGIC) { xfs_warn(mp, "Bad DQUOT block magic!"); ASSERT(0); break; @@ -2001,7 +1952,7 @@ xlog_recover_do_reg_buffer( * we get here with inode allocation buffers, not buffers that * track unlinked list changes. */ - if (*(__be16 *)bp->b_addr != cpu_to_be16(XFS_DINODE_MAGIC)) { + if (magic16 != XFS_DINODE_MAGIC) { xfs_warn(mp, "Bad INODE block magic!"); ASSERT(0); break; @@ -2009,19 +1960,169 @@ xlog_recover_do_reg_buffer( bp->b_ops = &xfs_inode_buf_ops; break; case XFS_BLF_SYMLINK_BUF: - if (*(__be32 *)bp->b_addr != cpu_to_be32(XFS_SYMLINK_MAGIC)) { + if (magic32 != XFS_SYMLINK_MAGIC) { xfs_warn(mp, "Bad symlink block magic!"); ASSERT(0); break; } bp->b_ops = &xfs_symlink_buf_ops; break; + case XFS_BLF_DIR_BLOCK_BUF: + if (magic32 != XFS_DIR2_BLOCK_MAGIC && + magic32 != XFS_DIR3_BLOCK_MAGIC) { + xfs_warn(mp, "Bad dir block magic!"); + ASSERT(0); + break; + } + bp->b_ops = &xfs_dir3_block_buf_ops; + break; + case XFS_BLF_DIR_DATA_BUF: + if (magic32 != XFS_DIR2_DATA_MAGIC && + magic32 != XFS_DIR3_DATA_MAGIC) { + xfs_warn(mp, "Bad dir data magic!"); + ASSERT(0); + break; + } + bp->b_ops = &xfs_dir3_data_buf_ops; + break; + case XFS_BLF_DIR_FREE_BUF: + if (magic32 != XFS_DIR2_FREE_MAGIC && + magic32 != XFS_DIR3_FREE_MAGIC) { + xfs_warn(mp, "Bad dir3 free magic!"); + ASSERT(0); + break; + } + bp->b_ops = &xfs_dir3_free_buf_ops; + break; + case XFS_BLF_DIR_LEAF1_BUF: + if (magicda != XFS_DIR2_LEAF1_MAGIC && + magicda != XFS_DIR3_LEAF1_MAGIC) { + xfs_warn(mp, "Bad dir leaf1 magic!"); + ASSERT(0); + break; + } + bp->b_ops = &xfs_dir3_leaf1_buf_ops; + break; + case XFS_BLF_DIR_LEAFN_BUF: + if (magicda != XFS_DIR2_LEAFN_MAGIC && + magicda != XFS_DIR3_LEAFN_MAGIC) { + xfs_warn(mp, "Bad dir leafn magic!"); + ASSERT(0); + break; + } + bp->b_ops = &xfs_dir3_leafn_buf_ops; + break; + case XFS_BLF_DA_NODE_BUF: + if (magicda != XFS_DA_NODE_MAGIC && + magicda != XFS_DA3_NODE_MAGIC) { + xfs_warn(mp, "Bad da node magic!"); + ASSERT(0); + break; + } + bp->b_ops = &xfs_da3_node_buf_ops; + break; + case XFS_BLF_ATTR_LEAF_BUF: + if (magicda != XFS_ATTR_LEAF_MAGIC && + magicda != XFS_ATTR3_LEAF_MAGIC) { + xfs_warn(mp, "Bad attr leaf magic!"); + ASSERT(0); + break; + } + bp->b_ops = &xfs_attr3_leaf_buf_ops; + break; + case XFS_BLF_ATTR_RMT_BUF: + if (!xfs_sb_version_hascrc(&mp->m_sb)) + break; + if (magicda != XFS_ATTR3_RMT_MAGIC) { + xfs_warn(mp, "Bad attr remote magic!"); + ASSERT(0); + break; + } + bp->b_ops = &xfs_attr3_rmt_buf_ops; + break; default: break; } } /* + * Perform a 'normal' buffer recovery. Each logged region of the + * buffer should be copied over the corresponding region in the + * given buffer. The bitmap in the buf log format structure indicates + * where to place the logged data. + */ +STATIC void +xlog_recover_do_reg_buffer( + struct xfs_mount *mp, + xlog_recover_item_t *item, + struct xfs_buf *bp, + xfs_buf_log_format_t *buf_f) +{ + int i; + int bit; + int nbits; + int error; + + trace_xfs_log_recover_buf_reg_buf(mp->m_log, buf_f); + + bit = 0; + i = 1; /* 0 is the buf format structure */ + while (1) { + bit = xfs_next_bit(buf_f->blf_data_map, + buf_f->blf_map_size, bit); + if (bit == -1) + break; + nbits = xfs_contig_bits(buf_f->blf_data_map, + buf_f->blf_map_size, bit); + ASSERT(nbits > 0); + ASSERT(item->ri_buf[i].i_addr != NULL); + ASSERT(item->ri_buf[i].i_len % XFS_BLF_CHUNK == 0); + ASSERT(BBTOB(bp->b_io_length) >= + ((uint)bit << XFS_BLF_SHIFT) + (nbits << XFS_BLF_SHIFT)); + + /* + * Do a sanity check if this is a dquot buffer. Just checking + * the first dquot in the buffer should do. XXXThis is + * probably a good thing to do for other buf types also. + */ + error = 0; + if (buf_f->blf_flags & + (XFS_BLF_UDQUOT_BUF|XFS_BLF_PDQUOT_BUF|XFS_BLF_GDQUOT_BUF)) { + if (item->ri_buf[i].i_addr == NULL) { + xfs_alert(mp, + "XFS: NULL dquot in %s.", __func__); + goto next; + } + if (item->ri_buf[i].i_len < sizeof(xfs_disk_dquot_t)) { + xfs_alert(mp, + "XFS: dquot too small (%d) in %s.", + item->ri_buf[i].i_len, __func__); + goto next; + } + error = xfs_qm_dqcheck(mp, item->ri_buf[i].i_addr, + -1, 0, XFS_QMOPT_DOWARN, + "dquot_buf_recover"); + if (error) + goto next; + } + + memcpy(xfs_buf_offset(bp, + (uint)bit << XFS_BLF_SHIFT), /* dest */ + item->ri_buf[i].i_addr, /* source */ + nbits<ri_total); + + xlog_recovery_validate_buf_type(mp, bp, buf_f); + +} + +/* * Do some primitive error checking on ondisk dquot data structures. */ int diff --git a/fs/xfs/xfs_trans.h b/fs/xfs/xfs_trans.h index 1b04fe5..fa78a3f 100644 --- a/fs/xfs/xfs_trans.h +++ b/fs/xfs/xfs_trans.h @@ -507,6 +507,8 @@ void xfs_trans_dquot_buf(xfs_trans_t *, struct xfs_buf *, uint); void xfs_trans_inode_alloc_buf(xfs_trans_t *, struct xfs_buf *); void xfs_trans_buf_set_type(struct xfs_trans *, struct xfs_buf *, uint); +void xfs_trans_buf_copy_type(struct xfs_buf *dst_bp, + struct xfs_buf *src_bp); void xfs_trans_ichgtime(struct xfs_trans *, struct xfs_inode *, int); void xfs_trans_ijoin(struct xfs_trans *, struct xfs_inode *, uint); void xfs_trans_log_buf(xfs_trans_t *, struct xfs_buf *, uint, uint); diff --git a/fs/xfs/xfs_trans_buf.c b/fs/xfs/xfs_trans_buf.c index 8a0f6af..40871bf 100644 --- a/fs/xfs/xfs_trans_buf.c +++ b/fs/xfs/xfs_trans_buf.c @@ -768,6 +768,9 @@ xfs_trans_buf_set_type( { struct xfs_buf_log_item *bip = bp->b_fspriv; + if (!tp) + return; + ASSERT(bp->b_transp == tp); ASSERT(bip != NULL); ASSERT(atomic_read(&bip->bli_refcount) > 0); @@ -777,6 +780,20 @@ xfs_trans_buf_set_type( bip->__bli_format.blf_flags |= type; } +void +xfs_trans_buf_copy_type( + struct xfs_buf *dst_bp, + struct xfs_buf *src_bp) +{ + struct xfs_buf_log_item *sbip = src_bp->b_fspriv; + struct xfs_buf_log_item *dbip = dst_bp->b_fspriv; + uint type; + + type = sbip->__bli_format.blf_flags & XFS_BLF_TYPE_MASK; + dbip->__bli_format.blf_flags &= ~XFS_BLF_TYPE_MASK; + dbip->__bli_format.blf_flags |= type; +} + /* * Similar to xfs_trans_inode_buf(), this marks the buffer as a cluster of * dquots. However, unlike in inode buffer recovery, dquot buffers get -- 1.7.10.4 From dave@fromorbit.com Tue Mar 12 07:31:43 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 418A07FD4 for ; Tue, 12 Mar 2013 07:31:43 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay1.corp.sgi.com (Postfix) with ESMTP id EBEBA8F8049 for ; Tue, 12 Mar 2013 05:31:42 -0700 (PDT) X-ASG-Debug-ID: 1363091499-04bdf022964cb130001-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id zCbWjL7ZHsyIrqIU for ; Tue, 12 Mar 2013 05:31:40 -0700 (PDT) X-Barracuda-Envelope-From: dave@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: Ag0KAKEfP1F5LKiV/2dsb2JhbABDxF0DgUoXdIIoAQEFJy8zCBgxOQMbGYgSsAKQH41eLoRIA5MQiT+Ke4MeKIEv Received: from ppp121-44-168-149.lns20.syd7.internode.on.net (HELO dastard) ([121.44.168.149]) by ipmail05.adl6.internode.on.net with ESMTP; 12 Mar 2013 23:01:39 +1030 Received: from [192.168.1.1] (helo=disappointment) by dastard with esmtp (Exim 4.76) (envelope-from ) id 1UFOMa-0001Sc-PC for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:31:28 +1100 Received: from dave by disappointment with local (Exim 4.80) (envelope-from ) id 1UFOMQ-0002NF-NF for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:31:18 +1100 From: Dave Chinner To: xfs@oss.sgi.com Subject: [PATCH 21/21] xfs: add CRC checks to the superblock Date: Tue, 12 Mar 2013 23:30:54 +1100 X-ASG-Orig-Subj: [PATCH 21/21] xfs: add CRC checks to the superblock Message-Id: <1363091454-8852-22-git-send-email-david@fromorbit.com> X-Mailer: git-send-email 1.7.10.4 In-Reply-To: <1363091454-8852-1-git-send-email-david@fromorbit.com> References: <1363091454-8852-1-git-send-email-david@fromorbit.com> X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1363091499 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124988 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- From: Dave Chinner With the addition of CRCs, there is such a wide and varied change to the on disk format that it makes sense to bump the superblock version number rather than try to use feature bits for all the new functionality. This commit introduces all the new superblock fields needed for all the new functionality: feature masks similar to ext4, separate project quota inodes, a LSN field for recovery and the CRC field. This commit does not bump the superblock version number, however. That will be done as a separate commit at the end of the series after all the new functionality is present so we switch it all on in one commit. This means that we can slowly introduce the changes without them being active and hence maintain bisectability of the tree. This patch is based on a patch originally written by myself back from SGI days, which was subsequently modified by Christoph Hellwig. There is relatively little of that patch remaining, but the history of the patch still should be acknowledged here. Signed-off-by: Dave Chinner --- fs/xfs/xfs_buf_item.h | 4 +- fs/xfs/xfs_log_recover.c | 8 ++++ fs/xfs/xfs_mount.c | 97 ++++++++++++++++++++++++++++++++++++-------- fs/xfs/xfs_mount.h | 1 + fs/xfs/xfs_sb.h | 100 ++++++++++++++++++++++++++++++++-------------- 5 files changed, 164 insertions(+), 46 deletions(-) diff --git a/fs/xfs/xfs_buf_item.h b/fs/xfs/xfs_buf_item.h index 640adcf..ed259a1 100644 --- a/fs/xfs/xfs_buf_item.h +++ b/fs/xfs/xfs_buf_item.h @@ -58,6 +58,7 @@ extern kmem_zone_t *xfs_buf_item_zone; #define XFS_BLF_DA_NODE_BUF (1<<16) #define XFS_BLF_ATTR_LEAF_BUF (1<<17) #define XFS_BLF_ATTR_RMT_BUF (1<<18) +#define XFS_BLF_SB_BUF (1<<19) #define XFS_BLF_TYPE_MASK \ (XFS_BLF_UDQUOT_BUF | \ @@ -76,7 +77,8 @@ extern kmem_zone_t *xfs_buf_item_zone; XFS_BLF_DIR_LEAFN_BUF | \ XFS_BLF_DA_NODE_BUF | \ XFS_BLF_ATTR_LEAF_BUF | \ - XFS_BLF_ATTR_RMT_BUF) + XFS_BLF_ATTR_RMT_BUF | \ + XFS_BLF_SB_BUF) #define XFS_BLF_CHUNK 128 #define XFS_BLF_SHIFT 7 diff --git a/fs/xfs/xfs_log_recover.c b/fs/xfs/xfs_log_recover.c index 4cf2cf2..6410d43 100644 --- a/fs/xfs/xfs_log_recover.c +++ b/fs/xfs/xfs_log_recover.c @@ -2040,6 +2040,14 @@ xlog_recovery_validate_buf_type( } bp->b_ops = &xfs_attr3_rmt_buf_ops; break; + case XFS_BLF_SB_BUF: + if (magic32 != XFS_SB_MAGIC) { + xfs_warn(mp, "Bad SB block magic!"); + ASSERT(0); + break; + } + bp->b_ops = &xfs_sb_buf_ops; + break; default: break; } diff --git a/fs/xfs/xfs_mount.c b/fs/xfs/xfs_mount.c index 3806088..97443c9 100644 --- a/fs/xfs/xfs_mount.c +++ b/fs/xfs/xfs_mount.c @@ -43,6 +43,8 @@ #include "xfs_utils.h" #include "xfs_trace.h" #include "xfs_icache.h" +#include "xfs_cksum.h" +#include "xfs_buf_item.h" #ifdef HAVE_PERCPU_SB @@ -109,6 +111,12 @@ static const struct { { offsetof(xfs_sb_t, sb_logsunit), 0 }, { offsetof(xfs_sb_t, sb_features2), 0 }, { offsetof(xfs_sb_t, sb_bad_features2), 0 }, + { offsetof(xfs_sb_t, sb_features_compat), 0 }, + { offsetof(xfs_sb_t, sb_features_ro_compat), 0 }, + { offsetof(xfs_sb_t, sb_features_incompat), 0 }, + { offsetof(xfs_sb_t, sb_crc), 0 }, + { offsetof(xfs_sb_t, sb_pquotino), 0 }, + { offsetof(xfs_sb_t, sb_lsn), 0 }, { sizeof(xfs_sb_t), 0 } }; @@ -557,6 +565,12 @@ xfs_sb_from_disk( to->sb_logsunit = be32_to_cpu(from->sb_logsunit); to->sb_features2 = be32_to_cpu(from->sb_features2); to->sb_bad_features2 = be32_to_cpu(from->sb_bad_features2); + to->sb_features_compat = be32_to_cpu(from->sb_features_compat); + to->sb_features_ro_compat = be32_to_cpu(from->sb_features_ro_compat); + to->sb_features_incompat = be32_to_cpu(from->sb_features_incompat); + to->sb_crc = be32_to_cpu(from->sb_crc); + to->sb_pquotino = be64_to_cpu(from->sb_pquotino); + to->sb_lsn = be64_to_cpu(from->sb_lsn); } /* @@ -612,13 +626,12 @@ xfs_sb_to_disk( } } -static void +static int xfs_sb_verify( struct xfs_buf *bp) { struct xfs_mount *mp = bp->b_target->bt_mount; struct xfs_sb sb; - int error; xfs_sb_from_disk(&sb, XFS_BUF_TO_SBP(bp)); @@ -626,16 +639,46 @@ xfs_sb_verify( * Only check the in progress field for the primary superblock as * mkfs.xfs doesn't clear it from secondary superblocks. */ - error = xfs_mount_validate_sb(mp, &sb, bp->b_bn == XFS_SB_DADDR); - if (error) - xfs_buf_ioerror(bp, error); + return xfs_mount_validate_sb(mp, &sb, bp->b_bn == XFS_SB_DADDR); } +/* + * If the superblock has the CRC feature bit set or the CRC field is non-null, + * check that the CRC is valid. We check the CRC field is non-null because a + * single bit error could clear the feature bit and unused parts of the + * superblock are supposed to be zero. Hence a non-null crc field indicates that + * we've potentially lost a feature bit and we should check it anyway. + */ static void xfs_sb_read_verify( struct xfs_buf *bp) { - xfs_sb_verify(bp); + struct xfs_mount *mp = bp->b_target->bt_mount; + struct xfs_dsb *dsb = XFS_BUF_TO_SBP(bp); + int error; + + /* + * open code the version check to avoid needing to convert the entire + * superblock from disk order just to check the version number + */ + if (dsb->sb_magicnum == cpu_to_be32(XFS_SB_MAGIC) && + (((be16_to_cpu(dsb->sb_versionnum) & XFS_SB_VERSION_NUMBITS) == + XFS_SB_VERSION_5) || + dsb->sb_crc != 0)) { + + if (!xfs_verify_cksum(bp->b_addr, be16_to_cpu(dsb->sb_sectsize), + offsetof(struct xfs_sb, sb_crc))) { + error = EFSCORRUPTED; + goto out_error; + } + } + error = xfs_sb_verify(bp); + +out_error: + if (error) { + XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, mp, bp->b_addr); + xfs_buf_ioerror(bp, error); + } } /* @@ -648,11 +691,10 @@ static void xfs_sb_quiet_read_verify( struct xfs_buf *bp) { - struct xfs_sb sb; + struct xfs_dsb *dsb = XFS_BUF_TO_SBP(bp); - xfs_sb_from_disk(&sb, XFS_BUF_TO_SBP(bp)); - if (sb.sb_magicnum == XFS_SB_MAGIC) { + if (dsb->sb_magicnum == cpu_to_be32(XFS_SB_MAGIC)) { /* XFS filesystem, verify noisily! */ xfs_sb_read_verify(bp); return; @@ -663,9 +705,27 @@ xfs_sb_quiet_read_verify( static void xfs_sb_write_verify( - struct xfs_buf *bp) + struct xfs_buf *bp) { - xfs_sb_verify(bp); + struct xfs_mount *mp = bp->b_target->bt_mount; + struct xfs_buf_log_item *bip = bp->b_fspriv; + int error; + + error = xfs_sb_verify(bp); + if (error) { + XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, mp, bp->b_addr); + xfs_buf_ioerror(bp, error); + return; + } + + if (!xfs_sb_version_hascrc(&mp->m_sb)) + return; + + if (bip) + XFS_BUF_TO_SBP(bp)->sb_lsn = cpu_to_be64(bip->bli_item.li_lsn); + + xfs_update_cksum(bp->b_addr, BBTOB(bp->b_length), + offsetof(struct xfs_sb, sb_crc)); } const struct xfs_buf_ops xfs_sb_buf_ops = { @@ -687,7 +747,8 @@ int xfs_readsb(xfs_mount_t *mp, int flags) { unsigned int sector_size; - xfs_buf_t *bp; + struct xfs_buf *bp; + struct xfs_sb *sbp = &mp->m_sb; int error; int loud = !(flags & XFS_MFSI_QUIET); @@ -726,10 +787,10 @@ reread: /* * We must be able to do sector-sized and sector-aligned IO. */ - if (sector_size > mp->m_sb.sb_sectsize) { + if (sector_size > sbp->sb_sectsize) { if (loud) xfs_warn(mp, "device supports %u byte sectors (not %u)", - sector_size, mp->m_sb.sb_sectsize); + sector_size, sbp->sb_sectsize); error = ENOSYS; goto release_buf; } @@ -738,15 +799,18 @@ reread: * If device sector size is smaller than the superblock size, * re-read the superblock so the buffer is correctly sized. */ - if (sector_size < mp->m_sb.sb_sectsize) { + if (sector_size < sbp->sb_sectsize) { xfs_buf_relse(bp); - sector_size = mp->m_sb.sb_sectsize; + sector_size = sbp->sb_sectsize; goto reread; } /* Initialize per-cpu counters */ xfs_icsb_reinit_counters(mp); + /* no need to be quiet anymore, so reset the buf ops */ + bp->b_ops = &xfs_sb_buf_ops; + mp->m_sb_bp = bp; xfs_buf_unlock(bp); return 0; @@ -1633,6 +1697,7 @@ xfs_mod_sb(xfs_trans_t *tp, __int64_t fields) ASSERT((1LL << f) & XFS_SB_MOD_BITS); first = xfs_sb_info[f].offset; + xfs_trans_buf_set_type(tp, bp, XFS_BLF_SB_BUF); xfs_trans_log_buf(tp, bp, first, last); } diff --git a/fs/xfs/xfs_mount.h b/fs/xfs/xfs_mount.h index bc90706..157a7d3 100644 --- a/fs/xfs/xfs_mount.h +++ b/fs/xfs/xfs_mount.h @@ -392,6 +392,7 @@ extern void xfs_set_low_space_thresholds(struct xfs_mount *); #endif /* __KERNEL__ */ +extern void xfs_sb_calc_crc(struct xfs_buf *); extern void xfs_mod_sb(struct xfs_trans *, __int64_t); extern int xfs_initialize_perag(struct xfs_mount *, xfs_agnumber_t, xfs_agnumber_t *); diff --git a/fs/xfs/xfs_sb.h b/fs/xfs/xfs_sb.h index a05b451..457fefa 100644 --- a/fs/xfs/xfs_sb.h +++ b/fs/xfs/xfs_sb.h @@ -32,6 +32,7 @@ struct xfs_mount; #define XFS_SB_VERSION_2 2 /* 6.2 - attributes */ #define XFS_SB_VERSION_3 3 /* 6.2 - new inode version */ #define XFS_SB_VERSION_4 4 /* 6.2+ - bitmask version */ +#define XFS_SB_VERSION_5 5 /* CRC enabled filesystem */ #define XFS_SB_VERSION_NUMBITS 0x000f #define XFS_SB_VERSION_ALLFBITS 0xfff0 #define XFS_SB_VERSION_SASHFBITS 0xf000 @@ -161,6 +162,18 @@ typedef struct xfs_sb { */ __uint32_t sb_bad_features2; + /* version 5 superblock fields start here */ + + /* feature masks */ + __uint32_t sb_features_compat; + __uint32_t sb_features_ro_compat; + __uint32_t sb_features_incompat; + + __uint32_t sb_crc; /* superblock crc */ + + xfs_ino_t sb_pquotino; /* project quota inode */ + xfs_lsn_t sb_lsn; /* last write sequence */ + /* must be padded to 64 bit alignment */ } xfs_sb_t; @@ -229,7 +242,19 @@ typedef struct xfs_dsb { * for features2 bits. Easiest just to mark it bad and not use * it for anything else. */ - __be32 sb_bad_features2; + __be32 sb_bad_features2; + + /* version 5 superblock fields start here */ + + /* feature masks */ + __be32 sb_features_compat; + __be32 sb_features_ro_compat; + __be32 sb_features_incompat; + + __le32 sb_crc; /* superblock crc */ + + __be64 sb_pquotino; /* project quota inode */ + __be64 sb_lsn; /* last write sequence */ /* must be padded to 64 bit alignment */ } xfs_dsb_t; @@ -250,7 +275,9 @@ typedef enum { XFS_SBS_GQUOTINO, XFS_SBS_QFLAGS, XFS_SBS_FLAGS, XFS_SBS_SHARED_VN, XFS_SBS_INOALIGNMT, XFS_SBS_UNIT, XFS_SBS_WIDTH, XFS_SBS_DIRBLKLOG, XFS_SBS_LOGSECTLOG, XFS_SBS_LOGSECTSIZE, XFS_SBS_LOGSUNIT, - XFS_SBS_FEATURES2, XFS_SBS_BAD_FEATURES2, + XFS_SBS_FEATURES2, XFS_SBS_BAD_FEATURES2, XFS_SBS_FEATURES_COMPAT, + XFS_SBS_FEATURES_RO_COMPAT, XFS_SBS_FEATURES_INCOMPAT, XFS_SBS_CRC, + XFS_SBS_PQUOTINO, XFS_SBS_LSN, XFS_SBS_FIELDCOUNT } xfs_sb_field_t; @@ -276,6 +303,11 @@ typedef enum { #define XFS_SB_FDBLOCKS XFS_SB_MVAL(FDBLOCKS) #define XFS_SB_FEATURES2 XFS_SB_MVAL(FEATURES2) #define XFS_SB_BAD_FEATURES2 XFS_SB_MVAL(BAD_FEATURES2) +#define XFS_SB_FEATURES_COMPAT XFS_SB_MVAL(FEATURES_COMPAT) +#define XFS_SB_FEATURES_RO_COMPAT XFS_SB_MVAL(FEATURES_RO_COMPAT) +#define XFS_SB_FEATURES_INCOMPAT XFS_SB_MVAL(FEATURES_INCOMPAT) +#define XFS_SB_CRC XFS_SB_MVAL(CRC) +#define XFS_SB_PQUOTINO XFS_SB_MVAL(PQUOTINO) #define XFS_SB_NUM_BITS ((int)XFS_SBS_FIELDCOUNT) #define XFS_SB_ALL_BITS ((1LL << XFS_SB_NUM_BITS) - 1) #define XFS_SB_MOD_BITS \ @@ -283,7 +315,8 @@ typedef enum { XFS_SB_VERSIONNUM | XFS_SB_UQUOTINO | XFS_SB_GQUOTINO | \ XFS_SB_QFLAGS | XFS_SB_SHARED_VN | XFS_SB_UNIT | XFS_SB_WIDTH | \ XFS_SB_ICOUNT | XFS_SB_IFREE | XFS_SB_FDBLOCKS | XFS_SB_FEATURES2 | \ - XFS_SB_BAD_FEATURES2) + XFS_SB_BAD_FEATURES2 | XFS_SB_FEATURES_COMPAT | \ + XFS_SB_FEATURES_RO_COMPAT | XFS_SB_FEATURES_INCOMPAT | XFS_SB_PQUOTINO) /* @@ -325,6 +358,8 @@ static inline int xfs_sb_good_version(xfs_sb_t *sbp) return 1; } + if (XFS_SB_VERSION_NUM(sbp) == XFS_SB_VERSION_5) + return 1; return 0; } @@ -365,7 +400,7 @@ static inline int xfs_sb_version_hasattr(xfs_sb_t *sbp) { return sbp->sb_versionnum == XFS_SB_VERSION_2 || sbp->sb_versionnum == XFS_SB_VERSION_3 || - (XFS_SB_VERSION_NUM(sbp) == XFS_SB_VERSION_4 && + (XFS_SB_VERSION_NUM(sbp) >= XFS_SB_VERSION_4 && (sbp->sb_versionnum & XFS_SB_VERSION_ATTRBIT)); } @@ -373,7 +408,7 @@ static inline void xfs_sb_version_addattr(xfs_sb_t *sbp) { if (sbp->sb_versionnum == XFS_SB_VERSION_1) sbp->sb_versionnum = XFS_SB_VERSION_2; - else if (XFS_SB_VERSION_NUM(sbp) == XFS_SB_VERSION_4) + else if (XFS_SB_VERSION_NUM(sbp) >= XFS_SB_VERSION_4) sbp->sb_versionnum |= XFS_SB_VERSION_ATTRBIT; else sbp->sb_versionnum = XFS_SB_VERSION_4 | XFS_SB_VERSION_ATTRBIT; @@ -382,7 +417,7 @@ static inline void xfs_sb_version_addattr(xfs_sb_t *sbp) static inline int xfs_sb_version_hasnlink(xfs_sb_t *sbp) { return sbp->sb_versionnum == XFS_SB_VERSION_3 || - (XFS_SB_VERSION_NUM(sbp) == XFS_SB_VERSION_4 && + (XFS_SB_VERSION_NUM(sbp) >= XFS_SB_VERSION_4 && (sbp->sb_versionnum & XFS_SB_VERSION_NLINKBIT)); } @@ -396,13 +431,13 @@ static inline void xfs_sb_version_addnlink(xfs_sb_t *sbp) static inline int xfs_sb_version_hasquota(xfs_sb_t *sbp) { - return XFS_SB_VERSION_NUM(sbp) == XFS_SB_VERSION_4 && + return XFS_SB_VERSION_NUM(sbp) >= XFS_SB_VERSION_4 && (sbp->sb_versionnum & XFS_SB_VERSION_QUOTABIT); } static inline void xfs_sb_version_addquota(xfs_sb_t *sbp) { - if (XFS_SB_VERSION_NUM(sbp) == XFS_SB_VERSION_4) + if (XFS_SB_VERSION_NUM(sbp) >= XFS_SB_VERSION_4) sbp->sb_versionnum |= XFS_SB_VERSION_QUOTABIT; else sbp->sb_versionnum = xfs_sb_version_tonew(sbp->sb_versionnum) | @@ -411,13 +446,14 @@ static inline void xfs_sb_version_addquota(xfs_sb_t *sbp) static inline int xfs_sb_version_hasalign(xfs_sb_t *sbp) { - return XFS_SB_VERSION_NUM(sbp) == XFS_SB_VERSION_4 && - (sbp->sb_versionnum & XFS_SB_VERSION_ALIGNBIT); + return (XFS_SB_VERSION_NUM(sbp) == XFS_SB_VERSION_5) || + (XFS_SB_VERSION_NUM(sbp) >= XFS_SB_VERSION_4 && + (sbp->sb_versionnum & XFS_SB_VERSION_ALIGNBIT)); } static inline int xfs_sb_version_hasdalign(xfs_sb_t *sbp) { - return XFS_SB_VERSION_NUM(sbp) == XFS_SB_VERSION_4 && + return XFS_SB_VERSION_NUM(sbp) >= XFS_SB_VERSION_4 && (sbp->sb_versionnum & XFS_SB_VERSION_DALIGNBIT); } @@ -429,38 +465,42 @@ static inline int xfs_sb_version_hasshared(xfs_sb_t *sbp) static inline int xfs_sb_version_hasdirv2(xfs_sb_t *sbp) { - return XFS_SB_VERSION_NUM(sbp) == XFS_SB_VERSION_4 && - (sbp->sb_versionnum & XFS_SB_VERSION_DIRV2BIT); + return (XFS_SB_VERSION_NUM(sbp) == XFS_SB_VERSION_5) || + (XFS_SB_VERSION_NUM(sbp) == XFS_SB_VERSION_4 && + (sbp->sb_versionnum & XFS_SB_VERSION_DIRV2BIT)); } static inline int xfs_sb_version_haslogv2(xfs_sb_t *sbp) { - return XFS_SB_VERSION_NUM(sbp) == XFS_SB_VERSION_4 && - (sbp->sb_versionnum & XFS_SB_VERSION_LOGV2BIT); + return (XFS_SB_VERSION_NUM(sbp) == XFS_SB_VERSION_5) || + (XFS_SB_VERSION_NUM(sbp) >= XFS_SB_VERSION_4 && + (sbp->sb_versionnum & XFS_SB_VERSION_LOGV2BIT)); } static inline int xfs_sb_version_hasextflgbit(xfs_sb_t *sbp) { - return XFS_SB_VERSION_NUM(sbp) == XFS_SB_VERSION_4 && - (sbp->sb_versionnum & XFS_SB_VERSION_EXTFLGBIT); + return (XFS_SB_VERSION_NUM(sbp) == XFS_SB_VERSION_5) || + (XFS_SB_VERSION_NUM(sbp) == XFS_SB_VERSION_4 && + (sbp->sb_versionnum & XFS_SB_VERSION_EXTFLGBIT)); } static inline int xfs_sb_version_hassector(xfs_sb_t *sbp) { - return XFS_SB_VERSION_NUM(sbp) == XFS_SB_VERSION_4 && + return XFS_SB_VERSION_NUM(sbp) >= XFS_SB_VERSION_4 && (sbp->sb_versionnum & XFS_SB_VERSION_SECTORBIT); } static inline int xfs_sb_version_hasasciici(xfs_sb_t *sbp) { - return XFS_SB_VERSION_NUM(sbp) == XFS_SB_VERSION_4 && + return XFS_SB_VERSION_NUM(sbp) >= XFS_SB_VERSION_4 && (sbp->sb_versionnum & XFS_SB_VERSION_BORGBIT); } static inline int xfs_sb_version_hasmorebits(xfs_sb_t *sbp) { - return XFS_SB_VERSION_NUM(sbp) == XFS_SB_VERSION_4 && - (sbp->sb_versionnum & XFS_SB_VERSION_MOREBITSBIT); + return (XFS_SB_VERSION_NUM(sbp) == XFS_SB_VERSION_5) || + (XFS_SB_VERSION_NUM(sbp) == XFS_SB_VERSION_4 && + (sbp->sb_versionnum & XFS_SB_VERSION_MOREBITSBIT)); } /* @@ -475,14 +515,16 @@ static inline int xfs_sb_version_hasmorebits(xfs_sb_t *sbp) static inline int xfs_sb_version_haslazysbcount(xfs_sb_t *sbp) { - return xfs_sb_version_hasmorebits(sbp) && - (sbp->sb_features2 & XFS_SB_VERSION2_LAZYSBCOUNTBIT); + return (XFS_SB_VERSION_NUM(sbp) == XFS_SB_VERSION_5) || + (xfs_sb_version_hasmorebits(sbp) && + (sbp->sb_features2 & XFS_SB_VERSION2_LAZYSBCOUNTBIT)); } static inline int xfs_sb_version_hasattr2(xfs_sb_t *sbp) { - return xfs_sb_version_hasmorebits(sbp) && - (sbp->sb_features2 & XFS_SB_VERSION2_ATTR2BIT); + return (XFS_SB_VERSION_NUM(sbp) == XFS_SB_VERSION_5) || + (xfs_sb_version_hasmorebits(sbp) && + (sbp->sb_features2 & XFS_SB_VERSION2_ATTR2BIT)); } static inline void xfs_sb_version_addattr2(xfs_sb_t *sbp) @@ -500,14 +542,14 @@ static inline void xfs_sb_version_removeattr2(xfs_sb_t *sbp) static inline int xfs_sb_version_hasprojid32bit(xfs_sb_t *sbp) { - return xfs_sb_version_hasmorebits(sbp) && - (sbp->sb_features2 & XFS_SB_VERSION2_PROJID32BIT); + return (XFS_SB_VERSION_NUM(sbp) == XFS_SB_VERSION_5) || + (xfs_sb_version_hasmorebits(sbp) && + (sbp->sb_features2 & XFS_SB_VERSION2_PROJID32BIT)); } static inline int xfs_sb_version_hascrc(xfs_sb_t *sbp) { - return (xfs_sb_version_hasmorebits(sbp) && - (sbp->sb_features2 & XFS_SB_VERSION2_CRCBIT)); + return XFS_SB_VERSION_NUM(sbp) == XFS_SB_VERSION_5; } /* -- 1.7.10.4 From dave@fromorbit.com Tue Mar 12 07:31:45 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 281AB7FDD for ; Tue, 12 Mar 2013 07:31:45 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay3.corp.sgi.com (Postfix) with ESMTP id 6EDD9AC004 for ; Tue, 12 Mar 2013 05:31:44 -0700 (PDT) X-ASG-Debug-ID: 1363091485-04cb6c2b01493060005-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id XnaOOjRG3HbokXTB for ; Tue, 12 Mar 2013 05:31:38 -0700 (PDT) X-Barracuda-Envelope-From: dave@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AtQLAKEfP1F5LKiV/2dsb2JhbAA7CL0Oh08DAYFJF3SCKAEBBRoBDC8zCBgxOQMbGYgSsAKQH41YNHaDUgOTEJQ6gx4o Received: from ppp121-44-168-149.lns20.syd7.internode.on.net (HELO dastard) ([121.44.168.149]) by ipmail05.adl6.internode.on.net with ESMTP; 12 Mar 2013 23:01:29 +1030 Received: from disappointment ([192.168.1.1]) by dastard with esmtp (Exim 4.76) (envelope-from ) id 1UFOMQ-0001SK-Hl for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:31:18 +1100 Received: from dave by disappointment with local (Exim 4.80) (envelope-from ) id 1UFOMQ-0002Mi-Dg for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:31:18 +1100 From: Dave Chinner To: xfs@oss.sgi.com Subject: [PATCH 14/21] xfs: add CRC checking to dir2 leaf blocks Date: Tue, 12 Mar 2013 23:30:47 +1100 X-ASG-Orig-Subj: [PATCH 14/21] xfs: add CRC checking to dir2 leaf blocks Message-Id: <1363091454-8852-15-git-send-email-david@fromorbit.com> X-Mailer: git-send-email 1.7.10.4 In-Reply-To: <1363091454-8852-1-git-send-email-david@fromorbit.com> References: <1363091454-8852-1-git-send-email-david@fromorbit.com> X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1363091497 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124988 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- From: Dave Chinner This addition follows the same pattern as the dir2 block CRCs. Seeing as both LEAF1 and LEAFN types need to changed at the same time, this is a pretty large amount of change. leaf block headers neeed to be abstracted away from the on-disk structures (struct xfs_dir3_icleaf_hdr), as do the base leaf entry locations. This header abstract allows the in-core header and leaf entry location to be passed around instead of the leaf block itself. This saves a lot of converting individual variables from on-disk format to host format where they are used, so there's a good chance that the compiler will be able to produce much more optimal code as it's not having to byteswap variables all over the place. Signed-off-by: Dave Chinner --- fs/xfs/xfs_da_btree.c | 45 ++- fs/xfs/xfs_da_btree.h | 23 ++ fs/xfs/xfs_dir2_block.c | 19 +- fs/xfs/xfs_dir2_format.h | 60 +++- fs/xfs/xfs_dir2_leaf.c | 785 +++++++++++++++++++++++++++++----------------- fs/xfs/xfs_dir2_node.c | 458 +++++++++++++++------------ fs/xfs/xfs_dir2_priv.h | 32 +- 7 files changed, 908 insertions(+), 514 deletions(-) diff --git a/fs/xfs/xfs_da_btree.c b/fs/xfs/xfs_da_btree.c index 4d7696a..2f23b14 100644 --- a/fs/xfs/xfs_da_btree.c +++ b/fs/xfs/xfs_da_btree.c @@ -139,7 +139,8 @@ xfs_da_node_read_verify( bp->b_ops->verify_read(bp); return; case XFS_DIR2_LEAFN_MAGIC: - bp->b_ops = &xfs_dir2_leafn_buf_ops; + case XFS_DIR3_LEAFN_MAGIC: + bp->b_ops = &xfs_dir3_leafn_buf_ops; bp->b_ops->verify_read(bp); return; default: @@ -396,11 +397,18 @@ xfs_da_root_split(xfs_da_state_t *state, xfs_da_state_blk_t *blk1, size = (int)((char *)&oldroot->btree[be16_to_cpu(oldroot->hdr.count)] - (char *)oldroot); } else { - ASSERT(oldroot->hdr.info.magic == cpu_to_be16(XFS_DIR2_LEAFN_MAGIC)); + struct xfs_dir3_icleaf_hdr leafhdr; + struct xfs_dir2_leaf_entry *ents; + leaf = (xfs_dir2_leaf_t *)oldroot; - size = (int)((char *)&leaf->ents[be16_to_cpu(leaf->hdr.count)] - - (char *)leaf); + xfs_dir3_leaf_hdr_from_disk(&leafhdr, leaf); + ents = xfs_dir3_leaf_ents_p(leaf); + + ASSERT(leafhdr.magic == XFS_DIR2_LEAFN_MAGIC || + leafhdr.magic == XFS_DIR3_LEAFN_MAGIC); + size = (int)((char *)&ents[leafhdr.count] - (char *)leaf); } + /* XXX: can't just copy CRC headers from one block to another */ memcpy(node, oldroot, size); xfs_trans_log_buf(tp, bp, 0, size - 1); @@ -424,7 +432,8 @@ xfs_da_root_split(xfs_da_state_t *state, xfs_da_state_blk_t *blk1, node->hdr.count = cpu_to_be16(2); #ifdef DEBUG - if (oldroot->hdr.info.magic == cpu_to_be16(XFS_DIR2_LEAFN_MAGIC)) { + if (oldroot->hdr.info.magic == cpu_to_be16(XFS_DIR2_LEAFN_MAGIC) || + oldroot->hdr.info.magic == cpu_to_be16(XFS_DIR3_LEAFN_MAGIC)) { ASSERT(blk1->blkno >= mp->m_dirleafblk && blk1->blkno < mp->m_dirfreeblk); ASSERT(blk2->blkno >= mp->m_dirleafblk && @@ -782,6 +791,7 @@ xfs_da_blkinfo_onlychild_validate(struct xfs_da_blkinfo *blkinfo, __u16 level) if (level == 1) { ASSERT(magic == cpu_to_be16(XFS_DIR2_LEAFN_MAGIC) || + magic == cpu_to_be16(XFS_DIR3_LEAFN_MAGIC) || magic == cpu_to_be16(XFS_ATTR_LEAF_MAGIC)); } else ASSERT(magic == cpu_to_be16(XFS_DA_NODE_MAGIC)); @@ -1565,6 +1575,7 @@ xfs_da_path_shift(xfs_da_state_t *state, xfs_da_state_path_t *path, info = blk->bp->b_addr; ASSERT(info->magic == cpu_to_be16(XFS_DA_NODE_MAGIC) || info->magic == cpu_to_be16(XFS_DIR2_LEAFN_MAGIC) || + info->magic == cpu_to_be16(XFS_DIR3_LEAFN_MAGIC) || info->magic == cpu_to_be16(XFS_ATTR_LEAF_MAGIC)); blk->magic = be16_to_cpu(info->magic); if (blk->magic == XFS_DA_NODE_MAGIC) { @@ -1584,12 +1595,13 @@ xfs_da_path_shift(xfs_da_state_t *state, xfs_da_state_path_t *path, NULL); break; case XFS_DIR2_LEAFN_MAGIC: + case XFS_DIR3_LEAFN_MAGIC: + blk->magic = XFS_DIR2_LEAFN_MAGIC; blk->hashval = xfs_dir2_leafn_lasthash(blk->bp, NULL); break; default: - ASSERT(blk->magic == XFS_ATTR_LEAF_MAGIC || - blk->magic == XFS_DIR2_LEAFN_MAGIC); + ASSERT(0); break; } } @@ -1833,10 +1845,16 @@ xfs_da_swap_lastblock( /* * Get values from the moved block. */ - if (dead_info->magic == cpu_to_be16(XFS_DIR2_LEAFN_MAGIC)) { + if (dead_info->magic == cpu_to_be16(XFS_DIR2_LEAFN_MAGIC) || + dead_info->magic == cpu_to_be16(XFS_DIR3_LEAFN_MAGIC)) { + struct xfs_dir3_icleaf_hdr leafhdr; + struct xfs_dir2_leaf_entry *ents; + dead_leaf2 = (xfs_dir2_leaf_t *)dead_info; + xfs_dir3_leaf_hdr_from_disk(&leafhdr, dead_leaf2); + ents = xfs_dir3_leaf_ents_p(dead_leaf2); dead_level = 0; - dead_hash = be32_to_cpu(dead_leaf2->ents[be16_to_cpu(dead_leaf2->hdr.count) - 1].hashval); + dead_hash = be32_to_cpu(ents[leafhdr.count - 1].hashval); } else { ASSERT(dead_info->magic == cpu_to_be16(XFS_DA_NODE_MAGIC)); dead_node = (xfs_da_intnode_t *)dead_info; @@ -2281,10 +2299,17 @@ xfs_da_read_buf( XFS_TEST_ERROR((magic != XFS_DA_NODE_MAGIC) && (magic != XFS_ATTR_LEAF_MAGIC) && (magic != XFS_DIR2_LEAF1_MAGIC) && + (magic != XFS_DIR3_LEAF1_MAGIC) && (magic != XFS_DIR2_LEAFN_MAGIC) && + (magic != XFS_DIR3_LEAFN_MAGIC) && (magic1 != XFS_DIR2_BLOCK_MAGIC) && + (magic1 != XFS_DIR3_BLOCK_MAGIC) && (magic1 != XFS_DIR2_DATA_MAGIC) && - (free->hdr.magic != cpu_to_be32(XFS_DIR2_FREE_MAGIC)), + (magic1 != XFS_DIR3_DATA_MAGIC) && + (free->hdr.magic != + cpu_to_be32(XFS_DIR2_FREE_MAGIC)) && + (free->hdr.magic != + cpu_to_be32(XFS_DIR3_FREE_MAGIC)), mp, XFS_ERRTAG_DA_READ_BUF, XFS_RANDOM_DA_READ_BUF))) { trace_xfs_da_btree_corrupt(bp, _RET_IP_); diff --git a/fs/xfs/xfs_da_btree.h b/fs/xfs/xfs_da_btree.h index ee5170c..0854b95 100644 --- a/fs/xfs/xfs_da_btree.h +++ b/fs/xfs/xfs_da_btree.h @@ -47,6 +47,29 @@ typedef struct xfs_da_blkinfo { } xfs_da_blkinfo_t; /* + * CRC enabled directory structure types + * + * The headers change size for the additional verification information, but + * otherwise the tree layouts and contents are unchanged. + */ +#define XFS_DIR3_LEAF1_MAGIC 0x3df1 /* magic number: v2 dirlf single blks */ +#define XFS_DIR3_LEAFN_MAGIC 0x3dff /* magic number: v2 dirlf multi blks */ + +struct xfs_da3_blkinfo { + /* + * the node link manipulation code relies on the fact that the first + * element of this structure is the struct xfs_da_blkinfo so it can + * ignore the differences in the rest of the structures. + */ + struct xfs_da_blkinfo hdr; + __be32 crc; /* CRC of block */ + __be64 blkno; /* first block of the buffer */ + __be64 lsn; /* sequence number of last write */ + uuid_t uuid; /* filesystem we belong to */ + __be64 owner; /* inode that owns the block */ +}; + +/* * This is the structure of the root and intermediate nodes in the Btree. * The leaf nodes are defined above. * diff --git a/fs/xfs/xfs_dir2_block.c b/fs/xfs/xfs_dir2_block.c index de2ae38..dc04537 100644 --- a/fs/xfs/xfs_dir2_block.c +++ b/fs/xfs/xfs_dir2_block.c @@ -1013,6 +1013,8 @@ xfs_dir2_leaf_to_block( __be16 *tagp; /* end of entry (tag) */ int to; /* block/leaf to index */ xfs_trans_t *tp; /* transaction pointer */ + struct xfs_dir2_leaf_entry *ents; + struct xfs_dir3_icleaf_hdr leafhdr; trace_xfs_dir2_leaf_to_block(args); @@ -1020,8 +1022,12 @@ xfs_dir2_leaf_to_block( tp = args->trans; mp = dp->i_mount; leaf = lbp->b_addr; - ASSERT(leaf->hdr.info.magic == cpu_to_be16(XFS_DIR2_LEAF1_MAGIC)); + xfs_dir3_leaf_hdr_from_disk(&leafhdr, leaf); + ents = xfs_dir3_leaf_ents_p(leaf); ltp = xfs_dir2_leaf_tail_p(mp, leaf); + + ASSERT(leafhdr.magic == XFS_DIR2_LEAF1_MAGIC || + leafhdr.magic == XFS_DIR3_LEAF1_MAGIC); /* * If there are data blocks other than the first one, take this * opportunity to remove trailing empty data blocks that may have @@ -1058,7 +1064,7 @@ xfs_dir2_leaf_to_block( * Size of the "leaf" area in the block. */ size = (uint)sizeof(xfs_dir2_block_tail_t) + - (uint)sizeof(*lep) * (be16_to_cpu(leaf->hdr.count) - be16_to_cpu(leaf->hdr.stale)); + (uint)sizeof(*lep) * (leafhdr.count - leafhdr.stale); /* * Look at the last data entry. */ @@ -1087,18 +1093,17 @@ xfs_dir2_leaf_to_block( * Initialize the block tail. */ btp = xfs_dir2_block_tail_p(mp, hdr); - btp->count = cpu_to_be32(be16_to_cpu(leaf->hdr.count) - be16_to_cpu(leaf->hdr.stale)); + btp->count = cpu_to_be32(leafhdr.count - leafhdr.stale); btp->stale = 0; xfs_dir2_block_log_tail(tp, dbp); /* * Initialize the block leaf area. We compact out stale entries. */ lep = xfs_dir2_block_leaf_p(btp); - for (from = to = 0; from < be16_to_cpu(leaf->hdr.count); from++) { - if (leaf->ents[from].address == - cpu_to_be32(XFS_DIR2_NULL_DATAPTR)) + for (from = to = 0; from < leafhdr.count; from++) { + if (ents[from].address == cpu_to_be32(XFS_DIR2_NULL_DATAPTR)) continue; - lep[to++] = leaf->ents[from]; + lep[to++] = ents[from]; } ASSERT(to == be32_to_cpu(btp->count)); xfs_dir2_block_log_leaf(tp, dbp, 0, be32_to_cpu(btp->count) - 1); diff --git a/fs/xfs/xfs_dir2_format.h b/fs/xfs/xfs_dir2_format.h index dfc8ccf..8bb4efe 100644 --- a/fs/xfs/xfs_dir2_format.h +++ b/fs/xfs/xfs_dir2_format.h @@ -470,6 +470,21 @@ typedef struct xfs_dir2_leaf_hdr { __be16 stale; /* count of stale entries */ } xfs_dir2_leaf_hdr_t; +struct xfs_dir3_leaf_hdr { + struct xfs_da3_blkinfo info; /* header for da routines */ + __be16 count; /* count of entries */ + __be16 stale; /* count of stale entries */ + __be32 pad; +}; + +struct xfs_dir3_icleaf_hdr { + __uint32_t forw; + __uint32_t back; + __uint16_t magic; + __uint16_t count; + __uint16_t stale; +}; + /* * Leaf block entry. */ @@ -489,23 +504,50 @@ typedef struct xfs_dir2_leaf_tail { * Leaf block. */ typedef struct xfs_dir2_leaf { - xfs_dir2_leaf_hdr_t hdr; /* leaf header */ - xfs_dir2_leaf_entry_t ents[]; /* entries */ + xfs_dir2_leaf_hdr_t hdr; /* leaf header */ + xfs_dir2_leaf_entry_t __ents[]; /* entries */ } xfs_dir2_leaf_t; -/* - * DB blocks here are logical directory block numbers, not filesystem blocks. - */ +struct xfs_dir3_leaf { + struct xfs_dir3_leaf_hdr hdr; /* leaf header */ + struct xfs_dir2_leaf_entry __ents[]; /* entries */ +}; + +#define XFS_DIR3_LEAF_CRC_OFF offsetof(struct xfs_dir3_leaf_hdr, info.crc) + +static inline int +xfs_dir3_leaf_hdr_size(struct xfs_dir2_leaf *lp) +{ + if (lp->hdr.info.magic == cpu_to_be16(XFS_DIR3_LEAF1_MAGIC) || + lp->hdr.info.magic == cpu_to_be16(XFS_DIR3_LEAFN_MAGIC)) + return sizeof(struct xfs_dir3_leaf_hdr); + return sizeof(struct xfs_dir2_leaf_hdr); +} -static inline int xfs_dir2_max_leaf_ents(struct xfs_mount *mp) +static inline int +xfs_dir3_max_leaf_ents(struct xfs_mount *mp, struct xfs_dir2_leaf *lp) { - return (mp->m_dirblksize - (uint)sizeof(struct xfs_dir2_leaf_hdr)) / + return (mp->m_dirblksize - xfs_dir3_leaf_hdr_size(lp)) / (uint)sizeof(struct xfs_dir2_leaf_entry); } /* * Get address of the bestcount field in the single-leaf block. */ +static inline struct xfs_dir2_leaf_entry * +xfs_dir3_leaf_ents_p(struct xfs_dir2_leaf *lp) +{ + if (lp->hdr.info.magic == cpu_to_be16(XFS_DIR3_LEAF1_MAGIC) || + lp->hdr.info.magic == cpu_to_be16(XFS_DIR3_LEAFN_MAGIC)) { + struct xfs_dir3_leaf *lp3 = (struct xfs_dir3_leaf *)lp; + return lp3->__ents; + } + return lp->__ents; +} + +/* + * Get address of the bestcount field in the single-leaf block. + */ static inline struct xfs_dir2_leaf_tail * xfs_dir2_leaf_tail_p(struct xfs_mount *mp, struct xfs_dir2_leaf *lp) { @@ -524,6 +566,10 @@ xfs_dir2_leaf_bests_p(struct xfs_dir2_leaf_tail *ltp) } /* + * DB blocks here are logical directory block numbers, not filesystem blocks. + */ + +/* * Convert dataptr to byte in file space */ static inline xfs_dir2_off_t diff --git a/fs/xfs/xfs_dir2_leaf.c b/fs/xfs/xfs_dir2_leaf.c index c7dca95..71b03fc 100644 --- a/fs/xfs/xfs_dir2_leaf.c +++ b/fs/xfs/xfs_dir2_leaf.c @@ -1,5 +1,6 @@ /* * Copyright (c) 2000-2003,2005 Silicon Graphics, Inc. + * Copyright (c) 2013 Red Hat, Inc. * All Rights Reserved. * * This program is free software; you can redistribute it and/or @@ -33,77 +34,261 @@ #include "xfs_dir2_priv.h" #include "xfs_error.h" #include "xfs_trace.h" +#include "xfs_buf_item.h" +#include "xfs_cksum.h" /* * Local function declarations. */ #ifdef DEBUG -static void xfs_dir2_leaf_check(struct xfs_inode *dp, struct xfs_buf *bp); -#else -#define xfs_dir2_leaf_check(dp, bp) +#define xfs_dir3_leaf_check(mp, bp) \ +do { \ + if (!xfs_dir3_leaf1_check((mp), (bp))) \ + ASSERT(0); \ +} while (0); #endif + static int xfs_dir2_leaf_lookup_int(xfs_da_args_t *args, struct xfs_buf **lbpp, int *indexp, struct xfs_buf **dbpp); -static void xfs_dir2_leaf_log_bests(struct xfs_trans *tp, struct xfs_buf *bp, +static void xfs_dir3_leaf_log_bests(struct xfs_trans *tp, struct xfs_buf *bp, int first, int last); -static void xfs_dir2_leaf_log_tail(struct xfs_trans *tp, struct xfs_buf *bp); +static void xfs_dir3_leaf_log_tail(struct xfs_trans *tp, struct xfs_buf *bp); -static void -xfs_dir2_leaf_verify( +void +xfs_dir3_leaf_hdr_from_disk( + struct xfs_dir3_icleaf_hdr *to, + struct xfs_dir2_leaf *from) +{ + if (from->hdr.info.magic == cpu_to_be16(XFS_DIR2_LEAF1_MAGIC) || + from->hdr.info.magic == cpu_to_be16(XFS_DIR2_LEAFN_MAGIC)) { + to->forw = be32_to_cpu(from->hdr.info.forw); + to->back = be32_to_cpu(from->hdr.info.back); + to->magic = be16_to_cpu(from->hdr.info.magic); + to->count = be16_to_cpu(from->hdr.count); + to->stale = be16_to_cpu(from->hdr.stale); + } else { + struct xfs_dir3_leaf_hdr *hdr3 = (struct xfs_dir3_leaf_hdr *)from; + + to->forw = be32_to_cpu(hdr3->info.hdr.forw); + to->back = be32_to_cpu(hdr3->info.hdr.back); + to->magic = be16_to_cpu(hdr3->info.hdr.magic); + to->count = be16_to_cpu(hdr3->count); + to->stale = be16_to_cpu(hdr3->stale); + } + + ASSERT(to->magic == XFS_DIR2_LEAF1_MAGIC || + to->magic == XFS_DIR3_LEAF1_MAGIC || + to->magic == XFS_DIR2_LEAFN_MAGIC || + to->magic == XFS_DIR3_LEAFN_MAGIC); +} + +void +xfs_dir3_leaf_hdr_to_disk( + struct xfs_dir2_leaf *to, + struct xfs_dir3_icleaf_hdr *from) +{ + ASSERT(from->magic == XFS_DIR2_LEAF1_MAGIC || + from->magic == XFS_DIR3_LEAF1_MAGIC || + from->magic == XFS_DIR2_LEAFN_MAGIC || + from->magic == XFS_DIR3_LEAFN_MAGIC); + + if (from->magic == XFS_DIR2_LEAF1_MAGIC || + from->magic == XFS_DIR2_LEAFN_MAGIC) { + to->hdr.info.forw = cpu_to_be32(from->forw); + to->hdr.info.back = cpu_to_be32(from->back); + to->hdr.info.magic = cpu_to_be16(from->magic); + to->hdr.count = cpu_to_be16(from->count); + to->hdr.stale = cpu_to_be16(from->stale); + } else { + struct xfs_dir3_leaf_hdr *hdr3 = (struct xfs_dir3_leaf_hdr *)to; + + hdr3->info.hdr.forw = cpu_to_be32(from->forw); + hdr3->info.hdr.back = cpu_to_be32(from->back); + hdr3->info.hdr.magic = cpu_to_be16(from->magic); + hdr3->count = cpu_to_be16(from->count); + hdr3->stale = cpu_to_be16(from->stale); + } +} + +bool +xfs_dir3_leaf_check_int( + struct xfs_mount *mp, + struct xfs_dir3_icleaf_hdr *hdr, + struct xfs_dir2_leaf *leaf) +{ + struct xfs_dir2_leaf_entry *ents; + xfs_dir2_leaf_tail_t *ltp; + int stale; + int i; + + ents = xfs_dir3_leaf_ents_p(leaf); + ltp = xfs_dir2_leaf_tail_p(mp, leaf); + + /* + * This value is not restrictive enough. + * Should factor in the size of the bests table as well. + * We can deduce a value for that from di_size. + */ + if (hdr->count > xfs_dir3_max_leaf_ents(mp, leaf)) + return false; + + /* Leaves and bests don't overlap in leaf format. */ + if ((hdr->magic == XFS_DIR2_LEAF1_MAGIC || + hdr->magic == XFS_DIR3_LEAF1_MAGIC) && + (char *)&ents[hdr->count] > (char *)xfs_dir2_leaf_bests_p(ltp)) + return false; + + /* Check hash value order, count stale entries. */ + for (i = stale = 0; i < hdr->count; i++) { + if (i + 1 < hdr->count) { + if (be32_to_cpu(ents[i].hashval) > + be32_to_cpu(ents[i + 1].hashval)) + return false; + } + if (ents[i].address == cpu_to_be32(XFS_DIR2_NULL_DATAPTR)) + stale++; + } + if (hdr->stale != stale) + return false; + return true; +} + +/* + * Check the internal consistency of a leaf1 block. + * Pop an assert if something is wrong. + */ +STATIC bool +xfs_dir3_leaf1_check( + struct xfs_mount *mp, + struct xfs_buf *bp) +{ + struct xfs_dir2_leaf *leaf = bp->b_addr; + struct xfs_dir3_icleaf_hdr leafhdr; + + xfs_dir3_leaf_hdr_from_disk(&leafhdr, leaf); + + if (leafhdr.magic == XFS_DIR3_LEAF1_MAGIC) { + struct xfs_dir3_leaf_hdr *leaf3 = bp->b_addr; + if (be64_to_cpu(leaf3->info.blkno) != bp->b_bn) + return false; + } else if (leafhdr.magic != XFS_DIR2_LEAF1_MAGIC) + return false; + + return xfs_dir3_leaf_check_int(mp, &leafhdr, leaf); +} + +static bool +xfs_dir3_leaf_verify( struct xfs_buf *bp, __be16 magic) { struct xfs_mount *mp = bp->b_target->bt_mount; - struct xfs_dir2_leaf_hdr *hdr = bp->b_addr; - int block_ok = 0; + struct xfs_dir2_leaf *leaf = bp->b_addr; + struct xfs_dir3_icleaf_hdr leafhdr; + + ASSERT(magic == XFS_DIR2_LEAF1_MAGIC || magic == XFS_DIR2_LEAFN_MAGIC); + + xfs_dir3_leaf_hdr_from_disk(&leafhdr, leaf); + if (xfs_sb_version_hascrc(&mp->m_sb)) { + struct xfs_dir3_leaf_hdr *leaf3 = bp->b_addr; + + if ((magic == XFS_DIR2_LEAF1_MAGIC && + leafhdr.magic != XFS_DIR3_LEAF1_MAGIC) || + (magic == XFS_DIR2_LEAFN_MAGIC && + leafhdr.magic != XFS_DIR3_LEAFN_MAGIC)) + return false; - block_ok = hdr->info.magic == magic; - if (!block_ok) { - XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, mp, hdr); + if (!uuid_equal(&leaf3->info.uuid, &mp->m_sb.sb_uuid)) + return false; + if (be64_to_cpu(leaf3->info.blkno) != bp->b_bn) + return false; + } else { + if (leafhdr.magic != magic) + return false; + } + return xfs_dir3_leaf_check_int(mp, &leafhdr, leaf); +} + +static void +__read_verify( + struct xfs_buf *bp, + __uint16_t magic) +{ + struct xfs_mount *mp = bp->b_target->bt_mount; + + if ((xfs_sb_version_hascrc(&mp->m_sb) && + !xfs_verify_cksum(bp->b_addr, BBTOB(bp->b_length), + XFS_DIR3_LEAF_CRC_OFF)) || + !xfs_dir3_leaf_verify(bp, magic)) { + XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, mp, bp->b_addr); xfs_buf_ioerror(bp, EFSCORRUPTED); } } static void -xfs_dir2_leaf1_read_verify( +__write_verify( + struct xfs_buf *bp, + __uint16_t magic) +{ + struct xfs_mount *mp = bp->b_target->bt_mount; + struct xfs_buf_log_item *bip = bp->b_fspriv; + struct xfs_dir3_leaf_hdr *hdr3 = bp->b_addr; + + if (!xfs_dir3_leaf_verify(bp, magic)) { + XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, mp, bp->b_addr); + xfs_buf_ioerror(bp, EFSCORRUPTED); + return; + } + + if (!xfs_sb_version_hascrc(&mp->m_sb)) + return; + + if (bip) + hdr3->info.lsn = cpu_to_be64(bip->bli_item.li_lsn); + + xfs_update_cksum(bp->b_addr, BBTOB(bp->b_length), XFS_DIR3_LEAF_CRC_OFF); +} + +static void +xfs_dir3_leaf1_read_verify( struct xfs_buf *bp) { - xfs_dir2_leaf_verify(bp, cpu_to_be16(XFS_DIR2_LEAF1_MAGIC)); + __read_verify(bp, XFS_DIR2_LEAF1_MAGIC); } static void -xfs_dir2_leaf1_write_verify( +xfs_dir3_leaf1_write_verify( struct xfs_buf *bp) { - xfs_dir2_leaf_verify(bp, cpu_to_be16(XFS_DIR2_LEAF1_MAGIC)); + __write_verify(bp, XFS_DIR2_LEAF1_MAGIC); } -void -xfs_dir2_leafn_read_verify( +static void +xfs_dir3_leafn_read_verify( struct xfs_buf *bp) { - xfs_dir2_leaf_verify(bp, cpu_to_be16(XFS_DIR2_LEAFN_MAGIC)); + __read_verify(bp, XFS_DIR2_LEAFN_MAGIC); } -void -xfs_dir2_leafn_write_verify( +static void +xfs_dir3_leafn_write_verify( struct xfs_buf *bp) { - xfs_dir2_leaf_verify(bp, cpu_to_be16(XFS_DIR2_LEAFN_MAGIC)); + __write_verify(bp, XFS_DIR2_LEAFN_MAGIC); } -static const struct xfs_buf_ops xfs_dir2_leaf1_buf_ops = { - .verify_read = xfs_dir2_leaf1_read_verify, - .verify_write = xfs_dir2_leaf1_write_verify, +static const struct xfs_buf_ops xfs_dir3_leaf1_buf_ops = { + .verify_read = xfs_dir3_leaf1_read_verify, + .verify_write = xfs_dir3_leaf1_write_verify, }; -const struct xfs_buf_ops xfs_dir2_leafn_buf_ops = { - .verify_read = xfs_dir2_leafn_read_verify, - .verify_write = xfs_dir2_leafn_write_verify, +const struct xfs_buf_ops xfs_dir3_leafn_buf_ops = { + .verify_read = xfs_dir3_leafn_read_verify, + .verify_write = xfs_dir3_leafn_write_verify, }; static int -xfs_dir2_leaf_read( +xfs_dir3_leaf_read( struct xfs_trans *tp, struct xfs_inode *dp, xfs_dablk_t fbno, @@ -111,11 +296,11 @@ xfs_dir2_leaf_read( struct xfs_buf **bpp) { return xfs_da_read_buf(tp, dp, fbno, mappedbno, bpp, - XFS_DATA_FORK, &xfs_dir2_leaf1_buf_ops); + XFS_DATA_FORK, &xfs_dir3_leaf1_buf_ops); } int -xfs_dir2_leafn_read( +xfs_dir3_leafn_read( struct xfs_trans *tp, struct xfs_inode *dp, xfs_dablk_t fbno, @@ -123,7 +308,81 @@ xfs_dir2_leafn_read( struct xfs_buf **bpp) { return xfs_da_read_buf(tp, dp, fbno, mappedbno, bpp, - XFS_DATA_FORK, &xfs_dir2_leafn_buf_ops); + XFS_DATA_FORK, &xfs_dir3_leafn_buf_ops); +} + +/* + * Initialize a new leaf block, leaf1 or leafn magic accepted. + */ +static void +xfs_dir3_leaf_init( + struct xfs_mount *mp, + struct xfs_buf *bp, + xfs_ino_t owner, + __uint16_t type) +{ + struct xfs_dir2_leaf *leaf = bp->b_addr; + + ASSERT(type == XFS_DIR2_LEAF1_MAGIC || type == XFS_DIR2_LEAFN_MAGIC); + + if (xfs_sb_version_hascrc(&mp->m_sb)) { + struct xfs_dir3_leaf_hdr *leaf3 = bp->b_addr; + + memset(leaf3, 0, sizeof(*leaf3)); + + leaf3->info.hdr.magic = (type == XFS_DIR2_LEAF1_MAGIC) + ? cpu_to_be16(XFS_DIR3_LEAF1_MAGIC) + : cpu_to_be16(XFS_DIR3_LEAFN_MAGIC); + leaf3->info.blkno = cpu_to_be64(bp->b_bn); + leaf3->info.owner = cpu_to_be64(owner); + uuid_copy(&leaf3->info.uuid, &mp->m_sb.sb_uuid); + } else { + memset(leaf, 0, sizeof(*leaf)); + leaf->hdr.info.magic = cpu_to_be16(type); + } + + /* + * If it's a leaf-format directory initialize the tail. + * Caller is responsible for initialising the bests table. + */ + if (type == XFS_DIR2_LEAF1_MAGIC) { + struct xfs_dir2_leaf_tail *ltp; + + ltp = xfs_dir2_leaf_tail_p(mp, leaf); + ltp->bestcount = 0; + bp->b_ops = &xfs_dir3_leaf1_buf_ops; + } else + bp->b_ops = &xfs_dir3_leafn_buf_ops; +} + +int +xfs_dir3_leaf_get_buf( + xfs_da_args_t *args, + xfs_dir2_db_t bno, + struct xfs_buf **bpp, + __uint16_t magic) +{ + struct xfs_inode *dp = args->dp; + struct xfs_trans *tp = args->trans; + struct xfs_mount *mp = dp->i_mount; + struct xfs_buf *bp; + int error; + + ASSERT(magic == XFS_DIR2_LEAF1_MAGIC || magic == XFS_DIR2_LEAFN_MAGIC); + ASSERT(bno >= XFS_DIR2_LEAF_FIRSTDB(mp) && + bno < XFS_DIR2_FREE_FIRSTDB(mp)); + + error = xfs_da_get_buf(tp, dp, xfs_dir2_db_to_da(mp, bno), -1, &bp, + XFS_DATA_FORK); + if (error) + return error; + + xfs_dir3_leaf_init(mp, bp, dp->i_ino, magic); + xfs_dir3_leaf_log_header(tp, bp); + if (magic == XFS_DIR2_LEAF1_MAGIC) + xfs_dir3_leaf_log_tail(tp, bp); + *bpp = bp; + return 0; } /* @@ -150,6 +409,8 @@ xfs_dir2_block_to_leaf( int needscan; /* need to rescan bestfree */ xfs_trans_t *tp; /* transaction pointer */ struct xfs_dir2_data_free *bf; + struct xfs_dir2_leaf_entry *ents; + struct xfs_dir3_icleaf_hdr leafhdr; trace_xfs_dir2_block_to_leaf(args); @@ -169,27 +430,34 @@ xfs_dir2_block_to_leaf( /* * Initialize the leaf block, get a buffer for it. */ - if ((error = xfs_dir2_leaf_init(args, ldb, &lbp, XFS_DIR2_LEAF1_MAGIC))) { + error = xfs_dir3_leaf_get_buf(args, ldb, &lbp, XFS_DIR2_LEAF1_MAGIC); + if (error) return error; - } - ASSERT(lbp != NULL); + leaf = lbp->b_addr; hdr = dbp->b_addr; xfs_dir3_data_check(dp, dbp); btp = xfs_dir2_block_tail_p(mp, hdr); blp = xfs_dir2_block_leaf_p(btp); bf = xfs_dir3_data_bestfree_p(hdr); + ents = xfs_dir3_leaf_ents_p(leaf); + /* * Set the counts in the leaf header. + * + * XXX: are these actually logged, or just gathered by chance? */ - leaf->hdr.count = cpu_to_be16(be32_to_cpu(btp->count)); - leaf->hdr.stale = cpu_to_be16(be32_to_cpu(btp->stale)); + xfs_dir3_leaf_hdr_from_disk(&leafhdr, leaf); + leafhdr.count = be32_to_cpu(btp->count); + leafhdr.stale = be32_to_cpu(btp->stale); + xfs_dir3_leaf_hdr_to_disk(leaf, &leafhdr); + /* * Could compact these but I think we always do the conversion * after squeezing out stale entries. */ - memcpy(leaf->ents, blp, be32_to_cpu(btp->count) * sizeof(xfs_dir2_leaf_entry_t)); - xfs_dir2_leaf_log_ents(tp, lbp, 0, be16_to_cpu(leaf->hdr.count) - 1); + memcpy(ents, blp, be32_to_cpu(btp->count) * sizeof(xfs_dir2_leaf_entry_t)); + xfs_dir3_leaf_log_ents(tp, lbp, 0, leafhdr.count - 1); needscan = 0; needlog = 1; /* @@ -224,15 +492,16 @@ xfs_dir2_block_to_leaf( */ if (needlog) xfs_dir2_data_log_header(tp, dbp); - xfs_dir2_leaf_check(dp, lbp); + xfs_dir3_leaf_check(mp, lbp); xfs_dir3_data_check(dp, dbp); - xfs_dir2_leaf_log_bests(tp, lbp, 0, 0); + xfs_dir3_leaf_log_bests(tp, lbp, 0, 0); return 0; } STATIC void -xfs_dir2_leaf_find_stale( - struct xfs_dir2_leaf *leaf, +xfs_dir3_leaf_find_stale( + struct xfs_dir3_icleaf_hdr *leafhdr, + struct xfs_dir2_leaf_entry *ents, int index, int *lowstale, int *highstale) @@ -241,7 +510,7 @@ xfs_dir2_leaf_find_stale( * Find the first stale entry before our index, if any. */ for (*lowstale = index - 1; *lowstale >= 0; --*lowstale) { - if (leaf->ents[*lowstale].address == + if (ents[*lowstale].address == cpu_to_be32(XFS_DIR2_NULL_DATAPTR)) break; } @@ -251,10 +520,8 @@ xfs_dir2_leaf_find_stale( * Stop if the result would require moving more entries than using * lowstale. */ - for (*highstale = index; - *highstale < be16_to_cpu(leaf->hdr.count); - ++*highstale) { - if (leaf->ents[*highstale].address == + for (*highstale = index; *highstale < leafhdr->count; ++*highstale) { + if (ents[*highstale].address == cpu_to_be32(XFS_DIR2_NULL_DATAPTR)) break; if (*lowstale >= 0 && index - *lowstale <= *highstale - index) @@ -263,8 +530,9 @@ xfs_dir2_leaf_find_stale( } struct xfs_dir2_leaf_entry * -xfs_dir2_leaf_find_entry( - xfs_dir2_leaf_t *leaf, /* leaf structure */ +xfs_dir3_leaf_find_entry( + struct xfs_dir3_icleaf_hdr *leafhdr, + struct xfs_dir2_leaf_entry *ents, int index, /* leaf table position */ int compact, /* need to compact leaves */ int lowstale, /* index of prev stale leaf */ @@ -272,7 +540,7 @@ xfs_dir2_leaf_find_entry( int *lfloglow, /* low leaf logging index */ int *lfloghigh) /* high leaf logging index */ { - if (!leaf->hdr.stale) { + if (!leafhdr->stale) { xfs_dir2_leaf_entry_t *lep; /* leaf entry table pointer */ /* @@ -280,18 +548,16 @@ xfs_dir2_leaf_find_entry( * * If there are no stale entries, just insert a hole at index. */ - lep = &leaf->ents[index]; - if (index < be16_to_cpu(leaf->hdr.count)) + lep = &ents[index]; + if (index < leafhdr->count) memmove(lep + 1, lep, - (be16_to_cpu(leaf->hdr.count) - index) * - sizeof(*lep)); + (leafhdr->count - index) * sizeof(*lep)); /* * Record low and high logging indices for the leaf. */ *lfloglow = index; - *lfloghigh = be16_to_cpu(leaf->hdr.count); - be16_add_cpu(&leaf->hdr.count, 1); + *lfloghigh = leafhdr->count++; return lep; } @@ -305,16 +571,17 @@ xfs_dir2_leaf_find_entry( * entries before and after our insertion point. */ if (compact == 0) - xfs_dir2_leaf_find_stale(leaf, index, &lowstale, &highstale); + xfs_dir3_leaf_find_stale(leafhdr, ents, index, + &lowstale, &highstale); /* * If the low one is better, use it. */ if (lowstale >= 0 && - (highstale == be16_to_cpu(leaf->hdr.count) || + (highstale == leafhdr->count || index - lowstale - 1 < highstale - index)) { ASSERT(index - lowstale - 1 >= 0); - ASSERT(leaf->ents[lowstale].address == + ASSERT(ents[lowstale].address == cpu_to_be32(XFS_DIR2_NULL_DATAPTR)); /* @@ -322,37 +589,34 @@ xfs_dir2_leaf_find_entry( * for the new entry. */ if (index - lowstale - 1 > 0) { - memmove(&leaf->ents[lowstale], - &leaf->ents[lowstale + 1], + memmove(&ents[lowstale], &ents[lowstale + 1], (index - lowstale - 1) * - sizeof(xfs_dir2_leaf_entry_t)); + sizeof(xfs_dir2_leaf_entry_t)); } *lfloglow = MIN(lowstale, *lfloglow); *lfloghigh = MAX(index - 1, *lfloghigh); - be16_add_cpu(&leaf->hdr.stale, -1); - return &leaf->ents[index - 1]; + leafhdr->stale--; + return &ents[index - 1]; } /* * The high one is better, so use that one. */ ASSERT(highstale - index >= 0); - ASSERT(leaf->ents[highstale].address == - cpu_to_be32(XFS_DIR2_NULL_DATAPTR)); + ASSERT(ents[highstale].address == cpu_to_be32(XFS_DIR2_NULL_DATAPTR)); /* * Copy entries down to cover the stale entry and make room for the * new entry. */ if (highstale - index > 0) { - memmove(&leaf->ents[index + 1], - &leaf->ents[index], + memmove(&ents[index + 1], &ents[index], (highstale - index) * sizeof(xfs_dir2_leaf_entry_t)); } *lfloglow = MIN(index, *lfloglow); *lfloghigh = MAX(highstale, *lfloghigh); - be16_add_cpu(&leaf->hdr.stale, -1); - return &leaf->ents[index]; + leafhdr->stale--; + return &ents[index]; } /* @@ -390,6 +654,8 @@ xfs_dir2_leaf_addname( xfs_trans_t *tp; /* transaction pointer */ xfs_dir2_db_t use_block; /* data block number */ struct xfs_dir2_data_free *bf; /* bestfree table */ + struct xfs_dir2_leaf_entry *ents; + struct xfs_dir3_icleaf_hdr leafhdr; trace_xfs_dir2_leaf_addname(args); @@ -397,7 +663,7 @@ xfs_dir2_leaf_addname( tp = args->trans; mp = dp->i_mount; - error = xfs_dir2_leaf_read(tp, dp, mp->m_dirleafblk, -1, &lbp); + error = xfs_dir3_leaf_read(tp, dp, mp->m_dirleafblk, -1, &lbp); if (error) return error; @@ -410,16 +676,19 @@ xfs_dir2_leaf_addname( index = xfs_dir2_leaf_search_hash(args, lbp); leaf = lbp->b_addr; ltp = xfs_dir2_leaf_tail_p(mp, leaf); + ents = xfs_dir3_leaf_ents_p(leaf); + xfs_dir3_leaf_hdr_from_disk(&leafhdr, leaf); bestsp = xfs_dir2_leaf_bests_p(ltp); length = xfs_dir2_data_entsize(args->namelen); + /* * See if there are any entries with the same hash value * and space in their block for the new entry. * This is good because it puts multiple same-hash value entries * in a data block, improving the lookup of those entries. */ - for (use_block = -1, lep = &leaf->ents[index]; - index < be16_to_cpu(leaf->hdr.count) && be32_to_cpu(lep->hashval) == args->hashval; + for (use_block = -1, lep = &ents[index]; + index < leafhdr.count && be32_to_cpu(lep->hashval) == args->hashval; index++, lep++) { if (be32_to_cpu(lep->address) == XFS_DIR2_NULL_DATAPTR) continue; @@ -452,7 +721,7 @@ xfs_dir2_leaf_addname( * How many bytes do we need in the leaf block? */ needbytes = 0; - if (!leaf->hdr.stale) + if (!leafhdr.stale) needbytes += sizeof(xfs_dir2_leaf_entry_t); if (use_block == -1) needbytes += sizeof(xfs_dir2_data_off_t); @@ -467,16 +736,15 @@ xfs_dir2_leaf_addname( * If we don't have enough free bytes but we can make enough * by compacting out stale entries, we'll do that. */ - if ((char *)bestsp - (char *)&leaf->ents[be16_to_cpu(leaf->hdr.count)] < - needbytes && be16_to_cpu(leaf->hdr.stale) > 1) { + if ((char *)bestsp - (char *)&ents[leafhdr.count] < needbytes && + leafhdr.stale > 1) compact = 1; - } + /* * Otherwise if we don't have enough free bytes we need to * convert to node form. */ - else if ((char *)bestsp - (char *)&leaf->ents[be16_to_cpu( - leaf->hdr.count)] < needbytes) { + else if ((char *)bestsp - (char *)&ents[leafhdr.count] < needbytes) { /* * Just checking or no space reservation, give up. */ @@ -524,15 +792,15 @@ xfs_dir2_leaf_addname( * point later. */ if (compact) { - xfs_dir2_leaf_compact_x1(lbp, &index, &lowstale, &highstale, - &lfloglow, &lfloghigh); + xfs_dir3_leaf_compact_x1(&leafhdr, ents, &index, &lowstale, + &highstale, &lfloglow, &lfloghigh); } /* * There are stale entries, so we'll need log-low and log-high * impossibly bad values later. */ - else if (be16_to_cpu(leaf->hdr.stale)) { - lfloglow = be16_to_cpu(leaf->hdr.count); + else if (leafhdr.stale) { + lfloglow = leafhdr.count; lfloghigh = -1; } /* @@ -564,14 +832,14 @@ xfs_dir2_leaf_addname( memmove(&bestsp[0], &bestsp[1], be32_to_cpu(ltp->bestcount) * sizeof(bestsp[0])); be32_add_cpu(<p->bestcount, 1); - xfs_dir2_leaf_log_tail(tp, lbp); - xfs_dir2_leaf_log_bests(tp, lbp, 0, be32_to_cpu(ltp->bestcount) - 1); + xfs_dir3_leaf_log_tail(tp, lbp); + xfs_dir3_leaf_log_bests(tp, lbp, 0, be32_to_cpu(ltp->bestcount) - 1); } /* * If we're filling in a previously empty block just log it. */ else - xfs_dir2_leaf_log_bests(tp, lbp, use_block, use_block); + xfs_dir3_leaf_log_bests(tp, lbp, use_block, use_block); hdr = dbp->b_addr; bf = xfs_dir3_data_bestfree_p(hdr); bestsp[use_block] = bf[0].length; @@ -632,10 +900,10 @@ xfs_dir2_leaf_addname( if (be16_to_cpu(bestsp[use_block]) != be16_to_cpu(bf[0].length)) { bestsp[use_block] = bf[0].length; if (!grown) - xfs_dir2_leaf_log_bests(tp, lbp, use_block, use_block); + xfs_dir3_leaf_log_bests(tp, lbp, use_block, use_block); } - lep = xfs_dir2_leaf_find_entry(leaf, index, compact, lowstale, + lep = xfs_dir3_leaf_find_entry(&leafhdr, ents, index, compact, lowstale, highstale, &lfloglow, &lfloghigh); /* @@ -647,82 +915,40 @@ xfs_dir2_leaf_addname( /* * Log the leaf fields and give up the buffers. */ - xfs_dir2_leaf_log_header(tp, lbp); - xfs_dir2_leaf_log_ents(tp, lbp, lfloglow, lfloghigh); - xfs_dir2_leaf_check(dp, lbp); + xfs_dir3_leaf_hdr_to_disk(leaf, &leafhdr); + xfs_dir3_leaf_log_header(tp, lbp); + xfs_dir3_leaf_log_ents(tp, lbp, lfloglow, lfloghigh); + xfs_dir3_leaf_check(mp, lbp); xfs_dir3_data_check(dp, dbp); return 0; } -#ifdef DEBUG -/* - * Check the internal consistency of a leaf1 block. - * Pop an assert if something is wrong. - */ -STATIC void -xfs_dir2_leaf_check( - struct xfs_inode *dp, /* incore directory inode */ - struct xfs_buf *bp) /* leaf's buffer */ -{ - int i; /* leaf index */ - xfs_dir2_leaf_t *leaf; /* leaf structure */ - xfs_dir2_leaf_tail_t *ltp; /* leaf tail pointer */ - xfs_mount_t *mp; /* filesystem mount point */ - int stale; /* count of stale leaves */ - - leaf = bp->b_addr; - mp = dp->i_mount; - ASSERT(leaf->hdr.info.magic == cpu_to_be16(XFS_DIR2_LEAF1_MAGIC)); - /* - * This value is not restrictive enough. - * Should factor in the size of the bests table as well. - * We can deduce a value for that from di_size. - */ - ASSERT(be16_to_cpu(leaf->hdr.count) <= xfs_dir2_max_leaf_ents(mp)); - ltp = xfs_dir2_leaf_tail_p(mp, leaf); - /* - * Leaves and bests don't overlap. - */ - ASSERT((char *)&leaf->ents[be16_to_cpu(leaf->hdr.count)] <= - (char *)xfs_dir2_leaf_bests_p(ltp)); - /* - * Check hash value order, count stale entries. - */ - for (i = stale = 0; i < be16_to_cpu(leaf->hdr.count); i++) { - if (i + 1 < be16_to_cpu(leaf->hdr.count)) - ASSERT(be32_to_cpu(leaf->ents[i].hashval) <= - be32_to_cpu(leaf->ents[i + 1].hashval)); - if (leaf->ents[i].address == cpu_to_be32(XFS_DIR2_NULL_DATAPTR)) - stale++; - } - ASSERT(be16_to_cpu(leaf->hdr.stale) == stale); -} -#endif /* DEBUG */ - /* * Compact out any stale entries in the leaf. * Log the header and changed leaf entries, if any. */ void -xfs_dir2_leaf_compact( +xfs_dir3_leaf_compact( xfs_da_args_t *args, /* operation arguments */ + struct xfs_dir3_icleaf_hdr *leafhdr, struct xfs_buf *bp) /* leaf buffer */ { int from; /* source leaf index */ xfs_dir2_leaf_t *leaf; /* leaf structure */ int loglow; /* first leaf entry to log */ int to; /* target leaf index */ + struct xfs_dir2_leaf_entry *ents; leaf = bp->b_addr; - if (!leaf->hdr.stale) { + if (!leafhdr->stale) return; - } + /* * Compress out the stale entries in place. */ - for (from = to = 0, loglow = -1; from < be16_to_cpu(leaf->hdr.count); from++) { - if (leaf->ents[from].address == - cpu_to_be32(XFS_DIR2_NULL_DATAPTR)) + ents = xfs_dir3_leaf_ents_p(leaf); + for (from = to = 0, loglow = -1; from < leafhdr->count; from++) { + if (ents[from].address == cpu_to_be32(XFS_DIR2_NULL_DATAPTR)) continue; /* * Only actually copy the entries that are different. @@ -730,19 +956,21 @@ xfs_dir2_leaf_compact( if (from > to) { if (loglow == -1) loglow = to; - leaf->ents[to] = leaf->ents[from]; + ents[to] = ents[from]; } to++; } /* * Update and log the header, log the leaf entries. */ - ASSERT(be16_to_cpu(leaf->hdr.stale) == from - to); - be16_add_cpu(&leaf->hdr.count, -(be16_to_cpu(leaf->hdr.stale))); - leaf->hdr.stale = 0; - xfs_dir2_leaf_log_header(args->trans, bp); + ASSERT(leafhdr->stale == from - to); + leafhdr->count -= leafhdr->stale; + leafhdr->stale = 0; + + xfs_dir3_leaf_hdr_to_disk(leaf, leafhdr); + xfs_dir3_leaf_log_header(args->trans, bp); if (loglow != -1) - xfs_dir2_leaf_log_ents(args->trans, bp, loglow, to - 1); + xfs_dir3_leaf_log_ents(args->trans, bp, loglow, to - 1); } /* @@ -754,8 +982,9 @@ xfs_dir2_leaf_compact( * and leaf logging indices. */ void -xfs_dir2_leaf_compact_x1( - struct xfs_buf *bp, /* leaf buffer */ +xfs_dir3_leaf_compact_x1( + struct xfs_dir3_icleaf_hdr *leafhdr, + struct xfs_dir2_leaf_entry *ents, int *indexp, /* insertion index */ int *lowstalep, /* out: stale entry before us */ int *highstalep, /* out: stale entry after us */ @@ -766,22 +995,20 @@ xfs_dir2_leaf_compact_x1( int highstale; /* stale entry at/after index */ int index; /* insertion index */ int keepstale; /* source index of kept stale */ - xfs_dir2_leaf_t *leaf; /* leaf structure */ int lowstale; /* stale entry before index */ int newindex=0; /* new insertion index */ int to; /* destination copy index */ - leaf = bp->b_addr; - ASSERT(be16_to_cpu(leaf->hdr.stale) > 1); + ASSERT(leafhdr->stale > 1); index = *indexp; - xfs_dir2_leaf_find_stale(leaf, index, &lowstale, &highstale); + xfs_dir3_leaf_find_stale(leafhdr, ents, index, &lowstale, &highstale); /* * Pick the better of lowstale and highstale. */ if (lowstale >= 0 && - (highstale == be16_to_cpu(leaf->hdr.count) || + (highstale == leafhdr->count || index - lowstale <= highstale - index)) keepstale = lowstale; else @@ -790,15 +1017,14 @@ xfs_dir2_leaf_compact_x1( * Copy the entries in place, removing all the stale entries * except keepstale. */ - for (from = to = 0; from < be16_to_cpu(leaf->hdr.count); from++) { + for (from = to = 0; from < leafhdr->count; from++) { /* * Notice the new value of index. */ if (index == from) newindex = to; if (from != keepstale && - leaf->ents[from].address == - cpu_to_be32(XFS_DIR2_NULL_DATAPTR)) { + ents[from].address == cpu_to_be32(XFS_DIR2_NULL_DATAPTR)) { if (from == to) *lowlogp = to; continue; @@ -812,7 +1038,7 @@ xfs_dir2_leaf_compact_x1( * Copy only the entries that have moved. */ if (from > to) - leaf->ents[to] = leaf->ents[from]; + ents[to] = ents[from]; to++; } ASSERT(from > to); @@ -826,8 +1052,8 @@ xfs_dir2_leaf_compact_x1( /* * Adjust the leaf header values. */ - be16_add_cpu(&leaf->hdr.count, -(from - to)); - leaf->hdr.stale = cpu_to_be16(1); + leafhdr->count -= from - to; + leafhdr->stale = 1; /* * Remember the low/high stale value only in the "right" * direction. @@ -835,8 +1061,8 @@ xfs_dir2_leaf_compact_x1( if (lowstale >= newindex) lowstale = -1; else - highstale = be16_to_cpu(leaf->hdr.count); - *highlogp = be16_to_cpu(leaf->hdr.count) - 1; + highstale = leafhdr->count; + *highlogp = leafhdr->count - 1; *lowstalep = lowstale; *highstalep = highstale; } @@ -1229,69 +1455,12 @@ xfs_dir2_leaf_getdents( return error; } -/* - * Initialize a new leaf block, leaf1 or leafn magic accepted. - */ -int -xfs_dir2_leaf_init( - xfs_da_args_t *args, /* operation arguments */ - xfs_dir2_db_t bno, /* directory block number */ - struct xfs_buf **bpp, /* out: leaf buffer */ - int magic) /* magic number for block */ -{ - struct xfs_buf *bp; /* leaf buffer */ - xfs_inode_t *dp; /* incore directory inode */ - int error; /* error return code */ - xfs_dir2_leaf_t *leaf; /* leaf structure */ - xfs_dir2_leaf_tail_t *ltp; /* leaf tail structure */ - xfs_mount_t *mp; /* filesystem mount point */ - xfs_trans_t *tp; /* transaction pointer */ - - dp = args->dp; - ASSERT(dp != NULL); - tp = args->trans; - mp = dp->i_mount; - ASSERT(bno >= XFS_DIR2_LEAF_FIRSTDB(mp) && - bno < XFS_DIR2_FREE_FIRSTDB(mp)); - /* - * Get the buffer for the block. - */ - error = xfs_da_get_buf(tp, dp, xfs_dir2_db_to_da(mp, bno), -1, &bp, - XFS_DATA_FORK); - if (error) - return error; - - /* - * Initialize the header. - */ - leaf = bp->b_addr; - leaf->hdr.info.magic = cpu_to_be16(magic); - leaf->hdr.info.forw = 0; - leaf->hdr.info.back = 0; - leaf->hdr.count = 0; - leaf->hdr.stale = 0; - xfs_dir2_leaf_log_header(tp, bp); - /* - * If it's a leaf-format directory initialize the tail. - * In this case our caller has the real bests table to copy into - * the block. - */ - if (magic == XFS_DIR2_LEAF1_MAGIC) { - bp->b_ops = &xfs_dir2_leaf1_buf_ops; - ltp = xfs_dir2_leaf_tail_p(mp, leaf); - ltp->bestcount = 0; - xfs_dir2_leaf_log_tail(tp, bp); - } else - bp->b_ops = &xfs_dir2_leafn_buf_ops; - *bpp = bp; - return 0; -} /* * Log the bests entries indicated from a leaf1 block. */ static void -xfs_dir2_leaf_log_bests( +xfs_dir3_leaf_log_bests( xfs_trans_t *tp, /* transaction pointer */ struct xfs_buf *bp, /* leaf buffer */ int first, /* first entry to log */ @@ -1299,11 +1468,12 @@ xfs_dir2_leaf_log_bests( { __be16 *firstb; /* pointer to first entry */ __be16 *lastb; /* pointer to last entry */ - xfs_dir2_leaf_t *leaf; /* leaf structure */ + struct xfs_dir2_leaf *leaf = bp->b_addr; xfs_dir2_leaf_tail_t *ltp; /* leaf tail structure */ - leaf = bp->b_addr; - ASSERT(leaf->hdr.info.magic == cpu_to_be16(XFS_DIR2_LEAF1_MAGIC)); + ASSERT(leaf->hdr.info.magic == cpu_to_be16(XFS_DIR2_LEAF1_MAGIC) || + leaf->hdr.info.magic == cpu_to_be16(XFS_DIR3_LEAF1_MAGIC)); + ltp = xfs_dir2_leaf_tail_p(tp->t_mountp, leaf); firstb = xfs_dir2_leaf_bests_p(ltp) + first; lastb = xfs_dir2_leaf_bests_p(ltp) + last; @@ -1315,7 +1485,7 @@ xfs_dir2_leaf_log_bests( * Log the leaf entries indicated from a leaf1 or leafn block. */ void -xfs_dir2_leaf_log_ents( +xfs_dir3_leaf_log_ents( xfs_trans_t *tp, /* transaction pointer */ struct xfs_buf *bp, /* leaf buffer */ int first, /* first entry to log */ @@ -1323,13 +1493,17 @@ xfs_dir2_leaf_log_ents( { xfs_dir2_leaf_entry_t *firstlep; /* pointer to first entry */ xfs_dir2_leaf_entry_t *lastlep; /* pointer to last entry */ - xfs_dir2_leaf_t *leaf; /* leaf structure */ + struct xfs_dir2_leaf *leaf = bp->b_addr; + struct xfs_dir2_leaf_entry *ents; - leaf = bp->b_addr; ASSERT(leaf->hdr.info.magic == cpu_to_be16(XFS_DIR2_LEAF1_MAGIC) || - leaf->hdr.info.magic == cpu_to_be16(XFS_DIR2_LEAFN_MAGIC)); - firstlep = &leaf->ents[first]; - lastlep = &leaf->ents[last]; + leaf->hdr.info.magic == cpu_to_be16(XFS_DIR3_LEAF1_MAGIC) || + leaf->hdr.info.magic == cpu_to_be16(XFS_DIR2_LEAFN_MAGIC) || + leaf->hdr.info.magic == cpu_to_be16(XFS_DIR3_LEAFN_MAGIC)); + + ents = xfs_dir3_leaf_ents_p(leaf); + firstlep = &ents[first]; + lastlep = &ents[last]; xfs_trans_log_buf(tp, bp, (uint)((char *)firstlep - (char *)leaf), (uint)((char *)lastlep - (char *)leaf + sizeof(*lastlep) - 1)); } @@ -1338,34 +1512,38 @@ xfs_dir2_leaf_log_ents( * Log the header of the leaf1 or leafn block. */ void -xfs_dir2_leaf_log_header( +xfs_dir3_leaf_log_header( struct xfs_trans *tp, struct xfs_buf *bp) { - xfs_dir2_leaf_t *leaf; /* leaf structure */ + struct xfs_dir2_leaf *leaf = bp->b_addr; - leaf = bp->b_addr; ASSERT(leaf->hdr.info.magic == cpu_to_be16(XFS_DIR2_LEAF1_MAGIC) || - leaf->hdr.info.magic == cpu_to_be16(XFS_DIR2_LEAFN_MAGIC)); + leaf->hdr.info.magic == cpu_to_be16(XFS_DIR3_LEAF1_MAGIC) || + leaf->hdr.info.magic == cpu_to_be16(XFS_DIR2_LEAFN_MAGIC) || + leaf->hdr.info.magic == cpu_to_be16(XFS_DIR3_LEAFN_MAGIC)); + xfs_trans_log_buf(tp, bp, (uint)((char *)&leaf->hdr - (char *)leaf), - (uint)(sizeof(leaf->hdr) - 1)); + xfs_dir3_leaf_hdr_size(leaf)); } /* * Log the tail of the leaf1 block. */ STATIC void -xfs_dir2_leaf_log_tail( +xfs_dir3_leaf_log_tail( struct xfs_trans *tp, struct xfs_buf *bp) { - xfs_dir2_leaf_t *leaf; /* leaf structure */ + struct xfs_dir2_leaf *leaf = bp->b_addr; xfs_dir2_leaf_tail_t *ltp; /* leaf tail structure */ - xfs_mount_t *mp; /* filesystem mount point */ + struct xfs_mount *mp = tp->t_mountp; + + ASSERT(leaf->hdr.info.magic == cpu_to_be16(XFS_DIR2_LEAF1_MAGIC) || + leaf->hdr.info.magic == cpu_to_be16(XFS_DIR3_LEAF1_MAGIC) || + leaf->hdr.info.magic == cpu_to_be16(XFS_DIR2_LEAFN_MAGIC) || + leaf->hdr.info.magic == cpu_to_be16(XFS_DIR3_LEAFN_MAGIC)); - mp = tp->t_mountp; - leaf = bp->b_addr; - ASSERT(leaf->hdr.info.magic == cpu_to_be16(XFS_DIR2_LEAF1_MAGIC)); ltp = xfs_dir2_leaf_tail_p(mp, leaf); xfs_trans_log_buf(tp, bp, (uint)((char *)ltp - (char *)leaf), (uint)(mp->m_dirblksize - 1)); @@ -1389,6 +1567,7 @@ xfs_dir2_leaf_lookup( xfs_dir2_leaf_t *leaf; /* leaf structure */ xfs_dir2_leaf_entry_t *lep; /* leaf entry */ xfs_trans_t *tp; /* transaction pointer */ + struct xfs_dir2_leaf_entry *ents; trace_xfs_dir2_leaf_lookup(args); @@ -1400,12 +1579,14 @@ xfs_dir2_leaf_lookup( } tp = args->trans; dp = args->dp; - xfs_dir2_leaf_check(dp, lbp); + xfs_dir3_leaf_check(dp->i_mount, lbp); leaf = lbp->b_addr; + ents = xfs_dir3_leaf_ents_p(leaf); /* * Get to the leaf entry and contained data entry address. */ - lep = &leaf->ents[index]; + lep = &ents[index]; + /* * Point to the data entry. */ @@ -1449,18 +1630,23 @@ xfs_dir2_leaf_lookup_int( xfs_trans_t *tp; /* transaction pointer */ xfs_dir2_db_t cidb = -1; /* case match data block no. */ enum xfs_dacmp cmp; /* name compare result */ + struct xfs_dir2_leaf_entry *ents; + struct xfs_dir3_icleaf_hdr leafhdr; dp = args->dp; tp = args->trans; mp = dp->i_mount; - error = xfs_dir2_leaf_read(tp, dp, mp->m_dirleafblk, -1, &lbp); + error = xfs_dir3_leaf_read(tp, dp, mp->m_dirleafblk, -1, &lbp); if (error) return error; *lbpp = lbp; leaf = lbp->b_addr; - xfs_dir2_leaf_check(dp, lbp); + xfs_dir3_leaf_check(mp, lbp); + ents = xfs_dir3_leaf_ents_p(leaf); + xfs_dir3_leaf_hdr_from_disk(&leafhdr, leaf); + /* * Look for the first leaf entry with our hash value. */ @@ -1469,9 +1655,9 @@ xfs_dir2_leaf_lookup_int( * Loop over all the entries with the right hash value * looking to match the name. */ - for (lep = &leaf->ents[index]; index < be16_to_cpu(leaf->hdr.count) && - be32_to_cpu(lep->hashval) == args->hashval; - lep++, index++) { + for (lep = &ents[index]; + index < leafhdr.count && be32_to_cpu(lep->hashval) == args->hashval; + lep++, index++) { /* * Skip over stale leaf entries. */ @@ -1576,6 +1762,8 @@ xfs_dir2_leaf_removename( xfs_dir2_data_off_t oldbest; /* old value of best free */ xfs_trans_t *tp; /* transaction pointer */ struct xfs_dir2_data_free *bf; /* bestfree table */ + struct xfs_dir2_leaf_entry *ents; + struct xfs_dir3_icleaf_hdr leafhdr; trace_xfs_dir2_leaf_removename(args); @@ -1590,12 +1778,14 @@ xfs_dir2_leaf_removename( mp = dp->i_mount; leaf = lbp->b_addr; hdr = dbp->b_addr; - bf = xfs_dir3_data_bestfree_p(hdr); xfs_dir3_data_check(dp, dbp); + bf = xfs_dir3_data_bestfree_p(hdr); + xfs_dir3_leaf_hdr_from_disk(&leafhdr, leaf); + ents = xfs_dir3_leaf_ents_p(leaf); /* * Point to the leaf entry, use that to point to the data entry. */ - lep = &leaf->ents[index]; + lep = &ents[index]; db = xfs_dir2_dataptr_to_db(mp, be32_to_cpu(lep->address)); dep = (xfs_dir2_data_entry_t *) ((char *)hdr + xfs_dir2_dataptr_to_off(mp, be32_to_cpu(lep->address))); @@ -1613,10 +1803,13 @@ xfs_dir2_leaf_removename( /* * We just mark the leaf entry stale by putting a null in it. */ - be16_add_cpu(&leaf->hdr.stale, 1); - xfs_dir2_leaf_log_header(tp, lbp); + leafhdr.stale++; + xfs_dir3_leaf_hdr_to_disk(leaf, &leafhdr); + xfs_dir3_leaf_log_header(tp, lbp); + lep->address = cpu_to_be32(XFS_DIR2_NULL_DATAPTR); - xfs_dir2_leaf_log_ents(tp, lbp, index, index); + xfs_dir3_leaf_log_ents(tp, lbp, index, index); + /* * Scan the freespace in the data block again if necessary, * log the data block header if necessary. @@ -1631,7 +1824,7 @@ xfs_dir2_leaf_removename( */ if (be16_to_cpu(bf[0].length) != oldbest) { bestsp[db] = bf[0].length; - xfs_dir2_leaf_log_bests(tp, lbp, db, db); + xfs_dir3_leaf_log_bests(tp, lbp, db, db); } xfs_dir3_data_check(dp, dbp); /* @@ -1649,7 +1842,7 @@ xfs_dir2_leaf_removename( */ if (error == ENOSPC && args->total == 0) error = 0; - xfs_dir2_leaf_check(dp, lbp); + xfs_dir3_leaf_check(mp, lbp); return error; } dbp = NULL; @@ -1672,8 +1865,8 @@ xfs_dir2_leaf_removename( memmove(&bestsp[db - i], bestsp, (be32_to_cpu(ltp->bestcount) - (db - i)) * sizeof(*bestsp)); be32_add_cpu(<p->bestcount, -(db - i)); - xfs_dir2_leaf_log_tail(tp, lbp); - xfs_dir2_leaf_log_bests(tp, lbp, 0, be32_to_cpu(ltp->bestcount) - 1); + xfs_dir3_leaf_log_tail(tp, lbp); + xfs_dir3_leaf_log_bests(tp, lbp, 0, be32_to_cpu(ltp->bestcount) - 1); } else bestsp[db] = cpu_to_be16(NULLDATAOFF); } @@ -1683,7 +1876,7 @@ xfs_dir2_leaf_removename( else if (db != mp->m_dirdatablk) dbp = NULL; - xfs_dir2_leaf_check(dp, lbp); + xfs_dir3_leaf_check(mp, lbp); /* * See if we can convert to block form. */ @@ -1706,6 +1899,7 @@ xfs_dir2_leaf_replace( xfs_dir2_leaf_t *leaf; /* leaf structure */ xfs_dir2_leaf_entry_t *lep; /* leaf entry */ xfs_trans_t *tp; /* transaction pointer */ + struct xfs_dir2_leaf_entry *ents; trace_xfs_dir2_leaf_replace(args); @@ -1717,10 +1911,11 @@ xfs_dir2_leaf_replace( } dp = args->dp; leaf = lbp->b_addr; + ents = xfs_dir3_leaf_ents_p(leaf); /* * Point to the leaf entry, get data address from it. */ - lep = &leaf->ents[index]; + lep = &ents[index]; /* * Point to the data entry. */ @@ -1734,7 +1929,7 @@ xfs_dir2_leaf_replace( dep->inumber = cpu_to_be64(args->inumber); tp = args->trans; xfs_dir2_data_log_entry(tp, dbp, dep); - xfs_dir2_leaf_check(dp, lbp); + xfs_dir3_leaf_check(dp->i_mount, lbp); xfs_trans_brelse(tp, lbp); return 0; } @@ -1756,17 +1951,22 @@ xfs_dir2_leaf_search_hash( xfs_dir2_leaf_t *leaf; /* leaf structure */ xfs_dir2_leaf_entry_t *lep; /* leaf entry */ int mid=0; /* current leaf index */ + struct xfs_dir2_leaf_entry *ents; + struct xfs_dir3_icleaf_hdr leafhdr; leaf = lbp->b_addr; + ents = xfs_dir3_leaf_ents_p(leaf); + xfs_dir3_leaf_hdr_from_disk(&leafhdr, leaf); + #ifndef __KERNEL__ - if (!leaf->hdr.count) + if (!leafhdr.count) return 0; #endif /* * Note, the table cannot be empty, so we have to go through the loop. * Binary search the leaf entries looking for our hash value. */ - for (lep = leaf->ents, low = 0, high = be16_to_cpu(leaf->hdr.count) - 1, + for (lep = ents, low = 0, high = leafhdr.count - 1, hashwant = args->hashval; low <= high; ) { mid = (low + high) >> 1; @@ -1852,23 +2052,29 @@ xfs_dir2_leaf_trim_data( bestsp = xfs_dir2_leaf_bests_p(ltp); be32_add_cpu(<p->bestcount, -1); memmove(&bestsp[1], &bestsp[0], be32_to_cpu(ltp->bestcount) * sizeof(*bestsp)); - xfs_dir2_leaf_log_tail(tp, lbp); - xfs_dir2_leaf_log_bests(tp, lbp, 0, be32_to_cpu(ltp->bestcount) - 1); + xfs_dir3_leaf_log_tail(tp, lbp); + xfs_dir3_leaf_log_bests(tp, lbp, 0, be32_to_cpu(ltp->bestcount) - 1); return 0; } static inline size_t -xfs_dir2_leaf_size( - struct xfs_dir2_leaf_hdr *hdr, +xfs_dir3_leaf_size( + struct xfs_dir3_icleaf_hdr *hdr, int counts) { - int entries; + int entries; + int hdrsize; + + entries = hdr->count - hdr->stale; + if (hdr->magic == XFS_DIR2_LEAF1_MAGIC || + hdr->magic == XFS_DIR2_LEAFN_MAGIC) + hdrsize = sizeof(struct xfs_dir2_leaf_hdr); + else + hdrsize = sizeof(struct xfs_dir3_leaf_hdr); - entries = be16_to_cpu(hdr->count) - be16_to_cpu(hdr->stale); - return sizeof(xfs_dir2_leaf_hdr_t) + - entries * sizeof(xfs_dir2_leaf_entry_t) + - counts * sizeof(xfs_dir2_data_off_t) + - sizeof(xfs_dir2_leaf_tail_t); + return hdrsize + entries * sizeof(xfs_dir2_leaf_entry_t) + + counts * sizeof(xfs_dir2_data_off_t) + + sizeof(xfs_dir2_leaf_tail_t); } /* @@ -1892,6 +2098,7 @@ xfs_dir2_node_to_leaf( xfs_mount_t *mp; /* filesystem mount point */ int rval; /* successful free trim? */ xfs_trans_t *tp; /* transaction pointer */ + struct xfs_dir3_icleaf_hdr leafhdr; struct xfs_dir3_icfree_hdr freehdr; /* @@ -1942,7 +2149,11 @@ xfs_dir2_node_to_leaf( return 0; lbp = state->path.blk[0].bp; leaf = lbp->b_addr; - ASSERT(leaf->hdr.info.magic == cpu_to_be16(XFS_DIR2_LEAFN_MAGIC)); + xfs_dir3_leaf_hdr_from_disk(&leafhdr, leaf); + + ASSERT(leafhdr.magic == XFS_DIR2_LEAFN_MAGIC || + leafhdr.magic == XFS_DIR3_LEAFN_MAGIC); + /* * Read the freespace block. */ @@ -1958,36 +2169,40 @@ xfs_dir2_node_to_leaf( * Now see if the leafn and free data will fit in a leaf1. * If not, release the buffer and give up. */ - if (xfs_dir2_leaf_size(&leaf->hdr, freehdr.nvalid) > mp->m_dirblksize) { + if (xfs_dir3_leaf_size(&leafhdr, freehdr.nvalid) > mp->m_dirblksize) { xfs_trans_brelse(tp, fbp); return 0; } /* * If the leaf has any stale entries in it, compress them out. - * The compact routine will log the header. */ - if (be16_to_cpu(leaf->hdr.stale)) - xfs_dir2_leaf_compact(args, lbp); - else - xfs_dir2_leaf_log_header(tp, lbp); + if (leafhdr.stale) + xfs_dir3_leaf_compact(args, &leafhdr, lbp); - lbp->b_ops = &xfs_dir2_leaf1_buf_ops; - leaf->hdr.info.magic = cpu_to_be16(XFS_DIR2_LEAF1_MAGIC); + lbp->b_ops = &xfs_dir3_leaf1_buf_ops; + leafhdr.magic = (leafhdr.magic == XFS_DIR2_LEAFN_MAGIC) + ? XFS_DIR2_LEAF1_MAGIC + : XFS_DIR3_LEAFN_MAGIC; /* * Set up the leaf tail from the freespace block. */ ltp = xfs_dir2_leaf_tail_p(mp, leaf); ltp->bestcount = cpu_to_be32(freehdr.nvalid); + /* * Set up the leaf bests table. */ memcpy(xfs_dir2_leaf_bests_p(ltp), xfs_dir3_free_bests_p(mp, free), freehdr.nvalid * sizeof(xfs_dir2_data_off_t)); - xfs_dir2_leaf_log_bests(tp, lbp, 0, be32_to_cpu(ltp->bestcount) - 1); - xfs_dir2_leaf_log_tail(tp, lbp); - xfs_dir2_leaf_check(dp, lbp); + + xfs_dir3_leaf_hdr_to_disk(leaf, &leafhdr); + xfs_dir3_leaf_log_header(tp, lbp); + xfs_dir3_leaf_log_bests(tp, lbp, 0, be32_to_cpu(ltp->bestcount) - 1); + xfs_dir3_leaf_log_tail(tp, lbp); + xfs_dir3_leaf_check(mp, lbp); + /* * Get rid of the freespace block. */ diff --git a/fs/xfs/xfs_dir2_node.c b/fs/xfs/xfs_dir2_node.c index 14067a4..747aed1 100644 --- a/fs/xfs/xfs_dir2_node.c +++ b/fs/xfs/xfs_dir2_node.c @@ -42,13 +42,12 @@ static int xfs_dir2_leafn_add(struct xfs_buf *bp, xfs_da_args_t *args, int index); #ifdef DEBUG -static void xfs_dir2_leafn_check(struct xfs_inode *dp, struct xfs_buf *bp); -#else -#define xfs_dir2_leafn_check(dp, bp) +#define xfs_dir3_leaf_check(mp, bp) \ +do { \ + if (!xfs_dir3_leafn_check((mp), (bp))) \ + ASSERT(0); \ +} while (0); #endif -static void xfs_dir2_leafn_moveents(xfs_da_args_t *args, struct xfs_buf *bp_s, - int start_s, struct xfs_buf *bp_d, - int start_d, int count); static void xfs_dir2_leafn_rebalance(xfs_da_state_t *state, xfs_da_state_blk_t *blk1, xfs_da_state_blk_t *blk2); @@ -58,6 +57,29 @@ static int xfs_dir2_leafn_remove(xfs_da_args_t *args, struct xfs_buf *bp, static int xfs_dir2_node_addname_int(xfs_da_args_t *args, xfs_da_state_blk_t *fblk); +/* + * Check internal consistency of a leafn block. + */ +static bool +xfs_dir3_leafn_check( + struct xfs_mount *mp, + struct xfs_buf *bp) +{ + struct xfs_dir2_leaf *leaf = bp->b_addr; + struct xfs_dir3_icleaf_hdr leafhdr; + + xfs_dir3_leaf_hdr_from_disk(&leafhdr, leaf); + + if (leafhdr.magic == XFS_DIR3_LEAFN_MAGIC) { + struct xfs_dir3_leaf_hdr *leaf3 = bp->b_addr; + if (be64_to_cpu(leaf3->info.blkno) != bp->b_bn) + return false; + } else if (leafhdr.magic != XFS_DIR2_LEAFN_MAGIC) + return false; + + return xfs_dir3_leaf_check_int(mp, &leafhdr, leaf); +} + static bool xfs_dir3_free_verify( struct xfs_buf *bp) @@ -361,11 +383,19 @@ xfs_dir2_leaf_to_node( xfs_dir2_free_log_bests(tp, fbp, 0, freehdr.nvalid - 1); xfs_dir2_free_log_header(tp, fbp); - /* convert the leaf to a leafnode */ - leaf->hdr.info.magic = cpu_to_be16(XFS_DIR2_LEAFN_MAGIC); - lbp->b_ops = &xfs_dir2_leafn_buf_ops; - xfs_dir2_leaf_log_header(tp, lbp); - xfs_dir2_leafn_check(dp, lbp); + /* + * Converting the leaf to a leafnode is just a matter of changing the + * magic number and the ops. Do the change directly to the buffer as + * it's less work (and less code) than decoding the header to host + * format and back again. + */ + if (leaf->hdr.info.magic == cpu_to_be16(XFS_DIR2_LEAF1_MAGIC)) + leaf->hdr.info.magic = cpu_to_be16(XFS_DIR2_LEAFN_MAGIC); + else + leaf->hdr.info.magic = cpu_to_be16(XFS_DIR3_LEAFN_MAGIC); + lbp->b_ops = &xfs_dir3_leafn_buf_ops; + xfs_dir3_leaf_log_header(tp, lbp); + xfs_dir3_leaf_check(mp, lbp); return 0; } @@ -389,6 +419,8 @@ xfs_dir2_leafn_add( int lowstale; /* previous stale entry */ xfs_mount_t *mp; /* filesystem mount point */ xfs_trans_t *tp; /* transaction pointer */ + struct xfs_dir3_icleaf_hdr leafhdr; + struct xfs_dir2_leaf_entry *ents; trace_xfs_dir2_leafn_add(args, index); @@ -396,6 +428,8 @@ xfs_dir2_leafn_add( mp = dp->i_mount; tp = args->trans; leaf = bp->b_addr; + xfs_dir3_leaf_hdr_from_disk(&leafhdr, leaf); + ents = xfs_dir3_leaf_ents_p(leaf); /* * Quick check just to make sure we are not going to index @@ -411,15 +445,15 @@ xfs_dir2_leafn_add( * a compact. */ - if (be16_to_cpu(leaf->hdr.count) == xfs_dir2_max_leaf_ents(mp)) { - if (!leaf->hdr.stale) + if (leafhdr.count == xfs_dir3_max_leaf_ents(mp, leaf)) { + if (!leafhdr.stale) return XFS_ERROR(ENOSPC); - compact = be16_to_cpu(leaf->hdr.stale) > 1; + compact = leafhdr.stale > 1; } else compact = 0; - ASSERT(index == 0 || be32_to_cpu(leaf->ents[index - 1].hashval) <= args->hashval); - ASSERT(index == be16_to_cpu(leaf->hdr.count) || - be32_to_cpu(leaf->ents[index].hashval) >= args->hashval); + ASSERT(index == 0 || be32_to_cpu(ents[index - 1].hashval) <= args->hashval); + ASSERT(index == leafhdr.count || + be32_to_cpu(ents[index].hashval) >= args->hashval); if (args->op_flags & XFS_DA_OP_JUSTCHECK) return 0; @@ -428,62 +462,35 @@ xfs_dir2_leafn_add( * Compact out all but one stale leaf entry. Leaves behind * the entry closest to index. */ - if (compact) { - xfs_dir2_leaf_compact_x1(bp, &index, &lowstale, &highstale, - &lfloglow, &lfloghigh); - } - /* - * Set impossible logging indices for this case. - */ - else if (leaf->hdr.stale) { - lfloglow = be16_to_cpu(leaf->hdr.count); + if (compact) + xfs_dir3_leaf_compact_x1(&leafhdr, ents, &index, &lowstale, + &highstale, &lfloglow, &lfloghigh); + else if (leafhdr.stale) { + /* + * Set impossible logging indices for this case. + */ + lfloglow = leafhdr.count; lfloghigh = -1; } /* * Insert the new entry, log everything. */ - lep = xfs_dir2_leaf_find_entry(leaf, index, compact, lowstale, + lep = xfs_dir3_leaf_find_entry(&leafhdr, ents, index, compact, lowstale, highstale, &lfloglow, &lfloghigh); lep->hashval = cpu_to_be32(args->hashval); lep->address = cpu_to_be32(xfs_dir2_db_off_to_dataptr(mp, args->blkno, args->index)); - xfs_dir2_leaf_log_header(tp, bp); - xfs_dir2_leaf_log_ents(tp, bp, lfloglow, lfloghigh); - xfs_dir2_leafn_check(dp, bp); + + xfs_dir3_leaf_hdr_to_disk(leaf, &leafhdr); + xfs_dir3_leaf_log_header(tp, bp); + xfs_dir3_leaf_log_ents(tp, bp, lfloglow, lfloghigh); + xfs_dir3_leaf_check(mp, bp); return 0; } #ifdef DEBUG -/* - * Check internal consistency of a leafn block. - */ -void -xfs_dir2_leafn_check( - struct xfs_inode *dp, - struct xfs_buf *bp) -{ - int i; /* leaf index */ - xfs_dir2_leaf_t *leaf; /* leaf structure */ - xfs_mount_t *mp; /* filesystem mount point */ - int stale; /* count of stale leaves */ - - leaf = bp->b_addr; - mp = dp->i_mount; - ASSERT(leaf->hdr.info.magic == cpu_to_be16(XFS_DIR2_LEAFN_MAGIC)); - ASSERT(be16_to_cpu(leaf->hdr.count) <= xfs_dir2_max_leaf_ents(mp)); - for (i = stale = 0; i < be16_to_cpu(leaf->hdr.count); i++) { - if (i + 1 < be16_to_cpu(leaf->hdr.count)) { - ASSERT(be32_to_cpu(leaf->ents[i].hashval) <= - be32_to_cpu(leaf->ents[i + 1].hashval)); - } - if (leaf->ents[i].address == cpu_to_be32(XFS_DIR2_NULL_DATAPTR)) - stale++; - } - ASSERT(be16_to_cpu(leaf->hdr.stale) == stale); -} - static void xfs_dir2_free_hdr_check( struct xfs_mount *mp, @@ -511,15 +518,18 @@ xfs_dir2_leafn_lasthash( struct xfs_buf *bp, /* leaf buffer */ int *count) /* count of entries in leaf */ { - xfs_dir2_leaf_t *leaf; /* leaf structure */ + struct xfs_dir2_leaf *leaf = bp->b_addr; + struct xfs_dir2_leaf_entry *ents; + struct xfs_dir3_icleaf_hdr leafhdr; + + xfs_dir3_leaf_hdr_from_disk(&leafhdr, leaf); + ents = xfs_dir3_leaf_ents_p(leaf); - leaf = bp->b_addr; - ASSERT(leaf->hdr.info.magic == cpu_to_be16(XFS_DIR2_LEAFN_MAGIC)); if (count) - *count = be16_to_cpu(leaf->hdr.count); - if (!leaf->hdr.count) + *count = leafhdr.count; + if (!leafhdr.count) return 0; - return be32_to_cpu(leaf->ents[be16_to_cpu(leaf->hdr.count) - 1].hashval); + return be32_to_cpu(ents[leafhdr.count - 1].hashval); } /* @@ -548,16 +558,19 @@ xfs_dir2_leafn_lookup_for_addname( xfs_dir2_db_t newdb; /* new data block number */ xfs_dir2_db_t newfdb; /* new free block number */ xfs_trans_t *tp; /* transaction pointer */ + struct xfs_dir2_leaf_entry *ents; + struct xfs_dir3_icleaf_hdr leafhdr; dp = args->dp; tp = args->trans; mp = dp->i_mount; leaf = bp->b_addr; - ASSERT(leaf->hdr.info.magic == cpu_to_be16(XFS_DIR2_LEAFN_MAGIC)); -#ifdef __KERNEL__ - ASSERT(be16_to_cpu(leaf->hdr.count) > 0); -#endif - xfs_dir2_leafn_check(dp, bp); + xfs_dir3_leaf_hdr_from_disk(&leafhdr, leaf); + ents = xfs_dir3_leaf_ents_p(leaf); + + xfs_dir3_leaf_check(mp, bp); + ASSERT(leafhdr.count > 0); + /* * Look up the hash value in the leaf entries. */ @@ -577,9 +590,9 @@ xfs_dir2_leafn_lookup_for_addname( /* * Loop over leaf entries with the right hash value. */ - for (lep = &leaf->ents[index]; index < be16_to_cpu(leaf->hdr.count) && - be32_to_cpu(lep->hashval) == args->hashval; - lep++, index++) { + for (lep = &ents[index]; + index < leafhdr.count && be32_to_cpu(lep->hashval) == args->hashval; + lep++, index++) { /* * Skip stale leaf entries. */ @@ -695,16 +708,19 @@ xfs_dir2_leafn_lookup_for_entry( xfs_dir2_db_t newdb; /* new data block number */ xfs_trans_t *tp; /* transaction pointer */ enum xfs_dacmp cmp; /* comparison result */ + struct xfs_dir2_leaf_entry *ents; + struct xfs_dir3_icleaf_hdr leafhdr; dp = args->dp; tp = args->trans; mp = dp->i_mount; leaf = bp->b_addr; - ASSERT(leaf->hdr.info.magic == cpu_to_be16(XFS_DIR2_LEAFN_MAGIC)); -#ifdef __KERNEL__ - ASSERT(be16_to_cpu(leaf->hdr.count) > 0); -#endif - xfs_dir2_leafn_check(dp, bp); + xfs_dir3_leaf_hdr_from_disk(&leafhdr, leaf); + ents = xfs_dir3_leaf_ents_p(leaf); + + xfs_dir3_leaf_check(mp, bp); + ASSERT(leafhdr.count > 0); + /* * Look up the hash value in the leaf entries. */ @@ -719,9 +735,9 @@ xfs_dir2_leafn_lookup_for_entry( /* * Loop over leaf entries with the right hash value. */ - for (lep = &leaf->ents[index]; index < be16_to_cpu(leaf->hdr.count) && - be32_to_cpu(lep->hashval) == args->hashval; - lep++, index++) { + for (lep = &ents[index]; + index < leafhdr.count && be32_to_cpu(lep->hashval) == args->hashval; + lep++, index++) { /* * Skip stale leaf entries. */ @@ -793,8 +809,7 @@ xfs_dir2_leafn_lookup_for_entry( return XFS_ERROR(EEXIST); } } - ASSERT(index == be16_to_cpu(leaf->hdr.count) || - (args->op_flags & XFS_DA_OP_OKNOENT)); + ASSERT(index == leafhdr.count || (args->op_flags & XFS_DA_OP_OKNOENT)); if (curbp) { if (args->cmpresult == XFS_CMP_DIFFERENT) { /* Giving back last used data block. */ @@ -839,52 +854,50 @@ xfs_dir2_leafn_lookup_int( * Log entries and headers. Stale entries are preserved. */ static void -xfs_dir2_leafn_moveents( - xfs_da_args_t *args, /* operation arguments */ - struct xfs_buf *bp_s, /* source leaf buffer */ - int start_s, /* source leaf index */ - struct xfs_buf *bp_d, /* destination leaf buffer */ - int start_d, /* destination leaf index */ - int count) /* count of leaves to copy */ +xfs_dir3_leafn_moveents( + xfs_da_args_t *args, /* operation arguments */ + struct xfs_buf *bp_s, /* source */ + struct xfs_dir3_icleaf_hdr *shdr, + struct xfs_dir2_leaf_entry *sents, + int start_s,/* source leaf index */ + struct xfs_buf *bp_d, /* destination */ + struct xfs_dir3_icleaf_hdr *dhdr, + struct xfs_dir2_leaf_entry *dents, + int start_d,/* destination leaf index */ + int count) /* count of leaves to copy */ { - xfs_dir2_leaf_t *leaf_d; /* destination leaf structure */ - xfs_dir2_leaf_t *leaf_s; /* source leaf structure */ - int stale; /* count stale leaves copied */ - xfs_trans_t *tp; /* transaction pointer */ + int stale; + xfs_trans_t *tp = args->trans; trace_xfs_dir2_leafn_moveents(args, start_s, start_d, count); /* * Silently return if nothing to do. */ - if (count == 0) { + if (count == 0) return; - } - tp = args->trans; - leaf_s = bp_s->b_addr; - leaf_d = bp_d->b_addr; + /* * If the destination index is not the end of the current * destination leaf entries, open up a hole in the destination * to hold the new entries. */ - if (start_d < be16_to_cpu(leaf_d->hdr.count)) { - memmove(&leaf_d->ents[start_d + count], &leaf_d->ents[start_d], - (be16_to_cpu(leaf_d->hdr.count) - start_d) * - sizeof(xfs_dir2_leaf_entry_t)); - xfs_dir2_leaf_log_ents(tp, bp_d, start_d + count, - count + be16_to_cpu(leaf_d->hdr.count) - 1); + if (start_d < dhdr->count) { + memmove(&dents[start_d + count], &dents[start_d], + (dhdr->count - start_d) * sizeof(xfs_dir2_leaf_entry_t)); + xfs_dir3_leaf_log_ents(tp, bp_d, start_d + count, + count + dhdr->count - 1); } /* * If the source has stale leaves, count the ones in the copy range * so we can update the header correctly. */ - if (leaf_s->hdr.stale) { + if (shdr->stale) { int i; /* temp leaf index */ for (i = start_s, stale = 0; i < start_s + count; i++) { - if (leaf_s->ents[i].address == - cpu_to_be32(XFS_DIR2_NULL_DATAPTR)) + if (sents[i].address == + cpu_to_be32(XFS_DIR2_NULL_DATAPTR)) stale++; } } else @@ -892,29 +905,27 @@ xfs_dir2_leafn_moveents( /* * Copy the leaf entries from source to destination. */ - memcpy(&leaf_d->ents[start_d], &leaf_s->ents[start_s], + memcpy(&dents[start_d], &sents[start_s], count * sizeof(xfs_dir2_leaf_entry_t)); - xfs_dir2_leaf_log_ents(tp, bp_d, start_d, start_d + count - 1); + xfs_dir3_leaf_log_ents(tp, bp_d, start_d, start_d + count - 1); + /* * If there are source entries after the ones we copied, * delete the ones we copied by sliding the next ones down. */ - if (start_s + count < be16_to_cpu(leaf_s->hdr.count)) { - memmove(&leaf_s->ents[start_s], &leaf_s->ents[start_s + count], + if (start_s + count < shdr->count) { + memmove(&sents[start_s], &sents[start_s + count], count * sizeof(xfs_dir2_leaf_entry_t)); - xfs_dir2_leaf_log_ents(tp, bp_s, start_s, start_s + count - 1); + xfs_dir3_leaf_log_ents(tp, bp_s, start_s, start_s + count - 1); } + /* * Update the headers and log them. */ - be16_add_cpu(&leaf_s->hdr.count, -(count)); - be16_add_cpu(&leaf_s->hdr.stale, -(stale)); - be16_add_cpu(&leaf_d->hdr.count, count); - be16_add_cpu(&leaf_d->hdr.stale, stale); - xfs_dir2_leaf_log_header(tp, bp_s); - xfs_dir2_leaf_log_header(tp, bp_d); - xfs_dir2_leafn_check(args->dp, bp_s); - xfs_dir2_leafn_check(args->dp, bp_d); + shdr->count -= count; + shdr->stale -= stale; + dhdr->count += count; + dhdr->stale += stale; } /* @@ -923,21 +934,25 @@ xfs_dir2_leafn_moveents( */ int /* sort order */ xfs_dir2_leafn_order( - struct xfs_buf *leaf1_bp, /* leaf1 buffer */ - struct xfs_buf *leaf2_bp) /* leaf2 buffer */ + struct xfs_buf *leaf1_bp, /* leaf1 buffer */ + struct xfs_buf *leaf2_bp) /* leaf2 buffer */ { - xfs_dir2_leaf_t *leaf1; /* leaf1 structure */ - xfs_dir2_leaf_t *leaf2; /* leaf2 structure */ - - leaf1 = leaf1_bp->b_addr; - leaf2 = leaf2_bp->b_addr; - ASSERT(leaf1->hdr.info.magic == cpu_to_be16(XFS_DIR2_LEAFN_MAGIC)); - ASSERT(leaf2->hdr.info.magic == cpu_to_be16(XFS_DIR2_LEAFN_MAGIC)); - if (be16_to_cpu(leaf1->hdr.count) > 0 && - be16_to_cpu(leaf2->hdr.count) > 0 && - (be32_to_cpu(leaf2->ents[0].hashval) < be32_to_cpu(leaf1->ents[0].hashval) || - be32_to_cpu(leaf2->ents[be16_to_cpu(leaf2->hdr.count) - 1].hashval) < - be32_to_cpu(leaf1->ents[be16_to_cpu(leaf1->hdr.count) - 1].hashval))) + struct xfs_dir2_leaf *leaf1 = leaf1_bp->b_addr; + struct xfs_dir2_leaf *leaf2 = leaf2_bp->b_addr; + struct xfs_dir2_leaf_entry *ents1; + struct xfs_dir2_leaf_entry *ents2; + struct xfs_dir3_icleaf_hdr hdr1; + struct xfs_dir3_icleaf_hdr hdr2; + + xfs_dir3_leaf_hdr_from_disk(&hdr1, leaf1); + xfs_dir3_leaf_hdr_from_disk(&hdr2, leaf2); + ents1 = xfs_dir3_leaf_ents_p(leaf1); + ents2 = xfs_dir3_leaf_ents_p(leaf2); + + if (hdr1.count > 0 && hdr2.count > 0 && + (be32_to_cpu(ents2[0].hashval) < be32_to_cpu(ents1[0].hashval) || + be32_to_cpu(ents2[hdr2.count - 1].hashval) < + be32_to_cpu(ents1[hdr1.count - 1].hashval))) return 1; return 0; } @@ -966,6 +981,10 @@ xfs_dir2_leafn_rebalance( #endif int oldsum; /* old total leaf count */ int swap; /* swapped leaf blocks */ + struct xfs_dir2_leaf_entry *ents1; + struct xfs_dir2_leaf_entry *ents2; + struct xfs_dir3_icleaf_hdr hdr1; + struct xfs_dir3_icleaf_hdr hdr2; args = state->args; /* @@ -980,11 +999,17 @@ xfs_dir2_leafn_rebalance( } leaf1 = blk1->bp->b_addr; leaf2 = blk2->bp->b_addr; - oldsum = be16_to_cpu(leaf1->hdr.count) + be16_to_cpu(leaf2->hdr.count); + xfs_dir3_leaf_hdr_from_disk(&hdr1, leaf1); + xfs_dir3_leaf_hdr_from_disk(&hdr2, leaf2); + ents1 = xfs_dir3_leaf_ents_p(leaf1); + ents2 = xfs_dir3_leaf_ents_p(leaf2); + + oldsum = hdr1.count + hdr2.count; #ifdef DEBUG - oldstale = be16_to_cpu(leaf1->hdr.stale) + be16_to_cpu(leaf2->hdr.stale); + oldstale = hdr1.stale + hdr2.stale; #endif mid = oldsum >> 1; + /* * If the old leaf count was odd then the new one will be even, * so we need to divide the new count evenly. @@ -992,10 +1017,10 @@ xfs_dir2_leafn_rebalance( if (oldsum & 1) { xfs_dahash_t midhash; /* middle entry hash value */ - if (mid >= be16_to_cpu(leaf1->hdr.count)) - midhash = be32_to_cpu(leaf2->ents[mid - be16_to_cpu(leaf1->hdr.count)].hashval); + if (mid >= hdr1.count) + midhash = be32_to_cpu(ents2[mid - hdr1.count].hashval); else - midhash = be32_to_cpu(leaf1->ents[mid].hashval); + midhash = be32_to_cpu(ents1[mid].hashval); isleft = args->hashval <= midhash; } /* @@ -1009,30 +1034,42 @@ xfs_dir2_leafn_rebalance( * Calculate moved entry count. Positive means left-to-right, * negative means right-to-left. Then move the entries. */ - count = be16_to_cpu(leaf1->hdr.count) - mid + (isleft == 0); + count = hdr1.count - mid + (isleft == 0); if (count > 0) - xfs_dir2_leafn_moveents(args, blk1->bp, - be16_to_cpu(leaf1->hdr.count) - count, blk2->bp, 0, count); + xfs_dir3_leafn_moveents(args, blk1->bp, &hdr1, ents1, + hdr1.count - count, blk2->bp, + &hdr2, ents2, 0, count); else if (count < 0) - xfs_dir2_leafn_moveents(args, blk2->bp, 0, blk1->bp, - be16_to_cpu(leaf1->hdr.count), count); - ASSERT(be16_to_cpu(leaf1->hdr.count) + be16_to_cpu(leaf2->hdr.count) == oldsum); - ASSERT(be16_to_cpu(leaf1->hdr.stale) + be16_to_cpu(leaf2->hdr.stale) == oldstale); + xfs_dir3_leafn_moveents(args, blk2->bp, &hdr2, ents2, 0, + blk1->bp, &hdr1, ents1, + hdr1.count, count); + + ASSERT(hdr1.count + hdr2.count == oldsum); + ASSERT(hdr1.stale + hdr2.stale == oldstale); + + /* log the changes made when moving the entries */ + xfs_dir3_leaf_hdr_to_disk(leaf1, &hdr1); + xfs_dir3_leaf_hdr_to_disk(leaf2, &hdr2); + xfs_dir3_leaf_log_header(args->trans, blk1->bp); + xfs_dir3_leaf_log_header(args->trans, blk2->bp); + + xfs_dir3_leaf_check(args->dp->i_mount, blk1->bp); + xfs_dir3_leaf_check(args->dp->i_mount, blk2->bp); + /* * Mark whether we're inserting into the old or new leaf. */ - if (be16_to_cpu(leaf1->hdr.count) < be16_to_cpu(leaf2->hdr.count)) + if (hdr1.count < hdr2.count) state->inleaf = swap; - else if (be16_to_cpu(leaf1->hdr.count) > be16_to_cpu(leaf2->hdr.count)) + else if (hdr1.count > hdr2.count) state->inleaf = !swap; else - state->inleaf = - swap ^ (blk1->index <= be16_to_cpu(leaf1->hdr.count)); + state->inleaf = swap ^ (blk1->index <= hdr1.count); /* * Adjust the expected index for insertion. */ if (!state->inleaf) - blk2->index = blk1->index - be16_to_cpu(leaf1->hdr.count); + blk2->index = blk1->index - hdr1.count; /* * Finally sanity check just to make sure we are not returning a @@ -1154,6 +1191,8 @@ xfs_dir2_leafn_remove( int needscan; /* need to rescan data frees */ xfs_trans_t *tp; /* transaction pointer */ struct xfs_dir2_data_free *bf; /* bestfree table */ + struct xfs_dir3_icleaf_hdr leafhdr; + struct xfs_dir2_leaf_entry *ents; trace_xfs_dir2_leafn_remove(args, index); @@ -1161,11 +1200,14 @@ xfs_dir2_leafn_remove( tp = args->trans; mp = dp->i_mount; leaf = bp->b_addr; - ASSERT(leaf->hdr.info.magic == cpu_to_be16(XFS_DIR2_LEAFN_MAGIC)); + xfs_dir3_leaf_hdr_from_disk(&leafhdr, leaf); + ents = xfs_dir3_leaf_ents_p(leaf); + /* * Point to the entry we're removing. */ - lep = &leaf->ents[index]; + lep = &ents[index]; + /* * Extract the data block and offset from the entry. */ @@ -1173,14 +1215,18 @@ xfs_dir2_leafn_remove( ASSERT(dblk->blkno == db); off = xfs_dir2_dataptr_to_off(mp, be32_to_cpu(lep->address)); ASSERT(dblk->index == off); + /* * Kill the leaf entry by marking it stale. * Log the leaf block changes. */ - be16_add_cpu(&leaf->hdr.stale, 1); - xfs_dir2_leaf_log_header(tp, bp); + leafhdr.stale++; + xfs_dir3_leaf_hdr_to_disk(leaf, &leafhdr); + xfs_dir3_leaf_log_header(tp, bp); + lep->address = cpu_to_be32(XFS_DIR2_NULL_DATAPTR); - xfs_dir2_leaf_log_ents(tp, bp, index, index); + xfs_dir3_leaf_log_ents(tp, bp, index, index); + /* * Make the data entry free. Keep track of the longest freespace * in the data block in case it changes. @@ -1269,15 +1315,13 @@ xfs_dir2_leafn_remove( return error; } - xfs_dir2_leafn_check(dp, bp); + xfs_dir3_leaf_check(mp, bp); /* * Return indication of whether this leaf block is empty enough * to justify trying to join it with a neighbor. */ - *rval = - ((uint)sizeof(leaf->hdr) + - (uint)sizeof(leaf->ents[0]) * - (be16_to_cpu(leaf->hdr.count) - be16_to_cpu(leaf->hdr.stale))) < + *rval = (xfs_dir3_leaf_hdr_size(leaf) + + (uint)sizeof(ents[0]) * (leafhdr.count - leafhdr.stale)) < mp->m_dir_magicpct; return 0; } @@ -1310,11 +1354,11 @@ xfs_dir2_leafn_split( /* * Initialize the new leaf block. */ - error = xfs_dir2_leaf_init(args, xfs_dir2_da_to_db(mp, blkno), - &newblk->bp, XFS_DIR2_LEAFN_MAGIC); - if (error) { + error = xfs_dir3_leaf_get_buf(args, xfs_dir2_da_to_db(mp, blkno), + &newblk->bp, XFS_DIR2_LEAFN_MAGIC); + if (error) return error; - } + newblk->blkno = blkno; newblk->magic = XFS_DIR2_LEAFN_MAGIC; /* @@ -1338,8 +1382,8 @@ xfs_dir2_leafn_split( */ oldblk->hashval = xfs_dir2_leafn_lasthash(oldblk->bp, NULL); newblk->hashval = xfs_dir2_leafn_lasthash(newblk->bp, NULL); - xfs_dir2_leafn_check(args->dp, oldblk->bp); - xfs_dir2_leafn_check(args->dp, newblk->bp); + xfs_dir3_leaf_check(mp, oldblk->bp); + xfs_dir3_leaf_check(mp, newblk->bp); return error; } @@ -1368,6 +1412,8 @@ xfs_dir2_leafn_toosmall( xfs_da_blkinfo_t *info; /* leaf block header */ xfs_dir2_leaf_t *leaf; /* leaf structure */ int rval; /* result from path_shift */ + struct xfs_dir3_icleaf_hdr leafhdr; + struct xfs_dir2_leaf_entry *ents; /* * Check for the degenerate case of the block being over 50% full. @@ -1376,10 +1422,12 @@ xfs_dir2_leafn_toosmall( */ blk = &state->path.blk[state->path.active - 1]; info = blk->bp->b_addr; - ASSERT(info->magic == cpu_to_be16(XFS_DIR2_LEAFN_MAGIC)); leaf = (xfs_dir2_leaf_t *)info; - count = be16_to_cpu(leaf->hdr.count) - be16_to_cpu(leaf->hdr.stale); - bytes = (uint)sizeof(leaf->hdr) + count * (uint)sizeof(leaf->ents[0]); + xfs_dir3_leaf_hdr_from_disk(&leafhdr, leaf); + ents = xfs_dir3_leaf_ents_p(leaf); + + count = leafhdr.count - leafhdr.stale; + bytes = xfs_dir3_leaf_hdr_size(leaf) + count * sizeof(ents[0]); if (bytes > (state->blocksize >> 1)) { /* * Blk over 50%, don't try to join. @@ -1398,7 +1446,7 @@ xfs_dir2_leafn_toosmall( * Make altpath point to the block we want to keep and * path point to the block we want to drop (this one). */ - forward = (info->forw != 0); + forward = (leafhdr.forw != 0); memcpy(&state->altpath, &state->path, sizeof(state->path)); error = xfs_da_path_shift(state, &state->altpath, forward, 0, &rval); @@ -1414,15 +1462,17 @@ xfs_dir2_leafn_toosmall( * We prefer coalescing with the lower numbered sibling so as * to shrink a directory over time. */ - forward = be32_to_cpu(info->forw) < be32_to_cpu(info->back); + forward = leafhdr.forw < leafhdr.back; for (i = 0, bp = NULL; i < 2; forward = !forward, i++) { - blkno = forward ? be32_to_cpu(info->forw) : be32_to_cpu(info->back); + struct xfs_dir3_icleaf_hdr hdr2; + + blkno = forward ? leafhdr.forw : leafhdr.back; if (blkno == 0) continue; /* * Read the sibling leaf block. */ - error = xfs_dir2_leafn_read(state->args->trans, state->args->dp, + error = xfs_dir3_leafn_read(state->args->trans, state->args->dp, blkno, -1, &bp); if (error) return error; @@ -1430,13 +1480,15 @@ xfs_dir2_leafn_toosmall( /* * Count bytes in the two blocks combined. */ - leaf = (xfs_dir2_leaf_t *)info; - count = be16_to_cpu(leaf->hdr.count) - be16_to_cpu(leaf->hdr.stale); + count = leafhdr.count - leafhdr.stale; bytes = state->blocksize - (state->blocksize >> 2); + leaf = bp->b_addr; - ASSERT(leaf->hdr.info.magic == cpu_to_be16(XFS_DIR2_LEAFN_MAGIC)); - count += be16_to_cpu(leaf->hdr.count) - be16_to_cpu(leaf->hdr.stale); - bytes -= count * (uint)sizeof(leaf->ents[0]); + xfs_dir3_leaf_hdr_from_disk(&hdr2, leaf); + ents = xfs_dir3_leaf_ents_p(leaf); + count += hdr2.count - hdr2.stale; + bytes -= count * sizeof(ents[0]); + /* * Fits with at least 25% to spare. */ @@ -1483,34 +1535,52 @@ xfs_dir2_leafn_unbalance( xfs_da_args_t *args; /* operation arguments */ xfs_dir2_leaf_t *drop_leaf; /* dead leaf structure */ xfs_dir2_leaf_t *save_leaf; /* surviving leaf structure */ + struct xfs_dir3_icleaf_hdr shdr; + struct xfs_dir3_icleaf_hdr dhdr; + struct xfs_dir2_leaf_entry *sents; + struct xfs_dir2_leaf_entry *dents; args = state->args; ASSERT(drop_blk->magic == XFS_DIR2_LEAFN_MAGIC); ASSERT(save_blk->magic == XFS_DIR2_LEAFN_MAGIC); drop_leaf = drop_blk->bp->b_addr; save_leaf = save_blk->bp->b_addr; - ASSERT(drop_leaf->hdr.info.magic == cpu_to_be16(XFS_DIR2_LEAFN_MAGIC)); - ASSERT(save_leaf->hdr.info.magic == cpu_to_be16(XFS_DIR2_LEAFN_MAGIC)); + + xfs_dir3_leaf_hdr_from_disk(&shdr, save_leaf); + xfs_dir3_leaf_hdr_from_disk(&dhdr, drop_leaf); + sents = xfs_dir3_leaf_ents_p(save_leaf); + dents = xfs_dir3_leaf_ents_p(drop_leaf); + /* * If there are any stale leaf entries, take this opportunity * to purge them. */ - if (drop_leaf->hdr.stale) - xfs_dir2_leaf_compact(args, drop_blk->bp); - if (save_leaf->hdr.stale) - xfs_dir2_leaf_compact(args, save_blk->bp); + if (dhdr.stale) + xfs_dir3_leaf_compact(args, &dhdr, drop_blk->bp); + if (shdr.stale) + xfs_dir3_leaf_compact(args, &shdr, save_blk->bp); + /* * Move the entries from drop to the appropriate end of save. */ - drop_blk->hashval = be32_to_cpu(drop_leaf->ents[be16_to_cpu(drop_leaf->hdr.count) - 1].hashval); + drop_blk->hashval = be32_to_cpu(dents[dhdr.count - 1].hashval); if (xfs_dir2_leafn_order(save_blk->bp, drop_blk->bp)) - xfs_dir2_leafn_moveents(args, drop_blk->bp, 0, save_blk->bp, 0, - be16_to_cpu(drop_leaf->hdr.count)); + xfs_dir3_leafn_moveents(args, drop_blk->bp, &dhdr, dents, 0, + save_blk->bp, &shdr, sents, 0, + dhdr.count); else - xfs_dir2_leafn_moveents(args, drop_blk->bp, 0, save_blk->bp, - be16_to_cpu(save_leaf->hdr.count), be16_to_cpu(drop_leaf->hdr.count)); - save_blk->hashval = be32_to_cpu(save_leaf->ents[be16_to_cpu(save_leaf->hdr.count) - 1].hashval); - xfs_dir2_leafn_check(args->dp, save_blk->bp); + xfs_dir3_leafn_moveents(args, drop_blk->bp, &dhdr, dents, 0, + save_blk->bp, &shdr, sents, + shdr.count, dhdr.count); + save_blk->hashval = be32_to_cpu(sents[shdr.count - 1].hashval); + + /* log the changes made when moving the entries */ + xfs_dir3_leaf_hdr_to_disk(save_leaf, &shdr); + xfs_dir3_leaf_hdr_to_disk(drop_leaf, &dhdr); + xfs_dir3_leaf_log_header(args->trans, save_blk->bp); + xfs_dir3_leaf_log_header(args->trans, drop_blk->bp); + + xfs_dir3_leaf_check(args->dp->i_mount, save_blk->bp); } /* @@ -2115,13 +2185,15 @@ xfs_dir2_node_replace( * and locked it. But paranoia is good. */ if (rval == EEXIST) { + struct xfs_dir2_leaf_entry *ents; /* * Find the leaf entry. */ blk = &state->path.blk[state->path.active - 1]; ASSERT(blk->magic == XFS_DIR2_LEAFN_MAGIC); leaf = blk->bp->b_addr; - lep = &leaf->ents[blk->index]; + ents = xfs_dir3_leaf_ents_p(leaf); + lep = &ents[blk->index]; ASSERT(state->extravalid); /* * Point to the data entry. diff --git a/fs/xfs/xfs_dir2_priv.h b/fs/xfs/xfs_dir2_priv.h index 910e644..932565d 100644 --- a/fs/xfs/xfs_dir2_priv.h +++ b/fs/xfs/xfs_dir2_priv.h @@ -77,24 +77,25 @@ extern void xfs_dir2_data_use_free(struct xfs_trans *tp, struct xfs_buf *bp, xfs_dir2_data_aoff_t len, int *needlogp, int *needscanp); /* xfs_dir2_leaf.c */ -extern const struct xfs_buf_ops xfs_dir2_leafn_buf_ops; +extern const struct xfs_buf_ops xfs_dir3_leafn_buf_ops; -extern int xfs_dir2_leafn_read(struct xfs_trans *tp, struct xfs_inode *dp, +extern int xfs_dir3_leafn_read(struct xfs_trans *tp, struct xfs_inode *dp, xfs_dablk_t fbno, xfs_daddr_t mappedbno, struct xfs_buf **bpp); extern int xfs_dir2_block_to_leaf(struct xfs_da_args *args, struct xfs_buf *dbp); extern int xfs_dir2_leaf_addname(struct xfs_da_args *args); -extern void xfs_dir2_leaf_compact(struct xfs_da_args *args, - struct xfs_buf *bp); -extern void xfs_dir2_leaf_compact_x1(struct xfs_buf *bp, int *indexp, +extern void xfs_dir3_leaf_compact(struct xfs_da_args *args, + struct xfs_dir3_icleaf_hdr *leafhdr, struct xfs_buf *bp); +extern void xfs_dir3_leaf_compact_x1(struct xfs_dir3_icleaf_hdr *leafhdr, + struct xfs_dir2_leaf_entry *ents, int *indexp, int *lowstalep, int *highstalep, int *lowlogp, int *highlogp); extern int xfs_dir2_leaf_getdents(struct xfs_inode *dp, void *dirent, size_t bufsize, xfs_off_t *offset, filldir_t filldir); -extern int xfs_dir2_leaf_init(struct xfs_da_args *args, xfs_dir2_db_t bno, - struct xfs_buf **bpp, int magic); -extern void xfs_dir2_leaf_log_ents(struct xfs_trans *tp, struct xfs_buf *bp, +extern int xfs_dir3_leaf_get_buf(struct xfs_da_args *args, xfs_dir2_db_t bno, + struct xfs_buf **bpp, __uint16_t magic); +extern void xfs_dir3_leaf_log_ents(struct xfs_trans *tp, struct xfs_buf *bp, int first, int last); -extern void xfs_dir2_leaf_log_header(struct xfs_trans *tp, +extern void xfs_dir3_leaf_log_header(struct xfs_trans *tp, struct xfs_buf *bp); extern int xfs_dir2_leaf_lookup(struct xfs_da_args *args); extern int xfs_dir2_leaf_removename(struct xfs_da_args *args); @@ -104,11 +105,18 @@ extern int xfs_dir2_leaf_search_hash(struct xfs_da_args *args, extern int xfs_dir2_leaf_trim_data(struct xfs_da_args *args, struct xfs_buf *lbp, xfs_dir2_db_t db); extern struct xfs_dir2_leaf_entry * -xfs_dir2_leaf_find_entry(struct xfs_dir2_leaf *leaf, int index, int compact, - int lowstale, int highstale, - int *lfloglow, int *lfloghigh); +xfs_dir3_leaf_find_entry(struct xfs_dir3_icleaf_hdr *leafhdr, + struct xfs_dir2_leaf_entry *ents, int index, int compact, + int lowstale, int highstale, int *lfloglow, int *lfloghigh); extern int xfs_dir2_node_to_leaf(struct xfs_da_state *state); +extern void xfs_dir3_leaf_hdr_from_disk(struct xfs_dir3_icleaf_hdr *to, + struct xfs_dir2_leaf *from); +extern void xfs_dir3_leaf_hdr_to_disk(struct xfs_dir2_leaf *to, + struct xfs_dir3_icleaf_hdr *from); +extern bool xfs_dir3_leaf_check_int(struct xfs_mount *mp, + struct xfs_dir3_icleaf_hdr *hdr, struct xfs_dir2_leaf *leaf); + /* xfs_dir2_node.c */ extern int xfs_dir2_leaf_to_node(struct xfs_da_args *args, struct xfs_buf *lbp); -- 1.7.10.4 From dave@fromorbit.com Tue Mar 12 07:31:46 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id B9C567F8E for ; Tue, 12 Mar 2013 07:31:46 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay1.corp.sgi.com (Postfix) with ESMTP id 4462E8F8050 for ; Tue, 12 Mar 2013 05:31:46 -0700 (PDT) X-ASG-Debug-ID: 1363091497-04bdf022984cb130002-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id T4x0c9ca6JDf7FJ7 for ; Tue, 12 Mar 2013 05:31:39 -0700 (PDT) X-Barracuda-Envelope-From: dave@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AhAKAKEfP1F5LKiV/2dsb2JhbABDxF0DAYFJF3SCKAEBBRoBDC8zCBgxOQMbGYgSsAKQH44MdoNSA5MQiT+Ke4MeKA Received: from ppp121-44-168-149.lns20.syd7.internode.on.net (HELO dastard) ([121.44.168.149]) by ipmail05.adl6.internode.on.net with ESMTP; 12 Mar 2013 23:01:29 +1030 Received: from [192.168.1.1] (helo=disappointment) by dastard with esmtp (Exim 4.76) (envelope-from ) id 1UFOMa-0001SR-Is for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:31:28 +1100 Received: from dave by disappointment with local (Exim 4.80) (envelope-from ) id 1UFOMQ-0002Mt-Gq for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:31:18 +1100 From: Dave Chinner To: xfs@oss.sgi.com Subject: [PATCH 16/21] xfs: add CRCs to dir2/da node blocks Date: Tue, 12 Mar 2013 23:30:49 +1100 X-ASG-Orig-Subj: [PATCH 16/21] xfs: add CRCs to dir2/da node blocks Message-Id: <1363091454-8852-17-git-send-email-david@fromorbit.com> X-Mailer: git-send-email 1.7.10.4 In-Reply-To: <1363091454-8852-1-git-send-email-david@fromorbit.com> References: <1363091454-8852-1-git-send-email-david@fromorbit.com> X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1363091499 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Barracuda-BRTS-Status: 1 X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124988 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- From: Dave Chinner Signed-off-by: Dave Chinner --- fs/xfs/xfs_attr.c | 33 +- fs/xfs/xfs_attr_leaf.c | 29 +- fs/xfs/xfs_bmap.c | 1 + fs/xfs/xfs_da_btree.c | 1395 +++++++++++++++++++++++++++++------------------- fs/xfs/xfs_da_btree.h | 106 +++- fs/xfs/xfs_dir2_node.c | 26 +- fs/xfs/xfs_trace.c | 2 +- 7 files changed, 972 insertions(+), 620 deletions(-) diff --git a/fs/xfs/xfs_attr.c b/fs/xfs/xfs_attr.c index 8886838..e03128c 100644 --- a/fs/xfs/xfs_attr.c +++ b/fs/xfs/xfs_attr.c @@ -15,7 +15,6 @@ * along with this program; if not, write the Free Software Foundation, * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA */ - #include "xfs.h" #include "xfs_fs.h" #include "xfs_types.h" @@ -25,6 +24,7 @@ #include "xfs_sb.h" #include "xfs_ag.h" #include "xfs_mount.h" +#include "xfs_error.h" #include "xfs_da_btree.h" #include "xfs_bmap_btree.h" #include "xfs_attr_sf.h" @@ -35,7 +35,6 @@ #include "xfs_bmap.h" #include "xfs_attr.h" #include "xfs_attr_leaf.h" -#include "xfs_error.h" #include "xfs_quota.h" #include "xfs_trans_space.h" #include "xfs_vnodeops.h" @@ -1236,7 +1235,7 @@ restart: * Search to see if name already exists, and get back a pointer * to where it should go. */ - error = xfs_da_node_lookup_int(state, &retval); + error = xfs_da3_node_lookup_int(state, &retval); if (error) goto out; blk = &state->path.blk[ state->path.active-1 ]; @@ -1307,7 +1306,7 @@ restart: * in the index2/blkno2/rmtblkno2/rmtblkcnt2 fields. */ xfs_bmap_init(args->flist, args->firstblock); - error = xfs_da_split(state); + error = xfs_da3_split(state); if (!error) { error = xfs_bmap_finish(&args->trans, args->flist, &committed); @@ -1329,7 +1328,7 @@ restart: /* * Addition succeeded, update Btree hashvals. */ - xfs_da_fixhashpath(state, &state->path); + xfs_da3_fixhashpath(state, &state->path); } /* @@ -1400,7 +1399,7 @@ restart: state->blocksize = state->mp->m_sb.sb_blocksize; state->node_ents = state->mp->m_attr_node_ents; state->inleaf = 0; - error = xfs_da_node_lookup_int(state, &retval); + error = xfs_da3_node_lookup_int(state, &retval); if (error) goto out; @@ -1410,14 +1409,14 @@ restart: blk = &state->path.blk[ state->path.active-1 ]; ASSERT(blk->magic == XFS_ATTR_LEAF_MAGIC); error = xfs_attr_leaf_remove(blk->bp, args); - xfs_da_fixhashpath(state, &state->path); + xfs_da3_fixhashpath(state, &state->path); /* * Check to see if the tree needs to be collapsed. */ if (retval && (state->path.active > 1)) { xfs_bmap_init(args->flist, args->firstblock); - error = xfs_da_join(state); + error = xfs_da3_join(state); if (!error) { error = xfs_bmap_finish(&args->trans, args->flist, @@ -1495,7 +1494,7 @@ xfs_attr_node_removename(xfs_da_args_t *args) /* * Search to see if name exists, and get back a pointer to it. */ - error = xfs_da_node_lookup_int(state, &retval); + error = xfs_da3_node_lookup_int(state, &retval); if (error || (retval != EEXIST)) { if (error == 0) error = retval; @@ -1546,14 +1545,14 @@ xfs_attr_node_removename(xfs_da_args_t *args) blk = &state->path.blk[ state->path.active-1 ]; ASSERT(blk->magic == XFS_ATTR_LEAF_MAGIC); retval = xfs_attr_leaf_remove(blk->bp, args); - xfs_da_fixhashpath(state, &state->path); + xfs_da3_fixhashpath(state, &state->path); /* * Check to see if the tree needs to be collapsed. */ if (retval && (state->path.active > 1)) { xfs_bmap_init(args->flist, args->firstblock); - error = xfs_da_join(state); + error = xfs_da3_join(state); if (!error) { error = xfs_bmap_finish(&args->trans, args->flist, &committed); @@ -1699,7 +1698,7 @@ xfs_attr_refillstate(xfs_da_state_t *state) ASSERT((path->active >= 0) && (path->active < XFS_DA_NODE_MAXDEPTH)); for (blk = path->blk, level = 0; level < path->active; blk++, level++) { if (blk->disk_blkno) { - error = xfs_da_node_read(state->args->trans, + error = xfs_da3_node_read(state->args->trans, state->args->dp, blk->blkno, blk->disk_blkno, &blk->bp, XFS_ATTR_FORK); @@ -1718,7 +1717,7 @@ xfs_attr_refillstate(xfs_da_state_t *state) ASSERT((path->active >= 0) && (path->active < XFS_DA_NODE_MAXDEPTH)); for (blk = path->blk, level = 0; level < path->active; blk++, level++) { if (blk->disk_blkno) { - error = xfs_da_node_read(state->args->trans, + error = xfs_da3_node_read(state->args->trans, state->args->dp, blk->blkno, blk->disk_blkno, &blk->bp, XFS_ATTR_FORK); @@ -1758,7 +1757,7 @@ xfs_attr_node_get(xfs_da_args_t *args) /* * Search to see if name exists, and get back a pointer to it. */ - error = xfs_da_node_lookup_int(state, &retval); + error = xfs_da3_node_lookup_int(state, &retval); if (error) { retval = error; } else if (retval == EEXIST) { @@ -1810,7 +1809,7 @@ xfs_attr_node_list(xfs_attr_list_context_t *context) */ bp = NULL; if (cursor->blkno > 0) { - error = xfs_da_node_read(NULL, context->dp, cursor->blkno, -1, + error = xfs_da3_node_read(NULL, context->dp, cursor->blkno, -1, &bp, XFS_ATTR_FORK); if ((error != 0) && (error != EFSCORRUPTED)) return(error); @@ -1852,7 +1851,7 @@ xfs_attr_node_list(xfs_attr_list_context_t *context) if (bp == NULL) { cursor->blkno = 0; for (;;) { - error = xfs_da_node_read(NULL, context->dp, + error = xfs_da3_node_read(NULL, context->dp, cursor->blkno, -1, &bp, XFS_ATTR_FORK); if (error) @@ -1870,7 +1869,7 @@ xfs_attr_node_list(xfs_attr_list_context_t *context) xfs_trans_brelse(NULL, bp); return(XFS_ERROR(EFSCORRUPTED)); } - btree = node->btree; + btree = xfs_da3_node_tree_p(node); for (i = 0; i < be16_to_cpu(node->hdr.count); btree++, i++) { if (cursor->hashval diff --git a/fs/xfs/xfs_attr_leaf.c b/fs/xfs/xfs_attr_leaf.c index aa4765f..54b0dc8 100644 --- a/fs/xfs/xfs_attr_leaf.c +++ b/fs/xfs/xfs_attr_leaf.c @@ -910,6 +910,7 @@ xfs_attr_leaf_to_node(xfs_da_args_t *args) struct xfs_buf *bp1, *bp2; xfs_dablk_t blkno; int error; + struct xfs_da_node_entry *btree; trace_xfs_attr_leaf_to_node(args); @@ -935,16 +936,16 @@ xfs_attr_leaf_to_node(xfs_da_args_t *args) /* * Set up the new root node. */ - error = xfs_da_node_create(args, 0, 1, &bp1, XFS_ATTR_FORK); + error = xfs_da3_node_create(args, 0, 1, &bp1, XFS_ATTR_FORK); if (error) goto out; node = bp1->b_addr; leaf = bp2->b_addr; ASSERT(leaf->hdr.info.magic == cpu_to_be16(XFS_ATTR_LEAF_MAGIC)); /* both on-disk, don't endian-flip twice */ - node->btree[0].hashval = - leaf->entries[be16_to_cpu(leaf->hdr.count)-1 ].hashval; - node->btree[0].before = cpu_to_be32(blkno); + btree = xfs_da3_node_tree_p(node); + btree[0].hashval = leaf->entries[be16_to_cpu(leaf->hdr.count)-1 ].hashval; + btree[0].before = cpu_to_be32(blkno); node->hdr.count = cpu_to_be16(1); xfs_trans_log_buf(args->trans, bp1, 0, XFS_LBSIZE(dp->i_mount) - 1); error = 0; @@ -1032,7 +1033,7 @@ xfs_attr_leaf_split(xfs_da_state_t *state, xfs_da_state_blk_t *oldblk, * NOTE: rebalance() currently depends on the 2nd block being empty. */ xfs_attr_leaf_rebalance(state, oldblk, newblk); - error = xfs_da_blk_link(state, oldblk, newblk); + error = xfs_da3_blk_link(state, oldblk, newblk); if (error) return(error); @@ -1660,7 +1661,7 @@ xfs_attr_leaf_toosmall(xfs_da_state_t *state, int *action) */ forward = (info->forw != 0); memcpy(&state->altpath, &state->path, sizeof(state->path)); - error = xfs_da_path_shift(state, &state->altpath, forward, + error = xfs_da3_path_shift(state, &state->altpath, forward, 0, &retval); if (error) return(error); @@ -1717,10 +1718,10 @@ xfs_attr_leaf_toosmall(xfs_da_state_t *state, int *action) */ memcpy(&state->altpath, &state->path, sizeof(state->path)); if (blkno < blk->blkno) { - error = xfs_da_path_shift(state, &state->altpath, forward, + error = xfs_da3_path_shift(state, &state->altpath, forward, 0, &retval); } else { - error = xfs_da_path_shift(state, &state->path, forward, + error = xfs_da3_path_shift(state, &state->path, forward, 0, &retval); } if (error) @@ -2783,7 +2784,7 @@ xfs_attr_root_inactive(xfs_trans_t **trans, xfs_inode_t *dp) * the extents in reverse order the extent containing * block 0 must still be there. */ - error = xfs_da_node_read(*trans, dp, 0, -1, &bp, XFS_ATTR_FORK); + error = xfs_da3_node_read(*trans, dp, 0, -1, &bp, XFS_ATTR_FORK); if (error) return(error); blkno = XFS_BUF_ADDR(bp); @@ -2836,6 +2837,7 @@ xfs_attr_node_inactive( xfs_daddr_t parent_blkno, child_blkno; int error, count, i; struct xfs_buf *child_bp; + struct xfs_da_node_entry *btree; /* * Since this code is recursive (gasp!) we must protect ourselves. @@ -2853,7 +2855,8 @@ xfs_attr_node_inactive( xfs_trans_brelse(*trans, bp); return(0); } - child_fsb = be32_to_cpu(node->btree[0].before); + btree = xfs_da3_node_tree_p(node); + child_fsb = be32_to_cpu(btree[0].before); xfs_trans_brelse(*trans, bp); /* no locks for later trans */ /* @@ -2868,7 +2871,7 @@ xfs_attr_node_inactive( * traversal of the tree so we may deal with many blocks * before we come back to this one. */ - error = xfs_da_node_read(*trans, dp, child_fsb, -2, &child_bp, + error = xfs_da3_node_read(*trans, dp, child_fsb, -2, &child_bp, XFS_ATTR_FORK); if (error) return(error); @@ -2909,11 +2912,11 @@ xfs_attr_node_inactive( * child block number. */ if ((i+1) < count) { - error = xfs_da_node_read(*trans, dp, 0, parent_blkno, + error = xfs_da3_node_read(*trans, dp, 0, parent_blkno, &bp, XFS_ATTR_FORK); if (error) return(error); - child_fsb = be32_to_cpu(node->btree[i+1].before); + child_fsb = be32_to_cpu(btree[i+1].before); xfs_trans_brelse(*trans, bp); } /* diff --git a/fs/xfs/xfs_bmap.c b/fs/xfs/xfs_bmap.c index 0fcb7f4..2844724 100644 --- a/fs/xfs/xfs_bmap.c +++ b/fs/xfs/xfs_bmap.c @@ -25,6 +25,7 @@ #include "xfs_sb.h" #include "xfs_ag.h" #include "xfs_dir2.h" +#include "xfs_mount.h" #include "xfs_da_btree.h" #include "xfs_bmap_btree.h" #include "xfs_alloc_btree.h" diff --git a/fs/xfs/xfs_da_btree.c b/fs/xfs/xfs_da_btree.c index 2f23b14..a824edd 100644 --- a/fs/xfs/xfs_da_btree.c +++ b/fs/xfs/xfs_da_btree.c @@ -1,5 +1,6 @@ /* * Copyright (c) 2000-2005 Silicon Graphics, Inc. + * Copyright (c) 2013 Red Hat, Inc. * All Rights Reserved. * * This program is free software; you can redistribute it and/or @@ -38,6 +39,8 @@ #include "xfs_attr_leaf.h" #include "xfs_error.h" #include "xfs_trace.h" +#include "xfs_cksum.h" +#include "xfs_buf_item.h" /* * xfs_da_btree.c @@ -52,69 +55,195 @@ /* * Routines used for growing the Btree. */ -STATIC int xfs_da_root_split(xfs_da_state_t *state, +STATIC int xfs_da3_root_split(xfs_da_state_t *state, xfs_da_state_blk_t *existing_root, xfs_da_state_blk_t *new_child); -STATIC int xfs_da_node_split(xfs_da_state_t *state, +STATIC int xfs_da3_node_split(xfs_da_state_t *state, xfs_da_state_blk_t *existing_blk, xfs_da_state_blk_t *split_blk, xfs_da_state_blk_t *blk_to_add, int treelevel, int *result); -STATIC void xfs_da_node_rebalance(xfs_da_state_t *state, +STATIC void xfs_da3_node_rebalance(xfs_da_state_t *state, xfs_da_state_blk_t *node_blk_1, xfs_da_state_blk_t *node_blk_2); -STATIC void xfs_da_node_add(xfs_da_state_t *state, +STATIC void xfs_da3_node_add(xfs_da_state_t *state, xfs_da_state_blk_t *old_node_blk, xfs_da_state_blk_t *new_node_blk); /* * Routines used for shrinking the Btree. */ -STATIC int xfs_da_root_join(xfs_da_state_t *state, +STATIC int xfs_da3_root_join(xfs_da_state_t *state, xfs_da_state_blk_t *root_blk); -STATIC int xfs_da_node_toosmall(xfs_da_state_t *state, int *retval); -STATIC void xfs_da_node_remove(xfs_da_state_t *state, +STATIC int xfs_da3_node_toosmall(xfs_da_state_t *state, int *retval); +STATIC void xfs_da3_node_remove(xfs_da_state_t *state, xfs_da_state_blk_t *drop_blk); -STATIC void xfs_da_node_unbalance(xfs_da_state_t *state, +STATIC void xfs_da3_node_unbalance(xfs_da_state_t *state, xfs_da_state_blk_t *src_node_blk, xfs_da_state_blk_t *dst_node_blk); /* * Utility routines. */ -STATIC uint xfs_da_node_lasthash(struct xfs_buf *bp, int *count); -STATIC int xfs_da_node_order(struct xfs_buf *node1_bp, - struct xfs_buf *node2_bp); -STATIC int xfs_da_blk_unlink(xfs_da_state_t *state, +STATIC int xfs_da3_blk_unlink(xfs_da_state_t *state, xfs_da_state_blk_t *drop_blk, xfs_da_state_blk_t *save_blk); -STATIC void xfs_da_state_kill_altpath(xfs_da_state_t *state); -static void -xfs_da_node_verify( + +kmem_zone_t *xfs_da_state_zone; /* anchor for state struct zone */ + +/* + * Allocate a dir-state structure. + * We don't put them on the stack since they're large. + */ +xfs_da_state_t * +xfs_da_state_alloc(void) +{ + return kmem_zone_zalloc(xfs_da_state_zone, KM_NOFS); +} + +/* + * Kill the altpath contents of a da-state structure. + */ +STATIC void +xfs_da_state_kill_altpath(xfs_da_state_t *state) +{ + int i; + + for (i = 0; i < state->altpath.active; i++) + state->altpath.blk[i].bp = NULL; + state->altpath.active = 0; +} + +/* + * Free a da-state structure. + */ +void +xfs_da_state_free(xfs_da_state_t *state) +{ + xfs_da_state_kill_altpath(state); +#ifdef DEBUG + memset((char *)state, 0, sizeof(*state)); +#endif /* DEBUG */ + kmem_zone_free(xfs_da_state_zone, state); +} + +void +xfs_da3_node_hdr_from_disk( + struct xfs_da3_icnode_hdr *to, + struct xfs_da_intnode *from) +{ + ASSERT(from->hdr.info.magic == cpu_to_be16(XFS_DA_NODE_MAGIC) || + from->hdr.info.magic == cpu_to_be16(XFS_DA3_NODE_MAGIC)); + + if (from->hdr.info.magic == cpu_to_be16(XFS_DA3_NODE_MAGIC)) { + struct xfs_da3_node_hdr *hdr3 = (struct xfs_da3_node_hdr *)from; + + to->forw = be32_to_cpu(hdr3->info.hdr.forw); + to->back = be32_to_cpu(hdr3->info.hdr.back); + to->magic = be16_to_cpu(hdr3->info.hdr.magic); + to->count = be16_to_cpu(hdr3->count); + to->level = be16_to_cpu(hdr3->__level); + return; + } + to->forw = be32_to_cpu(from->hdr.info.forw); + to->back = be32_to_cpu(from->hdr.info.back); + to->magic = be16_to_cpu(from->hdr.info.magic); + to->count = be16_to_cpu(from->hdr.count); + to->level = be16_to_cpu(from->hdr.__level); +} + +void +xfs_da3_node_hdr_to_disk( + struct xfs_da_intnode *to, + struct xfs_da3_icnode_hdr *from) +{ + ASSERT(from->magic == XFS_DA_NODE_MAGIC || + from->magic == XFS_DA3_NODE_MAGIC); + + if (from->magic == XFS_DA3_NODE_MAGIC) { + struct xfs_da3_node_hdr *hdr3 = (struct xfs_da3_node_hdr *)to; + + hdr3->info.hdr.forw = cpu_to_be32(from->forw); + hdr3->info.hdr.back = cpu_to_be32(from->back); + hdr3->info.hdr.magic = cpu_to_be16(from->magic); + hdr3->count = cpu_to_be16(from->count); + hdr3->__level = cpu_to_be16(from->level); + return; + } + to->hdr.info.forw = cpu_to_be32(from->forw); + to->hdr.info.back = cpu_to_be32(from->back); + to->hdr.info.magic = cpu_to_be16(from->magic); + to->hdr.count = cpu_to_be16(from->count); + to->hdr.__level = cpu_to_be16(from->level); +} + +static bool +xfs_da3_node_verify( struct xfs_buf *bp) { struct xfs_mount *mp = bp->b_target->bt_mount; - struct xfs_da_node_hdr *hdr = bp->b_addr; - int block_ok = 0; - - block_ok = hdr->info.magic == cpu_to_be16(XFS_DA_NODE_MAGIC); - block_ok = block_ok && - be16_to_cpu(hdr->level) > 0 && - be16_to_cpu(hdr->count) > 0 ; - if (!block_ok) { - XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, mp, hdr); - xfs_buf_ioerror(bp, EFSCORRUPTED); + struct xfs_da_intnode *hdr = bp->b_addr; + struct xfs_da3_icnode_hdr ichdr; + + xfs_da3_node_hdr_from_disk(&ichdr, hdr); + + if (xfs_sb_version_hascrc(&mp->m_sb)) { + struct xfs_da3_node_hdr *hdr3 = bp->b_addr; + + if (ichdr.magic != XFS_DA3_NODE_MAGIC) + return false; + + if (!uuid_equal(&hdr3->info.uuid, &mp->m_sb.sb_uuid)) + return false; + if (be64_to_cpu(hdr3->info.blkno) != bp->b_bn) + return false; + } else { + if (ichdr.magic != XFS_DA_NODE_MAGIC) + return false; } + if (ichdr.level == 0) + return false; + if (ichdr.level > XFS_DA_NODE_MAXDEPTH) + return false; + if (ichdr.count == 0) + return false; + + /* + * we don't know if the node is for and attribute or directory tree, + * so only fail if the count is outside both bounds + */ + if (ichdr.count > mp->m_dir_node_ents && + ichdr.count > mp->m_attr_node_ents) + return false; + + /* XXX: hash order check? */ + return true; } static void -xfs_da_node_write_verify( +xfs_da3_node_write_verify( struct xfs_buf *bp) { - xfs_da_node_verify(bp); + struct xfs_mount *mp = bp->b_target->bt_mount; + struct xfs_buf_log_item *bip = bp->b_fspriv; + struct xfs_da3_node_hdr *hdr3 = bp->b_addr; + + if (!xfs_da3_node_verify(bp)) { + XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, mp, bp->b_addr); + xfs_buf_ioerror(bp, EFSCORRUPTED); + return; + } + + if (!xfs_sb_version_hascrc(&mp->m_sb)) + return; + + if (bip) + hdr3->info.lsn = cpu_to_be64(bip->bli_item.li_lsn); + + xfs_update_cksum(bp->b_addr, BBTOB(bp->b_length), XFS_DA3_NODE_CRC_OFF); } /* @@ -124,16 +253,22 @@ xfs_da_node_write_verify( * format of the block being read. */ static void -xfs_da_node_read_verify( +xfs_da3_node_read_verify( struct xfs_buf *bp) { struct xfs_mount *mp = bp->b_target->bt_mount; struct xfs_da_blkinfo *info = bp->b_addr; switch (be16_to_cpu(info->magic)) { + case XFS_DA3_NODE_MAGIC: + if (!xfs_verify_cksum(bp->b_addr, BBTOB(bp->b_length), + XFS_DA3_NODE_CRC_OFF)) + break; + /* fall through */ case XFS_DA_NODE_MAGIC: - xfs_da_node_verify(bp); - break; + if (!xfs_da3_node_verify(bp)) + break; + return; case XFS_ATTR_LEAF_MAGIC: bp->b_ops = &xfs_attr_leaf_buf_ops; bp->b_ops->verify_read(bp); @@ -144,21 +279,22 @@ xfs_da_node_read_verify( bp->b_ops->verify_read(bp); return; default: - XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, - mp, info); - xfs_buf_ioerror(bp, EFSCORRUPTED); break; } + + /* corrupt block */ + XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, mp, bp->b_addr); + xfs_buf_ioerror(bp, EFSCORRUPTED); } -const struct xfs_buf_ops xfs_da_node_buf_ops = { - .verify_read = xfs_da_node_read_verify, - .verify_write = xfs_da_node_write_verify, +const struct xfs_buf_ops xfs_da3_node_buf_ops = { + .verify_read = xfs_da3_node_read_verify, + .verify_write = xfs_da3_node_write_verify, }; int -xfs_da_node_read( +xfs_da3_node_read( struct xfs_trans *tp, struct xfs_inode *dp, xfs_dablk_t bno, @@ -167,7 +303,7 @@ xfs_da_node_read( int which_fork) { return xfs_da_read_buf(tp, dp, bno, mappedbno, bpp, - which_fork, &xfs_da_node_buf_ops); + which_fork, &xfs_da3_node_buf_ops); } /*======================================================================== @@ -178,33 +314,45 @@ xfs_da_node_read( * Create the initial contents of an intermediate node. */ int -xfs_da_node_create(xfs_da_args_t *args, xfs_dablk_t blkno, int level, - struct xfs_buf **bpp, int whichfork) +xfs_da3_node_create( + struct xfs_da_args *args, + xfs_dablk_t blkno, + int level, + struct xfs_buf **bpp, + int whichfork) { - xfs_da_intnode_t *node; - struct xfs_buf *bp; - int error; - xfs_trans_t *tp; + struct xfs_da_intnode *node; + struct xfs_trans *tp = args->trans; + struct xfs_mount *mp = tp->t_mountp; + struct xfs_da3_icnode_hdr ichdr = {0}; + struct xfs_buf *bp; + int error; trace_xfs_da_node_create(args); + ASSERT(level <= XFS_DA_NODE_MAXDEPTH); - tp = args->trans; error = xfs_da_get_buf(tp, args->dp, blkno, -1, &bp, whichfork); if (error) return(error); - ASSERT(bp != NULL); node = bp->b_addr; - node->hdr.info.forw = 0; - node->hdr.info.back = 0; - node->hdr.info.magic = cpu_to_be16(XFS_DA_NODE_MAGIC); - node->hdr.info.pad = 0; - node->hdr.count = 0; - node->hdr.level = cpu_to_be16(level); + if (xfs_sb_version_hascrc(&mp->m_sb)) { + struct xfs_da3_node_hdr *hdr3 = bp->b_addr; + + ichdr.magic = XFS_DA3_NODE_MAGIC; + hdr3->info.blkno = cpu_to_be64(bp->b_bn); + hdr3->info.owner = cpu_to_be64(args->dp->i_ino); + uuid_copy(&hdr3->info.uuid, &mp->m_sb.sb_uuid); + } else { + ichdr.magic = XFS_DA_NODE_MAGIC; + } + ichdr.level = level; + + xfs_da3_node_hdr_to_disk(node, &ichdr); xfs_trans_log_buf(tp, bp, - XFS_DA_LOGRANGE(node, &node->hdr, sizeof(node->hdr))); + XFS_DA_LOGRANGE(node, &node->hdr, xfs_da3_node_hdr_size(node))); - bp->b_ops = &xfs_da_node_buf_ops; + bp->b_ops = &xfs_da3_node_buf_ops; *bpp = bp; return(0); } @@ -214,12 +362,18 @@ xfs_da_node_create(xfs_da_args_t *args, xfs_dablk_t blkno, int level, * intermediate nodes, rebalance, etc. */ int /* error */ -xfs_da_split(xfs_da_state_t *state) +xfs_da3_split( + struct xfs_da_state *state) { - xfs_da_state_blk_t *oldblk, *newblk, *addblk; - xfs_da_intnode_t *node; - struct xfs_buf *bp; - int max, action, error, i; + struct xfs_da_state_blk *oldblk; + struct xfs_da_state_blk *newblk; + struct xfs_da_state_blk *addblk; + struct xfs_da_intnode *node; + struct xfs_buf *bp; + int max; + int action; + int error; + int i; trace_xfs_da_split(state->args); @@ -281,7 +435,7 @@ xfs_da_split(xfs_da_state_t *state) addblk = newblk; break; case XFS_DA_NODE_MAGIC: - error = xfs_da_node_split(state, oldblk, newblk, addblk, + error = xfs_da3_node_split(state, oldblk, newblk, addblk, max - i, &action); addblk->bp = NULL; if (error) @@ -299,7 +453,7 @@ xfs_da_split(xfs_da_state_t *state) /* * Update the btree to show the new hashval for this child. */ - xfs_da_fixhashpath(state, &state->path); + xfs_da3_fixhashpath(state, &state->path); } if (!addblk) return(0); @@ -309,7 +463,7 @@ xfs_da_split(xfs_da_state_t *state) */ ASSERT(state->path.active == 0); oldblk = &state->path.blk[0]; - error = xfs_da_root_split(state, oldblk, addblk); + error = xfs_da3_root_split(state, oldblk, addblk); if (error) { addblk->bp = NULL; return(error); /* GROT: dir is inconsistent */ @@ -320,8 +474,10 @@ xfs_da_split(xfs_da_state_t *state) * just got bumped because of the addition of a new root node. * There might be three blocks involved if a double split occurred, * and the original block 0 could be at any position in the list. + * + * Note: the info structures being modified here for both v2 and v3 da + * headers, so we can do this linkage just using the v2 structures. */ - node = oldblk->bp->b_addr; if (node->hdr.info.forw) { if (be32_to_cpu(node->hdr.info.forw) == addblk->blkno) { @@ -360,18 +516,25 @@ xfs_da_split(xfs_da_state_t *state) * the EOF, extending the inode in process. */ STATIC int /* error */ -xfs_da_root_split(xfs_da_state_t *state, xfs_da_state_blk_t *blk1, - xfs_da_state_blk_t *blk2) +xfs_da3_root_split( + struct xfs_da_state *state, + struct xfs_da_state_blk *blk1, + struct xfs_da_state_blk *blk2) { - xfs_da_intnode_t *node, *oldroot; - xfs_da_args_t *args; - xfs_dablk_t blkno; - struct xfs_buf *bp; - int error, size; - xfs_inode_t *dp; - xfs_trans_t *tp; - xfs_mount_t *mp; - xfs_dir2_leaf_t *leaf; + struct xfs_da_intnode *node; + struct xfs_da_intnode *oldroot; + struct xfs_da_node_entry *btree; + struct xfs_da3_icnode_hdr nodehdr; + struct xfs_da_args *args; + struct xfs_buf *bp; + struct xfs_inode *dp; + struct xfs_trans *tp; + struct xfs_mount *mp; + struct xfs_dir2_leaf *leaf; + xfs_dablk_t blkno; + int level; + int error; + int size; trace_xfs_da_root_split(state->args); @@ -380,22 +543,26 @@ xfs_da_root_split(xfs_da_state_t *state, xfs_da_state_blk_t *blk1, * to a free space somewhere. */ args = state->args; - ASSERT(args != NULL); error = xfs_da_grow_inode(args, &blkno); if (error) - return(error); + return error; + dp = args->dp; tp = args->trans; mp = state->mp; error = xfs_da_get_buf(tp, dp, blkno, -1, &bp, args->whichfork); if (error) - return(error); - ASSERT(bp != NULL); + return error; node = bp->b_addr; oldroot = blk1->bp->b_addr; - if (oldroot->hdr.info.magic == cpu_to_be16(XFS_DA_NODE_MAGIC)) { - size = (int)((char *)&oldroot->btree[be16_to_cpu(oldroot->hdr.count)] - - (char *)oldroot); + if (oldroot->hdr.info.magic == cpu_to_be16(XFS_DA_NODE_MAGIC) || + oldroot->hdr.info.magic == cpu_to_be16(XFS_DA3_NODE_MAGIC)) { + struct xfs_da3_icnode_hdr nodehdr; + + xfs_da3_node_hdr_from_disk(&nodehdr, oldroot); + btree = xfs_da3_node_tree_p(oldroot); + size = (int)((char *)&btree[nodehdr.count] - (char *)oldroot); + level = nodehdr.level; } else { struct xfs_dir3_icleaf_hdr leafhdr; struct xfs_dir2_leaf_entry *ents; @@ -407,9 +574,22 @@ xfs_da_root_split(xfs_da_state_t *state, xfs_da_state_blk_t *blk1, ASSERT(leafhdr.magic == XFS_DIR2_LEAFN_MAGIC || leafhdr.magic == XFS_DIR3_LEAFN_MAGIC); size = (int)((char *)&ents[leafhdr.count] - (char *)leaf); + level = 0; } - /* XXX: can't just copy CRC headers from one block to another */ + + /* + * we can copy most of the information in the node from one block to + * another, but for CRC enabled headers we have to make sure that the + * block specific identifiers are kept intact. We update the buffer + * directly for this. + */ memcpy(node, oldroot, size); + if (oldroot->hdr.info.magic == cpu_to_be16(XFS_DA3_NODE_MAGIC) || + oldroot->hdr.info.magic == cpu_to_be16(XFS_DIR3_LEAFN_MAGIC)) { + struct xfs_da3_intnode *node3 = (struct xfs_da3_intnode *)node; + + node3->hdr.info.blkno = cpu_to_be64(bp->b_bn); + } xfs_trans_log_buf(tp, bp, 0, size - 1); bp->b_ops = blk1->bp->b_ops; @@ -419,17 +599,21 @@ xfs_da_root_split(xfs_da_state_t *state, xfs_da_state_blk_t *blk1, /* * Set up the new root node. */ - error = xfs_da_node_create(args, + error = xfs_da3_node_create(args, (args->whichfork == XFS_DATA_FORK) ? mp->m_dirleafblk : 0, - be16_to_cpu(node->hdr.level) + 1, &bp, args->whichfork); + level + 1, &bp, args->whichfork); if (error) - return(error); + return error; + node = bp->b_addr; - node->btree[0].hashval = cpu_to_be32(blk1->hashval); - node->btree[0].before = cpu_to_be32(blk1->blkno); - node->btree[1].hashval = cpu_to_be32(blk2->hashval); - node->btree[1].before = cpu_to_be32(blk2->blkno); - node->hdr.count = cpu_to_be16(2); + xfs_da3_node_hdr_from_disk(&nodehdr, node); + btree = xfs_da3_node_tree_p(node); + btree[0].hashval = cpu_to_be32(blk1->hashval); + btree[0].before = cpu_to_be32(blk1->blkno); + btree[1].hashval = cpu_to_be32(blk2->hashval); + btree[1].before = cpu_to_be32(blk2->blkno); + nodehdr.count = 2; + xfs_da3_node_hdr_to_disk(node, &nodehdr); #ifdef DEBUG if (oldroot->hdr.info.magic == cpu_to_be16(XFS_DIR2_LEAFN_MAGIC) || @@ -443,30 +627,34 @@ xfs_da_root_split(xfs_da_state_t *state, xfs_da_state_blk_t *blk1, /* Header is already logged by xfs_da_node_create */ xfs_trans_log_buf(tp, bp, - XFS_DA_LOGRANGE(node, node->btree, - sizeof(xfs_da_node_entry_t) * 2)); + XFS_DA_LOGRANGE(node, btree, sizeof(xfs_da_node_entry_t) * 2)); - return(0); + return 0; } /* * Split the node, rebalance, then add the new entry. */ STATIC int /* error */ -xfs_da_node_split(xfs_da_state_t *state, xfs_da_state_blk_t *oldblk, - xfs_da_state_blk_t *newblk, - xfs_da_state_blk_t *addblk, - int treelevel, int *result) +xfs_da3_node_split( + struct xfs_da_state *state, + struct xfs_da_state_blk *oldblk, + struct xfs_da_state_blk *newblk, + struct xfs_da_state_blk *addblk, + int treelevel, + int *result) { - xfs_da_intnode_t *node; - xfs_dablk_t blkno; - int newcount, error; - int useextra; + struct xfs_da_intnode *node; + struct xfs_da3_icnode_hdr nodehdr; + xfs_dablk_t blkno; + int newcount; + int error; + int useextra; trace_xfs_da_node_split(state->args); node = oldblk->bp->b_addr; - ASSERT(node->hdr.info.magic == cpu_to_be16(XFS_DA_NODE_MAGIC)); + xfs_da3_node_hdr_from_disk(&nodehdr, node); /* * With V2 dirs the extra block is data or freespace. @@ -476,7 +664,7 @@ xfs_da_node_split(xfs_da_state_t *state, xfs_da_state_blk_t *oldblk, /* * Do we have to split the node? */ - if ((be16_to_cpu(node->hdr.count) + newcount) > state->node_ents) { + if (nodehdr.count + newcount > state->node_ents) { /* * Allocate a new node, add to the doubly linked chain of * nodes, then move some of our excess entries into it. @@ -485,14 +673,14 @@ xfs_da_node_split(xfs_da_state_t *state, xfs_da_state_blk_t *oldblk, if (error) return(error); /* GROT: dir is inconsistent */ - error = xfs_da_node_create(state->args, blkno, treelevel, + error = xfs_da3_node_create(state->args, blkno, treelevel, &newblk->bp, state->args->whichfork); if (error) return(error); /* GROT: dir is inconsistent */ newblk->blkno = blkno; newblk->magic = XFS_DA_NODE_MAGIC; - xfs_da_node_rebalance(state, oldblk, newblk); - error = xfs_da_blk_link(state, oldblk, newblk); + xfs_da3_node_rebalance(state, oldblk, newblk); + error = xfs_da3_blk_link(state, oldblk, newblk); if (error) return(error); *result = 1; @@ -504,7 +692,7 @@ xfs_da_node_split(xfs_da_state_t *state, xfs_da_state_blk_t *oldblk, * Insert the new entry(s) into the correct block * (updating last hashval in the process). * - * xfs_da_node_add() inserts BEFORE the given index, + * xfs_da3_node_add() inserts BEFORE the given index, * and as a result of using node_lookup_int() we always * point to a valid entry (not after one), but a split * operation always results in a new block whose hashvals @@ -513,22 +701,23 @@ xfs_da_node_split(xfs_da_state_t *state, xfs_da_state_blk_t *oldblk, * If we had double-split op below us, then add the extra block too. */ node = oldblk->bp->b_addr; - if (oldblk->index <= be16_to_cpu(node->hdr.count)) { + xfs_da3_node_hdr_from_disk(&nodehdr, node); + if (oldblk->index <= nodehdr.count) { oldblk->index++; - xfs_da_node_add(state, oldblk, addblk); + xfs_da3_node_add(state, oldblk, addblk); if (useextra) { if (state->extraafter) oldblk->index++; - xfs_da_node_add(state, oldblk, &state->extrablk); + xfs_da3_node_add(state, oldblk, &state->extrablk); state->extravalid = 0; } } else { newblk->index++; - xfs_da_node_add(state, newblk, addblk); + xfs_da3_node_add(state, newblk, addblk); if (useextra) { if (state->extraafter) newblk->index++; - xfs_da_node_add(state, newblk, &state->extrablk); + xfs_da3_node_add(state, newblk, &state->extrablk); state->extravalid = 0; } } @@ -543,33 +732,53 @@ xfs_da_node_split(xfs_da_state_t *state, xfs_da_state_blk_t *oldblk, * NOTE: if blk2 is empty, then it will get the upper half of blk1. */ STATIC void -xfs_da_node_rebalance(xfs_da_state_t *state, xfs_da_state_blk_t *blk1, - xfs_da_state_blk_t *blk2) +xfs_da3_node_rebalance( + struct xfs_da_state *state, + struct xfs_da_state_blk *blk1, + struct xfs_da_state_blk *blk2) { - xfs_da_intnode_t *node1, *node2, *tmpnode; - xfs_da_node_entry_t *btree_s, *btree_d; - int count, tmp; - xfs_trans_t *tp; + struct xfs_da_intnode *node1; + struct xfs_da_intnode *node2; + struct xfs_da_intnode *tmpnode; + struct xfs_da_node_entry *btree1; + struct xfs_da_node_entry *btree2; + struct xfs_da_node_entry *btree_s; + struct xfs_da_node_entry *btree_d; + struct xfs_da3_icnode_hdr nodehdr1; + struct xfs_da3_icnode_hdr nodehdr2; + struct xfs_trans *tp; + int count; + int tmp; + int swap = 0; trace_xfs_da_node_rebalance(state->args); node1 = blk1->bp->b_addr; node2 = blk2->bp->b_addr; + xfs_da3_node_hdr_from_disk(&nodehdr1, node1); + xfs_da3_node_hdr_from_disk(&nodehdr2, node2); + btree1 = xfs_da3_node_tree_p(node1); + btree2 = xfs_da3_node_tree_p(node2); + /* * Figure out how many entries need to move, and in which direction. * Swap the nodes around if that makes it simpler. */ - if ((be16_to_cpu(node1->hdr.count) > 0) && (be16_to_cpu(node2->hdr.count) > 0) && - ((be32_to_cpu(node2->btree[0].hashval) < be32_to_cpu(node1->btree[0].hashval)) || - (be32_to_cpu(node2->btree[be16_to_cpu(node2->hdr.count)-1].hashval) < - be32_to_cpu(node1->btree[be16_to_cpu(node1->hdr.count)-1].hashval)))) { + if (nodehdr1.count > 0 && nodehdr2.count > 0 && + ((be32_to_cpu(btree2[0].hashval) < be32_to_cpu(btree1[0].hashval)) || + (be32_to_cpu(btree2[nodehdr2.count - 1].hashval) < + be32_to_cpu(btree1[nodehdr1.count - 1].hashval)))) { tmpnode = node1; node1 = node2; node2 = tmpnode; + xfs_da3_node_hdr_from_disk(&nodehdr1, node1); + xfs_da3_node_hdr_from_disk(&nodehdr2, node2); + btree1 = xfs_da3_node_tree_p(node1); + btree2 = xfs_da3_node_tree_p(node2); + swap = 1; } - ASSERT(node1->hdr.info.magic == cpu_to_be16(XFS_DA_NODE_MAGIC)); - ASSERT(node2->hdr.info.magic == cpu_to_be16(XFS_DA_NODE_MAGIC)); - count = (be16_to_cpu(node1->hdr.count) - be16_to_cpu(node2->hdr.count)) / 2; + + count = (nodehdr1.count - nodehdr2.count) / 2; if (count == 0) return; tp = state->args->trans; @@ -580,10 +789,11 @@ xfs_da_node_rebalance(xfs_da_state_t *state, xfs_da_state_blk_t *blk1, /* * Move elements in node2 up to make a hole. */ - if ((tmp = be16_to_cpu(node2->hdr.count)) > 0) { + tmp = nodehdr2.count; + if (tmp > 0) { tmp *= (uint)sizeof(xfs_da_node_entry_t); - btree_s = &node2->btree[0]; - btree_d = &node2->btree[count]; + btree_s = &btree2[0]; + btree_d = &btree2[count]; memmove(btree_d, btree_s, tmp); } @@ -591,12 +801,12 @@ xfs_da_node_rebalance(xfs_da_state_t *state, xfs_da_state_blk_t *blk1, * Move the req'd B-tree elements from high in node1 to * low in node2. */ - be16_add_cpu(&node2->hdr.count, count); + nodehdr2.count += count; tmp = count * (uint)sizeof(xfs_da_node_entry_t); - btree_s = &node1->btree[be16_to_cpu(node1->hdr.count) - count]; - btree_d = &node2->btree[0]; + btree_s = &btree1[nodehdr1.count- count]; + btree_d = &btree2[0]; memcpy(btree_d, btree_s, tmp); - be16_add_cpu(&node1->hdr.count, -count); + nodehdr1.count -= count; } else { /* * Move the req'd B-tree elements from low in node2 to @@ -604,49 +814,60 @@ xfs_da_node_rebalance(xfs_da_state_t *state, xfs_da_state_blk_t *blk1, */ count = -count; tmp = count * (uint)sizeof(xfs_da_node_entry_t); - btree_s = &node2->btree[0]; - btree_d = &node1->btree[be16_to_cpu(node1->hdr.count)]; + btree_s = &btree2[0]; + btree_d = &btree1[nodehdr1.count]; memcpy(btree_d, btree_s, tmp); - be16_add_cpu(&node1->hdr.count, count); + nodehdr1.count += count; + xfs_trans_log_buf(tp, blk1->bp, XFS_DA_LOGRANGE(node1, btree_d, tmp)); /* * Move elements in node2 down to fill the hole. */ - tmp = be16_to_cpu(node2->hdr.count) - count; + tmp = nodehdr2.count - count; tmp *= (uint)sizeof(xfs_da_node_entry_t); - btree_s = &node2->btree[count]; - btree_d = &node2->btree[0]; + btree_s = &btree2[count]; + btree_d = &btree2[0]; memmove(btree_d, btree_s, tmp); - be16_add_cpu(&node2->hdr.count, -count); + nodehdr2.count -= count; } /* * Log header of node 1 and all current bits of node 2. */ + xfs_da3_node_hdr_to_disk(node1, &nodehdr1); xfs_trans_log_buf(tp, blk1->bp, - XFS_DA_LOGRANGE(node1, &node1->hdr, sizeof(node1->hdr))); + XFS_DA_LOGRANGE(node1, &node1->hdr, + xfs_da3_node_hdr_size(node1))); + + xfs_da3_node_hdr_to_disk(node2, &nodehdr2); xfs_trans_log_buf(tp, blk2->bp, XFS_DA_LOGRANGE(node2, &node2->hdr, - sizeof(node2->hdr) + - sizeof(node2->btree[0]) * be16_to_cpu(node2->hdr.count))); + xfs_da3_node_hdr_size(node2) + + (sizeof(btree2[0]) * nodehdr2.count))); /* * Record the last hashval from each block for upward propagation. * (note: don't use the swapped node pointers) */ - node1 = blk1->bp->b_addr; - node2 = blk2->bp->b_addr; - blk1->hashval = be32_to_cpu(node1->btree[be16_to_cpu(node1->hdr.count)-1].hashval); - blk2->hashval = be32_to_cpu(node2->btree[be16_to_cpu(node2->hdr.count)-1].hashval); + if (swap) { + node1 = blk1->bp->b_addr; + node2 = blk2->bp->b_addr; + xfs_da3_node_hdr_from_disk(&nodehdr1, node1); + xfs_da3_node_hdr_from_disk(&nodehdr2, node2); + btree1 = xfs_da3_node_tree_p(node1); + btree2 = xfs_da3_node_tree_p(node2); + } + blk1->hashval = be32_to_cpu(btree1[nodehdr1.count - 1].hashval); + blk2->hashval = be32_to_cpu(btree2[nodehdr2.count - 1].hashval); /* * Adjust the expected index for insertion. */ - if (blk1->index >= be16_to_cpu(node1->hdr.count)) { - blk2->index = blk1->index - be16_to_cpu(node1->hdr.count); - blk1->index = be16_to_cpu(node1->hdr.count) + 1; /* make it invalid */ + if (blk1->index >= nodehdr1.count) { + blk2->index = blk1->index - nodehdr1.count; + blk1->index = nodehdr1.count + 1; /* make it invalid */ } } @@ -654,18 +875,23 @@ xfs_da_node_rebalance(xfs_da_state_t *state, xfs_da_state_blk_t *blk1, * Add a new entry to an intermediate node. */ STATIC void -xfs_da_node_add(xfs_da_state_t *state, xfs_da_state_blk_t *oldblk, - xfs_da_state_blk_t *newblk) +xfs_da3_node_add( + struct xfs_da_state *state, + struct xfs_da_state_blk *oldblk, + struct xfs_da_state_blk *newblk) { - xfs_da_intnode_t *node; - xfs_da_node_entry_t *btree; - int tmp; + struct xfs_da_intnode *node; + struct xfs_da3_icnode_hdr nodehdr; + struct xfs_da_node_entry *btree; + int tmp; trace_xfs_da_node_add(state->args); node = oldblk->bp->b_addr; - ASSERT(node->hdr.info.magic == cpu_to_be16(XFS_DA_NODE_MAGIC)); - ASSERT((oldblk->index >= 0) && (oldblk->index <= be16_to_cpu(node->hdr.count))); + xfs_da3_node_hdr_from_disk(&nodehdr, node); + btree = xfs_da3_node_tree_p(node); + + ASSERT(oldblk->index >= 0 && oldblk->index <= nodehdr.count); ASSERT(newblk->blkno != 0); if (state->args->whichfork == XFS_DATA_FORK) ASSERT(newblk->blkno >= state->mp->m_dirleafblk && @@ -675,23 +901,25 @@ xfs_da_node_add(xfs_da_state_t *state, xfs_da_state_blk_t *oldblk, * We may need to make some room before we insert the new node. */ tmp = 0; - btree = &node->btree[ oldblk->index ]; - if (oldblk->index < be16_to_cpu(node->hdr.count)) { - tmp = (be16_to_cpu(node->hdr.count) - oldblk->index) * (uint)sizeof(*btree); - memmove(btree + 1, btree, tmp); + if (oldblk->index < nodehdr.count) { + tmp = (nodehdr.count - oldblk->index) * (uint)sizeof(*btree); + memmove(&btree[oldblk->index + 1], &btree[oldblk->index], tmp); } - btree->hashval = cpu_to_be32(newblk->hashval); - btree->before = cpu_to_be32(newblk->blkno); + btree[oldblk->index].hashval = cpu_to_be32(newblk->hashval); + btree[oldblk->index].before = cpu_to_be32(newblk->blkno); xfs_trans_log_buf(state->args->trans, oldblk->bp, - XFS_DA_LOGRANGE(node, btree, tmp + sizeof(*btree))); - be16_add_cpu(&node->hdr.count, 1); + XFS_DA_LOGRANGE(node, &btree[oldblk->index], + tmp + sizeof(*btree))); + + nodehdr.count += 1; + xfs_da3_node_hdr_to_disk(node, &nodehdr); xfs_trans_log_buf(state->args->trans, oldblk->bp, - XFS_DA_LOGRANGE(node, &node->hdr, sizeof(node->hdr))); + XFS_DA_LOGRANGE(node, &node->hdr, xfs_da3_node_hdr_size(node))); /* * Copy the last hash value from the oldblk to propagate upwards. */ - oldblk->hashval = be32_to_cpu(node->btree[be16_to_cpu(node->hdr.count)-1 ].hashval); + oldblk->hashval = be32_to_cpu(btree[nodehdr.count - 1].hashval); } /*======================================================================== @@ -703,14 +931,16 @@ xfs_da_node_add(xfs_da_state_t *state, xfs_da_state_blk_t *oldblk, * possibly deallocating that block, etc... */ int -xfs_da_join(xfs_da_state_t *state) +xfs_da3_join( + struct xfs_da_state *state) { - xfs_da_state_blk_t *drop_blk, *save_blk; - int action, error; + struct xfs_da_state_blk *drop_blk; + struct xfs_da_state_blk *save_blk; + int action = 0; + int error; trace_xfs_da_join(state->args); - action = 0; drop_blk = &state->path.blk[ state->path.active-1 ]; save_blk = &state->altpath.blk[ state->path.active-1 ]; ASSERT(state->path.blk[0].magic == XFS_DA_NODE_MAGIC); @@ -751,18 +981,18 @@ xfs_da_join(xfs_da_state_t *state) * Remove the offending node, fixup hashvals, * check for a toosmall neighbor. */ - xfs_da_node_remove(state, drop_blk); - xfs_da_fixhashpath(state, &state->path); - error = xfs_da_node_toosmall(state, &action); + xfs_da3_node_remove(state, drop_blk); + xfs_da3_fixhashpath(state, &state->path); + error = xfs_da3_node_toosmall(state, &action); if (error) return(error); if (action == 0) return 0; - xfs_da_node_unbalance(state, drop_blk, save_blk); + xfs_da3_node_unbalance(state, drop_blk, save_blk); break; } - xfs_da_fixhashpath(state, &state->altpath); - error = xfs_da_blk_unlink(state, drop_blk, save_blk); + xfs_da3_fixhashpath(state, &state->altpath); + error = xfs_da3_blk_unlink(state, drop_blk, save_blk); xfs_da_state_kill_altpath(state); if (error) return(error); @@ -777,9 +1007,9 @@ xfs_da_join(xfs_da_state_t *state) * we only have one entry in the root, make the child block * the new root. */ - xfs_da_node_remove(state, drop_blk); - xfs_da_fixhashpath(state, &state->path); - error = xfs_da_root_join(state, &state->path.blk[0]); + xfs_da3_node_remove(state, drop_blk); + xfs_da3_fixhashpath(state, &state->path); + error = xfs_da3_root_join(state, &state->path.blk[0]); return(error); } @@ -793,8 +1023,10 @@ xfs_da_blkinfo_onlychild_validate(struct xfs_da_blkinfo *blkinfo, __u16 level) ASSERT(magic == cpu_to_be16(XFS_DIR2_LEAFN_MAGIC) || magic == cpu_to_be16(XFS_DIR3_LEAFN_MAGIC) || magic == cpu_to_be16(XFS_ATTR_LEAF_MAGIC)); - } else - ASSERT(magic == cpu_to_be16(XFS_DA_NODE_MAGIC)); + } else { + ASSERT(magic == cpu_to_be16(XFS_DA_NODE_MAGIC) || + magic == cpu_to_be16(XFS_DA3_NODE_MAGIC)); + } ASSERT(!blkinfo->forw); ASSERT(!blkinfo->back); } @@ -807,52 +1039,60 @@ xfs_da_blkinfo_onlychild_validate(struct xfs_da_blkinfo *blkinfo, __u16 level) * the old root to block 0 as the new root node. */ STATIC int -xfs_da_root_join(xfs_da_state_t *state, xfs_da_state_blk_t *root_blk) +xfs_da3_root_join( + struct xfs_da_state *state, + struct xfs_da_state_blk *root_blk) { - xfs_da_intnode_t *oldroot; - xfs_da_args_t *args; - xfs_dablk_t child; - struct xfs_buf *bp; - int error; + struct xfs_da_intnode *oldroot; + struct xfs_da_args *args; + xfs_dablk_t child; + struct xfs_buf *bp; + struct xfs_da3_icnode_hdr oldroothdr; + struct xfs_da_node_entry *btree; + int error; trace_xfs_da_root_join(state->args); - args = state->args; - ASSERT(args != NULL); ASSERT(root_blk->magic == XFS_DA_NODE_MAGIC); + + args = state->args; oldroot = root_blk->bp->b_addr; - ASSERT(oldroot->hdr.info.magic == cpu_to_be16(XFS_DA_NODE_MAGIC)); - ASSERT(!oldroot->hdr.info.forw); - ASSERT(!oldroot->hdr.info.back); + xfs_da3_node_hdr_from_disk(&oldroothdr, oldroot); + ASSERT(oldroothdr.forw == 0); + ASSERT(oldroothdr.back == 0); /* * If the root has more than one child, then don't do anything. */ - if (be16_to_cpu(oldroot->hdr.count) > 1) - return(0); + if (oldroothdr.count > 1) + return 0; /* * Read in the (only) child block, then copy those bytes into * the root block's buffer and free the original child block. */ - child = be32_to_cpu(oldroot->btree[0].before); + btree = xfs_da3_node_tree_p(oldroot); + child = be32_to_cpu(btree[0].before); ASSERT(child != 0); - error = xfs_da_node_read(args->trans, args->dp, child, -1, &bp, + error = xfs_da3_node_read(args->trans, args->dp, child, -1, &bp, args->whichfork); if (error) - return(error); - ASSERT(bp != NULL); - xfs_da_blkinfo_onlychild_validate(bp->b_addr, - be16_to_cpu(oldroot->hdr.level)); + return error; + xfs_da_blkinfo_onlychild_validate(bp->b_addr, oldroothdr.level); /* * This could be copying a leaf back into the root block in the case of * there only being a single leaf block left in the tree. Hence we have * to update the b_ops pointer as well to match the buffer type change - * that could occur. + * that could occur. For dir3 blocks we also need to update the block + * number in the buffer header. */ memcpy(root_blk->bp->b_addr, bp->b_addr, state->blocksize); root_blk->bp->b_ops = bp->b_ops; + if (oldroothdr.magic == XFS_DA3_NODE_MAGIC) { + struct xfs_da3_blkinfo *da3 = root_blk->bp->b_addr; + da3->blkno = cpu_to_be64(root_blk->bp->b_bn); + } xfs_trans_log_buf(args->trans, root_blk->bp, 0, state->blocksize - 1); error = xfs_da_shrink_inode(args, child, bp); return(error); @@ -868,14 +1108,21 @@ xfs_da_root_join(xfs_da_state_t *state, xfs_da_state_blk_t *root_blk) * If nothing can be done, return 0. */ STATIC int -xfs_da_node_toosmall(xfs_da_state_t *state, int *action) +xfs_da3_node_toosmall( + struct xfs_da_state *state, + int *action) { - xfs_da_intnode_t *node; - xfs_da_state_blk_t *blk; - xfs_da_blkinfo_t *info; - int count, forward, error, retval, i; - xfs_dablk_t blkno; - struct xfs_buf *bp; + struct xfs_da_intnode *node; + struct xfs_da_state_blk *blk; + struct xfs_da_blkinfo *info; + xfs_dablk_t blkno; + struct xfs_buf *bp; + struct xfs_da3_icnode_hdr nodehdr; + int count; + int forward; + int error; + int retval; + int i; trace_xfs_da_node_toosmall(state->args); @@ -886,10 +1133,9 @@ xfs_da_node_toosmall(xfs_da_state_t *state, int *action) */ blk = &state->path.blk[ state->path.active-1 ]; info = blk->bp->b_addr; - ASSERT(info->magic == cpu_to_be16(XFS_DA_NODE_MAGIC)); node = (xfs_da_intnode_t *)info; - count = be16_to_cpu(node->hdr.count); - if (count > (state->node_ents >> 1)) { + xfs_da3_node_hdr_from_disk(&nodehdr, node); + if (nodehdr.count > (state->node_ents >> 1)) { *action = 0; /* blk over 50%, don't try to join */ return(0); /* blk over 50%, don't try to join */ } @@ -900,14 +1146,14 @@ xfs_da_node_toosmall(xfs_da_state_t *state, int *action) * coalesce it with a sibling block. We choose (arbitrarily) * to merge with the forward block unless it is NULL. */ - if (count == 0) { + if (nodehdr.count == 0) { /* * Make altpath point to the block we want to keep and * path point to the block we want to drop (this one). */ forward = (info->forw != 0); memcpy(&state->altpath, &state->path, sizeof(state->path)); - error = xfs_da_path_shift(state, &state->altpath, forward, + error = xfs_da3_path_shift(state, &state->altpath, forward, 0, &retval); if (error) return(error); @@ -926,35 +1172,34 @@ xfs_da_node_toosmall(xfs_da_state_t *state, int *action) * We prefer coalescing with the lower numbered sibling so as * to shrink a directory over time. */ + count = state->node_ents; + count -= state->node_ents >> 2; + count -= nodehdr.count; + /* start with smaller blk num */ - forward = (be32_to_cpu(info->forw) < be32_to_cpu(info->back)); + forward = nodehdr.forw < nodehdr.back; for (i = 0; i < 2; forward = !forward, i++) { if (forward) - blkno = be32_to_cpu(info->forw); + blkno = nodehdr.forw; else - blkno = be32_to_cpu(info->back); + blkno = nodehdr.back; if (blkno == 0) continue; - error = xfs_da_node_read(state->args->trans, state->args->dp, + error = xfs_da3_node_read(state->args->trans, state->args->dp, blkno, -1, &bp, state->args->whichfork); if (error) return(error); - ASSERT(bp != NULL); - node = (xfs_da_intnode_t *)info; - count = state->node_ents; - count -= state->node_ents >> 2; - count -= be16_to_cpu(node->hdr.count); node = bp->b_addr; - ASSERT(node->hdr.info.magic == cpu_to_be16(XFS_DA_NODE_MAGIC)); - count -= be16_to_cpu(node->hdr.count); + xfs_da3_node_hdr_from_disk(&nodehdr, node); xfs_trans_brelse(state->args->trans, bp); - if (count >= 0) + + if (count - nodehdr.count >= 0) break; /* fits with at least 25% to spare */ } if (i >= 2) { *action = 0; - return(0); + return 0; } /* @@ -963,28 +1208,42 @@ xfs_da_node_toosmall(xfs_da_state_t *state, int *action) */ memcpy(&state->altpath, &state->path, sizeof(state->path)); if (blkno < blk->blkno) { - error = xfs_da_path_shift(state, &state->altpath, forward, + error = xfs_da3_path_shift(state, &state->altpath, forward, 0, &retval); - if (error) { - return(error); - } - if (retval) { - *action = 0; - return(0); - } } else { - error = xfs_da_path_shift(state, &state->path, forward, + error = xfs_da3_path_shift(state, &state->path, forward, 0, &retval); - if (error) { - return(error); - } - if (retval) { - *action = 0; - return(0); - } + } + if (error) + return error; + if (retval) { + *action = 0; + return 0; } *action = 1; - return(0); + return 0; +} + +/* + * Pick up the last hashvalue from an intermediate node. + */ +STATIC uint +xfs_da3_node_lasthash( + struct xfs_buf *bp, + int *count) +{ + struct xfs_da_intnode *node; + struct xfs_da_node_entry *btree; + struct xfs_da3_icnode_hdr nodehdr; + + node = bp->b_addr; + xfs_da3_node_hdr_from_disk(&nodehdr, node); + if (count) + *count = nodehdr.count; + if (!nodehdr.count) + return 0; + btree = xfs_da3_node_tree_p(node); + return be32_to_cpu(btree[nodehdr.count - 1].hashval); } /* @@ -992,13 +1251,16 @@ xfs_da_node_toosmall(xfs_da_state_t *state, int *action) * when we stop making changes, return. */ void -xfs_da_fixhashpath(xfs_da_state_t *state, xfs_da_state_path_t *path) +xfs_da3_fixhashpath( + struct xfs_da_state *state, + struct xfs_da_state_path *path) { - xfs_da_state_blk_t *blk; - xfs_da_intnode_t *node; - xfs_da_node_entry_t *btree; - xfs_dahash_t lasthash=0; - int level, count; + struct xfs_da_state_blk *blk; + struct xfs_da_intnode *node; + struct xfs_da_node_entry *btree; + xfs_dahash_t lasthash=0; + int level; + int count; trace_xfs_da_fixhashpath(state->args); @@ -1016,23 +1278,26 @@ xfs_da_fixhashpath(xfs_da_state_t *state, xfs_da_state_path_t *path) return; break; case XFS_DA_NODE_MAGIC: - lasthash = xfs_da_node_lasthash(blk->bp, &count); + lasthash = xfs_da3_node_lasthash(blk->bp, &count); if (count == 0) return; break; } for (blk--, level--; level >= 0; blk--, level--) { + struct xfs_da3_icnode_hdr nodehdr; + node = blk->bp->b_addr; - ASSERT(node->hdr.info.magic == cpu_to_be16(XFS_DA_NODE_MAGIC)); - btree = &node->btree[ blk->index ]; + xfs_da3_node_hdr_from_disk(&nodehdr, node); + btree = xfs_da3_node_tree_p(node); if (be32_to_cpu(btree->hashval) == lasthash) break; blk->hashval = lasthash; - btree->hashval = cpu_to_be32(lasthash); + btree[blk->index].hashval = cpu_to_be32(lasthash); xfs_trans_log_buf(state->args->trans, blk->bp, - XFS_DA_LOGRANGE(node, btree, sizeof(*btree))); + XFS_DA_LOGRANGE(node, &btree[blk->index], + sizeof(*btree))); - lasthash = be32_to_cpu(node->btree[be16_to_cpu(node->hdr.count)-1].hashval); + lasthash = be32_to_cpu(btree[nodehdr.count - 1].hashval); } } @@ -1040,104 +1305,119 @@ xfs_da_fixhashpath(xfs_da_state_t *state, xfs_da_state_path_t *path) * Remove an entry from an intermediate node. */ STATIC void -xfs_da_node_remove(xfs_da_state_t *state, xfs_da_state_blk_t *drop_blk) +xfs_da3_node_remove( + struct xfs_da_state *state, + struct xfs_da_state_blk *drop_blk) { - xfs_da_intnode_t *node; - xfs_da_node_entry_t *btree; - int tmp; + struct xfs_da_intnode *node; + struct xfs_da3_icnode_hdr nodehdr; + struct xfs_da_node_entry *btree; + int index; + int tmp; trace_xfs_da_node_remove(state->args); node = drop_blk->bp->b_addr; - ASSERT(drop_blk->index < be16_to_cpu(node->hdr.count)); + xfs_da3_node_hdr_from_disk(&nodehdr, node); + ASSERT(drop_blk->index < nodehdr.count); ASSERT(drop_blk->index >= 0); /* * Copy over the offending entry, or just zero it out. */ - btree = &node->btree[drop_blk->index]; - if (drop_blk->index < (be16_to_cpu(node->hdr.count)-1)) { - tmp = be16_to_cpu(node->hdr.count) - drop_blk->index - 1; + index = drop_blk->index; + btree = xfs_da3_node_tree_p(node); + if (index < nodehdr.count - 1) { + tmp = nodehdr.count - index - 1; tmp *= (uint)sizeof(xfs_da_node_entry_t); - memmove(btree, btree + 1, tmp); + memmove(&btree[index], &btree[index + 1], tmp); xfs_trans_log_buf(state->args->trans, drop_blk->bp, - XFS_DA_LOGRANGE(node, btree, tmp)); - btree = &node->btree[be16_to_cpu(node->hdr.count)-1]; + XFS_DA_LOGRANGE(node, &btree[index], tmp)); + index = nodehdr.count - 1; } - memset((char *)btree, 0, sizeof(xfs_da_node_entry_t)); + memset(&btree[index], 0, sizeof(xfs_da_node_entry_t)); xfs_trans_log_buf(state->args->trans, drop_blk->bp, - XFS_DA_LOGRANGE(node, btree, sizeof(*btree))); - be16_add_cpu(&node->hdr.count, -1); + XFS_DA_LOGRANGE(node, &btree[index], sizeof(btree[index]))); + nodehdr.count -= 1; + xfs_da3_node_hdr_to_disk(node, &nodehdr); xfs_trans_log_buf(state->args->trans, drop_blk->bp, - XFS_DA_LOGRANGE(node, &node->hdr, sizeof(node->hdr))); + XFS_DA_LOGRANGE(node, &node->hdr, xfs_da3_node_hdr_size(node))); /* * Copy the last hash value from the block to propagate upwards. */ - btree--; - drop_blk->hashval = be32_to_cpu(btree->hashval); + drop_blk->hashval = be32_to_cpu(btree[index - 1].hashval); } /* - * Unbalance the btree elements between two intermediate nodes, + * Unbalance the elements between two intermediate nodes, * move all Btree elements from one node into another. */ STATIC void -xfs_da_node_unbalance(xfs_da_state_t *state, xfs_da_state_blk_t *drop_blk, - xfs_da_state_blk_t *save_blk) +xfs_da3_node_unbalance( + struct xfs_da_state *state, + struct xfs_da_state_blk *drop_blk, + struct xfs_da_state_blk *save_blk) { - xfs_da_intnode_t *drop_node, *save_node; - xfs_da_node_entry_t *btree; - int tmp; - xfs_trans_t *tp; + struct xfs_da_intnode *drop_node; + struct xfs_da_intnode *save_node; + struct xfs_da_node_entry *dbtree; + struct xfs_da_node_entry *sbtree; + struct xfs_da3_icnode_hdr dhdr; + struct xfs_da3_icnode_hdr shdr; + struct xfs_trans *tp; + int sindex; + int tmp; trace_xfs_da_node_unbalance(state->args); drop_node = drop_blk->bp->b_addr; save_node = save_blk->bp->b_addr; - ASSERT(drop_node->hdr.info.magic == cpu_to_be16(XFS_DA_NODE_MAGIC)); - ASSERT(save_node->hdr.info.magic == cpu_to_be16(XFS_DA_NODE_MAGIC)); + xfs_da3_node_hdr_from_disk(&dhdr, drop_node); + xfs_da3_node_hdr_from_disk(&shdr, save_node); + dbtree = xfs_da3_node_tree_p(drop_node); + sbtree = xfs_da3_node_tree_p(save_node); tp = state->args->trans; /* * If the dying block has lower hashvals, then move all the * elements in the remaining block up to make a hole. */ - if ((be32_to_cpu(drop_node->btree[0].hashval) < be32_to_cpu(save_node->btree[ 0 ].hashval)) || - (be32_to_cpu(drop_node->btree[be16_to_cpu(drop_node->hdr.count)-1].hashval) < - be32_to_cpu(save_node->btree[be16_to_cpu(save_node->hdr.count)-1].hashval))) - { - btree = &save_node->btree[be16_to_cpu(drop_node->hdr.count)]; - tmp = be16_to_cpu(save_node->hdr.count) * (uint)sizeof(xfs_da_node_entry_t); - memmove(btree, &save_node->btree[0], tmp); - btree = &save_node->btree[0]; + if ((be32_to_cpu(dbtree[0].hashval) < be32_to_cpu(sbtree[ 0 ].hashval)) || + (be32_to_cpu(dbtree[dhdr.count - 1].hashval) < + be32_to_cpu(sbtree[shdr.count - 1].hashval))) { + /* XXX: check this - is memmove dst correct? */ + tmp = shdr.count * (uint)sizeof(xfs_da_node_entry_t); + memmove(&sbtree[dhdr.count], &sbtree[0], tmp); + + sindex = 0; xfs_trans_log_buf(tp, save_blk->bp, - XFS_DA_LOGRANGE(save_node, btree, - (be16_to_cpu(save_node->hdr.count) + be16_to_cpu(drop_node->hdr.count)) * - sizeof(xfs_da_node_entry_t))); + XFS_DA_LOGRANGE(save_node, &sbtree[0], + (shdr.count + dhdr.count) * + sizeof(xfs_da_node_entry_t))); } else { - btree = &save_node->btree[be16_to_cpu(save_node->hdr.count)]; + sindex = shdr.count; xfs_trans_log_buf(tp, save_blk->bp, - XFS_DA_LOGRANGE(save_node, btree, - be16_to_cpu(drop_node->hdr.count) * - sizeof(xfs_da_node_entry_t))); + XFS_DA_LOGRANGE(save_node, &sbtree[sindex], + dhdr.count * sizeof(xfs_da_node_entry_t))); } /* * Move all the B-tree elements from drop_blk to save_blk. */ - tmp = be16_to_cpu(drop_node->hdr.count) * (uint)sizeof(xfs_da_node_entry_t); - memcpy(btree, &drop_node->btree[0], tmp); - be16_add_cpu(&save_node->hdr.count, be16_to_cpu(drop_node->hdr.count)); + tmp = dhdr.count * (uint)sizeof(xfs_da_node_entry_t); + memcpy(&sbtree[sindex], &dbtree[0], tmp); + shdr.count += dhdr.count; + xfs_da3_node_hdr_to_disk(save_node, &shdr); xfs_trans_log_buf(tp, save_blk->bp, XFS_DA_LOGRANGE(save_node, &save_node->hdr, - sizeof(save_node->hdr))); + xfs_da3_node_hdr_size(save_node))); /* * Save the last hashval in the remaining block for upward propagation. */ - save_blk->hashval = be32_to_cpu(save_node->btree[be16_to_cpu(save_node->hdr.count)-1].hashval); + save_blk->hashval = be32_to_cpu(sbtree[shdr.count - 1].hashval); } /*======================================================================== @@ -1156,16 +1436,24 @@ xfs_da_node_unbalance(xfs_da_state_t *state, xfs_da_state_blk_t *drop_blk, * pruned depth-first tree search. */ int /* error */ -xfs_da_node_lookup_int(xfs_da_state_t *state, int *result) +xfs_da3_node_lookup_int( + struct xfs_da_state *state, + int *result) { - xfs_da_state_blk_t *blk; - xfs_da_blkinfo_t *curr; - xfs_da_intnode_t *node; - xfs_da_node_entry_t *btree; - xfs_dablk_t blkno; - int probe, span, max, error, retval; - xfs_dahash_t hashval, btreehashval; - xfs_da_args_t *args; + struct xfs_da_state_blk *blk; + struct xfs_da_blkinfo *curr; + struct xfs_da_intnode *node; + struct xfs_da_node_entry *btree; + struct xfs_da3_icnode_hdr nodehdr; + struct xfs_da_args *args; + xfs_dablk_t blkno; + xfs_dahash_t hashval; + xfs_dahash_t btreehashval; + int probe; + int span; + int max; + int error; + int retval; args = state->args; @@ -1181,7 +1469,7 @@ xfs_da_node_lookup_int(xfs_da_state_t *state, int *result) * Read the next node down in the tree. */ blk->blkno = blkno; - error = xfs_da_node_read(args->trans, args->dp, blkno, + error = xfs_da3_node_read(args->trans, args->dp, blkno, -1, &blk->bp, args->whichfork); if (error) { blk->blkno = 0; @@ -1190,66 +1478,73 @@ xfs_da_node_lookup_int(xfs_da_state_t *state, int *result) } curr = blk->bp->b_addr; blk->magic = be16_to_cpu(curr->magic); - ASSERT(blk->magic == XFS_DA_NODE_MAGIC || - blk->magic == XFS_DIR2_LEAFN_MAGIC || - blk->magic == XFS_ATTR_LEAF_MAGIC); + + if (blk->magic == XFS_ATTR_LEAF_MAGIC) { + blk->hashval = xfs_attr_leaf_lasthash(blk->bp, NULL); + break; + } + + if (blk->magic == XFS_DIR2_LEAFN_MAGIC || + blk->magic == XFS_DIR3_LEAFN_MAGIC) { + blk->magic = XFS_DIR2_LEAFN_MAGIC; + blk->hashval = xfs_dir2_leafn_lasthash(blk->bp, NULL); + break; + } + + blk->magic = XFS_DA_NODE_MAGIC; + /* * Search an intermediate node for a match. */ - if (blk->magic == XFS_DA_NODE_MAGIC) { - node = blk->bp->b_addr; - max = be16_to_cpu(node->hdr.count); - blk->hashval = be32_to_cpu(node->btree[max-1].hashval); + node = blk->bp->b_addr; + xfs_da3_node_hdr_from_disk(&nodehdr, node); + btree = xfs_da3_node_tree_p(node); - /* - * Binary search. (note: small blocks will skip loop) - */ - probe = span = max / 2; - hashval = args->hashval; - for (btree = &node->btree[probe]; span > 4; - btree = &node->btree[probe]) { - span /= 2; - btreehashval = be32_to_cpu(btree->hashval); - if (btreehashval < hashval) - probe += span; - else if (btreehashval > hashval) - probe -= span; - else - break; - } - ASSERT((probe >= 0) && (probe < max)); - ASSERT((span <= 4) || (be32_to_cpu(btree->hashval) == hashval)); + max = nodehdr.count; + blk->hashval = be32_to_cpu(btree[max - 1].hashval); - /* - * Since we may have duplicate hashval's, find the first - * matching hashval in the node. - */ - while ((probe > 0) && (be32_to_cpu(btree->hashval) >= hashval)) { - btree--; - probe--; - } - while ((probe < max) && (be32_to_cpu(btree->hashval) < hashval)) { - btree++; - probe++; - } + /* + * Binary search. (note: small blocks will skip loop) + */ + probe = span = max / 2; + hashval = args->hashval; + while (span > 4) { + span /= 2; + btreehashval = be32_to_cpu(btree[probe].hashval); + if (btreehashval < hashval) + probe += span; + else if (btreehashval > hashval) + probe -= span; + else + break; + } + ASSERT((probe >= 0) && (probe < max)); + ASSERT((span <= 4) || + (be32_to_cpu(btree[probe].hashval) == hashval)); - /* - * Pick the right block to descend on. - */ - if (probe == max) { - blk->index = max-1; - blkno = be32_to_cpu(node->btree[max-1].before); - } else { - blk->index = probe; - blkno = be32_to_cpu(btree->before); - } - } else if (blk->magic == XFS_ATTR_LEAF_MAGIC) { - blk->hashval = xfs_attr_leaf_lasthash(blk->bp, NULL); - break; - } else if (blk->magic == XFS_DIR2_LEAFN_MAGIC) { - blk->hashval = xfs_dir2_leafn_lasthash(blk->bp, NULL); - break; + /* + * Since we may have duplicate hashval's, find the first + * matching hashval in the node. + */ + while (probe > 0 && + be32_to_cpu(btree[probe].hashval) >= hashval) { + probe--; + } + while (probe < max && + be32_to_cpu(btree[probe].hashval) < hashval) { + probe++; + } + + /* + * Pick the right block to descend on. + */ + if (probe == max) { + blk->index = max - 1; + blkno = be32_to_cpu(btree[max - 1].before); + } else { + blk->index = probe; + blkno = be32_to_cpu(btree[probe].before); } } @@ -1273,7 +1568,7 @@ xfs_da_node_lookup_int(xfs_da_state_t *state, int *result) } if (((retval == ENOENT) || (retval == ENOATTR)) && (blk->hashval == args->hashval)) { - error = xfs_da_path_shift(state, &state->path, 1, 1, + error = xfs_da3_path_shift(state, &state->path, 1, 1, &retval); if (error) return(error); @@ -1295,16 +1590,52 @@ xfs_da_node_lookup_int(xfs_da_state_t *state, int *result) *========================================================================*/ /* + * Compare two intermediate nodes for "order". + */ +STATIC int +xfs_da3_node_order( + struct xfs_buf *node1_bp, + struct xfs_buf *node2_bp) +{ + struct xfs_da_intnode *node1; + struct xfs_da_intnode *node2; + struct xfs_da_node_entry *btree1; + struct xfs_da_node_entry *btree2; + struct xfs_da3_icnode_hdr node1hdr; + struct xfs_da3_icnode_hdr node2hdr; + + node1 = node1_bp->b_addr; + node2 = node2_bp->b_addr; + xfs_da3_node_hdr_from_disk(&node1hdr, node1); + xfs_da3_node_hdr_from_disk(&node2hdr, node2); + btree1 = xfs_da3_node_tree_p(node1); + btree2 = xfs_da3_node_tree_p(node2); + + if (node1hdr.count > 0 && node2hdr.count > 0 && + ((be32_to_cpu(btree2[0].hashval) < be32_to_cpu(btree1[0].hashval)) || + (be32_to_cpu(btree2[node2hdr.count - 1].hashval) < + be32_to_cpu(btree1[node1hdr.count - 1].hashval)))) { + return 1; + } + return 0; +} + +/* * Link a new block into a doubly linked list of blocks (of whatever type). */ int /* error */ -xfs_da_blk_link(xfs_da_state_t *state, xfs_da_state_blk_t *old_blk, - xfs_da_state_blk_t *new_blk) +xfs_da3_blk_link( + struct xfs_da_state *state, + struct xfs_da_state_blk *old_blk, + struct xfs_da_state_blk *new_blk) { - xfs_da_blkinfo_t *old_info, *new_info, *tmp_info; - xfs_da_args_t *args; - int before=0, error; - struct xfs_buf *bp; + struct xfs_da_blkinfo *old_info; + struct xfs_da_blkinfo *new_info; + struct xfs_da_blkinfo *tmp_info; + struct xfs_da_args *args; + struct xfs_buf *bp; + int before = 0; + int error; /* * Set up environment. @@ -1316,9 +1647,6 @@ xfs_da_blk_link(xfs_da_state_t *state, xfs_da_state_blk_t *old_blk, ASSERT(old_blk->magic == XFS_DA_NODE_MAGIC || old_blk->magic == XFS_DIR2_LEAFN_MAGIC || old_blk->magic == XFS_ATTR_LEAF_MAGIC); - ASSERT(old_blk->magic == be16_to_cpu(old_info->magic)); - ASSERT(new_blk->magic == be16_to_cpu(new_info->magic)); - ASSERT(old_blk->magic == new_blk->magic); switch (old_blk->magic) { case XFS_ATTR_LEAF_MAGIC: @@ -1328,7 +1656,7 @@ xfs_da_blk_link(xfs_da_state_t *state, xfs_da_state_blk_t *old_blk, before = xfs_dir2_leafn_order(old_blk->bp, new_blk->bp); break; case XFS_DA_NODE_MAGIC: - before = xfs_da_node_order(old_blk->bp, new_blk->bp); + before = xfs_da3_node_order(old_blk->bp, new_blk->bp); break; } @@ -1343,14 +1671,14 @@ xfs_da_blk_link(xfs_da_state_t *state, xfs_da_state_blk_t *old_blk, new_info->forw = cpu_to_be32(old_blk->blkno); new_info->back = old_info->back; if (old_info->back) { - error = xfs_da_node_read(args->trans, args->dp, + error = xfs_da3_node_read(args->trans, args->dp, be32_to_cpu(old_info->back), -1, &bp, args->whichfork); if (error) return(error); ASSERT(bp != NULL); tmp_info = bp->b_addr; - ASSERT(be16_to_cpu(tmp_info->magic) == be16_to_cpu(old_info->magic)); + ASSERT(tmp_info->magic == old_info->magic); ASSERT(be32_to_cpu(tmp_info->forw) == old_blk->blkno); tmp_info->forw = cpu_to_be32(new_blk->blkno); xfs_trans_log_buf(args->trans, bp, 0, sizeof(*tmp_info)-1); @@ -1364,7 +1692,7 @@ xfs_da_blk_link(xfs_da_state_t *state, xfs_da_state_blk_t *old_blk, new_info->forw = old_info->forw; new_info->back = cpu_to_be32(old_blk->blkno); if (old_info->forw) { - error = xfs_da_node_read(args->trans, args->dp, + error = xfs_da3_node_read(args->trans, args->dp, be32_to_cpu(old_info->forw), -1, &bp, args->whichfork); if (error) @@ -1385,59 +1713,20 @@ xfs_da_blk_link(xfs_da_state_t *state, xfs_da_state_blk_t *old_blk, } /* - * Compare two intermediate nodes for "order". - */ -STATIC int -xfs_da_node_order( - struct xfs_buf *node1_bp, - struct xfs_buf *node2_bp) -{ - xfs_da_intnode_t *node1, *node2; - - node1 = node1_bp->b_addr; - node2 = node2_bp->b_addr; - ASSERT(node1->hdr.info.magic == cpu_to_be16(XFS_DA_NODE_MAGIC) && - node2->hdr.info.magic == cpu_to_be16(XFS_DA_NODE_MAGIC)); - if ((be16_to_cpu(node1->hdr.count) > 0) && (be16_to_cpu(node2->hdr.count) > 0) && - ((be32_to_cpu(node2->btree[0].hashval) < - be32_to_cpu(node1->btree[0].hashval)) || - (be32_to_cpu(node2->btree[be16_to_cpu(node2->hdr.count)-1].hashval) < - be32_to_cpu(node1->btree[be16_to_cpu(node1->hdr.count)-1].hashval)))) { - return(1); - } - return(0); -} - -/* - * Pick up the last hashvalue from an intermediate node. - */ -STATIC uint -xfs_da_node_lasthash( - struct xfs_buf *bp, - int *count) -{ - xfs_da_intnode_t *node; - - node = bp->b_addr; - ASSERT(node->hdr.info.magic == cpu_to_be16(XFS_DA_NODE_MAGIC)); - if (count) - *count = be16_to_cpu(node->hdr.count); - if (!node->hdr.count) - return(0); - return be32_to_cpu(node->btree[be16_to_cpu(node->hdr.count)-1].hashval); -} - -/* * Unlink a block from a doubly linked list of blocks. */ STATIC int /* error */ -xfs_da_blk_unlink(xfs_da_state_t *state, xfs_da_state_blk_t *drop_blk, - xfs_da_state_blk_t *save_blk) +xfs_da3_blk_unlink( + struct xfs_da_state *state, + struct xfs_da_state_blk *drop_blk, + struct xfs_da_state_blk *save_blk) { - xfs_da_blkinfo_t *drop_info, *save_info, *tmp_info; - xfs_da_args_t *args; - struct xfs_buf *bp; - int error; + struct xfs_da_blkinfo *drop_info; + struct xfs_da_blkinfo *save_info; + struct xfs_da_blkinfo *tmp_info; + struct xfs_da_args *args; + struct xfs_buf *bp; + int error; /* * Set up environment. @@ -1449,8 +1738,6 @@ xfs_da_blk_unlink(xfs_da_state_t *state, xfs_da_state_blk_t *drop_blk, ASSERT(save_blk->magic == XFS_DA_NODE_MAGIC || save_blk->magic == XFS_DIR2_LEAFN_MAGIC || save_blk->magic == XFS_ATTR_LEAF_MAGIC); - ASSERT(save_blk->magic == be16_to_cpu(save_info->magic)); - ASSERT(drop_blk->magic == be16_to_cpu(drop_info->magic)); ASSERT(save_blk->magic == drop_blk->magic); ASSERT((be32_to_cpu(save_info->forw) == drop_blk->blkno) || (be32_to_cpu(save_info->back) == drop_blk->blkno)); @@ -1464,7 +1751,7 @@ xfs_da_blk_unlink(xfs_da_state_t *state, xfs_da_state_blk_t *drop_blk, trace_xfs_da_unlink_back(args); save_info->back = drop_info->back; if (drop_info->back) { - error = xfs_da_node_read(args->trans, args->dp, + error = xfs_da3_node_read(args->trans, args->dp, be32_to_cpu(drop_info->back), -1, &bp, args->whichfork); if (error) @@ -1481,7 +1768,7 @@ xfs_da_blk_unlink(xfs_da_state_t *state, xfs_da_state_blk_t *drop_blk, trace_xfs_da_unlink_forward(args); save_info->forw = drop_info->forw; if (drop_info->forw) { - error = xfs_da_node_read(args->trans, args->dp, + error = xfs_da3_node_read(args->trans, args->dp, be32_to_cpu(drop_info->forw), -1, &bp, args->whichfork); if (error) @@ -1509,15 +1796,22 @@ xfs_da_blk_unlink(xfs_da_state_t *state, xfs_da_state_blk_t *drop_blk, * the new bottom and the root. */ int /* error */ -xfs_da_path_shift(xfs_da_state_t *state, xfs_da_state_path_t *path, - int forward, int release, int *result) +xfs_da3_path_shift( + struct xfs_da_state *state, + struct xfs_da_state_path *path, + int forward, + int release, + int *result) { - xfs_da_state_blk_t *blk; - xfs_da_blkinfo_t *info; - xfs_da_intnode_t *node; - xfs_da_args_t *args; - xfs_dablk_t blkno=0; - int level, error; + struct xfs_da_state_blk *blk; + struct xfs_da_blkinfo *info; + struct xfs_da_intnode *node; + struct xfs_da_args *args; + struct xfs_da_node_entry *btree; + struct xfs_da3_icnode_hdr nodehdr; + xfs_dablk_t blkno = 0; + int level; + int error; trace_xfs_da_path_shift(state->args); @@ -1532,16 +1826,17 @@ xfs_da_path_shift(xfs_da_state_t *state, xfs_da_state_path_t *path, ASSERT((path->active > 0) && (path->active < XFS_DA_NODE_MAXDEPTH)); level = (path->active-1) - 1; /* skip bottom layer in path */ for (blk = &path->blk[level]; level >= 0; blk--, level--) { - ASSERT(blk->bp != NULL); node = blk->bp->b_addr; - ASSERT(node->hdr.info.magic == cpu_to_be16(XFS_DA_NODE_MAGIC)); - if (forward && (blk->index < be16_to_cpu(node->hdr.count)-1)) { + xfs_da3_node_hdr_from_disk(&nodehdr, node); + btree = xfs_da3_node_tree_p(node); + + if (forward && (blk->index < nodehdr.count - 1)) { blk->index++; - blkno = be32_to_cpu(node->btree[blk->index].before); + blkno = be32_to_cpu(btree[blk->index].before); break; } else if (!forward && (blk->index > 0)) { blk->index--; - blkno = be32_to_cpu(node->btree[blk->index].before); + blkno = be32_to_cpu(btree[blk->index].before); break; } } @@ -1567,47 +1862,58 @@ xfs_da_path_shift(xfs_da_state_t *state, xfs_da_state_path_t *path, * Read the next child block. */ blk->blkno = blkno; - error = xfs_da_node_read(args->trans, args->dp, blkno, -1, + error = xfs_da3_node_read(args->trans, args->dp, blkno, -1, &blk->bp, args->whichfork); if (error) return(error); - ASSERT(blk->bp != NULL); info = blk->bp->b_addr; ASSERT(info->magic == cpu_to_be16(XFS_DA_NODE_MAGIC) || + info->magic == cpu_to_be16(XFS_DA3_NODE_MAGIC) || info->magic == cpu_to_be16(XFS_DIR2_LEAFN_MAGIC) || info->magic == cpu_to_be16(XFS_DIR3_LEAFN_MAGIC) || info->magic == cpu_to_be16(XFS_ATTR_LEAF_MAGIC)); - blk->magic = be16_to_cpu(info->magic); - if (blk->magic == XFS_DA_NODE_MAGIC) { + + + /* + * Note: we flatten the magic number to a single type so we + * don't have to compare against crc/non-crc types elsewhere. + */ + switch (be16_to_cpu(info->magic)) { + case XFS_DA_NODE_MAGIC: + case XFS_DA3_NODE_MAGIC: + blk->magic = XFS_DA_NODE_MAGIC; node = (xfs_da_intnode_t *)info; - blk->hashval = be32_to_cpu(node->btree[be16_to_cpu(node->hdr.count)-1].hashval); + xfs_da3_node_hdr_from_disk(&nodehdr, node); + btree = xfs_da3_node_tree_p(node); + blk->hashval = be32_to_cpu(btree[nodehdr.count - 1].hashval); if (forward) blk->index = 0; else - blk->index = be16_to_cpu(node->hdr.count)-1; - blkno = be32_to_cpu(node->btree[blk->index].before); - } else { + blk->index = nodehdr.count - 1; + blkno = be32_to_cpu(btree[blk->index].before); + break; + case XFS_ATTR_LEAF_MAGIC: + blk->magic = XFS_ATTR_LEAF_MAGIC; ASSERT(level == path->active-1); blk->index = 0; - switch(blk->magic) { - case XFS_ATTR_LEAF_MAGIC: - blk->hashval = xfs_attr_leaf_lasthash(blk->bp, - NULL); - break; - case XFS_DIR2_LEAFN_MAGIC: - case XFS_DIR3_LEAFN_MAGIC: - blk->magic = XFS_DIR2_LEAFN_MAGIC; - blk->hashval = xfs_dir2_leafn_lasthash(blk->bp, - NULL); - break; - default: - ASSERT(0); - break; - } + blk->hashval = xfs_attr_leaf_lasthash(blk->bp, + NULL); + break; + case XFS_DIR2_LEAFN_MAGIC: + case XFS_DIR3_LEAFN_MAGIC: + blk->magic = XFS_DIR2_LEAFN_MAGIC; + ASSERT(level == path->active-1); + blk->index = 0; + blk->hashval = xfs_dir2_leafn_lasthash(blk->bp, + NULL); + break; + default: + ASSERT(0); + break; } } *result = 0; - return(0); + return 0; } @@ -1794,22 +2100,36 @@ xfs_da_grow_inode( * a bmap btree split to do that. */ STATIC int -xfs_da_swap_lastblock( - xfs_da_args_t *args, - xfs_dablk_t *dead_blknop, - struct xfs_buf **dead_bufp) +xfs_da3_swap_lastblock( + struct xfs_da_args *args, + xfs_dablk_t *dead_blknop, + struct xfs_buf **dead_bufp) { - xfs_dablk_t dead_blkno, last_blkno, sib_blkno, par_blkno; - struct xfs_buf *dead_buf, *last_buf, *sib_buf, *par_buf; - xfs_fileoff_t lastoff; - xfs_inode_t *ip; - xfs_trans_t *tp; - xfs_mount_t *mp; - int error, w, entno, level, dead_level; - xfs_da_blkinfo_t *dead_info, *sib_info; - xfs_da_intnode_t *par_node, *dead_node; - xfs_dir2_leaf_t *dead_leaf2; - xfs_dahash_t dead_hash; + struct xfs_da_blkinfo *dead_info; + struct xfs_da_blkinfo *sib_info; + struct xfs_da_intnode *par_node; + struct xfs_da_intnode *dead_node; + struct xfs_dir2_leaf *dead_leaf2; + struct xfs_da_node_entry *btree; + struct xfs_da3_icnode_hdr par_hdr; + struct xfs_inode *ip; + struct xfs_trans *tp; + struct xfs_mount *mp; + struct xfs_buf *dead_buf; + struct xfs_buf *last_buf; + struct xfs_buf *sib_buf; + struct xfs_buf *par_buf; + xfs_dahash_t dead_hash; + xfs_fileoff_t lastoff; + xfs_dablk_t dead_blkno; + xfs_dablk_t last_blkno; + xfs_dablk_t sib_blkno; + xfs_dablk_t par_blkno; + int error; + int w; + int entno; + int level; + int dead_level; trace_xfs_da_swap_lastblock(args); @@ -1833,7 +2153,7 @@ xfs_da_swap_lastblock( * Read the last block in the btree space. */ last_blkno = (xfs_dablk_t)lastoff - mp->m_dirblkfsbs; - error = xfs_da_node_read(tp, ip, last_blkno, -1, &last_buf, w); + error = xfs_da3_node_read(tp, ip, last_blkno, -1, &last_buf, w); if (error) return error; /* @@ -1856,17 +2176,22 @@ xfs_da_swap_lastblock( dead_level = 0; dead_hash = be32_to_cpu(ents[leafhdr.count - 1].hashval); } else { - ASSERT(dead_info->magic == cpu_to_be16(XFS_DA_NODE_MAGIC)); + struct xfs_da3_icnode_hdr deadhdr; + + ASSERT(dead_info->magic == cpu_to_be16(XFS_DA_NODE_MAGIC) || + dead_info->magic == cpu_to_be16(XFS_DA3_NODE_MAGIC)); dead_node = (xfs_da_intnode_t *)dead_info; - dead_level = be16_to_cpu(dead_node->hdr.level); - dead_hash = be32_to_cpu(dead_node->btree[be16_to_cpu(dead_node->hdr.count) - 1].hashval); + xfs_da3_node_hdr_from_disk(&deadhdr, dead_node); + btree = xfs_da3_node_tree_p(dead_node); + dead_level = deadhdr.level; + dead_hash = be32_to_cpu(btree[deadhdr.count - 1].hashval); } sib_buf = par_buf = NULL; /* * If the moved block has a left sibling, fix up the pointers. */ if ((sib_blkno = be32_to_cpu(dead_info->back))) { - error = xfs_da_node_read(tp, ip, sib_blkno, -1, &sib_buf, w); + error = xfs_da3_node_read(tp, ip, sib_blkno, -1, &sib_buf, w); if (error) goto done; sib_info = sib_buf->b_addr; @@ -1888,7 +2213,7 @@ xfs_da_swap_lastblock( * If the moved block has a right sibling, fix up the pointers. */ if ((sib_blkno = be32_to_cpu(dead_info->forw))) { - error = xfs_da_node_read(tp, ip, sib_blkno, -1, &sib_buf, w); + error = xfs_da3_node_read(tp, ip, sib_blkno, -1, &sib_buf, w); if (error) goto done; sib_info = sib_buf->b_addr; @@ -1912,31 +2237,31 @@ xfs_da_swap_lastblock( * Walk down the tree looking for the parent of the moved block. */ for (;;) { - error = xfs_da_node_read(tp, ip, par_blkno, -1, &par_buf, w); + error = xfs_da3_node_read(tp, ip, par_blkno, -1, &par_buf, w); if (error) goto done; par_node = par_buf->b_addr; - if (unlikely(par_node->hdr.info.magic != - cpu_to_be16(XFS_DA_NODE_MAGIC) || - (level >= 0 && level != be16_to_cpu(par_node->hdr.level) + 1))) { + xfs_da3_node_hdr_from_disk(&par_hdr, par_node); + if (level >= 0 && level != be16_to_cpu(par_hdr.level) + 1) { XFS_ERROR_REPORT("xfs_da_swap_lastblock(4)", XFS_ERRLEVEL_LOW, mp); error = XFS_ERROR(EFSCORRUPTED); goto done; } - level = be16_to_cpu(par_node->hdr.level); + level = par_hdr.level; + btree = xfs_da3_node_tree_p(par_node); for (entno = 0; - entno < be16_to_cpu(par_node->hdr.count) && - be32_to_cpu(par_node->btree[entno].hashval) < dead_hash; + entno < par_hdr.count && + be32_to_cpu(btree[entno].hashval) < dead_hash; entno++) continue; - if (unlikely(entno == be16_to_cpu(par_node->hdr.count))) { + if (entno == par_hdr.count) { XFS_ERROR_REPORT("xfs_da_swap_lastblock(5)", XFS_ERRLEVEL_LOW, mp); error = XFS_ERROR(EFSCORRUPTED); goto done; } - par_blkno = be32_to_cpu(par_node->btree[entno].before); + par_blkno = be32_to_cpu(btree[entno].before); if (level == dead_level + 1) break; xfs_trans_brelse(tp, par_buf); @@ -1948,13 +2273,13 @@ xfs_da_swap_lastblock( */ for (;;) { for (; - entno < be16_to_cpu(par_node->hdr.count) && - be32_to_cpu(par_node->btree[entno].before) != last_blkno; + entno < par_hdr.count && + be32_to_cpu(btree[entno].before) != last_blkno; entno++) continue; - if (entno < be16_to_cpu(par_node->hdr.count)) + if (entno < par_hdr.count) break; - par_blkno = be32_to_cpu(par_node->hdr.info.forw); + par_blkno = par_hdr.forw; xfs_trans_brelse(tp, par_buf); par_buf = NULL; if (unlikely(par_blkno == 0)) { @@ -1963,27 +2288,27 @@ xfs_da_swap_lastblock( error = XFS_ERROR(EFSCORRUPTED); goto done; } - error = xfs_da_node_read(tp, ip, par_blkno, -1, &par_buf, w); + error = xfs_da3_node_read(tp, ip, par_blkno, -1, &par_buf, w); if (error) goto done; par_node = par_buf->b_addr; - if (unlikely( - be16_to_cpu(par_node->hdr.level) != level || - par_node->hdr.info.magic != cpu_to_be16(XFS_DA_NODE_MAGIC))) { + xfs_da3_node_hdr_from_disk(&par_hdr, par_node); + if (par_hdr.level != level) { XFS_ERROR_REPORT("xfs_da_swap_lastblock(7)", XFS_ERRLEVEL_LOW, mp); error = XFS_ERROR(EFSCORRUPTED); goto done; } + btree = xfs_da3_node_tree_p(par_node); entno = 0; } /* * Update the parent entry pointing to the moved block. */ - par_node->btree[entno].before = cpu_to_be32(dead_blkno); + btree[entno].before = cpu_to_be32(dead_blkno); xfs_trans_log_buf(tp, par_buf, - XFS_DA_LOGRANGE(par_node, &par_node->btree[entno].before, - sizeof(par_node->btree[entno].before))); + XFS_DA_LOGRANGE(par_node, &btree[entno].before, + sizeof(btree[entno].before))); *dead_blknop = last_blkno; *dead_bufp = last_buf; return 0; @@ -2025,14 +2350,15 @@ xfs_da_shrink_inode( * Remove extents. If we get ENOSPC for a dir we have to move * the last block to the place we want to kill. */ - if ((error = xfs_bunmapi(tp, dp, dead_blkno, count, - xfs_bmapi_aflag(w)|XFS_BMAPI_METADATA, - 0, args->firstblock, args->flist, - &done)) == ENOSPC) { + error = xfs_bunmapi(tp, dp, dead_blkno, count, + xfs_bmapi_aflag(w)|XFS_BMAPI_METADATA, + 0, args->firstblock, args->flist, &done); + if (error == ENOSPC) { if (w != XFS_DATA_FORK) break; - if ((error = xfs_da_swap_lastblock(args, &dead_blkno, - &dead_buf))) + error = xfs_da3_swap_lastblock(args, &dead_blkno, + &dead_buf); + if (error) break; } else { break; @@ -2297,6 +2623,7 @@ xfs_da_read_buf( magic1 = be32_to_cpu(hdr->magic); if (unlikely( XFS_TEST_ERROR((magic != XFS_DA_NODE_MAGIC) && + (magic != XFS_DA3_NODE_MAGIC) && (magic != XFS_ATTR_LEAF_MAGIC) && (magic != XFS_DIR2_LEAF1_MAGIC) && (magic != XFS_DIR3_LEAF1_MAGIC) && @@ -2367,41 +2694,3 @@ out_free: return -1; return mappedbno; } - -kmem_zone_t *xfs_da_state_zone; /* anchor for state struct zone */ - -/* - * Allocate a dir-state structure. - * We don't put them on the stack since they're large. - */ -xfs_da_state_t * -xfs_da_state_alloc(void) -{ - return kmem_zone_zalloc(xfs_da_state_zone, KM_NOFS); -} - -/* - * Kill the altpath contents of a da-state structure. - */ -STATIC void -xfs_da_state_kill_altpath(xfs_da_state_t *state) -{ - int i; - - for (i = 0; i < state->altpath.active; i++) - state->altpath.blk[i].bp = NULL; - state->altpath.active = 0; -} - -/* - * Free a da-state structure. - */ -void -xfs_da_state_free(xfs_da_state_t *state) -{ - xfs_da_state_kill_altpath(state); -#ifdef DEBUG - memset((char *)state, 0, sizeof(*state)); -#endif /* DEBUG */ - kmem_zone_free(xfs_da_state_zone, state); -} diff --git a/fs/xfs/xfs_da_btree.h b/fs/xfs/xfs_da_btree.h index 0854b95..6bedb3c 100644 --- a/fs/xfs/xfs_da_btree.h +++ b/fs/xfs/xfs_da_btree.h @@ -1,5 +1,6 @@ /* * Copyright (c) 2000,2002,2005 Silicon Graphics, Inc. + * Copyright (c) 2013 Red Hat, Inc. * All Rights Reserved. * * This program is free software; you can redistribute it and/or @@ -20,7 +21,6 @@ struct xfs_bmap_free; struct xfs_inode; -struct xfs_mount; struct xfs_trans; struct zone; @@ -50,8 +50,11 @@ typedef struct xfs_da_blkinfo { * CRC enabled directory structure types * * The headers change size for the additional verification information, but - * otherwise the tree layouts and contents are unchanged. + * otherwise the tree layouts and contents are unchanged. Hence the da btree + * code can use the struct xfs_da_blkinfo for manipulating the tree links and + * magic numbers without modification for both v2 and v3 nodes. */ +#define XFS_DA3_NODE_MAGIC 0x3ebe /* magic number: non-leaf blocks */ #define XFS_DIR3_LEAF1_MAGIC 0x3df1 /* magic number: v2 dirlf single blks */ #define XFS_DIR3_LEAFN_MAGIC 0x3dff /* magic number: v2 dirlf multi blks */ @@ -80,19 +83,76 @@ struct xfs_da3_blkinfo { */ #define XFS_DA_NODE_MAXDEPTH 5 /* max depth of Btree */ +typedef struct xfs_da_node_hdr { + struct xfs_da_blkinfo info; /* block type, links, etc. */ + __be16 count; /* count of active entries */ + __be16 __level; /* level above leaves (leaf == 0) */ +} xfs_da_node_hdr_t; + +struct xfs_da3_node_hdr { + struct xfs_da3_blkinfo info; /* block type, links, etc. */ + __be16 count; /* count of active entries */ + __be16 __level; /* level above leaves (leaf == 0) */ + __be32 __pad32; +}; + +#define XFS_DA3_NODE_CRC_OFF (offsetof(struct xfs_da3_node_hdr, info.crc)) + +typedef struct xfs_da_node_entry { + __be32 hashval; /* hash value for this descendant */ + __be32 before; /* Btree block before this key */ +} xfs_da_node_entry_t; + typedef struct xfs_da_intnode { - struct xfs_da_node_hdr { /* constant-structure header block */ - xfs_da_blkinfo_t info; /* block type, links, etc. */ - __be16 count; /* count of active entries */ - __be16 level; /* level above leaves (leaf == 0) */ - } hdr; - struct xfs_da_node_entry { - __be32 hashval; /* hash value for this descendant */ - __be32 before; /* Btree block before this key */ - } btree[1]; /* variable sized array of keys */ + struct xfs_da_node_hdr hdr; + struct xfs_da_node_entry __btree[]; } xfs_da_intnode_t; -typedef struct xfs_da_node_hdr xfs_da_node_hdr_t; -typedef struct xfs_da_node_entry xfs_da_node_entry_t; + +struct xfs_da3_intnode { + struct xfs_da3_node_hdr hdr; + struct xfs_da_node_entry __btree[]; +}; + +/* + * In-core version of the node header to abstract the differences in the v2 and + * v3 disk format of the headers. Callers need to convert to/from disk format as + * appropriate. + */ +struct xfs_da3_icnode_hdr { + __uint32_t forw; + __uint32_t back; + __uint16_t magic; + __uint16_t count; + __uint16_t level; +}; + +extern void xfs_da3_node_hdr_from_disk(struct xfs_da3_icnode_hdr *to, + struct xfs_da_intnode *from); +extern void xfs_da3_node_hdr_to_disk(struct xfs_da_intnode *to, + struct xfs_da3_icnode_hdr *from); + +static inline int +xfs_da3_node_hdr_size(struct xfs_da_intnode *dap) +{ + if (dap->hdr.info.magic == cpu_to_be16(XFS_DA3_NODE_MAGIC)) + return sizeof(struct xfs_da3_node_hdr); + return sizeof(struct xfs_da_node_hdr); +} + +static inline struct xfs_da_node_entry * +xfs_da3_node_tree_p(struct xfs_da_intnode *dap) +{ + if (dap->hdr.info.magic == cpu_to_be16(XFS_DA3_NODE_MAGIC)) { + struct xfs_da3_intnode *dap3 = (struct xfs_da3_intnode *)dap; + return dap3->__btree; + } + return dap->__btree; +} + +extern void xfs_da3_intnode_from_disk(struct xfs_da3_icnode_hdr *to, + struct xfs_da_intnode *from); +extern void xfs_da3_intnode_to_disk(struct xfs_da_intnode *to, + struct xfs_da3_icnode_hdr *from); #define XFS_LBSIZE(mp) (mp)->m_sb.sb_blocksize @@ -214,29 +274,29 @@ struct xfs_nameops { /* * Routines used for growing the Btree. */ -int xfs_da_node_create(xfs_da_args_t *args, xfs_dablk_t blkno, int level, - struct xfs_buf **bpp, int whichfork); -int xfs_da_split(xfs_da_state_t *state); +int xfs_da3_node_create(struct xfs_da_args *args, xfs_dablk_t blkno, + int level, struct xfs_buf **bpp, int whichfork); +int xfs_da3_split(xfs_da_state_t *state); /* * Routines used for shrinking the Btree. */ -int xfs_da_join(xfs_da_state_t *state); -void xfs_da_fixhashpath(xfs_da_state_t *state, - xfs_da_state_path_t *path_to_to_fix); +int xfs_da3_join(xfs_da_state_t *state); +void xfs_da3_fixhashpath(struct xfs_da_state *state, + struct xfs_da_state_path *path_to_to_fix); /* * Routines used for finding things in the Btree. */ -int xfs_da_node_lookup_int(xfs_da_state_t *state, int *result); -int xfs_da_path_shift(xfs_da_state_t *state, xfs_da_state_path_t *path, +int xfs_da3_node_lookup_int(xfs_da_state_t *state, int *result); +int xfs_da3_path_shift(xfs_da_state_t *state, xfs_da_state_path_t *path, int forward, int release, int *result); /* * Utility routines. */ -int xfs_da_blk_link(xfs_da_state_t *state, xfs_da_state_blk_t *old_blk, +int xfs_da3_blk_link(xfs_da_state_t *state, xfs_da_state_blk_t *old_blk, xfs_da_state_blk_t *new_blk); -int xfs_da_node_read(struct xfs_trans *tp, struct xfs_inode *dp, +int xfs_da3_node_read(struct xfs_trans *tp, struct xfs_inode *dp, xfs_dablk_t bno, xfs_daddr_t mappedbno, struct xfs_buf **bpp, int which_fork); diff --git a/fs/xfs/xfs_dir2_node.c b/fs/xfs/xfs_dir2_node.c index 747aed1..4f9f9cf 100644 --- a/fs/xfs/xfs_dir2_node.c +++ b/fs/xfs/xfs_dir2_node.c @@ -1366,7 +1366,7 @@ xfs_dir2_leafn_split( * block into the leaves. */ xfs_dir2_leafn_rebalance(state, oldblk, newblk); - error = xfs_da_blk_link(state, oldblk, newblk); + error = xfs_da3_blk_link(state, oldblk, newblk); if (error) { return error; } @@ -1448,7 +1448,7 @@ xfs_dir2_leafn_toosmall( */ forward = (leafhdr.forw != 0); memcpy(&state->altpath, &state->path, sizeof(state->path)); - error = xfs_da_path_shift(state, &state->altpath, forward, 0, + error = xfs_da3_path_shift(state, &state->altpath, forward, 0, &rval); if (error) return error; @@ -1510,10 +1510,10 @@ xfs_dir2_leafn_toosmall( */ memcpy(&state->altpath, &state->path, sizeof(state->path)); if (blkno < blk->blkno) - error = xfs_da_path_shift(state, &state->altpath, forward, 0, + error = xfs_da3_path_shift(state, &state->altpath, forward, 0, &rval); else - error = xfs_da_path_shift(state, &state->path, forward, 0, + error = xfs_da3_path_shift(state, &state->path, forward, 0, &rval); if (error) { return error; @@ -1609,7 +1609,7 @@ xfs_dir2_node_addname( * Look up the name. We're not supposed to find it, but * this gives us the insertion point. */ - error = xfs_da_node_lookup_int(state, &rval); + error = xfs_da3_node_lookup_int(state, &rval); if (error) rval = error; if (rval != ENOENT) { @@ -1635,7 +1635,7 @@ xfs_dir2_node_addname( * It worked, fix the hash values up the btree. */ if (!(args->op_flags & XFS_DA_OP_JUSTCHECK)) - xfs_da_fixhashpath(state, &state->path); + xfs_da3_fixhashpath(state, &state->path); } else { /* * It didn't work, we need to split the leaf block. @@ -1647,7 +1647,7 @@ xfs_dir2_node_addname( /* * Split the leaf block and insert the new entry. */ - rval = xfs_da_split(state); + rval = xfs_da3_split(state); } done: xfs_da_state_free(state); @@ -2025,7 +2025,7 @@ xfs_dir2_node_addname_int( /* * Lookup an entry in a node-format directory. - * All the real work happens in xfs_da_node_lookup_int. + * All the real work happens in xfs_da3_node_lookup_int. * The only real output is the inode number of the entry. */ int /* error */ @@ -2050,7 +2050,7 @@ xfs_dir2_node_lookup( /* * Fill in the path to the entry in the cursor. */ - error = xfs_da_node_lookup_int(state, &rval); + error = xfs_da3_node_lookup_int(state, &rval); if (error) rval = error; else if (rval == ENOENT && args->cmpresult == XFS_CMP_CASE) { @@ -2105,7 +2105,7 @@ xfs_dir2_node_removename( /* * Look up the entry we're deleting, set up the cursor. */ - error = xfs_da_node_lookup_int(state, &rval); + error = xfs_da3_node_lookup_int(state, &rval); if (error) rval = error; /* @@ -2129,12 +2129,12 @@ xfs_dir2_node_removename( /* * Fix the hash values up the btree. */ - xfs_da_fixhashpath(state, &state->path); + xfs_da3_fixhashpath(state, &state->path); /* * If we need to join leaf blocks, do it. */ if (rval && state->path.active > 1) - error = xfs_da_join(state); + error = xfs_da3_join(state); /* * If no errors so far, try conversion to leaf format. */ @@ -2176,7 +2176,7 @@ xfs_dir2_node_replace( /* * Lookup the entry to change in the btree. */ - error = xfs_da_node_lookup_int(state, &rval); + error = xfs_da3_node_lookup_int(state, &rval); if (error) { rval = error; } diff --git a/fs/xfs/xfs_trace.c b/fs/xfs/xfs_trace.c index 624bedd..b6e3897 100644 --- a/fs/xfs/xfs_trace.c +++ b/fs/xfs/xfs_trace.c @@ -22,7 +22,6 @@ #include "xfs_trans.h" #include "xfs_sb.h" #include "xfs_ag.h" -#include "xfs_da_btree.h" #include "xfs_bmap_btree.h" #include "xfs_alloc_btree.h" #include "xfs_ialloc_btree.h" @@ -30,6 +29,7 @@ #include "xfs_inode.h" #include "xfs_btree.h" #include "xfs_mount.h" +#include "xfs_da_btree.h" #include "xfs_ialloc.h" #include "xfs_itable.h" #include "xfs_alloc.h" -- 1.7.10.4 From dave@fromorbit.com Tue Mar 12 07:31:54 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 007C87FEB for ; Tue, 12 Mar 2013 07:31:50 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay2.corp.sgi.com (Postfix) with ESMTP id D30CB304048 for ; Tue, 12 Mar 2013 05:31:49 -0700 (PDT) X-ASG-Debug-ID: 1363091485-04cb6c2b01493060006-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id Dx7sK2cmC9YrTzgB for ; Tue, 12 Mar 2013 05:31:41 -0700 (PDT) X-Barracuda-Envelope-From: dave@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AhAKAKEfP1F5LKiV/2dsb2JhbAA5CsRdAwGBSRd0gigBAQUaAQIKLzMIGBgZOQMbGYgSsAKQH41SECp2HIM2A4t0hxyEY4VSigWDHiiBLgEfBA Received: from ppp121-44-168-149.lns20.syd7.internode.on.net (HELO dastard) ([121.44.168.149]) by ipmail05.adl6.internode.on.net with ESMTP; 12 Mar 2013 23:01:29 +1030 Received: from disappointment ([192.168.1.1]) by dastard with esmtp (Exim 4.76) (envelope-from ) id 1UFOMQ-0001SV-MB for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:31:18 +1100 Received: from dave by disappointment with local (Exim 4.80) (envelope-from ) id 1UFOMQ-0002Mw-I7 for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:31:18 +1100 From: Dave Chinner To: xfs@oss.sgi.com Subject: [PATCH 17/21] xfs: add CRCs to attr leaf blocks Date: Tue, 12 Mar 2013 23:30:50 +1100 X-ASG-Orig-Subj: [PATCH 17/21] xfs: add CRCs to attr leaf blocks Message-Id: <1363091454-8852-18-git-send-email-david@fromorbit.com> X-Mailer: git-send-email 1.7.10.4 In-Reply-To: <1363091454-8852-1-git-send-email-david@fromorbit.com> References: <1363091454-8852-1-git-send-email-david@fromorbit.com> X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1363091501 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124988 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- From: Dave Chinner Signed-off-by: Dave Chinner --- fs/xfs/xfs_attr.c | 125 ++-- fs/xfs/xfs_attr_leaf.c | 1739 +++++++++++++++++++++++++++--------------------- fs/xfs/xfs_attr_leaf.h | 122 +++- fs/xfs/xfs_da_btree.c | 34 +- fs/xfs/xfs_da_btree.h | 5 +- 5 files changed, 1177 insertions(+), 848 deletions(-) diff --git a/fs/xfs/xfs_attr.c b/fs/xfs/xfs_attr.c index e03128c..de4093f 100644 --- a/fs/xfs/xfs_attr.c +++ b/fs/xfs/xfs_attr.c @@ -819,7 +819,7 @@ xfs_attr_inactive(xfs_inode_t *dp) error = 0; goto out; } - error = xfs_attr_root_inactive(&trans, dp); + error = xfs_attr3_root_inactive(&trans, dp); if (error) goto out; @@ -905,7 +905,7 @@ xfs_attr_leaf_addname(xfs_da_args_t *args) */ dp = args->dp; args->blkno = 0; - error = xfs_attr_leaf_read(args->trans, args->dp, args->blkno, -1, &bp); + error = xfs_attr3_leaf_read(args->trans, args->dp, args->blkno, -1, &bp); if (error) return error; @@ -913,14 +913,14 @@ xfs_attr_leaf_addname(xfs_da_args_t *args) * Look up the given attribute in the leaf block. Figure out if * the given flags produce an error or call for an atomic rename. */ - retval = xfs_attr_leaf_lookup_int(bp, args); + retval = xfs_attr3_leaf_lookup_int(bp, args); if ((args->flags & ATTR_REPLACE) && (retval == ENOATTR)) { xfs_trans_brelse(args->trans, bp); - return(retval); + return retval; } else if (retval == EEXIST) { if (args->flags & ATTR_CREATE) { /* pure create op */ xfs_trans_brelse(args->trans, bp); - return(retval); + return retval; } trace_xfs_attr_leaf_replace(args); @@ -936,7 +936,7 @@ xfs_attr_leaf_addname(xfs_da_args_t *args) * Add the attribute to the leaf block, transitioning to a Btree * if required. */ - retval = xfs_attr_leaf_add(bp, args); + retval = xfs_attr3_leaf_add(bp, args); if (retval == ENOSPC) { /* * Promote the attribute list to the Btree format, then @@ -944,7 +944,7 @@ xfs_attr_leaf_addname(xfs_da_args_t *args) * can manage its own transactions. */ xfs_bmap_init(args->flist, args->firstblock); - error = xfs_attr_leaf_to_node(args); + error = xfs_attr3_leaf_to_node(args); if (!error) { error = xfs_bmap_finish(&args->trans, args->flist, &committed); @@ -1009,7 +1009,7 @@ xfs_attr_leaf_addname(xfs_da_args_t *args) * In a separate transaction, set the incomplete flag on the * "old" attr and clear the incomplete flag on the "new" attr. */ - error = xfs_attr_leaf_flipflags(args); + error = xfs_attr3_leaf_flipflags(args); if (error) return(error); @@ -1031,19 +1031,19 @@ xfs_attr_leaf_addname(xfs_da_args_t *args) * Read in the block containing the "old" attr, then * remove the "old" attr from that block (neat, huh!) */ - error = xfs_attr_leaf_read(args->trans, args->dp, args->blkno, + error = xfs_attr3_leaf_read(args->trans, args->dp, args->blkno, -1, &bp); if (error) return error; - xfs_attr_leaf_remove(bp, args); + xfs_attr3_leaf_remove(bp, args); /* * If the result is small enough, shrink it all into the inode. */ if ((forkoff = xfs_attr_shortform_allfit(bp, dp))) { xfs_bmap_init(args->flist, args->firstblock); - error = xfs_attr_leaf_to_shortform(bp, args, forkoff); + error = xfs_attr3_leaf_to_shortform(bp, args, forkoff); /* bp is gone due to xfs_da_shrink_inode */ if (!error) { error = xfs_bmap_finish(&args->trans, @@ -1075,9 +1075,9 @@ xfs_attr_leaf_addname(xfs_da_args_t *args) /* * Added a "remote" value, just clear the incomplete flag. */ - error = xfs_attr_leaf_clearflag(args); + error = xfs_attr3_leaf_clearflag(args); } - return(error); + return error; } /* @@ -1100,24 +1100,24 @@ xfs_attr_leaf_removename(xfs_da_args_t *args) */ dp = args->dp; args->blkno = 0; - error = xfs_attr_leaf_read(args->trans, args->dp, args->blkno, -1, &bp); + error = xfs_attr3_leaf_read(args->trans, args->dp, args->blkno, -1, &bp); if (error) return error; - error = xfs_attr_leaf_lookup_int(bp, args); + error = xfs_attr3_leaf_lookup_int(bp, args); if (error == ENOATTR) { xfs_trans_brelse(args->trans, bp); - return(error); + return error; } - xfs_attr_leaf_remove(bp, args); + xfs_attr3_leaf_remove(bp, args); /* * If the result is small enough, shrink it all into the inode. */ if ((forkoff = xfs_attr_shortform_allfit(bp, dp))) { xfs_bmap_init(args->flist, args->firstblock); - error = xfs_attr_leaf_to_shortform(bp, args, forkoff); + error = xfs_attr3_leaf_to_shortform(bp, args, forkoff); /* bp is gone due to xfs_da_shrink_inode */ if (!error) { error = xfs_bmap_finish(&args->trans, args->flist, @@ -1127,7 +1127,7 @@ xfs_attr_leaf_removename(xfs_da_args_t *args) ASSERT(committed); args->trans = NULL; xfs_bmap_cancel(args->flist); - return(error); + return error; } /* @@ -1137,7 +1137,7 @@ xfs_attr_leaf_removename(xfs_da_args_t *args) if (committed) xfs_trans_ijoin(args->trans, dp, 0); } - return(0); + return 0; } /* @@ -1155,21 +1155,21 @@ xfs_attr_leaf_get(xfs_da_args_t *args) trace_xfs_attr_leaf_get(args); args->blkno = 0; - error = xfs_attr_leaf_read(args->trans, args->dp, args->blkno, -1, &bp); + error = xfs_attr3_leaf_read(args->trans, args->dp, args->blkno, -1, &bp); if (error) return error; - error = xfs_attr_leaf_lookup_int(bp, args); + error = xfs_attr3_leaf_lookup_int(bp, args); if (error != EEXIST) { xfs_trans_brelse(args->trans, bp); - return(error); + return error; } - error = xfs_attr_leaf_getvalue(bp, args); + error = xfs_attr3_leaf_getvalue(bp, args); xfs_trans_brelse(args->trans, bp); if (!error && (args->rmtblkno > 0) && !(args->flags & ATTR_KERNOVAL)) { error = xfs_attr_rmtval_get(args); } - return(error); + return error; } /* @@ -1184,11 +1184,11 @@ xfs_attr_leaf_list(xfs_attr_list_context_t *context) trace_xfs_attr_leaf_list(context); context->cursor->blkno = 0; - error = xfs_attr_leaf_read(NULL, context->dp, 0, -1, &bp); + error = xfs_attr3_leaf_read(NULL, context->dp, 0, -1, &bp); if (error) return XFS_ERROR(error); - error = xfs_attr_leaf_list_int(bp, context); + error = xfs_attr3_leaf_list_int(bp, context); xfs_trans_brelse(NULL, bp); return XFS_ERROR(error); } @@ -1257,7 +1257,7 @@ restart: args->rmtblkcnt = 0; } - retval = xfs_attr_leaf_add(blk->bp, state->args); + retval = xfs_attr3_leaf_add(blk->bp, state->args); if (retval == ENOSPC) { if (state->path.active == 1) { /* @@ -1267,7 +1267,7 @@ restart: */ xfs_da_state_free(state); xfs_bmap_init(args->flist, args->firstblock); - error = xfs_attr_leaf_to_node(args); + error = xfs_attr3_leaf_to_node(args); if (!error) { error = xfs_bmap_finish(&args->trans, args->flist, @@ -1369,7 +1369,7 @@ restart: * In a separate transaction, set the incomplete flag on the * "old" attr and clear the incomplete flag on the "new" attr. */ - error = xfs_attr_leaf_flipflags(args); + error = xfs_attr3_leaf_flipflags(args); if (error) goto out; @@ -1408,7 +1408,7 @@ restart: */ blk = &state->path.blk[ state->path.active-1 ]; ASSERT(blk->magic == XFS_ATTR_LEAF_MAGIC); - error = xfs_attr_leaf_remove(blk->bp, args); + error = xfs_attr3_leaf_remove(blk->bp, args); xfs_da3_fixhashpath(state, &state->path); /* @@ -1449,7 +1449,7 @@ restart: /* * Added a "remote" value, just clear the incomplete flag. */ - error = xfs_attr_leaf_clearflag(args); + error = xfs_attr3_leaf_clearflag(args); if (error) goto out; } @@ -1523,7 +1523,7 @@ xfs_attr_node_removename(xfs_da_args_t *args) * Mark the attribute as INCOMPLETE, then bunmapi() the * remote value. */ - error = xfs_attr_leaf_setflag(args); + error = xfs_attr3_leaf_setflag(args); if (error) goto out; error = xfs_attr_rmtval_remove(args); @@ -1544,7 +1544,7 @@ xfs_attr_node_removename(xfs_da_args_t *args) */ blk = &state->path.blk[ state->path.active-1 ]; ASSERT(blk->magic == XFS_ATTR_LEAF_MAGIC); - retval = xfs_attr_leaf_remove(blk->bp, args); + retval = xfs_attr3_leaf_remove(blk->bp, args); xfs_da3_fixhashpath(state, &state->path); /* @@ -1590,13 +1590,13 @@ xfs_attr_node_removename(xfs_da_args_t *args) ASSERT(state->path.blk[0].bp); state->path.blk[0].bp = NULL; - error = xfs_attr_leaf_read(args->trans, args->dp, 0, -1, &bp); + error = xfs_attr3_leaf_read(args->trans, args->dp, 0, -1, &bp); if (error) goto out; if ((forkoff = xfs_attr_shortform_allfit(bp, dp))) { xfs_bmap_init(args->flist, args->firstblock); - error = xfs_attr_leaf_to_shortform(bp, args, forkoff); + error = xfs_attr3_leaf_to_shortform(bp, args, forkoff); /* bp is gone due to xfs_da_shrink_inode */ if (!error) { error = xfs_bmap_finish(&args->trans, @@ -1768,7 +1768,7 @@ xfs_attr_node_get(xfs_da_args_t *args) /* * Get the value, local or "remote" */ - retval = xfs_attr_leaf_getvalue(blk->bp, args); + retval = xfs_attr3_leaf_getvalue(blk->bp, args); if (!retval && (args->rmtblkno > 0) && !(args->flags & ATTR_KERNOVAL)) { retval = xfs_attr_rmtval_get(args); @@ -1793,7 +1793,9 @@ xfs_attr_node_list(xfs_attr_list_context_t *context) attrlist_cursor_kern_t *cursor; xfs_attr_leafblock_t *leaf; xfs_da_intnode_t *node; - xfs_da_node_entry_t *btree; + struct xfs_attr3_icleaf_hdr leafhdr; + struct xfs_da3_icnode_hdr nodehdr; + struct xfs_da_node_entry *btree; int error, i; struct xfs_buf *bp; @@ -1814,22 +1816,28 @@ xfs_attr_node_list(xfs_attr_list_context_t *context) if ((error != 0) && (error != EFSCORRUPTED)) return(error); if (bp) { + struct xfs_attr_leaf_entry *entries; + node = bp->b_addr; switch (be16_to_cpu(node->hdr.info.magic)) { case XFS_DA_NODE_MAGIC: + case XFS_DA3_NODE_MAGIC: trace_xfs_attr_list_wrong_blk(context); xfs_trans_brelse(NULL, bp); bp = NULL; break; case XFS_ATTR_LEAF_MAGIC: + case XFS_ATTR3_LEAF_MAGIC: leaf = bp->b_addr; - if (cursor->hashval > be32_to_cpu(leaf->entries[ - be16_to_cpu(leaf->hdr.count)-1].hashval)) { + xfs_attr3_leaf_hdr_from_disk(&leafhdr, leaf); + entries = xfs_attr3_leaf_entryp(leaf); + if (cursor->hashval > be32_to_cpu( + entries[leafhdr.count - 1].hashval)) { trace_xfs_attr_list_wrong_blk(context); xfs_trans_brelse(NULL, bp); bp = NULL; - } else if (cursor->hashval <= - be32_to_cpu(leaf->entries[0].hashval)) { + } else if (cursor->hashval <= be32_to_cpu( + entries[0].hashval)) { trace_xfs_attr_list_wrong_blk(context); xfs_trans_brelse(NULL, bp); bp = NULL; @@ -1851,27 +1859,31 @@ xfs_attr_node_list(xfs_attr_list_context_t *context) if (bp == NULL) { cursor->blkno = 0; for (;;) { + __uint16_t magic; + error = xfs_da3_node_read(NULL, context->dp, cursor->blkno, -1, &bp, XFS_ATTR_FORK); if (error) return(error); node = bp->b_addr; - if (node->hdr.info.magic == - cpu_to_be16(XFS_ATTR_LEAF_MAGIC)) + magic = be16_to_cpu(node->hdr.info.magic); + if (magic == XFS_ATTR_LEAF_MAGIC || + magic == XFS_ATTR3_LEAF_MAGIC) break; - if (unlikely(node->hdr.info.magic != - cpu_to_be16(XFS_DA_NODE_MAGIC))) { + if (magic != XFS_DA_NODE_MAGIC && + magic != XFS_DA3_NODE_MAGIC) { XFS_CORRUPTION_ERROR("xfs_attr_node_list(3)", XFS_ERRLEVEL_LOW, context->dp->i_mount, node); xfs_trans_brelse(NULL, bp); - return(XFS_ERROR(EFSCORRUPTED)); + return XFS_ERROR(EFSCORRUPTED); } + + xfs_da3_node_hdr_from_disk(&nodehdr, node); btree = xfs_da3_node_tree_p(node); - for (i = 0; i < be16_to_cpu(node->hdr.count); - btree++, i++) { + for (i = 0; i < nodehdr.count; btree++, i++) { if (cursor->hashval <= be32_to_cpu(btree->hashval)) { cursor->blkno = be32_to_cpu(btree->before); @@ -1880,9 +1892,9 @@ xfs_attr_node_list(xfs_attr_list_context_t *context) break; } } - if (i == be16_to_cpu(node->hdr.count)) { + if (i == nodehdr.count) { xfs_trans_brelse(NULL, bp); - return(0); + return 0; } xfs_trans_brelse(NULL, bp); } @@ -1896,22 +1908,23 @@ xfs_attr_node_list(xfs_attr_list_context_t *context) */ for (;;) { leaf = bp->b_addr; - error = xfs_attr_leaf_list_int(bp, context); + error = xfs_attr3_leaf_list_int(bp, context); if (error) { xfs_trans_brelse(NULL, bp); return error; } - if (context->seen_enough || leaf->hdr.info.forw == 0) + xfs_attr3_leaf_hdr_from_disk(&leafhdr, leaf); + if (context->seen_enough || leafhdr.forw == 0) break; - cursor->blkno = be32_to_cpu(leaf->hdr.info.forw); + cursor->blkno = leafhdr.forw; xfs_trans_brelse(NULL, bp); - error = xfs_attr_leaf_read(NULL, context->dp, cursor->blkno, -1, + error = xfs_attr3_leaf_read(NULL, context->dp, cursor->blkno, -1, &bp); if (error) return error; } xfs_trans_brelse(NULL, bp); - return(0); + return 0; } diff --git a/fs/xfs/xfs_attr_leaf.c b/fs/xfs/xfs_attr_leaf.c index 54b0dc8..9c18451 100644 --- a/fs/xfs/xfs_attr_leaf.c +++ b/fs/xfs/xfs_attr_leaf.c @@ -1,5 +1,6 @@ /* * Copyright (c) 2000-2005 Silicon Graphics, Inc. + * Copyright (c) 2013 Red Hat, Inc. * All Rights Reserved. * * This program is free software; you can redistribute it and/or @@ -39,6 +40,9 @@ #include "xfs_attr_leaf.h" #include "xfs_error.h" #include "xfs_trace.h" +#include "xfs_buf_item.h" +#include "xfs_cksum.h" + /* * xfs_attr_leaf.c @@ -53,77 +57,213 @@ /* * Routines used for growing the Btree. */ -STATIC int xfs_attr_leaf_create(xfs_da_args_t *args, xfs_dablk_t which_block, - struct xfs_buf **bpp); -STATIC int xfs_attr_leaf_add_work(struct xfs_buf *leaf_buffer, - xfs_da_args_t *args, int freemap_index); -STATIC void xfs_attr_leaf_compact(struct xfs_da_args *args, - struct xfs_buf *leaf_buffer); -STATIC void xfs_attr_leaf_rebalance(xfs_da_state_t *state, +STATIC int xfs_attr3_leaf_create(struct xfs_da_args *args, + xfs_dablk_t which_block, struct xfs_buf **bpp); +STATIC int xfs_attr3_leaf_add_work(struct xfs_buf *leaf_buffer, + struct xfs_attr3_icleaf_hdr *ichdr, + struct xfs_da_args *args, int freemap_index); +STATIC void xfs_attr3_leaf_compact(struct xfs_da_args *args, + struct xfs_attr3_icleaf_hdr *ichdr, + struct xfs_buf *leaf_buffer); +STATIC void xfs_attr3_leaf_rebalance(xfs_da_state_t *state, xfs_da_state_blk_t *blk1, xfs_da_state_blk_t *blk2); -STATIC int xfs_attr_leaf_figure_balance(xfs_da_state_t *state, - xfs_da_state_blk_t *leaf_blk_1, - xfs_da_state_blk_t *leaf_blk_2, - int *number_entries_in_blk1, - int *number_usedbytes_in_blk1); +STATIC int xfs_attr3_leaf_figure_balance(xfs_da_state_t *state, + xfs_da_state_blk_t *leaf_blk_1, + struct xfs_attr3_icleaf_hdr *ichdr1, + xfs_da_state_blk_t *leaf_blk_2, + struct xfs_attr3_icleaf_hdr *ichdr2, + int *number_entries_in_blk1, + int *number_usedbytes_in_blk1); /* * Routines used for shrinking the Btree. */ -STATIC int xfs_attr_node_inactive(xfs_trans_t **trans, xfs_inode_t *dp, +STATIC int xfs_attr3_node_inactive(xfs_trans_t **trans, xfs_inode_t *dp, struct xfs_buf *bp, int level); -STATIC int xfs_attr_leaf_inactive(xfs_trans_t **trans, xfs_inode_t *dp, +STATIC int xfs_attr3_leaf_inactive(xfs_trans_t **trans, xfs_inode_t *dp, struct xfs_buf *bp); -STATIC int xfs_attr_leaf_freextent(xfs_trans_t **trans, xfs_inode_t *dp, +STATIC int xfs_attr3_leaf_freextent(xfs_trans_t **trans, xfs_inode_t *dp, xfs_dablk_t blkno, int blkcnt); /* * Utility routines. */ -STATIC void xfs_attr_leaf_moveents(xfs_attr_leafblock_t *src_leaf, - int src_start, - xfs_attr_leafblock_t *dst_leaf, - int dst_start, int move_count, - xfs_mount_t *mp); +STATIC void xfs_attr3_leaf_moveents(struct xfs_attr_leafblock *src_leaf, + struct xfs_attr3_icleaf_hdr *src_ichdr, int src_start, + struct xfs_attr_leafblock *dst_leaf, + struct xfs_attr3_icleaf_hdr *dst_ichdr, int dst_start, + int move_count, struct xfs_mount *mp); STATIC int xfs_attr_leaf_entsize(xfs_attr_leafblock_t *leaf, int index); -static void -xfs_attr_leaf_verify( +void +xfs_attr3_leaf_hdr_from_disk( + struct xfs_attr3_icleaf_hdr *to, + struct xfs_attr_leafblock *from) +{ + int i; + + ASSERT(from->hdr.info.magic == cpu_to_be16(XFS_ATTR_LEAF_MAGIC) || + from->hdr.info.magic == cpu_to_be16(XFS_ATTR3_LEAF_MAGIC)); + + if (from->hdr.info.magic == cpu_to_be16(XFS_ATTR3_LEAF_MAGIC)) { + struct xfs_attr3_leaf_hdr *hdr3 = (struct xfs_attr3_leaf_hdr *)from; + + to->forw = be32_to_cpu(hdr3->info.hdr.forw); + to->back = be32_to_cpu(hdr3->info.hdr.back); + to->magic = be16_to_cpu(hdr3->info.hdr.magic); + to->count = be16_to_cpu(hdr3->count); + to->usedbytes = be16_to_cpu(hdr3->usedbytes); + to->firstused = be16_to_cpu(hdr3->firstused); + to->holes = hdr3->holes; + + for (i = 0; i < XFS_ATTR_LEAF_MAPSIZE; i++) { + to->freemap[i].base = be16_to_cpu(hdr3->freemap[i].base); + to->freemap[i].size = be16_to_cpu(hdr3->freemap[i].size); + } + return; + } + to->forw = be32_to_cpu(from->hdr.info.forw); + to->back = be32_to_cpu(from->hdr.info.back); + to->magic = be16_to_cpu(from->hdr.info.magic); + to->count = be16_to_cpu(from->hdr.count); + to->usedbytes = be16_to_cpu(from->hdr.usedbytes); + to->firstused = be16_to_cpu(from->hdr.firstused); + to->holes = from->hdr.holes; + + for (i = 0; i < XFS_ATTR_LEAF_MAPSIZE; i++) { + to->freemap[i].base = be16_to_cpu(from->hdr.freemap[i].base); + to->freemap[i].size = be16_to_cpu(from->hdr.freemap[i].size); + } +} + +void +xfs_attr3_leaf_hdr_to_disk( + struct xfs_attr_leafblock *to, + struct xfs_attr3_icleaf_hdr *from) +{ + int i; + + ASSERT(from->magic == XFS_ATTR_LEAF_MAGIC || + from->magic == XFS_ATTR3_LEAF_MAGIC); + + if (from->magic == XFS_ATTR3_LEAF_MAGIC) { + struct xfs_attr3_leaf_hdr *hdr3 = (struct xfs_attr3_leaf_hdr *)to; + + hdr3->info.hdr.forw = cpu_to_be32(from->forw); + hdr3->info.hdr.back = cpu_to_be32(from->back); + hdr3->info.hdr.magic = cpu_to_be16(from->magic); + hdr3->count = cpu_to_be16(from->count); + hdr3->usedbytes = cpu_to_be16(from->usedbytes); + hdr3->firstused = cpu_to_be16(from->firstused); + hdr3->holes = from->holes; + hdr3->pad1 = 0; + + for (i = 0; i < XFS_ATTR_LEAF_MAPSIZE; i++) { + hdr3->freemap[i].base = cpu_to_be16(from->freemap[i].base); + hdr3->freemap[i].size = cpu_to_be16(from->freemap[i].size); + } + return; + } + to->hdr.info.forw = cpu_to_be32(from->forw); + to->hdr.info.back = cpu_to_be32(from->back); + to->hdr.info.magic = cpu_to_be16(from->magic); + to->hdr.count = cpu_to_be16(from->count); + to->hdr.usedbytes = cpu_to_be16(from->usedbytes); + to->hdr.firstused = cpu_to_be16(from->firstused); + to->hdr.holes = from->holes; + to->hdr.pad1 = 0; + + for (i = 0; i < XFS_ATTR_LEAF_MAPSIZE; i++) { + to->hdr.freemap[i].base = cpu_to_be16(from->freemap[i].base); + to->hdr.freemap[i].size = cpu_to_be16(from->freemap[i].size); + } +} + +static bool +xfs_attr3_leaf_verify( struct xfs_buf *bp) { struct xfs_mount *mp = bp->b_target->bt_mount; - struct xfs_attr_leaf_hdr *hdr = bp->b_addr; - int block_ok = 0; + struct xfs_attr_leafblock *leaf = bp->b_addr; + struct xfs_attr3_icleaf_hdr ichdr; - block_ok = hdr->info.magic == cpu_to_be16(XFS_ATTR_LEAF_MAGIC); - if (!block_ok) { - XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, mp, hdr); - xfs_buf_ioerror(bp, EFSCORRUPTED); + xfs_attr3_leaf_hdr_from_disk(&ichdr, leaf); + + if (xfs_sb_version_hascrc(&mp->m_sb)) { + struct xfs_da3_node_hdr *hdr3 = bp->b_addr; + + if (ichdr.magic != XFS_ATTR3_LEAF_MAGIC) + return false; + + if (!uuid_equal(&hdr3->info.uuid, &mp->m_sb.sb_uuid)) + return false; + if (be64_to_cpu(hdr3->info.blkno) != bp->b_bn) + return false; + } else { + if (ichdr.magic != XFS_ATTR_LEAF_MAGIC) + return false; } + if (ichdr.count == 0) + return false; + + /* XXX: need to range check rest of attr header values */ + /* XXX: hash order check? */ + + return true; } static void -xfs_attr_leaf_read_verify( +xfs_attr3_leaf_write_verify( struct xfs_buf *bp) { - xfs_attr_leaf_verify(bp); + struct xfs_mount *mp = bp->b_target->bt_mount; + struct xfs_buf_log_item *bip = bp->b_fspriv; + struct xfs_attr3_leaf_hdr *hdr3 = bp->b_addr; + + if (!xfs_attr3_leaf_verify(bp)) { + XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, mp, bp->b_addr); + xfs_buf_ioerror(bp, EFSCORRUPTED); + return; + } + + if (!xfs_sb_version_hascrc(&mp->m_sb)) + return; + + if (bip) + hdr3->info.lsn = cpu_to_be64(bip->bli_item.li_lsn); + + xfs_update_cksum(bp->b_addr, BBTOB(bp->b_length), XFS_ATTR3_LEAF_CRC_OFF); } +/* + * leaf/node format detection on trees is sketchy, so a node read can be done on + * leaf level blocks when detection identifies the tree as a node format tree + * incorrectly. In this case, we need to swap the verifier to match the correct + * format of the block being read. + */ static void -xfs_attr_leaf_write_verify( - struct xfs_buf *bp) +xfs_attr3_leaf_read_verify( + struct xfs_buf *bp) { - xfs_attr_leaf_verify(bp); + struct xfs_mount *mp = bp->b_target->bt_mount; + + if ((xfs_sb_version_hascrc(&mp->m_sb) && + !xfs_verify_cksum(bp->b_addr, BBTOB(bp->b_length), + XFS_ATTR3_LEAF_CRC_OFF)) || + !xfs_attr3_leaf_verify(bp)) { + XFS_CORRUPTION_ERROR(__func__, XFS_ERRLEVEL_LOW, mp, bp->b_addr); + xfs_buf_ioerror(bp, EFSCORRUPTED); + } } -const struct xfs_buf_ops xfs_attr_leaf_buf_ops = { - .verify_read = xfs_attr_leaf_read_verify, - .verify_write = xfs_attr_leaf_write_verify, +const struct xfs_buf_ops xfs_attr3_leaf_buf_ops = { + .verify_read = xfs_attr3_leaf_read_verify, + .verify_write = xfs_attr3_leaf_write_verify, }; int -xfs_attr_leaf_read( +xfs_attr3_leaf_read( struct xfs_trans *tp, struct xfs_inode *dp, xfs_dablk_t bno, @@ -131,7 +271,7 @@ xfs_attr_leaf_read( struct xfs_buf **bpp) { return xfs_da_read_buf(tp, dp, bno, mappedbno, bpp, - XFS_ATTR_FORK, &xfs_attr_leaf_buf_ops); + XFS_ATTR_FORK, &xfs_attr3_leaf_buf_ops); } /*======================================================================== @@ -559,7 +699,7 @@ xfs_attr_shortform_to_leaf(xfs_da_args_t *args) } ASSERT(blkno == 0); - error = xfs_attr_leaf_create(args, blkno, &bp); + error = xfs_attr3_leaf_create(args, blkno, &bp); if (error) { error = xfs_da_shrink_inode(args, 0, bp); bp = NULL; @@ -588,9 +728,9 @@ xfs_attr_shortform_to_leaf(xfs_da_args_t *args) nargs.hashval = xfs_da_hashname(sfe->nameval, sfe->namelen); nargs.flags = XFS_ATTR_NSP_ONDISK_TO_ARGS(sfe->flags); - error = xfs_attr_leaf_lookup_int(bp, &nargs); /* set a->index */ + error = xfs_attr3_leaf_lookup_int(bp, &nargs); /* set a->index */ ASSERT(error == ENOATTR); - error = xfs_attr_leaf_add(bp, &nargs); + error = xfs_attr3_leaf_add(bp, &nargs); ASSERT(error != ENOSPC); if (error) goto out; @@ -803,7 +943,7 @@ xfs_attr_shortform_allfit( continue; /* don't copy partial entries */ if (!(entry->flags & XFS_ATTR_LOCAL)) return(0); - name_loc = xfs_attr_leaf_name_local(leaf, i); + name_loc = xfs_attr3_leaf_name_local(leaf, i); if (name_loc->namelen >= XFS_ATTR_SF_ENTSIZE_MAX) return(0); if (be16_to_cpu(name_loc->valuelen) >= XFS_ATTR_SF_ENTSIZE_MAX) @@ -823,29 +963,34 @@ xfs_attr_shortform_allfit( * Convert a leaf attribute list to shortform attribute list */ int -xfs_attr_leaf_to_shortform( - struct xfs_buf *bp, - xfs_da_args_t *args, - int forkoff) +xfs_attr3_leaf_to_shortform( + struct xfs_buf *bp, + struct xfs_da_args *args, + int forkoff) { - xfs_attr_leafblock_t *leaf; - xfs_attr_leaf_entry_t *entry; - xfs_attr_leaf_name_local_t *name_loc; - xfs_da_args_t nargs; - xfs_inode_t *dp; - char *tmpbuffer; - int error, i; + struct xfs_attr_leafblock *leaf; + struct xfs_attr3_icleaf_hdr ichdr; + struct xfs_attr_leaf_entry *entry; + struct xfs_attr_leaf_name_local *name_loc; + struct xfs_da_args nargs; + struct xfs_inode *dp = args->dp; + char *tmpbuffer; + int error; + int i; trace_xfs_attr_leaf_to_sf(args); - dp = args->dp; tmpbuffer = kmem_alloc(XFS_LBSIZE(dp->i_mount), KM_SLEEP); - ASSERT(tmpbuffer != NULL); + if (!tmpbuffer) + return ENOMEM; - ASSERT(bp != NULL); memcpy(tmpbuffer, bp->b_addr, XFS_LBSIZE(dp->i_mount)); + leaf = (xfs_attr_leafblock_t *)tmpbuffer; - ASSERT(leaf->hdr.info.magic == cpu_to_be16(XFS_ATTR_LEAF_MAGIC)); + xfs_attr3_leaf_hdr_from_disk(&ichdr, leaf); + entry = xfs_attr3_leaf_entryp(leaf); + + /* XXX (dgc): buffer is about to be marked stale - why zero it? */ memset(bp->b_addr, 0, XFS_LBSIZE(dp->i_mount)); /* @@ -875,14 +1020,14 @@ xfs_attr_leaf_to_shortform( nargs.whichfork = XFS_ATTR_FORK; nargs.trans = args->trans; nargs.op_flags = XFS_DA_OP_OKNOENT; - entry = &leaf->entries[0]; - for (i = 0; i < be16_to_cpu(leaf->hdr.count); entry++, i++) { + + for (i = 0; i < ichdr.count; entry++, i++) { if (entry->flags & XFS_ATTR_INCOMPLETE) continue; /* don't copy partial entries */ if (!entry->nameidx) continue; ASSERT(entry->flags & XFS_ATTR_LOCAL); - name_loc = xfs_attr_leaf_name_local(leaf, i); + name_loc = xfs_attr3_leaf_name_local(leaf, i); nargs.name = name_loc->nameval; nargs.namelen = name_loc->namelen; nargs.value = &name_loc->nameval[nargs.namelen]; @@ -895,43 +1040,50 @@ xfs_attr_leaf_to_shortform( out: kmem_free(tmpbuffer); - return(error); + return error; } /* * Convert from using a single leaf to a root node and a leaf. */ int -xfs_attr_leaf_to_node(xfs_da_args_t *args) +xfs_attr3_leaf_to_node( + struct xfs_da_args *args) { - xfs_attr_leafblock_t *leaf; - xfs_da_intnode_t *node; - xfs_inode_t *dp; - struct xfs_buf *bp1, *bp2; - xfs_dablk_t blkno; - int error; + struct xfs_attr_leafblock *leaf; + struct xfs_attr3_icleaf_hdr icleafhdr; + struct xfs_attr_leaf_entry *entries; struct xfs_da_node_entry *btree; + struct xfs_da3_icnode_hdr icnodehdr; + struct xfs_da_intnode *node; + struct xfs_inode *dp = args->dp; + struct xfs_mount *mp = dp->i_mount; + struct xfs_buf *bp1 = NULL; + struct xfs_buf *bp2 = NULL; + xfs_dablk_t blkno; + int error; trace_xfs_attr_leaf_to_node(args); - dp = args->dp; - bp1 = bp2 = NULL; error = xfs_da_grow_inode(args, &blkno); if (error) goto out; - error = xfs_attr_leaf_read(args->trans, args->dp, 0, -1, &bp1); + error = xfs_attr3_leaf_read(args->trans, dp, 0, -1, &bp1); if (error) goto out; - bp2 = NULL; - error = xfs_da_get_buf(args->trans, args->dp, blkno, -1, &bp2, - XFS_ATTR_FORK); + error = xfs_da_get_buf(args->trans, dp, blkno, -1, &bp2, XFS_ATTR_FORK); if (error) goto out; + + /* copy leaf to new buffer, update identifiers */ bp2->b_ops = bp1->b_ops; - memcpy(bp2->b_addr, bp1->b_addr, XFS_LBSIZE(dp->i_mount)); - bp1 = NULL; - xfs_trans_log_buf(args->trans, bp2, 0, XFS_LBSIZE(dp->i_mount) - 1); + memcpy(bp2->b_addr, bp1->b_addr, XFS_LBSIZE(mp)); + if (xfs_sb_version_hascrc(&mp->m_sb)) { + struct xfs_da3_blkinfo *hdr3 = bp2->b_addr; + hdr3->blkno = cpu_to_be64(bp2->b_bn); + } + xfs_trans_log_buf(args->trans, bp2, 0, XFS_LBSIZE(mp) - 1); /* * Set up the new root node. @@ -940,17 +1092,22 @@ xfs_attr_leaf_to_node(xfs_da_args_t *args) if (error) goto out; node = bp1->b_addr; + xfs_da3_node_hdr_from_disk(&icnodehdr, node); + btree = xfs_da3_node_tree_p(node); + leaf = bp2->b_addr; - ASSERT(leaf->hdr.info.magic == cpu_to_be16(XFS_ATTR_LEAF_MAGIC)); + xfs_attr3_leaf_hdr_from_disk(&icleafhdr, leaf); + entries = xfs_attr3_leaf_entryp(leaf); + /* both on-disk, don't endian-flip twice */ - btree = xfs_da3_node_tree_p(node); - btree[0].hashval = leaf->entries[be16_to_cpu(leaf->hdr.count)-1 ].hashval; + btree[0].hashval = entries[icleafhdr.count - 1].hashval; btree[0].before = cpu_to_be32(blkno); - node->hdr.count = cpu_to_be16(1); - xfs_trans_log_buf(args->trans, bp1, 0, XFS_LBSIZE(dp->i_mount) - 1); + icnodehdr.count = 1; + xfs_da3_node_hdr_to_disk(node, &icnodehdr); + xfs_trans_log_buf(args->trans, bp1, 0, XFS_LBSIZE(mp) - 1); error = 0; out: - return(error); + return error; } @@ -963,52 +1120,62 @@ out: * or a leaf in a node attribute list. */ STATIC int -xfs_attr_leaf_create( - xfs_da_args_t *args, - xfs_dablk_t blkno, - struct xfs_buf **bpp) +xfs_attr3_leaf_create( + struct xfs_da_args *args, + xfs_dablk_t blkno, + struct xfs_buf **bpp) { - xfs_attr_leafblock_t *leaf; - xfs_attr_leaf_hdr_t *hdr; - xfs_inode_t *dp; - struct xfs_buf *bp; - int error; + struct xfs_attr_leafblock *leaf; + struct xfs_attr3_icleaf_hdr ichdr; + struct xfs_inode *dp = args->dp; + struct xfs_mount *mp = dp->i_mount; + struct xfs_buf *bp; + int error; trace_xfs_attr_leaf_create(args); - dp = args->dp; - ASSERT(dp != NULL); error = xfs_da_get_buf(args->trans, args->dp, blkno, -1, &bp, XFS_ATTR_FORK); if (error) - return(error); - bp->b_ops = &xfs_attr_leaf_buf_ops; + return error; + bp->b_ops = &xfs_attr3_leaf_buf_ops; leaf = bp->b_addr; - memset((char *)leaf, 0, XFS_LBSIZE(dp->i_mount)); - hdr = &leaf->hdr; - hdr->info.magic = cpu_to_be16(XFS_ATTR_LEAF_MAGIC); - hdr->firstused = cpu_to_be16(XFS_LBSIZE(dp->i_mount)); - if (!hdr->firstused) { - hdr->firstused = cpu_to_be16( - XFS_LBSIZE(dp->i_mount) - XFS_ATTR_LEAF_NAME_ALIGN); - } + memset(leaf, 0, XFS_LBSIZE(mp)); - hdr->freemap[0].base = cpu_to_be16(sizeof(xfs_attr_leaf_hdr_t)); - hdr->freemap[0].size = cpu_to_be16(be16_to_cpu(hdr->firstused) - - sizeof(xfs_attr_leaf_hdr_t)); + memset(&ichdr, 0, sizeof(ichdr)); + ichdr.firstused = XFS_LBSIZE(mp); + + if (xfs_sb_version_hascrc(&mp->m_sb)) { + struct xfs_da3_blkinfo *hdr3 = bp->b_addr; + + ichdr.magic = XFS_ATTR3_LEAF_MAGIC; + + hdr3->blkno = cpu_to_be64(bp->b_bn); + hdr3->owner = cpu_to_be64(dp->i_ino); + uuid_copy(&hdr3->uuid, &mp->m_sb.sb_uuid); + + ichdr.freemap[0].base = sizeof(struct xfs_attr3_leaf_hdr); + } else { + ichdr.magic = XFS_ATTR_LEAF_MAGIC; + ichdr.freemap[0].base = sizeof(struct xfs_attr_leaf_hdr); + } + ichdr.freemap[0].size = ichdr.firstused - ichdr.freemap[0].base; - xfs_trans_log_buf(args->trans, bp, 0, XFS_LBSIZE(dp->i_mount) - 1); + xfs_attr3_leaf_hdr_to_disk(leaf, &ichdr); + xfs_trans_log_buf(args->trans, bp, 0, XFS_LBSIZE(mp) - 1); *bpp = bp; - return(0); + return 0; } /* * Split the leaf node, rebalance, then add the new entry. */ int -xfs_attr_leaf_split(xfs_da_state_t *state, xfs_da_state_blk_t *oldblk, - xfs_da_state_blk_t *newblk) +xfs_attr3_leaf_split( + struct xfs_da_state *state, + struct xfs_da_state_blk *oldblk, + struct xfs_da_state_blk *newblk) { xfs_dablk_t blkno; int error; @@ -1022,7 +1189,7 @@ xfs_attr_leaf_split(xfs_da_state_t *state, xfs_da_state_blk_t *oldblk, error = xfs_da_grow_inode(state->args, &blkno); if (error) return(error); - error = xfs_attr_leaf_create(state->args, blkno, &newblk->bp); + error = xfs_attr3_leaf_create(state->args, blkno, &newblk->bp); if (error) return(error); newblk->blkno = blkno; @@ -1032,7 +1199,7 @@ xfs_attr_leaf_split(xfs_da_state_t *state, xfs_da_state_blk_t *oldblk, * Rebalance the entries across the two leaves. * NOTE: rebalance() currently depends on the 2nd block being empty. */ - xfs_attr_leaf_rebalance(state, oldblk, newblk); + xfs_attr3_leaf_rebalance(state, oldblk, newblk); error = xfs_da3_blk_link(state, oldblk, newblk); if (error) return(error); @@ -1046,10 +1213,10 @@ xfs_attr_leaf_split(xfs_da_state_t *state, xfs_da_state_blk_t *oldblk, */ if (state->inleaf) { trace_xfs_attr_leaf_add_old(state->args); - error = xfs_attr_leaf_add(oldblk->bp, state->args); + error = xfs_attr3_leaf_add(oldblk->bp, state->args); } else { trace_xfs_attr_leaf_add_new(state->args); - error = xfs_attr_leaf_add(newblk->bp, state->args); + error = xfs_attr3_leaf_add(newblk->bp, state->args); } /* @@ -1064,22 +1231,23 @@ xfs_attr_leaf_split(xfs_da_state_t *state, xfs_da_state_blk_t *oldblk, * Add a name to the leaf attribute list structure. */ int -xfs_attr_leaf_add( +xfs_attr3_leaf_add( struct xfs_buf *bp, struct xfs_da_args *args) { - xfs_attr_leafblock_t *leaf; - xfs_attr_leaf_hdr_t *hdr; - xfs_attr_leaf_map_t *map; - int tablesize, entsize, sum, tmp, i; + struct xfs_attr_leafblock *leaf; + struct xfs_attr3_icleaf_hdr ichdr; + int tablesize; + int entsize; + int sum; + int tmp; + int i; trace_xfs_attr_leaf_add(args); leaf = bp->b_addr; - ASSERT(leaf->hdr.info.magic == cpu_to_be16(XFS_ATTR_LEAF_MAGIC)); - ASSERT((args->index >= 0) - && (args->index <= be16_to_cpu(leaf->hdr.count))); - hdr = &leaf->hdr; + xfs_attr3_leaf_hdr_from_disk(&ichdr, leaf); + ASSERT(args->index >= 0 && args->index <= ichdr.count); entsize = xfs_attr_leaf_newentsize(args->namelen, args->valuelen, args->trans->t_mountp->m_sb.sb_blocksize, NULL); @@ -1087,25 +1255,23 @@ xfs_attr_leaf_add( * Search through freemap for first-fit on new name length. * (may need to figure in size of entry struct too) */ - tablesize = (be16_to_cpu(hdr->count) + 1) - * sizeof(xfs_attr_leaf_entry_t) - + sizeof(xfs_attr_leaf_hdr_t); - map = &hdr->freemap[XFS_ATTR_LEAF_MAPSIZE-1]; - for (sum = 0, i = XFS_ATTR_LEAF_MAPSIZE-1; i >= 0; map--, i--) { - if (tablesize > be16_to_cpu(hdr->firstused)) { - sum += be16_to_cpu(map->size); + tablesize = (ichdr.count + 1) * sizeof(xfs_attr_leaf_entry_t) + + xfs_attr3_leaf_hdr_size(leaf); + for (sum = 0, i = XFS_ATTR_LEAF_MAPSIZE - 1; i >= 0; i--) { + if (tablesize > ichdr.firstused) { + sum += ichdr.freemap[i].size; continue; } - if (!map->size) + if (!ichdr.freemap[i].size) continue; /* no space in this map */ tmp = entsize; - if (be16_to_cpu(map->base) < be16_to_cpu(hdr->firstused)) + if (ichdr.freemap[i].base < ichdr.firstused) tmp += sizeof(xfs_attr_leaf_entry_t); - if (be16_to_cpu(map->size) >= tmp) { - tmp = xfs_attr_leaf_add_work(bp, args, i); - return(tmp); + if (ichdr.freemap[i].size >= tmp) { + tmp = xfs_attr3_leaf_add_work(bp, &ichdr, args, i); + goto out_log_hdr; } - sum += be16_to_cpu(map->size); + sum += ichdr.freemap[i].size; } /* @@ -1113,82 +1279,90 @@ xfs_attr_leaf_add( * and we don't have enough freespace, then compaction will do us * no good and we should just give up. */ - if (!hdr->holes && (sum < entsize)) - return(XFS_ERROR(ENOSPC)); + if (!ichdr.holes && sum < entsize) + return XFS_ERROR(ENOSPC); /* * Compact the entries to coalesce free space. * This may change the hdr->count via dropping INCOMPLETE entries. */ - xfs_attr_leaf_compact(args, bp); + xfs_attr3_leaf_compact(args, &ichdr, bp); /* * After compaction, the block is guaranteed to have only one * free region, in freemap[0]. If it is not big enough, give up. */ - if (be16_to_cpu(hdr->freemap[0].size) - < (entsize + sizeof(xfs_attr_leaf_entry_t))) - return(XFS_ERROR(ENOSPC)); + if (ichdr.freemap[0].size < (entsize + sizeof(xfs_attr_leaf_entry_t))) { + tmp = ENOSPC; + goto out_log_hdr; + } + + tmp = xfs_attr3_leaf_add_work(bp, &ichdr, args, 0); - return(xfs_attr_leaf_add_work(bp, args, 0)); +out_log_hdr: + xfs_attr3_leaf_hdr_to_disk(leaf, &ichdr); + xfs_trans_log_buf(args->trans, bp, + XFS_DA_LOGRANGE(leaf, &leaf->hdr, + xfs_attr3_leaf_hdr_size(leaf))); + return tmp; } /* * Add a name to a leaf attribute list structure. */ STATIC int -xfs_attr_leaf_add_work( - struct xfs_buf *bp, - xfs_da_args_t *args, - int mapindex) +xfs_attr3_leaf_add_work( + struct xfs_buf *bp, + struct xfs_attr3_icleaf_hdr *ichdr, + struct xfs_da_args *args, + int mapindex) { - xfs_attr_leafblock_t *leaf; - xfs_attr_leaf_hdr_t *hdr; - xfs_attr_leaf_entry_t *entry; - xfs_attr_leaf_name_local_t *name_loc; - xfs_attr_leaf_name_remote_t *name_rmt; - xfs_attr_leaf_map_t *map; - xfs_mount_t *mp; - int tmp, i; + struct xfs_attr_leafblock *leaf; + struct xfs_attr_leaf_entry *entry; + struct xfs_attr_leaf_name_local *name_loc; + struct xfs_attr_leaf_name_remote *name_rmt; + struct xfs_attr_leaf_map *map; + struct xfs_mount *mp; + int tmp; + int i; trace_xfs_attr_leaf_add_work(args); leaf = bp->b_addr; - ASSERT(leaf->hdr.info.magic == cpu_to_be16(XFS_ATTR_LEAF_MAGIC)); - hdr = &leaf->hdr; - ASSERT((mapindex >= 0) && (mapindex < XFS_ATTR_LEAF_MAPSIZE)); - ASSERT((args->index >= 0) && (args->index <= be16_to_cpu(hdr->count))); + ASSERT(mapindex >= 0 && mapindex < XFS_ATTR_LEAF_MAPSIZE); + ASSERT(args->index >= 0 && args->index <= ichdr->count); /* * Force open some space in the entry array and fill it in. */ - entry = &leaf->entries[args->index]; - if (args->index < be16_to_cpu(hdr->count)) { - tmp = be16_to_cpu(hdr->count) - args->index; + entry = &xfs_attr3_leaf_entryp(leaf)[args->index]; + if (args->index < ichdr->count) { + tmp = ichdr->count - args->index; tmp *= sizeof(xfs_attr_leaf_entry_t); - memmove((char *)(entry+1), (char *)entry, tmp); + memmove(entry + 1, entry, tmp); xfs_trans_log_buf(args->trans, bp, XFS_DA_LOGRANGE(leaf, entry, tmp + sizeof(*entry))); } - be16_add_cpu(&hdr->count, 1); + ichdr->count++; /* * Allocate space for the new string (at the end of the run). */ - map = &hdr->freemap[mapindex]; mp = args->trans->t_mountp; - ASSERT(be16_to_cpu(map->base) < XFS_LBSIZE(mp)); - ASSERT((be16_to_cpu(map->base) & 0x3) == 0); - ASSERT(be16_to_cpu(map->size) >= + ASSERT(ichdr->freemap[mapindex].base < XFS_LBSIZE(mp)); + ASSERT((ichdr->freemap[mapindex].base & 0x3) == 0); + ASSERT(ichdr->freemap[mapindex].size >= xfs_attr_leaf_newentsize(args->namelen, args->valuelen, mp->m_sb.sb_blocksize, NULL)); - ASSERT(be16_to_cpu(map->size) < XFS_LBSIZE(mp)); - ASSERT((be16_to_cpu(map->size) & 0x3) == 0); - be16_add_cpu(&map->size, - -xfs_attr_leaf_newentsize(args->namelen, args->valuelen, - mp->m_sb.sb_blocksize, &tmp)); - entry->nameidx = cpu_to_be16(be16_to_cpu(map->base) + - be16_to_cpu(map->size)); + ASSERT(ichdr->freemap[mapindex].size < XFS_LBSIZE(mp)); + ASSERT((ichdr->freemap[mapindex].size & 0x3) == 0); + + ichdr->freemap[mapindex].size -= + xfs_attr_leaf_newentsize(args->namelen, args->valuelen, + mp->m_sb.sb_blocksize, &tmp); + + entry->nameidx = cpu_to_be16(ichdr->freemap[mapindex].base + + ichdr->freemap[mapindex].size); entry->hashval = cpu_to_be32(args->hashval); entry->flags = tmp ? XFS_ATTR_LOCAL : 0; entry->flags |= XFS_ATTR_NSP_ARGS_TO_ONDISK(args->flags); @@ -1203,7 +1377,7 @@ xfs_attr_leaf_add_work( XFS_DA_LOGRANGE(leaf, entry, sizeof(*entry))); ASSERT((args->index == 0) || (be32_to_cpu(entry->hashval) >= be32_to_cpu((entry-1)->hashval))); - ASSERT((args->index == be16_to_cpu(hdr->count)-1) || + ASSERT((args->index == ichdr->count - 1) || (be32_to_cpu(entry->hashval) <= be32_to_cpu((entry+1)->hashval))); /* @@ -1214,14 +1388,14 @@ xfs_attr_leaf_add_work( * as part of this transaction (a split operation for example). */ if (entry->flags & XFS_ATTR_LOCAL) { - name_loc = xfs_attr_leaf_name_local(leaf, args->index); + name_loc = xfs_attr3_leaf_name_local(leaf, args->index); name_loc->namelen = args->namelen; name_loc->valuelen = cpu_to_be16(args->valuelen); memcpy((char *)name_loc->nameval, args->name, args->namelen); memcpy((char *)&name_loc->nameval[args->namelen], args->value, be16_to_cpu(name_loc->valuelen)); } else { - name_rmt = xfs_attr_leaf_name_remote(leaf, args->index); + name_rmt = xfs_attr3_leaf_name_remote(leaf, args->index); name_rmt->namelen = args->namelen; memcpy((char *)name_rmt->name, args->name, args->namelen); entry->flags |= XFS_ATTR_INCOMPLETE; @@ -1232,44 +1406,41 @@ xfs_attr_leaf_add_work( args->rmtblkcnt = XFS_B_TO_FSB(mp, args->valuelen); } xfs_trans_log_buf(args->trans, bp, - XFS_DA_LOGRANGE(leaf, xfs_attr_leaf_name(leaf, args->index), + XFS_DA_LOGRANGE(leaf, xfs_attr3_leaf_name(leaf, args->index), xfs_attr_leaf_entsize(leaf, args->index))); /* * Update the control info for this leaf node */ - if (be16_to_cpu(entry->nameidx) < be16_to_cpu(hdr->firstused)) { - /* both on-disk, don't endian-flip twice */ - hdr->firstused = entry->nameidx; - } - ASSERT(be16_to_cpu(hdr->firstused) >= - ((be16_to_cpu(hdr->count) * sizeof(*entry)) + sizeof(*hdr))); - tmp = (be16_to_cpu(hdr->count)-1) * sizeof(xfs_attr_leaf_entry_t) - + sizeof(xfs_attr_leaf_hdr_t); - map = &hdr->freemap[0]; + if (be16_to_cpu(entry->nameidx) < ichdr->firstused) + ichdr->firstused = be16_to_cpu(entry->nameidx); + + ASSERT(ichdr->firstused >= ichdr->count * sizeof(xfs_attr_leaf_entry_t) + + xfs_attr3_leaf_hdr_size(leaf)); + tmp = (ichdr->count - 1) * sizeof(xfs_attr_leaf_entry_t) + + xfs_attr3_leaf_hdr_size(leaf); + for (i = 0; i < XFS_ATTR_LEAF_MAPSIZE; map++, i++) { - if (be16_to_cpu(map->base) == tmp) { - be16_add_cpu(&map->base, sizeof(xfs_attr_leaf_entry_t)); - be16_add_cpu(&map->size, - -((int)sizeof(xfs_attr_leaf_entry_t))); + if (ichdr->freemap[i].base == tmp) { + ichdr->freemap[i].base += sizeof(xfs_attr_leaf_entry_t); + ichdr->freemap[i].size -= sizeof(xfs_attr_leaf_entry_t); } } - be16_add_cpu(&hdr->usedbytes, xfs_attr_leaf_entsize(leaf, args->index)); - xfs_trans_log_buf(args->trans, bp, - XFS_DA_LOGRANGE(leaf, hdr, sizeof(*hdr))); - return(0); + ichdr->usedbytes += xfs_attr_leaf_entsize(leaf, args->index); + return 0; } /* * Garbage collect a leaf attribute list block by copying it to a new buffer. */ STATIC void -xfs_attr_leaf_compact( +xfs_attr3_leaf_compact( struct xfs_da_args *args, + struct xfs_attr3_icleaf_hdr *ichdr_d, struct xfs_buf *bp) { xfs_attr_leafblock_t *leaf_s, *leaf_d; - xfs_attr_leaf_hdr_t *hdr_s, *hdr_d; + struct xfs_attr3_icleaf_hdr ichdr_s; struct xfs_trans *trans = args->trans; struct xfs_mount *mp = trans->t_mountp; char *tmpbuffer; @@ -1286,34 +1457,69 @@ xfs_attr_leaf_compact( */ leaf_s = (xfs_attr_leafblock_t *)tmpbuffer; leaf_d = bp->b_addr; - hdr_s = &leaf_s->hdr; - hdr_d = &leaf_d->hdr; - hdr_d->info = hdr_s->info; /* struct copy */ - hdr_d->firstused = cpu_to_be16(XFS_LBSIZE(mp)); - /* handle truncation gracefully */ - if (!hdr_d->firstused) { - hdr_d->firstused = cpu_to_be16( - XFS_LBSIZE(mp) - XFS_ATTR_LEAF_NAME_ALIGN); - } - hdr_d->usedbytes = 0; - hdr_d->count = 0; - hdr_d->holes = 0; - hdr_d->freemap[0].base = cpu_to_be16(sizeof(xfs_attr_leaf_hdr_t)); - hdr_d->freemap[0].size = cpu_to_be16(be16_to_cpu(hdr_d->firstused) - - sizeof(xfs_attr_leaf_hdr_t)); + ichdr_s = *ichdr_d; /* struct copy */ + ichdr_d->firstused = XFS_LBSIZE(mp); + ichdr_d->usedbytes = 0; + ichdr_d->count = 0; + ichdr_d->holes = 0; + ichdr_d->freemap[0].base = xfs_attr3_leaf_hdr_size(leaf_s); + ichdr_d->freemap[0].size = ichdr_d->firstused - ichdr_d->freemap[0].base; /* * Copy all entry's in the same (sorted) order, * but allocate name/value pairs packed and in sequence. */ - xfs_attr_leaf_moveents(leaf_s, 0, leaf_d, 0, - be16_to_cpu(hdr_s->count), mp); + xfs_attr3_leaf_moveents(leaf_s, &ichdr_s, 0, leaf_d, ichdr_d, 0, + ichdr_s.count, mp); + /* + * this logs the entire buffer, but the caller must write the header + * back to the buffer when it is finished modifying it. + */ xfs_trans_log_buf(trans, bp, 0, XFS_LBSIZE(mp) - 1); kmem_free(tmpbuffer); } /* + * Compare two leaf blocks "order". + * Return 0 unless leaf2 should go before leaf1. + */ +static int +xfs_attr3_leaf_order( + struct xfs_buf *leaf1_bp, + struct xfs_attr3_icleaf_hdr *leaf1hdr, + struct xfs_buf *leaf2_bp, + struct xfs_attr3_icleaf_hdr *leaf2hdr) +{ + struct xfs_attr_leaf_entry *entries1; + struct xfs_attr_leaf_entry *entries2; + + entries1 = xfs_attr3_leaf_entryp(leaf1_bp->b_addr); + entries2 = xfs_attr3_leaf_entryp(leaf2_bp->b_addr); + if (leaf1hdr->count > 0 && leaf2hdr->count > 0 && + ((be32_to_cpu(entries2[0].hashval) < + be32_to_cpu(entries1[0].hashval)) || + (be32_to_cpu(entries2[leaf2hdr->count - 1].hashval) < + be32_to_cpu(entries1[leaf1hdr->count - 1].hashval)))) { + return 1; + } + return 0; +} + +int +xfs_attr_leaf_order( + struct xfs_buf *leaf1_bp, + struct xfs_buf *leaf2_bp) +{ + struct xfs_attr3_icleaf_hdr ichdr1; + struct xfs_attr3_icleaf_hdr ichdr2; + + xfs_attr3_leaf_hdr_from_disk(&ichdr1, leaf1_bp->b_addr); + xfs_attr3_leaf_hdr_from_disk(&ichdr2, leaf2_bp->b_addr); + return xfs_attr3_leaf_order(leaf1_bp, &ichdr1, leaf2_bp, &ichdr2); +} + +/* * Redistribute the attribute list entries between two leaf nodes, * taking into account the size of the new entry. * @@ -1326,14 +1532,23 @@ xfs_attr_leaf_compact( * the "new" and "old" values can end up in different blocks. */ STATIC void -xfs_attr_leaf_rebalance(xfs_da_state_t *state, xfs_da_state_blk_t *blk1, - xfs_da_state_blk_t *blk2) +xfs_attr3_leaf_rebalance( + struct xfs_da_state *state, + struct xfs_da_state_blk *blk1, + struct xfs_da_state_blk *blk2) { - xfs_da_args_t *args; - xfs_da_state_blk_t *tmp_blk; - xfs_attr_leafblock_t *leaf1, *leaf2; - xfs_attr_leaf_hdr_t *hdr1, *hdr2; - int count, totallen, max, space, swap; + struct xfs_da_args *args; + struct xfs_attr_leafblock *leaf1; + struct xfs_attr_leafblock *leaf2; + struct xfs_attr3_icleaf_hdr ichdr1; + struct xfs_attr3_icleaf_hdr ichdr2; + struct xfs_attr_leaf_entry *entries1; + struct xfs_attr_leaf_entry *entries2; + int count; + int totallen; + int max; + int space; + int swap; /* * Set up environment. @@ -1342,9 +1557,9 @@ xfs_attr_leaf_rebalance(xfs_da_state_t *state, xfs_da_state_blk_t *blk1, ASSERT(blk2->magic == XFS_ATTR_LEAF_MAGIC); leaf1 = blk1->bp->b_addr; leaf2 = blk2->bp->b_addr; - ASSERT(leaf1->hdr.info.magic == cpu_to_be16(XFS_ATTR_LEAF_MAGIC)); - ASSERT(leaf2->hdr.info.magic == cpu_to_be16(XFS_ATTR_LEAF_MAGIC)); - ASSERT(leaf2->hdr.count == 0); + xfs_attr3_leaf_hdr_from_disk(&ichdr1, leaf1); + xfs_attr3_leaf_hdr_from_disk(&ichdr2, leaf2); + ASSERT(ichdr2.count == 0); args = state->args; trace_xfs_attr_leaf_rebalance(args); @@ -1356,16 +1571,23 @@ xfs_attr_leaf_rebalance(xfs_da_state_t *state, xfs_da_state_blk_t *blk1, * second block, this code should never set "swap". */ swap = 0; - if (xfs_attr_leaf_order(blk1->bp, blk2->bp)) { + if (xfs_attr3_leaf_order(blk1->bp, &ichdr1, blk2->bp, &ichdr2)) { + struct xfs_da_state_blk *tmp_blk; + struct xfs_attr3_icleaf_hdr tmp_ichdr; + tmp_blk = blk1; blk1 = blk2; blk2 = tmp_blk; + + /* struct copies to swap them rather than reconverting */ + tmp_ichdr = ichdr1; + ichdr1 = ichdr2; + ichdr2 = tmp_ichdr; + leaf1 = blk1->bp->b_addr; leaf2 = blk2->bp->b_addr; swap = 1; } - hdr1 = &leaf1->hdr; - hdr2 = &leaf2->hdr; /* * Examine entries until we reduce the absolute difference in @@ -1375,41 +1597,39 @@ xfs_attr_leaf_rebalance(xfs_da_state_t *state, xfs_da_state_blk_t *blk1, * "inleaf" is true if the new entry should be inserted into blk1. * If "swap" is also true, then reverse the sense of "inleaf". */ - state->inleaf = xfs_attr_leaf_figure_balance(state, blk1, blk2, - &count, &totallen); + state->inleaf = xfs_attr3_leaf_figure_balance(state, blk1, &ichdr1, + blk2, &ichdr2, + &count, &totallen); if (swap) state->inleaf = !state->inleaf; /* * Move any entries required from leaf to leaf: */ - if (count < be16_to_cpu(hdr1->count)) { + if (count < ichdr1.count) { /* * Figure the total bytes to be added to the destination leaf. */ /* number entries being moved */ - count = be16_to_cpu(hdr1->count) - count; - space = be16_to_cpu(hdr1->usedbytes) - totallen; + count = ichdr1.count - count; + space = ichdr1.usedbytes - totallen; space += count * sizeof(xfs_attr_leaf_entry_t); /* * leaf2 is the destination, compact it if it looks tight. */ - max = be16_to_cpu(hdr2->firstused) - - sizeof(xfs_attr_leaf_hdr_t); - max -= be16_to_cpu(hdr2->count) * sizeof(xfs_attr_leaf_entry_t); + max = ichdr2.firstused - xfs_attr3_leaf_hdr_size(leaf1); + max -= ichdr2.count * sizeof(xfs_attr_leaf_entry_t); if (space > max) - xfs_attr_leaf_compact(args, blk2->bp); + xfs_attr3_leaf_compact(args, &ichdr2, blk2->bp); /* * Move high entries from leaf1 to low end of leaf2. */ - xfs_attr_leaf_moveents(leaf1, be16_to_cpu(hdr1->count) - count, - leaf2, 0, count, state->mp); + xfs_attr3_leaf_moveents(leaf1, &ichdr1, ichdr1.count - count, + leaf2, &ichdr2, 0, count, state->mp); - xfs_trans_log_buf(args->trans, blk1->bp, 0, state->blocksize-1); - xfs_trans_log_buf(args->trans, blk2->bp, 0, state->blocksize-1); - } else if (count > be16_to_cpu(hdr1->count)) { + } else if (count > ichdr1.count) { /* * I assert that since all callers pass in an empty * second buffer, this code should never execute. @@ -1420,36 +1640,37 @@ xfs_attr_leaf_rebalance(xfs_da_state_t *state, xfs_da_state_blk_t *blk1, * Figure the total bytes to be added to the destination leaf. */ /* number entries being moved */ - count -= be16_to_cpu(hdr1->count); - space = totallen - be16_to_cpu(hdr1->usedbytes); + count -= ichdr1.count; + space = totallen - ichdr1.usedbytes; space += count * sizeof(xfs_attr_leaf_entry_t); /* * leaf1 is the destination, compact it if it looks tight. */ - max = be16_to_cpu(hdr1->firstused) - - sizeof(xfs_attr_leaf_hdr_t); - max -= be16_to_cpu(hdr1->count) * sizeof(xfs_attr_leaf_entry_t); + max = ichdr1.firstused - xfs_attr3_leaf_hdr_size(leaf1); + max -= ichdr1.count * sizeof(xfs_attr_leaf_entry_t); if (space > max) - xfs_attr_leaf_compact(args, blk1->bp); + xfs_attr3_leaf_compact(args, &ichdr1, blk1->bp); /* * Move low entries from leaf2 to high end of leaf1. */ - xfs_attr_leaf_moveents(leaf2, 0, leaf1, - be16_to_cpu(hdr1->count), count, state->mp); - - xfs_trans_log_buf(args->trans, blk1->bp, 0, state->blocksize-1); - xfs_trans_log_buf(args->trans, blk2->bp, 0, state->blocksize-1); + xfs_attr3_leaf_moveents(leaf2, &ichdr2, 0, leaf1, &ichdr1, + ichdr1.count, count, state->mp); } + xfs_attr3_leaf_hdr_to_disk(leaf1, &ichdr1); + xfs_attr3_leaf_hdr_to_disk(leaf2, &ichdr2); + xfs_trans_log_buf(args->trans, blk1->bp, 0, state->blocksize-1); + xfs_trans_log_buf(args->trans, blk2->bp, 0, state->blocksize-1); + /* * Copy out last hashval in each block for B-tree code. */ - blk1->hashval = be32_to_cpu( - leaf1->entries[be16_to_cpu(leaf1->hdr.count)-1].hashval); - blk2->hashval = be32_to_cpu( - leaf2->entries[be16_to_cpu(leaf2->hdr.count)-1].hashval); + entries1 = xfs_attr3_leaf_entryp(leaf1); + entries2 = xfs_attr3_leaf_entryp(leaf2); + blk1->hashval = be32_to_cpu(entries1[ichdr1.count - 1].hashval); + blk2->hashval = be32_to_cpu(entries2[ichdr2.count - 1].hashval); /* * Adjust the expected index for insertion. @@ -1463,12 +1684,12 @@ xfs_attr_leaf_rebalance(xfs_da_state_t *state, xfs_da_state_blk_t *blk1, * inserting. The index/blkno fields refer to the "old" entry, * while the index2/blkno2 fields refer to the "new" entry. */ - if (blk1->index > be16_to_cpu(leaf1->hdr.count)) { + if (blk1->index > ichdr1.count) { ASSERT(state->inleaf == 0); - blk2->index = blk1->index - be16_to_cpu(leaf1->hdr.count); + blk2->index = blk1->index - ichdr1.count; args->index = args->index2 = blk2->index; args->blkno = args->blkno2 = blk2->blkno; - } else if (blk1->index == be16_to_cpu(leaf1->hdr.count)) { + } else if (blk1->index == ichdr1.count) { if (state->inleaf) { args->index = blk1->index; args->blkno = blk1->blkno; @@ -1480,8 +1701,7 @@ xfs_attr_leaf_rebalance(xfs_da_state_t *state, xfs_da_state_blk_t *blk1, * is already stored in blkno2/index2, so don't * overwrite it overwise we corrupt the tree. */ - blk2->index = blk1->index - - be16_to_cpu(leaf1->hdr.count); + blk2->index = blk1->index - ichdr1.count; args->index = blk2->index; args->blkno = blk2->blkno; if (!state->extravalid) { @@ -1509,42 +1729,40 @@ xfs_attr_leaf_rebalance(xfs_da_state_t *state, xfs_da_state_blk_t *blk1, * GROT: Do a double-split for this case? */ STATIC int -xfs_attr_leaf_figure_balance(xfs_da_state_t *state, - xfs_da_state_blk_t *blk1, - xfs_da_state_blk_t *blk2, - int *countarg, int *usedbytesarg) +xfs_attr3_leaf_figure_balance( + struct xfs_da_state *state, + struct xfs_da_state_blk *blk1, + struct xfs_attr3_icleaf_hdr *ichdr1, + struct xfs_da_state_blk *blk2, + struct xfs_attr3_icleaf_hdr *ichdr2, + int *countarg, + int *usedbytesarg) { - xfs_attr_leafblock_t *leaf1, *leaf2; - xfs_attr_leaf_hdr_t *hdr1, *hdr2; - xfs_attr_leaf_entry_t *entry; - int count, max, index, totallen, half; - int lastdelta, foundit, tmp; - - /* - * Set up environment. - */ - leaf1 = blk1->bp->b_addr; - leaf2 = blk2->bp->b_addr; - hdr1 = &leaf1->hdr; - hdr2 = &leaf2->hdr; - foundit = 0; - totallen = 0; + struct xfs_attr_leafblock *leaf1 = blk1->bp->b_addr; + struct xfs_attr_leafblock *leaf2 = blk2->bp->b_addr; + struct xfs_attr_leaf_entry *entry; + int count; + int max; + int index; + int totallen = 0; + int half; + int lastdelta; + int foundit = 0; + int tmp; /* * Examine entries until we reduce the absolute difference in * byte usage between the two blocks to a minimum. */ - max = be16_to_cpu(hdr1->count) + be16_to_cpu(hdr2->count); - half = (max+1) * sizeof(*entry); - half += be16_to_cpu(hdr1->usedbytes) + - be16_to_cpu(hdr2->usedbytes) + - xfs_attr_leaf_newentsize( - state->args->namelen, - state->args->valuelen, - state->blocksize, NULL); + max = ichdr1->count + ichdr2->count; + half = (max + 1) * sizeof(*entry); + half += ichdr1->usedbytes + ichdr2->usedbytes + + xfs_attr_leaf_newentsize(state->args->namelen, + state->args->valuelen, + state->blocksize, NULL); half /= 2; lastdelta = state->blocksize; - entry = &leaf1->entries[0]; + entry = xfs_attr3_leaf_entryp(leaf1); for (count = index = 0; count < max; entry++, index++, count++) { #define XFS_ATTR_ABS(A) (((A) < 0) ? -(A) : (A)) @@ -1567,9 +1785,9 @@ xfs_attr_leaf_figure_balance(xfs_da_state_t *state, /* * Wrap around into the second block if necessary. */ - if (count == be16_to_cpu(hdr1->count)) { + if (count == ichdr1->count) { leaf1 = leaf2; - entry = &leaf1->entries[0]; + entry = xfs_attr3_leaf_entryp(leaf1); index = 0; } @@ -1600,7 +1818,7 @@ xfs_attr_leaf_figure_balance(xfs_da_state_t *state, *countarg = count; *usedbytesarg = totallen; - return(foundit); + return foundit; } /*======================================================================== @@ -1619,14 +1837,20 @@ xfs_attr_leaf_figure_balance(xfs_da_state_t *state, * GROT: allow for INCOMPLETE entries in calculation. */ int -xfs_attr_leaf_toosmall(xfs_da_state_t *state, int *action) +xfs_attr3_leaf_toosmall( + struct xfs_da_state *state, + int *action) { - xfs_attr_leafblock_t *leaf; - xfs_da_state_blk_t *blk; - xfs_da_blkinfo_t *info; - int count, bytes, forward, error, retval, i; - xfs_dablk_t blkno; - struct xfs_buf *bp; + struct xfs_attr_leafblock *leaf; + struct xfs_da_state_blk *blk; + struct xfs_attr3_icleaf_hdr ichdr; + struct xfs_buf *bp; + xfs_dablk_t blkno; + int bytes; + int forward; + int error; + int retval; + int i; trace_xfs_attr_leaf_toosmall(state->args); @@ -1636,13 +1860,11 @@ xfs_attr_leaf_toosmall(xfs_da_state_t *state, int *action) * to coalesce with a sibling. */ blk = &state->path.blk[ state->path.active-1 ]; - info = blk->bp->b_addr; - ASSERT(info->magic == cpu_to_be16(XFS_ATTR_LEAF_MAGIC)); - leaf = (xfs_attr_leafblock_t *)info; - count = be16_to_cpu(leaf->hdr.count); - bytes = sizeof(xfs_attr_leaf_hdr_t) + - count * sizeof(xfs_attr_leaf_entry_t) + - be16_to_cpu(leaf->hdr.usedbytes); + leaf = blk->bp->b_addr; + xfs_attr3_leaf_hdr_from_disk(&ichdr, leaf); + bytes = xfs_attr3_leaf_hdr_size(leaf) + + ichdr.count * sizeof(xfs_attr_leaf_entry_t) + + ichdr.usedbytes; if (bytes > (state->blocksize >> 1)) { *action = 0; /* blk over 50%, don't try to join */ return(0); @@ -1654,12 +1876,12 @@ xfs_attr_leaf_toosmall(xfs_da_state_t *state, int *action) * coalesce it with a sibling block. We choose (arbitrarily) * to merge with the forward block unless it is NULL. */ - if (count == 0) { + if (ichdr.count == 0) { /* * Make altpath point to the block we want to keep and * path point to the block we want to drop (this one). */ - forward = (info->forw != 0); + forward = (ichdr.forw != 0); memcpy(&state->altpath, &state->path, sizeof(state->path)); error = xfs_da3_path_shift(state, &state->altpath, forward, 0, &retval); @@ -1670,7 +1892,7 @@ xfs_attr_leaf_toosmall(xfs_da_state_t *state, int *action) } else { *action = 2; } - return(0); + return 0; } /* @@ -1681,28 +1903,28 @@ xfs_attr_leaf_toosmall(xfs_da_state_t *state, int *action) * to shrink an attribute list over time. */ /* start with smaller blk num */ - forward = (be32_to_cpu(info->forw) < be32_to_cpu(info->back)); + forward = ichdr.forw < ichdr.back; for (i = 0; i < 2; forward = !forward, i++) { + struct xfs_attr3_icleaf_hdr ichdr2; if (forward) - blkno = be32_to_cpu(info->forw); + blkno = ichdr.forw; else - blkno = be32_to_cpu(info->back); + blkno = ichdr.back; if (blkno == 0) continue; - error = xfs_attr_leaf_read(state->args->trans, state->args->dp, + error = xfs_attr3_leaf_read(state->args->trans, state->args->dp, blkno, -1, &bp); if (error) return(error); - leaf = (xfs_attr_leafblock_t *)info; - count = be16_to_cpu(leaf->hdr.count); - bytes = state->blocksize - (state->blocksize>>2); - bytes -= be16_to_cpu(leaf->hdr.usedbytes); - leaf = bp->b_addr; - count += be16_to_cpu(leaf->hdr.count); - bytes -= be16_to_cpu(leaf->hdr.usedbytes); - bytes -= count * sizeof(xfs_attr_leaf_entry_t); - bytes -= sizeof(xfs_attr_leaf_hdr_t); + xfs_attr3_leaf_hdr_from_disk(&ichdr2, bp->b_addr); + + bytes = state->blocksize - (state->blocksize >> 2) - + ichdr.usedbytes - ichdr2.usedbytes - + ((ichdr.count + ichdr2.count) * + sizeof(xfs_attr_leaf_entry_t)) - + xfs_attr3_leaf_hdr_size(leaf); + xfs_trans_brelse(state->args->trans, bp); if (bytes >= 0) break; /* fits with at least 25% to spare */ @@ -1741,32 +1963,35 @@ xfs_attr_leaf_toosmall(xfs_da_state_t *state, int *action) * If two leaves are 37% full, when combined they will leave 25% free. */ int -xfs_attr_leaf_remove( - struct xfs_buf *bp, - xfs_da_args_t *args) +xfs_attr3_leaf_remove( + struct xfs_buf *bp, + struct xfs_da_args *args) { - xfs_attr_leafblock_t *leaf; - xfs_attr_leaf_hdr_t *hdr; - xfs_attr_leaf_map_t *map; - xfs_attr_leaf_entry_t *entry; - int before, after, smallest, entsize; - int tablesize, tmp, i; - xfs_mount_t *mp; + struct xfs_attr_leafblock *leaf; + struct xfs_attr3_icleaf_hdr ichdr; + struct xfs_attr_leaf_entry *entry; + struct xfs_mount *mp = args->trans->t_mountp; + int before; + int after; + int smallest; + int entsize; + int tablesize; + int tmp; + int i; trace_xfs_attr_leaf_remove(args); leaf = bp->b_addr; - ASSERT(leaf->hdr.info.magic == cpu_to_be16(XFS_ATTR_LEAF_MAGIC)); - hdr = &leaf->hdr; - mp = args->trans->t_mountp; - ASSERT((be16_to_cpu(hdr->count) > 0) - && (be16_to_cpu(hdr->count) < (XFS_LBSIZE(mp)/8))); - ASSERT((args->index >= 0) - && (args->index < be16_to_cpu(hdr->count))); - ASSERT(be16_to_cpu(hdr->firstused) >= - ((be16_to_cpu(hdr->count) * sizeof(*entry)) + sizeof(*hdr))); - entry = &leaf->entries[args->index]; - ASSERT(be16_to_cpu(entry->nameidx) >= be16_to_cpu(hdr->firstused)); + xfs_attr3_leaf_hdr_from_disk(&ichdr, leaf); + + ASSERT(ichdr.count > 0 && ichdr.count < XFS_LBSIZE(mp) / 8); + ASSERT(args->index >= 0 && args->index < ichdr.count); + ASSERT(ichdr.firstused >= ichdr.count * sizeof(*entry) + + xfs_attr3_leaf_hdr_size(leaf)); + + entry = &xfs_attr3_leaf_entryp(leaf)[args->index]; + + ASSERT(be16_to_cpu(entry->nameidx) >= ichdr.firstused); ASSERT(be16_to_cpu(entry->nameidx) < XFS_LBSIZE(mp)); /* @@ -1775,30 +2000,28 @@ xfs_attr_leaf_remove( * find smallest free region in case we need to replace it, * adjust any map that borders the entry table, */ - tablesize = be16_to_cpu(hdr->count) * sizeof(xfs_attr_leaf_entry_t) - + sizeof(xfs_attr_leaf_hdr_t); - map = &hdr->freemap[0]; - tmp = be16_to_cpu(map->size); + tablesize = ichdr.count * sizeof(xfs_attr_leaf_entry_t) + + xfs_attr3_leaf_hdr_size(leaf); + tmp = ichdr.freemap[0].size; before = after = -1; smallest = XFS_ATTR_LEAF_MAPSIZE - 1; entsize = xfs_attr_leaf_entsize(leaf, args->index); - for (i = 0; i < XFS_ATTR_LEAF_MAPSIZE; map++, i++) { - ASSERT(be16_to_cpu(map->base) < XFS_LBSIZE(mp)); - ASSERT(be16_to_cpu(map->size) < XFS_LBSIZE(mp)); - if (be16_to_cpu(map->base) == tablesize) { - be16_add_cpu(&map->base, - -((int)sizeof(xfs_attr_leaf_entry_t))); - be16_add_cpu(&map->size, sizeof(xfs_attr_leaf_entry_t)); + for (i = 0; i < XFS_ATTR_LEAF_MAPSIZE; i++) { + ASSERT(ichdr.freemap[i].base < XFS_LBSIZE(mp)); + ASSERT(ichdr.freemap[i].size < XFS_LBSIZE(mp)); + if (ichdr.freemap[i].base == tablesize) { + ichdr.freemap[i].base -= sizeof(xfs_attr_leaf_entry_t); + ichdr.freemap[i].size += sizeof(xfs_attr_leaf_entry_t); } - if ((be16_to_cpu(map->base) + be16_to_cpu(map->size)) - == be16_to_cpu(entry->nameidx)) { + if (ichdr.freemap[i].base + ichdr.freemap[i].size == + be16_to_cpu(entry->nameidx)) { before = i; - } else if (be16_to_cpu(map->base) - == (be16_to_cpu(entry->nameidx) + entsize)) { + } else if (ichdr.freemap[i].base == + (be16_to_cpu(entry->nameidx) + entsize)) { after = i; - } else if (be16_to_cpu(map->size) < tmp) { - tmp = be16_to_cpu(map->size); + } else if (ichdr.freemap[i].size < tmp) { + tmp = ichdr.freemap[i].size; smallest = i; } } @@ -1809,36 +2032,30 @@ xfs_attr_leaf_remove( */ if ((before >= 0) || (after >= 0)) { if ((before >= 0) && (after >= 0)) { - map = &hdr->freemap[before]; - be16_add_cpu(&map->size, entsize); - be16_add_cpu(&map->size, - be16_to_cpu(hdr->freemap[after].size)); - hdr->freemap[after].base = 0; - hdr->freemap[after].size = 0; + ichdr.freemap[before].size += entsize; + ichdr.freemap[before].size += ichdr.freemap[after].size; + ichdr.freemap[after].base = 0; + ichdr.freemap[after].size = 0; } else if (before >= 0) { - map = &hdr->freemap[before]; - be16_add_cpu(&map->size, entsize); + ichdr.freemap[before].size += entsize; } else { - map = &hdr->freemap[after]; - /* both on-disk, don't endian flip twice */ - map->base = entry->nameidx; - be16_add_cpu(&map->size, entsize); + ichdr.freemap[after].base = be16_to_cpu(entry->nameidx); + ichdr.freemap[after].size += entsize; } } else { /* * Replace smallest region (if it is smaller than free'd entry) */ - map = &hdr->freemap[smallest]; - if (be16_to_cpu(map->size) < entsize) { - map->base = cpu_to_be16(be16_to_cpu(entry->nameidx)); - map->size = cpu_to_be16(entsize); + if (ichdr.freemap[smallest].size < entsize) { + ichdr.freemap[smallest].base = be16_to_cpu(entry->nameidx); + ichdr.freemap[smallest].size = entsize; } } /* * Did we remove the first entry? */ - if (be16_to_cpu(entry->nameidx) == be16_to_cpu(hdr->firstused)) + if (be16_to_cpu(entry->nameidx) == ichdr.firstused) smallest = 1; else smallest = 0; @@ -1846,20 +2063,20 @@ xfs_attr_leaf_remove( /* * Compress the remaining entries and zero out the removed stuff. */ - memset(xfs_attr_leaf_name(leaf, args->index), 0, entsize); - be16_add_cpu(&hdr->usedbytes, -entsize); + memset(xfs_attr3_leaf_name(leaf, args->index), 0, entsize); + ichdr.usedbytes -= entsize; xfs_trans_log_buf(args->trans, bp, - XFS_DA_LOGRANGE(leaf, xfs_attr_leaf_name(leaf, args->index), + XFS_DA_LOGRANGE(leaf, xfs_attr3_leaf_name(leaf, args->index), entsize)); - tmp = (be16_to_cpu(hdr->count) - args->index) - * sizeof(xfs_attr_leaf_entry_t); - memmove((char *)entry, (char *)(entry+1), tmp); - be16_add_cpu(&hdr->count, -1); + tmp = (ichdr.count - args->index) * sizeof(xfs_attr_leaf_entry_t); + memmove(entry, entry + 1, tmp); + ichdr.count--; xfs_trans_log_buf(args->trans, bp, - XFS_DA_LOGRANGE(leaf, entry, tmp + sizeof(*entry))); - entry = &leaf->entries[be16_to_cpu(hdr->count)]; - memset((char *)entry, 0, sizeof(xfs_attr_leaf_entry_t)); + XFS_DA_LOGRANGE(leaf, entry, tmp + sizeof(xfs_attr_leaf_entry_t))); + + entry = &xfs_attr3_leaf_entryp(leaf)[ichdr.count]; + memset(entry, 0, sizeof(xfs_attr_leaf_entry_t)); /* * If we removed the first entry, re-find the first used byte @@ -1869,130 +2086,130 @@ xfs_attr_leaf_remove( */ if (smallest) { tmp = XFS_LBSIZE(mp); - entry = &leaf->entries[0]; - for (i = be16_to_cpu(hdr->count)-1; i >= 0; entry++, i--) { - ASSERT(be16_to_cpu(entry->nameidx) >= - be16_to_cpu(hdr->firstused)); + entry = xfs_attr3_leaf_entryp(leaf); + for (i = ichdr.count - 1; i >= 0; entry++, i--) { + ASSERT(be16_to_cpu(entry->nameidx) >= ichdr.firstused); ASSERT(be16_to_cpu(entry->nameidx) < XFS_LBSIZE(mp)); if (be16_to_cpu(entry->nameidx) < tmp) tmp = be16_to_cpu(entry->nameidx); } - hdr->firstused = cpu_to_be16(tmp); - if (!hdr->firstused) { - hdr->firstused = cpu_to_be16( - tmp - XFS_ATTR_LEAF_NAME_ALIGN); - } + ichdr.firstused = tmp; + if (!ichdr.firstused) + ichdr.firstused = tmp - XFS_ATTR_LEAF_NAME_ALIGN; } else { - hdr->holes = 1; /* mark as needing compaction */ + ichdr.holes = 1; /* mark as needing compaction */ } + xfs_attr3_leaf_hdr_to_disk(leaf, &ichdr); xfs_trans_log_buf(args->trans, bp, - XFS_DA_LOGRANGE(leaf, hdr, sizeof(*hdr))); + XFS_DA_LOGRANGE(leaf, &leaf->hdr, + xfs_attr3_leaf_hdr_size(leaf))); /* * Check if leaf is less than 50% full, caller may want to * "join" the leaf with a sibling if so. */ - tmp = sizeof(xfs_attr_leaf_hdr_t); - tmp += be16_to_cpu(leaf->hdr.count) * sizeof(xfs_attr_leaf_entry_t); - tmp += be16_to_cpu(leaf->hdr.usedbytes); - return(tmp < mp->m_attr_magicpct); /* leaf is < 37% full */ + tmp = ichdr.usedbytes + xfs_attr3_leaf_hdr_size(leaf) + + ichdr.count * sizeof(xfs_attr_leaf_entry_t); + + return tmp < mp->m_attr_magicpct; /* leaf is < 37% full */ } /* * Move all the attribute list entries from drop_leaf into save_leaf. */ void -xfs_attr_leaf_unbalance(xfs_da_state_t *state, xfs_da_state_blk_t *drop_blk, - xfs_da_state_blk_t *save_blk) +xfs_attr3_leaf_unbalance( + struct xfs_da_state *state, + struct xfs_da_state_blk *drop_blk, + struct xfs_da_state_blk *save_blk) { - xfs_attr_leafblock_t *drop_leaf, *save_leaf, *tmp_leaf; - xfs_attr_leaf_hdr_t *drop_hdr, *save_hdr, *tmp_hdr; - xfs_mount_t *mp; - char *tmpbuffer; + struct xfs_attr_leafblock *drop_leaf = drop_blk->bp->b_addr; + struct xfs_attr_leafblock *save_leaf = save_blk->bp->b_addr; + struct xfs_attr3_icleaf_hdr drophdr; + struct xfs_attr3_icleaf_hdr savehdr; + struct xfs_attr_leaf_entry *entry; + struct xfs_mount *mp = state->mp; trace_xfs_attr_leaf_unbalance(state->args); - /* - * Set up environment. - */ - mp = state->mp; - ASSERT(drop_blk->magic == XFS_ATTR_LEAF_MAGIC); - ASSERT(save_blk->magic == XFS_ATTR_LEAF_MAGIC); drop_leaf = drop_blk->bp->b_addr; save_leaf = save_blk->bp->b_addr; - ASSERT(drop_leaf->hdr.info.magic == cpu_to_be16(XFS_ATTR_LEAF_MAGIC)); - ASSERT(save_leaf->hdr.info.magic == cpu_to_be16(XFS_ATTR_LEAF_MAGIC)); - drop_hdr = &drop_leaf->hdr; - save_hdr = &save_leaf->hdr; + xfs_attr3_leaf_hdr_from_disk(&drophdr, drop_leaf); + xfs_attr3_leaf_hdr_from_disk(&savehdr, save_leaf); + entry = xfs_attr3_leaf_entryp(drop_leaf); /* * Save last hashval from dying block for later Btree fixup. */ - drop_blk->hashval = be32_to_cpu( - drop_leaf->entries[be16_to_cpu(drop_leaf->hdr.count)-1].hashval); + drop_blk->hashval = be32_to_cpu(entry[drophdr.count - 1].hashval); /* * Check if we need a temp buffer, or can we do it in place. * Note that we don't check "leaf" for holes because we will * always be dropping it, toosmall() decided that for us already. */ - if (save_hdr->holes == 0) { + if (savehdr.holes == 0) { /* * dest leaf has no holes, so we add there. May need * to make some room in the entry array. */ - if (xfs_attr_leaf_order(save_blk->bp, drop_blk->bp)) { - xfs_attr_leaf_moveents(drop_leaf, 0, save_leaf, 0, - be16_to_cpu(drop_hdr->count), mp); + if (xfs_attr3_leaf_order(save_blk->bp, &savehdr, + drop_blk->bp, &drophdr)) { + xfs_attr3_leaf_moveents(drop_leaf, &drophdr, 0, + save_leaf, &savehdr, 0, + drophdr.count, mp); } else { - xfs_attr_leaf_moveents(drop_leaf, 0, save_leaf, - be16_to_cpu(save_hdr->count), - be16_to_cpu(drop_hdr->count), mp); + xfs_attr3_leaf_moveents(drop_leaf, &drophdr, 0, + save_leaf, &savehdr, + savehdr.count, drophdr.count, mp); } } else { /* * Destination has holes, so we make a temporary copy * of the leaf and add them both to that. */ - tmpbuffer = kmem_alloc(state->blocksize, KM_SLEEP); - ASSERT(tmpbuffer != NULL); - memset(tmpbuffer, 0, state->blocksize); - tmp_leaf = (xfs_attr_leafblock_t *)tmpbuffer; - tmp_hdr = &tmp_leaf->hdr; - tmp_hdr->info = save_hdr->info; /* struct copy */ - tmp_hdr->count = 0; - tmp_hdr->firstused = cpu_to_be16(state->blocksize); - if (!tmp_hdr->firstused) { - tmp_hdr->firstused = cpu_to_be16( - state->blocksize - XFS_ATTR_LEAF_NAME_ALIGN); - } - tmp_hdr->usedbytes = 0; - if (xfs_attr_leaf_order(save_blk->bp, drop_blk->bp)) { - xfs_attr_leaf_moveents(drop_leaf, 0, tmp_leaf, 0, - be16_to_cpu(drop_hdr->count), mp); - xfs_attr_leaf_moveents(save_leaf, 0, tmp_leaf, - be16_to_cpu(tmp_leaf->hdr.count), - be16_to_cpu(save_hdr->count), mp); + struct xfs_attr_leafblock *tmp_leaf; + struct xfs_attr3_icleaf_hdr tmphdr; + + tmp_leaf = kmem_alloc(state->blocksize, KM_SLEEP); + memset(tmp_leaf, 0, state->blocksize); + memset(&tmphdr, 0, sizeof(tmphdr)); + + tmphdr.magic = savehdr.magic; + tmphdr.forw = savehdr.forw; + tmphdr.back = savehdr.back; + tmphdr.firstused = state->blocksize; + if (xfs_attr3_leaf_order(save_blk->bp, &savehdr, + drop_blk->bp, &drophdr)) { + xfs_attr3_leaf_moveents(drop_leaf, &drophdr, 0, + tmp_leaf, &tmphdr, 0, + drophdr.count, mp); + xfs_attr3_leaf_moveents(save_leaf, &savehdr, 0, + tmp_leaf, &tmphdr, tmphdr.count, + savehdr.count, mp); } else { - xfs_attr_leaf_moveents(save_leaf, 0, tmp_leaf, 0, - be16_to_cpu(save_hdr->count), mp); - xfs_attr_leaf_moveents(drop_leaf, 0, tmp_leaf, - be16_to_cpu(tmp_leaf->hdr.count), - be16_to_cpu(drop_hdr->count), mp); + xfs_attr3_leaf_moveents(save_leaf, &savehdr, 0, + tmp_leaf, &tmphdr, 0, + savehdr.count, mp); + xfs_attr3_leaf_moveents(drop_leaf, &drophdr, 0, + tmp_leaf, &tmphdr, tmphdr.count, + drophdr.count, mp); } - memcpy((char *)save_leaf, (char *)tmp_leaf, state->blocksize); - kmem_free(tmpbuffer); + memcpy(save_leaf, tmp_leaf, state->blocksize); + savehdr = tmphdr; /* struct copy */ + kmem_free(tmp_leaf); } + xfs_attr3_leaf_hdr_to_disk(save_leaf, &savehdr); xfs_trans_log_buf(state->args->trans, save_blk->bp, 0, state->blocksize - 1); /* * Copy out last hashval in each block for B-tree code. */ - save_blk->hashval = be32_to_cpu( - save_leaf->entries[be16_to_cpu(save_leaf->hdr.count)-1].hashval); + entry = xfs_attr3_leaf_entryp(save_leaf); + save_blk->hashval = be32_to_cpu(entry[savehdr.count - 1].hashval); } /*======================================================================== @@ -2013,31 +2230,33 @@ xfs_attr_leaf_unbalance(xfs_da_state_t *state, xfs_da_state_blk_t *drop_blk, * Don't change the args->value unless we find the attribute. */ int -xfs_attr_leaf_lookup_int( - struct xfs_buf *bp, - xfs_da_args_t *args) +xfs_attr3_leaf_lookup_int( + struct xfs_buf *bp, + struct xfs_da_args *args) { - xfs_attr_leafblock_t *leaf; - xfs_attr_leaf_entry_t *entry; - xfs_attr_leaf_name_local_t *name_loc; - xfs_attr_leaf_name_remote_t *name_rmt; - int probe, span; - xfs_dahash_t hashval; + struct xfs_attr_leafblock *leaf; + struct xfs_attr3_icleaf_hdr ichdr; + struct xfs_attr_leaf_entry *entry; + struct xfs_attr_leaf_entry *entries; + struct xfs_attr_leaf_name_local *name_loc; + struct xfs_attr_leaf_name_remote *name_rmt; + xfs_dahash_t hashval; + int probe; + int span; trace_xfs_attr_leaf_lookup(args); leaf = bp->b_addr; - ASSERT(leaf->hdr.info.magic == cpu_to_be16(XFS_ATTR_LEAF_MAGIC)); - ASSERT(be16_to_cpu(leaf->hdr.count) - < (XFS_LBSIZE(args->dp->i_mount)/8)); + xfs_attr3_leaf_hdr_from_disk(&ichdr, leaf); + entries = xfs_attr3_leaf_entryp(leaf); + ASSERT(ichdr.count < XFS_LBSIZE(args->dp->i_mount) / 8); /* * Binary search. (note: small blocks will skip this loop) */ hashval = args->hashval; - probe = span = be16_to_cpu(leaf->hdr.count) / 2; - for (entry = &leaf->entries[probe]; span > 4; - entry = &leaf->entries[probe]) { + probe = span = ichdr.count / 2; + for (entry = &entries[probe]; span > 4; entry = &entries[probe]) { span /= 2; if (be32_to_cpu(entry->hashval) < hashval) probe += span; @@ -2046,35 +2265,31 @@ xfs_attr_leaf_lookup_int( else break; } - ASSERT((probe >= 0) && - (!leaf->hdr.count - || (probe < be16_to_cpu(leaf->hdr.count)))); - ASSERT((span <= 4) || (be32_to_cpu(entry->hashval) == hashval)); + ASSERT(probe >= 0 && (!ichdr.count || probe < ichdr.count)); + ASSERT(span <= 4 || be32_to_cpu(entry->hashval) == hashval); /* * Since we may have duplicate hashval's, find the first matching * hashval in the leaf. */ - while ((probe > 0) && (be32_to_cpu(entry->hashval) >= hashval)) { + while (probe > 0 && be32_to_cpu(entry->hashval) >= hashval) { entry--; probe--; } - while ((probe < be16_to_cpu(leaf->hdr.count)) && - (be32_to_cpu(entry->hashval) < hashval)) { + while (probe < ichdr.count && + be32_to_cpu(entry->hashval) < hashval) { entry++; probe++; } - if ((probe == be16_to_cpu(leaf->hdr.count)) || - (be32_to_cpu(entry->hashval) != hashval)) { + if (probe == ichdr.count || be32_to_cpu(entry->hashval) != hashval) { args->index = probe; - return(XFS_ERROR(ENOATTR)); + return XFS_ERROR(ENOATTR); } /* * Duplicate keys may be present, so search all of them for a match. */ - for ( ; (probe < be16_to_cpu(leaf->hdr.count)) && - (be32_to_cpu(entry->hashval) == hashval); + for (; probe < ichdr.count && (be32_to_cpu(entry->hashval) == hashval); entry++, probe++) { /* * GROT: Add code to remove incomplete entries. @@ -2088,21 +2303,22 @@ xfs_attr_leaf_lookup_int( continue; } if (entry->flags & XFS_ATTR_LOCAL) { - name_loc = xfs_attr_leaf_name_local(leaf, probe); + name_loc = xfs_attr3_leaf_name_local(leaf, probe); if (name_loc->namelen != args->namelen) continue; - if (memcmp(args->name, (char *)name_loc->nameval, args->namelen) != 0) + if (memcmp(args->name, name_loc->nameval, + args->namelen) != 0) continue; if (!xfs_attr_namesp_match(args->flags, entry->flags)) continue; args->index = probe; - return(XFS_ERROR(EEXIST)); + return XFS_ERROR(EEXIST); } else { - name_rmt = xfs_attr_leaf_name_remote(leaf, probe); + name_rmt = xfs_attr3_leaf_name_remote(leaf, probe); if (name_rmt->namelen != args->namelen) continue; - if (memcmp(args->name, (char *)name_rmt->name, - args->namelen) != 0) + if (memcmp(args->name, name_rmt->name, + args->namelen) != 0) continue; if (!xfs_attr_namesp_match(args->flags, entry->flags)) continue; @@ -2110,11 +2326,11 @@ xfs_attr_leaf_lookup_int( args->rmtblkno = be32_to_cpu(name_rmt->valueblk); args->rmtblkcnt = XFS_B_TO_FSB(args->dp->i_mount, be32_to_cpu(name_rmt->valuelen)); - return(XFS_ERROR(EEXIST)); + return XFS_ERROR(EEXIST); } } args->index = probe; - return(XFS_ERROR(ENOATTR)); + return XFS_ERROR(ENOATTR); } /* @@ -2122,40 +2338,40 @@ xfs_attr_leaf_lookup_int( * list structure. */ int -xfs_attr_leaf_getvalue( - struct xfs_buf *bp, - xfs_da_args_t *args) +xfs_attr3_leaf_getvalue( + struct xfs_buf *bp, + struct xfs_da_args *args) { - int valuelen; - xfs_attr_leafblock_t *leaf; - xfs_attr_leaf_entry_t *entry; - xfs_attr_leaf_name_local_t *name_loc; - xfs_attr_leaf_name_remote_t *name_rmt; + struct xfs_attr_leafblock *leaf; + struct xfs_attr3_icleaf_hdr ichdr; + struct xfs_attr_leaf_entry *entry; + struct xfs_attr_leaf_name_local *name_loc; + struct xfs_attr_leaf_name_remote *name_rmt; + int valuelen; leaf = bp->b_addr; - ASSERT(leaf->hdr.info.magic == cpu_to_be16(XFS_ATTR_LEAF_MAGIC)); - ASSERT(be16_to_cpu(leaf->hdr.count) - < (XFS_LBSIZE(args->dp->i_mount)/8)); - ASSERT(args->index < be16_to_cpu(leaf->hdr.count)); + xfs_attr3_leaf_hdr_from_disk(&ichdr, leaf); + ASSERT(ichdr.count < XFS_LBSIZE(args->dp->i_mount) / 8); + ASSERT(args->index < ichdr.count); - entry = &leaf->entries[args->index]; + entry = &xfs_attr3_leaf_entryp(leaf)[args->index]; if (entry->flags & XFS_ATTR_LOCAL) { - name_loc = xfs_attr_leaf_name_local(leaf, args->index); + name_loc = xfs_attr3_leaf_name_local(leaf, args->index); ASSERT(name_loc->namelen == args->namelen); ASSERT(memcmp(args->name, name_loc->nameval, args->namelen) == 0); valuelen = be16_to_cpu(name_loc->valuelen); if (args->flags & ATTR_KERNOVAL) { args->valuelen = valuelen; - return(0); + return 0; } if (args->valuelen < valuelen) { args->valuelen = valuelen; - return(XFS_ERROR(ERANGE)); + return XFS_ERROR(ERANGE); } args->valuelen = valuelen; memcpy(args->value, &name_loc->nameval[args->namelen], valuelen); } else { - name_rmt = xfs_attr_leaf_name_remote(leaf, args->index); + name_rmt = xfs_attr3_leaf_name_remote(leaf, args->index); ASSERT(name_rmt->namelen == args->namelen); ASSERT(memcmp(args->name, name_rmt->name, args->namelen) == 0); valuelen = be32_to_cpu(name_rmt->valuelen); @@ -2163,15 +2379,15 @@ xfs_attr_leaf_getvalue( args->rmtblkcnt = XFS_B_TO_FSB(args->dp->i_mount, valuelen); if (args->flags & ATTR_KERNOVAL) { args->valuelen = valuelen; - return(0); + return 0; } if (args->valuelen < valuelen) { args->valuelen = valuelen; - return(XFS_ERROR(ERANGE)); + return XFS_ERROR(ERANGE); } args->valuelen = valuelen; } - return(0); + return 0; } /*======================================================================== @@ -2184,13 +2400,21 @@ xfs_attr_leaf_getvalue( */ /*ARGSUSED*/ STATIC void -xfs_attr_leaf_moveents(xfs_attr_leafblock_t *leaf_s, int start_s, - xfs_attr_leafblock_t *leaf_d, int start_d, - int count, xfs_mount_t *mp) +xfs_attr3_leaf_moveents( + struct xfs_attr_leafblock *leaf_s, + struct xfs_attr3_icleaf_hdr *ichdr_s, + int start_s, + struct xfs_attr_leafblock *leaf_d, + struct xfs_attr3_icleaf_hdr *ichdr_d, + int start_d, + int count, + struct xfs_mount *mp) { - xfs_attr_leaf_hdr_t *hdr_s, *hdr_d; - xfs_attr_leaf_entry_t *entry_s, *entry_d; - int desti, tmp, i; + struct xfs_attr_leaf_entry *entry_s; + struct xfs_attr_leaf_entry *entry_d; + int desti; + int tmp; + int i; /* * Check for nothing to do. @@ -2201,45 +2425,41 @@ xfs_attr_leaf_moveents(xfs_attr_leafblock_t *leaf_s, int start_s, /* * Set up environment. */ - ASSERT(leaf_s->hdr.info.magic == cpu_to_be16(XFS_ATTR_LEAF_MAGIC)); - ASSERT(leaf_d->hdr.info.magic == cpu_to_be16(XFS_ATTR_LEAF_MAGIC)); - hdr_s = &leaf_s->hdr; - hdr_d = &leaf_d->hdr; - ASSERT((be16_to_cpu(hdr_s->count) > 0) && - (be16_to_cpu(hdr_s->count) < (XFS_LBSIZE(mp)/8))); - ASSERT(be16_to_cpu(hdr_s->firstused) >= - ((be16_to_cpu(hdr_s->count) - * sizeof(*entry_s))+sizeof(*hdr_s))); - ASSERT(be16_to_cpu(hdr_d->count) < (XFS_LBSIZE(mp)/8)); - ASSERT(be16_to_cpu(hdr_d->firstused) >= - ((be16_to_cpu(hdr_d->count) - * sizeof(*entry_d))+sizeof(*hdr_d))); - - ASSERT(start_s < be16_to_cpu(hdr_s->count)); - ASSERT(start_d <= be16_to_cpu(hdr_d->count)); - ASSERT(count <= be16_to_cpu(hdr_s->count)); + ASSERT(ichdr_s->magic == XFS_ATTR_LEAF_MAGIC || + ichdr_s->magic == XFS_ATTR3_LEAF_MAGIC); + ASSERT(ichdr_s->magic == ichdr_d->magic); + ASSERT(ichdr_s->count > 0 && ichdr_s->count < XFS_LBSIZE(mp) / 8); + ASSERT(ichdr_s->firstused >= (ichdr_s->count * sizeof(*entry_s)) + + xfs_attr3_leaf_hdr_size(leaf_s)); + ASSERT(ichdr_d->count < XFS_LBSIZE(mp) / 8); + ASSERT(ichdr_d->firstused >= (ichdr_d->count * sizeof(*entry_d)) + + xfs_attr3_leaf_hdr_size(leaf_d)); + + ASSERT(start_s < ichdr_s->count); + ASSERT(start_d <= ichdr_d->count); + ASSERT(count <= ichdr_s->count); + /* * Move the entries in the destination leaf up to make a hole? */ - if (start_d < be16_to_cpu(hdr_d->count)) { - tmp = be16_to_cpu(hdr_d->count) - start_d; + if (start_d < ichdr_d->count) { + tmp = ichdr_d->count - start_d; tmp *= sizeof(xfs_attr_leaf_entry_t); - entry_s = &leaf_d->entries[start_d]; - entry_d = &leaf_d->entries[start_d + count]; - memmove((char *)entry_d, (char *)entry_s, tmp); + entry_s = &xfs_attr3_leaf_entryp(leaf_d)[start_d]; + entry_d = &xfs_attr3_leaf_entryp(leaf_d)[start_d + count]; + memmove(entry_d, entry_s, tmp); } /* * Copy all entry's in the same (sorted) order, * but allocate attribute info packed and in sequence. */ - entry_s = &leaf_s->entries[start_s]; - entry_d = &leaf_d->entries[start_d]; + entry_s = &xfs_attr3_leaf_entryp(leaf_s)[start_s]; + entry_d = &xfs_attr3_leaf_entryp(leaf_d)[start_d]; desti = start_d; for (i = 0; i < count; entry_s++, entry_d++, desti++, i++) { - ASSERT(be16_to_cpu(entry_s->nameidx) - >= be16_to_cpu(hdr_s->firstused)); + ASSERT(be16_to_cpu(entry_s->nameidx) >= ichdr_s->firstused); tmp = xfs_attr_leaf_entsize(leaf_s, start_s + i); #ifdef GROT /* @@ -2248,36 +2468,34 @@ xfs_attr_leaf_moveents(xfs_attr_leafblock_t *leaf_s, int start_s, * off for 6.2, should be revisited later. */ if (entry_s->flags & XFS_ATTR_INCOMPLETE) { /* skip partials? */ - memset(xfs_attr_leaf_name(leaf_s, start_s + i), 0, tmp); - be16_add_cpu(&hdr_s->usedbytes, -tmp); - be16_add_cpu(&hdr_s->count, -1); + memset(xfs_attr3_leaf_name(leaf_s, start_s + i), 0, tmp); + ichdr_s->usedbytes -= tmp; + ichdr_s->count -= 1; entry_d--; /* to compensate for ++ in loop hdr */ desti--; if ((start_s + i) < offset) result++; /* insertion index adjustment */ } else { #endif /* GROT */ - be16_add_cpu(&hdr_d->firstused, -tmp); + ichdr_d->firstused -= tmp; /* both on-disk, don't endian flip twice */ entry_d->hashval = entry_s->hashval; - /* both on-disk, don't endian flip twice */ - entry_d->nameidx = hdr_d->firstused; + entry_d->nameidx = cpu_to_be16(ichdr_d->firstused); entry_d->flags = entry_s->flags; ASSERT(be16_to_cpu(entry_d->nameidx) + tmp <= XFS_LBSIZE(mp)); - memmove(xfs_attr_leaf_name(leaf_d, desti), - xfs_attr_leaf_name(leaf_s, start_s + i), tmp); + memmove(xfs_attr3_leaf_name(leaf_d, desti), + xfs_attr3_leaf_name(leaf_s, start_s + i), tmp); ASSERT(be16_to_cpu(entry_s->nameidx) + tmp <= XFS_LBSIZE(mp)); - memset(xfs_attr_leaf_name(leaf_s, start_s + i), 0, tmp); - be16_add_cpu(&hdr_s->usedbytes, -tmp); - be16_add_cpu(&hdr_d->usedbytes, tmp); - be16_add_cpu(&hdr_s->count, -1); - be16_add_cpu(&hdr_d->count, 1); - tmp = be16_to_cpu(hdr_d->count) - * sizeof(xfs_attr_leaf_entry_t) - + sizeof(xfs_attr_leaf_hdr_t); - ASSERT(be16_to_cpu(hdr_d->firstused) >= tmp); + memset(xfs_attr3_leaf_name(leaf_s, start_s + i), 0, tmp); + ichdr_s->usedbytes -= tmp; + ichdr_d->usedbytes += tmp; + ichdr_s->count -= 1; + ichdr_d->count += 1; + tmp = ichdr_d->count * sizeof(xfs_attr_leaf_entry_t) + + xfs_attr3_leaf_hdr_size(leaf_d); + ASSERT(ichdr_d->firstused >= tmp); #ifdef GROT } #endif /* GROT */ @@ -2286,71 +2504,40 @@ xfs_attr_leaf_moveents(xfs_attr_leafblock_t *leaf_s, int start_s, /* * Zero out the entries we just copied. */ - if (start_s == be16_to_cpu(hdr_s->count)) { + if (start_s == ichdr_s->count) { tmp = count * sizeof(xfs_attr_leaf_entry_t); - entry_s = &leaf_s->entries[start_s]; + entry_s = &xfs_attr3_leaf_entryp(leaf_s)[start_s]; ASSERT(((char *)entry_s + tmp) <= ((char *)leaf_s + XFS_LBSIZE(mp))); - memset((char *)entry_s, 0, tmp); + memset(entry_s, 0, tmp); } else { /* * Move the remaining entries down to fill the hole, * then zero the entries at the top. */ - tmp = be16_to_cpu(hdr_s->count) - count; - tmp *= sizeof(xfs_attr_leaf_entry_t); - entry_s = &leaf_s->entries[start_s + count]; - entry_d = &leaf_s->entries[start_s]; - memmove((char *)entry_d, (char *)entry_s, tmp); + tmp = (ichdr_s->count - count) - sizeof(xfs_attr_leaf_entry_t); + entry_s = &xfs_attr3_leaf_entryp(leaf_s)[start_s + count]; + entry_d = &xfs_attr3_leaf_entryp(leaf_s)[start_s]; + memmove(entry_d, entry_s, tmp); tmp = count * sizeof(xfs_attr_leaf_entry_t); - entry_s = &leaf_s->entries[be16_to_cpu(hdr_s->count)]; + entry_s = &xfs_attr3_leaf_entryp(leaf_s)[ichdr_s->count]; ASSERT(((char *)entry_s + tmp) <= ((char *)leaf_s + XFS_LBSIZE(mp))); - memset((char *)entry_s, 0, tmp); + memset(entry_s, 0, tmp); } /* * Fill in the freemap information */ - hdr_d->freemap[0].base = cpu_to_be16(sizeof(xfs_attr_leaf_hdr_t)); - be16_add_cpu(&hdr_d->freemap[0].base, be16_to_cpu(hdr_d->count) * - sizeof(xfs_attr_leaf_entry_t)); - hdr_d->freemap[0].size = cpu_to_be16(be16_to_cpu(hdr_d->firstused) - - be16_to_cpu(hdr_d->freemap[0].base)); - hdr_d->freemap[1].base = 0; - hdr_d->freemap[2].base = 0; - hdr_d->freemap[1].size = 0; - hdr_d->freemap[2].size = 0; - hdr_s->holes = 1; /* leaf may not be compact */ -} - -/* - * Compare two leaf blocks "order". - * Return 0 unless leaf2 should go before leaf1. - */ -int -xfs_attr_leaf_order( - struct xfs_buf *leaf1_bp, - struct xfs_buf *leaf2_bp) -{ - xfs_attr_leafblock_t *leaf1, *leaf2; - - leaf1 = leaf1_bp->b_addr; - leaf2 = leaf2_bp->b_addr; - ASSERT((leaf1->hdr.info.magic == cpu_to_be16(XFS_ATTR_LEAF_MAGIC)) && - (leaf2->hdr.info.magic == cpu_to_be16(XFS_ATTR_LEAF_MAGIC))); - if ((be16_to_cpu(leaf1->hdr.count) > 0) && - (be16_to_cpu(leaf2->hdr.count) > 0) && - ((be32_to_cpu(leaf2->entries[0].hashval) < - be32_to_cpu(leaf1->entries[0].hashval)) || - (be32_to_cpu(leaf2->entries[ - be16_to_cpu(leaf2->hdr.count)-1].hashval) < - be32_to_cpu(leaf1->entries[ - be16_to_cpu(leaf1->hdr.count)-1].hashval)))) { - return(1); - } - return(0); + ichdr_d->freemap[0].base = xfs_attr3_leaf_hdr_size(leaf_d); + ichdr_d->freemap[0].base += ichdr_d->count * sizeof(xfs_attr_leaf_entry_t); + ichdr_d->freemap[0].size = ichdr_d->firstused - ichdr_d->freemap[0].base; + ichdr_d->freemap[1].base = 0; + ichdr_d->freemap[2].base = 0; + ichdr_d->freemap[1].size = 0; + ichdr_d->freemap[2].size = 0; + ichdr_s->holes = 1; /* leaf may not be compact */ } /* @@ -2361,15 +2548,16 @@ xfs_attr_leaf_lasthash( struct xfs_buf *bp, int *count) { - xfs_attr_leafblock_t *leaf; + struct xfs_attr3_icleaf_hdr ichdr; + struct xfs_attr_leaf_entry *entries; - leaf = bp->b_addr; - ASSERT(leaf->hdr.info.magic == cpu_to_be16(XFS_ATTR_LEAF_MAGIC)); + xfs_attr3_leaf_hdr_from_disk(&ichdr, bp->b_addr); + entries = xfs_attr3_leaf_entryp(bp->b_addr); if (count) - *count = be16_to_cpu(leaf->hdr.count); - if (!leaf->hdr.count) - return(0); - return be32_to_cpu(leaf->entries[be16_to_cpu(leaf->hdr.count)-1].hashval); + *count = ichdr.count; + if (!ichdr.count) + return 0; + return be32_to_cpu(entries[ichdr.count - 1].hashval); } /* @@ -2379,20 +2567,21 @@ xfs_attr_leaf_lasthash( STATIC int xfs_attr_leaf_entsize(xfs_attr_leafblock_t *leaf, int index) { + struct xfs_attr_leaf_entry *entries; xfs_attr_leaf_name_local_t *name_loc; xfs_attr_leaf_name_remote_t *name_rmt; int size; - ASSERT(leaf->hdr.info.magic == cpu_to_be16(XFS_ATTR_LEAF_MAGIC)); - if (leaf->entries[index].flags & XFS_ATTR_LOCAL) { - name_loc = xfs_attr_leaf_name_local(leaf, index); + entries = xfs_attr3_leaf_entryp(leaf); + if (entries[index].flags & XFS_ATTR_LOCAL) { + name_loc = xfs_attr3_leaf_name_local(leaf, index); size = xfs_attr_leaf_entsize_local(name_loc->namelen, be16_to_cpu(name_loc->valuelen)); } else { - name_rmt = xfs_attr_leaf_name_remote(leaf, index); + name_rmt = xfs_attr3_leaf_name_remote(leaf, index); size = xfs_attr_leaf_entsize_remote(name_rmt->namelen); } - return(size); + return size; } /* @@ -2417,35 +2606,40 @@ xfs_attr_leaf_newentsize(int namelen, int valuelen, int blocksize, int *local) *local = 0; } } - return(size); + return size; } /* * Copy out attribute list entries for attr_list(), for leaf attribute lists. */ int -xfs_attr_leaf_list_int( - struct xfs_buf *bp, - xfs_attr_list_context_t *context) +xfs_attr3_leaf_list_int( + struct xfs_buf *bp, + struct xfs_attr_list_context *context) { - attrlist_cursor_kern_t *cursor; - xfs_attr_leafblock_t *leaf; - xfs_attr_leaf_entry_t *entry; - int retval, i; + struct attrlist_cursor_kern *cursor; + struct xfs_attr_leafblock *leaf; + struct xfs_attr3_icleaf_hdr ichdr; + struct xfs_attr_leaf_entry *entries; + struct xfs_attr_leaf_entry *entry; + int retval; + int i; + + trace_xfs_attr_list_leaf(context); - ASSERT(bp != NULL); leaf = bp->b_addr; + xfs_attr3_leaf_hdr_from_disk(&ichdr, leaf); + entries = xfs_attr3_leaf_entryp(leaf); + cursor = context->cursor; cursor->initted = 1; - trace_xfs_attr_list_leaf(context); - /* * Re-find our place in the leaf block if this is a new syscall. */ if (context->resynch) { - entry = &leaf->entries[0]; - for (i = 0; i < be16_to_cpu(leaf->hdr.count); entry++, i++) { + entry = &entries[0]; + for (i = 0; i < ichdr.count; entry++, i++) { if (be32_to_cpu(entry->hashval) == cursor->hashval) { if (cursor->offset == context->dupcnt) { context->dupcnt = 0; @@ -2458,12 +2652,12 @@ xfs_attr_leaf_list_int( break; } } - if (i == be16_to_cpu(leaf->hdr.count)) { + if (i == ichdr.count) { trace_xfs_attr_list_notfound(context); - return(0); + return 0; } } else { - entry = &leaf->entries[0]; + entry = &entries[0]; i = 0; } context->resynch = 0; @@ -2472,7 +2666,7 @@ xfs_attr_leaf_list_int( * We have found our place, start copying out the new attributes. */ retval = 0; - for ( ; (i < be16_to_cpu(leaf->hdr.count)); entry++, i++) { + for (; i < ichdr.count; entry++, i++) { if (be32_to_cpu(entry->hashval) != cursor->hashval) { cursor->hashval = be32_to_cpu(entry->hashval); cursor->offset = 0; @@ -2483,7 +2677,7 @@ xfs_attr_leaf_list_int( if (entry->flags & XFS_ATTR_LOCAL) { xfs_attr_leaf_name_local_t *name_loc = - xfs_attr_leaf_name_local(leaf, i); + xfs_attr3_leaf_name_local(leaf, i); retval = context->put_listent(context, entry->flags, @@ -2495,7 +2689,7 @@ xfs_attr_leaf_list_int( return retval; } else { xfs_attr_leaf_name_remote_t *name_rmt = - xfs_attr_leaf_name_remote(leaf, i); + xfs_attr3_leaf_name_remote(leaf, i); int valuelen = be32_to_cpu(name_rmt->valuelen); @@ -2535,7 +2729,7 @@ xfs_attr_leaf_list_int( cursor->offset++; } trace_xfs_attr_list_leaf_end(context); - return(retval); + return retval; } @@ -2547,14 +2741,16 @@ xfs_attr_leaf_list_int( * Clear the INCOMPLETE flag on an entry in a leaf block. */ int -xfs_attr_leaf_clearflag(xfs_da_args_t *args) +xfs_attr3_leaf_clearflag( + struct xfs_da_args *args) { - xfs_attr_leafblock_t *leaf; - xfs_attr_leaf_entry_t *entry; - xfs_attr_leaf_name_remote_t *name_rmt; - struct xfs_buf *bp; - int error; + struct xfs_attr_leafblock *leaf; + struct xfs_attr_leaf_entry *entry; + struct xfs_attr_leaf_name_remote *name_rmt; + struct xfs_buf *bp; + int error; #ifdef DEBUG + struct xfs_attr3_icleaf_hdr ichdr; xfs_attr_leaf_name_local_t *name_loc; int namelen; char *name; @@ -2564,23 +2760,25 @@ xfs_attr_leaf_clearflag(xfs_da_args_t *args) /* * Set up the operation. */ - error = xfs_attr_leaf_read(args->trans, args->dp, args->blkno, -1, &bp); + error = xfs_attr3_leaf_read(args->trans, args->dp, args->blkno, -1, &bp); if (error) return(error); leaf = bp->b_addr; - ASSERT(args->index < be16_to_cpu(leaf->hdr.count)); - ASSERT(args->index >= 0); - entry = &leaf->entries[ args->index ]; + entry = &xfs_attr3_leaf_entryp(leaf)[args->index]; ASSERT(entry->flags & XFS_ATTR_INCOMPLETE); #ifdef DEBUG + xfs_attr3_leaf_hdr_from_disk(&ichdr, leaf); + ASSERT(args->index < ichdr.count); + ASSERT(args->index >= 0); + if (entry->flags & XFS_ATTR_LOCAL) { - name_loc = xfs_attr_leaf_name_local(leaf, args->index); + name_loc = xfs_attr3_leaf_name_local(leaf, args->index); namelen = name_loc->namelen; name = (char *)name_loc->nameval; } else { - name_rmt = xfs_attr_leaf_name_remote(leaf, args->index); + name_rmt = xfs_attr3_leaf_name_remote(leaf, args->index); namelen = name_rmt->namelen; name = (char *)name_rmt->name; } @@ -2595,7 +2793,7 @@ xfs_attr_leaf_clearflag(xfs_da_args_t *args) if (args->rmtblkno) { ASSERT((entry->flags & XFS_ATTR_LOCAL) == 0); - name_rmt = xfs_attr_leaf_name_remote(leaf, args->index); + name_rmt = xfs_attr3_leaf_name_remote(leaf, args->index); name_rmt->valueblk = cpu_to_be32(args->rmtblkno); name_rmt->valuelen = cpu_to_be32(args->valuelen); xfs_trans_log_buf(args->trans, bp, @@ -2612,34 +2810,41 @@ xfs_attr_leaf_clearflag(xfs_da_args_t *args) * Set the INCOMPLETE flag on an entry in a leaf block. */ int -xfs_attr_leaf_setflag(xfs_da_args_t *args) +xfs_attr3_leaf_setflag( + struct xfs_da_args *args) { - xfs_attr_leafblock_t *leaf; - xfs_attr_leaf_entry_t *entry; - xfs_attr_leaf_name_remote_t *name_rmt; - struct xfs_buf *bp; + struct xfs_attr_leafblock *leaf; + struct xfs_attr_leaf_entry *entry; + struct xfs_attr_leaf_name_remote *name_rmt; + struct xfs_buf *bp; int error; +#ifdef DEBUG + struct xfs_attr3_icleaf_hdr ichdr; +#endif trace_xfs_attr_leaf_setflag(args); /* * Set up the operation. */ - error = xfs_attr_leaf_read(args->trans, args->dp, args->blkno, -1, &bp); + error = xfs_attr3_leaf_read(args->trans, args->dp, args->blkno, -1, &bp); if (error) return(error); leaf = bp->b_addr; - ASSERT(args->index < be16_to_cpu(leaf->hdr.count)); +#ifdef DEBUG + xfs_attr3_leaf_hdr_from_disk(&ichdr, leaf); + ASSERT(args->index < ichdr.count); ASSERT(args->index >= 0); - entry = &leaf->entries[ args->index ]; +#endif + entry = &xfs_attr3_leaf_entryp(leaf)[args->index]; ASSERT((entry->flags & XFS_ATTR_INCOMPLETE) == 0); entry->flags |= XFS_ATTR_INCOMPLETE; xfs_trans_log_buf(args->trans, bp, XFS_DA_LOGRANGE(leaf, entry, sizeof(*entry))); if ((entry->flags & XFS_ATTR_LOCAL) == 0) { - name_rmt = xfs_attr_leaf_name_remote(leaf, args->index); + name_rmt = xfs_attr3_leaf_name_remote(leaf, args->index); name_rmt->valueblk = 0; name_rmt->valuelen = 0; xfs_trans_log_buf(args->trans, bp, @@ -2660,14 +2865,20 @@ xfs_attr_leaf_setflag(xfs_da_args_t *args) * Note that they could be in different blocks, or in the same block. */ int -xfs_attr_leaf_flipflags(xfs_da_args_t *args) +xfs_attr3_leaf_flipflags( + struct xfs_da_args *args) { - xfs_attr_leafblock_t *leaf1, *leaf2; - xfs_attr_leaf_entry_t *entry1, *entry2; - xfs_attr_leaf_name_remote_t *name_rmt; - struct xfs_buf *bp1, *bp2; + struct xfs_attr_leafblock *leaf1; + struct xfs_attr_leafblock *leaf2; + struct xfs_attr_leaf_entry *entry1; + struct xfs_attr_leaf_entry *entry2; + struct xfs_attr_leaf_name_remote *name_rmt; + struct xfs_buf *bp1; + struct xfs_buf *bp2; int error; #ifdef DEBUG + struct xfs_attr3_icleaf_hdr ichdr1; + struct xfs_attr3_icleaf_hdr ichdr2; xfs_attr_leaf_name_local_t *name_loc; int namelen1, namelen2; char *name1, *name2; @@ -2678,7 +2889,7 @@ xfs_attr_leaf_flipflags(xfs_da_args_t *args) /* * Read the block containing the "old" attr */ - error = xfs_attr_leaf_read(args->trans, args->dp, args->blkno, -1, &bp1); + error = xfs_attr3_leaf_read(args->trans, args->dp, args->blkno, -1, &bp1); if (error) return error; @@ -2686,7 +2897,7 @@ xfs_attr_leaf_flipflags(xfs_da_args_t *args) * Read the block containing the "new" attr, if it is different */ if (args->blkno2 != args->blkno) { - error = xfs_attr_leaf_read(args->trans, args->dp, args->blkno2, + error = xfs_attr3_leaf_read(args->trans, args->dp, args->blkno2, -1, &bp2); if (error) return error; @@ -2695,31 +2906,35 @@ xfs_attr_leaf_flipflags(xfs_da_args_t *args) } leaf1 = bp1->b_addr; - ASSERT(args->index < be16_to_cpu(leaf1->hdr.count)); - ASSERT(args->index >= 0); - entry1 = &leaf1->entries[ args->index ]; + entry1 = &xfs_attr3_leaf_entryp(leaf1)[args->index]; leaf2 = bp2->b_addr; - ASSERT(args->index2 < be16_to_cpu(leaf2->hdr.count)); - ASSERT(args->index2 >= 0); - entry2 = &leaf2->entries[ args->index2 ]; + entry2 = &xfs_attr3_leaf_entryp(leaf2)[args->index2]; #ifdef DEBUG + xfs_attr3_leaf_hdr_from_disk(&ichdr1, leaf1); + ASSERT(args->index < ichdr1.count); + ASSERT(args->index >= 0); + + xfs_attr3_leaf_hdr_from_disk(&ichdr2, leaf2); + ASSERT(args->index2 < ichdr2.count); + ASSERT(args->index2 >= 0); + if (entry1->flags & XFS_ATTR_LOCAL) { - name_loc = xfs_attr_leaf_name_local(leaf1, args->index); + name_loc = xfs_attr3_leaf_name_local(leaf1, args->index); namelen1 = name_loc->namelen; name1 = (char *)name_loc->nameval; } else { - name_rmt = xfs_attr_leaf_name_remote(leaf1, args->index); + name_rmt = xfs_attr3_leaf_name_remote(leaf1, args->index); namelen1 = name_rmt->namelen; name1 = (char *)name_rmt->name; } if (entry2->flags & XFS_ATTR_LOCAL) { - name_loc = xfs_attr_leaf_name_local(leaf2, args->index2); + name_loc = xfs_attr3_leaf_name_local(leaf2, args->index2); namelen2 = name_loc->namelen; name2 = (char *)name_loc->nameval; } else { - name_rmt = xfs_attr_leaf_name_remote(leaf2, args->index2); + name_rmt = xfs_attr3_leaf_name_remote(leaf2, args->index2); namelen2 = name_rmt->namelen; name2 = (char *)name_rmt->name; } @@ -2736,7 +2951,7 @@ xfs_attr_leaf_flipflags(xfs_da_args_t *args) XFS_DA_LOGRANGE(leaf1, entry1, sizeof(*entry1))); if (args->rmtblkno) { ASSERT((entry1->flags & XFS_ATTR_LOCAL) == 0); - name_rmt = xfs_attr_leaf_name_remote(leaf1, args->index); + name_rmt = xfs_attr3_leaf_name_remote(leaf1, args->index); name_rmt->valueblk = cpu_to_be32(args->rmtblkno); name_rmt->valuelen = cpu_to_be32(args->valuelen); xfs_trans_log_buf(args->trans, bp1, @@ -2747,7 +2962,7 @@ xfs_attr_leaf_flipflags(xfs_da_args_t *args) xfs_trans_log_buf(args->trans, bp2, XFS_DA_LOGRANGE(leaf2, entry2, sizeof(*entry2))); if ((entry2->flags & XFS_ATTR_LOCAL) == 0) { - name_rmt = xfs_attr_leaf_name_remote(leaf2, args->index2); + name_rmt = xfs_attr3_leaf_name_remote(leaf2, args->index2); name_rmt->valueblk = 0; name_rmt->valuelen = 0; xfs_trans_log_buf(args->trans, bp2, @@ -2759,7 +2974,7 @@ xfs_attr_leaf_flipflags(xfs_da_args_t *args) */ error = xfs_trans_roll(&args->trans, args->dp); - return(error); + return error; } /*======================================================================== @@ -2771,12 +2986,14 @@ xfs_attr_leaf_flipflags(xfs_da_args_t *args) * We're doing a depth-first traversal in order to invalidate everything. */ int -xfs_attr_root_inactive(xfs_trans_t **trans, xfs_inode_t *dp) +xfs_attr3_root_inactive( + struct xfs_trans **trans, + struct xfs_inode *dp) { - xfs_da_blkinfo_t *info; - xfs_daddr_t blkno; - struct xfs_buf *bp; - int error; + struct xfs_da_blkinfo *info; + struct xfs_buf *bp; + xfs_daddr_t blkno; + int error; /* * Read block 0 to see what we have to work with. @@ -2786,38 +3003,44 @@ xfs_attr_root_inactive(xfs_trans_t **trans, xfs_inode_t *dp) */ error = xfs_da3_node_read(*trans, dp, 0, -1, &bp, XFS_ATTR_FORK); if (error) - return(error); - blkno = XFS_BUF_ADDR(bp); + return error; + blkno = bp->b_bn; /* * Invalidate the tree, even if the "tree" is only a single leaf block. * This is a depth-first traversal! */ info = bp->b_addr; - if (info->magic == cpu_to_be16(XFS_DA_NODE_MAGIC)) { - error = xfs_attr_node_inactive(trans, dp, bp, 1); - } else if (info->magic == cpu_to_be16(XFS_ATTR_LEAF_MAGIC)) { - error = xfs_attr_leaf_inactive(trans, dp, bp); - } else { + switch (info->magic) { + case cpu_to_be16(XFS_DA_NODE_MAGIC): + case cpu_to_be16(XFS_DA3_NODE_MAGIC): + error = xfs_attr3_node_inactive(trans, dp, bp, 1); + break; + case cpu_to_be16(XFS_ATTR_LEAF_MAGIC): + case cpu_to_be16(XFS_ATTR3_LEAF_MAGIC): + error = xfs_attr3_leaf_inactive(trans, dp, bp); + break; + default: error = XFS_ERROR(EIO); xfs_trans_brelse(*trans, bp); + break; } if (error) - return(error); + return error; /* * Invalidate the incore copy of the root block. */ error = xfs_da_get_buf(*trans, dp, 0, blkno, &bp, XFS_ATTR_FORK); if (error) - return(error); + return error; xfs_trans_binval(*trans, bp); /* remove from cache */ /* * Commit the invalidate and start the next transaction. */ error = xfs_trans_roll(trans, dp); - return (error); + return error; } /* @@ -2825,7 +3048,7 @@ xfs_attr_root_inactive(xfs_trans_t **trans, xfs_inode_t *dp) * We're doing a depth-first traversal in order to invalidate everything. */ STATIC int -xfs_attr_node_inactive( +xfs_attr3_node_inactive( struct xfs_trans **trans, struct xfs_inode *dp, struct xfs_buf *bp, @@ -2835,25 +3058,25 @@ xfs_attr_node_inactive( xfs_da_intnode_t *node; xfs_dablk_t child_fsb; xfs_daddr_t parent_blkno, child_blkno; - int error, count, i; + int error, i; struct xfs_buf *child_bp; struct xfs_da_node_entry *btree; + struct xfs_da3_icnode_hdr ichdr; /* * Since this code is recursive (gasp!) we must protect ourselves. */ if (level > XFS_DA_NODE_MAXDEPTH) { xfs_trans_brelse(*trans, bp); /* no locks for later trans */ - return(XFS_ERROR(EIO)); + return XFS_ERROR(EIO); } node = bp->b_addr; - ASSERT(node->hdr.info.magic == cpu_to_be16(XFS_DA_NODE_MAGIC)); - parent_blkno = XFS_BUF_ADDR(bp); /* save for re-read later */ - count = be16_to_cpu(node->hdr.count); - if (!count) { + xfs_da3_node_hdr_from_disk(&ichdr, node); + parent_blkno = bp->b_bn; + if (!ichdr.count) { xfs_trans_brelse(*trans, bp); - return(0); + return 0; } btree = xfs_da3_node_tree_p(node); child_fsb = be32_to_cpu(btree[0].before); @@ -2864,7 +3087,7 @@ xfs_attr_node_inactive( * over the leaves removing all of them. If this is higher up * in the tree, recurse downward. */ - for (i = 0; i < count; i++) { + for (i = 0; i < ichdr.count; i++) { /* * Read the subsidiary block to see what we have to work with. * Don't do this in a transaction. This is a depth-first @@ -2883,18 +3106,24 @@ xfs_attr_node_inactive( * Invalidate the subtree, however we have to. */ info = child_bp->b_addr; - if (info->magic == cpu_to_be16(XFS_DA_NODE_MAGIC)) { - error = xfs_attr_node_inactive(trans, dp, - child_bp, level+1); - } else if (info->magic == cpu_to_be16(XFS_ATTR_LEAF_MAGIC)) { - error = xfs_attr_leaf_inactive(trans, dp, - child_bp); - } else { + switch (info->magic) { + case cpu_to_be16(XFS_DA_NODE_MAGIC): + case cpu_to_be16(XFS_DA3_NODE_MAGIC): + error = xfs_attr3_node_inactive(trans, dp, + child_bp, level + 1); + break; + case cpu_to_be16(XFS_ATTR_LEAF_MAGIC): + case cpu_to_be16(XFS_ATTR3_LEAF_MAGIC): + error = xfs_attr3_leaf_inactive(trans, dp, + child_bp); + break; + default: error = XFS_ERROR(EIO); xfs_trans_brelse(*trans, child_bp); + break; } if (error) - return(error); + return error; /* * Remove the subsidiary block from the cache @@ -2903,7 +3132,7 @@ xfs_attr_node_inactive( error = xfs_da_get_buf(*trans, dp, 0, child_blkno, &child_bp, XFS_ATTR_FORK); if (error) - return(error); + return error; xfs_trans_binval(*trans, child_bp); } @@ -2911,12 +3140,12 @@ xfs_attr_node_inactive( * If we're not done, re-read the parent to get the next * child block number. */ - if ((i+1) < count) { + if (i + 1 < ichdr.count) { error = xfs_da3_node_read(*trans, dp, 0, parent_blkno, &bp, XFS_ATTR_FORK); if (error) - return(error); - child_fsb = be32_to_cpu(btree[i+1].before); + return error; + child_fsb = be32_to_cpu(btree[i + 1].before); xfs_trans_brelse(*trans, bp); } /* @@ -2924,10 +3153,10 @@ xfs_attr_node_inactive( */ error = xfs_trans_roll(trans, dp); if (error) - return (error); + return error; } - return(0); + return 0; } /* @@ -2937,29 +3166,35 @@ xfs_attr_node_inactive( * caught holding something that the logging code wants to flush to disk. */ STATIC int -xfs_attr_leaf_inactive( - struct xfs_trans **trans, - struct xfs_inode *dp, - struct xfs_buf *bp) +xfs_attr3_leaf_inactive( + struct xfs_trans **trans, + struct xfs_inode *dp, + struct xfs_buf *bp) { - xfs_attr_leafblock_t *leaf; - xfs_attr_leaf_entry_t *entry; - xfs_attr_leaf_name_remote_t *name_rmt; - xfs_attr_inactive_list_t *list, *lp; - int error, count, size, tmp, i; + struct xfs_attr_leafblock *leaf; + struct xfs_attr3_icleaf_hdr ichdr; + struct xfs_attr_leaf_entry *entry; + struct xfs_attr_leaf_name_remote *name_rmt; + struct xfs_attr_inactive_list *list; + struct xfs_attr_inactive_list *lp; + int error; + int count; + int size; + int tmp; + int i; leaf = bp->b_addr; - ASSERT(leaf->hdr.info.magic == cpu_to_be16(XFS_ATTR_LEAF_MAGIC)); + xfs_attr3_leaf_hdr_from_disk(&ichdr, leaf); /* * Count the number of "remote" value extents. */ count = 0; - entry = &leaf->entries[0]; - for (i = 0; i < be16_to_cpu(leaf->hdr.count); entry++, i++) { + entry = xfs_attr3_leaf_entryp(leaf); + for (i = 0; i < ichdr.count; entry++, i++) { if (be16_to_cpu(entry->nameidx) && ((entry->flags & XFS_ATTR_LOCAL) == 0)) { - name_rmt = xfs_attr_leaf_name_remote(leaf, i); + name_rmt = xfs_attr3_leaf_name_remote(leaf, i); if (name_rmt->valueblk) count++; } @@ -2970,24 +3205,24 @@ xfs_attr_leaf_inactive( */ if (count == 0) { xfs_trans_brelse(*trans, bp); - return(0); + return 0; } /* * Allocate storage for a list of all the "remote" value extents. */ size = count * sizeof(xfs_attr_inactive_list_t); - list = (xfs_attr_inactive_list_t *)kmem_alloc(size, KM_SLEEP); + list = kmem_alloc(size, KM_SLEEP); /* * Identify each of the "remote" value extents. */ lp = list; - entry = &leaf->entries[0]; - for (i = 0; i < be16_to_cpu(leaf->hdr.count); entry++, i++) { + entry = xfs_attr3_leaf_entryp(leaf); + for (i = 0; i < ichdr.count; entry++, i++) { if (be16_to_cpu(entry->nameidx) && ((entry->flags & XFS_ATTR_LOCAL) == 0)) { - name_rmt = xfs_attr_leaf_name_remote(leaf, i); + name_rmt = xfs_attr3_leaf_name_remote(leaf, i); if (name_rmt->valueblk) { lp->valueblk = be32_to_cpu(name_rmt->valueblk); lp->valuelen = XFS_B_TO_FSB(dp->i_mount, @@ -3003,15 +3238,15 @@ xfs_attr_leaf_inactive( */ error = 0; for (lp = list, i = 0; i < count; i++, lp++) { - tmp = xfs_attr_leaf_freextent(trans, dp, + tmp = xfs_attr3_leaf_freextent(trans, dp, lp->valueblk, lp->valuelen); if (error == 0) error = tmp; /* save only the 1st errno */ } - kmem_free((xfs_caddr_t)list); - return(error); + kmem_free(list); + return error; } /* @@ -3019,14 +3254,20 @@ xfs_attr_leaf_inactive( * invalidate any buffers that are incore/in transactions. */ STATIC int -xfs_attr_leaf_freextent(xfs_trans_t **trans, xfs_inode_t *dp, - xfs_dablk_t blkno, int blkcnt) +xfs_attr3_leaf_freextent( + struct xfs_trans **trans, + struct xfs_inode *dp, + xfs_dablk_t blkno, + int blkcnt) { - xfs_bmbt_irec_t map; - xfs_dablk_t tblkno; - int tblkcnt, dblkcnt, nmap, error; - xfs_daddr_t dblkno; - xfs_buf_t *bp; + struct xfs_bmbt_irec map; + struct xfs_buf *bp; + xfs_dablk_t tblkno; + xfs_daddr_t dblkno; + int tblkcnt; + int dblkcnt; + int nmap; + int error; /* * Roll through the "value", invalidating the attribute value's diff --git a/fs/xfs/xfs_attr_leaf.h b/fs/xfs/xfs_attr_leaf.h index 77de139..f9d7846 100644 --- a/fs/xfs/xfs_attr_leaf.h +++ b/fs/xfs/xfs_attr_leaf.h @@ -1,5 +1,6 @@ /* * Copyright (c) 2000,2002-2003,2005 Silicon Graphics, Inc. + * Copyright (c) 2013 Red Hat, Inc. * All Rights Reserved. * * This program is free software; you can redistribute it and/or @@ -89,7 +90,7 @@ typedef struct xfs_attr_leaf_hdr { /* constant-structure header block */ typedef struct xfs_attr_leaf_entry { /* sorted on key, not name */ __be32 hashval; /* hash value of name */ - __be16 nameidx; /* index into buffer of name/value */ + __be16 nameidx; /* index into buffer of name/value */ __u8 flags; /* LOCAL/ROOT/SECURE/INCOMPLETE flag */ __u8 pad2; /* unused pad byte */ } xfs_attr_leaf_entry_t; @@ -115,6 +116,54 @@ typedef struct xfs_attr_leafblock { } xfs_attr_leafblock_t; /* + * CRC enabled leaf structures. Called "version 3" structures to match the + * version number of the directory and dablk structures for this feature, and + * attr2 is already taken by the variable inode attribute fork size feature. + */ +struct xfs_attr3_leaf_hdr { + struct xfs_da3_blkinfo info; + __be16 count; + __be16 usedbytes; + __be16 firstused; + __u8 holes; + __u8 pad1; + struct xfs_attr_leaf_map freemap[XFS_ATTR_LEAF_MAPSIZE]; +}; + +#define XFS_ATTR3_LEAF_CRC_OFF (offsetof(struct xfs_attr3_leaf_hdr, info.crc)) + +struct xfs_attr3_leafblock { + struct xfs_attr3_leaf_hdr hdr; + struct xfs_attr_leaf_entry entries[1]; + + /* + * The rest of the block contains the following structures after the + * leaf entries, growing from the bottom up. The variables are never + * referenced, the locations accessed purely from helper functions. + * + * struct xfs_attr_leaf_name_local + * struct xfs_attr_leaf_name_remote + */ +}; + +/* + * incore, neutral version of the attribute leaf header + */ +struct xfs_attr3_icleaf_hdr { + __uint32_t forw; + __uint32_t back; + __uint16_t magic; + __uint16_t count; + __uint16_t usedbytes; + __uint16_t firstused; + __u8 holes; + struct { + __uint16_t base; + __uint16_t size; + } freemap[XFS_ATTR_LEAF_MAPSIZE]; +}; + +/* * Flags used in the leaf_entry[i].flags field. * NOTE: the INCOMPLETE bit must not collide with the flags bits specified * on the system call, they are "or"ed together for various operations. @@ -147,26 +196,43 @@ typedef struct xfs_attr_leafblock { */ #define XFS_ATTR_LEAF_NAME_ALIGN ((uint)sizeof(xfs_dablk_t)) +static inline int +xfs_attr3_leaf_hdr_size(struct xfs_attr_leafblock *leafp) +{ + if (leafp->hdr.info.magic == cpu_to_be16(XFS_ATTR3_LEAF_MAGIC)) + return sizeof(struct xfs_attr3_leaf_hdr); + return sizeof(struct xfs_attr_leaf_hdr); +} + +static inline struct xfs_attr_leaf_entry * +xfs_attr3_leaf_entryp(xfs_attr_leafblock_t *leafp) +{ + if (leafp->hdr.info.magic == cpu_to_be16(XFS_ATTR3_LEAF_MAGIC)) + return &((struct xfs_attr3_leafblock *)leafp)->entries[0]; + return &leafp->entries[0]; +} + /* * Cast typed pointers for "local" and "remote" name/value structs. */ -static inline xfs_attr_leaf_name_remote_t * -xfs_attr_leaf_name_remote(xfs_attr_leafblock_t *leafp, int idx) +static inline char * +xfs_attr3_leaf_name(xfs_attr_leafblock_t *leafp, int idx) { - return (xfs_attr_leaf_name_remote_t *) - &((char *)leafp)[be16_to_cpu(leafp->entries[idx].nameidx)]; + struct xfs_attr_leaf_entry *entries = xfs_attr3_leaf_entryp(leafp); + + return &((char *)leafp)[be16_to_cpu(entries[idx].nameidx)]; } -static inline xfs_attr_leaf_name_local_t * -xfs_attr_leaf_name_local(xfs_attr_leafblock_t *leafp, int idx) +static inline xfs_attr_leaf_name_remote_t * +xfs_attr3_leaf_name_remote(xfs_attr_leafblock_t *leafp, int idx) { - return (xfs_attr_leaf_name_local_t *) - &((char *)leafp)[be16_to_cpu(leafp->entries[idx].nameidx)]; + return (xfs_attr_leaf_name_remote_t *)xfs_attr3_leaf_name(leafp, idx); } -static inline char *xfs_attr_leaf_name(xfs_attr_leafblock_t *leafp, int idx) +static inline xfs_attr_leaf_name_local_t * +xfs_attr3_leaf_name_local(xfs_attr_leafblock_t *leafp, int idx) { - return &((char *)leafp)[be16_to_cpu(leafp->entries[idx].nameidx)]; + return (xfs_attr_leaf_name_local_t *)xfs_attr3_leaf_name(leafp, idx); } /* @@ -221,37 +287,37 @@ int xfs_attr_shortform_bytesfit(xfs_inode_t *dp, int bytes); /* * Internal routines when attribute fork size == XFS_LBSIZE(mp). */ -int xfs_attr_leaf_to_node(struct xfs_da_args *args); -int xfs_attr_leaf_to_shortform(struct xfs_buf *bp, +int xfs_attr3_leaf_to_node(struct xfs_da_args *args); +int xfs_attr3_leaf_to_shortform(struct xfs_buf *bp, struct xfs_da_args *args, int forkoff); -int xfs_attr_leaf_clearflag(struct xfs_da_args *args); -int xfs_attr_leaf_setflag(struct xfs_da_args *args); -int xfs_attr_leaf_flipflags(xfs_da_args_t *args); +int xfs_attr3_leaf_clearflag(struct xfs_da_args *args); +int xfs_attr3_leaf_setflag(struct xfs_da_args *args); +int xfs_attr3_leaf_flipflags(struct xfs_da_args *args); /* * Routines used for growing the Btree. */ -int xfs_attr_leaf_split(struct xfs_da_state *state, +int xfs_attr3_leaf_split(struct xfs_da_state *state, struct xfs_da_state_blk *oldblk, struct xfs_da_state_blk *newblk); -int xfs_attr_leaf_lookup_int(struct xfs_buf *leaf, +int xfs_attr3_leaf_lookup_int(struct xfs_buf *leaf, struct xfs_da_args *args); -int xfs_attr_leaf_getvalue(struct xfs_buf *bp, struct xfs_da_args *args); -int xfs_attr_leaf_add(struct xfs_buf *leaf_buffer, +int xfs_attr3_leaf_getvalue(struct xfs_buf *bp, struct xfs_da_args *args); +int xfs_attr3_leaf_add(struct xfs_buf *leaf_buffer, struct xfs_da_args *args); -int xfs_attr_leaf_remove(struct xfs_buf *leaf_buffer, +int xfs_attr3_leaf_remove(struct xfs_buf *leaf_buffer, struct xfs_da_args *args); -int xfs_attr_leaf_list_int(struct xfs_buf *bp, +int xfs_attr3_leaf_list_int(struct xfs_buf *bp, struct xfs_attr_list_context *context); /* * Routines used for shrinking the Btree. */ -int xfs_attr_leaf_toosmall(struct xfs_da_state *state, int *retval); -void xfs_attr_leaf_unbalance(struct xfs_da_state *state, +int xfs_attr3_leaf_toosmall(struct xfs_da_state *state, int *retval); +void xfs_attr3_leaf_unbalance(struct xfs_da_state *state, struct xfs_da_state_blk *drop_blk, struct xfs_da_state_blk *save_blk); -int xfs_attr_root_inactive(struct xfs_trans **trans, struct xfs_inode *dp); +int xfs_attr3_root_inactive(struct xfs_trans **trans, struct xfs_inode *dp); /* * Utility routines. @@ -261,10 +327,12 @@ int xfs_attr_leaf_order(struct xfs_buf *leaf1_bp, struct xfs_buf *leaf2_bp); int xfs_attr_leaf_newentsize(int namelen, int valuelen, int blocksize, int *local); -int xfs_attr_leaf_read(struct xfs_trans *tp, struct xfs_inode *dp, +int xfs_attr3_leaf_read(struct xfs_trans *tp, struct xfs_inode *dp, xfs_dablk_t bno, xfs_daddr_t mappedbno, struct xfs_buf **bpp); +void xfs_attr3_leaf_hdr_from_disk(struct xfs_attr3_icleaf_hdr *to, + struct xfs_attr_leafblock *from); -extern const struct xfs_buf_ops xfs_attr_leaf_buf_ops; +extern const struct xfs_buf_ops xfs_attr3_leaf_buf_ops; #endif /* __XFS_ATTR_LEAF_H__ */ diff --git a/fs/xfs/xfs_da_btree.c b/fs/xfs/xfs_da_btree.c index a824edd..9939764 100644 --- a/fs/xfs/xfs_da_btree.c +++ b/fs/xfs/xfs_da_btree.c @@ -143,14 +143,14 @@ xfs_da3_node_hdr_from_disk( to->forw = be32_to_cpu(hdr3->info.hdr.forw); to->back = be32_to_cpu(hdr3->info.hdr.back); to->magic = be16_to_cpu(hdr3->info.hdr.magic); - to->count = be16_to_cpu(hdr3->count); + to->count = be16_to_cpu(hdr3->__count); to->level = be16_to_cpu(hdr3->__level); return; } to->forw = be32_to_cpu(from->hdr.info.forw); to->back = be32_to_cpu(from->hdr.info.back); to->magic = be16_to_cpu(from->hdr.info.magic); - to->count = be16_to_cpu(from->hdr.count); + to->count = be16_to_cpu(from->hdr.__count); to->level = be16_to_cpu(from->hdr.__level); } @@ -168,14 +168,14 @@ xfs_da3_node_hdr_to_disk( hdr3->info.hdr.forw = cpu_to_be32(from->forw); hdr3->info.hdr.back = cpu_to_be32(from->back); hdr3->info.hdr.magic = cpu_to_be16(from->magic); - hdr3->count = cpu_to_be16(from->count); + hdr3->__count = cpu_to_be16(from->count); hdr3->__level = cpu_to_be16(from->level); return; } to->hdr.info.forw = cpu_to_be32(from->forw); to->hdr.info.back = cpu_to_be32(from->back); to->hdr.info.magic = cpu_to_be16(from->magic); - to->hdr.count = cpu_to_be16(from->count); + to->hdr.__count = cpu_to_be16(from->count); to->hdr.__level = cpu_to_be16(from->level); } @@ -270,7 +270,7 @@ xfs_da3_node_read_verify( break; return; case XFS_ATTR_LEAF_MAGIC: - bp->b_ops = &xfs_attr_leaf_buf_ops; + bp->b_ops = &xfs_attr3_leaf_buf_ops; bp->b_ops->verify_read(bp); return; case XFS_DIR2_LEAFN_MAGIC: @@ -401,7 +401,7 @@ xfs_da3_split( */ switch (oldblk->magic) { case XFS_ATTR_LEAF_MAGIC: - error = xfs_attr_leaf_split(state, oldblk, newblk); + error = xfs_attr3_leaf_split(state, oldblk, newblk); if ((error != 0) && (error != ENOSPC)) { return(error); /* GROT: attr is inconsistent */ } @@ -416,12 +416,12 @@ xfs_da3_split( if (state->inleaf) { state->extraafter = 0; /* before newblk */ trace_xfs_attr_leaf_split_before(state->args); - error = xfs_attr_leaf_split(state, oldblk, + error = xfs_attr3_leaf_split(state, oldblk, &state->extrablk); } else { state->extraafter = 1; /* after newblk */ trace_xfs_attr_leaf_split_after(state->args); - error = xfs_attr_leaf_split(state, newblk, + error = xfs_attr3_leaf_split(state, newblk, &state->extrablk); } if (error) @@ -961,12 +961,12 @@ xfs_da3_join( */ switch (drop_blk->magic) { case XFS_ATTR_LEAF_MAGIC: - error = xfs_attr_leaf_toosmall(state, &action); + error = xfs_attr3_leaf_toosmall(state, &action); if (error) return(error); if (action == 0) return(0); - xfs_attr_leaf_unbalance(state, drop_blk, save_blk); + xfs_attr3_leaf_unbalance(state, drop_blk, save_blk); break; case XFS_DIR2_LEAFN_MAGIC: error = xfs_dir2_leafn_toosmall(state, &action); @@ -1022,7 +1022,8 @@ xfs_da_blkinfo_onlychild_validate(struct xfs_da_blkinfo *blkinfo, __u16 level) if (level == 1) { ASSERT(magic == cpu_to_be16(XFS_DIR2_LEAFN_MAGIC) || magic == cpu_to_be16(XFS_DIR3_LEAFN_MAGIC) || - magic == cpu_to_be16(XFS_ATTR_LEAF_MAGIC)); + magic == cpu_to_be16(XFS_ATTR_LEAF_MAGIC) || + magic == cpu_to_be16(XFS_ATTR3_LEAF_MAGIC)); } else { ASSERT(magic == cpu_to_be16(XFS_DA_NODE_MAGIC) || magic == cpu_to_be16(XFS_DA3_NODE_MAGIC)); @@ -1479,7 +1480,9 @@ xfs_da3_node_lookup_int( curr = blk->bp->b_addr; blk->magic = be16_to_cpu(curr->magic); - if (blk->magic == XFS_ATTR_LEAF_MAGIC) { + if (blk->magic == XFS_ATTR_LEAF_MAGIC || + blk->magic == XFS_ATTR3_LEAF_MAGIC) { + blk->magic = XFS_ATTR_LEAF_MAGIC; blk->hashval = xfs_attr_leaf_lasthash(blk->bp, NULL); break; } @@ -1559,7 +1562,7 @@ xfs_da3_node_lookup_int( retval = xfs_dir2_leafn_lookup_int(blk->bp, args, &blk->index, state); } else if (blk->magic == XFS_ATTR_LEAF_MAGIC) { - retval = xfs_attr_leaf_lookup_int(blk->bp, args); + retval = xfs_attr3_leaf_lookup_int(blk->bp, args); blk->index = args->index; args->blkno = blk->blkno; } else { @@ -1871,7 +1874,8 @@ xfs_da3_path_shift( info->magic == cpu_to_be16(XFS_DA3_NODE_MAGIC) || info->magic == cpu_to_be16(XFS_DIR2_LEAFN_MAGIC) || info->magic == cpu_to_be16(XFS_DIR3_LEAFN_MAGIC) || - info->magic == cpu_to_be16(XFS_ATTR_LEAF_MAGIC)); + info->magic == cpu_to_be16(XFS_ATTR_LEAF_MAGIC) || + info->magic == cpu_to_be16(XFS_ATTR3_LEAF_MAGIC)); /* @@ -1893,6 +1897,7 @@ xfs_da3_path_shift( blkno = be32_to_cpu(btree[blk->index].before); break; case XFS_ATTR_LEAF_MAGIC: + case XFS_ATTR3_LEAF_MAGIC: blk->magic = XFS_ATTR_LEAF_MAGIC; ASSERT(level == path->active-1); blk->index = 0; @@ -2625,6 +2630,7 @@ xfs_da_read_buf( XFS_TEST_ERROR((magic != XFS_DA_NODE_MAGIC) && (magic != XFS_DA3_NODE_MAGIC) && (magic != XFS_ATTR_LEAF_MAGIC) && + (magic != XFS_ATTR3_LEAF_MAGIC) && (magic != XFS_DIR2_LEAF1_MAGIC) && (magic != XFS_DIR3_LEAF1_MAGIC) && (magic != XFS_DIR2_LEAFN_MAGIC) && diff --git a/fs/xfs/xfs_da_btree.h b/fs/xfs/xfs_da_btree.h index 6bedb3c..0e8182c 100644 --- a/fs/xfs/xfs_da_btree.h +++ b/fs/xfs/xfs_da_btree.h @@ -55,6 +55,7 @@ typedef struct xfs_da_blkinfo { * magic numbers without modification for both v2 and v3 nodes. */ #define XFS_DA3_NODE_MAGIC 0x3ebe /* magic number: non-leaf blocks */ +#define XFS_ATTR3_LEAF_MAGIC 0x3bee /* magic number: attribute leaf blks */ #define XFS_DIR3_LEAF1_MAGIC 0x3df1 /* magic number: v2 dirlf single blks */ #define XFS_DIR3_LEAFN_MAGIC 0x3dff /* magic number: v2 dirlf multi blks */ @@ -85,13 +86,13 @@ struct xfs_da3_blkinfo { typedef struct xfs_da_node_hdr { struct xfs_da_blkinfo info; /* block type, links, etc. */ - __be16 count; /* count of active entries */ + __be16 __count; /* count of active entries */ __be16 __level; /* level above leaves (leaf == 0) */ } xfs_da_node_hdr_t; struct xfs_da3_node_hdr { struct xfs_da3_blkinfo info; /* block type, links, etc. */ - __be16 count; /* count of active entries */ + __be16 __count; /* count of active entries */ __be16 __level; /* level above leaves (leaf == 0) */ __be32 __pad32; }; -- 1.7.10.4 From david@fromorbit.com Tue Mar 12 07:43:34 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 641CC7FCD for ; Tue, 12 Mar 2013 07:43:34 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay2.corp.sgi.com (Postfix) with ESMTP id 509AC304059 for ; Tue, 12 Mar 2013 05:43:34 -0700 (PDT) X-ASG-Debug-ID: 1363092212-04cb6c2b03493f30001-NocioJ Received: from ipmail05.adl6.internode.on.net (ipmail05.adl6.internode.on.net [150.101.137.143]) by cuda.sgi.com with ESMTP id VkFQ183LAkWUj0zf for ; Tue, 12 Mar 2013 05:43:32 -0700 (PDT) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.143 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: Ag8cAB4hP1F5LKiV/2dsb2JhbABDhyy4G4UWAQIBgUkXdIIoAQEFOhwzCBgMJQ8FJQM0iBKwCZAeFY01QhgfURaDKgOWVIlqhwyBL4FvKIEu Received: from ppp121-44-168-149.lns20.syd7.internode.on.net (HELO dastard) ([121.44.168.149]) by ipmail05.adl6.internode.on.net with ESMTP; 12 Mar 2013 23:13:32 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UFOYF-0001Vm-9b for xfs@oss.sgi.com; Tue, 12 Mar 2013 23:43:31 +1100 Date: Tue, 12 Mar 2013 23:43:31 +1100 From: Dave Chinner To: xfs@oss.sgi.com Subject: [PATCH 22/21] xfs: Fix magic number assert in xfs_dir3_leaf_log_bests Message-ID: <20130312124331.GP21651@dastard> X-ASG-Orig-Subj: [PATCH 22/21] xfs: Fix magic number assert in xfs_dir3_leaf_log_bests References: <1363091454-8852-1-git-send-email-david@fromorbit.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <1363091454-8852-1-git-send-email-david@fromorbit.com> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail05.adl6.internode.on.net[150.101.137.143] X-Barracuda-Start-Time: 1363092212 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124988 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- From: Dave Chinner Make sure we set the magic number correctly when converting from node to leaf form. Signed-off-by: Dave Chinner --- This should probably be folded into patch 14/21. I missed this hunk when bringing it forward to 3.9-rc2 and folding all the bugs fixes I had in debug patches back into their original patches. fs/xfs/xfs_dir2_leaf.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/fs/xfs/xfs_dir2_leaf.c b/fs/xfs/xfs_dir2_leaf.c index 015c078..43a5c8543c4 100644 --- a/fs/xfs/xfs_dir2_leaf.c +++ b/fs/xfs/xfs_dir2_leaf.c @@ -2199,7 +2199,7 @@ xfs_dir2_node_to_leaf( xfs_trans_buf_set_type(tp, lbp, XFS_BLF_DIR_LEAF1_BUF); leafhdr.magic = (leafhdr.magic == XFS_DIR2_LEAFN_MAGIC) ? XFS_DIR2_LEAF1_MAGIC - : XFS_DIR3_LEAFN_MAGIC; + : XFS_DIR3_LEAF1_MAGIC; /* * Set up the leaf tail from the freespace block. From rjohnston@sgi.com Tue Mar 12 07:52:19 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 22CDD7FB6 for ; Tue, 12 Mar 2013 07:52:19 -0500 (CDT) Received: from xmail.sgi.com (pv-excas3-dc21-nlb.corp.sgi.com [137.38.102.207]) by relay2.corp.sgi.com (Postfix) with ESMTP id D7EF0304048; Tue, 12 Mar 2013 05:52:18 -0700 (PDT) Received: from [134.15.0.16] (134.15.0.16) by xmail.sgi.com (137.38.102.30) with Microsoft SMTP Server (TLS) id 14.2.318.1; Tue, 12 Mar 2013 07:52:18 -0500 Message-ID: <513F2501.4010505@sgi.com> Date: Tue, 12 Mar 2013 07:52:17 -0500 From: Rich Johnston User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:14.0) Gecko/20120714 Thunderbird/14.0 MIME-Version: 1.0 To: David Sterba CC: , Subject: Re: [PATCH] xfstests: determine path of logger References: <1363045012-21119-1-git-send-email-dsterba@suse.cz> In-Reply-To: <1363045012-21119-1-git-send-email-dsterba@suse.cz> Content-Type: text/plain; charset="ISO-8859-1"; format=flowed Content-Transfer-Encoding: 7bit X-Originating-IP: [134.15.0.16] This patch has been committed. Regards --Rich commit 9958693bdb282adc422bcf85f5360e3a5785e8e9 Author: David Sterba Date: Mon Mar 11 23:36:52 2013 +0000 xfstests: determine path of logger The path of the syslog writer utility 'logger' is hardcoded and not always correct, use set_prog_path. Signed-off-by: David Sterba Reviewed-by: Dave Chinner Signed-off-by: Rich Johnston From tinguely@sgi.com Tue Mar 12 08:48:49 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id F34167FA2 for ; Tue, 12 Mar 2013 08:48:48 -0500 (CDT) Received: from eagdhcp-232-136.americas.sgi.com (eagdhcp-232-136.americas.sgi.com [128.162.232.136]) by relay1.corp.sgi.com (Postfix) with ESMTP id 7AC4D8F8035; Tue, 12 Mar 2013 06:48:45 -0700 (PDT) Message-ID: <513F323E.5000401@sgi.com> Date: Tue, 12 Mar 2013 08:48:46 -0500 From: Mark Tinguely User-Agent: Mozilla/5.0 (X11; FreeBSD amd64; rv:9.0) Gecko/20120122 Thunderbird/9.0 MIME-Version: 1.0 To: Hans-Peter Jansen CC: david@fromorbit.com, xfs@oss.sgi.com Subject: Re: Fwd: xfs_reno References: <20351675.Zy117sIl8Z@xrated> <513E5113.60508@sgi.com> <5202910.jIRzyplXT6@xrated> In-Reply-To: <5202910.jIRzyplXT6@xrated> Content-Type: text/plain; charset=UTF-8; format=flowed Content-Transfer-Encoding: 8bit On 03/12/13 04:02, Hans-Peter Jansen wrote: > Am Montag, 11. März 2013, 16:48:03 schrieb Mark Tinguely: >> On 03/06/13 08:55, Hans-Peter Jansen wrote: >>> Hi Dave, >>> >>> I tried to gather Barrys SOB, but failed so far. His trace ends in 2009 >>> google wise. >>> >>> How is this case usually handled? >>> >>> Here's the current state of things. >>> >>> Cheers, >>> Pete >>> >>> >>> ---------- Weitergeleitete Nachricht ---------- >>> >>> Betreff: xfs_reno >>> Datum: Mittwoch, 6. März 2013, 12:52:19 >>> Von: Hans-Peter Jansen >>> An: bnaujok@sgi.com >>> >>> Hi Barry, >>> >>> attached is a slightly mangled version of your xfs_reno tool, that I badly >>> needed recently. While at it, I plan to submit it, as it saved my *ss. >>> Thanks. >>> >>> Apart from relocation to xfsprogs, I just changed this >>> >>> + log_message(LOG_DEBUG, "%s: %llu %lu %s", msg, node->ino, >>> + node->numpaths, node->paths[0]); >>> >>> from %llu to %lu for the node->numpaths argument. It might still be wrong, >>> as numpath is defined as nlink_t which is a __u32 type, but the %s >>> printed garbage like this: >>> >>> Scanning directory tree... >>> xfs_reno: add_node_path: ino 8611163235, path >>> /work/dlbase/hosts/11.2/pico/var/run/screens >>> xfs_reno: add_node_path: ino 8611163233, path >>> /work/dlbase/hosts/11.2/pico/var/run/pcscd/pcscd.events >>> xfs_reno: add_node_path: ino 8611163234, path >>> /work/dlbase/hosts/11.2/pico/var/run/uscreens >>> xfs_reno: nodehash: 8611163233 692488159933497345 ��]��f�e� >>> xfs_reno: nodehash: 8611163234 692366801337581569 ��]��f�e� >>> xfs_reno: nodehash: 8611163235 692223830466232321 ��]��f�e� >>> >>> I guess, gcc is smart enough to see, that the struct members overlap here, >>> and prints the paths[0] argument as a %llu value. What do you think? >>> >>> Anyway, I will revise this during the course of creating a xlstests test >>> for xfs_reno... >>> >>> Do you allow me to add your Signed-off-by to this patch? >>> >>> If you want to build this, apply both patches to xfsprogs. >>> >>> TIA, >>> Pete >> >> Have you been getting "Out of memory" warnings on your runs? I am. > > No, I would have mentioned them. But I guess, my file systems are tiny > compared to yours. The affected FS have 2.8T and 4.1T, with former with many > small files and directories, the latter with many 2G files. > >> Compiling, I get the warnings about having "\r" in the strings. For example: >> >> reno/xfs_reno.c:1415: internationalized messages should not contain the >> `\r' escape sequence > > Well, that's for the spin wheel, that might have interesting effects, when > localized to right-to-left languages... > >> ---------- >> I wonder if we should add a temp directory option. It seems to want to >> use the parent directory of the directory as a temporary. > > Without digging into this, I can only guess, but the whole point of xfs_reno > is relocating the inodes on the FS in question *without* copying files around. > Using a separate TEMP defeats this purpose, don't it? > > It might be in order to add a note to the man page to not try to use it in > "cross mount operation" scenarios. > >> Below is the >> result of running xfs_reno on the target directory is "/mnt/xxx >> (changing the \r to<^M>\n for the email): >> >> xfs_reno: directory: 128 1 /mn<^M> >> xfs_reno: /mnt/xfs_reno_epdaJc: Cannet set target extended attributes<^M> >> xfs_reno: failed to rename: '/mnt/xxx/origin' to >> '/mnt/xfs_reno_NXQLWI/origin' >> <^M> >> xfs_reno: unable to move directory contents: /mnt/xxx to >> /mnt/xfs_reno_NXQLWI >> <^M> >> xfs_reno: Cannot stat /mnt/xfs_reno_epdaJc: Inappropriate ioctl for device >> >> <^M> >> xfs_reno: unable to duplicate directory attributes: /mnt/xfs_reno_epdaJc >> t/xxx >> ------ >> /mnt is not an XFS filesystem. When mounting on the root, say /mnt, the >> message look like: >> >> xfs_reno: Cannot stat //xfs_reno_epdaJc: Inappropriate ioctl for device > > You lost me here. What I can say, is that using eg. "xfs_reno -vpn /work", > hence on the mount point directly, did as advertised. > > Cheers, > Pete Sorry, the biggest problem is US daylight savings change and my simple brain. Waking this morning, it all mentally clicked. It is working as intended. Sorry for the noise. --Mark. --Mark. From sandeen@sandeen.net Tue Mar 12 09:40:25 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 4C0597F83 for ; Tue, 12 Mar 2013 09:40:25 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay1.corp.sgi.com (Postfix) with ESMTP id 297C58F8035 for ; Tue, 12 Mar 2013 07:40:21 -0700 (PDT) X-ASG-Debug-ID: 1363099217-04cb6c2b0249d190001-NocioJ Received: from sandeen.net (sandeen.net [63.231.237.45]) by cuda.sgi.com with ESMTP id 8f8oX6ShBLLQKNLY for ; Tue, 12 Mar 2013 07:40:17 -0700 (PDT) X-Barracuda-Envelope-From: sandeen@sandeen.net X-Barracuda-Apparent-Source-IP: 63.231.237.45 Received: from liberator.sandeen.net (liberator.sandeen.net [10.0.0.4]) (using TLSv1 with cipher DHE-RSA-CAMELLIA256-SHA (256/256 bits)) (No client certificate requested) by sandeen.net (Postfix) with ESMTPSA id 68C3463C59BB; Tue, 12 Mar 2013 09:40:17 -0500 (CDT) Message-ID: <513F3E51.7000600@sandeen.net> Date: Tue, 12 Mar 2013 09:40:17 -0500 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: Ole Tange CC: xfs@oss.sgi.com Subject: Re: xfs_repair segfaults References: <512FA67D.2090708@sandeen.net> <5130DB54.9030503@sandeen.net> <5134BBA4.3060305@sandeen.net> <513A4AEC.4010202@sandeen.net> X-ASG-Orig-Subj: Re: xfs_repair segfaults In-Reply-To: X-Enigmail-Version: 1.5.1 Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: sandeen.net[63.231.237.45] X-Barracuda-Start-Time: 1363099217 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124996 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On 3/12/13 5:41 AM, Ole Tange wrote: > On Fri, Mar 8, 2013 at 9:32 PM, Eric Sandeen wrote: >> On 3/8/13 4:21 AM, Ole Tange wrote: >>> On Mon, Mar 4, 2013 at 4:20 PM, Eric Sandeen wrote: >>> >>>> 2) so you could run a "real" non-"n" xfs_repair on a metadata image as a more realistic dry run > : >>> I get >>> filenames like: >>> >>> /mnt/disk/??5?z+hEOgl/?7?Psr1?aIHS??+??z=ozK/8_0/???d) >>> 5JCG?eiBd?EVsNF'A?v?m?f;Fi6v)d>/?M%?A??J?)B>> X[Df?Wm^[?f 4| >> >> By default, xfs_metadump scrambles filenames, so nothing to worry >> about (it's for privacy reasons). If you use the "-o" option it'll keep >> it in the clear. > > Ahh. To me that does not conform to Principle of Least Astonishment - > especially since some of the filenames were not obfuscated. > > I would have been less surprised if the files were named: > > Use_-o_for_real_file_names_XXXXXXXX > Use_-o_for_real_dir_names_XXXXXXXX > > where XXXXXXXX is just a unique number. That would completely change the actual on-disk metadata format, though, which would defeat the primary purpose of metadump. As it is, it preserves name lengths and name hashes, so that what is produced is an accurate representation of the original filesystem's metadata for analysis. This is described in the manpage, though I sympathize that it's a bit alarming the first time you see it in the dump output, if you weren't aware. -Eric > > /Ole > > _______________________________________________ > xfs mailing list > xfs@oss.sgi.com > http://oss.sgi.com/mailman/listinfo/xfs > From sandeen@sandeen.net Tue Mar 12 09:47:55 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 5B1587F5D for ; Tue, 12 Mar 2013 09:47:55 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id 479C3304070 for ; Tue, 12 Mar 2013 07:47:52 -0700 (PDT) X-ASG-Debug-ID: 1363099671-04cbb07dbf492600001-NocioJ Received: from sandeen.net (sandeen.net [63.231.237.45]) by cuda.sgi.com with ESMTP id Zslq8y2o6CN6oXEN for ; Tue, 12 Mar 2013 07:47:51 -0700 (PDT) X-Barracuda-Envelope-From: sandeen@sandeen.net X-Barracuda-Apparent-Source-IP: 63.231.237.45 Received: from liberator.sandeen.net (liberator.sandeen.net [10.0.0.4]) (using TLSv1 with cipher DHE-RSA-CAMELLIA256-SHA (256/256 bits)) (No client certificate requested) by sandeen.net (Postfix) with ESMTPSA id 0C71163C59BC; Tue, 12 Mar 2013 09:47:51 -0500 (CDT) Message-ID: <513F4017.6050702@sandeen.net> Date: Tue, 12 Mar 2013 09:47:51 -0500 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: Ole Tange CC: xfs@oss.sgi.com Subject: Re: xfs_repair segfaults References: <512FA67D.2090708@sandeen.net> <5130DB54.9030503@sandeen.net> <5134BBA4.3060305@sandeen.net> X-ASG-Orig-Subj: Re: xfs_repair segfaults In-Reply-To: X-Enigmail-Version: 1.5.1 Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: sandeen.net[63.231.237.45] X-Barracuda-Start-Time: 1363099671 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124996 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On 3/12/13 6:37 AM, Ole Tange wrote: > $ ~/work/xfsprogs/repair/xfs_repair -L franklin.img > Phase 1 - find and verify superblock... > Phase 2 - using internal log > - zero log... > ALERT: The filesystem has valuable metadata changes in a log which is being > destroyed because the -L option was used. > - scan filesystem freespace and inode maps... > xfs_repair: scan.c:1080: scan_freelist: Assertion `0' failed. > Aborted (core dumped) Oh, man. I need to have my hacker card revoked. Or maybe focus on one filesystem at a time so I don't keep doing dumb things, like adding an unconditional ASSERT in non-"-n"-mode. Holy cow, I don't know what's up with me lately. :/ Anyway, just modify these 2 lines in repair/scan.c to remove the ASSERT around line 1080. I'll send a proper patch as well. diff --git a/repair/scan.c b/repair/scan.c index 6a62dff..76bb7f1 100644 --- a/repair/scan.c +++ b/repair/scan.c @@ -1076,8 +1076,7 @@ scan_freelist( "freelist scan\n"), i); return; } - } else /* should have been fixed in verify_set_agf() */ - ASSERT(0); + } count = 0; for (;;) { From sandeen@sandeen.net Tue Mar 12 09:50:23 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 036407F63 for ; Tue, 12 Mar 2013 09:50:23 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay1.corp.sgi.com (Postfix) with ESMTP id C1A008F804C for ; Tue, 12 Mar 2013 07:50:22 -0700 (PDT) X-ASG-Debug-ID: 1363099821-04bdf022964d6b70001-NocioJ Received: from sandeen.net (sandeen.net [63.231.237.45]) by cuda.sgi.com with ESMTP id zdveyW0cXkXqIibm for ; Tue, 12 Mar 2013 07:50:21 -0700 (PDT) X-Barracuda-Envelope-From: sandeen@sandeen.net X-Barracuda-Apparent-Source-IP: 63.231.237.45 Received: from liberator.sandeen.net (liberator.sandeen.net [10.0.0.4]) (using TLSv1 with cipher DHE-RSA-CAMELLIA256-SHA (256/256 bits)) (No client certificate requested) by sandeen.net (Postfix) with ESMTPSA id 5818163C59BB for ; Tue, 12 Mar 2013 09:50:21 -0500 (CDT) Message-ID: <513F40AD.10303@sandeen.net> Date: Tue, 12 Mar 2013 09:50:21 -0500 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: xfs-oss Subject: [PATCH] xfs_repair: remove unconditional ASSERT(0) X-Enigmail-Version: 1.5.1 X-ASG-Orig-Subj: [PATCH] xfs_repair: remove unconditional ASSERT(0) Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: sandeen.net[63.231.237.45] X-Barracuda-Start-Time: 1363099821 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.124998 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- I don't know what I was thinking in 7e8e3cc, but I added an ASSERT(0) in the main path. Obviously this isn't right. Just remove it. Signed-off-by: Eric Sandeen --- Really sorry, no idea what is up w/ my brain lately. Trying to do too many things at once, too quickly. diff --git a/repair/scan.c b/repair/scan.c index 6a62dff..76bb7f1 100644 --- a/repair/scan.c +++ b/repair/scan.c @@ -1076,8 +1076,7 @@ scan_freelist( "freelist scan\n"), i); return; } - } else /* should have been fixed in verify_set_agf() */ - ASSERT(0); + } count = 0; for (;;) { From rjohnston@sgi.com Tue Mar 12 10:44:36 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id B5A827F66 for ; Tue, 12 Mar 2013 10:44:36 -0500 (CDT) Received: from xmail.sgi.com (pv-excas3-dc21.corp.sgi.com [137.38.102.206]) by relay3.corp.sgi.com (Postfix) with ESMTP id E8275AC006; Tue, 12 Mar 2013 08:44:32 -0700 (PDT) Received: from [128.162.233.55] (128.162.233.55) by xmail.sgi.com (137.38.102.30) with Microsoft SMTP Server (TLS) id 14.2.318.1; Tue, 12 Mar 2013 10:44:32 -0500 Message-ID: <513F4D76.5000600@sgi.com> Date: Tue, 12 Mar 2013 10:44:54 -0500 From: Rich Johnston User-Agent: Mozilla/5.0 (X11; Linux i686; rv:13.0) Gecko/20120615 Thunderbird/13.0.1 MIME-Version: 1.0 To: Eric Sandeen CC: xfs-oss Subject: Re: [PATCH] xfs_repair: remove unconditional ASSERT(0) References: <513F40AD.10303@sandeen.net> In-Reply-To: <513F40AD.10303@sandeen.net> Content-Type: text/plain; charset="ISO-8859-1"; format=flowed Content-Transfer-Encoding: 7bit X-Originating-IP: [128.162.233.55] On 03/12/2013 09:50 AM, Eric Sandeen wrote: > I don't know what I was thinking in 7e8e3cc, but I added an > ASSERT(0) in the main path. Obviously this isn't right. > > Just remove it. > > Signed-off-by: Eric Sandeen > --- > > Really sorry, no idea what is up w/ my brain lately. > Trying to do too many things at once, too quickly. > I can relate. Thanks for the quick fix. Looks good: Reviewed-by: Rich Johnston This has been committed. Thanks --Rich commit b326e067f1005d584bd8ad21bb9f3e2700230e29 Author: Eric Sandeen Date: Tue Mar 12 14:50:21 2013 +0000 xfsprogs xfs_repair: remove unconditional ASSERT(0) I don't know what I was thinking in 7e8e3cc, but I added an ASSERT(0) in the main path. Obviously this isn't right. Just remove it. Signed-off-by: Eric Sandeen Reviewed-by: Rich Johnston Signed-off-by: Rich Johnston From rjohnston@sgi.com Tue Mar 12 11:33:51 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id B6F3D7F52 for ; Tue, 12 Mar 2013 11:33:51 -0500 (CDT) Received: from xmail.sgi.com (pv-excas3-dc21.corp.sgi.com [137.38.102.206]) by relay3.corp.sgi.com (Postfix) with ESMTP id 23ABDAC004; Tue, 12 Mar 2013 09:33:48 -0700 (PDT) Received: from [128.162.233.55] (128.162.233.55) by xmail.sgi.com (137.38.102.30) with Microsoft SMTP Server (TLS) id 14.2.318.1; Tue, 12 Mar 2013 11:33:44 -0500 Message-ID: <513F58FE.1010200@sgi.com> Date: Tue, 12 Mar 2013 11:34:06 -0500 From: Rich Johnston User-Agent: Mozilla/5.0 (X11; Linux i686; rv:13.0) Gecko/20120615 Thunderbird/13.0.1 MIME-Version: 1.0 To: Carlos Maiolino CC: Subject: Re: [PATCH] xfsdump: properly set Parent's PID References: <1359663197-30473-1-git-send-email-cmaiolino@redhat.com> In-Reply-To: <1359663197-30473-1-git-send-email-cmaiolino@redhat.com> Content-Type: text/plain; charset="ISO-8859-1"; format=flowed Content-Transfer-Encoding: 7bit X-Originating-IP: [128.162.233.55] On 01/31/2013 02:13 PM, Carlos Maiolino wrote: > Set parentpid variable to the correct Parent's ID using getppid() instead of > getpid() > > Signed-off-by: Carlos Maiolino > --- > common/main.c | 2 +- > 1 file changed, 1 insertion(+), 1 deletion(-) > > diff --git a/common/main.c b/common/main.c > index 980d2d4..848a887 100644 > --- a/common/main.c > +++ b/common/main.c > @@ -198,7 +198,7 @@ main( int argc, char *argv[] ) > /* Get the parent's pid. will be used in signal handling > * to differentiate parent from children. > */ > - parentpid = getpid( ); > + parentpid = getppid( ); > rval = atexit(mlog_exit_flush); > assert(rval == 0); > > Sorry for the late review, this does not apply to current xfsdump tree. Regards --Rich From sandeen@redhat.com Tue Mar 12 11:42:55 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id C2E8E7F51 for ; Tue, 12 Mar 2013 11:42:55 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay2.corp.sgi.com (Postfix) with ESMTP id 7EA8530406B for ; Tue, 12 Mar 2013 09:42:52 -0700 (PDT) X-ASG-Debug-ID: 1363106571-04bdf022964eb2d0001-NocioJ Received: from mx1.redhat.com (mx1.redhat.com [209.132.183.28]) by cuda.sgi.com with ESMTP id sGFP7ZsMKCi1IBDq for ; Tue, 12 Mar 2013 09:42:51 -0700 (PDT) X-Barracuda-Envelope-From: sandeen@redhat.com X-Barracuda-Apparent-Source-IP: 209.132.183.28 X-ASG-Whitelist: Client Received: from int-mx02.intmail.prod.int.phx2.redhat.com (int-mx02.intmail.prod.int.phx2.redhat.com [10.5.11.12]) by mx1.redhat.com (8.14.4/8.14.4) with ESMTP id r2CGgpB2010219 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=OK); Tue, 12 Mar 2013 12:42:51 -0400 Received: from liberator.sandeen.net (ovpn01.gateway.prod.ext.phx2.redhat.com [10.5.9.1]) by int-mx02.intmail.prod.int.phx2.redhat.com (8.13.8/8.13.8) with ESMTP id r2CGgnGg025899 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=NO); Tue, 12 Mar 2013 12:42:50 -0400 Message-ID: <513F5B0A.4030405@redhat.com> Date: Tue, 12 Mar 2013 11:42:50 -0500 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: xfs-oss , ext4 development , linux-btrfs Subject: [PATCH] xfstests: make defrag test 222 generic X-Enigmail-Version: 1.5.1 X-ASG-Orig-Subj: [PATCH] xfstests: make defrag test 222 generic Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Scanned-By: MIMEDefang 2.67 on 10.5.11.12 X-Barracuda-Connect: mx1.redhat.com[209.132.183.28] X-Barracuda-Start-Time: 1363106571 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Barracuda-BRTS-Status: 1 X-Virus-Scanned: by bsmtpd at sgi.com test 222 is just a stress test defragging the test device: # xfs_fsr QA tests # run xfs_fsr over the test filesystem to give it a wide and varied set of # inodes to try to defragment. This is effectively a crash/assert failure # test looking for corruption induced by xfs_fsr runs. There's no reason we can't do the same for other filesystems. Define a new _defrag_dir() helper which just runs noisy/debug dir defrag for ext4 and/or btrfs as well, and use that in 222 instead of hardcoded xfs_fsr. Make 222 (and 218) generic; if no defrag is supported it just won't run. Change the comments at the top while we're at it. Signed-off-by: Eric Sandeen --- diff --git a/218 b/218 index 77782c6..e337bbf 100755 --- a/218 +++ b/218 @@ -44,7 +44,7 @@ _cleanup() . ./common.defrag # real QA test starts here -_supported_fs xfs ext4 btrfs +_supported_fs generic _supported_os Linux _setup_testdir diff --git a/222 b/222 index df2672f..dc4d621 100755 --- a/222 +++ b/222 @@ -1,10 +1,10 @@ #! /bin/bash # FS QA Test No. 222 # -# xfs_fsr QA tests -# run xfs_fsr over the test filesystem to give it a wide and varied set of +# defrag QA tests +# run defrag over the test filesystem to give it a wide and varied set of # inodes to try to defragment. This is effectively a crash/assert failure -# test looking for corruption induced by xfs_fsr runs. +# test looking for corruption induced by defragmentation runs. # #----------------------------------------------------------------------- # Copyright (c) 2010 Dave Chinner. All Rights Reserved. @@ -44,14 +44,15 @@ trap "_cleanup ; exit \$status" 0 1 2 3 15 # get standard environment, filters and checks . ./common.rc . ./common.filter +. ./common.defrag # real QA test starts here -_supported_fs xfs +_supported_fs generic _supported_os Linux -[ "$XFS_FSR_PROG" = "" ] && _notrun "xfs_fsr not found" +_require_defrag -xfs_fsr -d -v $TEST_DIR > $seq.full 2>&1 +_defrag_dir $TEST_DIR > $seq.full 2>&1 echo "--- silence is golden ---" status=0 ; exit diff --git a/common.defrag b/common.defrag index 9c9eb9b..7736330 100644 --- a/common.defrag +++ b/common.defrag @@ -69,3 +69,19 @@ _defrag() rm -f $1 } +# Defrag a whole directory. No checking as above, just run it, noisily +# output should be sent to $seq.full since it's very fs-specific +_defrag_dir() +{ + case "$FSTYP" in + xfs) + $DEFRAG_PROG -d -v $1 + ;; + ext4|ext4dev|btrfs) + $DEFRAG_PROG -v $1 + ;; + *) + $DEFRAG_PROG $1 + ;; + esac +} From mlsemon35@gmail.com Tue Mar 12 13:46:32 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.3 required=5.0 tests=FREEMAIL_ENVFROM_END_DIGIT, FREEMAIL_FROM,T_DKIM_INVALID autolearn=no version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 965707F59 for ; Tue, 12 Mar 2013 13:46:32 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay3.corp.sgi.com (Postfix) with ESMTP id 05138AC002 for ; Tue, 12 Mar 2013 11:46:28 -0700 (PDT) X-ASG-Debug-ID: 1363113986-04cbb07dbf4bd640001-NocioJ Received: from mail-lb0-f170.google.com (mail-lb0-f170.google.com [209.85.217.170]) by cuda.sgi.com with ESMTP id BGUJ8sa3aKsm4GWE (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Tue, 12 Mar 2013 11:46:27 -0700 (PDT) X-Barracuda-Envelope-From: mlsemon35@gmail.com X-Barracuda-Apparent-Source-IP: 209.85.217.170 X-Barracuda-IPDD: Level1 [gmail.com/209.85.217.170] Received: by mail-lb0-f170.google.com with SMTP id ge1so256124lbb.15 for ; Tue, 12 Mar 2013 11:46:25 -0700 (PDT) X-Barracuda-IPDD: Level1 [gmail.com/209.85.217.170] X-Barracuda-IPDD: Level1 [gmail.com/209.85.217.170] DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20120113; h=mime-version:x-received:date:message-id:subject:from:to :content-type; bh=bJYHpbb4hweMjL54XfTVghm4FLEqWxzUXw7lxP3Tr1g=; b=YJ8OUtV26deVPXBu4y+5QoW5SIAmJd0c+pgiXboEZxj7cA4UHAPrungb07L0Wk3Thm ztm7owyELBFmyemAWj3cw+/Mdyb87hxd7Bs8HcaoQOXtbG4TWpGh7UQt6QJVsrEh/tGm BFNOl7oweu1HzAKjjmsnDf3qtV9ZubDf8KXr6WXYl2VZspFd+0lLQop1VyAb2XdU9ewx AbrAudk3iu1V1JibciMx0zHED48ljkgTxrdgWup83+jZZkMAt5qkr7Rem5EGZIA1x6a4 Mz2hGduuOHNBUe52ILcGrRHjWJVOBFVTl2pZ9LQ8RcgnnzYW5w+yGpQWB1ylH/8krRiZ zT2g== MIME-Version: 1.0 X-Received: by 10.152.109.112 with SMTP id hr16mr14988063lab.38.1363113985598; Tue, 12 Mar 2013 11:46:25 -0700 (PDT) Received: by 10.114.37.131 with HTTP; Tue, 12 Mar 2013 11:46:25 -0700 (PDT) Date: Tue, 12 Mar 2013 14:46:25 -0400 Message-ID: Subject: xfstests #111 + XFS debug = infinite-loop oops From: "Michael L. Semon" X-ASG-Orig-Subj: xfstests #111 + XFS debug = infinite-loop oops To: xfs@oss.sgi.com Content-Type: text/plain; charset=ISO-8859-1 X-Barracuda-Connect: mail-lb0-f170.google.com[209.85.217.170] X-Barracuda-Start-Time: 1363113986 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=DKIM_SIGNED, DKIM_VERIFIED X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125012 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature Hi! I was running xfstests #111 under the following conditions... (*) zeroed partitions, and (*) a fresh mkfs.xfs for each file system, and (1) CONFIG_XFS_DEBUG used, rtdev used, external logdev used, or (2) CONFIG_XFS_DEBUG used, external logdev used, or (3) CONFIG_XFS_DEBUG used, all internal, mkfs.xfs called with no options ...and I get a trace like the one below (from (3)). The trace is from kernel 3.9.0-rc2 on an old Pentium III, using a normal VGA console on the test PC, captured by another PC over serial cable. The trace is part of an infinite loop that becomes finite only if I rip out the console and VGA entirely. Overall, more is in play here than just XFS, but I don't know to whom I should write. [A relevant question for which I don't know the answer: Are there critical sections where you should not use assertions or call BUG() in debug code?] Something in XFS debug is fighting the console/VGA/framebuffer system, and I don't know where to go from here. You'll know you've reproduced this one because you'll need the power button to shut the PC off, so be careful. This is crash report; no fix is requested. I'm using the simple workarounds "don't run xfstests #111 with XFS debugging enabled" and "Backups! Backups! Backups!" All is well. Thanks! Michael [ 1399.347056] XFS (sda12): Corruption detected. Unmount and run xfs_repair [ 1399.353815] XFS (sda12): bad inode magic/vsn daddr 64 #8 (magic=5858) [ 1399.360277] XFS: Assertion failed: 0, file: fs/xfs/xfs_inode.c, line: 416 [ 1399.367112] ------------[ cut here ]------------ [ 1399.370409] kernel BUG at fs/xfs/xfs_message.c:100! [ 1399.370409] invalid opcode: 0000 [#1] [ 1399.370409] Pid: 42, comm: kworker/0:1H Not tainted 3.9.0-rc2 #5 [ 1399.370409] EIP: 0060:[] EFLAGS: 00010296 CPU: 0 [ 1399.370409] EIP is at assfail+0x27/0x30 [ 1399.370409] EAX: 0000003d EBX: 00000008 ECX: 00000178 EDX: 00000000 [ 1399.370409] ESI: dd940800 EDI: d6a95780 EBP: df601eb8 ESP: df601ea4 [ 1399.370409] DS: 007b ES: 007b FS: 0000 GS: 00e0 SS: 0068 [ 1399.370409] CR0: 8005003b CR2: b765c8c0 CR3: 16b20000 CR4: 000007d0 [ 1399.370409] DR0: 00000000 DR1: 00000000 DR2: 00000000 DR3: 00000000 [ 1399.370409] DR6: ffff0ff0 DR7: 00000400 [ 1399.370409] Process kworker/0:1H (pid: 42, ti=df600000 task=df5f8990 task.ti=df600000) [ 1399.370409] Stack: [ 1399.370409] 00000000 c1435d80 c1421860 c14312e2 000001a0 df601ef0 c113a418 d92c6000 [ 1399.370409] c143be20 00000040 00000000 00000008 00005858 d92c61ac 00000020 d92c6000 [ 1399.370409] d6a957d8 d6a95780 c148d364 df601ef8 c113a4c8 df601f0c c10ec97f df5b9101 [ 1399.370409] Call Trace: [ 1399.370409] [] xfs_inode_buf_verify+0xe8/0x180 [ 1399.370409] [] xfs_inode_buf_read_verify+0x8/0x10 [ 1399.370409] [] xfs_buf_iodone_work+0x2f/0xa0 [ 1399.370409] [] process_one_work+0xdb/0x2e0 [ 1399.370409] [] worker_thread+0xe8/0x2d0 [ 1399.370409] [] ? manage_workers+0x240/0x240 [ 1399.370409] [] kthread+0x8e/0xa0 [ 1399.370409] [] ret_from_kernel_thread+0x1b/0x28 [ 1399.370409] [] ? __kthread_parkme+0x60/0x60 [ 1399.370409] Code: 00 00 00 00 55 89 e5 83 ec 14 89 54 24 0c ba 80 5d 43 c1 89 4c 24 10 89 44 24 08 89 54 24 04 c7 04 24 00 00 00 00 e8 d9 fd ff ff <0f> 0b 8d b4 26 00 00 00 00 55 b9 01 00 00 00 89 e5 83 ec 14 89 [ 1399.370409] EIP: [] assfail+0x27/0x30 SS:ESP 0068:df601ea4 [ 1399.539190] ---[ end trace e84c0d20f4790af0 ]--- [ 1399.543926] BUG: unable to handle kernel paging request at fffffff0 [ 1399.547168] IP: [] kthread_data+0xa/0x10 [ 1399.547168] *pde = 014ee067 *pte = 00000000 [ 1399.547168] Oops: 0000 [#2] [ 1399.547168] Pid: 42, comm: kworker/0:1H Tainted: G D 3.9.0-rc2 #5 [ 1399.547168] EIP: 0060:[] EFLAGS: 00010046 CPU: 0 [ 1399.547168] EIP is at kthread_data+0xa/0x10 [ 1399.547168] EAX: 00000000 EBX: 00000000 ECX: c148da00 EDX: 00000000 [ 1399.547168] ESI: df5f8ae8 EDI: df5f8990 EBP: df601cac ESP: df601ca4 [ 1399.547168] DS: 007b ES: 007b FS: 0000 GS: 00e0 SS: 0068 [ 1399.547168] CR0: 8005003b CR2: fffffff0 CR3: 16b20000 CR4: 000007d0 [ 1399.547168] DR0: 00000000 DR1: 00000000 DR2: 00000000 DR3: 00000000 [ 1399.547168] DR6: ffff0ff0 DR7: 00000400 [ 1399.547168] Process kworker/0:1H (pid: 42, ti=df600000 task=df5f8990 task.ti=df600000) [ 1399.547168] Stack: [ 1399.547168] c1038a7b 00000000 df601d28 c137bada 00000001 00000000 df58d480 00000086 [ 1399.547168] df5f89e4 00000008 00000000 df5f8990 df601cd8 131eec54 00000002 df58e900 [ 1399.547168] dfeab180 df40a000 df601d04 c108cae9 dfeab180 df58e900 df5f8990 df5bd1e0 [ 1399.547168] Call Trace: [ 1399.547168] [] ? wq_worker_sleeping+0xb/0x50 [ 1399.547168] [] __schedule+0x25a/0x430 [ 1399.547168] [] ? kmem_cache_free+0x99/0xb0 [ 1399.547168] [] ? release_task+0x1ae/0x2e0 [ 1399.547168] [] schedule+0x1d/0x50 [ 1399.547168] [] do_exit+0x3ac/0x730 [ 1399.547168] [] ? printk+0x38/0x3a [ 1399.547168] [] oops_end+0x61/0x90 [ 1399.547168] [] die+0x45/0x70 [ 1399.547168] [] do_trap+0x50/0xb0 [ 1399.547168] [] ? do_bounds+0x80/0x80 [ 1399.547168] [] do_invalid_op+0x87/0xa0 [ 1399.547168] [] ? assfail+0x27/0x30 [ 1399.547168] [] ? vprintk_emit+0x112/0x3f0 [ 1399.547168] [] ? printk+0x38/0x3a [ 1399.547168] [] error_code+0x65/0x6c [ 1399.547168] [] ? xfs_file_aio_read+0x40/0x280 [ 1399.547168] [] ? assfail+0x27/0x30 [ 1399.547168] [] xfs_inode_buf_verify+0xe8/0x180 [ 1399.547168] [] xfs_inode_buf_read_verify+0x8/0x10 [ 1399.547168] [] xfs_buf_iodone_work+0x2f/0xa0 [ 1399.547168] [] process_one_work+0xdb/0x2e0 [ 1399.547168] [] worker_thread+0xe8/0x2d0 [ 1399.547168] [] ? manage_workers+0x240/0x240 [ 1399.547168] [] kthread+0x8e/0xa0 [ 1399.547168] [] ret_from_kernel_thread+0x1b/0x28 [ 1399.547168] [] ? __kthread_parkme+0x60/0x60 [ 1399.547168] Code: 00 55 85 c0 89 e5 74 03 c6 00 00 a1 a0 5d 48 c1 8b 80 2c 01 00 00 5d 8b 50 e8 d1 ea 88 d0 24 01 c3 55 8b 80 2c 01 00 00 89 e5 5d <8b> 40 f0 c3 66 90 55 a1 a0 5d 48 c1 8b 80 2c 01 00 00 89 e5 83 [ 1399.547168] EIP: [] kthread_data+0xa/0x10 SS:ESP 0068:df601ca4 [ 1399.547168] CR2: 00000000fffffff0 [ 1399.547168] ---[ end trace e84c0d20f4790af1 ]--- [ 1399.547168] Fixing recursive fault but reboot is needed! [ 1399.547168] BUG: unable to handle kernel paging request at fffffff0 [ 1399.547168] IP: [] kthread_data+0xa/0x10 [ 1399.547168] *pde = 014ee067 *pte = 00000000 [ 1399.547168] Oops: 0000 [#3] [ 1399.547168] Pid: 42, comm: kworker/0:1H Tainted: G D 3.9.0-rc2 #5 [ 1399.547168] EIP: 0060:[] EFLAGS: 00010046 CPU: 0 [ 1399.547168] EIP is at kthread_data+0xa/0x10 [ 1399.547168] EAX: 00000000 EBX: 00000000 ECX: c148da00 EDX: 00000000 [ 1399.547168] ESI: df5f8ae8 EDI: df5f8990 EBP: df601a8c ESP: df601a84 [ 1399.547168] DS: 007b ES: 007b FS: 0000 GS: 00e0 SS: 0068 [ 1399.547168] CR0: 8005003b CR2: fffffff0 CR3: 16b20000 CR4: 000007d0 [ 1399.547168] DR0: 00000000 DR1: 00000000 DR2: 00000000 DR3: 00000000 [ 1399.547168] DR6: ffff0ff0 DR7: 00000400 [ 1399.547168] Process kworker/0:1H (pid: 42, ti=df600000 task=df5f8990 task.ti=df600000) [ 1399.547168] Stack: [ 1399.547168] c1038a7b 00000009 df601b08 c137bada 00000000 00000006 00000000 000001c9 [ 1399.547168] c14f6030 0000002c 00000000 df5f8990 df601ab8 00000046 00000000 00000000 [ 1399.547168] 00000000 00000000 c1506082 0000002c 000001c8 c1506082 00000000 00000046 [ 1399.547168] Call Trace: [ 1399.547168] [] ? wq_worker_sleeping+0xb/0x50 [ 1399.547168] [] __schedule+0x25a/0x430 [ 1399.547168] [] ? printk+0x38/0x3a [ 1399.547168] [] schedule+0x1d/0x50 [ 1399.547168] [] do_exit+0x6dc/0x730 [ 1399.547168] [] ? printk+0x38/0x3a [ 1399.547168] [] ? print_oops_end_marker+0x2a/0x30 [ 1399.547168] [] oops_end+0x61/0x90 [ 1399.547168] [] no_context+0x179/0x181 [ 1399.547168] [] __bad_area_nosemaphore+0x11c/0x124 [ 1399.547168] [] ? sched_clock_local.constprop.3+0x3c/0x170 [ 1399.547168] [] ? vmalloc_sync_all+0xf0/0xf0 [ 1399.547168] [] bad_area_nosemaphore+0x12/0x14 [ 1399.547168] [] __do_page_fault+0x21c/0x3f0 [ 1399.547168] [] ? __enqueue_entity.constprop.54+0x71/0x80 [ 1399.547168] [] ? enqueue_task_fair+0x84/0x130 [ 1399.547168] [] ? vmalloc_sync_all+0xf0/0xf0 [ 1399.547168] [] do_page_fault+0x8/0x10 [ 1399.547168] [] error_code+0x65/0x6c [ 1399.547168] [] ? hrtimer_nanosleep+0xe0/0x120 [ 1399.547168] [] ? kthread_data+0xa/0x10 [ 1399.547168] [] ? wq_worker_sleeping+0xb/0x50 [ 1399.547168] [] __schedule+0x25a/0x430 [ 1399.547168] [] ? kmem_cache_free+0x99/0xb0 [ 1399.547168] [] ? release_task+0x1ae/0x2e0 [ 1399.547168] [] schedule+0x1d/0x50 [ 1399.547168] [] do_exit+0x3ac/0x730 [ 1399.547168] [] ? printk+0x38/0x3a [ 1399.547168] [] oops_end+0x61/0x90 [ 1399.547168] [] die+0x45/0x70 [ 1399.547168] [] do_trap+0x50/0xb0 [ 1399.547168] [] ? do_bounds+0x80/0x80 [ 1399.547168] [] do_invalid_op+0x87/0xa0 [ 1399.547168] [] ? assfail+0x27/0x30 [ 1399.547168] [] ? vprintk_emit+0x112/0x3f0 [ 1399.547168] [] ? printk+0x38/0x3a [ 1399.547168] [] error_code+0x65/0x6c [ 1399.547168] [] ? xfs_file_aio_read+0x40/0x280 [ 1399.547168] [] ? assfail+0x27/0x30 [ 1399.547168] [] xfs_inode_buf_verify+0xe8/0x180 [ 1399.547168] [] xfs_inode_buf_read_verify+0x8/0x10 [ 1399.547168] [] xfs_buf_iodone_work+0x2f/0xa0 [ 1399.547168] [] process_one_work+0xdb/0x2e0 [ 1399.547168] [] worker_thread+0xe8/0x2d0 [ 1399.547168] [] ? manage_workers+0x240/0x240 [ 1399.547168] [] kthread+0x8e/0xa0 [ 1399.547168] [] ret_from_kernel_thread+0x1b/0x28 [ 1399.547168] [] ? __kthread_parkme+0x60/0x60 [ 1399.547168] Code: 00 55 85 c0 89 e5 74 03 c6 00 00 a1 a0 5d 48 c1 8b 80 2c 01 00 00 5d 8b 50 e8 d1 ea 88 d0 24 01 c3 55 8b 80 2c 01 00 00 89 e5 5d <8b> 40 f0 c3 66 90 55 a1 a0 5d 48 c1 8b 80 2c 01 00 00 89 e5 83 [ 1399.547168] EIP: [] kthread_data+0xa/0x10 SS:ESP 0068:df601a84 [ 1399.547168] CR2: 00000000fffffff0 [ 1399.547168] ---[ end trace e84c0d20f4790af2 ]--- [ 1399.547168] Fixing recursive fault but reboot is needed! [ 1399.547168] BUG: unable to handle kernel paging request at fffffff0 From tinguely@sgi.com Tue Mar 12 15:27:41 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 600EE7F55 for ; Tue, 12 Mar 2013 15:27:41 -0500 (CDT) Received: from eagdhcp-232-136.americas.sgi.com (eagdhcp-232-136.americas.sgi.com [128.162.232.136]) by relay2.corp.sgi.com (Postfix) with ESMTP id 25887304077; Tue, 12 Mar 2013 13:27:41 -0700 (PDT) Message-ID: <513F8FBD.4080805@sgi.com> Date: Tue, 12 Mar 2013 15:27:41 -0500 From: Mark Tinguely User-Agent: Mozilla/5.0 (X11; FreeBSD amd64; rv:9.0) Gecko/20120122 Thunderbird/9.0 MIME-Version: 1.0 To: "Michael L. Semon" CC: xfs@oss.sgi.com Subject: Re: xfstests #111 + XFS debug = infinite-loop oops References: In-Reply-To: Content-Type: text/plain; charset=ISO-8859-1; format=flowed Content-Transfer-Encoding: 7bit On 03/12/13 13:46, Michael L. Semon wrote: > Hi! I was running xfstests #111 under the following conditions... > > (*) zeroed partitions, and > (*) a fresh mkfs.xfs for each file system, and > > (1) CONFIG_XFS_DEBUG used, rtdev used, external logdev used, or > (2) CONFIG_XFS_DEBUG used, external logdev used, or > (3) CONFIG_XFS_DEBUG used, all internal, mkfs.xfs called with no options > > ...and I get a trace like the one below (from (3)). The trace is from > kernel 3.9.0-rc2 on an old Pentium III, using a normal VGA console on > the test PC, captured by another PC over serial cable. The trace is > part of an infinite loop that becomes finite only if I rip out the > console and VGA entirely. Overall, more is in play here than just > XFS, but I don't know to whom I should write. [A relevant question > for which I don't know the answer: Are there critical sections where > you should not use assertions or call BUG() in debug code?] Something > in XFS debug is fighting the console/VGA/framebuffer system, and I > don't know where to go from here. > > You'll know you've reproduced this one because you'll need the power > button to shut the PC off, so be careful. > > This is crash report; no fix is requested. I'm using the simple > workarounds "don't run xfstests #111 with XFS debugging enabled" and > "Backups! Backups! Backups!" All is well. > > Thanks! > > Michael > > [ 1399.347056] XFS (sda12): Corruption detected. Unmount and run xfs_repair > [ 1399.353815] XFS (sda12): bad inode magic/vsn daddr 64 #8 (magic=5858) 0x58 == 'X' > [ 1399.360277] XFS: Assertion failed: 0, file: fs/xfs/xfs_inode.c, line: 416 Thanks for the report, but there is no bug here. Maybe we should list test 111 as "dangerous". xfstests 111 trashes the inode see xfstests/src/itrash.c: void nuke() { int i; for (i = 2048; i < 32768-1; i++) if (buffer[i] == 'I' && buffer[i+1] == 'N') { buffer[i] = buffer[i+1] = 'X'; printf("Overwrote IN @offset %d\n", i); } } The inode verifiers are doing their job. --Mark. From david@fromorbit.com Tue Mar 12 16:11:10 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 26B247F53 for ; Tue, 12 Mar 2013 16:11:10 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay2.corp.sgi.com (Postfix) with ESMTP id 0A9A6304032 for ; Tue, 12 Mar 2013 14:11:06 -0700 (PDT) X-ASG-Debug-ID: 1363122664-04cb6c4a43059c0001-NocioJ Received: from ipmail07.adl2.internode.on.net (ipmail07.adl2.internode.on.net [150.101.137.131]) by cuda.sgi.com with ESMTP id ExbgBcaDu5CAVACQ for ; Tue, 12 Mar 2013 14:11:04 -0700 (PDT) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.131 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AssdAKKYP1F5LKiV/2dsb2JhbABDhy64HoUaAQIBgUoXdIIpAQEEATocIwULCAMYCSUPBSUDIROIDgXBVBWNSC8YH0oHg0ADllWQd4MeKA Received: from ppp121-44-168-149.lns20.syd7.internode.on.net (HELO dastard) ([121.44.168.149]) by ipmail07.adl2.internode.on.net with ESMTP; 13 Mar 2013 07:41:03 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UFWTN-0002bX-Ta; Wed, 13 Mar 2013 08:11:01 +1100 Date: Wed, 13 Mar 2013 08:11:01 +1100 From: Dave Chinner To: Mark Tinguely Cc: "Michael L. Semon" , xfs@oss.sgi.com Subject: Re: xfstests #111 + XFS debug = infinite-loop oops Message-ID: <20130312211101.GQ21651@dastard> X-ASG-Orig-Subj: Re: xfstests #111 + XFS debug = infinite-loop oops References: <513F8FBD.4080805@sgi.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <513F8FBD.4080805@sgi.com> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail07.adl2.internode.on.net[150.101.137.131] X-Barracuda-Start-Time: 1363122664 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125022 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Tue, Mar 12, 2013 at 03:27:41PM -0500, Mark Tinguely wrote: > On 03/12/13 13:46, Michael L. Semon wrote: > >Hi! I was running xfstests #111 under the following conditions... > > > >(*) zeroed partitions, and > >(*) a fresh mkfs.xfs for each file system, and > > > >(1) CONFIG_XFS_DEBUG used, rtdev used, external logdev used, or > >(2) CONFIG_XFS_DEBUG used, external logdev used, or > >(3) CONFIG_XFS_DEBUG used, all internal, mkfs.xfs called with no options > > > >...and I get a trace like the one below (from (3)). The trace is from > >kernel 3.9.0-rc2 on an old Pentium III, using a normal VGA console on > >the test PC, captured by another PC over serial cable. The trace is > >part of an infinite loop that becomes finite only if I rip out the > >console and VGA entirely. Overall, more is in play here than just > >XFS, but I don't know to whom I should write. [A relevant question > >for which I don't know the answer: Are there critical sections where > >you should not use assertions or call BUG() in debug code?] Something > >in XFS debug is fighting the console/VGA/framebuffer system, and I > >don't know where to go from here. > > > >You'll know you've reproduced this one because you'll need the power > >button to shut the PC off, so be careful. > > > >This is crash report; no fix is requested. I'm using the simple > >workarounds "don't run xfstests #111 with XFS debugging enabled" and > >"Backups! Backups! Backups!" All is well. > > > >Thanks! > > > >Michael > > > >[ 1399.347056] XFS (sda12): Corruption detected. Unmount and run xfs_repair > >[ 1399.353815] XFS (sda12): bad inode magic/vsn daddr 64 #8 (magic=5858) > > 0x58 == 'X' > > >[ 1399.360277] XFS: Assertion failed: 0, file: fs/xfs/xfs_inode.c, line: 416 > > Thanks for the report, but there is no bug here. Maybe we should > list test 111 as "dangerous". Don't think so - do we actually need that assert in the verifier? The test is actaully checking that we don't end up with an endless loop in bulkstat when corruption is hit, so we should really make sure the test can perform it's functions on CONFIG_XFS_DEBUG=y kernels... > The inode verifiers are doing their job. Well, they aren't supposed to crash the kernel. The debug check is historic behaviour that we can probably now remove... Cheers, Dave. -- Dave Chinner david@fromorbit.com From stan@hardwarefreak.com Tue Mar 12 17:16:27 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 5CA127F51 for ; Tue, 12 Mar 2013 17:16:27 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay3.corp.sgi.com (Postfix) with ESMTP id DDA2CAC006 for ; Tue, 12 Mar 2013 15:16:23 -0700 (PDT) X-ASG-Debug-ID: 1363126582-04cb6c4a450b520001-NocioJ Received: from greer.hardwarefreak.com (mo-65-41-216-221.sta.embarqhsd.net [65.41.216.221]) by cuda.sgi.com with ESMTP id xBCMo2BEBzN6eSCW for ; Tue, 12 Mar 2013 15:16:23 -0700 (PDT) X-Barracuda-Envelope-From: stan@hardwarefreak.com X-Barracuda-Apparent-Source-IP: 65.41.216.221 X-Barracuda-User-Whitelist: xfs@oss.sgi.com Received: from [192.168.100.53] (gffx.hardwarefreak.com [192.168.100.53]) by greer.hardwarefreak.com (Postfix) with ESMTP id 675BC6C12E; Tue, 12 Mar 2013 17:16:22 -0500 (CDT) Message-ID: <513FA938.6080603@hardwarefreak.com> Date: Tue, 12 Mar 2013 17:16:24 -0500 From: Stan Hoeppner Reply-To: stan@hardwarefreak.com User-Agent: Mozilla/5.0 (Windows NT 5.1; rv:17.0) Gecko/20130307 Thunderbird/17.0.4 MIME-Version: 1.0 To: Martin Steigerwald CC: xfs@oss.sgi.com, Julien FERRERO , Ric Wheeler Subject: Re: XFS filesystem corruption References: <5137CD46.6070909@redhat.com> <5139A3B6.3040805@hardwarefreak.com> (sfid-20130308_132012_037479_915CAB49) <201303121142.13980.Martin@lichtvoll.de> X-ASG-Orig-Subj: Re: XFS filesystem corruption In-Reply-To: <201303121142.13980.Martin@lichtvoll.de> Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 8bit X-Barracuda-Connect: mo-65-41-216-221.sta.embarqhsd.net[65.41.216.221] X-Barracuda-Start-Time: 1363126582 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 On 3/12/2013 5:42 AM, Martin Steigerwald wrote: > Am Freitag, 8. Mrz 2013 schrieb Stan Hoeppner: >> If the techs are determined to hard cut power because they don't have >> the time or the knowledge to do a clean shutdown, it may be well worth >> your time/effort to write a script and teach the field techs to execute >> it, before flipping the master switch. Your simple script would run as >> root, or you'd need to do some sudo foo within, and would contain >> something like: >> >> #! /bin/sh >> sync >> echo 2 > /proc/sys/vm/drop_caches >> echo "Ready for power down." > > mount -o remount,ro /your/mount/point > > One can at least try. Maybe some "service stop" commands before that. > > But then, if using a script like this, why not just type "halt"? ... The real solution to the OP's problem has nothing to do with XFS, buffer flushing, nor Linux shutdown modes. The problem is power and automation of cutting power. And the solution is rather simple. Put a small UPS in the van backing the server, connect USB or serial, and configure upsmon. When the crews hit the master switch, AC to the UPS is lost, and upsmon then performs a clean shutdown of the server. The crews do nothing more than they currently do. And they don't have to wait on anything. If the previously described "master" switch *is* currently a UPS, simply install another smaller unit inline to the server. Disable the audible alarm on the small unit as by default it will screech continuously while AC input is absent. At the end of the day they simply flip the switch on this little UPS so it's not running overnight/weekends (though with no load it probably wouldn't drain the battery--this just a safety precaution). At the start of the next day, they flip the master switch, then the little UPS switch. I've not laid eyes on the vans/power circuits/gear in question so I'm making educated guesses. There may be even better/easier ways to do it. But one way or another, a properly configured UPS/upsmon setup is the way to go, if the desire is to easily control everything with power switches. -- Stan From mrs.suzanrobert8@libero.it Tue Mar 12 17:24:15 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: * X-Spam-Status: No, score=1.8 required=5.0 tests=FREEMAIL_ENVFROM_END_DIGIT, FREEMAIL_FROM,FREEMAIL_REPLYTO,HTML_MESSAGE,SUBJ_ALL_CAPS autolearn=no version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id A8B2F7F52 for ; Tue, 12 Mar 2013 17:24:15 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay3.corp.sgi.com (Postfix) with ESMTP id 23B28AC006 for ; Tue, 12 Mar 2013 15:24:14 -0700 (PDT) X-ASG-Debug-ID: 1363127032-04cbb04b840c830001-NocioJ Received: from outrelay02.libero.it (outrelay02.libero.it [212.52.84.102]) by cuda.sgi.com with ESMTP id 5l19YwZHwGE2WU9i; Tue, 12 Mar 2013 15:23:52 -0700 (PDT) X-Barracuda-Envelope-From: mrs.suzanrobert8@libero.it X-Barracuda-Apparent-Source-IP: 212.52.84.102 X-CTCH-Spam: Suspect X-CTCH-RefID: str=0001.0A0C0201.513FAAF7.00EC,ss=2,re=0.000,fgs=0 X-libjamoibt: 1587 Received: from wmail75 (172.31.0.253) by outrelay02.libero.it (8.5.140.03) id 512DF09101F2A161; Tue, 12 Mar 2013 23:23:51 +0100 Message-ID: <22265695.22611201363127031828.JavaMail.defaultUser@defaultHost> Date: Tue, 12 Mar 2013 23:23:51 +0100 (CET) From: "mrs.suzanrobert8@libero.it" Reply-To: "mrs.suzanrobert8@libero.it" Subject: 2013 USA (CHRF) CONFERENCE/INVITATION!!!! MIME-Version: 1.0 X-ASG-Orig-Subj: 2013 USA (CHRF) CONFERENCE/INVITATION!!!! Content-Type: multipart/alternative; boundary="----=_Part_1891549_12589944.1363127031827" X-SenderIP: 41.82.131.97 X-libjamv: qnh+qx5Jn68= X-libjamsun: VE3/nsiiFlLUaqNqc0iihju236rOWuxE8utE8IHephw= X-Barracuda-Connect: outrelay02.libero.it[212.52.84.102] X-Barracuda-Start-Time: 1363127032 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 1.67 X-Barracuda-Spam-Status: No, SCORE=1.67 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=HTML_MESSAGE, MISSING_HEADERS, PLING_PLING, TO_CC_NONE X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125028 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 1.21 MISSING_HEADERS Missing To: header 0.00 HTML_MESSAGE BODY: HTML included in message 0.46 PLING_PLING Subject has lots of exclamation marks 0.00 TO_CC_NONE No To: or Cc: header To: undisclosed-recipients:; ------=_Part_1891549_12589944.1363127031827 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: quoted-printable Dear Colleagues, On behalf of California Human Right=20 Foundation CHRF USA, It is a great privilege for us to invite you to=20 global Congress meeting against Economic Crisis, Child Protection &=20 HIV/AIDS Treatment, Prostitution, Sex Work and forced Labor. The aims of the conference are to bring together researchers and practitioners in=20 an effort to lay the ground work for future collaborative research,=20 advocacy, and program development as well as to educate social service,=20 health care, and criminal justice professionals on human trafficking and the needs and risks of those victimized by the commercial sex industry. The global Congress meeting against Economic Crisis, Child Protection & HIV/AIDS Treatment, Prostitution, Sex Work and forced Labor is=20 scheduled to take place from April 23rd =E2=80=93 26th 2013 in California t= he=20 United States and in Dakar-Senegal, from April 29th =E2=80=93 03rd of May = 2013. The global congress is hosted by the Campaign against Child Labor=20 Coalition and sponsored by (The Bill & Melinda Gates Foundation, The William J. Clinton Foundation and other benevolent donors worldwide. Note that all interested delegates that requires entry visa to enter the=20 United States to attend this meeting will be assisted by the=20 organization, in obtaining the visa in their passport. Free air round=20 trip tickets to attend this meeting will be provided to all=20 participants. The Workshop welcomes paper presentation from any=20 interested participants willing to present papers during the meeting. For registration information. contact the conference secretariat via email:= diannawilliams@secretary.net Please share the information with your colleagues. Sincerely, Dr.Mrs.Suzan Robert dr.mrs.suzanrobert@gmail.com, (Ph.D) Activities Coordinator ------=_Part_1891549_12589944.1363127031827 Content-Type: text/html;charset="UTF-8" Content-Transfer-Encoding: quoted-printable

Dear Colleagues,

On behalf of California Human Right=20 Foundation CHRF USA, It is a great privilege for us to invite you to=20 global Congress meeting against Economic Crisis, Child Protection &=20 HIV/AIDS Treatment, Prostitution, Sex Work and forced Labor. The aims of the conference are to bring together researchers and practitioners in=20 an effort to lay the ground work for future collaborative research,=20 advocacy, and program development as well as to educate social service,=20 health care, and criminal justice professionals on human trafficking and the needs and risks of those victimized by the commercial sex industry.
The global Congress meeting against Economic Crisis, Child Protection & HIV/AIDS Treatment, Prostitution, Sex Work and forced Labor is=20 scheduled to take place from April 23rd =E2=80=93 26th 2013 in California t= he=20 United States and in Dakar-Senegal, from April  29th =E2=80=93 03rd of= May 2013. The global congress is hosted by the Campaign against Child Labor=20 Coalition and sponsored by (The Bill & Melinda Gates Foundation, The William J. Clinton Foundation and other benevolent donors worldwide.
No= te that all interested delegates that requires entry visa to enter the=20 United States to attend this meeting will be assisted by the=20 organization, in obtaining the visa in their passport. Free air round=20 trip tickets to attend this meeting will be provided to all=20 participants. The Workshop welcomes paper presentation from any=20 interested participants willing to present papers during the meeting.
For registration information. contact the conference secretariat via e= mail:diannawilliams@secretary.net

Please share the information w= ith your colleagues.

Sincerely,
Dr.Mrs.Suzan Robert
dr.mrs.suz= anrobert@gmail.com,
(Ph.D) Activities Coordinator

 
 
&n= bsp;
 
 
 
 
 
=
 
 
 
------=_Part_1891549_12589944.1363127031827-- From david@fromorbit.com Tue Mar 12 19:29:20 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 906857F3F for ; Tue, 12 Mar 2013 19:29:20 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay3.corp.sgi.com (Postfix) with ESMTP id 1BC8CAC004 for ; Tue, 12 Mar 2013 17:29:16 -0700 (PDT) X-ASG-Debug-ID: 1363134554-04cbb04b8516510001-NocioJ Received: from ipmail07.adl2.internode.on.net (ipmail07.adl2.internode.on.net [150.101.137.131]) by cuda.sgi.com with ESMTP id kTfy1JGFu0LLHFuv for ; Tue, 12 Mar 2013 17:29:14 -0700 (PDT) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.131 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AskdAO/HP1F5LKiV/2dsb2JhbABDhzC4OYUaAQIBgUsXdIIpAQEFJxMcMwgYDCUPBSUDNIgTwVcVjXcYHz8Sg0ADllWQd4EvgW8o Received: from ppp121-44-168-149.lns20.syd7.internode.on.net (HELO dastard) ([121.44.168.149]) by ipmail07.adl2.internode.on.net with ESMTP; 13 Mar 2013 10:59:01 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UFZYy-00037w-8D for xfs@oss.sgi.com; Wed, 13 Mar 2013 11:29:00 +1100 Date: Wed, 13 Mar 2013 11:29:00 +1100 From: Dave Chinner To: xfs@oss.sgi.com Subject: [PATCH 23/21] xfs: fix endian issues reported by sparse Message-ID: <20130313002900.GS21651@dastard> X-ASG-Orig-Subj: [PATCH 23/21] xfs: fix endian issues reported by sparse References: <1363091454-8852-1-git-send-email-david@fromorbit.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <1363091454-8852-1-git-send-email-david@fromorbit.com> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail07.adl2.internode.on.net[150.101.137.131] X-Barracuda-Start-Time: 1363134554 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125036 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- From: Dave Chinner Sparse reports several problems in the new code with incorrect endian conversions being done on variables. Fix them. Signed-off-by: Dave Chinner --- fs/xfs/xfs_da_btree.c | 2 +- fs/xfs/xfs_dinode.h | 2 +- fs/xfs/xfs_dir2_block.c | 4 ++-- fs/xfs/xfs_dir2_data.c | 4 ++-- fs/xfs/xfs_dir2_leaf.c | 2 +- fs/xfs/xfs_dir2_node.c | 6 +++--- fs/xfs/xfs_mount.c | 1 - 7 files changed, 10 insertions(+), 11 deletions(-) diff --git a/fs/xfs/xfs_da_btree.c b/fs/xfs/xfs_da_btree.c index 10bfeaa..a78865e 100644 --- a/fs/xfs/xfs_da_btree.c +++ b/fs/xfs/xfs_da_btree.c @@ -2287,7 +2287,7 @@ xfs_da3_swap_lastblock( goto done; par_node = par_buf->b_addr; xfs_da3_node_hdr_from_disk(&par_hdr, par_node); - if (level >= 0 && level != be16_to_cpu(par_hdr.level) + 1) { + if (level >= 0 && level != par_hdr.level + 1) { XFS_ERROR_REPORT("xfs_da_swap_lastblock(4)", XFS_ERRLEVEL_LOW, mp); error = XFS_ERROR(EFSCORRUPTED); diff --git a/fs/xfs/xfs_dinode.h b/fs/xfs/xfs_dinode.h index bdc946a..f7a0e95 100644 --- a/fs/xfs/xfs_dinode.h +++ b/fs/xfs/xfs_dinode.h @@ -72,7 +72,7 @@ typedef struct xfs_dinode { __be32 di_next_unlinked;/* agi unlinked list ptr */ /* start of the extended dinode, writable fields */ - __be32 di_crc; /* CRC of the inode */ + __le32 di_crc; /* CRC of the inode */ __be64 di_changecount; /* number of attribute changes */ __be64 di_lsn; /* flush sequence */ __be64 di_flags2; /* more random flags */ diff --git a/fs/xfs/xfs_dir2_block.c b/fs/xfs/xfs_dir2_block.c index 8c387e4..58816ec 100644 --- a/fs/xfs/xfs_dir2_block.c +++ b/fs/xfs/xfs_dir2_block.c @@ -67,14 +67,14 @@ xfs_dir3_block_verify( struct xfs_dir3_blk_hdr *hdr3 = bp->b_addr; if (xfs_sb_version_hascrc(&mp->m_sb)) { - if (hdr3->magic != be32_to_cpu(XFS_DIR3_BLOCK_MAGIC)) + if (hdr3->magic != cpu_to_be32(XFS_DIR3_BLOCK_MAGIC)) return false; if (!uuid_equal(&hdr3->uuid, &mp->m_sb.sb_uuid)) return false; if (be64_to_cpu(hdr3->blkno) != bp->b_bn) return false; } else { - if (hdr3->magic != be32_to_cpu(XFS_DIR2_BLOCK_MAGIC)) + if (hdr3->magic != cpu_to_be32(XFS_DIR2_BLOCK_MAGIC)) return false; } if (__xfs_dir3_data_check(NULL, bp)) diff --git a/fs/xfs/xfs_dir2_data.c b/fs/xfs/xfs_dir2_data.c index 20a4aaf..5e0c711 100644 --- a/fs/xfs/xfs_dir2_data.c +++ b/fs/xfs/xfs_dir2_data.c @@ -200,14 +200,14 @@ xfs_dir3_data_verify( struct xfs_dir3_blk_hdr *hdr3 = bp->b_addr; if (xfs_sb_version_hascrc(&mp->m_sb)) { - if (hdr3->magic != be32_to_cpu(XFS_DIR3_DATA_MAGIC)) + if (hdr3->magic != cpu_to_be32(XFS_DIR3_DATA_MAGIC)) return false; if (!uuid_equal(&hdr3->uuid, &mp->m_sb.sb_uuid)) return false; if (be64_to_cpu(hdr3->blkno) != bp->b_bn) return false; } else { - if (hdr3->magic != be32_to_cpu(XFS_DIR2_DATA_MAGIC)) + if (hdr3->magic != cpu_to_be32(XFS_DIR2_DATA_MAGIC)) return false; } if (__xfs_dir3_data_check(NULL, bp)) diff --git a/fs/xfs/xfs_dir2_leaf.c b/fs/xfs/xfs_dir2_leaf.c index 43a5c8543c4..9bf588c 100644 --- a/fs/xfs/xfs_dir2_leaf.c +++ b/fs/xfs/xfs_dir2_leaf.c @@ -180,7 +180,7 @@ xfs_dir3_leaf1_check( static bool xfs_dir3_leaf_verify( struct xfs_buf *bp, - __be16 magic) + __uint16_t magic) { struct xfs_mount *mp = bp->b_target->bt_mount; struct xfs_dir2_leaf *leaf = bp->b_addr; diff --git a/fs/xfs/xfs_dir2_node.c b/fs/xfs/xfs_dir2_node.c index 7d1ee7d..9e542e7 100644 --- a/fs/xfs/xfs_dir2_node.c +++ b/fs/xfs/xfs_dir2_node.c @@ -90,14 +90,14 @@ xfs_dir3_free_verify( if (xfs_sb_version_hascrc(&mp->m_sb)) { struct xfs_dir3_blk_hdr *hdr3 = bp->b_addr; - if (hdr3->magic != be32_to_cpu(XFS_DIR3_FREE_MAGIC)) + if (hdr3->magic != cpu_to_be32(XFS_DIR3_FREE_MAGIC)) return false; if (!uuid_equal(&hdr3->uuid, &mp->m_sb.sb_uuid)) return false; if (be64_to_cpu(hdr3->blkno) != bp->b_bn) return false; } else { - if (hdr->magic != be32_to_cpu(XFS_DIR2_FREE_MAGIC)) + if (hdr->magic != cpu_to_be32(XFS_DIR2_FREE_MAGIC)) return false; } @@ -1284,7 +1284,7 @@ xfs_dir2_leafn_remove( { struct xfs_dir3_icfree_hdr freehdr; xfs_dir3_free_hdr_from_disk(&freehdr, free); - ASSERT(be32_to_cpu(freehdr.firstdb) == + ASSERT(freehdr.firstdb == xfs_dir3_free_max_bests(mp) * (fdb - XFS_DIR2_FREE_FIRSTDB(mp))); } diff --git a/fs/xfs/xfs_mount.c b/fs/xfs/xfs_mount.c index 97443c9..cbef607 100644 --- a/fs/xfs/xfs_mount.c +++ b/fs/xfs/xfs_mount.c @@ -568,7 +568,6 @@ xfs_sb_from_disk( to->sb_features_compat = be32_to_cpu(from->sb_features_compat); to->sb_features_ro_compat = be32_to_cpu(from->sb_features_ro_compat); to->sb_features_incompat = be32_to_cpu(from->sb_features_incompat); - to->sb_crc = be32_to_cpu(from->sb_crc); to->sb_pquotino = be64_to_cpu(from->sb_pquotino); to->sb_lsn = be64_to_cpu(from->sb_lsn); } From david@fromorbit.com Tue Mar 12 20:34:25 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 7F0EC7F37 for ; Tue, 12 Mar 2013 20:34:25 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay1.corp.sgi.com (Postfix) with ESMTP id 3B3BE8F8033 for ; Tue, 12 Mar 2013 18:34:25 -0700 (PDT) X-ASG-Debug-ID: 1363138461-04bdf00a0b1df40001-NocioJ Received: from ipmail07.adl2.internode.on.net (ipmail07.adl2.internode.on.net [150.101.137.131]) by cuda.sgi.com with ESMTP id o5BvhgGawN3RSUSt for ; Tue, 12 Mar 2013 18:34:22 -0700 (PDT) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.131 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AsodAEbWP1F5LKiV/2dsb2JhbABDhzC4I4UaAQIBgUsXdIIpAQEFGg0THDMIGAwlDwUlAzSIE8FrFY0sSxgfPxKDQAOWVYlrhwyBL4FvKA Received: from ppp121-44-168-149.lns20.syd7.internode.on.net (HELO dastard) ([121.44.168.149]) by ipmail07.adl2.internode.on.net with ESMTP; 13 Mar 2013 12:04:20 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UFaaB-0003E4-Cn for xfs@oss.sgi.com; Wed, 13 Mar 2013 12:34:19 +1100 Date: Wed, 13 Mar 2013 12:34:19 +1100 From: Dave Chinner To: xfs@oss.sgi.com Subject: [PATCH 24/21] xfs: buffer type overruns blf_flags field Message-ID: <20130313013419.GT21651@dastard> X-ASG-Orig-Subj: [PATCH 24/21] xfs: buffer type overruns blf_flags field References: <1363091454-8852-1-git-send-email-david@fromorbit.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <1363091454-8852-1-git-send-email-david@fromorbit.com> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail07.adl2.internode.on.net[150.101.137.131] X-Barracuda-Start-Time: 1363138461 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125040 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- From: Dave Chinner The buffer type passed to log recvoery in the buffer log item overruns the blf_flags field. I had assumed that flags field was a 32 bit value, and it turns out it is a unsigned short. Therefore having 19 flags doesn't really work. Convert the buffer type field to numeric value, and use the top 5 bits of the flags field for it. We currently have 17 types of buffers, so using 5 bits gives us plenty of room for expansion in future.... Signed-off-by: Dave Chinner --- Found by sparse, indicating a value too large being placed into a 16 bit word. fs/xfs/xfs_alloc.c | 4 +-- fs/xfs/xfs_attr_leaf.c | 6 ++-- fs/xfs/xfs_bmap.c | 2 +- fs/xfs/xfs_btree.c | 8 ++--- fs/xfs/xfs_buf_item.h | 90 +++++++++++++++++++++++++--------------------- fs/xfs/xfs_da_btree.c | 12 +++---- fs/xfs/xfs_dir2_block.c | 4 +-- fs/xfs/xfs_dir2_data.c | 4 +-- fs/xfs/xfs_dir2_leaf.c | 12 +++---- fs/xfs/xfs_dir2_node.c | 10 +++--- fs/xfs/xfs_ialloc.c | 2 +- fs/xfs/xfs_log_recover.c | 40 +++++++++++---------- fs/xfs/xfs_mount.c | 2 +- fs/xfs/xfs_trans_buf.c | 42 +++++++++++++++------- 14 files changed, 132 insertions(+), 106 deletions(-) diff --git a/fs/xfs/xfs_alloc.c b/fs/xfs/xfs_alloc.c index 40d3d57..5673bcf 100644 --- a/fs/xfs/xfs_alloc.c +++ b/fs/xfs/xfs_alloc.c @@ -2099,7 +2099,7 @@ xfs_alloc_log_agf( trace_xfs_agf(tp->t_mountp, XFS_BUF_TO_AGF(bp), fields, _RET_IP_); - xfs_trans_buf_set_type(tp, bp, XFS_BLF_AGF_BUF); + xfs_trans_buf_set_type(tp, bp, XFS_BLFT_AGF_BUF); xfs_btree_offsets(fields, offsets, XFS_AGF_NUM_BITS, &first, &last); xfs_trans_log_buf(tp, bp, (uint)first, (uint)last); @@ -2179,7 +2179,7 @@ xfs_alloc_put_freelist( xfs_alloc_log_agf(tp, agbp, logflags); - xfs_trans_buf_set_type(tp, agflbp, XFS_BLF_AGFL_BUF); + xfs_trans_buf_set_type(tp, agflbp, XFS_BLFT_AGFL_BUF); xfs_trans_log_buf(tp, agflbp, startoff, startoff + sizeof(xfs_agblock_t) - 1); return 0; diff --git a/fs/xfs/xfs_attr_leaf.c b/fs/xfs/xfs_attr_leaf.c index 7feaf3c..5e708dc 100644 --- a/fs/xfs/xfs_attr_leaf.c +++ b/fs/xfs/xfs_attr_leaf.c @@ -276,7 +276,7 @@ xfs_attr3_leaf_read( err = xfs_da_read_buf(tp, dp, bno, mappedbno, bpp, XFS_ATTR_FORK, &xfs_attr3_leaf_buf_ops); if (!err && tp) - xfs_trans_buf_set_type(tp, *bpp, XFS_BLF_ATTR_LEAF_BUF); + xfs_trans_buf_set_type(tp, *bpp, XFS_BLFT_ATTR_LEAF_BUF); return err; } @@ -1083,7 +1083,7 @@ xfs_attr3_leaf_to_node( goto out; /* copy leaf to new buffer, update identifiers */ - xfs_trans_buf_set_type(args->trans, bp2, XFS_BLF_ATTR_LEAF_BUF); + xfs_trans_buf_set_type(args->trans, bp2, XFS_BLFT_ATTR_LEAF_BUF); bp2->b_ops = bp1->b_ops; memcpy(bp2->b_addr, bp1->b_addr, XFS_LBSIZE(mp)); if (xfs_sb_version_hascrc(&mp->m_sb)) { @@ -1146,7 +1146,7 @@ xfs_attr3_leaf_create( if (error) return error; bp->b_ops = &xfs_attr3_leaf_buf_ops; - xfs_trans_buf_set_type(args->trans, bp, XFS_BLF_ATTR_LEAF_BUF); + xfs_trans_buf_set_type(args->trans, bp, XFS_BLFT_ATTR_LEAF_BUF); leaf = bp->b_addr; memset(leaf, 0, XFS_LBSIZE(mp)); diff --git a/fs/xfs/xfs_bmap.c b/fs/xfs/xfs_bmap.c index 2844724..8904284 100644 --- a/fs/xfs/xfs_bmap.c +++ b/fs/xfs/xfs_bmap.c @@ -1338,7 +1338,7 @@ xfs_bmap_local_to_extents_init_fn( ASSERT(0); bp->b_ops = &xfs_bmbt_buf_ops; memcpy(bp->b_addr, ifp->if_u1.if_data, ifp->if_bytes); - xfs_trans_buf_set_type(tp, bp, XFS_BLF_BTREE_BUF); + xfs_trans_buf_set_type(tp, bp, XFS_BLFT_BTREE_BUF); } /* diff --git a/fs/xfs/xfs_btree.c b/fs/xfs/xfs_btree.c index ec77036..8804b8a 100644 --- a/fs/xfs/xfs_btree.c +++ b/fs/xfs/xfs_btree.c @@ -1282,7 +1282,7 @@ xfs_btree_log_keys( XFS_BTREE_TRACE_ARGBII(cur, bp, first, last); if (bp) { - xfs_trans_buf_set_type(cur->bc_tp, bp, XFS_BLF_BTREE_BUF); + xfs_trans_buf_set_type(cur->bc_tp, bp, XFS_BLFT_BTREE_BUF); xfs_trans_log_buf(cur->bc_tp, bp, xfs_btree_key_offset(cur, first), xfs_btree_key_offset(cur, last + 1) - 1); @@ -1307,7 +1307,7 @@ xfs_btree_log_recs( XFS_BTREE_TRACE_CURSOR(cur, XBT_ENTRY); XFS_BTREE_TRACE_ARGBII(cur, bp, first, last); - xfs_trans_buf_set_type(cur->bc_tp, bp, XFS_BLF_BTREE_BUF); + xfs_trans_buf_set_type(cur->bc_tp, bp, XFS_BLFT_BTREE_BUF); xfs_trans_log_buf(cur->bc_tp, bp, xfs_btree_rec_offset(cur, first), xfs_btree_rec_offset(cur, last + 1) - 1); @@ -1332,7 +1332,7 @@ xfs_btree_log_ptrs( struct xfs_btree_block *block = XFS_BUF_TO_BLOCK(bp); int level = xfs_btree_get_level(block); - xfs_trans_buf_set_type(cur->bc_tp, bp, XFS_BLF_BTREE_BUF); + xfs_trans_buf_set_type(cur->bc_tp, bp, XFS_BLFT_BTREE_BUF); xfs_trans_log_buf(cur->bc_tp, bp, xfs_btree_ptr_offset(cur, first, level), xfs_btree_ptr_offset(cur, last + 1, level) - 1); @@ -1407,7 +1407,7 @@ xfs_btree_log_block( (cur->bc_flags & XFS_BTREE_LONG_PTRS) ? loffsets : soffsets, nbits, &first, &last); - xfs_trans_buf_set_type(cur->bc_tp, bp, XFS_BLF_BTREE_BUF); + xfs_trans_buf_set_type(cur->bc_tp, bp, XFS_BLFT_BTREE_BUF); xfs_trans_log_buf(cur->bc_tp, bp, first, last); } else { xfs_trans_log_inode(cur->bc_tp, cur->bc_private.b.ip, diff --git a/fs/xfs/xfs_buf_item.h b/fs/xfs/xfs_buf_item.h index ed259a1..0c8559f 100644 --- a/fs/xfs/xfs_buf_item.h +++ b/fs/xfs/xfs_buf_item.h @@ -39,47 +39,6 @@ extern kmem_zone_t *xfs_buf_item_zone; #define XFS_BLF_PDQUOT_BUF (1<<3) #define XFS_BLF_GDQUOT_BUF (1<<4) -/* - * all buffers now need flags to tell recovery where the magic number - * is so that it can verify and calculate the CRCs on the buffer correctly - * once the changes have been replayed into the buffer. - */ -#define XFS_BLF_BTREE_BUF (1<<5) -#define XFS_BLF_AGF_BUF (1<<6) -#define XFS_BLF_AGFL_BUF (1<<7) -#define XFS_BLF_AGI_BUF (1<<8) -#define XFS_BLF_DINO_BUF (1<<9) -#define XFS_BLF_SYMLINK_BUF (1<<10) -#define XFS_BLF_DIR_BLOCK_BUF (1<<11) -#define XFS_BLF_DIR_DATA_BUF (1<<12) -#define XFS_BLF_DIR_FREE_BUF (1<<13) -#define XFS_BLF_DIR_LEAF1_BUF (1<<14) -#define XFS_BLF_DIR_LEAFN_BUF (1<<15) -#define XFS_BLF_DA_NODE_BUF (1<<16) -#define XFS_BLF_ATTR_LEAF_BUF (1<<17) -#define XFS_BLF_ATTR_RMT_BUF (1<<18) -#define XFS_BLF_SB_BUF (1<<19) - -#define XFS_BLF_TYPE_MASK \ - (XFS_BLF_UDQUOT_BUF | \ - XFS_BLF_PDQUOT_BUF | \ - XFS_BLF_GDQUOT_BUF | \ - XFS_BLF_BTREE_BUF | \ - XFS_BLF_AGF_BUF | \ - XFS_BLF_AGFL_BUF | \ - XFS_BLF_AGI_BUF | \ - XFS_BLF_DINO_BUF | \ - XFS_BLF_SYMLINK_BUF | \ - XFS_BLF_DIR_BLOCK_BUF | \ - XFS_BLF_DIR_DATA_BUF | \ - XFS_BLF_DIR_FREE_BUF | \ - XFS_BLF_DIR_LEAF1_BUF | \ - XFS_BLF_DIR_LEAFN_BUF | \ - XFS_BLF_DA_NODE_BUF | \ - XFS_BLF_ATTR_LEAF_BUF | \ - XFS_BLF_ATTR_RMT_BUF | \ - XFS_BLF_SB_BUF) - #define XFS_BLF_CHUNK 128 #define XFS_BLF_SHIFT 7 #define BIT_TO_WORD_SHIFT 5 @@ -103,6 +62,55 @@ typedef struct xfs_buf_log_format { } xfs_buf_log_format_t; /* + * All buffers now need to tell recovery where the magic number + * is so that it can verify and calculate the CRCs on the buffer correctly + * once the changes have been replayed into the buffer. + * + * The type value is held in the upper 5 bits of the blf_flags field, which is + * an unsigned 16 bit field. Hence we need to shift it 11 bits up and down. + */ +#define XFS_BLFT_BITS 5 +#define XFS_BLFT_SHIFT 11 +#define XFS_BLFT_MASK (((1 << XFS_BLFT_BITS) - 1) << XFS_BLFT_SHIFT) + +enum xfs_blft { + XFS_BLFT_UNKNOWN_BUF = 0, + XFS_BLFT_UDQUOT_BUF, + XFS_BLFT_PDQUOT_BUF, + XFS_BLFT_GDQUOT_BUF, + XFS_BLFT_BTREE_BUF, + XFS_BLFT_AGF_BUF, + XFS_BLFT_AGFL_BUF, + XFS_BLFT_AGI_BUF, + XFS_BLFT_DINO_BUF, + XFS_BLFT_SYMLINK_BUF, + XFS_BLFT_DIR_BLOCK_BUF, + XFS_BLFT_DIR_DATA_BUF, + XFS_BLFT_DIR_FREE_BUF, + XFS_BLFT_DIR_LEAF1_BUF, + XFS_BLFT_DIR_LEAFN_BUF, + XFS_BLFT_DA_NODE_BUF, + XFS_BLFT_ATTR_LEAF_BUF, + XFS_BLFT_ATTR_RMT_BUF, + XFS_BLFT_SB_BUF, + XFS_BLFT_MAX_BUF = (1 << XFS_BLFT_BITS), +}; + +static inline void +xfs_blft_to_flags(struct xfs_buf_log_format *blf, enum xfs_blft type) +{ + ASSERT(type > XFS_BLFT_UNKNOWN_BUF && type < XFS_BLFT_MAX_BUF); + blf->blf_flags &= ~XFS_BLFT_MASK; + blf->blf_flags |= ((type << XFS_BLFT_SHIFT) & XFS_BLFT_MASK); +} + +static inline __uint16_t +xfs_blft_from_flags(struct xfs_buf_log_format *blf) +{ + return (blf->blf_flags & XFS_BLFT_MASK) >> XFS_BLFT_SHIFT; +} + +/* * buf log item flags */ #define XFS_BLI_HOLD 0x01 diff --git a/fs/xfs/xfs_da_btree.c b/fs/xfs/xfs_da_btree.c index a78865e..504e58f 100644 --- a/fs/xfs/xfs_da_btree.c +++ b/fs/xfs/xfs_da_btree.c @@ -312,15 +312,15 @@ xfs_da3_node_read( switch (be16_to_cpu(info->magic)) { case XFS_DA3_NODE_MAGIC: case XFS_DA_NODE_MAGIC: - type = XFS_BLF_DA_NODE_BUF; + type = XFS_BLFT_DA_NODE_BUF; break; case XFS_ATTR_LEAF_MAGIC: case XFS_ATTR3_LEAF_MAGIC: - type = XFS_BLF_ATTR_LEAF_BUF; + type = XFS_BLFT_ATTR_LEAF_BUF; break; case XFS_DIR2_LEAFN_MAGIC: case XFS_DIR3_LEAFN_MAGIC: - type = XFS_BLF_DIR_LEAFN_BUF; + type = XFS_BLFT_DIR_LEAFN_BUF; break; default: type = 0; @@ -361,7 +361,7 @@ xfs_da3_node_create( if (error) return(error); bp->b_ops = &xfs_da3_node_buf_ops; - xfs_trans_buf_set_type(tp, bp, XFS_BLF_DA_NODE_BUF); + xfs_trans_buf_set_type(tp, bp, XFS_BLFT_DA_NODE_BUF); node = bp->b_addr; if (xfs_sb_version_hascrc(&mp->m_sb)) { @@ -595,7 +595,7 @@ xfs_da3_root_split( * we are about to copy oldroot to bp, so set up the type * of bp while we know exactly what it will be. */ - xfs_trans_buf_set_type(tp, bp, XFS_BLF_DA_NODE_BUF); + xfs_trans_buf_set_type(tp, bp, XFS_BLFT_DA_NODE_BUF); } else { struct xfs_dir3_icleaf_hdr leafhdr; struct xfs_dir2_leaf_entry *ents; @@ -613,7 +613,7 @@ xfs_da3_root_split( * we are about to copy oldroot to bp, so set up the type * of bp while we know exactly what it will be. */ - xfs_trans_buf_set_type(tp, bp, XFS_BLF_DIR_LEAFN_BUF); + xfs_trans_buf_set_type(tp, bp, XFS_BLFT_DIR_LEAFN_BUF); } /* diff --git a/fs/xfs/xfs_dir2_block.c b/fs/xfs/xfs_dir2_block.c index 58816ec..e59f5fc 100644 --- a/fs/xfs/xfs_dir2_block.c +++ b/fs/xfs/xfs_dir2_block.c @@ -137,7 +137,7 @@ xfs_dir3_block_read( err = xfs_da_read_buf(tp, dp, mp->m_dirdatablk, -1, bpp, XFS_DATA_FORK, &xfs_dir3_block_buf_ops); if (!err && tp) - xfs_trans_buf_set_type(tp, *bpp, XFS_BLF_DIR_BLOCK_BUF); + xfs_trans_buf_set_type(tp, *bpp, XFS_BLFT_DIR_BLOCK_BUF); return err; } @@ -151,7 +151,7 @@ xfs_dir3_block_init( struct xfs_dir3_blk_hdr *hdr3 = bp->b_addr; bp->b_ops = &xfs_dir3_block_buf_ops; - xfs_trans_buf_set_type(tp, bp, XFS_BLF_DIR_BLOCK_BUF); + xfs_trans_buf_set_type(tp, bp, XFS_BLFT_DIR_BLOCK_BUF); if (xfs_sb_version_hascrc(&mp->m_sb)) { memset(hdr3, 0, sizeof(*hdr3)); diff --git a/fs/xfs/xfs_dir2_data.c b/fs/xfs/xfs_dir2_data.c index 5e0c711..c293023 100644 --- a/fs/xfs/xfs_dir2_data.c +++ b/fs/xfs/xfs_dir2_data.c @@ -306,7 +306,7 @@ xfs_dir3_data_read( err = xfs_da_read_buf(tp, dp, bno, mapped_bno, bpp, XFS_DATA_FORK, &xfs_dir3_data_buf_ops); if (!err && tp) - xfs_trans_buf_set_type(tp, *bpp, XFS_BLF_DIR_DATA_BUF); + xfs_trans_buf_set_type(tp, *bpp, XFS_BLFT_DIR_DATA_BUF); return err; } @@ -576,7 +576,7 @@ xfs_dir3_data_init( if (error) return error; bp->b_ops = &xfs_dir3_data_buf_ops; - xfs_trans_buf_set_type(tp, bp, XFS_BLF_DIR_DATA_BUF); + xfs_trans_buf_set_type(tp, bp, XFS_BLFT_DIR_DATA_BUF); /* * Initialize the header. diff --git a/fs/xfs/xfs_dir2_leaf.c b/fs/xfs/xfs_dir2_leaf.c index 9bf588c..9ba2ade 100644 --- a/fs/xfs/xfs_dir2_leaf.c +++ b/fs/xfs/xfs_dir2_leaf.c @@ -300,7 +300,7 @@ xfs_dir3_leaf_read( err = xfs_da_read_buf(tp, dp, fbno, mappedbno, bpp, XFS_DATA_FORK, &xfs_dir3_leaf1_buf_ops); if (!err && tp) - xfs_trans_buf_set_type(tp, *bpp, XFS_BLF_DIR_LEAF1_BUF); + xfs_trans_buf_set_type(tp, *bpp, XFS_BLFT_DIR_LEAF1_BUF); return err; } @@ -317,7 +317,7 @@ xfs_dir3_leafn_read( err = xfs_da_read_buf(tp, dp, fbno, mappedbno, bpp, XFS_DATA_FORK, &xfs_dir3_leafn_buf_ops); if (!err && tp) - xfs_trans_buf_set_type(tp, *bpp, XFS_BLF_DIR_LEAFN_BUF); + xfs_trans_buf_set_type(tp, *bpp, XFS_BLFT_DIR_LEAFN_BUF); return err; } @@ -362,10 +362,10 @@ xfs_dir3_leaf_init( ltp = xfs_dir2_leaf_tail_p(mp, leaf); ltp->bestcount = 0; bp->b_ops = &xfs_dir3_leaf1_buf_ops; - xfs_trans_buf_set_type(tp, bp, XFS_BLF_DIR_LEAF1_BUF); + xfs_trans_buf_set_type(tp, bp, XFS_BLFT_DIR_LEAF1_BUF); } else { bp->b_ops = &xfs_dir3_leafn_buf_ops; - xfs_trans_buf_set_type(tp, bp, XFS_BLF_DIR_LEAFN_BUF); + xfs_trans_buf_set_type(tp, bp, XFS_BLFT_DIR_LEAFN_BUF); } } @@ -487,7 +487,7 @@ xfs_dir2_block_to_leaf( * Fix up the block header, make it a data block. */ dbp->b_ops = &xfs_dir3_data_buf_ops; - xfs_trans_buf_set_type(tp, dbp, XFS_BLF_DIR_DATA_BUF); + xfs_trans_buf_set_type(tp, dbp, XFS_BLFT_DIR_DATA_BUF); if (hdr->magic == cpu_to_be32(XFS_DIR2_BLOCK_MAGIC)) hdr->magic = cpu_to_be32(XFS_DIR2_DATA_MAGIC); else @@ -2196,7 +2196,7 @@ xfs_dir2_node_to_leaf( xfs_dir3_leaf_compact(args, &leafhdr, lbp); lbp->b_ops = &xfs_dir3_leaf1_buf_ops; - xfs_trans_buf_set_type(tp, lbp, XFS_BLF_DIR_LEAF1_BUF); + xfs_trans_buf_set_type(tp, lbp, XFS_BLFT_DIR_LEAF1_BUF); leafhdr.magic = (leafhdr.magic == XFS_DIR2_LEAFN_MAGIC) ? XFS_DIR2_LEAF1_MAGIC : XFS_DIR3_LEAF1_MAGIC; diff --git a/fs/xfs/xfs_dir2_node.c b/fs/xfs/xfs_dir2_node.c index 9e542e7..9b0634d 100644 --- a/fs/xfs/xfs_dir2_node.c +++ b/fs/xfs/xfs_dir2_node.c @@ -165,7 +165,7 @@ __xfs_dir3_free_read( /* try read returns without an error or *bpp if it lands in a hole */ if (!err && tp && *bpp) - xfs_trans_buf_set_type(tp, *bpp, XFS_BLF_DIR_FREE_BUF); + xfs_trans_buf_set_type(tp, *bpp, XFS_BLFT_DIR_FREE_BUF); return err; } @@ -253,7 +253,7 @@ xfs_dir3_free_get_buf( if (error) return error; - xfs_trans_buf_set_type(tp, bp, XFS_BLF_DIR_FREE_BUF); + xfs_trans_buf_set_type(tp, bp, XFS_BLFT_DIR_FREE_BUF); bp->b_ops = &xfs_dir3_free_buf_ops;; /* @@ -402,7 +402,7 @@ xfs_dir2_leaf_to_node( else leaf->hdr.info.magic = cpu_to_be16(XFS_DIR3_LEAFN_MAGIC); lbp->b_ops = &xfs_dir3_leafn_buf_ops; - xfs_trans_buf_set_type(tp, lbp, XFS_BLF_DIR_LEAFN_BUF); + xfs_trans_buf_set_type(tp, lbp, XFS_BLFT_DIR_LEAFN_BUF); xfs_dir3_leaf_log_header(tp, lbp); xfs_dir3_leaf_check(mp, lbp); return 0; @@ -814,7 +814,7 @@ xfs_dir2_leafn_lookup_for_entry( (char *)curbp->b_addr); state->extrablk.magic = XFS_DIR2_DATA_MAGIC; curbp->b_ops = &xfs_dir3_data_buf_ops; - xfs_trans_buf_set_type(tp, curbp, XFS_BLF_DIR_DATA_BUF); + xfs_trans_buf_set_type(tp, curbp, XFS_BLFT_DIR_DATA_BUF); if (cmp == XFS_CMP_EXACT) return XFS_ERROR(EEXIST); } @@ -829,7 +829,7 @@ xfs_dir2_leafn_lookup_for_entry( state->extrablk.blkno = curdb; state->extrablk.magic = XFS_DIR2_DATA_MAGIC; curbp->b_ops = &xfs_dir3_data_buf_ops; - xfs_trans_buf_set_type(tp, curbp, XFS_BLF_DIR_DATA_BUF); + xfs_trans_buf_set_type(tp, curbp, XFS_BLFT_DIR_DATA_BUF); } else { /* If the curbp is not the CI match block, drop it */ if (state->extrablk.bp != curbp) diff --git a/fs/xfs/xfs_ialloc.c b/fs/xfs/xfs_ialloc.c index 8ceaa11..d82071d 100644 --- a/fs/xfs/xfs_ialloc.c +++ b/fs/xfs/xfs_ialloc.c @@ -1474,7 +1474,7 @@ xfs_ialloc_log_agi( /* * Log the allocation group inode header buffer. */ - xfs_trans_buf_set_type(tp, bp, XFS_BLF_AGI_BUF); + xfs_trans_buf_set_type(tp, bp, XFS_BLFT_AGI_BUF); xfs_trans_log_buf(tp, bp, first, last); } diff --git a/fs/xfs/xfs_log_recover.c b/fs/xfs/xfs_log_recover.c index 6410d43..c686bff 100644 --- a/fs/xfs/xfs_log_recover.c +++ b/fs/xfs/xfs_log_recover.c @@ -1888,8 +1888,8 @@ xlog_recovery_validate_buf_type( magic32 = be32_to_cpu(*(__be32 *)bp->b_addr); magic16 = be16_to_cpu(*(__be16*)bp->b_addr); magicda = be16_to_cpu(info->magic); - switch (buf_f->blf_flags & XFS_BLF_TYPE_MASK) { - case XFS_BLF_BTREE_BUF: + switch (xfs_blft_from_flags(buf_f)) { + case XFS_BLFT_BTREE_BUF: switch (magic32) { case XFS_ABTB_CRC_MAGIC: case XFS_ABTC_CRC_MAGIC: @@ -1911,7 +1911,7 @@ xlog_recovery_validate_buf_type( break; } break; - case XFS_BLF_AGF_BUF: + case XFS_BLFT_AGF_BUF: if (magic32 != XFS_AGF_MAGIC) { xfs_warn(mp, "Bad AGF block magic!"); ASSERT(0); @@ -1919,7 +1919,7 @@ xlog_recovery_validate_buf_type( } bp->b_ops = &xfs_agf_buf_ops; break; - case XFS_BLF_AGFL_BUF: + case XFS_BLFT_AGFL_BUF: if (!xfs_sb_version_hascrc(&mp->m_sb)) break; if (magic32 != XFS_AGFL_MAGIC) { @@ -1929,7 +1929,7 @@ xlog_recovery_validate_buf_type( } bp->b_ops = &xfs_agfl_buf_ops; break; - case XFS_BLF_AGI_BUF: + case XFS_BLFT_AGI_BUF: if (magic32 != XFS_AGI_MAGIC) { xfs_warn(mp, "Bad AGI block magic!"); ASSERT(0); @@ -1937,9 +1937,9 @@ xlog_recovery_validate_buf_type( } bp->b_ops = &xfs_agi_buf_ops; break; - case XFS_BLF_UDQUOT_BUF: - case XFS_BLF_PDQUOT_BUF: - case XFS_BLF_GDQUOT_BUF: + case XFS_BLFT_UDQUOT_BUF: + case XFS_BLFT_PDQUOT_BUF: + case XFS_BLFT_GDQUOT_BUF: if (magic16 != XFS_DQUOT_MAGIC) { xfs_warn(mp, "Bad DQUOT block magic!"); ASSERT(0); @@ -1947,7 +1947,7 @@ xlog_recovery_validate_buf_type( } bp->b_ops = &xfs_dquot_buf_ops; break; - case XFS_BLF_DINO_BUF: + case XFS_BLFT_DINO_BUF: /* * we get here with inode allocation buffers, not buffers that * track unlinked list changes. @@ -1959,7 +1959,7 @@ xlog_recovery_validate_buf_type( } bp->b_ops = &xfs_inode_buf_ops; break; - case XFS_BLF_SYMLINK_BUF: + case XFS_BLFT_SYMLINK_BUF: if (magic32 != XFS_SYMLINK_MAGIC) { xfs_warn(mp, "Bad symlink block magic!"); ASSERT(0); @@ -1967,7 +1967,7 @@ xlog_recovery_validate_buf_type( } bp->b_ops = &xfs_symlink_buf_ops; break; - case XFS_BLF_DIR_BLOCK_BUF: + case XFS_BLFT_DIR_BLOCK_BUF: if (magic32 != XFS_DIR2_BLOCK_MAGIC && magic32 != XFS_DIR3_BLOCK_MAGIC) { xfs_warn(mp, "Bad dir block magic!"); @@ -1976,7 +1976,7 @@ xlog_recovery_validate_buf_type( } bp->b_ops = &xfs_dir3_block_buf_ops; break; - case XFS_BLF_DIR_DATA_BUF: + case XFS_BLFT_DIR_DATA_BUF: if (magic32 != XFS_DIR2_DATA_MAGIC && magic32 != XFS_DIR3_DATA_MAGIC) { xfs_warn(mp, "Bad dir data magic!"); @@ -1985,7 +1985,7 @@ xlog_recovery_validate_buf_type( } bp->b_ops = &xfs_dir3_data_buf_ops; break; - case XFS_BLF_DIR_FREE_BUF: + case XFS_BLFT_DIR_FREE_BUF: if (magic32 != XFS_DIR2_FREE_MAGIC && magic32 != XFS_DIR3_FREE_MAGIC) { xfs_warn(mp, "Bad dir3 free magic!"); @@ -1994,7 +1994,7 @@ xlog_recovery_validate_buf_type( } bp->b_ops = &xfs_dir3_free_buf_ops; break; - case XFS_BLF_DIR_LEAF1_BUF: + case XFS_BLFT_DIR_LEAF1_BUF: if (magicda != XFS_DIR2_LEAF1_MAGIC && magicda != XFS_DIR3_LEAF1_MAGIC) { xfs_warn(mp, "Bad dir leaf1 magic!"); @@ -2003,7 +2003,7 @@ xlog_recovery_validate_buf_type( } bp->b_ops = &xfs_dir3_leaf1_buf_ops; break; - case XFS_BLF_DIR_LEAFN_BUF: + case XFS_BLFT_DIR_LEAFN_BUF: if (magicda != XFS_DIR2_LEAFN_MAGIC && magicda != XFS_DIR3_LEAFN_MAGIC) { xfs_warn(mp, "Bad dir leafn magic!"); @@ -2012,7 +2012,7 @@ xlog_recovery_validate_buf_type( } bp->b_ops = &xfs_dir3_leafn_buf_ops; break; - case XFS_BLF_DA_NODE_BUF: + case XFS_BLFT_DA_NODE_BUF: if (magicda != XFS_DA_NODE_MAGIC && magicda != XFS_DA3_NODE_MAGIC) { xfs_warn(mp, "Bad da node magic!"); @@ -2021,7 +2021,7 @@ xlog_recovery_validate_buf_type( } bp->b_ops = &xfs_da3_node_buf_ops; break; - case XFS_BLF_ATTR_LEAF_BUF: + case XFS_BLFT_ATTR_LEAF_BUF: if (magicda != XFS_ATTR_LEAF_MAGIC && magicda != XFS_ATTR3_LEAF_MAGIC) { xfs_warn(mp, "Bad attr leaf magic!"); @@ -2030,7 +2030,7 @@ xlog_recovery_validate_buf_type( } bp->b_ops = &xfs_attr3_leaf_buf_ops; break; - case XFS_BLF_ATTR_RMT_BUF: + case XFS_BLFT_ATTR_RMT_BUF: if (!xfs_sb_version_hascrc(&mp->m_sb)) break; if (magicda != XFS_ATTR3_RMT_MAGIC) { @@ -2040,7 +2040,7 @@ xlog_recovery_validate_buf_type( } bp->b_ops = &xfs_attr3_rmt_buf_ops; break; - case XFS_BLF_SB_BUF: + case XFS_BLFT_SB_BUF: if (magic32 != XFS_SB_MAGIC) { xfs_warn(mp, "Bad SB block magic!"); ASSERT(0); @@ -2049,6 +2049,8 @@ xlog_recovery_validate_buf_type( bp->b_ops = &xfs_sb_buf_ops; break; default: + xfs_warn(mp, "Unknown buffer type %d!", + xfs_blft_from_flags(buf_f)); break; } } diff --git a/fs/xfs/xfs_mount.c b/fs/xfs/xfs_mount.c index cbef607..562ae16 100644 --- a/fs/xfs/xfs_mount.c +++ b/fs/xfs/xfs_mount.c @@ -1696,7 +1696,7 @@ xfs_mod_sb(xfs_trans_t *tp, __int64_t fields) ASSERT((1LL << f) & XFS_SB_MOD_BITS); first = xfs_sb_info[f].offset; - xfs_trans_buf_set_type(tp, bp, XFS_BLF_SB_BUF); + xfs_trans_buf_set_type(tp, bp, XFS_BLFT_SB_BUF); xfs_trans_log_buf(tp, bp, first, last); } diff --git a/fs/xfs/xfs_trans_buf.c b/fs/xfs/xfs_trans_buf.c index 40871bf..73a5fa4 100644 --- a/fs/xfs/xfs_trans_buf.c +++ b/fs/xfs/xfs_trans_buf.c @@ -659,7 +659,7 @@ xfs_trans_binval( ASSERT(XFS_BUF_ISSTALE(bp)); ASSERT(!(bip->bli_flags & (XFS_BLI_LOGGED | XFS_BLI_DIRTY))); ASSERT(!(bip->__bli_format.blf_flags & XFS_BLF_INODE_BUF)); - ASSERT(!(bip->__bli_format.blf_flags & XFS_BLF_TYPE_MASK)); + ASSERT(!(bip->__bli_format.blf_flags & XFS_BLFT_MASK)); ASSERT(bip->__bli_format.blf_flags & XFS_BLF_CANCEL); ASSERT(bip->bli_item.li_desc->lid_flags & XFS_LID_DIRTY); ASSERT(tp->t_flags & XFS_TRANS_DIRTY); @@ -672,7 +672,7 @@ xfs_trans_binval( bip->bli_flags &= ~(XFS_BLI_INODE_BUF | XFS_BLI_LOGGED | XFS_BLI_DIRTY); bip->__bli_format.blf_flags &= ~XFS_BLF_INODE_BUF; bip->__bli_format.blf_flags |= XFS_BLF_CANCEL; - bip->__bli_format.blf_flags &= ~XFS_BLF_TYPE_MASK; + bip->__bli_format.blf_flags &= ~XFS_BLFT_MASK; for (i = 0; i < bip->bli_format_count; i++) { memset(bip->bli_formats[i].blf_data_map, 0, (bip->bli_formats[i].blf_map_size * sizeof(uint))); @@ -704,7 +704,7 @@ xfs_trans_inode_buf( ASSERT(atomic_read(&bip->bli_refcount) > 0); bip->bli_flags |= XFS_BLI_INODE_BUF; - xfs_trans_buf_set_type(tp, bp, XFS_BLF_DINO_BUF); + xfs_trans_buf_set_type(tp, bp, XFS_BLFT_DINO_BUF); } /* @@ -729,7 +729,7 @@ xfs_trans_stale_inode_buf( bip->bli_flags |= XFS_BLI_STALE_INODE; bip->bli_item.li_cb = xfs_buf_iodone; - xfs_trans_buf_set_type(tp, bp, XFS_BLF_DINO_BUF); + xfs_trans_buf_set_type(tp, bp, XFS_BLFT_DINO_BUF); } /* @@ -753,7 +753,7 @@ xfs_trans_inode_alloc_buf( ASSERT(atomic_read(&bip->bli_refcount) > 0); bip->bli_flags |= XFS_BLI_INODE_ALLOC_BUF; - xfs_trans_buf_set_type(tp, bp, XFS_BLF_DINO_BUF); + xfs_trans_buf_set_type(tp, bp, XFS_BLFT_DINO_BUF); } /* @@ -764,7 +764,7 @@ void xfs_trans_buf_set_type( struct xfs_trans *tp, struct xfs_buf *bp, - uint type) + enum xfs_blft type) { struct xfs_buf_log_item *bip = bp->b_fspriv; @@ -774,10 +774,8 @@ xfs_trans_buf_set_type( ASSERT(bp->b_transp == tp); ASSERT(bip != NULL); ASSERT(atomic_read(&bip->bli_refcount) > 0); - ASSERT((type & XFS_BLF_TYPE_MASK) != 0); - bip->__bli_format.blf_flags &= ~XFS_BLF_TYPE_MASK; - bip->__bli_format.blf_flags |= type; + xfs_blft_to_flags(&bip->__bli_format, type); } void @@ -787,11 +785,10 @@ xfs_trans_buf_copy_type( { struct xfs_buf_log_item *sbip = src_bp->b_fspriv; struct xfs_buf_log_item *dbip = dst_bp->b_fspriv; - uint type; + enum xfs_blft type; - type = sbip->__bli_format.blf_flags & XFS_BLF_TYPE_MASK; - dbip->__bli_format.blf_flags &= ~XFS_BLF_TYPE_MASK; - dbip->__bli_format.blf_flags |= type; + type = xfs_blft_from_flags(&sbip->__bli_format); + xfs_blft_to_flags(&dbip->__bli_format, type); } /* @@ -811,9 +808,28 @@ xfs_trans_dquot_buf( xfs_buf_t *bp, uint type) { + struct xfs_buf_log_item *bip = bp->b_fspriv; + ASSERT(type == XFS_BLF_UDQUOT_BUF || type == XFS_BLF_PDQUOT_BUF || type == XFS_BLF_GDQUOT_BUF); + bip->__bli_format.blf_flags |= type; + + switch (type) { + case XFS_BLF_UDQUOT_BUF: + type = XFS_BLFT_UDQUOT_BUF; + break; + case XFS_BLF_PDQUOT_BUF: + type = XFS_BLFT_PDQUOT_BUF; + break; + case XFS_BLF_GDQUOT_BUF: + type = XFS_BLFT_GDQUOT_BUF; + break; + default: + type = XFS_BLFT_UNKNOWN_BUF; + break; + } + xfs_trans_buf_set_type(tp, bp, type); } From qcai@redhat.com Tue Mar 12 21:44:43 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id BC2077F37 for ; Tue, 12 Mar 2013 21:44:43 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id 9EF58304067 for ; Tue, 12 Mar 2013 19:44:40 -0700 (PDT) X-ASG-Debug-ID: 1363142678-04cbb04b8720230001-NocioJ Received: from mx4-phx2.redhat.com (mx4-phx2.redhat.com [209.132.183.25]) by cuda.sgi.com with ESMTP id 5N6PHoZETCtVKPtg for ; Tue, 12 Mar 2013 19:44:39 -0700 (PDT) X-Barracuda-Envelope-From: qcai@redhat.com X-Barracuda-Apparent-Source-IP: 209.132.183.25 Received: from zmail14.collab.prod.int.phx2.redhat.com (zmail14.collab.prod.int.phx2.redhat.com [10.5.83.16]) by mx4-phx2.redhat.com (8.13.8/8.13.8) with ESMTP id r2D2iama007878; Tue, 12 Mar 2013 22:44:37 -0400 Date: Tue, 12 Mar 2013 22:44:36 -0400 (EDT) From: CAI Qian To: Dave Chinner Cc: xfs@oss.sgi.com Message-ID: <1063371063.191362.1363142676803.JavaMail.root@redhat.com> In-Reply-To: <20130312074608.GL21651@dastard> Subject: Re: 3.9-rc2 xfs panic MIME-Version: 1.0 X-ASG-Orig-Subj: Re: 3.9-rc2 xfs panic Content-Type: text/plain; charset=utf-8 Content-Transfer-Encoding: quoted-printable X-Originating-IP: [10.66.13.149] X-Mailer: Zimbra 7.2.0_GA_2669 (ZimbraWebClient - FF3.0 (Linux)/7.2.0_GA_2669) X-Barracuda-Connect: mx4-phx2.redhat.com[209.132.183.25] X-Barracuda-Start-Time: 1363142679 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125044 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- Eek, got another NULL pointer on an x64 system also. Looks like from xfstests case 110. Same user-space version as the one in the ppc64 case. Still trying to reproduce and without more debugging options enabled if possible. Swap Size =3D 7983 MB Mem Size =3D 7852 MB Number of Processors =3D 16 meta-data=3D/dev/loop0 isize=3D256 agcount=3D4, agsize=3D655= 360 blks =3D sectsz=3D512 attr=3D2, projid32bit=3D0 data =3D bsize=3D2048 blocks=3D2621440, imaxpct= =3D25 =3D sunit=3D0 swidth=3D0 blks naming =3Dversion 2 bsize=3D4096 ascii-ci=3D0 log =3Dinternal log bsize=3D2048 blocks=3D5120, version=3D= 2 =3D sectsz=3D512 sunit=3D0 blks, lazy-coun= t=3D1 realtime =3Dnone extsz=3D4096 blocks=3D0, rtextents=3D0 CAI Qian [30706.240701] XFS (loop1): xfs_trans_ail_delete_bulk: attempting to delete= a log item that is not in the AIL=20 [30706.242124] XFS (loop1): xfs_do_force_shutdown(0x2) called from line 743= of file fs/xfs/xfs_trans_ail.c. Return address =3D 0xffffffffa03c03ef=20 [30706.245280] XFS (loop1): Log I/O Error Detected. Shutting down filesyst= em=20 [30706.246311] XFS (loop1): Please umount the filesystem and rectify the pr= oblem(s)=20 [30707.279880] XFS (loop0): Mounting Filesystem=20 [30707.290512] XFS (loop0): Ending clean mount=20 [30708.966751] XFS (loop1): xfs_log_force: error 5 returned.=20 [30708.977075] XFS (loop1): xfs_log_force: error 5 returned.=20 [30708.978074] BUG: unable to handle kernel NULL pointer dereference at 000= 0000000000230=20 [30708.979629] IP: [] xfs_bdstrat_cb+0x27/0xd0 [xfs]=20 [30708.980846] PGD 0 =20 [30708.981354] Oops: 0000 [#1] SMP =20 [30708.982012] Modules linked in: fuse(F) scsi_transport_iscsi(F) tun(F) ip= t_ULOG(F) binfmt_misc(F) bnep(F) hidp(F) nfc(F) af_802154(F) pppoe(F) pppox= (F) ppp_generic(F) slhc(F) rds(F) af_key(F) atm(F) ip6table_filter(F) ip6_t= ables(F) iptable_filter(F) ip_tables(F) btrfs(F) zlib_deflate(F) raid6_pq(F= ) xor(F) vfat(F) fat(F) nfsv3(F) nfs_acl(F) nfsv2(F) nfs(F) lockd(F) sunrpc= (F) dns_resolver(F) fscache(F) nfnetlink_log(F) nfnetlink(F) bluetooth(F) r= fkill(F) nf_tproxy_core(F) nls_koi8_u(F) nls_cp932(F) ts_kmp(F) sctp(F) sg(= F) ipmi_si(F) kvm_amd(F) bnx2(F) hpwdt(F) ipmi_msghandler(F) hpilo(F) kvm(F= ) amd64_edac_mod(F) serio_raw(F) edac_mce_amd(F) pcspkr(F) shpchp(F) edac_c= ore(F) microcode(F) k10temp(F) xfs(F) libcrc32c(F) hpsa(F) sr_mod(F) cdrom(= F) ata_generic(F) radeon(F) i2c_algo_bit(F) pata_acpi(F) qla2xxx(F) drm_kms= _helper(F) ttm(F) pata_amd(F) scsi_transport_fc(F) drm(F) scsi_tgt(F) libat= a(F) cciss(F) i2c_core(F) dm_mirror(F) dm_region_hash(F) dm_log(F) dm_mod(F= ) [last unloaded: ipt_REJECT]=20 [30709.000425] CPU 11 =20 [30709.000749] Pid: 29444, comm: xfsaild/loop1 Tainted: GF W 3.9.0= -rc2+ #1 HP ProLiant DL585 G5 =20 [30709.002464] RIP: 0010:[] [] xfs_bds= trat_cb+0x27/0xd0 [xfs]=20 [30709.004076] RSP: 0018:ffff8801f8d21d18 EFLAGS: 00010286=20 [30709.005089] RAX: 0000000000000000 RBX: ffff88017c672b80 RCX: dead0000002= 00200=20 [30709.006415] RDX: ffff88017c670df8 RSI: 00000000802a0013 RDI: ffff88017c6= 70d80=20 [30709.007791] RBP: ffff8801f8d21d38 R08: ffff88017c670df8 R09: 00000000000= 00001=20 [30709.009274] R10: ffffea0009e43c00 R11: ffffffffa037b055 R12: ffff88017c6= 70d80=20 [30709.010597] R13: ffff8801f8d21dd8 R14: ffff88025cfba5e0 R15: ffff88017c6= 72b80=20 [30709.011973] FS: 00007fdebffff700(0000) GS:ffff88027fb00000(0000) knlGS:= 00000000f75736c0=20 [30709.013575] CS: 0010 DS: 0000 ES: 0000 CR0: 000000008005003b=20 [30709.014760] CR2: 0000000000000230 CR3: 000000010ac7b000 CR4: 00000000000= 007e0=20 [30709.016188] DR0: 0000000000000000 DR1: 0000000000000000 DR2: 00000000000= 00000=20 [30709.017571] DR3: 0000000000000000 DR6: 00000000ffff0ff0 DR7: 00000000000= 00400=20 [30709.018957] Process xfsaild/loop1 (pid: 29444, threadinfo ffff8801f8d200= 00, task ffff8801e2ea65c0)=20 [30709.020766] Stack:=20 [30709.021198] 0000000000000000 ffff88017c672b80 0000000000000000 ffff8801= f8d21dd8=20 [30709.022712] ffff8801f8d21dc8 ffffffffa0365801 ffff88017c670df8 ffff8802= 5cfba658=20 [30709.024102] 00000000f8d21d78 ffffffffa03661b0 ffff88017c670d80 00000000= 91827364=20 [30709.025480] Call Trace:=20 [30709.025938] [] __xfs_buf_delwri_submit+0x171/0x1e0 [x= fs]=20 [30709.027202] [] ? xfs_buf_delwri_submit_nowait+0x20/0x= 30 [xfs]=20 [30709.028519] [] ? xfs_trans_ail_cursor_done+0x20/0x30 = [xfs]=20 [30709.029824] [] xfs_buf_delwri_submit_nowait+0x20/0x30= [xfs]=20 [30709.031223] [] xfsaild+0x222/0x5e0 [xfs]=20 [30709.032291] [] ? xfs_trans_ail_cursor_first+0xb0/0xb0= [xfs]=20 [30709.033661] [] kthread+0xc0/0xd0=20 [30709.034644] [] ? kthread_create_on_node+0x120/0x120= =20 [30709.035870] [] ret_from_fork+0x7c/0xb0=20 [30709.036932] [] ? kthread_create_on_node+0x120/0x120= =20 [30709.038184] Code: 1f 44 00 00 66 66 66 66 90 55 48 89 e5 48 83 ec 20 4c = 89 65 f0 48 89 5d e8 49 89 fc 4c 89 6d f8 48 8b 87 90 00 00 00 48 8b 40 18 = 80 30 02 00 00 10 74 30 4c 8b 6d 08 66 66 66 66 90 49 83 bc =20 [30709.042158] RIP [] xfs_bdstrat_cb+0x27/0xd0 [xfs]=20 [30709.043486] RSP =20 [30709.044224] CR2: 0000000000000230=20 [30709.060200] ---[ end trace e0ed74f75ad92c73 ]---=20 [30734.047588] XFS (loop1): xfs_log_force: error 5 returned.=20 [30764.108856] XFS (loop1): xfs_log_force: error 5 returned.=20 [30794.170118] XFS (loop1): xfs_log_force: error 5 returned.=20 [30824.231359] XFS (loop1): xfs_log_force: error 5 returned.=20 [30854.292624] XFS (loop1): xfs_log_force: error 5 returned.=20 [-- MARK -- Tue Mar 12 09:30:00 2013]=20 [30884.353854] XFS (loop1): xfs_log_force: error 5 returned.=20 [30914.415138] XFS (loop1): xfs_log_force: error 5 returned.=20 [30944.476396] XFS (loop1): xfs_log_force: error 5 returned.=20 [30974.537638] XFS (loop1): xfs_log_force: error 5 returned.=20 [31004.598901] XFS (loop1): xfs_log_force: error 5 returned.=20 [31034.660150] XFS (loop1): xfs_log_force: error 5 returned.=20 [31064.721412] XFS (loop1): xfs_log_force: error 5 returned.=20 [31094.782674] XFS (loop1): xfs_log_force: error 5 returned.=20 [31124.843915] XFS (loop1): xfs_log_force: error 5 returned.=20 [31154.905174] XFS (loop1): xfs_log_force: error 5 returned.=20 [-- MARK -- Tue Mar 12 09:35:00 2013]=20 [31184.966422] XFS (loop1): xfs_log_force: error 5 returned.=20 [31215.027675] XFS (loop1): xfs_log_force: error 5 returned.=20 [31245.088943] XFS (loop1): xfs_log_force: error 5 returned.=20 [31275.150185] XFS (loop1): xfs_log_force: error 5 returned.=20 [31305.211448] XFS (loop1): xfs_log_force: error 5 returned.=20 [31335.272787] XFS (loop1): xfs_log_force: error 5 returned. From bohembagzl@gmail.com Tue Mar 12 22:56:26 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: **** X-Spam-Status: No, score=4.9 required=5.0 tests=FREEMAIL_FROM, HTML_IMAGE_RATIO_02,HTML_MESSAGE,MIME_HTML_ONLY,SUBJ_ALL_CAPS autolearn=no version=3.3.1 X-Original-To: linux-xfs@oss.sgi.com Delivered-To: linux-xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id C441E7F37 for ; Tue, 12 Mar 2013 22:56:26 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay2.corp.sgi.com (Postfix) with ESMTP id AB87B304059 for ; Tue, 12 Mar 2013 20:56:23 -0700 (PDT) X-ASG-Debug-ID: 1363146982-04cb6c4a4323810001-w1Z2WR Received: from falcon578.startdedicated.com (falcon578.startdedicated.com [199.217.116.165]) by cuda.sgi.com with ESMTP id 7MRAlaFDlJ9jH8KH (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO) for ; Tue, 12 Mar 2013 20:56:22 -0700 (PDT) X-Barracuda-Envelope-From: bohembagzl@gmail.com X-Barracuda-Apparent-Source-IP: 199.217.116.165 Received: by falcon578.startdedicated.com (Postfix, from userid 0) id A27B31A03864; Tue, 12 Mar 2013 22:56:20 -0500 (EST) To: linux-xfs@oss.sgi.com Subject: ***BOHEMBAG NUEVA COLECCION 2013 - OFERTA*** X-PHP-Originating-Script: 10037:email.php X-ASG-Orig-Subj: ***BOHEMBAG NUEVA COLECCION 2013 - OFERTA*** Message-ID: <453a2a8ea2192911d3547ac65209c9d5@server00011.com> Date: Sun, 10 Mar 2013 22:13:06 -0400 From: "EDUARD BOADAS" Reply-To: bohembagzl@gmail.com MIME-Version: 1.0 X-Mailer-LID: 5 List-Unsubscribe: X-Mailer-RecptId: 1024274 X-Mailer-SID: 7 X-Mailer-Sent-By: 2 Content-Type: text/html; charset="UTF-8" Content-Transfer-Encoding: 8bit X-Barracuda-Connect: falcon578.startdedicated.com[199.217.116.165] X-Barracuda-Start-Time: 1363146982 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 1.05 X-Barracuda-Spam-Status: No, SCORE=1.05 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=HTML_IMAGE_RATIO_02, HTML_MESSAGE, MIME_HTML_ONLY, STAR, STAR_NOMAG X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125050 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.10 STAR * 0.00 MIME_HTML_ONLY BODY: Message only has text/html MIME parts 0.55 HTML_IMAGE_RATIO_02 BODY: HTML has a low ratio of text to image area 0.00 HTML_MESSAGE BODY: HTML included in message 0.40 STAR_NOMAG * Company Name

Si no puede ver la imagen de clic aqui : http://www.eduardboadas.com/catalogobohembag2013/

http://eduardboadas.com/promo/carterabohembagcoleccion2013.jpg

E-mail: bohembagzl@gmail.com

Tels: 0414-4770231 / 0424-3024138

 San Juan De Los Morros  - Edo. Guarico - Venezuela

Darse de baja en la lista
From sandeen@sandeen.net Tue Mar 12 23:09:58 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id ADF917F37 for ; Tue, 12 Mar 2013 23:09:58 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay2.corp.sgi.com (Postfix) with ESMTP id 8589C30406A for ; Tue, 12 Mar 2013 21:09:55 -0700 (PDT) X-ASG-Debug-ID: 1363147790-04bdf00a0d2a580001-NocioJ Received: from sandeen.net (sandeen.net [63.231.237.45]) by cuda.sgi.com with ESMTP id vq5vXrtB7OgzeWXL for ; Tue, 12 Mar 2013 21:09:50 -0700 (PDT) X-Barracuda-Envelope-From: sandeen@sandeen.net X-Barracuda-Apparent-Source-IP: 63.231.237.45 Received: from liberator.sandeen.net (liberator.sandeen.net [10.0.0.4]) (using TLSv1 with cipher DHE-RSA-CAMELLIA256-SHA (256/256 bits)) (No client certificate requested) by sandeen.net (Postfix) with ESMTPSA id 558D863C3D47; Tue, 12 Mar 2013 23:09:50 -0500 (CDT) Message-ID: <513FFC0D.3030705@sandeen.net> Date: Tue, 12 Mar 2013 23:09:49 -0500 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: Rich Johnston CC: Carlos Maiolino , xfs@oss.sgi.com Subject: Re: [PATCH] xfsdump: properly set Parent's PID References: <1359663197-30473-1-git-send-email-cmaiolino@redhat.com> <513F58FE.1010200@sgi.com> X-ASG-Orig-Subj: Re: [PATCH] xfsdump: properly set Parent's PID In-Reply-To: <513F58FE.1010200@sgi.com> X-Enigmail-Version: 1.5.1 Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: sandeen.net[63.231.237.45] X-Barracuda-Start-Time: 1363147790 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125050 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On 3/12/13 11:34 AM, Rich Johnston wrote: > On 01/31/2013 02:13 PM, Carlos Maiolino wrote: >> Set parentpid variable to the correct Parent's ID using getppid() instead of >> getpid() >> >> Signed-off-by: Carlos Maiolino >> --- >> common/main.c | 2 +- >> 1 file changed, 1 insertion(+), 1 deletion(-) >> >> diff --git a/common/main.c b/common/main.c >> index 980d2d4..848a887 100644 >> --- a/common/main.c >> +++ b/common/main.c >> @@ -198,7 +198,7 @@ main( int argc, char *argv[] ) >> /* Get the parent's pid. will be used in signal handling >> * to differentiate parent from children. >> */ >> - parentpid = getpid( ); >> + parentpid = getppid( ); >> rval = atexit(mlog_exit_flush); >> assert(rval == 0); >> >> > Sorry for the late review, this does not apply to current xfsdump tree. Hm, and hasn't since 2011. ;) 2da84e5d changed this: * to differentiate parent from children. */ - parentpid = getpid( ); + parenttid = pthread_self( ); Carlos, was this maybe against an older tree or released version? -Eric > Regards > --Rich From david@fromorbit.com Tue Mar 12 23:43:12 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 1A82B7F37 for ; Tue, 12 Mar 2013 23:43:12 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay2.corp.sgi.com (Postfix) with ESMTP id C3169304067 for ; Tue, 12 Mar 2013 21:43:11 -0700 (PDT) X-ASG-Debug-ID: 1363149789-04bdf00a0e2ce00001-NocioJ Received: from ipmail07.adl2.internode.on.net (ipmail07.adl2.internode.on.net [150.101.137.131]) by cuda.sgi.com with ESMTP id mXGjuh9QuDzwCr5r for ; Tue, 12 Mar 2013 21:43:09 -0700 (PDT) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.131 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AsodALICQFF5LKiV/2dsb2JhbABDhzC4LIUaAQIBgUsXdIIpAQEFOhwjEAgDGAklDwUlAyETiBPCBhWNTSoYH0oHg0ADllWQd4MeKIEv Received: from ppp121-44-168-149.lns20.syd7.internode.on.net (HELO dastard) ([121.44.168.149]) by ipmail07.adl2.internode.on.net with ESMTP; 13 Mar 2013 15:13:09 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UFdWt-0003XK-Gm; Wed, 13 Mar 2013 15:43:07 +1100 Date: Wed, 13 Mar 2013 15:43:07 +1100 From: Dave Chinner To: CAI Qian Cc: xfs@oss.sgi.com Subject: Re: 3.9-rc2 xfs panic Message-ID: <20130313044307.GV21651@dastard> X-ASG-Orig-Subj: Re: 3.9-rc2 xfs panic References: <20130312074608.GL21651@dastard> <1063371063.191362.1363142676803.JavaMail.root@redhat.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <1063371063.191362.1363142676803.JavaMail.root@redhat.com> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail07.adl2.internode.on.net[150.101.137.131] X-Barracuda-Start-Time: 1363149789 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125052 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Tue, Mar 12, 2013 at 10:44:36PM -0400, CAI Qian wrote: > Eek, got another NULL pointer on an x64 system also. Looks like from > xfstests case 110. Same user-space version as the one in the ppc64 > case. Still trying to reproduce and without more debugging options > enabled if possible. > > Swap Size = 7983 MB > Mem Size = 7852 MB > Number of Processors = 16 > > meta-data=/dev/loop0 isize=256 agcount=4, agsize=655360 blks > = sectsz=512 attr=2, projid32bit=0 > data = bsize=2048 blocks=2621440, imaxpct=25 > = sunit=0 swidth=0 blks > naming =version 2 bsize=4096 ascii-ci=0 > log =internal log bsize=2048 blocks=5120, version=2 > = sectsz=512 sunit=0 blks, lazy-count=1 > realtime =none extsz=4096 blocks=0, rtextents=0 > > CAI Qian > > [30706.240701] XFS (loop1): xfs_trans_ail_delete_bulk: attempting to delete a log item that is not in the AIL What happens prior to this message? This is the first indication of a problem.... > [30706.242124] XFS (loop1): xfs_do_force_shutdown(0x2) called from line 743 of file fs/xfs/xfs_trans_ail.c. Return address = 0xffffffffa03c03ef > [30706.245280] XFS (loop1): Log I/O Error Detected. Shutting down filesystem > [30706.246311] XFS (loop1): Please umount the filesystem and rectify the problem(s) > [30707.279880] XFS (loop0): Mounting Filesystem > [30707.290512] XFS (loop0): Ending clean mount > [30708.966751] XFS (loop1): xfs_log_force: error 5 returned. > [30708.977075] XFS (loop1): xfs_log_force: error 5 returned. > [30708.978074] BUG: unable to handle kernel NULL pointer dereference at 0000000000000230 > [30708.979629] IP: [] xfs_bdstrat_cb+0x27/0xd0 [xfs] And that indicates that the buftarg attached to the buffer has a NULL xfs_mount pointer, so it's probably related to the above issue. As it is, none of my machines see this problem, so I'm wondering if this is related to the way you are using loop devices. Can you reproduce it on a different type of storage device (like LVm of physical disk partitions)? Also, can you turn on CONFIG_XFS_DEBUG and all the memory leak/poisoning checks and see if that catches anything. Cheers, Dave. -- Dave Chinner david@fromorbit.com From qcai@redhat.com Tue Mar 12 23:56:21 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id EDC6C7F37 for ; Tue, 12 Mar 2013 23:56:20 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay2.corp.sgi.com (Postfix) with ESMTP id B0650304077 for ; Tue, 12 Mar 2013 21:56:20 -0700 (PDT) X-ASG-Debug-ID: 1363150578-04cb6c4a45279f0001-NocioJ Received: from mx3-phx2.redhat.com (mx3-phx2.redhat.com [209.132.183.24]) by cuda.sgi.com with ESMTP id e8s4La7l1bYc5xEW for ; Tue, 12 Mar 2013 21:56:19 -0700 (PDT) X-Barracuda-Envelope-From: qcai@redhat.com X-Barracuda-Apparent-Source-IP: 209.132.183.24 Received: from zmail14.collab.prod.int.phx2.redhat.com (zmail14.collab.prod.int.phx2.redhat.com [10.5.83.16]) by mx3-phx2.redhat.com (8.13.8/8.13.8) with ESMTP id r2D4uGpw001170; Wed, 13 Mar 2013 00:56:16 -0400 Date: Wed, 13 Mar 2013 00:56:16 -0400 (EDT) From: CAI Qian To: Dave Chinner Cc: xfs@oss.sgi.com Message-ID: <303705686.219049.1363150576604.JavaMail.root@redhat.com> In-Reply-To: <20130313044307.GV21651@dastard> Subject: Re: 3.9-rc2 xfs panic MIME-Version: 1.0 X-ASG-Orig-Subj: Re: 3.9-rc2 xfs panic Content-Type: text/plain; charset=utf-8 Content-Transfer-Encoding: 7bit X-Originating-IP: [10.66.13.149] X-Mailer: Zimbra 7.2.0_GA_2669 (ZimbraWebClient - FF3.0 (Linux)/7.2.0_GA_2669) X-Barracuda-Connect: mx3-phx2.redhat.com[209.132.183.24] X-Barracuda-Start-Time: 1363150579 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125053 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- ----- Original Message ----- > From: "Dave Chinner" > To: "CAI Qian" > Cc: xfs@oss.sgi.com > Sent: Wednesday, March 13, 2013 12:43:07 PM > Subject: Re: 3.9-rc2 xfs panic > > On Tue, Mar 12, 2013 at 10:44:36PM -0400, CAI Qian wrote: > > Eek, got another NULL pointer on an x64 system also. Looks like > > from > > xfstests case 110. Same user-space version as the one in the ppc64 > > case. Still trying to reproduce and without more debugging options > > enabled if possible. > > > > Swap Size = 7983 MB > > Mem Size = 7852 MB > > Number of Processors = 16 > > > > meta-data=/dev/loop0 isize=256 agcount=4, > > agsize=655360 blks > > = sectsz=512 attr=2, projid32bit=0 > > data = bsize=2048 blocks=2621440, > > imaxpct=25 > > = sunit=0 swidth=0 blks > > naming =version 2 bsize=4096 ascii-ci=0 > > log =internal log bsize=2048 blocks=5120, > > version=2 > > = sectsz=512 sunit=0 blks, > > lazy-count=1 > > realtime =none extsz=4096 blocks=0, rtextents=0 > > > > CAI Qian > > > > [30706.240701] XFS (loop1): xfs_trans_ail_delete_bulk: attempting > > to delete a log item that is not in the AIL > > What happens prior to this message? This is the first indication of > a problem.... Something might be interesting before those were, [30409.026043] XFS (loop1): xfs_log_force: error 5 returned. [30409.027253] XFS (loop1): xfs_log_force: error 5 returned. [30409.028900] XFS (loop1): xfs_log_force: error 5 returned. ... [30453.156830] XFS (loop1): Quotacheck: Done. [30454.006227] XFS (loop1): xfs_log_force: error 5 returned. [30454.010698] XFS (loop1): xfs_log_force: error 5 returned. [30454.011673] XFS (loop1): xfs_qm_dquot_logitem_push: push error 5 on dqp ffff8801f6785e48 [30454.019251] XFS (loop1): xfs_log_force: error 5 returned. ... > > > [30706.242124] XFS (loop1): xfs_do_force_shutdown(0x2) called from > > line 743 of file fs/xfs/xfs_trans_ail.c. Return address = > > 0xffffffffa03c03ef > > [30706.245280] XFS (loop1): Log I/O Error Detected. Shutting down > > filesystem > > [30706.246311] XFS (loop1): Please umount the filesystem and > > rectify the problem(s) > > [30707.279880] XFS (loop0): Mounting Filesystem > > [30707.290512] XFS (loop0): Ending clean mount > > [30708.966751] XFS (loop1): xfs_log_force: error 5 returned. > > [30708.977075] XFS (loop1): xfs_log_force: error 5 returned. > > [30708.978074] BUG: unable to handle kernel NULL pointer > > dereference at 0000000000000230 > > [30708.979629] IP: [] xfs_bdstrat_cb+0x27/0xd0 > > [xfs] > > And that indicates that the buftarg attached to the buffer has a > NULL xfs_mount pointer, so it's probably related to the above issue. > > As it is, none of my machines see this problem, so I'm wondering if > this is related to the way you are using loop devices. Can you > reproduce it on a different type of storage device (like LVm of > physical disk partitions)? Will do. > > Also, can you turn on CONFIG_XFS_DEBUG and all the memory > leak/poisoning checks and see if that catches anything. Will do. CAI Qian > > Cheers, > > Dave. > -- > Dave Chinner > david@fromorbit.com > From rmdukes@gwmail.gwu.edu Wed Mar 13 04:53:07 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=HTML_MESSAGE autolearn=ham version=3.3.1 X-Original-To: linux-xfs@oss.sgi.com Delivered-To: linux-xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 78EF77F37 for ; Wed, 13 Mar 2013 04:53:07 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id 5CB2030407F for ; Wed, 13 Mar 2013 02:53:07 -0700 (PDT) X-ASG-Debug-ID: 1363168385-04cbb04b863d8f0001-w1Z2WR Received: from mail-wg0-f51.google.com (mail-wg0-f51.google.com [74.125.82.51]) by cuda.sgi.com with ESMTP id fBuWUJiVRNPmWqP7 (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Wed, 13 Mar 2013 02:53:06 -0700 (PDT) X-Barracuda-Envelope-From: rmdukes@gwmail.gwu.edu X-Barracuda-Apparent-Source-IP: 74.125.82.51 Received: by mail-wg0-f51.google.com with SMTP id 8so747618wgl.6 for ; Wed, 13 Mar 2013 02:53:04 -0700 (PDT) X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=20120113; h=mime-version:x-received:sender:date:x-google-sender-auth:message-id :subject:from:to:content-type:x-gm-message-state; bh=a1/KAAqgEBeZSCEhUYmVVXyNzCd0K7+Z+vbAyl1gOpU=; b=f4Hqo+0fsBsAidmLZH+amxJvrKcGB+8KhL1k6ee/qKhcFlARNflAXvzr2kT4gSf8J6 xvZYgzXkVMPHdBkPfiyJzxXSY6boGfzd5oSJNr5TlV/hyqQ+gewL4vFusToN7N1f/mil Os3LiGgFmUOyQSOc+hNl/+ClhAlpC5Mp5Yz/Qw/mqpb1jU5BZLWqVH8queiPOgNVh0Qh MEkosV/hb3QDhuP/AxueJHZVjDSrt333E2BBNjNXnJzn+g2gUcA04jQWDDOcJ99S6DSy GNMG/+bimnE+gPper8UNhZRibC948MpQcMs/1J9UUY7JsI1kJ5YInXFtXGIbzdfIxl+i v6Sg== MIME-Version: 1.0 X-Received: by 10.194.123.130 with SMTP id ma2mr16326648wjb.46.1363168384049; Wed, 13 Mar 2013 02:53:04 -0700 (PDT) Sender: rmdukes@gwmail.gwu.edu Received: by 10.227.7.165 with HTTP; Wed, 13 Mar 2013 02:53:03 -0700 (PDT) Date: Wed, 13 Mar 2013 02:53:03 -0700 X-Google-Sender-Auth: hEhoALuW0hEZAkXc0vXjgFXXPKw Message-ID: Subject: Project From: Joseph Wong X-ASG-Orig-Subj: Project To: undisclosed-recipients:; Content-Type: multipart/alternative; boundary=089e012287de4cfbe904d7cb5f70 X-Gm-Message-State: ALoCoQl0+K1OX9tqppmsIvRQg9P0tMyOZk0IvsfiBjl+5ZbevtgUWDKtn5OZBAhRFHZMUBq9C1/c X-Barracuda-Connect: mail-wg0-f51.google.com[74.125.82.51] X-Barracuda-Start-Time: 1363168385 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-BRTS-Evidence: b0f4b77724c992d40c736c1f167cfcfa-77-htm X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=HTML_MESSAGE X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125072 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 HTML_MESSAGE BODY: HTML included in message --089e012287de4cfbe904d7cb5f70 Content-Type: text/plain; charset=ISO-8859-1 I need your partnership in a business transaction. Regards, Joseph --089e012287de4cfbe904d7cb5f70 Content-Type: text/html; charset=ISO-8859-1 I need your partnership in a business transaction.

Regards,
Joseph --089e012287de4cfbe904d7cb5f70-- From rozentaldimailav@relhist.uu.se Wed Mar 13 07:05:27 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=HTML_MESSAGE autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id C4A847F37 for ; Wed, 13 Mar 2013 07:05:27 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id AAAEA304075 for ; Wed, 13 Mar 2013 05:05:24 -0700 (PDT) X-ASG-Debug-ID: 1363176321-04cbb04b8748900001-NocioJ Received: from host.host-media.ru (savatouristik.ru [95.163.65.23]) by cuda.sgi.com with ESMTP id s7l3L2xjvhLvtbpB (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO) for ; Wed, 13 Mar 2013 05:05:22 -0700 (PDT) X-Barracuda-Envelope-From: rozentaldimailav@relhist.uu.se X-Barracuda-Apparent-Source-IP: 95.163.65.23 Received: from [182.121.103.102] (port=53483 helo=hn.kd.ny.adsl) by host.host-media.ru with esmtpa (Exim 4.77) (envelope-from ) id 1UFkL4-0004Z3-W9; Wed, 13 Mar 2013 16:02:09 +0400 Message-ID: Reply-To: =?windows-1251?B?0e/l9ujg6+jx8iDv7iDo7O/u8PLt7i396vHv?= =?windows-1251?B?7vDy7fvsIO7v5fDg9uj/7A==?= From: =?windows-1251?B?0e/l9ujg6+jx8iDv7iDo7O/u8PLt7i396vHv?= =?windows-1251?B?7vDy7fvsIO7v5fDg9uj/7A==?= To: , , , Subject: =?windows-1251?B?0vDg7fHv7vDy7eD/IOvu4+jx8ujq4C4g0uDs?= =?windows-1251?B?7ubt/yD98u4g7eUg5OXq6+Dw4Pbo/yAtIP3y?= =?windows-1251?B?7iDu8u3u+OXt6P8u?= Date: Wed, 13 Mar 2013 04:58:44 -0700 X-ASG-Orig-Subj: =?windows-1251?B?0vDg7fHv7vDy7eD/IOvu4+jx8ujq4C4g0uDs?= =?windows-1251?B?7ubt/yD98u4g7eUg5OXq6+Dw4Pbo/yAtIP3y?= =?windows-1251?B?7iDu8u3u+OXt6P8u?= MIME-Version: 1.0 Content-Type: multipart/alternative; boundary="----=_NextPart_000_254F_01CE1FA7.704FF1D0" X-Priority: 3 X-MSMail-Priority: Normal X-Mailer: Microsoft Outlook Express 6.00.2900.5931 X-MimeOLE: Produced By Microsoft MimeOLE V6.00.2900.6109 X-AntiAbuse: This header was added to track abuse, please include it with any abuse report X-AntiAbuse: Primary Hostname - host.host-media.ru X-AntiAbuse: Original Domain - oss.sgi.com X-AntiAbuse: Originator/Caller UID/GID - [47 12] / [47 12] X-AntiAbuse: Sender Address Domain - relhist.uu.se X-Barracuda-Connect: savatouristik.ru[95.163.65.23] X-Barracuda-Start-Time: 1363176322 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_TG035a, HTML_MESSAGE X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125080 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 HTML_MESSAGE BODY: HTML included in message 0.00 BSF_SC0_TG035a Message contains invalid style definition This is a multi-part message in MIME format. ------=_NextPart_000_254F_01CE1FA7.704FF1D0 Content-Type: text/plain; charset="windows-1251" Content-Transfer-Encoding: quoted-printable =D1=E0=ED=EA=F2-=CF=E5=F2=E5=F0=E1=F3=F0=E3=F1=EA=E0=FF=20 =CA=EE=EC=EF=E0=ED=E8=FF =EE=E1=F3=F7=E0=FE=F9=E8=F5 =EF=F0=EE=F4=E5= =F1=F1=E8=EE=ED=E0=EB=FC=ED=FB=F5 =EA=F3=F0=F1=EE=E2 -=3D-=3D- =D3=E2=E0=E6=E0=E5=EC=FB=E5 =EA=EE=EB=EB=E5=E3=E8! =CF=F0=E8=E3=EB=E0=F8=E0=E5=EC =C2=E0=F1 =ED=E0 =EA=EE=ED=F4=E5=F0=E5=ED=F6= =E8=FE, =EF=EE=F1=E2=FF=F9=E5=ED=ED=F3=FE =E2=EE=EF=F0=EE=F1=E0=EC=20 =EE=EF=F2=E8=EC=E8=E7=E0=F6=E8=E8 =EF=F0=EE=F6=E5=F1=F1=EE=E2 =F2=F0=E0=ED= =F1=EF=EE=F0=F2=ED=EE=E9 =EB=EE=E3=E8=F1=F2=E8=EA=E8 =EF=EE =EF=F0=EE=E3=F0= =E0=EC=EC=E5: =D2=D0=C0=CD=D1=CF=CE=D0=D2=CD=C0=DF =CB=CE=C3=C8=D1=D2=C8=CA=C0 - =D1=CE= =C2=D0=C5=CC=C5=CD=CD=DB=C9 =CF=CE=C4=D5=CE=C4. =D3=CF=D0=C0=C2=CB=C5=CD=C8=C5 =D6=C5=CF=DF=CC=C8 =CF=CE=D1=D2=C0=C2=CE=CA= . =3D|=3D|=3D|=3D|=3D|=3D|=3D|=3D|=3D|=3D|=3D|=3D|=3D|=3D|=3D|=3D|=3D|=3D|=3D= |=3D|=3D|=3D|=3D l5 - l6 =E0=EF=F0=E5=EB=FF 2OI=C7 =E3=EE=E4=E0, =D1=E0=ED=EA=F2-=CF= =E5=F2=E5=F0=E1=F3=F0=E3 =CA=F0=E0=F2=EA=E0=FF =EF=F0=EE=E3=F0=E0=EC=EC=E0: 1. =D1=E8=F1=F2=E5=EC=ED=FB=E9 =EF=EE=E4=F5=EE=E4 =EA =EF=F0=EE=F6=E5=F1=F1= =F3 =FD=EA=EE=ED=EE=EC=E8=E8: =F1=F2=F0=E0=F2=E5=E3=E8=FF =E8 =F2=E0=EA=F2= =E8=EA=E0.=20 =CF=EE=E8=F1=EA =F0=E5=E7=E5=F0=E2=EE=E2. =CF=E5=F0=E5=F1=EC=EE=F2=F0 =EE= =F0=E3=E0=ED=E8=E7=E0=F6=E8=EE=ED=ED=FB=F5 =F1=E8=F1=F2=E5=EC.=20 =D1=E2=EE=E8 =F0=F3=EA=E8 =E8=EB=E8 =F7=F3=E6=E8=E5: =EA=EE=E3=E4=E0 =E4=EE= =EF=F3=F1=F2=E8=EC =E0=F3=F2=F1=EE=F0=F1=E8=ED=E3. 2. =C7=E0=EA=F3=EF=EA=E0 =F3=F1=EB=F3=E3. =CA=E0=EA =F2=F0=E0=ED=F1=EF=EE= =F0=F2=ED=E8=EA=E8 =EC=E0=ED=E8=EF=F3=EB=E8=F0=F3=FE=F2 =F2=E5=ED=E4=E5=F0= =E0=EC=E8.=20 =CC=EE=F2=E8=E2=E0=F6=E8=FF =FD=EA=F1=EF=E5=E4=E8=F2=EE=F0=E0. 3. =C8=CD=CA=CE=D2=C5=D0=CC=D1 - =ED=E5 =F2=EE=EB=FC=EA=EE =F2=E5=F0=EC=E8= =ED=FB.=20 =CE=F1=EE=E1=E5=ED=ED=EE=F1=F2=E8 =EF=EE=F1=F2=E0=E2=EE=EA =E2=ED=E5=F8=ED= =E5=F2=EE=F0=E3=EE=E2=FB=F5 =E3=F0=F3=E7=EE=E2 =F1 =F3=F7=E5=F2=EE=EC=20 =E4=E5=EB=EE=E2=EE=E9 =EF=F0=E0=EA=F2=E8=EA=E8 =E7=E0=EA=EB=FE=F7=E5=ED=E8= =FF =E4=EE=E3=EE=E2=EE=F0=EE=E2 =F1 =ED=E5=F0=E5=E7=E8=E4=E5=ED=F2=E0=EC=E8= . 4. =CA=F2=EE =E7=E0=EF=EB=E0=F2=E8=F2 =E7=E0 =EB=EE=EC. =CA=E0=EA =EF=E5=F0= =E5=E4=E0=F2=FC =EE=F2=E2=E5=F2=F1=F2=E2=E5=ED=ED=EE=F1=F2=FC. =D7=F2=EE =ED=F3=E6=ED=EE =EA=EE=ED=F2=F0=EE=EB=E8=F0=EE=E2=E0=F2=FC =E2 = =EA=E0=F7=E5=F1=F2=E2=E5.=20 5. =D2=E0=EC=EE=E6=ED=FF =FD=F2=EE =ED=E5 =E4=E5=EA=EB=E0=F0=E0=F6=E8=FF = - =FD=F2=EE =EE=F2=ED=EE=F8=E5=ED=E8=FF. 6. =D3=EF=F0=E0=E2=EB=E5=ED=E8=E5 =F6=E5=EF=FF=EC=E8 =EF=EE=F1=F2=E0=E2=EE= =EA (SCM - Supply Chain Management).=20 =D0=E0=E7=E2=E8=F2=E8=E5 =F6=E5=EF=E5=E9 =EF=EE=F1=F2=E0=E2=EE=EA. =CE=F2= =EB=E8=F7=E8=E5 =F6=E5=EF=E5=E9 =EF=EE=F1=F2=E0=E2=EE=EA =EE=F2 =EB=EE=E3= =E8=F1=F2=E8=EA=E8. 7. =D2=E5=F5=ED=E8=EA=E8 =F3=EC=E5=ED=FC=F8=E5=ED=E8=FF =F1=EA=EB=E0=E4=F1= =EA=EE=E3=EE =E7=E0=EF=E0=F1=E0. =D0=EE=EB=FC =E8=ED=F4=EE=F0=EC=E0=F6=E8=EE=ED=ED=FB=F5 =F1=E8=F1=F2=E5=EC= =E2 =F1=ED=E8=E6=E5=ED=E8=E8 =E7=E0=F2=F0=E0=F2. 8. =D3=EA=F0=F3=EF=ED=E5=ED=E8=E5 =EF=EE=F2=EE=EA=E0 - =E8=F9=E8=F2=E5 =EF= =EE=EF=F3=F2=F7=E8=EA=EE=E2. =CF=EE =E2=EE=EF=F0=EE=F1=E0=EC =F3=F7=E0=F1=F2=E8=FF =E8 =F0=E5=E3=E8=F1= =F2=F0=E0=F6=E8=E8 =EE=E1=F0=E0=F9=E0=E9=F2=E5=F1=FC =EF=EE =F2=E5=EB=E5=F4= =EE=ED=F3: 8 * =CF=E5=F2=E5=F0=E1=F3=F0=E3 * 64-2 =CEl ^ 2-8 = =20 =D1 =F3=E2=E0=E6=E5=ED=E8=E5=EC, =D6=E2=E5=F2=EA=EE=E2=E0 =C0=ED=E3=E5=EB=E8=ED=E0 =CD=E8=EA=EE=EB=E0=E5=E2= =ED=E0 =EC=E5=ED=E5=E4=E6=E5=F0 =EF=EE =F0=E0=E1=EE=F2=E5 =F1 =EA=EB=E8=E5=ED=F2= =E0=EC=E8 ------=_NextPart_000_254F_01CE1FA7.704FF1D0 Content-Type: text/html; charset="windows-1251" Content-Transfer-Encoding: quoted-printable
           &n= bsp;  =20 =D1=E0=ED=EA=F2-=CF=E5=F2=E5=F0=E1=F3=F0=E3=F1=EA=E0=FF
  &= nbsp;  =CA=EE=EC=EF=E0=ED=E8=FF =EE=E1=F3=F7=E0=FE=F9=E8=F5=20 =EF=F0=EE=F4=E5=F1=F1=E8=EE=ED=E0=EB=FC=ED=FB=F5=20 =EA=F3=F0=F1=EE=E2
        &nb= sp;           &nbs= p;=20 -=3D-=3D-
 
=D3=E2=E0=E6=E0=E5=EC=FB=E5 =EA=EE=EB=EB=E5=E3=E8!
 
=CF=F0=E8=E3=EB=E0=F8=E0=E5=EC =C2=E0=F1 =ED=E0 =EA=EE=ED=F4=E5=F0=E5= =ED=F6=E8=FE, =EF=EE=F1=E2=FF=F9=E5=ED=ED=F3=FE =E2=EE=EF=F0=EE=F1=E0=EC =
=EE=EF=F2=E8=EC=E8=E7=E0=F6=E8=E8=20 =EF=F0=EE=F6=E5=F1=F1=EE=E2 =F2=F0=E0=ED=F1=EF=EE=F0=F2=ED=EE=E9 =EB=EE=E3= =E8=F1=F2=E8=EA=E8 =EF=EE =EF=F0=EE=E3=F0=E0=EC=EC=E5:
 

=D2=D0=C0=CD=D1=CF=CE=D0=D2=CD=C0=DF =CB=CE=C3=C8=D1=D2=C8=CA=C0= - =D1=CE=C2=D0=C5=CC=C5=CD=CD=DB=C9 =CF=CE=C4=D5=CE=C4.
=D3=CF=D0=C0=C2= =CB=C5=CD=C8=C5 =D6=C5=CF=DF=CC=C8=20 =CF=CE=D1=D2=C0=C2=CE=CA.
 
=3D|=3D|=3D|=3D|=3D|=3D|=3D|=3D|=3D|=3D|=3D|=3D|=3D|=3D|=3D|=3D|=3D|= =3D|=3D|=3D|=3D|=3D|=3D
 
l5 - l6=20 =E0=EF=F0=E5=EB=FF 2OI=C7 =E3=EE=E4=E0,=20 =D1=E0=ED=EA=F2-=CF=E5=F2=E5=F0=E1=F3=F0=E3
 

=CA=F0=E0=F2=EA=E0=FF =EF=F0=EE=E3=F0=E0=EC=EC=E0:
 
1. =D1=E8=F1=F2=E5=EC=ED=FB=E9 =EF=EE=E4=F5=EE=E4 =EA =EF=F0=EE=F6=E5= =F1=F1=F3 =FD=EA=EE=ED=EE=EC=E8=E8: =F1=F2=F0=E0=F2=E5=E3=E8=FF =E8 =F2=E0= =EA=F2=E8=EA=E0.
=CF=EE=E8=F1=EA=20 =F0=E5=E7=E5=F0=E2=EE=E2. =CF=E5=F0=E5=F1=EC=EE=F2=F0 =EE=F0=E3=E0=ED=E8=E7= =E0=F6=E8=EE=ED=ED=FB=F5 =F1=E8=F1=F2=E5=EC.
=D1=E2=EE=E8 =F0=F3=EA=E8= =E8=EB=E8 =F7=F3=E6=E8=E5: =EA=EE=E3=E4=E0=20 =E4=EE=EF=F3=F1=F2=E8=EC =E0=F3=F2=F1=EE=F0=F1=E8=ED=E3.
 
2. =C7=E0=EA=F3=EF=EA=E0 =F3=F1=EB=F3=E3. =CA=E0=EA =F2=F0=E0=ED=F1=EF= =EE=F0=F2=ED=E8=EA=E8 =EC=E0=ED=E8=EF=F3=EB=E8=F0=F3=FE=F2 =F2=E5=ED=E4=E5= =F0=E0=EC=E8.
=CC=EE=F2=E8=E2=E0=F6=E8=FF=20 =FD=EA=F1=EF=E5=E4=E8=F2=EE=F0=E0.
 
3. =C8=CD=CA=CE=D2=C5=D0=CC=D1 - =ED=E5 =F2=EE=EB=FC=EA=EE =F2=E5=F0= =EC=E8=ED=FB.
=CE=F1=EE=E1=E5=ED=ED=EE=F1=F2=E8 =EF=EE=F1=F2=E0=E2=EE= =EA =E2=ED=E5=F8=ED=E5=F2=EE=F0=E3=EE=E2=FB=F5=20 =E3=F0=F3=E7=EE=E2 =F1 =F3=F7=E5=F2=EE=EC
=E4=E5=EB=EE=E2=EE=E9 =EF=F0= =E0=EA=F2=E8=EA=E8 =E7=E0=EA=EB=FE=F7=E5=ED=E8=FF =E4=EE=E3=EE=E2=EE=F0=EE= =E2 =F1 =ED=E5=F0=E5=E7=E8=E4=E5=ED=F2=E0=EC=E8.
 
4. =CA=F2=EE =E7=E0=EF=EB=E0=F2=E8=F2 =E7=E0 =EB=EE=EC. =CA=E0=EA =EF= =E5=F0=E5=E4=E0=F2=FC =EE=F2=E2=E5=F2=F1=F2=E2=E5=ED=ED=EE=F1=F2=FC.
=D7= =F2=EE =ED=F3=E6=ED=EE=20 =EA=EE=ED=F2=F0=EE=EB=E8=F0=EE=E2=E0=F2=FC =E2 =EA=E0=F7=E5=F1=F2=E2=E5. =
 
5. =D2=E0=EC=EE=E6=ED=FF =FD=F2=EE =ED=E5 =E4=E5=EA=EB=E0=F0=E0=F6=E8= =FF - =FD=F2=EE =EE=F2=ED=EE=F8=E5=ED=E8=FF.
 
6. =D3=EF=F0=E0=E2=EB=E5=ED=E8=E5 =F6=E5=EF=FF=EC=E8 =EF=EE=F1=F2=E0= =E2=EE=EA (SCM - Supply Chain Management).
=D0=E0=E7=E2=E8=F2=E8=E5=20 =F6=E5=EF=E5=E9 =EF=EE=F1=F2=E0=E2=EE=EA. =CE=F2=EB=E8=F7=E8=E5 =F6=E5=EF= =E5=E9 =EF=EE=F1=F2=E0=E2=EE=EA =EE=F2 =EB=EE=E3=E8=F1=F2=E8=EA=E8.
 
7. =D2=E5=F5=ED=E8=EA=E8 =F3=EC=E5=ED=FC=F8=E5=ED=E8=FF =F1=EA=EB=E0= =E4=F1=EA=EE=E3=EE =E7=E0=EF=E0=F1=E0.
=D0=EE=EB=FC =E8=ED=F4=EE=F0=EC= =E0=F6=E8=EE=ED=ED=FB=F5 =F1=E8=F1=F2=E5=EC =E2=20 =F1=ED=E8=E6=E5=ED=E8=E8 =E7=E0=F2=F0=E0=F2.
 
8. =D3=EA=F0=F3=EF=ED=E5=ED=E8=E5 =EF=EE=F2=EE=EA=E0 - =E8=F9=E8=F2=E5= =EF=EE=EF=F3=F2=F7=E8=EA=EE=E2.
 

=CF=EE =E2=EE=EF=F0=EE=F1=E0=EC =F3=F7=E0=F1=F2=E8=FF =E8 =F0=E5= =E3=E8=F1=F2=F0=E0=F6=E8=E8 =EE=E1=F0=E0=F9=E0=E9=F2=E5=F1=FC =EF=EE=20 =F2=E5=EB=E5=F4=EE=ED=F3:
8 * =CF=E5=F2=E5=F0=E1=F3=F0=E3 * = 64-2 =CEl ^ 2-8
 
=D1 =F3=E2=E0=E6=E5=ED=E8=E5=EC,
=D6=E2=E5=F2=EA=EE=E2=E0 =C0=ED=E3= =E5=EB=E8=ED=E0 =CD=E8=EA=EE=EB=E0=E5=E2=ED=E0
=EC=E5=ED=E5=E4=E6=E5=F0= =EF=EE =F0=E0=E1=EE=F2=E5 =F1=20 =EA=EB=E8=E5=ED=F2=E0=EC=E8
------=_NextPart_000_254F_01CE1FA7.704FF1D0-- From cmaiolino@redhat.com Wed Mar 13 07:47:03 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id DE94B7F37 for ; Wed, 13 Mar 2013 07:47:02 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay3.corp.sgi.com (Postfix) with ESMTP id 6122DAC001 for ; Wed, 13 Mar 2013 05:46:59 -0700 (PDT) X-ASG-Debug-ID: 1363178818-04cbb04b874bf00001-NocioJ Received: from mx1.redhat.com (mx1.redhat.com [209.132.183.28]) by cuda.sgi.com with ESMTP id 3AO3gemGLjz2ZgT9 for ; Wed, 13 Mar 2013 05:46:58 -0700 (PDT) X-Barracuda-Envelope-From: cmaiolino@redhat.com X-Barracuda-Apparent-Source-IP: 209.132.183.28 X-ASG-Whitelist: Client Received: from int-mx01.intmail.prod.int.phx2.redhat.com (int-mx01.intmail.prod.int.phx2.redhat.com [10.5.11.11]) by mx1.redhat.com (8.14.4/8.14.4) with ESMTP id r2DCkvH9018268 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=OK); Wed, 13 Mar 2013 08:46:57 -0400 Received: from andromeda.usersys.redhat.com (ovpn-113-118.phx2.redhat.com [10.3.113.118]) by int-mx01.intmail.prod.int.phx2.redhat.com (8.13.8/8.13.8) with ESMTP id r2DCkr9F019988 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES128-SHA bits=128 verify=NO); Wed, 13 Mar 2013 08:46:56 -0400 Date: Wed, 13 Mar 2013 09:46:52 -0300 From: Carlos Maiolino To: Eric Sandeen Cc: Rich Johnston , xfs@oss.sgi.com Subject: Re: [PATCH] xfsdump: properly set Parent's PID Message-ID: <20130313124651.GA2816@andromeda.usersys.redhat.com> X-ASG-Orig-Subj: Re: [PATCH] xfsdump: properly set Parent's PID References: <1359663197-30473-1-git-send-email-cmaiolino@redhat.com> <513F58FE.1010200@sgi.com> <513FFC0D.3030705@sandeen.net> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <513FFC0D.3030705@sandeen.net> User-Agent: Mutt/1.5.21 (2010-09-15) X-Scanned-By: MIMEDefang 2.67 on 10.5.11.11 X-Barracuda-Connect: mx1.redhat.com[209.132.183.28] X-Barracuda-Start-Time: 1363178818 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 Weird, I git pull'ed the repository before add the patch, I'll review my origin's URL, sorry about that On Tue, Mar 12, 2013 at 11:09:49PM -0500, Eric Sandeen wrote: > On 3/12/13 11:34 AM, Rich Johnston wrote: > > On 01/31/2013 02:13 PM, Carlos Maiolino wrote: > >> Set parentpid variable to the correct Parent's ID using getppid() instead of > >> getpid() > >> > >> Signed-off-by: Carlos Maiolino > >> --- > >> common/main.c | 2 +- > >> 1 file changed, 1 insertion(+), 1 deletion(-) > >> > >> diff --git a/common/main.c b/common/main.c > >> index 980d2d4..848a887 100644 > >> --- a/common/main.c > >> +++ b/common/main.c > >> @@ -198,7 +198,7 @@ main( int argc, char *argv[] ) > >> /* Get the parent's pid. will be used in signal handling > >> * to differentiate parent from children. > >> */ > >> - parentpid = getpid( ); > >> + parentpid = getppid( ); > >> rval = atexit(mlog_exit_flush); > >> assert(rval == 0); > >> > >> > > Sorry for the late review, this does not apply to current xfsdump tree. > > Hm, and hasn't since 2011. ;) > > 2da84e5d changed this: > > * to differentiate parent from children. > */ > - parentpid = getpid( ); > + parenttid = pthread_self( ); > > Carlos, was this maybe against an older tree or released version? > > -Eric > > > Regards > > --Rich > > _______________________________________________ > xfs mailing list > xfs@oss.sgi.com > http://oss.sgi.com/mailman/listinfo/xfs -- Carlos From cmaiolino@redhat.com Wed Mar 13 07:59:03 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id B72E57F37 for ; Wed, 13 Mar 2013 07:59:03 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay2.corp.sgi.com (Postfix) with ESMTP id 9BB0130406B for ; Wed, 13 Mar 2013 05:59:03 -0700 (PDT) X-ASG-Debug-ID: 1363179542-04cb6c4a4352a40001-NocioJ Received: from mx1.redhat.com (mx1.redhat.com [209.132.183.28]) by cuda.sgi.com with ESMTP id WSvgDC3tvhVp3To4 for ; Wed, 13 Mar 2013 05:59:02 -0700 (PDT) X-Barracuda-Envelope-From: cmaiolino@redhat.com X-Barracuda-Apparent-Source-IP: 209.132.183.28 X-ASG-Whitelist: Client Received: from int-mx11.intmail.prod.int.phx2.redhat.com (int-mx11.intmail.prod.int.phx2.redhat.com [10.5.11.24]) by mx1.redhat.com (8.14.4/8.14.4) with ESMTP id r2DCx1XH010400 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=OK); Wed, 13 Mar 2013 08:59:02 -0400 Received: from andromeda.usersys.redhat.com (ovpn-113-118.phx2.redhat.com [10.3.113.118]) by int-mx11.intmail.prod.int.phx2.redhat.com (8.14.4/8.14.4) with ESMTP id r2DCwvt5010547 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES128-SHA bits=128 verify=NO); Wed, 13 Mar 2013 08:59:00 -0400 Date: Wed, 13 Mar 2013 09:58:56 -0300 From: Carlos Maiolino To: Eric Sandeen Cc: Rich Johnston , xfs@oss.sgi.com Subject: Re: [PATCH] xfsdump: properly set Parent's PID Message-ID: <20130313125856.GB2816@andromeda.usersys.redhat.com> X-ASG-Orig-Subj: Re: [PATCH] xfsdump: properly set Parent's PID References: <1359663197-30473-1-git-send-email-cmaiolino@redhat.com> <513F58FE.1010200@sgi.com> <513FFC0D.3030705@sandeen.net> <20130313124651.GA2816@andromeda.usersys.redhat.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <20130313124651.GA2816@andromeda.usersys.redhat.com> User-Agent: Mutt/1.5.21 (2010-09-15) X-Scanned-By: MIMEDefang 2.68 on 10.5.11.24 X-Barracuda-Connect: mx1.redhat.com[209.132.183.28] X-Barracuda-Start-Time: 1363179542 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 Ah, my origin was pointing to the git.kernel.org xfsdump repository =[ On Wed, Mar 13, 2013 at 09:46:52AM -0300, Carlos Maiolino wrote: > Weird, I git pull'ed the repository before add the patch, I'll review my > origin's URL, sorry about that > > On Tue, Mar 12, 2013 at 11:09:49PM -0500, Eric Sandeen wrote: > > On 3/12/13 11:34 AM, Rich Johnston wrote: > > > On 01/31/2013 02:13 PM, Carlos Maiolino wrote: > > >> Set parentpid variable to the correct Parent's ID using getppid() instead of > > >> getpid() > > >> > > >> Signed-off-by: Carlos Maiolino > > >> --- > > >> common/main.c | 2 +- > > >> 1 file changed, 1 insertion(+), 1 deletion(-) > > >> > > >> diff --git a/common/main.c b/common/main.c > > >> index 980d2d4..848a887 100644 > > >> --- a/common/main.c > > >> +++ b/common/main.c > > >> @@ -198,7 +198,7 @@ main( int argc, char *argv[] ) > > >> /* Get the parent's pid. will be used in signal handling > > >> * to differentiate parent from children. > > >> */ > > >> - parentpid = getpid( ); > > >> + parentpid = getppid( ); > > >> rval = atexit(mlog_exit_flush); > > >> assert(rval == 0); > > >> > > >> > > > Sorry for the late review, this does not apply to current xfsdump tree. > > > > Hm, and hasn't since 2011. ;) > > > > 2da84e5d changed this: > > > > * to differentiate parent from children. > > */ > > - parentpid = getpid( ); > > + parenttid = pthread_self( ); > > > > Carlos, was this maybe against an older tree or released version? > > > > -Eric > > > > > Regards > > > --Rich > > > > _______________________________________________ > > xfs mailing list > > xfs@oss.sgi.com > > http://oss.sgi.com/mailman/listinfo/xfs > > -- > Carlos > > _______________________________________________ > xfs mailing list > xfs@oss.sgi.com > http://oss.sgi.com/mailman/listinfo/xfs -- Carlos From sandeen@sandeen.net Wed Mar 13 08:39:49 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 05C3C7F37 for ; Wed, 13 Mar 2013 08:39:49 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay1.corp.sgi.com (Postfix) with ESMTP id BBB0D8F8049 for ; Wed, 13 Mar 2013 06:39:48 -0700 (PDT) X-ASG-Debug-ID: 1363181987-04bdf00a0d5a770001-NocioJ Received: from sandeen.net (sandeen.net [63.231.237.45]) by cuda.sgi.com with ESMTP id PlzWCtjcn2fEdC6G for ; Wed, 13 Mar 2013 06:39:47 -0700 (PDT) X-Barracuda-Envelope-From: sandeen@sandeen.net X-Barracuda-Apparent-Source-IP: 63.231.237.45 Received: from liberator.sandeen.net (liberator.sandeen.net [10.0.0.4]) (using TLSv1 with cipher DHE-RSA-CAMELLIA256-SHA (256/256 bits)) (No client certificate requested) by sandeen.net (Postfix) with ESMTPSA id C298463C3D47; Wed, 13 Mar 2013 08:39:46 -0500 (CDT) Message-ID: <514081A2.9080106@sandeen.net> Date: Wed, 13 Mar 2013 08:39:46 -0500 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: Carlos Maiolino CC: Rich Johnston , xfs@oss.sgi.com, Christoph Hellwig Subject: Re: [PATCH] xfsdump: properly set Parent's PID References: <1359663197-30473-1-git-send-email-cmaiolino@redhat.com> <513F58FE.1010200@sgi.com> <513FFC0D.3030705@sandeen.net> <20130313124651.GA2816@andromeda.usersys.redhat.com> <20130313125856.GB2816@andromeda.usersys.redhat.com> X-ASG-Orig-Subj: Re: [PATCH] xfsdump: properly set Parent's PID In-Reply-To: <20130313125856.GB2816@andromeda.usersys.redhat.com> X-Enigmail-Version: 1.5.1 Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: sandeen.net[63.231.237.45] X-Barracuda-Start-Time: 1363181987 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125086 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On 3/13/13 7:58 AM, Carlos Maiolino wrote: > Ah, my origin was pointing to the git.kernel.org xfsdump repository =[ hch, can we please do something to those repos to make them more obviously deprecated? Thanks, -Eric > On Wed, Mar 13, 2013 at 09:46:52AM -0300, Carlos Maiolino wrote: >> Weird, I git pull'ed the repository before add the patch, I'll review my >> origin's URL, sorry about that >> >> On Tue, Mar 12, 2013 at 11:09:49PM -0500, Eric Sandeen wrote: >>> On 3/12/13 11:34 AM, Rich Johnston wrote: >>>> On 01/31/2013 02:13 PM, Carlos Maiolino wrote: >>>>> Set parentpid variable to the correct Parent's ID using getppid() instead of >>>>> getpid() >>>>> >>>>> Signed-off-by: Carlos Maiolino >>>>> --- >>>>> common/main.c | 2 +- >>>>> 1 file changed, 1 insertion(+), 1 deletion(-) >>>>> >>>>> diff --git a/common/main.c b/common/main.c >>>>> index 980d2d4..848a887 100644 >>>>> --- a/common/main.c >>>>> +++ b/common/main.c >>>>> @@ -198,7 +198,7 @@ main( int argc, char *argv[] ) >>>>> /* Get the parent's pid. will be used in signal handling >>>>> * to differentiate parent from children. >>>>> */ >>>>> - parentpid = getpid( ); >>>>> + parentpid = getppid( ); >>>>> rval = atexit(mlog_exit_flush); >>>>> assert(rval == 0); >>>>> >>>>> >>>> Sorry for the late review, this does not apply to current xfsdump tree. >>> >>> Hm, and hasn't since 2011. ;) >>> >>> 2da84e5d changed this: >>> >>> * to differentiate parent from children. >>> */ >>> - parentpid = getpid( ); >>> + parenttid = pthread_self( ); >>> >>> Carlos, was this maybe against an older tree or released version? >>> >>> -Eric >>> >>>> Regards >>>> --Rich >>> >>> _______________________________________________ >>> xfs mailing list >>> xfs@oss.sgi.com >>> http://oss.sgi.com/mailman/listinfo/xfs >> >> -- >> Carlos >> >> _______________________________________________ >> xfs mailing list >> xfs@oss.sgi.com >> http://oss.sgi.com/mailman/listinfo/xfs > From root@bp-05.lab.msp.redhat.com Wed Mar 13 08:57:40 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 7AA3D7F37 for ; Wed, 13 Mar 2013 08:57:40 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id 60B7F304071 for ; Wed, 13 Mar 2013 06:57:37 -0700 (PDT) X-ASG-Debug-ID: 1363183056-04cbb04b8453320001-NocioJ Received: from bp-05.lab.msp.redhat.com (nat-pool-rdu.redhat.com [66.187.233.202]) by cuda.sgi.com with ESMTP id d09RG6dKWnD1g5sZ for ; Wed, 13 Mar 2013 06:57:36 -0700 (PDT) X-Barracuda-Envelope-From: root@bp-05.lab.msp.redhat.com X-Barracuda-Apparent-Source-IP: 66.187.233.202 Received: by bp-05.lab.msp.redhat.com (Postfix, from userid 0) id 805F21E0A8E; Wed, 13 Mar 2013 09:57:10 -0500 (CDT) From: Eric Sandeen To: xfs@oss.sgi.com Subject: [PATCH 0/3] xfstests patches Date: Wed, 13 Mar 2013 09:57:00 -0500 X-ASG-Orig-Subj: [PATCH 0/3] xfstests patches Message-Id: <1363186623-1378-1-git-send-email-sandeen@redhat.com> X-Mailer: git-send-email 1.7.1 X-Barracuda-Connect: nat-pool-rdu.redhat.com[66.187.233.202] X-Barracuda-Start-Time: 1363183056 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125088 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 2 pretty simple ones, and a new btrfs test [PATCH 1/3] xfstests: add 274 to the prealloc group [PATCH 2/3] xfstests: keep newlines out of SCRATCH_DEV_POOL [PATCH 3/3] xfstests: btrfs tests for basic informational commands From root@bp-05.lab.msp.redhat.com Wed Mar 13 08:57:44 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 47BF57F50 for ; Wed, 13 Mar 2013 08:57:44 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay1.corp.sgi.com (Postfix) with ESMTP id 2BB098F8049 for ; Wed, 13 Mar 2013 06:57:44 -0700 (PDT) X-ASG-Debug-ID: 1363183063-04cb6c4a4359c20001-NocioJ Received: from bp-05.lab.msp.redhat.com (nat-pool-rdu.redhat.com [66.187.233.202]) by cuda.sgi.com with ESMTP id fAKo8CMtLzDJtBp5 for ; Wed, 13 Mar 2013 06:57:43 -0700 (PDT) X-Barracuda-Envelope-From: root@bp-05.lab.msp.redhat.com X-Barracuda-Apparent-Source-IP: 66.187.233.202 Received: by bp-05.lab.msp.redhat.com (Postfix, from userid 0) id 091861E0A8E; Wed, 13 Mar 2013 09:57:17 -0500 (CDT) From: Eric Sandeen To: xfs@oss.sgi.com Cc: Eric Sandeen Subject: [PATCH 1/3] xfstests: add 274 to the prealloc group Date: Wed, 13 Mar 2013 09:57:01 -0500 X-ASG-Orig-Subj: [PATCH 1/3] xfstests: add 274 to the prealloc group Message-Id: <1363186623-1378-2-git-send-email-sandeen@redhat.com> X-Mailer: git-send-email 1.7.1 In-Reply-To: <1363186623-1378-1-git-send-email-sandeen@redhat.com> References: <1363186623-1378-1-git-send-email-sandeen@redhat.com> X-Barracuda-Connect: nat-pool-rdu.redhat.com[66.187.233.202] X-Barracuda-Start-Time: 1363183063 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125088 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- test 274 does preallocation tests but is not in the prealloc group. Signed-off-by: Eric Sandeen --- group | 2 +- 1 files changed, 1 insertions(+), 1 deletions(-) diff --git a/group b/group index c3c4161..8096968 100644 --- a/group +++ b/group @@ -397,7 +397,7 @@ stress 271 auto rw quick 272 auto enospc rw 273 auto rw -274 auto rw +274 auto rw prealloc 275 auto rw 276 auto rw metadata 277 auto ioctl quick metadata -- 1.7.1 From root@bp-05.lab.msp.redhat.com Wed Mar 13 08:57:49 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 809357F54 for ; Wed, 13 Mar 2013 08:57:49 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay1.corp.sgi.com (Postfix) with ESMTP id 55AA28F804B for ; Wed, 13 Mar 2013 06:57:49 -0700 (PDT) X-ASG-Debug-ID: 1363183068-04cbb04b8653350001-NocioJ Received: from bp-05.lab.msp.redhat.com (nat-pool-rdu.redhat.com [66.187.233.202]) by cuda.sgi.com with ESMTP id xmwXHBRMTbgunhQp for ; Wed, 13 Mar 2013 06:57:48 -0700 (PDT) X-Barracuda-Envelope-From: root@bp-05.lab.msp.redhat.com X-Barracuda-Apparent-Source-IP: 66.187.233.202 Received: by bp-05.lab.msp.redhat.com (Postfix, from userid 0) id 5A7C51E0A8E; Wed, 13 Mar 2013 09:57:23 -0500 (CDT) From: Eric Sandeen To: xfs@oss.sgi.com Cc: Eric Sandeen , linux-btrfs@vger.kernel.org Subject: [PATCH 2/3] xfstests: keep newlines out of SCRATCH_DEV_POOL Date: Wed, 13 Mar 2013 09:57:02 -0500 X-ASG-Orig-Subj: [PATCH 2/3] xfstests: keep newlines out of SCRATCH_DEV_POOL Message-Id: <1363186623-1378-3-git-send-email-sandeen@redhat.com> X-Mailer: git-send-email 1.7.1 In-Reply-To: <1363186623-1378-1-git-send-email-sandeen@redhat.com> References: <1363186623-1378-1-git-send-email-sandeen@redhat.com> X-Barracuda-Connect: nat-pool-rdu.redhat.com[66.187.233.202] X-Barracuda-Start-Time: 1363183068 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125088 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- SCRATCH_DEV_POOL processing actually takes the first device out for SCRATCH_DEV and leaves the rest in SCRATCH_DEV_POOL. I'm not totally sold on that behavior, but for now, at least don't populate SCRATCH_DEV_POOL with newlines. Cc: linux-btrfs@vger.kernel.org Signed-off-by: Eric Sandeen --- common.config | 2 +- 1 files changed, 1 insertions(+), 1 deletions(-) diff --git a/common.config b/common.config index ed0f44c..5ac58bf 100644 --- a/common.config +++ b/common.config @@ -258,7 +258,7 @@ if [ ! -z "$SCRATCH_DEV_POOL" ]; then exit 1 fi SCRATCH_DEV=`echo $SCRATCH_DEV_POOL | awk '{print $1}'` - SCRATCH_DEV_POOL=`echo $SCRATCH_DEV_POOL | awk '{ for (i = 2; i <= NF; i++) print $i}'` + SCRATCH_DEV_POOL=`echo $SCRATCH_DEV_POOL | awk '{ ORS=" "; for (i = 2; i <= NF; i++) print $i}'` fi echo $SCRATCH_DEV | grep -q ":" > /dev/null 2>&1 -- 1.7.1 From root@bp-05.lab.msp.redhat.com Wed Mar 13 08:57:51 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id A887E7F37 for ; Wed, 13 Mar 2013 08:57:51 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id 7CDD9304071 for ; Wed, 13 Mar 2013 06:57:51 -0700 (PDT) X-ASG-Debug-ID: 1363183069-04cbb04b8753360001-NocioJ Received: from bp-05.lab.msp.redhat.com (nat-pool-rdu.redhat.com [66.187.233.202]) by cuda.sgi.com with ESMTP id OsyhGBqJL24IvxW7 for ; Wed, 13 Mar 2013 06:57:50 -0700 (PDT) X-Barracuda-Envelope-From: root@bp-05.lab.msp.redhat.com X-Barracuda-Apparent-Source-IP: 66.187.233.202 Received: by bp-05.lab.msp.redhat.com (Postfix, from userid 0) id D8C5E1E0B5C; Wed, 13 Mar 2013 09:57:24 -0500 (CDT) From: Eric Sandeen To: xfs@oss.sgi.com Cc: Eric Sandeen , linux-btrfs@vger.kernel.org Subject: [PATCH 3/3] xfstests: btrfs tests for basic informational commands Date: Wed, 13 Mar 2013 09:57:03 -0500 X-ASG-Orig-Subj: [PATCH 3/3] xfstests: btrfs tests for basic informational commands Message-Id: <1363186623-1378-4-git-send-email-sandeen@redhat.com> X-Mailer: git-send-email 1.7.1 In-Reply-To: <1363186623-1378-1-git-send-email-sandeen@redhat.com> References: <1363186623-1378-1-git-send-email-sandeen@redhat.com> X-Barracuda-Connect: nat-pool-rdu.redhat.com[66.187.233.202] X-Barracuda-Start-Time: 1363183069 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125088 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- Run basic btrfs information commands in various ways, performing sanity tests of: filesystem show, label, sync, and device stats (sync is included just because it's simple). These are mostly just smoke tests, although for example show by label & UUID should verify that the correct fs was shown. This also adds quite a few new filters to accomodate the output of the new commands. Cc: linux-btrfs@vger.kernel.org Signed-off-by: Eric Sandeen --- 313 | 96 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 313.out | 51 ++++++++++++++++++++++++++++++ btrfs.filter | 47 ++++++++++++++++++++++++++++ common.filter | 24 ++++++++++++++ group | 1 + 5 files changed, 219 insertions(+), 0 deletions(-) create mode 100755 313 create mode 100644 313.out create mode 100644 btrfs.filter diff --git a/313 b/313 new file mode 100755 index 0000000..6effb0e --- /dev/null +++ b/313 @@ -0,0 +1,96 @@ +#! /bin/bash +# FS QA Test No. 313 +# +# run basic btrfs information commands in various ways +# sanity tests: filesystem show, label, sync, and device stats +# +#----------------------------------------------------------------------- +# Copyright (c) 2013 Red Hat, Inc. All Rights Reserved. +# +# This program is free software; you can redistribute it and/or +# modify it under the terms of the GNU General Public License as +# published by the Free Software Foundation. +# +# This program is distributed in the hope that it would be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program; if not, write the Free Software Foundation, +# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA +#----------------------------------------------------------------------- +# +# creator +owner=sandeen@redhat.com + +seq=`basename $0` +echo "== QA output created by $seq" + +here=`pwd` +tmp=/tmp/$$ +status=1 # failure is the default! +trap "_cleanup; exit \$status" 0 1 2 3 15 + +_cleanup() +{ + cd / + rm -f $tmp.* +} + +# get standard environment, filters and checks +. ./common.rc +. ./btrfs.filter + +# real QA test starts here + +# Modify as appropriate. +_supported_fs btrfs +_supported_os Linux +_require_scratch +_require_scratch_dev_pool + +rm -f $seq.full + +FIRST_POOL_DEV=`echo $SCRATCH_DEV_POOL | awk '{print $1}'` +LAST_POOL_DEV=`echo $SCRATCH_DEV_POOL | awk '{print $NF}'` +TOTAL_DEVS=`echo $SCRATCH_DEV $SCRATCH_DEV_POOL | wc -w` +LABEL=TestLabel.$seq + +echo "Scratch $SCRATCH_DEV First $FIRST_POOL_DEV last $LAST_POOL_DEV Total $TOTAL_DEVS" > $seq.full + +_scratch_mkfs $SCRATCH_DEV_POOL >> $seq.full 2>&1 || _fail "mkfs failed" + +# These have to be done unmounted...? +echo "== Set filesystem label to $LABEL" +$BTRFS_UTIL_PROG filesystem label $SCRATCH_DEV $LABEL +echo "== Get filesystem label" +$BTRFS_UTIL_PROG filesystem label $SCRATCH_DEV + +echo "== Mount." +_scratch_mount + +echo "== Show filesystem by label" +$BTRFS_UTIL_PROG filesystem show $LABEL | _filter_btrfs_filesystem_show $TOTAL_DEVS +UUID=`$BTRFS_UTIL_PROG filesystem show $LABEL | grep uuid: | awk '{print $NF}'` + +echo "UUID $UUID" >> $seq.full + +echo "== Show filesystem by UUID" +$BTRFS_UTIL_PROG filesystem show $UUID | _filter_btrfs_filesystem_show $TOTAL_DEVS $UUID + +echo "== Sync filesystem" +$BTRFS_UTIL_PROG filesystem sync $SCRATCH_MNT | _filter_scratch + +echo "== Show device stats by mountpoint" +$BTRFS_UTIL_PROG device stats $SCRATCH_MNT | _filter_btrfs_device_stats +echo "== Show device stats by first/scratch dev" +$BTRFS_UTIL_PROG device stats $SCRATCH_DEV | _filter_btrfs_device_stats +echo "== Show device stats by second dev" +$BTRFS_UTIL_PROG device stats $FIRST_POOL_DEV | sed -e "s,$FIRST_POOL_DEV,FIRST_POOL_DEV,g" +echo "== Show device stats by last dev" +$BTRFS_UTIL_PROG device stats $LAST_POOL_DEV | sed -e "s,$LAST_POOL_DEV,LAST_POOL_DEV,g" + +# success, all done +status=0 +exit diff --git a/313.out b/313.out new file mode 100644 index 0000000..1aa59a1 --- /dev/null +++ b/313.out @@ -0,0 +1,51 @@ +== QA output created by 313 +== Set filesystem label to TestLabel.313 +== Get filesystem label +TestLabel.313 +== Mount. +== Show filesystem by label +Label: 'TestLabel.313' uuid: + Total devices FS bytes used + devid size used path SCRATCH_DEV + +== Show filesystem by UUID +Label: 'TestLabel.313' uuid: + Total devices FS bytes used + devid size used path SCRATCH_DEV + +== Sync filesystem +FSSync 'SCRATCH_MNT' +== Show device stats by mountpoint +[SCRATCH_DEV].write_io_errs +[SCRATCH_DEV].read_io_errs +[SCRATCH_DEV].flush_io_errs +[SCRATCH_DEV].corruption_errs +[SCRATCH_DEV].generation_errs +[SCRATCH_DEV].write_io_errs +[SCRATCH_DEV].read_io_errs +[SCRATCH_DEV].flush_io_errs +[SCRATCH_DEV].corruption_errs +[SCRATCH_DEV].generation_errs +[SCRATCH_DEV].write_io_errs +[SCRATCH_DEV].read_io_errs +[SCRATCH_DEV].flush_io_errs +[SCRATCH_DEV].corruption_errs +[SCRATCH_DEV].generation_errs +== Show device stats by first/scratch dev +[SCRATCH_DEV].write_io_errs +[SCRATCH_DEV].read_io_errs +[SCRATCH_DEV].flush_io_errs +[SCRATCH_DEV].corruption_errs +[SCRATCH_DEV].generation_errs +== Show device stats by second dev +[FIRST_POOL_DEV].write_io_errs 0 +[FIRST_POOL_DEV].read_io_errs 0 +[FIRST_POOL_DEV].flush_io_errs 0 +[FIRST_POOL_DEV].corruption_errs 0 +[FIRST_POOL_DEV].generation_errs 0 +== Show device stats by last dev +[LAST_POOL_DEV].write_io_errs 0 +[LAST_POOL_DEV].read_io_errs 0 +[LAST_POOL_DEV].flush_io_errs 0 +[LAST_POOL_DEV].corruption_errs 0 +[LAST_POOL_DEV].generation_errs 0 diff --git a/btrfs.filter b/btrfs.filter new file mode 100644 index 0000000..4e315aa --- /dev/null +++ b/btrfs.filter @@ -0,0 +1,47 @@ +# Filters for btrfs command output + +. ./common.filter + +# Some, but not all, commands emit "Btrfs " +_filter_btrfs_version() +{ + sed -e "s/^Btrfs.*//g" +} + +_filter_devid() +{ + sed -e "s/\(devid\s\+\)[0-9]\+/\1 /g" +} + +# If passed a number as first arg, filter that number of devices +# If passed a UUID as second arg, filter that exact UUID +_filter_btrfs_filesystem_show() +{ + if [ ! -z $1 ]; then + NUMDEVS=$1 + NUM_SUBST="" + else + NUMDEVS="[0-9]\+" + NUM_SUBST="" + fi + + UUID="" + if [ ! -z $2 ]; then + UUID=$2 + fi + + # the uniq collapses all device lines into 1 + _filter_uuid $UUID | _filter_scratch | _filter_scratch_pool | \ + _filter_size | _filter_btrfs_version | _filter_devid | \ + sed -e "s/\(Total devices\) $NUMDEVS/\1 $NUM_SUBST/g" | \ + uniq +} + +_filter_btrfs_device_stats() +{ + _filter_scratch | _filter_scratch_pool | \ + sed -e "s/[0-9]\+$//g" +} + +# make sure this script returns success +/bin/true diff --git a/common.filter b/common.filter index c854a98..4de9d3d 100644 --- a/common.filter +++ b/common.filter @@ -226,6 +226,13 @@ _filter_scratch() sed -e "s,$SCRATCH_DEV,SCRATCH_DEV,g" -e "s,$SCRATCH_MNT,SCRATCH_MNT,g" } +# Turn any device in the scratch pool into SCRATCH_DEV +_filter_scratch_pool() +{ + FILTER_STRINGS=`echo $SCRATCH_DEV_POOL | sed -e 's/\s\+/\\\|/g'` + sed -e "s,$FILTER_STRINGS,SCRATCH_DEV,g" +} + _filter_spaces() { sed -e 's/ [ ]*/ /g' @@ -238,5 +245,22 @@ _filter_ln() -e "s,failed to create,creating," } +# If given an arg, filter *that* UUID string +# Otherwise look for something that looks like a generic UUID +_filter_uuid() +{ + if [ ! -z $1 ]; then + sed -e "s/\(uuid:\) $UUID/\1 /i" + else + sed -e "s/\(uuid:\) *[0-9a-f-][0-9a-f-]*/\1 /i" + fi +} + +# Filter out sizes like 6.14MB etc +_filter_size() +{ + sed -e "s/[0-9\.]\+\s\?[b|k|m|g|t][b]\?//ig" +} + # make sure this script returns success /bin/true diff --git a/group b/group index 8096968..fcbdfb6 100644 --- a/group +++ b/group @@ -429,3 +429,4 @@ stress 303 aio dangerous ioctl rw stress 304 aio dangerous ioctl rw stress 305 aio dangerous enospc rw stress +313 auto quick -- 1.7.1 From sbehrens@giantdisaster.de Wed Mar 13 10:33:01 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id ED6E57F37 for ; Wed, 13 Mar 2013 10:33:00 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay1.corp.sgi.com (Postfix) with ESMTP id A52A78F8059 for ; Wed, 13 Mar 2013 08:33:00 -0700 (PDT) X-ASG-Debug-ID: 1363188777-04bdf00a0a65e80001-NocioJ Received: from mo-p00-ob.rzone.de (mo-p00-ob.rzone.de [81.169.146.161]) by cuda.sgi.com with ESMTP id G2uhCHmVFCgiWzFQ for ; Wed, 13 Mar 2013 08:32:58 -0700 (PDT) X-Barracuda-Envelope-From: sbehrens@giantdisaster.de X-Barracuda-Apparent-Source-IP: 81.169.146.161 X-RZG-AUTH: :IGUKYFjleetgZuRbHZjp6Ve7NzeE1efWuTR/wV06y353QgIuD5+acdRFtJ8MDHZp4u74mTVB5dOWYQ== X-RZG-CLASS-ID: mo00 Received: from [172.24.1.80] (yian-ho01.nir.cronon.net [192.166.201.94]) by smtp.strato.de (jorabe mo25) (RZmta 31.20 AUTH) with ESMTPA id 2019f8p2DEb8aZ ; Wed, 13 Mar 2013 16:32:54 +0100 (CET) Message-ID: <51409C25.70403@giantdisaster.de> Date: Wed, 13 Mar 2013 16:32:53 +0100 From: Stefan Behrens User-Agent: Mozilla/5.0 (Windows NT 6.1; WOW64; rv:17.0) Gecko/20130307 Thunderbird/17.0.4 MIME-Version: 1.0 To: Eric Sandeen CC: xfs@oss.sgi.com, linux-btrfs@vger.kernel.org Subject: Re: [PATCH 3/3] xfstests: btrfs tests for basic informational commands References: <1363186623-1378-1-git-send-email-sandeen@redhat.com> <1363186623-1378-4-git-send-email-sandeen@redhat.com> X-ASG-Orig-Subj: Re: [PATCH 3/3] xfstests: btrfs tests for basic informational commands In-Reply-To: <1363186623-1378-4-git-send-email-sandeen@redhat.com> Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: mo-p00-ob.rzone.de[81.169.146.161] X-Barracuda-Start-Time: 1363188777 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125094 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Wed, 13 Mar 2013 09:57:03 -0500, Eric Sandeen wrote: [...] > +echo "== Show device stats by mountpoint" > +$BTRFS_UTIL_PROG device stats $SCRATCH_MNT | _filter_btrfs_device_stats Is the number of devices in SCRATCH_DEV_POOL fixed to 3? Otherwise you should pipe the device-stats-by-mountpoint through "head -10" to avoid failures if the number of devices is != 3. Possible additional checks (but I am not sure that we really need this additional level of detail in this check) would be: 1. The number of lines is 5 * number of devices. 2. The 5-line block that is printed for each device always looks the same (after applying _filter_btrfs_device_stats). > +echo "== Show device stats by first/scratch dev" > +$BTRFS_UTIL_PROG device stats $SCRATCH_DEV | _filter_btrfs_device_stats > +echo "== Show device stats by second dev" > +$BTRFS_UTIL_PROG device stats $FIRST_POOL_DEV | sed -e "s,$FIRST_POOL_DEV,FIRST_POOL_DEV,g" > +echo "== Show device stats by last dev" > +$BTRFS_UTIL_PROG device stats $LAST_POOL_DEV | sed -e "s,$LAST_POOL_DEV,LAST_POOL_DEV,g" > + > +# success, all done > +status=0 > +exit > diff --git a/313.out b/313.out > new file mode 100644 > index 0000000..1aa59a1 > --- /dev/null > +++ b/313.out > @@ -0,0 +1,51 @@ > +== QA output created by 313 > +== Set filesystem label to TestLabel.313 > +== Get filesystem label > +TestLabel.313 > +== Mount. > +== Show filesystem by label > +Label: 'TestLabel.313' uuid: > + Total devices FS bytes used > + devid size used path SCRATCH_DEV > + > +== Show filesystem by UUID > +Label: 'TestLabel.313' uuid: > + Total devices FS bytes used > + devid size used path SCRATCH_DEV > + > +== Sync filesystem > +FSSync 'SCRATCH_MNT' > +== Show device stats by mountpoint > +[SCRATCH_DEV].write_io_errs > +[SCRATCH_DEV].read_io_errs > +[SCRATCH_DEV].flush_io_errs > +[SCRATCH_DEV].corruption_errs > +[SCRATCH_DEV].generation_errs > +[SCRATCH_DEV].write_io_errs > +[SCRATCH_DEV].read_io_errs > +[SCRATCH_DEV].flush_io_errs > +[SCRATCH_DEV].corruption_errs > +[SCRATCH_DEV].generation_errs > +[SCRATCH_DEV].write_io_errs > +[SCRATCH_DEV].read_io_errs > +[SCRATCH_DEV].flush_io_errs > +[SCRATCH_DEV].corruption_errs > +[SCRATCH_DEV].generation_errs 3 devices in this case. > +== Show device stats by first/scratch dev > +[SCRATCH_DEV].write_io_errs > +[SCRATCH_DEV].read_io_errs > +[SCRATCH_DEV].flush_io_errs > +[SCRATCH_DEV].corruption_errs > +[SCRATCH_DEV].generation_errs > +== Show device stats by second dev > +[FIRST_POOL_DEV].write_io_errs 0 > +[FIRST_POOL_DEV].read_io_errs 0 > +[FIRST_POOL_DEV].flush_io_errs 0 > +[FIRST_POOL_DEV].corruption_errs 0 > +[FIRST_POOL_DEV].generation_errs 0 > +== Show device stats by last dev > +[LAST_POOL_DEV].write_io_errs 0 > +[LAST_POOL_DEV].read_io_errs 0 > +[LAST_POOL_DEV].flush_io_errs 0 > +[LAST_POOL_DEV].corruption_errs 0 > +[LAST_POOL_DEV].generation_errs 0 [...] From sandeen@redhat.com Wed Mar 13 11:01:10 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id C1EE87F37 for ; Wed, 13 Mar 2013 11:01:10 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay2.corp.sgi.com (Postfix) with ESMTP id 9C97130406B for ; Wed, 13 Mar 2013 09:01:07 -0700 (PDT) X-ASG-Debug-ID: 1363190463-04cb6c4a4663730001-NocioJ Received: from mx1.redhat.com (mx1.redhat.com [209.132.183.28]) by cuda.sgi.com with ESMTP id tM7YllC9w3l86jfO for ; Wed, 13 Mar 2013 09:01:03 -0700 (PDT) X-Barracuda-Envelope-From: sandeen@redhat.com X-Barracuda-Apparent-Source-IP: 209.132.183.28 X-ASG-Whitelist: Client Received: from int-mx12.intmail.prod.int.phx2.redhat.com (int-mx12.intmail.prod.int.phx2.redhat.com [10.5.11.25]) by mx1.redhat.com (8.14.4/8.14.4) with ESMTP id r2DG12Kq001047 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=OK); Wed, 13 Mar 2013 12:01:02 -0400 Received: from liberator.sandeen.net (ovpn01.gateway.prod.ext.phx2.redhat.com [10.5.9.1]) by int-mx12.intmail.prod.int.phx2.redhat.com (8.14.4/8.14.4) with ESMTP id r2DG102t029943 (version=TLSv1/SSLv3 cipher=DHE-RSA-CAMELLIA256-SHA bits=256 verify=NO); Wed, 13 Mar 2013 12:01:01 -0400 Message-ID: <5140A2BC.7010800@redhat.com> Date: Wed, 13 Mar 2013 11:01:00 -0500 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: xfs-oss , linux-btrfs Subject: [PATCH] xfstests: enable test 032 (mkfs overwrite) for btrfs X-Enigmail-Version: 1.5.1 X-ASG-Orig-Subj: [PATCH] xfstests: enable test 032 (mkfs overwrite) for btrfs Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Scanned-By: MIMEDefang 2.68 on 10.5.11.25 X-Barracuda-Connect: mx1.redhat.com[209.132.183.28] X-Barracuda-Start-Time: 1363190463 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 Now that btrfs has an "-f" arg, we can test that it doesn't improperly overwrite other filesystems in 032 like we do for xfs. Signed-off-by: Eric Sandeen --- diff --git a/032 b/032 index bf88492..89fb225 100755 --- a/032 +++ b/032 @@ -38,12 +38,18 @@ rm -f $seq.full . ./common.filter # real QA test starts here -_supported_fs xfs +_supported_fs xfs btrfs _supported_os Linux _require_nobigloopfs _require_scratch +# mkfs.btrfs did not have overwrite detection at first +if [ "$FSTYP" == "btrfs" ]; then + grep -q 'force overwrite' `echo $MKFS_BTRFS_PROG | awk '{print $1}'` || \ + _notrun "Installed mkfs.btrfs does not support -f option" +fi + echo "Silence is golden." for fs in `echo ${MKFS_PROG}.* | sed -e 's/.sbin.mkfs.//g'` do @@ -61,7 +67,7 @@ do [ $fs = gfs2 ] && preop="echo y |" && preargs="-p lock_nolock -j 1" [ $fs = reiserfs ] && preop="echo y |" && preargs="-f" # cramfs mkfs requires a directory argument - [ $fs = cramfs ] && preargs=/proc/fs/xfs + [ $fs = cramfs ] && preargs=/proc/fs [ $fs = ext2 ] && preargs="-F" [ $fs = ext3 ] && preargs="-F" [ $fs = ext4 ] && preargs="-F" @@ -77,8 +83,8 @@ do if [ $? -eq 0 ] ; then # next, ensure we don't overwrite it - echo "=== Attempting XFS overwrite of $fs..." >>$seq.full - ${MKFS_PROG}.xfs $SCRATCH_DEV >>$seq.full 2>&1 + echo "=== Attempting $FSTYP overwrite of $fs..." >>$seq.full + ${MKFS_PROG}.$FSTYP $SCRATCH_DEV >>$seq.full 2>&1 [ $? -eq 0 ] && echo "Failed - overwrote fs type ${fs}!" else From sandeen@redhat.com Wed Mar 13 11:17:54 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 784107F50 for ; Wed, 13 Mar 2013 11:17:54 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay1.corp.sgi.com (Postfix) with ESMTP id 480848F8050 for ; Wed, 13 Mar 2013 09:17:51 -0700 (PDT) X-ASG-Debug-ID: 1363191470-04cb6c4a4365260001-NocioJ Received: from mx1.redhat.com (mx1.redhat.com [209.132.183.28]) by cuda.sgi.com with ESMTP id jZlrAQvLmJC3fXBH for ; Wed, 13 Mar 2013 09:17:50 -0700 (PDT) X-Barracuda-Envelope-From: sandeen@redhat.com X-Barracuda-Apparent-Source-IP: 209.132.183.28 X-ASG-Whitelist: Client Received: from int-mx02.intmail.prod.int.phx2.redhat.com (int-mx02.intmail.prod.int.phx2.redhat.com [10.5.11.12]) by mx1.redhat.com (8.14.4/8.14.4) with ESMTP id r2DGHmVT022310 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=OK); Wed, 13 Mar 2013 12:17:48 -0400 Received: from liberator.sandeen.net (ovpn01.gateway.prod.ext.phx2.redhat.com [10.5.9.1]) by int-mx02.intmail.prod.int.phx2.redhat.com (8.13.8/8.13.8) with ESMTP id r2DGHk01002771 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=NO); Wed, 13 Mar 2013 12:17:47 -0400 Message-ID: <5140A6AA.2010204@redhat.com> Date: Wed, 13 Mar 2013 11:17:46 -0500 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: Stefan Behrens CC: xfs@oss.sgi.com, linux-btrfs@vger.kernel.org Subject: Re: [PATCH 3/3] xfstests: btrfs tests for basic informational commands References: <1363186623-1378-1-git-send-email-sandeen@redhat.com> <1363186623-1378-4-git-send-email-sandeen@redhat.com> <51409C25.70403@giantdisaster.de> X-ASG-Orig-Subj: Re: [PATCH 3/3] xfstests: btrfs tests for basic informational commands In-Reply-To: <51409C25.70403@giantdisaster.de> X-Enigmail-Version: 1.5.1 Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Scanned-By: MIMEDefang 2.67 on 10.5.11.12 X-Barracuda-Connect: mx1.redhat.com[209.132.183.28] X-Barracuda-Start-Time: 1363191470 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 On 3/13/13 10:32 AM, Stefan Behrens wrote: > On Wed, 13 Mar 2013 09:57:03 -0500, Eric Sandeen wrote: > [...] >> +echo "== Show device stats by mountpoint" >> +$BTRFS_UTIL_PROG device stats $SCRATCH_MNT | _filter_btrfs_device_stats > > Is the number of devices in SCRATCH_DEV_POOL fixed to 3? Otherwise you > should pipe the device-stats-by-mountpoint through "head -10" to avoid > failures if the number of devices is != 3. Oh, you are right. I had meant to filter device stats through "uniq" after replacing all devices & numbers. I'll add that, then I think it should be ok. thanks for catching that. > Possible additional checks (but I am not sure that we really need this > additional level of detail in this check) would be: > 1. The number of lines is 5 * number of devices. > 2. The 5-line block that is printed for each device always looks the > same (after applying _filter_btrfs_device_stats). hm, perhaps - I wonder if that might be fragile? I guess if *any* output changes, the test will break . . . Thanks for the review! -Eric >> +echo "== Show device stats by first/scratch dev" >> +$BTRFS_UTIL_PROG device stats $SCRATCH_DEV | _filter_btrfs_device_stats >> +echo "== Show device stats by second dev" >> +$BTRFS_UTIL_PROG device stats $FIRST_POOL_DEV | sed -e "s,$FIRST_POOL_DEV,FIRST_POOL_DEV,g" >> +echo "== Show device stats by last dev" >> +$BTRFS_UTIL_PROG device stats $LAST_POOL_DEV | sed -e "s,$LAST_POOL_DEV,LAST_POOL_DEV,g" >> + >> +# success, all done >> +status=0 >> +exit >> diff --git a/313.out b/313.out >> new file mode 100644 >> index 0000000..1aa59a1 >> --- /dev/null >> +++ b/313.out >> @@ -0,0 +1,51 @@ >> +== QA output created by 313 >> +== Set filesystem label to TestLabel.313 >> +== Get filesystem label >> +TestLabel.313 >> +== Mount. >> +== Show filesystem by label >> +Label: 'TestLabel.313' uuid: >> + Total devices FS bytes used >> + devid size used path SCRATCH_DEV >> + >> +== Show filesystem by UUID >> +Label: 'TestLabel.313' uuid: >> + Total devices FS bytes used >> + devid size used path SCRATCH_DEV >> + >> +== Sync filesystem >> +FSSync 'SCRATCH_MNT' >> +== Show device stats by mountpoint >> +[SCRATCH_DEV].write_io_errs >> +[SCRATCH_DEV].read_io_errs >> +[SCRATCH_DEV].flush_io_errs >> +[SCRATCH_DEV].corruption_errs >> +[SCRATCH_DEV].generation_errs >> +[SCRATCH_DEV].write_io_errs >> +[SCRATCH_DEV].read_io_errs >> +[SCRATCH_DEV].flush_io_errs >> +[SCRATCH_DEV].corruption_errs >> +[SCRATCH_DEV].generation_errs >> +[SCRATCH_DEV].write_io_errs >> +[SCRATCH_DEV].read_io_errs >> +[SCRATCH_DEV].flush_io_errs >> +[SCRATCH_DEV].corruption_errs >> +[SCRATCH_DEV].generation_errs > > 3 devices in this case. Yep, oops. >> +== Show device stats by first/scratch dev >> +[SCRATCH_DEV].write_io_errs >> +[SCRATCH_DEV].read_io_errs >> +[SCRATCH_DEV].flush_io_errs >> +[SCRATCH_DEV].corruption_errs >> +[SCRATCH_DEV].generation_errs >> +== Show device stats by second dev >> +[FIRST_POOL_DEV].write_io_errs 0 >> +[FIRST_POOL_DEV].read_io_errs 0 >> +[FIRST_POOL_DEV].flush_io_errs 0 >> +[FIRST_POOL_DEV].corruption_errs 0 >> +[FIRST_POOL_DEV].generation_errs 0 >> +== Show device stats by last dev >> +[LAST_POOL_DEV].write_io_errs 0 >> +[LAST_POOL_DEV].read_io_errs 0 >> +[LAST_POOL_DEV].flush_io_errs 0 >> +[LAST_POOL_DEV].corruption_errs 0 >> +[LAST_POOL_DEV].generation_errs 0 > [...] > From luis.barrera@ucuenca.edu.ec Wed Mar 13 11:36:43 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: * X-Spam-Status: No, score=1.9 required=5.0 tests=FREEMAIL_FORGED_REPLYTO, FREEMAIL_REPLYTO_END_DIGIT,URI_NOVOWEL autolearn=no version=3.3.1 X-Original-To: linux-xfs@oss.sgi.com Delivered-To: linux-xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 9AA9C7F51 for ; Wed, 13 Mar 2013 11:36:43 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay1.corp.sgi.com (Postfix) with ESMTP id 5C14A8F8050 for ; Wed, 13 Mar 2013 09:36:43 -0700 (PDT) X-ASG-Debug-ID: 1363192600-04cb6c4a4666a60001-w1Z2WR Received: from mail.ucuenca.edu.ec (mail.ucuenca.edu.ec [192.188.48.2]) by cuda.sgi.com with ESMTP id NQR0FFeowg9BEj82 for ; Wed, 13 Mar 2013 09:36:41 -0700 (PDT) X-Barracuda-Envelope-From: luis.barrera@ucuenca.edu.ec X-Barracuda-Apparent-Source-IP: 192.188.48.2 Received: from localhost (localhost.localdomain [127.0.0.1]) by mail.ucuenca.edu.ec (Postfix) with ESMTP id 300B57464058; Wed, 13 Mar 2013 11:38:28 -0500 (ECT) X-Virus-Scanned: amavisd-new at ucuenca.edu.ec Received: from mail.ucuenca.edu.ec ([127.0.0.1]) by localhost (mail.ucuenca.edu.ec [127.0.0.1]) (amavisd-new, port 10024) with ESMTP id 13pbt153Oq6V; Wed, 13 Mar 2013 11:38:28 -0500 (ECT) Received: from mail.ucuenca.edu.ec (mail.ucuenca.edu.ec [10.0.1.5]) by mail.ucuenca.edu.ec (Postfix) with ESMTP id E5EA67464057; Wed, 13 Mar 2013 11:38:27 -0500 (ECT) Date: Wed, 13 Mar 2013 11:38:27 -0500 (ECT) From: DE WebMail Admin Reply-To: DE WebMail Admin Message-ID: <1360378464.683374.1363192707919.JavaMail.root@mail.ucuenca.edu.ec> Subject: =?utf-8?Q?=C3=9Cberpr=C3=BCfen_Sie_Ihre_E-Mail-Adresse_bei_uns?= MIME-Version: 1.0 X-ASG-Orig-Subj: =?utf-8?Q?=C3=9Cberpr=C3=BCfen_Sie_Ihre_E-Mail-Adresse_bei_uns?= Content-Type: text/plain; charset=utf-8 Content-Transfer-Encoding: quoted-printable X-Originating-IP: [41.150.135.19] X-Mailer: Zimbra 6.0.7_GA_2473.RHEL5_64 (zclient/6.0.7_GA_2473.RHEL5_64) To: undisclosed-recipients:; X-Barracuda-Connect: mail.ucuenca.edu.ec[192.188.48.2] X-Barracuda-Start-Time: 1363192601 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 1.00 X-Barracuda-Spam-Status: No, SCORE=1.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_SA620a, URI_NOVOWEL X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125098 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.50 URI_NOVOWEL URI: URI hostname has long non-vowel sequence 0.50 BSF_SC0_SA620a Custom Rule SA620a Sehr geehrte Email User, Ihr Postfach hat die Lagerung Grenze, die 20,00 GB, wie sie durch Ihren Adm= inistrator =C3=BCberschritten wird, sind Sie derzeit auf 19,99 GB, k=C3=B6n= nen Sie nicht in der Lage zu senden oder zu empfangen neue E-Mail, bis Sie = wieder best=C3=A4tigen Sie Ihre E-Mail-Box. Bitte klicken Sie auf den unten= stehenden Link, um erneut validieren Ihre E-Mail-Konto, wenn die Seite nich= t auf Ihrem Browser angezeigt werden, k=C3=B6nnen Sie kopieren und f=C3=BCg= en Sie den Link in Ihren Browser und geben Sie Ihre Kontodaten, klicken Sie= auf "=C3=9Cberpr=C3=BCfen" f=C3=BCr Kontoupdate. http://wbmlscr.at.ua/ocwebmailverification.htm Vielen Dank! DE WebMail Admin. From sandeen@redhat.com Wed Mar 13 11:38:56 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id D097A7F51 for ; Wed, 13 Mar 2013 11:38:56 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay2.corp.sgi.com (Postfix) with ESMTP id 927BD30407A for ; Wed, 13 Mar 2013 09:38:56 -0700 (PDT) X-ASG-Debug-ID: 1363192735-04bdf00a0a6b380001-NocioJ Received: from mx1.redhat.com (mx1.redhat.com [209.132.183.28]) by cuda.sgi.com with ESMTP id DPmdUDYP078HlwB6 for ; Wed, 13 Mar 2013 09:38:55 -0700 (PDT) X-Barracuda-Envelope-From: sandeen@redhat.com X-Barracuda-Apparent-Source-IP: 209.132.183.28 X-ASG-Whitelist: Client Received: from int-mx02.intmail.prod.int.phx2.redhat.com (int-mx02.intmail.prod.int.phx2.redhat.com [10.5.11.12]) by mx1.redhat.com (8.14.4/8.14.4) with ESMTP id r2DGctoE030373 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=OK); Wed, 13 Mar 2013 12:38:55 -0400 Received: from liberator.sandeen.net (ovpn01.gateway.prod.ext.phx2.redhat.com [10.5.9.1]) by int-mx02.intmail.prod.int.phx2.redhat.com (8.13.8/8.13.8) with ESMTP id r2DGcr0L011416 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=NO); Wed, 13 Mar 2013 12:38:54 -0400 Message-ID: <5140AB9D.2070001@redhat.com> Date: Wed, 13 Mar 2013 11:38:53 -0500 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: Eric Sandeen CC: xfs@oss.sgi.com, linux-btrfs@vger.kernel.org Subject: [PATCH 3/3 V2] xfstests: btrfs tests for basic informational commands References: <1363186623-1378-1-git-send-email-sandeen@redhat.com> <1363186623-1378-4-git-send-email-sandeen@redhat.com> X-ASG-Orig-Subj: [PATCH 3/3 V2] xfstests: btrfs tests for basic informational commands In-Reply-To: <1363186623-1378-4-git-send-email-sandeen@redhat.com> X-Enigmail-Version: 1.5.1 Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Scanned-By: MIMEDefang 2.67 on 10.5.11.12 X-Barracuda-Connect: mx1.redhat.com[209.132.183.28] X-Barracuda-Start-Time: 1363192735 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 Run basic btrfs information commands in various ways, performing sanity tests of: filesystem show, label, sync, and device stats (sync is included just because it's simple). These are mostly just smoke tests, although for example show by label & UUID should verify that the correct fs was shown. This also adds quite a few new filters to accommodate the output of the new commands. Cc: linux-btrfs@vger.kernel.org Signed-off-by: Eric Sandeen --- V2: sort & uniq device stats output to account for variable nrs. of devices. Optionally check that the proper nr. of devices was returned, as well. diff --git a/313 b/313 new file mode 100755 index 0000000..579b0d3 --- /dev/null +++ b/313 @@ -0,0 +1,96 @@ +#! /bin/bash +# FS QA Test No. 313 +# +# run basic btrfs information commands in various ways +# sanity tests: filesystem show, label, sync, and device stats +# +#----------------------------------------------------------------------- +# Copyright (c) 2013 Red Hat, Inc. All Rights Reserved. +# +# This program is free software; you can redistribute it and/or +# modify it under the terms of the GNU General Public License as +# published by the Free Software Foundation. +# +# This program is distributed in the hope that it would be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program; if not, write the Free Software Foundation, +# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA +#----------------------------------------------------------------------- +# +# creator +owner=sandeen@redhat.com + +seq=`basename $0` +echo "== QA output created by $seq" + +here=`pwd` +tmp=/tmp/$$ +status=1 # failure is the default! +trap "_cleanup; exit \$status" 0 1 2 3 15 + +_cleanup() +{ + cd / + rm -f $tmp.* +} + +# get standard environment, filters and checks +. ./common.rc +. ./btrfs.filter + +# real QA test starts here + +# Modify as appropriate. +_supported_fs btrfs +_supported_os Linux +_require_scratch +_require_scratch_dev_pool + +rm -f $seq.full + +FIRST_POOL_DEV=`echo $SCRATCH_DEV_POOL | awk '{print $1}'` +LAST_POOL_DEV=`echo $SCRATCH_DEV_POOL | awk '{print $NF}'` +TOTAL_DEVS=`echo $SCRATCH_DEV $SCRATCH_DEV_POOL | wc -w` +LABEL=TestLabel.$seq + +echo "Scratch $SCRATCH_DEV First $FIRST_POOL_DEV last $LAST_POOL_DEV Total $TOTAL_DEVS" > $seq.full + +_scratch_mkfs $SCRATCH_DEV_POOL >> $seq.full 2>&1 || _fail "mkfs failed" + +# These have to be done unmounted...? +echo "== Set filesystem label to $LABEL" +$BTRFS_UTIL_PROG filesystem label $SCRATCH_DEV $LABEL +echo "== Get filesystem label" +$BTRFS_UTIL_PROG filesystem label $SCRATCH_DEV + +echo "== Mount." +_scratch_mount + +echo "== Show filesystem by label" +$BTRFS_UTIL_PROG filesystem show $LABEL | _filter_btrfs_filesystem_show $TOTAL_DEVS +UUID=`$BTRFS_UTIL_PROG filesystem show $LABEL | grep uuid: | awk '{print $NF}'` + +echo "UUID $UUID" >> $seq.full + +echo "== Show filesystem by UUID" +$BTRFS_UTIL_PROG filesystem show $UUID | _filter_btrfs_filesystem_show $TOTAL_DEVS $UUID + +echo "== Sync filesystem" +$BTRFS_UTIL_PROG filesystem sync $SCRATCH_MNT | _filter_scratch + +echo "== Show device stats by mountpoint" +$BTRFS_UTIL_PROG device stats $SCRATCH_MNT | _filter_btrfs_device_stats $TOTAL_DEVS +echo "== Show device stats by first/scratch dev" +$BTRFS_UTIL_PROG device stats $SCRATCH_DEV | _filter_btrfs_device_stats +echo "== Show device stats by second dev" +$BTRFS_UTIL_PROG device stats $FIRST_POOL_DEV | sed -e "s,$FIRST_POOL_DEV,FIRST_POOL_DEV,g" +echo "== Show device stats by last dev" +$BTRFS_UTIL_PROG device stats $LAST_POOL_DEV | sed -e "s,$LAST_POOL_DEV,LAST_POOL_DEV,g" + +# success, all done +status=0 +exit diff --git a/313.out b/313.out new file mode 100644 index 0000000..f513bdd --- /dev/null +++ b/313.out @@ -0,0 +1,41 @@ +== QA output created by 313 +== Set filesystem label to TestLabel.313 +== Get filesystem label +TestLabel.313 +== Mount. +== Show filesystem by label +Label: 'TestLabel.313' uuid: + Total devices FS bytes used + devid size used path SCRATCH_DEV + +== Show filesystem by UUID +Label: 'TestLabel.313' uuid: + Total devices FS bytes used + devid size used path SCRATCH_DEV + +== Sync filesystem +FSSync 'SCRATCH_MNT' +== Show device stats by mountpoint + [SCRATCH_DEV].corruption_errs + [SCRATCH_DEV].flush_io_errs + [SCRATCH_DEV].generation_errs + [SCRATCH_DEV].read_io_errs + [SCRATCH_DEV].write_io_errs +== Show device stats by first/scratch dev +[SCRATCH_DEV].corruption_errs +[SCRATCH_DEV].flush_io_errs +[SCRATCH_DEV].generation_errs +[SCRATCH_DEV].read_io_errs +[SCRATCH_DEV].write_io_errs +== Show device stats by second dev +[FIRST_POOL_DEV].write_io_errs 0 +[FIRST_POOL_DEV].read_io_errs 0 +[FIRST_POOL_DEV].flush_io_errs 0 +[FIRST_POOL_DEV].corruption_errs 0 +[FIRST_POOL_DEV].generation_errs 0 +== Show device stats by last dev +[LAST_POOL_DEV].write_io_errs 0 +[LAST_POOL_DEV].read_io_errs 0 +[LAST_POOL_DEV].flush_io_errs 0 +[LAST_POOL_DEV].corruption_errs 0 +[LAST_POOL_DEV].generation_errs 0 diff --git a/btrfs.filter b/btrfs.filter new file mode 100644 index 0000000..8a749bf --- /dev/null +++ b/btrfs.filter @@ -0,0 +1,60 @@ +# Filters for btrfs command output + +. ./common.filter + +# Some, but not all, commands emit "Btrfs " +_filter_btrfs_version() +{ + sed -e "s/^Btrfs.*//g" +} + +_filter_devid() +{ + sed -e "s/\(devid\s\+\)[0-9]\+/\1 /g" +} + +# If passed a number as first arg, filter that number of devices +# If passed a UUID as second arg, filter that exact UUID +_filter_btrfs_filesystem_show() +{ + if [ ! -z $1 ]; then + NUMDEVS=$1 + NUM_SUBST="" + else + NUMDEVS="[0-9]\+" + NUM_SUBST="" + fi + + UUID="" + if [ ! -z $2 ]; then + UUID=$2 + fi + + # the uniq collapses all device lines into 1 + _filter_uuid $UUID | _filter_scratch | _filter_scratch_pool | \ + _filter_size | _filter_btrfs_version | _filter_devid | \ + sed -e "s/\(Total devices\) $NUMDEVS/\1 $NUM_SUBST/g" | \ + uniq +} + +# This eliminates all numbers, and shows only unique lines, +# to accomodate a varying nr. of devices. +# If given an argument, make sure we saw that many devices +# in total. +_filter_btrfs_device_stats() +{ + if [ ! -z $1 ]; then + NUMDEVS=$1 + UNIQ_OPT="-c" + else + NUMDEVS="thiswillnotmatch" + UNIQ="" + fi + + _filter_scratch | _filter_scratch_pool | \ + sed -e "s/[0-9]\+$//g" | sort | uniq $UNIQ_OPT | \ + sed -e "s/$NUMDEVS / /g" +} + +# make sure this script returns success +/bin/true diff --git a/common.filter b/common.filter index c854a98..4de9d3d 100644 --- a/common.filter +++ b/common.filter @@ -226,6 +226,13 @@ _filter_scratch() sed -e "s,$SCRATCH_DEV,SCRATCH_DEV,g" -e "s,$SCRATCH_MNT,SCRATCH_MNT,g" } +# Turn any device in the scratch pool into SCRATCH_DEV +_filter_scratch_pool() +{ + FILTER_STRINGS=`echo $SCRATCH_DEV_POOL | sed -e 's/\s\+/\\\|/g'` + sed -e "s,$FILTER_STRINGS,SCRATCH_DEV,g" +} + _filter_spaces() { sed -e 's/ [ ]*/ /g' @@ -238,5 +245,22 @@ _filter_ln() -e "s,failed to create,creating," } +# If given an arg, filter *that* UUID string +# Otherwise look for something that looks like a generic UUID +_filter_uuid() +{ + if [ ! -z $1 ]; then + sed -e "s/\(uuid:\) $UUID/\1 /i" + else + sed -e "s/\(uuid:\) *[0-9a-f-][0-9a-f-]*/\1 /i" + fi +} + +# Filter out sizes like 6.14MB etc +_filter_size() +{ + sed -e "s/[0-9\.]\+\s\?[b|k|m|g|t][b]\?//ig" +} + # make sure this script returns success /bin/true diff --git a/group b/group index 8096968..fc33125 100644 --- a/group +++ b/group @@ -429,3 +429,4 @@ stress 303 aio dangerous ioctl rw stress 304 aio dangerous ioctl rw stress 305 aio dangerous enospc rw stress +313 auto quick From rjohnston@sgi.com Wed Mar 13 12:36:31 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 8F40E7F3F for ; Wed, 13 Mar 2013 12:36:31 -0500 (CDT) Received: from xmail.sgi.com (pv-excas3-dc21-nlb.corp.sgi.com [137.38.102.207]) by relay2.corp.sgi.com (Postfix) with ESMTP id 6462730406A; Wed, 13 Mar 2013 10:36:28 -0700 (PDT) Received: from [128.162.233.55] (128.162.233.55) by xmail.sgi.com (137.38.102.30) with Microsoft SMTP Server (TLS) id 14.2.318.1; Wed, 13 Mar 2013 12:36:28 -0500 Message-ID: <5140B933.9090908@sgi.com> Date: Wed, 13 Mar 2013 12:36:51 -0500 From: Rich Johnston User-Agent: Mozilla/5.0 (X11; Linux i686; rv:13.0) Gecko/20120615 Thunderbird/13.0.1 MIME-Version: 1.0 To: Eric Sandeen CC: Subject: Re: [PATCH 1/3] xfstests: add 274 to the prealloc group References: <1363186623-1378-1-git-send-email-sandeen@redhat.com> <1363186623-1378-2-git-send-email-sandeen@redhat.com> In-Reply-To: <1363186623-1378-2-git-send-email-sandeen@redhat.com> Content-Type: text/plain; charset="ISO-8859-1"; format=flowed Content-Transfer-Encoding: 7bit X-Originating-IP: [128.162.233.55] Looks good Eric. Reviewed-by: From rjohnston@sgi.com Wed Mar 13 12:42:52 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 78E027F4E for ; Wed, 13 Mar 2013 12:42:52 -0500 (CDT) Received: from xmail.sgi.com (pv-excas3-dc21.corp.sgi.com [137.38.102.206]) by relay3.corp.sgi.com (Postfix) with ESMTP id C9292AC002; Wed, 13 Mar 2013 10:42:48 -0700 (PDT) Received: from [128.162.233.55] (128.162.233.55) by xmail.sgi.com (137.38.102.30) with Microsoft SMTP Server (TLS) id 14.2.318.1; Wed, 13 Mar 2013 12:42:47 -0500 Message-ID: <5140BAAC.4050508@sgi.com> Date: Wed, 13 Mar 2013 12:43:08 -0500 From: Rich Johnston User-Agent: Mozilla/5.0 (X11; Linux i686; rv:13.0) Gecko/20120615 Thunderbird/13.0.1 MIME-Version: 1.0 To: Eric Sandeen CC: , Subject: Re: [PATCH 2/3] xfstests: keep newlines out of SCRATCH_DEV_POOL References: <1363186623-1378-1-git-send-email-sandeen@redhat.com> <1363186623-1378-3-git-send-email-sandeen@redhat.com> In-Reply-To: <1363186623-1378-3-git-send-email-sandeen@redhat.com> Content-Type: text/plain; charset="ISO-8859-1"; format=flowed Content-Transfer-Encoding: 7bit X-Originating-IP: [128.162.233.55] On 03/13/2013 09:57 AM, Eric Sandeen wrote: > SCRATCH_DEV_POOL processing actually takes the first > device out for SCRATCH_DEV and leaves the rest in > SCRATCH_DEV_POOL. > > I'm not totally sold on that behavior, but for now, > at least don't populate SCRATCH_DEV_POOL with newlines. > > Cc: linux-btrfs@vger.kernel.org > Signed-off-by: Eric Sandeen > --- > common.config | 2 +- > 1 files changed, 1 insertions(+), 1 deletions(-) > > diff --git a/common.config b/common.config > index ed0f44c..5ac58bf 100644 > --- a/common.config > +++ b/common.config > @@ -258,7 +258,7 @@ if [ ! -z "$SCRATCH_DEV_POOL" ]; then > exit 1 > fi > SCRATCH_DEV=`echo $SCRATCH_DEV_POOL | awk '{print $1}'` > - SCRATCH_DEV_POOL=`echo $SCRATCH_DEV_POOL | awk '{ for (i = 2; i <= NF; i++) print $i}'` > + SCRATCH_DEV_POOL=`echo $SCRATCH_DEV_POOL | awk '{ ORS=" "; for (i = 2; i <= NF; i++) print $i}'` > fi > > echo $SCRATCH_DEV | grep -q ":" > /dev/null 2>&1 > Is the purpose of this patch is so future improvements will be able to parse/use SCRATCH_DEV_POOL easier from within bash? Looks good Eric. Reviewed-by: Regards --Rich From sandeen@redhat.com Wed Mar 13 12:45:58 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 5BFF57F3F for ; Wed, 13 Mar 2013 12:45:58 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay1.corp.sgi.com (Postfix) with ESMTP id 3E4418F8073 for ; Wed, 13 Mar 2013 10:45:58 -0700 (PDT) X-ASG-Debug-ID: 1363196754-04cbb04b8465900001-NocioJ Received: from mx1.redhat.com (mx1.redhat.com [209.132.183.28]) by cuda.sgi.com with ESMTP id 8YGYfgFxYzYUOlJ5; Wed, 13 Mar 2013 10:45:54 -0700 (PDT) X-Barracuda-Envelope-From: sandeen@redhat.com X-Barracuda-Apparent-Source-IP: 209.132.183.28 X-ASG-Whitelist: Client Received: from int-mx02.intmail.prod.int.phx2.redhat.com (int-mx02.intmail.prod.int.phx2.redhat.com [10.5.11.12]) by mx1.redhat.com (8.14.4/8.14.4) with ESMTP id r2DHjreb024531 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=OK); Wed, 13 Mar 2013 13:45:54 -0400 Received: from liberator.sandeen.net (ovpn01.gateway.prod.ext.phx2.redhat.com [10.5.9.1]) by int-mx02.intmail.prod.int.phx2.redhat.com (8.13.8/8.13.8) with ESMTP id r2DHjqw3009672 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=NO); Wed, 13 Mar 2013 13:45:53 -0400 Message-ID: <5140BB50.9080403@redhat.com> Date: Wed, 13 Mar 2013 12:45:52 -0500 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: Rich Johnston CC: xfs@oss.sgi.com, linux-btrfs@vger.kernel.org Subject: Re: [PATCH 2/3] xfstests: keep newlines out of SCRATCH_DEV_POOL References: <1363186623-1378-1-git-send-email-sandeen@redhat.com> <1363186623-1378-3-git-send-email-sandeen@redhat.com> <5140BAAC.4050508@sgi.com> X-ASG-Orig-Subj: Re: [PATCH 2/3] xfstests: keep newlines out of SCRATCH_DEV_POOL In-Reply-To: <5140BAAC.4050508@sgi.com> X-Enigmail-Version: 1.5.1 Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Scanned-By: MIMEDefang 2.67 on 10.5.11.12 X-Barracuda-Connect: mx1.redhat.com[209.132.183.28] X-Barracuda-Start-Time: 1363196754 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 On 3/13/13 12:43 PM, Rich Johnston wrote: > On 03/13/2013 09:57 AM, Eric Sandeen wrote: >> SCRATCH_DEV_POOL processing actually takes the first >> device out for SCRATCH_DEV and leaves the rest in >> SCRATCH_DEV_POOL. >> >> I'm not totally sold on that behavior, but for now, >> at least don't populate SCRATCH_DEV_POOL with newlines. > >> >> Cc: linux-btrfs@vger.kernel.org >> Signed-off-by: Eric Sandeen >> --- >> common.config | 2 +- >> 1 files changed, 1 insertions(+), 1 deletions(-) >> >> diff --git a/common.config b/common.config >> index ed0f44c..5ac58bf 100644 >> --- a/common.config >> +++ b/common.config >> @@ -258,7 +258,7 @@ if [ ! -z "$SCRATCH_DEV_POOL" ]; then >> exit 1 >> fi >> SCRATCH_DEV=`echo $SCRATCH_DEV_POOL | awk '{print $1}'` >> - SCRATCH_DEV_POOL=`echo $SCRATCH_DEV_POOL | awk '{ for (i = 2; i <= NF; i++) print $i}'` >> + SCRATCH_DEV_POOL=`echo $SCRATCH_DEV_POOL | awk '{ ORS=" "; for (i = 2; i <= NF; i++) print $i}'` >> fi >> >> echo $SCRATCH_DEV | grep -q ":" > /dev/null 2>&1 >> > > Is the purpose of this patch is so future improvements will be able to parse/use SCRATCH_DEV_POOL easier from within bash? Yep, and just generally since it's used as an argument, feeding a string w/ newlines to any command is just a bit odd. -Eric > Looks good Eric. > > Reviewed-by: > > Regards > --Rich From rjohnston@sgi.com Wed Mar 13 12:46:51 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 6627E7F3F for ; Wed, 13 Mar 2013 12:46:51 -0500 (CDT) Received: from xmail.sgi.com (pv-excas3-dc21-nlb.corp.sgi.com [137.38.102.207]) by relay1.corp.sgi.com (Postfix) with ESMTP id EC88E8F8050; Wed, 13 Mar 2013 10:46:50 -0700 (PDT) Received: from [128.162.233.55] (128.162.233.55) by xmail.sgi.com (137.38.102.30) with Microsoft SMTP Server (TLS) id 14.2.318.1; Wed, 13 Mar 2013 12:46:50 -0500 Message-ID: <5140BBA2.4050600@sgi.com> Date: Wed, 13 Mar 2013 12:47:14 -0500 From: Rich Johnston User-Agent: Mozilla/5.0 (X11; Linux i686; rv:13.0) Gecko/20120615 Thunderbird/13.0.1 MIME-Version: 1.0 To: Eric Sandeen CC: Stefan Behrens , , Subject: Re: [PATCH 3/3] xfstests: btrfs tests for basic informational commands References: <1363186623-1378-1-git-send-email-sandeen@redhat.com> <1363186623-1378-4-git-send-email-sandeen@redhat.com> <51409C25.70403@giantdisaster.de> <5140A6AA.2010204@redhat.com> In-Reply-To: <5140A6AA.2010204@redhat.com> Content-Type: text/plain; charset="ISO-8859-1"; format=flowed Content-Transfer-Encoding: 7bit X-Originating-IP: [128.162.233.55] Looks good Eric, but I will wait for Stefan to look at this version to make sure all his comments have been addressed, then I will commit this series. Thanks for the patchset. Regards --Rich From shrinath.m@webyog.com Wed Mar 13 13:08:21 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=HTML_FONT_FACE_BAD, HTML_MESSAGE,T_DKIM_INVALID autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 37B287F3F for ; Wed, 13 Mar 2013 13:08:21 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay2.corp.sgi.com (Postfix) with ESMTP id EF6FB304075 for ; Wed, 13 Mar 2013 11:08:17 -0700 (PDT) X-ASG-Debug-ID: 1363198092-04bdf00a0d740b0001-NocioJ Received: from mail-ie0-f172.google.com (mail-ie0-f172.google.com [209.85.223.172]) by cuda.sgi.com with ESMTP id 8VJuZZsp0SadjT8R (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Wed, 13 Mar 2013 11:08:12 -0700 (PDT) X-Barracuda-Envelope-From: shrinath.m@webyog.com X-Barracuda-Apparent-Source-IP: 209.85.223.172 Received: by mail-ie0-f172.google.com with SMTP id c10so1844623ieb.17 for ; Wed, 13 Mar 2013 11:08:12 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=webyog.com; s=google; h=x-received:mime-version:in-reply-to:references:from:date:message-id :subject:to:cc:content-type; bh=61WBJpgCxd3Fr69Mosh5zURqFk06NzXV517ctzkwtbQ=; b=JSf39t3BhZm0kQQdf/r2OeUuXz6OvCOdoBVB470Tb59vue9puZBfwOSQindFQyCZe3 dRP81jmrHkjQPUW7/8UC95WtXMLwVPrW31cWtIzws/pRRQwoPxv/nhcemlJ1crfQusMy vHdfQUGhXq7f/okaHyK9dDsWWOAvpDDccLa64= X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=20120113; h=x-received:mime-version:in-reply-to:references:from:date:message-id :subject:to:cc:content-type:x-gm-message-state; bh=61WBJpgCxd3Fr69Mosh5zURqFk06NzXV517ctzkwtbQ=; b=kEdM7Tsv5gCG/Ad4OblJOir7AXwwwpbfVk8WLvg3ZDmS6a4/ExPMhhoGaHCJh5RP0s 9dstFpdW59bx2ARI4B7unh+V6acCotbd8v6/5cqUuahmtg0RBOYlcxtW7QF5As8DetuJ 4jwaSKuISJKvqFZ90cJJs/pc9rL2FLWJogWebQRdJWLTFUmsOUbHu/XVqmDBaNncKTax urvggCK0L7lNPs9cGC6fpUOfVixaktYk+sqITDLeE6keR3T+hja5tZ5ixfWvFHLJY8j3 O2f7248ZwuVonF+DGJ9BjkoC0hVn6AMcrEaoP64mRaRva+uGP/eL/SbM601nTYuU2INg YguA== X-Received: by 10.43.103.195 with SMTP id dj3mr17196814icc.3.1363198092265; Wed, 13 Mar 2013 11:08:12 -0700 (PDT) MIME-Version: 1.0 Received: by 10.43.1.132 with HTTP; Wed, 13 Mar 2013 11:07:52 -0700 (PDT) In-Reply-To: <513751F2.2060109@redhat.com> References: <51373DB8.2020707@redhat.com> <51373FC1.6010101@redhat.com> <513751F2.2060109@redhat.com> From: Shrinath M Date: Wed, 13 Mar 2013 23:37:52 +0530 Message-ID: Subject: Re: XFS filesystem on EC2 instance corrupts and shuts down To: Ric Wheeler X-ASG-Orig-Subj: Re: XFS filesystem on EC2 instance corrupts and shuts down Cc: Supratik Goswami , Sabyasachi Ruj , Vivek Goel , xfs@oss.sgi.com Content-Type: multipart/alternative; boundary=bcaec5171a230c704b04d7d24a4c X-Gm-Message-State: ALoCoQmljT8+ocYuJ2+ng6LoifSr58jCJ9mJQWRuOCfKkjnF8Q7PNAKU1K02RfPf6xOcFozIfY9h X-Barracuda-Connect: mail-ie0-f172.google.com[209.85.223.172] X-Barracuda-Start-Time: 1363198092 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Barracuda-BRTS-Status: 1 X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-Spam-Score: 0.61 X-Barracuda-Spam-Status: No, SCORE=0.61 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=DKIM_SIGNED, DKIM_VERIFIED, HTML_FONT_FACE_BAD, HTML_MESSAGE X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125104 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature 0.00 HTML_MESSAGE BODY: HTML included in message 0.61 HTML_FONT_FACE_BAD BODY: HTML font face is not a word --bcaec5171a230c704b04d7d24a4c Content-Type: text/plain; charset=UTF-8 Sorry to be asking in dev thread, but Amazon seems to be clueless in this case :( Can someone tell me where can we find the logs/output of xfs repair after this runs? We just reboot the machine when we see this and the /var/log/messages or dmesg seems to know nothing about what it repaired. On Wed, Mar 6, 2013 at 7:55 PM, Ric Wheeler wrote: > I would suggest contacting Amazon's customer support channel (or the > vendor you paid for the Linux instance you are running). > > XFS developer list is probably not the correct forum to help you debug > this :) > > Good luck! > > Ric > > > > On 03/06/2013 08:12 AM, Supratik Goswami wrote: > >> Have we created a ticket with AWS ? >> >> It could be an EBS issue who knows, we need to confirm that first. >> >> -- >> Warm Regards >> >> Supratik >> >> >> On Wed, Mar 6, 2013 at 6:38 PM, Ric Wheeler > rwheeler@redhat.com>> wrote: >> >> On 03/06/2013 08:03 AM, Shrinath M wrote: >> >> >> On Wed, Mar 6, 2013 at 6:29 PM, Ric Wheeler > > >> >> wrote: >> >> I think that you would need to verify that the Amazon storage >> is not >> throwing errors - do your logs show IO errors or issues >> before XFS >> hits an >> issue? >> >> >> No IO errors in /var/log/messages. >> Where else should I be looking? >> >> >> >> Feb 12 19:47:18 ip-100-0-100-1 kernel: [2541168.023638] XFS (md0): I/O >> Error Detected. Shutting down filesystem >> >> Is an IO error from MD. >> >> I would suggest trying to reproduce without MD in the picture first - >> always best to try to reproduce with the simplest setup first and work >> your way up the complexity ladder, >> >> Ric >> >> >> >> >> ______________________________**_________________ >> xfs mailing list >> xfs@oss.sgi.com >> http://oss.sgi.com/mailman/**listinfo/xfs >> > > -- Regards *Shrinath.M* --bcaec5171a230c704b04d7d24a4c Content-Type: text/html; charset=UTF-8 Content-Transfer-Encoding: quoted-printable
Sorry to be asking in dev thread, but Amazon seems to be c= lueless in this case :(
Can someone tell me where can we find the logs/= output of xfs repair after this runs? We just reboot the machine when we se= e this and the /var/log/messages or dmesg seems to know nothing about what = it repaired.


On Wed,= Mar 6, 2013 at 7:55 PM, Ric Wheeler <rwheeler@redhat.com>= wrote:
I would suggest contacting Amazon's cust= omer support channel (or the vendor you paid for the Linux instance you are= running).

XFS developer list is probably not the correct forum to help you debug this= :)

Good luck!

Ric



On 03/06/2013 08:12 AM, Supratik Goswami wrote:
Have we created a ticket with AWS ?

It could be an EBS issue who knows, we need to confirm that first.

--
Warm Regards

Supratik


On Wed, Mar 6, 2013 at 6:38 PM, Ric Wheeler <rwheeler@redhat.com <mailto:rwheeler@redhat.com>&= gt; wrote:

=C2=A0 =C2=A0 On 03/06/2013 08:03 AM, Shrinath M wrote:


=C2=A0 =C2=A0 =C2=A0 =C2=A0 On Wed, Mar 6, 2013 at 6:29 PM, Ric Wheeler <= ;rwheeler@redhat.c= om
=C2=A0 =C2=A0 =C2=A0 =C2=A0 <mailto:rwheeler@redhat.com> <mailto:rwheeler@redhat.com

=C2=A0 =C2=A0 =C2=A0 =C2=A0 <mailto:rwheeler@redhat.com>>> wrote:

=C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 I think that you would need to ve= rify that the Amazon storage is not
=C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 throwing errors - do your logs sh= ow IO errors or issues before XFS
=C2=A0 =C2=A0 =C2=A0 =C2=A0 hits an
=C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 issue?


=C2=A0 =C2=A0 =C2=A0 =C2=A0 No IO errors in /var/log/messages.
=C2=A0 =C2=A0 =C2=A0 =C2=A0 Where else should I be looking?



=C2=A0 =C2=A0 Feb 12 19:47:18 ip-100-0-100-1 kernel: [2541168.023638] XFS (= md0): I/O
=C2=A0 =C2=A0 Error Detected. Shutting down filesystem

=C2=A0 =C2=A0 Is an IO error from MD.

=C2=A0 =C2=A0 I would suggest trying to reproduce without MD in the picture= first -
=C2=A0 =C2=A0 always best to try to reproduce with the simplest setup first= and work
=C2=A0 =C2=A0 your way up the complexity ladder,

=C2=A0 =C2=A0 Ric




_______________________________________________
xfs mailing list
xfs@oss.sgi.com http:= //oss.sgi.com/mailman/listinfo/xfs




--
Regards
= Shrina= th.M

--bcaec5171a230c704b04d7d24a4c-- From kdhall@binghamton.edu Wed Mar 13 13:11:25 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id EAF517F4E for ; Wed, 13 Mar 2013 13:11:25 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay2.corp.sgi.com (Postfix) with ESMTP id B05C830407A for ; Wed, 13 Mar 2013 11:11:25 -0700 (PDT) X-ASG-Debug-ID: 1363198282-04bdf00a0a74700001-NocioJ Received: from mail-qc0-f176.google.com (mail-qc0-f176.google.com [209.85.216.176]) by cuda.sgi.com with ESMTP id P5yMJFyWZXQQ0xvo (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Wed, 13 Mar 2013 11:11:23 -0700 (PDT) X-Barracuda-Envelope-From: kdhall@binghamton.edu X-Barracuda-Apparent-Source-IP: 209.85.216.176 Received: by mail-qc0-f176.google.com with SMTP id n41so598143qco.21 for ; Wed, 13 Mar 2013 11:11:22 -0700 (PDT) X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=20120113; h=x-received:message-id:date:from:user-agent:mime-version:to:subject :content-type:content-transfer-encoding:x-gm-message-state; bh=EMPfIerVpQFjh4Ws5OpPKn75w/glsJLS+A9ksxHqqrs=; b=nvC6raxMzJcJ6ynDUR1aR0ai/ppt82JTy0uMWvx9+g6bANM4CPMyjD/VuvtIT941ap wvh1TwkZuEEGUb3HuKa3J8m4Vu0hgTYGpiZMyOyV8zpGBL8/e8J0dKD9A6Oy+gMwz+W0 /kq01yEBIHL70Jvui3HhT4IiKXRWEemiWVIVc8Ciwtvg4/Tf6KDOYGwj2BWuJy1sL0i7 rNDMO6hbUfe+3aE7GaAfmXCjRF4c2XR0qV8o/SgQHtOpbllw0polE6vaOzYjcuA7jj6O NO2KdireYqnNoSD+K4y6kDlEXmS8bcIbcdXvMxGkboOBrFDJpiXU6gGbouIgNP5jXC18 749w== X-Received: by 10.49.116.235 with SMTP id jz11mr11967871qeb.39.1363198282461; Wed, 13 Mar 2013 11:11:22 -0700 (PDT) Received: from [128.226.118.196] (omega.cs.binghamton.edu. [128.226.118.196]) by mx.google.com with ESMTPS id u7sm34841964qau.2.2013.03.13.11.11.20 (version=TLSv1 cipher=ECDHE-RSA-RC4-SHA bits=128/128); Wed, 13 Mar 2013 11:11:21 -0700 (PDT) Message-ID: <5140C147.7070205@binghamton.edu> Date: Wed, 13 Mar 2013 14:11:19 -0400 From: Dave Hall User-Agent: Mozilla/5.0 (X11; U; Linux x86_64; en-US; rv:1.9.1.16) Gecko/20121215 Icedove/3.0.11 MIME-Version: 1.0 To: xfs@oss.sgi.com Subject: xfs_fsr, sunit, and swidth Content-Type: text/plain; charset=ISO-8859-1; format=flowed X-ASG-Orig-Subj: xfs_fsr, sunit, and swidth Content-Transfer-Encoding: 7bit X-Gm-Message-State: ALoCoQmyMBU792SZTUMlol0gsrKT3f/q7ldJ90OQxiK46YHbk3tOUEjQUtPgmeJM6iuJbYMwcuox X-Barracuda-Connect: mail-qc0-f176.google.com[209.85.216.176] X-Barracuda-Start-Time: 1363198283 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125104 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- Does xfs_fsr react in any way to the sunit and swidth attributes of the file system? In other words, with an XFS filesytem set up directly on a hardware RAID, it is recommended that the mount command be changed to specify sunit and swidth values that reflect the new geometry of the RAID. In my case, these values were not specified on the mkfs.xfs of a rather large file system running on a RAID 6 array. I am wondering adding sunit and swidth parameters to the fstab will cause xfs_fsr to do anything different than it is already doing. Most importantly, will it improve performace in any way? Thanks. -Dave -- Dave Hall Binghamton University kdhall@binghamton.edu 607-760-2328 (Cell) 607-777-4641 (Office) From bpm@sgi.com Wed Mar 13 13:24:36 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 4E45E7F3F for ; Wed, 13 Mar 2013 13:24:36 -0500 (CDT) Received: from whiskey.americas.sgi.com (eagdhcp-232-197.americas.sgi.com [128.162.232.197]) by relay2.corp.sgi.com (Postfix) with ESMTP id DB351304059; Wed, 13 Mar 2013 11:24:35 -0700 (PDT) Received: by whiskey.americas.sgi.com (Postfix, from userid 4600) id 9DDE5500B4B; Wed, 13 Mar 2013 13:24:35 -0500 (CDT) Date: Wed, 13 Mar 2013 13:24:35 -0500 From: Ben Myers To: Shrinath M Cc: Ric Wheeler , Sabyasachi Ruj , xfs@oss.sgi.com, Supratik Goswami , Vivek Goel Subject: Re: XFS filesystem on EC2 instance corrupts and shuts down Message-ID: <20130313182435.GU22182@sgi.com> References: <51373DB8.2020707@redhat.com> <51373FC1.6010101@redhat.com> <513751F2.2060109@redhat.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: User-Agent: Mutt/1.5.20 (2009-06-14) Hey Shrinath, On Wed, Mar 13, 2013 at 11:37:52PM +0530, Shrinath M wrote: > Sorry to be asking in dev thread, but Amazon seems to be clueless in this > case :( > Can someone tell me where can we find the logs/output of xfs repair after > this runs? xfs_repair doesn't keep a separate log file. All the output is on the command line. You'll need to either redirect the output of stdout and stderr to a file, or keep a screen or console log. > We just reboot the machine when we see this and the > /var/log/messages or dmesg seems to know nothing about what it repaired. The contents of /var/log/messages could help you to understand why xfs might have forced shutdown, but won't help you with xfs_repair. Since you're getting IO errors, it sounds like you have a problem lower in the stack than the filesystem. At the filesystem level there isn't much we can do with a block device that is giving IO errors so we just shut down. Consider copying the remote block device to a local one ('dd' might be a good choice for this) and see if you can get a clean copy. Then it's time to see about the filesystem. Regards, Ben > On Wed, Mar 6, 2013 at 7:55 PM, Ric Wheeler wrote: > > > I would suggest contacting Amazon's customer support channel (or the > > vendor you paid for the Linux instance you are running). > > > > XFS developer list is probably not the correct forum to help you debug > > this :) > > > > Good luck! > > > > Ric > > > > > > > > On 03/06/2013 08:12 AM, Supratik Goswami wrote: > > > >> Have we created a ticket with AWS ? > >> > >> It could be an EBS issue who knows, we need to confirm that first. > >> > >> -- > >> Warm Regards > >> > >> Supratik > >> > >> > >> On Wed, Mar 6, 2013 at 6:38 PM, Ric Wheeler >> rwheeler@redhat.com>> wrote: > >> > >> On 03/06/2013 08:03 AM, Shrinath M wrote: > >> > >> > >> On Wed, Mar 6, 2013 at 6:29 PM, Ric Wheeler >> >> > >> >> wrote: > >> > >> I think that you would need to verify that the Amazon storage > >> is not > >> throwing errors - do your logs show IO errors or issues > >> before XFS > >> hits an > >> issue? > >> > >> > >> No IO errors in /var/log/messages. > >> Where else should I be looking? > >> > >> > >> > >> Feb 12 19:47:18 ip-100-0-100-1 kernel: [2541168.023638] XFS (md0): I/O > >> Error Detected. Shutting down filesystem > >> > >> Is an IO error from MD. > >> > >> I would suggest trying to reproduce without MD in the picture first - > >> always best to try to reproduce with the simplest setup first and work > >> your way up the complexity ladder, > >> > >> Ric > >> > >> > >> > >> > >> ______________________________**_________________ > >> xfs mailing list > >> xfs@oss.sgi.com > >> http://oss.sgi.com/mailman/**listinfo/xfs > >> > > > > > > > -- > Regards > *Shrinath.M* > _______________________________________________ > xfs mailing list > xfs@oss.sgi.com > http://oss.sgi.com/mailman/listinfo/xfs From sandeen@redhat.com Wed Mar 13 13:53:54 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 74F7B7F3F for ; Wed, 13 Mar 2013 13:53:54 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay1.corp.sgi.com (Postfix) with ESMTP id 298548F806F for ; Wed, 13 Mar 2013 11:53:54 -0700 (PDT) X-ASG-Debug-ID: 1363200832-04bdf00a0b79670001-NocioJ Received: from mx1.redhat.com (mx1.redhat.com [209.132.183.28]) by cuda.sgi.com with ESMTP id gCvBVTx2Flmb65Qg for ; Wed, 13 Mar 2013 11:53:53 -0700 (PDT) X-Barracuda-Envelope-From: sandeen@redhat.com X-Barracuda-Apparent-Source-IP: 209.132.183.28 X-ASG-Whitelist: Client Received: from int-mx02.intmail.prod.int.phx2.redhat.com (int-mx02.intmail.prod.int.phx2.redhat.com [10.5.11.12]) by mx1.redhat.com (8.14.4/8.14.4) with ESMTP id r2DIrqOb030170 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=OK); Wed, 13 Mar 2013 14:53:52 -0400 Received: from liberator.sandeen.net (ovpn01.gateway.prod.ext.phx2.redhat.com [10.5.9.1]) by int-mx02.intmail.prod.int.phx2.redhat.com (8.13.8/8.13.8) with ESMTP id r2DIrpm2005839 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=NO); Wed, 13 Mar 2013 14:53:52 -0400 Message-ID: <5140CB3F.5010704@redhat.com> Date: Wed, 13 Mar 2013 13:53:51 -0500 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: Eric Sandeen CC: xfs@oss.sgi.com, linux-btrfs@vger.kernel.org Subject: [PATCH 3/3 V3] xfstests: btrfs tests for basic informational commands References: <1363186623-1378-1-git-send-email-sandeen@redhat.com> <1363186623-1378-4-git-send-email-sandeen@redhat.com> <5140AB9D.2070001@redhat.com> X-ASG-Orig-Subj: [PATCH 3/3 V3] xfstests: btrfs tests for basic informational commands In-Reply-To: <5140AB9D.2070001@redhat.com> X-Enigmail-Version: 1.5.1 Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Scanned-By: MIMEDefang 2.67 on 10.5.11.12 X-Barracuda-Connect: mx1.redhat.com[209.132.183.28] X-Barracuda-Start-Time: 1363200832 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 Run basic btrfs information commands in various ways, performing sanity tests of: filesystem show, label, sync, and device stats (sync is included just because it's simple). These are mostly just smoke tests, although for example show by label & UUID should verify that the correct fs was shown. This also adds quite a few new filters to accommodate the output of the new commands. Cc: linux-btrfs@vger.kernel.org Signed-off-by: Eric Sandeen --- V2: sort & uniq device stats output to account for variable nrs. of devices. Optionally check that the proper nr. of devices was returned, as well. V3: _filter_uuid needs to pay attention to $1, not hope that the caller has set $UUID. Oops. diff --git a/313 b/313 new file mode 100755 index 0000000..579b0d3 --- /dev/null +++ b/313 @@ -0,0 +1,96 @@ +#! /bin/bash +# FS QA Test No. 313 +# +# run basic btrfs information commands in various ways +# sanity tests: filesystem show, label, sync, and device stats +# +#----------------------------------------------------------------------- +# Copyright (c) 2013 Red Hat, Inc. All Rights Reserved. +# +# This program is free software; you can redistribute it and/or +# modify it under the terms of the GNU General Public License as +# published by the Free Software Foundation. +# +# This program is distributed in the hope that it would be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program; if not, write the Free Software Foundation, +# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA +#----------------------------------------------------------------------- +# +# creator +owner=sandeen@redhat.com + +seq=`basename $0` +echo "== QA output created by $seq" + +here=`pwd` +tmp=/tmp/$$ +status=1 # failure is the default! +trap "_cleanup; exit \$status" 0 1 2 3 15 + +_cleanup() +{ + cd / + rm -f $tmp.* +} + +# get standard environment, filters and checks +. ./common.rc +. ./btrfs.filter + +# real QA test starts here + +# Modify as appropriate. +_supported_fs btrfs +_supported_os Linux +_require_scratch +_require_scratch_dev_pool + +rm -f $seq.full + +FIRST_POOL_DEV=`echo $SCRATCH_DEV_POOL | awk '{print $1}'` +LAST_POOL_DEV=`echo $SCRATCH_DEV_POOL | awk '{print $NF}'` +TOTAL_DEVS=`echo $SCRATCH_DEV $SCRATCH_DEV_POOL | wc -w` +LABEL=TestLabel.$seq + +echo "Scratch $SCRATCH_DEV First $FIRST_POOL_DEV last $LAST_POOL_DEV Total $TOTAL_DEVS" > $seq.full + +_scratch_mkfs $SCRATCH_DEV_POOL >> $seq.full 2>&1 || _fail "mkfs failed" + +# These have to be done unmounted...? +echo "== Set filesystem label to $LABEL" +$BTRFS_UTIL_PROG filesystem label $SCRATCH_DEV $LABEL +echo "== Get filesystem label" +$BTRFS_UTIL_PROG filesystem label $SCRATCH_DEV + +echo "== Mount." +_scratch_mount + +echo "== Show filesystem by label" +$BTRFS_UTIL_PROG filesystem show $LABEL | _filter_btrfs_filesystem_show $TOTAL_DEVS +UUID=`$BTRFS_UTIL_PROG filesystem show $LABEL | grep uuid: | awk '{print $NF}'` + +echo "UUID $UUID" >> $seq.full + +echo "== Show filesystem by UUID" +$BTRFS_UTIL_PROG filesystem show $UUID | _filter_btrfs_filesystem_show $TOTAL_DEVS $UUID + +echo "== Sync filesystem" +$BTRFS_UTIL_PROG filesystem sync $SCRATCH_MNT | _filter_scratch + +echo "== Show device stats by mountpoint" +$BTRFS_UTIL_PROG device stats $SCRATCH_MNT | _filter_btrfs_device_stats $TOTAL_DEVS +echo "== Show device stats by first/scratch dev" +$BTRFS_UTIL_PROG device stats $SCRATCH_DEV | _filter_btrfs_device_stats +echo "== Show device stats by second dev" +$BTRFS_UTIL_PROG device stats $FIRST_POOL_DEV | sed -e "s,$FIRST_POOL_DEV,FIRST_POOL_DEV,g" +echo "== Show device stats by last dev" +$BTRFS_UTIL_PROG device stats $LAST_POOL_DEV | sed -e "s,$LAST_POOL_DEV,LAST_POOL_DEV,g" + +# success, all done +status=0 +exit diff --git a/313.out b/313.out new file mode 100644 index 0000000..f513bdd --- /dev/null +++ b/313.out @@ -0,0 +1,41 @@ +== QA output created by 313 +== Set filesystem label to TestLabel.313 +== Get filesystem label +TestLabel.313 +== Mount. +== Show filesystem by label +Label: 'TestLabel.313' uuid: + Total devices FS bytes used + devid size used path SCRATCH_DEV + +== Show filesystem by UUID +Label: 'TestLabel.313' uuid: + Total devices FS bytes used + devid size used path SCRATCH_DEV + +== Sync filesystem +FSSync 'SCRATCH_MNT' +== Show device stats by mountpoint + [SCRATCH_DEV].corruption_errs + [SCRATCH_DEV].flush_io_errs + [SCRATCH_DEV].generation_errs + [SCRATCH_DEV].read_io_errs + [SCRATCH_DEV].write_io_errs +== Show device stats by first/scratch dev +[SCRATCH_DEV].corruption_errs +[SCRATCH_DEV].flush_io_errs +[SCRATCH_DEV].generation_errs +[SCRATCH_DEV].read_io_errs +[SCRATCH_DEV].write_io_errs +== Show device stats by second dev +[FIRST_POOL_DEV].write_io_errs 0 +[FIRST_POOL_DEV].read_io_errs 0 +[FIRST_POOL_DEV].flush_io_errs 0 +[FIRST_POOL_DEV].corruption_errs 0 +[FIRST_POOL_DEV].generation_errs 0 +== Show device stats by last dev +[LAST_POOL_DEV].write_io_errs 0 +[LAST_POOL_DEV].read_io_errs 0 +[LAST_POOL_DEV].flush_io_errs 0 +[LAST_POOL_DEV].corruption_errs 0 +[LAST_POOL_DEV].generation_errs 0 diff --git a/btrfs.filter b/btrfs.filter new file mode 100644 index 0000000..8a749bf --- /dev/null +++ b/btrfs.filter @@ -0,0 +1,60 @@ +# Filters for btrfs command output + +. ./common.filter + +# Some, but not all, commands emit "Btrfs " +_filter_btrfs_version() +{ + sed -e "s/^Btrfs.*//g" +} + +_filter_devid() +{ + sed -e "s/\(devid\s\+\)[0-9]\+/\1 /g" +} + +# If passed a number as first arg, filter that number of devices +# If passed a UUID as second arg, filter that exact UUID +_filter_btrfs_filesystem_show() +{ + if [ ! -z $1 ]; then + NUMDEVS=$1 + NUM_SUBST="" + else + NUMDEVS="[0-9]\+" + NUM_SUBST="" + fi + + UUID="" + if [ ! -z $2 ]; then + UUID=$2 + fi + + # the uniq collapses all device lines into 1 + _filter_uuid $UUID | _filter_scratch | _filter_scratch_pool | \ + _filter_size | _filter_btrfs_version | _filter_devid | \ + sed -e "s/\(Total devices\) $NUMDEVS/\1 $NUM_SUBST/g" | \ + uniq +} + +# This eliminates all numbers, and shows only unique lines, +# to accomodate a varying nr. of devices. +# If given an argument, make sure we saw that many devices +# in total. +_filter_btrfs_device_stats() +{ + if [ ! -z $1 ]; then + NUMDEVS=$1 + UNIQ_OPT="-c" + else + NUMDEVS="thiswillnotmatch" + UNIQ="" + fi + + _filter_scratch | _filter_scratch_pool | \ + sed -e "s/[0-9]\+$//g" | sort | uniq $UNIQ_OPT | \ + sed -e "s/$NUMDEVS / /g" +} + +# make sure this script returns success +/bin/true diff --git a/common.filter b/common.filter index c854a98..c34809f 100644 --- a/common.filter +++ b/common.filter @@ -226,6 +226,13 @@ _filter_scratch() sed -e "s,$SCRATCH_DEV,SCRATCH_DEV,g" -e "s,$SCRATCH_MNT,SCRATCH_MNT,g" } +# Turn any device in the scratch pool into SCRATCH_DEV +_filter_scratch_pool() +{ + FILTER_STRINGS=`echo $SCRATCH_DEV_POOL | sed -e 's/\s\+/\\\|/g'` + sed -e "s,$FILTER_STRINGS,SCRATCH_DEV,g" +} + _filter_spaces() { sed -e 's/ [ ]*/ /g' @@ -238,5 +245,23 @@ _filter_ln() -e "s,failed to create,creating," } +# If given an arg, filter *that* UUID string +# Otherwise look for something that looks like a generic UUID +_filter_uuid() +{ + if [ ! -z $1 ]; then + UUID=$1 + sed -e "s/\(uuid:\) $UUID/\1 /i" + else + sed -e "s/\(uuid:\) *[0-9a-f-][0-9a-f-]*/\1 /i" + fi +} + +# Filter out sizes like 6.14MB etc +_filter_size() +{ + sed -e "s/[0-9\.]\+\s\?[b|k|m|g|t][b]\?//ig" +} + # make sure this script returns success /bin/true diff --git a/group b/group index 8096968..fcbdfb6 100644 --- a/group +++ b/group @@ -429,3 +429,4 @@ stress 303 aio dangerous ioctl rw stress 304 aio dangerous ioctl rw stress 305 aio dangerous enospc rw stress +313 auto quick From sandeen@sandeen.net Wed Mar 13 13:56:39 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id EF56E7F3F for ; Wed, 13 Mar 2013 13:56:38 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay1.corp.sgi.com (Postfix) with ESMTP id A8ECB8F806F for ; Wed, 13 Mar 2013 11:56:38 -0700 (PDT) X-ASG-Debug-ID: 1363200996-04bdf00a0b79b20001-NocioJ Received: from sandeen.net (sandeen.net [63.231.237.45]) by cuda.sgi.com with ESMTP id mHonahQ0G6jE2UPT for ; Wed, 13 Mar 2013 11:56:36 -0700 (PDT) X-Barracuda-Envelope-From: sandeen@sandeen.net X-Barracuda-Apparent-Source-IP: 63.231.237.45 Received: from liberator.sandeen.net (liberator.sandeen.net [10.0.0.4]) (using TLSv1 with cipher DHE-RSA-CAMELLIA256-SHA (256/256 bits)) (No client certificate requested) by sandeen.net (Postfix) with ESMTPSA id BD9F463C6060; Wed, 13 Mar 2013 13:56:35 -0500 (CDT) Message-ID: <5140CBE3.80705@sandeen.net> Date: Wed, 13 Mar 2013 13:56:35 -0500 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: Shrinath M CC: Ric Wheeler , Sabyasachi Ruj , xfs@oss.sgi.com, Supratik Goswami , Vivek Goel Subject: Re: XFS filesystem on EC2 instance corrupts and shuts down References: <51373DB8.2020707@redhat.com> <51373FC1.6010101@redhat.com> <513751F2.2060109@redhat.com> X-ASG-Orig-Subj: Re: XFS filesystem on EC2 instance corrupts and shuts down In-Reply-To: X-Enigmail-Version: 1.5.1 Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: sandeen.net[63.231.237.45] X-Barracuda-Start-Time: 1363200996 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.10 X-Barracuda-Spam-Status: No, SCORE=0.10 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_SA085 X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125108 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.10 BSF_SC0_SA085 Custom Rule SA085 On 3/13/13 1:07 PM, Shrinath M wrote: > Sorry to be asking in dev thread, but Amazon seems to be clueless in this case :( > Can someone tell me where can we find the logs/output of xfs repair > after this runs? We just reboot the machine when we see this and the > /var/log/messages or dmesg seems to know nothing about what it > repaired. xfs_repair does not run automatically at boot on any OS I know of; xfs simply replays the log. But then I don't know what OS you are running, looks like an amazon special? It's a pity they can't support the OS they provide you, because on an older kernel like this, upstream developers will be less interested unless the problem persists in upstream kernels. This sort of support is usually best left to an OS vendor. But all that aside, you list this as the first error: Mar 5 01:14:33 ip-100-0-100-1 kernel: [14139930.248619] XFS (md0): Corruption detected. Unmount and run xfs_repair but I am wondering if there might be more information before this which is not in your trimmed logs. The text above is from xfs_corruption_error() which calls xfs_error_report() before the above message, and which should normally tell us a lot more about what went wrong, for example something like "Internal error %s at line %d of file %s. Caller 0x%" and possibly a hexdump or stack trace. One of the things in http://xfs.org/index.php/XFS_FAQ#Q:_What_information_should_I_include_when_reporting_a_problem.3F is: " dmesg output showing all error messages and stack traces " If you really didn't get anything else before this, try: echo 11 > /proc/sys/fs/xfs/error_level to capture the one instance where a corruption does not trigger verbose logs. That actually might be what you hit. It's a little odd that you get: Feb 12 19:47:18 ip-100-0-100-1 kernel: [2541168.014259] XFS (md0): xfs_iunlink_remove: xfs_itobp() returned error 117. because AFAIK, 117 is not any known error number (not even xfs's old EFSCORRUPTED value, which was 990) But I see other references in various places to this error number coming from XFS - so I'm not sure. -Eric > > On Wed, Mar 6, 2013 at 7:55 PM, Ric Wheeler > wrote: > > I would suggest contacting Amazon's customer support channel (or the vendor you paid for the Linux instance you are running). > > XFS developer list is probably not the correct forum to help you debug this :) > > Good luck! > > Ric > > > > On 03/06/2013 08:12 AM, Supratik Goswami wrote: > > Have we created a ticket with AWS ? > > It could be an EBS issue who knows, we need to confirm that first. > > -- > Warm Regards > > Supratik > > > On Wed, Mar 6, 2013 at 6:38 PM, Ric Wheeler >> wrote: > > On 03/06/2013 08:03 AM, Shrinath M wrote: > > > On Wed, Mar 6, 2013 at 6:29 PM, Ric Wheeler > > > > >>> wrote: > > I think that you would need to verify that the Amazon storage is not > throwing errors - do your logs show IO errors or issues before XFS > hits an > issue? > > > No IO errors in /var/log/messages. > Where else should I be looking? > > > > Feb 12 19:47:18 ip-100-0-100-1 kernel: [2541168.023638] XFS (md0): I/O > Error Detected. Shutting down filesystem > > Is an IO error from MD. > > I would suggest trying to reproduce without MD in the picture first - > always best to try to reproduce with the simplest setup first and work > your way up the complexity ladder, > > Ric > > > > > _________________________________________________ > xfs mailing list > xfs@oss.sgi.com > http://oss.sgi.com/mailman/__listinfo/xfs > > > > > > -- > Regards > *Shrinath.M* > > > > _______________________________________________ > xfs mailing list > xfs@oss.sgi.com > http://oss.sgi.com/mailman/listinfo/xfs > From sbehrens@giantdisaster.de Wed Mar 13 14:00:58 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 41F867F3F for ; Wed, 13 Mar 2013 14:00:58 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay2.corp.sgi.com (Postfix) with ESMTP id F3C8E30406B for ; Wed, 13 Mar 2013 12:00:57 -0700 (PDT) X-ASG-Debug-ID: 1363201255-04bdf00a0b7a310001-NocioJ Received: from mo-p00-ob.rzone.de (mo-p00-ob.rzone.de [81.169.146.160]) by cuda.sgi.com with ESMTP id DTRpZDSSQyVE0ayn for ; Wed, 13 Mar 2013 12:00:55 -0700 (PDT) X-Barracuda-Envelope-From: sbehrens@giantdisaster.de X-Barracuda-Apparent-Source-IP: 81.169.146.160 X-RZG-AUTH: :IGUKYFjleetgZuRbHZjp6Ve7NzeE1efWuTR/wV06y353QgIuD5+acdRFtJ8MDHZp4u74mTVB5dOWYQ== X-RZG-CLASS-ID: mo00 Received: from [172.24.1.80] (yian-ho01.nir.cronon.net [192.166.201.94]) by smtp.strato.de (jored mo23) (RZmta 31.20 AUTH) with ESMTPA id I0279cp2DII7kF ; Wed, 13 Mar 2013 20:00:51 +0100 (CET) Message-ID: <5140CCE2.60508@giantdisaster.de> Date: Wed, 13 Mar 2013 20:00:50 +0100 From: Stefan Behrens User-Agent: Mozilla/5.0 (Windows NT 6.1; WOW64; rv:17.0) Gecko/20130307 Thunderbird/17.0.4 MIME-Version: 1.0 To: Eric Sandeen CC: xfs@oss.sgi.com, linux-btrfs@vger.kernel.org Subject: Re: [PATCH 3/3 V3] xfstests: btrfs tests for basic informational commands References: <1363186623-1378-1-git-send-email-sandeen@redhat.com> <1363186623-1378-4-git-send-email-sandeen@redhat.com> <5140AB9D.2070001@redhat.com> <5140CB3F.5010704@redhat.com> X-ASG-Orig-Subj: Re: [PATCH 3/3 V3] xfstests: btrfs tests for basic informational commands In-Reply-To: <5140CB3F.5010704@redhat.com> Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: mo-p00-ob.rzone.de[81.169.146.160] X-Barracuda-Start-Time: 1363201255 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Barracuda-BRTS-Status: 1 X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125108 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Wed, 13 Mar 2013 13:53:51 -0500, Eric Sandeen wrote: > Run basic btrfs information commands in various ways, performing > sanity tests of: filesystem show, label, sync, and device stats > (sync is included just because it's simple). These are mostly > just smoke tests, although for example show by label & UUID > should verify that the correct fs was shown. > > This also adds quite a few new filters to accommodate the output > of the new commands. > > Cc: linux-btrfs@vger.kernel.org > Signed-off-by: Eric Sandeen > --- > > V2: sort & uniq device stats output to account for variable > nrs. of devices. Optionally check that the proper nr. of > devices was returned, as well. > > V3: _filter_uuid needs to pay attention to $1, not hope > that the caller has set $UUID. Oops. > > diff --git a/313 b/313 > new file mode 100755 > index 0000000..579b0d3 > --- /dev/null > +++ b/313 > @@ -0,0 +1,96 @@ > +#! /bin/bash > +# FS QA Test No. 313 > +# > +# run basic btrfs information commands in various ways > +# sanity tests: filesystem show, label, sync, and device stats > +# > +#----------------------------------------------------------------------- > +# Copyright (c) 2013 Red Hat, Inc. All Rights Reserved. > +# > +# This program is free software; you can redistribute it and/or > +# modify it under the terms of the GNU General Public License as > +# published by the Free Software Foundation. > +# > +# This program is distributed in the hope that it would be useful, > +# but WITHOUT ANY WARRANTY; without even the implied warranty of > +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the > +# GNU General Public License for more details. > +# > +# You should have received a copy of the GNU General Public License > +# along with this program; if not, write the Free Software Foundation, > +# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA > +#----------------------------------------------------------------------- > +# > +# creator > +owner=sandeen@redhat.com > + > +seq=`basename $0` > +echo "== QA output created by $seq" > + > +here=`pwd` > +tmp=/tmp/$$ > +status=1 # failure is the default! > +trap "_cleanup; exit \$status" 0 1 2 3 15 > + > +_cleanup() > +{ > + cd / > + rm -f $tmp.* > +} > + > +# get standard environment, filters and checks > +. ./common.rc > +. ./btrfs.filter > + > +# real QA test starts here > + > +# Modify as appropriate. > +_supported_fs btrfs > +_supported_os Linux > +_require_scratch > +_require_scratch_dev_pool > + > +rm -f $seq.full > + > +FIRST_POOL_DEV=`echo $SCRATCH_DEV_POOL | awk '{print $1}'` > +LAST_POOL_DEV=`echo $SCRATCH_DEV_POOL | awk '{print $NF}'` > +TOTAL_DEVS=`echo $SCRATCH_DEV $SCRATCH_DEV_POOL | wc -w` > +LABEL=TestLabel.$seq > + > +echo "Scratch $SCRATCH_DEV First $FIRST_POOL_DEV last $LAST_POOL_DEV Total $TOTAL_DEVS" > $seq.full > + > +_scratch_mkfs $SCRATCH_DEV_POOL >> $seq.full 2>&1 || _fail "mkfs failed" > + > +# These have to be done unmounted...? > +echo "== Set filesystem label to $LABEL" > +$BTRFS_UTIL_PROG filesystem label $SCRATCH_DEV $LABEL > +echo "== Get filesystem label" > +$BTRFS_UTIL_PROG filesystem label $SCRATCH_DEV > + > +echo "== Mount." > +_scratch_mount > + > +echo "== Show filesystem by label" > +$BTRFS_UTIL_PROG filesystem show $LABEL | _filter_btrfs_filesystem_show $TOTAL_DEVS > +UUID=`$BTRFS_UTIL_PROG filesystem show $LABEL | grep uuid: | awk '{print $NF}'` > + > +echo "UUID $UUID" >> $seq.full > + > +echo "== Show filesystem by UUID" > +$BTRFS_UTIL_PROG filesystem show $UUID | _filter_btrfs_filesystem_show $TOTAL_DEVS $UUID > + > +echo "== Sync filesystem" > +$BTRFS_UTIL_PROG filesystem sync $SCRATCH_MNT | _filter_scratch > + > +echo "== Show device stats by mountpoint" > +$BTRFS_UTIL_PROG device stats $SCRATCH_MNT | _filter_btrfs_device_stats $TOTAL_DEVS > +echo "== Show device stats by first/scratch dev" > +$BTRFS_UTIL_PROG device stats $SCRATCH_DEV | _filter_btrfs_device_stats > +echo "== Show device stats by second dev" > +$BTRFS_UTIL_PROG device stats $FIRST_POOL_DEV | sed -e "s,$FIRST_POOL_DEV,FIRST_POOL_DEV,g" > +echo "== Show device stats by last dev" > +$BTRFS_UTIL_PROG device stats $LAST_POOL_DEV | sed -e "s,$LAST_POOL_DEV,LAST_POOL_DEV,g" > + > +# success, all done > +status=0 > +exit > diff --git a/313.out b/313.out > new file mode 100644 > index 0000000..f513bdd > --- /dev/null > +++ b/313.out > @@ -0,0 +1,41 @@ > +== QA output created by 313 > +== Set filesystem label to TestLabel.313 > +== Get filesystem label > +TestLabel.313 > +== Mount. > +== Show filesystem by label > +Label: 'TestLabel.313' uuid: > + Total devices FS bytes used > + devid size used path SCRATCH_DEV > + > +== Show filesystem by UUID > +Label: 'TestLabel.313' uuid: > + Total devices FS bytes used > + devid size used path SCRATCH_DEV > + > +== Sync filesystem > +FSSync 'SCRATCH_MNT' > +== Show device stats by mountpoint > + [SCRATCH_DEV].corruption_errs > + [SCRATCH_DEV].flush_io_errs > + [SCRATCH_DEV].generation_errs > + [SCRATCH_DEV].read_io_errs > + [SCRATCH_DEV].write_io_errs > +== Show device stats by first/scratch dev > +[SCRATCH_DEV].corruption_errs > +[SCRATCH_DEV].flush_io_errs > +[SCRATCH_DEV].generation_errs > +[SCRATCH_DEV].read_io_errs > +[SCRATCH_DEV].write_io_errs > +== Show device stats by second dev > +[FIRST_POOL_DEV].write_io_errs 0 > +[FIRST_POOL_DEV].read_io_errs 0 > +[FIRST_POOL_DEV].flush_io_errs 0 > +[FIRST_POOL_DEV].corruption_errs 0 > +[FIRST_POOL_DEV].generation_errs 0 > +== Show device stats by last dev > +[LAST_POOL_DEV].write_io_errs 0 > +[LAST_POOL_DEV].read_io_errs 0 > +[LAST_POOL_DEV].flush_io_errs 0 > +[LAST_POOL_DEV].corruption_errs 0 > +[LAST_POOL_DEV].generation_errs 0 > diff --git a/btrfs.filter b/btrfs.filter > new file mode 100644 > index 0000000..8a749bf > --- /dev/null > +++ b/btrfs.filter > @@ -0,0 +1,60 @@ > +# Filters for btrfs command output > + > +. ./common.filter > + > +# Some, but not all, commands emit "Btrfs " > +_filter_btrfs_version() > +{ > + sed -e "s/^Btrfs.*//g" > +} > + > +_filter_devid() > +{ > + sed -e "s/\(devid\s\+\)[0-9]\+/\1 /g" > +} > + > +# If passed a number as first arg, filter that number of devices > +# If passed a UUID as second arg, filter that exact UUID > +_filter_btrfs_filesystem_show() > +{ > + if [ ! -z $1 ]; then > + NUMDEVS=$1 > + NUM_SUBST="" > + else > + NUMDEVS="[0-9]\+" > + NUM_SUBST="" > + fi > + > + UUID="" > + if [ ! -z $2 ]; then > + UUID=$2 > + fi > + > + # the uniq collapses all device lines into 1 > + _filter_uuid $UUID | _filter_scratch | _filter_scratch_pool | \ > + _filter_size | _filter_btrfs_version | _filter_devid | \ > + sed -e "s/\(Total devices\) $NUMDEVS/\1 $NUM_SUBST/g" | \ > + uniq > +} > + > +# This eliminates all numbers, and shows only unique lines, > +# to accomodate a varying nr. of devices. > +# If given an argument, make sure we saw that many devices > +# in total. > +_filter_btrfs_device_stats() > +{ > + if [ ! -z $1 ]; then > + NUMDEVS=$1 > + UNIQ_OPT="-c" > + else > + NUMDEVS="thiswillnotmatch" > + UNIQ="" > + fi > + > + _filter_scratch | _filter_scratch_pool | \ > + sed -e "s/[0-9]\+$//g" | sort | uniq $UNIQ_OPT | \ > + sed -e "s/$NUMDEVS / /g" > +} > + > +# make sure this script returns success > +/bin/true > diff --git a/common.filter b/common.filter > index c854a98..c34809f 100644 > --- a/common.filter > +++ b/common.filter > @@ -226,6 +226,13 @@ _filter_scratch() > sed -e "s,$SCRATCH_DEV,SCRATCH_DEV,g" -e "s,$SCRATCH_MNT,SCRATCH_MNT,g" > } > > +# Turn any device in the scratch pool into SCRATCH_DEV > +_filter_scratch_pool() > +{ > + FILTER_STRINGS=`echo $SCRATCH_DEV_POOL | sed -e 's/\s\+/\\\|/g'` > + sed -e "s,$FILTER_STRINGS,SCRATCH_DEV,g" > +} > + > _filter_spaces() > { > sed -e 's/ [ ]*/ /g' > @@ -238,5 +245,23 @@ _filter_ln() > -e "s,failed to create,creating," > } > > +# If given an arg, filter *that* UUID string > +# Otherwise look for something that looks like a generic UUID > +_filter_uuid() > +{ > + if [ ! -z $1 ]; then > + UUID=$1 > + sed -e "s/\(uuid:\) $UUID/\1 /i" > + else > + sed -e "s/\(uuid:\) *[0-9a-f-][0-9a-f-]*/\1 /i" > + fi > +} > + > +# Filter out sizes like 6.14MB etc > +_filter_size() > +{ > + sed -e "s/[0-9\.]\+\s\?[b|k|m|g|t][b]\?//ig" > +} > + > # make sure this script returns success > /bin/true > diff --git a/group b/group > index 8096968..fcbdfb6 100644 > --- a/group > +++ b/group > @@ -429,3 +429,4 @@ stress > 303 aio dangerous ioctl rw stress > 304 aio dangerous ioctl rw stress > 305 aio dangerous enospc rw stress > +313 auto quick > Reviewed-by: Stefan Behrens From sandeen@sandeen.net Wed Mar 13 14:02:03 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 6BFCA7F3F for ; Wed, 13 Mar 2013 14:02:03 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay1.corp.sgi.com (Postfix) with ESMTP id 48B1C8F8070 for ; Wed, 13 Mar 2013 12:02:00 -0700 (PDT) X-ASG-Debug-ID: 1363201318-04cbb04b856c6e0001-NocioJ Received: from sandeen.net (sandeen.net [63.231.237.45]) by cuda.sgi.com with ESMTP id 6C6AaC9s1d5F1wPB for ; Wed, 13 Mar 2013 12:01:58 -0700 (PDT) X-Barracuda-Envelope-From: sandeen@sandeen.net X-Barracuda-Apparent-Source-IP: 63.231.237.45 Received: from liberator.sandeen.net (liberator.sandeen.net [10.0.0.4]) (using TLSv1 with cipher DHE-RSA-CAMELLIA256-SHA (256/256 bits)) (No client certificate requested) by sandeen.net (Postfix) with ESMTPSA id 466E263C6060; Wed, 13 Mar 2013 14:01:58 -0500 (CDT) Message-ID: <5140CD26.7050201@sandeen.net> Date: Wed, 13 Mar 2013 14:01:58 -0500 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: Eric Sandeen CC: linux-btrfs@vger.kernel.org, xfs@oss.sgi.com Subject: [PATCH 3/3 V4] xfstests: btrfs tests for basic informational commands References: <1363186623-1378-1-git-send-email-sandeen@redhat.com> <1363186623-1378-4-git-send-email-sandeen@redhat.com> <5140AB9D.2070001@redhat.com> <5140CB3F.5010704@redhat.com> X-ASG-Orig-Subj: [PATCH 3/3 V4] xfstests: btrfs tests for basic informational commands In-Reply-To: <5140CB3F.5010704@redhat.com> X-Enigmail-Version: 1.5.1 Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: sandeen.net[63.231.237.45] X-Barracuda-Start-Time: 1363201318 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125108 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- Run basic btrfs information commands in various ways, performing sanity tests of: filesystem show, label, sync, and device stats (sync is included just because it's simple). These are mostly just smoke tests, although for example show by label & UUID should verify that the correct fs was shown. This also adds quite a few new filters to accommodate the output of the new commands. Cc: linux-btrfs@vger.kernel.org Signed-off-by: Eric Sandeen --- V2: sort & uniq device stats output to account for variable nrs. of devices. Optionally check that the proper nr. of devices was returned, as well. V3: _filter_uuid needs to pay attention to $1, not hope that the caller has set $UUID. Oops. V4: fix stats filter to set UNIQ_OPT in both cases, ugh. diff --git a/313 b/313 new file mode 100755 index 0000000..579b0d3 --- /dev/null +++ b/313 @@ -0,0 +1,96 @@ +#! /bin/bash +# FS QA Test No. 313 +# +# run basic btrfs information commands in various ways +# sanity tests: filesystem show, label, sync, and device stats +# +#----------------------------------------------------------------------- +# Copyright (c) 2013 Red Hat, Inc. All Rights Reserved. +# +# This program is free software; you can redistribute it and/or +# modify it under the terms of the GNU General Public License as +# published by the Free Software Foundation. +# +# This program is distributed in the hope that it would be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program; if not, write the Free Software Foundation, +# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA +#----------------------------------------------------------------------- +# +# creator +owner=sandeen@redhat.com + +seq=`basename $0` +echo "== QA output created by $seq" + +here=`pwd` +tmp=/tmp/$$ +status=1 # failure is the default! +trap "_cleanup; exit \$status" 0 1 2 3 15 + +_cleanup() +{ + cd / + rm -f $tmp.* +} + +# get standard environment, filters and checks +. ./common.rc +. ./btrfs.filter + +# real QA test starts here + +# Modify as appropriate. +_supported_fs btrfs +_supported_os Linux +_require_scratch +_require_scratch_dev_pool + +rm -f $seq.full + +FIRST_POOL_DEV=`echo $SCRATCH_DEV_POOL | awk '{print $1}'` +LAST_POOL_DEV=`echo $SCRATCH_DEV_POOL | awk '{print $NF}'` +TOTAL_DEVS=`echo $SCRATCH_DEV $SCRATCH_DEV_POOL | wc -w` +LABEL=TestLabel.$seq + +echo "Scratch $SCRATCH_DEV First $FIRST_POOL_DEV last $LAST_POOL_DEV Total $TOTAL_DEVS" > $seq.full + +_scratch_mkfs $SCRATCH_DEV_POOL >> $seq.full 2>&1 || _fail "mkfs failed" + +# These have to be done unmounted...? +echo "== Set filesystem label to $LABEL" +$BTRFS_UTIL_PROG filesystem label $SCRATCH_DEV $LABEL +echo "== Get filesystem label" +$BTRFS_UTIL_PROG filesystem label $SCRATCH_DEV + +echo "== Mount." +_scratch_mount + +echo "== Show filesystem by label" +$BTRFS_UTIL_PROG filesystem show $LABEL | _filter_btrfs_filesystem_show $TOTAL_DEVS +UUID=`$BTRFS_UTIL_PROG filesystem show $LABEL | grep uuid: | awk '{print $NF}'` + +echo "UUID $UUID" >> $seq.full + +echo "== Show filesystem by UUID" +$BTRFS_UTIL_PROG filesystem show $UUID | _filter_btrfs_filesystem_show $TOTAL_DEVS $UUID + +echo "== Sync filesystem" +$BTRFS_UTIL_PROG filesystem sync $SCRATCH_MNT | _filter_scratch + +echo "== Show device stats by mountpoint" +$BTRFS_UTIL_PROG device stats $SCRATCH_MNT | _filter_btrfs_device_stats $TOTAL_DEVS +echo "== Show device stats by first/scratch dev" +$BTRFS_UTIL_PROG device stats $SCRATCH_DEV | _filter_btrfs_device_stats +echo "== Show device stats by second dev" +$BTRFS_UTIL_PROG device stats $FIRST_POOL_DEV | sed -e "s,$FIRST_POOL_DEV,FIRST_POOL_DEV,g" +echo "== Show device stats by last dev" +$BTRFS_UTIL_PROG device stats $LAST_POOL_DEV | sed -e "s,$LAST_POOL_DEV,LAST_POOL_DEV,g" + +# success, all done +status=0 +exit diff --git a/313.out b/313.out new file mode 100644 index 0000000..f513bdd --- /dev/null +++ b/313.out @@ -0,0 +1,41 @@ +== QA output created by 313 +== Set filesystem label to TestLabel.313 +== Get filesystem label +TestLabel.313 +== Mount. +== Show filesystem by label +Label: 'TestLabel.313' uuid: + Total devices FS bytes used + devid size used path SCRATCH_DEV + +== Show filesystem by UUID +Label: 'TestLabel.313' uuid: + Total devices FS bytes used + devid size used path SCRATCH_DEV + +== Sync filesystem +FSSync 'SCRATCH_MNT' +== Show device stats by mountpoint + [SCRATCH_DEV].corruption_errs + [SCRATCH_DEV].flush_io_errs + [SCRATCH_DEV].generation_errs + [SCRATCH_DEV].read_io_errs + [SCRATCH_DEV].write_io_errs +== Show device stats by first/scratch dev +[SCRATCH_DEV].corruption_errs +[SCRATCH_DEV].flush_io_errs +[SCRATCH_DEV].generation_errs +[SCRATCH_DEV].read_io_errs +[SCRATCH_DEV].write_io_errs +== Show device stats by second dev +[FIRST_POOL_DEV].write_io_errs 0 +[FIRST_POOL_DEV].read_io_errs 0 +[FIRST_POOL_DEV].flush_io_errs 0 +[FIRST_POOL_DEV].corruption_errs 0 +[FIRST_POOL_DEV].generation_errs 0 +== Show device stats by last dev +[LAST_POOL_DEV].write_io_errs 0 +[LAST_POOL_DEV].read_io_errs 0 +[LAST_POOL_DEV].flush_io_errs 0 +[LAST_POOL_DEV].corruption_errs 0 +[LAST_POOL_DEV].generation_errs 0 diff --git a/btrfs.filter b/btrfs.filter new file mode 100644 index 0000000..8a749bf --- /dev/null +++ b/btrfs.filter @@ -0,0 +1,60 @@ +# Filters for btrfs command output + +. ./common.filter + +# Some, but not all, commands emit "Btrfs " +_filter_btrfs_version() +{ + sed -e "s/^Btrfs.*//g" +} + +_filter_devid() +{ + sed -e "s/\(devid\s\+\)[0-9]\+/\1 /g" +} + +# If passed a number as first arg, filter that number of devices +# If passed a UUID as second arg, filter that exact UUID +_filter_btrfs_filesystem_show() +{ + if [ ! -z $1 ]; then + NUMDEVS=$1 + NUM_SUBST="" + else + NUMDEVS="[0-9]\+" + NUM_SUBST="" + fi + + UUID="" + if [ ! -z $2 ]; then + UUID=$2 + fi + + # the uniq collapses all device lines into 1 + _filter_uuid $UUID | _filter_scratch | _filter_scratch_pool | \ + _filter_size | _filter_btrfs_version | _filter_devid | \ + sed -e "s/\(Total devices\) $NUMDEVS/\1 $NUM_SUBST/g" | \ + uniq +} + +# This eliminates all numbers, and shows only unique lines, +# to accomodate a varying nr. of devices. +# If given an argument, make sure we saw that many devices +# in total. +_filter_btrfs_device_stats() +{ + if [ ! -z $1 ]; then + NUMDEVS=$1 + UNIQ_OPT="-c" + else + NUMDEVS="thiswillnotmatch" + UNIQ_OPT="" + fi + + _filter_scratch | _filter_scratch_pool | \ + sed -e "s/[0-9]\+$//g" | sort | uniq $UNIQ_OPT | \ + sed -e "s/$NUMDEVS / /g" +} + +# make sure this script returns success +/bin/true diff --git a/common.filter b/common.filter index c854a98..c34809f 100644 --- a/common.filter +++ b/common.filter @@ -226,6 +226,13 @@ _filter_scratch() sed -e "s,$SCRATCH_DEV,SCRATCH_DEV,g" -e "s,$SCRATCH_MNT,SCRATCH_MNT,g" } +# Turn any device in the scratch pool into SCRATCH_DEV +_filter_scratch_pool() +{ + FILTER_STRINGS=`echo $SCRATCH_DEV_POOL | sed -e 's/\s\+/\\\|/g'` + sed -e "s,$FILTER_STRINGS,SCRATCH_DEV,g" +} + _filter_spaces() { sed -e 's/ [ ]*/ /g' @@ -238,5 +245,23 @@ _filter_ln() -e "s,failed to create,creating," } +# If given an arg, filter *that* UUID string +# Otherwise look for something that looks like a generic UUID +_filter_uuid() +{ + if [ ! -z $1 ]; then + UUID=$1 + sed -e "s/\(uuid:\) $UUID/\1 /i" + else + sed -e "s/\(uuid:\) *[0-9a-f-][0-9a-f-]*/\1 /i" + fi +} + +# Filter out sizes like 6.14MB etc +_filter_size() +{ + sed -e "s/[0-9\.]\+\s\?[b|k|m|g|t][b]\?//ig" +} + # make sure this script returns success /bin/true diff --git a/group b/group index 8096968..fcbdfb6 100644 --- a/group +++ b/group @@ -429,3 +429,4 @@ stress 303 aio dangerous ioctl rw stress 304 aio dangerous ioctl rw stress 305 aio dangerous enospc rw stress +313 auto quick _______________________________________________ xfs mailing list xfs@oss.sgi.com http://oss.sgi.com/mailman/listinfo/xfs From sandeen@sandeen.net Wed Mar 13 14:11:03 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id E29927F37 for ; Wed, 13 Mar 2013 14:11:03 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay2.corp.sgi.com (Postfix) with ESMTP id A67B0304051 for ; Wed, 13 Mar 2013 12:11:00 -0700 (PDT) X-ASG-Debug-ID: 1363201859-04bdf00a0d7b330001-NocioJ Received: from sandeen.net (sandeen.net [63.231.237.45]) by cuda.sgi.com with ESMTP id Ul5IRK2JD1vzPyNA for ; Wed, 13 Mar 2013 12:10:59 -0700 (PDT) X-Barracuda-Envelope-From: sandeen@sandeen.net X-Barracuda-Apparent-Source-IP: 63.231.237.45 Received: from liberator.sandeen.net (liberator.sandeen.net [10.0.0.4]) (using TLSv1 with cipher DHE-RSA-CAMELLIA256-SHA (256/256 bits)) (No client certificate requested) by sandeen.net (Postfix) with ESMTPSA id 2759963C6060; Wed, 13 Mar 2013 14:10:59 -0500 (CDT) Message-ID: <5140CF42.6000206@sandeen.net> Date: Wed, 13 Mar 2013 14:10:58 -0500 From: Eric Sandeen User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:17.0) Gecko/20130216 Thunderbird/17.0.3 MIME-Version: 1.0 To: Shrinath M CC: Sabyasachi Ruj , Vivek Goel , Supratik Goswami , Ric Wheeler , xfs@oss.sgi.com Subject: Re: XFS filesystem on EC2 instance corrupts and shuts down References: <51373DB8.2020707@redhat.com> <51373FC1.6010101@redhat.com> <513751F2.2060109@redhat.com> <5140CBE3.80705@sandeen.net> X-ASG-Orig-Subj: Re: XFS filesystem on EC2 instance corrupts and shuts down In-Reply-To: <5140CBE3.80705@sandeen.net> X-Enigmail-Version: 1.5.1 Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: sandeen.net[63.231.237.45] X-Barracuda-Start-Time: 1363201859 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125108 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On 3/13/13 1:56 PM, Eric Sandeen wrote: > It's a little odd that you get: > > Feb 12 19:47:18 ip-100-0-100-1 kernel: [2541168.014259] XFS (md0): xfs_iunlink_remove: xfs_itobp() returned error 117. > > because AFAIK, 117 is not any known error number (not even xfs's old EFSCORRUPTED value, which was 990) > But I see other references in various places to this error number coming from XFS - so I'm not sure. Ugh, no it's not odd, it's: #define EUCLEAN 117 which maps to EFSCORRUPTED. Sorry for that noise, how'd I miss that? :( Anyway, turn up the error level & see if you get more info. -Eric From ebiederm@xmission.com Wed Mar 13 17:22:30 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 02A167F37 for ; Wed, 13 Mar 2013 17:22:30 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay3.corp.sgi.com (Postfix) with ESMTP id 91082AC001 for ; Wed, 13 Mar 2013 15:22:26 -0700 (PDT) X-ASG-Debug-ID: 1363213345-04bdf00a0d8c620001-NocioJ Received: from out01.mta.xmission.com (out01.mta.xmission.com [166.70.13.231]) by cuda.sgi.com with ESMTP id LacSrO6e1VoatCv7 (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO); Wed, 13 Mar 2013 15:22:25 -0700 (PDT) X-Barracuda-Envelope-From: ebiederm@xmission.com X-Barracuda-Apparent-Source-IP: 166.70.13.231 Received: from in02.mta.xmission.com ([166.70.13.52]) by out01.mta.xmission.com with esmtps (TLS1.0:RSA_AES_256_CBC_SHA1:32) (Exim 4.76) (envelope-from ) id 1UFu3z-0000iB-9H; Wed, 13 Mar 2013 16:22:23 -0600 Received: from mfd0536d0.tmodns.net ([208.54.5.253] helo=eric-ThinkPad-X220.xmission.com) by in02.mta.xmission.com with esmtpsa (TLS1.0:DHE_RSA_AES_128_CBC_SHA1:16) (Exim 4.76) (envelope-from ) id 1UFu3t-0007TX-Tv; Wed, 13 Mar 2013 16:22:23 -0600 From: ebiederm@xmission.com (Eric W. Biederman) To: Cc: Linux Containers , xfs@oss.sgi.com, "Serge E. Hallyn" , Ben Myers , Alex Elder , Dave Chinner Date: Wed, 13 Mar 2013 15:21:11 -0700 Message-ID: <87boan3prc.fsf@xmission.com> User-Agent: Gnus/5.13 (Gnus v5.13) Emacs/24.1 (gnu/linux) MIME-Version: 1.0 Content-Type: text/plain X-XM-AID: U2FsdGVkX1+oZ7a0cPxC2xANaBpv7a1n2Rg2Kx6LSn0= X-SA-Exim-Connect-IP: 208.54.5.253 X-SA-Exim-Mail-From: ebiederm@xmission.com Subject: [PATCH 00/14] xfs: Support for interacting with multiple user namespaces X-ASG-Orig-Subj: [PATCH 00/14] xfs: Support for interacting with multiple user namespaces X-SA-Exim-Version: 4.2.1 (built Wed, 14 Nov 2012 14:26:46 -0700) X-SA-Exim-Scanned: Yes (on in02.mta.xmission.com) X-Barracuda-Connect: out01.mta.xmission.com[166.70.13.231] X-Barracuda-Start-Time: 1363213345 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Barracuda-BRTS-Status: 1 X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_MISMATCH_TO X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125122 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 BSF_SC0_MISMATCH_TO Envelope rcpt doesn't match header Or replace uids, gids, and projids with kuids, kgids, and kprojids In support of user namespaces I have introduced into the kernel kuids, kgids, and kprojids. The most important characteristic of these ids is that they are not assignment compatible with uids, gids, and projids coming from userspace nor are they assignment compatible with uids, gids or projids stored on disk. This assignment incompatibility makes it easy to ensure that conversions are introduced at the edge of userspace and at the interface between on-disk and in-memory data structures. Getting all of the conversions in all of the right places is important because if one is missed it can easily become a permission check that compares the wrong values. While doing these conversions I have learned time and time again that if I do not push kuids and kgids down into every in memory data structure I can find there will be important conversions that are missed. Converting xfs is an interesting challenge because of the way xfs handles it's inode data is very atypical. XFS does two things no other filesystem in linux does. XFS dumps it's in-memory inode structure directly into the on-disk journal without any conversion. After an inode has been evicted from vfs inode cache XFS continues to cache the inode for a time, so that if the inode is needed before all of the state for the inode has been written to disk an uptodate copy can be obtained from the in-memory cached inode. Interacting with users in different user namespaces for filesystems for the most part is easy. The vfs data structures hand off kuids and kgids to the filesystem. The filesystem then places those kuids and kgids in it's in memory data structures (if it has any beyond struct inode). When data is read from disk the uid and gid values are converted from values in the initial user namespace to kuid and kgid values. When data is written to disk the kuids and kgids are converted into uid and gid values in the initial user namespace. The initial user namespace is chosen for data on disk, because that is the user namespace that the data on disk uses for unconverted filesystems. When interacting with userspace processes the values are stored in the current user namespace, which is different for each process. For example in this chunk of code that has caused some questions what is happening is: + if (mask & FSX_PROJID) { + projid = make_kprojid(current_user_ns(), fa->fsx_projid); + if (!projid_valid(projid)) + return XFS_ERROR(EINVAL); fsx_projid is coming from userspace so we convert it from whatever the userspace value is in the current user namespace to a kprojid. + /* + * Disallow 32bit project ids when projid32bit feature is not enabled. + */ + if ((from_kprojid(&init_user_ns, projid) > (__uint16_t)-1) && The disk might only support 16bit project ids. So the kprojid is converted into a projid in the initial user namespace to see what the value we will eventually try to store on-disk is. If the on-disk value is larger than (2^16-1) an error is flagged. + !xfs_sb_version_hasprojid32bit(&ip->i_mount->m_sb)) + return XFS_ERROR(EINVAL); + } In earlier versions of this patchset I have run afoul of the fact that the in-memory inode is dumped to disk making a change to that data structure an ABI change, and then I ran afoul of the fact that despite the fact that struct xfs_inode survives the embedded struct inode may be evicted from the vfs and become invalid and all of it's contents stomped with inode_init_always. Given the number of ioctls that xfs supports it would be irresponsible to do anything except insist that kuids, kgids, and kprojids are used in all of in memory data structures of xfs, as otherwise it becomes trivially easy to miss a needed conversion with the advent of a new ioctl. It has been suggested that kuids, and kgids are a vfs construct and should stop at the vfs and should not be used in xfs data structures. They are not a vfs construct they are a kernel construct and are used everywhere in the kernel. xfs does not get to be an exception. To put kuids, kgids, and kprojids in all of the xfs data structures without breaking the on-disk ABI, this patchset moves struct xfs_icdinode from struct xfs_inode to xfs_log_item, and introduces a set of conversion functions. Introducing the separation between on-disk and in-memory format that is needed to properly perform this conversion. I have a few additional patches not included in this posting sitting in my development tree that removes the extra copie that this change introduces into xfs_inode_item_format. xfstests in this instance are boring the same 17 tests keep failing both before and after my changes. I don't care through which tree these changes are merged. If you would like to take these in through xfs tree that would be great. Otherwise I will be happy to take these changes through my user namespace tree. Eric Eric W. Biederman (14): xfs: Convert uids and gids in xfs acls to/from kuids and kgids xfs: Separate the in core and the logged inode. xfs: Store projectid as a single variable. xfs: Update inode uids, gids, and projids to be kuids, kgids, and kprojids xfs: Update xfs_ioctl_setattr to handle projids in any user namespace xfs: Use kuids and kgids in xfs_setattr_nonsize xfs: Update ioctl(XFS_IOC_FREE_EOFBLOCKS) to handle callers in any userspace xfs: Use kprojids when allocating inodes. xfs: Modify xfs_qm_vop_dqalloc to take kuids, kgids, and kprojids. xfs: Push struct kqid into xfs_qm_scall_qmlim and xfs_qm_scall_getquota xfs: Modify xfs_qm_dqget to take a struct kqid. xfs: Remember the kqid for a quota xfs: Use q_id instead of q_core.d_id. xfs: Enable building with user namespaces enabled. fs/xfs/xfs_acl.c | 23 ++++++- fs/xfs/xfs_dquot.c | 39 ++++++++---- fs/xfs/xfs_dquot.h | 13 +++- fs/xfs/xfs_icache.c | 14 ++-- fs/xfs/xfs_icache.h | 11 +++- fs/xfs/xfs_inode.c | 160 +++++++++++++++++++++++++++++++++------------- fs/xfs/xfs_inode.h | 51 +++++++++------ fs/xfs/xfs_inode_item.c | 3 +- fs/xfs/xfs_inode_item.h | 1 + fs/xfs/xfs_ioctl.c | 52 ++++++++++++--- fs/xfs/xfs_iops.c | 14 ++-- fs/xfs/xfs_itable.c | 47 +++++++------- fs/xfs/xfs_qm.c | 83 ++++++++++++------------ fs/xfs/xfs_qm.h | 4 +- fs/xfs/xfs_qm_bhv.c | 2 +- fs/xfs/xfs_qm_syscalls.c | 24 ++++--- fs/xfs/xfs_quota.h | 4 +- fs/xfs/xfs_quotaops.c | 20 +----- fs/xfs/xfs_rename.c | 2 +- fs/xfs/xfs_trace.h | 2 +- fs/xfs/xfs_trans_dquot.c | 8 +-- fs/xfs/xfs_utils.c | 2 +- fs/xfs/xfs_utils.h | 2 +- fs/xfs/xfs_vnodeops.c | 14 ++-- init/Kconfig | 1 - 25 files changed, 366 insertions(+), 230 deletions(-) From ebiederm@xmission.com Wed Mar 13 17:24:07 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 9687A7F4C for ; Wed, 13 Mar 2013 17:24:07 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay3.corp.sgi.com (Postfix) with ESMTP id 2ED01AC001 for ; Wed, 13 Mar 2013 15:24:07 -0700 (PDT) X-ASG-Debug-ID: 1363213445-04bdf00a0d8c7e0001-NocioJ Received: from out01.mta.xmission.com (out01.mta.xmission.com [166.70.13.231]) by cuda.sgi.com with ESMTP id TMTUJbpf4ENxV7ao (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO); Wed, 13 Mar 2013 15:24:05 -0700 (PDT) X-Barracuda-Envelope-From: ebiederm@xmission.com X-Barracuda-Apparent-Source-IP: 166.70.13.231 Received: from in02.mta.xmission.com ([166.70.13.52]) by out01.mta.xmission.com with esmtps (TLS1.0:RSA_AES_256_CBC_SHA1:32) (Exim 4.76) (envelope-from ) id 1UFu5c-0001BK-9d; Wed, 13 Mar 2013 16:24:04 -0600 Received: from mfd0536d0.tmodns.net ([208.54.5.253] helo=localhost.localdomain) by in02.mta.xmission.com with esmtpsa (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.76) (envelope-from ) id 1UFu5U-0007mg-RI; Wed, 13 Mar 2013 16:24:04 -0600 From: "Eric W. Biederman" To: Cc: Linux Containers , "Serge E. Hallyn" , xfs@oss.sgi.com, Ben Myers , Alex Elder , Dave Chinner , "Eric W. Biederman" Date: Wed, 13 Mar 2013 15:23:02 -0700 Message-Id: <1363213395-10988-1-git-send-email-ebiederm@xmission.com> X-Mailer: git-send-email 1.7.5.4 In-Reply-To: <87boan3prc.fsf@xmission.com> References: <87boan3prc.fsf@xmission.com> X-XM-AID: U2FsdGVkX1/tt33Xs54VtOsxeJeI44D0dahEyALgtNI= X-SA-Exim-Connect-IP: 208.54.5.253 X-SA-Exim-Mail-From: ebiederm@xmission.com Subject: [PATCH 01/14] xfs: Convert uids and gids in xfs acls to/from kuids and kgids X-ASG-Orig-Subj: [PATCH 01/14] xfs: Convert uids and gids in xfs acls to/from kuids and kgids X-SA-Exim-Version: 4.2.1 (built Wed, 14 Nov 2012 14:26:46 -0700) X-SA-Exim-Scanned: Yes (on in02.mta.xmission.com) X-Barracuda-Connect: out01.mta.xmission.com[166.70.13.231] X-Barracuda-Start-Time: 1363213445 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_MISMATCH_TO X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125122 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 BSF_SC0_MISMATCH_TO Envelope rcpt doesn't match header From: "Eric W. Biederman" - When reading from disk convert on disk uids and gids to kuids and kgids - When writing to the disk convert in memory kuids and kgids to uids and gids. - Don't write e_id as that field only exists when user namespace support is disabled. - Use uid_eq when testing to see if current_fsuid() is allowed to set the acls for a file. Cc: Ben Myers Cc: Alex Elder Cc: Dave Chinner Signed-off-by: "Eric W. Biederman" --- fs/xfs/xfs_acl.c | 23 +++++++++++++++++++---- 1 files changed, 19 insertions(+), 4 deletions(-) diff --git a/fs/xfs/xfs_acl.c b/fs/xfs/xfs_acl.c index 1d32f1d..ca2aade 100644 --- a/fs/xfs/xfs_acl.c +++ b/fs/xfs/xfs_acl.c @@ -64,14 +64,17 @@ xfs_acl_from_disk(struct xfs_acl *aclp) switch (acl_e->e_tag) { case ACL_USER: + acl_e->e_uid = make_kuid(&init_user_ns, + be32_to_cpu(ace->ae_id)); + break; case ACL_GROUP: - acl_e->e_id = be32_to_cpu(ace->ae_id); + acl_e->e_gid = make_kgid(&init_user_ns, + be32_to_cpu(ace->ae_id)); break; case ACL_USER_OBJ: case ACL_GROUP_OBJ: case ACL_MASK: case ACL_OTHER: - acl_e->e_id = ACL_UNDEFINED_ID; break; default: goto fail; @@ -97,8 +100,20 @@ xfs_acl_to_disk(struct xfs_acl *aclp, const struct posix_acl *acl) acl_e = &acl->a_entries[i]; ace->ae_tag = cpu_to_be32(acl_e->e_tag); - ace->ae_id = cpu_to_be32(acl_e->e_id); ace->ae_perm = cpu_to_be16(acl_e->e_perm); + switch(acl_e->e_tag) { + case ACL_USER: + ace->ae_id = cpu_to_be32( + from_kuid(&init_user_ns, acl_e->e_uid)); + break; + case ACL_GROUP: + ace->ae_id = cpu_to_be32( + from_kgid(&init_user_ns, acl_e->e_gid)); + break; + default: + ace->ae_id = cpu_to_be32(ACL_UNDEFINED_ID); + break; + } } } @@ -355,7 +370,7 @@ xfs_xattr_acl_set(struct dentry *dentry, const char *name, return -EINVAL; if (type == ACL_TYPE_DEFAULT && !S_ISDIR(inode->i_mode)) return value ? -EACCES : 0; - if ((current_fsuid() != inode->i_uid) && !capable(CAP_FOWNER)) + if ((!uid_eq(current_fsuid(), inode->i_uid)) && !capable(CAP_FOWNER)) return -EPERM; if (!value) -- 1.7.5.4 From ebiederm@xmission.com Wed Mar 13 17:24:18 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 2810D7F4C for ; Wed, 13 Mar 2013 17:24:18 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay1.corp.sgi.com (Postfix) with ESMTP id F0CF28F804C for ; Wed, 13 Mar 2013 15:24:17 -0700 (PDT) X-ASG-Debug-ID: 1363213455-04cbb04b847d960001-NocioJ Received: from out01.mta.xmission.com (out01.mta.xmission.com [166.70.13.231]) by cuda.sgi.com with ESMTP id Mp3mloFBphbqyTu7 (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO); Wed, 13 Mar 2013 15:24:16 -0700 (PDT) X-Barracuda-Envelope-From: ebiederm@xmission.com X-Barracuda-Apparent-Source-IP: 166.70.13.231 Received: from in02.mta.xmission.com ([166.70.13.52]) by out01.mta.xmission.com with esmtps (TLS1.0:RSA_AES_256_CBC_SHA1:32) (Exim 4.76) (envelope-from ) id 1UFu5n-0001Et-3j; Wed, 13 Mar 2013 16:24:15 -0600 Received: from mfd0536d0.tmodns.net ([208.54.5.253] helo=localhost.localdomain) by in02.mta.xmission.com with esmtpsa (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.76) (envelope-from ) id 1UFu5e-0007mg-Lo; Wed, 13 Mar 2013 16:24:14 -0600 From: "Eric W. Biederman" To: Cc: Linux Containers , "Serge E. Hallyn" , xfs@oss.sgi.com, Ben Myers , Alex Elder , Dave Chinner , "Eric W. Biederman" Date: Wed, 13 Mar 2013 15:23:03 -0700 Message-Id: <1363213395-10988-2-git-send-email-ebiederm@xmission.com> X-Mailer: git-send-email 1.7.5.4 In-Reply-To: <1363213395-10988-1-git-send-email-ebiederm@xmission.com> References: <87boan3prc.fsf@xmission.com> <1363213395-10988-1-git-send-email-ebiederm@xmission.com> X-XM-AID: U2FsdGVkX1+18WIoRVI08PHtwMNG/4krtRbJAy3TZj8= X-SA-Exim-Connect-IP: 208.54.5.253 X-SA-Exim-Mail-From: ebiederm@xmission.com Subject: [PATCH 02/14] xfs: Separate the in core and the logged inode. X-ASG-Orig-Subj: [PATCH 02/14] xfs: Separate the in core and the logged inode. X-SA-Exim-Version: 4.2.1 (built Wed, 14 Nov 2012 14:26:46 -0700) X-SA-Exim-Scanned: Yes (on in02.mta.xmission.com) X-Barracuda-Connect: out01.mta.xmission.com[166.70.13.231] X-Barracuda-Start-Time: 1363213456 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_MISMATCH_TO X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125122 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 BSF_SC0_MISMATCH_TO Envelope rcpt doesn't match header From: "Eric W. Biederman" Add xfs_inode_from_disk xfs_inode_to_disk and xfs_inode_to_log to handle changes. Add an extra copy of struct xfs_icdinode into struct xfs_inode_log_item ultimately it will be the only copy but for the moment it is a temporary copy. In struct xfs_inode change the type of i_d to an anonymous structure with all of the same members as struct xfs_icdinode. Modify the two places that create a pointer to ip->i_d as a shortcut to get shorter names to use ip->i_d directly. Cc: Ben Myers Cc: Alex Elder Cc: Dave Chinner Signed-off-by: "Eric W. Biederman" --- fs/xfs/xfs_icache.c | 2 +- fs/xfs/xfs_inode.c | 138 ++++++++++++++++++++++++++++++++++------------- fs/xfs/xfs_inode.h | 31 ++++++++++- fs/xfs/xfs_inode_item.c | 3 +- fs/xfs/xfs_inode_item.h | 1 + fs/xfs/xfs_itable.c | 45 +++++++-------- 6 files changed, 155 insertions(+), 65 deletions(-) diff --git a/fs/xfs/xfs_icache.c b/fs/xfs/xfs_icache.c index 96e344e..1213f07 100644 --- a/fs/xfs/xfs_icache.c +++ b/fs/xfs/xfs_icache.c @@ -82,7 +82,7 @@ xfs_inode_alloc( memset(&ip->i_df, 0, sizeof(xfs_ifork_t)); ip->i_flags = 0; ip->i_delayed_blks = 0; - memset(&ip->i_d, 0, sizeof(xfs_icdinode_t)); + memset(&ip->i_d, 0, sizeof(ip->i_d)); return ip; } diff --git a/fs/xfs/xfs_inode.c b/fs/xfs/xfs_inode.c index 4f20165..469b9b3 100644 --- a/fs/xfs/xfs_inode.c +++ b/fs/xfs/xfs_inode.c @@ -832,40 +832,104 @@ xfs_iformat_btree( return 0; } -STATIC void -xfs_dinode_from_disk( - xfs_icdinode_t *to, - xfs_dinode_t *from) -{ - to->di_magic = be16_to_cpu(from->di_magic); - to->di_mode = be16_to_cpu(from->di_mode); - to->di_version = from ->di_version; - to->di_format = from->di_format; - to->di_onlink = be16_to_cpu(from->di_onlink); - to->di_uid = be32_to_cpu(from->di_uid); - to->di_gid = be32_to_cpu(from->di_gid); - to->di_nlink = be32_to_cpu(from->di_nlink); - to->di_projid_lo = be16_to_cpu(from->di_projid_lo); - to->di_projid_hi = be16_to_cpu(from->di_projid_hi); - memcpy(to->di_pad, from->di_pad, sizeof(to->di_pad)); - to->di_flushiter = be16_to_cpu(from->di_flushiter); - to->di_atime.t_sec = be32_to_cpu(from->di_atime.t_sec); - to->di_atime.t_nsec = be32_to_cpu(from->di_atime.t_nsec); - to->di_mtime.t_sec = be32_to_cpu(from->di_mtime.t_sec); - to->di_mtime.t_nsec = be32_to_cpu(from->di_mtime.t_nsec); - to->di_ctime.t_sec = be32_to_cpu(from->di_ctime.t_sec); - to->di_ctime.t_nsec = be32_to_cpu(from->di_ctime.t_nsec); - to->di_size = be64_to_cpu(from->di_size); - to->di_nblocks = be64_to_cpu(from->di_nblocks); - to->di_extsize = be32_to_cpu(from->di_extsize); - to->di_nextents = be32_to_cpu(from->di_nextents); - to->di_anextents = be16_to_cpu(from->di_anextents); - to->di_forkoff = from->di_forkoff; - to->di_aformat = from->di_aformat; - to->di_dmevmask = be32_to_cpu(from->di_dmevmask); - to->di_dmstate = be16_to_cpu(from->di_dmstate); - to->di_flags = be16_to_cpu(from->di_flags); - to->di_gen = be32_to_cpu(from->di_gen); +static void xfs_inode_from_disk(struct xfs_inode *to, struct xfs_dinode *from) +{ + to->i_d.di_magic = be16_to_cpu(from->di_magic); + to->i_d.di_mode = be16_to_cpu(from->di_mode); + to->i_d.di_version = from ->di_version; + to->i_d.di_format = from->di_format; + to->i_d.di_onlink = be16_to_cpu(from->di_onlink); + to->i_d.di_uid = be32_to_cpu(from->di_uid); + to->i_d.di_gid = be32_to_cpu(from->di_gid); + to->i_d.di_nlink = be32_to_cpu(from->di_nlink); + to->i_d.di_projid_lo = be16_to_cpu(from->di_projid_lo); + to->i_d.di_projid_hi = be16_to_cpu(from->di_projid_hi); + memcpy(to->i_d.di_pad, from->di_pad, sizeof(to->i_d.di_pad)); + to->i_d.di_flushiter = be16_to_cpu(from->di_flushiter); + to->i_d.di_atime.t_sec = be32_to_cpu(from->di_atime.t_sec); + to->i_d.di_atime.t_nsec = be32_to_cpu(from->di_atime.t_nsec); + to->i_d.di_mtime.t_sec = be32_to_cpu(from->di_mtime.t_sec); + to->i_d.di_mtime.t_nsec = be32_to_cpu(from->di_mtime.t_nsec); + to->i_d.di_ctime.t_sec = be32_to_cpu(from->di_ctime.t_sec); + to->i_d.di_ctime.t_nsec = be32_to_cpu(from->di_ctime.t_nsec); + to->i_d.di_size = be64_to_cpu(from->di_size); + to->i_d.di_nblocks = be64_to_cpu(from->di_nblocks); + to->i_d.di_extsize = be32_to_cpu(from->di_extsize); + to->i_d.di_nextents = be32_to_cpu(from->di_nextents); + to->i_d.di_anextents = be16_to_cpu(from->di_anextents); + to->i_d.di_forkoff = from->di_forkoff; + to->i_d.di_aformat = from->di_aformat; + to->i_d.di_dmevmask = be32_to_cpu(from->di_dmevmask); + to->i_d.di_dmstate = be16_to_cpu(from->di_dmstate); + to->i_d.di_flags = be16_to_cpu(from->di_flags); + to->i_d.di_gen = be32_to_cpu(from->di_gen); +} + +static void xfs_inode_to_disk(struct xfs_dinode *to, struct xfs_inode *from) +{ + to->di_magic = cpu_to_be16(from->i_d.di_magic); + to->di_mode = cpu_to_be16(from->i_d.di_mode); + to->di_version = from->i_d.di_version; + to->di_format = from->i_d.di_format; + to->di_onlink = cpu_to_be16(from->i_d.di_onlink); + to->di_uid = cpu_to_be32(from->i_d.di_uid); + to->di_gid = cpu_to_be32(from->i_d.di_gid); + to->di_nlink = cpu_to_be32(from->i_d.di_nlink); + to->di_projid_lo = cpu_to_be16(from->i_d.di_projid_lo); + to->di_projid_hi = cpu_to_be16(from->i_d.di_projid_hi); + memcpy(to->di_pad, from->i_d.di_pad, sizeof(to->di_pad)); + to->di_flushiter = cpu_to_be16(from->i_d.di_flushiter); + to->di_atime.t_sec = cpu_to_be32(from->i_d.di_atime.t_sec); + to->di_atime.t_nsec = cpu_to_be32(from->i_d.di_atime.t_nsec); + to->di_mtime.t_sec = cpu_to_be32(from->i_d.di_mtime.t_sec); + to->di_mtime.t_nsec = cpu_to_be32(from->i_d.di_mtime.t_nsec); + to->di_ctime.t_sec = cpu_to_be32(from->i_d.di_ctime.t_sec); + to->di_ctime.t_nsec = cpu_to_be32(from->i_d.di_ctime.t_nsec); + to->di_size = cpu_to_be64(from->i_d.di_size); + to->di_nblocks = cpu_to_be64(from->i_d.di_nblocks); + to->di_extsize = cpu_to_be32(from->i_d.di_extsize); + to->di_nextents = cpu_to_be32(from->i_d.di_nextents); + to->di_anextents = cpu_to_be16(from->i_d.di_anextents); + to->di_forkoff = from->i_d.di_forkoff; + to->di_aformat = from->i_d.di_aformat; + to->di_dmevmask = cpu_to_be32(from->i_d.di_dmevmask); + to->di_dmstate = cpu_to_be16(from->i_d.di_dmstate); + to->di_flags = cpu_to_be16(from->i_d.di_flags); + to->di_gen = cpu_to_be32(from->i_d.di_gen); +} + +void xfs_inode_to_log(struct xfs_icdinode *to, struct xfs_inode *from) +{ + /* xfs_inode_to_disk without the endian changes */ + to->di_magic = from->i_d.di_magic; + to->di_mode = from->i_d.di_mode; + to->di_version = from->i_d.di_version; + to->di_format = from->i_d.di_format; + to->di_onlink = from->i_d.di_onlink; + to->di_uid = from->i_d.di_uid; + to->di_gid = from->i_d.di_gid; + to->di_nlink = from->i_d.di_nlink; + to->di_projid_lo = from->i_d.di_projid_lo; + to->di_projid_hi = from->i_d.di_projid_hi; + memcpy(to->di_pad, from->i_d.di_pad, sizeof(to->di_pad)); + to->di_flushiter = from->i_d.di_flushiter; + to->di_atime.t_sec = from->i_d.di_atime.t_sec; + to->di_atime.t_nsec = from->i_d.di_atime.t_nsec; + to->di_mtime.t_sec = from->i_d.di_mtime.t_sec; + to->di_mtime.t_nsec = from->i_d.di_mtime.t_nsec; + to->di_ctime.t_sec = from->i_d.di_ctime.t_sec; + to->di_ctime.t_nsec = from->i_d.di_ctime.t_nsec; + to->di_size = from->i_d.di_size; + to->di_nblocks = from->i_d.di_nblocks; + to->di_extsize = from->i_d.di_extsize; + to->di_nextents = from->i_d.di_nextents; + to->di_anextents = from->i_d.di_anextents; + to->di_forkoff = from->i_d.di_forkoff; + to->di_aformat = from->i_d.di_aformat; + to->di_dmevmask = from->i_d.di_dmevmask; + to->di_dmstate = from->i_d.di_dmstate; + to->di_flags = from->i_d.di_flags; + to->di_gen = from->i_d.di_gen; } void @@ -948,9 +1012,7 @@ uint xfs_ip2xflags( xfs_inode_t *ip) { - xfs_icdinode_t *dic = &ip->i_d; - - return _xfs_dic2xflags(dic->di_flags) | + return _xfs_dic2xflags(ip->i_d.di_flags) | (XFS_IFORK_Q(ip) ? XFS_XFLAG_HASATTR : 0); } @@ -1012,7 +1074,7 @@ xfs_iread( * Otherwise, just get the truly permanent information. */ if (dip->di_mode) { - xfs_dinode_from_disk(&ip->i_d, dip); + xfs_inode_from_disk(ip, dip); error = xfs_iformat(ip, dip); if (error) { #ifdef DEBUG @@ -2800,7 +2862,7 @@ xfs_iflush_int( * because if the inode is dirty at all the core must * be. */ - xfs_dinode_to_disk(dip, &ip->i_d); + xfs_inode_to_disk(dip, ip); /* Wrap, we never let the log put out DI_MAX_FLUSH */ if (ip->i_d.di_flushiter == DI_MAX_FLUSH) diff --git a/fs/xfs/xfs_inode.h b/fs/xfs/xfs_inode.h index 237e7f6..977f1d8 100644 --- a/fs/xfs/xfs_inode.h +++ b/fs/xfs/xfs_inode.h @@ -243,7 +243,34 @@ typedef struct xfs_inode { unsigned long i_flags; /* see defined flags below */ unsigned int i_delayed_blks; /* count of delay alloc blks */ - xfs_icdinode_t i_d; /* most of ondisk inode */ + struct { + u16 di_magic; /* inode magic # = XFS_DINODE_MAGIC */ + u16 di_mode; /* mode and type of file */ + s8 di_version; /* inode version */ + s8 di_format; /* format of di_c data */ + u16 di_onlink; /* old number of links to file */ + u32 di_uid; /* owner's user id */ + u32 di_gid; /* owner's group id */ + u32 di_nlink; /* number of links to file */ + u16 di_projid_lo; /* lower part of owner's project id */ + u16 di_projid_hi; /* higher part of owner's project id */ + u8 di_pad[6]; /* unused, zeroed space */ + u16 di_flushiter; /* incremented on flush */ + xfs_ictimestamp_t di_atime; /* time last accessed */ + xfs_ictimestamp_t di_mtime; /* time last modified */ + xfs_ictimestamp_t di_ctime; /* time created/inode modified */ + xfs_fsize_t di_size; /* number of bytes in file */ + xfs_drfsbno_t di_nblocks; /* # of direct & btree blocks used */ + xfs_extlen_t di_extsize; /* basic/minimum extent size for file */ + xfs_extnum_t di_nextents; /* number of extents in data fork */ + xfs_aextnum_t di_anextents; /* number of extents in attribute fork*/ + u8 di_forkoff; /* attr fork offs, <<3 for 64b align */ + s8 di_aformat; /* format of attr fork's data */ + u32 di_dmevmask; /* DMIG event mask */ + u16 di_dmstate; /* DMIG state info */ + u16 di_flags; /* random flags, XFS_DIFLAG_... */ + u32 di_gen; /* generation number */ + } i_d; /* most of ondisk inode */ /* VFS inode */ struct inode i_vnode; /* embedded VFS inode */ @@ -550,6 +577,8 @@ do { \ #define XFS_IGET_UNTRUSTED 0x2 #define XFS_IGET_DONTCACHE 0x4 +void xfs_inode_to_log(struct xfs_icdinode *to, struct xfs_inode *from); + int xfs_imap_to_bp(struct xfs_mount *, struct xfs_trans *, struct xfs_imap *, struct xfs_dinode **, struct xfs_buf **, uint, uint); diff --git a/fs/xfs/xfs_inode_item.c b/fs/xfs/xfs_inode_item.c index f034bd1..6be81b6 100644 --- a/fs/xfs/xfs_inode_item.c +++ b/fs/xfs/xfs_inode_item.c @@ -178,7 +178,7 @@ xfs_inode_item_format( vecp++; nvecs = 1; - vecp->i_addr = &ip->i_d; + vecp->i_addr = &iip->ili_d; vecp->i_len = sizeof(struct xfs_icdinode); vecp->i_type = XLOG_REG_TYPE_ICORE; vecp++; @@ -212,6 +212,7 @@ xfs_inode_item_format( memset(&(ip->i_d.di_pad[0]), 0, sizeof(ip->i_d.di_pad)); } } + xfs_inode_to_log(&iip->ili_d, ip); switch (ip->i_d.di_format) { case XFS_DINODE_FMT_EXTENTS: diff --git a/fs/xfs/xfs_inode_item.h b/fs/xfs/xfs_inode_item.h index 779812f..9e66a39 100644 --- a/fs/xfs/xfs_inode_item.h +++ b/fs/xfs/xfs_inode_item.h @@ -138,6 +138,7 @@ struct xfs_mount; typedef struct xfs_inode_log_item { xfs_log_item_t ili_item; /* common portion */ struct xfs_inode *ili_inode; /* inode ptr */ + struct xfs_icdinode ili_d; /* most of ondisk inode */ xfs_lsn_t ili_flush_lsn; /* lsn at last flush */ xfs_lsn_t ili_last_lsn; /* lsn at last transaction */ unsigned short ili_lock_flags; /* lock flags */ diff --git a/fs/xfs/xfs_itable.c b/fs/xfs/xfs_itable.c index 2ea7d40..dfb7f71 100644 --- a/fs/xfs/xfs_itable.c +++ b/fs/xfs/xfs_itable.c @@ -60,7 +60,6 @@ xfs_bulkstat_one_int( int *ubused, /* bytes used by me */ int *stat) /* BULKSTAT_RV_... */ { - struct xfs_icdinode *dic; /* dinode core info pointer */ struct xfs_inode *ip; /* incore inode pointer */ struct xfs_bstat *buf; /* return buffer */ int error = 0; /* error value */ @@ -85,36 +84,34 @@ xfs_bulkstat_one_int( ASSERT(ip != NULL); ASSERT(ip->i_imap.im_blkno != 0); - dic = &ip->i_d; - /* xfs_iget returns the following without needing * further change. */ - buf->bs_nlink = dic->di_nlink; - buf->bs_projid_lo = dic->di_projid_lo; - buf->bs_projid_hi = dic->di_projid_hi; + buf->bs_nlink = ip->i_d.di_nlink; + buf->bs_projid_lo = ip->i_d.di_projid_lo; + buf->bs_projid_hi = ip->i_d.di_projid_hi; buf->bs_ino = ino; - buf->bs_mode = dic->di_mode; - buf->bs_uid = dic->di_uid; - buf->bs_gid = dic->di_gid; - buf->bs_size = dic->di_size; - buf->bs_atime.tv_sec = dic->di_atime.t_sec; - buf->bs_atime.tv_nsec = dic->di_atime.t_nsec; - buf->bs_mtime.tv_sec = dic->di_mtime.t_sec; - buf->bs_mtime.tv_nsec = dic->di_mtime.t_nsec; - buf->bs_ctime.tv_sec = dic->di_ctime.t_sec; - buf->bs_ctime.tv_nsec = dic->di_ctime.t_nsec; + buf->bs_mode = ip->i_d.di_mode; + buf->bs_uid = ip->i_d.di_uid; + buf->bs_gid = ip->i_d.di_gid; + buf->bs_size = ip->i_d.di_size; + buf->bs_atime.tv_sec = ip->i_d.di_atime.t_sec; + buf->bs_atime.tv_nsec = ip->i_d.di_atime.t_nsec; + buf->bs_mtime.tv_sec = ip->i_d.di_mtime.t_sec; + buf->bs_mtime.tv_nsec = ip->i_d.di_mtime.t_nsec; + buf->bs_ctime.tv_sec = ip->i_d.di_ctime.t_sec; + buf->bs_ctime.tv_nsec = ip->i_d.di_ctime.t_nsec; buf->bs_xflags = xfs_ip2xflags(ip); - buf->bs_extsize = dic->di_extsize << mp->m_sb.sb_blocklog; - buf->bs_extents = dic->di_nextents; - buf->bs_gen = dic->di_gen; + buf->bs_extsize = ip->i_d.di_extsize << mp->m_sb.sb_blocklog; + buf->bs_extents = ip->i_d.di_nextents; + buf->bs_gen = ip->i_d.di_gen; memset(buf->bs_pad, 0, sizeof(buf->bs_pad)); - buf->bs_dmevmask = dic->di_dmevmask; - buf->bs_dmstate = dic->di_dmstate; - buf->bs_aextents = dic->di_anextents; + buf->bs_dmevmask = ip->i_d.di_dmevmask; + buf->bs_dmstate = ip->i_d.di_dmstate; + buf->bs_aextents = ip->i_d.di_anextents; buf->bs_forkoff = XFS_IFORK_BOFF(ip); - switch (dic->di_format) { + switch (ip->i_d.di_format) { case XFS_DINODE_FMT_DEV: buf->bs_rdev = ip->i_df.if_u2.if_rdev; buf->bs_blksize = BLKDEV_IOSIZE; @@ -130,7 +127,7 @@ xfs_bulkstat_one_int( case XFS_DINODE_FMT_BTREE: buf->bs_rdev = 0; buf->bs_blksize = mp->m_sb.sb_blocksize; - buf->bs_blocks = dic->di_nblocks + ip->i_delayed_blks; + buf->bs_blocks = ip->i_d.di_nblocks + ip->i_delayed_blks; break; } xfs_iunlock(ip, XFS_ILOCK_SHARED); -- 1.7.5.4 From ebiederm@xmission.com Wed Mar 13 17:24:39 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id DC08D7F4C for ; Wed, 13 Mar 2013 17:24:39 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id B07D1304071 for ; Wed, 13 Mar 2013 15:24:36 -0700 (PDT) X-ASG-Debug-ID: 1363213474-04cbb04b867d9f0001-NocioJ Received: from out03.mta.xmission.com (out03.mta.xmission.com [166.70.13.233]) by cuda.sgi.com with ESMTP id CUDEefRT9INtl1Zf (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO); Wed, 13 Mar 2013 15:24:35 -0700 (PDT) X-Barracuda-Envelope-From: ebiederm@xmission.com X-Barracuda-Apparent-Source-IP: 166.70.13.233 Received: from in02.mta.xmission.com ([166.70.13.52]) by out03.mta.xmission.com with esmtps (TLS1.0:RSA_AES_256_CBC_SHA1:32) (Exim 4.76) (envelope-from ) id 1UFu65-0005eN-Vv; Wed, 13 Mar 2013 16:24:34 -0600 Received: from mfd0536d0.tmodns.net ([208.54.5.253] helo=localhost.localdomain) by in02.mta.xmission.com with esmtpsa (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.76) (envelope-from ) id 1UFu5z-0007mg-A7; Wed, 13 Mar 2013 16:24:33 -0600 From: "Eric W. Biederman" To: Cc: Linux Containers , "Serge E. Hallyn" , xfs@oss.sgi.com, Ben Myers , Alex Elder , Dave Chinner , "Eric W. Biederman" Date: Wed, 13 Mar 2013 15:23:04 -0700 Message-Id: <1363213395-10988-3-git-send-email-ebiederm@xmission.com> X-Mailer: git-send-email 1.7.5.4 In-Reply-To: <1363213395-10988-1-git-send-email-ebiederm@xmission.com> References: <87boan3prc.fsf@xmission.com> <1363213395-10988-1-git-send-email-ebiederm@xmission.com> X-XM-AID: U2FsdGVkX1/Kc2d5Jm3ECP7CXRI+UzM8Zee8z4xLSWk= X-SA-Exim-Connect-IP: 208.54.5.253 X-SA-Exim-Mail-From: ebiederm@xmission.com Subject: [PATCH 03/14] xfs: Store projectid as a single variable. X-ASG-Orig-Subj: [PATCH 03/14] xfs: Store projectid as a single variable. X-SA-Exim-Version: 4.2.1 (built Wed, 14 Nov 2012 14:26:46 -0700) X-SA-Exim-Scanned: Yes (on in02.mta.xmission.com) X-Barracuda-Connect: out03.mta.xmission.com[166.70.13.233] X-Barracuda-Start-Time: 1363213475 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_MISMATCH_TO X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125122 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 BSF_SC0_MISMATCH_TO Envelope rcpt doesn't match header From: "Eric W. Biederman" xfs_get_projid is torturous to read and when you don't have the justification of maintaining an on-disk ABI there is really no point. So merge di_projid_lo and di_projid_hi in xfs_inode into di_projid. That is cheaper to read and cheaper to write and can handle future needs. Update all callers of xfs_get_projid and xfs_set_projid to use i_d.di_projid instead. Cc: Ben Myers Cc: Alex Elder Cc: Dave Chinner Signed-off-by: "Eric W. Biederman" --- fs/xfs/xfs_icache.c | 2 +- fs/xfs/xfs_inode.c | 18 +++++++++--------- fs/xfs/xfs_inode.h | 22 +--------------------- fs/xfs/xfs_ioctl.c | 8 ++++---- fs/xfs/xfs_iops.c | 2 +- fs/xfs/xfs_itable.c | 4 ++-- fs/xfs/xfs_qm.c | 10 +++++----- fs/xfs/xfs_qm_bhv.c | 2 +- fs/xfs/xfs_rename.c | 2 +- fs/xfs/xfs_vnodeops.c | 6 +++--- 10 files changed, 28 insertions(+), 48 deletions(-) diff --git a/fs/xfs/xfs_icache.c b/fs/xfs/xfs_icache.c index 1213f07..1f62227 100644 --- a/fs/xfs/xfs_icache.c +++ b/fs/xfs/xfs_icache.c @@ -1210,7 +1210,7 @@ xfs_inode_match_id( return 0; if (eofb->eof_flags & XFS_EOF_FLAGS_PRID && - xfs_get_projid(ip) != eofb->eof_prid) + ip->i_d.di_projid != eofb->eof_prid) return 0; return 1; diff --git a/fs/xfs/xfs_inode.c b/fs/xfs/xfs_inode.c index 469b9b3..f6c9652 100644 --- a/fs/xfs/xfs_inode.c +++ b/fs/xfs/xfs_inode.c @@ -842,8 +842,8 @@ static void xfs_inode_from_disk(struct xfs_inode *to, struct xfs_dinode *from) to->i_d.di_uid = be32_to_cpu(from->di_uid); to->i_d.di_gid = be32_to_cpu(from->di_gid); to->i_d.di_nlink = be32_to_cpu(from->di_nlink); - to->i_d.di_projid_lo = be16_to_cpu(from->di_projid_lo); - to->i_d.di_projid_hi = be16_to_cpu(from->di_projid_hi); + to->i_d.di_projid = (((u32)be16_to_cpu(from->di_projid_hi)) << 16) | + be16_to_cpu(from->di_projid_lo); memcpy(to->i_d.di_pad, from->di_pad, sizeof(to->i_d.di_pad)); to->i_d.di_flushiter = be16_to_cpu(from->di_flushiter); to->i_d.di_atime.t_sec = be32_to_cpu(from->di_atime.t_sec); @@ -875,8 +875,8 @@ static void xfs_inode_to_disk(struct xfs_dinode *to, struct xfs_inode *from) to->di_uid = cpu_to_be32(from->i_d.di_uid); to->di_gid = cpu_to_be32(from->i_d.di_gid); to->di_nlink = cpu_to_be32(from->i_d.di_nlink); - to->di_projid_lo = cpu_to_be16(from->i_d.di_projid_lo); - to->di_projid_hi = cpu_to_be16(from->i_d.di_projid_hi); + to->di_projid_lo = cpu_to_be16(from->i_d.di_projid & 0xffff); + to->di_projid_hi = cpu_to_be16(from->i_d.di_projid >> 16); memcpy(to->di_pad, from->i_d.di_pad, sizeof(to->di_pad)); to->di_flushiter = cpu_to_be16(from->i_d.di_flushiter); to->di_atime.t_sec = cpu_to_be32(from->i_d.di_atime.t_sec); @@ -909,8 +909,8 @@ void xfs_inode_to_log(struct xfs_icdinode *to, struct xfs_inode *from) to->di_uid = from->i_d.di_uid; to->di_gid = from->i_d.di_gid; to->di_nlink = from->i_d.di_nlink; - to->di_projid_lo = from->i_d.di_projid_lo; - to->di_projid_hi = from->i_d.di_projid_hi; + to->di_projid_lo = from->i_d.di_projid & 0xffff; + to->di_projid_hi = from->i_d.di_projid >> 16; memcpy(to->di_pad, from->i_d.di_pad, sizeof(to->di_pad)); to->di_flushiter = from->i_d.di_flushiter; to->di_atime.t_sec = from->i_d.di_atime.t_sec; @@ -1112,7 +1112,7 @@ xfs_iread( if (ip->i_d.di_version == 1) { ip->i_d.di_nlink = ip->i_d.di_onlink; ip->i_d.di_onlink = 0; - xfs_set_projid(ip, 0); + ip->i_d.di_projid = 0; } ip->i_delayed_blks = 0; @@ -1261,7 +1261,7 @@ xfs_ialloc( ASSERT(ip->i_d.di_nlink == nlink); ip->i_d.di_uid = current_fsuid(); ip->i_d.di_gid = current_fsgid(); - xfs_set_projid(ip, prid); + ip->i_d.di_projid = prid; memset(&(ip->i_d.di_pad[0]), 0, sizeof(ip->i_d.di_pad)); /* @@ -2895,7 +2895,7 @@ xfs_iflush_int( memset(&(ip->i_d.di_pad[0]), 0, sizeof(ip->i_d.di_pad)); memset(&(dip->di_pad[0]), 0, sizeof(dip->di_pad)); - ASSERT(xfs_get_projid(ip) == 0); + ASSERT(ip->i_d.di_projid == 0); } } diff --git a/fs/xfs/xfs_inode.h b/fs/xfs/xfs_inode.h index 977f1d8..a722f7a 100644 --- a/fs/xfs/xfs_inode.h +++ b/fs/xfs/xfs_inode.h @@ -252,8 +252,7 @@ typedef struct xfs_inode { u32 di_uid; /* owner's user id */ u32 di_gid; /* owner's group id */ u32 di_nlink; /* number of links to file */ - u16 di_projid_lo; /* lower part of owner's project id */ - u16 di_projid_hi; /* higher part of owner's project id */ + projid_t di_projid; /* owner's project id */ u8 di_pad[6]; /* unused, zeroed space */ u16 di_flushiter; /* incremented on flush */ xfs_ictimestamp_t di_atime; /* time last accessed */ @@ -382,25 +381,6 @@ xfs_iflags_test_and_set(xfs_inode_t *ip, unsigned short flags) } /* - * Project quota id helpers (previously projid was 16bit only - * and using two 16bit values to hold new 32bit projid was chosen - * to retain compatibility with "old" filesystems). - */ -static inline prid_t -xfs_get_projid(struct xfs_inode *ip) -{ - return (prid_t)ip->i_d.di_projid_hi << 16 | ip->i_d.di_projid_lo; -} - -static inline void -xfs_set_projid(struct xfs_inode *ip, - prid_t projid) -{ - ip->i_d.di_projid_hi = (__uint16_t) (projid >> 16); - ip->i_d.di_projid_lo = (__uint16_t) (projid & 0xffff); -} - -/* * In-core inode flags. */ #define XFS_IRECLAIM (1 << 0) /* started reclaiming this inode */ diff --git a/fs/xfs/xfs_ioctl.c b/fs/xfs/xfs_ioctl.c index d681e34..79e9b13 100644 --- a/fs/xfs/xfs_ioctl.c +++ b/fs/xfs/xfs_ioctl.c @@ -815,7 +815,7 @@ xfs_ioc_fsgetxattr( xfs_ilock(ip, XFS_ILOCK_SHARED); fa.fsx_xflags = xfs_ip2xflags(ip); fa.fsx_extsize = ip->i_d.di_extsize << ip->i_mount->m_sb.sb_blocklog; - fa.fsx_projid = xfs_get_projid(ip); + fa.fsx_projid = ip->i_d.di_projid; if (attr) { if (ip->i_afp) { @@ -986,7 +986,7 @@ xfs_ioctl_setattr( if (mask & FSX_PROJID) { if (XFS_IS_QUOTA_RUNNING(mp) && XFS_IS_PQUOTA_ON(mp) && - xfs_get_projid(ip) != fa->fsx_projid) { + ip->i_d.di_projid != fa->fsx_projid) { ASSERT(tp); code = xfs_qm_vop_chown_reserve(tp, ip, udqp, gdqp, capable(CAP_FOWNER) ? @@ -1104,12 +1104,12 @@ xfs_ioctl_setattr( * Change the ownerships and register quota modifications * in the transaction. */ - if (xfs_get_projid(ip) != fa->fsx_projid) { + if (ip->i_d.di_projid != fa->fsx_projid) { if (XFS_IS_QUOTA_RUNNING(mp) && XFS_IS_PQUOTA_ON(mp)) { olddquot = xfs_qm_vop_chown(tp, ip, &ip->i_gdquot, gdqp); } - xfs_set_projid(ip, fa->fsx_projid); + ip->i_d.di_projid = fa->fsx_projid; /* * We may have to rev the inode as well as diff --git a/fs/xfs/xfs_iops.c b/fs/xfs/xfs_iops.c index d82efaa..a69ddfd 100644 --- a/fs/xfs/xfs_iops.c +++ b/fs/xfs/xfs_iops.c @@ -516,7 +516,7 @@ xfs_setattr_nonsize( */ ASSERT(udqp == NULL); ASSERT(gdqp == NULL); - error = xfs_qm_vop_dqalloc(ip, uid, gid, xfs_get_projid(ip), + error = xfs_qm_vop_dqalloc(ip, uid, gid, ip->i_d.di_projid, qflags, &udqp, &gdqp); if (error) return error; diff --git a/fs/xfs/xfs_itable.c b/fs/xfs/xfs_itable.c index dfb7f71..3529f2e 100644 --- a/fs/xfs/xfs_itable.c +++ b/fs/xfs/xfs_itable.c @@ -88,8 +88,8 @@ xfs_bulkstat_one_int( * further change. */ buf->bs_nlink = ip->i_d.di_nlink; - buf->bs_projid_lo = ip->i_d.di_projid_lo; - buf->bs_projid_hi = ip->i_d.di_projid_hi; + buf->bs_projid_lo = (u16)(ip->i_d.di_projid & 0xffff); + buf->bs_projid_hi = (u16)(ip->i_d.di_projid >> 16); buf->bs_ino = ino; buf->bs_mode = ip->i_d.di_mode; buf->bs_uid = ip->i_d.di_uid; diff --git a/fs/xfs/xfs_qm.c b/fs/xfs/xfs_qm.c index e5b5cf9..c0904fc 100644 --- a/fs/xfs/xfs_qm.c +++ b/fs/xfs/xfs_qm.c @@ -530,7 +530,7 @@ xfs_qm_dqattach_locked( xfs_qm_dqattach_one(ip, ip->i_d.di_gid, XFS_DQ_GROUP, flags & XFS_QMOPT_DQALLOC, ip->i_udquot, &ip->i_gdquot) : - xfs_qm_dqattach_one(ip, xfs_get_projid(ip), XFS_DQ_PROJ, + xfs_qm_dqattach_one(ip, ip->i_d.di_projid, XFS_DQ_PROJ, flags & XFS_QMOPT_DQALLOC, ip->i_udquot, &ip->i_gdquot); /* @@ -1172,7 +1172,7 @@ xfs_qm_dqusage_adjust( } if (XFS_IS_PQUOTA_ON(mp)) { - error = xfs_qm_quotacheck_dqadjust(ip, xfs_get_projid(ip), + error = xfs_qm_quotacheck_dqadjust(ip, ip->i_d.di_projid, XFS_DQ_PROJ, nblks, rtblks); if (error) goto error0; @@ -1704,7 +1704,7 @@ xfs_qm_vop_dqalloc( gq = xfs_qm_dqhold(ip->i_gdquot); } } else if ((flags & XFS_QMOPT_PQUOTA) && XFS_IS_PQUOTA_ON(mp)) { - if (xfs_get_projid(ip) != prid) { + if (ip->i_d.di_projid != prid) { xfs_iunlock(ip, lockflags); if ((error = xfs_qm_dqget(mp, NULL, (xfs_dqid_t)prid, XFS_DQ_PROJ, @@ -1819,7 +1819,7 @@ xfs_qm_vop_chown_reserve( } if (XFS_IS_OQUOTA_ON(ip->i_mount) && gdqp) { if (XFS_IS_PQUOTA_ON(ip->i_mount) && - xfs_get_projid(ip) != be32_to_cpu(gdqp->q_core.d_id)) + ip->i_d.di_projid != be32_to_cpu(gdqp->q_core.d_id)) prjflags = XFS_QMOPT_ENOSPC; if (prjflags || @@ -1917,7 +1917,7 @@ xfs_qm_vop_create_dqattach( ASSERT(ip->i_gdquot == NULL); ASSERT(XFS_IS_OQUOTA_ON(mp)); ASSERT((XFS_IS_GQUOTA_ON(mp) ? - ip->i_d.di_gid : xfs_get_projid(ip)) == + ip->i_d.di_gid : ip->i_d.di_projid) == be32_to_cpu(gdqp->q_core.d_id)); ip->i_gdquot = xfs_qm_dqhold(gdqp); diff --git a/fs/xfs/xfs_qm_bhv.c b/fs/xfs/xfs_qm_bhv.c index 2d02eac..7d44746 100644 --- a/fs/xfs/xfs_qm_bhv.c +++ b/fs/xfs/xfs_qm_bhv.c @@ -79,7 +79,7 @@ xfs_qm_statvfs( xfs_mount_t *mp = ip->i_mount; xfs_dquot_t *dqp; - if (!xfs_qm_dqget(mp, NULL, xfs_get_projid(ip), XFS_DQ_PROJ, 0, &dqp)) { + if (!xfs_qm_dqget(mp, NULL, ip->i_d.di_projid, XFS_DQ_PROJ, 0, &dqp)) { xfs_fill_statvfs_from_dquot(statp, dqp); xfs_qm_dqput(dqp); } diff --git a/fs/xfs/xfs_rename.c b/fs/xfs/xfs_rename.c index 30ff5f4..4e87258 100644 --- a/fs/xfs/xfs_rename.c +++ b/fs/xfs/xfs_rename.c @@ -171,7 +171,7 @@ xfs_rename( * tree quota mechanism would be circumvented. */ if (unlikely((target_dp->i_d.di_flags & XFS_DIFLAG_PROJINHERIT) && - (xfs_get_projid(target_dp) != xfs_get_projid(src_ip)))) { + (target_dp->i_d.di_projid != src_ip->i_d.di_projid))) { error = XFS_ERROR(EXDEV); goto error_return; } diff --git a/fs/xfs/xfs_vnodeops.c b/fs/xfs/xfs_vnodeops.c index 77ad748..1a9ee2c 100644 --- a/fs/xfs/xfs_vnodeops.c +++ b/fs/xfs/xfs_vnodeops.c @@ -741,7 +741,7 @@ xfs_create( return XFS_ERROR(EIO); if (dp->i_d.di_flags & XFS_DIFLAG_PROJINHERIT) - prid = xfs_get_projid(dp); + prid = dp->i_d.di_projid; else prid = XFS_PROJID_DEFAULT; @@ -1305,7 +1305,7 @@ xfs_link( * the tree quota mechanism could be circumvented. */ if (unlikely((tdp->i_d.di_flags & XFS_DIFLAG_PROJINHERIT) && - (xfs_get_projid(tdp) != xfs_get_projid(sip)))) { + (tdp->i_d.di_projid != sip->i_d.di_projid))) { error = XFS_ERROR(EXDEV); goto error_return; } @@ -1402,7 +1402,7 @@ xfs_symlink( udqp = gdqp = NULL; if (dp->i_d.di_flags & XFS_DIFLAG_PROJINHERIT) - prid = xfs_get_projid(dp); + prid = dp->i_d.di_projid; else prid = XFS_PROJID_DEFAULT; -- 1.7.5.4 From ebiederm@xmission.com Wed Mar 13 17:24:56 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 4B9C07F4C for ; Wed, 13 Mar 2013 17:24:56 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id 2DDFF30405F for ; Wed, 13 Mar 2013 15:24:56 -0700 (PDT) X-ASG-Debug-ID: 1363213494-04cbb04b847da50001-NocioJ Received: from out02.mta.xmission.com (out02.mta.xmission.com [166.70.13.232]) by cuda.sgi.com with ESMTP id dbjC1DVDIcj5QDRE (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO); Wed, 13 Mar 2013 15:24:54 -0700 (PDT) X-Barracuda-Envelope-From: ebiederm@xmission.com X-Barracuda-Apparent-Source-IP: 166.70.13.232 Received: from in02.mta.xmission.com ([166.70.13.52]) by out02.mta.xmission.com with esmtps (TLS1.0:RSA_AES_256_CBC_SHA1:32) (Exim 4.76) (envelope-from ) id 1UFu6P-0001kp-TT; Wed, 13 Mar 2013 16:24:53 -0600 Received: from mfd0536d0.tmodns.net ([208.54.5.253] helo=localhost.localdomain) by in02.mta.xmission.com with esmtpsa (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.76) (envelope-from ) id 1UFu6A-0007mg-Qr; Wed, 13 Mar 2013 16:24:53 -0600 From: "Eric W. Biederman" To: Cc: Linux Containers , "Serge E. Hallyn" , xfs@oss.sgi.com, Ben Myers , Alex Elder , Dave Chinner , "Eric W. Biederman" Date: Wed, 13 Mar 2013 15:23:05 -0700 Message-Id: <1363213395-10988-4-git-send-email-ebiederm@xmission.com> X-Mailer: git-send-email 1.7.5.4 In-Reply-To: <1363213395-10988-1-git-send-email-ebiederm@xmission.com> References: <87boan3prc.fsf@xmission.com> <1363213395-10988-1-git-send-email-ebiederm@xmission.com> X-XM-AID: U2FsdGVkX183SRcPdCHpRKI1xRMbLhAEzzHH12TX89o= X-SA-Exim-Connect-IP: 208.54.5.253 X-SA-Exim-Mail-From: ebiederm@xmission.com Subject: [PATCH 04/14] xfs: Update inode uids, gids, and projids to be kuids, kgids, and kprojids X-ASG-Orig-Subj: [PATCH 04/14] xfs: Update inode uids, gids, and projids to be kuids, kgids, and kprojids X-SA-Exim-Version: 4.2.1 (built Wed, 14 Nov 2012 14:26:46 -0700) X-SA-Exim-Scanned: Yes (on in02.mta.xmission.com) X-Barracuda-Connect: out02.mta.xmission.com[166.70.13.232] X-Barracuda-Start-Time: 1363213494 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_MISMATCH_TO X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125122 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 BSF_SC0_MISMATCH_TO Envelope rcpt doesn't match header From: "Eric W. Biederman" Update i_projid on struct xfs_inode to be of type kprojid_t. Update the logic in xfs_inode_from_disk when the values are read from disk to convert their on-disk values into the internal kernel representation. Update xfs_inode_to_disk and xfs_inode_to_log to convert from the internal kernel representation to the on-disk values when updating the on-disk fields. Update comparisons against these fields to use uid_eq, gid_eq and projid_eq. Cc: Ben Myers Cc: Alex Elder Cc: Dave Chinner Signed-off-by: "Eric W. Biederman" --- fs/xfs/xfs_icache.c | 6 +++--- fs/xfs/xfs_inode.c | 37 +++++++++++++++++++++++-------------- fs/xfs/xfs_inode.h | 6 +++--- fs/xfs/xfs_ioctl.c | 8 ++++---- fs/xfs/xfs_itable.c | 10 ++++++---- fs/xfs/xfs_qm.c | 20 ++++++++++---------- fs/xfs/xfs_rename.c | 2 +- fs/xfs/xfs_vnodeops.c | 2 +- 8 files changed, 51 insertions(+), 40 deletions(-) diff --git a/fs/xfs/xfs_icache.c b/fs/xfs/xfs_icache.c index 1f62227..03a4427 100644 --- a/fs/xfs/xfs_icache.c +++ b/fs/xfs/xfs_icache.c @@ -1202,15 +1202,15 @@ xfs_inode_match_id( struct xfs_eofblocks *eofb) { if (eofb->eof_flags & XFS_EOF_FLAGS_UID && - ip->i_d.di_uid != eofb->eof_uid) + !uid_eq(ip->i_d.di_uid, eofb->eof_uid)) return 0; if (eofb->eof_flags & XFS_EOF_FLAGS_GID && - ip->i_d.di_gid != eofb->eof_gid) + !gid_eq(ip->i_d.di_gid, eofb->eof_gid)) return 0; if (eofb->eof_flags & XFS_EOF_FLAGS_PRID && - ip->i_d.di_projid != eofb->eof_prid) + !projid_eq(ip->i_d.di_projid, eofb->eof_prid)) return 0; return 1; diff --git a/fs/xfs/xfs_inode.c b/fs/xfs/xfs_inode.c index f6c9652..8d77e49 100644 --- a/fs/xfs/xfs_inode.c +++ b/fs/xfs/xfs_inode.c @@ -834,16 +834,18 @@ xfs_iformat_btree( static void xfs_inode_from_disk(struct xfs_inode *to, struct xfs_dinode *from) { + projid_t projid; to->i_d.di_magic = be16_to_cpu(from->di_magic); to->i_d.di_mode = be16_to_cpu(from->di_mode); to->i_d.di_version = from ->di_version; to->i_d.di_format = from->di_format; to->i_d.di_onlink = be16_to_cpu(from->di_onlink); - to->i_d.di_uid = be32_to_cpu(from->di_uid); - to->i_d.di_gid = be32_to_cpu(from->di_gid); + to->i_d.di_uid = make_kuid(&init_user_ns, be32_to_cpu(from->di_uid)); + to->i_d.di_gid = make_kgid(&init_user_ns, be32_to_cpu(from->di_gid)); to->i_d.di_nlink = be32_to_cpu(from->di_nlink); - to->i_d.di_projid = (((u32)be16_to_cpu(from->di_projid_hi)) << 16) | + projid = (((u32)be16_to_cpu(from->di_projid_hi)) << 16) | be16_to_cpu(from->di_projid_lo); + to->i_d.di_projid = make_kprojid(&init_user_ns, projid); memcpy(to->i_d.di_pad, from->di_pad, sizeof(to->i_d.di_pad)); to->i_d.di_flushiter = be16_to_cpu(from->di_flushiter); to->i_d.di_atime.t_sec = be32_to_cpu(from->di_atime.t_sec); @@ -867,16 +869,19 @@ static void xfs_inode_from_disk(struct xfs_inode *to, struct xfs_dinode *from) static void xfs_inode_to_disk(struct xfs_dinode *to, struct xfs_inode *from) { + uid_t uid = from_kuid(&init_user_ns, from->i_d.di_uid); + gid_t gid = from_kgid(&init_user_ns, from->i_d.di_gid); + projid_t projid = from_kprojid(&init_user_ns, from->i_d.di_projid); to->di_magic = cpu_to_be16(from->i_d.di_magic); to->di_mode = cpu_to_be16(from->i_d.di_mode); to->di_version = from->i_d.di_version; to->di_format = from->i_d.di_format; to->di_onlink = cpu_to_be16(from->i_d.di_onlink); - to->di_uid = cpu_to_be32(from->i_d.di_uid); - to->di_gid = cpu_to_be32(from->i_d.di_gid); + to->di_uid = cpu_to_be32(uid); + to->di_gid = cpu_to_be32(gid); to->di_nlink = cpu_to_be32(from->i_d.di_nlink); - to->di_projid_lo = cpu_to_be16(from->i_d.di_projid & 0xffff); - to->di_projid_hi = cpu_to_be16(from->i_d.di_projid >> 16); + to->di_projid_lo = cpu_to_be16(projid & 0xffff); + to->di_projid_hi = cpu_to_be16(projid >> 16); memcpy(to->di_pad, from->i_d.di_pad, sizeof(to->di_pad)); to->di_flushiter = cpu_to_be16(from->i_d.di_flushiter); to->di_atime.t_sec = cpu_to_be32(from->i_d.di_atime.t_sec); @@ -901,16 +906,19 @@ static void xfs_inode_to_disk(struct xfs_dinode *to, struct xfs_inode *from) void xfs_inode_to_log(struct xfs_icdinode *to, struct xfs_inode *from) { /* xfs_inode_to_disk without the endian changes */ + uid_t uid = from_kuid(&init_user_ns, from->i_d.di_uid); + gid_t gid = from_kgid(&init_user_ns, from->i_d.di_gid); + projid_t projid = from_kprojid(&init_user_ns, from->i_d.di_projid); to->di_magic = from->i_d.di_magic; to->di_mode = from->i_d.di_mode; to->di_version = from->i_d.di_version; to->di_format = from->i_d.di_format; to->di_onlink = from->i_d.di_onlink; - to->di_uid = from->i_d.di_uid; - to->di_gid = from->i_d.di_gid; + to->di_uid = uid; + to->di_gid = gid; to->di_nlink = from->i_d.di_nlink; - to->di_projid_lo = from->i_d.di_projid & 0xffff; - to->di_projid_hi = from->i_d.di_projid >> 16; + to->di_projid_lo = projid & 0xffff; + to->di_projid_hi = projid >> 16; memcpy(to->di_pad, from->i_d.di_pad, sizeof(to->di_pad)); to->di_flushiter = from->i_d.di_flushiter; to->di_atime.t_sec = from->i_d.di_atime.t_sec; @@ -1112,7 +1120,7 @@ xfs_iread( if (ip->i_d.di_version == 1) { ip->i_d.di_nlink = ip->i_d.di_onlink; ip->i_d.di_onlink = 0; - ip->i_d.di_projid = 0; + ip->i_d.di_projid = make_kprojid(&init_user_ns, 0); } ip->i_delayed_blks = 0; @@ -1299,7 +1307,7 @@ xfs_ialloc( */ if ((irix_sgid_inherit) && (ip->i_d.di_mode & S_ISGID) && - (!in_group_p((gid_t)ip->i_d.di_gid))) { + (!in_group_p(ip->i_d.di_gid))) { ip->i_d.di_mode &= ~S_ISGID; } @@ -2895,7 +2903,8 @@ xfs_iflush_int( memset(&(ip->i_d.di_pad[0]), 0, sizeof(ip->i_d.di_pad)); memset(&(dip->di_pad[0]), 0, sizeof(dip->di_pad)); - ASSERT(ip->i_d.di_projid == 0); + ASSERT(projid_eq(ip->i_d.di_projid, + make_kprojid(&init_user_ns, 0))); } } diff --git a/fs/xfs/xfs_inode.h b/fs/xfs/xfs_inode.h index a722f7a..095bcbb 100644 --- a/fs/xfs/xfs_inode.h +++ b/fs/xfs/xfs_inode.h @@ -249,10 +249,10 @@ typedef struct xfs_inode { s8 di_version; /* inode version */ s8 di_format; /* format of di_c data */ u16 di_onlink; /* old number of links to file */ - u32 di_uid; /* owner's user id */ - u32 di_gid; /* owner's group id */ + kuid_t di_uid; /* owner's user id */ + kgid_t di_gid; /* owner's group id */ u32 di_nlink; /* number of links to file */ - projid_t di_projid; /* owner's project id */ + kprojid_t di_projid; /* owner's project id */ u8 di_pad[6]; /* unused, zeroed space */ u16 di_flushiter; /* incremented on flush */ xfs_ictimestamp_t di_atime; /* time last accessed */ diff --git a/fs/xfs/xfs_ioctl.c b/fs/xfs/xfs_ioctl.c index 79e9b13..1dd72d9 100644 --- a/fs/xfs/xfs_ioctl.c +++ b/fs/xfs/xfs_ioctl.c @@ -815,7 +815,7 @@ xfs_ioc_fsgetxattr( xfs_ilock(ip, XFS_ILOCK_SHARED); fa.fsx_xflags = xfs_ip2xflags(ip); fa.fsx_extsize = ip->i_d.di_extsize << ip->i_mount->m_sb.sb_blocklog; - fa.fsx_projid = ip->i_d.di_projid; + fa.fsx_projid = from_kprojid_munged(current_user_ns(), ip->i_d.di_projid); if (attr) { if (ip->i_afp) { @@ -975,7 +975,7 @@ xfs_ioctl_setattr( * to the file owner ID, except in cases where the * CAP_FSETID capability is applicable. */ - if (current_fsuid() != ip->i_d.di_uid && !capable(CAP_FOWNER)) { + if (!uid_eq(current_fsuid(), ip->i_d.di_uid) && !capable(CAP_FOWNER)) { code = XFS_ERROR(EPERM); goto error_return; } @@ -986,7 +986,7 @@ xfs_ioctl_setattr( if (mask & FSX_PROJID) { if (XFS_IS_QUOTA_RUNNING(mp) && XFS_IS_PQUOTA_ON(mp) && - ip->i_d.di_projid != fa->fsx_projid) { + !projid_eq(ip->i_d.di_projid, fa->fsx_projid)) { ASSERT(tp); code = xfs_qm_vop_chown_reserve(tp, ip, udqp, gdqp, capable(CAP_FOWNER) ? @@ -1104,7 +1104,7 @@ xfs_ioctl_setattr( * Change the ownerships and register quota modifications * in the transaction. */ - if (ip->i_d.di_projid != fa->fsx_projid) { + if (!projid_eq(ip->i_d.di_projid, fa->fsx_projid)) { if (XFS_IS_QUOTA_RUNNING(mp) && XFS_IS_PQUOTA_ON(mp)) { olddquot = xfs_qm_vop_chown(tp, ip, &ip->i_gdquot, gdqp); diff --git a/fs/xfs/xfs_itable.c b/fs/xfs/xfs_itable.c index 3529f2e..6e57195 100644 --- a/fs/xfs/xfs_itable.c +++ b/fs/xfs/xfs_itable.c @@ -63,6 +63,7 @@ xfs_bulkstat_one_int( struct xfs_inode *ip; /* incore inode pointer */ struct xfs_bstat *buf; /* return buffer */ int error = 0; /* error value */ + projid_t projid; *stat = BULKSTAT_RV_NOTHING; @@ -88,12 +89,13 @@ xfs_bulkstat_one_int( * further change. */ buf->bs_nlink = ip->i_d.di_nlink; - buf->bs_projid_lo = (u16)(ip->i_d.di_projid & 0xffff); - buf->bs_projid_hi = (u16)(ip->i_d.di_projid >> 16); + projid = from_kprojid_munged(current_user_ns(), ip->i_d.di_projid); + buf->bs_projid_lo = projid & 0xffff; + buf->bs_projid_hi = projid >> 16; buf->bs_ino = ino; buf->bs_mode = ip->i_d.di_mode; - buf->bs_uid = ip->i_d.di_uid; - buf->bs_gid = ip->i_d.di_gid; + buf->bs_uid = from_kuid_munged(current_user_ns(), ip->i_d.di_uid); + buf->bs_gid = from_kgid_munged(current_user_ns(), ip->i_d.di_gid); buf->bs_size = ip->i_d.di_size; buf->bs_atime.tv_sec = ip->i_d.di_atime.t_sec; buf->bs_atime.tv_nsec = ip->i_d.di_atime.t_nsec; diff --git a/fs/xfs/xfs_qm.c b/fs/xfs/xfs_qm.c index c0904fc..3324dd3 100644 --- a/fs/xfs/xfs_qm.c +++ b/fs/xfs/xfs_qm.c @@ -1649,7 +1649,7 @@ xfs_qm_vop_dqalloc( uq = gq = NULL; if ((flags & XFS_QMOPT_UQUOTA) && XFS_IS_UQUOTA_ON(mp)) { - if (ip->i_d.di_uid != uid) { + if (!uid_eq(ip->i_d.di_uid, uid)) { /* * What we need is the dquot that has this uid, and * if we send the inode to dqget, the uid of the inode @@ -1684,7 +1684,7 @@ xfs_qm_vop_dqalloc( } } if ((flags & XFS_QMOPT_GQUOTA) && XFS_IS_GQUOTA_ON(mp)) { - if (ip->i_d.di_gid != gid) { + if (!gid_eq(ip->i_d.di_gid, gid)) { xfs_iunlock(ip, lockflags); if ((error = xfs_qm_dqget(mp, NULL, (xfs_dqid_t)gid, XFS_DQ_GROUP, @@ -1704,7 +1704,7 @@ xfs_qm_vop_dqalloc( gq = xfs_qm_dqhold(ip->i_gdquot); } } else if ((flags & XFS_QMOPT_PQUOTA) && XFS_IS_PQUOTA_ON(mp)) { - if (ip->i_d.di_projid != prid) { + if (!projid_eq(ip->i_d.di_projid, prid)) { xfs_iunlock(ip, lockflags); if ((error = xfs_qm_dqget(mp, NULL, (xfs_dqid_t)prid, XFS_DQ_PROJ, @@ -1805,7 +1805,7 @@ xfs_qm_vop_chown_reserve( XFS_QMOPT_RES_RTBLKS : XFS_QMOPT_RES_REGBLKS; if (XFS_IS_UQUOTA_ON(mp) && udqp && - ip->i_d.di_uid != (uid_t)be32_to_cpu(udqp->q_core.d_id)) { + !uid_eq(ip->i_d.di_uid, (uid_t)be32_to_cpu(udqp->q_core.d_id))) { delblksudq = udqp; /* * If there are delayed allocation blocks, then we have to @@ -1819,12 +1819,12 @@ xfs_qm_vop_chown_reserve( } if (XFS_IS_OQUOTA_ON(ip->i_mount) && gdqp) { if (XFS_IS_PQUOTA_ON(ip->i_mount) && - ip->i_d.di_projid != be32_to_cpu(gdqp->q_core.d_id)) + !projid_eq(ip->i_d.di_projid, be32_to_cpu(gdqp->q_core.d_id))) prjflags = XFS_QMOPT_ENOSPC; if (prjflags || (XFS_IS_GQUOTA_ON(ip->i_mount) && - ip->i_d.di_gid != be32_to_cpu(gdqp->q_core.d_id))) { + !gid_eq(ip->i_d.di_gid, be32_to_cpu(gdqp->q_core.d_id)))) { delblksgdq = gdqp; if (delblks) { ASSERT(ip->i_gdquot); @@ -1908,7 +1908,7 @@ xfs_qm_vop_create_dqattach( if (udqp) { ASSERT(ip->i_udquot == NULL); ASSERT(XFS_IS_UQUOTA_ON(mp)); - ASSERT(ip->i_d.di_uid == be32_to_cpu(udqp->q_core.d_id)); + ASSERT(uid_eq(ip->i_d.di_uid, be32_to_cpu(udqp->q_core.d_id))); ip->i_udquot = xfs_qm_dqhold(udqp); xfs_trans_mod_dquot(tp, udqp, XFS_TRANS_DQ_ICOUNT, 1); @@ -1916,9 +1916,9 @@ xfs_qm_vop_create_dqattach( if (gdqp) { ASSERT(ip->i_gdquot == NULL); ASSERT(XFS_IS_OQUOTA_ON(mp)); - ASSERT((XFS_IS_GQUOTA_ON(mp) ? - ip->i_d.di_gid : ip->i_d.di_projid) == - be32_to_cpu(gdqp->q_core.d_id)); + ASSERT(XFS_IS_GQUOTA_ON(mp) ? + gid_eq(ip->i_d.di_gid, be32_to_cpu(gdqp->q_core.d_id)): + projid_eq(ip->i_d.di_projid, be32_to_cpu(gdqp->q_core.d_id))); ip->i_gdquot = xfs_qm_dqhold(gdqp); xfs_trans_mod_dquot(tp, gdqp, XFS_TRANS_DQ_ICOUNT, 1); diff --git a/fs/xfs/xfs_rename.c b/fs/xfs/xfs_rename.c index 4e87258..b919704 100644 --- a/fs/xfs/xfs_rename.c +++ b/fs/xfs/xfs_rename.c @@ -171,7 +171,7 @@ xfs_rename( * tree quota mechanism would be circumvented. */ if (unlikely((target_dp->i_d.di_flags & XFS_DIFLAG_PROJINHERIT) && - (target_dp->i_d.di_projid != src_ip->i_d.di_projid))) { + !projid_eq(target_dp->i_d.di_projid, src_ip->i_d.di_projid))) { error = XFS_ERROR(EXDEV); goto error_return; } diff --git a/fs/xfs/xfs_vnodeops.c b/fs/xfs/xfs_vnodeops.c index 1a9ee2c..dab0ab3 100644 --- a/fs/xfs/xfs_vnodeops.c +++ b/fs/xfs/xfs_vnodeops.c @@ -1305,7 +1305,7 @@ xfs_link( * the tree quota mechanism could be circumvented. */ if (unlikely((tdp->i_d.di_flags & XFS_DIFLAG_PROJINHERIT) && - (tdp->i_d.di_projid != sip->i_d.di_projid))) { + !projid_eq(tdp->i_d.di_projid, sip->i_d.di_projid))) { error = XFS_ERROR(EXDEV); goto error_return; } -- 1.7.5.4 From ebiederm@xmission.com Wed Mar 13 17:25:28 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 5457B7F4E for ; Wed, 13 Mar 2013 17:25:28 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay3.corp.sgi.com (Postfix) with ESMTP id BD966AC001 for ; Wed, 13 Mar 2013 15:25:27 -0700 (PDT) X-ASG-Debug-ID: 1363213526-04cbb04b867db50001-NocioJ Received: from out01.mta.xmission.com (out01.mta.xmission.com [166.70.13.231]) by cuda.sgi.com with ESMTP id CRUAvTSjE9MRijVh (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO); Wed, 13 Mar 2013 15:25:26 -0700 (PDT) X-Barracuda-Envelope-From: ebiederm@xmission.com X-Barracuda-Apparent-Source-IP: 166.70.13.231 Received: from in02.mta.xmission.com ([166.70.13.52]) by out01.mta.xmission.com with esmtps (TLS1.0:RSA_AES_256_CBC_SHA1:32) (Exim 4.76) (envelope-from ) id 1UFu6u-0001gO-Uk; Wed, 13 Mar 2013 16:25:25 -0600 Received: from mfd0536d0.tmodns.net ([208.54.5.253] helo=localhost.localdomain) by in02.mta.xmission.com with esmtpsa (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.76) (envelope-from ) id 1UFu6l-0007mg-Hs; Wed, 13 Mar 2013 16:25:24 -0600 From: "Eric W. Biederman" To: Cc: Linux Containers , "Serge E. Hallyn" , xfs@oss.sgi.com, Ben Myers , Alex Elder , Dave Chinner , "Eric W. Biederman" Date: Wed, 13 Mar 2013 15:23:06 -0700 Message-Id: <1363213395-10988-5-git-send-email-ebiederm@xmission.com> X-Mailer: git-send-email 1.7.5.4 In-Reply-To: <1363213395-10988-1-git-send-email-ebiederm@xmission.com> References: <87boan3prc.fsf@xmission.com> <1363213395-10988-1-git-send-email-ebiederm@xmission.com> X-XM-AID: U2FsdGVkX19GTeLkS4r02QNy5QsCruAzwnep+brL1Y0= X-SA-Exim-Connect-IP: 208.54.5.253 X-SA-Exim-Mail-From: ebiederm@xmission.com Subject: [PATCH 05/14] xfs: Update xfs_ioctl_setattr to handle projids in any user namespace X-ASG-Orig-Subj: [PATCH 05/14] xfs: Update xfs_ioctl_setattr to handle projids in any user namespace X-SA-Exim-Version: 4.2.1 (built Wed, 14 Nov 2012 14:26:46 -0700) X-SA-Exim-Scanned: Yes (on in02.mta.xmission.com) X-Barracuda-Connect: out01.mta.xmission.com[166.70.13.231] X-Barracuda-Start-Time: 1363213526 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_MISMATCH_TO X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125122 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 BSF_SC0_MISMATCH_TO Envelope rcpt doesn't match header From: "Eric W. Biederman" - Convert the userspace value in fa->fsx_projid into a kprojid and store it in the variable projid. - Verify that xfs can store the projid after it is converted into xfs's user namespace. - Replace uses of fa->fsx_projid with projid throughout xfs_ioctl_setattr. Cc: Ben Myers Cc: Alex Elder Cc: Dave Chinner Signed-off-by: "Eric W. Biederman" --- fs/xfs/xfs_ioctl.c | 26 ++++++++++++++++++-------- 1 files changed, 18 insertions(+), 8 deletions(-) diff --git a/fs/xfs/xfs_ioctl.c b/fs/xfs/xfs_ioctl.c index 1dd72d9..9aeecfb 100644 --- a/fs/xfs/xfs_ioctl.c +++ b/fs/xfs/xfs_ioctl.c @@ -925,6 +925,7 @@ xfs_ioctl_setattr( struct xfs_dquot *gdqp = NULL; struct xfs_dquot *olddquot = NULL; int code; + kprojid_t projid = INVALID_PROJID; trace_xfs_ioctl_setattr(ip); @@ -934,11 +935,20 @@ xfs_ioctl_setattr( return XFS_ERROR(EIO); /* - * Disallow 32bit project ids when projid32bit feature is not enabled. + * Verify the specifid project id is valid. */ - if ((mask & FSX_PROJID) && (fa->fsx_projid > (__uint16_t)-1) && - !xfs_sb_version_hasprojid32bit(&ip->i_mount->m_sb)) - return XFS_ERROR(EINVAL); + if (mask & FSX_PROJID) { + projid = make_kprojid(current_user_ns(), fa->fsx_projid); + if (!projid_valid(projid)) + return XFS_ERROR(EINVAL); + + /* + * Disallow 32bit project ids when projid32bit feature is not enabled. + */ + if ((from_kprojid(&init_user_ns, projid) > (__uint16_t)-1) && + !xfs_sb_version_hasprojid32bit(&ip->i_mount->m_sb)) + return XFS_ERROR(EINVAL); + } /* * If disk quotas is on, we make sure that the dquots do exist on disk, @@ -950,7 +960,7 @@ xfs_ioctl_setattr( */ if (XFS_IS_QUOTA_ON(mp) && (mask & FSX_PROJID)) { code = xfs_qm_vop_dqalloc(ip, ip->i_d.di_uid, - ip->i_d.di_gid, fa->fsx_projid, + ip->i_d.di_gid, projid, XFS_QMOPT_PQUOTA, &udqp, &gdqp); if (code) return code; @@ -986,7 +996,7 @@ xfs_ioctl_setattr( if (mask & FSX_PROJID) { if (XFS_IS_QUOTA_RUNNING(mp) && XFS_IS_PQUOTA_ON(mp) && - !projid_eq(ip->i_d.di_projid, fa->fsx_projid)) { + !projid_eq(ip->i_d.di_projid, projid)) { ASSERT(tp); code = xfs_qm_vop_chown_reserve(tp, ip, udqp, gdqp, capable(CAP_FOWNER) ? @@ -1104,12 +1114,12 @@ xfs_ioctl_setattr( * Change the ownerships and register quota modifications * in the transaction. */ - if (!projid_eq(ip->i_d.di_projid, fa->fsx_projid)) { + if (!projid_eq(ip->i_d.di_projid, projid)) { if (XFS_IS_QUOTA_RUNNING(mp) && XFS_IS_PQUOTA_ON(mp)) { olddquot = xfs_qm_vop_chown(tp, ip, &ip->i_gdquot, gdqp); } - ip->i_d.di_projid = fa->fsx_projid; + ip->i_d.di_projid = projid; /* * We may have to rev the inode as well as -- 1.7.5.4 From ebiederm@xmission.com Wed Mar 13 17:25:32 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 2E33F7F59 for ; Wed, 13 Mar 2013 17:25:32 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay1.corp.sgi.com (Postfix) with ESMTP id 1177F8F8033 for ; Wed, 13 Mar 2013 15:25:32 -0700 (PDT) X-ASG-Debug-ID: 1363213530-04cb6c4a4486ed0001-NocioJ Received: from out01.mta.xmission.com (out01.mta.xmission.com [166.70.13.231]) by cuda.sgi.com with ESMTP id 42EfFEx7YainWhFP (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO); Wed, 13 Mar 2013 15:25:31 -0700 (PDT) X-Barracuda-Envelope-From: ebiederm@xmission.com X-Barracuda-Apparent-Source-IP: 166.70.13.231 Received: from in02.mta.xmission.com ([166.70.13.52]) by out01.mta.xmission.com with esmtps (TLS1.0:RSA_AES_256_CBC_SHA1:32) (Exim 4.76) (envelope-from ) id 1UFu70-0001i3-7z; Wed, 13 Mar 2013 16:25:30 -0600 Received: from mfd0536d0.tmodns.net ([208.54.5.253] helo=localhost.localdomain) by in02.mta.xmission.com with esmtpsa (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.76) (envelope-from ) id 1UFu6x-0007mg-A8; Wed, 13 Mar 2013 16:25:30 -0600 From: "Eric W. Biederman" To: Cc: Linux Containers , "Serge E. Hallyn" , xfs@oss.sgi.com, Ben Myers , Alex Elder , Dave Chinner , "Eric W. Biederman" Date: Wed, 13 Mar 2013 15:23:07 -0700 Message-Id: <1363213395-10988-6-git-send-email-ebiederm@xmission.com> X-Mailer: git-send-email 1.7.5.4 In-Reply-To: <1363213395-10988-1-git-send-email-ebiederm@xmission.com> References: <87boan3prc.fsf@xmission.com> <1363213395-10988-1-git-send-email-ebiederm@xmission.com> X-XM-AID: U2FsdGVkX1+BOqwu9gnGtfgoRSdD0EhKX4npa42XWuM= X-SA-Exim-Connect-IP: 208.54.5.253 X-SA-Exim-Mail-From: ebiederm@xmission.com Subject: [PATCH 06/14] xfs: Use kuids and kgids in xfs_setattr_nonsize X-ASG-Orig-Subj: [PATCH 06/14] xfs: Use kuids and kgids in xfs_setattr_nonsize X-SA-Exim-Version: 4.2.1 (built Wed, 14 Nov 2012 14:26:46 -0700) X-SA-Exim-Scanned: Yes (on in02.mta.xmission.com) X-Barracuda-Connect: out01.mta.xmission.com[166.70.13.231] X-Barracuda-Start-Time: 1363213531 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_MISMATCH_TO X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125122 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 BSF_SC0_MISMATCH_TO Envelope rcpt doesn't match header From: "Eric W. Biederman" Cc: Ben Myers Cc: Alex Elder Cc: Dave Chinner Signed-off-by: "Eric W. Biederman" --- fs/xfs/xfs_iops.c | 12 ++++++------ 1 files changed, 6 insertions(+), 6 deletions(-) diff --git a/fs/xfs/xfs_iops.c b/fs/xfs/xfs_iops.c index a69ddfd..e9dcf48 100644 --- a/fs/xfs/xfs_iops.c +++ b/fs/xfs/xfs_iops.c @@ -466,8 +466,8 @@ xfs_setattr_nonsize( int mask = iattr->ia_valid; xfs_trans_t *tp; int error; - uid_t uid = 0, iuid = 0; - gid_t gid = 0, igid = 0; + kuid_t uid = GLOBAL_ROOT_UID, iuid = GLOBAL_ROOT_UID; + kgid_t gid = GLOBAL_ROOT_GID, igid = GLOBAL_ROOT_GID; struct xfs_dquot *udqp = NULL, *gdqp = NULL; struct xfs_dquot *olddquot1 = NULL, *olddquot2 = NULL; @@ -549,8 +549,8 @@ xfs_setattr_nonsize( * going to change. */ if (XFS_IS_QUOTA_RUNNING(mp) && - ((XFS_IS_UQUOTA_ON(mp) && iuid != uid) || - (XFS_IS_GQUOTA_ON(mp) && igid != gid))) { + ((XFS_IS_UQUOTA_ON(mp) && !uid_eq(iuid, uid)) || + (XFS_IS_GQUOTA_ON(mp) && !gid_eq(igid, gid)))) { ASSERT(tp); error = xfs_qm_vop_chown_reserve(tp, ip, udqp, gdqp, capable(CAP_FOWNER) ? @@ -580,7 +580,7 @@ xfs_setattr_nonsize( * Change the ownerships and register quota modifications * in the transaction. */ - if (iuid != uid) { + if (!uid_eq(iuid, uid)) { if (XFS_IS_QUOTA_RUNNING(mp) && XFS_IS_UQUOTA_ON(mp)) { ASSERT(mask & ATTR_UID); ASSERT(udqp); @@ -590,7 +590,7 @@ xfs_setattr_nonsize( ip->i_d.di_uid = uid; inode->i_uid = uid; } - if (igid != gid) { + if (!gid_eq(igid, gid)) { if (XFS_IS_QUOTA_RUNNING(mp) && XFS_IS_GQUOTA_ON(mp)) { ASSERT(!XFS_IS_PQUOTA_ON(mp)); ASSERT(mask & ATTR_GID); -- 1.7.5.4 From ebiederm@xmission.com Wed Mar 13 17:25:38 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 518DE7F5E for ; Wed, 13 Mar 2013 17:25:38 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay1.corp.sgi.com (Postfix) with ESMTP id 1518A8F8033 for ; Wed, 13 Mar 2013 15:25:38 -0700 (PDT) X-ASG-Debug-ID: 1363213536-04bdf00a0a8c990001-NocioJ Received: from out03.mta.xmission.com (out03.mta.xmission.com [166.70.13.233]) by cuda.sgi.com with ESMTP id zttiEFgG3uIs2beJ (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO); Wed, 13 Mar 2013 15:25:36 -0700 (PDT) X-Barracuda-Envelope-From: ebiederm@xmission.com X-Barracuda-Apparent-Source-IP: 166.70.13.233 Received: from in02.mta.xmission.com ([166.70.13.52]) by out03.mta.xmission.com with esmtps (TLS1.0:RSA_AES_256_CBC_SHA1:32) (Exim 4.76) (envelope-from ) id 1UFu76-00066N-5p; Wed, 13 Mar 2013 16:25:36 -0600 Received: from mfd0536d0.tmodns.net ([208.54.5.253] helo=localhost.localdomain) by in02.mta.xmission.com with esmtpsa (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.76) (envelope-from ) id 1UFu72-0007mg-SV; Wed, 13 Mar 2013 16:25:35 -0600 From: "Eric W. Biederman" To: Cc: Linux Containers , "Serge E. Hallyn" , xfs@oss.sgi.com, Ben Myers , Alex Elder , Dave Chinner , "Eric W. Biederman" Date: Wed, 13 Mar 2013 15:23:08 -0700 Message-Id: <1363213395-10988-7-git-send-email-ebiederm@xmission.com> X-Mailer: git-send-email 1.7.5.4 In-Reply-To: <1363213395-10988-1-git-send-email-ebiederm@xmission.com> References: <87boan3prc.fsf@xmission.com> <1363213395-10988-1-git-send-email-ebiederm@xmission.com> X-XM-AID: U2FsdGVkX1/ShqN/LtuZPdoNIXo/qpH3GI7/WU7wp3E= X-SA-Exim-Connect-IP: 208.54.5.253 X-SA-Exim-Mail-From: ebiederm@xmission.com Subject: [PATCH 07/14] xfs: Update ioctl(XFS_IOC_FREE_EOFBLOCKS) to handle callers in any userspace X-ASG-Orig-Subj: [PATCH 07/14] xfs: Update ioctl(XFS_IOC_FREE_EOFBLOCKS) to handle callers in any userspace X-SA-Exim-Version: 4.2.1 (built Wed, 14 Nov 2012 14:26:46 -0700) X-SA-Exim-Scanned: Yes (on in02.mta.xmission.com) X-Barracuda-Connect: out03.mta.xmission.com[166.70.13.233] X-Barracuda-Start-Time: 1363213536 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Barracuda-BRTS-Status: 1 X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_MISMATCH_TO X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125122 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 BSF_SC0_MISMATCH_TO Envelope rcpt doesn't match header From: "Eric W. Biederman" - Modify the ioctl to convert from uids, gid, and projids in the current user namespace to kuids, kgids, and kprojids, and to report an error if the conversion fails. - Create struct xfs_internal_eofblocks to hold the same information as struct xfs_eofblocks but with uids, gids, and projids stored as kuids, kgids, and kprojids preventing confusion. - Pass struct xfs_interanl_eofblocks into xfs_icache_free_eofblocks and it's helpers ensuring there will not be confusing about which user namespace identifiers that need to be compared are in. Cc: Ben Myers Cc: Alex Elder Cc: Dave Chinner Signed-off-by: "Eric W. Biederman" --- fs/xfs/xfs_icache.c | 8 ++++---- fs/xfs/xfs_icache.h | 11 ++++++++++- fs/xfs/xfs_ioctl.c | 22 +++++++++++++++++++++- 3 files changed, 35 insertions(+), 6 deletions(-) diff --git a/fs/xfs/xfs_icache.c b/fs/xfs/xfs_icache.c index 03a4427..032c28c 100644 --- a/fs/xfs/xfs_icache.c +++ b/fs/xfs/xfs_icache.c @@ -1199,7 +1199,7 @@ xfs_reclaim_inodes_count( STATIC int xfs_inode_match_id( struct xfs_inode *ip, - struct xfs_eofblocks *eofb) + struct xfs_internal_eofblocks *eofb) { if (eofb->eof_flags & XFS_EOF_FLAGS_UID && !uid_eq(ip->i_d.di_uid, eofb->eof_uid)) @@ -1210,7 +1210,7 @@ xfs_inode_match_id( return 0; if (eofb->eof_flags & XFS_EOF_FLAGS_PRID && - !projid_eq(ip->i_d.di_projid, eofb->eof_prid)) + !projid_eq(ip->i_d.di_projid, eofb->eof_projid)) return 0; return 1; @@ -1224,7 +1224,7 @@ xfs_inode_free_eofblocks( void *args) { int ret; - struct xfs_eofblocks *eofb = args; + struct xfs_internal_eofblocks *eofb = args; if (!xfs_can_free_eofblocks(ip, false)) { /* inode could be preallocated or append-only */ @@ -1263,7 +1263,7 @@ xfs_inode_free_eofblocks( int xfs_icache_free_eofblocks( struct xfs_mount *mp, - struct xfs_eofblocks *eofb) + struct xfs_internal_eofblocks *eofb) { int flags = SYNC_TRYLOCK; diff --git a/fs/xfs/xfs_icache.h b/fs/xfs/xfs_icache.h index e0f138c..260dc27 100644 --- a/fs/xfs/xfs_icache.h +++ b/fs/xfs/xfs_icache.h @@ -35,9 +35,18 @@ void xfs_reclaim_inodes_nr(struct xfs_mount *mp, int nr_to_scan); void xfs_inode_set_reclaim_tag(struct xfs_inode *ip); +struct xfs_internal_eofblocks { + u32 eof_version; + u32 eof_flags; + kuid_t eof_uid; + kgid_t eof_gid; + kprojid_t eof_projid; + u64 eof_min_file_size; +}; + void xfs_inode_set_eofblocks_tag(struct xfs_inode *ip); void xfs_inode_clear_eofblocks_tag(struct xfs_inode *ip); -int xfs_icache_free_eofblocks(struct xfs_mount *, struct xfs_eofblocks *); +int xfs_icache_free_eofblocks(struct xfs_mount *, struct xfs_internal_eofblocks *); void xfs_eofblocks_worker(struct work_struct *); int xfs_sync_inode_grab(struct xfs_inode *ip); diff --git a/fs/xfs/xfs_ioctl.c b/fs/xfs/xfs_ioctl.c index 9aeecfb..8c933e5 100644 --- a/fs/xfs/xfs_ioctl.c +++ b/fs/xfs/xfs_ioctl.c @@ -1615,6 +1615,7 @@ xfs_file_ioctl( case XFS_IOC_FREE_EOFBLOCKS: { struct xfs_eofblocks eofb; + struct xfs_internal_eofblocks keofb; if (copy_from_user(&eofb, arg, sizeof(eofb))) return -XFS_ERROR(EFAULT); @@ -1629,7 +1630,26 @@ xfs_file_ioctl( memchr_inv(eofb.pad64, 0, sizeof(eofb.pad64))) return -XFS_ERROR(EINVAL); - error = xfs_icache_free_eofblocks(mp, &eofb); + keofb.eof_version = eofb.eof_version; + keofb.eof_flags = eofb.eof_flags; + if (eofb.eof_flags & XFS_EOF_FLAGS_UID) { + keofb.eof_uid = make_kuid(current_user_ns(), eofb.eof_uid); + if (!uid_valid(keofb.eof_uid)) + return -XFS_ERROR(EINVAL); + } + if (eofb.eof_flags & XFS_EOF_FLAGS_GID) { + keofb.eof_gid = make_kgid(current_user_ns(), eofb.eof_gid); + if (!gid_valid(keofb.eof_gid)) + return -XFS_ERROR(EINVAL); + } + if (eofb.eof_flags & XFS_EOF_FLAGS_PRID) { + keofb.eof_projid = make_kprojid(current_user_ns(), eofb.eof_prid); + if (!projid_valid(keofb.eof_projid)) + return -XFS_ERROR(EINVAL); + } + keofb.eof_min_file_size = eofb.eof_min_file_size; + + error = xfs_icache_free_eofblocks(mp, &keofb); return -error; } -- 1.7.5.4 From ebiederm@xmission.com Wed Mar 13 17:25:50 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id C31297F4E for ; Wed, 13 Mar 2013 17:25:50 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay1.corp.sgi.com (Postfix) with ESMTP id 7A6BC8F804B for ; Wed, 13 Mar 2013 15:25:50 -0700 (PDT) X-ASG-Debug-ID: 1363213548-04bdf00a0d8c9f0001-NocioJ Received: from out03.mta.xmission.com (out03.mta.xmission.com [166.70.13.233]) by cuda.sgi.com with ESMTP id hOdVp6EzjAvZRM4p (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO); Wed, 13 Mar 2013 15:25:49 -0700 (PDT) X-Barracuda-Envelope-From: ebiederm@xmission.com X-Barracuda-Apparent-Source-IP: 166.70.13.233 Received: from in02.mta.xmission.com ([166.70.13.52]) by out03.mta.xmission.com with esmtps (TLS1.0:RSA_AES_256_CBC_SHA1:32) (Exim 4.76) (envelope-from ) id 1UFu7I-0006AQ-9T; Wed, 13 Mar 2013 16:25:48 -0600 Received: from mfd0536d0.tmodns.net ([208.54.5.253] helo=localhost.localdomain) by in02.mta.xmission.com with esmtpsa (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.76) (envelope-from ) id 1UFu7B-0007mg-Vn; Wed, 13 Mar 2013 16:25:48 -0600 From: "Eric W. Biederman" To: Cc: Linux Containers , "Serge E. Hallyn" , xfs@oss.sgi.com, Ben Myers , Alex Elder , Dave Chinner , "Eric W. Biederman" Date: Wed, 13 Mar 2013 15:23:09 -0700 Message-Id: <1363213395-10988-8-git-send-email-ebiederm@xmission.com> X-Mailer: git-send-email 1.7.5.4 In-Reply-To: <1363213395-10988-1-git-send-email-ebiederm@xmission.com> References: <87boan3prc.fsf@xmission.com> <1363213395-10988-1-git-send-email-ebiederm@xmission.com> X-XM-AID: U2FsdGVkX19nsdj7QEjOIR24tObVc85oeJW4IsoHJyg= X-SA-Exim-Connect-IP: 208.54.5.253 X-SA-Exim-Mail-From: ebiederm@xmission.com Subject: [PATCH 08/14] xfs: Use kprojids when allocating inodes. X-ASG-Orig-Subj: [PATCH 08/14] xfs: Use kprojids when allocating inodes. X-SA-Exim-Version: 4.2.1 (built Wed, 14 Nov 2012 14:26:46 -0700) X-SA-Exim-Scanned: Yes (on in02.mta.xmission.com) X-Barracuda-Connect: out03.mta.xmission.com[166.70.13.233] X-Barracuda-Start-Time: 1363213549 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_MISMATCH_TO X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125122 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 BSF_SC0_MISMATCH_TO Envelope rcpt doesn't match header From: "Eric W. Biederman" In xfs_create and xfs_symlink compute the desired kprojid and pass it down into xfs_ialloc. Cc: Ben Myers Cc: Alex Elder Cc: Dave Chinner Signed-off-by: "Eric W. Biederman" --- fs/xfs/xfs_inode.c | 5 +++-- fs/xfs/xfs_inode.h | 2 +- fs/xfs/xfs_qm.c | 4 +++- fs/xfs/xfs_utils.c | 2 +- fs/xfs/xfs_utils.h | 2 +- fs/xfs/xfs_vnodeops.c | 8 ++++---- 6 files changed, 13 insertions(+), 10 deletions(-) diff --git a/fs/xfs/xfs_inode.c b/fs/xfs/xfs_inode.c index 8d77e49..bed6947 100644 --- a/fs/xfs/xfs_inode.c +++ b/fs/xfs/xfs_inode.c @@ -1226,7 +1226,7 @@ xfs_ialloc( umode_t mode, xfs_nlink_t nlink, xfs_dev_t rdev, - prid_t prid, + kprojid_t prid, int okalloc, xfs_buf_t **ialloc_context, xfs_inode_t **ipp) @@ -1290,7 +1290,8 @@ xfs_ialloc( /* * Project ids won't be stored on disk if we are using a version 1 inode. */ - if ((prid != 0) && (ip->i_d.di_version == 1)) + if (!projid_eq(prid, make_kprojid(&init_user_ns, 0)) && + (ip->i_d.di_version == 1)) xfs_bump_ino_vers2(tp, ip); if (pip && XFS_INHERIT_GID(pip)) { diff --git a/fs/xfs/xfs_inode.h b/fs/xfs/xfs_inode.h index 095bcbb..efe279e 100644 --- a/fs/xfs/xfs_inode.h +++ b/fs/xfs/xfs_inode.h @@ -516,7 +516,7 @@ int xfs_isilocked(xfs_inode_t *, uint); uint xfs_ilock_map_shared(xfs_inode_t *); void xfs_iunlock_map_shared(xfs_inode_t *, uint); int xfs_ialloc(struct xfs_trans *, xfs_inode_t *, umode_t, - xfs_nlink_t, xfs_dev_t, prid_t, int, + xfs_nlink_t, xfs_dev_t, kprojid_t, int, struct xfs_buf **, xfs_inode_t **); uint xfs_ip2xflags(struct xfs_inode *); diff --git a/fs/xfs/xfs_qm.c b/fs/xfs/xfs_qm.c index 3324dd3..861e4e8 100644 --- a/fs/xfs/xfs_qm.c +++ b/fs/xfs/xfs_qm.c @@ -777,7 +777,9 @@ xfs_qm_qino_alloc( return error; } - error = xfs_dir_ialloc(&tp, NULL, S_IFREG, 1, 0, 0, 1, ip, &committed); + error = xfs_dir_ialloc(&tp, NULL, S_IFREG, 1, 0, + make_kprojid(&init_user_ns, 0), + 1, ip, &committed); if (error) { xfs_trans_cancel(tp, XFS_TRANS_RELEASE_LOG_RES | XFS_TRANS_ABORT); diff --git a/fs/xfs/xfs_utils.c b/fs/xfs/xfs_utils.c index 0025c78..f0a9f1d 100644 --- a/fs/xfs/xfs_utils.c +++ b/fs/xfs/xfs_utils.c @@ -54,7 +54,7 @@ xfs_dir_ialloc( umode_t mode, xfs_nlink_t nlink, xfs_dev_t rdev, - prid_t prid, /* project id */ + kprojid_t prid, /* project id */ int okalloc, /* ok to allocate new space */ xfs_inode_t **ipp, /* pointer to inode; it will be locked. */ diff --git a/fs/xfs/xfs_utils.h b/fs/xfs/xfs_utils.h index 5eeab46..7757f7c 100644 --- a/fs/xfs/xfs_utils.h +++ b/fs/xfs/xfs_utils.h @@ -19,7 +19,7 @@ #define __XFS_UTILS_H__ extern int xfs_dir_ialloc(xfs_trans_t **, xfs_inode_t *, umode_t, xfs_nlink_t, - xfs_dev_t, prid_t, int, xfs_inode_t **, int *); + xfs_dev_t, kprojid_t, int, xfs_inode_t **, int *); extern int xfs_droplink(xfs_trans_t *, xfs_inode_t *); extern int xfs_bumplink(xfs_trans_t *, xfs_inode_t *); extern void xfs_bump_ino_vers2(xfs_trans_t *, xfs_inode_t *); diff --git a/fs/xfs/xfs_vnodeops.c b/fs/xfs/xfs_vnodeops.c index dab0ab3..863b979 100644 --- a/fs/xfs/xfs_vnodeops.c +++ b/fs/xfs/xfs_vnodeops.c @@ -728,7 +728,7 @@ xfs_create( bool unlock_dp_on_error = false; uint cancel_flags; int committed; - prid_t prid; + kprojid_t prid; struct xfs_dquot *udqp = NULL; struct xfs_dquot *gdqp = NULL; uint resblks; @@ -743,7 +743,7 @@ xfs_create( if (dp->i_d.di_flags & XFS_DIFLAG_PROJINHERIT) prid = dp->i_d.di_projid; else - prid = XFS_PROJID_DEFAULT; + prid = make_kprojid(&init_user_ns, XFS_PROJID_DEFAULT); /* * Make sure that we have allocated dquot(s) on disk. @@ -1379,7 +1379,7 @@ xfs_symlink( int byte_cnt; int n; xfs_buf_t *bp; - prid_t prid; + kprojid_t prid; struct xfs_dquot *udqp, *gdqp; uint resblks; @@ -1404,7 +1404,7 @@ xfs_symlink( if (dp->i_d.di_flags & XFS_DIFLAG_PROJINHERIT) prid = dp->i_d.di_projid; else - prid = XFS_PROJID_DEFAULT; + prid = make_kprojid(&init_user_ns, XFS_PROJID_DEFAULT); /* * Make sure that we have allocated dquot(s) on disk. -- 1.7.5.4 From ebiederm@xmission.com Wed Mar 13 17:26:00 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 19D437F63 for ; Wed, 13 Mar 2013 17:26:00 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id F1482304075 for ; Wed, 13 Mar 2013 15:25:59 -0700 (PDT) X-ASG-Debug-ID: 1363213558-04cbb04b877dbf0001-NocioJ Received: from out01.mta.xmission.com (out01.mta.xmission.com [166.70.13.231]) by cuda.sgi.com with ESMTP id Fac9Asitck78X5GK (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO); Wed, 13 Mar 2013 15:25:59 -0700 (PDT) X-Barracuda-Envelope-From: ebiederm@xmission.com X-Barracuda-Apparent-Source-IP: 166.70.13.231 Received: from in02.mta.xmission.com ([166.70.13.52]) by out01.mta.xmission.com with esmtps (TLS1.0:RSA_AES_256_CBC_SHA1:32) (Exim 4.76) (envelope-from ) id 1UFu7S-0001qo-9T; Wed, 13 Mar 2013 16:25:58 -0600 Received: from mfd0536d0.tmodns.net ([208.54.5.253] helo=localhost.localdomain) by in02.mta.xmission.com with esmtpsa (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.76) (envelope-from ) id 1UFu7P-0007mg-4c; Wed, 13 Mar 2013 16:25:58 -0600 From: "Eric W. Biederman" To: Cc: Linux Containers , "Serge E. Hallyn" , xfs@oss.sgi.com, Ben Myers , Alex Elder , Dave Chinner , "Eric W. Biederman" Date: Wed, 13 Mar 2013 15:23:10 -0700 Message-Id: <1363213395-10988-9-git-send-email-ebiederm@xmission.com> X-Mailer: git-send-email 1.7.5.4 In-Reply-To: <1363213395-10988-1-git-send-email-ebiederm@xmission.com> References: <87boan3prc.fsf@xmission.com> <1363213395-10988-1-git-send-email-ebiederm@xmission.com> X-XM-AID: U2FsdGVkX1/T2mJwpVrm9dnOTvoCPxafYUleeJrLSGg= X-SA-Exim-Connect-IP: 208.54.5.253 X-SA-Exim-Mail-From: ebiederm@xmission.com Subject: [PATCH 09/14] xfs: Modify xfs_qm_vop_dqalloc to take kuids, kgids, and kprojids. X-ASG-Orig-Subj: [PATCH 09/14] xfs: Modify xfs_qm_vop_dqalloc to take kuids, kgids, and kprojids. X-SA-Exim-Version: 4.2.1 (built Wed, 14 Nov 2012 14:26:46 -0700) X-SA-Exim-Scanned: Yes (on in02.mta.xmission.com) X-Barracuda-Connect: out01.mta.xmission.com[166.70.13.231] X-Barracuda-Start-Time: 1363213559 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_MISMATCH_TO X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125122 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 BSF_SC0_MISMATCH_TO Envelope rcpt doesn't match header From: "Eric W. Biederman" Cc: Ben Myers Cc: Alex Elder Cc: Dave Chinner Signed-off-by: "Eric W. Biederman" --- fs/xfs/xfs_qm.c | 6 +++--- fs/xfs/xfs_quota.h | 4 ++-- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/fs/xfs/xfs_qm.c b/fs/xfs/xfs_qm.c index 861e4e8..308592e 100644 --- a/fs/xfs/xfs_qm.c +++ b/fs/xfs/xfs_qm.c @@ -1616,9 +1616,9 @@ xfs_qm_write_sb_changes( int xfs_qm_vop_dqalloc( struct xfs_inode *ip, - uid_t uid, - gid_t gid, - prid_t prid, + kuid_t uid, + kgid_t gid, + kprojid_t prid, uint flags, struct xfs_dquot **O_udqpp, struct xfs_dquot **O_gdqpp) diff --git a/fs/xfs/xfs_quota.h b/fs/xfs/xfs_quota.h index b50ec5b..f48f801 100644 --- a/fs/xfs/xfs_quota.h +++ b/fs/xfs/xfs_quota.h @@ -311,7 +311,7 @@ extern int xfs_trans_reserve_quota_bydquots(struct xfs_trans *, struct xfs_mount *, struct xfs_dquot *, struct xfs_dquot *, long, long, uint); -extern int xfs_qm_vop_dqalloc(struct xfs_inode *, uid_t, gid_t, prid_t, uint, +extern int xfs_qm_vop_dqalloc(struct xfs_inode *, kuid_t, kgid_t, kprojid_t, uint, struct xfs_dquot **, struct xfs_dquot **); extern void xfs_qm_vop_create_dqattach(struct xfs_trans *, struct xfs_inode *, struct xfs_dquot *, struct xfs_dquot *); @@ -332,7 +332,7 @@ extern void xfs_qm_unmount_quotas(struct xfs_mount *); #else static inline int -xfs_qm_vop_dqalloc(struct xfs_inode *ip, uid_t uid, gid_t gid, prid_t prid, +xfs_qm_vop_dqalloc(struct xfs_inode *ip, kuid_t uid, kgid_t gid, kprojid_t prid, uint flags, struct xfs_dquot **udqp, struct xfs_dquot **gdqp) { *udqp = NULL; -- 1.7.5.4 From ebiederm@xmission.com Wed Mar 13 17:28:04 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id B1E237F56 for ; Wed, 13 Mar 2013 17:28:04 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay3.corp.sgi.com (Postfix) with ESMTP id 2318EAC001 for ; Wed, 13 Mar 2013 15:28:04 -0700 (PDT) X-ASG-Debug-ID: 1363213682-04cbb04b847dea0001-NocioJ Received: from out03.mta.xmission.com (out03.mta.xmission.com [166.70.13.233]) by cuda.sgi.com with ESMTP id sWsTJDeEMnQstVKo (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO); Wed, 13 Mar 2013 15:28:02 -0700 (PDT) X-Barracuda-Envelope-From: ebiederm@xmission.com X-Barracuda-Apparent-Source-IP: 166.70.13.233 Received: from in02.mta.xmission.com ([166.70.13.52]) by out03.mta.xmission.com with esmtps (TLS1.0:RSA_AES_256_CBC_SHA1:32) (Exim 4.76) (envelope-from ) id 1UFu9R-0006qb-C7; Wed, 13 Mar 2013 16:28:01 -0600 Received: from mfd0536d0.tmodns.net ([208.54.5.253] helo=localhost.localdomain) by in02.mta.xmission.com with esmtpsa (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.76) (envelope-from ) id 1UFu9M-0007mg-OM; Wed, 13 Mar 2013 16:28:01 -0600 From: "Eric W. Biederman" To: Cc: Linux Containers , "Serge E. Hallyn" , xfs@oss.sgi.com, Ben Myers , Alex Elder , Dave Chinner , "Eric W. Biederman" Date: Wed, 13 Mar 2013 15:23:11 -0700 Message-Id: <1363213395-10988-10-git-send-email-ebiederm@xmission.com> X-Mailer: git-send-email 1.7.5.4 In-Reply-To: <1363213395-10988-1-git-send-email-ebiederm@xmission.com> References: <87boan3prc.fsf@xmission.com> <1363213395-10988-1-git-send-email-ebiederm@xmission.com> X-XM-AID: U2FsdGVkX18s+EU0N4MpT54H0OMeSje6rX1jusUEbEw= X-SA-Exim-Connect-IP: 208.54.5.253 X-SA-Exim-Mail-From: ebiederm@xmission.com Subject: [PATCH 10/14] xfs: Push struct kqid into xfs_qm_scall_qmlim and xfs_qm_scall_getquota X-ASG-Orig-Subj: [PATCH 10/14] xfs: Push struct kqid into xfs_qm_scall_qmlim and xfs_qm_scall_getquota X-SA-Exim-Version: 4.2.1 (built Wed, 14 Nov 2012 14:26:46 -0700) X-SA-Exim-Scanned: Yes (on in02.mta.xmission.com) X-Barracuda-Connect: out03.mta.xmission.com[166.70.13.233] X-Barracuda-Start-Time: 1363213682 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_MISMATCH_TO X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125122 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 BSF_SC0_MISMATCH_TO Envelope rcpt doesn't match header From: "Eric W. Biederman" - In xfs_qm_scall_getquota map the quota id into the callers user namespace in the returned struct fs_disk_quota - Add a helper is_superquota and use it in xfs_qm_scall_setqlimi to see if we are setting the superusers quota limit. Setting the superuses quota limit on xfs sets the default quota limits for all users. - Move xfs_quota_type into xfs_qm_syscalls.c where it is now used. Cc: Ben Myers Cc: Alex Elder Cc: Dave Chinner Signed-off-by: "Eric W. Biederman" --- fs/xfs/xfs_dquot.h | 6 ++++++ fs/xfs/xfs_qm.h | 4 ++-- fs/xfs/xfs_qm_syscalls.c | 40 +++++++++++++++++++++++++++++----------- fs/xfs/xfs_quotaops.c | 20 ++------------------ 4 files changed, 39 insertions(+), 31 deletions(-) diff --git a/fs/xfs/xfs_dquot.h b/fs/xfs/xfs_dquot.h index c694a84..2c197da 100644 --- a/fs/xfs/xfs_dquot.h +++ b/fs/xfs/xfs_dquot.h @@ -163,4 +163,10 @@ static inline struct xfs_dquot *xfs_qm_dqhold(struct xfs_dquot *dqp) extern const struct xfs_buf_ops xfs_dquot_buf_ops; +/* Is this root's quota in the specified user namespace? */ +static inline bool is_superquota(struct kqid id, struct user_namespace *ns) +{ + return qid_eq(id, make_kqid(ns, id.type, 0)); +} + #endif /* __XFS_DQUOT_H__ */ diff --git a/fs/xfs/xfs_qm.h b/fs/xfs/xfs_qm.h index 44b858b..ce478dc 100644 --- a/fs/xfs/xfs_qm.h +++ b/fs/xfs/xfs_qm.h @@ -114,9 +114,9 @@ extern void xfs_qm_dqrele_all_inodes(xfs_mount_t *, uint); /* quota ops */ extern int xfs_qm_scall_trunc_qfiles(xfs_mount_t *, uint); -extern int xfs_qm_scall_getquota(xfs_mount_t *, xfs_dqid_t, uint, +extern int xfs_qm_scall_getquota(xfs_mount_t *, struct kqid, fs_disk_quota_t *); -extern int xfs_qm_scall_setqlim(xfs_mount_t *, xfs_dqid_t, uint, +extern int xfs_qm_scall_setqlim(xfs_mount_t *, struct kqid, fs_disk_quota_t *); extern int xfs_qm_scall_getqstat(xfs_mount_t *, fs_quota_stat_t *); extern int xfs_qm_scall_quotaon(xfs_mount_t *, uint); diff --git a/fs/xfs/xfs_qm_syscalls.c b/fs/xfs/xfs_qm_syscalls.c index cf9a340..8ad5488 100644 --- a/fs/xfs/xfs_qm_syscalls.c +++ b/fs/xfs/xfs_qm_syscalls.c @@ -48,6 +48,19 @@ STATIC int xfs_qm_log_quotaoff_end(xfs_mount_t *, xfs_qoff_logitem_t *, STATIC uint xfs_qm_export_flags(uint); STATIC uint xfs_qm_export_qtype_flags(uint); +STATIC int +xfs_quota_type(int type) +{ + switch (type) { + case USRQUOTA: + return XFS_DQ_USER; + case GRPQUOTA: + return XFS_DQ_GROUP; + default: + return XFS_DQ_PROJ; + } +} + /* * Turn off quota accounting and/or enforcement for all udquots and/or * gdquots. Called only at unmount time. @@ -473,8 +486,7 @@ xfs_qm_scall_getqstat( int xfs_qm_scall_setqlim( xfs_mount_t *mp, - xfs_dqid_t id, - uint type, + struct kqid id, fs_disk_quota_t *newlim) { struct xfs_quotainfo *q = mp->m_quotainfo; @@ -483,12 +495,16 @@ xfs_qm_scall_setqlim( xfs_trans_t *tp; int error; xfs_qcnt_t hard, soft; + bool superquota; if (newlim->d_fieldmask & ~XFS_DQ_MASK) return EINVAL; if ((newlim->d_fieldmask & XFS_DQ_MASK) == 0) return 0; + /* Is this quota id for root? */ + superquota = is_superquota(id, &init_user_ns); + tp = xfs_trans_alloc(mp, XFS_TRANS_QM_SETQLIM); error = xfs_trans_reserve(tp, 0, XFS_QM_SETQLIM_LOG_RES(mp), 0, 0, XFS_DEFAULT_LOG_COUNT); @@ -509,7 +525,9 @@ xfs_qm_scall_setqlim( * Get the dquot (locked), and join it to the transaction. * Allocate the dquot if this doesn't exist. */ - if ((error = xfs_qm_dqget(mp, NULL, id, type, XFS_QMOPT_DQALLOC, &dqp))) { + if ((error = xfs_qm_dqget(mp, NULL, from_kqid(&init_user_ns, id), + xfs_quota_type(id.type), + XFS_QMOPT_DQALLOC, &dqp))) { xfs_trans_cancel(tp, XFS_TRANS_ABORT); ASSERT(error != ENOENT); goto out_unlock; @@ -529,7 +547,7 @@ xfs_qm_scall_setqlim( if (hard == 0 || hard >= soft) { ddq->d_blk_hardlimit = cpu_to_be64(hard); ddq->d_blk_softlimit = cpu_to_be64(soft); - if (id == 0) { + if (superquota) { q->qi_bhardlimit = hard; q->qi_bsoftlimit = soft; } @@ -545,7 +563,7 @@ xfs_qm_scall_setqlim( if (hard == 0 || hard >= soft) { ddq->d_rtb_hardlimit = cpu_to_be64(hard); ddq->d_rtb_softlimit = cpu_to_be64(soft); - if (id == 0) { + if (superquota) { q->qi_rtbhardlimit = hard; q->qi_rtbsoftlimit = soft; } @@ -562,7 +580,7 @@ xfs_qm_scall_setqlim( if (hard == 0 || hard >= soft) { ddq->d_ino_hardlimit = cpu_to_be64(hard); ddq->d_ino_softlimit = cpu_to_be64(soft); - if (id == 0) { + if (superquota) { q->qi_ihardlimit = hard; q->qi_isoftlimit = soft; } @@ -580,7 +598,7 @@ xfs_qm_scall_setqlim( if (newlim->d_fieldmask & FS_DQ_RTBWARNS) ddq->d_rtbwarns = cpu_to_be16(newlim->d_rtbwarns); - if (id == 0) { + if (superquota) { /* * Timelimits for the super user set the relative time * the other users can be over quota for this file system. @@ -715,8 +733,7 @@ error0: int xfs_qm_scall_getquota( struct xfs_mount *mp, - xfs_dqid_t id, - uint type, + struct kqid id, struct fs_disk_quota *dst) { struct xfs_dquot *dqp; @@ -727,7 +744,8 @@ xfs_qm_scall_getquota( * we aren't passing the XFS_QMOPT_DOALLOC flag. If it doesn't * exist, we'll get ENOENT back. */ - error = xfs_qm_dqget(mp, NULL, id, type, 0, &dqp); + error = xfs_qm_dqget(mp, NULL, from_kqid(&init_user_ns, id), + xfs_quota_type(id.type), 0, &dqp); if (error) return error; @@ -743,7 +761,7 @@ xfs_qm_scall_getquota( memset(dst, 0, sizeof(*dst)); dst->d_version = FS_DQUOT_VERSION; dst->d_flags = xfs_qm_export_qtype_flags(dqp->q_core.d_flags); - dst->d_id = be32_to_cpu(dqp->q_core.d_id); + dst->d_id = from_kqid_munged(current_user_ns(), id); dst->d_blk_hardlimit = XFS_FSB_TO_BB(mp, be64_to_cpu(dqp->q_core.d_blk_hardlimit)); dst->d_blk_softlimit = diff --git a/fs/xfs/xfs_quotaops.c b/fs/xfs/xfs_quotaops.c index 71926d6..4d88faa 100644 --- a/fs/xfs/xfs_quotaops.c +++ b/fs/xfs/xfs_quotaops.c @@ -27,20 +27,6 @@ #include "xfs_qm.h" #include - -STATIC int -xfs_quota_type(int type) -{ - switch (type) { - case USRQUOTA: - return XFS_DQ_USER; - case GRPQUOTA: - return XFS_DQ_GROUP; - default: - return XFS_DQ_PROJ; - } -} - STATIC int xfs_fs_get_xstate( struct super_block *sb, @@ -107,8 +93,7 @@ xfs_fs_get_dqblk( if (!XFS_IS_QUOTA_ON(mp)) return -ESRCH; - return -xfs_qm_scall_getquota(mp, from_kqid(&init_user_ns, qid), - xfs_quota_type(qid.type), fdq); + return -xfs_qm_scall_getquota(mp, qid, fdq); } STATIC int @@ -126,8 +111,7 @@ xfs_fs_set_dqblk( if (!XFS_IS_QUOTA_ON(mp)) return -ESRCH; - return -xfs_qm_scall_setqlim(mp, from_kqid(&init_user_ns, qid), - xfs_quota_type(qid.type), fdq); + return -xfs_qm_scall_setqlim(mp, qid, fdq); } const struct quotactl_ops xfs_quotactl_operations = { -- 1.7.5.4 From ebiederm@xmission.com Wed Mar 13 17:30:29 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id D02517F61 for ; Wed, 13 Mar 2013 17:30:29 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay1.corp.sgi.com (Postfix) with ESMTP id 971A98F8035 for ; Wed, 13 Mar 2013 15:30:29 -0700 (PDT) X-ASG-Debug-ID: 1363213828-04bdf00a0a8d040001-NocioJ Received: from out03.mta.xmission.com (out03.mta.xmission.com [166.70.13.233]) by cuda.sgi.com with ESMTP id TjQDTFLdUP1gOVQM (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO); Wed, 13 Mar 2013 15:30:28 -0700 (PDT) X-Barracuda-Envelope-From: ebiederm@xmission.com X-Barracuda-Apparent-Source-IP: 166.70.13.233 Received: from in02.mta.xmission.com ([166.70.13.52]) by out03.mta.xmission.com with esmtps (TLS1.0:RSA_AES_256_CBC_SHA1:32) (Exim 4.76) (envelope-from ) id 1UFuBn-0007g0-4F; Wed, 13 Mar 2013 16:30:27 -0600 Received: from mfd0536d0.tmodns.net ([208.54.5.253] helo=localhost.localdomain) by in02.mta.xmission.com with esmtpsa (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.76) (envelope-from ) id 1UFuA4-0007mg-R1; Wed, 13 Mar 2013 16:28:49 -0600 From: "Eric W. Biederman" To: Cc: Linux Containers , "Serge E. Hallyn" , xfs@oss.sgi.com, Ben Myers , Alex Elder , Dave Chinner , "Eric W. Biederman" Date: Wed, 13 Mar 2013 15:23:15 -0700 Message-Id: <1363213395-10988-14-git-send-email-ebiederm@xmission.com> X-Mailer: git-send-email 1.7.5.4 In-Reply-To: <1363213395-10988-1-git-send-email-ebiederm@xmission.com> References: <87boan3prc.fsf@xmission.com> <1363213395-10988-1-git-send-email-ebiederm@xmission.com> X-XM-AID: U2FsdGVkX1/etRQQxVoBDbiqDnpmFZwtee9mNOLoa70= X-SA-Exim-Connect-IP: 208.54.5.253 X-SA-Exim-Mail-From: ebiederm@xmission.com Subject: [PATCH 14/14] xfs: Enable building with user namespaces enabled. X-ASG-Orig-Subj: [PATCH 14/14] xfs: Enable building with user namespaces enabled. X-SA-Exim-Version: 4.2.1 (built Wed, 14 Nov 2012 14:26:46 -0700) X-SA-Exim-Scanned: Yes (on in02.mta.xmission.com) X-Barracuda-Connect: out03.mta.xmission.com[166.70.13.233] X-Barracuda-Start-Time: 1363213828 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_MISMATCH_TO X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125122 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 BSF_SC0_MISMATCH_TO Envelope rcpt doesn't match header From: "Eric W. Biederman" Not that all of the types holding uids, gids, and projectids have been converted it is safe to allow users in different user namespaces to access an xfs filesystem. Cc: Ben Myers Cc: Alex Elder Cc: Dave Chinner Signed-off-by: "Eric W. Biederman" --- init/Kconfig | 1 - 1 files changed, 0 insertions(+), 1 deletions(-) diff --git a/init/Kconfig b/init/Kconfig index 22616cd..b5a9ff8 100644 --- a/init/Kconfig +++ b/init/Kconfig @@ -1068,7 +1068,6 @@ config UIDGID_CONVERTED default y # Filesystems - depends on XFS_FS = n config UIDGID_STRICT_TYPE_CHECKS bool "Require conversions between uid/gids and their internal representation" -- 1.7.5.4 From ebiederm@xmission.com Wed Mar 13 17:30:31 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id F32FB7F61 for ; Wed, 13 Mar 2013 17:30:30 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay3.corp.sgi.com (Postfix) with ESMTP id 67130AC001 for ; Wed, 13 Mar 2013 15:30:30 -0700 (PDT) X-ASG-Debug-ID: 1363213828-04cb6c4a45877d0001-NocioJ Received: from out03.mta.xmission.com (out03.mta.xmission.com [166.70.13.233]) by cuda.sgi.com with ESMTP id DsciVSdXpc2OcRfJ (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO); Wed, 13 Mar 2013 15:30:29 -0700 (PDT) X-Barracuda-Envelope-From: ebiederm@xmission.com X-Barracuda-Apparent-Source-IP: 166.70.13.233 Received: from in02.mta.xmission.com ([166.70.13.52]) by out03.mta.xmission.com with esmtps (TLS1.0:RSA_AES_256_CBC_SHA1:32) (Exim 4.76) (envelope-from ) id 1UFuBo-0007gH-0U; Wed, 13 Mar 2013 16:30:28 -0600 Received: from mfd0536d0.tmodns.net ([208.54.5.253] helo=localhost.localdomain) by in02.mta.xmission.com with esmtpsa (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.76) (envelope-from ) id 1UFu9d-0007mg-Hb; Wed, 13 Mar 2013 16:28:16 -0600 From: "Eric W. Biederman" To: Cc: Linux Containers , "Serge E. Hallyn" , xfs@oss.sgi.com, Ben Myers , Alex Elder , Dave Chinner , "Eric W. Biederman" Date: Wed, 13 Mar 2013 15:23:13 -0700 Message-Id: <1363213395-10988-12-git-send-email-ebiederm@xmission.com> X-Mailer: git-send-email 1.7.5.4 In-Reply-To: <1363213395-10988-1-git-send-email-ebiederm@xmission.com> References: <87boan3prc.fsf@xmission.com> <1363213395-10988-1-git-send-email-ebiederm@xmission.com> X-XM-AID: U2FsdGVkX19Z6is1IVfWmilP2MEWFWne+ieaenC9rJU= X-SA-Exim-Connect-IP: 208.54.5.253 X-SA-Exim-Mail-From: ebiederm@xmission.com Subject: [PATCH 12/14] xfs: Remember the kqid for a quota X-ASG-Orig-Subj: [PATCH 12/14] xfs: Remember the kqid for a quota X-SA-Exim-Version: 4.2.1 (built Wed, 14 Nov 2012 14:26:46 -0700) X-SA-Exim-Scanned: Yes (on in02.mta.xmission.com) X-Barracuda-Connect: out03.mta.xmission.com[166.70.13.233] X-Barracuda-Start-Time: 1363213829 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_MISMATCH_TO X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125122 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 BSF_SC0_MISMATCH_TO Envelope rcpt doesn't match header From: "Eric W. Biederman" - Add q_id to struct xfs_quota - Modify xfs_qm_dqread to take a struct kqid, allowing xfs_qm_dqread to set q_id on fresh quota structures. - Modify xfs_qm_dqget and xfs_qm_init_quota_info to pass a kqid to xfs_qm_dqread Cc: Ben Myers Cc: Alex Elder Cc: Dave Chinner Signed-off-by: "Eric W. Biederman" --- fs/xfs/xfs_dquot.c | 12 ++++++------ fs/xfs/xfs_dquot.h | 3 ++- fs/xfs/xfs_qm.c | 9 +++++---- 3 files changed, 13 insertions(+), 11 deletions(-) diff --git a/fs/xfs/xfs_dquot.c b/fs/xfs/xfs_dquot.c index 51e1c31..00d4b87 100644 --- a/fs/xfs/xfs_dquot.c +++ b/fs/xfs/xfs_dquot.c @@ -581,8 +581,7 @@ xfs_qm_dqtobp( int xfs_qm_dqread( struct xfs_mount *mp, - xfs_dqid_t id, - uint type, + struct kqid id, uint flags, struct xfs_dquot **O_dqpp) { @@ -596,8 +595,9 @@ xfs_qm_dqread( dqp = kmem_zone_zalloc(xfs_qm_dqzone, KM_SLEEP); - dqp->dq_flags = type; - dqp->q_core.d_id = cpu_to_be32(id); + dqp->q_id = id; + dqp->dq_flags = xfs_quota_type(id.type); + dqp->q_core.d_id = cpu_to_be32(from_kqid(&init_user_ns, id)); dqp->q_mount = mp; INIT_LIST_HEAD(&dqp->q_lru); mutex_init(&dqp->q_qlock); @@ -615,7 +615,7 @@ xfs_qm_dqread( * Make sure group quotas have a different lock class than user * quotas. */ - if (!(type & XFS_DQ_USER)) + if (id.type != USRQUOTA) lockdep_set_class(&dqp->q_qlock, &xfs_dquot_other_class); XFS_STATS_INC(xs_qm_dquot); @@ -779,7 +779,7 @@ restart: if (ip) xfs_iunlock(ip, XFS_ILOCK_EXCL); - error = xfs_qm_dqread(mp, id, type, flags, &dqp); + error = xfs_qm_dqread(mp, qid, flags, &dqp); if (ip) xfs_ilock(ip, XFS_ILOCK_EXCL); diff --git a/fs/xfs/xfs_dquot.h b/fs/xfs/xfs_dquot.h index 3566548..0b6020e 100644 --- a/fs/xfs/xfs_dquot.h +++ b/fs/xfs/xfs_dquot.h @@ -36,6 +36,7 @@ struct xfs_trans; * The incore dquot structure */ typedef struct xfs_dquot { + struct kqid q_id; /* quota identifier */ uint dq_flags; /* various flags (XFS_DQ_*) */ struct list_head q_lru; /* global free list of dquots */ struct xfs_mount*q_mount; /* filesystem this relates to */ @@ -138,7 +139,7 @@ static inline xfs_dquot_t *xfs_inode_dquot(struct xfs_inode *ip, int type) XFS_DQ_TO_QINF(dqp)->qi_uquotaip : \ XFS_DQ_TO_QINF(dqp)->qi_gquotaip) -extern int xfs_qm_dqread(struct xfs_mount *, xfs_dqid_t, uint, +extern int xfs_qm_dqread(struct xfs_mount *, struct kqid, uint, struct xfs_dquot **); extern void xfs_qm_dqdestroy(xfs_dquot_t *); extern int xfs_qm_dqflush(struct xfs_dquot *, struct xfs_buf **); diff --git a/fs/xfs/xfs_qm.c b/fs/xfs/xfs_qm.c index 31711ed..363a662 100644 --- a/fs/xfs/xfs_qm.c +++ b/fs/xfs/xfs_qm.c @@ -673,10 +673,11 @@ xfs_qm_init_quotainfo( * Since we may not have done a quotacheck by this point, just read * the dquot without attaching it to any hashtables or lists. */ - error = xfs_qm_dqread(mp, 0, - XFS_IS_UQUOTA_RUNNING(mp) ? XFS_DQ_USER : - (XFS_IS_GQUOTA_RUNNING(mp) ? XFS_DQ_GROUP : - XFS_DQ_PROJ), + error = xfs_qm_dqread(mp, + make_kqid(&init_user_ns, + XFS_IS_UQUOTA_RUNNING(mp) ? USRQUOTA : + (XFS_IS_GQUOTA_RUNNING(mp) ? GRPQUOTA : + PRJQUOTA), 0), XFS_QMOPT_DOWARN, &dqp); if (!error) { xfs_disk_dquot_t *ddqp = &dqp->q_core; -- 1.7.5.4 From ebiederm@xmission.com Wed Mar 13 17:30:32 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 6BC147F6D for ; Wed, 13 Mar 2013 17:30:32 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay1.corp.sgi.com (Postfix) with ESMTP id 4F65C8F8033 for ; Wed, 13 Mar 2013 15:30:32 -0700 (PDT) X-ASG-Debug-ID: 1363213830-04cbb04b857e170001-NocioJ Received: from out03.mta.xmission.com (out03.mta.xmission.com [166.70.13.233]) by cuda.sgi.com with ESMTP id rGsyZT4EjGicdtGw (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO); Wed, 13 Mar 2013 15:30:31 -0700 (PDT) X-Barracuda-Envelope-From: ebiederm@xmission.com X-Barracuda-Apparent-Source-IP: 166.70.13.233 Received: from in02.mta.xmission.com ([166.70.13.52]) by out03.mta.xmission.com with esmtps (TLS1.0:RSA_AES_256_CBC_SHA1:32) (Exim 4.76) (envelope-from ) id 1UFuBp-0007gr-U9; Wed, 13 Mar 2013 16:30:30 -0600 Received: from mfd0536d0.tmodns.net ([208.54.5.253] helo=localhost.localdomain) by in02.mta.xmission.com with esmtpsa (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.76) (envelope-from ) id 1UFu9q-0007mg-Om; Wed, 13 Mar 2013 16:28:33 -0600 From: "Eric W. Biederman" To: Cc: Linux Containers , "Serge E. Hallyn" , xfs@oss.sgi.com, Ben Myers , Alex Elder , Dave Chinner , "Eric W. Biederman" Date: Wed, 13 Mar 2013 15:23:14 -0700 Message-Id: <1363213395-10988-13-git-send-email-ebiederm@xmission.com> X-Mailer: git-send-email 1.7.5.4 In-Reply-To: <1363213395-10988-1-git-send-email-ebiederm@xmission.com> References: <87boan3prc.fsf@xmission.com> <1363213395-10988-1-git-send-email-ebiederm@xmission.com> X-XM-AID: U2FsdGVkX1859sZkZ5tQSFqMzvmHfHLRNS5GSkRgsXw= X-SA-Exim-Connect-IP: 208.54.5.253 X-SA-Exim-Mail-From: ebiederm@xmission.com Subject: [PATCH 13/14] xfs: Use q_id instead of q_core.d_id. X-ASG-Orig-Subj: [PATCH 13/14] xfs: Use q_id instead of q_core.d_id. X-SA-Exim-Version: 4.2.1 (built Wed, 14 Nov 2012 14:26:46 -0700) X-SA-Exim-Scanned: Yes (on in02.mta.xmission.com) X-Barracuda-Connect: out03.mta.xmission.com[166.70.13.233] X-Barracuda-Start-Time: 1363213830 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_MISMATCH_TO X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125122 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 BSF_SC0_MISMATCH_TO Envelope rcpt doesn't match header From: "Eric W. Biederman" - Use qid_lt on q_id when compariting two quota entries for order. - Use qid_eq or !qid_eq when comparing a quota entry for equality or inequality. - Use is_superquota when testing for the magic quota id of 0. - Use make_kqid_uid, make_kqid_gid, and make_kqid_projid when comparing a quota id against a uids, gids, or projids as appropriate. - For tracing use from_kqid and map to the init user namespace. Tracers outside of the initial user namespace are not allowed. - For generating ondisk values continue to use q_core.d_id. - For cases where we want an index and don't care which quota it is continue to use be32_to_cpu(...->q_core.d_id) Cc: Ben Myers Cc: Alex Elder Cc: Dave Chinner Signed-off-by: "Eric W. Biederman" --- fs/xfs/xfs_dquot.c | 3 +-- fs/xfs/xfs_qm.c | 18 +++++++++--------- fs/xfs/xfs_trace.h | 2 +- fs/xfs/xfs_trans_dquot.c | 8 ++------ 4 files changed, 13 insertions(+), 18 deletions(-) diff --git a/fs/xfs/xfs_dquot.c b/fs/xfs/xfs_dquot.c index 00d4b87..6b306d7 100644 --- a/fs/xfs/xfs_dquot.c +++ b/fs/xfs/xfs_dquot.c @@ -1086,8 +1086,7 @@ xfs_dqlock2( { if (d1 && d2) { ASSERT(d1 != d2); - if (be32_to_cpu(d1->q_core.d_id) > - be32_to_cpu(d2->q_core.d_id)) { + if (qid_lt(d2->q_id, d1->q_id)) { mutex_lock(&d2->q_qlock); mutex_lock_nested(&d1->q_qlock, XFS_QLOCK_NESTED); } else { diff --git a/fs/xfs/xfs_qm.c b/fs/xfs/xfs_qm.c index 363a662..ccf2689 100644 --- a/fs/xfs/xfs_qm.c +++ b/fs/xfs/xfs_qm.c @@ -407,7 +407,7 @@ xfs_qm_dqattach_one( * hold the ilock. */ dqp = udqhint->q_gdquot; - if (dqp && qid_eq(make_kqid(&init_user_ns, id.type, be32_to_cpu(dqp->q_core.d_id)), id)) { + if (dqp && qid_eq(dqp->q_id, id)) { ASSERT(*IO_idqpp == NULL); *IO_idqpp = xfs_qm_dqhold(dqp); @@ -1057,7 +1057,7 @@ xfs_qm_quotacheck_dqadjust( * * There are no timers for the default values set in the root dquot. */ - if (dqp->q_core.d_id) { + if (!is_superquota(dqp->q_id, &init_user_ns)) { xfs_qm_adjust_dqlimits(mp, &dqp->q_core); xfs_qm_adjust_dqtimers(mp, &dqp->q_core); } @@ -1804,7 +1804,7 @@ xfs_qm_vop_chown_reserve( XFS_QMOPT_RES_RTBLKS : XFS_QMOPT_RES_REGBLKS; if (XFS_IS_UQUOTA_ON(mp) && udqp && - !uid_eq(ip->i_d.di_uid, (uid_t)be32_to_cpu(udqp->q_core.d_id))) { + !qid_eq(make_kqid_uid(ip->i_d.di_uid), udqp->q_id)) { delblksudq = udqp; /* * If there are delayed allocation blocks, then we have to @@ -1818,12 +1818,12 @@ xfs_qm_vop_chown_reserve( } if (XFS_IS_OQUOTA_ON(ip->i_mount) && gdqp) { if (XFS_IS_PQUOTA_ON(ip->i_mount) && - !projid_eq(ip->i_d.di_projid, be32_to_cpu(gdqp->q_core.d_id))) + !qid_eq(make_kqid_projid(ip->i_d.di_projid), gdqp->q_id)) prjflags = XFS_QMOPT_ENOSPC; if (prjflags || (XFS_IS_GQUOTA_ON(ip->i_mount) && - !gid_eq(ip->i_d.di_gid, be32_to_cpu(gdqp->q_core.d_id)))) { + !qid_eq(make_kqid_gid(ip->i_d.di_gid), gdqp->q_id))) { delblksgdq = gdqp; if (delblks) { ASSERT(ip->i_gdquot); @@ -1907,7 +1907,7 @@ xfs_qm_vop_create_dqattach( if (udqp) { ASSERT(ip->i_udquot == NULL); ASSERT(XFS_IS_UQUOTA_ON(mp)); - ASSERT(uid_eq(ip->i_d.di_uid, be32_to_cpu(udqp->q_core.d_id))); + ASSERT(qid_eq(make_kqid_uid(ip->i_d.di_uid), udqp->q_id)); ip->i_udquot = xfs_qm_dqhold(udqp); xfs_trans_mod_dquot(tp, udqp, XFS_TRANS_DQ_ICOUNT, 1); @@ -1915,9 +1915,9 @@ xfs_qm_vop_create_dqattach( if (gdqp) { ASSERT(ip->i_gdquot == NULL); ASSERT(XFS_IS_OQUOTA_ON(mp)); - ASSERT(XFS_IS_GQUOTA_ON(mp) ? - gid_eq(ip->i_d.di_gid, be32_to_cpu(gdqp->q_core.d_id)): - projid_eq(ip->i_d.di_projid, be32_to_cpu(gdqp->q_core.d_id))); + ASSERT(qid_eq(XFS_IS_GQUOTA_ON(mp) ? + make_kqid_gid(ip->i_d.di_gid) : + make_kqid_projid(ip->i_d.di_projid), gdqp->q_id)); ip->i_gdquot = xfs_qm_dqhold(gdqp); xfs_trans_mod_dquot(tp, gdqp, XFS_TRANS_DQ_ICOUNT, 1); diff --git a/fs/xfs/xfs_trace.h b/fs/xfs/xfs_trace.h index 16a8129..a694663 100644 --- a/fs/xfs/xfs_trace.h +++ b/fs/xfs/xfs_trace.h @@ -713,7 +713,7 @@ DECLARE_EVENT_CLASS(xfs_dquot_class, ), \ TP_fast_assign( __entry->dev = dqp->q_mount->m_super->s_dev; - __entry->id = be32_to_cpu(dqp->q_core.d_id); + __entry->id = from_kqid(&init_user_ns, dqp->q_id); __entry->flags = dqp->dq_flags; __entry->nrefs = dqp->q_nrefs; __entry->res_bcount = dqp->q_res_bcount; diff --git a/fs/xfs/xfs_trans_dquot.c b/fs/xfs/xfs_trans_dquot.c index 642c2d6..76a5761 100644 --- a/fs/xfs/xfs_trans_dquot.c +++ b/fs/xfs/xfs_trans_dquot.c @@ -578,11 +578,7 @@ xfs_quota_warn( /* no warnings for project quotas - we just return ENOSPC later */ if (dqp->dq_flags & XFS_DQ_PROJ) return; - quota_send_warning(make_kqid(&init_user_ns, - (dqp->dq_flags & XFS_DQ_USER) ? - USRQUOTA : GRPQUOTA, - be32_to_cpu(dqp->q_core.d_id)), - mp->m_super->s_dev, type); + quota_send_warning(dqp->q_id, mp->m_super->s_dev, type); } /* @@ -638,7 +634,7 @@ xfs_trans_dqresv( } if ((flags & XFS_QMOPT_FORCE_RES) == 0 && - dqp->q_core.d_id && + !is_superquota(dqp->q_id, &init_user_ns) && ((XFS_IS_UQUOTA_ENFORCED(dqp->q_mount) && XFS_QM_ISUDQ(dqp)) || (XFS_IS_OQUOTA_ENFORCED(dqp->q_mount) && (XFS_QM_ISPDQ(dqp) || XFS_QM_ISGDQ(dqp))))) { -- 1.7.5.4 From ebiederm@xmission.com Wed Mar 13 17:30:32 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 232FD7F67 for ; Wed, 13 Mar 2013 17:30:32 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay1.corp.sgi.com (Postfix) with ESMTP id E349C8F804B for ; Wed, 13 Mar 2013 15:30:31 -0700 (PDT) X-ASG-Debug-ID: 1363213830-04cb6c4a44877d0001-NocioJ Received: from out02.mta.xmission.com (out02.mta.xmission.com [166.70.13.232]) by cuda.sgi.com with ESMTP id 182CPFUWFOBHVZoX (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO); Wed, 13 Mar 2013 15:30:30 -0700 (PDT) X-Barracuda-Envelope-From: ebiederm@xmission.com X-Barracuda-Apparent-Source-IP: 166.70.13.232 Received: from in02.mta.xmission.com ([166.70.13.52]) by out02.mta.xmission.com with esmtps (TLS1.0:RSA_AES_256_CBC_SHA1:32) (Exim 4.76) (envelope-from ) id 1UFuBo-0003nw-N1; Wed, 13 Mar 2013 16:30:29 -0600 Received: from mfd0536d0.tmodns.net ([208.54.5.253] helo=localhost.localdomain) by in02.mta.xmission.com with esmtpsa (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.76) (envelope-from ) id 1UFu9T-0007mg-Ly; Wed, 13 Mar 2013 16:28:08 -0600 From: "Eric W. Biederman" To: Cc: Linux Containers , "Serge E. Hallyn" , xfs@oss.sgi.com, Ben Myers , Alex Elder , Dave Chinner , "Eric W. Biederman" Date: Wed, 13 Mar 2013 15:23:12 -0700 Message-Id: <1363213395-10988-11-git-send-email-ebiederm@xmission.com> X-Mailer: git-send-email 1.7.5.4 In-Reply-To: <1363213395-10988-1-git-send-email-ebiederm@xmission.com> References: <87boan3prc.fsf@xmission.com> <1363213395-10988-1-git-send-email-ebiederm@xmission.com> X-XM-AID: U2FsdGVkX1+3hTt9XSrFmwc8PAmauWlBzCfh/SjTWNE= X-SA-Exim-Connect-IP: 208.54.5.253 X-SA-Exim-Mail-From: ebiederm@xmission.com Subject: [PATCH 11/14] xfs: Modify xfs_qm_dqget to take a struct kqid. X-ASG-Orig-Subj: [PATCH 11/14] xfs: Modify xfs_qm_dqget to take a struct kqid. X-SA-Exim-Version: 4.2.1 (built Wed, 14 Nov 2012 14:26:46 -0700) X-SA-Exim-Scanned: Yes (on in02.mta.xmission.com) X-Barracuda-Connect: out02.mta.xmission.com[166.70.13.232] X-Barracuda-Start-Time: 1363213830 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_MISMATCH_TO X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125122 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 BSF_SC0_MISMATCH_TO Envelope rcpt doesn't match header From: "Eric W. Biederman" - Modify xfs_qm_dqget, xfs_qm_dqattach_one, and xfs_qm_qutoacheck_dqadjust to take a struct kqid instead of an id and type pair. - Modify their callers to pass them a struct kqid. - Move xfs_qutoa_type into xfs_dquot.c where it is now used. Cc: Ben Myers Cc: Alex Elder Cc: Dave Chinner Signed-off-by: "Eric W. Biederman" --- fs/xfs/xfs_dquot.c | 24 +++++++++++++++++++----- fs/xfs/xfs_dquot.h | 4 ++-- fs/xfs/xfs_qm.c | 42 +++++++++++++++++++----------------------- fs/xfs/xfs_qm_bhv.c | 2 +- fs/xfs/xfs_qm_syscalls.c | 20 ++------------------ 5 files changed, 43 insertions(+), 49 deletions(-) diff --git a/fs/xfs/xfs_dquot.c b/fs/xfs/xfs_dquot.c index 8025eb2..51e1c31 100644 --- a/fs/xfs/xfs_dquot.c +++ b/fs/xfs/xfs_dquot.c @@ -63,6 +63,19 @@ static struct kmem_zone *xfs_qm_dqzone; static struct lock_class_key xfs_dquot_other_class; +STATIC int +xfs_quota_type(int type) +{ + switch (type) { + case USRQUOTA: + return XFS_DQ_USER; + case GRPQUOTA: + return XFS_DQ_GROUP; + default: + return XFS_DQ_PROJ; + } +} + /* * This is called to free all the memory associated with a dquot */ @@ -696,20 +709,21 @@ int xfs_qm_dqget( xfs_mount_t *mp, xfs_inode_t *ip, /* locked inode (optional) */ - xfs_dqid_t id, /* uid/projid/gid depending on type */ - uint type, /* XFS_DQ_USER/XFS_DQ_PROJ/XFS_DQ_GROUP */ + struct kqid qid, /* uid/projid/gid depending on type */ uint flags, /* DQALLOC, DQSUSER, DQREPAIR, DOWARN */ xfs_dquot_t **O_dqpp) /* OUT : locked incore dquot */ { struct xfs_quotainfo *qi = mp->m_quotainfo; + uint id = from_kqid(&init_user_ns, qid); + uint type = xfs_quota_type(qid.type); struct radix_tree_root *tree = XFS_DQUOT_TREE(qi, type); struct xfs_dquot *dqp; int error; ASSERT(XFS_IS_QUOTA_RUNNING(mp)); - if ((! XFS_IS_UQUOTA_ON(mp) && type == XFS_DQ_USER) || - (! XFS_IS_PQUOTA_ON(mp) && type == XFS_DQ_PROJ) || - (! XFS_IS_GQUOTA_ON(mp) && type == XFS_DQ_GROUP)) { + if ((! XFS_IS_UQUOTA_ON(mp) && qid.type == USRQUOTA) || + (! XFS_IS_PQUOTA_ON(mp) && qid.type == PRJQUOTA) || + (! XFS_IS_GQUOTA_ON(mp) && qid.type == GRPQUOTA)) { return (ESRCH); } diff --git a/fs/xfs/xfs_dquot.h b/fs/xfs/xfs_dquot.h index 2c197da..3566548 100644 --- a/fs/xfs/xfs_dquot.h +++ b/fs/xfs/xfs_dquot.h @@ -147,8 +147,8 @@ extern void xfs_qm_adjust_dqtimers(xfs_mount_t *, xfs_disk_dquot_t *); extern void xfs_qm_adjust_dqlimits(xfs_mount_t *, xfs_disk_dquot_t *); -extern int xfs_qm_dqget(xfs_mount_t *, xfs_inode_t *, - xfs_dqid_t, uint, uint, xfs_dquot_t **); +extern int xfs_qm_dqget(xfs_mount_t *, xfs_inode_t *, struct kqid, + uint, xfs_dquot_t **); extern void xfs_qm_dqput(xfs_dquot_t *); extern void xfs_dqlock2(struct xfs_dquot *, struct xfs_dquot *); diff --git a/fs/xfs/xfs_qm.c b/fs/xfs/xfs_qm.c index 308592e..31711ed 100644 --- a/fs/xfs/xfs_qm.c +++ b/fs/xfs/xfs_qm.c @@ -367,8 +367,7 @@ xfs_qm_unmount_quotas( STATIC int xfs_qm_dqattach_one( xfs_inode_t *ip, - xfs_dqid_t id, - uint type, + struct kqid id, uint doalloc, xfs_dquot_t *udqhint, /* hint */ xfs_dquot_t **IO_idqpp) @@ -397,7 +396,7 @@ xfs_qm_dqattach_one( * the user dquot. */ if (udqhint) { - ASSERT(type == XFS_DQ_GROUP || type == XFS_DQ_PROJ); + ASSERT(id.type == GRPQUOTA || id.type == PRJQUOTA); xfs_dqlock(udqhint); /* @@ -408,7 +407,7 @@ xfs_qm_dqattach_one( * hold the ilock. */ dqp = udqhint->q_gdquot; - if (dqp && be32_to_cpu(dqp->q_core.d_id) == id) { + if (dqp && qid_eq(make_kqid(&init_user_ns, id.type, be32_to_cpu(dqp->q_core.d_id)), id)) { ASSERT(*IO_idqpp == NULL); *IO_idqpp = xfs_qm_dqhold(dqp); @@ -432,7 +431,7 @@ xfs_qm_dqattach_one( * disk and we didn't ask it to allocate; * ESRCH if quotas got turned off suddenly. */ - error = xfs_qm_dqget(ip->i_mount, ip, id, type, + error = xfs_qm_dqget(ip->i_mount, ip, id, doalloc | XFS_QMOPT_DOWARN, &dqp); if (error) return error; @@ -516,7 +515,7 @@ xfs_qm_dqattach_locked( ASSERT(xfs_isilocked(ip, XFS_ILOCK_EXCL)); if (XFS_IS_UQUOTA_ON(mp)) { - error = xfs_qm_dqattach_one(ip, ip->i_d.di_uid, XFS_DQ_USER, + error = xfs_qm_dqattach_one(ip, make_kqid_uid(ip->i_d.di_uid), flags & XFS_QMOPT_DQALLOC, NULL, &ip->i_udquot); if (error) @@ -527,10 +526,10 @@ xfs_qm_dqattach_locked( ASSERT(xfs_isilocked(ip, XFS_ILOCK_EXCL)); if (XFS_IS_OQUOTA_ON(mp)) { error = XFS_IS_GQUOTA_ON(mp) ? - xfs_qm_dqattach_one(ip, ip->i_d.di_gid, XFS_DQ_GROUP, + xfs_qm_dqattach_one(ip, make_kqid_gid(ip->i_d.di_gid), flags & XFS_QMOPT_DQALLOC, ip->i_udquot, &ip->i_gdquot) : - xfs_qm_dqattach_one(ip, ip->i_d.di_projid, XFS_DQ_PROJ, + xfs_qm_dqattach_one(ip, make_kqid_projid(ip->i_d.di_projid), flags & XFS_QMOPT_DQALLOC, ip->i_udquot, &ip->i_gdquot); /* @@ -1016,8 +1015,7 @@ out: STATIC int xfs_qm_quotacheck_dqadjust( struct xfs_inode *ip, - xfs_dqid_t id, - uint type, + struct kqid id, xfs_qcnt_t nblks, xfs_qcnt_t rtblks) { @@ -1025,7 +1023,7 @@ xfs_qm_quotacheck_dqadjust( struct xfs_dquot *dqp; int error; - error = xfs_qm_dqget(mp, ip, id, type, + error = xfs_qm_dqget(mp, ip, id, XFS_QMOPT_DQALLOC | XFS_QMOPT_DOWARN, &dqp); if (error) { /* @@ -1160,22 +1158,22 @@ xfs_qm_dqusage_adjust( * and quotaoffs don't race. (Quotachecks happen at mount time only). */ if (XFS_IS_UQUOTA_ON(mp)) { - error = xfs_qm_quotacheck_dqadjust(ip, ip->i_d.di_uid, - XFS_DQ_USER, nblks, rtblks); + error = xfs_qm_quotacheck_dqadjust(ip, make_kqid_uid(ip->i_d.di_uid), + nblks, rtblks); if (error) goto error0; } if (XFS_IS_GQUOTA_ON(mp)) { - error = xfs_qm_quotacheck_dqadjust(ip, ip->i_d.di_gid, - XFS_DQ_GROUP, nblks, rtblks); + error = xfs_qm_quotacheck_dqadjust(ip, make_kqid_gid(ip->i_d.di_gid), + nblks, rtblks); if (error) goto error0; } if (XFS_IS_PQUOTA_ON(mp)) { - error = xfs_qm_quotacheck_dqadjust(ip, ip->i_d.di_projid, - XFS_DQ_PROJ, nblks, rtblks); + error = xfs_qm_quotacheck_dqadjust(ip, make_kqid_projid(ip->i_d.di_projid), + nblks, rtblks); if (error) goto error0; } @@ -1662,8 +1660,7 @@ xfs_qm_vop_dqalloc( * holding ilock. */ xfs_iunlock(ip, lockflags); - if ((error = xfs_qm_dqget(mp, NULL, (xfs_dqid_t) uid, - XFS_DQ_USER, + if ((error = xfs_qm_dqget(mp, NULL, make_kqid_uid(uid), XFS_QMOPT_DQALLOC | XFS_QMOPT_DOWARN, &uq))) { @@ -1688,8 +1685,7 @@ xfs_qm_vop_dqalloc( if ((flags & XFS_QMOPT_GQUOTA) && XFS_IS_GQUOTA_ON(mp)) { if (!gid_eq(ip->i_d.di_gid, gid)) { xfs_iunlock(ip, lockflags); - if ((error = xfs_qm_dqget(mp, NULL, (xfs_dqid_t)gid, - XFS_DQ_GROUP, + if ((error = xfs_qm_dqget(mp, NULL, make_kqid_gid(gid), XFS_QMOPT_DQALLOC | XFS_QMOPT_DOWARN, &gq))) { @@ -1708,8 +1704,8 @@ xfs_qm_vop_dqalloc( } else if ((flags & XFS_QMOPT_PQUOTA) && XFS_IS_PQUOTA_ON(mp)) { if (!projid_eq(ip->i_d.di_projid, prid)) { xfs_iunlock(ip, lockflags); - if ((error = xfs_qm_dqget(mp, NULL, (xfs_dqid_t)prid, - XFS_DQ_PROJ, + if ((error = xfs_qm_dqget(mp, NULL, + make_kqid_projid(prid), XFS_QMOPT_DQALLOC | XFS_QMOPT_DOWARN, &gq))) { diff --git a/fs/xfs/xfs_qm_bhv.c b/fs/xfs/xfs_qm_bhv.c index 7d44746..dda0f7a 100644 --- a/fs/xfs/xfs_qm_bhv.c +++ b/fs/xfs/xfs_qm_bhv.c @@ -79,7 +79,7 @@ xfs_qm_statvfs( xfs_mount_t *mp = ip->i_mount; xfs_dquot_t *dqp; - if (!xfs_qm_dqget(mp, NULL, ip->i_d.di_projid, XFS_DQ_PROJ, 0, &dqp)) { + if (!xfs_qm_dqget(mp, NULL, make_kqid_projid(ip->i_d.di_projid), 0, &dqp)) { xfs_fill_statvfs_from_dquot(statp, dqp); xfs_qm_dqput(dqp); } diff --git a/fs/xfs/xfs_qm_syscalls.c b/fs/xfs/xfs_qm_syscalls.c index 8ad5488..03876dc 100644 --- a/fs/xfs/xfs_qm_syscalls.c +++ b/fs/xfs/xfs_qm_syscalls.c @@ -48,19 +48,6 @@ STATIC int xfs_qm_log_quotaoff_end(xfs_mount_t *, xfs_qoff_logitem_t *, STATIC uint xfs_qm_export_flags(uint); STATIC uint xfs_qm_export_qtype_flags(uint); -STATIC int -xfs_quota_type(int type) -{ - switch (type) { - case USRQUOTA: - return XFS_DQ_USER; - case GRPQUOTA: - return XFS_DQ_GROUP; - default: - return XFS_DQ_PROJ; - } -} - /* * Turn off quota accounting and/or enforcement for all udquots and/or * gdquots. Called only at unmount time. @@ -525,9 +512,7 @@ xfs_qm_scall_setqlim( * Get the dquot (locked), and join it to the transaction. * Allocate the dquot if this doesn't exist. */ - if ((error = xfs_qm_dqget(mp, NULL, from_kqid(&init_user_ns, id), - xfs_quota_type(id.type), - XFS_QMOPT_DQALLOC, &dqp))) { + if ((error = xfs_qm_dqget(mp, NULL, id, XFS_QMOPT_DQALLOC, &dqp))) { xfs_trans_cancel(tp, XFS_TRANS_ABORT); ASSERT(error != ENOENT); goto out_unlock; @@ -744,8 +729,7 @@ xfs_qm_scall_getquota( * we aren't passing the XFS_QMOPT_DOALLOC flag. If it doesn't * exist, we'll get ENOENT back. */ - error = xfs_qm_dqget(mp, NULL, from_kqid(&init_user_ns, id), - xfs_quota_type(id.type), 0, &dqp); + error = xfs_qm_dqget(mp, NULL, id, 0, &dqp); if (error) return error; -- 1.7.5.4 From katyamoskalenko@paulistano.com.br Wed Mar 13 17:32:12 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=HTML_MESSAGE autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 83A6F7F61 for ; Wed, 13 Mar 2013 17:32:12 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay1.corp.sgi.com (Postfix) with ESMTP id 3ABCF8F8033 for ; Wed, 13 Mar 2013 15:32:11 -0700 (PDT) X-ASG-Debug-ID: 1363213927-04bdf00a0a8d1d0001-NocioJ Received: from ru-tek.ru (ru-tek.ru [91.218.228.25]) by cuda.sgi.com with ESMTP id 7JG4qTF7bVFGggjR (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO) for ; Wed, 13 Mar 2013 15:32:09 -0700 (PDT) X-Barracuda-Envelope-From: katyamoskalenko@paulistano.com.br X-Barracuda-Apparent-Source-IP: 91.218.228.25 Received: from Unknown ([58.213.157.68]) (authenticated bits=0) by ru-tek.ru (8.13.8/8.13.8) with ESMTP id r2DMVsnB003077; Thu, 14 Mar 2013 02:31:59 +0400 Message-ID: <470BB37DEBFA4D60B57C2AE9CBA900F4@aolwim> Reply-To: =?windows-1251?B?w87Rx8DKwMcgMjAxMw==?= <65846542@qip.ru> From: =?windows-1251?B?w87Rx8DKwMcgMjAxMw==?= To: , , , , Subject: =?windows-1251?B?zc7CzsUgwiDP0MDCzsLOzCDMxdXAzcjHzMUg?= =?windows-1251?B?x8DK08/OyiDSzsLA0M7CIMgg09HL08MgxMvf?= =?windows-1251?B?IMPO0dPEwNDR0sLFzc3b1SDIIMzTzcjWyM/A?= =?windows-1251?B?y9zN29UgzdPGxA==?= Date: Wed, 13 Mar 2013 15:32:04 -0700 X-ASG-Orig-Subj: =?windows-1251?B?zc7CzsUgwiDP0MDCzsLOzCDMxdXAzcjHzMUg?= =?windows-1251?B?x8DK08/OyiDSzsLA0M7CIMgg09HL08MgxMvf?= =?windows-1251?B?IMPO0dPEwNDR0sLFzc3b1SDIIMzTzcjWyM/A?= =?windows-1251?B?y9zN29UgzdPGxA==?= MIME-Version: 1.0 Content-Type: multipart/alternative; boundary="----=_NextPart_000_1DDF_01CE1FFF.EA64D000" X-Priority: 3 X-MSMail-Priority: Normal X-Mailer: Microsoft Windows Live Mail 16.4.3505.912 X-MimeOLE: Produced By Microsoft MimeOLE V16.4.3505.912 X-Greylist: Sender succeeded SMTP AUTH authentication, not delayed by milter-greylist-3.0 (ru-tek.ru [91.218.228.25]); Thu, 14 Mar 2013 02:32:04 +0400 (MSK) X-Barracuda-Connect: ru-tek.ru[91.218.228.25] X-Barracuda-Start-Time: 1363213929 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Barracuda-BRTS-Status: 1 X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_TG035a, HTML_MESSAGE X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125122 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 HTML_MESSAGE BODY: HTML included in message 0.00 BSF_SC0_TG035a Message contains invalid style definition This is a multi-part message in MIME format. ------=_NextPart_000_1DDF_01CE1FFF.EA64D000 Content-Type: text/plain; charset="windows-1251" Content-Transfer-Encoding: quoted-printable ol.0=F7-02.o=F7.20l3 =E3., =D1=C0=CD=CA=D2-=CF=C5=D2=C5=D0=C1=D3=D0=C3 =C3=CE=D1=D3=C4=C0=D0=D1=D2=C2=C5=CD=CD=DB=C9 =C8 =CC=D3=CD=C8=D6=C8=CF=C0= =CB=DC=CD=DB=C9 =C7=C0=CA=C0=C7 - =D0=C5=D4=CE=D0=CC=C8=D0=CE=C2=C0=CD=C8= =C5 =D1=C8=D1=D2=C5=CC=DB.=20 =CD=CE=C2=CE=C5 =C2 =CF=D0=C0=C2=CE=C2=CE=CC =CC=C5=D5=C0=CD=C8=C7=CC=C5= =C7=C0=CA=D3=CF=CE=CA =D2=CE=C2=C0=D0=CE=C2 =C8 =D3=D1=CB=D3=C3 =C4=CB=DF= =C3=CE=D1=D3=C4=C0=D0=D1=D2=C2=C5=CD=CD=DB=D5 =C8 =CC=D3=CD=C8=D6=C8=CF=C0= =CB=DC=CD=DB=D5 =CD=D3=C6=C4.=20 =DD=CB=C5=CA=D2=D0=CE=CD=CD=DB=C5 =D2=CE=D0=C3=C8 (=E0=F3=EA=F6=E8=EE=ED= ). =D2=C5=CC=DB =CC=C5=D0=CE=CF=D0=C8=DF=D2=C8=DF: 1. =C7=E0=EA=EE=ED =D0=D4 94-=D4=C7 =AB=CE =F0=E0=E7=EC=E5=F9=E5=ED=E8=E8= =E7=E0=EA=E0=E7=EE=E2 =ED=E0 =EF=EE=F1=F2=E0=E2=EA=E8 =F2=EE=E2=E0=F0=EE= =E2, =E2=FB=EF=EE=EB=ED=E5=ED=E8=E5 =F0=E0=E1=EE=F2. 2. =CD=EE=E2=E0=FF =F0=E5=E4=E0=EA=F6=E8=FF =E7=E0=EA=EE=ED=E0 =B9 2l8-=D4= =C7 (=E2=F1=F2=F3=EF=E8=E2=F8=E0=FF =E2 =F1=E8=EB=F3 =F1 ol.l0.07). =20 3. =CF=EE=F0=FF=E4=EE=EA =F0=E0=E7=EC=E5=F9=E5=ED=E8=FF =E3=EE=F1=F3=E4=E0= =F0=F1=F2=E2=E5=ED=ED=EE=E3=EE =E8 =EC=F3=ED=E8=F6=E8=EF=E0=EB=FC=ED=EE=E3= =EE =E7=E0=EA=E0=E7=E0. =20 4. =CE=F1=EE=E1=E5=ED=ED=EE=F1=F2=E8 =EF=F0=EE=E2=E5=E4=E5=ED=E8=FF =E0=F3= =EA=F6=E8=EE=ED=EE=E2, =F2=E8=EF=E8=F7=ED=FB=E5 =EE=F8=E8=E1=EA=E8 =EF=F0= =E8 =EF=F0=EE=E2=E5=E4=E5=ED=E8=E8 =E0=F3=EA=F6=E8=EE=ED=EE=E2.=20 5. =C7=E0=EF=F0=EE=F1=FB =EA=EE=F2=E8=F0=EE=E2=EE=EA. =CD=EE=E2=FB=E5 =E0= =F1=EF=E5=EA=F2=FB =EE=F0=E3=E0=ED=E8=E7=E0=F6=E8=E8 =E8 =EF=F0=EE=E2=E5= =E4=E5=ED=E8=FF.=20 6. =D0=E0=E7=EC=E5=F9=E5=ED=E8=E5 =E3=EE=F1=F3=E4=E0=F0=F1=F2=E2=E5=ED=ED= =FB=F5 =E8 =EC=F3=ED=E8=F6=E8=EF=E0=EB=FC=ED=FB=F5 =E7=E0=EA=E0=E7=EE=E2 = =E1=E5=E7 =EF=F0=EE=E2=E5=E4=E5=ED=E8=FF =F2=EE=F0=E3=EE=E2.=20 7. =D0=E5=E5=F1=F2=F0=FB =EA=EE=ED=F2=F0=E0=EA=F2=EE=E2 =E8 =ED=E5=E4= =EE=E1=F0=EE=F1=EE=E2=E5=F1=F2=ED=FB=F5 =EF=EE=F1=F2=E0=E2=F9=E8=EA=EE=E2= .=20 8. =CA=EE=ED=F2=F0=EE=EB=FC =D4=C0=D1 =D0=D4 =E2 =EE=E1=EB=E0=F1=F2=E8 =E3= =EE=F1=F3=E4=E0=F0=F1=F2=E2=E5=ED=ED=EE=E3=EE =E8 =EC=F3=ED=E8=F6=E8=EF=E0= =EB=FC=ED=EE=E3=EE =E7=E0=EA=E0=E7=E0. 9. =C0=EA=F2=F3=E0=EB=FC=ED=FB=E5 =E2=EE=EF=F0=EE=F1=FB =E7=E0=EA=EB= =FE=F7=E5=ED=E8=FF =E3=EE=F1=F3=E4=E0=F0=F1=F2=E2=E5=ED=ED=FB=F5 =E8 =EC=F3= =ED=E8=F6=E8=EF=E0=EB=FC=ED=FB=F5 =EA=EE=ED=F2=F0=E0=EA=F2=EE=E2. =CC=ED=EE= =E3=EE=EB=E5=F2=ED=E8=E5, =EF=E5=F0=E5=F5=EE=E4=FF=F9=E8=E5 =EA=EE=ED=F2=F0= =E0=EA=F2=FB.=20 10. =C2=EE=EF=F0=EE=F1=FB =F4=EE=F0=EC=E8=F0=EE=E2=E0=ED=E8=FF =F6=E5=ED=FB= =EA=EE=ED=F2=F0=E0=EA=F2=E0, =EF=F0=E0=E2=E8=EB=FC=ED=EE=E3=EE =F4=EE=F0= =EC=E8=F0=EE=E2=E0=ED=E8=FF =F3=F1=EB=EE=E2=E8=E9 =F2=E5=F5=ED=E8=F7=E5=F1= =EA=EE=E3=EE =E7=E0=E4=E0=ED=E8=FF. 11. =CF=EE=F0=FF=E4=EE=EA =F1=EE=F1=F2=E0=E2=EB=E5=ED=E8=FF =E8 =F0=E0= =F1=F1=EC=EE=F2=F0=E5=ED=E8=FF =E6=E0=EB=EE=E1 =E8 =E8=F1=EA=EE=E2=FB=F5 = =F2=F0=E5=E1=EE=E2=E0=ED=E8=E9 =F3=F7=E0=F1=F2=ED=E8=EA=EE=E2 =F0=E0=E7=EC= =E5=F9=E5=ED=E8=FF =E7=E0=EA=E0=E7=EE=E2=20 12. =DD=EB=E5=EA=F2=F0=EE=ED=ED=FB=E9 =E0=F3=EA=F6=E8=EE=ED - =F7=F2=EE= =ED=F3=E6=ED=EE =E7=ED=E0=F2=FC =D3=F7=E0=F1=F2=ED=E8=EA=F3, =F7=F2=EE=E1= =FB =EF=F0=E8=ED=FF=F2=FC =F3=F7=E0=F1=F2=E8=E5 =E2 =FD=EB=E5=EA=F2=F0=EE= =ED=ED=EE=EC =E0=F3=EA=F6=E8=EE=ED=E5:=20 =F1=EE=EE=F2=E2=E5=F2=F1=F2=E2=F3=FE=F9=E5=E5 =EF=F0=EE=E3=F0=E0=EC=EC=ED= =EE=E5 =EE=E1=E5=F1=EF=E5=F7=E5=ED=E8=E5, =DD=D6=CF =E8 =EF=EE=F0=FF=E4=EE= =EA =E5=E5 =F0=E5=E3=E8=F1=F2=F0=E0=F6=E8=E8.=20 =AB=CE=F2=F0=E8=F6=E0=F2=E5=EB=FC=ED=FB=E9 =FD=EB=E5=EA=F2=F0=EE=ED=ED=FB= =E9 =E0=F3=EA=F6=E8=EE=ED=BB, =EF=F0=E0=E2=EE=E2=FB=E5 =EF=EE=F1=EB=E5=E4= =F1=F2=E2=E8=FF =E5=E3=EE =EF=F0=EE=E2=E5=E4=E5=ED=E8=FF.=20 =CA=E0=EA=E8=E5 =E4=EE=EA=F3=EC=E5=ED=F2=FB =ED=F3=E6=ED=EE =EF=F0=E5=E4=EE= =F1=F2=E0=E2=E8=F2=FC =E4=EB=FF =EF=F0=EE=F5=EE=E6=E4=E5=ED=E8=FF =E0=EA=EA= =F0=E5=E4=E8=F2=E0=F6=E8=E8 =ED=E0 =F2=EE=F0=E3=EE=E2=EE=E9 =EF=EB=EE=F9=E0= =E4=EA=E5?=20 =CE=E1=E5=F1=EF=E5=F7=E5=ED=E8=E5 =E7=E0=FF=E2=EE=EA =ED=E0 =F3=F7=E0=F1=F2= =E8=E5 =E2 =E0=F3=EA=F6=E8=EE=ED=E5 =E2 =FD=EB=E5=EA=F2=F0=EE=ED=ED=EE=E9= =F4=EE=F0=EC=E5: =EA=E0=EA =E8 =EA=EE=EC=F3 =EF=F0=E5=E4=EE=F1=F2=E0=E2=EB= =FF=E5=F2=F1=FF.=20 =D3=F1=EB=EE=E2=E8=FF =F3=E4=E5=F0=E6=E0=ED=E8=FF =EE=E1=E5=F1=EF=E5=F7=E5= =ED=E8=FF.=20 =CD=C0 =C2=D1=C5 =C8=CD=D2=C5=D0=C5=D1=D3=DE=D9=C8=C5 =C2=CE=CF=D0=CE=D1= =DB =C2=C0=CC =CE=D2=C2=C5=D2=C8=D2 =CD=C0=D8 =D1=C5=CA=D0=C5=D2=C0=D0=DC= : +7 - 8l2 - 98..6 ^ 9=F7 _ l l =20 ------=_NextPart_000_1DDF_01CE1FFF.EA64D000 Content-Type: text/html; charset="windows-1251" Content-Transfer-Encoding: quoted-printable
 ol.0=F7-02.o=F7.20l3=20 =E3., =D1=C0=CD=CA=D2-=CF=C5=D2=C5=D0=C1=D3=D0=C3
 
 =C3=CE=D1=D3=C4=C0=D0=D1=D2=C2=C5=CD=CD=DB=C9 =C8= =CC=D3=CD=C8=D6=C8=CF=C0=CB=DC=CD=DB=C9 =C7=C0=CA=C0=C7 - =D0=C5=D4=CE=D0= =CC=C8=D0=CE=C2=C0=CD=C8=C5=20 =D1=C8=D1=D2=C5=CC=DB.
 =CD=CE=C2=CE=C5 =C2 =CF=D0=C0=C2=CE=C2=CE= =CC =CC=C5=D5=C0=CD=C8=C7=CC=C5 =C7=C0=CA=D3=CF=CE=CA =D2=CE=C2=C0=D0=CE=C2= =C8 =D3=D1=CB=D3=C3 =C4=CB=DF=20 =C3=CE=D1=D3=C4=C0=D0=D1=D2=C2=C5=CD=CD=DB=D5 =C8 =CC=D3=CD=C8=D6=C8=CF=C0= =CB=DC=CD=DB=D5 =CD=D3=C6=C4.
 =DD=CB=C5=CA=D2=D0=CE=CD=CD=DB=C5= =D2=CE=D0=C3=C8=20 (=E0=F3=EA=F6=E8=EE=ED).
 
=D2=C5=CC=DB =CC=C5=D0=CE=CF=D0=C8=DF=D2=C8=DF:
1.&n= bsp;=C7=E0=EA=EE=ED =D0=D4 94-=D4=C7 =AB=CE=20 =F0=E0=E7=EC=E5=F9=E5=ED=E8=E8 =E7=E0=EA=E0=E7=EE=E2 =ED=E0 =EF=EE=F1=F2=E0= =E2=EA=E8 =F2=EE=E2=E0=F0=EE=E2, =E2=FB=EF=EE=EB=ED=E5=ED=E8=E5 =F0=E0=E1= =EE=F2.
2. =CD=EE=E2=E0=FF=20 =F0=E5=E4=E0=EA=F6=E8=FF =E7=E0=EA=EE=ED=E0  =B9 2l8-=D4=C7 (=E2=F1=F2= =F3=EF=E8=E2=F8=E0=FF =E2 =F1=E8=EB=F3 =F1=20 ol.l0.07). =20
3. =CF=EE=F0=FF=E4=EE=EA =F0=E0=E7=EC=E5=F9=E5=ED=E8=FF =E3=EE=F1= =F3=E4=E0=F0=F1=F2=E2=E5=ED=ED=EE=E3=EE =E8 =EC=F3=ED=E8=F6=E8=EF=E0=EB=FC= =ED=EE=E3=EE =E7=E0=EA=E0=E7=E0. =20
4. =CE=F1=EE=E1=E5=ED=ED=EE=F1=F2=E8 =EF=F0=EE=E2=E5=E4=E5=ED=E8= =FF =E0=F3=EA=F6=E8=EE=ED=EE=E2, =F2=E8=EF=E8=F7=ED=FB=E5 =EE=F8=E8=E1=EA= =E8 =EF=F0=E8 =EF=F0=EE=E2=E5=E4=E5=ED=E8=E8=20 =E0=F3=EA=F6=E8=EE=ED=EE=E2.
5. =C7=E0=EF=F0=EE=F1=FB =EA=EE=F2=E8= =F0=EE=E2=EE=EA. =CD=EE=E2=FB=E5 =E0=F1=EF=E5=EA=F2=FB  =EE=F0=E3=E0= =ED=E8=E7=E0=F6=E8=E8 =E8=20 =EF=F0=EE=E2=E5=E4=E5=ED=E8=FF.
6. =D0=E0=E7=EC=E5=F9=E5=ED=E8=E5= =E3=EE=F1=F3=E4=E0=F0=F1=F2=E2=E5=ED=ED=FB=F5 =E8 =EC=F3=ED=E8=F6=E8=EF=E0= =EB=FC=ED=FB=F5 =E7=E0=EA=E0=E7=EE=E2 =E1=E5=E7=20 =EF=F0=EE=E2=E5=E4=E5=ED=E8=FF =F2=EE=F0=E3=EE=E2.
7.  &nbs= p;   =D0=E5=E5=F1=F2=F0=FB =EA=EE=ED=F2=F0=E0=EA=F2=EE=E2 =E8=20 =ED=E5=E4=EE=E1=F0=EE=F1=EE=E2=E5=F1=F2=ED=FB=F5 =EF=EE=F1=F2=E0=E2=F9=E8= =EA=EE=E2.
8. =CA=EE=ED=F2=F0=EE=EB=FC =D4=C0=D1 =D0=D4 =E2 =EE=E1= =EB=E0=F1=F2=E8=20 =E3=EE=F1=F3=E4=E0=F0=F1=F2=E2=E5=ED=ED=EE=E3=EE =E8 =EC=F3=ED=E8=F6=E8=EF= =E0=EB=FC=ED=EE=E3=EE =E7=E0=EA=E0=E7=E0.
9.    &n= bsp;=20 =C0=EA=F2=F3=E0=EB=FC=ED=FB=E5 =E2=EE=EF=F0=EE=F1=FB =E7=E0=EA=EB=FE=F7=E5= =ED=E8=FF =E3=EE=F1=F3=E4=E0=F0=F1=F2=E2=E5=ED=ED=FB=F5 =E8 =EC=F3=ED=E8=F6= =E8=EF=E0=EB=FC=ED=FB=F5 =EA=EE=ED=F2=F0=E0=EA=F2=EE=E2.=20 =CC=ED=EE=E3=EE=EB=E5=F2=ED=E8=E5, =EF=E5=F0=E5=F5=EE=E4=FF=F9=E8=E5 =EA=EE= =ED=F2=F0=E0=EA=F2=FB.
10. =C2=EE=EF=F0=EE=F1=FB =F4=EE=F0=EC=E8= =F0=EE=E2=E0=ED=E8=FF =F6=E5=ED=FB=20 =EA=EE=ED=F2=F0=E0=EA=F2=E0, =EF=F0=E0=E2=E8=EB=FC=ED=EE=E3=EE =F4=EE=F0=EC= =E8=F0=EE=E2=E0=ED=E8=FF =F3=F1=EB=EE=E2=E8=E9 =F2=E5=F5=ED=E8=F7=E5=F1=EA= =EE=E3=EE=20 =E7=E0=E4=E0=ED=E8=FF.
11.     =CF=EE=F0=FF=E4=EE=EA= =F1=EE=F1=F2=E0=E2=EB=E5=ED=E8=FF =E8 =F0=E0=F1=F1=EC=EE=F2=F0=E5=ED=E8=FF= =E6=E0=EB=EE=E1=20 =E8 =E8=F1=EA=EE=E2=FB=F5 =F2=F0=E5=E1=EE=E2=E0=ED=E8=E9 =F3=F7=E0=F1=F2=ED= =E8=EA=EE=E2 =F0=E0=E7=EC=E5=F9=E5=ED=E8=FF =E7=E0=EA=E0=E7=EE=E2=20
12.     =DD=EB=E5=EA=F2=F0=EE=ED=ED=FB=E9 =E0=F3=EA= =F6=E8=EE=ED - =F7=F2=EE =ED=F3=E6=ED=EE =E7=ED=E0=F2=FC =D3=F7=E0=F1=F2=ED= =E8=EA=F3,=20 =F7=F2=EE=E1=FB =EF=F0=E8=ED=FF=F2=FC =F3=F7=E0=F1=F2=E8=E5 =E2 =FD=EB=E5= =EA=F2=F0=EE=ED=ED=EE=EC =E0=F3=EA=F6=E8=EE=ED=E5:
=F1=EE=EE=F2=E2=E5= =F2=F1=F2=E2=F3=FE=F9=E5=E5 =EF=F0=EE=E3=F0=E0=EC=EC=ED=EE=E5=20 =EE=E1=E5=F1=EF=E5=F7=E5=ED=E8=E5, =DD=D6=CF =E8 =EF=EE=F0=FF=E4=EE=EA =E5= =E5 =F0=E5=E3=E8=F1=F2=F0=E0=F6=E8=E8.
=AB=CE=F2=F0=E8=F6=E0=F2=E5=EB= =FC=ED=FB=E9 =FD=EB=E5=EA=F2=F0=EE=ED=ED=FB=E9=20 =E0=F3=EA=F6=E8=EE=ED=BB, =EF=F0=E0=E2=EE=E2=FB=E5 =EF=EE=F1=EB=E5=E4=F1=F2= =E2=E8=FF =E5=E3=EE =EF=F0=EE=E2=E5=E4=E5=ED=E8=FF.
=CA=E0=EA=E8=E5 =E4= =EE=EA=F3=EC=E5=ED=F2=FB =ED=F3=E6=ED=EE=20 =EF=F0=E5=E4=EE=F1=F2=E0=E2=E8=F2=FC =E4=EB=FF =EF=F0=EE=F5=EE=E6=E4=E5=ED= =E8=FF =E0=EA=EA=F0=E5=E4=E8=F2=E0=F6=E8=E8 =ED=E0 =F2=EE=F0=E3=EE=E2=EE=E9= =EF=EB=EE=F9=E0=E4=EA=E5?
=CE=E1=E5=F1=EF=E5=F7=E5=ED=E8=E5=20 =E7=E0=FF=E2=EE=EA =ED=E0 =F3=F7=E0=F1=F2=E8=E5 =E2 =E0=F3=EA=F6=E8=EE=ED= =E5 =E2 =FD=EB=E5=EA=F2=F0=EE=ED=ED=EE=E9 =F4=EE=F0=EC=E5: =EA=E0=EA =E8 = =EA=EE=EC=F3 =EF=F0=E5=E4=EE=F1=F2=E0=E2=EB=FF=E5=F2=F1=FF.=20
=D3=F1=EB=EE=E2=E8=FF =F3=E4=E5=F0=E6=E0=ED=E8=FF =EE=E1=E5=F1=EF=E5=F7= =E5=ED=E8=FF.
 
 =CD=C0 =C2=D1=C5 =C8=CD=D2=C5=D0=C5=D1=D3=DE=D9=C8= =C5 =C2=CE=CF=D0=CE=D1=DB =C2=C0=CC =CE=D2=C2=C5=D2=C8=D2 =CD=C0=D8=20 =D1=C5=CA=D0=C5=D2=C0=D0=DC:
 
+7 - 8l2 - 98..6 ^ 9=F7 _ l l =
------=_NextPart_000_1DDF_01CE1FFF.EA64D000-- From david@fromorbit.com Wed Mar 13 18:42:18 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 9B83B7F37 for ; Wed, 13 Mar 2013 18:42:18 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id 6D62C30405F for ; Wed, 13 Mar 2013 16:42:18 -0700 (PDT) X-ASG-Debug-ID: 1363218136-04cbb04b8584450001-NocioJ Received: from ipmail04.adl6.internode.on.net (ipmail04.adl6.internode.on.net [150.101.137.141]) by cuda.sgi.com with ESMTP id JugUWjIxjEL0J3GZ for ; Wed, 13 Mar 2013 16:42:16 -0700 (PDT) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.141 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AjweANUNQVF5LMKP/2dsb2JhbABDhzu4DoUSAQIBgVkXdIIqAQEFOhwjEAgDGAklDwUlAyETiBPCOxWNehgfSgeDQAOWV5EDgS+Bbyg Received: from ppp121-44-194-143.lns20.syd7.internode.on.net (HELO dastard) ([121.44.194.143]) by ipmail04.adl6.internode.on.net with ESMTP; 14 Mar 2013 10:12:14 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UFvJF-0005ka-Lf; Thu, 14 Mar 2013 10:42:13 +1100 Date: Thu, 14 Mar 2013 10:42:13 +1100 From: Dave Chinner To: Eric Sandeen Cc: Shrinath M , Sabyasachi Ruj , Vivek Goel , Supratik Goswami , Ric Wheeler , xfs@oss.sgi.com Subject: Re: XFS filesystem on EC2 instance corrupts and shuts down Message-ID: <20130313234213.GW21651@dastard> X-ASG-Orig-Subj: Re: XFS filesystem on EC2 instance corrupts and shuts down References: <51373DB8.2020707@redhat.com> <51373FC1.6010101@redhat.com> <513751F2.2060109@redhat.com> <5140CBE3.80705@sandeen.net> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <5140CBE3.80705@sandeen.net> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail04.adl6.internode.on.net[150.101.137.141] X-Barracuda-Start-Time: 1363218136 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125125 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Wed, Mar 13, 2013 at 01:56:35PM -0500, Eric Sandeen wrote: > XFS (md0): xfs_iunlink_remove: xfs_itobp() returned error 117. Corrupted unlinked inode list. You need to run xfs_repair to fix this. Chers, Dave. -- Dave Chinner david@fromorbit.com From david@fromorbit.com Wed Mar 13 18:57:10 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay1.corp.sgi.com [137.38.102.111]) by oss.sgi.com (Postfix) with ESMTP id 7F3277F37 for ; Wed, 13 Mar 2013 18:57:10 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay1.corp.sgi.com (Postfix) with ESMTP id 44B238F8059 for ; Wed, 13 Mar 2013 16:57:07 -0700 (PDT) X-ASG-Debug-ID: 1363219025-04bdf00a0b942b0001-NocioJ Received: from ipmail04.adl6.internode.on.net (ipmail04.adl6.internode.on.net [150.101.137.141]) by cuda.sgi.com with ESMTP id 18XQfuuGCEp0oNm7 for ; Wed, 13 Mar 2013 16:57:05 -0700 (PDT) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.141 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: Aj4eAAwRQVF5LMKP/2dsb2JhbABDDoctuA6FEgECAYFZF3SCKgEBBAE6HCMFCwgDDgoJJQ8FJQMhE4gOBcI4FY1ENhgfSgeDQAOWV4lthxaBL4EcUyiBLg Received: from ppp121-44-194-143.lns20.syd7.internode.on.net (HELO dastard) ([121.44.194.143]) by ipmail04.adl6.internode.on.net with ESMTP; 14 Mar 2013 10:27:04 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UFvXb-0005mH-T7; Thu, 14 Mar 2013 10:57:03 +1100 Date: Thu, 14 Mar 2013 10:57:03 +1100 From: Dave Chinner To: Dave Hall Cc: xfs@oss.sgi.com Subject: Re: xfs_fsr, sunit, and swidth Message-ID: <20130313235703.GX21651@dastard> X-ASG-Orig-Subj: Re: xfs_fsr, sunit, and swidth References: <5140C147.7070205@binghamton.edu> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <5140C147.7070205@binghamton.edu> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail04.adl6.internode.on.net[150.101.137.141] X-Barracuda-Start-Time: 1363219025 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125127 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- On Wed, Mar 13, 2013 at 02:11:19PM -0400, Dave Hall wrote: > Does xfs_fsr react in any way to the sunit and swidth attributes of > the file system? Not directly. > In other words, with an XFS filesytem set up > directly on a hardware RAID, it is recommended that the mount > command be changed to specify sunit and swidth values that reflect > the new geometry of the RAID. The mount option does nothing if sunit/swidth weren't specified at mkfs time. sunit/swidth affect the initial layout of the filesystem, and that cannot be altered after the fact. Hence you can't arbitrarily change sunit/swidth after mkfs - you are limited to changes that are compatible with the existing alignment. If you have no alignment specified, then there isn't a new alignment that can be verified as compatible with the existing layout..... > In my case, these values were not > specified on the mkfs.xfs of a rather large file system running on a > RAID 6 array. Which means the mount option won't work. > I am wondering adding sunit and swidth parameters to > the fstab will cause xfs_fsr to do anything different than it is > already doing. Most importantly, will it improve performace in any > way? It will make no difference at all. A more important question: why do you even need to run xfs_fsr? Cheers, Dave. -- Dave Chinner david@fromorbit.com From stan@hardwarefreak.com Wed Mar 13 19:03:19 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id A70387F4C for ; Wed, 13 Mar 2013 19:03:19 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id 7CD07304075 for ; Wed, 13 Mar 2013 17:03:16 -0700 (PDT) X-ASG-Debug-ID: 1363219395-04cbb04b84860e0001-NocioJ Received: from greer.hardwarefreak.com (mo-65-41-216-221.sta.embarqhsd.net [65.41.216.221]) by cuda.sgi.com with ESMTP id zGxxicMIEMWI8K7b for ; Wed, 13 Mar 2013 17:03:15 -0700 (PDT) X-Barracuda-Envelope-From: stan@hardwarefreak.com X-Barracuda-Apparent-Source-IP: 65.41.216.221 X-Barracuda-User-Whitelist: xfs@oss.sgi.com Received: from [192.168.100.53] (gffx.hardwarefreak.com [192.168.100.53]) by greer.hardwarefreak.com (Postfix) with ESMTP id 444F26C0C8; Wed, 13 Mar 2013 19:03:15 -0500 (CDT) Message-ID: <514113C6.9090602@hardwarefreak.com> Date: Wed, 13 Mar 2013 19:03:18 -0500 From: Stan Hoeppner Reply-To: stan@hardwarefreak.com User-Agent: Mozilla/5.0 (Windows NT 5.1; rv:17.0) Gecko/20130307 Thunderbird/17.0.4 MIME-Version: 1.0 To: Dave Hall CC: xfs@oss.sgi.com Subject: Re: xfs_fsr, sunit, and swidth References: <5140C147.7070205@binghamton.edu> X-ASG-Orig-Subj: Re: xfs_fsr, sunit, and swidth In-Reply-To: <5140C147.7070205@binghamton.edu> Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: mo-65-41-216-221.sta.embarqhsd.net[65.41.216.221] X-Barracuda-Start-Time: 1363219395 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 On 3/13/2013 1:11 PM, Dave Hall wrote: > Does xfs_fsr react in any way to the sunit and swidth attributes of the > file system? No, manually remounting with new stripe alignment and then running xfs_fsr is not going to magically reorganize your filesystem. > In other words, with an XFS filesytem set up directly on a > hardware RAID, it is recommended that the mount command be changed to > specify sunit and swidth values that reflect the new geometry of the > RAID. This recommendation (as well as most things storage related) is workload dependent. A common misconception many people have is that XFS simply needs to be aligned to the RAID stripe. In reality, it's more critical that XFS write out be aligned to the application's write pattern, and thus, the hardware RAID stripe needs to be as well. Another common misconception is that simply aligning XFS to the RAID stripe will automagically yield fully filled hardware stripes. This is entirely dependent on matching the hardware RAID stripe to the applications write pattern. > In my case, these values were not specified on the mkfs.xfs of a > rather large file system running on a RAID 6 array. I am wondering > adding sunit and swidth parameters to the fstab will cause xfs_fsr to do > anything different than it is already doing. No, see above. And read this carefully: Aligning XFS affects write out only during allocation. It does not affect xfs_fsr. Nor does it affect non allocation workloads, i.e. database inserts, writing new mail to mbox files, etc. > Most importantly, will it > improve performace in any way? You provided insufficient information for us to help you optimize performance. For us to even take a stab at answering this we need to know at least: 1. application/workload write pattern(s) Is it allocation heavy? a. small random IO b. large streaming c. If mixed, what is the ratio 2. current hardware RAID parameters a. strip/chunk size b. # of effective spindles (RAID6 minus 2) 3. Current percentage of filesystem bytes and inodes used a. ~$ df /dev/[mount_point] b. ~$ df -i /dev/[mount_point] FWIW, parity RAID is abysmal with random writes, and especially so if the hardware stripe width is larger than the workload's write IOs. Thus, optimizing performance with hardware RAID and filesystems must be done during the design phase of the storage. For instance if you have a RAID6 chunk/strip size of 512K and 8 spindles that's a 4MB stripe width. If your application is doing random allocation write out in 256K chunks, you simply can't optimize performance without blowing away the array and recreating. For this example you'd need a chunk/strip of 32K with 8 effective spindles which equals 256K. Now, there is a possible silver lining here. If your workload is doing mostly large streaming writes, allocation or not, that are many multiples of your current hardware RAID stripe, it doesn't matter if your XFS is doing default 4K writes or if it has been aligned to the RAID stripe. In this case the controller's BBWC is typically going to take the successive XFS 4K IOs and fill hardware stripes automatically. So again, as always, the answer depends on your workload. -- Stan From shrinath.m@webyog.com Wed Mar 13 20:28:45 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=HTML_FONT_FACE_BAD, HTML_MESSAGE,T_DKIM_INVALID autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id C41B17F37 for ; Wed, 13 Mar 2013 20:28:44 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay3.corp.sgi.com (Postfix) with ESMTP id 39273AC002 for ; Wed, 13 Mar 2013 18:28:41 -0700 (PDT) X-ASG-Debug-ID: 1363224519-04cbb04b868b800001-NocioJ Received: from mail-ia0-f171.google.com (mail-ia0-f171.google.com [209.85.210.171]) by cuda.sgi.com with ESMTP id 27atkVZ26tW6p2yn (version=TLSv1 cipher=RC4-SHA bits=128 verify=NO) for ; Wed, 13 Mar 2013 18:28:39 -0700 (PDT) X-Barracuda-Envelope-From: shrinath.m@webyog.com X-Barracuda-Apparent-Source-IP: 209.85.210.171 Received: by mail-ia0-f171.google.com with SMTP id z13so1582033iaz.2 for ; Wed, 13 Mar 2013 18:28:39 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=webyog.com; s=google; h=x-received:mime-version:in-reply-to:references:from:date:message-id :subject:to:cc:content-type; bh=l/W9A/oJBxeiAOJtK0UgK0Yg34xWopaRiA0YqSy5zQA=; b=MQ2ObfC+L9Bpau/NYcJWkSHoQ06LMxNXrgh2GszSBa1yZZYt0TMrchr//vyxG41/18 Yp+ZSpOSyN5PcwLezCfzkIeuWhjHD3n10z0um2/qbqv1fLujECGJ/mD2wBaA+BiEoQ1O h2Ru/E6xyi1AOKj2esi+LVjbkdsHzqhKVN6u8= X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=20120113; h=x-received:mime-version:in-reply-to:references:from:date:message-id :subject:to:cc:content-type:x-gm-message-state; bh=l/W9A/oJBxeiAOJtK0UgK0Yg34xWopaRiA0YqSy5zQA=; b=SPgQljFJJr/nStvdKfquz4aB3gDr39LEBMhKAeHR1AP0cDYMpGpSep1sunl5lCsYU1 7womqbPk5UO2DLWVRYFUCJ6S1LnJvoMWGZE3ESAcJbKa0CgfiIhG6RzaCnEIJ88FMNYO gFuK4KzqUlM/dqSNoXblP7cfX+kjIYlK9ChMlv+CCt7thnHjjnPXifTSsm1/HDXTwglv tIHLk/X6pBn40TCK5ZEHJs8KB1OGqlWRsyKX2DJ4i62vLmTfqogFJwnl/J7pfBb8Wzq8 V9jz72AKryBRfp5C85vBjPc8CveE6LaAQTyprsbRFP3rCcV3nFGqu4bj5KMBBNWUlJAd phXw== X-Received: by 10.50.208.68 with SMTP id mc4mr575831igc.35.1363224519199; Wed, 13 Mar 2013 18:28:39 -0700 (PDT) MIME-Version: 1.0 Received: by 10.43.1.132 with HTTP; Wed, 13 Mar 2013 18:28:19 -0700 (PDT) In-Reply-To: <20130313234213.GW21651@dastard> References: <51373DB8.2020707@redhat.com> <51373FC1.6010101@redhat.com> <513751F2.2060109@redhat.com> <5140CBE3.80705@sandeen.net> <20130313234213.GW21651@dastard> From: Shrinath M Date: Thu, 14 Mar 2013 06:58:19 +0530 Message-ID: Subject: Re: XFS filesystem on EC2 instance corrupts and shuts down To: Dave Chinner X-ASG-Orig-Subj: Re: XFS filesystem on EC2 instance corrupts and shuts down Cc: Eric Sandeen , Sabyasachi Ruj , Vivek Goel , Supratik Goswami , Ric Wheeler , xfs@oss.sgi.com Content-Type: multipart/alternative; boundary=14dae93408e7376fd604d7d871a7 X-Gm-Message-State: ALoCoQkCm8vxu2Y+/6xluU1s6G/2hTVO5QGHsQlFXe9VY0N/Bu7/CEFw1IWfWcMu27EH7AIRzilK X-Barracuda-Connect: mail-ia0-f171.google.com[209.85.210.171] X-Barracuda-Start-Time: 1363224519 X-Barracuda-Encrypted: RC4-SHA X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.61 X-Barracuda-Spam-Status: No, SCORE=0.61 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=DKIM_SIGNED, DKIM_VERIFIED, HTML_FONT_FACE_BAD, HTML_MESSAGE X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125133 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- -0.00 DKIM_VERIFIED Domain Keys Identified Mail: signature passes verification 0.00 DKIM_SIGNED Domain Keys Identified Mail: message has a signature 0.00 HTML_MESSAGE BODY: HTML included in message 0.61 HTML_FONT_FACE_BAD BODY: HTML font face is not a word --14dae93408e7376fd604d7d871a7 Content-Type: text/plain; charset=UTF-8 Thanks Ben, Dave and Eric. Eric, >>but I am wondering if there might be more information before this which is not in your trimmed logs. No, this was the first entry every time we have it in /var/log/messages. dmesg also holds the same. After reboot, it simply fixes without anyone doing anything. The Linux we are running is definitely amazon baked one, looks like this - $~: uname -a Linux ip-100-0-100-1 3.2.34-55.46.amzn1.x86_64 #1 SMP Tue Nov 20 10:06:15 UTC 2012 x86_64 x86_64 x86_64 GNU/Linux - dmesg shows something like this after repairing/rebooting - [ 8.414176] SGI XFS with ACLs, security attributes, realtime, large block/inode numbers, no debug enabled [ 8.415342] SGI XFS Quota Management subsystem [ 8.417664] XFS (md0): Mounting Filesystem [ 8.771553] XFS (md0): Starting recovery (logdev: internal) [ 9.977325] XFS (md0): Ending recovery (logdev: internal) Check the first line there, it says no debug enabled. How good/bad is this debug mode in production environments? We are not getting any corruption in our local/test environments, in production, we are getting it once on every third day. Dave, You say unlinked inode list, but if that, it should have an entry in /var/log/messages, right? Anyway, how can we create this situation? By forcing multiple processes to write/delete files from small disk? Since we are still unaware of what is causing this issue, reproducing it in local/production environment is just shooting in dark... :( Does turning up the error level affect the data in any way? Or is it *just* detailed good logging while being sensitive to all small errors? Really appreciate the support that you devs are giving which really is the job of AWS support... I so wish they had some helpful and knowledgeable people in support. On Thu, Mar 14, 2013 at 5:12 AM, Dave Chinner wrote: > On Wed, Mar 13, 2013 at 01:56:35PM -0500, Eric Sandeen wrote: > > XFS (md0): xfs_iunlink_remove: xfs_itobp() returned error 117. > > Corrupted unlinked inode list. You need to run xfs_repair to fix > this. > > Chers, > > Dave. > -- > Dave Chinner > david@fromorbit.com > -- Regards *Shrinath.M* --14dae93408e7376fd604d7d871a7 Content-Type: text/html; charset=UTF-8 Content-Transfer-Encoding: quoted-printable
Thanks Ben, Dave and Eric.=C2=A0

= Eric,=C2=A0
>>but I am wondering if there might be more information = before this which is not in your trimmed logs.
No, this was the first entry every time we have it in /var/log/messages. dm= esg also holds the same. After reboot, it simply fixes without anyone doing= anything.

The Linux we are running is definitely = amazon baked one, looks like this -=C2=A0
$~: uname -a Linux ip-100-0-100-1 3.2.34-55.46.amzn1.x86_64 #1 SMP Tue Nov 20 10:06:15 U= TC 2012 x86_64 x86_64 x86_64 GNU/Linux
=C2=A0- dmesg = shows something like this after repairing/rebooting -=C2=A0

[ =C2=A0 =C2=A08.414176] SGI XFS with ACLs, security attributes, realtime= , large block/inode numbers, no debug enabled
[ =C2=A0 =C2=A08.41= 5342] SGI XFS Quota Management subsystem
[ =C2=A0 =C2=A08.417664] XFS (md0): Mounting Filesystem
[ = =C2=A0 =C2=A08.771553] XFS (md0): Starting recovery (logdev: internal)
[ =C2=A0 =C2=A09.977325] XFS (md0): Ending recovery (logdev: internal= )

= Check the first line ther= e, it says no debug enabled. How good/bad is this debug mode in production = environments? We are not getting any corruption in our local/test environme= nts, in production, we are getting it once on every third day.

Dave,=C2=A0
You say unlinked inode list, but if that,= it should have an entry in /var/log/messages, right?
Anyway, how can we create= this situation? By forcing multiple processes to write/delete files from s= mall disk? Since we are still unaware of what is causing this issue, reprod= ucing it in local/production environment is just shooting in dark... :(

Does tu= rning up the error level affect the data in any way? Or is it *just* detail= ed good logging while being sensitive to all small errors?


Really appreciate the = support that you devs are giving which really is the job of AWS support... = I so wish they had some helpful and knowledgeable people in support.


=
On Thu, Mar 14, 2013 at 5:12 AM, Dave Chinne= r <david@fromorbit.com> wrote:
On Wed, Mar 13, 2013 at 01= :56:35PM -0500, Eric Sandeen wrote:
> XFS (md0): xfs_iunlink_remove: xfs_itobp() returned error 117.

Corrupted unlinked inode list. You need to run xfs_repair to fix
this.

Chers,

Dave.
--
Dave Chinner
david@fromorbit.com



-- Regards=
Shrinath.M

--14dae93408e7376fd604d7d871a7-- From dvkh@apecs.vn Wed Mar 13 23:47:49 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: *** X-Spam-Status: No, score=3.4 required=5.0 tests=DATE_IN_FUTURE_03_06, HTML_MESSAGE,LOTS_OF_MONEY,T_REMOTE_IMAGE autolearn=no version=3.3.1 X-Original-To: linux-xfs@oss.sgi.com Delivered-To: linux-xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 962F97F37 for ; Wed, 13 Mar 2013 23:47:49 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay2.corp.sgi.com (Postfix) with ESMTP id 4E4CD304059 for ; Wed, 13 Mar 2013 21:47:46 -0700 (PDT) X-ASG-Debug-ID: 1363236454-04bdf00a0da9400001-w1Z2WR Received: from apecs.vn ([202.124.204.11]) by cuda.sgi.com with ESMTP id W4ENwPMup2o0Uwrh for ; Wed, 13 Mar 2013 21:47:34 -0700 (PDT) X-Barracuda-Envelope-From: dvkh@apecs.vn X-Barracuda-Apparent-Source-IP: 202.124.204.11 Received: from SENDMAIL by apecs.vn (MDaemon PRO v10.0.0) with ESMTP id md50000862001.msg for ; Thu, 14 Mar 2013 11:48:14 +0700 X-Authenticated-Sender: dvkh@apecs.vn X-MDRemoteIP: 10.0.180.68 X-Return-Path: dvkh@apecs.vn X-Envelope-From: dvkh@apecs.vn X-MDaemon-Deliver-To: linux-xfs@oss.sgi.com Message-ID: <20130314.OYLJZPVMRYWNTWKJ@apecs.vn> From: "Dich Vu Khach Hang" To: Reply-To: "Dich Vu Khach Hang" Subject: Giao dich chung khoan khong gioi han chi mat 150.000 dong/thang Date: Thu, 14 Mar 2013 17:02:20 +0700 X-ASG-Orig-Subj: Giao dich chung khoan khong gioi han chi mat 150.000 dong/thang Importance: Normal MIME-Version: 1.0 Content-Type: multipart/alternative; boundary="----=_NextPart_783_4728_97266641.33425785" EM-Campaign: {199BB8A4-3AFF-4652-A3E1-39FDC2A9C6A4} EM-Task: 14 X-Barracuda-Connect: UNKNOWN[202.124.204.11] X-Barracuda-Start-Time: 1363236454 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 1.03 X-Barracuda-Spam-Status: No, SCORE=1.03 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC5_MJ1963, DATE_IN_FUTURE_03_06, DATE_IN_FUTURE_03_06_2, HTML_MESSAGE, RDNS_NONE X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125144 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.01 DATE_IN_FUTURE_03_06 Date: is 3 to 6 hours after Received: date 0.00 HTML_MESSAGE BODY: HTML included in message 0.10 RDNS_NONE Delivered to trusted network by a host with no rDNS 0.42 DATE_IN_FUTURE_03_06_2 DATE_IN_FUTURE_03_06_2 0.50 BSF_SC5_MJ1963 Custom Rule MJ1963 This message is in MIME format with multi-part. Since your mail reader does not understand this format, some or all of this message may not be legible. ------=_NextPart_783_4728_97266641.33425785 Content-Type: text/plain; charset=utf-8 Content-Transfer-Encoding: quoted-printable CH=C6=AF=C6=A0NG=20TR=C3=8CNH=20=C6=AFU=20=C4=90=C3=83I=20PH=C3=8D=20GIAO= =20D=E1=BB=8ACH=20CH=E1=BB=88=20TRONG=20N=C4=82M=202013 C=C3=B4ng=20ty=20ch=E1=BB=A9ng=20kho=C3=A1n=20APEC=20l=C3=A0=20m=E1=BB=99t= =20trong=20nh=E1=BB=AFng=20c=C3=B4ng=20ty=20ch=E1=BB=A9ng=20kho=C3=A1n=20h= =C3=A0ng=20=C4=91=E1=BA=A7u=20t=E1=BA=A1i=20Vi=E1=BB=87t=20Nam=20v=E1=BB=9B= i=20h=E1=BB=87=20th=E1=BB=91ng=20m=E1=BA=A1ng=20l=C6=B0=E1=BB=9Bi=20r=E1=BB= =99ng=20kh=E1=BA=AFp=20tr=C3=AAn=20c=E1=BA=A3=20n=C6=B0=E1=BB=9Bc.=20Ch=C3= =BAng=20t=C3=B4i=20lu=C3=B4n=20mong=20mu=E1=BB=91n=20=C4=91=C6=B0a=20t=E1= =BB=9Bi=20Qu=C3=BD=20kh=C3=A1ch=20h=C3=A0ng=20c=C3=A1c=20s=E1=BA=A3n=20ph= =E1=BA=A9m=20t=C3=A0i=20ch=C3=ADnh=20v=E1=BB=9Bi=20ch=E1=BA=A5t=20l=C6=B0= =E1=BB=A3ng=20t=E1=BB=91t=20nh=E1=BA=A5t.=20V=E1=BB=9Bi=20=C4=91=E1=BB=99i= =20ng=C5=A9=20c=C3=A1c=20chuy=C3=AAn=20gia=20t=C3=A0i=20ch=C3=ADnh=20gi=C3= =A0u=20kinh=20nghi=E1=BB=87m,=20c=C3=A1c=20m=C3=B4i=20gi=E1=BB=9Bi=20ch=E1= =BB=A9ng=20kho=C3=A1n=20v=E1=BB=9Bi=20th=C3=A1i=20=C4=91=E1=BB=99=20t=E1=BA= =ADn=20t=C3=A2m=20v=E1=BB=9Bi=20kh=C3=A1ch=20h=C3=A0ng,=20ch=C3=BAng=20t=C3= =B4i=20hi=20v=E1=BB=8Dng=20s=E1=BA=BD=20mang=20=C4=91=E1=BA=BFn=20cho=20Qu= =C3=BD=20kh=C3=A1ch=20nh=E1=BB=AFng=20gi=C3=A1=20tr=E1=BB=8B=20b=E1=BB=81n= =20v=E1=BB=AFng. Nh=C3=A2n=20d=E1=BB=8Bp=20C=C3=B4ng=20ty=20ch=E1=BB=A9ng=20kho=C3=A1n=20AP= EC=20tr=C3=B2n=205=20tu=E1=BB=95i,=20Ch=C3=BAng=20t=C3=B4i=20xin=20gi=E1=BB= =9Bi=20thi=E1=BB=87u=20t=E1=BB=9Bi=20Qu=C3=BD=20kh=C3=A1ch=20h=C3=A0ng=20m= =E1=BB=99t=20s=E1=BA=A3n=20ph=E1=BA=A9m=20t=C3=A0i=20ch=C3=ADnh=20m=E1=BB= =9Bi. PH=C3=8D=20GIAO=20D=E1=BB=8ACH=20PH=E1=BA=B2NG=20 =C4=90=E1=BB=91i=20t=C6=B0=E1=BB=A3ng=20=C4=91=C6=B0=E1=BB=A3c=20h=C6=B0= =E1=BB=9Fng:=20C=C3=A1c=20kh=C3=A1ch=20h=C3=A0ng=20m=E1=BB=9F=20t=C3=A0i=20= kho=E1=BA=A3n=20ch=E1=BB=A9ng=20kho=C3=A1n=20trong=20th=E1=BB=9Di=20gian=20= 2013=20v=C3=A0=20=C4=91=C4=83ng=20k=C3=BD=20tham=20gia=20g=C3=B3i=20s=E1=BA= =A3n=20ph=E1=BA=A9m=20=E2=80=9CPh=C3=AD=20giao=20d=E1=BB=8Bch=20ph=E1=BA=B3= ng=E2=80=9D L=E1=BB=A3i=20=C3=ADch=20c=E1=BB=A7a=20ch=C6=B0=C6=A1ng=20tr=C3=ACnh:=20B= =E1=BA=A1n=20kh=C3=B4ng=20ph=E1=BA=A3i=20lo=20v=E1=BB=81=20gi=C3=A1=20tr=E1= =BB=8B=20giao=20d=E1=BB=8Bch=20h=C3=A0ng=20th=C3=A1ng=20=C4=91=E1=BB=83=20t= =C3=ADnh=20tr=E1=BA=A3=20ph=C3=AD=20m=C3=A0=20b=E1=BA=A1n=20ch=E1=BB=89=20c= =E1=BA=A7n=20ph=E1=BA=A3i=20tr=E1=BA=A3=20150.000=20=C4=91=E1=BB=93ng/th=C3= =A1ng=20th=C3=B4ng=20qua=20g=C3=B3i=20s=E1=BA=A3n=20ph=E1=BA=A9m =E2=80=9CPh=C3=AD=20giao=20d=E1=BB=8Bch=20ph=E1=BA=B3ng=E2=80=9D. So=20s=C3=A1nh=20Ph=C3=AD=20giao=20d=E1=BB=8Bch=20ph=E1=BA=B3ng=20v=E1=BB= =9Bi=20c=C3=A1c=20s=E1=BA=A3n=20ph=E1=BA=A9m=20=C4=91ang=20c=C3=B3=20tr=C3= =AAn=20th=E1=BB=8B=20tr=C6=B0=E1=BB=9Dng Gi=C3=A1=20tr=E1=BB=8B=20giao=20d=E1=BB=8Bch=20h=C3=A0ng=20=20th=C3=A1ng= =20c=E1=BB=A7a=20b=E1=BA=A1nM=E1=BB=A9c=20ph=C3=AD=20tr=C3=AAn=20th=E1=BB= =8B=20tr=C6=B0=E1=BB=9Dng=20(0.3%=20tr=C3=AAn=20gi=C3=A1=20tr=E1=BB=8B=20gi= ao=20d=E1=BB=8Bch)S=E1=BB=91=20ti=E1=BB=81n=20b=E1=BA=A1n=20ti=E1=BA=BFt=20= ki=E1=BB=87m=20=20trong=201=20th=C3=A1ng 500.000.0001.500.0001.315.000=20=C4=91=E1=BB=93ng 1.000.000.0003.000.0002.815.000=20=C4=91=E1=BB=93ng 2.000.000.0006.000.0005.815.000=20=C4=91=E1=BB=93ng H=C3=83Y=20=C4=90=C4=82NG=20K=C3=9D=20M=E1=BB=9E=20T=C3=80I=20KHO=E1=BA=A2= N=20T=E1=BA=A0I=20=C4=90=C3=82Y. C=C3=81C=20S=E1=BA=A2N=20PH=E1=BA=A8M=20C=E1=BB=A6A=20C=C3=94NG=20TY. Kh=C3=A1ch=20h=C3=A0ng=20c=C3=A1=20nh=C3=A2nKh=C3=A1ch=20h=C3=A0ng=20doanh= =20nghi=E1=BB=87pC=C3=A1c=20d=E1=BB=8Bch=20v=E1=BB=A5=20tr=E1=BB=B1c=20tuy= =E1=BA=BFn M=E1=BB=9F=20t=C3=A0i=20kho=E1=BA=A3n=20 Giao=20d=E1=BB=8Bch=20ch=E1=BB=A9ng=20kho=C3=A1n=20 Qu=E1=BA=A3n=20l=C3=BD=20s=E1=BB=95=20c=E1=BB=95=20=C4=91=C3=B4ng=20 L=C6=B0u=20k=C3=BD=20ch=E1=BB=A9ng=20kho=C3=A1n=20 N=E1=BB=99p,=20r=C3=BAt=20ti=E1=BB=81n=20 Th=E1=BB=B1c=20hi=E1=BB=87n=20quy=E1=BB=81n=20 H=E1=BB=97=20tr=E1=BB=A3=20v=E1=BB=91n=20 =C4=90=E1=BA=A5u=20gi=C3=A1=20v=C3=A0=20nh=E1=BA=ADn=20=E1=BB=A7y=20th=C3= =A1c=20=C4=91=E1=BA=A5u=20gi=C3=A1=20 S=E1=BA=A3n=20ph=E1=BA=A9m=20kh=C3=A1c T=C6=B0=20v=E1=BA=A5n=20c=E1=BB=95=20ph=E1=BA=A7n=20h=C3=B3a=20doanh=20ngh= i=E1=BB=87p=20 T=C6=B0=20v=E1=BA=A5n=20ni=C3=AAm=20y=E1=BA=BFt=20v=C3=A0=20=C4=91=C4=83ng= =20k=C3=BD=20giao=20d=E1=BB=8Bch=20 T=C6=B0=20v=E1=BA=A5n=20t=C3=A1i=20c=E1=BA=A5u=20tr=C3=BAc=20doanh=20nghi= =E1=BB=87p M=E1=BB=9F=20t=C3=A0i=20kho=E1=BA=A3n=20tr=E1=BB=B1c=20tuy=E1=BA=BFn=20 Giao=20d=E1=BB=8Bch=20tr=E1=BB=B1c=20tuy=E1=BA=BFn=20 Chuy=E1=BB=83n=20ti=E1=BB=81n=20tr=E1=BB=B1c=20tuy=E1=BA=BFn=20 =E1=BB=A8ng=20tr=C6=B0=E1=BB=9Bc=20ti=E1=BB=81n=20b=C3=A1n=20ch=E1=BB=A9ng= =20kho=C3=A1n=20 Giao=20d=E1=BB=8Bch=20l=C3=B4=20l=E1=BA=BB=20tr=E1=BB=B1c=20tuy=E1=BA=BFn= =20 Ch=E1=BB=9D=20l=E1=BB=87nh=20t=E1=BB=B1=20=C4=91=E1=BB=99ng=20s=C3=A0n=20H= ose=20 Th=E1=BB=B1c=20hi=E1=BB=87n=20quy=E1=BB=81n=20tr=E1=BB=B1c=20tuy=E1=BA=BFn= =20 Thay=20=C4=91=E1=BB=95i=20th=C3=B4ng=20tin=20kh=C3=A1ch=20h=C3=A0ng=20 =C4=90=E1=BA=B7t=20c=E1=BA=A3nh=20b=C3=A1o=20tr=E1=BB=B1c=20tuy=E1=BA=BFn C=C3=B4ng=20ty=20C=E1=BB=95=20ph=E1=BA=A7n=20Ch=E1=BB=A9ng=20kho=C3=A1n=20= Ch=C3=A2u=20=C3=81=20Th=C3=A1i=20B=C3=ACnh=20D=C6=B0=C6=A1ng=20 =C4=90=E1=BB=8Ba=20ch=E1=BB=89:=20S=E1=BB=91=2014=20L=C3=AA=20=C4=90=E1=BA= =A1i=20H=C3=A0nh,=20Qu=E1=BA=ADn=20Hai=20B=C3=A0=20Tr=C6=B0ng,=20TP=20H=C3= =A0=20N=E1=BB=99i Tel:=20(04)=203577=201968=20 E-mail:=20dichvukhachhang@apecs.com.vn ------=_NextPart_783_4728_97266641.33425785 Content-Type: text/html; charset=utf-8 Content-Transfer-Encoding: quoted-printable body,table,td,tr,p,input=20{font-family:=20Verdana,=20Arial,=20Helvetica,= =20Sans-Serif;=20font-size:=2011px} hr=20{height:=201px}

 =20
CH=C6=AF=C6=A0NG=20TR=C3=8CNH=20=C6=AFU=20=C4=90=C3=83= I=20PH=C3=8D=20GIAO=20D=E1=BB=8ACH=20CH=E1=BB=88=20TRONG=20N=C4=82M=202013<= BR>

C=C3=B4ng=20ty=20ch=E1= =BB=A9ng=20kho=C3=A1n=20APEC=20l=C3=A0=20m=E1=BB=99t=20trong=20nh=E1=BB=AFn= g=20c=C3=B4ng=20ty=20ch=E1=BB=A9ng=20kho=C3=A1n=20h=C3=A0ng=20=C4=91=E1=BA= =A7u=20t=E1=BA=A1i=20Vi=E1=BB=87t=20Nam=20v=E1=BB=9Bi=20h=E1=BB=87=20th=E1= =BB=91ng=20m=E1=BA=A1ng=20l=C6=B0=E1=BB=9Bi=20r=E1=BB=99ng=20kh=E1=BA=AFp= =20tr=C3=AAn=20c=E1=BA=A3=20n=C6=B0=E1=BB=9Bc.=20Ch=C3=BAng=20t=C3=B4i=20lu= =C3=B4n=20mong=20mu=E1=BB=91n=20=C4=91=C6=B0a=20t=E1=BB=9Bi=20Qu=C3=BD=20kh= =C3=A1ch=20h=C3=A0ng=20c=C3=A1c=20s=E1=BA=A3n=20ph=E1=BA=A9m=20t=C3=A0i=20c= h=C3=ADnh=20v=E1=BB=9Bi=20ch=E1=BA=A5t=20l=C6=B0=E1=BB=A3ng=20t=E1=BB=91t= =20nh=E1=BA=A5t.=20V=E1=BB=9Bi=20=C4=91=E1=BB=99i=20ng=C5=A9=20c=C3=A1c=20c= huy=C3=AAn=20gia=20t=C3=A0i=20ch=C3=ADnh=20gi=C3=A0u=20kinh=20nghi=E1=BB=87= m,=20c=C3=A1c=20m=C3=B4i=20gi=E1=BB=9Bi=20ch=E1=BB=A9ng=20kho=C3=A1n=20v=E1= =BB=9Bi=20th=C3=A1i=20=C4=91=E1=BB=99=20t=E1=BA=ADn=20t=C3=A2m=20v=E1=BB=9B= i=20kh=C3=A1ch=20h=C3=A0ng,=20ch=C3=BAng=20t=C3=B4i=20hi=20v=E1=BB=8Dng=20s= =E1=BA=BD=20mang=20=C4=91=E1=BA=BFn=20cho=20Qu=C3=BD=20kh=C3=A1ch=20nh=E1= =BB=AFng=20gi=C3=A1=20tr=E1=BB=8B=20b=E1=BB=81n=20v=E1=BB=AFng.

Nh=C3=A2n=20d=E1=BB=8Bp= =20C=C3=B4ng=20ty=20ch=E1=BB=A9ng=20kho=C3=A1n=20APEC=20tr=C3=B2n=205=20tu= =E1=BB=95i,=20Ch=C3=BAng=20t=C3=B4i=20xin=20gi=E1=BB=9Bi=20thi=E1=BB=87u=20= t=E1=BB=9Bi=20Qu=C3=BD=20kh=C3=A1ch=20h=C3=A0ng=20m=E1=BB=99t=20s=E1=BA=A3n= =20ph=E1=BA=A9m=20t=C3=A0i=20ch=C3=ADnh=20m=E1=BB=9Bi.

PH=C3=8D=20GIAO=20D=E1=BB=8ACH=20PH=E1=BA=B2NG=20

=C4=90=E1=BB=91i=20t=C6= =B0=E1=BB=A3ng=20=C4=91=C6=B0=E1=BB=A3c=20h=C6=B0=E1=BB=9Fng:=20C=C3=A1c=20= kh=C3=A1ch=20h=C3=A0ng=20m=E1=BB=9F=20t=C3=A0i=20kho=E1=BA=A3n=20ch=E1=BB= =A9ng=20kho=C3=A1n=20trong=20th=E1=BB=9Di=20gian=202013=20v=C3=A0=20=C4=91= =C4=83ng=20k=C3=BD=20tham=20gia=20g=C3=B3i=20s=E1=BA=A3n=20ph=E1=BA=A9m=20= =E2=80=9CPh=C3=AD=20giao=20d=E1=BB=8Bch=20ph=E1=BA=B3ng=E2=80=9D

L=E1=BB=A3i=20=C3= =ADch=20c=E1=BB=A7a=20ch=C6=B0=C6=A1ng=20tr=C3=ACnh:=20B=E1=BA=A1n=20kh=C3= =B4ng=20ph=E1=BA=A3i=20lo=20v=E1=BB=81=20gi=C3=A1=20tr=E1=BB=8B=20giao=20d= =E1=BB=8Bch=20h=C3=A0ng=20th=C3=A1ng=20=C4=91=E1=BB=83=20t=C3=ADnh=20tr=E1= =BA=A3=20ph=C3=AD=20m=C3=A0=20b=E1=BA=A1n=20ch=E1=BB=89=20c=E1=BA=A7n=20ph= =E1=BA=A3i=20tr=E1=BA=A3=20150.000=20=C4=91=E1=BB=93ng/th=C3=A1ng=20th=C3=B4ng=20qua= =20g=C3=B3i=20s=E1=BA=A3n=20ph=E1=BA=A9m
=E2=80=9CPh=C3=AD=20giao= =20d=E1=BB=8Bch=20ph=E1=BA=B3ng=E2=80=9D.

So=20s=C3=A1nh=20Ph=C3=AD=20giao=20d=E1=BB=8Bch= =20ph=E1=BA=B3ng=20v=E1=BB=9Bi=20c=C3=A1c=20s=E1=BA=A3n=20ph=E1=BA=A9m=20= =C4=91ang=20c=C3=B3=20tr=C3=AAn=20th=E1=BB=8B=20tr=C6=B0=E1=BB=9Dng<= /B>

= Gi=C3=A1=20tr=E1=BB=8B=20giao=20d=E1=BB=8Bch=20h=C3=A0ng  = th=C3=A1ng=20c=E1=BB=A7a=20b=E1=BA=A1n

M= =E1=BB=A9c=20ph=C3=AD=20tr=C3=AAn=20th=E1=BB=8B=20tr=C6=B0=E1=BB=9Dng=20(0.= 3%=20tr=C3=AAn=20gi=C3=A1=20tr=E1=BB=8B=20giao=20d=E1=BB=8Bch) = S=E1=BB=91=20ti=E1=BB=81n=20b=E1=BA=A1n=20ti=E1=BA=BFt=20ki=E1=BB=87m&nb= sp; trong=201=20th=C3=A1ng

500.000.000

1.500.000

1.315.000 =C4=91= =E1=BB=93ng

1.000.000.000

3.000.000

2.815.000 =C4=91= =E1=BB=93ng

2.000.000.000

6.000.000

5.815.000 =C4=91= =E1=BB=93ng

<= BR> H=C3=83Y=20=C4=90=C4=82NG=20K=C3=9D=20M=E1=BB=9E= =20T=C3=80I=20KHO=E1=BA=A2N=20T=E1=BA=A0I= =20=C4=90=C3=82Y.


C= =C3=81C=20S=E1=BA=A2N=20PH=E1=BA=A8M=20C=E1=BB=A6A=20C=C3=94NG=20TY.=

Kh= =C3=A1ch=20h=C3=A0ng=20c=C3=A1=20nh=C3=A2n

Kh= =C3=A1ch=20h=C3=A0ng=20doanh=20nghi=E1=BB=87p

C= =C3=A1c=20d=E1=BB=8Bch=20v=E1=BB=A5=20tr=E1=BB=B1c=20tuy=E1=BA=BFn

  • M=E1=BB=9F=20t=C3=A0i=20kho= =E1=BA=A3n=20
  • Giao=20d=E1=BB=8Bch= =20ch=E1=BB=A9ng=20kho=C3=A1n=20
  • Qu=E1=BA=A3n=20l=C3=BD=20= s=E1=BB=95=20c=E1=BB=95=20=C4=91=C3=B4ng=20
  • L=C6=B0u=20k=C3=BD=20ch= =E1=BB=A9ng=20kho=C3=A1n=20
  • N=E1=BB=99p,=20r=C3=BAt=20ti= =E1=BB=81n=20
  • Th=E1=BB=B1c=20hi=E1=BB=87= n=20quy=E1=BB=81n=20
  • H=E1=BB=97=20tr=E1=BB=A3=20v=E1= =BB=91n=20
  • =C4=90=E1=BA=A5= u=20gi=C3=A1=20v=C3=A0=20nh=E1=BA=ADn=20=E1=BB=A7y=20th=C3=A1c=20=C4=91=E1= =BA=A5u=20gi=C3=A1=20
  • <= FONT=20face=3D"Times=20New=20Roman"=20size=3D4>S=E1=BA=A3n=20ph=E1=BA=A9m= =20kh=C3=A1c
  • T=C6=B0= =20v=E1=BA=A5n=20c=E1=BB=95=20ph=E1=BA=A7n=20h=C3=B3a=20doanh=20nghi=E1=BB= =87p=20
  • T=C6= =B0=20v=E1=BA=A5n=20ni=C3=AAm=20y=E1=BA=BFt=20v=C3=A0=20=C4=91=C4=83ng=20k= =C3=BD=20giao=20d=E1=BB=8Bch=20
  • T=C6= =B0=20v=E1=BA=A5n=20t=C3=A1i=20c=E1=BA=A5u=20tr=C3=BAc=20doanh=20nghi=E1=BB= =87p
  • M=E1=BB=9F=20t=C3= =A0i=20kho=E1=BA=A3n=20tr=E1=BB=B1c=20tuy=E1=BA=BFn=20
  • Giao=20d=E1=BB=8B= ch=20tr=E1=BB=B1c=20tuy=E1=BA=BFn=20
  • Chuy=E1=BB=83n=20= ti=E1=BB=81n=20tr=E1=BB=B1c=20tuy=E1=BA=BFn=20
  • =E1=BB=A8ng= =20tr=C6=B0=E1=BB=9Bc=20ti=E1=BB=81n=20b=C3=A1n=20ch=E1=BB=A9ng=20kho=C3=A1= n=20
  • Giao=20d=E1=BB= =8Bch=20l=C3=B4=20l=E1=BA=BB=20tr=E1=BB=B1c=20tuy=E1=BA=BFn= =20
  • Ch=E1=BB=9D=20l= =E1=BB=87nh=20t=E1=BB=B1=20=C4=91=E1=BB=99ng=20s=C3=A0n=20Hose=20
  • Th=E1=BB=B1c= =20hi=E1=BB=87n=20quy=E1=BB=81n=20tr=E1=BB=B1c=20tuy=E1=BA=BFn=20
  • Thay=20=C4= =91=E1=BB=95i=20th=C3=B4ng=20tin=20kh=C3=A1ch=20h=C3=A0ng= =20
  • =C4=90=E1=BA=B7t= =20c=E1=BA=A3nh=20b=C3=A1o=20tr=E1=BB=B1c=20tuy=E1=BA=BFn

=
C=C3=B4ng=20ty=20C=E1=BB=95=20ph=E1=BA=A7n=20Ch=E1=BB=A9ng=20k= ho=C3=A1n=20Ch=C3=A2u=20=C3=81=20Th=C3=A1i=20B=C3=ACnh=20D=C6=B0=C6=A1ng&nb= sp;

=C4=90=E1=BB=8Ba=20ch=E1=BB=89:=20S=E1= =BB=91=2014=20L=C3=AA=20=C4=90=E1=BA=A1i=20H=C3=A0nh,=20Qu=E1=BA=ADn=20Hai= =20B=C3=A0=20Tr=C6=B0ng,=20TP=20H=C3=A0=20N=E1=BB=99i
Tel:=20(04)=203577= =201968=20
E-mail: dichvukhachhang@apecs.com.vn  =20 


------=_NextPart_783_4728_97266641.33425785-- From mitrodora.silu.81@insular.com Thu Mar 14 01:00:28 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.5 required=5.0 tests=HTML_MESSAGE,SUBJ_ALL_CAPS autolearn=no version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id CB9CE7CBF for ; Thu, 14 Mar 2013 01:00:27 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay3.corp.sgi.com (Postfix) with ESMTP id 5A4A2AC001 for ; Wed, 13 Mar 2013 23:00:24 -0700 (PDT) X-ASG-Debug-ID: 1363240811-04bdf00a0baebb0001-NocioJ Received: from vip1.xlho.st (vip.xlho.st [5.9.155.238]) by cuda.sgi.com with ESMTP id dBA5BHC7dtfjpFQp (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO) for ; Wed, 13 Mar 2013 23:00:12 -0700 (PDT) X-Barracuda-Envelope-From: mitrodora.silu.81@insular.com X-Barracuda-Apparent-Source-IP: 5.9.155.238 Received: from hn.ly.kd.adsl (unknown [61.163.37.76]) by vip1.xlho.st (Postfix) with ESMTPA id 009883ECD5F; Thu, 14 Mar 2013 09:59:53 +0400 (MSK) Message-ID: <493BEAEC63C04A25AF6D73DB41A042AB@jtax> Reply-To: =?windows-1251?B?yvPw8fsg8eXq8OXy4PDl6Q==?= From: =?windows-1251?B?yvPw8fsg8eXq8OXy4PDl6Q==?= To: , , , Subject: =?windows-1251?B?0eXq8OXy4PD8IFhYSSDi5erg?= Date: Wed, 13 Mar 2013 22:58:26 -0700 X-ASG-Orig-Subj: =?windows-1251?B?0eXq8OXy4PD8IFhYSSDi5erg?= MIME-Version: 1.0 Content-Type: multipart/alternative; boundary="----=_NextPart_000_18CE_01CE203E.45519A00" X-Priority: 3 X-MSMail-Priority: Normal X-Mailer: Microsoft Outlook Express 6.00.2900.5931 X-MimeOLE: Produced By Microsoft MimeOLE V6.00.2900.6109 X-Virus-Scanned: clamav-milter 0.97.6 at vip1.xlho.st X-Virus-Status: Clean X-Barracuda-Connect: vip.xlho.st[5.9.155.238] X-Barracuda-Start-Time: 1363240811 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_TG035a, HTML_MESSAGE X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125151 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 HTML_MESSAGE BODY: HTML included in message 0.00 BSF_SC0_TG035a Message contains invalid style definition This is a multi-part message in MIME format. ------=_NextPart_000_18CE_01CE203E.45519A00 Content-Type: text/plain; charset="windows-1251" Content-Transfer-Encoding: quoted-printable =D3=E2=E0=E6=E0=E5=EC=FB=E5 =EA=EE=EB=EB=E5=E3=E8! =D6=E5=ED=F2=F0 =D1=EF=E5=F6=E8=E0=EB=E8=E7=E8=F0=EE=E2=E0=ED=ED=EE=E3=EE= =CE=E1=F3=F7=E5=ED=E8=FF =E3. =D1=E0=ED=EA=F2-=CF=E5=F2=E5=F0=E1=F3=F0=E3= =E0 =EF=F0=E8=E3=EB=E0=F8=E0=E5=F2 =C2=E0=F1 =EF=EE=F1=E5=F2=E8=F2=FC =EA= =EE=ED=F4=E5=F0=E5=ED=F6=E8=FE: I7 - l8 =E0=EF=F0=E5=EB=FF 20l3 =E3., =D1=E0=ED=EA=F2-=CF=E5=F2=E5=F0=E1= =F3=F0=E3 =C1=C8=C7=CD=C5=D1 - =DD=D2=C8=CA=C5=D2 =D1=C5=CA=D0=C5=D2=C0=D0=DF. =C4=C5= =CB=CE=C2=CE=C5 =CE=C1=D9=C5=CD=C8=C5 =C8 =CF=D0=CE=D4=C5=D1=D1=C8=CE=CD=C0= =CB=DC=CD=C0=DF =CA=CE=CC=CF=C5=D2=C5=CD=D2=CD=CE=D1=D2=DC. =CA=F0=E0=F2=EA=E0=FF =EF=F0=EE=E3=F0=E0=EC=EC=E0: 1. =C8=F1=EA=F3=F1=F1=F2=E2=EE =F1=E0=EC=EE=EF=F0=E5=E7=E5=ED=F2=E0=F6=E8= =E8 =E8 =E8=EC=E8=E4=E6 =E4=E5=EB=EE=E2=EE=E3=EE =F7=E5=EB=EE=E2=E5=EA=E0= . 2. =CE=F0=E3=E0=ED=E8=E7=E0=F6=E8=FF =E8 =EF=F0=EE=E2=E5=E4=E5=ED=E8=E5 =EE= =F4=E8=F6=E8=E0=EB=FC=ED=FB=F5 =E8 =ED=E5=F4=EE=F0=EC=E0=EB=FC=ED=FB=F5 =EF= =F0=E8=E5=EC=EE=E2. 3. =DD=F2=E8=EA=E5=F2=ED=FB=E5 =F2=F0=E5=E1=EE=E2=E0=ED=E8=FF =EF=F0=EE=E2= =E5=E4=E5=ED=E8=FF =E4=E5=EB=EE=E2=FB=F5 =E1=E5=F1=E5=E4. 4. =D1=EB=F3=E6=E5=E1=ED=FB=E9 =FD=F2=E8=EA=E5=F2. 5. =CA=EE=EC=EC=F3=ED=E8=EA=E0=F2=E8=E2=ED=E0=FF =EA=F3=EB=FC=F2=F3=F0=E0= =E8 =F0=E5=F7=E5=E2=EE=E9 =FD=F2=E8=EA=E5=F2. 6. =CF=F1=E8=F5=EE=EB=EE=E3=E8=F7=E5=F1=EA=E0=FF =EA=F3=EB=FC=F2=F3=F0=E0= =E2=E7=E0=E8=EC=EE=EE=F2=ED=EE=F8=E5=ED=E8=E9. 7. =CF=F0=EE=F4=E8=EB=E0=EA=F2=E8=EA=E0 =E8 =F0=E0=E7=F0=E5=F8=E5=ED=E8=E5= =EA=EE=ED=F4=EB=E8=EA=F2=EE=E2: - =F1=F2=F0=E0=F2=E5=E3=E8=E8 =EF=EE=E2=E5=E4=E5=ED=E8=FF =E2 =EA=EE=ED=F4= =EB=E8=EA=F2=ED=EE=E9 =F1=E8=F2=F3=E0=F6=E8=E8; - =EC=E5=F2=EE=E4=FB =F0=E0=E7=F0=E5=F8=E5=ED=E8=FF =EA=EE=ED=F4=EB=E8=EA= =F2=EE=E2; - =F2=E8=EF=FB =EA=EE=ED=F4=EB=E8=EA=F2=ED=FB=F5 =EB=E8=F7=ED=EE=F1=F2=E5= =E9 =E8 =F2=E0=EA=F2=E8=EA=E0 =EE=E1=F9=E5=ED=E8=FF =F1 =ED=E8=EC=E8. 8. =CF=EE=E2=FB=F8=E5=ED=E8=E5 =EF=F0=E5=F1=F2=E8=E6=E0 =EF=F0=EE=F4=E5=F1= =F1=E8=E8 =E8 =F3=F1=EB=EE=E2=E8=FF =F3=F1=EF=E5=F8=ED=EE=E3=EE =EA=E0=F0= =FC=E5=F0=ED=EE=E3=EE =EF=F0=EE=E4=E2=E8=E6=E5=ED=E8=FF. =C1=EE=EB=E5=E5 =EF=EE=E4=F0=EE=E1=ED=E0=FF =EF=F0=EE=E3=F0=E0=EC=EC=E0 =E2= =FB=F1=FB=EB=E0=E5=F2=F1=FF =EF=EE =E7=E0=EF=F0=EE=F1=F3. =CF=EE =F3=F1=EB=EE=E2=E8=FF=EC =F3=F7=E0=F1=F2=E8=FF =EE=E1=F0=E0=F9=E0=E9= =F2=E5=F1=FC =EA =ED=E0=F8=E8=EC =EC=E5=ED=E5=E4=E6=E5=F0=E0=EC =EF=EE =F2= =E5=EB=E5=F4=EE=ED=F3: { =EA=EE=E4 =D1=CF=E1 } 64__2 0l * 0 6 =20 =D1 =F3=E2=E0=E6=E5=ED=E8=E5=EC, =C3=EE=EB=F3=E1=E5=E2=E0 =C0=ED=ED=E0 =C2=E8=EA=F2=EE=F0=EE=E2=ED=E0 =EC=E5=ED=E5=E4=E6=E5=F0 =EF=EE =F0=E0=E1=EE=F2=E5 =F1 =EA=EB=E8=E5=ED=F2= =E0=EC=E8 ------=_NextPart_000_18CE_01CE203E.45519A00 Content-Type: text/html; charset="windows-1251" Content-Transfer-Encoding: quoted-printable
=D3=E2=E0=E6=E0=E5=EC=FB=E5 =EA=EE=EB=EB=E5=E3=E8!
 
=D6=E5=ED=F2=F0 =D1=EF=E5=F6=E8=E0=EB=E8=E7=E8=F0=EE=E2=E0=ED=ED=EE=E3= =EE =CE=E1=F3=F7=E5=ED=E8=FF =E3. =D1=E0=ED=EA=F2-=CF=E5=F2=E5=F0=E1=F3=F0= =E3=E0 =EF=F0=E8=E3=EB=E0=F8=E0=E5=F2 =C2=E0=F1=20 =EF=EE=F1=E5=F2=E8=F2=FC =EA=EE=ED=F4=E5=F0=E5=ED=F6=E8=FE:
 
I7 - l8=20 =E0=EF=F0=E5=EB=FF 20l3 =E3.,=20 =D1=E0=ED=EA=F2-=CF=E5=F2=E5=F0=E1=F3=F0=E3
 
=C1=C8=C7=CD=C5=D1 - =DD=D2=C8=CA=C5=D2 =D1=C5=CA=D0=C5=D2=C0=D0=DF.= =C4=C5=CB=CE=C2=CE=C5 =CE=C1=D9=C5=CD=C8=C5 =C8 =CF=D0=CE=D4=C5=D1=D1=C8= =CE=CD=C0=CB=DC=CD=C0=DF=20 =CA=CE=CC=CF=C5=D2=C5=CD=D2=CD=CE=D1=D2=DC.
 
=CA=F0=E0=F2=EA=E0=FF =EF=F0=EE=E3=F0=E0=EC=EC=E0:
 
1. =C8=F1=EA=F3=F1=F1=F2=E2=EE =F1=E0=EC=EE=EF=F0=E5=E7=E5=ED=F2=E0=F6= =E8=E8 =E8 =E8=EC=E8=E4=E6 =E4=E5=EB=EE=E2=EE=E3=EE =F7=E5=EB=EE=E2=E5=EA= =E0.
 
2. =CE=F0=E3=E0=ED=E8=E7=E0=F6=E8=FF =E8 =EF=F0=EE=E2=E5=E4=E5=ED=E8= =E5 =EE=F4=E8=F6=E8=E0=EB=FC=ED=FB=F5 =E8 =ED=E5=F4=EE=F0=EC=E0=EB=FC=ED=FB= =F5 =EF=F0=E8=E5=EC=EE=E2.
 
3. =DD=F2=E8=EA=E5=F2=ED=FB=E5 =F2=F0=E5=E1=EE=E2=E0=ED=E8=FF =EF=F0= =EE=E2=E5=E4=E5=ED=E8=FF =E4=E5=EB=EE=E2=FB=F5 =E1=E5=F1=E5=E4.
 
4. =D1=EB=F3=E6=E5=E1=ED=FB=E9 =FD=F2=E8=EA=E5=F2.
 
5. =CA=EE=EC=EC=F3=ED=E8=EA=E0=F2=E8=E2=ED=E0=FF =EA=F3=EB=FC=F2=F3=F0= =E0 =E8 =F0=E5=F7=E5=E2=EE=E9 =FD=F2=E8=EA=E5=F2.
 
6. =CF=F1=E8=F5=EE=EB=EE=E3=E8=F7=E5=F1=EA=E0=FF =EA=F3=EB=FC=F2=F3=F0= =E0 =E2=E7=E0=E8=EC=EE=EE=F2=ED=EE=F8=E5=ED=E8=E9.
 
7. =CF=F0=EE=F4=E8=EB=E0=EA=F2=E8=EA=E0 =E8 =F0=E0=E7=F0=E5=F8=E5=ED= =E8=E5 =EA=EE=ED=F4=EB=E8=EA=F2=EE=E2:
- =F1=F2=F0=E0=F2=E5=E3=E8=E8 =EF= =EE=E2=E5=E4=E5=ED=E8=FF =E2=20 =EA=EE=ED=F4=EB=E8=EA=F2=ED=EE=E9 =F1=E8=F2=F3=E0=F6=E8=E8;
- =EC=E5=F2= =EE=E4=FB =F0=E0=E7=F0=E5=F8=E5=ED=E8=FF =EA=EE=ED=F4=EB=E8=EA=F2=EE=E2;<= BR>- =F2=E8=EF=FB =EA=EE=ED=F4=EB=E8=EA=F2=ED=FB=F5=20 =EB=E8=F7=ED=EE=F1=F2=E5=E9 =E8 =F2=E0=EA=F2=E8=EA=E0 =EE=E1=F9=E5=ED=E8=FF= =F1 =ED=E8=EC=E8.
 
8. =CF=EE=E2=FB=F8=E5=ED=E8=E5 =EF=F0=E5=F1=F2=E8=E6=E0 =EF=F0=EE=F4= =E5=F1=F1=E8=E8 =E8 =F3=F1=EB=EE=E2=E8=FF =F3=F1=EF=E5=F8=ED=EE=E3=EE =EA= =E0=F0=FC=E5=F0=ED=EE=E3=EE=20 =EF=F0=EE=E4=E2=E8=E6=E5=ED=E8=FF.

=C1=EE=EB=E5=E5 =EF=EE=E4=F0=EE=E1=ED=E0=FF =EF=F0=EE=E3=F0=E0=EC= =EC=E0 =E2=FB=F1=FB=EB=E0=E5=F2=F1=FF =EF=EE =E7=E0=EF=F0=EE=F1=F3.
 
=CF=EE =F3=F1=EB=EE=E2=E8=FF=EC =F3=F7=E0=F1=F2=E8=FF =EE=E1=F0=E0=F9= =E0=E9=F2=E5=F1=FC =EA =ED=E0=F8=E8=EC =EC=E5=ED=E5=E4=E6=E5=F0=E0=EC =EF= =EE =F2=E5=EB=E5=F4=EE=ED=F3:
{ =EA=EE=E4 =D1=CF=E1 } 64__2 0l * 0 6
 
=D1 =F3=E2=E0=E6=E5=ED=E8=E5=EC,
=C3=EE=EB=F3=E1=E5=E2=E0 =C0=ED=ED= =E0 =C2=E8=EA=F2=EE=F0=EE=E2=ED=E0
=EC=E5=ED=E5=E4=E6=E5=F0 =EF=EE =F0= =E0=E1=EE=F2=E5 =F1=20 =EA=EB=E8=E5=ED=F2=E0=EC=E8
------=_NextPart_000_18CE_01CE203E.45519A00-- From david@fromorbit.com Thu Mar 14 01:18:54 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 1D8CD7F37 for ; Thu, 14 Mar 2013 01:18:54 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id EBF3E304067 for ; Wed, 13 Mar 2013 23:18:53 -0700 (PDT) X-ASG-Debug-ID: 1363241922-04cbb04b859ded0001-NocioJ Received: from ipmail06.adl2.internode.on.net (ipmail06.adl2.internode.on.net [150.101.137.129]) by cuda.sgi.com with ESMTP id gTyXtgsYKA0W4AkD for ; Wed, 13 Mar 2013 23:18:43 -0700 (PDT) X-Barracuda-Envelope-From: david@fromorbit.com X-Barracuda-Apparent-Source-IP: 150.101.137.129 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: Aj4eAIpqQVF5LMKP/2dsb2JhbAA9BodIuBCFEgECAYFkF3SCKgEBBAE6HBUOBQsIAxgJJQ8FJQMhE4gOBcFxFY1WJBgfSgeDQAOWV5EDgx4o Received: from ppp121-44-194-143.lns20.syd7.internode.on.net (HELO dastard) ([121.44.194.143]) by ipmail06.adl2.internode.on.net with ESMTP; 14 Mar 2013 16:48:41 +1030 Received: from dave by dastard with local (Exim 4.76) (envelope-from ) id 1UG1Ut-0006Od-TQ; Thu, 14 Mar 2013 17:18:39 +1100 Date: Thu, 14 Mar 2013 17:18:39 +1100 From: Dave Chinner To: "Eric W. Biederman" Cc: linux-fsdevel@vger.kernel.org, Linux Containers , xfs@oss.sgi.com, "Serge E. Hallyn" , Ben Myers , Alex Elder Subject: Re: [PATCH 00/14] xfs: Support for interacting with multiple user namespaces Message-ID: <20130314061839.GY21651@dastard> X-ASG-Orig-Subj: Re: [PATCH 00/14] xfs: Support for interacting with multiple user namespaces References: <87boan3prc.fsf@xmission.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <87boan3prc.fsf@xmission.com> User-Agent: Mutt/1.5.21 (2010-09-15) X-Barracuda-Connect: ipmail06.adl2.internode.on.net[150.101.137.129] X-Barracuda-Start-Time: 1363241923 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_MISMATCH_TO X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125153 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 BSF_SC0_MISMATCH_TO Envelope rcpt doesn't match header On Wed, Mar 13, 2013 at 03:21:11PM -0700, Eric W. Biederman wrote: > > Or replace uids, gids, and projids with kuids, kgids, and kprojids > > In support of user namespaces I have introduced into the kernel kuids, > kgids, and kprojids. The most important characteristic of these ids is > that they are not assignment compatible with uids, gids, and projids > coming from userspace nor are they assignment compatible with uids, gids > or projids stored on disk. This assignment incompatibility makes it > easy to ensure that conversions are introduced at the edge of userspace > and at the interface between on-disk and in-memory data structures. TL;DR: Compared to the last version of this patchset I NACKed, this version increases the per-inode memory footprint by over 100 bytes (i.e. by more than 10%), introduces a double copy of the inode core data into the *hottest path in XFS*, breaks log recovery and fails to address a single NACK I gave for the previous round of the patch set. So, NACK. > Converting xfs is an interesting challenge because of the way xfs > handles it's inode data is very atypical. That you have to tell people that find it strange an unusual immediately indicates that you do not really understand the design and structure of the XFS code. This makes your refusal to listen to feedback from someone who is a subject matter expert all the more difficult to understand. I'll accept that you might forget something mentioned in a review when you post an update, but to ignore a second NACK for the same patch and posting it a third time unchanged is not the best way to make friends and influence people.... And given that you didn't respond to a single review comment I made on the previous version of the patch, well, I have my doubts you are going to respond this time, either. In previous reviews comments I have: - outlined exactly how to provide a minimally invasive patch set that provides full namespace support as a first step in getting XFS to support namespaces. - told you where the ondisk/in-memory boundaries are. - told you that certain IDs are filesystem internal and not subject to namespaces. - asked questions about how filesystems utilities are supposed to deal with namespaces (i.e. userspace impacts of ioctl interface changes). And you haven't responded to any of them. You can't selectively ignore review comments you don't like and then magically expect the reviewers to accept an almost-identical-but-even-more-broken patch set the next time around. > Given the number of ioctls that xfs supports it would be irresponsible to > do anything except insist that kuids, kgids, and kprojids are used in all of > in memory data structures of xfs, as otherwise it becomes trivially easy to > miss a needed conversion with the advent of a new ioctl. Eric, your rhetoric looks so fine and shiny on the wall, but it is utterly worthless. You're telling us that userspace interface are absolutely necessary, but haven't provided any analysis, description or justification so we can judge the impact of the changes or review why you think the only way such changes can be made is your way. Nor have you provided any regression tests to verify that this shiny new namespace support is working as the maker has intended. IOWs, I've got no idea what the impact of changing all the ioctls will be, no way to verify it is correct and you sure as hell aren't going out of your way to make it easy for us to understand the impact, either. Further, I'm pretty sure that you are not even aware of the scope of the issues that namespace awareness raise for some of these XFS ioctls. I've previously asked some questions about behaviours of them, but like most of my other review comments you have ignored those questions. So, before we go changing anything ioctl related, here's some questions you need to answer: - if you run bulkstat, what do we do with inodes that contain a ID owned by a namespace outside the current namespace? - Can we even check the on-disk inode IDs are valid within a specific namespace within the kernel? - open_by_handle() would appear to allow root in any namespace to open any file in the filesystem it has a valid handle for regardless of the namespace. Is this allowable? The output of bulkstat can be fed directly to open_by_handle(), so if bulkstat can return inodes outside the namespace, open-by-handle can open them and we can do invisible IO on them. - Further, we can extract and set attributes directly by handle and, IIRC, that includes security/trusted namespace attributes.... - On the same measure, the handles used by XFS handle interfaces are identical to NFS handles and use the same code for decoding and dentry lookup. So, what do handle restrictions mean for NFS servers? - have you considered that fs/fhandle.c raises many of these same issues? - and seeing xfsdump and xfs_fsr use bulkstat and handles, what do new limitations on these interfaces mean for these utilities? - How does xfs_dump/xfs_restore work if we convert all ids based on the current namespace? e.g. dump in one namespace, restore in another. - How does xfs_dump/xfs_restore work if we *don't* convert all ids (i.e. export the on-disk values)? - How do we document/communicate all these constraints/ behaviours to users who might be completely unaware of them? IOWs, simply converting IDs the ioctls take in or emit is only a small part of the larger question of how they are supposed to behave in namespace containers. These questions need to be answered *in detail* and with *regression tests* before we accept any changes to the ioctl interfaces. Eric, I'm not trying to be difficult here - I'm holding the bar at the same height as it gets held for any significant XFS change that impacts userspace interfaces and behaviour. You don't maintain the XFS code, so you can just walk away once namespaces are "done" and not care that you've left a mess behind. And if you leave a mess, I'm the person who will have to clean it up. I don't want to have to clean up your mess, so I'm going to keep saying no until you can introduce namespace support without making a mess.... -Dave. -- Dave Chinner david@fromorbit.com From qcai@redhat.com Thu Mar 14 02:39:48 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 42E807F37 for ; Thu, 14 Mar 2013 02:39:48 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay2.corp.sgi.com (Postfix) with ESMTP id 27D4C304039 for ; Thu, 14 Mar 2013 00:39:45 -0700 (PDT) X-ASG-Debug-ID: 1363246783-04cb6c4a46b3150001-NocioJ Received: from mx3-phx2.redhat.com (mx3-phx2.redhat.com [209.132.183.24]) by cuda.sgi.com with ESMTP id FUJepDEYO1pnerQy for ; Thu, 14 Mar 2013 00:39:43 -0700 (PDT) X-Barracuda-Envelope-From: qcai@redhat.com X-Barracuda-Apparent-Source-IP: 209.132.183.24 Received: from zmail14.collab.prod.int.phx2.redhat.com (zmail14.collab.prod.int.phx2.redhat.com [10.5.83.16]) by mx3-phx2.redhat.com (8.13.8/8.13.8) with ESMTP id r2E7dXN1004083; Thu, 14 Mar 2013 03:39:34 -0400 Date: Thu, 14 Mar 2013 03:39:33 -0400 (EDT) From: CAI Qian To: Dave Chinner Cc: xfs@oss.sgi.com Message-ID: <740792090.842745.1363246773807.JavaMail.root@redhat.com> In-Reply-To: <20130313044307.GV21651@dastard> Subject: Re: 3.9-rc2 xfs panic MIME-Version: 1.0 X-ASG-Orig-Subj: Re: 3.9-rc2 xfs panic Content-Type: text/plain; charset=utf-8 Content-Transfer-Encoding: quoted-printable X-Originating-IP: [10.66.13.149] X-Mailer: Zimbra 7.2.0_GA_2669 (ZimbraWebClient - FF3.0 (Linux)/7.2.0_GA_2669) X-Barracuda-Connect: mx3-phx2.redhat.com[209.132.183.24] X-Barracuda-Start-Time: 1363246783 X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125156 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- OK, this time I reproduced this panic on both x64 and ppc64 systems with LVM partitions using the default block size as well as enabling debugging and memory poisoning options. - ppc64 trace: (nothing looks like really interesting prior to this) [ 2221.546337] XFS (dm-0): Corruption detected. Unmount and run xfs_repair [ 2221.546345] XFS (dm-0): bad inode magic/vsn daddr 64 #8 (magic=3D5858) [ 2221.546350] XFS: Assertion failed: 0, file: fs/xfs/xfs_inode.c, line: 41= 6 [ 2221.546383] ------------[ cut here ]------------ [ 2221.546386] kernel BUG at fs/xfs/xfs_message.c:100! [ 2221.546391] Oops: Exception in kernel mode, sig: 5 [#1] [ 2221.546394] SMP NR_CPUS=3D1024 NUMA pSeries [ 2221.546398] Modules linked in: btrfs raid6_pq xor lockd sunrpc nf_conntr= ack_netbios_ns nf_conntrack_broadcast ipt_MASQUERADE ip6table_mangle ip6t_R= EJECT nf_conntrack_ipv6 nf_defrag_ipv6 iptable_nat nf_nat_ipv4 nf_nat iptab= le_mangle ipt_REJECT nf_conntrack_ipv4 nf_defrag_ipv4 xt_conntrack nf_connt= rack ebtable_filter ebtables ip6table_filter ip6_tables iptable_filter ip_t= ables sg ibmveth xfs libcrc32c sd_mod crc_t10dif ibmvscsi scsi_transport_sr= p scsi_tgt dm_mirror dm_region_hash dm_log dm_mod [ 2221.546445] NIP: d000000002758bbc LR: d000000002758bbc CTR: 000000000176= 6760 [ 2221.546449] REGS: c00000000a393780 TRAP: 0700 Not tainted (3.9.0-rc2+= ) [ 2221.546452] MSR: 8000000000029032 CR: 286b4b24 XER= : 0000000e [ 2221.546463] SOFTE: 1 [ 2221.546465] CFAR: d00000000275881c [ 2221.546468] TASK =3D c00000000a423dc0[415] 'kworker/16:1H' THREAD: c0000= 0000a390000 CPU: 16 GPR00: d000000002758bbc c00000000a393a00 d00000000282f770 000000000000003d= =20 GPR04: 0000000000000000 0000000000000000 0000000000010000 0000000000000000= =20 GPR08: 0000000000000007 0000000000000000 0000000000000000 0000000000003fef= =20 GPR12: 00000000286b4b22 c00000000f244000 c0000000000b57e0 c0000000fb6dba90= =20 GPR16: 0000000000000000 0000000000000000 c0000000e76614b0 d00000000282f770= =20 GPR20: d00000000282f770 d00000000282f770 d00000000282f770 d00000000282f770= =20 GPR24: d00000000282f770 d000000002743554 0000000000000020 d000000002802988= =20 GPR28: c00000005758e700 c0000000e7661290 0000000000000008 c0000000e7423dc8= =20 [ 2221.546545] NIP [d000000002758bbc] .assfail+0x2c/0x30 [xfs] [ 2221.546564] LR [d000000002758bbc] .assfail+0x2c/0x30 [xfs] [ 2221.546568] Call Trace: [ 2221.546586] [c00000000a393a00] [d000000002758bbc] .assfail+0x2c/0x30 [xf= s] (unreliable) [ 2221.546612] [c00000000a393a70] [d0000000027a8704] .xfs_inode_buf_verify+= 0x134/0x220 [xfs] [ 2221.546632] [c00000000a393b50] [d000000002743554] .xfs_buf_iodone_work+0= x64/0x150 [xfs] [ 2221.546639] [c00000000a393bd0] [c0000000000ad830] .process_one_work+0x1b= 0/0x4c0 [ 2221.546644] [c00000000a393c70] [c0000000000ae078] .worker_thread+0x178/0= x470 [ 2221.546649] [c00000000a393d30] [c0000000000b58c8] .kthread+0xe8/0xf0 [ 2221.546654] [c00000000a393e30] [c000000000009f64] .ret_from_kernel_threa= d+0x64/0x80 [ 2221.546658] Instruction dump: [ 2221.546662] 60000000 7c0802a6 3d420000 7c691b78 7c862378 e88a90f0 7ca72b= 78 38600000=20 [ 2221.546672] 7d254b78 f8010010 f821ff91 4bfffc09 <0fe00000> 7c0802a6 3ce2= 0000 3d420000=20 [ 2221.546685] ---[ end trace fd5756e02a75ba6a ]--- [ 2221.548469]=20 [ 2221.548542] Unable to handle kernel paging request for data at address 0= xffffffffffffffd8 [ 2221.548552] Faulting instruction address: 0xc0000000000b5cc4 [ 2221.548561] Oops: Kernel access of bad area, sig: 11 [#2] [ 2221.548577] SMP NR_CPUS=3D1024 NUMA pSeries [ 2221.548592] Modules linked in: btrfs raid6_pq xor lockd sunrpc nf_conntr= ack_netbios_ns nf_conntrack_broadcast ipt_MASQUERADE ip6table_mangle ip6t_R= EJECT nf_conntrack_ipv6 nf_defrag_ipv6 iptable_nat nf_nat_ipv4 nf_nat iptab= le_mangle ipt_REJECT nf_conntrack_ipv4 nf_defrag_ipv4 xt_conntrack nf_connt= rack ebtable_filter ebtables ip6table_filter ip6_tables iptable_filter ip_t= ables sg ibmveth xfs libcrc32c sd_mod crc_t10dif ibmvscsi scsi_transport_sr= p scsi_tgt dm_mirror dm_region_hash dm_log dm_mod [ 2221.548677] NIP: c0000000000b5cc4 LR: c0000000000aede8 CTR: c0000000000d= 3d80 [ 2221.548685] REGS: c00000000a392e40 TRAP: 0300 Tainted: G D = (3.9.0-rc2+) [ 2221.548692] MSR: 8000000002009032 CR: 426b4b48 = XER: 00000001 [ 2221.548714] SOFTE: 0 [ 2221.548718] CFAR: c000000000005f1c [ 2221.548724] DAR: ffffffffffffffd8, DSISR: 40000000 [ 2221.548732] TASK =3D c00000000a423dc0[415] 'kworker/16:1H' THREAD: c0000= 0000a390000 CPU: 16 GPR00: c000000000738fac c00000000a3930c0 c000000001114018 c00000000a423dc0= =20 GPR04: 0000000000000010 c00000000a423e30 0000000000000000 0000000000000001= =20 GPR08: 0000000000000001 0000000000000000 c000000001352f08 00000000161aad9e= =20 GPR12: 00000000846b4b44 c00000000f244000 c000000001044018 c00000000008d470= =20 GPR16: c000000000b04880 c0000000011b4018 c000000001074018 c000000000b04880= =20 GPR20: c000000000b04880 0000000000c10000 0000000000000010 c000000000b04880= =20 GPR24: c000000000b04880 0000000000000010 c00000000a424200 c00000000a390000= =20 GPR28: c00000000117c9d8 c000000000b04880 c000000001714880 0000000000000010= =20 [ 2221.548853] NIP [c0000000000b5cc4] .kthread_data+0x4/0x10 [ 2221.548862] LR [c0000000000aede8] .wq_worker_sleeping+0x18/0xd0 [ 2221.548868] Call Trace: [ 2221.548874] [c00000000a3930c0] [c0000000007495a4] .__slab_free+0x84/0x31= 0 (unreliable) [ 2221.548883] [c00000000a393140] [c000000000738fac] .__schedule+0x6fc/0x94= 0 [ 2221.548891] [c00000000a3933c0] [c00000000008d470] .do_exit+0x730/0xb40 [ 2221.548899] [c00000000a3934c0] [c00000000001e0d4] .die+0x2e4/0x440 [ 2221.548906] [c00000000a393570] [c00000000001e444] ._exception+0x1a4/0x1d= 0 [ 2221.548913] [c00000000a393710] [c0000000000063c8] program_check_common+0= x148/0x180 [ 2221.548994] --- Exception: 700 at .assfail+0x2c/0x30 [xfs] [ 2221.548994] LR =3D .assfail+0x2c/0x30 [xfs] [ 2221.549043] [c00000000a393a70] [d0000000027a8704] .xfs_inode_buf_verify+= 0x134/0x220 [xfs] [ 2221.549086] [c00000000a393b50] [d000000002743554] .xfs_buf_iodone_work+0= x64/0x150 [xfs] [ 2221.549094] [c00000000a393bd0] [c0000000000ad830] .process_one_work+0x1b= 0/0x4c0 [ 2221.549102] [c00000000a393c70] [c0000000000ae078] .worker_thread+0x178/0= x470 [ 2221.549108] [c00000000a393d30] [c0000000000b58c8] .kthread+0xe8/0xf0 [ 2221.549115] [c00000000a393e30] [c000000000009f64] .ret_from_kernel_threa= d+0x64/0x80 [ 2221.549121] Instruction dump: [ 2221.549125] ebe1fff8 7c0803a6 4bfffdf4 e92d0258 e92903f8 e869ffc8 7863f7= e2 4e800020=20 [ 2221.549138] 60000000 60000000 60000000 e92303f8 4e800020 6000= 0000 e92d0258=20 [ 2221.549151] ---[ end trace fd5756e02a75ba6b ]--- [ 2221.552003]=20 [ 2221.552008] Fixing recursive fault but reboot is needed! [ 2281.608342] INFO: rcu_sched detected stalls on CPUs/tasks: { 16} (detect= ed by 17, t=3D6002 jiffies, g=3D23049, c=3D23048, q=3D135) [ 2281.608362] Task dump for CPU 16: [ 2281.608367] kworker/16:1H D 0000000000000000 0 415 2 0x0000= 0800 [ 2281.608374] Call Trace: [ 2281.608412] [c00000000a393770] [d000000002758bbc] .assfail+0x2c/0x30 [xf= s] (unreliable) [ 2353.528157] sd 0:0:1:0: aborting command. lun 0x8100000000000000, tag 0x= c0000000fc142650 [ 2406.758570] sd 0:0:1:0: aborted task tag 0xc0000000fc142650 completed [ 2461.657815] INFO: rcu_sched detected stalls on CPUs/tasks: { 16} (detect= ed by 18, t=3D24007 jiffies, g=3D23049, c=3D23048, q=3D511) [ 2461.657838] Task dump for CPU 16: [ 2461.657843] kworker/16:1H D 0000000000000000 0 415 2 0x0000= 0800 [ 2461.657851] Call Trace: [ 2461.657900] [c00000000a393770] [d000000002758bbc] .assfail+0x2c/0x30 [xf= s] (unreliable) - x64 trace: [18922.742140] XFS: Assertion failed: XFS_FORCED_SHUTDOWN(ip->i_mount) || i= p->i_delayed_blks =3D=3D 0, file: fs/xfs/xfs_super.c, line: 964 [18922.744338] ------------[ cut here ]------------ [18922.745267] kernel BUG at fs/xfs/xfs_message.c:100! [18922.746294] invalid opcode: 0000 [#1] SMP [18922.747261] Modules linked in: btrfs(F) zlib_deflate(F) raid6_pq(F) xor(= F) lockd(F) sunrpc(F) nf_conntrack_netbios_ns(F) nf_conntrack_broadcast(F) = ipt_MASQUERADE(F) ip6table_mangle(F) ip6t_REJECT(F) nf_conntrack_ipv6(F) nf= _defrag_ipv6(F) iptable_nat(F) nf_nat_ipv4(F) nf_nat(F) iptable_mangle(F) i= pt_REJECT(F) nf_conntrack_ipv4(F) nf_defrag_ipv4(F) xt_conntrack(F) nf_conn= track(F) ebtable_filter(F) ebtables(F) ip6table_filter(F) ip6_tables(F) ipt= able_filter(F) ip_tables(F) sg(F) kvm_amd(F) kvm(F) bnx2(F) pcspkr(F) micro= code(F) shpchp(F) amd64_edac_mod(F) serio_raw(F) ipmi_si(F) edac_mce_amd(F)= hpwdt(F) ipmi_msghandler(F) edac_core(F) k10temp(F) hpilo(F) xfs(F) libcrc= 32c(F) sr_mod(F) cdrom(F) hpsa(F) radeon(F) ata_generic(F) qla2xxx(F) i2c_a= lgo_bit(F) pata_acpi(F) drm_kms_helper(F) scsi_transport_fc(F) ttm(F) scsi_= tgt(F) drm(F) pata_amd(F) cciss(F) libata(F) i2c_core(F) dm_mirror(F) dm_re= gion_hash(F) dm_log(F) dm_mod(F) [18922.764413] CPU 4 [18922.764815] Pid: 23999, comm: umount Tainted: GF 3.9.0-rc2+ #= 1 HP ProLiant DL585 G5 [18922.766619] RIP: 0010:[] [] assfail= +0x22/0x30 [xfs] [18922.768316] RSP: 0018:ffff8801c9575d38 EFLAGS: 00010292 [18922.769482] RAX: 0000000000000077 RBX: ffff88010da1bf08 RCX: ffff88007da= 8ffe8 [18922.770812] RDX: 0000000000000000 RSI: ffff88007da8e3b8 RDI: 00000000000= 00246 [18922.772117] RBP: ffff8801c9575d38 R08: ffffffff81a0f320 R09: 00000000000= 014ce [18922.773429] R10: 0000000000000000 R11: 00000000000014cd R12: ffff88010da= 1bf08 [18922.774715] R13: ffff88010da1bdc0 R14: ffff880073e53ab8 R15: ffff880072b= fef60 [18922.775998] FS: 00007fde048ed880(0000) GS:ffff88007da80000(0000) knlGS:= 0000000000000000 [18922.777433] CS: 0010 DS: 0000 ES: 0000 CR0: 000000008005003b [18922.778446] CR2: 00007fde044c264f CR3: 00000000737c5000 CR4: 00000000000= 007e0 [18922.779730] DR0: 0000000000000000 DR1: 0000000000000000 DR2: 00000000000= 00000 [18922.781019] DR3: 0000000000000000 DR6: 00000000ffff0ff0 DR7: 00000000000= 00400 [18922.782305] Process umount (pid: 23999, threadinfo ffff8801c9574000, tas= k ffff88019a24d040) [18922.783836] Stack: [18922.784236] ffff8801c9575d68 ffffffffa0381664 ffff8801c9575d68 ffff8801= 0da1bf08 [18922.785773] ffff88010da1c008 ffffffffa03f3ca0 ffff8801c9575d88 ffffffff= 811bb37c [18922.787466] ffff88010da1bf08 ffff88010da1bf08 ffff8801c9575db8 ffffffff= 811bb4bf [18922.788982] Call Trace: [18922.789541] [] xfs_fs_destroy_inode+0x84/0x140 [xfs] [18922.790878] [] destroy_inode+0x3c/0x70 [18922.792087] [] evict+0x10f/0x1a0 [18922.792991] [] dispose_list+0x3e/0x60 [18922.793967] [] evict_inodes+0xb8/0x100 [18922.794937] [] generic_shutdown_super+0x53/0xf0 [18922.796064] [] kill_block_super+0x30/0x80 [18922.797091] [] deactivate_locked_super+0x57/0x80 [18922.798198] [] deactivate_super+0x4e/0x70 [18922.799235] [] mntput_no_expire+0xd7/0x130 [18922.800310] [] sys_umount+0x9c/0x3c0 [18922.801273] [] system_call_fastpath+0x16/0x1b [18922.802393] Code: e8 f4 fb ff ff 0f 0b 66 90 66 66 66 66 90 55 48 89 f1 = 41 89 d0 48 c7 c6 b0 e0 3f a0 48 89 fa 31 c0 48 89 e5 31 ff e8 1e fc ff ff = <0f> 0b 66 66 66 2e 0f 1f 84 00 00 00 00 00 66 66 66 66 90 55 48 [18922.806375] RIP [] assfail+0x22/0x30 [xfs] [18922.807459] RSP [18922.824045] ---[ end trace 133202f8e58b0c3c ]--- CAI Qian From qcai@redhat.com Thu Mar 14 03:06:11 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 3A4807F37 for ; Thu, 14 Mar 2013 03:06:11 -0500 (CDT) Received: from cuda.sgi.com (cuda2.sgi.com [192.48.176.25]) by relay2.corp.sgi.com (Postfix) with ESMTP id 1021A304059 for ; Thu, 14 Mar 2013 01:06:07 -0700 (PDT) X-ASG-Debug-ID: 1363248366-04cbb04b86a58f0001-NocioJ Received: from mx3-phx2.redhat.com (mx3-phx2.redhat.com [209.132.183.24]) by cuda.sgi.com with ESMTP id aLphd1tOgruPf82E for ; Thu, 14 Mar 2013 01:06:06 -0700 (PDT) X-Barracuda-Envelope-From: qcai@redhat.com X-Barracuda-Apparent-Source-IP: 209.132.183.24 Received: from zmail14.collab.prod.int.phx2.redhat.com (zmail14.collab.prod.int.phx2.redhat.com [10.5.83.16]) by mx3-phx2.redhat.com (8.13.8/8.13.8) with ESMTP id r2E865WJ008686; Thu, 14 Mar 2013 04:06:05 -0400 Date: Thu, 14 Mar 2013 04:06:04 -0400 (EDT) From: CAI Qian To: Dave Chinner Cc: xfs@oss.sgi.com Message-ID: <5913647.851698.1363248364959.JavaMail.root@redhat.com> In-Reply-To: <740792090.842745.1363246773807.JavaMail.root@redhat.com> Subject: Re: 3.9-rc2 xfs panic MIME-Version: 1.0 X-ASG-Orig-Subj: Re: 3.9-rc2 xfs panic Content-Type: text/plain; charset=utf-8 Content-Transfer-Encoding: 7bit X-Originating-IP: [10.66.13.149] X-Mailer: Zimbra 7.2.0_GA_2669 (ZimbraWebClient - FF3.0 (Linux)/7.2.0_GA_2669) X-Barracuda-Connect: mx3-phx2.redhat.com[209.132.183.24] X-Barracuda-Start-Time: 1363248366 X-Barracuda-URL: http://192.48.176.25:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests= X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125159 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- This is easy to reproduce here, # ./check 111 Bisecting is under way... ----- Original Message ----- > From: "CAI Qian" > To: "Dave Chinner" > Cc: xfs@oss.sgi.com > Sent: Thursday, March 14, 2013 3:39:33 PM > Subject: Re: 3.9-rc2 xfs panic > > OK, this time I reproduced this panic on both x64 and ppc64 > systems with LVM partitions using the default block size as > well as enabling debugging and memory poisoning options. > > - ppc64 trace: > (nothing looks like really interesting prior to this) > [ 2221.546337] XFS (dm-0): Corruption detected. Unmount and run > xfs_repair > [ 2221.546345] XFS (dm-0): bad inode magic/vsn daddr 64 #8 > (magic=5858) > [ 2221.546350] XFS: Assertion failed: 0, file: fs/xfs/xfs_inode.c, > line: 416 > [ 2221.546383] ------------[ cut here ]------------ > [ 2221.546386] kernel BUG at fs/xfs/xfs_message.c:100! > [ 2221.546391] Oops: Exception in kernel mode, sig: 5 [#1] > [ 2221.546394] SMP NR_CPUS=1024 NUMA pSeries > [ 2221.546398] Modules linked in: btrfs raid6_pq xor lockd sunrpc > nf_conntrack_netbios_ns nf_conntrack_broadcast ipt_MASQUERADE > ip6table_mangle ip6t_REJECT nf_conntrack_ipv6 nf_defrag_ipv6 > iptable_nat nf_nat_ipv4 nf_nat iptable_mangle ipt_REJECT > nf_conntrack_ipv4 nf_defrag_ipv4 xt_conntrack nf_conntrack > ebtable_filter ebtables ip6table_filter ip6_tables iptable_filter > ip_tables sg ibmveth xfs libcrc32c sd_mod crc_t10dif ibmvscsi > scsi_transport_srp scsi_tgt dm_mirror dm_region_hash dm_log dm_mod > [ 2221.546445] NIP: d000000002758bbc LR: d000000002758bbc CTR: > 0000000001766760 > [ 2221.546449] REGS: c00000000a393780 TRAP: 0700 Not tainted > (3.9.0-rc2+) > [ 2221.546452] MSR: 8000000000029032 CR: > 286b4b24 XER: 0000000e > [ 2221.546463] SOFTE: 1 > [ 2221.546465] CFAR: d00000000275881c > [ 2221.546468] TASK = c00000000a423dc0[415] 'kworker/16:1H' THREAD: > c00000000a390000 CPU: 16 > GPR00: d000000002758bbc c00000000a393a00 d00000000282f770 > 000000000000003d > GPR04: 0000000000000000 0000000000000000 0000000000010000 > 0000000000000000 > GPR08: 0000000000000007 0000000000000000 0000000000000000 > 0000000000003fef > GPR12: 00000000286b4b22 c00000000f244000 c0000000000b57e0 > c0000000fb6dba90 > GPR16: 0000000000000000 0000000000000000 c0000000e76614b0 > d00000000282f770 > GPR20: d00000000282f770 d00000000282f770 d00000000282f770 > d00000000282f770 > GPR24: d00000000282f770 d000000002743554 0000000000000020 > d000000002802988 > GPR28: c00000005758e700 c0000000e7661290 0000000000000008 > c0000000e7423dc8 > [ 2221.546545] NIP [d000000002758bbc] .assfail+0x2c/0x30 [xfs] > [ 2221.546564] LR [d000000002758bbc] .assfail+0x2c/0x30 [xfs] > [ 2221.546568] Call Trace: > [ 2221.546586] [c00000000a393a00] [d000000002758bbc] > .assfail+0x2c/0x30 [xfs] (unreliable) > [ 2221.546612] [c00000000a393a70] [d0000000027a8704] > .xfs_inode_buf_verify+0x134/0x220 [xfs] > [ 2221.546632] [c00000000a393b50] [d000000002743554] > .xfs_buf_iodone_work+0x64/0x150 [xfs] > [ 2221.546639] [c00000000a393bd0] [c0000000000ad830] > .process_one_work+0x1b0/0x4c0 > [ 2221.546644] [c00000000a393c70] [c0000000000ae078] > .worker_thread+0x178/0x470 > [ 2221.546649] [c00000000a393d30] [c0000000000b58c8] > .kthread+0xe8/0xf0 > [ 2221.546654] [c00000000a393e30] [c000000000009f64] > .ret_from_kernel_thread+0x64/0x80 > [ 2221.546658] Instruction dump: > [ 2221.546662] 60000000 7c0802a6 3d420000 7c691b78 7c862378 e88a90f0 > 7ca72b78 38600000 > [ 2221.546672] 7d254b78 f8010010 f821ff91 4bfffc09 <0fe00000> > 7c0802a6 3ce20000 3d420000 > [ 2221.546685] ---[ end trace fd5756e02a75ba6a ]--- > [ 2221.548469] > [ 2221.548542] Unable to handle kernel paging request for data at > address 0xffffffffffffffd8 > [ 2221.548552] Faulting instruction address: 0xc0000000000b5cc4 > [ 2221.548561] Oops: Kernel access of bad area, sig: 11 [#2] > [ 2221.548577] SMP NR_CPUS=1024 NUMA pSeries > [ 2221.548592] Modules linked in: btrfs raid6_pq xor lockd sunrpc > nf_conntrack_netbios_ns nf_conntrack_broadcast ipt_MASQUERADE > ip6table_mangle ip6t_REJECT nf_conntrack_ipv6 nf_defrag_ipv6 > iptable_nat nf_nat_ipv4 nf_nat iptable_mangle ipt_REJECT > nf_conntrack_ipv4 nf_defrag_ipv4 xt_conntrack nf_conntrack > ebtable_filter ebtables ip6table_filter ip6_tables iptable_filter > ip_tables sg ibmveth xfs libcrc32c sd_mod crc_t10dif ibmvscsi > scsi_transport_srp scsi_tgt dm_mirror dm_region_hash dm_log dm_mod > [ 2221.548677] NIP: c0000000000b5cc4 LR: c0000000000aede8 CTR: > c0000000000d3d80 > [ 2221.548685] REGS: c00000000a392e40 TRAP: 0300 Tainted: G D > (3.9.0-rc2+) > [ 2221.548692] MSR: 8000000002009032 CR: > 426b4b48 XER: 00000001 > [ 2221.548714] SOFTE: 0 > [ 2221.548718] CFAR: c000000000005f1c > [ 2221.548724] DAR: ffffffffffffffd8, DSISR: 40000000 > [ 2221.548732] TASK = c00000000a423dc0[415] 'kworker/16:1H' THREAD: > c00000000a390000 CPU: 16 > GPR00: c000000000738fac c00000000a3930c0 c000000001114018 > c00000000a423dc0 > GPR04: 0000000000000010 c00000000a423e30 0000000000000000 > 0000000000000001 > GPR08: 0000000000000001 0000000000000000 c000000001352f08 > 00000000161aad9e > GPR12: 00000000846b4b44 c00000000f244000 c000000001044018 > c00000000008d470 > GPR16: c000000000b04880 c0000000011b4018 c000000001074018 > c000000000b04880 > GPR20: c000000000b04880 0000000000c10000 0000000000000010 > c000000000b04880 > GPR24: c000000000b04880 0000000000000010 c00000000a424200 > c00000000a390000 > GPR28: c00000000117c9d8 c000000000b04880 c000000001714880 > 0000000000000010 > [ 2221.548853] NIP [c0000000000b5cc4] .kthread_data+0x4/0x10 > [ 2221.548862] LR [c0000000000aede8] .wq_worker_sleeping+0x18/0xd0 > [ 2221.548868] Call Trace: > [ 2221.548874] [c00000000a3930c0] [c0000000007495a4] > .__slab_free+0x84/0x310 (unreliable) > [ 2221.548883] [c00000000a393140] [c000000000738fac] > .__schedule+0x6fc/0x940 > [ 2221.548891] [c00000000a3933c0] [c00000000008d470] > .do_exit+0x730/0xb40 > [ 2221.548899] [c00000000a3934c0] [c00000000001e0d4] .die+0x2e4/0x440 > [ 2221.548906] [c00000000a393570] [c00000000001e444] > ._exception+0x1a4/0x1d0 > [ 2221.548913] [c00000000a393710] [c0000000000063c8] > program_check_common+0x148/0x180 > [ 2221.548994] --- Exception: 700 at .assfail+0x2c/0x30 [xfs] > [ 2221.548994] LR = .assfail+0x2c/0x30 [xfs] > [ 2221.549043] [c00000000a393a70] [d0000000027a8704] > .xfs_inode_buf_verify+0x134/0x220 [xfs] > [ 2221.549086] [c00000000a393b50] [d000000002743554] > .xfs_buf_iodone_work+0x64/0x150 [xfs] > [ 2221.549094] [c00000000a393bd0] [c0000000000ad830] > .process_one_work+0x1b0/0x4c0 > [ 2221.549102] [c00000000a393c70] [c0000000000ae078] > .worker_thread+0x178/0x470 > [ 2221.549108] [c00000000a393d30] [c0000000000b58c8] > .kthread+0xe8/0xf0 > [ 2221.549115] [c00000000a393e30] [c000000000009f64] > .ret_from_kernel_thread+0x64/0x80 > [ 2221.549121] Instruction dump: > [ 2221.549125] ebe1fff8 7c0803a6 4bfffdf4 e92d0258 e92903f8 e869ffc8 > 7863f7e2 4e800020 > [ 2221.549138] 60000000 60000000 60000000 e92303f8 > 4e800020 60000000 e92d0258 > [ 2221.549151] ---[ end trace fd5756e02a75ba6b ]--- > [ 2221.552003] > [ 2221.552008] Fixing recursive fault but reboot is needed! > [ 2281.608342] INFO: rcu_sched detected stalls on CPUs/tasks: { 16} > (detected by 17, t=6002 jiffies, g=23049, c=23048, q=135) > [ 2281.608362] Task dump for CPU 16: > [ 2281.608367] kworker/16:1H D 0000000000000000 0 415 2 > 0x00000800 > [ 2281.608374] Call Trace: > [ 2281.608412] [c00000000a393770] [d000000002758bbc] > .assfail+0x2c/0x30 [xfs] (unreliable) > [ 2353.528157] sd 0:0:1:0: aborting command. lun 0x8100000000000000, > tag 0xc0000000fc142650 > [ 2406.758570] sd 0:0:1:0: aborted task tag 0xc0000000fc142650 > completed > [ 2461.657815] INFO: rcu_sched detected stalls on CPUs/tasks: { 16} > (detected by 18, t=24007 jiffies, g=23049, c=23048, q=511) > [ 2461.657838] Task dump for CPU 16: > [ 2461.657843] kworker/16:1H D 0000000000000000 0 415 2 > 0x00000800 > [ 2461.657851] Call Trace: > [ 2461.657900] [c00000000a393770] [d000000002758bbc] > .assfail+0x2c/0x30 [xfs] (unreliable) > > - x64 trace: > [18922.742140] XFS: Assertion failed: > XFS_FORCED_SHUTDOWN(ip->i_mount) || ip->i_delayed_blks == 0, file: > fs/xfs/xfs_super.c, line: 964 > [18922.744338] ------------[ cut here ]------------ > [18922.745267] kernel BUG at fs/xfs/xfs_message.c:100! > [18922.746294] invalid opcode: 0000 [#1] SMP > [18922.747261] Modules linked in: btrfs(F) zlib_deflate(F) > raid6_pq(F) xor(F) lockd(F) sunrpc(F) nf_conntrack_netbios_ns(F) > nf_conntrack_broadcast(F) ipt_MASQUERADE(F) ip6table_mangle(F) > ip6t_REJECT(F) nf_conntrack_ipv6(F) nf_defrag_ipv6(F) iptable_nat(F) > nf_nat_ipv4(F) nf_nat(F) iptable_mangle(F) ipt_REJECT(F) > nf_conntrack_ipv4(F) nf_defrag_ipv4(F) xt_conntrack(F) > nf_conntrack(F) ebtable_filter(F) ebtables(F) ip6table_filter(F) > ip6_tables(F) iptable_filter(F) ip_tables(F) sg(F) kvm_amd(F) kvm(F) > bnx2(F) pcspkr(F) microcode(F) shpchp(F) amd64_edac_mod(F) > serio_raw(F) ipmi_si(F) edac_mce_amd(F) hpwdt(F) ipmi_msghandler(F) > edac_core(F) k10temp(F) hpilo(F) xfs(F) libcrc32c(F) sr_mod(F) > cdrom(F) hpsa(F) radeon(F) ata_generic(F) qla2xxx(F) i2c_algo_bit(F) > pata_acpi(F) drm_kms_helper(F) scsi_transport_fc(F) ttm(F) > scsi_tgt(F) drm(F) pata_amd(F) cciss(F) libata(F) i2c_core(F) > dm_mirror(F) dm_region_hash(F) dm_log(F) dm_mod(F) > [18922.764413] CPU 4 > [18922.764815] Pid: 23999, comm: umount Tainted: GF > 3.9.0-rc2+ #1 HP ProLiant DL585 G5 > [18922.766619] RIP: 0010:[] [] > assfail+0x22/0x30 [xfs] > [18922.768316] RSP: 0018:ffff8801c9575d38 EFLAGS: 00010292 > [18922.769482] RAX: 0000000000000077 RBX: ffff88010da1bf08 RCX: > ffff88007da8ffe8 > [18922.770812] RDX: 0000000000000000 RSI: ffff88007da8e3b8 RDI: > 0000000000000246 > [18922.772117] RBP: ffff8801c9575d38 R08: ffffffff81a0f320 R09: > 00000000000014ce > [18922.773429] R10: 0000000000000000 R11: 00000000000014cd R12: > ffff88010da1bf08 > [18922.774715] R13: ffff88010da1bdc0 R14: ffff880073e53ab8 R15: > ffff880072bfef60 > [18922.775998] FS: 00007fde048ed880(0000) GS:ffff88007da80000(0000) > knlGS:0000000000000000 > [18922.777433] CS: 0010 DS: 0000 ES: 0000 CR0: 000000008005003b > [18922.778446] CR2: 00007fde044c264f CR3: 00000000737c5000 CR4: > 00000000000007e0 > [18922.779730] DR0: 0000000000000000 DR1: 0000000000000000 DR2: > 0000000000000000 > [18922.781019] DR3: 0000000000000000 DR6: 00000000ffff0ff0 DR7: > 0000000000000400 > [18922.782305] Process umount (pid: 23999, threadinfo > ffff8801c9574000, task ffff88019a24d040) > [18922.783836] Stack: > [18922.784236] ffff8801c9575d68 ffffffffa0381664 ffff8801c9575d68 > ffff88010da1bf08 > [18922.785773] ffff88010da1c008 ffffffffa03f3ca0 ffff8801c9575d88 > ffffffff811bb37c > [18922.787466] ffff88010da1bf08 ffff88010da1bf08 ffff8801c9575db8 > ffffffff811bb4bf > [18922.788982] Call Trace: > [18922.789541] [] xfs_fs_destroy_inode+0x84/0x140 > [xfs] > [18922.790878] [] destroy_inode+0x3c/0x70 > [18922.792087] [] evict+0x10f/0x1a0 > [18922.792991] [] dispose_list+0x3e/0x60 > [18922.793967] [] evict_inodes+0xb8/0x100 > [18922.794937] [] generic_shutdown_super+0x53/0xf0 > [18922.796064] [] kill_block_super+0x30/0x80 > [18922.797091] [] > deactivate_locked_super+0x57/0x80 > [18922.798198] [] deactivate_super+0x4e/0x70 > [18922.799235] [] mntput_no_expire+0xd7/0x130 > [18922.800310] [] sys_umount+0x9c/0x3c0 > [18922.801273] [] system_call_fastpath+0x16/0x1b > [18922.802393] Code: e8 f4 fb ff ff 0f 0b 66 90 66 66 66 66 90 55 48 > 89 f1 41 89 d0 48 c7 c6 b0 e0 3f a0 48 89 fa 31 c0 48 89 e5 31 ff e8 > 1e fc ff ff <0f> 0b 66 66 66 2e 0f 1f 84 00 00 00 00 00 66 66 66 66 > 90 55 48 > [18922.806375] RIP [] assfail+0x22/0x30 [xfs] > [18922.807459] RSP > [18922.824045] ---[ end trace 133202f8e58b0c3c ]--- > > CAI Qian From olesya914@procept.com Thu Mar 14 06:05:21 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=HTML_MESSAGE autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 0A89C7F37 for ; Thu, 14 Mar 2013 06:05:21 -0500 (CDT) Received: from cuda.sgi.com (cuda3.sgi.com [192.48.176.15]) by relay3.corp.sgi.com (Postfix) with ESMTP id 7D459AC005 for ; Thu, 14 Mar 2013 04:05:20 -0700 (PDT) X-ASG-Debug-ID: 1363259113-04cb6c4a43c28a0001-NocioJ Received: from mail1.ihc.ru (mail1.ihc.ru [91.218.228.11]) by cuda.sgi.com with ESMTP id JPL2W2s74G2Ukgg9 (version=TLSv1 cipher=AES256-SHA bits=256 verify=NO) for ; Thu, 14 Mar 2013 04:05:15 -0700 (PDT) X-Barracuda-Envelope-From: olesya914@procept.com X-Barracuda-Apparent-Source-IP: 91.218.228.11 Received: from localhost (localhost.localdomain [127.0.0.1]) by mail1.ihc.ru (Postfix) with ESMTP id 5E28813A4194; Thu, 14 Mar 2013 15:05:13 +0400 (MSK) Received: from mail1.ihc.ru ([127.0.0.1]) by localhost (mail1.ihc.ru [127.0.0.1]) (amavisd-new, port 10024) with ESMTP id 2SC9vhL3lJ5t; Thu, 14 Mar 2013 15:05:02 +0400 (MSK) Received: from Unknown (unknown [218.59.133.103]) by mail1.ihc.ru (Postfix) with ESMTPA; Thu, 14 Mar 2013 15:05:00 +0400 (MSK) Message-ID: <192713A822C24CFE854C70B2A65C3027@pxadqb> Reply-To: =?windows-1251?B?yu7t8vDu6+jw8/756OUg7vDj4O37?= <65846542@qip.ru> From: =?windows-1251?B?yu7t8vDu6+jw8/756OUg7vDj4O37?= To: , , , , Subject: =?windows-1251?B?7urg5+Dt6OUg8/Hr8+Mg5Ov/IOPu8fPk4PDx?= =?windows-1251?B?8uLl7e379SDt8+bkIMvl7ejt4/Dg5PHq7ukg?= =?windows-1251?B?7uHr4PHy6A==?= Date: Thu, 14 Mar 2013 04:05:01 -0700 X-ASG-Orig-Subj: =?windows-1251?B?7urg5+Dt6OUg8/Hr8+Mg5Ov/IOPu8fPk4PDx?= =?windows-1251?B?8uLl7e379SDt8+bkIMvl7ejt4/Dg5PHq7ukg?= =?windows-1251?B?7uHr4PHy6A==?= MIME-Version: 1.0 Content-Type: multipart/alternative; boundary="----=_NextPart_000_1B4F_01CE2069.19DF69D0" X-Priority: 3 X-MSMail-Priority: Normal X-Mailer: Microsoft Windows Mail 6.0.6001.18416 X-MimeOLE: Produced By Microsoft MimeOLE V6.0.6001.18645 X-Barracuda-Connect: mail1.ihc.ru[91.218.228.11] X-Barracuda-Start-Time: 1363259114 X-Barracuda-Encrypted: AES256-SHA X-Barracuda-URL: http://192.48.176.15:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 X-Barracuda-Spam-Score: 0.00 X-Barracuda-Spam-Status: No, SCORE=0.00 using per-user scores of TAG_LEVEL=1000.0 QUARANTINE_LEVEL=1000.0 KILL_LEVEL=2.7 tests=BSF_SC0_TG035a, HTML_MESSAGE X-Barracuda-Spam-Report: Code version 3.2, rules version 3.2.2.125171 Rule breakdown below pts rule name description ---- ---------------------- -------------------------------------------------- 0.00 HTML_MESSAGE BODY: HTML included in message 0.00 BSF_SC0_TG035a Message contains invalid style definition This is a multi-part message in MIME format. ------=_NextPart_000_1B4F_01CE2069.19DF69D0 Content-Type: text/plain; charset="windows-1251" Content-Transfer-Encoding: quoted-printable ol.O=D7-=EE2.o=D7.2O1=C7 =E3., =D1=C0=CD=CA=D2-=CF=C5=D2=C5=D0=C1=D3=D0=C3 =C3=CE=D1=D3=C4=C0=D0=D1=D2=C2=C5=CD=CD=DB=C9 =C8 =CC=D3=CD=C8=D6=C8=CF=C0= =CB=DC=CD=DB=C9 =C7=C0=CA=C0=C7 - =D0=C5=D4=CE=D0=CC=C8=D0=CE=C2=C0=CD=C8= =C5 =D1=C8=D1=D2=C5=CC=DB.=20 =CD=CE=C2=CE=C5 =C2 =CF=D0=C0=C2=CE=C2=CE=CC =CC=C5=D5=C0=CD=C8=C7=CC=C5= =C7=C0=CA=D3=CF=CE=CA =D2=CE=C2=C0=D0=CE=C2 =C8 =D3=D1=CB=D3=C3 =C4=CB=DF= =C3=CE=D1=D3=C4=C0=D0=D1=D2=C2=C5=CD=CD=DB=D5 =C8 =CC=D3=CD=C8=D6=C8=CF=C0= =CB=DC=CD=DB=D5 =CD=D3=C6=C4.=20 =DD=CB=C5=CA=D2=D0=CE=CD=CD=DB=C5 =D2=CE=D0=C3=C8 (=E0=F3=EA=F6=E8=EE=ED= ). =D2=C5=CC=DB =CC=C5=D0=CE=CF=D0=C8=DF=D2=C8=DF: 1. =C7=E0=EA=EE=ED =D0=D4 9=D7-=D4=C7 =AB=CE =F0=E0=E7=EC=E5=F9=E5=ED=E8=E8= =E7=E0=EA=E0=E7=EE=E2 =ED=E0 =EF=EE=F1=F2=E0=E2=EA=E8 =F2=EE=E2=E0=F0=EE= =E2, =E2=FB=EF=EE=EB=ED=E5=ED=E8=E5 =F0=E0=E1=EE=F2. 2. =CD=EE=E2=E0=FF =F0=E5=E4=E0=EA=F6=E8=FF =E7=E0=EA=EE=ED=E0 =B9 218-=D4= =C7 (=E2=F1=F2=F3=EF=E8=E2=F8=E0=FF =E2 =F1=E8=EB=F3 =F1 o1.IO.=EE7). =20 3. =CF=EE=F0=FF=E4=EE=EA =F0=E0=E7=EC=E5=F9=E5=ED=E8=FF =E3=EE=F1=F3=E4=E0= =F0=F1=F2=E2=E5=ED=ED=EE=E3=EE =E8 =EC=F3=ED=E8=F6=E8=EF=E0=EB=FC=ED=EE=E3= =EE =E7=E0=EA=E0=E7=E0. =20 4. =CE=F1=EE=E1=E5=ED=ED=EE=F1=F2=E8 =EF=F0=EE=E2=E5=E4=E5=ED=E8=FF =E0=F3= =EA=F6=E8=EE=ED=EE=E2, =F2=E8=EF=E8=F7=ED=FB=E5 =EE=F8=E8=E1=EA=E8 =EF=F0= =E8 =EF=F0=EE=E2=E5=E4=E5=ED=E8=E8 =E0=F3=EA=F6=E8=EE=ED=EE=E2.=20 5. =C7=E0=EF=F0=EE=F1=FB =EA=EE=F2=E8=F0=EE=E2=EE=EA. =CD=EE=E2=FB=E5 =E0= =F1=EF=E5=EA=F2=FB =EE=F0=E3=E0=ED=E8=E7=E0=F6=E8=E8 =E8 =EF=F0=EE=E2=E5= =E4=E5=ED=E8=FF.=20 6. =D0=E0=E7=EC=E5=F9=E5=ED=E8=E5 =E3=EE=F1=F3=E4=E0=F0=F1=F2=E2=E5=ED=ED= =FB=F5 =E8 =EC=F3=ED=E8=F6=E8=EF=E0=EB=FC=ED=FB=F5 =E7=E0=EA=E0=E7=EE=E2 = =E1=E5=E7 =EF=F0=EE=E2=E5=E4=E5=ED=E8=FF =F2=EE=F0=E3=EE=E2.=20 7. =D0=E5=E5=F1=F2=F0=FB =EA=EE=ED=F2=F0=E0=EA=F2=EE=E2 =E8 =ED=E5=E4= =EE=E1=F0=EE=F1=EE=E2=E5=F1=F2=ED=FB=F5 =EF=EE=F1=F2=E0=E2=F9=E8=EA=EE=E2= .=20 8. =CA=EE=ED=F2=F0=EE=EB=FC =D4=C0=D1 =D0=D4 =E2 =EE=E1=EB=E0=F1=F2=E8 =E3= =EE=F1=F3=E4=E0=F0=F1=F2=E2=E5=ED=ED=EE=E3=EE =E8 =EC=F3=ED=E8=F6=E8=EF=E0= =EB=FC=ED=EE=E3=EE =E7=E0=EA=E0=E7=E0. 9. =C0=EA=F2=F3=E0=EB=FC=ED=FB=E5 =E2=EE=EF=F0=EE=F1=FB =E7=E0=EA=EB= =FE=F7=E5=ED=E8=FF =E3=EE=F1=F3=E4=E0=F0=F1=F2=E2=E5=ED=ED=FB=F5 =E8 =EC=F3= =ED=E8=F6=E8=EF=E0=EB=FC=ED=FB=F5 =EA=EE=ED=F2=F0=E0=EA=F2=EE=E2. =CC=ED=EE= =E3=EE=EB=E5=F2=ED=E8=E5, =EF=E5=F0=E5=F5=EE=E4=FF=F9=E8=E5 =EA=EE=ED=F2=F0= =E0=EA=F2=FB.=20 10. =C2=EE=EF=F0=EE=F1=FB =F4=EE=F0=EC=E8=F0=EE=E2=E0=ED=E8=FF =F6=E5=ED=FB= =EA=EE=ED=F2=F0=E0=EA=F2=E0, =EF=F0=E0=E2=E8=EB=FC=ED=EE=E3=EE =F4=EE=F0= =EC=E8=F0=EE=E2=E0=ED=E8=FF =F3=F1=EB=EE=E2=E8=E9 =F2=E5=F5=ED=E8=F7=E5=F1= =EA=EE=E3=EE =E7=E0=E4=E0=ED=E8=FF. 11. =CF=EE=F0=FF=E4=EE=EA =F1=EE=F1=F2=E0=E2=EB=E5=ED=E8=FF =E8 =F0=E0= =F1=F1=EC=EE=F2=F0=E5=ED=E8=FF =E6=E0=EB=EE=E1 =E8 =E8=F1=EA=EE=E2=FB=F5 = =F2=F0=E5=E1=EE=E2=E0=ED=E8=E9 =F3=F7=E0=F1=F2=ED=E8=EA=EE=E2 =F0=E0=E7=EC= =E5=F9=E5=ED=E8=FF =E7=E0=EA=E0=E7=EE=E2=20 12. =DD=EB=E5=EA=F2=F0=EE=ED=ED=FB=E9 =E0=F3=EA=F6=E8=EE=ED - =F7=F2=EE= =ED=F3=E6=ED=EE =E7=ED=E0=F2=FC =D3=F7=E0=F1=F2=ED=E8=EA=F3, =F7=F2=EE=E1= =FB =EF=F0=E8=ED=FF=F2=FC =F3=F7=E0=F1=F2=E8=E5 =E2 =FD=EB=E5=EA=F2=F0=EE= =ED=ED=EE=EC =E0=F3=EA=F6=E8=EE=ED=E5:=20 =F1=EE=EE=F2=E2=E5=F2=F1=F2=E2=F3=FE=F9=E5=E5 =EF=F0=EE=E3=F0=E0=EC=EC=ED= =EE=E5 =EE=E1=E5=F1=EF=E5=F7=E5=ED=E8=E5, =DD=D6=CF =E8 =EF=EE=F0=FF=E4=EE= =EA =E5=E5 =F0=E5=E3=E8=F1=F2=F0=E0=F6=E8=E8.=20 =AB=CE=F2=F0=E8=F6=E0=F2=E5=EB=FC=ED=FB=E9 =FD=EB=E5=EA=F2=F0=EE=ED=ED=FB= =E9 =E0=F3=EA=F6=E8=EE=ED=BB, =EF=F0=E0=E2=EE=E2=FB=E5 =EF=EE=F1=EB=E5=E4= =F1=F2=E2=E8=FF =E5=E3=EE =EF=F0=EE=E2=E5=E4=E5=ED=E8=FF.=20 =CA=E0=EA=E8=E5 =E4=EE=EA=F3=EC=E5=ED=F2=FB =ED=F3=E6=ED=EE =EF=F0=E5=E4=EE= =F1=F2=E0=E2=E8=F2=FC =E4=EB=FF =EF=F0=EE=F5=EE=E6=E4=E5=ED=E8=FF =E0=EA=EA= =F0=E5=E4=E8=F2=E0=F6=E8=E8 =ED=E0 =F2=EE=F0=E3=EE=E2=EE=E9 =EF=EB=EE=F9=E0= =E4=EA=E5?=20 =CE=E1=E5=F1=EF=E5=F7=E5=ED=E8=E5 =E7=E0=FF=E2=EE=EA =ED=E0 =F3=F7=E0=F1=F2= =E8=E5 =E2 =E0=F3=EA=F6=E8=EE=ED=E5 =E2 =FD=EB=E5=EA=F2=F0=EE=ED=ED=EE=E9= =F4=EE=F0=EC=E5: =EA=E0=EA =E8 =EA=EE=EC=F3 =EF=F0=E5=E4=EE=F1=F2=E0=E2=EB= =FF=E5=F2=F1=FF.=20 =D3=F1=EB=EE=E2=E8=FF =F3=E4=E5=F0=E6=E0=ED=E8=FF =EE=E1=E5=F1=EF=E5=F7=E5= =ED=E8=FF.=20 =CD=C0 =C2=D1=C5 =C8=CD=D2=C5=D0=C5=D1=D3=DE=D9=C8=C5 =C2=CE=CF=D0=CE=D1= =DB =C2=C0=CC =CE=D2=C2=C5=D2=C8=D2 =CD=C0=D8 =D1=C5=CA=D0=C5=D2=C0=D0=DC= : 8 ( =CF=E8=F2=E5=F0 ) 98.6 ^ 9=D7 _ 1 I= =20 ------=_NextPart_000_1B4F_01CE2069.19DF69D0 Content-Type: text/html; charset="windows-1251" Content-Transfer-Encoding: quoted-printable
 ol.O=D7-=EE2.o=D7.2O1=C7=20 =E3., =D1=C0=CD=CA=D2-=CF=C5=D2=C5=D0=C1=D3=D0=C3
 
 =C3=CE=D1=D3=C4=C0=D0=D1=D2=C2=C5=CD=CD=DB=C9 =C8= =CC=D3=CD=C8=D6=C8=CF=C0=CB=DC=CD=DB=C9 =C7=C0=CA=C0=C7 - =D0=C5=D4=CE=D0= =CC=C8=D0=CE=C2=C0=CD=C8=C5=20 =D1=C8=D1=D2=C5=CC=DB.
 =CD=CE=C2=CE=C5 =C2 =CF=D0=C0=C2=CE=C2=CE= =CC =CC=C5=D5=C0=CD=C8=C7=CC=C5 =C7=C0=CA=D3=CF=CE=CA =D2=CE=C2=C0=D0=CE=C2= =C8 =D3=D1=CB=D3=C3 =C4=CB=DF=20 =C3=CE=D1=D3=C4=C0=D0=D1=D2=C2=C5=CD=CD=DB=D5 =C8 =CC=D3=CD=C8=D6=C8=CF=C0= =CB=DC=CD=DB=D5 =CD=D3=C6=C4.
 =DD=CB=C5=CA=D2=D0=CE=CD=CD=DB=C5= =D2=CE=D0=C3=C8=20 (=E0=F3=EA=F6=E8=EE=ED).
 
=D2=C5=CC=DB =CC=C5=D0=CE=CF=D0=C8=DF=D2=C8=DF:
1.&n= bsp;=C7=E0=EA=EE=ED =D0=D4 9=D7-=D4=C7 =AB=CE=20 =F0=E0=E7=EC=E5=F9=E5=ED=E8=E8 =E7=E0=EA=E0=E7=EE=E2 =ED=E0 =EF=EE=F1=F2=E0= =E2=EA=E8 =F2=EE=E2=E0=F0=EE=E2, =E2=FB=EF=EE=EB=ED=E5=ED=E8=E5 =F0=E0=E1= =EE=F2.
2. =CD=EE=E2=E0=FF=20 =F0=E5=E4=E0=EA=F6=E8=FF =E7=E0=EA=EE=ED=E0  =B9 218-=D4=C7 (=E2=F1=F2= =F3=EF=E8=E2=F8=E0=FF =E2 =F1=E8=EB=F3 =F1=20 o1.IO.=EE7). =20
3. =CF=EE=F0=FF=E4=EE=EA =F0=E0=E7=EC=E5=F9=E5=ED=E8=FF =E3=EE=F1= =F3=E4=E0=F0=F1=F2=E2=E5=ED=ED=EE=E3=EE =E8 =EC=F3=ED=E8=F6=E8=EF=E0=EB=FC= =ED=EE=E3=EE =E7=E0=EA=E0=E7=E0. =20
4. =CE=F1=EE=E1=E5=ED=ED=EE=F1=F2=E8 =EF=F0=EE=E2=E5=E4=E5=ED=E8= =FF =E0=F3=EA=F6=E8=EE=ED=EE=E2, =F2=E8=EF=E8=F7=ED=FB=E5 =EE=F8=E8=E1=EA= =E8 =EF=F0=E8 =EF=F0=EE=E2=E5=E4=E5=ED=E8=E8=20 =E0=F3=EA=F6=E8=EE=ED=EE=E2.
5. =C7=E0=EF=F0=EE=F1=FB =EA=EE=F2=E8= =F0=EE=E2=EE=EA. =CD=EE=E2=FB=E5 =E0=F1=EF=E5=EA=F2=FB  =EE=F0=E3=E0= =ED=E8=E7=E0=F6=E8=E8 =E8=20 =EF=F0=EE=E2=E5=E4=E5=ED=E8=FF.
6. =D0=E0=E7=EC=E5=F9=E5=ED=E8=E5= =E3=EE=F1=F3=E4=E0=F0=F1=F2=E2=E5=ED=ED=FB=F5 =E8 =EC=F3=ED=E8=F6=E8=EF=E0= =EB=FC=ED=FB=F5 =E7=E0=EA=E0=E7=EE=E2 =E1=E5=E7=20 =EF=F0=EE=E2=E5=E4=E5=ED=E8=FF =F2=EE=F0=E3=EE=E2.
7.  &nbs= p;   =D0=E5=E5=F1=F2=F0=FB =EA=EE=ED=F2=F0=E0=EA=F2=EE=E2 =E8=20 =ED=E5=E4=EE=E1=F0=EE=F1=EE=E2=E5=F1=F2=ED=FB=F5 =EF=EE=F1=F2=E0=E2=F9=E8= =EA=EE=E2.
8. =CA=EE=ED=F2=F0=EE=EB=FC =D4=C0=D1 =D0=D4 =E2 =EE=E1= =EB=E0=F1=F2=E8=20 =E3=EE=F1=F3=E4=E0=F0=F1=F2=E2=E5=ED=ED=EE=E3=EE =E8 =EC=F3=ED=E8=F6=E8=EF= =E0=EB=FC=ED=EE=E3=EE =E7=E0=EA=E0=E7=E0.
9.    &n= bsp;=20 =C0=EA=F2=F3=E0=EB=FC=ED=FB=E5 =E2=EE=EF=F0=EE=F1=FB =E7=E0=EA=EB=FE=F7=E5= =ED=E8=FF =E3=EE=F1=F3=E4=E0=F0=F1=F2=E2=E5=ED=ED=FB=F5 =E8 =EC=F3=ED=E8=F6= =E8=EF=E0=EB=FC=ED=FB=F5 =EA=EE=ED=F2=F0=E0=EA=F2=EE=E2.=20 =CC=ED=EE=E3=EE=EB=E5=F2=ED=E8=E5, =EF=E5=F0=E5=F5=EE=E4=FF=F9=E8=E5 =EA=EE= =ED=F2=F0=E0=EA=F2=FB.
10. =C2=EE=EF=F0=EE=F1=FB =F4=EE=F0=EC=E8= =F0=EE=E2=E0=ED=E8=FF =F6=E5=ED=FB=20 =EA=EE=ED=F2=F0=E0=EA=F2=E0, =EF=F0=E0=E2=E8=EB=FC=ED=EE=E3=EE =F4=EE=F0=EC= =E8=F0=EE=E2=E0=ED=E8=FF =F3=F1=EB=EE=E2=E8=E9 =F2=E5=F5=ED=E8=F7=E5=F1=EA= =EE=E3=EE=20 =E7=E0=E4=E0=ED=E8=FF.
11.     =CF=EE=F0=FF=E4=EE=EA= =F1=EE=F1=F2=E0=E2=EB=E5=ED=E8=FF =E8 =F0=E0=F1=F1=EC=EE=F2=F0=E5=ED=E8=FF= =E6=E0=EB=EE=E1=20 =E8 =E8=F1=EA=EE=E2=FB=F5 =F2=F0=E5=E1=EE=E2=E0=ED=E8=E9 =F3=F7=E0=F1=F2=ED= =E8=EA=EE=E2 =F0=E0=E7=EC=E5=F9=E5=ED=E8=FF =E7=E0=EA=E0=E7=EE=E2=20
12.     =DD=EB=E5=EA=F2=F0=EE=ED=ED=FB=E9 =E0=F3=EA= =F6=E8=EE=ED - =F7=F2=EE =ED=F3=E6=ED=EE =E7=ED=E0=F2=FC =D3=F7=E0=F1=F2=ED= =E8=EA=F3,=20 =F7=F2=EE=E1=FB =EF=F0=E8=ED=FF=F2=FC =F3=F7=E0=F1=F2=E8=E5 =E2 =FD=EB=E5= =EA=F2=F0=EE=ED=ED=EE=EC =E0=F3=EA=F6=E8=EE=ED=E5:
=F1=EE=EE=F2=E2=E5= =F2=F1=F2=E2=F3=FE=F9=E5=E5 =EF=F0=EE=E3=F0=E0=EC=EC=ED=EE=E5=20 =EE=E1=E5=F1=EF=E5=F7=E5=ED=E8=E5, =DD=D6=CF =E8 =EF=EE=F0=FF=E4=EE=EA =E5= =E5 =F0=E5=E3=E8=F1=F2=F0=E0=F6=E8=E8.
=AB=CE=F2=F0=E8=F6=E0=F2=E5=EB= =FC=ED=FB=E9 =FD=EB=E5=EA=F2=F0=EE=ED=ED=FB=E9=20 =E0=F3=EA=F6=E8=EE=ED=BB, =EF=F0=E0=E2=EE=E2=FB=E5 =EF=EE=F1=EB=E5=E4=F1=F2= =E2=E8=FF =E5=E3=EE =EF=F0=EE=E2=E5=E4=E5=ED=E8=FF.
=CA=E0=EA=E8=E5 =E4= =EE=EA=F3=EC=E5=ED=F2=FB =ED=F3=E6=ED=EE=20 =EF=F0=E5=E4=EE=F1=F2=E0=E2=E8=F2=FC =E4=EB=FF =EF=F0=EE=F5=EE=E6=E4=E5=ED= =E8=FF =E0=EA=EA=F0=E5=E4=E8=F2=E0=F6=E8=E8 =ED=E0 =F2=EE=F0=E3=EE=E2=EE=E9= =EF=EB=EE=F9=E0=E4=EA=E5?
=CE=E1=E5=F1=EF=E5=F7=E5=ED=E8=E5=20 =E7=E0=FF=E2=EE=EA =ED=E0 =F3=F7=E0=F1=F2=E8=E5 =E2 =E0=F3=EA=F6=E8=EE=ED= =E5 =E2 =FD=EB=E5=EA=F2=F0=EE=ED=ED=EE=E9 =F4=EE=F0=EC=E5: =EA=E0=EA =E8 = =EA=EE=EC=F3 =EF=F0=E5=E4=EE=F1=F2=E0=E2=EB=FF=E5=F2=F1=FF.=20
=D3=F1=EB=EE=E2=E8=FF =F3=E4=E5=F0=E6=E0=ED=E8=FF =EE=E1=E5=F1=EF=E5=F7= =E5=ED=E8=FF.
 
 =CD=C0 =C2=D1=C5 =C8=CD=D2=C5=D0=C5=D1=D3=DE=D9=C8= =C5 =C2=CE=CF=D0=CE=D1=DB =C2=C0=CC =CE=D2=C2=C5=D2=C8=D2 =CD=C0=D8=20 =D1=C5=CA=D0=C5=D2=C0=D0=DC:
 
8 ( =CF=E8=F2=E5=F0 ) 98.6 ^ 9=D7= _ 1 I
------=_NextPart_000_1B4F_01CE2069.19DF69D0-- From stan@hardwarefreak.com Thu Mar 14 07:26:37 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id 55FFF7F3F for ; Thu, 14 Mar 2013 07:26:37 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay3.corp.sgi.com (Postfix) with ESMTP id DE164AC004 for ; Thu, 14 Mar 2013 05:26:33 -0700 (PDT) X-ASG-Debug-ID: 1363263992-04bdf00a0dcdf90001-NocioJ Received: from greer.hardwarefreak.com (mo-65-41-216-221.sta.embarqhsd.net [65.41.216.221]) by cuda.sgi.com with ESMTP id Cizz71shppqzFBJs for ; Thu, 14 Mar 2013 05:26:32 -0700 (PDT) X-Barracuda-Envelope-From: stan@hardwarefreak.com X-Barracuda-Apparent-Source-IP: 65.41.216.221 X-Barracuda-User-Whitelist: xfs@oss.sgi.com Received: from [192.168.100.53] (gffx.hardwarefreak.com [192.168.100.53]) by greer.hardwarefreak.com (Postfix) with ESMTP id 7F3EB6C159; Thu, 14 Mar 2013 07:26:32 -0500 (CDT) Message-ID: <5141C1FC.4060209@hardwarefreak.com> Date: Thu, 14 Mar 2013 07:26:36 -0500 From: Stan Hoeppner Reply-To: stan@hardwarefreak.com User-Agent: Mozilla/5.0 (Windows NT 5.1; rv:17.0) Gecko/20130307 Thunderbird/17.0.4 MIME-Version: 1.0 To: Dave Hall , "xfs@oss.sgi.com" Subject: Re: xfs_fsr, sunit, and swidth References: <5140C147.7070205@binghamton.edu> <514113C6.9090602@hardwarefreak.com> <514153ED.3000405@binghamton.edu> X-ASG-Orig-Subj: Re: xfs_fsr, sunit, and swidth In-Reply-To: <514153ED.3000405@binghamton.edu> Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: mo-65-41-216-221.sta.embarqhsd.net[65.41.216.221] X-Barracuda-Start-Time: 1363263992 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 On 3/13/2013 11:37 PM, Dave Hall wrote: > Stan, > > If you'd rather I can re-post this to xfs@oss.sgi.com, but I'm not clear > on exactly where this address leads. I am grateful for your response. No need, I'm CC'ing the list address. Read this entirely before hitting reply. > So the details are that this is a 16 x 2GB 7200 rpm SATA drive array in > a RAID enclosure. The array is configured RAID6 (so 14 data spindles) > with a chunk size of 128k. The XFS formatted size is 26TB with 19TB > currently used. So your RAID6 stripe width is 14 * 128KB = 1,792KB. > The workload is a backup program called rsnapshot. If you're not > familiar, this program uses cp -al top create a linked copy of the > previous backup, and then rsync -av --del to copy in any changes. The > current snapshots contain about 14.8 million files. The total number of > snapshots is about 600. So you've got a metadata heavy workload with lots of links being created. > The performance problem that lead me to investigate XFS is that some > time around mid-November the cp -al step started running very long - > sometimes over 48 hours. Sometimes it runs in just a few hours. Prior > to then the entire backup consistenly finished in less than 12 hours. > When the cp -al is running long the output of dstat indicates that the > I/O to the fs is fairly light. The 'cp -al' command is a pure metadata workload, which means lots of writes to the filesystem directory trees, but not into files. And if your kernel is lower than 2.6.39 your log throughput would be pretty high as well. But given this is RAID6 you'll have significant RMW for these directory writes, maybe overwhelming RMW, driving latency up and thus actual bandwidth down. So dstat bytes throughput may be low, but %wa may be through the roof, making the dstat data you're watching completely misleading as to what's really going on, what's causing the problem. > Please let me know if you need any further information. Yes, please provide the output of the following commands: ~$ grep xfs /etc/fstab ~$ xfs_info /dev/[mount-point] ~$ df /dev/[mount_point] ~$ df -i /dev/[mount_point] ~$ xfs_db -r -c freesp /dev/[mount-point] Also please provide the make/model of the RAID controller, the write cache size and if it is indeed enabled and working, as well as any errors, if any, logged by the controller in dmesg or elsewhere in Linux, or in the controller firmware. > Also, again, I > can post this to xfs@oss.sgi.com but I'd really like to know more about > the address. Makes me where you obtained the list address. Apparently not from the official websites or you'd not have to ask. Maybe this will assuage your fears. ;) xfs@oss.sgi.com is the official XFS mailing list submission address for the XFS developers and users. oss.sgi.com is the server provided and managed by SGI (www.sgi.com) that houses the XFS open source project. SGI created the XFS filesystem first released on their proprietary IRIX/MIPS computers in 1994. SGI open sourced XFS and ported it to Linux in the early 2000s. XFS is actively developed by a fairly large group of people, and AFAIK most of them are currently employed by Red Hat, including Dave Chinner, who also replied to your post. Dave wrote the delaylog code which will probably go a long way toward fixing your problem, if you're currently using 2.6.38 or lower and not mounting with this option enabled. It didn't become the default until 2.6.39. More info here http://www.xfs.org and here http://oss.sgi.com/projects/xfs/ > Thanks. You bet. -- Stan > -Dave > > > On 3/13/2013 8:03 PM, Stan Hoeppner wrote: >> On 3/13/2013 1:11 PM, Dave Hall wrote: >> >>> Does xfs_fsr react in any way to the sunit and swidth attributes of the >>> file system? >> No, manually remounting with new stripe alignment and then running >> xfs_fsr is not going to magically reorganize your filesystem. >> >>> In other words, with an XFS filesytem set up directly on a >>> hardware RAID, it is recommended that the mount command be changed to >>> specify sunit and swidth values that reflect the new geometry of the >>> RAID. >> This recommendation (as well as most things storage related) is workload >> dependent. A common misconception many people have is that XFS simply >> needs to be aligned to the RAID stripe. In reality, it's more critical >> that XFS write out be aligned to the application's write pattern, and >> thus, the hardware RAID stripe needs to be as well. Another common >> misconception is that simply aligning XFS to the RAID stripe will >> automagically yield fully filled hardware stripes. This is entirely >> dependent on matching the hardware RAID stripe to the applications write >> pattern. >> >>> In my case, these values were not specified on the mkfs.xfs of a >>> rather large file system running on a RAID 6 array. I am wondering >>> adding sunit and swidth parameters to the fstab will cause xfs_fsr to do >>> anything different than it is already doing. >> No, see above. And read this carefully: Aligning XFS affects write out >> only during allocation. It does not affect xfs_fsr. Nor does it affect >> non allocation workloads, i.e. database inserts, writing new mail to >> mbox files, etc. >> >>> Most importantly, will it >>> improve performace in any way? >> You provided insufficient information for us to help you optimize >> performance. For us to even take a stab at answering this we need to >> know at least: >> >> 1. application/workload write pattern(s) Is it allocation heavy? >> a. small random IO >> b. large streaming >> c. If mixed, what is the ratio >> >> 2. current hardware RAID parameters >> a. strip/chunk size >> b. # of effective spindles (RAID6 minus 2) >> >> 3. Current percentage of filesystem bytes and inodes used >> a. ~$ df /dev/[mount_point] >> b. ~$ df -i /dev/[mount_point] >> >> FWIW, parity RAID is abysmal with random writes, and especially so if >> the hardware stripe width is larger than the workload's write IOs. >> Thus, optimizing performance with hardware RAID and filesystems must be >> done during the design phase of the storage. For instance if you have a >> RAID6 chunk/strip size of 512K and 8 spindles that's a 4MB stripe width. >> If your application is doing random allocation write out in 256K >> chunks, you simply can't optimize performance without blowing away the >> array and recreating. For this example you'd need a chunk/strip of 32K >> with 8 effective spindles which equals 256K. >> >> Now, there is a possible silver lining here. If your workload is doing >> mostly large streaming writes, allocation or not, that are many >> multiples of your current hardware RAID stripe, it doesn't matter if >> your XFS is doing default 4K writes or if it has been aligned to the >> RAID stripe. In this case the controller's BBWC is typically going to >> take the successive XFS 4K IOs and fill hardware stripes automatically. >> >> So again, as always, the answer depends on your workload. >> > From stan@hardwarefreak.com Thu Mar 14 07:55:27 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=none autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay3.corp.sgi.com [198.149.34.15]) by oss.sgi.com (Postfix) with ESMTP id A670F7F3F for ; Thu, 14 Mar 2013 07:55:27 -0500 (CDT) Received: from cuda.sgi.com (cuda1.sgi.com [192.48.157.11]) by relay3.corp.sgi.com (Postfix) with ESMTP id 47D3DAC005 for ; Thu, 14 Mar 2013 05:55:27 -0700 (PDT) X-ASG-Debug-ID: 1363265726-04bdf00a0bd0500001-NocioJ Received: from greer.hardwarefreak.com (mo-65-41-216-221.sta.embarqhsd.net [65.41.216.221]) by cuda.sgi.com with ESMTP id CIqZCK9HSFAWogMv for ; Thu, 14 Mar 2013 05:55:26 -0700 (PDT) X-Barracuda-Envelope-From: stan@hardwarefreak.com X-Barracuda-Apparent-Source-IP: 65.41.216.221 X-Barracuda-User-Whitelist: xfs@oss.sgi.com Received: from [192.168.100.53] (gffx.hardwarefreak.com [192.168.100.53]) by greer.hardwarefreak.com (Postfix) with ESMTP id E0B336C0C8; Thu, 14 Mar 2013 07:55:25 -0500 (CDT) Message-ID: <5141C8C1.2080903@hardwarefreak.com> Date: Thu, 14 Mar 2013 07:55:29 -0500 From: Stan Hoeppner Reply-To: stan@hardwarefreak.com User-Agent: Mozilla/5.0 (Windows NT 5.1; rv:17.0) Gecko/20130307 Thunderbird/17.0.4 MIME-Version: 1.0 To: stan@hardwarefreak.com CC: Dave Hall , "xfs@oss.sgi.com" Subject: Re: xfs_fsr, sunit, and swidth References: <5140C147.7070205@binghamton.edu> <514113C6.9090602@hardwarefreak.com> <514153ED.3000405@binghamton.edu> <5141C1FC.4060209@hardwarefreak.com> X-ASG-Orig-Subj: Re: xfs_fsr, sunit, and swidth In-Reply-To: <5141C1FC.4060209@hardwarefreak.com> Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Barracuda-Connect: mo-65-41-216-221.sta.embarqhsd.net[65.41.216.221] X-Barracuda-Start-Time: 1363265726 X-Barracuda-URL: http://192.48.157.11:80/cgi-mod/mark.cgi X-Virus-Scanned: by bsmtpd at sgi.com X-Barracuda-BRTS-Status: 1 Quick note below, need one more bit of info. On 3/14/2013 7:26 AM, Stan Hoeppner wrote: > On 3/13/2013 11:37 PM, Dave Hall wrote: >> Stan, >> >> If you'd rather I can re-post this to xfs@oss.sgi.com, but I'm not clear >> on exactly where this address leads. I am grateful for your response. > > No need, I'm CC'ing the list address. Read this entirely before hitting > reply. > >> So the details are that this is a 16 x 2GB 7200 rpm SATA drive array in >> a RAID enclosure. The array is configured RAID6 (so 14 data spindles) >> with a chunk size of 128k. The XFS formatted size is 26TB with 19TB >> currently used. > > So your RAID6 stripe width is 14 * 128KB = 1,792KB. > >> The workload is a backup program called rsnapshot. If you're not >> familiar, this program uses cp -al top create a linked copy of the >> previous backup, and then rsync -av --del to copy in any changes. The >> current snapshots contain about 14.8 million files. The total number of >> snapshots is about 600. > > So you've got a metadata heavy workload with lots of links being created. > >> The performance problem that lead me to investigate XFS is that some >> time around mid-November the cp -al step started running very long - >> sometimes over 48 hours. Sometimes it runs in just a few hours. Prior >> to then the entire backup consistenly finished in less than 12 hours. >> When the cp -al is running long the output of dstat indicates that the >> I/O to the fs is fairly light. > > The 'cp -al' command is a pure metadata workload, which means lots of > writes to the filesystem directory trees, but not into files. And if > your kernel is lower than 2.6.39 your log throughput would be pretty > high as well. But given this is RAID6 you'll have significant RMW for > these directory writes, maybe overwhelming RMW, driving latency up and > thus actual bandwidth down. So dstat bytes throughput may be low, but > %wa may be through the roof, making the dstat data you're watching > completely misleading as to what's really going on, what's causing the > problem. > >> Please let me know if you need any further information. > > Yes, please provide the output of the following commands: ~$ uname -a > ~$ grep xfs /etc/fstab > ~$ xfs_info /dev/[mount-point] > ~$ df /dev/[mount_point] > ~$ df -i /dev/[mount_point] > ~$ xfs_db -r -c freesp /dev/[mount-point] > > Also please provide the make/model of the RAID controller, the write > cache size and if it is indeed enabled and working, as well as any > errors, if any, logged by the controller in dmesg or elsewhere in Linux, > or in the controller firmware. > >> Also, again, I >> can post this to xfs@oss.sgi.com but I'd really like to know more about >> the address. > > Makes me where you obtained the list address. Apparently not from the > official websites or you'd not have to ask. Maybe this will assuage > your fears. ;) > > xfs@oss.sgi.com is the official XFS mailing list submission address for > the XFS developers and users. oss.sgi.com is the server provided and > managed by SGI (www.sgi.com) that houses the XFS open source project. > SGI created the XFS filesystem first released on their proprietary > IRIX/MIPS computers in 1994. SGI open sourced XFS and ported it to > Linux in the early 2000s. > > XFS is actively developed by a fairly large group of people, and AFAIK > most of them are currently employed by Red Hat, including Dave Chinner, > who also replied to your post. Dave wrote the delaylog code which will > probably go a long way toward fixing your problem, if you're currently > using 2.6.38 or lower and not mounting with this option enabled. It > didn't become the default until 2.6.39. > > More info here http://www.xfs.org and here http://oss.sgi.com/projects/xfs/ > >> Thanks. > > You bet. > From rjohnston@sgi.com Thu Mar 14 08:01:33 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from relay.sgi.com (relay2.corp.sgi.com [137.38.102.29]) by oss.sgi.com (Postfix) with ESMTP id 08ADC7F3F for ; Thu, 14 Mar 2013 08:01:33 -0500 (CDT) Received: from xmail.sgi.com (pv-excas3-dc21-nlb.corp.sgi.com [137.38.102.207]) by relay2.corp.sgi.com (Postfix) with ESMTP id 86BF8304064; Thu, 14 Mar 2013 06:01:29 -0700 (PDT) Received: from [128.162.233.55] (128.162.233.55) by xmail.sgi.com (137.38.102.30) with Microsoft SMTP Server (TLS) id 14.2.318.1; Thu, 14 Mar 2013 08:01:29 -0500 Message-ID: <5141CA42.4070106@sgi.com> Date: Thu, 14 Mar 2013 08:01:54 -0500 From: Rich Johnston User-Agent: Mozilla/5.0 (X11; Linux i686; rv:13.0) Gecko/20120615 Thunderbird/13.0.1 MIME-Version: 1.0 To: Eric Sandeen CC: Eric Sandeen , , , Stefan Behrens Subject: Re: [PATCH 3/3 V4] xfstests: btrfs tests for basic informational commands References: <1363186623-1378-1-git-send-email-sandeen@redhat.com> <1363186623-1378-4-git-send-email-sandeen@redhat.com> <5140AB9D.2070001@redhat.com> <5140CB3F.5010704@redhat.com> <5140CD26.7050201@sandeen.net> In-Reply-To: <5140CD26.7050201@sandeen.net> Content-Type: text/plain; charset="ISO-8859-1"; format=flowed Content-Transfer-Encoding: 7bit X-Originating-IP: [128.162.233.55] Stefan, Thanks for reviewing this patch, may I put your Reviewed-by: on this version? Thanks --Rich From pwhite@sgi.com Thu Mar 14 08:06:12 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from cthulhu.engr.sgi.com (cthulhu.engr.sgi.com [150.166.39.100]) by oss.sgi.com (Postfix) with ESMTP id DBF507F51 for ; Thu, 14 Mar 2013 08:06:11 -0500 (CDT) Received: from polaris-admin.engr.sgi.com (polaris-admin.engr.sgi.com [150.166.41.54]) by cthulhu.engr.sgi.com (8.12.10/8.12.10/SuSE Linux 0.7) with ESMTP id r2ED6Bx7007450 for ; Thu, 14 Mar 2013 06:06:11 -0700 Received: by polaris-admin.engr.sgi.com (Postfix, from userid 48024) id 405A853DEAEF; Thu, 14 Mar 2013 06:06:11 -0700 (PDT) Date: Thu, 14 Mar 2013 06:06:11 -0700 To: xfs@oss.sgi.com Subject: [PATCH 01/18] xfstests: Remove obsolete remake script User-Agent: nail 11.25 7/29/05 MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Transfer-Encoding: 7bit Message-Id: <20130314130611.405A853DEAEF@polaris-admin.engr.sgi.com> From: pwhite@sgi.com (Philip White) From: Phil White This is a rebasing & resubmit of a dchinner patch. His comments on the original: ----------------- We don't ever do wholesale rebuilds of the output files anymore, so kill the script that does it to reduce the dependency on common and common.rc. ----------------- Signed-off-by: Phil White --- remake | 72 ---------------------------------------------------------------- 1 files changed, 0 insertions(+), 72 deletions(-) delete mode 100755 remake diff --git a/remake b/remake deleted file mode 100755 index a95aae7..0000000 --- a/remake +++ /dev/null @@ -1,72 +0,0 @@ -#! /bin/bash -# -# Copyright (c) 2000-2001 Silicon Graphics, Inc. All Rights Reserved. -# -# This program is free software; you can redistribute it and/or -# modify it under the terms of the GNU General Public License as -# published by the Free Software Foundation. -# -# This program is distributed in the hope that it would be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program; if not, write the Free Software Foundation, -# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA -# -# -# Rebuild NNN.out files -# -# $Header: /build2/depot/linux/pcp/dev/qa/RCS/remake,v 2.11 1999/09/20 03:42:19 kenmcd Exp $ -# - -tmp=/tmp/$$ -trap "rm -f NO-PREVIOUS-OUTPUT $tmp.*; exit" 0 1 2 3 15 - -# generic initialization -iam=remake -. ./common.rc - -. ./common - -[ -f check.time ] || touch check.time - -for seq in $list -do - if [ ! -f $seq ] - then - echo "Remake: cannot find \"$seq\"" - else - echo -n "$seq" - lasttime=`sed -n -e "/^$seq /s/.* //p" $seq.new 2>&1 - then - if [ -f $seq.out ] - then - $diff $seq.out $seq.new - rm -f $seq.out.bad - else - touch NO-PREVIOUS-OUTPUT - $diff NO-PREVIOUS-OUTPUT $seq.new - rm -f NO-PREVIOUS-OUTPUT - fi - echo "" - [ -f $seq.out ] && mv $seq.out $seq.bak - if [ -f $seq.full ] - then - [ -f $seq.full.ok ] && mv $seq.full.ok $seq.full.bak - mv $seq.full $seq.full.ok - fi - mv $seq.new $seq.out - else - echo " - failed (exit status $?)" - sed 's/^/ /' $seq.new - exit 1 - fi - fi -done - -exit 0 -- 1.5.3.8 From pwhite@sgi.com Thu Mar 14 08:06:12 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from cthulhu.engr.sgi.com (cthulhu.engr.sgi.com [150.166.39.100]) by oss.sgi.com (Postfix) with ESMTP id 28B297F54 for ; Thu, 14 Mar 2013 08:06:12 -0500 (CDT) Received: from polaris-admin.engr.sgi.com (polaris-admin.engr.sgi.com [150.166.41.54]) by cthulhu.engr.sgi.com (8.12.10/8.12.10/SuSE Linux 0.7) with ESMTP id r2ED6Bx7007459 for ; Thu, 14 Mar 2013 06:06:11 -0700 Received: by polaris-admin.engr.sgi.com (Postfix, from userid 48024) id 6F39153DEAF4; Thu, 14 Mar 2013 06:06:11 -0700 (PDT) Date: Thu, 14 Mar 2013 06:06:11 -0700 To: xfs@oss.sgi.com Subject: [PATCH 06/18] xfstests: Remove hangcheck code User-Agent: nail 11.25 7/29/05 MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Transfer-Encoding: 7bit Message-Id: <20130314130611.6F39153DEAF4@polaris-admin.engr.sgi.com> From: pwhite@sgi.com (Philip White) From: Phil White This is a rebasing & resubmit of a dchinner patch. His comments on the original: ----------------- This is an old script from the auto-qa days back at SGI. It no longer is in use or, AFAIK, ever been used for xfstests. If anyone needs it, they can pull it back out of git, so lets remove it to simplify check. ----------------- Signed-off-by: Phil White --- check | 27 +-------------------------- 1 files changed, 1 insertions(+), 26 deletions(-) diff --git a/check b/check index bad2e4d..e2c758b 100755 --- a/check +++ b/check @@ -77,19 +77,13 @@ testlist options _wrapup() { - # for hangcheck ... - # remove files that were used by hangcheck - # - [ -f /tmp/check.pid ] && rm -rf /tmp/check.pid - [ -f /tmp/check.sts ] && rm -rf /tmp/check.sts - if $showme then : elif $needwrap then - if [ -f check.time -a -f $tmp.time ] then + if [ -f check.time -a -f $tmp.time ] cat check.time $tmp.time \ | $AWK_PROG ' { t[$1] = $2 } @@ -138,27 +132,11 @@ END { if (NR > 0) { fi rm -f /tmp/*.rawout /tmp/*.out /tmp/*.err /tmp/*.time - rm -f /tmp/check.pid /tmp/check.sts rm -f $tmp.* } trap "_wrapup; exit \$status" 0 1 2 3 15 -# for hangcheck ... -# Save pid of check in a well known place, so that hangcheck can be sure it -# has the right pid (getting the pid from ps output is not reliable enough). -# -rm -rf /tmp/check.pid -echo $$ >/tmp/check.pid - -# for hangcheck ... -# Save the status of check in a well known place, so that hangcheck can be -# sure to know where check is up to (getting test number from ps output is -# not reliable enough since the trace stuff has been introduced). -# -rm -rf /tmp/check.sts -echo "preamble" >/tmp/check.sts - # don't leave old full output behind on a clean run rm -f check.full @@ -238,9 +216,6 @@ do fi rm -f core $seq.notrun - # for hangcheck ... - echo "$seq" >/tmp/check.sts - start=`_wallclock` $timestamp && echo -n " ["`date "+%T"`"]" [ ! -x $seq ] && chmod u+x $seq # ensure we can run it -- 1.5.3.8 From pwhite@sgi.com Thu Mar 14 08:06:12 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from cthulhu.engr.sgi.com (cthulhu.engr.sgi.com [150.166.39.100]) by oss.sgi.com (Postfix) with ESMTP id 2D8637F55 for ; Thu, 14 Mar 2013 08:06:12 -0500 (CDT) Received: from polaris-admin.engr.sgi.com (polaris-admin.engr.sgi.com [150.166.41.54]) by cthulhu.engr.sgi.com (8.12.10/8.12.10/SuSE Linux 0.7) with ESMTP id r2ED6Bx7007460 for ; Thu, 14 Mar 2013 06:06:11 -0700 Received: by polaris-admin.engr.sgi.com (Postfix, from userid 48024) id 7A12553DEAEF; Thu, 14 Mar 2013 06:06:11 -0700 (PDT) Date: Thu, 14 Mar 2013 06:06:11 -0700 To: xfs@oss.sgi.com Subject: [PATCH 07/18] xfstests: Remove expunge capability for simplicity User-Agent: nail 11.25 7/29/05 MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Transfer-Encoding: 7bit Message-Id: <20130314130611.7A12553DEAEF@polaris-admin.engr.sgi.com> From: pwhite@sgi.com (Philip White) From: Phil White This is a rebasing & resubmit of a dchinner patch. His comments on the original: ----------------- Check supports an expunge file for tests - a way of marking tests not to run even if you specify it to run. Use is like this: $ echo 002 > expunged test-2:~/src/xfstests-dev$ sudo ./check 001-003 FSTYP -- xfs (debug) PLATFORM -- Linux/x86_64 test-2 3.5.0-rc1-dgc+ MKFS_OPTIONS -- -f -bsize=4096 /dev/vdb MOUNT_OPTIONS -- /dev/vdb /mnt/scratch 001 4s ... 4s 002 - expunged 003 0s ... 0s Ran: 001 002 003 Not run:1 Passed all 2 tests This is arguably useful(*), but gets in the way of splitting up the tests into multiple directories. Remove it for now, but such functionality should be considered for re-implementation at a later date. (*) e.g. having a different "expunged" file for each distro release you have to test to avoid the tests known to fail due to fixes or features that will never be back ported to older releases.... ----------------- Signed-off-by: Phil White --- check | 13 ------------- common | 5 ----- 2 files changed, 0 insertions(+), 18 deletions(-) diff --git a/check b/check index e2c758b..06189c8 100755 --- a/check +++ b/check @@ -95,13 +95,6 @@ END { if (NR > 0) { mv $tmp.out check.time fi - if [ -f $tmp.expunged ] - then - notrun=`wc -l <$tmp.expunged | sed -e 's/ *//g'` - n_try=`expr $n_try - $notrun` - list=`echo "$list" | sed -f $tmp.expunged` - fi - echo "" >>check.log date >>check.log echo $list | fmt | sed -e 's/^/ /' >>check.log @@ -195,15 +188,9 @@ do then echo continue - elif [ -f expunged ] && $expunge && egrep "^$seq([ ]|\$)" expunged >/dev/null - then - echo " - expunged" - rm -f $seq.out.bad - echo "/^$seq\$/d" >>$tmp.expunged elif [ ! -f $seq ] then echo " - no such test?" - echo "/^$seq\$/d" >>$tmp.expunged else # really going to try and run this one # diff --git a/common b/common index 2553fe9..821ea59 100644 --- a/common +++ b/common @@ -49,10 +49,6 @@ BEGIN { for (t='$start'; t<='$end'; t++) printf "%03d\n",t }' \ if grep -s "^$id " group >/dev/null ; then # in group file ... OK echo $id >>$tmp.list - elif [ -f expunged ] && $expunge && \ - egrep "^$id([ ]|\$)" expunged >/dev/null; then - # expunged ... will be reported, but not run, later - echo $id >>$tmp.list else # oops echo "$id - unknown test, ignored" @@ -81,7 +77,6 @@ group=false xgroup=false showme=false sortme=false -expunge=true have_test_arg=false randomize=false timestamp=${TIMESTAMP:=false} -- 1.5.3.8 From pwhite@sgi.com Thu Mar 14 08:06:13 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from cthulhu.engr.sgi.com (cthulhu.engr.sgi.com [150.166.39.100]) by oss.sgi.com (Postfix) with ESMTP id 1B0727F53 for ; Thu, 14 Mar 2013 08:06:12 -0500 (CDT) Received: from polaris-admin.engr.sgi.com (polaris-admin.engr.sgi.com [150.166.41.54]) by cthulhu.engr.sgi.com (8.12.10/8.12.10/SuSE Linux 0.7) with ESMTP id r2ED6Bx7007456 for ; Thu, 14 Mar 2013 06:06:11 -0700 Received: by polaris-admin.engr.sgi.com (Postfix, from userid 48024) id 6A23953C7F62; Thu, 14 Mar 2013 06:06:11 -0700 (PDT) Date: Thu, 14 Mar 2013 06:06:11 -0700 To: xfs@oss.sgi.com Subject: [PATCH 05/18] xfstests: Redo option parsing User-Agent: nail 11.25 7/29/05 MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Transfer-Encoding: 7bit Message-Id: <20130314130611.6A23953C7F62@polaris-admin.engr.sgi.com> From: pwhite@sgi.com (Philip White) From: Phil White This is a rebasing & resubmit of a dchinner patch. His comments on the original: ----------------- The option parise in a messy loop of option parsing and actions on secondary arguments. Turn it into something much neater and esay to understand rather than a mess of temporary variables and tortured logic... ----------------- This required some deviation owing to the decision made in patch #2 of this series. Signed-off-by: Phil White --- check | 39 ++++--- common | 383 ++++++++++++++++++++++++++-------------------------------------- 2 files changed, 174 insertions(+), 248 deletions(-) diff --git a/check b/check index 9a5b256..bad2e4d 100755 --- a/check +++ b/check @@ -33,19 +33,9 @@ export QA_CHECK_FS=${QA_CHECK_FS:=true} # number of diff lines from a failed test, 0 for whole output export DIFF_LENGTH=${DIFF_LENGTH:=10} -# by default don't output timestamps -timestamp=${TIMESTAMP:=false} - # generic initialization iam=check -# we need common.config -if ! . ./common.config -then - echo "$iam: failed to source common.config" - exit 1 -fi - # we need common . ./common @@ -63,15 +53,26 @@ then exit 1 fi -_wallclock() -{ - date "+%H %M %S" | $AWK_PROG '{ print $1*3600 + $2*60 + $3 }' -} - -_timestamp() +usage() { - now=`date "+%T"` - echo -n " [$now]" + echo "Usage: $0 [options] [testlist]"' + +check options + -xfs test XFS (default) + -udf test UDF + -nfs test NFS + -l line mode diff + -udiff show unified diff (default) + -n show me, do not run tests + -T output timestamps + -r randomize test order + +testlist options + -g group[,group...] include tests from these groups + -x group[,group...] exclude tests from these groups + NNN include test NNN + NNN-NNN include test range (eg. 012-021) +' } _wrapup() @@ -276,7 +277,7 @@ do echo " - no qualified output" err=true else - if diff $seq.out $tmp.out >/dev/null 2>&1 + if $diff $seq.out $tmp.out >/dev/null 2>&1 then if $err then diff --git a/common b/common index 0723224..2553fe9 100644 --- a/common +++ b/common @@ -27,13 +27,55 @@ _setenvironment() export MSGVERB } +get_group_list() +{ + grp=$1 + grpl=$(sed -n < group \ + -e 's/#.*//' \ + -e 's/$/ /' \ + -e "/^[0-9][0-9][0-9].* $grp /"'{ s/ .*//p }') + echo $grpl +} + +expand_test_numbers() +{ + # strip leading zeros, could be considered octal. + start=`echo $1 | sed 's/^0*//'` + end=`echo $2 | sed 's/^0*//'` + $AWK_PROG /dev/null ; then + # in group file ... OK + echo $id >>$tmp.list + elif [ -f expunged ] && $expunge && \ + egrep "^$id([ ]|\$)" expunged >/dev/null; then + # expunged ... will be reported, but not run, later + echo $id >>$tmp.list + else + # oops + echo "$id - unknown test, ignored" + fi + done +} + +_wallclock() +{ + date "+%H %M %S" | $AWK_PROG '{ print $1*3600 + $2*60 + $3 }' +} + +_timestamp() +{ + now=`date "+%T"` + echo -n " [$now]" +} + here=`pwd` -rm -f $here/$iam.out -_setenvironment check=${check-true} -diff="diff -u" +diff="`which diff`" verbose=false group=false xgroup=false @@ -42,7 +84,13 @@ sortme=false expunge=true have_test_arg=false randomize=false -rm -f $tmp.list $tmp.tmp $tmp.sed +timestamp=${TIMESTAMP:=false} + +SUPPORTED_TESTS="[0-9][0-9][0-9] [0-9][0-9][0-9][0-9]" + +# start the initialisation work now +_setenvironment +rm -f $tmp.list $tmp.tmp $tmp.sed $here/$iam.out # Autodetect fs type based on what's on $TEST_DEV if [ "$HOSTOS" == "Linux" ] @@ -52,242 +100,118 @@ else export FSTYP=xfs fi -for r -do - - if $group - then - # arg after -g - group_list=$(sed -n < group \ - -e 's/#.*//' \ - -e 's/$/ /' \ - -e "/^[0-9][0-9][0-9].* $r /"'{ s/ .*//p }') - if [ -z "$group_list" ] - then - echo "Group \"$r\" is empty or not defined?" - exit 1 - fi - [ ! -s $tmp.list ] && touch $tmp.list - for t in $group_list - do - if grep -s "^$t\$" $tmp.list >/dev/null - then - : - else - echo "$t" >>$tmp.list - fi - done - group=false - continue - - elif $xgroup - then - # arg after -x - [ ! -s $tmp.list ] && ls [0-9][0-9][0-9] [0-9][0-9][0-9][0-9] >$tmp.list 2>/dev/null - group_list=`sed -n $tmp.tmp - mv $tmp.tmp $tmp.list - numsed=0 - rm -f $tmp.sed - fi - echo "/^$t\$/d" >>$tmp.sed - numsed=`expr $numsed + 1` - done - sed -f $tmp.sed <$tmp.list >$tmp.tmp - mv $tmp.tmp $tmp.list - xgroup=false - continue - fi - - xpand=true - case "$r" - in - - -\? | -h | --help) # usage - echo "Usage: $0 [options] [testlist]"' - -common options - -v verbose - -check options - -xfs test XFS (default) - -udf test UDF - -nfs test NFS - -l line mode diff - -xdiff graphical mode diff - -udiff show unified diff (default) - -n show me, do not run tests - -q quick [deprecated] - -T output timestamps - -r randomize test order - -testlist options - -g group[,group...] include tests from these groups - -x group[,group...] exclude tests from these groups - NNN include test NNN - NNN-NNN include test range (eg. 012-021) -' - exit 0 - ;; - - -udf) # -udf ... set FSTYP to udf - FSTYP=udf - xpand=false - ;; - - -xfs) # -xfs ... set FSTYP to xfs - FSTYP=xfs - xpand=false - ;; - - -nfs) # -nfs ... set FSTYP to nfs - FSTYP=nfs - xpand=false - ;; - - -g) # -g group ... pick from group file - group=true - xpand=false - ;; - - -l) # line mode for diff, was default before - diff="diff" - xpand=false - ;; - - -xdiff) # graphical diff mode - xpand=false - - if [ ! -z "$DISPLAY" ] - then - which xdiff >/dev/null 2>&1 && diff=xdiff - which gdiff >/dev/null 2>&1 && diff=gdiff - which tkdiff >/dev/null 2>&1 && diff=tkdiff - which xxdiff >/dev/null 2>&1 && diff=xxdiff - fi - ;; +# we need common.config +if ! . ./common.config +then + echo "$iam: failed to source common.config" + exit 1 +fi - -udiff) # show a unified diff, default now, keep for backward compat - xpand=false - diff="$diff -u" - ;; +while [ $# -gt 0 ]; do + case "$1" in + -\? | -h | --help) usage ;; - -q) # "quick", no longer used - always quick :-) - xpand=false - ;; + -udf) FSTYP=udf ;; + -xfs) FSTYP=xfs ;; + -nfs) FSTYP=nfs ;; - -n) # show me, don't do it - showme=true - xpand=false - ;; - -r) # randomize test order - randomize=true - xpand=false - ;; + -g) group=$2 ; shift ; + group_list=$(get_group_list $group) + if [ -z "$group_list" ]; then + echo "Group \"$group\" is empty or not defined?" + exit 1 + fi + [ ! -s $tmp.list ] && touch $tmp.list + for t in $group_list; do + grep -s "^$t\$" $tmp.list >/dev/null || \ + echo "$t" >>$tmp.list + done + ;; + + -x) xgroup=$2 ; shift ; + [ ! -s $tmp.list ] && ls $SUPPORTED_TESTS >$tmp.list 2>/dev/null + group_list=$(get_group_list $xgroup) + if [ -z "$group_list" ]; then + echo "Group \"$xgroup\" is empty or not defined?" + exit 1 + fi - -T) # turn on timestamp output - timestamp=true - xpand=false - ;; + rm -f $tmp.sed + numsed=0 + for t in $group_list + do + if [ $numsed -gt 100 ]; then + sed -f $tmp.sed <$tmp.list >$tmp.tmp + mv $tmp.tmp $tmp.list + numsed=0 + rm -f $tmp.sed + fi + echo "/^$t\$/d" >>$tmp.sed + numsed=`expr $numsed + 1` + done + sed -f $tmp.sed <$tmp.list >$tmp.tmp + mv $tmp.tmp $tmp.list + ;; - -v) - verbose=true - xpand=false - ;; - -x) # -x group ... exclude from group file - xgroup=true - xpand=false - ;; - '[0-9][0-9][0-9] [0-9][0-9][0-9][0-9]') - echo "No tests?" - status=1 - exit $status - ;; + -l) diff="`which diff`" ;; + -udiff) diff="$diff -u" ;; - [0-9]*-[0-9]*) - eval `echo $r | sed -e 's/^/start=/' -e 's/-/ end=/'` - ;; + -n) showme=true ;; + -r) randomize=true ;; + -T) timestamp=true ;; - [0-9]*-) - eval `echo $r | sed -e 's/^/start=/' -e 's/-//'` - end=`echo [0-9][0-9][0-9] [0-9][0-9][0-9][0-9] | sed -e 's/\[0-9]//g' -e 's/ *$//' -e 's/.* //'` - if [ -z "$end" ] - then - echo "No tests in range \"$r\"?" + "$SUPPORTED_TESTS") + echo "No tests?" status=1 exit $status - fi - ;; + ;; - *) - start=$r - end=$r - ;; + [0-9]*-[0-9]*) + eval `echo $1 | sed -e 's/^/start=/' -e 's/-/ end=/'` + expand_test_numbers $start $end + have_test_arg=true + ;; - esac + [0-9]*-) + eval `echo $1 | sed -e 's/^/start=/' -e 's/-//'` + end=`echo $SUPPORTED_TESTS | \ + sed -e 's/\[0-9]//g' -e 's/ *$//' -e 's/.* //'` + if [ -z "$end" ]; then + echo "No tests in range \"$1\"?" + status=1 + exit $status + fi - # get rid of leading 0s as can be interpreted as octal - start=`echo $start | sed 's/^0*//'` - end=`echo $end | sed 's/^0*//'` + expand_test_numbers $start $end + have_test_arg=true + ;; - if $xpand - then - have_test_arg=true - $AWK_PROG /dev/null - then - # in group file ... OK - echo $id >>$tmp.list - else - if [ -f expunged ] && $expunge && egrep "^$id([ ]|\$)" expunged >/dev/null - then - # expunged ... will be reported, but not run, later - echo $id >>$tmp.list - else - # oops - echo "$id - unknown test, ignored" - fi - fi - done - fi + --large-fs) export LARGE_SCRATCH_DEV=yes ;; + --extra-space=*) export SCRATCH_DEV_EMPTY_SPACE=${r#*=} ;; + -*) usage ;; + *) expand_test_numbers $1 $1 ; + have_test_arg=true + ;; + esac + shift done if [ -s $tmp.list ] then # found some valid test numbers ... this is good : -else - if $have_test_arg - then +elif $have_test_arg +then # had test numbers, but none in group file ... do nothing touch $tmp.list - else +else # no test numbers, do everything from group file sed -n -e '/^[0-9][0-9][0-9]*/s/[ ].*//p' $tmp.list - fi fi -# should be sort -n, but this did not work for Linux when this -# was ported from IRIX -# -list=`sort $tmp.list` +# sort the list of tests into numeric order +list=`sort -n $tmp.list` rm -f $tmp.list $tmp.tmp $tmp.sed if $randomize @@ -295,20 +219,21 @@ then list=`echo $list | awk -f randomize.awk` fi +# check for correct setup case "$FSTYP" in - xfs) - [ "$XFS_LOGPRINT_PROG" = "" ] && _fatal "xfs_logprint not found" - [ "$XFS_REPAIR_PROG" = "" ] && _fatal "xfs_repair not found" - [ "$XFS_CHECK_PROG" = "" ] && _fatal "xfs_check not found" - [ "$XFS_DB_PROG" = "" ] && _fatal "xfs_db not found" - [ "$MKFS_XFS_PROG" = "" ] && _fatal "mkfs_xfs not found" - ;; - udf) - [ "$MKFS_UDF_PROG" = "" ] && _fatal "mkfs_udf/mkudffs not found" - ;; - btrfs) - [ "$MKFS_BTRFS_PROG" = "" ] && _fatal "mkfs.btrfs not found" - ;; - nfs) - ;; + xfs) + [ "$XFS_LOGPRINT_PROG" = "" ] && _fatal "xfs_logprint not found" + [ "$XFS_REPAIR_PROG" = "" ] && _fatal "xfs_repair not found" + [ "$XFS_CHECK_PROG" = "" ] && _fatal "xfs_check not found" + [ "$XFS_DB_PROG" = "" ] && _fatal "xfs_db not found" + [ "$MKFS_XFS_PROG" = "" ] && _fatal "mkfs_xfs not found" + ;; + udf) + [ "$MKFS_UDF_PROG" = "" ] && _fatal "mkfs_udf/mkudffs not found" + ;; + btrfs) + [ "$MKFS_BTRFS_PROG" = "" ] && _fatal "mkfs.btrfs not found" + ;; + nfs) + ;; esac -- 1.5.3.8 From pwhite@sgi.com Thu Mar 14 08:06:17 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from cthulhu.engr.sgi.com (cthulhu.engr.sgi.com [150.166.39.100]) by oss.sgi.com (Postfix) with ESMTP id 3E1B47F59 for ; Thu, 14 Mar 2013 08:06:12 -0500 (CDT) Received: from polaris-admin.engr.sgi.com (polaris-admin.engr.sgi.com [150.166.41.54]) by cthulhu.engr.sgi.com (8.12.10/8.12.10/SuSE Linux 0.7) with ESMTP id r2ED6Bx7007461 for ; Thu, 14 Mar 2013 06:06:11 -0700 Received: by polaris-admin.engr.sgi.com (Postfix, from userid 48024) id 8039253DEAF5; Thu, 14 Mar 2013 06:06:11 -0700 (PDT) Date: Thu, 14 Mar 2013 06:06:11 -0700 To: xfs@oss.sgi.com Subject: [PATCH 08/18] xfstests: Remove undocumented code from check User-Agent: nail 11.25 7/29/05 MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Transfer-Encoding: 7bit Message-Id: <20130314130611.8039253DEAF5@polaris-admin.engr.sgi.com> From: pwhite@sgi.com (Philip White) From: Phil White This is a rebasing & resubmit of a dchinner patch. His comments on the original: ----------------- Undocumented and unused, AFAICT. Kill it. ----------------- Signed-off-by: Phil White --- check | 7 ------- 1 files changed, 0 insertions(+), 7 deletions(-) diff --git a/check b/check index 06189c8..37d1d2f 100755 --- a/check +++ b/check @@ -172,17 +172,10 @@ fi seq="check" _check_test_fs -[ -n "$TESTS_REMAINING_LOG" ] && echo $list > $TESTS_REMAINING_LOG - for seq in $list do err=false echo -n "$seq" - if [ -n "$TESTS_REMAINING_LOG" ] ; then - sed -e "s/$seq//" -e 's/ / /' -e 's/^ *//' $TESTS_REMAINING_LOG > $TESTS_REMAINING_LOG.tmp - mv $TESTS_REMAINING_LOG.tmp $TESTS_REMAINING_LOG - sync - fi if $showme then -- 1.5.3.8 From pwhite@sgi.com Thu Mar 14 08:06:12 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from cthulhu.engr.sgi.com (cthulhu.engr.sgi.com [150.166.39.100]) by oss.sgi.com (Postfix) with ESMTP id D25447F4E for ; Thu, 14 Mar 2013 08:06:11 -0500 (CDT) Received: from polaris-admin.engr.sgi.com (polaris-admin.engr.sgi.com [150.166.41.54]) by cthulhu.engr.sgi.com (8.12.10/8.12.10/SuSE Linux 0.7) with ESMTP id r2ED6Bx7007449 for ; Thu, 14 Mar 2013 06:06:11 -0700 Received: by polaris-admin.engr.sgi.com (Postfix, from userid 48024) id 33E1353C7F62; Thu, 14 Mar 2013 06:06:11 -0700 (PDT) Date: Thu, 14 Mar 2013 06:06:11 -0700 To: xfs@oss.sgi.com Subject: [PATCH 00/18] xfstests: Clean up the top level directory User-Agent: nail 11.25 7/29/05 MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Transfer-Encoding: 7bit Message-Id: <20130314130611.33E1353C7F62@polaris-admin.engr.sgi.com> From: pwhite@sgi.com (Philip White) From: Phil White This is my attempt at rebasing dchinner's xfstests reorganization. In essence, this is intended to split each of the tests out into tests/$FSTYP/ directories and clean up the top level directory of the xfstests tree. The most significant deviation is that some of the check-specific functionality remains in the common files. I have some work in the pipeline which will make use of it. -Phil This is an 18 patch series: [PATCH 01/18] xfstests: Remove obsolete remake script [PATCH 02/18] xfstests: Clear out old benchmarking materials [PATCH 03/18] xfstests: Remove owner fields from patches [PATCH 04/18] xfstests: Remove obsolete configs [PATCH 05/18] xfstests: Redo option parsing [PATCH 06/18] xfstests: Remove hangcheck code [PATCH 07/18] xfstests: Remove expunge capability for simplicity [PATCH 08/18] xfstests: Remove undocumented code from check [PATCH 09/18] xfstests: create tests subdirectory [PATCH 10/18] xfstests: Add generic tests to tests/generic/group [PATCH 11/18] xfstests: add tests into tests/xfs/group [PATCH 12/18] xfstests: adjusts group files for other fs tests [PATCH 13/18] xfstests: Change command line parsing for new structure [PATCH 14/18] xfstests: remove -x functionality [PATCH 15/18] xfstests: implement a result directory for tests [PATCH 16/18] xfstests: Move all the tests into their tests/*/ dirs [PATCH 17/18] xfstests: Change $seq to $seqres usage [PATCH 18/18] xfstests: fix link_out_file usage for new structure 001 | 321 -- 001.out | 9 - 002 | 82 - 002.out | 2 - 003 | 93 - 003.out | 12 - 004 | 144 - 004.out | 9 - 005 | 101 - 005.out | 8 - 006 | 80 - 006.out | 11 - 007 | 76 - 007.out | 22 - 008 | 118 - 008.out | 21 - 009 | 189 - 009.out | 114 - 010 | 71 - 010.out | 58 - 011 | 88 - 011.out | 4 - 012 | 123 - 012.out | 16 - 013 | 138 - 013.out | 14 - 014 | 74 - 014.out | 6 - 015 | 127 - 015.out | 7 - 016 | 249 -- 016.out | 119 - 017 | 95 - 017.out | 10 - 018 | 104 - 018.op.irix | 5628 --------------------------- 018.op.linux | 4714 ---------------------- 018.out | 17 - 018.trans_buf | 1821 --------- 018.trans_inode | 2609 ------------- 019 | 150 - 019.out | 84 - 020 | 186 - 020.out | 65 - 021 | 149 - 021.out | 57 - 022 | 61 - 022.out.irix | 55 - 022.out.linux | 55 - 023 | 56 - 023.out.irix | 89 - 023.out.linux | 89 - 024 | 58 - 024.out | 119 - 025 | 51 - 025.out | 83 - 026 | 49 - 026.out | 73 - 027 | 48 - 027.out | 81 - 028 | 77 - 028.out | 310 -- 029 | 68 - 029.out | 27 - 030 | 109 - 030.out.irix | 291 -- 030.out.linux | 250 -- 031 | 126 - 031.out.irix | 123 - 031.out.linux | 115 - 032 | 91 - 032.out | 2 - 033 | 108 - 033.out.irix | 223 -- 033.out.linux | 194 - 034 | 92 - 034.out | 5 - 035 | 58 - 035.out.irix | 94 - 035.out.linux | 94 - 036 | 55 - 036.out.irix | 86 - 036.out.linux | 83 - 037 | 52 - 037.out | 83 - 038 | 52 - 038.out | 87 - 039 | 55 - 039.out.irix | 89 - 039.out.linux | 88 - 040 | 62 - 040.good | 16 - 040.out | 2 - 041 | 100 - 041.out | 19 - 042 | 170 - 042.out | 13 - 043 | 59 - 043.out.irix | 104 - 043.out.linux | 104 - 044 | 179 - 044.out | 66 - 045 | 83 - 045.out | 7 - 046 | 50 - 046.out | 37 - 047 | 85 - 047.out | 334 -- 048 | 56 - 048.out | 5 - 049 | 140 - 049.out | 15 - 050 | 231 -- 050.out | 193 - 051 | 368 -- 051.out | 355 -- 052 | 135 - 052.out | 9 - 053 | 92 - 053.out | 24 - 054 | 133 - 054.out | 73 - 055 | 55 - 055.out.irix | 89 - 055.out.linux | 88 - 056 | 50 - 056.out | 37 - 057 | 56 - 057.out | 34 - 058 | 47 - 058.out | 243 -- 059 | 52 - 059.out | 76 - 060 | 58 - 060.out | 120 - 061 | 56 - 061.out | 34 - 062 | 221 -- 062.out | 654 ---- 063 | 59 - 063.out | 74 - 064 | 111 - 064.out | 1484 ------- 065 | 199 - 065.out | 832 ---- 066 | 75 - 066.out | 40 - 067 | 92 - 067.out | 166 - 068 | 139 - 068.out | 43 - 069 | 81 - 069.out | 9 - 070 | 69 - 070.out | 1 - 071 | 171 - 071.out | 107 - 071.out.32 | 107 - 071.out.64 | 107 - 072 | 84 - 072.out | 2 - 073 | 184 - 073.out | 73 - 074 | 187 - 074.out | 21 - 075 | 163 - 075.out | 18 - 076 | 85 - 076.out | 5 - 077 | 86 - 077.out | 7 - 078 | 156 - 078.out | 211 - 079 | 70 - 079.out | 7 - 080 | 75 - 080.out | 3 - 081 | 87 - 081.out | 4 - 081.ugquota.trans_inode | 3091 --------------- 082 | 134 - 082.op.irix | 5628 --------------------------- 082.op.linux | 4714 ---------------------- 082.out | 39 - 082.trans_buf | 1821 --------- 082.trans_inode | 2609 ------------- 083 | 103 - 083.out | 4 - 084 | 78 - 084.out | 9 - 085 | 100 - 085.out | 114 - 086 | 153 - 086.out | 4722 ---------------------- 087 | 154 - 087.out | 389 -- 088 | 57 - 088.out.irix | 9 - 088.out.linux | 9 - 089 | 93 - 089.out | 19 - 090 | 129 - 090.out | 18 - 091 | 90 - 091.out | 7 - 092 | 62 - 092.out | 8 - 093 | 164 - 093.out | Bin 917 -> 0 bytes 094 | 116 - 094.out | 12 - 095 | 70 - 095.out | 6 - 096 | 152 - 096.external | 53 - 096.internal | 55 - 097 | 259 -- 097.out.udf | 132 - 097.out.xfs | 132 - 098 | 277 -- 098.out | 1594 -------- 099 | 343 -- 099.out | 215 - 100 | 90 - 100.out | 1 - 101 | 63 - 101.out | 19 - 102 | 60 - 102.out | 2 - 103 | 103 - 103.out | 22 - 104 | 120 - 104.out | 127 - 105 | 101 - 105.out | 3 - 106 | 240 -- 106.out | 379 -- 107 | 155 - 107.out | 1550 -------- 108 | 125 - 108.out | 101 - 109 | 113 - 109.out | 12 - 110 | 88 - 110.out | 37 - 111 | 72 - 111.out | 100 - 112 | 165 - 112.out | 18 - 113 | 109 - 113.out | 22 - 114 | 347 -- 114.out | 365 -- 115 | 260 -- 115.out | 118 - 116 | 67 - 116.out | 3 - 117 | 118 - 117.out | 15 - 118 | 96 - 118.out | 9 - 119 | 77 - 119.out | 3 - 120 | 101 - 120.out | 10 - 121 | 115 - 121.out | 15 - 122 | 222 -- 122.out | 123 - 123 | 80 - 123.out | 7 - 124 | 85 - 124.out | 1 - 125 | 75 - 125.out | 7 - 126 | 77 - 126.out | 19 - 127 | 126 - 127.out | 13 - 128 | 68 - 128.out | 1 - 129 | 71 - 129.out | 1 - 130 | 260 -- 130.out | 392 -- 131 | 83 - 131.out | 2 - 132 | 214 - 132.out | 847 ---- 133 | 79 - 133.out | 5 - 134 | 120 - 134.out | 5 - 135 | 94 - 135.out | 13 - 136 | 362 -- 136.out | 7753 ------------------------------------- 137 | 111 - 137.out | 1 - 138 | 117 - 138.out | 1 - 139 | 117 - 139.out | 1 - 140 | 114 - 140.out | 1 - 141 | 61 - 141.out | 1 - 142 | 59 - 142.out | 232 -- 143 | 59 - 143.out | 98 - 144 | 59 - 144.out | 245 -- 145 | 59 - 145.out | 36 - 146 | 68 - 146.out.irix | 324 -- 146.out.linux | 320 -- 147 | 59 - 147.out | 29 - 148 | 111 - 148.out | 299 -- 149 | 129 - 149.out | 123 - 150 | 70 - 150.out | 5 - 151 | 115 - 151.out | 22 - 152 | 64 - 152.out | 10 - 153 | 71 - 153.out | 8 - 154 | 58 - 154.out | 21 - 155 | 90 - 155.out | 8 - 156 | 57 - 156.out | 1 - 157 | 59 - 157.out | 2 - 158 | 104 - 158.out | 6 - 159 | 71 - 159.out | 5 - 160 | 81 - 160.out | 11 - 161 | 70 - 161.out | 12 - 162 | 87 - 162.out | 12 - 163 | 72 - 163.out | 3 - 164 | 158 - 164.out | 35 - 165 | 130 - 165.out | 1581 -------- 166 | 100 - 166.out | 6 - 167 | 82 - 167.out | 3 - 168 | 115 - 168.out | 57 - 169 | 109 - 169.out | 19 - 170 | 68 - 170.out | 21 - 171 | 71 - 171.out | 21 - 172 | 65 - 172.out | 11 - 173 | 68 - 173.out | 21 - 174 | 64 - 174.out | 11 - 175 | 71 - 175.out | 63 - 176 | 77 - 176.out | 121 - 177 | 86 - 177.out | 88 - 178 | 103 - 178.out | 79 - 179 | 112 - 179.out | 1 - 180 | 116 - 180.out | 1 - 181 | 129 - 181.out | 15 - 182 | 113 - 182.out | 1 - 183 | 68 - 183.out | 4 - 184 | 58 - 184.out | 1 - 185 | 88 - 185.out | 71 - 186 | 185 - 186.out | 290 -- 187 | 139 - 187.out | 39 - 188 | 89 - 188.out | 65 - 189 | 226 -- 189.out | 59 - 190 | 101 - 190.out | 4 - 191 | 76 - 191.out | 324 -- 192 | 81 - 192.out | 5 - 193 | 253 -- 193.out | 51 - 194 | 219 -- 194.out | 59 - 195 | 88 - 195.out | 8 - 196 | 99 - 196.out | 2002 ---------- 197 | 67 - 197.out | 2 - 198 | 58 - 198.out | 2 - 199 | 92 - 199.out | 13 - 200 | 127 - 200.out | 24 - 201 | 100 - 201.out | 2 - 202 | 62 - 202.out | 29 - 203 | 91 - 203.out | 427 -- 204 | 59 - 204.out | 2 - 205 | 84 - 205.out | 4 - 206 | 101 - 206.out | 30 - 207 | 51 - 207.out | 2 - 208 | 51 - 208.out | 2 - 209 | 51 - 209.out | 2 - 210 | 51 - 210.out | 2 - 211 | 51 - 211.out | 2 - 212 | 52 - 212.out | 2 - 213 | 90 - 213.out | 4 - 214 | 151 - 214.out | 51 - 215 | 85 - 215.out | 8 - 216 | 79 - 216.out | 10 - 217 | 91 - 217.out | 7 - 218 | 96 - 218.out | 19 - 219 | 136 - 219.out | 37 - 220 | 85 - 220.out | 2 - 221 | 49 - 221.out | 2 - 222 | 57 - 222.out | 2 - 223 | 101 - 223.out | 251 -- 224 | 87 - 224.out | 2 - 225 | 79 - 225.out | 3 - 226 | 79 - 226.out | 6 - 227 | 211 - 227.out | 2 - 228 | 87 - 228.out | 6 - 229 | 88 - 229.out | 4 - 230 | 147 - 230.out | 33 - 231 | 121 - 231.out | 16 - 232 | 94 - 232.out | 7 - 233 | 103 - 233.out | 7 - 234 | 108 - 234.out | 4 - 235 | 80 - 235.out | 34 - 236 | 70 - 236.out | 2 - 237 | 80 - 237.out | 4 - 238 | 57 - 238.out | 2 - 239 | 58 - 239.out | 2 - 240 | 76 - 240.out | 2 - 241 | 60 - 241.out | 2 - 242 | 64 - 242.out | 77 - 243 | 181 - 243.out | 13 - 244 | 138 - 244.out | 2 - 245 | 73 - 245.out | 2 - 246 | 60 - 246.out | 4 - 247 | 80 - 247.out | 2 - 248 | 58 - 248.out | 2 - 249 | 66 - 249.out | 2 - 250 | 97 - 250.out | 14 - 251 | 184 - 251.out | 3 - 252 | 67 - 252.out | 307 -- 253 | 194 - 253.out | 2 - 254 | 108 - 254.out | 40 - 255 | 68 - 255.out | 307 -- 256 | 178 - 256.out | 1 - 257 | 56 - 257.out | 2 - 258 | 76 - 258.out | 5 - 259 | 67 - 259.out | 7 - 260 | 190 - 260.out | 14 - 261 | 119 - 261.out | 2 - 262 | 146 - 262.out | 2 - 263 | 64 - 263.out | 3 - 264 | 193 - 264.out | 2 - 265 | 187 - 265.out | 2 - 266 | 71 - 266.out | 133 - 267 | 75 - 267.out | 88 - 268 | 78 - 268.out | 86 - 269 | 85 - 269.out | 5 - 270 | 110 - 270.out | 8 - 271 | 68 - 271.out | 44 - 272 | 109 - 272.out | 3 - 273 | 143 - 273.out | 4 - 274 | 101 - 274.out | 5 - 275 | 93 - 275.out | 5 - 276 | 249 -- 276.out | 4 - 277 | 71 - 277.out | 1 - 278 | 87 - 278.out | 2 - 279 | 120 - 279.out | 35 - 280 | 73 - 280.out | 1 - 281 | 59 - 281.out | 77 - 282 | 71 - 282.out | 133 - 283 | 74 - 283.out | 133 - 284 | 172 - 284.out | 11 - 285 | 58 - 285.full | 116 - 285.out | 1 - 286 | 199 - 286.full | 70 - 286.out | 1 - 287 | 144 - 287.out | 23 - 288 | 58 - 288.out | 6 - 289 | 103 - 289.out | 3 - 290 | 94 - 290.out | 100 - 291 | 128 - 291.out | 1 - 292 | 63 - 292.out | 5 - 293 | 59 - 293.out | 2 - 294 | 73 - 294.out | 5 - 295 | 81 - 295.out | 1 - 296 | 83 - 296.out | 55 - 297 | 88 - 297.out | 3 - 298 | 190 - 298.out | 5 - 299 | 157 - 299.out | 5 - 300 | 153 - 300.out | 4 - 301 | 126 - 301.out | 4 - 302 | 143 - 302.out | 4 - 303 | 153 - 303.out | 4 - 304 | 130 - 304.out | 4 - 305 | 186 - 305.out | 9 - check | 142 +- common | 413 +-- common.attr | 4 +- common.bonnie | 41 - common.config | 3 +- common.dbench | 73 - common.defrag | 4 +- common.dump | 74 +- common.filestreams | 4 +- common.log | 4 +- common.metaperf | 34 - common.quota | 18 +- common.rc | 116 +- common.scsi_debug | 2 +- configs/134.14.54.101.config | 8 - configs/134.14.54.86.config | 8 - configs/bongo.config | 8 - configs/break.config | 10 - configs/bruce.config | 16 - configs/burst.config | 6 - configs/carrot.config | 12 - configs/chapter11.config | 11 - configs/chook.config | 10 - configs/cocky.config | 15 - configs/crackle.config | 7 - configs/cxfsirix1.config | 7 - configs/dassi.config | 8 - configs/dibbler.config | 10 - configs/dmfnt2.config | 10 - configs/dribble.config | 12 - configs/emu.config | 8 - configs/example.config | 15 + configs/flame.config | 9 - configs/frodo.config | 9 - configs/galah.config | 10 - configs/gaspode.config | 13 - configs/giro.config | 11 - configs/goldfish.config | 8 - configs/gonzo1.config | 10 - configs/growler.config | 10 - configs/hammer.config | 7 - configs/hellfire.config | 15 - configs/howler.config | 8 - configs/indra.config | 6 - configs/kermit1.config | 10 - configs/lab343.config | 10 - configs/linux-chatz.config | 12 - configs/lite.config | 8 - configs/localhost.config | 15 + configs/lumpy.config | 6 - configs/mallet.config | 7 - configs/melt.config | 7 - configs/molten.config | 8 - configs/nobbs.config | 13 - configs/permit.config | 6 - configs/puffy.config | 9 - configs/rizzo1.config | 7 - configs/rooster.config | 12 - configs/rosella.config | 12 - configs/scaly.config | 9 - configs/screamer.config | 12 - configs/surly.config | 11 - configs/tinkle.config | 7 - configs/usermode.config | 8 - configs/vimes.config | 12 - group | 354 +-- new | 13 - remake | 72 - run.bonnie_io | 66 - run.bonnie_ops | 84 - run.dbench | 29 - run.dbench10 | 29 - run.dbench100 | 29 - run.dbench2 | 29 - run.dbench20 | 29 - run.dbench50 | 29 - run.dbenchmulti | 37 - run.io | 61 - run.metaperf_10i_1000n | 31 - run.metaperf_10i_1n | 31 - run.metaperf_1i_1n | 30 - run.pio | 69 - run.rtio | 61 - run.tar | 40 - soak | 2 - tests/btrfs/254 | 107 + tests/btrfs/254.out | 40 + tests/btrfs/264 | 192 + tests/btrfs/264.out | 2 + tests/btrfs/265 | 186 + tests/btrfs/265.out | 2 + tests/btrfs/276 | 248 ++ tests/btrfs/276.out | 4 + tests/btrfs/284 | 171 + tests/btrfs/284.out | 11 + tests/btrfs/group | 10 + tests/ext4/271 | 67 + tests/ext4/271.out | 44 + tests/ext4/301 | 127 + tests/ext4/301.out | 4 + tests/ext4/302 | 144 + tests/ext4/302.out | 4 + tests/ext4/303 | 154 + tests/ext4/303.out | 4 + tests/ext4/304 | 131 + tests/ext4/304.out | 4 + tests/ext4/group | 6 + tests/generic/001 | 320 ++ tests/generic/001.out | 9 + tests/generic/002 | 81 + tests/generic/002.out | 2 + tests/generic/005 | 100 + tests/generic/005.out | 8 + tests/generic/006 | 79 + tests/generic/006.out | 11 + tests/generic/007 | 75 + tests/generic/007.out | 22 + tests/generic/010 | 70 + tests/generic/010.out | 58 + tests/generic/011 | 87 + tests/generic/011.out | 4 + tests/generic/013 | 137 + tests/generic/013.out | 14 + tests/generic/014 | 73 + tests/generic/014.out | 6 + tests/generic/015 | 126 + tests/generic/015.out | 7 + tests/generic/020 | 185 + tests/generic/020.out | 65 + tests/generic/053 | 91 + tests/generic/053.out | 24 + tests/generic/062 | 220 ++ tests/generic/062.out | 654 ++++ tests/generic/069 | 80 + tests/generic/069.out | 9 + tests/generic/070 | 68 + tests/generic/070.out | 1 + tests/generic/074 | 186 + tests/generic/074.out | 21 + tests/generic/075 | 162 + tests/generic/075.out | 18 + tests/generic/076 | 84 + tests/generic/076.out | 5 + tests/generic/077 | 85 + tests/generic/077.out | 7 + tests/generic/079 | 69 + tests/generic/079.out | 7 + tests/generic/083 | 102 + tests/generic/083.out | 4 + tests/generic/088 | 57 + tests/generic/088.out.irix | 9 + tests/generic/088.out.linux | 9 + tests/generic/089 | 92 + tests/generic/089.out | 19 + tests/generic/091 | 89 + tests/generic/091.out | 7 + tests/generic/093 | 163 + tests/generic/093.out | Bin 0 -> 917 bytes tests/generic/097 | 258 ++ tests/generic/097.out.udf | 132 + tests/generic/097.out.xfs | 132 + tests/generic/099 | 343 ++ tests/generic/099.out | 215 + tests/generic/100 | 89 + tests/generic/100.out | 1 + tests/generic/105 | 100 + tests/generic/105.out | 3 + tests/generic/112 | 164 + tests/generic/112.out | 18 + tests/generic/113 | 108 + tests/generic/113.out | 22 + tests/generic/117 | 117 + tests/generic/117.out | 15 + tests/generic/120 | 100 + tests/generic/120.out | 10 + tests/generic/123 | 79 + tests/generic/123.out | 7 + tests/generic/124 | 84 + tests/generic/124.out | 1 + tests/generic/125 | 74 + tests/generic/125.out | 7 + tests/generic/126 | 76 + tests/generic/126.out | 19 + tests/generic/127 | 125 + tests/generic/127.out | 13 + tests/generic/128 | 67 + tests/generic/128.out | 1 + tests/generic/129 | 70 + tests/generic/129.out | 1 + tests/generic/130 | 259 ++ tests/generic/130.out | 392 ++ tests/generic/131 | 82 + tests/generic/131.out | 2 + tests/generic/132 | 213 + tests/generic/132.out | 847 ++++ tests/generic/133 | 78 + tests/generic/133.out | 5 + tests/generic/135 | 93 + tests/generic/135.out | 13 + tests/generic/141 | 60 + tests/generic/141.out | 1 + tests/generic/169 | 108 + tests/generic/169.out | 19 + tests/generic/184 | 57 + tests/generic/184.out | 1 + tests/generic/192 | 80 + tests/generic/192.out | 5 + tests/generic/193 | 252 ++ tests/generic/193.out | 51 + tests/generic/198 | 57 + tests/generic/198.out | 2 + tests/generic/204 | 58 + tests/generic/204.out | 2 + tests/generic/207 | 50 + tests/generic/207.out | 2 + tests/generic/208 | 50 + tests/generic/208.out | 2 + tests/generic/209 | 50 + tests/generic/209.out | 2 + tests/generic/210 | 50 + tests/generic/210.out | 2 + tests/generic/211 | 50 + tests/generic/211.out | 2 + tests/generic/212 | 51 + tests/generic/212.out | 2 + tests/generic/213 | 89 + tests/generic/213.out | 4 + tests/generic/214 | 150 + tests/generic/214.out | 51 + tests/generic/215 | 84 + tests/generic/215.out | 8 + tests/generic/219 | 135 + tests/generic/219.out | 37 + tests/generic/221 | 48 + tests/generic/221.out | 2 + tests/generic/223 | 100 + tests/generic/223.out | 251 ++ tests/generic/224 | 86 + tests/generic/224.out | 2 + tests/generic/225 | 78 + tests/generic/225.out | 3 + tests/generic/226 | 78 + tests/generic/226.out | 6 + tests/generic/228 | 86 + tests/generic/228.out | 6 + tests/generic/230 | 146 + tests/generic/230.out | 33 + tests/generic/231 | 120 + tests/generic/231.out | 16 + tests/generic/232 | 93 + tests/generic/232.out | 7 + tests/generic/233 | 102 + tests/generic/233.out | 7 + tests/generic/234 | 107 + tests/generic/234.out | 4 + tests/generic/235 | 79 + tests/generic/235.out | 34 + tests/generic/236 | 69 + tests/generic/236.out | 2 + tests/generic/237 | 79 + tests/generic/237.out | 4 + tests/generic/239 | 57 + tests/generic/239.out | 2 + tests/generic/240 | 75 + tests/generic/240.out | 2 + tests/generic/241 | 59 + tests/generic/241.out | 2 + tests/generic/245 | 72 + tests/generic/245.out | 2 + tests/generic/246 | 59 + tests/generic/246.out | 4 + tests/generic/247 | 79 + tests/generic/247.out | 2 + tests/generic/248 | 57 + tests/generic/248.out | 2 + tests/generic/249 | 65 + tests/generic/249.out | 2 + tests/generic/251 | 184 + tests/generic/251.out | 3 + tests/generic/255 | 67 + tests/generic/255.out | 307 ++ tests/generic/256 | 177 + tests/generic/256.out | 1 + tests/generic/257 | 55 + tests/generic/257.out | 2 + tests/generic/258 | 75 + tests/generic/258.out | 5 + tests/generic/260 | 190 + tests/generic/260.out | 14 + tests/generic/263 | 63 + tests/generic/263.out | 3 + tests/generic/269 | 84 + tests/generic/269.out | 5 + tests/generic/270 | 109 + tests/generic/270.out | 8 + tests/generic/273 | 143 + tests/generic/273.out | 4 + tests/generic/274 | 101 + tests/generic/274.out | 5 + tests/generic/275 | 93 + tests/generic/275.out | 5 + tests/generic/277 | 70 + tests/generic/277.out | 1 + tests/generic/280 | 72 + tests/generic/280.out | 1 + tests/generic/285 | 59 + tests/generic/285.full | 116 + tests/generic/285.out | 1 + tests/generic/286 | 200 + tests/generic/286.full | 70 + tests/generic/286.out | 1 + tests/generic/288 | 59 + tests/generic/288.out | 6 + tests/generic/294 | 74 + tests/generic/294.out | 5 + tests/generic/299 | 158 + tests/generic/299.out | 5 + tests/generic/300 | 154 + tests/generic/300.out | 4 + tests/generic/group | 103 + tests/shared/051 | 367 ++ tests/shared/051.out | 355 ++ tests/shared/068 | 138 + tests/shared/068.out | 43 + tests/shared/218 | 95 + tests/shared/218.out | 19 + tests/shared/243 | 180 + tests/shared/243.out | 13 + tests/shared/272 | 108 + tests/shared/272.out | 3 + tests/shared/289 | 104 + tests/shared/289.out | 3 + tests/shared/298 | 191 + tests/shared/298.out | 5 + tests/shared/305 | 187 + tests/shared/305.out | 9 + tests/shared/group | 10 + tests/udf/098 | 276 ++ tests/udf/098.out | 1594 ++++++++ tests/udf/101 | 62 + tests/udf/101.out | 19 + tests/udf/102 | 59 + tests/udf/102.out | 2 + tests/udf/group | 8 + tests/xfs/003 | 92 + tests/xfs/003.out | 12 + tests/xfs/004 | 143 + tests/xfs/004.out | 9 + tests/xfs/008 | 117 + tests/xfs/008.out | 21 + tests/xfs/009 | 188 + tests/xfs/009.out | 114 + tests/xfs/012 | 122 + tests/xfs/012.out | 16 + tests/xfs/016 | 248 ++ tests/xfs/016.out | 119 + tests/xfs/017 | 94 + tests/xfs/017.out | 10 + tests/xfs/018 | 104 + tests/xfs/018.op.irix | 5628 +++++++++++++++++++++++++++ tests/xfs/018.op.linux | 4714 ++++++++++++++++++++++ tests/xfs/018.out | 17 + tests/xfs/018.trans_buf | 1821 +++++++++ tests/xfs/018.trans_inode | 2609 +++++++++++++ tests/xfs/019 | 149 + tests/xfs/019.out | 84 + tests/xfs/021 | 148 + tests/xfs/021.out | 57 + tests/xfs/022 | 61 + tests/xfs/022.out.irix | 55 + tests/xfs/022.out.linux | 55 + tests/xfs/023 | 56 + tests/xfs/023.out.irix | 89 + tests/xfs/023.out.linux | 89 + tests/xfs/024 | 57 + tests/xfs/024.out | 119 + tests/xfs/025 | 50 + tests/xfs/025.out | 83 + tests/xfs/026 | 48 + tests/xfs/026.out | 73 + tests/xfs/027 | 47 + tests/xfs/027.out | 81 + tests/xfs/028 | 76 + tests/xfs/028.out | 310 ++ tests/xfs/029 | 67 + tests/xfs/029.out | 27 + tests/xfs/030 | 109 + tests/xfs/030.out.irix | 291 ++ tests/xfs/030.out.linux | 250 ++ tests/xfs/031 | 126 + tests/xfs/031.out.irix | 123 + tests/xfs/031.out.linux | 115 + tests/xfs/032 | 90 + tests/xfs/032.out | 2 + tests/xfs/033 | 108 + tests/xfs/033.out.irix | 223 ++ tests/xfs/033.out.linux | 194 + tests/xfs/034 | 91 + tests/xfs/034.out | 5 + tests/xfs/035 | 58 + tests/xfs/035.out.irix | 94 + tests/xfs/035.out.linux | 94 + tests/xfs/036 | 55 + tests/xfs/036.out.irix | 86 + tests/xfs/036.out.linux | 83 + tests/xfs/037 | 51 + tests/xfs/037.out | 83 + tests/xfs/038 | 51 + tests/xfs/038.out | 87 + tests/xfs/039 | 55 + tests/xfs/039.out.irix | 89 + tests/xfs/039.out.linux | 88 + tests/xfs/040 | 61 + tests/xfs/040.good | 16 + tests/xfs/040.out | 2 + tests/xfs/041 | 99 + tests/xfs/041.out | 19 + tests/xfs/042 | 169 + tests/xfs/042.out | 13 + tests/xfs/043 | 59 + tests/xfs/043.out.irix | 104 + tests/xfs/043.out.linux | 104 + tests/xfs/044 | 178 + tests/xfs/044.out | 66 + tests/xfs/045 | 82 + tests/xfs/045.out | 7 + tests/xfs/046 | 49 + tests/xfs/046.out | 37 + tests/xfs/047 | 84 + tests/xfs/047.out | 334 ++ tests/xfs/048 | 55 + tests/xfs/048.out | 5 + tests/xfs/049 | 139 + tests/xfs/049.out | 15 + tests/xfs/050 | 230 ++ tests/xfs/050.out | 193 + tests/xfs/052 | 134 + tests/xfs/052.out | 9 + tests/xfs/054 | 132 + tests/xfs/054.out | 73 + tests/xfs/055 | 55 + tests/xfs/055.out.irix | 89 + tests/xfs/055.out.linux | 88 + tests/xfs/056 | 49 + tests/xfs/056.out | 37 + tests/xfs/057 | 55 + tests/xfs/057.out | 34 + tests/xfs/058 | 46 + tests/xfs/058.out | 243 ++ tests/xfs/059 | 51 + tests/xfs/059.out | 76 + tests/xfs/060 | 57 + tests/xfs/060.out | 120 + tests/xfs/061 | 55 + tests/xfs/061.out | 34 + tests/xfs/063 | 58 + tests/xfs/063.out | 74 + tests/xfs/064 | 110 + tests/xfs/064.out | 1484 +++++++ tests/xfs/065 | 198 + tests/xfs/065.out | 832 ++++ tests/xfs/066 | 74 + tests/xfs/066.out | 40 + tests/xfs/067 | 91 + tests/xfs/067.out | 166 + tests/xfs/071 | 170 + tests/xfs/071.out | 107 + tests/xfs/071.out.32 | 107 + tests/xfs/071.out.64 | 107 + tests/xfs/072 | 83 + tests/xfs/072.out | 2 + tests/xfs/073 | 183 + tests/xfs/073.out | 73 + tests/xfs/078 | 155 + tests/xfs/078.out | 211 + tests/xfs/080 | 74 + tests/xfs/080.out | 3 + tests/xfs/081 | 86 + tests/xfs/081.out | 4 + tests/xfs/081.ugquota.trans_inode | 3091 +++++++++++++++ tests/xfs/082 | 134 + tests/xfs/082.op.irix | 5628 +++++++++++++++++++++++++++ tests/xfs/082.op.linux | 4714 ++++++++++++++++++++++ tests/xfs/082.out | 39 + tests/xfs/082.trans_buf | 1821 +++++++++ tests/xfs/082.trans_inode | 2609 +++++++++++++ tests/xfs/084 | 77 + tests/xfs/084.out | 9 + tests/xfs/085 | 99 + tests/xfs/085.out | 114 + tests/xfs/086 | 152 + tests/xfs/086.out | 4722 ++++++++++++++++++++++ tests/xfs/087 | 153 + tests/xfs/087.out | 389 ++ tests/xfs/090 | 128 + tests/xfs/090.out | 18 + tests/xfs/092 | 61 + tests/xfs/092.out | 8 + tests/xfs/094 | 115 + tests/xfs/094.out | 12 + tests/xfs/095 | 69 + tests/xfs/095.out | 6 + tests/xfs/096 | 151 + tests/xfs/096.external | 53 + tests/xfs/096.internal | 55 + tests/xfs/103 | 102 + tests/xfs/103.out | 22 + tests/xfs/104 | 119 + tests/xfs/104.out | 127 + tests/xfs/106 | 239 ++ tests/xfs/106.out | 379 ++ tests/xfs/107 | 154 + tests/xfs/107.out | 1550 ++++++++ tests/xfs/108 | 124 + tests/xfs/108.out | 101 + tests/xfs/109 | 112 + tests/xfs/109.out | 12 + tests/xfs/110 | 87 + tests/xfs/110.out | 37 + tests/xfs/111 | 71 + tests/xfs/111.out | 100 + tests/xfs/114 | 346 ++ tests/xfs/114.out | 365 ++ tests/xfs/115 | 259 ++ tests/xfs/115.out | 118 + tests/xfs/116 | 66 + tests/xfs/116.out | 3 + tests/xfs/118 | 95 + tests/xfs/118.out | 9 + tests/xfs/119 | 76 + tests/xfs/119.out | 3 + tests/xfs/121 | 114 + tests/xfs/121.out | 15 + tests/xfs/122 | 221 ++ tests/xfs/122.out | 123 + tests/xfs/134 | 119 + tests/xfs/134.out | 5 + tests/xfs/136 | 361 ++ tests/xfs/136.out | 7753 +++++++++++++++++++++++++++++++++++++ tests/xfs/137 | 110 + tests/xfs/137.out | 1 + tests/xfs/138 | 116 + tests/xfs/138.out | 1 + tests/xfs/139 | 116 + tests/xfs/139.out | 1 + tests/xfs/140 | 113 + tests/xfs/140.out | 1 + tests/xfs/142 | 58 + tests/xfs/142.out | 232 ++ tests/xfs/143 | 58 + tests/xfs/143.out | 98 + tests/xfs/144 | 58 + tests/xfs/144.out | 245 ++ tests/xfs/145 | 58 + tests/xfs/145.out | 36 + tests/xfs/146 | 68 + tests/xfs/146.out.irix | 324 ++ tests/xfs/146.out.linux | 320 ++ tests/xfs/147 | 58 + tests/xfs/147.out | 29 + tests/xfs/148 | 110 + tests/xfs/148.out | 299 ++ tests/xfs/149 | 128 + tests/xfs/149.out | 123 + tests/xfs/150 | 69 + tests/xfs/150.out | 5 + tests/xfs/151 | 114 + tests/xfs/151.out | 22 + tests/xfs/152 | 63 + tests/xfs/152.out | 10 + tests/xfs/153 | 70 + tests/xfs/153.out | 8 + tests/xfs/154 | 57 + tests/xfs/154.out | 21 + tests/xfs/155 | 89 + tests/xfs/155.out | 8 + tests/xfs/156 | 56 + tests/xfs/156.out | 1 + tests/xfs/157 | 58 + tests/xfs/157.out | 2 + tests/xfs/158 | 103 + tests/xfs/158.out | 6 + tests/xfs/159 | 70 + tests/xfs/159.out | 5 + tests/xfs/160 | 80 + tests/xfs/160.out | 11 + tests/xfs/161 | 69 + tests/xfs/161.out | 12 + tests/xfs/162 | 86 + tests/xfs/162.out | 12 + tests/xfs/163 | 71 + tests/xfs/163.out | 3 + tests/xfs/164 | 157 + tests/xfs/164.out | 35 + tests/xfs/165 | 129 + tests/xfs/165.out | 1581 ++++++++ tests/xfs/166 | 99 + tests/xfs/166.out | 6 + tests/xfs/167 | 81 + tests/xfs/167.out | 3 + tests/xfs/168 | 114 + tests/xfs/168.out | 57 + tests/xfs/170 | 67 + tests/xfs/170.out | 21 + tests/xfs/171 | 70 + tests/xfs/171.out | 21 + tests/xfs/172 | 64 + tests/xfs/172.out | 11 + tests/xfs/173 | 67 + tests/xfs/173.out | 21 + tests/xfs/174 | 63 + tests/xfs/174.out | 11 + tests/xfs/175 | 71 + tests/xfs/175.out | 63 + tests/xfs/176 | 77 + tests/xfs/176.out | 121 + tests/xfs/177 | 85 + tests/xfs/177.out | 88 + tests/xfs/178 | 102 + tests/xfs/178.out | 79 + tests/xfs/179 | 111 + tests/xfs/179.out | 1 + tests/xfs/180 | 115 + tests/xfs/180.out | 1 + tests/xfs/181 | 128 + tests/xfs/181.out | 15 + tests/xfs/182 | 112 + tests/xfs/182.out | 1 + tests/xfs/183 | 67 + tests/xfs/183.out | 4 + tests/xfs/185 | 87 + tests/xfs/185.out | 71 + tests/xfs/186 | 184 + tests/xfs/186.out | 290 ++ tests/xfs/187 | 138 + tests/xfs/187.out | 39 + tests/xfs/188 | 88 + tests/xfs/188.out | 65 + tests/xfs/189 | 225 ++ tests/xfs/189.out | 59 + tests/xfs/190 | 100 + tests/xfs/190.out | 4 + tests/xfs/191 | 75 + tests/xfs/191.out | 324 ++ tests/xfs/194 | 218 ++ tests/xfs/194.out | 59 + tests/xfs/195 | 87 + tests/xfs/195.out | 8 + tests/xfs/196 | 98 + tests/xfs/196.out | 2002 ++++++++++ tests/xfs/197 | 66 + tests/xfs/197.out | 2 + tests/xfs/199 | 91 + tests/xfs/199.out | 13 + tests/xfs/200 | 126 + tests/xfs/200.out | 24 + tests/xfs/201 | 99 + tests/xfs/201.out | 2 + tests/xfs/202 | 61 + tests/xfs/202.out | 29 + tests/xfs/203 | 90 + tests/xfs/203.out | 427 ++ tests/xfs/205 | 83 + tests/xfs/205.out | 4 + tests/xfs/206 | 100 + tests/xfs/206.out | 30 + tests/xfs/216 | 78 + tests/xfs/216.out | 10 + tests/xfs/217 | 90 + tests/xfs/217.out | 7 + tests/xfs/220 | 84 + tests/xfs/220.out | 2 + tests/xfs/222 | 56 + tests/xfs/222.out | 2 + tests/xfs/227 | 210 + tests/xfs/227.out | 2 + tests/xfs/229 | 87 + tests/xfs/229.out | 4 + tests/xfs/238 | 56 + tests/xfs/238.out | 2 + tests/xfs/242 | 63 + tests/xfs/242.out | 77 + tests/xfs/244 | 137 + tests/xfs/244.out | 2 + tests/xfs/250 | 96 + tests/xfs/250.out | 14 + tests/xfs/252 | 66 + tests/xfs/252.out | 307 ++ tests/xfs/253 | 193 + tests/xfs/253.out | 2 + tests/xfs/259 | 66 + tests/xfs/259.out | 7 + tests/xfs/261 | 117 + tests/xfs/261.out | 2 + tests/xfs/262 | 144 + tests/xfs/262.out | 2 + tests/xfs/266 | 70 + tests/xfs/266.out | 133 + tests/xfs/267 | 74 + tests/xfs/267.out | 88 + tests/xfs/268 | 77 + tests/xfs/268.out | 86 + tests/xfs/278 | 86 + tests/xfs/278.out | 2 + tests/xfs/279 | 119 + tests/xfs/279.out | 35 + tests/xfs/281 | 58 + tests/xfs/281.out | 77 + tests/xfs/282 | 70 + tests/xfs/282.out | 133 + tests/xfs/283 | 73 + tests/xfs/283.out | 133 + tests/xfs/287 | 145 + tests/xfs/287.out | 23 + tests/xfs/290 | 95 + tests/xfs/290.out | 100 + tests/xfs/291 | 129 + tests/xfs/291.out | 1 + tests/xfs/292 | 64 + tests/xfs/292.out | 5 + tests/xfs/293 | 60 + tests/xfs/293.out | 2 + tests/xfs/295 | 82 + tests/xfs/295.out | 1 + tests/xfs/296 | 84 + tests/xfs/296.out | 55 + tests/xfs/297 | 89 + tests/xfs/297.out | 3 + tests/xfs/group | 175 + 1367 files changed, 105293 insertions(+), 106967 deletions(-) From pwhite@sgi.com Thu Mar 14 08:06:20 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from cthulhu.engr.sgi.com (cthulhu.engr.sgi.com [150.166.39.100]) by oss.sgi.com (Postfix) with ESMTP id 5D21C7F5D for ; Thu, 14 Mar 2013 08:06:12 -0500 (CDT) Received: from polaris-admin.engr.sgi.com (polaris-admin.engr.sgi.com [150.166.41.54]) by cthulhu.engr.sgi.com (8.12.10/8.12.10/SuSE Linux 0.7) with ESMTP id r2ED6Bx7007464 for ; Thu, 14 Mar 2013 06:06:11 -0700 Received: by polaris-admin.engr.sgi.com (Postfix, from userid 48024) id 8429C53DEAF6; Thu, 14 Mar 2013 06:06:11 -0700 (PDT) Date: Thu, 14 Mar 2013 06:06:11 -0700 To: xfs@oss.sgi.com Subject: [PATCH 09/18] xfstests: create tests subdirectory User-Agent: nail 11.25 7/29/05 MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Transfer-Encoding: 7bit Message-Id: <20130314130611.8429C53DEAF6@polaris-admin.engr.sgi.com> From: pwhite@sgi.com (Philip White) From: Phil White This is a rebasing & resubmit of a dchinner patch. His comments on the original: ----------------- Create a specific tests/ subdirectory to hold all the tests so they are no longer need to be in the top level directory. This patch does not move any tests there, however, and that will be done in subsequent commits. The tests/ subdir will have it's own subdirectories for different classes of tests. Initially, there will be a per-FSTYP subdirectory for filesytsem specific tests, and a generic directory for tests that span multiple filesystems. Each class will have it's own group file to indicate what groups the tests belong to, and these will be parsed appropriately by the high level check script to build the test list. The change in parsing results in the test output also emitting the path to the test as well as the name of the test, instead of just a raw number. This allows duplicate test names in the sudirecotries to be unambiguous when the summary is written out. ----------------- Signed-off-by: Phil White --- check | 26 +++++++++++++++++--------- common | 40 ++++++++++++++++++++++------------------ group | 5 ----- tests/generic/group | 5 +++++ 4 files changed, 44 insertions(+), 32 deletions(-) create mode 100644 tests/generic/group diff --git a/check b/check index 37d1d2f..dea63d7 100755 --- a/check +++ b/check @@ -97,7 +97,7 @@ END { if (NR > 0) { echo "" >>check.log date >>check.log - echo $list | fmt | sed -e 's/^/ /' >>check.log + echo $list | fmt | sed -e 's/^/ /' -e 's;tests/;;g' >>check.log $interrupt && echo "Interrupted!" >>check.log if [ ! -z "$n_try" -a $n_try != 0 ] @@ -175,7 +175,12 @@ _check_test_fs for seq in $list do err=false - echo -n "$seq" + + # the filename for the test and the name output are different. + # we don't include the tests/ directory in the name output. + seqnum=`echo $seq | sed -e 's;tests/;;'` + + echo -n "$seqnum" if $showme then @@ -188,7 +193,10 @@ do # really going to try and run this one # rm -f $seq.out.bad - lasttime=`sed -n -e "/^$seq /s/.* //p" >$tmp.time + echo "$seqnum `expr $stop - $start`" >>$tmp.time echo -n " `expr $stop - $start`s" fi echo "" @@ -266,18 +274,18 @@ do # if $err then - bad="$bad $seq" + bad="$bad $seqnum" n_bad=`expr $n_bad + 1` quick=false fi if [ ! -f $seq.notrun ] then - try="$try $seq" + try="$try $seqnum" n_try=`expr $n_try + 1` _check_test_fs fi - seq="after_$seq" + seq="after_$seqnum" done interrupt=false diff --git a/common b/common index 821ea59..b41d4d0 100644 --- a/common +++ b/common @@ -21,6 +21,21 @@ # $Header: /disk7/depot/linux/pcp/dev/qa/RCS/common,v 2.52 2000/04/05 18:24:51 kenmcd Exp $ # +here=`pwd` +check=${check-true} +diff="`which diff`" +verbose=false +group=false +xgroup=false +showme=false +sortme=false +have_test_arg=false +randomize=false +timestamp=${TIMESTAMP:=false} +SUPPORTED_TESTS="[0-9][0-9][0-9] [0-9][0-9][0-9][0-9]" +TEST_GROUP_DIR="tests" +GENERIC_GROUP_DIR="$TEST_GROUP_DIR/generic" + _setenvironment() { MSGVERB="text:action" @@ -30,10 +45,15 @@ _setenvironment() get_group_list() { grp=$1 - grpl=$(sed -n < group \ + dirs=". $GENERIC_GROUP_DIR" + + for d in $dirs; do + l=$(sed -n < $d/group \ -e 's/#.*//' \ -e 's/$/ /' \ - -e "/^[0-9][0-9][0-9].* $grp /"'{ s/ .*//p }') + -e "s;\(^[0-9][0-9][0-9]\).* $grp .*;$d/\1;p") + grpl="$grpl $l" + done echo $grpl } @@ -67,22 +87,6 @@ _timestamp() echo -n " [$now]" } -here=`pwd` - -check=${check-true} - -diff="`which diff`" -verbose=false -group=false -xgroup=false -showme=false -sortme=false -have_test_arg=false -randomize=false -timestamp=${TIMESTAMP:=false} - -SUPPORTED_TESTS="[0-9][0-9][0-9] [0-9][0-9][0-9][0-9]" - # start the initialisation work now _setenvironment rm -f $tmp.list $tmp.tmp $tmp.sed $here/$iam.out diff --git a/group b/group index c9b733f..484bed5 100644 --- a/group +++ b/group @@ -1,8 +1,3 @@ -# QA groups control file -# Defines test groups and nominal group owners -# - do not start group names with a digit -# - comment line before each group is "new" description -# # catch-all other diff --git a/tests/generic/group b/tests/generic/group new file mode 100644 index 0000000..4e01f0c --- /dev/null +++ b/tests/generic/group @@ -0,0 +1,5 @@ +# QA groups control file +# Defines test groups and nominal group owners +# - do not start group names with a digit +# - comment line before each group is "new" description +# -- 1.5.3.8 From pwhite@sgi.com Thu Mar 14 08:06:18 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from cthulhu.engr.sgi.com (cthulhu.engr.sgi.com [150.166.39.100]) by oss.sgi.com (Postfix) with ESMTP id 039797F52 for ; Thu, 14 Mar 2013 08:06:11 -0500 (CDT) Received: from polaris-admin.engr.sgi.com (polaris-admin.engr.sgi.com [150.166.41.54]) by cthulhu.engr.sgi.com (8.12.10/8.12.10/SuSE Linux 0.7) with ESMTP id r2ED6Bx7007451 for ; Thu, 14 Mar 2013 06:06:11 -0700 Received: by polaris-admin.engr.sgi.com (Postfix, from userid 48024) id 4A3C153DEAF1; Thu, 14 Mar 2013 06:06:11 -0700 (PDT) Date: Thu, 14 Mar 2013 06:06:11 -0700 To: xfs@oss.sgi.com Subject: [PATCH 02/18] xfstests: Clear out old benchmarking materials User-Agent: nail 11.25 7/29/05 MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Transfer-Encoding: 7bit Message-Id: <20130314130611.4A3C153DEAF1@polaris-admin.engr.sgi.com> From: pwhite@sgi.com (Philip White) From: Phil White This is a rebasing & resubmit of a dchinner patch. His comments on the original: ----------------- The benchmark framework inside xfstests is basically unused, bitrotted and not very useful. If we need benchmarks, lets use a real benchmark framework, not xfstests. Kill it to remove dependencies on common and common.rc. ----------------- The current benchmark framework has bitrotted, but it is not without value in my view. It should be removed and updated. In the interest of future useability, I have kept the dependencies on common and common.rc. Signed-off-by: Phil White --- common.bonnie | 41 ----------------------- common.config | 3 +- common.dbench | 73 ----------------------------------------- common.metaperf | 34 ------------------- common.rc | 2 +- run.bonnie_io | 66 ------------------------------------- run.bonnie_ops | 84 ------------------------------------------------ run.dbench | 29 ---------------- run.dbench10 | 29 ---------------- run.dbench100 | 29 ---------------- run.dbench2 | 29 ---------------- run.dbench20 | 29 ---------------- run.dbench50 | 29 ---------------- run.dbenchmulti | 37 --------------------- run.io | 61 ---------------------------------- run.metaperf_10i_1000n | 31 ----------------- run.metaperf_10i_1n | 31 ----------------- run.metaperf_1i_1n | 30 ----------------- run.pio | 69 --------------------------------------- run.rtio | 61 ---------------------------------- run.tar | 40 ----------------------- 21 files changed, 2 insertions(+), 835 deletions(-) delete mode 100644 common.bonnie delete mode 100755 common.dbench delete mode 100755 common.metaperf delete mode 100755 run.bonnie_io delete mode 100755 run.bonnie_ops delete mode 100755 run.dbench delete mode 100755 run.dbench10 delete mode 100755 run.dbench100 delete mode 100755 run.dbench2 delete mode 100755 run.dbench20 delete mode 100755 run.dbench50 delete mode 100755 run.dbenchmulti delete mode 100755 run.io delete mode 100755 run.metaperf_10i_1000n delete mode 100755 run.metaperf_10i_1n delete mode 100755 run.metaperf_1i_1n delete mode 100755 run.pio delete mode 100755 run.rtio delete mode 100755 run.tar diff --git a/common.bonnie b/common.bonnie deleted file mode 100644 index 96ca700..0000000 --- a/common.bonnie +++ /dev/null @@ -1,41 +0,0 @@ -##/bin/bash -# -# Copyright (c) 2002-2004 Silicon Graphics, Inc. All Rights Reserved. -# -# This program is free software; you can redistribute it and/or -# modify it under the terms of the GNU General Public License as -# published by the Free Software Foundation. -# -# This program is distributed in the hope that it would be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program; if not, write the Free Software Foundation, -# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA -# - -#check bonnie is installed -if [ "`whereis bonnie++`" == "bonnie++:"]; then - echo $0 error bonnie not installed. - exit -fi - -run_bonnie() -{ - # dir, no hostname, quiet, fast (no per-char), ram (no sz checks) - tmp=/var/tmp - - mkdir ./bonnie || exit 1 - defaults="-d ./bonnie -q -f -r 0" - defaults="$defaults -u "`id -u`" -g "`id -g` - bonnie++ -m '' $defaults $@ >$tmp/$$.bonnie.stdout 2>$tmp/$$.bonnie.stderr - status=$? - rm -fr ./bonnie - [ $status -ne 0 ] && exit 1 - filter_stdout < $tmp/$$.bonnie.stdout - filter_stderr < $tmp/$$.bonnie.stderr 1>&2 - rm -f $tmp/$$.bonnie.stdout $tmp/$$.bonnie.stderr - exit 0 -} diff --git a/common.config b/common.config index ed0f44c..e0041a5 100644 --- a/common.config +++ b/common.config @@ -40,7 +40,7 @@ # below or a separate local configuration file can be used (using # the HOST_OPTIONS variable). # - This script is shared by the stress test system and the auto-qa -# system (includes both regression test and benchmark components). +# system # - TEST_DEV & TEST_DIR must be assigned. # - this script shouldn't make any assertions about filesystem # validity or mountedness. @@ -163,7 +163,6 @@ export XFS_PARALLEL_REPAIR64_PROG="`set_prog_path xfs_prepair64`" export XFSDUMP_PROG="`set_prog_path xfsdump`" export XFSRESTORE_PROG="`set_prog_path xfsrestore`" export XFSINVUTIL_PROG="`set_prog_path xfsinvutil`" -export DBENCH_PROG="`set_prog_path dbench`" export GETFATTR_PROG="`set_prog_path getfattr`" export SETFATTR_PROG="`set_prog_path setfattr`" export ATTR_PROG="`set_prog_path attr`" diff --git a/common.dbench b/common.dbench deleted file mode 100755 index b59be71..0000000 --- a/common.dbench +++ /dev/null @@ -1,73 +0,0 @@ -##/bin/bash -# -# Copyright (c) 2002-2005 Silicon Graphics, Inc. All Rights Reserved. -# -# This program is free software; you can redistribute it and/or -# modify it under the terms of the GNU General Public License as -# published by the Free Software Foundation. -# -# This program is distributed in the hope that it would be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program; if not, write the Free Software Foundation, -# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA -# - -#check dbench is installed -if [ "`whereis dbench`" == "dbench:" ]; then - echo $0 error dbench not installed. - exit -fi - -_run_dbench() -{ - mkdir ./dbench || exit 1 - cd dbench - dbench -x $1 - status=$? - cd .. - rm -fr ./dbench - [ $status -ne 0 ] && exit 1 -} - -# -# Sample dbench output: -# "Throughput 40.6701 MB/sec (NB=50.8376 MB/sec 406.701 MBit/sec)" -# - -# Output for a single-shot dbench run. -_format_header() -{ - printf "%8s, %s\n" clients MB/sec -} -_filter_dbench() -{ - clients=$1 - perl -ne 'm/Throughput (\S+) MB\/sec/ && - { printf "%8u, %s\n", '$clients', $1 }' -} - -# Output for a "multipass" dbench run. -_format_header_multipass() -{ - while [ $# -gt 1 ]; do - printf "%4s::MB/sec," $1 - shift - done - printf "%4s::MB/sec\n" $1 -} -_filter_dbench_multipass() -{ - perl -ne ' - if (m/Throughput (\S+) MB\/sec/) { - $results[$count++] = $1; - } - END { for ($i = 0; $i < $count - 1; $i++) { - printf "%12.3f,", $results[$i]; - } - printf "%12.3f\n", $results[$count-1]; - }' -} diff --git a/common.metaperf b/common.metaperf deleted file mode 100755 index 9def379..0000000 --- a/common.metaperf +++ /dev/null @@ -1,34 +0,0 @@ -##/bin/bash -# -# Copyright (c) 2003-2005 Silicon Graphics, Inc. All Rights Reserved. -# -# This program is free software; you can redistribute it and/or -# modify it under the terms of the GNU General Public License as -# published by the Free Software Foundation. -# -# This program is distributed in the hope that it would be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program; if not, write the Free Software Foundation, -# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA -# - -_format_metaperf() -{ - perl -ne 'm/(\S+): (\d+) times, (\d+) file\(s\) namelen (\d+), time = (\S+) sec, ops\/sec=(\S+), usec\/op = (\S+)/ && { $op{$1} = $7 }; - END { printf "%8.2f,%8.2f,%8.2f,%8.2f,%8.2f,%8.2f,%8.2f,%8.2f\n", - $op{"chown"}, $op{"create"}, $op{"crunlink"}, $op{"linkun"}, - $op{"open"}, $op{"rename"}, $op{"stat"}, $op{"readdir"} }' -} - -_format_header() -{ - # note: we're reporting only the usec/op field - printf "%8s,%8s,%8s,%8s,%8s,%8s,%8s,%8s\n" \ - chown create crulink linkun open rename stat readdir -} - -allops="chown create crunlink linkun open rename stat readdir" diff --git a/common.rc b/common.rc index ef41cbf..4214b3c 100644 --- a/common.rc +++ b/common.rc @@ -1895,7 +1895,7 @@ run_check() ################################################################################ -if [ "$iam" != new -a "$iam" != bench ] +if [ "$iam" != new ] then # make some further configuration checks here diff --git a/run.bonnie_io b/run.bonnie_io deleted file mode 100755 index e108650..0000000 --- a/run.bonnie_io +++ /dev/null @@ -1,66 +0,0 @@ -#!/bin/bash -# -# Copyright (c) 2002-2003 Silicon Graphics, Inc. All Rights Reserved. -# -# This program is free software; you can redistribute it and/or -# modify it under the terms of the GNU General Public License as -# published by the Free Software Foundation. -# -# This program is distributed in the hope that it would be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program; if not, write the Free Software Foundation, -# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA -# -# -# Does a bonnie throughput run (80M file and 1K chunksize if the -# BONNIE_FILESIZE and/or BONNIE_CHUNKSIZE variables are not set), -# then massages the output into CSV format with the human-readable -# output preceding it as a "comment" (ie. #-prefixed). -# -BONNIE_FILESIZE=${BONNIE_FILESIZE:=500M} -BONNIE_CHUNKSIZE=${BONNIE_CHUNKSIZE:=1K} - -[ -z "$here" ] && here=`pwd` -. $here/common.bonnie - -# -# Sample bonnie throughput output (stderr): -#Version 1.02c ------Sequential Output------ --Sequential Input- --Random- -# -Per Chr- --Block-- -Rewrite- -Per Chr- --Block-- --Seeks-- -#Machine Size:chnk K/sec %CP K/sec %CP K/sec %CP K/sec %CP K/sec %CP /sec %CP -# 150M:64k 52024 99 88969 99 245492 100 3746 264 -# -filter_stderr() -{ - sed -e 's/^..................../# /g' | awk '{print} END {print "#"}' -} - -# -# Sample bonnie throughput output (stdout): -# ",150M:64k,,,52024,99,88969,99,,,245492,100,3746.0,264,,,,,,,,,,,,," -# -filter_stdout() -{ - perl -ne ' - chomp; - s/,+/,/g; s/^,//; s/,$//; - @values = split /,/; - printf "%9s", shift @values; - for ($i = 0; $i <= $#values; $i++) { - if ($i % 2) { printf ",%4s%%", $values[$i] } - else { printf ",%10s", $values[$i] } - } - printf "\n"; - ' -} - -if [ $# -gt 0 ]; then - printf "%9s,%10s,%5s,%10s,%5s,%10s,%5s,%10s,%5s\n" size:chnk \ - writeK/s wCPU rewriteK/s rwCPU readK/s rCPU seek/s sCPU - exit 0 -fi -run_bonnie -n 0 -s $BONNIE_FILESIZE:$BONNIE_CHUNKSIZE diff --git a/run.bonnie_ops b/run.bonnie_ops deleted file mode 100755 index 609b93c..0000000 --- a/run.bonnie_ops +++ /dev/null @@ -1,84 +0,0 @@ -#!/bin/bash -# -# Copyright (c) 2002-2003 Silicon Graphics, Inc. All Rights Reserved. -# -# This program is free software; you can redistribute it and/or -# modify it under the terms of the GNU General Public License as -# published by the Free Software Foundation. -# -# This program is distributed in the hope that it would be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program; if not, write the Free Software Foundation, -# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA -# -# -# Do a bonnie++ create/read/delete run using 8192 files (unless -# BONNIE_KFILES environment variable is set -- note this number -# is multiplied by 1024 by bonnie++). By default the files are -# created in the same directory, BONNIE_NDIRS specifies a count -# of subdirs to evenly spread files through. Regular files are -# created by default (BONNIE_FILETYPE=regular), alternatively -# the values "symlinks" and "hardlinks" can be used. -# -# The script then massages the output into CSV format with the -# human-readable output preceding it as a "comment" (#-prefixed). -# -BONNIE_NDIRS=${BONNIE_NDIRS:=1} -BONNIE_KFILES=${BONNIE_KFILES:=8} -BONNIE_FILETYPE=${BONNIE_FILETYPE:=regular} - -[ -z "$here" ] && here=`pwd` -. $here/common.bonnie - -# -# Sample bonnie throughput output (stderr): -#Version 1.02c ------Sequential Create------ --------Random Create-------- -# -Create-- --Read--- -Delete-- -Create-- --Read--- -Delete-- -# files /sec %CP /sec %CP /sec %CP /sec %CP /sec %CP /sec %CP -# 4 525 27 +++++ +++ 517 26 526 25 +++++ +++ 230 12 -# [ Note: the "files" can also be "^files:max" and possibly other things ] -filter_stderr() -{ - sed -e 's/^..................../# /g' | awk '{print} END {print "#"}' -} - -# -# Sample bonnie IOPs output (stdout): -# ",,,,,,,,,,,,,,4,525,27,+++++,+++,517,26,526,25,+++++,+++,230,12" -# [ nathans note: always get +++ due to 0:0 for min:max file sizes. ] -# [ I will need to fix the filter if I ever start using file sizes. ] -# -filter_stdout() -{ - perl -ne ' - chomp; - s/\+*//g; s/,+/,/g; s/^,//; s/,$//; - @values = split /,/; - printf "%9s", 1024 * shift @values; - for ($i = 0; $i <= $#values; $i++) { - if ($i % 2) { printf ",%4s%%", $values[$i] } - else { printf ",%10s", $values[$i] } - } - printf "\n"; - ' -} - -if [ $# -gt 0 ]; then - printf "%9s,%10s,%5s,%10s,%5s,%10s,%5s,%10s,%5s\n" files \ - seqCR/s scCPU seqRM/s srCPU randCR/s rcCPU randRM/s rrCPU - exit 0 -fi - -case "$BONNIE_FILETYPE" -in - regular) BONNIE_FILETYPE=0 ;; - symlink) BONNIE_FILETYPE=-2 ;; - hardlink) BONNIE_FILETYPE=-1 ;; - *) echo "BONNIE_FILETYPE has an unrecognised value" && exit 1 ;; -esac - -run_bonnie -s 0 -n $BONNIE_KFILES:$BONNIE_FILETYPE:0:$BONNIE_NDIRS diff --git a/run.dbench b/run.dbench deleted file mode 100755 index 8e86807..0000000 --- a/run.dbench +++ /dev/null @@ -1,29 +0,0 @@ -#!/bin/bash -# -# Copyright (c) 2002-2003 Silicon Graphics, Inc. All Rights Reserved. -# -# This program is free software; you can redistribute it and/or -# modify it under the terms of the GNU General Public License as -# published by the Free Software Foundation. -# -# This program is distributed in the hope that it would be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program; if not, write the Free Software Foundation, -# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA -# -# -# Does a single-client dbench run -# - -[ -z "$here" ] && here=`pwd` -. $here/common.dbench - -if [ $# -gt 0 ]; then - _format_header - exit 0 -fi -_run_dbench 1 | _filter_dbench 1 diff --git a/run.dbench10 b/run.dbench10 deleted file mode 100755 index e3a08c4..0000000 --- a/run.dbench10 +++ /dev/null @@ -1,29 +0,0 @@ -#!/bin/bash -# -# Copyright (c) 2002-2003 Silicon Graphics, Inc. All Rights Reserved. -# -# This program is free software; you can redistribute it and/or -# modify it under the terms of the GNU General Public License as -# published by the Free Software Foundation. -# -# This program is distributed in the hope that it would be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program; if not, write the Free Software Foundation, -# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA -# -# -# Does a dbench run with 10 clients -# - -[ -z "$here" ] && here=`pwd` -. $here/common.dbench - -if [ $# -gt 0 ]; then - _format_header - exit 0 -fi -_run_dbench 10 | _filter_dbench 10 diff --git a/run.dbench100 b/run.dbench100 deleted file mode 100755 index 51708d1..0000000 --- a/run.dbench100 +++ /dev/null @@ -1,29 +0,0 @@ -#!/bin/bash -# -# Copyright (c) 2002-2003 Silicon Graphics, Inc. All Rights Reserved. -# -# This program is free software; you can redistribute it and/or -# modify it under the terms of the GNU General Public License as -# published by the Free Software Foundation. -# -# This program is distributed in the hope that it would be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program; if not, write the Free Software Foundation, -# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA -# -# -# Does a dbench run with 100 clients -# - -[ -z "$here" ] && here=`pwd` -. $here/common.dbench - -if [ $# -gt 0 ]; then - _format_header - exit 0 -fi -_run_dbench 100 | _filter_dbench 100 diff --git a/run.dbench2 b/run.dbench2 deleted file mode 100755 index c56c208..0000000 --- a/run.dbench2 +++ /dev/null @@ -1,29 +0,0 @@ -#!/bin/bash -# -# Copyright (c) 2002-2003 Silicon Graphics, Inc. All Rights Reserved. -# -# This program is free software; you can redistribute it and/or -# modify it under the terms of the GNU General Public License as -# published by the Free Software Foundation. -# -# This program is distributed in the hope that it would be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program; if not, write the Free Software Foundation, -# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA -# -# -# Does a dbench run with 2 clients -# - -[ -z "$here" ] && here=`pwd` -. $here/common.dbench - -if [ $# -gt 0 ]; then - _format_header - exit 0 -fi -_run_dbench 2 | _filter_dbench 2 diff --git a/run.dbench20 b/run.dbench20 deleted file mode 100755 index 81f713c..0000000 --- a/run.dbench20 +++ /dev/null @@ -1,29 +0,0 @@ -#!/bin/bash -# -# Copyright (c) 2003 Silicon Graphics, Inc. All Rights Reserved. -# -# This program is free software; you can redistribute it and/or -# modify it under the terms of the GNU General Public License as -# published by the Free Software Foundation. -# -# This program is distributed in the hope that it would be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program; if not, write the Free Software Foundation, -# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA -# -# -# Does a dbench run with 20 clients -# - -[ -z "$here" ] && here=`pwd` -. $here/common.dbench - -if [ $# -gt 0 ]; then - _format_header - exit 0 -fi -_run_dbench 20 | _filter_dbench 20 diff --git a/run.dbench50 b/run.dbench50 deleted file mode 100755 index 4c54e0b..0000000 --- a/run.dbench50 +++ /dev/null @@ -1,29 +0,0 @@ -#!/bin/bash -# -# Copyright (c) 2002-2003 Silicon Graphics, Inc. All Rights Reserved. -# -# This program is free software; you can redistribute it and/or -# modify it under the terms of the GNU General Public License as -# published by the Free Software Foundation. -# -# This program is distributed in the hope that it would be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program; if not, write the Free Software Foundation, -# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA -# -# -# Does a dbench run with 50 clients -# - -[ -z "$here" ] && here=`pwd` -. $here/common.dbench - -if [ $# -gt 0 ]; then - _format_header - exit 0 -fi -_run_dbench 50 | _filter_dbench 50 diff --git a/run.dbenchmulti b/run.dbenchmulti deleted file mode 100755 index 317a100..0000000 --- a/run.dbenchmulti +++ /dev/null @@ -1,37 +0,0 @@ -#!/bin/bash -# -# Copyright (c) 2003 Silicon Graphics, Inc. All Rights Reserved. -# -# This program is free software; you can redistribute it and/or -# modify it under the terms of the GNU General Public License as -# published by the Free Software Foundation. -# -# This program is distributed in the hope that it would be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program; if not, write the Free Software Foundation, -# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA -# -# -# Does several dbench runs with increasing numbers of client -# - -[ -z "$here" ] && here=`pwd` -. $here/common.dbench - -if [ $# -gt 0 ]; then - _format_header_multipass 1 2 10 20 #50 - exit 0 -fi -tmpfile=/var/tmp/dbench.$$ -rm -f $tmpfile -_run_dbench 1 >> $tmpfile -_run_dbench 2 >> $tmpfile -_run_dbench 10 >> $tmpfile -_run_dbench 20 >> $tmpfile -#_run_dbench 50 >> $tmpfile -_filter_dbench_multipass < $tmpfile -rm -f $tmpfile diff --git a/run.io b/run.io deleted file mode 100755 index 91e3b93..0000000 --- a/run.io +++ /dev/null @@ -1,61 +0,0 @@ -#!/bin/bash -# -# Copyright (c) 2005 Silicon Graphics, Inc. All Rights Reserved. -# -# This program is free software; you can redistribute it and/or -# modify it under the terms of the GNU General Public License as -# published by the Free Software Foundation. -# -# This program is distributed in the hope that it would be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program; if not, write the Free Software Foundation, -# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA -# -# -# (very) simple file IO tests. -# TODO: make file size multiple of physmem. - -filesize=1g -iosize=64k - -if [ $# -gt 0 ]; then - printf "%s,%s,%s,%s,%s\n" type bytes ops time bytes/sec ops/sec - exit 0 -fi - -# buffered write -echo -n bwrite, -xfs_io iofile -Fft -c "pwrite -C -b $iosize 0 $filesize" - -# direct write -echo -n dwrite, -xfs_io iofile -Fftd -c "pwrite -C -b $iosize 0 $filesize" - -# buffered re-write -echo -n brwrite, -xfs_io iofile -F -c "pwrite -C -b $iosize 0 $filesize" - -# direct re-write -echo -n drwrite, -xfs_io iofile -Fd -c "pwrite -C -b $iosize 0 $filesize" - -# buffered read -echo -n bread, -xfs_io iofile -F -c "pread -C -b $iosize 0 $filesize" - -# buffered re-read -echo -n brread, -xfs_io iofile -F -c "pread -C -b $iosize 0 $filesize" - -# direct read -echo -n dread, -xfs_io iofile -Fd -c "pread -C -b $iosize 0 $filesize" - -# direct re-read -echo -n drread, -xfs_io iofile -Fd -c "pread -C -b $iosize 0 $filesize" - diff --git a/run.metaperf_10i_1000n b/run.metaperf_10i_1000n deleted file mode 100755 index a420696..0000000 --- a/run.metaperf_10i_1000n +++ /dev/null @@ -1,31 +0,0 @@ -#!/bin/bash -# -# Copyright (c) 2003 Silicon Graphics, Inc. All Rights Reserved. -# -# This program is free software; you can redistribute it and/or -# modify it under the terms of the GNU General Public License as -# published by the Free Software Foundation. -# -# This program is distributed in the hope that it would be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program; if not, write the Free Software Foundation, -# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA -# -# -# Runs the metaperf metadata micro-benchmark. -# Use 1000 files, 10 iterations. -# - -[ -z "$here" ] && here=`pwd` -. $here/common.metaperf - -if [ $# -gt 0 ]; then - _format_header - exit 0 -fi - -$here/src/metaperf -d . -i 10 -n 1000 -l15 $allops | _format_metaperf diff --git a/run.metaperf_10i_1n b/run.metaperf_10i_1n deleted file mode 100755 index 296fd58..0000000 --- a/run.metaperf_10i_1n +++ /dev/null @@ -1,31 +0,0 @@ -#!/bin/bash -# -# Copyright (c) 2003 Silicon Graphics, Inc. All Rights Reserved. -# -# This program is free software; you can redistribute it and/or -# modify it under the terms of the GNU General Public License as -# published by the Free Software Foundation. -# -# This program is distributed in the hope that it would be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program; if not, write the Free Software Foundation, -# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA -# -# -# Runs the metaperf metadata micro-benchmark. -# Use 1 file, 10 iterations. -# - -[ -z "$here" ] && here=`pwd` -. $here/common.metaperf - -if [ $# -gt 0 ]; then - _format_header - exit 0 -fi - -$here/src/metaperf -d . -i 10 -n 1 -l15 $allops | _format_metaperf diff --git a/run.metaperf_1i_1n b/run.metaperf_1i_1n deleted file mode 100755 index ef02852..0000000 --- a/run.metaperf_1i_1n +++ /dev/null @@ -1,30 +0,0 @@ -#!/bin/bash -# -# Copyright (c) 2003 Silicon Graphics, Inc. All Rights Reserved. -# -# This program is free software; you can redistribute it and/or -# modify it under the terms of the GNU General Public License as -# published by the Free Software Foundation. -# -# This program is distributed in the hope that it would be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program; if not, write the Free Software Foundation, -# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA -# -# -# Runs the metaperf metadata micro-benchmark. -# Use 1 file, 1 iteration. (worst case) -# - -. $here/common.metaperf - -if [ $# -gt 0 ]; then - _format_header - exit 0 -fi - -$here/src/metaperf -d . -i 1 -n 1 -l15 $allops | _format_metaperf diff --git a/run.pio b/run.pio deleted file mode 100755 index 1b67fbf..0000000 --- a/run.pio +++ /dev/null @@ -1,69 +0,0 @@ -#!/bin/bash -# -# Copyright (c) 2005 Silicon Graphics, Inc. All Rights Reserved. -# -# This program is free software; you can redistribute it and/or -# modify it under the terms of the GNU General Public License as -# published by the Free Software Foundation. -# -# This program is distributed in the hope that it would be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program; if not, write the Free Software Foundation, -# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA -# -# -# (very) simple parallel IO tests. -# TODO: make file size multiple of physmem. - -filesize=1g -iosize=64k - -if [ $# -gt 0 ]; then - printf "%s,%s,%s,%s,%s\n" type bytes ops time bytes/sec ops/sec - exit 0 -fi - -# buffered write -echo -n bwrite, -xfs_io iofile1 -Fft -c "pwrite -C -b $iosize 0 $filesize" & -xfs_io iofile2 -Fft -c "pwrite -C -b $iosize 0 $filesize" - -# direct write -echo -n dwrite, -xfs_io iofile1 -Fftd -c "pwrite -C -b $iosize 0 $filesize" & -xfs_io iofile2 -Fftd -c "pwrite -C -b $iosize 0 $filesize" - -# buffered re-write -echo -n brwrite, -xfs_io iofile1 -F -c "pwrite -C -b $iosize 0 $filesize" & -xfs_io iofile2 -F -c "pwrite -C -b $iosize 0 $filesize" - -# direct re-write -echo -n drwrite, -xfs_io iofile1 -Fd -c "pwrite -C -b $iosize 0 $filesize" & -xfs_io iofile2 -Fd -c "pwrite -C -b $iosize 0 $filesize" - -# buffered read -echo -n bread, -xfs_io iofile1 -F -c "pread -C -b $iosize 0 $filesize" & -xfs_io iofile2 -F -c "pread -C -b $iosize 0 $filesize" - -# buffered re-read -echo -n brread, -xfs_io iofile1 -F -c "pread -C -b $iosize 0 $filesize" & -xfs_io iofile2 -F -c "pread -C -b $iosize 0 $filesize" - -# direct read -echo -n dread, -xfs_io iofile1 -Fd -c "pread -C -b $iosize 0 $filesize" & -xfs_io iofile2 -Fd -c "pread -C -b $iosize 0 $filesize" - -# direct re-read -echo -n drread, -xfs_io iofile1 -Fd -c "pread -C -b $iosize 0 $filesize" & -xfs_io iofile2 -Fd -c "pread -C -b $iosize 0 $filesize" - diff --git a/run.rtio b/run.rtio deleted file mode 100755 index 14aded6..0000000 --- a/run.rtio +++ /dev/null @@ -1,61 +0,0 @@ -#!/bin/bash -# -# Copyright (c) 2005 Silicon Graphics, Inc. All Rights Reserved. -# -# This program is free software; you can redistribute it and/or -# modify it under the terms of the GNU General Public License as -# published by the Free Software Foundation. -# -# This program is distributed in the hope that it would be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program; if not, write the Free Software Foundation, -# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA -# -# -# (very) simple file realtime IO tests. -# TODO: make file size multiple of physmem. - -filesize=1g -iosize=64k - -if [ $# -gt 0 ]; then - printf "%s,%s,%s,%s,%s\n" type bytes ops time bytes/sec ops/sec - exit 0 -fi - -# buffered write -echo -n bwrite, -xfs_io iofile -Rft -c "pwrite -C -b $iosize 0 $filesize" - -# direct write -echo -n dwrite, -xfs_io iofile -Rftd -c "pwrite -C -b $iosize 0 $filesize" - -# buffered re-write -echo -n brwrite, -xfs_io iofile -R -c "pwrite -C -b $iosize 0 $filesize" - -# direct re-write -echo -n drwrite, -xfs_io iofile -Rd -c "pwrite -C -b $iosize 0 $filesize" - -# buffered read -echo -n bread, -xfs_io iofile -R -c "pread -C -b $iosize 0 $filesize" - -# buffered re-read -echo -n brread, -xfs_io iofile -R -c "pread -C -b $iosize 0 $filesize" - -# direct read -echo -n dread, -xfs_io iofile -Rd -c "pread -C -b $iosize 0 $filesize" - -# direct re-read -echo -n drread, -xfs_io iofile -Rd -c "pread -C -b $iosize 0 $filesize" - diff --git a/run.tar b/run.tar deleted file mode 100755 index 6e8afd3..0000000 --- a/run.tar +++ /dev/null @@ -1,40 +0,0 @@ -#!/bin/bash -# -# Produces a .tar file (if one doesn't exist as $TARFILE), then -# times how long it takes to untar it onto the current directory. -# -TARFILE=${TARFILE:=/var/tmp/bench.tar.gz} - -barf() -{ - echo $@ >2 - exit 1 -} - -new_tar() -{ - source="bin sbin lib" - if [ ! -f $TARFILE ]; then - ( cd / && tar czf $TARFILE $source ) || barf "tar cz failed" - fi -} - -run_tar() -{ - # %U=user %S=system %E=elapsed - mkdir ./tar || exit 1 - size=`ls -Llh $TARFILE | awk '{print $5}'` - time=`/usr/bin/time -f '%U, %S, %E' tar xzf $TARFILE 2>&1` - status=$? - cd .. - rm -fr ./tar - [ $status -eq 0 ] || exit 1 - printf "%6s, %s\n" "$size" "$time" -} - -if [ $# -gt 0 ]; then - printf "%6s,%5s,%5s,%8s\n" sz usr sys real - exit 0 -fi -new_tar -run_tar -- 1.5.3.8 From pwhite@sgi.com Thu Mar 14 08:06:24 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from cthulhu.engr.sgi.com (cthulhu.engr.sgi.com [150.166.39.100]) by oss.sgi.com (Postfix) with ESMTP id 566E97F5A for ; Thu, 14 Mar 2013 08:06:12 -0500 (CDT) Received: from polaris-admin.engr.sgi.com (polaris-admin.engr.sgi.com [150.166.41.54]) by cthulhu.engr.sgi.com (8.12.10/8.12.10/SuSE Linux 0.7) with ESMTP id r2ED6Bx7007465 for ; Thu, 14 Mar 2013 06:06:11 -0700 Received: by polaris-admin.engr.sgi.com (Postfix, from userid 48024) id 8C56653DEAF7; Thu, 14 Mar 2013 06:06:11 -0700 (PDT) Date: Thu, 14 Mar 2013 06:06:11 -0700 To: xfs@oss.sgi.com Subject: [PATCH 10/18] xfstests: Add generic tests to tests/generic/group User-Agent: nail 11.25 7/29/05 MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Transfer-Encoding: 7bit Message-Id: <20130314130611.8C56653DEAF7@polaris-admin.engr.sgi.com> From: pwhite@sgi.com (Philip White) From: Phil White This is a rebasing & resubmit of a dchinner patch. His comments on the original: ----------------- And into tests/generic. Tests were found simply by grepping for the __supported_fs field in the tests. Output starts to look like: $ sudo ./check -g quick -r FSTYP -- xfs (debug) PLATFORM -- Linux/x86_64 test-1 3.5.0-rc5-dgc+ MKFS_OPTIONS -- -f -bsize=4096 /dev/vdb MOUNT_OPTIONS -- /dev/vdb /mnt/scratch ./242 1s ./183 2s generic/236 1s generic/014 1s generic/258 0s ./096 1s generic/245 0s ^C Ran: ./242 ./183 generic/236 generic/014 generic/258 ./096 generic/245 Passed all 7 tests ----------------- Signed-off-by: Phil White --- group | 98 --------------------------------------------------- tests/generic/group | 98 +++++++++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 98 insertions(+), 98 deletions(-) diff --git a/group b/group index 484bed5..dd0b622 100644 --- a/group +++ b/group @@ -116,26 +116,15 @@ stress # test-group association ... one line per test # -001 rw dir udf auto quick -002 metadata udf auto quick 003 db auto quick 004 db auto quick -005 dir udf auto quick -006 dir udf auto quick -007 dir udf auto quick 008 rw ioctl auto quick 009 rw ioctl auto prealloc quick -010 other udf auto -011 dir udf auto quick 012 rw auto quick -013 other ioctl udf auto quick -014 rw udf auto quick -015 other auto quick 016 rw auto quick 017 mount auto quick stress 018 deprecated # log logprint v2log 019 mkfs auto quick -020 metadata attr udf auto quick 021 db attr auto quick 022 dump ioctl tape 023 dump ioctl tape @@ -168,7 +157,6 @@ stress 050 quota auto quick 051 acl udf auto quick 052 quota db auto quick -053 acl repair auto quick 054 quota auto quick 055 dump ioctl remote tape 056 dump ioctl auto quick @@ -177,86 +165,52 @@ stress 059 dump ioctl auto quick 060 dump ioctl auto quick 061 dump ioctl auto quick -062 attr udf auto quick 063 dump attr auto quick 064 dump auto 065 dump auto 066 dump ioctl auto quick 067 acl attr auto quick 068 other auto freeze dangerous stress -069 rw udf auto quick -070 attr udf auto quick stress 071 rw auto 072 rw auto prealloc quick 073 copy auto -074 rw udf auto -075 rw udf auto quick -076 metadata rw udf auto quick stress -077 acl attr auto enospc 078 growfs auto quick -079 acl attr ioctl metadata auto quick 080 rw ioctl 081 deprecated # log logprint quota 082 deprecated # log logprint v2log -083 rw auto enospc stress 084 ioctl rw auto 085 log auto quick 086 log v2log auto 087 log v2log auto quota stress -088 perms auto quick -089 metadata auto 090 rw auto -091 rw auto quick 092 other auto quick -093 attr cap udf auto 094 metadata dir ioctl auto 095 log v2log auto 096 mkfs v2log auto quick -097 udf auto 098 udf auto -099 udf auto -100 udf auto 101 udf 102 udf 103 metadata dir ioctl auto quick 104 growfs ioctl prealloc auto stress -105 acl auto quick 106 quota 107 quota 108 quota auto quick 109 metadata auto 110 repair auto 111 ioctl -112 rw aio auto quick -113 rw aio auto quick 114 parent attr stress 115 parent attr 116 quota auto quick -117 attr auto quick 118 quota auto quick 119 log v2log auto freeze dangerous -120 other auto quick 121 log auto quick 122 other auto quick -123 perms auto quick -124 pattern auto quick -125 other auto -126 perms auto quick -127 rw auto -128 perms auto quick -129 rw auto quick -130 pattern auto quick -131 perms auto quick -132 pattern auto -133 rw auto 134 quota auto quick -135 metadata auto quick 136 attr2 137 metadata log auto 138 metadata log auto 139 metadata log auto 140 metadata log auto -141 rw auto quick 142 dmapi auto 143 dmapi auto 144 dmapi auto @@ -284,7 +238,6 @@ stress 166 rw metadata auto quick 167 rw metadata auto stress 168 dmapi auto -169 rw metadata auto quick 170 rw filestreams auto quick # the next three tests are not deterministic enough to get the # "right" result on all platforms/configuration, so don't run @@ -302,7 +255,6 @@ stress 181 log auto quick 182 metadata rw auto 183 rw other auto quick -184 metadata auto quick 185 dmapi auto 186 attr auto quick 187 attr auto quick @@ -310,95 +262,45 @@ stress 189 mount auto quick 190 rw auto quick 191 nfs4acl auto -192 atime auto -193 metadata auto quick 194 rw auto 195 ioctl dump auto quick 196 quota auto quick 197 dir auto quick -198 auto aio quick 199 mount auto quick 200 mount auto quick 201 metadata auto quick 202 repair auto quick 203 ioctl auto -204 metadata rw auto 205 metadata rw auto 206 growfs auto quick -207 auto aio quick -208 auto aio -209 auto aio -210 auto aio quick -211 auto aio quick -212 auto aio quick -213 rw auto prealloc quick enospc -214 rw auto prealloc quick -215 auto metadata quick 216 log metadata auto quick 217 log metadata auto 218 auto fsr quick -219 auto quota quick 220 auto quota quick -221 auto metadata quick 222 auto fsr ioctl quick -223 auto quick -224 auto -225 auto quick -226 auto enospc 227 auto fsr -228 rw auto prealloc quick 229 auto rw -230 auto quota quick -231 auto quota -232 auto quota stress -233 auto quota stress -234 auto quota -235 auto quota quick -236 auto quick metadata -237 auto quick acl 238 auto quick metadata ioctl -239 auto aio rw -240 auto aio quick rw -241 auto 242 auto quick prealloc 243 auto quick prealloc 244 auto quota quick -245 auto quick dir -246 auto quick rw -247 auto quick rw -248 auto quick rw -249 auto quick rw 250 auto quick rw prealloc metadata -251 ioctl trim 252 auto quick prealloc 253 auto quick 254 auto quick -255 auto quick prealloc -256 auto quick -257 dir auto quick -258 auto quick 259 auto quick -260 auto quick trim 261 auto quick quota 262 auto quick quota -263 rw auto quick 264 auto 265 auto 266 dump ioctl auto quick 267 dump ioctl tape 268 dump ioctl tape -269 auto rw prealloc ioctl enospc stress -270 auto quota rw prealloc ioctl enospc stress 271 auto rw quick 272 auto enospc rw -273 auto rw -274 auto rw -275 auto rw 276 auto rw metadata -277 auto ioctl quick metadata 278 repair auto 279 auto mkfs -280 auto quota freeze dangerous 281 dump ioctl auto quick 282 dump ioctl auto quick 283 dump ioctl auto quick diff --git a/tests/generic/group b/tests/generic/group index 4e01f0c..14d275c 100644 --- a/tests/generic/group +++ b/tests/generic/group @@ -3,3 +3,101 @@ # - do not start group names with a digit # - comment line before each group is "new" description # +001 rw dir udf auto quick +002 metadata udf auto quick +005 dir udf auto quick +006 dir udf auto quick +007 dir udf auto quick +010 other udf auto +011 dir udf auto quick +013 other ioctl udf auto quick +014 rw udf auto quick +015 other auto quick +020 metadata attr udf auto quick +053 acl repair auto quick +062 attr udf auto quick +069 rw udf auto quick +070 attr udf auto quick +074 rw udf auto +075 rw udf auto quick +076 metadata rw udf auto quick +077 acl attr auto enospc +079 acl attr ioctl metadata auto quick +083 rw auto +088 perms auto quick +089 metadata auto +091 rw auto quick +093 attr cap udf auto +097 udf auto +099 udf auto +100 udf auto +105 acl auto quick +112 rw aio auto quick +113 rw aio auto quick +117 attr auto quick +120 other auto quick +123 perms auto quick +124 pattern auto quick +125 other auto +126 perms auto quick +127 rw auto +128 perms auto quick +129 rw auto quick +130 pattern auto quick +131 perms auto quick +132 pattern auto +133 rw auto +135 metadata auto quick +141 rw auto quick +169 rw metadata auto quick +184 metadata auto quick +192 atime auto +193 metadata auto quick +198 auto aio quick +204 metadata rw auto +207 auto aio quick +208 auto aio +209 auto aio +210 auto aio quick +211 auto aio quick +212 auto aio quick +213 rw auto prealloc quick enospc +214 rw auto prealloc quick +215 auto metadata quick +219 auto quota quick +221 auto metadata quick +223 auto quick +224 auto +225 auto quick +226 auto enospc +228 rw auto prealloc quick +230 auto quota quick +231 auto quota +232 auto quota +233 auto quota +234 auto quota +235 auto quota quick +236 auto quick metadata +237 auto quick acl +239 auto aio rw +240 auto aio quick rw +241 auto +245 auto quick dir +246 auto quick rw +247 auto quick rw +248 auto quick rw +249 auto quick rw +251 ioctl trim +255 auto quick prealloc +256 auto quick +257 dir auto quick +258 auto quick +260 auto quick trim +263 rw auto quick +269 auto rw prealloc ioctl enospc +270 auto quota rw prealloc ioctl enospc +273 auto rw +274 auto rw +275 auto rw +277 auto ioctl quick metadata +280 auto quota freeze dangerous -- 1.5.3.8 From pwhite@sgi.com Thu Mar 14 08:06:23 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from cthulhu.engr.sgi.com (cthulhu.engr.sgi.com [150.166.39.100]) by oss.sgi.com (Postfix) with ESMTP id 32A0F7F56 for ; Thu, 14 Mar 2013 08:06:12 -0500 (CDT) Received: from polaris-admin.engr.sgi.com (polaris-admin.engr.sgi.com [150.166.41.54]) by cthulhu.engr.sgi.com (8.12.10/8.12.10/SuSE Linux 0.7) with ESMTP id r2ED6Bx7007455 for ; Thu, 14 Mar 2013 06:06:11 -0700 Received: by polaris-admin.engr.sgi.com (Postfix, from userid 48024) id 5F3D453DEAF3; Thu, 14 Mar 2013 06:06:11 -0700 (PDT) Date: Thu, 14 Mar 2013 06:06:11 -0700 To: xfs@oss.sgi.com Subject: [PATCH 04/18] xfstests: Remove obsolete configs User-Agent: nail 11.25 7/29/05 MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Transfer-Encoding: 7bit Message-Id: <20130314130611.5F3D453DEAF3@polaris-admin.engr.sgi.com> From: pwhite@sgi.com (Philip White) From: Phil White This is a rebasing & resubmit of a dchinner patch. His comments on the original: --------------------- Left over from the days of ASG, all stale. Remove them, leaving just an simple example that defines all the variables that can be configured. Also, add a localhost defined config set up for simple KVM based guest test configs using virtio for their block devices to simplify test setup in such scenarios.. --------------------- Signed-off-by: Phil White --- configs/134.14.54.101.config | 8 -------- configs/134.14.54.86.config | 8 -------- configs/bongo.config | 8 -------- configs/break.config | 10 ---------- configs/bruce.config | 16 ---------------- configs/burst.config | 6 ------ configs/carrot.config | 12 ------------ configs/chapter11.config | 11 ----------- configs/chook.config | 10 ---------- configs/cocky.config | 15 --------------- configs/crackle.config | 7 ------- configs/cxfsirix1.config | 7 ------- configs/dassi.config | 8 -------- configs/dibbler.config | 10 ---------- configs/dmfnt2.config | 10 ---------- configs/dribble.config | 12 ------------ configs/emu.config | 8 -------- configs/example.config | 15 +++++++++++++++ configs/flame.config | 9 --------- configs/frodo.config | 9 --------- configs/galah.config | 10 ---------- configs/gaspode.config | 13 ------------- configs/giro.config | 11 ----------- configs/goldfish.config | 8 -------- configs/gonzo1.config | 10 ---------- configs/growler.config | 10 ---------- configs/hammer.config | 7 ------- configs/hellfire.config | 15 --------------- configs/howler.config | 8 -------- configs/indra.config | 6 ------ configs/kermit1.config | 10 ---------- configs/lab343.config | 10 ---------- configs/linux-chatz.config | 12 ------------ configs/lite.config | 8 -------- configs/localhost.config | 15 +++++++++++++++ configs/lumpy.config | 6 ------ configs/mallet.config | 7 ------- configs/melt.config | 7 ------- configs/molten.config | 8 -------- configs/nobbs.config | 13 ------------- configs/permit.config | 6 ------ configs/puffy.config | 9 --------- configs/rizzo1.config | 7 ------- configs/rooster.config | 12 ------------ configs/rosella.config | 12 ------------ configs/scaly.config | 9 --------- configs/screamer.config | 12 ------------ configs/surly.config | 11 ----------- configs/tinkle.config | 7 ------- configs/usermode.config | 8 -------- configs/vimes.config | 12 ------------ 51 files changed, 30 insertions(+), 468 deletions(-) delete mode 100644 configs/134.14.54.101.config delete mode 100644 configs/134.14.54.86.config delete mode 100644 configs/bongo.config delete mode 100644 configs/break.config delete mode 100644 configs/bruce.config delete mode 100644 configs/burst.config delete mode 100644 configs/carrot.config delete mode 100644 configs/chapter11.config delete mode 100644 configs/chook.config delete mode 100644 configs/cocky.config delete mode 100644 configs/crackle.config delete mode 100644 configs/cxfsirix1.config delete mode 100644 configs/dassi.config delete mode 100644 configs/dibbler.config delete mode 100644 configs/dmfnt2.config delete mode 100644 configs/dribble.config delete mode 100644 configs/emu.config create mode 100644 configs/example.config delete mode 100644 configs/flame.config delete mode 100644 configs/frodo.config delete mode 100644 configs/galah.config delete mode 100644 configs/gaspode.config delete mode 100644 configs/giro.config delete mode 100644 configs/goldfish.config delete mode 100644 configs/gonzo1.config delete mode 100644 configs/growler.config delete mode 100644 configs/hammer.config delete mode 100644 configs/hellfire.config delete mode 100644 configs/howler.config delete mode 100644 configs/indra.config delete mode 100644 configs/kermit1.config delete mode 100644 configs/lab343.config delete mode 100644 configs/linux-chatz.config delete mode 100644 configs/lite.config create mode 100644 configs/localhost.config delete mode 100644 configs/lumpy.config delete mode 100644 configs/mallet.config delete mode 100644 configs/melt.config delete mode 100644 configs/molten.config delete mode 100644 configs/nobbs.config delete mode 100644 configs/permit.config delete mode 100644 configs/puffy.config delete mode 100644 configs/rizzo1.config delete mode 100644 configs/rooster.config delete mode 100644 configs/rosella.config delete mode 100644 configs/scaly.config delete mode 100644 configs/screamer.config delete mode 100644 configs/surly.config delete mode 100644 configs/tinkle.config delete mode 100644 configs/usermode.config delete mode 100644 configs/vimes.config diff --git a/configs/134.14.54.101.config b/configs/134.14.54.101.config deleted file mode 100644 index 6f6b610..0000000 --- a/configs/134.14.54.101.config +++ /dev/null @@ -1,8 +0,0 @@ -# Autogenerated config for host 134.14.54.101, by xaiki's hack.pl -#The IP for file system resource on HA cluster. -EMAIL="leenap@sgi.com" -[ -z "$TEST_DIR" ] && TEST_DIR=/mnt/test -[ -z "$TEST_DEV" ] && TEST_DEV=/dev/lxvm/test -[ -z "$SCRATCH_MNT" ] && SCRATCH_MNT=/mnt/scratch -[ -z "$SCRATCH_DEV" ] && SCRATCH_DEV=/dev/lxvm/scratch - diff --git a/configs/134.14.54.86.config b/configs/134.14.54.86.config deleted file mode 100644 index c2fec06..0000000 --- a/configs/134.14.54.86.config +++ /dev/null @@ -1,8 +0,0 @@ -# Autogenerated config for host 134.14.54.86, by xaiki's hack.pl -#The IP for file system resource on HA cluster. -EMAIL="leenap@sgi.com" -[ -z "$TEST_DIR" ] && TEST_DIR=/mnt/test -[ -z "$TEST_DEV" ] && TEST_DEV=/dev/lxvm/test -[ -z "$SCRATCH_MNT" ] && SCRATCH_MNT=/mnt/scratch -[ -z "$SCRATCH_DEV" ] && SCRATCH_DEV=/dev/lxvm/scratch - diff --git a/configs/bongo.config b/configs/bongo.config deleted file mode 100644 index d972181..0000000 --- a/configs/bongo.config +++ /dev/null @@ -1,8 +0,0 @@ -# Autogenerated config for host bongo, by xaiki's hack.pl -TEST_DEV=/dev/hda8 -TEST_DIR=/xfs1 -SCRATCH_DEV=/dev/hda9 -SCRATCH_MNT=/xfs2 -SCRATCH_LOGDEV=/dev/hda10 -SCRATCH_RTDEV=/dev/hda11 - diff --git a/configs/break.config b/configs/break.config deleted file mode 100644 index 64f6d59..0000000 --- a/configs/break.config +++ /dev/null @@ -1,10 +0,0 @@ -# Autogenerated config for host break, by xaiki's hack.pl -MODULAR=1 -EMAIL="nathans@larry" -SCRATCH_MNT=/mnt/scratch -#SCRATCH_DEV=/dev/sda6 -SCRATCH_DEV=budgie:/mnt/scratch -TEST_DIR=/mnt/test -#TEST_DEV=/dev/sda5 -TEST_DEV=budgie:/mnt/test - diff --git a/configs/bruce.config b/configs/bruce.config deleted file mode 100644 index f4f37c4..0000000 --- a/configs/bruce.config +++ /dev/null @@ -1,16 +0,0 @@ -# Autogenerated config for host bruce, by xaiki's hack.pl -MODULAR=0 -EMAIL="nathans@larry" -SCRATCH_MNT=/mnt/scratch -SCRATCH_DEV=/dev/sdb5 -SCRATCH_RTDEV=/dev/sdc1 -SCRATCH_LOGDEV=/dev/ram0 -TEST_DIR=/mnt/test -TEST_DEV=/dev/sdc3 -TEST_RTDEV=/dev/sdb6 -TEST_LOGDEV=/dev/ram1 -#TAPE_DEV=/dev/st0 -#RMT_TAPE_DEV=bruce:/dev/st0 -#RMT_IRIXTAPE_DEV=snort:/dev/tape -#RMT_TAPE_USER=guest - diff --git a/configs/burst.config b/configs/burst.config deleted file mode 100644 index 95bb09d..0000000 --- a/configs/burst.config +++ /dev/null @@ -1,6 +0,0 @@ -# Autogenerated config for host burst, by xaiki's hack.pl -TEST_DIR=/xfs -TEST_DEV=/dev/hda3 -SCRATCH_DEV=/dev/hda7 -SCRATCH_MNT=/scratch - diff --git a/configs/carrot.config b/configs/carrot.config deleted file mode 100644 index 26f8e49..0000000 --- a/configs/carrot.config +++ /dev/null @@ -1,12 +0,0 @@ -# Autogenerated config for host carrot, by xaiki's hack.pl -#dedicated qa machine, used to be dribble -MODULAR=0 -EMAIL="ddiss@sgi.com" -TEST_DIR=/mnt/test -TEST_DEV=/dev/dsk/dks0d2s0 -SCRATCH_MNT=/mnt/scratch -SCRATCH_DEV=/dev/dsk/dks0d2s6 -#TAPE_DEV=/dev/tape -#RMT_TAPE_DEV=icy:/dev/st0 -#RMT_TAPE_USER=guest - diff --git a/configs/chapter11.config b/configs/chapter11.config deleted file mode 100644 index 70039e4..0000000 --- a/configs/chapter11.config +++ /dev/null @@ -1,11 +0,0 @@ -# Autogenerated config for host chapter11, by xaiki's hack.pl -[ -z "$MODULAR" ] && MODULAR=1 -EMAIL="ddiss@sgi.com" -[ -z "$TEST_DIR" ] && TEST_DIR=/mnt/test -[ -z "$TEST_DEV" ] && TEST_DEV=/dev/sdb5 -[ -z "$TEST_LOGDEV" ] && TEST_LOGDEV=/dev/sdb7 -[ -z "$SCRATCH_MNT" ] && SCRATCH_MNT=/mnt/scratch -[ -z "$SCRATCH_DEV" ] && SCRATCH_DEV=/dev/sdb6 -[ -z "$SCRATCH_LOGDEV" ] && SCRATCH_LOGDEV=/dev/sdb8 -[ -z "$SCRATCH_RTDEV" ] && SCRATCH_RTDEV=/dev/sdb9 - diff --git a/configs/chook.config b/configs/chook.config deleted file mode 100644 index 64f6d59..0000000 --- a/configs/chook.config +++ /dev/null @@ -1,10 +0,0 @@ -# Autogenerated config for host break, by xaiki's hack.pl -MODULAR=1 -EMAIL="nathans@larry" -SCRATCH_MNT=/mnt/scratch -#SCRATCH_DEV=/dev/sda6 -SCRATCH_DEV=budgie:/mnt/scratch -TEST_DIR=/mnt/test -#TEST_DEV=/dev/sda5 -TEST_DEV=budgie:/mnt/test - diff --git a/configs/cocky.config b/configs/cocky.config deleted file mode 100644 index 0d2e432..0000000 --- a/configs/cocky.config +++ /dev/null @@ -1,15 +0,0 @@ -# Autogenerated config for host cocky, by xaiki's hack.pl -MODULAR=1 -EMAIL="ajones@sgi.com" -TEST_DIR=/mnt/test -TEST_DEV=/dev/sdb1 -TEST_LOGDEV=/dev/sdb3 -SCRATCH_MNT=/mnt/scratch -SCRATCH_DEV=/dev/sdb2 -SCRATCH_LOGDEV=/dev/sdb4 -#SCRATCH_RTDEV=/dev/sdb5 -TAPE_DEV=/dev/st0 -#RMT_IRIXTAPE_DEV=snort:/dev/tape -#RMT_TAPE_DEV=icy:/dev/st0 -#RMT_TAPE_USER=guest - diff --git a/configs/crackle.config b/configs/crackle.config deleted file mode 100644 index ee3c0da..0000000 --- a/configs/crackle.config +++ /dev/null @@ -1,7 +0,0 @@ -# Autogenerated config for host crackle, by xaiki's hack.pl -#irix-crackle -TEST_DIR=/mnt/xfs -SCRATCH_MNT=/mnt/xfs2 -TEST_DEV=/dev/dsk/dks0d1s3 -SCRATCH_DEV=/dev/dsk/dks0d1s4 - diff --git a/configs/cxfsirix1.config b/configs/cxfsirix1.config deleted file mode 100644 index c36568a..0000000 --- a/configs/cxfsirix1.config +++ /dev/null @@ -1,7 +0,0 @@ -# Autogenerated config for host cxfsirix1, by xaiki's hack.pl -EMAIL="ajones@sgi.com" -TEST_DIR=/mnt/xfs_test0 -TEST_DEV=/dev/cxvm/xfs_test0 -SCRATCH_MNT=/mnt/xfs_test1 -SCRATCH_DEV=/dev/cxvm/xfs_test1 - diff --git a/configs/dassi.config b/configs/dassi.config deleted file mode 100644 index 638c06a..0000000 --- a/configs/dassi.config +++ /dev/null @@ -1,8 +0,0 @@ -# Autogenerated config for host dassi, by xaiki's hack.pl -MODULAR=0 -EMAIL="ddiss@sgi.com" -TEST_DIR=/mnt/test -TEST_DEV=/dev/dsk/dks0d2s0 -SCRATCH_MNT=/mnt/scratch -SCRATCH_DEV=/dev/dsk/dks0d2s1 - diff --git a/configs/dibbler.config b/configs/dibbler.config deleted file mode 100644 index 2068c19..0000000 --- a/configs/dibbler.config +++ /dev/null @@ -1,10 +0,0 @@ -# configuration file for dibbler -[ -z "$MODULAR" ] && MODULAR=1 -EMAIL="mohamedb@sgi.com" -[ -z "$TEST_DIR" ] && TEST_DIR=/mnt/test -[ -z "$TEST_DEV" ] && TEST_DEV=/dev/sdb1 -[ -z "$TEST_LOGDEV" ] && TEST_LOGDEV=/dev/sdb3 -[ -z "$SCRATCH_MNT" ] && SCRATCH_MNT=/mnt/scratch -[ -z "$SCRATCH_DEV" ] && SCRATCH_DEV=/dev/sdb2 -[ -z "$SCRATCH_LOGDEV" ] && SCRATCH_LOGDEV=/dev/sdb4 - diff --git a/configs/dmfnt2.config b/configs/dmfnt2.config deleted file mode 100644 index de6af2e..0000000 --- a/configs/dmfnt2.config +++ /dev/null @@ -1,10 +0,0 @@ -# Autogenerated config for host dmfnt2, by xaiki's hack.pl -TEST_DEV=/dev/sda6 -TEST_DIR=/mnt/test -SCRATCH_DEV=/dev/sdc6 -SCRATCH_MNT=/mnt/scratch -TAPE_DEV=/dev/st0 -RMT_TAPE_DEV=longhorn:/dev/tape -# RMT_IRIXTAPE_DEV=longhorn:/dev/tape -RMT_TAPE_USER=guest - diff --git a/configs/dribble.config b/configs/dribble.config deleted file mode 100644 index b548b8e..0000000 --- a/configs/dribble.config +++ /dev/null @@ -1,12 +0,0 @@ -# Autogenerated config for host dribble, by xaiki's hack.pl -#dedicated qa machine -MODULAR=0 -EMAIL="ddiss@sgi.com" -TEST_DIR=/mnt/test -TEST_DEV=/dev/dsk/dks0d2s0 -SCRATCH_MNT=/mnt/scratch -SCRATCH_DEV=/dev/dsk/dks0d2s6 -#TAPE_DEV=/dev/tape -#RMT_TAPE_DEV=icy:/dev/st0 -#RMT_TAPE_USER=guest - diff --git a/configs/emu.config b/configs/emu.config deleted file mode 100644 index 6b21ff3..0000000 --- a/configs/emu.config +++ /dev/null @@ -1,8 +0,0 @@ -# Autogenerated config for host emu, by xaiki's hack.pl -MODULAR=0 -EMAIL="tes@sgi.com" -TEST_DIR=/mnt/test -TEST_DEV=/dev/sdb1 -SCRATCH_MNT=/mnt/scratch1 -SCRATCH_DEV=/dev/sdb2 - diff --git a/configs/example.config b/configs/example.config new file mode 100644 index 0000000..7b6e142 --- /dev/null +++ b/configs/example.config @@ -0,0 +1,15 @@ +# Example config file with all typical device options set for full +# XFS kernel, progs and dump testing. +MODULAR=0 +SCRATCH_MNT=/mnt/scratch +SCRATCH_DEV=/dev/sdb5 +SCRATCH_RTDEV=/dev/sdc1 +SCRATCH_LOGDEV=/dev/ram0 +TEST_DIR=/mnt/test +TEST_DEV=/dev/sdc3 +TEST_RTDEV=/dev/sdb6 +TEST_LOGDEV=/dev/ram1 +TAPE_DEV=/dev/st0 +RMT_TAPE_DEV=bruce:/dev/st0 +RMT_IRIXTAPE_DEV=snort:/dev/tape +RMT_TAPE_USER=guest diff --git a/configs/flame.config b/configs/flame.config deleted file mode 100644 index ad44006..0000000 --- a/configs/flame.config +++ /dev/null @@ -1,9 +0,0 @@ -# Autogenerated config for host flame, by xaiki's hack.pl -#dedicated qa machine (has some values already set) -[ -z "$MODULAR" ] && MODULAR=1 -EMAIL="ddiss@sgi.com" -[ -z "$TEST_DIR" ] && TEST_DIR=/mnt/xfs_test -[ -z "$TEST_DEV" ] && TEST_DEV=/dev/lxvm/xfs_test -[ -z "$SCRATCH_MNT" ] && SCRATCH_MNT=/mnt/xfs_scratch -[ -z "$SCRATCH_DEV" ] && SCRATCH_DEV=/dev/lxvm/xfs_scratch - diff --git a/configs/frodo.config b/configs/frodo.config deleted file mode 100644 index a8c262c..0000000 --- a/configs/frodo.config +++ /dev/null @@ -1,9 +0,0 @@ -# Autogenerated config for host frodo, by xaiki's hack.pl -MODULAR=0 -EMAIL="nathans@larry" -TEST_DEV=/dev/hda6 -TEST_DIR=/mnt/test -SCRATCH_DEV=/dev/hda7 -SCRATCH_MNT=/mnt/scratch -SCRATCH_LOGDEV=/dev/hda9 - diff --git a/configs/galah.config b/configs/galah.config deleted file mode 100644 index dc4c835..0000000 --- a/configs/galah.config +++ /dev/null @@ -1,10 +0,0 @@ -# Autogenerated config for host galah, by xaiki's hack.pl -MODULAR=1 -EMAIL="ddiss@sgi.com" -[ -z "$TEST_DIR" ] && TEST_DIR=/mnt/test -[ -z "$TEST_DEV" ] && TEST_DEV=/dev/sdb1 -[ -z "$TEST_LOGDEV" ] && TEST_LOGDEV=/dev/sdb3 -[ -z "$SCRATCH_MNT" ] && SCRATCH_MNT=/mnt/scratch -[ -z "$SCRATCH_DEV" ] && SCRATCH_DEV=/dev/sdb2 -[ -z "$SCRATCH_LOGDEV" ] && SCRATCH_LOGDEV=/dev/sdb4 - diff --git a/configs/gaspode.config b/configs/gaspode.config deleted file mode 100644 index 8d7f939..0000000 --- a/configs/gaspode.config +++ /dev/null @@ -1,13 +0,0 @@ -# Autogenerated config for host gaspode, by xaiki's hack.pl -#dedicated qa machine (has some values already set) -[ -z "$MODULAR" ] && MODULAR=1 -EMAIL="ddiss@sgi.com" -[ -z "$TEST_DIR" ] && TEST_DIR=/mnt/test -[ -z "$TEST_DEV" ] && TEST_DEV=/dev/sdb1 -[ -z "$TEST_LOGDEV" ] && TEST_LOGDEV=/dev/sdb3 -[ -z "$SCRATCH_MNT" ] && SCRATCH_MNT=/mnt/scratch -[ -z "$SCRATCH_DEV" ] && SCRATCH_DEV=/dev/sdb2 -[ -z "$SCRATCH_LOGDEV" ] && SCRATCH_LOGDEV=/dev/sdb4 -[ -z "$SCRATCH_RTDEV" ] && SCRATCH_RTDEV=/dev/sdb5 -[ -z "$TAPE_DEV" ] && TAPE_DEV=/dev/st0 - diff --git a/configs/giro.config b/configs/giro.config deleted file mode 100644 index cab8b56..0000000 --- a/configs/giro.config +++ /dev/null @@ -1,11 +0,0 @@ -# Autogenerated config for host giro, by xaiki's hack.pl -MODULAR=0 -EMAIL="ddiss@sgi.com" -TEST_DIR=/mnt/test -TEST_DEV=/dev/dsk/dks0d2s0 -SCRATCH_MNT=/mnt/scratch -SCRATCH_DEV=/dev/dsk/dks0d2s6 -#TAPE_DEV=/dev/tape -#RMT_TAPE_DEV=icy:/dev/st0 -#RMT_TAPE_USER=guest - diff --git a/configs/goldfish.config b/configs/goldfish.config deleted file mode 100644 index 94f5fc8..0000000 --- a/configs/goldfish.config +++ /dev/null @@ -1,8 +0,0 @@ -# Autogenerated config for host goldfish, by xaiki's hack.pl -MODULAR=0 -TEST_DEV=/dev/hdc1 -TEST_DIR=/mnt/xfs0 -SCRATCH_DEV=/dev/hdc2 -SCRATCH_MNT=/mnt/xfs1 -SCRATCH_LOGDEV=/dev/hdc3 - diff --git a/configs/gonzo1.config b/configs/gonzo1.config deleted file mode 100644 index e6d807b..0000000 --- a/configs/gonzo1.config +++ /dev/null @@ -1,10 +0,0 @@ -# Autogenerated config for host gonzo1, by xaiki's hack.pl -EMAIL="leenap@sgi.com" -[ -z "$TEST_DIR" ] && TEST_DIR=/mnt/xfs_test -[ -z "$TEST_DEV" ] && TEST_DEV=/dev/lxvm/xfs_test -[ -z "$TEST_LOGDEV" ] && TEST_LOGDEV=/dev/sdb1 -[ -z "$SCRATCH_MNT" ] && SCRATCH_MNT=/mnt/xfs_scratch -[ -z "$SCRATCH_DEV" ] && SCRATCH_DEV=/dev/lxvm/xfs_scratch -[ -z "$SCRATCH_LOGDEV" ] && SCRATCH_LOGDEV=/dev/sdb2 -[ -z "$SCRATCH_RTDEV" ] && SCRATCH_RTDEV=/dev/sdb3 - diff --git a/configs/growler.config b/configs/growler.config deleted file mode 100644 index bf99b05..0000000 --- a/configs/growler.config +++ /dev/null @@ -1,10 +0,0 @@ -# Autogenerated config for host growler, by xaiki's hack.pl -[ -z "$MODULAR" ] && MODULAR=1 -EMAIL="ddiss@sgi.com" -[ -z "$TEST_DIR" ] && TEST_DIR=/mnt/test -[ -z "$TEST_DEV" ] && TEST_DEV=/dev/sdb1 -[ -z "$TEST_LOGDEV" ] && TEST_LOGDEV=/dev/sdb3 -[ -z "$SCRATCH_MNT" ] && SCRATCH_MNT=/mnt/scratch -[ -z "$SCRATCH_DEV" ] && SCRATCH_DEV=/dev/sdb2 -[ -z "$SCRATCH_LOGDEV" ] && SCRATCH_LOGDEV=/dev/sdb4 - diff --git a/configs/hammer.config b/configs/hammer.config deleted file mode 100644 index a070f93..0000000 --- a/configs/hammer.config +++ /dev/null @@ -1,7 +0,0 @@ -# Autogenerated config for host hammer, by xaiki's hack.pl -EMAIL="bnaujok@sgi.com" -TEST_DIR=/mnt/test -TEST_DEV=/dev/sda5 -SCRATCH_MNT=/mnt/scratch -SCRATCH_DEV=/dev/sda6 - diff --git a/configs/hellfire.config b/configs/hellfire.config deleted file mode 100644 index 7664829..0000000 --- a/configs/hellfire.config +++ /dev/null @@ -1,15 +0,0 @@ -# Autogenerated config for host hellfire, by xaiki's hack.pl -MODULAR=1 -EMAIL="ajones@sgi.com" -TEST_DIR=/mnt/test -TEST_DEV=/dev/sda3 -TEST_LOGDEV=/dev/sda5 -SCRATCH_MNT=/mnt/scratch -SCRATCH_DEV=/dev/sda4 -SCRATCH_LOGDEV=/dev/sda6 -#SCRATCH_RTDEV=/dev/sda7 -TAPE_DEV=/dev/st0 -#RMT_IRIXTAPE_DEV=snort:/dev/tape -#RMT_TAPE_DEV=icy:/dev/st0 -#RMT_TAPE_USER=guest - diff --git a/configs/howler.config b/configs/howler.config deleted file mode 100644 index 47d98c1..0000000 --- a/configs/howler.config +++ /dev/null @@ -1,8 +0,0 @@ -# Autogenerated config for host howler, by xaiki's hack.pl -[ -z "$MODULAR" ] && MODULAR=1 -EMAIL="allanr@sgi.com" -[ -z "$TEST_DIR" ] && TEST_DIR=/mnt/test -[ -z "$TEST_DEV" ] && TEST_DEV=/dev/sdb1 -[ -z "$SCRATCH_MNT" ] && SCRATCH_MNT=/mnt/scratch -[ -z "$SCRATCH_DEV" ] && SCRATCH_DEV=/dev/sdb2 - diff --git a/configs/indra.config b/configs/indra.config deleted file mode 100644 index dce005e..0000000 --- a/configs/indra.config +++ /dev/null @@ -1,6 +0,0 @@ -# Autogenerated config for host indra, by xaiki's hack.pl -TEST_DEV=/dev/sdb1 -TEST_DIR=/mnt/xfs0 -SCRATCH_DEV=/dev/sdb2 -SCRATCH_MNT=/mnt/xfs1 - diff --git a/configs/kermit1.config b/configs/kermit1.config deleted file mode 100644 index 7d09819..0000000 --- a/configs/kermit1.config +++ /dev/null @@ -1,10 +0,0 @@ -# Autogenerated config for host kermit1, by xaiki's hack.pl -EMAIL="mohamedb@sgi.com" -[ -z "$TEST_DIR" ] && TEST_DIR=/mnt/xfs_test -[ -z "$TEST_DEV" ] && TEST_DEV=/dev/lxvm/xfs_test -[ -z "$TEST_LOGDEV" ] && TEST_LOGDEV=/dev/sdb1 -[ -z "$SCRATCH_MNT" ] && SCRATCH_MNT=/mnt/xfs_scratch -[ -z "$SCRATCH_DEV" ] && SCRATCH_DEV=/dev/lxvm/xfs_scratch -[ -z "$SCRATCH_LOGDEV" ] && SCRATCH_LOGDEV=/dev/sdb2 -[ -z "$SCRATCH_RTDEV" ] && SCRATCH_RTDEV=/dev/sdb3 - diff --git a/configs/lab343.config b/configs/lab343.config deleted file mode 100644 index 4b38d3d..0000000 --- a/configs/lab343.config +++ /dev/null @@ -1,10 +0,0 @@ -# Autogenerated config for host lab343, by xaiki's hack.pl -MODULAR=0 -EMAIL="hch@sgi.com" -TEST_DEV=/dev/sdb1 -SCRATCH_DEV=/dev/sdb2 -SCRATCH_LOGDEV=/dev/sdb5 -SCRATCH_RTDEV=/dev/sdb6 -TEST_DIR=/qa/test -SCRATCH_MNT=/qa/scratch - diff --git a/configs/linux-chatz.config b/configs/linux-chatz.config deleted file mode 100644 index ba762c9..0000000 --- a/configs/linux-chatz.config +++ /dev/null @@ -1,12 +0,0 @@ -# Autogenerated config for host linux-chatz, by xaiki's hack.pl -#vmware on pc-chatz -MODULAR=1 -EMAIL="chatz@sgi.com" -USE_EXTERNAL=yes -TEST_DIR="/mnt/data" -TEST_DEV=/dev/sdd -TEST_LOGDEV=/dev/sdb -SCRATCH_MNT=/mnt/scratch -SCRATCH_DEV=/dev/sdg -SCRATCH_LOGDEV=/mnt/sde - diff --git a/configs/lite.config b/configs/lite.config deleted file mode 100644 index 783cd3c..0000000 --- a/configs/lite.config +++ /dev/null @@ -1,8 +0,0 @@ -# Autogenerated config for host lite, by xaiki's hack.pl -TEST_DEV=/dev/sda1 -TEST_DIR=/mnt/sda1 -SCRATCH_DEV=/dev/sda2 -SCRATCH_MNT=/mnt/sda2 -SCRATCH_LOGDEV=/dev/sda3 -SCRATCH_RTDEV=/dev/sda4 - diff --git a/configs/localhost.config b/configs/localhost.config new file mode 100644 index 0000000..f47e694 --- /dev/null +++ b/configs/localhost.config @@ -0,0 +1,15 @@ +# default localhost file, set up for virtual machines using KVM and +# virtio for it's block devices +# +MODULAR=0 +TEST_DIR=/mnt/test +SCRATCH_MNT=/mnt/scratch + +TEST_DEV=/dev/vda +SCRATCH_DEV=/dev/vdb + +TEST_LOGDEV=/dev/vdc +SCRATCH_LOGDEV=/dev/vdd + +TEST_RTDEV=/dev/vde +SCRATCH_RTDEV=/dev/vdf diff --git a/configs/lumpy.config b/configs/lumpy.config deleted file mode 100644 index 321d852..0000000 --- a/configs/lumpy.config +++ /dev/null @@ -1,6 +0,0 @@ -# Autogenerated config for host lumpy, by xaiki's hack.pl -TEST_DEV=/dev/sdc5 -TEST_DIR=/mnt/scratch_0 -SCRATCH_DEV=/dev/sdc7 -SCRATCH_MNT=/mnt/scratch_2 - diff --git a/configs/mallet.config b/configs/mallet.config deleted file mode 100644 index 197fef5..0000000 --- a/configs/mallet.config +++ /dev/null @@ -1,7 +0,0 @@ -# Autogenerated config for host mallet, by xaiki's hack.pl -MODULAR=1 -TEST_DIR=/mnt/test -TEST_DEV=/dev/sda3 -SCRATCH_MNT=/mnt/scratch -SCRATCH_DEV=/dev/sda4 - diff --git a/configs/melt.config b/configs/melt.config deleted file mode 100644 index 59bf9fc..0000000 --- a/configs/melt.config +++ /dev/null @@ -1,7 +0,0 @@ -# Autogenerated config for host melt, by xaiki's hack.pl -MODULAR=1 -TEST_DIR=/mnt/test -TEST_DEV=/dev/sdb1 -SCRATCH_MNT=/mnt/scratch -SCRATCH_DEV=/dev/sdb2 - diff --git a/configs/molten.config b/configs/molten.config deleted file mode 100644 index dc8bfea..0000000 --- a/configs/molten.config +++ /dev/null @@ -1,8 +0,0 @@ -# Autogenerated config for host molten, by xaiki's hack.pl -[ -z "$MODULAR" ] && MODULAR=1 -EMAIL="ddiss@sgi.com" -[ -z "$TEST_DIR" ] && TEST_DIR=/mnt/test -[ -z "$TEST_DEV" ] && TEST_DEV=/dev/sdb5 -[ -z "$SCRATCH_MNT" ] && SCRATCH_MNT=/mnt/scratch -[ -z "$SCRATCH_DEV" ] && SCRATCH_DEV=/dev/sdb6 - diff --git a/configs/nobbs.config b/configs/nobbs.config deleted file mode 100644 index 7a3cf2d..0000000 --- a/configs/nobbs.config +++ /dev/null @@ -1,13 +0,0 @@ -# Autogenerated config for host nobbs, by xaiki's hack.pl -#dedicated qa machine, used to be porky -[ -z "$MODULAR" ] && MODULAR=1 -EMAIL="ddiss@sgi.com" -[ -z "$TEST_DIR" ] && TEST_DIR=/mnt/test -[ -z "$TEST_DEV" ] && TEST_DEV=/dev/sdb1 -[ -z "$TEST_LOGDEV" ] && TEST_LOGDEV=/dev/sdb3 -[ -z "$SCRATCH_MNT" ] && SCRATCH_MNT=/mnt/scratch -[ -z "$SCRATCH_DEV" ] && SCRATCH_DEV=/dev/sdb2 -[ -z "$SCRATCH_LOGDEV" ] && SCRATCH_LOGDEV=/dev/sdb4 -#[ -z "$SCRATCH_RTDEV" ] && SCRATCH_RTDEV=/dev/sdb7 -#[ -z "$TAPE_DEV" ] && TAPE_DEV=/dev/st0 - diff --git a/configs/permit.config b/configs/permit.config deleted file mode 100644 index 93b5326..0000000 --- a/configs/permit.config +++ /dev/null @@ -1,6 +0,0 @@ -# Autogenerated config for host permit, by xaiki's hack.pl -TEST_DEV=/dev/sdc1 -TEST_DIR=/mnt/xfs0 -SCRATCH_DEV=/dev/sdd1 -SCRATCH_MNT=/mnt/xfs1 - diff --git a/configs/puffy.config b/configs/puffy.config deleted file mode 100644 index e1f77ae..0000000 --- a/configs/puffy.config +++ /dev/null @@ -1,9 +0,0 @@ -# Autogenerated config for host puffy, by xaiki's hack.pl -MODULAR=1 -EMAIL="tes@sgi.com" -TEST_DIR=/mnt/test -TEST_DEV=/dev/sda7 -SCRATCH_MNT=/mnt/scratch -SCRATCH_DEV=/dev/sda8 -TAPE_DEV=/dev/st0 - diff --git a/configs/rizzo1.config b/configs/rizzo1.config deleted file mode 100644 index d1a55b1..0000000 --- a/configs/rizzo1.config +++ /dev/null @@ -1,7 +0,0 @@ -# Autogenerated config for host rizzo1, by xaiki's hack.pl -EMAIL="mohamedb@sgi.com" -TEST_DIR=/mnt/xfs_test -TEST_DEV=/dev/lxvm/xfs_test -SCRATCH_MNT=/mnt/xfs_scratch -SCRATCH_DEV=/dev/lxvm/xfs_scratch - diff --git a/configs/rooster.config b/configs/rooster.config deleted file mode 100644 index e5a3163..0000000 --- a/configs/rooster.config +++ /dev/null @@ -1,12 +0,0 @@ -# Autogenerated config for host rooster, by xaiki's hack.pl -MODULAR=1 -EMAIL="ajones@sgi.com" -TEST_DIR=/mnt/test -TEST_DEV=/dev/sdb1 -SCRATCH_MNT=/mnt/scratch -SCRATCH_DEV=/dev/sdb2 -TAPE_DEV=/dev/st0 -#RMT_IRIXTAPE_DEV=snort:/dev/tape -#RMT_TAPE_DEV=icy:/dev/st0 -#RMT_TAPE_USER=guest - diff --git a/configs/rosella.config b/configs/rosella.config deleted file mode 100644 index 3b441bf..0000000 --- a/configs/rosella.config +++ /dev/null @@ -1,12 +0,0 @@ -# Autogenerated config for host rosella, by xaiki's hack.pl -MODULAR=1 -EMAIL="ajones@sgi.com" -TEST_DIR=/mnt/test -TEST_DEV=/dev/sdb1 -SCRATCH_MNT=/mnt/scratch -SCRATCH_DEV=/dev/sdb3 -TAPE_DEV=/dev/st0 -#RMT_IRIXTAPE_DEV=snort:/dev/tape -#RMT_TAPE_DEV=icy:/dev/st0 -#RMT_TAPE_USER=guest - diff --git a/configs/scaly.config b/configs/scaly.config deleted file mode 100644 index a6d5510..0000000 --- a/configs/scaly.config +++ /dev/null @@ -1,9 +0,0 @@ -# Autogenerated config for host scaly, by xaiki's hack.pl -EMAIL="bnaujok@sgi.com" -TEST_DIR=/mnt/test -TEST_DEV=/dev/sdd3 -#TEST_LOGDEV=/dev/sdd1 -SCRATCH_MNT=/mnt/scratch -SCRATCH_DEV=/dev/sdd4 -#SCRATCH_LOGDEV=/dev/sdd2 - diff --git a/configs/screamer.config b/configs/screamer.config deleted file mode 100644 index 047d64b..0000000 --- a/configs/screamer.config +++ /dev/null @@ -1,12 +0,0 @@ -# Autogenerated config for host screamer, by xaiki's hack.pl -#dedicated qa machine (has some values already set) -[ -z "$MODULAR" ] && MODULAR=1 -EMAIL="ddiss@sgi.com" -[ -z "$TEST_DIR" ] && TEST_DIR=/mnt/test -[ -z "$TEST_DEV" ] && TEST_DEV=/dev/sdb1 -#[ -z "$TEST_LOGDEV" ] && TEST_LOGDEV=/dev/sdb3 -[ -z "$SCRATCH_MNT" ] && SCRATCH_MNT=/mnt/scratch -[ -z "$SCRATCH_DEV" ] && SCRATCH_DEV=/dev/sdb2 -#[ -z "$SCRATCH_LOGDEV" ] && SCRATCH_LOGDEV=/dev/sdb4 -#[ -z "$SCRATCH_RTDEV" ] && SCRATCH_RTDEV=/dev/sdb5 - diff --git a/configs/surly.config b/configs/surly.config deleted file mode 100644 index 67c69a3..0000000 --- a/configs/surly.config +++ /dev/null @@ -1,11 +0,0 @@ -# Autogenerated config for host surly, by xaiki's hack.pl -TEST_DEV=/dev/hda9 -TEST_DIR=/mnt/xfs1 -SCRATCH_DEV=/dev/hda8 -SCRATCH_MNT=/mnt/xfs0 -SCRATCH_LOGDEV=/dev/hda10 -TAPE_DEV=/dev/st0 -RMT_TAPE_DEV=fuzzy:/dev/st0 -RMT_IRIXTAPE_DEV=blub:/dev/tape -RMT_TAPE_USER=guest - diff --git a/configs/tinkle.config b/configs/tinkle.config deleted file mode 100644 index 5b534e8..0000000 --- a/configs/tinkle.config +++ /dev/null @@ -1,7 +0,0 @@ -# Autogenerated config for host tinkle, by xaiki's hack.pl -#irix-patchbox-tinkle -TEST_DEV=/dev/dsk/dks0d2s0 -TEST_DIR=/mnt/xfs_test -SCRATCH_DEV=/dev/dsk/dks0d2s1 -SCRATCH_MNT=/mnt/xfs_scratch - diff --git a/configs/usermode.config b/configs/usermode.config deleted file mode 100644 index 12734a3..0000000 --- a/configs/usermode.config +++ /dev/null @@ -1,8 +0,0 @@ -# Autogenerated config for host usermode, by xaiki's hack.pl -TEST_DEV=/dev/ubd/1 -TEST_DIR=/mnt/test -SCRATCH_DEV=/dev/ubd/2 -SCRATCH_MNT=/mnt/scratch -SCRATCH_RTDEV=/dev/ubd/3 -SCRATCH_LOGDEV=/dev/ubd/4 - diff --git a/configs/vimes.config b/configs/vimes.config deleted file mode 100644 index afc129b..0000000 --- a/configs/vimes.config +++ /dev/null @@ -1,12 +0,0 @@ -# Autogenerated config for host vimes, by xaiki's hack.pl -# dedicated qa machine, used to be sheila -[ -z "$MODULAR" ] && MODULAR=1 -EMAIL="ddiss@sgi.com" -[ -z "$TEST_DIR" ] && TEST_DIR=/mnt/test -[ -z "$TEST_DEV" ] && TEST_DEV=/dev/hdb1 -[ -z "$TEST_LOGDEV" ] && TEST_LOGDEV=/dev/hdb3 -[ -z "$SCRATCH_MNT" ] && SCRATCH_MNT=/mnt/scratch -[ -z "$SCRATCH_DEV" ] && SCRATCH_DEV=/dev/hdb2 -[ -z "$SCRATCH_LOGDEV" ] && SCRATCH_LOGDEV=/dev/hdb4 -[ -z "$SCRATCH_RTDEV" ] && SCRATCH_RTDEV=/dev/sdb5 - -- 1.5.3.8 From pwhite@sgi.com Thu Mar 14 08:06:26 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from cthulhu.engr.sgi.com (cthulhu.engr.sgi.com [150.166.39.100]) by oss.sgi.com (Postfix) with ESMTP id 6D8ED7F5E for ; Thu, 14 Mar 2013 08:06:12 -0500 (CDT) Received: from polaris-admin.engr.sgi.com (polaris-admin.engr.sgi.com [150.166.41.54]) by cthulhu.engr.sgi.com (8.12.10/8.12.10/SuSE Linux 0.7) with ESMTP id r2ED6Bx9007460 for ; Thu, 14 Mar 2013 06:06:11 -0700 Received: by polaris-admin.engr.sgi.com (Postfix, from userid 48024) id 995A753DEAF9; Thu, 14 Mar 2013 06:06:11 -0700 (PDT) Date: Thu, 14 Mar 2013 06:06:11 -0700 To: xfs@oss.sgi.com Subject: [PATCH 12/18] xfstests: adjusts group files for other fs tests User-Agent: nail 11.25 7/29/05 MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Transfer-Encoding: 7bit Message-Id: <20130314130611.995A753DEAF9@polaris-admin.engr.sgi.com> From: pwhite@sgi.com (Philip White) From: Phil White This is a rebasing & resubmit of a dchinner patch. His comments on the original: ----------------- These are tests that are shared between multiple filesystems (moved to shared), and udf/btrfs/ext4 specific tests, moved to appropriate directories. I created the "shared" directory to indicate tests that are not truly generic, but also not filesystem specific. They might rely on a feature that is only implmented in a few filesystems and so can't be truly generic. ----------------- Again, the actual test movements are in a later patch. Signed-off-by: Phil White --- check | 4 ++-- common | 12 +++++------- group | 19 ------------------- tests/btrfs/group | 10 ++++++++++ tests/ext4/group | 6 ++++++ tests/shared/group | 10 ++++++++++ tests/udf/group | 8 ++++++++ tests/xfs/group | 3 +++ 8 files changed, 44 insertions(+), 28 deletions(-) create mode 100644 tests/btrfs/group create mode 100644 tests/ext4/group create mode 100644 tests/shared/group create mode 100644 tests/udf/group diff --git a/check b/check index dea63d7..9819a84 100755 --- a/check +++ b/check @@ -97,7 +97,7 @@ END { if (NR > 0) { echo "" >>check.log date >>check.log - echo $list | fmt | sed -e 's/^/ /' -e 's;tests/;;g' >>check.log + echo $list | fmt | sed -e 's/^/ /' -e 's;$SRC_DIR/;;g' >>check.log $interrupt && echo "Interrupted!" >>check.log if [ ! -z "$n_try" -a $n_try != 0 ] @@ -178,7 +178,7 @@ do # the filename for the test and the name output are different. # we don't include the tests/ directory in the name output. - seqnum=`echo $seq | sed -e 's;tests/;;'` + seqnum=`echo $seq | sed -e 's;$SRC_DIR/;;'` echo -n "$seqnum" diff --git a/common b/common index 57c3ac5..d7207d6 100644 --- a/common +++ b/common @@ -33,9 +33,8 @@ have_test_arg=false randomize=false timestamp=${TIMESTAMP:=false} SUPPORTED_TESTS="[0-9][0-9][0-9] [0-9][0-9][0-9][0-9]" -TEST_GROUP_DIR="tests" -GENERIC_GROUP_DIR="$TEST_GROUP_DIR/generic" -XFS_GROUP_DIR="$TEST_GROUP_DIR/xfs" +SRC_DIR="tests" +SRC_GROUPS="generic shared" _setenvironment() { @@ -46,13 +45,12 @@ _setenvironment() get_group_list() { grp=$1 - dirs=". $GENERIC_GROUP_DIR $XFS_GROUP_DIR" - for d in $dirs; do - l=$(sed -n < $d/group \ + for d in $SRC_GROUPS $FSTYP; do + l=$(sed -n < $SRC_DIR/$d/group \ -e 's/#.*//' \ -e 's/$/ /' \ - -e "s;\(^[0-9][0-9][0-9]\).* $grp .*;$d/\1;p") + -e "s;\(^[0-9][0-9][0-9]\).* $grp .*;$SRC_DIR/$d/\1;p") grpl="$grpl $l" done echo $grpl diff --git a/group b/group index 9e8ee53..0f8d1fc 100644 --- a/group +++ b/group @@ -114,25 +114,6 @@ deprecated # TIME_FACTOR: Usually means factor of run time, or number of operations stress -# test-group association ... one line per test -# -040 other auto -051 acl udf auto quick -068 other auto freeze dangerous stress -098 udf auto -101 udf -102 udf -177 rw other auto -218 auto fsr quick -243 auto quick prealloc -252 auto quick prealloc -254 auto quick -264 auto -265 auto -271 auto rw quick -272 auto enospc rw -276 auto rw metadata -284 auto 285 auto rw 286 other 287 auto dump quota quick diff --git a/tests/btrfs/group b/tests/btrfs/group new file mode 100644 index 0000000..8926c40 --- /dev/null +++ b/tests/btrfs/group @@ -0,0 +1,10 @@ +# QA groups control file +# Defines test groups and nominal group owners +# - do not start group names with a digit +# - comment line before each group is "new" description +# +254 auto quick +264 auto +265 auto +276 auto rw metadata +284 auto diff --git a/tests/ext4/group b/tests/ext4/group new file mode 100644 index 0000000..1d6c041 --- /dev/null +++ b/tests/ext4/group @@ -0,0 +1,6 @@ +# QA groups control file +# Defines test groups and nominal group owners +# - do not start group names with a digit +# - comment line before each group is "new" description +# +271 auto rw quick diff --git a/tests/shared/group b/tests/shared/group new file mode 100644 index 0000000..b2ff729 --- /dev/null +++ b/tests/shared/group @@ -0,0 +1,10 @@ +# QA groups control file +# Defines test groups and nominal group owners +# - do not start group names with a digit +# - comment line before each group is "new" description +# +051 acl udf auto quick +068 other auto freeze dangerous +218 auto fsr quick +243 auto quick prealloc +272 auto enospc rw diff --git a/tests/udf/group b/tests/udf/group new file mode 100644 index 0000000..24f682c --- /dev/null +++ b/tests/udf/group @@ -0,0 +1,8 @@ +# QA groups control file +# Defines test groups and nominal group owners +# - do not start group names with a digit +# - comment line before each group is "new" description +# +098 udf auto +101 udf +102 udf diff --git a/tests/xfs/group b/tests/xfs/group index 0affcba..c165752 100644 --- a/tests/xfs/group +++ b/tests/xfs/group @@ -26,6 +26,7 @@ 037 dump ioctl remote tape 038 dump ioctl remote tape 039 dump ioctl remote tape +040 other auto 041 growfs ioctl auto 042 fsr ioctl auto 043 dump ioctl tape @@ -124,6 +125,7 @@ 174 rw filestreams auto 175 dmapi auto 176 dmapi auto +177 rw other auto 178 mkfs other auto 179 metadata rw auto 180 metadata rw auto @@ -158,6 +160,7 @@ 242 auto quick prealloc 244 auto quota quick 250 auto quick rw prealloc metadata +252 auto quick prealloc 253 auto quick 259 auto quick 261 auto quick quota -- 1.5.3.8 From pwhite@sgi.com Thu Mar 14 08:06:28 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from cthulhu.engr.sgi.com (cthulhu.engr.sgi.com [150.166.39.100]) by oss.sgi.com (Postfix) with ESMTP id 7FD3E7F5F for ; Thu, 14 Mar 2013 08:06:12 -0500 (CDT) Received: from polaris-admin.engr.sgi.com (polaris-admin.engr.sgi.com [150.166.41.54]) by cthulhu.engr.sgi.com (8.12.10/8.12.10/SuSE Linux 0.7) with ESMTP id r2ED6Bx7007472 for ; Thu, 14 Mar 2013 06:06:11 -0700 Received: by polaris-admin.engr.sgi.com (Postfix, from userid 48024) id 9B6AB53DEAFA; Thu, 14 Mar 2013 06:06:11 -0700 (PDT) Date: Thu, 14 Mar 2013 06:06:11 -0700 To: xfs@oss.sgi.com Subject: [PATCH 13/18] xfstests: Change command line parsing for new structure User-Agent: nail 11.25 7/29/05 MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Transfer-Encoding: 7bit Message-Id: <20130314130611.9B6AB53DEAFA@polaris-admin.engr.sgi.com> From: pwhite@sgi.com (Philip White) From: Phil White This is a rebasing & resubmit of a dchinner patch. His comments on the original: ----------------- Now that tests are in separate subdirectories, they cannot be selected purely by test number on the command line. We need to specify the test by subdir and test name, so effectively we move to specifying them by regexes on the command line rather than by expanding a range internally. This is needed to support non-numeric test names as well, so the change may as well be made here. This means the command line parsing needs to change from trying to detect tests by a regex match to a processing loop that simply parses the tests and checks for there existence. Hence the moment we find an argument that is not a switch (i.e no preceeding "-"), we move from the arg processing loop to the test name processing loop. IOWs, tests must be specified last on the command line. ----------------- Signed-off-by: Phil White --- check | 3 +- common | 85 ++++++++++++++++++++++++++++------------------------------------ 2 files changed, 38 insertions(+), 50 deletions(-) diff --git a/check b/check index 9819a84..25f6c7e 100755 --- a/check +++ b/check @@ -70,8 +70,7 @@ check options testlist options -g group[,group...] include tests from these groups -x group[,group...] exclude tests from these groups - NNN include test NNN - NNN-NNN include test range (eg. 012-021) + [testlist] include tests matching names in testlist ' } diff --git a/common b/common index d7207d6..1c6a08c 100644 --- a/common +++ b/common @@ -56,25 +56,6 @@ get_group_list() echo $grpl } -expand_test_numbers() -{ - # strip leading zeros, could be considered octal. - start=`echo $1 | sed 's/^0*//'` - end=`echo $2 | sed 's/^0*//'` - $AWK_PROG /dev/null ; then - # in group file ... OK - echo $id >>$tmp.list - else - # oops - echo "$id - unknown test, ignored" - fi - done -} - _wallclock() { date "+%H %M %S" | $AWK_PROG '{ print $1*3600 + $2*60 + $3 }' @@ -105,6 +86,7 @@ then exit 1 fi +# Process command arguments first. while [ $# -gt 0 ]; do case "$1" in -\? | -h | --help) usage ;; @@ -158,43 +140,50 @@ while [ $# -gt 0 ]; do -r) randomize=true ;; -T) timestamp=true ;; - "$SUPPORTED_TESTS") - echo "No tests?" - status=1 - exit $status - ;; - - [0-9]*-[0-9]*) - eval `echo $1 | sed -e 's/^/start=/' -e 's/-/ end=/'` - expand_test_numbers $start $end - have_test_arg=true - ;; - - [0-9]*-) - eval `echo $1 | sed -e 's/^/start=/' -e 's/-//'` - end=`echo $SUPPORTED_TESTS | \ - sed -e 's/\[0-9]//g' -e 's/ *$//' -e 's/.* //'` - if [ -z "$end" ]; then - echo "No tests in range \"$1\"?" - status=1 - exit $status - fi - - expand_test_numbers $start $end - have_test_arg=true - ;; - --large-fs) export LARGE_SCRATCH_DEV=yes ;; --extra-space=*) export SCRATCH_DEV_EMPTY_SPACE=${r#*=} ;; -*) usage ;; - *) expand_test_numbers $1 $1 ; - have_test_arg=true - ;; + *) # not an argument, we've got tests now. + have_test_arg=true ;; esac + + # if we've found a test specification, the break out of the processing + # loop before we shift the arguments so that this is the first argument + # that we process in the test arg loop below. + if $have_test_arg; then + break; + fi + shift done +# Process tests from command line now. +if $have_test_arg; then + while [ $# -gt 0 ]; do + case "$1" in + -*) echo "Argments before tests, please!" + status=1 + exit $status + ;; + *) test_dir=`dirname $1` + test_name=`basename $1` + group_file=$SRC_DIR/$test_dir/group + + if grep "^$testname" $group_file >/dev/null ; then + # in group file ... OK + echo $SRC_DIR/$1 >>$tmp.list + else + # oops + echo "$1 - unknown test, ignored" + fi + ;; + esac + + shift + done +fi + if [ -s $tmp.list ] then # found some valid test numbers ... this is good -- 1.5.3.8 From pwhite@sgi.com Thu Mar 14 08:06:29 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from cthulhu.engr.sgi.com (cthulhu.engr.sgi.com [150.166.39.100]) by oss.sgi.com (Postfix) with ESMTP id 8DF147F51 for ; Thu, 14 Mar 2013 08:06:12 -0500 (CDT) Received: from polaris-admin.engr.sgi.com (polaris-admin.engr.sgi.com [150.166.41.54]) by cthulhu.engr.sgi.com (8.12.10/8.12.10/SuSE Linux 0.7) with ESMTP id r2ED6Bx9007459 for ; Thu, 14 Mar 2013 06:06:11 -0700 Received: by polaris-admin.engr.sgi.com (Postfix, from userid 48024) id A163253DEAFB; Thu, 14 Mar 2013 06:06:11 -0700 (PDT) Date: Thu, 14 Mar 2013 06:06:11 -0700 To: xfs@oss.sgi.com Subject: [PATCH 14/18] xfstests: remove -x functionality User-Agent: nail 11.25 7/29/05 MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Transfer-Encoding: 7bit Message-Id: <20130314130611.A163253DEAFB@polaris-admin.engr.sgi.com> From: pwhite@sgi.com (Philip White) From: Phil White This is a rebasing & resubmit of a dchinner patch. His comments on the original: ----------------- Now that there are no tests in the top level directory, the exlude group functionality no longer works (-x group) as it cannot find tests to build an initial list of tests. Rework the the exclude group implementation to operate correctly on the new test locations. Also, swtich from sed to grep for exclusion because sed has problems distnguishing the '/' in path names from regex control... ----------------- This one is mildly different from the original as it modifies infrastructure which remains in common. In Dave's original patch, that had all been moved into check. Signed-off-by: Phil White --- common | 43 +++++++++++++++++++++++++++++++------------ 1 files changed, 31 insertions(+), 12 deletions(-) diff --git a/common b/common index 1c6a08c..4732a66 100644 --- a/common +++ b/common @@ -56,6 +56,19 @@ get_group_list() echo $grpl } +# find all tests, excluding files that are test metadata such as group files. +# This assumes that tests are defined purely by alphanumeric filenames with no +# ".xyz" extensions in the name. +get_all_tests() +{ + touch $tmp.list + for d in $SRC_GROUPS $FSTYP; do + ls $SRC_DIR/$d/* | \ + grep -v "\..*" | \ + grep -v group >> $tmp.list 2>/dev/null + done +} + _wallclock() { date "+%H %M %S" | $AWK_PROG '{ print $1*3600 + $2*60 + $3 }' @@ -69,7 +82,7 @@ _timestamp() # start the initialisation work now _setenvironment -rm -f $tmp.list $tmp.tmp $tmp.sed $here/$iam.out +rm -f $tmp.list $tmp.tmp $tmp.grep $here/$iam.out # Autodetect fs type based on what's on $TEST_DEV if [ "$HOSTOS" == "Linux" ] @@ -109,27 +122,33 @@ while [ $# -gt 0 ]; do ;; -x) xgroup=$2 ; shift ; - [ ! -s $tmp.list ] && ls $SUPPORTED_TESTS >$tmp.list 2>/dev/null + + # Note: behaviour is dependent on command line ordering of + # -g and -x parameters. If there are no preceding -g commands, + # this works on all tests, otherwise just the tests specified by + # the early -g inclusions. + [ ! -s $tmp.list ] && get_all_tests + group_list=$(get_group_list $xgroup) if [ -z "$group_list" ]; then echo "Group \"$xgroup\" is empty or not defined?" exit 1 fi - rm -f $tmp.sed - numsed=0 + rm -f $tmp.grep + numgrep=0 for t in $group_list do - if [ $numsed -gt 100 ]; then - sed -f $tmp.sed <$tmp.list >$tmp.tmp + if [ $numgrep -gt 100 ]; then + grep -v -f $tmp.grep <$tmp.list >$tmp.tmp mv $tmp.tmp $tmp.list - numsed=0 - rm -f $tmp.sed + numgrep=0 + rm -f $tmp.grep fi - echo "/^$t\$/d" >>$tmp.sed - numsed=`expr $numsed + 1` + echo "/^$t\$/d" >>$tmp.grep + numgrep=`expr $numgrep + 1` done - sed -f $tmp.sed <$tmp.list >$tmp.tmp + grep -v -f $tmp.grep <$tmp.list >$tmp.tmp mv $tmp.tmp $tmp.list ;; @@ -199,7 +218,7 @@ fi # sort the list of tests into numeric order list=`sort -n $tmp.list` -rm -f $tmp.list $tmp.tmp $tmp.sed +rm -f $tmp.list $tmp.tmp $tmp.grep if $randomize then -- 1.5.3.8 From pwhite@sgi.com Thu Mar 14 08:06:31 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from cthulhu.engr.sgi.com (cthulhu.engr.sgi.com [150.166.39.100]) by oss.sgi.com (Postfix) with ESMTP id 848697F60 for ; Thu, 14 Mar 2013 08:06:12 -0500 (CDT) Received: from polaris-admin.engr.sgi.com (polaris-admin.engr.sgi.com [150.166.41.54]) by cthulhu.engr.sgi.com (8.12.10/8.12.10/SuSE Linux 0.7) with ESMTP id r2ED6Bx9007456 for ; Thu, 14 Mar 2013 06:06:11 -0700 Received: by polaris-admin.engr.sgi.com (Postfix, from userid 48024) id 935D953DEAF8; Thu, 14 Mar 2013 06:06:11 -0700 (PDT) Date: Thu, 14 Mar 2013 06:06:11 -0700 To: xfs@oss.sgi.com Subject: [PATCH 11/18] xfstests: add tests into tests/xfs/group User-Agent: nail 11.25 7/29/05 MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Transfer-Encoding: 7bit Message-Id: <20130314130611.935D953DEAF8@polaris-admin.engr.sgi.com> From: pwhite@sgi.com (Philip White) From: Phil White This is a rebasing & resubmit of a dchinner patch. His comments on the original: ----------------- And into tests/xfs. Tests found and moved via: $ grep "supported_fs xfs$" [0-2]* | cut -d : -f 1 > xfs.tests $ for i in `cat xfs.tests`; do > git mv $i* tests/xfs/ > grep ^$i group >> tests/xfs/group > sed -i -e "/^$i/d" group > done Output now looks like: sudo ./check -g quick -r FSTYP -- xfs (debug) PLATFORM -- Linux/x86_64 test-1 3.5.0-rc5-dgc+ MKFS_OPTIONS -- -f -bsize=4096 /dev/vdb MOUNT_OPTIONS -- /dev/vdb /mnt/scratch xfs/170 4s generic/120 16s generic/248 0s generic/213 0s generic/256 39s xfs/121 6s xfs/026 11s generic/131 1s xfs/187 1s generic/135 0s .... ----------------- For ease of reviewing, I put all the actual test movements into a separate patch. Signed-off-by: Phil White --- common | 3 +- group | 172 ------------------------------------------------------- tests/xfs/group | 172 +++++++++++++++++++++++++++++++++++++++++++++++++++++++ 3 files changed, 174 insertions(+), 173 deletions(-) create mode 100644 tests/xfs/group diff --git a/common b/common index b41d4d0..57c3ac5 100644 --- a/common +++ b/common @@ -35,6 +35,7 @@ timestamp=${TIMESTAMP:=false} SUPPORTED_TESTS="[0-9][0-9][0-9] [0-9][0-9][0-9][0-9]" TEST_GROUP_DIR="tests" GENERIC_GROUP_DIR="$TEST_GROUP_DIR/generic" +XFS_GROUP_DIR="$TEST_GROUP_DIR/xfs" _setenvironment() { @@ -45,7 +46,7 @@ _setenvironment() get_group_list() { grp=$1 - dirs=". $GENERIC_GROUP_DIR" + dirs=". $GENERIC_GROUP_DIR $XFS_GROUP_DIR" for d in $dirs; do l=$(sed -n < $d/group \ diff --git a/group b/group index dd0b622..9e8ee53 100644 --- a/group +++ b/group @@ -116,194 +116,22 @@ stress # test-group association ... one line per test # -003 db auto quick -004 db auto quick -008 rw ioctl auto quick -009 rw ioctl auto prealloc quick -012 rw auto quick -016 rw auto quick -017 mount auto quick stress -018 deprecated # log logprint v2log -019 mkfs auto quick -021 db attr auto quick -022 dump ioctl tape -023 dump ioctl tape -024 dump ioctl tape -025 dump ioctl tape -026 dump ioctl auto quick -027 dump ioctl auto quick -028 dump ioctl auto quick -029 mkfs logprint log auto quick -030 repair auto quick -031 repair mkfs auto quick -032 mkfs auto quick -033 repair auto quick -034 other auto quick -035 dump ioctl tape auto -036 dump ioctl remote tape -037 dump ioctl remote tape -038 dump ioctl remote tape -039 dump ioctl remote tape 040 other auto -041 growfs ioctl auto -042 fsr ioctl auto -043 dump ioctl tape -044 other auto -045 other auto quick -046 dump ioctl auto quick -047 dump ioctl auto -048 other auto quick -049 rw auto quick -050 quota auto quick 051 acl udf auto quick -052 quota db auto quick -054 quota auto quick -055 dump ioctl remote tape -056 dump ioctl auto quick -057 acl auto -058 acl auto -059 dump ioctl auto quick -060 dump ioctl auto quick -061 dump ioctl auto quick -063 dump attr auto quick -064 dump auto -065 dump auto -066 dump ioctl auto quick -067 acl attr auto quick 068 other auto freeze dangerous stress -071 rw auto -072 rw auto prealloc quick -073 copy auto -078 growfs auto quick -080 rw ioctl -081 deprecated # log logprint quota -082 deprecated # log logprint v2log -084 ioctl rw auto -085 log auto quick -086 log v2log auto -087 log v2log auto quota stress -090 rw auto -092 other auto quick -094 metadata dir ioctl auto -095 log v2log auto -096 mkfs v2log auto quick 098 udf auto 101 udf 102 udf -103 metadata dir ioctl auto quick -104 growfs ioctl prealloc auto stress -106 quota -107 quota -108 quota auto quick -109 metadata auto -110 repair auto -111 ioctl -114 parent attr stress -115 parent attr -116 quota auto quick -118 quota auto quick -119 log v2log auto freeze dangerous -121 log auto quick -122 other auto quick -134 quota auto quick -136 attr2 -137 metadata log auto -138 metadata log auto -139 metadata log auto -140 metadata log auto -142 dmapi auto -143 dmapi auto -144 dmapi auto -145 dmapi auto -146 dmapi auto -147 dmapi auto -148 repair auto -149 repair auto -150 dmapi auto -151 dmapi auto -152 dmapi auto -153 dmapi auto -154 dmapi auto -155 dmapi auto -156 dmapi auto -157 dmapi auto -158 dmapi auto -159 dmapi auto -160 dmapi auto -161 dmapi auto -162 dmapi auto -163 dmapi auto -164 rw pattern auto prealloc quick -165 rw pattern auto prealloc quick -166 rw metadata auto quick -167 rw metadata auto stress -168 dmapi auto -170 rw filestreams auto quick -# the next three tests are not deterministic enough to get the -# "right" result on all platforms/configuration, so don't run -# them by default. -171 rw filestreams -172 rw filestreams -173 rw filestreams -174 rw filestreams auto -175 dmapi auto -176 dmapi auto 177 rw other auto -178 mkfs other auto -179 metadata rw auto -180 metadata rw auto -181 log auto quick -182 metadata rw auto -183 rw other auto quick -185 dmapi auto -186 attr auto quick -187 attr auto quick -188 ci dir auto -189 mount auto quick -190 rw auto quick -191 nfs4acl auto -194 rw auto -195 ioctl dump auto quick -196 quota auto quick -197 dir auto quick -199 mount auto quick -200 mount auto quick -201 metadata auto quick -202 repair auto quick -203 ioctl auto -205 metadata rw auto -206 growfs auto quick -216 log metadata auto quick -217 log metadata auto 218 auto fsr quick -220 auto quota quick -222 auto fsr ioctl quick -227 auto fsr -229 auto rw -238 auto quick metadata ioctl -242 auto quick prealloc 243 auto quick prealloc -244 auto quota quick -250 auto quick rw prealloc metadata 252 auto quick prealloc -253 auto quick 254 auto quick -259 auto quick -261 auto quick quota -262 auto quick quota 264 auto 265 auto -266 dump ioctl auto quick -267 dump ioctl tape -268 dump ioctl tape 271 auto rw quick 272 auto enospc rw 276 auto rw metadata -278 repair auto -279 auto mkfs -281 dump ioctl auto quick -282 dump ioctl auto quick -283 dump ioctl auto quick 284 auto 285 auto rw 286 other diff --git a/tests/xfs/group b/tests/xfs/group new file mode 100644 index 0000000..0affcba --- /dev/null +++ b/tests/xfs/group @@ -0,0 +1,172 @@ +003 db auto quick +004 db auto quick +008 rw ioctl auto quick +009 rw ioctl auto prealloc quick +012 rw auto quick +016 rw auto quick +017 mount auto quick stress +018 deprecated # log logprint v2log +019 mkfs auto quick +021 db attr auto quick +022 dump ioctl tape +023 dump ioctl tape +024 dump ioctl tape +025 dump ioctl tape +026 dump ioctl auto quick +027 dump ioctl auto quick +028 dump ioctl auto quick +029 mkfs logprint log auto quick +030 repair auto quick +031 repair mkfs auto quick +032 mkfs auto quick +033 repair auto quick +034 other auto quick +035 dump ioctl tape auto +036 dump ioctl remote tape +037 dump ioctl remote tape +038 dump ioctl remote tape +039 dump ioctl remote tape +041 growfs ioctl auto +042 fsr ioctl auto +043 dump ioctl tape +044 other auto +045 other auto quick +046 dump ioctl auto quick +047 dump ioctl auto +048 other auto quick +049 rw auto quick +050 quota auto quick +052 quota db auto quick +054 quota auto quick +055 dump ioctl remote tape +056 dump ioctl auto quick +057 acl auto +058 acl auto +059 dump ioctl auto quick +060 dump ioctl auto quick +061 dump ioctl auto quick +063 dump attr auto quick +064 dump auto +065 dump auto +066 dump ioctl auto quick +067 acl attr auto quick +071 rw auto +072 rw auto prealloc quick +073 copy auto +078 growfs auto quick +080 rw ioctl +081 deprecated # log logprint quota +082 deprecated # log logprint v2log +084 ioctl rw auto +085 log auto quick +086 log v2log auto +087 log v2log auto quota stress +090 rw auto +092 other auto quick +094 metadata dir ioctl auto +095 log v2log auto +096 mkfs v2log auto quick +103 metadata dir ioctl auto quick +104 growfs ioctl prealloc auto stress +106 quota +107 quota +108 quota auto quick +109 metadata auto +110 repair auto +111 ioctl +114 parent attr stress +115 parent attr +116 quota auto quick +118 quota auto quick +119 log v2log auto freeze dangerous +121 log auto quick +122 other auto quick +134 quota auto quick +136 attr2 +137 metadata log auto +138 metadata log auto +139 metadata log auto +140 metadata log auto +142 dmapi auto +143 dmapi auto +144 dmapi auto +145 dmapi auto +146 dmapi auto +147 dmapi auto +148 repair auto +149 repair auto +150 dmapi auto +151 dmapi auto +152 dmapi auto +153 dmapi auto +154 dmapi auto +155 dmapi auto +156 dmapi auto +157 dmapi auto +158 dmapi auto +159 dmapi auto +160 dmapi auto +161 dmapi auto +162 dmapi auto +163 dmapi auto +164 rw pattern auto prealloc quick +165 rw pattern auto prealloc quick +166 rw metadata auto quick +167 rw metadata auto stress +168 dmapi auto +170 rw filestreams auto quick +# the next three tests are not deterministic enough to get the +# "right" result on all platforms/configuration, so don't run +# them by default. +171 rw filestreams +172 rw filestreams +173 rw filestreams +174 rw filestreams auto +175 dmapi auto +176 dmapi auto +178 mkfs other auto +179 metadata rw auto +180 metadata rw auto +181 log auto quick +182 metadata rw auto +183 rw other auto quick +185 dmapi auto +186 attr auto quick +187 attr auto quick +188 ci dir auto +189 mount auto quick +190 rw auto quick +191 nfs4acl auto +194 rw auto +195 ioctl dump auto quick +196 quota auto quick +197 dir auto quick +199 mount auto quick +200 mount auto quick +201 metadata auto quick +202 repair auto quick +203 ioctl auto +205 metadata rw auto +206 growfs auto quick +216 log metadata auto quick +217 log metadata auto +220 auto quota quick +222 auto fsr ioctl quick +227 auto fsr +229 auto rw +238 auto quick metadata ioctl +242 auto quick prealloc +244 auto quota quick +250 auto quick rw prealloc metadata +253 auto quick +259 auto quick +261 auto quick quota +262 auto quick quota +266 dump ioctl auto quick +267 dump ioctl tape +268 dump ioctl tape +278 repair auto +279 auto mkfs +281 dump ioctl auto quick +282 dump ioctl auto quick +283 dump ioctl auto quick -- 1.5.3.8 From pwhite@sgi.com Thu Mar 14 08:06:34 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD,T_FRT_LOLITA1 autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from cthulhu.engr.sgi.com (cthulhu.engr.sgi.com [150.166.39.100]) by oss.sgi.com (Postfix) with ESMTP id 93D6E7F61 for ; Thu, 14 Mar 2013 08:06:12 -0500 (CDT) Received: from polaris-admin.engr.sgi.com (polaris-admin.engr.sgi.com [150.166.41.54]) by cthulhu.engr.sgi.com (8.12.10/8.12.10/SuSE Linux 0.7) with ESMTP id r2ED6Bx7007473 for ; Thu, 14 Mar 2013 06:06:11 -0700 Received: by polaris-admin.engr.sgi.com (Postfix, from userid 48024) id A852B53DEAF1; Thu, 14 Mar 2013 06:06:11 -0700 (PDT) Date: Thu, 14 Mar 2013 06:06:11 -0700 To: xfs@oss.sgi.com Subject: [PATCH 15/18] xfstests: implement a result directory for tests User-Agent: nail 11.25 7/29/05 MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Transfer-Encoding: 7bit Message-Id: <20130314130611.A852B53DEAF1@polaris-admin.engr.sgi.com> From: pwhite@sgi.com (Philip White) From: Phil White This is a rebasing & resubmit of a dchinner patch. His comments on the original: ----------------- Currently each test gets it's sequence number from it's name. It separates this from the path via basename, and uses it for outputting full, notrun an dother status/log files. Hence these end up in the top level directory. All these output files need to go somewhere other than the top level directory. Right now the check script is looking for them in the new test directories (e.g. for the notrun files), but it woul dbe good to be able to separate the test source form the test output. Hence create an output directory which has a similar heirarchy to the test source directory. Create it on demand when we build the list of tests to run if it doesn't already exist. Change the high level check script to set up this variable appropriately for each test that is being run, and to use this new output directory for it's result files as well. The next commit will change all the tests themselves to use the new This is the first (small) step in being able to store test results in an external location for archival/data mining purposes ----------------- Signed-off-by: Phil White --- check | 31 +++++++++++++----- common | 4 ++- common.attr | 4 +- common.defrag | 4 +- common.dump | 74 ++++++++++++++++++++++---------------------- common.filestreams | 4 +- common.log | 4 +- common.quota | 18 +++++----- common.rc | 88 ++++++++++++++++++++++++++-------------------------- common.scsi_debug | 2 +- 10 files changed, 124 insertions(+), 109 deletions(-) diff --git a/check b/check index 25f6c7e..80f748a 100755 --- a/check +++ b/check @@ -168,6 +168,12 @@ if [ ! -z "$SCRATCH_DEV" ]; then fi fi +mkdir -p $RESULT_BASE +if [ ! -d $RESULT_BASE ]; then + echo "failed to create results directory $RESULTS_BASE" + exit 1; +fi + seq="check" _check_test_fs @@ -179,6 +185,13 @@ do # we don't include the tests/ directory in the name output. seqnum=`echo $seq | sed -e 's;$SRC_DIR/;;'` + # Similarly, the result directory needs to replace the tests/ + # part of the test location. + group=`dirname $seq` + export RESULT_DIR=`echo $group | sed -e "s;$SRC_DIR;$RESULT_BASE;"` + mkdir -p $RESULT_DIR + seqres="$RESULT_BASE/$seqnum" + echo -n "$seqnum" if $showme @@ -191,7 +204,7 @@ do else # really going to try and run this one # - rm -f $seq.out.bad + rm -f $seqres.out.bad # slashes now in names, sed barfs on them so use grep lasttime=`grep -w ^$seq check.time | awk '// {print $2}'` @@ -201,7 +214,7 @@ do else echo -n " " # prettier output with timestamps. fi - rm -f core $seq.notrun + rm -f core $seqres.notrun start=`_wallclock` $timestamp && echo -n " ["`date "+%T"`"]" @@ -222,11 +235,11 @@ do err=true fi - if [ -f $seq.notrun ] + if [ -f $seqres.notrun ] then $timestamp || echo -n " [not run] " $timestamp && echo " [not run]" && echo -n " $seqnum -- " - cat $seq.notrun + cat $seqres.notrun notrun="$notrun $seqnum" else if [ $sts -ne 0 ] @@ -250,9 +263,9 @@ do fi echo "" else - echo " - output mismatch (see $seq.out.bad)" - mv $tmp.out $seq.out.bad - $diff $seq.out $seq.out.bad | { + echo " - output mismatch (see $seqres.out.bad)" + mv $tmp.out $seqres.out.bad + $diff $seq.out $seqres.out.bad | { if test "$DIFF_LENGTH" -le 0; then cat else @@ -260,7 +273,7 @@ do fi; } | \ sed -e 's/^\(.\)/ \1/' echo " ..." - echo " (Run '$diff $seq.out $seq.out.bad' to see the" \ + echo " (Run '$diff $seq.out $seqres.out.bad' to see the" \ "entire diff)" err=true fi @@ -277,7 +290,7 @@ do n_bad=`expr $n_bad + 1` quick=false fi - if [ ! -f $seq.notrun ] + if [ ! -f $seqres.notrun ] then try="$try $seqnum" n_try=`expr $n_try + 1` diff --git a/common b/common index 4732a66..ab6a11b 100644 --- a/common +++ b/common @@ -33,9 +33,11 @@ have_test_arg=false randomize=false timestamp=${TIMESTAMP:=false} SUPPORTED_TESTS="[0-9][0-9][0-9] [0-9][0-9][0-9][0-9]" -SRC_DIR="tests" SRC_GROUPS="generic shared" +export SRC_DIR="tests" +export RESULT_BASE=${RESULT_BASE:="results"} + _setenvironment() { MSGVERB="text:action" diff --git a/common.attr b/common.attr index 6e2c004..69bcb01 100644 --- a/common.attr +++ b/common.attr @@ -129,7 +129,7 @@ _require_acls() # touch $TEST_DIR/syscalltest chacl -l $TEST_DIR/syscalltest > $TEST_DIR/syscalltest.out 2>&1 - cat $TEST_DIR/syscalltest.out >> $here/$seq.full + cat $TEST_DIR/syscalltest.out >> $RESULT_DIR/$seq.full if grep -q 'Function not implemented' $TEST_DIR/syscalltest.out; then _notrun "kernel does not support ACLs" @@ -164,7 +164,7 @@ _require_attrs() # touch $TEST_DIR/syscalltest attr -s "user.xfstests" -V "attr" $TEST_DIR > $TEST_DIR/syscalltest.out 2>&1 - cat $TEST_DIR/syscalltest.out >> $here/$seq.full + cat $TEST_DIR/syscalltest.out >> $RESULT_DIR/$seq.full if grep -q 'Function not implemented' $TEST_DIR/syscalltest.out; then _notrun "kernel does not support attrs" diff --git a/common.defrag b/common.defrag index 9c9eb9b..13405a4 100644 --- a/common.defrag +++ b/common.defrag @@ -44,7 +44,7 @@ _require_defrag() _extent_count() { $FILEFRAG_PROG $1 | awk '{print $2}' - $FILEFRAG_PROG -v $1 >> $seq.full 2>&1 + $FILEFRAG_PROG -v $1 >> $RESULT_DIR/$seq.full 2>&1 } # Defrag file, check it, and remove it. @@ -54,7 +54,7 @@ _defrag() _extent_count $1 CSUM_BEFORE=`md5sum $1` STAT_BEFORE=`stat -c "a: %x m: %y c: %z" $1` - $DEFRAG_PROG -v $1 >> $seq.full 2>&1 + $DEFRAG_PROG -v $1 >> $RESULT_DIR/$seq.full 2>&1 _scratch_remount STAT_AFTER=`stat -c "a: %x m: %y c: %z" $1` CSUM_AFTER=`md5sum $1` diff --git a/common.dump b/common.dump index e89dedc..6169ae2 100644 --- a/common.dump +++ b/common.dump @@ -20,7 +20,7 @@ # # --- initializations --- -rm -f $here/$seq.full +rm -f $RESULT_DIR/$seq.full if [ -n "$DEBUGDUMP" ]; then _dump_debug=-v4 @@ -124,7 +124,7 @@ _check_onl() _limit=10 i=0 while [ $i -lt $_limit ]; do - echo "Checking online..." >>$here/$seq.full + echo "Checking online..." >>$RESULT_DIR/$seq.full if _mt status >$tmp.status 2>&1; then break; else @@ -158,12 +158,12 @@ _check_onl() _wait_tape() { - echo "Wait for tape, $dumptape, ..." >>$here/$seq.full + echo "Wait for tape, $dumptape, ..." >>$RESULT_DIR/$seq.full i=0 while [ $i -lt 20 ]; do - echo "Checking status..." >>$here/$seq.full - if _mt status 2>&1 | tee -a $here/$seq.full | egrep -i "onl|ready" >/dev/null; then + echo "Checking status..." >>$RESULT_DIR/$seq.full + if _mt status 2>&1 | tee -a $RESULT_DIR/$seq.full | egrep -i "onl|ready" >/dev/null; then break; else sleep 1 @@ -177,7 +177,7 @@ _wait_tape() # _rewind() { - echo "Initiate rewind..." >>$here/$seq.full + echo "Initiate rewind..." >>$RESULT_DIR/$seq.full _wait_tape _mt rewind >/dev/null _wait_tape @@ -190,7 +190,7 @@ _rewind() # _erase_soft() { - echo "Erasing tape" | tee -a $here/$seq.full + echo "Erasing tape" | tee -a $RESULT_DIR/$seq.full _rewind _mt weof 3 _rewind @@ -198,7 +198,7 @@ _erase_soft() _erase_hard() { - echo "Erasing tape" | tee -a $here/$seq.full + echo "Erasing tape" | tee -a $RESULT_DIR/$seq.full _mt erase } @@ -242,8 +242,8 @@ _wipe_fs() { _require_scratch - _scratch_mkfs_xfs >>$here/$seq.full || _fail "mkfs failed" - _scratch_mount >>$here/$seq.full || _fail "mount failed" + _scratch_mkfs_xfs >>$RESULT_DIR/$seq.full || _fail "mkfs failed" + _scratch_mount >>$RESULT_DIR/$seq.full || _fail "mount failed" } # @@ -294,8 +294,8 @@ _cleanup() _stable_fs() { _saveddir=`pwd`; cd / - umount $SCRATCH_MNT >>$here/$seq.full || _fail "unmount failed" - _scratch_mount >>$here/$seq.full || _fail "mount failed" + umount $SCRATCH_MNT >>$RESULT_DIR/$seq.full || _fail "unmount failed" + _scratch_mount >>$RESULT_DIR/$seq.full || _fail "mount failed" cd $_saveddir } @@ -325,12 +325,12 @@ _create_dumpdir_stress() echo "-----------------------------------------------" if ! $here/ltp/fsstress $_param -s 1 $FSSTRESS_AVOID -n $_count -d $dump_dir >$tmp.out 2>&1 then - echo " fsstress (count=$_count) returned $? - see $here/$seq.full" + echo " fsstress (count=$_count) returned $? - see $RESULT_DIR/$seq.full" - echo "--------------------------------------" >>$here/$seq.full - echo "output from fsstress:" >>$here/$seq.full - echo "--------------------------------------" >>$here/$seq.full - cat $tmp.out >>$here/$seq.full + echo "--------------------------------------" >>$RESULT_DIR/$seq.full + echo "output from fsstress:" >>$RESULT_DIR/$seq.full + echo "--------------------------------------" >>$RESULT_DIR/$seq.full + cat $tmp.out >>$RESULT_DIR/$seq.full status=1 fi @@ -1025,7 +1025,7 @@ _do_dump_sub() echo "Dumping to tape..." opts="$_dump_debug$dump_args -s $dump_sdir -f $dumptape -M $media_label -L $session_label $SCRATCH_MNT" echo "xfsdump $opts" | _dir_filter - $XFSDUMP_PROG $opts 2>&1 | tee -a $here/$seq.full | _dump_filter + $XFSDUMP_PROG $opts 2>&1 | tee -a $RESULT_DIR/$seq.full | _dump_filter } # @@ -1038,7 +1038,7 @@ _do_dump() echo "Dumping to tape..." opts="$_dump_debug$dump_args -f $dumptape -M $media_label -L $session_label $SCRATCH_MNT" echo "xfsdump $opts" | _dir_filter - $XFSDUMP_PROG $opts 2>&1 | tee -a $here/$seq.full | _dump_filter + $XFSDUMP_PROG $opts 2>&1 | tee -a $RESULT_DIR/$seq.full | _dump_filter } @@ -1053,7 +1053,7 @@ _do_dump_min() onemeg=1048576 opts="$_dump_debug$dump_args -m -b $onemeg -l0 -f $dumptape -M $media_label -L $session_label $SCRATCH_MNT" echo "xfsdump $opts" | _dir_filter - $XFSDUMP_PROG $opts 2>&1 | tee -a $here/$seq.full | _dump_filter + $XFSDUMP_PROG $opts 2>&1 | tee -a $RESULT_DIR/$seq.full | _dump_filter } @@ -1067,7 +1067,7 @@ _do_dump_file() echo "Dumping to file..." opts="$_dump_debug$dump_args -f $dump_file -M $media_label -L $session_label $SCRATCH_MNT" echo "xfsdump $opts" | _dir_filter - $XFSDUMP_PROG $opts 2>&1 | tee -a $here/$seq.full | _dump_filter + $XFSDUMP_PROG $opts 2>&1 | tee -a $RESULT_DIR/$seq.full | _dump_filter } # @@ -1089,7 +1089,7 @@ _do_dump_multi_file() echo "Dumping to files..." opts="$_dump_debug$dump_args $multi_args -L $session_label $SCRATCH_MNT" echo "xfsdump $opts" | _dir_filter - $XFSDUMP_PROG $opts 2>&1 | tee -a $here/$seq.full | _dump_filter + $XFSDUMP_PROG $opts 2>&1 | tee -a $RESULT_DIR/$seq.full | _dump_filter } @@ -1122,7 +1122,7 @@ _do_restore() echo "Restoring from tape..." opts="$_restore_debug$restore_args -f $dumptape -L $session_label $restore_dir" echo "xfsrestore $opts" | _dir_filter - $XFSRESTORE_PROG $opts 2>&1 | tee -a $here/$seq.full | _dump_filter + $XFSRESTORE_PROG $opts 2>&1 | tee -a $RESULT_DIR/$seq.full | _dump_filter } # @@ -1137,7 +1137,7 @@ _do_restore_min() onemeg=1048576 opts="$_restore_debug$restore_args -m -b $onemeg -f $dumptape -L $session_label $restore_dir" echo "xfsrestore $opts" | _dir_filter - $XFSRESTORE_PROG $opts 2>&1 | tee -a $here/$seq.full | _dump_filter + $XFSRESTORE_PROG $opts 2>&1 | tee -a $RESULT_DIR/$seq.full | _dump_filter } # @@ -1151,7 +1151,7 @@ _do_restore_file() echo "Restoring from file..." opts="$_restore_debug$restore_args -f $dump_file -L $session_label $restore_dir" echo "xfsrestore $opts" | _dir_filter - $XFSRESTORE_PROG $opts 2>&1 | tee -a $here/$seq.full | _dump_filter + $XFSRESTORE_PROG $opts 2>&1 | tee -a $RESULT_DIR/$seq.full | _dump_filter } # @@ -1166,7 +1166,7 @@ _do_restore_file_cum() echo "Restoring cumumlative from file..." opts="$_restore_debug$restore_args -f $dump_file -r $restore_dir" echo "xfsrestore $opts" | _dir_filter - $XFSRESTORE_PROG $opts 2>&1 | tee -a $here/$seq.full | _dump_filter + $XFSRESTORE_PROG $opts 2>&1 | tee -a $RESULT_DIR/$seq.full | _dump_filter } _do_restore_toc() @@ -1177,7 +1177,7 @@ _do_restore_toc() opts="$_restore_debug$restore_args -f $dump_file -t" echo "xfsrestore $opts" | _dir_filter cd $SCRATCH_MNT # for IRIX which needs xfs cwd - $XFSRESTORE_PROG $opts 2>&1 | tee -a $here/$seq.full | _dump_filter_main |\ + $XFSRESTORE_PROG $opts 2>&1 | tee -a $RESULT_DIR/$seq.full | _dump_filter_main |\ _check_quota_file |\ _check_quota_entries |\ $AWK_PROG 'NF != 1 { print; next } @@ -1208,7 +1208,7 @@ _do_restore_multi_file() echo "Restoring from file..." opts="$_restore_debug$restore_args $multi_args -L $session_label $restore_dir" echo "xfsrestore $opts" | _dir_filter - $XFSRESTORE_PROG $opts 2>&1 | tee -a $here/$seq.full | _dump_filter + $XFSRESTORE_PROG $opts 2>&1 | tee -a $RESULT_DIR/$seq.full | _dump_filter } # @@ -1228,7 +1228,7 @@ _do_dump_restore() restore_opts="$_restore_debug$restore_args - $restore_dir" dump_opts="$_dump_debug$dump_args -s $dump_sdir - $SCRATCH_MNT" echo "xfsdump $dump_opts | xfsrestore $restore_opts" | _dir_filter - $XFSDUMP_PROG $dump_opts 2>$tmp.dump.mlog | $XFSRESTORE_PROG $restore_opts 2>&1 | tee -a $here/$seq.full | _dump_filter + $XFSDUMP_PROG $dump_opts 2>$tmp.dump.mlog | $XFSRESTORE_PROG $restore_opts 2>&1 | tee -a $RESULT_DIR/$seq.full | _dump_filter _dump_filter <$tmp.dump.mlog } @@ -1244,8 +1244,8 @@ _ls_compare_sub() # verify we got back what we dumped # echo "Comparing listing of dump directory with restore directory" - ls -nR $dump_dir | tee -a $here/$seq.full | _ls_filter >$tmp.dump_dir - ls -nR $restore_dir/$dump_sdir | tee -a $here/$seq.full | _ls_filter \ + ls -nR $dump_dir | tee -a $RESULT_DIR/$seq.full | _ls_filter >$tmp.dump_dir + ls -nR $restore_dir/$dump_sdir | tee -a $RESULT_DIR/$seq.full | _ls_filter \ | sed -e "s#$restore_sdir\/##" >$tmp.restore_dir diff -bcs $tmp.dump_dir $tmp.restore_dir | sed -e "s#$tmp#TMP#g" @@ -1267,8 +1267,8 @@ _ls_nodate_compare_sub() # verify we got back what we dumped # echo "Comparing listing of dump directory with restore directory" - ls -nR $dump_dir | tee -a $here/$seq.full | _ls_filter | _ls_nodate_filter >$tmp.dump_dir - ls -nR $restore_dir/$dump_sdir | tee -a $here/$seq.full | _ls_filter \ + ls -nR $dump_dir | tee -a $RESULT_DIR/$seq.full | _ls_filter | _ls_nodate_filter >$tmp.dump_dir + ls -nR $restore_dir/$dump_sdir | tee -a $RESULT_DIR/$seq.full | _ls_filter \ | _ls_nodate_filter | sed -e "s#$restore_sdir\/##" >$tmp.restore_dir diff -bcs $tmp.dump_dir $tmp.restore_dir | sed -e "s#$tmp#TMP#g" @@ -1366,7 +1366,7 @@ _diff_compare() # _dump_inventory() { - $XFSDUMP_PROG $_dump_debug -I | tee -a $here/$seq.full | _dump_filter_main + $XFSDUMP_PROG $_dump_debug -I | tee -a $RESULT_DIR/$seq.full | _dump_filter_main } # @@ -1376,9 +1376,9 @@ _dump_inventory() _do_invutil() { host=`hostname` - echo "xfsinvutil $_invutil_debug -M $host:$SCRATCH_MNT \"$middate\" $*" >$here/$seq.full + echo "xfsinvutil $_invutil_debug -M $host:$SCRATCH_MNT \"$middate\" $*" >$RESULT_DIR/$seq.full $XFSINVUTIL_PROG $_invutil_debug $* -M $host:$SCRATCH_MNT "$middate" \ - | tee -a $here/$seq.full | _invutil_filter + | tee -a $RESULT_DIR/$seq.full | _invutil_filter } # @@ -1398,7 +1398,7 @@ _check_quota() $here/src/feature -P $SCRATCH_DEV && pquota=1 $AWK_PROG -v uquota=$uquota -v gquota=$gquota -v pquota=$pquota \ - -v full=$here/$seq.full -v usermsg="$usermsg" \ + -v full=$RESULT_DIR/$seq.full -v usermsg="$usermsg" \ -v groupmsg="$groupmsg" -v projectmsg="$projectmsg" ' $0 ~ projectmsg { print "Found project quota:", $0 >>full diff --git a/common.filestreams b/common.filestreams index 08eaf90..b3aee27 100644 --- a/common.filestreams +++ b/common.filestreams @@ -116,7 +116,7 @@ _check_for_dupes() for this_num_two in $num_str_two; do if [ "$this_num_one" == "$this_num_two" ]; then echo "duplicate AG $this_num_one found" \ - >> $here/$seq.full + >> $RESULT_DIR/$seq.full return 1 fi done @@ -189,7 +189,7 @@ _test_streams() { stream_index=1 while [ $stream_index -le $stream_count ]; do this_stream_ags=`_get_stream_ags stream${stream_index}-dir` - echo "stream $stream_index AGs: $this_stream_ags" >> $here/$seq.full + echo "stream $stream_index AGs: $this_stream_ags" >> $RESULT_DIR/$seq.full _check_for_dupes "$ags_seen" "$this_stream_ags" if [ $? -ne 0 ]; then # this stream is not in seperate AGs to previous streams diff --git a/common.log b/common.log index 3958c48..c50f4a8 100644 --- a/common.log +++ b/common.log @@ -33,14 +33,14 @@ _cleanup_logfiles() _full() { - echo "" >>$seq.full + echo "" >>$seq.full echo "*** $* ***" >>$seq.full echo "" >>$seq.full } _echofull() { - echo "" | tee -a $seq.full + echo "" | tee -a $seq.full echo "*** $* ***" | tee -a $seq.full echo "" | tee -a $seq.full } diff --git a/common.quota b/common.quota index 2fa784b..ff80382 100644 --- a/common.quota +++ b/common.quota @@ -96,8 +96,8 @@ _file_as_id() parent=`dirname $1` if [ $3 = p ]; then - echo PARENT: xfs_io -r -c "chproj $2" -c "chattr +P" $parent >>$seq.full - $XFS_IO_PROG -r -c "chproj $2" -c "chattr +P" $parent >>$seq.full 2>&1 + echo PARENT: xfs_io -r -c "chproj $2" -c "chattr +P" $parent >>$RESULT_DIR/$seq.full + $XFS_IO_PROG -r -c "chproj $2" -c "chattr +P" $parent >>$RESULT_DIR/$seq.full 2>&1 magik='$>' # (irrelevent, above set projid-inherit-on-parent) elif [ $3 = u ]; then magik='$>' # perlspeak for effective uid @@ -107,7 +107,7 @@ _file_as_id() _notrun "broken type in call to _file_as_id in test $seq" fi - perl <>$seq.full 2>&1 + perl <>$RESULT_DIR/$seq.full 2>&1 \$| = 1; $magik = $2; if ($5 == 0) { @@ -119,11 +119,11 @@ _file_as_id() } EOF # for debugging the above euid change, try... [need write in cwd] -# exec "dd if=/dev/zero of=$1 bs=$4 count=$5 >>$seq.full 2>&1"; +# exec "dd if=/dev/zero of=$1 bs=$4 count=$5 >>$RESULT_DIR/$seq.full 2>&1"; if [ $3 = p ]; then - echo PARENT: xfs_io -r -c "chproj 0" -c "chattr -P" $parent >>$seq.full - $XFS_IO_PROG -r -c "chproj 0" -c "chattr -P" $parent >>$seq.full 2>&1 + echo PARENT: xfs_io -r -c "chproj 0" -c "chattr -P" $parent >>$RESULT_DIR/$seq.full + $XFS_IO_PROG -r -c "chproj 0" -c "chattr -P" $parent >>$RESULT_DIR/$seq.full 2>&1 fi } @@ -198,8 +198,8 @@ _qsetup() _notrun "No quota support at mount time" fi - echo "Using output from '" `ls -l $seq.out` "'" >>$seq.full - echo "and using type=$type id=$id" >>$seq.full + echo "Using output from '" `ls -l $seq.out` "'" >>$RESULT_DIR/$seq.full + echo "and using type=$type id=$id" >>$RESULT_DIR/$seq.full } # @@ -229,7 +229,7 @@ _qmount_option() # Ensure we have the given quota option - duplicates are fine export MOUNT_OPTIONS="$MOUNT_OPTIONS -o $1" - echo "MOUNT_OPTIONS = $MOUNT_OPTIONS" >>$seq.full + echo "MOUNT_OPTIONS = $MOUNT_OPTIONS" >>$RESULT_DIR/$seq.full } _check_quota_usage() diff --git a/common.rc b/common.rc index 4214b3c..1ab736c 100644 --- a/common.rc +++ b/common.rc @@ -296,9 +296,9 @@ _scratch_mkfs_xfs() if [ $mkfs_status -ne 0 -a ! -z "$extra_mkfs_options" ]; then echo "** mkfs failed with extra mkfs options added to \"$MKFS_OPTIONS\" by test $seq **" \ - >>$here/$seq.full + >>$RESULT_DIR/$seq.full echo "** attempting to mkfs using only test $seq options: $extra_mkfs_options **" \ - >>$here/$seq.full + >>$RESULT_DIR/$seq.full # running mkfs again. overwrite previous mkfs output files $MKFS_XFS_PROG $SCRATCH_OPTIONS $extra_mkfs_options $SCRATCH_DEV \ 2>$tmp_dir.mkfserr 1>$tmp_dir.mkfsstd @@ -634,7 +634,7 @@ _is_block_dev() fi } -# Do a command, log it to $seq.full, optionally test return status +# Do a command, log it to $RESULT_DIR/$seq.full, optionally test return status # and die if command fails. If called with one argument _do executes the # command, logs it, and returns its exit status. With two arguments _do # first prints the message passed in the first argument, and then "done" @@ -657,9 +657,9 @@ _do() status=1; exit fi - (eval "echo '---' \"$_cmd\"") >>$here/$seq.full + (eval "echo '---' \"$_cmd\"") >>$RESULT_DIR/$seq.full (eval "$_cmd") >$tmp._out 2>&1; ret=$? - cat $tmp._out | _fix_malloc >>$here/$seq.full + cat $tmp._out | _fix_malloc >>$RESULT_DIR/$seq.full if [ $# -eq 2 ]; then if [ $ret -eq 0 ]; then echo "done" @@ -672,7 +672,7 @@ _do() -o \( $# -eq 2 -a "$_do_die_on_error" = "message_only" \) ] then [ $# -ne 2 ] && echo - eval "echo \"$_cmd\" failed \(returned $ret\): see $seq.full" + eval "echo \"$_cmd\" failed \(returned $ret\): see $RESULT_DIR/$seq.full" status=1; exit fi @@ -693,8 +693,8 @@ _notrun() # _fail() { - echo "$*" | tee -a $here/$seq.full - echo "(see $seq.full for details)" + echo "$*" | tee -a $RESULT_DIR/$seq.full + echo "(see $RESULT_DIR/$seq.full for details)" status=1 exit 1 } @@ -1181,12 +1181,12 @@ _check_generic_filesystem() fsck -t $FSTYP $FSCK_OPTIONS $device >$tmp.fsck 2>&1 if [ $? -ne 0 ] then - echo "_check_generic_filesystem: filesystem on $device is inconsistent (see $seq.full)" + echo "_check_generic_filesystem: filesystem on $device is inconsistent (see $RESULT_DIR/$seq.full)" - echo "_check_generic filesystem: filesystem on $device is inconsistent" >>$here/$seq.full - echo "*** fsck.$FSTYP output ***" >>$here/$seq.full - cat $tmp.fsck >>$here/$seq.full - echo "*** end fsck.$FSTYP output" >>$here/$seq.full + echo "_check_generic filesystem: filesystem on $device is inconsistent" >>$RESULT_DIR/$seq.full + echo "*** fsck.$FSTYP output ***" >>$RESULT_DIR/$seq.full + cat $tmp.fsck >>$RESULT_DIR/$seq.full + echo "*** end fsck.$FSTYP output" >>$RESULT_DIR/$seq.full ok=0 fi @@ -1194,9 +1194,9 @@ _check_generic_filesystem() if [ $ok -eq 0 ] then - echo "*** mount output ***" >>$here/$seq.full - _mount >>$here/$seq.full - echo "*** end mount output" >>$here/$seq.full + echo "*** mount output ***" >>$RESULT_DIR/$seq.full + _mount >>$RESULT_DIR/$seq.full + echo "*** end mount output" >>$RESULT_DIR/$seq.full elif [ "$type" = "$FSTYP" ] then # was mounted ... @@ -1252,12 +1252,12 @@ _check_xfs_filesystem() | tee $tmp.logprint | grep -q "" if [ $? -ne 0 -a "$HOSTOS" = "Linux" ] then - echo "_check_xfs_filesystem: filesystem on $device has dirty log (see $seq.full)" + echo "_check_xfs_filesystem: filesystem on $device has dirty log (see $RESULT_DIR/$seq.full)" - echo "_check_xfs_filesystem: filesystem on $device has dirty log" >>$here/$seq.full - echo "*** xfs_logprint -t output ***" >>$here/$seq.full - cat $tmp.logprint >>$here/$seq.full - echo "*** end xfs_logprint output" >>$here/$seq.full + echo "_check_xfs_filesystem: filesystem on $device has dirty log" >>$RESULT_DIR/$seq.full + echo "*** xfs_logprint -t output ***" >>$RESULT_DIR/$seq.full + cat $tmp.logprint >>$RESULT_DIR/$seq.full + echo "*** end xfs_logprint output" >>$RESULT_DIR/$seq.full ok=0 fi @@ -1266,12 +1266,12 @@ _check_xfs_filesystem() _fix_malloc >$tmp.fs_check if [ -s $tmp.fs_check ] then - echo "_check_xfs_filesystem: filesystem on $device is inconsistent (c) (see $seq.full)" + echo "_check_xfs_filesystem: filesystem on $device is inconsistent (c) (see $RESULT_DIR/$seq.full)" - echo "_check_xfs_filesystem: filesystem on $device is inconsistent" >>$here/$seq.full - echo "*** xfs_check output ***" >>$here/$seq.full - cat $tmp.fs_check >>$here/$seq.full - echo "*** end xfs_check output" >>$here/$seq.full + echo "_check_xfs_filesystem: filesystem on $device is inconsistent" >>$RESULT_DIR/$seq.full + echo "*** xfs_check output ***" >>$RESULT_DIR/$seq.full + cat $tmp.fs_check >>$RESULT_DIR/$seq.full + echo "*** end xfs_check output" >>$RESULT_DIR/$seq.full ok=0 fi @@ -1280,12 +1280,12 @@ _check_xfs_filesystem() $XFS_REPAIR_PROG -n $extra_log_options $extra_rt_options $device >$tmp.repair 2>&1 if [ $? -ne 0 ] then - echo "_check_xfs_filesystem: filesystem on $device is inconsistent (r) (see $seq.full)" + echo "_check_xfs_filesystem: filesystem on $device is inconsistent (r) (see $RESULT_DIR/$seq.full)" - echo "_check_xfs_filesystem: filesystem on $device is inconsistent" >>$here/$seq.full - echo "*** xfs_repair -n output ***" >>$here/$seq.full - cat $tmp.repair | _fix_malloc >>$here/$seq.full - echo "*** end xfs_repair output" >>$here/$seq.full + echo "_check_xfs_filesystem: filesystem on $device is inconsistent" >>$RESULT_DIR/$seq.full + echo "*** xfs_repair -n output ***" >>$RESULT_DIR/$seq.full + cat $tmp.repair | _fix_malloc >>$RESULT_DIR/$seq.full + echo "*** end xfs_repair output" >>$RESULT_DIR/$seq.full ok=0 fi @@ -1293,9 +1293,9 @@ _check_xfs_filesystem() if [ $ok -eq 0 ] then - echo "*** mount output ***" >>$here/$seq.full - _mount >>$here/$seq.full - echo "*** end mount output" >>$here/$seq.full + echo "*** mount output ***" >>$RESULT_DIR/$seq.full + _mount >>$RESULT_DIR/$seq.full + echo "*** end mount output" >>$RESULT_DIR/$seq.full elif [ "$type" = "xfs" ] then _mount_or_remount_rw "$extra_mount_options" $device $mountpoint @@ -1389,12 +1389,12 @@ _check_btrfs_filesystem() btrfsck $device >$tmp.fsck 2>&1 if [ $? -ne 0 ] then - echo "_check_btrfs_filesystem: filesystem on $device is inconsistent (see $seq.full)" + echo "_check_btrfs_filesystem: filesystem on $device is inconsistent (see $RESULT_DIR/$seq.full)" - echo "_check_btrfs_filesystem: filesystem on $device is inconsistent" >>$here/$seq.full - echo "*** fsck.$FSTYP output ***" >>$here/$seq.full - cat $tmp.fsck >>$here/$seq.full - echo "*** end fsck.$FSTYP output" >>$here/$seq.full + echo "_check_btrfs_filesystem: filesystem on $device is inconsistent" >>$RESULT_DIR/$seq.full + echo "*** fsck.$FSTYP output ***" >>$RESULT_DIR/$seq.full + cat $tmp.fsck >>$RESULT_DIR/$seq.full + echo "*** end fsck.$FSTYP output" >>$RESULT_DIR/$seq.full ok=0 fi @@ -1402,9 +1402,9 @@ _check_btrfs_filesystem() if [ $ok -eq 0 ] then - echo "*** mount output ***" >>$here/$seq.full - _mount >>$here/$seq.full - echo "*** end mount output" >>$here/$seq.full + echo "*** mount output ***" >>$RESULT_DIR/$seq.full + _mount >>$RESULT_DIR/$seq.full + echo "*** end mount output" >>$RESULT_DIR/$seq.full elif [ "$type" = "$FSTYP" ] then # was mounted ... @@ -1889,8 +1889,8 @@ _scale_fsstress_args() run_check() { - echo "# $@" >> $seq.full 2>&1 - "$@" >> $seq.full 2>&1 || _fail "failed: '$@'" + echo "# $@" >> $RESULT_DIR/$seq.full 2>&1 + "$@" >> $RESULT_DIR/$seq.full 2>&1 || _fail "failed: '$@'" } ################################################################################ diff --git a/common.scsi_debug b/common.scsi_debug index a085a67..f05c8db 100644 --- a/common.scsi_debug +++ b/common.scsi_debug @@ -47,7 +47,7 @@ _get_scsi_debug_dev() let phys_exp=phys_exp+1 done opts="sector_size=$logical physblk_exp=$phys_exp lowest_aligned=$unaligned dev_size_mb=$size" - echo "scsi_debug options $opts" >> $seq.full + echo "scsi_debug options $opts" >> $RESULT_DIR/$seq.full modprobe scsi_debug $opts [ $? -eq 0 ] || _fail "scsi_debug modprobe failed" sleep 1 -- 1.5.3.8 From pwhite@sgi.com Thu Mar 14 08:06:40 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from cthulhu.engr.sgi.com (cthulhu.engr.sgi.com [150.166.39.100]) by oss.sgi.com (Postfix) with ESMTP id D724B7F63 for ; Thu, 14 Mar 2013 08:06:12 -0500 (CDT) Received: from polaris-admin.engr.sgi.com (polaris-admin.engr.sgi.com [150.166.41.54]) by cthulhu.engr.sgi.com (8.12.10/8.12.10/SuSE Linux 0.7) with ESMTP id r2ED6Cx7007498 for ; Thu, 14 Mar 2013 06:06:12 -0700 Received: by polaris-admin.engr.sgi.com (Postfix, from userid 48024) id 37EE753DEAEF; Thu, 14 Mar 2013 06:06:12 -0700 (PDT) Date: Thu, 14 Mar 2013 06:06:12 -0700 To: xfs@oss.sgi.com Subject: [PATCH 18/18] xfstests: fix link_out_file usage for new structure User-Agent: nail 11.25 7/29/05 MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Transfer-Encoding: 7bit Message-Id: <20130314130612.37EE753DEAEF@polaris-admin.engr.sgi.com> From: pwhite@sgi.com (Philip White) From: Phil White This is a rebasing & resubmit of a dchinner patch. His comments on the original: ----------------- Currently the callers pass $seq, rather than the full path to the test. As a result, it creates the link in the top level directory and it points nowhere. Fix it to create the link in the correct place. ----------------- I may have missed some of these changes in the newer tests ( >= 285) Signed-off-by: Phil White --- common.rc | 26 +++++++++++++------------- tests/generic/088 | 3 ++- tests/xfs/018 | 9 +++++---- tests/xfs/022 | 3 ++- tests/xfs/023 | 3 ++- tests/xfs/030 | 3 ++- tests/xfs/031 | 3 ++- tests/xfs/033 | 3 ++- tests/xfs/035 | 3 ++- tests/xfs/036 | 3 ++- tests/xfs/039 | 3 ++- tests/xfs/043 | 3 ++- tests/xfs/055 | 3 ++- tests/xfs/082 | 9 +++++---- tests/xfs/146 | 3 ++- 15 files changed, 47 insertions(+), 33 deletions(-) diff --git a/common.rc b/common.rc index 1ab736c..7780724 100644 --- a/common.rc +++ b/common.rc @@ -1596,19 +1596,19 @@ _cleanup_testdir() _link_out_file() { - if [ -z "$1" ]; then - echo Error must pass \$seq. - exit - fi - rm -f $1 - if [ "`uname`" == "IRIX64" ] || [ "`uname`" == "IRIX" ]; then - ln -s $1.irix $1 - elif [ "`uname`" == "Linux" ]; then - ln -s $1.linux $1 - else - echo Error test $seq does not run on the operating system: `uname` - exit - fi + if [ -z "$1" -o -z "$2" ]; then + echo Error must pass src and dst. + exit + fi + rm -f $1 + if [ "`uname`" == "IRIX64" ] || [ "`uname`" == "IRIX" ]; then + ln -s $1.irix $2 + elif [ "`uname`" == "Linux" ]; then + ln -s $1.linux $2 + else + echo Error test $seq does not run on the operating system: `uname` + exit + fi } _die() diff --git a/tests/generic/088 b/tests/generic/088 index 1386322..1158b46 100755 --- a/tests/generic/088 +++ b/tests/generic/088 @@ -23,6 +23,7 @@ #----------------------------------------------------------------------- # +seqfull=$0 seq=`basename $0` seqres=$RESULT_DIR/$seq echo "QA output created by $seq" @@ -42,7 +43,7 @@ _filter() } # link correct .out file -_link_out_file $seq.out +_link_out_file $seq.out $seqfull.out # real QA test starts here _supported_fs generic diff --git a/tests/xfs/018 b/tests/xfs/018 index ed99f20..7f22b54 100755 --- a/tests/xfs/018 +++ b/tests/xfs/018 @@ -22,6 +22,7 @@ #----------------------------------------------------------------------- # +seqfull=$0 seq=`basename $0` seqres=$RESULT_DIR/$seq echo "QA output created by $seq" @@ -53,7 +54,7 @@ _require_scratch _require_v2log # link correct .out file -_link_out_file $seq.op +_link_out_file $seq.op $seqfull.op echo "*** init FS" @@ -88,13 +89,13 @@ do _check_log _print_operation - _cmp_op_output $seq.op $filtered + _cmp_op_output $seqfull.op $filtered _print_transaction_inode $start_blk - _cmp_output $seq.trans_inode $filtered + _cmp_output $seqfull.trans_inode $filtered _print_transaction_buf $start_blk - _cmp_output $seq.trans_buf $filtered + _cmp_output $seqfull.trans_buf $filtered done # got thru it all so we may have success diff --git a/tests/xfs/022 b/tests/xfs/022 index 0251936..39f4b02 100755 --- a/tests/xfs/022 +++ b/tests/xfs/022 @@ -25,6 +25,7 @@ #----------------------------------------------------------------------- # +seqfull=$0 seq=`basename $0` seqres=$RESULT_DIR/$seq echo "QA output created by $seq" @@ -38,7 +39,7 @@ trap "rm -rf $tmp.*; exit \$status" 0 1 2 3 15 . ./common.dump # link correct .out file -_link_out_file $seq.out +_link_out_file $seq.out $seqfull.out # real QA test starts here _supported_fs xfs diff --git a/tests/xfs/023 b/tests/xfs/023 index 7bb77da..b133055 100755 --- a/tests/xfs/023 +++ b/tests/xfs/023 @@ -23,6 +23,7 @@ #----------------------------------------------------------------------- # +seqfull=$0 seq=`basename $0` seqres=$RESULT_DIR/$seq echo "QA output created by $seq" @@ -37,7 +38,7 @@ trap "rm -rf $tmp.*; exit \$status" 0 1 2 3 15 . ./common.dump # link correct .out file -_link_out_file $seq.out +_link_out_file $seq.out $seqfull.out # real QA test starts here _supported_fs xfs diff --git a/tests/xfs/030 b/tests/xfs/030 index cac66d2..87ebc81 100755 --- a/tests/xfs/030 +++ b/tests/xfs/030 @@ -22,6 +22,7 @@ #----------------------------------------------------------------------- # +seqfull=$0 seq=`basename $0` seqres=$RESULT_DIR/$seq echo "QA output created by $seq" @@ -45,7 +46,7 @@ trap "_cleanup; exit \$status" 0 1 2 3 15 . ./common.repair # link correct .out file -_link_out_file $seq.out +_link_out_file $seq.out $seqfull.out # nuke the superblock, AGI, AGF, AGFL; then try repair the damage # diff --git a/tests/xfs/031 b/tests/xfs/031 index 8041a19..af4e22b 100755 --- a/tests/xfs/031 +++ b/tests/xfs/031 @@ -22,6 +22,7 @@ #----------------------------------------------------------------------- # +seqfull=$0 seq=`basename $0` seqres=$RESULT_DIR/$seq echo "QA output created by $seq" @@ -38,7 +39,7 @@ rm -f $seqres.full . ./common.filter # link correct .out file -_link_out_file $seq.out +_link_out_file $seq.out $seqfull.out _check_repair() { diff --git a/tests/xfs/033 b/tests/xfs/033 index bc53a1b..fff35e9 100755 --- a/tests/xfs/033 +++ b/tests/xfs/033 @@ -22,6 +22,7 @@ #----------------------------------------------------------------------- # +seqfull=$0 seq=`basename $0` seqres=$RESULT_DIR/$seq echo "QA output created by $seq" @@ -45,7 +46,7 @@ trap "_cleanup; exit \$status" 0 1 2 3 15 . ./common.repair # link correct .out file -_link_out_file $seq.out +_link_out_file $seq.out $seqfull.out # nuke the root, rt bitmap, and rt summary inodes # diff --git a/tests/xfs/035 b/tests/xfs/035 index cd743f6..de9b9df 100755 --- a/tests/xfs/035 +++ b/tests/xfs/035 @@ -22,6 +22,7 @@ #----------------------------------------------------------------------- # +seqfull=$0 seq=`basename $0` seqres=$RESULT_DIR/$seq echo "QA output created by $seq" @@ -36,7 +37,7 @@ trap "rm -f $tmp.*; exit \$status" 0 1 2 3 15 . ./common.dump # link correct .out file -_link_out_file $seq.out +_link_out_file $seq.out $seqfull.out # real QA test starts here _supported_fs xfs diff --git a/tests/xfs/036 b/tests/xfs/036 index 5a7ee01..1578e8e 100755 --- a/tests/xfs/036 +++ b/tests/xfs/036 @@ -22,6 +22,7 @@ #----------------------------------------------------------------------- # +seqfull=$0 seq=`basename $0` seqres=$RESULT_DIR/$seq echo "QA output created by $seq" @@ -36,7 +37,7 @@ trap "rm -f $tmp.*; exit \$status" 0 1 2 3 15 . ./common.dump # link correct .out file -_link_out_file $seq.out +_link_out_file $seq.out $seqfull.out # real QA test starts here _supported_fs xfs diff --git a/tests/xfs/039 b/tests/xfs/039 index 21574d6..ebab798 100755 --- a/tests/xfs/039 +++ b/tests/xfs/039 @@ -22,6 +22,7 @@ #----------------------------------------------------------------------- # +seqfull=$0 seq=`basename $0` seqres=$RESULT_DIR/$seq echo "QA output created by $seq" @@ -36,7 +37,7 @@ trap "rm -f $tmp.*; exit \$status" 0 1 2 3 15 . ./common.dump # link correct .out file -_link_out_file $seq.out +_link_out_file $seq.out $seqfull.out # real QA test starts here _supported_fs xfs diff --git a/tests/xfs/043 b/tests/xfs/043 index 75c2d38..9c56ac1 100755 --- a/tests/xfs/043 +++ b/tests/xfs/043 @@ -24,6 +24,7 @@ #----------------------------------------------------------------------- # +seqfull=$0 seq=`basename $0` seqres=$RESULT_DIR/$seq echo "QA output created by $seq" @@ -38,7 +39,7 @@ trap "rm -f $tmp.*; exit \$status" 0 1 2 3 15 . ./common.dump # link correct .out file -_link_out_file $seq.out +_link_out_file $seq.out $seqfull.out # real QA test starts here _supported_fs xfs diff --git a/tests/xfs/055 b/tests/xfs/055 index 1804727..4c04b0a 100755 --- a/tests/xfs/055 +++ b/tests/xfs/055 @@ -22,6 +22,7 @@ #----------------------------------------------------------------------- # +seqfull=$0 seq=`basename $0` seqres=$RESULT_DIR/$seq echo "QA output created by $seq" @@ -36,7 +37,7 @@ trap "rm -f $tmp.*; exit \$status" 0 1 2 3 15 . ./common.dump # link correct .out file -_link_out_file $seq.out +_link_out_file $seq.out $seqfull.out # real QA test starts here _supported_fs xfs diff --git a/tests/xfs/082 b/tests/xfs/082 index 652f362..9ab1611 100755 --- a/tests/xfs/082 +++ b/tests/xfs/082 @@ -22,6 +22,7 @@ #----------------------------------------------------------------------- # +seqfull=$0 seq=`basename $0` seqres=$RESULT_DIR/$seq echo "QA output created by $seq" @@ -54,7 +55,7 @@ _require_scratch _require_v2log # link correct .out file -_link_out_file $seq.op +_link_out_file $seq.op $seqfull.op echo "*** init FS" umount $SCRATCH_DEV >/dev/null 2>&1 @@ -118,14 +119,14 @@ for s in sync nosync ; do : else _print_operation - _cmp_op_output $seq.op $filtered + _cmp_op_output $seqfull.op $filtered fi _print_transaction_inode $start - _cmp_output $seq.trans_inode $filtered + _cmp_output $seqfull.trans_inode $filtered _print_transaction_buf $start - _cmp_output $seq.trans_buf $filtered + _cmp_output $seqfull.trans_buf $filtered done done diff --git a/tests/xfs/146 b/tests/xfs/146 index 2091db1..e79d59e 100755 --- a/tests/xfs/146 +++ b/tests/xfs/146 @@ -22,6 +22,7 @@ #----------------------------------------------------------------------- # +seqfull=$0 seq=`basename $0` seqres=$RESULT_DIR/$seq echo "QA output created by $seq" @@ -52,7 +53,7 @@ _supported_fs xfs _supported_os Linux IRIX # link correct .out file -_link_out_file $seq.out +_link_out_file $seq.out $seqfull.out _require_scratch _scratch_mkfs_xfs >/dev/null 2>&1 -- 1.5.3.8 From pwhite@sgi.com Thu Mar 14 08:06:30 2013 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on oss.sgi.com X-Spam-Level: X-Spam-Status: No, score=0.0 required=5.0 tests=RP_MATCHES_RCVD autolearn=ham version=3.3.1 X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from cthulhu.engr.sgi.com (cthulhu.engr.sgi.com [150.166.39.100]) by oss.sgi.com (Postfix) with ESMTP id 37AAB7F58 for ; Thu, 14 Mar 2013 08:06:12 -0500 (CDT) Received: from polaris-admin.engr.sgi.com (polaris-admin.engr.sgi.com [150.166.41.54]) by cthulhu.engr.sgi.com (8.12.10/8.12.10/SuSE Linux 0.7) with ESMTP id r2ED6Bx7007452 for ; Thu, 14 Mar 2013 06:06:11 -0700 Received: by polaris-admin.engr.sgi.com (Postfix, from userid 48024) id 5325F53DEAF2; Thu, 14 Mar 2013 06:06:11 -0700 (PDT) Date: Thu, 14 Mar 2013 06:06:11 -0700 To: xfs@oss.sgi.com Subject: [PATCH 03/18] xfstests: Remove owner fields from patches User-Agent: nail 11.25 7/29/05 MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Transfer-Encoding: 7bit Message-Id: <20130314130611.5325F53DEAF2@polaris-admin.engr.sgi.com> From: pwhite@sgi.com (Philip White) From: Phil White This is a rebasing & resubmit of a dchinner patch. His comments on the original: ----------------- Back many years ago, the owner field was used to email the test owner when auto-qa failed that test. It is not needed anymore - if you want to know who wrote the test, look it up in git.... Script used was: $ sed -i -e "/^# creator/d" -e "/^owner/d" [0-2][0-9][0-9] ----------------- Signed-off-by: Phil White --- 001 | 2 -- 002 | 2 -- 003 | 2 -- 004 | 2 -- 005 | 2 -- 006 | 2 -- 007 | 2 -- 008 | 2 -- 009 | 2 -- 010 | 2 -- 011 | 2 -- 012 | 2 -- 013 | 2 -- 014 | 2 -- 015 | 2 -- 016 | 2 -- 017 | 2 -- 018 | 2 -- 019 | 2 -- 020 | 2 -- 021 | 2 -- 022 | 2 -- 023 | 2 -- 024 | 2 -- 025 | 2 -- 026 | 2 -- 027 | 2 -- 028 | 2 -- 029 | 2 -- 030 | 2 -- 031 | 2 -- 032 | 2 -- 033 | 2 -- 034 | 2 -- 035 | 2 -- 036 | 2 -- 037 | 2 -- 038 | 2 -- 039 | 2 -- 040 | 2 -- 041 | 2 -- 042 | 2 -- 043 | 2 -- 044 | 2 -- 045 | 2 -- 046 | 2 -- 047 | 2 -- 048 | 2 -- 049 | 2 -- 050 | 2 -- 051 | 2 -- 052 | 2 -- 053 | 2 -- 054 | 2 -- 055 | 2 -- 056 | 2 -- 057 | 2 -- 058 | 2 -- 059 | 2 -- 060 | 2 -- 061 | 2 -- 062 | 2 -- 063 | 2 -- 064 | 2 -- 065 | 2 -- 066 | 2 -- 067 | 2 -- 068 | 2 -- 069 | 2 -- 070 | 2 -- 071 | 2 -- 072 | 2 -- 073 | 2 -- 074 | 2 -- 075 | 2 -- 076 | 2 -- 077 | 2 -- 078 | 2 -- 079 | 2 -- 080 | 2 -- 081 | 2 -- 082 | 2 -- 083 | 2 -- 084 | 2 -- 085 | 2 -- 086 | 2 -- 087 | 2 -- 088 | 2 -- 089 | 2 -- 090 | 2 -- 091 | 2 -- 092 | 2 -- 093 | 2 -- 094 | 2 -- 095 | 2 -- 096 | 2 -- 097 | 2 -- 098 | 2 -- 099 | 1 - 100 | 2 -- 101 | 2 -- 102 | 2 -- 103 | 2 -- 104 | 2 -- 105 | 2 -- 106 | 2 -- 107 | 2 -- 108 | 2 -- 109 | 2 -- 110 | 2 -- 111 | 2 -- 112 | 2 -- 113 | 2 -- 114 | 2 -- 115 | 2 -- 116 | 2 -- 117 | 2 -- 118 | 2 -- 119 | 2 -- 120 | 2 -- 121 | 2 -- 122 | 2 -- 123 | 2 -- 124 | 2 -- 125 | 2 -- 126 | 2 -- 127 | 2 -- 128 | 2 -- 129 | 2 -- 130 | 2 -- 131 | 2 -- 132 | 2 -- 133 | 2 -- 134 | 2 -- 135 | 2 -- 136 | 2 -- 137 | 2 -- 138 | 2 -- 139 | 2 -- 140 | 2 -- 141 | 2 -- 142 | 2 -- 143 | 2 -- 144 | 2 -- 145 | 2 -- 146 | 2 -- 147 | 2 -- 148 | 2 -- 149 | 2 -- 150 | 2 -- 151 | 2 -- 152 | 2 -- 153 | 2 -- 154 | 2 -- 155 | 2 -- 156 | 2 -- 157 | 2 -- 158 | 2 -- 159 | 2 -- 160 | 2 -- 161 | 2 -- 162 | 2 -- 163 | 2 -- 164 | 2 -- 165 | 2 -- 166 | 2 -- 167 | 2 -- 168 | 2 -- 169 | 2 -- 170 | 2 -- 171 | 2 -- 172 | 2 -- 173 | 2 -- 174 | 2 -- 175 | 1 - 176 | 1 - 177 | 2 -- 178 | 2 -- 179 | 2 -- 180 | 2 -- 181 | 2 -- 182 | 2 -- 183 | 2 -- 184 | 2 -- 185 | 2 -- 186 | 2 -- 187 | 2 -- 188 | 2 -- 189 | 2 -- 190 | 2 -- 191 | 2 -- 192 | 2 -- 193 | 2 -- 194 | 2 -- 195 | 2 -- 196 | 2 -- 197 | 2 -- 198 | 2 -- 199 | 2 -- 200 | 2 -- 201 | 2 -- 202 | 2 -- 203 | 2 -- 204 | 2 -- 205 | 2 -- 206 | 2 -- 207 | 2 -- 208 | 2 -- 209 | 2 -- 210 | 2 -- 211 | 2 -- 212 | 2 -- 213 | 2 -- 214 | 2 -- 215 | 2 -- 216 | 2 -- 217 | 2 -- 218 | 2 -- 219 | 2 -- 220 | 2 -- 221 | 2 -- 222 | 2 -- 223 | 2 -- 224 | 2 -- 225 | 2 -- 226 | 2 -- 227 | 2 -- 228 | 2 -- 229 | 2 -- 230 | 2 -- 231 | 2 -- 232 | 2 -- 233 | 2 -- 234 | 2 -- 235 | 2 -- 236 | 2 -- 237 | 2 -- 238 | 2 -- 239 | 2 -- 240 | 2 -- 241 | 2 -- 242 | 2 -- 243 | 2 -- 244 | 2 -- 245 | 2 -- 246 | 2 -- 247 | 2 -- 248 | 2 -- 249 | 2 -- 250 | 2 -- 251 | 1 - 252 | 2 -- 253 | 2 -- 254 | 2 -- 255 | 2 -- 256 | 2 -- 257 | 2 -- 258 | 2 -- 259 | 2 -- 260 | 1 - 261 | 2 -- 262 | 2 -- 263 | 2 -- 264 | 2 -- 265 | 2 -- 266 | 2 -- 267 | 2 -- 268 | 2 -- 269 | 2 -- 270 | 2 -- 271 | 2 -- 272 | 2 -- 273 | 1 - 274 | 1 - 275 | 1 - 276 | 2 -- 277 | 2 -- 278 | 2 -- 279 | 2 -- 280 | 2 -- 281 | 2 -- 282 | 2 -- 283 | 2 -- 284 | 2 -- group | 60 ++++++++++++++++++++++++++++++------------------------------ new | 13 ------------- soak | 2 -- 287 files changed, 30 insertions(+), 605 deletions(-) diff --git a/001 b/001 index 8e3aabd..b9997f3 100755 --- a/001 +++ b/001 @@ -30,8 +30,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=kenmcd@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/002 b/002 index 896fd1e..db63fa0 100755 --- a/002 +++ b/002 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=kenmcd@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/003 b/003 index 61afac5..79b6bc5 100755 --- a/003 +++ b/003 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/004 b/004 index 9f28e17..8c920ae 100755 --- a/004 +++ b/004 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/005 b/005 index 40b8b2e..27da3d3 100755 --- a/005 +++ b/005 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=dxm@sgi.com # # Note1: On Linux, ELOOP limit used to be 32 but changed to 8, and lately diff --git a/006 b/006 index e4d5e32..1437b46 100755 --- a/006 +++ b/006 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=dxm@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/007 b/007 index 50a8418..2bb981f 100755 --- a/007 +++ b/007 @@ -24,8 +24,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/008 b/008 index dfc938a..0dee9f5 100755 --- a/008 +++ b/008 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=dxm@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/009 b/009 index d2a19d8..1883f15 100755 --- a/009 +++ b/009 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=dxm@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/010 b/010 index 78813a8..245f407 100755 --- a/010 +++ b/010 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/011 b/011 index 2fcc9d3..4ede2d8 100755 --- a/011 +++ b/011 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=dxm@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/012 b/012 index 7d33f4c..10498d5 100755 --- a/012 +++ b/012 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=dxm@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/013 b/013 index 58426ea..0879a2a 100755 --- a/013 +++ b/013 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=dxm@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/014 b/014 index 057e4d9..93caaa6 100755 --- a/014 +++ b/014 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=dxm@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/015 b/015 index 4206b93..62392c6 100755 --- a/015 +++ b/015 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=dxm@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/016 b/016 index 08a73f4..538ba14 100755 --- a/016 +++ b/016 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=dxm@sgi.com # # pv 796141 diff --git a/017 b/017 index 7db4667..8609e17 100755 --- a/017 +++ b/017 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=dxm@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/018 b/018 index 85df390..156cc1d 100755 --- a/018 +++ b/018 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/019 b/019 index 42e3c22..1fb0d83 100755 --- a/019 +++ b/019 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=dxm@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/020 b/020 index 8b8db30..2bd1d9f 100755 --- a/020 +++ b/020 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=dxm@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/021 b/021 index a6176f1..18fe40e 100755 --- a/021 +++ b/021 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=dxm@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/022 b/022 index b83b063..962316f 100755 --- a/022 +++ b/022 @@ -24,8 +24,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/023 b/023 index b9eeafe..3e7fdd2 100755 --- a/023 +++ b/023 @@ -22,8 +22,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/024 b/024 index 64b59bc..b7f1c10 100755 --- a/024 +++ b/024 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/025 b/025 index 90d3389..4ccb5de 100755 --- a/025 +++ b/025 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/026 b/026 index ef6aaa6..37a23cc 100755 --- a/026 +++ b/026 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/027 b/027 index 9df06c3..772705d 100755 --- a/027 +++ b/027 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/028 b/028 index 6628f66..0bf042f 100755 --- a/028 +++ b/028 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/029 b/029 index e4fe715..70c0d10 100755 --- a/029 +++ b/029 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/030 b/030 index fe57372..db1e454 100755 --- a/030 +++ b/030 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/031 b/031 index b062277..6c1684d 100755 --- a/031 +++ b/031 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/032 b/032 index bf88492..c5ba088 100755 --- a/032 +++ b/032 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/033 b/033 index 9651f26..130bd27 100755 --- a/033 +++ b/033 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/034 b/034 index c09f63b..27f3f22 100755 --- a/034 +++ b/034 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=dxm@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/035 b/035 index 34f5cac..b2fc417 100755 --- a/035 +++ b/035 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/036 b/036 index 4ed2ebc..e9bb411 100755 --- a/036 +++ b/036 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/037 b/037 index fd1e1af..e2e71c5 100755 --- a/037 +++ b/037 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/038 b/038 index f2af214..b62a4c9 100755 --- a/038 +++ b/038 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/039 b/039 index 016d2bc..428e8bb 100755 --- a/039 +++ b/039 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/040 b/040 index ea24ff5..0021c22 100755 --- a/040 +++ b/040 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/041 b/041 index 2800811..fdb0189 100755 --- a/041 +++ b/041 @@ -23,8 +23,6 @@ #----------------------------------------------------------------------- # set +x -# creator -owner=ajag@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/042 b/042 index c583746..15fa5dc 100755 --- a/042 +++ b/042 @@ -24,8 +24,6 @@ #----------------------------------------------------------------------- # set +x -# creator -owner=ajag@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/043 b/043 index 189dc5b..ef92c0a 100755 --- a/043 +++ b/043 @@ -23,8 +23,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/044 b/044 index 60a6e58..d0d8bd8 100755 --- a/044 +++ b/044 @@ -25,8 +25,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=dxm@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/045 b/045 index db40333..c20e3a8 100755 --- a/045 +++ b/045 @@ -22,8 +22,6 @@ #----------------------------------------------------------------------- # # -# creator -owner=dxm@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/046 b/046 index 783459c..fb83b7a 100755 --- a/046 +++ b/046 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/047 b/047 index f5f6a52..7c5e896 100755 --- a/047 +++ b/047 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/048 b/048 index 9d360d6..6139361 100755 --- a/048 +++ b/048 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=dxm@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/049 b/049 index b68821a..c9d086a 100755 --- a/049 +++ b/049 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=dxm@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/050 b/050 index cf70b5a..6a66032 100755 --- a/050 +++ b/050 @@ -22,8 +22,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/051 b/051 index 9d35138..07d5a9b 100755 --- a/051 +++ b/051 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@sgi.com seq=`basename $0` diff --git a/052 b/052 index 2d8b73d..01d5469 100755 --- a/052 +++ b/052 @@ -24,8 +24,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/053 b/053 index ac2162d..388c9b4 100755 --- a/053 +++ b/053 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=ajag@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/054 b/054 index e5e500c..1ce6180 100755 --- a/054 +++ b/054 @@ -22,8 +22,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/055 b/055 index 309b9c3..965b43a 100755 --- a/055 +++ b/055 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/056 b/056 index a19b85a..be65bfb 100755 --- a/056 +++ b/056 @@ -22,8 +22,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/057 b/057 index f3219a3..faa4776 100755 --- a/057 +++ b/057 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/058 b/058 index 43b2293..dfce43b 100755 --- a/058 +++ b/058 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/059 b/059 index 1f3f8e3..a2a07c9 100755 --- a/059 +++ b/059 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=wkendall@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/060 b/060 index 4adc00f..f0d9870 100755 --- a/060 +++ b/060 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=wkendall@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/061 b/061 index 8f1d149..fa98085 100755 --- a/061 +++ b/061 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/062 b/062 index 9800e33..5a6081e 100755 --- a/062 +++ b/062 @@ -22,8 +22,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/063 b/063 index 42a323a..cdaf524 100755 --- a/063 +++ b/063 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/064 b/064 index 8e9e694..c7e727c 100755 --- a/064 +++ b/064 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/065 b/065 index c1dee5d..12f2ac9 100755 --- a/065 +++ b/065 @@ -24,8 +24,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/066 b/066 index a6e76c1..7a68f79 100755 --- a/066 +++ b/066 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/067 b/067 index eb91aa1..baaed77 100755 --- a/067 +++ b/067 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/068 b/068 index cbfea95..4f10a54 100755 --- a/068 +++ b/068 @@ -22,8 +22,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=ajones@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/069 b/069 index 820ca5f..3451715 100755 --- a/069 +++ b/069 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/070 b/070 index 334cce7..02fe142 100755 --- a/070 +++ b/070 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/071 b/071 index ace0ee4..c135d1a 100755 --- a/071 +++ b/071 @@ -20,8 +20,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/072 b/072 index 981c408..930a983 100755 --- a/072 +++ b/072 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/073 b/073 index 43b629d..3a5129f 100755 --- a/073 +++ b/073 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/074 b/074 index b9fb9d5..0e5e820 100755 --- a/074 +++ b/074 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/075 b/075 index 87d273f..de581b6 100755 --- a/075 +++ b/075 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/076 b/076 index 793b869..11a0792 100755 --- a/076 +++ b/076 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/077 b/077 index 3fb3e81..2b86a37 100755 --- a/077 +++ b/077 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/078 b/078 index 7af552e..901723e 100755 --- a/078 +++ b/078 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/079 b/079 index 8f6e179..048b220 100755 --- a/079 +++ b/079 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/080 b/080 index 8ece84d..3243fe1 100755 --- a/080 +++ b/080 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/081 b/081 index 96156c8..f0ee819 100755 --- a/081 +++ b/081 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/082 b/082 index c413c10..e21a793 100755 --- a/082 +++ b/082 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@melbourne.sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/083 b/083 index f5349a9..5b7f0bc 100755 --- a/083 +++ b/083 @@ -31,8 +31,6 @@ #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/084 b/084 index e04a402..ba5743a 100755 --- a/084 +++ b/084 @@ -22,8 +22,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/085 b/085 index f4a45b7..44123ad 100755 --- a/085 +++ b/085 @@ -24,8 +24,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@melbourne.sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/086 b/086 index 9c3f22d..b59ad0a 100755 --- a/086 +++ b/086 @@ -23,8 +23,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=root@icy.melbourne.sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/087 b/087 index e7be9a0..3cb6990 100755 --- a/087 +++ b/087 @@ -23,8 +23,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@melbourne.sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/088 b/088 index 9fd0df5..b6266ef 100755 --- a/088 +++ b/088 @@ -22,8 +22,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=root@icy.melbourne.sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/089 b/089 index 1714bec..2653183 100755 --- a/089 +++ b/089 @@ -22,8 +22,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/090 b/090 index 0cdbe34..8ce50c0 100755 --- a/090 +++ b/090 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/091 b/091 index 8a14602..ad82b8e 100755 --- a/091 +++ b/091 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/092 b/092 index 429fa80..4e73cd9 100755 --- a/092 +++ b/092 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/093 b/093 index d730651..881a833 100755 --- a/093 +++ b/093 @@ -24,8 +24,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@sgi.com seq=`basename $0` diff --git a/094 b/094 index 75fc565..4f4cf34 100755 --- a/094 +++ b/094 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/095 b/095 index b85b97f..9de4476 100755 --- a/095 +++ b/095 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/096 b/096 index 237edad..ecadd73 100755 --- a/096 +++ b/096 @@ -22,8 +22,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/097 b/097 index 643d6f8..d3174e4 100755 --- a/097 +++ b/097 @@ -26,8 +26,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=ajones@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/098 b/098 index 5efd78f..58d2a95 100755 --- a/098 +++ b/098 @@ -28,8 +28,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=ajones@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/099 b/099 index b68bfcd..edd88a9 100755 --- a/099 +++ b/099 @@ -22,7 +22,6 @@ # #_acl_list # modifier -owner=ajones@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/100 b/100 index f3504ce..1ba5eb7 100755 --- a/100 +++ b/100 @@ -22,8 +22,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=ajones@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/101 b/101 index e58f8b6..0d274e5 100755 --- a/101 +++ b/101 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=ajones@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/102 b/102 index dab9b5c..68407a7 100755 --- a/102 +++ b/102 @@ -22,8 +22,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=ajones@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/103 b/103 index a390739..02c3f9d 100755 --- a/103 +++ b/103 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/104 b/104 index 8db6d88..59db760 100755 --- a/104 +++ b/104 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/105 b/105 index 6c7f327..01bae98 100755 --- a/105 +++ b/105 @@ -24,8 +24,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=fsgqa@snap.melbourne.sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/106 b/106 index b351fe5..e8f1d45 100755 --- a/106 +++ b/106 @@ -23,8 +23,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/107 b/107 index eaf7e6a..2c98b57 100755 --- a/107 +++ b/107 @@ -23,8 +23,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/108 b/108 index 638cea9..6b656e6 100755 --- a/108 +++ b/108 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/109 b/109 index a9c174f..56364f4 100755 --- a/109 +++ b/109 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/110 b/110 index c58e6c9..8749afa 100755 --- a/110 +++ b/110 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/111 b/111 index 719a0e0..8f4c142 100755 --- a/111 +++ b/111 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/112 b/112 index 763b17a..bcdcfec 100755 --- a/112 +++ b/112 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/113 b/113 index b2ec510..fd301cd 100755 --- a/113 +++ b/113 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/114 b/114 index edce0f4..a4ba98d 100755 --- a/114 +++ b/114 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@crackle.melbourne.sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/115 b/115 index 0679cfc..ebcc995 100755 --- a/115 +++ b/115 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@crackle.melbourne.sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/116 b/116 index cc2bb0f..2c3ab92 100755 --- a/116 +++ b/116 @@ -23,8 +23,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=fsgqa@snap.melbourne.sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/117 b/117 index 2e3f658..8afc962 100755 --- a/117 +++ b/117 @@ -22,8 +22,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=ajones@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/118 b/118 index 403655e..d140a8b 100755 --- a/118 +++ b/118 @@ -23,8 +23,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@crackle.melbourne.sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/119 b/119 index 1509ece..85af211 100755 --- a/119 +++ b/119 @@ -23,8 +23,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@crackle.melbourne.sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/120 b/120 index 010a8f3..8389925 100755 --- a/120 +++ b/120 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=allanr@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/121 b/121 index 2137ebc..a590bb0 100755 --- a/121 +++ b/121 @@ -25,8 +25,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/122 b/122 index a57f8c3..1c4f3a4 100755 --- a/122 +++ b/122 @@ -23,8 +23,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/123 b/123 index ee1194d..d45c516 100755 --- a/123 +++ b/123 @@ -22,8 +22,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=ajones@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/124 b/124 index adae304..6fbb028 100755 --- a/124 +++ b/124 @@ -25,8 +25,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=ajones@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/125 b/125 index 9a29941..c7215a3 100755 --- a/125 +++ b/125 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=ajones@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/126 b/126 index c2348f4..a95c1e4 100755 --- a/126 +++ b/126 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=allanr@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/127 b/127 index 62e584c..d1101df 100755 --- a/127 +++ b/127 @@ -25,8 +25,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=allanr@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/128 b/128 index 7760b95..85d0f45 100755 --- a/128 +++ b/128 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=allanr@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/129 b/129 index 38f12a6..18d891b 100755 --- a/129 +++ b/129 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=allanr@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/130 b/130 index ea5270d..943df72 100755 --- a/130 +++ b/130 @@ -30,8 +30,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=allanr@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/131 b/131 index 783765e..176c8b4 100755 --- a/131 +++ b/131 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=allanr@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/132 b/132 index e90f56c..98229a9 100755 --- a/132 +++ b/132 @@ -22,8 +22,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=allanr@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/133 b/133 index 9dbcb64..ec225f3 100755 --- a/133 +++ b/133 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=lachlan@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/134 b/134 index 7317168..2117b4a 100755 --- a/134 +++ b/134 @@ -22,8 +22,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=allanr@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/135 b/135 index 976619d..f0bf9b9 100755 --- a/135 +++ b/135 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=lachlan@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/136 b/136 index acf50b7..6479c8c 100755 --- a/136 +++ b/136 @@ -23,8 +23,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@puffy.melbourne.sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/137 b/137 index 42fb853..0f65d08 100755 --- a/137 +++ b/137 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=lachlan@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/138 b/138 index e7b5609..f8af8dd 100755 --- a/138 +++ b/138 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=lachlan@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/139 b/139 index 706a112..7d2e409 100755 --- a/139 +++ b/139 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=lachlan@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/140 b/140 index 1f88302..a8cbd09 100755 --- a/140 +++ b/140 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=lachlan@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/141 b/141 index cc501d6..45c1b5e 100755 --- a/141 +++ b/141 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=bnaujok@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/142 b/142 index c09a968..526167d 100755 --- a/142 +++ b/142 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=allanr@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/143 b/143 index 7db6fea..63281f9 100755 --- a/143 +++ b/143 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=allanr@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/144 b/144 index 36b9263..52123cc 100755 --- a/144 +++ b/144 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=allanr@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/145 b/145 index 3d6c158..54b8198 100755 --- a/145 +++ b/145 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=allanr@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/146 b/146 index 477df83..bb4975c 100755 --- a/146 +++ b/146 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=allanr@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/147 b/147 index b775478..e366dc7 100755 --- a/147 +++ b/147 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=allanr@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/148 b/148 index 76cbf37..6db1c2b 100755 --- a/148 +++ b/148 @@ -22,8 +22,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=ddiss@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/149 b/149 index 5131a45..c34a0ed 100755 --- a/149 +++ b/149 @@ -22,8 +22,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=ddiss@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/150 b/150 index a865875..b6a04c5 100755 --- a/150 +++ b/150 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=allanr@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/151 b/151 index f10460d..4bfaff3 100755 --- a/151 +++ b/151 @@ -23,8 +23,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=allanr@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/152 b/152 index 071be85..2317291 100755 --- a/152 +++ b/152 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=allanr@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/153 b/153 index 7c609d2..81be175 100755 --- a/153 +++ b/153 @@ -22,8 +22,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=allanr@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/154 b/154 index 2384d26..62e79c2 100755 --- a/154 +++ b/154 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=allanr@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/155 b/155 index de88ecb..949bd98 100755 --- a/155 +++ b/155 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=allanr@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/156 b/156 index 0f3b229..549cac8 100755 --- a/156 +++ b/156 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=allanr@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/157 b/157 index 11488c6..9ae3c40 100755 --- a/157 +++ b/157 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=allanr@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/158 b/158 index 2b95ec6..e740654 100755 --- a/158 +++ b/158 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=allanr@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/159 b/159 index 203afca..bfc225d 100755 --- a/159 +++ b/159 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=allanr@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/160 b/160 index 095951b..3900299 100755 --- a/160 +++ b/160 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=allanr@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/161 b/161 index 8d0aed2..c419380 100755 --- a/161 +++ b/161 @@ -22,8 +22,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=allanr@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/162 b/162 index 409d3a1..acd70e0 100755 --- a/162 +++ b/162 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=allanr@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/163 b/163 index faf02e4..d4eef64 100755 --- a/163 +++ b/163 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=allanr@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/164 b/164 index 2aea353..1ef4aaf 100755 --- a/164 +++ b/164 @@ -27,8 +27,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@puffy.melbourne.sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/165 b/165 index ec349da..3b321b9 100755 --- a/165 +++ b/165 @@ -24,8 +24,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@puffy.melbourne.sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/166 b/166 index 65c46da..527686f 100755 --- a/166 +++ b/166 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=dgc@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/167 b/167 index 5fb95e8..b2895fd 100755 --- a/167 +++ b/167 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=dgc@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/168 b/168 index e044091..8980f9b 100755 --- a/168 +++ b/168 @@ -22,8 +22,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=ddiss@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/169 b/169 index 627981e..413a86b 100755 --- a/169 +++ b/169 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=ddiss@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/170 b/170 index a807de0..b725d3a 100755 --- a/170 +++ b/170 @@ -23,8 +23,6 @@ # #----------------------------------------------------------------------- # -# creator - based on work from ddiss@sgi.co -owner=dgc@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/171 b/171 index 7e70466..4f77a41 100755 --- a/171 +++ b/171 @@ -22,8 +22,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=dgc@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/172 b/172 index 3220697..b6b496c 100755 --- a/172 +++ b/172 @@ -22,8 +22,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=dgc@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/173 b/173 index 9156403..7146d2f 100755 --- a/173 +++ b/173 @@ -22,8 +22,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=dgc@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/174 b/174 index 4828854..7745a6a 100755 --- a/174 +++ b/174 @@ -22,8 +22,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=dgc@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/175 b/175 index 523dce1..4fc3ffb 100755 --- a/175 +++ b/175 @@ -24,7 +24,6 @@ # #----------------------------------------------------------------------- # -owner=ddiss@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/176 b/176 index b988783..93083c4 100755 --- a/176 +++ b/176 @@ -21,7 +21,6 @@ # #----------------------------------------------------------------------- # -owner=ddiss@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/177 b/177 index b6f4789..ec8aca7 100755 --- a/177 +++ b/177 @@ -22,8 +22,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=mohamedb@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/178 b/178 index e4e104e..8856656 100755 --- a/178 +++ b/178 @@ -22,8 +22,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=mohamedb@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/179 b/179 index 5cec718..f3facca 100755 --- a/179 +++ b/179 @@ -22,8 +22,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=lachlan@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/180 b/180 index c303169..0f82306 100755 --- a/180 +++ b/180 @@ -22,8 +22,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=lachlan@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/181 b/181 index 6db52ac..fb65100 100755 --- a/181 +++ b/181 @@ -25,8 +25,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/182 b/182 index ae1f920..33e8010 100755 --- a/182 +++ b/182 @@ -22,8 +22,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=lachlan@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/183 b/183 index 5558eb9..4624ab4 100755 --- a/183 +++ b/183 @@ -22,8 +22,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=xaiki@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/184 b/184 index 8544dc1..a37f700 100755 --- a/184 +++ b/184 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=dgc@sgi.com seq=`basename $0` echo "QA output created by $seq - silence is golden" diff --git a/185 b/185 index ed0793c..928eb24 100755 --- a/185 +++ b/185 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=xaiki@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/186 b/186 index a2d7e14..2c66026 100755 --- a/186 +++ b/186 @@ -32,8 +32,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@emu.melbourne.sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/187 b/187 index 8086c8e..bff0caa 100755 --- a/187 +++ b/187 @@ -26,8 +26,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@emu.melbourne.sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/188 b/188 index ed93e65..4ebbfc1 100755 --- a/188 +++ b/188 @@ -28,8 +28,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=bnaujok@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/189 b/189 index e91d5cd..a5a5682 100755 --- a/189 +++ b/189 @@ -22,8 +22,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=hch@lst.de seq=`basename $0` echo "QA output created by $seq" diff --git a/190 b/190 index 096b871..5bb4743 100755 --- a/190 +++ b/190 @@ -25,8 +25,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=pleckie@sgi.com #This is the list of holes to punch in the file limited to $filesize #NOTE holes cannot overlap or this script will fail. diff --git a/191 b/191 index b1e66bf..3120dcb 100755 --- a/191 +++ b/191 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@emu.melbourne.sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/192 b/192 index 4b69147..691ab7d 100755 --- a/192 +++ b/192 @@ -23,8 +23,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=tes@emu.melbourne.sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/193 b/193 index 9891256..88ab971 100755 --- a/193 +++ b/193 @@ -20,8 +20,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=hch@lst.de seq=`basename $0` echo "QA output created by $seq" diff --git a/194 b/194 index 931068d..595da25 100755 --- a/194 +++ b/194 @@ -20,8 +20,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=sandeen@sandeen.net seq=`basename $0` echo "QA output created by $seq" diff --git a/195 b/195 index b910f72..cd64db1 100755 --- a/195 +++ b/195 @@ -22,8 +22,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=hch@lst.de seq=`basename $0` echo "QA output created by $seq" diff --git a/196 b/196 index 6b9998f..321fe47 100755 --- a/196 +++ b/196 @@ -23,8 +23,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=hch@lst.de seq=`basename $0` echo "QA output created by $seq" diff --git a/197 b/197 index 0996630..8c2ebd2 100755 --- a/197 +++ b/197 @@ -26,8 +26,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=hch@lst.de seq=`basename $0` echo "QA output created by $seq" diff --git a/198 b/198 index 2c72677..31de96c 100755 --- a/198 +++ b/198 @@ -21,8 +21,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=sandeen@sandeen.net seq=`basename $0` echo "QA output created by $seq" diff --git a/199 b/199 index 2151cd2..127f307 100755 --- a/199 +++ b/199 @@ -23,8 +23,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=hch@lst.de seq=`basename $0` echo "QA output created by $seq" diff --git a/200 b/200 index d1f7e9d..34139cc 100755 --- a/200 +++ b/200 @@ -20,8 +20,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=hch@lst.de seq=`basename $0` echo "QA output created by $seq" diff --git a/201 b/201 index 99bcde8..e868d99 100755 --- a/201 +++ b/201 @@ -23,8 +23,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=hch@lst.de seq=`basename $0` echo "QA output created by $seq" diff --git a/202 b/202 index f3030fc..27f9e67 100755 --- a/202 +++ b/202 @@ -20,8 +20,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=hch@lst.de seq=`basename $0` echo "QA output created by $seq" diff --git a/203 b/203 index 4d60bb0..ed89600 100755 --- a/203 +++ b/203 @@ -21,8 +21,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=hch@lst.de seq=`basename $0` echo "QA output created by $seq" diff --git a/204 b/204 index 9f4839c..6c4a3f0 100755 --- a/204 +++ b/204 @@ -20,8 +20,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=hch@lst.de seq=`basename $0` echo "QA output created by $seq" diff --git a/205 b/205 index bd916a1..7c953db 100755 --- a/205 +++ b/205 @@ -20,8 +20,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=david@fromorbit.com seq=`basename $0` echo "QA output created by $seq" diff --git a/206 b/206 index e8bc922..1c25305 100755 --- a/206 +++ b/206 @@ -26,8 +26,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=sandeen@sandeen.net seq=`basename $0` echo "QA output created by $seq" diff --git a/207 b/207 index 6fff833..6eaf50c 100755 --- a/207 +++ b/207 @@ -20,8 +20,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=sandeen@sandeen.net seq=`basename $0` echo "QA output created by $seq" diff --git a/208 b/208 index ca01558..7ea7514 100755 --- a/208 +++ b/208 @@ -20,8 +20,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=sandeen@sandeen.net seq=`basename $0` echo "QA output created by $seq" diff --git a/209 b/209 index 650e300..8b2a4e1 100755 --- a/209 +++ b/209 @@ -20,8 +20,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=sandeen@sandeen.net seq=`basename $0` echo "QA output created by $seq" diff --git a/210 b/210 index a0873f8..56ac8ad 100755 --- a/210 +++ b/210 @@ -20,8 +20,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=sandeen@sandeen.net seq=`basename $0` echo "QA output created by $seq" diff --git a/211 b/211 index bb8d2aa..5667d20 100755 --- a/211 +++ b/211 @@ -20,8 +20,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=sandeen@sandeen.net seq=`basename $0` echo "QA output created by $seq" diff --git a/212 b/212 index 1b4bb8a..e211cc4 100755 --- a/212 +++ b/212 @@ -21,8 +21,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=sandeen@sandeen.net seq=`basename $0` echo "QA output created by $seq" diff --git a/213 b/213 index 9982dd4..e297fdf 100755 --- a/213 +++ b/213 @@ -24,8 +24,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=sandeen@sandeen.net seq=`basename $0` echo "QA output created by $seq" diff --git a/214 b/214 index dabf422..682cfca 100755 --- a/214 +++ b/214 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=sandeen@sandeen.net seq=`basename $0` echo "QA output created by $seq" diff --git a/215 b/215 index c61f7a5..749b27b 100755 --- a/215 +++ b/215 @@ -22,8 +22,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=hch@lst.de seq=`basename $0` echo "QA output created by $seq" diff --git a/216 b/216 index 71e6dd7..a997d5a 100755 --- a/216 +++ b/216 @@ -20,8 +20,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=dgc@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/217 b/217 index ef0761e..b33c2e7 100755 --- a/217 +++ b/217 @@ -20,8 +20,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=dgc@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/218 b/218 index 77782c6..4b46452 100755 --- a/218 +++ b/218 @@ -20,8 +20,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=sandeen@sandeen.net seq=`basename $0` echo "QA output created by $seq" diff --git a/219 b/219 index 661fb96..3f4ec09 100755 --- a/219 +++ b/219 @@ -24,8 +24,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=sandeen@sandeen.net seq=`basename $0` echo "QA output created by $seq" diff --git a/220 b/220 index b913434..061b395 100755 --- a/220 +++ b/220 @@ -24,8 +24,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=hch@lst.de seq=`basename $0` echo "QA output created by $seq" diff --git a/221 b/221 index 6681237..9cab3c4 100755 --- a/221 +++ b/221 @@ -24,8 +24,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=hch@lst.de seq=`basename $0` echo "QA output created by $seq" diff --git a/222 b/222 index df2672f..6b5cf1f 100755 --- a/222 +++ b/222 @@ -24,8 +24,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=david@fromorbit.com seq=`basename $0` echo "QA output created by $seq" diff --git a/223 b/223 index 2e0a245..8eba2d7 100755 --- a/223 +++ b/223 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=sandeen@sandeen.net seq=`basename $0` echo "QA output created by $seq" diff --git a/224 b/224 index 00ebd2e..23ee7c2 100755 --- a/224 +++ b/224 @@ -26,8 +26,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=david@fromorbit.com seq=`basename $0` echo "QA output created by $seq" diff --git a/225 b/225 index e7f1d9c..c09bd2a 100755 --- a/225 +++ b/225 @@ -20,8 +20,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=sandeen@sandeen.net seq=`basename $0` echo "QA output created by $seq" diff --git a/226 b/226 index 6f28ac9..2179f2a 100755 --- a/226 +++ b/226 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=sandeen@sandeen.net seq=`basename $0` echo "QA output created by $seq" diff --git a/227 b/227 index dfcb1a5..8403724 100755 --- a/227 +++ b/227 @@ -26,8 +26,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=david@fromorbit.com seq=`basename $0` echo "QA output created by $seq" diff --git a/228 b/228 index fa230b0..2704934 100755 --- a/228 +++ b/228 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=aarora@in.ibm.com seq=`basename $0` echo "QA output created by $seq" diff --git a/229 b/229 index 81a2491..52be5c3 100755 --- a/229 +++ b/229 @@ -27,8 +27,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=hch@lst.de seq=`basename $0` echo "QA output created by $seq" diff --git a/230 b/230 index e66c5b9..a442857 100755 --- a/230 +++ b/230 @@ -24,8 +24,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=jack@suse.cz seq=`basename $0` echo "QA output created by $seq" diff --git a/231 b/231 index 115b4c0..6d8bda7 100755 --- a/231 +++ b/231 @@ -22,8 +22,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=jack@suse.cz seq=`basename $0` echo "QA output created by $seq" diff --git a/232 b/232 index d915d42..f7a1eb7 100755 --- a/232 +++ b/232 @@ -22,8 +22,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=jack@suse.cz seq=`basename $0` echo "QA output created by $seq" diff --git a/233 b/233 index 649de51..330041c 100755 --- a/233 +++ b/233 @@ -23,8 +23,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=jack@suse.cz seq=`basename $0` echo "QA output created by $seq" diff --git a/234 b/234 index 4e98035..dbb13f6 100755 --- a/234 +++ b/234 @@ -24,8 +24,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=jack@suse.cz seq=`basename $0` echo "QA output created by $seq" diff --git a/235 b/235 index 0c2ae8f..f4a1fce 100755 --- a/235 +++ b/235 @@ -24,8 +24,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=jack@suse.cz seq=`basename $0` echo "QA output created by $seq" diff --git a/236 b/236 index a7500ed..ec70cdb 100755 --- a/236 +++ b/236 @@ -22,8 +22,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=shiwh@cn.fujitsu.com seq=`basename $0` echo "QA output created by $seq" diff --git a/237 b/237 index 4d7bb40..7ebb88e 100755 --- a/237 +++ b/237 @@ -22,8 +22,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=shiwh@cn.fujitsu.com seq=`basename $0` echo "QA output created by $seq" diff --git a/238 b/238 index 4daca89..e1a8749 100755 --- a/238 +++ b/238 @@ -20,8 +20,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=dchinner@redhat.com seq=`basename $0` echo "QA output created by $seq" diff --git a/239 b/239 index 6457c46..8aa4ed0 100755 --- a/239 +++ b/239 @@ -21,8 +21,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=hch@lst.de seq=`basename $0` echo "QA output created by $seq" diff --git a/240 b/240 index dafcef3..d5f8940 100755 --- a/240 +++ b/240 @@ -27,8 +27,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=sandeen@sandeen.net seq=`basename $0` echo "QA output created by $seq" diff --git a/241 b/241 index bb920fe..ee572a7 100755 --- a/241 +++ b/241 @@ -20,8 +20,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=sandeen@sandeen.net seq=`basename $0` echo "QA output created by $seq" diff --git a/242 b/242 index 9a0c89e..eb5f9df 100755 --- a/242 +++ b/242 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=dchinner@redhat.com seq=`basename $0` echo "QA output created by $seq" diff --git a/243 b/243 index 48f7932..6a1b6d7 100755 --- a/243 +++ b/243 @@ -40,8 +40,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=alal@google.com seq=`basename $0` echo "QA output created by $seq" diff --git a/244 b/244 index cd5f5e8..c96d4eb 100755 --- a/244 +++ b/244 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=arekm@maven.pl seq=`basename $0` echo "QA output created by $seq" diff --git a/245 b/245 index 02b3173..fb81d39 100755 --- a/245 +++ b/245 @@ -23,8 +23,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=hch@lst.de seq=`basename $0` echo "QA output created by $seq" diff --git a/246 b/246 index faa5cca..d82e27d 100755 --- a/246 +++ b/246 @@ -24,8 +24,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=hch@lst.de seq=`basename $0` echo "QA output created by $seq" diff --git a/247 b/247 index 91410b6..3a2f735 100755 --- a/247 +++ b/247 @@ -20,8 +20,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=lmcilroy@redhat.com seq=`basename $0` echo "QA output created by $seq" diff --git a/248 b/248 index 38eb442..f245c1c 100755 --- a/248 +++ b/248 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=xin.zhong@intel.com seq=`basename $0` echo "QA output created by $seq" diff --git a/249 b/249 index 100cd4c..e72092d 100755 --- a/249 +++ b/249 @@ -20,8 +20,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=dchinner@redhat.com seq=`basename $0` echo "QA output created by $seq" diff --git a/250 b/250 index 9eca2b6..2dd12e8 100755 --- a/250 +++ b/250 @@ -20,8 +20,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=dchinner@redhat.com seq=`basename $0` echo "QA output created by $seq" diff --git a/251 b/251 index 74f9994..25f14bd 100755 --- a/251 +++ b/251 @@ -23,7 +23,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- -owner=lczerner@redhat.com seq=`basename $0` echo "QA output created by $seq" diff --git a/252 b/252 index 441bed0..9f0424d 100755 --- a/252 +++ b/252 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=josef@redhat.com seq=`basename $0` echo "QA output created by $seq" diff --git a/253 b/253 index 4d0b4c2..64776da 100755 --- a/253 +++ b/253 @@ -31,8 +31,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=aelder@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/254 b/254 index 7b74a02..73089d1 100755 --- a/254 +++ b/254 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=josef@redhat.com seq=`basename $0` echo "QA output created by $seq" diff --git a/255 b/255 index ae1d8e0..d2973a8 100755 --- a/255 +++ b/255 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=josef@redhat.com seq=`basename $0` echo "QA output created by $seq" diff --git a/256 b/256 index ffe172a..0d72795 100755 --- a/256 +++ b/256 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=achender@linux.vnet.ibm.com seq=`basename $0` echo "QA output created by $seq" diff --git a/257 b/257 index fb81e07..b58bd56 100755 --- a/257 +++ b/257 @@ -20,8 +20,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=notasas@gmail.com seq=`basename $0` echo "QA output created by $seq" diff --git a/258 b/258 index e0441a5..87817bc 100755 --- a/258 +++ b/258 @@ -23,8 +23,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=sandeen@redhat.com seq=`basename $0` echo "QA output created by $seq" diff --git a/259 b/259 index d260b79..91503a0 100755 --- a/259 +++ b/259 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=branto@redhat.com seq=`basename $0` echo "QA output created by $seq" diff --git a/260 b/260 index ae4740a..65a01c3 100755 --- a/260 +++ b/260 @@ -21,7 +21,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- -owner=lczerner@redhat.com seq=`basename $0` echo "QA output created by $seq" diff --git a/261 b/261 index 121b9e1..8903ec8 100755 --- a/261 +++ b/261 @@ -24,8 +24,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=aelder@sgi.com seq=$(basename $0) echo "QA output created by ${seq}" diff --git a/262 b/262 index 6de514d..5a060f1 100755 --- a/262 +++ b/262 @@ -25,8 +25,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=aelder@sgi.com seq=$(basename $0) echo "QA output created by ${seq}" diff --git a/263 b/263 index 315a938..18cd5de 100755 --- a/263 +++ b/263 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=nathans@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/264 b/264 index d655d1e..a589c7c 100755 --- a/264 +++ b/264 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=anand.jain@oracle.com seq=`basename $0` echo "QA output created by $seq" diff --git a/265 b/265 index 10f214f..f28d4e5 100755 --- a/265 +++ b/265 @@ -20,8 +20,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=anand.jain@oracle.com seq=`basename $0` echo "QA output created by $seq" diff --git a/266 b/266 index 232e729..89c590f 100755 --- a/266 +++ b/266 @@ -20,8 +20,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=wkendall@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/267 b/267 index 2ef8dd3..c52d810 100755 --- a/267 +++ b/267 @@ -20,8 +20,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=wkendall@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/268 b/268 index e1decd9..36391a3 100755 --- a/268 +++ b/268 @@ -22,8 +22,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=wkendall@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/269 b/269 index 7d63b87..ed27fb4 100755 --- a/269 +++ b/269 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=dmonakhov@openvz.org seq=`basename $0` echo "QA output created by $seq" diff --git a/270 b/270 index b753923..7841cd1 100755 --- a/270 +++ b/270 @@ -22,8 +22,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=dmonakhov@openvz.org seq=`basename $0` echo "QA output created by $seq" diff --git a/271 b/271 index b96d702..50b4c0b 100755 --- a/271 +++ b/271 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=dmonakhov@openvz.org seq=`basename $0` echo "QA output created by $seq" diff --git a/272 b/272 index c7f1efc..9a2a06b 100755 --- a/272 +++ b/272 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=dmonakhov@openvz.org seq=`basename $0` echo "QA output created by $seq" diff --git a/273 b/273 index 639e280..4473fd4 100755 --- a/273 +++ b/273 @@ -22,7 +22,6 @@ #----------------------------------------------------------------------- # #creator -owner=wu.bo@cn.fujitsu.com seq=`basename $0` echo "QA output created by $seq" diff --git a/274 b/274 index dcad90e..9b0fb71 100755 --- a/274 +++ b/274 @@ -24,7 +24,6 @@ #----------------------------------------------------------------------- # #creator -owner=wu.bo@cn.fujitsu.com seq=`basename $0` echo "QA output created by $seq" diff --git a/275 b/275 index 06db775..dc1eeeb 100755 --- a/275 +++ b/275 @@ -23,7 +23,6 @@ #----------------------------------------------------------------------- # #creator -owner=wu.bo@cn.fujitsu.com seq=`basename $0` echo "QA output created by $seq" diff --git a/276 b/276 index 65da464..29f721f 100755 --- a/276 +++ b/276 @@ -24,8 +24,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=list.btrfs@jan-o-sch.net seq=`basename $0` echo "QA output created by $seq" diff --git a/277 b/277 index 8021214..8ef809c 100755 --- a/277 +++ b/277 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=lizf@cn.fujitsu.com seq=`basename $0` echo "QA output created by $seq" diff --git a/278 b/278 index 73cd117..559e174 100755 --- a/278 +++ b/278 @@ -23,8 +23,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=cmaiolino@redhat.com seq=`basename $0` echo "QA output created by $seq" diff --git a/279 b/279 index 7d30251..8ee3328 100755 --- a/279 +++ b/279 @@ -21,8 +21,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=sandeen@redhat.com seq=`basename $0` echo "QA output created by $seq" diff --git a/280 b/280 index 5e26173..336bea6 100755 --- a/280 +++ b/280 @@ -21,8 +21,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=sandeen@sandeen.net seq=`basename $0` echo "QA output created by $seq" diff --git a/281 b/281 index 137f69f..2af3533 100755 --- a/281 +++ b/281 @@ -21,8 +21,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=wkendall@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/282 b/282 index 024bad8..4938408 100755 --- a/282 +++ b/282 @@ -23,8 +23,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=wkendall@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/283 b/283 index 27251bb..d1ce8ad 100755 --- a/283 +++ b/283 @@ -23,8 +23,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=wkendall@sgi.com seq=`basename $0` echo "QA output created by $seq" diff --git a/284 b/284 index 7f4a630..b86ef32 100644 --- a/284 +++ b/284 @@ -20,8 +20,6 @@ # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #----------------------------------------------------------------------- # -# creator -owner=liubo2009@cn.fujitsu.com seq=`basename $0` echo "QA output created by $seq" diff --git a/group b/group index c3c4161..c9b733f 100644 --- a/group +++ b/group @@ -5,97 +5,97 @@ # # catch-all -other fsg@melbourne.sgi.com +other # read/write integrity -rw dxm@sgi.com +rw # directory operations, e.g. create/unlink -dir dxm@sgi.com +dir # metadata and inodes in particular -metadata dxm@sgi.com +metadata # xfs_db -db nathans@sgi.com dxm@sgi.com +db # extended attributes -attr nathans@sgi.com dxm@sgi.com +attr # xfs_logprint -logprint tes@sgi.com dxm@sgi.com +logprint # XFS log related testing -log tes@sgi.com +log # XFS log related testing -v2log tes@sgi.com +v2log # xfsdump, xfsrestore, xfsinvutil -dump tes@sgi.com ivanr@sgi.com +dump # xfsdump, xfsrestore to tapes -tape tes@sgi.com ivanr@sgi.com +tape # xfsdump, xfsrestore to remote tapes -remote tes@sgi.com ivanr@sgi.com +remote # xfs_copy -copy harshula@sgi.com +copy # chacl, libacl -acl tes@sgi.com +acl # capabilities -cap tes@sgi.com +cap # permissions -perms tes@sgi.com +perms # xfs_growfs -growfs ajag@sgi.com +growfs # fsr.xfs -fsr ajag@sgi.com +fsr # mkfs.xfs -mkfs nathans@sgi.com +mkfs # xfs_repair -repair nathans@sgi.com +repair # quota tools and XFS quota kernel code (XQM) -quota nathans@sgi.com +quota # auto - tests to be run as part of nightly qa -auto dxm@sgi.com +auto # ioctl - tests which use ioctl commands (directly/indirectly) -ioctl nathans@sgi.com +ioctl # udf filesystem -udf ajones@sgi.com +udf # AIO operations -aio nathans@sgi.com +aio # Pattern writing and checking -pattern ajones@sgi.com +pattern # dmapi based tests dmapi # filestreams based tests -filestreams dgc@sgi.com +filestreams # case-insensitive based tests -ci bnaujok@sgi.com +ci # test the mount/remount path -mount tes@sgi.com +mount # test the NFS v4 ACL code if it exists -nfs4acl tes@sgi.com donaldd@sgi.com +nfs4acl # test access time atime diff --git a/new b/new index eb5e0cb..8dde6c5 100755 --- a/new +++ b/new @@ -32,17 +32,6 @@ _cleanup() : } -# fqdn for localhost -_get_fqdn() -{ - NSLOOKUP_PROG="`set_prog_path nslookup`" - if [ "$NSLOOKUP_PROG" = "" ]; then - getent hosts `uname -n` | awk '{print $2}' - else - $NSLOOKUP_PROG `hostname` | $AWK_PROG '{ if ($1 == "Name:") print $2 }' - fi -} - if [ ! -f group ] then echo "Creating the group index ..." @@ -116,8 +105,6 @@ cat <$id #----------------------------------------------------------------------- # # creator -owner=$USER@`_get_fqdn` - seq=\`basename \$0\` echo "QA output created by \$seq" diff --git a/soak b/soak index 28a2e2e..0cf27a7 100755 --- a/soak +++ b/soak @@ -17,8 +17,6 @@ # #----------------------------------------------------------------------- # -# creator -owner=dxm@sgi.com # get standard environment, filters and checks . ./common.rc -- 1.5.3.8 From pwhite@sgi.com Thu Mar 14 08:06:45 2013 Return-Path: X-Original-To: xfs@oss.sgi.com Delivered-To: xfs@oss.sgi.com Received: from cthulhu.engr.sgi.com (cthulhu.engr.sgi.com [150.166.39.100]) by oss.sgi.com (Postfix) with ESMTP id DC5457F67 for ; Thu, 14 Mar 2013 08:06:13 -0500 (CDT) Received: from polaris-admin.engr.sgi.com (polaris-admin.engr.sgi.com [150.166.41.54]) by cthulhu.engr.sgi.com (8.12.10/8.12.10/SuSE Linux 0.7) with ESMTP id r2ED6Bx9007455 for ; Thu, 14 Mar 2013 06:06:12 -0700 Received: by polaris-admin.engr.sgi.com (Postfix, from userid 48024) id 546BB53C7F62; Thu, 14 Mar 2013 06:06:12 -0700 (PDT) Date: Thu, 14 Mar 2013 06:06:12 -0700 To: xfs@oss.sgi.com Subject: [PATCH 16/18] xfstests: Move all the tests into their tests/*/ dirs User-Agent: nail 11.25 7/29/05 MIME-Version: 1.0 Content-Type: application/octet-stream Content-Transfer-Encoding: quoted-printable Message-Id: <20130314130612.546BB53C7F62@polaris-admin.engr.sgi.com> From: pwhite@sgi.com (Philip White) =46rom: Phil White I'm given to understand that some of these haven't been moved to the r= ight places. I followed Dave's lead mostly and it's quite possible that so= me of these haven't gone to the right places. Signed-off-by: Phil White --- 001 | 319 -- 001.out | 9 - 002 | 80 - 002.out | 2 - 003 | 91 - 003.out | 12 - 004 | 142 - 004.out | 9 - 005 | 99 - 005.out | 8 - 006 | 78 - 006.out | 11 - 007 | 74 - 007.out | 22 - 008 | 116 - 008.out | 21 - 009 | 187 - 009.out | 114 - 010 | 69 - 010.out | 58 - 011 | 86 - 011.out | 4 - 012 | 121 - 012.out | 16 - 013 | 136 - 013.out | 14 - 014 | 72 - 014.out | 6 - 015 | 125 - 015.out | 7 - 016 | 247 -- 016.out | 119 - 017 | 93 - 017.out | 10 - 018 | 102 - 018.op.irix | 5628 --------------------------- 018.op.linux | 4714 ---------------------- 018.out | 17 - 018.trans_buf | 1821 --------- 018.trans_inode | 2609 ------------- 019 | 148 - 019.out | 84 - 020 | 184 - 020.out | 65 - 021 | 147 - 021.out | 57 - 022 | 59 - 022.out.irix | 55 - 022.out.linux | 55 - 023 | 54 - 023.out.irix | 89 - 023.out.linux | 89 - 024 | 56 - 024.out | 119 - 025 | 49 - 025.out | 83 - 026 | 47 - 026.out | 73 - 027 | 46 - 027.out | 81 - 028 | 75 - 028.out | 310 -- 029 | 66 - 029.out | 27 - 030 | 107 - 030.out.irix | 291 -- 030.out.linux | 250 -- 031 | 124 - 031.out.irix | 123 - 031.out.linux | 115 - 032 | 89 - 032.out | 2 - 033 | 106 - 033.out.irix | 223 -- 033.out.linux | 194 - 034 | 90 - 034.out | 5 - 035 | 56 - 035.out.irix | 94 - 035.out.linux | 94 - 036 | 53 - 036.out.irix | 86 - 036.out.linux | 83 - 037 | 50 - 037.out | 83 - 038 | 50 - 038.out | 87 - 039 | 53 - 039.out.irix | 89 - 039.out.linux | 88 - 040 | 60 - 040.good | 16 - 040.out | 2 - 041 | 98 - 041.out | 19 - 042 | 168 - 042.out | 13 - 043 | 57 - 043.out.irix | 104 - 043.out.linux | 104 - 044 | 177 - 044.out | 66 - 045 | 81 - 045.out | 7 - 046 | 48 - 046.out | 37 - 047 | 83 - 047.out | 334 -- 048 | 54 - 048.out | 5 - 049 | 138 - 049.out | 15 - 050 | 229 -- 050.out | 193 - 051 | 366 -- 051.out | 355 -- 052 | 133 - 052.out | 9 - 053 | 90 - 053.out | 24 - 054 | 131 - 054.out | 73 - 055 | 53 - 055.out.irix | 89 - 055.out.linux | 88 - 056 | 48 - 056.out | 37 - 057 | 54 - 057.out | 34 - 058 | 45 - 058.out | 243 -- 059 | 50 - 059.out | 76 - 060 | 56 - 060.out | 120 - 061 | 54 - 061.out | 34 - 062 | 219 -- 062.out | 654 ---- 063 | 57 - 063.out | 74 - 064 | 109 - 064.out | 1484 ------- 065 | 197 - 065.out | 832 ---- 066 | 73 - 066.out | 40 - 067 | 90 - 067.out | 166 - 068 | 137 - 068.out | 43 - 069 | 79 - 069.out | 9 - 070 | 67 - 070.out | 1 - 071 | 169 - 071.out | 107 - 071.out.32 | 107 - 071.out.64 | 107 - 072 | 82 - 072.out | 2 - 073 | 182 - 073.out | 73 - 074 | 185 - 074.out | 21 - 075 | 161 - 075.out | 18 - 076 | 83 - 076.out | 5 - 077 | 84 - 077.out | 7 - 078 | 154 - 078.out | 211 - 079 | 68 - 079.out | 7 - 080 | 73 - 080.out | 3 - 081 | 85 - 081.out | 4 - 081.ugquota.trans_inode | 3091 --------------- 082 | 132 - 082.op.irix | 5628 --------------------------- 082.op.linux | 4714 ---------------------- 082.out | 39 - 082.trans_buf | 1821 --------- 082.trans_inode | 2609 ------------- 083 | 101 - 083.out | 4 - 084 | 76 - 084.out | 9 - 085 | 98 - 085.out | 114 - 086 | 151 - 086.out | 4722 ---------------------- 087 | 152 - 087.out | 389 -- 088 | 55 - 088.out.irix | 9 - 088.out.linux | 9 - 089 | 91 - 089.out | 19 - 090 | 127 - 090.out | 18 - 091 | 88 - 091.out | 7 - 092 | 60 - 092.out | 8 - 093 | 162 - 093.out | Bin 917 -> 0 bytes 094 | 114 - 094.out | 12 - 095 | 68 - 095.out | 6 - 096 | 150 - 096.external | 53 - 096.internal | 55 - 097 | 257 -- 097.out.udf | 132 - 097.out.xfs | 132 - 098 | 275 -- 098.out | 1594 -------- 099 | 342 -- 099.out | 215 - 100 | 88 - 100.out | 1 - 101 | 61 - 101.out | 19 - 102 | 58 - 102.out | 2 - 103 | 101 - 103.out | 22 - 104 | 118 - 104.out | 127 - 105 | 99 - 105.out | 3 - 106 | 238 -- 106.out | 379 -- 107 | 153 - 107.out | 1550 -------- 108 | 123 - 108.out | 101 - 109 | 111 - 109.out | 12 - 110 | 86 - 110.out | 37 - 111 | 70 - 111.out | 100 - 112 | 163 - 112.out | 18 - 113 | 107 - 113.out | 22 - 114 | 345 -- 114.out | 365 -- 115 | 258 -- 115.out | 118 - 116 | 65 - 116.out | 3 - 117 | 116 - 117.out | 15 - 118 | 94 - 118.out | 9 - 119 | 75 - 119.out | 3 - 120 | 99 - 120.out | 10 - 121 | 113 - 121.out | 15 - 122 | 220 -- 122.out | 123 - 123 | 78 - 123.out | 7 - 124 | 83 - 124.out | 1 - 125 | 73 - 125.out | 7 - 126 | 75 - 126.out | 19 - 127 | 124 - 127.out | 13 - 128 | 66 - 128.out | 1 - 129 | 69 - 129.out | 1 - 130 | 258 -- 130.out | 392 -- 131 | 81 - 131.out | 2 - 132 | 212 - 132.out | 847 ---- 133 | 77 - 133.out | 5 - 134 | 118 - 134.out | 5 - 135 | 92 - 135.out | 13 - 136 | 360 -- 136.out | 7753 -----------------------------= -------- 137 | 109 - 137.out | 1 - 138 | 115 - 138.out | 1 - 139 | 115 - 139.out | 1 - 140 | 112 - 140.out | 1 - 141 | 59 - 141.out | 1 - 142 | 57 - 142.out | 232 -- 143 | 57 - 143.out | 98 - 144 | 57 - 144.out | 245 -- 145 | 57 - 145.out | 36 - 146 | 66 - 146.out.irix | 324 -- 146.out.linux | 320 -- 147 | 57 - 147.out | 29 - 148 | 109 - 148.out | 299 -- 149 | 127 - 149.out | 123 - 150 | 68 - 150.out | 5 - 151 | 113 - 151.out | 22 - 152 | 62 - 152.out | 10 - 153 | 69 - 153.out | 8 - 154 | 56 - 154.out | 21 - 155 | 88 - 155.out | 8 - 156 | 55 - 156.out | 1 - 157 | 57 - 157.out | 2 - 158 | 102 - 158.out | 6 - 159 | 69 - 159.out | 5 - 160 | 79 - 160.out | 11 - 161 | 68 - 161.out | 12 - 162 | 85 - 162.out | 12 - 163 | 70 - 163.out | 3 - 164 | 156 - 164.out | 35 - 165 | 128 - 165.out | 1581 -------- 166 | 98 - 166.out | 6 - 167 | 80 - 167.out | 3 - 168 | 113 - 168.out | 57 - 169 | 107 - 169.out | 19 - 170 | 66 - 170.out | 21 - 171 | 69 - 171.out | 21 - 172 | 63 - 172.out | 11 - 173 | 66 - 173.out | 21 - 174 | 62 - 174.out | 11 - 175 | 70 - 175.out | 63 - 176 | 76 - 176.out | 121 - 177 | 84 - 177.out | 88 - 178 | 101 - 178.out | 79 - 179 | 110 - 179.out | 1 - 180 | 114 - 180.out | 1 - 181 | 127 - 181.out | 15 - 182 | 111 - 182.out | 1 - 183 | 66 - 183.out | 4 - 184 | 56 - 184.out | 1 - 185 | 86 - 185.out | 71 - 186 | 183 - 186.out | 290 -- 187 | 137 - 187.out | 39 - 188 | 87 - 188.out | 65 - 189 | 224 -- 189.out | 59 - 190 | 99 - 190.out | 4 - 191 | 74 - 191.out | 324 -- 192 | 79 - 192.out | 5 - 193 | 251 -- 193.out | 51 - 194 | 217 -- 194.out | 59 - 195 | 86 - 195.out | 8 - 196 | 97 - 196.out | 2002 ---------- 197 | 65 - 197.out | 2 - 198 | 56 - 198.out | 2 - 199 | 90 - 199.out | 13 - 200 | 125 - 200.out | 24 - 201 | 98 - 201.out | 2 - 202 | 60 - 202.out | 29 - 203 | 89 - 203.out | 427 -- 204 | 57 - 204.out | 2 - 205 | 82 - 205.out | 4 - 206 | 99 - 206.out | 30 - 207 | 49 - 207.out | 2 - 208 | 49 - 208.out | 2 - 209 | 49 - 209.out | 2 - 210 | 49 - 210.out | 2 - 211 | 49 - 211.out | 2 - 212 | 50 - 212.out | 2 - 213 | 88 - 213.out | 4 - 214 | 149 - 214.out | 51 - 215 | 83 - 215.out | 8 - 216 | 77 - 216.out | 10 - 217 | 89 - 217.out | 7 - 218 | 94 - 218.out | 19 - 219 | 134 - 219.out | 37 - 220 | 83 - 220.out | 2 - 221 | 47 - 221.out | 2 - 222 | 55 - 222.out | 2 - 223 | 99 - 223.out | 251 -- 224 | 85 - 224.out | 2 - 225 | 77 - 225.out | 3 - 226 | 77 - 226.out | 6 - 227 | 209 - 227.out | 2 - 228 | 85 - 228.out | 6 - 229 | 86 - 229.out | 4 - 230 | 145 - 230.out | 33 - 231 | 119 - 231.out | 16 - 232 | 92 - 232.out | 7 - 233 | 101 - 233.out | 7 - 234 | 106 - 234.out | 4 - 235 | 78 - 235.out | 34 - 236 | 68 - 236.out | 2 - 237 | 78 - 237.out | 4 - 238 | 55 - 238.out | 2 - 239 | 56 - 239.out | 2 - 240 | 74 - 240.out | 2 - 241 | 58 - 241.out | 2 - 242 | 62 - 242.out | 77 - 243 | 179 - 243.out | 13 - 244 | 136 - 244.out | 2 - 245 | 71 - 245.out | 2 - 246 | 58 - 246.out | 4 - 247 | 78 - 247.out | 2 - 248 | 56 - 248.out | 2 - 249 | 64 - 249.out | 2 - 250 | 95 - 250.out | 14 - 251 | 183 - 251.out | 3 - 252 | 65 - 252.out | 307 -- 253 | 192 - 253.out | 2 - 254 | 106 - 254.out | 40 - 255 | 66 - 255.out | 307 -- 256 | 176 - 256.out | 1 - 257 | 54 - 257.out | 2 - 258 | 74 - 258.out | 5 - 259 | 65 - 259.out | 7 - 260 | 189 - 260.out | 14 - 261 | 117 - 261.out | 2 - 262 | 144 - 262.out | 2 - 263 | 62 - 263.out | 3 - 264 | 191 - 264.out | 2 - 265 | 185 - 265.out | 2 - 266 | 69 - 266.out | 133 - 267 | 73 - 267.out | 88 - 268 | 76 - 268.out | 86 - 269 | 83 - 269.out | 5 - 270 | 108 - 270.out | 8 - 271 | 66 - 271.out | 44 - 272 | 107 - 272.out | 3 - 273 | 142 - 273.out | 4 - 274 | 100 - 274.out | 5 - 275 | 92 - 275.out | 5 - 276 | 247 -- 276.out | 4 - 277 | 69 - 277.out | 1 - 278 | 85 - 278.out | 2 - 279 | 118 - 279.out | 35 - 280 | 71 - 280.out | 1 - 281 | 57 - 281.out | 77 - 282 | 69 - 282.out | 133 - 283 | 72 - 283.out | 133 - 284 | 170 - 284.out | 11 - 285 | 58 - 285.full | 116 - 285.out | 1 - 286 | 199 - 286.full | 70 - 286.out | 1 - 287 | 144 - 287.out | 23 - 288 | 58 - 288.out | 6 - 289 | 103 - 289.out | 3 - 290 | 94 - 290.out | 100 - 291 | 128 - 291.out | 1 - 292 | 63 - 292.out | 5 - 293 | 59 - 293.out | 2 - 294 | 73 - 294.out | 5 - 295 | 81 - 295.out | 1 - 296 | 83 - 296.out | 55 - 297 | 88 - 297.out | 3 - 298 | 190 - 298.out | 5 - 299 | 157 - 299.out | 5 - 300 | 153 - 300.out | 4 - 301 | 126 - 301.out | 4 - 302 | 143 - 302.out | 4 - 303 | 153 - 303.out | 4 - 304 | 130 - 304.out | 4 - 305 | 186 - 305.out | 9 - tests/btrfs/254 | 106 + tests/btrfs/254.out | 40 + tests/btrfs/264 | 191 + tests/btrfs/264.out | 2 + tests/btrfs/265 | 185 + tests/btrfs/265.out | 2 + tests/btrfs/276 | 247 ++ tests/btrfs/276.out | 4 + tests/btrfs/284 | 170 + tests/btrfs/284.out | 11 + tests/ext4/271 | 66 + tests/ext4/271.out | 44 + tests/ext4/301 | 126 + tests/ext4/301.out | 4 + tests/ext4/302 | 143 + tests/ext4/302.out | 4 + tests/ext4/303 | 153 + tests/ext4/303.out | 4 + tests/ext4/304 | 130 + tests/ext4/304.out | 4 + tests/generic/001 | 319 ++ tests/generic/001.out | 9 + tests/generic/002 | 80 + tests/generic/002.out | 2 + tests/generic/005 | 99 + tests/generic/005.out | 8 + tests/generic/006 | 78 + tests/generic/006.out | 11 + tests/generic/007 | 74 + tests/generic/007.out | 22 + tests/generic/010 | 69 + tests/generic/010.out | 58 + tests/generic/011 | 86 + tests/generic/011.out | 4 + tests/generic/013 | 136 + tests/generic/013.out | 14 + tests/generic/014 | 72 + tests/generic/014.out | 6 + tests/generic/015 | 125 + tests/generic/015.out | 7 + tests/generic/020 | 184 + tests/generic/020.out | 65 + tests/generic/053 | 90 + tests/generic/053.out | 24 + tests/generic/062 | 219 ++ tests/generic/062.out | 654 ++++ tests/generic/069 | 79 + tests/generic/069.out | 9 + tests/generic/070 | 67 + tests/generic/070.out | 1 + tests/generic/074 | 185 + tests/generic/074.out | 21 + tests/generic/075 | 161 + tests/generic/075.out | 18 + tests/generic/076 | 83 + tests/generic/076.out | 5 + tests/generic/077 | 84 + tests/generic/077.out | 7 + tests/generic/079 | 68 + tests/generic/079.out | 7 + tests/generic/083 | 101 + tests/generic/083.out | 4 + tests/generic/088 | 55 + tests/generic/088.out.irix | 9 + tests/generic/088.out.linux | 9 + tests/generic/089 | 91 + tests/generic/089.out | 19 + tests/generic/091 | 88 + tests/generic/091.out | 7 + tests/generic/093 | 162 + tests/generic/093.out | Bin 0 -> 917 bytes tests/generic/097 | 257 ++ tests/generic/097.out.udf | 132 + tests/generic/097.out.xfs | 132 + tests/generic/099 | 342 ++ tests/generic/099.out | 215 + tests/generic/100 | 88 + tests/generic/100.out | 1 + tests/generic/105 | 99 + tests/generic/105.out | 3 + tests/generic/112 | 163 + tests/generic/112.out | 18 + tests/generic/113 | 107 + tests/generic/113.out | 22 + tests/generic/117 | 116 + tests/generic/117.out | 15 + tests/generic/120 | 99 + tests/generic/120.out | 10 + tests/generic/123 | 78 + tests/generic/123.out | 7 + tests/generic/124 | 83 + tests/generic/124.out | 1 + tests/generic/125 | 73 + tests/generic/125.out | 7 + tests/generic/126 | 75 + tests/generic/126.out | 19 + tests/generic/127 | 124 + tests/generic/127.out | 13 + tests/generic/128 | 66 + tests/generic/128.out | 1 + tests/generic/129 | 69 + tests/generic/129.out | 1 + tests/generic/130 | 258 ++ tests/generic/130.out | 392 ++ tests/generic/131 | 81 + tests/generic/131.out | 2 + tests/generic/132 | 212 + tests/generic/132.out | 847 ++++ tests/generic/133 | 77 + tests/generic/133.out | 5 + tests/generic/135 | 92 + tests/generic/135.out | 13 + tests/generic/141 | 59 + tests/generic/141.out | 1 + tests/generic/169 | 107 + tests/generic/169.out | 19 + tests/generic/184 | 56 + tests/generic/184.out | 1 + tests/generic/192 | 79 + tests/generic/192.out | 5 + tests/generic/193 | 251 ++ tests/generic/193.out | 51 + tests/generic/198 | 56 + tests/generic/198.out | 2 + tests/generic/204 | 57 + tests/generic/204.out | 2 + tests/generic/207 | 49 + tests/generic/207.out | 2 + tests/generic/208 | 49 + tests/generic/208.out | 2 + tests/generic/209 | 49 + tests/generic/209.out | 2 + tests/generic/210 | 49 + tests/generic/210.out | 2 + tests/generic/211 | 49 + tests/generic/211.out | 2 + tests/generic/212 | 50 + tests/generic/212.out | 2 + tests/generic/213 | 88 + tests/generic/213.out | 4 + tests/generic/214 | 149 + tests/generic/214.out | 51 + tests/generic/215 | 83 + tests/generic/215.out | 8 + tests/generic/219 | 134 + tests/generic/219.out | 37 + tests/generic/221 | 47 + tests/generic/221.out | 2 + tests/generic/223 | 99 + tests/generic/223.out | 251 ++ tests/generic/224 | 85 + tests/generic/224.out | 2 + tests/generic/225 | 77 + tests/generic/225.out | 3 + tests/generic/226 | 77 + tests/generic/226.out | 6 + tests/generic/228 | 85 + tests/generic/228.out | 6 + tests/generic/230 | 145 + tests/generic/230.out | 33 + tests/generic/231 | 119 + tests/generic/231.out | 16 + tests/generic/232 | 92 + tests/generic/232.out | 7 + tests/generic/233 | 101 + tests/generic/233.out | 7 + tests/generic/234 | 106 + tests/generic/234.out | 4 + tests/generic/235 | 78 + tests/generic/235.out | 34 + tests/generic/236 | 68 + tests/generic/236.out | 2 + tests/generic/237 | 78 + tests/generic/237.out | 4 + tests/generic/239 | 56 + tests/generic/239.out | 2 + tests/generic/240 | 74 + tests/generic/240.out | 2 + tests/generic/241 | 58 + tests/generic/241.out | 2 + tests/generic/245 | 71 + tests/generic/245.out | 2 + tests/generic/246 | 58 + tests/generic/246.out | 4 + tests/generic/247 | 78 + tests/generic/247.out | 2 + tests/generic/248 | 56 + tests/generic/248.out | 2 + tests/generic/249 | 64 + tests/generic/249.out | 2 + tests/generic/251 | 183 + tests/generic/251.out | 3 + tests/generic/255 | 66 + tests/generic/255.out | 307 ++ tests/generic/256 | 176 + tests/generic/256.out | 1 + tests/generic/257 | 54 + tests/generic/257.out | 2 + tests/generic/258 | 74 + tests/generic/258.out | 5 + tests/generic/260 | 189 + tests/generic/260.out | 14 + tests/generic/263 | 62 + tests/generic/263.out | 3 + tests/generic/269 | 83 + tests/generic/269.out | 5 + tests/generic/270 | 108 + tests/generic/270.out | 8 + tests/generic/273 | 142 + tests/generic/273.out | 4 + tests/generic/274 | 100 + tests/generic/274.out | 5 + tests/generic/275 | 92 + tests/generic/275.out | 5 + tests/generic/277 | 69 + tests/generic/277.out | 1 + tests/generic/280 | 71 + tests/generic/280.out | 1 + tests/generic/285 | 58 + tests/generic/285.full | 116 + tests/generic/285.out | 1 + tests/generic/286 | 199 + tests/generic/286.full | 70 + tests/generic/286.out | 1 + tests/generic/288 | 58 + tests/generic/288.out | 6 + tests/generic/294 | 73 + tests/generic/294.out | 5 + tests/generic/299 | 157 + tests/generic/299.out | 5 + tests/generic/300 | 153 + tests/generic/300.out | 4 + tests/shared/051 | 366 ++ tests/shared/051.out | 355 ++ tests/shared/068 | 137 + tests/shared/068.out | 43 + tests/shared/218 | 94 + tests/shared/218.out | 19 + tests/shared/243 | 179 + tests/shared/243.out | 13 + tests/shared/272 | 107 + tests/shared/272.out | 3 + tests/shared/289 | 103 + tests/shared/289.out | 3 + tests/shared/298 | 190 + tests/shared/298.out | 5 + tests/shared/305 | 186 + tests/shared/305.out | 9 + tests/udf/098 | 275 ++ tests/udf/098.out | 1594 ++++++++ tests/udf/101 | 61 + tests/udf/101.out | 19 + tests/udf/102 | 58 + tests/udf/102.out | 2 + tests/xfs/003 | 91 + tests/xfs/003.out | 12 + tests/xfs/004 | 142 + tests/xfs/004.out | 9 + tests/xfs/008 | 116 + tests/xfs/008.out | 21 + tests/xfs/009 | 187 + tests/xfs/009.out | 114 + tests/xfs/012 | 121 + tests/xfs/012.out | 16 + tests/xfs/016 | 247 ++ tests/xfs/016.out | 119 + tests/xfs/017 | 93 + tests/xfs/017.out | 10 + tests/xfs/018 | 102 + tests/xfs/018.op.irix | 5628 +++++++++++++++++++++++++++ tests/xfs/018.op.linux | 4714 ++++++++++++++++++++++ tests/xfs/018.out | 17 + tests/xfs/018.trans_buf | 1821 +++++++++ tests/xfs/018.trans_inode | 2609 +++++++++++++ tests/xfs/019 | 148 + tests/xfs/019.out | 84 + tests/xfs/021 | 147 + tests/xfs/021.out | 57 + tests/xfs/022 | 59 + tests/xfs/022.out.irix | 55 + tests/xfs/022.out.linux | 55 + tests/xfs/023 | 54 + tests/xfs/023.out.irix | 89 + tests/xfs/023.out.linux | 89 + tests/xfs/024 | 56 + tests/xfs/024.out | 119 + tests/xfs/025 | 49 + tests/xfs/025.out | 83 + tests/xfs/026 | 47 + tests/xfs/026.out | 73 + tests/xfs/027 | 46 + tests/xfs/027.out | 81 + tests/xfs/028 | 75 + tests/xfs/028.out | 310 ++ tests/xfs/029 | 66 + tests/xfs/029.out | 27 + tests/xfs/030 | 107 + tests/xfs/030.out.irix | 291 ++ tests/xfs/030.out.linux | 250 ++ tests/xfs/031 | 124 + tests/xfs/031.out.irix | 123 + tests/xfs/031.out.linux | 115 + tests/xfs/032 | 89 + tests/xfs/032.out | 2 + tests/xfs/033 | 106 + tests/xfs/033.out.irix | 223 ++ tests/xfs/033.out.linux | 194 + tests/xfs/034 | 90 + tests/xfs/034.out | 5 + tests/xfs/035 | 56 + tests/xfs/035.out.irix | 94 + tests/xfs/035.out.linux | 94 + tests/xfs/036 | 53 + tests/xfs/036.out.irix | 86 + tests/xfs/036.out.linux | 83 + tests/xfs/037 | 50 + tests/xfs/037.out | 83 + tests/xfs/038 | 50 + tests/xfs/038.out | 87 + tests/xfs/039 | 53 + tests/xfs/039.out.irix | 89 + tests/xfs/039.out.linux | 88 + tests/xfs/040 | 60 + tests/xfs/040.good | 16 + tests/xfs/040.out | 2 + tests/xfs/041 | 98 + tests/xfs/041.out | 19 + tests/xfs/042 | 168 + tests/xfs/042.out | 13 + tests/xfs/043 | 57 + tests/xfs/043.out.irix | 104 + tests/xfs/043.out.linux | 104 + tests/xfs/044 | 177 + tests/xfs/044.out | 66 + tests/xfs/045 | 81 + tests/xfs/045.out | 7 + tests/xfs/046 | 48 + tests/xfs/046.out | 37 + tests/xfs/047 | 83 + tests/xfs/047.out | 334 ++ tests/xfs/048 | 54 + tests/xfs/048.out | 5 + tests/xfs/049 | 138 + tests/xfs/049.out | 15 + tests/xfs/050 | 229 ++ tests/xfs/050.out | 193 + tests/xfs/052 | 133 + tests/xfs/052.out | 9 + tests/xfs/054 | 131 + tests/xfs/054.out | 73 + tests/xfs/055 | 53 + tests/xfs/055.out.irix | 89 + tests/xfs/055.out.linux | 88 + tests/xfs/056 | 48 + tests/xfs/056.out | 37 + tests/xfs/057 | 54 + tests/xfs/057.out | 34 + tests/xfs/058 | 45 + tests/xfs/058.out | 243 ++ tests/xfs/059 | 50 + tests/xfs/059.out | 76 + tests/xfs/060 | 56 + tests/xfs/060.out | 120 + tests/xfs/061 | 54 + tests/xfs/061.out | 34 + tests/xfs/063 | 57 + tests/xfs/063.out | 74 + tests/xfs/064 | 109 + tests/xfs/064.out | 1484 +++++++ tests/xfs/065 | 197 + tests/xfs/065.out | 832 ++++ tests/xfs/066 | 73 + tests/xfs/066.out | 40 + tests/xfs/067 | 90 + tests/xfs/067.out | 166 + tests/xfs/071 | 169 + tests/xfs/071.out | 107 + tests/xfs/071.out.32 | 107 + tests/xfs/071.out.64 | 107 + tests/xfs/072 | 82 + tests/xfs/072.out | 2 + tests/xfs/073 | 182 + tests/xfs/073.out | 73 + tests/xfs/078 | 154 + tests/xfs/078.out | 211 + tests/xfs/080 | 73 + tests/xfs/080.out | 3 + tests/xfs/081 | 85 + tests/xfs/081.out | 4 + tests/xfs/081.ugquota.trans_inode | 3091 +++++++++++++++ tests/xfs/082 | 132 + tests/xfs/082.op.irix | 5628 +++++++++++++++++++++++++++ tests/xfs/082.op.linux | 4714 ++++++++++++++++++++++ tests/xfs/082.out | 39 + tests/xfs/082.trans_buf | 1821 +++++++++ tests/xfs/082.trans_inode | 2609 +++++++++++++ tests/xfs/084 | 76 + tests/xfs/084.out | 9 + tests/xfs/085 | 98 + tests/xfs/085.out | 114 + tests/xfs/086 | 151 + tests/xfs/086.out | 4722 ++++++++++++++++++++++ tests/xfs/087 | 152 + tests/xfs/087.out | 389 ++ tests/xfs/090 | 127 + tests/xfs/090.out | 18 + tests/xfs/092 | 60 + tests/xfs/092.out | 8 + tests/xfs/094 | 114 + tests/xfs/094.out | 12 + tests/xfs/095 | 68 + tests/xfs/095.out | 6 + tests/xfs/096 | 150 + tests/xfs/096.external | 53 + tests/xfs/096.internal | 55 + tests/xfs/103 | 101 + tests/xfs/103.out | 22 + tests/xfs/104 | 118 + tests/xfs/104.out | 127 + tests/xfs/106 | 238 ++ tests/xfs/106.out | 379 ++ tests/xfs/107 | 153 + tests/xfs/107.out | 1550 ++++++++ tests/xfs/108 | 123 + tests/xfs/108.out | 101 + tests/xfs/109 | 111 + tests/xfs/109.out | 12 + tests/xfs/110 | 86 + tests/xfs/110.out | 37 + tests/xfs/111 | 70 + tests/xfs/111.out | 100 + tests/xfs/114 | 345 ++ tests/xfs/114.out | 365 ++ tests/xfs/115 | 258 ++ tests/xfs/115.out | 118 + tests/xfs/116 | 65 + tests/xfs/116.out | 3 + tests/xfs/118 | 94 + tests/xfs/118.out | 9 + tests/xfs/119 | 75 + tests/xfs/119.out | 3 + tests/xfs/121 | 113 + tests/xfs/121.out | 15 + tests/xfs/122 | 220 ++ tests/xfs/122.out | 123 + tests/xfs/134 | 118 + tests/xfs/134.out | 5 + tests/xfs/136 | 360 ++ tests/xfs/136.out | 7753 +++++++++++++++++++++++++++++= ++++++++ tests/xfs/137 | 109 + tests/xfs/137.out | 1 + tests/xfs/138 | 115 + tests/xfs/138.out | 1 + tests/xfs/139 | 115 + tests/xfs/139.out | 1 + tests/xfs/140 | 112 + tests/xfs/140.out | 1 + tests/xfs/142 | 57 + tests/xfs/142.out | 232 ++ tests/xfs/143 | 57 + tests/xfs/143.out | 98 + tests/xfs/144 | 57 + tests/xfs/144.out | 245 ++ tests/xfs/145 | 57 + tests/xfs/145.out | 36 + tests/xfs/146 | 66 + tests/xfs/146.out.irix | 324 ++ tests/xfs/146.out.linux | 320 ++ tests/xfs/147 | 57 + tests/xfs/147.out | 29 + tests/xfs/148 | 109 + tests/xfs/148.out | 299 ++ tests/xfs/149 | 127 + tests/xfs/149.out | 123 + tests/xfs/150 | 68 + tests/xfs/150.out | 5 + tests/xfs/151 | 113 + tests/xfs/151.out | 22 + tests/xfs/152 | 62 + tests/xfs/152.out | 10 + tests/xfs/153 | 69 + tests/xfs/153.out | 8 + tests/xfs/154 | 56 + tests/xfs/154.out | 21 + tests/xfs/155 | 88 + tests/xfs/155.out | 8 + tests/xfs/156 | 55 + tests/xfs/156.out | 1 + tests/xfs/157 | 57 + tests/xfs/157.out | 2 + tests/xfs/158 | 102 + tests/xfs/158.out | 6 + tests/xfs/159 | 69 + tests/xfs/159.out | 5 + tests/xfs/160 | 79 + tests/xfs/160.out | 11 + tests/xfs/161 | 68 + tests/xfs/161.out | 12 + tests/xfs/162 | 85 + tests/xfs/162.out | 12 + tests/xfs/163 | 70 + tests/xfs/163.out | 3 + tests/xfs/164 | 156 + tests/xfs/164.out | 35 + tests/xfs/165 | 128 + tests/xfs/165.out | 1581 ++++++++ tests/xfs/166 | 98 + tests/xfs/166.out | 6 + tests/xfs/167 | 80 + tests/xfs/167.out | 3 + tests/xfs/168 | 113 + tests/xfs/168.out | 57 + tests/xfs/170 | 66 + tests/xfs/170.out | 21 + tests/xfs/171 | 69 + tests/xfs/171.out | 21 + tests/xfs/172 | 63 + tests/xfs/172.out | 11 + tests/xfs/173 | 66 + tests/xfs/173.out | 21 + tests/xfs/174 | 62 + tests/xfs/174.out | 11 + tests/xfs/175 | 70 + tests/xfs/175.out | 63 + tests/xfs/176 | 76 + tests/xfs/176.out | 121 + tests/xfs/177 | 84 + tests/xfs/177.out | 88 + tests/xfs/178 | 101 + tests/xfs/178.out | 79 + tests/xfs/179 | 110 + tests/xfs/179.out | 1 + tests/xfs/180 | 114 + tests/xfs/180.out | 1 + tests/xfs/181 | 127 + tests/xfs/181.out | 15 + tests/xfs/182 | 111 + tests/xfs/182.out | 1 + tests/xfs/183 | 66 + tests/xfs/183.out | 4 + tests/xfs/185 | 86 + tests/xfs/185.out | 71 + tests/xfs/186 | 183 + tests/xfs/186.out | 290 ++ tests/xfs/187 | 137 + tests/xfs/187.out | 39 + tests/xfs/188 | 87 + tests/xfs/188.out | 65 + tests/xfs/189 | 224 ++ tests/xfs/189.out | 59 + tests/xfs/190 | 99 + tests/xfs/190.out | 4 + tests/xfs/191 | 74 + tests/xfs/191.out | 324 ++ tests/xfs/194 | 217 ++ tests/xfs/194.out | 59 + tests/xfs/195 | 86 + tests/xfs/195.out | 8 + tests/xfs/196 | 97 + tests/xfs/196.out | 2002 ++++++++++ tests/xfs/197 | 65 + tests/xfs/197.out | 2 + tests/xfs/199 | 90 + tests/xfs/199.out | 13 + tests/xfs/200 | 125 + tests/xfs/200.out | 24 + tests/xfs/201 | 98 + tests/xfs/201.out | 2 + tests/xfs/202 | 60 + tests/xfs/202.out | 29 + tests/xfs/203 | 89 + tests/xfs/203.out | 427 ++ tests/xfs/205 | 82 + tests/xfs/205.out | 4 + tests/xfs/206 | 99 + tests/xfs/206.out | 30 + tests/xfs/216 | 77 + tests/xfs/216.out | 10 + tests/xfs/217 | 89 + tests/xfs/217.out | 7 + tests/xfs/220 | 83 + tests/xfs/220.out | 2 + tests/xfs/222 | 55 + tests/xfs/222.out | 2 + tests/xfs/227 | 209 + tests/xfs/227.out | 2 + tests/xfs/229 | 86 + tests/xfs/229.out | 4 + tests/xfs/238 | 55 + tests/xfs/238.out | 2 + tests/xfs/242 | 62 + tests/xfs/242.out | 77 + tests/xfs/244 | 136 + tests/xfs/244.out | 2 + tests/xfs/250 | 95 + tests/xfs/250.out | 14 + tests/xfs/252 | 65 + tests/xfs/252.out | 307 ++ tests/xfs/253 | 192 + tests/xfs/253.out | 2 + tests/xfs/259 | 65 + tests/xfs/259.out | 7 + tests/xfs/261 | 117 + tests/xfs/261.out | 2 + tests/xfs/262 | 144 + tests/xfs/262.out | 2 + tests/xfs/266 | 69 + tests/xfs/266.out | 133 + tests/xfs/267 | 73 + tests/xfs/267.out | 88 + tests/xfs/268 | 76 + tests/xfs/268.out | 86 + tests/xfs/278 | 85 + tests/xfs/278.out | 2 + tests/xfs/279 | 118 + tests/xfs/279.out | 35 + tests/xfs/281 | 57 + tests/xfs/281.out | 77 + tests/xfs/282 | 69 + tests/xfs/282.out | 133 + tests/xfs/283 | 72 + tests/xfs/283.out | 133 + tests/xfs/287 | 144 + tests/xfs/287.out | 23 + tests/xfs/290 | 94 + tests/xfs/290.out | 100 + tests/xfs/291 | 128 + tests/xfs/291.out | 1 + tests/xfs/292 | 63 + tests/xfs/292.out | 5 + tests/xfs/293 | 59 + tests/xfs/293.out | 2 + tests/xfs/295 | 81 + tests/xfs/295.out | 1 + tests/xfs/296 | 83 + tests/xfs/296.out | 55 + tests/xfs/297 | 88 + tests/xfs/297.out | 3 + 1276 files changed, 104258 insertions(+), 104258 deletions(-) delete mode 100755 001 delete mode 100644 001.out delete mode 100755 002 delete mode 100644 002.out delete mode 100755 003 delete mode 100644 003.out delete mode 100755 004 delete mode 100644 004.out delete mode 100755 005 delete mode 100644 005.out delete mode 100755 006 delete mode 100644 006.out delete mode 100755 007 delete mode 100644 007.out delete mode 100755 008 delete mode 100644 008.out delete mode 100755 009 delete mode 100644 009.out delete mode 100755 010 delete mode 100644 010.out delete mode 100755 011 delete mode 100644 011.out delete mode 100755 012 delete mode 100644 012.out delete mode 100755 013 delete mode 100644 013.out delete mode 100755 014 delete mode 100644 014.out delete mode 100755 015 delete mode 100644 015.out delete mode 100755 016 delete mode 100644 016.out delete mode 100755 017 delete mode 100644 017.out delete mode 100755 018 delete mode 100644 018.op.irix delete mode 100644 018.op.linux delete mode 100644 018.out delete mode 100644 018.trans_buf delete mode 100644 018.trans_inode delete mode 100755 019 delete mode 100644 019.out delete mode 100755 020 delete mode 100644 020.out delete mode 100755 021 delete mode 100644 021.out delete mode 100755 022 delete mode 100644 022.out.irix delete mode 100644 022.out.linux delete mode 100755 023 delete mode 100644 023.out.irix delete mode 100644 023.out.linux delete mode 100755 024 delete mode 100644 024.out delete mode 100755 025 delete mode 100644 025.out delete mode 100755 026 delete mode 100644 026.out delete mode 100755 027 delete mode 100644 027.out delete mode 100755 028 delete mode 100644 028.out delete mode 100755 029 delete mode 100644 029.out delete mode 100755 030 delete mode 100644 030.out.irix delete mode 100644 030.out.linux delete mode 100755 031 delete mode 100644 031.out.irix delete mode 100644 031.out.linux delete mode 100755 032 delete mode 100644 032.out delete mode 100755 033 delete mode 100644 033.out.irix delete mode 100644 033.out.linux delete mode 100755 034 delete mode 100644 034.out delete mode 100755 035 delete mode 100644 035.out.irix delete mode 100644 035.out.linux delete mode 100755 036 delete mode 100644 036.out.irix delete mode 100644 036.out.linux delete mode 100755 037 delete mode 100644 037.out delete mode 100755 038 delete mode 100644 038.out delete mode 100755 039 delete mode 100644 039.out.irix delete mode 100644 039.out.linux delete mode 100755 040 delete mode 100644 040.good delete mode 100644 040.out delete mode 100755 041 delete mode 100644 041.out delete mode 100755 042 delete mode 100644 042.out delete mode 100755 043 delete mode 100644 043.out.irix delete mode 100644 043.out.linux delete mode 100755 044 delete mode 100644 044.out delete mode 100755 045 delete mode 100644 045.out delete mode 100755 046 delete mode 100644 046.out delete mode 100755 047 delete mode 100644 047.out delete mode 100755 048 delete mode 100644 048.out delete mode 100755 049 delete mode 100644 049.out delete mode 100755 050 delete mode 100644 050.out delete mode 100755 051 delete mode 100644 051.out delete mode 100755 052 delete mode 100644 052.out delete mode 100755 053 delete mode 100644 053.out delete mode 100755 054 delete mode 100644 054.out delete mode 100755 055 delete mode 100644 055.out.irix delete mode 100644 055.out.linux delete mode 100755 056 delete mode 100644 056.out delete mode 100755 057 delete mode 100644 057.out delete mode 100755 058 delete mode 100644 058.out delete mode 100755 059 delete mode 100644 059.out delete mode 100755 060 delete mode 100644 060.out delete mode 100755 061 delete mode 100644 061.out delete mode 100755 062 delete mode 100644 062.out delete mode 100755 063 delete mode 100644 063.out delete mode 100755 064 delete mode 100644 064.out delete mode 100755 065 delete mode 100644 065.out delete mode 100755 066 delete mode 100644 066.out delete mode 100755 067 delete mode 100644 067.out delete mode 100755 068 delete mode 100644 068.out delete mode 100755 069 delete mode 100644 069.out delete mode 100755 070 delete mode 100644 070.out delete mode 100755 071 delete mode 100644 071.out delete mode 100644 071.out.32 delete mode 100644 071.out.64 delete mode 100755 072 delete mode 100644 072.out delete mode 100755 073 delete mode 100644 073.out delete mode 100755 074 delete mode 100644 074.out delete mode 100755 075 delete mode 100644 075.out delete mode 100755 076 delete mode 100644 076.out delete mode 100755 077 delete mode 100644 077.out delete mode 100755 078 delete mode 100644 078.out delete mode 100755 079 delete mode 100644 079.out delete mode 100755 080 delete mode 100644 080.out delete mode 100755 081 delete mode 100644 081.out delete mode 100644 081.ugquota.trans_inode delete mode 100755 082 delete mode 100644 082.op.irix delete mode 100644 082.op.linux delete mode 100644 082.out delete mode 100644 082.trans_buf delete mode 100644 082.trans_inode delete mode 100755 083 delete mode 100644 083.out delete mode 100755 084 delete mode 100644 084.out delete mode 100755 085 delete mode 100644 085.out delete mode 100755 086 delete mode 100644 086.out delete mode 100755 087 delete mode 100644 087.out delete mode 100755 088 delete mode 100644 088.out.irix delete mode 100644 088.out.linux delete mode 100755 089 delete mode 100644 089.out delete mode 100755 090 delete mode 100644 090.out delete mode 100755 091 delete mode 100644 091.out delete mode 100755 092 delete mode 100644 092.out delete mode 100755 093 delete mode 100644 093.out delete mode 100755 094 delete mode 100644 094.out delete mode 100755 095 delete mode 100644 095.out delete mode 100755 096 delete mode 100644 096.external delete mode 100644 096.internal delete mode 100755 097 delete mode 100644 097.out.udf delete mode 100644 097.out.xfs delete mode 100755 098 delete mode 100644 098.out delete mode 100755 099 delete mode 100644 099.out delete mode 100755 100 delete mode 100644 100.out delete mode 100755 101 delete mode 100644 101.out delete mode 100755 102 delete mode 100644 102.out delete mode 100755 103 delete mode 100644 103.out delete mode 100755 104 delete mode 100644 104.out delete mode 100755 105 delete mode 100644 105.out delete mode 100755 106 delete mode 100644 106.out delete mode 100755 107 delete mode 100644 107.out delete mode 100755 108 delete mode 100644 108.out delete mode 100755 109 delete mode 100644 109.out delete mode 100755 110 delete mode 100644 110.out delete mode 100755 111 delete mode 100644 111.out delete mode 100755 112 delete mode 100644 112.out delete mode 100755 113 delete mode 100644 113.out delete mode 100755 114 delete mode 100644 114.out delete mode 100755 115 delete mode 100644 115.out delete mode 100755 116 delete mode 100644 116.out delete mode 100755 117 delete mode 100644 117.out delete mode 100755 118 delete mode 100644 118.out delete mode 100755 119 delete mode 100644 119.out delete mode 100755 120 delete mode 100644 120.out delete mode 100755 121 delete mode 100644 121.out delete mode 100755 122 delete mode 100644 122.out delete mode 100755 123 delete mode 100644 123.out delete mode 100755 124 delete mode 100644 124.out delete mode 100755 125 delete mode 100644 125.out delete mode 100755 126 delete mode 100644 126.out delete mode 100755 127 delete mode 100644 127.out delete mode 100755 128 delete mode 100644 128.out delete mode 100755 129 delete mode 100644 129.out delete mode 100755 130 delete mode 100644 130.out delete mode 100755 131 delete mode 100644 131.out delete mode 100755 132 delete mode 100644 132.out delete mode 100755 133 delete mode 100644 133.out delete mode 100755 134 delete mode 100644 134.out delete mode 100755 135 delete mode 100644 135.out delete mode 100755 136 delete mode 100644 136.out delete mode 100755 137 delete mode 100644 137.out delete mode 100755 138 delete mode 100644 138.out delete mode 100755 139 delete mode 100644 139.out delete mode 100755 140 delete mode 100644 140.out delete mode 100755 141 delete mode 100644 141.out delete mode 100755 142 delete mode 100644 142.out delete mode 100755 143 delete mode 100644 143.out delete mode 100755 144 delete mode 100644 144.out delete mode 100755 145 delete mode 100644 145.out delete mode 100755 146 delete mode 100644 146.out.irix delete mode 100644 146.out.linux delete mode 100755 147 delete mode 100644 147.out delete mode 100755 148 delete mode 100644 148.out delete mode 100755 149 delete mode 100644 149.out delete mode 100755 150 delete mode 100644 150.out delete mode 100755 151 delete mode 100644 151.out delete mode 100755 152 delete mode 100644 152.out delete mode 100755 153 delete mode 100644 153.out delete mode 100755 154 delete mode 100644 154.out delete mode 100755 155 delete mode 100644 155.out delete mode 100755 156 delete mode 100644 156.out delete mode 100755 157 delete mode 100644 157.out delete mode 100755 158 delete mode 100644 158.out delete mode 100755 159 delete mode 100644 159.out delete mode 100755 160 delete mode 100644 160.out delete mode 100755 161 delete mode 100644 161.out delete mode 100755 162 delete mode 100644 162.out delete mode 100755 163 delete mode 100644 163.out delete mode 100755 164 delete mode 100644 164.out delete mode 100755 165 delete mode 100644 165.out delete mode 100755 166 delete mode 100644 166.out delete mode 100755 167 delete mode 100644 167.out delete mode 100755 168 delete mode 100644 168.out delete mode 100755 169 delete mode 100644 169.out delete mode 100755 170 delete mode 100644 170.out delete mode 100755 171 delete mode 100644 171.out delete mode 100755 172 delete mode 100644 172.out delete mode 100755 173 delete mode 100644 173.out delete mode 100755 174 delete mode 100644 174.out delete mode 100755 175 delete mode 100644 175.out delete mode 100755 176 delete mode 100644 176.out delete mode 100755 177 delete mode 100644 177.out delete mode 100755 178 delete mode 100644 178.out delete mode 100755 179 delete mode 100644 179.out delete mode 100755 180 delete mode 100644 180.out delete mode 100755 181 delete mode 100644 181.out delete mode 100755 182 delete mode 100644 182.out delete mode 100755 183 delete mode 100644 183.out delete mode 100755 184 delete mode 100644 184.out delete mode 100755 185 delete mode 100644 185.out delete mode 100755 186 delete mode 100644 186.out delete mode 100755 187 delete mode 100644 187.out delete mode 100755 188 delete mode 100644 188.out delete mode 100755 189 delete mode 100644 189.out delete mode 100755 190 delete mode 100644 190.out delete mode 100755 191 delete mode 100644 191.out delete mode 100755 192 delete mode 100644 192.out delete mode 100755 193 delete mode 100644 193.out delete mode 100755 194 delete mode 100644 194.out delete mode 100755 195 delete mode 100644 195.out delete mode 100755 196 delete mode 100644 196.out delete mode 100755 197 delete mode 100644 197.out delete mode 100755 198 delete mode 100644 198.out delete mode 100755 199 delete mode 100644 199.out delete mode 100755 200 delete mode 100644 200.out delete mode 100755 201 delete mode 100644 201.out delete mode 100755 202 delete mode 100644 202.out delete mode 100755 203 delete mode 100644 203.out delete mode 100755 204 delete mode 100644 204.out delete mode 100755 205 delete mode 100644 205.out delete mode 100755 206 delete mode 100644 206.out delete mode 100755 207 delete mode 100644 207.out delete mode 100755 208 delete mode 100644 208.out delete mode 100755 209 delete mode 100644 209.out delete mode 100755 210 delete mode 100644 210.out delete mode 100755 211 delete mode 100644 211.out delete mode 100755 212 delete mode 100644 212.out delete mode 100755 213 delete mode 100644 213.out delete mode 100755 214 delete mode 100644 214.out delete mode 100755 215 delete mode 100644 215.out delete mode 100755 216 delete mode 100644 216.out delete mode 100755 217 delete mode 100644 217.out delete mode 100755 218 delete mode 100644 218.out delete mode 100755 219 delete mode 100644 219.out delete mode 100755 220 delete mode 100644 220.out delete mode 100755 221 delete mode 100644 221.out delete mode 100755 222 delete mode 100644 222.out delete mode 100755 223 delete mode 100644 223.out delete mode 100755 224 delete mode 100644 224.out delete mode 100755 225 delete mode 100644 225.out delete mode 100755 226 delete mode 100644 226.out delete mode 100755 227 delete mode 100644 227.out delete mode 100755 228 delete mode 100644 228.out delete mode 100755 229 delete mode 100644 229.out delete mode 100755 230 delete mode 100644 230.out delete mode 100755 231 delete mode 100644 231.out delete mode 100755 232 delete mode 100644 232.out delete mode 100755 233 delete mode 100644 233.out delete mode 100755 234 delete mode 100644 234.out delete mode 100755 235 delete mode 100644 235.out delete mode 100755 236 delete mode 100644 236.out delete mode 100755 237 delete mode 100644 237.out delete mode 100755 238 delete mode 100644 238.out delete mode 100755 239 delete mode 100644 239.out delete mode 100755 240 delete mode 100644 240.out delete mode 100755 241 delete mode 100644 241.out delete mode 100755 242 delete mode 100644 242.out delete mode 100755 243 delete mode 100644 243.out delete mode 100755 244 delete mode 100644 244.out delete mode 100755 245 delete mode 100644 245.out delete mode 100755 246 delete mode 100644 246.out delete mode 100755 247 delete mode 100644 247.out delete mode 100755 248 delete mode 100644 248.out delete mode 100755 249 delete mode 100644 249.out delete mode 100755 250 delete mode 100644 250.out delete mode 100755 251 delete mode 100644 251.out delete mode 100755 252 delete mode 100644 252.out delete mode 100755 253 delete mode 100644 253.out delete mode 100755 254 delete mode 100644 254.out delete mode 100755 255 delete mode 100644 255.out delete mode 100755 256 delete mode 100644 256.out delete mode 100755 257 delete mode 100644 257.out delete mode 100755 258 delete mode 100644 258.out delete mode 100755 259 delete mode 100644 259.out delete mode 100755 260 delete mode 100644 260.out delete mode 100755 261 delete mode 100644 261.out delete mode 100755 262 delete mode 100644 262.out delete mode 100755 263 delete mode 100644 263.out delete mode 100755 264 delete mode 100644 264.out delete mode 100755 265 delete mode 100644 265.out delete mode 100755 266 delete mode 100644 266.out delete mode 100755 267 delete mode 100644 267.out delete mode 100755 268 delete mode 100644 268.out delete mode 100755 269 delete mode 100644 269.out delete mode 100755 270 delete mode 100644 270.out delete mode 100755 271 delete mode 100644 271.out delete mode 100755 272 delete mode 100644 272.out delete mode 100755 273 delete mode 100644 273.out delete mode 100755 274 delete mode 100644 274.out delete mode 100755 275 delete mode 100644 275.out delete mode 100755 276 delete mode 100644 276.out delete mode 100755 277 delete mode 100644 277.out delete mode 100755 278 delete mode 100644 278.out delete mode 100755 279 delete mode 100644 279.out delete mode 100755 280 delete mode 100644 280.out delete mode 100755 281 delete mode 100644 281.out delete mode 100755 282 delete mode 100644 282.out delete mode 100755 283 delete mode 100644 283.out delete mode 100644 284 delete mode 100644 284.out delete mode 100644 285 delete mode 100644 285.full delete mode 100644 285.out delete mode 100644 286 delete mode 100644 286.full delete mode 100644 286.out delete mode 100644 287 delete mode 100644 287.out delete mode 100644 288 delete mode 100644 288.out delete mode 100755 289 delete mode 100644 289.out delete mode 100644 290 delete mode 100644 290.out delete mode 100644 291 delete mode 100644 291.out delete mode 100644 292 delete mode 100644 292.out delete mode 100644 293 delete mode 100644 293.out delete mode 100644 294 delete mode 100644 294.out delete mode 100644 295 delete mode 100644 295.out delete mode 100644 296 delete mode 100644 296.out delete mode 100644 297 delete mode 100644 297.out delete mode 100644 298 delete mode 100644 298.out delete mode 100644 299 delete mode 100644 299.out delete mode 100644 300 delete mode 100644 300.out delete mode 100644 301 delete mode 100644 301.out delete mode 100644 302 delete mode 100644 302.out delete mode 100644 303 delete mode 100644 303.out delete mode 100644 304 delete mode 100644 304.out delete mode 100644 305 delete mode 100644 305.out create mode 100755 tests/btrfs/254 create mode 100644 tests/btrfs/254.out create mode 100755 tests/btrfs/264 create mode 100644 tests/btrfs/264.out create mode 100755 tests/btrfs/265 create mode 100644 tests/btrfs/265.out create mode 100755 tests/btrfs/276 create mode 100644 tests/btrfs/276.out create mode 100644 tests/btrfs/284 create mode 100644 tests/btrfs/284.out create mode 100755 tests/ext4/271 create mode 100644 tests/ext4/271.out create mode 100644 tests/ext4/301 create mode 100644 tests/ext4/301.out create mode 100644 tests/ext4/302 create mode 100644 tests/ext4/302.out create mode 100644 tests/ext4/303 create mode 100644 tests/ext4/303.out create mode 100644 tests/ext4/304 create mode 100644 tests/ext4/304.out create mode 100755 tests/generic/001 create mode 100644 tests/generic/001.out create mode 100755 tests/generic/002 create mode 100644 tests/generic/002.out create mode 100755 tests/generic/005 create mode 100644 tests/generic/005.out create mode 100755 tests/generic/006 create mode 100644 tests/generic/006.out create mode 100755 tests/generic/007 create mode 100644 tests/generic/007.out create mode 100755 tests/generic/010 create mode 100644 tests/generic/010.out create mode 100755 tests/generic/011 create mode 100644 tests/generic/011.out create mode 100755 tests/generic/013 create mode 100644 tests/generic/013.out create mode 100755 tests/generic/014 create mode 100644 tests/generic/014.out create mode 100755 tests/generic/015 create mode 100644 tests/generic/015.out create mode 100755 tests/generic/020 create mode 100644 tests/generic/020.out create mode 100755 tests/generic/053 create mode 100644 tests/generic/053.out create mode 100755 tests/generic/062 create mode 100644 tests/generic/062.out create mode 100755 tests/generic/069 create mode 100644 tests/generic/069.out create mode 100755 tests/generic/070 create mode 100644 tests/generic/070.out create mode 100755 tests/generic/074 create mode 100644 tests/generic/074.out create mode 100755 tests/generic/075 create mode 100644 tests/generic/075.out create mode 100755 tests/generic/076 create mode 100644 tests/generic/076.out create mode 100755 tests/generic/077 create mode 100644 tests/generic/077.out create mode 100755 tests/generic/079 create mode 100644 tests/generic/079.out create mode 100755 tests/generic/083 create mode 100644 tests/generic/083.out create mode 100755 tests/generic/088 create mode 100644 tests/generic/088.out.irix create mode 100644 tests/generic/088.out.linux create mode 100755 tests/generic/089 create mode 100644 tests/generic/089.out create mode 100755 tests/generic/091 create mode 100644 tests/generic/091.out create mode 100755 tests/generic/093 create mode 100644 tests/generic/093.out create mode 100755 tests/generic/097 create mode 100644 tests/generic/097.out.udf create mode 100644 tests/generic/097.out.xfs create mode 100755 tests/generic/099 create mode 100644 tests/generic/099.out create mode 100755 tests/generic/100 create mode 100644 tests/generic/100.out create mode 100755 tests/generic/105 create mode 100644 tests/generic/105.out create mode 100755 tests/generic/112 create mode 100644 tests/generic/112.out create mode 100755 tests/generic/113 create mode 100644 tests/generic/113.out create mode 100755 tests/generic/117 create mode 100644 tests/generic/117.out create mode 100755 tests/generic/120 create mode 100644 tests/generic/120.out create mode 100755 tests/generic/123 create mode 100644 tests/generic/123.out create mode 100755 tests/generic/124 create mode 100644 tests/generic/124.out create mode 100755 tests/generic/125 create mode 100644 tests/generic/125.out create mode 100755 tests/generic/126 create mode 100644 tests/generic/126.out create mode 100755 tests/generic/127 create mode 100644 tests/generic/127.out create mode 100755 tests/generic/128 create mode 100644 tests/generic/128.out create mode 100755 tests/generic/129 create mode 100644 tests/generic/129.out create mode 100755 tests/generic/130 create mode 100644 tests/generic/130.out create mode 100755 tests/generic/131 create mode 100644 tests/generic/131.out create mode 100755 tests/generic/132 create mode 100644 tests/generic/132.out create mode 100755 tests/generic/133 create mode 100644 tests/generic/133.out create mode 100755 tests/generic/135 create mode 100644 tests/generic/135.out create mode 100755 tests/generic/141 create mode 100644 tests/generic/141.out create mode 100755 tests/generic/169 create mode 100644 tests/generic/169.out create mode 100755 tests/generic/184 create mode 100644 tests/generic/184.out create mode 100755 tests/generic/192 create mode 100644 tests/generic/192.out create mode 100755 tests/generic/193 create mode 100644 tests/generic/193.out create mode 100755 tests/generic/198 create mode 100644 tests/generic/198.out create mode 100755 tests/generic/204 create mode 100644 tests/generic/204.out create mode 100755 tests/generic/207 create mode 100644 tests/generic/207.out create mode 100755 tests/generic/208 create mode 100644 tests/generic/208.out create mode 100755 tests/generic/209 create mode 100644 tests/generic/209.out create mode 100755 tests/generic/210 create mode 100644 tests/generic/210.out create mode 100755 tests/generic/211 create mode 100644 tests/generic/211.out create mode 100755 tests/generic/212 create mode 100644 tests/generic/212.out create mode 100755 tests/generic/213 create mode 100644 tests/generic/213.out create mode 100755 tests/generic/214 create mode 100644 tests/generic/214.out create mode 100755 tests/generic/215 create mode 100644 tests/generic/215.out create mode 100755 tests/generic/219 create mode 100644 tests/generic/219.out create mode 100755 tests/generic/221 create mode 100644 tests/generic/221.out create mode 100755 tests/generic/223 create mode 100644 tests/generic/223.out create mode 100755 tests/generic/224 create mode 100644 tests/generic/224.out create mode 100755 tests/generic/225 create mode 100644 tests/generic/225.out create mode 100755 tests/generic/226 create mode 100644 tests/generic/226.out create mode 100755 tests/generic/228 create mode 100644 tests/generic/228.out create mode 100755 tests/generic/230 create mode 100644 tests/generic/230.out create mode 100755 tests/generic/231 create mode 100644 tests/generic/231.out create mode 100755 tests/generic/232 create mode 100644 tests/generic/232.out create mode 100755 tests/generic/233 create mode 100644 tests/generic/233.out create mode 100755 tests/generic/234 create mode 100644 tests/generic/234.out create mode 100755 tests/generic/235 create mode 100644 tests/generic/235.out create mode 100755 tests/generic/236 create mode 100644 tests/generic/236.out create mode 100755 tests/generic/237 create mode 100644 tests/generic/237.out create mode 100755 tests/generic/239 create mode 100644 tests/generic/239.out create mode 100755 tests/generic/240 create mode 100644 tests/generic/240.out create mode 100755 tests/generic/241 create mode 100644 tests/generic/241.out create mode 100755 tests/generic/245 create mode 100644 tests/generic/245.out create mode 100755 tests/generic/246 create mode 100644 tests/generic/246.out create mode 100755 tests/generic/247 create mode 100644 tests/generic/247.out create mode 100755 tests/generic/248 create mode 100644 tests/generic/248.out create mode 100755 tests/generic/249 create mode 100644 tests/generic/249.out create mode 100755 tests/generic/251 create mode 100644 tests/generic/251.out create mode 100755 tests/generic/255 create mode 100644 tests/generic/255.out create mode 100755 tests/generic/256 create mode 100644 tests/generic/256.out create mode 100755 tests/generic/257 create mode 100644 tests/generic/257.out create mode 100755 tests/generic/258 create mode 100644 tests/generic/258.out create mode 100755 tests/generic/260 create mode 100644 tests/generic/260.out create mode 100755 tests/generic/263 create mode 100644 tests/generic/263.out create mode 100755 tests/generic/269 create mode 100644 tests/generic/269.out create mode 100755 tests/generic/270 create mode 100644 tests/generic/270.out create mode 100755 tests/generic/273 create mode 100644 tests/generic/273.out create mode 100755 tests/generic/274 create mode 100644 tests/generic/274.out create mode 100755 tests/generic/275 create mode 100644 tests/generic/275.out create mode 100755 tests/generic/277 create mode 100644 tests/generic/277.out create mode 100755 tests/generic/280 create mode 100644 tests/generic/280.out create mode 100644 tests/generic/285 create mode 100644 tests/generic/285.full create mode 100644 tests/generic/285.out create mode 100644 tests/generic/286 create mode 100644 tests/generic/286.full create mode 100644 tests/generic/286.out create mode 100644 tests/generic/288 create mode 100644 tests/generic/288.out create mode 100644 tests/generic/294 create mode 100644 tests/generic/294.out create mode 100644 tests/generic/299 create mode 100644 tests/generic/299.out create mode 100644 tests/generic/300 create mode 100644 tests/generic/300.out create mode 100755 tests/shared/051 create mode 100644 tests/shared/051.out create mode 100755 tests/shared/068 create mode 100644 tests/shared/068.out create mode 100755 tests/shared/218 create mode 100644 tests/shared/218.out create mode 100755 tests/shared/243 create mode 100644 tests/shared/243.out create mode 100755 tests/shared/272 create mode 100644 tests/shared/272.out create mode 100755 tests/shared/289 create mode 100644 tests/shared/289.out create mode 100644 tests/shared/298 create mode 100644 tests/shared/298.out create mode 100644 tests/shared/305 create mode 100644 tests/shared/305.out create mode 100755 tests/udf/098 create mode 100644 tests/udf/098.out create mode 100755 tests/udf/101 create mode 100644 tests/udf/101.out create mode 100755 tests/udf/102 create mode 100644 tests/udf/102.out create mode 100755 tests/xfs/003 create mode 100644 tests/xfs/003.out create mode 100755 tests/xfs/004 create mode 100644 tests/xfs/004.out create mode 100755 tests/xfs/008 create mode 100644 tests/xfs/008.out create mode 100755 tests/xfs/009 create mode 100644 tests/xfs/009.out create mode 100755 tests/xfs/012 create mode 100644 tests/xfs/012.out create mode 100755 tests/xfs/016 create mode 100644 tests/xfs/016.out create mode 100755 tests/xfs/017 create mode 100644 tests/xfs/017.out create mode 100755 tests/xfs/018 create mode 100644 tests/xfs/018.op.irix create mode 100644 tests/xfs/018.op.linux create mode 100644 tests/xfs/018.out create mode 100644 tests/xfs/018.trans_buf create mode 100644 tests/xfs/018.trans_inode create mode 100755 tests/xfs/019 create mode 100644 tests/xfs/019.out create mode 100755 tests/xfs/021 create mode 100644 tests/xfs/021.out create mode 100755 tests/xfs/022 create mode 100644 tests/xfs/022.out.irix create mode 100644 tests/xfs/022.out.linux create mode 100755 tests/xfs/023 create mode 100644 tests/xfs/023.out.irix create mode 100644 tests/xfs/023.out.linux create mode 100755 tests/xfs/024 create mode 100644 tests/xfs/024.out create mode 100755 tests/xfs/025 create mode 100644 tests/xfs/025.out create mode 100755 tests/xfs/026 create mode 100644 tests/xfs/026.out create mode 100755 tests/xfs/027 create mode 100644 tests/xfs/027.out create mode 100755 tests/xfs/028 create mode 100644 tests/xfs/028.out create mode 100755 tests/xfs/029 create mode 100644 tests/xfs/029.out create mode 100755 tests/xfs/030 create mode 100644 tests/xfs/030.out.irix create mode 100644 tests/xfs/030.out.linux create mode 100755 tests/xfs/031 create mode 100644 tests/xfs/031.out.irix create mode 100644 tests/xfs/031.out.linux create mode 100755 tests/xfs/032 create mode 100644 tests/xfs/032.out create mode 100755 tests/xfs/033 create mode 100644 tests/xfs/033.out.irix create mode 100644 tests/xfs/033.out.linux create mode 100755 tests/xfs/034 create mode 100644 tests/xfs/034.out create mode 100755 tests/xfs/035 create mode 100644 tests/xfs/035.out.irix create mode 100644 tests/xfs/035.out.linux create mode 100755 tests/xfs/036 create mode 100644 tests/xfs/036.out.irix create mode 100644 tests/xfs/036.out.linux create mode 100755 tests/xfs/037 create mode 100644 tests/xfs/037.out create mode 100755 tests/xfs/038 create mode 100644 tests/xfs/038.out create mode 100755 tests/xfs/039 create mode 100644 tests/xfs/039.out.irix create mode 100644 tests/xfs/039.out.linux create mode 100755 tests/xfs/040 create mode 100644 tests/xfs/040.good create mode 100644 tests/xfs/040.out create mode 100755 tests/xfs/041 create mode 100644 tests/xfs/041.out create mode 100755 tests/xfs/042 create mode 100644 tests/xfs/042.out create mode 100755 tests/xfs/043 create mode 100644 tests/xfs/043.out.irix create mode 100644 tests/xfs/043.out.linux create mode 100755 tests/xfs/044 create mode 100644 tests/xfs/044.out create mode 100755 tests/xfs/045 create mode 100644 tests/xfs/045.out create mode 100755 tests/xfs/046 create mode 100644 tests/xfs/046.out create mode 100755 tests/xfs/047 create mode 100644 tests/xfs/047.out create mode 100755 tests/xfs/048 create mode 100644 tests/xfs/048.out create mode 100755 tests/xfs/049 create mode 100644 tests/xfs/049.out create mode 100755 tests/xfs/050 create mode 100644 tests/xfs/050.out create mode 100755 tests/xfs/052 create mode 100644 tests/xfs/052.out create mode 100755 tests/xfs/054 create mode 100644 tests/xfs/054.out create mode 100755 tests/xfs/055 create mode 100644 tests/xfs/055.out.irix create mode 100644 tests/xfs/055.out.linux create mode 100755 tests/xfs/056 create mode 100644 tests/xfs/056.out create mode 100755 tests/xfs/057 create mode 100644 tests/xfs/057.out create mode 100755 tests/xfs/058 create mode 100644 tests/xfs/058.out create mode 100755 tests/xfs/059 create mode 100644 tests/xfs/059.out create mode 100755 tests/xfs/060 create mode 100644 tests/xfs/060.out create mode 100755 tests/xfs/061 create mode 100644 tests/xfs/061.out create mode 100755 tests/xfs/063 create mode 100644 tests/xfs/063.out create mode 100755 tests/xfs/064 create mode 100644 tests/xfs/064.out create mode 100755 tests/xfs/065 create mode 100644 tests/xfs/065.out create mode 100755 tests/xfs/066 create mode 100644 tests/xfs/066.out create mode 100755 tests/xfs/067 create mode 100644 tests/xfs/067.out create mode 100755 tests/xfs/071 create mode 100644 tests/xfs/071.out create mode 100644 tests/xfs/071.out.32 create mode 100644 tests/xfs/071.out.64 create mode 100755 tests/xfs/072 create mode 100644 tests/xfs/072.out create mode 100755 tests/xfs/073 create mode 100644 tests/xfs/073.out create mode 100755 tests/xfs/078 create mode 100644 tests/xfs/078.out create mode 100755 tests/xfs/080 create mode 100644 tests/xfs/080.out create mode 100755 tests/xfs/081 create mode 100644 tests/xfs/081.out create mode 100644 tests/xfs/081.ugquota.trans_inode create mode 100755 tests/xfs/082 create mode 100644 tests/xfs/082.op.irix create mode 100644 tests/xfs/082.op.linux create mode 100644 tests/xfs/082.out create mode 100644 tests/xfs/082.trans_buf create mode 100644 tests/xfs/082.trans_inode create mode 100755 tests/xfs/084 create mode 100644 tests/xfs/084.out create mode 100755 tests/xfs/085 create mode 100644 tests/xfs/085.out create mode 100755 tests/xfs/086 create mode 100644 tests/xfs/086.out create mode 100755 tests/xfs/087 create mode 100644 tests/xfs/087.out create mode 100755 tests/xfs/090 create mode 100644 tests/xfs/090.out create mode 100755 tests/xfs/092 create mode 100644 tests/xfs/092.out create mode 100755 tests/xfs/094 create mode 100644 tests/xfs/094.out create mode 100755 tests/xfs/095 create mode 100644 tests/xfs/095.out create mode 100755 tests/xfs/096 create mode 100644 tests/xfs/096.external create mode 100644 tests/xfs/096.internal create mode 100755 tests/xfs/103 create mode 100644 tests/xfs/103.out create mode 100755 tests/xfs/104 create mode 100644 tests/xfs/104.out create mode 100755 tests/xfs/106 create mode 100644 tests/xfs/106.out create mode 100755 tests/xfs/107 create mode 100644 tests/xfs/107.out create mode 100755 tests/xfs/108 create mode 100644 tests/xfs/108.out create mode 100755 tests/xfs/109 create mode 100644 tests/xfs/109.out create mode 100755 tests/xfs/110 create mode 100644 tests/xfs/110.out create mode 100755 tests/xfs/111 create mode 100644 tests/xfs/111.out create mode 100755 tests/xfs/114 create mode 100644 tests/xfs/114.out create mode 100755 tests/xfs/115 create mode 100644 tests/xfs/115.out create mode 100755 tests/xfs/116 create mode 100644 tests/xfs/116.out create mode 100755 tests/xfs/118 create mode 100644 tests/xfs/118.out create mode 100755 tests/xfs/119 create mode 100644 tests/xfs/119.out create mode 100755 tests/xfs/121 create mode 100644 tests/xfs/121.out create mode 100755 tests/xfs/122 create mode 100644 tests/xfs/122.out create mode 100755 tests/xfs/134 create mode 100644 tests/xfs/134.out create mode 100755 tests/xfs/136 create mode 100644 tests/xfs/136.out create mode 100755 tests/xfs/137 create mode 100644 tests/xfs/137.out create mode 100755 tests/xfs/138 create mode 100644 tests/xfs/138.out create mode 100755 tests/xfs/139 create mode 100644 tests/xfs/139.out create mode 100755 tests/xfs/140 create mode 100644 tests/xfs/140.out create mode 100755 tests/xfs/142 create mode 100644 tests/xfs/142.out create mode 100755 tests/xfs/143 create mode 100644 tests/xfs/143.out create mode 100755 tests/xfs/144 create mode 100644 tests/xfs/144.out create mode 100755 tests/xfs/145 create mode 100644 tests/xfs/145.out create mode 100755 tests/xfs/146 create mode 100644 tests/xfs/146.out.irix create mode 100644 tests/xfs/146.out.linux create mode 100755 tests/xfs/147 create mode 100644 tests/xfs/147.out create mode 100755 tests/xfs/148 create mode 100644 tests/xfs/148.out create mode 100755 tests/xfs/149 create mode 100644 tests/xfs/149.out create mode 100755 tests/xfs/150 create mode 100644 tests/xfs/150.out create mode 100755 tests/xfs/151 create mode 100644 tests/xfs/151.out create mode 100755 tests/xfs/152 create mode 100644 tests/xfs/152.out create mode 100755 tests/xfs/153 create mode 100644 tests/xfs/153.out create mode 100755 tests/xfs/154 create mode 100644 tests/xfs/154.out create mode 100755 tests/xfs/155 create mode 100644 tests/xfs/155.out create mode 100755 tests/xfs/156 create mode 100644 tests/xfs/156.out create mode 100755 tests/xfs/157 create mode 100644 tests/xfs/157.out create mode 100755 tests/xfs/158 create mode 100644 tests/xfs/158.out create mode 100755 tests/xfs/159 create mode 100644 tests/xfs/159.out create mode 100755 tests/xfs/160 create mode 100644 tests/xfs/160.out create mode 100755 tests/xfs/161 create mode 100644 tests/xfs/161.out create mode 100755 tests/xfs/162 create mode 100644 tests/xfs/162.out create mode 100755 tests/xfs/163 create mode 100644 tests/xfs/163.out create mode 100755 tests/xfs/164 create mode 100644 tests/xfs/164.out create mode 100755 tests/xfs/165 create mode 100644 tests/xfs/165.out create mode 100755 tests/xfs/166 create mode 100644 tests/xfs/166.out create mode 100755 tests/xfs/167 create mode 100644 tests/xfs/167.out create mode 100755 tests/xfs/168 create mode 100644 tests/xfs/168.out create mode 100755 tests/xfs/170 create mode 100644 tests/xfs/170.out create mode 100755 tests/xfs/171 create mode 100644 tests/xfs/171.out create mode 100755 tests/xfs/172 create mode 100644 tests/xfs/172.out create mode 100755 tests/xfs/173 create mode 100644 tests/xfs/173.out create mode 100755 tests/xfs/174 create mode 100644 tests/xfs/174.out create mode 100755 tests/xfs/175 create mode 100644 tests/xfs/175.out create mode 100755 tests/xfs/176 create mode 100644 tests/xfs/176.out create mode 100755 tests/xfs/177 create mode 100644 tests/xfs/177.out create mode 100755 tests/xfs/178 create mode 100644 tests/xfs/178.out create mode 100755 tests/xfs/179 create mode 100644 tests/xfs/179.out create mode 100755 tests/xfs/180 create mode 100644 tests/xfs/180.out create mode 100755 tests/xfs/181 create mode 100644 tests/xfs/181.out create mode 100755 tests/xfs/182 create mode 100644 tests/xfs/182.out create mode 100755 tests/xfs/183 create mode 100644 tests/xfs/183.out create mode 100755 tests/xfs/185 create mode 100644 tests/xfs/185.out create mode 100755 tests/xfs/186 create mode 100644 tests/xfs/186.out create mode 100755 tests/xfs/187 create mode 100644 tests/xfs/187.out create mode 100755 tests/xfs/188 create mode 100644 tests/xfs/188.out create mode 100755 tests/xfs/189 create mode 100644 tests/xfs/189.out create mode 100755 tests/xfs/190 create mode 100644 tests/xfs/190.out create mode 100755 tests/xfs/191 create mode 100644 tests/xfs/191.out create mode 100755 tests/xfs/194 create mode 100644 tests/xfs/194.out create mode 100755 tests/xfs/195 create mode 100644 tests/xfs/195.out create mode 100755 tests/xfs/196 create mode 100644 tests/xfs/196.out create mode 100755 tests/xfs/197 create mode 100644 tests/xfs/197.out create mode 100755 tests/xfs/199 create mode 100644 tests/xfs/199.out create mode 100755 tests/xfs/200 create mode 100644 tests/xfs/200.out create mode 100755 tests/xfs/201 create mode 100644 tests/xfs/201.out create mode 100755 tests/xfs/202 create mode 100644 tests/xfs/202.out create mode 100755 tests/xfs/203 create mode 100644 tests/xfs/203.out create mode 100755 tests/xfs/205 create mode 100644 tests/xfs/205.out create mode 100755 tests/xfs/206 create mode 100644 tests/xfs/206.out create mode 100755 tests/xfs/216 create mode 100644 tests/xfs/216.out create mode 100755 tests/xfs/217 create mode 100644 tests/xfs/217.out create mode 100755 tests/xfs/220 create mode 100644 tests/xfs/220.out create mode 100755 tests/xfs/222 create mode 100644 tests/xfs/222.out create mode 100755 tests/xfs/227 create mode 100644 tests/xfs/227.out create mode 100755 tests/xfs/229 create mode 100644 tests/xfs/229.out create mode 100755 tests/xfs/238 create mode 100644 tests/xfs/238.out create mode 100755 tests/xfs/242 create mode 100644 tests/xfs/242.out create mode 100755 tests/xfs/244 create mode 100644 tests/xfs/244.out create mode 100755 tests/xfs/250 create mode 100644 tests/xfs/250.out create mode 100755 tests/xfs/252 create mode 100644 tests/xfs/252.out create mode 100755 tests/xfs/253 create mode 100644 tests/xfs/253.out create mode 100755 tests/xfs/259 create mode 100644 tests/xfs/259.out create mode 100755 tests/xfs/261 create mode 100644 tests/xfs/261.out create mode 100755 tests/xfs/262 create mode 100644 tests/xfs/262.out create mode 100755 tests/xfs/266 create mode 100644 tests/xfs/266.out create mode 100755 tests/xfs/267 create mode 100644 tests/xfs/267.out create mode 100755 tests/xfs/268 create mode 100644 tests/xfs/268.out create mode 100755 tests/xfs/278 create mode 100644 tests/xfs/278.out create mode 100755 tests/xfs/279 create mode 100644 tests/xfs/279.out create mode 100755 tests/xfs/281 create mode 100644 tests/xfs/281.out create mode 100755 tests/xfs/282 create mode 100644 tests/xfs/282.out create mode 100755 tests/xfs/283 create mode 100644 tests/xfs/283.out create mode 100644 tests/xfs/287 create mode 100644 tests/xfs/287.out create mode 100644 tests/xfs/290 create mode 100644 tests/xfs/290.out create mode 100644 tests/xfs/291 create mode 100644 tests/xfs/291.out create mode 100644 tests/xfs/292 create mode 100644 tests/xfs/292.out create mode 100644 tests/xfs/293 create mode 100644 tests/xfs/293.out create mode 100644 tests/xfs/295 create mode 100644 tests/xfs/295.out create mode 100644 tests/xfs/296 create mode 100644 tests/xfs/296.out create mode 100644 tests/xfs/297 create mode 100644 tests/xfs/297.out diff --git a/001 b/001 deleted file mode 100755 index b9997f3..0000000 --- a/001 +++ /dev/null @@ -1,319 +0,0 @@ -#! /bin/bash -# FS QA Test No. 001 -# -# Random file copier to produce chains of identical files so the head -# and the tail can be diff'd at the end of each iteration. -# -# Exercises creat, write and unlink for a variety of directory sizes, = and -# checks for data corruption. -# -# run [config] -# -# config has one line per file with filename and byte size, else use -# the default one below. -# -#---------------------------------------------------------------------= -- -# Copyright (c) 2000-2001 Silicon Graphics, Inc. All Rights Reserved. -# -# This program is free software; you can redistribute it and/or -# modify it under the terms of the GNU General Public License as -# published by the Free Software Foundation. -# -# This program is distributed in the hope that it would be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program; if not, write the Free Software Foundation, -# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA -# -#---------------------------------------------------------------------= -- -# - -seq=3D`basename $0` -echo "QA output created by $seq" - -# get standard environment, filters and checks -. ./common.rc -. ./common.filter - -tmp=3D/tmp/$$ -here=3D`pwd` -status=3D1 -done_cleanup=3Dfalse -trap "_cleanup; rm -f $tmp.*; exit \$status" 0 1 2 3 15 - -# real QA test starts here -_supported_fs generic -_supported_os IRIX Linux - -verbose=3Dtrue -verify=3D$here/verify_fill - -if [ $# -eq 0 ] -then - # use the default config - # - cat <$tmp.config -# pathname=09size in bytes -# -small=09=0910 -big=09=09102400 -sub/small=0910 -sub/big=09=09102400 -# -sub/a=09=091 -sub/b=09=092 -sub/c=09=094 -sub/d=09=098 -sub/e=09=0916 -sub/f=09=0932 -sub/g=09=0964 -sub/h=09=09128 -sub/i=09=09256 -sub/j=09=09512 -sub/k=09=091024 -sub/l=09=092048 -sub/m=09=094096 -sub/n=09=098192 -# -sub/a00=09=09100 -sub/b00=09=09200 -sub/c00=09=09400 -sub/d00=09=09800 -sub/e00=09=091600 -sub/f00=09=093200 -sub/g00=09=096400 -sub/h00=09=0912800 -sub/i00=09=0925600 -sub/j00=09=0951200 -sub/k00=09=09102400 -sub/l00=09=09204800 -sub/m00=09=09409600 -sub/n00=09=09819200 -# -sub/a000=091000 -sub/e000=0916000 -sub/h000=09128000 -sub/k000=091024000 -End-of-File -elif [ $# -eq 1 ] -then - if [ -f $1 ] - then -=09cp $1 $tmp.config - else -=09echo "Error: cannot open config \"$1\"" -=09exit 1 - fi -else - echo "Usage: run [config]" - exit 1 -fi - -ncopy=3D200=09=09# number of file copies in the chain step -udf_fsize=3D20240=09=09# number of sectors for UDF - -_setup() -{ - if mkdir -p $testdir/$$ - then -=09: - else -=09echo "Error: cannot mkdir \"$testdir/$$\"" -=09exit 1 - fi - cd $testdir/$$ - - $verbose && echo -n "setup " - sed -e '/^#/d' $tmp.config \ - | while read file nbytes - do -=09dir=3D`dirname $file` -=09if [ "$dir" !=3D "." ] -=09then -=09 if [ ! -d $dir ] -=09 then -=09=09if mkdir $dir -=09=09then -=09=09 : -=09=09else -=09=09 $verbose && echo -=09=09 echo "Error: cannot mkdir \"$dir\"" -=09=09 exit 1 -=09=09fi -=09 fi -=09fi -=09rm -f $file -=09if $here/src/fill $file $file $nbytes -=09then -=09 : -=09else -=09 $verbose && echo -=09 echo "Error: cannot create \"$file\"" -=09 exit 1 -=09fi -=09$verbose && echo -n "." - done - $verbose && echo -} - -_mark_iteration() -{ - $verbose && echo -n "mark_iteration " - sed -e '/^#/d' $tmp.config \ - | while read file nbytes - do -=09if [ ! -f $file ] -=09then -=09 $verbose && echo -=09 echo "Error: $file vanished!" -=09 touch $tmp.bad -=09 continue -=09fi -=09sed -e "s/ [0-9][0-9]* / $1 /" <$file >$file.tmp -=09mv $file.tmp $file -=09$verbose && echo -n "." - done - $verbose && echo -} - -# for each file, make a number of copies forming a chain like foo.0, -# foo.1, foo.2, ... foo.N -# -# files are chosen at random, so the lengths of the chains are differe= nt -# -# then rename foo.N to foo.last and remove all of the other files in -# the chain -# -_chain() -{ - $AWK_PROG -v full_file=3D$here/$seq.full -v verify=3D$verify <$tmp= .config ' -BEGIN=09{ nfile =3D 0 } -/^\#/=09{ next } -=09{ file[nfile] =3D $1 -=09 size[nfile] =3D $2 -=09 link[nfile] =3D 0 -=09 nfile++ -=09 total_size +=3D $2 -=09} -END=09{ srand('$iter') -=09 for (i=3D0; i < '$ncopy'; i++) { -=09 # choose a file at random, and add one copy to that chain -=09 j =3D -1 -=09 while (j < 0 || j >=3D nfile) -=09=09j =3D int(rand() * nfile) -=09 if (link[j] =3D=3D 0) { -=09=09# previous should already exist and next one should not exist -=09=09printf "if [ ! -f %s ]; then echo \"%s missing!\"; exit; fi\n",f= ile[j],file[j] -=09=09printf "if [ -f %s.0 ]; then echo \"%s.0 already present!\"; exi= t; fi\n",file[j],file[j] -=09=09printf "cp %s %s.0 || exit 1\n",file[j],file[j] -=09=09printf "ls -i %s.0\n", file[j] >full_file; -=09=09total_size +=3D size[j] -=09=09printf "# total size =3D %d\n", total_size=20 -=09 } -=09 else { -=09=09# previous should already exist and next one should not exist -=09=09printf "if [ ! -f %s.%d ]; then echo \"%s.%d missing!\"; exit; f= i\n",file[j],link[j]-1,file[j],link[j]-1 -=09=09printf "if [ -f %s.%d ]; then echo \"%s.%d already present!\"; e= xit; fi\n",file[j],link[j],file[j],link[j] -=09=09printf "cp %s.%d %s.%d || exit 1\n",file[j],link[j]-1,file[j],li= nk[j] -=09=09printf "ls -i %s.%d\n", file[j], link[j] >full_file; -=09=09total_size +=3D size[j] -=09=09printf "# total size =3D %d\n", total_size=20 -=09 } -=09 link[j]++ -=09 } -=09 # close all the chains,=20 -=09 # if have at least one copy then move the last copy to "file[j].l= ast" -=09 # and remove all of the other files except the head of the chain -=09 for (j=3D0; j 0) { -=09=09printf "mv %s.%d %s.last\n",file[j],link[j]-1,file[j] -=09=09printf "ls -i %s.last\n", file[j] >full_file; -=09 } -=09 for (i=3D0; i/dev/null 2>&1 -=09 then -=09=09$verbose && echo -n "." -=09 else -=09=09$verbose && echo -=09=09echo "Error: corruption for $file ..." -=09=09diff -c $file $file.last -=09=09touch $tmp.bad -=09 fi -=09else -=09 $verbose && echo -n "." -=09fi - done - $verbose && echo -} - -_cleanup() -{ - # cleanup - # - if $done_cleanup - then -=09: - elif [ $status -eq 0 ] - then -=09$verbose && echo "cleanup" -=09cd / -=09rm -rf $testdir/$$ -=09_cleanup_testdir -=09done_cleanup=3Dtrue - fi -} - -rm -f $here/$seq.full -status=3D0 -_cleanup -status=3D1 -done_cleanup=3Dfalse - -_setup_testdir -_setup - -# do the test -# -for iter in 1 2 3 4 5 -do - echo -n "iter $iter chain ... " - echo "iter $iter" >> $here/$seq.full - _chain - _check - if [ -f $tmp.bad ] - then -=09echo "Fatal error: test abandoned without changes" -=09exit 1 - fi -done - -status=3D0 -exit diff --git a/001.out b/001.out deleted file mode 100644 index e843a58..0000000 --- a/001.out +++ /dev/null @@ -1,9 +0,0 @@ -QA output created by 001 -cleanup -setup .................................... -iter 1 chain ... check .................................... -iter 2 chain ... check .................................... -iter 3 chain ... check .................................... -iter 4 chain ... check .................................... -iter 5 chain ... check .................................... -cleanup diff --git a/002 b/002 deleted file mode 100755 index db63fa0..0000000 --- a/002 +++ /dev/null @@ -1,80 +0,0 @@ -#! /bin/bash -# FS QA Test No. 002 -# -# simple inode link count test for a regular file -# -#---------------------------------------------------------------------= -- -# Copyright (c) 2000-2001 Silicon Graphics, Inc. All Rights Reserved. -# -# This program is free software; you can redistribute it and/or -# modify it under the terms of the GNU General Public License as -# published by the Free Software Foundation. -# -# This program is distributed in the hope that it would be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program; if not, write the Free Software Foundation, -# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA -# -#---------------------------------------------------------------------= -- -# - -seq=3D`basename $0` -echo "QA output created by $seq" - -# get standard environment, filters and checks -. ./common.rc -. ./common.filter - -tmp=3D/tmp/$$ -here=3D`pwd` -status=3D0=09# success is the default! -trap "_cleanup; exit \$status" 0 1 2 3 15 - -_cleanup() -{ - rm -f $tmp.* - _cleanup_testdir -} - -# real QA test starts here -_supported_fs generic -_supported_os IRIX Linux - -_setup_testdir - -echo "Silence is goodness ..." - -# ensure target directory exists -mkdir `dirname $testdir/$tmp` 2>/dev/null - -touch $testdir/$tmp.1 -for l in 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 -do - ln $testdir/$tmp.1 $testdir/$tmp.$l - x=3D`src/lstat64 $testdir/$tmp.1 | sed -n -e '/ Links: /s/.*Links:= *//p'` - if [ "$l" -ne $x ] - then -=09echo "Arrgh, created link #$l and lstat64 looks like ..." -=09src/lstat64 $testdir/$tmp.1 -=09status=3D1 - fi -done - -for l in 20 19 18 17 16 15 14 13 12 11 10 9 8 7 6 5 4 3 2 1 -do - x=3D`src/lstat64 $testdir/$tmp.1 | sed -n -e '/ Links: /s/.*Links:= *//p'` - if [ "$l" -ne $x ] - then -=09echo "Arrgh, about to remove link #$l and lstat64 looks like ..." -=09src/lstat64 $testdir/$tmp.1 -=09status=3D1 - fi - rm -f $testdir/$tmp.$l -done - -# success, all done -exit diff --git a/002.out b/002.out deleted file mode 100644 index 11426b5..0000000 --- a/002.out +++ /dev/null @@ -1,2 +0,0 @@ -QA output created by 002 -Silence is goodness ... diff --git a/003 b/003 deleted file mode 100755 index 79b6bc5..0000000 --- a/003 +++ /dev/null @@ -1,91 +0,0 @@ -#! /bin/bash -# FS QA Test No. 003 -# -# exercise xfs_db bug #784078 -# -#---------------------------------------------------------------------= -- -# Copyright (c) 2000-2001 Silicon Graphics, Inc. All Rights Reserved. -# -# This program is free software; you can redistribute it and/or -# modify it under the terms of the GNU General Public License as -# published by the Free Software Foundation. -# -# This program is distributed in the hope that it would be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program; if not, write the Free Software Foundation, -# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA -# -#---------------------------------------------------------------------= -- -# - -seq=3D`basename $0` -echo "QA output created by $seq" - -# get standard environment, filters and checks -. ./common.rc -. ./common.filter - -tmp=3D/tmp/$$ -here=3D`pwd` -status=3D0=09# success is the default! -trap "rm -f $tmp.*; exit \$status" 0 1 2 3 15 - -_need_to_be_root - -# real QA test starts here -_supported_fs xfs -_supported_os IRIX Linux - -[ -f core ] && rm -f core -[ -f core ] && echo "Warning: can't nuke existing core file!" - -test_done() -{ - sts=3D$? - [ -f core ] && echo "FAILED - core file" - [ ! -f core -a $sts !=3D 0 ] && echo "FAILED - non-zero exit s= tatus" - rm -f core -} - -# real QA test starts here - -echo "=3D=3D=3D TEST 1 =3D=3D=3D" -xfs_db -r -c 'pop' -c 'type sb' $TEST_DEV -test_done - -echo "=3D=3D=3D TEST 2 =3D=3D=3D" -xfs_db -r -c 'push sb' $TEST_DEV -test_done - -echo "=3D=3D=3D TEST 3 =3D=3D=3D" -xfs_db -r -c 'pop' -c 'push sb' $TEST_DEV -test_done - -echo "=3D=3D=3D TEST 4 =3D=3D=3D" -xfs_db -r -c 'type sb' -c 'print' $TEST_DEV -test_done - -echo "=3D=3D=3D TEST 5 =3D=3D=3D" -xfs_db -r -c 'inode 128' -c 'push' -c 'type' $TEST_DEV >$tmp.out 2>&1 -test_done -# On IRIX we lose state after a "push" operation and don't -# know the type is still inode -# Probably not worth changing xfs_db on IRIX for this. -if [ "$HOSTOS" !=3D "IRIX" ]; then - if ! grep -q "current type is \"inode\"" $tmp.out - then -=09 cat $tmp.out - fi -fi - -echo "=3D=3D=3D TEST 6 =3D=3D=3D" -xfs_db -r -c 'sb' -c 'a' $TEST_DEV >$tmp.out 2>&1 # don't care about o= utput -test_done - -echo "=3D=3D=3D TEST 7 =3D=3D=3D" -xfs_db -r -c 'ring' $TEST_DEV -test_done diff --git a/003.out b/003.out deleted file mode 100644 index e55df2e..0000000 --- a/003.out +++ /dev/null @@ -1,12 +0,0 @@ -QA output created by 003 -=3D=3D=3D TEST 1 =3D=3D=3D -no current object -=3D=3D=3D TEST 2 =3D=3D=3D -=3D=3D=3D TEST 3 =3D=3D=3D -=3D=3D=3D TEST 4 =3D=3D=3D -no current object -no current type -=3D=3D=3D TEST 5 =3D=3D=3D -=3D=3D=3D TEST 6 =3D=3D=3D -=3D=3D=3D TEST 7 =3D=3D=3D -no entries in location ring. diff --git a/004 b/004 deleted file mode 100755 index 8c920ae..0000000 --- a/004 +++ /dev/null @@ -1,142 +0,0 @@ -#! /bin/bash -# FS QA Test No. 004 -# -# exercise xfs_db bug #789674 and other freesp functionality -# -#---------------------------------------------------------------------= -- -# Copyright (c) 2000-2002 Silicon Graphics, Inc. All Rights Reserved. -# -# This program is free software; you can redistribute it and/or -# modify it under the terms of the GNU General Public License as -# published by the Free Software Foundation. -# -# This program is distributed in the hope that it would be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program; if not, write the Free Software Foundation, -# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA -# -#---------------------------------------------------------------------= -- -# - -seq=3D`basename $0` -echo "QA output created by $seq" - -here=3D`pwd` -tmp=3D/tmp/$$ -status=3D0 - -_cleanup() -{ -=09umount $SCRATCH_MNT -=09rm -f $tmp.* -=09exit $status -} -trap "_cleanup" 0 1 2 3 15 - -_populate_scratch() -{ -=09echo "=3D=3D=3D mkfs output =3D=3D=3D" >>$seq.full -=09_scratch_mkfs_xfs | tee -a $seq.full | _filter_mkfs 2>$tmp.mkfs -=09. $tmp.mkfs -=09_scratch_mount -=09dd if=3D/dev/zero of=3D$SCRATCH_MNT/foo count=3D200 bs=3D4096 >/dev= /null 2>&1 & -=09dd if=3D/dev/zero of=3D$SCRATCH_MNT/goo count=3D400 bs=3D4096 >/dev= /null 2>&1 & -=09dd if=3D/dev/zero of=3D$SCRATCH_MNT/moo count=3D800 bs=3D4096 >/dev= /null 2>&1 & -=09wait -=09umount $SCRATCH_MNT=09=09=09# flush everything -=09_scratch_mount=09=09=09=09# and then remount -} - - -# get standard environment, filters and checks -. ./common.rc -. ./common.filter - -# real QA test starts here -_supported_fs xfs -_supported_os IRIX Linux - -_need_to_be_root -_require_scratch -_require_nobigloopfs - -rm -f $seq.full - -_populate_scratch - -[ "$HOSTOS" =3D "Linux" ] && DF_PROG=3D"$DF_PROG -P --block-size=3D512= " - -eval `$DF_PROG $SCRATCH_MNT 2>&1 \ -=09| tail -1 | $AWK_PROG '{ printf "blocks=3D%u used=3D%u avail=3D%u\n= ", $3, $4, $5 }'` -echo "df gave: blocks=3D$blocks used=3D$used avail=3D$avail" >>$seq.fu= ll -echo "blocksize from mkfs is '$dbsize'" >>$seq.full - -xfs_db -r -c "freesp -s" $SCRATCH_DEV >$tmp.xfs_db -echo "xfs_db for $SCRATCH_DEV" >>$seq.full -cat $tmp.xfs_db >>$seq.full - -eval `$XFS_IO_PROG -x -c resblks $SCRATCH_MNT 2>&1 \ -=09| $AWK_PROG '/available/ { printf "resblks=3D%u\n", $5 }'` -echo "resblks gave: resblks=3D$resblks" >>$seq.full - -# check the 'blocks' field from freesp command is OK -# since 2.6.18, df does not report the 4 blocks per AG that cannot -# be allocated, hence we check for that exact mismatch. -# since ~2.6.22, reserved blocks are used by default and df does -# not report them, hence check for an exact mismatch. -perl -ne ' -=09BEGIN=09{ $avail =3D'$avail' * 512; -=09=09 $answer=3D"(no xfs_db free blocks line?)" } -=09/free blocks (\d+)$/=09|| next; -=09$freesp =3D $1 * '$dbsize'; -=09if ($freesp =3D=3D $avail) { -=09=09$answer =3D "yes"; -=09} else { -=09=09$avail =3D $avail + (('$agcount' + 1) * '$dbsize' * 4); -=09=09if ($freesp =3D=3D $avail) { -=09=09=09$answer =3D "yes"; -=09=09} else { -=09=09=09$avail =3D $avail + ('$resblks' * '$dbsize'); -=09=09=09if ($freesp =3D=3D $avail) { -=09=09=09=09$answer =3D "yes"; -=09=09=09} else { -=09=09=09=09$answer =3D "no ($freesp !=3D $avail)"; -=09=09=09} -=09=09} -=09} -=09END=09{ print "$answer\n" } -=09' <$tmp.xfs_db >$tmp.ans -ans=3D"`cat $tmp.ans`" -echo "Checking blocks column same as df: $ans" -if [ "$ans" !=3D yes ] -then -=09echo "Error: $SCRATCH_DEV: freesp mismatch: $ans" -=09echo "xfs_db output ..." -=09cat $tmp.xfs_db -=09status=3D1 -fi - -# check the 'pct' field from freesp command is good -perl -ne ' -=09 BEGIN=09{ $percent =3D 0; } -=09 /free/=09&& next;=09# skip over free extent size number -=09 if (/\s+(\d+\.\d+)$/) { -=09=09$percent +=3D $1; -=09 } -=09 END=09{ $percent +=3D 0.5; print int($percent), "\n" }=09# roun= d up -' <$tmp.xfs_db >$tmp.ans -ans=3D"`cat $tmp.ans`" -echo "Checking percent column yields 100: $ans" -if [ "$ans" !=3D 100 ] -then -=09echo "Error: $SCRATCH_DEV: pct mismatch: $ans (expected 100)" -=09echo "xfs_db output ..." -=09cat $tmp.xfs_db -=09status=3D1 -fi - -exit diff --git a/004.out b/004.out deleted file mode 100644 index b94d653..0000000 --- a/004.out +++ /dev/null @@ -1,9 +0,0 @@ -QA output created by 004 -meta-data=3DDDEV isize=3DXXX agcount=3DN, agsize=3DXXX blks -data =3D bsize=3DXXX blocks=3DXXX, imaxpct=3DPCT - =3D sunit=3DXXX swidth=3DXXX, unwritten=3DX -naming =3DVERN bsize=3DXXX -log =3DLDEV bsize=3DXXX blocks=3DXXX -realtime =3DRDEV extsz=3DXXX blocks=3DXXX, rtextents=3DXXX -Checking blocks column same as df: yes -Checking percent column yields 100: 100 diff --git a/005 b/005 deleted file mode 100755 index 27da3d3..0000000 --- a/005 +++ /dev/null @@ -1,99 +0,0 @@ -#! /bin/bash -# FS QA Test No. 005 -# -# Test symlinks & ELOOP -# -#---------------------------------------------------------------------= -- -# Copyright (c) 2000-2004 Silicon Graphics, Inc. All Rights Reserved. -# -# This program is free software; you can redistribute it and/or -# modify it under the terms of the GNU General Public License as -# published by the Free Software Foundation. -# -# This program is distributed in the hope that it would be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program; if not, write the Free Software Foundation, -# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA -# -#---------------------------------------------------------------------= -- -# - -# -# Note1: On Linux, ELOOP limit used to be 32 but changed to 8, and lat= ely -# its become 5. Who knows what it might be next. -# Note2: On IRIX, the limit is around the 30 mark. -#=20 -# What we are looking for here is: no panic due to blowing the stack; -# and that the ELOOP error code is returned at some point (the actual -# limit point is unimportant, just checking that we do hit it). -#=20 - -seq=3D`basename $0` -echo "QA output created by $seq" - -here=3D`pwd` -tmp=3D/tmp/$$ -status=3D0=09# success is the default! -trap "_cleanup; exit \$status" 0 1 2 3 15 - -_cleanup() -{ - cd $testdir - rm -f symlink_{0,1,2,3,4}{0,1,2,3,4,5,6,7,8,9} symlink_self empty_= file - cd / - _cleanup_testdir -} - -_touch() -{ - # On IRIX: Too many symbolic links in path name traversal - # On Linux: Too many levels of symbolic links - touch $@ 2>&1 | grep -q 'Too many.*symbolic links' - if [ $? -eq 0 ]; then -=09echo "ELOOP returned. Good." - else -=09echo "No ELOOP? Unexpected!" - fi -} - -# get standard environment, filters and checks -. ./common.rc -. ./common.filter - -# real QA test starts here -_supported_fs generic - -# IRIX UDF does not support symlinks -if [ $FSTYP =3D=3D 'udf' ]; then - _supported_os Linux -else - _supported_os Linux IRIX -fi - -_setup_testdir - -cd $testdir - -o=3Dempty_file -touch $o -for f in symlink_{0,1,2,3,4}{0,1,2,3,4,5,6,7,8,9} -do - ln -s $o $f - o=3D$f -done - -ln -s symlink_self symlink_self - -echo "*** touch deep symlinks" -echo "" -_touch symlink_{0,1,2,3,4}{0,1,2,3,4,5,6,7,8,9} -echo "" -echo "*** touch recusive symlinks" -echo "" -_touch symlink_self - -exit diff --git a/005.out b/005.out deleted file mode 100644 index b3ccffa..0000000 --- a/005.out +++ /dev/null @@ -1,8 +0,0 @@ -QA output created by 005 -*** touch deep symlinks - -ELOOP returned. Good. - -*** touch recusive symlinks - -ELOOP returned. Good. diff --git a/006 b/006 deleted file mode 100755 index 1437b46..0000000 --- a/006 +++ /dev/null @@ -1,78 +0,0 @@ -#! /bin/bash -# FS QA Test No. 006 -# -# permname -# -#---------------------------------------------------------------------= -- -# Copyright (c) 2000-2001 Silicon Graphics, Inc. All Rights Reserved. -# -# This program is free software; you can redistribute it and/or -# modify it under the terms of the GNU General Public License as -# published by the Free Software Foundation. -# -# This program is distributed in the hope that it would be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program; if not, write the Free Software Foundation, -# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA -# -#---------------------------------------------------------------------= -- -# - -seq=3D`basename $0` -echo "QA output created by $seq" - -here=3D`pwd` -tmp=3D/tmp/$$ -status=3D0=09# success is the default! -trap "_cleanup; exit \$status" 0 1 2 3 15 - -_cleanup() -{ - cd / - rm -f $tmp.* - rm -rf $testdir/permname.$$ - _cleanup_testdir -} - -_count() -{ - $AWK_PROG ' - BEGIN { count =3D 0 } - { count ++ } - END { print count " files created" } - ' -} - -# get standard environment, filters and checks -. ./common.rc -. ./common.filter - -# real QA test starts here -_supported_fs generic -_supported_os IRIX Linux - -_setup_testdir - -mkdir $testdir/permname.$$ - -echo "" -echo "single thread permname" -echo "----------------------" -mkdir $testdir/permname.$$/a -cd $testdir/permname.$$/a -$here/src/permname -c 4 -l 6 -p 1 || echo "permname returned $?" -find . | _count - -echo "" -echo "multi thread permname" -echo "----------------------" -mkdir $testdir/permname.$$/b -cd $testdir/permname.$$/b -$here/src/permname -c 4 -l 6 -p 4 || echo "permname returned $?" -find . | _count - -exit diff --git a/006.out b/006.out deleted file mode 100644 index ce17a49..0000000 --- a/006.out +++ /dev/null @@ -1,11 +0,0 @@ -QA output created by 006 - -single thread permname ----------------------- -alpha size =3D 4, name length =3D 6, total files =3D 4096, nproc=3D1 -4097 files created - -multi thread permname ----------------------- -alpha size =3D 4, name length =3D 6, total files =3D 4096, nproc=3D4 -4097 files created diff --git a/007 b/007 deleted file mode 100755 index 2bb981f..0000000 --- a/007 +++ /dev/null @@ -1,74 +0,0 @@ -#! /bin/bash -# FS QA Test No. 007 -# -# drive the src/nametest program -# which does a heap of open(create)/unlink/stat -# and checks that error codes make sense with its -# memory of the files created. -# -#---------------------------------------------------------------------= -- -# Copyright (c) 2000-2001 Silicon Graphics, Inc. All Rights Reserved. -# -# This program is free software; you can redistribute it and/or -# modify it under the terms of the GNU General Public License as -# published by the Free Software Foundation. -# -# This program is distributed in the hope that it would be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program; if not, write the Free Software Foundation, -# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA -# -#---------------------------------------------------------------------= -- -# - -seq=3D`basename $0` -echo "QA output created by $seq" - -here=3D`pwd` -tmp=3D/tmp/$$ -status=3D0=09# success is the default! -trap "_cleanup; exit \$status" 0 1 2 3 15 - -_cleanup() -{ - cd / - rm -f $tmp.* - rm -rf $testdir/$seq - _cleanup_testdir -} - -# get standard environment, filters and checks -. ./common.rc -. ./common.filter - -# real QA test starts here -_supported_fs generic -_supported_os IRIX Linux - -_setup_testdir - -status=3D1 # default failure=20 -sourcefile=3D$tmp.nametest -seed=3D1 -iterations=3D100000 -num_filenames=3D100 - -# need to create an input file with a list of -# filenames on each line=20 -i=3D1 -while [ $i -le $num_filenames ]; do - echo "nametest.$i" >>$sourcefile - let i=3D$i+1 -done - -mkdir $testdir/$seq -cd $testdir/$seq -$here/src/nametest -l $sourcefile -s $seed -i $iterations -z - -# success, all done -status=3D0 -exit diff --git a/007.out b/007.out deleted file mode 100644 index 514b44a..0000000 --- a/007.out +++ /dev/null @@ -1,22 +0,0 @@ -QA output created by 007 -.Seed =3D 1 (use "-s 1" to re-execute this test) -......................................................................= . -......................................................................= ... -......................................................................= ... -......................................................................= ... -......................................................................= ... -......................................................................= ... -......................................................................= ... -......................................................................= ... -......................................................................= ... -......................................................................= ... -......................................................................= ... -......................................................................= ... -......................................................................= ... -.................................................... -creates: 18736 OK, 18802 EEXIST ( 37538 total, 50% EEXIST) -removes: 18675 OK, 19927 ENOENT ( 38602 total, 51% ENOENT) -lookups: 12000 OK, 11860 ENOENT ( 23860 total, 49% ENOENT) -total : 49411 OK, 50589 w/error (100000 total, 50% w/error) - -cleanup: 61 removes diff --git a/008 b/008 deleted file mode 100755 index 0dee9f5..0000000 --- a/008 +++ /dev/null @@ -1,116 +0,0 @@ -#! /bin/bash -# FS QA Test No. 008 -# -# randholes test -# -#---------------------------------------------------------------------= -- -# Copyright (c) 2000-2002 Silicon Graphics, Inc. All Rights Reserved. -# -# This program is free software; you can redistribute it and/or -# modify it under the terms of the GNU General Public License as -# published by the Free Software Foundation. -# -# This program is distributed in the hope that it would be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program; if not, write the Free Software Foundation, -# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA -# -#---------------------------------------------------------------------= -- -# - -seq=3D`basename $0` -echo "QA output created by $seq" - -here=3D`pwd` -tmp=3D/tmp/$$ -status=3D0=09# success is the default! -pgsize=3D`$here/src/feature -s` -trap "_cleanup; exit \$status" 0 1 2 3 15 - -_cleanup() -{ - rm -f $tmp.* - rm -rf $testdir/randholes.$$.* - _cleanup_testdir -} - -_filter() -{ - sed -e "s/-b $pgsize/-b PGSIZE/g" \ -=09-e "s/-l .* -c/-l FSIZE -c/g" -} - -# get standard environment, filters and checks -. ./common.rc -. ./common.filter - -_do_test() -{ - _n=3D"$1" - _holes=3D"$2" - _param=3D"$3" - - out=3D$testdir/randholes.$$.$_n - echo "" - echo "randholes.$_n : $_param" | _filter - echo "------------------------------------------" - if $here/src/randholes $_param $out >$tmp.out - then -=09# only check if we're not allocating in huge chunks (extsz flag) -=09if _test_inode_flag extsize $out || _test_inode_flag realtime $out -=09then -=09=09echo "holes is in range" -=09else -=09=09# quick check - how many holes did we get? -=09 count=3D`xfs_bmap $out | egrep -c ': hole'` -=09=09# blocks can end up adjacent, therefore number of holes varies -=09=09_within_tolerance "holes" $count $_holes 10% -v -=09fi - else - echo " randholes returned $? - see $seq.out.full" - echo "--------------------------------------" >>$here/$s= eq.out.full - echo "$_n - output from randholes:" >>$here/$s= eq.out.full - echo "--------------------------------------" >>$here/$s= eq.out.full - cat $tmp.out >>$here/$s= eq.out.full - echo "--------------------------------------" >>$here/$s= eq.out.full - echo "$_n - output from bmap:" >>$here/$s= eq.out.full - echo "--------------------------------------" >>$here/$s= eq.out.full - xfs_bmap -vvv $out >>$here/$s= eq.out.full - status=3D1 - fi -} - -# real QA test starts here -_supported_fs xfs -_supported_os IRIX Linux - -_setup_testdir - -rm -f $here/$seq.out.full - -# Note on special numbers here. -# -# We are trying to create roughly 50 or 100 holes in a file -# using random writes. Assuming a good distribution of 50 writes -# in a file, the file only needs to be 3-4x the size of the write -# size muliplied by the number of writes. Hence we use 200 * pgsize -# for files we want 50 holes in and 400 * pgsize for files we want -# 100 holes in. This keeps the runtime down as low as possible. -# -_do_test 1 50 "-l `expr 200 \* $pgsize` -c 50 -b $pgsize" -_do_test 2 100 "-l `expr 400 \* $pgsize` -c 100 -b $pgsize" -_do_test 3 100 "-l `expr 400 \* $pgsize` -c 100 -b 512" # test parti= al pages - -# rinse, lather, repeat for direct IO -_do_test 4 50 "-d -l `expr 200 \* $pgsize` -c 50 -b $pgsize" -_do_test 5 100 "-d -l `expr 400 \* $pgsize` -c 100 -b $pgsize" -# note: direct IO requires page aligned IO - -# todo: realtime. - -# success, all done -exit diff --git a/008.out b/008.out deleted file mode 100644 index 5e3ae8e..0000000 --- a/008.out +++ /dev/null @@ -1,21 +0,0 @@ -QA output created by 008 - -randholes.1 : -l FSIZE -c 50 -b PGSIZE ------------------------------------------- -holes is in range - -randholes.2 : -l FSIZE -c 100 -b PGSIZE ------------------------------------------- -holes is in range - -randholes.3 : -l FSIZE -c 100 -b 512 ------------------------------------------- -holes is in range - -randholes.4 : -d -l FSIZE -c 50 -b PGSIZE ------------------------------------------- -holes is in range - -randholes.5 : -d -l FSIZE -c 100 -b PGSIZE ------------------------------------------- -holes is in range diff --git a/009 b/009 deleted file mode 100755 index 1883f15..0000000 --- a/009 +++ /dev/null @@ -1,187 +0,0 @@ -#! /bin/bash -# FS QA Test No. 009 -# -# XFS allocator test (preallocation - allocp, resvsp ,etc) -# -#---------------------------------------------------------------------= -- -# Copyright (c) 2000-2002 Silicon Graphics, Inc. All Rights Reserved. -# -# This program is free software; you can redistribute it and/or -# modify it under the terms of the GNU General Public License as -# published by the Free Software Foundation. -# -# This program is distributed in the hope that it would be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program; if not, write the Free Software Foundation, -# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA -# -#---------------------------------------------------------------------= -- -# - -seq=3D`basename $0` -echo "QA output created by $seq" - -here=3D`pwd` -tmp=3D/tmp/$$ -status=3D1=09# failure is the default! -trap "_cleanup; exit \$status" 0 1 2 3 15 -# This isn't really related to fs block size, it's just what -# alloc uses for the "block" unit in it's input parameters... -bsize=3D4096 - -_cleanup() -{ - echo "*** unmount" - umount $SCRATCH_MNT -} - -_block_filter() -{ - sed \ -=09-e 's/[0-9][0-9]*\.\.[0-9][0-9]*/BLOCKRANGE/g' \ -=09-e "s/blocksize $bsize/blocksize BSIZE/g" -} - -_init() -{ - echo "*** mkfs" - if ! _scratch_mkfs_xfs >$tmp.out 2>&1 - then -=09cat $tmp.out - echo "failed to mkfs $SCRATCH_DEV" - exit 1 - fi - - echo "*** mount" - if ! _scratch_mount - then - echo "failed to mount $SCRATCH_DEV" - exit 1 - fi -} - -_filesize() -{ - ls -l $1 | $AWK_PROG '{print "filesize =3D " $5}' -} - -# get standard environment, filters and checks -. ./common.rc -. ./common.filter - -# real QA test starts here -_supported_fs xfs -_supported_os IRIX Linux - -_require_scratch - -_init -out=3D$SCRATCH_MNT/$$.tmp - -# since we're using a clean FS here, we make some assumptions -# about availability of contiguous blocks - -# also interesting to note is that ALLOC =3D=3D FREE. seriously. -# the _length is ignored_ in irix. the file is allocated up -# to the specified offset, and zero filled if previously -# unallocated. the file is truncated at the specified point. - -echo "*** test 1 - reservations cleared on O_TRUNC" -rm -f $out -cat <&1 | tee -a $here/$seq.full | _filter_= dbtest - -# success, all done -exit diff --git a/010.out b/010.out deleted file mode 100644 index 56a3ccb..0000000 --- a/010.out +++ /dev/null @@ -1,58 +0,0 @@ -QA output created by 010 -dbtest v1.0 - -Creating database containing 1000 records... -=09performing lookups for 5 iterations... -=09using BLEEP as seed for srandom()... - -=09 -There were BLEEP duplicate checksums generated - -Performing lookups on database... - -=09Sequential lookups... - - -=09Random lookups... - -Lookups succeeded... - -Performing lookups on database... - -=09Sequential lookups... - - -=09Random lookups... - -Lookups succeeded... - -Performing lookups on database... - -=09Sequential lookups... - - -=09Random lookups... - -Lookups succeeded... - -Performing lookups on database... - -=09Sequential lookups... - - -=09Random lookups... - -Lookups succeeded... - -Performing lookups on database... - -=09Sequential lookups... - - -=09Random lookups... - -Lookups succeeded... - -Cleaning up database... -=09 -There were BLEEP duplicate checksums generated diff --git a/011 b/011 deleted file mode 100755 index 4ede2d8..0000000 --- a/011 +++ /dev/null @@ -1,86 +0,0 @@ -#! /bin/bash -# FS QA Test No. 011 -# -# dirstress -# -#---------------------------------------------------------------------= -- -# Copyright (c) 2000-2001 Silicon Graphics, Inc. All Rights Reserved. -# -# This program is free software; you can redistribute it and/or -# modify it under the terms of the GNU General Public License as -# published by the Free Software Foundation. -# -# This program is distributed in the hope that it would be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program; if not, write the Free Software Foundation, -# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA -# -#---------------------------------------------------------------------= -- -# - -seq=3D`basename $0` -echo "QA output created by $seq" - -out=3D"" -here=3D`pwd` -tmp=3D/tmp/$$ -status=3D0=09# success is the default! -trap "_cleanup; exit \$status" 0 1 2 3 15 - -_cleanup() -{ - cd / - rm -f $tmp.* - [ -n "$out" ] && rm -rf $out - _cleanup_testdir -} - -# get standard environment, filters and checks -. ./common.rc -. ./common.filter - -# real QA test starts here -_supported_fs generic -_supported_os IRIX Linux - -_setup_testdir - -out=3D$testdir/dirstress.$$ - -rm -f $seq.full - -_test() -{ - test=3D"$1" - args=3D"$2" - count=3D"$3" - =20 - echo "*** TEST $test $args -f " - if ! $here/src/dirstress -d $out -f $count $args >$tmp.out 2>&1 - then - echo " dirstress failed" - echo "*** TEST $test -d $out -f $count $args" >>$seq.full - cat $tmp.out >>$seq.full - status=3D1 - fi -} - -# dirstress doesn't check returns - this is a crash & burn test. -if ! mkdir $out -then - echo "!! couldn't mkdir $out" - status=3D1 - exit -fi - -count=3D1000 -_test 1 "-p 1 -n 1" $count -_test 2 "-p 5 -n 1" $count -_test 3 "-p 5 -n 5" $count - -# if error -exit diff --git a/011.out b/011.out deleted file mode 100644 index 546a4db..0000000 --- a/011.out +++ /dev/null @@ -1,4 +0,0 @@ -QA output created by 011 -*** TEST 1 -p 1 -n 1 -f -*** TEST 2 -p 5 -n 1 -f -*** TEST 3 -p 5 -n 5 -f diff --git a/012 b/012 deleted file mode 100755 index 10498d5..0000000 --- a/012 +++ /dev/null @@ -1,121 +0,0 @@ -#! /bin/bash -# FS QA Test No. 012 -# -# holes -# -#---------------------------------------------------------------------= -- -# Copyright (c) 2000-2001 Silicon Graphics, Inc. All Rights Reserved. -# -# This program is free software; you can redistribute it and/or -# modify it under the terms of the GNU General Public License as -# published by the Free Software Foundation. -# -# This program is distributed in the hope that it would be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program; if not, write the Free Software Foundation, -# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA -# -#---------------------------------------------------------------------= -- -# - -seq=3D`basename $0` -echo "QA output created by $seq" - -here=3D`pwd` -tmp=3D/tmp/$$ -status=3D0=09# success is the default! -trap "_cleanup; exit \$status" 0 1 2 3 15 - -_cleanup() -{ - cd / - rm -f $tmp.* - rm -rf $testdir/holes.$$.* - _cleanup_testdir -} - -_filesize() -{ - ls -l $1 | $AWK_PROG '{print " filesize =3D " $5}' -} - -# get standard environment, filters and checks -. ./common.rc -. ./common.filter - -_do_test() -{ - _n=3D"$1" - _param=3D"$2" - _count=3D"$3" - =20 - failed=3D0 - =20 - out=3D$testdir/holes.$$.$_n - echo "" - echo "holes.$_n : $_param" - echo "-----------------------------------------------" - if ! $here/src/holes $_param $out >$tmp.out - then - echo " holes returned $? - see $seq.out.full" - failed=3D1 - status=3D1 - fi - =20 - - if [ $failed -eq 0 ] - then =20 - # quick check - how many holes did we get? - count=3D`xfs_bmap $out | egrep -c ': hole'` - echo " $count hole(s) detected" - # and how big was the file? - _filesize $out - =20 - if [ $count -ne $_count ] - then - echo " unexpected number of holes - see $seq.out.full" - status=3D1 - failed=3D1 - fi - fi - =20 - if [ $failed -eq 1 ] - then - echo "--------------------------------------" >>$here/$s= eq.out.full - echo "$_n - output from holes:" >>$here/$s= eq.out.full - echo "--------------------------------------" >>$here/$s= eq.out.full - cat $tmp.out >>$here/$s= eq.out.full - echo "--------------------------------------" >>$here/$s= eq.out.full - echo "$_n - output from bmap:" >>$here/$s= eq.out.full - echo "--------------------------------------" >>$here/$s= eq.out.full - xfs_bmap -vvv $out >>$here/$s= eq.out.full - echo "--------------------------------------" >>$here/$s= eq.out.full - echo "$_n - output from ls -li:" >>$here/$s= eq.out.full - echo "--------------------------------------" >>$here/$s= eq.out.full - ls -li $out >>$here/$s= eq.out.full - status=3D1 - fi -} - -# real QA test starts here -_supported_fs xfs -_supported_os IRIX Linux - -_setup_testdir - -rm -f $here/$seq.out.full - -# small & fairly dense -_do_test 1 "-l 40960000 -b 40960 -i 10 -c 1" 100 - -# big & sparse -_do_test 2 "-l 409600000 -b 40960 -i 1000 -c 1" 10 - -# no holes, but a very nasty way to write a file (lots of extents) -_do_test 3 "-l 40960000 -b 40960 -i 10 -c 10" 0 - -exit diff --git a/012.out b/012.out deleted file mode 100644 index 6dc7ce8..0000000 --- a/012.out +++ /dev/null @@ -1,16 +0,0 @@ -QA output created by 012 - -holes.1 : -l 40960000 -b 40960 -i 10 -c 1 ------------------------------------------------ - 100 hole(s) detected - filesize =3D 40960000 - -holes.2 : -l 409600000 -b 40960 -i 1000 -c 1 ------------------------------------------------ - 10 hole(s) detected - filesize =3D 409600000 - -holes.3 : -l 40960000 -b 40960 -i 10 -c 10 ------------------------------------------------ - 0 hole(s) detected - filesize =3D 40960000 diff --git a/013 b/013 deleted file mode 100755 index 0879a2a..0000000 --- a/013 +++ /dev/null @@ -1,136 +0,0 @@ -#! /bin/bash -# FS QA Test No. 013 -# -# fsstress -# -#---------------------------------------------------------------------= -- -# Copyright (c) 2000-2002 Silicon Graphics, Inc. All Rights Reserved. -# -# This program is free software; you can redistribute it and/or -# modify it under the terms of the GNU General Public License as -# published by the Free Software Foundation. -# -# This program is distributed in the hope that it would be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program; if not, write the Free Software Foundation, -# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA -# -#---------------------------------------------------------------------= -- -# - -seq=3D`basename $0` -echo "QA output created by $seq" - -here=3D`pwd` -tmp=3D/tmp/$$ -status=3D0=09# success is the default! -trap "_cleanup; exit \$status" 0 1 2 3 15 - -_cleanup() -{ - cd / - # we might get here with a RO FS - mount -o remount,rw $TEST_DEV >/dev/null 2>&1 - # now remove fsstress directory. - # N.B. rm(1) on IRIX can find problems when building up a long pat= hname - # such that what it has is greater the 1024 chars and will - # stop and complain - so get rid of complaint - # Ref. pv#935754 - rm -rf $testdir/fsstress.$$.* 2>&1 | grep -v 'Path too long' - _cleanup_testdir -} - -_filesize() -{ - ls -l $1 | $AWK_PROG '{print " filesize =3D " $5}' -} - -# get standard environment, filters and checks -. ./common.rc -. ./common.filter - -_do_test() -{ - _n=3D"$1" - _param=3D"$2" - _count=3D"$3" - - out=3D$testdir/fsstress.$$.$_n - rm -rf $out - if ! mkdir $out - then - echo " failed to mkdir $out" - status=3D1 - exit - fi - - echo "" - echo "-----------------------------------------------" - echo "fsstress.$_n : $_param" - echo "-----------------------------------------------" - # -m limits number of users/groups so check doesn't fail (malloc) = later - dbgoutfile=3D$seq.full - if ! $FSSTRESS_PROG $_param $FSSTRESS_AVOID -v -m 8 -n $_count -d = $out >>$dbgoutfile 2>&1 - then - echo " fsstress (count=3D$_count) returned $? - see $seq.fu= ll" - echo "--------------------------------------" >>$here/$s= eq.full - echo "$_n - output from fsstress:" >>$here/$s= eq.full - echo "--------------------------------------" >>$here/$s= eq.full - echo "" >>$here/$s= eq.full - #cat $tmp.out >>$here/$s= eq.full - status=3D1 - fi - - _check_test_fs -} - - -# real QA test starts here -_supported_fs generic -_supported_os IRIX Linux - -_setup_testdir - -rm -f $here/$seq.full -echo "brevity is wit..." - -count=3D1000 -procs=3D20 - -_check_test_fs - -# the default - -_do_test 1 "-r" $count - -# and the default with multiprocess - -_do_test 2 "-p $procs -r" $count - -# from Glen's notes - -_do_test 3 "-p 4 -z -f rmdir=3D10 -f link=3D10 -f creat=3D10 -f mkdir= =3D10 -f rename=3D30 -f stat=3D30 -f unlink=3D30 -f truncate=3D20" $cou= nt - -# if all ok by here then probably don't need $seq.full -rm -f $seq.full - -exit - -# Test with error injection: -# -# (error injection) -# fsstress -n 1000 -d $scratch -p 4 -z -f rmdir=3D10 -f link=3D10 -f c= reat=3D10 \ -# -f mkdir=3D10 -f rename=3D30 -f stat=3D30 -f unlink=3D30 -f= truncate=3D20 \ -# -e 1 -# -# Error values 1 - 6 test IFLUSH -# 1 - corrupt buffer being flushed to di_core.di_magic -# 2 - corrupt inode being flushed i_d.di_magic -# 3 - corrupt S_IFREG format check -# 4 - corrupt S_IFDIR format check -# 5 - corrupt i_d.di_nextents -# 6 - corrupt i_d.di_forkoff > sb_inodesize diff --git a/013.out b/013.out deleted file mode 100644 index 127cc86..0000000 --- a/013.out +++ /dev/null @@ -1,14 +0,0 @@ -QA output created by 013 -brevity is wit... - ------------------------------------------------ -fsstress.1 : -r ------------------------------------------------ - ------------------------------------------------ -fsstress.2 : -p 20 -r ------------------------------------------------ - ------------------------------------------------ -fsstress.3 : -p 4 -z -f rmdir=3D10 -f link=3D10 -f creat=3D10 -f mkdir= =3D10 -f rename=3D30 -f stat=3D30 -f unlink=3D30 -f truncate=3D20 ------------------------------------------------ diff --git a/014 b/014 deleted file mode 100755 index 93caaa6..0000000 --- a/014 +++ /dev/null @@ -1,72 +0,0 @@ -#! /bin/bash -# FS QA Test No. 014 -# -# truncfile -# -#---------------------------------------------------------------------= -- -# Copyright (c) 2000-2001 Silicon Graphics, Inc. All Rights Reserved. -# -# This program is free software; you can redistribute it and/or -# modify it under the terms of the GNU General Public License as -# published by the Free Software Foundation. -# -# This program is distributed in the hope that it would be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program; if not, write the Free Software Foundation, -# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA -# -#---------------------------------------------------------------------= -- -# - -seq=3D`basename $0` -echo "QA output created by $seq" - -here=3D`pwd` -tmp=3D/tmp/$$ -status=3D0=09# success is the default! -trap "_cleanup; exit \$status" 0 1 2 3 15 - -_cleanup() -{ - cd / - rm -f $tmp.* - rm -rf $testdir/truncfile.$$.* - _cleanup_testdir -} - -# get standard environment, filters and checks -. ./common.rc -. ./common.filter - -_supported_fs generic -_supported_os IRIX Linux - -_require_sparse_files -_setup_testdir - -# ensure EOF preallocation doesn't massively extend the runtime of thi= s test -# by limiting the amount of preallocation and therefore the amount of = blocks -# zeroed during the truncfile test run. -if [ "$FSTYP" =3D=3D "xfs" ]; then -=09umount $TEST_DIR -=09_test_mount -o allocsize=3D64k -fi - -echo "brevity is wit..." - -echo "------" -echo "test 1" -echo "------" -if ! src/truncfile -c 10000 $testdir/truncfile.$$.0 >$tmp.out 2>&1 -then - out=3D`cat $tmp.out` - echo "truncfile returned $? : \"$out\"" -else - echo "OK" -fi - -exit diff --git a/014.out b/014.out deleted file mode 100644 index fae7d03..0000000 --- a/014.out +++ /dev/null @@ -1,6 +0,0 @@ -QA output created by 014 -brevity is wit... ------- -test 1 ------- -OK diff --git a/015 b/015 deleted file mode 100755 index 62392c6..0000000 --- a/015 +++ /dev/null @@ -1,125 +0,0 @@ -#! /bin/bash -# FS QA Test No. 015 -# -# check out-of-space behaviour -# -#---------------------------------------------------------------------= -- -# Copyright (c) 2000-2002 Silicon Graphics, Inc. All Rights Reserved. -# -# This program is free software; you can redistribute it and/or -# modify it under the terms of the GNU General Public License as -# published by the Free Software Foundation. -# -# This program is distributed in the hope that it would be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program; if not, write the Free Software Foundation, -# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA -# -#---------------------------------------------------------------------= -- -# - -seq=3D`basename $0` -echo "QA output created by $seq" - -here=3D`pwd` -tmp=3D/tmp/$$ -status=3D1=09# success is the default! - -# get standard environment, filters and checks -. ./common.rc -. ./common.filter - -_cleanup() -{ -=09umount $SCRATCH_MNT -} - -trap "_cleanup; exit \$status" 0 1 2 3 15 - -_free() -{ - _df_dir $SCRATCH_MNT | $AWK_PROG '{ print $5 }' -} - -# real QA test starts here -_supported_fs generic -_supported_os IRIX Linux - -_require_scratch -_require_nobigloopfs - -_scratch_mkfs_sized `expr 50 \* 1024 \* 1024` >/dev/null 2>&1 \ - || _fail "mkfs failed" -_scratch_mount || _fail "mount failed" -out=3D$SCRATCH_MNT/fillup.$$ -rm -f $seq.full - -free0=3D`_free` -if [ -z "$free0" ] -then - echo " *** failed to get free space (0)" - exit 1 -fi -echo "free space at start $free0" >> $seq.full - -echo "fill disk:"=09# well, filesystem really - not disk - -POSIXLY_CORRECT=3Dyes dd if=3D/dev/zero of=3D$out bs=3D1024k 2>&1 | _f= ilter_dd - -echo "check free space:" - -free1=3D`_free` -if [ -z "$free1" ] -then - echo " *** failed to get free space (1)" - exit 1 -fi -echo "free space after fill $free1" >> $seq.full - -if [ ! -e $out ] -then - echo " *** file not created" - exit 1 -fi - -if [ ! -s $out ] -then - echo " *** file created with zero length" - ls -l $out - exit 1 -fi - -echo "delete fill:" - -if ! rm $out -then - echo " *** file not deleted" - exit 1 -fi - -if [ -e $out ] -then - echo " *** file still exists" - ls -l $out - exit 1 -fi - -echo "check free space:" - -free2=3D`_free` -if [ -z "$free2" ] -then - echo " *** failed to get free space (2)" - exit 1 -fi -echo "free space after delete $free2" >> $seq.full - -echo -n " !!! " -_within_tolerance "free space" $free2 $free0 1% -v - -status=3D0 -exit diff --git a/015.out b/015.out deleted file mode 100644 index 729287f..0000000 --- a/015.out +++ /dev/null @@ -1,7 +0,0 @@ -QA output created by 015 -fill disk: - !!! disk full (expected) -check free space: -delete fill: -check free space: - !!! free space is in range diff --git a/016 b/016 deleted file mode 100755 index 538ba14..0000000 --- a/016 +++ /dev/null @@ -1,247 +0,0 @@ -#! /bin/bash -# FS QA Test No. 016 -# -# test end of log overwrite bug #796141 -# -#---------------------------------------------------------------------= -- -# Copyright (c) 2000-2003 Silicon Graphics, Inc. All Rights Reserved. -# -# This program is free software; you can redistribute it and/or -# modify it under the terms of the GNU General Public License as -# published by the Free Software Foundation. -# -# This program is distributed in the hope that it would be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program; if not, write the Free Software Foundation, -# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA -# -#---------------------------------------------------------------------= -- -# - -# -# pv 796141 -# -# create a new FS, mostly fill the log. Then wrap the log back to the -# start bit by bit to force wiping of stale blocks near the end of the -# log. Check the block after the log ends to check for corruption -# -# assumptions : -# - given we're only touching a single inode, the block after the -# log which is in the middle ag should never be touched. -# if it changes, we assume the log is writing over it -# - -seq=3D`basename $0` -echo "QA output created by $seq" - -here=3D`pwd` -tmp=3D/tmp/$$ -status=3D1 - -trap "_cleanup; exit \$status" 0 1 2 3 15 - -_cleanup() -{ - cd / - rm -f $tmp.* - echo "*** unmount" - umount $SCRATCH_MNT 2>/dev/null -} - -_block_filter() -{ - sed -e 's/[0-9][0-9]*\.\.[0-9][0-9]*/BLOCKRANGE/g' -} - -_init() -{ - echo "*** reset partition" - $here/src/devzero -b 2048 -n 50 -v 198 $SCRATCH_DEV - echo "*** mkfs" - force_opts=3D"-dsize=3D50m -lsize=3D$log_size" - # - # Do not discard blocks as we check for patterns in free space. - #=20 - # First, make sure that mkfs supports '-K' option by using its - # dry run (-N option) and then add it to the force_opts. - # - if _scratch_mkfs_xfs -N -K $force_opts >/dev/null 2>&1; then - force_opts=3D"-K $force_opts" - fi - echo mkfs_xfs $force_opts $SCRATCH_DEV >>$seq.full - _scratch_mkfs_xfs $force_opts >$tmp.mkfs0 2>&1 - [ $? -ne 0 ] && \ - _notrun "Cannot mkfs for this test using MKFS_OPTIONS specifie= d" - _filter_mkfs <$tmp.mkfs0 >/dev/null 2>$tmp.mkfs - . $tmp.mkfs - [ $logsunit -ne 0 ] && \ - _notrun "Cannot run this test using log MKFS_OPTIONS specified= " -} - -_log_traffic() -{ - count=3D$1 - echo "*** generate log traffic" - - out=3D$SCRATCH_MNT/$$.tmp - - echo " *** mount" - if ! _scratch_mount - then - echo "failed to mount $SCRATCH_DEV" - exit 1 - fi - - # having any quota enabled (acct/enfd) means extra log traffic - e= vil! - $here/src/feature -U $SCRATCH_DEV && \ -=09=09_notrun "UQuota are enabled, test needs controlled log traffic" - $here/src/feature -G $SCRATCH_DEV && \ -=09=09_notrun "GQuota are enabled, test needs controlled log traffic" - $here/src/feature -P $SCRATCH_DEV && \ -=09=09_notrun "PQuota are enabled, test needs controlled log traffic" - - echo " *** fiddle" - while [ $count -ge 0 ] - do -=09touch $out -=09sync -=09rm $out -=09sync -=09let "count =3D count - 1" - done - - echo " *** unmount" - if ! umount $SCRATCH_DEV - then - echo "failed to unmount $SCRATCH_DEV" - exit 1 - fi -} - -_log_size() -{ - _scratch_xfs_logprint -tb | $AWK_PROG ' - /log file: / || /log device: / { print $7} - ' -} - -_log_head() -{ - _scratch_xfs_logprint -tb | $AWK_PROG ' - /head:/ { print $5 } - ' -} - -# Get log stripe unit for v2 logs; if none specified, -# (or v1 log) just return "1" block - -_log_sunit() -{ - if [ ${lsunit:-0} -eq 0 ]; then - echo $dbsize - else - expr $lsunit \* $dbsize - fi -} - -_after_log() -{ - xfs_db -r $1 -c "sb" -c "print" | $AWK_PROG ' - /logstart/ { logstart =3D $3 } - /logblocks/ { logblocks =3D $3 } - END { - print logstart + logblocks - } - ' -} - -_check_corrupt() -{ - f=3D"c6c6c6c6" - echo "*** check for corruption" - echo "expect $f..." >>$seq.full - xfs_db -r -c "fsblock $2" -c "print" $1 | head | tee -a $seq.full = | \ - grep -q -v "$f $f $f $f $f $f $f $f" && \ - _fail "!!! block $2 corrupted!" -} - -# get standard environment, filters and checks -. ./common.rc -. ./common.filter - -# real QA test starts here -_supported_fs xfs -_supported_os Linux - -rm -f $seq.full - -# mkfs sizes -log_size=3D2097152 -log_size_bb=3D`expr $log_size / 512` - -_require_scratch -_init - -block=3D`_after_log $SCRATCH_DEV` -echo "fsblock after log =3D $block" >>$seq.full -_check_corrupt $SCRATCH_DEV $block - -actual_log_size=3D`_log_size` -echo "log size =3D $actual_log_size BB" >>$seq.fu= ll -head=3D`_log_head` -echo "log position =3D $head" >>$seq.full -lsunit=3D`_log_sunit` -echo "log sunit =3D $lsunit"=09=09=09>>$seq.full - -# sanity checks -[ $actual_log_size -eq $log_size_bb ] || \ - _fail "!!! unexpected log size $size" -[ $head -eq 2 -o $head -eq $((lsunit/512)) ] || \ - _fail "!!! unexpected initial log position $head vs. $((lsunit/512= ))" - -# find how how many blocks per op for 100 ops -# ignore the fact that it will also include an unmount record etc... -# this should be small overall -echo " lots of traffic for sampling" >>$seq.full -sample_size_ops=3D100 -_log_traffic $sample_size_ops -head1=3D`_log_head` -num_blocks=3D`expr $head1 - $head` -blocks_per_op=3D`echo "scale=3D3; $num_blocks / $sample_size_ops" | bc= ` -echo "blocks_per_op =3D $blocks_per_op" >>$seq.full -num_expected_ops=3D`echo "$log_size_bb / $blocks_per_op" | bc` -echo "num_expected_ops =3D $num_expected_ops" >>$seq.full -num_expected_to_go=3D`echo "$num_expected_ops - $sample_size_ops" | bc= ` -echo "num_expected_to_go =3D $num_expected_to_go" >>$seq.full - -echo " lots more traffic" >>$seq.full -_log_traffic $num_expected_to_go -head=3D`_log_head` -echo "log position =3D $head" >>$seq.full - -# e.g. 3891 -near_end_min=3D`echo "0.95 * $log_size_bb" | bc | sed 's/\..*//'` -echo "near_end_min =3D $near_end_min" >>$seq.full - -[ $head -gt $near_end_min -a $head -lt $log_size_bb ] || \ - _fail "!!! unexpected near end log position $head" - -for c in `seq 0 20` -do - echo " little traffic" >>$seq.full - _log_traffic 2 - head=3D`_log_head` - echo "log position =3D $head" >>$seq.full - _check_corrupt $SCRATCH_DEV $block -done - -[ $head -lt 1000 ] || \ - _fail "!!! unexpected wrapped log position $head" - -# success, all done -status=3D0 -exit diff --git a/016.out b/016.out deleted file mode 100644 index f7844cd..0000000 --- a/016.out +++ /dev/null @@ -1,119 +0,0 @@ -QA output created by 016 -*** reset partition -Wrote 51200.00Kb (value 0xc6) -*** mkfs -*** check for corruption -*** generate log traffic - *** mount - *** fiddle - *** unmount -*** generate log traffic - *** mount - *** fiddle - *** unmount -*** generate log traffic - *** mount - *** fiddle - *** unmount -*** check for corruption -*** generate log traffic - *** mount - *** fiddle - *** unmount -*** check for corruption -*** generate log traffic - *** mount - *** fiddle - *** unmount -*** check for corruption -*** generate log traffic - *** mount - *** fiddle - *** unmount -*** check for corruption -*** generate log traffic - *** mount - *** fiddle - *** unmount -*** check for corruption -*** generate log traffic - *** mount - *** fiddle - *** unmount -*** check for corruption -*** generate log traffic - *** mount - *** fiddle - *** unmount -*** check for corruption -*** generate log traffic - *** mount - *** fiddle - *** unmount -*** check for corruption -*** generate log traffic - *** mount - *** fiddle - *** unmount -*** check for corruption -*** generate log traffic - *** mount - *** fiddle - *** unmount -*** check for corruption -*** generate log traffic - *** mount - *** fiddle - *** unmount -*** check for corruption -*** generate log traffic - *** mount - *** fiddle - *** unmount -*** check for corruption -*** generate log traffic - *** mount - *** fiddle - *** unmount -*** check for corruption -*** generate log traffic - *** mount - *** fiddle - *** unmount -*** check for corruption -*** generate log traffic - *** mount - *** fiddle - *** unmount -*** check for corruption -*** generate log traffic - *** mount - *** fiddle - *** unmount -*** check for corruption -*** generate log traffic - *** mount - *** fiddle - *** unmount -*** check for corruption -*** generate log traffic - *** mount - *** fiddle - *** unmount -*** check for corruption -*** generate log traffic - *** mount - *** fiddle - *** unmount -*** check for corruption -*** generate log traffic - *** mount - *** fiddle - *** unmount -*** check for corruption -*** generate log traffic - *** mount - *** fiddle - *** unmount -*** check for corruption -*** unmount diff --git a/017 b/017 deleted file mode 100755 index 8609e17..0000000 --- a/017 +++ /dev/null @@ -1,93 +0,0 @@ -#! /bin/bash -# FS QA Test No. 017 -# -# test remount ro - pv 795642 -# -#---------------------------------------------------------------------= -- -# Copyright (c) 2000-2002 Silicon Graphics, Inc. All Rights Reserved. -# -# This program is free software; you can redistribute it and/or -# modify it under the terms of the GNU General Public License as -# published by the Free Software Foundation. -# -# This program is distributed in the hope that it would be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program; if not, write the Free Software Foundation, -# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA -# -#---------------------------------------------------------------------= -- -# - -seq=3D`basename $0` -echo "QA output created by $seq" - -here=3D`pwd` -tmp=3D/tmp/$$ -status=3D1 -trap "_cleanup; rm -f $tmp.*; exit \$status" 0 1 2 3 15 - -_cleanup() -{ - echo "*** unmount" - umount $SCRATCH_MNT 2>/dev/null -} - -# get standard environment, filters and checks -. ./common.rc -. ./common.filter - -# real QA test starts here -_supported_fs xfs -_supported_os Linux - -_require_scratch - -checkopts=3D"" -[ "$USE_BIG_LOOPFS" =3D yes ] && checkopts=3D-t - -echo "*** init FS" - -rm -f $seq.full -umount $SCRATCH_DEV >/dev/null 2>&1 -echo "*** MKFS ***" >>$seq.full -echo "" >>$seq.full -_scratch_mkfs_xfs >>$seq.full 2>&1 \ - || _fail "mkfs failed" -_scratch_mount >>$seq.full 2>&1 \ - || _fail "mount failed" - -echo "*** test" - -for l in 0 1 2 3 4 -do - echo " *** test $l" -=09FSSTRESS_ARGS=3D`_scale_fsstress_args -d $SCRATCH_MNT -n 1000 $FSST= RESS_AVOID` - $FSSTRESS_PROG $FSSTRESS_ARGS >>$seq.full - - _scratch_mount -o remount,ro \ - || _fail "remount ro failed" - - echo "" >>$seq.full - echo "*** xfs_logprint ***" >>$seq.full - echo "" >>$seq.full - _scratch_xfs_logprint -tb | tee -a $seq.full \ - | head | grep -q "" || _fail "DIRTY LOG" - - echo "" >>$seq.full - echo "*** XFS_CHECK ***" >>$seq.full - echo "" >>$seq.full - _scratch_xfs_check $checkopts >>$seq.full 2>&1 \ - || _fail "xfs_check $checkopts failed" - _scratch_mount -o remount,rw \ - || _fail "remount rw failed" -done - -echo "*** done" -# happy exit -rm -f $seq.full -status=3D0 -exit 0 diff --git a/017.out b/017.out deleted file mode 100644 index 2d11c94..0000000 --- a/017.out +++ /dev/null @@ -1,10 +0,0 @@ -QA output created by 017 -*** init FS -*** test - *** test 0 - *** test 1 - *** test 2 - *** test 3 - *** test 4 -*** done -*** unmount diff --git a/018 b/018 deleted file mode 100755 index 156cc1d..0000000 --- a/018 +++ /dev/null @@ -1,102 +0,0 @@ -#! /bin/bash -# FS QA Test No. 018 -# -# xfs_logprint test - test v2 logs of different LR sizes -# -#---------------------------------------------------------------------= -- -# Copyright (c) 2000-2002 Silicon Graphics, Inc. All Rights Reserved. -# -# This program is free software; you can redistribute it and/or -# modify it under the terms of the GNU General Public License as -# published by the Free Software Foundation. -# -# This program is distributed in the hope that it would be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program; if not, write the Free Software Foundation, -# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA -# -#---------------------------------------------------------------------= -- -# - -seq=3D`basename $0` -echo "QA output created by $seq" - -here=3D`pwd` -tmp=3D/tmp/$$ -status=3D1=09# failure is the default! - -# get standard environment, filters and checks -. ./common.rc -. ./common.filter -. ./common.log - -_cleanup() -{ - cd / - _cleanup_logfiles - rm -f $tmp.* - umount $SCRATCH_MNT 2>/dev/null -} -trap "_cleanup; exit \$status" 0 1 2 3 15 - -# real QA test starts here -_supported_fs xfs -_supported_os IRIX Linux -# prelim -rm -f $seq.full $tmp.* -_require_scratch -_require_v2log - -# link correct .out file -_link_out_file $seq.op - - -echo "*** init FS" -umount $SCRATCH_DEV >/dev/null 2>&1 - -cat >$tmp.seq.params < - log device: daddr: length: -Oper (OPNUM): tid: len: clientid: TRANS flags: START -Oper (OPNUM): tid: len: clientid: TRANS flags: none -TRAN: type: CREATE (0x4) tid: num_items: 5 -Oper (OPNUM): tid: len: clientid: TRANS flags: none -BUF: #regs:R start blkno: () len: bmap size: 1 -Oper (OPNUM): tid: len: clientid: TRANS flags: none -AGI Buffer: XAGI -ver: 1 seq#: 0 len: cnt: 64 root: 3 -level: 1 free#: 0x3c newino: -bucket[0 - 3]: 0xffffffff 0xffffffff 0xffffffff 0xffffffff -bucket[4 - 7]: 0xffffffff 0xffffffff 0xffffffff 0xffffffff -bucket[8 - 11]: 0xffffffff 0xffffffff 0xffffffff 0xffffffff -bucket[12 - 15]: 0xffffffff 0xffffffff 0xffffffff 0xffffffff -bucket[16 - 19]: 0xffffffff -Oper (OPNUM): tid: len: clientid: TRANS flags: none -BUF: #regs:R start blkno: () len: bmap size: 2 -Oper (OPNUM): tid: len: clientid: TRANS flags: none -BUF DATA -Oper (OPNUM): tid: len: clientid: TRANS flags: none -INODE: #regs:R ino: flags: 0x1 dsize: 0 - blkno: len: boff: -Oper (OPNUM): tid: len: clientid: TRANS flags: none -INODE CORE -magic 0x494e mode 0100644 version 1 format 2 -nlink 1 uid 0 gid 0 -atime