From 3f2a0b75c01df7ea144fe1a1149ea03ec6daf433 Mon Sep 17 00:00:00 2001 From: Vlad Yasevich Date: Mon, 25 Aug 2008 15:16:19 -0700 Subject: [PATCH] --- yaml --- r: 109118 b: refs/heads/master c: 30c2235cbc477d4629983d440cdc4f496fec9246 h: refs/heads/master v: v3 --- [refs] | 2 +- trunk/Documentation/filesystems/ext4.txt | 6 - trunk/Documentation/ja_JP/HOWTO | 67 +- trunk/Documentation/ja_JP/SubmitChecklist | 111 --- trunk/Documentation/kernel-parameters.txt | 3 - trunk/Documentation/lguest/lguest.c | 8 - trunk/arch/arm/mach-integrator/impd1.c | 2 +- trunk/arch/arm/mach-ixp4xx/fsg-setup.c | 4 +- trunk/arch/arm/mach-pxa/clock.c | 25 - trunk/arch/arm/mach-pxa/clock.h | 5 - trunk/arch/arm/mach-pxa/eseries.c | 170 ++-- trunk/arch/arm/mach-pxa/include/mach/irqs.h | 1 - trunk/arch/arm/mach-pxa/lubbock.c | 2 - trunk/arch/arm/mach-pxa/pxa25x.c | 10 +- trunk/arch/arm/mach-pxa/pxa300.c | 2 - trunk/arch/arm/plat-omap/clock.c | 1 + trunk/arch/cris/arch-v32/kernel/fasttimer.c | 2 + trunk/arch/mn10300/kernel/mn10300-serial.c | 1 + trunk/arch/powerpc/sysdev/bestcomm/gen_bd.c | 1 + trunk/arch/s390/defconfig | 54 +- trunk/arch/s390/include/asm/bitops.h | 6 +- trunk/arch/s390/kernel/process.c | 4 +- trunk/arch/s390/kernel/smp.c | 2 + trunk/arch/x86/Kconfig | 30 +- trunk/arch/x86/kernel/amd_iommu.c | 2 +- .../x86/kernel/cpu/addon_cpuid_features.c | 17 +- trunk/arch/x86/kernel/cpu/cyrix.c | 18 + trunk/arch/x86/kernel/cpu/mcheck/mce_64.c | 5 - trunk/arch/x86/kernel/cpu/mcheck/mce_amd_64.c | 18 +- trunk/arch/x86/kernel/cpu/mtrr/generic.c | 20 +- trunk/arch/x86/kernel/cpu/mtrr/main.c | 5 +- trunk/arch/x86/kernel/genx2apic_uv_x.c | 8 +- trunk/arch/x86/kernel/numaq_32.c | 2 +- trunk/arch/x86/kernel/paravirt.c | 2 +- trunk/arch/x86/kernel/pci-calgary_64.c | 14 +- trunk/arch/x86/kernel/setup.c | 16 +- trunk/arch/x86/kernel/smpboot.c | 3 - trunk/arch/x86/kernel/tlb_uv.c | 3 +- trunk/arch/x86/kernel/tsc.c | 6 +- trunk/arch/x86/kernel/tsc_sync.c | 6 +- trunk/arch/x86/kvm/paging_tmpl.h | 2 +- trunk/arch/x86/mach-rdc321x/platform.c | 1 + trunk/arch/x86/mm/init_64.c | 36 +- trunk/arch/x86/mm/ioremap.c | 8 +- trunk/arch/x86/mm/mmio-mod.c | 4 +- trunk/arch/x86/mm/pageattr.c | 6 +- trunk/arch/x86/mm/pat.c | 50 +- trunk/arch/x86/oprofile/nmi_int.c | 39 +- trunk/arch/x86/pci/amd_bus.c | 52 +- trunk/arch/x86/pci/i386.c | 78 -- trunk/block/genhd.c | 36 +- trunk/crypto/authenc.c | 10 +- trunk/drivers/ata/ahci.c | 8 +- trunk/drivers/ata/ata_piix.c | 8 - trunk/drivers/ata/libata-core.c | 60 +- trunk/drivers/ata/libata-eh.c | 30 +- trunk/drivers/ata/pata_acpi.c | 2 +- trunk/drivers/ata/pata_atiixp.c | 2 +- trunk/drivers/ata/pata_cs5530.c | 6 +- trunk/drivers/ata/pata_it821x.c | 2 +- trunk/drivers/ata/pata_oldpiix.c | 2 +- trunk/drivers/ata/pata_sc1200.c | 6 +- trunk/drivers/ata/pata_via.c | 59 +- trunk/drivers/ata/sata_mv.c | 37 +- trunk/drivers/atm/adummy.c | 1 + trunk/drivers/base/class.c | 11 - trunk/drivers/base/core.c | 31 +- trunk/drivers/base/driver.c | 3 + trunk/drivers/base/power/main.c | 19 +- trunk/drivers/base/power/power.h | 9 +- .../drivers/char/xilinx_hwicap/buffer_icap.h | 1 + trunk/drivers/char/xilinx_hwicap/fifo_icap.h | 1 + .../char/xilinx_hwicap/xilinx_hwicap.h | 1 + trunk/drivers/edac/edac_core.h | 1 + trunk/drivers/i2c/busses/i2c-at91.c | 1 + trunk/drivers/infiniband/hw/ehca/ehca_tools.h | 1 + trunk/drivers/infiniband/hw/ipath/ipath_fs.c | 1 + .../infiniband/hw/ipath/ipath_iba7220.c | 2 +- trunk/drivers/infiniband/hw/ipath/ipath_ud.c | 8 +- trunk/drivers/infiniband/hw/nes/nes.h | 1 + .../drivers/infiniband/ulp/ipoib/ipoib_main.c | 19 +- .../infiniband/ulp/ipoib/ipoib_multicast.c | 10 +- .../drivers/infiniband/ulp/iser/iser_verbs.c | 1 + trunk/drivers/input/keyboard/bf54x-keys.c | 1 + .../input/touchscreen/mainstone-wm97xx.c | 1 + trunk/drivers/lguest/lguest_device.c | 8 - trunk/drivers/mfd/asic3.c | 1 + trunk/drivers/misc/acer-wmi.c | 5 - trunk/drivers/misc/eeprom_93cx6.c | 1 + trunk/drivers/mtd/maps/amd76xrom.c | 1 + trunk/drivers/mtd/maps/ck804xrom.c | 1 + trunk/drivers/mtd/maps/esb2rom.c | 1 + trunk/drivers/mtd/nand/au1550nd.c | 1 + trunk/drivers/net/myri10ge/myri10ge.c | 1 + trunk/drivers/net/netxen/netxen_nic.h | 1 + trunk/drivers/net/netxen/netxen_nic_ethtool.c | 1 + trunk/drivers/net/netxen/netxen_nic_hdr.h | 2 + trunk/drivers/net/tokenring/lanstreamer.c | 1 + trunk/drivers/net/tokenring/lanstreamer.h | 2 + trunk/drivers/net/wireless/b43legacy/main.c | 1 + .../net/wireless/iwlwifi/iwl-3945-led.c | 1 + trunk/drivers/net/wireless/iwlwifi/iwl-led.c | 1 + .../drivers/net/wireless/iwlwifi/iwl-rfkill.c | 1 + trunk/drivers/pci/hotplug/pciehp.h | 1 + trunk/drivers/pci/hotplug/pciehp_core.c | 21 +- trunk/drivers/pci/hotplug/pciehp_hpc.c | 11 +- trunk/drivers/pci/hotplug/shpchp_core.c | 34 +- trunk/drivers/pci/search.c | 2 - trunk/drivers/rtc/rtc-max6902.c | 2 + trunk/drivers/rtc/rtc-r9701.c | 1 + trunk/drivers/s390/block/dasd.c | 5 +- trunk/drivers/s390/block/dasd_eckd.h | 2 +- trunk/drivers/s390/block/dasd_eer.c | 3 +- trunk/drivers/s390/block/dcssblk.c | 4 - trunk/drivers/s390/char/tape_char.c | 2 +- trunk/drivers/s390/char/tape_std.c | 2 +- trunk/drivers/s390/cio/ccwgroup.c | 20 +- trunk/drivers/s390/cio/css.c | 1 + trunk/drivers/s390/cio/device.c | 40 +- trunk/drivers/s390/cio/device.h | 2 +- trunk/drivers/s390/cio/device_fsm.c | 31 +- trunk/drivers/s390/cio/qdio_debug.h | 6 +- trunk/drivers/s390/cio/qdio_main.c | 74 +- trunk/drivers/s390/cio/qdio_setup.c | 6 +- trunk/drivers/s390/cio/qdio_thinint.c | 6 +- trunk/drivers/s390/net/ctcm_mpc.c | 1 + trunk/drivers/scsi/dpt/dpti_i2o.h | 1 + trunk/drivers/scsi/ips.c | 1 + trunk/drivers/scsi/ips.h | 1 + trunk/drivers/scsi/lpfc/lpfc_debugfs.c | 1 + trunk/drivers/scsi/nsp32.c | 1 + trunk/drivers/scsi/nsp32.h | 1 + trunk/drivers/scsi/pcmcia/nsp_cs.c | 1 + trunk/drivers/scsi/qla2xxx/qla_mid.c | 1 + trunk/drivers/uio/Kconfig | 13 - trunk/drivers/uio/Makefile | 1 - trunk/drivers/uio/uio_pdrv.c | 4 +- trunk/drivers/uio/uio_pdrv_genirq.c | 188 ---- trunk/drivers/usb/atm/ueagle-atm.c | 1 + trunk/drivers/usb/class/cdc-acm.c | 5 +- trunk/drivers/usb/core/driver.c | 96 +- trunk/drivers/usb/core/hcd.c | 9 + trunk/drivers/usb/core/hcd.h | 4 + trunk/drivers/usb/core/hub.c | 9 + trunk/drivers/usb/core/urb.c | 9 +- trunk/drivers/usb/core/usb.c | 73 +- trunk/drivers/usb/core/usb.h | 3 - trunk/drivers/usb/gadget/amd5536udc.c | 1 + trunk/drivers/usb/gadget/pxa27x_udc.c | 2 +- trunk/drivers/usb/gadget/s3c2410_udc.c | 1 + trunk/drivers/usb/host/isp1760-hcd.c | 2 +- trunk/drivers/usb/host/ohci-at91.c | 1 + trunk/drivers/usb/host/ohci-au1xxx.c | 1 + trunk/drivers/usb/host/ohci-ep93xx.c | 1 + trunk/drivers/usb/host/ohci-hub.c | 53 +- trunk/drivers/usb/host/ohci-lh7a404.c | 1 + trunk/drivers/usb/host/ohci-omap.c | 1 + trunk/drivers/usb/host/ohci-pci.c | 1 + trunk/drivers/usb/host/ohci-pnx4008.c | 1 + trunk/drivers/usb/host/ohci-pnx8550.c | 1 + trunk/drivers/usb/host/ohci-ppc-of.c | 1 + trunk/drivers/usb/host/ohci-ppc-soc.c | 1 + trunk/drivers/usb/host/ohci-ps3.c | 1 + trunk/drivers/usb/host/ohci-pxa27x.c | 1 + trunk/drivers/usb/host/ohci-s3c2410.c | 1 + trunk/drivers/usb/host/ohci-sa1111.c | 1 + trunk/drivers/usb/host/ohci-sh.c | 1 + trunk/drivers/usb/host/ohci-sm501.c | 1 + trunk/drivers/usb/host/ohci-ssb.c | 1 + trunk/drivers/usb/host/u132-hcd.c | 11 + trunk/drivers/usb/misc/iowarrior.c | 1 + trunk/drivers/usb/misc/sisusbvga/sisusb.c | 1 - trunk/drivers/usb/musb/Kconfig | 13 +- trunk/drivers/usb/musb/Makefile | 21 +- trunk/drivers/usb/musb/musb_core.c | 38 +- trunk/drivers/usb/musb/musb_core.h | 19 + trunk/drivers/usb/musb/musb_debug.h | 4 + trunk/drivers/usb/musb/musb_gadget_ep0.c | 2 - trunk/drivers/usb/musb/musb_procfs.c | 830 ++++++++++++++++++ trunk/drivers/usb/serial/garmin_gps.c | 2 + trunk/drivers/usb/serial/option.c | 2 - trunk/drivers/video/arkfb.c | 1 + trunk/drivers/video/s3fb.c | 1 + trunk/drivers/video/vermilion/vermilion.h | 1 + trunk/drivers/video/vt8623fb.c | 1 + trunk/drivers/video/xilinxfb.c | 1 + trunk/drivers/virtio/virtio_balloon.c | 2 +- trunk/drivers/xen/manage.c | 2 +- trunk/fs/ext4/balloc.c | 3 - trunk/fs/ext4/dir.c | 20 +- trunk/fs/ext4/ext4.h | 4 - trunk/fs/ext4/ext4_extents.h | 4 +- trunk/fs/ext4/ext4_jbd2.h | 8 - trunk/fs/ext4/extents.c | 113 ++- trunk/fs/ext4/ialloc.c | 2 +- trunk/fs/ext4/inode.c | 478 ++++------ trunk/fs/ext4/mballoc.c | 53 +- trunk/fs/ext4/migrate.c | 3 +- trunk/fs/ext4/resize.c | 3 +- trunk/fs/ext4/super.c | 1 - trunk/fs/jffs2/jffs2_fs_i.h | 1 + trunk/fs/xfs/xfs_dmapi.h | 1 + trunk/include/asm-generic/rtc.h | 12 +- trunk/include/asm-x86/cpufeature.h | 2 - trunk/include/asm-x86/genapic_32.h | 1 - trunk/include/asm-x86/genapic_64.h | 1 - trunk/include/asm-x86/irq_vectors.h | 1 - trunk/include/asm-x86/kvm_host.h | 2 +- trunk/include/asm-x86/mce.h | 1 - trunk/include/asm-x86/uv/uv_bau.h | 5 + trunk/include/asm-x86/xen/hypervisor.h | 1 + trunk/include/linux/device.h | 5 +- trunk/include/linux/fs_uart_pd.h | 1 + trunk/include/linux/kvm.h | 4 +- trunk/include/linux/libata.h | 24 - trunk/include/linux/stop_machine.h | 19 +- trunk/include/linux/tick.h | 5 +- trunk/include/linux/usb.h | 3 - trunk/kernel/module.c | 2 +- trunk/kernel/nsproxy.c | 1 + trunk/kernel/power/swap.c | 1 + trunk/kernel/rcupdate.c | 1 - trunk/kernel/sched_clock.c | 84 +- trunk/kernel/sched_features.h | 2 +- trunk/kernel/time/tick-sched.c | 6 +- trunk/kernel/user_namespace.c | 1 + trunk/kernel/utsname.c | 1 + trunk/kernel/utsname_sysctl.c | 1 + trunk/lib/kobject.c | 3 +- trunk/net/sctp/auth.c | 4 + trunk/net/sctp/socket.c | 5 + trunk/scripts/mod/file2alias.c | 16 +- trunk/sound/mips/au1x00.c | 1 + trunk/sound/pci/ca0106/ca0106_main.c | 5 +- trunk/sound/pci/hda/hda_intel.c | 9 - trunk/sound/pci/hda/patch_realtek.c | 6 +- trunk/sound/soc/at91/eti_b1_wm8731.c | 1 + trunk/sound/soc/codecs/ak4535.c | 11 +- trunk/sound/soc/codecs/tlv320aic3x.c | 11 +- trunk/sound/soc/codecs/uda1380.c | 9 +- trunk/sound/soc/codecs/wm8510.c | 9 +- trunk/sound/soc/codecs/wm8731.c | 11 +- trunk/sound/soc/codecs/wm8750.c | 10 +- trunk/sound/soc/codecs/wm8753.c | 12 +- trunk/sound/soc/codecs/wm8990.c | 11 +- trunk/sound/soc/codecs/wm9712.c | 1 + 246 files changed, 2049 insertions(+), 2059 deletions(-) delete mode 100644 trunk/Documentation/ja_JP/SubmitChecklist delete mode 100644 trunk/drivers/uio/uio_pdrv_genirq.c create mode 100644 trunk/drivers/usb/musb/musb_procfs.c diff --git a/[refs] b/[refs] index d9087c11eaf9..e00a575c1e06 100644 --- a/[refs] +++ b/[refs] @@ -1,2 +1,2 @@ --- -refs/heads/master: e5778ec91e823b97262f045814d34d0abde689c0 +refs/heads/master: 30c2235cbc477d4629983d440cdc4f496fec9246 diff --git a/trunk/Documentation/filesystems/ext4.txt b/trunk/Documentation/filesystems/ext4.txt index 0d5394920a31..80e193d82e2e 100644 --- a/trunk/Documentation/filesystems/ext4.txt +++ b/trunk/Documentation/filesystems/ext4.txt @@ -26,12 +26,6 @@ Mailing list: linux-ext4@vger.kernel.org git://git.kernel.org/pub/scm/fs/ext2/e2fsprogs.git - - Note that it is highly important to install the mke2fs.conf file - that comes with the e2fsprogs 1.41.x sources in /etc/mke2fs.conf. If - you have edited the /etc/mke2fs.conf file installed on your system, - you will need to merge your changes with the version from e2fsprogs - 1.41.x. - - Create a new filesystem using the ext4dev filesystem type: # mke2fs -t ext4dev /dev/hda1 diff --git a/trunk/Documentation/ja_JP/HOWTO b/trunk/Documentation/ja_JP/HOWTO index 0775cf4798b2..488c77fa3aae 100644 --- a/trunk/Documentation/ja_JP/HOWTO +++ b/trunk/Documentation/ja_JP/HOWTO @@ -11,14 +11,14 @@ for non English (read: Japanese) speakers and is not intended as a fork. So if you have any comments or updates for this file, please try to update the original English file first. -Last Updated: 2008/08/21 +Last Updated: 2007/11/16 ================================== これは、 -linux-2.6.27/Documentation/HOWTO +linux-2.6.24/Documentation/HOWTO の和訳です。 翻訳団体: JF プロジェクト < http://www.linux.or.jp/JF/ > -翻訳日: 2008/8/5 +翻訳日: 2007/11/10 翻訳者: Tsugikazu Shibata 校正者: 松倉さん 小林 雅典さん (Masanori Kobayasi) @@ -287,15 +287,13 @@ Linux カーネルの開発プロセスは現在幾つかの異なるメイン に安定した状態にあると判断したときにリリースされます。目標は毎週新 しい -rc カーネルをリリースすることです。 + - 以下の URL で各 -rc リリースに存在する既知の後戻り問題のリスト + が追跡されます- + http://kernelnewbies.org/known_regressions + - このプロセスはカーネルが 「準備ができた」と考えられるまで継続しま す。このプロセスはだいたい 6週間継続します。 - - 各リリースでの既知の後戻り問題(regression: このリリースの中で新規 - に作り込まれた問題を指す) はその都度 Linux-kernel メーリングリスト - に投稿されます。ゴールとしては、カーネルが 「準備ができた」と宣言 - する前にこのリストの長さをゼロに減らすことですが、現実には、数個の - 後戻り問題がリリース時にたびたび残ってしまいます。 - Andrew Morton が Linux-kernel メーリングリストにカーネルリリースについ て書いたことをここで言っておくことは価値があります- 「カーネルがいつリリースされるかは誰も知りません。なぜなら、これは現 @@ -305,20 +303,18 @@ Andrew Morton が Linux-kernel メーリングリストにカーネルリリー 2.6.x.y -stable カーネルツリー --------------------------- -バージョン番号が4つの数字に分かれているカーネルは -stable カーネルです。 -これには、2.6.x カーネルで見つかったセキュリティ問題や重大な後戻りに対 -する比較的小さい重要な修正が含まれます。 +バージョンに4つ目の数字がついたカーネルは -stable カーネルです。これに +は、2.6.x カーネルで見つかったセキュリティ問題や重大な後戻りに対する比 +較的小さい重要な修正が含まれます。 これは、開発/実験的バージョンのテストに協力することに興味が無く、 最新の安定したカーネルを使いたいユーザに推奨するブランチです。 -もし、2.6.x.y カーネルが存在しない場合には、番号が一番大きい 2.6.x が -最新の安定版カーネルです。 +もし、2.6.x.y カーネルが存在しない場合には、番号が一番大きい 2.6.x +が最新の安定版カーネルです。 -2.6.x.y は "stable" チーム でメンテされており、必 -要に応じてリリースされます。通常のリリース期間は 2週間毎ですが、差し迫っ -た問題がなければもう少し長くなることもあります。セキュリティ関連の問題 -の場合はこれに対してだいたいの場合、すぐにリリースがされます。 +2.6.x.y は "stable" チーム でメンテされており、だ +いたい隔週でリリースされています。 カーネルツリーに入っている、Documentation/stable_kernel_rules.txt ファ イルにはどのような種類の変更が -stable ツリーに受け入れ可能か、またリ @@ -345,9 +341,7 @@ linux-kernel メーリングリストで収集された多数のパッチと同 メインラインへ入れるように Linus にプッシュします。 メインカーネルツリーに含めるために Linus に送る前に、すべての新しいパッ -チが -mm ツリーでテストされることが強く推奨されています。マージウィン -ドウが開く前に -mm ツリーに現れなかったパッチはメインラインにマージさ -れることは困難になります。 +チが -mm ツリーでテストされることが強く推奨されます。 これらのカーネルは安定して動作すべきシステムとして使うのには適切ではあ りませんし、カーネルブランチの中でももっとも動作にリスクが高いものです。 @@ -401,15 +395,13 @@ linux-kernel メーリングリストで収集された多数のパッチと同 - pcmcia, Dominik Brodowski git.kernel.org:/pub/scm/linux/kernel/git/brodo/pcmcia-2.6.git - - SCSI, James Bottomley + - SCSI, James Bottomley git.kernel.org:/pub/scm/linux/kernel/git/jejb/scsi-misc-2.6.git - - x86, Ingo Molnar - git://git.kernel.org/pub/scm/linux/kernel/git/x86/linux-2.6-x86.git - quilt ツリー- - - USB, ドライバコアと I2C, Greg Kroah-Hartman + - USB, PCI ドライバコアと I2C, Greg Kroah-Hartman kernel.org/pub/linux/kernel/people/gregkh/gregkh-2.6/ + - x86-64 と i386 の仲間 Andi Kleen その他のカーネルツリーは http://git.kernel.org/ と MAINTAINERS ファ イルに一覧表があります。 @@ -420,32 +412,13 @@ linux-kernel メーリングリストで収集された多数のパッチと同 bugzilla.kernel.org は Linux カーネル開発者がカーネルのバグを追跡する 場所です。ユーザは見つけたバグの全てをこのツールで報告すべきです。 どう kernel bugzilla を使うかの詳細は、以下を参照してください- - http://bugzilla.kernel.org/page.cgi?id=faq.html + http://test.kernel.org/bugzilla/faq.html + メインカーネルソースディレクトリにあるファイル REPORTING-BUGS はカーネ ルバグらしいものについてどうレポートするかの良いテンプレートであり、問 題の追跡を助けるためにカーネル開発者にとってどんな情報が必要なのかの詳 細が書かれています。 -バグレポートの管理 -------------------- - -あなたのハッキングのスキルを訓練する最高の方法のひとつに、他人がレポー -トしたバグを修正することがあります。あなたがカーネルをより安定化させる -こに寄与するということだけでなく、あなたは 現実の問題を修正することを -学び、自分のスキルも強化でき、また他の開発者があなたの存在に気がつき -ます。バグを修正することは、多くの開発者の中から自分が功績をあげる最善 -の道です、なぜなら多くの人は他人のバグの修正に時間を浪費することを好ま -ないからです。 - -すでにレポートされたバグのために仕事をするためには、 -http://bugzilla.kernel.org に行ってください。もし今後のバグレポートに -ついてアドバイスを受けたいのであれば、bugme-new メーリングリスト(新し -いバグレポートだけがここにメールされる) または bugme-janitor メーリン -グリスト(bugzilla の変更毎にここにメールされる)を購読できます。 - - http://lists.linux-foundation.org/mailman/listinfo/bugme-new - http://lists.linux-foundation.org/mailman/listinfo/bugme-janitors - メーリングリスト ------------- diff --git a/trunk/Documentation/ja_JP/SubmitChecklist b/trunk/Documentation/ja_JP/SubmitChecklist deleted file mode 100644 index 6c42e071d723..000000000000 --- a/trunk/Documentation/ja_JP/SubmitChecklist +++ /dev/null @@ -1,111 +0,0 @@ -NOTE: -This is a version of Documentation/SubmitChecklist into Japanese. -This document is maintained by Takenori Nagano -and the JF Project team . -If you find any difference between this document and the original file -or a problem with the translation, -please contact the maintainer of this file or JF project. - -Please also note that the purpose of this file is to be easier to read -for non English (read: Japanese) speakers and is not intended as a -fork. So if you have any comments or updates of this file, please try -to update the original English file first. - -Last Updated: 2008/07/14 -================================== -これは、 -linux-2.6.26/Documentation/SubmitChecklist の和訳です。 - -翻訳団体: JF プロジェクト < http://www.linux.or.jp/JF/ > -翻訳日: 2008/07/14 -翻訳者: Takenori Nagano -校正者: Masanori Kobayashi さん -================================== - - -Linux カーネルパッチ投稿者向けチェックリスト -~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ - -本書では、パッチをより素早く取り込んでもらいたい開発者が実践すべき基本的な事柄 -をいくつか紹介します。ここにある全ての事柄は、Documentation/SubmittingPatches -などのLinuxカーネルパッチ投稿に際しての心得を補足するものです。 - - 1: 妥当なCONFIGオプションや変更されたCONFIGオプション、つまり =y, =m, =n - 全てで正しくビルドできることを確認してください。その際、gcc及びリンカが - warningやerrorを出していないことも確認してください。 - - 2: allnoconfig, allmodconfig オプションを用いて正しくビルドできることを - 確認してください。 - - 3: 手許のクロスコンパイルツールやOSDLのPLMのようなものを用いて、複数の - アーキテクチャにおいても正しくビルドできることを確認してください。 - - 4: 64bit長の'unsigned long'を使用しているppc64は、クロスコンパイルでの - チェックに適当なアーキテクチャです。 - - 5: カーネルコーディングスタイルに準拠しているかどうか確認してください(!) - - 6: CONFIGオプションの追加・変更をした場合には、CONFIGメニューが壊れていない - ことを確認してください。 - - 7: 新しくKconfigのオプションを追加する際には、必ずそのhelpも記述してください。 - - 8: 適切なKconfigの依存関係を考えながら慎重にチェックしてください。 - ただし、この作業はマシンを使ったテストできちんと行うのがとても困難です。 - うまくやるには、自分の頭で考えることです。 - - 9: sparseを利用してちゃんとしたコードチェックをしてください。 - -10: 'make checkstack' と 'make namespacecheck' を利用し、問題が発見されたら - 修正してください。'make checkstack' は明示的に問題を示しませんが、どれか - 1つの関数が512バイトより大きいスタックを使っていれば、修正すべき候補と - なります。 - -11: グローバルなkernel API を説明する kernel-doc をソースの中に含めてください。 - ( staticな関数においては必須ではありませんが、含めてもらっても結構です ) - そして、'make htmldocs' もしくは 'make mandocs' を利用して追記した - ドキュメントのチェックを行い、問題が見つかった場合には修正を行ってください。 - -12: CONFIG_PREEMPT, CONFIG_DEBUG_PREEMPT, CONFIG_DEBUG_SLAB, - CONFIG_DEBUG_PAGEALLOC, CONFIG_DEBUG_MUTEXES, CONFIG_DEBUG_SPINLOCK, - CONFIG_DEBUG_SPINLOCK_SLEEP これら全てを同時に有効にして動作確認を - 行ってください。 - -13: CONFIG_SMP, CONFIG_PREEMPT を有効にした場合と無効にした場合の両方で - ビルドした上、動作確認を行ってください。 - -14: もしパッチがディスクのI/O性能などに影響を与えるようであれば、 - 'CONFIG_LBD'オプションを有効にした場合と無効にした場合の両方で - テストを実施してみてください。 - -15: lockdepの機能を全て有効にした上で、全てのコードパスを評価してください。 - -16: /proc に新しいエントリを追加した場合には、Documentation/ 配下に - 必ずドキュメントを追加してください。 - -17: 新しいブートパラメータを追加した場合には、 - 必ずDocumentation/kernel-parameters.txt に説明を追加してください。 - -18: 新しくmoduleにパラメータを追加した場合には、MODULE_PARM_DESC()を - 利用して必ずその説明を記述してください。 - -19: 新しいuserspaceインタフェースを作成した場合には、Documentation/ABI/ に - Documentation/ABI/README を参考にして必ずドキュメントを追加してください。 - -20: 'make headers_check'を実行して全く問題がないことを確認してください。 - -21: 少なくともslabアロケーションとpageアロケーションに失敗した場合の - 挙動について、fault-injectionを利用して確認してください。 - Documentation/fault-injection/ を参照してください。 - - 追加したコードがかなりの量であったならば、サブシステム特有の - fault-injectionを追加したほうが良いかもしれません。 - -22: 新たに追加したコードは、`gcc -W'でコンパイルしてください。 - このオプションは大量の不要なメッセージを出力しますが、 - "warning: comparison between signed and unsigned" のようなメッセージは、 - バグを見つけるのに役に立ちます。 - -23: 投稿したパッチが -mm パッチセットにマージされた後、全ての既存のパッチや - VM, VFS およびその他のサブシステムに関する様々な変更と、現時点でも共存 - できることを確認するテストを行ってください。 diff --git a/trunk/Documentation/kernel-parameters.txt b/trunk/Documentation/kernel-parameters.txt index 1150444a21ab..a8976467a983 100644 --- a/trunk/Documentation/kernel-parameters.txt +++ b/trunk/Documentation/kernel-parameters.txt @@ -1074,9 +1074,6 @@ and is between 256 and 4096 characters. It is defined in the file * [no]ncq: Turn on or off NCQ. - * nohrst, nosrst, norst: suppress hard, soft - and both resets. - If there are multiple matching configurations changing the same attribute, the last one is used. diff --git a/trunk/Documentation/lguest/lguest.c b/trunk/Documentation/lguest/lguest.c index 7228369d1014..655414821edc 100644 --- a/trunk/Documentation/lguest/lguest.c +++ b/trunk/Documentation/lguest/lguest.c @@ -895,9 +895,6 @@ static void handle_console_output(int fd, struct virtqueue *vq, bool timeout) } } -/* This is called when we no longer want to hear about Guest changes to a - * virtqueue. This is more efficient in high-traffic cases, but it means we - * have to set a timer to check if any more changes have occurred. */ static void block_vq(struct virtqueue *vq) { struct itimerval itm; @@ -942,11 +939,6 @@ static void handle_net_output(int fd, struct virtqueue *vq, bool timeout) if (!timeout && num) block_vq(vq); - /* We never quite know how long should we wait before we check the - * queue again for more packets. We start at 500 microseconds, and if - * we get fewer packets than last time, we assume we made the timeout - * too small and increase it by 10 microseconds. Otherwise, we drop it - * by one microsecond every time. It seems to work well enough. */ if (timeout) { if (num < last_timeout_num) timeout_usec += 10; diff --git a/trunk/arch/arm/mach-integrator/impd1.c b/trunk/arch/arm/mach-integrator/impd1.c index 3c8383dbe9e6..0a7b3267c8d8 100644 --- a/trunk/arch/arm/mach-integrator/impd1.c +++ b/trunk/arch/arm/mach-integrator/impd1.c @@ -405,7 +405,7 @@ static int impd1_probe(struct lm_device *dev) ret = amba_device_register(d, &dev->resource); if (ret) { - dev_err(&d->dev, "unable to register device: %d\n", ret); + dev_err(&d->dev, "unable to register device: %d\n"); kfree(d); } } diff --git a/trunk/arch/arm/mach-ixp4xx/fsg-setup.c b/trunk/arch/arm/mach-ixp4xx/fsg-setup.c index 501dfdcc39fe..0db3a909ae61 100644 --- a/trunk/arch/arm/mach-ixp4xx/fsg-setup.c +++ b/trunk/arch/arm/mach-ixp4xx/fsg-setup.c @@ -64,7 +64,7 @@ static struct platform_device fsg_i2c_gpio = { static struct i2c_board_info __initdata fsg_i2c_board_info [] = { { - I2C_BOARD_INFO("isl1208", 0x6f), + I2C_BOARD_INFO("rtc-isl1208", 0x6f), }, }; @@ -179,6 +179,7 @@ static void __init fsg_init(void) { DECLARE_MAC_BUF(mac_buf); uint8_t __iomem *f; + int i; ixp4xx_sys_init(); @@ -227,7 +228,6 @@ static void __init fsg_init(void) f = ioremap(IXP4XX_EXP_BUS_BASE(0), 0x400000); if (f) { #ifdef __ARMEB__ - int i; for (i = 0; i < 6; i++) { fsg_plat_eth[0].hwaddr[i] = readb(f + 0x3C0422 + i); fsg_plat_eth[1].hwaddr[i] = readb(f + 0x3C043B + i); diff --git a/trunk/arch/arm/mach-pxa/clock.c b/trunk/arch/arm/mach-pxa/clock.c index ca8e20538157..c01eea88f787 100644 --- a/trunk/arch/arm/mach-pxa/clock.c +++ b/trunk/arch/arm/mach-pxa/clock.c @@ -125,28 +125,3 @@ void clks_register(struct clk *clks, size_t num) list_add(&clks[i].node, &clocks); mutex_unlock(&clocks_mutex); } - -int clk_add_alias(char *alias, struct device *alias_dev, char *id, - struct device *dev) -{ - struct clk *r = clk_lookup(dev, id); - struct clk *new; - - if (!r) - return -ENODEV; - - new = kzalloc(sizeof(struct clk), GFP_KERNEL); - - if (!new) - return -ENOMEM; - - new->name = alias; - new->dev = alias_dev; - new->other = r; - - mutex_lock(&clocks_mutex); - list_add(&new->node, &clocks); - mutex_unlock(&clocks_mutex); - - return 0; -} diff --git a/trunk/arch/arm/mach-pxa/clock.h b/trunk/arch/arm/mach-pxa/clock.h index 73be795fe3bf..1ec8f9178aaf 100644 --- a/trunk/arch/arm/mach-pxa/clock.h +++ b/trunk/arch/arm/mach-pxa/clock.h @@ -1,5 +1,3 @@ -#include - struct clk; struct clkops { @@ -88,6 +86,3 @@ extern void clk_pxa3xx_cken_disable(struct clk *); #endif void clks_register(struct clk *clks, size_t num); -int clk_add_alias(char *alias, struct device *alias_dev, char *id, - struct device *dev); - diff --git a/trunk/arch/arm/mach-pxa/eseries.c b/trunk/arch/arm/mach-pxa/eseries.c index 001a252bd514..03942450885b 100644 --- a/trunk/arch/arm/mach-pxa/eseries.c +++ b/trunk/arch/arm/mach-pxa/eseries.c @@ -10,78 +10,18 @@ * */ -#include #include #include #include -#include - -#include #include +#include #include "generic.h" -static unsigned long e740_pin_config[] __initdata = { - /* Chip selects */ - GPIO15_nCS_1, /* CS1 - Flash */ - GPIO79_nCS_3, /* CS3 - IMAGEON */ - GPIO80_nCS_4, /* CS4 - TMIO */ - - /* Clocks */ - GPIO12_32KHz, - - /* BTUART */ - GPIO42_BTUART_RXD, - GPIO43_BTUART_TXD, - GPIO44_BTUART_CTS, - GPIO45_GPIO, /* Used by TMIO for #SUSPEND */ - - /* PC Card */ - GPIO8_GPIO, /* CD0 */ - GPIO44_GPIO, /* CD1 */ - GPIO11_GPIO, /* IRQ0 */ - GPIO6_GPIO, /* IRQ1 */ - GPIO27_GPIO, /* RST0 */ - GPIO24_GPIO, /* RST1 */ - GPIO20_GPIO, /* PWR0 */ - GPIO23_GPIO, /* PWR1 */ - GPIO48_nPOE, - GPIO49_nPWE, - GPIO50_nPIOR, - GPIO51_nPIOW, - GPIO52_nPCE_1, - GPIO53_nPCE_2, - GPIO54_nPSKTSEL, - GPIO55_nPREG, - GPIO56_nPWAIT, - GPIO57_nIOIS16, - - /* wakeup */ - GPIO0_GPIO | WAKEUP_ON_EDGE_RISE, -}; - -static unsigned long e400_pin_config[] __initdata = { - /* Chip selects */ - GPIO15_nCS_1, /* CS1 - Flash */ - GPIO80_nCS_4, /* CS4 - TMIO */ - - /* Clocks */ - GPIO12_32KHz, - - /* BTUART */ - GPIO42_BTUART_RXD, - GPIO43_BTUART_TXD, - GPIO44_BTUART_CTS, - GPIO45_GPIO, /* Used by TMIO for #SUSPEND */ - - /* wakeup */ - GPIO0_GPIO | WAKEUP_ON_EDGE_RISE, -}; - /* Only e800 has 128MB RAM */ static void __init eseries_fixup(struct machine_desc *desc, - struct tag *tags, char **cmdline, struct meminfo *mi) + struct tag *tags, char **cmdline, struct meminfo *mi) { mi->nr_banks=1; mi->bank[0].start = 0xa0000000; @@ -92,95 +32,83 @@ static void __init eseries_fixup(struct machine_desc *desc, mi->bank[0].size = (64*1024*1024); } -static void __init e740_init(void) -{ - pxa2xx_mfp_config(ARRAY_AND_SIZE(e740_pin_config)); -} - -static void __init e400_init(void) -{ - pxa2xx_mfp_config(ARRAY_AND_SIZE(e400_pin_config)); -} - /* e-series machine definitions */ #ifdef CONFIG_MACH_E330 MACHINE_START(E330, "Toshiba e330") - /* Maintainer: Ian Molton (spyro@f2s.com) */ - .phys_io = 0x40000000, - .io_pg_offst = (io_p2v(0x40000000) >> 18) & 0xfffc, - .boot_params = 0xa0000100, - .map_io = pxa_map_io, - .init_irq = pxa25x_init_irq, - .fixup = eseries_fixup, - .timer = &pxa_timer, + /* Maintainer: Ian Molton (spyro@f2s.com) */ + .phys_io = 0x40000000, + .io_pg_offst = (io_p2v(0x40000000) >> 18) & 0xfffc, + .boot_params = 0xa0000100, + .map_io = pxa_map_io, + .init_irq = pxa25x_init_irq, + .fixup = eseries_fixup, + .timer = &pxa_timer, MACHINE_END #endif #ifdef CONFIG_MACH_E350 MACHINE_START(E350, "Toshiba e350") /* Maintainer: Ian Molton (spyro@f2s.com) */ - .phys_io = 0x40000000, - .io_pg_offst = (io_p2v(0x40000000) >> 18) & 0xfffc, - .boot_params = 0xa0000100, - .map_io = pxa_map_io, - .init_irq = pxa25x_init_irq, - .fixup = eseries_fixup, - .timer = &pxa_timer, + .phys_io = 0x40000000, + .io_pg_offst = (io_p2v(0x40000000) >> 18) & 0xfffc, + .boot_params = 0xa0000100, + .map_io = pxa_map_io, + .init_irq = pxa25x_init_irq, + .fixup = eseries_fixup, + .timer = &pxa_timer, MACHINE_END #endif #ifdef CONFIG_MACH_E740 MACHINE_START(E740, "Toshiba e740") - /* Maintainer: Ian Molton (spyro@f2s.com) */ - .phys_io = 0x40000000, - .io_pg_offst = (io_p2v(0x40000000) >> 18) & 0xfffc, - .boot_params = 0xa0000100, - .map_io = pxa_map_io, - .init_irq = pxa25x_init_irq, - .fixup = eseries_fixup, - .init_machine = e740_init, - .timer = &pxa_timer, + /* Maintainer: Ian Molton (spyro@f2s.com) */ + .phys_io = 0x40000000, + .io_pg_offst = (io_p2v(0x40000000) >> 18) & 0xfffc, + .boot_params = 0xa0000100, + .map_io = pxa_map_io, + .init_irq = pxa25x_init_irq, + .fixup = eseries_fixup, + .timer = &pxa_timer, MACHINE_END #endif #ifdef CONFIG_MACH_E750 MACHINE_START(E750, "Toshiba e750") - /* Maintainer: Ian Molton (spyro@f2s.com) */ - .phys_io = 0x40000000, - .io_pg_offst = (io_p2v(0x40000000) >> 18) & 0xfffc, - .boot_params = 0xa0000100, - .map_io = pxa_map_io, - .init_irq = pxa25x_init_irq, - .fixup = eseries_fixup, - .timer = &pxa_timer, + /* Maintainer: Ian Molton (spyro@f2s.com) */ + .phys_io = 0x40000000, + .io_pg_offst = (io_p2v(0x40000000) >> 18) & 0xfffc, + .boot_params = 0xa0000100, + .map_io = pxa_map_io, + .init_irq = pxa25x_init_irq, + .fixup = eseries_fixup, + .timer = &pxa_timer, MACHINE_END #endif #ifdef CONFIG_MACH_E400 MACHINE_START(E400, "Toshiba e400") - /* Maintainer: Ian Molton (spyro@f2s.com) */ - .phys_io = 0x40000000, - .io_pg_offst = (io_p2v(0x40000000) >> 18) & 0xfffc, - .boot_params = 0xa0000100, - .map_io = pxa_map_io, - .init_irq = pxa25x_init_irq, - .fixup = eseries_fixup, - .init_machine = e400_init, - .timer = &pxa_timer, + /* Maintainer: Ian Molton (spyro@f2s.com) */ + .phys_io = 0x40000000, + .io_pg_offst = (io_p2v(0x40000000) >> 18) & 0xfffc, + .boot_params = 0xa0000100, + .map_io = pxa_map_io, + .init_irq = pxa25x_init_irq, + .fixup = eseries_fixup, + .timer = &pxa_timer, MACHINE_END #endif #ifdef CONFIG_MACH_E800 MACHINE_START(E800, "Toshiba e800") - /* Maintainer: Ian Molton (spyro@f2s.com) */ - .phys_io = 0x40000000, - .io_pg_offst = (io_p2v(0x40000000) >> 18) & 0xfffc, - .boot_params = 0xa0000100, - .map_io = pxa_map_io, - .init_irq = pxa25x_init_irq, - .fixup = eseries_fixup, - .timer = &pxa_timer, + /* Maintainer: Ian Molton (spyro@f2s.com) */ + .phys_io = 0x40000000, + .io_pg_offst = (io_p2v(0x40000000) >> 18) & 0xfffc, + .boot_params = 0xa0000100, + .map_io = pxa_map_io, + .init_irq = pxa25x_init_irq, + .fixup = eseries_fixup, + .timer = &pxa_timer, MACHINE_END #endif diff --git a/trunk/arch/arm/mach-pxa/include/mach/irqs.h b/trunk/arch/arm/mach-pxa/include/mach/irqs.h index 108b5db9b2af..32772bc6925c 100644 --- a/trunk/arch/arm/mach-pxa/include/mach/irqs.h +++ b/trunk/arch/arm/mach-pxa/include/mach/irqs.h @@ -183,7 +183,6 @@ defined(CONFIG_MACH_TOSA) || \ defined(CONFIG_MACH_MAINSTONE) || \ defined(CONFIG_MACH_PCM027) || \ - defined(CONFIG_ARCH_PXA_ESERIES) || \ defined(CONFIG_MACH_MAGICIAN) #define NR_IRQS (IRQ_BOARD_END) #elif defined(CONFIG_MACH_ZYLONITE) diff --git a/trunk/arch/arm/mach-pxa/lubbock.c b/trunk/arch/arm/mach-pxa/lubbock.c index 4ffdff2d9ff1..bb9e09208b9f 100644 --- a/trunk/arch/arm/mach-pxa/lubbock.c +++ b/trunk/arch/arm/mach-pxa/lubbock.c @@ -52,7 +52,6 @@ #include #include "generic.h" -#include "clock.h" #include "devices.h" static unsigned long lubbock_pin_config[] __initdata = { @@ -486,7 +485,6 @@ static void __init lubbock_init(void) pxa2xx_mfp_config(ARRAY_AND_SIZE(lubbock_pin_config)); - clk_add_alias("SA1111_CLK", NULL, "GPIO11_CLK", NULL); pxa_set_udc_info(&udc_info); set_pxa_fb_info(&sharp_lm8v31); pxa_set_mci_info(&lubbock_mci_platform_data); diff --git a/trunk/arch/arm/mach-pxa/pxa25x.c b/trunk/arch/arm/mach-pxa/pxa25x.c index 305452b56e91..9e5d8a8c6424 100644 --- a/trunk/arch/arm/mach-pxa/pxa25x.c +++ b/trunk/arch/arm/mach-pxa/pxa25x.c @@ -166,7 +166,8 @@ static struct clk pxa25x_hwuart_clk = ; /* - * PXA 2xx clock declarations. + * PXA 2xx clock declarations. Order is important (see aliases below) + * Please be careful not to disrupt the ordering. */ static struct clk pxa25x_clks[] = { INIT_CK("LCDCLK", LCD, &clk_pxa25x_lcd_ops, &pxa_device_fb.dev), @@ -193,6 +194,11 @@ static struct clk pxa25x_clks[] = { INIT_CKEN("FICPCLK", FICP, 47923000, 0, NULL), }; +static struct clk pxa2xx_clk_aliases[] = { + INIT_CKOTHER("GPIO7_CLK", &pxa25x_clks[4], NULL), + INIT_CKOTHER("SA1111_CLK", &pxa25x_clks[5], NULL), +}; + #ifdef CONFIG_PM #define SAVE(x) sleep_save[SLEEP_SAVE_##x] = x @@ -369,6 +375,8 @@ static int __init pxa25x_init(void) if (cpu_is_pxa255()) ret = platform_device_register(&pxa_device_hwuart); + clks_register(pxa2xx_clk_aliases, ARRAY_SIZE(pxa2xx_clk_aliases)); + return ret; } diff --git a/trunk/arch/arm/mach-pxa/pxa300.c b/trunk/arch/arm/mach-pxa/pxa300.c index 9adc7fc4618a..494fc1f032db 100644 --- a/trunk/arch/arm/mach-pxa/pxa300.c +++ b/trunk/arch/arm/mach-pxa/pxa300.c @@ -90,9 +90,7 @@ static struct clk common_clks[] = { }; static struct clk pxa310_clks[] = { -#ifdef CONFIG_CPU_PXA310 PXA3xx_CKEN("MMCCLK", MMC3, 19500000, 0, &pxa3xx_device_mci3.dev), -#endif }; static int __init pxa300_init(void) diff --git a/trunk/arch/arm/plat-omap/clock.c b/trunk/arch/arm/plat-omap/clock.c index 197974defbe4..23a070599993 100644 --- a/trunk/arch/arm/plat-omap/clock.c +++ b/trunk/arch/arm/plat-omap/clock.c @@ -10,6 +10,7 @@ * it under the terms of the GNU General Public License version 2 as * published by the Free Software Foundation. */ +#include #include #include #include diff --git a/trunk/arch/cris/arch-v32/kernel/fasttimer.c b/trunk/arch/cris/arch-v32/kernel/fasttimer.c index 111caa1a2efb..2de9d5849ef0 100644 --- a/trunk/arch/cris/arch-v32/kernel/fasttimer.c +++ b/trunk/arch/cris/arch-v32/kernel/fasttimer.c @@ -19,6 +19,8 @@ #include #include +#include + #include #include #include diff --git a/trunk/arch/mn10300/kernel/mn10300-serial.c b/trunk/arch/mn10300/kernel/mn10300-serial.c index aa07d0cd1905..8b054e7a8ae8 100644 --- a/trunk/arch/mn10300/kernel/mn10300-serial.c +++ b/trunk/arch/mn10300/kernel/mn10300-serial.c @@ -17,6 +17,7 @@ static const char serial_revdate[] = "2007-11-06"; #define SUPPORT_SYSRQ #endif +#include #include #include #include diff --git a/trunk/arch/powerpc/sysdev/bestcomm/gen_bd.c b/trunk/arch/powerpc/sysdev/bestcomm/gen_bd.c index e0a53e3147b2..a3a134c35b0a 100644 --- a/trunk/arch/powerpc/sysdev/bestcomm/gen_bd.c +++ b/trunk/arch/powerpc/sysdev/bestcomm/gen_bd.c @@ -11,6 +11,7 @@ * */ +#include #include #include #include diff --git a/trunk/arch/s390/defconfig b/trunk/arch/s390/defconfig index 9b0bc2c9fba0..c5cdb975d590 100644 --- a/trunk/arch/s390/defconfig +++ b/trunk/arch/s390/defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.27-rc4 -# Thu Aug 21 19:43:29 2008 +# Linux kernel version: 2.6.26-rc4 +# Fri May 30 09:49:33 2008 # CONFIG_SCHED_MC=y CONFIG_MMU=y @@ -68,6 +68,7 @@ CONFIG_INITRAMFS_SOURCE="" CONFIG_SYSCTL=y # CONFIG_EMBEDDED is not set CONFIG_SYSCTL_SYSCALL=y +CONFIG_SYSCTL_SYSCALL_CHECK=y CONFIG_KALLSYMS=y # CONFIG_KALLSYMS_ALL is not set # CONFIG_KALLSYMS_EXTRA_PASS is not set @@ -92,17 +93,11 @@ CONFIG_SLAB=y # CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y CONFIG_KPROBES=y -# CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS is not set CONFIG_KRETPROBES=y -# CONFIG_HAVE_IOREMAP_PROT is not set CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y -# CONFIG_HAVE_ARCH_TRACEHOOK is not set # CONFIG_HAVE_DMA_ATTRS is not set -# CONFIG_USE_GENERIC_SMP_HELPERS is not set -# CONFIG_HAVE_CLK is not set CONFIG_PROC_PAGE_MONITOR=y -# CONFIG_HAVE_GENERIC_DMA_COHERENT is not set CONFIG_SLABINFO=y CONFIG_RT_MUTEXES=y # CONFIG_TINY_SHMEM is not set @@ -118,7 +113,6 @@ CONFIG_STOP_MACHINE=y CONFIG_BLOCK=y # CONFIG_BLK_DEV_IO_TRACE is not set CONFIG_BLK_DEV_BSG=y -# CONFIG_BLK_DEV_INTEGRITY is not set CONFIG_BLOCK_COMPAT=y # @@ -181,8 +175,6 @@ CONFIG_PREEMPT=y CONFIG_ARCH_SPARSEMEM_ENABLE=y CONFIG_ARCH_SPARSEMEM_DEFAULT=y CONFIG_ARCH_SELECT_MEMORY_MODEL=y -CONFIG_ARCH_ENABLE_MEMORY_HOTPLUG=y -CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y CONFIG_SELECT_MEMORY_MODEL=y # CONFIG_FLATMEM_MANUAL is not set # CONFIG_DISCONTIGMEM_MANUAL is not set @@ -193,12 +185,8 @@ CONFIG_HAVE_MEMORY_PRESENT=y CONFIG_SPARSEMEM_EXTREME=y CONFIG_SPARSEMEM_VMEMMAP_ENABLE=y CONFIG_SPARSEMEM_VMEMMAP=y -CONFIG_MEMORY_HOTPLUG=y -CONFIG_MEMORY_HOTPLUG_SPARSE=y -CONFIG_MEMORY_HOTREMOVE=y CONFIG_PAGEFLAGS_EXTENDED=y CONFIG_SPLIT_PTLOCK_CPUS=4 -CONFIG_MIGRATION=y CONFIG_RESOURCES_64BIT=y CONFIG_ZONE_DMA_FLAG=1 CONFIG_BOUNCE=y @@ -210,7 +198,6 @@ CONFIG_VIRT_TO_BUS=y CONFIG_MACHCHK_WARNING=y CONFIG_QDIO=y # CONFIG_QDIO_DEBUG is not set -CONFIG_CHSC_SCH=m # # Misc @@ -219,7 +206,6 @@ CONFIG_IPL=y # CONFIG_IPL_TAPE is not set CONFIG_IPL_VM=y CONFIG_BINFMT_ELF=y -CONFIG_COMPAT_BINFMT_ELF=y CONFIG_BINFMT_MISC=m CONFIG_FORCE_MAX_ZONEORDER=9 # CONFIG_PROCESS_DEBUG is not set @@ -240,6 +226,10 @@ CONFIG_S390_HYPFS_FS=y CONFIG_KEXEC=y # CONFIG_ZFCPDUMP is not set CONFIG_S390_GUEST=y + +# +# Networking +# CONFIG_NET=y # @@ -374,6 +364,7 @@ CONFIG_NET_SCH_CBQ=m # CONFIG_NET_SCH_HTB is not set # CONFIG_NET_SCH_HFSC is not set CONFIG_NET_SCH_PRIO=m +CONFIG_NET_SCH_RR=m CONFIG_NET_SCH_RED=m CONFIG_NET_SCH_SFQ=m CONFIG_NET_SCH_TEQL=m @@ -439,9 +430,7 @@ CONFIG_CCW=y CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y -CONFIG_FW_LOADER=y -# CONFIG_FIRMWARE_IN_KERNEL is not set -CONFIG_EXTRA_FIRMWARE="" +# CONFIG_FW_LOADER is not set # CONFIG_DEBUG_DRIVER is not set # CONFIG_DEBUG_DEVRES is not set CONFIG_SYS_HYPERVISOR=y @@ -518,11 +507,6 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_ISCSI_TCP is not set # CONFIG_SCSI_DEBUG is not set CONFIG_ZFCP=y -CONFIG_SCSI_DH=m -CONFIG_SCSI_DH_RDAC=m -CONFIG_SCSI_DH_HP_SW=m -CONFIG_SCSI_DH_EMC=m -CONFIG_SCSI_DH_ALUA=m CONFIG_MD=y CONFIG_BLK_DEV_MD=y CONFIG_MD_LINEAR=m @@ -538,10 +522,14 @@ CONFIG_DM_CRYPT=y CONFIG_DM_SNAPSHOT=y CONFIG_DM_MIRROR=y CONFIG_DM_ZERO=y -CONFIG_DM_MULTIPATH=m +CONFIG_DM_MULTIPATH=y +# CONFIG_DM_MULTIPATH_EMC is not set +# CONFIG_DM_MULTIPATH_RDAC is not set +# CONFIG_DM_MULTIPATH_HP is not set # CONFIG_DM_DELAY is not set # CONFIG_DM_UEVENT is not set CONFIG_NETDEVICES=y +# CONFIG_NETDEVICES_MULTIQUEUE is not set # CONFIG_IFB is not set CONFIG_DUMMY=m CONFIG_BONDING=m @@ -556,6 +544,7 @@ CONFIG_NET_ETHERNET=y # CONFIG_IBM_NEW_EMAC_TAH is not set # CONFIG_IBM_NEW_EMAC_EMAC4 is not set CONFIG_NETDEV_1000=y +# CONFIG_E1000E_ENABLED is not set CONFIG_NETDEV_10000=y # CONFIG_TR is not set # CONFIG_WAN is not set @@ -587,10 +576,7 @@ CONFIG_DEVKMEM=y CONFIG_UNIX98_PTYS=y CONFIG_LEGACY_PTYS=y CONFIG_LEGACY_PTY_COUNT=256 -CONFIG_HVC_DRIVER=y -CONFIG_VIRTIO_CONSOLE=y CONFIG_HW_RANDOM=m -CONFIG_HW_RANDOM_VIRTIO=m # CONFIG_R3964 is not set CONFIG_RAW_DRIVER=m CONFIG_MAX_RAW_DEVS=256 @@ -630,7 +616,6 @@ CONFIG_MONWRITER=m CONFIG_S390_VMUR=m # CONFIG_POWER_SUPPLY is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set # CONFIG_WATCHDOG is not set # @@ -708,7 +693,6 @@ CONFIG_CONFIGFS_FS=m # CONFIG_CRAMFS is not set # CONFIG_VXFS_FS is not set # CONFIG_MINIX_FS is not set -# CONFIG_OMFS_FS is not set # CONFIG_HPFS_FS is not set # CONFIG_QNX4FS_FS is not set # CONFIG_ROMFS_FS is not set @@ -728,6 +712,7 @@ CONFIG_LOCKD_V4=y CONFIG_EXPORTFS=y CONFIG_NFS_COMMON=y CONFIG_SUNRPC=y +# CONFIG_SUNRPC_BIND34 is not set # CONFIG_RPCSEC_GSS_KRB5 is not set # CONFIG_RPCSEC_GSS_SPKM3 is not set # CONFIG_SMB_FS is not set @@ -795,7 +780,6 @@ CONFIG_DEBUG_BUGVERBOSE=y # CONFIG_DEBUG_INFO is not set # CONFIG_DEBUG_VM is not set # CONFIG_DEBUG_WRITECOUNT is not set -CONFIG_DEBUG_MEMORY_INIT=y # CONFIG_DEBUG_LIST is not set # CONFIG_DEBUG_SG is not set # CONFIG_FRAME_POINTER is not set @@ -805,7 +789,6 @@ CONFIG_DEBUG_MEMORY_INIT=y # CONFIG_LKDTM is not set # CONFIG_FAULT_INJECTION is not set # CONFIG_LATENCYTOP is not set -CONFIG_SYSCTL_SYSCALL_CHECK=y CONFIG_SAMPLES=y # CONFIG_SAMPLE_KOBJECT is not set # CONFIG_SAMPLE_KPROBES is not set @@ -864,10 +847,6 @@ CONFIG_CRYPTO_HMAC=m # CONFIG_CRYPTO_MD4 is not set CONFIG_CRYPTO_MD5=m # CONFIG_CRYPTO_MICHAEL_MIC is not set -CONFIG_CRYPTO_RMD128=m -CONFIG_CRYPTO_RMD160=m -CONFIG_CRYPTO_RMD256=m -CONFIG_CRYPTO_RMD320=m CONFIG_CRYPTO_SHA1=m # CONFIG_CRYPTO_SHA256 is not set # CONFIG_CRYPTO_SHA512 is not set @@ -916,7 +895,6 @@ CONFIG_BITREVERSE=m # CONFIG_GENERIC_FIND_NEXT_BIT is not set # CONFIG_CRC_CCITT is not set # CONFIG_CRC16 is not set -CONFIG_CRC_T10DIF=y # CONFIG_CRC_ITU_T is not set CONFIG_CRC32=m CONFIG_CRC7=m diff --git a/trunk/arch/s390/include/asm/bitops.h b/trunk/arch/s390/include/asm/bitops.h index 8e9243ae0c19..b4eb24ab5af9 100644 --- a/trunk/arch/s390/include/asm/bitops.h +++ b/trunk/arch/s390/include/asm/bitops.h @@ -709,7 +709,7 @@ static inline int find_next_zero_bit (const unsigned long * addr, * __ffz_word returns __BITOPS_WORDSIZE * if no zero bit is present in the word. */ - set = __ffz_word(bit, *p >> bit); + set = __ffz_word(0, *p >> bit) + bit; if (set >= size) return size + offset; if (set < __BITOPS_WORDSIZE) @@ -824,7 +824,7 @@ static inline int ext2_find_next_zero_bit(void *vaddr, unsigned long size, * s390 version of ffz returns __BITOPS_WORDSIZE * if no zero bit is present in the word. */ - set = __ffz_word(bit, __load_ulong_le(p, 0) >> bit); + set = ffz(__load_ulong_le(p, 0) >> bit) + bit; if (set >= size) return size + offset; if (set < __BITOPS_WORDSIZE) @@ -865,7 +865,7 @@ static inline int ext2_find_next_bit(void *vaddr, unsigned long size, * s390 version of ffz returns __BITOPS_WORDSIZE * if no zero bit is present in the word. */ - set = __ffs_word(0, __load_ulong_le(p, 0) & (~0UL << bit)); + set = ffs(__load_ulong_le(p, 0) >> bit) + bit; if (set >= size) return size + offset; if (set < __BITOPS_WORDSIZE) diff --git a/trunk/arch/s390/kernel/process.c b/trunk/arch/s390/kernel/process.c index 3e2c05cb6a87..9839767d0842 100644 --- a/trunk/arch/s390/kernel/process.c +++ b/trunk/arch/s390/kernel/process.c @@ -75,9 +75,7 @@ unsigned long thread_saved_pc(struct task_struct *tsk) return sf->gprs[8]; } -DEFINE_PER_CPU(struct s390_idle_data, s390_idle) = { - .lock = __SPIN_LOCK_UNLOCKED(s390_idle.lock) -}; +DEFINE_PER_CPU(struct s390_idle_data, s390_idle); static int s390_idle_enter(void) { diff --git a/trunk/arch/s390/kernel/smp.c b/trunk/arch/s390/kernel/smp.c index 00b9b4dec5eb..b795b3e24afd 100644 --- a/trunk/arch/s390/kernel/smp.c +++ b/trunk/arch/s390/kernel/smp.c @@ -610,6 +610,7 @@ static void __init smp_create_idle(unsigned int cpu) if (IS_ERR(p)) panic("failed fork for CPU %u: %li", cpu, PTR_ERR(p)); current_set[cpu] = p; + spin_lock_init(&(&per_cpu(s390_idle, cpu))->lock); } static int __cpuinit smp_alloc_lowcore(int cpu) @@ -844,6 +845,7 @@ void __init smp_prepare_boot_cpu(void) current_set[0] = current; smp_cpu_state[0] = CPU_STATE_CONFIGURED; smp_cpu_polarization[0] = POLARIZATION_UNKNWN; + spin_lock_init(&(&__get_cpu_var(s390_idle))->lock); } void __init smp_cpus_done(unsigned int max_cpus) diff --git a/trunk/arch/x86/Kconfig b/trunk/arch/x86/Kconfig index ed92864d1325..68d91c8233f4 100644 --- a/trunk/arch/x86/Kconfig +++ b/trunk/arch/x86/Kconfig @@ -577,29 +577,35 @@ config SWIOTLB config IOMMU_HELPER def_bool (CALGARY_IOMMU || GART_IOMMU || SWIOTLB || AMD_IOMMU) - config MAXSMP bool "Configure Maximum number of SMP Processors and NUMA Nodes" - depends on X86_64 && SMP && BROKEN + depends on X86_64 && SMP default n help Configure maximum number of CPUS and NUMA Nodes for this architecture. If unsure, say N. +if MAXSMP +config NR_CPUS + int + default "4096" +endif + +if !MAXSMP config NR_CPUS - int "Maximum number of CPUs (2-512)" if !MAXSMP - range 2 512 + int "Maximum number of CPUs (2-4096)" + range 2 4096 depends on SMP - default "4096" if MAXSMP default "32" if X86_NUMAQ || X86_SUMMIT || X86_BIGSMP || X86_ES7000 default "8" help This allows you to specify the maximum number of CPUs which this - kernel will support. The maximum supported value is 512 and the + kernel will support. The maximum supported value is 4096 and the minimum value which makes sense is 2. This is purely to save memory - each supported CPU adds approximately eight kilobytes to the kernel image. +endif config SCHED_SMT bool "SMT (Hyperthreading) scheduler support" @@ -990,10 +996,17 @@ config NUMA_EMU into virtual nodes when booted with "numa=fake=N", where N is the number of nodes. This is only useful for debugging. +if MAXSMP + config NODES_SHIFT - int "Maximum NUMA Nodes (as a power of 2)" if !MAXSMP + int + default "9" +endif + +if !MAXSMP +config NODES_SHIFT + int "Maximum NUMA Nodes (as a power of 2)" range 1 9 if X86_64 - default "9" if MAXSMP default "6" if X86_64 default "4" if X86_NUMAQ default "3" @@ -1001,6 +1014,7 @@ config NODES_SHIFT help Specify the maximum number of NUMA Nodes available on the target system. Increases memory reserved to accomodate various tables. +endif config HAVE_ARCH_BOOTMEM_NODE def_bool y diff --git a/trunk/arch/x86/kernel/amd_iommu.c b/trunk/arch/x86/kernel/amd_iommu.c index 69b4d060b21c..de39e1f2ede5 100644 --- a/trunk/arch/x86/kernel/amd_iommu.c +++ b/trunk/arch/x86/kernel/amd_iommu.c @@ -65,7 +65,7 @@ static int __iommu_queue_command(struct amd_iommu *iommu, struct iommu_cmd *cmd) u8 *target; tail = readl(iommu->mmio_base + MMIO_CMD_TAIL_OFFSET); - target = iommu->cmd_buf + tail; + target = (iommu->cmd_buf + tail); memcpy_toio(target, cmd, sizeof(*cmd)); tail = (tail + sizeof(*cmd)) % iommu->cmd_buf_size; head = readl(iommu->mmio_base + MMIO_CMD_HEAD_OFFSET); diff --git a/trunk/arch/x86/kernel/cpu/addon_cpuid_features.c b/trunk/arch/x86/kernel/cpu/addon_cpuid_features.c index a6ef672adbba..84a8220a6072 100644 --- a/trunk/arch/x86/kernel/cpu/addon_cpuid_features.c +++ b/trunk/arch/x86/kernel/cpu/addon_cpuid_features.c @@ -56,22 +56,9 @@ void __cpuinit validate_pat_support(struct cpuinfo_x86 *c) switch (c->x86_vendor) { case X86_VENDOR_INTEL: - /* - * There is a known erratum on Pentium III and Core Solo - * and Core Duo CPUs. - * " Page with PAT set to WC while associated MTRR is UC - * may consolidate to UC " - * Because of this erratum, it is better to stick with - * setting WC in MTRR rather than using PAT on these CPUs. - * - * Enable PAT WC only on P4, Core 2 or later CPUs. - */ - if (c->x86 > 0x6 || (c->x86 == 6 && c->x86_model >= 15)) + if (c->x86 == 0xF || (c->x86 == 6 && c->x86_model >= 15)) return; - - pat_disable("PAT WC disabled due to known CPU erratum."); - return; - + break; case X86_VENDOR_AMD: case X86_VENDOR_CENTAUR: case X86_VENDOR_TRANSMETA: diff --git a/trunk/arch/x86/kernel/cpu/cyrix.c b/trunk/arch/x86/kernel/cpu/cyrix.c index e710a21bb6e8..3fd7a67bb06a 100644 --- a/trunk/arch/x86/kernel/cpu/cyrix.c +++ b/trunk/arch/x86/kernel/cpu/cyrix.c @@ -134,6 +134,23 @@ static void __cpuinit set_cx86_memwb(void) setCx86(CX86_CCR2, getCx86(CX86_CCR2) | 0x14); } +static void __cpuinit set_cx86_inc(void) +{ + unsigned char ccr3; + + printk(KERN_INFO "Enable Incrementor on Cyrix/NSC processor.\n"); + + ccr3 = getCx86(CX86_CCR3); + setCx86(CX86_CCR3, (ccr3 & 0x0f) | 0x10); /* enable MAPEN */ + /* PCR1 -- Performance Control */ + /* Incrementor on, whatever that is */ + setCx86(CX86_PCR1, getCx86(CX86_PCR1) | 0x02); + /* PCR0 -- Performance Control */ + /* Incrementor Margin 10 */ + setCx86(CX86_PCR0, getCx86(CX86_PCR0) | 0x04); + setCx86(CX86_CCR3, ccr3); /* disable MAPEN */ +} + /* * Configure later MediaGX and/or Geode processor. */ @@ -157,6 +174,7 @@ static void __cpuinit geode_configure(void) set_cx86_memwb(); set_cx86_reorder(); + set_cx86_inc(); local_irq_restore(flags); } diff --git a/trunk/arch/x86/kernel/cpu/mcheck/mce_64.c b/trunk/arch/x86/kernel/cpu/mcheck/mce_64.c index 726a5fcdf341..65a339678ece 100644 --- a/trunk/arch/x86/kernel/cpu/mcheck/mce_64.c +++ b/trunk/arch/x86/kernel/cpu/mcheck/mce_64.c @@ -759,7 +759,6 @@ static struct sysdev_class mce_sysclass = { }; DEFINE_PER_CPU(struct sys_device, device_mce); -void (*threshold_cpu_callback)(unsigned long action, unsigned int cpu) __cpuinitdata; /* Why are there no generic functions for this? */ #define ACCESSOR(name, var, start) \ @@ -884,13 +883,9 @@ static int __cpuinit mce_cpu_callback(struct notifier_block *nfb, case CPU_ONLINE: case CPU_ONLINE_FROZEN: mce_create_device(cpu); - if (threshold_cpu_callback) - threshold_cpu_callback(action, cpu); break; case CPU_DEAD: case CPU_DEAD_FROZEN: - if (threshold_cpu_callback) - threshold_cpu_callback(action, cpu); mce_remove_device(cpu); break; } diff --git a/trunk/arch/x86/kernel/cpu/mcheck/mce_amd_64.c b/trunk/arch/x86/kernel/cpu/mcheck/mce_amd_64.c index 5eb390a4b2e9..88736cadbaa6 100644 --- a/trunk/arch/x86/kernel/cpu/mcheck/mce_amd_64.c +++ b/trunk/arch/x86/kernel/cpu/mcheck/mce_amd_64.c @@ -628,7 +628,6 @@ static void threshold_remove_bank(unsigned int cpu, int bank) deallocate_threshold_block(cpu, bank); free_out: - kobject_del(b->kobj); kobject_put(b->kobj); kfree(b); per_cpu(threshold_banks, cpu)[bank] = NULL; @@ -646,11 +645,14 @@ static void threshold_remove_device(unsigned int cpu) } /* get notified when a cpu comes on/off */ -static void __cpuinit amd_64_threshold_cpu_callback(unsigned long action, - unsigned int cpu) +static int __cpuinit threshold_cpu_callback(struct notifier_block *nfb, + unsigned long action, void *hcpu) { + /* cpu was unsigned int to begin with */ + unsigned int cpu = (unsigned long)hcpu; + if (cpu >= NR_CPUS) - return; + goto out; switch (action) { case CPU_ONLINE: @@ -664,8 +666,14 @@ static void __cpuinit amd_64_threshold_cpu_callback(unsigned long action, default: break; } + out: + return NOTIFY_OK; } +static struct notifier_block threshold_cpu_notifier __cpuinitdata = { + .notifier_call = threshold_cpu_callback, +}; + static __init int threshold_init_device(void) { unsigned lcpu = 0; @@ -676,7 +684,7 @@ static __init int threshold_init_device(void) if (err) return err; } - threshold_cpu_callback = amd_64_threshold_cpu_callback; + register_hotcpu_notifier(&threshold_cpu_notifier); return 0; } diff --git a/trunk/arch/x86/kernel/cpu/mtrr/generic.c b/trunk/arch/x86/kernel/cpu/mtrr/generic.c index cb7d3b6a80eb..509bd3d9eacd 100644 --- a/trunk/arch/x86/kernel/cpu/mtrr/generic.c +++ b/trunk/arch/x86/kernel/cpu/mtrr/generic.c @@ -379,7 +379,6 @@ static void generic_get_mtrr(unsigned int reg, unsigned long *base, unsigned long *size, mtrr_type *type) { unsigned int mask_lo, mask_hi, base_lo, base_hi; - unsigned int tmp, hi; rdmsr(MTRRphysMask_MSR(reg), mask_lo, mask_hi); if ((mask_lo & 0x800) == 0) { @@ -393,23 +392,8 @@ static void generic_get_mtrr(unsigned int reg, unsigned long *base, rdmsr(MTRRphysBase_MSR(reg), base_lo, base_hi); /* Work out the shifted address mask. */ - tmp = mask_hi << (32 - PAGE_SHIFT) | mask_lo >> PAGE_SHIFT; - mask_lo = size_or_mask | tmp; - /* Expand tmp with high bits to all 1s*/ - hi = fls(tmp); - if (hi > 0) { - tmp |= ~((1<<(hi - 1)) - 1); - - if (tmp != mask_lo) { - static int once = 1; - - if (once) { - printk(KERN_INFO "mtrr: your BIOS has set up an incorrect mask, fixing it up.\n"); - once = 0; - } - mask_lo = tmp; - } - } + mask_lo = size_or_mask | mask_hi << (32 - PAGE_SHIFT) + | mask_lo >> PAGE_SHIFT; /* This works correctly if size is a power of two, i.e. a contiguous range. */ diff --git a/trunk/arch/x86/kernel/cpu/mtrr/main.c b/trunk/arch/x86/kernel/cpu/mtrr/main.c index b117d7f8a564..6f23969c8faf 100644 --- a/trunk/arch/x86/kernel/cpu/mtrr/main.c +++ b/trunk/arch/x86/kernel/cpu/mtrr/main.c @@ -1496,8 +1496,11 @@ int __init mtrr_trim_uncached_memory(unsigned long end_pfn) /* kvm/qemu doesn't have mtrr set right, don't trim them all */ if (!highest_pfn) { - WARN(!kvm_para_available(), KERN_WARNING + if (!kvm_para_available()) { + printk(KERN_WARNING "WARNING: strange, CPU MTRRs all blank?\n"); + WARN_ON(1); + } return 0; } diff --git a/trunk/arch/x86/kernel/genx2apic_uv_x.c b/trunk/arch/x86/kernel/genx2apic_uv_x.c index bfa837cb16be..2d7e307c7779 100644 --- a/trunk/arch/x86/kernel/genx2apic_uv_x.c +++ b/trunk/arch/x86/kernel/genx2apic_uv_x.c @@ -293,9 +293,7 @@ static __init void uv_rtc_init(void) sn_rtc_cycles_per_second = ticks_per_sec; } -static bool uv_system_inited; - -void __init uv_system_init(void) +static __init void uv_system_init(void) { union uvh_si_addr_map_config_u m_n_config; union uvh_node_id_u node_id; @@ -385,7 +383,6 @@ void __init uv_system_init(void) map_mmr_high(max_pnode); map_config_high(max_pnode); map_mmioh_high(max_pnode); - uv_system_inited = true; } /* @@ -394,7 +391,8 @@ void __init uv_system_init(void) */ void __cpuinit uv_cpu_init(void) { - BUG_ON(!uv_system_inited); + if (!uv_node_to_blade) + uv_system_init(); uv_blade_info[uv_numa_blade_id()].nr_online_cpus++; diff --git a/trunk/arch/x86/kernel/numaq_32.c b/trunk/arch/x86/kernel/numaq_32.c index eecc8c18f010..b8c45610b20a 100644 --- a/trunk/arch/x86/kernel/numaq_32.c +++ b/trunk/arch/x86/kernel/numaq_32.c @@ -73,7 +73,7 @@ static void __init smp_dump_qct(void) } -void __cpuinit numaq_tsc_disable(void) +void __init numaq_tsc_disable(void) { if (!found_numaq) return; diff --git a/trunk/arch/x86/kernel/paravirt.c b/trunk/arch/x86/kernel/paravirt.c index 300da17e61cb..94da4d52d798 100644 --- a/trunk/arch/x86/kernel/paravirt.c +++ b/trunk/arch/x86/kernel/paravirt.c @@ -471,7 +471,7 @@ struct pv_lock_ops pv_lock_ops = { .spin_unlock = __ticket_spin_unlock, #endif }; -EXPORT_SYMBOL(pv_lock_ops); +EXPORT_SYMBOL_GPL(pv_lock_ops); EXPORT_SYMBOL_GPL(pv_time_ops); EXPORT_SYMBOL (pv_cpu_ops); diff --git a/trunk/arch/x86/kernel/pci-calgary_64.c b/trunk/arch/x86/kernel/pci-calgary_64.c index dcdac6c826e9..218d783ed7a8 100644 --- a/trunk/arch/x86/kernel/pci-calgary_64.c +++ b/trunk/arch/x86/kernel/pci-calgary_64.c @@ -343,8 +343,9 @@ static void iommu_free(struct iommu_table *tbl, dma_addr_t dma_addr, /* were we called with bad_dma_address? */ badend = bad_dma_address + (EMERGENCY_PAGES * PAGE_SIZE); if (unlikely((dma_addr >= bad_dma_address) && (dma_addr < badend))) { - WARN(1, KERN_ERR "Calgary: driver tried unmapping bad DMA " + printk(KERN_ERR "Calgary: driver tried unmapping bad DMA " "address 0x%Lx\n", dma_addr); + WARN_ON(1); return; } @@ -1268,15 +1269,13 @@ static inline int __init determine_tce_table_size(u64 ram) static int __init build_detail_arrays(void) { unsigned long ptr; - unsigned numnodes, i; - int scal_detail_size, rio_detail_size; + int i, scal_detail_size, rio_detail_size; - numnodes = rio_table_hdr->num_scal_dev; - if (numnodes > MAX_NUMNODES){ + if (rio_table_hdr->num_scal_dev > MAX_NUMNODES){ printk(KERN_WARNING "Calgary: MAX_NUMNODES too low! Defined as %d, " "but system has %d nodes.\n", - MAX_NUMNODES, numnodes); + MAX_NUMNODES, rio_table_hdr->num_scal_dev); return -ENODEV; } @@ -1297,7 +1296,8 @@ static int __init build_detail_arrays(void) } ptr = ((unsigned long)rio_table_hdr) + 3; - for (i = 0; i < numnodes; i++, ptr += scal_detail_size) + for (i = 0; i < rio_table_hdr->num_scal_dev; + i++, ptr += scal_detail_size) scal_devs[i] = (struct scal_detail *)ptr; for (i = 0; i < rio_table_hdr->num_rio_dev; diff --git a/trunk/arch/x86/kernel/setup.c b/trunk/arch/x86/kernel/setup.c index 362d4e7f2d38..a4656adab53b 100644 --- a/trunk/arch/x86/kernel/setup.c +++ b/trunk/arch/x86/kernel/setup.c @@ -604,6 +604,14 @@ void __init setup_arch(char **cmdline_p) early_cpu_init(); early_ioremap_init(); +#if defined(CONFIG_VMI) && defined(CONFIG_X86_32) + /* + * Must be before kernel pagetables are setup + * or fixmap area is touched. + */ + vmi_init(); +#endif + ROOT_DEV = old_decode_dev(boot_params.hdr.root_dev); screen_info = boot_params.screen_info; edid_info = boot_params.edid_info; @@ -670,14 +678,6 @@ void __init setup_arch(char **cmdline_p) parse_early_param(); -#if defined(CONFIG_VMI) && defined(CONFIG_X86_32) - /* - * Must be before kernel pagetables are setup - * or fixmap area is touched. - */ - vmi_init(); -#endif - /* after early param, so could get panic from serial */ reserve_early_setup_data(); diff --git a/trunk/arch/x86/kernel/smpboot.c b/trunk/arch/x86/kernel/smpboot.c index 7985c5b3f916..e139e617f422 100644 --- a/trunk/arch/x86/kernel/smpboot.c +++ b/trunk/arch/x86/kernel/smpboot.c @@ -1221,9 +1221,6 @@ void __init native_smp_prepare_cpus(unsigned int max_cpus) printk(KERN_INFO "CPU%d: ", 0); print_cpu_info(&cpu_data(0)); setup_boot_clock(); - - if (is_uv_system()) - uv_system_init(); out: preempt_enable(); } diff --git a/trunk/arch/x86/kernel/tlb_uv.c b/trunk/arch/x86/kernel/tlb_uv.c index 8b8c0d6640fa..d0fbb7712ab0 100644 --- a/trunk/arch/x86/kernel/tlb_uv.c +++ b/trunk/arch/x86/kernel/tlb_uv.c @@ -17,7 +17,6 @@ #include #include #include -#include #include @@ -784,7 +783,7 @@ static int __init uv_bau_init(void) uv_init_blade(blade, node, cur_cpu); cur_cpu += uv_blade_nr_possible_cpus(blade); } - alloc_intr_gate(UV_BAU_MESSAGE, uv_bau_message_intr1); + set_intr_gate(UV_BAU_MESSAGE, uv_bau_message_intr1); uv_enable_timeouts(); return 0; diff --git a/trunk/arch/x86/kernel/tsc.c b/trunk/arch/x86/kernel/tsc.c index 8e786b0d665a..46af71676738 100644 --- a/trunk/arch/x86/kernel/tsc.c +++ b/trunk/arch/x86/kernel/tsc.c @@ -314,7 +314,7 @@ static int time_cpufreq_notifier(struct notifier_block *nb, unsigned long val, mark_tsc_unstable("cpufreq changes"); } - set_cyc2ns_scale(tsc_khz, freq->cpu); + set_cyc2ns_scale(tsc_khz_ref, freq->cpu); return 0; } @@ -325,10 +325,6 @@ static struct notifier_block time_cpufreq_notifier_block = { static int __init cpufreq_tsc(void) { - if (!cpu_has_tsc) - return 0; - if (boot_cpu_has(X86_FEATURE_CONSTANT_TSC)) - return 0; cpufreq_register_notifier(&time_cpufreq_notifier_block, CPUFREQ_TRANSITION_NOTIFIER); return 0; diff --git a/trunk/arch/x86/kernel/tsc_sync.c b/trunk/arch/x86/kernel/tsc_sync.c index 9ffb01c31c40..0577825cf89b 100644 --- a/trunk/arch/x86/kernel/tsc_sync.c +++ b/trunk/arch/x86/kernel/tsc_sync.c @@ -88,9 +88,11 @@ static __cpuinit void check_tsc_warp(void) __raw_spin_unlock(&sync_lock); } } - WARN(!(now-start), - "Warning: zero tsc calibration delta: %Ld [max: %Ld]\n", + if (!(now-start)) { + printk("Warning: zero tsc calibration delta: %Ld [max: %Ld]\n", now-start, end-start); + WARN_ON(1); + } } /* diff --git a/trunk/arch/x86/kvm/paging_tmpl.h b/trunk/arch/x86/kvm/paging_tmpl.h index 4a814bff21f2..f72ac1fa35f0 100644 --- a/trunk/arch/x86/kvm/paging_tmpl.h +++ b/trunk/arch/x86/kvm/paging_tmpl.h @@ -345,7 +345,7 @@ static u64 *FNAME(fetch)(struct kvm_vcpu *vcpu, gva_t addr, shadow_addr = __pa(shadow_page->spt); shadow_pte = shadow_addr | PT_PRESENT_MASK | PT_ACCESSED_MASK | PT_WRITABLE_MASK | PT_USER_MASK; - set_shadow_pte(shadow_ent, shadow_pte); + *shadow_ent = shadow_pte; } mmu_set_spte(vcpu, shadow_ent, access, walker->pte_access & access, diff --git a/trunk/arch/x86/mach-rdc321x/platform.c b/trunk/arch/x86/mach-rdc321x/platform.c index 4f4e50c3ad3b..a037041817c7 100644 --- a/trunk/arch/x86/mach-rdc321x/platform.c +++ b/trunk/arch/x86/mach-rdc321x/platform.c @@ -25,6 +25,7 @@ #include #include #include +#include #include #include diff --git a/trunk/arch/x86/mm/init_64.c b/trunk/arch/x86/mm/init_64.c index d3746efb060d..a87ea0e4b3dc 100644 --- a/trunk/arch/x86/mm/init_64.c +++ b/trunk/arch/x86/mm/init_64.c @@ -241,7 +241,7 @@ static unsigned long __initdata table_start; static unsigned long __meminitdata table_end; static unsigned long __meminitdata table_top; -static __ref void *alloc_low_page(unsigned long *phys) +static __meminit void *alloc_low_page(unsigned long *phys) { unsigned long pfn = table_end++; void *adr; @@ -262,7 +262,7 @@ static __ref void *alloc_low_page(unsigned long *phys) return adr; } -static __ref void unmap_low_page(void *adr) +static __meminit void unmap_low_page(void *adr) { if (after_bootmem) return; @@ -336,12 +336,9 @@ phys_pmd_init(pmd_t *pmd_page, unsigned long address, unsigned long end, } if (pmd_val(*pmd)) { - if (!pmd_large(*pmd)) { - spin_lock(&init_mm.page_table_lock); + if (!pmd_large(*pmd)) last_map_addr = phys_pte_update(pmd, address, - end); - spin_unlock(&init_mm.page_table_lock); - } + end); /* Count entries we're using from level2_ident_pgt */ if (start == 0) pages++; @@ -350,10 +347,8 @@ phys_pmd_init(pmd_t *pmd_page, unsigned long address, unsigned long end, if (page_size_mask & (1<> PAGE_SHIFT, PAGE_KERNEL_LARGE)); - spin_unlock(&init_mm.page_table_lock); last_map_addr = (address & PMD_MASK) + PMD_SIZE; continue; } @@ -362,9 +357,7 @@ phys_pmd_init(pmd_t *pmd_page, unsigned long address, unsigned long end, last_map_addr = phys_pte_init(pte, address, end); unmap_low_page(pte); - spin_lock(&init_mm.page_table_lock); pmd_populate_kernel(&init_mm, pmd, __va(pte_phys)); - spin_unlock(&init_mm.page_table_lock); } update_page_count(PG_LEVEL_2M, pages); return last_map_addr; @@ -377,7 +370,9 @@ phys_pmd_update(pud_t *pud, unsigned long address, unsigned long end, pmd_t *pmd = pmd_offset(pud, 0); unsigned long last_map_addr; + spin_lock(&init_mm.page_table_lock); last_map_addr = phys_pmd_init(pmd, address, end, page_size_mask); + spin_unlock(&init_mm.page_table_lock); __flush_tlb_all(); return last_map_addr; } @@ -413,21 +408,20 @@ phys_pud_init(pud_t *pud_page, unsigned long addr, unsigned long end, if (page_size_mask & (1<> PAGE_SHIFT, PAGE_KERNEL_LARGE)); - spin_unlock(&init_mm.page_table_lock); last_map_addr = (addr & PUD_MASK) + PUD_SIZE; continue; } pmd = alloc_low_page(&pmd_phys); - last_map_addr = phys_pmd_init(pmd, addr, end, page_size_mask); - unmap_low_page(pmd); spin_lock(&init_mm.page_table_lock); + last_map_addr = phys_pmd_init(pmd, addr, end, page_size_mask); + unmap_low_page(pmd); pud_populate(&init_mm, pud, __va(pmd_phys)); spin_unlock(&init_mm.page_table_lock); + } __flush_tlb_all(); update_page_count(PG_LEVEL_1G, pages); @@ -519,14 +513,16 @@ static unsigned long __init kernel_physical_mapping_init(unsigned long start, continue; } - pud = alloc_low_page(&pud_phys); + if (after_bootmem) + pud = pud_offset(pgd, start & PGDIR_MASK); + else + pud = alloc_low_page(&pud_phys); + last_map_addr = phys_pud_init(pud, __pa(start), __pa(next), page_size_mask); unmap_low_page(pud); - - spin_lock(&init_mm.page_table_lock); - pgd_populate(&init_mm, pgd, __va(pud_phys)); - spin_unlock(&init_mm.page_table_lock); + pgd_populate(&init_mm, pgd_offset_k(start), + __va(pud_phys)); } return last_map_addr; diff --git a/trunk/arch/x86/mm/ioremap.c b/trunk/arch/x86/mm/ioremap.c index d4b6e6a29ae3..6ba6f889c79d 100644 --- a/trunk/arch/x86/mm/ioremap.c +++ b/trunk/arch/x86/mm/ioremap.c @@ -553,11 +553,13 @@ static int __init check_early_ioremap_leak(void) { if (!early_ioremap_nested) return 0; - WARN(1, KERN_WARNING + + printk(KERN_WARNING "Debug warning: early ioremap leak of %d areas detected.\n", - early_ioremap_nested); + early_ioremap_nested); printk(KERN_WARNING - "please boot with early_ioremap_debug and report the dmesg.\n"); + "please boot with early_ioremap_debug and report the dmesg.\n"); + WARN_ON(1); return 1; } diff --git a/trunk/arch/x86/mm/mmio-mod.c b/trunk/arch/x86/mm/mmio-mod.c index 635b50e85581..e7397e108beb 100644 --- a/trunk/arch/x86/mm/mmio-mod.c +++ b/trunk/arch/x86/mm/mmio-mod.c @@ -430,9 +430,7 @@ static void enter_uniprocessor(void) "may miss events.\n"); } -/* __ref because leave_uniprocessor calls cpu_up which is __cpuinit, - but this whole function is ifdefed CONFIG_HOTPLUG_CPU */ -static void __ref leave_uniprocessor(void) +static void leave_uniprocessor(void) { int cpu; int err; diff --git a/trunk/arch/x86/mm/pageattr.c b/trunk/arch/x86/mm/pageattr.c index 43e2f8483e4f..f5f5154ea11e 100644 --- a/trunk/arch/x86/mm/pageattr.c +++ b/trunk/arch/x86/mm/pageattr.c @@ -849,7 +849,7 @@ int set_memory_uc(unsigned long addr, int numpages) /* * for now UC MINUS. see comments in ioremap_nocache() */ - if (reserve_memtype(__pa(addr), __pa(addr) + numpages * PAGE_SIZE, + if (reserve_memtype(addr, addr + numpages * PAGE_SIZE, _PAGE_CACHE_UC_MINUS, NULL)) return -EINVAL; @@ -868,7 +868,7 @@ int set_memory_wc(unsigned long addr, int numpages) if (!pat_enabled) return set_memory_uc(addr, numpages); - if (reserve_memtype(__pa(addr), __pa(addr) + numpages * PAGE_SIZE, + if (reserve_memtype(addr, addr + numpages * PAGE_SIZE, _PAGE_CACHE_WC, NULL)) return -EINVAL; @@ -884,7 +884,7 @@ int _set_memory_wb(unsigned long addr, int numpages) int set_memory_wb(unsigned long addr, int numpages) { - free_memtype(__pa(addr), __pa(addr) + numpages * PAGE_SIZE); + free_memtype(addr, addr + numpages * PAGE_SIZE); return _set_memory_wb(addr, numpages); } diff --git a/trunk/arch/x86/mm/pat.c b/trunk/arch/x86/mm/pat.c index 2a50e0fa64a5..2fe30916d4b6 100644 --- a/trunk/arch/x86/mm/pat.c +++ b/trunk/arch/x86/mm/pat.c @@ -207,9 +207,6 @@ static int chk_conflict(struct memtype *new, struct memtype *entry, return -EBUSY; } -static struct memtype *cached_entry; -static u64 cached_start; - /* * req_type typically has one of the: * - _PAGE_CACHE_WB @@ -283,17 +280,11 @@ int reserve_memtype(u64 start, u64 end, unsigned long req_type, spin_lock(&memtype_lock); - if (cached_entry && start >= cached_start) - entry = cached_entry; - else - entry = list_entry(&memtype_list, struct memtype, nd); - /* Search for existing mapping that overlaps the current range */ where = NULL; - list_for_each_entry_continue(entry, &memtype_list, nd) { + list_for_each_entry(entry, &memtype_list, nd) { if (end <= entry->start) { where = entry->nd.prev; - cached_entry = list_entry(where, struct memtype, nd); break; } else if (start <= entry->start) { /* end > entry->start */ err = chk_conflict(new, entry, new_type); @@ -301,8 +292,6 @@ int reserve_memtype(u64 start, u64 end, unsigned long req_type, dprintk("Overlap at 0x%Lx-0x%Lx\n", entry->start, entry->end); where = entry->nd.prev; - cached_entry = list_entry(where, - struct memtype, nd); } break; } else if (start < entry->end) { /* start > entry->start */ @@ -310,20 +299,7 @@ int reserve_memtype(u64 start, u64 end, unsigned long req_type, if (!err) { dprintk("Overlap at 0x%Lx-0x%Lx\n", entry->start, entry->end); - cached_entry = list_entry(entry->nd.prev, - struct memtype, nd); - - /* - * Move to right position in the linked - * list to add this new entry - */ - list_for_each_entry_continue(entry, - &memtype_list, nd) { - if (start <= entry->start) { - where = entry->nd.prev; - break; - } - } + where = &entry->nd; } break; } @@ -338,8 +314,6 @@ int reserve_memtype(u64 start, u64 end, unsigned long req_type, return err; } - cached_start = start; - if (where) list_add(&new->nd, where); else @@ -369,9 +343,6 @@ int free_memtype(u64 start, u64 end) spin_lock(&memtype_lock); list_for_each_entry(entry, &memtype_list, nd) { if (entry->start == start && entry->end == end) { - if (cached_entry == entry || cached_start == start) - cached_entry = NULL; - list_del(&entry->nd); kfree(entry); err = 0; @@ -390,6 +361,14 @@ int free_memtype(u64 start, u64 end) } +/* + * /dev/mem mmap interface. The memtype used for mapping varies: + * - Use UC for mappings with O_SYNC flag + * - Without O_SYNC flag, if there is any conflict in reserve_memtype, + * inherit the memtype from existing mapping. + * - Else use UC_MINUS memtype (for backward compatibility with existing + * X drivers. + */ pgprot_t phys_mem_access_prot(struct file *file, unsigned long pfn, unsigned long size, pgprot_t vma_prot) { @@ -427,14 +406,14 @@ int phys_mem_access_prot_allowed(struct file *file, unsigned long pfn, unsigned long size, pgprot_t *vma_prot) { u64 offset = ((u64) pfn) << PAGE_SHIFT; - unsigned long flags = -1; + unsigned long flags = _PAGE_CACHE_UC_MINUS; int retval; if (!range_is_allowed(pfn, size)) return 0; if (file->f_flags & O_SYNC) { - flags = _PAGE_CACHE_UC_MINUS; + flags = _PAGE_CACHE_UC; } #ifdef CONFIG_X86_32 @@ -457,14 +436,13 @@ int phys_mem_access_prot_allowed(struct file *file, unsigned long pfn, #endif /* - * With O_SYNC, we can only take UC_MINUS mapping. Fail if we cannot. - * + * With O_SYNC, we can only take UC mapping. Fail if we cannot. * Without O_SYNC, we want to get * - WB for WB-able memory and no other conflicting mappings * - UC_MINUS for non-WB-able memory with no other conflicting mappings * - Inherit from confliting mappings otherwise */ - if (flags != -1) { + if (flags != _PAGE_CACHE_UC_MINUS) { retval = reserve_memtype(offset, offset + size, flags, NULL); } else { retval = reserve_memtype(offset, offset + size, -1, &flags); diff --git a/trunk/arch/x86/oprofile/nmi_int.c b/trunk/arch/x86/oprofile/nmi_int.c index 0227694f7dab..3f90289410e6 100644 --- a/trunk/arch/x86/oprofile/nmi_int.c +++ b/trunk/arch/x86/oprofile/nmi_int.c @@ -15,7 +15,6 @@ #include #include #include -#include #include #include #include @@ -29,48 +28,23 @@ static DEFINE_PER_CPU(unsigned long, saved_lvtpc); static int nmi_start(void); static void nmi_stop(void); -static void nmi_cpu_start(void *dummy); -static void nmi_cpu_stop(void *dummy); /* 0 == registered but off, 1 == registered and on */ static int nmi_enabled = 0; -#ifdef CONFIG_SMP -static int oprofile_cpu_notifier(struct notifier_block *b, unsigned long action, - void *data) -{ - int cpu = (unsigned long)data; - switch (action) { - case CPU_DOWN_FAILED: - case CPU_ONLINE: - smp_call_function_single(cpu, nmi_cpu_start, NULL, 0); - break; - case CPU_DOWN_PREPARE: - smp_call_function_single(cpu, nmi_cpu_stop, NULL, 1); - break; - } - return NOTIFY_DONE; -} - -static struct notifier_block oprofile_cpu_nb = { - .notifier_call = oprofile_cpu_notifier -}; -#endif - #ifdef CONFIG_PM static int nmi_suspend(struct sys_device *dev, pm_message_t state) { - /* Only one CPU left, just stop that one */ if (nmi_enabled == 1) - nmi_cpu_stop(NULL); + nmi_stop(); return 0; } static int nmi_resume(struct sys_device *dev) { if (nmi_enabled == 1) - nmi_cpu_start(NULL); + nmi_start(); return 0; } @@ -489,9 +463,6 @@ int __init op_nmi_init(struct oprofile_operations *ops) } init_sysfs(); -#ifdef CONFIG_SMP - register_cpu_notifier(&oprofile_cpu_nb); -#endif using_nmi = 1; ops->create_files = nmi_create_files; ops->setup = nmi_setup; @@ -505,10 +476,6 @@ int __init op_nmi_init(struct oprofile_operations *ops) void op_nmi_exit(void) { - if (using_nmi) { + if (using_nmi) exit_sysfs(); -#ifdef CONFIG_SMP - unregister_cpu_notifier(&oprofile_cpu_nb); -#endif - } } diff --git a/trunk/arch/x86/pci/amd_bus.c b/trunk/arch/x86/pci/amd_bus.c index 6a0fca78c362..dbf532369711 100644 --- a/trunk/arch/x86/pci/amd_bus.c +++ b/trunk/arch/x86/pci/amd_bus.c @@ -1,7 +1,6 @@ #include #include #include -#include #include "pci.h" #ifdef CONFIG_X86_64 @@ -556,17 +555,15 @@ static int __init early_fill_mp_bus_info(void) return 0; } -#else /* !CONFIG_X86_64 */ +postcore_initcall(early_fill_mp_bus_info); -static int __init early_fill_mp_bus_info(void) { return 0; } - -#endif /* !CONFIG_X86_64 */ +#endif /* common 32/64 bit code */ #define ENABLE_CF8_EXT_CFG (1ULL << 46) -static void enable_pci_io_ecs(void *unused) +static void enable_pci_io_ecs_per_cpu(void *unused) { u64 reg; rdmsrl(MSR_AMD64_NB_CFG, reg); @@ -576,51 +573,14 @@ static void enable_pci_io_ecs(void *unused) } } -static int __cpuinit amd_cpu_notify(struct notifier_block *self, - unsigned long action, void *hcpu) +static int __init enable_pci_io_ecs(void) { - int cpu = (long)hcpu; - switch(action) { - case CPU_ONLINE: - case CPU_ONLINE_FROZEN: - smp_call_function_single(cpu, enable_pci_io_ecs, NULL, 0); - break; - default: - break; - } - return NOTIFY_OK; -} - -static struct notifier_block __cpuinitdata amd_cpu_notifier = { - .notifier_call = amd_cpu_notify, -}; - -static int __init pci_io_ecs_init(void) -{ - int cpu; - /* assume all cpus from fam10h have IO ECS */ if (boot_cpu_data.x86 < 0x10) return 0; - - register_cpu_notifier(&amd_cpu_notifier); - for_each_online_cpu(cpu) - amd_cpu_notify(&amd_cpu_notifier, (unsigned long)CPU_ONLINE, - (void *)(long)cpu); + on_each_cpu(enable_pci_io_ecs_per_cpu, NULL, 1); pci_probe |= PCI_HAS_IO_ECS; - - return 0; -} - -static int __init amd_postcore_init(void) -{ - if (boot_cpu_data.x86_vendor != X86_VENDOR_AMD) - return 0; - - early_fill_mp_bus_info(); - pci_io_ecs_init(); - return 0; } -postcore_initcall(amd_postcore_init); +postcore_initcall(enable_pci_io_ecs); diff --git a/trunk/arch/x86/pci/i386.c b/trunk/arch/x86/pci/i386.c index d765da913842..5807d1bc73f7 100644 --- a/trunk/arch/x86/pci/i386.c +++ b/trunk/arch/x86/pci/i386.c @@ -31,11 +31,8 @@ #include #include #include -#include #include -#include -#include #include "pci.h" @@ -80,77 +77,6 @@ pcibios_align_resource(void *data, struct resource *res, } EXPORT_SYMBOL(pcibios_align_resource); -static int check_res_with_valid(struct pci_dev *dev, struct resource *res) -{ - unsigned long base; - unsigned long size; - int i; - - base = res->start; - size = (res->start == 0 && res->end == res->start) ? 0 : - (res->end - res->start + 1); - - if (!base || !size) - return 0; - -#ifdef CONFIG_HPET_TIMER - /* for hpet */ - if (base == hpet_address && (res->flags & IORESOURCE_MEM)) { - dev_info(&dev->dev, "BAR has HPET at %08lx-%08lx\n", - base, base + size - 1); - return 1; - } -#endif - -#ifdef CONFIG_X86_IO_APIC - for (i = 0; i < nr_ioapics; i++) { - unsigned long ioapic_phys = mp_ioapics[i].mp_apicaddr; - - if (base == ioapic_phys && (res->flags & IORESOURCE_MEM)) { - dev_info(&dev->dev, "BAR has ioapic at %08lx-%08lx\n", - base, base + size - 1); - return 1; - } - } -#endif - -#ifdef CONFIG_PCI_MMCONFIG - for (i = 0; i < pci_mmcfg_config_num; i++) { - unsigned long addr; - - addr = pci_mmcfg_config[i].address; - if (base == addr && (res->flags & IORESOURCE_MEM)) { - dev_info(&dev->dev, "BAR has MMCONFIG at %08lx-%08lx\n", - base, base + size - 1); - return 1; - } - } -#endif - - return 0; -} - -static int check_platform(struct pci_dev *dev, struct resource *res) -{ - struct resource *root = NULL; - - /* - * forcibly insert it into the - * resource tree - */ - if (res->flags & IORESOURCE_MEM) - root = &iomem_resource; - else if (res->flags & IORESOURCE_IO) - root = &ioport_resource; - - if (root && check_res_with_valid(dev, res)) { - insert_resource(root, res); - - return 1; - } - - return 0; -} /* * Handle resources of PCI devices. If the world were perfect, we could * just allocate all the resource regions and do nothing more. It isn't. @@ -202,8 +128,6 @@ static void __init pcibios_allocate_bus_resources(struct list_head *bus_list) pr = pci_find_parent_resource(dev, r); if (!r->start || !pr || request_resource(pr, r) < 0) { - if (check_platform(dev, r)) - continue; dev_err(&dev->dev, "BAR %d: can't " "allocate resource\n", idx); /* @@ -247,8 +171,6 @@ static void __init pcibios_allocate_resources(int pass) r->flags, disabled, pass); pr = pci_find_parent_resource(dev, r); if (!pr || request_resource(pr, r) < 0) { - if (check_platform(dev, r)) - continue; dev_err(&dev->dev, "BAR %d: can't " "allocate resource\n", idx); /* We'll assign a new address later */ diff --git a/trunk/block/genhd.c b/trunk/block/genhd.c index 656c2c7abf99..c13cc77291af 100644 --- a/trunk/block/genhd.c +++ b/trunk/block/genhd.c @@ -293,30 +293,27 @@ void __init printk_all_partitions(void) /* iterator */ static int find_start(struct device *dev, void *data) { - loff_t *k = data; + loff_t k = *(loff_t *)data; if (dev->type != &disk_type) return 0; - if (!*k) + if (!k--) return 1; - (*k)--; return 0; } static void *part_start(struct seq_file *part, loff_t *pos) { struct device *dev; - loff_t k = *pos; + loff_t n = *pos; - if (!k) + if (!n) seq_puts(part, "major minor #blocks name\n\n"); mutex_lock(&block_class_lock); - dev = class_find_device(&block_class, NULL, &k, find_start); - if (dev) { - put_device(dev); + dev = class_find_device(&block_class, NULL, (void *)pos, find_start); + if (dev) return dev_to_disk(dev); - } return NULL; } @@ -333,10 +330,8 @@ static void *part_next(struct seq_file *part, void *v, loff_t *pos) struct device *dev; ++*pos; dev = class_find_device(&block_class, &gp->dev, NULL, find_next); - if (dev) { - put_device(dev); + if (dev) return dev_to_disk(dev); - } return NULL; } @@ -573,14 +568,11 @@ static struct device_type disk_type = { static void *diskstats_start(struct seq_file *part, loff_t *pos) { struct device *dev; - loff_t k = *pos; mutex_lock(&block_class_lock); - dev = class_find_device(&block_class, NULL, &k, find_start); - if (dev) { - put_device(dev); + dev = class_find_device(&block_class, NULL, (void *)pos, find_start); + if (dev) return dev_to_disk(dev); - } return NULL; } @@ -591,10 +583,8 @@ static void *diskstats_next(struct seq_file *part, void *v, loff_t *pos) ++*pos; dev = class_find_device(&block_class, &gp->dev, NULL, find_next); - if (dev) { - put_device(dev); + if (dev) return dev_to_disk(dev); - } return NULL; } @@ -722,12 +712,10 @@ dev_t blk_lookup_devt(const char *name, int part) mutex_lock(&block_class_lock); find.name = name; find.part = part; - dev = class_find_device(&block_class, NULL, &find, match_id); - if (dev) { - put_device(dev); + dev = class_find_device(&block_class, NULL, (void *)&find, match_id); + if (dev) devt = MKDEV(MAJOR(dev->devt), MINOR(dev->devt) + part); - } mutex_unlock(&block_class_lock); return devt; diff --git a/trunk/crypto/authenc.c b/trunk/crypto/authenc.c index fd9f06c63d76..4b226768752a 100644 --- a/trunk/crypto/authenc.c +++ b/trunk/crypto/authenc.c @@ -174,9 +174,8 @@ static int crypto_authenc_genicv(struct aead_request *req, u8 *iv, static void crypto_authenc_encrypt_done(struct crypto_async_request *req, int err) { - struct aead_request *areq = req->data; - if (!err) { + struct aead_request *areq = req->data; struct crypto_aead *authenc = crypto_aead_reqtfm(areq); struct crypto_authenc_ctx *ctx = crypto_aead_ctx(authenc); struct ablkcipher_request *abreq = aead_request_ctx(areq); @@ -186,7 +185,7 @@ static void crypto_authenc_encrypt_done(struct crypto_async_request *req, err = crypto_authenc_genicv(areq, iv, 0); } - aead_request_complete(areq, err); + aead_request_complete(req->data, err); } static int crypto_authenc_encrypt(struct aead_request *req) @@ -217,15 +216,14 @@ static int crypto_authenc_encrypt(struct aead_request *req) static void crypto_authenc_givencrypt_done(struct crypto_async_request *req, int err) { - struct aead_request *areq = req->data; - if (!err) { + struct aead_request *areq = req->data; struct skcipher_givcrypt_request *greq = aead_request_ctx(areq); err = crypto_authenc_genicv(areq, greq->giv, 0); } - aead_request_complete(areq, err); + aead_request_complete(req->data, err); } static int crypto_authenc_givencrypt(struct aead_givcrypt_request *req) diff --git a/trunk/drivers/ata/ahci.c b/trunk/drivers/ata/ahci.c index c729e6988bbb..ef3e5522e1a4 100644 --- a/trunk/drivers/ata/ahci.c +++ b/trunk/drivers/ata/ahci.c @@ -486,8 +486,6 @@ static const struct pci_device_id ahci_pci_tbl[] = { { PCI_VDEVICE(INTEL, 0x502b), board_ahci }, /* Tolapai */ { PCI_VDEVICE(INTEL, 0x3a05), board_ahci }, /* ICH10 */ { PCI_VDEVICE(INTEL, 0x3a25), board_ahci }, /* ICH10 */ - { PCI_VDEVICE(INTEL, 0x3b24), board_ahci }, /* PCH RAID */ - { PCI_VDEVICE(INTEL, 0x3b2b), board_ahci }, /* PCH RAID */ /* JMicron 360/1/3/5/6, match class to avoid IDE function */ { PCI_VENDOR_ID_JMICRON, PCI_ANY_ID, PCI_ANY_ID, PCI_ANY_ID, @@ -577,9 +575,9 @@ static const struct pci_device_id ahci_pci_tbl[] = { { PCI_VDEVICE(NVIDIA, 0x0bc7), board_ahci }, /* MCP7B */ /* SiS */ - { PCI_VDEVICE(SI, 0x1184), board_ahci }, /* SiS 966 */ - { PCI_VDEVICE(SI, 0x1185), board_ahci }, /* SiS 968 */ - { PCI_VDEVICE(SI, 0x0186), board_ahci }, /* SiS 968 */ + { PCI_VDEVICE(SI, 0x1184), board_ahci_nopmp }, /* SiS 966 */ + { PCI_VDEVICE(SI, 0x1185), board_ahci_nopmp }, /* SiS 968 */ + { PCI_VDEVICE(SI, 0x0186), board_ahci_nopmp }, /* SiS 968 */ /* Marvell */ { PCI_VDEVICE(MARVELL, 0x6145), board_ahci_mv }, /* 6145 */ diff --git a/trunk/drivers/ata/ata_piix.c b/trunk/drivers/ata/ata_piix.c index b1d08a8f5003..c294121fd69e 100644 --- a/trunk/drivers/ata/ata_piix.c +++ b/trunk/drivers/ata/ata_piix.c @@ -275,14 +275,6 @@ static const struct pci_device_id piix_pci_tbl[] = { { 0x8086, 0x3a20, PCI_ANY_ID, PCI_ANY_ID, 0, 0, ich8_sata }, /* SATA Controller IDE (ICH10) */ { 0x8086, 0x3a26, PCI_ANY_ID, PCI_ANY_ID, 0, 0, ich8_2port_sata }, - /* SATA Controller IDE (PCH) */ - { 0x8086, 0x3b20, PCI_ANY_ID, PCI_ANY_ID, 0, 0, ich8_sata }, - /* SATA Controller IDE (PCH) */ - { 0x8086, 0x3b26, PCI_ANY_ID, PCI_ANY_ID, 0, 0, ich8_2port_sata }, - /* SATA Controller IDE (PCH) */ - { 0x8086, 0x3b2d, PCI_ANY_ID, PCI_ANY_ID, 0, 0, ich8_2port_sata }, - /* SATA Controller IDE (PCH) */ - { 0x8086, 0x3b2e, PCI_ANY_ID, PCI_ANY_ID, 0, 0, ich8_sata }, { } /* terminate list */ }; diff --git a/trunk/drivers/ata/libata-core.c b/trunk/drivers/ata/libata-core.c index 79e3a8e7a84a..5ba96c5052c8 100644 --- a/trunk/drivers/ata/libata-core.c +++ b/trunk/drivers/ata/libata-core.c @@ -104,7 +104,6 @@ struct ata_force_param { unsigned long xfer_mask; unsigned int horkage_on; unsigned int horkage_off; - unsigned int lflags; }; struct ata_force_ent { @@ -197,23 +196,22 @@ void ata_force_cbl(struct ata_port *ap) } /** - * ata_force_link_limits - force link limits according to libata.force + * ata_force_spd_limit - force SATA spd limit according to libata.force * @link: ATA link of interest * - * Force link flags and SATA spd limit according to libata.force - * and whine about it. When only the port part is specified - * (e.g. 1:), the limit applies to all links connected to both - * the host link and all fan-out ports connected via PMP. If the - * device part is specified as 0 (e.g. 1.00:), it specifies the - * first fan-out link not the host link. Device number 15 always - * points to the host link whether PMP is attached or not. + * Force SATA spd limit according to libata.force and whine about + * it. When only the port part is specified (e.g. 1:), the limit + * applies to all links connected to both the host link and all + * fan-out ports connected via PMP. If the device part is + * specified as 0 (e.g. 1.00:), it specifies the first fan-out + * link not the host link. Device number 15 always points to the + * host link whether PMP is attached or not. * * LOCKING: * EH context. */ -static void ata_force_link_limits(struct ata_link *link) +static void ata_force_spd_limit(struct ata_link *link) { - bool did_spd = false; int linkno, i; if (ata_is_host_link(link)) @@ -230,22 +228,13 @@ static void ata_force_link_limits(struct ata_link *link) if (fe->device != -1 && fe->device != linkno) continue; - /* only honor the first spd limit */ - if (!did_spd && fe->param.spd_limit) { - link->hw_sata_spd_limit = (1 << fe->param.spd_limit) - 1; - ata_link_printk(link, KERN_NOTICE, - "FORCE: PHY spd limit set to %s\n", - fe->param.name); - did_spd = true; - } + if (!fe->param.spd_limit) + continue; - /* let lflags stack */ - if (fe->param.lflags) { - link->flags |= fe->param.lflags; - ata_link_printk(link, KERN_NOTICE, - "FORCE: link flag 0x%x forced -> 0x%x\n", - fe->param.lflags, link->flags); - } + link->hw_sata_spd_limit = (1 << fe->param.spd_limit) - 1; + ata_link_printk(link, KERN_NOTICE, + "FORCE: PHY spd limit set to %s\n", fe->param.name); + return; } } @@ -3288,7 +3277,7 @@ int ata_do_set_mode(struct ata_link *link, struct ata_device **r_failed_dev) dev->dma_mode = ata_xfer_mask2mode(dma_mask); found = 1; - if (ata_dma_enabled(dev)) + if (dev->dma_mode != 0xff) used_dma = 1; } if (!found) @@ -3313,7 +3302,7 @@ int ata_do_set_mode(struct ata_link *link, struct ata_device **r_failed_dev) /* step 3: set host DMA timings */ ata_link_for_each_dev(dev, link) { - if (!ata_dev_enabled(dev) || !ata_dma_enabled(dev)) + if (!ata_dev_enabled(dev) || dev->dma_mode == 0xff) continue; dev->xfer_mode = dev->dma_mode; @@ -5199,18 +5188,19 @@ void ata_link_init(struct ata_port *ap, struct ata_link *link, int pmp) */ int sata_link_init_spd(struct ata_link *link) { + u32 scontrol; u8 spd; int rc; - rc = sata_scr_read(link, SCR_CONTROL, &link->saved_scontrol); + rc = sata_scr_read(link, SCR_CONTROL, &scontrol); if (rc) return rc; - spd = (link->saved_scontrol >> 4) & 0xf; + spd = (scontrol >> 4) & 0xf; if (spd) link->hw_sata_spd_limit &= (1 << spd) - 1; - ata_force_link_limits(link); + ata_force_spd_limit(link); link->sata_spd_limit = link->hw_sata_spd_limit; @@ -5793,10 +5783,9 @@ static void ata_port_detach(struct ata_port *ap) ata_port_wait_eh(ap); /* EH is now guaranteed to see UNLOADING - EH context belongs - * to us. Restore SControl and disable all existing devices. + * to us. Disable all existing devices. */ - __ata_port_for_each_link(link, ap) { - sata_scr_write(link, SCR_CONTROL, link->saved_scontrol); + ata_port_for_each_link(link, ap) { ata_link_for_each_dev(dev, link) ata_dev_disable(dev); } @@ -6002,9 +5991,6 @@ static int __init ata_parse_force_one(char **cur, { "udma133", .xfer_mask = 1 << (ATA_SHIFT_UDMA + 6) }, { "udma/133", .xfer_mask = 1 << (ATA_SHIFT_UDMA + 6) }, { "udma7", .xfer_mask = 1 << (ATA_SHIFT_UDMA + 7) }, - { "nohrst", .lflags = ATA_LFLAG_NO_HRST }, - { "nosrst", .lflags = ATA_LFLAG_NO_SRST }, - { "norst", .lflags = ATA_LFLAG_NO_HRST | ATA_LFLAG_NO_SRST }, }; char *start = *cur, *p = *cur; char *id, *val, *endp; diff --git a/trunk/drivers/ata/libata-eh.c b/trunk/drivers/ata/libata-eh.c index c1db2f234d2e..58bdc538d229 100644 --- a/trunk/drivers/ata/libata-eh.c +++ b/trunk/drivers/ata/libata-eh.c @@ -2040,7 +2040,7 @@ static void ata_eh_link_report(struct ata_link *link) } if (ehc->i.serror) - ata_link_printk(link, KERN_ERR, + ata_port_printk(ap, KERN_ERR, "SError: { %s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s}\n", ehc->i.serror & SERR_DATA_RECOVERED ? "RecovData " : "", ehc->i.serror & SERR_COMM_RECOVERED ? "RecovComm " : "", @@ -2171,12 +2171,18 @@ static int ata_do_reset(struct ata_link *link, ata_reset_fn_t reset, } static int ata_eh_followup_srst_needed(struct ata_link *link, - int rc, const unsigned int *classes) + int rc, int classify, + const unsigned int *classes) { if ((link->flags & ATA_LFLAG_NO_SRST) || ata_link_offline(link)) return 0; - if (rc == -EAGAIN) - return 1; + if (rc == -EAGAIN) { + if (classify) + return 1; + rc = 0; + } + if (rc != 0) + return 0; if (sata_pmp_supported(link->ap) && ata_is_host_link(link)) return 1; return 0; @@ -2204,10 +2210,6 @@ int ata_eh_reset(struct ata_link *link, int classify, */ while (ata_eh_reset_timeouts[max_tries] != ULONG_MAX) max_tries++; - if (link->flags & ATA_LFLAG_NO_HRST) - hardreset = NULL; - if (link->flags & ATA_LFLAG_NO_SRST) - softreset = NULL; now = jiffies; deadline = ata_deadline(ehc->last_reset, ATA_EH_RESET_COOL_DOWN); @@ -2245,10 +2247,10 @@ int ata_eh_reset(struct ata_link *link, int classify, ehc->i.action &= ~ATA_EH_RESET; if (hardreset) { reset = hardreset; - ehc->i.action |= ATA_EH_HARDRESET; + ehc->i.action = ATA_EH_HARDRESET; } else if (softreset) { reset = softreset; - ehc->i.action |= ATA_EH_SOFTRESET; + ehc->i.action = ATA_EH_SOFTRESET; } if (prereset) { @@ -2303,11 +2305,9 @@ int ata_eh_reset(struct ata_link *link, int classify, ehc->i.flags |= ATA_EHI_DID_SOFTRESET; rc = ata_do_reset(link, reset, classes, deadline); - if (rc && rc != -EAGAIN) - goto fail; if (reset == hardreset && - ata_eh_followup_srst_needed(link, rc, classes)) { + ata_eh_followup_srst_needed(link, rc, classify, classes)) { /* okay, let's do follow-up softreset */ reset = softreset; @@ -2322,6 +2322,10 @@ int ata_eh_reset(struct ata_link *link, int classify, ata_eh_about_to_do(link, NULL, ATA_EH_RESET); rc = ata_do_reset(link, reset, classes, deadline); } + + /* -EAGAIN can happen if we skipped followup SRST */ + if (rc && rc != -EAGAIN) + goto fail; } else { if (verbose) ata_link_printk(link, KERN_INFO, "no reset method " diff --git a/trunk/drivers/ata/pata_acpi.c b/trunk/drivers/ata/pata_acpi.c index eb919c16a03e..fbe605711554 100644 --- a/trunk/drivers/ata/pata_acpi.c +++ b/trunk/drivers/ata/pata_acpi.c @@ -181,7 +181,7 @@ static unsigned int pacpi_qc_issue(struct ata_queued_cmd *qc) if (adev != acpi->last) { pacpi_set_piomode(ap, adev); - if (ata_dma_enabled(adev)) + if (adev->dma_mode) pacpi_set_dmamode(ap, adev); acpi->last = adev; } diff --git a/trunk/drivers/ata/pata_atiixp.c b/trunk/drivers/ata/pata_atiixp.c index e8a0d99d7356..d7de7baf58a8 100644 --- a/trunk/drivers/ata/pata_atiixp.c +++ b/trunk/drivers/ata/pata_atiixp.c @@ -183,7 +183,7 @@ static void atiixp_bmdma_start(struct ata_queued_cmd *qc) u16 tmp16; pci_read_config_word(pdev, ATIIXP_IDE_UDMA_CONTROL, &tmp16); - if (ata_using_udma(adev)) + if (adev->dma_mode >= XFER_UDMA_0) tmp16 |= (1 << dn); else tmp16 &= ~(1 << dn); diff --git a/trunk/drivers/ata/pata_cs5530.c b/trunk/drivers/ata/pata_cs5530.c index 0c4b271a9d5a..744beebaaf49 100644 --- a/trunk/drivers/ata/pata_cs5530.c +++ b/trunk/drivers/ata/pata_cs5530.c @@ -149,10 +149,10 @@ static unsigned int cs5530_qc_issue(struct ata_queued_cmd *qc) struct ata_device *prev = ap->private_data; /* See if the DMA settings could be wrong */ - if (ata_dma_enabled(adev) && adev != prev && prev != NULL) { + if (adev->dma_mode != 0 && adev != prev && prev != NULL) { /* Maybe, but do the channels match MWDMA/UDMA ? */ - if ((ata_using_udma(adev) && !ata_using_udma(prev)) || - (ata_using_udma(prev) && !ata_using_udma(adev))) + if ((adev->dma_mode >= XFER_UDMA_0 && prev->dma_mode < XFER_UDMA_0) || + (adev->dma_mode < XFER_UDMA_0 && prev->dma_mode >= XFER_UDMA_0)) /* Switch the mode bits */ cs5530_set_dmamode(ap, adev); } diff --git a/trunk/drivers/ata/pata_it821x.c b/trunk/drivers/ata/pata_it821x.c index 0221c9a46769..27843c70eb9d 100644 --- a/trunk/drivers/ata/pata_it821x.c +++ b/trunk/drivers/ata/pata_it821x.c @@ -606,7 +606,7 @@ static void it821x_display_disk(int n, u8 *buf) { unsigned char id[41]; int mode = 0; - char *mtype = ""; + char *mtype; char mbuf[8]; char *cbl = "(40 wire cable)"; diff --git a/trunk/drivers/ata/pata_oldpiix.c b/trunk/drivers/ata/pata_oldpiix.c index df64f2443001..e678af383d13 100644 --- a/trunk/drivers/ata/pata_oldpiix.c +++ b/trunk/drivers/ata/pata_oldpiix.c @@ -198,7 +198,7 @@ static unsigned int oldpiix_qc_issue(struct ata_queued_cmd *qc) if (adev != ap->private_data) { oldpiix_set_piomode(ap, adev); - if (ata_dma_enabled(adev)) + if (adev->dma_mode) oldpiix_set_dmamode(ap, adev); } return ata_sff_qc_issue(qc); diff --git a/trunk/drivers/ata/pata_sc1200.c b/trunk/drivers/ata/pata_sc1200.c index 0278fd2b8fb1..cbab397e3db7 100644 --- a/trunk/drivers/ata/pata_sc1200.c +++ b/trunk/drivers/ata/pata_sc1200.c @@ -167,10 +167,10 @@ static unsigned int sc1200_qc_issue(struct ata_queued_cmd *qc) struct ata_device *prev = ap->private_data; /* See if the DMA settings could be wrong */ - if (ata_dma_enabled(adev) && adev != prev && prev != NULL) { + if (adev->dma_mode != 0 && adev != prev && prev != NULL) { /* Maybe, but do the channels match MWDMA/UDMA ? */ - if ((ata_using_udma(adev) && !ata_using_udma(prev)) || - (ata_using_udma(prev) && !ata_using_udma(adev))) + if ((adev->dma_mode >= XFER_UDMA_0 && prev->dma_mode < XFER_UDMA_0) || + (adev->dma_mode < XFER_UDMA_0 && prev->dma_mode >= XFER_UDMA_0)) /* Switch the mode bits */ sc1200_set_dmamode(ap, adev); } diff --git a/trunk/drivers/ata/pata_via.c b/trunk/drivers/ata/pata_via.c index 8fdb2ce73210..57d951b11f2d 100644 --- a/trunk/drivers/ata/pata_via.c +++ b/trunk/drivers/ata/pata_via.c @@ -324,26 +324,62 @@ static void via_set_dmamode(struct ata_port *ap, struct ata_device *adev) } /** - * via_tf_load - send taskfile registers to host controller + * via_ata_sff_tf_load - send taskfile registers to host controller * @ap: Port to which output is sent * @tf: ATA taskfile register set * * Outputs ATA taskfile to standard ATA host controller. * * Note: This is to fix the internal bug of via chipsets, which - * will reset the device register after changing the IEN bit on - * ctl register + * will reset the device register after changing the IEN bit on + * ctl register */ -static void via_tf_load(struct ata_port *ap, const struct ata_taskfile *tf) +static void via_ata_tf_load(struct ata_port *ap, const struct ata_taskfile *tf) { - struct ata_taskfile tmp_tf; + struct ata_ioports *ioaddr = &ap->ioaddr; + unsigned int is_addr = tf->flags & ATA_TFLAG_ISADDR; + + if (tf->ctl != ap->last_ctl) { + iowrite8(tf->ctl, ioaddr->ctl_addr); + iowrite8(tf->device, ioaddr->device_addr); + ap->last_ctl = tf->ctl; + ata_wait_idle(ap); + } + + if (is_addr && (tf->flags & ATA_TFLAG_LBA48)) { + iowrite8(tf->hob_feature, ioaddr->feature_addr); + iowrite8(tf->hob_nsect, ioaddr->nsect_addr); + iowrite8(tf->hob_lbal, ioaddr->lbal_addr); + iowrite8(tf->hob_lbam, ioaddr->lbam_addr); + iowrite8(tf->hob_lbah, ioaddr->lbah_addr); + VPRINTK("hob: feat 0x%X nsect 0x%X, lba 0x%X 0x%X 0x%X\n", + tf->hob_feature, + tf->hob_nsect, + tf->hob_lbal, + tf->hob_lbam, + tf->hob_lbah); + } - if (ap->ctl != ap->last_ctl && !(tf->flags & ATA_TFLAG_DEVICE)) { - tmp_tf = *tf; - tmp_tf.flags |= ATA_TFLAG_DEVICE; - tf = &tmp_tf; + if (is_addr) { + iowrite8(tf->feature, ioaddr->feature_addr); + iowrite8(tf->nsect, ioaddr->nsect_addr); + iowrite8(tf->lbal, ioaddr->lbal_addr); + iowrite8(tf->lbam, ioaddr->lbam_addr); + iowrite8(tf->lbah, ioaddr->lbah_addr); + VPRINTK("feat 0x%X nsect 0x%X lba 0x%X 0x%X 0x%X\n", + tf->feature, + tf->nsect, + tf->lbal, + tf->lbam, + tf->lbah); } - ata_sff_tf_load(ap, tf); + + if (tf->flags & ATA_TFLAG_DEVICE) { + iowrite8(tf->device, ioaddr->device_addr); + VPRINTK("device 0x%X\n", tf->device); + } + + ata_wait_idle(ap); } static struct scsi_host_template via_sht = { @@ -356,12 +392,13 @@ static struct ata_port_operations via_port_ops = { .set_piomode = via_set_piomode, .set_dmamode = via_set_dmamode, .prereset = via_pre_reset, - .sff_tf_load = via_tf_load, + .sff_tf_load = via_ata_tf_load, }; static struct ata_port_operations via_port_ops_noirq = { .inherits = &via_port_ops, .sff_data_xfer = ata_sff_data_xfer_noirq, + .sff_tf_load = via_ata_tf_load, }; /** diff --git a/trunk/drivers/ata/sata_mv.c b/trunk/drivers/ata/sata_mv.c index 13c1d2af18ac..ad169ffbc4cb 100644 --- a/trunk/drivers/ata/sata_mv.c +++ b/trunk/drivers/ata/sata_mv.c @@ -1134,16 +1134,30 @@ static int mv_qc_defer(struct ata_queued_cmd *qc) if (ap->nr_active_links == 0) return 0; - /* - * The port is operating in host queuing mode (EDMA) with NCQ - * enabled, allow multiple NCQ commands. EDMA also allows - * queueing multiple DMA commands but libata core currently - * doesn't allow it. - */ - if ((pp->pp_flags & MV_PP_FLAG_EDMA_EN) && - (pp->pp_flags & MV_PP_FLAG_NCQ_EN) && ata_is_ncq(qc->tf.protocol)) - return 0; - + if (pp->pp_flags & MV_PP_FLAG_EDMA_EN) { + /* + * The port is operating in host queuing mode (EDMA). + * It can accomodate a new qc if the qc protocol + * is compatible with the current host queue mode. + */ + if (pp->pp_flags & MV_PP_FLAG_NCQ_EN) { + /* + * The host queue (EDMA) is in NCQ mode. + * If the new qc is also an NCQ command, + * then allow the new qc. + */ + if (qc->tf.protocol == ATA_PROT_NCQ) + return 0; + } else { + /* + * The host queue (EDMA) is in non-NCQ, DMA mode. + * If the new qc is also a non-NCQ, DMA command, + * then allow the new qc. + */ + if (qc->tf.protocol == ATA_PROT_DMA) + return 0; + } + } return ATA_DEFER_PORT; } @@ -3022,8 +3036,7 @@ static int mv_chip_id(struct ata_host *host, unsigned int board_idx) break; case chip_soc: hpriv->ops = &mv_soc_ops; - hp_flags |= MV_HP_FLAG_SOC | MV_HP_GEN_IIE | - MV_HP_ERRATA_60X1C0; + hp_flags |= MV_HP_FLAG_SOC | MV_HP_ERRATA_60X1C0; break; default: diff --git a/trunk/drivers/atm/adummy.c b/trunk/drivers/atm/adummy.c index 5effec6f5458..2ebd07f2ef81 100644 --- a/trunk/drivers/atm/adummy.c +++ b/trunk/drivers/atm/adummy.c @@ -3,6 +3,7 @@ */ #include +#include #include #include #include diff --git a/trunk/drivers/base/class.c b/trunk/drivers/base/class.c index cc5e28c8885c..5667c2f02c51 100644 --- a/trunk/drivers/base/class.c +++ b/trunk/drivers/base/class.c @@ -295,12 +295,6 @@ int class_for_each_device(struct class *class, struct device *start, if (!class) return -EINVAL; - if (!class->p) { - WARN(1, "%s called for class '%s' before it was initialized", - __func__, class->name); - return -EINVAL; - } - mutex_lock(&class->p->class_mutex); list_for_each_entry(dev, &class->p->class_devices, node) { if (start) { @@ -350,11 +344,6 @@ struct device *class_find_device(struct class *class, struct device *start, if (!class) return NULL; - if (!class->p) { - WARN(1, "%s called for class '%s' before it was initialized", - __func__, class->name); - return NULL; - } mutex_lock(&class->p->class_mutex); list_for_each_entry(dev, &class->p->class_devices, node) { diff --git a/trunk/drivers/base/core.c b/trunk/drivers/base/core.c index d021c98605b3..068aa1c9538c 100644 --- a/trunk/drivers/base/core.c +++ b/trunk/drivers/base/core.c @@ -53,7 +53,7 @@ static inline int device_is_not_partition(struct device *dev) * it is attached to. If it is not attached to a bus either, an empty * string will be returned. */ -const char *dev_driver_string(const struct device *dev) +const char *dev_driver_string(struct device *dev) { return dev->driver ? dev->driver->name : (dev->bus ? dev->bus->name : @@ -541,7 +541,6 @@ void device_initialize(struct device *dev) spin_lock_init(&dev->devres_lock); INIT_LIST_HEAD(&dev->devres_head); device_init_wakeup(dev, 0); - device_pm_init(dev); set_dev_node(dev, -1); } @@ -844,19 +843,13 @@ int device_add(struct device *dev) { struct device *parent = NULL; struct class_interface *class_intf; - int error = -EINVAL; + int error; dev = get_device(dev); - if (!dev) - goto done; - - /* Temporarily support init_name if it is set. - * It will override bus_id for now */ - if (dev->init_name) - dev_set_name(dev, "%s", dev->init_name); - - if (!strlen(dev->bus_id)) - goto done; + if (!dev || !strlen(dev->bus_id)) { + error = -EINVAL; + goto Done; + } pr_debug("device: '%s': %s\n", dev->bus_id, __func__); @@ -904,10 +897,9 @@ int device_add(struct device *dev) error = bus_add_device(dev); if (error) goto BusError; - error = dpm_sysfs_add(dev); + error = device_pm_add(dev); if (error) - goto DPMError; - device_pm_add(dev); + goto PMError; kobject_uevent(&dev->kobj, KOBJ_ADD); bus_attach_device(dev); if (parent) @@ -925,10 +917,10 @@ int device_add(struct device *dev) class_intf->add_dev(dev, class_intf); mutex_unlock(&dev->class->p->class_mutex); } -done: + Done: put_device(dev); return error; - DPMError: + PMError: bus_remove_device(dev); BusError: if (dev->bus) @@ -952,7 +944,7 @@ int device_add(struct device *dev) cleanup_device_parent(dev); if (parent) put_device(parent); - goto done; + goto Done; } /** @@ -1015,7 +1007,6 @@ void device_del(struct device *dev) struct class_interface *class_intf; device_pm_remove(dev); - dpm_sysfs_remove(dev); if (parent) klist_del(&dev->knode_parent); if (MAJOR(dev->devt)) { diff --git a/trunk/drivers/base/driver.c b/trunk/drivers/base/driver.c index 1e2bda780e48..2ef5acf4368b 100644 --- a/trunk/drivers/base/driver.c +++ b/trunk/drivers/base/driver.c @@ -16,6 +16,9 @@ #include #include "base.h" +#define to_dev(node) container_of(node, struct device, driver_list) + + static struct device *next_device(struct klist_iter *i) { struct klist_node *n = klist_next(i); diff --git a/trunk/drivers/base/power/main.c b/trunk/drivers/base/power/main.c index 273a944d4040..3250c5257b74 100644 --- a/trunk/drivers/base/power/main.c +++ b/trunk/drivers/base/power/main.c @@ -67,16 +67,20 @@ void device_pm_unlock(void) * device_pm_add - add a device to the list of active devices * @dev: Device to be added to the list */ -void device_pm_add(struct device *dev) +int device_pm_add(struct device *dev) { + int error; + pr_debug("PM: Adding info for %s:%s\n", dev->bus ? dev->bus->name : "No Bus", kobject_name(&dev->kobj)); mutex_lock(&dpm_list_mtx); if (dev->parent) { - if (dev->parent->power.status >= DPM_SUSPENDING) - dev_warn(dev, "parent %s should not be sleeping\n", + if (dev->parent->power.status >= DPM_SUSPENDING) { + dev_warn(dev, "parent %s is sleeping, will not add\n", dev->parent->bus_id); + WARN_ON(true); + } } else if (transition_started) { /* * We refuse to register parentless devices while a PM @@ -85,9 +89,13 @@ void device_pm_add(struct device *dev) */ WARN_ON(true); } - - list_add_tail(&dev->power.entry, &dpm_list); + error = dpm_sysfs_add(dev); + if (!error) { + dev->power.status = DPM_ON; + list_add_tail(&dev->power.entry, &dpm_list); + } mutex_unlock(&dpm_list_mtx); + return error; } /** @@ -102,6 +110,7 @@ void device_pm_remove(struct device *dev) dev->bus ? dev->bus->name : "No Bus", kobject_name(&dev->kobj)); mutex_lock(&dpm_list_mtx); + dpm_sysfs_remove(dev); list_del_init(&dev->power.entry); mutex_unlock(&dpm_list_mtx); } diff --git a/trunk/drivers/base/power/power.h b/trunk/drivers/base/power/power.h index 41f51fae042f..a3252c0e2887 100644 --- a/trunk/drivers/base/power/power.h +++ b/trunk/drivers/base/power/power.h @@ -1,8 +1,3 @@ -static inline void device_pm_init(struct device *dev) -{ - dev->power.status = DPM_ON; -} - #ifdef CONFIG_PM_SLEEP /* @@ -16,12 +11,12 @@ static inline struct device *to_device(struct list_head *entry) return container_of(entry, struct device, power.entry); } -extern void device_pm_add(struct device *); +extern int device_pm_add(struct device *); extern void device_pm_remove(struct device *); #else /* CONFIG_PM_SLEEP */ -static inline void device_pm_add(struct device *dev) {} +static inline int device_pm_add(struct device *dev) { return 0; } static inline void device_pm_remove(struct device *dev) {} #endif diff --git a/trunk/drivers/char/xilinx_hwicap/buffer_icap.h b/trunk/drivers/char/xilinx_hwicap/buffer_icap.h index 8b0252bf06e2..c5b1840906b2 100644 --- a/trunk/drivers/char/xilinx_hwicap/buffer_icap.h +++ b/trunk/drivers/char/xilinx_hwicap/buffer_icap.h @@ -38,6 +38,7 @@ #include #include +#include #include #include diff --git a/trunk/drivers/char/xilinx_hwicap/fifo_icap.h b/trunk/drivers/char/xilinx_hwicap/fifo_icap.h index 62bda453c90b..ffabd3ba2bd8 100644 --- a/trunk/drivers/char/xilinx_hwicap/fifo_icap.h +++ b/trunk/drivers/char/xilinx_hwicap/fifo_icap.h @@ -38,6 +38,7 @@ #include #include +#include #include #include diff --git a/trunk/drivers/char/xilinx_hwicap/xilinx_hwicap.h b/trunk/drivers/char/xilinx_hwicap/xilinx_hwicap.h index 24d0d9b938fb..1f9c8b082dbe 100644 --- a/trunk/drivers/char/xilinx_hwicap/xilinx_hwicap.h +++ b/trunk/drivers/char/xilinx_hwicap/xilinx_hwicap.h @@ -38,6 +38,7 @@ #include #include +#include #include #include diff --git a/trunk/drivers/edac/edac_core.h b/trunk/drivers/edac/edac_core.h index 4b55ec607a88..b27b13c5eb5a 100644 --- a/trunk/drivers/edac/edac_core.h +++ b/trunk/drivers/edac/edac_core.h @@ -34,6 +34,7 @@ #include #include #include +#include #define EDAC_MC_LABEL_LEN 31 #define EDAC_DEVICE_NAME_LEN 31 diff --git a/trunk/drivers/i2c/busses/i2c-at91.c b/trunk/drivers/i2c/busses/i2c-at91.c index 9efb02137254..c1adcdbf7979 100644 --- a/trunk/drivers/i2c/busses/i2c-at91.c +++ b/trunk/drivers/i2c/busses/i2c-at91.c @@ -14,6 +14,7 @@ */ #include +#include #include #include #include diff --git a/trunk/drivers/infiniband/hw/ehca/ehca_tools.h b/trunk/drivers/infiniband/hw/ehca/ehca_tools.h index 21f7d06f14ad..ec950bf8c479 100644 --- a/trunk/drivers/infiniband/hw/ehca/ehca_tools.h +++ b/trunk/drivers/infiniband/hw/ehca/ehca_tools.h @@ -54,6 +54,7 @@ #include #include #include +#include #include #include #include diff --git a/trunk/drivers/infiniband/hw/ipath/ipath_fs.c b/trunk/drivers/infiniband/hw/ipath/ipath_fs.c index 8bb5170b4e41..23faba9d21eb 100644 --- a/trunk/drivers/infiniband/hw/ipath/ipath_fs.c +++ b/trunk/drivers/infiniband/hw/ipath/ipath_fs.c @@ -31,6 +31,7 @@ * SOFTWARE. */ +#include #include #include #include diff --git a/trunk/drivers/infiniband/hw/ipath/ipath_iba7220.c b/trunk/drivers/infiniband/hw/ipath/ipath_iba7220.c index 9839e20119bc..d90f5e9a54fa 100644 --- a/trunk/drivers/infiniband/hw/ipath/ipath_iba7220.c +++ b/trunk/drivers/infiniband/hw/ipath/ipath_iba7220.c @@ -1720,7 +1720,7 @@ static void ipath_7220_put_tid(struct ipath_devdata *dd, u64 __iomem *tidptr, "not 2KB aligned!\n", pa); return; } - if (chippa >= (1UL << IBA7220_TID_SZ_SHIFT)) { + if (pa >= (1UL << IBA7220_TID_SZ_SHIFT)) { ipath_dev_err(dd, "BUG: Physical page address 0x%lx " "larger than supported\n", pa); diff --git a/trunk/drivers/infiniband/hw/ipath/ipath_ud.c b/trunk/drivers/infiniband/hw/ipath/ipath_ud.c index 729446f56aab..36aa242c487c 100644 --- a/trunk/drivers/infiniband/hw/ipath/ipath_ud.c +++ b/trunk/drivers/infiniband/hw/ipath/ipath_ud.c @@ -267,7 +267,6 @@ int ipath_make_ud_req(struct ipath_qp *qp) u16 lrh0; u16 lid; int ret = 0; - int next_cur; spin_lock_irqsave(&qp->s_lock, flags); @@ -291,9 +290,8 @@ int ipath_make_ud_req(struct ipath_qp *qp) goto bail; wqe = get_swqe_ptr(qp, qp->s_cur); - next_cur = qp->s_cur + 1; - if (next_cur >= qp->s_size) - next_cur = 0; + if (++qp->s_cur >= qp->s_size) + qp->s_cur = 0; /* Construct the header. */ ah_attr = &to_iah(wqe->wr.wr.ud.ah)->attr; @@ -317,7 +315,6 @@ int ipath_make_ud_req(struct ipath_qp *qp) qp->s_flags |= IPATH_S_WAIT_DMA; goto bail; } - qp->s_cur = next_cur; spin_unlock_irqrestore(&qp->s_lock, flags); ipath_ud_loopback(qp, wqe); spin_lock_irqsave(&qp->s_lock, flags); @@ -326,7 +323,6 @@ int ipath_make_ud_req(struct ipath_qp *qp) } } - qp->s_cur = next_cur; extra_bytes = -wqe->length & 3; nwords = (wqe->length + extra_bytes) >> 2; diff --git a/trunk/drivers/infiniband/hw/nes/nes.h b/trunk/drivers/infiniband/hw/nes/nes.h index 8eb7ae96974d..39bd897b40c6 100644 --- a/trunk/drivers/infiniband/hw/nes/nes.h +++ b/trunk/drivers/infiniband/hw/nes/nes.h @@ -43,6 +43,7 @@ #include #include #include +#include #include #include diff --git a/trunk/drivers/infiniband/ulp/ipoib/ipoib_main.c b/trunk/drivers/infiniband/ulp/ipoib/ipoib_main.c index 7e9e218738fa..f51201b17bfd 100644 --- a/trunk/drivers/infiniband/ulp/ipoib/ipoib_main.c +++ b/trunk/drivers/infiniband/ulp/ipoib/ipoib_main.c @@ -156,8 +156,14 @@ static int ipoib_stop(struct net_device *dev) netif_stop_queue(dev); - ipoib_ib_dev_down(dev, 0); - ipoib_ib_dev_stop(dev, 0); + /* + * Now flush workqueue to make sure a scheduled task doesn't + * bring our internal state back up. + */ + flush_workqueue(ipoib_workqueue); + + ipoib_ib_dev_down(dev, 1); + ipoib_ib_dev_stop(dev, 1); if (!test_bit(IPOIB_FLAG_SUBINTERFACE, &priv->flags)) { struct ipoib_dev_priv *cpriv; @@ -1308,7 +1314,7 @@ static struct net_device *ipoib_add_port(const char *format, register_failed: ib_unregister_event_handler(&priv->event_handler); - flush_workqueue(ipoib_workqueue); + flush_scheduled_work(); event_failed: ipoib_dev_cleanup(priv->dev); @@ -1367,12 +1373,7 @@ static void ipoib_remove_one(struct ib_device *device) list_for_each_entry_safe(priv, tmp, dev_list, list) { ib_unregister_event_handler(&priv->event_handler); - - rtnl_lock(); - dev_change_flags(priv->dev, priv->dev->flags & ~IFF_UP); - rtnl_unlock(); - - flush_workqueue(ipoib_workqueue); + flush_scheduled_work(); unregister_netdev(priv->dev); ipoib_dev_cleanup(priv->dev); diff --git a/trunk/drivers/infiniband/ulp/ipoib/ipoib_multicast.c b/trunk/drivers/infiniband/ulp/ipoib/ipoib_multicast.c index ac33c8f3ea85..8950e9546f4e 100644 --- a/trunk/drivers/infiniband/ulp/ipoib/ipoib_multicast.c +++ b/trunk/drivers/infiniband/ulp/ipoib/ipoib_multicast.c @@ -392,16 +392,8 @@ static int ipoib_mcast_join_complete(int status, &priv->mcast_task, 0); mutex_unlock(&mcast_mutex); - if (mcast == priv->broadcast) { - /* - * Take RTNL lock here to avoid racing with - * ipoib_stop() and turning the carrier back - * on while a device is being removed. - */ - rtnl_lock(); + if (mcast == priv->broadcast) netif_carrier_on(dev); - rtnl_unlock(); - } return 0; } diff --git a/trunk/drivers/infiniband/ulp/iser/iser_verbs.c b/trunk/drivers/infiniband/ulp/iser/iser_verbs.c index 26ff6214a81f..63462ecca147 100644 --- a/trunk/drivers/infiniband/ulp/iser/iser_verbs.c +++ b/trunk/drivers/infiniband/ulp/iser/iser_verbs.c @@ -33,6 +33,7 @@ #include #include #include +#include #include "iscsi_iser.h" diff --git a/trunk/drivers/input/keyboard/bf54x-keys.c b/trunk/drivers/input/keyboard/bf54x-keys.c index 6f227d3dbda1..54ed8e2e1c02 100644 --- a/trunk/drivers/input/keyboard/bf54x-keys.c +++ b/trunk/drivers/input/keyboard/bf54x-keys.c @@ -29,6 +29,7 @@ */ #include +#include #include #include diff --git a/trunk/drivers/input/touchscreen/mainstone-wm97xx.c b/trunk/drivers/input/touchscreen/mainstone-wm97xx.c index 37a555f37306..283f93a0cee2 100644 --- a/trunk/drivers/input/touchscreen/mainstone-wm97xx.c +++ b/trunk/drivers/input/touchscreen/mainstone-wm97xx.c @@ -25,6 +25,7 @@ #include #include +#include #include #include #include diff --git a/trunk/drivers/lguest/lguest_device.c b/trunk/drivers/lguest/lguest_device.c index a661bbdae3d6..37344aaee22f 100644 --- a/trunk/drivers/lguest/lguest_device.c +++ b/trunk/drivers/lguest/lguest_device.c @@ -98,10 +98,6 @@ static u32 lg_get_features(struct virtio_device *vdev) return features; } -/* The virtio core takes the features the Host offers, and copies the - * ones supported by the driver into the vdev->features array. Once - * that's all sorted out, this routine is called so we can tell the - * Host which features we understand and accept. */ static void lg_finalize_features(struct virtio_device *vdev) { unsigned int i, bits; @@ -112,10 +108,6 @@ static void lg_finalize_features(struct virtio_device *vdev) /* Give virtio_ring a chance to accept features. */ vring_transport_features(vdev); - /* The vdev->feature array is a Linux bitmask: this isn't the - * same as a the simple array of bits used by lguest devices - * for features. So we do this slow, manual conversion which is - * completely general. */ memset(out_features, 0, desc->feature_len); bits = min_t(unsigned, desc->feature_len, sizeof(vdev->features)) * 8; for (i = 0; i < bits; i++) { diff --git a/trunk/drivers/mfd/asic3.c b/trunk/drivers/mfd/asic3.c index bc2a807f210d..c6408a62d95e 100644 --- a/trunk/drivers/mfd/asic3.c +++ b/trunk/drivers/mfd/asic3.c @@ -16,6 +16,7 @@ * */ +#include #include #include #include diff --git a/trunk/drivers/misc/acer-wmi.c b/trunk/drivers/misc/acer-wmi.c index c6c77a505ec1..b2d9878dc3f0 100644 --- a/trunk/drivers/misc/acer-wmi.c +++ b/trunk/drivers/misc/acer-wmi.c @@ -192,9 +192,6 @@ static struct quirk_entry *quirks; static void set_quirks(void) { - if (!interface) - return; - if (quirks->mailled) interface->capability |= ACER_CAP_MAILLED; @@ -1240,8 +1237,6 @@ static int __init acer_wmi_init(void) return -ENODEV; } - set_quirks(); - if (platform_driver_register(&acer_platform_driver)) { printk(ACER_ERR "Unable to register platform driver.\n"); goto error_platform_register; diff --git a/trunk/drivers/misc/eeprom_93cx6.c b/trunk/drivers/misc/eeprom_93cx6.c index 15b1780025c8..ea55654e5948 100644 --- a/trunk/drivers/misc/eeprom_93cx6.c +++ b/trunk/drivers/misc/eeprom_93cx6.c @@ -26,6 +26,7 @@ #include #include +#include #include #include diff --git a/trunk/drivers/mtd/maps/amd76xrom.c b/trunk/drivers/mtd/maps/amd76xrom.c index d1eec7d3243f..948b86f35ef4 100644 --- a/trunk/drivers/mtd/maps/amd76xrom.c +++ b/trunk/drivers/mtd/maps/amd76xrom.c @@ -6,6 +6,7 @@ #include #include +#include #include #include #include diff --git a/trunk/drivers/mtd/maps/ck804xrom.c b/trunk/drivers/mtd/maps/ck804xrom.c index 1a6feb4474de..effaf7cdefab 100644 --- a/trunk/drivers/mtd/maps/ck804xrom.c +++ b/trunk/drivers/mtd/maps/ck804xrom.c @@ -9,6 +9,7 @@ #include #include +#include #include #include #include diff --git a/trunk/drivers/mtd/maps/esb2rom.c b/trunk/drivers/mtd/maps/esb2rom.c index bbbcdd4c8d13..aa64a4752781 100644 --- a/trunk/drivers/mtd/maps/esb2rom.c +++ b/trunk/drivers/mtd/maps/esb2rom.c @@ -12,6 +12,7 @@ #include #include +#include #include #include #include diff --git a/trunk/drivers/mtd/nand/au1550nd.c b/trunk/drivers/mtd/nand/au1550nd.c index 92c334ff4508..761946ea45b1 100644 --- a/trunk/drivers/mtd/nand/au1550nd.c +++ b/trunk/drivers/mtd/nand/au1550nd.c @@ -16,6 +16,7 @@ #include #include #include +#include #include #include diff --git a/trunk/drivers/net/myri10ge/myri10ge.c b/trunk/drivers/net/myri10ge/myri10ge.c index 54cd89cb0838..5d76cd09e246 100644 --- a/trunk/drivers/net/myri10ge/myri10ge.c +++ b/trunk/drivers/net/myri10ge/myri10ge.c @@ -56,6 +56,7 @@ #include #include #include +#include #include #include #include diff --git a/trunk/drivers/net/netxen/netxen_nic.h b/trunk/drivers/net/netxen/netxen_nic.h index 244ab49c4337..ab871df6b1db 100644 --- a/trunk/drivers/net/netxen/netxen_nic.h +++ b/trunk/drivers/net/netxen/netxen_nic.h @@ -45,6 +45,7 @@ #include #include #include +#include #include #include diff --git a/trunk/drivers/net/netxen/netxen_nic_ethtool.c b/trunk/drivers/net/netxen/netxen_nic_ethtool.c index b974ca0fc530..4ad3e0844b99 100644 --- a/trunk/drivers/net/netxen/netxen_nic_ethtool.c +++ b/trunk/drivers/net/netxen/netxen_nic_ethtool.c @@ -38,6 +38,7 @@ #include #include #include +#include #include "netxen_nic.h" #include "netxen_nic_hw.h" diff --git a/trunk/drivers/net/netxen/netxen_nic_hdr.h b/trunk/drivers/net/netxen/netxen_nic_hdr.h index e80f9e3e5973..e8e8d73f6ed7 100644 --- a/trunk/drivers/net/netxen/netxen_nic_hdr.h +++ b/trunk/drivers/net/netxen/netxen_nic_hdr.h @@ -32,6 +32,8 @@ #include #include +#include + #include #include #include diff --git a/trunk/drivers/net/tokenring/lanstreamer.c b/trunk/drivers/net/tokenring/lanstreamer.c index 59d1673f9387..47d84cd28097 100644 --- a/trunk/drivers/net/tokenring/lanstreamer.c +++ b/trunk/drivers/net/tokenring/lanstreamer.c @@ -119,6 +119,7 @@ #include #include #include +#include #include #include diff --git a/trunk/drivers/net/tokenring/lanstreamer.h b/trunk/drivers/net/tokenring/lanstreamer.h index 13ccee6449c1..e7bb3494afc7 100644 --- a/trunk/drivers/net/tokenring/lanstreamer.h +++ b/trunk/drivers/net/tokenring/lanstreamer.h @@ -60,6 +60,8 @@ * */ +#include + /* MAX_INTR - the maximum number of times we can loop * inside the interrupt function before returning * control to the OS (maximum value is 256) diff --git a/trunk/drivers/net/wireless/b43legacy/main.c b/trunk/drivers/net/wireless/b43legacy/main.c index 1cb77db5c292..2541c81932f0 100644 --- a/trunk/drivers/net/wireless/b43legacy/main.c +++ b/trunk/drivers/net/wireless/b43legacy/main.c @@ -34,6 +34,7 @@ #include #include #include +#include #include #include #include diff --git a/trunk/drivers/net/wireless/iwlwifi/iwl-3945-led.c b/trunk/drivers/net/wireless/iwlwifi/iwl-3945-led.c index 705c65bed9fd..d3336966b6b5 100644 --- a/trunk/drivers/net/wireless/iwlwifi/iwl-3945-led.c +++ b/trunk/drivers/net/wireless/iwlwifi/iwl-3945-led.c @@ -27,6 +27,7 @@ #include #include +#include #include #include #include diff --git a/trunk/drivers/net/wireless/iwlwifi/iwl-led.c b/trunk/drivers/net/wireless/iwlwifi/iwl-led.c index 4eee1b163cd2..cb11c4a4d691 100644 --- a/trunk/drivers/net/wireless/iwlwifi/iwl-led.c +++ b/trunk/drivers/net/wireless/iwlwifi/iwl-led.c @@ -27,6 +27,7 @@ #include #include +#include #include #include #include diff --git a/trunk/drivers/net/wireless/iwlwifi/iwl-rfkill.c b/trunk/drivers/net/wireless/iwlwifi/iwl-rfkill.c index 5d642298f04c..e5e5846e9f25 100644 --- a/trunk/drivers/net/wireless/iwlwifi/iwl-rfkill.c +++ b/trunk/drivers/net/wireless/iwlwifi/iwl-rfkill.c @@ -27,6 +27,7 @@ *****************************************************************************/ #include #include +#include #include #include diff --git a/trunk/drivers/pci/hotplug/pciehp.h b/trunk/drivers/pci/hotplug/pciehp.h index 9e6cec67e1cc..e3a1e7e7dba2 100644 --- a/trunk/drivers/pci/hotplug/pciehp.h +++ b/trunk/drivers/pci/hotplug/pciehp.h @@ -43,6 +43,7 @@ extern int pciehp_poll_mode; extern int pciehp_poll_time; extern int pciehp_debug; extern int pciehp_force; +extern int pciehp_slot_with_bus; extern struct workqueue_struct *pciehp_wq; #define dbg(format, arg...) \ diff --git a/trunk/drivers/pci/hotplug/pciehp_core.c b/trunk/drivers/pci/hotplug/pciehp_core.c index 4fd5355bc3b5..3677495c4f91 100644 --- a/trunk/drivers/pci/hotplug/pciehp_core.c +++ b/trunk/drivers/pci/hotplug/pciehp_core.c @@ -41,6 +41,7 @@ int pciehp_debug; int pciehp_poll_mode; int pciehp_poll_time; int pciehp_force; +int pciehp_slot_with_bus; struct workqueue_struct *pciehp_wq; #define DRIVER_VERSION "0.4" @@ -55,10 +56,12 @@ module_param(pciehp_debug, bool, 0644); module_param(pciehp_poll_mode, bool, 0644); module_param(pciehp_poll_time, int, 0644); module_param(pciehp_force, bool, 0644); +module_param(pciehp_slot_with_bus, bool, 0644); MODULE_PARM_DESC(pciehp_debug, "Debugging mode enabled or not"); MODULE_PARM_DESC(pciehp_poll_mode, "Using polling mechanism for hot-plug events or not"); MODULE_PARM_DESC(pciehp_poll_time, "Polling mechanism frequency, in seconds"); MODULE_PARM_DESC(pciehp_force, "Force pciehp, even if _OSC and OSHP are missing"); +MODULE_PARM_DESC(pciehp_slot_with_bus, "Use bus number in the slot name"); #define PCIE_MODULE_NAME "pciehp" @@ -191,7 +194,6 @@ static int init_slots(struct controller *ctrl) struct slot *slot; struct hotplug_slot *hotplug_slot; struct hotplug_slot_info *info; - int len, dup = 1; int retval = -ENOMEM; list_for_each_entry(slot, &ctrl->slot_list, slot_list) { @@ -218,24 +220,15 @@ static int init_slots(struct controller *ctrl) dbg("Registering bus=%x dev=%x hp_slot=%x sun=%x " "slot_device_offset=%x\n", slot->bus, slot->device, slot->hp_slot, slot->number, ctrl->slot_device_offset); -duplicate_name: retval = pci_hp_register(hotplug_slot, ctrl->pci_dev->subordinate, slot->device); if (retval) { - /* - * If slot N already exists, we'll try to create - * slot N-1, N-2 ... N-M, until we overflow. - */ - if (retval == -EEXIST) { - len = snprintf(slot->name, SLOT_NAME_SIZE, - "%d-%d", slot->number, dup++); - if (len < SLOT_NAME_SIZE) - goto duplicate_name; - else - err("duplicate slot name overflow\n"); - } err("pci_hp_register failed with error %d\n", retval); + if (retval == -EEXIST) + err("Failed to register slot because of name " + "collision. Try \'pciehp_slot_with_bus\' " + "module option.\n"); goto error_info; } /* create additional sysfs entries */ diff --git a/trunk/drivers/pci/hotplug/pciehp_hpc.c b/trunk/drivers/pci/hotplug/pciehp_hpc.c index ab31f5ba665d..ad27e9e225a6 100644 --- a/trunk/drivers/pci/hotplug/pciehp_hpc.c +++ b/trunk/drivers/pci/hotplug/pciehp_hpc.c @@ -1030,6 +1030,15 @@ static void pcie_shutdown_notification(struct controller *ctrl) pciehp_free_irq(ctrl); } +static void make_slot_name(struct slot *slot) +{ + if (pciehp_slot_with_bus) + snprintf(slot->name, SLOT_NAME_SIZE, "%04d_%04d", + slot->bus, slot->number); + else + snprintf(slot->name, SLOT_NAME_SIZE, "%d", slot->number); +} + static int pcie_init_slot(struct controller *ctrl) { struct slot *slot; @@ -1044,7 +1053,7 @@ static int pcie_init_slot(struct controller *ctrl) slot->device = ctrl->slot_device_offset + slot->hp_slot; slot->hpc_ops = ctrl->hpc_ops; slot->number = ctrl->first_slot; - snprintf(slot->name, SLOT_NAME_SIZE, "%d", slot->number); + make_slot_name(slot); mutex_init(&slot->lock); INIT_DELAYED_WORK(&slot->work, pciehp_queue_pushbutton_work); list_add(&slot->slot_list, &ctrl->slot_list); diff --git a/trunk/drivers/pci/hotplug/shpchp_core.c b/trunk/drivers/pci/hotplug/shpchp_core.c index cc38615395f1..a8cbd039b85b 100644 --- a/trunk/drivers/pci/hotplug/shpchp_core.c +++ b/trunk/drivers/pci/hotplug/shpchp_core.c @@ -39,6 +39,7 @@ int shpchp_debug; int shpchp_poll_mode; int shpchp_poll_time; +static int shpchp_slot_with_bus; struct workqueue_struct *shpchp_wq; #define DRIVER_VERSION "0.4" @@ -52,9 +53,11 @@ MODULE_LICENSE("GPL"); module_param(shpchp_debug, bool, 0644); module_param(shpchp_poll_mode, bool, 0644); module_param(shpchp_poll_time, int, 0644); +module_param(shpchp_slot_with_bus, bool, 0644); MODULE_PARM_DESC(shpchp_debug, "Debugging mode enabled or not"); MODULE_PARM_DESC(shpchp_poll_mode, "Using polling mechanism for hot-plug events or not"); MODULE_PARM_DESC(shpchp_poll_time, "Polling mechanism frequency, in seconds"); +MODULE_PARM_DESC(shpchp_slot_with_bus, "Use bus number in the slot name"); #define SHPC_MODULE_NAME "shpchp" @@ -96,13 +99,23 @@ static void release_slot(struct hotplug_slot *hotplug_slot) kfree(slot); } +static void make_slot_name(struct slot *slot) +{ + if (shpchp_slot_with_bus) + snprintf(slot->hotplug_slot->name, SLOT_NAME_SIZE, "%04d_%04d", + slot->bus, slot->number); + else + snprintf(slot->hotplug_slot->name, SLOT_NAME_SIZE, "%d", + slot->number); +} + static int init_slots(struct controller *ctrl) { struct slot *slot; struct hotplug_slot *hotplug_slot; struct hotplug_slot_info *info; int retval = -ENOMEM; - int i, len, dup = 1; + int i; for (i = 0; i < ctrl->num_slots; i++) { slot = kzalloc(sizeof(*slot), GFP_KERNEL); @@ -133,7 +146,7 @@ static int init_slots(struct controller *ctrl) /* register this slot with the hotplug pci core */ hotplug_slot->private = slot; hotplug_slot->release = &release_slot; - snprintf(slot->name, SLOT_NAME_SIZE, "%d", slot->number); + make_slot_name(slot); hotplug_slot->ops = &shpchp_hotplug_slot_ops; get_power_status(hotplug_slot, &info->power_status); @@ -144,23 +157,14 @@ static int init_slots(struct controller *ctrl) dbg("Registering bus=%x dev=%x hp_slot=%x sun=%x " "slot_device_offset=%x\n", slot->bus, slot->device, slot->hp_slot, slot->number, ctrl->slot_device_offset); -duplicate_name: retval = pci_hp_register(slot->hotplug_slot, ctrl->pci_dev->subordinate, slot->device); if (retval) { - /* - * If slot N already exists, we'll try to create - * slot N-1, N-2 ... N-M, until we overflow. - */ - if (retval == -EEXIST) { - len = snprintf(slot->name, SLOT_NAME_SIZE, - "%d-%d", slot->number, dup++); - if (len < SLOT_NAME_SIZE) - goto duplicate_name; - else - err("duplicate slot name overflow\n"); - } err("pci_hp_register failed with error %d\n", retval); + if (retval == -EEXIST) + err("Failed to register slot because of name " + "collision. Try \'shpchp_slot_with_bus\' " + "module option.\n"); goto error_info; } diff --git a/trunk/drivers/pci/search.c b/trunk/drivers/pci/search.c index 3b3b5f178797..217814fef4ef 100644 --- a/trunk/drivers/pci/search.c +++ b/trunk/drivers/pci/search.c @@ -280,8 +280,6 @@ static struct pci_dev *pci_get_dev_by_id(const struct pci_device_id *id, match_pci_dev_by_id); if (dev) pdev = to_pci_dev(dev); - if (from) - pci_dev_put(from); return pdev; } diff --git a/trunk/drivers/rtc/rtc-max6902.c b/trunk/drivers/rtc/rtc-max6902.c index 78b2551fb19d..12f0310ae89c 100644 --- a/trunk/drivers/rtc/rtc-max6902.c +++ b/trunk/drivers/rtc/rtc-max6902.c @@ -20,6 +20,8 @@ */ #include +#include + #include #include #include diff --git a/trunk/drivers/rtc/rtc-r9701.c b/trunk/drivers/rtc/rtc-r9701.c index 395985b339c9..b35f9bfa2af4 100644 --- a/trunk/drivers/rtc/rtc-r9701.c +++ b/trunk/drivers/rtc/rtc-r9701.c @@ -14,6 +14,7 @@ */ #include +#include #include #include #include diff --git a/trunk/drivers/s390/block/dasd.c b/trunk/drivers/s390/block/dasd.c index acb78017e7d0..1b6c52ef7339 100644 --- a/trunk/drivers/s390/block/dasd.c +++ b/trunk/drivers/s390/block/dasd.c @@ -2333,11 +2333,13 @@ int dasd_generic_notify(struct ccw_device *cdev, int event) { struct dasd_device *device; struct dasd_ccw_req *cqr; + unsigned long flags; int ret; - device = dasd_device_from_cdev_locked(cdev); + device = dasd_device_from_cdev(cdev); if (IS_ERR(device)) return 0; + spin_lock_irqsave(get_ccwdev_lock(cdev), flags); ret = 0; switch (event) { case CIO_GONE: @@ -2367,6 +2369,7 @@ int dasd_generic_notify(struct ccw_device *cdev, int event) ret = 1; break; } + spin_unlock_irqrestore(get_ccwdev_lock(cdev), flags); dasd_put_device(device); return ret; } diff --git a/trunk/drivers/s390/block/dasd_eckd.h b/trunk/drivers/s390/block/dasd_eckd.h index 2476f87d21d0..4bf0aa5112c1 100644 --- a/trunk/drivers/s390/block/dasd_eckd.h +++ b/trunk/drivers/s390/block/dasd_eckd.h @@ -308,7 +308,7 @@ struct dasd_psf_prssd_data { unsigned char flags; unsigned char reserved[4]; unsigned char suborder; - unsigned char varies[5]; + unsigned char varies[9]; } __attribute__ ((packed)); /* diff --git a/trunk/drivers/s390/block/dasd_eer.c b/trunk/drivers/s390/block/dasd_eer.c index bf512ac75b9e..29da4413ad43 100644 --- a/trunk/drivers/s390/block/dasd_eer.c +++ b/trunk/drivers/s390/block/dasd_eer.c @@ -16,7 +16,6 @@ #include #include #include -#include #include #include @@ -458,7 +457,7 @@ int dasd_eer_enable(struct dasd_device *device) cqr = dasd_kmalloc_request("ECKD", 1 /* SNSS */, SNSS_DATA_SIZE, device); - if (IS_ERR(cqr)) + if (!cqr) return -ENOMEM; cqr->startdev = device; diff --git a/trunk/drivers/s390/block/dcssblk.c b/trunk/drivers/s390/block/dcssblk.c index db85f1fb131e..01fcdd91b846 100644 --- a/trunk/drivers/s390/block/dcssblk.c +++ b/trunk/drivers/s390/block/dcssblk.c @@ -384,10 +384,6 @@ dcssblk_add_store(struct device *dev, struct device_attribute *attr, const char * get minor, add to list */ down_write(&dcssblk_devices_sem); - if (dcssblk_get_segment_by_name(local_buf)) { - rc = -EEXIST; - goto release_gd; - } rc = dcssblk_assign_free_minor(dev_info); if (rc) { up_write(&dcssblk_devices_sem); diff --git a/trunk/drivers/s390/char/tape_char.c b/trunk/drivers/s390/char/tape_char.c index be0ce2215c8d..687720b552d1 100644 --- a/trunk/drivers/s390/char/tape_char.c +++ b/trunk/drivers/s390/char/tape_char.c @@ -109,7 +109,7 @@ tapechar_check_idalbuffer(struct tape_device *device, size_t block_size) /* The current idal buffer is not correct. Allocate a new one. */ new = idal_buffer_alloc(block_size, 0); - if (IS_ERR(new)) + if (new == NULL) return -ENOMEM; if (device->char_data.idal_buf != NULL) diff --git a/trunk/drivers/s390/char/tape_std.c b/trunk/drivers/s390/char/tape_std.c index cc8fd781ee22..2a1af4e60be0 100644 --- a/trunk/drivers/s390/char/tape_std.c +++ b/trunk/drivers/s390/char/tape_std.c @@ -248,7 +248,7 @@ tape_std_mtsetblk(struct tape_device *device, int count) /* Allocate a new idal buffer. */ new = idal_buffer_alloc(count, 0); - if (IS_ERR(new)) + if (new == NULL) return -ENOMEM; if (device->char_data.idal_buf != NULL) idal_buffer_free(device->char_data.idal_buf); diff --git a/trunk/drivers/s390/cio/ccwgroup.c b/trunk/drivers/s390/cio/ccwgroup.c index e0ce65fca4e7..26a930e832bd 100644 --- a/trunk/drivers/s390/cio/ccwgroup.c +++ b/trunk/drivers/s390/cio/ccwgroup.c @@ -112,10 +112,8 @@ ccwgroup_release (struct device *dev) gdev = to_ccwgroupdev(dev); for (i = 0; i < gdev->count; i++) { - if (gdev->cdev[i]) { - dev_set_drvdata(&gdev->cdev[i]->dev, NULL); - put_device(&gdev->cdev[i]->dev); - } + dev_set_drvdata(&gdev->cdev[i]->dev, NULL); + put_device(&gdev->cdev[i]->dev); } kfree(gdev); } @@ -223,13 +221,6 @@ int ccwgroup_create_from_string(struct device *root, unsigned int creator_id, atomic_set(&gdev->onoff, 0); mutex_init(&gdev->reg_mutex); mutex_lock(&gdev->reg_mutex); - gdev->creator_id = creator_id; - gdev->count = num_devices; - gdev->dev.bus = &ccwgroup_bus_type; - gdev->dev.parent = root; - gdev->dev.release = ccwgroup_release; - device_initialize(&gdev->dev); - curr_buf = buf; for (i = 0; i < num_devices && curr_buf; i++) { rc = __get_next_bus_id(&curr_buf, tmp_bus_id); @@ -267,11 +258,16 @@ int ccwgroup_create_from_string(struct device *root, unsigned int creator_id, rc = -EINVAL; goto error; } + gdev->creator_id = creator_id; + gdev->count = num_devices; + gdev->dev.bus = &ccwgroup_bus_type; + gdev->dev.parent = root; + gdev->dev.release = ccwgroup_release; snprintf (gdev->dev.bus_id, BUS_ID_SIZE, "%s", gdev->cdev[0]->dev.bus_id); - rc = device_add(&gdev->dev); + rc = device_register(&gdev->dev); if (rc) goto error; get_device(&gdev->dev); diff --git a/trunk/drivers/s390/cio/css.c b/trunk/drivers/s390/cio/css.c index 51489eff6b0b..46c021d880dc 100644 --- a/trunk/drivers/s390/cio/css.c +++ b/trunk/drivers/s390/cio/css.c @@ -477,6 +477,7 @@ void css_schedule_eval_all(void) void css_wait_for_slow_path(void) { + flush_workqueue(ccw_device_notify_work); flush_workqueue(slow_path_wq); } diff --git a/trunk/drivers/s390/cio/device.c b/trunk/drivers/s390/cio/device.c index 28221030b886..e818d0c54c09 100644 --- a/trunk/drivers/s390/cio/device.c +++ b/trunk/drivers/s390/cio/device.c @@ -150,6 +150,7 @@ static struct css_driver io_subchannel_driver = { }; struct workqueue_struct *ccw_device_work; +struct workqueue_struct *ccw_device_notify_work; wait_queue_head_t ccw_device_init_wq; atomic_t ccw_device_init_count; @@ -167,6 +168,11 @@ init_ccw_bus_type (void) ccw_device_work = create_singlethread_workqueue("cio"); if (!ccw_device_work) return -ENOMEM; /* FIXME: better errno ? */ + ccw_device_notify_work = create_singlethread_workqueue("cio_notify"); + if (!ccw_device_notify_work) { + ret = -ENOMEM; /* FIXME: better errno ? */ + goto out_err; + } slow_path_wq = create_singlethread_workqueue("kslowcrw"); if (!slow_path_wq) { ret = -ENOMEM; /* FIXME: better errno ? */ @@ -186,6 +192,8 @@ init_ccw_bus_type (void) out_err: if (ccw_device_work) destroy_workqueue(ccw_device_work); + if (ccw_device_notify_work) + destroy_workqueue(ccw_device_notify_work); if (slow_path_wq) destroy_workqueue(slow_path_wq); return ret; @@ -196,6 +204,7 @@ cleanup_ccw_bus_type (void) { css_driver_unregister(&io_subchannel_driver); bus_unregister(&ccw_bus_type); + destroy_workqueue(ccw_device_notify_work); destroy_workqueue(ccw_device_work); } @@ -1487,22 +1496,11 @@ static void device_set_disconnected(struct ccw_device *cdev) ccw_device_schedule_recovery(); } -void ccw_device_set_notoper(struct ccw_device *cdev) -{ - struct subchannel *sch = to_subchannel(cdev->dev.parent); - - CIO_TRACE_EVENT(2, "notoper"); - CIO_TRACE_EVENT(2, sch->dev.bus_id); - ccw_device_set_timeout(cdev, 0); - cio_disable_subchannel(sch); - cdev->private->state = DEV_STATE_NOT_OPER; -} - static int io_subchannel_sch_event(struct subchannel *sch, int slow) { int event, ret, disc; unsigned long flags; - enum { NONE, UNREGISTER, UNREGISTER_PROBE, REPROBE, DISC } action; + enum { NONE, UNREGISTER, UNREGISTER_PROBE, REPROBE } action; struct ccw_device *cdev; spin_lock_irqsave(sch->lock, flags); @@ -1537,11 +1535,16 @@ static int io_subchannel_sch_event(struct subchannel *sch, int slow) } /* fall through */ case CIO_GONE: + /* Prevent unwanted effects when opening lock. */ + cio_disable_subchannel(sch); + device_set_disconnected(cdev); /* Ask driver what to do with device. */ - if (io_subchannel_notify(sch, event)) - action = DISC; - else - action = UNREGISTER; + action = UNREGISTER; + spin_unlock_irqrestore(sch->lock, flags); + ret = io_subchannel_notify(sch, event); + spin_lock_irqsave(sch->lock, flags); + if (ret) + action = NONE; break; case CIO_REVALIDATE: /* Device will be removed, so no notify necessary. */ @@ -1562,7 +1565,6 @@ static int io_subchannel_sch_event(struct subchannel *sch, int slow) switch (action) { case UNREGISTER: case UNREGISTER_PROBE: - ccw_device_set_notoper(cdev); /* Unregister device (will use subchannel lock). */ spin_unlock_irqrestore(sch->lock, flags); css_sch_device_unregister(sch); @@ -1575,9 +1577,6 @@ static int io_subchannel_sch_event(struct subchannel *sch, int slow) case REPROBE: ccw_device_trigger_reprobe(cdev); break; - case DISC: - device_set_disconnected(cdev); - break; default: break; } @@ -1829,4 +1828,5 @@ EXPORT_SYMBOL(ccw_driver_unregister); EXPORT_SYMBOL(get_ccwdev_by_busid); EXPORT_SYMBOL(ccw_bus_type); EXPORT_SYMBOL(ccw_device_work); +EXPORT_SYMBOL(ccw_device_notify_work); EXPORT_SYMBOL_GPL(ccw_device_get_subchannel_id); diff --git a/trunk/drivers/s390/cio/device.h b/trunk/drivers/s390/cio/device.h index 6f5c3f2b3587..9800a8335a3f 100644 --- a/trunk/drivers/s390/cio/device.h +++ b/trunk/drivers/s390/cio/device.h @@ -72,6 +72,7 @@ dev_fsm_final_state(struct ccw_device *cdev) } extern struct workqueue_struct *ccw_device_work; +extern struct workqueue_struct *ccw_device_notify_work; extern wait_queue_head_t ccw_device_init_wq; extern atomic_t ccw_device_init_count; @@ -119,7 +120,6 @@ int ccw_device_stlck(struct ccw_device *); void ccw_device_trigger_reprobe(struct ccw_device *); void ccw_device_kill_io(struct ccw_device *); int ccw_device_notify(struct ccw_device *, int); -void ccw_device_set_notoper(struct ccw_device *cdev); /* qdio needs this. */ void ccw_device_set_timeout(struct ccw_device *, int); diff --git a/trunk/drivers/s390/cio/device_fsm.c b/trunk/drivers/s390/cio/device_fsm.c index 550508df952b..8b5fe57fb2f3 100644 --- a/trunk/drivers/s390/cio/device_fsm.c +++ b/trunk/drivers/s390/cio/device_fsm.c @@ -337,34 +337,26 @@ int ccw_device_notify(struct ccw_device *cdev, int event) return 0; if (!cdev->online) return 0; - CIO_MSG_EVENT(2, "notify called for 0.%x.%04x, event=%d\n", - cdev->private->dev_id.ssid, cdev->private->dev_id.devno, - event); return cdev->drv->notify ? cdev->drv->notify(cdev, event) : 0; } -static void cmf_reenable_delayed(struct work_struct *work) +static void +ccw_device_oper_notify(struct work_struct *work) { struct ccw_device_private *priv; struct ccw_device *cdev; + int ret; priv = container_of(work, struct ccw_device_private, kick_work); cdev = priv->cdev; - cmf_reenable(cdev); -} - -static void ccw_device_oper_notify(struct ccw_device *cdev) -{ - if (ccw_device_notify(cdev, CIO_OPER)) { + ret = ccw_device_notify(cdev, CIO_OPER); + if (ret) { /* Reenable channel measurements, if needed. */ - PREPARE_WORK(&cdev->private->kick_work, cmf_reenable_delayed); - queue_work(ccw_device_work, &cdev->private->kick_work); - return; - } - /* Driver doesn't want device back. */ - ccw_device_set_notoper(cdev); - PREPARE_WORK(&cdev->private->kick_work, ccw_device_do_unreg_rereg); - queue_work(ccw_device_work, &cdev->private->kick_work); + cmf_reenable(cdev); + wake_up(&cdev->private->wait_q); + } else + /* Driver doesn't want device back. */ + ccw_device_do_unreg_rereg(work); } /* @@ -394,7 +386,8 @@ ccw_device_done(struct ccw_device *cdev, int state) if (cdev->private->flags.donotify) { cdev->private->flags.donotify = 0; - ccw_device_oper_notify(cdev); + PREPARE_WORK(&cdev->private->kick_work, ccw_device_oper_notify); + queue_work(ccw_device_notify_work, &cdev->private->kick_work); } wake_up(&cdev->private->wait_q); diff --git a/trunk/drivers/s390/cio/qdio_debug.h b/trunk/drivers/s390/cio/qdio_debug.h index 5a4d85b829ad..8484b83698e1 100644 --- a/trunk/drivers/s390/cio/qdio_debug.h +++ b/trunk/drivers/s390/cio/qdio_debug.h @@ -61,18 +61,18 @@ /* s390dbf views */ #define QDIO_DBF_SETUP_LEN 8 -#define QDIO_DBF_SETUP_PAGES 8 +#define QDIO_DBF_SETUP_PAGES 4 #define QDIO_DBF_SETUP_NR_AREAS 1 #define QDIO_DBF_TRACE_LEN 8 #define QDIO_DBF_TRACE_NR_AREAS 2 #ifdef CONFIG_QDIO_DEBUG -#define QDIO_DBF_TRACE_PAGES 32 +#define QDIO_DBF_TRACE_PAGES 16 #define QDIO_DBF_SETUP_LEVEL 6 #define QDIO_DBF_TRACE_LEVEL 4 #else /* !CONFIG_QDIO_DEBUG */ -#define QDIO_DBF_TRACE_PAGES 8 +#define QDIO_DBF_TRACE_PAGES 4 #define QDIO_DBF_SETUP_LEVEL 2 #define QDIO_DBF_TRACE_LEVEL 2 #endif /* CONFIG_QDIO_DEBUG */ diff --git a/trunk/drivers/s390/cio/qdio_main.c b/trunk/drivers/s390/cio/qdio_main.c index e6eabc853422..d15648514a0f 100644 --- a/trunk/drivers/s390/cio/qdio_main.c +++ b/trunk/drivers/s390/cio/qdio_main.c @@ -330,7 +330,6 @@ static int qdio_siga_output(struct qdio_q *q) int cc; u32 busy_bit; u64 start_time = 0; - char dbf_text[15]; QDIO_DBF_TEXT5(0, trace, "sigaout"); QDIO_DBF_HEX5(0, trace, &q, sizeof(void *)); @@ -339,9 +338,6 @@ static int qdio_siga_output(struct qdio_q *q) again: cc = qdio_do_siga_output(q, &busy_bit); if (queue_type(q) == QDIO_IQDIO_QFMT && cc == 2 && busy_bit) { - sprintf(dbf_text, "bb%4x%2x", q->irq_ptr->schid.sch_no, q->nr); - QDIO_DBF_TEXT3(0, trace, dbf_text); - if (!start_time) start_time = get_usecs(); else if ((get_usecs() - start_time) < QDIO_BUSY_BIT_PATIENCE) @@ -752,18 +748,16 @@ static void qdio_kick_outbound_q(struct qdio_q *q) rc = qdio_siga_output(q); switch (rc) { case 0: + /* went smooth this time, reset timestamp */ + q->u.out.timestamp = 0; + /* TODO: improve error handling for CC=0 case */ #ifdef CONFIG_QDIO_DEBUG - if (q->u.out.timestamp) { - QDIO_DBF_TEXT3(0, trace, "cc2reslv"); - sprintf(dbf_text, "%4x%2x%2x", q->irq_ptr->schid.sch_no, - q->nr, - atomic_read(&q->u.out.busy_siga_counter)); - QDIO_DBF_TEXT3(0, trace, dbf_text); - } + QDIO_DBF_TEXT3(0, trace, "cc2reslv"); + sprintf(dbf_text, "%4x%2x%2x", q->irq_ptr->schid.sch_no, q->nr, + atomic_read(&q->u.out.busy_siga_counter)); + QDIO_DBF_TEXT3(0, trace, dbf_text); #endif /* CONFIG_QDIO_DEBUG */ - /* went smooth this time, reset timestamp */ - q->u.out.timestamp = 0; break; /* cc=2 and busy bit */ case (2 | QDIO_ERROR_SIGA_BUSY): @@ -1072,12 +1066,14 @@ void qdio_int_handler(struct ccw_device *cdev, unsigned long intparm, if (IS_ERR(irb)) { switch (PTR_ERR(irb)) { case -EIO: - sprintf(dbf_text, "ierr%4x", irq_ptr->schid.sch_no); + sprintf(dbf_text, "ierr%4x", + cdev->private->schid.sch_no); QDIO_DBF_TEXT2(1, setup, dbf_text); qdio_int_error(cdev); return; case -ETIMEDOUT: - sprintf(dbf_text, "qtoh%4x", irq_ptr->schid.sch_no); + sprintf(dbf_text, "qtoh%4x", + cdev->private->schid.sch_no); QDIO_DBF_TEXT2(1, setup, dbf_text); qdio_int_error(cdev); return; @@ -1128,10 +1124,8 @@ void qdio_int_handler(struct ccw_device *cdev, unsigned long intparm, struct qdio_ssqd_desc *qdio_get_ssqd_desc(struct ccw_device *cdev) { struct qdio_irq *irq_ptr; - char dbf_text[15]; - sprintf(dbf_text, "qssq%4x", cdev->private->schid.sch_no); - QDIO_DBF_TEXT0(0, setup, dbf_text); + QDIO_DBF_TEXT0(0, setup, "getssqd"); irq_ptr = cdev->private->qdio_data; if (!irq_ptr) @@ -1155,13 +1149,14 @@ int qdio_cleanup(struct ccw_device *cdev, int how) char dbf_text[15]; int rc; - sprintf(dbf_text, "qcln%4x", cdev->private->schid.sch_no); - QDIO_DBF_TEXT0(0, setup, dbf_text); - irq_ptr = cdev->private->qdio_data; if (!irq_ptr) return -ENODEV; + sprintf(dbf_text, "qcln%4x", irq_ptr->schid.sch_no); + QDIO_DBF_TEXT1(0, trace, dbf_text); + QDIO_DBF_TEXT0(0, setup, dbf_text); + rc = qdio_shutdown(cdev, how); if (rc == 0) rc = qdio_free(cdev); @@ -1196,9 +1191,6 @@ int qdio_shutdown(struct ccw_device *cdev, int how) unsigned long flags; char dbf_text[15]; - sprintf(dbf_text, "qshu%4x", cdev->private->schid.sch_no); - QDIO_DBF_TEXT0(0, setup, dbf_text); - irq_ptr = cdev->private->qdio_data; if (!irq_ptr) return -ENODEV; @@ -1213,6 +1205,10 @@ int qdio_shutdown(struct ccw_device *cdev, int how) return 0; } + sprintf(dbf_text, "qsqs%4x", irq_ptr->schid.sch_no); + QDIO_DBF_TEXT1(0, trace, dbf_text); + QDIO_DBF_TEXT0(0, setup, dbf_text); + tiqdio_remove_input_queues(irq_ptr); qdio_shutdown_queues(cdev); qdio_shutdown_debug_entries(irq_ptr, cdev); @@ -1251,6 +1247,7 @@ int qdio_shutdown(struct ccw_device *cdev, int how) qdio_set_state(irq_ptr, QDIO_IRQ_STATE_INACTIVE); mutex_unlock(&irq_ptr->setup_mutex); + module_put(THIS_MODULE); if (rc) return rc; return 0; @@ -1266,14 +1263,16 @@ int qdio_free(struct ccw_device *cdev) struct qdio_irq *irq_ptr; char dbf_text[15]; - sprintf(dbf_text, "qfre%4x", cdev->private->schid.sch_no); - QDIO_DBF_TEXT0(0, setup, dbf_text); - irq_ptr = cdev->private->qdio_data; if (!irq_ptr) return -ENODEV; mutex_lock(&irq_ptr->setup_mutex); + + sprintf(dbf_text, "qfqs%4x", irq_ptr->schid.sch_no); + QDIO_DBF_TEXT1(0, trace, dbf_text); + QDIO_DBF_TEXT0(0, setup, dbf_text); + cdev->private->qdio_data = NULL; mutex_unlock(&irq_ptr->setup_mutex); @@ -1296,6 +1295,7 @@ int qdio_initialize(struct qdio_initialize *init_data) sprintf(dbf_text, "qini%4x", init_data->cdev->private->schid.sch_no); QDIO_DBF_TEXT0(0, setup, dbf_text); + QDIO_DBF_TEXT0(0, trace, dbf_text); rc = qdio_allocate(init_data); if (rc) @@ -1319,6 +1319,7 @@ int qdio_allocate(struct qdio_initialize *init_data) sprintf(dbf_text, "qalc%4x", init_data->cdev->private->schid.sch_no); QDIO_DBF_TEXT0(0, setup, dbf_text); + QDIO_DBF_TEXT0(0, trace, dbf_text); if ((init_data->no_input_qs && !init_data->input_handler) || (init_data->no_output_qs && !init_data->output_handler)) @@ -1388,9 +1389,6 @@ int qdio_establish(struct qdio_initialize *init_data) unsigned long saveflags; int rc; - sprintf(dbf_text, "qest%4x", cdev->private->schid.sch_no); - QDIO_DBF_TEXT0(0, setup, dbf_text); - irq_ptr = cdev->private->qdio_data; if (!irq_ptr) return -ENODEV; @@ -1398,6 +1396,13 @@ int qdio_establish(struct qdio_initialize *init_data) if (cdev->private->state != DEV_STATE_ONLINE) return -EINVAL; + if (!try_module_get(THIS_MODULE)) + return -EINVAL; + + sprintf(dbf_text, "qest%4x", cdev->private->schid.sch_no); + QDIO_DBF_TEXT0(0, setup, dbf_text); + QDIO_DBF_TEXT0(0, trace, dbf_text); + mutex_lock(&irq_ptr->setup_mutex); qdio_setup_irq(init_data); @@ -1467,9 +1472,6 @@ int qdio_activate(struct ccw_device *cdev) unsigned long saveflags; char dbf_text[20]; - sprintf(dbf_text, "qact%4x", cdev->private->schid.sch_no); - QDIO_DBF_TEXT0(0, setup, dbf_text); - irq_ptr = cdev->private->qdio_data; if (!irq_ptr) return -ENODEV; @@ -1483,6 +1485,10 @@ int qdio_activate(struct ccw_device *cdev) goto out; } + sprintf(dbf_text, "qact%4x", irq_ptr->schid.sch_no); + QDIO_DBF_TEXT2(0, setup, dbf_text); + QDIO_DBF_TEXT2(0, trace, dbf_text); + irq_ptr->ccw.cmd_code = irq_ptr->aqueue.cmd; irq_ptr->ccw.flags = CCW_FLAG_SLI; irq_ptr->ccw.count = irq_ptr->aqueue.count; @@ -1657,7 +1663,7 @@ int do_QDIO(struct ccw_device *cdev, unsigned int callflags, #ifdef CONFIG_QDIO_DEBUG char dbf_text[20]; - sprintf(dbf_text, "doQD%4x", cdev->private->schid.sch_no); + sprintf(dbf_text, "doQD%04x", cdev->private->schid.sch_no); QDIO_DBF_TEXT3(0, trace, dbf_text); #endif /* CONFIG_QDIO_DEBUG */ diff --git a/trunk/drivers/s390/cio/qdio_setup.c b/trunk/drivers/s390/cio/qdio_setup.c index 1679e2f91c94..1bd2a208db28 100644 --- a/trunk/drivers/s390/cio/qdio_setup.c +++ b/trunk/drivers/s390/cio/qdio_setup.c @@ -165,7 +165,7 @@ static void setup_queues(struct qdio_irq *irq_ptr, void **output_sbal_array = qdio_init->output_sbal_addr_array; int i; - sprintf(dbf_text, "qset%4x", qdio_init->cdev->private->schid.sch_no); + sprintf(dbf_text, "qfqs%4x", qdio_init->cdev->private->schid.sch_no); QDIO_DBF_TEXT0(0, setup, dbf_text); for_each_input_queue(irq_ptr, q, i) { @@ -285,7 +285,7 @@ void qdio_setup_ssqd_info(struct qdio_irq *irq_ptr) rc = __get_ssqd_info(irq_ptr); if (rc) { QDIO_DBF_TEXT2(0, setup, "ssqdasig"); - sprintf(dbf_text, "schn%4x", irq_ptr->schid.sch_no); + sprintf(dbf_text, "schno%x", irq_ptr->schid.sch_no); QDIO_DBF_TEXT2(0, setup, dbf_text); sprintf(dbf_text, "rc:%d", rc); QDIO_DBF_TEXT2(0, setup, dbf_text); @@ -447,7 +447,7 @@ void qdio_print_subchannel_info(struct qdio_irq *irq_ptr, { char s[80]; - sprintf(s, "%s sc:%x ", cdev->dev.bus_id, irq_ptr->schid.sch_no); + sprintf(s, "%s ", cdev->dev.bus_id); switch (irq_ptr->qib.qfmt) { case QDIO_QETH_QFMT: diff --git a/trunk/drivers/s390/cio/qdio_thinint.c b/trunk/drivers/s390/cio/qdio_thinint.c index ea7f61400267..9291a771d812 100644 --- a/trunk/drivers/s390/cio/qdio_thinint.c +++ b/trunk/drivers/s390/cio/qdio_thinint.c @@ -113,11 +113,7 @@ void tiqdio_remove_input_queues(struct qdio_irq *irq_ptr) struct qdio_q *q; int i; - for (i = 0; i < irq_ptr->nr_input_qs; i++) { - q = irq_ptr->input_qs[i]; - /* if establish triggered an error */ - if (!q || !q->entry.prev || !q->entry.next) - continue; + for_each_input_queue(irq_ptr, q, i) { list_del_rcu(&q->entry); synchronize_rcu(); } diff --git a/trunk/drivers/s390/net/ctcm_mpc.c b/trunk/drivers/s390/net/ctcm_mpc.c index 2de1e2fccbf9..49ae1cd25caa 100644 --- a/trunk/drivers/s390/net/ctcm_mpc.c +++ b/trunk/drivers/s390/net/ctcm_mpc.c @@ -19,6 +19,7 @@ #undef DEBUGDATA #undef DEBUGCCW +#include #include #include #include diff --git a/trunk/drivers/scsi/dpt/dpti_i2o.h b/trunk/drivers/scsi/dpt/dpti_i2o.h index 179ad77f6cc9..19406cea6d6a 100644 --- a/trunk/drivers/scsi/dpt/dpti_i2o.h +++ b/trunk/drivers/scsi/dpt/dpti_i2o.h @@ -21,6 +21,7 @@ #include +#include #include #include diff --git a/trunk/drivers/scsi/ips.c b/trunk/drivers/scsi/ips.c index bc9e6ddf41df..7c615c70ec5c 100644 --- a/trunk/drivers/scsi/ips.c +++ b/trunk/drivers/scsi/ips.c @@ -165,6 +165,7 @@ #include #include #include +#include #include #include #include diff --git a/trunk/drivers/scsi/ips.h b/trunk/drivers/scsi/ips.h index 4e49fbcfe8af..e0657b6f009c 100644 --- a/trunk/drivers/scsi/ips.h +++ b/trunk/drivers/scsi/ips.h @@ -50,6 +50,7 @@ #ifndef _IPS_H_ #define _IPS_H_ +#include #include #include #include diff --git a/trunk/drivers/scsi/lpfc/lpfc_debugfs.c b/trunk/drivers/scsi/lpfc/lpfc_debugfs.c index 094b47e94b29..90272e65957a 100644 --- a/trunk/drivers/scsi/lpfc/lpfc_debugfs.c +++ b/trunk/drivers/scsi/lpfc/lpfc_debugfs.c @@ -27,6 +27,7 @@ #include #include #include +#include #include #include diff --git a/trunk/drivers/scsi/nsp32.c b/trunk/drivers/scsi/nsp32.c index 22052bb7becb..edf9fdb3cb3c 100644 --- a/trunk/drivers/scsi/nsp32.c +++ b/trunk/drivers/scsi/nsp32.c @@ -23,6 +23,7 @@ * 1.2: PowerPC (big endian) support. */ +#include #include #include #include diff --git a/trunk/drivers/scsi/nsp32.h b/trunk/drivers/scsi/nsp32.h index 9565acf1aa72..6715ecb3bfca 100644 --- a/trunk/drivers/scsi/nsp32.h +++ b/trunk/drivers/scsi/nsp32.h @@ -16,6 +16,7 @@ #ifndef _NSP32_H #define _NSP32_H +#include //#define NSP32_DEBUG 9 /* diff --git a/trunk/drivers/scsi/pcmcia/nsp_cs.c b/trunk/drivers/scsi/pcmcia/nsp_cs.c index 24e6cb8396e3..a221b6ef9fa9 100644 --- a/trunk/drivers/scsi/pcmcia/nsp_cs.c +++ b/trunk/drivers/scsi/pcmcia/nsp_cs.c @@ -25,6 +25,7 @@ ***********************************************************************/ +#include #include #include #include diff --git a/trunk/drivers/scsi/qla2xxx/qla_mid.c b/trunk/drivers/scsi/qla2xxx/qla_mid.c index 93560cd72784..50baf6a1d67c 100644 --- a/trunk/drivers/scsi/qla2xxx/qla_mid.c +++ b/trunk/drivers/scsi/qla2xxx/qla_mid.c @@ -6,6 +6,7 @@ */ #include "qla_def.h" +#include #include #include #include diff --git a/trunk/drivers/uio/Kconfig b/trunk/drivers/uio/Kconfig index 4190be64917f..2e9079df26b3 100644 --- a/trunk/drivers/uio/Kconfig +++ b/trunk/drivers/uio/Kconfig @@ -33,19 +33,6 @@ config UIO_PDRV If you don't know what to do here, say N. -config UIO_PDRV_GENIRQ - tristate "Userspace I/O platform driver with generic IRQ handling" - help - Platform driver for Userspace I/O devices, including generic - interrupt handling code. Shared interrupts are not supported. - - This kernel driver requires that the matching userspace driver - handles interrupts in a special way. Userspace is responsible - for acknowledging the hardware device if needed, and re-enabling - interrupts in the interrupt controller using the write() syscall. - - If you don't know what to do here, say N. - config UIO_SMX tristate "SMX cryptengine UIO interface" default n diff --git a/trunk/drivers/uio/Makefile b/trunk/drivers/uio/Makefile index 8667bbdef904..e00ce0def1a0 100644 --- a/trunk/drivers/uio/Makefile +++ b/trunk/drivers/uio/Makefile @@ -1,5 +1,4 @@ obj-$(CONFIG_UIO) += uio.o obj-$(CONFIG_UIO_CIF) += uio_cif.o obj-$(CONFIG_UIO_PDRV) += uio_pdrv.o -obj-$(CONFIG_UIO_PDRV_GENIRQ) += uio_pdrv_genirq.o obj-$(CONFIG_UIO_SMX) += uio_smx.o diff --git a/trunk/drivers/uio/uio_pdrv.c b/trunk/drivers/uio/uio_pdrv.c index 0b4ef39cd85d..5d0d2e85d982 100644 --- a/trunk/drivers/uio/uio_pdrv.c +++ b/trunk/drivers/uio/uio_pdrv.c @@ -88,8 +88,6 @@ static int uio_pdrv_remove(struct platform_device *pdev) uio_unregister_device(pdata->uioinfo); - kfree(pdata); - return 0; } @@ -116,5 +114,5 @@ module_exit(uio_pdrv_exit); MODULE_AUTHOR("Uwe Kleine-Koenig"); MODULE_DESCRIPTION("Userspace I/O platform driver"); -MODULE_LICENSE("GPL v2"); +MODULE_LICENSE("GPL"); MODULE_ALIAS("platform:" DRIVER_NAME); diff --git a/trunk/drivers/uio/uio_pdrv_genirq.c b/trunk/drivers/uio/uio_pdrv_genirq.c deleted file mode 100644 index 1f82c83a92ae..000000000000 --- a/trunk/drivers/uio/uio_pdrv_genirq.c +++ /dev/null @@ -1,188 +0,0 @@ -/* - * drivers/uio/uio_pdrv_genirq.c - * - * Userspace I/O platform driver with generic IRQ handling code. - * - * Copyright (C) 2008 Magnus Damm - * - * Based on uio_pdrv.c by Uwe Kleine-Koenig, - * Copyright (C) 2008 by Digi International 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 version 2 as published by - * the Free Software Foundation. - */ - -#include -#include -#include -#include -#include -#include - -#define DRIVER_NAME "uio_pdrv_genirq" - -struct uio_pdrv_genirq_platdata { - struct uio_info *uioinfo; - spinlock_t lock; - unsigned long flags; -}; - -static irqreturn_t uio_pdrv_genirq_handler(int irq, struct uio_info *dev_info) -{ - struct uio_pdrv_genirq_platdata *priv = dev_info->priv; - - /* Just disable the interrupt in the interrupt controller, and - * remember the state so we can allow user space to enable it later. - */ - - if (!test_and_set_bit(0, &priv->flags)) - disable_irq_nosync(irq); - - return IRQ_HANDLED; -} - -static int uio_pdrv_genirq_irqcontrol(struct uio_info *dev_info, s32 irq_on) -{ - struct uio_pdrv_genirq_platdata *priv = dev_info->priv; - unsigned long flags; - - /* Allow user space to enable and disable the interrupt - * in the interrupt controller, but keep track of the - * state to prevent per-irq depth damage. - * - * Serialize this operation to support multiple tasks. - */ - - spin_lock_irqsave(&priv->lock, flags); - if (irq_on) { - if (test_and_clear_bit(0, &priv->flags)) - enable_irq(dev_info->irq); - } else { - if (!test_and_set_bit(0, &priv->flags)) - disable_irq(dev_info->irq); - } - spin_unlock_irqrestore(&priv->lock, flags); - - return 0; -} - -static int uio_pdrv_genirq_probe(struct platform_device *pdev) -{ - struct uio_info *uioinfo = pdev->dev.platform_data; - struct uio_pdrv_genirq_platdata *priv; - struct uio_mem *uiomem; - int ret = -EINVAL; - int i; - - if (!uioinfo || !uioinfo->name || !uioinfo->version) { - dev_err(&pdev->dev, "missing platform_data\n"); - goto bad0; - } - - if (uioinfo->handler || uioinfo->irqcontrol || uioinfo->irq_flags) { - dev_err(&pdev->dev, "interrupt configuration error\n"); - goto bad0; - } - - priv = kzalloc(sizeof(*priv), GFP_KERNEL); - if (!priv) { - ret = -ENOMEM; - dev_err(&pdev->dev, "unable to kmalloc\n"); - goto bad0; - } - - priv->uioinfo = uioinfo; - spin_lock_init(&priv->lock); - priv->flags = 0; /* interrupt is enabled to begin with */ - - uiomem = &uioinfo->mem[0]; - - for (i = 0; i < pdev->num_resources; ++i) { - struct resource *r = &pdev->resource[i]; - - if (r->flags != IORESOURCE_MEM) - continue; - - if (uiomem >= &uioinfo->mem[MAX_UIO_MAPS]) { - dev_warn(&pdev->dev, "device has more than " - __stringify(MAX_UIO_MAPS) - " I/O memory resources.\n"); - break; - } - - uiomem->memtype = UIO_MEM_PHYS; - uiomem->addr = r->start; - uiomem->size = r->end - r->start + 1; - ++uiomem; - } - - while (uiomem < &uioinfo->mem[MAX_UIO_MAPS]) { - uiomem->size = 0; - ++uiomem; - } - - /* This driver requires no hardware specific kernel code to handle - * interrupts. Instead, the interrupt handler simply disables the - * interrupt in the interrupt controller. User space is responsible - * for performing hardware specific acknowledge and re-enabling of - * the interrupt in the interrupt controller. - * - * Interrupt sharing is not supported. - */ - - uioinfo->irq_flags = IRQF_DISABLED; - uioinfo->handler = uio_pdrv_genirq_handler; - uioinfo->irqcontrol = uio_pdrv_genirq_irqcontrol; - uioinfo->priv = priv; - - ret = uio_register_device(&pdev->dev, priv->uioinfo); - if (ret) { - dev_err(&pdev->dev, "unable to register uio device\n"); - goto bad1; - } - - platform_set_drvdata(pdev, priv); - return 0; - bad1: - kfree(priv); - bad0: - return ret; -} - -static int uio_pdrv_genirq_remove(struct platform_device *pdev) -{ - struct uio_pdrv_genirq_platdata *priv = platform_get_drvdata(pdev); - - uio_unregister_device(priv->uioinfo); - kfree(priv); - return 0; -} - -static struct platform_driver uio_pdrv_genirq = { - .probe = uio_pdrv_genirq_probe, - .remove = uio_pdrv_genirq_remove, - .driver = { - .name = DRIVER_NAME, - .owner = THIS_MODULE, - }, -}; - -static int __init uio_pdrv_genirq_init(void) -{ - return platform_driver_register(&uio_pdrv_genirq); -} - -static void __exit uio_pdrv_genirq_exit(void) -{ - platform_driver_unregister(&uio_pdrv_genirq); -} - -module_init(uio_pdrv_genirq_init); -module_exit(uio_pdrv_genirq_exit); - -MODULE_AUTHOR("Magnus Damm"); -MODULE_DESCRIPTION("Userspace I/O platform driver with generic IRQ handling"); -MODULE_LICENSE("GPL v2"); -MODULE_ALIAS("platform:" DRIVER_NAME); diff --git a/trunk/drivers/usb/atm/ueagle-atm.c b/trunk/drivers/usb/atm/ueagle-atm.c index b6483dd98acc..cb01b5106efd 100644 --- a/trunk/drivers/usb/atm/ueagle-atm.c +++ b/trunk/drivers/usb/atm/ueagle-atm.c @@ -64,6 +64,7 @@ #include #include #include +#include #include #include diff --git a/trunk/drivers/usb/class/cdc-acm.c b/trunk/drivers/usb/class/cdc-acm.c index c257453fa9de..efc4373ededb 100644 --- a/trunk/drivers/usb/class/cdc-acm.c +++ b/trunk/drivers/usb/class/cdc-acm.c @@ -589,8 +589,8 @@ static int acm_tty_open(struct tty_struct *tty, struct file *filp) tasklet_schedule(&acm->urb_task); done: - mutex_unlock(&acm->mutex); err_out: + mutex_unlock(&acm->mutex); mutex_unlock(&open_mutex); return rv; @@ -1362,9 +1362,6 @@ static struct usb_device_id acm_ids[] = { { USB_DEVICE(0x0803, 0x3095), /* Zoom Telephonics Model 3095F USB MODEM */ .driver_info = NO_UNION_NORMAL, /* has no union descriptor */ }, - { USB_DEVICE(0x0572, 0x1321), /* Conexant USB MODEM CX93010 */ - .driver_info = NO_UNION_NORMAL, /* has no union descriptor */ - }, /* control interfaces with various AT-command sets */ { USB_INTERFACE_INFO(USB_CLASS_COMM, USB_CDC_SUBCLASS_ACM, diff --git a/trunk/drivers/usb/core/driver.c b/trunk/drivers/usb/core/driver.c index 5a7fa6f09958..2be37fe466f2 100644 --- a/trunk/drivers/usb/core/driver.c +++ b/trunk/drivers/usb/core/driver.c @@ -230,13 +230,6 @@ static int usb_probe_interface(struct device *dev) */ intf->pm_usage_cnt = !(driver->supports_autosuspend); - /* Carry out a deferred switch to altsetting 0 */ - if (intf->needs_altsetting0) { - usb_set_interface(udev, intf->altsetting[0]. - desc.bInterfaceNumber, 0); - intf->needs_altsetting0 = 0; - } - error = driver->probe(intf, id); if (error) { mark_quiesced(intf); @@ -273,17 +266,8 @@ static int usb_unbind_interface(struct device *dev) driver->disconnect(intf); - /* Reset other interface state. - * We cannot do a Set-Interface if the device is suspended or - * if it is prepared for a system sleep (since installing a new - * altsetting means creating new endpoint device entries). - * When either of these happens, defer the Set-Interface. - */ - if (!error && intf->dev.power.status == DPM_ON) - usb_set_interface(udev, intf->altsetting[0]. - desc.bInterfaceNumber, 0); - else - intf->needs_altsetting0 = 1; + /* reset other interface state */ + usb_set_interface(udev, intf->altsetting[0].desc.bInterfaceNumber, 0); usb_set_intfdata(intf, NULL); intf->condition = USB_INTERFACE_UNBOUND; @@ -814,8 +798,7 @@ void usb_forced_unbind_intf(struct usb_interface *intf) * The caller must hold @intf's device's lock, but not its pm_mutex * and not @intf->dev.sem. * - * Note: Rebinds will be skipped if a system sleep transition is in - * progress and the PM "complete" callback hasn't occurred yet. + * FIXME: The caller must block system sleep transitions. */ void usb_rebind_intf(struct usb_interface *intf) { @@ -831,12 +814,10 @@ void usb_rebind_intf(struct usb_interface *intf) } /* Try to rebind the interface */ - if (intf->dev.power.status == DPM_ON) { - intf->needs_binding = 0; - rc = device_attach(&intf->dev); - if (rc < 0) - dev_warn(&intf->dev, "rebind failed: %d\n", rc); - } + intf->needs_binding = 0; + rc = device_attach(&intf->dev); + if (rc < 0) + dev_warn(&intf->dev, "rebind failed: %d\n", rc); } #ifdef CONFIG_PM @@ -848,6 +829,7 @@ void usb_rebind_intf(struct usb_interface *intf) * or rebind interfaces that have been unbound, according to @action. * * The caller must hold @udev's device lock. + * FIXME: For rebinds, the caller must block system sleep transitions. */ static void do_unbind_rebind(struct usb_device *udev, int action) { @@ -869,8 +851,22 @@ static void do_unbind_rebind(struct usb_device *udev, int action) } break; case DO_REBIND: - if (intf->needs_binding) + if (intf->needs_binding) { + + /* FIXME: The next line is needed because we are going to probe + * the interface, but as far as the PM core is concerned the + * interface is still suspended. The problem wouldn't exist + * if we could rebind the interface during the interface's own + * resume() call, but at the time the usb_device isn't locked! + * + * The real solution will be to carry this out during the device's + * complete() callback. Until that is implemented, we have to + * use this hack. + */ +// intf->dev.power.sleeping = 0; + usb_rebind_intf(intf); + } break; } } @@ -930,14 +926,14 @@ static int usb_resume_device(struct usb_device *udev) } /* Caller has locked intf's usb_device's pm mutex */ -static int usb_suspend_interface(struct usb_device *udev, - struct usb_interface *intf, pm_message_t msg) +static int usb_suspend_interface(struct usb_interface *intf, pm_message_t msg) { struct usb_driver *driver; int status = 0; /* with no hardware, USB interfaces only use FREEZE and ON states */ - if (udev->state == USB_STATE_NOTATTACHED || !is_active(intf)) + if (interface_to_usbdev(intf)->state == USB_STATE_NOTATTACHED || + !is_active(intf)) goto done; if (intf->condition == USB_INTERFACE_UNBOUND) /* This can't happen */ @@ -948,7 +944,7 @@ static int usb_suspend_interface(struct usb_device *udev, status = driver->suspend(intf, msg); if (status == 0) mark_quiesced(intf); - else if (!udev->auto_pm) + else if (!interface_to_usbdev(intf)->auto_pm) dev_err(&intf->dev, "%s error %d\n", "suspend", status); } else { @@ -965,13 +961,13 @@ static int usb_suspend_interface(struct usb_device *udev, } /* Caller has locked intf's usb_device's pm_mutex */ -static int usb_resume_interface(struct usb_device *udev, - struct usb_interface *intf, int reset_resume) +static int usb_resume_interface(struct usb_interface *intf, int reset_resume) { struct usb_driver *driver; int status = 0; - if (udev->state == USB_STATE_NOTATTACHED || is_active(intf)) + if (interface_to_usbdev(intf)->state == USB_STATE_NOTATTACHED || + is_active(intf)) goto done; /* Don't let autoresume interfere with unbinding */ @@ -979,17 +975,8 @@ static int usb_resume_interface(struct usb_device *udev, goto done; /* Can't resume it if it doesn't have a driver. */ - if (intf->condition == USB_INTERFACE_UNBOUND) { - - /* Carry out a deferred switch to altsetting 0 */ - if (intf->needs_altsetting0 && - intf->dev.power.status == DPM_ON) { - usb_set_interface(udev, intf->altsetting[0]. - desc.bInterfaceNumber, 0); - intf->needs_altsetting0 = 0; - } + if (intf->condition == USB_INTERFACE_UNBOUND) goto done; - } /* Don't resume if the interface is marked for rebinding */ if (intf->needs_binding) @@ -1164,7 +1151,7 @@ static int usb_suspend_both(struct usb_device *udev, pm_message_t msg) if (udev->actconfig) { for (; i < udev->actconfig->desc.bNumInterfaces; i++) { intf = udev->actconfig->interface[i]; - status = usb_suspend_interface(udev, intf, msg); + status = usb_suspend_interface(intf, msg); if (status != 0) break; } @@ -1176,7 +1163,7 @@ static int usb_suspend_both(struct usb_device *udev, pm_message_t msg) if (status != 0) { while (--i >= 0) { intf = udev->actconfig->interface[i]; - usb_resume_interface(udev, intf, 0); + usb_resume_interface(intf, 0); } /* Try another autosuspend when the interfaces aren't busy */ @@ -1289,7 +1276,7 @@ static int usb_resume_both(struct usb_device *udev) if (status == 0 && udev->actconfig) { for (i = 0; i < udev->actconfig->desc.bNumInterfaces; i++) { intf = udev->actconfig->interface[i]; - usb_resume_interface(udev, intf, udev->reset_resume); + usb_resume_interface(intf, udev->reset_resume); } } @@ -1618,10 +1605,12 @@ int usb_external_resume_device(struct usb_device *udev) return status; } -int usb_suspend(struct device *dev, pm_message_t message) +static int usb_suspend(struct device *dev, pm_message_t message) { struct usb_device *udev; + if (!is_usb_device(dev)) /* Ignore PM for interfaces */ + return 0; udev = to_usb_device(dev); /* If udev is already suspended, we can skip this suspend and @@ -1640,10 +1629,12 @@ int usb_suspend(struct device *dev, pm_message_t message) return usb_external_suspend_device(udev, message); } -int usb_resume(struct device *dev) +static int usb_resume(struct device *dev) { struct usb_device *udev; + if (!is_usb_device(dev)) /* Ignore PM for interfaces */ + return 0; udev = to_usb_device(dev); /* If udev->skip_sys_resume is set then udev was already suspended @@ -1655,10 +1646,17 @@ int usb_resume(struct device *dev) return usb_external_resume_device(udev); } +#else + +#define usb_suspend NULL +#define usb_resume NULL + #endif /* CONFIG_PM */ struct bus_type usb_bus_type = { .name = "usb", .match = usb_device_match, .uevent = usb_uevent, + .suspend = usb_suspend, + .resume = usb_resume, }; diff --git a/trunk/drivers/usb/core/hcd.c b/trunk/drivers/usb/core/hcd.c index 8abd4e59bf4a..f7bfd72ef115 100644 --- a/trunk/drivers/usb/core/hcd.c +++ b/trunk/drivers/usb/core/hcd.c @@ -924,6 +924,15 @@ static int register_root_hub(struct usb_hcd *hcd) return retval; } +void usb_enable_root_hub_irq (struct usb_bus *bus) +{ + struct usb_hcd *hcd; + + hcd = container_of (bus, struct usb_hcd, self); + if (hcd->driver->hub_irq_enable && hcd->state != HC_STATE_HALT) + hcd->driver->hub_irq_enable (hcd); +} + /*-------------------------------------------------------------------------*/ diff --git a/trunk/drivers/usb/core/hcd.h b/trunk/drivers/usb/core/hcd.h index e710ce04e228..5b0b59b0d89b 100644 --- a/trunk/drivers/usb/core/hcd.h +++ b/trunk/drivers/usb/core/hcd.h @@ -212,6 +212,8 @@ struct hc_driver { int (*bus_suspend)(struct usb_hcd *); int (*bus_resume)(struct usb_hcd *); int (*start_port_reset)(struct usb_hcd *, unsigned port_num); + void (*hub_irq_enable)(struct usb_hcd *); + /* Needed only if port-change IRQs are level-triggered */ /* force handover of high-speed port to full-speed companion */ void (*relinquish_port)(struct usb_hcd *, int); @@ -377,6 +379,8 @@ extern struct list_head usb_bus_list; extern struct mutex usb_bus_list_lock; extern wait_queue_head_t usb_kill_urb_queue; +extern void usb_enable_root_hub_irq(struct usb_bus *bus); + extern int usb_find_interface_driver(struct usb_device *dev, struct usb_interface *interface); diff --git a/trunk/drivers/usb/core/hub.c b/trunk/drivers/usb/core/hub.c index 6a5cb018383d..107e1d25ddec 100644 --- a/trunk/drivers/usb/core/hub.c +++ b/trunk/drivers/usb/core/hub.c @@ -2102,6 +2102,8 @@ int usb_port_resume(struct usb_device *udev) } clear_bit(port1, hub->busy_bits); + if (!hub->hdev->parent && !hub->busy_bits[0]) + usb_enable_root_hub_irq(hub->hdev->bus); status = check_port_resume_type(udev, hub, port1, status, portchange, portstatus); @@ -3079,6 +3081,11 @@ static void hub_events(void) } } + /* If this is a root hub, tell the HCD it's okay to + * re-enable port-change interrupts now. */ + if (!hdev->parent && !hub->busy_bits[0]) + usb_enable_root_hub_irq(hdev->bus); + loop_autopm: /* Allow autosuspend if we're not going to run again */ if (list_empty(&hub->event_list)) @@ -3304,6 +3311,8 @@ static int usb_reset_and_verify_device(struct usb_device *udev) break; } clear_bit(port1, parent_hub->busy_bits); + if (!parent_hdev->parent && !parent_hub->busy_bits[0]) + usb_enable_root_hub_irq(parent_hdev->bus); if (ret < 0) goto re_enumerate; diff --git a/trunk/drivers/usb/core/urb.c b/trunk/drivers/usb/core/urb.c index 47111e88f791..c0b1ae25ae2a 100644 --- a/trunk/drivers/usb/core/urb.c +++ b/trunk/drivers/usb/core/urb.c @@ -601,20 +601,15 @@ EXPORT_SYMBOL_GPL(usb_kill_anchored_urbs); void usb_unlink_anchored_urbs(struct usb_anchor *anchor) { struct urb *victim; - unsigned long flags; - spin_lock_irqsave(&anchor->lock, flags); + spin_lock_irq(&anchor->lock); while (!list_empty(&anchor->urb_list)) { victim = list_entry(anchor->urb_list.prev, struct urb, anchor_list); - usb_get_urb(victim); - spin_unlock_irqrestore(&anchor->lock, flags); /* this will unanchor the URB */ usb_unlink_urb(victim); - usb_put_urb(victim); - spin_lock_irqsave(&anchor->lock, flags); } - spin_unlock_irqrestore(&anchor->lock, flags); + spin_unlock_irq(&anchor->lock); } EXPORT_SYMBOL_GPL(usb_unlink_anchored_urbs); diff --git a/trunk/drivers/usb/core/usb.c b/trunk/drivers/usb/core/usb.c index be1fa0723f2c..84fcaa6a21ec 100644 --- a/trunk/drivers/usb/core/usb.c +++ b/trunk/drivers/usb/core/usb.c @@ -219,6 +219,12 @@ static int usb_dev_uevent(struct device *dev, struct kobj_uevent_env *env) } #endif /* CONFIG_HOTPLUG */ +struct device_type usb_device_type = { + .name = "usb_device", + .release = usb_release_dev, + .uevent = usb_dev_uevent, +}; + #ifdef CONFIG_PM static int ksuspend_usb_init(void) @@ -238,80 +244,13 @@ static void ksuspend_usb_cleanup(void) destroy_workqueue(ksuspend_usb_wq); } -/* USB device Power-Management thunks. - * There's no need to distinguish here between quiescing a USB device - * and powering it down; the generic_suspend() routine takes care of - * it by skipping the usb_port_suspend() call for a quiesce. And for - * USB interfaces there's no difference at all. - */ - -static int usb_dev_prepare(struct device *dev) -{ - return 0; /* Implement eventually? */ -} - -static void usb_dev_complete(struct device *dev) -{ - /* Currently used only for rebinding interfaces */ - usb_resume(dev); /* Implement eventually? */ -} - -static int usb_dev_suspend(struct device *dev) -{ - return usb_suspend(dev, PMSG_SUSPEND); -} - -static int usb_dev_resume(struct device *dev) -{ - return usb_resume(dev); -} - -static int usb_dev_freeze(struct device *dev) -{ - return usb_suspend(dev, PMSG_FREEZE); -} - -static int usb_dev_thaw(struct device *dev) -{ - return usb_resume(dev); -} - -static int usb_dev_poweroff(struct device *dev) -{ - return usb_suspend(dev, PMSG_HIBERNATE); -} - -static int usb_dev_restore(struct device *dev) -{ - return usb_resume(dev); -} - -static struct pm_ops usb_device_pm_ops = { - .prepare = usb_dev_prepare, - .complete = usb_dev_complete, - .suspend = usb_dev_suspend, - .resume = usb_dev_resume, - .freeze = usb_dev_freeze, - .thaw = usb_dev_thaw, - .poweroff = usb_dev_poweroff, - .restore = usb_dev_restore, -}; - #else #define ksuspend_usb_init() 0 #define ksuspend_usb_cleanup() do {} while (0) -#define usb_device_pm_ops (*(struct pm_ops *)0) #endif /* CONFIG_PM */ -struct device_type usb_device_type = { - .name = "usb_device", - .release = usb_release_dev, - .uevent = usb_dev_uevent, - .pm = &usb_device_pm_ops, -}; - /* Returns 1 if @usb_bus is WUSB, 0 otherwise */ static unsigned usb_bus_is_wusb(struct usb_bus *bus) diff --git a/trunk/drivers/usb/core/usb.h b/trunk/drivers/usb/core/usb.h index 9a1a45ac3add..d9a6e16dbf84 100644 --- a/trunk/drivers/usb/core/usb.h +++ b/trunk/drivers/usb/core/usb.h @@ -41,9 +41,6 @@ extern void usb_host_cleanup(void); #ifdef CONFIG_PM -extern int usb_suspend(struct device *dev, pm_message_t msg); -extern int usb_resume(struct device *dev); - extern void usb_autosuspend_work(struct work_struct *work); extern int usb_port_suspend(struct usb_device *dev); extern int usb_port_resume(struct usb_device *dev); diff --git a/trunk/drivers/usb/gadget/amd5536udc.c b/trunk/drivers/usb/gadget/amd5536udc.c index abf8192f89e8..1500e1b3c302 100644 --- a/trunk/drivers/usb/gadget/amd5536udc.c +++ b/trunk/drivers/usb/gadget/amd5536udc.c @@ -44,6 +44,7 @@ #include #include #include +#include #include #include #include diff --git a/trunk/drivers/usb/gadget/pxa27x_udc.c b/trunk/drivers/usb/gadget/pxa27x_udc.c index 7cbc78a6853d..a28513ecbe5b 100644 --- a/trunk/drivers/usb/gadget/pxa27x_udc.c +++ b/trunk/drivers/usb/gadget/pxa27x_udc.c @@ -1622,7 +1622,7 @@ int usb_gadget_register_driver(struct usb_gadget_driver *driver) struct pxa_udc *udc = the_controller; int retval; - if (!driver || driver->speed < USB_SPEED_FULL || !driver->bind + if (!driver || driver->speed != USB_SPEED_FULL || !driver->bind || !driver->disconnect || !driver->setup) return -EINVAL; if (!udc) diff --git a/trunk/drivers/usb/gadget/s3c2410_udc.c b/trunk/drivers/usb/gadget/s3c2410_udc.c index 29d13ebe7500..538807384592 100644 --- a/trunk/drivers/usb/gadget/s3c2410_udc.c +++ b/trunk/drivers/usb/gadget/s3c2410_udc.c @@ -35,6 +35,7 @@ #include #include #include +#include #include #include diff --git a/trunk/drivers/usb/host/isp1760-hcd.c b/trunk/drivers/usb/host/isp1760-hcd.c index 8017f1cf78e2..d22a84f86a33 100644 --- a/trunk/drivers/usb/host/isp1760-hcd.c +++ b/trunk/drivers/usb/host/isp1760-hcd.c @@ -988,7 +988,7 @@ static void do_atl_int(struct usb_hcd *usb_hcd) /* * write bank1 address twice to ensure the 90ns delay (time * between BANK0 write and the priv_read_copy() call is at - * least 3*t_WHWL + 2*t_w11 = 3*25ns + 2*17ns = 109ns) + * least 3*t_WHWL + 2*t_w11 = 3*25ns + 2*17ns = 92ns) */ isp1760_writel(payload + ISP_BANK(1), usb_hcd->regs + HC_MEMORY_REG); diff --git a/trunk/drivers/usb/host/ohci-at91.c b/trunk/drivers/usb/host/ohci-at91.c index 4ed228a89943..6db7a2889e66 100644 --- a/trunk/drivers/usb/host/ohci-at91.c +++ b/trunk/drivers/usb/host/ohci-at91.c @@ -260,6 +260,7 @@ static const struct hc_driver ohci_at91_hc_driver = { */ .hub_status_data = ohci_hub_status_data, .hub_control = ohci_hub_control, + .hub_irq_enable = ohci_rhsc_enable, #ifdef CONFIG_PM .bus_suspend = ohci_bus_suspend, .bus_resume = ohci_bus_resume, diff --git a/trunk/drivers/usb/host/ohci-au1xxx.c b/trunk/drivers/usb/host/ohci-au1xxx.c index 2ac4e022a13f..c0948008fe3d 100644 --- a/trunk/drivers/usb/host/ohci-au1xxx.c +++ b/trunk/drivers/usb/host/ohci-au1xxx.c @@ -163,6 +163,7 @@ static const struct hc_driver ohci_au1xxx_hc_driver = { */ .hub_status_data = ohci_hub_status_data, .hub_control = ohci_hub_control, + .hub_irq_enable = ohci_rhsc_enable, #ifdef CONFIG_PM .bus_suspend = ohci_bus_suspend, .bus_resume = ohci_bus_resume, diff --git a/trunk/drivers/usb/host/ohci-ep93xx.c b/trunk/drivers/usb/host/ohci-ep93xx.c index fb3055f084b5..cb0b506f8259 100644 --- a/trunk/drivers/usb/host/ohci-ep93xx.c +++ b/trunk/drivers/usb/host/ohci-ep93xx.c @@ -134,6 +134,7 @@ static struct hc_driver ohci_ep93xx_hc_driver = { .get_frame_number = ohci_get_frame, .hub_status_data = ohci_hub_status_data, .hub_control = ohci_hub_control, + .hub_irq_enable = ohci_rhsc_enable, #ifdef CONFIG_PM .bus_suspend = ohci_bus_suspend, .bus_resume = ohci_bus_resume, diff --git a/trunk/drivers/usb/host/ohci-hub.c b/trunk/drivers/usb/host/ohci-hub.c index 7ea9a7b31155..439beb784f3e 100644 --- a/trunk/drivers/usb/host/ohci-hub.c +++ b/trunk/drivers/usb/host/ohci-hub.c @@ -36,6 +36,18 @@ /*-------------------------------------------------------------------------*/ +/* hcd->hub_irq_enable() */ +static void ohci_rhsc_enable (struct usb_hcd *hcd) +{ + struct ohci_hcd *ohci = hcd_to_ohci (hcd); + + spin_lock_irq(&ohci->lock); + if (!ohci->autostop) + del_timer(&hcd->rh_timer); /* Prevent next poll */ + ohci_writel(ohci, OHCI_INTR_RHSC, &ohci->regs->intrenable); + spin_unlock_irq(&ohci->lock); +} + #define OHCI_SCHED_ENABLES \ (OHCI_CTRL_CLE|OHCI_CTRL_BLE|OHCI_CTRL_PLE|OHCI_CTRL_IE) @@ -362,28 +374,18 @@ static int ohci_root_hub_state_changes(struct ohci_hcd *ohci, int changed, int any_connected) { int poll_rh = 1; - int rhsc; - rhsc = ohci_readl(ohci, &ohci->regs->intrenable) & OHCI_INTR_RHSC; switch (ohci->hc_control & OHCI_CTRL_HCFS) { case OHCI_USB_OPER: - /* If no status changes are pending, enable status-change - * interrupts. - */ - if (!rhsc && !changed) { - rhsc = OHCI_INTR_RHSC; - ohci_writel(ohci, rhsc, &ohci->regs->intrenable); - } - - /* Keep on polling until we know a device is connected - * and RHSC is enabled, or until we autostop. - */ + /* keep on polling until we know a device is connected + * and RHSC is enabled */ if (!ohci->autostop) { if (any_connected || !device_may_wakeup(&ohci_to_hcd(ohci) ->self.root_hub->dev)) { - if (rhsc) + if (ohci_readl(ohci, &ohci->regs->intrenable) & + OHCI_INTR_RHSC) poll_rh = 0; } else { ohci->autostop = 1; @@ -396,13 +398,12 @@ static int ohci_root_hub_state_changes(struct ohci_hcd *ohci, int changed, ohci->autostop = 0; ohci->next_statechange = jiffies + STATECHANGE_DELAY; - } else if (rhsc && time_after_eq(jiffies, + } else if (time_after_eq(jiffies, ohci->next_statechange) && !ohci->ed_rm_list && !(ohci->hc_control & OHCI_SCHED_ENABLES)) { ohci_rh_suspend(ohci, 1); - poll_rh = 0; } } break; @@ -416,12 +417,6 @@ static int ohci_root_hub_state_changes(struct ohci_hcd *ohci, int changed, else usb_hcd_resume_root_hub(ohci_to_hcd(ohci)); } else { - if (!rhsc && (ohci->autostop || - ohci_to_hcd(ohci)->self.root_hub-> - do_remote_wakeup)) - ohci_writel(ohci, OHCI_INTR_RHSC, - &ohci->regs->intrenable); - /* everything is idle, no need for polling */ poll_rh = 0; } @@ -443,16 +438,12 @@ static inline int ohci_rh_resume(struct ohci_hcd *ohci) static int ohci_root_hub_state_changes(struct ohci_hcd *ohci, int changed, int any_connected) { - /* If RHSC is enabled, don't poll */ - if (ohci_readl(ohci, &ohci->regs->intrenable) & OHCI_INTR_RHSC) - return 0; + int poll_rh = 1; - /* If no status changes are pending, enable status-change interrupts */ - if (!changed) { - ohci_writel(ohci, OHCI_INTR_RHSC, &ohci->regs->intrenable); - return 0; - } - return 1; + /* keep on polling until RHSC is enabled */ + if (ohci_readl(ohci, &ohci->regs->intrenable) & OHCI_INTR_RHSC) + poll_rh = 0; + return poll_rh; } #endif /* CONFIG_PM */ diff --git a/trunk/drivers/usb/host/ohci-lh7a404.c b/trunk/drivers/usb/host/ohci-lh7a404.c index de42283149c7..9e31d440d115 100644 --- a/trunk/drivers/usb/host/ohci-lh7a404.c +++ b/trunk/drivers/usb/host/ohci-lh7a404.c @@ -193,6 +193,7 @@ static const struct hc_driver ohci_lh7a404_hc_driver = { */ .hub_status_data = ohci_hub_status_data, .hub_control = ohci_hub_control, + .hub_irq_enable = ohci_rhsc_enable, #ifdef CONFIG_PM .bus_suspend = ohci_bus_suspend, .bus_resume = ohci_bus_resume, diff --git a/trunk/drivers/usb/host/ohci-omap.c b/trunk/drivers/usb/host/ohci-omap.c index 1eb64d08b60a..3d532b709670 100644 --- a/trunk/drivers/usb/host/ohci-omap.c +++ b/trunk/drivers/usb/host/ohci-omap.c @@ -470,6 +470,7 @@ static const struct hc_driver ohci_omap_hc_driver = { */ .hub_status_data = ohci_hub_status_data, .hub_control = ohci_hub_control, + .hub_irq_enable = ohci_rhsc_enable, #ifdef CONFIG_PM .bus_suspend = ohci_bus_suspend, .bus_resume = ohci_bus_resume, diff --git a/trunk/drivers/usb/host/ohci-pci.c b/trunk/drivers/usb/host/ohci-pci.c index a9c2ae36c7ad..083e8df0a817 100644 --- a/trunk/drivers/usb/host/ohci-pci.c +++ b/trunk/drivers/usb/host/ohci-pci.c @@ -459,6 +459,7 @@ static const struct hc_driver ohci_pci_hc_driver = { */ .hub_status_data = ohci_hub_status_data, .hub_control = ohci_hub_control, + .hub_irq_enable = ohci_rhsc_enable, #ifdef CONFIG_PM .bus_suspend = ohci_bus_suspend, .bus_resume = ohci_bus_resume, diff --git a/trunk/drivers/usb/host/ohci-pnx4008.c b/trunk/drivers/usb/host/ohci-pnx4008.c index 658a2a978c32..b02cd0761977 100644 --- a/trunk/drivers/usb/host/ohci-pnx4008.c +++ b/trunk/drivers/usb/host/ohci-pnx4008.c @@ -277,6 +277,7 @@ static const struct hc_driver ohci_pnx4008_hc_driver = { */ .hub_status_data = ohci_hub_status_data, .hub_control = ohci_hub_control, + .hub_irq_enable = ohci_rhsc_enable, #ifdef CONFIG_PM .bus_suspend = ohci_bus_suspend, .bus_resume = ohci_bus_resume, diff --git a/trunk/drivers/usb/host/ohci-pnx8550.c b/trunk/drivers/usb/host/ohci-pnx8550.c index 28467e288a93..605d59cba28e 100644 --- a/trunk/drivers/usb/host/ohci-pnx8550.c +++ b/trunk/drivers/usb/host/ohci-pnx8550.c @@ -201,6 +201,7 @@ static const struct hc_driver ohci_pnx8550_hc_driver = { */ .hub_status_data = ohci_hub_status_data, .hub_control = ohci_hub_control, + .hub_irq_enable = ohci_rhsc_enable, #ifdef CONFIG_PM .bus_suspend = ohci_bus_suspend, .bus_resume = ohci_bus_resume, diff --git a/trunk/drivers/usb/host/ohci-ppc-of.c b/trunk/drivers/usb/host/ohci-ppc-of.c index 7ac53264ead3..91e6e101a4cc 100644 --- a/trunk/drivers/usb/host/ohci-ppc-of.c +++ b/trunk/drivers/usb/host/ohci-ppc-of.c @@ -72,6 +72,7 @@ static const struct hc_driver ohci_ppc_of_hc_driver = { */ .hub_status_data = ohci_hub_status_data, .hub_control = ohci_hub_control, + .hub_irq_enable = ohci_rhsc_enable, #ifdef CONFIG_PM .bus_suspend = ohci_bus_suspend, .bus_resume = ohci_bus_resume, diff --git a/trunk/drivers/usb/host/ohci-ppc-soc.c b/trunk/drivers/usb/host/ohci-ppc-soc.c index cd3398b675b2..523c30125577 100644 --- a/trunk/drivers/usb/host/ohci-ppc-soc.c +++ b/trunk/drivers/usb/host/ohci-ppc-soc.c @@ -172,6 +172,7 @@ static const struct hc_driver ohci_ppc_soc_hc_driver = { */ .hub_status_data = ohci_hub_status_data, .hub_control = ohci_hub_control, + .hub_irq_enable = ohci_rhsc_enable, #ifdef CONFIG_PM .bus_suspend = ohci_bus_suspend, .bus_resume = ohci_bus_resume, diff --git a/trunk/drivers/usb/host/ohci-ps3.c b/trunk/drivers/usb/host/ohci-ps3.c index 2089d8a46c4b..55c95647f008 100644 --- a/trunk/drivers/usb/host/ohci-ps3.c +++ b/trunk/drivers/usb/host/ohci-ps3.c @@ -68,6 +68,7 @@ static const struct hc_driver ps3_ohci_hc_driver = { .get_frame_number = ohci_get_frame, .hub_status_data = ohci_hub_status_data, .hub_control = ohci_hub_control, + .hub_irq_enable = ohci_rhsc_enable, .start_port_reset = ohci_start_port_reset, #if defined(CONFIG_PM) .bus_suspend = ohci_bus_suspend, diff --git a/trunk/drivers/usb/host/ohci-pxa27x.c b/trunk/drivers/usb/host/ohci-pxa27x.c index 7f0f35c78185..8c9c4849db6e 100644 --- a/trunk/drivers/usb/host/ohci-pxa27x.c +++ b/trunk/drivers/usb/host/ohci-pxa27x.c @@ -298,6 +298,7 @@ static const struct hc_driver ohci_pxa27x_hc_driver = { */ .hub_status_data = ohci_hub_status_data, .hub_control = ohci_hub_control, + .hub_irq_enable = ohci_rhsc_enable, #ifdef CONFIG_PM .bus_suspend = ohci_bus_suspend, .bus_resume = ohci_bus_resume, diff --git a/trunk/drivers/usb/host/ohci-s3c2410.c b/trunk/drivers/usb/host/ohci-s3c2410.c index f46af7a718d4..9e3dc4069e8b 100644 --- a/trunk/drivers/usb/host/ohci-s3c2410.c +++ b/trunk/drivers/usb/host/ohci-s3c2410.c @@ -466,6 +466,7 @@ static const struct hc_driver ohci_s3c2410_hc_driver = { */ .hub_status_data = ohci_s3c2410_hub_status_data, .hub_control = ohci_s3c2410_hub_control, + .hub_irq_enable = ohci_rhsc_enable, #ifdef CONFIG_PM .bus_suspend = ohci_bus_suspend, .bus_resume = ohci_bus_resume, diff --git a/trunk/drivers/usb/host/ohci-sa1111.c b/trunk/drivers/usb/host/ohci-sa1111.c index e4bbe8e188e4..4626b002e670 100644 --- a/trunk/drivers/usb/host/ohci-sa1111.c +++ b/trunk/drivers/usb/host/ohci-sa1111.c @@ -231,6 +231,7 @@ static const struct hc_driver ohci_sa1111_hc_driver = { */ .hub_status_data = ohci_hub_status_data, .hub_control = ohci_hub_control, + .hub_irq_enable = ohci_rhsc_enable, #ifdef CONFIG_PM .bus_suspend = ohci_bus_suspend, .bus_resume = ohci_bus_resume, diff --git a/trunk/drivers/usb/host/ohci-sh.c b/trunk/drivers/usb/host/ohci-sh.c index 60f03cc7ec4f..e7ee607278fe 100644 --- a/trunk/drivers/usb/host/ohci-sh.c +++ b/trunk/drivers/usb/host/ohci-sh.c @@ -68,6 +68,7 @@ static const struct hc_driver ohci_sh_hc_driver = { */ .hub_status_data = ohci_hub_status_data, .hub_control = ohci_hub_control, + .hub_irq_enable = ohci_rhsc_enable, #ifdef CONFIG_PM .bus_suspend = ohci_bus_suspend, .bus_resume = ohci_bus_resume, diff --git a/trunk/drivers/usb/host/ohci-sm501.c b/trunk/drivers/usb/host/ohci-sm501.c index cff23637cfcc..21b164e4abeb 100644 --- a/trunk/drivers/usb/host/ohci-sm501.c +++ b/trunk/drivers/usb/host/ohci-sm501.c @@ -75,6 +75,7 @@ static const struct hc_driver ohci_sm501_hc_driver = { */ .hub_status_data = ohci_hub_status_data, .hub_control = ohci_hub_control, + .hub_irq_enable = ohci_rhsc_enable, #ifdef CONFIG_PM .bus_suspend = ohci_bus_suspend, .bus_resume = ohci_bus_resume, diff --git a/trunk/drivers/usb/host/ohci-ssb.c b/trunk/drivers/usb/host/ohci-ssb.c index 23fd6a886bdd..3660c83d80af 100644 --- a/trunk/drivers/usb/host/ohci-ssb.c +++ b/trunk/drivers/usb/host/ohci-ssb.c @@ -81,6 +81,7 @@ static const struct hc_driver ssb_ohci_hc_driver = { .hub_status_data = ohci_hub_status_data, .hub_control = ohci_hub_control, + .hub_irq_enable = ohci_rhsc_enable, #ifdef CONFIG_PM .bus_suspend = ohci_bus_suspend, .bus_resume = ohci_bus_resume, diff --git a/trunk/drivers/usb/host/u132-hcd.c b/trunk/drivers/usb/host/u132-hcd.c index 228f2b070f2b..20ad3c48fcb2 100644 --- a/trunk/drivers/usb/host/u132-hcd.c +++ b/trunk/drivers/usb/host/u132-hcd.c @@ -2934,6 +2934,16 @@ static int u132_start_port_reset(struct usb_hcd *hcd, unsigned port_num) return 0; } +static void u132_hub_irq_enable(struct usb_hcd *hcd) +{ + struct u132 *u132 = hcd_to_u132(hcd); + if (u132->going > 1) { + dev_err(&u132->platform_dev->dev, "device has been removed %d\n" + , u132->going); + } else if (u132->going > 0) + dev_err(&u132->platform_dev->dev, "device is being removed\n"); +} + #ifdef CONFIG_PM static int u132_bus_suspend(struct usb_hcd *hcd) @@ -2985,6 +2995,7 @@ static struct hc_driver u132_hc_driver = { .bus_suspend = u132_bus_suspend, .bus_resume = u132_bus_resume, .start_port_reset = u132_start_port_reset, + .hub_irq_enable = u132_hub_irq_enable, }; /* diff --git a/trunk/drivers/usb/misc/iowarrior.c b/trunk/drivers/usb/misc/iowarrior.c index a4ef77ef917d..e6ca9979e3ae 100644 --- a/trunk/drivers/usb/misc/iowarrior.c +++ b/trunk/drivers/usb/misc/iowarrior.c @@ -19,6 +19,7 @@ #include #include #include +#include #include /* Version Information */ diff --git a/trunk/drivers/usb/misc/sisusbvga/sisusb.c b/trunk/drivers/usb/misc/sisusbvga/sisusb.c index 69c34a58e205..fbace41a7cba 100644 --- a/trunk/drivers/usb/misc/sisusbvga/sisusb.c +++ b/trunk/drivers/usb/misc/sisusbvga/sisusb.c @@ -3270,7 +3270,6 @@ static struct usb_device_id sisusb_table [] = { { USB_DEVICE(0x0711, 0x0900) }, { USB_DEVICE(0x0711, 0x0901) }, { USB_DEVICE(0x0711, 0x0902) }, - { USB_DEVICE(0x0711, 0x0918) }, { USB_DEVICE(0x182d, 0x021c) }, { USB_DEVICE(0x182d, 0x0269) }, { } diff --git a/trunk/drivers/usb/musb/Kconfig b/trunk/drivers/usb/musb/Kconfig index a0017486ad4e..faca4333f27a 100644 --- a/trunk/drivers/usb/musb/Kconfig +++ b/trunk/drivers/usb/musb/Kconfig @@ -165,11 +165,12 @@ config USB_TUSB_OMAP_DMA help Enable DMA transfers on TUSB 6010 when OMAP DMA is available. -config USB_MUSB_DEBUG +config USB_MUSB_LOGLEVEL depends on USB_MUSB_HDRC - bool "Enable debugging messages" - default n + int 'Logging Level (0 - none / 3 - annoying / ... )' + default 0 help - This enables musb debugging. To set the logging level use the debug - module parameter. Starting at level 3, per-transfer (urb, usb_request, - packet, or dma transfer) tracing may kick in. + Set the logging level. 0 disables the debugging altogether, + although when USB_DEBUG is set the value is at least 1. + Starting at level 3, per-transfer (urb, usb_request, packet, + or dma transfer) tracing may kick in. diff --git a/trunk/drivers/usb/musb/Makefile b/trunk/drivers/usb/musb/Makefile index b6af0d687a73..88eb67de08ae 100644 --- a/trunk/drivers/usb/musb/Makefile +++ b/trunk/drivers/usb/musb/Makefile @@ -64,6 +64,23 @@ endif # Debugging -ifeq ($(CONFIG_USB_MUSB_DEBUG),y) - EXTRA_CFLAGS += -DDEBUG +MUSB_DEBUG:=$(CONFIG_USB_MUSB_LOGLEVEL) + +ifeq ("$(strip $(MUSB_DEBUG))","") + ifdef CONFIG_USB_DEBUG + MUSB_DEBUG:=1 + else + MUSB_DEBUG:=0 + endif endif + +ifneq ($(MUSB_DEBUG),0) + EXTRA_CFLAGS += -DDEBUG + + ifeq ($(CONFIG_PROC_FS),y) + musb_hdrc-objs += musb_procfs.o + endif + +endif + +EXTRA_CFLAGS += -DMUSB_DEBUG=$(MUSB_DEBUG) diff --git a/trunk/drivers/usb/musb/musb_core.c b/trunk/drivers/usb/musb/musb_core.c index c5b8f0296fcf..d68ec6daf335 100644 --- a/trunk/drivers/usb/musb/musb_core.c +++ b/trunk/drivers/usb/musb/musb_core.c @@ -114,14 +114,23 @@ -unsigned debug; -module_param(debug, uint, S_IRUGO | S_IWUSR); -MODULE_PARM_DESC(debug, "Debug message level. Default = 0"); +#if MUSB_DEBUG > 0 +unsigned debug = MUSB_DEBUG; +module_param(debug, uint, 0); +MODULE_PARM_DESC(debug, "initial debug message level"); + +#define MUSB_VERSION_SUFFIX "/dbg" +#endif #define DRIVER_AUTHOR "Mentor Graphics, Texas Instruments, Nokia" #define DRIVER_DESC "Inventra Dual-Role USB Controller Driver" -#define MUSB_VERSION "6.0" +#define MUSB_VERSION_BASE "6.0" + +#ifndef MUSB_VERSION_SUFFIX +#define MUSB_VERSION_SUFFIX "" +#endif +#define MUSB_VERSION MUSB_VERSION_BASE MUSB_VERSION_SUFFIX #define DRIVER_INFO DRIVER_DESC ", v" MUSB_VERSION @@ -2028,8 +2037,6 @@ musb_init_controller(struct device *dev, int nIrq, void __iomem *ctrl) musb->xceiv.state = OTG_STATE_A_IDLE; status = usb_add_hcd(musb_to_hcd(musb), -1, 0); - if (status) - goto fail; DBG(1, "%s mode, status %d, devctl %02x %c\n", "HOST", status, @@ -2044,8 +2051,6 @@ musb_init_controller(struct device *dev, int nIrq, void __iomem *ctrl) musb->xceiv.state = OTG_STATE_B_IDLE; status = musb_gadget_setup(musb); - if (status) - goto fail; DBG(1, "%s mode, status %d, dev%02x\n", is_otg_enabled(musb) ? "OTG" : "PERIPHERAL", @@ -2054,14 +2059,16 @@ musb_init_controller(struct device *dev, int nIrq, void __iomem *ctrl) } - return 0; - + if (status == 0) + musb_debug_create("driver/musb_hdrc", musb); + else { fail: - if (musb->clock) - clk_put(musb->clock); - device_init_wakeup(dev, 0); - musb_free(musb); - return status; + if (musb->clock) + clk_put(musb->clock); + device_init_wakeup(dev, 0); + musb_free(musb); + return status; + } #ifdef CONFIG_SYSFS status = device_create_file(dev, &dev_attr_mode); @@ -2124,6 +2131,7 @@ static int __devexit musb_remove(struct platform_device *pdev) * - OTG mode: both roles are deactivated (or never-activated) */ musb_shutdown(pdev); + musb_debug_delete("driver/musb_hdrc", musb); #ifdef CONFIG_USB_MUSB_HDRC_HCD if (musb->board_mode == MUSB_HOST) usb_remove_hcd(musb_to_hcd(musb)); diff --git a/trunk/drivers/usb/musb/musb_core.h b/trunk/drivers/usb/musb/musb_core.h index 82227251931b..eade46d81708 100644 --- a/trunk/drivers/usb/musb/musb_core.h +++ b/trunk/drivers/usb/musb/musb_core.h @@ -485,4 +485,23 @@ extern int musb_platform_get_vbus_status(struct musb *musb); extern int __init musb_platform_init(struct musb *musb); extern int musb_platform_exit(struct musb *musb); +/*-------------------------- ProcFS definitions ---------------------*/ + +struct proc_dir_entry; + +#if (MUSB_DEBUG > 0) && defined(MUSB_CONFIG_PROC_FS) +extern struct proc_dir_entry *musb_debug_create(char *name, struct musb *data); +extern void musb_debug_delete(char *name, struct musb *data); + +#else +static inline struct proc_dir_entry * +musb_debug_create(char *name, struct musb *data) +{ + return NULL; +} +static inline void musb_debug_delete(char *name, struct musb *data) +{ +} +#endif + #endif /* __MUSB_CORE_H__ */ diff --git a/trunk/drivers/usb/musb/musb_debug.h b/trunk/drivers/usb/musb/musb_debug.h index 4d2794441b15..3bdb311e820d 100644 --- a/trunk/drivers/usb/musb/musb_debug.h +++ b/trunk/drivers/usb/musb/musb_debug.h @@ -48,7 +48,11 @@ __func__, __LINE__ , ## args); \ } } while (0) +#if MUSB_DEBUG > 0 extern unsigned debug; +#else +#define debug 0 +#endif static inline int _dbg_level(unsigned l) { diff --git a/trunk/drivers/usb/musb/musb_gadget_ep0.c b/trunk/drivers/usb/musb/musb_gadget_ep0.c index a57652fff39c..48d7d3ccb243 100644 --- a/trunk/drivers/usb/musb/musb_gadget_ep0.c +++ b/trunk/drivers/usb/musb/musb_gadget_ep0.c @@ -476,7 +476,6 @@ static void ep0_rxstate(struct musb *musb) return; musb->ackpend = 0; } - musb_ep_select(musb->mregs, 0); musb_writew(regs, MUSB_CSR0, tmp); } @@ -529,7 +528,6 @@ static void ep0_txstate(struct musb *musb) } /* send it out, triggering a "txpktrdy cleared" irq */ - musb_ep_select(musb->mregs, 0); musb_writew(regs, MUSB_CSR0, csr); } diff --git a/trunk/drivers/usb/musb/musb_procfs.c b/trunk/drivers/usb/musb/musb_procfs.c new file mode 100644 index 000000000000..55e6b78bdccc --- /dev/null +++ b/trunk/drivers/usb/musb/musb_procfs.c @@ -0,0 +1,830 @@ +/* + * MUSB OTG driver debug support + * + * Copyright 2005 Mentor Graphics Corporation + * Copyright (C) 2005-2006 by Texas Instruments + * Copyright (C) 2006-2007 Nokia Corporation + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will 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 to the Free Software + * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA + * 02110-1301 USA + * + * THIS SOFTWARE IS PROVIDED "AS IS" AND ANY EXPRESS OR IMPLIED + * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF + * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN + * NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT + * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF + * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON + * ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + * + */ + +#include +#include +#include +#include /* FIXME remove procfs writes */ +#include + +#include "musb_core.h" + +#include "davinci.h" + +#ifdef CONFIG_USB_MUSB_HDRC_HCD + +static int dump_qh(struct musb_qh *qh, char *buf, unsigned max) +{ + int count; + int tmp; + struct usb_host_endpoint *hep = qh->hep; + struct urb *urb; + + count = snprintf(buf, max, " qh %p dev%d ep%d%s max%d\n", + qh, qh->dev->devnum, qh->epnum, + ({ char *s; switch (qh->type) { + case USB_ENDPOINT_XFER_BULK: + s = "-bulk"; break; + case USB_ENDPOINT_XFER_INT: + s = "-int"; break; + case USB_ENDPOINT_XFER_CONTROL: + s = ""; break; + default: + s = "iso"; break; + }; s; }), + qh->maxpacket); + if (count <= 0) + return 0; + buf += count; + max -= count; + + list_for_each_entry(urb, &hep->urb_list, urb_list) { + tmp = snprintf(buf, max, "\t%s urb %p %d/%d\n", + usb_pipein(urb->pipe) ? "in" : "out", + urb, urb->actual_length, + urb->transfer_buffer_length); + if (tmp <= 0) + break; + tmp = min(tmp, (int)max); + count += tmp; + buf += tmp; + max -= tmp; + } + return count; +} + +static int +dump_queue(struct list_head *q, char *buf, unsigned max) +{ + int count = 0; + struct musb_qh *qh; + + list_for_each_entry(qh, q, ring) { + int tmp; + + tmp = dump_qh(qh, buf, max); + if (tmp <= 0) + break; + tmp = min(tmp, (int)max); + count += tmp; + buf += tmp; + max -= tmp; + } + return count; +} + +#endif /* HCD */ + +#ifdef CONFIG_USB_GADGET_MUSB_HDRC +static int dump_ep(struct musb_ep *ep, char *buffer, unsigned max) +{ + char *buf = buffer; + int code = 0; + void __iomem *regs = ep->hw_ep->regs; + char *mode = "1buf"; + + if (ep->is_in) { + if (ep->hw_ep->tx_double_buffered) + mode = "2buf"; + } else { + if (ep->hw_ep->rx_double_buffered) + mode = "2buf"; + } + + do { + struct usb_request *req; + + code = snprintf(buf, max, + "\n%s (hw%d): %s%s, csr %04x maxp %04x\n", + ep->name, ep->current_epnum, + mode, ep->dma ? " dma" : "", + musb_readw(regs, + (ep->is_in || !ep->current_epnum) + ? MUSB_TXCSR + : MUSB_RXCSR), + musb_readw(regs, ep->is_in + ? MUSB_TXMAXP + : MUSB_RXMAXP) + ); + if (code <= 0) + break; + code = min(code, (int) max); + buf += code; + max -= code; + + if (is_cppi_enabled() && ep->current_epnum) { + unsigned cppi = ep->current_epnum - 1; + void __iomem *base = ep->musb->ctrl_base; + unsigned off1 = cppi << 2; + void __iomem *ram = base; + char tmp[16]; + + if (ep->is_in) { + ram += DAVINCI_TXCPPI_STATERAM_OFFSET(cppi); + tmp[0] = 0; + } else { + ram += DAVINCI_RXCPPI_STATERAM_OFFSET(cppi); + snprintf(tmp, sizeof tmp, "%d left, ", + musb_readl(base, + DAVINCI_RXCPPI_BUFCNT0_REG + off1)); + } + + code = snprintf(buf, max, "%cX DMA%d: %s" + "%08x %08x, %08x %08x; " + "%08x %08x %08x .. %08x\n", + ep->is_in ? 'T' : 'R', + ep->current_epnum - 1, tmp, + musb_readl(ram, 0 * 4), + musb_readl(ram, 1 * 4), + musb_readl(ram, 2 * 4), + musb_readl(ram, 3 * 4), + musb_readl(ram, 4 * 4), + musb_readl(ram, 5 * 4), + musb_readl(ram, 6 * 4), + musb_readl(ram, 7 * 4)); + if (code <= 0) + break; + code = min(code, (int) max); + buf += code; + max -= code; + } + + if (list_empty(&ep->req_list)) { + code = snprintf(buf, max, "\t(queue empty)\n"); + if (code <= 0) + break; + code = min(code, (int) max); + buf += code; + max -= code; + break; + } + list_for_each_entry(req, &ep->req_list, list) { + code = snprintf(buf, max, "\treq %p, %s%s%d/%d\n", + req, + req->zero ? "zero, " : "", + req->short_not_ok ? "!short, " : "", + req->actual, req->length); + if (code <= 0) + break; + code = min(code, (int) max); + buf += code; + max -= code; + } + } while (0); + return buf - buffer; +} +#endif + +static int +dump_end_info(struct musb *musb, u8 epnum, char *aBuffer, unsigned max) +{ + int code = 0; + char *buf = aBuffer; + struct musb_hw_ep *hw_ep = &musb->endpoints[epnum]; + + do { + musb_ep_select(musb->mregs, epnum); +#ifdef CONFIG_USB_MUSB_HDRC_HCD + if (is_host_active(musb)) { + int dump_rx, dump_tx; + void __iomem *regs = hw_ep->regs; + + /* TEMPORARY (!) until we have a real periodic + * schedule tree ... + */ + if (!epnum) { + /* control is shared, uses RX queue + * but (mostly) shadowed tx registers + */ + dump_tx = !list_empty(&musb->control); + dump_rx = 0; + } else if (hw_ep == musb->bulk_ep) { + dump_tx = !list_empty(&musb->out_bulk); + dump_rx = !list_empty(&musb->in_bulk); + } else if (musb->periodic[epnum]) { + struct usb_host_endpoint *hep; + + hep = musb->periodic[epnum]->hep; + dump_rx = hep->desc.bEndpointAddress + & USB_ENDPOINT_DIR_MASK; + dump_tx = !dump_rx; + } else + break; + /* END TEMPORARY */ + + + if (dump_rx) { + code = snprintf(buf, max, + "\nRX%d: %s rxcsr %04x interval %02x " + "max %04x type %02x; " + "dev %d hub %d port %d" + "\n", + epnum, + hw_ep->rx_double_buffered + ? "2buf" : "1buf", + musb_readw(regs, MUSB_RXCSR), + musb_readb(regs, MUSB_RXINTERVAL), + musb_readw(regs, MUSB_RXMAXP), + musb_readb(regs, MUSB_RXTYPE), + /* FIXME: assumes multipoint */ + musb_readb(musb->mregs, + MUSB_BUSCTL_OFFSET(epnum, + MUSB_RXFUNCADDR)), + musb_readb(musb->mregs, + MUSB_BUSCTL_OFFSET(epnum, + MUSB_RXHUBADDR)), + musb_readb(musb->mregs, + MUSB_BUSCTL_OFFSET(epnum, + MUSB_RXHUBPORT)) + ); + if (code <= 0) + break; + code = min(code, (int) max); + buf += code; + max -= code; + + if (is_cppi_enabled() + && epnum + && hw_ep->rx_channel) { + unsigned cppi = epnum - 1; + unsigned off1 = cppi << 2; + void __iomem *base; + void __iomem *ram; + char tmp[16]; + + base = musb->ctrl_base; + ram = DAVINCI_RXCPPI_STATERAM_OFFSET( + cppi) + base; + snprintf(tmp, sizeof tmp, "%d left, ", + musb_readl(base, + DAVINCI_RXCPPI_BUFCNT0_REG + + off1)); + + code = snprintf(buf, max, + " rx dma%d: %s" + "%08x %08x, %08x %08x; " + "%08x %08x %08x .. %08x\n", + cppi, tmp, + musb_readl(ram, 0 * 4), + musb_readl(ram, 1 * 4), + musb_readl(ram, 2 * 4), + musb_readl(ram, 3 * 4), + musb_readl(ram, 4 * 4), + musb_readl(ram, 5 * 4), + musb_readl(ram, 6 * 4), + musb_readl(ram, 7 * 4)); + if (code <= 0) + break; + code = min(code, (int) max); + buf += code; + max -= code; + } + + if (hw_ep == musb->bulk_ep + && !list_empty( + &musb->in_bulk)) { + code = dump_queue(&musb->in_bulk, + buf, max); + if (code <= 0) + break; + code = min(code, (int) max); + buf += code; + max -= code; + } else if (musb->periodic[epnum]) { + code = dump_qh(musb->periodic[epnum], + buf, max); + if (code <= 0) + break; + code = min(code, (int) max); + buf += code; + max -= code; + } + } + + if (dump_tx) { + code = snprintf(buf, max, + "\nTX%d: %s txcsr %04x interval %02x " + "max %04x type %02x; " + "dev %d hub %d port %d" + "\n", + epnum, + hw_ep->tx_double_buffered + ? "2buf" : "1buf", + musb_readw(regs, MUSB_TXCSR), + musb_readb(regs, MUSB_TXINTERVAL), + musb_readw(regs, MUSB_TXMAXP), + musb_readb(regs, MUSB_TXTYPE), + /* FIXME: assumes multipoint */ + musb_readb(musb->mregs, + MUSB_BUSCTL_OFFSET(epnum, + MUSB_TXFUNCADDR)), + musb_readb(musb->mregs, + MUSB_BUSCTL_OFFSET(epnum, + MUSB_TXHUBADDR)), + musb_readb(musb->mregs, + MUSB_BUSCTL_OFFSET(epnum, + MUSB_TXHUBPORT)) + ); + if (code <= 0) + break; + code = min(code, (int) max); + buf += code; + max -= code; + + if (is_cppi_enabled() + && epnum + && hw_ep->tx_channel) { + unsigned cppi = epnum - 1; + void __iomem *base; + void __iomem *ram; + + base = musb->ctrl_base; + ram = DAVINCI_RXCPPI_STATERAM_OFFSET( + cppi) + base; + code = snprintf(buf, max, + " tx dma%d: " + "%08x %08x, %08x %08x; " + "%08x %08x %08x .. %08x\n", + cppi, + musb_readl(ram, 0 * 4), + musb_readl(ram, 1 * 4), + musb_readl(ram, 2 * 4), + musb_readl(ram, 3 * 4), + musb_readl(ram, 4 * 4), + musb_readl(ram, 5 * 4), + musb_readl(ram, 6 * 4), + musb_readl(ram, 7 * 4)); + if (code <= 0) + break; + code = min(code, (int) max); + buf += code; + max -= code; + } + + if (hw_ep == musb->control_ep + && !list_empty( + &musb->control)) { + code = dump_queue(&musb->control, + buf, max); + if (code <= 0) + break; + code = min(code, (int) max); + buf += code; + max -= code; + } else if (hw_ep == musb->bulk_ep + && !list_empty( + &musb->out_bulk)) { + code = dump_queue(&musb->out_bulk, + buf, max); + if (code <= 0) + break; + code = min(code, (int) max); + buf += code; + max -= code; + } else if (musb->periodic[epnum]) { + code = dump_qh(musb->periodic[epnum], + buf, max); + if (code <= 0) + break; + code = min(code, (int) max); + buf += code; + max -= code; + } + } + } +#endif +#ifdef CONFIG_USB_GADGET_MUSB_HDRC + if (is_peripheral_active(musb)) { + code = 0; + + if (hw_ep->ep_in.desc || !epnum) { + code = dump_ep(&hw_ep->ep_in, buf, max); + if (code <= 0) + break; + code = min(code, (int) max); + buf += code; + max -= code; + } + if (hw_ep->ep_out.desc) { + code = dump_ep(&hw_ep->ep_out, buf, max); + if (code <= 0) + break; + code = min(code, (int) max); + buf += code; + max -= code; + } + } +#endif + } while (0); + + return buf - aBuffer; +} + +/* Dump the current status and compile options. + * @param musb the device driver instance + * @param buffer where to dump the status; it must be big enough to hold the + * result otherwise "BAD THINGS HAPPENS(TM)". + */ +static int dump_header_stats(struct musb *musb, char *buffer) +{ + int code, count = 0; + const void __iomem *mbase = musb->mregs; + + *buffer = 0; + count = sprintf(buffer, "Status: %sHDRC, Mode=%s " + "(Power=%02x, DevCtl=%02x)\n", + (musb->is_multipoint ? "M" : ""), MUSB_MODE(musb), + musb_readb(mbase, MUSB_POWER), + musb_readb(mbase, MUSB_DEVCTL)); + if (count <= 0) + return 0; + buffer += count; + + code = sprintf(buffer, "OTG state: %s; %sactive\n", + otg_state_string(musb), + musb->is_active ? "" : "in"); + if (code <= 0) + goto done; + buffer += code; + count += code; + + code = sprintf(buffer, + "Options: " +#ifdef CONFIG_MUSB_PIO_ONLY + "pio" +#elif defined(CONFIG_USB_TI_CPPI_DMA) + "cppi-dma" +#elif defined(CONFIG_USB_INVENTRA_DMA) + "musb-dma" +#elif defined(CONFIG_USB_TUSB_OMAP_DMA) + "tusb-omap-dma" +#else + "?dma?" +#endif + ", " +#ifdef CONFIG_USB_MUSB_OTG + "otg (peripheral+host)" +#elif defined(CONFIG_USB_GADGET_MUSB_HDRC) + "peripheral" +#elif defined(CONFIG_USB_MUSB_HDRC_HCD) + "host" +#endif + ", debug=%d [eps=%d]\n", + debug, + musb->nr_endpoints); + if (code <= 0) + goto done; + count += code; + buffer += code; + +#ifdef CONFIG_USB_GADGET_MUSB_HDRC + code = sprintf(buffer, "Peripheral address: %02x\n", + musb_readb(musb->ctrl_base, MUSB_FADDR)); + if (code <= 0) + goto done; + buffer += code; + count += code; +#endif + +#ifdef CONFIG_USB_MUSB_HDRC_HCD + code = sprintf(buffer, "Root port status: %08x\n", + musb->port1_status); + if (code <= 0) + goto done; + buffer += code; + count += code; +#endif + +#ifdef CONFIG_ARCH_DAVINCI + code = sprintf(buffer, + "DaVinci: ctrl=%02x stat=%1x phy=%03x\n" + "\trndis=%05x auto=%04x intsrc=%08x intmsk=%08x" + "\n", + musb_readl(musb->ctrl_base, DAVINCI_USB_CTRL_REG), + musb_readl(musb->ctrl_base, DAVINCI_USB_STAT_REG), + __raw_readl((void __force __iomem *) + IO_ADDRESS(USBPHY_CTL_PADDR)), + musb_readl(musb->ctrl_base, DAVINCI_RNDIS_REG), + musb_readl(musb->ctrl_base, DAVINCI_AUTOREQ_REG), + musb_readl(musb->ctrl_base, + DAVINCI_USB_INT_SOURCE_REG), + musb_readl(musb->ctrl_base, + DAVINCI_USB_INT_MASK_REG)); + if (code <= 0) + goto done; + count += code; + buffer += code; +#endif /* DAVINCI */ + +#ifdef CONFIG_USB_TUSB6010 + code = sprintf(buffer, + "TUSB6010: devconf %08x, phy enable %08x drive %08x" + "\n\totg %03x timer %08x" + "\n\tprcm conf %08x mgmt %08x; int src %08x mask %08x" + "\n", + musb_readl(musb->ctrl_base, TUSB_DEV_CONF), + musb_readl(musb->ctrl_base, TUSB_PHY_OTG_CTRL_ENABLE), + musb_readl(musb->ctrl_base, TUSB_PHY_OTG_CTRL), + musb_readl(musb->ctrl_base, TUSB_DEV_OTG_STAT), + musb_readl(musb->ctrl_base, TUSB_DEV_OTG_TIMER), + musb_readl(musb->ctrl_base, TUSB_PRCM_CONF), + musb_readl(musb->ctrl_base, TUSB_PRCM_MNGMT), + musb_readl(musb->ctrl_base, TUSB_INT_SRC), + musb_readl(musb->ctrl_base, TUSB_INT_MASK)); + if (code <= 0) + goto done; + count += code; + buffer += code; +#endif /* DAVINCI */ + + if (is_cppi_enabled() && musb->dma_controller) { + code = sprintf(buffer, + "CPPI: txcr=%d txsrc=%01x txena=%01x; " + "rxcr=%d rxsrc=%01x rxena=%01x " + "\n", + musb_readl(musb->ctrl_base, + DAVINCI_TXCPPI_CTRL_REG), + musb_readl(musb->ctrl_base, + DAVINCI_TXCPPI_RAW_REG), + musb_readl(musb->ctrl_base, + DAVINCI_TXCPPI_INTENAB_REG), + musb_readl(musb->ctrl_base, + DAVINCI_RXCPPI_CTRL_REG), + musb_readl(musb->ctrl_base, + DAVINCI_RXCPPI_RAW_REG), + musb_readl(musb->ctrl_base, + DAVINCI_RXCPPI_INTENAB_REG)); + if (code <= 0) + goto done; + count += code; + buffer += code; + } + +#ifdef CONFIG_USB_GADGET_MUSB_HDRC + if (is_peripheral_enabled(musb)) { + code = sprintf(buffer, "Gadget driver: %s\n", + musb->gadget_driver + ? musb->gadget_driver->driver.name + : "(none)"); + if (code <= 0) + goto done; + count += code; + buffer += code; + } +#endif + +done: + return count; +} + +/* Write to ProcFS + * + * C soft-connect + * c soft-disconnect + * I enable HS + * i disable HS + * s stop session + * F force session (OTG-unfriendly) + * E rElinquish bus (OTG) + * H request host mode + * h cancel host request + * T start sending TEST_PACKET + * D set/query the debug level + */ +static int musb_proc_write(struct file *file, const char __user *buffer, + unsigned long count, void *data) +{ + char cmd; + u8 reg; + struct musb *musb = (struct musb *)data; + void __iomem *mbase = musb->mregs; + + /* MOD_INC_USE_COUNT; */ + + if (unlikely(copy_from_user(&cmd, buffer, 1))) + return -EFAULT; + + switch (cmd) { + case 'C': + if (mbase) { + reg = musb_readb(mbase, MUSB_POWER) + | MUSB_POWER_SOFTCONN; + musb_writeb(mbase, MUSB_POWER, reg); + } + break; + + case 'c': + if (mbase) { + reg = musb_readb(mbase, MUSB_POWER) + & ~MUSB_POWER_SOFTCONN; + musb_writeb(mbase, MUSB_POWER, reg); + } + break; + + case 'I': + if (mbase) { + reg = musb_readb(mbase, MUSB_POWER) + | MUSB_POWER_HSENAB; + musb_writeb(mbase, MUSB_POWER, reg); + } + break; + + case 'i': + if (mbase) { + reg = musb_readb(mbase, MUSB_POWER) + & ~MUSB_POWER_HSENAB; + musb_writeb(mbase, MUSB_POWER, reg); + } + break; + + case 'F': + reg = musb_readb(mbase, MUSB_DEVCTL); + reg |= MUSB_DEVCTL_SESSION; + musb_writeb(mbase, MUSB_DEVCTL, reg); + break; + + case 'H': + if (mbase) { + reg = musb_readb(mbase, MUSB_DEVCTL); + reg |= MUSB_DEVCTL_HR; + musb_writeb(mbase, MUSB_DEVCTL, reg); + /* MUSB_HST_MODE( ((struct musb*)data) ); */ + /* WARNING("Host Mode\n"); */ + } + break; + + case 'h': + if (mbase) { + reg = musb_readb(mbase, MUSB_DEVCTL); + reg &= ~MUSB_DEVCTL_HR; + musb_writeb(mbase, MUSB_DEVCTL, reg); + } + break; + + case 'T': + if (mbase) { + musb_load_testpacket(musb); + musb_writeb(mbase, MUSB_TESTMODE, + MUSB_TEST_PACKET); + } + break; + +#if (MUSB_DEBUG > 0) + /* set/read debug level */ + case 'D':{ + if (count > 1) { + char digits[8], *p = digits; + int i = 0, level = 0, sign = 1; + int len = min(count - 1, (unsigned long)8); + + if (copy_from_user(&digits, &buffer[1], len)) + return -EFAULT; + + /* optional sign */ + if (*p == '-') { + len -= 1; + sign = -sign; + p++; + } + + /* read it */ + while (i++ < len && *p > '0' && *p < '9') { + level = level * 10 + (*p - '0'); + p++; + } + + level *= sign; + DBG(1, "debug level %d\n", level); + debug = level; + } + } + break; + + + case '?': + INFO("?: you are seeing it\n"); + INFO("C/c: soft connect enable/disable\n"); + INFO("I/i: hispeed enable/disable\n"); + INFO("F: force session start\n"); + INFO("H: host mode\n"); + INFO("T: start sending TEST_PACKET\n"); + INFO("D: set/read dbug level\n"); + break; +#endif + + default: + ERR("Command %c not implemented\n", cmd); + break; + } + + musb_platform_try_idle(musb, 0); + + return count; +} + +static int musb_proc_read(char *page, char **start, + off_t off, int count, int *eof, void *data) +{ + char *buffer = page; + int code = 0; + unsigned long flags; + struct musb *musb = data; + unsigned epnum; + + count -= off; + count -= 1; /* for NUL at end */ + if (count <= 0) + return -EINVAL; + + spin_lock_irqsave(&musb->lock, flags); + + code = dump_header_stats(musb, buffer); + if (code > 0) { + buffer += code; + count -= code; + } + + /* generate the report for the end points */ + /* REVISIT ... not unless something's connected! */ + for (epnum = 0; count >= 0 && epnum < musb->nr_endpoints; + epnum++) { + code = dump_end_info(musb, epnum, buffer, count); + if (code > 0) { + buffer += code; + count -= code; + } + } + + musb_platform_try_idle(musb, 0); + + spin_unlock_irqrestore(&musb->lock, flags); + *eof = 1; + + return buffer - page; +} + +void __devexit musb_debug_delete(char *name, struct musb *musb) +{ + if (musb->proc_entry) + remove_proc_entry(name, NULL); +} + +struct proc_dir_entry *__init +musb_debug_create(char *name, struct musb *data) +{ + struct proc_dir_entry *pde; + + /* FIXME convert everything to seq_file; then later, debugfs */ + + if (!name) + return NULL; + + pde = create_proc_entry(name, S_IFREG | S_IRUGO | S_IWUSR, NULL); + data->proc_entry = pde; + if (pde) { + pde->data = data; + /* pde->owner = THIS_MODULE; */ + + pde->read_proc = musb_proc_read; + pde->write_proc = musb_proc_write; + + pde->size = 0; + + pr_debug("Registered /proc/%s\n", name); + } else { + pr_debug("Cannot create a valid proc file entry"); + } + + return pde; +} diff --git a/trunk/drivers/usb/serial/garmin_gps.c b/trunk/drivers/usb/serial/garmin_gps.c index d95382088075..2e663f1afd5e 100644 --- a/trunk/drivers/usb/serial/garmin_gps.c +++ b/trunk/drivers/usb/serial/garmin_gps.c @@ -38,6 +38,8 @@ #include #include +#include + /* the mode to be set when the port ist opened */ static int initial_mode = 1; diff --git a/trunk/drivers/usb/serial/option.c b/trunk/drivers/usb/serial/option.c index 9f9cd36455f4..e143198aeb02 100644 --- a/trunk/drivers/usb/serial/option.c +++ b/trunk/drivers/usb/serial/option.c @@ -173,7 +173,6 @@ static int option_send_setup(struct tty_struct *tty, struct usb_serial_port *po #define KYOCERA_PRODUCT_KPC680 0x180a #define ANYDATA_VENDOR_ID 0x16d5 -#define ANYDATA_PRODUCT_ADU_620UW 0x6202 #define ANYDATA_PRODUCT_ADU_E100A 0x6501 #define ANYDATA_PRODUCT_ADU_500A 0x6502 @@ -319,7 +318,6 @@ static struct usb_device_id option_ids[] = { { USB_DEVICE(DELL_VENDOR_ID, 0x8138) }, /* Dell Wireless 5520 Voda I Mobile Broadband (3G HSDPA) Minicard */ { USB_DEVICE(ANYDATA_VENDOR_ID, ANYDATA_PRODUCT_ADU_E100A) }, { USB_DEVICE(ANYDATA_VENDOR_ID, ANYDATA_PRODUCT_ADU_500A) }, - { USB_DEVICE(ANYDATA_VENDOR_ID, ANYDATA_PRODUCT_ADU_620UW) }, { USB_DEVICE(AXESSTEL_VENDOR_ID, AXESSTEL_PRODUCT_MV110H) }, { USB_DEVICE(ONDA_VENDOR_ID, ONDA_PRODUCT_MSA501HS) }, { USB_DEVICE(ONDA_VENDOR_ID, ONDA_PRODUCT_ET502HS) }, diff --git a/trunk/drivers/video/arkfb.c b/trunk/drivers/video/arkfb.c index 314d18694b6a..4bd569e479a7 100644 --- a/trunk/drivers/video/arkfb.c +++ b/trunk/drivers/video/arkfb.c @@ -11,6 +11,7 @@ * Code is based on s3fb */ +#include #include #include #include diff --git a/trunk/drivers/video/s3fb.c b/trunk/drivers/video/s3fb.c index 4dcec48a1d78..8361bd0e3df1 100644 --- a/trunk/drivers/video/s3fb.c +++ b/trunk/drivers/video/s3fb.c @@ -11,6 +11,7 @@ * which is based on the code of neofb. */ +#include #include #include #include diff --git a/trunk/drivers/video/vermilion/vermilion.h b/trunk/drivers/video/vermilion/vermilion.h index 7491abfcf1fc..c4aba59d4809 100644 --- a/trunk/drivers/video/vermilion/vermilion.h +++ b/trunk/drivers/video/vermilion/vermilion.h @@ -30,6 +30,7 @@ #define _VERMILION_H_ #include +#include #include #include #include diff --git a/trunk/drivers/video/vt8623fb.c b/trunk/drivers/video/vt8623fb.c index 3df17dc8c3d7..34aae7a2a62b 100644 --- a/trunk/drivers/video/vt8623fb.c +++ b/trunk/drivers/video/vt8623fb.c @@ -12,6 +12,7 @@ * (http://davesdomain.org.uk/viafb/) */ +#include #include #include #include diff --git a/trunk/drivers/video/xilinxfb.c b/trunk/drivers/video/xilinxfb.c index 5da3d2423cc0..7b3a8423f485 100644 --- a/trunk/drivers/video/xilinxfb.c +++ b/trunk/drivers/video/xilinxfb.c @@ -24,6 +24,7 @@ #include #include #include +#include #include #include #include diff --git a/trunk/drivers/virtio/virtio_balloon.c b/trunk/drivers/virtio/virtio_balloon.c index 62eab43152d2..bfef604160d1 100644 --- a/trunk/drivers/virtio/virtio_balloon.c +++ b/trunk/drivers/virtio/virtio_balloon.c @@ -158,7 +158,7 @@ static inline s64 towards_target(struct virtio_balloon *vb) vb->vdev->config->get(vb->vdev, offsetof(struct virtio_balloon_config, num_pages), &v, sizeof(v)); - return (s64)v - vb->num_pages; + return v - vb->num_pages; } static void update_balloon_size(struct virtio_balloon *vb) diff --git a/trunk/drivers/xen/manage.c b/trunk/drivers/xen/manage.c index d0e87cbe157c..a5bc91ae6ff6 100644 --- a/trunk/drivers/xen/manage.c +++ b/trunk/drivers/xen/manage.c @@ -102,7 +102,7 @@ static void do_suspend(void) /* XXX use normal device tree? */ xenbus_suspend(); - err = stop_machine(xen_suspend, &cancelled, &cpumask_of_cpu(0)); + err = stop_machine_run(xen_suspend, &cancelled, 0); if (err) { printk(KERN_ERR "failed to start xen_suspend: %d\n", err); goto out; diff --git a/trunk/fs/ext4/balloc.c b/trunk/fs/ext4/balloc.c index e9fa960ba6da..1ae5004e93fc 100644 --- a/trunk/fs/ext4/balloc.c +++ b/trunk/fs/ext4/balloc.c @@ -1626,9 +1626,6 @@ ext4_fsblk_t ext4_has_free_blocks(struct ext4_sb_info *sbi, free_blocks = percpu_counter_sum_and_set(&sbi->s_freeblocks_counter); #endif - if (free_blocks <= root_blocks) - /* we don't have free space */ - return 0; if (free_blocks - root_blocks < nblocks) return free_blocks - root_blocks; return nblocks; diff --git a/trunk/fs/ext4/dir.c b/trunk/fs/ext4/dir.c index ec8e33b45219..d3d23d73c08b 100644 --- a/trunk/fs/ext4/dir.c +++ b/trunk/fs/ext4/dir.c @@ -411,7 +411,7 @@ static int call_filldir(struct file * filp, void * dirent, get_dtype(sb, fname->file_type)); if (error) { filp->f_pos = curr_pos; - info->extra_fname = fname; + info->extra_fname = fname->next; return error; } fname = fname->next; @@ -450,21 +450,11 @@ static int ext4_dx_readdir(struct file * filp, * If there are any leftover names on the hash collision * chain, return them first. */ - if (info->extra_fname) { - if (call_filldir(filp, dirent, filldir, info->extra_fname)) - goto finished; + if (info->extra_fname && + call_filldir(filp, dirent, filldir, info->extra_fname)) + goto finished; - info->extra_fname = NULL; - info->curr_node = rb_next(info->curr_node); - if (!info->curr_node) { - if (info->next_hash == ~0) { - filp->f_pos = EXT4_HTREE_EOF; - goto finished; - } - info->curr_hash = info->next_hash; - info->curr_minor_hash = 0; - } - } else if (!info->curr_node) + if (!info->curr_node) info->curr_node = rb_first(&info->root); while (1) { diff --git a/trunk/fs/ext4/ext4.h b/trunk/fs/ext4/ext4.h index 295003241d3d..6c7924d9e358 100644 --- a/trunk/fs/ext4/ext4.h +++ b/trunk/fs/ext4/ext4.h @@ -1072,8 +1072,6 @@ extern void ext4_set_inode_flags(struct inode *); extern void ext4_get_inode_flags(struct ext4_inode_info *); extern void ext4_set_aops(struct inode *inode); extern int ext4_writepage_trans_blocks(struct inode *); -extern int ext4_meta_trans_blocks(struct inode *, int nrblocks, int idxblocks); -extern int ext4_chunk_trans_blocks(struct inode *, int nrblocks); extern int ext4_block_truncate_page(handle_t *handle, struct address_space *mapping, loff_t from); extern int ext4_page_mkwrite(struct vm_area_struct *vma, struct page *page); @@ -1229,8 +1227,6 @@ extern const struct inode_operations ext4_fast_symlink_inode_operations; /* extents.c */ extern int ext4_ext_tree_init(handle_t *handle, struct inode *); extern int ext4_ext_writepage_trans_blocks(struct inode *, int); -extern int ext4_ext_index_trans_blocks(struct inode *inode, int nrblocks, - int chunk); extern int ext4_ext_get_blocks(handle_t *handle, struct inode *inode, ext4_lblk_t iblock, unsigned long max_blocks, struct buffer_head *bh_result, diff --git a/trunk/fs/ext4/ext4_extents.h b/trunk/fs/ext4/ext4_extents.h index d33dc56d6986..6c166c0a54b7 100644 --- a/trunk/fs/ext4/ext4_extents.h +++ b/trunk/fs/ext4/ext4_extents.h @@ -216,9 +216,7 @@ extern int ext4_ext_calc_metadata_amount(struct inode *inode, int blocks); extern ext4_fsblk_t idx_pblock(struct ext4_extent_idx *); extern void ext4_ext_store_pblock(struct ext4_extent *, ext4_fsblk_t); extern int ext4_extent_tree_init(handle_t *, struct inode *); -extern int ext4_ext_calc_credits_for_single_extent(struct inode *inode, - int num, - struct ext4_ext_path *path); +extern int ext4_ext_calc_credits_for_insert(struct inode *, struct ext4_ext_path *); extern int ext4_ext_try_to_merge(struct inode *inode, struct ext4_ext_path *path, struct ext4_extent *); diff --git a/trunk/fs/ext4/ext4_jbd2.h b/trunk/fs/ext4/ext4_jbd2.h index b455c685a98b..eb8bc3afe6e9 100644 --- a/trunk/fs/ext4/ext4_jbd2.h +++ b/trunk/fs/ext4/ext4_jbd2.h @@ -51,14 +51,6 @@ EXT4_XATTR_TRANS_BLOCKS - 2 + \ 2*EXT4_QUOTA_TRANS_BLOCKS(sb)) -/* - * Define the number of metadata blocks we need to account to modify data. - * - * This include super block, inode block, quota blocks and xattr blocks - */ -#define EXT4_META_TRANS_BLOCKS(sb) (EXT4_XATTR_TRANS_BLOCKS + \ - 2*EXT4_QUOTA_TRANS_BLOCKS(sb)) - /* Delete operations potentially hit one directory's namespace plus an * entire inode, plus arbitrary amounts of bitmap/indirection data. Be * generous. We can grow the delete transaction later if necessary. */ diff --git a/trunk/fs/ext4/extents.c b/trunk/fs/ext4/extents.c index b24d3c53f20c..612c3d2c3824 100644 --- a/trunk/fs/ext4/extents.c +++ b/trunk/fs/ext4/extents.c @@ -1747,61 +1747,54 @@ static int ext4_ext_rm_idx(handle_t *handle, struct inode *inode, } /* - * ext4_ext_calc_credits_for_single_extent: - * This routine returns max. credits that needed to insert an extent - * to the extent tree. - * When pass the actual path, the caller should calculate credits - * under i_data_sem. + * ext4_ext_calc_credits_for_insert: + * This routine returns max. credits that the extent tree can consume. + * It should be OK for low-performance paths like ->writepage() + * To allow many writing processes to fit into a single transaction, + * the caller should calculate credits under i_data_sem and + * pass the actual path. */ -int ext4_ext_calc_credits_for_single_extent(struct inode *inode, int nrblocks, +int ext4_ext_calc_credits_for_insert(struct inode *inode, struct ext4_ext_path *path) { - if (path) { - int depth = ext_depth(inode); - int ret = 0; + int depth, needed; + if (path) { /* probably there is space in leaf? */ + depth = ext_depth(inode); if (le16_to_cpu(path[depth].p_hdr->eh_entries) - < le16_to_cpu(path[depth].p_hdr->eh_max)) { - - /* - * There are some space in the leaf tree, no - * need to account for leaf block credit - * - * bitmaps and block group descriptor blocks - * and other metadat blocks still need to be - * accounted. - */ - /* 1 bitmap, 1 block group descriptor */ - ret = 2 + EXT4_META_TRANS_BLOCKS(inode->i_sb); - } + < le16_to_cpu(path[depth].p_hdr->eh_max)) + return 1; } - return ext4_chunk_trans_blocks(inode, nrblocks); -} + /* + * given 32-bit logical block (4294967296 blocks), max. tree + * can be 4 levels in depth -- 4 * 340^4 == 53453440000. + * Let's also add one more level for imbalance. + */ + depth = 5; -/* - * How many index/leaf blocks need to change/allocate to modify nrblocks? - * - * if nrblocks are fit in a single extent (chunk flag is 1), then - * in the worse case, each tree level index/leaf need to be changed - * if the tree split due to insert a new extent, then the old tree - * index/leaf need to be updated too - * - * If the nrblocks are discontiguous, they could cause - * the whole tree split more than once, but this is really rare. - */ -int ext4_ext_index_trans_blocks(struct inode *inode, int nrblocks, int chunk) -{ - int index; - int depth = ext_depth(inode); + /* allocation of new data block(s) */ + needed = 2; - if (chunk) - index = depth * 2; - else - index = depth * 3; + /* + * tree can be full, so it would need to grow in depth: + * we need one credit to modify old root, credits for + * new root will be added in split accounting + */ + needed += 1; + + /* + * Index split can happen, we would need: + * allocate intermediate indexes (bitmap + group) + * + change two blocks at each level, but root (already included) + */ + needed += (depth * 2) + (depth * 2); - return index; + /* any allocation modifies superblock */ + needed += 1; + + return needed; } static int ext4_remove_blocks(handle_t *handle, struct inode *inode, @@ -1928,7 +1921,9 @@ ext4_ext_rm_leaf(handle_t *handle, struct inode *inode, correct_index = 1; credits += (ext_depth(inode)) + 1; } +#ifdef CONFIG_QUOTA credits += 2 * EXT4_QUOTA_TRANS_BLOCKS(inode->i_sb); +#endif err = ext4_ext_journal_restart(handle, credits); if (err) @@ -2810,7 +2805,7 @@ void ext4_ext_truncate(struct inode *inode) /* * probably first extent we're gonna free will be last in block */ - err = ext4_writepage_trans_blocks(inode); + err = ext4_writepage_trans_blocks(inode) + 3; handle = ext4_journal_start(inode, err); if (IS_ERR(handle)) return; @@ -2824,7 +2819,7 @@ void ext4_ext_truncate(struct inode *inode) down_write(&EXT4_I(inode)->i_data_sem); ext4_ext_invalidate_cache(inode); - ext4_discard_reservation(inode); + ext4_mb_discard_inode_preallocations(inode); /* * TODO: optimization is possible here. @@ -2863,6 +2858,27 @@ void ext4_ext_truncate(struct inode *inode) ext4_journal_stop(handle); } +/* + * ext4_ext_writepage_trans_blocks: + * calculate max number of blocks we could modify + * in order to allocate new block for an inode + */ +int ext4_ext_writepage_trans_blocks(struct inode *inode, int num) +{ + int needed; + + needed = ext4_ext_calc_credits_for_insert(inode, NULL); + + /* caller wants to allocate num blocks, but note it includes sb */ + needed = needed * num - (num - 1); + +#ifdef CONFIG_QUOTA + needed += 2 * EXT4_QUOTA_TRANS_BLOCKS(inode->i_sb); +#endif + + return needed; +} + static void ext4_falloc_update_inode(struct inode *inode, int mode, loff_t new_size, int update_ctime) { @@ -2923,9 +2939,10 @@ long ext4_fallocate(struct inode *inode, int mode, loff_t offset, loff_t len) max_blocks = (EXT4_BLOCK_ALIGN(len + offset, blkbits) >> blkbits) - block; /* - * credits to insert 1 extent into extent tree + * credits to insert 1 extent into extent tree + buffers to be able to + * modify 1 super block, 1 block bitmap and 1 group descriptor. */ - credits = ext4_chunk_trans_blocks(inode, max_blocks); + credits = EXT4_DATA_TRANS_BLOCKS(inode->i_sb) + 3; mutex_lock(&inode->i_mutex); retry: while (ret >= 0 && ret < max_blocks) { diff --git a/trunk/fs/ext4/ialloc.c b/trunk/fs/ext4/ialloc.c index f344834bbf58..655e760212b8 100644 --- a/trunk/fs/ext4/ialloc.c +++ b/trunk/fs/ext4/ialloc.c @@ -351,7 +351,7 @@ static int find_group_flex(struct super_block *sb, struct inode *parent, goto found_flexbg; } - if (flex_group[best_flex].free_inodes == 0 || + if (best_flex < 0 || (flex_group[i].free_blocks > flex_group[best_flex].free_blocks && flex_group[i].free_inodes)) diff --git a/trunk/fs/ext4/inode.c b/trunk/fs/ext4/inode.c index 7e91913e325b..59fbbe899acc 100644 --- a/trunk/fs/ext4/inode.c +++ b/trunk/fs/ext4/inode.c @@ -41,8 +41,6 @@ #include "acl.h" #include "ext4_extents.h" -#define MPAGE_DA_EXTENT_TAIL 0x01 - static inline int ext4_begin_ordered_truncate(struct inode *inode, loff_t new_size) { @@ -1007,9 +1005,6 @@ static int ext4_indirect_calc_metadata_amount(struct inode *inode, int blocks) */ static int ext4_calc_metadata_amount(struct inode *inode, int blocks) { - if (!blocks) - return 0; - if (EXT4_I(inode)->i_flags & EXT4_EXTENTS_FL) return ext4_ext_calc_metadata_amount(inode, blocks); @@ -1046,6 +1041,18 @@ static void ext4_da_update_reserve_space(struct inode *inode, int used) spin_unlock(&EXT4_I(inode)->i_block_reservation_lock); } +/* Maximum number of blocks we map for direct IO at once. */ +#define DIO_MAX_BLOCKS 4096 +/* + * Number of credits we need for writing DIO_MAX_BLOCKS: + * We need sb + group descriptor + bitmap + inode -> 4 + * For B blocks with A block pointers per block we need: + * 1 (triple ind.) + (B/A/A + 2) (doubly ind.) + (B/A + 2) (indirect). + * If we plug in 4096 for B and 256 for A (for 1KB block size), we get 25. + */ +#define DIO_CREDITS 25 + + /* * The ext4_get_blocks_wrap() function try to look up the requested blocks, * and returns if the blocks are already mapped. @@ -1157,23 +1164,19 @@ int ext4_get_blocks_wrap(handle_t *handle, struct inode *inode, sector_t block, return retval; } -/* Maximum number of blocks we map for direct IO at once. */ -#define DIO_MAX_BLOCKS 4096 - static int ext4_get_block(struct inode *inode, sector_t iblock, struct buffer_head *bh_result, int create) { handle_t *handle = ext4_journal_current_handle(); int ret = 0, started = 0; unsigned max_blocks = bh_result->b_size >> inode->i_blkbits; - int dio_credits; if (create && !handle) { /* Direct IO write... */ if (max_blocks > DIO_MAX_BLOCKS) max_blocks = DIO_MAX_BLOCKS; - dio_credits = ext4_chunk_trans_blocks(inode, max_blocks); - handle = ext4_journal_start(inode, dio_credits); + handle = ext4_journal_start(inode, DIO_CREDITS + + 2 * EXT4_QUOTA_TRANS_BLOCKS(inode->i_sb)); if (IS_ERR(handle)) { ret = PTR_ERR(handle); goto out; @@ -1556,25 +1559,7 @@ static void ext4_da_release_space(struct inode *inode, int to_free) struct ext4_sb_info *sbi = EXT4_SB(inode->i_sb); int total, mdb, mdb_free, release; - if (!to_free) - return; /* Nothing to release, exit */ - spin_lock(&EXT4_I(inode)->i_block_reservation_lock); - - if (!EXT4_I(inode)->i_reserved_data_blocks) { - /* - * if there is no reserved blocks, but we try to free some - * then the counter is messed up somewhere. - * but since this function is called from invalidate - * page, it's harmless to return without any action - */ - printk(KERN_INFO "ext4 delalloc try to release %d reserved " - "blocks for inode %lu, but there is no reserved " - "data blocks\n", to_free, inode->i_ino); - spin_unlock(&EXT4_I(inode)->i_block_reservation_lock); - return; - } - /* recalculate the number of metablocks still need to be reserved */ total = EXT4_I(inode)->i_reserved_data_blocks - to_free; mdb = ext4_calc_metadata_amount(inode, total); @@ -1628,13 +1613,11 @@ struct mpage_da_data { unsigned long first_page, next_page; /* extent of pages */ get_block_t *get_block; struct writeback_control *wbc; - int io_done; - long pages_written; }; /* * mpage_da_submit_io - walks through extent of pages and try to write - * them with writepage() call back + * them with __mpage_writepage() * * @mpd->inode: inode * @mpd->first_page: first page of the extent @@ -1649,11 +1632,18 @@ struct mpage_da_data { static int mpage_da_submit_io(struct mpage_da_data *mpd) { struct address_space *mapping = mpd->inode->i_mapping; + struct mpage_data mpd_pp = { + .bio = NULL, + .last_block_in_bio = 0, + .get_block = mpd->get_block, + .use_writepage = 1, + }; int ret = 0, err, nr_pages, i; unsigned long index, end; struct pagevec pvec; BUG_ON(mpd->next_page <= mpd->first_page); + pagevec_init(&pvec, 0); index = mpd->first_page; end = mpd->next_page - 1; @@ -1671,9 +1661,8 @@ static int mpage_da_submit_io(struct mpage_da_data *mpd) break; index++; - err = mapping->a_ops->writepage(page, mpd->wbc); - if (!err) - mpd->pages_written++; + err = __mpage_writepage(page, mpd->wbc, &mpd_pp); + /* * In error case, we have to continue because * remaining pages are still locked @@ -1684,6 +1673,9 @@ static int mpage_da_submit_io(struct mpage_da_data *mpd) } pagevec_release(&pvec); } + if (mpd_pp.bio) + mpage_bio_submit(WRITE, mpd_pp.bio); + return ret; } @@ -1706,7 +1698,7 @@ static void mpage_put_bnr_to_bhs(struct mpage_da_data *mpd, sector_t logical, int blocks = exbh->b_size >> inode->i_blkbits; sector_t pblock = exbh->b_blocknr, cur_logical; struct buffer_head *head, *bh; - pgoff_t index, end; + unsigned long index, end; struct pagevec pvec; int nr_pages, i; @@ -1749,13 +1741,6 @@ static void mpage_put_bnr_to_bhs(struct mpage_da_data *mpd, sector_t logical, if (buffer_delay(bh)) { bh->b_blocknr = pblock; clear_buffer_delay(bh); - bh->b_bdev = inode->i_sb->s_bdev; - } else if (buffer_unwritten(bh)) { - bh->b_blocknr = pblock; - clear_buffer_unwritten(bh); - set_buffer_mapped(bh); - set_buffer_new(bh); - bh->b_bdev = inode->i_sb->s_bdev; } else if (buffer_mapped(bh)) BUG_ON(bh->b_blocknr != pblock); @@ -1791,11 +1776,13 @@ static inline void __unmap_underlying_blocks(struct inode *inode, * * The function skips space we know is already mapped to disk blocks. * + * The function ignores errors ->get_block() returns, thus real + * error handling is postponed to __mpage_writepage() */ static void mpage_da_map_blocks(struct mpage_da_data *mpd) { - int err = 0; struct buffer_head *lbh = &mpd->lbh; + int err = 0, remain = lbh->b_size; sector_t next = lbh->b_blocknr; struct buffer_head new; @@ -1805,36 +1792,38 @@ static void mpage_da_map_blocks(struct mpage_da_data *mpd) if (buffer_mapped(lbh) && !buffer_delay(lbh)) return; - new.b_state = lbh->b_state; - new.b_blocknr = 0; - new.b_size = lbh->b_size; - - /* - * If we didn't accumulate anything - * to write simply return - */ - if (!new.b_size) - return; - err = mpd->get_block(mpd->inode, next, &new, 1); - if (err) - return; - BUG_ON(new.b_size == 0); + while (remain) { + new.b_state = lbh->b_state; + new.b_blocknr = 0; + new.b_size = remain; + err = mpd->get_block(mpd->inode, next, &new, 1); + if (err) { + /* + * Rather than implement own error handling + * here, we just leave remaining blocks + * unallocated and try again with ->writepage() + */ + break; + } + BUG_ON(new.b_size == 0); - if (buffer_new(&new)) - __unmap_underlying_blocks(mpd->inode, &new); + if (buffer_new(&new)) + __unmap_underlying_blocks(mpd->inode, &new); - /* - * If blocks are delayed marked, we need to - * put actual blocknr and drop delayed bit - */ - if (buffer_delay(lbh) || buffer_unwritten(lbh)) - mpage_put_bnr_to_bhs(mpd, next, &new); + /* + * If blocks are delayed marked, we need to + * put actual blocknr and drop delayed bit + */ + if (buffer_delay(lbh)) + mpage_put_bnr_to_bhs(mpd, next, &new); - return; + /* go for the remaining blocks */ + next += new.b_size >> mpd->inode->i_blkbits; + remain -= new.b_size; + } } -#define BH_FLAGS ((1 << BH_Uptodate) | (1 << BH_Mapped) | \ - (1 << BH_Delay) | (1 << BH_Unwritten)) +#define BH_FLAGS ((1 << BH_Uptodate) | (1 << BH_Mapped) | (1 << BH_Delay)) /* * mpage_add_bh_to_extent - try to add one more block to extent of blocks @@ -1848,61 +1837,41 @@ static void mpage_da_map_blocks(struct mpage_da_data *mpd) static void mpage_add_bh_to_extent(struct mpage_da_data *mpd, sector_t logical, struct buffer_head *bh) { - sector_t next; - size_t b_size = bh->b_size; struct buffer_head *lbh = &mpd->lbh; - int nrblocks = lbh->b_size >> mpd->inode->i_blkbits; + sector_t next; + + next = lbh->b_blocknr + (lbh->b_size >> mpd->inode->i_blkbits); - /* check if thereserved journal credits might overflow */ - if (!(EXT4_I(mpd->inode)->i_flags & EXT4_EXTENTS_FL)) { - if (nrblocks >= EXT4_MAX_TRANS_DATA) { - /* - * With non-extent format we are limited by the journal - * credit available. Total credit needed to insert - * nrblocks contiguous blocks is dependent on the - * nrblocks. So limit nrblocks. - */ - goto flush_it; - } else if ((nrblocks + (b_size >> mpd->inode->i_blkbits)) > - EXT4_MAX_TRANS_DATA) { - /* - * Adding the new buffer_head would make it cross the - * allowed limit for which we have journal credit - * reserved. So limit the new bh->b_size - */ - b_size = (EXT4_MAX_TRANS_DATA - nrblocks) << - mpd->inode->i_blkbits; - /* we will do mpage_da_submit_io in the next loop */ - } - } /* * First block in the extent */ if (lbh->b_size == 0) { lbh->b_blocknr = logical; - lbh->b_size = b_size; + lbh->b_size = bh->b_size; lbh->b_state = bh->b_state & BH_FLAGS; return; } - next = lbh->b_blocknr + nrblocks; /* * Can we merge the block to our big extent? */ if (logical == next && (bh->b_state & BH_FLAGS) == lbh->b_state) { - lbh->b_size += b_size; + lbh->b_size += bh->b_size; return; } -flush_it: /* * We couldn't merge the block to our extent, so we * need to flush current extent and start new one */ mpage_da_map_blocks(mpd); - mpage_da_submit_io(mpd); - mpd->io_done = 1; - return; + + /* + * Now start a new extent + */ + lbh->b_size = bh->b_size; + lbh->b_state = bh->b_state & BH_FLAGS; + lbh->b_blocknr = logical; } /* @@ -1922,35 +1891,17 @@ static int __mpage_da_writepage(struct page *page, struct buffer_head *bh, *head, fake; sector_t logical; - if (mpd->io_done) { - /* - * Rest of the page in the page_vec - * redirty then and skip then. We will - * try to to write them again after - * starting a new transaction - */ - redirty_page_for_writepage(wbc, page); - unlock_page(page); - return MPAGE_DA_EXTENT_TAIL; - } /* * Can we merge this page to current extent? */ if (mpd->next_page != page->index) { /* * Nope, we can't. So, we map non-allocated blocks - * and start IO on them using writepage() + * and start IO on them using __mpage_writepage() */ if (mpd->next_page != mpd->first_page) { mpage_da_map_blocks(mpd); mpage_da_submit_io(mpd); - /* - * skip rest of the page in the page_vec - */ - mpd->io_done = 1; - redirty_page_for_writepage(wbc, page); - unlock_page(page); - return MPAGE_DA_EXTENT_TAIL; } /* @@ -1981,8 +1932,6 @@ static int __mpage_da_writepage(struct page *page, set_buffer_dirty(bh); set_buffer_uptodate(bh); mpage_add_bh_to_extent(mpd, logical, bh); - if (mpd->io_done) - return MPAGE_DA_EXTENT_TAIL; } else { /* * Page with regular buffer heads, just add all dirty ones @@ -1991,12 +1940,8 @@ static int __mpage_da_writepage(struct page *page, bh = head; do { BUG_ON(buffer_locked(bh)); - if (buffer_dirty(bh) && - (!buffer_mapped(bh) || buffer_delay(bh))) { + if (buffer_dirty(bh)) mpage_add_bh_to_extent(mpd, logical, bh); - if (mpd->io_done) - return MPAGE_DA_EXTENT_TAIL; - } logical++; } while ((bh = bh->b_this_page) != head); } @@ -2015,13 +1960,22 @@ static int __mpage_da_writepage(struct page *page, * * This is a library function, which implements the writepages() * address_space_operation. + * + * In order to avoid duplication of logic that deals with partial pages, + * multiple bio per page, etc, we find non-allocated blocks, allocate + * them with minimal calls to ->get_block() and re-use __mpage_writepage() + * + * It's important that we call __mpage_writepage() only once for each + * involved page, otherwise we'd have to implement more complicated logic + * to deal with pages w/o PG_lock or w/ PG_writeback and so on. + * + * See comments to mpage_writepages() */ static int mpage_da_writepages(struct address_space *mapping, struct writeback_control *wbc, get_block_t get_block) { struct mpage_da_data mpd; - long to_write; int ret; if (!get_block) @@ -2035,22 +1989,17 @@ static int mpage_da_writepages(struct address_space *mapping, mpd.first_page = 0; mpd.next_page = 0; mpd.get_block = get_block; - mpd.io_done = 0; - mpd.pages_written = 0; - - to_write = wbc->nr_to_write; ret = write_cache_pages(mapping, wbc, __mpage_da_writepage, &mpd); /* * Handle last extent of pages */ - if (!mpd.io_done && mpd.next_page != mpd.first_page) { + if (mpd.next_page != mpd.first_page) { mpage_da_map_blocks(&mpd); mpage_da_submit_io(&mpd); } - wbc->nr_to_write = to_write - mpd.pages_written; return ret; } @@ -2255,95 +2204,63 @@ static int ext4_da_writepage(struct page *page, } /* - * This is called via ext4_da_writepages() to - * calulate the total number of credits to reserve to fit - * a single extent allocation into a single transaction, - * ext4_da_writpeages() will loop calling this before - * the block allocation. + * For now just follow the DIO way to estimate the max credits + * needed to write out EXT4_MAX_WRITEBACK_PAGES. + * todo: need to calculate the max credits need for + * extent based files, currently the DIO credits is based on + * indirect-blocks mapping way. + * + * Probably should have a generic way to calculate credits + * for DIO, writepages, and truncate */ - -static int ext4_da_writepages_trans_blocks(struct inode *inode) -{ - int max_blocks = EXT4_I(inode)->i_reserved_data_blocks; - - /* - * With non-extent format the journal credit needed to - * insert nrblocks contiguous block is dependent on - * number of contiguous block. So we will limit - * number of contiguous block to a sane value - */ - if (!(inode->i_flags & EXT4_EXTENTS_FL) && - (max_blocks > EXT4_MAX_TRANS_DATA)) - max_blocks = EXT4_MAX_TRANS_DATA; - - return ext4_chunk_trans_blocks(inode, max_blocks); -} +#define EXT4_MAX_WRITEBACK_PAGES DIO_MAX_BLOCKS +#define EXT4_MAX_WRITEBACK_CREDITS DIO_CREDITS static int ext4_da_writepages(struct address_space *mapping, - struct writeback_control *wbc) + struct writeback_control *wbc) { + struct inode *inode = mapping->host; handle_t *handle = NULL; + int needed_blocks; + int ret = 0; + long to_write; loff_t range_start = 0; - struct inode *inode = mapping->host; - int needed_blocks, ret = 0, nr_to_writebump = 0; - long to_write, pages_skipped = 0; - struct ext4_sb_info *sbi = EXT4_SB(mapping->host->i_sb); /* * No pages to write? This is mainly a kludge to avoid starting * a transaction for special inodes like journal inode on last iput() * because that could violate lock ordering on umount */ - if (!mapping->nrpages || !mapping_tagged(mapping, PAGECACHE_TAG_DIRTY)) + if (!mapping->nrpages) return 0; + /* - * Make sure nr_to_write is >= sbi->s_mb_stream_request - * This make sure small files blocks are allocated in - * single attempt. This ensure that small files - * get less fragmented. + * Estimate the worse case needed credits to write out + * EXT4_MAX_BUF_BLOCKS pages */ - if (wbc->nr_to_write < sbi->s_mb_stream_request) { - nr_to_writebump = sbi->s_mb_stream_request - wbc->nr_to_write; - wbc->nr_to_write = sbi->s_mb_stream_request; - } + needed_blocks = EXT4_MAX_WRITEBACK_CREDITS; - if (!wbc->range_cyclic) + to_write = wbc->nr_to_write; + if (!wbc->range_cyclic) { /* * If range_cyclic is not set force range_cont * and save the old writeback_index */ wbc->range_cont = 1; + range_start = wbc->range_start; + } - range_start = wbc->range_start; - pages_skipped = wbc->pages_skipped; - -restart_loop: - to_write = wbc->nr_to_write; - while (!ret && to_write > 0) { - - /* - * we insert one extent at a time. So we need - * credit needed for single extent allocation. - * journalled mode is currently not supported - * by delalloc - */ - BUG_ON(ext4_should_journal_data(inode)); - needed_blocks = ext4_da_writepages_trans_blocks(inode); - + while (!ret && to_write) { /* start a new transaction*/ handle = ext4_journal_start(inode, needed_blocks); if (IS_ERR(handle)) { ret = PTR_ERR(handle); - printk(KERN_EMERG "%s: jbd2_start: " - "%ld pages, ino %lu; err %d\n", __func__, - wbc->nr_to_write, inode->i_ino, ret); - dump_stack(); goto out_writepages; } if (ext4_should_order_data(inode)) { /* * With ordered mode we need to add - * the inode to the journal handl + * the inode to the journal handle * when we do block allocation. */ ret = ext4_jbd2_file_inode(handle, inode); @@ -2351,20 +2268,20 @@ static int ext4_da_writepages(struct address_space *mapping, ext4_journal_stop(handle); goto out_writepages; } + } + /* + * set the max dirty pages could be write at a time + * to fit into the reserved transaction credits + */ + if (wbc->nr_to_write > EXT4_MAX_WRITEBACK_PAGES) + wbc->nr_to_write = EXT4_MAX_WRITEBACK_PAGES; to_write -= wbc->nr_to_write; ret = mpage_da_writepages(mapping, wbc, - ext4_da_get_block_write); + ext4_da_get_block_write); ext4_journal_stop(handle); - if (ret == MPAGE_DA_EXTENT_TAIL) { - /* - * got one extent now try with - * rest of the pages - */ - to_write += wbc->nr_to_write; - ret = 0; - } else if (wbc->nr_to_write) { + if (wbc->nr_to_write) { /* * There is no more writeout needed * or we requested for a noblocking writeout @@ -2376,18 +2293,10 @@ static int ext4_da_writepages(struct address_space *mapping, wbc->nr_to_write = to_write; } - if (wbc->range_cont && (pages_skipped != wbc->pages_skipped)) { - /* We skipped pages in this loop */ - wbc->range_start = range_start; - wbc->nr_to_write = to_write + - wbc->pages_skipped - pages_skipped; - wbc->pages_skipped = pages_skipped; - goto restart_loop; - } - out_writepages: - wbc->nr_to_write = to_write - nr_to_writebump; - wbc->range_start = range_start; + wbc->nr_to_write = to_write; + if (range_start) + wbc->range_start = range_start; return ret; } @@ -3577,9 +3486,6 @@ void ext4_truncate(struct inode *inode) * modify the block allocation tree. */ down_write(&ei->i_data_sem); - - ext4_discard_reservation(inode); - /* * The orphan list entry will now protect us from any crash which * occurs before the truncate completes, so it is now safe to propagate @@ -3649,6 +3555,8 @@ void ext4_truncate(struct inode *inode) ; } + ext4_discard_reservation(inode); + up_write(&ei->i_data_sem); inode->i_mtime = inode->i_ctime = ext4_current_time(inode); ext4_mark_inode_dirty(handle, inode); @@ -4416,126 +4324,54 @@ int ext4_getattr(struct vfsmount *mnt, struct dentry *dentry, return 0; } -static int ext4_indirect_trans_blocks(struct inode *inode, int nrblocks, - int chunk) -{ - int indirects; - - /* if nrblocks are contiguous */ - if (chunk) { - /* - * With N contiguous data blocks, it need at most - * N/EXT4_ADDR_PER_BLOCK(inode->i_sb) indirect blocks - * 2 dindirect blocks - * 1 tindirect block - */ - indirects = nrblocks / EXT4_ADDR_PER_BLOCK(inode->i_sb); - return indirects + 3; - } - /* - * if nrblocks are not contiguous, worse case, each block touch - * a indirect block, and each indirect block touch a double indirect - * block, plus a triple indirect block - */ - indirects = nrblocks * 2 + 1; - return indirects; -} - -static int ext4_index_trans_blocks(struct inode *inode, int nrblocks, int chunk) -{ - if (!(EXT4_I(inode)->i_flags & EXT4_EXTENTS_FL)) - return ext4_indirect_trans_blocks(inode, nrblocks, 0); - return ext4_ext_index_trans_blocks(inode, nrblocks, 0); -} /* - * Account for index blocks, block groups bitmaps and block group - * descriptor blocks if modify datablocks and index blocks - * worse case, the indexs blocks spread over different block groups + * How many blocks doth make a writepage()? * - * If datablocks are discontiguous, they are possible to spread over - * different block groups too. If they are contiugous, with flexbg, - * they could still across block group boundary. + * With N blocks per page, it may be: + * N data blocks + * 2 indirect block + * 2 dindirect + * 1 tindirect + * N+5 bitmap blocks (from the above) + * N+5 group descriptor summary blocks + * 1 inode block + * 1 superblock. + * 2 * EXT4_SINGLEDATA_TRANS_BLOCKS for the quote files * - * Also account for superblock, inode, quota and xattr blocks - */ -int ext4_meta_trans_blocks(struct inode *inode, int nrblocks, int chunk) -{ - int groups, gdpblocks; - int idxblocks; - int ret = 0; - - /* - * How many index blocks need to touch to modify nrblocks? - * The "Chunk" flag indicating whether the nrblocks is - * physically contiguous on disk - * - * For Direct IO and fallocate, they calls get_block to allocate - * one single extent at a time, so they could set the "Chunk" flag - */ - idxblocks = ext4_index_trans_blocks(inode, nrblocks, chunk); - - ret = idxblocks; - - /* - * Now let's see how many group bitmaps and group descriptors need - * to account - */ - groups = idxblocks; - if (chunk) - groups += 1; - else - groups += nrblocks; - - gdpblocks = groups; - if (groups > EXT4_SB(inode->i_sb)->s_groups_count) - groups = EXT4_SB(inode->i_sb)->s_groups_count; - if (groups > EXT4_SB(inode->i_sb)->s_gdb_count) - gdpblocks = EXT4_SB(inode->i_sb)->s_gdb_count; - - /* bitmaps and block group descriptor blocks */ - ret += groups + gdpblocks; - - /* Blocks for super block, inode, quota and xattr blocks */ - ret += EXT4_META_TRANS_BLOCKS(inode->i_sb); - - return ret; -} - -/* - * Calulate the total number of credits to reserve to fit - * the modification of a single pages into a single transaction, - * which may include multiple chunks of block allocations. + * 3 * (N + 5) + 2 + 2 * EXT4_SINGLEDATA_TRANS_BLOCKS * - * This could be called via ext4_write_begin() + * With ordered or writeback data it's the same, less the N data blocks. * - * We need to consider the worse case, when - * one new block per extent. + * If the inode's direct blocks can hold an integral number of pages then a + * page cannot straddle two indirect blocks, and we can only touch one indirect + * and dindirect block, and the "5" above becomes "3". + * + * This still overestimates under most circumstances. If we were to pass the + * start and end offsets in here as well we could do block_to_path() on each + * block and work out the exact number of indirects which are touched. Pah. */ + int ext4_writepage_trans_blocks(struct inode *inode) { int bpp = ext4_journal_blocks_per_page(inode); + int indirects = (EXT4_NDIR_BLOCKS % bpp) ? 5 : 3; int ret; - ret = ext4_meta_trans_blocks(inode, bpp, 0); + if (EXT4_I(inode)->i_flags & EXT4_EXTENTS_FL) + return ext4_ext_writepage_trans_blocks(inode, bpp); - /* Account for data blocks for journalled mode */ if (ext4_should_journal_data(inode)) - ret += bpp; - return ret; -} + ret = 3 * (bpp + indirects) + 2; + else + ret = 2 * (bpp + indirects) + 2; -/* - * Calculate the journal credits for a chunk of data modification. - * - * This is called from DIO, fallocate or whoever calling - * ext4_get_blocks_wrap() to map/allocate a chunk of contigous disk blocks. - * - * journal buffers for data blocks are not included here, as DIO - * and fallocate do no need to journal data buffers. - */ -int ext4_chunk_trans_blocks(struct inode *inode, int nrblocks) -{ - return ext4_meta_trans_blocks(inode, nrblocks, 1); +#ifdef CONFIG_QUOTA + /* We know that structure was already allocated during DQUOT_INIT so + * we will be updating only the data blocks + inodes */ + ret += 2*EXT4_QUOTA_TRANS_BLOCKS(inode->i_sb); +#endif + + return ret; } /* diff --git a/trunk/fs/ext4/mballoc.c b/trunk/fs/ext4/mballoc.c index e0e3a5eb1ddb..865e9ddb44d4 100644 --- a/trunk/fs/ext4/mballoc.c +++ b/trunk/fs/ext4/mballoc.c @@ -3281,35 +3281,6 @@ static void ext4_mb_use_group_pa(struct ext4_allocation_context *ac, mb_debug("use %u/%u from group pa %p\n", pa->pa_lstart-len, len, pa); } -/* - * Return the prealloc space that have minimal distance - * from the goal block. @cpa is the prealloc - * space that is having currently known minimal distance - * from the goal block. - */ -static struct ext4_prealloc_space * -ext4_mb_check_group_pa(ext4_fsblk_t goal_block, - struct ext4_prealloc_space *pa, - struct ext4_prealloc_space *cpa) -{ - ext4_fsblk_t cur_distance, new_distance; - - if (cpa == NULL) { - atomic_inc(&pa->pa_count); - return pa; - } - cur_distance = abs(goal_block - cpa->pa_pstart); - new_distance = abs(goal_block - pa->pa_pstart); - - if (cur_distance < new_distance) - return cpa; - - /* drop the previous reference */ - atomic_dec(&cpa->pa_count); - atomic_inc(&pa->pa_count); - return pa; -} - /* * search goal blocks in preallocated space */ @@ -3319,8 +3290,7 @@ ext4_mb_use_preallocated(struct ext4_allocation_context *ac) int order, i; struct ext4_inode_info *ei = EXT4_I(ac->ac_inode); struct ext4_locality_group *lg; - struct ext4_prealloc_space *pa, *cpa = NULL; - ext4_fsblk_t goal_block; + struct ext4_prealloc_space *pa; /* only data can be preallocated */ if (!(ac->ac_flags & EXT4_MB_HINT_DATA)) @@ -3363,13 +3333,6 @@ ext4_mb_use_preallocated(struct ext4_allocation_context *ac) /* The max size of hash table is PREALLOC_TB_SIZE */ order = PREALLOC_TB_SIZE - 1; - goal_block = ac->ac_g_ex.fe_group * EXT4_BLOCKS_PER_GROUP(ac->ac_sb) + - ac->ac_g_ex.fe_start + - le32_to_cpu(EXT4_SB(ac->ac_sb)->s_es->s_first_data_block); - /* - * search for the prealloc space that is having - * minimal distance from the goal block. - */ for (i = order; i < PREALLOC_TB_SIZE; i++) { rcu_read_lock(); list_for_each_entry_rcu(pa, &lg->lg_prealloc_list[i], @@ -3377,19 +3340,17 @@ ext4_mb_use_preallocated(struct ext4_allocation_context *ac) spin_lock(&pa->pa_lock); if (pa->pa_deleted == 0 && pa->pa_free >= ac->ac_o_ex.fe_len) { - - cpa = ext4_mb_check_group_pa(goal_block, - pa, cpa); + atomic_inc(&pa->pa_count); + ext4_mb_use_group_pa(ac, pa); + spin_unlock(&pa->pa_lock); + ac->ac_criteria = 20; + rcu_read_unlock(); + return 1; } spin_unlock(&pa->pa_lock); } rcu_read_unlock(); } - if (cpa) { - ext4_mb_use_group_pa(ac, cpa); - ac->ac_criteria = 20; - return 1; - } return 0; } diff --git a/trunk/fs/ext4/migrate.c b/trunk/fs/ext4/migrate.c index 46fc0b5b12ba..b9e077ba07e9 100644 --- a/trunk/fs/ext4/migrate.c +++ b/trunk/fs/ext4/migrate.c @@ -53,8 +53,7 @@ static int finish_range(handle_t *handle, struct inode *inode, * credit. But below we try to not accumalate too much * of them by restarting the journal. */ - needed = ext4_ext_calc_credits_for_single_extent(inode, - lb->last_block - lb->first_block + 1, path); + needed = ext4_ext_calc_credits_for_insert(inode, path); /* * Make sure the credit we accumalated is not really high diff --git a/trunk/fs/ext4/resize.c b/trunk/fs/ext4/resize.c index b3d35604ea18..0a9265164265 100644 --- a/trunk/fs/ext4/resize.c +++ b/trunk/fs/ext4/resize.c @@ -773,8 +773,7 @@ int ext4_group_add(struct super_block *sb, struct ext4_new_group_data *input) if (reserved_gdb || gdb_off == 0) { if (!EXT4_HAS_COMPAT_FEATURE(sb, - EXT4_FEATURE_COMPAT_RESIZE_INODE) - || !le16_to_cpu(es->s_reserved_gdt_blocks)) { + EXT4_FEATURE_COMPAT_RESIZE_INODE)){ ext4_warning(sb, __func__, "No reserved GDT blocks, can't resize"); return -EPERM; diff --git a/trunk/fs/ext4/super.c b/trunk/fs/ext4/super.c index 566344b926b7..d5d77958b861 100644 --- a/trunk/fs/ext4/super.c +++ b/trunk/fs/ext4/super.c @@ -568,7 +568,6 @@ static struct inode *ext4_alloc_inode(struct super_block *sb) #endif ei->i_block_alloc_info = NULL; ei->vfs_inode.i_version = 1; - ei->vfs_inode.i_data.writeback_index = 0; memset(&ei->i_cached_extent, 0, sizeof(struct ext4_ext_cache)); INIT_LIST_HEAD(&ei->i_prealloc_list); spin_lock_init(&ei->i_prealloc_lock); diff --git a/trunk/fs/jffs2/jffs2_fs_i.h b/trunk/fs/jffs2/jffs2_fs_i.h index 4c41db91eaa4..31559f45fdde 100644 --- a/trunk/fs/jffs2/jffs2_fs_i.h +++ b/trunk/fs/jffs2/jffs2_fs_i.h @@ -12,6 +12,7 @@ #ifndef _JFFS2_FS_I #define _JFFS2_FS_I +#include #include #include #include diff --git a/trunk/fs/xfs/xfs_dmapi.h b/trunk/fs/xfs/xfs_dmapi.h index 2813cdd72375..cdc2d3464a1a 100644 --- a/trunk/fs/xfs/xfs_dmapi.h +++ b/trunk/fs/xfs/xfs_dmapi.h @@ -18,6 +18,7 @@ #ifndef __XFS_DMAPI_H__ #define __XFS_DMAPI_H__ +#include /* Values used to define the on-disk version of dm_attrname_t. All * on-disk attribute names start with the 8-byte string "SGI_DMI_". * diff --git a/trunk/include/asm-generic/rtc.h b/trunk/include/asm-generic/rtc.h index 71ef3f0b9685..be4af0029ac0 100644 --- a/trunk/include/asm-generic/rtc.h +++ b/trunk/include/asm-generic/rtc.h @@ -15,7 +15,6 @@ #include #include #include -#include #define RTC_PIE 0x40 /* periodic interrupt enable */ #define RTC_AIE 0x20 /* alarm interrupt enable */ @@ -44,6 +43,7 @@ static inline unsigned char rtc_is_updating(void) static inline unsigned int get_rtc_time(struct rtc_time *time) { + unsigned long uip_watchdog = jiffies; unsigned char ctrl; unsigned long flags; @@ -53,15 +53,19 @@ static inline unsigned int get_rtc_time(struct rtc_time *time) /* * read RTC once any update in progress is done. The update - * can take just over 2ms. We wait 20ms. There is no need to + * can take just over 2ms. We wait 10 to 20ms. There is no need to * to poll-wait (up to 1s - eeccch) for the falling edge of RTC_UIP. * If you need to know *exactly* when a second has started, enable * periodic update complete interrupts, (via ioctl) and then * immediately read /dev/rtc which will block until you get the IRQ. * Once the read clears, read the RTC time (again via ioctl). Easy. */ - if (rtc_is_updating()) - mdelay(20); + + if (rtc_is_updating() != 0) + while (jiffies - uip_watchdog < 2*HZ/100) { + barrier(); + cpu_relax(); + } /* * Only the values that we read from the RTC are set. We leave diff --git a/trunk/include/asm-x86/cpufeature.h b/trunk/include/asm-x86/cpufeature.h index 762f6a6bc707..2f5a792b0acc 100644 --- a/trunk/include/asm-x86/cpufeature.h +++ b/trunk/include/asm-x86/cpufeature.h @@ -91,7 +91,6 @@ #define X86_FEATURE_CX16 (4*32+13) /* CMPXCHG16B */ #define X86_FEATURE_XTPR (4*32+14) /* Send Task Priority Messages */ #define X86_FEATURE_DCA (4*32+18) /* Direct Cache Access */ -#define X86_FEATURE_XMM4_2 (4*32+20) /* Streaming SIMD Extensions-4.2 */ /* VIA/Cyrix/Centaur-defined CPU features, CPUID level 0xC0000001, word 5 */ #define X86_FEATURE_XSTORE (5*32+ 2) /* on-CPU RNG present (xstore insn) */ @@ -190,7 +189,6 @@ extern const char * const x86_power_flags[32]; #define cpu_has_gbpages boot_cpu_has(X86_FEATURE_GBPAGES) #define cpu_has_arch_perfmon boot_cpu_has(X86_FEATURE_ARCH_PERFMON) #define cpu_has_pat boot_cpu_has(X86_FEATURE_PAT) -#define cpu_has_xmm4_2 boot_cpu_has(X86_FEATURE_XMM4_2) #if defined(CONFIG_X86_INVLPG) || defined(CONFIG_X86_64) # define cpu_has_invlpg 1 diff --git a/trunk/include/asm-x86/genapic_32.h b/trunk/include/asm-x86/genapic_32.h index 754d635f90ff..b02ea6e17de8 100644 --- a/trunk/include/asm-x86/genapic_32.h +++ b/trunk/include/asm-x86/genapic_32.h @@ -118,7 +118,6 @@ enum uv_system_type {UV_NONE, UV_LEGACY_APIC, UV_X2APIC, UV_NON_UNIQUE_APIC}; #define get_uv_system_type() UV_NONE #define is_uv_system() 0 #define uv_wakeup_secondary(a, b) 1 -#define uv_system_init() do {} while (0) #endif diff --git a/trunk/include/asm-x86/genapic_64.h b/trunk/include/asm-x86/genapic_64.h index a47d63129135..0f8504627c41 100644 --- a/trunk/include/asm-x86/genapic_64.h +++ b/trunk/include/asm-x86/genapic_64.h @@ -42,7 +42,6 @@ extern int is_uv_system(void); extern struct genapic apic_x2apic_uv_x; DECLARE_PER_CPU(int, x2apic_extra_bits); extern void uv_cpu_init(void); -extern void uv_system_init(void); extern int uv_wakeup_secondary(int phys_apicid, unsigned int start_rip); extern void setup_apic_routing(void); diff --git a/trunk/include/asm-x86/irq_vectors.h b/trunk/include/asm-x86/irq_vectors.h index a48c7f2dbdc0..b95d167b7fb2 100644 --- a/trunk/include/asm-x86/irq_vectors.h +++ b/trunk/include/asm-x86/irq_vectors.h @@ -76,7 +76,6 @@ #define CALL_FUNCTION_SINGLE_VECTOR 0xfb #define THERMAL_APIC_VECTOR 0xfa #define THRESHOLD_APIC_VECTOR 0xf9 -#define UV_BAU_MESSAGE 0xf8 #define INVALIDATE_TLB_VECTOR_END 0xf7 #define INVALIDATE_TLB_VECTOR_START 0xf0 /* f0-f7 used for TLB flush */ diff --git a/trunk/include/asm-x86/kvm_host.h b/trunk/include/asm-x86/kvm_host.h index c2e34c275900..0f3c53114614 100644 --- a/trunk/include/asm-x86/kvm_host.h +++ b/trunk/include/asm-x86/kvm_host.h @@ -722,7 +722,7 @@ asmlinkage void kvm_handle_fault_on_reboot(void); #define __kvm_handle_fault_on_reboot(insn) \ "666: " insn "\n\t" \ - ".pushsection .fixup, \"ax\" \n" \ + ".pushsection .text.fixup, \"ax\" \n" \ "667: \n\t" \ KVM_EX_PUSH " $666b \n\t" \ "jmp kvm_handle_fault_on_reboot \n\t" \ diff --git a/trunk/include/asm-x86/mce.h b/trunk/include/asm-x86/mce.h index 531eaa587455..94f1fd79e22a 100644 --- a/trunk/include/asm-x86/mce.h +++ b/trunk/include/asm-x86/mce.h @@ -92,7 +92,6 @@ extern int mce_disabled; void mce_log(struct mce *m); DECLARE_PER_CPU(struct sys_device, device_mce); -extern void (*threshold_cpu_callback)(unsigned long action, unsigned int cpu); #ifdef CONFIG_X86_MCE_INTEL void mce_intel_feature_init(struct cpuinfo_x86 *c); diff --git a/trunk/include/asm-x86/uv/uv_bau.h b/trunk/include/asm-x86/uv/uv_bau.h index 610b6b308e93..91ac0dfb7588 100644 --- a/trunk/include/asm-x86/uv/uv_bau.h +++ b/trunk/include/asm-x86/uv/uv_bau.h @@ -40,6 +40,11 @@ #define UV_ACTIVATION_DESCRIPTOR_SIZE 32 #define UV_DISTRIBUTION_SIZE 256 #define UV_SW_ACK_NPENDING 8 +#define UV_BAU_MESSAGE 200 +/* + * Messaging irq; see irq_64.h and include/asm-x86/hw_irq_64.h + * To be dynamically allocated in the future + */ #define UV_NET_ENDPOINT_INTD 0x38 #define UV_DESC_BASE_PNODE_SHIFT 49 #define UV_PAYLOADQ_PNODE_SHIFT 49 diff --git a/trunk/include/asm-x86/xen/hypervisor.h b/trunk/include/asm-x86/xen/hypervisor.h index 04ee0610014a..8e15dd28c91f 100644 --- a/trunk/include/asm-x86/xen/hypervisor.h +++ b/trunk/include/asm-x86/xen/hypervisor.h @@ -35,6 +35,7 @@ #include #include +#include #include #include diff --git a/trunk/include/linux/device.h b/trunk/include/linux/device.h index 4d8372d135df..d24a47f80f9c 100644 --- a/trunk/include/linux/device.h +++ b/trunk/include/linux/device.h @@ -358,7 +358,6 @@ struct device { struct kobject kobj; char bus_id[BUS_ID_SIZE]; /* position on parent bus */ - const char *init_name; /* initial name of the device */ struct device_type *type; unsigned uevent_suppress:1; @@ -407,7 +406,7 @@ struct device { /* Get the wakeup routines, which depend on struct device */ #include -static inline const char *dev_name(const struct device *dev) +static inline const char *dev_name(struct device *dev) { /* will be changed into kobject_name(&dev->kobj) in the near future */ return dev->bus_id; @@ -519,7 +518,7 @@ extern void device_shutdown(void); extern void sysdev_shutdown(void); /* debugging and troubleshooting/diagnostic helpers. */ -extern const char *dev_driver_string(const struct device *dev); +extern const char *dev_driver_string(struct device *dev); #define dev_printk(level, dev, format, arg...) \ printk(level "%s %s: " format , dev_driver_string(dev) , \ dev_name(dev) , ## arg) diff --git a/trunk/include/linux/fs_uart_pd.h b/trunk/include/linux/fs_uart_pd.h index 36b61ff39277..809bb9ffc788 100644 --- a/trunk/include/linux/fs_uart_pd.h +++ b/trunk/include/linux/fs_uart_pd.h @@ -12,6 +12,7 @@ #ifndef FS_UART_PD_H #define FS_UART_PD_H +#include #include enum fs_uart_id { diff --git a/trunk/include/linux/kvm.h b/trunk/include/linux/kvm.h index 70a30651cd12..69511f74f912 100644 --- a/trunk/include/linux/kvm.h +++ b/trunk/include/linux/kvm.h @@ -320,12 +320,12 @@ struct kvm_trace_rec { struct { __u64 cycle_u64; __u32 extra_u32[KVM_TRC_EXTRA_MAX]; - } __attribute__((packed)) cycle; + } cycle; struct { __u32 extra_u32[KVM_TRC_EXTRA_MAX]; } nocycle; } u; -}; +} __attribute__((packed)); #define KVMIO 0xAE diff --git a/trunk/include/linux/libata.h b/trunk/include/linux/libata.h index 225bfc5bd9ec..06b80337303b 100644 --- a/trunk/include/linux/libata.h +++ b/trunk/include/linux/libata.h @@ -163,7 +163,6 @@ enum { ATA_DEV_NONE = 9, /* no device */ /* struct ata_link flags */ - ATA_LFLAG_NO_HRST = (1 << 1), /* avoid hardreset */ ATA_LFLAG_NO_SRST = (1 << 2), /* avoid softreset */ ATA_LFLAG_ASSUME_ATA = (1 << 3), /* assume ATA class */ ATA_LFLAG_ASSUME_SEMB = (1 << 4), /* assume SEMB class */ @@ -647,7 +646,6 @@ struct ata_link { unsigned int flags; /* ATA_LFLAG_xxx */ - u32 saved_scontrol; /* SControl on probe */ unsigned int hw_sata_spd_limit; unsigned int sata_spd_limit; unsigned int sata_spd; /* current SATA PHY speed */ @@ -1429,28 +1427,6 @@ static inline unsigned long ata_deadline(unsigned long from_jiffies, return from_jiffies + msecs_to_jiffies(timeout_msecs); } -/* Don't open code these in drivers as there are traps. Firstly the range may - change in future hardware and specs, secondly 0xFF means 'no DMA' but is - > UDMA_0. Dyma ddreigiau */ - -static inline int ata_using_mwdma(struct ata_device *adev) -{ - if (adev->dma_mode >= XFER_MW_DMA_0 && adev->dma_mode <= XFER_MW_DMA_4) - return 1; - return 0; -} - -static inline int ata_using_udma(struct ata_device *adev) -{ - if (adev->dma_mode >= XFER_UDMA_0 && adev->dma_mode <= XFER_UDMA_7) - return 1; - return 0; -} - -static inline int ata_dma_enabled(struct ata_device *adev) -{ - return (adev->dma_mode == 0xFF ? 0 : 1); -} /************************************************************************** * PMP - drivers/ata/libata-pmp.c diff --git a/trunk/include/linux/stop_machine.h b/trunk/include/linux/stop_machine.h index faf1519b5adc..f1cb0ba6d715 100644 --- a/trunk/include/linux/stop_machine.h +++ b/trunk/include/linux/stop_machine.h @@ -3,13 +3,16 @@ /* "Bogolock": stop the entire machine, disable interrupts. This is a very heavy lock, which is equivalent to grabbing every spinlock (and more). So the "read" side to such a lock is anything which - disables preeempt. */ + diables preeempt. */ #include #include #include #if defined(CONFIG_STOP_MACHINE) && defined(CONFIG_SMP) +/* Deprecated, but useful for transition. */ +#define ALL_CPUS ~0U + /** * stop_machine: freeze the machine on all CPUs and run this function * @fn: the function to run @@ -47,4 +50,18 @@ static inline int stop_machine(int (*fn)(void *), void *data, return ret; } #endif /* CONFIG_SMP */ + +static inline int __deprecated stop_machine_run(int (*fn)(void *), void *data, + unsigned int cpu) +{ + /* If they don't care which cpu fn runs on, just pick one. */ + if (cpu == NR_CPUS) + return stop_machine(fn, data, NULL); + else if (cpu == ~0U) + return stop_machine(fn, data, &cpu_possible_map); + else { + cpumask_t cpus = cpumask_of_cpu(cpu); + return stop_machine(fn, data, &cpus); + } +} #endif /* _LINUX_STOP_MACHINE */ diff --git a/trunk/include/linux/tick.h b/trunk/include/linux/tick.h index 8cf8cfe2cc97..d3c02695dc5d 100644 --- a/trunk/include/linux/tick.h +++ b/trunk/include/linux/tick.h @@ -74,13 +74,10 @@ extern struct tick_device *tick_get_device(int cpu); extern int tick_init_highres(void); extern int tick_program_event(ktime_t expires, int force); extern void tick_setup_sched_timer(void); -# endif - -# if defined CONFIG_NO_HZ || defined CONFIG_HIGH_RES_TIMERS extern void tick_cancel_sched_timer(int cpu); # else static inline void tick_cancel_sched_timer(int cpu) { } -# endif +# endif /* HIGHRES */ # ifdef CONFIG_GENERIC_CLOCKEVENTS_BROADCAST extern struct tick_device *tick_get_broadcast_device(void); diff --git a/trunk/include/linux/usb.h b/trunk/include/linux/usb.h index 94ac74aba6b6..0924cd9c30f6 100644 --- a/trunk/include/linux/usb.h +++ b/trunk/include/linux/usb.h @@ -110,8 +110,6 @@ enum usb_interface_condition { * @sysfs_files_created: sysfs attributes exist * @needs_remote_wakeup: flag set when the driver requires remote-wakeup * capability during autosuspend. - * @needs_altsetting0: flag set when a set-interface request for altsetting 0 - * has been deferred. * @needs_binding: flag set when the driver should be re-probed or unbound * following a reset or suspend operation it doesn't support. * @dev: driver model's view of this device @@ -164,7 +162,6 @@ struct usb_interface { unsigned is_active:1; /* the interface is not suspended */ unsigned sysfs_files_created:1; /* the sysfs attributes exist */ unsigned needs_remote_wakeup:1; /* driver requires remote wakeup */ - unsigned needs_altsetting0:1; /* switch to altsetting 0 is pending */ unsigned needs_binding:1; /* needs delayed unbind/rebind */ struct device dev; /* interface specific device info */ diff --git a/trunk/kernel/module.c b/trunk/kernel/module.c index 9db11911e04b..08864d257eb0 100644 --- a/trunk/kernel/module.c +++ b/trunk/kernel/module.c @@ -1799,7 +1799,7 @@ static void *module_alloc_update_bounds(unsigned long size) /* Allocate and load the module: note that size of section 0 is always zero, and we rely on this for optional sections. */ -static noinline struct module *load_module(void __user *umod, +static struct module *load_module(void __user *umod, unsigned long len, const char __user *uargs) { diff --git a/trunk/kernel/nsproxy.c b/trunk/kernel/nsproxy.c index 1d3ef29a2583..21575fc46d05 100644 --- a/trunk/kernel/nsproxy.c +++ b/trunk/kernel/nsproxy.c @@ -14,6 +14,7 @@ */ #include +#include #include #include #include diff --git a/trunk/kernel/power/swap.c b/trunk/kernel/power/swap.c index 80ccac849e46..a0abf9a463f9 100644 --- a/trunk/kernel/power/swap.c +++ b/trunk/kernel/power/swap.c @@ -14,6 +14,7 @@ #include #include #include +#include #include #include #include diff --git a/trunk/kernel/rcupdate.c b/trunk/kernel/rcupdate.c index 467d5940f624..f14f372cf6f5 100644 --- a/trunk/kernel/rcupdate.c +++ b/trunk/kernel/rcupdate.c @@ -77,7 +77,6 @@ void wakeme_after_rcu(struct rcu_head *head) * sections are delimited by rcu_read_lock() and rcu_read_unlock(), * and may be nested. */ -void synchronize_rcu(void); /* Makes kernel-doc tools happy */ synchronize_rcu_xxx(synchronize_rcu, call_rcu) EXPORT_SYMBOL_GPL(synchronize_rcu); diff --git a/trunk/kernel/sched_clock.c b/trunk/kernel/sched_clock.c index e8ab096ddfe3..204991a0bfa7 100644 --- a/trunk/kernel/sched_clock.c +++ b/trunk/kernel/sched_clock.c @@ -12,17 +12,19 @@ * * Create a semi stable clock from a mixture of other events, including: * - gtod + * - jiffies * - sched_clock() * - explicit idle events * * We use gtod as base and the unstable clock deltas. The deltas are filtered, - * making it monotonic and keeping it within an expected window. + * making it monotonic and keeping it within an expected window. This window + * is set up using jiffies. * * Furthermore, explicit sleep and wakeup hooks allow us to account for time * that is otherwise invisible (TSC gets stopped). * * The clock: sched_clock_cpu() is monotonic per cpu, and should be somewhat - * consistent between cpus (never more than 2 jiffies difference). + * consistent between cpus (never more than 1 jiffies difference). */ #include #include @@ -52,6 +54,7 @@ struct sched_clock_data { */ raw_spinlock_t lock; + unsigned long tick_jiffies; u64 tick_raw; u64 tick_gtod; u64 clock; @@ -72,12 +75,14 @@ static inline struct sched_clock_data *cpu_sdc(int cpu) void sched_clock_init(void) { u64 ktime_now = ktime_to_ns(ktime_get()); + unsigned long now_jiffies = jiffies; int cpu; for_each_possible_cpu(cpu) { struct sched_clock_data *scd = cpu_sdc(cpu); scd->lock = (raw_spinlock_t)__RAW_SPIN_LOCK_UNLOCKED; + scd->tick_jiffies = now_jiffies; scd->tick_raw = 0; scd->tick_gtod = ktime_now; scd->clock = ktime_now; @@ -86,52 +91,47 @@ void sched_clock_init(void) sched_clock_running = 1; } -/* - * min,max except they take wrapping into account - */ - -static inline u64 wrap_min(u64 x, u64 y) -{ - return (s64)(x - y) < 0 ? x : y; -} - -static inline u64 wrap_max(u64 x, u64 y) -{ - return (s64)(x - y) > 0 ? x : y; -} - /* * update the percpu scd from the raw @now value * * - filter out backward motion - * - use the GTOD tick value to create a window to filter crazy TSC values + * - use jiffies to generate a min,max window to clip the raw values */ static u64 __update_sched_clock(struct sched_clock_data *scd, u64 now) { + unsigned long now_jiffies = jiffies; + long delta_jiffies = now_jiffies - scd->tick_jiffies; + u64 clock = scd->clock; + u64 min_clock, max_clock; s64 delta = now - scd->tick_raw; - u64 clock, min_clock, max_clock; WARN_ON_ONCE(!irqs_disabled()); + min_clock = scd->tick_gtod + delta_jiffies * TICK_NSEC; - if (unlikely(delta < 0)) - delta = 0; + if (unlikely(delta < 0)) { + clock++; + goto out; + } - /* - * scd->clock = clamp(scd->tick_gtod + delta, - * max(scd->tick_gtod, scd->clock), - * scd->tick_gtod + TICK_NSEC); - */ + max_clock = min_clock + TICK_NSEC; - clock = scd->tick_gtod + delta; - min_clock = wrap_max(scd->tick_gtod, scd->clock); - max_clock = scd->tick_gtod + TICK_NSEC; + if (unlikely(clock + delta > max_clock)) { + if (clock < max_clock) + clock = max_clock; + else + clock++; + } else { + clock += delta; + } - clock = wrap_max(clock, min_clock); - clock = wrap_min(clock, max_clock); + out: + if (unlikely(clock < min_clock)) + clock = min_clock; + scd->tick_jiffies = now_jiffies; scd->clock = clock; - return scd->clock; + return clock; } static void lock_double_clock(struct sched_clock_data *data1, @@ -171,7 +171,7 @@ u64 sched_clock_cpu(int cpu) * larger time as the latest time for both * runqueues. (this creates monotonic movement) */ - if (likely((s64)(remote_clock - this_clock) < 0)) { + if (likely(remote_clock < this_clock)) { clock = this_clock; scd->clock = clock; } else { @@ -207,9 +207,14 @@ void sched_clock_tick(void) now = sched_clock(); __raw_spin_lock(&scd->lock); + __update_sched_clock(scd, now); + /* + * update tick_gtod after __update_sched_clock() because that will + * already observe 1 new jiffy; adding a new tick_gtod to that would + * increase the clock 2 jiffies. + */ scd->tick_raw = now; scd->tick_gtod = now_gtod; - __update_sched_clock(scd, now); __raw_spin_unlock(&scd->lock); } @@ -227,7 +232,18 @@ EXPORT_SYMBOL_GPL(sched_clock_idle_sleep_event); */ void sched_clock_idle_wakeup_event(u64 delta_ns) { - sched_clock_tick(); + struct sched_clock_data *scd = this_scd(); + + /* + * Override the previous timestamp and ignore all + * sched_clock() deltas that occured while we idled, + * and use the PM-provided delta_ns to advance the + * rq clock: + */ + __raw_spin_lock(&scd->lock); + scd->clock += delta_ns; + __raw_spin_unlock(&scd->lock); + touch_softlockup_watchdog(); } EXPORT_SYMBOL_GPL(sched_clock_idle_wakeup_event); diff --git a/trunk/kernel/sched_features.h b/trunk/kernel/sched_features.h index 9353ca78154e..862b06bd560a 100644 --- a/trunk/kernel/sched_features.h +++ b/trunk/kernel/sched_features.h @@ -8,6 +8,6 @@ SCHED_FEAT(SYNC_WAKEUPS, 1) SCHED_FEAT(HRTICK, 1) SCHED_FEAT(DOUBLE_TICK, 0) SCHED_FEAT(ASYM_GRAN, 1) -SCHED_FEAT(LB_BIAS, 1) +SCHED_FEAT(LB_BIAS, 0) SCHED_FEAT(LB_WAKEUP_UPDATE, 1) SCHED_FEAT(ASYM_EFF_LOAD, 1) diff --git a/trunk/kernel/time/tick-sched.c b/trunk/kernel/time/tick-sched.c index 7a46bde78c66..f5da526424a9 100644 --- a/trunk/kernel/time/tick-sched.c +++ b/trunk/kernel/time/tick-sched.c @@ -643,21 +643,17 @@ void tick_setup_sched_timer(void) ts->nohz_mode = NOHZ_MODE_HIGHRES; #endif } -#endif /* HIGH_RES_TIMERS */ -#if defined CONFIG_NO_HZ || defined CONFIG_HIGH_RES_TIMERS void tick_cancel_sched_timer(int cpu) { struct tick_sched *ts = &per_cpu(tick_cpu_sched, cpu); -# ifdef CONFIG_HIGH_RES_TIMERS if (ts->sched_timer.base) hrtimer_cancel(&ts->sched_timer); -# endif ts->nohz_mode = NOHZ_MODE_INACTIVE; } -#endif +#endif /* HIGH_RES_TIMERS */ /** * Async notification about clocksource changes diff --git a/trunk/kernel/user_namespace.c b/trunk/kernel/user_namespace.c index 532858fa5b88..a9ab0596de44 100644 --- a/trunk/kernel/user_namespace.c +++ b/trunk/kernel/user_namespace.c @@ -6,6 +6,7 @@ */ #include +#include #include #include #include diff --git a/trunk/kernel/utsname.c b/trunk/kernel/utsname.c index 815237a55af8..64d398f12444 100644 --- a/trunk/kernel/utsname.c +++ b/trunk/kernel/utsname.c @@ -12,6 +12,7 @@ #include #include #include +#include #include #include diff --git a/trunk/kernel/utsname_sysctl.c b/trunk/kernel/utsname_sysctl.c index 4ab9659d269e..fe3a56c2256d 100644 --- a/trunk/kernel/utsname_sysctl.c +++ b/trunk/kernel/utsname_sysctl.c @@ -12,6 +12,7 @@ #include #include #include +#include #include static void *get_uts(ctl_table *table, int write) diff --git a/trunk/lib/kobject.c b/trunk/lib/kobject.c index fbf0ae282376..bd732ffebc85 100644 --- a/trunk/lib/kobject.c +++ b/trunk/lib/kobject.c @@ -223,7 +223,8 @@ static int kobject_set_name_vargs(struct kobject *kobj, const char *fmt, return -ENOMEM; /* ewww... some of these buggers have '/' in the name ... */ - while ((s = strchr(kobj->name, '/'))) + s = strchr(kobj->name, '/'); + if (s) s[0] = '!'; kfree(old_name); diff --git a/trunk/net/sctp/auth.c b/trunk/net/sctp/auth.c index 675a5c3e68a6..1fcb4cf2f4c9 100644 --- a/trunk/net/sctp/auth.c +++ b/trunk/net/sctp/auth.c @@ -80,6 +80,10 @@ static struct sctp_auth_bytes *sctp_auth_create_key(__u32 key_len, gfp_t gfp) { struct sctp_auth_bytes *key; + /* Verify that we are not going to overflow INT_MAX */ + if ((INT_MAX - key_len) < sizeof(struct sctp_auth_bytes)) + return NULL; + /* Allocate the shared key */ key = kmalloc(sizeof(struct sctp_auth_bytes) + key_len, gfp); if (!key) diff --git a/trunk/net/sctp/socket.c b/trunk/net/sctp/socket.c index bb5c9ef13046..afa952e726d7 100644 --- a/trunk/net/sctp/socket.c +++ b/trunk/net/sctp/socket.c @@ -3144,6 +3144,11 @@ static int sctp_setsockopt_auth_key(struct sock *sk, goto out; } + if (authkey->sca_keylength > optlen) { + ret = -EINVAL; + goto out; + } + asoc = sctp_id2assoc(sk, authkey->sca_assoc_id); if (!asoc && authkey->sca_assoc_id && sctp_style(sk, UDP)) { ret = -EINVAL; diff --git a/trunk/scripts/mod/file2alias.c b/trunk/scripts/mod/file2alias.c index 4c9890ec2528..4fa1f3ad2513 100644 --- a/trunk/scripts/mod/file2alias.c +++ b/trunk/scripts/mod/file2alias.c @@ -344,20 +344,14 @@ static void do_pnp_device_entry(void *symval, unsigned long size, struct module *mod) { const unsigned long id_size = sizeof(struct pnp_device_id); - const unsigned int count = (size / id_size)-1; - const struct pnp_device_id *devs = symval; - unsigned int i; + const struct pnp_device_id *id = symval; device_id_check(mod->name, "pnp", size, id_size, symval); - for (i = 0; i < count; i++) { - const char *id = (char *)devs[i].id; - - buf_printf(&mod->dev_table_buf, - "MODULE_ALIAS(\"pnp:d%s*\");\n", id); - buf_printf(&mod->dev_table_buf, - "MODULE_ALIAS(\"acpi*:%s:*\");\n", id); - } + buf_printf(&mod->dev_table_buf, + "MODULE_ALIAS(\"pnp:d%s*\");\n", id->id); + buf_printf(&mod->dev_table_buf, + "MODULE_ALIAS(\"acpi*:%s:*\");\n", id->id); } /* looks like: "pnp:dD" for every device of the card */ diff --git a/trunk/sound/mips/au1x00.c b/trunk/sound/mips/au1x00.c index fbef38a9604a..ee0741f9eb53 100644 --- a/trunk/sound/mips/au1x00.c +++ b/trunk/sound/mips/au1x00.c @@ -38,6 +38,7 @@ #include #include #include +#include #include #include #include diff --git a/trunk/sound/pci/ca0106/ca0106_main.c b/trunk/sound/pci/ca0106/ca0106_main.c index 6abe8a3bd365..2f8b28add276 100644 --- a/trunk/sound/pci/ca0106/ca0106_main.c +++ b/trunk/sound/pci/ca0106/ca0106_main.c @@ -249,12 +249,11 @@ static struct snd_ca0106_details ca0106_chip_details[] = { .name = "MSI K8N Diamond MB [SB0438]", .gpio_type = 2, .i2c_adc = 1 } , - /* MSI K8N Diamond PLUS MB */ + /* Another MSI K8N Diamond MB, which has apprently a different SSID */ { .serial = 0x10091102, .name = "MSI K8N Diamond MB", .gpio_type = 2, - .i2c_adc = 1, - .spi_dac = 2 }, + .i2c_adc = 1 } , /* Shuttle XPC SD31P which has an onboard Creative Labs * Sound Blaster Live! 24-bit EAX * high-definition 7.1 audio processor". diff --git a/trunk/sound/pci/hda/hda_intel.c b/trunk/sound/pci/hda/hda_intel.c index 1c53e337ecb2..a73d6ca0a906 100644 --- a/trunk/sound/pci/hda/hda_intel.c +++ b/trunk/sound/pci/hda/hda_intel.c @@ -278,9 +278,6 @@ enum { /* Defines for Nvidia HDA support */ #define NVIDIA_HDA_TRANSREG_ADDR 0x4e #define NVIDIA_HDA_ENABLE_COHBITS 0x0f -#define NVIDIA_HDA_ISTRM_COH 0x4d -#define NVIDIA_HDA_OSTRM_COH 0x4c -#define NVIDIA_HDA_ENABLE_COHBIT 0x01 /* Defines for Intel SCH HDA snoop control */ #define INTEL_SCH_HDA_DEVC 0x78 @@ -903,12 +900,6 @@ static void azx_init_pci(struct azx *chip) update_pci_byte(chip->pci, NVIDIA_HDA_TRANSREG_ADDR, 0x0f, NVIDIA_HDA_ENABLE_COHBITS); - update_pci_byte(chip->pci, - NVIDIA_HDA_ISTRM_COH, - 0x01, NVIDIA_HDA_ENABLE_COHBIT); - update_pci_byte(chip->pci, - NVIDIA_HDA_OSTRM_COH, - 0x01, NVIDIA_HDA_ENABLE_COHBIT); break; case AZX_DRIVER_SCH: pci_read_config_word(chip->pci, INTEL_SCH_HDA_DEVC, &snoop); diff --git a/trunk/sound/pci/hda/patch_realtek.c b/trunk/sound/pci/hda/patch_realtek.c index 909f1c101c95..b80e725432f0 100644 --- a/trunk/sound/pci/hda/patch_realtek.c +++ b/trunk/sound/pci/hda/patch_realtek.c @@ -952,7 +952,7 @@ static void alc_subsystem_id(struct hda_codec *codec, tmp | 0x2010); break; case 0x10ec0888: - /*alc888_coef_init(codec);*/ /* called in alc_init() */ + alc888_coef_init(codec); break; case 0x10ec0267: case 0x10ec0268: @@ -2439,8 +2439,6 @@ static int alc_init(struct hda_codec *codec) unsigned int i; alc_fix_pll(codec); - if (codec->vendor_id == 0x10ec0888) - alc888_coef_init(codec); for (i = 0; i < spec->num_init_verbs; i++) snd_hda_sequence_write(codec, spec->init_verbs[i]); @@ -8428,6 +8426,8 @@ static int patch_alc883(struct hda_codec *codec) codec->patch_ops = alc_patch_ops; if (board_config == ALC883_AUTO) spec->init_hook = alc883_auto_init; + else if (codec->vendor_id == 0x10ec0888) + spec->init_hook = alc888_coef_init; #ifdef CONFIG_SND_HDA_POWER_SAVE if (!spec->loopback.amplist) diff --git a/trunk/sound/soc/at91/eti_b1_wm8731.c b/trunk/sound/soc/at91/eti_b1_wm8731.c index b81d6b2cfa1d..b081e83766b7 100644 --- a/trunk/sound/soc/at91/eti_b1_wm8731.c +++ b/trunk/sound/soc/at91/eti_b1_wm8731.c @@ -22,6 +22,7 @@ #include #include +#include #include #include #include diff --git a/trunk/sound/soc/codecs/ak4535.c b/trunk/sound/soc/codecs/ak4535.c index 7da9f467b7b8..b26003c4f3e8 100644 --- a/trunk/sound/soc/codecs/ak4535.c +++ b/trunk/sound/soc/codecs/ak4535.c @@ -562,9 +562,10 @@ static int ak4535_codec_probe(struct i2c_adapter *adap, int addr, int kind) client_template.addr = addr; i2c = kmemdup(&client_template, sizeof(client_template), GFP_KERNEL); - if (i2c == NULL) + if (i2c == NULL) { + kfree(codec); return -ENOMEM; - + } i2c_set_clientdata(i2c, codec); codec->control_data = i2c; @@ -582,6 +583,7 @@ static int ak4535_codec_probe(struct i2c_adapter *adap, int addr, int kind) return ret; err: + kfree(codec); kfree(i2c); return ret; } @@ -658,11 +660,6 @@ static int ak4535_probe(struct platform_device *pdev) #else /* Add other interfaces here */ #endif - - if (ret != 0) { - kfree(codec->private_data); - kfree(codec); - } return ret; } diff --git a/trunk/sound/soc/codecs/tlv320aic3x.c b/trunk/sound/soc/codecs/tlv320aic3x.c index 5f9abb199435..b1dce5f459db 100644 --- a/trunk/sound/soc/codecs/tlv320aic3x.c +++ b/trunk/sound/soc/codecs/tlv320aic3x.c @@ -1199,9 +1199,10 @@ static int aic3x_codec_probe(struct i2c_adapter *adap, int addr, int kind) client_template.addr = addr; i2c = kmemdup(&client_template, sizeof(client_template), GFP_KERNEL); - if (i2c == NULL) + if (i2c == NULL) { + kfree(codec); return -ENOMEM; - + } i2c_set_clientdata(i2c, codec); codec->control_data = i2c; @@ -1220,6 +1221,7 @@ static int aic3x_codec_probe(struct i2c_adapter *adap, int addr, int kind) return ret; err: + kfree(codec); kfree(i2c); return ret; } @@ -1300,11 +1302,6 @@ static int aic3x_probe(struct platform_device *pdev) #else /* Add other interfaces here */ #endif - - if (ret != 0) { - kfree(codec->private_data); - kfree(codec); - } return ret; } diff --git a/trunk/sound/soc/codecs/uda1380.c b/trunk/sound/soc/codecs/uda1380.c index 807318fbdc8f..a52d6d9e007a 100644 --- a/trunk/sound/soc/codecs/uda1380.c +++ b/trunk/sound/soc/codecs/uda1380.c @@ -729,9 +729,10 @@ static int uda1380_codec_probe(struct i2c_adapter *adap, int addr, int kind) client_template.addr = addr; i2c = kmemdup(&client_template, sizeof(client_template), GFP_KERNEL); - if (i2c == NULL) + if (i2c == NULL) { + kfree(codec); return -ENOMEM; - + } i2c_set_clientdata(i2c, codec); codec->control_data = i2c; @@ -749,6 +750,7 @@ static int uda1380_codec_probe(struct i2c_adapter *adap, int addr, int kind) return ret; err: + kfree(codec); kfree(i2c); return ret; } @@ -815,9 +817,6 @@ static int uda1380_probe(struct platform_device *pdev) #else /* Add other interfaces here */ #endif - - if (ret != 0) - kfree(codec); return ret; } diff --git a/trunk/sound/soc/codecs/wm8510.c b/trunk/sound/soc/codecs/wm8510.c index 3d998e6a997e..67325fd95447 100644 --- a/trunk/sound/soc/codecs/wm8510.c +++ b/trunk/sound/soc/codecs/wm8510.c @@ -693,9 +693,10 @@ static int wm8510_codec_probe(struct i2c_adapter *adap, int addr, int kind) client_template.addr = addr; i2c = kmemdup(&client_template, sizeof(client_template), GFP_KERNEL); - if (i2c == NULL) + if (i2c == NULL) { + kfree(codec); return -ENOMEM; - + } i2c_set_clientdata(i2c, codec); codec->control_data = i2c; @@ -713,6 +714,7 @@ static int wm8510_codec_probe(struct i2c_adapter *adap, int addr, int kind) return ret; err: + kfree(codec); kfree(i2c); return ret; } @@ -780,9 +782,6 @@ static int wm8510_probe(struct platform_device *pdev) #else /* Add other interfaces here */ #endif - - if (ret != 0) - kfree(codec); return ret; } diff --git a/trunk/sound/soc/codecs/wm8731.c b/trunk/sound/soc/codecs/wm8731.c index 9402fcaf04fa..369d39c3f745 100644 --- a/trunk/sound/soc/codecs/wm8731.c +++ b/trunk/sound/soc/codecs/wm8731.c @@ -596,9 +596,10 @@ static int wm8731_codec_probe(struct i2c_adapter *adap, int addr, int kind) client_template.addr = addr; i2c = kmemdup(&client_template, sizeof(client_template), GFP_KERNEL); - if (i2c == NULL) + if (i2c == NULL) { + kfree(codec); return -ENOMEM; - + } i2c_set_clientdata(i2c, codec); codec->control_data = i2c; @@ -616,6 +617,7 @@ static int wm8731_codec_probe(struct i2c_adapter *adap, int addr, int kind) return ret; err: + kfree(codec); kfree(i2c); return ret; } @@ -691,11 +693,6 @@ static int wm8731_probe(struct platform_device *pdev) #else /* Add other interfaces here */ #endif - - if (ret != 0) { - kfree(codec->private_data); - kfree(codec); - } return ret; } diff --git a/trunk/sound/soc/codecs/wm8750.c b/trunk/sound/soc/codecs/wm8750.c index dd1f55404b29..c6a8edf302ad 100644 --- a/trunk/sound/soc/codecs/wm8750.c +++ b/trunk/sound/soc/codecs/wm8750.c @@ -869,9 +869,10 @@ static int wm8750_codec_probe(struct i2c_adapter *adap, int addr, int kind) client_template.addr = addr; i2c = kmemdup(&client_template, sizeof(client_template), GFP_KERNEL); - if (i2c == NULL) + if (i2c == NULL) { + kfree(codec); return -ENOMEM; - + } i2c_set_clientdata(i2c, codec); codec->control_data = i2c; @@ -889,6 +890,7 @@ static int wm8750_codec_probe(struct i2c_adapter *adap, int addr, int kind) return ret; err: + kfree(codec); kfree(i2c); return ret; } @@ -964,10 +966,6 @@ static int wm8750_probe(struct platform_device *pdev) /* Add other interfaces here */ #endif - if (ret != 0) { - kfree(codec->private_data); - kfree(codec); - } return ret; } diff --git a/trunk/sound/soc/codecs/wm8753.c b/trunk/sound/soc/codecs/wm8753.c index 5761164fe16d..8604809f0c36 100644 --- a/trunk/sound/soc/codecs/wm8753.c +++ b/trunk/sound/soc/codecs/wm8753.c @@ -34,6 +34,7 @@ #include #include +#include #include #include #include @@ -1660,9 +1661,10 @@ static int wm8753_codec_probe(struct i2c_adapter *adap, int addr, int kind) client_template.addr = addr; i2c = kmemdup(&client_template, sizeof(client_template), GFP_KERNEL); - if (!i2c) + if (!i2c) { + kfree(codec); return -ENOMEM; - + } i2c_set_clientdata(i2c, codec); codec->control_data = i2c; @@ -1681,6 +1683,7 @@ static int wm8753_codec_probe(struct i2c_adapter *adap, int addr, int kind) return ret; err: + kfree(codec); kfree(i2c); return ret; } @@ -1757,11 +1760,6 @@ static int wm8753_probe(struct platform_device *pdev) #else /* Add other interfaces here */ #endif - - if (ret != 0) { - kfree(codec->private_data); - kfree(codec); - } return ret; } diff --git a/trunk/sound/soc/codecs/wm8990.c b/trunk/sound/soc/codecs/wm8990.c index dd995ef448b4..e44153fa38de 100644 --- a/trunk/sound/soc/codecs/wm8990.c +++ b/trunk/sound/soc/codecs/wm8990.c @@ -1500,9 +1500,10 @@ static int wm8990_codec_probe(struct i2c_adapter *adap, int addr, int kind) client_template.addr = addr; i2c = kmemdup(&client_template, sizeof(client_template), GFP_KERNEL); - if (i2c == NULL) + if (i2c == NULL) { + kfree(codec); return -ENOMEM; - + } i2c_set_clientdata(i2c, codec); codec->control_data = i2c; @@ -1520,6 +1521,7 @@ static int wm8990_codec_probe(struct i2c_adapter *adap, int addr, int kind) return ret; err: + kfree(codec); kfree(i2c); return ret; } @@ -1593,11 +1595,6 @@ static int wm8990_probe(struct platform_device *pdev) #else /* Add other interfaces here */ #endif - - if (ret != 0) { - kfree(codec->private_data); - kfree(codec); - } return ret; } diff --git a/trunk/sound/soc/codecs/wm9712.c b/trunk/sound/soc/codecs/wm9712.c index 2f1c91b1d556..1fb7f9a7aecd 100644 --- a/trunk/sound/soc/codecs/wm9712.c +++ b/trunk/sound/soc/codecs/wm9712.c @@ -13,6 +13,7 @@ #include #include +#include #include #include #include