Merge branch 'master'
authorSteven Whitehouse <swhiteho@redhat.com>
Fri, 21 Apr 2006 16:52:36 +0000 (12:52 -0400)
committerSteven Whitehouse <swhiteho@redhat.com>
Fri, 21 Apr 2006 16:52:36 +0000 (12:52 -0400)
1126 files changed:
CREDITS
Documentation/DMA-API.txt
Documentation/DMA-mapping.txt
Documentation/DocBook/libata.tmpl
Documentation/block/switching-sched.txt [new file with mode: 0644]
Documentation/cpu-freq/index.txt
Documentation/feature-removal-schedule.txt
Documentation/filesystems/vfs.txt
Documentation/i2c/busses/i2c-parport
Documentation/isdn/README.gigaset [new file with mode: 0644]
Documentation/kbuild/modules.txt
Documentation/laptop-mode.txt
Documentation/memory-barriers.txt
Documentation/mtrr.txt
Documentation/networking/xfrm_sync.txt [new file with mode: 0644]
Documentation/scsi/scsi_eh.txt
Documentation/scsi/scsi_mid_low_api.txt
Documentation/serial/driver
Documentation/sound/alsa/DocBook/writing-an-alsa-driver.tmpl
Documentation/vm/hugetlbpage.txt
Documentation/x86_64/boot-options.txt
Kbuild
MAINTAINERS
Makefile
README
arch/alpha/Kconfig
arch/alpha/kernel/alpha_ksyms.c
arch/alpha/kernel/setup.c
arch/alpha/kernel/smp.c
arch/arm/Kconfig
arch/arm/boot/compressed/vmlinux.lds.in
arch/arm/common/scoop.c
arch/arm/configs/ep93xx_defconfig
arch/arm/configs/ixp2000_defconfig
arch/arm/configs/ixp23xx_defconfig
arch/arm/kernel/armksyms.c
arch/arm/kernel/setup.c
arch/arm/mach-at91rm9200/devices.c
arch/arm/mach-ixp4xx/common.c
arch/arm/mach-omap1/devices.c
arch/arm/mach-omap2/devices.c
arch/arm/mach-pxa/corgi_ssp.c
arch/arm/mach-s3c2410/clock.c
arch/arm/mach-s3c2410/common-smdk.c
arch/arm/mach-s3c2410/s3c2440-clock.c
arch/arm/mm/cache-v4wb.S
arch/arm/mm/init.c
arch/arm/mm/proc-sa110.S
arch/arm/mm/proc-sa1100.S
arch/arm/plat-omap/clock.c
arch/arm/plat-omap/devices.c
arch/arm/vfp/vfpdouble.c
arch/arm/vfp/vfphw.S
arch/arm/vfp/vfpsingle.c
arch/arm26/kernel/armksyms.c
arch/cris/kernel/crisksyms.c
arch/frv/kernel/entry.S
arch/frv/kernel/frv_ksyms.c
arch/h8300/kernel/h8300_ksyms.c
arch/i386/Kconfig
arch/i386/Kconfig.cpu
arch/i386/Kconfig.debug
arch/i386/boot/video.S
arch/i386/kernel/Makefile
arch/i386/kernel/acpi/boot.c
arch/i386/kernel/apic.c
arch/i386/kernel/apm.c
arch/i386/kernel/cpu/amd.c
arch/i386/kernel/cpu/cpufreq/powernow-k8.c
arch/i386/kernel/cpuid.c
arch/i386/kernel/dmi_scan.c [deleted file]
arch/i386/kernel/i386_ksyms.c
arch/i386/kernel/kprobes.c
arch/i386/kernel/mpparse.c
arch/i386/kernel/msr.c
arch/i386/kernel/reboot_fixups.c
arch/i386/kernel/setup.c
arch/i386/kernel/syscall_table.S
arch/i386/kernel/traps.c
arch/i386/mach-voyager/voyager_cat.c
arch/i386/mm/init.c
arch/i386/pci/direct.c
arch/i386/pci/irq.c
arch/i386/pci/mmconfig.c
arch/ia64/Kconfig
arch/ia64/kernel/Makefile
arch/ia64/kernel/acpi-ext.c
arch/ia64/kernel/entry.S
arch/ia64/kernel/kprobes.c
arch/ia64/kernel/mca.c
arch/ia64/kernel/mca_asm.S
arch/ia64/kernel/module.c
arch/ia64/mm/discontig.c
arch/ia64/mm/fault.c
arch/ia64/sn/kernel/xpc_channel.c
arch/m32r/Kconfig
arch/m32r/kernel/entry.S
arch/m32r/kernel/m32r_ksyms.c
arch/m32r/kernel/process.c
arch/m32r/kernel/setup.c
arch/m32r/kernel/signal.c
arch/m32r/kernel/smpboot.c
arch/m32r/lib/Makefile
arch/m32r/lib/getuser.S [deleted file]
arch/m32r/lib/putuser.S [deleted file]
arch/m68k/kernel/m68k_ksyms.c
arch/m68knommu/kernel/m68k_ksyms.c
arch/mips/Kconfig
arch/mips/Makefile
arch/mips/au1000/common/Makefile
arch/mips/au1000/common/int-handler.S [deleted file]
arch/mips/au1000/common/irq.c
arch/mips/cobalt/Makefile
arch/mips/cobalt/int-handler.S [deleted file]
arch/mips/cobalt/irq.c
arch/mips/configs/tb0287_defconfig [new file with mode: 0644]
arch/mips/ddb5xxx/ddb5074/Makefile
arch/mips/ddb5xxx/ddb5074/int-handler.S [deleted file]
arch/mips/ddb5xxx/ddb5074/irq.c
arch/mips/ddb5xxx/ddb5476/Makefile
arch/mips/ddb5xxx/ddb5476/int-handler.S [deleted file]
arch/mips/ddb5xxx/ddb5476/irq.c
arch/mips/ddb5xxx/ddb5476/vrc5476_irq.c
arch/mips/ddb5xxx/ddb5477/Makefile
arch/mips/ddb5xxx/ddb5477/int-handler.S [deleted file]
arch/mips/ddb5xxx/ddb5477/irq.c
arch/mips/dec/boot/decstation.c
arch/mips/dec/int-handler.S
arch/mips/dec/setup.c
arch/mips/galileo-boards/ev96100/Makefile
arch/mips/galileo-boards/ev96100/int-handler.S [deleted file]
arch/mips/galileo-boards/ev96100/irq.c
arch/mips/gt64120/ev64120/Makefile
arch/mips/gt64120/ev64120/int-handler.S [deleted file]
arch/mips/gt64120/ev64120/irq.c
arch/mips/gt64120/momenco_ocelot/Makefile
arch/mips/gt64120/momenco_ocelot/int-handler.S [deleted file]
arch/mips/gt64120/momenco_ocelot/irq.c
arch/mips/ite-boards/generic/Makefile
arch/mips/ite-boards/generic/int-handler.S [deleted file]
arch/mips/ite-boards/generic/irq.c
arch/mips/ite-boards/generic/time.c
arch/mips/ite-boards/ivr/init.c
arch/mips/ite-boards/qed-4n-s01b/init.c
arch/mips/jazz/Makefile
arch/mips/jazz/int-handler.S [deleted file]
arch/mips/jazz/irq.c
arch/mips/jmr3927/common/rtc_ds1742.c
arch/mips/jmr3927/rbhma3100/Makefile
arch/mips/jmr3927/rbhma3100/int-handler.S [deleted file]
arch/mips/jmr3927/rbhma3100/irq.c
arch/mips/kernel/Makefile
arch/mips/kernel/asm-offsets.c
arch/mips/kernel/entry.S
arch/mips/kernel/gdb-low.S
arch/mips/kernel/gdb-stub.c
arch/mips/kernel/genex.S
arch/mips/kernel/head.S
arch/mips/kernel/i8259.c
arch/mips/kernel/irq-msc01.c
arch/mips/kernel/irq.c
arch/mips/kernel/kspd.c [new file with mode: 0644]
arch/mips/kernel/linux32.c
arch/mips/kernel/mips-mt.c [new file with mode: 0644]
arch/mips/kernel/mips_ksyms.c
arch/mips/kernel/process.c
arch/mips/kernel/ptrace.c
arch/mips/kernel/ptrace32.c
arch/mips/kernel/r4k_switch.S
arch/mips/kernel/rtlx.c
arch/mips/kernel/scall32-o32.S
arch/mips/kernel/scall64-64.S
arch/mips/kernel/scall64-n32.S
arch/mips/kernel/scall64-o32.S
arch/mips/kernel/setup.c
arch/mips/kernel/smp-mt.c [new file with mode: 0644]
arch/mips/kernel/smp.c
arch/mips/kernel/smp_mt.c [deleted file]
arch/mips/kernel/smtc-asm.S [new file with mode: 0644]
arch/mips/kernel/smtc-proc.c [new file with mode: 0644]
arch/mips/kernel/smtc.c [new file with mode: 0644]
arch/mips/kernel/time.c
arch/mips/kernel/traps.c
arch/mips/kernel/vmlinux.lds.S
arch/mips/kernel/vpe.c
arch/mips/lasat/Makefile
arch/mips/lasat/interrupt.c
arch/mips/lasat/lasatIRQ.S [deleted file]
arch/mips/mips-boards/atlas/atlas_int.c
arch/mips/mips-boards/generic/Makefile
arch/mips/mips-boards/generic/gdb_hook.c
arch/mips/mips-boards/generic/init.c
arch/mips/mips-boards/generic/memory.c
arch/mips/mips-boards/generic/mipsIRQ.S [deleted file]
arch/mips/mips-boards/generic/time.c
arch/mips/mips-boards/malta/Makefile
arch/mips/mips-boards/malta/malta_int.c
arch/mips/mips-boards/malta/malta_smp.c [new file with mode: 0644]
arch/mips/mips-boards/sead/sead_int.c
arch/mips/mips-boards/sim/cmdline.c [deleted file]
arch/mips/mips-boards/sim/sim_cmdline.c
arch/mips/mips-boards/sim/sim_int.c
arch/mips/mips-boards/sim/sim_irq.S
arch/mips/mips-boards/sim/sim_mem.c
arch/mips/mips-boards/sim/sim_smp.c
arch/mips/mm/c-r3k.c
arch/mips/mm/c-r4k.c
arch/mips/mm/c-sb1.c
arch/mips/mm/c-tx39.c
arch/mips/mm/cache.c
arch/mips/mm/fault.c
arch/mips/mm/highmem.c
arch/mips/mm/init.c
arch/mips/mm/sc-rm7k.c
arch/mips/mm/tlb-r4k.c
arch/mips/mm/tlbex.c
arch/mips/momentum/jaguar_atx/Makefile
arch/mips/momentum/jaguar_atx/int-handler.S [deleted file]
arch/mips/momentum/jaguar_atx/irq.c
arch/mips/momentum/jaguar_atx/setup.c
arch/mips/momentum/ocelot_3/Makefile
arch/mips/momentum/ocelot_3/int-handler.S [deleted file]
arch/mips/momentum/ocelot_3/irq.c
arch/mips/momentum/ocelot_3/setup.c
arch/mips/momentum/ocelot_c/Makefile
arch/mips/momentum/ocelot_c/int-handler.S [deleted file]
arch/mips/momentum/ocelot_c/irq.c
arch/mips/momentum/ocelot_g/Makefile
arch/mips/momentum/ocelot_g/int-handler.S [deleted file]
arch/mips/momentum/ocelot_g/irq.c
arch/mips/philips/pnx8550/common/Makefile
arch/mips/philips/pnx8550/common/int.c
arch/mips/philips/pnx8550/common/mipsIRQ.S [deleted file]
arch/mips/philips/pnx8550/common/platform.c
arch/mips/pmc-sierra/yosemite/Makefile
arch/mips/pmc-sierra/yosemite/irq-handler.S [deleted file]
arch/mips/pmc-sierra/yosemite/irq.c
arch/mips/qemu/Makefile
arch/mips/qemu/q-int.S [deleted file]
arch/mips/qemu/q-irq.c
arch/mips/sgi-ip22/Makefile
arch/mips/sgi-ip22/ip22-int.c
arch/mips/sgi-ip22/ip22-irq.S [deleted file]
arch/mips/sgi-ip27/Makefile
arch/mips/sgi-ip27/TODO
arch/mips/sgi-ip27/ip27-irq-glue.S [deleted file]
arch/mips/sgi-ip27/ip27-irq.c
arch/mips/sgi-ip32/Makefile
arch/mips/sgi-ip32/ip32-irq-glue.S [deleted file]
arch/mips/sgi-ip32/ip32-irq.c
arch/mips/sibyte/bcm1480/Makefile
arch/mips/sibyte/bcm1480/irq.c
arch/mips/sibyte/bcm1480/irq_handler.S [deleted file]
arch/mips/sibyte/sb1250/Makefile
arch/mips/sibyte/sb1250/irq.c
arch/mips/sibyte/sb1250/irq_handler.S [deleted file]
arch/mips/sni/Makefile
arch/mips/sni/int-handler.S [deleted file]
arch/mips/sni/irq.c
arch/mips/tx4927/common/Makefile
arch/mips/tx4927/common/tx4927_irq.c
arch/mips/tx4927/common/tx4927_irq_handler.S [deleted file]
arch/mips/tx4938/common/Makefile
arch/mips/tx4938/common/irq.c
arch/mips/tx4938/common/irq_handler.S [deleted file]
arch/mips/vr41xx/Kconfig
arch/mips/vr41xx/common/Makefile
arch/mips/vr41xx/common/int-handler.S [deleted file]
arch/mips/vr41xx/common/irq.c
arch/parisc/Kconfig
arch/parisc/kernel/parisc_ksyms.c
arch/powerpc/Kconfig
arch/powerpc/Makefile
arch/powerpc/kernel/Makefile
arch/powerpc/kernel/asm-offsets.c
arch/powerpc/kernel/entry_32.S
arch/powerpc/kernel/head_64.S
arch/powerpc/kernel/idle.c
arch/powerpc/kernel/idle_6xx.S
arch/powerpc/kernel/idle_power4.S
arch/powerpc/kernel/irq.c
arch/powerpc/kernel/kprobes.c
arch/powerpc/kernel/prom_init.c
arch/powerpc/kernel/rtas-proc.c
arch/powerpc/kernel/systbl.S
arch/powerpc/platforms/cell/spufs/switch.c
arch/powerpc/platforms/chrp/chrp.h
arch/powerpc/platforms/chrp/pci.c
arch/powerpc/platforms/chrp/setup.c
arch/powerpc/platforms/iseries/setup.c
arch/powerpc/platforms/pseries/eeh.c
arch/powerpc/platforms/pseries/rtasd.c
arch/ppc/boot/lib/Makefile
arch/ppc/syslib/ppc_sys.c
arch/s390/Makefile
arch/s390/defconfig
arch/sh/Kconfig
arch/sh/kernel/sh_ksyms.c
arch/sh64/kernel/sh_ksyms.c
arch/sparc/kernel/smp.c
arch/sparc/kernel/sparc_ksyms.c
arch/sparc/kernel/systbls.S
arch/sparc/math-emu/Makefile
arch/sparc64/Kconfig
arch/sparc64/defconfig
arch/sparc64/kernel/kprobes.c
arch/sparc64/kernel/pci.c
arch/sparc64/kernel/pci_sun4v.c
arch/sparc64/kernel/ptrace.c
arch/sparc64/kernel/setup.c
arch/sparc64/kernel/smp.c
arch/sparc64/kernel/sparc64_ksyms.c
arch/sparc64/kernel/sys32.S
arch/sparc64/kernel/systbls.S
arch/sparc64/kernel/traps.c
arch/um/Makefile
arch/um/drivers/cow.h
arch/um/drivers/cow_sys.h
arch/um/drivers/cow_user.c
arch/um/drivers/mconsole_kern.c
arch/um/drivers/net_user.c
arch/um/drivers/slirp_user.c
arch/um/include/kern_util.h
arch/um/include/longjmp.h
arch/um/include/sysdep-i386/kernel-offsets.h
arch/um/include/sysdep-x86_64/kernel-offsets.h
arch/um/include/tt/tt.h
arch/um/include/user.h
arch/um/include/user_util.h
arch/um/kernel/ksyms.c
arch/um/os-Linux/drivers/ethertap_user.c
arch/um/os-Linux/helper.c
arch/um/os-Linux/mem.c
arch/um/os-Linux/process.c
arch/um/os-Linux/sigio.c
arch/um/os-Linux/skas/mem.c
arch/um/os-Linux/skas/process.c
arch/um/os-Linux/start_up.c
arch/um/os-Linux/sys-i386/tls.c
arch/um/os-Linux/trap.c
arch/um/os-Linux/uaccess.c
arch/um/os-Linux/umid.c
arch/um/os-Linux/user_syms.c
arch/um/os-Linux/util.c
arch/um/scripts/Makefile.rules
arch/um/sys-i386/ksyms.c
arch/um/sys-i386/ptrace_user.c
arch/um/sys-i386/signal.c
arch/um/sys-i386/stub_segv.c
arch/um/sys-i386/tls.c
arch/um/sys-x86_64/signal.c
arch/um/sys-x86_64/stub_segv.c
arch/v850/kernel/v850_ksyms.c
arch/x86_64/Kconfig
arch/x86_64/Makefile
arch/x86_64/boot/video.S
arch/x86_64/defconfig
arch/x86_64/ia32/ia32entry.S
arch/x86_64/kernel/Makefile
arch/x86_64/kernel/aperture.c
arch/x86_64/kernel/e820.c
arch/x86_64/kernel/entry.S
arch/x86_64/kernel/kprobes.c
arch/x86_64/kernel/mce.c
arch/x86_64/kernel/nmi.c
arch/x86_64/kernel/pci-dma.c
arch/x86_64/kernel/process.c
arch/x86_64/kernel/ptrace.c
arch/x86_64/kernel/setup.c
arch/x86_64/kernel/time.c
arch/x86_64/kernel/traps.c
arch/x86_64/kernel/vmlinux.lds.S
arch/x86_64/kernel/x8664_ksyms.c
arch/x86_64/mm/init.c
arch/x86_64/mm/numa.c
arch/x86_64/mm/srat.c
arch/x86_64/pci/mmconfig.c
arch/xtensa/kernel/xtensa_ksyms.c
block/as-iosched.c
block/cfq-iosched.c
block/elevator.c
block/ll_rw_blk.c
block/scsi_ioctl.c
drivers/acpi/Kconfig
drivers/base/bus.c
drivers/base/class.c
drivers/base/dd.c
drivers/base/node.c
drivers/base/power/suspend.c
drivers/block/cciss.c
drivers/cdrom/aztcd.c
drivers/char/Kconfig
drivers/char/Makefile
drivers/char/agp/efficeon-agp.c
drivers/char/applicom.c
drivers/char/cs5535_gpio.c
drivers/char/drm/drmP.h
drivers/char/drm/drm_drv.c
drivers/char/drm/drm_memory.c
drivers/char/drm/drm_memory.h
drivers/char/drm/drm_memory_debug.h
drivers/char/drm/drm_pci.c
drivers/char/drm/via_irq.c
drivers/char/dtlk.c
drivers/char/ipmi/ipmi_bt_sm.c
drivers/char/ipmi/ipmi_msghandler.c
drivers/char/ipmi/ipmi_si_intf.c
drivers/char/random.c
drivers/char/sonypi.c
drivers/char/tlclk.c
drivers/char/tty_io.c
drivers/char/vr41xx_rtc.c [deleted file]
drivers/cpufreq/Kconfig
drivers/cpufreq/cpufreq.c
drivers/cpufreq/cpufreq_conservative.c
drivers/firmware/Makefile
drivers/firmware/dmi_scan.c [new file with mode: 0644]
drivers/hwmon/hdaps.c
drivers/hwmon/w83792d.c
drivers/i2c/busses/Kconfig
drivers/i2c/busses/i2c-i801.c
drivers/i2c/busses/i2c-parport-light.c
drivers/i2c/busses/i2c-parport.c
drivers/i2c/busses/i2c-parport.h
drivers/i2c/busses/i2c-sis96x.c
drivers/i2c/chips/ds1374.c
drivers/i2c/chips/m41t00.c
drivers/ide/pci/alim15x3.c
drivers/ide/pci/atiixp.c
drivers/ide/pci/pdc202xx_old.c
drivers/ide/setup-pci.c
drivers/infiniband/core/cache.c
drivers/infiniband/core/mad.c
drivers/infiniband/core/verbs.c
drivers/infiniband/hw/ipath/ipath_diag.c
drivers/infiniband/hw/ipath/ipath_driver.c
drivers/infiniband/hw/ipath/ipath_intr.c
drivers/infiniband/hw/ipath/ipath_kernel.h
drivers/infiniband/hw/ipath/ipath_layer.c
drivers/infiniband/hw/ipath/ipath_pe800.c
drivers/infiniband/hw/ipath/ipath_qp.c
drivers/infiniband/hw/ipath/ipath_ud.c
drivers/infiniband/hw/ipath/ipath_verbs.c
drivers/infiniband/hw/ipath/ipath_verbs.h
drivers/infiniband/hw/mthca/Kconfig
drivers/infiniband/hw/mthca/Makefile
drivers/infiniband/hw/mthca/mthca_av.c
drivers/infiniband/hw/mthca/mthca_cmd.c
drivers/infiniband/hw/mthca/mthca_cmd.h
drivers/infiniband/hw/mthca/mthca_dev.h
drivers/infiniband/hw/mthca/mthca_mad.c
drivers/infiniband/hw/mthca/mthca_main.c
drivers/infiniband/hw/mthca/mthca_provider.c
drivers/infiniband/hw/mthca/mthca_provider.h
drivers/infiniband/hw/mthca/mthca_qp.c
drivers/infiniband/hw/mthca/mthca_srq.c
drivers/infiniband/ulp/ipoib/Kconfig
drivers/infiniband/ulp/ipoib/ipoib.h
drivers/infiniband/ulp/ipoib/ipoib_fs.c
drivers/infiniband/ulp/ipoib/ipoib_ib.c
drivers/infiniband/ulp/ipoib/ipoib_main.c
drivers/infiniband/ulp/ipoib/ipoib_multicast.c
drivers/infiniband/ulp/ipoib/ipoib_verbs.c
drivers/infiniband/ulp/srp/ib_srp.c
drivers/isdn/gigaset/Kconfig
drivers/isdn/gigaset/asyncdata.c
drivers/isdn/gigaset/bas-gigaset.c
drivers/isdn/gigaset/common.c
drivers/isdn/gigaset/ev-layer.c
drivers/isdn/gigaset/gigaset.h
drivers/isdn/gigaset/i4l.c
drivers/isdn/gigaset/interface.c
drivers/isdn/gigaset/isocdata.c
drivers/isdn/gigaset/proc.c
drivers/isdn/gigaset/usb-gigaset.c
drivers/isdn/i4l/isdn_ppp.c
drivers/leds/Kconfig
drivers/leds/Makefile
drivers/leds/leds-s3c24xx.c [new file with mode: 0644]
drivers/md/Kconfig
drivers/md/md.c
drivers/media/video/Makefile
drivers/media/video/bt8xx/Makefile
drivers/media/video/cx25840/Makefile
drivers/media/video/cx88/Makefile
drivers/media/video/em28xx/Makefile
drivers/media/video/saa7134/Makefile
drivers/media/video/saa7134/saa7134-core.c
drivers/message/fusion/mptsas.c
drivers/mtd/devices/Kconfig
drivers/mtd/devices/Makefile
drivers/mtd/devices/blkmtd.c [deleted file]
drivers/net/b44.c
drivers/net/bnx2.c
drivers/net/chelsio/Makefile
drivers/net/hydra.h [deleted file]
drivers/net/irda/irda-usb.c
drivers/net/irda/irda-usb.h
drivers/net/irda/smsc-ircc2.c
drivers/net/ixgb/ixgb_main.c
drivers/net/mv643xx_eth.c
drivers/net/natsemi.c
drivers/net/ne.c
drivers/net/netconsole.c
drivers/net/pcmcia/axnet_cs.c
drivers/net/skge.c
drivers/net/sky2.c
drivers/net/sky2.h
drivers/net/starfire.c
drivers/net/sungem_phy.c
drivers/net/tg3.c
drivers/net/tg3.h
drivers/net/typhoon.c
drivers/net/via-rhine.c
drivers/net/wan/Kconfig
drivers/net/wan/Makefile
drivers/net/wan/sdla_chdlc.c [deleted file]
drivers/net/wan/sdla_fr.c [deleted file]
drivers/net/wan/sdla_ft1.c [deleted file]
drivers/net/wan/sdla_ppp.c [deleted file]
drivers/net/wan/sdla_x25.c [deleted file]
drivers/net/wan/sdladrv.c [deleted file]
drivers/net/wan/sdlamain.c [deleted file]
drivers/net/wan/wanpipe_multppp.c [deleted file]
drivers/net/wireless/Kconfig
drivers/net/wireless/airo.c
drivers/net/wireless/atmel.c
drivers/net/wireless/bcm43xx/Kconfig
drivers/net/wireless/bcm43xx/bcm43xx.h
drivers/net/wireless/bcm43xx/bcm43xx_debugfs.c
drivers/net/wireless/bcm43xx/bcm43xx_dma.c
drivers/net/wireless/bcm43xx/bcm43xx_main.c
drivers/net/wireless/bcm43xx/bcm43xx_phy.c
drivers/net/wireless/bcm43xx/bcm43xx_power.c
drivers/net/wireless/bcm43xx/bcm43xx_power.h
drivers/net/wireless/bcm43xx/bcm43xx_sysfs.c
drivers/net/wireless/bcm43xx/bcm43xx_sysfs.h
drivers/net/wireless/bcm43xx/bcm43xx_wx.c
drivers/net/wireless/orinoco.c
drivers/parport/parport_pc.c
drivers/parport/parport_serial.c
drivers/pci/hotplug/rpaphp_core.c
drivers/pci/msi.c
drivers/pci/pci-driver.c
drivers/pci/pci.c
drivers/pci/pci.h
drivers/pci/quirks.c
drivers/pcmcia/at91_cf.c
drivers/pcmcia/pxa2xx_sharpsl.c
drivers/pnp/manager.c
drivers/rtc/Kconfig
drivers/rtc/Makefile
drivers/rtc/class.c
drivers/rtc/rtc-ds1672.c
drivers/rtc/rtc-ep93xx.c
drivers/rtc/rtc-m48t86.c
drivers/rtc/rtc-pcf8563.c
drivers/rtc/rtc-proc.c
drivers/rtc/rtc-rs5c372.c
drivers/rtc/rtc-sa1100.c
drivers/rtc/rtc-test.c
drivers/rtc/rtc-vr41xx.c [new file with mode: 0644]
drivers/rtc/rtc-x1205.c
drivers/s390/block/dasd.c
drivers/s390/block/dasd_proc.c
drivers/s390/char/keyboard.c
drivers/s390/char/tape_block.c
drivers/s390/char/tape_core.c
drivers/s390/cio/blacklist.c
drivers/s390/cio/cio.c
drivers/s390/cio/cio_debug.h
drivers/scsi/3w-9xxx.c
drivers/scsi/3w-xxxx.c
drivers/scsi/Kconfig
drivers/scsi/Makefile
drivers/scsi/aacraid/aachba.c
drivers/scsi/aacraid/aacraid.h
drivers/scsi/aacraid/commctrl.c
drivers/scsi/aacraid/commsup.c
drivers/scsi/aacraid/linit.c
drivers/scsi/aacraid/rkt.c
drivers/scsi/aacraid/rx.c
drivers/scsi/aacraid/sa.c
drivers/scsi/ahci.c
drivers/scsi/aic7xxx/aic79xx.h
drivers/scsi/aic7xxx/aic79xx_core.c
drivers/scsi/aic7xxx/aic79xx_osm.c
drivers/scsi/ata_piix.c
drivers/scsi/hosts.c
drivers/scsi/ibmvscsi/ibmvscsi.c
drivers/scsi/ibmvscsi/ibmvscsi.h
drivers/scsi/ibmvscsi/rpa_vscsi.c
drivers/scsi/ibmvscsi/srp.h [deleted file]
drivers/scsi/ibmvscsi/viosrp.h
drivers/scsi/ipr.c
drivers/scsi/ipr.h
drivers/scsi/libata-core.c
drivers/scsi/libata-scsi.c
drivers/scsi/libata.h
drivers/scsi/pdc_adma.c
drivers/scsi/qlogicfc.c [deleted file]
drivers/scsi/qlogicfc_asm.c [deleted file]
drivers/scsi/sata_mv.c
drivers/scsi/sata_nv.c
drivers/scsi/sata_promise.c
drivers/scsi/sata_qstor.c
drivers/scsi/sata_sil.c
drivers/scsi/sata_sil24.c
drivers/scsi/sata_sis.c
drivers/scsi/sata_svw.c
drivers/scsi/sata_sx4.c
drivers/scsi/sata_uli.c
drivers/scsi/sata_via.c
drivers/scsi/sata_vsc.c
drivers/scsi/scsi.c
drivers/scsi/scsi_devinfo.c
drivers/scsi/scsi_error.c
drivers/scsi/scsi_ioctl.c
drivers/scsi/scsi_lib.c
drivers/scsi/scsi_sas_internal.h [new file with mode: 0644]
drivers/scsi/scsi_scan.c
drivers/scsi/scsi_transport_fc.c
drivers/scsi/scsi_transport_sas.c
drivers/scsi/sg.c
drivers/scsi/sym53c8xx_2/sym_defs.h
drivers/scsi/sym53c8xx_2/sym_glue.c
drivers/scsi/sym53c8xx_2/sym_glue.h
drivers/scsi/sym53c8xx_2/sym_hipd.c
drivers/scsi/sym53c8xx_2/sym_hipd.h
drivers/serial/m32r_sio.c
drivers/sn/ioc3.c
drivers/usb/atm/ueagle-atm.c
drivers/usb/core/Kconfig
drivers/usb/core/hcd-pci.c
drivers/usb/core/hub.c
drivers/usb/core/usb.c
drivers/usb/gadget/Kconfig
drivers/usb/gadget/at91_udc.c
drivers/usb/gadget/ether.c
drivers/usb/gadget/file_storage.c
drivers/usb/gadget/gadget_chips.h
drivers/usb/gadget/inode.c
drivers/usb/gadget/net2280.c
drivers/usb/gadget/net2280.h
drivers/usb/gadget/zero.c
drivers/usb/host/ohci-at91.c
drivers/usb/host/ohci-s3c2410.c
drivers/usb/host/pci-quirks.c
drivers/usb/host/pci-quirks.h [new file with mode: 0644]
drivers/usb/host/uhci-hcd.c
drivers/usb/host/uhci-hcd.h
drivers/usb/host/uhci-hub.c
drivers/usb/input/Kconfig
drivers/usb/input/Makefile
drivers/usb/input/hid-core.c
drivers/usb/input/hid-ff.c
drivers/usb/input/hid.h
drivers/usb/input/keyspan_remote.c
drivers/usb/input/usbtouchscreen.c [new file with mode: 0644]
drivers/usb/input/wacom.c
drivers/usb/misc/usbtest.c
drivers/usb/net/asix.c
drivers/usb/net/pegasus.c
drivers/usb/net/rndis_host.c
drivers/usb/serial/Kconfig
drivers/usb/serial/Makefile
drivers/usb/serial/console.c
drivers/usb/serial/ftdi_sio.c
drivers/usb/serial/ftdi_sio.h
drivers/usb/serial/funsoft.c [new file with mode: 0644]
drivers/usb/serial/option.c
drivers/usb/serial/pl2303.c
drivers/usb/serial/pl2303.h
drivers/usb/serial/usb-serial.c
drivers/usb/serial/usb-serial.h
drivers/usb/storage/Kconfig
drivers/video/Kconfig
drivers/video/aty/atyfb_base.c
drivers/video/aty/radeon_base.c
drivers/video/fbmem.c
drivers/video/pm2fb.c
drivers/video/savage/savagefb_driver.c
drivers/video/vesafb.c
fs/9p/vfs_super.c
fs/Kconfig
fs/configfs/dir.c
fs/eventpoll.c
fs/exec.c
fs/ext3/resize.c
fs/fifo.c
fs/fuse/dev.c
fs/fuse/dir.c
fs/fuse/file.c
fs/fuse/fuse_i.h
fs/fuse/inode.c
fs/inotify.c
fs/lockd/svclock.c
fs/locks.c
fs/namespace.c
fs/nfs/dir.c
fs/nfs/direct.c
fs/nfs/file.c
fs/nfs/inode.c
fs/nfs/nfs4proc.c
fs/nfsd/auth.c
fs/nfsd/export.c
fs/nfsd/nfs3proc.c
fs/nfsd/nfs4acl.c
fs/nfsd/nfs4callback.c
fs/nfsd/nfs4proc.c
fs/nfsd/nfs4state.c
fs/nfsd/nfs4xdr.c
fs/nfsd/nfsproc.c
fs/nfsd/vfs.c
fs/ocfs2/cluster/heartbeat.c
fs/ocfs2/dlm/userdlm.c
fs/ocfs2/file.c
fs/open.c
fs/partitions/check.c
fs/pipe.c
fs/proc/base.c
fs/proc/vmcore.c
fs/read_write.c
fs/select.c
fs/splice.c
fs/sync.c
fs/sysfs/dir.c
fs/sysfs/file.c
fs/sysfs/sysfs.h
fs/xfs/linux-2.6/xfs_aops.c
fs/xfs/linux-2.6/xfs_buf.c
fs/xfs/linux-2.6/xfs_file.c
fs/xfs/linux-2.6/xfs_iops.c
fs/xfs/linux-2.6/xfs_lrw.c
fs/xfs/linux-2.6/xfs_lrw.h
fs/xfs/linux-2.6/xfs_vnode.h
fs/xfs/xfs_ialloc.c
fs/xfs/xfs_iget.c
fs/xfs/xfs_inode.c
fs/xfs/xfs_inode.h
fs/xfs/xfs_mount.c
include/asm-alpha/numnodes.h [deleted file]
include/asm-arm/arch-cl7500/hardware.h
include/asm-arm/arch-cl7500/memory.h
include/asm-arm/arch-ebsa110/debug-macro.S
include/asm-arm/arch-ebsa110/hardware.h
include/asm-arm/arch-ebsa110/memory.h
include/asm-arm/arch-ebsa110/uncompress.h
include/asm-arm/arch-ebsa285/hardware.h
include/asm-arm/arch-ebsa285/memory.h
include/asm-arm/arch-ixp23xx/debug-macro.S
include/asm-arm/arch-l7200/hardware.h
include/asm-arm/arch-l7200/memory.h
include/asm-arm/arch-lh7a40x/memory.h
include/asm-arm/arch-rpc/hardware.h
include/asm-arm/arch-rpc/memory.h
include/asm-arm/arch-s3c2410/leds-gpio.h [new file with mode: 0644]
include/asm-arm/arch-sa1100/hardware.h
include/asm-arm/arch-sa1100/memory.h
include/asm-arm/arch-shark/hardware.h
include/asm-arm/arch-shark/memory.h
include/asm-arm/fpstate.h
include/asm-arm/memory.h
include/asm-arm/numnodes.h [deleted file]
include/asm-arm/unistd.h
include/asm-arm/vfpmacros.h
include/asm-cris/system.h
include/asm-cris/unistd.h
include/asm-frv/system.h
include/asm-frv/unistd.h
include/asm-h8300/system.h
include/asm-h8300/unistd.h
include/asm-i386/apic.h
include/asm-i386/atomic.h
include/asm-i386/cpufeature.h
include/asm-i386/e820.h
include/asm-i386/hpet.h
include/asm-i386/i387.h
include/asm-i386/mpspec.h
include/asm-i386/numnodes.h [deleted file]
include/asm-i386/unistd.h
include/asm-ia64/acpi-ext.h
include/asm-ia64/kdebug.h
include/asm-ia64/mca.h
include/asm-ia64/mutex.h
include/asm-ia64/numnodes.h [deleted file]
include/asm-ia64/unistd.h
include/asm-ia64/vga.h
include/asm-m32r/assembler.h
include/asm-m32r/mappi3/mappi3_pld.h
include/asm-m32r/numnodes.h [deleted file]
include/asm-m32r/ptrace.h
include/asm-m32r/semaphore.h
include/asm-m32r/sigcontext.h
include/asm-m32r/smp.h
include/asm-m32r/system.h
include/asm-m32r/uaccess.h
include/asm-m32r/unistd.h
include/asm-mips/asmmacro.h
include/asm-mips/cacheflush.h
include/asm-mips/cpu-features.h
include/asm-mips/cpu-info.h
include/asm-mips/ds1742.h [new file with mode: 0644]
include/asm-mips/elf.h
include/asm-mips/fpu.h
include/asm-mips/hazards.h
include/asm-mips/interrupt.h
include/asm-mips/irq.h
include/asm-mips/kspd.h [new file with mode: 0644]
include/asm-mips/mach-generic/ide.h
include/asm-mips/mach-jmr3927/ds1742.h
include/asm-mips/mach-mips/param.h [new file with mode: 0644]
include/asm-mips/marvell.h
include/asm-mips/mips-boards/atlas.h
include/asm-mips/mips-boards/atlasint.h
include/asm-mips/mips_mt.h [new file with mode: 0644]
include/asm-mips/mipsmtregs.h
include/asm-mips/mipsregs.h
include/asm-mips/mmu_context.h
include/asm-mips/numnodes.h [deleted file]
include/asm-mips/processor.h
include/asm-mips/ptrace.h
include/asm-mips/r4kcache.h
include/asm-mips/rtc.h
include/asm-mips/rtlx.h
include/asm-mips/serial.h
include/asm-mips/smtc.h [new file with mode: 0644]
include/asm-mips/smtc_ipi.h [new file with mode: 0644]
include/asm-mips/smtc_proc.h [new file with mode: 0644]
include/asm-mips/stackframe.h
include/asm-mips/system.h
include/asm-mips/unistd.h
include/asm-mips/vpe.h [new file with mode: 0644]
include/asm-parisc/numnodes.h [deleted file]
include/asm-powerpc/irq.h
include/asm-powerpc/numnodes.h [deleted file]
include/asm-powerpc/thread_info.h
include/asm-powerpc/unistd.h
include/asm-s390/atomic.h
include/asm-s390/ebcdic.h
include/asm-sh/numnodes.h [deleted file]
include/asm-sh/unistd.h
include/asm-sh64/unistd.h
include/asm-sparc/unistd.h
include/asm-sparc/vga.h [new file with mode: 0644]
include/asm-sparc64/percpu.h
include/asm-sparc64/unistd.h
include/asm-um/ptrace-i386.h
include/asm-v850/system.h
include/asm-x86_64/cache.h
include/asm-x86_64/cpufeature.h
include/asm-x86_64/e820.h
include/asm-x86_64/hpet.h
include/asm-x86_64/i387.h
include/asm-x86_64/ia32_unistd.h
include/asm-x86_64/io.h
include/asm-x86_64/mce.h
include/asm-x86_64/mmzone.h
include/asm-x86_64/numa.h
include/asm-x86_64/numnodes.h [deleted file]
include/asm-x86_64/percpu.h
include/asm-x86_64/timex.h
include/asm-x86_64/unistd.h
include/asm-xtensa/ioctls.h
include/asm-xtensa/system.h
include/linux/blkdev.h
include/linux/bootmem.h
include/linux/dma-mapping.h
include/linux/fs.h
include/linux/genhd.h
include/linux/gfp.h
include/linux/ide.h
include/linux/init.h
include/linux/jiffies.h
include/linux/kernel.h
include/linux/kobject.h
include/linux/leds.h
include/linux/libata.h
include/linux/memory_hotplug.h
include/linux/mm.h
include/linux/mv643xx.h
include/linux/netfilter.h
include/linux/netfilter_ipv4.h
include/linux/netfilter_ipv4/ip_conntrack_h323.h
include/linux/netfilter_ipv4/ip_conntrack_helper_h323_asn1.h [new file with mode: 0644]
include/linux/netfilter_ipv4/ip_conntrack_helper_h323_types.h [new file with mode: 0644]
include/linux/netfilter_ipv6.h
include/linux/numa.h
include/linux/page-flags.h
include/linux/pci.h
include/linux/pci_ids.h
include/linux/pipe_fs_i.h
include/linux/pm.h
include/linux/pm_legacy.h
include/linux/proc_fs.h
include/linux/raid/md_p.h
include/linux/sched.h
include/linux/screen_info.h
include/linux/sdla_asy.h [deleted file]
include/linux/sdla_chdlc.h [deleted file]
include/linux/sdla_ppp.h [deleted file]
include/linux/sdla_x25.h [deleted file]
include/linux/sdladrv.h [deleted file]
include/linux/sdlapci.h [deleted file]
include/linux/sdlasfm.h [deleted file]
include/linux/seqlock.h
include/linux/skbuff.h
include/linux/string.h
include/linux/sunrpc/metrics.h
include/linux/sunrpc/svc.h
include/linux/sunrpc/xprt.h
include/linux/swap.h
include/linux/syscalls.h
include/linux/sysfs.h
include/linux/tty_flip.h
include/linux/usb/net2280.h [new file with mode: 0644]
include/linux/vermagic.h
include/linux/wanpipe.h [deleted file]
include/net/arp.h
include/net/ieee80211softmac.h
include/net/inet6_hashtables.h
include/net/ip.h
include/net/ipv6.h
include/net/sock.h
include/net/x25device.h
include/net/xfrm.h
include/rdma/ib_sa.h
include/rdma/ib_verbs.h
include/scsi/scsi_devinfo.h
include/scsi/scsi_host.h
include/scsi/scsi_ioctl.h
include/scsi/scsi_transport.h
include/scsi/scsi_transport_fc.h
include/sound/pcm.h
ipc/shm.c
ipc/util.c
kernel/exit.c
kernel/fork.c
kernel/hrtimer.c
kernel/irq/Makefile
kernel/irq/migration.c
kernel/kprobes.c
kernel/panic.c
kernel/power/pm.c
kernel/power/snapshot.c
kernel/ptrace.c
kernel/sched.c
kernel/signal.c
kernel/sys_ni.c
kernel/timer.c
kernel/uid16.c
lib/Kconfig.debug
lib/kobject.c
lib/string.c
mm/bootmem.c
mm/madvise.c
mm/mempolicy.c
mm/migrate.c
mm/mmap.c
mm/nommu.c
mm/oom_kill.c
mm/page-writeback.c
mm/page_alloc.c
mm/slab.c
mm/slob.c
net/atm/clip.c
net/bluetooth/sco.c
net/bridge/br_input.c
net/bridge/br_netfilter.c
net/bridge/netfilter/ebtables.c
net/core/dev.c
net/core/dv.c
net/core/filter.c
net/core/flow.c
net/core/gen_estimator.c
net/core/neighbour.c
net/core/net-sysfs.c
net/core/request_sock.c
net/core/skbuff.c
net/core/stream.c
net/core/utils.c
net/core/wireless.c
net/dccp/ipv4.c
net/ieee80211/softmac/Kconfig
net/ieee80211/softmac/ieee80211softmac_assoc.c
net/ieee80211/softmac/ieee80211softmac_event.c
net/ieee80211/softmac/ieee80211softmac_io.c
net/ieee80211/softmac/ieee80211softmac_scan.c
net/ieee80211/softmac/ieee80211softmac_wx.c
net/ipv4/arp.c
net/ipv4/devinet.c
net/ipv4/fib_frontend.c
net/ipv4/fib_trie.c
net/ipv4/icmp.c
net/ipv4/inet_hashtables.c
net/ipv4/ip_fragment.c
net/ipv4/ip_gre.c
net/ipv4/ip_output.c
net/ipv4/ipcomp.c
net/ipv4/ipip.c
net/ipv4/netfilter.c
net/ipv4/netfilter/Kconfig
net/ipv4/netfilter/arp_tables.c
net/ipv4/netfilter/arptable_filter.c
net/ipv4/netfilter/ip_conntrack_core.c
net/ipv4/netfilter/ip_conntrack_helper_h323.c
net/ipv4/netfilter/ip_conntrack_helper_h323_asn1.c
net/ipv4/netfilter/ip_conntrack_helper_h323_asn1.h [deleted file]
net/ipv4/netfilter/ip_conntrack_helper_h323_types.h [deleted file]
net/ipv4/netfilter/ip_conntrack_proto_icmp.c
net/ipv4/netfilter/ip_conntrack_proto_tcp.c
net/ipv4/netfilter/ip_conntrack_proto_udp.c
net/ipv4/netfilter/ip_conntrack_standalone.c
net/ipv4/netfilter/ip_nat_helper_h323.c
net/ipv4/netfilter/ip_nat_rule.c
net/ipv4/netfilter/ip_nat_standalone.c
net/ipv4/netfilter/ip_queue.c
net/ipv4/netfilter/ip_tables.c
net/ipv4/netfilter/ipt_CLUSTERIP.c
net/ipv4/netfilter/ipt_REJECT.c
net/ipv4/netfilter/iptable_filter.c
net/ipv4/netfilter/iptable_mangle.c
net/ipv4/netfilter/iptable_raw.c
net/ipv4/netfilter/nf_conntrack_l3proto_ipv4.c
net/ipv4/netfilter/nf_conntrack_proto_icmp.c
net/ipv4/proc.c
net/ipv4/route.c
net/ipv4/tcp_input.c
net/ipv4/tcp_ipv4.c
net/ipv4/tcp_output.c
net/ipv4/tunnel4.c
net/ipv4/xfrm4_input.c
net/ipv6/exthdrs.c
net/ipv6/icmp.c
net/ipv6/inet6_hashtables.c
net/ipv6/ip6_input.c
net/ipv6/ip6_tunnel.c
net/ipv6/ipcomp6.c
net/ipv6/netfilter.c
net/ipv6/netfilter/ip6_queue.c
net/ipv6/netfilter/ip6_tables.c
net/ipv6/netfilter/ip6table_filter.c
net/ipv6/netfilter/ip6table_mangle.c
net/ipv6/netfilter/ip6table_raw.c
net/ipv6/netfilter/nf_conntrack_l3proto_ipv6.c
net/ipv6/netfilter/nf_conntrack_proto_icmpv6.c
net/ipv6/proc.c
net/ipv6/reassembly.c
net/ipv6/sit.c
net/ipv6/tunnel6.c
net/ipv6/xfrm6_policy.c
net/llc/llc_input.c
net/netfilter/core.c
net/netfilter/nf_conntrack_core.c
net/netfilter/nf_conntrack_proto_tcp.c
net/netfilter/nf_conntrack_proto_udp.c
net/netfilter/nf_conntrack_standalone.c
net/netfilter/nf_queue.c
net/netfilter/nfnetlink_log.c
net/netfilter/nfnetlink_queue.c
net/netfilter/x_tables.c
net/sched/act_police.c
net/sctp/proc.c
net/socket.c
net/sunrpc/auth_gss/auth_gss.c
net/sunrpc/auth_gss/gss_krb5_crypto.c
net/sunrpc/auth_gss/svcauth_gss.c
net/sunrpc/stats.c
net/tipc/name_distr.c
net/wanrouter/af_wanpipe.c
net/xfrm/xfrm_state.c
scripts/Kbuild.include
scripts/Makefile.lib
scripts/bloat-o-meter [changed mode: 0644->0755]
scripts/checkstack.pl [changed mode: 0644->0755]
scripts/gen_initramfs_list.sh
scripts/kconfig/conf.c
scripts/kconfig/confdata.c
scripts/kconfig/lxdialog/checklist.c
scripts/kconfig/lxdialog/menubox.c
scripts/mod/modpost.c
scripts/namespace.pl [changed mode: 0644->0755]
scripts/show_delta [changed mode: 0644->0755]
scripts/ver_linux
security/keys/key.c
security/keys/keyring.c
security/keys/process_keys.c
security/selinux/ss/mls.c
security/selinux/xfrm.c
sound/core/oss/pcm_oss.c
sound/core/pcm.c
sound/core/pcm_native.c
sound/drivers/mpu401/mpu401_uart.c
sound/isa/ad1848/ad1848.c
sound/isa/adlib.c
sound/isa/cmi8330.c
sound/isa/cs423x/cs4231.c
sound/isa/cs423x/cs4236.c
sound/isa/es1688/es1688.c
sound/isa/es18xx.c
sound/isa/gus/gusclassic.c
sound/isa/gus/gusextreme.c
sound/isa/gus/gusmax.c
sound/isa/gus/interwave.c
sound/isa/opl3sa2.c
sound/isa/opti9xx/miro.c
sound/isa/opti9xx/opti92x-ad1848.c
sound/isa/sb/sb16.c
sound/isa/sb/sb8.c
sound/isa/sgalaxy.c
sound/isa/sscape.c
sound/isa/wavefront/wavefront.c
sound/oss/Kconfig
sound/oss/emu10k1/main.c
sound/pci/ac97/ac97_codec.c
sound/pci/als300.c
sound/pci/au88x0/au88x0.h
sound/pci/au88x0/au88x0_core.c
sound/pci/au88x0/au88x0_eq.c
sound/pci/au88x0/au88x0_pcm.c
sound/pci/emu10k1/emu10k1_main.c
sound/pci/hda/patch_analog.c
sound/pci/hda/patch_sigmatel.c
sound/pci/via82xx.c
usr/Makefile
usr/gen_init_cpio.c

diff --git a/CREDITS b/CREDITS
index 0bf31eac6dc221add4980576b5e55f6fce384d70..787564bc248b1d6125fc42f3932966b60aa2f7f4 100644 (file)
--- a/CREDITS
+++ b/CREDITS
@@ -3382,7 +3382,7 @@ S: Germany
 
 N: Geert Uytterhoeven
 E: geert@linux-m68k.org
-W: http://home.tvd.be/cr26864/
+W: http://users.telenet.be/geertu/
 P: 1024/862678A6 C51D 361C 0BD1 4C90 B275  C553 6EEA 11BA 8626 78A6
 D: m68k/Amiga and PPC/CHRP Longtrail coordinator
 D: Frame buffer device and XF68_FBDev maintainer
@@ -3392,8 +3392,8 @@ D: Amiga Buddha and Catweasel chipset IDE
 D: Atari Falcon chipset IDE
 D: Amiga Gayle chipset IDE
 D: mipsel NEC DDB Vrc-5074
-S: Emiel Vlieberghlaan 2A/21
-S: B-3010 Kessel-Lo
+S: Haterbeekstraat 55B
+S: B-3200 Aarschot
 S: Belgium
 
 N: Chris Vance
index 1af0f2d5022066f1a205ad5265771e3ab112c018..2ffb0d62f0fe3ed8156586505b7faf1efe1c33ce 100644 (file)
@@ -33,7 +33,9 @@ pci_alloc_consistent(struct pci_dev *dev, size_t size,
 
 Consistent memory is memory for which a write by either the device or
 the processor can immediately be read by the processor or device
-without having to worry about caching effects.
+without having to worry about caching effects.  (You may however need
+to make sure to flush the processor's write buffers before telling
+devices to read that memory.)
 
 This routine allocates a region of <size> bytes of consistent memory.
 it also returns a <dma_handle> which may be cast to an unsigned
@@ -304,12 +306,12 @@ dma address with dma_mapping_error(). A non zero return value means the mapping
 could not be created and the driver should take appropriate action (eg
 reduce current DMA mapping usage or delay and try again later).
 
-int
-dma_map_sg(struct device *dev, struct scatterlist *sg, int nents,
-          enum dma_data_direction direction)
-int
-pci_map_sg(struct pci_dev *hwdev, struct scatterlist *sg,
-          int nents, int direction)
+       int
+       dma_map_sg(struct device *dev, struct scatterlist *sg,
+               int nents, enum dma_data_direction direction)
+       int
+       pci_map_sg(struct pci_dev *hwdev, struct scatterlist *sg,
+               int nents, int direction)
 
 Maps a scatter gather list from the block layer.
 
@@ -327,12 +329,33 @@ critical that the driver do something, in the case of a block driver
 aborting the request or even oopsing is better than doing nothing and
 corrupting the filesystem.
 
-void
-dma_unmap_sg(struct device *dev, struct scatterlist *sg, int nhwentries,
-            enum dma_data_direction direction)
-void
-pci_unmap_sg(struct pci_dev *hwdev, struct scatterlist *sg,
-            int nents, int direction)
+With scatterlists, you use the resulting mapping like this:
+
+       int i, count = dma_map_sg(dev, sglist, nents, direction);
+       struct scatterlist *sg;
+
+       for (i = 0, sg = sglist; i < count; i++, sg++) {
+               hw_address[i] = sg_dma_address(sg);
+               hw_len[i] = sg_dma_len(sg);
+       }
+
+where nents is the number of entries in the sglist.
+
+The implementation is free to merge several consecutive sglist entries
+into one (e.g. with an IOMMU, or if several pages just happen to be
+physically contiguous) and returns the actual number of sg entries it
+mapped them to. On failure 0, is returned.
+
+Then you should loop count times (note: this can be less than nents times)
+and use sg_dma_address() and sg_dma_len() macros where you previously
+accessed sg->address and sg->length as shown above.
+
+       void
+       dma_unmap_sg(struct device *dev, struct scatterlist *sg,
+               int nhwentries, enum dma_data_direction direction)
+       void
+       pci_unmap_sg(struct pci_dev *hwdev, struct scatterlist *sg,
+               int nents, int direction)
 
 unmap the previously mapped scatter/gather list.  All the parameters
 must be the same as those and passed in to the scatter/gather mapping
index ee4bb73683cd40e3550484b2b2248ef75088910f..7c717699032c90f403432ef793cfeed8c359fe7b 100644 (file)
@@ -58,11 +58,15 @@ translating each of those pages back to a kernel address using
 something like __va().  [ EDIT: Update this when we integrate
 Gerd Knorr's generic code which does this. ]
 
-This rule also means that you may not use kernel image addresses
-(ie. items in the kernel's data/text/bss segment, or your driver's)
-nor may you use kernel stack addresses for DMA.  Both of these items
-might be mapped somewhere entirely different than the rest of physical
-memory.
+This rule also means that you may use neither kernel image addresses
+(items in data/text/bss segments), nor module image addresses, nor
+stack addresses for DMA.  These could all be mapped somewhere entirely
+different than the rest of physical memory.  Even if those classes of
+memory could physically work with DMA, you'd need to ensure the I/O
+buffers were cacheline-aligned.  Without that, you'd see cacheline
+sharing problems (data corruption) on CPUs with DMA-incoherent caches.
+(The CPU could write to one word, DMA would write to a different one
+in the same cache line, and one of them could be overwritten.)
 
 Also, this means that you cannot take the return of a kmap()
 call and DMA to/from that.  This is similar to vmalloc().
@@ -194,7 +198,7 @@ document for how to handle this case.
 Finally, if your device can only drive the low 24-bits of
 address during PCI bus mastering you might do something like:
 
-       if (pci_set_dma_mask(pdev, 0x00ffffff)) {
+       if (pci_set_dma_mask(pdev, DMA_24BIT_MASK)) {
                printk(KERN_WARNING
                       "mydev: 24-bit DMA addressing not available.\n");
                goto ignore_this_device;
@@ -212,7 +216,7 @@ functions (for example a sound card provides playback and record
 functions) and the various different functions have _different_
 DMA addressing limitations, you may wish to probe each mask and
 only provide the functionality which the machine can handle.  It
-is important that the last call to pci_set_dma_mask() be for the 
+is important that the last call to pci_set_dma_mask() be for the
 most specific mask.
 
 Here is pseudo-code showing how this might be done:
@@ -284,6 +288,11 @@ There are two types of DMA mappings:
 
              in order to get correct behavior on all platforms.
 
+            Also, on some platforms your driver may need to flush CPU write
+            buffers in much the same way as it needs to flush write buffers
+            found in PCI bridges (such as by reading a register's value
+            after writing it).
+
 - Streaming DMA mappings which are usually mapped for one DMA transfer,
   unmapped right after it (unless you use pci_dma_sync_* below) and for which
   hardware can optimize for sequential accesses.
@@ -303,6 +312,9 @@ There are two types of DMA mappings:
 
 Neither type of DMA mapping has alignment restrictions that come
 from PCI, although some devices may have such restrictions.
+Also, systems with caches that aren't DMA-coherent will work better
+when the underlying buffers don't share cache lines with other data.
+
 
                 Using Consistent DMA mappings.
 
index 5bcbb6ee3bc03cf1632bd345a7b28bc2a610e033..f869b03929db44fa6a5c391bf9d1fd09a4e7ea0d 100644 (file)
@@ -705,7 +705,7 @@ and other resources, etc.
 
        <sect1><title>ata_scsi_error()</title>
        <para>
-       ata_scsi_error() is the current hostt->eh_strategy_handler()
+       ata_scsi_error() is the current transportt->eh_strategy_handler()
        for libata.  As discussed above, this will be entered in two
        cases - timeout and ATAPI error completion.  This function
        calls low level libata driver's eng_timeout() callback, the
diff --git a/Documentation/block/switching-sched.txt b/Documentation/block/switching-sched.txt
new file mode 100644 (file)
index 0000000..5fa130a
--- /dev/null
@@ -0,0 +1,22 @@
+As of the Linux 2.6.10 kernel, it is now possible to change the
+IO scheduler for a given block device on the fly (thus making it possible,
+for instance, to set the CFQ scheduler for the system default, but
+set a specific device to use the anticipatory or noop schedulers - which
+can improve that device's throughput).
+
+To set a specific scheduler, simply do this:
+
+echo SCHEDNAME > /sys/block/DEV/queue/scheduler
+
+where SCHEDNAME is the name of a defined IO scheduler, and DEV is the
+device name (hda, hdb, sga, or whatever you happen to have).
+
+The list of defined schedulers can be found by simply doing
+a "cat /sys/block/DEV/queue/scheduler" - the list of valid names
+will be displayed, with the currently selected scheduler in brackets:
+
+# cat /sys/block/hda/queue/scheduler
+noop anticipatory deadline [cfq]
+# echo anticipatory > /sys/block/hda/queue/scheduler
+# cat /sys/block/hda/queue/scheduler
+noop [anticipatory] deadline cfq
index 5009805f9378b6b60a566da9e9644be0dc34acfc..ffdb5323df378b84963e4f91cd1470ff17865b6d 100644 (file)
@@ -53,4 +53,4 @@ the CPUFreq Mailing list:
 * http://lists.linux.org.uk/mailman/listinfo/cpufreq
 
 Clock and voltage scaling for the SA-1100:
-* http://www.lart.tudelft.nl/projects/scaling
+* http://www.lartmaker.nl/projects/scaling
index 59d0c74c79c955d4859e0c7cb3de222c14a23a1a..421bcfff6ad21be680fcf819243ca9d750fa8ab2 100644 (file)
@@ -25,8 +25,9 @@ Who:  Adrian Bunk <bunk@stusta.de>
 
 ---------------------------
 
-What:  drivers depending on OBSOLETE_OSS_DRIVER
-When:  January 2006
+What:  drivers that were depending on OBSOLETE_OSS_DRIVER
+        (config options already removed)
+When:  before 2.6.19
 Why:   OSS drivers with ALSA replacements
 Who:   Adrian Bunk <bunk@stusta.de>
 
@@ -71,14 +72,6 @@ Who: Mauro Carvalho Chehab <mchehab@brturbo.com.br>
 
 ---------------------------
 
-What:  remove EXPORT_SYMBOL(panic_timeout)
-When:  April 2006
-Files: kernel/panic.c
-Why:   No modular usage in the kernel.
-Who:   Adrian Bunk <bunk@stusta.de>
-
----------------------------
-
 What:  remove EXPORT_SYMBOL(insert_resource)
 When:  April 2006
 Files: kernel/resource.c
index adaa899e5c903763a4f0938efedd1bd3bbdce4a0..3a2e5520c1e3af38ea2ff91dc13a15d17f24aac0 100644 (file)
@@ -694,7 +694,7 @@ struct file_operations
 ----------------------
 
 This describes how the VFS can manipulate an open file. As of kernel
-2.6.13, the following members are defined:
+2.6.17, the following members are defined:
 
 struct file_operations {
        loff_t (*llseek) (struct file *, loff_t, int);
@@ -723,6 +723,10 @@ struct file_operations {
        int (*check_flags)(int);
        int (*dir_notify)(struct file *filp, unsigned long arg);
        int (*flock) (struct file *, int, struct file_lock *);
+       ssize_t (*splice_write)(struct pipe_inode_info *, struct file *, size_t, unsigned 
+int);
+       ssize_t (*splice_read)(struct file *, struct pipe_inode_info *, size_t, unsigned  
+int);
 };
 
 Again, all methods are called without any locks being held, unless
@@ -790,6 +794,12 @@ otherwise noted.
 
   flock: called by the flock(2) system call
 
+  splice_write: called by the VFS to splice data from a pipe to a file. This
+               method is used by the splice(2) system call
+
+  splice_read: called by the VFS to splice data from file to a pipe. This
+              method is used by the splice(2) system call
+
 Note that the file operations are implemented by the specific
 filesystem in which the inode resides. When opening a device node
 (character or block special) most filesystems will call special
index d9f23c0763f1c25d1cec80310abe11b09828c76e..77b995dfca22652bc94532a9145047d444b8baec 100644 (file)
@@ -12,18 +12,22 @@ meant as a replacement for the older, individual drivers:
                       teletext adapters)
 
 It currently supports the following devices:
- * Philips adapter
- * home brew teletext adapter
- * Velleman K8000 adapter
- * ELV adapter
- * Analog Devices evaluation boards (ADM1025, ADM1030, ADM1031, ADM1032)
- * Barco LPT->DVI (K5800236) adapter
+ * (type=0) Philips adapter
+ * (type=1) home brew teletext adapter
+ * (type=2) Velleman K8000 adapter
+ * (type=3) ELV adapter
+ * (type=4) Analog Devices ADM1032 evaluation board
+ * (type=5) Analog Devices evaluation boards: ADM1025, ADM1030, ADM1031
+ * (type=6) Barco LPT->DVI (K5800236) adapter
 
 These devices use different pinout configurations, so you have to tell
 the driver what you have, using the type module parameter. There is no
 way to autodetect the devices. Support for different pinout configurations
 can be easily added when needed.
 
+Earlier kernels defaulted to type=0 (Philips).  But now, if the type
+parameter is missing, the driver will simply fail to initialize.
+
 
 Building your own adapter
 -------------------------
diff --git a/Documentation/isdn/README.gigaset b/Documentation/isdn/README.gigaset
new file mode 100644 (file)
index 0000000..85a64de
--- /dev/null
@@ -0,0 +1,286 @@
+GigaSet 307x Device Driver
+==========================
+
+1.   Requirements
+     ------------
+1.1. Hardware
+     --------
+     This release supports the connection of the Gigaset 307x/417x family of
+     ISDN DECT bases via Gigaset M101 Data, Gigaset M105 Data or direct USB
+     connection. The following devices are reported to be compatible:
+     307x/417x:
+        Gigaset SX255isdn
+        Gigaset SX353isdn
+        Sinus 45 [AB] isdn (Deutsche Telekom)
+        Sinus 721X/XA
+        Vox Chicago 390 ISDN (KPN Telecom)
+     M101:
+        Sinus 45 Data 1 (Telekom)
+     M105:
+        Gigaset USB Adapter DECT
+        Sinus 45 Data 2 (Telekom)
+        Sinus 721 data
+        Chicago 390 USB (KPN)
+     See also http://www.erbze.info/sinus_gigaset.htm and
+              http://gigaset307x.sourceforge.net/
+
+     We had also reports from users of Gigaset M105 who could use the drivers
+     with SX 100 and CX 100 ISDN bases (only in unimodem mode, see section 2.4.)
+     If you have another device that works with our driver, please let us know.
+     For example, Gigaset SX205isdn/Sinus 721 X SE and Gigaset SX303isdn bases
+     are just versions without answering machine of models known to work, so
+     they should work just as well; but so far we are lacking positive reports
+     on these.
+
+     Chances of getting an USB device to work are good if the output of
+        lsusb
+     at the command line contains one of the following:
+        ID 0681:0001
+        ID 0681:0002
+        ID 0681:0009
+        ID 0681:0021
+        ID 0681:0022
+
+1.2. Software
+     --------
+     The driver works with ISDN4linux and so can be used with any software
+     which is able to use ISDN4linux for ISDN connections (voice or data).
+     CAPI4Linux support is planned but not yet available.
+
+     There are some user space tools available at
+     http://sourceforge.net/projects/gigaset307x/
+     which provide access to additional device specific functions like SMS,
+     phonebook or call journal.
+
+
+2.   How to use the driver
+     ---------------------
+2.1. Modules
+     -------
+     To get the device working, you have to load the proper kernel module. You
+     can do this using
+         modprobe modulename
+     where modulename is usb_gigaset (M105) or bas_gigaset (direct USB
+     connection to the base).
+
+2.2. Device nodes for user space programs
+     ------------------------------------
+     The device can be accessed from user space (eg. by the user space tools
+     mentioned in 1.2.) through the device nodes:
+
+     - /dev/ttyGU0 for M105 (USB data boxes)
+     - /dev/ttyGB0 for the base driver (direct USB connection)
+
+     You can also select a "default device" which is used by the frontends when
+     no device node is given as parameter, by creating a symlink /dev/ttyG to
+     one of them, eg.:
+
+        ln -s /dev/ttyGB0 /dev/ttyG
+
+2.3. ISDN4linux
+     ----------
+     This is the "normal" mode of operation. After loading the module you can
+     set up the ISDN system just as you'd do with any ISDN card.
+     Your distribution should provide some configuration utility.
+     If not, you can use some HOWTOs like
+         http://www.linuxhaven.de/dlhp/HOWTO/DE-ISDN-HOWTO-5.html
+     If this doesn't work, because you have some recent device like SX100 where
+     debug output (see section 3.2.) shows something like this when dialing
+         CMD Received: ERROR
+         Available Params: 0
+         Connection State: 0, Response: -1
+         gigaset_process_response: resp_code -1 in ConState 0 !
+         Timeout occurred
+     you might need to use unimodem mode:
+
+2.4. Unimodem mode
+     -------------
+     This is needed for some devices [e.g. SX100] as they have problems with
+     the "normal" commands.
+
+     If you have installed the command line tool gigacontr, you can enter
+     unimodem mode using
+         gigacontr --mode unimodem
+     You can switch back using
+         gigacontr --mode isdn
+
+     You can also load the driver using e.g.
+         modprobe usb_gigaset startmode=0
+     to prevent the driver from starting in "isdn4linux mode".
+
+     In this mode the device works like a modem connected to a serial port
+     (the /dev/ttyGU0, ... mentioned above) which understands the commands
+         ATZ                 init, reset
+             => OK or ERROR
+         ATD
+         ATDT                dial
+             => OK, CONNECT,
+                BUSY,
+                NO DIAL TONE,
+                NO CARRIER,
+                NO ANSWER
+         <pause>+++<pause>   change to command mode when connected
+         ATH                 hangup
+
+     You can use some configuration tool of your distribution to configure this
+     "modem" or configure pppd/wvdial manually. There are some example ppp
+     configuration files and chat scripts in the gigaset-VERSION/ppp directory.
+     Please note that the USB drivers are not able to change the state of the
+     control lines (the M105 driver can be configured to use some undocumented
+     control requests, if you really need the control lines, though). This means
+     you must use "Stupid Mode" if you are using wvdial or you should use the
+     nocrtscts option of pppd.
+     You must also assure that the ppp_async module is loaded with the parameter
+     flag_time=0. You can do this e.g. by adding a line like
+
+        options ppp_async flag_time=0
+
+     to /etc/modprobe.conf. If your distribution has some local module
+     configuration file like /etc/modprobe.conf.local,
+     using that should be preferred.
+
+2.5. Call-ID (CID) mode
+     ------------------
+     Call-IDs are numbers used to tag commands to, and responses from, the
+     Gigaset base in order to support the simultaneous handling of multiple
+     ISDN calls. Their use can be enabled ("CID mode") or disabled ("Unimodem
+     mode"). Without Call-IDs (in Unimodem mode), only a very limited set of
+     functions is available. It allows outgoing data connections only, but
+     does not signal incoming calls or other base events.
+
+     DECT cordless data devices (M10x) permanently occupy the cordless
+     connection to the base while Call-IDs are activated. As the Gigaset
+     bases only support one DECT data connection at a time, this prevents
+     other DECT cordless data devices from accessing the base.
+
+     During active operation, the driver switches to the necessary mode
+     automatically. However, for the reasons above, the mode chosen when
+     the device is not in use (idle) can be selected by the user.
+     - If you want to receive incoming calls, you can use the default
+       settings (CID mode).
+     - If you have several DECT data devices (M10x) which you want to use
+       in turn, select Unimodem mode by passing the parameter "cidmode=0" to
+       the driver ("modprobe usb_gigaset cidmode=0" or modprobe.conf).
+
+     If you want both of these at once, you are out of luck.
+
+     You can also use /sys/module/<name>/parameters/cidmode for changing
+     the CID mode setting (<name> is usb_gigaset or bas_gigaset).
+
+
+3.   Troubleshooting
+     ---------------
+3.1. Solutions to frequently reported problems
+     -----------------------------------------
+     Problem:
+        You have a slow provider and isdn4linux gives up dialing too early.
+     Solution:
+        Load the isdn module using the dialtimeout option. You can do this e.g.
+        by adding a line like
+
+           options isdn dialtimeout=15
+
+        to /etc/modprobe.conf. If your distribution has some local module
+        configuration file like /etc/modprobe.conf.local,
+        using that should be preferred.
+
+     Problem:
+        Your isdn script aborts with a message about isdnlog.
+     Solution:
+        Try deactivating (or commenting out) isdnlog. This driver does not
+        support it.
+
+     Problem:
+        You have two or more DECT data adapters (M101/M105) and only the
+        first one you turn on works.
+     Solution:
+        Select Unimodem mode for all DECT data adapters. (see section 2.4.)
+
+3.2. Telling the driver to provide more information
+     ----------------------------------------------
+     Building the driver with the "Gigaset debugging" kernel configuration
+     option (CONFIG_GIGASET_DEBUG) gives it the ability to produce additional
+     information useful for debugging.
+
+     You can control the amount of debugging information the driver produces by
+     writing an appropriate value to /sys/module/gigaset/parameters/debug, e.g.
+        echo 0 > /sys/module/gigaset/parameters/debug
+     switches off debugging output completely,
+        echo 0x10a020 > /sys/module/gigaset/parameters/debug
+     enables the standard set of debugging output messages. These values are
+     bit patterns where every bit controls a certain type of debugging output.
+     See the constants DEBUG_* in the source file gigaset.h for details.
+
+     The initial value can be set using the debug parameter when loading the
+     module "gigaset", e.g. by adding a line
+        options gigaset debug=0
+     to /etc/modprobe.conf, ...
+
+     Generated debugging information can be found
+     - as output of the command
+         dmesg
+     - in system log files written by your syslog daemon, usually
+       in /var/log/, e.g. /var/log/messages.
+
+3.3. Reporting problems and bugs
+     ---------------------------
+     If you can't solve problems with the driver on your own, feel free to
+     use one of the forums, bug trackers, or mailing lists on
+         http://sourceforge.net/projects/gigaset307x
+     or write an electronic mail to the maintainers.
+
+     Try to provide as much information as possible, such as
+     - distribution
+     - kernel version (uname -r)
+     - gcc version (gcc --version)
+     - hardware architecture (uname -m, ...)
+     - type and firmware version of your device (base and wireless module,
+       if any)
+     - output of "lsusb -v" (if using an USB device)
+     - error messages
+     - relevant system log messages (it would help if you activate debug
+       output as described in 3.2.)
+
+     For help with general configuration problems not specific to our driver,
+     such as isdn4linux and network configuration issues, please refer to the
+     appropriate forums and newsgroups.
+
+3.4. Reporting problem solutions
+     ---------------------------
+     If you solved a problem with our drivers, wrote startup scripts for your
+     distribution, ... feel free to contact us (using one of the places
+     mentioned in 3.3.). We'd like to add scripts, hints, documentation
+     to the driver and/or the project web page.
+
+
+4.   Links, other software
+     ---------------------
+     - Sourceforge project developing this driver and associated tools
+         http://sourceforge.net/projects/gigaset307x
+     - Yahoo! Group on the Siemens Gigaset family of devices
+         http://de.groups.yahoo.com/group/Siemens-Gigaset
+     - Siemens Gigaset/T-Sinus compatibility table
+         http://www.erbze.info/sinus_gigaset.htm
+
+
+5.   Credits
+     -------
+     Thanks to
+
+     Karsten Keil
+        for his help with isdn4linux
+     Deti Fliegl
+        for his base driver code
+     Dennis Dietrich
+        for his kernel 2.6 patches
+     Andreas Rummel
+        for his work and logs to get unimodem mode working
+     Andreas Degert
+        for his logs and patches to get cx 100 working
+     Dietrich Feist
+        for his generous donation of one M105 and two M101 cordless adapters
+     Christoph Schweers
+        for his generous donation of a M34 device
+
+     and all the other people who sent logs and other information.
+
index fcccf2432f98ff48d8d87b040c92e9ab5a8ef01a..61fc079eb9661a7bd5eff33bc11e05e437734cc9 100644 (file)
@@ -44,7 +44,7 @@ What is covered within this file is mainly information to authors
 of modules. The author of an external modules should supply
 a makefile that hides most of the complexity so one only has to type
 'make' to build the module. A complete example will be present in
-chapter Â¤. Creating a kbuild file for an external module".
+chapter 4, "Creating a kbuild file for an external module".
 
 
 === 2. How to build external modules
index b18e216759060ef792f3b62f4e0865f86dd60b06..5696e879449bca5c7353804d5fca069cd9926f46 100644 (file)
@@ -919,11 +919,11 @@ int main(int argc, char **argv)
     int settle_time = 60;
 
     /* Parse the simple command-line */
-    if (ac == 2)
-       disk = av[1];
-    else if (ac == 4) {
-       settle_time = atoi(av[2]);
-       disk = av[3];
+    if (argc == 2)
+       disk = argv[1];
+    else if (argc == 4) {
+       settle_time = atoi(argv[2]);
+       disk = argv[3];
     } else
        usage();
 
index f8550310a6d5d6481ac15417dac04fcfaf0e910a..92f0056d928c1f5ff485e250a93a843bb60058bc 100644 (file)
@@ -610,6 +610,7 @@ loads.  Consider the following sequence of events:
 
        CPU 1                   CPU 2
        ======================= =======================
+               { B = 7; X = 9; Y = 8; C = &Y }
        STORE A = 1
        STORE B = 2
        <write barrier>
@@ -651,7 +652,20 @@ In the above example, CPU 2 perceives that B is 7, despite the load of *C
 (which would be B) coming after the the LOAD of C.
 
 If, however, a data dependency barrier were to be placed between the load of C
-and the load of *C (ie: B) on CPU 2, then the following will occur:
+and the load of *C (ie: B) on CPU 2:
+
+       CPU 1                   CPU 2
+       ======================= =======================
+               { B = 7; X = 9; Y = 8; C = &Y }
+       STORE A = 1
+       STORE B = 2
+       <write barrier>
+       STORE C = &B            LOAD X
+       STORE D = 4             LOAD C (gets &B)
+                               <data dependency barrier>
+                               LOAD *C (reads B)
+
+then the following will occur:
 
        +-------+       :      :                :       :
        |       |       +------+                +-------+
@@ -829,8 +843,8 @@ There are some more advanced barrier functions:
  (*) smp_mb__after_atomic_inc();
 
      These are for use with atomic add, subtract, increment and decrement
-     functions, especially when used for reference counting.  These functions
-     do not imply memory barriers.
+     functions that don't return a value, especially when used for reference
+     counting.  These functions do not imply memory barriers.
 
      As an example, consider a piece of code that marks an object as being dead
      and then decrements the object's reference count:
@@ -1263,15 +1277,17 @@ else.
 ATOMIC OPERATIONS
 -----------------
 
-Though they are technically interprocessor interaction considerations, atomic
-operations are noted specially as they do _not_ generally imply memory
-barriers.  The possible offenders include:
+Whilst they are technically interprocessor interaction considerations, atomic
+operations are noted specially as some of them imply full memory barriers and
+some don't, but they're very heavily relied on as a group throughout the
+kernel.
+
+Any atomic operation that modifies some state in memory and returns information
+about the state (old or new) implies an SMP-conditional general memory barrier
+(smp_mb()) on each side of the actual operation.  These include:
 
        xchg();
        cmpxchg();
-       test_and_set_bit();
-       test_and_clear_bit();
-       test_and_change_bit();
        atomic_cmpxchg();
        atomic_inc_return();
        atomic_dec_return();
@@ -1282,21 +1298,31 @@ barriers.  The possible offenders include:
        atomic_sub_and_test();
        atomic_add_negative();
        atomic_add_unless();
+       test_and_set_bit();
+       test_and_clear_bit();
+       test_and_change_bit();
 
-These may be used for such things as implementing LOCK operations or controlling
-the lifetime of objects by decreasing their reference counts.  In such cases
-they need preceding memory barriers.
+These are used for such things as implementing LOCK-class and UNLOCK-class
+operations and adjusting reference counters towards object destruction, and as
+such the implicit memory barrier effects are necessary.
 
-The following may also be possible offenders as they may be used as UNLOCK
-operations.
 
+The following operation are potential problems as they do _not_ imply memory
+barriers, but might be used for implementing such things as UNLOCK-class
+operations:
+
+       atomic_set();
        set_bit();
        clear_bit();
        change_bit();
-       atomic_set();
 
+With these the appropriate explicit memory barrier should be used if necessary
+(smp_mb__before_clear_bit() for instance).
 
-The following are a little tricky:
+
+The following also do _not_ imply memory barriers, and so may require explicit
+memory barriers under some circumstances (smp_mb__before_atomic_dec() for
+instance)):
 
        atomic_add();
        atomic_sub();
@@ -1317,10 +1343,12 @@ specific order.
 
 
 Basically, each usage case has to be carefully considered as to whether memory
-barriers are needed or not.  The simplest rule is probably: if the atomic
-operation is protected by a lock, then it does not require a barrier unless
-there's another operation within the critical section with respect to which an
-ordering must be maintained.
+barriers are needed or not.
+
+[!] Note that special memory barrier primitives are available for these
+situations because on some CPUs the atomic instructions used imply full memory
+barriers, and so barrier instructions are superfluous in conjunction with them,
+and in such cases the special barrier primitives will be no-ops.
 
 See Documentation/atomic_ops.txt for more information.
 
index b78af1c329967adcd5da3c7a9098d351b034645d..c39ac395970ecfa7ee58dada23478c886952a415 100644 (file)
@@ -138,19 +138,29 @@ Reading MTRRs from a C program using ioctl()'s:
 
 */
 #include <stdio.h>
+#include <stdlib.h>
 #include <string.h>
 #include <sys/types.h>
 #include <sys/stat.h>
 #include <fcntl.h>
 #include <sys/ioctl.h>
 #include <errno.h>
-#define MTRR_NEED_STRINGS
 #include <asm/mtrr.h>
 
 #define TRUE 1
 #define FALSE 0
 #define ERRSTRING strerror (errno)
 
+static char *mtrr_strings[MTRR_NUM_TYPES] =
+{
+    "uncachable",               /* 0 */
+    "write-combining",          /* 1 */
+    "?",                        /* 2 */
+    "?",                        /* 3 */
+    "write-through",            /* 4 */
+    "write-protect",            /* 5 */
+    "write-back",               /* 6 */
+};
 
 int main ()
 {
@@ -232,13 +242,22 @@ Creating MTRRs from a C programme using ioctl()'s:
 #include <fcntl.h>
 #include <sys/ioctl.h>
 #include <errno.h>
-#define MTRR_NEED_STRINGS
 #include <asm/mtrr.h>
 
 #define TRUE 1
 #define FALSE 0
 #define ERRSTRING strerror (errno)
 
+static char *mtrr_strings[MTRR_NUM_TYPES] =
+{
+    "uncachable",               /* 0 */
+    "write-combining",          /* 1 */
+    "?",                        /* 2 */
+    "?",                        /* 3 */
+    "write-through",            /* 4 */
+    "write-protect",            /* 5 */
+    "write-back",               /* 6 */
+};
 
 int main (int argc, char **argv)
 {
diff --git a/Documentation/networking/xfrm_sync.txt b/Documentation/networking/xfrm_sync.txt
new file mode 100644 (file)
index 0000000..8be626f
--- /dev/null
@@ -0,0 +1,166 @@
+
+The sync patches work is based on initial patches from
+Krisztian <hidden@balabit.hu> and others and additional patches
+from Jamal <hadi@cyberus.ca>.
+
+The end goal for syncing is to be able to insert attributes + generate
+events so that the an SA can be safely moved from one machine to another
+for HA purposes.
+The idea is to synchronize the SA so that the takeover machine can do
+the processing of the SA as accurate as possible if it has access to it.
+
+We already have the ability to generate SA add/del/upd events.
+These patches add ability to sync and have accurate lifetime byte (to
+ensure proper decay of SAs) and replay counters to avoid replay attacks
+with as minimal loss at failover time.
+This way a backup stays as closely uptodate as an active member.
+
+Because the above items change for every packet the SA receives,
+it is possible for a lot of the events to be generated.
+For this reason, we also add a nagle-like algorithm to restrict
+the events. i.e we are going to set thresholds to say "let me
+know if the replay sequence threshold is reached or 10 secs have passed"
+These thresholds are set system-wide via sysctls or can be updated
+per SA.
+
+The identified items that need to be synchronized are:
+- the lifetime byte counter
+note that: lifetime time limit is not important if you assume the failover
+machine is known ahead of time since the decay of the time countdown
+is not driven by packet arrival.
+- the replay sequence for both inbound and outbound
+
+1) Message Structure
+----------------------
+
+nlmsghdr:aevent_id:optional-TLVs.
+
+The netlink message types are:
+
+XFRM_MSG_NEWAE and XFRM_MSG_GETAE.
+
+A XFRM_MSG_GETAE does not have TLVs.
+A XFRM_MSG_NEWAE will have at least two TLVs (as is
+discussed further below).
+
+aevent_id structure looks like:
+
+   struct xfrm_aevent_id {
+             struct xfrm_usersa_id           sa_id;
+             __u32                           flags;
+   };
+
+xfrm_usersa_id in this message layout identifies the SA.
+
+flags are used to indicate different things. The possible
+flags are:
+        XFRM_AE_RTHR=1, /* replay threshold*/
+        XFRM_AE_RVAL=2, /* replay value */
+        XFRM_AE_LVAL=4, /* lifetime value */
+        XFRM_AE_ETHR=8, /* expiry timer threshold */
+        XFRM_AE_CR=16, /* Event cause is replay update */
+        XFRM_AE_CE=32, /* Event cause is timer expiry */
+        XFRM_AE_CU=64, /* Event cause is policy update */
+
+How these flags are used is dependent on the direction of the
+message (kernel<->user) as well the cause (config, query or event).
+This is described below in the different messages.
+
+The pid will be set appropriately in netlink to recognize direction
+(0 to the kernel and pid = processid that created the event
+when going from kernel to user space)
+
+A program needs to subscribe to multicast group XFRMNLGRP_AEVENTS
+to get notified of these events.
+
+2) TLVS reflect the different parameters:
+-----------------------------------------
+
+a) byte value (XFRMA_LTIME_VAL)
+This TLV carries the running/current counter for byte lifetime since
+last event.
+
+b)replay value (XFRMA_REPLAY_VAL)
+This TLV carries the running/current counter for replay sequence since
+last event.
+
+c)replay threshold (XFRMA_REPLAY_THRESH)
+This TLV carries the threshold being used by the kernel to trigger events
+when the replay sequence is exceeded.
+
+d) expiry timer (XFRMA_ETIMER_THRESH)
+This is a timer value in milliseconds which is used as the nagle
+value to rate limit the events.
+
+3) Default configurations for the parameters:
+----------------------------------------------
+
+By default these events should be turned off unless there is
+at least one listener registered to listen to the multicast
+group XFRMNLGRP_AEVENTS.
+
+Programs installing SAs will need to specify the two thresholds, however,
+in order to not change existing applications such as racoon
+we also provide default threshold values for these different parameters
+in case they are not specified.
+
+the two sysctls/proc entries are:
+a) /proc/sys/net/core/sysctl_xfrm_aevent_etime
+used to provide default values for the XFRMA_ETIMER_THRESH in incremental
+units of time of 100ms. The default is 10 (1 second)
+
+b) /proc/sys/net/core/sysctl_xfrm_aevent_rseqth
+used to provide default values for XFRMA_REPLAY_THRESH parameter
+in incremental packet count. The default is two packets.
+
+4) Message types
+----------------
+
+a) XFRM_MSG_GETAE issued by user-->kernel.
+XFRM_MSG_GETAE does not carry any TLVs.
+The response is a XFRM_MSG_NEWAE which is formatted based on what
+XFRM_MSG_GETAE queried for.
+The response will always have XFRMA_LTIME_VAL and XFRMA_REPLAY_VAL TLVs.
+*if XFRM_AE_RTHR flag is set, then XFRMA_REPLAY_THRESH is also retrieved
+*if XFRM_AE_ETHR flag is set, then XFRMA_ETIMER_THRESH is also retrieved
+
+b) XFRM_MSG_NEWAE is issued by either user space to configure
+or kernel to announce events or respond to a XFRM_MSG_GETAE.
+
+i) user --> kernel to configure a specific SA.
+any of the values or threshold parameters can be updated by passing the
+appropriate TLV.
+A response is issued back to the sender in user space to indicate success
+or failure.
+In the case of success, additionally an event with
+XFRM_MSG_NEWAE is also issued to any listeners as described in iii).
+
+ii) kernel->user direction as a response to XFRM_MSG_GETAE
+The response will always have XFRMA_LTIME_VAL and XFRMA_REPLAY_VAL TLVs.
+The threshold TLVs will be included if explicitly requested in
+the XFRM_MSG_GETAE message.
+
+iii) kernel->user to report as event if someone sets any values or
+thresholds for an SA using XFRM_MSG_NEWAE (as described in #i above).
+In such a case XFRM_AE_CU flag is set to inform the user that
+the change happened as a result of an update.
+The message will always have XFRMA_LTIME_VAL and XFRMA_REPLAY_VAL TLVs.
+
+iv) kernel->user to report event when replay threshold or a timeout
+is exceeded.
+In such a case either XFRM_AE_CR (replay exceeded) or XFRM_AE_CE (timeout
+happened) is set to inform the user what happened.
+Note the two flags are mutually exclusive.
+The message will always have XFRMA_LTIME_VAL and XFRMA_REPLAY_VAL TLVs.
+
+Exceptions to threshold settings
+--------------------------------
+
+If you have an SA that is getting hit by traffic in bursts such that
+there is a period where the timer threshold expires with no packets
+seen, then an odd behavior is seen as follows:
+The first packet arrival after a timer expiry will trigger a timeout
+aevent; i.e we dont wait for a timeout period or a packet threshold
+to be reached. This is done for simplicity and efficiency reasons.
+
+-JHS
index 331afd791cbb474f774d10a008493459cce77886..ce767b90bb0dd288118fbee62df7176fcc9260fd 100644 (file)
@@ -19,9 +19,9 @@ TABLE OF CONTENTS
        [2-1-1] Overview
        [2-1-2] Flow of scmds through EH
        [2-1-3] Flow of control
-    [2-2] EH through hostt->eh_strategy_handler()
-       [2-2-1] Pre hostt->eh_strategy_handler() SCSI midlayer conditions
-       [2-2-2] Post hostt->eh_strategy_handler() SCSI midlayer conditions
+    [2-2] EH through transportt->eh_strategy_handler()
+       [2-2-1] Pre transportt->eh_strategy_handler() SCSI midlayer conditions
+       [2-2-2] Post transportt->eh_strategy_handler() SCSI midlayer conditions
        [2-2-3] Things to consider
 
 
@@ -413,9 +413,9 @@ scmd->allowed.
            layer of failure of the scmds.
 
 
-[2-2] EH through hostt->eh_strategy_handler()
+[2-2] EH through transportt->eh_strategy_handler()
 
hostt->eh_strategy_handler() is invoked in the place of
transportt->eh_strategy_handler() is invoked in the place of
 scsi_unjam_host() and it is responsible for whole recovery process.
 On completion, the handler should have made lower layers forget about
 all failed scmds and either ready for new commands or offline.  Also,
@@ -424,7 +424,7 @@ SCSI midlayer.  IOW, of the steps described in [2-1-2], all steps
 except for #1 must be implemented by eh_strategy_handler().
 
 
-[2-2-1] Pre hostt->eh_strategy_handler() SCSI midlayer conditions
+[2-2-1] Pre transportt->eh_strategy_handler() SCSI midlayer conditions
 
  The following conditions are true on entry to the handler.
 
@@ -437,7 +437,7 @@ except for #1 must be implemented by eh_strategy_handler().
  - shost->host_failed == shost->host_busy
 
 
-[2-2-2] Post hostt->eh_strategy_handler() SCSI midlayer conditions
+[2-2-2] Post transportt->eh_strategy_handler() SCSI midlayer conditions
 
  The following conditions must be true on exit from the handler.
 
index 8bbae3e1abdfa1c1a35f9c00f4b118cae9afdbf2..75a535a975c361986b40aa881cda3a49997455ae 100644 (file)
@@ -804,7 +804,6 @@ Summary:
    eh_bus_reset_handler - issue SCSI bus reset
    eh_device_reset_handler - issue SCSI device reset
    eh_host_reset_handler - reset host (host bus adapter)
-   eh_strategy_handler - driver supplied alternate to scsi_unjam_host()
    info - supply information about given host
    ioctl - driver can respond to ioctls
    proc_info - supports /proc/scsi/{driver_name}/{host_no}
@@ -969,24 +968,6 @@ Details:
      int eh_host_reset_handler(struct scsi_cmnd * scp)
 
 
-/**
- *      eh_strategy_handler - driver supplied alternate to scsi_unjam_host()
- *      @shp: host on which error has occurred
- *
- *      Returns TRUE if host unjammed, else FALSE.
- *
- *      Locks: none
- *
- *      Calling context: kernel thread
- *
- *      Notes: Invoked from scsi_eh thread. LLD supplied alternate to 
- *      scsi_unjam_host() found in scsi_error.c
- *
- *      Optionally defined in: LLD
- **/
-     int eh_strategy_handler(struct Scsi_Host * shp)
-
-
 /**
  *      info - supply information about given host: driver name plus data
  *             to distinguish given host
index 42ef9970bc86b1ad762a5928942f63085be0019d..df82116a9f261c35998c3bb5a69eb1a38c8d83d1 100644 (file)
@@ -3,14 +3,11 @@
                        --------------------
 
 
-   $Id: driver,v 1.10 2002/07/22 15:27:30 rmk Exp $
-
-
 This document is meant as a brief overview of some aspects of the new serial
 driver.  It is not complete, any questions you have should be directed to
 <rmk@arm.linux.org.uk>
 
-The reference implementation is contained within serial_amba.c.
+The reference implementation is contained within amba_pl011.c.
 
 
 
@@ -31,6 +28,11 @@ The serial core provides a few helper functions.  This includes identifing
 the correct port structure (via uart_get_console) and decoding command line
 arguments (uart_parse_options).
 
+There is also a helper function (uart_write_console) which performs a
+character by character write, translating newlines to CRLF sequences.
+Driver writers are recommended to use this function rather than implementing
+their own version.
+
 
 Locking
 -------
@@ -86,6 +88,7 @@ hardware.
                - TIOCM_DTR     DTR signal.
                - TIOCM_OUT1    OUT1 signal.
                - TIOCM_OUT2    OUT2 signal.
+               - TIOCM_LOOP    Set the port into loopback mode.
        If the appropriate bit is set, the signal should be driven
        active.  If the bit is clear, the signal should be driven
        inactive.
@@ -141,6 +144,10 @@ hardware.
   enable_ms(port)
        Enable the modem status interrupts.
 
+       This method may be called multiple times.  Modem status
+       interrupts should be disabled when the shutdown method is
+       called.
+
        Locking: port->lock taken.
        Interrupts: locally disabled.
        This call must not sleep
@@ -160,6 +167,8 @@ hardware.
        state.  Enable the port for reception.  It should not activate
        RTS nor DTR; this will be done via a separate call to set_mctrl.
 
+       This method will only be called when the port is initially opened.
+
        Locking: port_sem taken.
        Interrupts: globally disabled.
 
@@ -169,6 +178,11 @@ hardware.
        RTS nor DTR; this will have already been done via a separate
        call to set_mctrl.
 
+       Drivers must not access port->info once this call has completed.
+
+       This method will only be called when there are no more users of
+       this port.
+
        Locking: port_sem taken.
        Interrupts: caller dependent.
 
index 6feef9e82b63f832a26272d4909a575fcdc3cd03..68eeebc17ff43508a8fbae95f2432258eb6ebfc7 100644 (file)
           if ((err = pci_enable_device(pci)) < 0)
                   return err;
           /* check PCI availability (28bit DMA) */
-          if (pci_set_dma_mask(pci, 0x0fffffff) < 0 ||
-              pci_set_consistent_dma_mask(pci, 0x0fffffff) < 0) {
+          if (pci_set_dma_mask(pci, DMA_28BIT_MASK) < 0 ||
+              pci_set_consistent_dma_mask(pci, DMA_28BIT_MASK) < 0) {
                   printk(KERN_ERR "error to set 28bit mask DMA\n");
                   pci_disable_device(pci);
                   return -ENXIO;
         The allocation of PCI resources is done in the
       <function>probe()</function> function, and usually an extra
       <function>xxx_create()</function> function is written for this
-      purpose. 
+      purpose.
       </para>
 
       <para>
       allocating resources. Also, you need to set the proper PCI DMA
       mask to limit the accessed i/o range. In some cases, you might
       need to call <function>pci_set_master()</function> function,
-      too. 
+      too.
       </para>
 
       <para>
 <![CDATA[
   if ((err = pci_enable_device(pci)) < 0)
           return err;
-  if (pci_set_dma_mask(pci, 0x0fffffff) < 0 ||
-      pci_set_consistent_dma_mask(pci, 0x0fffffff) < 0) {
+  if (pci_set_dma_mask(pci, DMA_28BIT_MASK) < 0 ||
+      pci_set_consistent_dma_mask(pci, DMA_28BIT_MASK) < 0) {
           printk(KERN_ERR "error to set 28bit mask DMA\n");
           pci_disable_device(pci);
           return -ENXIO;
       functions. Unlike ALSA ver.0.5.x., there are no helpers for
       that. And these resources must be released in the destructor
       function (see below). Also, on ALSA 0.9.x, you don't need to
-      allocate (pseudo-)DMA for PCI like ALSA 0.5.x. 
+      allocate (pseudo-)DMA for PCI like ALSA 0.5.x.
       </para>
 
       <para>
         Now assume that this PCI device has an I/O port with 8 bytes
         and an interrupt. Then struct <structname>mychip</structname> will have the
-        following fields: 
+        following fields:
 
         <informalexample>
           <programlisting>
index 1ad9af1ca4d0b1f2c58b49009c139a69c6124f2d..687104bfd09a79eef794b8dbe1357c33864d028c 100644 (file)
@@ -27,12 +27,21 @@ number of free hugetlb pages at any time.  It also displays information about
 the configured hugepage size - this is needed for generating the proper
 alignment and size of the arguments to the above system calls.
 
-The output of "cat /proc/meminfo" will have output like:
+The output of "cat /proc/meminfo" will have lines like:
 
 .....
 HugePages_Total: xxx
 HugePages_Free:  yyy
-Hugepagesize:    zzz KB
+HugePages_Rsvd:  www
+Hugepagesize:    zzz kB
+
+where:
+HugePages_Total is the size of the pool of hugepages.
+HugePages_Free is the number of hugepages in the pool that are not yet
+allocated.
+HugePages_Rsvd is short for "reserved," and is the number of hugepages
+for which a commitment to allocate from the pool has been made, but no
+allocation has yet been made. It's vaguely analogous to overcommit.
 
 /proc/filesystems should also show a filesystem of type "hugetlbfs" configured
 in the kernel.
@@ -42,11 +51,11 @@ pages in the kernel.  Super user can dynamically request more (or free some
 pre-configured) hugepages.
 The allocation (or deallocation) of hugetlb pages is possible only if there are
 enough physically contiguous free pages in system (freeing of hugepages is
-possible only if there are enough hugetlb pages free that can be transfered
+possible only if there are enough hugetlb pages free that can be transferred
 back to regular memory pool).
 
-Pages that are used as hugetlb pages are reserved inside the kernel and can
-not be used for other purposes.
+Pages that are used as hugetlb pages are reserved inside the kernel and cannot
+be used for other purposes.
 
 Once the kernel with Hugetlb page support is built and running, a user can
 use either the mmap system call or shared memory system calls to start using
@@ -60,7 +69,7 @@ Use the following command to dynamically allocate/deallocate hugepages:
 This command will try to configure 20 hugepages in the system.  The success
 or failure of allocation depends on the amount of physically contiguous
 memory that is preset in system at this time.  System administrators may want
-to put this command in one of the local rc init file.  This will enable the
+to put this command in one of the local rc init files.  This will enable the
 kernel to request huge pages early in the boot process (when the possibility
 of getting physical contiguous pages is still very high).
 
@@ -78,8 +87,8 @@ the uid and gid of the current process are taken.  The mode option sets the
 mode of root of file system to value & 0777.  This value is given in octal.
 By default the value 0755 is picked. The size option sets the maximum value of
 memory (huge pages) allowed for that filesystem (/mnt/huge). The size is
-rounded down to HPAGE_SIZE.  The option nr_inode sets the maximum number of
-inodes that /mnt/huge can use.  If the size or nr_inode options are not
+rounded down to HPAGE_SIZE.  The option nr_inodes sets the maximum number of
+inodes that /mnt/huge can use.  If the size or nr_inodes options are not
 provided on command line then no limits are set.  For size and nr_inodes
 options, you can use [G|g]/[M|m]/[K|k] to represent giga/mega/kilo. For
 example, size=2K has the same meaning as size=2048. An example is given at
@@ -88,7 +97,7 @@ the end of this document.
 read and write system calls are not supported on files that reside on hugetlb
 file systems.
 
-A regular chown, chgrp and chmod commands (with right permissions) could be
+Regular chown, chgrp, and chmod commands (with right permissions) could be
 used to change the file attributes on hugetlbfs.
 
 Also, it is important to note that no such mount command is required if the
@@ -96,8 +105,8 @@ applications are going to use only shmat/shmget system calls.  Users who
 wish to use hugetlb page via shared memory segment should be a member of
 a supplementary group and system admin needs to configure that gid into
 /proc/sys/vm/hugetlb_shm_group.  It is possible for same or different
-applications to use any combination of mmaps and shm* calls.  Though the
-mount of filesystem will be required for using mmaps.
+applications to use any combination of mmaps and shm* calls, though the
+mount of filesystem will be required for using mmap calls.
 
 *******************************************************************
 
index 1921353259aeeca2ab07f4ced32a8cd0f3edc559..f2cd6ef53ff33e92f6545a43a7f2498c0582b107 100644 (file)
@@ -151,6 +151,11 @@ NUMA
 
   numa=fake=X   Fake X nodes and ignore NUMA setup of the actual machine.
 
+  numa=hotadd=percent
+               Only allow hotadd memory to preallocate page structures upto
+               percent of already available memory.
+               numa=hotadd=0 will disable hotadd memory.
+
 ACPI
 
   acpi=off     Don't enable ACPI
diff --git a/Kbuild b/Kbuild
index 95d6a00bace08c0ac50b80356847d5f19f6dc55a..2d4f95e4b89f7f81da6cb94b07e8449b3689ba37 100644 (file)
--- a/Kbuild
+++ b/Kbuild
@@ -18,7 +18,7 @@ define sed-y
        "/^->/{s:^->\([^ ]*\) [\$$#]*\([^ ]*\) \(.*\):#define \1 \2 /* \3 */:; s:->::; p;}"
 endef
 # Override default regexp for specific architectures
-sed-$(CONFIG_MIPS) := "/^@@@/s///p"
+sed-$(CONFIG_MIPS) := "/^@@@/{s/^@@@//; s/ \#.*\$$//; p;}"
 
 quiet_cmd_offsets = GEN     $@
 define cmd_offsets
index f97657b7e2c712e54ab7d67f0ab671e6118b706d..61060e82fb0eb0f28b5c496f045e7b2b7845f6b1 100644 (file)
@@ -411,6 +411,7 @@ AX.25 NETWORK LAYER
 P:     Ralf Baechle
 M:     ralf@linux-mips.org
 L:     linux-hams@vger.kernel.org
+W:     http://www.linux-ax25.org/
 S:     Maintained
 
 BAYCOM/HDLCDRV DRIVERS FOR AX.25
@@ -1457,6 +1458,13 @@ M:       support@pathscale.com
 L:     openib-general@openib.org
 S:     Supported
 
+IPMI SUBSYSTEM
+P:     Corey Minyard
+M:     minyard@acm.org
+L:     openipmi-developer@lists.sourceforge.net
+W:     http://openipmi.sourceforge.net/
+S:     Supported
+
 IPX NETWORK LAYER
 P:     Arnaldo Carvalho de Melo
 M:     acme@conectiva.com.br
@@ -1556,9 +1564,7 @@ S:        Maintained
 
 KEXEC
 P:     Eric Biederman
-P:     Randy Dunlap
 M:     ebiederm@xmission.com
-M:     rdunlap@xenotime.net
 W:     http://www.xmission.com/~ebiederm/files/kexec/
 L:     linux-kernel@vger.kernel.org
 L:     fastboot@osdl.org
@@ -1871,6 +1877,7 @@ NETROM NETWORK LAYER
 P:     Ralf Baechle
 M:     ralf@linux-mips.org
 L:     linux-hams@vger.kernel.org
+W:     http://www.linux-ax25.org/
 S:     Maintained
 
 NETWORK BLOCK DEVICE
@@ -2262,6 +2269,7 @@ ROSE NETWORK LAYER
 P:     Ralf Baechle
 M:     ralf@linux-mips.org
 L:     linux-hams@vger.kernel.org
+W:     http://www.linux-ax25.org/
 S:     Maintained
 
 RISCOM8 DRIVER
@@ -3060,13 +3068,6 @@ M:       khali@linux-fr.org
 L:     lm-sensors@lm-sensors.org
 S:     Odd Fixes
 
-WAN ROUTER & SANGOMA WANPIPE DRIVERS & API (X.25, FRAME RELAY, PPP, CISCO HDLC)
-P:     Nenad Corbic
-M:     ncorbic@sangoma.com
-M:     dm@sangoma.com
-W:     http://www.sangoma.com
-S:     Supported
-
 WATCHDOG DEVICE DRIVERS
 P:     Wim Van Sebroeck
 M:     wim@iguana.be
index b4019426fa25bfc46db5624d185c33abe8ec3498..a940eaefe1c4d7859a8a2aa6b5baa7808704a1c1 100644 (file)
--- a/Makefile
+++ b/Makefile
@@ -1,7 +1,7 @@
 VERSION = 2
 PATCHLEVEL = 6
 SUBLEVEL = 17
-EXTRAVERSION =-rc1
+EXTRAVERSION =-rc2
 NAME=Sliding Snow Leopard
 
 # *DOCUMENTATION*
@@ -1112,7 +1112,6 @@ modules_install: _emodinst_ _emodinst_post
 install-dir := $(if $(INSTALL_MOD_DIR),$(INSTALL_MOD_DIR),extra)
 PHONY += _emodinst_
 _emodinst_:
-       $(Q)rm -rf $(MODLIB)/$(install-dir)
        $(Q)mkdir -p $(MODLIB)/$(install-dir)
        $(Q)$(MAKE) -rR -f $(srctree)/scripts/Makefile.modinst
 
@@ -1275,40 +1274,43 @@ kernelversion:
 
 # Single targets
 # ---------------------------------------------------------------------------
-# The directory part is taken from first prerequisite, so this
-# works even with external modules
+# Single targets are compatible with:
+# - build whith mixed source and output
+# - build with separate output dir 'make O=...'
+# - external modules
+#
+#  target-dir => where to store outputfile
+#  build-dir  => directory in kernel source tree to use
+
+ifeq ($(KBUILD_EXTMOD),)
+        build-dir  = $(patsubst %/,%,$(dir $@))
+        target-dir = $(dir $@)
+else
+        zap-slash=$(filter-out .,$(patsubst %/,%,$(dir $@)))
+        build-dir  = $(KBUILD_EXTMOD)$(if $(zap-slash),/$(zap-slash))
+        target-dir = $(if $(KBUILD_EXTMOD),$(dir $<),$(dir $@))
+endif
+
 %.s: %.c prepare scripts FORCE
-       $(Q)$(MAKE) $(build)=$(dir $<) $(dir $<)$(notdir $@)
+       $(Q)$(MAKE) $(build)=$(build-dir) $(target-dir)$(notdir $@)
 %.i: %.c prepare scripts FORCE
-       $(Q)$(MAKE) $(build)=$(dir $<) $(dir $<)$(notdir $@)
+       $(Q)$(MAKE) $(build)=$(build-dir) $(target-dir)$(notdir $@)
 %.o: %.c prepare scripts FORCE
-       $(Q)$(MAKE) $(build)=$(dir $<) $(dir $<)$(notdir $@)
+       $(Q)$(MAKE) $(build)=$(build-dir) $(target-dir)$(notdir $@)
 %.lst: %.c prepare scripts FORCE
-       $(Q)$(MAKE) $(build)=$(dir $<) $(dir $<)$(notdir $@)
+       $(Q)$(MAKE) $(build)=$(build-dir) $(target-dir)$(notdir $@)
 %.s: %.S prepare scripts FORCE
-       $(Q)$(MAKE) $(build)=$(dir $<) $(dir $<)$(notdir $@)
+       $(Q)$(MAKE) $(build)=$(build-dir) $(target-dir)$(notdir $@)
 %.o: %.S prepare scripts FORCE
-       $(Q)$(MAKE) $(build)=$(dir $<) $(dir $<)$(notdir $@)
-
-# For external modules we shall include any directory of the target,
-# but usual case there is no directory part.
-# make M=`pwd` module.o     => $(dir $@)=./
-# make M=`pwd` foo/module.o => $(dir $@)=foo/
-# make M=`pwd` /            => $(dir $@)=/
-ifeq ($(KBUILD_EXTMOD),)
-        target-dir = $(@D)
-else
-        zap-slash=$(filter-out .,$(patsubst %/,%,$(dir $@)))
-        target-dir = $(KBUILD_EXTMOD)$(if $(zap-slash),/$(zap-slash))
-endif
+       $(Q)$(MAKE) $(build)=$(build-dir) $(target-dir)$(notdir $@)
 
-/ %/:      scripts prepare FORCE
+# Modules
+/ %/: prepare scripts FORCE
        $(Q)$(MAKE) KBUILD_MODULES=$(if $(CONFIG_MODULES),1) \
-       $(build)=$(target-dir)
-%.ko: scripts FORCE
+       $(build)=$(build-dir)
+%.ko: prepare scripts FORCE
        $(Q)$(MAKE) KBUILD_MODULES=$(if $(CONFIG_MODULES),1)   \
-       $(build)=$(target-dir) $(@:.ko=.o)
+       $(build)=$(build-dir) $(@:.ko=.o)
        $(Q)$(MAKE) -rR -f $(srctree)/scripts/Makefile.modpost
 
 # FIXME Should go into a make.lib or something 
diff --git a/README b/README
index 05e055530bbb687599dd732d6753c77ffa281ae5..3e264723b863add275e6f32c44762f8d09cfe0a0 100644 (file)
--- a/README
+++ b/README
@@ -165,10 +165,31 @@ CONFIGURING the kernel:
        "make xconfig"     X windows (Qt) based configuration tool.
        "make gconfig"     X windows (Gtk) based configuration tool.
        "make oldconfig"   Default all questions based on the contents of
-                          your existing ./.config file.
+                          your existing ./.config file and asking about
+                          new config symbols.
        "make silentoldconfig"
                           Like above, but avoids cluttering the screen
                           with questions already answered.
+       "make defconfig"   Create a ./.config file by using the default
+                          symbol values from arch/$ARCH/defconfig.
+       "make allyesconfig"
+                          Create a ./.config file by setting symbol
+                          values to 'y' as much as possible.
+       "make allmodconfig"
+                          Create a ./.config file by setting symbol
+                          values to 'm' as much as possible.
+       "make allnoconfig" Create a ./.config file by setting symbol
+                          values to 'n' as much as possible.
+       "make randconfig"  Create a ./.config file by setting symbol
+                          values to random values.
+
+   The allyesconfig/allmodconfig/allnoconfig/randconfig variants can
+   also use the environment variable KCONFIG_ALLCONFIG to specify a
+   filename that contains config options that the user requires to be
+   set to a specific value.  If KCONFIG_ALLCONFIG=filename is not used,
+   "make *config" checks for a file named "all{yes/mod/no/random}.config"
+   for symbol values that are to be forced.  If this file is not found,
+   it checks for a file named "all.config" to contain forced values.
    
        NOTES on "make config":
        - having unnecessary drivers will make the kernel bigger, and can
index 9bef61b303674e3be48a0fbb403ee7d85c126e30..8290b69da20214a7e19fedd0fc047d33d5d82ba7 100644 (file)
@@ -549,6 +549,11 @@ config NUMA
          Access).  This option is for configuring high-end multiprocessor
          server machines.  If in doubt, say N.
 
+config NODES_SHIFT
+       int
+       default "7"
+       depends on NEED_MULTIPLE_NODES
+
 # LARGE_VMALLOC is racy, if you *really* need it then fix it first
 config ALPHA_LARGE_VMALLOC
        bool
index 9d6186d50245c24624229ebd5ccb753ede91f8b3..c645c5e14786fdd17efddf40bb3ae2b40524ffd8 100644 (file)
@@ -76,7 +76,6 @@ EXPORT_SYMBOL(strncpy);
 EXPORT_SYMBOL(strnlen);
 EXPORT_SYMBOL(strncat);
 EXPORT_SYMBOL(strstr);
-EXPORT_SYMBOL(strpbrk);
 EXPORT_SYMBOL(strchr);
 EXPORT_SYMBOL(strrchr);
 EXPORT_SYMBOL(memcmp);
index a15e18a00258ee69d65329945c174e0ec0e3f66c..558b83368559396f4d50f793d37d8e7dd83c26d1 100644 (file)
@@ -24,6 +24,7 @@
 #include <linux/config.h>      /* CONFIG_ALPHA_LCA etc */
 #include <linux/mc146818rtc.h>
 #include <linux/console.h>
+#include <linux/cpu.h>
 #include <linux/errno.h>
 #include <linux/init.h>
 #include <linux/string.h>
@@ -471,6 +472,22 @@ page_is_ram(unsigned long pfn)
        return 0;
 }
 
+static int __init
+register_cpus(void)
+{
+       int i;
+
+       for_each_possible_cpu(i) {
+               struct cpu *p = kzalloc(sizeof(*p), GFP_KERNEL);
+               if (!p)
+                       return -ENOMEM;
+               register_cpu(p, i, NULL);
+       }
+       return 0;
+}
+
+arch_initcall(register_cpus);
+
 void __init
 setup_arch(char **cmdline_p)
 {
index 02c2db08114ad66e42876d5e1f2b80c402ec9a84..185255416e8538c22384ae89491720834aa6fcc1 100644 (file)
@@ -439,7 +439,7 @@ setup_smp(void)
                        if ((cpu->flags & 0x1cc) == 0x1cc) {
                                smp_num_probed++;
                                /* Assume here that "whami" == index */
-                               cpu_set(i, cpu_possible_map);
+                               cpu_set(i, cpu_present_mask);
                                cpu->pal_revision = boot_cpu_palrev;
                        }
 
@@ -450,9 +450,8 @@ setup_smp(void)
                }
        } else {
                smp_num_probed = 1;
-               cpu_set(boot_cpuid, cpu_possible_map);
+               cpu_set(boot_cpuid, cpu_present_mask);
        }
-       cpu_present_mask = cpumask_of_cpu(boot_cpuid);
 
        printk(KERN_INFO "SMP: %d CPUs probed -- cpu_present_mask = %lx\n",
               smp_num_probed, cpu_possible_map.bits[0]);
@@ -488,9 +487,8 @@ void __devinit
 smp_prepare_boot_cpu(void)
 {
        /*
-        * Mark the boot cpu (current cpu) as both present and online
+        * Mark the boot cpu (current cpu) as online
         */ 
-       cpu_set(smp_processor_id(), cpu_present_mask);
        cpu_set(smp_processor_id(), cpu_online_map);
 }
 
index dc5a9332c91597f7cbc82d06db7be40138f7d551..1dbf6ddb300d2b5a9cfafd9e064dffee468dec52 100644 (file)
@@ -512,6 +512,12 @@ config ARCH_DISCONTIGMEM_ENABLE
          or have huge holes in the physical address space for other reasons.
          See <file:Documentation/vm/numa> for more.
 
+config NODES_SHIFT
+       int
+       default "4" if ARCH_LH7A40X
+       default "2"
+       depends on NEED_MULTIPLE_NODES
+
 source "mm/Kconfig"
 
 config LEDS
index eed616113e473f76dbf99deb3a6ebd7cdab123b8..153a07e7222bd4a4d8ede7d5b9bc7b0a9f31566d 100644 (file)
@@ -18,6 +18,7 @@ SECTIONS
     _start = .;
     *(.start)
     *(.text)
+    *(.text.*)
     *(.fixup)
     *(.gnu.warning)
     *(.rodata)
index 5e830f444c6c6b9d8148b7cd34a505f30bdbf294..314ebd3a1d718c60f2d7f16f2f8a5dcb98239681 100644 (file)
 #include <asm/io.h>
 #include <asm/hardware/scoop.h>
 
+/* PCMCIA to Scoop linkage
+
+   There is no easy way to link multiple scoop devices into one
+   single entity for the pxa2xx_pcmcia device so this structure
+   is used which is setup by the platform code.
+
+   This file is never modular so this symbol is always
+   accessile to the board support files.
+*/
+struct scoop_pcmcia_config *platform_scoop_config;
+EXPORT_SYMBOL(platform_scoop_config);
+
 #define SCOOP_REG(d,adr) (*(volatile unsigned short*)(d +(adr)))
 
 struct  scoop_dev {
index 8dcc8e8ec81314a662a5a60fd5fd028ce11829df..b69e88bbc909d906df7730eecf9b8e897e691fc0 100644 (file)
@@ -1,12 +1,14 @@
 #
 # Automatically generated make config: don't edit
-# Linux kernel version: 2.6.16
-# Mon Mar 20 14:54:51 2006
+# Linux kernel version: 2.6.17-rc2
+# Wed Apr 19 21:21:01 2006
 #
 CONFIG_ARM=y
 CONFIG_MMU=y
 CONFIG_RWSEM_GENERIC_SPINLOCK=y
+CONFIG_GENERIC_HWEIGHT=y
 CONFIG_GENERIC_CALIBRATE_DELAY=y
+CONFIG_VECTORS_BASE=0xffff0000
 
 #
 # Code maturity level options
@@ -28,6 +30,7 @@ CONFIG_SYSCTL=y
 # CONFIG_AUDIT is not set
 CONFIG_IKCONFIG=y
 CONFIG_IKCONFIG_PROC=y
+# CONFIG_RELAY is not set
 CONFIG_INITRAMFS_SOURCE=""
 CONFIG_UID16=y
 CONFIG_CC_OPTIMIZE_FOR_SIZE=y
@@ -43,10 +46,6 @@ CONFIG_BASE_FULL=y
 CONFIG_FUTEX=y
 CONFIG_EPOLL=y
 CONFIG_SHMEM=y
-CONFIG_CC_ALIGN_FUNCTIONS=0
-CONFIG_CC_ALIGN_LABELS=0
-CONFIG_CC_ALIGN_LOOPS=0
-CONFIG_CC_ALIGN_JUMPS=0
 CONFIG_SLAB=y
 # CONFIG_TINY_SHMEM is not set
 CONFIG_BASE_SMALL=0
@@ -59,7 +58,6 @@ CONFIG_OBSOLETE_INTERMODULE=y
 CONFIG_MODULES=y
 CONFIG_MODULE_UNLOAD=y
 CONFIG_MODULE_FORCE_UNLOAD=y
-CONFIG_OBSOLETE_MODPARM=y
 # CONFIG_MODVERSIONS is not set
 # CONFIG_MODULE_SRCVERSION_ALL is not set
 CONFIG_KMOD=y
@@ -67,6 +65,7 @@ CONFIG_KMOD=y
 #
 # Block layer
 #
+# CONFIG_BLK_DEV_IO_TRACE is not set
 
 #
 # IO Schedulers
@@ -94,6 +93,7 @@ CONFIG_ARCH_EP93XX=y
 # CONFIG_ARCH_IOP3XX is not set
 # CONFIG_ARCH_IXP4XX is not set
 # CONFIG_ARCH_IXP2000 is not set
+# CONFIG_ARCH_IXP23XX is not set
 # CONFIG_ARCH_L7200 is not set
 # CONFIG_ARCH_PXA is not set
 # CONFIG_ARCH_RPC is not set
@@ -112,7 +112,6 @@ CONFIG_ARCH_EP93XX=y
 #
 # Cirrus EP93xx Implementation Options
 #
-CONFIG_CRUNCH=y
 
 #
 # EP93xx Platforms
@@ -232,12 +231,15 @@ CONFIG_SYN_COOKIES=y
 # CONFIG_INET_AH is not set
 # CONFIG_INET_ESP is not set
 # CONFIG_INET_IPCOMP is not set
+# CONFIG_INET_XFRM_TUNNEL is not set
 # CONFIG_INET_TUNNEL is not set
 CONFIG_INET_DIAG=y
 CONFIG_INET_TCP_DIAG=y
 # CONFIG_TCP_CONG_ADVANCED is not set
 CONFIG_TCP_CONG_BIC=y
 # CONFIG_IPV6 is not set
+# CONFIG_INET6_XFRM_TUNNEL is not set
+# CONFIG_INET6_TUNNEL is not set
 # CONFIG_NETFILTER is not set
 
 #
@@ -346,7 +348,6 @@ CONFIG_MTD_CFI_I2=y
 # CONFIG_MTD_OTP is not set
 CONFIG_MTD_CFI_INTELEXT=y
 CONFIG_MTD_CFI_AMDSTD=y
-CONFIG_MTD_CFI_AMDSTD_RETRY=0
 CONFIG_MTD_CFI_STAA=y
 CONFIG_MTD_CFI_UTIL=y
 # CONFIG_MTD_RAM is not set
@@ -371,7 +372,6 @@ CONFIG_MTD_PHYSMAP_BANKWIDTH=1
 # CONFIG_MTD_SLRAM is not set
 # CONFIG_MTD_PHRAM is not set
 # CONFIG_MTD_MTDRAM is not set
-# CONFIG_MTD_BLKMTD is not set
 # CONFIG_MTD_BLOCK2MTD is not set
 
 #
@@ -412,7 +412,7 @@ CONFIG_MTD_NAND_IDS=y
 # CONFIG_BLK_DEV_NBD is not set
 # CONFIG_BLK_DEV_UB is not set
 # CONFIG_BLK_DEV_RAM is not set
-CONFIG_BLK_DEV_RAM_COUNT=16
+# CONFIG_BLK_DEV_INITRD is not set
 # CONFIG_CDROM_PKTCDVD is not set
 # CONFIG_ATA_OVER_ETH is not set
 
@@ -576,13 +576,13 @@ CONFIG_WATCHDOG=y
 # Watchdog Device Drivers
 #
 # CONFIG_SOFT_WATCHDOG is not set
+CONFIG_EP93XX_WATCHDOG=y
 
 #
 # USB-based Watchdog Cards
 #
 # CONFIG_USBPCWATCHDOG is not set
 # CONFIG_NVRAM is not set
-# CONFIG_RTC is not set
 # CONFIG_DTLK is not set
 # CONFIG_R3964 is not set
 
@@ -626,9 +626,7 @@ CONFIG_I2C_ALGOBIT=y
 # CONFIG_SENSORS_PCF8574 is not set
 # CONFIG_SENSORS_PCA9539 is not set
 # CONFIG_SENSORS_PCF8591 is not set
-# CONFIG_SENSORS_RTC8564 is not set
 # CONFIG_SENSORS_MAX6875 is not set
-# CONFIG_RTC_X1205_I2C is not set
 CONFIG_I2C_DEBUG_CORE=y
 CONFIG_I2C_DEBUG_ALGO=y
 CONFIG_I2C_DEBUG_BUS=y
@@ -690,7 +688,16 @@ CONFIG_HWMON=y
 #
 
 #
-# Multimedia Capabilities Port drivers
+# LED devices
+#
+# CONFIG_NEW_LEDS is not set
+
+#
+# LED drivers
+#
+
+#
+# LED Triggers
 #
 
 #
@@ -702,6 +709,7 @@ CONFIG_HWMON=y
 # Digital Video Broadcasting Devices
 #
 # CONFIG_DVB is not set
+# CONFIG_USB_DABUSB is not set
 
 #
 # Graphics support
@@ -718,6 +726,7 @@ CONFIG_HWMON=y
 #
 CONFIG_USB_ARCH_HAS_HCD=y
 # CONFIG_USB_ARCH_HAS_OHCI is not set
+# CONFIG_USB_ARCH_HAS_EHCI is not set
 CONFIG_USB=y
 CONFIG_USB_DEBUG=y
 
@@ -775,15 +784,6 @@ CONFIG_USB_STORAGE=y
 # CONFIG_USB_MDC800 is not set
 # CONFIG_USB_MICROTEK is not set
 
-#
-# USB Multimedia devices
-#
-# CONFIG_USB_DABUSB is not set
-
-#
-# Video4Linux support is needed for USB Multimedia device support
-#
-
 #
 # USB Network Adapters
 #
@@ -813,6 +813,7 @@ CONFIG_USB_SERIAL_CONSOLE=y
 # CONFIG_USB_SERIAL_CYPRESS_M8 is not set
 # CONFIG_USB_SERIAL_EMPEG is not set
 # CONFIG_USB_SERIAL_FTDI_SIO is not set
+# CONFIG_USB_SERIAL_FUNSOFT is not set
 # CONFIG_USB_SERIAL_VISOR is not set
 # CONFIG_USB_SERIAL_IPAQ is not set
 # CONFIG_USB_SERIAL_IR is not set
@@ -825,6 +826,7 @@ CONFIG_USB_SERIAL_CONSOLE=y
 # CONFIG_USB_SERIAL_KLSI is not set
 # CONFIG_USB_SERIAL_KOBIL_SCT is not set
 # CONFIG_USB_SERIAL_MCT_U232 is not set
+# CONFIG_USB_SERIAL_NAVMAN is not set
 CONFIG_USB_SERIAL_PL2303=y
 # CONFIG_USB_SERIAL_HP4X is not set
 # CONFIG_USB_SERIAL_SAFE is not set
@@ -864,6 +866,32 @@ CONFIG_USB_SERIAL_PL2303=y
 #
 # CONFIG_MMC is not set
 
+#
+# Real Time Clock
+#
+CONFIG_RTC_LIB=y
+CONFIG_RTC_CLASS=y
+CONFIG_RTC_HCTOSYS=y
+CONFIG_RTC_HCTOSYS_DEVICE="rtc0"
+
+#
+# RTC interfaces
+#
+CONFIG_RTC_INTF_SYSFS=y
+CONFIG_RTC_INTF_PROC=y
+CONFIG_RTC_INTF_DEV=y
+
+#
+# RTC drivers
+#
+# CONFIG_RTC_DRV_X1205 is not set
+# CONFIG_RTC_DRV_DS1672 is not set
+# CONFIG_RTC_DRV_PCF8563 is not set
+# CONFIG_RTC_DRV_RS5C372 is not set
+CONFIG_RTC_DRV_M48T86=y
+CONFIG_RTC_DRV_EP93XX=y
+# CONFIG_RTC_DRV_TEST is not set
+
 #
 # File systems
 #
@@ -912,7 +940,6 @@ CONFIG_SYSFS=y
 CONFIG_TMPFS=y
 # CONFIG_HUGETLB_PAGE is not set
 CONFIG_RAMFS=y
-# CONFIG_RELAYFS_FS is not set
 # CONFIG_CONFIGFS_FS is not set
 
 #
@@ -1044,6 +1071,7 @@ CONFIG_LOG_BUF_SHIFT=14
 CONFIG_DETECT_SOFTLOCKUP=y
 # CONFIG_SCHEDSTATS is not set
 CONFIG_DEBUG_SLAB=y
+# CONFIG_DEBUG_SLAB_LEAK is not set
 CONFIG_DEBUG_MUTEXES=y
 CONFIG_DEBUG_SPINLOCK=y
 # CONFIG_DEBUG_SPINLOCK_SLEEP is not set
@@ -1053,6 +1081,7 @@ CONFIG_DEBUG_BUGVERBOSE=y
 # CONFIG_DEBUG_FS is not set
 # CONFIG_DEBUG_VM is not set
 CONFIG_FRAME_POINTER=y
+# CONFIG_UNWIND_INFO is not set
 CONFIG_FORCED_INLINING=y
 # CONFIG_RCU_TORTURE_TEST is not set
 CONFIG_DEBUG_USER=y
index 7b02ca04c3eebb681c5ef027fc5c93d3f085d599..e6f3e4873d6cb967342e41afec4883b1b63341d8 100644 (file)
@@ -1,18 +1,19 @@
 #
 # Automatically generated make config: don't edit
-# Linux kernel version: 2.6.16-rc2
-# Wed Feb  8 04:49:11 2006
+# Linux kernel version: 2.6.17-rc2
+# Wed Apr 19 21:12:49 2006
 #
 CONFIG_ARM=y
 CONFIG_MMU=y
 CONFIG_RWSEM_GENERIC_SPINLOCK=y
+CONFIG_GENERIC_HWEIGHT=y
 CONFIG_GENERIC_CALIBRATE_DELAY=y
+CONFIG_VECTORS_BASE=0xffff0000
 
 #
 # Code maturity level options
 #
 CONFIG_EXPERIMENTAL=y
-CONFIG_CLEAN_COMPILE=y
 CONFIG_BROKEN_ON_SMP=y
 CONFIG_INIT_ENV_ARG_LIMIT=32
 
@@ -29,6 +30,7 @@ CONFIG_BSD_PROCESS_ACCT=y
 CONFIG_SYSCTL=y
 # CONFIG_AUDIT is not set
 # CONFIG_IKCONFIG is not set
+# CONFIG_RELAY is not set
 CONFIG_INITRAMFS_SOURCE=""
 CONFIG_UID16=y
 CONFIG_CC_OPTIMIZE_FOR_SIZE=y
@@ -44,10 +46,6 @@ CONFIG_BASE_FULL=y
 CONFIG_FUTEX=y
 CONFIG_EPOLL=y
 CONFIG_SHMEM=y
-CONFIG_CC_ALIGN_FUNCTIONS=0
-CONFIG_CC_ALIGN_LABELS=0
-CONFIG_CC_ALIGN_LOOPS=0
-CONFIG_CC_ALIGN_JUMPS=0
 CONFIG_SLAB=y
 # CONFIG_TINY_SHMEM is not set
 CONFIG_BASE_SMALL=0
@@ -60,7 +58,6 @@ CONFIG_OBSOLETE_INTERMODULE=y
 CONFIG_MODULES=y
 CONFIG_MODULE_UNLOAD=y
 # CONFIG_MODULE_FORCE_UNLOAD is not set
-CONFIG_OBSOLETE_MODPARM=y
 # CONFIG_MODVERSIONS is not set
 # CONFIG_MODULE_SRCVERSION_ALL is not set
 CONFIG_KMOD=y
@@ -68,6 +65,7 @@ CONFIG_KMOD=y
 #
 # Block layer
 #
+# CONFIG_BLK_DEV_IO_TRACE is not set
 
 #
 # IO Schedulers
@@ -89,11 +87,13 @@ CONFIG_DEFAULT_IOSCHED="anticipatory"
 # CONFIG_ARCH_CLPS711X is not set
 # CONFIG_ARCH_CO285 is not set
 # CONFIG_ARCH_EBSA110 is not set
+# CONFIG_ARCH_EP93XX is not set
 # CONFIG_ARCH_FOOTBRIDGE is not set
 # CONFIG_ARCH_INTEGRATOR is not set
 # CONFIG_ARCH_IOP3XX is not set
 # CONFIG_ARCH_IXP4XX is not set
 CONFIG_ARCH_IXP2000=y
+# CONFIG_ARCH_IXP23XX is not set
 # CONFIG_ARCH_L7200 is not set
 # CONFIG_ARCH_PXA is not set
 # CONFIG_ARCH_RPC is not set
@@ -123,6 +123,7 @@ CONFIG_ARCH_IXDP2800=y
 CONFIG_ARCH_IXDP2X00=y
 CONFIG_ARCH_IXDP2401=y
 CONFIG_ARCH_IXDP2801=y
+CONFIG_MACH_IXDP28X5=y
 CONFIG_ARCH_IXDP2X01=y
 # CONFIG_IXP2000_SUPPORT_BROKEN_PCI_IO is not set
 
@@ -147,7 +148,6 @@ CONFIG_XSCALE_PMU=y
 # Bus support
 #
 CONFIG_PCI=y
-CONFIG_PCI_LEGACY_PROC=y
 # CONFIG_PCI_DEBUG is not set
 
 #
@@ -160,6 +160,7 @@ CONFIG_PCI_LEGACY_PROC=y
 #
 # CONFIG_PREEMPT is not set
 # CONFIG_NO_IDLE_HZ is not set
+CONFIG_HZ=100
 # CONFIG_AEABI is not set
 # CONFIG_ARCH_DISCONTIGMEM_ENABLE is not set
 CONFIG_SELECT_MEMORY_MODEL=y
@@ -213,6 +214,7 @@ CONFIG_NET=y
 #
 # Networking options
 #
+# CONFIG_NETDEBUG is not set
 CONFIG_PACKET=y
 CONFIG_PACKET_MMAP=y
 CONFIG_UNIX=y
@@ -232,12 +234,15 @@ CONFIG_SYN_COOKIES=y
 # CONFIG_INET_AH is not set
 # CONFIG_INET_ESP is not set
 # CONFIG_INET_IPCOMP is not set
+# CONFIG_INET_XFRM_TUNNEL is not set
 # CONFIG_INET_TUNNEL is not set
 CONFIG_INET_DIAG=y
 CONFIG_INET_TCP_DIAG=y
 # CONFIG_TCP_CONG_ADVANCED is not set
 CONFIG_TCP_CONG_BIC=y
 # CONFIG_IPV6 is not set
+# CONFIG_INET6_XFRM_TUNNEL is not set
+# CONFIG_INET6_TUNNEL is not set
 # CONFIG_NETFILTER is not set
 
 #
@@ -347,7 +352,6 @@ CONFIG_MTD_CFI_UTIL=y
 # CONFIG_MTD_ROM is not set
 # CONFIG_MTD_ABSENT is not set
 # CONFIG_MTD_OBSOLETE_CHIPS is not set
-# CONFIG_MTD_XIP is not set
 
 #
 # Mapping drivers for chip access
@@ -366,7 +370,6 @@ CONFIG_MTD_IXP2000=y
 # CONFIG_MTD_SLRAM is not set
 # CONFIG_MTD_PHRAM is not set
 # CONFIG_MTD_MTDRAM is not set
-# CONFIG_MTD_BLKMTD is not set
 # CONFIG_MTD_BLOCK2MTD is not set
 
 #
@@ -614,8 +617,9 @@ CONFIG_INPUT_MOUSEDEV_SCREEN_Y=768
 #
 CONFIG_SERIAL_8250=y
 CONFIG_SERIAL_8250_CONSOLE=y
+CONFIG_SERIAL_8250_PCI=y
 CONFIG_SERIAL_8250_NR_UARTS=3
-CONFIG_SERIAL_8250_RUNTIME_UARTS=4
+CONFIG_SERIAL_8250_RUNTIME_UARTS=3
 # CONFIG_SERIAL_8250_EXTENDED is not set
 
 #
@@ -623,6 +627,7 @@ CONFIG_SERIAL_8250_RUNTIME_UARTS=4
 #
 CONFIG_SERIAL_CORE=y
 CONFIG_SERIAL_CORE_CONSOLE=y
+# CONFIG_SERIAL_JSM is not set
 CONFIG_UNIX98_PTYS=y
 CONFIG_LEGACY_PTYS=y
 CONFIG_LEGACY_PTY_COUNT=256
@@ -650,7 +655,6 @@ CONFIG_IXP2000_WATCHDOG=y
 # CONFIG_PCIPCWATCHDOG is not set
 # CONFIG_WDTPCI is not set
 # CONFIG_NVRAM is not set
-# CONFIG_RTC is not set
 # CONFIG_DTLK is not set
 # CONFIG_R3964 is not set
 # CONFIG_APPLICOM is not set
@@ -696,7 +700,6 @@ CONFIG_I2C_IXP2000=y
 # CONFIG_I2C_PARPORT_LIGHT is not set
 # CONFIG_I2C_PROSAVAGE is not set
 # CONFIG_I2C_SAVAGE4 is not set
-# CONFIG_SCx200_ACB is not set
 # CONFIG_I2C_SIS5595 is not set
 # CONFIG_I2C_SIS630 is not set
 # CONFIG_I2C_SIS96X is not set
@@ -715,9 +718,7 @@ CONFIG_SENSORS_EEPROM=y
 # CONFIG_SENSORS_PCF8574 is not set
 # CONFIG_SENSORS_PCA9539 is not set
 # CONFIG_SENSORS_PCF8591 is not set
-# CONFIG_SENSORS_RTC8564 is not set
 # CONFIG_SENSORS_MAX6875 is not set
-# CONFIG_RTC_X1205_I2C is not set
 # CONFIG_I2C_DEBUG_CORE is not set
 # CONFIG_I2C_DEBUG_ALGO is not set
 # CONFIG_I2C_DEBUG_BUS is not set
@@ -729,6 +730,11 @@ CONFIG_SENSORS_EEPROM=y
 # CONFIG_SPI is not set
 # CONFIG_SPI_MASTER is not set
 
+#
+# Dallas's 1-wire bus
+#
+# CONFIG_W1 is not set
+
 #
 # Hardware Monitoring support
 #
@@ -742,6 +748,7 @@ CONFIG_HWMON=y
 # CONFIG_SENSORS_ASB100 is not set
 # CONFIG_SENSORS_ATXP1 is not set
 # CONFIG_SENSORS_DS1621 is not set
+# CONFIG_SENSORS_F71805F is not set
 # CONFIG_SENSORS_FSCHER is not set
 # CONFIG_SENSORS_FSCPOS is not set
 # CONFIG_SENSORS_GL518SM is not set
@@ -776,7 +783,16 @@ CONFIG_HWMON=y
 #
 
 #
-# Multimedia Capabilities Port drivers
+# LED devices
+#
+# CONFIG_NEW_LEDS is not set
+
+#
+# LED drivers
+#
+
+#
+# LED Triggers
 #
 
 #
@@ -804,6 +820,7 @@ CONFIG_HWMON=y
 #
 CONFIG_USB_ARCH_HAS_HCD=y
 CONFIG_USB_ARCH_HAS_OHCI=y
+CONFIG_USB_ARCH_HAS_EHCI=y
 # CONFIG_USB is not set
 
 #
@@ -820,6 +837,12 @@ CONFIG_USB_ARCH_HAS_OHCI=y
 #
 # CONFIG_MMC is not set
 
+#
+# Real Time Clock
+#
+CONFIG_RTC_LIB=y
+# CONFIG_RTC_CLASS is not set
+
 #
 # File systems
 #
@@ -870,7 +893,6 @@ CONFIG_SYSFS=y
 CONFIG_TMPFS=y
 # CONFIG_HUGETLB_PAGE is not set
 CONFIG_RAMFS=y
-# CONFIG_RELAYFS_FS is not set
 # CONFIG_CONFIGFS_FS is not set
 
 #
@@ -972,6 +994,7 @@ CONFIG_DEBUG_BUGVERBOSE=y
 # CONFIG_DEBUG_FS is not set
 # CONFIG_DEBUG_VM is not set
 CONFIG_FRAME_POINTER=y
+# CONFIG_UNWIND_INFO is not set
 CONFIG_FORCED_INLINING=y
 # CONFIG_RCU_TORTURE_TEST is not set
 CONFIG_DEBUG_USER=y
index 1a2751e9ab05793d40fcbd522bec29faeb537cd1..9ce898a6cf87f3daa5b4828f18fd608084271405 100644 (file)
@@ -1,12 +1,14 @@
 #
 # Automatically generated make config: don't edit
-# Linux kernel version: 2.6.16
-# Tue Mar 21 03:27:20 2006
+# Linux kernel version: 2.6.17-rc2
+# Wed Apr 19 21:13:50 2006
 #
 CONFIG_ARM=y
 CONFIG_MMU=y
 CONFIG_RWSEM_GENERIC_SPINLOCK=y
+CONFIG_GENERIC_HWEIGHT=y
 CONFIG_GENERIC_CALIBRATE_DELAY=y
+CONFIG_VECTORS_BASE=0xffff0000
 
 #
 # Code maturity level options
@@ -28,6 +30,7 @@ CONFIG_BSD_PROCESS_ACCT=y
 CONFIG_SYSCTL=y
 # CONFIG_AUDIT is not set
 # CONFIG_IKCONFIG is not set
+# CONFIG_RELAY is not set
 CONFIG_INITRAMFS_SOURCE=""
 CONFIG_UID16=y
 CONFIG_CC_OPTIMIZE_FOR_SIZE=y
@@ -43,10 +46,6 @@ CONFIG_BASE_FULL=y
 CONFIG_FUTEX=y
 CONFIG_EPOLL=y
 CONFIG_SHMEM=y
-CONFIG_CC_ALIGN_FUNCTIONS=0
-CONFIG_CC_ALIGN_LABELS=0
-CONFIG_CC_ALIGN_LOOPS=0
-CONFIG_CC_ALIGN_JUMPS=0
 CONFIG_SLAB=y
 # CONFIG_TINY_SHMEM is not set
 CONFIG_BASE_SMALL=0
@@ -59,7 +58,6 @@ CONFIG_OBSOLETE_INTERMODULE=y
 CONFIG_MODULES=y
 CONFIG_MODULE_UNLOAD=y
 # CONFIG_MODULE_FORCE_UNLOAD is not set
-CONFIG_OBSOLETE_MODPARM=y
 # CONFIG_MODVERSIONS is not set
 # CONFIG_MODULE_SRCVERSION_ALL is not set
 CONFIG_KMOD=y
@@ -67,6 +65,7 @@ CONFIG_KMOD=y
 #
 # Block layer
 #
+# CONFIG_BLK_DEV_IO_TRACE is not set
 
 #
 # IO Schedulers
@@ -143,7 +142,6 @@ CONFIG_CPU_BIG_ENDIAN=y
 # Bus support
 #
 CONFIG_PCI=y
-CONFIG_PCI_LEGACY_PROC=y
 # CONFIG_PCI_DEBUG is not set
 
 #
@@ -230,12 +228,15 @@ CONFIG_SYN_COOKIES=y
 # CONFIG_INET_AH is not set
 # CONFIG_INET_ESP is not set
 # CONFIG_INET_IPCOMP is not set
+# CONFIG_INET_XFRM_TUNNEL is not set
 # CONFIG_INET_TUNNEL is not set
 CONFIG_INET_DIAG=y
 CONFIG_INET_TCP_DIAG=y
 # CONFIG_TCP_CONG_ADVANCED is not set
 CONFIG_TCP_CONG_BIC=y
 # CONFIG_IPV6 is not set
+# CONFIG_INET6_XFRM_TUNNEL is not set
+# CONFIG_INET6_TUNNEL is not set
 # CONFIG_NETFILTER is not set
 
 #
@@ -365,7 +366,6 @@ CONFIG_MTD_PHYSMAP_BANKWIDTH=1
 # CONFIG_MTD_SLRAM is not set
 # CONFIG_MTD_PHRAM is not set
 # CONFIG_MTD_MTDRAM is not set
-# CONFIG_MTD_BLKMTD is not set
 # CONFIG_MTD_BLOCK2MTD is not set
 
 #
@@ -527,7 +527,6 @@ CONFIG_BLK_DEV_SD=y
 # CONFIG_SCSI_INIA100 is not set
 # CONFIG_SCSI_SYM53C8XX_2 is not set
 # CONFIG_SCSI_IPR is not set
-# CONFIG_SCSI_QLOGIC_FC is not set
 # CONFIG_SCSI_QLOGIC_1280 is not set
 # CONFIG_SCSI_QLA_FC is not set
 # CONFIG_SCSI_LPFC is not set
@@ -735,6 +734,7 @@ CONFIG_INPUT_MOUSEDEV_SCREEN_Y=768
 #
 CONFIG_SERIAL_8250=y
 CONFIG_SERIAL_8250_CONSOLE=y
+CONFIG_SERIAL_8250_PCI=y
 CONFIG_SERIAL_8250_NR_UARTS=4
 CONFIG_SERIAL_8250_RUNTIME_UARTS=4
 # CONFIG_SERIAL_8250_EXTENDED is not set
@@ -776,7 +776,6 @@ CONFIG_WATCHDOG=y
 #
 # CONFIG_USBPCWATCHDOG is not set
 # CONFIG_NVRAM is not set
-# CONFIG_RTC is not set
 # CONFIG_DTLK is not set
 # CONFIG_R3964 is not set
 # CONFIG_APPLICOM is not set
@@ -821,7 +820,6 @@ CONFIG_I2C_ALGOBIT=y
 # CONFIG_I2C_PARPORT_LIGHT is not set
 # CONFIG_I2C_PROSAVAGE is not set
 # CONFIG_I2C_SAVAGE4 is not set
-# CONFIG_SCx200_ACB is not set
 # CONFIG_I2C_SIS5595 is not set
 # CONFIG_I2C_SIS630 is not set
 # CONFIG_I2C_SIS96X is not set
@@ -840,9 +838,7 @@ CONFIG_SENSORS_EEPROM=y
 # CONFIG_SENSORS_PCF8574 is not set
 # CONFIG_SENSORS_PCA9539 is not set
 # CONFIG_SENSORS_PCF8591 is not set
-# CONFIG_SENSORS_RTC8564 is not set
 # CONFIG_SENSORS_MAX6875 is not set
-# CONFIG_RTC_X1205_I2C is not set
 # CONFIG_I2C_DEBUG_CORE is not set
 # CONFIG_I2C_DEBUG_ALGO is not set
 # CONFIG_I2C_DEBUG_BUS is not set
@@ -907,7 +903,16 @@ CONFIG_HWMON=y
 #
 
 #
-# Multimedia Capabilities Port drivers
+# LED devices
+#
+# CONFIG_NEW_LEDS is not set
+
+#
+# LED drivers
+#
+
+#
+# LED Triggers
 #
 
 #
@@ -919,6 +924,7 @@ CONFIG_HWMON=y
 # Digital Video Broadcasting Devices
 #
 # CONFIG_DVB is not set
+# CONFIG_USB_DABUSB is not set
 
 #
 # Graphics support
@@ -935,6 +941,7 @@ CONFIG_HWMON=y
 #
 CONFIG_USB_ARCH_HAS_HCD=y
 CONFIG_USB_ARCH_HAS_OHCI=y
+CONFIG_USB_ARCH_HAS_EHCI=y
 CONFIG_USB=y
 # CONFIG_USB_DEBUG is not set
 
@@ -1000,9 +1007,7 @@ CONFIG_USB_STORAGE=y
 # CONFIG_USB_ACECAD is not set
 # CONFIG_USB_KBTAB is not set
 # CONFIG_USB_POWERMATE is not set
-# CONFIG_USB_MTOUCH is not set
-# CONFIG_USB_ITMTOUCH is not set
-# CONFIG_USB_EGALAX is not set
+# CONFIG_USB_TOUCHSCREEN is not set
 # CONFIG_USB_YEALINK is not set
 # CONFIG_USB_XPAD is not set
 # CONFIG_USB_ATI_REMOTE is not set
@@ -1016,15 +1021,6 @@ CONFIG_USB_STORAGE=y
 # CONFIG_USB_MDC800 is not set
 # CONFIG_USB_MICROTEK is not set
 
-#
-# USB Multimedia devices
-#
-# CONFIG_USB_DABUSB is not set
-
-#
-# Video4Linux support is needed for USB Multimedia device support
-#
-
 #
 # USB Network Adapters
 #
@@ -1075,6 +1071,12 @@ CONFIG_USB_MON=y
 #
 # CONFIG_MMC is not set
 
+#
+# Real Time Clock
+#
+CONFIG_RTC_LIB=y
+# CONFIG_RTC_CLASS is not set
+
 #
 # File systems
 #
@@ -1127,7 +1129,6 @@ CONFIG_SYSFS=y
 CONFIG_TMPFS=y
 # CONFIG_HUGETLB_PAGE is not set
 CONFIG_RAMFS=y
-# CONFIG_RELAYFS_FS is not set
 # CONFIG_CONFIGFS_FS is not set
 
 #
@@ -1268,6 +1269,7 @@ CONFIG_DEBUG_BUGVERBOSE=y
 # CONFIG_DEBUG_FS is not set
 # CONFIG_DEBUG_VM is not set
 CONFIG_FRAME_POINTER=y
+# CONFIG_UNWIND_INFO is not set
 CONFIG_FORCED_INLINING=y
 # CONFIG_RCU_TORTURE_TEST is not set
 CONFIG_DEBUG_USER=y
index ee083b3f05220aee308aba8a8f0eff7f27100a30..c49b5d4d7fca2a77217c15732c0fbeeefdf90f6f 100644 (file)
@@ -101,7 +101,6 @@ EXPORT_SYMBOL(__raw_writesl);
 
        /* string / mem functions */
 EXPORT_SYMBOL(strchr);
-EXPORT_SYMBOL(strpbrk);
 EXPORT_SYMBOL(strrchr);
 EXPORT_SYMBOL(memset);
 EXPORT_SYMBOL(memcpy);
index 4375284039595f93f2ce9cf91b27abd3fb677375..9fc9af88c60c72e54cad5e835c579b95027624e6 100644 (file)
@@ -322,6 +322,12 @@ static void __init setup_processor(void)
        sprintf(system_utsname.machine, "%s%c", list->arch_name, ENDIANNESS);
        sprintf(elf_platform, "%s%c", list->elf_name, ENDIANNESS);
        elf_hwcap = list->elf_hwcap;
+#ifndef CONFIG_ARM_THUMB
+       elf_hwcap &= ~HWCAP_THUMB;
+#endif
+#ifndef CONFIG_VFP
+       elf_hwcap &= ~HWCAP_VFP;
+#endif
 
        cpu_proc_init();
 }
@@ -401,7 +407,7 @@ static void __init early_initrd(char **p)
 }
 __early_param("initrd=", early_initrd);
 
-static void __init add_memory(unsigned long start, unsigned long size)
+static void __init arm_add_memory(unsigned long start, unsigned long size)
 {
        /*
         * Ensure that start/size are aligned to a page boundary.
@@ -439,7 +445,7 @@ static void __init early_mem(char **p)
        if (**p == '@')
                start = memparse(*p + 1, p);
 
-       add_memory(start, size);
+       arm_add_memory(start, size);
 }
 __early_param("mem=", early_mem);
 
@@ -581,7 +587,7 @@ static int __init parse_tag_mem32(const struct tag *tag)
                        tag->u.mem.start, tag->u.mem.size / 1024);
                return -EINVAL;
        }
-       add_memory(tag->u.mem.start, tag->u.mem.size);
+       arm_add_memory(tag->u.mem.start, tag->u.mem.size);
        return 0;
 }
 
@@ -801,7 +807,7 @@ static int __init topology_init(void)
 {
        int cpu;
 
-       for_each_cpu(cpu)
+       for_each_possible_cpu(cpu)
                register_cpu(&per_cpu(cpu_data, cpu).cpu, cpu, NULL);
 
        return 0;
index 1781b8f342c4d1b43e53d7f1c5009c987c1d2cfb..bfe47bd6e50c595682322cdc909386ea73ded909 100644 (file)
@@ -194,13 +194,23 @@ void __init at91_add_device_eth(struct at91_eth_data *data) {}
 #if defined(CONFIG_AT91_CF) || defined(CONFIG_AT91_CF_MODULE)
 static struct at91_cf_data cf_data;
 
+static struct resource at91_cf_resources[] = {
+       [0] = {
+               .start  = AT91_CF_BASE,
+               /* ties up CS4, CS5, and CS6 */
+               .end    = AT91_CF_BASE + (0x30000000 - 1),
+               .flags  = IORESOURCE_MEM | IORESOURCE_MEM_8AND16BIT,
+       },
+};
+
 static struct platform_device at91rm9200_cf_device = {
        .name           = "at91_cf",
        .id             = -1,
        .dev            = {
                                .platform_data          = &cf_data,
        },
-       .num_resources  = 0,
+       .resource       = at91_cf_resources,
+       .num_resources  = ARRAY_SIZE(at91_cf_resources),
 };
 
 void __init at91_add_device_cf(struct at91_cf_data *data)
index a0888e160e3b7f180c8c91fafa9c636a284a919c..00b761ff0f9ce75b76fcf60217919eb1acbf308b 100644 (file)
@@ -91,7 +91,7 @@ static void ixp4xx_config_irq(unsigned irq, enum ixp4xx_irq_type type);
 /*
  * IRQ -> GPIO mapping table
  */
-static char irq2gpio[32] = {
+static signed char irq2gpio[32] = {
        -1, -1, -1, -1, -1, -1,  0,  1,
        -1, -1, -1, -1, -1, -1, -1, -1,
        -1, -1, -1,  2,  3,  4,  5,  6,
index 876c38da14f75c2d9e6023b9d5bbd05c5357d066..847329cafc5c060dc94f208a177652e8e9f047e2 100644 (file)
 #include <asm/arch/mux.h>
 #include <asm/arch/gpio.h>
 
-extern void omap_nop_release(struct device *dev);
-
-/*-------------------------------------------------------------------------*/
-
 #if    defined(CONFIG_OMAP1610_IR) || defined(CONFIG_OMAP161O_IR_MODULE)
 
 static u64 irda_dmamask = 0xffffffff;
@@ -37,7 +33,6 @@ static struct platform_device omap1610ir_device = {
        .name = "omap1610-ir",
        .id = -1,
        .dev = {
-               .release        = omap_nop_release,
                .dma_mask       = &irda_dmamask,
        },
 };
@@ -84,9 +79,6 @@ static struct resource rtc_resources[] = {
 static struct platform_device omap_rtc_device = {
        .name           = "omap_rtc",
        .id             = -1,
-       .dev = {
-               .release        = omap_nop_release,
-       },
        .num_resources  = ARRAY_SIZE(rtc_resources),
        .resource       = rtc_resources,
 };
@@ -124,9 +116,6 @@ static struct resource sti_resources[] = {
 static struct platform_device sti_device = {
        .name           = "sti",
        .id             = -1,
-       .dev = {
-               .release        = omap_nop_release,
-       },
        .num_resources  = ARRAY_SIZE(sti_resources),
        .resource       = sti_resources,
 };
index def9e5370edfb3554f146871552f731c4b01e62a..fb7f91da1aad12d8f8682eff0dcb558d6f314916 100644 (file)
 #include <asm/arch/mux.h>
 #include <asm/arch/gpio.h>
 
-extern void omap_nop_release(struct device *dev);
-
-/*-------------------------------------------------------------------------*/
-
 #if    defined(CONFIG_I2C_OMAP) || defined(CONFIG_I2C_OMAP_MODULE)
 
 #define OMAP2_I2C_BASE2                0x48072000
@@ -49,9 +45,6 @@ static struct resource i2c_resources2[] = {
 static struct platform_device omap_i2c_device2 = {
         .name           = "i2c_omap",
         .id             = 2,
-        .dev = {
-                .release        = omap_nop_release,
-        },
        .num_resources  = ARRAY_SIZE(i2c_resources2),
        .resource       = i2c_resources2,
 };
@@ -100,9 +93,6 @@ static struct resource sti_resources[] = {
 static struct platform_device sti_device = {
        .name           = "sti",
        .id             = -1,
-       .dev = {
-               .release        = omap_nop_release,
-       },
        .num_resources  = ARRAY_SIZE(sti_resources),
        .resource       = sti_resources,
 };
index b371d723635f38062d907059d5b9622604148f6b..8a25a1c8019f9bf7685f92561f04b1523a851c1a 100644 (file)
@@ -196,12 +196,9 @@ static int __init corgi_ssp_probe(struct platform_device *dev)
        int ret;
 
        /* Chip Select - Disable All */
-       GPDR(ssp_machinfo->cs_lcdcon) |= GPIO_bit(ssp_machinfo->cs_lcdcon); /* output */
-       GPSR(ssp_machinfo->cs_lcdcon) = GPIO_bit(ssp_machinfo->cs_lcdcon);  /* High - Disable LCD Control/Timing Gen */
-       GPDR(ssp_machinfo->cs_max1111) |= GPIO_bit(ssp_machinfo->cs_max1111); /* output */
-       GPSR(ssp_machinfo->cs_max1111) = GPIO_bit(ssp_machinfo->cs_max1111);  /* High - Disable MAX1111*/
-       GPDR(ssp_machinfo->cs_ads7846) |= GPIO_bit(ssp_machinfo->cs_ads7846);  /* output */
-       GPSR(ssp_machinfo->cs_ads7846) = GPIO_bit(ssp_machinfo->cs_ads7846);   /* High - Disable ADS7846*/
+       pxa_gpio_mode(ssp_machinfo->cs_lcdcon  | GPIO_OUT | GPIO_DFLT_HIGH);
+        pxa_gpio_mode(ssp_machinfo->cs_max1111 | GPIO_OUT | GPIO_DFLT_HIGH);
+        pxa_gpio_mode(ssp_machinfo->cs_ads7846 | GPIO_OUT | GPIO_DFLT_HIGH);
 
        ret = ssp_init(&corgi_ssp_dev, ssp_machinfo->port, 0);
 
index b7f85e6d6b76f6e09816a3c6dd9df34e48161f85..6de713ad319a1c798c3444da58c2f545d933fb37 100644 (file)
@@ -367,6 +367,8 @@ static int s3c24xx_clkout_setparent(struct clk *clk, struct clk *parent)
                source = S3C2410_MISCCR_CLK0_UPLL;
        else if (parent == &clk_f)
                source = S3C2410_MISCCR_CLK0_FCLK;
+       else if (parent == &clk_h)
+               source = S3C2410_MISCCR_CLK0_HCLK;
        else if (parent == &clk_p)
                source = S3C2410_MISCCR_CLK0_PCLK;
        else if (clk == &s3c24xx_clkout0 && parent == &s3c24xx_dclk0)
@@ -376,6 +378,8 @@ static int s3c24xx_clkout_setparent(struct clk *clk, struct clk *parent)
        else
                return -EINVAL;
 
+       clk->parent = parent;
+
        if (clk == &s3c24xx_dclk0)
                mask = S3C2410_MISCCR_CLK0_MASK;
        else {
index 36b8291b5e037e87cd5596aa732b805e6c4b80c6..c940890f621f1902fe761773acd2aa9b999b8188 100644 (file)
@@ -37,6 +37,7 @@
 
 #include <asm/arch/nand.h>
 
+#include "common-smdk.h"
 #include "devs.h"
 #include "pm.h"
 
@@ -49,7 +50,7 @@ static struct mtd_partition smdk_default_nand_part[] = {
                .offset = 0,
        },
        [1] = {
-               .name   = "S3C2410 flash parition 1",
+               .name   = "S3C2410 flash partition 1",
                .offset = 0,
                .size   = SZ_2M,
        },
index 57a15974d4b50aaded6667882e4004b459cca878..d7a30ed6c327eb57d2f3c4ff454939a70f6129fd 100644 (file)
@@ -139,7 +139,7 @@ static int s3c2440_clk_add(struct sys_device *sysdev)
 
                clkdivn = __raw_readl(S3C2410_CLKDIVN);
                clkdivn |= S3C2440_CLKDIVN_UCLK;
-               __raw_writel(camdivn, S3C2410_CLKDIVN);
+               __raw_writel(clkdivn, S3C2410_CLKDIVN);
 
                mutex_unlock(&clocks_mutex);
        }
index 5c4055b62d976808a9660903393d501dce5a5599..54e3c5bb5186a88203ed83441e58926347cb55a5 100644 (file)
@@ -10,7 +10,7 @@
 #include <linux/config.h>
 #include <linux/linkage.h>
 #include <linux/init.h>
-#include <asm/hardware.h>
+#include <asm/memory.h>
 #include <asm/page.h>
 #include "proc-macros.S"
 
  */
 #define CACHE_DLIMIT   (CACHE_DSIZE * 4)
 
+       .data
+flush_base:
+       .long   FLUSH_BASE
+       .text
+
 /*
  *     flush_user_cache_all()
  *
@@ -63,11 +68,21 @@ ENTRY(v4wb_flush_kern_cache_all)
        mov     ip, #0
        mcr     p15, 0, ip, c7, c5, 0           @ invalidate I cache
 __flush_whole_cache:
-       mov     r0, #FLUSH_BASE
-       add     r1, r0, #CACHE_DSIZE
-1:     ldr     r2, [r0], #32
-       cmp     r0, r1
+       ldr     r3, =flush_base
+       ldr     r1, [r3, #0]
+       eor     r1, r1, #CACHE_DSIZE
+       str     r1, [r3, #0]
+       add     r2, r1, #CACHE_DSIZE
+1:     ldr     r3, [r1], #32
+       cmp     r1, r2
+       blo     1b
+#ifdef FLUSH_BASE_MINICACHE
+       add     r2, r2, #FLUSH_BASE_MINICACHE - FLUSH_BASE
+       sub     r1, r2, #512                    @ only 512 bytes
+1:     ldr     r3, [r1], #32
+       cmp     r1, r2
        blo     1b
+#endif
        mcr     p15, 0, ip, c7, c10, 4          @ drain write buffer
        mov     pc, lr
 
@@ -82,6 +97,7 @@ __flush_whole_cache:
  *     - flags - vma_area_struct flags describing address space
  */
 ENTRY(v4wb_flush_user_cache_range)
+       mov     ip, #0
        sub     r3, r1, r0                      @ calculate total size
        tst     r2, #VM_EXEC                    @ executable region?
        mcrne   p15, 0, ip, c7, c5, 0           @ invalidate I cache
index 88279124317a6f5079091e62fb1c7d3487faf419..9ea1f87a7079b863ee4d061103ef46b2aa00fa9b 100644 (file)
@@ -20,6 +20,7 @@
 
 #include <asm/mach-types.h>
 #include <asm/setup.h>
+#include <asm/sizes.h>
 #include <asm/tlb.h>
 
 #include <asm/mach/arch.h>
@@ -455,14 +456,14 @@ static void __init devicemaps_init(struct machine_desc *mdesc)
 #ifdef FLUSH_BASE
        map.pfn = __phys_to_pfn(FLUSH_BASE_PHYS);
        map.virtual = FLUSH_BASE;
-       map.length = PGDIR_SIZE;
+       map.length = SZ_1M;
        map.type = MT_CACHECLEAN;
        create_mapping(&map);
 #endif
 #ifdef FLUSH_BASE_MINICACHE
-       map.pfn = __phys_to_pfn(FLUSH_BASE_PHYS + PGDIR_SIZE);
+       map.pfn = __phys_to_pfn(FLUSH_BASE_PHYS + SZ_1M);
        map.virtual = FLUSH_BASE_MINICACHE;
-       map.length = PGDIR_SIZE;
+       map.length = SZ_1M;
        map.type = MT_MINICLEAN;
        create_mapping(&map);
 #endif
index c916a6cae40428e53ade79211ba8994e70583cd4..a2dd5ae1077dda0c5257a768a6d69c880c0781af 100644 (file)
  * the cache line size of the I and D cache
  */
 #define DCACHELINESIZE 32
-#define FLUSH_OFFSET   32768
 
-       .macro flush_110_dcache rd, ra, re
-       ldr     \rd, =flush_base
-       ldr     \ra, [\rd]
-       eor     \ra, \ra, #FLUSH_OFFSET
-       str     \ra, [\rd]
-       add     \re, \ra, #16384                @ only necessary for 16k
-1001:  ldr     \rd, [\ra], #DCACHELINESIZE
-       teq     \re, \ra
-       bne     1001b
-       .endm
-
-       .data
-flush_base:
-       .long   FLUSH_BASE
        .text
 
 /*
@@ -145,13 +130,11 @@ ENTRY(cpu_sa110_dcache_clean_area)
  */
        .align  5
 ENTRY(cpu_sa110_switch_mm)
-       flush_110_dcache        r3, ip, r1
-       mov     r1, #0
-       mcr     p15, 0, r1, c7, c5, 0           @ invalidate I cache
-       mcr     p15, 0, r1, c7, c10, 4          @ drain WB
+       str     lr, [sp, #-4]!
+       bl      v4wb_flush_kern_cache_all       @ clears IP
        mcr     p15, 0, r0, c2, c0, 0           @ load page table pointer
-       mcr     p15, 0, r1, c8, c7, 0           @ invalidate I & D TLBs
-       mov     pc, lr
+       mcr     p15, 0, ip, c8, c7, 0           @ invalidate I & D TLBs
+       ldr     pc, [sp], #4
 
 /*
  * cpu_sa110_set_pte(ptep, pte)
index 41f21f2dd8ffae766afeae26f641a75a1994d6f2..777ad99c14395584690dfc32cd3c297540edca16 100644 (file)
  * the cache line size of the I and D cache
  */
 #define DCACHELINESIZE 32
-#define FLUSH_OFFSET   32768
-
-       .macro flush_1100_dcache rd, ra, re
-       ldr     \rd, =flush_base
-       ldr     \ra, [\rd]
-       eor     \ra, \ra, #FLUSH_OFFSET
-       str     \ra, [\rd]
-       add     \re, \ra, #8192                 @ only necessary for 8k
-1001:  ldr     \rd, [\ra], #DCACHELINESIZE
-       teq     \re, \ra
-       bne     1001b
-#ifdef FLUSH_BASE_MINICACHE
-       add     \ra, \ra, #FLUSH_BASE_MINICACHE - FLUSH_BASE
-       add     \re, \ra, #512                  @ only 512 bytes
-1002:  ldr     \rd, [\ra], #DCACHELINESIZE
-       teq     \re, \ra
-       bne     1002b
-#endif
-       .endm
-
-       .data
-flush_base:
-       .long   FLUSH_BASE
-       .text
 
        __INIT
 
@@ -79,9 +55,8 @@ ENTRY(cpu_sa1100_proc_fin)
        stmfd   sp!, {lr}
        mov     ip, #PSR_F_BIT | PSR_I_BIT | SVC_MODE
        msr     cpsr_c, ip
-       flush_1100_dcache r0, r1, r2            @ clean caches
-       mov     r0, #0
-       mcr     p15, 0, r0, c15, c2, 2          @ Disable clock switching
+       bl      v4wb_flush_kern_cache_all
+       mcr     p15, 0, ip, c15, c2, 2          @ Disable clock switching
        mrc     p15, 0, r0, c1, c0, 0           @ ctrl register
        bic     r0, r0, #0x1000                 @ ...i............
        bic     r0, r0, #0x000e                 @ ............wca.
@@ -167,14 +142,12 @@ ENTRY(cpu_sa1100_dcache_clean_area)
  */
        .align  5
 ENTRY(cpu_sa1100_switch_mm)
-       flush_1100_dcache r3, ip, r1
-       mov     ip, #0
-       mcr     p15, 0, ip, c7, c5, 0           @ invalidate I cache
+       str     lr, [sp, #-4]!
+       bl      v4wb_flush_kern_cache_all       @ clears IP
        mcr     p15, 0, ip, c9, c0, 0           @ invalidate RB
-       mcr     p15, 0, ip, c7, c10, 4          @ drain WB
        mcr     p15, 0, r0, c2, c0, 0           @ load page table pointer
        mcr     p15, 0, ip, c8, c7, 0           @ invalidate I & D TLBs
-       mov     pc, lr
+       ldr     pc, [sp], #4
 
 /*
  * cpu_sa1100_set_pte(ptep, pte)
index 06485c193ee37c7ec342b794120078321170ffae..32ec04c58bcd4fb66e4647d63c5cab6fbbb1e758 100644 (file)
@@ -58,7 +58,7 @@ struct clk * clk_get(struct device *dev, const char *id)
                if (p->id == idno &&
                    strcmp(id, p->name) == 0 && try_module_get(p->owner)) {
                        clk = p;
-                       break;
+                       goto found;
                }
        }
 
@@ -69,6 +69,7 @@ struct clk * clk_get(struct device *dev, const char *id)
                }
        }
 
+found:
        mutex_unlock(&clocks_mutex);
 
        return clk;
index 079b67deac0f20fef726ce550739fa4345f5220c..5d5d6eb222dd739e9b3d8be070ed4030bfa897ff 100644 (file)
 #include <asm/arch/gpio.h>
 #include <asm/arch/menelaus.h>
 
-
-void omap_nop_release(struct device *dev)
-{
-        /* Nothing */
-}
-
-/*-------------------------------------------------------------------------*/
-
 #if    defined(CONFIG_I2C_OMAP) || defined(CONFIG_I2C_OMAP_MODULE)
 
 #define        OMAP1_I2C_BASE          0xfffb3800
@@ -59,9 +51,6 @@ static struct resource i2c_resources1[] = {
 static struct platform_device omap_i2c_device1 = {
         .name           = "i2c_omap",
         .id             = 1,
-        .dev = {
-                .release        = omap_nop_release,
-        },
        .num_resources  = ARRAY_SIZE(i2c_resources1),
        .resource       = i2c_resources1,
 };
@@ -187,7 +176,6 @@ static struct platform_device mmc_omap_device1 = {
        .name           = "mmci-omap",
        .id             = 1,
        .dev = {
-               .release        = omap_nop_release,
                .dma_mask       = &mmc1_dmamask,
                .platform_data  = &mmc1_conf,
        },
@@ -217,7 +205,6 @@ static struct platform_device mmc_omap_device2 = {
        .name           = "mmci-omap",
        .id             = 2,
        .dev = {
-               .release        = omap_nop_release,
                .dma_mask       = &mmc2_dmamask,
                .platform_data  = &mmc2_conf,
        },
@@ -321,9 +308,6 @@ static struct resource uwire_resources[] = {
 static struct platform_device omap_uwire_device = {
        .name      = "omap_uwire",
        .id          = -1,
-       .dev = {
-               .release        = omap_nop_release,
-       },
        .num_resources  = ARRAY_SIZE(uwire_resources),
        .resource       = uwire_resources,
 };
@@ -365,9 +349,6 @@ static struct resource wdt_resources[] = {
 static struct platform_device omap_wdt_device = {
        .name      = "omap_wdt",
        .id          = -1,
-       .dev = {
-               .release        = omap_nop_release,
-       },
        .num_resources  = ARRAY_SIZE(wdt_resources),
        .resource       = wdt_resources,
 };
@@ -401,9 +382,6 @@ static struct resource rng_resources[] = {
 static struct platform_device omap_rng_device = {
        .name      = "omap_rng",
        .id          = -1,
-       .dev = {
-               .release        = omap_nop_release,
-       },
        .num_resources  = ARRAY_SIZE(rng_resources),
        .resource       = rng_resources,
 };
index 9b367a65cb4d65caec8afedf39b53c2cb99b0159..febd115dba28aa5a2314bc6727c3529aa1b6fc4c 100644 (file)
@@ -588,6 +588,7 @@ static u32 vfp_double_ftosi(int sd, int unused, int dm, u32 fpscr)
        struct vfp_double vdm;
        u32 d, exceptions = 0;
        int rmode = fpscr & FPSCR_RMODE_MASK;
+       int tm;
 
        vfp_double_unpack(&vdm, vfp_get_double(dm));
        vfp_double_dump("VDM", &vdm);
@@ -595,10 +596,14 @@ static u32 vfp_double_ftosi(int sd, int unused, int dm, u32 fpscr)
        /*
         * Do we have denormalised number?
         */
-       if (vfp_double_type(&vdm) & VFP_DENORMAL)
+       tm = vfp_double_type(&vdm);
+       if (tm & VFP_DENORMAL)
                exceptions |= FPSCR_IDC;
 
-       if (vdm.exponent >= 1023 + 32) {
+       if (tm & VFP_NAN) {
+               d = 0;
+               exceptions |= FPSCR_IOC;
+       } else if (vdm.exponent >= 1023 + 32) {
                d = 0x7fffffff;
                if (vdm.sign)
                        d = ~d;
@@ -1122,9 +1127,9 @@ u32 vfp_double_cpdo(u32 inst, u32 fpscr)
 {
        u32 op = inst & FOP_MASK;
        u32 exceptions = 0;
-       unsigned int dd = vfp_get_sd(inst);
-       unsigned int dn = vfp_get_sn(inst);
-       unsigned int dm = vfp_get_sm(inst);
+       unsigned int dd = vfp_get_dd(inst);
+       unsigned int dn = vfp_get_dn(inst);
+       unsigned int dm = vfp_get_dm(inst);
        unsigned int vecitr, veclen, vecstride;
        u32 (*fop)(int, int, s32, u32);
 
@@ -1141,7 +1146,7 @@ u32 vfp_double_cpdo(u32 inst, u32 fpscr)
        pr_debug("VFP: vecstride=%u veclen=%u\n", vecstride,
                 (veclen >> FPSCR_LENGTH_BIT) + 1);
 
-       fop = (op == FOP_EXT) ? fop_extfns[dn] : fop_fns[FOP_TO_IDX(op)];
+       fop = (op == FOP_EXT) ? fop_extfns[FEXT_TO_IDX(inst)] : fop_fns[FOP_TO_IDX(op)];
        if (!fop)
                goto invalid;
 
@@ -1149,17 +1154,13 @@ u32 vfp_double_cpdo(u32 inst, u32 fpscr)
                u32 except;
 
                if (op == FOP_EXT)
-                       pr_debug("VFP: itr%d (d%u.%u) = op[%u] (d%u.%u)\n",
+                       pr_debug("VFP: itr%d (d%u) = op[%u] (d%u)\n",
                                 vecitr >> FPSCR_LENGTH_BIT,
-                                dd >> 1, dd & 1, dn,
-                                dm >> 1, dm & 1);
+                                dd, dn, dm);
                else
-                       pr_debug("VFP: itr%d (d%u.%u) = (d%u.%u) op[%u] (d%u.%u)\n",
+                       pr_debug("VFP: itr%d (d%u) = (d%u) op[%u] (d%u)\n",
                                 vecitr >> FPSCR_LENGTH_BIT,
-                                dd >> 1, dd & 1,
-                                dn >> 1, dn & 1,
-                                FOP_TO_IDX(op),
-                                dm >> 1, dm & 1);
+                                dd, dn, FOP_TO_IDX(op), dm);
 
                except = fop(dd, dn, dm, fpscr);
                pr_debug("VFP: itr%d: exceptions=%08x\n",
index b7ed57e00cd47294a0e080ef34b1d21581f74f1d..a3f65b47aea9edfdbfe7c88fe303ca41c15fbf3b 100644 (file)
@@ -189,11 +189,10 @@ vfp_put_float:
 
        .globl  vfp_get_double
 vfp_get_double:
-       mov     r0, r0, lsr #1
        add     pc, pc, r0, lsl #3
        mov     r0, r0
        .irp    dr,0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15
-       mrrc    p10, 1, r0, r1, c\dr    @ fmrrd r0, r1, d\dr
+       mrrc    p11, 1, r0, r1, c\dr    @ fmrrd r0, r1, d\dr
        mov     pc, lr
        .endr
 
@@ -204,10 +203,9 @@ vfp_get_double:
 
        .globl  vfp_put_double
 vfp_put_double:
-       mov     r0, r0, lsr #1
        add     pc, pc, r0, lsl #3
        mov     r0, r0
        .irp    dr,0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15
-       mcrr    p10, 1, r1, r2, c\dr    @ fmrrd r1, r2, d\dr
+       mcrr    p11, 1, r1, r2, c\dr    @ fmdrr r1, r2, d\dr
        mov     pc, lr
        .endr
index 14dd696ddeb1e98177cbc3b9a9883d3218ca592f..4ac27f1939347dadc280131da47c93737db3ad55 100644 (file)
@@ -632,6 +632,7 @@ static u32 vfp_single_ftosi(int sd, int unused, s32 m, u32 fpscr)
        struct vfp_single vsm;
        u32 d, exceptions = 0;
        int rmode = fpscr & FPSCR_RMODE_MASK;
+       int tm;
 
        vfp_single_unpack(&vsm, m);
        vfp_single_dump("VSM", &vsm);
@@ -639,10 +640,14 @@ static u32 vfp_single_ftosi(int sd, int unused, s32 m, u32 fpscr)
        /*
         * Do we have a denormalised number?
         */
+       tm = vfp_single_type(&vsm);
        if (vfp_single_type(&vsm) & VFP_DENORMAL)
                exceptions |= FPSCR_IDC;
 
-       if (vsm.exponent >= 127 + 32) {
+       if (tm & VFP_NAN) {
+               d = 0;
+               exceptions |= FPSCR_IOC;
+       } else if (vsm.exponent >= 127 + 32) {
                /*
                 * m >= 2^31-2^7: invalid
                 */
@@ -1188,7 +1193,7 @@ u32 vfp_single_cpdo(u32 inst, u32 fpscr)
        pr_debug("VFP: vecstride=%u veclen=%u\n", vecstride,
                 (veclen >> FPSCR_LENGTH_BIT) + 1);
 
-       fop = (op == FOP_EXT) ? fop_extfns[sn] : fop_fns[FOP_TO_IDX(op)];
+       fop = (op == FOP_EXT) ? fop_extfns[FEXT_TO_IDX(inst)] : fop_fns[FOP_TO_IDX(op)];
        if (!fop)
                goto invalid;
 
index a6a1b33734440bf177f0312e835589bafed83128..9d66c27f272415a47ae11ccbda61e2c462b4c552 100644 (file)
@@ -152,7 +152,6 @@ EXPORT_SYMBOL(strncmp);
 EXPORT_SYMBOL(strchr);
 EXPORT_SYMBOL(strlen);
 EXPORT_SYMBOL(strnlen);
-EXPORT_SYMBOL(strpbrk);
 EXPORT_SYMBOL(strrchr);
 EXPORT_SYMBOL(strstr);
 EXPORT_SYMBOL(memset);
index de39725da9202e1940230bb42eb66203ad71d1b4..d57859053ce7a5ec7d64a70fb2cb02ab0dba10c0 100644 (file)
@@ -39,7 +39,6 @@ EXPORT_SYMBOL(loops_per_usec);
 /* String functions */
 EXPORT_SYMBOL(memcmp);
 EXPORT_SYMBOL(memmove);
-EXPORT_SYMBOL(strpbrk);
 EXPORT_SYMBOL(strstr);
 EXPORT_SYMBOL(strcpy);
 EXPORT_SYMBOL(strchr);
index 1d21c8d34d8ab0b7770599f5ce95f67e28b20886..a9b59527a74157c2bca661366467fa05c4a20fc2 100644 (file)
@@ -1170,12 +1170,6 @@ __syscall_badsys:
 # syscall vector table
 #
 ###############################################################################
-#ifdef CONFIG_MMU
-#define __MMU(X) X
-#else
-#define __MMU(X) sys_ni_syscall
-#endif
-
        .section .rodata
 ALIGN
        .globl          sys_call_table
@@ -1305,7 +1299,7 @@ sys_call_table:
        .long sys_newuname
        .long sys_ni_syscall    /* old "cacheflush" */
        .long sys_adjtimex
-       .long __MMU(sys_mprotect) /* 125 */
+       .long sys_mprotect      /* 125 */
        .long sys_sigprocmask
        .long sys_ni_syscall    /* old "create_module" */
        .long sys_init_module
@@ -1324,16 +1318,16 @@ sys_call_table:
        .long sys_getdents
        .long sys_select
        .long sys_flock
-       .long __MMU(sys_msync)
+       .long sys_msync
        .long sys_readv         /* 145 */
        .long sys_writev
        .long sys_getsid
        .long sys_fdatasync
        .long sys_sysctl
-       .long __MMU(sys_mlock)          /* 150 */
-       .long __MMU(sys_munlock)
-       .long __MMU(sys_mlockall)
-       .long __MMU(sys_munlockall)
+       .long sys_mlock         /* 150 */
+       .long sys_munlock
+       .long sys_mlockall
+       .long sys_munlockall
        .long sys_sched_setparam
        .long sys_sched_getparam   /* 155 */
        .long sys_sched_setscheduler
@@ -1343,7 +1337,7 @@ sys_call_table:
        .long sys_sched_get_priority_min  /* 160 */
        .long sys_sched_rr_get_interval
        .long sys_nanosleep
-       .long __MMU(sys_mremap)
+       .long sys_mremap
        .long sys_setresuid16
        .long sys_getresuid16   /* 165 */
        .long sys_ni_syscall    /* for vm86 */
@@ -1398,8 +1392,8 @@ sys_call_table:
        .long sys_setfsuid              /* 215 */
        .long sys_setfsgid
        .long sys_pivot_root
-       .long __MMU(sys_mincore)
-       .long __MMU(sys_madvise)
+       .long sys_mincore
+       .long sys_madvise
        .long sys_getdents64    /* 220 */
        .long sys_fcntl64
        .long sys_ni_syscall    /* reserved for TUX */
@@ -1437,7 +1431,7 @@ sys_call_table:
        .long sys_epoll_create
        .long sys_epoll_ctl     /* 255 */
        .long sys_epoll_wait
-       .long __MMU(sys_remap_file_pages)
+       .long sys_remap_file_pages
        .long sys_set_tid_address
        .long sys_timer_create
        .long sys_timer_settime         /* 260 */
index 07c8ffa0dd3912e278a6e6316120f4af49d41535..0f273a7aca5ae841691fae203728249511c85499 100644 (file)
@@ -27,7 +27,6 @@ EXPORT_SYMBOL(__ioremap);
 EXPORT_SYMBOL(iounmap);
 
 EXPORT_SYMBOL(strnlen);
-EXPORT_SYMBOL(strpbrk);
 EXPORT_SYMBOL(strrchr);
 EXPORT_SYMBOL(strstr);
 EXPORT_SYMBOL(strchr);
index b6cd78c972bb4a1a7cee5ce6202ce5879843a51a..f8d6dee8478112e92b1dc44e2c8d95c5a5afc740 100644 (file)
@@ -25,7 +25,6 @@ extern char h8300_debug_device[];
 /* platform dependent support */
 
 EXPORT_SYMBOL(strnlen);
-EXPORT_SYMBOL(strpbrk);
 EXPORT_SYMBOL(strrchr);
 EXPORT_SYMBOL(strstr);
 EXPORT_SYMBOL(strchr);
index f17bd1d2707eb31be18fd1010fb225b641e823d5..18ec9fe6deb69d887a1f48a204c7b126cb633e04 100644 (file)
@@ -53,6 +53,35 @@ source "init/Kconfig"
 
 menu "Processor type and features"
 
+config SMP
+       bool "Symmetric multi-processing support"
+       ---help---
+         This enables support for systems with more than one CPU. If you have
+         a system with only one CPU, like most personal computers, say N. If
+         you have a system with more than one CPU, say Y.
+
+         If you say N here, the kernel will run on single and multiprocessor
+         machines, but will use only one CPU of a multiprocessor machine. If
+         you say Y here, the kernel will run on many, but not all,
+         singleprocessor machines. On a singleprocessor machine, the kernel
+         will run faster if you say N here.
+
+         Note that if you say Y here and choose architecture "586" or
+         "Pentium" under "Processor family", the kernel will not work on 486
+         architectures. Similarly, multiprocessor kernels for the "PPro"
+         architecture may not work on all Pentium based boards.
+
+         People using multiprocessor machines who say Y here should also say
+         Y to "Enhanced Real Time Clock Support", below. The "Advanced Power
+         Management" code will be disabled if you say Y here.
+
+         See also the <file:Documentation/smp.txt>,
+         <file:Documentation/i386/IO-APIC.txt>,
+         <file:Documentation/nmi_watchdog.txt> and the SMP-HOWTO available at
+         <http://www.tldp.org/docs.html#howto>.
+
+         If you don't know what to do here, say N.
+
 choice
        prompt "Subarchitecture Type"
        default X86_PC
@@ -178,35 +207,6 @@ config HPET_EMULATE_RTC
        depends on HPET_TIMER && RTC=y
        default y
 
-config SMP
-       bool "Symmetric multi-processing support"
-       ---help---
-         This enables support for systems with more than one CPU. If you have
-         a system with only one CPU, like most personal computers, say N. If
-         you have a system with more than one CPU, say Y.
-
-         If you say N here, the kernel will run on single and multiprocessor
-         machines, but will use only one CPU of a multiprocessor machine. If
-         you say Y here, the kernel will run on many, but not all,
-         singleprocessor machines. On a singleprocessor machine, the kernel
-         will run faster if you say N here.
-
-         Note that if you say Y here and choose architecture "586" or
-         "Pentium" under "Processor family", the kernel will not work on 486
-         architectures. Similarly, multiprocessor kernels for the "PPro"
-         architecture may not work on all Pentium based boards.
-
-         People using multiprocessor machines who say Y here should also say
-         Y to "Enhanced Real Time Clock Support", below. The "Advanced Power
-         Management" code will be disabled if you say Y here.
-
-         See also the <file:Documentation/smp.txt>,
-         <file:Documentation/i386/IO-APIC.txt>,
-         <file:Documentation/nmi_watchdog.txt> and the SMP-HOWTO available at
-         <http://www.tldp.org/docs.html#howto>.
-
-         If you don't know what to do here, say N.
-
 config NR_CPUS
        int "Maximum number of CPUs (2-255)"
        range 2 255
@@ -522,6 +522,12 @@ config NUMA
 comment "NUMA (Summit) requires SMP, 64GB highmem support, ACPI"
        depends on X86_SUMMIT && (!HIGHMEM64G || !ACPI)
 
+config NODES_SHIFT
+       int
+       default "4" if X86_NUMAQ
+       default "3"
+       depends on NEED_MULTIPLE_NODES
+
 config HAVE_ARCH_BOOTMEM_NODE
        bool
        depends on NUMA
@@ -757,15 +763,6 @@ config HOTPLUG_CPU
 
          Say N.
 
-config DOUBLEFAULT
-       default y
-       bool "Enable doublefault exception handler" if EMBEDDED
-       help
-          This option allows trapping of rare doublefault exceptions that
-          would otherwise cause a system to silently reboot. Disabling this
-          option saves about 4k and might cause you much additional grey
-          hair.
-
 endmenu
 
 
index 79603b3471f96ef13e2836bc2a54c9db7e288132..eb130482ba186663a6411fa1b7d48fff652f3e72 100644 (file)
@@ -311,5 +311,5 @@ config X86_OOSTORE
 
 config X86_TSC
        bool
-       depends on (MWINCHIP3D || MWINCHIP2 || MCRUSOE || MEFFICEON || MCYRIXIII || MK7 || MK6 || MPENTIUM4 || MPENTIUMM || MPENTIUMIII || MPENTIUMII || M686 || M586MMX || M586TSC || MK8 || MVIAC3_2 || MGEODEGX1) && !X86_NUMAQ
+       depends on (MWINCHIP3D || MWINCHIP2 || MCRUSOE || MEFFICEON || MCYRIXIII || MK7 || MK6 || MPENTIUM4 || MPENTIUMM || MPENTIUMIII || MPENTIUMII || M686 || M586MMX || M586TSC || MK8 || MVIAC3_2 || MGEODEGX1 || MGEODE_LX) && !X86_NUMAQ
        default y
index 6e97df6979e859cd9e82b4c47d40a13f0af197d0..c92191b1fb672935527bccbadfdd129065306edb 100644 (file)
@@ -81,4 +81,13 @@ config X86_MPPARSE
        depends on X86_LOCAL_APIC && !X86_VISWS
        default y
 
+config DOUBLEFAULT
+       default y
+       bool "Enable doublefault exception handler" if EMBEDDED
+       help
+          This option allows trapping of rare doublefault exceptions that
+          would otherwise cause a system to silently reboot. Disabling this
+          option saves about 4k and might cause you much additional grey
+          hair.
+
 endmenu
index 0000a26745372abd273e6ebba7c040b0946948bc..c9343c3a8082c4d1d2e8fe906c1a757e7fd918d4 100644 (file)
@@ -97,6 +97,7 @@
 #define PARAM_VESAPM_OFF       0x30
 #define PARAM_LFB_PAGES                0x32
 #define PARAM_VESA_ATTRIB      0x34
+#define PARAM_CAPABILITIES     0x36
 
 /* Define DO_STORE according to CONFIG_VIDEO_RETAIN */
 #ifdef CONFIG_VIDEO_RETAIN
@@ -233,6 +234,10 @@ mopar_gr:
        movw    18(%di), %ax
        movl    %eax, %fs:(PARAM_LFB_SIZE)
 
+# store mode capabilities
+       movl 10(%di), %eax
+       movl %eax, %fs:(PARAM_CAPABILITIES)
+
 # switching the DAC to 8-bit is for <= 8 bpp only
        movw    %fs:(PARAM_LFB_DEPTH), %ax
        cmpw    $8, %ax
index 5b9ed21216cfd2fbb9199992370a5f4a57a68253..96fb8a020af25938eef052da80846f6a4c767c70 100644 (file)
@@ -6,7 +6,7 @@ extra-y := head.o init_task.o vmlinux.lds
 
 obj-y  := process.o semaphore.o signal.o entry.o traps.o irq.o \
                ptrace.o time.o ioport.o ldt.o setup.o i8259.o sys_i386.o \
-               pci-dma.o i386_ksyms.o i387.o dmi_scan.o bootflag.o \
+               pci-dma.o i386_ksyms.o i387.o bootflag.o \
                quirks.o i8237.o topology.o alternative.o
 
 obj-y                          += cpu/
index 033066176b3efdae5a097ca5cf11fbf4b8cd945f..049a25583793a26cd85201a0e69a190880fa24c7 100644 (file)
@@ -215,7 +215,7 @@ static int __init acpi_parse_madt(unsigned long phys_addr, unsigned long size)
 {
        struct acpi_table_madt *madt = NULL;
 
-       if (!phys_addr || !size)
+       if (!phys_addr || !size || !cpu_has_apic)
                return -EINVAL;
 
        madt = (struct acpi_table_madt *)__acpi_map_table(phys_addr, size);
@@ -693,6 +693,9 @@ static int __init acpi_parse_madt_lapic_entries(void)
 {
        int count;
 
+       if (!cpu_has_apic)
+               return -ENODEV;
+
        /* 
         * Note that the LAPIC address is obtained from the MADT (32-bit value)
         * and (optionally) overriden by a LAPIC_ADDR_OVR entry (64-bit value).
@@ -751,6 +754,9 @@ static int __init acpi_parse_madt_ioapic_entries(void)
                return -ENODEV;
        }
 
+       if (!cpu_has_apic)
+               return -ENODEV;
+
        /*
         * if "noapic" boot option, don't look for IO-APICs
         */
@@ -1096,6 +1102,9 @@ int __init acpi_boot_table_init(void)
        dmi_check_system(acpi_dmi_table);
 #endif
 
+       if (!cpu_has_apic)
+               return -ENODEV;
+
        /*
         * If acpi_disabled, bail out
         * One exception: acpi=ht continues far enough to enumerate LAPICs
index 6273bf74c2031e1cf8856aca5658b8de433a77c3..254cee9f0b7b352675b23ff9b94f69114bd07dd6 100644 (file)
@@ -62,6 +62,18 @@ int apic_verbosity;
 
 static void apic_pm_activate(void);
 
+int modern_apic(void)
+{
+       unsigned int lvr, version;
+       /* AMD systems use old APIC versions, so check the CPU */
+       if (boot_cpu_data.x86_vendor == X86_VENDOR_AMD &&
+               boot_cpu_data.x86 >= 0xf)
+               return 1;
+       lvr = apic_read(APIC_LVR);
+       version = GET_APIC_VERSION(lvr);
+       return version >= 0x14;
+}
+
 /*
  * 'what should we do if we get a hw irq event on an illegal vector'.
  * each architecture has to answer this themselves.
@@ -119,10 +131,7 @@ void enable_NMI_through_LVT0 (void * dummy)
 
 int get_physical_broadcast(void)
 {
-       unsigned int lvr, version;
-       lvr = apic_read(APIC_LVR);
-       version = GET_APIC_VERSION(lvr);
-       if (!APIC_INTEGRATED(version) || version >= 0x14)
+       if (modern_apic())
                return 0xff;
        else
                return 0xf;
@@ -349,9 +358,9 @@ int __init verify_local_APIC(void)
 
 void __init sync_Arb_IDs(void)
 {
-       /* Unsupported on P4 - see Intel Dev. Manual Vol. 3, Ch. 8.6.1 */
-       unsigned int ver = GET_APIC_VERSION(apic_read(APIC_LVR));
-       if (ver >= 0x14)        /* P4 or higher */
+       /* Unsupported on P4 - see Intel Dev. Manual Vol. 3, Ch. 8.6.1
+          And not needed on AMD */
+       if (modern_apic())
                return;
        /*
         * Wait for idle.
index da30a374dd4efba117ecf8de4b10a4fdfb59f920..df0e1745f189764174a70bb3d5430e36a290a0f1 100644 (file)
@@ -1079,7 +1079,7 @@ static int apm_console_blank(int blank)
                        break;
        }
 
-       if (error == APM_NOT_ENGAGED && state != APM_STATE_READY) {
+       if (error == APM_NOT_ENGAGED) {
                static int tried;
                int eng_error;
                if (tried++ == 0) {
index 0810f81f2a05d154cf0bc8bcd4885129eef831d8..786d1a57048b9156396a7f7d5739306097420c60 100644 (file)
@@ -207,13 +207,13 @@ static void __init init_amd(struct cpuinfo_x86 *c)
                set_bit(X86_FEATURE_K7, c->x86_capability); 
                break;
        }
+       if (c->x86 >= 6)
+               set_bit(X86_FEATURE_FXSAVE_LEAK, c->x86_capability);
 
        display_cacheinfo(c);
 
        if (cpuid_eax(0x80000000) >= 0x80000008) {
                c->x86_max_cores = (cpuid_ecx(0x80000008) & 0xff) + 1;
-               if (c->x86_max_cores & (c->x86_max_cores - 1))
-                       c->x86_max_cores = 1;
        }
 
        if (cpuid_eax(0x80000000) >= 0x80000007) {
index 712a26bd4457901618f81615a8b049eef6a9c93c..71fffa17442530949dccf45aa210c2e371188a59 100644 (file)
@@ -46,7 +46,7 @@
 
 #define PFX "powernow-k8: "
 #define BFX PFX "BIOS error: "
-#define VERSION "version 1.60.1"
+#define VERSION "version 1.60.2"
 #include "powernow-k8.h"
 
 /* serialize freq changes  */
@@ -55,7 +55,7 @@ static DEFINE_MUTEX(fidvid_mutex);
 static struct powernow_k8_data *powernow_data[NR_CPUS];
 
 #ifndef CONFIG_SMP
-static cpumask_t cpu_core_map[1] = { CPU_MASK_ALL };
+static cpumask_t cpu_core_map[1];
 #endif
 
 /* Return a frequency in MHz, given an input fid */
@@ -905,11 +905,17 @@ static int powernowk8_target(struct cpufreq_policy *pol, unsigned targfreq, unsi
 {
        cpumask_t oldmask = CPU_MASK_ALL;
        struct powernow_k8_data *data = powernow_data[pol->cpu];
-       u32 checkfid = data->currfid;
-       u32 checkvid = data->currvid;
+       u32 checkfid;
+       u32 checkvid;
        unsigned int newstate;
        int ret = -EIO;
 
+       if (!data)
+               return -EINVAL;
+
+       checkfid = data->currfid;
+       checkvid = data->currvid;
+
        /* only run on specific CPU from here on */
        oldmask = current->cpus_allowed;
        set_cpus_allowed(current, cpumask_of_cpu(pol->cpu));
@@ -969,6 +975,9 @@ static int powernowk8_verify(struct cpufreq_policy *pol)
 {
        struct powernow_k8_data *data = powernow_data[pol->cpu];
 
+       if (!data)
+               return -EINVAL;
+
        return cpufreq_frequency_table_verify(pol, data->powernow_table);
 }
 
@@ -977,7 +986,7 @@ static int __cpuinit powernowk8_cpu_init(struct cpufreq_policy *pol)
 {
        struct powernow_k8_data *data;
        cpumask_t oldmask = CPU_MASK_ALL;
-       int rc, i;
+       int rc;
 
        if (!cpu_online(pol->cpu))
                return -ENODEV;
@@ -1063,8 +1072,7 @@ static int __cpuinit powernowk8_cpu_init(struct cpufreq_policy *pol)
        printk("cpu_init done, current fid 0x%x, vid 0x%x\n",
               data->currfid, data->currvid);
 
-       for_each_cpu_mask(i, cpu_core_map[pol->cpu])
-               powernow_data[i] = data;
+       powernow_data[pol->cpu] = data;
 
        return 0;
 
index 006141d1c12a080f2d3fe39464db9da8a7a7bdf7..1d9a4abcdfc71f034c1c822853049280b32de0a2 100644 (file)
@@ -168,7 +168,7 @@ static int cpuid_class_device_create(int i)
        return err;
 }
 
-static int __devinit cpuid_class_cpu_callback(struct notifier_block *nfb, unsigned long action, void *hcpu)
+static int cpuid_class_cpu_callback(struct notifier_block *nfb, unsigned long action, void *hcpu)
 {
        unsigned int cpu = (unsigned long)hcpu;
 
diff --git a/arch/i386/kernel/dmi_scan.c b/arch/i386/kernel/dmi_scan.c
deleted file mode 100644 (file)
index 5efceeb..0000000
+++ /dev/null
@@ -1,358 +0,0 @@
-#include <linux/types.h>
-#include <linux/string.h>
-#include <linux/init.h>
-#include <linux/module.h>
-#include <linux/dmi.h>
-#include <linux/efi.h>
-#include <linux/bootmem.h>
-#include <linux/slab.h>
-#include <asm/dmi.h>
-
-static char * __init dmi_string(struct dmi_header *dm, u8 s)
-{
-       u8 *bp = ((u8 *) dm) + dm->length;
-       char *str = "";
-
-       if (s) {
-               s--;
-               while (s > 0 && *bp) {
-                       bp += strlen(bp) + 1;
-                       s--;
-               }
-
-               if (*bp != 0) {
-                       str = dmi_alloc(strlen(bp) + 1);
-                       if (str != NULL)
-                               strcpy(str, bp);
-                       else
-                               printk(KERN_ERR "dmi_string: out of memory.\n");
-               }
-       }
-
-       return str;
-}
-
-/*
- *     We have to be cautious here. We have seen BIOSes with DMI pointers
- *     pointing to completely the wrong place for example
- */
-static int __init dmi_table(u32 base, int len, int num,
-                           void (*decode)(struct dmi_header *))
-{
-       u8 *buf, *data;
-       int i = 0;
-               
-       buf = dmi_ioremap(base, len);
-       if (buf == NULL)
-               return -1;
-
-       data = buf;
-
-       /*
-        *      Stop when we see all the items the table claimed to have
-        *      OR we run off the end of the table (also happens)
-        */
-       while ((i < num) && (data - buf + sizeof(struct dmi_header)) <= len) {
-               struct dmi_header *dm = (struct dmi_header *)data;
-               /*
-                *  We want to know the total length (formated area and strings)
-                *  before decoding to make sure we won't run off the table in
-                *  dmi_decode or dmi_string
-                */
-               data += dm->length;
-               while ((data - buf < len - 1) && (data[0] || data[1]))
-                       data++;
-               if (data - buf < len - 1)
-                       decode(dm);
-               data += 2;
-               i++;
-       }
-       dmi_iounmap(buf, len);
-       return 0;
-}
-
-static int __init dmi_checksum(u8 *buf)
-{
-       u8 sum = 0;
-       int a;
-       
-       for (a = 0; a < 15; a++)
-               sum += buf[a];
-
-       return sum == 0;
-}
-
-static char *dmi_ident[DMI_STRING_MAX];
-static LIST_HEAD(dmi_devices);
-
-/*
- *     Save a DMI string
- */
-static void __init dmi_save_ident(struct dmi_header *dm, int slot, int string)
-{
-       char *p, *d = (char*) dm;
-
-       if (dmi_ident[slot])
-               return;
-
-       p = dmi_string(dm, d[string]);
-       if (p == NULL)
-               return;
-
-       dmi_ident[slot] = p;
-}
-
-static void __init dmi_save_devices(struct dmi_header *dm)
-{
-       int i, count = (dm->length - sizeof(struct dmi_header)) / 2;
-       struct dmi_device *dev;
-
-       for (i = 0; i < count; i++) {
-               char *d = (char *)(dm + 1) + (i * 2);
-
-               /* Skip disabled device */
-               if ((*d & 0x80) == 0)
-                       continue;
-
-               dev = dmi_alloc(sizeof(*dev));
-               if (!dev) {
-                       printk(KERN_ERR "dmi_save_devices: out of memory.\n");
-                       break;
-               }
-
-               dev->type = *d++ & 0x7f;
-               dev->name = dmi_string(dm, *d);
-               dev->device_data = NULL;
-
-               list_add(&dev->list, &dmi_devices);
-       }
-}
-
-static void __init dmi_save_ipmi_device(struct dmi_header *dm)
-{
-       struct dmi_device *dev;
-       void * data;
-
-       data = dmi_alloc(dm->length);
-       if (data == NULL) {
-               printk(KERN_ERR "dmi_save_ipmi_device: out of memory.\n");
-               return;
-       }
-
-       memcpy(data, dm, dm->length);
-
-       dev = dmi_alloc(sizeof(*dev));
-       if (!dev) {
-               printk(KERN_ERR "dmi_save_ipmi_device: out of memory.\n");
-               return;
-       }
-
-       dev->type = DMI_DEV_TYPE_IPMI;
-       dev->name = "IPMI controller";
-       dev->device_data = data;
-
-       list_add(&dev->list, &dmi_devices);
-}
-
-/*
- *     Process a DMI table entry. Right now all we care about are the BIOS
- *     and machine entries. For 2.5 we should pull the smbus controller info
- *     out of here.
- */
-static void __init dmi_decode(struct dmi_header *dm)
-{
-       switch(dm->type) {
-       case 0:         /* BIOS Information */
-               dmi_save_ident(dm, DMI_BIOS_VENDOR, 4);
-               dmi_save_ident(dm, DMI_BIOS_VERSION, 5);
-               dmi_save_ident(dm, DMI_BIOS_DATE, 8);
-               break;
-       case 1:         /* System Information */
-               dmi_save_ident(dm, DMI_SYS_VENDOR, 4);
-               dmi_save_ident(dm, DMI_PRODUCT_NAME, 5);
-               dmi_save_ident(dm, DMI_PRODUCT_VERSION, 6);
-               dmi_save_ident(dm, DMI_PRODUCT_SERIAL, 7);
-               break;
-       case 2:         /* Base Board Information */
-               dmi_save_ident(dm, DMI_BOARD_VENDOR, 4);
-               dmi_save_ident(dm, DMI_BOARD_NAME, 5);
-               dmi_save_ident(dm, DMI_BOARD_VERSION, 6);
-               break;
-       case 10:        /* Onboard Devices Information */
-               dmi_save_devices(dm);
-               break;
-       case 38:        /* IPMI Device Information */
-               dmi_save_ipmi_device(dm);
-       }
-}
-
-static int __init dmi_present(char __iomem *p)
-{
-       u8 buf[15];
-       memcpy_fromio(buf, p, 15);
-       if ((memcmp(buf, "_DMI_", 5) == 0) && dmi_checksum(buf)) {
-               u16 num = (buf[13] << 8) | buf[12];
-               u16 len = (buf[7] << 8) | buf[6];
-               u32 base = (buf[11] << 24) | (buf[10] << 16) |
-                       (buf[9] << 8) | buf[8];
-
-               /*
-                * DMI version 0.0 means that the real version is taken from
-                * the SMBIOS version, which we don't know at this point.
-                */
-               if (buf[14] != 0)
-                       printk(KERN_INFO "DMI %d.%d present.\n",
-                              buf[14] >> 4, buf[14] & 0xF);
-               else
-                       printk(KERN_INFO "DMI present.\n");
-               if (dmi_table(base,len, num, dmi_decode) == 0)
-                       return 0;
-       }
-       return 1;
-}
-
-void __init dmi_scan_machine(void)
-{
-       char __iomem *p, *q;
-       int rc;
-
-       if (efi_enabled) {
-               if (efi.smbios == EFI_INVALID_TABLE_ADDR)
-                       goto out;
-
-               /* This is called as a core_initcall() because it isn't
-                * needed during early boot.  This also means we can
-                * iounmap the space when we're done with it.
-               */
-               p = dmi_ioremap(efi.smbios, 32);
-               if (p == NULL)
-                       goto out;
-
-               rc = dmi_present(p + 0x10); /* offset of _DMI_ string */
-               dmi_iounmap(p, 32);
-               if (!rc)
-                       return;
-       }
-       else {
-               /*
-                * no iounmap() for that ioremap(); it would be a no-op, but
-                * it's so early in setup that sucker gets confused into doing
-                * what it shouldn't if we actually call it.
-                */
-               p = dmi_ioremap(0xF0000, 0x10000);
-               if (p == NULL)
-                       goto out;
-
-               for (q = p; q < p + 0x10000; q += 16) {
-                       rc = dmi_present(q);
-                       if (!rc)
-                               return;
-               }
-       }
- out:  printk(KERN_INFO "DMI not present or invalid.\n");
-}
-
-/**
- *     dmi_check_system - check system DMI data
- *     @list: array of dmi_system_id structures to match against
- *
- *     Walk the blacklist table running matching functions until someone
- *     returns non zero or we hit the end. Callback function is called for
- *     each successfull match. Returns the number of matches.
- */
-int dmi_check_system(struct dmi_system_id *list)
-{
-       int i, count = 0;
-       struct dmi_system_id *d = list;
-
-       while (d->ident) {
-               for (i = 0; i < ARRAY_SIZE(d->matches); i++) {
-                       int s = d->matches[i].slot;
-                       if (s == DMI_NONE)
-                               continue;
-                       if (dmi_ident[s] && strstr(dmi_ident[s], d->matches[i].substr))
-                               continue;
-                       /* No match */
-                       goto fail;
-               }
-               count++;
-               if (d->callback && d->callback(d))
-                       break;
-fail:          d++;
-       }
-
-       return count;
-}
-EXPORT_SYMBOL(dmi_check_system);
-
-/**
- *     dmi_get_system_info - return DMI data value
- *     @field: data index (see enum dmi_filed)
- *
- *     Returns one DMI data value, can be used to perform
- *     complex DMI data checks.
- */
-char *dmi_get_system_info(int field)
-{
-       return dmi_ident[field];
-}
-EXPORT_SYMBOL(dmi_get_system_info);
-
-/**
- *     dmi_find_device - find onboard device by type/name
- *     @type: device type or %DMI_DEV_TYPE_ANY to match all device types
- *     @desc: device name string or %NULL to match all
- *     @from: previous device found in search, or %NULL for new search.
- *
- *     Iterates through the list of known onboard devices. If a device is
- *     found with a matching @vendor and @device, a pointer to its device
- *     structure is returned.  Otherwise, %NULL is returned.
- *     A new search is initiated by passing %NULL to the @from argument.
- *     If @from is not %NULL, searches continue from next device.
- */
-struct dmi_device * dmi_find_device(int type, const char *name,
-                                   struct dmi_device *from)
-{
-       struct list_head *d, *head = from ? &from->list : &dmi_devices;
-
-       for(d = head->next; d != &dmi_devices; d = d->next) {
-               struct dmi_device *dev = list_entry(d, struct dmi_device, list);
-
-               if (((type == DMI_DEV_TYPE_ANY) || (dev->type == type)) &&
-                   ((name == NULL) || (strcmp(dev->name, name) == 0)))
-                       return dev;
-       }
-
-       return NULL;
-}
-EXPORT_SYMBOL(dmi_find_device);
-
-/**
- *     dmi_get_year - Return year of a DMI date
- *     @field: data index (like dmi_get_system_info)
- *
- *     Returns -1 when the field doesn't exist. 0 when it is broken.
- */
-int dmi_get_year(int field)
-{
-       int year;
-       char *s = dmi_get_system_info(field);
-
-       if (!s)
-               return -1;
-       if (*s == '\0')
-               return 0;
-       s = strrchr(s, '/');
-       if (!s)
-               return 0;
-
-       s += 1;
-       year = simple_strtoul(s, NULL, 0);
-       if (year && year < 100) {       /* 2-digit year */
-               year += 1900;
-               if (year < 1996)        /* no dates < spec 1.0 */
-                       year += 100;
-       }
-
-       return year;
-}
index 055325056a74aa7769d658b459f4840d7ffa328c..036a9857936fa26816ca97b3a74021399909a0e8 100644 (file)
@@ -19,7 +19,6 @@ EXPORT_SYMBOL(__put_user_2);
 EXPORT_SYMBOL(__put_user_4);
 EXPORT_SYMBOL(__put_user_8);
 
-EXPORT_SYMBOL(strpbrk);
 EXPORT_SYMBOL(strstr);
 
 #ifdef CONFIG_SMP
index f19768789e8a607203023d7ba3788efbc7bc3c1b..043f5292e70a203eda9ed4051331227adc6bffa5 100644 (file)
@@ -43,7 +43,7 @@ DEFINE_PER_CPU(struct kprobe *, current_kprobe) = NULL;
 DEFINE_PER_CPU(struct kprobe_ctlblk, kprobe_ctlblk);
 
 /* insert a jmp code */
-static inline void set_jmp_op(void *from, void *to)
+static __always_inline void set_jmp_op(void *from, void *to)
 {
        struct __arch_jmp_op {
                char op;
@@ -57,7 +57,7 @@ static inline void set_jmp_op(void *from, void *to)
 /*
  * returns non-zero if opcodes can be boosted.
  */
-static inline int can_boost(kprobe_opcode_t opcode)
+static __always_inline int can_boost(kprobe_opcode_t opcode)
 {
        switch (opcode & 0xf0 ) {
        case 0x70:
@@ -88,7 +88,7 @@ static inline int can_boost(kprobe_opcode_t opcode)
 /*
  * returns non-zero if opcode modifies the interrupt flag.
  */
-static inline int is_IF_modifier(kprobe_opcode_t opcode)
+static int __kprobes is_IF_modifier(kprobe_opcode_t opcode)
 {
        switch (opcode) {
        case 0xfa:              /* cli */
@@ -138,7 +138,7 @@ void __kprobes arch_remove_kprobe(struct kprobe *p)
        mutex_unlock(&kprobe_mutex);
 }
 
-static inline void save_previous_kprobe(struct kprobe_ctlblk *kcb)
+static void __kprobes save_previous_kprobe(struct kprobe_ctlblk *kcb)
 {
        kcb->prev_kprobe.kp = kprobe_running();
        kcb->prev_kprobe.status = kcb->kprobe_status;
@@ -146,7 +146,7 @@ static inline void save_previous_kprobe(struct kprobe_ctlblk *kcb)
        kcb->prev_kprobe.saved_eflags = kcb->kprobe_saved_eflags;
 }
 
-static inline void restore_previous_kprobe(struct kprobe_ctlblk *kcb)
+static void __kprobes restore_previous_kprobe(struct kprobe_ctlblk *kcb)
 {
        __get_cpu_var(current_kprobe) = kcb->prev_kprobe.kp;
        kcb->kprobe_status = kcb->prev_kprobe.status;
@@ -154,7 +154,7 @@ static inline void restore_previous_kprobe(struct kprobe_ctlblk *kcb)
        kcb->kprobe_saved_eflags = kcb->prev_kprobe.saved_eflags;
 }
 
-static inline void set_current_kprobe(struct kprobe *p, struct pt_regs *regs,
+static void __kprobes set_current_kprobe(struct kprobe *p, struct pt_regs *regs,
                                struct kprobe_ctlblk *kcb)
 {
        __get_cpu_var(current_kprobe) = p;
@@ -164,7 +164,7 @@ static inline void set_current_kprobe(struct kprobe *p, struct pt_regs *regs,
                kcb->kprobe_saved_eflags &= ~IF_MASK;
 }
 
-static inline void prepare_singlestep(struct kprobe *p, struct pt_regs *regs)
+static void __kprobes prepare_singlestep(struct kprobe *p, struct pt_regs *regs)
 {
        regs->eflags |= TF_MASK;
        regs->eflags &= ~IF_MASK;
@@ -507,7 +507,7 @@ no_change:
  * Interrupts are disabled on entry as trap1 is an interrupt gate and they
  * remain disabled thoroughout this function.
  */
-static inline int post_kprobe_handler(struct pt_regs *regs)
+static int __kprobes post_kprobe_handler(struct pt_regs *regs)
 {
        struct kprobe *cur = kprobe_running();
        struct kprobe_ctlblk *kcb = get_kprobe_ctlblk();
@@ -543,7 +543,7 @@ out:
        return 1;
 }
 
-static inline int kprobe_fault_handler(struct pt_regs *regs, int trapnr)
+static int __kprobes kprobe_fault_handler(struct pt_regs *regs, int trapnr)
 {
        struct kprobe *cur = kprobe_running();
        struct kprobe_ctlblk *kcb = get_kprobe_ctlblk();
index 8d8aa9d1796d5cdf02d9d3ccc5aff3e4b1f9ef0d..34d21e21e0124b89830fa2db7589a9ba06217e96 100644 (file)
 int smp_found_config;
 unsigned int __initdata maxcpus = NR_CPUS;
 
-#ifdef CONFIG_HOTPLUG_CPU
-#define CPU_HOTPLUG_ENABLED    (1)
-#else
-#define CPU_HOTPLUG_ENABLED    (0)
-#endif
-
 /*
  * Various Linux-internal data structures created from the
  * MP-table.
@@ -110,21 +104,6 @@ static int __init mpf_checksum(unsigned char *mp, int len)
 static int mpc_record; 
 static struct mpc_config_translation *translation_table[MAX_MPC_ENTRY] __initdata;
 
-#ifdef CONFIG_X86_NUMAQ
-static int MP_valid_apicid(int apicid, int version)
-{
-       return hweight_long(apicid & 0xf) == 1 && (apicid >> 4) != 0xf;
-}
-#else
-static int MP_valid_apicid(int apicid, int version)
-{
-       if (version >= 0x14)
-               return apicid < 0xff;
-       else
-               return apicid < 0xf;
-}
-#endif
-
 static void __devinit MP_processor_info (struct mpc_config_processor *m)
 {
        int ver, apicid;
@@ -190,12 +169,6 @@ static void __devinit MP_processor_info (struct mpc_config_processor *m)
 
        ver = m->mpc_apicver;
 
-       if (!MP_valid_apicid(apicid, ver)) {
-               printk(KERN_WARNING "Processor #%d INVALID. (Max ID: %d).\n",
-                       m->mpc_apicid, MAX_APICS);
-               return;
-       }
-
        /*
         * Validate version
         */
@@ -225,7 +198,14 @@ static void __devinit MP_processor_info (struct mpc_config_processor *m)
        cpu_set(num_processors, cpu_possible_map);
        num_processors++;
 
-       if (CPU_HOTPLUG_ENABLED || (num_processors > 8)) {
+       /*
+        * Would be preferable to switch to bigsmp when CONFIG_HOTPLUG_CPU=y
+        * but we need to work other dependencies like SMP_SUSPEND etc
+        * before this can be done without some confusion.
+        * if (CPU_HOTPLUG_ENABLED || num_processors > 8)
+        *       - Ashok Raj <ashok.raj@intel.com>
+        */
+       if (num_processors > 8) {
                switch (boot_cpu_data.x86_vendor) {
                case X86_VENDOR_INTEL:
                        if (!APIC_XAPIC(ver)) {
@@ -249,6 +229,13 @@ static void __init MP_bus_info (struct mpc_config_bus *m)
 
        mpc_oem_bus_info(m, str, translation_table[mpc_record]);
 
+       if (m->mpc_busid >= MAX_MP_BUSSES) {
+               printk(KERN_WARNING "MP table busid value (%d) for bustype %s "
+                       " is too large, max. supported is %d\n",
+                       m->mpc_busid, str, MAX_MP_BUSSES - 1);
+               return;
+       }
+
        if (strncmp(str, BUSTYPE_ISA, sizeof(BUSTYPE_ISA)-1) == 0) {
                mp_bus_id_to_type[m->mpc_busid] = MP_BUS_ISA;
        } else if (strncmp(str, BUSTYPE_EISA, sizeof(BUSTYPE_EISA)-1) == 0) {
index 1d0a55e687602ff49be8aed13771e76a1c43c3d2..7a328230e540f8b073e5d0306f457a1a9bffbc28 100644 (file)
@@ -251,7 +251,7 @@ static int msr_class_device_create(int i)
        return err;
 }
 
-static int __devinit msr_class_cpu_callback(struct notifier_block *nfb, unsigned long action, void *hcpu)
+static int msr_class_cpu_callback(struct notifier_block *nfb, unsigned long action, void *hcpu)
 {
        unsigned int cpu = (unsigned long)hcpu;
 
index 10e21a4773dd4e822a82d461c4d1ee17f3f7164d..99aab41a05b0f17d12c07110638699a6ec4360da 100644 (file)
@@ -51,7 +51,5 @@ void mach_reboot_fixups(void)
 
                cur->reboot_fixup(dev);
        }
-
-       printk(KERN_WARNING "No reboot fixup found for your hardware\n");
 }
 
index eacc3f0a2ea4de5b334f8172cce979570eddc133..80cb3b2d0997986a778b504f34b2a2e5d6b7b6fe 100644 (file)
@@ -963,6 +963,36 @@ efi_memory_present_wrapper(unsigned long start, unsigned long end, void *arg)
        return 0;
 }
 
+ /*
+  * This function checks if the entire range <start,end> is mapped with type.
+  *
+  * Note: this function only works correct if the e820 table is sorted and
+  * not-overlapping, which is the case
+  */
+int __init
+e820_all_mapped(unsigned long start, unsigned long end, unsigned type)
+{
+       int i;
+       for (i = 0; i < e820.nr_map; i++) {
+               struct e820entry *ei = &e820.map[i];
+               if (type && ei->type != type)
+                       continue;
+               /* is the region (part) in overlap with the current region ?*/
+               if (ei->addr >= end || ei->addr + ei->size <= start)
+                       continue;
+               /* if the region is at the beginning of <start,end> we move
+                * start to the end of the region since it's ok until there
+                */
+               if (ei->addr <= start)
+                       start = ei->addr + ei->size;
+               /* if start is now at or beyond end, we're done, full
+                * coverage */
+               if (start >= end)
+                       return 1; /* we're done */
+       }
+       return 0;
+}
+
 /*
  * Find the highest page frame number we have available
  */
@@ -1317,8 +1347,8 @@ legacy_init_iomem_resources(struct resource *code_resource, struct resource *dat
 /*
  * Request address space for all standard resources
  *
- * This is called just before pcibios_assign_resources(), which is also
- * an fs_initcall, but is linked in later (in arch/i386/pci/i386.c).
+ * This is called just before pcibios_init(), which is also a
+ * subsys_initcall, but is linked in later (in arch/i386/pci/common.c).
  */
 static int __init request_standard_resources(void)
 {
@@ -1339,7 +1369,7 @@ static int __init request_standard_resources(void)
        return 0;
 }
 
-fs_initcall(request_standard_resources);
+subsys_initcall(request_standard_resources);
 
 static void __init register_memory(void)
 {
index 4f58b9c0efe3cbb5f57a2bfda39371153b3eff2f..f48bef15b4f0dd5de72d4bbcc39f8c4f881947b6 100644 (file)
@@ -314,3 +314,4 @@ ENTRY(sys_call_table)
        .long sys_get_robust_list
        .long sys_splice
        .long sys_sync_file_range
+       .long sys_tee                   /* 315 */
index e38527994590f8ba12d19ea125e4c18aeb2fc96a..2d22f5761b1dc51ac6bee90789e1e867ad62e779 100644 (file)
@@ -365,6 +365,9 @@ void die(const char * str, struct pt_regs * regs, long err)
 
        if (++die.lock_owner_depth < 3) {
                int nl = 0;
+               unsigned long esp;
+               unsigned short ss;
+
                handle_BUG(regs);
                printk(KERN_EMERG "%s: %04lx [#%d]\n", str, err & 0xffff, ++die_counter);
 #ifdef CONFIG_PREEMPT
@@ -387,8 +390,19 @@ void die(const char * str, struct pt_regs * regs, long err)
                        printk("\n");
                if (notify_die(DIE_OOPS, str, regs, err,
                                        current->thread.trap_no, SIGSEGV) !=
-                               NOTIFY_STOP)
+                               NOTIFY_STOP) {
                        show_registers(regs);
+                       /* Executive summary in case the oops scrolled away */
+                       esp = (unsigned long) (&regs->esp);
+                       savesegment(ss, ss);
+                       if (user_mode(regs)) {
+                               esp = regs->esp;
+                               ss = regs->xss & 0xffff;
+                       }
+                       printk(KERN_EMERG "EIP: [<%08lx>] ", regs->eip);
+                       print_symbol("%s", regs->eip);
+                       printk(" SS:ESP %04x:%08lx\n", ss, esp);
+               }
                else
                        regs = NULL;
        } else
index 23967fe658d3ff5be1981b93cfb547b86a9ec6e6..10d21df1453143c5c8d6c33c629a6267985f2385 100644 (file)
@@ -106,15 +106,20 @@ voyager_module_t *voyager_cat_list;
 
 /* the I/O port assignments for the VIC and QIC */
 static struct resource vic_res = {
-       "Voyager Interrupt Controller", 0xFC00, 0xFC6F };
+       .name   = "Voyager Interrupt Controller",
+       .start  = 0xFC00,
+       .end    = 0xFC6F
+};
 static struct resource qic_res = {
-       "Quad Interrupt Controller", 0xFC70, 0xFCFF };
+       .name   = "Quad Interrupt Controller",
+       .start  = 0xFC70,
+       .end    = 0xFCFF
+};
 
 /* This function is used to pack a data bit stream inside a message.
  * It writes num_bits of the data buffer in msg starting at start_bit.
  * Note: This function assumes that any unused bit in the data stream
  * is set to zero so that the ors will work correctly */
-#define BITS_PER_BYTE 8
 static void
 cat_pack(__u8 *msg, const __u16 start_bit, __u8 *data, const __u16 num_bits)
 {
index 9f66ac582a8bf77eaff771c16294cdbcff3a6756..ae6534ad816113d40b05cc514e2626adf26a5de6 100644 (file)
@@ -651,6 +651,7 @@ void __init mem_init(void)
  * Specifically, in the case of x86, we will always add
  * memory to the highmem for now.
  */
+#ifdef CONFIG_HOTPLUG_MEMORY
 #ifndef CONFIG_NEED_MULTIPLE_NODES
 int add_memory(u64 start, u64 size)
 {
@@ -667,6 +668,7 @@ int remove_memory(u64 start, u64 size)
        return -EINVAL;
 }
 #endif
+#endif
 
 kmem_cache_t *pgd_cache;
 kmem_cache_t *pmd_cache;
index 99012b93bd12b9f66e853eb08706be58e301171e..5d81fb51037551b9ede92c2f0f7f785a2a6e4e2e 100644 (file)
@@ -4,6 +4,7 @@
 
 #include <linux/pci.h>
 #include <linux/init.h>
+#include <linux/dmi.h>
 #include "pci.h"
 
 /*
@@ -18,8 +19,10 @@ int pci_conf1_read(unsigned int seg, unsigned int bus,
 {
        unsigned long flags;
 
-       if (!value || (bus > 255) || (devfn > 255) || (reg > 255))
+       if ((bus > 255) || (devfn > 255) || (reg > 255)) {
+               *value = -1;
                return -EINVAL;
+       }
 
        spin_lock_irqsave(&pci_config_lock, flags);
 
@@ -91,8 +94,10 @@ static int pci_conf2_read(unsigned int seg, unsigned int bus,
        unsigned long flags;
        int dev, fn;
 
-       if (!value || (bus > 255) || (devfn > 255) || (reg > 255))
+       if ((bus > 255) || (devfn > 255) || (reg > 255)) {
+               *value = -1;
                return -EINVAL;
+       }
 
        dev = PCI_SLOT(devfn);
        fn = PCI_FUNC(devfn);
@@ -188,6 +193,10 @@ static int __init pci_sanity_check(struct pci_raw_ops *o)
 
        if (pci_probe & PCI_NO_CHECKS)
                return 1;
+       /* Assume Type 1 works for newer systems.
+          This handles machines that don't have anything on PCI Bus 0. */
+       if (dmi_get_year(DMI_BIOS_DATE) >= 2001)
+               return 1;
 
        for (devfn = 0; devfn < 0x100; devfn++) {
                if (o->read(0, 0, devfn, PCI_CLASS_DEVICE, 2, &x))
index 3ca59cad05f33d41ac3e663070d4e44223449a37..73235443fda732a3733380fe4e7042583b5fe887 100644 (file)
@@ -588,7 +588,10 @@ static __init int via_router_probe(struct irq_router *r,
        case PCI_DEVICE_ID_VIA_82C596:
        case PCI_DEVICE_ID_VIA_82C686:
        case PCI_DEVICE_ID_VIA_8231:
+       case PCI_DEVICE_ID_VIA_8233A:
        case PCI_DEVICE_ID_VIA_8235:
+       case PCI_DEVICE_ID_VIA_8237:
+       case PCI_DEVICE_ID_VIA_8237_SATA:
                /* FIXME: add new ones for 8233/5 */
                r->name = "VIA";
                r->get = pirq_via_get;
index 613789071f30dde13eec78efed2412ae3c399d90..6b1ea0c9a570ef7e142668dd03bc6b49a471d020 100644 (file)
 #include <linux/pci.h>
 #include <linux/init.h>
 #include <linux/acpi.h>
+#include <asm/e820.h>
 #include "pci.h"
 
+#define MMCONFIG_APER_SIZE (256*1024*1024)
+
+/* Assume systems with more busses have correct MCFG */
+#define MAX_CHECK_BUS 16
+
 #define mmcfg_virt_addr ((void __iomem *) fix_to_virt(FIX_PCIE_MCFG))
 
 /* The base address of the last MMCONFIG device accessed */
 static u32 mmcfg_last_accessed_device;
 
-static DECLARE_BITMAP(fallback_slots, 32);
+static DECLARE_BITMAP(fallback_slots, MAX_CHECK_BUS*32);
 
 /*
  * Functions for accessing PCI configuration space with MMCONFIG accesses
@@ -29,8 +35,8 @@ static u32 get_base_addr(unsigned int seg, int bus, unsigned devfn)
        int cfg_num = -1;
        struct acpi_table_mcfg_config *cfg;
 
-       if (seg == 0 && bus == 0 &&
-           test_bit(PCI_SLOT(devfn), fallback_slots))
+       if (seg == 0 && bus < MAX_CHECK_BUS &&
+           test_bit(PCI_SLOT(devfn) + 32*bus, fallback_slots))
                return 0;
 
        while (1) {
@@ -74,8 +80,10 @@ static int pci_mmcfg_read(unsigned int seg, unsigned int bus,
        unsigned long flags;
        u32 base;
 
-       if (!value || (bus > 255) || (devfn > 255) || (reg > 4095))
+       if ((bus > 255) || (devfn > 255) || (reg > 4095)) {
+               *value = -1;
                return -EINVAL;
+       }
 
        base = get_base_addr(seg, bus, devfn);
        if (!base)
@@ -146,29 +154,34 @@ static struct pci_raw_ops pci_mmcfg = {
    Normally this can be expressed in the MCFG by not listing them
    and assigning suitable _SEGs, but this isn't implemented in some BIOS.
    Instead try to discover all devices on bus 0 that are unreachable using MM
-   and fallback for them.
-   We only do this for bus 0/seg 0 */
+   and fallback for them. */
 static __init void unreachable_devices(void)
 {
-       int i;
+       int i, k;
        unsigned long flags;
 
-       for (i = 0; i < 32; i++) {
-               u32 val1;
-               u32 addr;
-
-               pci_conf1_read(0, 0, PCI_DEVFN(i, 0), 0, 4, &val1);
-               if (val1 == 0xffffffff)
-                       continue;
-
-               /* Locking probably not needed, but safer */
-               spin_lock_irqsave(&pci_config_lock, flags);
-               addr = get_base_addr(0, 0, PCI_DEVFN(i, 0));
-               if (addr != 0)
-                       pci_exp_set_dev_base(addr, 0, PCI_DEVFN(i, 0));
-               if (addr == 0 || readl((u32 __iomem *)mmcfg_virt_addr) != val1)
-                       set_bit(i, fallback_slots);
-               spin_unlock_irqrestore(&pci_config_lock, flags);
+       for (k = 0; k < MAX_CHECK_BUS; k++) {
+               for (i = 0; i < 32; i++) {
+                       u32 val1;
+                       u32 addr;
+
+                       pci_conf1_read(0, k, PCI_DEVFN(i, 0), 0, 4, &val1);
+                       if (val1 == 0xffffffff)
+                               continue;
+
+                       /* Locking probably not needed, but safer */
+                       spin_lock_irqsave(&pci_config_lock, flags);
+                       addr = get_base_addr(0, k, PCI_DEVFN(i, 0));
+                       if (addr != 0)
+                               pci_exp_set_dev_base(addr, k, PCI_DEVFN(i, 0));
+                       if (addr == 0 ||
+                           readl((u32 __iomem *)mmcfg_virt_addr) != val1) {
+                               set_bit(i, fallback_slots);
+                               printk(KERN_NOTICE
+                       "PCI: No mmconfig possible on %x:%x\n", k, i);
+                       }
+                       spin_unlock_irqrestore(&pci_config_lock, flags);
+               }
        }
 }
 
@@ -183,6 +196,14 @@ void __init pci_mmcfg_init(void)
            (pci_mmcfg_config[0].base_address == 0))
                return;
 
+       if (!e820_all_mapped(pci_mmcfg_config[0].base_address,
+                       pci_mmcfg_config[0].base_address + MMCONFIG_APER_SIZE,
+                       E820_RESERVED)) {
+               printk(KERN_ERR "PCI: BIOS Bug: MCFG area is not E820-reserved\n");
+               printk(KERN_ERR "PCI: Not using MMCONFIG.\n");
+               return;
+       }
+
        printk(KERN_INFO "PCI: Using MMCONFIG\n");
        raw_pci_ops = &pci_mmcfg;
        pci_probe = (pci_probe & ~PCI_PROBE_MASK) | PCI_PROBE_MMCONF;
index edffe25a477ab597a6615288df78ebdf976a0bba..9f40eeff0b5cec3cfec4ddfc6143fc30ca852b85 100644 (file)
@@ -260,15 +260,6 @@ config NR_CPUS
          than 64 will cause the use of a CPU mask array, causing a small
          performance hit.
 
-config IA64_NR_NODES
-       int "Maximum number of NODEs (256-1024)" if (IA64_SGI_SN2 || IA64_GENERIC)
-       range 256 1024
-       depends on IA64_SGI_SN2 || IA64_GENERIC
-       default "256"
-       help
-         This option specifies the maximum number of nodes in your SSI system.
-         If in doubt, use the default.
-
 config HOTPLUG_CPU
        bool "Support for hot-pluggable CPUs (EXPERIMENTAL)"
        depends on SMP && EXPERIMENTAL
@@ -352,6 +343,16 @@ config NUMA
          Access).  This option is for configuring high-end multiprocessor
          server systems.  If in doubt, say N.
 
+config NODES_SHIFT
+       int "Max num nodes shift(3-10)"
+       range 3 10
+       default "8"
+       depends on NEED_MULTIPLE_NODES
+       help
+         This option specifies the maximum number of nodes in your SSI system.
+         MAX_NUMNODES will be 2^(This value).
+         If in doubt, use the default.
+
 # VIRTUAL_MEM_MAP and FLAT_NODE_MEM_MAP are functionally equivalent.
 # VIRTUAL_MEM_MAP has been retained for historical reasons.
 config VIRTUAL_MEM_MAP
index 59e871dae7423454edcadb968b9e0a54ca9111e1..09a0dbc17fb687bfc6e79ba6377e012246846180 100644 (file)
@@ -7,7 +7,7 @@ extra-y := head.o init_task.o vmlinux.lds
 obj-y := acpi.o entry.o efi.o efi_stub.o gate-data.o fsys.o ia64_ksyms.o irq.o irq_ia64.o      \
         irq_lsapic.o ivt.o machvec.o pal.o patch.o process.o perfmon.o ptrace.o sal.o          \
         salinfo.o semaphore.o setup.o signal.o sys_ia64.o time.o traps.o unaligned.o \
-        unwind.o mca.o mca_asm.o topology.o dmi_scan.o
+        unwind.o mca.o mca_asm.o topology.o
 
 obj-$(CONFIG_IA64_BRL_EMU)     += brl_emu.o
 obj-$(CONFIG_IA64_GENERIC)     += acpi-ext.o
@@ -30,7 +30,6 @@ obj-$(CONFIG_IA64_MCA_RECOVERY)       += mca_recovery.o
 obj-$(CONFIG_KPROBES)          += kprobes.o jprobes.o
 obj-$(CONFIG_IA64_UNCACHED_ALLOCATOR)  += uncached.o
 mca_recovery-y                 += mca_drv.o mca_drv_asm.o
-dmi_scan-y                     += ../../i386/kernel/dmi_scan.o
 
 # The gate DSO image is built using a special linker script.
 targets += gate.so gate-syms.o
index 4a5574ff007b8a1f1d5b0205d417c936b86e23f6..fff82929d225a7436618be9493d6bc38565fd5f6 100644 (file)
 /*
- * arch/ia64/kernel/acpi-ext.c
+ * (c) Copyright 2003, 2006 Hewlett-Packard Development Company, L.P.
+ *     Alex Williamson <alex.williamson@hp.com>
+ *     Bjorn Helgaas <bjorn.helgaas@hp.com>
  *
- * Copyright (C) 2003 Hewlett-Packard
- * Copyright (C) Alex Williamson
- * Copyright (C) Bjorn Helgaas
- *
- * Vendor specific extensions to ACPI.
+ * 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 <linux/config.h>
 #include <linux/module.h>
 #include <linux/types.h>
 #include <linux/acpi.h>
-#include <linux/efi.h>
 
 #include <asm/acpi-ext.h>
 
-struct acpi_vendor_descriptor {
-       u8 guid_id;
-       efi_guid_t guid;
-};
+/*
+ * Device CSRs that do not appear in PCI config space should be described
+ * via ACPI.  This would normally be done with Address Space Descriptors
+ * marked as "consumer-only," but old versions of Windows and Linux ignore
+ * the producer/consumer flag, so HP invented a vendor-defined resource to
+ * describe the location and size of CSR space.
+ */
 
-struct acpi_vendor_info {
-       struct acpi_vendor_descriptor *descriptor;
-       u8 *data;
-       u32 length;
+struct acpi_vendor_uuid hp_ccsr_uuid = {
+       .subtype = 2,
+       .data = { 0xf9, 0xad, 0xe9, 0x69, 0x4f, 0x92, 0x5f, 0xab, 0xf6, 0x4a,
+           0x24, 0xd2, 0x01, 0x37, 0x0e, 0xad },
 };
 
-acpi_status
-acpi_vendor_resource_match(struct acpi_resource *resource, void *context)
+static acpi_status hp_ccsr_locate(acpi_handle obj, u64 *base, u64 *length)
 {
-       struct acpi_vendor_info *info = (struct acpi_vendor_info *)context;
-       struct acpi_resource_vendor *vendor;
-       struct acpi_vendor_descriptor *descriptor;
-       u32 byte_length;
-
-       if (resource->type != ACPI_RESOURCE_TYPE_VENDOR)
-               return AE_OK;
-
-       vendor = (struct acpi_resource_vendor *)&resource->data;
-       descriptor = (struct acpi_vendor_descriptor *)vendor->byte_data;
-       if (vendor->byte_length <= sizeof(*info->descriptor) ||
-           descriptor->guid_id != info->descriptor->guid_id ||
-           efi_guidcmp(descriptor->guid, info->descriptor->guid))
-               return AE_OK;
-
-       byte_length = vendor->byte_length - sizeof(struct acpi_vendor_descriptor);
-       info->data = acpi_os_allocate(byte_length);
-       if (!info->data)
-               return AE_NO_MEMORY;
-
-       memcpy(info->data,
-              vendor->byte_data + sizeof(struct acpi_vendor_descriptor),
-              byte_length);
-       info->length = byte_length;
-       return AE_CTRL_TERMINATE;
-}
+       acpi_status status;
+       struct acpi_buffer buffer = { ACPI_ALLOCATE_BUFFER, NULL };
+       struct acpi_resource *resource;
+       struct acpi_resource_vendor_typed *vendor;
 
-acpi_status
-acpi_find_vendor_resource(acpi_handle obj, struct acpi_vendor_descriptor * id,
-                         u8 ** data, u32 * byte_length)
-{
-       struct acpi_vendor_info info;
+       status = acpi_get_vendor_resource(obj, METHOD_NAME__CRS, &hp_ccsr_uuid,
+               &buffer);
 
-       info.descriptor = id;
-       info.data = NULL;
+       resource = buffer.pointer;
+       vendor = &resource->data.vendor_typed;
 
-       acpi_walk_resources(obj, METHOD_NAME__CRS, acpi_vendor_resource_match,
-                           &info);
-       if (!info.data)
-               return AE_NOT_FOUND;
+       if (ACPI_FAILURE(status) || vendor->byte_length < 16) {
+               status = AE_NOT_FOUND;
+               goto exit;
+       }
 
-       *data = info.data;
-       *byte_length = info.length;
-       return AE_OK;
+       memcpy(base, vendor->byte_data, sizeof(*base));
+       memcpy(length, vendor->byte_data + 8, sizeof(*length));
+
+  exit:
+       acpi_os_free(buffer.pointer);
+       return status;
 }
 
-struct acpi_vendor_descriptor hp_ccsr_descriptor = {
-       .guid_id = 2,
-       .guid =
-           EFI_GUID(0x69e9adf9, 0x924f, 0xab5f, 0xf6, 0x4a, 0x24, 0xd2, 0x01,
-                    0x37, 0x0e, 0xad)
+struct csr_space {
+       u64     base;
+       u64     length;
 };
 
-acpi_status hp_acpi_csr_space(acpi_handle obj, u64 * csr_base, u64 * csr_length)
+static acpi_status find_csr_space(struct acpi_resource *resource, void *data)
 {
+       struct csr_space *space = data;
+       struct acpi_resource_address64 addr;
        acpi_status status;
-       u8 *data;
-       u32 length;
 
-       status =
-           acpi_find_vendor_resource(obj, &hp_ccsr_descriptor, &data, &length);
+       status = acpi_resource_to_address64(resource, &addr);
+       if (ACPI_SUCCESS(status) &&
+           addr.resource_type == ACPI_MEMORY_RANGE &&
+           addr.address_length &&
+           addr.producer_consumer == ACPI_CONSUMER) {
+               space->base = addr.minimum;
+               space->length = addr.address_length;
+               return AE_CTRL_TERMINATE;
+       }
+       return AE_OK;           /* keep looking */
+}
 
-       if (ACPI_FAILURE(status) || length != 16)
-               return AE_NOT_FOUND;
+static acpi_status hp_crs_locate(acpi_handle obj, u64 *base, u64 *length)
+{
+       struct csr_space space = { 0, 0 };
 
-       memcpy(csr_base, data, sizeof(*csr_base));
-       memcpy(csr_length, data + 8, sizeof(*csr_length));
-       acpi_os_free(data);
+       acpi_walk_resources(obj, METHOD_NAME__CRS, find_csr_space, &space);
+       if (!space.length)
+               return AE_NOT_FOUND;
 
+       *base = space.base;
+       *length = space.length;
        return AE_OK;
 }
 
+acpi_status hp_acpi_csr_space(acpi_handle obj, u64 *csr_base, u64 *csr_length)
+{
+       acpi_status status;
+
+       status = hp_ccsr_locate(obj, csr_base, csr_length);
+       if (ACPI_SUCCESS(status))
+               return status;
+
+       return hp_crs_locate(obj, csr_base, csr_length);
+}
 EXPORT_SYMBOL(hp_acpi_csr_space);
index 750e8e7fbdc30a6c9f218b633a4e993c01c4038a..e3079881121667346e96d8141a838fded794bf15 100644 (file)
@@ -1606,5 +1606,9 @@ sys_call_table:
        data8 sys_ni_syscall                    // 1295 reserved for ppoll
        data8 sys_unshare
        data8 sys_splice
+       data8 sys_set_robust_list
+       data8 sys_get_robust_list
+       data8 sys_sync_file_range               // 1300
+       data8 sys_tee
 
        .org sys_call_table + 8*NR_syscalls     // guard against failures to increase NR_syscalls
index 789881ca83d43606e389b65b481a8fc99083fb54..f9039f88d01dfbcefb9174c0f59bb968fa92f5bd 100644 (file)
@@ -251,7 +251,7 @@ static void __kprobes prepare_break_inst(uint template, uint  slot,
        update_kprobe_inst_flag(template, slot, major_opcode, kprobe_inst, p);
 }
 
-static inline void get_kprobe_inst(bundle_t *bundle, uint slot,
+static void __kprobes get_kprobe_inst(bundle_t *bundle, uint slot,
                unsigned long *kprobe_inst, uint *major_opcode)
 {
        unsigned long kprobe_inst_p0, kprobe_inst_p1;
@@ -278,7 +278,7 @@ static inline void get_kprobe_inst(bundle_t *bundle, uint slot,
 }
 
 /* Returns non-zero if the addr is in the Interrupt Vector Table */
-static inline int in_ivt_functions(unsigned long addr)
+static int __kprobes in_ivt_functions(unsigned long addr)
 {
        return (addr >= (unsigned long)__start_ivt_text
                && addr < (unsigned long)__end_ivt_text);
@@ -308,19 +308,19 @@ static int __kprobes valid_kprobe_addr(int template, int slot,
        return 0;
 }
 
-static inline void save_previous_kprobe(struct kprobe_ctlblk *kcb)
+static void __kprobes save_previous_kprobe(struct kprobe_ctlblk *kcb)
 {
        kcb->prev_kprobe.kp = kprobe_running();
        kcb->prev_kprobe.status = kcb->kprobe_status;
 }
 
-static inline void restore_previous_kprobe(struct kprobe_ctlblk *kcb)
+static void __kprobes restore_previous_kprobe(struct kprobe_ctlblk *kcb)
 {
        __get_cpu_var(current_kprobe) = kcb->prev_kprobe.kp;
        kcb->kprobe_status = kcb->prev_kprobe.status;
 }
 
-static inline void set_current_kprobe(struct kprobe *p,
+static void __kprobes set_current_kprobe(struct kprobe *p,
                        struct kprobe_ctlblk *kcb)
 {
        __get_cpu_var(current_kprobe) = p;
index 8963171788d52b44873fda9433c968b194df4f57..6a0880639bc9396208c30a9f9ccd4b3ae93aa835 100644 (file)
@@ -581,10 +581,12 @@ ia64_mca_rendez_int_handler(int rendez_irq, void *arg, struct pt_regs *regs)
 {
        unsigned long flags;
        int cpu = smp_processor_id();
+       struct ia64_mca_notify_die nd =
+               { .sos = NULL, .monarch_cpu = &monarch_cpu };
 
        /* Mask all interrupts */
        local_irq_save(flags);
-       if (notify_die(DIE_MCA_RENDZVOUS_ENTER, "MCA", regs, 0, 0, 0)
+       if (notify_die(DIE_MCA_RENDZVOUS_ENTER, "MCA", regs, (long)&nd, 0, 0)
                        == NOTIFY_STOP)
                ia64_mca_spin(__FUNCTION__);
 
@@ -594,7 +596,7 @@ ia64_mca_rendez_int_handler(int rendez_irq, void *arg, struct pt_regs *regs)
         */
        ia64_sal_mc_rendez();
 
-       if (notify_die(DIE_MCA_RENDZVOUS_PROCESS, "MCA", regs, 0, 0, 0)
+       if (notify_die(DIE_MCA_RENDZVOUS_PROCESS, "MCA", regs, (long)&nd, 0, 0)
                        == NOTIFY_STOP)
                ia64_mca_spin(__FUNCTION__);
 
@@ -602,7 +604,7 @@ ia64_mca_rendez_int_handler(int rendez_irq, void *arg, struct pt_regs *regs)
        while (monarch_cpu != -1)
               cpu_relax();     /* spin until monarch leaves */
 
-       if (notify_die(DIE_MCA_RENDZVOUS_LEAVE, "MCA", regs, 0, 0, 0)
+       if (notify_die(DIE_MCA_RENDZVOUS_LEAVE, "MCA", regs, (long)&nd, 0, 0)
                        == NOTIFY_STOP)
                ia64_mca_spin(__FUNCTION__);
 
@@ -961,7 +963,7 @@ no_mod:
  */
 
 static void
-ia64_wait_for_slaves(int monarch)
+ia64_wait_for_slaves(int monarch, const char *type)
 {
        int c, wait = 0, missing = 0;
        for_each_online_cpu(c) {
@@ -987,7 +989,7 @@ ia64_wait_for_slaves(int monarch)
        }
        if (!missing)
                goto all_in;
-       printk(KERN_INFO "OS MCA slave did not rendezvous on cpu");
+       printk(KERN_INFO "OS %s slave did not rendezvous on cpu", type);
        for_each_online_cpu(c) {
                if (c == monarch)
                        continue;
@@ -998,7 +1000,7 @@ ia64_wait_for_slaves(int monarch)
        return;
 
 all_in:
-       printk(KERN_INFO "All OS MCA slaves have reached rendezvous\n");
+       printk(KERN_INFO "All OS %s slaves have reached rendezvous\n", type);
        return;
 }
 
@@ -1023,6 +1025,8 @@ ia64_mca_handler(struct pt_regs *regs, struct switch_stack *sw,
                &sos->proc_state_param;
        int recover, cpu = smp_processor_id();
        task_t *previous_current;
+       struct ia64_mca_notify_die nd =
+               { .sos = sos, .monarch_cpu = &monarch_cpu };
 
        oops_in_progress = 1;   /* FIXME: make printk NMI/MCA/INIT safe */
        console_loglevel = 15;  /* make sure printks make it to console */
@@ -1031,10 +1035,10 @@ ia64_mca_handler(struct pt_regs *regs, struct switch_stack *sw,
 
        previous_current = ia64_mca_modify_original_stack(regs, sw, sos, "MCA");
        monarch_cpu = cpu;
-       if (notify_die(DIE_MCA_MONARCH_ENTER, "MCA", regs, 0, 0, 0)
+       if (notify_die(DIE_MCA_MONARCH_ENTER, "MCA", regs, (long)&nd, 0, 0)
                        == NOTIFY_STOP)
                ia64_mca_spin(__FUNCTION__);
-       ia64_wait_for_slaves(cpu);
+       ia64_wait_for_slaves(cpu, "MCA");
 
        /* Wakeup all the processors which are spinning in the rendezvous loop.
         * They will leave SAL, then spin in the OS with interrupts disabled
@@ -1043,7 +1047,7 @@ ia64_mca_handler(struct pt_regs *regs, struct switch_stack *sw,
         * spinning in SAL does not work.
         */
        ia64_mca_wakeup_all();
-       if (notify_die(DIE_MCA_MONARCH_PROCESS, "MCA", regs, 0, 0, 0)
+       if (notify_die(DIE_MCA_MONARCH_PROCESS, "MCA", regs, (long)&nd, 0, 0)
                        == NOTIFY_STOP)
                ia64_mca_spin(__FUNCTION__);
 
@@ -1064,7 +1068,7 @@ ia64_mca_handler(struct pt_regs *regs, struct switch_stack *sw,
                ia64_sal_clear_state_info(SAL_INFO_TYPE_MCA);
                sos->os_status = IA64_MCA_CORRECTED;
        }
-       if (notify_die(DIE_MCA_MONARCH_LEAVE, "MCA", regs, 0, 0, recover)
+       if (notify_die(DIE_MCA_MONARCH_LEAVE, "MCA", regs, (long)&nd, 0, recover)
                        == NOTIFY_STOP)
                ia64_mca_spin(__FUNCTION__);
 
@@ -1351,10 +1355,14 @@ ia64_init_handler(struct pt_regs *regs, struct switch_stack *sw,
        static atomic_t monarchs;
        task_t *previous_current;
        int cpu = smp_processor_id();
+       struct ia64_mca_notify_die nd =
+               { .sos = sos, .monarch_cpu = &monarch_cpu };
 
        oops_in_progress = 1;   /* FIXME: make printk NMI/MCA/INIT safe */
        console_loglevel = 15;  /* make sure printks make it to console */
 
+       (void) notify_die(DIE_INIT_ENTER, "INIT", regs, (long)&nd, 0, 0);
+
        printk(KERN_INFO "Entered OS INIT handler. PSP=%lx cpu=%d monarch=%ld\n",
                sos->proc_state_param, cpu, sos->monarch);
        salinfo_log_wakeup(SAL_INFO_TYPE_INIT, NULL, 0, 0);
@@ -1390,15 +1398,15 @@ ia64_init_handler(struct pt_regs *regs, struct switch_stack *sw,
                ia64_mc_info.imi_rendez_checkin[cpu] = IA64_MCA_RENDEZ_CHECKIN_INIT;
                while (monarch_cpu == -1)
                       cpu_relax();     /* spin until monarch enters */
-               if (notify_die(DIE_INIT_SLAVE_ENTER, "INIT", regs, 0, 0, 0)
+               if (notify_die(DIE_INIT_SLAVE_ENTER, "INIT", regs, (long)&nd, 0, 0)
                                == NOTIFY_STOP)
                        ia64_mca_spin(__FUNCTION__);
-               if (notify_die(DIE_INIT_SLAVE_PROCESS, "INIT", regs, 0, 0, 0)
+               if (notify_die(DIE_INIT_SLAVE_PROCESS, "INIT", regs, (long)&nd, 0, 0)
                                == NOTIFY_STOP)
                        ia64_mca_spin(__FUNCTION__);
                while (monarch_cpu != -1)
                       cpu_relax();     /* spin until monarch leaves */
-               if (notify_die(DIE_INIT_SLAVE_LEAVE, "INIT", regs, 0, 0, 0)
+               if (notify_die(DIE_INIT_SLAVE_LEAVE, "INIT", regs, (long)&nd, 0, 0)
                                == NOTIFY_STOP)
                        ia64_mca_spin(__FUNCTION__);
                printk("Slave on cpu %d returning to normal service.\n", cpu);
@@ -1409,7 +1417,7 @@ ia64_init_handler(struct pt_regs *regs, struct switch_stack *sw,
        }
 
        monarch_cpu = cpu;
-       if (notify_die(DIE_INIT_MONARCH_ENTER, "INIT", regs, 0, 0, 0)
+       if (notify_die(DIE_INIT_MONARCH_ENTER, "INIT", regs, (long)&nd, 0, 0)
                        == NOTIFY_STOP)
                ia64_mca_spin(__FUNCTION__);
 
@@ -1421,15 +1429,15 @@ ia64_init_handler(struct pt_regs *regs, struct switch_stack *sw,
         */
        printk("Delaying for 5 seconds...\n");
        udelay(5*1000000);
-       ia64_wait_for_slaves(cpu);
+       ia64_wait_for_slaves(cpu, "INIT");
        /* If nobody intercepts DIE_INIT_MONARCH_PROCESS then we drop through
         * to default_monarch_init_process() above and just print all the
         * tasks.
         */
-       if (notify_die(DIE_INIT_MONARCH_PROCESS, "INIT", regs, 0, 0, 0)
+       if (notify_die(DIE_INIT_MONARCH_PROCESS, "INIT", regs, (long)&nd, 0, 0)
                        == NOTIFY_STOP)
                ia64_mca_spin(__FUNCTION__);
-       if (notify_die(DIE_INIT_MONARCH_LEAVE, "INIT", regs, 0, 0, 0)
+       if (notify_die(DIE_INIT_MONARCH_LEAVE, "INIT", regs, (long)&nd, 0, 0)
                        == NOTIFY_STOP)
                ia64_mca_spin(__FUNCTION__);
        printk("\nINIT dump complete.  Monarch on cpu %d returning to normal service.\n", cpu);
@@ -1631,6 +1639,7 @@ ia64_mca_init(void)
                        printk(KERN_INFO "Increasing MCA rendezvous timeout from "
                                "%ld to %ld milliseconds\n", timeout, isrv.v0);
                        timeout = isrv.v0;
+                       (void) notify_die(DIE_MCA_NEW_TIMEOUT, "MCA", NULL, timeout, 0, 0);
                        continue;
                }
                printk(KERN_ERR "Failed to register rendezvous interrupt "
index 60a464bfd9e27ce2afe46bb0de051806b9b0cbfa..6dff024cd62b03f45ae9f00cde9ae9c1a0fcebc8 100644 (file)
@@ -827,7 +827,7 @@ ia64_state_restore:
        ld8 r9=[temp2],16       // sal_gp
        ;;
        ld8 r22=[temp1],16      // pal_min_state, virtual
-       ld8 r21=[temp2],16      // prev_IA64_KR_CURRENT
+       ld8 r13=[temp2],16      // prev_IA64_KR_CURRENT
        ;;
        ld8 r16=[temp1],16      // prev_IA64_KR_CURRENT_STACK
        ld8 r20=[temp2],16      // prev_task
@@ -848,7 +848,7 @@ ia64_state_restore:
        mov cr.iim=temp3
        mov cr.iha=temp4
        dep r22=0,r22,62,1      // pal_min_state, physical, uncached
-       mov IA64_KR(CURRENT)=r21
+       mov IA64_KR(CURRENT)=r13
        ld8 r8=[temp1]          // os_status
        ld8 r10=[temp2]         // context
 
@@ -856,7 +856,7 @@ ia64_state_restore:
         * avoid any dependencies on the algorithm in ia64_switch_to(), just
         * purge any existing CURRENT_STACK mapping and insert the new one.
         *
-        * r16 contains prev_IA64_KR_CURRENT_STACK, r21 contains
+        * r16 contains prev_IA64_KR_CURRENT_STACK, r13 contains
         * prev_IA64_KR_CURRENT, these values may have been changed by the C
         * code.  Do not use r8, r9, r10, r22, they contain values ready for
         * the return to SAL.
@@ -873,7 +873,7 @@ ia64_state_restore:
        ;;
        srlz.d
 
-       extr.u r19=r21,61,3                     // r21 = prev_IA64_KR_CURRENT
+       extr.u r19=r13,61,3                     // r13 = prev_IA64_KR_CURRENT
        shl r20=r16,IA64_GRANULE_SHIFT          // r16 = prev_IA64_KR_CURRENT_STACK
        movl r21=PAGE_KERNEL                    // page properties
        ;;
@@ -883,7 +883,7 @@ ia64_state_restore:
 (p6)   br.spnt 1f                              // the dreaded cpu 0 idle task in region 5:(
        ;;
        mov cr.itir=r18
-       mov cr.ifa=r21
+       mov cr.ifa=r13
        mov r20=IA64_TR_CURRENT_STACK
        ;;
        itr.d dtr[r20]=r21
index 7a2f0a798d121c67a338b6f34cc9a59090f2505b..3a30cfc9574fd499cc5fa839ee34731aecf25e04 100644 (file)
@@ -947,7 +947,7 @@ void
 percpu_modcopy (void *pcpudst, const void *src, unsigned long size)
 {
        unsigned int i;
-       for_each_cpu(i) {
+       for_each_possible_cpu(i) {
                memcpy(pcpudst + __per_cpu_offset[i], src, size);
        }
 }
index ec9eeb89975d6c3c4952bdea4ca4511e12e465a5..b6bcc9fa36030690b073440781e48398847ae547 100644 (file)
@@ -519,6 +519,68 @@ void __cpuinit *per_cpu_init(void)
 }
 #endif /* CONFIG_SMP */
 
+#ifdef CONFIG_VIRTUAL_MEM_MAP
+static inline int find_next_valid_pfn_for_pgdat(pg_data_t *pgdat, int i)
+{
+       unsigned long end_address, hole_next_pfn;
+       unsigned long stop_address;
+
+       end_address = (unsigned long) &vmem_map[pgdat->node_start_pfn + i];
+       end_address = PAGE_ALIGN(end_address);
+
+       stop_address = (unsigned long) &vmem_map[
+               pgdat->node_start_pfn + pgdat->node_spanned_pages];
+
+       do {
+               pgd_t *pgd;
+               pud_t *pud;
+               pmd_t *pmd;
+               pte_t *pte;
+
+               pgd = pgd_offset_k(end_address);
+               if (pgd_none(*pgd)) {
+                       end_address += PGDIR_SIZE;
+                       continue;
+               }
+
+               pud = pud_offset(pgd, end_address);
+               if (pud_none(*pud)) {
+                       end_address += PUD_SIZE;
+                       continue;
+               }
+
+               pmd = pmd_offset(pud, end_address);
+               if (pmd_none(*pmd)) {
+                       end_address += PMD_SIZE;
+                       continue;
+               }
+
+               pte = pte_offset_kernel(pmd, end_address);
+retry_pte:
+               if (pte_none(*pte)) {
+                       end_address += PAGE_SIZE;
+                       pte++;
+                       if ((end_address < stop_address) &&
+                           (end_address != ALIGN(end_address, 1UL << PMD_SHIFT)))
+                               goto retry_pte;
+                       continue;
+               }
+               /* Found next valid vmem_map page */
+               break;
+       } while (end_address < stop_address);
+
+       end_address = min(end_address, stop_address);
+       end_address = end_address - (unsigned long) vmem_map + sizeof(struct page) - 1;
+       hole_next_pfn = end_address / sizeof(struct page);
+       return hole_next_pfn - pgdat->node_start_pfn;
+}
+#else
+static inline int find_next_valid_pfn_for_pgdat(pg_data_t *pgdat, int i)
+{
+       return i + 1;
+}
+#endif
+
 /**
  * show_mem - give short summary of memory stats
  *
@@ -547,8 +609,10 @@ void show_mem(void)
                        struct page *page;
                        if (pfn_valid(pgdat->node_start_pfn + i))
                                page = pfn_to_page(pgdat->node_start_pfn + i);
-                       else
+                       else {
+                               i = find_next_valid_pfn_for_pgdat(pgdat, i) - 1;
                                continue;
+                       }
                        if (PageReserved(page))
                                reserved++;
                        else if (PageSwapCache(page))
index af7eb087dca7af7df598e8c81c475e9b365f042c..d98ec49570b80f6e9d70a66d98e070ef19cc3dba 100644 (file)
@@ -60,6 +60,9 @@ ia64_do_page_fault (unsigned long address, unsigned long isr, struct pt_regs *re
        struct siginfo si;
        unsigned long mask;
 
+       /* mmap_sem is performance critical.... */
+       prefetchw(&mm->mmap_sem);
+
        /*
         * If we're in an interrupt or have no user context, we must not take the fault..
         */
index d0abddd9ffe682c8dc4d566c6619a33b180567a7..8255a9be4632adbc325bc96643208ea1a04b8fa6 100644 (file)
@@ -1831,7 +1831,7 @@ xpc_initiate_allocate(partid_t partid, int ch_number, u32 flags, void **payload)
 {
        struct xpc_partition *part = &xpc_partitions[partid];
        enum xpc_retval ret = xpcUnknownReason;
-       struct xpc_msg *msg;
+       struct xpc_msg *msg = NULL;
 
 
        DBUG_ON(partid <= 0 || partid >= XP_MAX_PARTITIONS);
index 05c864c6c2d937e31f893c3b1aa783e190906c33..41fd490af3b47a93c70e829a561506151f1e6e09 100644 (file)
@@ -285,6 +285,11 @@ config NUMA
        depends on SMP && BROKEN
        default n
 
+config NODES_SHIFT
+       int
+       default "1"
+       depends on NEED_MULTIPLE_NODES
+
 # turning this on wastes a bunch of space.
 # Summit needs it only when NUMA is on
 config BOOT_IOREMAP
index 3871b65f0c827966eede1b0cac8d1d07464198ff..920bb742b7a2a90394c133998809917f0bb33f56 100644 (file)
@@ -20,7 +20,7 @@
  * Stack layout in 'ret_from_system_call':
  *     ptrace needs to have all regs on the stack.
  *     if the order here is changed, it needs to be
- *     updated in fork.c:copy_process, signal.c:do_signal,
+ *     updated in fork.c:copy_thread, signal.c:do_signal,
  *     ptrace.c and ptrace.h
  *
  * M32Rx/M32R2                         M32R
  *       @(0x38,sp) - syscall_nr       ditto
  *       @(0x3c,sp) - acc0h            @(0x3c,sp) - acch
  *       @(0x40,sp) - acc0l            @(0x40,sp) - accl
- *       @(0x44,sp) - acc1h            @(0x44,sp) - psw
- *       @(0x48,sp) - acc1l            @(0x48,sp) - bpc
- *       @(0x4c,sp) - psw              @(0x4c,sp) - bbpsw
- *       @(0x50,sp) - bpc              @(0x50,sp) - bbpc
- *       @(0x54,sp) - bbpsw            @(0x54,sp) - spu (cr3)
- *       @(0x58,sp) - bbpc             @(0x58,sp) - fp (r13)
- *       @(0x5c,sp) - spu (cr3)                @(0x5c,sp) - lr (r14)
- *       @(0x60,sp) - fp (r13)         @(0x60,sp) - spi (cr12)
- *       @(0x64,sp) - lr (r14)         @(0x64,sp) - orig_r0
- *       @(0x68,sp) - spi (cr2)
- *       @(0x6c,sp) - orig_r0
- *
+ *       @(0x44,sp) - acc1h            @(0x44,sp) - dummy_acc1h
+ *       @(0x48,sp) - acc1l            @(0x48,sp) - dummy_acc1l
+ *       @(0x4c,sp) - psw              ditto
+ *       @(0x50,sp) - bpc              ditto
+ *       @(0x54,sp) - bbpsw            ditto
+ *       @(0x58,sp) - bbpc             ditto
+ *       @(0x5c,sp) - spu (cr3)                ditto
+ *       @(0x60,sp) - fp (r13)         ditto
+ *       @(0x64,sp) - lr (r14)         ditto
+ *       @(0x68,sp) - spi (cr2)                ditto
+ *       @(0x6c,sp) - orig_r0          ditto
  */
 
 #include <linux/config.h>
 #define ACC0L(reg)             @(0x40,reg)
 #define ACC1H(reg)             @(0x44,reg)
 #define ACC1L(reg)             @(0x48,reg)
+#elif defined(CONFIG_ISA_M32R2) || defined(CONFIG_ISA_M32R)
+#define ACCH(reg)              @(0x3C,reg)
+#define ACCL(reg)              @(0x40,reg)
+#else
+#error unknown isa configuration
+#endif
 #define PSW(reg)               @(0x4C,reg)
 #define BPC(reg)               @(0x50,reg)
 #define BBPSW(reg)             @(0x54,reg)
 #define LR(reg)                        @(0x64,reg)
 #define SP(reg)                        @(0x68,reg)
 #define ORIG_R0(reg)           @(0x6C,reg)
-#elif defined(CONFIG_ISA_M32R2) || defined(CONFIG_ISA_M32R)
-#define ACCH(reg)              @(0x3C,reg)
-#define ACCL(reg)              @(0x40,reg)
-#define PSW(reg)               @(0x44,reg)
-#define BPC(reg)               @(0x48,reg)
-#define BBPSW(reg)             @(0x4C,reg)
-#define BBPC(reg)              @(0x50,reg)
-#define SPU(reg)               @(0x54,reg)
-#define FP(reg)                        @(0x58,reg)  /* FP = R13 */
-#define LR(reg)                        @(0x5C,reg)
-#define SP(reg)                        @(0x60,reg)
-#define ORIG_R0(reg)           @(0x64,reg)
-#else
-#error unknown isa configuration
-#endif
 
 CF_MASK                = 0x00000001
 TF_MASK                = 0x00000100
@@ -142,7 +132,7 @@ VM_MASK             = 0x00020000
 #endif
 
 ENTRY(ret_from_fork)
-       ld      r0, @sp+
+       pop     r0
        bl      schedule_tail
        GET_THREAD_INFO(r8)
        bra     syscall_exit
@@ -231,7 +221,7 @@ restore_all:
        RESTORE_ALL
 
        # perform work that needs to be done immediately before resumption
-       # r9 : frags
+       # r9 : flags
        ALIGN
 work_pending:
        and3    r4, r9, #_TIF_NEED_RESCHED
@@ -320,7 +310,7 @@ ENTRY(ei_handler)
 ;    GET_ICU_STATUS;
        seth    r0, #shigh(M32R_ICU_ISTS_ADDR)
        ld      r0, @(low(M32R_ICU_ISTS_ADDR),r0)
-       st      r0, @-sp
+       push    r0
 #if defined(CONFIG_SMP)
        /*
         * If IRQ == 0      --> Nothing to do,  Not write IMASK
@@ -557,7 +547,7 @@ check_end:
 #endif  /* CONFIG_PLAT_M32104UT */
        bl      do_IRQ
 #endif  /* CONFIG_SMP */
-       ld      r14, @sp+
+       pop     r14
        seth    r0, #shigh(M32R_ICU_IMASK_ADDR)
        st      r14, @(low(M32R_ICU_IMASK_ADDR),r0)
 #else
@@ -1015,4 +1005,3 @@ ENTRY(sys_call_table)
        .long sys_waitid
 
 syscall_table_size=(.-sys_call_table)
-
index be8b711367ec5d7bde44d77cbd9beb189c11d9e2..c50330fa83b98a33ef58e40f6751671835ed3aee 100644 (file)
@@ -23,9 +23,6 @@ EXPORT_SYMBOL(boot_cpu_data);
 EXPORT_SYMBOL(dump_fpu);
 EXPORT_SYMBOL(__ioremap);
 EXPORT_SYMBOL(iounmap);
-EXPORT_SYMBOL(enable_irq);
-EXPORT_SYMBOL(disable_irq);
-EXPORT_SYMBOL(disable_irq_nosync);
 EXPORT_SYMBOL(kernel_thread);
 EXPORT_SYMBOL(__down);
 EXPORT_SYMBOL(__down_interruptible);
@@ -38,13 +35,6 @@ EXPORT_SYMBOL(__udelay);
 EXPORT_SYMBOL(__delay);
 EXPORT_SYMBOL(__const_udelay);
 
-EXPORT_SYMBOL(__get_user_1);
-EXPORT_SYMBOL(__get_user_2);
-EXPORT_SYMBOL(__get_user_4);
-
-EXPORT_SYMBOL(strpbrk);
-EXPORT_SYMBOL(strstr);
-
 EXPORT_SYMBOL(strncpy_from_user);
 EXPORT_SYMBOL(__strncpy_from_user);
 EXPORT_SYMBOL(clear_user);
@@ -59,11 +49,8 @@ extern void *dcache_dummy;
 EXPORT_SYMBOL(dcache_dummy);
 #endif
 EXPORT_SYMBOL(cpu_data);
-EXPORT_SYMBOL(cpu_online_map);
-EXPORT_SYMBOL(cpu_callout_map);
 
 /* Global SMP stuff */
-EXPORT_SYMBOL(synchronize_irq);
 EXPORT_SYMBOL(smp_call_function);
 
 /* TLB flushing */
@@ -83,27 +70,11 @@ EXPORT_SYMBOL(__lshrdi3);
 EXPORT_SYMBOL(__muldi3);
 
 /* memory and string operations */
-EXPORT_SYMBOL(memchr);
 EXPORT_SYMBOL(memcpy);
-/* EXPORT_SYMBOL(memcpy_fromio); // not implement yet */
-/* EXPORT_SYMBOL(memcpy_toio); // not implement yet */
 EXPORT_SYMBOL(memset);
-/* EXPORT_SYMBOL(memset_io); // not implement yet */
-EXPORT_SYMBOL(memmove);
-EXPORT_SYMBOL(memcmp);
-EXPORT_SYMBOL(memscan);
 EXPORT_SYMBOL(copy_page);
 EXPORT_SYMBOL(clear_page);
-
-EXPORT_SYMBOL(strcat);
-EXPORT_SYMBOL(strchr);
-EXPORT_SYMBOL(strcmp);
-EXPORT_SYMBOL(strcpy);
 EXPORT_SYMBOL(strlen);
-EXPORT_SYMBOL(strncat);
-EXPORT_SYMBOL(strncmp);
-EXPORT_SYMBOL(strnlen);
-EXPORT_SYMBOL(strncpy);
 
 EXPORT_SYMBOL(_inb);
 EXPORT_SYMBOL(_inw);
index 5dfc7ea45cf7a9b19887f7de1049a7d337e5833e..065f5e7190587cf4e6a8122a34c64617523ab1cc 100644 (file)
@@ -116,6 +116,10 @@ void cpu_idle (void)
 
 void machine_restart(char *__unused)
 {
+#if defined(CONFIG_PLAT_MAPPI3)
+       outw(1, (unsigned long)PLD_REBOOT);
+#endif
+
        printk("Please push reset button!\n");
        while (1)
                cpu_relax();
index 0d78942b4c7684d01f63e74c663aa79d0737b233..3cd3c2988a4875f6da0c8e2fb8af921264beba42 100644 (file)
@@ -9,6 +9,7 @@
 
 #include <linux/config.h>
 #include <linux/init.h>
+#include <linux/kernel.h>
 #include <linux/stddef.h>
 #include <linux/fs.h>
 #include <linux/sched.h>
@@ -219,8 +220,6 @@ static unsigned long __init setup_memory(void)
 extern unsigned long setup_memory(void);
 #endif /* CONFIG_DISCONTIGMEM */
 
-#define M32R_PCC_PCATCR        0x00ef7014      /* will move to m32r.h */
-
 void __init setup_arch(char **cmdline_p)
 {
        ROOT_DEV = old_decode_dev(ORIG_ROOT_DEV);
@@ -269,15 +268,14 @@ void __init setup_arch(char **cmdline_p)
        paging_init();
 }
 
-static struct cpu cpu[NR_CPUS];
+static struct cpu cpu_devices[NR_CPUS];
 
 static int __init topology_init(void)
 {
-       int cpu_id;
+       int i;
 
-       for (cpu_id = 0; cpu_id < NR_CPUS; cpu_id++)
-               if (cpu_possible(cpu_id))
-                       register_cpu(&cpu[cpu_id], cpu_id, NULL);
+       for_each_present_cpu(i)
+               register_cpu(&cpu_devices[i], i, NULL);
 
        return 0;
 }
index cb33097fefc4453475451d31443b2e380b97f0d5..6498ee70bb738d4c6aedf927b2b45d7de17215fe 100644 (file)
@@ -118,6 +118,8 @@ restore_sigcontext(struct pt_regs *regs, struct sigcontext __user *sc,
 #elif defined(CONFIG_ISA_M32R2) || defined(CONFIG_ISA_M32R)
        COPY(acch);
        COPY(accl);
+       COPY(dummy_acc1h);
+       COPY(dummy_acc1l);
 #else
 #error unknown isa configuration
 #endif
@@ -203,6 +205,8 @@ setup_sigcontext(struct sigcontext __user *sc, struct pt_regs *regs,
 #elif defined(CONFIG_ISA_M32R2) || defined(CONFIG_ISA_M32R)
        COPY(acch);
        COPY(accl);
+       COPY(dummy_acc1h);
+       COPY(dummy_acc1l);
 #else
 #error unknown isa configuration
 #endif
index d7ec16e7fb259f50d6ee32ef99a332259d3891cc..840b4348bf0ceb1eeefc3f767b63ba9b350b30db 100644 (file)
  *             Martin J. Bligh :       Added support for multi-quad systems
  */
 
+#include <linux/module.h>
 #include <linux/config.h>
 #include <linux/init.h>
+#include <linux/kernel.h>
 #include <linux/mm.h>
 #include <linux/smp_lock.h>
 #include <linux/irq.h>
@@ -72,11 +74,15 @@ physid_mask_t phys_cpu_present_map;
 
 /* Bitmask of currently online CPUs */
 cpumask_t cpu_online_map;
+EXPORT_SYMBOL(cpu_online_map);
 
 cpumask_t cpu_bootout_map;
 cpumask_t cpu_bootin_map;
-cpumask_t cpu_callout_map;
 static cpumask_t cpu_callin_map;
+cpumask_t cpu_callout_map;
+EXPORT_SYMBOL(cpu_callout_map);
+cpumask_t cpu_possible_map = CPU_MASK_ALL;
+EXPORT_SYMBOL(cpu_possible_map);
 
 /* Per CPU bogomips and other parameters */
 struct cpuinfo_m32r cpu_data[NR_CPUS] __cacheline_aligned;
@@ -110,7 +116,6 @@ static unsigned int calibration_result;
 
 void smp_prepare_boot_cpu(void);
 void smp_prepare_cpus(unsigned int);
-static void smp_tune_scheduling(void);
 static void init_ipi_lock(void);
 static void do_boot_cpu(int);
 int __cpu_up(unsigned int);
@@ -177,6 +182,9 @@ void __init smp_prepare_cpus(unsigned int max_cpus)
        }
        for (phys_id = 0 ; phys_id < nr_cpu ; phys_id++)
                physid_set(phys_id, phys_cpu_present_map);
+#ifndef CONFIG_HOTPLUG_CPU
+       cpu_present_map = cpu_possible_map;
+#endif
 
        show_mp_info(nr_cpu);
 
@@ -186,7 +194,6 @@ void __init smp_prepare_cpus(unsigned int max_cpus)
         * Setup boot CPU information
         */
        smp_store_cpu_info(0); /* Final full version of the data */
-       smp_tune_scheduling();
 
        /*
         * If SMP should be disabled, then really disable it!
@@ -230,11 +237,6 @@ smp_done:
        Dprintk("Boot done.\n");
 }
 
-static void __init smp_tune_scheduling(void)
-{
-       /* Nothing to do. */
-}
-
 /*
  * init_ipi_lock : Initialize IPI locks.
  */
@@ -629,4 +631,3 @@ static void __init unmap_cpu_to_physid(int cpu_id, int phys_id)
        physid_2_cpu[phys_id] = -1;
        cpu_2_physid[cpu_id] = -1;
 }
-
index e632d10c7d78ee9c18a48992406cb0d5447fa3df..d16b4e40d1ae9746165756d21628594e0a7a7ca1 100644 (file)
@@ -2,6 +2,6 @@
 # Makefile for M32R-specific library files..
 #
 
-lib-y  := checksum.o ashxdi3.o memset.o memcpy.o getuser.o \
-         putuser.o delay.o strlen.o usercopy.o csum_partial_copy.o
+lib-y  := checksum.o ashxdi3.o memset.o memcpy.o \
+         delay.o strlen.o usercopy.o csum_partial_copy.o
 
diff --git a/arch/m32r/lib/getuser.S b/arch/m32r/lib/getuser.S
deleted file mode 100644 (file)
index 58a0db0..0000000
+++ /dev/null
@@ -1,88 +0,0 @@
-/*
- * __get_user functions.
- *
- * (C) Copyright 2001 Hirokazu Takata
- *
- * These functions have a non-standard call interface
- * to make them more efficient, especially as they
- * return an error value in addition to the "real"
- * return value.
- */
-
-#include <linux/config.h>
-
-/*
- * __get_user_X
- *
- * Inputs:     r0 contains the address
- *
- * Outputs:    r0 is error code (0 or -EFAULT)
- *             r1 contains zero-extended value
- *
- * These functions should not modify any other registers,
- * as they get called from within inline assembly.
- */
-
-#ifdef CONFIG_ISA_DUAL_ISSUE
-
-       .text
-       .balign 4
-       .globl __get_user_1
-__get_user_1:
-1:     ldub    r1, @r0             ||  ldi     r0, #0
-       jmp     r14
-
-       .balign 4
-       .globl __get_user_2
-__get_user_2:
-2:     lduh    r1, @r0             ||  ldi     r0, #0
-       jmp     r14
-
-       .balign 4
-       .globl __get_user_4
-__get_user_4:
-3:     ld      r1, @r0             ||  ldi     r0, #0
-       jmp     r14
-
-bad_get_user:
-       ldi     r1, #0              ||  ldi     r0, #-14
-       jmp     r14
-
-#else /* not CONFIG_ISA_DUAL_ISSUE */
-
-       .text
-       .balign 4
-       .globl __get_user_1
-__get_user_1:
-1:     ldub    r1, @r0
-       ldi     r0, #0
-       jmp     r14
-
-       .balign 4
-       .globl __get_user_2
-__get_user_2:
-2:     lduh    r1, @r0
-       ldi     r0, #0
-       jmp     r14
-
-       .balign 4
-       .globl __get_user_4
-__get_user_4:
-3:     ld      r1, @r0
-       ldi     r0, #0
-       jmp     r14
-
-bad_get_user:
-       ldi     r1, #0
-       ldi     r0, #-14
-       jmp     r14
-
-#endif /* not CONFIG_ISA_DUAL_ISSUE */
-
-.section __ex_table,"a"
-       .long 1b,bad_get_user
-       .long 2b,bad_get_user
-       .long 3b,bad_get_user
-.previous
-
-       .end
diff --git a/arch/m32r/lib/putuser.S b/arch/m32r/lib/putuser.S
deleted file mode 100644 (file)
index 218154c..0000000
+++ /dev/null
@@ -1,84 +0,0 @@
-/*
- * __put_user functions.
- *
- * (C) Copyright 1998 Linus Torvalds
- * (C) Copyright 2001 Hirokazu Takata
- *
- * These functions have a non-standard call interface
- * to make them more efficient.
- */
-
-#include <linux/config.h>
-
-/*
- * __put_user_X
- *
- * Inputs:     r0 contains the address
- *             r1 contains the value
- *
- * Outputs:    r0 is error code (0 or -EFAULT)
- *             r1 is corrupted (will contain "current_task").
- *
- * These functions should not modify any other registers,
- * as they get called from within inline assembly.
- */
-
-#ifdef CONFIG_ISA_DUAL_ISSUE
-
-       .text
-       .balign 4
-       .globl __put_user_1
-__put_user_1:
-1:     stb     r1, @r0             ||  ldi     r0, #0
-       jmp     r14
-
-       .balign 4
-       .globl __put_user_2
-__put_user_2:
-2:     sth     r1, @r0             ||  ldi     r0, #0
-       jmp     r14
-
-       .balign 4
-       .globl __put_user_4
-__put_user_4:
-3:     st      r1, @r0             ||  ldi     r0, #0
-       jmp     r14
-
-bad_put_user:
-       ldi     r0, #-14            ||  jmp     r14
-
-#else /* not CONFIG_ISA_DUAL_ISSUE */
-
-       .text
-       .balign 4
-       .globl __put_user_1
-__put_user_1:
-1:     stb     r1, @r0
-       ldi     r0, #0
-       jmp     r14
-
-       .balign 4
-       .globl __put_user_2
-__put_user_2:
-2:     sth     r1, @r0
-       ldi     r0, #0
-       jmp     r14
-
-       .balign 4
-       .globl __put_user_4
-__put_user_4:
-3:     st      r1, @r0
-       ldi     r0, #0
-       jmp     r14
-
-bad_put_user:
-       ldi     r0, #-14
-       jmp     r14
-
-#endif /* not CONFIG_ISA_DUAL_ISSUE */
-
-.section __ex_table,"a"
-       .long 1b,bad_put_user
-       .long 2b,bad_put_user
-       .long 3b,bad_put_user
-.previous
index c3319514a85ed000686cb947d0f679d0b474d0fb..5b7952ea2bae431dde15bd7c04c48068d529e7c2 100644 (file)
@@ -57,7 +57,6 @@ EXPORT_SYMBOL(dump_thread);
 EXPORT_SYMBOL(strnlen);
 EXPORT_SYMBOL(strrchr);
 EXPORT_SYMBOL(strstr);
-EXPORT_SYMBOL(strpbrk);
 EXPORT_SYMBOL(enable_irq);
 EXPORT_SYMBOL(disable_irq);
 EXPORT_SYMBOL(kernel_thread);
index f9b4ea16c0998625fd0cd747bc2b62b4d8154f18..4320d5dcc9cb9b7e632bd98d8bf74d49b4ab3652 100644 (file)
@@ -26,7 +26,6 @@ EXPORT_SYMBOL(__ioremap);
 EXPORT_SYMBOL(iounmap);
 EXPORT_SYMBOL(dump_fpu);
 EXPORT_SYMBOL(strnlen);
-EXPORT_SYMBOL(strpbrk);
 EXPORT_SYMBOL(strrchr);
 EXPORT_SYMBOL(strstr);
 EXPORT_SYMBOL(strchr);
index e15709ce886626158aba18c05851cb5bc04065c6..87f0b79c6b1590b0875721d9ce16ca5c0d82a194 100644 (file)
@@ -816,6 +816,10 @@ config GENERIC_CALIBRATE_DELAY
        bool
        default y
 
+config SCHED_NO_NO_OMIT_FRAME_POINTER
+       bool
+       default y
+
 #
 # Select some configuration options automatically based on user selections.
 #
@@ -1443,6 +1447,10 @@ choice
        prompt "MIPS MT options"
        depends on MIPS_MT
 
+config MIPS_MT_SMTC
+       bool "SMTC: Use all TCs on all VPEs for SMP"
+       select SMP
+
 config MIPS_MT_SMP
        bool "Use 1 TC on each available VPE for SMP"
        select SMP
@@ -1456,6 +1464,11 @@ config MIPS_VPE_LOADER
 
 endchoice
 
+config MIPS_MT_FPAFF
+       bool "Dynamic FPU affinity for FP-intensive threads"
+       depends on MIPS_MT
+       default y
+
 config MIPS_VPE_LOADER_TOM
        bool "Load VPE program into memory hidden from linux"
        depends on MIPS_VPE_LOADER
@@ -1472,6 +1485,16 @@ config MIPS_VPE_APSP_API
        depends on MIPS_VPE_LOADER
        help
 
+config MIPS_APSP_KSPD
+       bool "Enable KSPD"
+       depends on MIPS_VPE_APSP_API
+       default y
+       help
+         KSPD is a kernel daemon that accepts syscall requests from the SP
+         side, actions them and returns the results. It also handles the
+         "exit" syscall notifying other kernel modules the SP program is
+         exiting.  You probably want to say yes here.
+
 config SB1_PASS_1_WORKAROUNDS
        bool
        depends on CPU_SB1_PASS_1
@@ -1590,11 +1613,16 @@ config ARCH_FLATMEM_ENABLE
        def_bool y
        depends on !NUMA
 
+config NODES_SHIFT
+       int
+       default "6"
+       depends on NEED_MULTIPLE_NODES
+
 source "mm/Kconfig"
 
 config SMP
        bool "Multi-Processing support"
-       depends on CPU_RM9000 || ((SIBYTE_BCM1x80 || SIBYTE_BCM1x55 || SIBYTE_SB1250 || QEMU) && !SIBYTE_STANDALONE) || SGI_IP27 || MIPS_MT_SMP
+       depends on CPU_RM9000 || ((SIBYTE_BCM1x80 || SIBYTE_BCM1x55 || SIBYTE_SB1250 || QEMU) && !SIBYTE_STANDALONE) || SGI_IP27 || MIPS_MT_SMP || MIPS_MT_SMTC
        ---help---
          This enables support for systems with more than one CPU. If you have
          a system with only one CPU, like most personal computers, say N. If
index 9a69e0f0ab765db60737334d34e3793c03ffb441..69b9c1b8fafc6f72bb9dc010b1a4422c20ce6c3e 100644 (file)
@@ -105,18 +105,18 @@ cflags-$(CONFIG_CPU_R4300)        += -march=r4300 -Wa,--trap
 cflags-$(CONFIG_CPU_VR41XX)    += -march=r4100 -Wa,--trap
 cflags-$(CONFIG_CPU_R4X00)     += -march=r4600 -Wa,--trap
 cflags-$(CONFIG_CPU_TX49XX)    += -march=r4600 -Wa,--trap
-cflags-$(CONFIG_CPU_MIPS32_R1) += $(call cc-option,-march=mips32,-mips2 -mtune=r4600) \
+cflags-$(CONFIG_CPU_MIPS32_R1) += $(call cc-option,-march=mips32,-mips32 -U_MIPS_ISA -D_MIPS_ISA=_MIPS_ISA_MIPS32) \
                        -Wa,-mips32 -Wa,--trap
-cflags-$(CONFIG_CPU_MIPS32_R2) += $(call cc-option,-march=mips32r2,-mips2 -mtune=r4600) \
+cflags-$(CONFIG_CPU_MIPS32_R2) += $(call cc-option,-march=mips32r2,-mips32r2 -U_MIPS_ISA -D_MIPS_ISA=_MIPS_ISA_MIPS32) \
                        -Wa,-mips32r2 -Wa,--trap
-cflags-$(CONFIG_CPU_MIPS64_R1) += $(call cc-option,-march=mips64,-mips2 -mtune=r4600) \
+cflags-$(CONFIG_CPU_MIPS64_R1) += $(call cc-option,-march=mips64,-mips64 -U_MIPS_ISA -D_MIPS_ISA=_MIPS_ISA_MIPS64) \
                        -Wa,-mips64 -Wa,--trap
-cflags-$(CONFIG_CPU_MIPS64_R2) += $(call cc-option,-march=mips64r2,-mips2 -mtune=r4600 ) \
+cflags-$(CONFIG_CPU_MIPS64_R2) += $(call cc-option,-march=mips64r2,-mips64r2 -U_MIPS_ISA -D_MIPS_ISA=_MIPS_ISA_MIPS64) \
                        -Wa,-mips64r2 -Wa,--trap
 cflags-$(CONFIG_CPU_R5000)     += -march=r5000 -Wa,--trap
-cflags-$(CONFIG_CPU_R5432)     += $(call cc-options,-march=r5400,-march=r5000) \
+cflags-$(CONFIG_CPU_R5432)     += $(call cc-option,-march=r5400,-march=r5000) \
                        -Wa,--trap
-cflags-$(CONFIG_CPU_NEVADA)    += $(call cc-options,-march=rm5200,-march=r5000) \
+cflags-$(CONFIG_CPU_NEVADA)    += $(call cc-option,-march=rm5200,-march=r5000) \
                        -Wa,--trap
 cflags-$(CONFIG_CPU_RM7000)    += $(call cc-option,-march=rm7000,-march=r5000) \
                        -Wa,--trap
index a1edfd1f643c4f53a7ec3b0889a6db0b1441197c..bf682f50b8598b18f8dc29a6c3698fa2c96fd778 100644 (file)
@@ -6,7 +6,7 @@
 # Makefile for the Alchemy Au1000 CPU, generic files.
 #
 
-obj-y += prom.o int-handler.o irq.o puts.o time.o reset.o \
+obj-y += prom.o irq.o puts.o time.o reset.o \
        au1xxx_irqmap.o clocks.o platform.o power.o setup.o \
        sleeper.o cputable.o dma.o dbdma.o gpio.o
 
diff --git a/arch/mips/au1000/common/int-handler.S b/arch/mips/au1000/common/int-handler.S
deleted file mode 100644 (file)
index 1c4ca88..0000000
+++ /dev/null
@@ -1,68 +0,0 @@
-/*
- * Copyright 2001 MontaVista Software Inc.
- * Author: ppopov@mvista.com
- *
- * Interrupt dispatcher for Au1000 boards.
- *
- * This program is free software; you can redistribute it and/or modify it
- * under  the terms of the GNU General  Public License as published by the
- * Free Software Foundation;  either version 2 of the  License, or (at your
- * option) any later version.
- */
-#include <asm/asm.h>
-#include <asm/mipsregs.h>
-#include <asm/addrspace.h>
-#include <asm/regdef.h>
-#include <asm/stackframe.h>
-
-       .text
-       .set    macro
-       .set    noat
-       .align  5
-
-NESTED(au1000_IRQ, PT_SIZE, sp)
-       SAVE_ALL
-       CLI                             # Important: mark KERNEL mode !
-
-       mfc0    t0,CP0_CAUSE            # get pending interrupts
-       mfc0    t1,CP0_STATUS           # get enabled interrupts
-       and     t0,t1                   # isolate allowed ones
-
-       andi    t0,0xff00               # isolate pending bits
-       beqz    t0, 3f                  # spurious interrupt
-
-       andi    a0, t0, CAUSEF_IP7
-       beq     a0, zero, 1f
-       move    a0, sp
-       jal     mips_timer_interrupt
-       j       ret_from_irq
-
-1:
-       andi    a0, t0, CAUSEF_IP2      # Interrupt Controller 0, Request 0
-       beq     a0, zero, 2f
-       move    a0,sp
-       jal     intc0_req0_irqdispatch
-       j       ret_from_irq
-2:
-       andi    a0, t0, CAUSEF_IP3      # Interrupt Controller 0, Request 1
-       beq     a0, zero, 3f
-       move    a0,sp
-       jal     intc0_req1_irqdispatch
-       j       ret_from_irq
-3:
-       andi    a0, t0, CAUSEF_IP4      # Interrupt Controller 1, Request 0
-       beq     a0, zero, 4f
-       move    a0,sp
-       jal     intc1_req0_irqdispatch
-       j       ret_from_irq
-4:
-       andi    a0, t0, CAUSEF_IP5      # Interrupt Controller 1, Request 1
-       beq     a0, zero, 5f
-       move    a0, sp
-       jal     intc1_req1_irqdispatch
-       j       ret_from_irq
-
-5:
-       move    a0, sp
-       j       spurious_interrupt
-END(au1000_IRQ)
index 1339a0979f66d61be72c1e65fdce3856ff558149..da61de7761549d89c3e5bc08204ebbdfdea5cd2a 100644 (file)
@@ -66,7 +66,6 @@
 #define EXT_INTC1_REQ1 5 /* IP 5 */
 #define MIPS_TIMER_IP  7 /* IP 7 */
 
-extern asmlinkage void au1000_IRQ(void);
 extern void set_debug_traps(void);
 extern irq_cpustat_t irq_stat [NR_CPUS];
 
@@ -446,7 +445,6 @@ void __init arch_init_irq(void)
        extern int au1xxx_ic0_nr_irqs;
 
        cp0_status = read_c0_status();
-       set_except_vector(0, au1000_IRQ);
 
        /* Initialize interrupt controllers to a safe state.
        */
@@ -661,3 +659,21 @@ restore_au1xxx_intctl(void)
        au_writel(sleep_intctl_mask[0], IC0_MASKSET); au_sync();
 }
 #endif /* CONFIG_PM */
+
+asmlinkage void plat_irq_dispatch(struct pt_regs *regs)
+{
+       unsigned int pending = read_c0_status() & read_c0_cause() & ST0_IM;
+
+       if (pending & CAUSEF_IP7)
+               mips_timer_interrupt(regs);
+       else if (pending & CAUSEF_IP2)
+               intc0_req0_irqdispatch(regs);
+       else if (pending & CAUSEF_IP3)
+               intc0_req1_irqdispatch(regs);
+       else if (pending & CAUSEF_IP4)
+               intc1_req0_irqdispatch(regs);
+       else if (pending  & CAUSEF_IP5)
+               intc1_req1_irqdispatch(regs);
+       else
+               spurious_interrupt(regs);
+}
index 720e757b2b6413cded55f094fc802bd565671412..225ac8f34ccd574cb3dd6f9d68d9d569c4782ada 100644 (file)
@@ -2,7 +2,7 @@
 # Makefile for the Cobalt micro systems family specific parts of the kernel
 #
 
-obj-y   := irq.o int-handler.o reset.o setup.o
+obj-y   := irq.o reset.o setup.o
 
 obj-$(CONFIG_EARLY_PRINTK)     += console.o
 
diff --git a/arch/mips/cobalt/int-handler.S b/arch/mips/cobalt/int-handler.S
deleted file mode 100644 (file)
index e75d5e3..0000000
+++ /dev/null
@@ -1,25 +0,0 @@
-/*
- * This file is subject to the terms and conditions of the GNU General Public
- * License.  See the file "COPYING" in the main directory of this archive
- * for more details.
- *
- * Copyright (C) 1995, 1996, 1997, 2003 by Ralf Baechle
- * Copyright (C) 2001, 2002, 2003 by Liam Davies (ldavies@agile.tv)
- */
-#include <asm/asm.h>
-#include <asm/mipsregs.h>
-#include <asm/mach-cobalt/cobalt.h>
-#include <asm/regdef.h>
-#include <asm/stackframe.h>
-
-               .text
-               .align  5
-               NESTED(cobalt_handle_int, PT_SIZE, sp)
-               SAVE_ALL
-               CLI
-
-               PTR_LA  ra, ret_from_irq
-               move    a0, sp
-               j       cobalt_irq
-
-               END(cobalt_handle_int)
index f9a108820d6e2d1245eb64ac942df5418fba03e0..0b75f4fb719570ef4a8f29be227e8c1f3d5d00d0 100644 (file)
@@ -20,8 +20,6 @@
 
 #include <asm/mach-cobalt/cobalt.h>
 
-extern void cobalt_handle_int(void);
-
 /*
  * We have two types of interrupts that we handle, ones that come in through
  * the CPU interrupt lines, and ones that come in on the via chip. The CPU
@@ -79,7 +77,7 @@ static inline void via_pic_irq(struct pt_regs *regs)
                do_IRQ(irq, regs);
 }
 
-asmlinkage void cobalt_irq(struct pt_regs *regs)
+asmlinkage void plat_irq_dispatch(struct pt_regs *regs)
 {
        unsigned pending;
 
@@ -122,8 +120,6 @@ void __init arch_init_irq(void)
         */
        GALILEO_OUTL(0, GT_INTRMASK_OFS);
 
-       set_except_vector(0, cobalt_handle_int);
-
        init_i8259_irqs();                              /*  0 ... 15 */
        mips_cpu_irq_init(COBALT_CPU_IRQ);              /* 16 ... 23 */
 
diff --git a/arch/mips/configs/tb0287_defconfig b/arch/mips/configs/tb0287_defconfig
new file mode 100644 (file)
index 0000000..8a1e3ac
--- /dev/null
@@ -0,0 +1,1096 @@
+#
+# Automatically generated make config: don't edit
+# Linux kernel version: 2.6.16
+# Wed Mar 22 11:07:34 2006
+#
+CONFIG_MIPS=y
+
+#
+# Machine selection
+#
+# CONFIG_MIPS_MTX1 is not set
+# CONFIG_MIPS_BOSPORUS is not set
+# CONFIG_MIPS_PB1000 is not set
+# CONFIG_MIPS_PB1100 is not set
+# CONFIG_MIPS_PB1500 is not set
+# CONFIG_MIPS_PB1550 is not set
+# CONFIG_MIPS_PB1200 is not set
+# CONFIG_MIPS_DB1000 is not set
+# CONFIG_MIPS_DB1100 is not set
+# CONFIG_MIPS_DB1500 is not set
+# CONFIG_MIPS_DB1550 is not set
+# CONFIG_MIPS_DB1200 is not set
+# CONFIG_MIPS_MIRAGE is not set
+# CONFIG_MIPS_COBALT is not set
+# CONFIG_MACH_DECSTATION is not set
+# CONFIG_MIPS_EV64120 is not set
+# CONFIG_MIPS_EV96100 is not set
+# CONFIG_MIPS_IVR is not set
+# CONFIG_MIPS_ITE8172 is not set
+# CONFIG_MACH_JAZZ is not set
+# CONFIG_LASAT is not set
+# CONFIG_MIPS_ATLAS is not set
+# CONFIG_MIPS_MALTA is not set
+# CONFIG_MIPS_SEAD is not set
+# CONFIG_MIPS_SIM is not set
+# CONFIG_MOMENCO_JAGUAR_ATX is not set
+# CONFIG_MOMENCO_OCELOT is not set
+# CONFIG_MOMENCO_OCELOT_3 is not set
+# CONFIG_MOMENCO_OCELOT_C is not set
+# CONFIG_MOMENCO_OCELOT_G is not set
+# CONFIG_MIPS_XXS1500 is not set
+# CONFIG_PNX8550_V2PCI is not set
+# CONFIG_PNX8550_JBS is not set
+# CONFIG_DDB5074 is not set
+# CONFIG_DDB5476 is not set
+# CONFIG_DDB5477 is not set
+CONFIG_MACH_VR41XX=y
+# CONFIG_PMC_YOSEMITE is not set
+# CONFIG_QEMU is not set
+# CONFIG_SGI_IP22 is not set
+# CONFIG_SGI_IP27 is not set
+# CONFIG_SGI_IP32 is not set
+# CONFIG_SIBYTE_BIGSUR is not set
+# CONFIG_SIBYTE_SWARM is not set
+# CONFIG_SIBYTE_SENTOSA is not set
+# CONFIG_SIBYTE_RHONE is not set
+# CONFIG_SIBYTE_CARMEL is not set
+# CONFIG_SIBYTE_PTSWARM is not set
+# CONFIG_SIBYTE_LITTLESUR is not set
+# CONFIG_SIBYTE_CRHINE is not set
+# CONFIG_SIBYTE_CRHONE is not set
+# CONFIG_SNI_RM200_PCI is not set
+# CONFIG_TOSHIBA_JMR3927 is not set
+# CONFIG_TOSHIBA_RBTX4927 is not set
+# CONFIG_TOSHIBA_RBTX4938 is not set
+# CONFIG_CASIO_E55 is not set
+# CONFIG_IBM_WORKPAD is not set
+# CONFIG_NEC_CMBVR4133 is not set
+CONFIG_TANBAC_TB022X=y
+# CONFIG_TANBAC_TB0226 is not set
+CONFIG_TANBAC_TB0287=y
+# CONFIG_VICTOR_MPC30X is not set
+# CONFIG_ZAO_CAPCELLA is not set
+CONFIG_PCI_VR41XX=y
+# CONFIG_VRC4173 is not set
+CONFIG_RWSEM_GENERIC_SPINLOCK=y
+CONFIG_GENERIC_CALIBRATE_DELAY=y
+CONFIG_DMA_NONCOHERENT=y
+CONFIG_DMA_NEED_PCI_MAP_STATE=y
+# CONFIG_CPU_BIG_ENDIAN is not set
+CONFIG_CPU_LITTLE_ENDIAN=y
+CONFIG_SYS_SUPPORTS_LITTLE_ENDIAN=y
+CONFIG_IRQ_CPU=y
+CONFIG_MIPS_L1_CACHE_SHIFT=5
+
+#
+# CPU selection
+#
+# CONFIG_CPU_MIPS32_R1 is not set
+# CONFIG_CPU_MIPS32_R2 is not set
+# CONFIG_CPU_MIPS64_R1 is not set
+# CONFIG_CPU_MIPS64_R2 is not set
+# CONFIG_CPU_R3000 is not set
+# CONFIG_CPU_TX39XX is not set
+CONFIG_CPU_VR41XX=y
+# CONFIG_CPU_R4300 is not set
+# CONFIG_CPU_R4X00 is not set
+# CONFIG_CPU_TX49XX is not set
+# CONFIG_CPU_R5000 is not set
+# CONFIG_CPU_R5432 is not set
+# CONFIG_CPU_R6000 is not set
+# CONFIG_CPU_NEVADA is not set
+# CONFIG_CPU_R8000 is not set
+# CONFIG_CPU_R10000 is not set
+# CONFIG_CPU_RM7000 is not set
+# CONFIG_CPU_RM9000 is not set
+# CONFIG_CPU_SB1 is not set
+CONFIG_SYS_HAS_CPU_VR41XX=y
+CONFIG_SYS_SUPPORTS_32BIT_KERNEL=y
+CONFIG_SYS_SUPPORTS_64BIT_KERNEL=y
+CONFIG_CPU_SUPPORTS_32BIT_KERNEL=y
+CONFIG_CPU_SUPPORTS_64BIT_KERNEL=y
+
+#
+# Kernel type
+#
+CONFIG_32BIT=y
+# CONFIG_64BIT is not set
+CONFIG_PAGE_SIZE_4KB=y
+# CONFIG_PAGE_SIZE_8KB is not set
+# CONFIG_PAGE_SIZE_16KB is not set
+# CONFIG_PAGE_SIZE_64KB is not set
+# CONFIG_MIPS_MT is not set
+# CONFIG_CPU_ADVANCED is not set
+CONFIG_CPU_HAS_SYNC=y
+CONFIG_GENERIC_HARDIRQS=y
+CONFIG_GENERIC_IRQ_PROBE=y
+CONFIG_ARCH_FLATMEM_ENABLE=y
+CONFIG_SELECT_MEMORY_MODEL=y
+CONFIG_FLATMEM_MANUAL=y
+# CONFIG_DISCONTIGMEM_MANUAL is not set
+# CONFIG_SPARSEMEM_MANUAL is not set
+CONFIG_FLATMEM=y
+CONFIG_FLAT_NODE_MEM_MAP=y
+# CONFIG_SPARSEMEM_STATIC is not set
+CONFIG_SPLIT_PTLOCK_CPUS=4
+CONFIG_PREEMPT_NONE=y
+# CONFIG_PREEMPT_VOLUNTARY is not set
+# CONFIG_PREEMPT is not set
+
+#
+# Code maturity level options
+#
+CONFIG_EXPERIMENTAL=y
+CONFIG_BROKEN_ON_SMP=y
+CONFIG_INIT_ENV_ARG_LIMIT=32
+
+#
+# General setup
+#
+CONFIG_LOCALVERSION=""
+CONFIG_LOCALVERSION_AUTO=y
+CONFIG_SWAP=y
+CONFIG_SYSVIPC=y
+# CONFIG_POSIX_MQUEUE is not set
+# CONFIG_BSD_PROCESS_ACCT is not set
+CONFIG_SYSCTL=y
+# CONFIG_AUDIT is not set
+# CONFIG_IKCONFIG is not set
+CONFIG_INITRAMFS_SOURCE=""
+# CONFIG_CC_OPTIMIZE_FOR_SIZE is not set
+CONFIG_EMBEDDED=y
+CONFIG_KALLSYMS=y
+# CONFIG_KALLSYMS_EXTRA_PASS is not set
+# CONFIG_HOTPLUG is not set
+CONFIG_PRINTK=y
+CONFIG_BUG=y
+CONFIG_ELF_CORE=y
+CONFIG_BASE_FULL=y
+CONFIG_FUTEX=y
+CONFIG_EPOLL=y
+CONFIG_SHMEM=y
+CONFIG_CC_ALIGN_FUNCTIONS=0
+CONFIG_CC_ALIGN_LABELS=0
+CONFIG_CC_ALIGN_LOOPS=0
+CONFIG_CC_ALIGN_JUMPS=0
+CONFIG_SLAB=y
+# CONFIG_TINY_SHMEM is not set
+CONFIG_BASE_SMALL=0
+# CONFIG_SLOB is not set
+
+#
+# Loadable module support
+#
+CONFIG_MODULES=y
+CONFIG_MODULE_UNLOAD=y
+# CONFIG_MODULE_FORCE_UNLOAD is not set
+CONFIG_OBSOLETE_MODPARM=y
+CONFIG_MODVERSIONS=y
+CONFIG_MODULE_SRCVERSION_ALL=y
+CONFIG_KMOD=y
+
+#
+# Block layer
+#
+# CONFIG_LBD is not set
+
+#
+# IO Schedulers
+#
+CONFIG_IOSCHED_NOOP=y
+CONFIG_IOSCHED_AS=y
+CONFIG_IOSCHED_DEADLINE=y
+CONFIG_IOSCHED_CFQ=y
+CONFIG_DEFAULT_AS=y
+# CONFIG_DEFAULT_DEADLINE is not set
+# CONFIG_DEFAULT_CFQ is not set
+# CONFIG_DEFAULT_NOOP is not set
+CONFIG_DEFAULT_IOSCHED="anticipatory"
+
+#
+# Bus options (PCI, PCMCIA, EISA, ISA, TC)
+#
+CONFIG_HW_HAS_PCI=y
+CONFIG_PCI=y
+# CONFIG_PCI_LEGACY_PROC is not set
+CONFIG_MMU=y
+
+#
+# PCCARD (PCMCIA/CardBus) support
+#
+# CONFIG_PCCARD is not set
+
+#
+# PCI Hotplug Support
+#
+# CONFIG_HOTPLUG_PCI is not set
+
+#
+# Executable file formats
+#
+CONFIG_BINFMT_ELF=y
+# CONFIG_BINFMT_MISC is not set
+CONFIG_TRAD_SIGNALS=y
+
+#
+# Networking
+#
+CONFIG_NET=y
+
+#
+# Networking options
+#
+# CONFIG_NETDEBUG is not set
+CONFIG_PACKET=y
+# CONFIG_PACKET_MMAP is not set
+CONFIG_UNIX=y
+CONFIG_XFRM=y
+CONFIG_XFRM_USER=m
+# CONFIG_NET_KEY is not set
+CONFIG_INET=y
+CONFIG_IP_MULTICAST=y
+CONFIG_IP_ADVANCED_ROUTER=y
+CONFIG_ASK_IP_FIB_HASH=y
+# CONFIG_IP_FIB_TRIE is not set
+CONFIG_IP_FIB_HASH=y
+CONFIG_IP_MULTIPLE_TABLES=y
+CONFIG_IP_ROUTE_MULTIPATH=y
+# CONFIG_IP_ROUTE_MULTIPATH_CACHED is not set
+CONFIG_IP_ROUTE_VERBOSE=y
+CONFIG_IP_PNP=y
+# CONFIG_IP_PNP_DHCP is not set
+CONFIG_IP_PNP_BOOTP=y
+# CONFIG_IP_PNP_RARP is not set
+CONFIG_NET_IPIP=m
+CONFIG_NET_IPGRE=m
+# CONFIG_NET_IPGRE_BROADCAST is not set
+# CONFIG_IP_MROUTE is not set
+# CONFIG_ARPD is not set
+CONFIG_SYN_COOKIES=y
+# CONFIG_INET_AH is not set
+# CONFIG_INET_ESP is not set
+# CONFIG_INET_IPCOMP is not set
+CONFIG_INET_TUNNEL=m
+CONFIG_INET_DIAG=y
+CONFIG_INET_TCP_DIAG=y
+CONFIG_TCP_CONG_ADVANCED=y
+
+#
+# TCP congestion control
+#
+CONFIG_TCP_CONG_BIC=y
+CONFIG_TCP_CONG_CUBIC=m
+CONFIG_TCP_CONG_WESTWOOD=m
+CONFIG_TCP_CONG_HTCP=m
+# CONFIG_TCP_CONG_HSTCP is not set
+# CONFIG_TCP_CONG_HYBLA is not set
+# CONFIG_TCP_CONG_VEGAS is not set
+# CONFIG_TCP_CONG_SCALABLE is not set
+# CONFIG_IPV6 is not set
+# CONFIG_NETFILTER is not set
+
+#
+# DCCP Configuration (EXPERIMENTAL)
+#
+# CONFIG_IP_DCCP is not set
+
+#
+# SCTP Configuration (EXPERIMENTAL)
+#
+# CONFIG_IP_SCTP is not set
+
+#
+# TIPC Configuration (EXPERIMENTAL)
+#
+# CONFIG_TIPC is not set
+# CONFIG_ATM is not set
+# CONFIG_BRIDGE is not set
+# CONFIG_VLAN_8021Q is not set
+# CONFIG_DECNET is not set
+# CONFIG_LLC2 is not set
+# CONFIG_IPX is not set
+# CONFIG_ATALK is not set
+# CONFIG_X25 is not set
+# CONFIG_LAPB is not set
+# CONFIG_NET_DIVERT is not set
+# CONFIG_ECONET is not set
+# CONFIG_WAN_ROUTER is not set
+
+#
+# QoS and/or fair queueing
+#
+# CONFIG_NET_SCHED is not set
+
+#
+# Network testing
+#
+# CONFIG_NET_PKTGEN is not set
+# CONFIG_HAMRADIO is not set
+# CONFIG_IRDA is not set
+# CONFIG_BT is not set
+# CONFIG_IEEE80211 is not set
+
+#
+# Device Drivers
+#
+
+#
+# Generic Driver Options
+#
+CONFIG_STANDALONE=y
+CONFIG_PREVENT_FIRMWARE_BUILD=y
+# CONFIG_FW_LOADER is not set
+
+#
+# Connector - unified userspace <-> kernelspace linker
+#
+# CONFIG_CONNECTOR is not set
+
+#
+# Memory Technology Devices (MTD)
+#
+# CONFIG_MTD is not set
+
+#
+# Parallel port support
+#
+# CONFIG_PARPORT is not set
+
+#
+# Plug and Play support
+#
+
+#
+# Block devices
+#
+# CONFIG_BLK_CPQ_DA is not set
+# CONFIG_BLK_CPQ_CISS_DA is not set
+# CONFIG_BLK_DEV_DAC960 is not set
+# CONFIG_BLK_DEV_UMEM is not set
+# CONFIG_BLK_DEV_COW_COMMON is not set
+CONFIG_BLK_DEV_LOOP=m
+# CONFIG_BLK_DEV_CRYPTOLOOP is not set
+CONFIG_BLK_DEV_NBD=m
+# CONFIG_BLK_DEV_SX8 is not set
+# CONFIG_BLK_DEV_UB is not set
+CONFIG_BLK_DEV_RAM=y
+CONFIG_BLK_DEV_RAM_COUNT=16
+CONFIG_BLK_DEV_RAM_SIZE=4096
+# CONFIG_BLK_DEV_INITRD is not set
+# CONFIG_CDROM_PKTCDVD is not set
+# CONFIG_ATA_OVER_ETH is not set
+
+#
+# ATA/ATAPI/MFM/RLL support
+#
+CONFIG_IDE=y
+CONFIG_BLK_DEV_IDE=y
+
+#
+# Please see Documentation/ide.txt for help/info on IDE drives
+#
+# CONFIG_BLK_DEV_IDE_SATA is not set
+CONFIG_BLK_DEV_IDEDISK=y
+# CONFIG_IDEDISK_MULTI_MODE is not set
+# CONFIG_BLK_DEV_IDECD is not set
+# CONFIG_BLK_DEV_IDETAPE is not set
+# CONFIG_BLK_DEV_IDEFLOPPY is not set
+# CONFIG_BLK_DEV_IDESCSI is not set
+# CONFIG_IDE_TASK_IOCTL is not set
+
+#
+# IDE chipset support/bugfixes
+#
+CONFIG_IDE_GENERIC=y
+CONFIG_BLK_DEV_IDEPCI=y
+# CONFIG_IDEPCI_SHARE_IRQ is not set
+# CONFIG_BLK_DEV_OFFBOARD is not set
+# CONFIG_BLK_DEV_GENERIC is not set
+# CONFIG_BLK_DEV_OPTI621 is not set
+CONFIG_BLK_DEV_IDEDMA_PCI=y
+# CONFIG_BLK_DEV_IDEDMA_FORCED is not set
+# CONFIG_IDEDMA_PCI_AUTO is not set
+# CONFIG_BLK_DEV_AEC62XX is not set
+# CONFIG_BLK_DEV_ALI15X3 is not set
+# CONFIG_BLK_DEV_AMD74XX is not set
+# CONFIG_BLK_DEV_CMD64X is not set
+# CONFIG_BLK_DEV_TRIFLEX is not set
+# CONFIG_BLK_DEV_CY82C693 is not set
+# CONFIG_BLK_DEV_CS5520 is not set
+# CONFIG_BLK_DEV_CS5530 is not set
+# CONFIG_BLK_DEV_HPT34X is not set
+# CONFIG_BLK_DEV_HPT366 is not set
+# CONFIG_BLK_DEV_SC1200 is not set
+# CONFIG_BLK_DEV_PIIX is not set
+# CONFIG_BLK_DEV_IT821X is not set
+# CONFIG_BLK_DEV_NS87415 is not set
+# CONFIG_BLK_DEV_PDC202XX_OLD is not set
+# CONFIG_BLK_DEV_PDC202XX_NEW is not set
+# CONFIG_BLK_DEV_SVWKS is not set
+CONFIG_BLK_DEV_SIIMAGE=y
+# CONFIG_BLK_DEV_SLC90E66 is not set
+# CONFIG_BLK_DEV_TRM290 is not set
+# CONFIG_BLK_DEV_VIA82CXXX is not set
+# CONFIG_IDE_ARM is not set
+CONFIG_BLK_DEV_IDEDMA=y
+# CONFIG_IDEDMA_IVB is not set
+# CONFIG_IDEDMA_AUTO is not set
+# CONFIG_BLK_DEV_HD is not set
+
+#
+# SCSI device support
+#
+# CONFIG_RAID_ATTRS is not set
+CONFIG_SCSI=y
+CONFIG_SCSI_PROC_FS=y
+
+#
+# SCSI support type (disk, tape, CD-ROM)
+#
+CONFIG_BLK_DEV_SD=y
+# CONFIG_CHR_DEV_ST is not set
+# CONFIG_CHR_DEV_OSST is not set
+# CONFIG_BLK_DEV_SR is not set
+# CONFIG_CHR_DEV_SG is not set
+# CONFIG_CHR_DEV_SCH is not set
+
+#
+# Some SCSI devices (e.g. CD jukebox) support multiple LUNs
+#
+# CONFIG_SCSI_MULTI_LUN is not set
+# CONFIG_SCSI_CONSTANTS is not set
+# CONFIG_SCSI_LOGGING is not set
+
+#
+# SCSI Transport Attributes
+#
+# CONFIG_SCSI_SPI_ATTRS is not set
+# CONFIG_SCSI_FC_ATTRS is not set
+# CONFIG_SCSI_ISCSI_ATTRS is not set
+# CONFIG_SCSI_SAS_ATTRS is not set
+
+#
+# SCSI low-level drivers
+#
+# CONFIG_ISCSI_TCP is not set
+# CONFIG_BLK_DEV_3W_XXXX_RAID is not set
+# CONFIG_SCSI_3W_9XXX is not set
+# CONFIG_SCSI_ACARD is not set
+# CONFIG_SCSI_AACRAID is not set
+# CONFIG_SCSI_AIC7XXX is not set
+# CONFIG_SCSI_AIC7XXX_OLD is not set
+# CONFIG_SCSI_AIC79XX is not set
+# CONFIG_SCSI_DPT_I2O is not set
+# CONFIG_MEGARAID_NEWGEN is not set
+# CONFIG_MEGARAID_LEGACY is not set
+# CONFIG_MEGARAID_SAS is not set
+# CONFIG_SCSI_SATA is not set
+# CONFIG_SCSI_DMX3191D is not set
+# CONFIG_SCSI_FUTURE_DOMAIN is not set
+# CONFIG_SCSI_IPS is not set
+# CONFIG_SCSI_INITIO is not set
+# CONFIG_SCSI_INIA100 is not set
+# CONFIG_SCSI_SYM53C8XX_2 is not set
+# CONFIG_SCSI_IPR is not set
+# CONFIG_SCSI_QLOGIC_FC is not set
+# CONFIG_SCSI_QLOGIC_1280 is not set
+# CONFIG_SCSI_QLA_FC is not set
+# CONFIG_SCSI_LPFC is not set
+# CONFIG_SCSI_DC395x is not set
+# CONFIG_SCSI_DC390T is not set
+# CONFIG_SCSI_NSP32 is not set
+# CONFIG_SCSI_DEBUG is not set
+
+#
+# Multi-device support (RAID and LVM)
+#
+# CONFIG_MD is not set
+
+#
+# Fusion MPT device support
+#
+# CONFIG_FUSION is not set
+# CONFIG_FUSION_SPI is not set
+# CONFIG_FUSION_FC is not set
+# CONFIG_FUSION_SAS is not set
+
+#
+# IEEE 1394 (FireWire) support
+#
+CONFIG_IEEE1394=m
+
+#
+# Subsystem Options
+#
+# CONFIG_IEEE1394_VERBOSEDEBUG is not set
+# CONFIG_IEEE1394_OUI_DB is not set
+CONFIG_IEEE1394_EXTRA_CONFIG_ROMS=y
+CONFIG_IEEE1394_CONFIG_ROM_IP1394=y
+# CONFIG_IEEE1394_EXPORT_FULL_API is not set
+
+#
+# Device Drivers
+#
+
+#
+# Texas Instruments PCILynx requires I2C
+#
+CONFIG_IEEE1394_OHCI1394=m
+
+#
+# Protocol Drivers
+#
+CONFIG_IEEE1394_VIDEO1394=m
+CONFIG_IEEE1394_SBP2=m
+# CONFIG_IEEE1394_SBP2_PHYS_DMA is not set
+CONFIG_IEEE1394_ETH1394=m
+CONFIG_IEEE1394_DV1394=m
+CONFIG_IEEE1394_RAWIO=m
+
+#
+# I2O device support
+#
+# CONFIG_I2O is not set
+
+#
+# Network device support
+#
+CONFIG_NETDEVICES=y
+CONFIG_DUMMY=m
+# CONFIG_BONDING is not set
+# CONFIG_EQUALIZER is not set
+# CONFIG_TUN is not set
+
+#
+# ARCnet devices
+#
+# CONFIG_ARCNET is not set
+
+#
+# PHY device support
+#
+# CONFIG_PHYLIB is not set
+
+#
+# Ethernet (10 or 100Mbit)
+#
+CONFIG_NET_ETHERNET=y
+CONFIG_MII=y
+# CONFIG_HAPPYMEAL is not set
+# CONFIG_SUNGEM is not set
+# CONFIG_CASSINI is not set
+# CONFIG_NET_VENDOR_3COM is not set
+# CONFIG_DM9000 is not set
+
+#
+# Tulip family network device support
+#
+# CONFIG_NET_TULIP is not set
+# CONFIG_HP100 is not set
+# CONFIG_NET_PCI is not set
+
+#
+# Ethernet (1000 Mbit)
+#
+# CONFIG_ACENIC is not set
+# CONFIG_DL2K is not set
+# CONFIG_E1000 is not set
+# CONFIG_NS83820 is not set
+# CONFIG_HAMACHI is not set
+# CONFIG_YELLOWFIN is not set
+CONFIG_R8169=y
+# CONFIG_R8169_NAPI is not set
+# CONFIG_SIS190 is not set
+# CONFIG_SKGE is not set
+# CONFIG_SKY2 is not set
+# CONFIG_SK98LIN is not set
+# CONFIG_TIGON3 is not set
+# CONFIG_BNX2 is not set
+
+#
+# Ethernet (10000 Mbit)
+#
+# CONFIG_CHELSIO_T1 is not set
+# CONFIG_IXGB is not set
+# CONFIG_S2IO is not set
+
+#
+# Token Ring devices
+#
+# CONFIG_TR is not set
+
+#
+# Wireless LAN (non-hamradio)
+#
+# CONFIG_NET_RADIO is not set
+
+#
+# Wan interfaces
+#
+# CONFIG_WAN is not set
+# CONFIG_FDDI is not set
+# CONFIG_HIPPI is not set
+# CONFIG_PPP is not set
+# CONFIG_SLIP is not set
+# CONFIG_NET_FC is not set
+# CONFIG_SHAPER is not set
+# CONFIG_NETCONSOLE is not set
+# CONFIG_NETPOLL is not set
+# CONFIG_NET_POLL_CONTROLLER is not set
+
+#
+# ISDN subsystem
+#
+# CONFIG_ISDN is not set
+
+#
+# Telephony Support
+#
+# CONFIG_PHONE is not set
+
+#
+# Input device support
+#
+CONFIG_INPUT=y
+
+#
+# Userland interfaces
+#
+# CONFIG_INPUT_MOUSEDEV is not set
+# CONFIG_INPUT_JOYDEV is not set
+# CONFIG_INPUT_TSDEV is not set
+# CONFIG_INPUT_EVDEV is not set
+# CONFIG_INPUT_EVBUG is not set
+
+#
+# Input Device Drivers
+#
+# CONFIG_INPUT_KEYBOARD is not set
+# CONFIG_INPUT_MOUSE is not set
+# CONFIG_INPUT_JOYSTICK is not set
+# CONFIG_INPUT_TOUCHSCREEN is not set
+# CONFIG_INPUT_MISC is not set
+
+#
+# Hardware I/O ports
+#
+# CONFIG_SERIO is not set
+# CONFIG_GAMEPORT is not set
+
+#
+# Character devices
+#
+CONFIG_VT=y
+CONFIG_VT_CONSOLE=y
+CONFIG_HW_CONSOLE=y
+# CONFIG_SERIAL_NONSTANDARD is not set
+
+#
+# Serial drivers
+#
+# CONFIG_SERIAL_8250 is not set
+
+#
+# Non-8250 serial port support
+#
+CONFIG_SERIAL_CORE=y
+CONFIG_SERIAL_CORE_CONSOLE=y
+CONFIG_SERIAL_VR41XX=y
+CONFIG_SERIAL_VR41XX_CONSOLE=y
+# CONFIG_SERIAL_JSM is not set
+CONFIG_UNIX98_PTYS=y
+CONFIG_LEGACY_PTYS=y
+CONFIG_LEGACY_PTY_COUNT=256
+
+#
+# IPMI
+#
+# CONFIG_IPMI_HANDLER is not set
+
+#
+# Watchdog Cards
+#
+# CONFIG_WATCHDOG is not set
+# CONFIG_RTC is not set
+# CONFIG_GEN_RTC is not set
+# CONFIG_RTC_VR41XX is not set
+# CONFIG_DTLK is not set
+# CONFIG_R3964 is not set
+# CONFIG_APPLICOM is not set
+# CONFIG_TANBAC_TB0219 is not set
+
+#
+# Ftape, the floppy tape device driver
+#
+# CONFIG_DRM is not set
+CONFIG_GPIO_VR41XX=y
+# CONFIG_RAW_DRIVER is not set
+
+#
+# TPM devices
+#
+# CONFIG_TCG_TPM is not set
+# CONFIG_TELCLOCK is not set
+
+#
+# I2C support
+#
+# CONFIG_I2C is not set
+
+#
+# SPI support
+#
+# CONFIG_SPI is not set
+# CONFIG_SPI_MASTER is not set
+
+#
+# Dallas's 1-wire bus
+#
+# CONFIG_W1 is not set
+
+#
+# Hardware Monitoring support
+#
+# CONFIG_HWMON is not set
+# CONFIG_HWMON_VID is not set
+
+#
+# Misc devices
+#
+
+#
+# Multimedia Capabilities Port drivers
+#
+
+#
+# Multimedia devices
+#
+# CONFIG_VIDEO_DEV is not set
+
+#
+# Digital Video Broadcasting Devices
+#
+# CONFIG_DVB is not set
+
+#
+# Graphics support
+#
+# CONFIG_FB is not set
+
+#
+# Console display driver support
+#
+# CONFIG_VGA_CONSOLE is not set
+CONFIG_DUMMY_CONSOLE=y
+
+#
+# Sound
+#
+# CONFIG_SOUND is not set
+
+#
+# USB support
+#
+CONFIG_USB_ARCH_HAS_HCD=y
+CONFIG_USB_ARCH_HAS_OHCI=y
+CONFIG_USB=m
+# CONFIG_USB_DEBUG is not set
+
+#
+# Miscellaneous USB options
+#
+# CONFIG_USB_DEVICEFS is not set
+# CONFIG_USB_BANDWIDTH is not set
+# CONFIG_USB_DYNAMIC_MINORS is not set
+# CONFIG_USB_OTG is not set
+
+#
+# USB Host Controller Drivers
+#
+CONFIG_USB_EHCI_HCD=m
+# CONFIG_USB_EHCI_SPLIT_ISO is not set
+# CONFIG_USB_EHCI_ROOT_HUB_TT is not set
+# CONFIG_USB_ISP116X_HCD is not set
+CONFIG_USB_OHCI_HCD=m
+# CONFIG_USB_OHCI_BIG_ENDIAN is not set
+CONFIG_USB_OHCI_LITTLE_ENDIAN=y
+# CONFIG_USB_UHCI_HCD is not set
+# CONFIG_USB_SL811_HCD is not set
+
+#
+# USB Device Class drivers
+#
+# CONFIG_USB_ACM is not set
+# CONFIG_USB_PRINTER is not set
+
+#
+# NOTE: USB_STORAGE enables SCSI, and 'SCSI disk support'
+#
+
+#
+# may also be needed; see USB_STORAGE Help for more information
+#
+CONFIG_USB_STORAGE=m
+# CONFIG_USB_STORAGE_DEBUG is not set
+# CONFIG_USB_STORAGE_DATAFAB is not set
+# CONFIG_USB_STORAGE_FREECOM is not set
+# CONFIG_USB_STORAGE_ISD200 is not set
+# CONFIG_USB_STORAGE_DPCM is not set
+# CONFIG_USB_STORAGE_USBAT is not set
+# CONFIG_USB_STORAGE_SDDR09 is not set
+# CONFIG_USB_STORAGE_SDDR55 is not set
+# CONFIG_USB_STORAGE_JUMPSHOT is not set
+# CONFIG_USB_STORAGE_ALAUDA is not set
+# CONFIG_USB_LIBUSUAL is not set
+
+#
+# USB Input Devices
+#
+CONFIG_USB_HID=m
+CONFIG_USB_HIDINPUT=y
+# CONFIG_USB_HIDINPUT_POWERBOOK is not set
+# CONFIG_HID_FF is not set
+# CONFIG_USB_HIDDEV is not set
+
+#
+# USB HID Boot Protocol drivers
+#
+# CONFIG_USB_KBD is not set
+# CONFIG_USB_MOUSE is not set
+# CONFIG_USB_AIPTEK is not set
+# CONFIG_USB_WACOM is not set
+# CONFIG_USB_ACECAD is not set
+# CONFIG_USB_KBTAB is not set
+# CONFIG_USB_POWERMATE is not set
+# CONFIG_USB_MTOUCH is not set
+# CONFIG_USB_ITMTOUCH is not set
+# CONFIG_USB_EGALAX is not set
+# CONFIG_USB_YEALINK is not set
+# CONFIG_USB_XPAD is not set
+# CONFIG_USB_ATI_REMOTE is not set
+# CONFIG_USB_ATI_REMOTE2 is not set
+# CONFIG_USB_KEYSPAN_REMOTE is not set
+# CONFIG_USB_APPLETOUCH is not set
+
+#
+# USB Imaging devices
+#
+# CONFIG_USB_MDC800 is not set
+# CONFIG_USB_MICROTEK is not set
+
+#
+# USB Multimedia devices
+#
+# CONFIG_USB_DABUSB is not set
+
+#
+# Video4Linux support is needed for USB Multimedia device support
+#
+
+#
+# USB Network Adapters
+#
+# CONFIG_USB_CATC is not set
+# CONFIG_USB_KAWETH is not set
+# CONFIG_USB_PEGASUS is not set
+# CONFIG_USB_RTL8150 is not set
+# CONFIG_USB_USBNET is not set
+CONFIG_USB_MON=y
+
+#
+# USB port drivers
+#
+
+#
+# USB Serial Converter support
+#
+# CONFIG_USB_SERIAL is not set
+
+#
+# USB Miscellaneous drivers
+#
+# CONFIG_USB_EMI62 is not set
+# CONFIG_USB_EMI26 is not set
+# CONFIG_USB_AUERSWALD is not set
+# CONFIG_USB_RIO500 is not set
+# CONFIG_USB_LEGOTOWER is not set
+# CONFIG_USB_LCD is not set
+# CONFIG_USB_LED is not set
+# CONFIG_USB_CYTHERM is not set
+# CONFIG_USB_PHIDGETKIT is not set
+# CONFIG_USB_PHIDGETSERVO is not set
+# CONFIG_USB_IDMOUSE is not set
+# CONFIG_USB_SISUSBVGA is not set
+# CONFIG_USB_LD is not set
+
+#
+# USB DSL modem support
+#
+
+#
+# USB Gadget Support
+#
+# CONFIG_USB_GADGET is not set
+
+#
+# MMC/SD Card support
+#
+# CONFIG_MMC is not set
+
+#
+# InfiniBand support
+#
+# CONFIG_INFINIBAND is not set
+
+#
+# EDAC - error detection and reporting (RAS) (EXPERIMENTAL)
+#
+
+#
+# File systems
+#
+CONFIG_EXT2_FS=y
+# CONFIG_EXT2_FS_XATTR is not set
+# CONFIG_EXT2_FS_XIP is not set
+CONFIG_EXT3_FS=y
+CONFIG_EXT3_FS_XATTR=y
+# CONFIG_EXT3_FS_POSIX_ACL is not set
+# CONFIG_EXT3_FS_SECURITY is not set
+CONFIG_JBD=y
+# CONFIG_JBD_DEBUG is not set
+CONFIG_FS_MBCACHE=y
+# CONFIG_REISERFS_FS is not set
+# CONFIG_JFS_FS is not set
+# CONFIG_FS_POSIX_ACL is not set
+CONFIG_XFS_FS=y
+CONFIG_XFS_QUOTA=y
+# CONFIG_XFS_SECURITY is not set
+CONFIG_XFS_POSIX_ACL=y
+# CONFIG_XFS_RT is not set
+# CONFIG_OCFS2_FS is not set
+# CONFIG_MINIX_FS is not set
+CONFIG_ROMFS_FS=m
+CONFIG_INOTIFY=y
+# CONFIG_QUOTA is not set
+CONFIG_QUOTACTL=y
+# CONFIG_DNOTIFY is not set
+# CONFIG_AUTOFS_FS is not set
+CONFIG_AUTOFS4_FS=y
+# CONFIG_FUSE_FS is not set
+
+#
+# CD-ROM/DVD Filesystems
+#
+# CONFIG_ISO9660_FS is not set
+# CONFIG_UDF_FS is not set
+
+#
+# DOS/FAT/NT Filesystems
+#
+# CONFIG_MSDOS_FS is not set
+# CONFIG_VFAT_FS is not set
+# CONFIG_NTFS_FS is not set
+
+#
+# Pseudo filesystems
+#
+CONFIG_PROC_FS=y
+CONFIG_PROC_KCORE=y
+CONFIG_SYSFS=y
+CONFIG_TMPFS=y
+# CONFIG_HUGETLB_PAGE is not set
+CONFIG_RAMFS=y
+# CONFIG_RELAYFS_FS is not set
+# CONFIG_CONFIGFS_FS is not set
+
+#
+# Miscellaneous filesystems
+#
+# CONFIG_ADFS_FS is not set
+# CONFIG_AFFS_FS is not set
+# CONFIG_HFS_FS is not set
+# CONFIG_HFSPLUS_FS is not set
+# CONFIG_BEFS_FS is not set
+# CONFIG_BFS_FS is not set
+# CONFIG_EFS_FS is not set
+CONFIG_CRAMFS=m
+# CONFIG_VXFS_FS is not set
+# CONFIG_HPFS_FS is not set
+# CONFIG_QNX4FS_FS is not set
+# CONFIG_SYSV_FS is not set
+# CONFIG_UFS_FS is not set
+
+#
+# Network File Systems
+#
+CONFIG_NFS_FS=y
+CONFIG_NFS_V3=y
+# CONFIG_NFS_V3_ACL is not set
+# CONFIG_NFS_V4 is not set
+# CONFIG_NFS_DIRECTIO is not set
+# CONFIG_NFSD is not set
+CONFIG_ROOT_NFS=y
+CONFIG_LOCKD=y
+CONFIG_LOCKD_V4=y
+CONFIG_NFS_COMMON=y
+CONFIG_SUNRPC=y
+# CONFIG_RPCSEC_GSS_KRB5 is not set
+# CONFIG_RPCSEC_GSS_SPKM3 is not set
+# CONFIG_SMB_FS is not set
+# CONFIG_CIFS is not set
+# CONFIG_NCP_FS is not set
+# CONFIG_CODA_FS is not set
+# CONFIG_AFS_FS is not set
+# CONFIG_9P_FS is not set
+
+#
+# Partition Types
+#
+# CONFIG_PARTITION_ADVANCED is not set
+CONFIG_MSDOS_PARTITION=y
+
+#
+# Native Language Support
+#
+# CONFIG_NLS is not set
+
+#
+# Profiling support
+#
+# CONFIG_PROFILING is not set
+
+#
+# Kernel hacking
+#
+# CONFIG_PRINTK_TIME is not set
+# CONFIG_MAGIC_SYSRQ is not set
+# CONFIG_DEBUG_KERNEL is not set
+CONFIG_LOG_BUF_SHIFT=14
+CONFIG_CROSSCOMPILE=y
+CONFIG_CMDLINE="mem=64M console=ttyVR0,115200 ip=any root=/dev/nfs"
+
+#
+# Security options
+#
+CONFIG_KEYS=y
+CONFIG_KEYS_DEBUG_PROC_KEYS=y
+# CONFIG_SECURITY is not set
+
+#
+# Cryptographic options
+#
+# CONFIG_CRYPTO is not set
+
+#
+# Hardware crypto devices
+#
+
+#
+# Library routines
+#
+# CONFIG_CRC_CCITT is not set
+# CONFIG_CRC16 is not set
+CONFIG_CRC32=y
+# CONFIG_LIBCRC32C is not set
+CONFIG_ZLIB_INFLATE=m
index 488206b8d94e7459ada11008325683a9ba95256f..304c02107b468169ac429f5fe0c27988b12f973f 100644 (file)
@@ -3,6 +3,6 @@
 # under Linux.
 #
 
-obj-y                  += setup.o irq.o int-handler.o nile4_pic.o
+obj-y                  += setup.o irq.o nile4_pic.o
 
 EXTRA_AFLAGS := $(CFLAGS)
diff --git a/arch/mips/ddb5xxx/ddb5074/int-handler.S b/arch/mips/ddb5xxx/ddb5074/int-handler.S
deleted file mode 100644 (file)
index a786441..0000000
+++ /dev/null
@@ -1,120 +0,0 @@
-/*
- *  arch/mips/ddb5074/int-handler.S -- NEC DDB Vrc-5074 interrupt handler
- *
- *  Based on arch/mips/sgi/kernel/indyIRQ.S
- *
- *  Copyright (C) 1996 David S. Miller (dm@engr.sgi.com)
- *
- *  Copyright (C) 2000 Geert Uytterhoeven <geert@sonycom.com>
- *                     Sony Software Development Center Europe (SDCE), Brussels
- */
-#include <asm/asm.h>
-#include <asm/mipsregs.h>
-#include <asm/regdef.h>
-#include <asm/stackframe.h>
-
-/* A lot of complication here is taken away because:
- *
- * 1) We handle one interrupt and return, sitting in a loop and moving across
- *    all the pending IRQ bits in the cause register is _NOT_ the answer, the
- *    common case is one pending IRQ so optimize in that direction.
- *
- * 2) We need not check against bits in the status register IRQ mask, that
- *    would make this routine slow as hell.
- *
- * 3) Linux only thinks in terms of all IRQs on or all IRQs off, nothing in
- *    between like BSD spl() brain-damage.
- *
- * Furthermore, the IRQs on the INDY look basically (barring software IRQs
- * which we don't use at all) like:
- *
- *     MIPS IRQ        Source
- *      --------        ------
- *             0       Software (ignored)
- *             1        Software (ignored)
- *             2        Local IRQ level zero
- *             3        Local IRQ level one
- *             4        8254 Timer zero
- *             5        8254 Timer one
- *             6        Bus Error
- *             7        R4k timer (what we use)
- *
- * We handle the IRQ according to _our_ priority which is:
- *
- * Highest ----     R4k Timer
- *                  Local IRQ zero
- *                  Local IRQ one
- *                  Bus Error
- *                  8254 Timer zero
- * Lowest  ----     8254 Timer one
- *
- * then we just return, if multiple IRQs are pending then we will just take
- * another exception, big deal.
- */
-
-       .text
-       .set    noreorder
-       .set    noat
-       .align  5
-       NESTED(ddbIRQ, PT_SIZE, sp)
-       SAVE_ALL
-       CLI
-       .set    at
-       mfc0    s0, CP0_CAUSE           # get irq mask
-
-#if 1
-       mfc0    t2,CP0_STATUS           # get enabled interrupts
-       and     s0,t2                   # isolate allowed ones
-#endif
-       /* First we check for r4k counter/timer IRQ. */
-       andi    a0, s0, CAUSEF_IP2      # delay slot, check local level zero
-       beq     a0, zero, 1f
-        andi   a0, s0, CAUSEF_IP3      # delay slot, check local level one
-
-       /* Wheee, local level zero interrupt. */
-       jal     ddb_local0_irqdispatch
-        move   a0, sp                  # delay slot
-
-       j       ret_from_irq
-        nop                            # delay slot
-
-1:
-       beq     a0, zero, 1f
-        andi   a0, s0, CAUSEF_IP6      # delay slot, check bus error
-
-       /* Wheee, local level one interrupt. */
-       move    a0, sp
-       jal     ddb_local1_irqdispatch
-        nop
-
-       j       ret_from_irq
-        nop
-
-1:
-       beq     a0, zero, 1f
-        nop
-
-       /* Wheee, an asynchronous bus error... */
-       move    a0, sp
-       jal     ddb_buserror_irq
-        nop
-
-       j       ret_from_irq
-        nop
-
-1:
-       /* Here by mistake?  This is possible, what can happen
-        * is that by the time we take the exception the IRQ
-        * pin goes low, so just leave if this is the case.
-        */
-       andi    a0, s0, (CAUSEF_IP4 | CAUSEF_IP5)
-       beq     a0, zero, 1f
-
-       /* Must be one of the 8254 timers... */
-       move    a0, sp
-       jal     ddb_8254timer_irq
-        nop
-1:
-       j       ret_from_irq
-        nop
-       END(ddbIRQ)
index 45088a1be4142a39c9cb2a8e5be63173778b63bf..60c087b7738c3c360214a788aa0528537b0b3852 100644 (file)
@@ -21,8 +21,6 @@
 #include <asm/ddb5xxx/ddb5074.h>
 
 
-extern asmlinkage void ddbIRQ(void);
-
 static struct irqaction irq_cascade = { no_action, 0, CPU_MASK_NONE, "cascade", NULL, NULL };
 
 #define M1543_PNP_CONFIG       0x03f0  /* PnP Config Port */
@@ -90,7 +88,7 @@ static void m1543_irq_setup(void)
 
 }
 
-void ddb_local0_irqdispatch(struct pt_regs *regs)
+static void ddb_local0_irqdispatch(struct pt_regs *regs)
 {
        u32 mask;
        int nile4_irq;
@@ -118,29 +116,41 @@ void ddb_local0_irqdispatch(struct pt_regs *regs)
                }
 }
 
-void ddb_local1_irqdispatch(void)
+static void ddb_local1_irqdispatch(void)
 {
        printk("ddb_local1_irqdispatch called\n");
 }
 
-void ddb_buserror_irq(void)
+static void ddb_buserror_irq(void)
 {
        printk("ddb_buserror_irq called\n");
 }
 
-void ddb_8254timer_irq(void)
+static void ddb_8254timer_irq(void)
 {
        printk("ddb_8254timer_irq called\n");
 }
 
+asmlinkage void plat_irq_dispatch(struct pt_regs *regs)
+{
+       unsigned int pending = read_c0_cause() & read_c0_status();
+
+       if (pending & CAUSEF_IP2)
+               ddb_local0_irqdispatch(regs);
+       else if (pending & CAUSEF_IP3)
+               ddb_local1_irqdispatch();
+       else if (pending & CAUSEF_IP6)
+               ddb_buserror_irq();
+       else if (pending & (CAUSEF_IP4 | CAUSEF_IP5))
+               ddb_8254timer_irq();
+}
+
 void __init arch_init_irq(void)
 {
        /* setup cascade interrupts */
        setup_irq(NILE4_IRQ_BASE  + NILE4_INT_INTE, &irq_cascade);
        setup_irq(CPU_IRQ_BASE + CPU_NILE4_CASCADE, &irq_cascade);
 
-       set_except_vector(0, ddbIRQ);
-
        nile4_irq_setup(NILE4_IRQ_BASE);
        m1543_irq_setup();
        init_i8259_irqs();
index 61eec363cb02593b5c706e80d12276319acaa664..ab0312cb47b4552c6578720fa62763f386ed7d7a 100644 (file)
@@ -3,7 +3,7 @@
 # under Linux.
 #
 
-obj-y                  += setup.o irq.o int-handler.o nile4_pic.o vrc5476_irq.o
+obj-y                  += setup.o irq.o nile4_pic.o vrc5476_irq.o
 obj-$(CONFIG_KGDB)     += dbg_io.o
 
 EXTRA_AFLAGS := $(CFLAGS)
diff --git a/arch/mips/ddb5xxx/ddb5476/int-handler.S b/arch/mips/ddb5xxx/ddb5476/int-handler.S
deleted file mode 100644 (file)
index 12c292e..0000000
+++ /dev/null
@@ -1,112 +0,0 @@
-/*
- * Copyright 2001 MontaVista Software Inc.
- * Author: jsun@mvista.com or jsun@junsun.net
- *
- * First-level interrupt dispatcher for ddb5476
- *
- * This program is free software; you can redistribute  it and/or modify it
- * under  the terms of  the GNU General  Public License as published by the
- * Free Software Foundation;  either version 2 of the  License, or (at your
- * option) any later version.
- */
-#include <asm/asm.h>
-#include <asm/mipsregs.h>
-#include <asm/addrspace.h>
-#include <asm/regdef.h>
-#include <asm/stackframe.h>
-
-#include <asm/ddb5xxx/ddb5476.h>
-
-/*
- * first level interrupt dispatcher for ocelot board -
- * We check for the timer first, then check PCI ints A and D.
- * Then check for serial IRQ and fall through.
- */
-       .align  5
-       NESTED(ddb5476_handle_int, PT_SIZE, sp)
-       SAVE_ALL
-       CLI
-       .set    at
-       .set    noreorder
-       mfc0    t0, CP0_CAUSE
-       mfc0    t2, CP0_STATUS
-
-       and     t0, t2
-
-        andi    t1, t0, STATUSF_IP7     /* cpu timer */
-        bnez    t1, ll_cpu_ip7
-        andi    t1, t0, STATUSF_IP2    /* vrc5476 & i8259 */
-        bnez    t1, ll_cpu_ip2
-        andi    t1, t0, STATUSF_IP3
-        bnez    t1, ll_cpu_ip3
-        andi    t1, t0, STATUSF_IP4
-        bnez    t1, ll_cpu_ip4
-        andi    t1, t0, STATUSF_IP5
-        bnez    t1, ll_cpu_ip5
-        andi    t1, t0, STATUSF_IP6
-        bnez    t1, ll_cpu_ip6
-        andi    t1, t0, STATUSF_IP0     /* software int 0 */
-        bnez    t1, ll_cpu_ip0
-        andi    t1, t0, STATUSF_IP1     /* software int 1 */
-        bnez    t1, ll_cpu_ip1
-        nop
-
-       .set    reorder
-
-       /* wrong alarm or masked ... */
-       // j    spurious_interrupt
-       move    a0, sp
-       jal     vrc5476_irq_dispatch
-       j       ret_from_irq
-       nop
-
-       .align  5
-
-ll_cpu_ip0:
-       li      a0, CPU_IRQ_BASE + 0
-       move    a1, sp
-       jal     do_IRQ
-       j       ret_from_irq
-
-ll_cpu_ip1:
-       li      a0, CPU_IRQ_BASE + 1
-       move    a1, sp
-       jal     do_IRQ
-       j       ret_from_irq
-
-ll_cpu_ip2:            /* jump to second-level dispatching */
-       move    a0, sp
-       jal     vrc5476_irq_dispatch
-       j       ret_from_irq
-
-ll_cpu_ip3:
-       li      a0, CPU_IRQ_BASE + 3
-       move    a1, sp
-       jal     do_IRQ
-       j       ret_from_irq
-
-ll_cpu_ip4:
-       li      a0, CPU_IRQ_BASE + 4
-       move    a1, sp
-       jal     do_IRQ
-       j       ret_from_irq
-
-ll_cpu_ip5:
-       li      a0, CPU_IRQ_BASE + 5
-       move    a1, sp
-       jal     do_IRQ
-       j       ret_from_irq
-
-ll_cpu_ip6:
-       li      a0, CPU_IRQ_BASE + 6
-       move    a1, sp
-       jal     do_IRQ
-       j       ret_from_irq
-
-ll_cpu_ip7:
-       li      a0, CPU_IRQ_BASE + 7
-       move    a1, sp
-       jal     do_IRQ
-       j       ret_from_irq
-
-       END(ddb5476_handle_int)
index 5388b5868c4a6b31ab5bb126bbde379f88d125f6..7583a1f307118e483707ee9e30415521bce27efe 100644 (file)
@@ -110,11 +110,36 @@ static void nile4_irq_setup(void)
 static struct irqaction irq_cascade = { no_action, 0, CPU_MASK_NONE, "cascade", NULL, NULL };
 static struct irqaction irq_error = { no_action, 0, CPU_MASK_NONE, "error", NULL, NULL };
 
-extern asmlinkage void ddb5476_handle_int(void);
 extern int setup_irq(unsigned int irq, struct irqaction *irqaction);
 extern void mips_cpu_irq_init(u32 irq_base);
 extern void vrc5476_irq_init(u32 irq_base);
 
+extern void vrc5476_irq_dispatch(struct pt_regs *regs);
+
+asmlinkage void plat_irq_dispatch(struct pt_regs *regs)
+{
+       unsigned int pending = read_c0_cause() & read_c0_status();
+
+       if (pending & STATUSF_IP7)
+               do_IRQ(CPU_IRQ_BASE + 7, regs);
+       else if (pending & STATUSF_IP2)
+               vrc5476_irq_dispatch(regs);
+       else if (pending & STATUSF_IP3)
+               do_IRQ(CPU_IRQ_BASE + 3, regs);
+       else if (pending & STATUSF_IP4)
+               do_IRQ(CPU_IRQ_BASE + 4, regs);
+       else if (pending & STATUSF_IP5)
+               do_IRQ(CPU_IRQ_BASE + 5, regs);
+       else if (pending & STATUSF_IP6)
+               do_IRQ(CPU_IRQ_BASE + 6, regs);
+       else if (pending & STATUSF_IP0)
+               do_IRQ(CPU_IRQ_BASE, regs);
+       else if (pending & STATUSF_IP1)
+               do_IRQ(CPU_IRQ_BASE + 1, regs);
+
+       vrc5476_irq_dispatch(regs);
+}
+
 void __init arch_init_irq(void)
 {
        /* hardware initialization */
@@ -137,7 +162,4 @@ void __init arch_init_irq(void)
        setup_irq(VRC5476_IRQ_BASE + VRC5476_IRQ_LBRT, &irq_error);
        setup_irq(VRC5476_IRQ_BASE + VRC5476_IRQ_PCIS, &irq_error);
        setup_irq(VRC5476_IRQ_BASE + VRC5476_IRQ_PCI, &irq_error);
-
-       /* setup the grandpa intr vector */
-       set_except_vector(0, ddb5476_handle_int);
 }
index f66fe5b5863660b4014c953ba8726f8b1fe6c87e..a3c5e7b18018015e89df25a5613f2dc5bccba9bb 100644 (file)
@@ -77,11 +77,9 @@ vrc5476_irq_init(u32 base)
 }
 
 
-asmlinkage void
+void
 vrc5476_irq_dispatch(struct pt_regs *regs)
 {
-       extern void spurious_interrupt(void);
-
        u32 mask;
        int nile4_irq;
 
@@ -107,5 +105,5 @@ vrc5476_irq_dispatch(struct pt_regs *regs)
                        return;
                }
        }
-       spurious_interrupt();
+       spurious_interrupt(regs);
 }
index b79b43c9f93b399775d4c769d0d56a1ecc0f9b91..ea68815ad17ae5be6542f0bba36107c5f4fd6b62 100644 (file)
@@ -2,7 +2,7 @@
 # Makefile for NEC DDB-Vrc5477 board
 #
 
-obj-y                  += int-handler.o irq.o irq_5477.o setup.o lcd44780.o
+obj-y                  += irq.o irq_5477.o setup.o lcd44780.o
 
 obj-$(CONFIG_RUNTIME_DEBUG)    += debug.o
 obj-$(CONFIG_KGDB)             += kgdb_io.o
diff --git a/arch/mips/ddb5xxx/ddb5477/int-handler.S b/arch/mips/ddb5xxx/ddb5477/int-handler.S
deleted file mode 100644 (file)
index a2502a1..0000000
+++ /dev/null
@@ -1,75 +0,0 @@
-/*
- * Copyright 2001 MontaVista Software Inc.
- * Author: jsun@mvista.com or jsun@junsun.net
- *
- * First-level interrupt dispatcher for ddb5477
- *
- * This program is free software; you can redistribute  it and/or modify it
- * under  the terms of  the GNU General  Public License as published by the
- * Free Software Foundation;  either version 2 of the  License, or (at your
- * option) any later version.
- */
-#include <asm/asm.h>
-#include <asm/mipsregs.h>
-#include <asm/addrspace.h>
-#include <asm/regdef.h>
-#include <asm/stackframe.h>
-#include <asm/ddb5xxx/ddb5477.h>
-
-/*
- * first level interrupt dispatcher for ocelot board -
- * We check for the timer first, then check PCI ints A and D.
- * Then check for serial IRQ and fall through.
- */
-       .align  5
-       NESTED(ddb5477_handle_int, PT_SIZE, sp)
-       SAVE_ALL
-       CLI
-       .set    at
-       .set    noreorder
-       mfc0    t0, CP0_CAUSE
-       mfc0    t2, CP0_STATUS
-
-       and     t0, t2
-
-       andi    t1, t0, STATUSF_IP7     /* cpu timer */
-       bnez    t1, ll_cputimer_irq
-       andi    t1, t0, (STATUSF_IP2 | STATUSF_IP3 | STATUSF_IP4 | STATUSF_IP5 | STATUSF_IP6 )
-       bnez    t1, ll_vrc5477_irq
-       andi    t1, t0, STATUSF_IP0     /* software int 0 */
-       bnez    t1, ll_cpu_ip0
-       andi    t1, t0, STATUSF_IP1     /* software int 1 */
-       bnez    t1, ll_cpu_ip1
-       nop
-       .set    reorder
-
-       /* wrong alarm or masked ... */
-       j       spurious_interrupt
-       nop
-       END(ddb5477_handle_int)
-
-       .align  5
-
-ll_vrc5477_irq:
-       move    a0, sp
-       jal     vrc5477_irq_dispatch
-       j       ret_from_irq
-
-ll_cputimer_irq:
-       li      a0, CPU_IRQ_BASE + 7
-       move    a1, sp
-       jal     do_IRQ
-       j       ret_from_irq
-
-
-ll_cpu_ip0:
-       li      a0, CPU_IRQ_BASE + 0
-       move    a1, sp
-       jal     do_IRQ
-       j       ret_from_irq
-
-ll_cpu_ip1:
-       li      a0, CPU_IRQ_BASE + 1
-       move    a1, sp
-       jal     do_IRQ
-       j       ret_from_irq
index 9ffe1a9142caef3e86c19faa03a4dd9906e94e6b..de433cf9fb5013b7c934e0b0bafef9038842e21e 100644 (file)
@@ -75,7 +75,6 @@ set_pci_int_attr(u32 pci, u32 intn, u32 active, u32 trigger)
 
 extern void vrc5477_irq_init(u32 base);
 extern void mips_cpu_irq_init(u32 base);
-extern asmlinkage void ddb5477_handle_int(void);
 extern int setup_irq(unsigned int irq, struct irqaction *irqaction);
 static struct irqaction irq_cascade = { no_action, 0, CPU_MASK_NONE, "cascade", NULL, NULL };
 
@@ -135,9 +134,6 @@ void __init arch_init_irq(void)
        /* setup cascade interrupts */
        setup_irq(VRC5477_IRQ_BASE + VRC5477_I8259_CASCADE, &irq_cascade);
        setup_irq(CPU_IRQ_BASE + CPU_VRC5477_CASCADE, &irq_cascade);
-
-       /* hook up the first-level interrupt handler */
-       set_except_vector(0, ddb5477_handle_int);
 }
 
 u8 i8259_interrupt_ack(void)
@@ -159,7 +155,7 @@ u8 i8259_interrupt_ack(void)
  * the first level int-handler will jump here if it is a vrc5477 irq
  */
 #define        NUM_5477_IRQS   32
-asmlinkage void
+static void
 vrc5477_irq_dispatch(struct pt_regs *regs)
 {
        u32 intStatus;
@@ -197,3 +193,21 @@ vrc5477_irq_dispatch(struct pt_regs *regs)
                }
        }
 }
+
+#define VR5477INTS (STATUSF_IP2|STATUSF_IP3|STATUSF_IP4|STATUSF_IP5|STATUSF_IP6)
+
+asmlinkage void plat_irq_dispatch(struct pt_regs *regs)
+{
+       unsigned int pending = read_c0_cause() & read_c0_status();
+
+       if (pending & STATUSF_IP7)
+               do_IRQ(CPU_IRQ_BASE + 7, regs);
+       else if (pending & VR5477INTS)
+               vrc5477_irq_dispatch(regs);
+       else if (pending & STATUSF_IP0)
+               do_IRQ(CPU_IRQ_BASE, regs);
+       else if (pending & STATUSF_IP1)
+               do_IRQ(CPU_IRQ_BASE + 1, regs);
+       else
+               spurious_interrupt(regs);
+}
index 56fd4277555e6064f63c629f4557c32424ec8f4d..4db8bacaf22d51398f1f5f4ac414c44c5c0be923 100644 (file)
@@ -1,6 +1,7 @@
 /*
  * arch/mips/dec/decstation.c
  */
+#include <asm/sections.h>
 
 #define RELOC
 #define INITRD
@@ -24,7 +25,7 @@
 #define INITRD_START (*(unsigned long *) (PARAM+0x218))
 #define INITRD_SIZE (*(unsigned long *) (PARAM+0x21c))
 
-extern int _ftext, _end;               /* begin and end of kernel image */
+extern int _ftext;                     /* begin and end of kernel image */
 extern void kernel_entry(int, char **, unsigned long, int *);
 
 void * memcpy(void * dest, const void *src, unsigned int count)
index 41fa372007bf07889f2facffc6edfd76f8287ff9..e8ec93e33fe60cc05eb0c7503992cbca38581d7b 100644 (file)
@@ -36,7 +36,7 @@
                .text
                .set    noreorder
 /*
- * decstation_handle_int: Interrupt handler for DECstations
+ * plat_irq_dispatch: Interrupt handler for DECstations
  *
  * We follow the model in the Indy interrupt code by David Miller, where he
  * says: a lot of complication here is taken away because:
  * just take another exception, big deal.
  */
                .align  5
-               NESTED(decstation_handle_int, PT_SIZE, ra)
-               .set    noat
-               SAVE_ALL
-               CLI                             # TEST: interrupts should be off
-               .set    at
+               NESTED(plat_irq_dispatch, PT_SIZE, ra)
                .set    noreorder
 
                /*
@@ -282,9 +278,11 @@ fpu:
 #endif
 
 spurious:
-               j       spurious_interrupt
+               jal     spurious_interrupt
                 nop
-               END(decstation_handle_int)
+               j       ret_from_irq
+                nop
+               END(plat_irq_dispatch)
 
 /*
  * Generic unimplemented interrupt routines -- cpu_mask_nr_tbl
index 7c1ca8f6330e0e33a69f6de58758effbe017be69..ad5d436d80c19bae206c86a6623b3aaa8e486263 100644 (file)
@@ -48,8 +48,6 @@ extern void dec_machine_halt(void);
 extern void dec_machine_power_off(void);
 extern irqreturn_t dec_intr_halt(int irq, void *dev_id, struct pt_regs *regs);
 
-extern asmlinkage void decstation_handle_int(void);
-
 unsigned long dec_kn_slot_base, dec_kn_slot_size;
 
 EXPORT_SYMBOL(dec_kn_slot_base);
@@ -744,7 +742,6 @@ void __init arch_init_irq(void)
                panic("Don't know how to set this up!");
                break;
        }
-       set_except_vector(0, decstation_handle_int);
 
        /* Free the FPU interrupt if the exception is present. */
        if (!cpu_has_nofpuex) {
index 58c02f9db69d86dfb20033a70573b3ad8118f719..cd868ec78cbc9e51d8850d2ec618393ea6e4724c 100644 (file)
@@ -6,4 +6,4 @@
 # Makefile for the Galileo EV96100 board.
 #
 
-obj-y          += init.o irq.o puts.o reset.o time.o int-handler.o setup.o
+obj-y          += init.o irq.o puts.o reset.o time.o setup.o
diff --git a/arch/mips/galileo-boards/ev96100/int-handler.S b/arch/mips/galileo-boards/ev96100/int-handler.S
deleted file mode 100644 (file)
index ff4d10a..0000000
+++ /dev/null
@@ -1,33 +0,0 @@
-#include <asm/asm.h>
-#include <asm/mipsregs.h>
-#include <asm/regdef.h>
-#include <asm/stackframe.h>
-
-       .set    noat
-       .align  5
-
-NESTED(ev96100IRQ, PT_SIZE, sp)
-       SAVE_ALL
-       CLI                             # Important: mark KERNEL mode !
-
-       mfc0    t0, CP0_CAUSE           # get pending interrupts
-       mfc0    t1, CP0_STATUS          # get enabled interrupts
-       and     t0, t1                  # isolate allowed ones
-
-       # FIX ME add R7000 extensions
-       andi    t0,0xff00               # isolate pending bits
-       andi    a0, t0, CAUSEF_IP7
-       beq     a0, zero, 1f
-       move    a0, sp
-       jal     mips_timer_interrupt
-       j       ret_from_irq
-
-1:     beqz    t0, 3f                  # spurious interrupt
-
-       move    a0, t0
-       move    a1, sp
-       jal     ev96100_cpu_irq
-       j       ret_from_irq
-
-3:     j       spurious_interrupt
-       END(ev96100IRQ)
index 97bf094da4fe07f2af22c77aed110a003f5e7b1c..ee5d6720f23bf614c8a6ea18ae985a5386e4f894 100644 (file)
@@ -40,8 +40,6 @@
 #include <linux/interrupt.h>
 #include <asm/irq_cpu.h>
 
-extern asmlinkage void ev96100IRQ(void);
-
 static inline unsigned int ffz8(unsigned int word)
 {
        unsigned long k;
@@ -54,13 +52,26 @@ static inline unsigned int ffz8(unsigned int word)
        return k;
 }
 
-asmlinkage void ev96100_cpu_irq(unsigned int pendin)
+extern void mips_timer_interrupt(struct pt_regs *regs);
+
+asmlinkage void ev96100_cpu_irq(unsigned int pending, struct pt_regs *regs)
 {
        do_IRQ(ffz8(pending >> 8), regs);
 }
 
+asmlinkage void plat_irq_dispatch(struct pt_regs *regs)
+{
+       unsigned int pending = read_c0_cause() & read_c0_status() & ST0_IM;
+
+       if (pending & CAUSEF_IP7)
+               mips_timer_interrupt(regs);
+       else if (pending)
+               ev96100_cpu_irq(pending, regs);
+       else
+               spurious_interrupt(regs);
+}
+
 void __init arch_init_irq(void)
 {
-       set_except_vector(0, ev96100IRQ);
        mips_cpu_irq_init(0);
 }
index ebe91c57e17345f1205a12cda20df5fda191cf3f..b2c53a8f8718a71476006fcdff36e76fa07c6318 100644 (file)
@@ -6,6 +6,6 @@
 # Makefile for the Galileo EV64120 board.
 #
 
-obj-y  += int-handler.o irq.o promcon.o reset.o serialGT.o setup.o
+obj-y  += irq.o promcon.o reset.o serialGT.o setup.o
 
 EXTRA_AFLAGS := $(CFLAGS)
diff --git a/arch/mips/gt64120/ev64120/int-handler.S b/arch/mips/gt64120/ev64120/int-handler.S
deleted file mode 100644 (file)
index 752435f..0000000
+++ /dev/null
@@ -1,113 +0,0 @@
-/*
- * int-handler.S
- *
- * Based on the cobalt handler.
- */
-#include <asm/asm.h>
-#include <asm/mipsregs.h>
-#include <asm/addrspace.h>
-#include <asm/regdef.h>
-#include <asm/stackframe.h>
-
-/*
- * galileo_handle_int -
- *      We check for the timer first, then check PCI ints A and D.
- *      Then check for serial IRQ and fall through.
- */
-               .align  5
-               .set    reorder
-               .set    noat
-               NESTED(galileo_handle_int, PT_SIZE, sp)
-               SAVE_ALL
-               CLI
-               .set    at
-               mfc0    t0,CP0_CAUSE
-               mfc0    t2,CP0_STATUS
-
-               and     t0,t2
-
-               andi    t1,t0,STATUSF_IP4 /* int2 hardware line (timer) */
-               bnez    t1,ll_gt64120_irq
-               andi    t1,t0,STATUSF_IP2 /* int0 hardware line */
-               bnez    t1,ll_pci_intA
-               andi    t1,t0,STATUSF_IP5 /* int3 hardware line */
-               bnez    t1,ll_pci_intD
-               andi    t1,t0,STATUSF_IP6 /* int4 hardware line */
-               bnez    t1,ll_serial_irq
-               andi    t1,t0,STATUSF_IP7 /* compare int */
-               bnez    t1,ll_compare_irq
-               nop
-
-    /* wrong alarm or masked ... */
-               j       spurious_interrupt
-               nop
-               END(galileo_handle_int)
-
-
-               .align  5
-               .set    reorder
-ll_gt64120_irq:
-               li      a0,4
-               move    a1,sp
-               jal     do_IRQ
-               nop
-               j       ret_from_irq
-               nop
-
-               .align  5
-               .set    reorder
-ll_compare_irq:
-               li      a0,7
-               move    a1,sp
-               jal     do_IRQ
-               nop
-               j       ret_from_irq
-               nop
-
-               .align  5
-               .set    reorder
-ll_pci_intA:
-               move    a0,sp
-               jal     pci_intA
-               nop
-               j       ret_from_irq
-               nop
-
-#if 0
-               .align  5
-               .set    reorder
-ll_pci_intB:
-               move    a0,sp
-               jal     pci_intB
-               nop
-               j       ret_from_irq
-               nop
-
-               .align  5
-               .set    reorder
-ll_pci_intC:
-               move    a0,sp
-               jal     pci_intC
-               nop
-               j       ret_from_irq
-               nop
-#endif
-
-               .align  5
-               .set    reorder
-ll_pci_intD:
-               move    a0,sp
-               jal     pci_intD
-               nop
-               j       ret_from_irq
-               nop
-
-               .align  5
-               .set    reorder
-ll_serial_irq:
-               li      a0,6
-               move    a1,sp
-               jal     do_IRQ
-               nop
-               j       ret_from_irq
-               nop
index 3b186159b21a17b9a1763736d736f550e1e0918f..46c468b26b30879c72b82e01e52a271b32e61d2a 100644 (file)
 #include <asm/system.h>
 #include <asm/gt64120.h>
 
-asmlinkage inline void pci_intA(struct pt_regs *regs)
+asmlinkage void plat_irq_dispatch(struct pt_regs *regs)
 {
-       do_IRQ(GT_INTA, regs);
-}
-
-asmlinkage inline void pci_intD(struct pt_regs *regs)
-{
-       do_IRQ(GT_INTD, regs);
+       unsigned int pending = read_c0_status() & read_c0_cause();
+
+       if (pending & STATUSF_IP4)              /* int2 hardware line (timer) */
+               do_IRQ(4, regs);
+       else if (pending & STATUSF_IP2)         /* int0 hardware line */
+               do_IRQ(GT_INTA, regs);
+       else if (pending & STATUSF_IP5)         /* int3 hardware line */
+               do_IRQ(GT_INTD, regs);
+       else if (pending & STATUSF_IP6)         /* int4 hardware line */
+               do_IRQ(6, regs);
+       else if (pending & STATUSF_IP7)         /* compare int */
+               do_IRQ(7, regs);
+       else
+               spurious_interrupt(regs);
 }
 
 static void disable_ev64120_irq(unsigned int irq_nr)
@@ -109,16 +117,11 @@ static struct hw_interrupt_type ev64120_irq_type = {
 
 void gt64120_irq_setup(void)
 {
-       extern asmlinkage void galileo_handle_int(void);
-
        /*
         * Clear all of the interrupts while we change the able around a bit.
         */
        clear_c0_status(ST0_IM);
 
-       /* Sets the exception_handler array. */
-       set_except_vector(0, galileo_handle_int);
-
        local_irq_disable();
 
        /*
index 7b59c6567c79437abcf80513dc2068c17c6fa8d2..6f708df8373be147689ee6b88f55189137ab77a2 100644 (file)
@@ -2,7 +2,7 @@
 # Makefile for Momentum's Ocelot board.
 #
 
-obj-y                  += int-handler.o irq.o prom.o reset.o setup.o
+obj-y                  += irq.o prom.o reset.o setup.o
 
 obj-$(CONFIG_KGDB)     += dbg_io.o
 
diff --git a/arch/mips/gt64120/momenco_ocelot/int-handler.S b/arch/mips/gt64120/momenco_ocelot/int-handler.S
deleted file mode 100644 (file)
index 808acef..0000000
+++ /dev/null
@@ -1,131 +0,0 @@
-/*
- * Copyright 2001 MontaVista Software Inc.
- * Author: jsun@mvista.com or jsun@junsun.net
- *
- * First-level interrupt dispatcher for ocelot board.
- *
- * This program is free software; you can redistribute  it and/or modify it
- * under  the terms of  the GNU General  Public License as published by the
- * Free Software Foundation;  either version 2 of the  License, or (at your
- * option) any later version.
- */
-#include <asm/asm.h>
-#include <asm/mipsregs.h>
-#include <asm/addrspace.h>
-#include <asm/regdef.h>
-#include <asm/stackframe.h>
-
-/*
- * first level interrupt dispatcher for ocelot board -
- * We check for the timer first, then check PCI ints A and D.
- * Then check for serial IRQ and fall through.
- */
-               .align  5
-               NESTED(ocelot_handle_int, PT_SIZE, sp)
-               SAVE_ALL
-               CLI
-               .set    at
-               mfc0    t0, CP0_CAUSE
-               mfc0    t2, CP0_STATUS
-
-               and     t0, t2
-
-                andi   t1, t0, STATUSF_IP2     /* int0 hardware line */
-               bnez    t1, ll_pri_enet_irq
-                andi   t1, t0, STATUSF_IP3     /* int1 hardware line */
-               bnez    t1, ll_sec_enet_irq
-                andi   t1, t0, STATUSF_IP4     /* int2 hardware line */
-               bnez    t1, ll_uart1_irq
-                andi   t1, t0, STATUSF_IP5     /* int3 hardware line */
-               bnez    t1, ll_cpci_irq
-                andi   t1, t0, STATUSF_IP6     /* int4 hardware line */
-               bnez    t1, ll_galileo_irq
-                andi   t1, t0, STATUSF_IP7     /* cpu timer */
-               bnez    t1, ll_cputimer_irq
-
-                /* now look at the extended interrupts */
-               mfc0    t0, CP0_CAUSE
-               cfc0    t1, CP0_S1_INTCONTROL
-
-               /* shift the mask 8 bits left to line up the bits */
-                sll    t2, t1, 8
-
-                and    t0, t2
-                srl    t0, t0, 16
-
-                andi   t1, t0, STATUSF_IP8     /* int6 hardware line */
-               bnez    t1, ll_pmc1_irq
-                andi   t1, t0, STATUSF_IP9     /* int7 hardware line */
-               bnez    t1, ll_pmc2_irq
-                andi   t1, t0, STATUSF_IP10    /* int8 hardware line */
-               bnez    t1, ll_cpci_abcd_irq
-                andi   t1, t0, STATUSF_IP11    /* int9 hardware line */
-               bnez    t1, ll_uart2_irq
-
-               .set    reorder
-
-               /* wrong alarm or masked ... */
-               j       spurious_interrupt
-               nop
-               END(ocelot_handle_int)
-
-               .align  5
-ll_pri_enet_irq:
-               li      a0, 2
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-
-ll_sec_enet_irq:
-               li      a0, 3
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-
-ll_uart1_irq:
-               li      a0, 4
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-
-ll_cpci_irq:
-               li      a0, 5
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-
-ll_galileo_irq:
-               li      a0, 6
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-
-ll_cputimer_irq:
-               li      a0, 7
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-
-ll_pmc1_irq:
-               li      a0, 8
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-
-ll_pmc2_irq:
-               li      a0, 9
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-
-ll_cpci_abcd_irq:
-               li      a0, 10
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-
-ll_uart2_irq:
-               li      a0, 11
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
index 4f108da71b2355d02b4185ac7ed409992c959347..885f67f32ea3dfa501916f5ed8e194984063c3a1 100644 (file)
 #include <asm/mipsregs.h>
 #include <asm/system.h>
 
-extern asmlinkage void ocelot_handle_int(void);
+asmlinkage void plat_irq_dispatch(struct pt_regs *regs)
+{
+       unsigned int pending = read_c0_status() & read_c0_cause();
+
+       if (pending & STATUSF_IP2)              /* int0 hardware line */
+               do_IRQ(2, regs);
+       else if (pending & STATUSF_IP3)         /* int1 hardware line */
+               do_IRQ(3, regs);
+       else if (pending & STATUSF_IP4)         /* int2 hardware line */
+               do_IRQ(4, regs);
+       else if (pending & STATUSF_IP5)         /* int3 hardware line */
+               do_IRQ(5, regs);
+       else if (pending & STATUSF_IP6)         /* int4 hardware line */
+               do_IRQ(6, regs);
+       else if (pending & STATUSF_IP7)         /* cpu timer */
+               do_IRQ(7, regs);
+       else {
+               /*
+                * Now look at the extended interrupts
+                */
+               pending = (read_c0_cause() & (read_c0_intcontrol() << 8)) >> 16;
+
+               if (pending & STATUSF_IP8)              /* int6 hardware line */
+                       do_IRQ(8, regs);
+               else if (pending & STATUSF_IP9)         /* int7 hardware line */
+                       do_IRQ(9, regs);
+               else if (pending & STATUSF_IP10)        /* int8 hardware line */
+                       do_IRQ(10, regs);
+               else if (pending & STATUSF_IP11)        /* int9 hardware line */
+                       do_IRQ(11, regs);
+       }
+}
 
 void __init arch_init_irq(void)
 {
@@ -59,9 +90,6 @@ void __init arch_init_irq(void)
        clear_c0_status(ST0_IM);
        local_irq_disable();
 
-       /* Sets the first-level interrupt dispatcher. */
-       set_except_vector(0, ocelot_handle_int);
-
        mips_cpu_irq_init(0);
        rm7k_cpu_irq_init(8);
 }
index 0e7853f43983f7725f712167738775be4f80a221..63431538d0ec81ad92a1771ec53c15a72474968c 100644 (file)
@@ -6,7 +6,7 @@
 # Makefile for the ITE 8172 (qed-4n-s01b) board, generic files.
 #
 
-obj-y                  += it8172_setup.o irq.o int-handler.o pmon_prom.o \
+obj-y                  += it8172_setup.o irq.o pmon_prom.o \
                           time.o lpc.o puts.o reset.o
 
 obj-$(CONFIG_IT8172_CIR)+= it8172_cir.o
diff --git a/arch/mips/ite-boards/generic/int-handler.S b/arch/mips/ite-boards/generic/int-handler.S
deleted file mode 100644 (file)
index d190d8a..0000000
+++ /dev/null
@@ -1,63 +0,0 @@
-#include <asm/asm.h>
-#include <asm/mipsregs.h>
-#include <asm/regdef.h>
-#include <asm/stackframe.h>
-
-       .text
-       .set    macro
-       .set    noat
-       .align  5
-
-NESTED(it8172_IRQ, PT_SIZE, sp)
-       SAVE_ALL
-       CLI                             # Important: mark KERNEL mode !
-
-        /* We're working with 'reorder' set at this point. */
-       /*
-        * Get pending interrupts
-        */
-
-       mfc0    t0,CP0_CAUSE            # get pending interrupts
-       mfc0    t1,CP0_STATUS           # get enabled interrupts
-       and     t0,t1                   # isolate allowed ones
-
-       andi    t0,0xff00               # isolate pending bits
-        beqz    t0, 3f                  # spurious interrupt
-
-        andi    a0, t0, CAUSEF_IP7
-        beq     a0, zero, 1f
-
-        li     a0, 127                 # MIPS_CPU_TIMER_IRQ = (NR_IRQS-1)
-        move    a1, sp
-        jal     ll_timer_interrupt
-       j       ret_from_irq
-        nop
-
-1:
-        andi    a0, t0, CAUSEF_IP2      # the only int we expect at this time
-        beq     a0, zero, 3f
-       move    a0,sp
-       jal     it8172_hw0_irqdispatch
-
-       mfc0    t0,CP0_STATUS           # disable interrupts
-       ori     t0,1
-       xori    t0,1
-       mtc0    t0,CP0_STATUS
-        nop
-        nop
-        nop
-
-       la      a1, ret_from_irq
-       jr      a1
-        nop
-
-3:
-       move a0, sp
-       jal     mips_spurious_interrupt
-        nop
-       la      a1, ret_from_irq
-       jr      a1
-        nop
-
-END(it8172_IRQ)
-
index e67f96129491009074f28187a7ee72edd9b864c9..77be7216bdd091430735ccb89c1e356144a779fd 100644 (file)
 
 #define ALLINTS_NOTIMER (IE_IRQ0 | IE_IRQ1 | IE_IRQ2 | IE_IRQ3 | IE_IRQ4)
 
-void disable_it8172_irq(unsigned int irq_nr);
-void enable_it8172_irq(unsigned int irq_nr);
-
 extern void set_debug_traps(void);
 extern void mips_timer_interrupt(int irq, struct pt_regs *regs);
-extern asmlinkage void it8172_IRQ(void);
 
 struct it8172_intc_regs volatile *it8172_hw0_icregs =
        (struct it8172_intc_regs volatile *)(KSEG1ADDR(IT8172_PCI_IO_BASE + IT_INTC_BASE));
@@ -181,8 +177,6 @@ void __init arch_init_irq(void)
        int i;
         unsigned long flags;
 
-        set_except_vector(0, it8172_IRQ);
-
        /* mask all interrupts */
        it8172_hw0_icregs->lb_mask  = 0xffff;
        it8172_hw0_icregs->lpc_mask = 0xffff;
@@ -282,6 +276,18 @@ void it8172_hw0_irqdispatch(struct pt_regs *regs)
        do_IRQ(irq, regs);
 }
 
+asmlinkage void plat_irq_dispatch(struct pt_regs *regs)
+{
+       unsigned int pending = read_c0_cause() & read_c0_status() & ST0_IM;
+
+       if (!pending)
+               mips_spurious_interrupt(regs);
+       else if (pending & CAUSEF_IP7)
+               ll_timer_interrupt(127, regs);
+       else if (pending & CAUSEF_IP2)
+               it8172_hw0_irqdispatch(regs);
+}
+
 void show_pending_irqs(void)
 {
        fputs("intstatus:  ");
index b79817bb6cceb777e79ce8f5a315e1811c6a20e5..dee497a91807b163a97392e4663463b6cd994869 100644 (file)
@@ -29,6 +29,7 @@
 #include <linux/sched.h>
 #include <linux/time.h>
 #include <linux/spinlock.h>
+#include <linux/mc146818rtc.h>
 
 #include <asm/time.h>
 #include <asm/mipsregs.h>
index b774db035b3132c69769d37dae693e3889fd1a53..05cf9218c43279b1c8a25e6a5c6ea1ce2072c0cb 100644 (file)
 #include <asm/bootinfo.h>
 #include <linux/string.h>
 #include <linux/kernel.h>
+#include <asm/sections.h>
 #include <asm/it8172/it8172.h>
 #include <asm/it8172/it8172_dbg.h>
 
 int prom_argc;
 char **prom_argv, **prom_envp;
 
-extern char _end;
 extern void  __init prom_init_cmdline(void);
 extern unsigned long __init prom_get_memsize(void);
 extern void __init it8172_init_ram_resource(unsigned long memsize);
index e8ec8be66a80b9d630948312f38654d993273cfb..ea2a754cafe582ef0d6b10dccb76bc7dd71b6edb 100644 (file)
 #include <asm/bootinfo.h>
 #include <linux/string.h>
 #include <linux/kernel.h>
+#include <asm/sections.h>
 #include <asm/it8172/it8172.h>
 #include <asm/it8172/it8172_dbg.h>
 
 int prom_argc;
 char **prom_argv, **prom_envp;
 
-extern char _end;
 extern void  __init prom_init_cmdline(void);
 extern unsigned long __init prom_get_memsize(void);
 extern void __init it8172_init_ram_resource(unsigned long memsize);
index 85749246a671481ead67aae3147198650cc9c6f7..02bd39add891c042a90295a0bd2abd2e2729df99 100644 (file)
@@ -2,6 +2,6 @@
 # Makefile for the Jazz family specific parts of the kernel
 #
 
-obj-y          := int-handler.o irq.o jazzdma.o reset.o setup.o
+obj-y          := irq.o jazzdma.o reset.o setup.o
 
 EXTRA_AFLAGS := $(CFLAGS)
diff --git a/arch/mips/jazz/int-handler.S b/arch/mips/jazz/int-handler.S
deleted file mode 100644 (file)
index dc752c6..0000000
+++ /dev/null
@@ -1,282 +0,0 @@
-/*
- * This file is subject to the terms and conditions of the GNU General Public
- * License.  See the file "COPYING" in the main directory of this archive
- * for more details.
- *
- * Copyright (C) 1995, 1996, 1997, 1998 by Ralf Baechle and Andreas Busse
- *
- * Jazz family specific interrupt stuff
- *
- * To do: On Jazz machines we remap some non-ISA interrupts to ISA
- *        interrupts.  These interrupts should use their own vectors.
- *        Squeeze the last cycles out of the handlers.  Only a dead
- *        cycle is a good cycle.
- */
-#include <asm/asm.h>
-#include <asm/mipsregs.h>
-#include <asm/jazz.h>
-#include <asm/regdef.h>
-#include <asm/stackframe.h>
-
-/*
- * jazz_handle_int: Interrupt handler for the ACER Pica-61 boards
- */
-               .set    noreorder
-
-               NESTED(jazz_handle_int, PT_SIZE, ra)
-               .set    noat
-               SAVE_ALL
-               CLI
-               .set    at
-
-               /*
-                * Get pending interrupts
-                */
-               mfc0    t0,CP0_CAUSE            # get pending interrupts
-               mfc0    t1,CP0_STATUS           # get enabled interrupts
-               and     t0,t1                   # isolate allowed ones
-               andi    t0,0xff00               # isolate pending bits
-               beqz    t0,3f
-               sll     t0,16                   # delay slot
-
-               /*
-                * Find irq with highest priority
-                * FIXME: This is slow - use binary search
-                */
-               la      t1,ll_vectors
-1:             bltz    t0,2f                   # found pending irq
-               sll     t0,1
-               b       1b
-               subu    t1,PTRSIZE              # delay slot
-
-               /*
-                * Do the low-level stuff
-                */
-2:             lw      t0,(t1)
-               jr      t0
-               nop                             # delay slot
-               END(jazz_handle_int)
-
-ll_sw0:                li      s1,~IE_SW0
-               mfc0    t0,CP0_CAUSE
-               and     t0,s1
-               mtc0    t0,CP0_CAUSE
-               PANIC("Unimplemented sw0 handler")
-
-ll_sw1:                li      s1,~IE_SW1
-               mfc0    t0,CP0_CAUSE
-               and     t0,s1
-               mtc0    t0,CP0_CAUSE
-               PANIC("Unimplemented sw1 handler")
-
-ll_local_dma:  li      s1,~IE_IRQ0
-               PANIC("Unimplemented local_dma handler")
-
-ll_local_dev:  lbu     t0,JAZZ_IO_IRQ_SOURCE
-#if PTRSIZE == 8       /* True 64 bit kernel */
-               dsll    t0,1
-#endif
-               .set    reorder
-               LONG_L  t0,local_vector(t0)
-               jr      t0
-               .set    noreorder
-
-/*
- * The braindead PICA hardware gives us no way to distinguish if we really
- * received interrupt 7 from the (E)ISA bus or if we just received an
- * interrupt with no findable cause.  This sometimes happens with braindead
- * cards.  Oh well - for all the Jazz boxes slots are more or less just
- * whistles and bells and we're aware of the problem.
- */
-ll_isa_irq:    lw      a0, JAZZ_EISA_IRQ_ACK
-
-               jal     do_IRQ
-                move   a1,sp
-
-               j       ret_from_irq
-               nop
-
-/*
- * Hmm...  This is not just a plain PC clone so the question is
- * which devices on Jazz machines can generate an (E)ISA NMI?
- * (Writing to nonexistent memory?)
- */
-ll_isa_nmi:    li      s1,~IE_IRQ3
-               PANIC("Unimplemented isa_nmi handler")
-
-/*
- * Timer IRQ - remapped to be more similar to an IBM compatible.
- *
- * The timer interrupt is handled specially to ensure that the jiffies
- * variable is updated at all times.  Specifically, the timer interrupt is
- * just like the complete handlers except that it is invoked with interrupts
- * disabled and should never re-enable them.  If other interrupts were
- * allowed to be processed while the timer interrupt is active, then the
- * other interrupts would have to avoid using the jiffies variable for delay
- * and interval timing operations to avoid hanging the system.
- */
-ll_timer:      lw      zero,JAZZ_TIMER_REGISTER # timer irq cleared on read
-               li      s1,~IE_IRQ4
-
-               li      a0, JAZZ_TIMER_IRQ
-               jal     do_IRQ
-                move   a1,sp
-
-               mfc0    t0,CP0_STATUS           # disable interrupts again
-               ori     t0,1
-               xori    t0,1
-               mtc0    t0,CP0_STATUS
-
-               j       ret_from_irq
-                nop
-
-/*
- * CPU count/compare IRQ (unused)
- */
-ll_count:      j       ret_from_irq
-                mtc0   zero,CP0_COMPARE
-
-#if 0
-/*
- * Call the handler for the interrupt
- * (Currently unused)
- */
-call_real:     /*
-                * temporarily disable interrupt
-                */
-               mfc0    t2,CP0_STATUS
-               and     t2,s1
-               mtc0    t2,CP0_STATUS
-               nor     s1,zero,s1
-               jal     do_IRQ
-
-               /*
-                * reenable interrupt
-                */
-               mfc0    t2,CP0_STATUS
-               or      t2,s1
-               mtc0    t2,CP0_STATUS
-               j       ret_from_irq
-#endif
-
-               .data
-               PTR     ll_sw0                  # SW0
-               PTR     ll_sw1                  # SW1
-               PTR     ll_local_dma            # Local DMA
-               PTR     ll_local_dev            # Local devices
-               PTR     ll_isa_irq              # ISA IRQ
-               PTR     ll_isa_nmi              # ISA NMI
-               PTR     ll_timer                # Timer
-ll_vectors:    PTR     ll_count                # Count/Compare IRQ
-
-               /*
-                * Interrupt handlers for local devices.
-                */
-               .text
-               .set    reorder
-loc_no_irq:    PANIC("Unimplemented loc_no_irq handler")
-/*
- * Parallel port IRQ
- */
-loc_parallel:  li      s1,~JAZZ_IE_PARALLEL
-               li      a0,JAZZ_PARALLEL_IRQ
-               b       loc_call
-
-/*
- * Floppy IRQ
- */
-loc_floppy:    li      s1,~JAZZ_IE_FLOPPY
-               li      a0,JAZZ_FLOPPY_IRQ
-               b       loc_call
-
-/*
- * Sound IRQ
- */
-loc_sound:     PANIC("Unimplemented loc_sound handler")
-loc_video:     PANIC("Unimplemented loc_video handler")
-
-/*
- * Ethernet interrupt handler
- */
-loc_ethernet:  li      s1,~JAZZ_IE_ETHERNET
-               li      a0,JAZZ_ETHERNET_IRQ
-               b       loc_call
-
-/*
- * SCSI interrupt handler
- */
-loc_scsi:      li      s1,~JAZZ_IE_SCSI
-               li      a0,JAZZ_SCSI_IRQ
-               b       loc_call
-
-/*
- * Keyboard interrupt handler
- */
-loc_keyboard:  li      s1,~JAZZ_IE_KEYBOARD
-               li      a0,JAZZ_KEYBOARD_IRQ
-               b       loc_call
-
-/*
- * Mouse interrupt handler
- */
-loc_mouse:     li      s1,~JAZZ_IE_MOUSE
-               li      a0,JAZZ_MOUSE_IRQ
-               b       loc_call
-
-/*
- * Serial port 1 IRQ
- */
-loc_serial1:   li      s1,~JAZZ_IE_SERIAL1
-               li      a0,JAZZ_SERIAL1_IRQ
-               b       loc_call
-
-/*
- * Serial port 2 IRQ
- */
-loc_serial2:   li      s1,~JAZZ_IE_SERIAL2
-               li      a0,JAZZ_SERIAL2_IRQ
-               b       loc_call
-
-/*
- * Call the interrupt handler for an interrupt generated by a
- * local device.
- */
-loc_call:      /*
-                * Temporarily disable interrupt source
-                */
-               lhu     t2,JAZZ_IO_IRQ_ENABLE
-               and     t2,s1
-               sh      t2,JAZZ_IO_IRQ_ENABLE
-
-               nor     s1,zero,s1
-               jal     do_IRQ
-
-               /*
-                * Reenable interrupt
-                */
-               lhu     t2,JAZZ_IO_IRQ_ENABLE
-               or      t2,s1
-               sh      t2,JAZZ_IO_IRQ_ENABLE
-
-               j       ret_from_irq
-
-/*
- * "Jump extender" to reach spurious_interrupt
- */
-3:             j       spurious_interrupt
-
-/*
- * Vectors for interrupts generated by local devices
- */
-               .data
-local_vector:  PTR     loc_no_irq
-               PTR     loc_parallel
-               PTR     loc_floppy
-               PTR     loc_sound
-               PTR     loc_video
-               PTR     loc_ethernet
-               PTR     loc_scsi
-               PTR     loc_keyboard
-               PTR     loc_mouse
-               PTR     loc_serial1
-               PTR     loc_serial2
index b309b1bcf2e87926117e1de16ea2b835107b96c2..becc9accd49573e5d24e052a8e3d8e2e40699339 100644 (file)
@@ -15,8 +15,6 @@
 #include <asm/io.h>
 #include <asm/jazz.h>
 
-extern asmlinkage void jazz_handle_int(void);
-
 static DEFINE_SPINLOCK(r4030_lock);
 
 static void enable_r4030_irq(unsigned int irq)
@@ -90,10 +88,82 @@ void __init init_r4030_ints(void)
  */
 void __init arch_init_irq(void)
 {
-       set_except_vector(0, jazz_handle_int);
-
        init_i8259_irqs();                      /* Integrated i8259  */
        init_r4030_ints();
 
        change_c0_status(ST0_IM, IE_IRQ4 | IE_IRQ3 | IE_IRQ2 | IE_IRQ1);
 }
+
+static void loc_call(unsigned int irq, struct pt_regs *regs, unsigned int mask)
+{
+       r4030_write_reg16(JAZZ_IO_IRQ_ENABLE,
+                         r4030_read_reg16(JAZZ_IO_IRQ_ENABLE) & mask);
+       do_IRQ(irq, regs);
+       r4030_write_reg16(JAZZ_IO_IRQ_ENABLE,
+                         r4030_read_reg16(JAZZ_IO_IRQ_ENABLE) | mask);
+}
+
+static void ll_local_dev(struct pt_regs *regs)
+{
+       switch (r4030_read_reg32(JAZZ_IO_IRQ_SOURCE)) {
+       case 0:
+               panic("Unimplemented loc_no_irq handler");
+               break;
+       case 4:
+               loc_call(JAZZ_PARALLEL_IRQ, regs, JAZZ_IE_PARALLEL);
+               break;
+       case 8:
+               loc_call(JAZZ_PARALLEL_IRQ, regs, JAZZ_IE_FLOPPY);
+               break;
+       case 12:
+               panic("Unimplemented loc_sound handler");
+               break;
+       case 16:
+               panic("Unimplemented loc_video handler");
+               break;
+       case 20:
+               loc_call(JAZZ_ETHERNET_IRQ, regs, JAZZ_IE_ETHERNET);
+               break;
+       case 24:
+               loc_call(JAZZ_SCSI_IRQ, regs, JAZZ_IE_SCSI);
+               break;
+       case 28:
+               loc_call(JAZZ_KEYBOARD_IRQ, regs, JAZZ_IE_KEYBOARD);
+               break;
+       case 32:
+               loc_call(JAZZ_MOUSE_IRQ, regs, JAZZ_IE_MOUSE);
+               break;
+       case 36:
+               loc_call(JAZZ_SERIAL1_IRQ, regs, JAZZ_IE_SERIAL1);
+               break;
+       case 40:
+               loc_call(JAZZ_SERIAL2_IRQ, regs, JAZZ_IE_SERIAL2);
+               break;
+       }
+}
+
+asmlinkage void plat_irq_dispatch(struct pt_regs *regs)
+{
+       unsigned int pending = read_c0_cause() & read_c0_status() & ST0_IM;
+
+       if (pending & IE_IRQ5)
+               write_c0_compare(0);
+       else if (pending & IE_IRQ4) {
+               r4030_read_reg32(JAZZ_TIMER_REGISTER);
+               do_IRQ(JAZZ_TIMER_IRQ, regs);
+       } else if (pending & IE_IRQ3)
+               panic("Unimplemented ISA NMI handler");
+       else if (pending & IE_IRQ2)
+               do_IRQ(r4030_read_reg32(JAZZ_EISA_IRQ_ACK), regs);
+       else if (pending & IE_IRQ1) {
+               ll_local_dev(regs);
+       } else if (unlikely(pending & IE_IRQ0))
+               panic("Unimplemented local_dma handler");
+       else if (pending & IE_SW1) {
+               clear_c0_cause(IE_SW1);
+               panic("Unimplemented sw1 handler");
+       } else if (pending & IE_SW0) {
+               clear_c0_cause(IE_SW0);
+               panic("Unimplemented sw0 handler");
+       }
+}
index a6bd3f4d3049d56c9790a1ffb450edeb29062d16..e6561345d12a345cec239a4daec921b98bf3dce5 100644 (file)
@@ -60,15 +60,15 @@ rtc_ds1742_get_time(void)
        unsigned long flags;
 
        spin_lock_irqsave(&rtc_lock, flags);
-       CMOS_WRITE(RTC_READ, RTC_CONTROL);
-       second = BCD2BIN(CMOS_READ(RTC_SECONDS) & RTC_SECONDS_MASK);
-       minute = BCD2BIN(CMOS_READ(RTC_MINUTES));
-       hour = BCD2BIN(CMOS_READ(RTC_HOURS));
-       day = BCD2BIN(CMOS_READ(RTC_DATE));
-       month = BCD2BIN(CMOS_READ(RTC_MONTH));
-       year = BCD2BIN(CMOS_READ(RTC_YEAR));
-       century = BCD2BIN(CMOS_READ(RTC_CENTURY) & RTC_CENTURY_MASK);
-       CMOS_WRITE(0, RTC_CONTROL);
+       rtc_write(RTC_READ, RTC_CONTROL);
+       second = BCD2BIN(rtc_read(RTC_SECONDS) & RTC_SECONDS_MASK);
+       minute = BCD2BIN(rtc_read(RTC_MINUTES));
+       hour = BCD2BIN(rtc_read(RTC_HOURS));
+       day = BCD2BIN(rtc_read(RTC_DATE));
+       month = BCD2BIN(rtc_read(RTC_MONTH));
+       year = BCD2BIN(rtc_read(RTC_YEAR));
+       century = BCD2BIN(rtc_read(RTC_CENTURY) & RTC_CENTURY_MASK);
+       rtc_write(0, RTC_CONTROL);
        spin_unlock_irqrestore(&rtc_lock, flags);
 
        year += century * 100;
@@ -87,16 +87,16 @@ rtc_ds1742_set_time(unsigned long t)
        unsigned long flags;
 
        spin_lock_irqsave(&rtc_lock, flags);
-       CMOS_WRITE(RTC_READ, RTC_CONTROL);
-       cmos_second = (u8)(CMOS_READ(RTC_SECONDS) & RTC_SECONDS_MASK);
-       cmos_minute = (u8)CMOS_READ(RTC_MINUTES);
-       cmos_hour = (u8)CMOS_READ(RTC_HOURS);
-       cmos_day = (u8)CMOS_READ(RTC_DATE);
-       cmos_month = (u8)CMOS_READ(RTC_MONTH);
-       cmos_year = (u8)CMOS_READ(RTC_YEAR);
-       cmos_century = CMOS_READ(RTC_CENTURY) & RTC_CENTURY_MASK;
+       rtc_write(RTC_READ, RTC_CONTROL);
+       cmos_second = (u8)(rtc_read(RTC_SECONDS) & RTC_SECONDS_MASK);
+       cmos_minute = (u8)rtc_read(RTC_MINUTES);
+       cmos_hour = (u8)rtc_read(RTC_HOURS);
+       cmos_day = (u8)rtc_read(RTC_DATE);
+       cmos_month = (u8)rtc_read(RTC_MONTH);
+       cmos_year = (u8)rtc_read(RTC_YEAR);
+       cmos_century = rtc_read(RTC_CENTURY) & RTC_CENTURY_MASK;
 
-       CMOS_WRITE(RTC_WRITE, RTC_CONTROL);
+       rtc_write(RTC_WRITE, RTC_CONTROL);
 
        /* convert */
        to_tm(t, &tm);
@@ -104,18 +104,18 @@ rtc_ds1742_set_time(unsigned long t)
        /* check each field one by one */
        year = BIN2BCD(tm.tm_year - EPOCH);
        if (year != cmos_year) {
-               CMOS_WRITE(year,RTC_YEAR);
+               rtc_write(year,RTC_YEAR);
        }
 
        month = BIN2BCD(tm.tm_mon);
        if (month != (cmos_month & 0x1f)) {
-               CMOS_WRITE((month & 0x1f) | (cmos_month & ~0x1f),RTC_MONTH);
+               rtc_write((month & 0x1f) | (cmos_month & ~0x1f),RTC_MONTH);
        }
 
        day = BIN2BCD(tm.tm_mday);
        if (day != cmos_day) {
 
-               CMOS_WRITE(day, RTC_DATE);
+               rtc_write(day, RTC_DATE);
        }
 
        if (cmos_hour & 0x40) {
@@ -130,20 +130,20 @@ rtc_ds1742_set_time(unsigned long t)
                /* 24 hour format */
                hour = BIN2BCD(tm.tm_hour) & 0x3f;
        }
-       if (hour != cmos_hour) CMOS_WRITE(hour, RTC_HOURS);
+       if (hour != cmos_hour) rtc_write(hour, RTC_HOURS);
 
        minute = BIN2BCD(tm.tm_min);
        if (minute !=  cmos_minute) {
-               CMOS_WRITE(minute, RTC_MINUTES);
+               rtc_write(minute, RTC_MINUTES);
        }
 
        second = BIN2BCD(tm.tm_sec);
        if (second !=  cmos_second) {
-               CMOS_WRITE(second & RTC_SECONDS_MASK,RTC_SECONDS);
+               rtc_write(second & RTC_SECONDS_MASK,RTC_SECONDS);
        }
 
        /* RTC_CENTURY and RTC_CONTROL share same address... */
-       CMOS_WRITE(cmos_century, RTC_CONTROL);
+       rtc_write(cmos_century, RTC_CONTROL);
        spin_unlock_irqrestore(&rtc_lock, flags);
 
        return 0;
@@ -163,9 +163,9 @@ rtc_ds1742_init(unsigned long base)
        rtc_mips_set_time = rtc_ds1742_set_time;
 
        /* clear oscillator stop bit */
-       CMOS_WRITE(RTC_READ, RTC_CONTROL);
-       cmos_second = (u8)(CMOS_READ(RTC_SECONDS) & RTC_SECONDS_MASK);
-       CMOS_WRITE(RTC_WRITE, RTC_CONTROL);
-       CMOS_WRITE(cmos_second, RTC_SECONDS); /* clear msb */
-       CMOS_WRITE(0, RTC_CONTROL);
+       rtc_write(RTC_READ, RTC_CONTROL);
+       cmos_second = (u8)(rtc_read(RTC_SECONDS) & RTC_SECONDS_MASK);
+       rtc_write(RTC_WRITE, RTC_CONTROL);
+       rtc_write(cmos_second, RTC_SECONDS); /* clear msb */
+       rtc_write(0, RTC_CONTROL);
 }
index 75bf418b94c0cf8a2192e14d165b3f5ebc2c1151..baf5077813c1ac2489be2ff0488c9aa6e42b679f 100644 (file)
@@ -2,7 +2,7 @@
 # Makefile for TOSHIBA JMR-TX3927 board
 #
 
-obj-y                          += init.o int-handler.o irq.o setup.o
+obj-y                          += init.o irq.o setup.o
 obj-$(CONFIG_RUNTIME_DEBUG)    += debug.o
 obj-$(CONFIG_KGDB)             += kgdb_io.o
 
diff --git a/arch/mips/jmr3927/rbhma3100/int-handler.S b/arch/mips/jmr3927/rbhma3100/int-handler.S
deleted file mode 100644 (file)
index f85bbf4..0000000
+++ /dev/null
@@ -1,74 +0,0 @@
-/*
- * Copyright 2001 MontaVista Software Inc.
- * Author: MontaVista Software, Inc.
- *              ahennessy@mvista.com
- *
- * Based on arch/mips/tsdb/kernel/int-handler.S
- *
- * Copyright (C) 2000-2001 Toshiba Corporation
- *
- *  This program is free software; you can redistribute  it and/or modify it
- *  under  the terms of  the GNU General  Public License as published by the
- *  Free Software Foundation;  either version 2 of the  License, or (at your
- *  option) any later version.
- *
- *  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 AUTHOR  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.
- *
- *  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.,
- *  675 Mass Ave, Cambridge, MA 02139, USA.
- */
-
-#include <asm/asm.h>
-#include <asm/mipsregs.h>
-#include <asm/regdef.h>
-#include <asm/stackframe.h>
-#include <asm/jmr3927/jmr3927.h>
-
-       /* A lot of complication here is taken away because:
-        *
-        * 1) We handle one interrupt and return, sitting in a loop
-        *    and moving across all the pending IRQ bits in the cause
-        *    register is _NOT_ the answer, the common case is one
-        *    pending IRQ so optimize in that direction.
-        *
-        * 2) We need not check against bits in the status register
-        *    IRQ mask, that would make this routine slow as hell.
-        *
-        * 3) Linux only thinks in terms of all IRQs on or all IRQs
-        *    off, nothing in between like BSD spl() brain-damage.
-        *
-        */
-
-/* Flush write buffer (needed?)
- * NOTE: TX39xx performs "non-blocking load", so explicitly use the target
- * register of LBU to flush immediately.
- */
-#define FLUSH_WB(tmp)  \
-       la      tmp, JMR3927_IOC_REV_ADDR; \
-       lbu     tmp, (tmp); \
-       move    tmp, zero;
-
-       .text
-       .set    noreorder
-       .set    noat
-       .align  5
-       NESTED(jmr3927_IRQ, PT_SIZE, sp)
-       SAVE_ALL
-       CLI
-       .set    at
-       jal     jmr3927_irc_irqdispatch
-        move   a0, sp
-       FLUSH_WB(t0)
-       j       ret_from_irq
-        nop
-       END(jmr3927_IRQ)
index 2810727f1d4e64312708827e6f8c88c4f5fab4e6..11304d1354f45b0d47afc511e9a7811fa9383ca6 100644 (file)
@@ -77,8 +77,6 @@ static int jmr3927_gen_iack(void)
 }
 #endif
 
-extern asmlinkage void jmr3927_IRQ(void);
-
 #define irc_dlevel     0
 #define irc_elevel     1
 
@@ -262,7 +260,7 @@ void jmr3927_spurious(struct pt_regs *regs)
               regs->cp0_cause, regs->cp0_epc, regs->regs[31]);
 }
 
-void jmr3927_irc_irqdispatch(struct pt_regs *regs)
+asmlinkage void plat_irq_dispatch(struct pt_regs *regs)
 {
        int irq;
 
@@ -398,8 +396,6 @@ void __init arch_init_irq(void)
 
        jmr3927_irq_init(NR_ISA_IRQS);
 
-       set_except_vector(0, jmr3927_IRQ);
-
        /* setup irq space */
        add_tb_irq_space(&jmr3927_isac_irqspace);
        add_tb_irq_space(&jmr3927_ioc_irqspace);
index 309d54cceda3c66eb93d4c48eb655aaa6238d72c..34e8a256765c3f2a811e6c6edc701ccb6544b032 100644 (file)
@@ -34,8 +34,11 @@ obj-$(CONFIG_CPU_R6000)              += r6000_fpu.o r4k_switch.o
 
 obj-$(CONFIG_SMP)              += smp.o
 
-obj-$(CONFIG_MIPS_MT_SMP)      += smp_mt.o
+obj-$(CONFIG_MIPS_MT)          += mips-mt.o
+obj-$(CONFIG_MIPS_MT_SMTC)     += smtc.o smtc-asm.o smtc-proc.o
+obj-$(CONFIG_MIPS_MT_SMP)      += smp-mt.o
 
+obj-$(CONFIG_MIPS_APSP_KSPD)   += kspd.o
 obj-$(CONFIG_MIPS_VPE_LOADER)  += vpe.o
 obj-$(CONFIG_MIPS_VPE_APSP_API)        += rtlx.o
 
index ca6b03c773be3b2d7da5578b2d8da7838a7c19b0..92b28b674d6f615be8ab8894ea117e06018f44d1 100644 (file)
@@ -69,6 +69,9 @@ void output_ptreg_defines(void)
        offset("#define PT_BVADDR ", struct pt_regs, cp0_badvaddr);
        offset("#define PT_STATUS ", struct pt_regs, cp0_status);
        offset("#define PT_CAUSE  ", struct pt_regs, cp0_cause);
+#ifdef CONFIG_MIPS_MT_SMTC
+       offset("#define PT_TCSTATUS  ", struct pt_regs, cp0_tcstatus);
+#endif /* CONFIG_MIPS_MT_SMTC */
        size("#define PT_SIZE   ", struct pt_regs);
        linefeed;
 }
index 83c87fe4ee4f0b631cb5be82dfd9783d15c3541d..d101d2fb24caab6f8283647a20a5c37768f30c05 100644 (file)
@@ -17,6 +17,9 @@
 #include <asm/isadep.h>
 #include <asm/thread_info.h>
 #include <asm/war.h>
+#ifdef CONFIG_MIPS_MT_SMTC
+#include <asm/mipsmtregs.h>
+#endif
 
 #ifdef CONFIG_PREEMPT
        .macro  preempt_stop
@@ -75,6 +78,37 @@ FEXPORT(syscall_exit)
        bnez    t0, syscall_exit_work
 
 FEXPORT(restore_all)                   # restore full frame
+#ifdef CONFIG_MIPS_MT_SMTC
+/* Detect and execute deferred IPI "interrupts" */
+       move    a0,sp
+       jal     deferred_smtc_ipi
+/* Re-arm any temporarily masked interrupts not explicitly "acked" */
+       mfc0    v0, CP0_TCSTATUS
+       ori     v1, v0, TCSTATUS_IXMT
+       mtc0    v1, CP0_TCSTATUS
+       andi    v0, TCSTATUS_IXMT
+       ehb
+       mfc0    t0, CP0_TCCONTEXT
+       DMT     9                               # dmt t1
+       jal     mips_ihb
+       mfc0    t2, CP0_STATUS
+       andi    t3, t0, 0xff00
+       or      t2, t2, t3
+       mtc0    t2, CP0_STATUS
+       ehb
+       andi    t1, t1, VPECONTROL_TE
+       beqz    t1, 1f
+       EMT
+1:
+       mfc0    v1, CP0_TCSTATUS
+       /* We set IXMT above, XOR should cler it here */
+       xori    v1, v1, TCSTATUS_IXMT
+       or      v1, v0, v1
+       mtc0    v1, CP0_TCSTATUS
+       ehb
+       xor     t0, t0, t3
+       mtc0    t0, CP0_TCCONTEXT
+#endif /* CONFIG_MIPS_MT_SMTC */
        .set    noat
        RESTORE_TEMP
        RESTORE_AT
@@ -120,28 +154,17 @@ syscall_exit_work:
        jal     do_syscall_trace
        b       resume_userspace
 
+#if defined(CONFIG_CPU_MIPSR2) || defined(CONFIG_MIPS_MT)
+
 /*
- * Common spurious interrupt handler.
+ * MIPS32R2 Instruction Hazard Barrier - must be called
+ *
+ * For C code use the inline version named instruction_hazard().
  */
-LEAF(spurious_interrupt)
-       /*
-        * Someone tried to fool us by sending an interrupt but we
-        * couldn't find a cause for it.
-        */
-       PTR_LA  t1, irq_err_count
-#ifdef CONFIG_SMP
-1:     ll      t0, (t1)
-       addiu   t0, 1
-       sc      t0, (t1)
-#if R10000_LLSC_WAR
-       beqzl   t0, 1b
-#else
-       beqz    t0, 1b
-#endif
-#else
-       lw      t0, (t1)
-       addiu   t0, 1
-       sw      t0, (t1)
-#endif
-       j       ret_from_irq
-       END(spurious_interrupt)
+LEAF(mips_ihb)
+       .set    mips32r2
+       jr.hb   ra
+       nop
+       END(mips_ihb)
+
+#endif /* CONFIG_CPU_MIPSR2 or CONFIG_MIPS_MT */
index 235ad9f6bd350595318335171a2ab4e2db5b72d5..10f28fb9f008a92fc89b68c89734233297e8472b 100644 (file)
  */
 
 3:
+#ifdef CONFIG_MIPS_MT_SMTC
+               /* Read-modify write of Status must be atomic */
+               mfc0    t2, CP0_TCSTATUS
+               ori     t1, t2, TCSTATUS_IXMT
+               mtc0    t1, CP0_TCSTATUS
+               andi    t2, t2, TCSTATUS_IXMT
+               ehb
+               DMT     9                               # dmt   t1
+               jal     mips_ihb
+               nop
+#endif /* CONFIG_MIPS_MT_SMTC */
                mfc0    t0, CP0_STATUS
                ori     t0, 0x1f
                xori    t0, 0x1f
                mtc0    t0, CP0_STATUS
-
+#ifdef CONFIG_MIPS_MT_SMTC
+               andi    t1, t1, VPECONTROL_TE
+               beqz    t1, 9f
+               nop
+               EMT                                     # emt
+9:
+               mfc0    t1, CP0_TCSTATUS
+               xori    t1, t1, TCSTATUS_IXMT
+               or      t1, t1, t2
+               mtc0    t1, CP0_TCSTATUS
+               ehb
+#endif /* CONFIG_MIPS_MT_SMTC */
                LONG_L  v0, GDB_FR_STATUS(sp)
                LONG_L  v1, GDB_FR_EPC(sp)
                mtc0    v0, CP0_STATUS
index d4f88e0af24c04fcb51271d50414242418f96ded..6ecbdc1fefd13acdd930998a07c19e633aaab354 100644 (file)
 #include <asm/system.h>
 #include <asm/gdb-stub.h>
 #include <asm/inst.h>
+#include <asm/smp.h>
 
 /*
  * external low-level support routines
@@ -669,6 +670,64 @@ static void kgdb_wait(void *arg)
        local_irq_restore(flags);
 }
 
+/*
+ * GDB stub needs to call kgdb_wait on all processor with interrupts
+ * disabled, so it uses it's own special variant.
+ */
+static int kgdb_smp_call_kgdb_wait(void)
+{
+#ifdef CONFIG_SMP
+       struct call_data_struct data;
+       int i, cpus = num_online_cpus() - 1;
+       int cpu = smp_processor_id();
+
+       /*
+        * Can die spectacularly if this CPU isn't yet marked online
+        */
+       BUG_ON(!cpu_online(cpu));
+
+       if (!cpus)
+               return 0;
+
+       if (spin_is_locked(&smp_call_lock)) {
+               /*
+                * Some other processor is trying to make us do something
+                * but we're not going to respond... give up
+                */
+               return -1;
+               }
+
+       /*
+        * We will continue here, accepting the fact that
+        * the kernel may deadlock if another CPU attempts
+        * to call smp_call_function now...
+        */
+
+       data.func = kgdb_wait;
+       data.info = NULL;
+       atomic_set(&data.started, 0);
+       data.wait = 0;
+
+       spin_lock(&smp_call_lock);
+       call_data = &data;
+       mb();
+
+       /* Send a message to all other CPUs and wait for them to respond */
+       for (i = 0; i < NR_CPUS; i++)
+               if (cpu_online(i) && i != cpu)
+                       core_send_ipi(i, SMP_CALL_FUNCTION);
+
+       /* Wait for response */
+       /* FIXME: lock-up detection, backtrace on lock-up */
+       while (atomic_read(&data.started) != cpus)
+               barrier();
+
+       call_data = NULL;
+       spin_unlock(&smp_call_lock);
+#endif
+
+       return 0;
+}
 
 /*
  * This function does all command processing for interfacing to gdb.  It
@@ -718,7 +777,7 @@ void handle_exception (struct gdb_regs *regs)
        /*
         * force other cpus to enter kgdb
         */
-       smp_call_function(kgdb_wait, NULL, 0, 0);
+       kgdb_smp_call_kgdb_wait();
 
        /*
         * If we're in breakpoint() increment the PC
index 13f22d1d0e8b7fe119ca0294e257567bf693359a..ff7af369f2862eedd4e8fbf08eb6eb3adf263010 100644 (file)
@@ -12,6 +12,7 @@
 #include <linux/init.h>
 
 #include <asm/asm.h>
+#include <asm/asmmacro.h>
 #include <asm/cacheops.h>
 #include <asm/regdef.h>
 #include <asm/fpregdef.h>
@@ -122,6 +123,20 @@ handle_vcei:
        .set    pop
        END(except_vec3_r4000)
 
+       __FINIT
+
+       .align  5
+NESTED(handle_int, PT_SIZE, sp)
+       SAVE_ALL
+       CLI
+
+       PTR_LA  ra, ret_from_irq
+       move    a0, sp
+       j       plat_irq_dispatch
+       END(handle_int)
+
+       __INIT
+
 /*
  * Special interrupt vector for MIPS64 ISA & embedded MIPS processors.
  * This is a dedicated interrupt exception vector which reduces the
@@ -157,6 +172,15 @@ NESTED(except_vec_vi, 0, sp)
        SAVE_AT
        .set    push
        .set    noreorder
+#ifdef CONFIG_MIPS_MT_SMTC
+       /*
+        * To keep from blindly blocking *all* interrupts
+        * during service by SMTC kernel, we also want to
+        * pass the IM value to be cleared.
+        */
+EXPORT(except_vec_vi_mori)
+       ori     a0, $0, 0
+#endif /* CONFIG_MIPS_MT_SMTC */
 EXPORT(except_vec_vi_lui)
        lui     v0, 0           /* Patched */
        j       except_vec_vi_handler
@@ -173,6 +197,25 @@ EXPORT(except_vec_vi_end)
 NESTED(except_vec_vi_handler, 0, sp)
        SAVE_TEMP
        SAVE_STATIC
+#ifdef CONFIG_MIPS_MT_SMTC
+       /*
+        * SMTC has an interesting problem that interrupts are level-triggered,
+        * and the CLI macro will clear EXL, potentially causing a duplicate
+        * interrupt service invocation. So we need to clear the associated
+        * IM bit of Status prior to doing CLI, and restore it after the
+        * service routine has been invoked - we must assume that the
+        * service routine will have cleared the state, and any active
+        * level represents a new or otherwised unserviced event...
+        */
+       mfc0    t1, CP0_STATUS
+       and     t0, a0, t1
+       mfc0    t2, CP0_TCCONTEXT
+       or      t0, t0, t2
+       mtc0    t0, CP0_TCCONTEXT
+       xor     t1, t1, t0
+       mtc0    t1, CP0_STATUS
+       ehb
+#endif /* CONFIG_MIPS_MT_SMTC */
        CLI
        move    a0, sp
        jalr    v0
index 2e9122a4213a2215480637903b0948910ef6128c..bdf6f6eff721262d1c98a9dc48adba2b569adba9 100644 (file)
@@ -18,6 +18,7 @@
 #include <linux/threads.h>
 
 #include <asm/asm.h>
+#include <asm/asmmacro.h>
 #include <asm/regdef.h>
 #include <asm/page.h>
 #include <asm/mipsregs.h>
         */
        .macro  setup_c0_status set clr
        .set    push
+#ifdef CONFIG_MIPS_MT_SMTC
+       /*
+        * For SMTC, we need to set privilege and disable interrupts only for
+        * the current TC, using the TCStatus register.
+        */
+       mfc0    t0, CP0_TCSTATUS
+       /* Fortunately CU 0 is in the same place in both registers */
+       /* Set TCU0, TMX, TKSU (for later inversion) and IXMT */
+       li      t1, ST0_CU0 | 0x08001c00
+       or      t0, t1
+       /* Clear TKSU, leave IXMT */
+       xori    t0, 0x00001800
+       mtc0    t0, CP0_TCSTATUS
+       ehb
+       /* We need to leave the global IE bit set, but clear EXL...*/
+       mfc0    t0, CP0_STATUS
+       or      t0, ST0_CU0 | ST0_EXL | ST0_ERL | \set | \clr
+       xor     t0, ST0_EXL | ST0_ERL | \clr
+       mtc0    t0, CP0_STATUS
+#else
        mfc0    t0, CP0_STATUS
        or      t0, ST0_CU0|\set|0x1f|\clr
        xor     t0, 0x1f|\clr
        mtc0    t0, CP0_STATUS
        .set    noreorder
        sll     zero,3                          # ehb
+#endif
        .set    pop
        .endm
 
@@ -134,6 +156,24 @@ NESTED(kernel_entry, 16, sp)                       # kernel entry point
 
        ARC64_TWIDDLE_PC
 
+#ifdef CONFIG_MIPS_MT_SMTC
+       /*
+        * In SMTC kernel, "CLI" is thread-specific, in TCStatus.
+        * We still need to enable interrupts globally in Status,
+        * and clear EXL/ERL.
+        *
+        * TCContext is used to track interrupt levels under
+        * service in SMTC kernel. Clear for boot TC before
+        * allowing any interrupts.
+        */
+       mtc0    zero, CP0_TCCONTEXT
+
+       mfc0    t0, CP0_STATUS
+       ori     t0, t0, 0xff1f
+       xori    t0, t0, 0x001e
+       mtc0    t0, CP0_STATUS
+#endif /* CONFIG_MIPS_MT_SMTC */
+
        PTR_LA          t0, __bss_start         # clear .bss
        LONG_S          zero, (t0)
        PTR_LA          t1, __bss_stop - LONGSIZE
@@ -166,8 +206,25 @@ NESTED(kernel_entry, 16, sp)                       # kernel entry point
  * function after setting up the stack and gp registers.
  */
 NESTED(smp_bootstrap, 16, sp)
+#ifdef CONFIG_MIPS_MT_SMTC
+       /*
+        * Read-modify-writes of Status must be atomic, and this
+        * is one case where CLI is invoked without EXL being
+        * necessarily set. The CLI and setup_c0_status will
+        * in fact be redundant for all but the first TC of
+        * each VPE being booted.
+        */
+       DMT     10      # dmt t2 /* t0, t1 are used by CLI and setup_c0_status() */
+       jal     mips_ihb
+#endif /* CONFIG_MIPS_MT_SMTC */
        setup_c0_status_sec
        smp_slave_setup
+#ifdef CONFIG_MIPS_MT_SMTC
+       andi    t2, t2, VPECONTROL_TE
+       beqz    t2, 2f
+       EMT             # emt
+2:
+#endif /* CONFIG_MIPS_MT_SMTC */
        j       start_secondary
        END(smp_bootstrap)
 #endif /* CONFIG_SMP */
index b974ac9057f616e5f3eb07882da80c3712762842..2125ba5f1d9b20b2d2e0fe282e6513b399546478 100644 (file)
@@ -187,6 +187,10 @@ handle_real_irq:
                outb(cached_21,0x21);
                outb(0x60+irq,0x20);    /* 'Specific EOI' to master */
        }
+#ifdef CONFIG_MIPS_MT_SMTC
+        if (irq_hwmask[irq] & ST0_IM)
+               set_c0_status(irq_hwmask[irq] & ST0_IM);
+#endif /* CONFIG_MIPS_MT_SMTC */
        spin_unlock_irqrestore(&i8259A_lock, flags);
        return;
 
index 3f653c7cfbf3d58eba3dbb300d96a13152a10aea..97ebdc754b9e6e8a59a1edf02611819872e606fb 100644 (file)
@@ -76,6 +76,11 @@ static void level_mask_and_ack_msc_irq(unsigned int irq)
        mask_msc_irq(irq);
        if (!cpu_has_veic)
                MSCIC_WRITE(MSC01_IC_EOI, 0);
+#ifdef CONFIG_MIPS_MT_SMTC
+       /* This actually needs to be a call into platform code */
+       if (irq_hwmask[irq] & ST0_IM)
+               set_c0_status(irq_hwmask[irq] & ST0_IM);
+#endif /* CONFIG_MIPS_MT_SMTC */
 }
 
 /*
@@ -92,6 +97,10 @@ static void edge_mask_and_ack_msc_irq(unsigned int irq)
                MSCIC_WRITE(MSC01_IC_SUP+irq*8, r | ~MSC01_IC_SUP_EDGE_BIT);
                MSCIC_WRITE(MSC01_IC_SUP+irq*8, r);
        }
+#ifdef CONFIG_MIPS_MT_SMTC
+       if (irq_hwmask[irq] & ST0_IM)
+               set_c0_status(irq_hwmask[irq] & ST0_IM);
+#endif /* CONFIG_MIPS_MT_SMTC */
 }
 
 /*
index 3dd76b3d296778c1f81596a8888da5bf96fc4ab3..3dce742e716fd3df1b36920dc3606d2e91fb056b 100644 (file)
@@ -38,6 +38,15 @@ void ack_bad_irq(unsigned int irq)
 
 atomic_t irq_err_count;
 
+#ifdef CONFIG_MIPS_MT_SMTC
+/*
+ * SMTC Kernel needs to manipulate low-level CPU interrupt mask
+ * in do_IRQ. These are passed in setup_irq_smtc() and stored
+ * in this table.
+ */
+unsigned long irq_hwmask[NR_IRQS];
+#endif /* CONFIG_MIPS_MT_SMTC */
+
 #undef do_IRQ
 
 /*
@@ -49,6 +58,7 @@ asmlinkage unsigned int do_IRQ(unsigned int irq, struct pt_regs *regs)
 {
        irq_enter();
 
+       __DO_IRQ_SMTC_HOOK();
        __do_IRQ(irq, regs);
 
        irq_exit();
@@ -101,6 +111,11 @@ skip:
        return 0;
 }
 
+asmlinkage void spurious_interrupt(struct pt_regs *regs)
+{
+       atomic_inc(&irq_err_count);
+}
+
 #ifdef CONFIG_KGDB
 extern void breakpoint(void);
 extern void set_debug_traps(void);
@@ -124,6 +139,9 @@ void __init init_IRQ(void)
                irq_desc[i].depth   = 1;
                irq_desc[i].handler = &no_irq_type;
                spin_lock_init(&irq_desc[i].lock);
+#ifdef CONFIG_MIPS_MT_SMTC
+               irq_hwmask[i] = 0;
+#endif /* CONFIG_MIPS_MT_SMTC */
        }
 
        arch_init_irq();
diff --git a/arch/mips/kernel/kspd.c b/arch/mips/kernel/kspd.c
new file mode 100644 (file)
index 0000000..f06a144
--- /dev/null
@@ -0,0 +1,398 @@
+/*
+ * Copyright (C) 2005 MIPS Technologies, Inc.  All rights reserved.
+ *
+ *  This program is free software; you can distribute 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 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.,
+ *  59 Temple Place - Suite 330, Boston MA 02111-1307, USA.
+ *
+ */
+#include <linux/kernel.h>
+#include <linux/module.h>
+#include <linux/unistd.h>
+#include <linux/file.h>
+#include <linux/fs.h>
+#include <linux/syscalls.h>
+#include <linux/workqueue.h>
+#include <linux/errno.h>
+#include <linux/list.h>
+
+#include <asm/vpe.h>
+#include <asm/rtlx.h>
+#include <asm/kspd.h>
+
+static struct workqueue_struct *workqueue = NULL;
+static struct work_struct work;
+
+extern unsigned long cpu_khz;
+
+struct mtsp_syscall {
+       int cmd;
+       unsigned char abi;
+       unsigned char size;
+};
+
+struct mtsp_syscall_ret {
+       int retval;
+       int errno;
+};
+
+struct mtsp_syscall_generic {
+       int arg0;
+       int arg1;
+       int arg2;
+       int arg3;
+       int arg4;
+       int arg5;
+       int arg6;
+};
+
+static struct list_head kspd_notifylist;
+static int sp_stopping = 0;
+
+/* these should match with those in the SDE kit */
+#define MTSP_SYSCALL_BASE      0
+#define MTSP_SYSCALL_EXIT      (MTSP_SYSCALL_BASE + 0)
+#define MTSP_SYSCALL_OPEN      (MTSP_SYSCALL_BASE + 1)
+#define MTSP_SYSCALL_READ      (MTSP_SYSCALL_BASE + 2)
+#define MTSP_SYSCALL_WRITE     (MTSP_SYSCALL_BASE + 3)
+#define MTSP_SYSCALL_CLOSE     (MTSP_SYSCALL_BASE + 4)
+#define MTSP_SYSCALL_LSEEK32   (MTSP_SYSCALL_BASE + 5)
+#define MTSP_SYSCALL_ISATTY    (MTSP_SYSCALL_BASE + 6)
+#define MTSP_SYSCALL_GETTIME   (MTSP_SYSCALL_BASE + 7)
+#define MTSP_SYSCALL_PIPEFREQ  (MTSP_SYSCALL_BASE + 8)
+#define MTSP_SYSCALL_GETTOD    (MTSP_SYSCALL_BASE + 9)
+
+#define MTSP_O_RDONLY          0x0000
+#define MTSP_O_WRONLY          0x0001
+#define MTSP_O_RDWR            0x0002
+#define MTSP_O_NONBLOCK                0x0004
+#define MTSP_O_APPEND          0x0008
+#define MTSP_O_SHLOCK          0x0010
+#define MTSP_O_EXLOCK          0x0020
+#define MTSP_O_ASYNC           0x0040
+#define MTSP_O_FSYNC           O_SYNC
+#define MTSP_O_NOFOLLOW                0x0100
+#define MTSP_O_SYNC            0x0080
+#define MTSP_O_CREAT           0x0200
+#define MTSP_O_TRUNC           0x0400
+#define MTSP_O_EXCL            0x0800
+#define MTSP_O_BINARY          0x8000
+
+#define SP_VPE 1
+
+struct apsp_table  {
+       int sp;
+       int ap;
+};
+
+/* we might want to do the mode flags too */
+struct apsp_table open_flags_table[] = {
+       { MTSP_O_RDWR, O_RDWR },
+       { MTSP_O_WRONLY, O_WRONLY },
+       { MTSP_O_CREAT, O_CREAT },
+       { MTSP_O_TRUNC, O_TRUNC },
+       { MTSP_O_NONBLOCK, O_NONBLOCK },
+       { MTSP_O_APPEND, O_APPEND },
+       { MTSP_O_NOFOLLOW, O_NOFOLLOW }
+};
+
+struct apsp_table syscall_command_table[] = {
+       { MTSP_SYSCALL_OPEN, __NR_open },
+       { MTSP_SYSCALL_CLOSE, __NR_close },
+       { MTSP_SYSCALL_READ, __NR_read },
+       { MTSP_SYSCALL_WRITE, __NR_write },
+       { MTSP_SYSCALL_LSEEK32, __NR_lseek }
+};
+
+static int sp_syscall(int num, int arg0, int arg1, int arg2, int arg3)
+{
+       register long int _num  __asm__ ("$2") = num;
+       register long int _arg0  __asm__ ("$4") = arg0;
+       register long int _arg1  __asm__ ("$5") = arg1;
+       register long int _arg2  __asm__ ("$6") = arg2;
+       register long int _arg3  __asm__ ("$7") = arg3;
+
+       mm_segment_t old_fs;
+
+       old_fs = get_fs();
+       set_fs(KERNEL_DS);
+
+       __asm__ __volatile__ (
+       "       syscall                                 \n"
+       : "=r" (_num), "=r" (_arg3)
+       : "r" (_num), "r" (_arg0), "r" (_arg1), "r" (_arg2), "r" (_arg3));
+
+       set_fs(old_fs);
+
+       /* $a3 is error flag */
+       if (_arg3)
+               return -_num;
+
+       return _num;
+}
+
+static int translate_syscall_command(int cmd)
+{
+       int i;
+       int ret = -1;
+
+       for (i = 0; i < ARRAY_SIZE(syscall_command_table); i++) {
+               if ((cmd == syscall_command_table[i].sp))
+                       return syscall_command_table[i].ap;
+       }
+
+       return ret;
+}
+
+static unsigned int translate_open_flags(int flags)
+{
+       int i;
+       unsigned int ret = 0;
+
+       for (i = 0; i < (sizeof(open_flags_table) / sizeof(struct apsp_table));
+            i++) {
+               if( (flags & open_flags_table[i].sp) ) {
+                       ret |= open_flags_table[i].ap;
+               }
+       }
+
+       return ret;
+}
+
+
+static void sp_setfsuidgid( uid_t uid, gid_t gid)
+{
+       current->fsuid = uid;
+       current->fsgid = gid;
+
+       key_fsuid_changed(current);
+       key_fsgid_changed(current);
+}
+
+/*
+ * Expects a request to be on the sysio channel. Reads it.  Decides whether
+ * its a linux syscall and runs it, or whatever.  Puts the return code back
+ * into the request and sends the whole thing back.
+ */
+void sp_work_handle_request(void)
+{
+       struct mtsp_syscall sc;
+       struct mtsp_syscall_generic generic;
+       struct mtsp_syscall_ret ret;
+       struct kspd_notifications *n;
+       struct timeval tv;
+       struct timezone tz;
+       int cmd;
+
+       char *vcwd;
+       mm_segment_t old_fs;
+       int size;
+
+       ret.retval = -1;
+
+       if (!rtlx_read(RTLX_CHANNEL_SYSIO, &sc, sizeof(struct mtsp_syscall), 0)) {
+               printk(KERN_ERR "Expected request but nothing to read\n");
+               return;
+       }
+
+       size = sc.size;
+
+       if (size) {
+               if (!rtlx_read(RTLX_CHANNEL_SYSIO, &generic, size, 0)) {
+                       printk(KERN_ERR "Expected request but nothing to read\n");
+                       return;
+               }
+       }
+
+       /* Run the syscall at the priviledge of the user who loaded the
+          SP program */
+
+       if (vpe_getuid(SP_VPE))
+               sp_setfsuidgid( vpe_getuid(SP_VPE), vpe_getgid(SP_VPE));
+
+       switch (sc.cmd) {
+       /* needs the flags argument translating from SDE kit to
+          linux */
+       case MTSP_SYSCALL_PIPEFREQ:
+               ret.retval = cpu_khz * 1000;
+               ret.errno = 0;
+               break;
+
+       case MTSP_SYSCALL_GETTOD:
+               memset(&tz, 0, sizeof(tz));
+               if ((ret.retval = sp_syscall(__NR_gettimeofday, (int)&tv,
+                                            (int)&tz, 0,0)) == 0)
+               ret.retval = tv.tv_sec;
+
+               ret.errno = errno;
+               break;
+
+       case MTSP_SYSCALL_EXIT:
+               list_for_each_entry(n, &kspd_notifylist, list)
+                       n->kspd_sp_exit(SP_VPE);
+               sp_stopping = 1;
+
+               printk(KERN_DEBUG "KSPD got exit syscall from SP exitcode %d\n",
+                      generic.arg0);
+               break;
+
+       case MTSP_SYSCALL_OPEN:
+               generic.arg1 = translate_open_flags(generic.arg1);
+
+               vcwd = vpe_getcwd(SP_VPE);
+
+               /* change to the cwd of the process that loaded the SP program */
+               old_fs = get_fs();
+               set_fs(KERNEL_DS);
+               sys_chdir(vcwd);
+               set_fs(old_fs);
+
+               sc.cmd = __NR_open;
+
+               /* fall through */
+
+       default:
+               if ((sc.cmd >= __NR_Linux) &&
+                   (sc.cmd <= (__NR_Linux +  __NR_Linux_syscalls)) )
+                       cmd = sc.cmd;
+               else
+                       cmd = translate_syscall_command(sc.cmd);
+
+               if (cmd >= 0) {
+                       ret.retval = sp_syscall(cmd, generic.arg0, generic.arg1,
+                                               generic.arg2, generic.arg3);
+                       ret.errno = errno;
+               } else
+                       printk(KERN_WARNING
+                              "KSPD: Unknown SP syscall number %d\n", sc.cmd);
+               break;
+       } /* switch */
+
+       if (vpe_getuid(SP_VPE))
+               sp_setfsuidgid( 0, 0);
+
+       if ((rtlx_write(RTLX_CHANNEL_SYSIO, &ret, sizeof(struct mtsp_syscall_ret), 0))
+           < sizeof(struct mtsp_syscall_ret))
+               printk("KSPD: sp_work_handle_request failed to send to SP\n");
+}
+
+static void sp_cleanup(void)
+{
+       struct files_struct *files = current->files;
+       int i, j;
+       struct fdtable *fdt;
+
+       j = 0;
+
+       /*
+        * It is safe to dereference the fd table without RCU or
+        * ->file_lock
+        */
+       fdt = files_fdtable(files);
+       for (;;) {
+               unsigned long set;
+               i = j * __NFDBITS;
+               if (i >= fdt->max_fdset || i >= fdt->max_fds)
+                       break;
+               set = fdt->open_fds->fds_bits[j++];
+               while (set) {
+                       if (set & 1) {
+                               struct file * file = xchg(&fdt->fd[i], NULL);
+                               if (file)
+                                       filp_close(file, files);
+                       }
+                       i++;
+                       set >>= 1;
+               }
+       }
+}
+
+static int channel_open = 0;
+
+/* the work handler */
+static void sp_work(void *data)
+{
+       if (!channel_open) {
+               if( rtlx_open(RTLX_CHANNEL_SYSIO, 1) != 0) {
+                       printk("KSPD: unable to open sp channel\n");
+                       sp_stopping = 1;
+               } else {
+                       channel_open++;
+                       printk(KERN_DEBUG "KSPD: SP channel opened\n");
+               }
+       } else {
+               /* wait for some data, allow it to sleep */
+               rtlx_read_poll(RTLX_CHANNEL_SYSIO, 1);
+
+               /* Check we haven't been woken because we are stopping */
+               if (!sp_stopping)
+                       sp_work_handle_request();
+       }
+
+       if (!sp_stopping)
+               queue_work(workqueue, &work);
+       else
+               sp_cleanup();
+}
+
+static void startwork(int vpe)
+{
+       sp_stopping = channel_open = 0;
+
+       if (workqueue == NULL) {
+               if ((workqueue = create_singlethread_workqueue("kspd")) == NULL) {
+                       printk(KERN_ERR "unable to start kspd\n");
+                       return;
+               }
+
+               INIT_WORK(&work, sp_work, NULL);
+               queue_work(workqueue, &work);
+       } else
+               queue_work(workqueue, &work);
+
+}
+
+static void stopwork(int vpe)
+{
+       sp_stopping = 1;
+
+       printk(KERN_DEBUG "KSPD: SP stopping\n");
+}
+
+void kspd_notify(struct kspd_notifications *notify)
+{
+       list_add(&notify->list, &kspd_notifylist);
+}
+
+static struct vpe_notifications notify;
+static int kspd_module_init(void)
+{
+       INIT_LIST_HEAD(&kspd_notifylist);
+
+       notify.start = startwork;
+       notify.stop = stopwork;
+       vpe_notify(SP_VPE, &notify);
+
+       return 0;
+}
+
+static void kspd_module_exit(void)
+{
+
+}
+
+module_init(kspd_module_init);
+module_exit(kspd_module_exit);
+
+MODULE_DESCRIPTION("MIPS KSPD");
+MODULE_AUTHOR("Elizabeth Oldham, MIPS Technologies, Inc.");
+MODULE_LICENSE("GPL");
index 3f40c37a9ee670252a56abf6066ad3b0cbfaec0d..7c953bcc5f6a076413ab740ec53cc925a723b5bc 100644 (file)
@@ -1182,6 +1182,16 @@ asmlinkage ssize_t sys32_readahead(int fd, u32 pad0, u64 a2, u64 a3,
        return sys_readahead(fd, merge_64(a2, a3), count);
 }
 
+asmlinkage long sys32_sync_file_range(int fd, int __pad,
+       unsigned long a2, unsigned long a3,
+       unsigned long a4, unsigned long a5,
+       int flags)
+{
+       return sys_sync_file_range(fd,
+                       merge_64(a2, a3), merge_64(a4, a5),
+                       flags);
+}
+
 /* Argument list sizes for sys_socketcall */
 #define AL(x) ((x) * sizeof(unsigned int))
 static unsigned char socketcall_nargs[18]={AL(0),AL(3),AL(3),AL(3),AL(2),AL(3),
diff --git a/arch/mips/kernel/mips-mt.c b/arch/mips/kernel/mips-mt.c
new file mode 100644 (file)
index 0000000..02237a6
--- /dev/null
@@ -0,0 +1,449 @@
+/*
+ * General MIPS MT support routines, usable in AP/SP, SMVP, or SMTC kernels
+ * Copyright (C) 2005 Mips Technologies, Inc
+ */
+
+#include <linux/kernel.h>
+#include <linux/sched.h>
+#include <linux/cpumask.h>
+#include <linux/interrupt.h>
+
+#include <asm/cpu.h>
+#include <asm/processor.h>
+#include <asm/atomic.h>
+#include <asm/system.h>
+#include <asm/hardirq.h>
+#include <asm/mmu_context.h>
+#include <asm/smp.h>
+#include <asm/mipsmtregs.h>
+#include <asm/r4kcache.h>
+#include <asm/cacheflush.h>
+
+/*
+ * CPU mask used to set process affinity for MT VPEs/TCs with FPUs
+ */
+
+cpumask_t mt_fpu_cpumask;
+
+#ifdef CONFIG_MIPS_MT_FPAFF
+
+#include <linux/cpu.h>
+#include <linux/delay.h>
+#include <asm/uaccess.h>
+
+unsigned long mt_fpemul_threshold = 0;
+
+/*
+ * Replacement functions for the sys_sched_setaffinity() and
+ * sys_sched_getaffinity() system calls, so that we can integrate
+ * FPU affinity with the user's requested processor affinity.
+ * This code is 98% identical with the sys_sched_setaffinity()
+ * and sys_sched_getaffinity() system calls, and should be
+ * updated when kernel/sched.c changes.
+ */
+
+/*
+ * find_process_by_pid - find a process with a matching PID value.
+ * used in sys_sched_set/getaffinity() in kernel/sched.c, so
+ * cloned here.
+ */
+static inline task_t *find_process_by_pid(pid_t pid)
+{
+       return pid ? find_task_by_pid(pid) : current;
+}
+
+
+/*
+ * mipsmt_sys_sched_setaffinity - set the cpu affinity of a process
+ */
+asmlinkage long mipsmt_sys_sched_setaffinity(pid_t pid, unsigned int len,
+                                     unsigned long __user *user_mask_ptr)
+{
+       cpumask_t new_mask;
+       cpumask_t effective_mask;
+       int retval;
+       task_t *p;
+
+       if (len < sizeof(new_mask))
+               return -EINVAL;
+
+       if (copy_from_user(&new_mask, user_mask_ptr, sizeof(new_mask)))
+               return -EFAULT;
+
+       lock_cpu_hotplug();
+       read_lock(&tasklist_lock);
+
+       p = find_process_by_pid(pid);
+       if (!p) {
+               read_unlock(&tasklist_lock);
+               unlock_cpu_hotplug();
+               return -ESRCH;
+       }
+
+       /*
+        * It is not safe to call set_cpus_allowed with the
+        * tasklist_lock held.  We will bump the task_struct's
+        * usage count and drop tasklist_lock before invoking
+        * set_cpus_allowed.
+        */
+       get_task_struct(p);
+
+       retval = -EPERM;
+       if ((current->euid != p->euid) && (current->euid != p->uid) &&
+                       !capable(CAP_SYS_NICE)) {
+               read_unlock(&tasklist_lock);
+               goto out_unlock;
+       }
+
+       /* Record new user-specified CPU set for future reference */
+       p->thread.user_cpus_allowed = new_mask;
+
+       /* Unlock the task list */
+       read_unlock(&tasklist_lock);
+
+       /* Compute new global allowed CPU set if necessary */
+       if( (p->thread.mflags & MF_FPUBOUND)
+       && cpus_intersects(new_mask, mt_fpu_cpumask)) {
+               cpus_and(effective_mask, new_mask, mt_fpu_cpumask);
+               retval = set_cpus_allowed(p, effective_mask);
+       } else {
+               p->thread.mflags &= ~MF_FPUBOUND;
+               retval = set_cpus_allowed(p, new_mask);
+       }
+
+
+out_unlock:
+       put_task_struct(p);
+       unlock_cpu_hotplug();
+       return retval;
+}
+
+/*
+ * mipsmt_sys_sched_getaffinity - get the cpu affinity of a process
+ */
+asmlinkage long mipsmt_sys_sched_getaffinity(pid_t pid, unsigned int len,
+                                     unsigned long __user *user_mask_ptr)
+{
+       unsigned int real_len;
+       cpumask_t mask;
+       int retval;
+       task_t *p;
+
+       real_len = sizeof(mask);
+       if (len < real_len)
+               return -EINVAL;
+
+       lock_cpu_hotplug();
+       read_lock(&tasklist_lock);
+
+       retval = -ESRCH;
+       p = find_process_by_pid(pid);
+       if (!p)
+               goto out_unlock;
+
+       retval = 0;
+
+       cpus_and(mask, p->thread.user_cpus_allowed, cpu_possible_map);
+
+out_unlock:
+       read_unlock(&tasklist_lock);
+       unlock_cpu_hotplug();
+       if (retval)
+               return retval;
+       if (copy_to_user(user_mask_ptr, &mask, real_len))
+               return -EFAULT;
+       return real_len;
+}
+
+#endif /* CONFIG_MIPS_MT_FPAFF */
+
+/*
+ * Dump new MIPS MT state for the core. Does not leave TCs halted.
+ * Takes an argument which taken to be a pre-call MVPControl value.
+ */
+
+void mips_mt_regdump(unsigned long mvpctl)
+{
+       unsigned long flags;
+       unsigned long vpflags;
+       unsigned long mvpconf0;
+       int nvpe;
+       int ntc;
+       int i;
+       int tc;
+       unsigned long haltval;
+       unsigned long tcstatval;
+#ifdef CONFIG_MIPS_MT_SMTC
+       void smtc_soft_dump(void);
+#endif /* CONFIG_MIPT_MT_SMTC */
+
+       local_irq_save(flags);
+       vpflags = dvpe();
+       printk("=== MIPS MT State Dump ===\n");
+       printk("-- Global State --\n");
+       printk("   MVPControl Passed: %08lx\n", mvpctl);
+       printk("   MVPControl Read: %08lx\n", vpflags);
+       printk("   MVPConf0 : %08lx\n", (mvpconf0 = read_c0_mvpconf0()));
+       nvpe = ((mvpconf0 & MVPCONF0_PVPE) >> MVPCONF0_PVPE_SHIFT) + 1;
+       ntc = ((mvpconf0 & MVPCONF0_PTC) >> MVPCONF0_PTC_SHIFT) + 1;
+       printk("-- per-VPE State --\n");
+       for(i = 0; i < nvpe; i++) {
+           for(tc = 0; tc < ntc; tc++) {
+                       settc(tc);
+               if((read_tc_c0_tcbind() & TCBIND_CURVPE) == i) {
+                   printk("  VPE %d\n", i);
+                   printk("   VPEControl : %08lx\n", read_vpe_c0_vpecontrol());
+                   printk("   VPEConf0 : %08lx\n", read_vpe_c0_vpeconf0());
+                   printk("   VPE%d.Status : %08lx\n",
+                               i, read_vpe_c0_status());
+                   printk("   VPE%d.EPC : %08lx\n", i, read_vpe_c0_epc());
+                   printk("   VPE%d.Cause : %08lx\n", i, read_vpe_c0_cause());
+                   printk("   VPE%d.Config7 : %08lx\n",
+                               i, read_vpe_c0_config7());
+                   break; /* Next VPE */
+               }
+           }
+       }
+       printk("-- per-TC State --\n");
+       for(tc = 0; tc < ntc; tc++) {
+               settc(tc);
+               if(read_tc_c0_tcbind() == read_c0_tcbind()) {
+                       /* Are we dumping ourself?  */
+                       haltval = 0; /* Then we're not halted, and mustn't be */
+                       tcstatval = flags; /* And pre-dump TCStatus is flags */
+                       printk("  TC %d (current TC with VPE EPC above)\n", tc);
+               } else {
+                       haltval = read_tc_c0_tchalt();
+                       write_tc_c0_tchalt(1);
+                       tcstatval = read_tc_c0_tcstatus();
+                       printk("  TC %d\n", tc);
+               }
+               printk("   TCStatus : %08lx\n", tcstatval);
+               printk("   TCBind : %08lx\n", read_tc_c0_tcbind());
+               printk("   TCRestart : %08lx\n", read_tc_c0_tcrestart());
+               printk("   TCHalt : %08lx\n", haltval);
+               printk("   TCContext : %08lx\n", read_tc_c0_tccontext());
+               if (!haltval)
+                       write_tc_c0_tchalt(0);
+       }
+#ifdef CONFIG_MIPS_MT_SMTC
+       smtc_soft_dump();
+#endif /* CONFIG_MIPT_MT_SMTC */
+       printk("===========================\n");
+       evpe(vpflags);
+       local_irq_restore(flags);
+}
+
+static int mt_opt_norps = 0;
+static int mt_opt_rpsctl = -1;
+static int mt_opt_nblsu = -1;
+static int mt_opt_forceconfig7 = 0;
+static int mt_opt_config7 = -1;
+
+static int __init rps_disable(char *s)
+{
+       mt_opt_norps = 1;
+       return 1;
+}
+__setup("norps", rps_disable);
+
+static int __init rpsctl_set(char *str)
+{
+       get_option(&str, &mt_opt_rpsctl);
+       return 1;
+}
+__setup("rpsctl=", rpsctl_set);
+
+static int __init nblsu_set(char *str)
+{
+       get_option(&str, &mt_opt_nblsu);
+       return 1;
+}
+__setup("nblsu=", nblsu_set);
+
+static int __init config7_set(char *str)
+{
+       get_option(&str, &mt_opt_config7);
+       mt_opt_forceconfig7 = 1;
+       return 1;
+}
+__setup("config7=", config7_set);
+
+/* Experimental cache flush control parameters that should go away some day */
+int mt_protiflush = 0;
+int mt_protdflush = 0;
+int mt_n_iflushes = 1;
+int mt_n_dflushes = 1;
+
+static int __init set_protiflush(char *s)
+{
+       mt_protiflush = 1;
+       return 1;
+}
+__setup("protiflush", set_protiflush);
+
+static int __init set_protdflush(char *s)
+{
+       mt_protdflush = 1;
+       return 1;
+}
+__setup("protdflush", set_protdflush);
+
+static int __init niflush(char *s)
+{
+       get_option(&s, &mt_n_iflushes);
+       return 1;
+}
+__setup("niflush=", niflush);
+
+static int __init ndflush(char *s)
+{
+       get_option(&s, &mt_n_dflushes);
+       return 1;
+}
+__setup("ndflush=", ndflush);
+#ifdef CONFIG_MIPS_MT_FPAFF
+static int fpaff_threshold = -1;
+
+static int __init fpaff_thresh(char *str)
+{
+       get_option(&str, &fpaff_threshold);
+       return 1;
+}
+
+__setup("fpaff=", fpaff_thresh);
+#endif /* CONFIG_MIPS_MT_FPAFF */
+
+static unsigned int itc_base = 0;
+
+static int __init set_itc_base(char *str)
+{
+       get_option(&str, &itc_base);
+       return 1;
+}
+
+__setup("itcbase=", set_itc_base);
+
+void mips_mt_set_cpuoptions(void)
+{
+       unsigned int oconfig7 = read_c0_config7();
+       unsigned int nconfig7 = oconfig7;
+
+       if (mt_opt_norps) {
+               printk("\"norps\" option deprectated: use \"rpsctl=\"\n");
+       }
+       if (mt_opt_rpsctl >= 0) {
+               printk("34K return prediction stack override set to %d.\n",
+                       mt_opt_rpsctl);
+               if (mt_opt_rpsctl)
+                       nconfig7 |= (1 << 2);
+               else
+                       nconfig7 &= ~(1 << 2);
+       }
+       if (mt_opt_nblsu >= 0) {
+               printk("34K ALU/LSU sync override set to %d.\n", mt_opt_nblsu);
+               if (mt_opt_nblsu)
+                       nconfig7 |= (1 << 5);
+               else
+                       nconfig7 &= ~(1 << 5);
+       }
+       if (mt_opt_forceconfig7) {
+               printk("CP0.Config7 forced to 0x%08x.\n", mt_opt_config7);
+               nconfig7 = mt_opt_config7;
+       }
+       if (oconfig7 != nconfig7) {
+               __asm__ __volatile("sync");
+               write_c0_config7(nconfig7);
+               ehb ();
+               printk("Config7: 0x%08x\n", read_c0_config7());
+       }
+
+       /* Report Cache management debug options */
+       if (mt_protiflush)
+               printk("I-cache flushes single-threaded\n");
+       if (mt_protdflush)
+               printk("D-cache flushes single-threaded\n");
+       if (mt_n_iflushes != 1)
+               printk("I-Cache Flushes Repeated %d times\n", mt_n_iflushes);
+       if (mt_n_dflushes != 1)
+               printk("D-Cache Flushes Repeated %d times\n", mt_n_dflushes);
+
+#ifdef CONFIG_MIPS_MT_FPAFF
+       /* FPU Use Factor empirically derived from experiments on 34K */
+#define FPUSEFACTOR 333
+
+       if (fpaff_threshold >= 0) {
+               mt_fpemul_threshold = fpaff_threshold;
+       } else {
+               mt_fpemul_threshold =
+                       (FPUSEFACTOR * (loops_per_jiffy/(500000/HZ))) / HZ;
+       }
+       printk("FPU Affinity set after %ld emulations\n",
+                       mt_fpemul_threshold);
+#endif /* CONFIG_MIPS_MT_FPAFF */
+
+       if (itc_base != 0) {
+               /*
+                * Configure ITC mapping.  This code is very
+                * specific to the 34K core family, which uses
+                * a special mode bit ("ITC") in the ErrCtl
+                * register to enable access to ITC control
+                * registers via cache "tag" operations.
+                */
+               unsigned long ectlval;
+               unsigned long itcblkgrn;
+
+               /* ErrCtl register is known as "ecc" to Linux */
+               ectlval = read_c0_ecc();
+               write_c0_ecc(ectlval | (0x1 << 26));
+               ehb();
+#define INDEX_0 (0x80000000)
+#define INDEX_8 (0x80000008)
+               /* Read "cache tag" for Dcache pseudo-index 8 */
+               cache_op(Index_Load_Tag_D, INDEX_8);
+               ehb();
+               itcblkgrn = read_c0_dtaglo();
+               itcblkgrn &= 0xfffe0000;
+               /* Set for 128 byte pitch of ITC cells */
+               itcblkgrn |= 0x00000c00;
+               /* Stage in Tag register */
+               write_c0_dtaglo(itcblkgrn);
+               ehb();
+               /* Write out to ITU with CACHE op */
+               cache_op(Index_Store_Tag_D, INDEX_8);
+               /* Now set base address, and turn ITC on with 0x1 bit */
+               write_c0_dtaglo((itc_base & 0xfffffc00) | 0x1 );
+               ehb();
+               /* Write out to ITU with CACHE op */
+               cache_op(Index_Store_Tag_D, INDEX_0);
+               write_c0_ecc(ectlval);
+               ehb();
+               printk("Mapped %ld ITC cells starting at 0x%08x\n",
+                       ((itcblkgrn & 0x7fe00000) >> 20), itc_base);
+       }
+}
+
+/*
+ * Function to protect cache flushes from concurrent execution
+ * depends on MP software model chosen.
+ */
+
+void mt_cflush_lockdown(void)
+{
+#ifdef CONFIG_MIPS_MT_SMTC
+       void smtc_cflush_lockdown(void);
+
+       smtc_cflush_lockdown();
+#endif /* CONFIG_MIPS_MT_SMTC */
+       /* FILL IN VSMP and AP/SP VERSIONS HERE */
+}
+
+void mt_cflush_release(void)
+{
+#ifdef CONFIG_MIPS_MT_SMTC
+       void smtc_cflush_release(void);
+
+       smtc_cflush_release();
+#endif /* CONFIG_MIPS_MT_SMTC */
+       /* FILL IN VSMP and AP/SP VERSIONS HERE */
+}
index 86e42c633f73a60e95a939a7433b18b89118dd1b..0a71a4c337161c5304e86730769c82fffcb1e2cf 100644 (file)
@@ -28,22 +28,9 @@ extern long __strnlen_user_asm(const char *s);
 /*
  * String functions
  */
-EXPORT_SYMBOL(memchr);
-EXPORT_SYMBOL(memcmp);
 EXPORT_SYMBOL(memset);
 EXPORT_SYMBOL(memcpy);
 EXPORT_SYMBOL(memmove);
-EXPORT_SYMBOL(strcat);
-EXPORT_SYMBOL(strchr);
-#ifdef CONFIG_64BIT
-EXPORT_SYMBOL(strncmp);
-#endif
-EXPORT_SYMBOL(strlen);
-EXPORT_SYMBOL(strpbrk);
-EXPORT_SYMBOL(strncat);
-EXPORT_SYMBOL(strnlen);
-EXPORT_SYMBOL(strrchr);
-EXPORT_SYMBOL(strstr);
 
 EXPORT_SYMBOL(kernel_thread);
 
@@ -62,6 +49,3 @@ EXPORT_SYMBOL(__strnlen_user_asm);
 EXPORT_SYMBOL(csum_partial);
 
 EXPORT_SYMBOL(invalid_pte_table);
-#ifdef CONFIG_GENERIC_IRQ_PROBE
-EXPORT_SYMBOL(probe_irq_mask);
-#endif
index c66db5e5ab624f9c2b0d3e7256539c6f0932cb97..199a06e873c6ab2e06166234a82d42fa1d3747e7 100644 (file)
 #include <asm/elf.h>
 #include <asm/isadep.h>
 #include <asm/inst.h>
+#ifdef CONFIG_MIPS_MT_SMTC
+#include <asm/mipsmtregs.h>
+extern void smtc_idle_loop_hook(void);
+#endif /* CONFIG_MIPS_MT_SMTC */
 
 /*
  * The idle thread. There's no useful work to be done, so just try to conserve
@@ -51,9 +55,13 @@ ATTRIB_NORET void cpu_idle(void)
 {
        /* endless idle loop with no priority at all */
        while (1) {
-               while (!need_resched())
+               while (!need_resched()) {
+#ifdef CONFIG_MIPS_MT_SMTC
+                       smtc_idle_loop_hook();
+#endif /* CONFIG_MIPS_MT_SMTC */
                        if (cpu_wait)
                                (*cpu_wait)();
+               }
                preempt_enable_no_resched();
                schedule();
                preempt_disable();
@@ -177,6 +185,17 @@ int copy_thread(int nr, unsigned long clone_flags, unsigned long usp,
        childregs->cp0_status &= ~(ST0_CU2|ST0_CU1);
        clear_tsk_thread_flag(p, TIF_USEDFPU);
 
+#ifdef CONFIG_MIPS_MT_FPAFF
+       /*
+        * FPU affinity support is cleaner if we track the
+        * user-visible CPU affinity from the very beginning.
+        * The generic cpus_allowed mask will already have
+        * been copied from the parent before copy_thread
+        * is invoked.
+        */
+       p->thread.user_cpus_allowed = p->cpus_allowed;
+#endif /* CONFIG_MIPS_MT_FPAFF */
+
        if (clone_flags & CLONE_SETTLS)
                ti->tp_value = regs->regs[7];
 
index f838b36cc765bcbc9ad544701aec14e2ff29c278..f3106d0771b0707ba21a767c32ed852530bc78d9 100644 (file)
@@ -248,10 +248,20 @@ long arch_ptrace(struct task_struct *child, long request, long addr, long data)
                        break;
                case FPC_EIR: { /* implementation / version register */
                        unsigned int flags;
+#ifdef CONFIG_MIPS_MT_SMTC
+                       unsigned int irqflags;
+                       unsigned int mtflags;
+#endif /* CONFIG_MIPS_MT_SMTC */
 
                        if (!cpu_has_fpu)
                                break;
 
+#ifdef CONFIG_MIPS_MT_SMTC
+                       /* Read-modify-write of Status must be atomic */
+                       local_irq_save(irqflags);
+                       mtflags = dmt();
+#endif /* CONFIG_MIPS_MT_SMTC */
+
                        preempt_disable();
                        if (cpu_has_mipsmt) {
                                unsigned int vpflags = dvpe();
@@ -266,6 +276,10 @@ long arch_ptrace(struct task_struct *child, long request, long addr, long data)
                                __asm__ __volatile__("cfc1\t%0,$0": "=r" (tmp));
                                write_c0_status(flags);
                        }
+#ifdef CONFIG_MIPS_MT_SMTC
+                       emt(mtflags);
+                       local_irq_restore(irqflags);
+#endif /* CONFIG_MIPS_MT_SMTC */
                        preempt_enable();
                        break;
                }
index 0d5cf97af727e3c39fd6c3e3fa965979c2a517bf..8704dc0496ea7f2427b4fd111dbbb54397955b0f 100644 (file)
@@ -173,12 +173,22 @@ asmlinkage int sys32_ptrace(int request, int pid, int addr, int data)
                        break;
                case FPC_EIR: { /* implementation / version register */
                        unsigned int flags;
+#ifdef CONFIG_MIPS_MT_SMTC
+                       unsigned int irqflags;
+                       unsigned int mtflags;
+#endif /* CONFIG_MIPS_MT_SMTC */
 
                        if (!cpu_has_fpu) {
                                tmp = 0;
                                break;
                        }
 
+#ifdef CONFIG_MIPS_MT_SMTC
+                       /* Read-modify-write of Status must be atomic */
+                       local_irq_save(irqflags);
+                       mtflags = dmt();
+#endif /* CONFIG_MIPS_MT_SMTC */
+
                        preempt_disable();
                        if (cpu_has_mipsmt) {
                                unsigned int vpflags = dvpe();
@@ -193,6 +203,10 @@ asmlinkage int sys32_ptrace(int request, int pid, int addr, int data)
                                __asm__ __volatile__("cfc1\t%0,$0": "=r" (tmp));
                                write_c0_status(flags);
                        }
+#ifdef CONFIG_MIPS_MT_SMTC
+                       emt(mtflags);
+                       local_irq_restore(irqflags);
+#endif /* CONFIG_MIPS_MT_SMTC */
                        preempt_enable();
                        break;
                }
index d2afbd19a9c8a0c013b4170008d55a18d701e61c..0b1b54acee9ffeb538a6667da285ee6c82a54777 100644 (file)
 
        PTR_ADDIU       t0, $28, _THREAD_SIZE - 32
        set_saved_sp    t0, t1, t2
-
+#ifdef CONFIG_MIPS_MT_SMTC
+       /* Read-modify-writes of Status must be atomic on a VPE */
+       mfc0    t2, CP0_TCSTATUS
+       ori     t1, t2, TCSTATUS_IXMT
+       mtc0    t1, CP0_TCSTATUS
+       andi    t2, t2, TCSTATUS_IXMT
+       ehb
+       DMT     8                               # dmt   t0
+       move    t1,ra
+       jal     mips_ihb
+       move    ra,t1
+#endif /* CONFIG_MIPS_MT_SMTC */
        mfc0    t1, CP0_STATUS          /* Do we really need this? */
        li      a3, 0xff01
        and     t1, a3
        and     a2, a3
        or      a2, t1
        mtc0    a2, CP0_STATUS
+#ifdef CONFIG_MIPS_MT_SMTC
+       ehb
+       andi    t0, t0, VPECONTROL_TE
+       beqz    t0, 1f
+       emt
+1:
+       mfc0    t1, CP0_TCSTATUS
+       xori    t1, t1, TCSTATUS_IXMT
+       or      t1, t1, t2
+       mtc0    t1, CP0_TCSTATUS
+       ehb
+#endif /* CONFIG_MIPS_MT_SMTC */
        move    v0, a0
        jr      ra
        END(resume)
@@ -131,10 +154,19 @@ LEAF(_restore_fp)
 #define FPU_DEFAULT  0x00000000
 
 LEAF(_init_fpu)
+#ifdef CONFIG_MIPS_MT_SMTC
+       /* Rather than manipulate per-VPE Status, set per-TC bit in TCStatus */
+       mfc0    t0, CP0_TCSTATUS
+       /* Bit position is the same for Status, TCStatus */
+       li      t1, ST0_CU1
+       or      t0, t1
+       mtc0    t0, CP0_TCSTATUS
+#else /* Normal MIPS CU1 enable */
        mfc0    t0, CP0_STATUS
        li      t1, ST0_CU1
        or      t0, t1
        mtc0    t0, CP0_STATUS
+#endif /* CONFIG_MIPS_MT_SMTC */
        fpu_enable_hazard
 
        li      t1, FPU_DEFAULT
index 986a9cf230673010e6f9ae678798d74de0a51474..6179805af9f06954a26786273634aedd2b67277d 100644 (file)
 #include <linux/module.h>
 #include <linux/fs.h>
 #include <linux/init.h>
+#include <asm/uaccess.h>
+#include <linux/slab.h>
+#include <linux/list.h>
+#include <linux/vmalloc.h>
+#include <linux/elf.h>
+#include <linux/seq_file.h>
+#include <linux/syscalls.h>
+#include <linux/moduleloader.h>
 #include <linux/interrupt.h>
-#include <linux/irq.h>
 #include <linux/poll.h>
 #include <linux/sched.h>
 #include <linux/wait.h>
-
 #include <asm/mipsmtregs.h>
-#include <asm/bitops.h>
+#include <asm/cacheflush.h>
+#include <asm/atomic.h>
 #include <asm/cpu.h>
 #include <asm/processor.h>
+#include <asm/system.h>
+#include <asm/vpe.h>
 #include <asm/rtlx.h>
-#include <asm/uaccess.h>
 
 #define RTLX_TARG_VPE 1
 
 static struct rtlx_info *rtlx;
 static int major;
 static char module_name[] = "rtlx";
-static struct irqaction irq;
-static int irq_num;
-
-static inline int spacefree(int read, int write, int size)
-{
-       if (read == write) {
-               /*
-                * never fill the buffer completely, so indexes are always
-                * equal if empty and only empty, or !equal if data available
-                */
-               return size - 1;
-       }
-
-       return ((read + size - write) % size) - 1;
-}
 
 static struct chan_waitqueues {
        wait_queue_head_t rt_queue;
        wait_queue_head_t lx_queue;
+       int in_open;
 } channel_wqs[RTLX_CHANNELS];
 
+static struct irqaction irq;
+static int irq_num;
+static struct vpe_notifications notify;
+static int sp_stopping = 0;
+
 extern void *vpe_get_shared(int index);
 
 static void rtlx_dispatch(struct pt_regs *regs)
@@ -67,174 +66,298 @@ static void rtlx_dispatch(struct pt_regs *regs)
        do_IRQ(MIPSCPU_INT_BASE + MIPS_CPU_RTLX_IRQ, regs);
 }
 
+
+/* Interrupt handler may be called before rtlx_init has otherwise had
+   a chance to run.
+*/
 static irqreturn_t rtlx_interrupt(int irq, void *dev_id, struct pt_regs *regs)
 {
        int i;
 
        for (i = 0; i < RTLX_CHANNELS; i++) {
-               struct rtlx_channel *chan = &rtlx->channel[i];
-
-               if (chan->lx_read != chan->lx_write)
-                       wake_up_interruptible(&channel_wqs[i].lx_queue);
+                       wake_up(&channel_wqs[i].lx_queue);
+                       wake_up(&channel_wqs[i].rt_queue);
        }
 
        return IRQ_HANDLED;
 }
 
-/* call when we have the address of the shared structure from the SP side. */
-static int rtlx_init(struct rtlx_info *rtlxi)
+static __attribute_used__ void dump_rtlx(void)
 {
        int i;
 
-       if (rtlxi->id != RTLX_ID) {
-               printk(KERN_WARNING "no valid RTLX id at 0x%p\n", rtlxi);
-               return -ENOEXEC;
-       }
+       printk("id 0x%lx state %d\n", rtlx->id, rtlx->state);
 
-       /* initialise the wait queues */
        for (i = 0; i < RTLX_CHANNELS; i++) {
-               init_waitqueue_head(&channel_wqs[i].rt_queue);
-               init_waitqueue_head(&channel_wqs[i].lx_queue);
-       }
+               struct rtlx_channel *chan = &rtlx->channel[i];
 
-       /* set up for interrupt handling */
-       memset(&irq, 0, sizeof(struct irqaction));
+               printk(" rt_state %d lx_state %d buffer_size %d\n",
+                      chan->rt_state, chan->lx_state, chan->buffer_size);
 
-       if (cpu_has_vint)
-               set_vi_handler(MIPS_CPU_RTLX_IRQ, rtlx_dispatch);
+               printk(" rt_read %d rt_write %d\n",
+                      chan->rt_read, chan->rt_write);
 
-       irq_num = MIPSCPU_INT_BASE + MIPS_CPU_RTLX_IRQ;
-       irq.handler = rtlx_interrupt;
-       irq.flags = SA_INTERRUPT;
-       irq.name = "RTLX";
-       irq.dev_id = rtlx;
-       setup_irq(irq_num, &irq);
+               printk(" lx_read %d lx_write %d\n",
+                      chan->lx_read, chan->lx_write);
+
+               printk(" rt_buffer <%s>\n", chan->rt_buffer);
+               printk(" lx_buffer <%s>\n", chan->lx_buffer);
+       }
+}
+
+/* call when we have the address of the shared structure from the SP side. */
+static int rtlx_init(struct rtlx_info *rtlxi)
+{
+       if (rtlxi->id != RTLX_ID) {
+               printk(KERN_ERR "no valid RTLX id at 0x%p 0x%x\n", rtlxi, rtlxi->id);
+               return -ENOEXEC;
+       }
 
        rtlx = rtlxi;
 
        return 0;
 }
 
-/* only allow one open process at a time to open each channel */
-static int rtlx_open(struct inode *inode, struct file *filp)
+/* notifications */
+static void starting(int vpe)
 {
-       int minor, ret;
+       int i;
+       sp_stopping = 0;
+
+       /* force a reload of rtlx */
+       rtlx=NULL;
+
+       /* wake up any sleeping rtlx_open's */
+       for (i = 0; i < RTLX_CHANNELS; i++)
+               wake_up_interruptible(&channel_wqs[i].lx_queue);
+}
+
+static void stopping(int vpe)
+{
+       int i;
+
+       sp_stopping = 1;
+       for (i = 0; i < RTLX_CHANNELS; i++)
+               wake_up_interruptible(&channel_wqs[i].lx_queue);
+}
+
+
+int rtlx_open(int index, int can_sleep)
+{
+       int ret;
        struct rtlx_channel *chan;
+       volatile struct rtlx_info **p;
 
-       /* assume only 1 device at the mo. */
-       minor = MINOR(inode->i_rdev);
+       if (index >= RTLX_CHANNELS) {
+               printk(KERN_DEBUG "rtlx_open index out of range\n");
+               return -ENOSYS;
+       }
+
+       if (channel_wqs[index].in_open) {
+               printk(KERN_DEBUG "rtlx_open channel %d already opened\n", index);
+               return -EBUSY;
+       }
+
+       channel_wqs[index].in_open++;
 
        if (rtlx == NULL) {
-               struct rtlx_info **p;
                if( (p = vpe_get_shared(RTLX_TARG_VPE)) == NULL) {
-                       printk(KERN_ERR "vpe_get_shared is NULL. "
-                              "Has an SP program been loaded?\n");
-                       return -EFAULT;
+                       if (can_sleep) {
+                               DECLARE_WAITQUEUE(wait, current);
+
+                               /* go to sleep */
+                               add_wait_queue(&channel_wqs[index].lx_queue, &wait);
+
+                               set_current_state(TASK_INTERRUPTIBLE);
+                               while ((p = vpe_get_shared(RTLX_TARG_VPE)) == NULL) {
+                                       schedule();
+                                       set_current_state(TASK_INTERRUPTIBLE);
+                               }
+
+                               set_current_state(TASK_RUNNING);
+                               remove_wait_queue(&channel_wqs[index].lx_queue, &wait);
+
+                               /* back running */
+                       } else {
+                               printk( KERN_DEBUG "No SP program loaded, and device "
+                                       "opened with O_NONBLOCK\n");
+                               channel_wqs[index].in_open = 0;
+                               return -ENOSYS;
+                       }
                }
 
                if (*p == NULL) {
-                       printk(KERN_ERR "vpe_shared %p %p\n", p, *p);
-                       return -EFAULT;
+                       if (can_sleep) {
+                               DECLARE_WAITQUEUE(wait, current);
+
+                               /* go to sleep */
+                               add_wait_queue(&channel_wqs[index].lx_queue, &wait);
+
+                               set_current_state(TASK_INTERRUPTIBLE);
+                               while (*p == NULL) {
+                                       schedule();
+
+                                       /* reset task state to interruptable otherwise
+                                          we'll whizz round here like a very fast loopy
+                                          thing. schedule() appears to return with state
+                                          set to TASK_RUNNING.
+
+                                          If the loaded SP program, for whatever reason,
+                                          doesn't set up the shared structure *p will never
+                                          become true. So whoever connected to either /dev/rt?
+                                          or if it was kspd, will then take up rather a lot of
+                                          processor cycles.
+                                       */
+
+                                       set_current_state(TASK_INTERRUPTIBLE);
+                               }
+
+                               set_current_state(TASK_RUNNING);
+                               remove_wait_queue(&channel_wqs[index].lx_queue, &wait);
+
+                               /* back running */
+                       }
+                       else {
+                               printk(" *vpe_get_shared is NULL. "
+                                      "Has an SP program been loaded?\n");
+                               channel_wqs[index].in_open = 0;
+                               return -ENOSYS;
+                       }
+               }
+
+               if ((unsigned int)*p < KSEG0) {
+                       printk(KERN_WARNING "vpe_get_shared returned an invalid pointer "
+                              "maybe an error code %d\n", (int)*p);
+                       channel_wqs[index].in_open = 0;
+                       return -ENOSYS;
                }
 
-               if ((ret = rtlx_init(*p)) < 0)
-                       return ret;
+               if ((ret = rtlx_init(*p)) < 0) {
+                       channel_wqs[index].in_open = 0;
+                       return ret;
+               }
        }
 
-       chan = &rtlx->channel[minor];
+       chan = &rtlx->channel[index];
 
-       if (test_and_set_bit(RTLX_STATE_OPENED, &chan->lx_state))
-               return -EBUSY;
+       if (chan->lx_state == RTLX_STATE_OPENED) {
+               channel_wqs[index].in_open = 0;
+               return -EBUSY;
+       }
 
+       chan->lx_state = RTLX_STATE_OPENED;
+       channel_wqs[index].in_open = 0;
        return 0;
 }
 
-static int rtlx_release(struct inode *inode, struct file *filp)
+int rtlx_release(int index)
 {
-       int minor = MINOR(inode->i_rdev);
-
-       clear_bit(RTLX_STATE_OPENED, &rtlx->channel[minor].lx_state);
-       smp_mb__after_clear_bit();
-
+       rtlx->channel[index].lx_state = RTLX_STATE_UNUSED;
        return 0;
 }
 
-static unsigned int rtlx_poll(struct file *file, poll_table * wait)
+unsigned int rtlx_read_poll(int index, int can_sleep)
 {
-       int minor;
-       unsigned int mask = 0;
-       struct rtlx_channel *chan;
+       struct rtlx_channel *chan;
 
-       minor = MINOR(file->f_dentry->d_inode->i_rdev);
-       chan = &rtlx->channel[minor];
+       if (rtlx == NULL)
+               return 0;
 
-       poll_wait(file, &channel_wqs[minor].rt_queue, wait);
-       poll_wait(file, &channel_wqs[minor].lx_queue, wait);
+       chan = &rtlx->channel[index];
 
        /* data available to read? */
-       if (chan->lx_read != chan->lx_write)
-               mask |= POLLIN | POLLRDNORM;
+       if (chan->lx_read == chan->lx_write) {
+               if (can_sleep) {
+                       DECLARE_WAITQUEUE(wait, current);
 
-       /* space to write */
-       if (spacefree(chan->rt_read, chan->rt_write, chan->buffer_size))
-               mask |= POLLOUT | POLLWRNORM;
+                       /* go to sleep */
+                       add_wait_queue(&channel_wqs[index].lx_queue, &wait);
 
-       return mask;
+                       set_current_state(TASK_INTERRUPTIBLE);
+                       while (chan->lx_read == chan->lx_write) {
+                               schedule();
+
+                               set_current_state(TASK_INTERRUPTIBLE);
+
+                               if (sp_stopping) {
+                                       set_current_state(TASK_RUNNING);
+                                       remove_wait_queue(&channel_wqs[index].lx_queue, &wait);
+                                       return 0;
+                               }
+                       }
+
+                       set_current_state(TASK_RUNNING);
+                       remove_wait_queue(&channel_wqs[index].lx_queue, &wait);
+
+                       /* back running */
+               }
+               else
+                       return 0;
+       }
+
+       return (chan->lx_write + chan->buffer_size - chan->lx_read)
+              % chan->buffer_size;
 }
 
-static ssize_t rtlx_read(struct file *file, char __user * buffer, size_t count,
-                        loff_t * ppos)
+static inline int write_spacefree(int read, int write, int size)
 {
-       unsigned long failed;
-       size_t fl = 0L;
-       int minor;
-       struct rtlx_channel *lx;
-       DECLARE_WAITQUEUE(wait, current);
+       if (read == write) {
+               /*
+                * Never fill the buffer completely, so indexes are always
+                * equal if empty and only empty, or !equal if data available
+                */
+               return size - 1;
+       }
 
-       minor = MINOR(file->f_dentry->d_inode->i_rdev);
-       lx = &rtlx->channel[minor];
+       return ((read + size - write) % size) - 1;
+}
 
-       /* data available? */
-       if (lx->lx_write == lx->lx_read) {
-               if (file->f_flags & O_NONBLOCK)
-                       return 0;       /* -EAGAIN makes cat whinge */
+unsigned int rtlx_write_poll(int index)
+{
+       struct rtlx_channel *chan = &rtlx->channel[index];
+       return write_spacefree(chan->rt_read, chan->rt_write, chan->buffer_size);
+}
 
-               /* go to sleep */
-               add_wait_queue(&channel_wqs[minor].lx_queue, &wait);
-               set_current_state(TASK_INTERRUPTIBLE);
+static inline void copy_to(void *dst, void *src, size_t count, int user)
+{
+       if (user)
+               copy_to_user(dst, src, count);
+       else
+               memcpy(dst, src, count);
+}
 
-               while (lx->lx_write == lx->lx_read)
-                       schedule();
+static inline void copy_from(void *dst, void *src, size_t count, int user)
+{
+       if (user)
+               copy_from_user(dst, src, count);
+       else
+               memcpy(dst, src, count);
+}
 
-               set_current_state(TASK_RUNNING);
-               remove_wait_queue(&channel_wqs[minor].lx_queue, &wait);
+ssize_t rtlx_read(int index, void *buff, size_t count, int user)
+{
+       size_t fl = 0L;
+       struct rtlx_channel *lx;
 
-               /* back running */
-       }
+       if (rtlx == NULL)
+               return -ENOSYS;
+
+       lx = &rtlx->channel[index];
 
        /* find out how much in total */
        count = min(count,
-                   (size_t)(lx->lx_write + lx->buffer_size - lx->lx_read) % lx->buffer_size);
+                    (size_t)(lx->lx_write + lx->buffer_size - lx->lx_read)
+                    % lx->buffer_size);
 
        /* then how much from the read pointer onwards */
-       fl = min(count, (size_t)lx->buffer_size - lx->lx_read);
+       fl = min( count, (size_t)lx->buffer_size - lx->lx_read);
 
-       failed = copy_to_user (buffer, &lx->lx_buffer[lx->lx_read], fl);
-       if (failed) {
-               count = fl - failed;
-               goto out;
-       }
+       copy_to(buff, &lx->lx_buffer[lx->lx_read], fl, user);
 
        /* and if there is anything left at the beginning of the buffer */
-       if (count - fl) {
-               failed = copy_to_user (buffer + fl, lx->lx_buffer, count - fl);
-               if (failed) {
-                       count -= failed;
-                       goto out;
-               }
-       }
+       if ( count - fl )
+               copy_to (buff + fl, lx->lx_buffer, count - fl, user);
 
-out:
        /* update the index */
        lx->lx_read += count;
        lx->lx_read %= lx->buffer_size;
@@ -242,20 +365,101 @@ out:
        return count;
 }
 
-static ssize_t rtlx_write(struct file *file, const char __user * buffer,
+ssize_t rtlx_write(int index, void *buffer, size_t count, int user)
+{
+       struct rtlx_channel *rt;
+       size_t fl;
+
+       if (rtlx == NULL)
+               return(-ENOSYS);
+
+       rt = &rtlx->channel[index];
+
+       /* total number of bytes to copy */
+       count = min(count,
+                   (size_t)write_spacefree(rt->rt_read, rt->rt_write,
+                                           rt->buffer_size));
+
+       /* first bit from write pointer to the end of the buffer, or count */
+       fl = min(count, (size_t) rt->buffer_size - rt->rt_write);
+
+       copy_from (&rt->rt_buffer[rt->rt_write], buffer, fl, user);
+
+       /* if there's any left copy to the beginning of the buffer */
+       if( count - fl )
+               copy_from (rt->rt_buffer, buffer + fl, count - fl, user);
+
+       rt->rt_write += count;
+       rt->rt_write %= rt->buffer_size;
+
+       return(count);
+}
+
+
+static int file_open(struct inode *inode, struct file *filp)
+{
+       int minor = MINOR(inode->i_rdev);
+
+       return rtlx_open(minor, (filp->f_flags & O_NONBLOCK) ? 0 : 1);
+}
+
+static int file_release(struct inode *inode, struct file *filp)
+{
+       int minor;
+       minor = MINOR(inode->i_rdev);
+
+       return rtlx_release(minor);
+}
+
+static unsigned int file_poll(struct file *file, poll_table * wait)
+{
+       int minor;
+       unsigned int mask = 0;
+
+       minor = MINOR(file->f_dentry->d_inode->i_rdev);
+
+       poll_wait(file, &channel_wqs[minor].rt_queue, wait);
+       poll_wait(file, &channel_wqs[minor].lx_queue, wait);
+
+       if (rtlx == NULL)
+               return 0;
+
+       /* data available to read? */
+       if (rtlx_read_poll(minor, 0))
+               mask |= POLLIN | POLLRDNORM;
+
+       /* space to write */
+       if (rtlx_write_poll(minor))
+               mask |= POLLOUT | POLLWRNORM;
+
+       return mask;
+}
+
+static ssize_t file_read(struct file *file, char __user * buffer, size_t count,
+                        loff_t * ppos)
+{
+       int minor = MINOR(file->f_dentry->d_inode->i_rdev);
+
+       /* data available? */
+       if (!rtlx_read_poll(minor, (file->f_flags & O_NONBLOCK) ? 0 : 1)) {
+               return 0;       // -EAGAIN makes cat whinge
+       }
+
+       return rtlx_read(minor, buffer, count, 1);
+}
+
+static ssize_t file_write(struct file *file, const char __user * buffer,
                          size_t count, loff_t * ppos)
 {
-       unsigned long failed;
        int minor;
        struct rtlx_channel *rt;
-       size_t fl;
        DECLARE_WAITQUEUE(wait, current);
 
        minor = MINOR(file->f_dentry->d_inode->i_rdev);
        rt = &rtlx->channel[minor];
 
        /* any space left... */
-       if (!spacefree(rt->rt_read, rt->rt_write, rt->buffer_size)) {
+       if (!rtlx_write_poll(minor)) {
 
                if (file->f_flags & O_NONBLOCK)
                        return -EAGAIN;
@@ -263,61 +467,64 @@ static ssize_t rtlx_write(struct file *file, const char __user * buffer,
                add_wait_queue(&channel_wqs[minor].rt_queue, &wait);
                set_current_state(TASK_INTERRUPTIBLE);
 
-               while (!spacefree(rt->rt_read, rt->rt_write, rt->buffer_size))
+               while (!rtlx_write_poll(minor))
                        schedule();
 
                set_current_state(TASK_RUNNING);
                remove_wait_queue(&channel_wqs[minor].rt_queue, &wait);
        }
 
-       /* total number of bytes to copy */
-       count = min(count, (size_t)spacefree(rt->rt_read, rt->rt_write, rt->buffer_size) );
-
-       /* first bit from write pointer to the end of the buffer, or count */
-       fl = min(count, (size_t) rt->buffer_size - rt->rt_write);
-
-       failed = copy_from_user(&rt->rt_buffer[rt->rt_write], buffer, fl);
-       if (failed) {
-               count = fl - failed;
-               goto out;
-       }
-
-       /* if there's any left copy to the beginning of the buffer */
-       if (count - fl) {
-               failed = copy_from_user(rt->rt_buffer, buffer + fl, count - fl);
-               if (failed) {
-                       count -= failed;
-                       goto out;
-               }
-       }
-
-out:
-       rt->rt_write += count;
-       rt->rt_write %= rt->buffer_size;
-
-       return count;
+       return rtlx_write(minor, (void *)buffer, count, 1);
 }
 
 static struct file_operations rtlx_fops = {
-       .owner          = THIS_MODULE,
-       .open           = rtlx_open,
-       .release        = rtlx_release,
-       .write          = rtlx_write,
-       .read           = rtlx_read,
-       .poll           = rtlx_poll
+       .owner =   THIS_MODULE,
+       .open =    file_open,
+       .release = file_release,
+       .write =   file_write,
+       .read =    file_read,
+       .poll =    file_poll
 };
 
+static struct irqaction rtlx_irq = {
+       .handler        = rtlx_interrupt,
+       .flags          = SA_INTERRUPT,
+       .name           = "RTLX",
+};
+
+static int rtlx_irq_num = MIPSCPU_INT_BASE + MIPS_CPU_RTLX_IRQ;
+
 static char register_chrdev_failed[] __initdata =
        KERN_ERR "rtlx_module_init: unable to register device\n";
 
-static int __init rtlx_module_init(void)
+static int rtlx_module_init(void)
 {
+       int i;
+
        major = register_chrdev(0, module_name, &rtlx_fops);
        if (major < 0) {
                printk(register_chrdev_failed);
                return major;
        }
 
+       /* initialise the wait queues */
+       for (i = 0; i < RTLX_CHANNELS; i++) {
+               init_waitqueue_head(&channel_wqs[i].rt_queue);
+               init_waitqueue_head(&channel_wqs[i].lx_queue);
+               channel_wqs[i].in_open = 0;
+       }
+
+       /* set up notifiers */
+       notify.start = starting;
+       notify.stop = stopping;
+       vpe_notify(RTLX_TARG_VPE, &notify);
+
+       if (cpu_has_vint)
+               set_vi_handler(MIPS_CPU_RTLX_IRQ, rtlx_dispatch);
+
+       rtlx_irq.dev_id = rtlx;
+       setup_irq(rtlx_irq_num, &rtlx_irq);
+
        return 0;
 }
 
@@ -330,5 +537,5 @@ module_init(rtlx_module_init);
 module_exit(rtlx_module_exit);
 
 MODULE_DESCRIPTION("MIPS RTLX");
-MODULE_AUTHOR("Elizabeth Clarke, MIPS Technologies, Inc.");
+MODULE_AUTHOR("Elizabeth Oldham, MIPS Technologies, Inc.");
 MODULE_LICENSE("GPL");
index 2f2dc54b2e267bce6ed09d31a0d1cc8738f81491..a0ac0e5f61ad67d2d9ef9b8cb734e9db416431bd 100644 (file)
@@ -569,8 +569,19 @@ einval:    li      v0, -EINVAL
        sys     sys_tkill               2
        sys     sys_sendfile64          5
        sys     sys_futex               6
+#ifdef CONFIG_MIPS_MT_FPAFF
+       /*
+        * For FPU affinity scheduling on MIPS MT processors, we need to
+        * intercept sys_sched_xxxaffinity() calls until we get a proper hook
+        * in kernel/sched.c.  Considered only temporary we only support these
+        * hooks for the 32-bit kernel - there is no MIPS64 MT processor atm.
+        */
+       sys     mipsmt_sys_sched_setaffinity    3
+       sys     mipsmt_sys_sched_getaffinity    3
+#else
        sys     sys_sched_setaffinity   3
        sys     sys_sched_getaffinity   3       /* 4240 */
+#endif /* CONFIG_MIPS_MT_FPAFF */
        sys     sys_io_setup            2
        sys     sys_io_destroy          1
        sys     sys_io_getevents        5
@@ -634,6 +645,8 @@ einval:     li      v0, -EINVAL
        sys     sys_pselect6            6
        sys     sys_ppoll               5
        sys     sys_unshare             1
+       sys     sys_splice              4
+       sys     sys_sync_file_range     7       /* 4305 */
        .endm
 
        /* We pre-compute the number of _instruction_ bytes needed to
index 98bf25df56f39f28d0b55c9192bf33b6761a952e..9ba750887377a23ce2ce10b9374862b8e8fc7fe6 100644 (file)
@@ -460,3 +460,5 @@ sys_call_table:
        PTR     sys_pselect6                    /* 5260 */
        PTR     sys_ppoll
        PTR     sys_unshare
+       PTR     sys_splice
+       PTR     sys_sync_file_range
index 05a2c0567daedd953d3a62cb82cc54c356fc2b8b..942aca26f9c422854c58a124abfec6ee2dd514a9 100644 (file)
@@ -386,3 +386,5 @@ EXPORT(sysn32_call_table)
        PTR     sys_pselect6
        PTR     sys_ppoll                       /* 6265 */
        PTR     sys_unshare
+       PTR     sys_splice
+       PTR     sys_sync_file_range
index 19c4ca481b02c3ee1ccc6560a1748d2807959ebf..b53a9207f530a9db07d58c19b556b9d1cc379594 100644 (file)
@@ -508,4 +508,6 @@ sys_call_table:
        PTR     sys_pselect6
        PTR     sys_ppoll
        PTR     sys_unshare
+       PTR     sys_splice
+       PTR     sys32_sync_file_range           /* 4305 */
        .size   sys_call_table,.-sys_call_table
index dcbfd27071f043c82f4b14710042d4fe8df2415b..bcf1b10e518f8be4b4302e13bb3186d1e1773438 100644 (file)
@@ -529,7 +529,10 @@ void __init setup_arch(char **cmdline_p)
 
 int __init fpu_disable(char *s)
 {
-       cpu_data[0].options &= ~MIPS_CPU_FPU;
+       int i;
+
+       for (i = 0; i < NR_CPUS; i++)
+               cpu_data[i].options &= ~MIPS_CPU_FPU;
 
        return 1;
 }
diff --git a/arch/mips/kernel/smp-mt.c b/arch/mips/kernel/smp-mt.c
new file mode 100644 (file)
index 0000000..5777090
--- /dev/null
@@ -0,0 +1,360 @@
+/*
+ *  This program is free software; you can distribute 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 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.,
+ *  59 Temple Place - Suite 330, Boston MA 02111-1307, USA.
+ *
+ * Copyright (C) 2004, 05, 06 MIPS Technologies, Inc.
+ *    Elizabeth Clarke (beth@mips.com)
+ *    Ralf Baechle (ralf@linux-mips.org)
+ * Copyright (C) 2006 Ralf Baechle (ralf@linux-mips.org)
+ */
+#include <linux/kernel.h>
+#include <linux/sched.h>
+#include <linux/cpumask.h>
+#include <linux/interrupt.h>
+#include <linux/compiler.h>
+
+#include <asm/atomic.h>
+#include <asm/cacheflush.h>
+#include <asm/cpu.h>
+#include <asm/processor.h>
+#include <asm/system.h>
+#include <asm/hardirq.h>
+#include <asm/mmu_context.h>
+#include <asm/smp.h>
+#include <asm/time.h>
+#include <asm/mipsregs.h>
+#include <asm/mipsmtregs.h>
+#include <asm/mips_mt.h>
+#include <asm/mips-boards/maltaint.h>  /* This is f*cking wrong */
+
+#define MIPS_CPU_IPI_RESCHED_IRQ 0
+#define MIPS_CPU_IPI_CALL_IRQ 1
+
+static int cpu_ipi_resched_irq, cpu_ipi_call_irq;
+
+#if 0
+static void dump_mtregisters(int vpe, int tc)
+{
+       printk("vpe %d tc %d\n", vpe, tc);
+
+       settc(tc);
+
+       printk("  c0 status  0x%lx\n", read_vpe_c0_status());
+       printk("  vpecontrol 0x%lx\n", read_vpe_c0_vpecontrol());
+       printk("  vpeconf0    0x%lx\n", read_vpe_c0_vpeconf0());
+       printk("  tcstatus 0x%lx\n", read_tc_c0_tcstatus());
+       printk("  tcrestart 0x%lx\n", read_tc_c0_tcrestart());
+       printk("  tcbind 0x%lx\n", read_tc_c0_tcbind());
+       printk("  tchalt 0x%lx\n", read_tc_c0_tchalt());
+}
+#endif
+
+void __init sanitize_tlb_entries(void)
+{
+       int i, tlbsiz;
+       unsigned long mvpconf0, ncpu;
+
+       if (!cpu_has_mipsmt)
+               return;
+
+       /* Enable VPC */
+       set_c0_mvpcontrol(MVPCONTROL_VPC);
+
+       back_to_back_c0_hazard();
+
+       /* Disable TLB sharing */
+       clear_c0_mvpcontrol(MVPCONTROL_STLB);
+
+       mvpconf0 = read_c0_mvpconf0();
+
+       printk(KERN_INFO "MVPConf0 0x%lx TLBS %lx PTLBE %ld\n", mvpconf0,
+                  (mvpconf0 & MVPCONF0_TLBS) >> MVPCONF0_TLBS_SHIFT,
+                          (mvpconf0 & MVPCONF0_PTLBE) >> MVPCONF0_PTLBE_SHIFT);
+
+       tlbsiz = (mvpconf0 & MVPCONF0_PTLBE) >> MVPCONF0_PTLBE_SHIFT;
+       ncpu = ((mvpconf0 & MVPCONF0_PVPE) >> MVPCONF0_PVPE_SHIFT) + 1;
+
+       printk(" tlbsiz %d ncpu %ld\n", tlbsiz, ncpu);
+
+       if (tlbsiz > 0) {
+               /* share them out across the vpe's */
+               tlbsiz /= ncpu;
+
+               printk(KERN_INFO "setting Config1.MMU_size to %d\n", tlbsiz);
+
+               for (i = 0; i < ncpu; i++) {
+                       settc(i);
+
+                       if (i == 0)
+                               write_c0_config1((read_c0_config1() & ~(0x3f << 25)) | (tlbsiz << 25));
+                       else
+                               write_vpe_c0_config1((read_vpe_c0_config1() & ~(0x3f << 25)) |
+                                                  (tlbsiz << 25));
+               }
+       }
+
+       clear_c0_mvpcontrol(MVPCONTROL_VPC);
+}
+
+static void ipi_resched_dispatch (struct pt_regs *regs)
+{
+       do_IRQ(MIPSCPU_INT_BASE + MIPS_CPU_IPI_RESCHED_IRQ, regs);
+}
+
+static void ipi_call_dispatch (struct pt_regs *regs)
+{
+       do_IRQ(MIPSCPU_INT_BASE + MIPS_CPU_IPI_CALL_IRQ, regs);
+}
+
+irqreturn_t ipi_resched_interrupt(int irq, void *dev_id, struct pt_regs *regs)
+{
+       return IRQ_HANDLED;
+}
+
+irqreturn_t ipi_call_interrupt(int irq, void *dev_id, struct pt_regs *regs)
+{
+       smp_call_function_interrupt();
+
+       return IRQ_HANDLED;
+}
+
+static struct irqaction irq_resched = {
+       .handler        = ipi_resched_interrupt,
+       .flags          = SA_INTERRUPT,
+       .name           = "IPI_resched"
+};
+
+static struct irqaction irq_call = {
+       .handler        = ipi_call_interrupt,
+       .flags          = SA_INTERRUPT,
+       .name           = "IPI_call"
+};
+
+/*
+ * Common setup before any secondaries are started
+ * Make sure all CPU's are in a sensible state before we boot any of the
+ * secondarys
+ */
+void plat_smp_setup(void)
+{
+       unsigned long val;
+       int i, num;
+
+#ifdef CONFIG_MIPS_MT_FPAFF
+       /* If we have an FPU, enroll ourselves in the FPU-full mask */
+       if (cpu_has_fpu)
+               cpu_set(0, mt_fpu_cpumask);
+#endif /* CONFIG_MIPS_MT_FPAFF */
+       if (!cpu_has_mipsmt)
+               return;
+
+       /* disable MT so we can configure */
+       dvpe();
+       dmt();
+
+       mips_mt_set_cpuoptions();
+
+       /* Put MVPE's into 'configuration state' */
+       set_c0_mvpcontrol(MVPCONTROL_VPC);
+
+       val = read_c0_mvpconf0();
+
+       /* we'll always have more TC's than VPE's, so loop setting everything
+          to a sensible state */
+       for (i = 0, num = 0; i <= ((val & MVPCONF0_PTC) >> MVPCONF0_PTC_SHIFT); i++) {
+               settc(i);
+
+               /* VPE's */
+               if (i <= ((val & MVPCONF0_PVPE) >> MVPCONF0_PVPE_SHIFT)) {
+
+                       /* deactivate all but vpe0 */
+                       if (i != 0) {
+                               unsigned long tmp = read_vpe_c0_vpeconf0();
+
+                               tmp &= ~VPECONF0_VPA;
+
+                               /* master VPE */
+                               tmp |= VPECONF0_MVP;
+                               write_vpe_c0_vpeconf0(tmp);
+
+                               /* Record this as available CPU */
+                               cpu_set(i, phys_cpu_present_map);
+                               __cpu_number_map[i]     = ++num;
+                               __cpu_logical_map[num]  = i;
+                       }
+
+                       /* disable multi-threading with TC's */
+                       write_vpe_c0_vpecontrol(read_vpe_c0_vpecontrol() & ~VPECONTROL_TE);
+
+                       if (i != 0) {
+                               write_vpe_c0_status((read_c0_status() & ~(ST0_IM | ST0_IE | ST0_KSU)) | ST0_CU0);
+
+                               /* set config to be the same as vpe0, particularly kseg0 coherency alg */
+                               write_vpe_c0_config( read_c0_config());
+
+                               /* make sure there are no software interrupts pending */
+                               write_vpe_c0_cause(read_vpe_c0_cause() & ~(C_SW1|C_SW0));
+
+                               /* Propagate Config7 */
+                               write_vpe_c0_config7(read_c0_config7());
+                       }
+
+               }
+
+               /* TC's */
+
+               if (i != 0) {
+                       unsigned long tmp;
+
+                       /* bind a TC to each VPE, May as well put all excess TC's
+                          on the last VPE */
+                       if ( i >= (((val & MVPCONF0_PVPE) >> MVPCONF0_PVPE_SHIFT)+1) )
+                               write_tc_c0_tcbind(read_tc_c0_tcbind() | ((val & MVPCONF0_PVPE) >> MVPCONF0_PVPE_SHIFT) );
+                       else {
+                               write_tc_c0_tcbind( read_tc_c0_tcbind() | i);
+
+                               /* and set XTC */
+                               write_vpe_c0_vpeconf0( read_vpe_c0_vpeconf0() | (i << VPECONF0_XTC_SHIFT));
+                       }
+
+                       tmp = read_tc_c0_tcstatus();
+
+                       /* mark not allocated and not dynamically allocatable */
+                       tmp &= ~(TCSTATUS_A | TCSTATUS_DA);
+                       tmp |= TCSTATUS_IXMT;           /* interrupt exempt */
+                       write_tc_c0_tcstatus(tmp);
+
+                       write_tc_c0_tchalt(TCHALT_H);
+               }
+       }
+
+       /* Release config state */
+       clear_c0_mvpcontrol(MVPCONTROL_VPC);
+
+       /* We'll wait until starting the secondaries before starting MVPE */
+
+       printk(KERN_INFO "Detected %i available secondary CPU(s)\n", num);
+}
+
+void __init plat_prepare_cpus(unsigned int max_cpus)
+{
+       /* set up ipi interrupts */
+       if (cpu_has_vint) {
+               set_vi_handler (MIPS_CPU_IPI_RESCHED_IRQ, ipi_resched_dispatch);
+               set_vi_handler (MIPS_CPU_IPI_CALL_IRQ, ipi_call_dispatch);
+       }
+
+       cpu_ipi_resched_irq = MIPSCPU_INT_BASE + MIPS_CPU_IPI_RESCHED_IRQ;
+       cpu_ipi_call_irq = MIPSCPU_INT_BASE + MIPS_CPU_IPI_CALL_IRQ;
+
+       setup_irq(cpu_ipi_resched_irq, &irq_resched);
+       setup_irq(cpu_ipi_call_irq, &irq_call);
+
+       /* need to mark IPI's as IRQ_PER_CPU */
+       irq_desc[cpu_ipi_resched_irq].status |= IRQ_PER_CPU;
+       irq_desc[cpu_ipi_call_irq].status |= IRQ_PER_CPU;
+}
+
+/*
+ * Setup the PC, SP, and GP of a secondary processor and start it
+ * running!
+ * smp_bootstrap is the place to resume from
+ * __KSTK_TOS(idle) is apparently the stack pointer
+ * (unsigned long)idle->thread_info the gp
+ * assumes a 1:1 mapping of TC => VPE
+ */
+void prom_boot_secondary(int cpu, struct task_struct *idle)
+{
+       struct thread_info *gp = task_thread_info(idle);
+       dvpe();
+       set_c0_mvpcontrol(MVPCONTROL_VPC);
+
+       settc(cpu);
+
+       /* restart */
+       write_tc_c0_tcrestart((unsigned long)&smp_bootstrap);
+
+       /* enable the tc this vpe/cpu will be running */
+       write_tc_c0_tcstatus((read_tc_c0_tcstatus() & ~TCSTATUS_IXMT) | TCSTATUS_A);
+
+       write_tc_c0_tchalt(0);
+
+       /* enable the VPE */
+       write_vpe_c0_vpeconf0(read_vpe_c0_vpeconf0() | VPECONF0_VPA);
+
+       /* stack pointer */
+       write_tc_gpr_sp( __KSTK_TOS(idle));
+
+       /* global pointer */
+       write_tc_gpr_gp((unsigned long)gp);
+
+       flush_icache_range((unsigned long)gp,
+                          (unsigned long)(gp + sizeof(struct thread_info)));
+
+       /* finally out of configuration and into chaos */
+       clear_c0_mvpcontrol(MVPCONTROL_VPC);
+
+       evpe(EVPE_ENABLE);
+}
+
+void prom_init_secondary(void)
+{
+       write_c0_status((read_c0_status() & ~ST0_IM ) |
+                       (STATUSF_IP0 | STATUSF_IP1 | STATUSF_IP7));
+}
+
+void prom_smp_finish(void)
+{
+       write_c0_compare(read_c0_count() + (8* mips_hpt_frequency/HZ));
+
+#ifdef CONFIG_MIPS_MT_FPAFF
+       /* If we have an FPU, enroll ourselves in the FPU-full mask */
+       if (cpu_has_fpu)
+               cpu_set(smp_processor_id(), mt_fpu_cpumask);
+#endif /* CONFIG_MIPS_MT_FPAFF */
+
+       local_irq_enable();
+}
+
+void prom_cpus_done(void)
+{
+}
+
+void core_send_ipi(int cpu, unsigned int action)
+{
+       int i;
+       unsigned long flags;
+       int vpflags;
+
+       local_irq_save (flags);
+
+       vpflags = dvpe();       /* cant access the other CPU's registers whilst MVPE enabled */
+
+       switch (action) {
+       case SMP_CALL_FUNCTION:
+               i = C_SW1;
+               break;
+
+       case SMP_RESCHEDULE_YOURSELF:
+       default:
+               i = C_SW0;
+               break;
+       }
+
+       /* 1:1 mapping of vpe and tc... */
+       settc(cpu);
+       write_vpe_c0_cause(read_vpe_c0_cause() | i);
+       evpe(vpflags);
+
+       local_irq_restore(flags);
+}
index 78d171bfa331cbbbdd024746ba49c8e61267e846..d42f358754ad829129663f01350d7c0757f8f078 100644 (file)
 #include <asm/mmu_context.h>
 #include <asm/smp.h>
 
+#ifdef CONFIG_MIPS_MT_SMTC
+#include <asm/mipsmtregs.h>
+#endif /* CONFIG_MIPS_MT_SMTC */
+
 cpumask_t phys_cpu_present_map;                /* Bitmask of available CPUs */
 volatile cpumask_t cpu_callin_map;     /* Bitmask of started secondaries */
 cpumask_t cpu_online_map;              /* Bitmask of currently online CPUs */
@@ -85,6 +89,10 @@ asmlinkage void start_secondary(void)
 {
        unsigned int cpu;
 
+#ifdef CONFIG_MIPS_MT_SMTC
+       /* Only do cpu_probe for first TC of CPU */
+       if ((read_c0_tcbind() & TCBIND_CURTC) == 0)
+#endif /* CONFIG_MIPS_MT_SMTC */
        cpu_probe();
        cpu_report();
        per_cpu_trap_init();
@@ -179,11 +187,13 @@ int smp_call_function (void (*func) (void *info), void *info, int retry,
        if (wait)
                while (atomic_read(&data.finished) != cpus)
                        barrier();
+       call_data = NULL;
        spin_unlock(&smp_call_lock);
 
        return 0;
 }
 
+
 void smp_call_function_interrupt(void)
 {
        void (*func) (void *info) = call_data->func;
@@ -446,5 +456,3 @@ subsys_initcall(topology_init);
 
 EXPORT_SYMBOL(flush_tlb_page);
 EXPORT_SYMBOL(flush_tlb_one);
-EXPORT_SYMBOL(cpu_data);
-EXPORT_SYMBOL(synchronize_irq);
diff --git a/arch/mips/kernel/smp_mt.c b/arch/mips/kernel/smp_mt.c
deleted file mode 100644 (file)
index 993b8bf..0000000
+++ /dev/null
@@ -1,342 +0,0 @@
-/*
- * Copyright (C) 2004, 2005 MIPS Technologies, Inc.  All rights reserved.
- *
- *  Elizabeth Clarke (beth@mips.com)
- *
- *  This program is free software; you can distribute 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 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.,
- *  59 Temple Place - Suite 330, Boston MA 02111-1307, USA.
- *
- */
-#include <linux/kernel.h>
-#include <linux/sched.h>
-#include <linux/cpumask.h>
-#include <linux/interrupt.h>
-#include <linux/compiler.h>
-
-#include <asm/atomic.h>
-#include <asm/cpu.h>
-#include <asm/processor.h>
-#include <asm/system.h>
-#include <asm/hardirq.h>
-#include <asm/mmu_context.h>
-#include <asm/smp.h>
-#include <asm/time.h>
-#include <asm/mipsregs.h>
-#include <asm/mipsmtregs.h>
-#include <asm/cacheflush.h>
-#include <asm/mips-boards/maltaint.h>
-
-#define MIPS_CPU_IPI_RESCHED_IRQ 0
-#define MIPS_CPU_IPI_CALL_IRQ 1
-
-static int cpu_ipi_resched_irq, cpu_ipi_call_irq;
-
-#if 0
-static void dump_mtregisters(int vpe, int tc)
-{
-       printk("vpe %d tc %d\n", vpe, tc);
-
-       settc(tc);
-
-       printk("  c0 status  0x%lx\n", read_vpe_c0_status());
-       printk("  vpecontrol 0x%lx\n", read_vpe_c0_vpecontrol());
-       printk("  vpeconf0    0x%lx\n", read_vpe_c0_vpeconf0());
-       printk("  tcstatus 0x%lx\n", read_tc_c0_tcstatus());
-       printk("  tcrestart 0x%lx\n", read_tc_c0_tcrestart());
-       printk("  tcbind 0x%lx\n", read_tc_c0_tcbind());
-       printk("  tchalt 0x%lx\n", read_tc_c0_tchalt());
-}
-#endif
-
-void __init sanitize_tlb_entries(void)
-{
-       int i, tlbsiz;
-       unsigned long mvpconf0, ncpu;
-
-       if (!cpu_has_mipsmt)
-               return;
-
-       set_c0_mvpcontrol(MVPCONTROL_VPC);
-
-       back_to_back_c0_hazard();
-
-       /* Disable TLB sharing */
-       clear_c0_mvpcontrol(MVPCONTROL_STLB);
-
-       mvpconf0 = read_c0_mvpconf0();
-
-       printk(KERN_INFO "MVPConf0 0x%lx TLBS %lx PTLBE %ld\n", mvpconf0,
-                  (mvpconf0 & MVPCONF0_TLBS) >> MVPCONF0_TLBS_SHIFT,
-                          (mvpconf0 & MVPCONF0_PTLBE) >> MVPCONF0_PTLBE_SHIFT);
-
-       tlbsiz = (mvpconf0 & MVPCONF0_PTLBE) >> MVPCONF0_PTLBE_SHIFT;
-       ncpu = ((mvpconf0 & MVPCONF0_PVPE) >> MVPCONF0_PVPE_SHIFT) + 1;
-
-       printk(" tlbsiz %d ncpu %ld\n", tlbsiz, ncpu);
-
-       if (tlbsiz > 0) {
-               /* share them out across the vpe's */
-               tlbsiz /= ncpu;
-
-               printk(KERN_INFO "setting Config1.MMU_size to %d\n", tlbsiz);
-
-               for (i = 0; i < ncpu; i++) {
-                       settc(i);
-
-                       if (i == 0)
-                               write_c0_config1((read_c0_config1() & ~(0x3f << 25)) | (tlbsiz << 25));
-                       else
-                               write_vpe_c0_config1((read_vpe_c0_config1() & ~(0x3f << 25)) |
-                                                  (tlbsiz << 25));
-               }
-       }
-
-       clear_c0_mvpcontrol(MVPCONTROL_VPC);
-}
-
-static void ipi_resched_dispatch (struct pt_regs *regs)
-{
-       do_IRQ(MIPS_CPU_IPI_RESCHED_IRQ, regs);
-}
-
-static void ipi_call_dispatch (struct pt_regs *regs)
-{
-       do_IRQ(MIPS_CPU_IPI_CALL_IRQ, regs);
-}
-
-irqreturn_t ipi_resched_interrupt(int irq, void *dev_id, struct pt_regs *regs)
-{
-       return IRQ_HANDLED;
-}
-
-irqreturn_t ipi_call_interrupt(int irq, void *dev_id, struct pt_regs *regs)
-{
-       smp_call_function_interrupt();
-
-       return IRQ_HANDLED;
-}
-
-static struct irqaction irq_resched = {
-       .handler        = ipi_resched_interrupt,
-       .flags          = SA_INTERRUPT,
-       .name           = "IPI_resched"
-};
-
-static struct irqaction irq_call = {
-       .handler        = ipi_call_interrupt,
-       .flags          = SA_INTERRUPT,
-       .name           = "IPI_call"
-};
-
-/*
- * Common setup before any secondaries are started
- * Make sure all CPU's are in a sensible state before we boot any of the
- * secondarys
- */
-void plat_smp_setup(void)
-{
-       unsigned long val;
-       int i, num;
-
-       if (!cpu_has_mipsmt)
-               return;
-
-       /* disable MT so we can configure */
-       dvpe();
-       dmt();
-
-       /* Put MVPE's into 'configuration state' */
-       set_c0_mvpcontrol(MVPCONTROL_VPC);
-
-       val = read_c0_mvpconf0();
-
-       /* we'll always have more TC's than VPE's, so loop setting everything
-          to a sensible state */
-       for (i = 0, num = 0; i <= ((val & MVPCONF0_PTC) >> MVPCONF0_PTC_SHIFT); i++) {
-               settc(i);
-
-               /* VPE's */
-               if (i <= ((val & MVPCONF0_PVPE) >> MVPCONF0_PVPE_SHIFT)) {
-
-                       /* deactivate all but vpe0 */
-                       if (i != 0) {
-                               unsigned long tmp = read_vpe_c0_vpeconf0();
-
-                               tmp &= ~VPECONF0_VPA;
-
-                               /* master VPE */
-                               tmp |= VPECONF0_MVP;
-                               write_vpe_c0_vpeconf0(tmp);
-
-                               /* Record this as available CPU */
-                               cpu_set(i, phys_cpu_present_map);
-                               __cpu_number_map[i]     = ++num;
-                               __cpu_logical_map[num]  = i;
-                       }
-
-                       /* disable multi-threading with TC's */
-                       write_vpe_c0_vpecontrol(read_vpe_c0_vpecontrol() & ~VPECONTROL_TE);
-
-                       if (i != 0) {
-                               write_vpe_c0_status((read_c0_status() & ~(ST0_IM | ST0_IE | ST0_KSU)) | ST0_CU0);
-                               write_vpe_c0_cause(read_vpe_c0_cause() & ~CAUSEF_IP);
-
-                               /* set config to be the same as vpe0, particularly kseg0 coherency alg */
-                               write_vpe_c0_config( read_c0_config());
-
-                               /* Propagate Config7 */
-                               write_vpe_c0_config7(read_c0_config7());
-                       }
-
-               }
-
-               /* TC's */
-
-               if (i != 0) {
-                       unsigned long tmp;
-
-                       /* bind a TC to each VPE, May as well put all excess TC's
-                          on the last VPE */
-                       if ( i >= (((val & MVPCONF0_PVPE) >> MVPCONF0_PVPE_SHIFT)+1) )
-                               write_tc_c0_tcbind(read_tc_c0_tcbind() | ((val & MVPCONF0_PVPE) >> MVPCONF0_PVPE_SHIFT) );
-                       else {
-                               write_tc_c0_tcbind( read_tc_c0_tcbind() | i);
-
-                               /* and set XTC */
-                               write_vpe_c0_vpeconf0( read_vpe_c0_vpeconf0() | (i << VPECONF0_XTC_SHIFT));
-                       }
-
-                       tmp = read_tc_c0_tcstatus();
-
-                       /* mark not allocated and not dynamically allocatable */
-                       tmp &= ~(TCSTATUS_A | TCSTATUS_DA);
-                       tmp |= TCSTATUS_IXMT;           /* interrupt exempt */
-                       write_tc_c0_tcstatus(tmp);
-
-                       write_tc_c0_tchalt(TCHALT_H);
-               }
-       }
-
-       /* Release config state */
-       clear_c0_mvpcontrol(MVPCONTROL_VPC);
-
-       /* We'll wait until starting the secondaries before starting MVPE */
-
-       printk(KERN_INFO "Detected %i available secondary CPU(s)\n", num);
-
-       /* set up ipi interrupts */
-       if (cpu_has_vint) {
-               set_vi_handler (MIPS_CPU_IPI_RESCHED_IRQ, ipi_resched_dispatch);
-               set_vi_handler (MIPS_CPU_IPI_CALL_IRQ, ipi_call_dispatch);
-       }
-}
-
-void __init plat_prepare_cpus(unsigned int max_cpus)
-{
-       cpu_ipi_resched_irq = MIPSCPU_INT_BASE + MIPS_CPU_IPI_RESCHED_IRQ;
-       cpu_ipi_call_irq = MIPSCPU_INT_BASE + MIPS_CPU_IPI_CALL_IRQ;
-
-       setup_irq(cpu_ipi_resched_irq, &irq_resched);
-       setup_irq(cpu_ipi_call_irq, &irq_call);
-
-       /* need to mark IPI's as IRQ_PER_CPU */
-       irq_desc[cpu_ipi_resched_irq].status |= IRQ_PER_CPU;
-       irq_desc[cpu_ipi_call_irq].status |= IRQ_PER_CPU;
-}
-
-/*
- * Setup the PC, SP, and GP of a secondary processor and start it
- * running!
- * smp_bootstrap is the place to resume from
- * __KSTK_TOS(idle) is apparently the stack pointer
- * (unsigned long)idle->thread_info the gp
- * assumes a 1:1 mapping of TC => VPE
- */
-void prom_boot_secondary(int cpu, struct task_struct *idle)
-{
-       struct thread_info *gp = task_thread_info(idle);
-       dvpe();
-       set_c0_mvpcontrol(MVPCONTROL_VPC);
-
-       settc(cpu);
-
-       /* restart */
-       write_tc_c0_tcrestart((unsigned long)&smp_bootstrap);
-
-       /* enable the tc this vpe/cpu will be running */
-       write_tc_c0_tcstatus((read_tc_c0_tcstatus() & ~TCSTATUS_IXMT) | TCSTATUS_A);
-
-       write_tc_c0_tchalt(0);
-
-       /* enable the VPE */
-       write_vpe_c0_vpeconf0(read_vpe_c0_vpeconf0() | VPECONF0_VPA);
-
-       /* stack pointer */
-       write_tc_gpr_sp( __KSTK_TOS(idle));
-
-       /* global pointer */
-       write_tc_gpr_gp((unsigned long)gp);
-
-       flush_icache_range((unsigned long)gp, (unsigned long)(gp + 1));
-
-       /* finally out of configuration and into chaos */
-       clear_c0_mvpcontrol(MVPCONTROL_VPC);
-
-       evpe(EVPE_ENABLE);
-}
-
-void prom_init_secondary(void)
-{
-       write_c0_status((read_c0_status() & ~ST0_IM ) |
-                       (STATUSF_IP0 | STATUSF_IP1 | STATUSF_IP7));
-}
-
-void prom_smp_finish(void)
-{
-       write_c0_compare(read_c0_count() + (8* mips_hpt_frequency/HZ));
-
-       local_irq_enable();
-}
-
-void prom_cpus_done(void)
-{
-}
-
-void core_send_ipi(int cpu, unsigned int action)
-{
-       int i;
-       unsigned long flags;
-       int vpflags;
-
-       local_irq_save (flags);
-
-       vpflags = dvpe();       /* cant access the other CPU's registers whilst MVPE enabled */
-
-       switch (action) {
-       case SMP_CALL_FUNCTION:
-               i = C_SW1;
-               break;
-
-       case SMP_RESCHEDULE_YOURSELF:
-       default:
-               i = C_SW0;
-               break;
-       }
-
-       /* 1:1 mapping of vpe and tc... */
-       settc(cpu);
-       write_vpe_c0_cause(read_vpe_c0_cause() | i);
-       evpe(vpflags);
-
-       local_irq_restore(flags);
-}
diff --git a/arch/mips/kernel/smtc-asm.S b/arch/mips/kernel/smtc-asm.S
new file mode 100644 (file)
index 0000000..c9d6519
--- /dev/null
@@ -0,0 +1,130 @@
+/*
+ * Assembly Language Functions for MIPS MT SMTC support
+ */
+
+/*
+ * This file should be built into the kernel only if CONFIG_MIPS_MT_SMTC is set. */
+
+#include <asm/regdef.h>
+#include <asm/asmmacro.h>
+#include <asm/stackframe.h>
+#include <asm/stackframe.h>
+
+/*
+ * "Software Interrupt" linkage.
+ *
+ * This is invoked when an "Interrupt" is sent from one TC to another,
+ * where the TC to be interrupted is halted, has it's Restart address
+ * and Status values saved by the "remote control" thread, then modified
+ * to cause execution to begin here, in kenel mode. This code then
+ * disguises the TC state as that of an exception and transfers
+ * control to the general exception or vectored interrupt handler.
+ */
+       .set noreorder
+
+/*
+The __smtc_ipi_vector would use k0 and k1 as temporaries and
+1) Set EXL (this is per-VPE, so this can't be done by proxy!)
+2) Restore the K/CU and IXMT bits to the pre "exception" state
+   (EXL means no interrupts and access to the kernel map).
+3) Set EPC to be the saved value of TCRestart.
+4) Jump to the exception handler entry point passed by the sender.
+
+CAN WE PROVE THAT WE WON'T DO THIS IF INTS DISABLED??
+*/
+
+/*
+ * Reviled and slandered vision: Set EXL and restore K/CU/IXMT
+ * state of pre-halt thread, then save everything and call
+ * thought some function pointer to imaginary_exception, which
+ * will parse a register value or memory message queue to
+ * deliver things like interprocessor interrupts. On return
+ * from that function, jump to the global ret_from_irq code
+ * to invoke the scheduler and return as appropriate.
+ */
+
+#define PT_PADSLOT4 (PT_R0-8)
+#define PT_PADSLOT5 (PT_R0-4)
+
+       .text
+       .align 5
+FEXPORT(__smtc_ipi_vector)
+       .set    noat
+       /* Disable thread scheduling to make Status update atomic */
+       DMT     27                                      # dmt   k1
+       ehb
+       /* Set EXL */
+       mfc0    k0,CP0_STATUS
+       ori     k0,k0,ST0_EXL
+       mtc0    k0,CP0_STATUS
+       ehb
+       /* Thread scheduling now inhibited by EXL. Restore TE state. */
+       andi    k1,k1,VPECONTROL_TE
+       beqz    k1,1f
+       emt
+1:
+       /*
+        * The IPI sender has put some information on the anticipated
+        * kernel stack frame.  If we were in user mode, this will be
+        * built above the saved kernel SP.  If we were already in the
+        * kernel, it will be built above the current CPU SP.
+        *
+        * Were we in kernel mode, as indicated by CU0?
+        */
+       sll     k1,k0,3
+       .set noreorder
+       bltz    k1,2f
+       move    k1,sp
+       .set reorder
+       /*
+        * If previously in user mode, set CU0 and use kernel stack.
+        */
+       li      k1,ST0_CU0
+       or      k1,k1,k0
+       mtc0    k1,CP0_STATUS
+       ehb
+       get_saved_sp
+       /* Interrupting TC will have pre-set values in slots in the new frame */
+2:     subu    k1,k1,PT_SIZE
+       /* Load TCStatus Value */
+       lw      k0,PT_TCSTATUS(k1)
+       /* Write it to TCStatus to restore CU/KSU/IXMT state */
+       mtc0    k0,$2,1
+       ehb
+       lw      k0,PT_EPC(k1)
+       mtc0    k0,CP0_EPC
+       /* Save all will redundantly recompute the SP, but use it for now */
+       SAVE_ALL
+       CLI
+       move    a0,sp
+       /* Function to be invoked passed stack pad slot 5 */
+       lw      t0,PT_PADSLOT5(sp)
+       /* Argument from sender passed in stack pad slot 4 */
+       lw      a1,PT_PADSLOT4(sp)
+       jalr    t0
+       nop
+       j       ret_from_irq
+       nop
+
+/*
+ * Called from idle loop to provoke processing of queued IPIs
+ * First IPI message in queue passed as argument.
+ */
+
+LEAF(self_ipi)
+       /* Before anything else, block interrupts */
+       mfc0    t0,CP0_TCSTATUS
+       ori     t1,t0,TCSTATUS_IXMT
+       mtc0    t1,CP0_TCSTATUS
+       ehb
+       /* We know we're in kernel mode, so prepare stack frame */
+       subu    t1,sp,PT_SIZE
+       sw      ra,PT_EPC(t1)
+       sw      a0,PT_PADSLOT4(t1)
+       la      t2,ipi_decode
+       sw      t2,PT_PADSLOT5(t1)
+       /* Save pre-disable value of TCStatus */
+       sw      t0,PT_TCSTATUS(t1)
+       j       __smtc_ipi_vector
+       nop
+END(self_ipi)
diff --git a/arch/mips/kernel/smtc-proc.c b/arch/mips/kernel/smtc-proc.c
new file mode 100644 (file)
index 0000000..6f37099
--- /dev/null
@@ -0,0 +1,93 @@
+/*
+ * /proc hooks for SMTC kernel
+ * Copyright (C) 2005 Mips Technologies, Inc
+ */
+
+#include <linux/kernel.h>
+#include <linux/sched.h>
+#include <linux/cpumask.h>
+#include <linux/interrupt.h>
+
+#include <asm/cpu.h>
+#include <asm/processor.h>
+#include <asm/atomic.h>
+#include <asm/system.h>
+#include <asm/hardirq.h>
+#include <asm/mmu_context.h>
+#include <asm/smp.h>
+#include <asm/mipsregs.h>
+#include <asm/cacheflush.h>
+#include <linux/proc_fs.h>
+
+#include <asm/smtc_proc.h>
+
+/*
+ * /proc diagnostic and statistics hooks
+ */
+
+/*
+ * Statistics gathered
+ */
+unsigned long selfipis[NR_CPUS];
+
+struct smtc_cpu_proc smtc_cpu_stats[NR_CPUS];
+
+static struct proc_dir_entry *smtc_stats;
+
+atomic_t smtc_fpu_recoveries;
+
+static int proc_read_smtc(char *page, char **start, off_t off,
+                          int count, int *eof, void *data)
+{
+       int totalen = 0;
+       int len;
+       int i;
+       extern unsigned long ebase;
+
+       len = sprintf(page, "SMTC Status Word: 0x%08x\n", smtc_status);
+       totalen += len;
+       page += len;
+       len = sprintf(page, "Config7: 0x%08x\n", read_c0_config7());
+       totalen += len;
+       page += len;
+       len = sprintf(page, "EBASE: 0x%08lx\n", ebase);
+       totalen += len;
+       page += len;
+       len = sprintf(page, "Counter Interrupts taken per CPU (TC)\n");
+       totalen += len;
+       page += len;
+       for (i=0; i < NR_CPUS; i++) {
+               len = sprintf(page, "%d: %ld\n", i, smtc_cpu_stats[i].timerints);
+               totalen += len;
+               page += len;
+       }
+       len = sprintf(page, "Self-IPIs by CPU:\n");
+       totalen += len;
+       page += len;
+       for(i = 0; i < NR_CPUS; i++) {
+               len = sprintf(page, "%d: %ld\n", i, smtc_cpu_stats[i].selfipis);
+               totalen += len;
+               page += len;
+       }
+       len = sprintf(page, "%d Recoveries of \"stolen\" FPU\n",
+                     atomic_read(&smtc_fpu_recoveries));
+       totalen += len;
+       page += len;
+
+       return totalen;
+}
+
+void init_smtc_stats(void)
+{
+       int i;
+
+       for (i=0; i<NR_CPUS; i++) {
+               smtc_cpu_stats[i].timerints = 0;
+               smtc_cpu_stats[i].selfipis = 0;
+       }
+
+       atomic_set(&smtc_fpu_recoveries, 0);
+
+       smtc_stats = create_proc_read_entry("smtc", 0444, NULL,
+                                           proc_read_smtc, NULL);
+}
diff --git a/arch/mips/kernel/smtc.c b/arch/mips/kernel/smtc.c
new file mode 100644 (file)
index 0000000..2e8e52c
--- /dev/null
@@ -0,0 +1,1322 @@
+/* Copyright (C) 2004 Mips Technologies, Inc */
+
+#include <linux/kernel.h>
+#include <linux/sched.h>
+#include <linux/cpumask.h>
+#include <linux/interrupt.h>
+
+#include <asm/cpu.h>
+#include <asm/processor.h>
+#include <asm/atomic.h>
+#include <asm/system.h>
+#include <asm/hardirq.h>
+#include <asm/hazards.h>
+#include <asm/mmu_context.h>
+#include <asm/smp.h>
+#include <asm/mipsregs.h>
+#include <asm/cacheflush.h>
+#include <asm/time.h>
+#include <asm/addrspace.h>
+#include <asm/smtc.h>
+#include <asm/smtc_ipi.h>
+#include <asm/smtc_proc.h>
+
+/*
+ * This file should be built into the kernel only if CONFIG_MIPS_MT_SMTC is set.
+ */
+
+/*
+ * MIPSCPU_INT_BASE is identically defined in both
+ * asm-mips/mips-boards/maltaint.h and asm-mips/mips-boards/simint.h,
+ * but as yet there's no properly organized include structure that
+ * will ensure that the right *int.h file will be included for a
+ * given platform build.
+ */
+
+#define MIPSCPU_INT_BASE       16
+
+#define MIPS_CPU_IPI_IRQ       1
+
+#define LOCK_MT_PRA() \
+       local_irq_save(flags); \
+       mtflags = dmt()
+
+#define UNLOCK_MT_PRA() \
+       emt(mtflags); \
+       local_irq_restore(flags)
+
+#define LOCK_CORE_PRA() \
+       local_irq_save(flags); \
+       mtflags = dvpe()
+
+#define UNLOCK_CORE_PRA() \
+       evpe(mtflags); \
+       local_irq_restore(flags)
+
+/*
+ * Data structures purely associated with SMTC parallelism
+ */
+
+
+/*
+ * Table for tracking ASIDs whose lifetime is prolonged.
+ */
+
+asiduse smtc_live_asid[MAX_SMTC_TLBS][MAX_SMTC_ASIDS];
+
+/*
+ * Clock interrupt "latch" buffers, per "CPU"
+ */
+
+unsigned int ipi_timer_latch[NR_CPUS];
+
+/*
+ * Number of InterProcessor Interupt (IPI) message buffers to allocate
+ */
+
+#define IPIBUF_PER_CPU 4
+
+struct smtc_ipi_q IPIQ[NR_CPUS];
+struct smtc_ipi_q freeIPIq;
+
+
+/* Forward declarations */
+
+void ipi_decode(struct pt_regs *, struct smtc_ipi *);
+void post_direct_ipi(int cpu, struct smtc_ipi *pipi);
+void setup_cross_vpe_interrupts(void);
+void init_smtc_stats(void);
+
+/* Global SMTC Status */
+
+unsigned int smtc_status = 0;
+
+/* Boot command line configuration overrides */
+
+static int vpelimit = 0;
+static int tclimit = 0;
+static int ipibuffers = 0;
+static int nostlb = 0;
+static int asidmask = 0;
+unsigned long smtc_asid_mask = 0xff;
+
+static int __init maxvpes(char *str)
+{
+       get_option(&str, &vpelimit);
+       return 1;
+}
+
+static int __init maxtcs(char *str)
+{
+       get_option(&str, &tclimit);
+       return 1;
+}
+
+static int __init ipibufs(char *str)
+{
+       get_option(&str, &ipibuffers);
+       return 1;
+}
+
+static int __init stlb_disable(char *s)
+{
+       nostlb = 1;
+       return 1;
+}
+
+static int __init asidmask_set(char *str)
+{
+       get_option(&str, &asidmask);
+       switch(asidmask) {
+       case 0x1:
+       case 0x3:
+       case 0x7:
+       case 0xf:
+       case 0x1f:
+       case 0x3f:
+       case 0x7f:
+       case 0xff:
+               smtc_asid_mask = (unsigned long)asidmask;
+               break;
+       default:
+               printk("ILLEGAL ASID mask 0x%x from command line\n", asidmask);
+       }
+       return 1;
+}
+
+__setup("maxvpes=", maxvpes);
+__setup("maxtcs=", maxtcs);
+__setup("ipibufs=", ipibufs);
+__setup("nostlb", stlb_disable);
+__setup("asidmask=", asidmask_set);
+
+/* Enable additional debug checks before going into CPU idle loop */
+#define SMTC_IDLE_HOOK_DEBUG
+
+#ifdef SMTC_IDLE_HOOK_DEBUG
+
+static int hang_trig = 0;
+
+static int __init hangtrig_enable(char *s)
+{
+       hang_trig = 1;
+       return 1;
+}
+
+
+__setup("hangtrig", hangtrig_enable);
+
+#define DEFAULT_BLOCKED_IPI_LIMIT 32
+
+static int timerq_limit = DEFAULT_BLOCKED_IPI_LIMIT;
+
+static int __init tintq(char *str)
+{
+       get_option(&str, &timerq_limit);
+       return 1;
+}
+
+__setup("tintq=", tintq);
+
+int imstuckcount[2][8];
+/* vpemask represents IM/IE bits of per-VPE Status registers, low-to-high */
+int vpemask[2][8] = {{0,1,1,0,0,0,0,1},{0,1,0,0,0,0,0,1}};
+int tcnoprog[NR_CPUS];
+static atomic_t idle_hook_initialized = {0};
+static int clock_hang_reported[NR_CPUS];
+
+#endif /* SMTC_IDLE_HOOK_DEBUG */
+
+/* Initialize shared TLB - the should probably migrate to smtc_setup_cpus() */
+
+void __init sanitize_tlb_entries(void)
+{
+       printk("Deprecated sanitize_tlb_entries() invoked\n");
+}
+
+
+/*
+ * Configure shared TLB - VPC configuration bit must be set by caller
+ */
+
+void smtc_configure_tlb(void)
+{
+       int i,tlbsiz,vpes;
+       unsigned long mvpconf0;
+       unsigned long config1val;
+
+       /* Set up ASID preservation table */
+       for (vpes=0; vpes<MAX_SMTC_TLBS; vpes++) {
+           for(i = 0; i < MAX_SMTC_ASIDS; i++) {
+               smtc_live_asid[vpes][i] = 0;
+           }
+       }
+       mvpconf0 = read_c0_mvpconf0();
+
+       if ((vpes = ((mvpconf0 & MVPCONF0_PVPE)
+                       >> MVPCONF0_PVPE_SHIFT) + 1) > 1) {
+           /* If we have multiple VPEs, try to share the TLB */
+           if ((mvpconf0 & MVPCONF0_TLBS) && !nostlb) {
+               /*
+                * If TLB sizing is programmable, shared TLB
+                * size is the total available complement.
+                * Otherwise, we have to take the sum of all
+                * static VPE TLB entries.
+                */
+               if ((tlbsiz = ((mvpconf0 & MVPCONF0_PTLBE)
+                               >> MVPCONF0_PTLBE_SHIFT)) == 0) {
+                   /*
+                    * If there's more than one VPE, there had better
+                    * be more than one TC, because we need one to bind
+                    * to each VPE in turn to be able to read
+                    * its configuration state!
+                    */
+                   settc(1);
+                   /* Stop the TC from doing anything foolish */
+                   write_tc_c0_tchalt(TCHALT_H);
+                   mips_ihb();
+                   /* No need to un-Halt - that happens later anyway */
+                   for (i=0; i < vpes; i++) {
+                       write_tc_c0_tcbind(i);
+                       /*
+                        * To be 100% sure we're really getting the right
+                        * information, we exit the configuration state
+                        * and do an IHB after each rebinding.
+                        */
+                       write_c0_mvpcontrol(
+                               read_c0_mvpcontrol() & ~ MVPCONTROL_VPC );
+                       mips_ihb();
+                       /*
+                        * Only count if the MMU Type indicated is TLB
+                        */
+                       if(((read_vpe_c0_config() & MIPS_CONF_MT) >> 7) == 1) {
+                               config1val = read_vpe_c0_config1();
+                               tlbsiz += ((config1val >> 25) & 0x3f) + 1;
+                       }
+
+                       /* Put core back in configuration state */
+                       write_c0_mvpcontrol(
+                               read_c0_mvpcontrol() | MVPCONTROL_VPC );
+                       mips_ihb();
+                   }
+               }
+               write_c0_mvpcontrol(read_c0_mvpcontrol() | MVPCONTROL_STLB);
+
+               /*
+                * Setup kernel data structures to use software total,
+                * rather than read the per-VPE Config1 value. The values
+                * for "CPU 0" gets copied to all the other CPUs as part
+                * of their initialization in smtc_cpu_setup().
+                */
+
+               tlbsiz = tlbsiz & 0x3f; /* MIPS32 limits TLB indices to 64 */
+               cpu_data[0].tlbsize = tlbsiz;
+               smtc_status |= SMTC_TLB_SHARED;
+
+               printk("TLB of %d entry pairs shared by %d VPEs\n",
+                       tlbsiz, vpes);
+           } else {
+               printk("WARNING: TLB Not Sharable on SMTC Boot!\n");
+           }
+       }
+}
+
+
+/*
+ * Incrementally build the CPU map out of constituent MIPS MT cores,
+ * using the specified available VPEs and TCs.  Plaform code needs
+ * to ensure that each MIPS MT core invokes this routine on reset,
+ * one at a time(!).
+ *
+ * This version of the build_cpu_map and prepare_cpus routines assumes
+ * that *all* TCs of a MIPS MT core will be used for Linux, and that
+ * they will be spread across *all* available VPEs (to minimise the
+ * loss of efficiency due to exception service serialization).
+ * An improved version would pick up configuration information and
+ * possibly leave some TCs/VPEs as "slave" processors.
+ *
+ * Use c0_MVPConf0 to find out how many TCs are available, setting up
+ * phys_cpu_present_map and the logical/physical mappings.
+ */
+
+int __init mipsmt_build_cpu_map(int start_cpu_slot)
+{
+       int i, ntcs;
+
+       /*
+        * The CPU map isn't actually used for anything at this point,
+        * so it's not clear what else we should do apart from set
+        * everything up so that "logical" = "physical".
+        */
+       ntcs = ((read_c0_mvpconf0() & MVPCONF0_PTC) >> MVPCONF0_PTC_SHIFT) + 1;
+       for (i=start_cpu_slot; i<NR_CPUS && i<ntcs; i++) {
+               cpu_set(i, phys_cpu_present_map);
+               __cpu_number_map[i] = i;
+               __cpu_logical_map[i] = i;
+       }
+       /* Initialize map of CPUs with FPUs */
+       cpus_clear(mt_fpu_cpumask);
+
+       /* One of those TC's is the one booting, and not a secondary... */
+       printk("%i available secondary CPU TC(s)\n", i - 1);
+
+       return i;
+}
+
+/*
+ * Common setup before any secondaries are started
+ * Make sure all CPU's are in a sensible state before we boot any of the
+ * secondaries.
+ *
+ * For MIPS MT "SMTC" operation, we set up all TCs, spread as evenly
+ * as possible across the available VPEs.
+ */
+
+static void smtc_tc_setup(int vpe, int tc, int cpu)
+{
+       settc(tc);
+       write_tc_c0_tchalt(TCHALT_H);
+       mips_ihb();
+       write_tc_c0_tcstatus((read_tc_c0_tcstatus()
+                       & ~(TCSTATUS_TKSU | TCSTATUS_DA | TCSTATUS_IXMT))
+                       | TCSTATUS_A);
+       write_tc_c0_tccontext(0);
+       /* Bind tc to vpe */
+       write_tc_c0_tcbind(vpe);
+       /* In general, all TCs should have the same cpu_data indications */
+       memcpy(&cpu_data[cpu], &cpu_data[0], sizeof(struct cpuinfo_mips));
+       /* For 34Kf, start with TC/CPU 0 as sole owner of single FPU context */
+       if (cpu_data[0].cputype == CPU_34K)
+               cpu_data[cpu].options &= ~MIPS_CPU_FPU;
+       cpu_data[cpu].vpe_id = vpe;
+       cpu_data[cpu].tc_id = tc;
+}
+
+
+void mipsmt_prepare_cpus(void)
+{
+       int i, vpe, tc, ntc, nvpe, tcpervpe, slop, cpu;
+       unsigned long flags;
+       unsigned long val;
+       int nipi;
+       struct smtc_ipi *pipi;
+
+       /* disable interrupts so we can disable MT */
+       local_irq_save(flags);
+       /* disable MT so we can configure */
+       dvpe();
+       dmt();
+
+       freeIPIq.lock = SPIN_LOCK_UNLOCKED;
+
+       /*
+        * We probably don't have as many VPEs as we do SMP "CPUs",
+        * but it's possible - and in any case we'll never use more!
+        */
+       for (i=0; i<NR_CPUS; i++) {
+               IPIQ[i].head = IPIQ[i].tail = NULL;
+               IPIQ[i].lock = SPIN_LOCK_UNLOCKED;
+               IPIQ[i].depth = 0;
+               ipi_timer_latch[i] = 0;
+       }
+
+       /* cpu_data index starts at zero */
+       cpu = 0;
+       cpu_data[cpu].vpe_id = 0;
+       cpu_data[cpu].tc_id = 0;
+       cpu++;
+
+       /* Report on boot-time options */
+       mips_mt_set_cpuoptions ();
+       if (vpelimit > 0)
+               printk("Limit of %d VPEs set\n", vpelimit);
+       if (tclimit > 0)
+               printk("Limit of %d TCs set\n", tclimit);
+       if (nostlb) {
+               printk("Shared TLB Use Inhibited - UNSAFE for Multi-VPE Operation\n");
+       }
+       if (asidmask)
+               printk("ASID mask value override to 0x%x\n", asidmask);
+
+       /* Temporary */
+#ifdef SMTC_IDLE_HOOK_DEBUG
+       if (hang_trig)
+               printk("Logic Analyser Trigger on suspected TC hang\n");
+#endif /* SMTC_IDLE_HOOK_DEBUG */
+
+       /* Put MVPE's into 'configuration state' */
+       write_c0_mvpcontrol( read_c0_mvpcontrol() | MVPCONTROL_VPC );
+
+       val = read_c0_mvpconf0();
+       nvpe = ((val & MVPCONF0_PVPE) >> MVPCONF0_PVPE_SHIFT) + 1;
+       if (vpelimit > 0 && nvpe > vpelimit)
+               nvpe = vpelimit;
+       ntc = ((val & MVPCONF0_PTC) >> MVPCONF0_PTC_SHIFT) + 1;
+       if (ntc > NR_CPUS)
+               ntc = NR_CPUS;
+       if (tclimit > 0 && ntc > tclimit)
+               ntc = tclimit;
+       tcpervpe = ntc / nvpe;
+       slop = ntc % nvpe;      /* Residual TCs, < NVPE */
+
+       /* Set up shared TLB */
+       smtc_configure_tlb();
+
+       for (tc = 0, vpe = 0 ; (vpe < nvpe) && (tc < ntc) ; vpe++) {
+               /*
+                * Set the MVP bits.
+                */
+               settc(tc);
+               write_vpe_c0_vpeconf0(read_vpe_c0_vpeconf0() | VPECONF0_MVP);
+               if (vpe != 0)
+                       printk(", ");
+               printk("VPE %d: TC", vpe);
+               for (i = 0; i < tcpervpe; i++) {
+                       /*
+                        * TC 0 is bound to VPE 0 at reset,
+                        * and is presumably executing this
+                        * code.  Leave it alone!
+                        */
+                       if (tc != 0) {
+                               smtc_tc_setup(vpe,tc, cpu);
+                               cpu++;
+                       }
+                       printk(" %d", tc);
+                       tc++;
+               }
+               if (slop) {
+                       if (tc != 0) {
+                               smtc_tc_setup(vpe,tc, cpu);
+                               cpu++;
+                       }
+                       printk(" %d", tc);
+                       tc++;
+                       slop--;
+               }
+               if (vpe != 0) {
+                       /*
+                        * Clear any stale software interrupts from VPE's Cause
+                        */
+                       write_vpe_c0_cause(0);
+
+                       /*
+                        * Clear ERL/EXL of VPEs other than 0
+                        * and set restricted interrupt enable/mask.
+                        */
+                       write_vpe_c0_status((read_vpe_c0_status()
+                               & ~(ST0_BEV | ST0_ERL | ST0_EXL | ST0_IM))
+                               | (STATUSF_IP0 | STATUSF_IP1 | STATUSF_IP7
+                               | ST0_IE));
+                       /*
+                        * set config to be the same as vpe0,
+                        *  particularly kseg0 coherency alg
+                        */
+                       write_vpe_c0_config(read_c0_config());
+                       /* Clear any pending timer interrupt */
+                       write_vpe_c0_compare(0);
+                       /* Propagate Config7 */
+                       write_vpe_c0_config7(read_c0_config7());
+               }
+               /* enable multi-threading within VPE */
+               write_vpe_c0_vpecontrol(read_vpe_c0_vpecontrol() | VPECONTROL_TE);
+               /* enable the VPE */
+               write_vpe_c0_vpeconf0(read_vpe_c0_vpeconf0() | VPECONF0_VPA);
+       }
+
+       /*
+        * Pull any physically present but unused TCs out of circulation.
+        */
+       while (tc < (((val & MVPCONF0_PTC) >> MVPCONF0_PTC_SHIFT) + 1)) {
+               cpu_clear(tc, phys_cpu_present_map);
+               cpu_clear(tc, cpu_present_map);
+               tc++;
+       }
+
+       /* release config state */
+       write_c0_mvpcontrol( read_c0_mvpcontrol() & ~ MVPCONTROL_VPC );
+
+       printk("\n");
+
+       /* Set up coprocessor affinity CPU mask(s) */
+
+       for (tc = 0; tc < ntc; tc++) {
+               if(cpu_data[tc].options & MIPS_CPU_FPU)
+                       cpu_set(tc, mt_fpu_cpumask);
+       }
+
+       /* set up ipi interrupts... */
+
+       /* If we have multiple VPEs running, set up the cross-VPE interrupt */
+
+       if (nvpe > 1)
+               setup_cross_vpe_interrupts();
+
+       /* Set up queue of free IPI "messages". */
+       nipi = NR_CPUS * IPIBUF_PER_CPU;
+       if (ipibuffers > 0)
+               nipi = ipibuffers;
+
+       pipi = kmalloc(nipi *sizeof(struct smtc_ipi), GFP_KERNEL);
+       if (pipi == NULL)
+               panic("kmalloc of IPI message buffers failed\n");
+       else
+               printk("IPI buffer pool of %d buffers\n", nipi);
+       for (i = 0; i < nipi; i++) {
+               smtc_ipi_nq(&freeIPIq, pipi);
+               pipi++;
+       }
+
+       /* Arm multithreading and enable other VPEs - but all TCs are Halted */
+       emt(EMT_ENABLE);
+       evpe(EVPE_ENABLE);
+       local_irq_restore(flags);
+       /* Initialize SMTC /proc statistics/diagnostics */
+       init_smtc_stats();
+}
+
+
+/*
+ * Setup the PC, SP, and GP of a secondary processor and start it
+ * running!
+ * smp_bootstrap is the place to resume from
+ * __KSTK_TOS(idle) is apparently the stack pointer
+ * (unsigned long)idle->thread_info the gp
+ *
+ */
+void smtc_boot_secondary(int cpu, struct task_struct *idle)
+{
+       extern u32 kernelsp[NR_CPUS];
+       long flags;
+       int mtflags;
+
+       LOCK_MT_PRA();
+       if (cpu_data[cpu].vpe_id != cpu_data[smp_processor_id()].vpe_id) {
+               dvpe();
+       }
+       settc(cpu_data[cpu].tc_id);
+
+       /* pc */
+       write_tc_c0_tcrestart((unsigned long)&smp_bootstrap);
+
+       /* stack pointer */
+       kernelsp[cpu] = __KSTK_TOS(idle);
+       write_tc_gpr_sp(__KSTK_TOS(idle));
+
+       /* global pointer */
+       write_tc_gpr_gp((unsigned long)idle->thread_info);
+
+       smtc_status |= SMTC_MTC_ACTIVE;
+       write_tc_c0_tchalt(0);
+       if (cpu_data[cpu].vpe_id != cpu_data[smp_processor_id()].vpe_id) {
+               evpe(EVPE_ENABLE);
+       }
+       UNLOCK_MT_PRA();
+}
+
+void smtc_init_secondary(void)
+{
+       /*
+        * Start timer on secondary VPEs if necessary.
+        * mips_timer_setup should already have been invoked by init/main
+        * on "boot" TC.  Like per_cpu_trap_init() hack, this assumes that
+        * SMTC init code assigns TCs consdecutively and in ascending order
+        * to across available VPEs.
+        */
+       if(((read_c0_tcbind() & TCBIND_CURTC) != 0)
+       && ((read_c0_tcbind() & TCBIND_CURVPE)
+           != cpu_data[smp_processor_id() - 1].vpe_id)){
+               write_c0_compare (read_c0_count() + mips_hpt_frequency/HZ);
+       }
+
+       local_irq_enable();
+}
+
+void smtc_smp_finish(void)
+{
+       printk("TC %d going on-line as CPU %d\n",
+               cpu_data[smp_processor_id()].tc_id, smp_processor_id());
+}
+
+void smtc_cpus_done(void)
+{
+}
+
+/*
+ * Support for SMTC-optimized driver IRQ registration
+ */
+
+/*
+ * SMTC Kernel needs to manipulate low-level CPU interrupt mask
+ * in do_IRQ. These are passed in setup_irq_smtc() and stored
+ * in this table.
+ */
+
+int setup_irq_smtc(unsigned int irq, struct irqaction * new,
+                       unsigned long hwmask)
+{
+       irq_hwmask[irq] = hwmask;
+
+       return setup_irq(irq, new);
+}
+
+/*
+ * IPI model for SMTC is tricky, because interrupts aren't TC-specific.
+ * Within a VPE one TC can interrupt another by different approaches.
+ * The easiest to get right would probably be to make all TCs except
+ * the target IXMT and set a software interrupt, but an IXMT-based
+ * scheme requires that a handler must run before a new IPI could
+ * be sent, which would break the "broadcast" loops in MIPS MT.
+ * A more gonzo approach within a VPE is to halt the TC, extract
+ * its Restart, Status, and a couple of GPRs, and program the Restart
+ * address to emulate an interrupt.
+ *
+ * Within a VPE, one can be confident that the target TC isn't in
+ * a critical EXL state when halted, since the write to the Halt
+ * register could not have issued on the writing thread if the
+ * halting thread had EXL set. So k0 and k1 of the target TC
+ * can be used by the injection code.  Across VPEs, one can't
+ * be certain that the target TC isn't in a critical exception
+ * state. So we try a two-step process of sending a software
+ * interrupt to the target VPE, which either handles the event
+ * itself (if it was the target) or injects the event within
+ * the VPE.
+ */
+
+void smtc_ipi_qdump(void)
+{
+       int i;
+
+       for (i = 0; i < NR_CPUS ;i++) {
+               printk("IPIQ[%d]: head = 0x%x, tail = 0x%x, depth = %d\n",
+                       i, (unsigned)IPIQ[i].head, (unsigned)IPIQ[i].tail,
+                       IPIQ[i].depth);
+       }
+}
+
+/*
+ * The standard atomic.h primitives don't quite do what we want
+ * here: We need an atomic add-and-return-previous-value (which
+ * could be done with atomic_add_return and a decrement) and an
+ * atomic set/zero-and-return-previous-value (which can't really
+ * be done with the atomic.h primitives). And since this is
+ * MIPS MT, we can assume that we have LL/SC.
+ */
+static __inline__ int atomic_postincrement(unsigned int *pv)
+{
+       unsigned long result;
+
+       unsigned long temp;
+
+       __asm__ __volatile__(
+       "1:     ll      %0, %2                                  \n"
+       "       addu    %1, %0, 1                               \n"
+       "       sc      %1, %2                                  \n"
+       "       beqz    %1, 1b                                  \n"
+       "       sync                                            \n"
+       : "=&r" (result), "=&r" (temp), "=m" (*pv)
+       : "m" (*pv)
+       : "memory");
+
+       return result;
+}
+
+/* No longer used in IPI dispatch, but retained for future recycling */
+
+static __inline__ int atomic_postclear(unsigned int *pv)
+{
+       unsigned long result;
+
+       unsigned long temp;
+
+       __asm__ __volatile__(
+       "1:     ll      %0, %2                                  \n"
+       "       or      %1, $0, $0                              \n"
+       "       sc      %1, %2                                  \n"
+       "       beqz    %1, 1b                                  \n"
+       "       sync                                            \n"
+       : "=&r" (result), "=&r" (temp), "=m" (*pv)
+       : "m" (*pv)
+       : "memory");
+
+       return result;
+}
+
+
+void smtc_send_ipi(int cpu, int type, unsigned int action)
+{
+       int tcstatus;
+       struct smtc_ipi *pipi;
+       long flags;
+       int mtflags;
+
+       if (cpu == smp_processor_id()) {
+               printk("Cannot Send IPI to self!\n");
+               return;
+       }
+       /* Set up a descriptor, to be delivered either promptly or queued */
+       pipi = smtc_ipi_dq(&freeIPIq);
+       if (pipi == NULL) {
+               bust_spinlocks(1);
+               mips_mt_regdump(dvpe());
+               panic("IPI Msg. Buffers Depleted\n");
+       }
+       pipi->type = type;
+       pipi->arg = (void *)action;
+       pipi->dest = cpu;
+       if (cpu_data[cpu].vpe_id != cpu_data[smp_processor_id()].vpe_id) {
+               /* If not on same VPE, enqueue and send cross-VPE interupt */
+               smtc_ipi_nq(&IPIQ[cpu], pipi);
+               LOCK_CORE_PRA();
+               settc(cpu_data[cpu].tc_id);
+               write_vpe_c0_cause(read_vpe_c0_cause() | C_SW1);
+               UNLOCK_CORE_PRA();
+       } else {
+               /*
+                * Not sufficient to do a LOCK_MT_PRA (dmt) here,
+                * since ASID shootdown on the other VPE may
+                * collide with this operation.
+                */
+               LOCK_CORE_PRA();
+               settc(cpu_data[cpu].tc_id);
+               /* Halt the targeted TC */
+               write_tc_c0_tchalt(TCHALT_H);
+               mips_ihb();
+
+               /*
+                * Inspect TCStatus - if IXMT is set, we have to queue
+                * a message. Otherwise, we set up the "interrupt"
+                * of the other TC
+                */
+               tcstatus = read_tc_c0_tcstatus();
+
+               if ((tcstatus & TCSTATUS_IXMT) != 0) {
+                       /*
+                        * Spin-waiting here can deadlock,
+                        * so we queue the message for the target TC.
+                        */
+                       write_tc_c0_tchalt(0);
+                       UNLOCK_CORE_PRA();
+                       /* Try to reduce redundant timer interrupt messages */
+                       if(type == SMTC_CLOCK_TICK) {
+                           if(atomic_postincrement(&ipi_timer_latch[cpu])!=0) {
+                               smtc_ipi_nq(&freeIPIq, pipi);
+                               return;
+                           }
+                       }
+                       smtc_ipi_nq(&IPIQ[cpu], pipi);
+               } else {
+                       post_direct_ipi(cpu, pipi);
+                       write_tc_c0_tchalt(0);
+                       UNLOCK_CORE_PRA();
+               }
+       }
+}
+
+/*
+ * Send IPI message to Halted TC, TargTC/TargVPE already having been set
+ */
+void post_direct_ipi(int cpu, struct smtc_ipi *pipi)
+{
+       struct pt_regs *kstack;
+       unsigned long tcstatus;
+       unsigned long tcrestart;
+       extern u32 kernelsp[NR_CPUS];
+       extern void __smtc_ipi_vector(void);
+
+       /* Extract Status, EPC from halted TC */
+       tcstatus = read_tc_c0_tcstatus();
+       tcrestart = read_tc_c0_tcrestart();
+       /* If TCRestart indicates a WAIT instruction, advance the PC */
+       if ((tcrestart & 0x80000000)
+           && ((*(unsigned int *)tcrestart & 0xfe00003f) == 0x42000020)) {
+               tcrestart += 4;
+       }
+       /*
+        * Save on TC's future kernel stack
+        *
+        * CU bit of Status is indicator that TC was
+        * already running on a kernel stack...
+        */
+       if(tcstatus & ST0_CU0)  {
+               /* Note that this "- 1" is pointer arithmetic */
+               kstack = ((struct pt_regs *)read_tc_gpr_sp()) - 1;
+       } else {
+               kstack = ((struct pt_regs *)kernelsp[cpu]) - 1;
+       }
+
+       kstack->cp0_epc = (long)tcrestart;
+       /* Save TCStatus */
+       kstack->cp0_tcstatus = tcstatus;
+       /* Pass token of operation to be performed kernel stack pad area */
+       kstack->pad0[4] = (unsigned long)pipi;
+       /* Pass address of function to be called likewise */
+       kstack->pad0[5] = (unsigned long)&ipi_decode;
+       /* Set interrupt exempt and kernel mode */
+       tcstatus |= TCSTATUS_IXMT;
+       tcstatus &= ~TCSTATUS_TKSU;
+       write_tc_c0_tcstatus(tcstatus);
+       ehb();
+       /* Set TC Restart address to be SMTC IPI vector */
+       write_tc_c0_tcrestart(__smtc_ipi_vector);
+}
+
+void ipi_resched_interrupt(struct pt_regs *regs)
+{
+       /* Return from interrupt should be enough to cause scheduler check */
+}
+
+
+void ipi_call_interrupt(struct pt_regs *regs)
+{
+       /* Invoke generic function invocation code in smp.c */
+       smp_call_function_interrupt();
+}
+
+void ipi_decode(struct pt_regs *regs, struct smtc_ipi *pipi)
+{
+       void *arg_copy = pipi->arg;
+       int type_copy = pipi->type;
+       int dest_copy = pipi->dest;
+
+       smtc_ipi_nq(&freeIPIq, pipi);
+       switch (type_copy) {
+               case SMTC_CLOCK_TICK:
+                       /* Invoke Clock "Interrupt" */
+                       ipi_timer_latch[dest_copy] = 0;
+#ifdef SMTC_IDLE_HOOK_DEBUG
+                       clock_hang_reported[dest_copy] = 0;
+#endif /* SMTC_IDLE_HOOK_DEBUG */
+                       local_timer_interrupt(0, NULL, regs);
+                       break;
+               case LINUX_SMP_IPI:
+                       switch ((int)arg_copy) {
+                       case SMP_RESCHEDULE_YOURSELF:
+                               ipi_resched_interrupt(regs);
+                               break;
+                       case SMP_CALL_FUNCTION:
+                               ipi_call_interrupt(regs);
+                               break;
+                       default:
+                               printk("Impossible SMTC IPI Argument 0x%x\n",
+                                       (int)arg_copy);
+                               break;
+                       }
+                       break;
+               default:
+                       printk("Impossible SMTC IPI Type 0x%x\n", type_copy);
+                       break;
+       }
+}
+
+void deferred_smtc_ipi(struct pt_regs *regs)
+{
+       struct smtc_ipi *pipi;
+       unsigned long flags;
+/* DEBUG */
+       int q = smp_processor_id();
+
+       /*
+        * Test is not atomic, but much faster than a dequeue,
+        * and the vast majority of invocations will have a null queue.
+        */
+       if(IPIQ[q].head != NULL) {
+               while((pipi = smtc_ipi_dq(&IPIQ[q])) != NULL) {
+                       /* ipi_decode() should be called with interrupts off */
+                       local_irq_save(flags);
+                       ipi_decode(regs, pipi);
+                       local_irq_restore(flags);
+               }
+       }
+}
+
+/*
+ * Send clock tick to all TCs except the one executing the funtion
+ */
+
+void smtc_timer_broadcast(int vpe)
+{
+       int cpu;
+       int myTC = cpu_data[smp_processor_id()].tc_id;
+       int myVPE = cpu_data[smp_processor_id()].vpe_id;
+
+       smtc_cpu_stats[smp_processor_id()].timerints++;
+
+       for_each_online_cpu(cpu) {
+               if (cpu_data[cpu].vpe_id == myVPE &&
+                   cpu_data[cpu].tc_id != myTC)
+                       smtc_send_ipi(cpu, SMTC_CLOCK_TICK, 0);
+       }
+}
+
+/*
+ * Cross-VPE interrupts in the SMTC prototype use "software interrupts"
+ * set via cross-VPE MTTR manipulation of the Cause register. It would be
+ * in some regards preferable to have external logic for "doorbell" hardware
+ * interrupts.
+ */
+
+static int cpu_ipi_irq = MIPSCPU_INT_BASE + MIPS_CPU_IPI_IRQ;
+
+static irqreturn_t ipi_interrupt(int irq, void *dev_idm, struct pt_regs *regs)
+{
+       int my_vpe = cpu_data[smp_processor_id()].vpe_id;
+       int my_tc = cpu_data[smp_processor_id()].tc_id;
+       int cpu;
+       struct smtc_ipi *pipi;
+       unsigned long tcstatus;
+       int sent;
+       long flags;
+       unsigned int mtflags;
+       unsigned int vpflags;
+
+       /*
+        * So long as cross-VPE interrupts are done via
+        * MFTR/MTTR read-modify-writes of Cause, we need
+        * to stop other VPEs whenever the local VPE does
+        * anything similar.
+        */
+       local_irq_save(flags);
+       vpflags = dvpe();
+       clear_c0_cause(0x100 << MIPS_CPU_IPI_IRQ);
+       set_c0_status(0x100 << MIPS_CPU_IPI_IRQ);
+       irq_enable_hazard();
+       evpe(vpflags);
+       local_irq_restore(flags);
+
+       /*
+        * Cross-VPE Interrupt handler: Try to directly deliver IPIs
+        * queued for TCs on this VPE other than the current one.
+        * Return-from-interrupt should cause us to drain the queue
+        * for the current TC, so we ought not to have to do it explicitly here.
+        */
+
+       for_each_online_cpu(cpu) {
+               if (cpu_data[cpu].vpe_id != my_vpe)
+                       continue;
+
+               pipi = smtc_ipi_dq(&IPIQ[cpu]);
+               if (pipi != NULL) {
+                       if (cpu_data[cpu].tc_id != my_tc) {
+                               sent = 0;
+                               LOCK_MT_PRA();
+                               settc(cpu_data[cpu].tc_id);
+                               write_tc_c0_tchalt(TCHALT_H);
+                               mips_ihb();
+                               tcstatus = read_tc_c0_tcstatus();
+                               if ((tcstatus & TCSTATUS_IXMT) == 0) {
+                                       post_direct_ipi(cpu, pipi);
+                                       sent = 1;
+                               }
+                               write_tc_c0_tchalt(0);
+                               UNLOCK_MT_PRA();
+                               if (!sent) {
+                                       smtc_ipi_req(&IPIQ[cpu], pipi);
+                               }
+                       } else {
+                               /*
+                                * ipi_decode() should be called
+                                * with interrupts off
+                                */
+                               local_irq_save(flags);
+                               ipi_decode(regs, pipi);
+                               local_irq_restore(flags);
+                       }
+               }
+       }
+
+       return IRQ_HANDLED;
+}
+
+static void ipi_irq_dispatch(struct pt_regs *regs)
+{
+       do_IRQ(cpu_ipi_irq, regs);
+}
+
+static struct irqaction irq_ipi;
+
+void setup_cross_vpe_interrupts(void)
+{
+       if (!cpu_has_vint)
+               panic("SMTC Kernel requires Vectored Interupt support");
+
+       set_vi_handler(MIPS_CPU_IPI_IRQ, ipi_irq_dispatch);
+
+       irq_ipi.handler = ipi_interrupt;
+       irq_ipi.flags = SA_INTERRUPT;
+       irq_ipi.name = "SMTC_IPI";
+
+       setup_irq_smtc(cpu_ipi_irq, &irq_ipi, (0x100 << MIPS_CPU_IPI_IRQ));
+
+       irq_desc[cpu_ipi_irq].status |= IRQ_PER_CPU;
+}
+
+/*
+ * SMTC-specific hacks invoked from elsewhere in the kernel.
+ */
+
+void smtc_idle_loop_hook(void)
+{
+#ifdef SMTC_IDLE_HOOK_DEBUG
+       int im;
+       int flags;
+       int mtflags;
+       int bit;
+       int vpe;
+       int tc;
+       int hook_ntcs;
+       /*
+        * printk within DMT-protected regions can deadlock,
+        * so buffer diagnostic messages for later output.
+        */
+       char *pdb_msg;
+       char id_ho_db_msg[768]; /* worst-case use should be less than 700 */
+
+       if (atomic_read(&idle_hook_initialized) == 0) { /* fast test */
+               if (atomic_add_return(1, &idle_hook_initialized) == 1) {
+                       int mvpconf0;
+                       /* Tedious stuff to just do once */
+                       mvpconf0 = read_c0_mvpconf0();
+                       hook_ntcs = ((mvpconf0 & MVPCONF0_PTC) >> MVPCONF0_PTC_SHIFT) + 1;
+                       if (hook_ntcs > NR_CPUS)
+                               hook_ntcs = NR_CPUS;
+                       for (tc = 0; tc < hook_ntcs; tc++) {
+                               tcnoprog[tc] = 0;
+                               clock_hang_reported[tc] = 0;
+                       }
+                       for (vpe = 0; vpe < 2; vpe++)
+                               for (im = 0; im < 8; im++)
+                                       imstuckcount[vpe][im] = 0;
+                       printk("Idle loop test hook initialized for %d TCs\n", hook_ntcs);
+                       atomic_set(&idle_hook_initialized, 1000);
+               } else {
+                       /* Someone else is initializing in parallel - let 'em finish */
+                       while (atomic_read(&idle_hook_initialized) < 1000)
+                               ;
+               }
+       }
+
+       /* Have we stupidly left IXMT set somewhere? */
+       if (read_c0_tcstatus() & 0x400) {
+               write_c0_tcstatus(read_c0_tcstatus() & ~0x400);
+               ehb();
+               printk("Dangling IXMT in cpu_idle()\n");
+       }
+
+       /* Have we stupidly left an IM bit turned off? */
+#define IM_LIMIT 2000
+       local_irq_save(flags);
+       mtflags = dmt();
+       pdb_msg = &id_ho_db_msg[0];
+       im = read_c0_status();
+       vpe = cpu_data[smp_processor_id()].vpe_id;
+       for (bit = 0; bit < 8; bit++) {
+               /*
+                * In current prototype, I/O interrupts
+                * are masked for VPE > 0
+                */
+               if (vpemask[vpe][bit]) {
+                       if (!(im & (0x100 << bit)))
+                               imstuckcount[vpe][bit]++;
+                       else
+                               imstuckcount[vpe][bit] = 0;
+                       if (imstuckcount[vpe][bit] > IM_LIMIT) {
+                               set_c0_status(0x100 << bit);
+                               ehb();
+                               imstuckcount[vpe][bit] = 0;
+                               pdb_msg += sprintf(pdb_msg,
+                                       "Dangling IM %d fixed for VPE %d\n", bit,
+                                       vpe);
+                       }
+               }
+       }
+
+       /*
+        * Now that we limit outstanding timer IPIs, check for hung TC
+        */
+       for (tc = 0; tc < NR_CPUS; tc++) {
+               /* Don't check ourself - we'll dequeue IPIs just below */
+               if ((tc != smp_processor_id()) &&
+                   ipi_timer_latch[tc] > timerq_limit) {
+                   if (clock_hang_reported[tc] == 0) {
+                       pdb_msg += sprintf(pdb_msg,
+                               "TC %d looks hung with timer latch at %d\n",
+                               tc, ipi_timer_latch[tc]);
+                       clock_hang_reported[tc]++;
+                       }
+               }
+       }
+       emt(mtflags);
+       local_irq_restore(flags);
+       if (pdb_msg != &id_ho_db_msg[0])
+               printk("CPU%d: %s", smp_processor_id(), id_ho_db_msg);
+#endif /* SMTC_IDLE_HOOK_DEBUG */
+       /*
+        * To the extent that we've ever turned interrupts off,
+        * we may have accumulated deferred IPIs.  This is subtle.
+        * If we use the smtc_ipi_qdepth() macro, we'll get an
+        * exact number - but we'll also disable interrupts
+        * and create a window of failure where a new IPI gets
+        * queued after we test the depth but before we re-enable
+        * interrupts. So long as IXMT never gets set, however,
+        * we should be OK:  If we pick up something and dispatch
+        * it here, that's great. If we see nothing, but concurrent
+        * with this operation, another TC sends us an IPI, IXMT
+        * is clear, and we'll handle it as a real pseudo-interrupt
+        * and not a pseudo-pseudo interrupt.
+        */
+       if (IPIQ[smp_processor_id()].depth > 0) {
+               struct smtc_ipi *pipi;
+               extern void self_ipi(struct smtc_ipi *);
+
+               if ((pipi = smtc_ipi_dq(&IPIQ[smp_processor_id()])) != NULL) {
+                       self_ipi(pipi);
+                       smtc_cpu_stats[smp_processor_id()].selfipis++;
+               }
+       }
+}
+
+void smtc_soft_dump(void)
+{
+       int i;
+
+       printk("Counter Interrupts taken per CPU (TC)\n");
+       for (i=0; i < NR_CPUS; i++) {
+               printk("%d: %ld\n", i, smtc_cpu_stats[i].timerints);
+       }
+       printk("Self-IPI invocations:\n");
+       for (i=0; i < NR_CPUS; i++) {
+               printk("%d: %ld\n", i, smtc_cpu_stats[i].selfipis);
+       }
+       smtc_ipi_qdump();
+       printk("Timer IPI Backlogs:\n");
+       for (i=0; i < NR_CPUS; i++) {
+               printk("%d: %d\n", i, ipi_timer_latch[i]);
+       }
+       printk("%d Recoveries of \"stolen\" FPU\n",
+              atomic_read(&smtc_fpu_recoveries));
+}
+
+
+/*
+ * TLB management routines special to SMTC
+ */
+
+void smtc_get_new_mmu_context(struct mm_struct *mm, unsigned long cpu)
+{
+       unsigned long flags, mtflags, tcstat, prevhalt, asid;
+       int tlb, i;
+
+       /*
+        * It would be nice to be able to use a spinlock here,
+        * but this is invoked from within TLB flush routines
+        * that protect themselves with DVPE, so if a lock is
+         * held by another TC, it'll never be freed.
+        *
+        * DVPE/DMT must not be done with interrupts enabled,
+        * so even so most callers will already have disabled
+        * them, let's be really careful...
+        */
+
+       local_irq_save(flags);
+       if (smtc_status & SMTC_TLB_SHARED) {
+               mtflags = dvpe();
+               tlb = 0;
+       } else {
+               mtflags = dmt();
+               tlb = cpu_data[cpu].vpe_id;
+       }
+       asid = asid_cache(cpu);
+
+       do {
+               if (!((asid += ASID_INC) & ASID_MASK) ) {
+                       if (cpu_has_vtag_icache)
+                               flush_icache_all();
+                       /* Traverse all online CPUs (hack requires contigous range) */
+                       for (i = 0; i < num_online_cpus(); i++) {
+                               /*
+                                * We don't need to worry about our own CPU, nor those of
+                                * CPUs who don't share our TLB.
+                                */
+                               if ((i != smp_processor_id()) &&
+                                   ((smtc_status & SMTC_TLB_SHARED) ||
+                                    (cpu_data[i].vpe_id == cpu_data[cpu].vpe_id))) {
+                                       settc(cpu_data[i].tc_id);
+                                       prevhalt = read_tc_c0_tchalt() & TCHALT_H;
+                                       if (!prevhalt) {
+                                               write_tc_c0_tchalt(TCHALT_H);
+                                               mips_ihb();
+                                       }
+                                       tcstat = read_tc_c0_tcstatus();
+                                       smtc_live_asid[tlb][(tcstat & ASID_MASK)] |= (asiduse)(0x1 << i);
+                                       if (!prevhalt)
+                                               write_tc_c0_tchalt(0);
+                               }
+                       }
+                       if (!asid)              /* fix version if needed */
+                               asid = ASID_FIRST_VERSION;
+                       local_flush_tlb_all();  /* start new asid cycle */
+               }
+       } while (smtc_live_asid[tlb][(asid & ASID_MASK)]);
+
+       /*
+        * SMTC shares the TLB within VPEs and possibly across all VPEs.
+        */
+       for (i = 0; i < num_online_cpus(); i++) {
+               if ((smtc_status & SMTC_TLB_SHARED) ||
+                   (cpu_data[i].vpe_id == cpu_data[cpu].vpe_id))
+                       cpu_context(i, mm) = asid_cache(i) = asid;
+       }
+
+       if (smtc_status & SMTC_TLB_SHARED)
+               evpe(mtflags);
+       else
+               emt(mtflags);
+       local_irq_restore(flags);
+}
+
+/*
+ * Invoked from macros defined in mmu_context.h
+ * which must already have disabled interrupts
+ * and done a DVPE or DMT as appropriate.
+ */
+
+void smtc_flush_tlb_asid(unsigned long asid)
+{
+       int entry;
+       unsigned long ehi;
+
+       entry = read_c0_wired();
+
+       /* Traverse all non-wired entries */
+       while (entry < current_cpu_data.tlbsize) {
+               write_c0_index(entry);
+               ehb();
+               tlb_read();
+               ehb();
+               ehi = read_c0_entryhi();
+               if((ehi & ASID_MASK) == asid) {
+                   /*
+                    * Invalidate only entries with specified ASID,
+                    * makiing sure all entries differ.
+                    */
+                   write_c0_entryhi(CKSEG0 + (entry << (PAGE_SHIFT + 1)));
+                   write_c0_entrylo0(0);
+                   write_c0_entrylo1(0);
+                   mtc0_tlbw_hazard();
+                   tlb_write_indexed();
+               }
+               entry++;
+       }
+       write_c0_index(PARKED_INDEX);
+       tlbw_use_hazard();
+}
+
+/*
+ * Support for single-threading cache flush operations.
+ */
+
+int halt_state_save[NR_CPUS];
+
+/*
+ * To really, really be sure that nothing is being done
+ * by other TCs, halt them all.  This code assumes that
+ * a DVPE has already been done, so while their Halted
+ * state is theoretically architecturally unstable, in
+ * practice, it's not going to change while we're looking
+ * at it.
+ */
+
+void smtc_cflush_lockdown(void)
+{
+       int cpu;
+
+       for_each_online_cpu(cpu) {
+               if (cpu != smp_processor_id()) {
+                       settc(cpu_data[cpu].tc_id);
+                       halt_state_save[cpu] = read_tc_c0_tchalt();
+                       write_tc_c0_tchalt(TCHALT_H);
+               }
+       }
+       mips_ihb();
+}
+
+/* It would be cheating to change the cpu_online states during a flush! */
+
+void smtc_cflush_release(void)
+{
+       int cpu;
+
+       /*
+        * Start with a hazard barrier to ensure
+        * that all CACHE ops have played through.
+        */
+       mips_ihb();
+
+       for_each_online_cpu(cpu) {
+               if (cpu != smp_processor_id()) {
+                       settc(cpu_data[cpu].tc_id);
+                       write_tc_c0_tchalt(halt_state_save[cpu]);
+               }
+       }
+       mips_ihb();
+}
index 5e51a2d8f3f0712072e59a2a53f01a46b9880453..13ff4da598cdfbcff3b2d34677c0e89cd3b55e28 100644 (file)
@@ -116,8 +116,7 @@ static void c0_timer_ack(void)
        write_c0_compare(expirelo);
 
        /* Check to see if we have missed any timer interrupts.  */
-       count = read_c0_count();
-       if ((count - expirelo) < 0x7fffffff) {
+       while (((count = read_c0_count()) - expirelo) < 0x7fffffff) {
                /* missed_timer_count++; */
                expirelo = count + cycles_per_jiffy;
                write_c0_compare(expirelo);
index bed0eb6cf55d58f7178ecf0f550e05c8a7ac6c47..4901f0a37fca2b3ddb2de93dcf998873b10e6643 100644 (file)
@@ -42,6 +42,7 @@
 #include <asm/watch.h>
 #include <asm/types.h>
 
+extern asmlinkage void handle_int(void);
 extern asmlinkage void handle_tlbm(void);
 extern asmlinkage void handle_tlbl(void);
 extern asmlinkage void handle_tlbs(void);
@@ -279,9 +280,16 @@ static DEFINE_SPINLOCK(die_lock);
 NORET_TYPE void ATTRIB_NORET die(const char * str, struct pt_regs * regs)
 {
        static int die_counter;
+#ifdef CONFIG_MIPS_MT_SMTC
+       unsigned long dvpret = dvpe();
+#endif /* CONFIG_MIPS_MT_SMTC */
 
        console_verbose();
        spin_lock_irq(&die_lock);
+       bust_spinlocks(1);
+#ifdef CONFIG_MIPS_MT_SMTC
+       mips_mt_regdump(dvpret);
+#endif /* CONFIG_MIPS_MT_SMTC */
        printk("%s[#%d]:\n", str, ++die_counter);
        show_registers(regs);
        spin_unlock_irq(&die_lock);
@@ -750,12 +758,43 @@ asmlinkage void do_cpu(struct pt_regs *regs)
                                                &current->thread.fpu.soft);
                        if (sig)
                                force_sig(sig, current);
+#ifdef CONFIG_MIPS_MT_FPAFF
+                       else {
+                       /*
+                        * MIPS MT processors may have fewer FPU contexts
+                        * than CPU threads. If we've emulated more than
+                        * some threshold number of instructions, force
+                        * migration to a "CPU" that has FP support.
+                        */
+                        if(mt_fpemul_threshold > 0
+                        && ((current->thread.emulated_fp++
+                           > mt_fpemul_threshold))) {
+                         /*
+                          * If there's no FPU present, or if the
+                          * application has already restricted
+                          * the allowed set to exclude any CPUs
+                          * with FPUs, we'll skip the procedure.
+                          */
+                         if (cpus_intersects(current->cpus_allowed,
+                                               mt_fpu_cpumask)) {
+                           cpumask_t tmask;
+
+                           cpus_and(tmask,
+                                       current->thread.user_cpus_allowed,
+                                       mt_fpu_cpumask);
+                           set_cpus_allowed(current, tmask);
+                           current->thread.mflags |= MF_FPUBOUND;
+                         }
+                        }
+                       }
+#endif /* CONFIG_MIPS_MT_FPAFF */
                }
 
                return;
 
        case 2:
        case 3:
+               die_if_kernel("do_cpu invoked from kernel context!", regs);
                break;
        }
 
@@ -793,6 +832,36 @@ asmlinkage void do_mcheck(struct pt_regs *regs)
 
 asmlinkage void do_mt(struct pt_regs *regs)
 {
+       int subcode;
+
+       die_if_kernel("MIPS MT Thread exception in kernel", regs);
+
+       subcode = (read_vpe_c0_vpecontrol() & VPECONTROL_EXCPT)
+                       >> VPECONTROL_EXCPT_SHIFT;
+       switch (subcode) {
+       case 0:
+               printk(KERN_ERR "Thread Underflow\n");
+               break;
+       case 1:
+               printk(KERN_ERR "Thread Overflow\n");
+               break;
+       case 2:
+               printk(KERN_ERR "Invalid YIELD Qualifier\n");
+               break;
+       case 3:
+               printk(KERN_ERR "Gating Storage Exception\n");
+               break;
+       case 4:
+               printk(KERN_ERR "YIELD Scheduler Exception\n");
+               break;
+       case 5:
+               printk(KERN_ERR "Gating Storage Schedulier Exception\n");
+               break;
+       default:
+               printk(KERN_ERR "*** UNKNOWN THREAD EXCEPTION %d ***\n",
+                       subcode);
+               break;
+       }
        die_if_kernel("MIPS MT Thread exception in kernel", regs);
 
        force_sig(SIGILL, current);
@@ -928,7 +997,15 @@ void ejtag_exception_handler(struct pt_regs *regs)
  */
 void nmi_exception_handler(struct pt_regs *regs)
 {
+#ifdef CONFIG_MIPS_MT_SMTC
+       unsigned long dvpret = dvpe();
+       bust_spinlocks(1);
+       printk("NMI taken!!!!\n");
+       mips_mt_regdump(dvpret);
+#else
+       bust_spinlocks(1);
        printk("NMI taken!!!!\n");
+#endif /* CONFIG_MIPS_MT_SMTC */
        die("NMI", regs);
        while(1) ;
 }
@@ -960,27 +1037,29 @@ void *set_except_vector(int n, void *addr)
 
 #ifdef CONFIG_CPU_MIPSR2
 /*
- * Shadow register allocation
+ * MIPSR2 shadow register set allocation
  * FIXME: SMP...
  */
 
-/* MIPSR2 shadow register sets */
-struct shadow_registers {
-       spinlock_t sr_lock;     /*  */
-       int sr_supported;       /* Number of shadow register sets supported */
-       int sr_allocated;       /* Bitmap of allocated shadow registers */
+static struct shadow_registers {
+       /*
+        * Number of shadow register sets supported
+        */
+       unsigned long sr_supported;
+       /*
+        * Bitmap of allocated shadow registers
+        */
+       unsigned long sr_allocated;
 } shadow_registers;
 
-void mips_srs_init(void)
+static void mips_srs_init(void)
 {
 #ifdef CONFIG_CPU_MIPSR2_SRS
        shadow_registers.sr_supported = ((read_c0_srsctl() >> 26) & 0x0f) + 1;
-       printk ("%d MIPSR2 register sets available\n", shadow_registers.sr_supported);
-#else
-       shadow_registers.sr_supported = 1;
+       printk(KERN_INFO "%d MIPSR2 register sets available\n",
+              shadow_registers.sr_supported);
 #endif
        shadow_registers.sr_allocated = 1;      /* Set 0 used by kernel */
-       spin_lock_init(&shadow_registers.sr_lock);
 }
 
 int mips_srs_max(void)
@@ -988,38 +1067,30 @@ int mips_srs_max(void)
        return shadow_registers.sr_supported;
 }
 
-int mips_srs_alloc (void)
+int mips_srs_alloc(void)
 {
        struct shadow_registers *sr = &shadow_registers;
-       unsigned long flags;
        int set;
 
-       spin_lock_irqsave(&sr->sr_lock, flags);
+again:
+       set = find_first_zero_bit(&sr->sr_allocated, sr->sr_supported);
+       if (set >= sr->sr_supported)
+               return -1;
 
-       for (set = 0; set < sr->sr_supported; set++) {
-               if ((sr->sr_allocated & (1 << set)) == 0) {
-                       sr->sr_allocated |= 1 << set;
-                       spin_unlock_irqrestore(&sr->sr_lock, flags);
-                       return set;
-               }
-       }
+       if (test_and_set_bit(set, &sr->sr_allocated))
+               goto again;
 
-       /* None available */
-       spin_unlock_irqrestore(&sr->sr_lock, flags);
-       return -1;
+       return set;
 }
 
-void mips_srs_free (int set)
+void mips_srs_free(int set)
 {
        struct shadow_registers *sr = &shadow_registers;
-       unsigned long flags;
 
-       spin_lock_irqsave(&sr->sr_lock, flags);
-       sr->sr_allocated &= ~(1 << set);
-       spin_unlock_irqrestore(&sr->sr_lock, flags);
+       clear_bit(set, &sr->sr_allocated);
 }
 
-void *set_vi_srs_handler (int n, void *addr, int srs)
+static void *set_vi_srs_handler(int n, void *addr, int srs)
 {
        unsigned long handler;
        unsigned long old_handler = vi_handlers[n];
@@ -1032,8 +1103,7 @@ void *set_vi_srs_handler (int n, void *addr, int srs)
        if (addr == NULL) {
                handler = (unsigned long) do_default_vi;
                srs = 0;
-       }
-       else
+       } else
                handler = (unsigned long) addr;
        vi_handlers[n] = (unsigned long) addr;
 
@@ -1045,8 +1115,7 @@ void *set_vi_srs_handler (int n, void *addr, int srs)
        if (cpu_has_veic) {
                if (board_bind_eic_interrupt)
                        board_bind_eic_interrupt (n, srs);
-       }
-       else if (cpu_has_vint) {
+       } else if (cpu_has_vint) {
                /* SRSMap is only defined if shadow sets are implemented */
                if (mips_srs_max() > 1)
                        change_c0_srsmap (0xf << n*4, srs << n*4);
@@ -1060,6 +1129,15 @@ void *set_vi_srs_handler (int n, void *addr, int srs)
 
                extern char except_vec_vi, except_vec_vi_lui;
                extern char except_vec_vi_ori, except_vec_vi_end;
+#ifdef CONFIG_MIPS_MT_SMTC
+               /*
+                * We need to provide the SMTC vectored interrupt handler
+                * not only with the address of the handler, but with the
+                * Status.IM bit to be masked before going there.
+                */
+               extern char except_vec_vi_mori;
+               const int mori_offset = &except_vec_vi_mori - &except_vec_vi;
+#endif /* CONFIG_MIPS_MT_SMTC */
                const int handler_len = &except_vec_vi_end - &except_vec_vi;
                const int lui_offset = &except_vec_vi_lui - &except_vec_vi;
                const int ori_offset = &except_vec_vi_ori - &except_vec_vi;
@@ -1073,6 +1151,12 @@ void *set_vi_srs_handler (int n, void *addr, int srs)
                }
 
                memcpy (b, &except_vec_vi, handler_len);
+#ifdef CONFIG_MIPS_MT_SMTC
+               if (n > 7)
+                       printk("Vector index %d exceeds SMTC maximum\n", n);
+               w = (u32 *)(b + mori_offset);
+               *w = (*w & 0xffff0000) | (0x100 << n);
+#endif /* CONFIG_MIPS_MT_SMTC */
                w = (u32 *)(b + lui_offset);
                *w = (*w & 0xffff0000) | (((u32)handler >> 16) & 0xffff);
                w = (u32 *)(b + ori_offset);
@@ -1095,9 +1179,9 @@ void *set_vi_srs_handler (int n, void *addr, int srs)
        return (void *)old_handler;
 }
 
-void *set_vi_handler (int n, void *addr)
+void *set_vi_handler(int n, void *addr)
 {
-       return set_vi_srs_handler (n, addr, 0);
+       return set_vi_srs_handler(n, addr, 0);
 }
 #endif
 
@@ -1113,8 +1197,29 @@ extern asmlinkage int _restore_fp_context(struct sigcontext *sc);
 extern asmlinkage int fpu_emulator_save_context(struct sigcontext *sc);
 extern asmlinkage int fpu_emulator_restore_context(struct sigcontext *sc);
 
+#ifdef CONFIG_SMP
+static int smp_save_fp_context(struct sigcontext *sc)
+{
+       return cpu_has_fpu
+              ? _save_fp_context(sc)
+              : fpu_emulator_save_context(sc);
+}
+
+static int smp_restore_fp_context(struct sigcontext *sc)
+{
+       return cpu_has_fpu
+              ? _restore_fp_context(sc)
+              : fpu_emulator_restore_context(sc);
+}
+#endif
+
 static inline void signal_init(void)
 {
+#ifdef CONFIG_SMP
+       /* For now just do the cpu_has_fpu check when the functions are invoked */
+       save_fp_context = smp_save_fp_context;
+       restore_fp_context = smp_restore_fp_context;
+#else
        if (cpu_has_fpu) {
                save_fp_context = _save_fp_context;
                restore_fp_context = _restore_fp_context;
@@ -1122,6 +1227,7 @@ static inline void signal_init(void)
                save_fp_context = fpu_emulator_save_context;
                restore_fp_context = fpu_emulator_restore_context;
        }
+#endif
 }
 
 #ifdef CONFIG_MIPS32_COMPAT
@@ -1158,6 +1264,20 @@ void __init per_cpu_trap_init(void)
 {
        unsigned int cpu = smp_processor_id();
        unsigned int status_set = ST0_CU0;
+#ifdef CONFIG_MIPS_MT_SMTC
+       int secondaryTC = 0;
+       int bootTC = (cpu == 0);
+
+       /*
+        * Only do per_cpu_trap_init() for first TC of Each VPE.
+        * Note that this hack assumes that the SMTC init code
+        * assigns TCs consecutively and in ascending order.
+        */
+
+       if (((read_c0_tcbind() & TCBIND_CURTC) != 0) &&
+           ((read_c0_tcbind() & TCBIND_CURVPE) == cpu_data[cpu - 1].vpe_id))
+               secondaryTC = 1;
+#endif /* CONFIG_MIPS_MT_SMTC */
 
        /*
         * Disable coprocessors and select 32-bit or 64-bit addressing
@@ -1180,6 +1300,10 @@ void __init per_cpu_trap_init(void)
        write_c0_hwrena (0x0000000f); /* Allow rdhwr to all registers */
 #endif
 
+#ifdef CONFIG_MIPS_MT_SMTC
+       if (!secondaryTC) {
+#endif /* CONFIG_MIPS_MT_SMTC */
+
        /*
         * Interrupt handling.
         */
@@ -1196,6 +1320,9 @@ void __init per_cpu_trap_init(void)
                } else
                        set_c0_cause(CAUSEF_IV);
        }
+#ifdef CONFIG_MIPS_MT_SMTC
+       }
+#endif /* CONFIG_MIPS_MT_SMTC */
 
        cpu_data[cpu].asid_cache = ASID_FIRST_VERSION;
        TLBMISS_HANDLER_SETUP();
@@ -1205,8 +1332,14 @@ void __init per_cpu_trap_init(void)
        BUG_ON(current->mm);
        enter_lazy_tlb(&init_mm, current);
 
-       cpu_cache_init();
-       tlb_init();
+#ifdef CONFIG_MIPS_MT_SMTC
+       if (bootTC) {
+#endif /* CONFIG_MIPS_MT_SMTC */
+               cpu_cache_init();
+               tlb_init();
+#ifdef CONFIG_MIPS_MT_SMTC
+       }
+#endif /* CONFIG_MIPS_MT_SMTC */
 }
 
 /* Install CPU exception handler */
@@ -1278,7 +1411,7 @@ void __init trap_init(void)
        if (cpu_has_veic || cpu_has_vint) {
                int nvec = cpu_has_veic ? 64 : 8;
                for (i = 0; i < nvec; i++)
-                       set_vi_handler (i, NULL);
+                       set_vi_handler(i, NULL);
        }
        else if (cpu_has_divec)
                set_handler(0x200, &except_vec4, 0x8);
@@ -1297,6 +1430,7 @@ void __init trap_init(void)
        if (board_be_init)
                board_be_init();
 
+       set_except_vector(0, handle_int);
        set_except_vector(1, handle_tlbm);
        set_except_vector(2, handle_tlbl);
        set_except_vector(3, handle_tlbs);
index 2ad0cedf29fee2236c32d7e1ec1cd3ac34b0b0ad..14fa00e3cdfa6007332e58fbd84fc9eba3c4d1ac 100644 (file)
@@ -2,7 +2,7 @@
 #include <asm/asm-offsets.h>
 #include <asm-generic/vmlinux.lds.h>
 
-#undef mips            /* CPP really sucks for this job  */
+#undef mips
 #define mips mips
 OUTPUT_ARCH(mips)
 ENTRY(kernel_entry)
index ae83b755cf4aae68c24fe36b80f339665f9d42fd..80ffaa6d50ad0fc9b9d62474bbc62743dc9158f6 100644 (file)
@@ -13,7 +13,6 @@
  *  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.,
  *  59 Temple Place - Suite 330, Boston MA 02111-1307, USA.
- *
  */
 
 /*
  *
  * To load and run, simply cat a SP 'program file' to /dev/vpe1.
  * i.e cat spapp >/dev/vpe1.
- *
- * You'll need to have the following device files.
- * mknod /dev/vpe0 c 63 0
- * mknod /dev/vpe1 c 63 1
  */
+
 #include <linux/config.h>
 #include <linux/kernel.h>
 #include <linux/module.h>
@@ -55,6 +51,8 @@
 #include <asm/cpu.h>
 #include <asm/processor.h>
 #include <asm/system.h>
+#include <asm/vpe.h>
+#include <asm/kspd.h>
 
 typedef void *vpe_handle;
 
@@ -68,6 +66,11 @@ typedef void *vpe_handle;
 static char module_name[] = "vpe";
 static int major;
 
+#ifdef CONFIG_MIPS_APSP_KSPD
+ static struct kspd_notifications kspd_events;
+static int kspd_events_reqd = 0;
+#endif
+
 /* grab the likely amount of memory we will need. */
 #ifdef CONFIG_MIPS_VPE_LOADER_TOM
 #define P_SIZE (2 * 1024 * 1024)
@@ -76,7 +79,10 @@ static int major;
 #define P_SIZE (256 * 1024)
 #endif
 
+extern unsigned long physical_memsize;
+
 #define MAX_VPES 16
+#define VPE_PATH_MAX 256
 
 enum vpe_state {
        VPE_STATE_UNUSED = 0,
@@ -102,6 +108,8 @@ struct vpe {
        unsigned long len;
        char *pbuffer;
        unsigned long plen;
+       unsigned int uid, gid;
+       char cwd[VPE_PATH_MAX];
 
        unsigned long __start;
 
@@ -113,6 +121,9 @@ struct vpe {
 
        /* shared symbol address */
        void *shared_ptr;
+
+       /* the list of who wants to know when something major happens */
+       struct list_head notify;
 };
 
 struct tc {
@@ -138,7 +149,7 @@ struct vpecontrol_ {
 } vpecontrol;
 
 static void release_progmem(void *ptr);
-static void dump_vpe(struct vpe * v);
+/* static __attribute_used__ void dump_vpe(struct vpe * v); */
 extern void save_gp_address(unsigned int secbase, unsigned int rel);
 
 /* get the vpe associated with this minor */
@@ -146,12 +157,14 @@ struct vpe *get_vpe(int minor)
 {
        struct vpe *v;
 
+       if (!cpu_has_mipsmt)
+               return NULL;
+
        list_for_each_entry(v, &vpecontrol.vpe_list, list) {
                if (v->minor == minor)
                        return v;
        }
 
-       printk(KERN_DEBUG "VPE: get_vpe minor %d not found\n", minor);
        return NULL;
 }
 
@@ -165,8 +178,6 @@ struct tc *get_tc(int index)
                        return t;
        }
 
-       printk(KERN_DEBUG "VPE: get_tc index %d not found\n", index);
-
        return NULL;
 }
 
@@ -179,8 +190,6 @@ struct tc *get_tc_unused(void)
                        return t;
        }
 
-       printk(KERN_DEBUG "VPE: All TC's are in use\n");
-
        return NULL;
 }
 
@@ -190,13 +199,13 @@ struct vpe *alloc_vpe(int minor)
        struct vpe *v;
 
        if ((v = kzalloc(sizeof(struct vpe), GFP_KERNEL)) == NULL) {
-               printk(KERN_WARNING "VPE: alloc_vpe no mem\n");
                return NULL;
        }
 
        INIT_LIST_HEAD(&v->tc);
        list_add_tail(&v->list, &vpecontrol.vpe_list);
 
+       INIT_LIST_HEAD(&v->notify);
        v->minor = minor;
        return v;
 }
@@ -207,7 +216,6 @@ struct tc *alloc_tc(int index)
        struct tc *t;
 
        if ((t = kzalloc(sizeof(struct tc), GFP_KERNEL)) == NULL) {
-               printk(KERN_WARNING "VPE: alloc_tc no mem\n");
                return NULL;
        }
 
@@ -236,20 +244,16 @@ void dump_mtregs(void)
        printk("config3 0x%lx MT %ld\n", val,
               (val & CONFIG3_MT) >> CONFIG3_MT_SHIFT);
 
-       val = read_c0_mvpconf0();
-       printk("mvpconf0 0x%lx, PVPE %ld PTC %ld M %ld\n", val,
-              (val & MVPCONF0_PVPE) >> MVPCONF0_PVPE_SHIFT,
-              val & MVPCONF0_PTC, (val & MVPCONF0_M) >> MVPCONF0_M_SHIFT);
-
        val = read_c0_mvpcontrol();
        printk("MVPControl 0x%lx, STLB %ld VPC %ld EVP %ld\n", val,
               (val & MVPCONTROL_STLB) >> MVPCONTROL_STLB_SHIFT,
               (val & MVPCONTROL_VPC) >> MVPCONTROL_VPC_SHIFT,
               (val & MVPCONTROL_EVP));
 
-       val = read_c0_vpeconf0();
-       printk("VPEConf0 0x%lx MVP %ld\n", val,
-              (val & VPECONF0_MVP) >> VPECONF0_MVP_SHIFT);
+       val = read_c0_mvpconf0();
+       printk("mvpconf0 0x%lx, PVPE %ld PTC %ld M %ld\n", val,
+              (val & MVPCONF0_PVPE) >> MVPCONF0_PVPE_SHIFT,
+              val & MVPCONF0_PTC, (val & MVPCONF0_M) >> MVPCONF0_M_SHIFT);
 }
 
 /* Find some VPE program space  */
@@ -354,9 +358,9 @@ static int apply_r_mips_gprel16(struct module *me, uint32_t *location,
        }
 
        if( (rel > 32768) || (rel < -32768) ) {
-               printk(KERN_ERR
-                      "apply_r_mips_gprel16: relative address out of range 0x%x %d\n",
-                      rel, rel);
+               printk(KERN_DEBUG "VPE loader: apply_r_mips_gprel16: "
+                      "relative address 0x%x out of range of gp register\n",
+                      rel);
                return -ENOEXEC;
        }
 
@@ -374,8 +378,8 @@ static int apply_r_mips_pc16(struct module *me, uint32_t *location,
        rel -= 1;               // and one instruction less due to the branch delay slot.
 
        if( (rel > 32768) || (rel < -32768) ) {
-               printk(KERN_ERR
-                      "apply_r_mips_pc16: relative address out of range 0x%x\n", rel);
+               printk(KERN_DEBUG "VPE loader: "
+                      "apply_r_mips_pc16: relative address out of range 0x%x\n", rel);
                return -ENOEXEC;
        }
 
@@ -396,7 +400,8 @@ static int apply_r_mips_26(struct module *me, uint32_t *location,
                           Elf32_Addr v)
 {
        if (v % 4) {
-               printk(KERN_ERR "module %s: dangerous relocation mod4\n", me->name);
+               printk(KERN_DEBUG "VPE loader: apply_r_mips_26 "
+                      " unaligned relocation\n");
                return -ENOEXEC;
        }
 
@@ -459,12 +464,13 @@ static int apply_r_mips_lo16(struct module *me, uint32_t *location,
                        /*
                         * The value for the HI16 had best be the same.
                         */
-                       if (v != l->value) {
-                               printk("%d != %d\n", v, l->value);
-                               goto out_danger;
+                       if (v != l->value) {
+                               printk(KERN_DEBUG "VPE loader: "
+                                      "apply_r_mips_lo16/hi16:         "
+                                      "inconsistent value information\n");
+                               return -ENOEXEC;
                        }
 
-
                        /*
                         * Do the HI16 relocation.  Note that we actually don't
                         * need to know anything about the LO16 itself, except
@@ -500,11 +506,6 @@ static int apply_r_mips_lo16(struct module *me, uint32_t *location,
        *location = insnlo;
 
        return 0;
-
-out_danger:
-       printk(KERN_ERR "module %s: dangerous " "relocation\n", me->name);
-
-       return -ENOEXEC;
 }
 
 static int (*reloc_handlers[]) (struct module *me, uint32_t *location,
@@ -518,6 +519,15 @@ static int (*reloc_handlers[]) (struct module *me, uint32_t *location,
        [R_MIPS_PC16] = apply_r_mips_pc16
 };
 
+static char *rstrs[] = {
+       [R_MIPS_NONE]   = "MIPS_NONE",
+       [R_MIPS_32]     = "MIPS_32",
+       [R_MIPS_26]     = "MIPS_26",
+       [R_MIPS_HI16]   = "MIPS_HI16",
+       [R_MIPS_LO16]   = "MIPS_LO16",
+       [R_MIPS_GPREL16] = "MIPS_GPREL16",
+       [R_MIPS_PC16] = "MIPS_PC16"
+};
 
 int apply_relocations(Elf32_Shdr *sechdrs,
                      const char *strtab,
@@ -552,15 +562,13 @@ int apply_relocations(Elf32_Shdr *sechdrs,
 
                res = reloc_handlers[ELF32_R_TYPE(r_info)](me, location, v);
                if( res ) {
-                       printk(KERN_DEBUG
-                              "relocation error 0x%x sym refer <%s> value 0x%x "
-                              "type 0x%x r_info 0x%x\n",
-                              (unsigned int)location, strtab + sym->st_name, v,
-                              r_info, ELF32_R_TYPE(r_info));
-               }
-
-               if (res)
+                       char *r = rstrs[ELF32_R_TYPE(r_info)];
+                       printk(KERN_WARNING "VPE loader: .text+0x%x "
+                              "relocation type %s for symbol \"%s\" failed\n",
+                              rel[i].r_offset, r ? r : "UNKNOWN",
+                              strtab + sym->st_name);
                        return res;
+               }
        }
 
        return 0;
@@ -576,7 +584,7 @@ void save_gp_address(unsigned int secbase, unsigned int rel)
 
 
 /* Change all symbols so that sh_value encodes the pointer directly. */
-static int simplify_symbols(Elf_Shdr * sechdrs,
+static void simplify_symbols(Elf_Shdr * sechdrs,
                            unsigned int symindex,
                            const char *strtab,
                            const char *secstrings,
@@ -585,18 +593,21 @@ static int simplify_symbols(Elf_Shdr * sechdrs,
        Elf_Sym *sym = (void *)sechdrs[symindex].sh_addr;
        unsigned long secbase, bssbase = 0;
        unsigned int i, n = sechdrs[symindex].sh_size / sizeof(Elf_Sym);
-       int ret = 0, size;
+       int size;
 
        /* find the .bss section for COMMON symbols */
        for (i = 0; i < nsecs; i++) {
-               if (strncmp(secstrings + sechdrs[i].sh_name, ".bss", 4) == 0)
+               if (strncmp(secstrings + sechdrs[i].sh_name, ".bss", 4) == 0) {
                        bssbase = sechdrs[i].sh_addr;
+                       break;
+               }
        }
 
        for (i = 1; i < n; i++) {
                switch (sym[i].st_shndx) {
                case SHN_COMMON:
-                       /* Allocate space for the symbol in the .bss section. st_value is currently size.
+                       /* Allocate space for the symbol in the .bss section.
+                          st_value is currently size.
                           We want it to have the address of the symbol. */
 
                        size = sym[i].st_value;
@@ -614,11 +625,9 @@ static int simplify_symbols(Elf_Shdr * sechdrs,
                        break;
 
                case SHN_MIPS_SCOMMON:
-
-                       printk(KERN_DEBUG
-                              "simplify_symbols: ignoring SHN_MIPS_SCOMMON symbol <%s> st_shndx %d\n",
-                              strtab + sym[i].st_name, sym[i].st_shndx);
-
+                       printk(KERN_DEBUG "simplify_symbols: ignoring SHN_MIPS_SCOMMON"
+                              "symbol <%s> st_shndx %d\n", strtab + sym[i].st_name,
+                              sym[i].st_shndx);
                        // .sbss section
                        break;
 
@@ -632,10 +641,7 @@ static int simplify_symbols(Elf_Shdr * sechdrs,
                        sym[i].st_value += secbase;
                        break;
                }
-
        }
-
-       return ret;
 }
 
 #ifdef DEBUG_ELFLOADER
@@ -655,9 +661,26 @@ static void dump_elfsymbols(Elf_Shdr * sechdrs, unsigned int symindex,
 
 static void dump_tc(struct tc *t)
 {
-       printk(KERN_WARNING "VPE: TC index %d TCStatus 0x%lx halt 0x%lx\n",
-              t->index, read_tc_c0_tcstatus(), read_tc_c0_tchalt());
-       printk(KERN_WARNING "VPE: tcrestart 0x%lx\n", read_tc_c0_tcrestart());
+       unsigned long val;
+
+       settc(t->index);
+       printk(KERN_DEBUG "VPE loader: TC index %d targtc %ld "
+              "TCStatus 0x%lx halt 0x%lx\n",
+              t->index, read_c0_vpecontrol() & VPECONTROL_TARGTC,
+              read_tc_c0_tcstatus(), read_tc_c0_tchalt());
+
+       printk(KERN_DEBUG " tcrestart 0x%lx\n", read_tc_c0_tcrestart());
+       printk(KERN_DEBUG " tcbind 0x%lx\n", read_tc_c0_tcbind());
+
+       val = read_c0_vpeconf0();
+       printk(KERN_DEBUG " VPEConf0 0x%lx MVP %ld\n", val,
+              (val & VPECONF0_MVP) >> VPECONF0_MVP_SHIFT);
+
+       printk(KERN_DEBUG " c0 status 0x%lx\n", read_vpe_c0_status());
+       printk(KERN_DEBUG " c0 cause 0x%lx\n", read_vpe_c0_cause());
+
+       printk(KERN_DEBUG " c0 badvaddr 0x%lx\n", read_vpe_c0_badvaddr());
+       printk(KERN_DEBUG " c0 epc 0x%lx\n", read_vpe_c0_epc());
 }
 
 static void dump_tclist(void)
@@ -672,96 +695,108 @@ static void dump_tclist(void)
 /* We are prepared so configure and start the VPE... */
 int vpe_run(struct vpe * v)
 {
-       unsigned long val;
+       struct vpe_notifications *n;
+       unsigned long val, dmt_flag;
        struct tc *t;
 
        /* check we are the Master VPE */
        val = read_c0_vpeconf0();
        if (!(val & VPECONF0_MVP)) {
                printk(KERN_WARNING
-                      "VPE: only Master VPE's are allowed to configure MT\n");
+                      "VPE loader: only Master VPE's are allowed to configure MT\n");
                return -1;
        }
 
        /* disable MT (using dvpe) */
        dvpe();
 
+       if (!list_empty(&v->tc)) {
+                if ((t = list_entry(v->tc.next, struct tc, tc)) == NULL) {
+                        printk(KERN_WARNING "VPE loader: TC %d is already in use.\n",
+                               t->index);
+                        return -ENOEXEC;
+                }
+        } else {
+                printk(KERN_WARNING "VPE loader: No TC's associated with VPE %d\n",
+                       v->minor);
+                return -ENOEXEC;
+        }
+
        /* Put MVPE's into 'configuration state' */
        set_c0_mvpcontrol(MVPCONTROL_VPC);
 
-       if (!list_empty(&v->tc)) {
-               if ((t = list_entry(v->tc.next, struct tc, tc)) == NULL) {
-                       printk(KERN_WARNING "VPE: TC %d is already in use.\n",
-                              t->index);
-                       return -ENOEXEC;
-               }
-       } else {
-               printk(KERN_WARNING "VPE: No TC's associated with VPE %d\n",
-                      v->minor);
-               return -ENOEXEC;
-       }
-
        settc(t->index);
 
-       val = read_vpe_c0_vpeconf0();
-
        /* should check it is halted, and not activated */
        if ((read_tc_c0_tcstatus() & TCSTATUS_A) || !(read_tc_c0_tchalt() & TCHALT_H)) {
-               printk(KERN_WARNING "VPE: TC %d is already doing something!\n",
+               printk(KERN_WARNING "VPE loader: TC %d is already doing something!\n",
                       t->index);
-
                dump_tclist();
                return -ENOEXEC;
        }
 
+       /*
+        * Disable multi-threaded execution whilst we activate, clear the
+        * halt bit and bound the tc to the other VPE...
+        */
+       dmt_flag = dmt();
+
        /* Write the address we want it to start running from in the TCPC register. */
        write_tc_c0_tcrestart((unsigned long)v->__start);
-
-       /* write the sivc_info address to tccontext */
        write_tc_c0_tccontext((unsigned long)0);
-
-       /* Set up the XTC bit in vpeconf0 to point at our tc */
-       write_vpe_c0_vpeconf0(read_vpe_c0_vpeconf0() | (t->index << VPECONF0_XTC_SHIFT));
-
-       /* mark the TC as activated, not interrupt exempt and not dynamically allocatable */
+       /*
+        * Mark the TC as activated, not interrupt exempt and not dynamically
+        * allocatable
+        */
        val = read_tc_c0_tcstatus();
        val = (val & ~(TCSTATUS_DA | TCSTATUS_IXMT)) | TCSTATUS_A;
        write_tc_c0_tcstatus(val);
 
        write_tc_c0_tchalt(read_tc_c0_tchalt() & ~TCHALT_H);
 
-       /* set up VPE1 */
-       write_vpe_c0_vpecontrol(read_vpe_c0_vpecontrol() & ~VPECONTROL_TE);     // no multiple TC's
-       write_vpe_c0_vpeconf0(read_vpe_c0_vpeconf0() | VPECONF0_VPA);   // enable this VPE
-
        /*
         * The sde-kit passes 'memsize' to __start in $a3, so set something
-        * here...
-        * Or set $a3 (register 7) to zero and define DFLT_STACK_SIZE and
+        * here...  Or set $a3 to zero and define DFLT_STACK_SIZE and
         * DFLT_HEAP_SIZE when you compile your program
         */
+       mttgpr(7, physical_memsize);
+
+
+       /* set up VPE1 */
+       /*
+        * bind the TC to VPE 1 as late as possible so we only have the final
+        * VPE registers to set up, and so an EJTAG probe can trigger on it
+        */
+       write_tc_c0_tcbind((read_tc_c0_tcbind() & ~TCBIND_CURVPE) | v->minor);
 
-       mttgpr(7, 0);
+        /* Set up the XTC bit in vpeconf0 to point at our tc */
+        write_vpe_c0_vpeconf0( (read_vpe_c0_vpeconf0() & ~(VPECONF0_XTC))
+                               | (t->index << VPECONF0_XTC_SHIFT));
 
-       /* set config to be the same as vpe0, particularly kseg0 coherency alg */
-       write_vpe_c0_config(read_c0_config());
+        /* enable this VPE */
+        write_vpe_c0_vpeconf0(read_vpe_c0_vpeconf0() | VPECONF0_VPA);
 
        /* clear out any left overs from a previous program */
+       write_vpe_c0_status(0);
        write_vpe_c0_cause(0);
 
        /* take system out of configuration state */
        clear_c0_mvpcontrol(MVPCONTROL_VPC);
 
-       /* clear interrupts enabled IE, ERL, EXL, and KSU from c0 status */
-       write_vpe_c0_status(read_vpe_c0_status() & ~(ST0_ERL | ST0_KSU | ST0_IE | ST0_EXL));
+       /* now safe to re-enable multi-threading */
+       emt(dmt_flag);
 
        /* set it running */
        evpe(EVPE_ENABLE);
 
+       list_for_each_entry(n, &v->notify, list) {
+               n->start(v->minor);
+       }
+
        return 0;
 }
 
-static unsigned long find_vpe_symbols(struct vpe * v, Elf_Shdr * sechdrs,
+static int find_vpe_symbols(struct vpe * v, Elf_Shdr * sechdrs,
                                      unsigned int symindex, const char *strtab,
                                      struct module *mod)
 {
@@ -778,26 +813,28 @@ static unsigned long find_vpe_symbols(struct vpe * v, Elf_Shdr * sechdrs,
                }
        }
 
+       if ( (v->__start == 0) || (v->shared_ptr == NULL))
+               return -1;
+
        return 0;
 }
 
 /*
- * Allocates a VPE with some program code space(the load address), copies
- * the contents of the program (p)buffer performing relocatations/etc,
- * free's it when finished.
-*/
+ * Allocates a VPE with some program code space(the load address), copies the
+ * contents of the program (p)buffer performing relocatations/etc, free's it
+ * when finished.
+ */
 int vpe_elfload(struct vpe * v)
 {
        Elf_Ehdr *hdr;
        Elf_Shdr *sechdrs;
        long err = 0;
        char *secstrings, *strtab = NULL;
-       unsigned int len, i, symindex = 0, strindex = 0;
-
+       unsigned int len, i, symindex = 0, strindex = 0, relocate = 0;
        struct module mod;      // so we can re-use the relocations code
 
        memset(&mod, 0, sizeof(struct module));
-       strcpy(mod.name, "VPE dummy prog module");
+       strcpy(mod.name, "VPE loader");
 
        hdr = (Elf_Ehdr *) v->pbuffer;
        len = v->plen;
@@ -805,16 +842,22 @@ int vpe_elfload(struct vpe * v)
        /* Sanity checks against insmoding binaries or wrong arch,
           weird elf version */
        if (memcmp(hdr->e_ident, ELFMAG, 4) != 0
-           || hdr->e_type != ET_REL || !elf_check_arch(hdr)
+           || (hdr->e_type != ET_REL && hdr->e_type != ET_EXEC)
+           || !elf_check_arch(hdr)
            || hdr->e_shentsize != sizeof(*sechdrs)) {
                printk(KERN_WARNING
-                      "VPE program, wrong arch or weird elf version\n");
+                      "VPE loader: program wrong arch or weird elf version\n");
 
                return -ENOEXEC;
        }
 
+       if (hdr->e_type == ET_REL)
+               relocate = 1;
+
        if (len < hdr->e_shoff + hdr->e_shnum * sizeof(Elf_Shdr)) {
-               printk(KERN_ERR "VPE program length %u truncated\n", len);
+               printk(KERN_ERR "VPE loader: program length %u truncated\n",
+                      len);
+
                return -ENOEXEC;
        }
 
@@ -826,82 +869,126 @@ int vpe_elfload(struct vpe * v)
        /* And these should exist, but gcc whinges if we don't init them */
        symindex = strindex = 0;
 
-       for (i = 1; i < hdr->e_shnum; i++) {
-
-               if (sechdrs[i].sh_type != SHT_NOBITS
-                   && len < sechdrs[i].sh_offset + sechdrs[i].sh_size) {
-                       printk(KERN_ERR "VPE program length %u truncated\n",
-                              len);
-                       return -ENOEXEC;
-               }
+       if (relocate) {
+               for (i = 1; i < hdr->e_shnum; i++) {
+                       if (sechdrs[i].sh_type != SHT_NOBITS
+                           && len < sechdrs[i].sh_offset + sechdrs[i].sh_size) {
+                               printk(KERN_ERR "VPE program length %u truncated\n",
+                                      len);
+                               return -ENOEXEC;
+                       }
 
-               /* Mark all sections sh_addr with their address in the
-                  temporary image. */
-               sechdrs[i].sh_addr = (size_t) hdr + sechdrs[i].sh_offset;
+                       /* Mark all sections sh_addr with their address in the
+                          temporary image. */
+                       sechdrs[i].sh_addr = (size_t) hdr + sechdrs[i].sh_offset;
 
-               /* Internal symbols and strings. */
-               if (sechdrs[i].sh_type == SHT_SYMTAB) {
-                       symindex = i;
-                       strindex = sechdrs[i].sh_link;
-                       strtab = (char *)hdr + sechdrs[strindex].sh_offset;
+                       /* Internal symbols and strings. */
+                       if (sechdrs[i].sh_type == SHT_SYMTAB) {
+                               symindex = i;
+                               strindex = sechdrs[i].sh_link;
+                               strtab = (char *)hdr + sechdrs[strindex].sh_offset;
+                       }
                }
+               layout_sections(&mod, hdr, sechdrs, secstrings);
        }
 
-       layout_sections(&mod, hdr, sechdrs, secstrings);
-
        v->load_addr = alloc_progmem(mod.core_size);
        memset(v->load_addr, 0, mod.core_size);
 
-       printk("VPE elf_loader: loading to %p\n", v->load_addr);
+       printk("VPE loader: loading to %p\n", v->load_addr);
 
-       for (i = 0; i < hdr->e_shnum; i++) {
-               void *dest;
+       if (relocate) {
+               for (i = 0; i < hdr->e_shnum; i++) {
+                       void *dest;
 
-               if (!(sechdrs[i].sh_flags & SHF_ALLOC))
-                       continue;
+                       if (!(sechdrs[i].sh_flags & SHF_ALLOC))
+                               continue;
 
-               dest = v->load_addr + sechdrs[i].sh_entsize;
+                       dest = v->load_addr + sechdrs[i].sh_entsize;
 
-               if (sechdrs[i].sh_type != SHT_NOBITS)
-                       memcpy(dest, (void *)sechdrs[i].sh_addr,
-                              sechdrs[i].sh_size);
-               /* Update sh_addr to point to copy in image. */
-               sechdrs[i].sh_addr = (unsigned long)dest;
-       }
+                       if (sechdrs[i].sh_type != SHT_NOBITS)
+                               memcpy(dest, (void *)sechdrs[i].sh_addr,
+                                      sechdrs[i].sh_size);
+                       /* Update sh_addr to point to copy in image. */
+                       sechdrs[i].sh_addr = (unsigned long)dest;
 
-       /* Fix up syms, so that st_value is a pointer to location. */
-       err =
-               simplify_symbols(sechdrs, symindex, strtab, secstrings,
-                                hdr->e_shnum, &mod);
-       if (err < 0) {
-               printk(KERN_WARNING "VPE: unable to simplify symbols\n");
-               goto cleanup;
-       }
+                       printk(KERN_DEBUG " section sh_name %s sh_addr 0x%x\n",
+                              secstrings + sechdrs[i].sh_name, sechdrs[i].sh_addr);
+               }
 
-       /* Now do relocations. */
-       for (i = 1; i < hdr->e_shnum; i++) {
-               const char *strtab = (char *)sechdrs[strindex].sh_addr;
-               unsigned int info = sechdrs[i].sh_info;
-
-               /* Not a valid relocation section? */
-               if (info >= hdr->e_shnum)
-                       continue;
-
-               /* Don't bother with non-allocated sections */
-               if (!(sechdrs[info].sh_flags & SHF_ALLOC))
-                       continue;
-
-               if (sechdrs[i].sh_type == SHT_REL)
-                       err =
-                               apply_relocations(sechdrs, strtab, symindex, i, &mod);
-               else if (sechdrs[i].sh_type == SHT_RELA)
-                       err = apply_relocate_add(sechdrs, strtab, symindex, i,
-                                                &mod);
-               if (err < 0) {
-                       printk(KERN_WARNING
-                              "vpe_elfload: error in relocations err %ld\n",
-                              err);
-                       goto cleanup;
+               /* Fix up syms, so that st_value is a pointer to location. */
+               simplify_symbols(sechdrs, symindex, strtab, secstrings,
+                                hdr->e_shnum, &mod);
+
+               /* Now do relocations. */
+               for (i = 1; i < hdr->e_shnum; i++) {
+                       const char *strtab = (char *)sechdrs[strindex].sh_addr;
+                       unsigned int info = sechdrs[i].sh_info;
+
+                       /* Not a valid relocation section? */
+                       if (info >= hdr->e_shnum)
+                               continue;
+
+                       /* Don't bother with non-allocated sections */
+                       if (!(sechdrs[info].sh_flags & SHF_ALLOC))
+                               continue;
+
+                       if (sechdrs[i].sh_type == SHT_REL)
+                               err = apply_relocations(sechdrs, strtab, symindex, i,
+                                                       &mod);
+                       else if (sechdrs[i].sh_type == SHT_RELA)
+                               err = apply_relocate_add(sechdrs, strtab, symindex, i,
+                                                        &mod);
+                       if (err < 0)
+                               return err;
+
+               }
+       } else {
+               for (i = 0; i < hdr->e_shnum; i++) {
+
+                       /* Internal symbols and strings. */
+                       if (sechdrs[i].sh_type == SHT_SYMTAB) {
+                               symindex = i;
+                               strindex = sechdrs[i].sh_link;
+                               strtab = (char *)hdr + sechdrs[strindex].sh_offset;
+
+                               /* mark the symtab's address for when we try to find the
+                                  magic symbols */
+                               sechdrs[i].sh_addr = (size_t) hdr + sechdrs[i].sh_offset;
+                       }
+
+                       /* filter sections we dont want in the final image */
+                       if (!(sechdrs[i].sh_flags & SHF_ALLOC) ||
+                           (sechdrs[i].sh_type == SHT_MIPS_REGINFO)) {
+                               printk( KERN_DEBUG " ignoring section, "
+                                       "name %s type %x address 0x%x \n",
+                                       secstrings + sechdrs[i].sh_name,
+                                       sechdrs[i].sh_type, sechdrs[i].sh_addr);
+                               continue;
+                       }
+
+                       if (sechdrs[i].sh_addr < (unsigned int)v->load_addr) {
+                               printk( KERN_WARNING "VPE loader: "
+                                       "fully linked image has invalid section, "
+                                       "name %s type %x address 0x%x, before load "
+                                       "address of 0x%x\n",
+                                       secstrings + sechdrs[i].sh_name,
+                                       sechdrs[i].sh_type, sechdrs[i].sh_addr,
+                                       (unsigned int)v->load_addr);
+                               return -ENOEXEC;
+                       }
+
+                       printk(KERN_DEBUG " copying section sh_name %s, sh_addr 0x%x "
+                              "size 0x%x0 from x%p\n",
+                              secstrings + sechdrs[i].sh_name, sechdrs[i].sh_addr,
+                              sechdrs[i].sh_size, hdr + sechdrs[i].sh_offset);
+
+                       if (sechdrs[i].sh_type != SHT_NOBITS)
+                               memcpy((void *)sechdrs[i].sh_addr,
+                                      (char *)hdr + sechdrs[i].sh_offset,
+                                      sechdrs[i].sh_size);
+                       else
+                               memset((void *)sechdrs[i].sh_addr, 0, sechdrs[i].sh_size);
                }
        }
 
@@ -910,71 +997,104 @@ int vpe_elfload(struct vpe * v)
                           (unsigned long)v->load_addr + v->len);
 
        if ((find_vpe_symbols(v, sechdrs, symindex, strtab, &mod)) < 0) {
+               if (v->__start == 0) {
+                       printk(KERN_WARNING "VPE loader: program does not contain "
+                              "a __start symbol\n");
+                       return -ENOEXEC;
+               }
 
-               printk(KERN_WARNING
-                      "VPE: program doesn't contain __start or vpe_shared symbols\n");
-               err = -ENOEXEC;
+               if (v->shared_ptr == NULL)
+                       printk(KERN_WARNING "VPE loader: "
+                              "program does not contain vpe_shared symbol.\n"
+                              " Unable to use AMVP (AP/SP) facilities.\n");
        }
 
        printk(" elf loaded\n");
-
-cleanup:
-       return err;
+       return 0;
 }
 
-static void dump_vpe(struct vpe * v)
+__attribute_used__ void dump_vpe(struct vpe * v)
 {
        struct tc *t;
 
+       settc(v->minor);
+
        printk(KERN_DEBUG "VPEControl 0x%lx\n", read_vpe_c0_vpecontrol());
        printk(KERN_DEBUG "VPEConf0 0x%lx\n", read_vpe_c0_vpeconf0());
 
-       list_for_each_entry(t, &vpecontrol.tc_list, list) {
+       list_for_each_entry(t, &vpecontrol.tc_list, list)
                dump_tc(t);
-       }
 }
 
-/* checks for VPE is unused and gets ready to load program      */
+static void cleanup_tc(struct tc *tc)
+{
+       int tmp;
+
+       /* Put MVPE's into 'configuration state' */
+       set_c0_mvpcontrol(MVPCONTROL_VPC);
+
+       settc(tc->index);
+       tmp = read_tc_c0_tcstatus();
+
+       /* mark not allocated and not dynamically allocatable */
+       tmp &= ~(TCSTATUS_A | TCSTATUS_DA);
+       tmp |= TCSTATUS_IXMT;   /* interrupt exempt */
+       write_tc_c0_tcstatus(tmp);
+
+       write_tc_c0_tchalt(TCHALT_H);
+
+       /* bind it to anything other than VPE1 */
+       write_tc_c0_tcbind(read_tc_c0_tcbind() & ~TCBIND_CURVPE); // | TCBIND_CURVPE
+
+       clear_c0_mvpcontrol(MVPCONTROL_VPC);
+}
+
+static int getcwd(char *buff, int size)
+{
+       mm_segment_t old_fs;
+       int ret;
+
+       old_fs = get_fs();
+       set_fs(KERNEL_DS);
+
+       ret = sys_getcwd(buff,size);
+
+       set_fs(old_fs);
+
+       return ret;
+}
+
+/* checks VPE is unused and gets ready to load program  */
 static int vpe_open(struct inode *inode, struct file *filp)
 {
-       int minor;
+       int minor, ret;
        struct vpe *v;
+       struct vpe_notifications *not;
 
        /* assume only 1 device at the mo. */
        if ((minor = MINOR(inode->i_rdev)) != 1) {
-               printk(KERN_WARNING "VPE: only vpe1 is supported\n");
+               printk(KERN_WARNING "VPE loader: only vpe1 is supported\n");
                return -ENODEV;
        }
 
        if ((v = get_vpe(minor)) == NULL) {
-               printk(KERN_WARNING "VPE: unable to get vpe\n");
+               printk(KERN_WARNING "VPE loader: unable to get vpe\n");
                return -ENODEV;
        }
 
        if (v->state != VPE_STATE_UNUSED) {
-               unsigned long tmp;
-               struct tc *t;
-
-               printk(KERN_WARNING "VPE: device %d already in use\n", minor);
-
                dvpe();
-               dump_vpe(v);
-
-               printk(KERN_WARNING "VPE: re-initialising %d\n", minor);
-
-               release_progmem(v->load_addr);
 
-               t = get_tc(minor);
-               settc(minor);
-               tmp = read_tc_c0_tcstatus();
+               printk(KERN_DEBUG "VPE loader: tc in use dumping regs\n");
 
-               /* mark not allocated and not dynamically allocatable */
-               tmp &= ~(TCSTATUS_A | TCSTATUS_DA);
-               tmp |= TCSTATUS_IXMT;   /* interrupt exempt */
-               write_tc_c0_tcstatus(tmp);
+               dump_tc(get_tc(minor));
 
-               write_tc_c0_tchalt(TCHALT_H);
+               list_for_each_entry(not, &v->notify, list) {
+                       not->stop(minor);
+               }
 
+               release_progmem(v->load_addr);
+               cleanup_tc(get_tc(minor));
        }
 
        // allocate it so when we get write ops we know it's expected.
@@ -986,6 +1106,24 @@ static int vpe_open(struct inode *inode, struct file *filp)
        v->load_addr = NULL;
        v->len = 0;
 
+       v->uid = filp->f_uid;
+       v->gid = filp->f_gid;
+
+#ifdef CONFIG_MIPS_APSP_KSPD
+       /* get kspd to tell us when a syscall_exit happens */
+       if (!kspd_events_reqd) {
+               kspd_notify(&kspd_events);
+               kspd_events_reqd++;
+       }
+#endif
+
+       v->cwd[0] = 0;
+       ret = getcwd(v->cwd, VPE_PATH_MAX);
+       if (ret < 0)
+               printk(KERN_WARNING "VPE loader: open, getcwd returned %d\n", ret);
+
+       v->shared_ptr = NULL;
+       v->__start = 0;
        return 0;
 }
 
@@ -1006,14 +1144,22 @@ static int vpe_release(struct inode *inode, struct file *filp)
                if (vpe_elfload(v) >= 0)
                        vpe_run(v);
                else {
-                       printk(KERN_WARNING "VPE: ELF load failed.\n");
+                       printk(KERN_WARNING "VPE loader: ELF load failed.\n");
                        ret = -ENOEXEC;
                }
        } else {
-               printk(KERN_WARNING "VPE: only elf files are supported\n");
+               printk(KERN_WARNING "VPE loader: only elf files are supported\n");
                ret = -ENOEXEC;
        }
 
+       /* It's good to be able to run the SP and if it chokes have a look at
+          the /dev/rt?. But if we reset the pointer to the shared struct we
+          loose what has happened. So perhaps if garbage is sent to the vpe
+          device, use it as a trigger for the reset. Hopefully a nice
+          executable will be along shortly. */
+       if (ret < 0)
+               v->shared_ptr = NULL;
+
        // cleanup any temp buffers
        if (v->pbuffer)
                vfree(v->pbuffer);
@@ -1033,21 +1179,19 @@ static ssize_t vpe_write(struct file *file, const char __user * buffer,
                return -ENODEV;
 
        if (v->pbuffer == NULL) {
-               printk(KERN_ERR "vpe_write: no pbuffer\n");
+               printk(KERN_ERR "VPE loader: no buffer for program\n");
                return -ENOMEM;
        }
 
        if ((count + v->len) > v->plen) {
                printk(KERN_WARNING
-                      "VPE Loader: elf size too big. Perhaps strip uneeded symbols\n");
+                      "VPE loader: elf size too big. Perhaps strip uneeded symbols\n");
                return -ENOMEM;
        }
 
        count -= copy_from_user(v->pbuffer + v->len, buffer, count);
-       if (!count) {
-               printk("vpe_write: copy_to_user failed\n");
+       if (!count)
                return -EFAULT;
-       }
 
        v->len += count;
        return ret;
@@ -1149,16 +1293,70 @@ void *vpe_get_shared(int index)
 {
        struct vpe *v;
 
-       if ((v = get_vpe(index)) == NULL) {
-               printk(KERN_WARNING "vpe: invalid vpe index %d\n", index);
+       if ((v = get_vpe(index)) == NULL)
                return NULL;
-       }
 
        return v->shared_ptr;
 }
 
 EXPORT_SYMBOL(vpe_get_shared);
 
+int vpe_getuid(int index)
+{
+       struct vpe *v;
+
+       if ((v = get_vpe(index)) == NULL)
+               return -1;
+
+       return v->uid;
+}
+
+EXPORT_SYMBOL(vpe_getuid);
+
+int vpe_getgid(int index)
+{
+       struct vpe *v;
+
+       if ((v = get_vpe(index)) == NULL)
+               return -1;
+
+       return v->gid;
+}
+
+EXPORT_SYMBOL(vpe_getgid);
+
+int vpe_notify(int index, struct vpe_notifications *notify)
+{
+       struct vpe *v;
+
+       if ((v = get_vpe(index)) == NULL)
+               return -1;
+
+       list_add(&notify->list, &v->notify);
+       return 0;
+}
+
+EXPORT_SYMBOL(vpe_notify);
+
+char *vpe_getcwd(int index)
+{
+       struct vpe *v;
+
+       if ((v = get_vpe(index)) == NULL)
+               return NULL;
+
+       return v->cwd;
+}
+
+EXPORT_SYMBOL(vpe_getcwd);
+
+#ifdef CONFIG_MIPS_APSP_KSPD
+static void kspd_sp_exit( int sp_id)
+{
+       cleanup_tc(get_tc(sp_id));
+}
+#endif
+
 static int __init vpe_module_init(void)
 {
        struct vpe *v = NULL;
@@ -1201,7 +1399,8 @@ static int __init vpe_module_init(void)
                                return -ENODEV;
                        }
 
-                       list_add(&t->tc, &v->tc);       /* add the tc to the list of this vpe's tc's. */
+                       /* add the tc to the list of this vpe's tc's. */
+                       list_add(&t->tc, &v->tc);
 
                        /* deactivate all but vpe0 */
                        if (i != 0) {
@@ -1222,10 +1421,12 @@ static int __init vpe_module_init(void)
                                                     ~(ST0_IM | ST0_IE | ST0_KSU))
                                                    | ST0_CU0);
 
-                               /* set config to be the same as vpe0, particularly kseg0 coherency alg */
+                               /*
+                                * Set config to be the same as vpe0,
+                                * particularly kseg0 coherency alg
+                                */
                                write_vpe_c0_config(read_c0_config());
                        }
-
                }
 
                /* TC's */
@@ -1234,23 +1435,28 @@ static int __init vpe_module_init(void)
                if (i != 0) {
                        unsigned long tmp;
 
-                       /* tc 0 will of course be running.... */
-                       if (i == 0)
-                               t->state = TC_STATE_RUNNING;
-
                        settc(i);
 
-                       /* bind a TC to each VPE, May as well put all excess TC's
-                          on the last VPE */
-                       if (i >= (((val & MVPCONF0_PVPE) >> MVPCONF0_PVPE_SHIFT) + 1))
-                               write_tc_c0_tcbind(read_tc_c0_tcbind() |
-                                                  ((val & MVPCONF0_PVPE) >> MVPCONF0_PVPE_SHIFT));
-                       else
-                               write_tc_c0_tcbind(read_tc_c0_tcbind() | i);
+                       /* Any TC that is bound to VPE0 gets left as is - in case
+                          we are running SMTC on VPE0. A TC that is bound to any
+                          other VPE gets bound to VPE0, ideally I'd like to make
+                          it homeless but it doesn't appear to let me bind a TC
+                          to a non-existent VPE. Which is perfectly reasonable.
+
+                          The (un)bound state is visible to an EJTAG probe so may
+                          notify GDB...
+                       */
+
+                       if (((tmp = read_tc_c0_tcbind()) & TCBIND_CURVPE)) {
+                               /* tc is bound >vpe0 */
+                               write_tc_c0_tcbind(tmp & ~TCBIND_CURVPE);
+
+                               t->pvpe = get_vpe(0);   /* set the parent vpe */
+                       }
 
                        tmp = read_tc_c0_tcstatus();
 
-                       /* mark not allocated and not dynamically allocatable */
+                       /* mark not activated and not dynamically allocatable */
                        tmp &= ~(TCSTATUS_A | TCSTATUS_DA);
                        tmp |= TCSTATUS_IXMT;   /* interrupt exempt */
                        write_tc_c0_tcstatus(tmp);
@@ -1262,6 +1468,9 @@ static int __init vpe_module_init(void)
        /* release config state */
        clear_c0_mvpcontrol(MVPCONTROL_VPC);
 
+#ifdef CONFIG_MIPS_APSP_KSPD
+       kspd_events.kspd_sp_exit = kspd_sp_exit;
+#endif
        return 0;
 }
 
@@ -1281,5 +1490,5 @@ static void __exit vpe_module_exit(void)
 module_init(vpe_module_init);
 module_exit(vpe_module_exit);
 MODULE_DESCRIPTION("MIPS VPE Loader");
-MODULE_AUTHOR("Elizabeth Clarke, MIPS Technologies, Inc");
+MODULE_AUTHOR("Elizabeth Oldham, MIPS Technologies, Inc.");
 MODULE_LICENSE("GPL");
index 0d5aec436725678eb99212db7c848c907ccb9e45..99f5046fdf4938bdc5558920feaaf67a5d43bc10 100644 (file)
@@ -3,7 +3,7 @@
 #
 
 obj-y                          += reset.o setup.o prom.o lasat_board.o \
-                                  at93c.o interrupt.o lasatIRQ.o
+                                  at93c.o interrupt.o
 
 obj-$(CONFIG_LASAT_SYSCTL)     += sysctl.o
 obj-$(CONFIG_DS1603)           += ds1603.o
index 852a41901a5e623eae2eb1b1eadec7e7699182b6..2d3472b21ebbe3ad62b98ff3046380b0039107a3 100644 (file)
 #include <asm/bootinfo.h>
 #include <asm/irq.h>
 #include <asm/lasat/lasatint.h>
+#include <asm/time.h>
 #include <asm/gdb-stub.h>
 
 static volatile int *lasat_int_status = NULL;
 static volatile int *lasat_int_mask = NULL;
 static volatile int lasat_int_mask_shift;
 
-extern asmlinkage void lasatIRQ(void);
-
 void disable_lasat_irq(unsigned int irq_nr)
 {
        unsigned long flags;
@@ -109,11 +108,17 @@ static unsigned long get_int_status_200(void)
        return int_status;
 }
 
-void lasat_hw0_irqdispatch(struct pt_regs *regs)
+asmlinkage void plat_irq_dispatch(struct pt_regs *regs)
 {
        unsigned long int_status;
+       unsigned int cause = read_c0_cause();
        int irq;
 
+       if (cause & CAUSEF_IP7) {       /* R4000 count / compare IRQ */
+               ll_timer_interrupt(7, regs);
+               return;
+       }
+
        int_status = get_int_status();
 
        /* if int_status == 0, then the interrupt has already been cleared */
@@ -147,9 +152,6 @@ void __init arch_init_irq(void)
                panic("arch_init_irq: mips_machtype incorrect");
        }
 
-       /* Now safe to set the exception vector. */
-       set_except_vector(0, lasatIRQ);
-
        for (i = 0; i <= LASATINT_END; i++) {
                irq_desc[i].status      = IRQ_DISABLED;
                irq_desc[i].action      = 0;
diff --git a/arch/mips/lasat/lasatIRQ.S b/arch/mips/lasat/lasatIRQ.S
deleted file mode 100644 (file)
index 2a2b0d0..0000000
+++ /dev/null
@@ -1,69 +0,0 @@
-/*
- * Carsten Langgaard, carstenl@mips.com
- * Copyright (C) 1999, 2000 MIPS Technologies, Inc.  All rights reserved.
- *
- *  This program is free software; you can distribute 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 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.,
- *  59 Temple Place - Suite 330, Boston MA 02111-1307, USA.
- *
- * Interrupt exception dispatch code.
- */
-#include <asm/asm.h>
-#include <asm/mipsregs.h>
-#include <asm/regdef.h>
-#include <asm/stackframe.h>
-
-       .text
-       .set    noreorder
-       .align  5
-       NESTED(lasatIRQ, PT_SIZE, sp)
-       .set    noat
-       SAVE_ALL
-       CLI
-       .set    at
-       .set    noreorder
-
-       mfc0    s0, CP0_CAUSE           # get irq mask
-
-       /* First we check for r4k counter/timer IRQ. */
-       andi    a0, s0, CAUSEF_IP7
-       beq     a0, zero, 1f
-        andi   a0, s0, CAUSEF_IP2      # delay slot, check hw0 interrupt
-
-       /* Wheee, a timer interrupt. */
-       li      a0, 7
-       jal     ll_timer_interrupt
-        move   a1, sp
-
-       j       ret_from_irq
-        nop
-
-1:
-       /* Wheee, combined hardware level zero interrupt. */
-       jal     lasat_hw0_irqdispatch
-        move   a0, sp                  # delay slot
-
-       j       ret_from_irq
-        nop                            # delay slot
-
-1:
-       /*
-        * Here by mistake?  This is possible, what can happen is that by the
-        * time we take the exception the IRQ pin goes low, so just leave if
-        * this is the case.
-        */
-       move    a1,s0
-       mfc0    a1, CP0_EPC
-
-       j       ret_from_irq
-        nop
-       END(lasatIRQ)
index bc0ebc69bfb3f4b9a2078bbb31c71a437f1558f0..db53950b7cfbae7bd9e8936ede6fd6f6f5c64882 100644 (file)
@@ -39,8 +39,6 @@
 
 static struct atlas_ictrl_regs *atlas_hw0_icregs;
 
-extern asmlinkage void mipsIRQ(void);
-
 #if 0
 #define DEBUG_INT(x...) printk(x)
 #else
@@ -98,7 +96,7 @@ static inline int ls1bit32(unsigned int x)
        return b;
 }
 
-void atlas_hw0_irqdispatch(struct pt_regs *regs)
+static inline void atlas_hw0_irqdispatch(struct pt_regs *regs)
 {
        unsigned long int_status;
        int irq;
@@ -116,6 +114,91 @@ void atlas_hw0_irqdispatch(struct pt_regs *regs)
        do_IRQ(irq, regs);
 }
 
+static inline int clz(unsigned long x)
+{
+       __asm__ (
+       "       .set    push                                    \n"
+       "       .set    mips32                                  \n"
+       "       clz     %0, %1                                  \n"
+       "       .set    pop                                     \n"
+       : "=r" (x)
+       : "r" (x));
+
+       return x;
+}
+
+/*
+ * Version of ffs that only looks at bits 12..15.
+ */
+static inline unsigned int irq_ffs(unsigned int pending)
+{
+#if defined(CONFIG_CPU_MIPS32) || defined(CONFIG_CPU_MIPS64)
+       return -clz(pending) + 31 - CAUSEB_IP;
+#else
+       unsigned int a0 = 7;
+       unsigned int t0;
+
+       t0 = s0 & 0xf000;
+       t0 = t0 < 1;
+       t0 = t0 << 2;
+       a0 = a0 - t0;
+       s0 = s0 << t0;
+
+       t0 = s0 & 0xc000;
+       t0 = t0 < 1;
+       t0 = t0 << 1;
+       a0 = a0 - t0;
+       s0 = s0 << t0;
+
+       t0 = s0 & 0x8000;
+       t0 = t0 < 1;
+       //t0 = t0 << 2;
+       a0 = a0 - t0;
+       //s0 = s0 << t0;
+
+       return a0;
+#endif
+}
+
+/*
+ * IRQs on the Atlas board look basically (barring software IRQs which we
+ * don't use at all and all external interrupt sources are combined together
+ * on hardware interrupt 0 (MIPS IRQ 2)) like:
+ *
+ *     MIPS IRQ        Source
+ *      --------        ------
+ *             0       Software (ignored)
+ *             1        Software (ignored)
+ *             2        Combined hardware interrupt (hw0)
+ *             3        Hardware (ignored)
+ *             4        Hardware (ignored)
+ *             5        Hardware (ignored)
+ *             6        Hardware (ignored)
+ *             7        R4k timer (what we use)
+ *
+ * We handle the IRQ according to _our_ priority which is:
+ *
+ * Highest ----     R4k Timer
+ * Lowest  ----     Combined hardware interrupt
+ *
+ * then we just return, if multiple IRQs are pending then we will just take
+ * another exception, big deal.
+ */
+asmlinkage void plat_irq_dispatch(struct pt_regs *regs)
+{
+       unsigned int pending = read_c0_cause() & read_c0_status() & ST0_IM;
+       int irq;
+
+       irq = irq_ffs(pending);
+
+       if (irq == MIPSCPU_INT_ATLAS)
+               atlas_hw0_irqdispatch(regs);
+       else if (irq > 0)
+               do_IRQ(MIPSCPU_INT_BASE + irq, regs);
+       else
+               spurious_interrupt(regs);
+}
+
 void __init arch_init_irq(void)
 {
        int i;
@@ -128,9 +211,6 @@ void __init arch_init_irq(void)
         */
        atlas_hw0_icregs->intrsten = 0xffffffff;
 
-       /* Now safe to set the exception vector. */
-       set_except_vector(0, mipsIRQ);
-
        for (i = ATLASINT_BASE; i <= ATLASINT_END; i++) {
                irq_desc[i].status      = IRQ_DISABLED;
                irq_desc[i].action      = 0;
index b21bc6887fa8f45c7ea298a7898dae1cdba14d01..be47c1c2bc8020f33726c620749a28ac2e48315f 100644 (file)
@@ -18,8 +18,8 @@
 # Makefile for the MIPS boards generic routines under Linux.
 #
 
-obj-y                          := mipsIRQ.o reset.o display.o init.o memory.o \
-                                  printf.o cmdline.o time.o
+obj-y                          := reset.o display.o init.o memory.o printf.o \
+                                  cmdline.o time.o
 obj-$(CONFIG_PCI)              += pci.o
 obj-$(CONFIG_KGDB)             += gdb_hook.o
 
index 91a2ccbe3730e3cfafd15908f0b8e1d766755b6d..6a1854de45799e40d91efa03f8385eecdbdb617b 100644 (file)
@@ -25,7 +25,7 @@
 #include <asm/serial.h>
 #include <asm/io.h>
 
-static struct serial_state rs_table[RS_TABLE_SIZE] = {
+static struct serial_state rs_table[] = {
        SERIAL_PORT_DFNS        /* Defined in serial.h */
 };
 
index eab5a705e9892732635938f393690ed1c514eda1..17dfe6a8cab9b38b9b3620217953c57c6a118406 100644 (file)
@@ -220,7 +220,6 @@ void __init kgdb_config (void)
                                generic_putDebugChar (*s++);
                }
 
-               kgdb_enabled = 1;
                /* Breakpoint is invoked after interrupts are initialised */
        }
 }
index 32c9210373ac864e5faab2c8789dff848f3c5322..bc4d093685bbec8725ab448723700f691b8d3ac8 100644 (file)
 #include <linux/init.h>
 #include <linux/mm.h>
 #include <linux/bootmem.h>
+#include <linux/pfn.h>
 #include <linux/string.h>
 
 #include <asm/bootinfo.h>
 #include <asm/page.h>
+#include <asm/sections.h>
 
 #include <asm/mips-boards/prom.h>
 
@@ -46,9 +48,6 @@ static char *mtypes[3] = {
 };
 #endif
 
-/* References to section boundaries */
-extern char _end;
-
 struct prom_pmemblock * __init prom_getmdesc(void)
 {
        char *memsize_str;
@@ -106,10 +105,10 @@ struct prom_pmemblock * __init prom_getmdesc(void)
 
        mdesc[3].type = yamon_dontuse;
        mdesc[3].base = 0x00100000;
-       mdesc[3].size = CPHYSADDR(PAGE_ALIGN(&_end)) - mdesc[3].base;
+       mdesc[3].size = CPHYSADDR(PFN_ALIGN((unsigned long)&_end)) - mdesc[3].base;
 
        mdesc[4].type = yamon_free;
-       mdesc[4].base = CPHYSADDR(PAGE_ALIGN(&_end));
+       mdesc[4].base = CPHYSADDR(PFN_ALIGN(&_end));
        mdesc[4].size = memsize - mdesc[4].base;
 
        return &mdesc[0];
diff --git a/arch/mips/mips-boards/generic/mipsIRQ.S b/arch/mips/mips-boards/generic/mipsIRQ.S
deleted file mode 100644 (file)
index ddd5c73..0000000
+++ /dev/null
@@ -1,155 +0,0 @@
-/*
- * Carsten Langgaard, carstenl@mips.com
- * Copyright (C) 1999, 2000 MIPS Technologies, Inc.  All rights reserved.
- *
- * ########################################################################
- *
- *  This program is free software; you can distribute 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 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.,
- *  59 Temple Place - Suite 330, Boston MA 02111-1307, USA.
- *
- * ########################################################################
- *
- * Interrupt exception dispatch code.
- *
- */
-#include <linux/config.h>
-
-#include <asm/asm.h>
-#include <asm/mipsregs.h>
-#include <asm/regdef.h>
-#include <asm/stackframe.h>
-
-#ifdef CONFIG_MIPS_ATLAS
-#include <asm/mips-boards/atlasint.h>
-#define CASCADE_IRQ            MIPSCPU_INT_ATLAS
-#define CASCADE_DISPATCH       atlas_hw0_irqdispatch
-#endif
-#ifdef CONFIG_MIPS_MALTA
-#include <asm/mips-boards/maltaint.h>
-#define CASCADE_IRQ            MIPSCPU_INT_I8259A
-#define CASCADE_DISPATCH       malta_hw0_irqdispatch
-#endif
-#ifdef CONFIG_MIPS_SEAD
-#include <asm/mips-boards/seadint.h>
-#endif
-
-/* A lot of complication here is taken away because:
- *
- * 1) We handle one interrupt and return, sitting in a loop and moving across
- *    all the pending IRQ bits in the cause register is _NOT_ the answer, the
- *    common case is one pending IRQ so optimize in that direction.
- *
- * 2) We need not check against bits in the status register IRQ mask, that
- *    would make this routine slow as hell.
- *
- * 3) Linux only thinks in terms of all IRQs on or all IRQs off, nothing in
- *    between like BSD spl() brain-damage.
- *
- * Furthermore, the IRQs on the MIPS board look basically (barring software
- * IRQs which we don't use at all and all external interrupt sources are
- * combined together on hardware interrupt 0 (MIPS IRQ 2)) like:
- *
- *     MIPS IRQ        Source
- *      --------        ------
- *             0       Software (ignored)
- *             1        Software (ignored)
- *             2        Combined hardware interrupt (hw0)
- *             3        Hardware (ignored)
- *             4        Hardware (ignored)
- *             5        Hardware (ignored)
- *             6        Hardware (ignored)
- *             7        R4k timer (what we use)
- *
- * Note: On the SEAD board thing are a little bit different.
- *       Here IRQ 2 (hw0) is wired to the UART0 and IRQ 3 (hw1) is wired
- *       wired to UART1.
- *
- * We handle the IRQ according to _our_ priority which is:
- *
- * Highest ----     R4k Timer
- * Lowest  ----     Combined hardware interrupt
- *
- * then we just return, if multiple IRQs are pending then we will just take
- * another exception, big deal.
- */
-
-       .text
-       .set    noreorder
-       .set    noat
-       .align  5
-       NESTED(mipsIRQ, PT_SIZE, sp)
-       SAVE_ALL
-       CLI
-       .set    at
-
-       mfc0    s0, CP0_CAUSE           # get irq bits
-       mfc0    s1, CP0_STATUS          # get irq mask
-       andi    s0, ST0_IM              # CAUSE.CE may be non-zero!
-       and     s0, s1
-
-#if defined(CONFIG_CPU_MIPS32) || defined(CONFIG_CPU_MIPS64)
-       .set    mips32
-       clz     a0, s0
-       .set    mips0
-       negu    a0
-       addu    a0, 31-CAUSEB_IP
-       bltz    a0, spurious
-#else
-       beqz    s0, spurious
-        li     a0, 7
-
-       and     t0, s0, 0xf000
-       sltiu   t0, t0, 1
-       sll     t0, 2
-       subu    a0, t0
-       sll     s0, t0
-
-       and     t0, s0, 0xc000
-       sltiu   t0, t0, 1
-       sll     t0, 1
-       subu    a0, t0
-       sll     s0, t0
-
-       and     t0, s0, 0x8000
-       sltiu   t0, t0, 1
-       # sll   t0, 0
-       subu    a0, t0
-       # sll   s0, t0
-#endif
-
-#ifdef CASCADE_IRQ
-        li     a1, CASCADE_IRQ
-       bne     a0, a1, 1f
-        addu   a0, MIPSCPU_INT_BASE
-
-       jal     CASCADE_DISPATCH
-        move    a0, sp
-
-       j       ret_from_irq
-        nop
-1:
-#else
-        addu   a0, MIPSCPU_INT_BASE
-#endif
-
-       jal     do_IRQ
-        move   a1, sp
-
-       j       ret_from_irq
-        nop
-
-
-spurious:
-       j       spurious_interrupt
-        nop
-       END(mipsIRQ)
index 93f3bf2c2b22364217e4fe9ae925b1e36b8470e0..a9f6124b3a227ee722288a5b239ddbfff3f821dc 100644 (file)
@@ -30,6 +30,7 @@
 #include <linux/mc146818rtc.h>
 
 #include <asm/mipsregs.h>
+#include <asm/mipsmtregs.h>
 #include <asm/ptrace.h>
 #include <asm/hardirq.h>
 #include <asm/irq.h>
@@ -50,16 +51,23 @@ unsigned long cpu_khz;
 static char display_string[] = "        LINUX ON ATLAS       ";
 #endif
 #if defined(CONFIG_MIPS_MALTA)
+#if defined(CONFIG_MIPS_MT_SMTC)
+static char display_string[] = "       SMTC LINUX ON MALTA       ";
+#else
 static char display_string[] = "        LINUX ON MALTA       ";
+#endif /* CONFIG_MIPS_MT_SMTC */
 #endif
 #if defined(CONFIG_MIPS_SEAD)
 static char display_string[] = "        LINUX ON SEAD       ";
 #endif
-static unsigned int display_count = 0;
+static unsigned int display_count;
 #define MAX_DISPLAY_COUNT (sizeof(display_string) - 8)
 
-static unsigned int timer_tick_count=0;
+#define CPUCTR_IMASKBIT (0x100 << MIPSCPU_INT_CPUCTR)
+
+static unsigned int timer_tick_count;
 static int mips_cpu_timer_irq;
+extern void smtc_timer_broadcast(int);
 
 static inline void scroll_display_message(void)
 {
@@ -75,15 +83,55 @@ static void mips_timer_dispatch (struct pt_regs *regs)
        do_IRQ (mips_cpu_timer_irq, regs);
 }
 
+/*
+ * Redeclare until I get around mopping the timer code insanity on MIPS.
+ */
 extern int null_perf_irq(struct pt_regs *regs);
 
 extern int (*perf_irq)(struct pt_regs *regs);
 
 irqreturn_t mips_timer_interrupt(int irq, void *dev_id, struct pt_regs *regs)
 {
-       int r2 = cpu_has_mips_r2;
        int cpu = smp_processor_id();
+       int r2 = cpu_has_mips_r2;
+
+#ifdef CONFIG_MIPS_MT_SMTC
+        /*
+        *  In an SMTC system, one Count/Compare set exists per VPE.
+        *  Which TC within a VPE gets the interrupt is essentially
+        *  random - we only know that it shouldn't be one with
+        *  IXMT set. Whichever TC gets the interrupt needs to
+        *  send special interprocessor interrupts to the other
+        *  TCs to make sure that they schedule, etc.
+        *
+        *  That code is specific to the SMTC kernel, not to
+        *  the a particular platform, so it's invoked from
+        *  the general MIPS timer_interrupt routine.
+        */
+
+       /*
+        * DVPE is necessary so long as cross-VPE interrupts
+        * are done via read-modify-write of Cause register.
+        */
+       int vpflags = dvpe();
+       write_c0_compare (read_c0_count() - 1);
+       clear_c0_cause(CPUCTR_IMASKBIT);
+       evpe(vpflags);
+
+       if (cpu_data[cpu].vpe_id == 0) {
+               timer_interrupt(irq, dev_id, regs);
+               scroll_display_message();
+       } else
+               write_c0_compare (read_c0_count() + ( mips_hpt_frequency/HZ));
+       smtc_timer_broadcast(cpu_data[cpu].vpe_id);
 
+       if (cpu != 0)
+               /*
+                * Other CPUs should do profiling and process accounting
+                */
+               local_timer_interrupt(irq, dev_id, regs);
+
+#else /* CONFIG_MIPS_MT_SMTC */
        if (cpu == 0) {
                /*
                 * CPU 0 handles the global timer interrupt job and process
@@ -107,12 +155,14 @@ irqreturn_t mips_timer_interrupt(int irq, void *dev_id, struct pt_regs *regs)
                 * More support needs to be added to kernel/time for
                 * counter/timer interrupts on multiple CPU's
                 */
-               write_c0_compare (read_c0_count() + (mips_hpt_frequency/HZ));
+               write_c0_compare(read_c0_count() + (mips_hpt_frequency/HZ));
+
                /*
-                * other CPUs should do profiling and process accounting
+                * Other CPUs should do profiling and process accounting
                 */
-               local_timer_interrupt (irq, dev_id, regs);
+               local_timer_interrupt(irq, dev_id, regs);
        }
+#endif /* CONFIG_MIPS_MT_SMTC */
 
 out:
        return IRQ_HANDLED;
@@ -126,7 +176,7 @@ static unsigned int __init estimate_cpu_frequency(void)
        unsigned int prid = read_c0_prid() & 0xffff00;
        unsigned int count;
 
-#ifdef CONFIG_MIPS_SEAD
+#if defined(CONFIG_MIPS_SEAD) || defined(CONFIG_MIPS_SIM)
        /*
         * The SEAD board doesn't have a real time clock, so we can't
         * really calculate the timer frequency
@@ -211,7 +261,11 @@ void __init mips_timer_setup(struct irqaction *irq)
 
        /* we are using the cpu counter for timer interrupts */
        irq->handler = mips_timer_interrupt;    /* we use our own handler */
+#ifdef CONFIG_MIPS_MT_SMTC
+       setup_irq_smtc(mips_cpu_timer_irq, irq, CPUCTR_IMASKBIT);
+#else
        setup_irq(mips_cpu_timer_irq, irq);
+#endif /* CONFIG_MIPS_MT_SMTC */
 
 #ifdef CONFIG_SMP
        /* irq_desc(riptor) is a global resource, when the interrupt overlaps
index fd4c143c0e2f712cf0cf8c68e0b70a0fed93a53b..77ee5c6d33c119964da2619f5484cf83772e3b49 100644 (file)
@@ -20,3 +20,4 @@
 #
 
 obj-y := malta_int.o malta_setup.o
+obj-$(CONFIG_SMP) += malta_smp.o
index d06dc5ad6c9e55edd2284540ea01e729f2678d55..64db07d4dbe500d5c3a66355ff1f19c9f6e9ec34 100644 (file)
@@ -40,7 +40,6 @@
 #include <asm/mips-boards/msc01_pci.h>
 #include <asm/msc01_ic.h>
 
-extern asmlinkage void mipsIRQ(void);
 extern void mips_timer_interrupt(void);
 
 static DEFINE_SPINLOCK(mips_irq_lock);
@@ -114,13 +113,14 @@ static inline int get_int(void)
        return irq;
 }
 
-void malta_hw0_irqdispatch(struct pt_regs *regs)
+static void malta_hw0_irqdispatch(struct pt_regs *regs)
 {
        int irq;
 
        irq = get_int();
-       if (irq < 0)
+       if (irq < 0) {
                return;  /* interrupt has already been cleared */
+       }
 
        do_IRQ(MALTA_INT_BASE+irq, regs);
 }
@@ -182,6 +182,92 @@ void corehi_irqdispatch(struct pt_regs *regs)
         die("CoreHi interrupt", regs);
 }
 
+static inline int clz(unsigned long x)
+{
+       __asm__ (
+       "       .set    push                                    \n"
+       "       .set    mips32                                  \n"
+       "       clz     %0, %1                                  \n"
+       "       .set    pop                                     \n"
+       : "=r" (x)
+       : "r" (x));
+
+       return x;
+}
+
+/*
+ * Version of ffs that only looks at bits 12..15.
+ */
+static inline unsigned int irq_ffs(unsigned int pending)
+{
+#if defined(CONFIG_CPU_MIPS32) || defined(CONFIG_CPU_MIPS64)
+       return -clz(pending) + 31 - CAUSEB_IP;
+#else
+       unsigned int a0 = 7;
+       unsigned int t0;
+
+       t0 = s0 & 0xf000;
+       t0 = t0 < 1;
+       t0 = t0 << 2;
+       a0 = a0 - t0;
+       s0 = s0 << t0;
+
+       t0 = s0 & 0xc000;
+       t0 = t0 < 1;
+       t0 = t0 << 1;
+       a0 = a0 - t0;
+       s0 = s0 << t0;
+
+       t0 = s0 & 0x8000;
+       t0 = t0 < 1;
+       //t0 = t0 << 2;
+       a0 = a0 - t0;
+       //s0 = s0 << t0;
+
+       return a0;
+#endif
+}
+
+/*
+ * IRQs on the Malta board look basically (barring software IRQs which we
+ * don't use at all and all external interrupt sources are combined together
+ * on hardware interrupt 0 (MIPS IRQ 2)) like:
+ *
+ *     MIPS IRQ        Source
+ *      --------        ------
+ *             0       Software (ignored)
+ *             1        Software (ignored)
+ *             2        Combined hardware interrupt (hw0)
+ *             3        Hardware (ignored)
+ *             4        Hardware (ignored)
+ *             5        Hardware (ignored)
+ *             6        Hardware (ignored)
+ *             7        R4k timer (what we use)
+ *
+ * We handle the IRQ according to _our_ priority which is:
+ *
+ * Highest ----     R4k Timer
+ * Lowest  ----     Combined hardware interrupt
+ *
+ * then we just return, if multiple IRQs are pending then we will just take
+ * another exception, big deal.
+ */
+
+asmlinkage void plat_irq_dispatch(struct pt_regs *regs)
+{
+       unsigned int pending = read_c0_cause() & read_c0_status() & ST0_IM;
+       int irq;
+
+       irq = irq_ffs(pending);
+
+       if (irq == MIPSCPU_INT_I8259A)
+               malta_hw0_irqdispatch(regs);
+       else if (irq > 0)
+               do_IRQ(MIPSCPU_INT_BASE + irq, regs);
+       else
+               spurious_interrupt(regs);
+}
+
 static struct irqaction i8259irq = {
        .handler = no_action,
        .name = "XT-PIC cascade"
@@ -214,7 +300,6 @@ int __initdata msc_nr_eicirqs = sizeof(msc_eicirqmap)/sizeof(msc_irqmap_t);
 
 void __init arch_init_irq(void)
 {
-       set_except_vector(0, mipsIRQ);
        init_i8259_irqs();
 
        if (!cpu_has_veic)
@@ -240,12 +325,17 @@ void __init arch_init_irq(void)
        else if (cpu_has_vint) {
                set_vi_handler (MIPSCPU_INT_I8259A, malta_hw0_irqdispatch);
                set_vi_handler (MIPSCPU_INT_COREHI, corehi_irqdispatch);
-
+#ifdef CONFIG_MIPS_MT_SMTC
+               setup_irq_smtc (MIPSCPU_INT_BASE+MIPSCPU_INT_I8259A, &i8259irq,
+                       (0x100 << MIPSCPU_INT_I8259A));
+               setup_irq_smtc (MIPSCPU_INT_BASE+MIPSCPU_INT_COREHI,
+                       &corehi_irqaction, (0x100 << MIPSCPU_INT_COREHI));
+#else /* Not SMTC */
                setup_irq (MIPSCPU_INT_BASE+MIPSCPU_INT_I8259A, &i8259irq);
                setup_irq (MIPSCPU_INT_BASE+MIPSCPU_INT_COREHI, &corehi_irqaction);
+#endif /* CONFIG_MIPS_MT_SMTC */
        }
        else {
-               set_except_vector(0, mipsIRQ);
                setup_irq (MIPSCPU_INT_BASE+MIPSCPU_INT_I8259A, &i8259irq);
                setup_irq (MIPSCPU_INT_BASE+MIPSCPU_INT_COREHI, &corehi_irqaction);
        }
diff --git a/arch/mips/mips-boards/malta/malta_smp.c b/arch/mips/mips-boards/malta/malta_smp.c
new file mode 100644 (file)
index 0000000..6c6c8ee
--- /dev/null
@@ -0,0 +1,128 @@
+/*
+ * Malta Platform-specific hooks for SMP operation
+ */
+
+#include <linux/kernel.h>
+#include <linux/sched.h>
+#include <linux/cpumask.h>
+#include <linux/interrupt.h>
+
+#include <asm/atomic.h>
+#include <asm/cpu.h>
+#include <asm/processor.h>
+#include <asm/system.h>
+#include <asm/hardirq.h>
+#include <asm/mmu_context.h>
+#include <asm/smp.h>
+#ifdef CONFIG_MIPS_MT_SMTC
+#include <asm/smtc_ipi.h>
+#endif /* CONFIG_MIPS_MT_SMTC */
+
+/* VPE/SMP Prototype implements platform interfaces directly */
+#if !defined(CONFIG_MIPS_MT_SMP)
+
+/*
+ * Cause the specified action to be performed on a targeted "CPU"
+ */
+
+void core_send_ipi(int cpu, unsigned int action)
+{
+/* "CPU" may be TC of same VPE, VPE of same CPU, or different CPU */
+#ifdef CONFIG_MIPS_MT_SMTC
+       smtc_send_ipi(cpu, LINUX_SMP_IPI, action);
+#endif /* CONFIG_MIPS_MT_SMTC */
+}
+
+/*
+ * Detect available CPUs/VPEs/TCs and populate phys_cpu_present_map
+ */
+
+void __init prom_build_cpu_map(void)
+{
+       int nextslot;
+
+       /*
+        * As of November, 2004, MIPSsim only simulates one core
+        * at a time.  However, that core may be a MIPS MT core
+        * with multiple virtual processors and thread contexts.
+        */
+
+       if (read_c0_config3() & (1<<2)) {
+               nextslot = mipsmt_build_cpu_map(1);
+       }
+}
+
+/*
+ * Platform "CPU" startup hook
+ */
+
+void prom_boot_secondary(int cpu, struct task_struct *idle)
+{
+#ifdef CONFIG_MIPS_MT_SMTC
+       smtc_boot_secondary(cpu, idle);
+#endif /* CONFIG_MIPS_MT_SMTC */
+}
+
+/*
+ * Post-config but pre-boot cleanup entry point
+ */
+
+void prom_init_secondary(void)
+{
+#ifdef CONFIG_MIPS_MT_SMTC
+        void smtc_init_secondary(void);
+       int myvpe;
+
+       /* Don't enable Malta I/O interrupts (IP2) for secondary VPEs */
+       myvpe = read_c0_tcbind() & TCBIND_CURVPE;
+       if (myvpe != 0) {
+               /* Ideally, this should be done only once per VPE, but... */
+               clear_c0_status(STATUSF_IP2);
+               set_c0_status(STATUSF_IP0 | STATUSF_IP1 | STATUSF_IP3
+                               | STATUSF_IP4 | STATUSF_IP5 | STATUSF_IP6
+                               | STATUSF_IP7);
+       }
+
+        smtc_init_secondary();
+#endif /* CONFIG_MIPS_MT_SMTC */
+}
+
+/*
+ * Platform SMP pre-initialization
+ *
+ * As noted above, we can assume a single CPU for now
+ * but it may be multithreaded.
+ */
+
+void plat_smp_setup(void)
+{
+       if (read_c0_config3() & (1<<2))
+               mipsmt_build_cpu_map(0);
+}
+
+void __init plat_prepare_cpus(unsigned int max_cpus)
+{
+       if (read_c0_config3() & (1<<2))
+               mipsmt_prepare_cpus();
+}
+
+/*
+ * SMP initialization finalization entry point
+ */
+
+void prom_smp_finish(void)
+{
+#ifdef CONFIG_MIPS_MT_SMTC
+       smtc_smp_finish();
+#endif /* CONFIG_MIPS_MT_SMTC */
+}
+
+/*
+ * Hook for after all CPUs are online
+ */
+
+void prom_cpus_done(void)
+{
+}
+
+#endif /* CONFIG_MIPS32R2_MT_SMP */
index 90fda0d9915f6464718c296df52d2111588b2c2c..9168d934c661477d421c784f4569c0cbffc668d3 100644 (file)
 #include <linux/irq.h>
 
 #include <asm/irq_cpu.h>
+#include <asm/mipsregs.h>
 #include <asm/system.h>
 
 #include <asm/mips-boards/seadint.h>
 
-extern asmlinkage void mipsIRQ(void);
+static inline int clz(unsigned long x)
+{
+       __asm__ (
+       "       .set    push                                    \n"
+       "       .set    mips32                                  \n"
+       "       clz     %0, %1                                  \n"
+       "       .set    pop                                     \n"
+       : "=r" (x)
+       : "r" (x));
+
+       return x;
+}
+
+/*
+ * Version of ffs that only looks at bits 12..15.
+ */
+static inline unsigned int irq_ffs(unsigned int pending)
+{
+#if defined(CONFIG_CPU_MIPS32) || defined(CONFIG_CPU_MIPS64)
+       return -clz(pending) + 31 - CAUSEB_IP;
+#else
+       unsigned int a0 = 7;
+       unsigned int t0;
+
+       t0 = s0 & 0xf000;
+       t0 = t0 < 1;
+       t0 = t0 << 2;
+       a0 = a0 - t0;
+       s0 = s0 << t0;
+
+       t0 = s0 & 0xc000;
+       t0 = t0 < 1;
+       t0 = t0 << 1;
+       a0 = a0 - t0;
+       s0 = s0 << t0;
+
+       t0 = s0 & 0x8000;
+       t0 = t0 < 1;
+       //t0 = t0 << 2;
+       a0 = a0 - t0;
+       //s0 = s0 << t0;
+
+       return a0;
+#endif
+}
+
+/*
+ * IRQs on the SEAD board look basically are combined together on hardware
+ * interrupt 0 (MIPS IRQ 2)) like:
+ *
+ *     MIPS IRQ        Source
+ *      --------        ------
+ *             0       Software (ignored)
+ *             1        Software (ignored)
+ *             2        UART0 (hw0)
+ *             3        UART1 (hw1)
+ *             4        Hardware (ignored)
+ *             5        Hardware (ignored)
+ *             6        Hardware (ignored)
+ *             7        R4k timer (what we use)
+ *
+ * We handle the IRQ according to _our_ priority which is:
+ *
+ * Highest ----     R4k Timer
+ * Lowest  ----     Combined hardware interrupt
+ *
+ * then we just return, if multiple IRQs are pending then we will just take
+ * another exception, big deal.
+ */
+asmlinkage void plat_irq_dispatch(struct pt_regs *regs)
+{
+       unsigned int pending = read_c0_cause() & read_c0_status() & ST0_IM;
+       int irq;
+
+       irq = irq_ffs(pending);
+
+       if (irq >= 0)
+               do_IRQ(MIPSCPU_INT_BASE + irq, regs);
+       else
+               spurious_interrupt(regs);
+}
 
 void __init arch_init_irq(void)
 {
        mips_cpu_irq_init(MIPSCPU_INT_BASE);
-
-       /* Now safe to set the exception vector. */
-       set_except_vector(0, mipsIRQ);
 }
diff --git a/arch/mips/mips-boards/sim/cmdline.c b/arch/mips/mips-boards/sim/cmdline.c
deleted file mode 100644 (file)
index fef9fbd..0000000
+++ /dev/null
@@ -1,59 +0,0 @@
-/*
- * Carsten Langgaard, carstenl@mips.com
- * Copyright (C) 1999,2000 MIPS Technologies, Inc.  All rights reserved.
- *
- * This program is free software; you can distribute 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 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.,
- * 59 Temple Place - Suite 330, Boston MA 02111-1307, USA.
- *
- * Kernel command line creation using the prom monitor (YAMON) argc/argv.
- */
-#include <linux/init.h>
-#include <linux/string.h>
-
-#include <asm/bootinfo.h>
-
-extern int prom_argc;
-extern int *_prom_argv;
-
-/*
- * YAMON (32-bit PROM) pass arguments and environment as 32-bit pointer.
- * This macro take care of sign extension.
- */
-#define prom_argv(index) ((char *)(((int *)(int)_prom_argv)[(index)]))
-
-char arcs_cmdline[CL_SIZE];
-
-char * __init prom_getcmdline(void)
-{
-       return &(arcs_cmdline[0]);
-}
-
-
-void  __init prom_init_cmdline(void)
-{
-       char *cp;
-       int actr;
-
-       actr = 1; /* Always ignore argv[0] */
-
-       cp = &(arcs_cmdline[0]);
-       while(actr < prom_argc) {
-               strcpy(cp, prom_argv(actr));
-               cp += strlen(prom_argv(actr));
-               *cp++ = ' ';
-               actr++;
-       }
-       if (cp != &(arcs_cmdline[0])) /* get rid of trailing space */
-               --cp;
-       *cp = '\0';
-}
index 9df37c6fca36ac5815c02d2017ad9566b1515675..c63021a5dc6c8928f216a8c35911ca90f0ec48b9 100644 (file)
@@ -26,8 +26,10 @@ char * __init prom_getcmdline(void)
        return arcs_cmdline;
 }
 
-
 void  __init prom_init_cmdline(void)
 {
-    /* nothing to do */
+       char *cp;
+       cp = arcs_cmdline;
+       /* Get boot line from environment? */
+       *cp = '\0';
 }
index a4d0a2c05031ed5ff5d37136200eb8e367108067..2c15c8efec4e30c8e0bdc27df5e5327c644117b5 100644 (file)
 
 extern void mips_cpu_irq_init(int);
 
-extern asmlinkage void simIRQ(void);
+static inline int clz(unsigned long x)
+{
+       __asm__ (
+       "       .set    push                                    \n"
+       "       .set    mips32                                  \n"
+       "       clz     %0, %1                                  \n"
+       "       .set    pop                                     \n"
+       : "=r" (x)
+       : "r" (x));
+
+       return x;
+}
+
+/*
+ * Version of ffs that only looks at bits 12..15.
+ */
+static inline unsigned int irq_ffs(unsigned int pending)
+{
+#if defined(CONFIG_CPU_MIPS32) || defined(CONFIG_CPU_MIPS64)
+       return -clz(pending) + 31 - CAUSEB_IP;
+#else
+       unsigned int a0 = 7;
+       unsigned int t0;
+
+       t0 = s0 & 0xf000;
+       t0 = t0 < 1;
+       t0 = t0 << 2;
+       a0 = a0 - t0;
+       s0 = s0 << t0;
+
+       t0 = s0 & 0xc000;
+       t0 = t0 < 1;
+       t0 = t0 << 1;
+       a0 = a0 - t0;
+       s0 = s0 << t0;
 
-asmlinkage void sim_hw0_irqdispatch(struct pt_regs *regs)
+       t0 = s0 & 0x8000;
+       t0 = t0 < 1;
+       //t0 = t0 << 2;
+       a0 = a0 - t0;
+       //s0 = s0 << t0;
+
+       return a0;
+#endif
+}
+
+static inline void sim_hw0_irqdispatch(struct pt_regs *regs)
 {
        do_IRQ(2, regs);
 }
 
-void __init arch_init_irq(void)
+asmlinkage void plat_irq_dispatch(struct pt_regs *regs)
 {
-       /* Now safe to set the exception vector. */
-       set_except_vector(0, simIRQ);
+       unsigned int pending = read_c0_cause() & read_c0_status() & ST0_IM;
+       int irq;
+
+       irq = irq_ffs(pending);
 
+       if (irq > 0)
+               do_IRQ(MIPSCPU_INT_BASE + irq, regs);
+       else
+               spurious_interrupt(regs);
+}
+
+void __init arch_init_irq(void)
+{
        mips_cpu_irq_init(MIPSCPU_INT_BASE);
 }
index da52297a221635b839b9537c8ef6a5ad4c8d70c6..d16cf38220763f34f7ef1a52da91cc4be21076b7 100644 (file)
@@ -94,6 +94,8 @@
 
 
 spurious:
-       j       spurious_interrupt
+       jal     spurious_interrupt
+        nop
+       j       ret_from_irq
         nop
        END(simIRQ)
index e57f737bab10265aeb1b46866336ad57651e24ba..f7ce769833283b38c6af2ecc8c3c24dd1db6c352 100644 (file)
 #include <linux/init.h>
 #include <linux/mm.h>
 #include <linux/bootmem.h>
+#include <linux/pfn.h>
 
 #include <asm/bootinfo.h>
 #include <asm/page.h>
+#include <asm/sections.h>
 
 #include <asm/mips-boards/prom.h>
 
@@ -39,9 +41,6 @@ static char *mtypes[3] = {
 };
 #endif
 
-/* References to section boundaries */
-extern char _end;
-
 struct prom_pmemblock * __init prom_getmdesc(void)
 {
        unsigned int memsize;
@@ -61,10 +60,10 @@ struct prom_pmemblock * __init prom_getmdesc(void)
 
        mdesc[2].type = simmem_reserved;
        mdesc[2].base = 0x00100000;
-       mdesc[2].size = CPHYSADDR(PAGE_ALIGN(&_end)) - mdesc[2].base;
+       mdesc[2].size = CPHYSADDR(PFN_ALIGN(&_end)) - mdesc[2].base;
 
        mdesc[3].type = simmem_free;
-       mdesc[3].base = CPHYSADDR(PAGE_ALIGN(&_end));
+       mdesc[3].base = CPHYSADDR(PFN_ALIGN(&_end));
        mdesc[3].size = memsize - mdesc[3].base;
 
        return &mdesc[0];
index a9f0c2bfe4ad7b4ee63480d6ec4b88b919a80c17..b7084e7c4bf9b7c4bce0ee742301ddfe198e85d5 100644 (file)
@@ -44,8 +44,6 @@
 void core_send_ipi(int cpu, unsigned int action)
 {
 #ifdef CONFIG_MIPS_MT_SMTC
-       void smtc_send_ipi(int, int, unsigned int);
-
        smtc_send_ipi(cpu, LINUX_SMP_IPI, action);
 #endif /* CONFIG_MIPS_MT_SMTC */
 /* "CPU" may be TC of same VPE, VPE of same CPU, or different CPU */
@@ -59,15 +57,8 @@ void core_send_ipi(int cpu, unsigned int action)
 void __init prom_build_cpu_map(void)
 {
 #ifdef CONFIG_MIPS_MT_SMTC
-       extern int mipsmt_build_cpu_map(int startslot);
        int nextslot;
 
-       cpus_clear(phys_cpu_present_map);
-
-       /* Register the boot CPU */
-
-       smp_prepare_boot_cpu();
-
        /*
         * As of November, 2004, MIPSsim only simulates one core
         * at a time.  However, that core may be a MIPS MT core
@@ -87,8 +78,6 @@ void __init prom_build_cpu_map(void)
 void prom_boot_secondary(int cpu, struct task_struct *idle)
 {
 #ifdef CONFIG_MIPS_MT_SMTC
-       extern void smtc_boot_secondary(int cpu, struct task_struct *t);
-
        smtc_boot_secondary(cpu, idle);
 #endif /* CONFIG_MIPS_MT_SMTC */
 }
@@ -113,7 +102,6 @@ void prom_init_secondary(void)
 void prom_prepare_cpus(unsigned int max_cpus)
 {
 #ifdef CONFIG_MIPS_MT_SMTC
-       void mipsmt_prepare_cpus(int c);
        /*
         * As noted above, we can assume a single CPU for now
         * but it may be multithreaded.
@@ -132,8 +120,6 @@ void prom_prepare_cpus(unsigned int max_cpus)
 void prom_smp_finish(void)
 {
 #ifdef CONFIG_MIPS_MT_SMTC
-       void smtc_smp_finish(void);
-
        smtc_smp_finish();
 #endif /* CONFIG_MIPS_MT_SMTC */
 }
index 9dd1352d57484a0b015b992c8759089ab5b483ab..bb041a22f20a55dd35f9eb28ffb3e5073abff1e8 100644 (file)
@@ -260,6 +260,10 @@ static void r3k_flush_cache_page(struct vm_area_struct *vma, unsigned long page,
 {
 }
 
+static void local_r3k_flush_data_cache_page(unsigned long addr)
+{
+}
+
 static void r3k_flush_data_cache_page(unsigned long addr)
 {
 }
@@ -335,6 +339,7 @@ void __init r3k_cache_init(void)
        flush_icache_range = r3k_flush_icache_range;
 
        flush_cache_sigtramp = r3k_flush_cache_sigtramp;
+       local_flush_data_cache_page = local_r3k_flush_data_cache_page;
        flush_data_cache_page = r3k_flush_data_cache_page;
 
        _dma_cache_wback_inv = r3k_dma_cache_wback_inv;
index 32b7f6aeb983271201702594c9d3a2da3e32ce5b..4182e1176faeaeb1181af9fe7d12094b42db1fc4 100644 (file)
@@ -154,7 +154,8 @@ static inline void blast_icache32_r4600_v1_page_indexed(unsigned long page)
 
 static inline void tx49_blast_icache32_page_indexed(unsigned long page)
 {
-       unsigned long start = page;
+       unsigned long indexmask = current_cpu_data.icache.waysize - 1;
+       unsigned long start = INDEX_BASE + (page & indexmask);
        unsigned long end = start + PAGE_SIZE;
        unsigned long ws_inc = 1UL << current_cpu_data.icache.waybit;
        unsigned long ws_end = current_cpu_data.icache.ways <<
@@ -749,12 +750,12 @@ static void __init probe_pcache(void)
                icache_size = 1 << (12 + ((config & CONF_IC) >> 9));
                c->icache.linesz = 16 << ((config & CONF_IB) >> 5);
                c->icache.ways = 2;
-               c->icache.waybit = ffs(icache_size/2) - 1;
+               c->icache.waybit = __ffs(icache_size/2);
 
                dcache_size = 1 << (12 + ((config & CONF_DC) >> 6));
                c->dcache.linesz = 16 << ((config & CONF_DB) >> 4);
                c->dcache.ways = 2;
-               c->dcache.waybit= ffs(dcache_size/2) - 1;
+               c->dcache.waybit= __ffs(dcache_size/2);
 
                c->options |= MIPS_CPU_CACHE_CDEX_P;
                break;
@@ -837,12 +838,12 @@ static void __init probe_pcache(void)
                icache_size = 1 << (10 + ((config & CONF_IC) >> 9));
                c->icache.linesz = 16 << ((config & CONF_IB) >> 5);
                c->icache.ways = 2;
-               c->icache.waybit = ffs(icache_size/2) - 1;
+               c->icache.waybit = __ffs(icache_size/2);
 
                dcache_size = 1 << (10 + ((config & CONF_DC) >> 6));
                c->dcache.linesz = 16 << ((config & CONF_DB) >> 4);
                c->dcache.ways = 2;
-               c->dcache.waybit = ffs(dcache_size/2) - 1;
+               c->dcache.waybit = __ffs(dcache_size/2);
 
                c->options |= MIPS_CPU_CACHE_CDEX_P;
                break;
@@ -873,12 +874,12 @@ static void __init probe_pcache(void)
                icache_size = 1 << (12 + ((config & CONF_IC) >> 9));
                c->icache.linesz = 16 << ((config & CONF_IB) >> 5);
                c->icache.ways = 4;
-               c->icache.waybit = ffs(icache_size / c->icache.ways) - 1;
+               c->icache.waybit = __ffs(icache_size / c->icache.ways);
 
                dcache_size = 1 << (12 + ((config & CONF_DC) >> 6));
                c->dcache.linesz = 16 << ((config & CONF_DB) >> 4);
                c->dcache.ways = 4;
-               c->dcache.waybit = ffs(dcache_size / c->dcache.ways) - 1;
+               c->dcache.waybit = __ffs(dcache_size / c->dcache.ways);
 
 #if !defined(CONFIG_SMP) || !defined(RM9000_CDEX_SMP_WAR)
                c->options |= MIPS_CPU_CACHE_CDEX_P;
@@ -906,7 +907,7 @@ static void __init probe_pcache(void)
                icache_size = c->icache.sets *
                              c->icache.ways *
                              c->icache.linesz;
-               c->icache.waybit = ffs(icache_size/c->icache.ways) - 1;
+               c->icache.waybit = __ffs(icache_size/c->icache.ways);
 
                if (config & 0x8)               /* VI bit */
                        c->icache.flags |= MIPS_CACHE_VTAG;
@@ -926,7 +927,7 @@ static void __init probe_pcache(void)
                dcache_size = c->dcache.sets *
                              c->dcache.ways *
                              c->dcache.linesz;
-               c->dcache.waybit = ffs(dcache_size/c->dcache.ways) - 1;
+               c->dcache.waybit = __ffs(dcache_size/c->dcache.ways);
 
                c->options |= MIPS_CPU_PREFETCH;
                break;
@@ -1198,6 +1199,7 @@ void __init r4k_cache_init(void)
 
        flush_cache_sigtramp    = r4k_flush_cache_sigtramp;
        flush_icache_all        = r4k_flush_icache_all;
+       local_flush_data_cache_page     = local_r4k_flush_data_cache_page;
        flush_data_cache_page   = r4k_flush_data_cache_page;
        flush_icache_range      = r4k_flush_icache_range;
 
index 2f08b535f20e8e9e6adc8a287398277598b36a5d..f9b129491b1e4e038019d715e0d4d63ae4b34629 100644 (file)
@@ -528,6 +528,7 @@ void sb1_cache_init(void)
        flush_cache_page = sb1_flush_cache_page;
 
        flush_cache_sigtramp = sb1_flush_cache_sigtramp;
+       local_flush_data_cache_page = (void *) sb1_nop;
        flush_data_cache_page = (void *) sb1_nop;
 
        /* Full flush */
index fe232e3988e39ade564b1141cf2a97870fca5952..5dfc9b1901f6537554bc7e34a1820b8cc8d5a6c0 100644 (file)
@@ -216,6 +216,11 @@ static void tx39_flush_cache_page(struct vm_area_struct *vma, unsigned long page
                tx39_blast_icache_page_indexed(page);
 }
 
+static void local_tx39_flush_data_cache_page(void * addr)
+{
+       tx39_blast_dcache_page(addr);
+}
+
 static void tx39_flush_data_cache_page(unsigned long addr)
 {
        tx39_blast_dcache_page(addr);
@@ -381,6 +386,7 @@ void __init tx39_cache_init(void)
                flush_icache_range      = (void *) tx39h_flush_icache_all;
 
                flush_cache_sigtramp    = (void *) tx39h_flush_icache_all;
+               local_flush_data_cache_page     = (void *) tx39h_flush_icache_all;
                flush_data_cache_page   = (void *) tx39h_flush_icache_all;
 
                _dma_cache_wback_inv    = tx39h_dma_cache_wback_inv;
@@ -406,6 +412,7 @@ void __init tx39_cache_init(void)
                flush_icache_range = tx39_flush_icache_range;
 
                flush_cache_sigtramp = tx39_flush_cache_sigtramp;
+               local_flush_data_cache_page = local_tx39_flush_data_cache_page;
                flush_data_cache_page = tx39_flush_data_cache_page;
 
                _dma_cache_wback_inv = tx39_dma_cache_wback_inv;
index 591c22b080e427edc681248508b86ffc3a3fecb7..83a56296be86d063c08296b6e39bb1df9ccaef85 100644 (file)
@@ -30,6 +30,7 @@ void (*flush_icache_page)(struct vm_area_struct *vma, struct page *page);
 
 /* MIPS specific cache operations */
 void (*flush_cache_sigtramp)(unsigned long addr);
+void (*local_flush_data_cache_page)(void * addr);
 void (*flush_data_cache_page)(unsigned long addr);
 void (*flush_icache_all)(void);
 
index 2d9624fd10ecb4ad61cc33f55901f2109d6a4137..e3a617224868f04643719e68c9020d9941688efc 100644 (file)
@@ -157,7 +157,6 @@ no_context:
         * Oops. The kernel tried to access some bad page. We'll have to
         * terminate things with extreme prejudice.
         */
-
        bust_spinlocks(1);
 
        printk(KERN_ALERT "CPU %d Unable to handle kernel paging request at "
@@ -188,11 +187,20 @@ do_sigbus:
        /* Kernel mode? Handle exceptions or die */
        if (!user_mode(regs))
                goto no_context;
-
+       else
        /*
         * Send a sigbus, regardless of whether we were in kernel
         * or user mode.
         */
+#if 0
+               printk("do_page_fault() #3: sending SIGBUS to %s for "
+                      "invalid %s\n%0*lx (epc == %0*lx, ra == %0*lx)\n",
+                      tsk->comm,
+                      write ? "write access to" : "read access from",
+                      field, address,
+                      field, (unsigned long) regs->cp0_epc,
+                      field, (unsigned long) regs->regs[31]);
+#endif
        tsk->thread.cp0_badvaddr = address;
        info.si_signo = SIGBUS;
        info.si_errno = 0;
@@ -201,7 +209,6 @@ do_sigbus:
        force_sig_info(SIGBUS, &info, tsk);
 
        return;
-
 vmalloc_fault:
        {
                /*
index 1f7b37b38f5c740839208cf7f6728e3335fde7f0..0c544375b856be81235c121c0fca81f0290deeb0 100644 (file)
@@ -83,6 +83,7 @@ void __kunmap_atomic(void *kvaddr, enum km_type type)
        preempt_check_resched();
 }
 
+#ifndef CONFIG_LIMITED_DMA
 /*
  * This is the same as kmap_atomic() but can map memory that doesn't
  * have a struct page associated with it.
@@ -101,6 +102,7 @@ void *kmap_atomic_pfn(unsigned long pfn, enum km_type type)
 
        return (void*) vaddr;
 }
+#endif /* CONFIG_LIMITED_DMA */
 
 struct page *__kmap_atomic_to_page(void *ptr)
 {
index ad89c442f2998918d52fdac6ad7a98c193fcdfa2..c22308b93ff05ce04aee860042733a63dc2bf713 100644 (file)
@@ -276,6 +276,20 @@ void __init mem_init(void)
 }
 #endif /* !CONFIG_NEED_MULTIPLE_NODES */
 
+void free_init_pages(char *what, unsigned long begin, unsigned long end)
+{
+       unsigned long addr;
+
+       for (addr = begin; addr < end; addr += PAGE_SIZE) {
+               ClearPageReserved(virt_to_page(addr));
+               init_page_count(virt_to_page(addr));
+               memset((void *)addr, 0xcc, PAGE_SIZE);
+               free_page(addr);
+               totalram_pages++;
+       }
+       printk(KERN_INFO "Freeing %s: %ldk freed\n", what, (end - begin) >> 10);
+}
+
 #ifdef CONFIG_BLK_DEV_INITRD
 void free_initrd_mem(unsigned long start, unsigned long end)
 {
@@ -284,16 +298,7 @@ void free_initrd_mem(unsigned long start, unsigned long end)
        start = (unsigned long)phys_to_virt(CPHYSADDR(start));
        end = (unsigned long)phys_to_virt(CPHYSADDR(end));
 #endif
-       if (start < end)
-               printk(KERN_INFO "Freeing initrd memory: %ldk freed\n",
-                      (end - start) >> 10);
-
-       for (; start < end; start += PAGE_SIZE) {
-               ClearPageReserved(virt_to_page(start));
-               init_page_count(virt_to_page(start));
-               free_page(start);
-               totalram_pages++;
-       }
+       free_init_pages("initrd memory", start, end);
 }
 #endif
 
@@ -301,24 +306,17 @@ extern unsigned long prom_free_prom_memory(void);
 
 void free_initmem(void)
 {
-       unsigned long addr, page, freed;
+       unsigned long start, end, freed;
 
        freed = prom_free_prom_memory();
+       if (freed)
+               printk(KERN_INFO "Freeing firmware memory: %ldk freed\n",freed);
 
-       addr = (unsigned long) &__init_begin;
-       while (addr < (unsigned long) &__init_end) {
+       start = (unsigned long)(&__init_begin);
+       end = (unsigned long)(&__init_end);
 #ifdef CONFIG_64BIT
-               page = PAGE_OFFSET | CPHYSADDR(addr);
-#else
-               page = addr;
+       start = PAGE_OFFSET | CPHYSADDR(start);
+       end = PAGE_OFFSET | CPHYSADDR(end);
 #endif
-               ClearPageReserved(virt_to_page(page));
-               init_page_count(virt_to_page(page));
-               free_page(page);
-               totalram_pages++;
-               freed += PAGE_SIZE;
-               addr += PAGE_SIZE;
-       }
-       printk(KERN_INFO "Freeing unused kernel memory: %ldk freed\n",
-              freed >> 10);
+       free_init_pages("unused kernel memory", start, end);
 }
index 3b6cc9ba1b052651b0c9b77fcb379e39668d0784..31ec730524239dcc9de7c22dd2cda845daa8b963 100644 (file)
@@ -138,7 +138,7 @@ void __init rm7k_sc_init(void)
 
        c->scache.linesz = sc_lsize;
        c->scache.ways = 4;
-       c->scache.waybit= ffs(scache_size / c->scache.ways) - 1;
+       c->scache.waybit= __ffs(scache_size / c->scache.ways);
        c->scache.waysize = scache_size / c->scache.ways;
        c->scache.sets = scache_size / (c->scache.linesz * c->scache.ways);
        printk(KERN_INFO "Secondary cache size %dK, linesize %d bytes.\n",
index a865f2394cb0d1de5d44acfdbbb1ee45b83beb28..9dca099ba16b01b907568d9f387f5ea9d693d665 100644 (file)
@@ -32,13 +32,35 @@ extern void build_tlb_refill_handler(void);
                                     "nop; nop; nop; nop; nop; nop;\n\t" \
                                     ".set reorder\n\t")
 
+/* Atomicity and interruptability */
+#ifdef CONFIG_MIPS_MT_SMTC
+
+#include <asm/smtc.h>
+#include <asm/mipsmtregs.h>
+
+#define ENTER_CRITICAL(flags) \
+       { \
+       unsigned int mvpflags; \
+       local_irq_save(flags);\
+       mvpflags = dvpe()
+#define EXIT_CRITICAL(flags) \
+       evpe(mvpflags); \
+       local_irq_restore(flags); \
+       }
+#else
+
+#define ENTER_CRITICAL(flags) local_irq_save(flags)
+#define EXIT_CRITICAL(flags) local_irq_restore(flags)
+
+#endif /* CONFIG_MIPS_MT_SMTC */
+
 void local_flush_tlb_all(void)
 {
        unsigned long flags;
        unsigned long old_ctx;
        int entry;
 
-       local_irq_save(flags);
+       ENTER_CRITICAL(flags);
        /* Save old context and create impossible VPN2 value */
        old_ctx = read_c0_entryhi();
        write_c0_entrylo0(0);
@@ -57,7 +79,7 @@ void local_flush_tlb_all(void)
        }
        tlbw_use_hazard();
        write_c0_entryhi(old_ctx);
-       local_irq_restore(flags);
+       EXIT_CRITICAL(flags);
 }
 
 /* All entries common to a mm share an asid.  To effectively flush
@@ -87,6 +109,7 @@ void local_flush_tlb_range(struct vm_area_struct *vma, unsigned long start,
                unsigned long flags;
                int size;
 
+               ENTER_CRITICAL(flags);
                size = (end - start + (PAGE_SIZE - 1)) >> PAGE_SHIFT;
                size = (size + 1) >> 1;
                local_irq_save(flags);
@@ -120,7 +143,7 @@ void local_flush_tlb_range(struct vm_area_struct *vma, unsigned long start,
                } else {
                        drop_mmu_context(mm, cpu);
                }
-               local_irq_restore(flags);
+               EXIT_CRITICAL(flags);
        }
 }
 
@@ -129,9 +152,9 @@ void local_flush_tlb_kernel_range(unsigned long start, unsigned long end)
        unsigned long flags;
        int size;
 
+       ENTER_CRITICAL(flags);
        size = (end - start + (PAGE_SIZE - 1)) >> PAGE_SHIFT;
        size = (size + 1) >> 1;
-       local_irq_save(flags);
        if (size <= current_cpu_data.tlbsize / 2) {
                int pid = read_c0_entryhi();
 
@@ -162,7 +185,7 @@ void local_flush_tlb_kernel_range(unsigned long start, unsigned long end)
        } else {
                local_flush_tlb_all();
        }
-       local_irq_restore(flags);
+       EXIT_CRITICAL(flags);
 }
 
 void local_flush_tlb_page(struct vm_area_struct *vma, unsigned long page)
@@ -175,7 +198,7 @@ void local_flush_tlb_page(struct vm_area_struct *vma, unsigned long page)
 
                newpid = cpu_asid(cpu, vma->vm_mm);
                page &= (PAGE_MASK << 1);
-               local_irq_save(flags);
+               ENTER_CRITICAL(flags);
                oldpid = read_c0_entryhi();
                write_c0_entryhi(page | newpid);
                mtc0_tlbw_hazard();
@@ -194,7 +217,7 @@ void local_flush_tlb_page(struct vm_area_struct *vma, unsigned long page)
 
        finish:
                write_c0_entryhi(oldpid);
-               local_irq_restore(flags);
+               EXIT_CRITICAL(flags);
        }
 }
 
@@ -207,7 +230,7 @@ void local_flush_tlb_one(unsigned long page)
        unsigned long flags;
        int oldpid, idx;
 
-       local_irq_save(flags);
+       ENTER_CRITICAL(flags);
        oldpid = read_c0_entryhi();
        page &= (PAGE_MASK << 1);
        write_c0_entryhi(page);
@@ -226,7 +249,7 @@ void local_flush_tlb_one(unsigned long page)
        }
        write_c0_entryhi(oldpid);
 
-       local_irq_restore(flags);
+       EXIT_CRITICAL(flags);
 }
 
 /*
@@ -249,7 +272,7 @@ void __update_tlb(struct vm_area_struct * vma, unsigned long address, pte_t pte)
        if (current->active_mm != vma->vm_mm)
                return;
 
-       local_irq_save(flags);
+       ENTER_CRITICAL(flags);
 
        pid = read_c0_entryhi() & ASID_MASK;
        address &= (PAGE_MASK << 1);
@@ -277,7 +300,7 @@ void __update_tlb(struct vm_area_struct * vma, unsigned long address, pte_t pte)
        else
                tlb_write_indexed();
        tlbw_use_hazard();
-       local_irq_restore(flags);
+       EXIT_CRITICAL(flags);
 }
 
 #if 0
@@ -291,7 +314,7 @@ static void r4k_update_mmu_cache_hwbug(struct vm_area_struct * vma,
        pte_t *ptep;
        int idx;
 
-       local_irq_save(flags);
+       ENTER_CRITICAL(flags);
        address &= (PAGE_MASK << 1);
        asid = read_c0_entryhi() & ASID_MASK;
        write_c0_entryhi(address | asid);
@@ -310,7 +333,7 @@ static void r4k_update_mmu_cache_hwbug(struct vm_area_struct * vma,
        else
                tlb_write_indexed();
        tlbw_use_hazard();
-       local_irq_restore(flags);
+       EXIT_CRITICAL(flags);
 }
 #endif
 
@@ -322,7 +345,7 @@ void __init add_wired_entry(unsigned long entrylo0, unsigned long entrylo1,
        unsigned long old_pagemask;
        unsigned long old_ctx;
 
-       local_irq_save(flags);
+       ENTER_CRITICAL(flags);
        /* Save old context and create impossible VPN2 value */
        old_ctx = read_c0_entryhi();
        old_pagemask = read_c0_pagemask();
@@ -342,7 +365,7 @@ void __init add_wired_entry(unsigned long entrylo0, unsigned long entrylo1,
        BARRIER;
        write_c0_pagemask(old_pagemask);
        local_flush_tlb_all();
-       local_irq_restore(flags);
+       EXIT_CRITICAL(flags);
 }
 
 /*
@@ -362,7 +385,7 @@ __init int add_temporary_entry(unsigned long entrylo0, unsigned long entrylo1,
        unsigned long old_pagemask;
        unsigned long old_ctx;
 
-       local_irq_save(flags);
+       ENTER_CRITICAL(flags);
        /* Save old context and create impossible VPN2 value */
        old_ctx = read_c0_entryhi();
        old_pagemask = read_c0_pagemask();
@@ -386,10 +409,11 @@ __init int add_temporary_entry(unsigned long entrylo0, unsigned long entrylo1,
        write_c0_entryhi(old_ctx);
        write_c0_pagemask(old_pagemask);
 out:
-       local_irq_restore(flags);
+       EXIT_CRITICAL(flags);
        return ret;
 }
 
+extern void __init sanitize_tlb_entries(void);
 static void __init probe_tlb(unsigned long config)
 {
        struct cpuinfo_mips *c = &current_cpu_data;
@@ -402,6 +426,14 @@ static void __init probe_tlb(unsigned long config)
         */
        if ((c->processor_id & 0xff0000) == PRID_COMP_LEGACY)
                return;
+#ifdef CONFIG_MIPS_MT_SMTC
+       /*
+        * If TLB is shared in SMTC system, total size already
+        * has been calculated and written into cpu_data tlbsize
+        */
+       if((smtc_status & SMTC_TLB_SHARED) == SMTC_TLB_SHARED)
+               return;
+#endif /* CONFIG_MIPS_MT_SMTC */
 
        reg = read_c0_config1();
        if (!((config >> 7) & 3))
@@ -410,6 +442,15 @@ static void __init probe_tlb(unsigned long config)
        c->tlbsize = ((reg >> 25) & 0x3f) + 1;
 }
 
+static int __initdata ntlb = 0;
+static int __init set_ntlb(char *str)
+{
+       get_option(&str, &ntlb);
+       return 1;
+}
+
+__setup("ntlb=", set_ntlb);
+
 void __init tlb_init(void)
 {
        unsigned int config = read_c0_config();
@@ -432,5 +473,15 @@ void __init tlb_init(void)
 
        /* Did I tell you that ARC SUCKS?  */
 
+       if (ntlb) {
+               if (ntlb > 1 && ntlb <= current_cpu_data.tlbsize) {
+                       int wired = current_cpu_data.tlbsize - ntlb;
+                       write_c0_wired(wired);
+                       write_c0_index(wired-1);
+                       printk ("Restricting TLB to %d entries\n", ntlb);
+               } else
+                       printk("Ignoring invalid argument ntlb=%d\n", ntlb);
+       }
+
        build_tlb_refill_handler();
 }
index 599b3c297186d360e3ce05cfd8f5135a827d021a..053dbacac56bdf4d5a797b0d115ddb1951297aa0 100644 (file)
@@ -7,6 +7,16 @@
  *
  * Copyright (C) 2004,2005 by Thiemo Seufer
  * Copyright (C) 2005  Maciej W. Rozycki
+ * Copyright (C) 2006  Ralf Baechle (ralf@linux-mips.org)
+ *
+ * ... and the days got worse and worse and now you see
+ * I've gone completly out of my mind.
+ *
+ * They're coming to take me a away haha
+ * they're coming to take me a away hoho hihi haha
+ * to the funny farm where code is beautiful all the time ...
+ *
+ * (Condolences to Napoleon XIV)
  */
 
 #include <stdarg.h>
@@ -68,6 +78,7 @@ enum fields
        BIMM = 0x040,
        JIMM = 0x080,
        FUNC = 0x100,
+       SET = 0x200
 };
 
 #define OP_MASK                0x2f
@@ -86,6 +97,8 @@ enum fields
 #define JIMM_SH                0
 #define FUNC_MASK      0x2f
 #define FUNC_SH                0
+#define SET_MASK       0x7
+#define SET_SH         0
 
 enum opcode {
        insn_invalid,
@@ -129,8 +142,8 @@ static __initdata struct insn insn_table[] = {
        { insn_bne, M(bne_op,0,0,0,0,0), RS | RT | BIMM },
        { insn_daddiu, M(daddiu_op,0,0,0,0,0), RS | RT | SIMM },
        { insn_daddu, M(spec_op,0,0,0,0,daddu_op), RS | RT | RD },
-       { insn_dmfc0, M(cop0_op,dmfc_op,0,0,0,0), RT | RD },
-       { insn_dmtc0, M(cop0_op,dmtc_op,0,0,0,0), RT | RD },
+       { insn_dmfc0, M(cop0_op,dmfc_op,0,0,0,0), RT | RD | SET},
+       { insn_dmtc0, M(cop0_op,dmtc_op,0,0,0,0), RT | RD | SET},
        { insn_dsll, M(spec_op,0,0,0,0,dsll_op), RT | RD | RE },
        { insn_dsll32, M(spec_op,0,0,0,0,dsll32_op), RT | RD | RE },
        { insn_dsra, M(spec_op,0,0,0,0,dsra_op), RT | RD | RE },
@@ -145,8 +158,8 @@ static __initdata struct insn insn_table[] = {
        { insn_lld, M(lld_op,0,0,0,0,0), RS | RT | SIMM },
        { insn_lui, M(lui_op,0,0,0,0,0), RT | SIMM },
        { insn_lw, M(lw_op,0,0,0,0,0), RS | RT | SIMM },
-       { insn_mfc0, M(cop0_op,mfc_op,0,0,0,0), RT | RD },
-       { insn_mtc0, M(cop0_op,mtc_op,0,0,0,0), RT | RD },
+       { insn_mfc0, M(cop0_op,mfc_op,0,0,0,0), RT | RD | SET},
+       { insn_mtc0, M(cop0_op,mtc_op,0,0,0,0), RT | RD | SET},
        { insn_ori, M(ori_op,0,0,0,0,0), RS | RT | UIMM },
        { insn_rfe, M(cop0_op,cop_op,0,0,0,rfe_op), 0 },
        { insn_sc, M(sc_op,0,0,0,0,0), RS | RT | SIMM },
@@ -242,6 +255,14 @@ static __init u32 build_func(u32 arg)
        return arg & FUNC_MASK;
 }
 
+static __init u32 build_set(u32 arg)
+{
+       if (arg & ~SET_MASK)
+               printk(KERN_WARNING "TLB synthesizer field overflow\n");
+
+       return arg & SET_MASK;
+}
+
 /*
  * The order of opcode arguments is implicitly left to right,
  * starting with RS and ending with FUNC or IMM.
@@ -273,6 +294,7 @@ static void __init build_insn(u32 **buf, enum opcode opc, ...)
        if (ip->fields & BIMM) op |= build_bimm(va_arg(ap, s32));
        if (ip->fields & JIMM) op |= build_jimm(va_arg(ap, u32));
        if (ip->fields & FUNC) op |= build_func(va_arg(ap, u32));
+       if (ip->fields & SET) op |= build_set(va_arg(ap, u32));
        va_end(ap);
 
        **buf = op;
@@ -358,8 +380,8 @@ I_u1s2(_bgezl);
 I_u1s2(_bltz);
 I_u1s2(_bltzl);
 I_u1u2s3(_bne);
-I_u1u2(_dmfc0);
-I_u1u2(_dmtc0);
+I_u1u2u3(_dmfc0);
+I_u1u2u3(_dmtc0);
 I_u2u1s3(_daddiu);
 I_u3u1u2(_daddu);
 I_u2u1u3(_dsll);
@@ -376,8 +398,8 @@ I_u2s3u1(_ll);
 I_u2s3u1(_lld);
 I_u1s2(_lui);
 I_u2s3u1(_lw);
-I_u1u2(_mfc0);
-I_u1u2(_mtc0);
+I_u1u2u3(_mfc0);
+I_u1u2u3(_mtc0);
 I_u2u1u3(_ori);
 I_0(_rfe);
 I_u2s3u1(_sc);
@@ -451,8 +473,8 @@ L_LA(_r3000_write_probe_fail)
 # define i_SLL(buf, rs, rt, sh) i_dsll(buf, rs, rt, sh)
 # define i_SRA(buf, rs, rt, sh) i_dsra(buf, rs, rt, sh)
 # define i_SRL(buf, rs, rt, sh) i_dsrl(buf, rs, rt, sh)
-# define i_MFC0(buf, rt, rd) i_dmfc0(buf, rt, rd)
-# define i_MTC0(buf, rt, rd) i_dmtc0(buf, rt, rd)
+# define i_MFC0(buf, rt, rd...) i_dmfc0(buf, rt, rd)
+# define i_MTC0(buf, rt, rd...) i_dmtc0(buf, rt, rd)
 # define i_ADDIU(buf, rs, rt, val) i_daddiu(buf, rs, rt, val)
 # define i_ADDU(buf, rs, rt, rd) i_daddu(buf, rs, rt, rd)
 # define i_SUBU(buf, rs, rt, rd) i_dsubu(buf, rs, rt, rd)
@@ -464,8 +486,8 @@ L_LA(_r3000_write_probe_fail)
 # define i_SLL(buf, rs, rt, sh) i_sll(buf, rs, rt, sh)
 # define i_SRA(buf, rs, rt, sh) i_sra(buf, rs, rt, sh)
 # define i_SRL(buf, rs, rt, sh) i_srl(buf, rs, rt, sh)
-# define i_MFC0(buf, rt, rd) i_mfc0(buf, rt, rd)
-# define i_MTC0(buf, rt, rd) i_mtc0(buf, rt, rd)
+# define i_MFC0(buf, rt, rd...) i_mfc0(buf, rt, rd)
+# define i_MTC0(buf, rt, rd...) i_mtc0(buf, rt, rd)
 # define i_ADDIU(buf, rs, rt, val) i_addiu(buf, rs, rt, val)
 # define i_ADDU(buf, rs, rt, rd) i_addu(buf, rs, rt, rd)
 # define i_SUBU(buf, rs, rt, rd) i_subu(buf, rs, rt, rd)
@@ -670,14 +692,15 @@ static void __init il_bgezl(u32 **p, struct reloc **r, unsigned int reg,
 #define K1             27
 
 /* Some CP0 registers */
-#define C0_INDEX       0
-#define C0_ENTRYLO0    2
-#define C0_ENTRYLO1    3
-#define C0_CONTEXT     4
-#define C0_BADVADDR    8
-#define C0_ENTRYHI     10
-#define C0_EPC         14
-#define C0_XCONTEXT    20
+#define C0_INDEX       0, 0
+#define C0_ENTRYLO0    2, 0
+#define C0_TCBIND      2, 2
+#define C0_ENTRYLO1    3, 0
+#define C0_CONTEXT     4, 0
+#define C0_BADVADDR    8, 0
+#define C0_ENTRYHI     10, 0
+#define C0_EPC         14, 0
+#define C0_XCONTEXT    20, 0
 
 #ifdef CONFIG_64BIT
 # define GET_CONTEXT(buf, reg) i_MFC0(buf, reg, C0_XCONTEXT)
@@ -742,7 +765,7 @@ static void __init build_r3000_tlb_refill_handler(void)
        }
 #endif
 
-       memcpy((void *)CAC_BASE, tlb_handler, 0x80);
+       memcpy((void *)ebase, tlb_handler, 0x80);
 }
 
 /*
@@ -951,12 +974,20 @@ build_get_pmde64(u32 **p, struct label **l, struct reloc **r,
        /* No i_nop needed here, since the next insn doesn't touch TMP. */
 
 #ifdef CONFIG_SMP
+# ifdef  CONFIG_MIPS_MT_SMTC
+       /*
+        * SMTC uses TCBind value as "CPU" index
+        */
+       i_mfc0(p, ptr, C0_TCBIND);
+       i_dsrl(p, ptr, ptr, 19);
+# else
        /*
         * 64 bit SMP running in XKPHYS has smp_processor_id() << 3
         * stored in CONTEXT.
         */
        i_dmfc0(p, ptr, C0_CONTEXT);
        i_dsrl(p, ptr, ptr, 23);
+#endif
        i_LA_mostly(p, tmp, pgdc);
        i_daddu(p, ptr, ptr, tmp);
        i_dmfc0(p, tmp, C0_BADVADDR);
@@ -1014,9 +1045,21 @@ build_get_pgde32(u32 **p, unsigned int tmp, unsigned int ptr)
 
        /* 32 bit SMP has smp_processor_id() stored in CONTEXT. */
 #ifdef CONFIG_SMP
+#ifdef  CONFIG_MIPS_MT_SMTC
+       /*
+        * SMTC uses TCBind value as "CPU" index
+        */
+       i_mfc0(p, ptr, C0_TCBIND);
+       i_LA_mostly(p, tmp, pgdc);
+       i_srl(p, ptr, ptr, 19);
+#else
+       /*
+        * smp_processor_id() << 3 is stored in CONTEXT.
+         */
        i_mfc0(p, ptr, C0_CONTEXT);
        i_LA_mostly(p, tmp, pgdc);
        i_srl(p, ptr, ptr, 23);
+#endif
        i_addu(p, ptr, tmp, ptr);
 #else
        i_LA_mostly(p, ptr, pgdc);
@@ -1247,7 +1290,7 @@ static void __init build_r4000_tlb_refill_handler(void)
        }
 #endif
 
-       memcpy((void *)CAC_BASE, final_handler, 0x100);
+       memcpy((void *)ebase, final_handler, 0x100);
 }
 
 /*
index 20bbd3ea44a8a1cc425241220583deda06fc53f6..67372f3f9654a3105e0b9d041d6c2650f848e240 100644 (file)
@@ -6,7 +6,7 @@
 # unless it's something special (ie not a .c file).
 #
 
-obj-y += int-handler.o irq.o prom.o reset.o setup.o
+obj-y += irq.o prom.o reset.o setup.o
 
 obj-$(CONFIG_SERIAL_8250_CONSOLE) += ja-console.o
 obj-$(CONFIG_REMOTE_DEBUG) += dbg_io.o
diff --git a/arch/mips/momentum/jaguar_atx/int-handler.S b/arch/mips/momentum/jaguar_atx/int-handler.S
deleted file mode 100644 (file)
index 55bc789..0000000
+++ /dev/null
@@ -1,128 +0,0 @@
-/*
- * Copyright 2002 Momentum Computer Inc.
- * Author: Matthew Dharm <mdharm@momenco.com>
- *
- * Based on work:
- *   Copyright 2001 MontaVista Software Inc.
- *   Author: jsun@mvista.com or jsun@junsun.net
- *
- * First-level interrupt dispatcher for Jaguar-ATX board.
- *
- * This program is free software; you can redistribute  it and/or modify it
- * under  the terms of  the GNU General  Public License as published by the
- * Free Software Foundation;  either version 2 of the  License, or (at your
- * option) any later version.
- */
-#include <asm/asm.h>
-#include <asm/mipsregs.h>
-#include <asm/addrspace.h>
-#include <asm/regdef.h>
-#include <asm/stackframe.h>
-
-/*
- * First level interrupt dispatcher for Ocelot-CS board
- */
-               .align  5
-               NESTED(jaguar_handle_int, PT_SIZE, sp)
-               SAVE_ALL
-               CLI
-               .set    at
-               mfc0    t0, CP0_CAUSE
-               mfc0    t2, CP0_STATUS
-
-               and     t0, t2
-
-               andi    t1, t0, STATUSF_IP0     /* sw0 software interrupt */
-               bnez    t1, ll_sw0_irq
-               andi    t1, t0, STATUSF_IP1     /* sw1 software interrupt */
-               bnez    t1, ll_sw1_irq
-               andi    t1, t0, STATUSF_IP2     /* int0 hardware line */
-               bnez    t1, ll_pcixa_irq
-               andi    t1, t0, STATUSF_IP3     /* int1 hardware line */
-               bnez    t1, ll_pcixb_irq
-               andi    t1, t0, STATUSF_IP4     /* int2 hardware line */
-               bnez    t1, ll_pcia_irq
-               andi    t1, t0, STATUSF_IP5     /* int3 hardware line */
-               bnez    t1, ll_pcib_irq
-               andi    t1, t0, STATUSF_IP6     /* int4 hardware line */
-               bnez    t1, ll_uart_irq
-               andi    t1, t0, STATUSF_IP7     /* cpu timer */
-               bnez    t1, ll_cputimer_irq
-
-               nop
-               nop
-
-               /* now look at extended interrupts */
-               mfc0    t0, CP0_CAUSE
-               cfc0    t1, CP0_S1_INTCONTROL
-
-               /* shift the mask 8 bits left to line up the bits */
-               sll     t2, t1, 8
-
-               and     t0, t2
-               srl     t0, t0, 16
-
-               andi    t1, t0, STATUSF_IP8     /* int6 hardware line */
-               bnez    t1, ll_mv64340_decode_irq
-
-               nop
-               nop
-
-               .set    reorder
-
-               /* wrong alarm or masked ... */
-               j       spurious_interrupt
-               nop
-               END(jaguar_handle_int)
-
-               .align  5
-ll_sw0_irq:
-               li      a0, 0
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-ll_sw1_irq:
-               li      a0, 1
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-ll_pcixa_irq:
-               li      a0, 2
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-
-ll_pcixb_irq:
-               li      a0, 3
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-
-ll_pcia_irq:
-               li      a0, 4
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-
-ll_pcib_irq:
-               li      a0, 5
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-
-ll_uart_irq:
-               li      a0, 6
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-
-ll_cputimer_irq:
-               li      a0, 7
-               move    a1, sp
-               jal     ll_timer_interrupt
-               j       ret_from_irq
-
-ll_mv64340_decode_irq:
-               move    a0, sp
-               jal     ll_mv64340_irq
-               j       ret_from_irq
index 15588f91ace2dd9499ae51506d8cdc8c3cef6899..ec4032b38f19230e26c169f57dceee4867bbf54f 100644 (file)
@@ -10,7 +10,7 @@
  *   Copyright 2001 MontaVista Software Inc.
  *   Author: Jun Sun, jsun@mvista.com or jsun@junsun.net
  *
- *   Copyright (C) 2000, 2001 Ralf Baechle (ralf@gnu.org)
+ *   Copyright (C) 2000, 01, 06 Ralf Baechle (ralf@linux-mips.org)
  *
  *  This program is free software; you can redistribute  it and/or modify it
  *  under  the terms of  the GNU General  Public License as published by the
 #include <linux/types.h>
 #include <asm/irq_cpu.h>
 #include <asm/mipsregs.h>
+#include <asm/time.h>
 
-extern asmlinkage void jaguar_handle_int(void);
+asmlinkage void plat_irq_dispatch(struct pt_regs *regs)
+{
+       unsigned int pending = read_c0_cause() & read_c0_status();
+
+       if (pending & STATUSF_IP0)
+               do_IRQ(0, regs);
+       else if (pending & STATUSF_IP1)
+               do_IRQ(1, regs);
+       else if (pending & STATUSF_IP2)
+               do_IRQ(2, regs);
+       else if (pending & STATUSF_IP3)
+               do_IRQ(3, regs);
+       else if (pending & STATUSF_IP4)
+               do_IRQ(4, regs);
+       else if (pending & STATUSF_IP5)
+               do_IRQ(5, regs);
+       else if (pending & STATUSF_IP6)
+               do_IRQ(6, regs);
+       else if (pending & STATUSF_IP7)
+               ll_timer_interrupt(7, regs);
+       else {
+               /*
+                * Now look at the extended interrupts
+                */
+               pending = (read_c0_cause() & (read_c0_intcontrol() << 8)) >> 16;
+               if (pending & STATUSF_IP8)
+                       ll_mv64340_irq(regs);
+       }
+}
 
 static struct irqaction cascade_mv64340 = {
        no_action, SA_INTERRUPT, CPU_MASK_NONE, "MV64340-Cascade", NULL, NULL
@@ -53,8 +82,6 @@ void __init arch_init_irq(void)
         */
        clear_c0_status(ST0_IM);
 
-       /* Sets the first-level interrupt dispatcher. */
-       set_except_vector(0, jaguar_handle_int);
        mips_cpu_irq_init(0);
        rm7k_cpu_irq_init(8);
 
index 91d9637143d7fe24690e063f16be9f887d4e909c..1379c76845dc6619436c064400f46226777130c1 100644 (file)
@@ -381,24 +381,24 @@ void __init plat_setup(void)
         * shut down ethernet ports, just to be sure our memory doesn't get
         * corrupted by random ethernet traffic.
         */
-       MV_WRITE(MV64340_ETH_TRANSMIT_QUEUE_COMMAND_REG(0), 0xff << 8);
-       MV_WRITE(MV64340_ETH_TRANSMIT_QUEUE_COMMAND_REG(1), 0xff << 8);
-       MV_WRITE(MV64340_ETH_TRANSMIT_QUEUE_COMMAND_REG(2), 0xff << 8);
-       MV_WRITE(MV64340_ETH_RECEIVE_QUEUE_COMMAND_REG(0), 0xff << 8);
-       MV_WRITE(MV64340_ETH_RECEIVE_QUEUE_COMMAND_REG(1), 0xff << 8);
-       MV_WRITE(MV64340_ETH_RECEIVE_QUEUE_COMMAND_REG(2), 0xff << 8);
-       while (MV_READ(MV64340_ETH_RECEIVE_QUEUE_COMMAND_REG(0)) & 0xff);
-       while (MV_READ(MV64340_ETH_RECEIVE_QUEUE_COMMAND_REG(1)) & 0xff);
-       while (MV_READ(MV64340_ETH_RECEIVE_QUEUE_COMMAND_REG(2)) & 0xff);
-       while (MV_READ(MV64340_ETH_TRANSMIT_QUEUE_COMMAND_REG(0)) & 0xff);
-       while (MV_READ(MV64340_ETH_TRANSMIT_QUEUE_COMMAND_REG(1)) & 0xff);
-       while (MV_READ(MV64340_ETH_TRANSMIT_QUEUE_COMMAND_REG(2)) & 0xff);
-       MV_WRITE(MV64340_ETH_PORT_SERIAL_CONTROL_REG(0),
-                MV_READ(MV64340_ETH_PORT_SERIAL_CONTROL_REG(0)) & ~1);
-       MV_WRITE(MV64340_ETH_PORT_SERIAL_CONTROL_REG(1),
-                MV_READ(MV64340_ETH_PORT_SERIAL_CONTROL_REG(1)) & ~1);
-       MV_WRITE(MV64340_ETH_PORT_SERIAL_CONTROL_REG(2),
-                MV_READ(MV64340_ETH_PORT_SERIAL_CONTROL_REG(2)) & ~1);
+       MV_WRITE(MV643XX_ETH_TRANSMIT_QUEUE_COMMAND_REG(0), 0xff << 8);
+       MV_WRITE(MV643XX_ETH_TRANSMIT_QUEUE_COMMAND_REG(1), 0xff << 8);
+       MV_WRITE(MV643XX_ETH_TRANSMIT_QUEUE_COMMAND_REG(2), 0xff << 8);
+       MV_WRITE(MV643XX_ETH_RECEIVE_QUEUE_COMMAND_REG(0), 0xff << 8);
+       MV_WRITE(MV643XX_ETH_RECEIVE_QUEUE_COMMAND_REG(1), 0xff << 8);
+       MV_WRITE(MV643XX_ETH_RECEIVE_QUEUE_COMMAND_REG(2), 0xff << 8);
+       while (MV_READ(MV643XX_ETH_RECEIVE_QUEUE_COMMAND_REG(0)) & 0xff);
+       while (MV_READ(MV643XX_ETH_RECEIVE_QUEUE_COMMAND_REG(1)) & 0xff);
+       while (MV_READ(MV643XX_ETH_RECEIVE_QUEUE_COMMAND_REG(2)) & 0xff);
+       while (MV_READ(MV643XX_ETH_TRANSMIT_QUEUE_COMMAND_REG(0)) & 0xff);
+       while (MV_READ(MV643XX_ETH_TRANSMIT_QUEUE_COMMAND_REG(1)) & 0xff);
+       while (MV_READ(MV643XX_ETH_TRANSMIT_QUEUE_COMMAND_REG(2)) & 0xff);
+       MV_WRITE(MV643XX_ETH_PORT_SERIAL_CONTROL_REG(0),
+                MV_READ(MV643XX_ETH_PORT_SERIAL_CONTROL_REG(0)) & ~1);
+       MV_WRITE(MV643XX_ETH_PORT_SERIAL_CONTROL_REG(1),
+                MV_READ(MV643XX_ETH_PORT_SERIAL_CONTROL_REG(1)) & ~1);
+       MV_WRITE(MV643XX_ETH_PORT_SERIAL_CONTROL_REG(2),
+                MV_READ(MV643XX_ETH_PORT_SERIAL_CONTROL_REG(2)) & ~1);
 
        /* Turn off the Bit-Error LED */
        JAGUAR_FPGA_WRITE(0x80, CLR);
index aab8fd89f830bd18062ecaa2731ae0c957cb1221..8bcea64dd27b90a5500dac81b10cf5c6e5f869f3 100644 (file)
@@ -5,4 +5,4 @@
 # removes any old dependencies. DON'T put your own dependencies here
 # unless it's something special (ie not a .c file).
 #
-obj-y   += int-handler.o irq.o prom.o reset.o setup.o
+obj-y   += irq.o prom.o reset.o setup.o
diff --git a/arch/mips/momentum/ocelot_3/int-handler.S b/arch/mips/momentum/ocelot_3/int-handler.S
deleted file mode 100644 (file)
index 4522f09..0000000
+++ /dev/null
@@ -1,137 +0,0 @@
-/*
- * Copyright 2002 Momentum Computer Inc.
- * Author: Matthew Dharm <mdharm@momenco.com>
- *
- * Copyright 2001 MontaVista Software Inc.
- * Author: jsun@mvista.com or jsun@junsun.net
- *
- * Copyright 2004 PMC-Sierra
- * Author: Manish Lachwani (lachwani@pmc-sierra.com)
- *
- * Copyright (C) 2004 MontaVista Software Inc.
- * Author: Manish Lachwani, mlachwani@mvista.com
- *
- * First-level interrupt dispatcher for Ocelot-3 board.
- *
- * This program is free software; you can redistribute  it and/or modify it
- * under  the terms of  the GNU General  Public License as published by the
- * Free Software Foundation;  either version 2 of the  License, or (at your
- * option) any later version.
- */
-#include <asm/asm.h>
-#include <asm/mipsregs.h>
-#include <asm/addrspace.h>
-#include <asm/regdef.h>
-#include <asm/stackframe.h>
-
-/*
- * First level interrupt dispatcher for Ocelot-3 board
- */
-               .align  5
-               NESTED(ocelot3_handle_int, PT_SIZE, sp)
-               SAVE_ALL
-               CLI
-               .set    at
-
-               mfc0    t0, CP0_CAUSE
-               mfc0    t2, CP0_STATUS
-
-               and     t0, t2
-
-               andi    t1, t0, STATUSF_IP0     /* sw0 software interrupt (IRQ0) */
-               bnez    t1, ll_sw0_irq
-
-               andi    t1, t0, STATUSF_IP1     /* sw1 software interrupt (IRQ1) */
-               bnez    t1, ll_sw1_irq
-
-               andi    t1, t0, STATUSF_IP2     /* int0 hardware line (IRQ2) */
-               bnez    t1, ll_pci0slot1_irq
-
-               andi    t1, t0, STATUSF_IP3     /* int1 hardware line (IRQ3) */
-               bnez    t1, ll_pci0slot2_irq
-
-               andi    t1, t0, STATUSF_IP4     /* int2 hardware line (IRQ4) */
-               bnez    t1, ll_pci1slot1_irq
-
-               andi    t1, t0, STATUSF_IP5     /* int3 hardware line (IRQ5) */
-               bnez    t1, ll_pci1slot2_irq
-
-               andi    t1, t0, STATUSF_IP6     /* int4 hardware line (IRQ6) */
-               bnez    t1, ll_uart_irq
-
-               andi    t1, t0, STATUSF_IP7     /* cpu timer (IRQ7) */
-               bnez    t1, ll_cputimer_irq
-
-                /* now look at extended interrupts */
-                mfc0    t0, CP0_CAUSE
-                cfc0    t1, CP0_S1_INTCONTROL
-
-                /* shift the mask 8 bits left to line up the bits */
-                sll     t2, t1, 8
-
-                and     t0, t2
-                srl     t0, t0, 16
-
-                andi    t1, t0, STATUSF_IP8     /* int6 hardware line (IRQ9) */
-                bnez    t1, ll_mv64340_decode_irq
-
-               .set    reorder
-
-               /* wrong alarm or masked ... */
-               j       spurious_interrupt
-               nop
-               END(ocelot3_handle_int)
-
-               .align  5
-ll_sw0_irq:
-               li      a0, 0           /* IRQ 1 */
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-ll_sw1_irq:
-               li      a0, 1           /* IRQ 2 */
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-
-ll_pci0slot1_irq:
-               li      a0, 2           /* IRQ 3 */
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-
-ll_pci0slot2_irq:
-               li      a0, 3           /* IRQ 4 */
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-
-ll_pci1slot1_irq:
-               li      a0, 4           /* IRQ 5 */
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-
-ll_pci1slot2_irq:
-               li      a0, 5           /* IRQ 6 */
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-
-ll_uart_irq:
-               li      a0, 6           /* IRQ 7 */
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-
-ll_cputimer_irq:
-               li      a0, 7           /* IRQ 8 */
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-
-ll_mv64340_decode_irq:
-               move    a0, sp
-               jal     ll_mv64340_irq
-               j       ret_from_irq
-
index 42464dbd4ad24d50fe07bab2dacda8ca0150fc0c..87c63c340ae3f4124f50887a07aa644b07efa414 100644 (file)
@@ -53,8 +53,6 @@
 #include <asm/mipsregs.h>
 #include <asm/system.h>
 
-extern asmlinkage void ocelot3_handle_int(void);
-
 static struct irqaction cascade_mv64340 = {
        no_action, SA_INTERRUPT, CPU_MASK_NONE, "MV64340-Cascade", NULL, NULL
 };
@@ -67,9 +65,6 @@ void __init arch_init_irq(void)
         */
        clear_c0_status(ST0_IM | ST0_BEV);
 
-       /* Sets the first-level interrupt dispatcher. */
-       set_except_vector(0, ocelot3_handle_int);
-       mips_cpu_irq_init(0);
        rm7k_cpu_irq_init(8);
 
        /* set up the cascading interrupts */
@@ -79,3 +74,36 @@ void __init arch_init_irq(void)
        set_c0_status(ST0_IM); /* IE in the status register */
 
 }
+
+asmlinkage void plat_irq_dispatch(struct pt_regs *regs)
+{
+       unsigned int pending = read_c0_cause() & read_c0_status();
+
+       if (pending & STATUSF_IP0)
+               do_IRQ(0, regs);
+       else if (pending & STATUSF_IP1)
+               do_IRQ(1, regs);
+       else if (pending & STATUSF_IP2)
+               do_IRQ(2, regs);
+       else if (pending & STATUSF_IP3)
+               do_IRQ(3, regs);
+       else if (pending & STATUSF_IP4)
+               do_IRQ(4, regs);
+       else if (pending & STATUSF_IP5)
+               do_IRQ(5, regs);
+       else if (pending & STATUSF_IP6)
+               do_IRQ(6, regs);
+       else if (pending & STATUSF_IP7)
+               do_IRQ(7, regs);
+       else {
+               /*
+                * Now look at the extended interrupts
+                */
+               pending = (read_c0_cause() & (read_c0_intcontrol() << 8)) >> 16;
+
+               if (pending & STATUSF_IP8)
+                       ll_mv64340_irq(regs);
+               else
+                       spurious_interrupt(regs);
+       }
+}
index 370e75d0e75cdf2d4897806a0c47d59a6ff3df0e..c69195234309687d3f03d52aa6a3fbace55fefbb 100644 (file)
@@ -329,22 +329,22 @@ void __init plat_setup(void)
        /* shut down ethernet ports, just to be sure our memory doesn't get
         * corrupted by random ethernet traffic.
         */
-       MV_WRITE(MV64340_ETH_TRANSMIT_QUEUE_COMMAND_REG(0), 0xff << 8);
-       MV_WRITE(MV64340_ETH_TRANSMIT_QUEUE_COMMAND_REG(1), 0xff << 8);
-       MV_WRITE(MV64340_ETH_RECEIVE_QUEUE_COMMAND_REG(0), 0xff << 8);
-       MV_WRITE(MV64340_ETH_RECEIVE_QUEUE_COMMAND_REG(1), 0xff << 8);
+       MV_WRITE(MV643XX_ETH_TRANSMIT_QUEUE_COMMAND_REG(0), 0xff << 8);
+       MV_WRITE(MV643XX_ETH_TRANSMIT_QUEUE_COMMAND_REG(1), 0xff << 8);
+       MV_WRITE(MV643XX_ETH_RECEIVE_QUEUE_COMMAND_REG(0), 0xff << 8);
+       MV_WRITE(MV643XX_ETH_RECEIVE_QUEUE_COMMAND_REG(1), 0xff << 8);
        do {}
-         while (MV_READ(MV64340_ETH_RECEIVE_QUEUE_COMMAND_REG(0)) & 0xff);
+         while (MV_READ(MV643XX_ETH_RECEIVE_QUEUE_COMMAND_REG(0)) & 0xff);
        do {}
-         while (MV_READ(MV64340_ETH_RECEIVE_QUEUE_COMMAND_REG(1)) & 0xff);
+         while (MV_READ(MV643XX_ETH_RECEIVE_QUEUE_COMMAND_REG(1)) & 0xff);
        do {}
-         while (MV_READ(MV64340_ETH_TRANSMIT_QUEUE_COMMAND_REG(0)) & 0xff);
+         while (MV_READ(MV643XX_ETH_TRANSMIT_QUEUE_COMMAND_REG(0)) & 0xff);
        do {}
-         while (MV_READ(MV64340_ETH_TRANSMIT_QUEUE_COMMAND_REG(1)) & 0xff);
-       MV_WRITE(MV64340_ETH_PORT_SERIAL_CONTROL_REG(0),
-                MV_READ(MV64340_ETH_PORT_SERIAL_CONTROL_REG(0)) & ~1);
-       MV_WRITE(MV64340_ETH_PORT_SERIAL_CONTROL_REG(1),
-                MV_READ(MV64340_ETH_PORT_SERIAL_CONTROL_REG(1)) & ~1);
+         while (MV_READ(MV643XX_ETH_TRANSMIT_QUEUE_COMMAND_REG(1)) & 0xff);
+       MV_WRITE(MV643XX_ETH_PORT_SERIAL_CONTROL_REG(0),
+                MV_READ(MV643XX_ETH_PORT_SERIAL_CONTROL_REG(0)) & ~1);
+       MV_WRITE(MV643XX_ETH_PORT_SERIAL_CONTROL_REG(1),
+                MV_READ(MV643XX_ETH_PORT_SERIAL_CONTROL_REG(1)) & ~1);
 
        /* Turn off the Bit-Error LED */
        OCELOT_FPGA_WRITE(0x80, CLR);
index 91240777f978703fa9abf465575baeaa7d0c6c49..94802b4db472848545361ed68ed25da0b3544cf3 100644 (file)
@@ -2,7 +2,7 @@
 # Makefile for Momentum Computer's Ocelot-C and -CS boards.
 #
 
-obj-y                  += cpci-irq.o int-handler.o irq.o prom.o reset.o \
+obj-y                  += cpci-irq.o irq.o prom.o reset.o \
                           setup.o uart-irq.o
 
 obj-$(CONFIG_KGDB)     += dbg_io.o
diff --git a/arch/mips/momentum/ocelot_c/int-handler.S b/arch/mips/momentum/ocelot_c/int-handler.S
deleted file mode 100644 (file)
index 52349d9..0000000
+++ /dev/null
@@ -1,102 +0,0 @@
-/*
- * Copyright 2002 Momentum Computer Inc.
- * Author: Matthew Dharm <mdharm@momenco.com>
- *
- * Copyright 2001 MontaVista Software Inc.
- * Author: jsun@mvista.com or jsun@junsun.net
- *
- * First-level interrupt dispatcher for Ocelot-CS board.
- *
- * This program is free software; you can redistribute  it and/or modify it
- * under  the terms of  the GNU General  Public License as published by the
- * Free Software Foundation;  either version 2 of the  License, or (at your
- * option) any later version.
- */
-#include <asm/asm.h>
-#include <asm/mipsregs.h>
-#include <asm/addrspace.h>
-#include <asm/regdef.h>
-#include <asm/stackframe.h>
-#include "ocelot_c_fpga.h"
-
-/*
- * First level interrupt dispatcher for Ocelot-CS board
- */
-               .align  5
-               NESTED(ocelot_handle_int, PT_SIZE, sp)
-               SAVE_ALL
-               CLI
-               .set    at
-               mfc0    t0, CP0_CAUSE
-               mfc0    t2, CP0_STATUS
-
-               and     t0, t2
-
-               andi    t1, t0, STATUSF_IP0     /* sw0 software interrupt */
-               bnez    t1, ll_sw0_irq
-               andi    t1, t0, STATUSF_IP1     /* sw1 software interrupt */
-               bnez    t1, ll_sw1_irq
-               andi    t1, t0, STATUSF_IP2     /* int0 hardware line */
-               bnez    t1, ll_scsi_irq
-               andi    t1, t0, STATUSF_IP3     /* int1 hardware line */
-               bnez    t1, ll_uart_decode_irq
-               andi    t1, t0, STATUSF_IP4     /* int2 hardware line */
-               bnez    t1, ll_pmc_irq
-               andi    t1, t0, STATUSF_IP5     /* int3 hardware line */
-               bnez    t1, ll_cpci_decode_irq
-               andi    t1, t0, STATUSF_IP6     /* int4 hardware line */
-               bnez    t1, ll_mv64340_decode_irq
-               andi    t1, t0, STATUSF_IP7     /* cpu timer */
-               bnez    t1, ll_cputimer_irq
-
-               .set    reorder
-
-               /* wrong alarm or masked ... */
-               j       spurious_interrupt
-               nop
-               END(ocelot_handle_int)
-
-               .align  5
-ll_sw0_irq:
-               li      a0, 0
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-ll_sw1_irq:
-               li      a0, 1
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-ll_scsi_irq:
-               li      a0, 2
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-
-ll_uart_decode_irq:
-               move    a0, sp
-               jal     ll_uart_irq
-               j       ret_from_irq
-
-ll_pmc_irq:
-               li      a0, 4
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-
-ll_cpci_decode_irq:
-               move    a0, sp
-               jal     ll_cpci_irq
-               j       ret_from_irq
-
-ll_mv64340_decode_irq:
-               move    a0, sp
-               jal     ll_mv64340_irq
-               j       ret_from_irq
-
-ll_cputimer_irq:
-               li      a0, 7
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-
index a5764bc20e36593df6d96ff6b25c1407106d9c53..86f61ce59e53b33d205040f14a903e6e44f37882 100644 (file)
@@ -48,7 +48,6 @@
 #include <asm/mipsregs.h>
 #include <asm/system.h>
 
-extern asmlinkage void ocelot_handle_int(void);
 extern void uart_irq_init(void);
 extern void cpci_irq_init(void);
 
@@ -60,6 +59,33 @@ static struct irqaction cascade_mv64340 = {
        no_action, SA_INTERRUPT, CPU_MASK_NONE, "cascade via MV64340", NULL, NULL
 };
 
+extern void ll_uart_irq(struct pt_regs *regs);
+extern void ll_cpci_irq(struct pt_regs *regs);
+
+asmlinkage void plat_irq_dispatch(struct pt_regs *regs)
+{
+       unsigned int pending = read_c0_cause() & read_c0_status();
+
+       if (pending & STATUSF_IP0)
+               do_IRQ(0, regs);
+       else if (pending & STATUSF_IP1)
+               do_IRQ(1, regs);
+       else if (pending & STATUSF_IP2)
+               do_IRQ(2, regs);
+       else if (pending & STATUSF_IP3)
+               ll_uart_irq(regs);
+       else if (pending & STATUSF_IP4)
+               do_IRQ(4, regs);
+       else if (pending & STATUSF_IP5)
+               ll_cpci_irq(regs);
+       else if (pending & STATUSF_IP6)
+               ll_mv64340_irq(regs);
+       else if (pending & STATUSF_IP7)
+               do_IRQ(7, regs);
+       else
+               spurious_interrupt(regs);
+}
+
 void __init arch_init_irq(void)
 {
        /*
@@ -68,8 +94,6 @@ void __init arch_init_irq(void)
         */
        clear_c0_status(ST0_IM);
 
-       /* Sets the first-level interrupt dispatcher. */
-       set_except_vector(0, ocelot_handle_int);
        mips_cpu_irq_init(0);
 
        /* set up the cascading interrupts */
index e5f1cb08697324ad3d7d3824a49989baad9bf022..adb5665d40a950cf19f3f6ace46dba092ffc4e44 100644 (file)
@@ -2,7 +2,7 @@
 # Makefile for Momentum Computer's Ocelot-G board.
 #
 
-obj-y                  += int-handler.o irq.o gt-irq.o prom.o reset.o setup.o
+obj-y                  += irq.o gt-irq.o prom.o reset.o setup.o
 obj-$(CONFIG_KGDB)     += dbg_io.o
 
 EXTRA_AFLAGS := $(CFLAGS)
diff --git a/arch/mips/momentum/ocelot_g/int-handler.S b/arch/mips/momentum/ocelot_g/int-handler.S
deleted file mode 100644 (file)
index 772e8f7..0000000
+++ /dev/null
@@ -1,131 +0,0 @@
-/*
- * Copyright 2001 MontaVista Software Inc.
- * Author: jsun@mvista.com or jsun@junsun.net
- *
- * First-level interrupt dispatcher for ocelot board.
- *
- * This program is free software; you can redistribute  it and/or modify it
- * under  the terms of  the GNU General  Public License as published by the
- * Free Software Foundation;  either version 2 of the  License, or (at your
- * option) any later version.
- */
-#include <asm/asm.h>
-#include <asm/mipsregs.h>
-#include <asm/addrspace.h>
-#include <asm/regdef.h>
-#include <asm/stackframe.h>
-
-/*
- * first level interrupt dispatcher for ocelot board -
- * We check for the timer first, then check PCI ints A and D.
- * Then check for serial IRQ and fall through.
- */
-               .align  5
-               NESTED(ocelot_handle_int, PT_SIZE, sp)
-               SAVE_ALL
-               CLI
-               .set    at
-               mfc0    t0, CP0_CAUSE
-               mfc0    t2, CP0_STATUS
-
-               and     t0, t2
-
-                andi   t1, t0, STATUSF_IP2     /* int0 hardware line */
-               bnez    t1, ll_pri_enet_irq
-                andi   t1, t0, STATUSF_IP3     /* int1 hardware line */
-               bnez    t1, ll_sec_enet_irq
-                andi   t1, t0, STATUSF_IP4     /* int2 hardware line */
-               bnez    t1, ll_uart_irq
-                andi   t1, t0, STATUSF_IP5     /* int3 hardware line */
-               bnez    t1, ll_cpci_irq
-                andi   t1, t0, STATUSF_IP6     /* int4 hardware line */
-               bnez    t1, ll_galileo_p0_irq
-                andi   t1, t0, STATUSF_IP7     /* cpu timer */
-               bnez    t1, ll_cputimer_irq
-
-                /* now look at the extended interrupts */
-               mfc0    t0, CP0_CAUSE
-               cfc0    t1, CP0_S1_INTCONTROL
-
-               /* shift the mask 8 bits left to line up the bits */
-                sll    t2, t1, 8
-
-                and    t0, t2
-                srl    t0, t0, 16
-
-                andi   t1, t0, STATUSF_IP8     /* int6 hardware line */
-               bnez    t1, ll_galileo_p1_irq
-                andi   t1, t0, STATUSF_IP9     /* int7 hardware line */
-               bnez    t1, ll_pmc_irq
-                andi   t1, t0, STATUSF_IP10    /* int8 hardware line */
-               bnez    t1, ll_cpci_abcd_irq
-                andi   t1, t0, STATUSF_IP11    /* int9 hardware line */
-               bnez    t1, ll_testpoint_irq
-
-               .set    reorder
-
-               /* wrong alarm or masked ... */
-               j       spurious_interrupt
-               nop
-               END(ocelot_handle_int)
-
-               .align  5
-ll_pri_enet_irq:
-               li      a0, 2
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-
-ll_sec_enet_irq:
-               li      a0, 3
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-
-ll_uart_irq:
-               li      a0, 4
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-
-ll_cpci_irq:
-               li      a0, 5
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-
-ll_galileo_p0_irq:
-               li      a0, 6
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-
-ll_cputimer_irq:
-               li      a0, 7
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-
-ll_galileo_p1_irq:
-               li      a0, 8
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-
-ll_pmc_irq:
-               li      a0, 9
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-
-ll_cpci_abcd_irq:
-               li      a0, 10
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-
-ll_testpoint_irq:
-               li      a0, 11
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
index 5eb85b1642051b3f9cf036d76d7d79847716c6aa..7a4a419804f19f0c202f6dcc6c3ea91d9d100231 100644 (file)
 #include <asm/mipsregs.h>
 #include <asm/system.h>
 
-extern asmlinkage void ocelot_handle_int(void);
+asmlinkage void plat_irq_dispatch(struct pt_regs *regs)
+{
+       unsigned int pending = read_c0_cause() & read_c0_status();
+
+       if (pending & STATUSF_IP2)
+               do_IRQ(2, regs);
+       else if (pending & STATUSF_IP3)
+               do_IRQ(3, regs);
+       else if (pending & STATUSF_IP4)
+               do_IRQ(4, regs);
+       else if (pending & STATUSF_IP5)
+               do_IRQ(5, regs);
+       else if (pending & STATUSF_IP6)
+               do_IRQ(6, regs);
+       else if (pending & STATUSF_IP7)
+               do_IRQ(7, regs);
+       else {
+               /*
+                * Now look at the extended interrupts
+                */
+               pending = (read_c0_cause() & (read_c0_intcontrol() << 8)) >> 16;
+
+               if (pending & STATUSF_IP8)
+                       do_IRQ(8, regs);
+               else if (pending & STATUSF_IP9)
+                       do_IRQ(9, regs);
+               else if (pending & STATUSF_IP10)
+                       do_IRQ(10, regs);
+               else if (pending & STATUSF_IP11)
+                       do_IRQ(11, regs);
+               else
+                       spurious_interrupt(regs);
+       }
+}
+
 extern void gt64240_irq_init(void);
 
 void __init arch_init_irq(void)
@@ -60,8 +94,6 @@ void __init arch_init_irq(void)
        clear_c0_status(ST0_IM);
        local_irq_disable();
 
-       /* Sets the first-level interrupt dispatcher. */
-       set_except_vector(0, ocelot_handle_int);
        mips_cpu_irq_init(0);
        rm7k_cpu_irq_init(8);
 
index 6e38f3bc443c6a590ef7e41665c9e54b7180676b..b7c638166e9f3a9927239f495e67a8429223c569 100644 (file)
@@ -22,6 +22,6 @@
 # under Linux.
 #
 
-obj-y := setup.o prom.o mipsIRQ.o int.o reset.o time.o proc.o platform.o
+obj-y := setup.o prom.o int.o reset.o time.o proc.o platform.o
 obj-$(CONFIG_PCI) += pci.o
 obj-$(CONFIG_KGDB) += gdb_hook.o
index c500e2d41f2c5f8d6c30ee843a98ca50f3576233..39ee6314f62757279e12118448a04b70713fb2a7 100644 (file)
@@ -38,8 +38,6 @@
 #include <int.h>
 #include <uart.h>
 
-extern asmlinkage void cp0_irqdispatch(void);
-
 static DEFINE_SPINLOCK(irq_lock);
 
 /* default prio for interrupts */
@@ -55,7 +53,7 @@ static char gic_prio[PNX8550_INT_GIC_TOTINT] = {
        1                       //  70
 };
 
-void hw0_irqdispatch(int irq, struct pt_regs *regs)
+static void hw0_irqdispatch(int irq, struct pt_regs *regs)
 {
        /* find out which interrupt */
        irq = PNX8550_GIC_VECTOR_0 >> 3;
@@ -68,7 +66,7 @@ void hw0_irqdispatch(int irq, struct pt_regs *regs)
 }
 
 
-void timer_irqdispatch(int irq, struct pt_regs *regs)
+static void timer_irqdispatch(int irq, struct pt_regs *regs)
 {
        irq = (0x01c0 & read_c0_config7()) >> 6;
 
@@ -88,6 +86,20 @@ void timer_irqdispatch(int irq, struct pt_regs *regs)
        }
 }
 
+asmlinkage void plat_irq_dispatch(struct pt_regs *regs)
+{
+       unsigned int pending = read_c0_status() & read_c0_cause();
+
+       if (pending & STATUSF_IP2)
+               do_IRQ(2, regs);
+       else if (pending & STATUSF_IP7) {
+               if (read_c0_config7() & 0x01c0)
+                       timer_irqdispatch(7, regs);
+       }
+
+       spurious_interrupt(regs);
+}
+
 static inline void modify_cp0_intmask(unsigned clr_mask, unsigned set_mask)
 {
        unsigned long status = read_c0_status();
@@ -223,9 +235,6 @@ void __init arch_init_irq(void)
        int i;
        int configPR;
 
-       /* init of cp0 interrupts */
-       set_except_vector(0, cp0_irqdispatch);
-
        for (i = 0; i < PNX8550_INT_CP0_TOTINT; i++) {
                irq_desc[i].handler = &level_irq_type;
                pnx8550_ack(i); /* mask the irq just in case  */
diff --git a/arch/mips/philips/pnx8550/common/mipsIRQ.S b/arch/mips/philips/pnx8550/common/mipsIRQ.S
deleted file mode 100644 (file)
index 338bffd..0000000
+++ /dev/null
@@ -1,76 +0,0 @@
-/*
- * Copyright (c) 2002 Philips, Inc. All rights.
- * Copyright (c) 2002 Red Hat, Inc. All rights.
- *
- * This software may be freely redistributed under the terms of the
- * GNU General Public License.
- *
- * 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., 675 Mass Ave, Cambridge, MA 02139, USA.
- *
- * Based upon arch/mips/galileo-boards/ev64240/int-handler.S
- *
- */
-#include <asm/asm.h>
-#include <asm/mipsregs.h>
-#include <asm/addrspace.h>
-#include <asm/regdef.h>
-#include <asm/stackframe.h>
-
-/*
- * cp0_irqdispatch
- *
- *    Code to handle in-core interrupt exception.
- */
-
-               .align  5
-               .set    reorder
-               .set    noat
-               NESTED(cp0_irqdispatch, PT_SIZE, sp)
-               SAVE_ALL
-               CLI
-               .set    at
-               mfc0    t0,CP0_CAUSE
-               mfc0    t2,CP0_STATUS
-
-               and     t0,t2
-
-               andi    t1,t0,STATUSF_IP2 /* int0 hardware line */
-               bnez    t1,ll_hw0_irq
-               nop
-
-               andi    t1,t0,STATUSF_IP7 /* int5 hardware line */
-               bnez    t1,ll_timer_irq
-               nop
-
-               /* wrong alarm or masked ... */
-
-               j       spurious_interrupt
-               nop
-               END(cp0_irqdispatch)
-
-               .align  5
-               .set    reorder
-ll_hw0_irq:
-               li      a0,2
-               move    a1,sp
-               jal     hw0_irqdispatch
-               nop
-               j       ret_from_irq
-               nop
-
-               .align  5
-               .set    reorder
-ll_timer_irq:
-               mfc0    t3,CP0_CONFIG,7
-               andi    t4,t3,0x01c0
-               beqz    t4,ll_timer_out
-               nop
-               li      a0,7
-               move    a1,sp
-               jal     timer_irqdispatch
-               nop
-
-ll_timer_out:  j       ret_from_irq
-               nop
index a592260fd6735b8a902e6939ddbd7826dcd0dec1..5436b4b97455f8ce95fffed943685d7eee5fda48 100644 (file)
@@ -18,6 +18,7 @@
 #include <linux/resource.h>
 #include <linux/serial.h>
 #include <linux/serial_ip3106.h>
+#include <linux/platform_device.h>
 
 #include <int.h>
 #include <usb.h>
index ae96a71a3089612e50c529bc8cf582315e01d1e2..e931e0d44229eee58b16b2cdc17c33965d9665ed 100644 (file)
@@ -2,7 +2,7 @@
 # Makefile for the PMC-Sierra Titan
 #
 
-obj-y    += irq-handler.o irq.o i2c-yosemite.o prom.o py-console.o setup.o
+obj-y    += irq.o i2c-yosemite.o prom.o py-console.o setup.o
 
 obj-$(CONFIG_KGDB)             += dbg_io.o
 obj-$(CONFIG_SMP)              += smp.o
diff --git a/arch/mips/pmc-sierra/yosemite/irq-handler.S b/arch/mips/pmc-sierra/yosemite/irq-handler.S
deleted file mode 100644 (file)
index 33b9c40..0000000
+++ /dev/null
@@ -1,93 +0,0 @@
-/*
- * Copyright 2003, 04 PMC-Sierra Inc.
- * Author: Manish Lachwani (lachwani@pmc-sierra.com
- * Copyright 2004 Ralf Baechle (ralf@linux-mips.org)
- *
- * First-level interrupt router for the PMC-Sierra Titan board
- *
- * This program is free software; you can redistribute  it and/or modify it
- * under  the terms of  the GNU General  Public License as published by the
- * Free Software Foundation;  either version 2 of the  License, or (at your
- * option) any later version.
- *
- * Titan supports Hypertransport or PCI but not both. Hence, one interrupt
- * line is shared between the PCI slot A and Hypertransport. This is the
- * Processor INTB #0.
- */
-
-#include <linux/config.h>
-#include <asm/asm.h>
-#include <asm/mipsregs.h>
-#include <asm/addrspace.h>
-#include <asm/regdef.h>
-#include <asm/stackframe.h>
-
-               .align  5
-               NESTED(titan_handle_int, PT_SIZE, sp)
-               SAVE_ALL
-               CLI
-               .set    at
-               .set    noreorder
-               la      ra, ret_from_irq
-               mfc0    t0, CP0_CAUSE
-               mfc0    t2, CP0_STATUS
-
-               and     t0, t2
-
-               andi    t2, t0, STATUSF_IP7     /* INTB5 hardware line */
-               bnez    t2, ll_timer_irq        /* Timer */
-               andi    t1, t0, STATUSF_IP2     /* INTB0 hardware line */
-               bnez    t1, ll_pcia_irq         /* 64-bit PCI */
-               andi    t2, t0, STATUSF_IP3     /* INTB1 hardware line */
-               bnez    t2, ll_pcib_irq         /* second 64-bit PCI slot */
-               andi    t1, t0, STATUSF_IP4     /* INTB2 hardware line */
-               bnez    t1, ll_duart_irq        /* UART */
-               andi    t2, t0, STATUSF_IP5     /* SMP inter-core interrupts */
-               bnez    t2, ll_smp_irq
-               andi    t1, t0, STATUSF_IP6
-               bnez    t1, ll_ht_irq           /* Hypertransport */
-
-               move    a0, sp
-               j       do_extended_irq
-               END(titan_handle_int)
-
-               .set    reorder
-               .align  5
-
-ll_pcia_irq:
-               li      a0, 2
-               move    a1, sp
-#ifdef CONFIG_HYPERTRANSPORT
-               j       ll_ht_smp_irq_handler
-#else
-               j       do_IRQ
-#endif
-
-ll_pcib_irq:
-               li      a0, 3
-               move    a1, sp
-               j       do_IRQ
-
-ll_duart_irq:
-               li      a0, 4
-               move    a1, sp
-               j       do_IRQ
-
-ll_smp_irq:
-               li      a0, 5
-               move    a1, sp
-#ifdef CONFIG_SMP
-               j       titan_mailbox_irq
-#else
-               j       do_IRQ
-#endif
-
-ll_ht_irq:
-               li      a0, 6
-               move    a1, sp
-               j       ll_ht_smp_irq_handler
-
-ll_timer_irq:
-               li      a0, 7
-               move    a1, sp
-               j       do_IRQ
index f4e2897d9bf73af83623a4fdefb94012b0da3bcf..a1f524fc4c107feb18ba11024c35fa0f7b49b963 100644 (file)
@@ -2,6 +2,8 @@
  * Copyright (C) 2003 PMC-Sierra Inc.
  * Author: Manish Lachwani (lachwani@pmc-sierra.com)
  *
+ * Copyright (C) 2006 Ralf Baechle (ralf@linux-mips.org)
+ *
  *  This program is free software; you can redistribute  it and/or modify it
  *  under  the terms of  the GNU General  Public License as published by the
  *  Free Software Foundation;  either version 2 of the  License, or (at your
@@ -55,7 +57,6 @@
 #define HYPERTRANSPORT_INTC     0x7a           /* INTC# */
 #define HYPERTRANSPORT_INTD     0x7b           /* INTD# */
 
-extern asmlinkage void titan_handle_int(void);
 extern void jaguar_mailbox_irq(struct pt_regs *);
 
 /*
@@ -125,6 +126,35 @@ asmlinkage void do_extended_irq(struct pt_regs *regs)
 
 }
 
+asmlinkage void plat_irq_dispatch(struct pt_regs *regs)
+{
+       unsigned int cause = read_c0_cause();
+       unsigned int status = read_c0_status();
+       unsigned int pending = cause & status;
+
+       if (pending & STATUSF_IP7) {
+               do_IRQ(7, regs);
+       } else if (pending & STATUSF_IP2) {
+#ifdef CONFIG_HYPERTRANSPORT
+               ll_ht_smp_irq_handler(2, regs);
+#else
+               do_IRQ(2, regs);
+#endif
+       } else if (pending & STATUSF_IP3) {
+               do_IRQ(3, regs);
+       } else if (pending & STATUSF_IP4) {
+               do_IRQ(4, regs);
+       } else if (pending & STATUSF_IP5) {
+#ifdef CONFIG_SMP
+               titan_mailbox_irq(regs);
+#else
+               do_IRQ(5, regs);
+#endif
+       } else if (pending & STATUSF_IP6) {
+               do_IRQ(4, regs);
+       }
+}
+
 #ifdef CONFIG_KGDB
 extern void init_second_port(void);
 #endif
@@ -136,7 +166,6 @@ void __init arch_init_irq(void)
 {
        clear_c0_status(ST0_IM);
 
-       set_except_vector(0, titan_handle_int);
        mips_cpu_irq_init(0);
        rm7k_cpu_irq_init(8);
        rm9k_cpu_irq_init(12);
index 6a8e8bcef5528181dec4943c60f2d3635a150201..730f459f3e9920e0efeaa257ad88063eb8ed0265 100644 (file)
@@ -2,6 +2,6 @@
 # Makefile for Qemu specific kernel interface routines under Linux.
 #
 
-obj-y          = q-firmware.o q-int.o q-irq.o q-mem.o q-setup.o
+obj-y          = q-firmware.o q-irq.o q-mem.o q-setup.o
 
 obj-$(CONFIG_SMP) += q-smp.o
diff --git a/arch/mips/qemu/q-int.S b/arch/mips/qemu/q-int.S
deleted file mode 100644 (file)
index 6e3dfe5..0000000
+++ /dev/null
@@ -1,17 +0,0 @@
-/*
- * Qemu interrupt handler code.
- *
- * Copyright (C) 2005 by Ralf Baechle
- */
-#include <asm/asm.h>
-#include <asm/regdef.h>
-#include <asm/stackframe.h>
-
-       .align  5
-       NESTED(qemu_handle_int, PT_SIZE, sp)
-       SAVE_ALL
-       CLI
-       move    a0, sp
-       PTR_LA  ra, ret_from_irq
-       j       do_qemu_int
-       END(qemu_handle_int)
index 2c4e0704ff10d4b6f90bdd62b053dae468088ac4..3352374c4c7d2ed9bd2e21249fe8276b4ef8c445 100644 (file)
@@ -9,7 +9,7 @@
 
 extern asmlinkage void qemu_handle_int(void);
 
-asmlinkage void do_qemu_int(struct pt_regs *regs)
+asmlinkage void plat_irq_dispatch(struct pt_regs *regs)
 {
        unsigned int pending = read_c0_status() & read_c0_cause();
 
@@ -29,7 +29,6 @@ asmlinkage void do_qemu_int(struct pt_regs *regs)
 
 void __init arch_init_irq(void)
 {
-       set_except_vector(0, qemu_handle_int);
        mips_hpt_frequency = QEMU_C0_COUNTER_CLOCK;             /* 100MHz */
 
        init_i8259_irqs();
index eb0820fe50bd4e33b390c2df3eddc5b805ef728d..6aa4c0cd169ce513eba9dcafadd98faf2f797cb6 100644 (file)
@@ -3,7 +3,7 @@
 # under Linux.
 #
 
-obj-y  += ip22-mc.o ip22-hpc.o ip22-int.o ip22-irq.o ip22-berr.o \
+obj-y  += ip22-mc.o ip22-hpc.o ip22-int.o ip22-berr.o \
           ip22-time.o ip22-nvram.o ip22-reset.o ip22-setup.o
 
 obj-$(CONFIG_EISA)     += ip22-eisa.o
index d16fb43b1a93ba745f2a9838247f7bd1f845f932..fc6a7e2b189ccd90224c54dbf6ac4ae62ba99b68 100644 (file)
@@ -37,7 +37,6 @@ static char lc1msk_to_irqnr[256];
 static char lc2msk_to_irqnr[256];
 static char lc3msk_to_irqnr[256];
 
-extern asmlinkage void indyIRQ(void);
 extern int ip22_eisa_init(void);
 
 static void enable_local0_irq(unsigned int irq)
@@ -224,7 +223,7 @@ static struct hw_interrupt_type ip22_local3_irq_type = {
        .end            = end_local3_irq,
 };
 
-void indy_local0_irqdispatch(struct pt_regs *regs)
+static void indy_local0_irqdispatch(struct pt_regs *regs)
 {
        u8 mask = sgint->istat0 & sgint->imask0;
        u8 mask2;
@@ -242,7 +241,7 @@ void indy_local0_irqdispatch(struct pt_regs *regs)
        return;
 }
 
-void indy_local1_irqdispatch(struct pt_regs *regs)
+static void indy_local1_irqdispatch(struct pt_regs *regs)
 {
        u8 mask = sgint->istat1 & sgint->imask1;
        u8 mask2;
@@ -262,7 +261,7 @@ void indy_local1_irqdispatch(struct pt_regs *regs)
 
 extern void ip22_be_interrupt(int irq, struct pt_regs *regs);
 
-void indy_buserror_irq(struct pt_regs *regs)
+static void indy_buserror_irq(struct pt_regs *regs)
 {
        int irq = SGI_BUSERR_IRQ;
 
@@ -307,6 +306,56 @@ static struct irqaction map1_cascade = {
 #define SGI_INTERRUPTS SGINT_LOCAL3
 #endif
 
+extern void indy_r4k_timer_interrupt(struct pt_regs *regs);
+extern void indy_8254timer_irq(struct pt_regs *regs);
+
+/*
+ * IRQs on the INDY look basically (barring software IRQs which we don't use
+ * at all) like:
+ *
+ *     MIPS IRQ        Source
+ *      --------        ------
+ *             0       Software (ignored)
+ *             1        Software (ignored)
+ *             2        Local IRQ level zero
+ *             3        Local IRQ level one
+ *             4        8254 Timer zero
+ *             5        8254 Timer one
+ *             6        Bus Error
+ *             7        R4k timer (what we use)
+ *
+ * We handle the IRQ according to _our_ priority which is:
+ *
+ * Highest ----     R4k Timer
+ *                  Local IRQ zero
+ *                  Local IRQ one
+ *                  Bus Error
+ *                  8254 Timer zero
+ * Lowest  ----     8254 Timer one
+ *
+ * then we just return, if multiple IRQs are pending then we will just take
+ * another exception, big deal.
+ */
+
+asmlinkage void plat_irq_dispatch(struct pt_regs *regs)
+{
+       unsigned int pending = read_c0_cause();
+
+       /*
+        * First we check for r4k counter/timer IRQ.
+        */
+       if (pending & CAUSEF_IP7)
+               indy_r4k_timer_interrupt(regs);
+       else if (pending & CAUSEF_IP2)
+               indy_local0_irqdispatch(regs);
+       else if (pending & CAUSEF_IP3)
+               indy_local1_irqdispatch(regs);
+       else if (pending & CAUSEF_IP6)
+               indy_buserror_irq(regs);
+       else if (pending & (CAUSEF_IP4 | CAUSEF_IP5))
+               indy_8254timer_irq(regs);
+}
+
 extern void mips_cpu_irq_init(unsigned int irq_base);
 
 void __init arch_init_irq(void)
@@ -369,8 +418,6 @@ void __init arch_init_irq(void)
        sgint->cmeimask0 = 0;
        sgint->cmeimask1 = 0;
 
-       set_except_vector(0, indyIRQ);
-
        /* init CPU irqs */
        mips_cpu_irq_init(SGINT_CPU);
 
diff --git a/arch/mips/sgi-ip22/ip22-irq.S b/arch/mips/sgi-ip22/ip22-irq.S
deleted file mode 100644 (file)
index 6ccbd9e..0000000
+++ /dev/null
@@ -1,118 +0,0 @@
-/*
- * ip22-irq.S: Interrupt exception dispatch code for FullHouse and
- *             Guiness.
- *
- * Copyright (C) 1996 David S. Miller (dm@engr.sgi.com)
- */
-
-#include <asm/asm.h>
-#include <asm/mipsregs.h>
-#include <asm/regdef.h>
-#include <asm/stackframe.h>
-
-/* A lot of complication here is taken away because:
- *
- * 1) We handle one interrupt and return, sitting in a loop and moving across
- *    all the pending IRQ bits in the cause register is _NOT_ the answer, the
- *    common case is one pending IRQ so optimize in that direction.
- *
- * 2) We need not check against bits in the status register IRQ mask, that
- *    would make this routine slow as hell.
- *
- * 3) Linux only thinks in terms of all IRQs on or all IRQs off, nothing in
- *    between like BSD spl() brain-damage.
- *
- * Furthermore, the IRQs on the INDY look basically (barring software IRQs
- * which we don't use at all) like:
- *
- *     MIPS IRQ        Source
- *      --------        ------
- *             0       Software (ignored)
- *             1        Software (ignored)
- *             2        Local IRQ level zero
- *             3        Local IRQ level one
- *             4        8254 Timer zero
- *             5        8254 Timer one
- *             6        Bus Error
- *             7        R4k timer (what we use)
- *
- * We handle the IRQ according to _our_ priority which is:
- *
- * Highest ----     R4k Timer
- *                  Local IRQ zero
- *                  Local IRQ one
- *                  Bus Error
- *                  8254 Timer zero
- * Lowest  ----     8254 Timer one
- *
- * then we just return, if multiple IRQs are pending then we will just take
- * another exception, big deal.
- */
-
-       .text
-       .set    noreorder
-       .set    noat
-       .align  5
-       NESTED(indyIRQ, PT_SIZE, sp)
-       SAVE_ALL
-       CLI
-       .set    at
-       mfc0    s0, CP0_CAUSE           # get irq mask
-
-       /* First we check for r4k counter/timer IRQ. */
-       andi    a0, s0, CAUSEF_IP7
-       beq     a0, zero, 1f
-        andi   a0, s0, CAUSEF_IP2      # delay slot, check local level zero
-
-       /* Wheee, a timer interrupt. */
-       jal     indy_r4k_timer_interrupt
-        move   a0, sp                  # delay slot
-       j       ret_from_irq
-        nop                            # delay slot
-
-1:
-       beq     a0, zero, 1f
-        andi   a0, s0, CAUSEF_IP3      # delay slot, check local level one
-
-       /* Wheee, local level zero interrupt. */
-       jal     indy_local0_irqdispatch
-        move   a0, sp                  # delay slot
-
-       j       ret_from_irq
-        nop                            # delay slot
-
-1:
-       beq     a0, zero, 1f
-        andi   a0, s0, CAUSEF_IP6      # delay slot, check bus error
-
-       /* Wheee, local level one interrupt. */
-       jal     indy_local1_irqdispatch
-        move   a0, sp                  # delay slot
-       j       ret_from_irq
-        nop                            # delay slot
-
-1:
-       beq     a0, zero, 1f
-        andi   a0, s0, (CAUSEF_IP4 | CAUSEF_IP5)       # delay slot
-
-       /* Wheee, an asynchronous bus error... */
-       jal     indy_buserror_irq
-        move   a0, sp                  # delay slot
-       j       ret_from_irq
-        nop                            # delay slot
-
-1:
-       /* Here by mistake? It is possible, that by the time we take
-        * the exception the IRQ pin goes low, so just leave if this
-        * is the case.
-        */
-       beq     a0, zero, 1f
-        nop                            # delay slot
-
-       /* Must be one of the 8254 timers... */
-       jal     indy_8254timer_irq
-        move   a0, sp                  # delay slot
-1:
-       j       ret_from_irq
-        nop                            # delay slot
-       END(indyIRQ)
index 4ba340780c351bbce9d67a7cc0dc0652b935c78b..686ba14e2882495039bc73fc256fa73840f0b2b4 100644 (file)
@@ -2,7 +2,7 @@
 # Makefile for the IP27 specific kernel interface routines under Linux.
 #
 
-obj-y  := ip27-berr.o ip27-console.o ip27-irq.o ip27-init.o ip27-irq-glue.o \
+obj-y  := ip27-berr.o ip27-console.o ip27-irq.o ip27-init.o \
           ip27-klconfig.o ip27-klnuma.o ip27-memory.o ip27-nmi.o ip27-reset.o \
           ip27-timer.o ip27-hubio.o ip27-xtalk.o
 
index 32106131b0d08ded043f432a414115f97419cbcf..19f1512c8f2e3934a649d48d80e0630f93e96a48 100644 (file)
@@ -9,10 +9,6 @@ ip27-init.c:find_lbaord_real. DONE
 in irix?
 6. Investigate why things do not work without the setup_test() call
 being invoked on all nodes in ip27-memory.c.
-7. Too many CLIs in the locore handlers :
-For the low level handlers set up by set_except_vector(),
-__tlb_refill_debug_tramp, __xtlb_refill_debug_tramp and cacheerror,
-investigate whether the code should do CLI, STI or KMODE.
 8. Too many do_page_faults invoked - investigate.
 9. start_thread must turn off UX64 ... and define tlb_refill_debug.
 10. Need a bad pmd table, bad pte table. __bad_pmd_table/__bad_pagetable
diff --git a/arch/mips/sgi-ip27/ip27-irq-glue.S b/arch/mips/sgi-ip27/ip27-irq-glue.S
deleted file mode 100644 (file)
index c304df7..0000000
+++ /dev/null
@@ -1,45 +0,0 @@
-/*
- * This file is subject to the terms and conditions of the GNU General Public
- * License.  See the file "COPYING" in the main directory of this archive
- * for more details.
- *
- * Copyright (C) 1999 Ralf Baechle
- * Copyright (C) 1999 Silicon Graphics, Inc.
- */
-#include <asm/asm.h>
-#include <asm/mipsregs.h>
-#include <asm/regdef.h>
-#include <asm/stackframe.h>
-
-       .text
-       .align  5
-NESTED(ip27_irq, PT_SIZE, sp)
-       SAVE_ALL
-       CLI
-
-       mfc0    s0, CP0_CAUSE
-       mfc0    t0, CP0_STATUS
-       and     s0, t0
-       move    a0, sp
-       PTR_LA  ra, ret_from_irq
-
-       /* First check for RT interrupt.  */
-       andi    t0, s0, CAUSEF_IP4
-       bnez    t0, ip4
-       andi    t0, s0, CAUSEF_IP2
-       bnez    t0, ip2
-       andi    t0, s0, CAUSEF_IP3
-       bnez    t0, ip3
-       andi    t0, s0, CAUSEF_IP5
-       bnez    t0, ip5
-       andi    t0, s0, CAUSEF_IP6
-       bnez    t0, ip6
-       j       ra
-
-ip2:   j       ip27_do_irq_mask0       # PI_INT_PEND_0 or CC_PEND_{A|B}
-ip3:   j       ip27_do_irq_mask1       # PI_INT_PEND_1
-ip4:   j       ip27_rt_timer_interrupt
-ip5:   j       ip27_prof_timer
-ip6:   j       ip27_hub_error
-
-       END(ip27_irq)
index 2854ac4c9be13e0d75430de1f99eaef2ff070edb..2e643d2f51cbb7b909e859c5f4aae0cfbae1dde7 100644 (file)
@@ -130,7 +130,7 @@ static int ms1bit(unsigned long x)
  * Kanoj 05.13.00
  */
 
-void ip27_do_irq_mask0(struct pt_regs *regs)
+static void ip27_do_irq_mask0(struct pt_regs *regs)
 {
        int irq, swlevel;
        hubreg_t pend0, mask0;
@@ -171,7 +171,7 @@ void ip27_do_irq_mask0(struct pt_regs *regs)
        LOCAL_HUB_L(PI_INT_PEND0);
 }
 
-void ip27_do_irq_mask1(struct pt_regs *regs)
+static void ip27_do_irq_mask1(struct pt_regs *regs)
 {
        int irq, swlevel;
        hubreg_t pend1, mask1;
@@ -196,12 +196,12 @@ void ip27_do_irq_mask1(struct pt_regs *regs)
        LOCAL_HUB_L(PI_INT_PEND1);
 }
 
-void ip27_prof_timer(struct pt_regs *regs)
+static void ip27_prof_timer(struct pt_regs *regs)
 {
        panic("CPU %d got a profiling interrupt", smp_processor_id());
 }
 
-void ip27_hub_error(struct pt_regs *regs)
+static void ip27_hub_error(struct pt_regs *regs)
 {
        panic("CPU %d got a hub error interrupt", smp_processor_id());
 }
@@ -421,9 +421,26 @@ int __devinit request_bridge_irq(struct bridge_controller *bc)
        return irq;
 }
 
+extern void ip27_rt_timer_interrupt(struct pt_regs *regs);
+
+asmlinkage void plat_irq_dispatch(struct pt_regs *regs)
+{
+       unsigned long pending = read_c0_cause() & read_c0_status();
+
+       if (pending & CAUSEF_IP4)
+               ip27_rt_timer_interrupt(regs);
+       else if (pending & CAUSEF_IP2)  /* PI_INT_PEND_0 or CC_PEND_{A|B} */
+               ip27_do_irq_mask0(regs);
+       else if (pending & CAUSEF_IP3)  /* PI_INT_PEND_1 */
+               ip27_do_irq_mask1(regs);
+       else if (pending & CAUSEF_IP5)
+               ip27_prof_timer(regs);
+       else if (pending & CAUSEF_IP6)
+               ip27_hub_error(regs);
+}
+
 void __init arch_init_irq(void)
 {
-       set_except_vector(0, ip27_irq);
 }
 
 void install_ipi(void)
index 470898f4afe15c4b855e55082ab938bd650dea46..530bf848c3d065fae9442b1175d3f4f5e6cceabb 100644 (file)
@@ -3,7 +3,7 @@
 # under Linux.
 #
 
-obj-y  += ip32-berr.o ip32-irq.o ip32-irq-glue.o ip32-setup.o ip32-reset.o \
+obj-y  += ip32-berr.o ip32-irq.o ip32-setup.o ip32-reset.o \
           crime.o ip32-memory.o
 
 EXTRA_AFLAGS := $(CFLAGS)
diff --git a/arch/mips/sgi-ip32/ip32-irq-glue.S b/arch/mips/sgi-ip32/ip32-irq-glue.S
deleted file mode 100644 (file)
index 200924e..0000000
+++ /dev/null
@@ -1,86 +0,0 @@
-/*
- * Low level interrupt handler for the SGI O2 aka IP32 aka Moosehead
- *
- * This file is subject to the terms and conditions of the GNU General Public
- * License.  See the file "COPYING" in the main directory of this archive
- * for more details.
- *
- * Copyright (C) 2000 Harald Koerfgen
- * Copyright (C) 2001 Keith M Wesolowski
- */
-#include <asm/asm.h>
-#include <asm/regdef.h>
-#include <asm/mipsregs.h>
-#include <asm/stackframe.h>
-#include <asm/addrspace.h>
-
-               .text
-               .set    noreorder
-               .set    noat
-               .align  5
-               NESTED(ip32_handle_int, PT_SIZE, ra)
-               .set    noat
-               SAVE_ALL
-               CLI                     # TEST: interrupts should be off
-               .set    at
-               .set    noreorder
-
-               mfc0    s0,CP0_CAUSE
-
-               andi    t1, s0, IE_IRQ0
-               bnez    t1, handle_irq0
-                andi   t1, s0, IE_IRQ1
-               bnez    t1, handle_irq1
-                andi   t1, s0, IE_IRQ2
-               bnez    t1, handle_irq2
-                andi   t1, s0, IE_IRQ3
-               bnez    t1, handle_irq3
-                andi   t1, s0, IE_IRQ4
-               bnez    t1, handle_irq4
-                andi   t1, s0, IE_IRQ5
-               bnez    t1, handle_irq5
-                nop
-
-               /* Either someone has triggered the "software interrupts"
-                * or we lost an interrupt somehow.  Ignore it.
-                */
-               j       ret_from_irq
-                nop
-
-handle_irq0:
-               jal     ip32_irq0
-                move   a0, sp
-               j       ret_from_irq
-                nop
-
-handle_irq1:
-               jal     ip32_irq1
-                move   a0, sp
-               j       ret_from_irq
-                nop
-
-handle_irq2:
-               jal     ip32_irq2
-                move   a0, sp
-               j       ret_from_irq
-                nop
-
-handle_irq3:
-               jal     ip32_irq3
-                move   a0, sp
-               j       ret_from_irq
-                nop
-
-handle_irq4:
-               jal     ip32_irq4
-                move   a0, sp
-               j       ret_from_irq
-                nop
-
-handle_irq5:
-               jal     ip32_irq5
-               move    a0, sp
-               j       ret_from_irq
-                nop
-
-               END(ip32_handle_int)
index 2eb22d692ed9bef6293f5345b68cdd0c6ba6e3c5..22a6df94b4a1e0ea81ae5602b710820b54014161 100644 (file)
@@ -130,8 +130,6 @@ struct irqaction memerr_irq = { crime_memerr_intr, SA_INTERRUPT,
 struct irqaction cpuerr_irq = { crime_cpuerr_intr, SA_INTERRUPT,
                        CPU_MASK_NONE, "CRIME CPU error", NULL, NULL };
 
-extern void ip32_handle_int(void);
-
 /*
  * For interrupts wired from a single device to the CPU.  Only the clock
  * uses this it seems, which is IRQ 0 and IP7.
@@ -503,7 +501,7 @@ static void ip32_unknown_interrupt(struct pt_regs *regs)
 
 /* CRIME 1.1 appears to deliver all interrupts to this one pin. */
 /* change this to loop over all edge-triggered irqs, exception masked out ones */
-void ip32_irq0(struct pt_regs *regs)
+static void ip32_irq0(struct pt_regs *regs)
 {
        uint64_t crime_int;
        int irq = 0;
@@ -520,31 +518,49 @@ void ip32_irq0(struct pt_regs *regs)
        do_IRQ(irq, regs);
 }
 
-void ip32_irq1(struct pt_regs *regs)
+static void ip32_irq1(struct pt_regs *regs)
 {
        ip32_unknown_interrupt(regs);
 }
 
-void ip32_irq2(struct pt_regs *regs)
+static void ip32_irq2(struct pt_regs *regs)
 {
        ip32_unknown_interrupt(regs);
 }
 
-void ip32_irq3(struct pt_regs *regs)
+static void ip32_irq3(struct pt_regs *regs)
 {
        ip32_unknown_interrupt(regs);
 }
 
-void ip32_irq4(struct pt_regs *regs)
+static void ip32_irq4(struct pt_regs *regs)
 {
        ip32_unknown_interrupt(regs);
 }
 
-void ip32_irq5(struct pt_regs *regs)
+static void ip32_irq5(struct pt_regs *regs)
 {
        ll_timer_interrupt(IP32_R4K_TIMER_IRQ, regs);
 }
 
+asmlinkage void plat_irq_dispatch(struct pt_regs *regs)
+{
+       unsigned int pending = read_c0_cause();
+
+       if (likely(pending & IE_IRQ0))
+               ip32_irq0(regs);
+       else if (unlikely(pending & IE_IRQ1))
+               ip32_irq1(regs);
+       else if (unlikely(pending & IE_IRQ2))
+               ip32_irq2(regs);
+       else if (unlikely(pending & IE_IRQ3))
+               ip32_irq3(regs);
+       else if (unlikely(pending & IE_IRQ4))
+               ip32_irq4(regs);
+       else if (likely(pending & IE_IRQ5))
+               ip32_irq5(regs);
+}
+
 void __init arch_init_irq(void)
 {
        unsigned int irq;
@@ -556,7 +572,6 @@ void __init arch_init_irq(void)
        crime->soft_int = 0;
        mace->perif.ctrl.istat = 0;
        mace->perif.ctrl.imask = 0;
-       set_except_vector(0, ip32_handle_int);
 
        for (irq = 0; irq <= IP32_IRQ_MAX; irq++) {
                hw_irq_controller *controller;
index 538d5a51ae94fb515db922290bcc541a722d4b50..7b36ff3873b7f75d0dccf86875ae8854d54f6310 100644 (file)
@@ -1,4 +1,4 @@
-obj-y := setup.o irq.o irq_handler.o time.o
+obj-y := setup.o irq.o time.o
 
 obj-$(CONFIG_SMP)                      += smp.o
 
index 9cf7d713b13ccbaccf782db784cbe82f0c395167..e61760b14d99ec208d741e85f121f99cfb189838 100644 (file)
@@ -187,9 +187,6 @@ static void bcm1480_set_affinity(unsigned int irq, cpumask_t mask)
 #endif
 
 
-/* Defined in arch/mips/sibyte/bcm1480/irq_handler.S */
-extern void bcm1480_irq_handler(void);
-
 /*****************************************************************************/
 
 static unsigned int startup_bcm1480_irq(unsigned int irq)
@@ -422,7 +419,6 @@ void __init arch_init_irq(void)
 #endif
        /* Enable necessary IPs, disable the rest */
        change_c0_status(ST0_IM, imask);
-       set_except_vector(0, bcm1480_irq_handler);
 
 #ifdef CONFIG_KGDB
        if (kgdb_flag) {
@@ -473,3 +469,76 @@ void bcm1480_kgdb_interrupt(struct pt_regs *regs)
 }
 
 #endif         /* CONFIG_KGDB */
+
+static inline int dclz(unsigned long long x)
+{
+       int lz;
+
+       __asm__ (
+       "       .set    push                                            \n"
+       "       .set    mips64                                          \n"
+       "       dclz    %0, %1                                          \n"
+       "       .set    pop                                             \n"
+       : "=r" (lz)
+       : "r" (x));
+
+       return lz;
+}
+
+extern void bcm1480_timer_interrupt(struct pt_regs *regs);
+extern void bcm1480_mailbox_interrupt(struct pt_regs *regs);
+extern void bcm1480_kgdb_interrupt(struct pt_regs *regs);
+
+asmlinkage void plat_irq_dispatch(struct pt_regs *regs)
+{
+       unsigned int pending;
+
+#ifdef CONFIG_SIBYTE_BCM1480_PROF
+       /* Set compare to count to silence count/compare timer interrupts */
+       write_c0_compare(read_c0_count());
+#endif
+
+       pending = read_c0_cause();
+
+#ifdef CONFIG_SIBYTE_BCM1480_PROF
+       if (pending & CAUSEF_IP7)       /* Cpu performance counter interrupt */
+               sbprof_cpu_intr(exception_epc(regs));
+#endif
+
+       if (pending & CAUSEF_IP4)
+               bcm1480_timer_interrupt(regs);
+
+#ifdef CONFIG_SMP
+       if (pending & CAUSEF_IP3)
+               bcm1480_mailbox_interrupt(regs);
+#endif
+
+#ifdef CONFIG_KGDB
+       if (pending & CAUSEF_IP6)
+               bcm1480_kgdb_interrupt(regs);           /* KGDB (uart 1) */
+#endif
+
+       if (pending & CAUSEF_IP2) {
+               unsigned long long mask_h, mask_l;
+               unsigned long base;
+
+               /*
+                * Default...we've hit an IP[2] interrupt, which means we've
+                * got to check the 1480 interrupt registers to figure out what
+                * to do.  Need to detect which CPU we're on, now that
+                * smp_affinity is supported.
+                */
+               base = A_BCM1480_IMR_MAPPER(smp_processor_id());
+               mask_h = __raw_readq(
+                       IOADDR(base + R_BCM1480_IMR_INTERRUPT_STATUS_BASE_H));
+               mask_l = __raw_readq(
+                       IOADDR(base + R_BCM1480_IMR_INTERRUPT_STATUS_BASE_L));
+
+               if (!mask_h) {
+                       if (mask_h ^ 1)
+                               do_IRQ(63 - dclz(mask_h), regs);
+                       else
+                               do_IRQ(127 - dclz(mask_l), regs);
+               }
+       }
+}
diff --git a/arch/mips/sibyte/bcm1480/irq_handler.S b/arch/mips/sibyte/bcm1480/irq_handler.S
deleted file mode 100644 (file)
index 408db88..0000000
+++ /dev/null
@@ -1,165 +0,0 @@
-/*
- * Copyright (C) 2000,2001,2002,2003,2004 Broadcom Corporation
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- *
- * 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., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
- */
-
-/*
- * bcm1480_irq_handler() is the routine that is actually called when an
- * interrupt occurs.  It is installed as the exception vector handler in
- * init_IRQ() in arch/mips/sibyte/bcm1480/irq.c
- *
- * In the handle we figure out which interrupts need handling, and use that
- * to call the dispatcher, which will take care of actually calling
- * registered handlers
- *
- * Note that we take care of all raised interrupts in one go at the handler.
- * This is more BSDish than the Indy code, and also, IMHO, more sane.
- */
-#include <linux/config.h>
-
-#include <asm/addrspace.h>
-#include <asm/asm.h>
-#include <asm/mipsregs.h>
-#include <asm/regdef.h>
-#include <asm/stackframe.h>
-#include <asm/sibyte/sb1250_defs.h>
-#include <asm/sibyte/bcm1480_regs.h>
-#include <asm/sibyte/bcm1480_int.h>
-
-/*
- * What a pain. We have to be really careful saving the upper 32 bits of any
- * register across function calls if we don't want them trashed--since were
- * running in -o32, the calling routing never saves the full 64 bits of a
- * register across a function call.  Being the interrupt handler, we're
- * guaranteed that interrupts are disabled during this code so we don't have
- * to worry about random interrupts blasting the high 32 bits.
- */
-
-       .text
-       .set    push
-       .set    noreorder
-       .set    noat
-       .set    mips64
-       #.set   mips4
-       .align  5
-       NESTED(bcm1480_irq_handler, PT_SIZE, sp)
-       SAVE_ALL
-       CLI
-
-#ifdef CONFIG_SIBYTE_BCM1480_PROF
-       /* Set compare to count to silence count/compare timer interrupts */
-       mfc0    t1, CP0_COUNT
-       mtc0    t1, CP0_COMPARE /* pause to clear IP[7] bit of cause ? */
-#endif
-       /* Read cause */
-       mfc0    s0, CP0_CAUSE
-
-#ifdef CONFIG_SIBYTE_BCM1480_PROF
-       /* Cpu performance counter interrupt is routed to IP[7] */
-       andi    t1, s0, CAUSEF_IP7
-       beqz    t1, 0f
-        srl    t1, s0, (CAUSEB_BD-2)   /* Shift BD bit to bit 2 */
-       and     t1, t1, 0x4             /* mask to get just BD bit */
-#ifdef CONFIG_MIPS64
-       dmfc0   a0, CP0_EPC
-       daddu   a0, a0, t1              /* a0 = EPC + (BD ? 4 : 0) */
-#else
-       mfc0    a0, CP0_EPC
-       addu    a0, a0, t1              /* a0 = EPC + (BD ? 4 : 0) */
-#endif
-       jal     sbprof_cpu_intr
-        nop
-       j       ret_from_irq
-        nop
-0:
-#endif
-
-       /* Timer interrupt is routed to IP[4] */
-       andi    t1, s0, CAUSEF_IP4
-       beqz    t1, 1f
-        nop
-       jal     bcm1480_timer_interrupt
-        move   a0, sp                  /* Pass the registers along */
-       j       ret_from_irq
-        nop                            /* delay slot  */
-1:
-
-#ifdef CONFIG_SMP
-       /* Mailbox interrupt is routed to IP[3] */
-       andi     t1, s0, CAUSEF_IP3
-       beqz     t1, 2f
-        nop
-       jal      bcm1480_mailbox_interrupt
-        move    a0, sp
-       j        ret_from_irq
-        nop                            /* delay slot  */
-2:
-#endif
-
-#ifdef CONFIG_KGDB
-       /* KGDB (uart 1) interrupt is routed to IP[6] */
-       andi     t1, s0, CAUSEF_IP6
-       beqz     t1, 3f
-        nop                            /* delay slot  */
-       jal      bcm1480_kgdb_interrupt
-        move    a0, sp
-       j        ret_from_irq
-        nop                            /* delay slot  */
-3:
-#endif
-
-       and      t1, s0, CAUSEF_IP2
-       beqz     t1, 9f
-        nop
-
-       /*
-        * Default...we've hit an IP[2] interrupt, which means we've got
-        * to check the 1480 interrupt registers to figure out what to do
-        * Need to detect which CPU we're on, now that smp_affinity is
-        * supported.
-        */
-       PTR_LA   v0, CKSEG1 + A_BCM1480_IMR_CPU0_BASE
-#ifdef CONFIG_SMP
-       lw       t1, TI_CPU($28)
-       sll      t1, t1, BCM1480_IMR_REGISTER_SPACING_SHIFT
-       addu     v0, v0, t1
-#endif
-
-       /* Read IP[2] status (get both high and low halves of status) */
-       ld       s0, R_BCM1480_IMR_INTERRUPT_STATUS_BASE_H(v0)
-       ld       s1, R_BCM1480_IMR_INTERRUPT_STATUS_BASE_L(v0)
-
-       move     s2, zero       /* intr number  */
-       li       s3, 64
-
-       beqz     s0, 9f         /* No interrupts.  Return.  */
-        move    a1, sp
-
-       xori     s4, s0, 1      /* if s0 (_H) == 1, it's a low intr, so...  */
-       movz     s2, s3, s4     /* start the intr number at 64, and  */
-       movz     s0, s1, s4     /* look at the low status value.  */
-
-       dclz     s1, s0         /* Find the next interrupt.  */
-       dsubu    a0, zero, s1
-       daddiu   a0, a0, 63
-       jal      do_IRQ
-        daddu   a0, a0, s2
-
-9:     j        ret_from_irq
-        nop
-
-       .set pop
-       END(bcm1480_irq_handler)
index a8af846975884c6e97c57bcf6adfc38fcf4294d1..a2fdbd62f8ac0f78852f92b3870a5c2f721dd9ea 100644 (file)
@@ -1,4 +1,4 @@
-obj-y := setup.o irq.o irq_handler.o time.o
+obj-y := setup.o irq.o time.o
 
 obj-$(CONFIG_SMP)                      += smp.o
 obj-$(CONFIG_SIBYTE_TBPROF)            += bcm1250_tbprof.o
index 589537bfcc3d11b3cc66cc26db44e450492b0734..0f6e54db4888869c35d639fdc9963a602e62ad8c 100644 (file)
@@ -163,10 +163,6 @@ static void sb1250_set_affinity(unsigned int irq, cpumask_t mask)
 }
 #endif
 
-
-/* Defined in arch/mips/sibyte/sb1250/irq_handler.S */
-extern void sb1250_irq_handler(void);
-
 /*****************************************************************************/
 
 static unsigned int startup_sb1250_irq(unsigned int irq)
@@ -379,7 +375,6 @@ void __init arch_init_irq(void)
 #endif
        /* Enable necessary IPs, disable the rest */
        change_c0_status(ST0_IM, imask);
-       set_except_vector(0, sb1250_irq_handler);
 
 #ifdef CONFIG_KGDB
        if (kgdb_flag) {
@@ -409,7 +404,7 @@ void __init arch_init_irq(void)
 #define duart_out(reg, val)     csr_out32(val, IOADDR(A_DUART_CHANREG(kgdb_port,reg)))
 #define duart_in(reg)           csr_in32(IOADDR(A_DUART_CHANREG(kgdb_port,reg)))
 
-void sb1250_kgdb_interrupt(struct pt_regs *regs)
+static void sb1250_kgdb_interrupt(struct pt_regs *regs)
 {
        /*
         * Clear break-change status (allow some time for the remote
@@ -424,3 +419,74 @@ void sb1250_kgdb_interrupt(struct pt_regs *regs)
 }
 
 #endif         /* CONFIG_KGDB */
+
+static inline int dclz(unsigned long long x)
+{
+       int lz;
+
+       __asm__ (
+       "       .set    push                                            \n"
+       "       .set    mips64                                          \n"
+       "       dclz    %0, %1                                          \n"
+       "       .set    pop                                             \n"
+       : "=r" (lz)
+       : "r" (x));
+
+       return lz;
+}
+
+asmlinkage void plat_irq_dispatch(struct pt_regs *regs)
+{
+       unsigned int pending;
+
+#ifdef CONFIG_SIBYTE_SB1250_PROF
+       /* Set compare to count to silence count/compare timer interrupts */
+       write_c0_count(read_c0_count());
+#endif
+
+       /*
+        * What a pain. We have to be really careful saving the upper 32 bits
+        * of any * register across function calls if we don't want them
+        * trashed--since were running in -o32, the calling routing never saves
+        * the full 64 bits of a register across a function call.  Being the
+        * interrupt handler, we're guaranteed that interrupts are disabled
+        * during this code so we don't have to worry about random interrupts
+        * blasting the high 32 bits.
+        */
+
+       pending = read_c0_cause();
+
+#ifdef CONFIG_SIBYTE_SB1250_PROF
+       if (pending & CAUSEF_IP7) { /* Cpu performance counter interrupt */
+               sbprof_cpu_intr(exception_epc(regs));
+       }
+#endif
+
+       if (pending & CAUSEF_IP4)
+               sb1250_timer_interrupt(regs);
+
+#ifdef CONFIG_SMP
+       if (pending & CAUSEF_IP3)
+               sb1250_mailbox_interrupt(regs);
+#endif
+
+#ifdef CONFIG_KGDB
+       if (pending & CAUSEF_IP6)                       /* KGDB (uart 1) */
+               sb1250_kgdb_interrupt(regs);
+#endif
+
+       if (pending & CAUSEF_IP2) {
+               unsigned long long mask;
+
+               /*
+                * Default...we've hit an IP[2] interrupt, which means we've
+                * got to check the 1250 interrupt registers to figure out what
+                * to do.  Need to detect which CPU we're on, now that
+                ~ smp_affinity is supported.
+                */
+               mask = __raw_readq(IOADDR(A_IMR_REGISTER(smp_processor_id(),
+                                             R_IMR_INTERRUPT_STATUS_BASE)));
+               if (mask)
+                       do_IRQ(63 - dclz(mask), regs);
+       }
+}
diff --git a/arch/mips/sibyte/sb1250/irq_handler.S b/arch/mips/sibyte/sb1250/irq_handler.S
deleted file mode 100644 (file)
index 60edc8f..0000000
+++ /dev/null
@@ -1,147 +0,0 @@
-/*
- * Copyright (C) 2000, 2001, 2002, 2003 Broadcom Corporation
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- *
- * 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., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
- */
-
-/*
- * sb1250_handle_int() is the routine that is actually called when an interrupt
- * occurs.  It is installed as the exception vector handler in arch_init_irq()
- * in arch/mips/sibyte/sb1250/irq.c
- *
- * In the handle we figure out which interrupts need handling, and use that to
- * call the dispatcher, which will take care of actually calling registered
- * handlers
- *
- * Note that we take care of all raised interrupts in one go at the handler.
- * This is more BSDish than the Indy code, and also, IMHO, more sane.
- */
-#include <linux/config.h>
-
-#include <asm/addrspace.h>
-#include <asm/asm.h>
-#include <asm/mipsregs.h>
-#include <asm/regdef.h>
-#include <asm/stackframe.h>
-#include <asm/sibyte/sb1250_defs.h>
-#include <asm/sibyte/sb1250_regs.h>
-#include <asm/sibyte/sb1250_int.h>
-
-/*
- * What a pain. We have to be really careful saving the upper 32 bits of any
- * register across function calls if we don't want them trashed--since were
- * running in -o32, the calling routing never saves the full 64 bits of a
- * register across a function call.  Being the interrupt handler, we're
- * guaranteed that interrupts are disabled during this code so we don't have
- * to worry about random interrupts blasting the high 32 bits.
- */
-
-       .text
-       .set    push
-       .set    noreorder
-       .set    noat
-       .set    mips64
-       .align  5
-       NESTED(sb1250_irq_handler, PT_SIZE, sp)
-       SAVE_ALL
-       CLI
-
-#ifdef CONFIG_SIBYTE_SB1250_PROF
-       /* Set compare to count to silence count/compare timer interrupts */
-       mfc0    t1, CP0_COUNT
-       mtc0    t1, CP0_COMPARE /* pause to clear IP[7] bit of cause ? */
-#endif
-       /* Read cause */
-       mfc0    s0, CP0_CAUSE
-
-#ifdef CONFIG_SIBYTE_SB1250_PROF
-       /* Cpu performance counter interrupt is routed to IP[7] */
-       andi    t1, s0, CAUSEF_IP7
-       beqz    t1, 0f
-        srl    t1, s0, (CAUSEB_BD-2)  /* Shift BD bit to bit 2 */
-       and     t1, t1, 0x4             /* mask to get just BD bit */
-       mfc0    a0, CP0_EPC
-       jal     sbprof_cpu_intr
-        addu   a0, a0, t1              /* a0 = EPC + (BD ? 4 : 0) */
-       j       ret_from_irq
-        nop
-0:
-#endif
-
-       /* Timer interrupt is routed to IP[4] */
-       andi    t1, s0, CAUSEF_IP4
-       beqz    t1, 1f
-        nop
-       jal     sb1250_timer_interrupt
-        move   a0, sp                  /* Pass the registers along */
-       j       ret_from_irq
-        nop                            # delay slot
-1:
-
-#ifdef CONFIG_SMP
-       /* Mailbox interrupt is routed to IP[3] */
-       andi     t1, s0, CAUSEF_IP3
-       beqz     t1, 2f
-        nop
-       jal      sb1250_mailbox_interrupt
-        move    a0, sp
-       j       ret_from_irq
-        nop                            # delay slot
-2:
-#endif
-
-#ifdef CONFIG_KGDB
-       /* KGDB (uart 1) interrupt is routed to IP[6] */
-       andi    t1, s0, CAUSEF_IP6
-       beqz    t1, 1f
-       nop                            # delay slot
-       jal     sb1250_kgdb_interrupt
-         move  a0, sp
-       j       ret_from_irq
-       nop                            # delay slot
-1:
-#endif
-
-       and      t1, s0, CAUSEF_IP2
-       beqz     t1, 4f
-        nop
-
-       /*
-        * Default...we've hit an IP[2] interrupt, which means we've got to
-        * check the 1250 interrupt registers to figure out what to do
-        * Need to detect which CPU we're on, now that smp_affinity is supported.
-        */
-       PTR_LA  v0, CKSEG1 + A_IMR_CPU0_BASE
-#ifdef CONFIG_SMP
-       lw      t1, TI_CPU($28)
-       sll     t1, IMR_REGISTER_SPACING_SHIFT
-       addu    v0, t1
-#endif
-       ld      s0, R_IMR_INTERRUPT_STATUS_BASE(v0)     /* read IP[2] status */
-
-       beqz    s0, 4f          /* No interrupts.  Return */
-        move   a1, sp
-
-3:     dclz    s1, s0          /* Find the next interrupt */
-       dsubu   a0, zero, s1
-       daddiu  a0, a0, 63
-       jal      do_IRQ
-        nop
-
-4:     j        ret_from_irq
-        nop
-
-       .set pop
-       END(sb1250_irq_handler)
index 1e5676e4be86080ec9f3df73a5afa9a9ef1bc55f..9c7eaa5fb2106ad5d63ce41bfb8fa63861f440b0 100644 (file)
@@ -2,6 +2,6 @@
 # Makefile for the SNI specific part of the kernel
 #
 
-obj-y          += int-handler.o irq.o pcimt_scache.o reset.o setup.o
+obj-y          += irq.o pcimt_scache.o reset.o setup.o
 
 EXTRA_AFLAGS := $(CFLAGS)
diff --git a/arch/mips/sni/int-handler.S b/arch/mips/sni/int-handler.S
deleted file mode 100644 (file)
index 2cdc09f..0000000
+++ /dev/null
@@ -1,106 +0,0 @@
-/*
- * SNI RM200 PCI specific interrupt handler code.
- *
- * Copyright (C) 1994, 95, 96, 97, 98, 1999, 2000, 01 by Ralf Baechle
- */
-#include <asm/asm.h>
-#include <asm/mipsregs.h>
-#include <asm/regdef.h>
-#include <asm/sni.h>
-#include <asm/stackframe.h>
-
-/*
- * The PCI ASIC has the nasty property that it may delay writes if it is busy.
- * As a consequence from writes that have not graduated when we exit from the
- * interrupt handler we might catch a spurious interrupt.  To avoid this we
- * force the PCI ASIC to graduate all writes by executing a read from the
- * PCI bus.
- */
-               .set    noreorder
-               .set    noat
-               .align  5
-               NESTED(sni_rm200_pci_handle_int, PT_SIZE, sp)
-               SAVE_ALL
-               CLI
-               .set    at
-
-               /* Blinken light ...  */
-               lb      t0, led_cache
-               addiu   t0, 1
-               sb      t0, led_cache
-               sb      t0, PCIMT_CSLED                 # write only register
-               .data
-led_cache:     .byte   0
-               .text
-
-               mfc0    t0, CP0_STATUS
-               mfc0    t1, CP0_CAUSE
-               and     t0, t1
-
-                andi   t1, t0, 0x0800                  # hardware interrupt 1
-               bnez    t1, _hwint1
-                andi   t1, t0, 0x4000                  # hardware interrupt 4
-               bnez    t1, _hwint4
-                andi   t1, t0, 0x2000                  # hardware interrupt 3
-               bnez    t1, _hwint3
-                andi   t1, t0, 0x1000                  # hardware interrupt 2
-               bnez    t1, _hwint2
-                andi   t1, t0, 0x8000                  # hardware interrupt 5
-               bnez    t1, _hwint5
-                andi   t1, t0, 0x0400                  # hardware interrupt 0
-               bnez    t1, _hwint0
-                nop
-
-               j       restore_all                     # spurious interrupt
-                nop
-
- ##############################################################################
-
-/* hwint0 should deal with MP agent, ASIC PCI, EISA NMI and debug
-   button interrupts.  */
-_hwint0:       jal     pciasic_hwint0
-                move   a0, sp
-               j       ret_from_irq
-                nop
-
-/*
- * hwint 1 deals with EISA and SCSI interrupts
- */
-_hwint1:       jal     pciasic_hwint1
-                move   a0, sp
-               j       ret_from_irq
-                nop
-
-
-/*
- * This interrupt was used for the com1 console on the first prototypes;
- * it's unsed otherwise
- */
-_hwint2:       jal     pciasic_hwint2
-                move   a0, sp
-               j       ret_from_irq
-                nop
-
-/*
- * hwint 3 are the PCI interrupts A - D
- */
-_hwint3:       jal     pciasic_hwint3
-                move   a0, sp
-               j       ret_from_irq
-                nop
-
-/*
- * hwint 4 is used for only the onboard PCnet 32.
- */
-_hwint4:       jal     pciasic_hwint4
-                move   a0, sp
-               j       ret_from_irq
-                nop
-
-/* hwint5 is the r4k count / compare interrupt  */
-_hwint5:       jal     pciasic_hwint5
-                move   a0, sp
-               j       ret_from_irq
-                nop
-
-               END(sni_rm200_pci_handle_int)
index 952038aa4b90d7c0a5d8ad6a96bcf233ddb6cd85..7365b4853ddb212a0d6073d49d60460838819f1f 100644 (file)
@@ -19,8 +19,6 @@
 
 DEFINE_SPINLOCK(pciasic_lock);
 
-extern asmlinkage void sni_rm200_pci_handle_int(void);
-
 static void enable_pciasic_irq(unsigned int irq)
 {
        unsigned int mask = 1 << (irq - PCIMT_IRQ_INT2);
@@ -71,20 +69,20 @@ static struct hw_interrupt_type pciasic_irq_type = {
  * hwint0 should deal with MP agent, ASIC PCI, EISA NMI and debug
  * button interrupts.  Later ...
  */
-void pciasic_hwint0(struct pt_regs *regs)
+static void pciasic_hwint0(struct pt_regs *regs)
 {
        panic("Received int0 but no handler yet ...");
 }
 
 /* This interrupt was used for the com1 console on the first prototypes.  */
-void pciasic_hwint2(struct pt_regs *regs)
+static void pciasic_hwint2(struct pt_regs *regs)
 {
        /* I think this shouldn't happen on production machines.  */
        panic("hwint2 and no handler yet");
 }
 
 /* hwint5 is the r4k count / compare interrupt  */
-void pciasic_hwint5(struct pt_regs *regs)
+static void pciasic_hwint5(struct pt_regs *regs)
 {
        panic("hwint5 and no handler yet");
 }
@@ -105,7 +103,7 @@ static unsigned int ls1bit8(unsigned int x)
  *
  * The EISA_INT bit in CSITPEND is high active, all others are low active.
  */
-void pciasic_hwint1(struct pt_regs *regs)
+static void pciasic_hwint1(struct pt_regs *regs)
 {
        u8 pend = *(volatile char *)PCIMT_CSITPEND;
        unsigned long flags;
@@ -135,7 +133,7 @@ void pciasic_hwint1(struct pt_regs *regs)
 /*
  * hwint 3 should deal with the PCI A - D interrupts,
  */
-void pciasic_hwint3(struct pt_regs *regs)
+static void pciasic_hwint3(struct pt_regs *regs)
 {
        u8 pend = *(volatile char *)PCIMT_CSITPEND;
        int irq;
@@ -150,13 +148,34 @@ void pciasic_hwint3(struct pt_regs *regs)
 /*
  * hwint 4 is used for only the onboard PCnet 32.
  */
-void pciasic_hwint4(struct pt_regs *regs)
+static void pciasic_hwint4(struct pt_regs *regs)
 {
        clear_c0_status(IE_IRQ4);
        do_IRQ(PCIMT_IRQ_ETHERNET, regs);
        set_c0_status(IE_IRQ4);
 }
 
+asmlinkage void plat_irq_dispatch(struct pt_regs *regs)
+{
+       unsigned int pending = read_c0_status() & read_c0_cause();
+       static unsigned char led_cache;
+
+       *(volatile unsigned char *) PCIMT_CSLED = ++led_cache;
+
+       if (pending & 0x0800)
+               pciasic_hwint1(regs);
+       else if (pending & 0x4000)
+               pciasic_hwint4(regs);
+       else if (pending & 0x2000)
+               pciasic_hwint3(regs);
+       else if (pending & 0x1000)
+               pciasic_hwint2(regs);
+       else if (pending & 0x8000)
+               pciasic_hwint5(regs);
+       else if (pending & 0x0400)
+               pciasic_hwint0(regs);
+}
+
 void __init init_pciasic(void)
 {
        unsigned long flags;
@@ -176,8 +195,6 @@ void __init arch_init_irq(void)
 {
        int i;
 
-       set_except_vector(0, sni_rm200_pci_handle_int);
-
        init_i8259_irqs();                      /* Integrated i8259  */
        init_pciasic();
 
index 8fa126b296e1f2ddde15c504e1b4ab4f014966f2..9cb9535ebacba6e9ad6b3c65113cde36b25444e8 100644 (file)
@@ -6,7 +6,7 @@
 # unless it's something special (ie not a .c file).
 #
 
-obj-y  += tx4927_prom.o tx4927_setup.o tx4927_irq.o tx4927_irq_handler.o
+obj-y  += tx4927_prom.o tx4927_setup.o tx4927_irq.o
 
 obj-$(CONFIG_TOSHIBA_FPCIB0)      += smsc_fdc37m81x.o
 obj-$(CONFIG_KGDB)                 += tx4927_dbgio.o
index 5ab2e2b7601817c36cce5898eda21aa55f911bfe..8ca68015cf40ffd9456a17febfa107187eb8b18d 100644 (file)
@@ -525,8 +525,6 @@ static void tx4927_irq_pic_end(unsigned int irq)
  */
 void __init tx4927_irq_init(void)
 {
-       extern asmlinkage void tx4927_irq_handler(void);
-
        TX4927_IRQ_DPRINTK(TX4927_IRQ_INIT, "-\n");
 
        TX4927_IRQ_DPRINTK(TX4927_IRQ_INIT, "=Calling tx4927_irq_cp0_init()\n");
@@ -535,16 +533,12 @@ void __init tx4927_irq_init(void)
        TX4927_IRQ_DPRINTK(TX4927_IRQ_INIT, "=Calling tx4927_irq_pic_init()\n");
        tx4927_irq_pic_init();
 
-       TX4927_IRQ_DPRINTK(TX4927_IRQ_INIT,
-                          "=Calling set_except_vector(tx4927_irq_handler)\n");
-       set_except_vector(0, tx4927_irq_handler);
-
        TX4927_IRQ_DPRINTK(TX4927_IRQ_INIT, "+\n");
 
        return;
 }
 
-int tx4927_irq_nested(void)
+static int tx4927_irq_nested(void)
 {
        int sw_irq = 0;
        u32 level2;
@@ -582,3 +576,25 @@ int tx4927_irq_nested(void)
 
        return (sw_irq);
 }
+
+asmlinkage void plat_irq_dispatch(struct pt_regs *regs)
+{
+       unsigned int pending = read_c0_status() & read_c0_cause();
+
+       if (pending & STATUSF_IP7)                      /* cpu timer */
+               do_IRQ(TX4927_IRQ_CPU_TIMER, regs);
+       else if (pending & STATUSF_IP2) {               /* tx4927 pic */
+               unsigned int irq = tx4927_irq_nested();
+
+               if (unlikely(irq == 0)) {
+                       spurious_interrupt(regs);
+                       return;
+               }
+               do_IRQ(irq, regs);
+       } else if (pending & STATUSF_IP0)               /* user line 0 */
+               do_IRQ(TX4927_IRQ_USER0, regs);
+       else if (pending & STATUSF_IP1)                 /* user line 1 */
+               do_IRQ(TX4927_IRQ_USER1, regs);
+       else
+               spurious_interrupt(regs);
+}
diff --git a/arch/mips/tx4927/common/tx4927_irq_handler.S b/arch/mips/tx4927/common/tx4927_irq_handler.S
deleted file mode 100644 (file)
index dd3ceda..0000000
+++ /dev/null
@@ -1,103 +0,0 @@
-/*
- * linux/arch/mips/tx4927/common/tx4927_irq_handler.S
- *
- * Primary interrupt handler for tx4927 based systems
- *
- * Author: MontaVista Software, Inc.
- * Author: jsun@mvista.com or jsun@junsun.net
- *         source@mvista.com
- *
- * Copyright 2001-2002 MontaVista Software Inc.
- *
- *  This program is free software; you can redistribute it and/or modify it
- *  under the terms of the GNU General Public License as published by the
- *  Free Software Foundation; either version 2 of the License, or (at your
- *  option) any later version.
- *
- *  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 AUTHOR 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.
- *
- *  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.,
- *  675 Mass Ave, Cambridge, MA 02139, USA.
- */
-#include <asm/asm.h>
-#include <asm/mipsregs.h>
-#include <asm/addrspace.h>
-#include <asm/regdef.h>
-#include <asm/stackframe.h>
-#include <asm/tx4927/tx4927.h>
-
-               .align  5
-               NESTED(tx4927_irq_handler, PT_SIZE, sp)
-               SAVE_ALL
-               CLI
-               .set    at
-
-               mfc0    t0, CP0_CAUSE
-               mfc0    t1, CP0_STATUS
-               and     t0, t1
-
-               andi    t1, t0, STATUSF_IP7     /* cpu timer */
-               bnez    t1, ll_ip7
-
-               /* IP6..IP3 multiplexed -- do not use */
-
-               andi    t1, t0, STATUSF_IP2     /* tx4927 pic */
-               bnez    t1, ll_ip2
-
-               andi    t1, t0, STATUSF_IP0     /* user line 0 */
-               bnez    t1, ll_ip0
-
-               andi    t1, t0, STATUSF_IP1     /* user line 1 */
-               bnez    t1, ll_ip1
-
-               .set    reorder
-
-               /* wrong alarm or masked ... */
-               j       spurious_interrupt
-               nop
-               END(tx4927_irq_handler)
-
-               .align  5
-
-
-ll_ip7:
-               li      a0, TX4927_IRQ_CPU_TIMER
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-
-ll_ip2:
-               jal     tx4927_irq_nested
-               nop
-               beqz    v0, goto_spurious_interrupt
-               nop
-               move    a0, v0
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-
-goto_spurious_interrupt:
-       j spurious_interrupt
-       nop
-
-ll_ip1:
-               li      a0, TX4927_IRQ_USER1
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-
-ll_ip0:
-               li      a0, TX4927_IRQ_USER0
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
index 74c95c5bcdbff3d514a12e0d4ed2e5589a065257..2033ae77f6321c305489294d7a4aba939e4a835d 100644 (file)
@@ -6,6 +6,6 @@
 # unless it's something special (ie not a .c file).
 #
 
-obj-y  += prom.o setup.o irq.o irq_handler.o rtc_rx5c348.o
+obj-y  += prom.o setup.o irq.o rtc_rx5c348.o
 obj-$(CONFIG_KGDB) += dbgio.o
 
index 4f90d7faf634e72011224f4c031d53de5b5fb1e4..873805178d8e993b09402aad77ce8a9524f9bf83 100644 (file)
@@ -392,11 +392,8 @@ tx4938_irq_pic_end(unsigned int irq)
 void __init
 tx4938_irq_init(void)
 {
-       extern asmlinkage void tx4938_irq_handler(void);
-
        tx4938_irq_cp0_init();
        tx4938_irq_pic_init();
-       set_except_vector(0, tx4938_irq_handler);
 
        return;
 }
@@ -422,3 +419,21 @@ tx4938_irq_nested(void)
        wbflush();
        return (sw_irq);
 }
+
+asmlinkage void plat_irq_dispatch(struct pt_regs *regs)
+{
+       unsigned int pending = read_c0_cause() & read_c0_status();
+
+       if (pending & STATUSF_IP7)
+               do_IRQ(TX4938_IRQ_CPU_TIMER, regs);
+       else if (pending & STATUSF_IP2) {
+               int irq = tx4938_irq_nested();
+               if (irq)
+                       do_IRQ(irq, regs);
+               else
+                       spurious_interrupt(regs);
+       } else if (pending & STATUSF_IP1)
+               do_IRQ(TX4938_IRQ_USER1, regs);
+       else if (pending & STATUSF_IP0)
+               do_IRQ(TX4938_IRQ_USER0, regs);
+}
diff --git a/arch/mips/tx4938/common/irq_handler.S b/arch/mips/tx4938/common/irq_handler.S
deleted file mode 100644 (file)
index 1b2f72b..0000000
+++ /dev/null
@@ -1,84 +0,0 @@
-/*
- * linux/arch/mips/tx4938/common/handler.S
- *
- * Primary interrupt handler for tx4938 based systems
- * Copyright (C) 2000-2001 Toshiba Corporation
- *
- * 2003-2005 (c) MontaVista Software, Inc. This file is licensed under the
- * terms of the GNU General Public License version 2. This program is
- * licensed "as is" without any warranty of any kind, whether express
- * or implied.
- *
- * Support for TX4938 in 2.6 - Manish Lachwani (mlachwani@mvista.com)
- */
-#include <asm/asm.h>
-#include <asm/mipsregs.h>
-#include <asm/addrspace.h>
-#include <asm/regdef.h>
-#include <asm/stackframe.h>
-#include <asm/tx4938/rbtx4938.h>
-
-
-               .align  5
-               NESTED(tx4938_irq_handler, PT_SIZE, sp)
-               SAVE_ALL
-               CLI
-               .set    at
-
-               mfc0    t0, CP0_CAUSE
-               mfc0    t1, CP0_STATUS
-               and     t0, t1
-
-               andi    t1, t0, STATUSF_IP7     /* cpu timer */
-               bnez    t1, ll_ip7
-
-               /* IP6..IP3 multiplexed -- do not use */
-
-               andi    t1, t0, STATUSF_IP2     /* tx4938 pic */
-               bnez    t1, ll_ip2
-
-               andi    t1, t0, STATUSF_IP1     /* user line 1 */
-               bnez    t1, ll_ip1
-
-               andi    t1, t0, STATUSF_IP0     /* user line 0 */
-               bnez    t1, ll_ip0
-
-               .set    reorder
-
-               nop
-               END(tx4938_irq_handler)
-
-               .align  5
-
-
-ll_ip7:
-               li      a0, TX4938_IRQ_CPU_TIMER
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-
-
-ll_ip2:
-               jal     tx4938_irq_nested
-               nop
-               beqz    v0, goto_spurious_interrupt
-               nop
-               move    a0, v0
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-
-goto_spurious_interrupt:
-               j       ret_from_irq
-
-ll_ip1:
-               li      a0, TX4938_IRQ_USER1
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
-
-ll_ip0:
-               li      a0, TX4938_IRQ_USER0
-               move    a1, sp
-               jal     do_IRQ
-               j       ret_from_irq
index a7add16c9aa49f5c5879a6cfb80fbf2059c97ac3..055a2cdfc841f080b5cadb277a46e5155d05a89d 100644 (file)
@@ -4,6 +4,8 @@ config CASIO_E55
        select DMA_NONCOHERENT
        select IRQ_CPU
        select ISA
+       select SYS_HAS_CPU_VR41XX
+       select SYS_SUPPORTS_32BIT_KERNEL
        select SYS_SUPPORTS_LITTLE_ENDIAN
 
 config IBM_WORKPAD
@@ -12,6 +14,8 @@ config IBM_WORKPAD
        select DMA_NONCOHERENT
        select IRQ_CPU
        select ISA
+       select SYS_HAS_CPU_VR41XX
+       select SYS_SUPPORTS_32BIT_KERNEL
        select SYS_SUPPORTS_LITTLE_ENDIAN
 
 config NEC_CMBVR4133
@@ -21,6 +25,9 @@ config NEC_CMBVR4133
        select DMA_NONCOHERENT
        select IRQ_CPU
        select HW_HAS_PCI
+       select SYS_HAS_CPU_VR41XX
+       select SYS_SUPPORTS_32BIT_KERNEL
+       select SYS_SUPPORTS_LITTLE_ENDIAN
 
 config ROCKHOPPER
        bool "Support for Rockhopper baseboard"
@@ -34,6 +41,8 @@ config TANBAC_TB022X
        select DMA_NONCOHERENT
        select HW_HAS_PCI
        select IRQ_CPU
+       select SYS_HAS_CPU_VR41XX
+       select SYS_SUPPORTS_32BIT_KERNEL
        select SYS_SUPPORTS_LITTLE_ENDIAN
        help
          The TANBAC VR4131 multichip module(TB0225) and
@@ -65,6 +74,8 @@ config VICTOR_MPC30X
        select DMA_NONCOHERENT
        select HW_HAS_PCI
        select IRQ_CPU
+       select SYS_HAS_CPU_VR41XX
+       select SYS_SUPPORTS_32BIT_KERNEL
        select SYS_SUPPORTS_LITTLE_ENDIAN
 
 config ZAO_CAPCELLA
@@ -73,6 +84,8 @@ config ZAO_CAPCELLA
        select DMA_NONCOHERENT
        select HW_HAS_PCI
        select IRQ_CPU
+       select SYS_HAS_CPU_VR41XX
+       select SYS_SUPPORTS_32BIT_KERNEL
        select SYS_SUPPORTS_LITTLE_ENDIAN
 
 config PCI_VR41XX
index 9096302a7ecc1e79fed3a3a73f71d67241c07fce..aa373974c80f44111230a81f31c560eed7683632 100644 (file)
@@ -2,7 +2,7 @@
 # Makefile for common code of the NEC VR4100 series.
 #
 
-obj-y                          += bcu.o cmu.o icu.o init.o int-handler.o irq.o pmu.o type.o
+obj-y                          += bcu.o cmu.o icu.o init.o irq.o pmu.o type.o
 obj-$(CONFIG_VRC4173)          += vrc4173.o
 
 EXTRA_AFLAGS := $(CFLAGS)
diff --git a/arch/mips/vr41xx/common/int-handler.S b/arch/mips/vr41xx/common/int-handler.S
deleted file mode 100644 (file)
index 2b6043f..0000000
+++ /dev/null
@@ -1,114 +0,0 @@
-/*
- * FILE NAME
- *     arch/mips/vr41xx/common/int-handler.S
- *
- * BRIEF MODULE DESCRIPTION
- *     Interrupt dispatcher for the NEC VR4100 series.
- *
- * Author: Yoichi Yuasa
- *         yyuasa@mvista.com or source@mvista.com
- *
- * Copyright 2001 MontaVista Software Inc.
- *
- *  This program is free software; you can redistribute it and/or modify it
- *  under the terms of the GNU General Public License as published by the
- *  Free Software Foundation; either version 2 of the License, or (at your
- *  option) any later version.
- *
- *  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 AUTHOR 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.
- *
- *  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.,
- *  675 Mass Ave, Cambridge, MA 02139, USA.
- */
-/*
- * Changes:
- *  MontaVista Software Inc. <yyuasa@mvista.com> or <source@mvista.com>
- *  - New creation, NEC VR4100 series are supported.
- *
- *  Yoichi Yuasa <yoichi_yuasa@tripeaks.co.jp>
- *  - Coped with INTASSIGN of NEC VR4133.
- */
-#include <asm/asm.h>
-#include <asm/regdef.h>
-#include <asm/mipsregs.h>
-#include <asm/stackframe.h>
-
-               .text
-               .set    noreorder
-
-               .align  5
-               NESTED(vr41xx_handle_interrupt, PT_SIZE, ra)
-               .set    noat
-               SAVE_ALL
-               CLI
-               .set    at
-               .set    noreorder
-
-               /*
-                * Get the pending interrupts
-                */
-               mfc0    t0, CP0_CAUSE
-               mfc0    t1, CP0_STATUS
-               andi    t0, 0xff00
-               and     t0, t0, t1
-
-               andi    t1, t0, CAUSEF_IP7      # MIPS timer interrupt
-               bnez    t1, handle_irq
-               li      a0, 7
-
-               andi    t1, t0, 0x7800          # check for Int1-4
-               beqz    t1, 1f
-
-               andi    t1, t0, CAUSEF_IP3      # check for Int1
-               bnez    t1, handle_int
-               li      a0, 3
-
-               andi    t1, t0, CAUSEF_IP4      # check for Int2
-               bnez    t1, handle_int
-               li      a0, 4
-
-               andi    t1, t0, CAUSEF_IP5      # check for Int3
-               bnez    t1, handle_int
-               li      a0, 5
-
-               andi    t1, t0, CAUSEF_IP6      # check for Int4
-               bnez    t1, handle_int
-               li      a0, 6
-
-1:
-               andi    t1, t0, CAUSEF_IP2      # check for Int0
-               bnez    t1, handle_int
-               li      a0, 2
-
-               andi    t1, t0, CAUSEF_IP0      # check for IP0
-               bnez    t1, handle_irq
-               li      a0, 0
-
-               andi    t1, t0, CAUSEF_IP1      # check for IP1
-               bnez    t1, handle_irq
-               li      a0, 1
-
-               j       spurious_interrupt
-               nop
-
-handle_int:
-               jal     irq_dispatch
-               move    a1, sp
-               j       ret_from_irq
-               nop
-
-handle_irq:
-               jal     do_IRQ
-               move    a1, sp
-               j       ret_from_irq
-               END(vr41xx_handle_interrupt)
index 61aa264275ff2883d0f1fbec5871645a307a5287..86796bb63c3c7e3d6b3aaa41626a52a43b8eca35 100644 (file)
@@ -59,7 +59,7 @@ int cascade_irq(unsigned int irq, int (*get_irq)(unsigned int, struct pt_regs *)
 
 EXPORT_SYMBOL_GPL(cascade_irq);
 
-asmlinkage void irq_dispatch(unsigned int irq, struct pt_regs *regs)
+static void irq_dispatch(unsigned int irq, struct pt_regs *regs)
 {
        irq_cascade_t *cascade;
        irq_desc_t *desc;
@@ -84,11 +84,32 @@ asmlinkage void irq_dispatch(unsigned int irq, struct pt_regs *regs)
                do_IRQ(irq, regs);
 }
 
-extern asmlinkage void vr41xx_handle_interrupt(void);
+asmlinkage void plat_irq_dispatch(struct pt_regs *regs)
+{
+       unsigned int pending = read_c0_cause() & read_c0_status() & ST0_IM;
+
+       if (pending & CAUSEF_IP7)
+               do_IRQ(7, regs);
+       else if (pending & 0x7800) {
+               if (pending & CAUSEF_IP3)
+                       irq_dispatch(3, regs);
+               else if (pending & CAUSEF_IP4)
+                       irq_dispatch(4, regs);
+               else if (pending & CAUSEF_IP5)
+                       irq_dispatch(5, regs);
+               else if (pending & CAUSEF_IP6)
+                       irq_dispatch(6, regs);
+       } else if (pending & CAUSEF_IP2)
+               irq_dispatch(2, regs);
+       else if (pending & CAUSEF_IP0)
+               do_IRQ(0, regs);
+       else if (pending & CAUSEF_IP1)
+               do_IRQ(1, regs);
+       else
+               spurious_interrupt(regs);
+}
 
 void __init arch_init_irq(void)
 {
        mips_cpu_irq_init(MIPS_CPU_IRQ_BASE);
-
-       set_except_vector(0, vr41xx_handle_interrupt);
 }
index 2fdf21989dc20a88d0d288bdf190dd3837bf8aaf..19f911c5dd58dce00114fc4ed397c7445952a6f8 100644 (file)
@@ -177,6 +177,11 @@ config ARCH_DISCONTIGMEM_DEFAULT
        def_bool y
        depends on ARCH_DISCONTIGMEM_ENABLE
 
+config NODES_SHIFT
+       int
+       default "3"
+       depends on NEED_MULTIPLE_NODES
+
 source "kernel/Kconfig.preempt"
 source "kernel/Kconfig.hz"
 source "mm/Kconfig"
index 47ca5c0a323b4542d120487c81198f6667fcd961..fc107add627cce2608d2699c2e608e8f72205c67 100644 (file)
@@ -31,7 +31,6 @@
 
 #include <linux/string.h>
 EXPORT_SYMBOL(memset);
-EXPORT_SYMBOL(strpbrk);
 
 #include <asm/atomic.h>
 EXPORT_SYMBOL(__xchg8);
index 2cdc35ce80451c5e503e97904cd763474d63b752..6729c98b66f969fb16566bcc949039c776370a24 100644 (file)
@@ -366,6 +366,7 @@ config PPC_PMAC64
        select U3_DART
        select MPIC_BROKEN_U3
        select GENERIC_TBSYNC
+       select PPC_970_NAP
        default y
 
 config PPC_PREP
@@ -383,6 +384,7 @@ config PPC_MAPLE
        select MPIC_BROKEN_U3
        select GENERIC_TBSYNC
        select PPC_UDBG_16550
+       select PPC_970_NAP
        default n
        help
           This option enables support for the Maple 970FX Evaluation Board.
@@ -457,6 +459,10 @@ config PPC_MPC106
        bool
        default n
 
+config PPC_970_NAP
+       bool
+       default n
+
 source "drivers/cpufreq/Kconfig"
 
 config CPU_FREQ_PMAC
@@ -649,6 +655,11 @@ config NUMA
        depends on PPC64
        default y if SMP && PPC_PSERIES
 
+config NODES_SHIFT
+       int
+       default "4"
+       depends on NEED_MULTIPLE_NODES
+
 config ARCH_SELECT_MEMORY_MODEL
        def_bool y
        depends on PPC64
index 6ec84d37a3378dbaa321fe217091eb149a01b58c..ed5b26aa8be36e914967c6b5e3530d639ed6b861 100644 (file)
@@ -104,6 +104,10 @@ ifndef CONFIG_FSL_BOOKE
 CFLAGS         += -mstring
 endif
 
+ifeq ($(CONFIG_6xx),y)
+CFLAGS         += -mcpu=powerpc
+endif
+
 cpu-as-$(CONFIG_PPC64BRIDGE)   += -Wa,-mppc64bridge
 cpu-as-$(CONFIG_4xx)           += -Wa,-m405
 cpu-as-$(CONFIG_6xx)           += -Wa,-maltivec
index 0cc0995b81b07ec355413ba07ce8bfff08c58b98..803858e8616031054c62fbb04021e0d6a3f13052 100644 (file)
@@ -20,7 +20,7 @@ obj-$(CONFIG_PPC64)           += setup_64.o binfmt_elf32.o sys_ppc32.o \
                                   firmware.o sysfs.o
 obj-$(CONFIG_PPC64)            += vdso64/
 obj-$(CONFIG_ALTIVEC)          += vecemu.o vector.o
-obj-$(CONFIG_POWER4)           += idle_power4.o
+obj-$(CONFIG_PPC_970_NAP)      += idle_power4.o
 obj-$(CONFIG_PPC_OF)           += of_device.o prom_parse.o
 procfs-$(CONFIG_PPC64)         := proc_ppc64.o
 obj-$(CONFIG_PROC_FS)          += $(procfs-y)
index 54b48f3300515eb082eed331267e0373ca575507..8f85c5e8a55a438e927d6ca729e67066199f63c4 100644 (file)
@@ -91,6 +91,7 @@ int main(void)
 #endif /* CONFIG_PPC64 */
 
        DEFINE(TI_FLAGS, offsetof(struct thread_info, flags));
+       DEFINE(TI_LOCAL_FLAGS, offsetof(struct thread_info, local_flags));
        DEFINE(TI_PREEMPT, offsetof(struct thread_info, preempt_count));
        DEFINE(TI_TASK, offsetof(struct thread_info, task));
 #ifdef CONFIG_PPC32
index b3a9794672250c4ba98c3710e4bef8b691a6a82e..8866fd26c6b97048dfb3c8142c95dcf4c43c3bcc 100644 (file)
@@ -128,37 +128,36 @@ transfer_to_handler:
        stw     r12,4(r11)
 #endif
        b       3f
+
 2:     /* if from kernel, check interrupted DOZE/NAP mode and
          * check for stack overflow
          */
+       lwz     r9,THREAD_INFO-THREAD(r12)
+       cmplw   r1,r9                   /* if r1 <= current->thread_info */
+       ble-    stack_ovf               /* then the kernel stack overflowed */
+5:
 #ifdef CONFIG_6xx
-       mfspr   r11,SPRN_HID0
-       mtcr    r11
-BEGIN_FTR_SECTION
-       bt-     8,4f                    /* Check DOZE */
-END_FTR_SECTION_IFSET(CPU_FTR_CAN_DOZE)
-BEGIN_FTR_SECTION
-       bt-     9,4f                    /* Check NAP */
-END_FTR_SECTION_IFSET(CPU_FTR_CAN_NAP)
+       tophys(r9,r9)                   /* check local flags */
+       lwz     r12,TI_LOCAL_FLAGS(r9)
+       mtcrf   0x01,r12
+       bt-     31-TLF_NAPPING,4f
 #endif /* CONFIG_6xx */
        .globl transfer_to_handler_cont
 transfer_to_handler_cont:
-       lwz     r11,THREAD_INFO-THREAD(r12)
-       cmplw   r1,r11                  /* if r1 <= current->thread_info */
-       ble-    stack_ovf               /* then the kernel stack overflowed */
 3:
        mflr    r9
        lwz     r11,0(r9)               /* virtual address of handler */
        lwz     r9,4(r9)                /* where to go when done */
-       FIX_SRR1(r10,r12)
        mtspr   SPRN_SRR0,r11
        mtspr   SPRN_SRR1,r10
        mtlr    r9
        SYNC
        RFI                             /* jump to handler, enable MMU */
 
-#ifdef CONFIG_6xx      
-4:     b       power_save_6xx_restore
+#ifdef CONFIG_6xx
+4:     rlwinm  r12,r12,0,~_TLF_NAPPING
+       stw     r12,TI_LOCAL_FLAGS(r9)
+       b       power_save_6xx_restore
 #endif
 
 /*
@@ -167,10 +166,10 @@ transfer_to_handler_cont:
  */
 stack_ovf:
        /* sometimes we use a statically-allocated stack, which is OK. */
-       lis     r11,_end@h
-       ori     r11,r11,_end@l
-       cmplw   r1,r11
-       ble     3b                      /* r1 <= &_end is OK */
+       lis     r12,_end@h
+       ori     r12,r12,_end@l
+       cmplw   r1,r12
+       ble     5b                      /* r1 <= &_end is OK */
        SAVE_NVGPRS(r11)
        addi    r3,r1,STACK_FRAME_OVERHEAD
        lis     r1,init_thread_union@ha
index a5ae04a57c784371c57b1a1e0dcaa6ab20fdac7d..b7d140430a41e4a4fc625161ad417211984a5570 100644 (file)
@@ -376,17 +376,53 @@ label##_common:                                           \
        bl      hdlr;                                   \
        b       .ret_from_except
 
+/*
+ * Like STD_EXCEPTION_COMMON, but for exceptions that can occur
+ * in the idle task and therefore need the special idle handling.
+ */
+#define STD_EXCEPTION_COMMON_IDLE(trap, label, hdlr)   \
+       .align  7;                                      \
+       .globl label##_common;                          \
+label##_common:                                                \
+       EXCEPTION_PROLOG_COMMON(trap, PACA_EXGEN);      \
+       FINISH_NAP;                                     \
+       DISABLE_INTS;                                   \
+       bl      .save_nvgprs;                           \
+       addi    r3,r1,STACK_FRAME_OVERHEAD;             \
+       bl      hdlr;                                   \
+       b       .ret_from_except
+
 #define STD_EXCEPTION_COMMON_LITE(trap, label, hdlr)   \
        .align  7;                                      \
        .globl label##_common;                          \
 label##_common:                                                \
        EXCEPTION_PROLOG_COMMON(trap, PACA_EXGEN);      \
+       FINISH_NAP;                                     \
        DISABLE_INTS;                                   \
        bl      .ppc64_runlatch_on;                     \
        addi    r3,r1,STACK_FRAME_OVERHEAD;             \
        bl      hdlr;                                   \
        b       .ret_from_except_lite
 
+/*
+ * When the idle code in power4_idle puts the CPU into NAP mode,
+ * it has to do so in a loop, and relies on the external interrupt
+ * and decrementer interrupt entry code to get it out of the loop.
+ * It sets the _TLF_NAPPING bit in current_thread_info()->local_flags
+ * to signal that it is in the loop and needs help to get out.
+ */
+#ifdef CONFIG_PPC_970_NAP
+#define FINISH_NAP                             \
+BEGIN_FTR_SECTION                              \
+       clrrdi  r11,r1,THREAD_SHIFT;            \
+       ld      r9,TI_LOCAL_FLAGS(r11);         \
+       andi.   r10,r9,_TLF_NAPPING;            \
+       bnel    power4_fixup_nap;               \
+END_FTR_SECTION_IFSET(CPU_FTR_CAN_NAP)
+#else
+#define FINISH_NAP
+#endif
+
 /*
  * Start of pSeries system interrupt routines
  */
@@ -772,6 +808,7 @@ hardware_interrupt_iSeries_masked:
        .globl machine_check_common
 machine_check_common:
        EXCEPTION_PROLOG_COMMON(0x200, PACA_EXMC)
+       FINISH_NAP
        DISABLE_INTS
        bl      .save_nvgprs
        addi    r3,r1,STACK_FRAME_OVERHEAD
@@ -783,7 +820,7 @@ machine_check_common:
        STD_EXCEPTION_COMMON(0xb00, trap_0b, .unknown_exception)
        STD_EXCEPTION_COMMON(0xd00, single_step, .single_step_exception)
        STD_EXCEPTION_COMMON(0xe00, trap_0e, .unknown_exception)
-       STD_EXCEPTION_COMMON(0xf00, performance_monitor, .performance_monitor_exception)
+       STD_EXCEPTION_COMMON_IDLE(0xf00, performance_monitor, .performance_monitor_exception)
        STD_EXCEPTION_COMMON(0x1300, instruction_breakpoint, .instruction_breakpoint_exception)
 #ifdef CONFIG_ALTIVEC
        STD_EXCEPTION_COMMON(0x1700, altivec_assist, .altivec_assist_exception)
@@ -1034,6 +1071,7 @@ unrecov_slb:
        .globl hardware_interrupt_entry
 hardware_interrupt_common:
        EXCEPTION_PROLOG_COMMON(0x500, PACA_EXGEN)
+       FINISH_NAP
 hardware_interrupt_entry:
        DISABLE_INTS
        bl      .ppc64_runlatch_on
@@ -1041,6 +1079,15 @@ hardware_interrupt_entry:
        bl      .do_IRQ
        b       .ret_from_except_lite
 
+#ifdef CONFIG_PPC_970_NAP
+power4_fixup_nap:
+       andc    r9,r9,r10
+       std     r9,TI_LOCAL_FLAGS(r11)
+       ld      r10,_LINK(r1)           /* make idle task do the */
+       std     r10,_NIP(r1)            /* equivalent of a blr */
+       blr
+#endif
+
        .align  7
        .globl alignment_common
 alignment_common:
index e9f321d74d85293323714af7b2bffa950e8760e6..d491052c8e0c5d3ab8c5ee1cfb70d7c1a93d45c5 100644 (file)
@@ -50,9 +50,9 @@ void cpu_idle(void)
 
        set_thread_flag(TIF_POLLING_NRFLAG);
        while (1) {
-               ppc64_runlatch_off();
-
                while (!need_resched() && !cpu_should_die()) {
+                       ppc64_runlatch_off();
+
                        if (ppc_md.power_save) {
                                clear_thread_flag(TIF_POLLING_NRFLAG);
                                /*
index 12a4efbaa08f41a684bfe00cd5ab410037548288..b45fa0e37212526614c88f5e384a5f5d7a59e1c6 100644 (file)
@@ -22,8 +22,6 @@
 #include <asm/ppc_asm.h>
 #include <asm/asm-offsets.h>
 
-#undef DEBUG
-
        .text
 
 /*
@@ -109,12 +107,6 @@ BEGIN_FTR_SECTION
        dcbf    0,r4
        dcbf    0,r4
 END_FTR_SECTION_IFSET(CPU_FTR_NAP_DISABLE_L2_PR)
-#ifdef DEBUG
-       lis     r6,nap_enter_count@ha
-       lwz     r4,nap_enter_count@l(r6)
-       addi    r4,r4,1
-       stw     r4,nap_enter_count@l(r6)
-#endif 
 2:
 BEGIN_FTR_SECTION
        /* Go to low speed mode on some 750FX */
@@ -144,48 +136,42 @@ BEGIN_FTR_SECTION
        DSSALL
        sync
 END_FTR_SECTION_IFSET(CPU_FTR_ALTIVEC)
+       rlwinm  r9,r1,0,0,31-THREAD_SHIFT       /* current thread_info */
+       lwz     r8,TI_LOCAL_FLAGS(r9)   /* set napping bit */
+       ori     r8,r8,_TLF_NAPPING      /* so when we take an exception */
+       stw     r8,TI_LOCAL_FLAGS(r9)   /* it will return to our caller */
        mfmsr   r7
        ori     r7,r7,MSR_EE
        oris    r7,r7,MSR_POW@h
-       sync
-       isync
+1:     sync
        mtmsr   r7
        isync
-       sync
-       blr
-       
+       b       1b
+
 /*
  * Return from NAP/DOZE mode, restore some CPU specific registers,
  * we are called with DR/IR still off and r2 containing physical
- * address of current.
+ * address of current.  R11 points to the exception frame (physical
+ * address).  We have to preserve r10.
  */
 _GLOBAL(power_save_6xx_restore)
-       mfspr   r11,SPRN_HID0
-       rlwinm. r11,r11,0,10,8  /* Clear NAP & copy NAP bit !state to cr1 EQ */
-       cror    4*cr1+eq,4*cr0+eq,4*cr0+eq
-BEGIN_FTR_SECTION
-       rlwinm  r11,r11,0,9,7   /* Clear DOZE */
-END_FTR_SECTION_IFSET(CPU_FTR_CAN_DOZE)
-       mtspr   SPRN_HID0, r11
+       lwz     r9,_LINK(r11)           /* interrupted in ppc6xx_idle: */
+       stw     r9,_NIP(r11)            /* make it do a blr */
 
-#ifdef DEBUG
-       beq     cr1,1f
-       lis     r11,(nap_return_count-KERNELBASE)@ha
-       lwz     r9,nap_return_count@l(r11)
-       addi    r9,r9,1
-       stw     r9,nap_return_count@l(r11)
-1:
-#endif
-       
-       rlwinm  r9,r1,0,0,18
-       tophys(r9,r9)
-       lwz     r11,TI_CPU(r9)
+#ifdef CONFIG_SMP
+       mfspr   r12,SPRN_SPRG3
+       lwz     r11,TI_CPU(r12)         /* get cpu number * 4 */
        slwi    r11,r11,2
+#else
+       li      r11,0
+#endif
        /* Todo make sure all these are in the same page
-        * and load r22 (@ha part + CPU offset) only once
+        * and load r11 (@ha part + CPU offset) only once
         */
 BEGIN_FTR_SECTION
-       beq     cr1,1f
+       mfspr   r9,SPRN_HID0
+       andis.  r9,r9,HID0_NAP@h
+       beq     1f
        addis   r9,r11,(nap_save_msscr0-KERNELBASE)@ha
        lwz     r9,nap_save_msscr0@l(r9)
        mtspr   SPRN_MSSCR0, r9
@@ -210,10 +196,3 @@ _GLOBAL(nap_save_hid1)
 
 _GLOBAL(powersave_lowspeed)
        .long   0
-
-#ifdef DEBUG
-_GLOBAL(nap_enter_count)
-       .space  4
-_GLOBAL(nap_return_count)
-       .space  4
-#endif
index 6dad1c02496e723ee794f582216ea3077bf8f882..d85c7c938eed37f075c4eca9c95c0510b739d1aa 100644 (file)
@@ -35,12 +35,16 @@ BEGIN_FTR_SECTION
        DSSALL
        sync
 END_FTR_SECTION_IFSET(CPU_FTR_ALTIVEC)
+       clrrdi  r9,r1,THREAD_SHIFT      /* current thread_info */
+       ld      r8,TI_LOCAL_FLAGS(r9)   /* set napping bit */
+       ori     r8,r8,_TLF_NAPPING      /* so when we take an exception */
+       std     r8,TI_LOCAL_FLAGS(r9)   /* it will return to our caller */
        mfmsr   r7
        ori     r7,r7,MSR_EE
        oris    r7,r7,MSR_POW@h
-       sync
+1:     sync
        isync
        mtmsrd  r7
        isync
-       sync
-       blr
+       b       1b
+
index bb5c9501234c8364c855cf11d7e363983603ef61..57d560c68897b08bcd85003eaefbf1c4442ad0ac 100644 (file)
@@ -272,18 +272,26 @@ unsigned int virt_irq_to_real_map[NR_IRQS];
  * Don't use virtual irqs 0, 1, 2 for devices.
  * The pcnet32 driver considers interrupt numbers < 2 to be invalid,
  * and 2 is the XICS IPI interrupt.
- * We limit virtual irqs to 17 less than NR_IRQS so that when we
- * offset them by 16 (to reserve the first 16 for ISA interrupts)
- * we don't end up with an interrupt number >= NR_IRQS.
+ * We limit virtual irqs to __irq_offet_value less than virt_irq_max so
+ * that when we offset them we don't end up with an interrupt
+ * number >= virt_irq_max.
  */
 #define MIN_VIRT_IRQ   3
-#define MAX_VIRT_IRQ   (NR_IRQS - NUM_ISA_INTERRUPTS - 1)
-#define NR_VIRT_IRQS   (MAX_VIRT_IRQ - MIN_VIRT_IRQ + 1)
+
+unsigned int virt_irq_max;
+static unsigned int max_virt_irq;
+static unsigned int nr_virt_irqs;
 
 void
 virt_irq_init(void)
 {
        int i;
+
+       if ((virt_irq_max == 0) || (virt_irq_max > (NR_IRQS - 1)))
+               virt_irq_max = NR_IRQS - 1;
+       max_virt_irq = virt_irq_max - __irq_offset_value;
+       nr_virt_irqs = max_virt_irq - MIN_VIRT_IRQ + 1;
+
        for (i = 0; i < NR_IRQS; i++)
                virt_irq_to_real_map[i] = UNDEFINED_IRQ;
 }
@@ -308,17 +316,17 @@ int virt_irq_create_mapping(unsigned int real_irq)
                return real_irq;
        }
 
-       /* map to a number between MIN_VIRT_IRQ and MAX_VIRT_IRQ */
+       /* map to a number between MIN_VIRT_IRQ and max_virt_irq */
        virq = real_irq;
-       if (virq > MAX_VIRT_IRQ)
-               virq = (virq % NR_VIRT_IRQS) + MIN_VIRT_IRQ;
+       if (virq > max_virt_irq)
+               virq = (virq % nr_virt_irqs) + MIN_VIRT_IRQ;
 
        /* search for this number or a free slot */
        first_virq = virq;
        while (virt_irq_to_real_map[virq] != UNDEFINED_IRQ) {
                if (virt_irq_to_real_map[virq] == real_irq)
                        return virq;
-               if (++virq > MAX_VIRT_IRQ)
+               if (++virq > max_virt_irq)
                        virq = MIN_VIRT_IRQ;
                if (virq == first_virq)
                        goto nospace;   /* oops, no free slots */
@@ -330,8 +338,8 @@ int virt_irq_create_mapping(unsigned int real_irq)
  nospace:
        if (!warned) {
                printk(KERN_CRIT "Interrupt table is full\n");
-               printk(KERN_CRIT "Increase NR_IRQS (currently %d) "
-                      "in your kernel sources and rebuild.\n", NR_IRQS);
+               printk(KERN_CRIT "Increase virt_irq_max (currently %d) "
+                      "in your kernel sources and rebuild.\n", virt_irq_max);
                warned = 1;
        }
        return NO_IRQ;
@@ -349,8 +357,8 @@ unsigned int real_irq_to_virt_slowpath(unsigned int real_irq)
 
        virq = real_irq;
 
-       if (virq > MAX_VIRT_IRQ)
-               virq = (virq % NR_VIRT_IRQS) + MIN_VIRT_IRQ;
+       if (virq > max_virt_irq)
+               virq = (virq % nr_virt_irqs) + MIN_VIRT_IRQ;
 
        first_virq = virq;
 
@@ -360,7 +368,7 @@ unsigned int real_irq_to_virt_slowpath(unsigned int real_irq)
 
                virq++;
 
-               if (virq >= MAX_VIRT_IRQ)
+               if (virq >= max_virt_irq)
                        virq = 0;
 
        } while (first_virq != virq);
index ad7a90212204ee68eea83075b51fbadf5a62ef4b..856ef1a832b9466031309cd9b20f4dda31242396 100644 (file)
@@ -88,7 +88,7 @@ void __kprobes arch_remove_kprobe(struct kprobe *p)
        mutex_unlock(&kprobe_mutex);
 }
 
-static inline void prepare_singlestep(struct kprobe *p, struct pt_regs *regs)
+static void __kprobes prepare_singlestep(struct kprobe *p, struct pt_regs *regs)
 {
        kprobe_opcode_t insn = *p->ainsn.insn;
 
@@ -101,21 +101,21 @@ static inline void prepare_singlestep(struct kprobe *p, struct pt_regs *regs)
                regs->nip = (unsigned long)p->ainsn.insn;
 }
 
-static inline void save_previous_kprobe(struct kprobe_ctlblk *kcb)
+static void __kprobes save_previous_kprobe(struct kprobe_ctlblk *kcb)
 {
        kcb->prev_kprobe.kp = kprobe_running();
        kcb->prev_kprobe.status = kcb->kprobe_status;
        kcb->prev_kprobe.saved_msr = kcb->kprobe_saved_msr;
 }
 
-static inline void restore_previous_kprobe(struct kprobe_ctlblk *kcb)
+static void __kprobes restore_previous_kprobe(struct kprobe_ctlblk *kcb)
 {
        __get_cpu_var(current_kprobe) = kcb->prev_kprobe.kp;
        kcb->kprobe_status = kcb->prev_kprobe.status;
        kcb->kprobe_saved_msr = kcb->prev_kprobe.saved_msr;
 }
 
-static inline void set_current_kprobe(struct kprobe *p, struct pt_regs *regs,
+static void __kprobes set_current_kprobe(struct kprobe *p, struct pt_regs *regs,
                                struct kprobe_ctlblk *kcb)
 {
        __get_cpu_var(current_kprobe) = p;
@@ -141,7 +141,7 @@ void __kprobes arch_prepare_kretprobe(struct kretprobe *rp,
        }
 }
 
-static inline int kprobe_handler(struct pt_regs *regs)
+static int __kprobes kprobe_handler(struct pt_regs *regs)
 {
        struct kprobe *p;
        int ret = 0;
@@ -334,7 +334,7 @@ static void __kprobes resume_execution(struct kprobe *p, struct pt_regs *regs)
                regs->nip = (unsigned long)p->addr + 4;
 }
 
-static inline int post_kprobe_handler(struct pt_regs *regs)
+static int __kprobes post_kprobe_handler(struct pt_regs *regs)
 {
        struct kprobe *cur = kprobe_running();
        struct kprobe_ctlblk *kcb = get_kprobe_ctlblk();
@@ -370,7 +370,7 @@ out:
        return 1;
 }
 
-static inline int kprobe_fault_handler(struct pt_regs *regs, int trapnr)
+static int __kprobes kprobe_fault_handler(struct pt_regs *regs, int trapnr)
 {
        struct kprobe *cur = kprobe_running();
        struct kprobe_ctlblk *kcb = get_kprobe_ctlblk();
index d66c5e77fcff35c9c5eb921339bd016b0c9c9978..7e4d54821a079411499dd2958f26bec980b1300b 100644 (file)
@@ -1528,12 +1528,11 @@ static int __init prom_find_machine_type(void)
         *    non-IBM designs !
         *  - it has /rtas
         */
-       len = prom_getprop(_prom->root, "model",
+       len = prom_getprop(_prom->root, "device_type",
                           compat, sizeof(compat)-1);
        if (len <= 0)
                return PLATFORM_GENERIC;
-       compat[len] = 0;
-       if (strcmp(compat, "chrp"))
+       if (strncmp(compat, RELOC("chrp"), 4))
                return PLATFORM_GENERIC;
 
        /* Default to pSeries. We need to know if we are running LPAR */
index 456286cf1d143cd8f6ca3ee9bf12af459620c1ce..9c9ad1fa9cce90748c7362d5dea5d744cdd84f08 100644 (file)
@@ -258,11 +258,11 @@ static int __init proc_rtas_init(void)
        struct proc_dir_entry *entry;
 
        if (!machine_is(pseries))
-               return 1;
+               return -ENODEV;
 
        rtas_node = of_find_node_by_name(NULL, "rtas");
        if (rtas_node == NULL)
-               return 1;
+               return -ENODEV;
 
        entry = create_proc_entry("ppc64/rtas/progress", S_IRUGO|S_IWUSR, NULL);
        if (entry)
index 1424eab450ee915322478f21ab00cefb5fd8a04b..a14c964038403fa6d6271967df95fa5727a41b1f 100644 (file)
@@ -323,3 +323,4 @@ COMPAT_SYS(pselect6)
 COMPAT_SYS(ppoll)
 SYSCALL(unshare)
 SYSCALL(splice)
+SYSCALL(tee)
index 97898d5d34e5c0539d942d4a7373c73eb6c3ff04..1726bfe38ee08f5dcd1aa3a198f43c7e086a2129 100644 (file)
@@ -1297,7 +1297,7 @@ static inline void setup_decr(struct spu_state *csa, struct spu *spu)
                cycles_t resume_time = get_cycles();
                cycles_t delta_time = resume_time - csa->suspend_time;
 
-               csa->lscsa->decr.slot[0] = delta_time;
+               csa->lscsa->decr.slot[0] -= delta_time;
        }
 }
 
index 63f0aee4c158e97df652e49b43d00551aaa21e03..996c28744e96a6d206a5f778dd562b5f30b3cf44 100644 (file)
@@ -9,3 +9,4 @@ extern long chrp_time_init(void);
 
 extern void chrp_find_bridges(void);
 extern void chrp_event_scan(unsigned long);
+extern void chrp_pcibios_fixup(void);
index 8ef279ad36ad15ddbd5500835b1580fb04134955..ac224876ce5943f999a0def0007f7214cd35ff9a 100644 (file)
@@ -23,6 +23,8 @@
 #include <asm/grackle.h>
 #include <asm/rtas.h>
 
+#include "chrp.h"
+
 /* LongTrail */
 void __iomem *gg2_pci_config_base;
 
@@ -314,6 +316,6 @@ chrp_find_bridges(void)
        }
 
        /* Do not fixup interrupts from OF tree on pegasos */
-       if (is_pegasos == 0)
-               ppc_md.pcibios_fixup = chrp_pcibios_fixup;
+       if (is_pegasos)
+               ppc_md.pcibios_fixup = NULL;
 }
index 23a2017187049d721dcac2f3b49efe82b1f221f1..18d89f38796b458d9953b93672893c528b537acf 100644 (file)
@@ -440,8 +440,6 @@ void __init chrp_init_IRQ(void)
 
        if (_chrp_type == _CHRP_Pegasos)
                ppc_md.get_irq        = i8259_irq;
-       else
-               ppc_md.get_irq        = mpic_get_irq;
 
 #if defined(CONFIG_VT) && defined(CONFIG_INPUT_ADBHID) && defined(XMON)
        /* see if there is a keyboard in the device tree
@@ -528,26 +526,24 @@ static int __init chrp_probe(void)
        /* Assume we have an 8259... */
        __irq_offset_value = NUM_ISA_INTERRUPTS;
 
-       ppc_md.setup_arch     = chrp_setup_arch;
-       ppc_md.show_cpuinfo   = chrp_show_cpuinfo;
-
-       ppc_md.init_IRQ       = chrp_init_IRQ;
-       ppc_md.init           = chrp_init2;
-
-       ppc_md.phys_mem_access_prot = pci_phys_mem_access_prot;
-
-       ppc_md.restart        = rtas_restart;
-       ppc_md.power_off      = rtas_power_off;
-       ppc_md.halt           = rtas_halt;
-
-       ppc_md.time_init      = chrp_time_init;
-       ppc_md.calibrate_decr = generic_calibrate_decr;
-
-       /* this may get overridden with rtas routines later... */
-       ppc_md.set_rtc_time   = chrp_set_rtc_time;
-       ppc_md.get_rtc_time   = chrp_get_rtc_time;
-
-#ifdef CONFIG_SMP
-       smp_ops = &chrp_smp_ops;
-#endif /* CONFIG_SMP */
+       return 1;
 }
+
+define_machine(chrp) {
+       .name                   = "CHRP",
+       .probe                  = chrp_probe,
+       .setup_arch             = chrp_setup_arch,
+       .init                   = chrp_init2,
+       .show_cpuinfo           = chrp_show_cpuinfo,
+       .init_IRQ               = chrp_init_IRQ,
+       .get_irq                = mpic_get_irq,
+       .pcibios_fixup          = chrp_pcibios_fixup,
+       .restart                = rtas_restart,
+       .power_off              = rtas_power_off,
+       .halt                   = rtas_halt,
+       .time_init              = chrp_time_init,
+       .set_rtc_time           = chrp_set_rtc_time,
+       .get_rtc_time           = chrp_get_rtc_time,
+       .calibrate_decr         = generic_calibrate_decr,
+       .phys_mem_access_prot   = pci_phys_mem_access_prot,
+};
index 6ce8a404ba6b2b9cd8f5ccbccbb1888b441df1ba..a6fd9bedb0741b533fc207650a128ef1c35070ec 100644 (file)
@@ -54,6 +54,7 @@
 #include <asm/iseries/hv_lp_event.h>
 #include <asm/iseries/lpar_map.h>
 #include <asm/udbg.h>
+#include <asm/irq.h>
 
 #include "naca.h"
 #include "setup.h"
@@ -684,6 +685,12 @@ static int __init iseries_probe(void)
        powerpc_firmware_features |= FW_FEATURE_ISERIES;
        powerpc_firmware_features |= FW_FEATURE_LPAR;
 
+       /*
+        * The Hypervisor only allows us up to 256 interrupt
+        * sources (the irq number is passed in a u8).
+        */
+       virt_irq_max = 255;
+
        return 1;
 }
 
index 780fb27a0099e24ca66b3fee2fbb9a5f7a258f1b..32eaddfa5470a635741228ada3365e4b9f20b5de 100644 (file)
@@ -957,8 +957,10 @@ static void eeh_remove_device(struct pci_dev *dev)
        pci_addr_cache_remove_device(dev);
 
        dn = pci_device_to_OF_node(dev);
-       PCI_DN(dn)->pcidev = NULL;
-       pci_dev_put (dev);
+       if (PCI_DN(dn)->pcidev) {
+               PCI_DN(dn)->pcidev = NULL;
+               pci_dev_put (dev);
+       }
 }
 
 void eeh_remove_bus_device(struct pci_dev *dev)
index fcc4d561a23653a659775efd27f9f8c4ccd75d4b..e0000ce769e51831db5df3fe82f25d57384c1e16 100644 (file)
@@ -488,7 +488,7 @@ static int __init rtas_init(void)
        /* No RTAS */
        if (rtas_token("event-scan") == RTAS_UNKNOWN_SERVICE) {
                printk(KERN_INFO "rtasd: no event-scan on system\n");
-               return 1;
+               return -ENODEV;
        }
 
        entry = create_proc_entry("ppc64/rtas/error_log", S_IRUSR, NULL);
index d4077e69086f8b29a8ac1279e2ebce97d48fb665..80c84d562fa4ac173b595cd22cdd4d2e02540f2c 100644 (file)
@@ -3,7 +3,7 @@
 #
 
 CFLAGS_kbd.o   := -Idrivers/char
-CFLAGS_vreset.o := -I$(srctree)/arch/ppc/boot/include
+CFLAGS_vreset.o := -Iarch/ppc/boot/include
 
 zlib  := infblock.c infcodes.c inffast.c inflate.c inftrees.c infutil.c
         
index 60c724e1158499e6c136542447c96f9a13ddce96..7662c4e6e7d6070786ce144cb97ea20e6d4bd3a9 100644 (file)
@@ -156,12 +156,13 @@ void platform_notify_map(const struct platform_notify_dev_map *map,
        while (map->bus_id != NULL) {
                idx = -1;
                s = strrchr(dev->bus_id, '.');
-               if (s != NULL)
+               if (s != NULL) {
                        idx = (int)simple_strtol(s + 1, NULL, 10);
-               else
+                       len = s - dev->bus_id;
+               } else {
                        s = dev->bus_id;
-
-               len = s - dev->bus_id;
+                       len = strlen(dev->bus_id);
+               }
 
                if (!strncmp(dev->bus_id, map->bus_id, len)) {
                        pdev = container_of(dev, struct platform_device, dev);
index 6c6b197898d0b61c0529636c318f24a57b41756e..7bb16fb97d4fbdb235ca54da0c0eba58f0192111 100644 (file)
@@ -67,7 +67,6 @@ cflags-$(CONFIG_WARN_STACK) += -mwarn-framesize=$(CONFIG_WARN_STACK_SIZE)
 endif
 
 CFLAGS         += -mbackchain -msoft-float $(cflags-y)
-CFLAGS         += $(call cc-option,-finline-limit=10000)
 CFLAGS                 += -pipe -fno-strength-reduce -Wno-sign-compare 
 AFLAGS         += $(aflags-y)
 
index f8d0cd540a06bb734f37272ef3a883e0f34ecb4f..f4dfc10026d2411fb8ec0a301360fb50b1dbf5f9 100644 (file)
@@ -1,10 +1,11 @@
 #
 # Automatically generated make config: don't edit
-# Linux kernel version: 2.6.16-rc2
-# Wed Feb  8 10:44:39 2006
+# Linux kernel version: 2.6.17-rc1
+# Mon Apr  3 14:34:15 2006
 #
 CONFIG_MMU=y
 CONFIG_RWSEM_XCHGADD_ALGORITHM=y
+CONFIG_GENERIC_HWEIGHT=y
 CONFIG_GENERIC_CALIBRATE_DELAY=y
 CONFIG_S390=y
 
@@ -30,8 +31,8 @@ CONFIG_AUDIT=y
 CONFIG_IKCONFIG=y
 CONFIG_IKCONFIG_PROC=y
 # CONFIG_CPUSETS is not set
+# CONFIG_RELAY is not set
 CONFIG_INITRAMFS_SOURCE=""
-CONFIG_UID16=y
 # CONFIG_CC_OPTIMIZE_FOR_SIZE is not set
 # CONFIG_EMBEDDED is not set
 CONFIG_KALLSYMS=y
@@ -45,10 +46,6 @@ CONFIG_BASE_FULL=y
 CONFIG_FUTEX=y
 CONFIG_EPOLL=y
 CONFIG_SHMEM=y
-CONFIG_CC_ALIGN_FUNCTIONS=0
-CONFIG_CC_ALIGN_LABELS=0
-CONFIG_CC_ALIGN_LOOPS=0
-CONFIG_CC_ALIGN_JUMPS=0
 CONFIG_SLAB=y
 # CONFIG_TINY_SHMEM is not set
 CONFIG_BASE_SMALL=0
@@ -60,7 +57,6 @@ CONFIG_BASE_SMALL=0
 CONFIG_MODULES=y
 CONFIG_MODULE_UNLOAD=y
 # CONFIG_MODULE_FORCE_UNLOAD is not set
-CONFIG_OBSOLETE_MODPARM=y
 CONFIG_MODVERSIONS=y
 # CONFIG_MODULE_SRCVERSION_ALL is not set
 CONFIG_KMOD=y
@@ -69,7 +65,7 @@ CONFIG_STOP_MACHINE=y
 #
 # Block layer
 #
-# CONFIG_LBD is not set
+# CONFIG_BLK_DEV_IO_TRACE is not set
 
 #
 # IO Schedulers
@@ -91,17 +87,20 @@ CONFIG_DEFAULT_IOSCHED="deadline"
 #
 # Processor type and features
 #
-# CONFIG_64BIT is not set
+CONFIG_64BIT=y
 CONFIG_SMP=y
 CONFIG_NR_CPUS=32
 CONFIG_HOTPLUG_CPU=y
-CONFIG_MATHEMU=y
+CONFIG_DEFAULT_MIGRATION_COST=1000000
+CONFIG_COMPAT=y
+CONFIG_SYSVIPC_COMPAT=y
+CONFIG_BINFMT_ELF32=y
 
 #
 # Code generation options
 #
-CONFIG_MARCH_G5=y
-# CONFIG_MARCH_Z900 is not set
+# CONFIG_MARCH_G5 is not set
+CONFIG_MARCH_Z900=y
 # CONFIG_MARCH_Z990 is not set
 CONFIG_PACK_STACK=y
 # CONFIG_SMALL_STACK is not set
@@ -143,7 +142,7 @@ CONFIG_VIRT_CPU_ACCOUNTING=y
 # CONFIG_APPLDATA_BASE is not set
 CONFIG_NO_IDLE_HZ=y
 CONFIG_NO_IDLE_HZ_INIT=y
-# CONFIG_KEXEC is not set
+CONFIG_KEXEC=y
 
 #
 # Networking
@@ -173,6 +172,7 @@ CONFIG_IP_FIB_HASH=y
 # CONFIG_INET_AH is not set
 # CONFIG_INET_ESP is not set
 # CONFIG_INET_IPCOMP is not set
+# CONFIG_INET_XFRM_TUNNEL is not set
 # CONFIG_INET_TUNNEL is not set
 CONFIG_INET_DIAG=y
 CONFIG_INET_TCP_DIAG=y
@@ -180,9 +180,11 @@ CONFIG_INET_TCP_DIAG=y
 CONFIG_TCP_CONG_BIC=y
 CONFIG_IPV6=y
 # CONFIG_IPV6_PRIVACY is not set
+# CONFIG_IPV6_ROUTER_PREF is not set
 # CONFIG_INET6_AH is not set
 # CONFIG_INET6_ESP is not set
 # CONFIG_INET6_IPCOMP is not set
+# CONFIG_INET6_XFRM_TUNNEL is not set
 # CONFIG_INET6_TUNNEL is not set
 # CONFIG_IPV6_TUNNEL is not set
 # CONFIG_NETFILTER is not set
@@ -275,6 +277,11 @@ CONFIG_PREVENT_FIRMWARE_BUILD=y
 # CONFIG_FW_LOADER is not set
 # CONFIG_DEBUG_DRIVER is not set
 
+#
+# Connector - unified userspace <-> kernelspace linker
+#
+# CONFIG_CONNECTOR is not set
+
 #
 # SCSI device support
 #
@@ -340,8 +347,7 @@ CONFIG_DASD_PROFILE=y
 CONFIG_DASD_ECKD=y
 CONFIG_DASD_FBA=y
 CONFIG_DASD_DIAG=y
-CONFIG_DASD_EER=m
-# CONFIG_DASD_CMB is not set
+CONFIG_DASD_EER=y
 # CONFIG_ATA_OVER_ETH is not set
 
 #
@@ -354,6 +360,7 @@ CONFIG_MD_RAID0=m
 CONFIG_MD_RAID1=m
 # CONFIG_MD_RAID10 is not set
 CONFIG_MD_RAID5=m
+# CONFIG_MD_RAID5_RESHAPE is not set
 # CONFIG_MD_RAID6 is not set
 CONFIG_MD_MULTIPATH=m
 # CONFIG_MD_FAULTY is not set
@@ -404,6 +411,7 @@ CONFIG_S390_TAPE_BLOCK=y
 # S/390 tape hardware support
 #
 CONFIG_S390_TAPE_34XX=m
+# CONFIG_S390_TAPE_3590 is not set
 # CONFIG_VMLOGRDR is not set
 # CONFIG_VMCP is not set
 # CONFIG_MONREADER is not set
@@ -529,7 +537,6 @@ CONFIG_SYSFS=y
 CONFIG_TMPFS=y
 # CONFIG_HUGETLB_PAGE is not set
 CONFIG_RAMFS=y
-# CONFIG_RELAYFS_FS is not set
 # CONFIG_CONFIGFS_FS is not set
 
 #
@@ -619,14 +626,15 @@ CONFIG_LOG_BUF_SHIFT=17
 # CONFIG_DETECT_SOFTLOCKUP is not set
 # CONFIG_SCHEDSTATS is not set
 # CONFIG_DEBUG_SLAB is not set
-# CONFIG_DEBUG_PREEMPT is not set
+CONFIG_DEBUG_PREEMPT=y
 CONFIG_DEBUG_MUTEXES=y
-# CONFIG_DEBUG_SPINLOCK is not set
-# CONFIG_DEBUG_SPINLOCK_SLEEP is not set
+CONFIG_DEBUG_SPINLOCK=y
+CONFIG_DEBUG_SPINLOCK_SLEEP=y
 # CONFIG_DEBUG_KOBJECT is not set
 # CONFIG_DEBUG_INFO is not set
 CONFIG_DEBUG_FS=y
 # CONFIG_DEBUG_VM is not set
+# CONFIG_UNWIND_INFO is not set
 CONFIG_FORCED_INLINING=y
 # CONFIG_RCU_TORTURE_TEST is not set
 
index 58583f4594719ddcd5da635bec148858ef5807fc..2bcecf42257343e0b2af310bf0b43b2b16fc3e93 100644 (file)
@@ -527,6 +527,11 @@ config CPU_HAS_SR_RB
          See <file:Documentation/sh/register-banks.txt> for further
          information on SR.RB and register banking in the kernel in general.
 
+config NODES_SHIFT
+       int
+       default "1"
+       depends on NEED_MULTIPLE_NODES
+
 endmenu
 
 menu "Boot options"
index 1cf94a618be3c97fa21207b4811e36e88634f780..d5d032533a8b3b1445f70ab6430b5e4deb6e7fa5 100644 (file)
@@ -37,7 +37,6 @@ EXPORT_SYMBOL(disable_irq_nosync);
 EXPORT_SYMBOL(irq_desc);
 EXPORT_SYMBOL(no_irq_type);
 
-EXPORT_SYMBOL(strpbrk);
 EXPORT_SYMBOL(strstr);
 EXPORT_SYMBOL(strlen);
 EXPORT_SYMBOL(strnlen);
index de29c45f23a7278ee01fb2930d3afc20d1cbed6e..6f3a1c946339442301f66de7e5ce78dc19ed5f69 100644 (file)
@@ -41,7 +41,6 @@ EXPORT_SYMBOL(kernel_thread);
 /* Networking helper routines. */
 EXPORT_SYMBOL(csum_partial_copy);
 
-EXPORT_SYMBOL(strpbrk);
 EXPORT_SYMBOL(strstr);
 
 #ifdef CONFIG_VT
index 2be8121151977d4404cb0976ca445786ba5621b7..a93f5da6855d58b1164ae734c9f5d2991ebbf8c1 100644 (file)
@@ -244,7 +244,7 @@ int setup_profiling_timer(unsigned int multiplier)
                return -EINVAL;
 
        spin_lock_irqsave(&prof_setup_lock, flags);
-       for_each_cpu(i) {
+       for_each_possible_cpu(i) {
                load_profile_irq(i, lvl14_resolution / multiplier);
                prof_multiplier(i) = multiplier;
        }
index 2c21d79076356e2a0c617bb290109fd8705f92b2..ec1c9687d67920312df790ec0b550d3740c1c08c 100644 (file)
@@ -263,7 +263,6 @@ EXPORT_SYMBOL(strcmp);
 EXPORT_SYMBOL(strncmp);
 EXPORT_SYMBOL(strchr);
 EXPORT_SYMBOL(strrchr);
-EXPORT_SYMBOL(strpbrk);
 EXPORT_SYMBOL(strstr);
 EXPORT_SYMBOL(page_kernel);
 
index fbbec5e761c68957c27a442374716df3404bf634..db8faa75f94dd318515ad2bcb86b59bf5df5e942 100644 (file)
@@ -75,7 +75,7 @@ sys_call_table:
 /*265*/        .long sys_timer_delete, sys_timer_create, sys_nis_syscall, sys_io_setup, sys_io_destroy
 /*270*/        .long sys_io_submit, sys_io_cancel, sys_io_getevents, sys_mq_open, sys_mq_unlink
 /*275*/        .long sys_mq_timedsend, sys_mq_timedreceive, sys_mq_notify, sys_mq_getsetattr, sys_waitid
-/*280*/        .long sys_ni_syscall, sys_add_key, sys_request_key, sys_keyctl, sys_openat
+/*280*/        .long sys_tee, sys_add_key, sys_request_key, sys_keyctl, sys_openat
 /*285*/        .long sys_mkdirat, sys_mknodat, sys_fchownat, sys_futimesat, sys_fstatat64
 /*290*/        .long sys_unlinkat, sys_renameat, sys_linkat, sys_symlinkat, sys_readlinkat
 /*295*/        .long sys_fchmodat, sys_faccessat, sys_pselect6, sys_ppoll, sys_unshare
index f84a9a6162be90a1399b218dd0f5aea0a49a81de..8136987977f45ce598f02f41c65a168254b59270 100644 (file)
@@ -5,4 +5,4 @@
 obj-y    := math.o
 
 EXTRA_AFLAGS := -ansi
-EXTRA_CFLAGS = -I. -I$(TOPDIR)/include/math-emu -w
+EXTRA_CFLAGS = -I. -Iinclude/math-emu -w
index d1e2fc56648629a5801f4b4e75ce30a882fdb61e..43a66f5407f45b2b5d04666f0f765f2cd287778b 100644 (file)
@@ -187,13 +187,16 @@ config HUGETLB_PAGE_SIZE_512K
        bool "512K"
 
 config HUGETLB_PAGE_SIZE_64K
-       depends on !SPARC64_PAGE_SIZE_4MB && !SPARC64_PAGE_SIZE_512KB && !SPARC64_PAGE_SIZE_64K
+       depends on !SPARC64_PAGE_SIZE_4MB && !SPARC64_PAGE_SIZE_512KB && !SPARC64_PAGE_SIZE_64KB
        bool "64K"
 
 endchoice
 
 endmenu
 
+config ARCH_SELECT_MEMORY_MODEL
+       def_bool y
+
 config ARCH_SPARSEMEM_ENABLE
        def_bool y
 
index 30389085a3591167b3e5adf37812246d102aeea9..1317380fa93779899be32254c629629fec2c84a3 100644 (file)
@@ -1,7 +1,7 @@
 #
 # Automatically generated make config: don't edit
 # Linux kernel version: 2.6.16
-# Fri Mar 31 01:40:57 2006
+# Sun Apr  2 19:31:04 2006
 #
 CONFIG_SPARC=y
 CONFIG_SPARC64=y
@@ -838,7 +838,6 @@ CONFIG_FB_TILEBLITTING=y
 # CONFIG_FB_NVIDIA is not set
 # CONFIG_FB_RIVA is not set
 # CONFIG_FB_MATROX is not set
-# CONFIG_FB_RADEON_OLD is not set
 CONFIG_FB_RADEON=y
 CONFIG_FB_RADEON_I2C=y
 # CONFIG_FB_RADEON_DEBUG is not set
@@ -924,6 +923,7 @@ CONFIG_SND_MTPAV=m
 # PCI devices
 #
 # CONFIG_SND_AD1889 is not set
+# CONFIG_SND_ALS300 is not set
 CONFIG_SND_ALI5451=m
 # CONFIG_SND_ATIIXP is not set
 # CONFIG_SND_ATIIXP_MODEM is not set
@@ -955,6 +955,7 @@ CONFIG_SND_ALI5451=m
 # CONFIG_SND_MIXART is not set
 # CONFIG_SND_NM256 is not set
 # CONFIG_SND_PCXHR is not set
+# CONFIG_SND_RIPTIDE is not set
 # CONFIG_SND_RME32 is not set
 # CONFIG_SND_RME96 is not set
 # CONFIG_SND_RME9652 is not set
@@ -1108,6 +1109,11 @@ CONFIG_USB_HIDDEV=y
 #
 # CONFIG_MMC is not set
 
+#
+# LED devices
+#
+# CONFIG_NEW_LEDS is not set
+
 #
 # InfiniBand support
 #
index ffc7309e9f22d51e640f77b95aab4028e57c841f..2e1c824c1cc9512356460ea3a09f2fd74c11dfe2 100644 (file)
@@ -63,7 +63,7 @@ void __kprobes arch_disarm_kprobe(struct kprobe *p)
        flushi(p->addr);
 }
 
-static inline void save_previous_kprobe(struct kprobe_ctlblk *kcb)
+static void __kprobes save_previous_kprobe(struct kprobe_ctlblk *kcb)
 {
        kcb->prev_kprobe.kp = kprobe_running();
        kcb->prev_kprobe.status = kcb->kprobe_status;
@@ -71,7 +71,7 @@ static inline void save_previous_kprobe(struct kprobe_ctlblk *kcb)
        kcb->prev_kprobe.orig_tstate_pil = kcb->kprobe_orig_tstate_pil;
 }
 
-static inline void restore_previous_kprobe(struct kprobe_ctlblk *kcb)
+static void __kprobes restore_previous_kprobe(struct kprobe_ctlblk *kcb)
 {
        __get_cpu_var(current_kprobe) = kcb->prev_kprobe.kp;
        kcb->kprobe_status = kcb->prev_kprobe.status;
@@ -79,7 +79,7 @@ static inline void restore_previous_kprobe(struct kprobe_ctlblk *kcb)
        kcb->kprobe_orig_tstate_pil = kcb->prev_kprobe.orig_tstate_pil;
 }
 
-static inline void set_current_kprobe(struct kprobe *p, struct pt_regs *regs,
+static void __kprobes set_current_kprobe(struct kprobe *p, struct pt_regs *regs,
                                struct kprobe_ctlblk *kcb)
 {
        __get_cpu_var(current_kprobe) = p;
@@ -87,7 +87,7 @@ static inline void set_current_kprobe(struct kprobe *p, struct pt_regs *regs,
        kcb->kprobe_orig_tstate_pil = (regs->tstate & TSTATE_PIL);
 }
 
-static inline void prepare_singlestep(struct kprobe *p, struct pt_regs *regs,
+static void __kprobes prepare_singlestep(struct kprobe *p, struct pt_regs *regs,
                        struct kprobe_ctlblk *kcb)
 {
        regs->tstate |= TSTATE_PIL;
@@ -273,7 +273,7 @@ static void __kprobes resume_execution(struct kprobe *p,
                        kcb->kprobe_orig_tstate_pil);
 }
 
-static inline int post_kprobe_handler(struct pt_regs *regs)
+static int __kprobes post_kprobe_handler(struct pt_regs *regs)
 {
        struct kprobe *cur = kprobe_running();
        struct kprobe_ctlblk *kcb = get_kprobe_ctlblk();
@@ -300,7 +300,7 @@ out:
        return 1;
 }
 
-static inline int kprobe_fault_handler(struct pt_regs *regs, int trapnr)
+static int __kprobes kprobe_fault_handler(struct pt_regs *regs, int trapnr)
 {
        struct kprobe *cur = kprobe_running();
        struct kprobe_ctlblk *kcb = get_kprobe_ctlblk();
index dfccff29e182c1b2c68876debad304b6bf52ed11..f97ddeb105ac492b6b66cc1b87642b88dd2afe2e 100644 (file)
@@ -419,6 +419,7 @@ void pcibios_resource_to_bus(struct pci_dev *pdev, struct pci_bus_region *region
        region->start = res->start - zero_res.start;
        region->end = res->end - zero_res.start;
 }
+EXPORT_SYMBOL(pcibios_resource_to_bus);
 
 void pcibios_bus_to_resource(struct pci_dev *pdev, struct resource *res,
                             struct pci_bus_region *region)
index 9372d4f376d5af9aad36d094194abd9da5e2d28a..9e94db2573a2f83f8c1d58072d8e2d28cd0035d4 100644 (file)
@@ -1092,7 +1092,7 @@ void sun4v_pci_init(int node, char *model_name)
                }
        }
 
-       for_each_cpu(i) {
+       for_each_possible_cpu(i) {
                unsigned long page = get_zeroed_page(GFP_ATOMIC);
 
                if (!page)
index eb93e9c528462c6a2d92a8cb76251b65f91f0db7..49e6dedd027d603b9b1788af35f38fb27a452515 100644 (file)
@@ -244,6 +244,13 @@ asmlinkage void do_ptrace(struct pt_regs *regs)
        }
 
        switch(request) {
+       case PTRACE_PEEKUSR:
+               if (addr != 0)
+                       pt_error_return(regs, EIO);
+               else
+                       pt_succ_return(regs, 0);
+               goto out_tsk;
+
        case PTRACE_PEEKTEXT: /* read word at location addr. */ 
        case PTRACE_PEEKDATA: {
                unsigned long tmp64;
@@ -602,6 +609,22 @@ asmlinkage void do_ptrace(struct pt_regs *regs)
 
        /* PTRACE_DUMPCORE unsupported... */
 
+       case PTRACE_GETEVENTMSG: {
+               int err;
+
+               if (test_thread_flag(TIF_32BIT))
+                       err = put_user(child->ptrace_message,
+                                      (unsigned int __user *) data);
+               else
+                       err = put_user(child->ptrace_message,
+                                      (unsigned long __user *) data);
+               if (err)
+                       pt_error_return(regs, -err);
+               else
+                       pt_succ_return(regs, 0);
+               break;
+       }
+
        default: {
                int err = ptrace_request(child, request, addr, data);
                if (err)
index 7d0e67c1ce5099102dce96928a2b3ae3b119ef57..005167f82419b475cb7ae1e4ef109610ba61a5dd 100644 (file)
@@ -535,7 +535,7 @@ static int __init topology_init(void)
        while (!cpu_find_by_instance(ncpus_probed, NULL, NULL))
                ncpus_probed++;
 
-       for_each_cpu(i) {
+       for_each_possible_cpu(i) {
                struct cpu *p = kzalloc(sizeof(*p), GFP_KERNEL);
                if (p) {
                        register_cpu(p, i, NULL);
index 8175a6968c6bcc5cdd66f96a89ee60b30bb5b328..90eaca3ec9a628c40ba90f27c2a89e825afdf736 100644 (file)
@@ -745,12 +745,21 @@ struct call_data_struct {
        int wait;
 };
 
-static DEFINE_SPINLOCK(call_lock);
+static __cacheline_aligned_in_smp DEFINE_SPINLOCK(call_lock);
 static struct call_data_struct *call_data;
 
 extern unsigned long xcall_call_function;
 
-/*
+/**
+ * smp_call_function(): Run a function on all other CPUs.
+ * @func: The function to run. This must be fast and non-blocking.
+ * @info: An arbitrary pointer to pass to the function.
+ * @nonatomic: currently unused.
+ * @wait: If true, wait (atomically) until function has completed on other CPUs.
+ *
+ * Returns 0 on success, else a negative status code. Does not return until
+ * remote CPUs are nearly ready to execute <<func>> or are or have executed.
+ *
  * You must not call this function with disabled interrupts or from a
  * hardware interrupt handler or from a bottom half handler.
  */
@@ -759,7 +768,6 @@ static int smp_call_function_mask(void (*func)(void *info), void *info,
 {
        struct call_data_struct data;
        int cpus;
-       long timeout;
 
        /* Can deadlock when called with interrupts disabled */
        WARN_ON(irqs_disabled());
@@ -777,31 +785,18 @@ static int smp_call_function_mask(void (*func)(void *info), void *info,
                goto out_unlock;
 
        call_data = &data;
+       mb();
 
        smp_cross_call_masked(&xcall_call_function, 0, 0, 0, mask);
 
-       /* 
-        * Wait for other cpus to complete function or at
-        * least snap the call data.
-        */
-       timeout = 1000000;
-       while (atomic_read(&data.finished) != cpus) {
-               if (--timeout <= 0)
-                       goto out_timeout;
-               barrier();
-               udelay(1);
-       }
+       /* Wait for response */
+       while (atomic_read(&data.finished) != cpus)
+               cpu_relax();
 
 out_unlock:
        spin_unlock(&call_lock);
 
        return 0;
-
-out_timeout:
-       spin_unlock(&call_lock);
-       printk("XCALL: Remote cpus not responding, ncpus=%d finished=%d\n",
-              cpus, atomic_read(&data.finished));
-       return 0;
 }
 
 int smp_call_function(void (*func)(void *info), void *info,
@@ -1285,7 +1280,7 @@ int setup_profiling_timer(unsigned int multiplier)
                return -EINVAL;
 
        spin_lock_irqsave(&prof_setup_lock, flags);
-       for_each_cpu(i)
+       for_each_possible_cpu(i)
                prof_multiplier(i) = multiplier;
        current_tick_offset = (timer_tick_offset / multiplier);
        spin_unlock_irqrestore(&prof_setup_lock, flags);
@@ -1313,12 +1308,12 @@ void __init smp_prepare_cpus(unsigned int max_cpus)
                }
        }
 
-       for_each_cpu(i) {
+       for_each_possible_cpu(i) {
                if (tlb_type == hypervisor) {
                        int j;
 
                        /* XXX get this mapping from machine description */
-                       for_each_cpu(j) {
+                       for_each_possible_cpu(j) {
                                if ((j >> 2) == (i >> 2))
                                        cpu_set(j, cpu_sibling_map[i]);
                        }
index f5e8db1de76b590400f8a143fa5a3ee107cef1c7..62d8a99271eac044e66906d15f3435944eaa3845 100644 (file)
@@ -276,7 +276,6 @@ EXPORT_SYMBOL(__prom_getsibling);
 EXPORT_SYMBOL(strlen);
 EXPORT_SYMBOL(__strlen_user);
 EXPORT_SYMBOL(__strnlen_user);
-EXPORT_SYMBOL(strpbrk);
 
 #ifdef CONFIG_SOLARIS_EMUL_MODULE
 EXPORT_SYMBOL(linux_sparc_syscall);
index 86dd5cb81e09fc9bfa08cce1c90ff6ffe5c5b026..f9b75760163c4b9a95fc55806d7ef4da006d0c36 100644 (file)
@@ -138,6 +138,7 @@ SIGN2(sys32_ioprio_get, sys_ioprio_get, %o0, %o1)
 SIGN3(sys32_ioprio_set, sys_ioprio_set, %o0, %o1, %o2)
 SIGN2(sys32_splice, sys_splice, %o0, %o1)
 SIGN2(sys32_sync_file_range, compat_sync_file_range, %o0, %o5)
+SIGN2(sys32_tee, sys_tee, %o0, %o1)
 
        .globl          sys32_mmap2
 sys32_mmap2:
index 857b82c82875bf4154a424b41ea9607a0f910e64..62672cd92eca6f216d2fa7a611f68fa9d44ab308 100644 (file)
@@ -76,7 +76,7 @@ sys_call_table32:
        .word sys_timer_delete, compat_sys_timer_create, sys_ni_syscall, compat_sys_io_setup, sys_io_destroy
 /*270*/        .word sys32_io_submit, sys_io_cancel, compat_sys_io_getevents, sys32_mq_open, sys_mq_unlink
        .word compat_sys_mq_timedsend, compat_sys_mq_timedreceive, compat_sys_mq_notify, compat_sys_mq_getsetattr, compat_sys_waitid
-/*280*/        .word sys_ni_syscall, sys_add_key, sys_request_key, sys_keyctl, compat_sys_openat
+/*280*/        .word sys32_tee, sys_add_key, sys_request_key, sys_keyctl, compat_sys_openat
        .word sys_mkdirat, sys_mknodat, sys_fchownat, compat_sys_futimesat, compat_sys_fstatat64
 /*285*/        .word sys_unlinkat, sys_renameat, sys_linkat, sys_symlinkat, sys_readlinkat
        .word sys_fchmodat, sys_faccessat, compat_sys_pselect6, compat_sys_ppoll, sys_unshare
@@ -145,7 +145,7 @@ sys_call_table:
        .word sys_timer_delete, sys_timer_create, sys_ni_syscall, sys_io_setup, sys_io_destroy
 /*270*/        .word sys_io_submit, sys_io_cancel, sys_io_getevents, sys_mq_open, sys_mq_unlink
        .word sys_mq_timedsend, sys_mq_timedreceive, sys_mq_notify, sys_mq_getsetattr, sys_waitid
-/*280*/        .word sys_nis_syscall, sys_add_key, sys_request_key, sys_keyctl, sys_openat
+/*280*/        .word sys_tee, sys_add_key, sys_request_key, sys_keyctl, sys_openat
        .word sys_mkdirat, sys_mknodat, sys_fchownat, sys_futimesat, sys_fstatat64
 /*285*/        .word sys_unlinkat, sys_renameat, sys_linkat, sys_symlinkat, sys_readlinkat
        .word sys_fchmodat, sys_faccessat, sys_pselect6, sys_ppoll, sys_unshare
index ff090bb9734b82a8f356c156d8f2ce86581187ae..2793a5d823803cb7b96055802935179d5e3d4333 100644 (file)
@@ -1130,9 +1130,9 @@ static void cheetah_log_errors(struct pt_regs *regs, struct cheetah_err_info *in
               (recoverable ? KERN_WARNING : KERN_CRIT), smp_processor_id(),
               afsr, afar,
               (afsr & CHAFSR_TL1) ? 1 : 0);
-       printk("%s" "ERROR(%d): TPC[%016lx] TNPC[%016lx] TSTATE[%016lx]\n",
+       printk("%s" "ERROR(%d): TPC[%lx] TNPC[%lx] O7[%lx] TSTATE[%lx]\n",
               (recoverable ? KERN_WARNING : KERN_CRIT), smp_processor_id(),
-              regs->tpc, regs->tnpc, regs->tstate);
+              regs->tpc, regs->tnpc, regs->u_regs[UREG_I7], regs->tstate);
        printk("%s" "ERROR(%d): M_SYND(%lx),  E_SYND(%lx)%s%s\n",
               (recoverable ? KERN_WARNING : KERN_CRIT), smp_processor_id(),
               (afsr & CHAFSR_M_SYNDROME) >> CHAFSR_M_SYNDROME_SHIFT,
index 24790bed2054d23af47fd8bd768999ff797f2967..a508e7a028910607c3b91e87e078017d8ecfc00f 100644 (file)
@@ -159,6 +159,7 @@ archclean:
 $(SYMLINK_HEADERS):
        @echo '  SYMLINK $@'
 ifneq ($(KBUILD_SRC),)
+       $(Q)mkdir -p $(objtree)/include/asm-um
        $(Q)ln -fsn $(srctree)/include/asm-um/$(basename $(notdir $@))-$(SUBARCH)$(suffix $@) $@
 else
        $(Q)cd $(TOPDIR)/$(dir $@) ; \
@@ -168,7 +169,7 @@ endif
 include/asm-um/arch:
        @echo '  SYMLINK $@'
 ifneq ($(KBUILD_SRC),)
-       $(Q)mkdir -p include/asm-um
+       $(Q)mkdir -p $(objtree)/include/asm-um
        $(Q)ln -fsn $(srctree)/include/asm-$(SUBARCH) include/asm-um/arch
 else
        $(Q)cd $(TOPDIR)/include/asm-um && ln -sf ../asm-$(SUBARCH) arch
index 04e3958266e07192c69a1b5ebba418a9e6cd43ed..dc36b222100b9abde780f996407a758f336afce4 100644 (file)
@@ -46,7 +46,7 @@ extern int file_reader(__u64 offset, char *buf, int len, void *arg);
 extern int read_cow_header(int (*reader)(__u64, char *, int, void *),
                           void *arg, __u32 *version_out,
                           char **backing_file_out, time_t *mtime_out,
-                          __u64 *size_out, int *sectorsize_out,
+                          unsigned long long *size_out, int *sectorsize_out,
                           __u32 *align_out, int *bitmap_offset_out);
 
 extern int write_cow_header(char *cow_file, int fd, char *backing_file,
index 94de4ead4f7a2533ee2cac6501acf925a5aa0ba2..7a5b4afde6929474f8422ab681076dd430ebaed1 100644 (file)
@@ -28,7 +28,7 @@ static inline int cow_seek_file(int fd, __u64 offset)
        return(os_seek_file(fd, offset));
 }
 
-static inline int cow_file_size(char *file, __u64 *size_out)
+static inline int cow_file_size(char *file, unsigned long long *size_out)
 {
        return(os_file_size(file, size_out));
 }
index 61951b721268f1c030279cff98b2a25213708ca8..6ab852bfcd3ac62cb66b18a02433d6b3feaadfcb 100644 (file)
 
 #define PATH_LEN_V1 256
 
+typedef __u32 time32_t;
+
 struct cow_header_v1 {
-       int magic;
-       int version;
+       __s32 magic;
+       __s32 version;
        char backing_file[PATH_LEN_V1];
-       time_t mtime;
+       time32_t mtime;
        __u64 size;
-       int sectorsize;
-};
+       __s32 sectorsize;
+} __attribute__((packed));
 
-#define PATH_LEN_V2 MAXPATHLEN
+/* Define PATH_LEN_V3 as the usual value of MAXPATHLEN, just hard-code it in
+ * case other systems have different values for MAXPATHLEN.
+ *
+ * The same must hold for V2 - we want file format compatibility, not anything
+ * else.
+ */
+#define PATH_LEN_V3 4096
+#define PATH_LEN_V2 PATH_LEN_V3
 
 struct cow_header_v2 {
        __u32 magic;
        __u32 version;
        char backing_file[PATH_LEN_V2];
-       time_t mtime;
+       time32_t mtime;
        __u64 size;
-       int sectorsize;
-};
-
-/* Define PATH_LEN_V3 as the usual value of MAXPATHLEN, just hard-code it in
- * case other systems have different values for MAXPATHLEN
- */
-#define PATH_LEN_V3 4096
+       __s32 sectorsize;
+} __attribute__((packed));
 
 /* Changes from V2 -
  *     PATH_LEN_V3 as described above
@@ -66,6 +70,15 @@ struct cow_header_v2 {
  *     Fixed (finally!) the rounding bug
  */
 
+/* Until Dec2005, __attribute__((packed)) was left out from the below
+ * definition, leading on 64-bit systems to 4 bytes of padding after mtime, to
+ * align size to 8-byte alignment.  This shifted all fields above (no padding
+ * was present on 32-bit, no other padding was added).
+ *
+ * However, this _can be detected_: it means that cow_format (always 0 until
+ * now) is shifted onto the first 4 bytes of backing_file, where it is otherwise
+ * impossible to find 4 zeros. -bb */
+
 struct cow_header_v3 {
        __u32 magic;
        __u32 version;
@@ -75,7 +88,19 @@ struct cow_header_v3 {
        __u32 alignment;
        __u32 cow_format;
        char backing_file[PATH_LEN_V3];
-};
+} __attribute__((packed));
+
+/* This is the broken layout used by some 64-bit binaries. */
+struct cow_header_v3_broken {
+       __u32 magic;
+       __u32 version;
+       __s64 mtime;
+       __u64 size;
+       __u32 sectorsize;
+       __u32 alignment;
+       __u32 cow_format;
+       char backing_file[PATH_LEN_V3];
+} __attribute__((packed));
 
 /* COW format definitions - for now, we have only the usual COW bitmap */
 #define COW_BITMAP 0
@@ -84,6 +109,7 @@ union cow_header {
        struct cow_header_v1 v1;
        struct cow_header_v2 v2;
        struct cow_header_v3 v3;
+       struct cow_header_v3_broken v3_b;
 };
 
 #define COW_MAGIC 0x4f4f4f4d  /* MOOO */
@@ -184,8 +210,9 @@ int write_cow_header(char *cow_file, int fd, char *backing_file,
 
        err = -EINVAL;
        if(strlen(backing_file) > sizeof(header->backing_file) - 1){
+               /* Below, %zd is for a size_t value */
                cow_printf("Backing file name \"%s\" is too long - names are "
-                          "limited to %d characters\n", backing_file,
+                          "limited to %zd characters\n", backing_file,
                           sizeof(header->backing_file) - 1);
                goto out_free;
        }
@@ -300,7 +327,8 @@ int read_cow_header(int (*reader)(__u64, char *, int, void *), void *arg,
                *align_out = *sectorsize_out;
                file = header->v2.backing_file;
        }
-       else if(version == 3){
+       /* This is very subtle - see above at union cow_header definition */
+       else if(version == 3 && (*((int*)header->v3.backing_file) != 0)){
                if(n < sizeof(header->v3)){
                        cow_printf("read_cow_header - failed to read V3 "
                                   "header\n");
@@ -310,9 +338,43 @@ int read_cow_header(int (*reader)(__u64, char *, int, void *), void *arg,
                *size_out = ntohll(header->v3.size);
                *sectorsize_out = ntohl(header->v3.sectorsize);
                *align_out = ntohl(header->v3.alignment);
+               if (*align_out == 0) {
+                       cow_printf("read_cow_header - invalid COW header, "
+                                  "align == 0\n");
+               }
                *bitmap_offset_out = ROUND_UP(sizeof(header->v3), *align_out);
                file = header->v3.backing_file;
        }
+       else if(version == 3){
+               cow_printf("read_cow_header - broken V3 file with"
+                          " 64-bit layout - recovering content.\n");
+
+               if(n < sizeof(header->v3_b)){
+                       cow_printf("read_cow_header - failed to read V3 "
+                                  "header\n");
+                       goto out;
+               }
+
+               /* this was used until Dec2005 - 64bits are needed to represent
+                * 2038+. I.e. we can safely do this truncating cast.
+                *
+                * Additionally, we must use ntohl() instead of ntohll(), since
+                * the program used to use the former (tested - I got mtime
+                * mismatch "0 vs whatever").
+                *
+                * Ever heard about bug-to-bug-compatibility ? ;-) */
+               *mtime_out = (time32_t) ntohl(header->v3_b.mtime);
+
+               *size_out = ntohll(header->v3_b.size);
+               *sectorsize_out = ntohl(header->v3_b.sectorsize);
+               *align_out = ntohl(header->v3_b.alignment);
+               if (*align_out == 0) {
+                       cow_printf("read_cow_header - invalid COW header, "
+                                  "align == 0\n");
+               }
+               *bitmap_offset_out = ROUND_UP(sizeof(header->v3_b), *align_out);
+               file = header->v3_b.backing_file;
+       }
        else {
                cow_printf("read_cow_header - invalid COW version\n");
                goto out;
index 28e3760e8b981ed20d1f46453c8405dbfc31bd42..6d7173fc55a395e3a1e1ef7f83263e1fa2711808 100644 (file)
@@ -62,7 +62,7 @@ static void mc_work_proc(void *unused)
        unsigned long flags;
 
        while(!list_empty(&mc_requests)){
-               local_save_flags(flags);
+               local_irq_save(flags);
                req = list_entry(mc_requests.next, struct mconsole_entry,
                                 list);
                list_del(&req->list);
@@ -87,7 +87,7 @@ static irqreturn_t mconsole_interrupt(int irq, void *dev_id,
                if(req.cmd->context == MCONSOLE_INTR)
                        (*req.cmd->handler)(&req);
                else {
-                       new = kmalloc(sizeof(*new), GFP_ATOMIC);
+                       new = kmalloc(sizeof(*new), GFP_NOWAIT);
                        if(new == NULL)
                                mconsole_reply(&req, "Out of memory", 1, 0);
                        else {
@@ -415,7 +415,6 @@ static int mem_config(char *str)
 
                        unplugged = page_address(page);
                        if(unplug_index == UNPLUGGED_PER_PAGE){
-                               INIT_LIST_HEAD(&unplugged->list);
                                list_add(&unplugged->list, &unplugged_pages);
                                unplug_index = 0;
                        }
@@ -616,7 +615,7 @@ static void console_write(struct console *console, const char *string,
                return;
 
        while(1){
-               n = min((size_t)len, ARRAY_SIZE(console_buf) - console_index);
+               n = min((size_t) len, ARRAY_SIZE(console_buf) - console_index);
                strncpy(&console_buf[console_index], string, n);
                console_index += n;
                string += n;
@@ -655,7 +654,6 @@ static void with_console(struct mc_request *req, void (*proc)(void *),
        struct mconsole_entry entry;
        unsigned long flags;
 
-       INIT_LIST_HEAD(&entry.list);
        entry.request = *req;
        list_add(&entry.list, &clients);
        spin_lock_irqsave(&console_lock, flags);
index 0e2f06187ea7a1b306370edd7ff9baf03c04958b..0a7786e00cfb80da658f6474f562eca1b9d5c067 100644 (file)
@@ -182,7 +182,9 @@ static int change_tramp(char **argv, char *output, int output_len)
        pe_data.stdout = fds[1];
        pid = run_helper(change_pre_exec, &pe_data, argv, NULL);
 
-       read_output(fds[0], output, output_len);
+       if (pid > 0)    /* Avoid hang as we won't get data in failure case. */
+               read_output(fds[0], output, output_len);
+
        os_close_file(fds[0]);
        os_close_file(fds[1]);
 
index b94c66114bc85d7a56fe4d9f6d29d4d31a633c13..33c5f6e625e83eecc26a97b774dffa6fe1bbb750 100644 (file)
@@ -104,7 +104,7 @@ static void slirp_close(int fd, void *data)
        }
 
        if(err == 0) {
-               printk("slirp_close: process %d has not exited\n");
+               printk("slirp_close: process %d has not exited\n", pri->pid);
                return;
        }
 
index 42557130a4081868e7d4c3cfc8cf9a5e8514d7db..efa3d33c0be6577a6ab533449ce2ed34032957de 100644 (file)
@@ -117,10 +117,6 @@ extern struct task_struct *get_task(int pid, int require);
 extern void machine_halt(void);
 extern int is_syscall(unsigned long addr);
 
-extern void arch_switch_to_tt(struct task_struct *from, struct task_struct *to);
-
-extern void arch_switch_to_skas(struct task_struct *from, struct task_struct *to);
-
 extern void free_irq(unsigned int, void *);
 extern int cpu(void);
 
index 018b3819ab0bf3ea4fc3007a8240b6b7f99c8dca..8e7053013f7b7d11d218603487abf8c9dcd96294 100644 (file)
@@ -4,11 +4,11 @@
 #include <setjmp.h>
 #include "os.h"
 
-#define UML_SIGLONGJMP(buf, val) do { \
+#define UML_LONGJMP(buf, val) do { \
        longjmp(*buf, val);     \
 } while(0)
 
-#define UML_SIGSETJMP(buf, enable) ({ \
+#define UML_SETJMP(buf, enable) ({ \
        int n; \
        enable = get_signals(); \
        n = setjmp(*buf); \
index 82f96c574144cbc327daa8b5c82624014bb9cf83..2c13de321f2fb330eb5dc162fe53bffca57f3bad 100644 (file)
@@ -1,6 +1,7 @@
 #include <linux/stddef.h>
 #include <linux/sched.h>
 #include <linux/elf.h>
+#include <asm/mman.h>
 
 #define DEFINE(sym, val) \
        asm volatile("\n->" #sym " %0 " #val : : "i" (val))
@@ -16,6 +17,7 @@
 void foo(void)
 {
        OFFSET(HOST_TASK_DEBUGREGS, task_struct, thread.arch.debugregs);
+       DEFINE(KERNEL_MADV_REMOVE, MADV_REMOVE);
 #ifdef CONFIG_MODE_TT
        OFFSET(HOST_TASK_EXTERN_PID, task_struct, thread.mode.tt.extern_pid);
 #endif
index 5ce93abd0b54fd79f95dea8df40cf3a756366bc0..939cc475757a583e7b38977f02c6f095de004465 100644 (file)
@@ -4,6 +4,7 @@
 #include <linux/time.h>
 #include <linux/elf.h>
 #include <asm/page.h>
+#include <asm/mman.h>
 
 #define DEFINE(sym, val) \
        asm volatile("\n->" #sym " %0 " #val : : "i" (val))
@@ -18,6 +19,7 @@
 
 void foo(void)
 {
+       DEFINE(KERNEL_MADV_REMOVE, MADV_REMOVE);
 #ifdef CONFIG_MODE_TT
        OFFSET(HOST_TASK_EXTERN_PID, task_struct, thread.mode.tt.extern_pid);
 #endif
index 8085219801861938cae75cc5c25a7edaf53cead3..acb8356e1f9839ff67435af56f39ebe17b4ab00b 100644 (file)
@@ -19,7 +19,8 @@ extern int fork_tramp(void *sig_stack);
 extern int do_proc_op(void *t, int proc_id);
 extern int tracer(int (*init_proc)(void *), void *sp);
 extern void attach_process(int pid);
-extern void tracer_panic(char *format, ...);
+extern void tracer_panic(char *format, ...)
+       __attribute__ ((format (printf, 1, 2)));
 extern void set_init_pid(int pid);
 extern int set_user_mode(void *task);
 extern void set_tracing(void *t, int tracing);
index 91b0ac4ad88cceb8b9961c6ba667f4d16133a197..39f8c8801076351de6b0c2cfc3d7b070a2c7dba4 100644 (file)
@@ -6,8 +6,10 @@
 #ifndef __USER_H__
 #define __USER_H__
 
-extern void panic(const char *fmt, ...);
-extern int printk(const char *fmt, ...);
+extern void panic(const char *fmt, ...)
+       __attribute__ ((format (printf, 1, 2)));
+extern int printk(const char *fmt, ...)
+       __attribute__ ((format (printf, 1, 2)));
 extern void schedule(void);
 extern void *um_kmalloc(int size);
 extern void *um_kmalloc_atomic(int size);
index fe0c29b5144db9ddc3351d91b18f00c8e67e989a..802d7842514d25ad63b5be204a573363a6992b60 100644 (file)
@@ -55,7 +55,8 @@ extern int get_pty(void);
 extern void *um_kmalloc(int size);
 extern int switcheroo(int fd, int prot, void *from, void *to, int size);
 extern void do_exec(int old_pid, int new_pid);
-extern void tracer_panic(char *msg, ...);
+extern void tracer_panic(char *msg, ...)
+       __attribute__ ((format (printf, 1, 2)));
 extern int detach(int pid, int sig);
 extern int attach(int pid);
 extern void kill_child_dead(int pid);
index 7713e7a6f476fcdf910a99565be74ccdb01828f5..432cf0b97a138716b39360274a09e6d769b7fcfe 100644 (file)
@@ -39,7 +39,6 @@ EXPORT_SYMBOL(um_virt_to_phys);
 EXPORT_SYMBOL(mode_tt);
 EXPORT_SYMBOL(handle_page_fault);
 EXPORT_SYMBOL(find_iomem);
-EXPORT_SYMBOL(end_iomem);
 
 #ifdef CONFIG_MODE_TT
 EXPORT_SYMBOL(strncpy_from_user_tt);
@@ -89,12 +88,10 @@ EXPORT_SYMBOL(dump_thread);
 EXPORT_SYMBOL(do_gettimeofday);
 EXPORT_SYMBOL(do_settimeofday);
 
-/* This is here because UML expands open to sys_open, not to a system
+/* This is here because UML expands lseek to sys_lseek, not to a system
  * call instruction.
  */
-EXPORT_SYMBOL(sys_open);
 EXPORT_SYMBOL(sys_lseek);
-EXPORT_SYMBOL(sys_read);
 EXPORT_SYMBOL(sys_wait4);
 
 #ifdef CONFIG_SMP
index 901b85e8a1c65c4df84ae87018b3d55cefd45698..8f49507e64ef5ac0091fe22189bea6413e427469 100644 (file)
@@ -40,7 +40,7 @@ static void etap_change(int op, unsigned char *addr, unsigned char *netmask,
                        int fd)
 {
        struct addr_change change;
-       void *output;
+       char *output;
        int n;
 
        change.what = op;
index 6490a4ff40ac458cdd96ee61128aeefb81303a43..6987d1d247a2e7bacf04e2ee72d4f0562f106ccb 100644 (file)
@@ -43,7 +43,7 @@ static int helper_child(void *arg)
                (*data->pre_exec)(data->pre_data);
        execvp(argv[0], argv);
        errval = errno;
-       printk("execvp of '%s' failed - errno = %d\n", argv[0], errno);
+       printk("helper_child - execve of '%s' failed - errno = %d\n", argv[0], errno);
        os_write_file(data->fd, &errval, sizeof(errval));
        kill(os_getpid(), SIGKILL);
        return(0);
@@ -92,15 +92,15 @@ int run_helper(void (*pre_exec)(void *), void *pre_data, char **argv,
        close(fds[1]);
        fds[1] = -1;
 
-       /*Read the errno value from the child.*/
+       /* Read the errno value from the child, if the exec failed, or get 0 if
+        * the exec succeeded because the pipe fd was set as close-on-exec. */
        n = os_read_file(fds[0], &ret, sizeof(ret));
-       if(n < 0){
+       if (n < 0) {
                printk("run_helper : read on pipe failed, ret = %d\n", -n);
                ret = n;
                kill(pid, SIGKILL);
                CATCH_EINTR(waitpid(pid, NULL, 0));
-       }
-       else if(n != 0){
+       } else if(n != 0){
                CATCH_EINTR(n = waitpid(pid, NULL, 0));
                ret = -errno;
        } else {
index 6ab372da96579e4a49e372b920ff302d703484f2..c6432e7292411de1ea2006aabf97a13c3a7fa4eb 100644 (file)
@@ -8,6 +8,7 @@
 #include <fcntl.h>
 #include <sys/types.h>
 #include <sys/mman.h>
+#include <sys/statfs.h>
 #include "kern_util.h"
 #include "user.h"
 #include "user_util.h"
@@ -19,6 +20,7 @@
 
 #include <sys/param.h>
 
+static char *default_tmpdir = "/tmp";
 static char *tempdir = NULL;
 
 static void __init find_tempdir(void)
@@ -34,7 +36,7 @@ static void __init find_tempdir(void)
                        break;
        }
        if((dir == NULL) || (*dir == '\0'))
-               dir = "/tmp";
+               dir = default_tmpdir;
 
        tempdir = malloc(strlen(dir) + 2);
        if(tempdir == NULL){
@@ -46,6 +48,96 @@ static void __init find_tempdir(void)
        strcat(tempdir, "/");
 }
 
+/* This will return 1, with the first character in buf being the
+ * character following the next instance of c in the file.  This will
+ * read the file as needed.  If there's an error, -errno is returned;
+ * if the end of the file is reached, 0 is returned.
+ */
+static int next(int fd, char *buf, int size, char c)
+{
+       int n;
+       char *ptr;
+
+       while((ptr = strchr(buf, c)) == NULL){
+               n = read(fd, buf, size - 1);
+               if(n == 0)
+                       return 0;
+               else if(n < 0)
+                       return -errno;
+
+               buf[n] = '\0';
+       }
+
+       ptr++;
+       memmove(buf, ptr, strlen(ptr) + 1);
+       return 1;
+}
+
+static int checked_tmpdir = 0;
+
+/* Look for a tmpfs mounted at /dev/shm.  I couldn't find a cleaner
+ * way to do this than to parse /proc/mounts.  statfs will return the
+ * same filesystem magic number and fs id for both /dev and /dev/shm
+ * when they are both tmpfs, so you can't tell if they are different
+ * filesystems.  Also, there seems to be no other way of finding the
+ * mount point of a filesystem from within it.
+ *
+ * If a /dev/shm tmpfs entry is found, then we switch to using it.
+ * Otherwise, we stay with the default /tmp.
+ */
+static void which_tmpdir(void)
+{
+       int fd, found;
+       char buf[128] = { '\0' };
+
+       if(checked_tmpdir)
+               return;
+
+       checked_tmpdir = 1;
+
+       printf("Checking for tmpfs mount on /dev/shm...");
+
+       fd = open("/proc/mounts", O_RDONLY);
+       if(fd < 0){
+               printf("failed to open /proc/mounts, errno = %d\n", errno);
+               return;
+       }
+
+       while(1){
+               found = next(fd, buf, sizeof(buf) / sizeof(buf[0]), ' ');
+               if(found != 1)
+                       break;
+
+               if(!strncmp(buf, "/dev/shm", strlen("/dev/shm")))
+                       goto found;
+
+               found = next(fd, buf, sizeof(buf) / sizeof(buf[0]), '\n');
+               if(found != 1)
+                       break;
+       }
+
+err:
+       if(found == 0)
+               printf("nothing mounted on /dev/shm\n");
+       else if(found < 0)
+               printf("read returned errno %d\n", -found);
+
+       return;
+
+found:
+       found = next(fd, buf, sizeof(buf) / sizeof(buf[0]), ' ');
+       if(found != 1)
+               goto err;
+
+       if(strncmp(buf, "tmpfs", strlen("tmpfs"))){
+               printf("not tmpfs\n");
+               return;
+       }
+
+       printf("OK\n");
+       default_tmpdir = "/dev/shm";
+}
+
 /*
  * This proc still used in tt-mode
  * (file: kernel/tt/ptproxy/proxy.c, proc: start_debugger).
@@ -53,33 +145,37 @@ static void __init find_tempdir(void)
  */
 int make_tempfile(const char *template, char **out_tempname, int do_unlink)
 {
-       char tempname[MAXPATHLEN];
+       char *tempname;
        int fd;
 
+       which_tmpdir();
+       tempname = malloc(MAXPATHLEN);
+
        find_tempdir();
-       if (*template != '/')
+       if (template[0] != '/')
                strcpy(tempname, tempdir);
        else
-               *tempname = 0;
+               tempname[0] = '\0';
        strcat(tempname, template);
        fd = mkstemp(tempname);
        if(fd < 0){
                fprintf(stderr, "open - cannot create %s: %s\n", tempname,
                        strerror(errno));
-               return -1;
+               goto out;
        }
        if(do_unlink && (unlink(tempname) < 0)){
                perror("unlink");
-               return -1;
+               goto out;
        }
        if(out_tempname){
-               *out_tempname = strdup(tempname);
-               if(*out_tempname == NULL){
-                       perror("strdup");
-                       return -1;
-               }
+               *out_tempname = tempname;
+       } else {
+               free(tempname);
        }
        return(fd);
+out:
+       free(tempname);
+       return -1;
 }
 
 #define TEMPNAME_TEMPLATE "vm_file-XXXXXX"
@@ -134,3 +230,26 @@ int create_mem_file(unsigned long long len)
        }
        return(fd);
 }
+
+
+void check_tmpexec(void)
+{
+       void *addr;
+       int err, fd = create_tmp_file(UM_KERN_PAGE_SIZE);
+
+       addr = mmap(NULL, UM_KERN_PAGE_SIZE,
+                   PROT_READ | PROT_WRITE | PROT_EXEC, MAP_PRIVATE, fd, 0);
+       printf("Checking PROT_EXEC mmap in %s...",tempdir);
+       fflush(stdout);
+       if(addr == MAP_FAILED){
+               err = errno;
+               perror("failed");
+               if(err == EPERM)
+                       printf("%s must be not mounted noexec\n",tempdir);
+               exit(1);
+       }
+       printf("OK\n");
+       munmap(addr, UM_KERN_PAGE_SIZE);
+
+       close(fd);
+}
index 8176b0b52047061ae681e19d51583f4e683cad97..3505f44f8a25b4d2687327f4844ee61c468752e7 100644 (file)
@@ -190,7 +190,7 @@ int os_unmap_memory(void *addr, int len)
 }
 
 #ifndef MADV_REMOVE
-#define MADV_REMOVE    0x5             /* remove these pages & resources */
+#define MADV_REMOVE KERNEL_MADV_REMOVE
 #endif
 
 int os_drop_memory(void *addr, int length)
@@ -216,7 +216,7 @@ int can_drop_memory(void)
        }
 
        addr = mmap64(NULL, UM_KERN_PAGE_SIZE, PROT_READ | PROT_WRITE,
-                     MAP_PRIVATE, fd, 0);
+                     MAP_SHARED, fd, 0);
        if(addr == MAP_FAILED){
                printk("Mapping test memory file failed, err = %d\n", -errno);
                return 0;
@@ -266,11 +266,11 @@ void init_new_thread_signals(int altstack)
 
 int run_kernel_thread(int (*fn)(void *), void *arg, void **jmp_ptr)
 {
-       sigjmp_buf buf;
+       jmp_buf buf;
        int n, enable;
 
        *jmp_ptr = &buf;
-       n = UML_SIGSETJMP(&buf, enable);
+       n = UML_SETJMP(&buf, enable);
        if(n != 0)
                return(n);
        (*fn)(arg);
index 9ba9429471468ce3f8b338b2c337db3f3bcd26aa..00e9388e947af4fa59442a3fdad627a82b7384e2 100644 (file)
@@ -304,8 +304,8 @@ out_clear_poll:
                                           .size        = 0,
                                           .used        = 0 });
 out_free:
-       kfree(p);
        sigio_unlock();
+       kfree(p);
 out_close2:
        close(l_sigio_private[0]);
        close(l_sigio_private[1]);
index fbb080c2fc261afdf70640e7a00e0c6a951d31ac..b3c11cfa995a7464a991978efdc3388bf9713389 100644 (file)
@@ -82,8 +82,8 @@ static inline long do_syscall_stub(struct mm_id * mm_idp, void **addr)
        if (offset) {
                data = (unsigned long *)(mm_idp->stack +
                                         offset - UML_CONFIG_STUB_DATA);
-               printk("do_syscall_stub : ret = %d, offset = %d, "
-                      "data = 0x%x\n", ret, offset, data);
+               printk("do_syscall_stub : ret = %ld, offset = %ld, "
+                      "data = %p\n", ret, offset, data);
                syscall = (unsigned long *)((unsigned long)data + data[0]);
                printk("do_syscall_stub: syscall %ld failed, return value = "
                       "0x%lx, expected return value = 0x%lx\n",
index bbf34cb91ce18cbea3e088aea56fe6d6edffdff4..0776bc18ca85ebeab95d1f579e244a7b2fe988e8 100644 (file)
@@ -265,7 +265,7 @@ void userspace(union uml_pt_regs *regs)
                if(err)
                        panic("userspace - could not resume userspace process, "
                              "pid=%d, ptrace operation = %d, errno = %d\n",
-                             op, errno);
+                             pid, op, errno);
 
                CATCH_EINTR(err = waitpid(pid, &status, WUNTRACED));
                if(err < 0)
@@ -369,7 +369,7 @@ int copy_context_skas0(unsigned long new_stack, int pid)
         */
        wait_stub_done(pid, -1, "copy_context_skas0");
        if (child_data->err != UML_CONFIG_STUB_DATA)
-               panic("copy_context_skas0 - stub-child reports error %d\n",
+               panic("copy_context_skas0 - stub-child reports error %ld\n",
                      child_data->err);
 
        if (ptrace(PTRACE_OLDSETOPTIONS, pid, NULL,
@@ -434,7 +434,7 @@ void new_thread(void *stack, void **switch_buf_ptr, void **fork_buf_ptr,
                void (*handler)(int))
 {
        unsigned long flags;
-       sigjmp_buf switch_buf, fork_buf;
+       jmp_buf switch_buf, fork_buf;
        int enable;
 
        *switch_buf_ptr = &switch_buf;
@@ -450,7 +450,7 @@ void new_thread(void *stack, void **switch_buf_ptr, void **fork_buf_ptr,
         */
        flags = get_signals();
        block_signals();
-       if(UML_SIGSETJMP(&fork_buf, enable) == 0)
+       if(UML_SETJMP(&fork_buf, enable) == 0)
                new_thread_proc(stack, handler);
 
        remove_sigstack();
@@ -466,35 +466,35 @@ void new_thread(void *stack, void **switch_buf_ptr, void **fork_buf_ptr,
 
 void thread_wait(void *sw, void *fb)
 {
-       sigjmp_buf buf, **switch_buf = sw, *fork_buf;
+       jmp_buf buf, **switch_buf = sw, *fork_buf;
        int enable;
 
        *switch_buf = &buf;
        fork_buf = fb;
-       if(UML_SIGSETJMP(&buf, enable) == 0)
+       if(UML_SETJMP(&buf, enable) == 0)
                siglongjmp(*fork_buf, INIT_JMP_REMOVE_SIGSTACK);
 }
 
 void switch_threads(void *me, void *next)
 {
-       sigjmp_buf my_buf, **me_ptr = me, *next_buf = next;
+       jmp_buf my_buf, **me_ptr = me, *next_buf = next;
        int enable;
 
        *me_ptr = &my_buf;
-       if(UML_SIGSETJMP(&my_buf, enable) == 0)
-               UML_SIGLONGJMP(next_buf, 1);
+       if(UML_SETJMP(&my_buf, enable) == 0)
+               UML_LONGJMP(next_buf, 1);
 }
 
-static sigjmp_buf initial_jmpbuf;
+static jmp_buf initial_jmpbuf;
 
 /* XXX Make these percpu */
 static void (*cb_proc)(void *arg);
 static void *cb_arg;
-static sigjmp_buf *cb_back;
+static jmp_buf *cb_back;
 
 int start_idle_thread(void *stack, void *switch_buf_ptr, void **fork_buf_ptr)
 {
-       sigjmp_buf **switch_buf = switch_buf_ptr;
+       jmp_buf **switch_buf = switch_buf_ptr;
        int n, enable;
 
        set_handler(SIGWINCH, (__sighandler_t) sig_handler,
@@ -502,7 +502,7 @@ int start_idle_thread(void *stack, void *switch_buf_ptr, void **fork_buf_ptr)
                    SIGVTALRM, -1);
 
        *fork_buf_ptr = &initial_jmpbuf;
-       n = UML_SIGSETJMP(&initial_jmpbuf, enable);
+       n = UML_SETJMP(&initial_jmpbuf, enable);
        switch(n){
        case INIT_JMP_NEW_THREAD:
                new_thread_proc((void *) stack, new_thread_handler);
@@ -512,7 +512,7 @@ int start_idle_thread(void *stack, void *switch_buf_ptr, void **fork_buf_ptr)
                break;
        case INIT_JMP_CALLBACK:
                (*cb_proc)(cb_arg);
-               UML_SIGLONGJMP(cb_back, 1);
+               UML_LONGJMP(cb_back, 1);
                break;
        case INIT_JMP_HALT:
                kmalloc_ok = 0;
@@ -523,12 +523,12 @@ int start_idle_thread(void *stack, void *switch_buf_ptr, void **fork_buf_ptr)
        default:
                panic("Bad sigsetjmp return in start_idle_thread - %d\n", n);
        }
-       UML_SIGLONGJMP(*switch_buf, 1);
+       UML_LONGJMP(*switch_buf, 1);
 }
 
 void initial_thread_cb_skas(void (*proc)(void *), void *arg)
 {
-       sigjmp_buf here;
+       jmp_buf here;
        int enable;
 
        cb_proc = proc;
@@ -536,8 +536,8 @@ void initial_thread_cb_skas(void (*proc)(void *), void *arg)
        cb_back = &here;
 
        block_signals();
-       if(UML_SIGSETJMP(&here, enable) == 0)
-               UML_SIGLONGJMP(&initial_jmpbuf, INIT_JMP_CALLBACK);
+       if(UML_SETJMP(&here, enable) == 0)
+               UML_LONGJMP(&initial_jmpbuf, INIT_JMP_CALLBACK);
        unblock_signals();
 
        cb_proc = NULL;
@@ -548,13 +548,13 @@ void initial_thread_cb_skas(void (*proc)(void *), void *arg)
 void halt_skas(void)
 {
        block_signals();
-       UML_SIGLONGJMP(&initial_jmpbuf, INIT_JMP_HALT);
+       UML_LONGJMP(&initial_jmpbuf, INIT_JMP_HALT);
 }
 
 void reboot_skas(void)
 {
        block_signals();
-       UML_SIGLONGJMP(&initial_jmpbuf, INIT_JMP_REBOOT);
+       UML_LONGJMP(&initial_jmpbuf, INIT_JMP_REBOOT);
 }
 
 void switch_mm_skas(struct mm_id *mm_idp)
index 387e26af301a57c6ca0a861c654727af7a5b3696..5031485040090bfc07ba71eca0a41564c0cc8b03 100644 (file)
@@ -296,29 +296,7 @@ static void __init check_ptrace(void)
        check_sysemu();
 }
 
-extern int create_tmp_file(unsigned long long len);
-
-static void check_tmpexec(void)
-{
-       void *addr;
-       int err, fd = create_tmp_file(UM_KERN_PAGE_SIZE);
-
-       addr = mmap(NULL, UM_KERN_PAGE_SIZE,
-                   PROT_READ | PROT_WRITE | PROT_EXEC, MAP_PRIVATE, fd, 0);
-       printf("Checking PROT_EXEC mmap in /tmp...");
-       fflush(stdout);
-       if(addr == MAP_FAILED){
-               err = errno;
-               perror("failed");
-               if(err == EPERM)
-                       printf("/tmp must be not mounted noexec\n");
-               exit(1);
-       }
-       printf("OK\n");
-       munmap(addr, UM_KERN_PAGE_SIZE);
-
-       close(fd);
-}
+extern void check_tmpexec(void);
 
 void os_early_checks(void)
 {
index ba21f0e04a2f3f28fa9a9f11e8934d64684d827e..120abbe4e3ce2916d7d20eb7680dcdfd2a8c0baa 100644 (file)
@@ -1,3 +1,4 @@
+#include <errno.h>
 #include <linux/unistd.h>
 #include "sysdep/tls.h"
 #include "user_util.h"
index a9f6b26f9828f8f4c0a99bc6a2f8449054be8bb8..90b29ae9af46158ed52154d7e77ce1c4b100f83f 100644 (file)
@@ -35,7 +35,7 @@ void os_fill_handlinfo(struct kern_handlers h)
 
 void do_longjmp(void *b, int val)
 {
-       sigjmp_buf *buf = b;
+       jmp_buf *buf = b;
 
-       UML_SIGLONGJMP(buf, val);
+       UML_LONGJMP(buf, val);
 }
index 166fb66995df87e58793c6f99a33334324eaddce..e523719330b27cb2b0a29bd1dacbf15bc8b1ca05 100644 (file)
@@ -16,9 +16,9 @@ unsigned long __do_user_copy(void *to, const void *from, int n,
        unsigned long *faddrp = (unsigned long *) fault_addr, ret;
        int enable;
 
-       sigjmp_buf jbuf;
+       jmp_buf jbuf;
        *fault_catcher = &jbuf;
-       if(UML_SIGSETJMP(&jbuf, enable) == 0){
+       if(UML_SETJMP(&jbuf, enable) == 0){
                (*op)(to, from, n);
                ret = 0;
                *faulted_out = 0;
index 198e591632887ce4b7abc0c9a39cfbd3b41c25c4..34bfc1bb9e38665f604b3b14c9521010b078a40f 100644 (file)
@@ -120,7 +120,8 @@ static int not_dead_yet(char *dir)
 
        dead = 0;
        fd = open(file, O_RDONLY);
-       if(fd < 0){
+       if(fd < 0) {
+               fd = -errno;
                if(fd != -ENOENT){
                        printk("not_dead_yet : couldn't open pid file '%s', "
                               "err = %d\n", file, -fd);
@@ -130,9 +131,13 @@ static int not_dead_yet(char *dir)
 
        err = 0;
        n = read(fd, pid, sizeof(pid));
-       if(n <= 0){
+       if(n < 0){
+               printk("not_dead_yet : couldn't read pid file '%s', "
+                      "err = %d\n", file, errno);
+               goto out_close;
+       } else if(n == 0){
                printk("not_dead_yet : couldn't read pid file '%s', "
-                      "err = %d\n", file, -n);
+                      "0-byte read\n", file);
                goto out_close;
        }
 
@@ -155,9 +160,9 @@ static int not_dead_yet(char *dir)
 
        return err;
 
- out_close:
+out_close:
        close(fd);
- out:
+out:
        return 0;
 }
 
index 8da6ab31152ad47918fa75bfa73437859e01eebe..2598158e1f53a30fff62dc85c24f474c89cfe890 100644 (file)
@@ -18,14 +18,19 @@ extern void *memmove(void *, const void *, size_t);
 extern void *memset(void *, int, size_t);
 extern int printf(const char *, ...);
 
+/* If they're not defined, the export is included in lib/string.c.*/
+#ifdef __HAVE_ARCH_STRLEN
 EXPORT_SYMBOL(strlen);
+#endif
+#ifdef __HAVE_ARCH_STRSTR
+EXPORT_SYMBOL(strstr);
+#endif
+
 EXPORT_SYMBOL(memcpy);
 EXPORT_SYMBOL(memmove);
 EXPORT_SYMBOL(memset);
 EXPORT_SYMBOL(printf);
 
-EXPORT_SYMBOL(strstr);
-
 /* Here, instead, I can provide a fake prototype. Yes, someone cares: genksyms.
  * However, the modules will use the CRC defined *here*, no matter if it is
  * good; so the versions of these symbols will always match
index e32065e2fdc80d7203a817d8708e3d3cbed845be..c47a2a7ce70e75614e425e7270b2e1364188b67d 100644 (file)
@@ -104,7 +104,7 @@ void setup_hostinfo(void)
 int setjmp_wrapper(void (*proc)(void *, void *), ...)
 {
        va_list args;
-       sigjmp_buf buf;
+       jmp_buf buf;
        int n;
 
        n = sigsetjmp(buf, 1);
index b696b451774cf7276c1496562fc8cd94ec4aa1e9..5e7a9c310aa50898a33d99d36756039df7c7f57d 100644 (file)
@@ -9,10 +9,8 @@ USER_OBJS := $(foreach file,$(USER_OBJS),$(obj)/$(file))
 
 $(USER_OBJS) $(USER_OBJS:.o=.i) $(USER_OBJS:.o=.s) $(USER_OBJS:.o=.lst): \
        c_flags = -Wp,-MD,$(depfile) $(USER_CFLAGS) $(CFLAGS_$(notdir $@))
-$(USER_OBJS): cmd_checksrc =
-$(USER_OBJS): quiet_cmd_checksrc =
-$(USER_OBJS): cmd_force_checksrc =
-$(USER_OBJS): quiet_cmd_force_checksrc =
+$(USER_OBJS) : CHECKFLAGS := -D__linux__ -Dlinux -D__STDC__ \
+       -Dunix -D__unix__ -D__$(SUBARCH)__
 
 
 # The stubs and unmap.o can't try to call mcount or update basic block data
index db524ab3f743a47f9d5a1b555c0efb48523dafc3..2a1eac1859ce75d8ac0725162259b1e8449ba087 100644 (file)
@@ -15,7 +15,3 @@ EXPORT_SYMBOL(__up_wakeup);
 
 /* Networking helper routines. */
 EXPORT_SYMBOL(csum_partial);
-
-/* delay core functions */
-EXPORT_SYMBOL(__const_udelay);
-EXPORT_SYMBOL(__udelay);
index 9f3bd8ed78f5b2d7cc47380227051327aad98e3b..40aa885314469f40bee2ee2a3ae171becbc0840c 100644 (file)
@@ -57,7 +57,7 @@ static void write_debugregs(int pid, unsigned long *regs)
                if(ptrace(PTRACE_POKEUSR, pid, &dummy->u_debugreg[i],
                          regs[i]) < 0)
                        printk("write_debugregs - ptrace failed on "
-                              "register %d, value = 0x%x, errno = %d\n", i,
+                              "register %d, value = 0x%lx, errno = %d\n", i,
                               regs[i], errno);
        }
 }
index f5d0e1c37ea263950d03d33a6edb50ce0966da81..0709fc6670c287ab4b3bf2323792ebc19e4a0873 100644 (file)
@@ -57,7 +57,7 @@ static int copy_sc_from_user_skas(struct pt_regs *regs,
        return(0);
 }
 
-int copy_sc_to_user_skas(struct sigcontext *to, struct _fpstate __user *to_fp,
+int copy_sc_to_user_skas(struct sigcontext __user *to, struct _fpstate __user *to_fp,
                          struct pt_regs *regs, unsigned long sp)
 {
        struct sigcontext sc;
@@ -132,7 +132,7 @@ int copy_sc_from_user_tt(struct sigcontext *to, struct sigcontext __user *from,
        return(err);
 }
 
-int copy_sc_to_user_tt(struct sigcontext *to, struct _fpstate __user *fp,
+int copy_sc_to_user_tt(struct sigcontext __user *to, struct _fpstate __user *fp,
                       struct sigcontext *from, int fpsize, unsigned long sp)
 {
        struct _fpstate __user *to_fp;
@@ -147,7 +147,7 @@ int copy_sc_to_user_tt(struct sigcontext *to, struct _fpstate __user *fp,
         * delivery.  The sp passed in is the original, and this needs
         * to be restored, so we stick it in separately.
         */
-       err |= copy_to_user(&SC_SP(to), sp, sizeof(sp));
+       err |= copy_to_user(&SC_SP(to), &sp, sizeof(sp));
 
        if(from_fp != NULL){
                err |= copy_to_user(&to->fpstate, &to_fp, sizeof(to->fpstate));
@@ -167,7 +167,7 @@ static int copy_sc_from_user(struct pt_regs *to, void __user *from)
        return(ret);
 }
 
-static int copy_sc_to_user(struct sigcontext *to, struct _fpstate __user *fp,
+static int copy_sc_to_user(struct sigcontext __user *to, struct _fpstate __user *fp,
                           struct pt_regs *from, unsigned long sp)
 {
        return(CHOOSE_MODE(copy_sc_to_user_tt(to, fp, UPT_SC(&from->regs),
index a37f672ec964e3815c4f2de247b82d7d09dc1e30..2355dc19c46c544db5627b4e6f678903a23a5a0c 100644 (file)
@@ -27,6 +27,6 @@ stub_segv_handler(int sig)
         * the stack in its original form when we do the sigreturn here, by
         * hand.
         */
-       __asm__("mov %0,%%esp ; movl %1, %%eax ; "
-               "int $0x80" : : "a" (sc), "g" (__NR_sigreturn));
+       __asm__ __volatile__("mov %0,%%esp ; movl %1, %%eax ; "
+                            "int $0x80" : : "a" (sc), "g" (__NR_sigreturn));
 }
index a3188e861cc7f9eba6efbc3c08765800e2cb06b3..71b9796258ef650dc008a5b45a7965fbc8e873aa 100644 (file)
@@ -378,7 +378,7 @@ static int __init __setup_host_supports_tls(void) {
        } else
                printk(KERN_ERR "  Host TLS support NOT detected! "
                                "TLS support inside UML will not work\n");
-       return 1;
+       return 0;
 }
 
 __initcall(__setup_host_supports_tls);
index e75c4e1838b0dacedf88ffcd79e31ce44e9cad1d..a4c46a8af00842078fb03e2f36592f4706abf49c 100644 (file)
@@ -137,7 +137,7 @@ int copy_sc_to_user_tt(struct sigcontext *to, struct _fpstate *fp,
         * delivery.  The sp passed in is the original, and this needs
         * to be restored, so we stick it in separately.
         */
-       err |= copy_to_user(&SC_SP(to), sp, sizeof(sp));
+       err |= copy_to_user(&SC_SP(to), &sp, sizeof(sp));
 
        if(from_fp != NULL){
                err |= copy_to_user(&to->fpstate, &to_fp, sizeof(to->fpstate));
index a27099533198573d223f54a94134b84f8b7b7674..1c967026c957dd08e4b81406a82712b60ada8ee6 100644 (file)
@@ -33,7 +33,7 @@ stub_segv_handler(int sig)
        struct ucontext *uc;
         int pid;
 
-       __asm__("movq %%rdx, %0" : "=g" (uc) :);
+       __asm__ __volatile__("movq %%rdx, %0" : "=g" (uc) :);
        GET_FAULTINFO_FROM_SC(*((struct faultinfo *) UML_CONFIG_STUB_DATA),
                              &uc->uc_mcontext);
 
@@ -44,8 +44,8 @@ stub_segv_handler(int sig)
         * the signal frame.  So, we use the ucontext pointer, which we know
         * already, to get the signal frame pointer, and add 8 to that.
         */
-       __asm__("movq %0, %%rsp; movq %1, %%rax ; syscall": :
-               "g" ((unsigned long) container_of(uc, struct rt_sigframe, 
-                                                 uc) + 8),
-                "g" (__NR_rt_sigreturn));
+       __asm__ __volatile__("movq %0, %%rsp; movq %1, %%rax ; syscall": :
+                             "g" ((unsigned long)
+                                  container_of(uc, struct rt_sigframe, uc) + 8),
+                             "g" (__NR_rt_sigreturn));
 }
index 8ffc29c1c89df749f71e0d3954e01642ede3770d..6bcfcfe88384b7d0a573f496d1f2afedd5e2f99e 100644 (file)
@@ -43,7 +43,6 @@ EXPORT_SYMBOL (strncmp);
 EXPORT_SYMBOL (strchr);
 EXPORT_SYMBOL (strlen);
 EXPORT_SYMBOL (strnlen);
-EXPORT_SYMBOL (strpbrk);
 EXPORT_SYMBOL (strrchr);
 EXPORT_SYMBOL (strstr);
 EXPORT_SYMBOL (memset);
index 4310b4a311a55a79326169751c93b3362d348b6f..408d44a59756f8050c4455fdbb471eb9c9881f09 100644 (file)
@@ -136,6 +136,11 @@ config X86_L1_CACHE_SHIFT
        default "7" if GENERIC_CPU || MPSC
        default "6" if MK8
 
+config X86_INTERNODE_CACHE_BYTES
+       int
+       default "4096" if X86_VSMP
+       default X86_L1_CACHE_BYTES if !X86_VSMP
+
 config X86_TSC
        bool
        default y
@@ -283,6 +288,11 @@ config K8_NUMA
         Northbridge of Opteron. It is recommended to use X86_64_ACPI_NUMA
         instead, which also takes priority if both are compiled in.   
 
+config NODES_SHIFT
+       int
+       default "6"
+       depends on NEED_MULTIPLE_NODES
+
 # Dummy CONFIG option to select ACPI_NUMA from drivers/acpi/Kconfig.
 
 config X86_64_ACPI_NUMA
index 585fd4a559c8792e20150c25339eb8d58aaea9db..e573e2ab55108fe2d2acf73fe16c950cc1b6b416 100644 (file)
 LDFLAGS                := -m elf_x86_64
 OBJCOPYFLAGS   := -O binary -R .note -R .comment -S
 LDFLAGS_vmlinux :=
-
 CHECKFLAGS      += -D__x86_64__ -m64
 
+cflags-y       :=
 cflags-$(CONFIG_MK8) += $(call cc-option,-march=k8)
 cflags-$(CONFIG_MPSC) += $(call cc-option,-march=nocona)
 cflags-$(CONFIG_GENERIC_CPU) += $(call cc-option,-mtune=generic)
-CFLAGS += $(cflags-y)
 
-CFLAGS += -m64
-CFLAGS += -mno-red-zone
-CFLAGS += -mcmodel=kernel
-CFLAGS += -pipe
+cflags-y += -m64
+cflags-y += -mno-red-zone
+cflags-y += -mcmodel=kernel
+cflags-y += -pipe
 cflags-$(CONFIG_REORDER) += -ffunction-sections
 # this makes reading assembly source easier, but produces worse code
 # actually it makes the kernel smaller too.
-CFLAGS += -fno-reorder-blocks  
-CFLAGS += -Wno-sign-compare
+cflags-y += -fno-reorder-blocks
+cflags-y += -Wno-sign-compare
 ifneq ($(CONFIG_UNWIND_INFO),y)
-CFLAGS += -fno-asynchronous-unwind-tables
+cflags-y += -fno-asynchronous-unwind-tables
 endif
 ifneq ($(CONFIG_DEBUG_INFO),y)
 # -fweb shrinks the kernel a bit, but the difference is very small
 # it also messes up debugging, so don't use it for now.
-#CFLAGS += $(call cc-option,-fweb)
+#cflags-y += $(call cc-option,-fweb)
 endif
 # -funit-at-a-time shrinks the kernel .text considerably
 # unfortunately it makes reading oopses harder.
-CFLAGS += $(call cc-option,-funit-at-a-time)
+cflags-y += $(call cc-option,-funit-at-a-time)
 # prevent gcc from generating any FP code by mistake
-CFLAGS += $(call cc-option,-mno-sse -mno-mmx -mno-sse2 -mno-3dnow,)
+cflags-y += $(call cc-option,-mno-sse -mno-mmx -mno-sse2 -mno-3dnow,)
 
+CFLAGS += $(cflags-y)
 AFLAGS += -m64
 
 head-y := arch/x86_64/kernel/head.o arch/x86_64/kernel/head64.o arch/x86_64/kernel/init_task.o
index 0587477c99f2f32afa73a4dc10cf48e4ecb757d7..32327bb37aff863323e0602a1d070cd6be0435f2 100644 (file)
@@ -97,6 +97,7 @@
 #define PARAM_VESAPM_OFF       0x30
 #define PARAM_LFB_PAGES                0x32
 #define PARAM_VESA_ATTRIB      0x34
+#define PARAM_CAPABILITIES     0x36
 
 /* Define DO_STORE according to CONFIG_VIDEO_RETAIN */
 #ifdef CONFIG_VIDEO_RETAIN
@@ -233,6 +234,10 @@ mopar_gr:
        movw    18(%di), %ax
        movl    %eax, %fs:(PARAM_LFB_SIZE)
 
+# store mode capabilities
+       movl 10(%di), %eax
+       movl %eax, %fs:(PARAM_CAPABILITIES)
+
 # switching the DAC to 8-bit is for <= 8 bpp only
        movw    %fs:(PARAM_LFB_DEPTH), %ax
        cmpw    $8, %ax
index 566ecc97ee5a1132ce9bef52e637f0d42e404a2f..69db0c0721d1c4835ff02fed98ff662c0db1665c 100644 (file)
@@ -1,7 +1,7 @@
 #
 # Automatically generated make config: don't edit
-# Linux kernel version: 2.6.16-git9
-# Sat Mar 25 15:18:40 2006
+# Linux kernel version: 2.6.17-rc1-git11
+# Sun Apr 16 07:22:36 2006
 #
 CONFIG_X86_64=y
 CONFIG_64BIT=y
@@ -9,6 +9,7 @@ CONFIG_X86=y
 CONFIG_SEMAPHORE_SLEEPERS=y
 CONFIG_MMU=y
 CONFIG_RWSEM_GENERIC_SPINLOCK=y
+CONFIG_GENERIC_HWEIGHT=y
 CONFIG_GENERIC_CALIBRATE_DELAY=y
 CONFIG_X86_CMPXCHG=y
 CONFIG_EARLY_PRINTK=y
@@ -55,11 +56,8 @@ CONFIG_BASE_FULL=y
 CONFIG_FUTEX=y
 CONFIG_EPOLL=y
 CONFIG_SHMEM=y
-CONFIG_CC_ALIGN_FUNCTIONS=0
-CONFIG_CC_ALIGN_LABELS=0
-CONFIG_CC_ALIGN_LOOPS=0
-CONFIG_CC_ALIGN_JUMPS=0
 CONFIG_SLAB=y
+CONFIG_DOUBLEFAULT=y
 # CONFIG_TINY_SHMEM is not set
 CONFIG_BASE_SMALL=0
 # CONFIG_SLOB is not set
@@ -70,7 +68,6 @@ CONFIG_BASE_SMALL=0
 CONFIG_MODULES=y
 CONFIG_MODULE_UNLOAD=y
 CONFIG_MODULE_FORCE_UNLOAD=y
-CONFIG_OBSOLETE_MODPARM=y
 # CONFIG_MODVERSIONS is not set
 # CONFIG_MODULE_SRCVERSION_ALL is not set
 # CONFIG_KMOD is not set
@@ -81,6 +78,7 @@ CONFIG_STOP_MACHINE=y
 #
 CONFIG_LBD=y
 # CONFIG_BLK_DEV_IO_TRACE is not set
+# CONFIG_LSF is not set
 
 #
 # IO Schedulers
@@ -105,6 +103,7 @@ CONFIG_X86_PC=y
 CONFIG_GENERIC_CPU=y
 CONFIG_X86_L1_CACHE_BYTES=128
 CONFIG_X86_L1_CACHE_SHIFT=7
+CONFIG_X86_INTERNODE_CACHE_BYTES=128
 CONFIG_X86_TSC=y
 CONFIG_X86_GOOD_APIC=y
 # CONFIG_MICROCODE is not set
@@ -116,12 +115,14 @@ CONFIG_X86_LOCAL_APIC=y
 CONFIG_MTRR=y
 CONFIG_SMP=y
 CONFIG_SCHED_SMT=y
+CONFIG_SCHED_MC=y
 # CONFIG_PREEMPT_NONE is not set
 CONFIG_PREEMPT_VOLUNTARY=y
 # CONFIG_PREEMPT is not set
 CONFIG_PREEMPT_BKL=y
 CONFIG_NUMA=y
 CONFIG_K8_NUMA=y
+CONFIG_NODES_SHIFT=6
 CONFIG_X86_64_ACPI_NUMA=y
 CONFIG_NUMA_EMU=y
 CONFIG_ARCH_DISCONTIGMEM_ENABLE=y
@@ -138,6 +139,7 @@ CONFIG_NEED_MULTIPLE_NODES=y
 CONFIG_SPLIT_PTLOCK_CPUS=4
 CONFIG_MIGRATION=y
 CONFIG_HAVE_ARCH_EARLY_PFN_TO_NID=y
+CONFIG_OUT_OF_LINE_PFN_TO_PAGE=y
 CONFIG_NR_CPUS=32
 CONFIG_HOTPLUG_CPU=y
 CONFIG_HPET_TIMER=y
@@ -289,6 +291,7 @@ CONFIG_IP_PNP_DHCP=y
 # CONFIG_INET_AH is not set
 # CONFIG_INET_ESP is not set
 # CONFIG_INET_IPCOMP is not set
+# CONFIG_INET_XFRM_TUNNEL is not set
 # CONFIG_INET_TUNNEL is not set
 CONFIG_INET_DIAG=y
 CONFIG_INET_TCP_DIAG=y
@@ -300,6 +303,7 @@ CONFIG_IPV6=y
 # CONFIG_INET6_AH is not set
 # CONFIG_INET6_ESP is not set
 # CONFIG_INET6_IPCOMP is not set
+# CONFIG_INET6_XFRM_TUNNEL is not set
 # CONFIG_INET6_TUNNEL is not set
 # CONFIG_IPV6_TUNNEL is not set
 # CONFIG_NETFILTER is not set
@@ -542,7 +546,6 @@ CONFIG_SCSI_SATA_INTEL_COMBINED=y
 # CONFIG_SCSI_INIA100 is not set
 # CONFIG_SCSI_SYM53C8XX_2 is not set
 # CONFIG_SCSI_IPR is not set
-# CONFIG_SCSI_QLOGIC_FC is not set
 # CONFIG_SCSI_QLOGIC_1280 is not set
 # CONFIG_SCSI_QLA_FC is not set
 # CONFIG_SCSI_LPFC is not set
@@ -704,7 +707,6 @@ CONFIG_S2IO=m
 # Wireless LAN (non-hamradio)
 #
 # CONFIG_NET_RADIO is not set
-# CONFIG_NET_WIRELESS_RTNETLINK is not set
 
 #
 # Wan interfaces
@@ -791,7 +793,7 @@ CONFIG_HW_CONSOLE=y
 #
 CONFIG_SERIAL_8250=y
 CONFIG_SERIAL_8250_CONSOLE=y
-# CONFIG_SERIAL_8250_ACPI is not set
+CONFIG_SERIAL_8250_PCI=y
 CONFIG_SERIAL_8250_NR_UARTS=4
 CONFIG_SERIAL_8250_RUNTIME_UARTS=4
 # CONFIG_SERIAL_8250_EXTENDED is not set
@@ -921,6 +923,7 @@ CONFIG_HWMON=y
 # Digital Video Broadcasting Devices
 #
 # CONFIG_DVB is not set
+# CONFIG_USB_DABUSB is not set
 
 #
 # Graphics support
@@ -932,6 +935,8 @@ CONFIG_VIDEO_SELECT=y
 # Console display driver support
 #
 CONFIG_VGA_CONSOLE=y
+CONFIG_VGACON_SOFT_SCROLLBACK=y
+CONFIG_VGACON_SOFT_SCROLLBACK_SIZE=256
 CONFIG_DUMMY_CONSOLE=y
 
 #
@@ -1041,9 +1046,7 @@ CONFIG_USB_HIDINPUT=y
 # CONFIG_USB_ACECAD is not set
 # CONFIG_USB_KBTAB is not set
 # CONFIG_USB_POWERMATE is not set
-# CONFIG_USB_MTOUCH is not set
-# CONFIG_USB_ITMTOUCH is not set
-# CONFIG_USB_EGALAX is not set
+# CONFIG_USB_TOUCHSCREEN is not set
 # CONFIG_USB_YEALINK is not set
 # CONFIG_USB_XPAD is not set
 # CONFIG_USB_ATI_REMOTE is not set
@@ -1057,15 +1060,6 @@ CONFIG_USB_HIDINPUT=y
 # CONFIG_USB_MDC800 is not set
 # CONFIG_USB_MICROTEK is not set
 
-#
-# USB Multimedia devices
-#
-# CONFIG_USB_DABUSB is not set
-
-#
-# Video4Linux support is needed for USB Multimedia device support
-#
-
 #
 # USB Network Adapters
 #
@@ -1117,16 +1111,35 @@ CONFIG_USB_MON=y
 #
 # CONFIG_MMC is not set
 
+#
+# LED devices
+#
+# CONFIG_NEW_LEDS is not set
+
+#
+# LED drivers
+#
+
+#
+# LED Triggers
+#
+
 #
 # InfiniBand support
 #
 # CONFIG_INFINIBAND is not set
+# CONFIG_IPATH_CORE is not set
 
 #
 # EDAC - error detection and reporting (RAS) (EXPERIMENTAL)
 #
 # CONFIG_EDAC is not set
 
+#
+# Real Time Clock
+#
+# CONFIG_RTC_CLASS is not set
+
 #
 # Firmware Drivers
 #
index 35b2faccdc6c28af5169f0e02d4a060acc4e2133..57fc37e0fb9c16d044156749c31157ef85a6302b 100644 (file)
@@ -15,6 +15,8 @@
 #include <asm/vsyscall32.h>
 #include <linux/linkage.h>
 
+#define IA32_NR_syscalls ((ia32_syscall_end - ia32_sys_call_table)/8)
+
        .macro IA32_ARG_FIXUP noebp=0
        movl    %edi,%r8d
        .if \noebp
@@ -109,8 +111,8 @@ ENTRY(ia32_sysenter_target)
        CFI_REMEMBER_STATE
        jnz  sysenter_tracesys
 sysenter_do_call:      
-       cmpl    $(IA32_NR_syscalls),%eax
-       jae     ia32_badsys
+       cmpl    $(IA32_NR_syscalls-1),%eax
+       ja      ia32_badsys
        IA32_ARG_FIXUP 1
        call    *ia32_sys_call_table(,%rax,8)
        movq    %rax,RAX-ARGOFFSET(%rsp)
@@ -210,8 +212,8 @@ ENTRY(ia32_cstar_target)
        CFI_REMEMBER_STATE
        jnz   cstar_tracesys
 cstar_do_call: 
-       cmpl $IA32_NR_syscalls,%eax
-       jae  ia32_badsys
+       cmpl $IA32_NR_syscalls-1,%eax
+       ja  ia32_badsys
        IA32_ARG_FIXUP 1
        call *ia32_sys_call_table(,%rax,8)
        movq %rax,RAX-ARGOFFSET(%rsp)
@@ -296,8 +298,8 @@ ENTRY(ia32_syscall)
        testl $(_TIF_SYSCALL_TRACE|_TIF_SYSCALL_AUDIT|_TIF_SECCOMP),threadinfo_flags(%r10)
        jnz ia32_tracesys
 ia32_do_syscall:       
-       cmpl $(IA32_NR_syscalls),%eax
-       jae  ia32_badsys
+       cmpl $(IA32_NR_syscalls-1),%eax
+       ja  ia32_badsys
        IA32_ARG_FIXUP
        call *ia32_sys_call_table(,%rax,8) # xxx: rip relative
 ia32_sysret:
@@ -685,12 +687,12 @@ ia32_sys_call_table:
        .quad sys_readlinkat            /* 305 */
        .quad sys_fchmodat
        .quad sys_faccessat
-       .quad sys_ni_syscall            /* pselect6 for now */
-       .quad sys_ni_syscall            /* ppoll for now */
+       .quad quiet_ni_syscall          /* pselect6 for now */
+       .quad quiet_ni_syscall          /* ppoll for now */
        .quad sys_unshare               /* 310 */
        .quad compat_sys_set_robust_list
        .quad compat_sys_get_robust_list
+       .quad sys_splice
+       .quad sys_sync_file_range
+       .quad sys_tee
 ia32_syscall_end:              
-       .rept IA32_NR_syscalls-(ia32_syscall_end-ia32_sys_call_table)/8
-               .quad ni_syscall
-       .endr
index a098a11e7755f38cba1b5751b26e9d10e98bc8a8..059c88313f4e03bde89e25835950bf4558acd611 100644 (file)
@@ -8,7 +8,7 @@ obj-y   := process.o signal.o entry.o traps.o irq.o \
                ptrace.o time.o ioport.o ldt.o setup.o i8259.o sys_x86_64.o \
                x8664_ksyms.o i387.o syscall.o vsyscall.o \
                setup64.o bootflag.o e820.o reboot.o quirks.o i8237.o \
-               dmi_scan.o pci-dma.o pci-nommu.o
+               pci-dma.o pci-nommu.o
 
 obj-$(CONFIG_X86_MCE)         += mce.o
 obj-$(CONFIG_X86_MCE_INTEL)    += mce_intel.o
@@ -49,5 +49,3 @@ intel_cacheinfo-y             += ../../i386/kernel/cpu/intel_cacheinfo.o
 quirks-y                       += ../../i386/kernel/quirks.o
 i8237-y                                += ../../i386/kernel/i8237.o
 msr-$(subst m,y,$(CONFIG_X86_MSR))  += ../../i386/kernel/msr.o
-dmi_scan-y                     += ../../i386/kernel/dmi_scan.o
-
index fffd6b0a2fab9f8e160b09e1c8b69e3a85610bdc..70b9d21ed675b1aabe1874d785fa5f0b98e3b87d 100644 (file)
@@ -80,7 +80,7 @@ static int __init aperture_valid(char *name, u64 aper_base, u32 aper_size)
                printk("Aperture from %s beyond 4GB. Ignoring.\n",name);
                return 0; 
        }
-       if (e820_mapped(aper_base, aper_base + aper_size, E820_RAM)) {  
+       if (e820_any_mapped(aper_base, aper_base + aper_size, E820_RAM)) {
                printk("Aperture from %s pointing to e820 RAM. Ignoring.\n",name);
                return 0; 
        } 
index 293cd71a266aa221800c6e3246ee768cce5a71cd..62776c07cff15deec7f772096ddf51693ba2303e 100644 (file)
@@ -80,7 +80,12 @@ static inline int bad_addr(unsigned long *addrp, unsigned long size)
        return 0;
 } 
 
-int __init e820_mapped(unsigned long start, unsigned long end, unsigned type) 
+/*
+ * This function checks if any part of the range <start,end> is mapped
+ * with type.
+ */
+int __meminit
+e820_any_mapped(unsigned long start, unsigned long end, unsigned type)
 { 
        int i;
        for (i = 0; i < e820.nr_map; i++) { 
@@ -94,6 +99,35 @@ int __init e820_mapped(unsigned long start, unsigned long end, unsigned type)
        return 0;
 }
 
+/*
+ * This function checks if the entire range <start,end> is mapped with type.
+ *
+ * Note: this function only works correct if the e820 table is sorted and
+ * not-overlapping, which is the case
+ */
+int __init e820_all_mapped(unsigned long start, unsigned long end, unsigned type)
+{
+       int i;
+       for (i = 0; i < e820.nr_map; i++) {
+               struct e820entry *ei = &e820.map[i];
+               if (type && ei->type != type)
+                       continue;
+               /* is the region (part) in overlap with the current region ?*/
+               if (ei->addr >= end || ei->addr + ei->size <= start)
+                       continue;
+
+               /* if the region is at the beginning of <start,end> we move
+                * start to the end of the region since it's ok until there
+                */
+               if (ei->addr <= start)
+                       start = ei->addr + ei->size;
+               /* if start is now at or beyond end, we're done, full coverage */
+               if (start >= end)
+                       return 1; /* we're done */
+       }
+       return 0;
+}
+
 /* 
  * Find a free area in a specific range. 
  */ 
index 8538bfea30e6b7841904387f45e8c72e49599413..c946e4fe67a7937ab15eba697246602c7dc67dbd 100644 (file)
@@ -180,6 +180,10 @@ rff_trace:
  *
  * XXX if we had a free scratch register we could save the RSP into the stack frame
  *      and report it properly in ps. Unfortunately we haven't.
+ *
+ * When user can change the frames always force IRET. That is because
+ * it deals with uncanonical addresses better. SYSRET has trouble
+ * with them due to bugs in both AMD and Intel CPUs.
  */                                    
 
 ENTRY(system_call)
@@ -254,7 +258,10 @@ sysret_signal:
        xorl %esi,%esi # oldset -> arg2
        call ptregscall_common
 1:     movl $_TIF_NEED_RESCHED,%edi
-       jmp sysret_check
+       /* Use IRET because user could have changed frame. This
+          works because ptregscall_common has called FIXUP_TOP_OF_STACK. */
+       cli
+       jmp int_with_check
        
 badsys:
        movq $-ENOSYS,RAX-ARGOFFSET(%rsp)
@@ -280,7 +287,8 @@ tracesys:
        call syscall_trace_leave
        RESTORE_TOP_OF_STACK %rbx
        RESTORE_REST
-       jmp ret_from_sys_call
+       /* Use IRET because user could have changed frame */
+       jmp int_ret_from_sys_call
        CFI_ENDPROC
                
 /* 
@@ -408,25 +416,9 @@ ENTRY(stub_execve)
        CFI_ADJUST_CFA_OFFSET -8
        CFI_REGISTER rip, r11
        SAVE_REST
-       movq %r11, %r15
-       CFI_REGISTER rip, r15
        FIXUP_TOP_OF_STACK %r11
        call sys_execve
-       GET_THREAD_INFO(%rcx)
-       bt $TIF_IA32,threadinfo_flags(%rcx)
-       CFI_REMEMBER_STATE
-       jc exec_32bit
        RESTORE_TOP_OF_STACK %r11
-       movq %r15, %r11
-       CFI_REGISTER rip, r11
-       RESTORE_REST
-       pushq %r11
-       CFI_ADJUST_CFA_OFFSET 8
-       CFI_REL_OFFSET rip, 0
-       ret
-
-exec_32bit:
-       CFI_RESTORE_STATE
        movq %rax,RAX(%rsp)
        RESTORE_REST
        jmp int_ret_from_sys_call
index accbff3fec491826071ad572c19d0207413a1bca..1eaa5dae6174ff57b514a56828f07e6f8ed0a149 100644 (file)
@@ -53,7 +53,7 @@ DEFINE_PER_CPU(struct kprobe_ctlblk, kprobe_ctlblk);
 /*
  * returns non-zero if opcode modifies the interrupt flag.
  */
-static inline int is_IF_modifier(kprobe_opcode_t *insn)
+static __always_inline int is_IF_modifier(kprobe_opcode_t *insn)
 {
        switch (*insn) {
        case 0xfa:              /* cli */
@@ -84,7 +84,7 @@ int __kprobes arch_prepare_kprobe(struct kprobe *p)
  * If it does, return the address of the 32-bit displacement word.
  * If not, return null.
  */
-static inline s32 *is_riprel(u8 *insn)
+static s32 __kprobes *is_riprel(u8 *insn)
 {
 #define W(row,b0,b1,b2,b3,b4,b5,b6,b7,b8,b9,ba,bb,bc,bd,be,bf)               \
        (((b0##UL << 0x0)|(b1##UL << 0x1)|(b2##UL << 0x2)|(b3##UL << 0x3) |   \
@@ -229,7 +229,7 @@ void __kprobes arch_remove_kprobe(struct kprobe *p)
        mutex_unlock(&kprobe_mutex);
 }
 
-static inline void save_previous_kprobe(struct kprobe_ctlblk *kcb)
+static void __kprobes save_previous_kprobe(struct kprobe_ctlblk *kcb)
 {
        kcb->prev_kprobe.kp = kprobe_running();
        kcb->prev_kprobe.status = kcb->kprobe_status;
@@ -237,7 +237,7 @@ static inline void save_previous_kprobe(struct kprobe_ctlblk *kcb)
        kcb->prev_kprobe.saved_rflags = kcb->kprobe_saved_rflags;
 }
 
-static inline void restore_previous_kprobe(struct kprobe_ctlblk *kcb)
+static void __kprobes restore_previous_kprobe(struct kprobe_ctlblk *kcb)
 {
        __get_cpu_var(current_kprobe) = kcb->prev_kprobe.kp;
        kcb->kprobe_status = kcb->prev_kprobe.status;
@@ -245,7 +245,7 @@ static inline void restore_previous_kprobe(struct kprobe_ctlblk *kcb)
        kcb->kprobe_saved_rflags = kcb->prev_kprobe.saved_rflags;
 }
 
-static inline void set_current_kprobe(struct kprobe *p, struct pt_regs *regs,
+static void __kprobes set_current_kprobe(struct kprobe *p, struct pt_regs *regs,
                                struct kprobe_ctlblk *kcb)
 {
        __get_cpu_var(current_kprobe) = p;
index 10b3e348fc9960c66fafec31350ba81f97196ebc..6f0790e8b6d3b50af3d6774ed4e127f00632076d 100644 (file)
@@ -29,6 +29,8 @@
 #define MISC_MCELOG_MINOR 227
 #define NR_BANKS 6
 
+atomic_t mce_entry;
+
 static int mce_dont_init;
 
 /* 0: always panic, 1: panic if deadlock possible, 2: try to avoid panic,
@@ -172,10 +174,12 @@ void do_machine_check(struct pt_regs * regs, long error_code)
        int i;
        int panicm_found = 0;
 
+       atomic_inc(&mce_entry);
+
        if (regs)
                notify_die(DIE_NMI, "machine check", regs, error_code, 18, SIGKILL);
        if (!banks)
-               return;
+               goto out2;
 
        memset(&m, 0, sizeof(struct mce));
        m.cpu = safe_smp_processor_id();
@@ -266,6 +270,8 @@ void do_machine_check(struct pt_regs * regs, long error_code)
  out:
        /* Last thing done in the machine check exception to clear state. */
        wrmsrl(MSR_IA32_MCG_STATUS, 0);
+ out2:
+       atomic_dec(&mce_entry);
 }
 
 /*
index d9e4067faf057531c60ceebd6b50a676609303f8..4e6357fe0ec3e21a76e8afc9a38a4211342e899b 100644 (file)
@@ -34,6 +34,7 @@
 #include <asm/proto.h>
 #include <asm/kdebug.h>
 #include <asm/local.h>
+#include <asm/mce.h>
 
 /*
  * lapic_nmi_owner tracks the ownership of the lapic NMI hardware:
@@ -480,6 +481,12 @@ void __kprobes nmi_watchdog_tick(struct pt_regs * regs, unsigned reason)
                __get_cpu_var(nmi_touch) = 0;
                touched = 1;
        }
+#ifdef CONFIG_X86_MCE
+       /* Could check oops_in_progress here too, but it's safer
+          not too */
+       if (atomic_read(&mce_entry) > 0)
+               touched = 1;
+#endif
        if (!touched && __get_cpu_var(last_irq_sum) == sum) {
                /*
                 * Ayiee, looks like this CPU is stuck ...
index 03c9eeedb0f30672839648984c94ec89103c9e2f..af035ede70cd43386f240438e2192cb343cab750 100644 (file)
@@ -48,9 +48,11 @@ dma_alloc_pages(struct device *dev, gfp_t gfp, unsigned order)
 {
        struct page *page;
        int node;
+#ifdef CONFIG_PCI
        if (dev->bus == &pci_bus_type)
                node = pcibus_to_node(to_pci_dev(dev)->bus);
        else
+#endif
                node = numa_node_id();
        page = alloc_pages_node(node, gfp, order);
        return page ? page_address(page) : NULL;
index 70dd8e5c68897a33c2fba8f3106663e034d62157..fb903e65e079a26034f76a30ef6f54b40613453d 100644 (file)
@@ -575,8 +575,10 @@ __switch_to(struct task_struct *prev_p, struct task_struct *next_p)
        prev->userrsp = read_pda(oldrsp); 
        write_pda(oldrsp, next->userrsp); 
        write_pda(pcurrent, next_p); 
+
        /* This must be here to ensure both math_state_restore() and
-          kernel_fpu_begin() work consistently. */
+          kernel_fpu_begin() work consistently. 
+          And the AMD workaround requires it to be after DS reload. */
        unlazy_fpu(prev_p);
        write_pda(kernelstack,
                  task_stack_page(next_p) + THREAD_SIZE - PDA_STACKOFFSET);
@@ -781,10 +783,16 @@ long do_arch_prctl(struct task_struct *task, int code, unsigned long addr)
        }
        case ARCH_GET_GS: { 
                unsigned long base;
+               unsigned gsindex;
                if (task->thread.gsindex == GS_TLS_SEL)
                        base = read_32bit_tls(task, GS_TLS);
-               else if (doit)
-                       rdmsrl(MSR_KERNEL_GS_BASE, base);
+               else if (doit) {
+                       asm("movl %%gs,%0" : "=r" (gsindex));
+                       if (gsindex)
+                               rdmsrl(MSR_KERNEL_GS_BASE, base);
+                       else
+                               base = task->thread.gs;
+               }
                else
                        base = task->thread.gs;
                ret = put_user(base, (unsigned long __user *)addr); 
index d44b2c1e63a6a5649aa57e561fafd6ef78192cf4..da8e7903d8174a59ff1caf84202fa943e5372c7e 100644 (file)
@@ -274,11 +274,6 @@ static int putreg(struct task_struct *child,
                                return -EIO;
                        value &= 0xffff;
                        break;
-               case offsetof(struct user_regs_struct, rip):
-                       /* Check if the new RIP address is canonical */
-                       if (value >= TASK_SIZE_OF(child))
-                               return -EIO;
-                       break;
        }
        put_stack_long(child, regno - sizeof(struct pt_regs), value);
        return 0;
index 0856ad444f90d8baf232af5903b3f7fb46143474..759070c827511bb482c3b770ff0f35407746936c 100644 (file)
@@ -353,8 +353,10 @@ static __init void parse_cmdline_early (char ** cmdline_p)
                if (fullarg(from, "enable_timer_pin_1"))
                        disable_timer_pin_1 = -1;
 
-               if (fullarg(from, "nolapic") || fullarg(from, "disableapic"))
+               if (fullarg(from, "nolapic") || fullarg(from, "disableapic")) {
+                       clear_bit(X86_FEATURE_APIC, boot_cpu_data.x86_capability);
                        disable_apic = 1;
+               }
 
                if (fullarg(from, "noapic"))
                        skip_ioapic_setup = 1;
@@ -928,6 +930,10 @@ static int __init init_amd(struct cpuinfo_x86 *c)
        if (c->x86 == 15 && ((level >= 0x0f48 && level < 0x0f50) || level >= 0x0f58))
                set_bit(X86_FEATURE_REP_GOOD, &c->x86_capability);
 
+       /* Enable workaround for FXSAVE leak */
+       if (c->x86 >= 6)
+               set_bit(X86_FEATURE_FXSAVE_LEAK, &c->x86_capability);
+
        r = get_model_name(c);
        if (!r) { 
                switch (c->x86) { 
index ef8bc46dc14023f1dc47aec58f8962d9c8c8518e..7392570f975dc705b2d29c98c2571366d8e9666d 100644 (file)
@@ -726,7 +726,7 @@ static __init int late_hpet_init(void)
        unsigned int            ntimer;
 
        if (!vxtime.hpet_address)
-               return -1;
+               return 0;
 
        memset(&hd, 0, sizeof (hd));
 
@@ -917,6 +917,8 @@ void __init time_init(void)
                vxtime.hpet_address = 0;
 
        if (hpet_use_timer) {
+               /* set tick_nsec to use the proper rate for HPET */
+               tick_nsec = TICK_NSEC_HPET;
                cpu_khz = hpet_calibrate_tsc();
                timename = "HPET";
 #ifdef CONFIG_X86_PM_TIMER
index 6bda322d3cafe30f64c03ed426f03c80dc42890b..2700b1375c1fe27c864d60ec41e15258d7c90cd6 100644 (file)
@@ -30,6 +30,7 @@
 #include <linux/moduleparam.h>
 #include <linux/nmi.h>
 #include <linux/kprobes.h>
+#include <linux/kexec.h>
 
 #include <asm/system.h>
 #include <asm/uaccess.h>
@@ -433,6 +434,8 @@ void __kprobes __die(const char * str, struct pt_regs * regs, long err)
        printk(KERN_ALERT "RIP ");
        printk_address(regs->rip); 
        printk(" RSP <%016lx>\n", regs->rsp); 
+       if (kexec_should_crash(current))
+               crash_kexec(regs);
 }
 
 void die(const char * str, struct pt_regs * regs, long err)
@@ -455,6 +458,8 @@ void __kprobes die_nmi(char *str, struct pt_regs *regs)
         */
        printk(str, safe_smp_processor_id());
        show_registers(regs);
+       if (kexec_should_crash(current))
+               crash_kexec(regs);
        if (panic_on_timeout || panic_on_oops)
                panic("nmi watchdog");
        printk("console shuts up ...\n");
index 39ff0708f803a208288913383fd0fdbd1b1d366a..b81f473c4a19bd4cec12f02bae4764fc30d436cf 100644 (file)
@@ -65,7 +65,7 @@ SECTIONS
   .data.cacheline_aligned : AT(ADDR(.data.cacheline_aligned) - LOAD_OFFSET) {
        *(.data.cacheline_aligned)
   }
-  . = ALIGN(CONFIG_X86_L1_CACHE_BYTES);
+  . = ALIGN(CONFIG_X86_INTERNODE_CACHE_BYTES);
   .data.read_mostly : AT(ADDR(.data.read_mostly) - LOAD_OFFSET) {
        *(.data.read_mostly)
   }
index d78f46056bda7634fbf1a8e255b74f020134bb2d..1def21c9f7cd9f426cd29b1fc0c7a425d32411e4 100644 (file)
@@ -112,7 +112,6 @@ EXPORT_SYMBOL_GPL(unset_nmi_callback);
 #undef memcpy
 #undef memset
 #undef memmove
-#undef strlen
 
 extern void * memset(void *,int,__kernel_size_t);
 extern size_t strlen(const char *);
@@ -121,8 +120,6 @@ extern void * memcpy(void *,const void *,__kernel_size_t);
 extern void * __memcpy(void *,const void *,__kernel_size_t);
 
 EXPORT_SYMBOL(memset);
-EXPORT_SYMBOL(strlen);
-EXPORT_SYMBOL(strpbrk);
 EXPORT_SYMBOL(memmove);
 EXPORT_SYMBOL(memcpy);
 EXPORT_SYMBOL(__memcpy);
index e5f7f1c344624126314f3aa450edfe717e989036..4ba34e95d835a17668e013bd5e4fd304077ef3a4 100644 (file)
@@ -305,7 +305,7 @@ static void __meminit phys_pud_init(pud_t *pud, unsigned long address, unsigned
                if (paddr >= end)
                        break;
 
-               if (!after_bootmem && !e820_mapped(paddr, paddr+PUD_SIZE, 0)) {
+               if (!after_bootmem && !e820_any_mapped(paddr, paddr+PUD_SIZE, 0)) {
                        set_pud(pud, __pud(0)); 
                        continue;
                } 
@@ -507,9 +507,8 @@ void __init clear_kernel_mapping(unsigned long address, unsigned long size)
 
 /*
  * Memory hotplug specific functions
- * These are only for non-NUMA machines right now.
  */
-#ifdef CONFIG_MEMORY_HOTPLUG
+#if defined(CONFIG_ACPI_HOTPLUG_MEMORY) || defined(CONFIG_ACPI_HOTPLUG_MEMORY_MODULE)
 
 void online_page(struct page *page)
 {
@@ -520,6 +519,38 @@ void online_page(struct page *page)
        num_physpages++;
 }
 
+#ifndef CONFIG_MEMORY_HOTPLUG
+/*
+ * Memory Hotadd without sparsemem. The mem_maps have been allocated in advance,
+ * just online the pages.
+ */
+int __add_pages(struct zone *z, unsigned long start_pfn, unsigned long nr_pages)
+{
+       int err = -EIO;
+       unsigned long pfn;
+       unsigned long total = 0, mem = 0;
+       for (pfn = start_pfn; pfn < start_pfn + nr_pages; pfn++) {
+               if (pfn_valid(pfn)) {
+                       online_page(pfn_to_page(pfn));
+                       err = 0;
+                       mem++;
+               }
+               total++;
+       }
+       if (!err) {
+               z->spanned_pages += total;
+               z->present_pages += mem;
+               z->zone_pgdat->node_spanned_pages += total;
+               z->zone_pgdat->node_present_pages += mem;
+       }
+       return err;
+}
+#endif
+
+/*
+ * Memory is added always to NORMAL zone. This means you will never get
+ * additional DMA/DMA32 memory.
+ */
 int add_memory(u64 start, u64 size)
 {
        struct pglist_data *pgdat = NODE_DATA(0);
index 4be82d6e2b48162327b6e58d632636946539f092..cc02573a327170f80cbf5fa64c99c3d25aad9eef 100644 (file)
@@ -100,11 +100,30 @@ int early_pfn_to_nid(unsigned long pfn)
 }
 #endif
 
+static void * __init
+early_node_mem(int nodeid, unsigned long start, unsigned long end,
+             unsigned long size)
+{
+       unsigned long mem = find_e820_area(start, end, size);
+       void *ptr;
+       if (mem != -1L)
+               return __va(mem);
+       ptr = __alloc_bootmem_nopanic(size,
+                               SMP_CACHE_BYTES, __pa(MAX_DMA_ADDRESS));
+       if (ptr == 0) {
+               printk(KERN_ERR "Cannot find %lu bytes in node %d\n",
+                       size, nodeid);
+               return NULL;
+       }
+       return ptr;
+}
+
 /* Initialize bootmem allocator for a node */
 void __init setup_node_bootmem(int nodeid, unsigned long start, unsigned long end)
 { 
        unsigned long start_pfn, end_pfn, bootmap_pages, bootmap_size, bootmap_start; 
        unsigned long nodedata_phys;
+       void *bootmap;
        const int pgdat_size = round_up(sizeof(pg_data_t), PAGE_SIZE);
 
        start = round_up(start, ZONE_ALIGN); 
@@ -114,13 +133,11 @@ void __init setup_node_bootmem(int nodeid, unsigned long start, unsigned long en
        start_pfn = start >> PAGE_SHIFT;
        end_pfn = end >> PAGE_SHIFT;
 
-       nodedata_phys = find_e820_area(start, end, pgdat_size); 
-       if (nodedata_phys == -1L) 
-               panic("Cannot find memory pgdat in node %d\n", nodeid);
-
-       Dprintk("nodedata_phys %lx\n", nodedata_phys); 
+       node_data[nodeid] = early_node_mem(nodeid, start, end, pgdat_size);
+       if (node_data[nodeid] == NULL)
+               return;
+       nodedata_phys = __pa(node_data[nodeid]);
 
-       node_data[nodeid] = phys_to_virt(nodedata_phys);
        memset(NODE_DATA(nodeid), 0, sizeof(pg_data_t));
        NODE_DATA(nodeid)->bdata = &plat_node_bdata[nodeid];
        NODE_DATA(nodeid)->node_start_pfn = start_pfn;
@@ -129,9 +146,15 @@ void __init setup_node_bootmem(int nodeid, unsigned long start, unsigned long en
        /* Find a place for the bootmem map */
        bootmap_pages = bootmem_bootmap_pages(end_pfn - start_pfn); 
        bootmap_start = round_up(nodedata_phys + pgdat_size, PAGE_SIZE);
-       bootmap_start = find_e820_area(bootmap_start, end, bootmap_pages<<PAGE_SHIFT);
-       if (bootmap_start == -1L) 
-               panic("Not enough continuous space for bootmap on node %d", nodeid); 
+       bootmap = early_node_mem(nodeid, bootmap_start, end,
+                                       bootmap_pages<<PAGE_SHIFT);
+       if (bootmap == NULL)  {
+               if (nodedata_phys < start || nodedata_phys >= end)
+                       free_bootmem((unsigned long)node_data[nodeid],pgdat_size);
+               node_data[nodeid] = NULL;
+               return;
+       }
+       bootmap_start = __pa(bootmap);
        Dprintk("bootmap start %lu pages %lu\n", bootmap_start, bootmap_pages); 
        
        bootmap_size = init_bootmem_node(NODE_DATA(nodeid),
@@ -142,6 +165,9 @@ void __init setup_node_bootmem(int nodeid, unsigned long start, unsigned long en
 
        reserve_bootmem_node(NODE_DATA(nodeid), nodedata_phys, pgdat_size); 
        reserve_bootmem_node(NODE_DATA(nodeid), bootmap_start, bootmap_pages<<PAGE_SHIFT);
+#ifdef CONFIG_ACPI_NUMA
+       srat_reserve_add_area(nodeid);
+#endif
        node_set_online(nodeid);
 } 
 
@@ -335,6 +361,8 @@ __init int numa_setup(char *opt)
 #ifdef CONFIG_ACPI_NUMA
        if (!strncmp(opt,"noacpi",6))
                acpi_numa = -1;
+       if (!strncmp(opt,"hotadd=", 7))
+               hotadd_percent = simple_strtoul(opt+7, NULL, 10);
 #endif
        return 1;
 } 
index 2eb879590dc42107bd4fc0ef7a4019d1617e7055..15ae9fcd65a700c9f9060860f0fce56f7f6f3fcf 100644 (file)
 #include <linux/bitmap.h>
 #include <linux/module.h>
 #include <linux/topology.h>
+#include <linux/bootmem.h>
+#include <linux/mm.h>
 #include <asm/proto.h>
 #include <asm/numa.h>
 #include <asm/e820.h>
 
+#if (defined(CONFIG_ACPI_HOTPLUG_MEMORY) || \
+       defined(CONFIG_ACPI_HOTPLUG_MEMORY_MODULE)) \
+               && !defined(CONFIG_MEMORY_HOTPLUG)
+#define RESERVE_HOTADD 1
+#endif
+
 static struct acpi_table_slit *acpi_slit;
 
 static nodemask_t nodes_parsed __initdata;
 static nodemask_t nodes_found __initdata;
 static struct bootnode nodes[MAX_NUMNODES] __initdata;
+static struct bootnode nodes_add[MAX_NUMNODES] __initdata;
+static int found_add_area __initdata;
+int hotadd_percent __initdata = 10;
 static u8 pxm2node[256] = { [0 ... 255] = 0xff };
 
 /* Too small nodes confuse the VM badly. Usually they result
@@ -71,6 +82,10 @@ static __init int conflicting_nodes(unsigned long start, unsigned long end)
 static __init void cutoff_node(int i, unsigned long start, unsigned long end)
 {
        struct bootnode *nd = &nodes[i];
+
+       if (found_add_area)
+               return;
+
        if (nd->start < start) {
                nd->start = start;
                if (nd->end < nd->start)
@@ -90,6 +105,8 @@ static __init void bad_srat(void)
        acpi_numa = -1;
        for (i = 0; i < MAX_LOCAL_APIC; i++)
                apicid_to_node[i] = NUMA_NO_NODE;
+       for (i = 0; i < MAX_NUMNODES; i++)
+               nodes_add[i].start = nodes[i].end = 0;
 }
 
 static __init inline int srat_disabled(void)
@@ -155,11 +172,114 @@ acpi_numa_processor_affinity_init(struct acpi_table_processor_affinity *pa)
               pxm, pa->apic_id, node);
 }
 
+#ifdef RESERVE_HOTADD
+/*
+ * Protect against too large hotadd areas that would fill up memory.
+ */
+static int hotadd_enough_memory(struct bootnode *nd)
+{
+       static unsigned long allocated;
+       static unsigned long last_area_end;
+       unsigned long pages = (nd->end - nd->start) >> PAGE_SHIFT;
+       long mem = pages * sizeof(struct page);
+       unsigned long addr;
+       unsigned long allowed;
+       unsigned long oldpages = pages;
+
+       if (mem < 0)
+               return 0;
+       allowed = (end_pfn - e820_hole_size(0, end_pfn)) * PAGE_SIZE;
+       allowed = (allowed / 100) * hotadd_percent;
+       if (allocated + mem > allowed) {
+               /* Give them at least part of their hotadd memory upto hotadd_percent
+                  It would be better to spread the limit out
+                  over multiple hotplug areas, but that is too complicated
+                  right now */
+               if (allocated >= allowed)
+                       return 0;
+               pages = (allowed - allocated + mem) / sizeof(struct page);
+               mem = pages * sizeof(struct page);
+               nd->end = nd->start + pages*PAGE_SIZE;
+       }
+       /* Not completely fool proof, but a good sanity check */
+       addr = find_e820_area(last_area_end, end_pfn<<PAGE_SHIFT, mem);
+       if (addr == -1UL)
+               return 0;
+       if (pages != oldpages)
+               printk(KERN_NOTICE "SRAT: Hotadd area limited to %lu bytes\n",
+                       pages << PAGE_SHIFT);
+       last_area_end = addr + mem;
+       allocated += mem;
+       return 1;
+}
+
+/*
+ * It is fine to add this area to the nodes data it will be used later
+ * This code supports one contigious hot add area per node.
+ */
+static int reserve_hotadd(int node, unsigned long start, unsigned long end)
+{
+       unsigned long s_pfn = start >> PAGE_SHIFT;
+       unsigned long e_pfn = end >> PAGE_SHIFT;
+       int changed = 0;
+       struct bootnode *nd = &nodes_add[node];
+
+       /* I had some trouble with strange memory hotadd regions breaking
+          the boot. Be very strict here and reject anything unexpected.
+          If you want working memory hotadd write correct SRATs.
+
+          The node size check is a basic sanity check to guard against
+          mistakes */
+       if ((signed long)(end - start) < NODE_MIN_SIZE) {
+               printk(KERN_ERR "SRAT: Hotplug area too small\n");
+               return -1;
+       }
+
+       /* This check might be a bit too strict, but I'm keeping it for now. */
+       if (e820_hole_size(s_pfn, e_pfn) != e_pfn - s_pfn) {
+               printk(KERN_ERR "SRAT: Hotplug area has existing memory\n");
+               return -1;
+       }
+
+       if (!hotadd_enough_memory(&nodes_add[node]))  {
+               printk(KERN_ERR "SRAT: Hotplug area too large\n");
+               return -1;
+       }
+
+       /* Looks good */
+
+       found_add_area = 1;
+       if (nd->start == nd->end) {
+               nd->start = start;
+               nd->end = end;
+               changed = 1;
+       } else {
+               if (nd->start == end) {
+                       nd->start = start;
+                       changed = 1;
+               }
+               if (nd->end == start) {
+                       nd->end = end;
+                       changed = 1;
+               }
+               if (!changed)
+                       printk(KERN_ERR "SRAT: Hotplug zone not continuous. Partly ignored\n");
+       }
+
+       if ((nd->end >> PAGE_SHIFT) > end_pfn)
+               end_pfn = nd->end >> PAGE_SHIFT;
+
+       if (changed)
+               printk(KERN_INFO "SRAT: hot plug zone found %Lx - %Lx\n", nd->start, nd->end);
+       return 0;
+}
+#endif
+
 /* Callback for parsing of the Proximity Domain <-> Memory Area mappings */
 void __init
 acpi_numa_memory_affinity_init(struct acpi_table_memory_affinity *ma)
 {
-       struct bootnode *nd;
+       struct bootnode *nd, oldnode;
        unsigned long start, end;
        int node, pxm;
        int i;
@@ -172,6 +292,8 @@ acpi_numa_memory_affinity_init(struct acpi_table_memory_affinity *ma)
        }
        if (ma->flags.enabled == 0)
                return;
+       if (ma->flags.hot_pluggable && hotadd_percent == 0)
+               return;
        start = ma->base_addr_lo | ((u64)ma->base_addr_hi << 32);
        end = start + (ma->length_lo | ((u64)ma->length_hi << 32));
        pxm = ma->proximity_domain;
@@ -181,10 +303,6 @@ acpi_numa_memory_affinity_init(struct acpi_table_memory_affinity *ma)
                bad_srat();
                return;
        }
-       /* It is fine to add this area to the nodes data it will be used later*/
-       if (ma->flags.hot_pluggable == 1)
-               printk(KERN_INFO "SRAT: hot plug zone found %lx - %lx \n",
-                               start, end);
        i = conflicting_nodes(start, end);
        if (i == node) {
                printk(KERN_WARNING
@@ -199,6 +317,7 @@ acpi_numa_memory_affinity_init(struct acpi_table_memory_affinity *ma)
                return;
        }
        nd = &nodes[node];
+       oldnode = *nd;
        if (!node_test_and_set(node, nodes_parsed)) {
                nd->start = start;
                nd->end = end;
@@ -208,8 +327,19 @@ acpi_numa_memory_affinity_init(struct acpi_table_memory_affinity *ma)
                if (nd->end < end)
                        nd->end = end;
        }
+
        printk(KERN_INFO "SRAT: Node %u PXM %u %Lx-%Lx\n", node, pxm,
               nd->start, nd->end);
+
+#ifdef RESERVE_HOTADD
+       if (ma->flags.hot_pluggable && reserve_hotadd(node, start, end) < 0) {
+               /* Ignore hotadd region. Undo damage */
+               printk(KERN_NOTICE "SRAT: Hotplug region ignored\n");
+               *nd = oldnode;
+               if ((nd->start | nd->end) == 0)
+                       node_clear(node, nodes_parsed);
+       }
+#endif
 }
 
 /* Sanity check to catch more bad SRATs (they are amazingly common).
@@ -225,6 +355,9 @@ static int nodes_cover_memory(void)
                unsigned long e = nodes[i].end >> PAGE_SHIFT;
                pxmram += e - s;
                pxmram -= e820_hole_size(s, e);
+               pxmram -= nodes_add[i].end - nodes_add[i].start;
+               if ((long)pxmram < 0)
+                       pxmram = 0;
        }
 
        e820ram = end_pfn - e820_hole_size(0, end_pfn);
@@ -258,7 +391,7 @@ int __init acpi_scan_nodes(unsigned long start, unsigned long end)
 
        /* First clean up the node list */
        for (i = 0; i < MAX_NUMNODES; i++) {
-               cutoff_node(i, start, end);
+               cutoff_node(i, start, end);
                if ((nodes[i].end - nodes[i].start) < NODE_MIN_SIZE)
                        unparse_node(i);
        }
@@ -282,6 +415,12 @@ int __init acpi_scan_nodes(unsigned long start, unsigned long end)
        /* Finally register nodes */
        for_each_node_mask(i, nodes_parsed)
                setup_node_bootmem(i, nodes[i].start, nodes[i].end);
+       /* Try again in case setup_node_bootmem missed one due
+          to missing bootmem */
+       for_each_node_mask(i, nodes_parsed)
+               if (!node_online(i))
+                       setup_node_bootmem(i, nodes[i].start, nodes[i].end);
+
        for (i = 0; i < NR_CPUS; i++) { 
                if (cpu_to_node[i] == NUMA_NO_NODE)
                        continue;
@@ -303,6 +442,25 @@ static int node_to_pxm(int n)
        return 0;
 }
 
+void __init srat_reserve_add_area(int nodeid)
+{
+       if (found_add_area && nodes_add[nodeid].end) {
+               u64 total_mb;
+
+               printk(KERN_INFO "SRAT: Reserving hot-add memory space "
+                               "for node %d at %Lx-%Lx\n",
+                       nodeid, nodes_add[nodeid].start, nodes_add[nodeid].end);
+               total_mb = (nodes_add[nodeid].end - nodes_add[nodeid].start)
+                                       >> PAGE_SHIFT;
+               total_mb *= sizeof(struct page);
+               total_mb >>= 20;
+               printk(KERN_INFO "SRAT: This will cost you %Lu MB of "
+                               "pre-allocated memory.\n", (unsigned long long)total_mb);
+               reserve_bootmem_node(NODE_DATA(nodeid), nodes_add[nodeid].start,
+                              nodes_add[nodeid].end - nodes_add[nodeid].start);
+       }
+}
+
 int __node_distance(int a, int b)
 {
        int index;
index e616500207e4bd77402ada45286745b70833ba26..a2060e4d5de66ff613383ba0b3f8268425b9bf5b 100644 (file)
@@ -9,11 +9,16 @@
 #include <linux/init.h>
 #include <linux/acpi.h>
 #include <linux/bitmap.h>
+#include <asm/e820.h>
+
 #include "pci.h"
 
 #define MMCONFIG_APER_SIZE (256*1024*1024)
+/* Verify the first 16 busses. We assume that systems with more busses
+   get MCFG right. */
+#define MAX_CHECK_BUS 16
 
-static DECLARE_BITMAP(fallback_slots, 32);
+static DECLARE_BITMAP(fallback_slots, 32*MAX_CHECK_BUS);
 
 /* Static virtual mapping of the MMCONFIG aperture */
 struct mmcfg_virt {
@@ -55,7 +60,8 @@ static char __iomem *get_virt(unsigned int seg, unsigned bus)
 static char __iomem *pci_dev_base(unsigned int seg, unsigned int bus, unsigned int devfn)
 {
        char __iomem *addr;
-       if (seg == 0 && bus == 0 && test_bit(PCI_SLOT(devfn), fallback_slots))
+       if (seg == 0 && bus < MAX_CHECK_BUS &&
+               test_bit(32*bus + PCI_SLOT(devfn), fallback_slots))
                return NULL;
        addr = get_virt(seg, bus);
        if (!addr)
@@ -69,8 +75,10 @@ static int pci_mmcfg_read(unsigned int seg, unsigned int bus,
        char __iomem *addr;
 
        /* Why do we have this when nobody checks it. How about a BUG()!? -AK */
-       if (unlikely(!value || (bus > 255) || (devfn > 255) || (reg > 4095)))
+       if (unlikely((bus > 255) || (devfn > 255) || (reg > 4095))) {
+               *value = -1;
                return -EINVAL;
+       }
 
        addr = pci_dev_base(seg, bus, devfn);
        if (!addr)
@@ -129,21 +137,26 @@ static struct pci_raw_ops pci_mmcfg = {
    Normally this can be expressed in the MCFG by not listing them
    and assigning suitable _SEGs, but this isn't implemented in some BIOS.
    Instead try to discover all devices on bus 0 that are unreachable using MM
-   and fallback for them.
-   We only do this for bus 0/seg 0 */
+   and fallback for them. */
 static __init void unreachable_devices(void)
 {
-       int i;
-       for (i = 0; i < 32; i++) {
-               u32 val1;
-               char __iomem *addr;
-
-               pci_conf1_read(0, 0, PCI_DEVFN(i,0), 0, 4, &val1);
-               if (val1 == 0xffffffff)
-                       continue;
-               addr = pci_dev_base(0, 0, PCI_DEVFN(i, 0));
-               if (addr == NULL|| readl(addr) != val1) {
-                       set_bit(i, fallback_slots);
+       int i, k;
+       /* Use the max bus number from ACPI here? */
+       for (k = 0; k < MAX_CHECK_BUS; k++) {
+               for (i = 0; i < 32; i++) {
+                       u32 val1;
+                       char __iomem *addr;
+
+                       pci_conf1_read(0, k, PCI_DEVFN(i,0), 0, 4, &val1);
+                       if (val1 == 0xffffffff)
+                               continue;
+                       addr = pci_dev_base(0, k, PCI_DEVFN(i, 0));
+                       if (addr == NULL|| readl(addr) != val1) {
+                               set_bit(i + 32*k, fallback_slots);
+                               printk(KERN_NOTICE
+                               "PCI: No mmconfig possible on device %x:%x\n",
+                                       k, i);
+                       }
                }
        }
 }
@@ -161,6 +174,14 @@ void __init pci_mmcfg_init(void)
            (pci_mmcfg_config[0].base_address == 0))
                return;
 
+       if (!e820_all_mapped(pci_mmcfg_config[0].base_address,
+                       pci_mmcfg_config[0].base_address + MMCONFIG_APER_SIZE,
+                       E820_RESERVED)) {
+               printk(KERN_ERR "PCI: BIOS Bug: MCFG area is not E820-reserved\n");
+               printk(KERN_ERR "PCI: Not using MMCONFIG.\n");
+               return;
+       }
+
        /* RED-PEN i386 doesn't do _nocache right now */
        pci_mmcfg_virt = kmalloc(sizeof(*pci_mmcfg_virt) * pci_mmcfg_config_num, GFP_KERNEL);
        if (pci_mmcfg_virt == NULL) {
index 152b9370789b194c0904ee2cabeb7f7258c5e1a4..a15b6e3e72c86d2d097baf57cd664b23d0303a84 100644 (file)
@@ -48,7 +48,6 @@ EXPORT_SYMBOL(memchr);
 EXPORT_SYMBOL(strcat);
 EXPORT_SYMBOL(strchr);
 EXPORT_SYMBOL(strlen);
-EXPORT_SYMBOL(strpbrk);
 EXPORT_SYMBOL(strncat);
 EXPORT_SYMBOL(strnlen);
 EXPORT_SYMBOL(strrchr);
index 296708ceceb2d62a8bacd8a954efeb1108d5547e..e25a5d79ab2715b2f3a07ce3331e46cd45ab86f1 100644 (file)
@@ -1844,9 +1844,10 @@ static void __exit as_exit(void)
        DECLARE_COMPLETION(all_gone);
        elv_unregister(&iosched_as);
        ioc_gone = &all_gone;
-       barrier();
+       /* ioc_gone's update must be visible before reading ioc_count */
+       smp_wmb();
        if (atomic_read(&ioc_count))
-               complete(ioc_gone);
+               wait_for_completion(ioc_gone);
        synchronize_rcu();
        kmem_cache_destroy(arq_pool);
 }
index 67d446de0227a3ac71aaa1563728717a21af5eb9..2540dfaa3e385def27a44284bf3e552f986ee15d 100644 (file)
@@ -1472,19 +1472,37 @@ out:
        return cfqq;
 }
 
+static void
+cfq_drop_dead_cic(struct io_context *ioc, struct cfq_io_context *cic)
+{
+       read_lock(&cfq_exit_lock);
+       rb_erase(&cic->rb_node, &ioc->cic_root);
+       read_unlock(&cfq_exit_lock);
+       kmem_cache_free(cfq_ioc_pool, cic);
+       atomic_dec(&ioc_count);
+}
+
 static struct cfq_io_context *
 cfq_cic_rb_lookup(struct cfq_data *cfqd, struct io_context *ioc)
 {
-       struct rb_node *n = ioc->cic_root.rb_node;
+       struct rb_node *n;
        struct cfq_io_context *cic;
-       void *key = cfqd;
+       void *k, *key = cfqd;
 
+restart:
+       n = ioc->cic_root.rb_node;
        while (n) {
                cic = rb_entry(n, struct cfq_io_context, rb_node);
+               /* ->key must be copied to avoid race with cfq_exit_queue() */
+               k = cic->key;
+               if (unlikely(!k)) {
+                       cfq_drop_dead_cic(ioc, cic);
+                       goto restart;
+               }
 
-               if (key < cic->key)
+               if (key < k)
                        n = n->rb_left;
-               else if (key > cic->key)
+               else if (key > k)
                        n = n->rb_right;
                else
                        return cic;
@@ -1497,29 +1515,37 @@ static inline void
 cfq_cic_link(struct cfq_data *cfqd, struct io_context *ioc,
             struct cfq_io_context *cic)
 {
-       struct rb_node **p = &ioc->cic_root.rb_node;
-       struct rb_node *parent = NULL;
+       struct rb_node **p;
+       struct rb_node *parent;
        struct cfq_io_context *__cic;
-
-       read_lock(&cfq_exit_lock);
+       void *k;
 
        cic->ioc = ioc;
        cic->key = cfqd;
 
        ioc->set_ioprio = cfq_ioc_set_ioprio;
-
+restart:
+       parent = NULL;
+       p = &ioc->cic_root.rb_node;
        while (*p) {
                parent = *p;
                __cic = rb_entry(parent, struct cfq_io_context, rb_node);
+               /* ->key must be copied to avoid race with cfq_exit_queue() */
+               k = __cic->key;
+               if (unlikely(!k)) {
+                       cfq_drop_dead_cic(ioc, cic);
+                       goto restart;
+               }
 
-               if (cic->key < __cic->key)
+               if (cic->key < k)
                        p = &(*p)->rb_left;
-               else if (cic->key > __cic->key)
+               else if (cic->key > k)
                        p = &(*p)->rb_right;
                else
                        BUG();
        }
 
+       read_lock(&cfq_exit_lock);
        rb_link_node(&cic->rb_node, parent, p);
        rb_insert_color(&cic->rb_node, &ioc->cic_root);
        list_add(&cic->queue_list, &cfqd->cic_list);
@@ -2439,9 +2465,10 @@ static void __exit cfq_exit(void)
        DECLARE_COMPLETION(all_gone);
        elv_unregister(&iosched_cfq);
        ioc_gone = &all_gone;
-       barrier();
+       /* ioc_gone's update must be visible before reading ioc_count */
+       smp_wmb();
        if (atomic_read(&ioc_count))
-               complete(ioc_gone);
+               wait_for_completion(ioc_gone);
        synchronize_rcu();
        cfq_slab_kill();
 }
index 0d6be03d929ea348423f8abf4a222f7c699d4e3b..29825792cbd5305cfbea9c1f6063710ec4b46be8 100644 (file)
@@ -895,10 +895,8 @@ ssize_t elv_iosched_show(request_queue_t *q, char *name)
 EXPORT_SYMBOL(elv_dispatch_sort);
 EXPORT_SYMBOL(elv_add_request);
 EXPORT_SYMBOL(__elv_add_request);
-EXPORT_SYMBOL(elv_requeue_request);
 EXPORT_SYMBOL(elv_next_request);
 EXPORT_SYMBOL(elv_dequeue_request);
 EXPORT_SYMBOL(elv_queue_empty);
-EXPORT_SYMBOL(elv_completed_request);
 EXPORT_SYMBOL(elevator_exit);
 EXPORT_SYMBOL(elevator_init);
index e112d1a5dab6b8c2dcae45e2a6b18bbfc4529760..1755c053fd68ce648ba90bcbc3c7132ac23d8ad1 100644 (file)
@@ -1554,7 +1554,7 @@ void blk_plug_device(request_queue_t *q)
         * don't plug a stopped queue, it must be paired with blk_start_queue()
         * which will restart the queueing
         */
-       if (test_bit(QUEUE_FLAG_STOPPED, &q->queue_flags))
+       if (blk_queue_stopped(q))
                return;
 
        if (!test_and_set_bit(QUEUE_FLAG_PLUGGED, &q->queue_flags)) {
@@ -1587,7 +1587,7 @@ EXPORT_SYMBOL(blk_remove_plug);
  */
 void __generic_unplug_device(request_queue_t *q)
 {
-       if (unlikely(test_bit(QUEUE_FLAG_STOPPED, &q->queue_flags)))
+       if (unlikely(blk_queue_stopped(q)))
                return;
 
        if (!blk_remove_plug(q))
index 24f7af9d0abc226b2630f8e227ce05ffa8f1ff0e..b33eda26e2053e84f85473a13cd657cf920e3fe0 100644 (file)
@@ -350,16 +350,51 @@ out:
        return ret;
 }
 
+/**
+ * sg_scsi_ioctl  --  handle deprecated SCSI_IOCTL_SEND_COMMAND ioctl
+ * @file:      file this ioctl operates on (optional)
+ * @q:         request queue to send scsi commands down
+ * @disk:      gendisk to operate on (option)
+ * @sic:       userspace structure describing the command to perform
+ *
+ * Send down the scsi command described by @sic to the device below
+ * the request queue @q.  If @file is non-NULL it's used to perform
+ * fine-grained permission checks that allow users to send down
+ * non-destructive SCSI commands.  If the caller has a struct gendisk
+ * available it should be passed in as @disk to allow the low level
+ * driver to use the information contained in it.  A non-NULL @disk
+ * is only allowed if the caller knows that the low level driver doesn't
+ * need it (e.g. in the scsi subsystem).
+ *
+ * Notes:
+ *   -  This interface is deprecated - users should use the SG_IO
+ *      interface instead, as this is a more flexible approach to
+ *      performing SCSI commands on a device.
+ *   -  The SCSI command length is determined by examining the 1st byte
+ *      of the given command. There is no way to override this.
+ *   -  Data transfers are limited to PAGE_SIZE
+ *   -  The length (x + y) must be at least OMAX_SB_LEN bytes long to
+ *      accommodate the sense buffer when an error occurs.
+ *      The sense buffer is truncated to OMAX_SB_LEN (16) bytes so that
+ *      old code will not be surprised.
+ *   -  If a Unix error occurs (e.g. ENOMEM) then the user will receive
+ *      a negative return and the Unix error code in 'errno'.
+ *      If the SCSI command succeeds then 0 is returned.
+ *      Positive numbers returned are the compacted SCSI error codes (4
+ *      bytes in one int) where the lowest byte is the SCSI status.
+ */
 #define OMAX_SB_LEN 16          /* For backward compatibility */
-
-static int sg_scsi_ioctl(struct file *file, request_queue_t *q,
-                        struct gendisk *bd_disk, Scsi_Ioctl_Command __user *sic)
+int sg_scsi_ioctl(struct file *file, struct request_queue *q,
+                 struct gendisk *disk, struct scsi_ioctl_command __user *sic)
 {
        struct request *rq;
        int err;
        unsigned int in_len, out_len, bytes, opcode, cmdlen;
        char *buffer = NULL, sense[SCSI_SENSE_BUFFERSIZE];
 
+       if (!sic)
+               return -EINVAL;
+
        /*
         * get in an out lengths, verify they don't exceed a page worth of data
         */
@@ -393,45 +428,53 @@ static int sg_scsi_ioctl(struct file *file, request_queue_t *q,
        if (copy_from_user(rq->cmd, sic->data, cmdlen))
                goto error;
 
-       if (copy_from_user(buffer, sic->data + cmdlen, in_len))
+       if (in_len && copy_from_user(buffer, sic->data + cmdlen, in_len))
                goto error;
 
        err = verify_command(file, rq->cmd);
        if (err)
                goto error;
 
+       /* default.  possible overriden later */
+       rq->retries = 5;
+
        switch (opcode) {
-               case SEND_DIAGNOSTIC:
-               case FORMAT_UNIT:
-                       rq->timeout = FORMAT_UNIT_TIMEOUT;
-                       break;
-               case START_STOP:
-                       rq->timeout = START_STOP_TIMEOUT;
-                       break;
-               case MOVE_MEDIUM:
-                       rq->timeout = MOVE_MEDIUM_TIMEOUT;
-                       break;
-               case READ_ELEMENT_STATUS:
-                       rq->timeout = READ_ELEMENT_STATUS_TIMEOUT;
-                       break;
-               case READ_DEFECT_DATA:
-                       rq->timeout = READ_DEFECT_DATA_TIMEOUT;
-                       break;
-               default:
-                       rq->timeout = BLK_DEFAULT_TIMEOUT;
-                       break;
+       case SEND_DIAGNOSTIC:
+       case FORMAT_UNIT:
+               rq->timeout = FORMAT_UNIT_TIMEOUT;
+               rq->retries = 1;
+               break;
+       case START_STOP:
+               rq->timeout = START_STOP_TIMEOUT;
+               break;
+       case MOVE_MEDIUM:
+               rq->timeout = MOVE_MEDIUM_TIMEOUT;
+               break;
+       case READ_ELEMENT_STATUS:
+               rq->timeout = READ_ELEMENT_STATUS_TIMEOUT;
+               break;
+       case READ_DEFECT_DATA:
+               rq->timeout = READ_DEFECT_DATA_TIMEOUT;
+               rq->retries = 1;
+               break;
+       default:
+               rq->timeout = BLK_DEFAULT_TIMEOUT;
+               break;
+       }
+
+       if (bytes && blk_rq_map_kern(q, rq, buffer, bytes, __GFP_WAIT)) {
+               err = DRIVER_ERROR << 24;
+               goto out;
        }
 
        memset(sense, 0, sizeof(sense));
        rq->sense = sense;
        rq->sense_len = 0;
-
-       rq->data = buffer;
-       rq->data_len = bytes;
        rq->flags |= REQ_BLOCK_PC;
-       rq->retries = 0;
 
-       blk_execute_rq(q, bd_disk, rq, 0);
+       blk_execute_rq(q, disk, rq, 0);
+
+out:
        err = rq->errors & 0xff;        /* only 8 bit SCSI status */
        if (err) {
                if (rq->sense_len && rq->sense) {
@@ -450,7 +493,7 @@ error:
        blk_put_request(rq);
        return err;
 }
-
+EXPORT_SYMBOL_GPL(sg_scsi_ioctl);
 
 /* Send basic block requests */
 static int __blk_send_generic(request_queue_t *q, struct gendisk *bd_disk, int cmd, int data)
index 5cb96300eb0f90ef49e9fb1067d88bc1ca579a42..c24652d31bf9b6f2fe763ecd20546fe047729e84 100644 (file)
@@ -329,7 +329,7 @@ config ACPI_CONTAINER
 config ACPI_HOTPLUG_MEMORY
        tristate "Memory Hotplug"
        depends on ACPI
-       depends on MEMORY_HOTPLUG
+       depends on MEMORY_HOTPLUG || X86_64
        default n
        help
          This driver adds supports for ACPI Memory Hotplug.  This driver
index 48718b7f4fa01737326174f42a775cdabbcc81a8..76656acd00d4e15c965c07a8a6ebcf1b4b511a42 100644 (file)
@@ -188,6 +188,11 @@ static ssize_t driver_bind(struct device_driver *drv,
                up(&dev->sem);
                if (dev->parent)
                        up(&dev->parent->sem);
+
+               if (err > 0)            /* success */
+                       err = count;
+               else if (err == 0)      /* driver didn't accept device */
+                       err = -ENODEV;
        }
        put_device(dev);
        put_bus(bus);
index df7fdabd073074a5b946e30c82b5127ff97a164a..0e71dff327cd896509060a66f9fe348972253460 100644 (file)
@@ -562,14 +562,13 @@ int class_device_add(struct class_device *class_dev)
        kobject_uevent(&class_dev->kobj, KOBJ_ADD);
 
        /* notify any interfaces this device is now here */
-       if (parent_class) {
-               down(&parent_class->sem);
-               list_add_tail(&class_dev->node, &parent_class->children);
-               list_for_each_entry(class_intf, &parent_class->interfaces, node)
-                       if (class_intf->add)
-                               class_intf->add(class_dev, class_intf);
-               up(&parent_class->sem);
+       down(&parent_class->sem);
+       list_add_tail(&class_dev->node, &parent_class->children);
+       list_for_each_entry(class_intf, &parent_class->interfaces, node) {
+               if (class_intf->add)
+                       class_intf->add(class_dev, class_intf);
        }
+       up(&parent_class->sem);
 
  register_done:
        if (error) {
index 730a9ce0a14a44d45c45fe34b15f1277157fe1d2..889c71111239436d1c9f705cfa5f32ff14ba6f0f 100644 (file)
@@ -209,7 +209,7 @@ static void __device_release_driver(struct device * dev)
                sysfs_remove_link(&dev->kobj, "driver");
                klist_remove(&dev->knode_driver);
 
-               if (dev->bus->remove)
+               if (dev->bus && dev->bus->remove)
                        dev->bus->remove(dev);
                else if (drv->remove)
                        drv->remove(dev);
index 16c513aa4d4877afa7522eedc7e695568648cbf7..c80c3aeed004a558de9cf9db0632191cf1c16c99 100644 (file)
@@ -106,7 +106,7 @@ static ssize_t node_read_numastat(struct sys_device * dev, char * buf)
        other_node = 0;
        for (i = 0; i < MAX_NR_ZONES; i++) {
                struct zone *z = &pg->node_zones[i];
-               for (cpu = 0; cpu < NR_CPUS; cpu++) {
+               for_each_online_cpu(cpu) {
                        struct per_cpu_pageset *ps = zone_pcp(z,cpu);
                        numa_hit += ps->numa_hit;
                        numa_miss += ps->numa_miss;
index bdb60663f2eff5e9243921d8c0e144b8f1c7cd17..662209d3f42d6a551c7001ab5adb62406abfcfb0 100644 (file)
@@ -10,6 +10,8 @@
 
 #include <linux/vt_kern.h>
 #include <linux/device.h>
+#include <linux/kallsyms.h>
+#include <linux/pm.h>
 #include "../base.h"
 #include "power.h"
 
@@ -58,6 +60,7 @@ int suspend_device(struct device * dev, pm_message_t state)
        if (dev->bus && dev->bus->suspend && !dev->power.power_state.event) {
                dev_dbg(dev, "suspending\n");
                error = dev->bus->suspend(dev, state);
+               suspend_report_result(dev->bus->suspend, error);
        }
        up(&dev->sem);
        return error;
@@ -169,3 +172,12 @@ int device_power_down(pm_message_t state)
 
 EXPORT_SYMBOL_GPL(device_power_down);
 
+void __suspend_report_result(const char *function, void *fn, int ret)
+{
+       if (ret) {
+               printk(KERN_ERR "%s(): ", function);
+               print_fn_descriptor_symbol("%s() returns ", (unsigned long)fn);
+               printk("%d\n", ret);
+       }
+}
+EXPORT_SYMBOL_GPL(__suspend_report_result);
index 1b0fd31c57c3dcd269dd60b528ccb2f3d68fa6a5..1319d8f20640505b69ebc6a37c3f9b435910ee0e 100644 (file)
@@ -1180,6 +1180,53 @@ static int revalidate_allvol(ctlr_info_t *host)
         return 0;
 }
 
+static inline void complete_buffers(struct bio *bio, int status)
+{
+       while (bio) {
+               struct bio *xbh = bio->bi_next;
+               int nr_sectors = bio_sectors(bio);
+
+               bio->bi_next = NULL;
+               blk_finished_io(len);
+               bio_endio(bio, nr_sectors << 9, status ? 0 : -EIO);
+               bio = xbh;
+       }
+
+}
+
+static void cciss_softirq_done(struct request *rq)
+{
+       CommandList_struct *cmd = rq->completion_data;
+       ctlr_info_t *h = hba[cmd->ctlr];
+       unsigned long flags;
+       u64bit temp64;
+       int i, ddir;
+
+       if (cmd->Request.Type.Direction == XFER_READ)
+               ddir = PCI_DMA_FROMDEVICE;
+       else
+               ddir = PCI_DMA_TODEVICE;
+
+       /* command did not need to be retried */
+       /* unmap the DMA mapping for all the scatter gather elements */
+       for(i=0; i<cmd->Header.SGList; i++) {
+               temp64.val32.lower = cmd->SG[i].Addr.lower;
+               temp64.val32.upper = cmd->SG[i].Addr.upper;
+               pci_unmap_page(h->pdev, temp64.val, cmd->SG[i].Len, ddir);
+       }
+
+       complete_buffers(rq->bio, rq->errors);
+
+#ifdef CCISS_DEBUG
+       printk("Done with %p\n", rq);
+#endif /* CCISS_DEBUG */
+
+       spin_lock_irqsave(&h->lock, flags);
+       end_that_request_last(rq, rq->errors);
+       cmd_free(h, cmd,1);
+       spin_unlock_irqrestore(&h->lock, flags);
+}
+
 /* This function will check the usage_count of the drive to be updated/added.
  * If the usage_count is zero then the drive information will be updated and
  * the disk will be re-registered with the kernel.  If not then it will be
@@ -1248,6 +1295,8 @@ static void cciss_update_drive_info(int ctlr, int drv_index)
 
                blk_queue_max_sectors(disk->queue, 512);
 
+               blk_queue_softirq_done(disk->queue, cciss_softirq_done);
+
                disk->queue->queuedata = hba[ctlr];
 
                blk_queue_hardsect_size(disk->queue,
@@ -2147,20 +2196,6 @@ static void start_io( ctlr_info_t *h)
                addQ (&(h->cmpQ), c); 
        }
 }
-
-static inline void complete_buffers(struct bio *bio, int status)
-{
-       while (bio) {
-               struct bio *xbh = bio->bi_next; 
-               int nr_sectors = bio_sectors(bio);
-
-               bio->bi_next = NULL; 
-               blk_finished_io(len);
-               bio_endio(bio, nr_sectors << 9, status ? 0 : -EIO);
-               bio = xbh;
-       }
-
-} 
 /* Assumes that CCISS_LOCK(h->ctlr) is held. */
 /* Zeros out the error record and then resends the command back */
 /* to the controller */
@@ -2178,39 +2213,6 @@ static inline void resend_cciss_cmd( ctlr_info_t *h, CommandList_struct *c)
        start_io(h);
 }
 
-static void cciss_softirq_done(struct request *rq)
-{
-       CommandList_struct *cmd = rq->completion_data;
-       ctlr_info_t *h = hba[cmd->ctlr];
-       unsigned long flags;
-       u64bit temp64;
-       int i, ddir;
-
-       if (cmd->Request.Type.Direction == XFER_READ)
-               ddir = PCI_DMA_FROMDEVICE;
-       else
-               ddir = PCI_DMA_TODEVICE;
-
-       /* command did not need to be retried */
-       /* unmap the DMA mapping for all the scatter gather elements */
-       for(i=0; i<cmd->Header.SGList; i++) {
-               temp64.val32.lower = cmd->SG[i].Addr.lower;
-               temp64.val32.upper = cmd->SG[i].Addr.upper;
-               pci_unmap_page(h->pdev, temp64.val, cmd->SG[i].Len, ddir);
-       }
-
-       complete_buffers(rq->bio, rq->errors);
-
-#ifdef CCISS_DEBUG
-       printk("Done with %p\n", rq);
-#endif /* CCISS_DEBUG */ 
-
-       spin_lock_irqsave(&h->lock, flags);
-       end_that_request_last(rq, rq->errors);
-       cmd_free(h, cmd,1);
-       spin_unlock_irqrestore(&h->lock, flags);
-}
-
 /* checks the status of the job and calls complete buffers to mark all 
  * buffers for the completed job. Note that this function does not need
  * to hold the hba/queue lock.
index ce4a1ce59d6a2369ee22bbebeca2f4bc62346659..ec004897b63494e220f87a211056903731a5b122 100644 (file)
@@ -1763,7 +1763,7 @@ static int __init aztcd_init(void)
                                release_region(azt_port, 4);
                        }
                }
-               if ((azt_port_auto[i] == 0) || (i == 16)) {
+               if ((i == 16) || (azt_port_auto[i] == 0)) {
                        printk(KERN_INFO "aztcd: no AZTECH CD-ROM drive found\n");
                        return -EIO;
                }
index 889cad07774e82d82ba1e47b6b51bdab8eeebf00..402296670d3a555acfecbe66ceff162edb887e99 100644 (file)
@@ -805,10 +805,6 @@ config S3C2410_RTC
          Samsung S3C2410. This can provide periodic interrupt rates
          from 1Hz to 64Hz for user programs, and wakeup from Alarm.
 
-config RTC_VR41XX
-       tristate "NEC VR4100 series Real Time Clock Support"
-       depends on CPU_VR41XX
-
 config COBALT_LCD
        bool "Support for Cobalt LCD"
        depends on MIPS_COBALT
index a73cb4956928f2b582e08f9af1250c0d30877025..f5b01c6d498e10c66efa1becb1cb06a9cd0fd265 100644 (file)
@@ -67,7 +67,6 @@ obj-$(CONFIG_SGI_DS1286)      += ds1286.o
 obj-$(CONFIG_SGI_IP27_RTC)     += ip27-rtc.o
 obj-$(CONFIG_DS1302)           += ds1302.o
 obj-$(CONFIG_S3C2410_RTC)      += s3c2410-rtc.o
-obj-$(CONFIG_RTC_VR41XX)       += vr41xx_rtc.o
 ifeq ($(CONFIG_GENERIC_NVRAM),y)
   obj-$(CONFIG_NVRAM)  += generic_nvram.o
 else
index fed0a87448d881301ca82d0dfb3cc7282a9e0665..86a966b652368c84d5331ab62cb25a357fefcfb8 100644 (file)
@@ -64,6 +64,12 @@ static struct gatt_mask efficeon_generic_masks[] =
        {.mask = 0x00000001, .type = 0}
 };
 
+/* This function does the same thing as mask_memory() for this chipset... */
+static inline unsigned long efficeon_mask_memory(unsigned long addr)
+{
+       return addr | 0x00000001;
+}
+
 static struct aper_size_info_lvl2 efficeon_generic_sizes[4] =
 {
        {256, 65536, 0},
@@ -251,7 +257,7 @@ static int efficeon_insert_memory(struct agp_memory * mem, off_t pg_start, int t
        last_page = NULL;
        for (i = 0; i < count; i++) {
                int index = pg_start + i;
-               unsigned long insert = mem->memory[i];
+               unsigned long insert = efficeon_mask_memory(mem->memory[i]);
 
                page = (unsigned int *) efficeon_private.l1_table[index >> 10];
 
index 927a5bbe112c9d9eb175e6840f557d4348d159c2..a370e7a0bad5a1ce46b77684587e0b42f4f4d2b3 100644 (file)
@@ -142,7 +142,7 @@ static int ac_register_board(unsigned long physloc, void __iomem *loc,
        if (!boardno)
                boardno = readb(loc + NUMCARD_OWNER_TO_PC);
 
-       if (!boardno && boardno > MAX_BOARD) {
+       if (!boardno || boardno > MAX_BOARD) {
                printk(KERN_WARNING "Board #%d (at 0x%lx) is out of range (1 <= x <= %d).\n",
                       boardno, physloc, MAX_BOARD);
                return 0;
index 5d72f50de1ac97c6e377fb6c5e0d0d4192016983..46d66037b917c5851222b56af77f4b158ce793aa 100644 (file)
@@ -241,9 +241,10 @@ static int __init cs5535_gpio_init(void)
 static void __exit cs5535_gpio_cleanup(void)
 {
        dev_t dev_id = MKDEV(major, 0);
+
+       cdev_del(&cs5535_gpio_cdev);
        unregister_chrdev_region(dev_id, CS5535_GPIO_COUNT);
-       if (gpio_base != 0)
-               release_region(gpio_base, CS5535_GPIO_SIZE);
+       release_region(gpio_base, CS5535_GPIO_SIZE);
 }
 
 module_init(cs5535_gpio_init);
index edc72a6348a72301ceb2cf4f1b33816a8ee0e91b..e1aadae006232bc8762ae69e4a11bfac7e384ddc 100644 (file)
@@ -815,8 +815,6 @@ extern int drm_mem_info(char *buf, char **start, off_t offset,
 extern void *drm_realloc(void *oldpt, size_t oldsize, size_t size, int area);
 extern void *drm_ioremap(unsigned long offset, unsigned long size,
                         drm_device_t * dev);
-extern void *drm_ioremap_nocache(unsigned long offset, unsigned long size,
-                                drm_device_t * dev);
 extern void drm_ioremapfree(void *pt, unsigned long size, drm_device_t * dev);
 
 extern DRM_AGP_MEM *drm_alloc_agp(drm_device_t * dev, int pages, u32 type);
@@ -1022,11 +1020,13 @@ static __inline__ void drm_core_ioremap(struct drm_map *map,
        map->handle = drm_ioremap(map->offset, map->size, dev);
 }
 
+#if 0
 static __inline__ void drm_core_ioremap_nocache(struct drm_map *map,
                                                struct drm_device *dev)
 {
        map->handle = drm_ioremap_nocache(map->offset, map->size, dev);
 }
+#endif  /*  0  */
 
 static __inline__ void drm_core_ioremapfree(struct drm_map *map,
                                            struct drm_device *dev)
index dc6bbe8a18dc762e158ed8084071ddbaf4eb6ce6..3c0b882a8e72843a2074b2b495ffa2f2ebf266ab 100644 (file)
@@ -75,8 +75,8 @@ static drm_ioctl_desc_t drm_ioctls[] = {
        [DRM_IOCTL_NR(DRM_IOCTL_SET_SAREA_CTX)] = {drm_setsareactx, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY},
        [DRM_IOCTL_NR(DRM_IOCTL_GET_SAREA_CTX)] = {drm_getsareactx, DRM_AUTH},
 
-       [DRM_IOCTL_NR(DRM_IOCTL_ADD_CTX)] = {drm_addctx, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY},
-       [DRM_IOCTL_NR(DRM_IOCTL_RM_CTX)] = {drm_rmctx, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY},
+       [DRM_IOCTL_NR(DRM_IOCTL_ADD_CTX)] = {drm_addctx, DRM_AUTH|DRM_ROOT_ONLY},
+       [DRM_IOCTL_NR(DRM_IOCTL_RM_CTX)] = {drm_rmctx, DRM_AUTH|DRM_ROOT_ONLY},
        [DRM_IOCTL_NR(DRM_IOCTL_MOD_CTX)] = {drm_modctx, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY},
        [DRM_IOCTL_NR(DRM_IOCTL_GET_CTX)] = {drm_getctx, DRM_AUTH},
        [DRM_IOCTL_NR(DRM_IOCTL_SWITCH_CTX)] = {drm_switchctx, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY},
index dddf8de661433cc21758fc5f1b98d25c775f483c..7e3318e1d1c655c2d93682ffbf910cc5aa78d8f0 100644 (file)
@@ -80,6 +80,71 @@ void *drm_realloc(void *oldpt, size_t oldsize, size_t size, int area)
 }
 
 #if __OS_HAS_AGP
+/*
+ * Find the drm_map that covers the range [offset, offset+size).
+ */
+static drm_map_t *drm_lookup_map(unsigned long offset,
+                                unsigned long size, drm_device_t * dev)
+{
+       struct list_head *list;
+       drm_map_list_t *r_list;
+       drm_map_t *map;
+
+       list_for_each(list, &dev->maplist->head) {
+               r_list = (drm_map_list_t *) list;
+               map = r_list->map;
+               if (!map)
+                       continue;
+               if (map->offset <= offset
+                   && (offset + size) <= (map->offset + map->size))
+                       return map;
+       }
+       return NULL;
+}
+
+static void *agp_remap(unsigned long offset, unsigned long size,
+                      drm_device_t * dev)
+{
+       unsigned long *phys_addr_map, i, num_pages =
+           PAGE_ALIGN(size) / PAGE_SIZE;
+       struct drm_agp_mem *agpmem;
+       struct page **page_map;
+       void *addr;
+
+       size = PAGE_ALIGN(size);
+
+#ifdef __alpha__
+       offset -= dev->hose->mem_space->start;
+#endif
+
+       for (agpmem = dev->agp->memory; agpmem; agpmem = agpmem->next)
+               if (agpmem->bound <= offset
+                   && (agpmem->bound + (agpmem->pages << PAGE_SHIFT)) >=
+                   (offset + size))
+                       break;
+       if (!agpmem)
+               return NULL;
+
+       /*
+        * OK, we're mapping AGP space on a chipset/platform on which memory accesses by
+        * the CPU do not get remapped by the GART.  We fix this by using the kernel's
+        * page-table instead (that's probably faster anyhow...).
+        */
+       /* note: use vmalloc() because num_pages could be large... */
+       page_map = vmalloc(num_pages * sizeof(struct page *));
+       if (!page_map)
+               return NULL;
+
+       phys_addr_map =
+           agpmem->memory->memory + (offset - agpmem->bound) / PAGE_SIZE;
+       for (i = 0; i < num_pages; ++i)
+               page_map[i] = pfn_to_page(phys_addr_map[i] >> PAGE_SHIFT);
+       addr = vmap(page_map, num_pages, VM_IOREMAP, PAGE_AGP);
+       vfree(page_map);
+
+       return addr;
+}
+
 /** Wrapper around agp_allocate_memory() */
 DRM_AGP_MEM *drm_alloc_agp(drm_device_t * dev, int pages, u32 type)
 {
@@ -103,5 +168,74 @@ int drm_unbind_agp(DRM_AGP_MEM * handle)
 {
        return drm_agp_unbind_memory(handle);
 }
+
+#else  /*  __OS_HAS_AGP  */
+
+static inline drm_map_t *drm_lookup_map(unsigned long offset,
+                                       unsigned long size, drm_device_t * dev)
+{
+       return NULL;
+}
+
+static inline void *agp_remap(unsigned long offset, unsigned long size,
+                             drm_device_t * dev)
+{
+       return NULL;
+}
+
 #endif                         /* agp */
+
+void *drm_ioremap(unsigned long offset, unsigned long size,
+                               drm_device_t * dev)
+{
+       if (drm_core_has_AGP(dev) && dev->agp && dev->agp->cant_use_aperture) {
+               drm_map_t *map = drm_lookup_map(offset, size, dev);
+
+               if (map && map->type == _DRM_AGP)
+                       return agp_remap(offset, size, dev);
+       }
+       return ioremap(offset, size);
+}
+EXPORT_SYMBOL(drm_ioremap);
+
+#if 0
+void *drm_ioremap_nocache(unsigned long offset,
+                                       unsigned long size, drm_device_t * dev)
+{
+       if (drm_core_has_AGP(dev) && dev->agp && dev->agp->cant_use_aperture) {
+               drm_map_t *map = drm_lookup_map(offset, size, dev);
+
+               if (map && map->type == _DRM_AGP)
+                       return agp_remap(offset, size, dev);
+       }
+       return ioremap_nocache(offset, size);
+}
+#endif  /*  0  */
+
+void drm_ioremapfree(void *pt, unsigned long size,
+                                  drm_device_t * dev)
+{
+       /*
+        * This is a bit ugly.  It would be much cleaner if the DRM API would use separate
+        * routines for handling mappings in the AGP space.  Hopefully this can be done in
+        * a future revision of the interface...
+        */
+       if (drm_core_has_AGP(dev) && dev->agp && dev->agp->cant_use_aperture
+           && ((unsigned long)pt >= VMALLOC_START
+               && (unsigned long)pt < VMALLOC_END)) {
+               unsigned long offset;
+               drm_map_t *map;
+
+               offset = drm_follow_page(pt) | ((unsigned long)pt & ~PAGE_MASK);
+               map = drm_lookup_map(offset, size, dev);
+               if (map && map->type == _DRM_AGP) {
+                       vunmap(pt);
+                       return;
+               }
+       }
+
+       iounmap(pt);
+}
+EXPORT_SYMBOL(drm_ioremapfree);
+
 #endif                         /* debug_memory */
index 3732a61c3762840553fd3e4470d71f050f9aaf26..714d9aedcff5dd38200eaf18dfcf029f1a36722c 100644 (file)
 # endif
 #endif
 
-/*
- * Find the drm_map that covers the range [offset, offset+size).
- */
-static inline drm_map_t *drm_lookup_map(unsigned long offset,
-                                       unsigned long size, drm_device_t * dev)
-{
-       struct list_head *list;
-       drm_map_list_t *r_list;
-       drm_map_t *map;
-
-       list_for_each(list, &dev->maplist->head) {
-               r_list = (drm_map_list_t *) list;
-               map = r_list->map;
-               if (!map)
-                       continue;
-               if (map->offset <= offset
-                   && (offset + size) <= (map->offset + map->size))
-                       return map;
-       }
-       return NULL;
-}
-
-static inline void *agp_remap(unsigned long offset, unsigned long size,
-                             drm_device_t * dev)
-{
-       unsigned long *phys_addr_map, i, num_pages =
-           PAGE_ALIGN(size) / PAGE_SIZE;
-       struct drm_agp_mem *agpmem;
-       struct page **page_map;
-       void *addr;
-
-       size = PAGE_ALIGN(size);
-
-#ifdef __alpha__
-       offset -= dev->hose->mem_space->start;
-#endif
-
-       for (agpmem = dev->agp->memory; agpmem; agpmem = agpmem->next)
-               if (agpmem->bound <= offset
-                   && (agpmem->bound + (agpmem->pages << PAGE_SHIFT)) >=
-                   (offset + size))
-                       break;
-       if (!agpmem)
-               return NULL;
-
-       /*
-        * OK, we're mapping AGP space on a chipset/platform on which memory accesses by
-        * the CPU do not get remapped by the GART.  We fix this by using the kernel's
-        * page-table instead (that's probably faster anyhow...).
-        */
-       /* note: use vmalloc() because num_pages could be large... */
-       page_map = vmalloc(num_pages * sizeof(struct page *));
-       if (!page_map)
-               return NULL;
-
-       phys_addr_map =
-           agpmem->memory->memory + (offset - agpmem->bound) / PAGE_SIZE;
-       for (i = 0; i < num_pages; ++i)
-               page_map[i] = pfn_to_page(phys_addr_map[i] >> PAGE_SHIFT);
-       addr = vmap(page_map, num_pages, VM_IOREMAP, PAGE_AGP);
-       vfree(page_map);
-
-       return addr;
-}
-
 static inline unsigned long drm_follow_page(void *vaddr)
 {
        pgd_t *pgd = pgd_offset_k((unsigned long)vaddr);
@@ -133,18 +68,6 @@ static inline unsigned long drm_follow_page(void *vaddr)
 
 #else                          /* __OS_HAS_AGP */
 
-static inline drm_map_t *drm_lookup_map(unsigned long offset,
-                                       unsigned long size, drm_device_t * dev)
-{
-       return NULL;
-}
-
-static inline void *agp_remap(unsigned long offset, unsigned long size,
-                             drm_device_t * dev)
-{
-       return NULL;
-}
-
 static inline unsigned long drm_follow_page(void *vaddr)
 {
        return 0;
@@ -152,51 +75,8 @@ static inline unsigned long drm_follow_page(void *vaddr)
 
 #endif
 
-static inline void *drm_ioremap(unsigned long offset, unsigned long size,
-                               drm_device_t * dev)
-{
-       if (drm_core_has_AGP(dev) && dev->agp && dev->agp->cant_use_aperture) {
-               drm_map_t *map = drm_lookup_map(offset, size, dev);
-
-               if (map && map->type == _DRM_AGP)
-                       return agp_remap(offset, size, dev);
-       }
-       return ioremap(offset, size);
-}
-
-static inline void *drm_ioremap_nocache(unsigned long offset,
-                                       unsigned long size, drm_device_t * dev)
-{
-       if (drm_core_has_AGP(dev) && dev->agp && dev->agp->cant_use_aperture) {
-               drm_map_t *map = drm_lookup_map(offset, size, dev);
-
-               if (map && map->type == _DRM_AGP)
-                       return agp_remap(offset, size, dev);
-       }
-       return ioremap_nocache(offset, size);
-}
-
-static inline void drm_ioremapfree(void *pt, unsigned long size,
-                                  drm_device_t * dev)
-{
-       /*
-        * This is a bit ugly.  It would be much cleaner if the DRM API would use separate
-        * routines for handling mappings in the AGP space.  Hopefully this can be done in
-        * a future revision of the interface...
-        */
-       if (drm_core_has_AGP(dev) && dev->agp && dev->agp->cant_use_aperture
-           && ((unsigned long)pt >= VMALLOC_START
-               && (unsigned long)pt < VMALLOC_END)) {
-               unsigned long offset;
-               drm_map_t *map;
-
-               offset = drm_follow_page(pt) | ((unsigned long)pt & ~PAGE_MASK);
-               map = drm_lookup_map(offset, size, dev);
-               if (map && map->type == _DRM_AGP) {
-                       vunmap(pt);
-                       return;
-               }
-       }
+void *drm_ioremap(unsigned long offset, unsigned long size,
+                               drm_device_t * dev);
 
-       iounmap(pt);
-}
+void drm_ioremapfree(void *pt, unsigned long size,
+                                  drm_device_t * dev);
index 7868341817da2f538f55764eb14055d096ff4df8..6543b9a14c42e677038bd001309e35143c5a10a1 100644 (file)
@@ -229,6 +229,7 @@ void *drm_ioremap (unsigned long offset, unsigned long size,
        return pt;
 }
 
+#if 0
 void *drm_ioremap_nocache (unsigned long offset, unsigned long size,
                            drm_device_t * dev) {
        void *pt;
@@ -251,6 +252,7 @@ void *drm_ioremap_nocache (unsigned long offset, unsigned long size,
        spin_unlock(&drm_mem_lock);
        return pt;
 }
+#endif  /*  0  */
 
 void drm_ioremapfree (void *pt, unsigned long size, drm_device_t * dev) {
        int alloc_count;
index b28ca9cea8a2a73c4f2c463fb762dc5fd94bae34..86a0f1c2209111075eb096d971271e08082f9e76 100644 (file)
@@ -37,6 +37,7 @@
  */
 
 #include <linux/pci.h>
+#include <linux/dma-mapping.h>
 #include "drmP.h"
 
 /**********************************************************************/
index 6152415644e9b4a327549841df072edd0c45f8e5..c33d068cde19f459b712147f0261829a59708804 100644 (file)
@@ -196,9 +196,9 @@ via_driver_irq_wait(drm_device_t * dev, unsigned int irq, int force_sequence,
 {
        drm_via_private_t *dev_priv = (drm_via_private_t *) dev->dev_private;
        unsigned int cur_irq_sequence;
-       drm_via_irq_t *cur_irq = dev_priv->via_irqs;
+       drm_via_irq_t *cur_irq;
        int ret = 0;
-       maskarray_t *masks = dev_priv->irq_masks;
+       maskarray_t *masks;
        int real_irq;
 
        DRM_DEBUG("%s\n", __FUNCTION__);
@@ -221,8 +221,9 @@ via_driver_irq_wait(drm_device_t * dev, unsigned int irq, int force_sequence,
                          __FUNCTION__, irq);
                return DRM_ERR(EINVAL);
        }
-       
-       cur_irq += real_irq;
+
+       masks = dev_priv->irq_masks;
+       cur_irq = dev_priv->via_irqs + real_irq;
 
        if (masks[real_irq][2] && !force_sequence) {
                DRM_WAIT_ON(ret, cur_irq->irq_queue, 3 * DRM_HZ,
@@ -247,11 +248,12 @@ void via_driver_irq_preinstall(drm_device_t * dev)
 {
        drm_via_private_t *dev_priv = (drm_via_private_t *) dev->dev_private;
        u32 status;
-       drm_via_irq_t *cur_irq = dev_priv->via_irqs;
+       drm_via_irq_t *cur_irq;
        int i;
 
        DRM_DEBUG("driver_irq_preinstall: dev_priv: %p\n", dev_priv);
        if (dev_priv) {
+               cur_irq = dev_priv->via_irqs;
 
                dev_priv->irq_enable_mask = VIA_IRQ_VBLANK_ENABLE;
                dev_priv->irq_pending_mask = VIA_IRQ_VBLANK_PENDING;
index a229915ce1b26b5ebb8d088ea9a125765abee686..87dcaa237f0753eb3e9f821bf17bb27b211b729d 100644 (file)
@@ -490,7 +490,7 @@ for (i = 0; i < 10; i++)                    \
                release_region(dtlk_portlist[i], DTLK_IO_EXTENT);
        }
 
-       printk(KERN_INFO "\nDoubleTalk PC - not found\n");
+       printk(KERN_INFO "DoubleTalk PC - not found\n");
        return -ENODEV;
 }
 
index 58dcdee1cd719ab3d165907fb76f53c6e55c5db6..0030cd8e2e956cb436ae781c854ba41df23058a9 100644 (file)
@@ -165,7 +165,7 @@ static int bt_start_transaction(struct si_sm_data *bt,
 {
        unsigned int i;
 
-       if ((size < 2) || (size > IPMI_MAX_MSG_LENGTH))
+       if ((size < 2) || (size > (IPMI_MAX_MSG_LENGTH - 2)))
               return -1;
 
        if ((bt->state != BT_STATE_IDLE) && (bt->state != BT_STATE_HOSED))
index 0ded046d5aa80011e5e267a0d1b8ca72fec69475..9f2f8fdec69a4b642003efd929aa4faea1fb293f 100644 (file)
@@ -941,6 +941,7 @@ int ipmi_set_gets_events(ipmi_user_t user, int val)
                        list_del(&msg->link);
                        list_add_tail(&msg->link, &msgs);
                }
+               intf->waiting_events_count = 0;
        }
 
        /* Hold the events lock while doing this to preserve order. */
@@ -2916,6 +2917,7 @@ static int handle_read_event_rsp(ipmi_smi_t          intf,
 
                copy_event_into_recv_msg(recv_msg, msg);
                list_add_tail(&(recv_msg->link), &(intf->waiting_events));
+               intf->waiting_events_count++;
        } else {
                /* There's too many things in the queue, discard this
                   message. */
index a86c0f29953e7c1e2fa5921af10bb7ba88ebe062..b36eef0e9d199ff2751ddba5b77d812bacf489cb 100644 (file)
@@ -2198,11 +2198,11 @@ static inline void wait_for_timer_and_thread(struct smi_info *smi_info)
        }
 }
 
-static struct ipmi_default_vals
+static __devinitdata struct ipmi_default_vals
 {
        int type;
        int port;
-} __devinit ipmi_defaults[] =
+} ipmi_defaults[] =
 {
        { .type = SI_KCS, .port = 0xca2 },
        { .type = SI_SMIC, .port = 0xca9 },
index 86be04b241e1b5c9fb5dd477f7766b47629af604..58f3512c52e16f1b92de5307c9e482a1ccf5b91f 100644 (file)
@@ -1584,7 +1584,6 @@ u32 secure_ipv6_port_ephemeral(const __u32 *saddr, const __u32 *daddr, __u16 dpo
 
        return twothirdsMD4Transform(daddr, hash);
 }
-EXPORT_SYMBOL(secure_ipv6_port_ephemeral);
 #endif
 
 #if defined(CONFIG_IP_DCCP) || defined(CONFIG_IP_DCCP_MODULE)
index f8dd8527c6aa9d8e30d17a26b64ed5b5dcccb2f7..a90f5d97df35dc8c262145efe0187085a6bd2009 100644 (file)
@@ -1341,6 +1341,9 @@ static int __devinit sonypi_probe(struct platform_device *dev)
        else if ((pcidev = pci_get_device(PCI_VENDOR_ID_INTEL,
                                          PCI_DEVICE_ID_INTEL_ICH6_1, NULL)))
                sonypi_device.model = SONYPI_DEVICE_MODEL_TYPE3;
+       else if ((pcidev = pci_get_device(PCI_VENDOR_ID_INTEL,
+                                         PCI_DEVICE_ID_INTEL_ICH7_1, NULL)))
+               sonypi_device.model = SONYPI_DEVICE_MODEL_TYPE3;
        else
                sonypi_device.model = SONYPI_DEVICE_MODEL_TYPE2;
 
index 2546637a55c0365ee8f37073b08427a777723404..f58ad7f6826738846e606aab135161b92cc83dcc 100644 (file)
@@ -327,7 +327,7 @@ static ssize_t store_received_ref_clk3a(struct device *d,
        return strnlen(buf, count);
 }
 
-static DEVICE_ATTR(received_ref_clk3a, S_IWUGO, NULL,
+static DEVICE_ATTR(received_ref_clk3a, (S_IWUSR|S_IWGRP), NULL,
                store_received_ref_clk3a);
 
 
@@ -349,7 +349,7 @@ static ssize_t store_received_ref_clk3b(struct device *d,
        return strnlen(buf, count);
 }
 
-static DEVICE_ATTR(received_ref_clk3b, S_IWUGO, NULL,
+static DEVICE_ATTR(received_ref_clk3b, (S_IWUSR|S_IWGRP), NULL,
                store_received_ref_clk3b);
 
 
@@ -371,7 +371,7 @@ static ssize_t store_enable_clk3b_output(struct device *d,
        return strnlen(buf, count);
 }
 
-static DEVICE_ATTR(enable_clk3b_output, S_IWUGO, NULL,
+static DEVICE_ATTR(enable_clk3b_output, (S_IWUSR|S_IWGRP), NULL,
                store_enable_clk3b_output);
 
 static ssize_t store_enable_clk3a_output(struct device *d,
@@ -392,7 +392,7 @@ static ssize_t store_enable_clk3a_output(struct device *d,
        return strnlen(buf, count);
 }
 
-static DEVICE_ATTR(enable_clk3a_output, S_IWUGO, NULL,
+static DEVICE_ATTR(enable_clk3a_output, (S_IWUSR|S_IWGRP), NULL,
                store_enable_clk3a_output);
 
 static ssize_t store_enable_clkb1_output(struct device *d,
@@ -413,7 +413,7 @@ static ssize_t store_enable_clkb1_output(struct device *d,
        return strnlen(buf, count);
 }
 
-static DEVICE_ATTR(enable_clkb1_output, S_IWUGO, NULL,
+static DEVICE_ATTR(enable_clkb1_output, (S_IWUSR|S_IWGRP), NULL,
                store_enable_clkb1_output);
 
 
@@ -435,7 +435,7 @@ static ssize_t store_enable_clka1_output(struct device *d,
        return strnlen(buf, count);
 }
 
-static DEVICE_ATTR(enable_clka1_output, S_IWUGO, NULL,
+static DEVICE_ATTR(enable_clka1_output, (S_IWUSR|S_IWGRP), NULL,
                store_enable_clka1_output);
 
 static ssize_t store_enable_clkb0_output(struct device *d,
@@ -456,7 +456,7 @@ static ssize_t store_enable_clkb0_output(struct device *d,
        return strnlen(buf, count);
 }
 
-static DEVICE_ATTR(enable_clkb0_output, S_IWUGO, NULL,
+static DEVICE_ATTR(enable_clkb0_output, (S_IWUSR|S_IWGRP), NULL,
                store_enable_clkb0_output);
 
 static ssize_t store_enable_clka0_output(struct device *d,
@@ -477,7 +477,7 @@ static ssize_t store_enable_clka0_output(struct device *d,
        return strnlen(buf, count);
 }
 
-static DEVICE_ATTR(enable_clka0_output, S_IWUGO, NULL,
+static DEVICE_ATTR(enable_clka0_output, (S_IWUSR|S_IWGRP), NULL,
                store_enable_clka0_output);
 
 static ssize_t store_select_amcb2_transmit_clock(struct device *d,
@@ -519,7 +519,7 @@ static ssize_t store_select_amcb2_transmit_clock(struct device *d,
        return strnlen(buf, count);
 }
 
-static DEVICE_ATTR(select_amcb2_transmit_clock, S_IWUGO, NULL,
+static DEVICE_ATTR(select_amcb2_transmit_clock, (S_IWUSR|S_IWGRP), NULL,
        store_select_amcb2_transmit_clock);
 
 static ssize_t store_select_amcb1_transmit_clock(struct device *d,
@@ -560,7 +560,7 @@ static ssize_t store_select_amcb1_transmit_clock(struct device *d,
        return strnlen(buf, count);
 }
 
-static DEVICE_ATTR(select_amcb1_transmit_clock, S_IWUGO, NULL,
+static DEVICE_ATTR(select_amcb1_transmit_clock, (S_IWUSR|S_IWGRP), NULL,
                store_select_amcb1_transmit_clock);
 
 static ssize_t store_select_redundant_clock(struct device *d,
@@ -581,7 +581,7 @@ static ssize_t store_select_redundant_clock(struct device *d,
        return strnlen(buf, count);
 }
 
-static DEVICE_ATTR(select_redundant_clock, S_IWUGO, NULL,
+static DEVICE_ATTR(select_redundant_clock, (S_IWUSR|S_IWGRP), NULL,
                store_select_redundant_clock);
 
 static ssize_t store_select_ref_frequency(struct device *d,
@@ -602,7 +602,7 @@ static ssize_t store_select_ref_frequency(struct device *d,
        return strnlen(buf, count);
 }
 
-static DEVICE_ATTR(select_ref_frequency, S_IWUGO, NULL,
+static DEVICE_ATTR(select_ref_frequency, (S_IWUSR|S_IWGRP), NULL,
                store_select_ref_frequency);
 
 static ssize_t store_filter_select(struct device *d,
@@ -623,7 +623,7 @@ static ssize_t store_filter_select(struct device *d,
        return strnlen(buf, count);
 }
 
-static DEVICE_ATTR(filter_select, S_IWUGO, NULL, store_filter_select);
+static DEVICE_ATTR(filter_select, (S_IWUSR|S_IWGRP), NULL, store_filter_select);
 
 static ssize_t store_hardware_switching_mode(struct device *d,
                 struct device_attribute *attr, const char *buf, size_t count)
@@ -643,7 +643,7 @@ static ssize_t store_hardware_switching_mode(struct device *d,
        return strnlen(buf, count);
 }
 
-static DEVICE_ATTR(hardware_switching_mode, S_IWUGO, NULL,
+static DEVICE_ATTR(hardware_switching_mode, (S_IWUSR|S_IWGRP), NULL,
                store_hardware_switching_mode);
 
 static ssize_t store_hardware_switching(struct device *d,
@@ -664,7 +664,7 @@ static ssize_t store_hardware_switching(struct device *d,
        return strnlen(buf, count);
 }
 
-static DEVICE_ATTR(hardware_switching, S_IWUGO, NULL,
+static DEVICE_ATTR(hardware_switching, (S_IWUSR|S_IWGRP), NULL,
                store_hardware_switching);
 
 static ssize_t store_refalign (struct device *d,
@@ -684,7 +684,7 @@ static ssize_t store_refalign (struct device *d,
        return strnlen(buf, count);
 }
 
-static DEVICE_ATTR(refalign, S_IWUGO, NULL, store_refalign);
+static DEVICE_ATTR(refalign, (S_IWUSR|S_IWGRP), NULL, store_refalign);
 
 static ssize_t store_mode_select (struct device *d,
                 struct device_attribute *attr, const char *buf, size_t count)
@@ -704,7 +704,7 @@ static ssize_t store_mode_select (struct device *d,
        return strnlen(buf, count);
 }
 
-static DEVICE_ATTR(mode_select, S_IWUGO, NULL, store_mode_select);
+static DEVICE_ATTR(mode_select, (S_IWUSR|S_IWGRP), NULL, store_mode_select);
 
 static ssize_t store_reset (struct device *d,
                 struct device_attribute *attr, const char *buf, size_t count)
@@ -724,7 +724,7 @@ static ssize_t store_reset (struct device *d,
        return strnlen(buf, count);
 }
 
-static DEVICE_ATTR(reset, S_IWUGO, NULL, store_reset);
+static DEVICE_ATTR(reset, (S_IWUSR|S_IWGRP), NULL, store_reset);
 
 static struct attribute *tlclk_sysfs_entries[] = {
        &dev_attr_current_ref.attr,
index 98b126c2ded862f5fd7747b8acad1a7a16d47aee..f07637a8f88fd038bac53f44c7181ea901c2ec51 100644 (file)
@@ -351,10 +351,10 @@ int tty_buffer_request_room(struct tty_struct *tty, size_t size)
        spin_unlock_irqrestore(&tty->buf.lock, flags);
        return size;
 }
-
 EXPORT_SYMBOL_GPL(tty_buffer_request_room);
 
-int tty_insert_flip_string(struct tty_struct *tty, const unsigned char *chars, size_t size)
+int tty_insert_flip_string(struct tty_struct *tty, const unsigned char *chars,
+                               size_t size)
 {
        int copied = 0;
        do {
@@ -368,17 +368,16 @@ int tty_insert_flip_string(struct tty_struct *tty, const unsigned char *chars, s
                tb->used += space;
                copied += space;
                chars += space;
-/*             printk("Flip insert %d.\n", space); */
        }
        /* There is a small chance that we need to split the data over
           several buffers. If this is the case we must loop */
        while (unlikely(size > copied));
        return copied;
 }
-
 EXPORT_SYMBOL(tty_insert_flip_string);
 
-int tty_insert_flip_string_flags(struct tty_struct *tty, const unsigned char *chars, const char *flags, size_t size)
+int tty_insert_flip_string_flags(struct tty_struct *tty,
+               const unsigned char *chars, const char *flags, size_t size)
 {
        int copied = 0;
        do {
@@ -399,9 +398,20 @@ int tty_insert_flip_string_flags(struct tty_struct *tty, const unsigned char *ch
        while (unlikely(size > copied));
        return copied;
 }
-
 EXPORT_SYMBOL_GPL(tty_insert_flip_string_flags);
 
+void tty_schedule_flip(struct tty_struct *tty)
+{
+       unsigned long flags;
+       spin_lock_irqsave(&tty->buf.lock, flags);
+       if (tty->buf.tail != NULL) {
+               tty->buf.tail->active = 0;
+               tty->buf.tail->commit = tty->buf.tail->used;
+       }
+       spin_unlock_irqrestore(&tty->buf.lock, flags);
+       schedule_delayed_work(&tty->buf.work, 1);
+}
+EXPORT_SYMBOL(tty_schedule_flip);
 
 /*
  *     Prepare a block of space in the buffer for data. Returns the length
@@ -1730,7 +1740,7 @@ static void release_dev(struct file * filp)
 {
        struct tty_struct *tty, *o_tty;
        int     pty_master, tty_closing, o_tty_closing, do_sleep;
-       int     devpts_master, devpts;
+       int     devpts;
        int     idx;
        char    buf[64];
        unsigned long flags;
@@ -1747,7 +1757,6 @@ static void release_dev(struct file * filp)
        pty_master = (tty->driver->type == TTY_DRIVER_TYPE_PTY &&
                      tty->driver->subtype == PTY_TYPE_MASTER);
        devpts = (tty->driver->flags & TTY_DRIVER_DEVPTS_MEM) != 0;
-       devpts_master = pty_master && devpts;
        o_tty = tty->link;
 
 #ifdef TTY_PARANOIA_CHECK
@@ -2185,6 +2194,7 @@ static int ptmx_open(struct inode * inode, struct file * filp)
                return 0;
 out1:
        release_dev(filp);
+       return retval;
 out:
        down(&allocated_ptys_lock);
        idr_remove(&allocated_ptys, index);
@@ -2713,7 +2723,11 @@ static void __do_SAK(void *arg)
                }
                task_lock(p);
                if (p->files) {
-                       rcu_read_lock();
+                       /*
+                        * We don't take a ref to the file, so we must
+                        * hold ->file_lock instead.
+                        */
+                       spin_lock(&p->files->file_lock);
                        fdt = files_fdtable(p->files);
                        for (i=0; i < fdt->max_fds; i++) {
                                filp = fcheck_files(p->files, i);
@@ -2724,11 +2738,11 @@ static void __do_SAK(void *arg)
                                        printk(KERN_NOTICE "SAK: killed process %d"
                                            " (%s): fd#%d opened to the tty\n",
                                            p->pid, p->comm, i);
-                                       send_sig(SIGKILL, p, 1);
+                                       force_sig(SIGKILL, p);
                                        break;
                                }
                        }
-                       rcu_read_unlock();
+                       spin_unlock(&p->files->file_lock);
                }
                task_unlock(p);
        } while_each_thread(g, p);
diff --git a/drivers/char/vr41xx_rtc.c b/drivers/char/vr41xx_rtc.c
deleted file mode 100644 (file)
index b109d9a..0000000
+++ /dev/null
@@ -1,717 +0,0 @@
-/*
- *  Driver for NEC VR4100 series  Real Time Clock unit.
- *
- *  Copyright (C) 2003-2005  Yoichi Yuasa <yoichi_yuasa@tripeaks.co.jp>
- *
- *  This program is free software; you can redistribute it and/or modify
- *  it under the terms of the GNU General Public License as published by
- *  the Free Software Foundation; either version 2 of the License, or
- *  (at your option) any later version.
- *
- *  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., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
- */
-#include <linux/platform_device.h>
-#include <linux/fs.h>
-#include <linux/init.h>
-#include <linux/ioport.h>
-#include <linux/irq.h>
-#include <linux/mc146818rtc.h>
-#include <linux/miscdevice.h>
-#include <linux/module.h>
-#include <linux/poll.h>
-#include <linux/rtc.h>
-#include <linux/spinlock.h>
-#include <linux/types.h>
-#include <linux/wait.h>
-
-#include <asm/div64.h>
-#include <asm/io.h>
-#include <asm/time.h>
-#include <asm/uaccess.h>
-#include <asm/vr41xx/vr41xx.h>
-
-MODULE_AUTHOR("Yoichi Yuasa <yoichi_yuasa@tripeaks.co.jp>");
-MODULE_DESCRIPTION("NEC VR4100 series RTC driver");
-MODULE_LICENSE("GPL");
-
-#define RTC1_TYPE1_START       0x0b0000c0UL
-#define RTC1_TYPE1_END         0x0b0000dfUL
-#define RTC2_TYPE1_START       0x0b0001c0UL
-#define RTC2_TYPE1_END         0x0b0001dfUL
-
-#define RTC1_TYPE2_START       0x0f000100UL
-#define RTC1_TYPE2_END         0x0f00011fUL
-#define RTC2_TYPE2_START       0x0f000120UL
-#define RTC2_TYPE2_END         0x0f00013fUL
-
-#define RTC1_SIZE              0x20
-#define RTC2_SIZE              0x20
-
-/* RTC 1 registers */
-#define ETIMELREG              0x00
-#define ETIMEMREG              0x02
-#define ETIMEHREG              0x04
-/* RFU */
-#define ECMPLREG               0x08
-#define ECMPMREG               0x0a
-#define ECMPHREG               0x0c
-/* RFU */
-#define RTCL1LREG              0x10
-#define RTCL1HREG              0x12
-#define RTCL1CNTLREG           0x14
-#define RTCL1CNTHREG           0x16
-#define RTCL2LREG              0x18
-#define RTCL2HREG              0x1a
-#define RTCL2CNTLREG           0x1c
-#define RTCL2CNTHREG           0x1e
-
-/* RTC 2 registers */
-#define TCLKLREG               0x00
-#define TCLKHREG               0x02
-#define TCLKCNTLREG            0x04
-#define TCLKCNTHREG            0x06
-/* RFU */
-#define RTCINTREG              0x1e
- #define TCLOCK_INT            0x08
- #define RTCLONG2_INT          0x04
- #define RTCLONG1_INT          0x02
- #define ELAPSEDTIME_INT       0x01
-
-#define RTC_FREQUENCY          32768
-#define MAX_PERIODIC_RATE      6553
-#define MAX_USER_PERIODIC_RATE 64
-
-static void __iomem *rtc1_base;
-static void __iomem *rtc2_base;
-
-#define rtc1_read(offset)              readw(rtc1_base + (offset))
-#define rtc1_write(offset, value)      writew((value), rtc1_base + (offset))
-
-#define rtc2_read(offset)              readw(rtc2_base + (offset))
-#define rtc2_write(offset, value)      writew((value), rtc2_base + (offset))
-
-static unsigned long epoch = 1970;     /* Jan 1 1970 00:00:00 */
-
-static spinlock_t rtc_task_lock;
-static wait_queue_head_t rtc_wait;
-static unsigned long rtc_irq_data;
-static struct fasync_struct *rtc_async_queue;
-static rtc_task_t *rtc_callback;
-static char rtc_name[] = "RTC";
-static unsigned long periodic_frequency;
-static unsigned long periodic_count;
-
-typedef enum {
-       RTC_RELEASE,
-       RTC_OPEN,
-} rtc_status_t;
-
-static rtc_status_t rtc_status;
-
-typedef enum {
-       FUNCTION_RTC_IOCTL,
-       FUNCTION_RTC_CONTROL,
-} rtc_callfrom_t;
-
-struct resource rtc_resource[2] = {
-       {       .name   = rtc_name,
-               .flags  = IORESOURCE_MEM,       },
-       {       .name   = rtc_name,
-               .flags  = IORESOURCE_MEM,       },
-};
-
-static inline unsigned long read_elapsed_second(void)
-{
-       unsigned long first_low, first_mid, first_high;
-       unsigned long second_low, second_mid, second_high;
-
-       do {
-               first_low = rtc1_read(ETIMELREG);
-               first_mid = rtc1_read(ETIMEMREG);
-               first_high = rtc1_read(ETIMEHREG);
-               second_low = rtc1_read(ETIMELREG);
-               second_mid = rtc1_read(ETIMEMREG);
-               second_high = rtc1_read(ETIMEHREG);
-       } while (first_low != second_low || first_mid != second_mid ||
-                first_high != second_high);
-
-       return (first_high << 17) | (first_mid << 1) | (first_low >> 15);
-}
-
-static inline void write_elapsed_second(unsigned long sec)
-{
-       spin_lock_irq(&rtc_lock);
-
-       rtc1_write(ETIMELREG, (uint16_t)(sec << 15));
-       rtc1_write(ETIMEMREG, (uint16_t)(sec >> 1));
-       rtc1_write(ETIMEHREG, (uint16_t)(sec >> 17));
-
-       spin_unlock_irq(&rtc_lock);
-}
-
-static void set_alarm(struct rtc_time *time)
-{
-       unsigned long alarm_sec;
-
-       alarm_sec = mktime(time->tm_year + 1900, time->tm_mon + 1, time->tm_mday,
-                          time->tm_hour, time->tm_min, time->tm_sec);
-
-       spin_lock_irq(&rtc_lock);
-
-       rtc1_write(ECMPLREG, (uint16_t)(alarm_sec << 15));
-       rtc1_write(ECMPMREG, (uint16_t)(alarm_sec >> 1));
-       rtc1_write(ECMPHREG, (uint16_t)(alarm_sec >> 17));
-
-       spin_unlock_irq(&rtc_lock);
-}
-
-static void read_alarm(struct rtc_time *time)
-{
-       unsigned long low, mid, high;
-
-       spin_lock_irq(&rtc_lock);
-
-       low = rtc1_read(ECMPLREG);
-       mid = rtc1_read(ECMPMREG);
-       high = rtc1_read(ECMPHREG);
-
-       spin_unlock_irq(&rtc_lock);
-
-       to_tm((high << 17) | (mid << 1) | (low >> 15), time);
-       time->tm_year -= 1900;
-}
-
-static void read_time(struct rtc_time *time)
-{
-       unsigned long epoch_sec, elapsed_sec;
-
-       epoch_sec = mktime(epoch, 1, 1, 0, 0, 0);
-       elapsed_sec = read_elapsed_second();
-
-       to_tm(epoch_sec + elapsed_sec, time);
-       time->tm_year -= 1900;
-}
-
-static void set_time(struct rtc_time *time)
-{
-       unsigned long epoch_sec, current_sec;
-
-       epoch_sec = mktime(epoch, 1, 1, 0, 0, 0);
-       current_sec = mktime(time->tm_year + 1900, time->tm_mon + 1, time->tm_mday,
-                            time->tm_hour, time->tm_min, time->tm_sec);
-
-       write_elapsed_second(current_sec - epoch_sec);
-}
-
-static ssize_t rtc_read(struct file *file, char __user *buf, size_t count, loff_t *ppos)
-{
-       DECLARE_WAITQUEUE(wait, current);
-       unsigned long irq_data;
-       int retval = 0;
-
-       if (count != sizeof(unsigned int) && count != sizeof(unsigned long))
-               return -EINVAL;
-
-       add_wait_queue(&rtc_wait, &wait);
-
-       do {
-               __set_current_state(TASK_INTERRUPTIBLE);
-
-               spin_lock_irq(&rtc_lock);
-               irq_data = rtc_irq_data;
-               rtc_irq_data = 0;
-               spin_unlock_irq(&rtc_lock);
-
-               if (irq_data != 0)
-                       break;
-
-               if (file->f_flags & O_NONBLOCK) {
-                       retval = -EAGAIN;
-                       break;
-               }
-
-               if (signal_pending(current)) {
-                       retval = -ERESTARTSYS;
-                       break;
-               }
-       } while (1);
-
-       if (retval == 0) {
-               if (count == sizeof(unsigned int)) {
-                       retval = put_user(irq_data, (unsigned int __user *)buf);
-                       if (retval == 0)
-                               retval = sizeof(unsigned int);
-               } else {
-                       retval = put_user(irq_data, (unsigned long __user *)buf);
-                       if (retval == 0)
-                               retval = sizeof(unsigned long);
-               }
-
-       }
-
-       __set_current_state(TASK_RUNNING);
-       remove_wait_queue(&rtc_wait, &wait);
-
-       return retval;
-}
-
-static unsigned int rtc_poll(struct file *file, struct poll_table_struct *table)
-{
-       poll_wait(file, &rtc_wait, table);
-
-       if (rtc_irq_data != 0)
-               return POLLIN | POLLRDNORM;
-
-       return 0;
-}
-
-static int rtc_do_ioctl(unsigned int cmd, unsigned long arg, rtc_callfrom_t from)
-{
-       struct rtc_time time;
-       unsigned long count;
-
-       switch (cmd) {
-       case RTC_AIE_ON:
-               enable_irq(ELAPSEDTIME_IRQ);
-               break;
-       case RTC_AIE_OFF:
-               disable_irq(ELAPSEDTIME_IRQ);
-               break;
-       case RTC_PIE_ON:
-               enable_irq(RTCLONG1_IRQ);
-               break;
-       case RTC_PIE_OFF:
-               disable_irq(RTCLONG1_IRQ);
-               break;
-       case RTC_ALM_SET:
-               if (copy_from_user(&time, (struct rtc_time __user *)arg,
-                                  sizeof(struct rtc_time)))
-                       return -EFAULT;
-
-               set_alarm(&time);
-               break;
-       case RTC_ALM_READ:
-               memset(&time, 0, sizeof(struct rtc_time));
-               read_alarm(&time);
-               break;
-       case RTC_RD_TIME:
-               memset(&time, 0, sizeof(struct rtc_time));
-               read_time(&time);
-               if (copy_to_user((void __user *)arg, &time, sizeof(struct rtc_time)))
-                       return -EFAULT;
-               break;
-       case RTC_SET_TIME:
-               if (capable(CAP_SYS_TIME) == 0)
-                       return -EACCES;
-
-               if (copy_from_user(&time, (struct rtc_time __user *)arg,
-                                  sizeof(struct rtc_time)))
-                       return -EFAULT;
-
-               set_time(&time);
-               break;
-       case RTC_IRQP_READ:
-               return put_user(periodic_frequency, (unsigned long __user *)arg);
-               break;
-       case RTC_IRQP_SET:
-               if (arg > MAX_PERIODIC_RATE)
-                       return -EINVAL;
-
-               if (from == FUNCTION_RTC_IOCTL && arg > MAX_USER_PERIODIC_RATE &&
-                   capable(CAP_SYS_RESOURCE) == 0)
-                       return -EACCES;
-
-               periodic_frequency = arg;
-
-               count = RTC_FREQUENCY;
-               do_div(count, arg);
-
-               periodic_count = count;
-
-               spin_lock_irq(&rtc_lock);
-
-               rtc1_write(RTCL1LREG, count);
-               rtc1_write(RTCL1HREG, count >> 16);
-
-               spin_unlock_irq(&rtc_lock);
-               break;
-       case RTC_EPOCH_READ:
-               return put_user(epoch, (unsigned long __user *)arg);
-       case RTC_EPOCH_SET:
-               /* Doesn't support before 1900 */
-               if (arg < 1900)
-                       return -EINVAL;
-
-               if (capable(CAP_SYS_TIME) == 0)
-                       return -EACCES;
-
-               epoch = arg;
-               break;
-       default:
-               return -EINVAL;
-       }
-
-       return 0;
-}
-
-static int rtc_ioctl(struct inode *inode, struct file *file, unsigned int cmd,
-                     unsigned long arg)
-{
-       return rtc_do_ioctl(cmd, arg, FUNCTION_RTC_IOCTL);
-}
-
-static int rtc_open(struct inode *inode, struct file *file)
-{
-       spin_lock_irq(&rtc_lock);
-
-       if (rtc_status == RTC_OPEN) {
-               spin_unlock_irq(&rtc_lock);
-               return -EBUSY;
-       }
-
-       rtc_status = RTC_OPEN;
-       rtc_irq_data = 0;
-
-       spin_unlock_irq(&rtc_lock);
-
-       return 0;
-}
-
-static int rtc_release(struct inode *inode, struct file *file)
-{
-       if (file->f_flags & FASYNC)
-               (void)fasync_helper(-1, file, 0, &rtc_async_queue);
-
-       spin_lock_irq(&rtc_lock);
-
-       rtc1_write(ECMPLREG, 0);
-       rtc1_write(ECMPMREG, 0);
-       rtc1_write(ECMPHREG, 0);
-       rtc1_write(RTCL1LREG, 0);
-       rtc1_write(RTCL1HREG, 0);
-
-       rtc_status = RTC_RELEASE;
-
-       spin_unlock_irq(&rtc_lock);
-
-       disable_irq(ELAPSEDTIME_IRQ);
-       disable_irq(RTCLONG1_IRQ);
-
-       return 0;
-}
-
-static int rtc_fasync(int fd, struct file *file, int on)
-{
-       return fasync_helper(fd, file, on, &rtc_async_queue);
-}
-
-static struct file_operations rtc_fops = {
-       .owner          = THIS_MODULE,
-       .llseek         = no_llseek,
-       .read           = rtc_read,
-       .poll           = rtc_poll,
-       .ioctl          = rtc_ioctl,
-       .open           = rtc_open,
-       .release        = rtc_release,
-       .fasync         = rtc_fasync,
-};
-
-static irqreturn_t elapsedtime_interrupt(int irq, void *dev_id, struct pt_regs *regs)
-{
-       spin_lock(&rtc_lock);
-       rtc2_write(RTCINTREG, ELAPSEDTIME_INT);
-
-       rtc_irq_data += 0x100;
-       rtc_irq_data &= ~0xff;
-       rtc_irq_data |= RTC_AF;
-       spin_unlock(&rtc_lock);
-
-       spin_lock(&rtc_lock);
-       if (rtc_callback)
-               rtc_callback->func(rtc_callback->private_data);
-       spin_unlock(&rtc_lock);
-
-       wake_up_interruptible(&rtc_wait);
-
-       kill_fasync(&rtc_async_queue, SIGIO, POLL_IN);
-
-       return IRQ_HANDLED;
-}
-
-static irqreturn_t rtclong1_interrupt(int irq, void *dev_id, struct pt_regs *regs)
-{
-       unsigned long count = periodic_count;
-
-       spin_lock(&rtc_lock);
-       rtc2_write(RTCINTREG, RTCLONG1_INT);
-
-       rtc1_write(RTCL1LREG, count);
-       rtc1_write(RTCL1HREG, count >> 16);
-
-       rtc_irq_data += 0x100;
-       rtc_irq_data &= ~0xff;
-       rtc_irq_data |= RTC_PF;
-       spin_unlock(&rtc_lock);
-
-       spin_lock(&rtc_task_lock);
-       if (rtc_callback)
-               rtc_callback->func(rtc_callback->private_data);
-       spin_unlock(&rtc_task_lock);
-
-       wake_up_interruptible(&rtc_wait);
-
-       kill_fasync(&rtc_async_queue, SIGIO, POLL_IN);
-
-       return IRQ_HANDLED;
-}
-
-int rtc_register(rtc_task_t *task)
-{
-       if (task == NULL || task->func == NULL)
-               return -EINVAL;
-
-       spin_lock_irq(&rtc_lock);
-       if (rtc_status == RTC_OPEN) {
-               spin_unlock_irq(&rtc_lock);
-               return -EBUSY;
-       }
-
-       spin_lock(&rtc_task_lock);
-       if (rtc_callback != NULL) {
-               spin_unlock(&rtc_task_lock);
-               spin_unlock_irq(&rtc_task_lock);
-               return -EBUSY;
-       }
-
-       rtc_callback = task;
-       spin_unlock(&rtc_task_lock);
-
-       rtc_status = RTC_OPEN;
-
-       spin_unlock_irq(&rtc_lock);
-
-       return 0;
-}
-
-EXPORT_SYMBOL_GPL(rtc_register);
-
-int rtc_unregister(rtc_task_t *task)
-{
-       spin_lock_irq(&rtc_task_lock);
-       if (task == NULL || rtc_callback != task) {
-               spin_unlock_irq(&rtc_task_lock);
-               return -ENXIO;
-       }
-
-       spin_lock(&rtc_lock);
-
-       rtc1_write(ECMPLREG, 0);
-       rtc1_write(ECMPMREG, 0);
-       rtc1_write(ECMPHREG, 0);
-       rtc1_write(RTCL1LREG, 0);
-       rtc1_write(RTCL1HREG, 0);
-
-       rtc_status = RTC_RELEASE;
-
-       spin_unlock(&rtc_lock);
-
-       rtc_callback = NULL;
-
-       spin_unlock_irq(&rtc_task_lock);
-
-       disable_irq(ELAPSEDTIME_IRQ);
-       disable_irq(RTCLONG1_IRQ);
-
-       return 0;
-}
-
-EXPORT_SYMBOL_GPL(rtc_unregister);
-
-int rtc_control(rtc_task_t *task, unsigned int cmd, unsigned long arg)
-{
-       int retval = 0;
-
-       spin_lock_irq(&rtc_task_lock);
-
-       if (rtc_callback != task)
-               retval = -ENXIO;
-       else
-               rtc_do_ioctl(cmd, arg, FUNCTION_RTC_CONTROL);
-
-       spin_unlock_irq(&rtc_task_lock);
-
-       return retval;
-}
-
-EXPORT_SYMBOL_GPL(rtc_control);
-
-static struct miscdevice rtc_miscdevice = {
-       .minor  = RTC_MINOR,
-       .name   = rtc_name,
-       .fops   = &rtc_fops,
-};
-
-static int __devinit rtc_probe(struct platform_device *pdev)
-{
-       unsigned int irq;
-       int retval;
-
-       if (pdev->num_resources != 2)
-               return -EBUSY;
-
-       rtc1_base = ioremap(pdev->resource[0].start, RTC1_SIZE);
-       if (rtc1_base == NULL)
-               return -EBUSY;
-
-       rtc2_base = ioremap(pdev->resource[1].start, RTC2_SIZE);
-       if (rtc2_base == NULL) {
-               iounmap(rtc1_base);
-               rtc1_base = NULL;
-               return -EBUSY;
-       }
-
-       retval = misc_register(&rtc_miscdevice);
-       if (retval < 0) {
-               iounmap(rtc1_base);
-               iounmap(rtc2_base);
-               rtc1_base = NULL;
-               rtc2_base = NULL;
-               return retval;
-       }
-
-       spin_lock_irq(&rtc_lock);
-
-       rtc1_write(ECMPLREG, 0);
-       rtc1_write(ECMPMREG, 0);
-       rtc1_write(ECMPHREG, 0);
-       rtc1_write(RTCL1LREG, 0);
-       rtc1_write(RTCL1HREG, 0);
-
-       rtc_status = RTC_RELEASE;
-       rtc_irq_data = 0;
-
-       spin_unlock_irq(&rtc_lock);
-
-       init_waitqueue_head(&rtc_wait);
-
-       irq = ELAPSEDTIME_IRQ;
-       retval = request_irq(irq, elapsedtime_interrupt, SA_INTERRUPT,
-                            "elapsed_time", NULL);
-       if (retval == 0) {
-               irq = RTCLONG1_IRQ;
-               retval = request_irq(irq, rtclong1_interrupt, SA_INTERRUPT,
-                                    "rtclong1", NULL);
-       }
-
-       if (retval < 0) {
-               printk(KERN_ERR "rtc: IRQ%d is busy\n", irq);
-               if (irq == RTCLONG1_IRQ)
-                       free_irq(ELAPSEDTIME_IRQ, NULL);
-               iounmap(rtc1_base);
-               iounmap(rtc2_base);
-               rtc1_base = NULL;
-               rtc2_base = NULL;
-               return retval;
-       }
-
-       disable_irq(ELAPSEDTIME_IRQ);
-       disable_irq(RTCLONG1_IRQ);
-
-       spin_lock_init(&rtc_task_lock);
-
-       printk(KERN_INFO "rtc: Real Time Clock of NEC VR4100 series\n");
-
-       return 0;
-}
-
-static int __devexit rtc_remove(struct platform_device *dev)
-{
-       int retval;
-
-       retval = misc_deregister(&rtc_miscdevice);
-       if (retval < 0)
-               return retval;
-
-       free_irq(ELAPSEDTIME_IRQ, NULL);
-       free_irq(RTCLONG1_IRQ, NULL);
-       if (rtc1_base != NULL)
-               iounmap(rtc1_base);
-       if (rtc2_base != NULL)
-               iounmap(rtc2_base);
-
-       return 0;
-}
-
-static struct platform_device *rtc_platform_device;
-
-static struct platform_driver rtc_device_driver = {
-       .probe          = rtc_probe,
-       .remove         = __devexit_p(rtc_remove),
-       .driver         = {
-               .name   = rtc_name,
-               .owner  = THIS_MODULE,
-       },
-};
-
-static int __init vr41xx_rtc_init(void)
-{
-       int retval;
-
-       switch (current_cpu_data.cputype) {
-       case CPU_VR4111:
-       case CPU_VR4121:
-               rtc_resource[0].start = RTC1_TYPE1_START;
-               rtc_resource[0].end = RTC1_TYPE1_END;
-               rtc_resource[1].start = RTC2_TYPE1_START;
-               rtc_resource[1].end = RTC2_TYPE1_END;
-               break;
-       case CPU_VR4122:
-       case CPU_VR4131:
-       case CPU_VR4133:
-               rtc_resource[0].start = RTC1_TYPE2_START;
-               rtc_resource[0].end = RTC1_TYPE2_END;
-               rtc_resource[1].start = RTC2_TYPE2_START;
-               rtc_resource[1].end = RTC2_TYPE2_END;
-               break;
-       default:
-               return -ENODEV;
-               break;
-       }
-
-       rtc_platform_device = platform_device_alloc("RTC", -1);
-       if (!rtc_platform_device)
-               return -ENOMEM;
-
-       retval = platform_device_add_resources(rtc_platform_device,
-                               rtc_resource, ARRAY_SIZE(rtc_resource));
-
-       if (retval == 0)
-               retval = platform_device_add(rtc_platform_device);
-
-       if (retval < 0) {
-               platform_device_put(rtc_platform_device);
-               return retval;
-       }
-
-       retval = platform_driver_register(&rtc_device_driver);
-       if (retval < 0)
-               platform_device_unregister(rtc_platform_device);
-
-       return retval;
-}
-
-static void __exit vr41xx_rtc_exit(void)
-{
-       platform_driver_unregister(&rtc_device_driver);
-       platform_device_unregister(rtc_platform_device);
-}
-
-module_init(vr41xx_rtc_init);
-module_exit(vr41xx_rtc_exit);
index 60c9be99c6d91244f311dccd2837f49e00b14e87..2cc71b66231ec07e81d7221578f040c6fdcaeed0 100644 (file)
@@ -99,7 +99,7 @@ config CPU_FREQ_GOV_USERSPACE
          Enable this cpufreq governor when you either want to set the
          CPU frequency manually or when an userspace program shall
          be able to set the CPU dynamically, like on LART 
-         <http://www.lart.tudelft.nl/>
+         <http://www.lartmaker.nl/>.
 
          For details, take a look at <file:Documentation/cpu-freq/>.
 
index 9b6ae7dc8b8a3a736666568fad41c3b8b567210d..9759d05b1972742b839b4188d0f8fcaf039859a9 100644 (file)
@@ -319,7 +319,6 @@ out:
        }
        return -EINVAL;
 }
-EXPORT_SYMBOL_GPL(cpufreq_parse_governor);
 
 
 /* drivers/base/cpu.c */
@@ -346,6 +345,8 @@ show_one(scaling_min_freq, min);
 show_one(scaling_max_freq, max);
 show_one(scaling_cur_freq, cur);
 
+static int __cpufreq_set_policy(struct cpufreq_policy *data, struct cpufreq_policy *policy);
+
 /**
  * cpufreq_per_cpu_attr_write() / store_##file_name() - sysfs write access
  */
@@ -364,7 +365,10 @@ static ssize_t store_##file_name                                   \
        if (ret != 1)                                                   \
                return -EINVAL;                                         \
                                                                        \
-       ret = cpufreq_set_policy(&new_policy);                          \
+       mutex_lock(&policy->lock);                                      \
+       ret = __cpufreq_set_policy(policy, &new_policy);                \
+       policy->user_policy.object = policy->object;                    \
+       mutex_unlock(&policy->lock);                                    \
                                                                        \
        return ret ? ret : count;                                       \
 }
@@ -420,7 +424,15 @@ static ssize_t store_scaling_governor (struct cpufreq_policy * policy,
        if (cpufreq_parse_governor(str_governor, &new_policy.policy, &new_policy.governor))
                return -EINVAL;
 
-       ret = cpufreq_set_policy(&new_policy);
+       /* Do not use cpufreq_set_policy here or the user_policy.max
+          will be wrongly overridden */
+       mutex_lock(&policy->lock);
+       ret = __cpufreq_set_policy(policy, &new_policy);
+
+       policy->user_policy.policy = policy->policy;
+       policy->user_policy.governor = policy->governor;
+       mutex_unlock(&policy->lock);
+
        return ret ? ret : count;
 }
 
@@ -685,7 +697,7 @@ static int cpufreq_add_dev (struct sys_device * sys_dev)
                if (!cpu_online(j))
                        continue;
 
-               dprintk("CPU already managed, adding link\n");
+               dprintk("CPU %u already managed, adding link\n", j);
                cpufreq_cpu_get(cpu);
                cpu_sys_dev = get_cpu_sysdev(j);
                sysfs_create_link(&cpu_sys_dev->kobj, &policy->kobj,
@@ -695,9 +707,8 @@ static int cpufreq_add_dev (struct sys_device * sys_dev)
        policy->governor = NULL; /* to assure that the starting sequence is
                                  * run in cpufreq_set_policy */
        mutex_unlock(&policy->lock);
-       
+
        /* set default policy */
-       
        ret = cpufreq_set_policy(&new_policy);
        if (ret) {
                dprintk("setting policy failed\n");
@@ -707,7 +718,7 @@ static int cpufreq_add_dev (struct sys_device * sys_dev)
        module_put(cpufreq_driver->owner);
        dprintk("initialization complete\n");
        cpufreq_debug_enable_ratelimit();
-       
+
        return 0;
 
 
index 037f6bf4543c3c29b98e6401d8cb242b85a2f993..e07a35487bde7cf5b713c0c203a4819a537ae901 100644 (file)
@@ -176,8 +176,7 @@ static ssize_t store_up_threshold(struct cpufreq_policy *unused,
        ret = sscanf (buf, "%u", &input);
 
        mutex_lock(&dbs_mutex);
-       if (ret != 1 || input > 100 || input < 0 ||
-                       input <= dbs_tuners_ins.down_threshold) {
+       if (ret != 1 || input > 100 || input <= dbs_tuners_ins.down_threshold) {
                mutex_unlock(&dbs_mutex);
                return -EINVAL;
        }
@@ -196,8 +195,7 @@ static ssize_t store_down_threshold(struct cpufreq_policy *unused,
        ret = sscanf (buf, "%u", &input);
 
        mutex_lock(&dbs_mutex);
-       if (ret != 1 || input > 100 || input < 0 ||
-                       input >= dbs_tuners_ins.up_threshold) {
+       if (ret != 1 || input > 100 || input >= dbs_tuners_ins.up_threshold) {
                mutex_unlock(&dbs_mutex);
                return -EINVAL;
        }
index 85429979d0db2a27021a34c5d8199b1dd47754c1..98e395f4bb29e8a37233f737f72fa5564208843d 100644 (file)
@@ -1,7 +1,8 @@
 #
 # Makefile for the linux kernel.
 #
-obj-$(CONFIG_EDD)              += edd.o
+obj-$(CONFIG_DMI)              += dmi_scan.o
+obj-$(CONFIG_EDD)              += edd.o
 obj-$(CONFIG_EFI_VARS)         += efivars.o
 obj-$(CONFIG_EFI_PCDP)         += pcdp.o
 obj-$(CONFIG_DELL_RBU)          += dell_rbu.o
diff --git a/drivers/firmware/dmi_scan.c b/drivers/firmware/dmi_scan.c
new file mode 100644 (file)
index 0000000..948bd7e
--- /dev/null
@@ -0,0 +1,358 @@
+#include <linux/types.h>
+#include <linux/string.h>
+#include <linux/init.h>
+#include <linux/module.h>
+#include <linux/dmi.h>
+#include <linux/efi.h>
+#include <linux/bootmem.h>
+#include <linux/slab.h>
+#include <asm/dmi.h>
+
+static char * __init dmi_string(struct dmi_header *dm, u8 s)
+{
+       u8 *bp = ((u8 *) dm) + dm->length;
+       char *str = "";
+
+       if (s) {
+               s--;
+               while (s > 0 && *bp) {
+                       bp += strlen(bp) + 1;
+                       s--;
+               }
+
+               if (*bp != 0) {
+                       str = dmi_alloc(strlen(bp) + 1);
+                       if (str != NULL)
+                               strcpy(str, bp);
+                       else
+                               printk(KERN_ERR "dmi_string: out of memory.\n");
+               }
+       }
+
+       return str;
+}
+
+/*
+ *     We have to be cautious here. We have seen BIOSes with DMI pointers
+ *     pointing to completely the wrong place for example
+ */
+static int __init dmi_table(u32 base, int len, int num,
+                           void (*decode)(struct dmi_header *))
+{
+       u8 *buf, *data;
+       int i = 0;
+
+       buf = dmi_ioremap(base, len);
+       if (buf == NULL)
+               return -1;
+
+       data = buf;
+
+       /*
+        *      Stop when we see all the items the table claimed to have
+        *      OR we run off the end of the table (also happens)
+        */
+       while ((i < num) && (data - buf + sizeof(struct dmi_header)) <= len) {
+               struct dmi_header *dm = (struct dmi_header *)data;
+               /*
+                *  We want to know the total length (formated area and strings)
+                *  before decoding to make sure we won't run off the table in
+                *  dmi_decode or dmi_string
+                */
+               data += dm->length;
+               while ((data - buf < len - 1) && (data[0] || data[1]))
+                       data++;
+               if (data - buf < len - 1)
+                       decode(dm);
+               data += 2;
+               i++;
+       }
+       dmi_iounmap(buf, len);
+       return 0;
+}
+
+static int __init dmi_checksum(u8 *buf)
+{
+       u8 sum = 0;
+       int a;
+
+       for (a = 0; a < 15; a++)
+               sum += buf[a];
+
+       return sum == 0;
+}
+
+static char *dmi_ident[DMI_STRING_MAX];
+static LIST_HEAD(dmi_devices);
+
+/*
+ *     Save a DMI string
+ */
+static void __init dmi_save_ident(struct dmi_header *dm, int slot, int string)
+{
+       char *p, *d = (char*) dm;
+
+       if (dmi_ident[slot])
+               return;
+
+       p = dmi_string(dm, d[string]);
+       if (p == NULL)
+               return;
+
+       dmi_ident[slot] = p;
+}
+
+static void __init dmi_save_devices(struct dmi_header *dm)
+{
+       int i, count = (dm->length - sizeof(struct dmi_header)) / 2;
+       struct dmi_device *dev;
+
+       for (i = 0; i < count; i++) {
+               char *d = (char *)(dm + 1) + (i * 2);
+
+               /* Skip disabled device */
+               if ((*d & 0x80) == 0)
+                       continue;
+
+               dev = dmi_alloc(sizeof(*dev));
+               if (!dev) {
+                       printk(KERN_ERR "dmi_save_devices: out of memory.\n");
+                       break;
+               }
+
+               dev->type = *d++ & 0x7f;
+               dev->name = dmi_string(dm, *d);
+               dev->device_data = NULL;
+
+               list_add(&dev->list, &dmi_devices);
+       }
+}
+
+static void __init dmi_save_ipmi_device(struct dmi_header *dm)
+{
+       struct dmi_device *dev;
+       void * data;
+
+       data = dmi_alloc(dm->length);
+       if (data == NULL) {
+               printk(KERN_ERR "dmi_save_ipmi_device: out of memory.\n");
+               return;
+       }
+
+       memcpy(data, dm, dm->length);
+
+       dev = dmi_alloc(sizeof(*dev));
+       if (!dev) {
+               printk(KERN_ERR "dmi_save_ipmi_device: out of memory.\n");
+               return;
+       }
+
+       dev->type = DMI_DEV_TYPE_IPMI;
+       dev->name = "IPMI controller";
+       dev->device_data = data;
+
+       list_add(&dev->list, &dmi_devices);
+}
+
+/*
+ *     Process a DMI table entry. Right now all we care about are the BIOS
+ *     and machine entries. For 2.5 we should pull the smbus controller info
+ *     out of here.
+ */
+static void __init dmi_decode(struct dmi_header *dm)
+{
+       switch(dm->type) {
+       case 0:         /* BIOS Information */
+               dmi_save_ident(dm, DMI_BIOS_VENDOR, 4);
+               dmi_save_ident(dm, DMI_BIOS_VERSION, 5);
+               dmi_save_ident(dm, DMI_BIOS_DATE, 8);
+               break;
+       case 1:         /* System Information */
+               dmi_save_ident(dm, DMI_SYS_VENDOR, 4);
+               dmi_save_ident(dm, DMI_PRODUCT_NAME, 5);
+               dmi_save_ident(dm, DMI_PRODUCT_VERSION, 6);
+               dmi_save_ident(dm, DMI_PRODUCT_SERIAL, 7);
+               break;
+       case 2:         /* Base Board Information */
+               dmi_save_ident(dm, DMI_BOARD_VENDOR, 4);
+               dmi_save_ident(dm, DMI_BOARD_NAME, 5);
+               dmi_save_ident(dm, DMI_BOARD_VERSION, 6);
+               break;
+       case 10:        /* Onboard Devices Information */
+               dmi_save_devices(dm);
+               break;
+       case 38:        /* IPMI Device Information */
+               dmi_save_ipmi_device(dm);
+       }
+}
+
+static int __init dmi_present(char __iomem *p)
+{
+       u8 buf[15];
+       memcpy_fromio(buf, p, 15);
+       if ((memcmp(buf, "_DMI_", 5) == 0) && dmi_checksum(buf)) {
+               u16 num = (buf[13] << 8) | buf[12];
+               u16 len = (buf[7] << 8) | buf[6];
+               u32 base = (buf[11] << 24) | (buf[10] << 16) |
+                       (buf[9] << 8) | buf[8];
+
+               /*
+                * DMI version 0.0 means that the real version is taken from
+                * the SMBIOS version, which we don't know at this point.
+                */
+               if (buf[14] != 0)
+                       printk(KERN_INFO "DMI %d.%d present.\n",
+                              buf[14] >> 4, buf[14] & 0xF);
+               else
+                       printk(KERN_INFO "DMI present.\n");
+               if (dmi_table(base,len, num, dmi_decode) == 0)
+                       return 0;
+       }
+       return 1;
+}
+
+void __init dmi_scan_machine(void)
+{
+       char __iomem *p, *q;
+       int rc;
+
+       if (efi_enabled) {
+               if (efi.smbios == EFI_INVALID_TABLE_ADDR)
+                       goto out;
+
+               /* This is called as a core_initcall() because it isn't
+                * needed during early boot.  This also means we can
+                * iounmap the space when we're done with it.
+               */
+               p = dmi_ioremap(efi.smbios, 32);
+               if (p == NULL)
+                       goto out;
+
+               rc = dmi_present(p + 0x10); /* offset of _DMI_ string */
+               dmi_iounmap(p, 32);
+               if (!rc)
+                       return;
+       }
+       else {
+               /*
+                * no iounmap() for that ioremap(); it would be a no-op, but
+                * it's so early in setup that sucker gets confused into doing
+                * what it shouldn't if we actually call it.
+                */
+               p = dmi_ioremap(0xF0000, 0x10000);
+               if (p == NULL)
+                       goto out;
+
+               for (q = p; q < p + 0x10000; q += 16) {
+                       rc = dmi_present(q);
+                       if (!rc)
+                               return;
+               }
+       }
+ out:  printk(KERN_INFO "DMI not present or invalid.\n");
+}
+
+/**
+ *     dmi_check_system - check system DMI data
+ *     @list: array of dmi_system_id structures to match against
+ *
+ *     Walk the blacklist table running matching functions until someone
+ *     returns non zero or we hit the end. Callback function is called for
+ *     each successfull match. Returns the number of matches.
+ */
+int dmi_check_system(struct dmi_system_id *list)
+{
+       int i, count = 0;
+       struct dmi_system_id *d = list;
+
+       while (d->ident) {
+               for (i = 0; i < ARRAY_SIZE(d->matches); i++) {
+                       int s = d->matches[i].slot;
+                       if (s == DMI_NONE)
+                               continue;
+                       if (dmi_ident[s] && strstr(dmi_ident[s], d->matches[i].substr))
+                               continue;
+                       /* No match */
+                       goto fail;
+               }
+               count++;
+               if (d->callback && d->callback(d))
+                       break;
+fail:          d++;
+       }
+
+       return count;
+}
+EXPORT_SYMBOL(dmi_check_system);
+
+/**
+ *     dmi_get_system_info - return DMI data value
+ *     @field: data index (see enum dmi_filed)
+ *
+ *     Returns one DMI data value, can be used to perform
+ *     complex DMI data checks.
+ */
+char *dmi_get_system_info(int field)
+{
+       return dmi_ident[field];
+}
+EXPORT_SYMBOL(dmi_get_system_info);
+
+/**
+ *     dmi_find_device - find onboard device by type/name
+ *     @type: device type or %DMI_DEV_TYPE_ANY to match all device types
+ *     @desc: device name string or %NULL to match all
+ *     @from: previous device found in search, or %NULL for new search.
+ *
+ *     Iterates through the list of known onboard devices. If a device is
+ *     found with a matching @vendor and @device, a pointer to its device
+ *     structure is returned.  Otherwise, %NULL is returned.
+ *     A new search is initiated by passing %NULL to the @from argument.
+ *     If @from is not %NULL, searches continue from next device.
+ */
+struct dmi_device * dmi_find_device(int type, const char *name,
+                                   struct dmi_device *from)
+{
+       struct list_head *d, *head = from ? &from->list : &dmi_devices;
+
+       for(d = head->next; d != &dmi_devices; d = d->next) {
+               struct dmi_device *dev = list_entry(d, struct dmi_device, list);
+
+               if (((type == DMI_DEV_TYPE_ANY) || (dev->type == type)) &&
+                   ((name == NULL) || (strcmp(dev->name, name) == 0)))
+                       return dev;
+       }
+
+       return NULL;
+}
+EXPORT_SYMBOL(dmi_find_device);
+
+/**
+ *     dmi_get_year - Return year of a DMI date
+ *     @field: data index (like dmi_get_system_info)
+ *
+ *     Returns -1 when the field doesn't exist. 0 when it is broken.
+ */
+int dmi_get_year(int field)
+{
+       int year;
+       char *s = dmi_get_system_info(field);
+
+       if (!s)
+               return -1;
+       if (*s == '\0')
+               return 0;
+       s = strrchr(s, '/');
+       if (!s)
+               return 0;
+
+       s += 1;
+       year = simple_strtoul(s, NULL, 0);
+       if (year && year < 100) {       /* 2-digit year */
+               year += 1900;
+               if (year < 1996)        /* no dates < spec 1.0 */
+                       year += 100;
+       }
+
+       return year;
+}
index 23a9e1ea8e321e218acc42de271e8e157191764f..1659f6c414581c9ad737b161edb575073dcd98c6 100644 (file)
@@ -509,12 +509,22 @@ static int hdaps_dmi_match_invert(struct dmi_system_id *id)
        }                                               \
 }
 
+#define HDAPS_DMI_MATCH_LENOVO(model)   {               \
+        .ident = "Lenovo " model,                       \
+        .callback = hdaps_dmi_match_invert,             \
+        .matches = {                                    \
+                DMI_MATCH(DMI_BOARD_VENDOR, "LENOVO"),  \
+                DMI_MATCH(DMI_PRODUCT_VERSION, model)   \
+        }                                               \
+}
+
 static int __init hdaps_init(void)
 {
        int ret;
 
        /* Note that DMI_MATCH(...,"ThinkPad T42") will match "ThinkPad T42p" */
        struct dmi_system_id hdaps_whitelist[] = {
+               HDAPS_DMI_MATCH_NORMAL("ThinkPad H"),
                HDAPS_DMI_MATCH_INVERT("ThinkPad R50p"),
                HDAPS_DMI_MATCH_NORMAL("ThinkPad R50"),
                HDAPS_DMI_MATCH_NORMAL("ThinkPad R51"),
@@ -524,15 +534,17 @@ static int __init hdaps_init(void)
                HDAPS_DMI_MATCH_INVERT("ThinkPad T42p"),
                HDAPS_DMI_MATCH_NORMAL("ThinkPad T42"),
                HDAPS_DMI_MATCH_NORMAL("ThinkPad T43"),
+               HDAPS_DMI_MATCH_LENOVO("ThinkPad T60p"),
                HDAPS_DMI_MATCH_NORMAL("ThinkPad X40"),
                HDAPS_DMI_MATCH_NORMAL("ThinkPad X41 Tablet"),
                HDAPS_DMI_MATCH_NORMAL("ThinkPad X41"),
+               HDAPS_DMI_MATCH_LENOVO("ThinkPad X60"),
                { .ident = NULL }
        };
 
        if (!dmi_check_system(hdaps_whitelist)) {
                printk(KERN_WARNING "hdaps: supported laptop not found!\n");
-               ret = -ENXIO;
+               ret = -ENODEV;
                goto out;
        }
 
index 6865c64d8a51d47b071b7930570e36dbf3c1fba1..958602e284124dbef22e18581c302f1f35334c9a 100644 (file)
@@ -1161,7 +1161,7 @@ w83792d_detect(struct i2c_adapter *adapter, int address, int kind)
           bank. */
        if (kind < 0) {
                if (w83792d_read_value(client, W83792D_REG_CONFIG) & 0x80) {
-                       dev_warn(dev, "Detection failed at step 3\n");
+                       dev_dbg(dev, "Detection failed at step 1\n");
                        goto ERROR1;
                }
                val1 = w83792d_read_value(client, W83792D_REG_BANK);
@@ -1170,6 +1170,7 @@ w83792d_detect(struct i2c_adapter *adapter, int address, int kind)
                if (!(val1 & 0x07)) {  /* is Bank0 */
                        if (((!(val1 & 0x80)) && (val2 != 0xa3)) ||
                             ((val1 & 0x80) && (val2 != 0x5c))) {
+                               dev_dbg(dev, "Detection failed at step 2\n");
                                goto ERROR1;
                        }
                }
@@ -1177,7 +1178,7 @@ w83792d_detect(struct i2c_adapter *adapter, int address, int kind)
                   should match */
                if (w83792d_read_value(client,
                                        W83792D_REG_I2C_ADDR) != address) {
-                       dev_warn(dev, "Detection failed at step 5\n");
+                       dev_dbg(dev, "Detection failed at step 3\n");
                        goto ERROR1;
                }
        }
index 089c6f5b24dee416a0196122d4f3f1e60fd162e5..d6d44946a283156e6d3829b6b6fca039ad331992 100644 (file)
@@ -286,7 +286,10 @@ config I2C_PARPORT
          This driver is a replacement for (and was inspired by) an older
          driver named i2c-philips-par.  The new driver supports more devices,
          and makes it easier to add support for new devices.
-         
+
+         An adapter type parameter is now mandatory.  Please read the file
+         Documentation/i2c/busses/i2c-parport for details.
+
          Another driver exists, named i2c-parport-light, which doesn't depend
          on the parport driver.  This is meant for embedded systems. Don't say
          Y here if you intend to say Y or M there.
index 8e0f3158215f6bc191864ef5f0a87f49ecc67bbd..dfca74933625e0c1c629778f0af1f9f8f00351b3 100644 (file)
@@ -478,6 +478,11 @@ static s32 i801_access(struct i2c_adapter * adap, u16 addr,
                ret = i801_transaction();
        }
 
+       /* Some BIOSes don't like it when PEC is enabled at reboot or resume
+          time, so we forcibly disable it after every transaction. */
+       if (hwpec)
+               outb_p(0, SMBAUXCTL);
+
        if(block)
                return ret;
        if(ret)
index c63025a4c8613744fb1a6e7706e018188391a5b3..e09ebbb2f9f09dc14dc00129211c82cfd4da95cb 100644 (file)
@@ -121,9 +121,14 @@ static struct i2c_adapter parport_adapter = {
 
 static int __init i2c_parport_init(void)
 {
-       if (type < 0 || type >= ARRAY_SIZE(adapter_parm)) {
+       if (type < 0) {
+               printk(KERN_WARNING "i2c-parport: adapter type unspecified\n");
+               return -ENODEV;
+       }
+
+       if (type >= ARRAY_SIZE(adapter_parm)) {
                printk(KERN_WARNING "i2c-parport: invalid type (%d)\n", type);
-               type = 0;
+               return -ENODEV;
        }
 
        if (base == 0) {
index 7e2e8cd1c14a90d0806d382df0e9b726e34768b2..934bd55bae15da1164ca7b14b79a5c7bb2cfcf18 100644 (file)
@@ -241,9 +241,14 @@ static struct parport_driver i2c_parport_driver = {
 
 static int __init i2c_parport_init(void)
 {
-       if (type < 0 || type >= ARRAY_SIZE(adapter_parm)) {
+       if (type < 0) {
+               printk(KERN_WARNING "i2c-parport: adapter type unspecified\n");
+               return -ENODEV;
+       }
+
+       if (type >= ARRAY_SIZE(adapter_parm)) {
                printk(KERN_WARNING "i2c-parport: invalid type (%d)\n", type);
-               type = 0;
+               return -ENODEV;
        }
 
        return parport_register_driver(&i2c_parport_driver);
index d702e5e0388d9439c661ef7b8e9a0c1057f123b5..9ddd816d5d0f6609eec3ecddf640f15e2839e24e 100644 (file)
@@ -90,7 +90,7 @@ static struct adapter_parm adapter_parm[] = {
        },
 };
 
-static int type;
+static int type = -1;
 module_param(type, int, 0);
 MODULE_PARM_DESC(type,
        "Type of adapter:\n"
index 3024907cdafe6d44bd0eaf1a54a8edc587987584..1a73c0532fc770bb6c1f812ba7959cdc511427b5 100644 (file)
 #include <linux/init.h>
 #include <asm/io.h>
 
-/*
-       HISTORY:
-       2003-05-11      1.0.0   Updated from lm_sensors project for kernel 2.5
-                               (was i2c-sis645.c from lm_sensors 2.7.0)
-*/
-#define SIS96x_VERSION "1.0.0"
-
 /* base address register in PCI config space */
 #define SIS96x_BAR 0x04
 
@@ -337,7 +330,6 @@ static struct pci_driver sis96x_driver = {
 
 static int __init i2c_sis96x_init(void)
 {
-       printk(KERN_INFO "i2c-sis96x version %s\n", SIS96x_VERSION);
        return pci_register_driver(&sis96x_driver);
 }
 
index 03d09ed5ec2c009d21a4816f85e82829f76e2706..4630f1969a0997875bb11fa8a7950cbbae75b2ca 100644 (file)
@@ -27,6 +27,7 @@
 #include <linux/rtc.h>
 #include <linux/bcd.h>
 #include <linux/mutex.h>
+#include <linux/workqueue.h>
 
 #define DS1374_REG_TOD0                0x00
 #define DS1374_REG_TOD1                0x01
@@ -139,7 +140,7 @@ ulong ds1374_get_rtc_time(void)
        return t1;
 }
 
-static void ds1374_set_tlet(ulong arg)
+static void ds1374_set_work(void *arg)
 {
        ulong t1, t2;
        int limit = 10;         /* arbitrary retry limit */
@@ -168,17 +169,18 @@ static void ds1374_set_tlet(ulong arg)
 
 static ulong new_time;
 
-static DECLARE_TASKLET_DISABLED(ds1374_tasklet, ds1374_set_tlet,
-                               (ulong) & new_time);
+static struct workqueue_struct *ds1374_workqueue;
+
+static DECLARE_WORK(ds1374_work, ds1374_set_work, &new_time);
 
 int ds1374_set_rtc_time(ulong nowtime)
 {
        new_time = nowtime;
 
        if (in_interrupt())
-               tasklet_schedule(&ds1374_tasklet);
+               queue_work(ds1374_workqueue, &ds1374_work);
        else
-               ds1374_set_tlet((ulong) & new_time);
+               ds1374_set_work(&new_time);
 
        return 0;
 }
@@ -204,6 +206,8 @@ static int ds1374_probe(struct i2c_adapter *adap, int addr, int kind)
        client->adapter = adap;
        client->driver = &ds1374_driver;
 
+       ds1374_workqueue = create_singlethread_workqueue("ds1374");
+
        if ((rc = i2c_attach_client(client)) != 0) {
                kfree(client);
                return rc;
@@ -227,7 +231,7 @@ static int ds1374_detach(struct i2c_client *client)
 
        if ((rc = i2c_detach_client(client)) == 0) {
                kfree(i2c_get_clientdata(client));
-               tasklet_kill(&ds1374_tasklet);
+               destroy_workqueue(ds1374_workqueue);
        }
        return rc;
 }
index b5aabe7cf7923e6b8eb90e4947f591f791c4ec82..99ab4ec343902e8d5f3054fba8ffd301cfa2f168 100644 (file)
@@ -25,6 +25,7 @@
 #include <linux/rtc.h>
 #include <linux/bcd.h>
 #include <linux/mutex.h>
+#include <linux/workqueue.h>
 
 #include <asm/time.h>
 #include <asm/rtc.h>
@@ -111,7 +112,7 @@ m41t00_get_rtc_time(void)
 }
 
 static void
-m41t00_set_tlet(ulong arg)
+m41t00_set(void *arg)
 {
        struct rtc_time tm;
        ulong   nowtime = *(ulong *)arg;
@@ -130,13 +131,13 @@ m41t00_set_tlet(ulong arg)
        if ((i2c_smbus_write_byte_data(save_client, 0, tm.tm_sec & 0x7f) < 0)
                || (i2c_smbus_write_byte_data(save_client, 1, tm.tm_min & 0x7f)
                        < 0)
-               || (i2c_smbus_write_byte_data(save_client, 2, tm.tm_hour & 0x7f)
+               || (i2c_smbus_write_byte_data(save_client, 2, tm.tm_hour & 0x3f)
                        < 0)
-               || (i2c_smbus_write_byte_data(save_client, 4, tm.tm_mday & 0x7f)
+               || (i2c_smbus_write_byte_data(save_client, 4, tm.tm_mday & 0x3f)
                        < 0)
-               || (i2c_smbus_write_byte_data(save_client, 5, tm.tm_mon & 0x7f)
+               || (i2c_smbus_write_byte_data(save_client, 5, tm.tm_mon & 0x1f)
                        < 0)
-               || (i2c_smbus_write_byte_data(save_client, 6, tm.tm_year & 0x7f)
+               || (i2c_smbus_write_byte_data(save_client, 6, tm.tm_year & 0xff)
                        < 0))
 
                dev_warn(&save_client->dev,"m41t00: can't write to rtc chip\n");
@@ -145,9 +146,9 @@ m41t00_set_tlet(ulong arg)
        return;
 }
 
-static ulong   new_time;
-
-DECLARE_TASKLET_DISABLED(m41t00_tasklet, m41t00_set_tlet, (ulong)&new_time);
+static ulong new_time;
+static struct workqueue_struct *m41t00_wq;
+static DECLARE_WORK(m41t00_work, m41t00_set, &new_time);
 
 int
 m41t00_set_rtc_time(ulong nowtime)
@@ -155,9 +156,9 @@ m41t00_set_rtc_time(ulong nowtime)
        new_time = nowtime;
 
        if (in_interrupt())
-               tasklet_schedule(&m41t00_tasklet);
+               queue_work(m41t00_wq, &m41t00_work);
        else
-               m41t00_set_tlet((ulong)&new_time);
+               m41t00_set(&new_time);
 
        return 0;
 }
@@ -189,6 +190,7 @@ m41t00_probe(struct i2c_adapter *adap, int addr, int kind)
                return rc;
        }
 
+       m41t00_wq = create_singlethread_workqueue("m41t00");
        save_client = client;
        return 0;
 }
@@ -206,7 +208,7 @@ m41t00_detach(struct i2c_client *client)
 
        if ((rc = i2c_detach_client(client)) == 0) {
                kfree(client);
-               tasklet_kill(&m41t00_tasklet);
+               destroy_workqueue(m41t00_wq);
        }
        return rc;
 }
index cf84350efc550b3dc804dd9a5cb03d8978dc9002..8b24b4f2a839a0abe424cf5e75eebd2bf5a9434b 100644 (file)
@@ -731,6 +731,8 @@ static unsigned int __devinit ata66_ali15x3 (ide_hwif_t *hwif)
        
        if(m5229_revision <= 0x20)
                tmpbyte = (tmpbyte & (~0x02)) | 0x01;
+       else if (m5229_revision == 0xc7)
+               tmpbyte |= 0x03;
        else
                tmpbyte |= 0x01;
 
index df9ee9a784350c2d63ab3ba345d90bd2da25c9cb..900efd1da587d782a0afd369579c62713935280b 100644 (file)
@@ -348,6 +348,7 @@ static struct pci_device_id atiixp_pci_tbl[] = {
        { PCI_VENDOR_ID_ATI, PCI_DEVICE_ID_ATI_IXP200_IDE, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0},
        { PCI_VENDOR_ID_ATI, PCI_DEVICE_ID_ATI_IXP300_IDE, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0},
        { PCI_VENDOR_ID_ATI, PCI_DEVICE_ID_ATI_IXP400_IDE, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0},
+       { PCI_VENDOR_ID_ATI, PCI_DEVICE_ID_ATI_IXP600_IDE, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0},
        { 0, },
 };
 MODULE_DEVICE_TABLE(pci, atiixp_pci_tbl);
index 6f8f8645b02c5666ad4cc336b0a93d8ba6aa7447..7ce5bf7836882b32ed8da8587706eee826a543b9 100644 (file)
@@ -798,7 +798,6 @@ static ide_pci_device_t pdc202xx_chipsets[] __devinitdata = {
                .autodma        = AUTODMA,
                .bootable       = OFF_BOARD,
                .extra          = 48,
-               .flags          = IDEPCI_FLAG_FORCE_PDC,
        },{     /* 2 */
                .name           = "PDC20263",
                .init_setup     = init_setup_pdc202ata4,
@@ -819,7 +818,6 @@ static ide_pci_device_t pdc202xx_chipsets[] __devinitdata = {
                .autodma        = AUTODMA,
                .bootable       = OFF_BOARD,
                .extra          = 48,
-               .flags          = IDEPCI_FLAG_FORCE_PDC,
        },{     /* 4 */
                .name           = "PDC20267",
                .init_setup     = init_setup_pdc202xx,
index 7ebf992e8c2f40f2050060ea2e3f8cd53d188436..462ed3006c3082124a0a9622dfa9e7448116cc09 100644 (file)
@@ -580,7 +580,6 @@ void ide_pci_setup_ports(struct pci_dev *dev, ide_pci_device_t *d, int pciirq, a
        int port;
        int at_least_one_hwif_enabled = 0;
        ide_hwif_t *hwif, *mate = NULL;
-       static int secondpdc = 0;
        u8 tmp;
 
        index->all = 0xf0f0;
@@ -592,21 +591,9 @@ void ide_pci_setup_ports(struct pci_dev *dev, ide_pci_device_t *d, int pciirq, a
        for (port = 0; port <= 1; ++port) {
                ide_pci_enablebit_t *e = &(d->enablebits[port]);
        
-               /* 
-                * If this is a Promise FakeRaid controller,
-                * the 2nd controller will be marked as 
-                * disabled while it is actually there and enabled
-                * by the bios for raid purposes. 
-                * Skip the normal "is it enabled" test for those.
-                */
-               if ((d->flags & IDEPCI_FLAG_FORCE_PDC) &&
-                   (secondpdc++==1) && (port==1))
-                       goto controller_ok;
-                       
                if (e->reg && (pci_read_config_byte(dev, e->reg, &tmp) ||
                    (tmp & e->mask) != e->val))
                        continue;       /* port not enabled */
-controller_ok:
 
                if (d->channels <= port)
                        break;
index c57a3871184ca0d419698ffb3b2cf10d8c155185..50364c0b090c7b6a141c6bd7e47583422826c351 100644 (file)
@@ -302,7 +302,7 @@ static void ib_cache_setup_one(struct ib_device *device)
                kmalloc(sizeof *device->cache.pkey_cache *
                        (end_port(device) - start_port(device) + 1), GFP_KERNEL);
        device->cache.gid_cache =
-               kmalloc(sizeof *device->cache.pkey_cache *
+               kmalloc(sizeof *device->cache.gid_cache *
                        (end_port(device) - start_port(device) + 1), GFP_KERNEL);
 
        if (!device->cache.pkey_cache || !device->cache.gid_cache) {
index ba54c856b0e5b98881320694cba80d3b333258f3..469b6923a2e2e0a2c59b388d8f93fedc2e961fac 100644 (file)
@@ -228,10 +228,7 @@ struct ib_mad_agent *ib_register_mad_agent(struct ib_device *device,
                                goto error1;
                }
                /* Make sure class supplied is consistent with RMPP */
-               if (ib_is_mad_class_rmpp(mad_reg_req->mgmt_class)) {
-                       if (!rmpp_version)
-                               goto error1;
-               } else {
+               if (!ib_is_mad_class_rmpp(mad_reg_req->mgmt_class)) {
                        if (rmpp_version)
                                goto error1;
                }
@@ -2311,6 +2308,7 @@ static void local_completions(void *data)
                local = list_entry(mad_agent_priv->local_list.next,
                                   struct ib_mad_local_private,
                                   completion_list);
+               list_del(&local->completion_list);
                spin_unlock_irqrestore(&mad_agent_priv->lock, flags);
                if (local->mad_priv) {
                        recv_mad_agent = local->recv_mad_agent;
@@ -2362,7 +2360,6 @@ local_send_completion:
                                                   &mad_send_wc);
 
                spin_lock_irqsave(&mad_agent_priv->lock, flags);
-               list_del(&local->completion_list);
                atomic_dec(&mad_agent_priv->refcount);
                if (!recv)
                        kmem_cache_free(ib_mad_cache, local->mad_priv);
index cae0845f472ac60fd41b4f9684b8111924540484..b78e7dc6933072c21f4bd943960a9b79f6e3393f 100644 (file)
 #include <rdma/ib_verbs.h>
 #include <rdma/ib_cache.h>
 
+int ib_rate_to_mult(enum ib_rate rate)
+{
+       switch (rate) {
+       case IB_RATE_2_5_GBPS: return  1;
+       case IB_RATE_5_GBPS:   return  2;
+       case IB_RATE_10_GBPS:  return  4;
+       case IB_RATE_20_GBPS:  return  8;
+       case IB_RATE_30_GBPS:  return 12;
+       case IB_RATE_40_GBPS:  return 16;
+       case IB_RATE_60_GBPS:  return 24;
+       case IB_RATE_80_GBPS:  return 32;
+       case IB_RATE_120_GBPS: return 48;
+       default:               return -1;
+       }
+}
+EXPORT_SYMBOL(ib_rate_to_mult);
+
+enum ib_rate mult_to_ib_rate(int mult)
+{
+       switch (mult) {
+       case 1:  return IB_RATE_2_5_GBPS;
+       case 2:  return IB_RATE_5_GBPS;
+       case 4:  return IB_RATE_10_GBPS;
+       case 8:  return IB_RATE_20_GBPS;
+       case 12: return IB_RATE_30_GBPS;
+       case 16: return IB_RATE_40_GBPS;
+       case 24: return IB_RATE_60_GBPS;
+       case 32: return IB_RATE_80_GBPS;
+       case 48: return IB_RATE_120_GBPS;
+       default: return IB_RATE_PORT_CURRENT;
+       }
+}
+EXPORT_SYMBOL(mult_to_ib_rate);
+
 /* Protection domains */
 
 struct ib_pd *ib_alloc_pd(struct ib_device *device)
index cd533cf951c26b5a7cc25b3dcad22386065ca092..7d3fb6996b41d6fb6aecf589b2ef2bcddbe5588e 100644 (file)
@@ -365,15 +365,3 @@ static ssize_t ipath_diag_write(struct file *fp, const char __user *data,
 bail:
        return ret;
 }
-
-void ipath_diag_bringup_link(struct ipath_devdata *dd)
-{
-       if (diag_set_link || (dd->ipath_flags & IPATH_LINKACTIVE))
-               return;
-
-       diag_set_link = 1;
-       ipath_cdbg(VERBOSE, "Trying to set to set link active for "
-                  "diag pkt\n");
-       ipath_layer_set_linkstate(dd, IPATH_IB_LINKARM);
-       ipath_layer_set_linkstate(dd, IPATH_IB_LINKACTIVE);
-}
index 58a94efb0070bb14d658ae1e32f90b2e17b9f3c0..e7617c3982ea6c18641d9a6be9aee2120e566d6b 100644 (file)
@@ -1729,7 +1729,7 @@ void ipath_free_pddata(struct ipath_devdata *dd, u32 port, int freehdrq)
        }
 }
 
-int __init infinipath_init(void)
+static int __init infinipath_init(void)
 {
        int ret;
 
index 60f5f4108069253e20c84d2c06eded189b2e0865..0bcb428041f32eb7fb2990ee9ae0610390fe201e 100644 (file)
@@ -172,8 +172,8 @@ static void handle_e_ibstatuschanged(struct ipath_devdata *dd,
                                   "was %s\n", dd->ipath_unit,
                                   ib_linkstate(lstate),
                                   ib_linkstate((unsigned)
-                                               dd->ipath_lastibcstat
-                                               & IPATH_IBSTATE_MASK));
+                                               dd->ipath_lastibcstat
+                                               & IPATH_IBSTATE_MASK));
        }
        else {
                lstate = dd->ipath_lastibcstat & IPATH_IBSTATE_MASK;
index 159d0aed31a5b0b792e69b28f1b6ef32dd2596b1..0ce5f19c9d62ac5f2bd07356f1bcc8ce9f31fee1 100644 (file)
@@ -528,7 +528,6 @@ extern spinlock_t ipath_devs_lock;
 extern struct ipath_devdata *ipath_lookup(int unit);
 
 extern u16 ipath_layer_rcv_opcode;
-extern int ipath_verbs_registered;
 extern int __ipath_layer_intr(struct ipath_devdata *, u32);
 extern int ipath_layer_intr(struct ipath_devdata *, u32);
 extern int __ipath_layer_rcv(struct ipath_devdata *, void *,
index 2cabf634057212f3ca8f2b8410b07b61ab6cecdc..69ed1100701af5db8ff1cbc226b8076b03979f15 100644 (file)
@@ -52,7 +52,7 @@ static int (*layer_rcv)(void *, void *, struct sk_buff *);
 static int (*layer_rcv_lid)(void *, void *);
 static int (*verbs_piobufavail)(void *);
 static void (*verbs_rcv)(void *, void *, void *, u32);
-int ipath_verbs_registered;
+static int ipath_verbs_registered;
 
 static void *(*layer_add_one)(int, struct ipath_devdata *);
 static void (*layer_remove_one)(void *);
index e693a7a8266703996f99e5fe58f5e30fe1a244b3..e1dc4f757062a5ac8f9595fc197de26c20e7dda7 100644 (file)
@@ -305,8 +305,8 @@ static const struct ipath_cregs ipath_pe_cregs = {
  * we'll print them and continue.  We reuse the same message buffer as
  * ipath_handle_errors() to avoid excessive stack usage.
  */
-void ipath_pe_handle_hwerrors(struct ipath_devdata *dd, char *msg,
-       size_t msgl)
+static void ipath_pe_handle_hwerrors(struct ipath_devdata *dd, char *msg,
+                                    size_t msgl)
 {
        ipath_err_t hwerrs;
        u32 bits, ctrl;
@@ -552,7 +552,7 @@ static int ipath_pe_boardname(struct ipath_devdata *dd, char *name,
  * freeze mode), and enable hardware errors as errors (along with
  * everything else) in errormask
  */
-void ipath_pe_init_hwerrors(struct ipath_devdata *dd)
+static void ipath_pe_init_hwerrors(struct ipath_devdata *dd)
 {
        ipath_err_t val;
        u64 extsval;
@@ -577,7 +577,7 @@ void ipath_pe_init_hwerrors(struct ipath_devdata *dd)
  * ipath_pe_bringup_serdes - bring up the serdes
  * @dd: the infinipath device
  */
-int ipath_pe_bringup_serdes(struct ipath_devdata *dd)
+static int ipath_pe_bringup_serdes(struct ipath_devdata *dd)
 {
        u64 val, tmp, config1;
        int ret = 0, change = 0;
@@ -694,7 +694,7 @@ int ipath_pe_bringup_serdes(struct ipath_devdata *dd)
  * @dd: the infinipath device
  * Called when driver is being unloaded
  */
-void ipath_pe_quiet_serdes(struct ipath_devdata *dd)
+static void ipath_pe_quiet_serdes(struct ipath_devdata *dd)
 {
        u64 val = ipath_read_kreg64(dd, dd->ipath_kregs->kr_serdesconfig0);
 
index 6058d70d7577bb349ab7e5db759e1e3d37db4fc3..18890716db1ed3bf5812968d8945f71905cdfd3a 100644 (file)
@@ -188,8 +188,8 @@ static void free_qpn(struct ipath_qp_table *qpt, u32 qpn)
  * Allocate the next available QPN and put the QP into the hash table.
  * The hash table holds a reference to the QP.
  */
-int ipath_alloc_qpn(struct ipath_qp_table *qpt, struct ipath_qp *qp,
-                   enum ib_qp_type type)
+static int ipath_alloc_qpn(struct ipath_qp_table *qpt, struct ipath_qp *qp,
+                          enum ib_qp_type type)
 {
        unsigned long flags;
        u32 qpn;
@@ -232,7 +232,7 @@ bail:
  * Remove the QP from the table so it can't be found asynchronously by
  * the receive interrupt routine.
  */
-void ipath_free_qp(struct ipath_qp_table *qpt, struct ipath_qp *qp)
+static void ipath_free_qp(struct ipath_qp_table *qpt, struct ipath_qp *qp)
 {
        struct ipath_qp *q, **qpp;
        unsigned long flags;
@@ -357,6 +357,65 @@ static void ipath_reset_qp(struct ipath_qp *qp)
        qp->r_reuse_sge = 0;
 }
 
+/**
+ * ipath_error_qp - put a QP into an error state
+ * @qp: the QP to put into an error state
+ *
+ * Flushes both send and receive work queues.
+ * QP r_rq.lock and s_lock should be held.
+ */
+
+static void ipath_error_qp(struct ipath_qp *qp)
+{
+       struct ipath_ibdev *dev = to_idev(qp->ibqp.device);
+       struct ib_wc wc;
+
+       _VERBS_INFO("QP%d/%d in error state\n",
+                   qp->ibqp.qp_num, qp->remote_qpn);
+
+       spin_lock(&dev->pending_lock);
+       /* XXX What if its already removed by the timeout code? */
+       if (qp->timerwait.next != LIST_POISON1)
+               list_del(&qp->timerwait);
+       if (qp->piowait.next != LIST_POISON1)
+               list_del(&qp->piowait);
+       spin_unlock(&dev->pending_lock);
+
+       wc.status = IB_WC_WR_FLUSH_ERR;
+       wc.vendor_err = 0;
+       wc.byte_len = 0;
+       wc.imm_data = 0;
+       wc.qp_num = qp->ibqp.qp_num;
+       wc.src_qp = 0;
+       wc.wc_flags = 0;
+       wc.pkey_index = 0;
+       wc.slid = 0;
+       wc.sl = 0;
+       wc.dlid_path_bits = 0;
+       wc.port_num = 0;
+
+       while (qp->s_last != qp->s_head) {
+               struct ipath_swqe *wqe = get_swqe_ptr(qp, qp->s_last);
+
+               wc.wr_id = wqe->wr.wr_id;
+               wc.opcode = ib_ipath_wc_opcode[wqe->wr.opcode];
+               if (++qp->s_last >= qp->s_size)
+                       qp->s_last = 0;
+               ipath_cq_enter(to_icq(qp->ibqp.send_cq), &wc, 1);
+       }
+       qp->s_cur = qp->s_tail = qp->s_head;
+       qp->s_hdrwords = 0;
+       qp->s_ack_state = IB_OPCODE_RC_ACKNOWLEDGE;
+
+       wc.opcode = IB_WC_RECV;
+       while (qp->r_rq.tail != qp->r_rq.head) {
+               wc.wr_id = get_rwqe_ptr(&qp->r_rq, qp->r_rq.tail)->wr_id;
+               if (++qp->r_rq.tail >= qp->r_rq.size)
+                       qp->r_rq.tail = 0;
+               ipath_cq_enter(to_icq(qp->ibqp.recv_cq), &wc, 1);
+       }
+}
+
 /**
  * ipath_modify_qp - modify the attributes of a queue pair
  * @ibqp: the queue pair who's attributes we're modifying
@@ -820,65 +879,6 @@ void ipath_sqerror_qp(struct ipath_qp *qp, struct ib_wc *wc)
        qp->state = IB_QPS_SQE;
 }
 
-/**
- * ipath_error_qp - put a QP into an error state
- * @qp: the QP to put into an error state
- *
- * Flushes both send and receive work queues.
- * QP r_rq.lock and s_lock should be held.
- */
-
-void ipath_error_qp(struct ipath_qp *qp)
-{
-       struct ipath_ibdev *dev = to_idev(qp->ibqp.device);
-       struct ib_wc wc;
-
-       _VERBS_INFO("QP%d/%d in error state\n",
-                   qp->ibqp.qp_num, qp->remote_qpn);
-
-       spin_lock(&dev->pending_lock);
-       /* XXX What if its already removed by the timeout code? */
-       if (qp->timerwait.next != LIST_POISON1)
-               list_del(&qp->timerwait);
-       if (qp->piowait.next != LIST_POISON1)
-               list_del(&qp->piowait);
-       spin_unlock(&dev->pending_lock);
-
-       wc.status = IB_WC_WR_FLUSH_ERR;
-       wc.vendor_err = 0;
-       wc.byte_len = 0;
-       wc.imm_data = 0;
-       wc.qp_num = qp->ibqp.qp_num;
-       wc.src_qp = 0;
-       wc.wc_flags = 0;
-       wc.pkey_index = 0;
-       wc.slid = 0;
-       wc.sl = 0;
-       wc.dlid_path_bits = 0;
-       wc.port_num = 0;
-
-       while (qp->s_last != qp->s_head) {
-               struct ipath_swqe *wqe = get_swqe_ptr(qp, qp->s_last);
-
-               wc.wr_id = wqe->wr.wr_id;
-               wc.opcode = ib_ipath_wc_opcode[wqe->wr.opcode];
-               if (++qp->s_last >= qp->s_size)
-                       qp->s_last = 0;
-               ipath_cq_enter(to_icq(qp->ibqp.send_cq), &wc, 1);
-       }
-       qp->s_cur = qp->s_tail = qp->s_head;
-       qp->s_hdrwords = 0;
-       qp->s_ack_state = IB_OPCODE_RC_ACKNOWLEDGE;
-
-       wc.opcode = IB_WC_RECV;
-       while (qp->r_rq.tail != qp->r_rq.head) {
-               wc.wr_id = get_rwqe_ptr(&qp->r_rq, qp->r_rq.tail)->wr_id;
-               if (++qp->r_rq.tail >= qp->r_rq.size)
-                       qp->r_rq.tail = 0;
-               ipath_cq_enter(to_icq(qp->ibqp.recv_cq), &wc, 1);
-       }
-}
-
 /**
  * ipath_get_credit - flush the send work queue of a QP
  * @qp: the qp who's send work queue to flush
index 5ff3de6128b2fd21b9f79f8dfb64704f65aa643e..01cfb30ee16040f31ee06a01527227ece95176ba 100644 (file)
@@ -46,8 +46,8 @@
  * This is called from ipath_post_ud_send() to forward a WQE addressed
  * to the same HCA.
  */
-void ipath_ud_loopback(struct ipath_qp *sqp, struct ipath_sge_state *ss,
-                      u32 length, struct ib_send_wr *wr, struct ib_wc *wc)
+static void ipath_ud_loopback(struct ipath_qp *sqp, struct ipath_sge_state *ss,
+                             u32 length, struct ib_send_wr *wr, struct ib_wc *wc)
 {
        struct ipath_ibdev *dev = to_idev(sqp->ibqp.device);
        struct ipath_qp *qp;
index 9f27fd35cdbb7e5500c4f5b7e17e8b5418b78221..8d2558a01f35e5a599d1fb0a0827987934fbdc75 100644 (file)
@@ -41,7 +41,7 @@
 /* Not static, because we don't want the compiler removing it */
 const char ipath_verbs_version[] = "ipath_verbs " IPATH_IDSTR;
 
-unsigned int ib_ipath_qp_table_size = 251;
+static unsigned int ib_ipath_qp_table_size = 251;
 module_param_named(qp_table_size, ib_ipath_qp_table_size, uint, S_IRUGO);
 MODULE_PARM_DESC(qp_table_size, "QP table size");
 
@@ -87,7 +87,7 @@ const enum ib_wc_opcode ib_ipath_wc_opcode[] = {
 /*
  * System image GUID.
  */
-__be64 sys_image_guid;
+static __be64 sys_image_guid;
 
 /**
  * ipath_copy_sge - copy data to SGE memory
@@ -1110,7 +1110,7 @@ static void ipath_unregister_ib_device(void *arg)
        ib_dealloc_device(ibdev);
 }
 
-int __init ipath_verbs_init(void)
+static int __init ipath_verbs_init(void)
 {
        return ipath_verbs_register(ipath_register_ib_device,
                                    ipath_unregister_ib_device,
@@ -1118,33 +1118,33 @@ int __init ipath_verbs_init(void)
                                    ipath_ib_timer);
 }
 
-void __exit ipath_verbs_cleanup(void)
+static void __exit ipath_verbs_cleanup(void)
 {
        ipath_verbs_unregister();
 }
 
 static ssize_t show_rev(struct class_device *cdev, char *buf)
 {
-        struct ipath_ibdev *dev =
-                container_of(cdev, struct ipath_ibdev, ibdev.class_dev);
-        int vendor, boardrev, majrev, minrev;
+       struct ipath_ibdev *dev =
+               container_of(cdev, struct ipath_ibdev, ibdev.class_dev);
+       int vendor, boardrev, majrev, minrev;
 
-        ipath_layer_query_device(dev->dd, &vendor, &boardrev,
-                                 &majrev, &minrev);
-        return sprintf(buf, "%d.%d\n", majrev, minrev);
+       ipath_layer_query_device(dev->dd, &vendor, &boardrev,
+                                &majrev, &minrev);
+       return sprintf(buf, "%d.%d\n", majrev, minrev);
 }
 
 static ssize_t show_hca(struct class_device *cdev, char *buf)
 {
-        struct ipath_ibdev *dev =
-                container_of(cdev, struct ipath_ibdev, ibdev.class_dev);
-        int ret;
+       struct ipath_ibdev *dev =
+               container_of(cdev, struct ipath_ibdev, ibdev.class_dev);
+       int ret;
 
-        ret = ipath_layer_get_boardname(dev->dd, buf, 128);
-        if (ret < 0)
-                goto bail;
-        strcat(buf, "\n");
-        ret = strlen(buf);
+       ret = ipath_layer_get_boardname(dev->dd, buf, 128);
+       if (ret < 0)
+               goto bail;
+       strcat(buf, "\n");
+       ret = strlen(buf);
 
 bail:
        return ret;
@@ -1152,40 +1152,40 @@ bail:
 
 static ssize_t show_stats(struct class_device *cdev, char *buf)
 {
-        struct ipath_ibdev *dev =
-                container_of(cdev, struct ipath_ibdev, ibdev.class_dev);
-        int i;
-        int len;
-
-        len = sprintf(buf,
-                      "RC resends  %d\n"
-                      "RC QACKs    %d\n"
-                      "RC ACKs     %d\n"
-                      "RC SEQ NAKs %d\n"
-                      "RC RDMA seq %d\n"
-                      "RC RNR NAKs %d\n"
-                      "RC OTH NAKs %d\n"
-                      "RC timeouts %d\n"
-                      "RC RDMA dup %d\n"
-                      "piobuf wait %d\n"
-                      "no piobuf   %d\n"
-                      "PKT drops   %d\n"
-                      "WQE errs    %d\n",
-                      dev->n_rc_resends, dev->n_rc_qacks, dev->n_rc_acks,
-                      dev->n_seq_naks, dev->n_rdma_seq, dev->n_rnr_naks,
-                      dev->n_other_naks, dev->n_timeouts,
-                      dev->n_rdma_dup_busy, dev->n_piowait,
-                      dev->n_no_piobuf, dev->n_pkt_drops, dev->n_wqe_errs);
-        for (i = 0; i < ARRAY_SIZE(dev->opstats); i++) {
+       struct ipath_ibdev *dev =
+               container_of(cdev, struct ipath_ibdev, ibdev.class_dev);
+       int i;
+       int len;
+
+       len = sprintf(buf,
+                     "RC resends  %d\n"
+                     "RC QACKs    %d\n"
+                     "RC ACKs     %d\n"
+                     "RC SEQ NAKs %d\n"
+                     "RC RDMA seq %d\n"
+                     "RC RNR NAKs %d\n"
+                     "RC OTH NAKs %d\n"
+                     "RC timeouts %d\n"
+                     "RC RDMA dup %d\n"
+                     "piobuf wait %d\n"
+                     "no piobuf   %d\n"
+                     "PKT drops   %d\n"
+                     "WQE errs    %d\n",
+                     dev->n_rc_resends, dev->n_rc_qacks, dev->n_rc_acks,
+                     dev->n_seq_naks, dev->n_rdma_seq, dev->n_rnr_naks,
+                     dev->n_other_naks, dev->n_timeouts,
+                     dev->n_rdma_dup_busy, dev->n_piowait,
+                     dev->n_no_piobuf, dev->n_pkt_drops, dev->n_wqe_errs);
+       for (i = 0; i < ARRAY_SIZE(dev->opstats); i++) {
                const struct ipath_opcode_stats *si = &dev->opstats[i];
 
-                if (!si->n_packets && !si->n_bytes)
-                        continue;
-                len += sprintf(buf + len, "%02x %llu/%llu\n", i,
+               if (!si->n_packets && !si->n_bytes)
+                       continue;
+               len += sprintf(buf + len, "%02x %llu/%llu\n", i,
                               (unsigned long long) si->n_packets,
-                               (unsigned long long) si->n_bytes);
-        }
-        return len;
+                              (unsigned long long) si->n_bytes);
+       }
+       return len;
 }
 
 static CLASS_DEVICE_ATTR(hw_rev, S_IRUGO, show_rev, NULL);
@@ -1194,25 +1194,25 @@ static CLASS_DEVICE_ATTR(board_id, S_IRUGO, show_hca, NULL);
 static CLASS_DEVICE_ATTR(stats, S_IRUGO, show_stats, NULL);
 
 static struct class_device_attribute *ipath_class_attributes[] = {
-        &class_device_attr_hw_rev,
-        &class_device_attr_hca_type,
-        &class_device_attr_board_id,
-        &class_device_attr_stats
+       &class_device_attr_hw_rev,
+       &class_device_attr_hca_type,
+       &class_device_attr_board_id,
+       &class_device_attr_stats
 };
 
 static int ipath_verbs_register_sysfs(struct ib_device *dev)
 {
-        int i;
+       int i;
        int ret;
 
-        for (i = 0; i < ARRAY_SIZE(ipath_class_attributes); ++i)
-                if (class_device_create_file(&dev->class_dev,
-                                             ipath_class_attributes[i])) {
-                        ret = 1;
+       for (i = 0; i < ARRAY_SIZE(ipath_class_attributes); ++i)
+               if (class_device_create_file(&dev->class_dev,
+                                            ipath_class_attributes[i])) {
+                       ret = 1;
                        goto bail;
                }
 
-        ret = 0;
+       ret = 0;
 
 bail:
        return ret;
index b824632b2a8c4f35809bcdb3ddc60c00cbece7c7..fcafbc7c9e71053002d9cd9b1a93bff2490ff545 100644 (file)
@@ -577,8 +577,6 @@ int ipath_init_qp_table(struct ipath_ibdev *idev, int size);
 
 void ipath_sqerror_qp(struct ipath_qp *qp, struct ib_wc *wc);
 
-void ipath_error_qp(struct ipath_qp *qp);
-
 void ipath_get_credit(struct ipath_qp *qp, u32 aeth);
 
 void ipath_do_rc_send(unsigned long data);
@@ -607,9 +605,6 @@ void ipath_rc_rcv(struct ipath_ibdev *dev, struct ipath_ib_header *hdr,
 
 void ipath_restart_rc(struct ipath_qp *qp, u32 psn, struct ib_wc *wc);
 
-void ipath_ud_loopback(struct ipath_qp *sqp, struct ipath_sge_state *ss,
-                      u32 length, struct ib_send_wr *wr, struct ib_wc *wc);
-
 int ipath_post_ud_send(struct ipath_qp *qp, struct ib_send_wr *wr);
 
 void ipath_ud_rcv(struct ipath_ibdev *dev, struct ipath_ib_header *hdr,
index e88be85b3d5cac6724e99532e0589ac0c391a0cd..9aa5a4468a753c0ee241277e8d957ffb8207b8d4 100644 (file)
@@ -7,10 +7,11 @@ config INFINIBAND_MTHCA
          ("Tavor") and the MT25208 PCI Express HCA ("Arbel").
 
 config INFINIBAND_MTHCA_DEBUG
-       bool "Verbose debugging output"
+       bool "Verbose debugging output" if EMBEDDED
        depends on INFINIBAND_MTHCA
-       default n
+       default y
        ---help---
-         This option causes the mthca driver produce a bunch of debug
-         messages.  Select this is you are developing the driver or
-         trying to diagnose a problem.
+         This option causes debugging code to be compiled into the
+         mthca driver.  The output can be turned on via the
+         debug_level module parameter (which can also be set after
+         the driver is loaded through sysfs).
index 47ec5a7cba0b61ba39744769866b5c91120b91e8..e388d95d0cf1e76c6eceeb61a1b793585b26e1ff 100644 (file)
@@ -1,7 +1,3 @@
-ifdef CONFIG_INFINIBAND_MTHCA_DEBUG
-EXTRA_CFLAGS += -DDEBUG
-endif
-
 obj-$(CONFIG_INFINIBAND_MTHCA) += ib_mthca.o
 
 ib_mthca-y :=  mthca_main.o mthca_cmd.o mthca_profile.o mthca_reset.o \
index bc5bdcbe51b5678c25c57789aacfa57aaf980637..b12aa03be25115a1198e7178ffb5720066e20f27 100644 (file)
 
 #include "mthca_dev.h"
 
+enum {
+      MTHCA_RATE_TAVOR_FULL   = 0,
+      MTHCA_RATE_TAVOR_1X     = 1,
+      MTHCA_RATE_TAVOR_4X     = 2,
+      MTHCA_RATE_TAVOR_1X_DDR = 3
+};
+
+enum {
+      MTHCA_RATE_MEMFREE_FULL    = 0,
+      MTHCA_RATE_MEMFREE_QUARTER = 1,
+      MTHCA_RATE_MEMFREE_EIGHTH  = 2,
+      MTHCA_RATE_MEMFREE_HALF    = 3
+};
+
 struct mthca_av {
        __be32 port_pd;
        u8     reserved1;
@@ -55,6 +69,90 @@ struct mthca_av {
        __be32 dgid[4];
 };
 
+static enum ib_rate memfree_rate_to_ib(u8 mthca_rate, u8 port_rate)
+{
+       switch (mthca_rate) {
+       case MTHCA_RATE_MEMFREE_EIGHTH:
+               return mult_to_ib_rate(port_rate >> 3);
+       case MTHCA_RATE_MEMFREE_QUARTER:
+               return mult_to_ib_rate(port_rate >> 2);
+       case MTHCA_RATE_MEMFREE_HALF:
+               return mult_to_ib_rate(port_rate >> 1);
+       case MTHCA_RATE_MEMFREE_FULL:
+       default:
+               return mult_to_ib_rate(port_rate);
+       }
+}
+
+static enum ib_rate tavor_rate_to_ib(u8 mthca_rate, u8 port_rate)
+{
+       switch (mthca_rate) {
+       case MTHCA_RATE_TAVOR_1X:     return IB_RATE_2_5_GBPS;
+       case MTHCA_RATE_TAVOR_1X_DDR: return IB_RATE_5_GBPS;
+       case MTHCA_RATE_TAVOR_4X:     return IB_RATE_10_GBPS;
+       default:                      return port_rate;
+       }
+}
+
+enum ib_rate mthca_rate_to_ib(struct mthca_dev *dev, u8 mthca_rate, u8 port)
+{
+       if (mthca_is_memfree(dev)) {
+               /* Handle old Arbel FW */
+               if (dev->limits.stat_rate_support == 0x3 && mthca_rate)
+                       return IB_RATE_2_5_GBPS;
+
+               return memfree_rate_to_ib(mthca_rate, dev->rate[port - 1]);
+       } else
+               return tavor_rate_to_ib(mthca_rate, dev->rate[port - 1]);
+}
+
+static u8 ib_rate_to_memfree(u8 req_rate, u8 cur_rate)
+{
+       if (cur_rate <= req_rate)
+               return 0;
+
+       /*
+        * Inter-packet delay (IPD) to get from rate X down to a rate
+        * no more than Y is (X - 1) / Y.
+        */
+       switch ((cur_rate - 1) / req_rate) {
+       case 0:  return MTHCA_RATE_MEMFREE_FULL;
+       case 1:  return MTHCA_RATE_MEMFREE_HALF;
+       case 2:  /* fall through */
+       case 3:  return MTHCA_RATE_MEMFREE_QUARTER;
+       default: return MTHCA_RATE_MEMFREE_EIGHTH;
+       }
+}
+
+static u8 ib_rate_to_tavor(u8 static_rate)
+{
+       switch (static_rate) {
+       case IB_RATE_2_5_GBPS: return MTHCA_RATE_TAVOR_1X;
+       case IB_RATE_5_GBPS:   return MTHCA_RATE_TAVOR_1X_DDR;
+       case IB_RATE_10_GBPS:  return MTHCA_RATE_TAVOR_4X;
+       default:               return MTHCA_RATE_TAVOR_FULL;
+       }
+}
+
+u8 mthca_get_rate(struct mthca_dev *dev, int static_rate, u8 port)
+{
+       u8 rate;
+
+       if (!static_rate || ib_rate_to_mult(static_rate) >= dev->rate[port - 1])
+               return 0;
+
+       if (mthca_is_memfree(dev))
+               rate = ib_rate_to_memfree(ib_rate_to_mult(static_rate),
+                                         dev->rate[port - 1]);
+       else
+               rate = ib_rate_to_tavor(static_rate);
+
+       if (!(dev->limits.stat_rate_support & (1 << rate)))
+               rate = 1;
+
+       return rate;
+}
+
 int mthca_create_ah(struct mthca_dev *dev,
                    struct mthca_pd *pd,
                    struct ib_ah_attr *ah_attr,
@@ -107,7 +205,7 @@ on_hca_fail:
        av->g_slid  = ah_attr->src_path_bits;
        av->dlid    = cpu_to_be16(ah_attr->dlid);
        av->msg_sr  = (3 << 4) | /* 2K message */
-               ah_attr->static_rate;
+               mthca_get_rate(dev, ah_attr->static_rate, ah_attr->port_num);
        av->sl_tclass_flowlabel = cpu_to_be32(ah_attr->sl << 28);
        if (ah_attr->ah_flags & IB_AH_GRH) {
                av->g_slid |= 0x80;
index 343eca507870c53eefcbdf8b881e89e1907791b6..1985b5dfa481bdb91efaf5611bba73f83de3a1b1 100644 (file)
@@ -965,6 +965,7 @@ int mthca_QUERY_DEV_LIM(struct mthca_dev *dev,
        u32 *outbox;
        u8 field;
        u16 size;
+       u16 stat_rate;
        int err;
 
 #define QUERY_DEV_LIM_OUT_SIZE             0x100
@@ -995,6 +996,7 @@ int mthca_QUERY_DEV_LIM(struct mthca_dev *dev,
 #define QUERY_DEV_LIM_MTU_WIDTH_OFFSET      0x36
 #define QUERY_DEV_LIM_VL_PORT_OFFSET        0x37
 #define QUERY_DEV_LIM_MAX_GID_OFFSET        0x3b
+#define QUERY_DEV_LIM_RATE_SUPPORT_OFFSET   0x3c
 #define QUERY_DEV_LIM_MAX_PKEY_OFFSET       0x3f
 #define QUERY_DEV_LIM_FLAGS_OFFSET          0x44
 #define QUERY_DEV_LIM_RSVD_UAR_OFFSET       0x48
@@ -1086,6 +1088,8 @@ int mthca_QUERY_DEV_LIM(struct mthca_dev *dev,
        dev_lim->num_ports = field & 0xf;
        MTHCA_GET(field, outbox, QUERY_DEV_LIM_MAX_GID_OFFSET);
        dev_lim->max_gids = 1 << (field & 0xf);
+       MTHCA_GET(stat_rate, outbox, QUERY_DEV_LIM_RATE_SUPPORT_OFFSET);
+       dev_lim->stat_rate_support = stat_rate;
        MTHCA_GET(field, outbox, QUERY_DEV_LIM_MAX_PKEY_OFFSET);
        dev_lim->max_pkeys = 1 << (field & 0xf);
        MTHCA_GET(dev_lim->flags, outbox, QUERY_DEV_LIM_FLAGS_OFFSET);
index e4ec35c40dd3c1cf892bf649ec2c4ca92ea5eed4..2f976f2051d6a1dbc9c39bc0046305d8a72fae66 100644 (file)
@@ -146,6 +146,7 @@ struct mthca_dev_lim {
        int max_vl;
        int num_ports;
        int max_gids;
+       u16 stat_rate_support;
        int max_pkeys;
        u32 flags;
        int reserved_uars;
index ad52edbefe98b16da4bb538cda021da760b539d0..4c1dcb4c18222056844f29999c9e2f61e61f0cff 100644 (file)
@@ -151,6 +151,7 @@ struct mthca_limits {
        int      reserved_qps;
        int      num_srqs;
        int      max_srq_wqes;
+       int      max_srq_sge;
        int      reserved_srqs;
        int      num_eecs;
        int      reserved_eecs;
@@ -172,6 +173,7 @@ struct mthca_limits {
        int      reserved_pds;
        u32      page_size_cap;
        u32      flags;
+       u16      stat_rate_support;
        u8       port_width_cap;
 };
 
@@ -353,10 +355,24 @@ struct mthca_dev {
        struct ib_mad_agent  *send_agent[MTHCA_MAX_PORTS][2];
        struct ib_ah         *sm_ah[MTHCA_MAX_PORTS];
        spinlock_t            sm_lock;
+       u8                    rate[MTHCA_MAX_PORTS];
 };
 
-#define mthca_dbg(mdev, format, arg...) \
-       dev_dbg(&mdev->pdev->dev, format, ## arg)
+#ifdef CONFIG_INFINIBAND_MTHCA_DEBUG
+extern int mthca_debug_level;
+
+#define mthca_dbg(mdev, format, arg...)                                        \
+       do {                                                            \
+               if (mthca_debug_level)                                  \
+                       dev_printk(KERN_DEBUG, &mdev->pdev->dev, format, ## arg); \
+       } while (0)
+
+#else /* CONFIG_INFINIBAND_MTHCA_DEBUG */
+
+#define mthca_dbg(mdev, format, arg...) do { (void) mdev; } while (0)
+
+#endif /* CONFIG_INFINIBAND_MTHCA_DEBUG */
+
 #define mthca_err(mdev, format, arg...) \
        dev_err(&mdev->pdev->dev, format, ## arg)
 #define mthca_info(mdev, format, arg...) \
@@ -492,6 +508,7 @@ void mthca_free_srq(struct mthca_dev *dev, struct mthca_srq *srq);
 int mthca_modify_srq(struct ib_srq *ibsrq, struct ib_srq_attr *attr,
                     enum ib_srq_attr_mask attr_mask);
 int mthca_query_srq(struct ib_srq *srq, struct ib_srq_attr *srq_attr);
+int mthca_max_srq_sge(struct mthca_dev *dev);
 void mthca_srq_event(struct mthca_dev *dev, u32 srqn,
                     enum ib_event_type event_type);
 void mthca_free_srq_wqe(struct mthca_srq *srq, u32 wqe_addr);
@@ -542,6 +559,8 @@ int mthca_read_ah(struct mthca_dev *dev, struct mthca_ah *ah,
                  struct ib_ud_header *header);
 int mthca_ah_query(struct ib_ah *ibah, struct ib_ah_attr *attr);
 int mthca_ah_grh_present(struct mthca_ah *ah);
+u8 mthca_get_rate(struct mthca_dev *dev, int static_rate, u8 port);
+enum ib_rate mthca_rate_to_ib(struct mthca_dev *dev, u8 mthca_rate, u8 port);
 
 int mthca_multicast_attach(struct ib_qp *ibqp, union ib_gid *gid, u16 lid);
 int mthca_multicast_detach(struct ib_qp *ibqp, union ib_gid *gid, u16 lid);
index dfb482eac9a25ef56123d3bc7396237f7fcbae87..4730863ece9a398c89e62c366d2f112d81b509f4 100644 (file)
@@ -49,6 +49,30 @@ enum {
        MTHCA_VENDOR_CLASS2 = 0xa
 };
 
+static int mthca_update_rate(struct mthca_dev *dev, u8 port_num)
+{
+       struct ib_port_attr *tprops = NULL;
+       int                  ret;
+
+       tprops = kmalloc(sizeof *tprops, GFP_KERNEL);
+       if (!tprops)
+               return -ENOMEM;
+
+       ret = ib_query_port(&dev->ib_dev, port_num, tprops);
+       if (ret) {
+               printk(KERN_WARNING "ib_query_port failed (%d) for %s port %d\n",
+                      ret, dev->ib_dev.name, port_num);
+               goto out;
+       }
+
+       dev->rate[port_num - 1] = tprops->active_speed *
+                                 ib_width_enum_to_int(tprops->active_width);
+
+out:
+       kfree(tprops);
+       return ret;
+}
+
 static void update_sm_ah(struct mthca_dev *dev,
                         u8 port_num, u16 lid, u8 sl)
 {
@@ -90,6 +114,7 @@ static void smp_snoop(struct ib_device *ibdev,
             mad->mad_hdr.mgmt_class  == IB_MGMT_CLASS_SUBN_DIRECTED_ROUTE) &&
            mad->mad_hdr.method     == IB_MGMT_METHOD_SET) {
                if (mad->mad_hdr.attr_id == IB_SMP_ATTR_PORT_INFO) {
+                       mthca_update_rate(to_mdev(ibdev), port_num);
                        update_sm_ah(to_mdev(ibdev), port_num,
                                     be16_to_cpup((__be16 *) (mad->data + 58)),
                                     (*(u8 *) (mad->data + 76)) & 0xf);
@@ -246,6 +271,7 @@ int mthca_create_agents(struct mthca_dev *dev)
 {
        struct ib_mad_agent *agent;
        int p, q;
+       int ret;
 
        spin_lock_init(&dev->sm_lock);
 
@@ -255,11 +281,23 @@ int mthca_create_agents(struct mthca_dev *dev)
                                                      q ? IB_QPT_GSI : IB_QPT_SMI,
                                                      NULL, 0, send_handler,
                                                      NULL, NULL);
-                       if (IS_ERR(agent))
+                       if (IS_ERR(agent)) {
+                               ret = PTR_ERR(agent);
                                goto err;
+                       }
                        dev->send_agent[p][q] = agent;
                }
 
+
+       for (p = 1; p <= dev->limits.num_ports; ++p) {
+               ret = mthca_update_rate(dev, p);
+               if (ret) {
+                       mthca_err(dev, "Failed to obtain port %d rate."
+                                 " aborting.\n", p);
+                       goto err;
+               }
+       }
+
        return 0;
 
 err:
@@ -268,7 +306,7 @@ err:
                        if (dev->send_agent[p][q])
                                ib_unregister_mad_agent(dev->send_agent[p][q]);
 
-       return PTR_ERR(agent);
+       return ret;
 }
 
 void __devexit mthca_free_agents(struct mthca_dev *dev)
index 266f347c670767285c138299a554de729b5b3697..9b9ff7bff357a2ea8a4d9ab8d6747eea373ade95 100644 (file)
@@ -52,6 +52,14 @@ MODULE_DESCRIPTION("Mellanox InfiniBand HCA low-level driver");
 MODULE_LICENSE("Dual BSD/GPL");
 MODULE_VERSION(DRV_VERSION);
 
+#ifdef CONFIG_INFINIBAND_MTHCA_DEBUG
+
+int mthca_debug_level = 0;
+module_param_named(debug_level, mthca_debug_level, int, 0644);
+MODULE_PARM_DESC(debug_level, "Enable debug tracing if > 0");
+
+#endif /* CONFIG_INFINIBAND_MTHCA_DEBUG */
+
 #ifdef CONFIG_PCI_MSI
 
 static int msi_x = 0;
@@ -69,6 +77,10 @@ MODULE_PARM_DESC(msi, "attempt to use MSI if nonzero");
 
 #endif /* CONFIG_PCI_MSI */
 
+static int tune_pci = 0;
+module_param(tune_pci, int, 0444);
+MODULE_PARM_DESC(tune_pci, "increase PCI burst from the default set by BIOS if nonzero");
+
 static const char mthca_version[] __devinitdata =
        DRV_NAME ": Mellanox InfiniBand HCA driver v"
        DRV_VERSION " (" DRV_RELDATE ")\n";
@@ -90,6 +102,9 @@ static int __devinit mthca_tune_pci(struct mthca_dev *mdev)
        int cap;
        u16 val;
 
+       if (!tune_pci)
+               return 0;
+
        /* First try to max out Read Byte Count */
        cap = pci_find_capability(mdev->pdev, PCI_CAP_ID_PCIX);
        if (cap) {
@@ -176,6 +191,7 @@ static int __devinit mthca_dev_lim(struct mthca_dev *mdev, struct mthca_dev_lim
        mdev->limits.reserved_srqs      = dev_lim->reserved_srqs;
        mdev->limits.reserved_eecs      = dev_lim->reserved_eecs;
        mdev->limits.max_desc_sz        = dev_lim->max_desc_sz;
+       mdev->limits.max_srq_sge        = mthca_max_srq_sge(mdev);
        /*
         * Subtract 1 from the limit because we need to allocate a
         * spare CQE so the HCA HW can tell the difference between an
@@ -191,6 +207,18 @@ static int __devinit mthca_dev_lim(struct mthca_dev *mdev, struct mthca_dev_lim
        mdev->limits.port_width_cap     = dev_lim->max_port_width;
        mdev->limits.page_size_cap      = ~(u32) (dev_lim->min_page_sz - 1);
        mdev->limits.flags              = dev_lim->flags;
+       /*
+        * For old FW that doesn't return static rate support, use a
+        * value of 0x3 (only static rate values of 0 or 1 are handled),
+        * except on Sinai, where even old FW can handle static rate
+        * values of 2 and 3.
+        */
+       if (dev_lim->stat_rate_support)
+               mdev->limits.stat_rate_support = dev_lim->stat_rate_support;
+       else if (mdev->mthca_flags & MTHCA_FLAG_SINAI_OPT)
+               mdev->limits.stat_rate_support = 0xf;
+       else
+               mdev->limits.stat_rate_support = 0x3;
 
        /* IB_DEVICE_RESIZE_MAX_WR not supported by driver.
           May be doable since hardware supports it for SRQ.
index 2c250bc11c332d180d0856f727aad96b241f7c05..565a24b1756f10647688e0ffb3b70a5b948160c6 100644 (file)
@@ -106,7 +106,7 @@ static int mthca_query_device(struct ib_device *ibdev,
        props->max_res_rd_atom     = props->max_qp_rd_atom * props->max_qp;
        props->max_srq             = mdev->limits.num_srqs - mdev->limits.reserved_srqs;
        props->max_srq_wr          = mdev->limits.max_srq_wqes;
-       props->max_srq_sge         = mdev->limits.max_sg;
+       props->max_srq_sge         = mdev->limits.max_srq_sge;
        props->local_ca_ack_delay  = mdev->limits.local_ca_ack_delay;
        props->atomic_cap          = mdev->limits.flags & DEV_LIM_FLAG_ATOMIC ?
                                        IB_ATOMIC_HCA : IB_ATOMIC_NONE;
index 2e7f5213696510b1828b745e3be9419f21b0ba10..6676a786d69091118d459ab428c794b829808367 100644 (file)
@@ -257,6 +257,8 @@ struct mthca_qp {
        atomic_t               refcount;
        u32                    qpn;
        int                    is_direct;
+       u8                     port; /* for SQP and memfree use only */
+       u8                     alt_port; /* for memfree use only */
        u8                     transport;
        u8                     state;
        u8                     atomic_rd_en;
@@ -278,7 +280,6 @@ struct mthca_qp {
 
 struct mthca_sqp {
        struct mthca_qp qp;
-       int             port;
        int             pkey_index;
        u32             qkey;
        u32             send_psn;
index 057c8e6af87b3900ceca707775dbd68cff12e64e..f37b0e3673230aa1d1bbd17b65d17ddc89d2de4b 100644 (file)
@@ -248,6 +248,9 @@ void mthca_qp_event(struct mthca_dev *dev, u32 qpn,
                return;
        }
 
+       if (event_type == IB_EVENT_PATH_MIG)
+               qp->port = qp->alt_port;
+
        event.device      = &dev->ib_dev;
        event.event       = event_type;
        event.element.qp  = &qp->ibqp;
@@ -392,10 +395,16 @@ static void to_ib_ah_attr(struct mthca_dev *dev, struct ib_ah_attr *ib_ah_attr,
 {
        memset(ib_ah_attr, 0, sizeof *path);
        ib_ah_attr->port_num      = (be32_to_cpu(path->port_pkey) >> 24) & 0x3;
+
+       if (ib_ah_attr->port_num == 0 || ib_ah_attr->port_num > dev->limits.num_ports)
+               return;
+
        ib_ah_attr->dlid          = be16_to_cpu(path->rlid);
        ib_ah_attr->sl            = be32_to_cpu(path->sl_tclass_flowlabel) >> 28;
        ib_ah_attr->src_path_bits = path->g_mylmc & 0x7f;
-       ib_ah_attr->static_rate   = path->static_rate & 0x7;
+       ib_ah_attr->static_rate   = mthca_rate_to_ib(dev,
+                                                    path->static_rate & 0x7,
+                                                    ib_ah_attr->port_num);
        ib_ah_attr->ah_flags      = (path->g_mylmc & (1 << 7)) ? IB_AH_GRH : 0;
        if (ib_ah_attr->ah_flags) {
                ib_ah_attr->grh.sgid_index = path->mgid_index & (dev->limits.gid_table_len - 1);
@@ -455,8 +464,10 @@ int mthca_query_qp(struct ib_qp *ibqp, struct ib_qp_attr *qp_attr, int qp_attr_m
        qp_attr->cap.max_recv_sge    = qp->rq.max_gs;
        qp_attr->cap.max_inline_data = qp->max_inline_data;
 
-       to_ib_ah_attr(dev, &qp_attr->ah_attr, &context->pri_path);
-       to_ib_ah_attr(dev, &qp_attr->alt_ah_attr, &context->alt_path);
+       if (qp->transport == RC || qp->transport == UC) {
+               to_ib_ah_attr(dev, &qp_attr->ah_attr, &context->pri_path);
+               to_ib_ah_attr(dev, &qp_attr->alt_ah_attr, &context->alt_path);
+       }
 
        qp_attr->pkey_index     = be32_to_cpu(context->pri_path.port_pkey) & 0x7f;
        qp_attr->alt_pkey_index = be32_to_cpu(context->alt_path.port_pkey) & 0x7f;
@@ -484,11 +495,11 @@ out:
 }
 
 static int mthca_path_set(struct mthca_dev *dev, struct ib_ah_attr *ah,
-                         struct mthca_qp_path *path)
+                         struct mthca_qp_path *path, u8 port)
 {
        path->g_mylmc     = ah->src_path_bits & 0x7f;
        path->rlid        = cpu_to_be16(ah->dlid);
-       path->static_rate = !!ah->static_rate;
+       path->static_rate = mthca_get_rate(dev, ah->static_rate, port);
 
        if (ah->ah_flags & IB_AH_GRH) {
                if (ah->grh.sgid_index >= dev->limits.gid_table_len) {
@@ -634,7 +645,7 @@ int mthca_modify_qp(struct ib_qp *ibqp, struct ib_qp_attr *attr, int attr_mask)
 
        if (qp->transport == MLX)
                qp_context->pri_path.port_pkey |=
-                       cpu_to_be32(to_msqp(qp)->port << 24);
+                       cpu_to_be32(qp->port << 24);
        else {
                if (attr_mask & IB_QP_PORT) {
                        qp_context->pri_path.port_pkey |=
@@ -657,7 +668,8 @@ int mthca_modify_qp(struct ib_qp *ibqp, struct ib_qp_attr *attr, int attr_mask)
        }
 
        if (attr_mask & IB_QP_AV) {
-               if (mthca_path_set(dev, &attr->ah_attr, &qp_context->pri_path))
+               if (mthca_path_set(dev, &attr->ah_attr, &qp_context->pri_path,
+                                  attr_mask & IB_QP_PORT ? attr->port_num : qp->port))
                        return -EINVAL;
 
                qp_param->opt_param_mask |= cpu_to_be32(MTHCA_QP_OPTPAR_PRIMARY_ADDR_PATH);
@@ -681,7 +693,8 @@ int mthca_modify_qp(struct ib_qp *ibqp, struct ib_qp_attr *attr, int attr_mask)
                        return -EINVAL;
                }
 
-               if (mthca_path_set(dev, &attr->alt_ah_attr, &qp_context->alt_path))
+               if (mthca_path_set(dev, &attr->alt_ah_attr, &qp_context->alt_path,
+                                  attr->alt_ah_attr.port_num))
                        return -EINVAL;
 
                qp_context->alt_path.port_pkey |= cpu_to_be32(attr->alt_pkey_index |
@@ -791,6 +804,10 @@ int mthca_modify_qp(struct ib_qp *ibqp, struct ib_qp_attr *attr, int attr_mask)
                qp->atomic_rd_en = attr->qp_access_flags;
        if (attr_mask & IB_QP_MAX_DEST_RD_ATOMIC)
                qp->resp_depth = attr->max_dest_rd_atomic;
+       if (attr_mask & IB_QP_PORT)
+               qp->port = attr->port_num;
+       if (attr_mask & IB_QP_ALT_PATH)
+               qp->alt_port = attr->alt_port_num;
 
        if (is_sqp(dev, qp))
                store_attrs(to_msqp(qp), attr, attr_mask);
@@ -802,13 +819,13 @@ int mthca_modify_qp(struct ib_qp *ibqp, struct ib_qp_attr *attr, int attr_mask)
        if (is_qp0(dev, qp)) {
                if (cur_state != IB_QPS_RTR &&
                    new_state == IB_QPS_RTR)
-                       init_port(dev, to_msqp(qp)->port);
+                       init_port(dev, qp->port);
 
                if (cur_state != IB_QPS_RESET &&
                    cur_state != IB_QPS_ERR &&
                    (new_state == IB_QPS_RESET ||
                     new_state == IB_QPS_ERR))
-                       mthca_CLOSE_IB(dev, to_msqp(qp)->port, &status);
+                       mthca_CLOSE_IB(dev, qp->port, &status);
        }
 
        /*
@@ -1212,6 +1229,9 @@ int mthca_alloc_qp(struct mthca_dev *dev,
        if (qp->qpn == -1)
                return -ENOMEM;
 
+       /* initialize port to zero for error-catching. */
+       qp->port = 0;
+
        err = mthca_alloc_qp_common(dev, pd, send_cq, recv_cq,
                                    send_policy, qp);
        if (err) {
@@ -1261,7 +1281,7 @@ int mthca_alloc_sqp(struct mthca_dev *dev,
        if (err)
                goto err_out;
 
-       sqp->port = port;
+       sqp->qp.port      = port;
        sqp->qp.qpn       = mqpn;
        sqp->qp.transport = MLX;
 
@@ -1404,10 +1424,10 @@ static int build_mlx_header(struct mthca_dev *dev, struct mthca_sqp *sqp,
                sqp->ud_header.lrh.source_lid = IB_LID_PERMISSIVE;
        sqp->ud_header.bth.solicited_event = !!(wr->send_flags & IB_SEND_SOLICITED);
        if (!sqp->qp.ibqp.qp_num)
-               ib_get_cached_pkey(&dev->ib_dev, sqp->port,
+               ib_get_cached_pkey(&dev->ib_dev, sqp->qp.port,
                                   sqp->pkey_index, &pkey);
        else
-               ib_get_cached_pkey(&dev->ib_dev, sqp->port,
+               ib_get_cached_pkey(&dev->ib_dev, sqp->qp.port,
                                   wr->wr.ud.pkey_index, &pkey);
        sqp->ud_header.bth.pkey = cpu_to_be16(pkey);
        sqp->ud_header.bth.destination_qpn = cpu_to_be32(wr->wr.ud.remote_qpn);
index 2dd3aea053415be7ce18ddf1186a6b32afceb462..adcaf85355ae6a33adb03dabb09c37f3ec85f0d3 100644 (file)
@@ -192,7 +192,7 @@ int mthca_alloc_srq(struct mthca_dev *dev, struct mthca_pd *pd,
 
        /* Sanity check SRQ size before proceeding */
        if (attr->max_wr  > dev->limits.max_srq_wqes ||
-           attr->max_sge > dev->limits.max_sg)
+           attr->max_sge > dev->limits.max_srq_sge)
                return -EINVAL;
 
        srq->max      = attr->max_wr;
@@ -660,6 +660,31 @@ int mthca_arbel_post_srq_recv(struct ib_srq *ibsrq, struct ib_recv_wr *wr,
        return err;
 }
 
+int mthca_max_srq_sge(struct mthca_dev *dev)
+{
+       if (mthca_is_memfree(dev))
+               return dev->limits.max_sg;
+
+       /*
+        * SRQ allocations are based on powers of 2 for Tavor,
+        * (although they only need to be multiples of 16 bytes).
+        *
+        * Therefore, we need to base the max number of sg entries on
+        * the largest power of 2 descriptor size that is <= to the
+        * actual max WQE descriptor size, rather than return the
+        * max_sg value given by the firmware (which is based on WQE
+        * sizes as multiples of 16, not powers of 2).
+        *
+        * If SRQ implementation is changed for Tavor to be based on
+        * multiples of 16, the calculation below can be deleted and
+        * the FW max_sg value returned.
+        */
+       return min_t(int, dev->limits.max_sg,
+                    ((1 << (fls(dev->limits.max_desc_sz) - 1)) -
+                     sizeof (struct mthca_next_seg)) /
+                    sizeof (struct mthca_data_seg));
+}
+
 int __devinit mthca_init_srq_table(struct mthca_dev *dev)
 {
        int err;
index 8d2e04cac68e02131e0ceb442a5506d7b2ccfa14..13d6d01c72c028f92b68fa27c7115e8c9c13c950 100644 (file)
@@ -10,8 +10,9 @@ config INFINIBAND_IPOIB
          group: <http://www.ietf.org/html.charters/ipoib-charter.html>.
 
 config INFINIBAND_IPOIB_DEBUG
-       bool "IP-over-InfiniBand debugging"
+       bool "IP-over-InfiniBand debugging" if EMBEDDED
        depends on INFINIBAND_IPOIB
+       default y
        ---help---
          This option causes debugging code to be compiled into the
          IPoIB driver.  The output can be turned on via the
index b640107fb732c4348e2d9d535ae8eb545913eba3..12a1e0572ef208fd341aad093aa45d4a29f0fce0 100644 (file)
@@ -65,6 +65,8 @@ enum {
 
        IPOIB_RX_RING_SIZE        = 128,
        IPOIB_TX_RING_SIZE        = 64,
+       IPOIB_MAX_QUEUE_SIZE      = 8192,
+       IPOIB_MIN_QUEUE_SIZE      = 2,
 
        IPOIB_NUM_WC              = 4,
 
@@ -230,6 +232,9 @@ static inline struct ipoib_neigh **to_ipoib_neigh(struct neighbour *neigh)
                                     INFINIBAND_ALEN, sizeof(void *));
 }
 
+struct ipoib_neigh *ipoib_neigh_alloc(struct neighbour *neigh);
+void ipoib_neigh_free(struct ipoib_neigh *neigh);
+
 extern struct workqueue_struct *ipoib_workqueue;
 
 /* functions */
@@ -329,6 +334,8 @@ static inline void ipoib_unregister_debugfs(void) { }
 #define ipoib_warn(priv, format, arg...)               \
        ipoib_printk(KERN_WARNING, priv, format , ## arg)
 
+extern int ipoib_sendq_size;
+extern int ipoib_recvq_size;
 
 #ifdef CONFIG_INFINIBAND_IPOIB_DEBUG
 extern int ipoib_debug_level;
index 685258e34034c90d24960b66a09041abd0fc0c05..5dde380e8dbe9c2653c0014020f32ebc8e87732d 100644 (file)
@@ -213,7 +213,7 @@ static int ipoib_path_seq_show(struct seq_file *file, void *iter_ptr)
                   gid_buf, path.pathrec.dlid ? "yes" : "no");
 
        if (path.pathrec.dlid) {
-               rate = ib_sa_rate_enum_to_int(path.pathrec.rate) * 25;
+               rate = ib_rate_to_mult(path.pathrec.rate) * 25;
 
                seq_printf(file,
                           "  DLID:     0x%04x\n"
index ed65202878d8fb5044ea960892b81d76385d7173..a54da42849ae1e9e19d3335326be70fe3c44880b 100644 (file)
@@ -161,7 +161,7 @@ static int ipoib_ib_post_receives(struct net_device *dev)
        struct ipoib_dev_priv *priv = netdev_priv(dev);
        int i;
 
-       for (i = 0; i < IPOIB_RX_RING_SIZE; ++i) {
+       for (i = 0; i < ipoib_recvq_size; ++i) {
                if (ipoib_alloc_rx_skb(dev, i)) {
                        ipoib_warn(priv, "failed to allocate receive buffer %d\n", i);
                        return -ENOMEM;
@@ -187,7 +187,7 @@ static void ipoib_ib_handle_wc(struct net_device *dev,
        if (wr_id & IPOIB_OP_RECV) {
                wr_id &= ~IPOIB_OP_RECV;
 
-               if (wr_id < IPOIB_RX_RING_SIZE) {
+               if (wr_id < ipoib_recvq_size) {
                        struct sk_buff *skb  = priv->rx_ring[wr_id].skb;
                        dma_addr_t      addr = priv->rx_ring[wr_id].mapping;
 
@@ -252,9 +252,9 @@ static void ipoib_ib_handle_wc(struct net_device *dev,
                struct ipoib_tx_buf *tx_req;
                unsigned long flags;
 
-               if (wr_id >= IPOIB_TX_RING_SIZE) {
+               if (wr_id >= ipoib_sendq_size) {
                        ipoib_warn(priv, "completion event with wrid %d (> %d)\n",
-                                  wr_id, IPOIB_TX_RING_SIZE);
+                                  wr_id, ipoib_sendq_size);
                        return;
                }
 
@@ -275,7 +275,7 @@ static void ipoib_ib_handle_wc(struct net_device *dev,
                spin_lock_irqsave(&priv->tx_lock, flags);
                ++priv->tx_tail;
                if (netif_queue_stopped(dev) &&
-                   priv->tx_head - priv->tx_tail <= IPOIB_TX_RING_SIZE / 2)
+                   priv->tx_head - priv->tx_tail <= ipoib_sendq_size >> 1)
                        netif_wake_queue(dev);
                spin_unlock_irqrestore(&priv->tx_lock, flags);
 
@@ -344,13 +344,13 @@ void ipoib_send(struct net_device *dev, struct sk_buff *skb,
         * means we have to make sure everything is properly recorded and
         * our state is consistent before we call post_send().
         */
-       tx_req = &priv->tx_ring[priv->tx_head & (IPOIB_TX_RING_SIZE - 1)];
+       tx_req = &priv->tx_ring[priv->tx_head & (ipoib_sendq_size - 1)];
        tx_req->skb = skb;
        addr = dma_map_single(priv->ca->dma_device, skb->data, skb->len,
                              DMA_TO_DEVICE);
        pci_unmap_addr_set(tx_req, mapping, addr);
 
-       if (unlikely(post_send(priv, priv->tx_head & (IPOIB_TX_RING_SIZE - 1),
+       if (unlikely(post_send(priv, priv->tx_head & (ipoib_sendq_size - 1),
                               address->ah, qpn, addr, skb->len))) {
                ipoib_warn(priv, "post_send failed\n");
                ++priv->stats.tx_errors;
@@ -363,7 +363,7 @@ void ipoib_send(struct net_device *dev, struct sk_buff *skb,
                address->last_send = priv->tx_head;
                ++priv->tx_head;
 
-               if (priv->tx_head - priv->tx_tail == IPOIB_TX_RING_SIZE) {
+               if (priv->tx_head - priv->tx_tail == ipoib_sendq_size) {
                        ipoib_dbg(priv, "TX ring full, stopping kernel net queue\n");
                        netif_stop_queue(dev);
                }
@@ -488,7 +488,7 @@ static int recvs_pending(struct net_device *dev)
        int pending = 0;
        int i;
 
-       for (i = 0; i < IPOIB_RX_RING_SIZE; ++i)
+       for (i = 0; i < ipoib_recvq_size; ++i)
                if (priv->rx_ring[i].skb)
                        ++pending;
 
@@ -527,7 +527,7 @@ int ipoib_ib_dev_stop(struct net_device *dev)
                         */
                        while ((int) priv->tx_tail - (int) priv->tx_head < 0) {
                                tx_req = &priv->tx_ring[priv->tx_tail &
-                                                       (IPOIB_TX_RING_SIZE - 1)];
+                                                       (ipoib_sendq_size - 1)];
                                dma_unmap_single(priv->ca->dma_device,
                                                 pci_unmap_addr(tx_req, mapping),
                                                 tx_req->skb->len,
@@ -536,7 +536,7 @@ int ipoib_ib_dev_stop(struct net_device *dev)
                                ++priv->tx_tail;
                        }
 
-                       for (i = 0; i < IPOIB_RX_RING_SIZE; ++i)
+                       for (i = 0; i < ipoib_recvq_size; ++i)
                                if (priv->rx_ring[i].skb) {
                                        dma_unmap_single(priv->ca->dma_device,
                                                         pci_unmap_addr(&priv->rx_ring[i],
index 9b0bd7c746ca1c8623c3d921f4135ba89a3b378c..cb078a7d0bf5b86551adf812fbc93724883616f8 100644 (file)
@@ -41,6 +41,7 @@
 #include <linux/init.h>
 #include <linux/slab.h>
 #include <linux/vmalloc.h>
+#include <linux/kernel.h>
 
 #include <linux/if_arp.h>      /* For ARPHRD_xxx */
 
@@ -53,6 +54,14 @@ MODULE_AUTHOR("Roland Dreier");
 MODULE_DESCRIPTION("IP-over-InfiniBand net driver");
 MODULE_LICENSE("Dual BSD/GPL");
 
+int ipoib_sendq_size __read_mostly = IPOIB_TX_RING_SIZE;
+int ipoib_recvq_size __read_mostly = IPOIB_RX_RING_SIZE;
+
+module_param_named(send_queue_size, ipoib_sendq_size, int, 0444);
+MODULE_PARM_DESC(send_queue_size, "Number of descriptors in send queue");
+module_param_named(recv_queue_size, ipoib_recvq_size, int, 0444);
+MODULE_PARM_DESC(recv_queue_size, "Number of descriptors in receive queue");
+
 #ifdef CONFIG_INFINIBAND_IPOIB_DEBUG
 int ipoib_debug_level;
 
@@ -252,8 +261,8 @@ static void path_free(struct net_device *dev, struct ipoib_path *path)
                 */
                if (neigh->ah)
                        ipoib_put_ah(neigh->ah);
-               *to_ipoib_neigh(neigh->neighbour) = NULL;
-               kfree(neigh);
+
+               ipoib_neigh_free(neigh);
        }
 
        spin_unlock_irqrestore(&priv->lock, flags);
@@ -327,9 +336,8 @@ void ipoib_flush_paths(struct net_device *dev)
        struct ipoib_dev_priv *priv = netdev_priv(dev);
        struct ipoib_path *path, *tp;
        LIST_HEAD(remove_list);
-       unsigned long flags;
 
-       spin_lock_irqsave(&priv->lock, flags);
+       spin_lock_irq(&priv->lock);
 
        list_splice(&priv->path_list, &remove_list);
        INIT_LIST_HEAD(&priv->path_list);
@@ -337,14 +345,15 @@ void ipoib_flush_paths(struct net_device *dev)
        list_for_each_entry(path, &remove_list, list)
                rb_erase(&path->rb_node, &priv->path_tree);
 
-       spin_unlock_irqrestore(&priv->lock, flags);
-
        list_for_each_entry_safe(path, tp, &remove_list, list) {
                if (path->query)
                        ib_sa_cancel_query(path->query_id, path->query);
+               spin_unlock_irq(&priv->lock);
                wait_for_completion(&path->done);
                path_free(dev, path);
+               spin_lock_irq(&priv->lock);
        }
+       spin_unlock_irq(&priv->lock);
 }
 
 static void path_rec_completion(int status,
@@ -373,16 +382,9 @@ static void path_rec_completion(int status,
                struct ib_ah_attr av = {
                        .dlid          = be16_to_cpu(pathrec->dlid),
                        .sl            = pathrec->sl,
-                       .port_num      = priv->port
+                       .port_num      = priv->port,
+                       .static_rate   = pathrec->rate
                };
-               int path_rate = ib_sa_rate_enum_to_int(pathrec->rate);
-
-               if (path_rate > 0 && priv->local_rate > path_rate)
-                       av.static_rate = (priv->local_rate - 1) / path_rate;
-
-               ipoib_dbg(priv, "static_rate %d for local port %dX, path %dX\n",
-                         av.static_rate, priv->local_rate,
-                         ib_sa_rate_enum_to_int(pathrec->rate));
 
                ah = ipoib_create_ah(dev, priv->pd, &av);
        }
@@ -481,7 +483,7 @@ static void neigh_add_path(struct sk_buff *skb, struct net_device *dev)
        struct ipoib_path *path;
        struct ipoib_neigh *neigh;
 
-       neigh = kmalloc(sizeof *neigh, GFP_ATOMIC);
+       neigh = ipoib_neigh_alloc(skb->dst->neighbour);
        if (!neigh) {
                ++priv->stats.tx_dropped;
                dev_kfree_skb_any(skb);
@@ -489,8 +491,6 @@ static void neigh_add_path(struct sk_buff *skb, struct net_device *dev)
        }
 
        skb_queue_head_init(&neigh->queue);
-       neigh->neighbour = skb->dst->neighbour;
-       *to_ipoib_neigh(skb->dst->neighbour) = neigh;
 
        /*
         * We can only be called from ipoib_start_xmit, so we're
@@ -503,7 +503,7 @@ static void neigh_add_path(struct sk_buff *skb, struct net_device *dev)
                path = path_rec_create(dev,
                                       (union ib_gid *) (skb->dst->neighbour->ha + 4));
                if (!path)
-                       goto err;
+                       goto err_path;
 
                __path_add(dev, path);
        }
@@ -521,17 +521,17 @@ static void neigh_add_path(struct sk_buff *skb, struct net_device *dev)
                __skb_queue_tail(&neigh->queue, skb);
 
                if (!path->query && path_rec_start(dev, path))
-                       goto err;
+                       goto err_list;
        }
 
        spin_unlock(&priv->lock);
        return;
 
-err:
-       *to_ipoib_neigh(skb->dst->neighbour) = NULL;
+err_list:
        list_del(&neigh->list);
-       kfree(neigh);
 
+err_path:
+       ipoib_neigh_free(neigh);
        ++priv->stats.tx_dropped;
        dev_kfree_skb_any(skb);
 
@@ -763,8 +763,7 @@ static void ipoib_neigh_destructor(struct neighbour *n)
                if (neigh->ah)
                        ah = neigh->ah;
                list_del(&neigh->list);
-               *to_ipoib_neigh(n) = NULL;
-               kfree(neigh);
+               ipoib_neigh_free(neigh);
        }
 
        spin_unlock_irqrestore(&priv->lock, flags);
@@ -773,6 +772,26 @@ static void ipoib_neigh_destructor(struct neighbour *n)
                ipoib_put_ah(ah);
 }
 
+struct ipoib_neigh *ipoib_neigh_alloc(struct neighbour *neighbour)
+{
+       struct ipoib_neigh *neigh;
+
+       neigh = kmalloc(sizeof *neigh, GFP_ATOMIC);
+       if (!neigh)
+               return NULL;
+
+       neigh->neighbour = neighbour;
+       *to_ipoib_neigh(neighbour) = neigh;
+
+       return neigh;
+}
+
+void ipoib_neigh_free(struct ipoib_neigh *neigh)
+{
+       *to_ipoib_neigh(neigh->neighbour) = NULL;
+       kfree(neigh);
+}
+
 static int ipoib_neigh_setup_dev(struct net_device *dev, struct neigh_parms *parms)
 {
        parms->neigh_destructor = ipoib_neigh_destructor;
@@ -785,20 +804,19 @@ int ipoib_dev_init(struct net_device *dev, struct ib_device *ca, int port)
        struct ipoib_dev_priv *priv = netdev_priv(dev);
 
        /* Allocate RX/TX "rings" to hold queued skbs */
-
-       priv->rx_ring = kzalloc(IPOIB_RX_RING_SIZE * sizeof (struct ipoib_rx_buf),
+       priv->rx_ring = kzalloc(ipoib_recvq_size * sizeof *priv->rx_ring,
                                GFP_KERNEL);
        if (!priv->rx_ring) {
                printk(KERN_WARNING "%s: failed to allocate RX ring (%d entries)\n",
-                      ca->name, IPOIB_RX_RING_SIZE);
+                      ca->name, ipoib_recvq_size);
                goto out;
        }
 
-       priv->tx_ring = kzalloc(IPOIB_TX_RING_SIZE * sizeof (struct ipoib_tx_buf),
+       priv->tx_ring = kzalloc(ipoib_sendq_size * sizeof *priv->tx_ring,
                                GFP_KERNEL);
        if (!priv->tx_ring) {
                printk(KERN_WARNING "%s: failed to allocate TX ring (%d entries)\n",
-                      ca->name, IPOIB_TX_RING_SIZE);
+                      ca->name, ipoib_sendq_size);
                goto out_rx_ring_cleanup;
        }
 
@@ -866,7 +884,7 @@ static void ipoib_setup(struct net_device *dev)
        dev->hard_header_len     = IPOIB_ENCAP_LEN + INFINIBAND_ALEN;
        dev->addr_len            = INFINIBAND_ALEN;
        dev->type                = ARPHRD_INFINIBAND;
-       dev->tx_queue_len        = IPOIB_TX_RING_SIZE * 2;
+       dev->tx_queue_len        = ipoib_sendq_size * 2;
        dev->features            = NETIF_F_VLAN_CHALLENGED | NETIF_F_LLTX;
 
        /* MTU will be reset when mcast join happens */
@@ -1118,6 +1136,14 @@ static int __init ipoib_init_module(void)
 {
        int ret;
 
+       ipoib_recvq_size = roundup_pow_of_two(ipoib_recvq_size);
+       ipoib_recvq_size = min(ipoib_recvq_size, IPOIB_MAX_QUEUE_SIZE);
+       ipoib_recvq_size = max(ipoib_recvq_size, IPOIB_MIN_QUEUE_SIZE);
+
+       ipoib_sendq_size = roundup_pow_of_two(ipoib_sendq_size);
+       ipoib_sendq_size = min(ipoib_sendq_size, IPOIB_MAX_QUEUE_SIZE);
+       ipoib_sendq_size = max(ipoib_sendq_size, IPOIB_MIN_QUEUE_SIZE);
+
        ret = ipoib_register_debugfs();
        if (ret)
                return ret;
index 93c462eaf4fd781c2ae93411c04c55878cc37325..1dae4b238252d3b204d68570bc4fa73f9e73959c 100644 (file)
@@ -114,8 +114,7 @@ static void ipoib_mcast_free(struct ipoib_mcast *mcast)
                 */
                if (neigh->ah)
                        ipoib_put_ah(neigh->ah);
-               *to_ipoib_neigh(neigh->neighbour) = NULL;
-               kfree(neigh);
+               ipoib_neigh_free(neigh);
        }
 
        spin_unlock_irqrestore(&priv->lock, flags);
@@ -251,6 +250,7 @@ static int ipoib_mcast_join_finish(struct ipoib_mcast *mcast,
                        .port_num      = priv->port,
                        .sl            = mcast->mcmember.sl,
                        .ah_flags      = IB_AH_GRH,
+                       .static_rate   = mcast->mcmember.rate,
                        .grh           = {
                                .flow_label    = be32_to_cpu(mcast->mcmember.flow_label),
                                .hop_limit     = mcast->mcmember.hop_limit,
@@ -258,17 +258,8 @@ static int ipoib_mcast_join_finish(struct ipoib_mcast *mcast,
                                .traffic_class = mcast->mcmember.traffic_class
                        }
                };
-               int path_rate = ib_sa_rate_enum_to_int(mcast->mcmember.rate);
-
                av.grh.dgid = mcast->mcmember.mgid;
 
-               if (path_rate > 0 && priv->local_rate > path_rate)
-                       av.static_rate = (priv->local_rate - 1) / path_rate;
-
-               ipoib_dbg_mcast(priv, "static_rate %d for local port %dX, mcmember %dX\n",
-                               av.static_rate, priv->local_rate,
-                               ib_sa_rate_enum_to_int(mcast->mcmember.rate));
-
                ah = ipoib_create_ah(dev, priv->pd, &av);
                if (!ah) {
                        ipoib_warn(priv, "ib_address_create failed\n");
@@ -618,6 +609,22 @@ int ipoib_mcast_start_thread(struct net_device *dev)
        return 0;
 }
 
+static void wait_for_mcast_join(struct ipoib_dev_priv *priv,
+                               struct ipoib_mcast *mcast)
+{
+       spin_lock_irq(&priv->lock);
+       if (mcast && mcast->query) {
+               ib_sa_cancel_query(mcast->query_id, mcast->query);
+               mcast->query = NULL;
+               spin_unlock_irq(&priv->lock);
+               ipoib_dbg_mcast(priv, "waiting for MGID " IPOIB_GID_FMT "\n",
+                               IPOIB_GID_ARG(mcast->mcmember.mgid));
+               wait_for_completion(&mcast->done);
+       }
+       else
+               spin_unlock_irq(&priv->lock);
+}
+
 int ipoib_mcast_stop_thread(struct net_device *dev, int flush)
 {
        struct ipoib_dev_priv *priv = netdev_priv(dev);
@@ -637,28 +644,10 @@ int ipoib_mcast_stop_thread(struct net_device *dev, int flush)
        if (flush)
                flush_workqueue(ipoib_workqueue);
 
-       spin_lock_irq(&priv->lock);
-       if (priv->broadcast && priv->broadcast->query) {
-               ib_sa_cancel_query(priv->broadcast->query_id, priv->broadcast->query);
-               priv->broadcast->query = NULL;
-               spin_unlock_irq(&priv->lock);
-               ipoib_dbg_mcast(priv, "waiting for bcast\n");
-               wait_for_completion(&priv->broadcast->done);
-       } else
-               spin_unlock_irq(&priv->lock);
+       wait_for_mcast_join(priv, priv->broadcast);
 
-       list_for_each_entry(mcast, &priv->multicast_list, list) {
-               spin_lock_irq(&priv->lock);
-               if (mcast->query) {
-                       ib_sa_cancel_query(mcast->query_id, mcast->query);
-                       mcast->query = NULL;
-                       spin_unlock_irq(&priv->lock);
-                       ipoib_dbg_mcast(priv, "waiting for MGID " IPOIB_GID_FMT "\n",
-                                       IPOIB_GID_ARG(mcast->mcmember.mgid));
-                       wait_for_completion(&mcast->done);
-               } else
-                       spin_unlock_irq(&priv->lock);
-       }
+       list_for_each_entry(mcast, &priv->multicast_list, list)
+               wait_for_mcast_join(priv, mcast);
 
        return 0;
 }
@@ -772,13 +761,11 @@ out:
                if (skb->dst            &&
                    skb->dst->neighbour &&
                    !*to_ipoib_neigh(skb->dst->neighbour)) {
-                       struct ipoib_neigh *neigh = kmalloc(sizeof *neigh, GFP_ATOMIC);
+                       struct ipoib_neigh *neigh = ipoib_neigh_alloc(skb->dst->neighbour);
 
                        if (neigh) {
                                kref_get(&mcast->ah->ref);
                                neigh->ah       = mcast->ah;
-                               neigh->neighbour = skb->dst->neighbour;
-                               *to_ipoib_neigh(skb->dst->neighbour) = neigh;
                                list_add_tail(&neigh->list, &mcast->neigh_list);
                        }
                }
@@ -913,6 +900,7 @@ void ipoib_mcast_restart_task(void *dev_ptr)
 
        /* We have to cancel outside of the spinlock */
        list_for_each_entry_safe(mcast, tmcast, &remove_list, list) {
+               wait_for_mcast_join(priv, mcast);
                ipoib_mcast_leave(mcast->dev, mcast);
                ipoib_mcast_free(mcast);
        }
index 5f0388027b2579bda2734a646cbf541348a57071..1d49d1643c5943246961a02c60b5acce7d8cd8f3 100644 (file)
@@ -159,8 +159,8 @@ int ipoib_transport_dev_init(struct net_device *dev, struct ib_device *ca)
        struct ipoib_dev_priv *priv = netdev_priv(dev);
        struct ib_qp_init_attr init_attr = {
                .cap = {
-                       .max_send_wr  = IPOIB_TX_RING_SIZE,
-                       .max_recv_wr  = IPOIB_RX_RING_SIZE,
+                       .max_send_wr  = ipoib_sendq_size,
+                       .max_recv_wr  = ipoib_recvq_size,
                        .max_send_sge = 1,
                        .max_recv_sge = 1
                },
@@ -175,7 +175,7 @@ int ipoib_transport_dev_init(struct net_device *dev, struct ib_device *ca)
        }
 
        priv->cq = ib_create_cq(priv->ca, ipoib_ib_completion, NULL, dev,
-                               IPOIB_TX_RING_SIZE + IPOIB_RX_RING_SIZE + 1);
+                               ipoib_sendq_size + ipoib_recvq_size + 1);
        if (IS_ERR(priv->cq)) {
                printk(KERN_WARNING "%s: failed to create CQ\n", ca->name);
                goto out_free_pd;
index fd8a95a9c5d3e6f26e9927df9f8a53ea8ce06ab6..5bb55742ada68d34249d11ae9390150b30e078f5 100644 (file)
@@ -617,6 +617,14 @@ static void srp_unmap_data(struct scsi_cmnd *scmnd,
                     scmnd->sc_data_direction);
 }
 
+static void srp_remove_req(struct srp_target_port *target, struct srp_request *req,
+                          int index)
+{
+       list_del(&req->list);
+       req->next = target->req_head;
+       target->req_head = index;
+}
+
 static void srp_process_rsp(struct srp_target_port *target, struct srp_rsp *rsp)
 {
        struct srp_request *req;
@@ -664,9 +672,7 @@ static void srp_process_rsp(struct srp_target_port *target, struct srp_rsp *rsp)
                        scmnd->host_scribble = (void *) -1L;
                        scmnd->scsi_done(scmnd);
 
-                       list_del(&req->list);
-                       req->next = target->req_head;
-                       target->req_head = rsp->tag & ~SRP_TAG_TSK_MGMT;
+                       srp_remove_req(target, req, rsp->tag & ~SRP_TAG_TSK_MGMT);
                } else
                        req->cmd_done = 1;
        }
@@ -1188,12 +1194,10 @@ static int srp_send_tsk_mgmt(struct scsi_cmnd *scmnd, u8 func)
        spin_lock_irq(target->scsi_host->host_lock);
 
        if (req->cmd_done) {
-               list_del(&req->list);
-               req->next = target->req_head;
-               target->req_head = req_index;
-
+               srp_remove_req(target, req, req_index);
                scmnd->scsi_done(scmnd);
        } else if (!req->tsk_status) {
+               srp_remove_req(target, req, req_index);
                scmnd->result = DID_ABORT << 16;
                ret = SUCCESS;
        }
@@ -1434,6 +1438,7 @@ static int srp_parse_options(const char *buf, struct srp_target_port *target)
                        p = match_strdup(args);
                        if (strlen(p) != 32) {
                                printk(KERN_WARNING PFX "bad dest GID parameter '%s'\n", p);
+                               kfree(p);
                                goto out;
                        }
 
index 53c4fb62ed855cf69ea3c9244e6727368eca1379..5b203fe21dcd5033c5e6edcedc90daeb619b2bd4 100644 (file)
@@ -3,8 +3,8 @@ menu "Siemens Gigaset"
 
 config ISDN_DRV_GIGASET
        tristate "Siemens Gigaset support (isdn)"
-       depends on ISDN_I4L && m
-#      depends on ISDN_I4L && MODULES
+       depends on ISDN_I4L
+       select CRC_CCITT
        help
          Say m here if you have a Gigaset or Sinus isdn device.
 
index 171f8b703d61da5c4a8ebdd684f98453be00cfae..ce3cd77094b334f8e362ca67404c8ab1baa2ffbd 100644 (file)
@@ -3,7 +3,7 @@
  *
  * Copyright (c) 2005 by Tilman Schmidt <tilman@imap.cc>,
  *                       Hansjoerg Lipp <hjlipp@web.de>,
- *                       Stefan Eilers <Eilers.Stefan@epost.de>.
+ *                       Stefan Eilers.
  *
  * =====================================================================
  *     This program is free software; you can redistribute it and/or
  *     published by the Free Software Foundation; either version 2 of
  *     the License, or (at your option) any later version.
  * =====================================================================
- * ToDo: ...
- * =====================================================================
- * Version: $Id: asyncdata.c,v 1.2.2.7 2005/11/13 23:05:18 hjlipp Exp $
- * =====================================================================
  */
 
 #include "gigaset.h"
@@ -45,7 +41,7 @@ static inline int muststuff(unsigned char c)
  *     number of processed bytes
  */
 static inline int cmd_loop(unsigned char c, unsigned char *src, int numbytes,
-                           struct inbuf_t *inbuf)
+                          struct inbuf_t *inbuf)
 {
        struct cardstate *cs = inbuf->cs;
        unsigned cbytes      = cs->cbytes;
@@ -55,10 +51,11 @@ static inline int cmd_loop(unsigned char c, unsigned char *src, int numbytes,
        for (;;) {
                cs->respdata[cbytes] = c;
                if (c == 10 || c == 13) {
-                       dbg(DEBUG_TRANSCMD, "%s: End of Command (%d Bytes)",
-                           __func__, cbytes);
+                       gig_dbg(DEBUG_TRANSCMD, "%s: End of Command (%d Bytes)",
+                               __func__, cbytes);
                        cs->cbytes = cbytes;
-                       gigaset_handle_modem_response(cs); /* can change cs->dle */
+                       gigaset_handle_modem_response(cs); /* can change
+                                                             cs->dle */
                        cbytes = 0;
 
                        if (cs->dle &&
@@ -71,7 +68,7 @@ static inline int cmd_loop(unsigned char c, unsigned char *src, int numbytes,
                        if (cbytes < MAX_RESP_SIZE - 1)
                                cbytes++;
                        else
-                               warn("response too large");
+                               dev_warn(cs->dev, "response too large\n");
                }
 
                if (!numbytes)
@@ -96,11 +93,12 @@ static inline int cmd_loop(unsigned char c, unsigned char *src, int numbytes,
  *     number of processed bytes
  */
 static inline int lock_loop(unsigned char *src, int numbytes,
-                            struct inbuf_t *inbuf)
+                           struct inbuf_t *inbuf)
 {
        struct cardstate *cs = inbuf->cs;
 
-       gigaset_dbg_buffer(DEBUG_LOCKCMD, "received response", numbytes, src, 0);
+       gigaset_dbg_buffer(DEBUG_LOCKCMD, "received response",
+                          numbytes, src);
        gigaset_if_receive(cs, src, numbytes);
 
        return numbytes;
@@ -115,24 +113,18 @@ static inline int lock_loop(unsigned char *src, int numbytes,
  *     numbytes (all bytes processed) on error --FIXME
  */
 static inline int hdlc_loop(unsigned char c, unsigned char *src, int numbytes,
-                            struct inbuf_t *inbuf)
+                           struct inbuf_t *inbuf)
 {
        struct cardstate *cs = inbuf->cs;
        struct bc_state *bcs = inbuf->bcs;
-       int inputstate;
-       __u16 fcs;
-       struct sk_buff *skb;
+       int inputstate = bcs->inputstate;
+       __u16 fcs = bcs->fcs;
+       struct sk_buff *skb = bcs->skb;
        unsigned char error;
        struct sk_buff *compskb;
        int startbytes = numbytes;
        int l;
 
-       IFNULLRETVAL(bcs, numbytes);
-       inputstate = bcs->inputstate;
-       fcs = bcs->fcs;
-       skb = bcs->skb;
-       IFNULLRETVAL(skb, numbytes);
-
        if (unlikely(inputstate & INS_byte_stuff)) {
                inputstate &= ~INS_byte_stuff;
                goto byte_stuff;
@@ -156,39 +148,37 @@ byte_stuff:
                        c ^= PPP_TRANS;
 #ifdef CONFIG_GIGASET_DEBUG
                        if (unlikely(!muststuff(c)))
-                               dbg(DEBUG_HDLC,
-                                   "byte stuffed: 0x%02x", c);
+                               gig_dbg(DEBUG_HDLC, "byte stuffed: 0x%02x", c);
 #endif
                } else if (unlikely(c == PPP_FLAG)) {
                        if (unlikely(inputstate & INS_skip_frame)) {
                                if (!(inputstate & INS_have_data)) { /* 7E 7E */
-                                       //dbg(DEBUG_HDLC, "(7e)7e------------------------");
 #ifdef CONFIG_GIGASET_DEBUG
                                        ++bcs->emptycount;
 #endif
                                } else
-                                       dbg(DEBUG_HDLC,
+                                       gig_dbg(DEBUG_HDLC,
                                            "7e----------------------------");
 
                                /* end of frame */
                                error = 1;
                                gigaset_rcv_error(NULL, cs, bcs);
                        } else if (!(inputstate & INS_have_data)) { /* 7E 7E */
-                               //dbg(DEBUG_HDLC, "(7e)7e------------------------");
 #ifdef CONFIG_GIGASET_DEBUG
                                ++bcs->emptycount;
 #endif
                                break;
                        } else {
-                               dbg(DEBUG_HDLC,
-                                   "7e----------------------------");
+                               gig_dbg(DEBUG_HDLC,
+                                       "7e----------------------------");
 
                                /* end of frame */
                                error = 0;
 
                                if (unlikely(fcs != PPP_GOODFCS)) {
-                                       err("Packet checksum at %lu failed, "
-                                           "packet is corrupted (%u bytes)!",
+                                       dev_err(cs->dev,
+                                           "Packet checksum at %lu failed, "
+                                           "packet is corrupted (%u bytes)!\n",
                                            bcs->rcvbytes, skb->len);
                                        compskb = NULL;
                                        gigaset_rcv_error(compskb, cs, bcs);
@@ -202,9 +192,11 @@ byte_stuff:
                                                skb = NULL;
                                                inputstate |= INS_skip_frame;
                                                if (l == 1) {
-                                                       err("invalid packet size (1)!");
+                                                       dev_err(cs->dev,
+                                                 "invalid packet size (1)!\n");
                                                        error = 1;
-                                                       gigaset_rcv_error(NULL, cs, bcs);
+                                                       gigaset_rcv_error(NULL,
+                                                               cs, bcs);
                                                }
                                        }
                                        if (likely(!(error ||
@@ -227,7 +219,8 @@ byte_stuff:
                        } else if (likely((skb = dev_alloc_skb(SBUFSIZE + HW_HDR_LEN)) != NULL)) {
                                skb_reserve(skb, HW_HDR_LEN);
                        } else {
-                               warn("could not allocate new skb");
+                               dev_warn(cs->dev,
+                                        "could not allocate new skb\n");
                                inputstate |= INS_skip_frame;
                        }
 
@@ -235,7 +228,7 @@ byte_stuff:
 #ifdef CONFIG_GIGASET_DEBUG
                } else if (unlikely(muststuff(c))) {
                        /* Should not happen. Possible after ZDLE=1<CR><LF>. */
-                       dbg(DEBUG_HDLC, "not byte stuffed: 0x%02x", c);
+                       gig_dbg(DEBUG_HDLC, "not byte stuffed: 0x%02x", c);
 #endif
                }
 
@@ -243,8 +236,8 @@ byte_stuff:
 
 #ifdef CONFIG_GIGASET_DEBUG
                if (unlikely(!(inputstate & INS_have_data))) {
-                       dbg(DEBUG_HDLC,
-                           "7e (%d x) ================", bcs->emptycount);
+                       gig_dbg(DEBUG_HDLC, "7e (%d x) ================",
+                               bcs->emptycount);
                        bcs->emptycount = 0;
                }
 #endif
@@ -253,14 +246,13 @@ byte_stuff:
 
                if (likely(!(inputstate & INS_skip_frame))) {
                        if (unlikely(skb->len == SBUFSIZE)) {
-                               warn("received packet too long");
+                               dev_warn(cs->dev, "received packet too long\n");
                                dev_kfree_skb_any(skb);
                                skb = NULL;
                                inputstate |= INS_skip_frame;
                                break;
                        }
-                       *gigaset_skb_put_quick(skb, 1) = c;
-                       /* *__skb_put (skb, 1) = c; */
+                       *__skb_put(skb, 1) = c;
                        fcs = crc_ccitt_byte(fcs, c);
                }
 
@@ -289,19 +281,14 @@ byte_stuff:
  *     numbytes (all bytes processed) on error --FIXME
  */
 static inline int iraw_loop(unsigned char c, unsigned char *src, int numbytes,
-                            struct inbuf_t *inbuf)
+                           struct inbuf_t *inbuf)
 {
        struct cardstate *cs = inbuf->cs;
        struct bc_state *bcs = inbuf->bcs;
-       int inputstate;
-       struct sk_buff *skb;
+       int inputstate = bcs->inputstate;
+       struct sk_buff *skb = bcs->skb;
        int startbytes = numbytes;
 
-       IFNULLRETVAL(bcs, numbytes);
-       inputstate = bcs->inputstate;
-       skb = bcs->skb;
-       IFNULLRETVAL(skb, numbytes);
-
        for (;;) {
                /* add character */
                inputstate |= INS_have_data;
@@ -309,13 +296,13 @@ static inline int iraw_loop(unsigned char c, unsigned char *src, int numbytes,
                if (likely(!(inputstate & INS_skip_frame))) {
                        if (unlikely(skb->len == SBUFSIZE)) {
                                //FIXME just pass skb up and allocate a new one
-                               warn("received packet too long");
+                               dev_warn(cs->dev, "received packet too long\n");
                                dev_kfree_skb_any(skb);
                                skb = NULL;
                                inputstate |= INS_skip_frame;
                                break;
                        }
-                       *gigaset_skb_put_quick(skb, 1) = gigaset_invtab[c];
+                       *__skb_put(skb, 1) = gigaset_invtab[c];
                }
 
                if (unlikely(!numbytes))
@@ -343,7 +330,7 @@ static inline int iraw_loop(unsigned char c, unsigned char *src, int numbytes,
                                  != NULL)) {
                        skb_reserve(skb, HW_HDR_LEN);
                } else {
-                       warn("could not allocate new skb");
+                       dev_warn(cs->dev, "could not allocate new skb\n");
                        inputstate |= INS_skip_frame;
                }
        }
@@ -364,13 +351,13 @@ void gigaset_m10x_input(struct inbuf_t *inbuf)
 
        head = atomic_read(&inbuf->head);
        tail = atomic_read(&inbuf->tail);
-       dbg(DEBUG_INTR, "buffer state: %u -> %u", head, tail);
+       gig_dbg(DEBUG_INTR, "buffer state: %u -> %u", head, tail);
 
        if (head != tail) {
                cs = inbuf->cs;
                src = inbuf->data + head;
                numbytes = (head > tail ? RBUFSIZE : tail) - head;
-               dbg(DEBUG_INTR, "processing %u bytes", numbytes);
+               gig_dbg(DEBUG_INTR, "processing %u bytes", numbytes);
 
                while (numbytes) {
                        if (atomic_read(&cs->mstate) == MS_LOCKED) {
@@ -392,8 +379,7 @@ void gigaset_m10x_input(struct inbuf_t *inbuf)
 
                                if (!(inbuf->inputstate & INS_DLE_char)) {
 
-                                       /* FIXME Einfach je nach Modus Funktionszeiger in cs setzen [hier+hdlc_loop]?  */
-                                       /* FIXME Spart folgendes "if" und ermoeglicht andere Protokolle */
+                                       /* FIXME use function pointers?  */
                                        if (inbuf->inputstate & INS_command)
                                                procbytes = cmd_loop(c, src, numbytes, inbuf);
                                        else if (inbuf->bcs->proto2 == ISDN_PROTO_L2_HDLC)
@@ -403,13 +389,14 @@ void gigaset_m10x_input(struct inbuf_t *inbuf)
 
                                        src += procbytes;
                                        numbytes -= procbytes;
-                               } else {  /* DLE-char */
+                               } else {  /* DLE char */
                                        inbuf->inputstate &= ~INS_DLE_char;
                                        switch (c) {
                                        case 'X': /*begin of command*/
 #ifdef CONFIG_GIGASET_DEBUG
                                                if (inbuf->inputstate & INS_command)
-                                                       err("received <DLE> 'X' in command mode");
+                                                       dev_err(cs->dev,
+                                       "received <DLE> 'X' in command mode\n");
 #endif
                                                inbuf->inputstate |=
                                                        INS_command | INS_DLE_command;
@@ -417,7 +404,8 @@ void gigaset_m10x_input(struct inbuf_t *inbuf)
                                        case '.': /*end of command*/
 #ifdef CONFIG_GIGASET_DEBUG
                                                if (!(inbuf->inputstate & INS_command))
-                                                       err("received <DLE> '.' in hdlc mode");
+                                                       dev_err(cs->dev,
+                                       "received <DLE> '.' in hdlc mode\n");
 #endif
                                                inbuf->inputstate &= cs->dle ?
                                                        ~(INS_DLE_command|INS_command)
@@ -425,7 +413,9 @@ void gigaset_m10x_input(struct inbuf_t *inbuf)
                                                break;
                                        //case DLE_FLAG: /*DLE_FLAG in data stream*/ /* schon oben behandelt! */
                                        default:
-                                               err("received 0x10 0x%02x!", (int) c);
+                                               dev_err(cs->dev,
+                                                     "received 0x10 0x%02x!\n",
+                                                       (int) c);
                                                /* FIXME: reset driver?? */
                                        }
                                }
@@ -444,7 +434,7 @@ nextbyte:
                        }
                }
 
-               dbg(DEBUG_INTR, "setting head to %u", head);
+               gig_dbg(DEBUG_INTR, "setting head to %u", head);
                atomic_set(&inbuf->head, head);
        }
 }
@@ -479,14 +469,13 @@ static struct sk_buff *HDLC_Encode(struct sk_buff *skb, int head, int tail)
                        stuf_cnt++;
                fcs = crc_ccitt_byte(fcs, *cp++);
        }
-       fcs ^= 0xffff;                 /* complement */
+       fcs ^= 0xffff;                  /* complement */
 
        /* size of new buffer: original size + number of stuffing bytes
         * + 2 bytes FCS + 2 stuffing bytes for FCS (if needed) + 2 flag bytes
         */
        hdlc_skb = dev_alloc_skb(skb->len + stuf_cnt + 6 + tail + head);
        if (!hdlc_skb) {
-               err("unable to allocate memory for HDLC encoding!");
                dev_kfree_skb(skb);
                return NULL;
        }
@@ -508,7 +497,7 @@ static struct sk_buff *HDLC_Encode(struct sk_buff *skb, int head, int tail)
        }
 
        /* Finally add FCS (byte stuffed) and flag sequence */
-       c = (fcs & 0x00ff);      /* least significant byte first */
+       c = (fcs & 0x00ff);     /* least significant byte first */
        if (muststuff(c)) {
                *(skb_put(hdlc_skb, 1)) = PPP_ESCAPE;
                c ^= PPP_TRANS;
@@ -546,7 +535,6 @@ static struct sk_buff *iraw_encode(struct sk_buff *skb, int head, int tail)
        /* worst case: every byte must be stuffed */
        iraw_skb = dev_alloc_skb(2*skb->len + tail + head);
        if (!iraw_skb) {
-               err("unable to allocate memory for HDLC encoding!");
                dev_kfree_skb(skb);
                return NULL;
        }
@@ -577,21 +565,23 @@ static struct sk_buff *iraw_encode(struct sk_buff *skb, int head, int tail)
  */
 int gigaset_m10x_send_skb(struct bc_state *bcs, struct sk_buff *skb)
 {
-       unsigned len;
-
-       IFNULLRETVAL(bcs, -EFAULT);
-       IFNULLRETVAL(skb, -EFAULT);
-       len = skb->len;
+       unsigned len = skb->len;
+       unsigned long flags;
 
        if (bcs->proto2 == ISDN_PROTO_L2_HDLC)
                skb = HDLC_Encode(skb, HW_HDR_LEN, 0);
        else
                skb = iraw_encode(skb, HW_HDR_LEN, 0);
-       if (!skb)
+       if (!skb) {
+               err("unable to allocate memory for encoding!\n");
                return -ENOMEM;
+       }
 
        skb_queue_tail(&bcs->squeue, skb);
-       tasklet_schedule(&bcs->cs->write_tasklet);
+       spin_lock_irqsave(&bcs->cs->lock, flags);
+       if (bcs->cs->connected)
+               tasklet_schedule(&bcs->cs->write_tasklet);
+       spin_unlock_irqrestore(&bcs->cs->lock, flags);
 
        return len;     /* ok so far */
 }
index 31f0f07832bc4bbd12a4ea521a697190af307530..f86ed6af3aa2d5fb68575cd4a78c2fb8082034ba 100644 (file)
@@ -3,7 +3,7 @@
  *
  * Copyright (c) 2001 by Hansjoerg Lipp <hjlipp@web.de>,
  *                       Tilman Schmidt <tilman@imap.cc>,
- *                       Stefan Eilers <Eilers.Stefan@epost.de>.
+ *                       Stefan Eilers.
  *
  * Based on usb-gigaset.c.
  *
  *     published by the Free Software Foundation; either version 2 of
  *     the License, or (at your option) any later version.
  * =====================================================================
- * ToDo: ...
- * =====================================================================
- * Version: $Id: bas-gigaset.c,v 1.52.4.19 2006/02/04 18:28:16 hjlipp Exp $
- * =====================================================================
  */
 
 #include "gigaset.h"
@@ -30,7 +26,7 @@
 #include <linux/moduleparam.h>
 
 /* Version Information */
-#define DRIVER_AUTHOR "Tilman Schmidt <tilman@imap.cc>, Hansjoerg Lipp <hjlipp@web.de>, Stefan Eilers <Eilers.Stefan@epost.de>"
+#define DRIVER_AUTHOR "Tilman Schmidt <tilman@imap.cc>, Hansjoerg Lipp <hjlipp@web.de>, Stefan Eilers"
 #define DRIVER_DESC "USB Driver for Gigaset 307x"
 
 
@@ -70,9 +66,6 @@ static struct usb_device_id gigaset_table [] = {
 
 MODULE_DEVICE_TABLE(usb, gigaset_table);
 
-/* Get a minor range for your devices from the usb maintainer */
-#define USB_SKEL_MINOR_BASE    200
-
 /*======================= local function prototypes =============================*/
 
 /* This function is called if a new device is connected to the USB port. It
@@ -88,25 +81,25 @@ static void gigaset_disconnect(struct usb_interface *interface);
 /*==============================================================================*/
 
 struct bas_cardstate {
-       struct usb_device       *udev;          /* USB device pointer */
-       struct usb_interface    *interface;     /* interface for this device */
+       struct usb_device       *udev;          /* USB device pointer */
+       struct usb_interface    *interface;     /* interface for this device */
        unsigned char           minor;          /* starting minor number */
 
-       struct urb              *urb_ctrl;      /* control pipe default URB */
+       struct urb              *urb_ctrl;      /* control pipe default URB */
        struct usb_ctrlrequest  dr_ctrl;
        struct timer_list       timer_ctrl;     /* control request timeout */
 
        struct timer_list       timer_atrdy;    /* AT command ready timeout */
-       struct urb              *urb_cmd_out;   /* for sending AT commands */
+       struct urb              *urb_cmd_out;   /* for sending AT commands */
        struct usb_ctrlrequest  dr_cmd_out;
        int                     retry_cmd_out;
 
-       struct urb              *urb_cmd_in;    /* for receiving AT replies */
+       struct urb              *urb_cmd_in;    /* for receiving AT replies */
        struct usb_ctrlrequest  dr_cmd_in;
        struct timer_list       timer_cmd_in;   /* receive request timeout */
-       unsigned char           *rcvbuf;        /* AT reply receive buffer */
+       unsigned char           *rcvbuf;        /* AT reply receive buffer */
 
-       struct urb              *urb_int_in;    /* URB for interrupt pipe */
+       struct urb              *urb_int_in;    /* URB for interrupt pipe */
        unsigned char           int_in_buf[3];
 
        spinlock_t              lock;           /* locks all following */
@@ -208,53 +201,54 @@ static inline char *usb_pipetype_str(int pipe)
  * write content of URB to syslog for debugging
  */
 static inline void dump_urb(enum debuglevel level, const char *tag,
-                            struct urb *urb)
+                           struct urb *urb)
 {
 #ifdef CONFIG_GIGASET_DEBUG
        int i;
-       IFNULLRET(tag);
-       dbg(level, "%s urb(0x%08lx)->{", tag, (unsigned long) urb);
+       gig_dbg(level, "%s urb(0x%08lx)->{", tag, (unsigned long) urb);
        if (urb) {
-               dbg(level,
-                   "  dev=0x%08lx, pipe=%s:EP%d/DV%d:%s, "
-                   "status=%d, hcpriv=0x%08lx, transfer_flags=0x%x,",
-                   (unsigned long) urb->dev,
-                   usb_pipetype_str(urb->pipe),
-                   usb_pipeendpoint(urb->pipe), usb_pipedevice(urb->pipe),
-                   usb_pipein(urb->pipe) ? "in" : "out",
-                   urb->status, (unsigned long) urb->hcpriv,
-                   urb->transfer_flags);
-               dbg(level,
-                   "  transfer_buffer=0x%08lx[%d], actual_length=%d, "
-                   "bandwidth=%d, setup_packet=0x%08lx,",
-                   (unsigned long) urb->transfer_buffer,
-                   urb->transfer_buffer_length, urb->actual_length,
-                   urb->bandwidth, (unsigned long) urb->setup_packet);
-               dbg(level,
-                   "  start_frame=%d, number_of_packets=%d, interval=%d, "
-                   "error_count=%d,",
-                   urb->start_frame, urb->number_of_packets, urb->interval,
-                   urb->error_count);
-               dbg(level,
-                   "  context=0x%08lx, complete=0x%08lx, iso_frame_desc[]={",
-                   (unsigned long) urb->context,
-                   (unsigned long) urb->complete);
+               gig_dbg(level,
+                       "  dev=0x%08lx, pipe=%s:EP%d/DV%d:%s, "
+                       "status=%d, hcpriv=0x%08lx, transfer_flags=0x%x,",
+                       (unsigned long) urb->dev,
+                       usb_pipetype_str(urb->pipe),
+                       usb_pipeendpoint(urb->pipe), usb_pipedevice(urb->pipe),
+                       usb_pipein(urb->pipe) ? "in" : "out",
+                       urb->status, (unsigned long) urb->hcpriv,
+                       urb->transfer_flags);
+               gig_dbg(level,
+                       "  transfer_buffer=0x%08lx[%d], actual_length=%d, "
+                       "bandwidth=%d, setup_packet=0x%08lx,",
+                       (unsigned long) urb->transfer_buffer,
+                       urb->transfer_buffer_length, urb->actual_length,
+                       urb->bandwidth, (unsigned long) urb->setup_packet);
+               gig_dbg(level,
+                       "  start_frame=%d, number_of_packets=%d, interval=%d, "
+                       "error_count=%d,",
+                       urb->start_frame, urb->number_of_packets, urb->interval,
+                       urb->error_count);
+               gig_dbg(level,
+                       "  context=0x%08lx, complete=0x%08lx, "
+                       "iso_frame_desc[]={",
+                       (unsigned long) urb->context,
+                       (unsigned long) urb->complete);
                for (i = 0; i < urb->number_of_packets; i++) {
-                       struct usb_iso_packet_descriptor *pifd = &urb->iso_frame_desc[i];
-                       dbg(level,
-                           "    {offset=%u, length=%u, actual_length=%u, "
-                           "status=%u}",
-                           pifd->offset, pifd->length, pifd->actual_length,
-                           pifd->status);
+                       struct usb_iso_packet_descriptor *pifd
+                               = &urb->iso_frame_desc[i];
+                       gig_dbg(level,
+                               "    {offset=%u, length=%u, actual_length=%u, "
+                               "status=%u}",
+                               pifd->offset, pifd->length, pifd->actual_length,
+                               pifd->status);
                }
        }
-       dbg(level, "}}");
+       gig_dbg(level, "}}");
 #endif
 }
 
 /* read/set modem control bits etc. (m10x only) */
 static int gigaset_set_modem_ctrl(struct cardstate *cs, unsigned old_state,
-                                  unsigned new_state)
+                                 unsigned new_state)
 {
        return -EINVAL;
 }
@@ -280,8 +274,8 @@ static inline void error_hangup(struct bc_state *bcs)
 {
        struct cardstate *cs = bcs->cs;
 
-       dbg(DEBUG_ANY,
-           "%s: scheduling HUP for channel %d", __func__, bcs->channel);
+       gig_dbg(DEBUG_ANY, "%s: scheduling HUP for channel %d",
+               __func__, bcs->channel);
 
        if (!gigaset_add_event(cs, &bcs->at_state, EV_HUP, NULL, 0, NULL)) {
                //FIXME what should we do?
@@ -301,22 +295,19 @@ static inline void error_hangup(struct bc_state *bcs)
 static inline void error_reset(struct cardstate *cs)
 {
        //FIXME try to recover without bothering the user
-       err("unrecoverable error - please disconnect the Gigaset base to reset");
+       dev_err(cs->dev,
+           "unrecoverable error - please disconnect Gigaset base to reset\n");
 }
 
 /* check_pending
  * check for completion of pending control request
  * parameter:
- *     urb     USB request block of completed request
- *             urb->context = hardware specific controller state structure
+ *     ucs     hardware specific controller state structure
  */
 static void check_pending(struct bas_cardstate *ucs)
 {
        unsigned long flags;
 
-       IFNULLRET(ucs);
-       IFNULLRET(cardstate);
-
        spin_lock_irqsave(&ucs->lock, flags);
        switch (ucs->pending) {
        case 0:
@@ -336,8 +327,6 @@ static void check_pending(struct bas_cardstate *ucs)
        case HD_CLOSE_ATCHANNEL:
                if (!(atomic_read(&ucs->basstate) & BS_ATOPEN))
                        ucs->pending = 0;
-               //wake_up_interruptible(cs->initwait);
-               //FIXME need own wait queue?
                break;
        case HD_CLOSE_B1CHANNEL:
                if (!(atomic_read(&ucs->basstate) & BS_B1OPEN))
@@ -354,7 +343,9 @@ static void check_pending(struct bas_cardstate *ucs)
         * are handled separately and should never end up here
         */
        default:
-               warn("unknown pending request 0x%02x cleared", ucs->pending);
+               dev_warn(&ucs->interface->dev,
+                        "unknown pending request 0x%02x cleared\n",
+                        ucs->pending);
                ucs->pending = 0;
        }
 
@@ -372,27 +363,23 @@ static void check_pending(struct bas_cardstate *ucs)
 static void cmd_in_timeout(unsigned long data)
 {
        struct cardstate *cs = (struct cardstate *) data;
-       struct bas_cardstate *ucs;
+       struct bas_cardstate *ucs = cs->hw.bas;
        unsigned long flags;
 
-       IFNULLRET(cs);
-       ucs = cs->hw.bas;
-       IFNULLRET(ucs);
-
        spin_lock_irqsave(&cs->lock, flags);
-       if (!atomic_read(&cs->connected)) {
-               dbg(DEBUG_USBREQ, "%s: disconnected", __func__);
+       if (unlikely(!cs->connected)) {
+               gig_dbg(DEBUG_USBREQ, "%s: disconnected", __func__);
                spin_unlock_irqrestore(&cs->lock, flags);
                return;
        }
        if (!ucs->rcvbuf_size) {
-               dbg(DEBUG_USBREQ, "%s: no receive in progress", __func__);
+               gig_dbg(DEBUG_USBREQ, "%s: no receive in progress", __func__);
                spin_unlock_irqrestore(&cs->lock, flags);
                return;
        }
        spin_unlock_irqrestore(&cs->lock, flags);
 
-       err("timeout reading AT response");
+       dev_err(cs->dev, "timeout reading AT response\n");
        error_reset(cs);        //FIXME retry?
 }
 
@@ -412,18 +399,15 @@ static void read_ctrl_callback(struct urb *urb, struct pt_regs *regs);
  */
 static int atread_submit(struct cardstate *cs, int timeout)
 {
-       struct bas_cardstate *ucs;
+       struct bas_cardstate *ucs = cs->hw.bas;
        int ret;
 
-       IFNULLRETVAL(cs, -EINVAL);
-       ucs = cs->hw.bas;
-       IFNULLRETVAL(ucs, -EINVAL);
-       IFNULLRETVAL(ucs->urb_cmd_in, -EINVAL);
-
-       dbg(DEBUG_USBREQ, "-------> HD_READ_ATMESSAGE (%d)", ucs->rcvbuf_size);
+       gig_dbg(DEBUG_USBREQ, "-------> HD_READ_ATMESSAGE (%d)",
+               ucs->rcvbuf_size);
 
        if (ucs->urb_cmd_in->status == -EINPROGRESS) {
-               err("could not submit HD_READ_ATMESSAGE: URB busy");
+               dev_err(cs->dev,
+                       "could not submit HD_READ_ATMESSAGE: URB busy\n");
                return -EBUSY;
        }
 
@@ -433,19 +417,19 @@ static int atread_submit(struct cardstate *cs, int timeout)
        ucs->dr_cmd_in.wIndex = 0;
        ucs->dr_cmd_in.wLength = cpu_to_le16(ucs->rcvbuf_size);
        usb_fill_control_urb(ucs->urb_cmd_in, ucs->udev,
-                            usb_rcvctrlpipe(ucs->udev, 0),
-                            (unsigned char*) & ucs->dr_cmd_in,
-                            ucs->rcvbuf, ucs->rcvbuf_size,
-                            read_ctrl_callback, cs->inbuf);
+                            usb_rcvctrlpipe(ucs->udev, 0),
+                            (unsigned char*) & ucs->dr_cmd_in,
+                            ucs->rcvbuf, ucs->rcvbuf_size,
+                            read_ctrl_callback, cs->inbuf);
 
        if ((ret = usb_submit_urb(ucs->urb_cmd_in, SLAB_ATOMIC)) != 0) {
-               err("could not submit HD_READ_ATMESSAGE: %s",
-                   get_usb_statmsg(ret));
+               dev_err(cs->dev, "could not submit HD_READ_ATMESSAGE: %s\n",
+                       get_usb_statmsg(ret));
                return ret;
        }
 
        if (timeout > 0) {
-               dbg(DEBUG_USBREQ, "setting timeout of %d/10 secs", timeout);
+               gig_dbg(DEBUG_USBREQ, "setting timeout of %d/10 secs", timeout);
                ucs->timer_cmd_in.expires = jiffies + timeout * HZ / 10;
                ucs->timer_cmd_in.data = (unsigned long) cs;
                ucs->timer_cmd_in.function = cmd_in_timeout;
@@ -483,25 +467,14 @@ inline static void update_basstate(struct bas_cardstate *ucs,
  */
 static void read_int_callback(struct urb *urb, struct pt_regs *regs)
 {
-       struct cardstate *cs;
-       struct bas_cardstate *ucs;
+       struct cardstate *cs = urb->context;
+       struct bas_cardstate *ucs = cs->hw.bas;
        struct bc_state *bcs;
        unsigned long flags;
        int status;
        unsigned l;
        int channel;
 
-       IFNULLRET(urb);
-       cs = (struct cardstate *) urb->context;
-       IFNULLRET(cs);
-       ucs = cs->hw.bas;
-       IFNULLRET(ucs);
-
-       if (unlikely(!atomic_read(&cs->connected))) {
-               warn("%s: disconnected", __func__);
-               return;
-       }
-
        switch (urb->status) {
        case 0:                 /* success */
                break;
@@ -509,11 +482,12 @@ static void read_int_callback(struct urb *urb, struct pt_regs *regs)
        case -ECONNRESET:               /* canceled (async) */
        case -EINPROGRESS:              /* pending */
                /* ignore silently */
-               dbg(DEBUG_USBREQ,
-                   "%s: %s", __func__, get_usb_statmsg(urb->status));
+               gig_dbg(DEBUG_USBREQ, "%s: %s",
+                       __func__, get_usb_statmsg(urb->status));
                return;
        default:                /* severe trouble */
-               warn("interrupt read: %s", get_usb_statmsg(urb->status));
+               dev_warn(cs->dev, "interrupt read: %s\n",
+                        get_usb_statmsg(urb->status));
                //FIXME corrective action? resubmission always ok?
                goto resubmit;
        }
@@ -521,10 +495,9 @@ static void read_int_callback(struct urb *urb, struct pt_regs *regs)
        l = (unsigned) ucs->int_in_buf[1] +
            (((unsigned) ucs->int_in_buf[2]) << 8);
 
-       dbg(DEBUG_USBREQ,
-           "<-------%d: 0x%02x (%u [0x%02x 0x%02x])", urb->actual_length,
-           (int)ucs->int_in_buf[0], l,
-           (int)ucs->int_in_buf[1], (int)ucs->int_in_buf[2]);
+       gig_dbg(DEBUG_USBREQ, "<-------%d: 0x%02x (%u [0x%02x 0x%02x])",
+               urb->actual_length, (int)ucs->int_in_buf[0], l,
+               (int)ucs->int_in_buf[1], (int)ucs->int_in_buf[2]);
 
        channel = 0;
 
@@ -570,28 +543,30 @@ static void read_int_callback(struct urb *urb, struct pt_regs *regs)
        case HD_B1_FLOW_CONTROL:
                bcs = cs->bcs + channel;
                atomic_add((l - BAS_NORMFRAME) * BAS_CORRFRAMES,
-                          &bcs->hw.bas->corrbytes);
-               dbg(DEBUG_ISO,
-                   "Flow control (channel %d, sub %d): 0x%02x => %d",
-                   channel, bcs->hw.bas->numsub, l,
-                   atomic_read(&bcs->hw.bas->corrbytes));
+                          &bcs->hw.bas->corrbytes);
+               gig_dbg(DEBUG_ISO,
+                       "Flow control (channel %d, sub %d): 0x%02x => %d",
+                       channel, bcs->hw.bas->numsub, l,
+                       atomic_read(&bcs->hw.bas->corrbytes));
                break;
 
        case HD_RECEIVEATDATA_ACK:      /* AT response ready to be received */
                if (!l) {
-                       warn("HD_RECEIVEATDATA_ACK with length 0 ignored");
+                       dev_warn(cs->dev,
+                               "HD_RECEIVEATDATA_ACK with length 0 ignored\n");
                        break;
                }
                spin_lock_irqsave(&cs->lock, flags);
                if (ucs->rcvbuf_size) {
                        spin_unlock_irqrestore(&cs->lock, flags);
-                       err("receive AT data overrun, %d bytes lost", l);
+                       dev_err(cs->dev,
+                               "receive AT data overrun, %d bytes lost\n", l);
                        error_reset(cs);        //FIXME reschedule
                        break;
                }
                if ((ucs->rcvbuf = kmalloc(l, GFP_ATOMIC)) == NULL) {
                        spin_unlock_irqrestore(&cs->lock, flags);
-                       err("%s: out of memory, %d bytes lost", __func__, l);
+                       dev_err(cs->dev, "out of memory, %d bytes lost\n", l);
                        error_reset(cs);        //FIXME reschedule
                        break;
                }
@@ -607,25 +582,28 @@ static void read_int_callback(struct urb *urb, struct pt_regs *regs)
                break;
 
        case HD_RESET_INTERRUPT_PIPE_ACK:
-               dbg(DEBUG_USBREQ, "HD_RESET_INTERRUPT_PIPE_ACK");
+               gig_dbg(DEBUG_USBREQ, "HD_RESET_INTERRUPT_PIPE_ACK");
                break;
 
        case HD_SUSPEND_END:
-               dbg(DEBUG_USBREQ, "HD_SUSPEND_END");
+               gig_dbg(DEBUG_USBREQ, "HD_SUSPEND_END");
                break;
 
        default:
-               warn("unknown Gigaset signal 0x%02x (%u) ignored",
-                    (int) ucs->int_in_buf[0], l);
+               dev_warn(cs->dev,
+                        "unknown Gigaset signal 0x%02x (%u) ignored\n",
+                        (int) ucs->int_in_buf[0], l);
        }
 
        check_pending(ucs);
 
 resubmit:
-       status = usb_submit_urb(urb, SLAB_ATOMIC);
+       spin_lock_irqsave(&cs->lock, flags);
+       status = cs->connected ? usb_submit_urb(urb, SLAB_ATOMIC) : -ENODEV;
+       spin_unlock_irqrestore(&cs->lock, flags);
        if (unlikely(status)) {
-               err("could not resubmit interrupt URB: %s",
-                   get_usb_statmsg(status));
+               dev_err(cs->dev, "could not resubmit interrupt URB: %s\n",
+                       get_usb_statmsg(status));
                error_reset(cs);
        }
 }
@@ -639,30 +617,22 @@ resubmit:
  */
 static void read_ctrl_callback(struct urb *urb, struct pt_regs *regs)
 {
-       struct cardstate *cs;
-       struct bas_cardstate *ucs;
+       struct inbuf_t *inbuf = urb->context;
+       struct cardstate *cs = inbuf->cs;
+       struct bas_cardstate *ucs = cs->hw.bas;
+       int have_data = 0;
        unsigned numbytes;
        unsigned long flags;
-       struct inbuf_t *inbuf;
-       int have_data = 0;
-
-       IFNULLRET(urb);
-       inbuf = (struct inbuf_t *) urb->context;
-       IFNULLRET(inbuf);
-       cs = inbuf->cs;
-       IFNULLRET(cs);
-       ucs = cs->hw.bas;
-       IFNULLRET(ucs);
 
        spin_lock_irqsave(&cs->lock, flags);
-       if (!atomic_read(&cs->connected)) {
+       if (unlikely(!cs->connected)) {
                warn("%s: disconnected", __func__);
                spin_unlock_irqrestore(&cs->lock, flags);
                return;
        }
 
        if (!ucs->rcvbuf_size) {
-               warn("%s: no receive in progress", __func__);
+               dev_warn(cs->dev, "%s: no receive in progress\n", __func__);
                spin_unlock_irqrestore(&cs->lock, flags);
                return;
        }
@@ -673,12 +643,14 @@ static void read_ctrl_callback(struct urb *urb, struct pt_regs *regs)
        case 0:                         /* normal completion */
                numbytes = urb->actual_length;
                if (unlikely(numbytes == 0)) {
-                       warn("control read: empty block received");
+                       dev_warn(cs->dev,
+                                "control read: empty block received\n");
                        goto retry;
                }
                if (unlikely(numbytes != ucs->rcvbuf_size)) {
-                       warn("control read: received %d chars, expected %d",
-                            numbytes, ucs->rcvbuf_size);
+                       dev_warn(cs->dev,
+                              "control read: received %d chars, expected %d\n",
+                                numbytes, ucs->rcvbuf_size);
                        if (numbytes > ucs->rcvbuf_size)
                                numbytes = ucs->rcvbuf_size;
                }
@@ -698,23 +670,26 @@ static void read_ctrl_callback(struct urb *urb, struct pt_regs *regs)
        case -ECONNRESET:               /* canceled (async) */
        case -EINPROGRESS:              /* pending */
                /* no action necessary */
-               dbg(DEBUG_USBREQ,
-                   "%s: %s", __func__, get_usb_statmsg(urb->status));
+               gig_dbg(DEBUG_USBREQ, "%s: %s",
+                       __func__, get_usb_statmsg(urb->status));
                break;
 
        default:                        /* severe trouble */
-               warn("control read: %s", get_usb_statmsg(urb->status));
+               dev_warn(cs->dev, "control read: %s\n",
+                        get_usb_statmsg(urb->status));
        retry:
                if (ucs->retry_cmd_in++ < BAS_RETRY) {
-                       notice("control read: retry %d", ucs->retry_cmd_in);
+                       dev_notice(cs->dev, "control read: retry %d\n",
+                                  ucs->retry_cmd_in);
                        if (atread_submit(cs, BAS_TIMEOUT) >= 0) {
                                /* resubmitted - bypass regular exit block */
                                spin_unlock_irqrestore(&cs->lock, flags);
                                return;
                        }
                } else {
-                       err("control read: giving up after %d tries",
-                           ucs->retry_cmd_in);
+                       dev_err(cs->dev,
+                               "control read: giving up after %d tries\n",
+                               ucs->retry_cmd_in);
                }
                error_reset(cs);
        }
@@ -724,7 +699,7 @@ static void read_ctrl_callback(struct urb *urb, struct pt_regs *regs)
        ucs->rcvbuf_size = 0;
        spin_unlock_irqrestore(&cs->lock, flags);
        if (have_data) {
-               dbg(DEBUG_INTR, "%s-->BH", __func__);
+               gig_dbg(DEBUG_INTR, "%s-->BH", __func__);
                gigaset_schedule_event(cs);
        }
 }
@@ -743,21 +718,16 @@ static void read_iso_callback(struct urb *urb, struct pt_regs *regs)
        unsigned long flags;
        int i, rc;
 
-       IFNULLRET(urb);
-       IFNULLRET(urb->context);
-       IFNULLRET(cardstate);
-
        /* status codes not worth bothering the tasklet with */
        if (unlikely(urb->status == -ENOENT || urb->status == -ECONNRESET ||
-                    urb->status == -EINPROGRESS)) {
-               dbg(DEBUG_ISO,
-                   "%s: %s", __func__, get_usb_statmsg(urb->status));
+                    urb->status == -EINPROGRESS)) {
+               gig_dbg(DEBUG_ISO, "%s: %s",
+                       __func__, get_usb_statmsg(urb->status));
                return;
        }
 
-       bcs = (struct bc_state *) urb->context;
+       bcs = urb->context;
        ubc = bcs->hw.bas;
-       IFNULLRET(ubc);
 
        spin_lock_irqsave(&ubc->isoinlock, flags);
        if (likely(ubc->isoindone == NULL)) {
@@ -777,14 +747,17 @@ static void read_iso_callback(struct urb *urb, struct pt_regs *regs)
                        urb->iso_frame_desc[i].actual_length = 0;
                }
                if (likely(atomic_read(&ubc->running))) {
-                       urb->dev = bcs->cs->hw.bas->udev;       /* clobbered by USB subsystem */
+                       /* urb->dev is clobbered by USB subsystem */
+                       urb->dev = bcs->cs->hw.bas->udev;
                        urb->transfer_flags = URB_ISO_ASAP;
                        urb->number_of_packets = BAS_NUMFRAMES;
-                       dbg(DEBUG_ISO, "%s: isoc read overrun/resubmit", __func__);
+                       gig_dbg(DEBUG_ISO, "%s: isoc read overrun/resubmit",
+                               __func__);
                        rc = usb_submit_urb(urb, SLAB_ATOMIC);
                        if (unlikely(rc != 0)) {
-                               err("could not resubmit isochronous read URB: %s",
-                                   get_usb_statmsg(rc));
+                               dev_err(bcs->cs->dev,
+                                       "could not resubmit isochronous read "
+                                       "URB: %s\n", get_usb_statmsg(rc));
                                dump_urb(DEBUG_ISO, "isoc read", urb);
                                error_hangup(bcs);
                        }
@@ -806,23 +779,17 @@ static void write_iso_callback(struct urb *urb, struct pt_regs *regs)
        struct bas_bc_state *ubc;
        unsigned long flags;
 
-       IFNULLRET(urb);
-       IFNULLRET(urb->context);
-       IFNULLRET(cardstate);
-
        /* status codes not worth bothering the tasklet with */
        if (unlikely(urb->status == -ENOENT || urb->status == -ECONNRESET ||
-                    urb->status == -EINPROGRESS)) {
-               dbg(DEBUG_ISO,
-                   "%s: %s", __func__, get_usb_statmsg(urb->status));
+                    urb->status == -EINPROGRESS)) {
+               gig_dbg(DEBUG_ISO, "%s: %s",
+                       __func__, get_usb_statmsg(urb->status));
                return;
        }
 
        /* pass URB context to tasklet */
-       ucx = (struct isow_urbctx_t *) urb->context;
-       IFNULLRET(ucx->bcs);
+       ucx = urb->context;
        ubc = ucx->bcs->hw.bas;
-       IFNULLRET(ubc);
 
        spin_lock_irqsave(&ubc->isooutlock, flags);
        ubc->isooutovfl = ubc->isooutdone;
@@ -841,15 +808,11 @@ static void write_iso_callback(struct urb *urb, struct pt_regs *regs)
  */
 static int starturbs(struct bc_state *bcs)
 {
+       struct bas_bc_state *ubc = bcs->hw.bas;
        struct urb *urb;
-       struct bas_bc_state *ubc;
        int j, k;
        int rc;
 
-       IFNULLRETVAL(bcs, -EFAULT);
-       ubc = bcs->hw.bas;
-       IFNULLRETVAL(ubc, -EFAULT);
-
        /* initialize L2 reception */
        if (bcs->proto2 == ISDN_PROTO_L2_HDLC)
                bcs->inputstate |= INS_flag_hunt;
@@ -859,7 +822,7 @@ static int starturbs(struct bc_state *bcs)
        for (k = 0; k < BAS_INURBS; k++) {
                urb = ubc->isoinurbs[k];
                if (!urb) {
-                       err("isoinurbs[%d]==NULL", k);
+                       dev_err(bcs->cs->dev, "isoinurbs[%d]==NULL\n", k);
                        rc = -EFAULT;
                        goto error;
                }
@@ -882,8 +845,9 @@ static int starturbs(struct bc_state *bcs)
 
                dump_urb(DEBUG_ISO, "Initial isoc read", urb);
                if ((rc = usb_submit_urb(urb, SLAB_ATOMIC)) != 0) {
-                       err("could not submit isochronous read URB %d: %s",
-                           k, get_usb_statmsg(rc));
+                       dev_err(bcs->cs->dev,
+                              "could not submit isochronous read URB %d: %s\n",
+                               k, get_usb_statmsg(rc));
                        goto error;
                }
        }
@@ -895,7 +859,7 @@ static int starturbs(struct bc_state *bcs)
        for (k = 0; k < BAS_OUTURBS; ++k) {
                urb = ubc->isoouturbs[k].urb;
                if (!urb) {
-                       err("isoouturbs[%d].urb==NULL", k);
+                       dev_err(bcs->cs->dev, "isoouturbs[%d].urb==NULL\n", k);
                        rc = -EFAULT;
                        goto error;
                }
@@ -922,8 +886,9 @@ static int starturbs(struct bc_state *bcs)
                dump_urb(DEBUG_ISO, "Initial isoc write", urb);
                rc = usb_submit_urb(ubc->isoouturbs[k].urb, SLAB_ATOMIC);
                if (rc != 0) {
-                       err("could not submit isochronous write URB %d: %s",
-                           k, get_usb_statmsg(rc));
+                       dev_err(bcs->cs->dev,
+                             "could not submit isochronous write URB %d: %s\n",
+                               k, get_usb_statmsg(rc));
                        goto error;
                }
        }
@@ -946,20 +911,20 @@ static void stopurbs(struct bas_bc_state *ubc)
 {
        int k, rc;
 
-       IFNULLRET(ubc);
-
        atomic_set(&ubc->running, 0);
 
        for (k = 0; k < BAS_INURBS; ++k) {
                rc = usb_unlink_urb(ubc->isoinurbs[k]);
-               dbg(DEBUG_ISO, "%s: isoc input URB %d unlinked, result = %d",
-                   __func__, k, rc);
+               gig_dbg(DEBUG_ISO,
+                       "%s: isoc input URB %d unlinked, result = %d",
+                       __func__, k, rc);
        }
 
        for (k = 0; k < BAS_OUTURBS; ++k) {
                rc = usb_unlink_urb(ubc->isoouturbs[k].urb);
-               dbg(DEBUG_ISO, "%s: isoc output URB %d unlinked, result = %d",
-                   __func__, k, rc);
+               gig_dbg(DEBUG_ISO,
+                       "%s: isoc output URB %d unlinked, result = %d",
+                       __func__, k, rc);
        }
 }
 
@@ -977,19 +942,14 @@ static void stopurbs(struct bas_bc_state *ubc)
  */
 static int submit_iso_write_urb(struct isow_urbctx_t *ucx)
 {
-       struct urb *urb;
-       struct bas_bc_state *ubc;
+       struct urb *urb = ucx->urb;
+       struct bas_bc_state *ubc = ucx->bcs->hw.bas;
        struct usb_iso_packet_descriptor *ifd;
        int corrbytes, nframe, rc;
+       unsigned long flags;
 
-       IFNULLRETVAL(ucx, -EFAULT);
-       urb = ucx->urb;
-       IFNULLRETVAL(urb, -EFAULT);
-       IFNULLRETVAL(ucx->bcs, -EFAULT);
-       ubc = ucx->bcs->hw.bas;
-       IFNULLRETVAL(ubc, -EFAULT);
-
-       urb->dev = ucx->bcs->cs->hw.bas->udev;  /* clobbered by USB subsystem */
+       /* urb->dev is clobbered by USB subsystem */
+       urb->dev = ucx->bcs->cs->hw.bas->udev;
        urb->transfer_flags = URB_ISO_ASAP;
        urb->transfer_buffer = ubc->isooutbuf->data;
        urb->transfer_buffer_length = sizeof(ubc->isooutbuf->data);
@@ -1000,7 +960,8 @@ static int submit_iso_write_urb(struct isow_urbctx_t *ucx)
                /* compute frame length according to flow control */
                ifd->length = BAS_NORMFRAME;
                if ((corrbytes = atomic_read(&ubc->corrbytes)) != 0) {
-                       dbg(DEBUG_ISO, "%s: corrbytes=%d", __func__, corrbytes);
+                       gig_dbg(DEBUG_ISO, "%s: corrbytes=%d",
+                               __func__, corrbytes);
                        if (corrbytes > BAS_HIGHFRAME - BAS_NORMFRAME)
                                corrbytes = BAS_HIGHFRAME - BAS_NORMFRAME;
                        else if (corrbytes < BAS_LOWFRAME - BAS_NORMFRAME)
@@ -1008,18 +969,21 @@ static int submit_iso_write_urb(struct isow_urbctx_t *ucx)
                        ifd->length += corrbytes;
                        atomic_add(-corrbytes, &ubc->corrbytes);
                }
-               //dbg(DEBUG_ISO, "%s: frame %d length=%d", __func__, nframe, ifd->length);
 
                /* retrieve block of data to send */
-               ifd->offset = gigaset_isowbuf_getbytes(ubc->isooutbuf, ifd->length);
+               ifd->offset = gigaset_isowbuf_getbytes(ubc->isooutbuf,
+                                                      ifd->length);
                if (ifd->offset < 0) {
                        if (ifd->offset == -EBUSY) {
-                               dbg(DEBUG_ISO, "%s: buffer busy at frame %d",
-                                   __func__, nframe);
-                               /* tasklet will be restarted from gigaset_send_skb() */
+                               gig_dbg(DEBUG_ISO,
+                                       "%s: buffer busy at frame %d",
+                                       __func__, nframe);
+                               /* tasklet will be restarted from
+                                  gigaset_send_skb() */
                        } else {
-                               err("%s: buffer error %d at frame %d",
-                                   __func__, ifd->offset, nframe);
+                               dev_err(ucx->bcs->cs->dev,
+                                       "%s: buffer error %d at frame %d\n",
+                                       __func__, ifd->offset, nframe);
                                return ifd->offset;
                        }
                        break;
@@ -1029,9 +993,14 @@ static int submit_iso_write_urb(struct isow_urbctx_t *ucx)
                ifd->actual_length = 0;
        }
        if ((urb->number_of_packets = nframe) > 0) {
-               if ((rc = usb_submit_urb(urb, SLAB_ATOMIC)) != 0) {
-                       err("could not submit isochronous write URB: %s",
-                           get_usb_statmsg(rc));
+               spin_lock_irqsave(&ucx->bcs->cs->lock, flags);
+               rc = ucx->bcs->cs->connected ? usb_submit_urb(urb, SLAB_ATOMIC) : -ENODEV;
+               spin_unlock_irqrestore(&ucx->bcs->cs->lock, flags);
+
+               if (rc) {
+                       dev_err(ucx->bcs->cs->dev,
+                               "could not submit isochronous write URB: %s\n",
+                               get_usb_statmsg(rc));
                        dump_urb(DEBUG_ISO, "isoc write", urb);
                        return rc;
                }
@@ -1048,9 +1017,9 @@ static int submit_iso_write_urb(struct isow_urbctx_t *ucx)
  */
 static void write_iso_tasklet(unsigned long data)
 {
-       struct bc_state *bcs;
-       struct bas_bc_state *ubc;
-       struct cardstate *cs;
+       struct bc_state *bcs = (struct bc_state *) data;
+       struct bas_bc_state *ubc = bcs->hw.bas;
+       struct cardstate *cs = bcs->cs;
        struct isow_urbctx_t *done, *next, *ovfl;
        struct urb *urb;
        struct usb_iso_packet_descriptor *ifd;
@@ -1060,22 +1029,10 @@ static void write_iso_tasklet(unsigned long data)
        struct sk_buff *skb;
        int len;
 
-       bcs = (struct bc_state *) data;
-       IFNULLRET(bcs);
-       ubc = bcs->hw.bas;
-       IFNULLRET(ubc);
-       cs = bcs->cs;
-       IFNULLRET(cs);
-
        /* loop while completed URBs arrive in time */
        for (;;) {
-               if (unlikely(!atomic_read(&cs->connected))) {
-                       warn("%s: disconnected", __func__);
-                       return;
-               }
-
                if (unlikely(!(atomic_read(&ubc->running)))) {
-                       dbg(DEBUG_ISO, "%s: not running", __func__);
+                       gig_dbg(DEBUG_ISO, "%s: not running", __func__);
                        return;
                }
 
@@ -1087,7 +1044,7 @@ static void write_iso_tasklet(unsigned long data)
                ubc->isooutovfl = NULL;
                spin_unlock_irqrestore(&ubc->isooutlock, flags);
                if (ovfl) {
-                       err("isochronous write buffer underrun - buy a faster machine :-)");
+                       dev_err(cs->dev, "isochronous write buffer underrun\n");
                        error_hangup(bcs);
                        break;
                }
@@ -1110,7 +1067,8 @@ static void write_iso_tasklet(unsigned long data)
                                spin_unlock_irqrestore(&ubc->isooutlock, flags);
                                if (next) {
                                        /* couldn't put it back */
-                                       err("losing isochronous write URB");
+                                       dev_err(cs->dev,
+                                             "losing isochronous write URB\n");
                                        error_hangup(bcs);
                                }
                        }
@@ -1123,22 +1081,25 @@ static void write_iso_tasklet(unsigned long data)
                        break;
                case -EXDEV:                    /* inspect individual frames */
                        /* assumptions (for lack of documentation):
-                        * - actual_length bytes of the frame in error are successfully sent
+                        * - actual_length bytes of the frame in error are
+                        *   successfully sent
                         * - all following frames are not sent at all
                         */
-                       dbg(DEBUG_ISO, "%s: URB partially completed", __func__);
+                       gig_dbg(DEBUG_ISO, "%s: URB partially completed",
+                               __func__);
                        offset = done->limit;   /* just in case */
                        for (i = 0; i < BAS_NUMFRAMES; i++) {
                                ifd = &urb->iso_frame_desc[i];
                                if (ifd->status ||
                                    ifd->actual_length != ifd->length) {
-                                       warn("isochronous write: frame %d: %s, "
-                                            "only %d of %d bytes sent",
+                                       dev_warn(cs->dev,
+                                            "isochronous write: frame %d: %s, "
+                                            "only %d of %d bytes sent\n",
                                             i, get_usb_statmsg(ifd->status),
                                             ifd->actual_length, ifd->length);
                                        offset = (ifd->offset +
-                                                 ifd->actual_length)
-                                                % BAS_OUTBUFSIZE;
+                                                 ifd->actual_length)
+                                                % BAS_OUTBUFSIZE;
                                        break;
                                }
                        }
@@ -1148,25 +1109,26 @@ static void write_iso_tasklet(unsigned long data)
                                ifd = &urb->iso_frame_desc[i];
                                if (ifd->status != -EINPROGRESS
                                    || ifd->actual_length != 0) {
-                                       warn("isochronous write: frame %d: %s, "
-                                            "%d of %d bytes sent",
+                                       dev_warn(cs->dev,
+                                            "isochronous write: frame %d: %s, "
+                                            "%d of %d bytes sent\n",
                                             i, get_usb_statmsg(ifd->status),
                                             ifd->actual_length, ifd->length);
                                        offset = (ifd->offset +
-                                                 ifd->actual_length)
-                                                % BAS_OUTBUFSIZE;
+                                                 ifd->actual_length)
+                                                % BAS_OUTBUFSIZE;
                                        break;
                                }
                        }
 #endif
                        break;
-               case -EPIPE:                    //FIXME is this the code for "underrun"?
-                       err("isochronous write stalled");
+               case -EPIPE:            //FIXME is this the code for "underrun"?
+                       dev_err(cs->dev, "isochronous write stalled\n");
                        error_hangup(bcs);
                        break;
                default:                        /* severe trouble */
-                       warn("isochronous write: %s",
-                            get_usb_statmsg(urb->status));
+                       dev_warn(cs->dev, "isochronous write: %s\n",
+                                get_usb_statmsg(urb->status));
                }
 
                /* mark the write buffer area covered by this URB as free */
@@ -1194,8 +1156,8 @@ static void write_iso_tasklet(unsigned long data)
                if (gigaset_isoc_buildframe(bcs, skb->data, len) == -EAGAIN) {
                        /* insufficient buffer space, push back onto queue */
                        skb_queue_head(&bcs->squeue, skb);
-                       dbg(DEBUG_ISO, "%s: skb requeued, qlen=%d",
-                           __func__, skb_queue_len(&bcs->squeue));
+                       gig_dbg(DEBUG_ISO, "%s: skb requeued, qlen=%d",
+                               __func__, skb_queue_len(&bcs->squeue));
                        break;
                }
                skb_pull(skb, len);
@@ -1215,28 +1177,16 @@ static void write_iso_tasklet(unsigned long data)
  */
 static void read_iso_tasklet(unsigned long data)
 {
-       struct bc_state *bcs;
-       struct bas_bc_state *ubc;
-       struct cardstate *cs;
+       struct bc_state *bcs = (struct bc_state *) data;
+       struct bas_bc_state *ubc = bcs->hw.bas;
+       struct cardstate *cs = bcs->cs;
        struct urb *urb;
        char *rcvbuf;
        unsigned long flags;
        int totleft, numbytes, offset, frame, rc;
 
-       bcs = (struct bc_state *) data;
-       IFNULLRET(bcs);
-       ubc = bcs->hw.bas;
-       IFNULLRET(ubc);
-       cs = bcs->cs;
-       IFNULLRET(cs);
-
        /* loop while more completed URBs arrive in the meantime */
        for (;;) {
-               if (!atomic_read(&cs->connected)) {
-                       warn("%s: disconnected", __func__);
-                       return;
-               }
-
                /* retrieve URB */
                spin_lock_irqsave(&ubc->isoinlock, flags);
                if (!(urb = ubc->isoindone)) {
@@ -1245,38 +1195,45 @@ static void read_iso_tasklet(unsigned long data)
                }
                ubc->isoindone = NULL;
                if (unlikely(ubc->loststatus != -EINPROGRESS)) {
-                       warn("isochronous read overrun, dropped URB with status: %s, %d bytes lost",
-                            get_usb_statmsg(ubc->loststatus), ubc->isoinlost);
+                       dev_warn(cs->dev,
+                                "isochronous read overrun, "
+                                "dropped URB with status: %s, %d bytes lost\n",
+                                get_usb_statmsg(ubc->loststatus),
+                                ubc->isoinlost);
                        ubc->loststatus = -EINPROGRESS;
                }
                spin_unlock_irqrestore(&ubc->isoinlock, flags);
 
                if (unlikely(!(atomic_read(&ubc->running)))) {
-                       dbg(DEBUG_ISO, "%s: channel not running, dropped URB with status: %s",
-                           __func__, get_usb_statmsg(urb->status));
+                       gig_dbg(DEBUG_ISO,
+                               "%s: channel not running, "
+                               "dropped URB with status: %s",
+                               __func__, get_usb_statmsg(urb->status));
                        return;
                }
 
                switch (urb->status) {
                case 0:                         /* normal completion */
                        break;
-               case -EXDEV:                    /* inspect individual frames (we do that anyway) */
-                       dbg(DEBUG_ISO, "%s: URB partially completed", __func__);
+               case -EXDEV:                    /* inspect individual frames
+                                                  (we do that anyway) */
+                       gig_dbg(DEBUG_ISO, "%s: URB partially completed",
+                               __func__);
                        break;
                case -ENOENT:
                case -ECONNRESET:
-                       dbg(DEBUG_ISO, "%s: URB canceled", __func__);
+                       gig_dbg(DEBUG_ISO, "%s: URB canceled", __func__);
                        continue;               /* -> skip */
                case -EINPROGRESS:              /* huh? */
-                       dbg(DEBUG_ISO, "%s: URB still pending", __func__);
+                       gig_dbg(DEBUG_ISO, "%s: URB still pending", __func__);
                        continue;               /* -> skip */
                case -EPIPE:
-                       err("isochronous read stalled");
+                       dev_err(cs->dev, "isochronous read stalled\n");
                        error_hangup(bcs);
                        continue;               /* -> skip */
                default:                        /* severe trouble */
-                       warn("isochronous read: %s",
-                            get_usb_statmsg(urb->status));
+                       dev_warn(cs->dev, "isochronous read: %s\n",
+                                get_usb_statmsg(urb->status));
                        goto error;
                }
 
@@ -1284,33 +1241,44 @@ static void read_iso_tasklet(unsigned long data)
                totleft = urb->actual_length;
                for (frame = 0; totleft > 0 && frame < BAS_NUMFRAMES; frame++) {
                        if (unlikely(urb->iso_frame_desc[frame].status)) {
-                               warn("isochronous read: frame %d: %s",
-                                    frame, get_usb_statmsg(urb->iso_frame_desc[frame].status));
+                               dev_warn(cs->dev,
+                                        "isochronous read: frame %d: %s\n",
+                                        frame,
+                                        get_usb_statmsg(
+                                           urb->iso_frame_desc[frame].status));
                                break;
                        }
                        numbytes = urb->iso_frame_desc[frame].actual_length;
                        if (unlikely(numbytes > BAS_MAXFRAME)) {
-                               warn("isochronous read: frame %d: numbytes (%d) > BAS_MAXFRAME",
-                                    frame, numbytes);
+                               dev_warn(cs->dev,
+                                        "isochronous read: frame %d: "
+                                        "numbytes (%d) > BAS_MAXFRAME\n",
+                                        frame, numbytes);
                                break;
                        }
                        if (unlikely(numbytes > totleft)) {
-                               warn("isochronous read: frame %d: numbytes (%d) > totleft (%d)",
-                                    frame, numbytes, totleft);
+                               dev_warn(cs->dev,
+                                        "isochronous read: frame %d: "
+                                        "numbytes (%d) > totleft (%d)\n",
+                                        frame, numbytes, totleft);
                                break;
                        }
                        offset = urb->iso_frame_desc[frame].offset;
                        if (unlikely(offset + numbytes > BAS_INBUFSIZE)) {
-                               warn("isochronous read: frame %d: offset (%d) + numbytes (%d) > BAS_INBUFSIZE",
-                                    frame, offset, numbytes);
+                               dev_warn(cs->dev,
+                                        "isochronous read: frame %d: "
+                                        "offset (%d) + numbytes (%d) "
+                                        "> BAS_INBUFSIZE\n",
+                                        frame, offset, numbytes);
                                break;
                        }
                        gigaset_isoc_receive(rcvbuf + offset, numbytes, bcs);
                        totleft -= numbytes;
                }
                if (unlikely(totleft > 0))
-                       warn("isochronous read: %d data bytes missing",
-                            totleft);
+                       dev_warn(cs->dev,
+                                "isochronous read: %d data bytes missing\n",
+                                totleft);
 
        error:
                /* URB processed, resubmit */
@@ -1318,12 +1286,17 @@ static void read_iso_tasklet(unsigned long data)
                        urb->iso_frame_desc[frame].status = 0;
                        urb->iso_frame_desc[frame].actual_length = 0;
                }
-               urb->dev = bcs->cs->hw.bas->udev;       /* clobbered by USB subsystem */
+               /* urb->dev is clobbered by USB subsystem */
+               urb->dev = bcs->cs->hw.bas->udev;
                urb->transfer_flags = URB_ISO_ASAP;
                urb->number_of_packets = BAS_NUMFRAMES;
-               if ((rc = usb_submit_urb(urb, SLAB_ATOMIC)) != 0) {
-                       err("could not resubmit isochronous read URB: %s",
-                           get_usb_statmsg(rc));
+               spin_lock_irqsave(&cs->lock, flags);
+               rc = cs->connected ? usb_submit_urb(urb, SLAB_ATOMIC) : -ENODEV;
+               spin_unlock_irqrestore(&cs->lock, flags);
+               if (rc) {
+                       dev_err(cs->dev,
+                               "could not resubmit isochronous read URB: %s\n",
+                               get_usb_statmsg(rc));
                        dump_urb(DEBUG_ISO, "resubmit iso read", urb);
                        error_hangup(bcs);
                }
@@ -1341,15 +1314,10 @@ static void read_iso_tasklet(unsigned long data)
 static void req_timeout(unsigned long data)
 {
        struct bc_state *bcs = (struct bc_state *) data;
-       struct bas_cardstate *ucs;
+       struct bas_cardstate *ucs = bcs->cs->hw.bas;
        int pending;
        unsigned long flags;
 
-       IFNULLRET(bcs);
-       IFNULLRET(bcs->cs);
-       ucs = bcs->cs->hw.bas;
-       IFNULLRET(ucs);
-
        check_pending(ucs);
 
        spin_lock_irqsave(&ucs->lock, flags);
@@ -1359,33 +1327,34 @@ static void req_timeout(unsigned long data)
 
        switch (pending) {
        case 0:                                 /* no pending request */
-               dbg(DEBUG_USBREQ, "%s: no request pending", __func__);
+               gig_dbg(DEBUG_USBREQ, "%s: no request pending", __func__);
                break;
 
        case HD_OPEN_ATCHANNEL:
-               err("timeout opening AT channel");
+               dev_err(bcs->cs->dev, "timeout opening AT channel\n");
                error_reset(bcs->cs);
                break;
 
        case HD_OPEN_B2CHANNEL:
        case HD_OPEN_B1CHANNEL:
-               err("timeout opening channel %d", bcs->channel + 1);
+               dev_err(bcs->cs->dev, "timeout opening channel %d\n",
+                       bcs->channel + 1);
                error_hangup(bcs);
                break;
 
        case HD_CLOSE_ATCHANNEL:
-               err("timeout closing AT channel");
-               //wake_up_interruptible(cs->initwait);
-               //FIXME need own wait queue?
+               dev_err(bcs->cs->dev, "timeout closing AT channel\n");
                break;
 
        case HD_CLOSE_B2CHANNEL:
        case HD_CLOSE_B1CHANNEL:
-               err("timeout closing channel %d", bcs->channel + 1);
+               dev_err(bcs->cs->dev, "timeout closing channel %d\n",
+                       bcs->channel + 1);
                break;
 
        default:
-               warn("request 0x%02x timed out, clearing", pending);
+               dev_warn(bcs->cs->dev, "request 0x%02x timed out, clearing\n",
+                        pending);
        }
 }
 
@@ -1398,18 +1367,14 @@ static void req_timeout(unsigned long data)
  */
 static void write_ctrl_callback(struct urb *urb, struct pt_regs *regs)
 {
-       struct bas_cardstate *ucs;
+       struct bas_cardstate *ucs = urb->context;
        unsigned long flags;
 
-       IFNULLRET(urb);
-       IFNULLRET(urb->context);
-       IFNULLRET(cardstate);
-
-       ucs = (struct bas_cardstate *) urb->context;
        spin_lock_irqsave(&ucs->lock, flags);
        if (urb->status && ucs->pending) {
-               err("control request 0x%02x failed: %s",
-                   ucs->pending, get_usb_statmsg(urb->status));
+               dev_err(&ucs->interface->dev,
+                       "control request 0x%02x failed: %s\n",
+                       ucs->pending, get_usb_statmsg(urb->status));
                del_timer(&ucs->timer_ctrl);
                ucs->pending = 0;
        }
@@ -1438,28 +1403,25 @@ static void write_ctrl_callback(struct urb *urb, struct pt_regs *regs)
  */
 static int req_submit(struct bc_state *bcs, int req, int val, int timeout)
 {
-       struct bas_cardstate *ucs;
+       struct bas_cardstate *ucs = bcs->cs->hw.bas;
        int ret;
        unsigned long flags;
 
-       IFNULLRETVAL(bcs, -EINVAL);
-       IFNULLRETVAL(bcs->cs, -EINVAL);
-       ucs = bcs->cs->hw.bas;
-       IFNULLRETVAL(ucs, -EINVAL);
-       IFNULLRETVAL(ucs->urb_ctrl, -EINVAL);
-
-       dbg(DEBUG_USBREQ, "-------> 0x%02x (%d)", req, val);
+       gig_dbg(DEBUG_USBREQ, "-------> 0x%02x (%d)", req, val);
 
        spin_lock_irqsave(&ucs->lock, flags);
        if (ucs->pending) {
                spin_unlock_irqrestore(&ucs->lock, flags);
-               err("submission of request 0x%02x failed: request 0x%02x still pending",
-                   req, ucs->pending);
+               dev_err(bcs->cs->dev,
+                       "submission of request 0x%02x failed: "
+                       "request 0x%02x still pending\n",
+                       req, ucs->pending);
                return -EBUSY;
        }
        if (ucs->urb_ctrl->status == -EINPROGRESS) {
                spin_unlock_irqrestore(&ucs->lock, flags);
-               err("could not submit request 0x%02x: URB busy", req);
+               dev_err(bcs->cs->dev,
+                       "could not submit request 0x%02x: URB busy\n", req);
                return -EBUSY;
        }
 
@@ -1469,19 +1431,19 @@ static int req_submit(struct bc_state *bcs, int req, int val, int timeout)
        ucs->dr_ctrl.wIndex = 0;
        ucs->dr_ctrl.wLength = 0;
        usb_fill_control_urb(ucs->urb_ctrl, ucs->udev,
-                             usb_sndctrlpipe(ucs->udev, 0),
-                             (unsigned char*) &ucs->dr_ctrl, NULL, 0,
-                             write_ctrl_callback, ucs);
+                            usb_sndctrlpipe(ucs->udev, 0),
+                            (unsigned char*) &ucs->dr_ctrl, NULL, 0,
+                            write_ctrl_callback, ucs);
        if ((ret = usb_submit_urb(ucs->urb_ctrl, SLAB_ATOMIC)) != 0) {
-               err("could not submit request 0x%02x: %s",
-                   req, get_usb_statmsg(ret));
+               dev_err(bcs->cs->dev, "could not submit request 0x%02x: %s\n",
+                       req, get_usb_statmsg(ret));
                spin_unlock_irqrestore(&ucs->lock, flags);
                return ret;
        }
        ucs->pending = req;
 
        if (timeout > 0) {
-               dbg(DEBUG_USBREQ, "setting timeout of %d/10 secs", timeout);
+               gig_dbg(DEBUG_USBREQ, "setting timeout of %d/10 secs", timeout);
                ucs->timer_ctrl.expires = jiffies + timeout * HZ / 10;
                ucs->timer_ctrl.data = (unsigned long) bcs;
                ucs->timer_ctrl.function = req_timeout;
@@ -1504,19 +1466,18 @@ static int gigaset_init_bchannel(struct bc_state *bcs)
 {
        int req, ret;
 
-       IFNULLRETVAL(bcs, -EINVAL);
-
        if ((ret = starturbs(bcs)) < 0) {
-               err("could not start isochronous I/O for channel %d",
-                   bcs->channel + 1);
+               dev_err(bcs->cs->dev,
+                       "could not start isochronous I/O for channel %d\n",
+                       bcs->channel + 1);
                error_hangup(bcs);
                return ret;
        }
 
        req = bcs->channel ? HD_OPEN_B2CHANNEL : HD_OPEN_B1CHANNEL;
        if ((ret = req_submit(bcs, req, 0, BAS_TIMEOUT)) < 0) {
-               err("could not open channel %d: %s",
-                   bcs->channel + 1, get_usb_statmsg(ret));
+               dev_err(bcs->cs->dev, "could not open channel %d: %s\n",
+                       bcs->channel + 1, get_usb_statmsg(ret));
                stopurbs(bcs->hw.bas);
                error_hangup(bcs);
        }
@@ -1537,8 +1498,6 @@ static int gigaset_close_bchannel(struct bc_state *bcs)
 {
        int req, ret;
 
-       IFNULLRETVAL(bcs, -EINVAL);
-
        if (!(atomic_read(&bcs->cs->hw.bas->basstate) &
              (bcs->channel ? BS_B2OPEN : BS_B1OPEN))) {
                /* channel not running: just signal common.c */
@@ -1548,8 +1507,9 @@ static int gigaset_close_bchannel(struct bc_state *bcs)
 
        req = bcs->channel ? HD_CLOSE_B2CHANNEL : HD_CLOSE_B1CHANNEL;
        if ((ret = req_submit(bcs, req, 0, BAS_TIMEOUT)) < 0)
-               err("could not submit HD_CLOSE_BxCHANNEL request: %s",
-                   get_usb_statmsg(ret));
+               dev_err(bcs->cs->dev,
+                       "could not submit HD_CLOSE_BxCHANNEL request: %s\n",
+                       get_usb_statmsg(ret));
        return ret;
 }
 
@@ -1564,17 +1524,13 @@ static int gigaset_close_bchannel(struct bc_state *bcs)
  */
 static void complete_cb(struct cardstate *cs)
 {
-       struct cmdbuf_t *cb;
-
-       IFNULLRET(cs);
-       cb = cs->cmdbuf;
-       IFNULLRET(cb);
+       struct cmdbuf_t *cb = cs->cmdbuf;
 
        /* unqueue completed buffer */
        cs->cmdbytes -= cs->curlen;
-       dbg(DEBUG_TRANSCMD | DEBUG_LOCKCMD,
-           "write_command: sent %u bytes, %u left",
-           cs->curlen, cs->cmdbytes);
+       gig_dbg(DEBUG_TRANSCMD|DEBUG_LOCKCMD,
+               "write_command: sent %u bytes, %u left",
+               cs->curlen, cs->cmdbytes);
        if ((cs->cmdbuf = cb->next) != NULL) {
                cs->cmdbuf->prev = NULL;
                cs->curlen = cs->cmdbuf->len;
@@ -1600,15 +1556,9 @@ static int atwrite_submit(struct cardstate *cs, unsigned char *buf, int len);
  */
 static void write_command_callback(struct urb *urb, struct pt_regs *regs)
 {
-       struct cardstate *cs;
+       struct cardstate *cs = urb->context;
+       struct bas_cardstate *ucs = cs->hw.bas;
        unsigned long flags;
-       struct bas_cardstate *ucs;
-
-       IFNULLRET(urb);
-       cs = (struct cardstate *) urb->context;
-       IFNULLRET(cs);
-       ucs = cs->hw.bas;
-       IFNULLRET(ucs);
 
        /* check status */
        switch (urb->status) {
@@ -1618,22 +1568,27 @@ static void write_command_callback(struct urb *urb, struct pt_regs *regs)
        case -ECONNRESET:               /* canceled (async) */
        case -EINPROGRESS:              /* pending */
                /* ignore silently */
-               dbg(DEBUG_USBREQ,
-                   "%s: %s", __func__, get_usb_statmsg(urb->status));
+               gig_dbg(DEBUG_USBREQ, "%s: %s",
+                       __func__, get_usb_statmsg(urb->status));
                return;
        default:                                /* any failure */
                if (++ucs->retry_cmd_out > BAS_RETRY) {
-                       warn("command write: %s, giving up after %d retries",
-                            get_usb_statmsg(urb->status), ucs->retry_cmd_out);
+                       dev_warn(cs->dev,
+                                "command write: %s, "
+                                "giving up after %d retries\n",
+                                get_usb_statmsg(urb->status),
+                                ucs->retry_cmd_out);
                        break;
                }
                if (cs->cmdbuf == NULL) {
-                       warn("command write: %s, cannot retry - cmdbuf gone",
-                            get_usb_statmsg(urb->status));
+                       dev_warn(cs->dev,
+                                "command write: %s, "
+                                "cannot retry - cmdbuf gone\n",
+                                get_usb_statmsg(urb->status));
                        break;
                }
-               notice("command write: %s, retry %d",
-                      get_usb_statmsg(urb->status), ucs->retry_cmd_out);
+               dev_notice(cs->dev, "command write: %s, retry %d\n",
+                          get_usb_statmsg(urb->status), ucs->retry_cmd_out);
                if (atwrite_submit(cs, cs->cmdbuf->buf, cs->cmdbuf->len) >= 0)
                        /* resubmitted - bypass regular exit block */
                        return;
@@ -1655,13 +1610,9 @@ static void write_command_callback(struct urb *urb, struct pt_regs *regs)
 static void atrdy_timeout(unsigned long data)
 {
        struct cardstate *cs = (struct cardstate *) data;
-       struct bas_cardstate *ucs;
-
-       IFNULLRET(cs);
-       ucs = cs->hw.bas;
-       IFNULLRET(ucs);
+       struct bas_cardstate *ucs = cs->hw.bas;
 
-       warn("timeout waiting for HD_READY_SEND_ATDATA");
+       dev_warn(cs->dev, "timeout waiting for HD_READY_SEND_ATDATA\n");
 
        /* fake the missing signal - what else can I do? */
        update_basstate(ucs, BS_ATREADY, BS_ATTIMER);
@@ -1682,18 +1633,15 @@ static void atrdy_timeout(unsigned long data)
  */
 static int atwrite_submit(struct cardstate *cs, unsigned char *buf, int len)
 {
-       struct bas_cardstate *ucs;
+       struct bas_cardstate *ucs = cs->hw.bas;
+       unsigned long flags;
        int ret;
 
-       IFNULLRETVAL(cs, -EFAULT);
-       ucs = cs->hw.bas;
-       IFNULLRETVAL(ucs, -EFAULT);
-       IFNULLRETVAL(ucs->urb_cmd_out, -EFAULT);
-
-       dbg(DEBUG_USBREQ, "-------> HD_WRITE_ATMESSAGE (%d)", len);
+       gig_dbg(DEBUG_USBREQ, "-------> HD_WRITE_ATMESSAGE (%d)", len);
 
        if (ucs->urb_cmd_out->status == -EINPROGRESS) {
-               err("could not submit HD_WRITE_ATMESSAGE: URB busy");
+               dev_err(cs->dev,
+                       "could not submit HD_WRITE_ATMESSAGE: URB busy\n");
                return -EBUSY;
        }
 
@@ -1707,9 +1655,13 @@ static int atwrite_submit(struct cardstate *cs, unsigned char *buf, int len)
                             (unsigned char*) &ucs->dr_cmd_out, buf, len,
                             write_command_callback, cs);
 
-       if ((ret = usb_submit_urb(ucs->urb_cmd_out, SLAB_ATOMIC)) != 0) {
-               err("could not submit HD_WRITE_ATMESSAGE: %s",
-                   get_usb_statmsg(ret));
+       spin_lock_irqsave(&cs->lock, flags);
+       ret = cs->connected ? usb_submit_urb(ucs->urb_cmd_out, SLAB_ATOMIC) : -ENODEV;
+       spin_unlock_irqrestore(&cs->lock, flags);
+
+       if (ret) {
+               dev_err(cs->dev, "could not submit HD_WRITE_ATMESSAGE: %s\n",
+                       get_usb_statmsg(ret));
                return ret;
        }
 
@@ -1718,8 +1670,8 @@ static int atwrite_submit(struct cardstate *cs, unsigned char *buf, int len)
 
        /* start timeout if necessary */
        if (!(atomic_read(&ucs->basstate) & BS_ATTIMER)) {
-               dbg(DEBUG_OUTPUT,
-                   "setting ATREADY timeout of %d/10 secs", ATRDY_TIMEOUT);
+               gig_dbg(DEBUG_OUTPUT, "setting ATREADY timeout of %d/10 secs",
+                       ATRDY_TIMEOUT);
                ucs->timer_atrdy.expires = jiffies + ATRDY_TIMEOUT * HZ / 10;
                ucs->timer_atrdy.data = (unsigned long) cs;
                ucs->timer_atrdy.function = atrdy_timeout;
@@ -1740,21 +1692,17 @@ static int atwrite_submit(struct cardstate *cs, unsigned char *buf, int len)
 static int start_cbsend(struct cardstate *cs)
 {
        struct cmdbuf_t *cb;
-       struct bas_cardstate *ucs;
+       struct bas_cardstate *ucs = cs->hw.bas;
        unsigned long flags;
        int rc;
        int retval = 0;
 
-       IFNULLRETVAL(cs, -EFAULT);
-       ucs = cs->hw.bas;
-       IFNULLRETVAL(ucs, -EFAULT);
-
        /* check if AT channel is open */
        if (!(atomic_read(&ucs->basstate) & BS_ATOPEN)) {
-               dbg(DEBUG_TRANSCMD | DEBUG_LOCKCMD, "AT channel not open");
+               gig_dbg(DEBUG_TRANSCMD|DEBUG_LOCKCMD, "AT channel not open");
                rc = req_submit(cs->bcs, HD_OPEN_ATCHANNEL, 0, BAS_TIMEOUT);
                if (rc < 0) {
-                       err("could not open AT channel");
+                       dev_err(cs->dev, "could not open AT channel\n");
                        /* flush command queue */
                        spin_lock_irqsave(&cs->cmdlock, flags);
                        while (cs->cmdbuf != NULL)
@@ -1792,27 +1740,23 @@ static int start_cbsend(struct cardstate *cs)
  *     cs              controller state structure
  *     buf             command string to send
  *     len             number of bytes to send (max. IF_WRITEBUF)
- *     wake_tasklet    tasklet to run when transmission is completed (NULL if none)
+ *     wake_tasklet    tasklet to run when transmission is completed
+ *                     (NULL if none)
  * return value:
  *     number of bytes queued on success
  *     error code < 0 on error
  */
 static int gigaset_write_cmd(struct cardstate *cs,
-                             const unsigned char *buf, int len,
-                             struct tasklet_struct *wake_tasklet)
+                            const unsigned char *buf, int len,
+                            struct tasklet_struct *wake_tasklet)
 {
        struct cmdbuf_t *cb;
        unsigned long flags;
        int status;
 
        gigaset_dbg_buffer(atomic_read(&cs->mstate) != MS_LOCKED ?
-                            DEBUG_TRANSCMD : DEBUG_LOCKCMD,
-                          "CMD Transmit", len, buf, 0);
-
-       if (!atomic_read(&cs->connected)) {
-               err("%s: not connected", __func__);
-               return -ENODEV;
-       }
+                            DEBUG_TRANSCMD : DEBUG_LOCKCMD,
+                          "CMD Transmit", len, buf);
 
        if (len <= 0)
                return 0;                       /* nothing to do */
@@ -1820,7 +1764,7 @@ static int gigaset_write_cmd(struct cardstate *cs,
        if (len > IF_WRITEBUF)
                len = IF_WRITEBUF;
        if (!(cb = kmalloc(sizeof(struct cmdbuf_t) + len, GFP_ATOMIC))) {
-               err("%s: out of memory", __func__);
+               dev_err(cs->dev, "%s: out of memory\n", __func__);
                return -ENOMEM;
        }
 
@@ -1849,7 +1793,8 @@ static int gigaset_write_cmd(struct cardstate *cs,
 
 /* gigaset_write_room
  * tty_driver.write_room interface routine
- * return number of characters the driver will accept to be written via gigaset_write_cmd
+ * return number of characters the driver will accept to be written via
+ * gigaset_write_cmd
  * parameter:
  *     controller state structure
  * return value:
@@ -1947,7 +1892,7 @@ static int gigaset_initbcshw(struct bc_state *bcs)
                return 0;
        }
        tasklet_init(&ubc->sent_tasklet,
-                    &write_iso_tasklet, (unsigned long) bcs);
+                    &write_iso_tasklet, (unsigned long) bcs);
 
        spin_lock_init(&ubc->isoinlock);
        for (i = 0; i < BAS_INURBS; ++i)
@@ -1968,7 +1913,7 @@ static int gigaset_initbcshw(struct bc_state *bcs)
        ubc->shared0s = 0;
        ubc->stolen0s = 0;
        tasklet_init(&ubc->rcvd_tasklet,
-                    &read_iso_tasklet, (unsigned long) bcs);
+                    &read_iso_tasklet, (unsigned long) bcs);
        return 1;
 }
 
@@ -2027,57 +1972,56 @@ static int gigaset_initcshw(struct cardstate *cs)
  */
 static void freeurbs(struct cardstate *cs)
 {
-       struct bas_cardstate *ucs;
+       struct bas_cardstate *ucs = cs->hw.bas;
        struct bas_bc_state *ubc;
        int i, j;
 
-       IFNULLRET(cs);
-       ucs = cs->hw.bas;
-       IFNULLRET(ucs);
-
        for (j = 0; j < 2; ++j) {
                ubc = cs->bcs[j].hw.bas;
-               IFNULLCONT(ubc);
                for (i = 0; i < BAS_OUTURBS; ++i)
                        if (ubc->isoouturbs[i].urb) {
                                usb_kill_urb(ubc->isoouturbs[i].urb);
-                               dbg(DEBUG_INIT,
-                                   "%s: isoc output URB %d/%d unlinked",
-                                   __func__, j, i);
+                               gig_dbg(DEBUG_INIT,
+                                       "%s: isoc output URB %d/%d unlinked",
+                                       __func__, j, i);
                                usb_free_urb(ubc->isoouturbs[i].urb);
                                ubc->isoouturbs[i].urb = NULL;
                        }
                for (i = 0; i < BAS_INURBS; ++i)
                        if (ubc->isoinurbs[i]) {
                                usb_kill_urb(ubc->isoinurbs[i]);
-                               dbg(DEBUG_INIT,
-                                   "%s: isoc input URB %d/%d unlinked",
-                                   __func__, j, i);
+                               gig_dbg(DEBUG_INIT,
+                                       "%s: isoc input URB %d/%d unlinked",
+                                       __func__, j, i);
                                usb_free_urb(ubc->isoinurbs[i]);
                                ubc->isoinurbs[i] = NULL;
                        }
        }
        if (ucs->urb_int_in) {
                usb_kill_urb(ucs->urb_int_in);
-               dbg(DEBUG_INIT, "%s: interrupt input URB unlinked", __func__);
+               gig_dbg(DEBUG_INIT, "%s: interrupt input URB unlinked",
+                       __func__);
                usb_free_urb(ucs->urb_int_in);
                ucs->urb_int_in = NULL;
        }
        if (ucs->urb_cmd_out) {
                usb_kill_urb(ucs->urb_cmd_out);
-               dbg(DEBUG_INIT, "%s: command output URB unlinked", __func__);
+               gig_dbg(DEBUG_INIT, "%s: command output URB unlinked",
+                       __func__);
                usb_free_urb(ucs->urb_cmd_out);
                ucs->urb_cmd_out = NULL;
        }
        if (ucs->urb_cmd_in) {
                usb_kill_urb(ucs->urb_cmd_in);
-               dbg(DEBUG_INIT, "%s: command input URB unlinked", __func__);
+               gig_dbg(DEBUG_INIT, "%s: command input URB unlinked",
+                       __func__);
                usb_free_urb(ucs->urb_cmd_in);
                ucs->urb_cmd_in = NULL;
        }
        if (ucs->urb_ctrl) {
                usb_kill_urb(ucs->urb_ctrl);
-               dbg(DEBUG_INIT, "%s: control output URB unlinked", __func__);
+               gig_dbg(DEBUG_INIT, "%s: control output URB unlinked",
+                       __func__);
                usb_free_urb(ucs->urb_ctrl);
                ucs->urb_ctrl = NULL;
        }
@@ -2099,12 +2043,10 @@ static int gigaset_probe(struct usb_interface *interface,
        int i, j;
        int ret;
 
-       IFNULLRETVAL(udev, -ENODEV);
-
-       dbg(DEBUG_ANY,
-           "%s: Check if device matches .. (Vendor: 0x%x, Product: 0x%x)",
-           __func__, le16_to_cpu(udev->descriptor.idVendor),
-           le16_to_cpu(udev->descriptor.idProduct));
+       gig_dbg(DEBUG_ANY,
+               "%s: Check if device matches .. (Vendor: 0x%x, Product: 0x%x)",
+               __func__, le16_to_cpu(udev->descriptor.idVendor),
+               le16_to_cpu(udev->descriptor.idProduct));
 
        /* See if the device offered us matches what we can accept */
        if ((le16_to_cpu(udev->descriptor.idVendor)  != USB_GIGA_VENDOR_ID) ||
@@ -2112,20 +2054,21 @@ static int gigaset_probe(struct usb_interface *interface,
             le16_to_cpu(udev->descriptor.idProduct) != USB_4175_PRODUCT_ID &&
             le16_to_cpu(udev->descriptor.idProduct) != USB_SX303_PRODUCT_ID &&
             le16_to_cpu(udev->descriptor.idProduct) != USB_SX353_PRODUCT_ID)) {
-               dbg(DEBUG_ANY, "%s: unmatched ID - exiting", __func__);
+               gig_dbg(DEBUG_ANY, "%s: unmatched ID - exiting", __func__);
                return -ENODEV;
        }
 
        /* set required alternate setting */
        hostif = interface->cur_altsetting;
        if (hostif->desc.bAlternateSetting != 3) {
-               dbg(DEBUG_ANY,
-                   "%s: wrong alternate setting %d - trying to switch",
-                   __func__, hostif->desc.bAlternateSetting);
+               gig_dbg(DEBUG_ANY,
+                       "%s: wrong alternate setting %d - trying to switch",
+                       __func__, hostif->desc.bAlternateSetting);
                if (usb_set_interface(udev, hostif->desc.bInterfaceNumber, 3) < 0) {
-                       warn("usb_set_interface failed, device %d interface %d altsetting %d",
-                            udev->devnum, hostif->desc.bInterfaceNumber,
-                            hostif->desc.bAlternateSetting);
+                       dev_warn(&udev->dev, "usb_set_interface failed, "
+                                "device %d interface %d altsetting %d\n",
+                                udev->devnum, hostif->desc.bInterfaceNumber,
+                                hostif->desc.bAlternateSetting);
                        return -ENODEV;
                }
                hostif = interface->cur_altsetting;
@@ -2134,23 +2077,28 @@ static int gigaset_probe(struct usb_interface *interface,
        /* Reject application specific interfaces
         */
        if (hostif->desc.bInterfaceClass != 255) {
-               warn("%s: bInterfaceClass == %d",
-                    __func__, hostif->desc.bInterfaceClass);
+               dev_warn(&udev->dev, "%s: bInterfaceClass == %d\n",
+                        __func__, hostif->desc.bInterfaceClass);
                return -ENODEV;
        }
 
-       info("%s: Device matched (Vendor: 0x%x, Product: 0x%x)",
-            __func__, le16_to_cpu(udev->descriptor.idVendor),
-            le16_to_cpu(udev->descriptor.idProduct));
+       dev_info(&udev->dev,
+                "%s: Device matched (Vendor: 0x%x, Product: 0x%x)\n",
+                __func__, le16_to_cpu(udev->descriptor.idVendor),
+                le16_to_cpu(udev->descriptor.idProduct));
 
        cs = gigaset_getunassignedcs(driver);
        if (!cs) {
-               err("%s: no free cardstate", __func__);
+               dev_err(&udev->dev, "no free cardstate\n");
                return -ENODEV;
        }
        ucs = cs->hw.bas;
+
+       /* save off device structure ptrs for later use */
+       usb_get_dev(udev);
        ucs->udev = udev;
        ucs->interface = interface;
+       cs->dev = &interface->dev;
 
        /* allocate URBs:
         * - one for the interrupt pipe
@@ -2159,22 +2107,22 @@ static int gigaset_probe(struct usb_interface *interface,
         */
        ucs->urb_int_in = usb_alloc_urb(0, SLAB_KERNEL);
        if (!ucs->urb_int_in) {
-               err("No free urbs available");
+               dev_err(cs->dev, "no free urbs available\n");
                goto error;
        }
        ucs->urb_cmd_in = usb_alloc_urb(0, SLAB_KERNEL);
        if (!ucs->urb_cmd_in) {
-               err("No free urbs available");
+               dev_err(cs->dev, "no free urbs available\n");
                goto error;
        }
        ucs->urb_cmd_out = usb_alloc_urb(0, SLAB_KERNEL);
        if (!ucs->urb_cmd_out) {
-               err("No free urbs available");
+               dev_err(cs->dev, "no free urbs available\n");
                goto error;
        }
        ucs->urb_ctrl = usb_alloc_urb(0, SLAB_KERNEL);
        if (!ucs->urb_ctrl) {
-               err("No free urbs available");
+               dev_err(cs->dev, "no free urbs available\n");
                goto error;
        }
 
@@ -2184,7 +2132,7 @@ static int gigaset_probe(struct usb_interface *interface,
                        ubc->isoouturbs[i].urb =
                                usb_alloc_urb(BAS_NUMFRAMES, SLAB_KERNEL);
                        if (!ubc->isoouturbs[i].urb) {
-                               err("No free urbs available");
+                               dev_err(cs->dev, "no free urbs available\n");
                                goto error;
                        }
                }
@@ -2192,7 +2140,7 @@ static int gigaset_probe(struct usb_interface *interface,
                        ubc->isoinurbs[i] =
                                usb_alloc_urb(BAS_NUMFRAMES, SLAB_KERNEL);
                        if (!ubc->isoinurbs[i]) {
-                               err("No free urbs available");
+                               dev_err(cs->dev, "no free urbs available\n");
                                goto error;
                        }
                }
@@ -2204,13 +2152,14 @@ static int gigaset_probe(struct usb_interface *interface,
        /* Fill the interrupt urb and send it to the core */
        endpoint = &hostif->endpoint[0].desc;
        usb_fill_int_urb(ucs->urb_int_in, udev,
-                        usb_rcvintpipe(udev,
-                                       (endpoint->bEndpointAddress) & 0x0f),
-                        ucs->int_in_buf, 3, read_int_callback, cs,
-                        endpoint->bInterval);
+                        usb_rcvintpipe(udev,
+                                       (endpoint->bEndpointAddress) & 0x0f),
+                        ucs->int_in_buf, 3, read_int_callback, cs,
+                        endpoint->bInterval);
        ret = usb_submit_urb(ucs->urb_int_in, SLAB_KERNEL);
        if (ret) {
-               err("could not submit interrupt URB: %s", get_usb_statmsg(ret));
+               dev_err(cs->dev, "could not submit interrupt URB: %s\n",
+                       get_usb_statmsg(ret));
                goto error;
        }
 
@@ -2221,18 +2170,18 @@ static int gigaset_probe(struct usb_interface *interface,
        /* tell common part that the device is ready */
        if (startmode == SM_LOCKED)
                atomic_set(&cs->mstate, MS_LOCKED);
-       if (!gigaset_start(cs))
-               goto error;
 
        /* save address of controller structure */
        usb_set_intfdata(interface, cs);
 
-       /* set up device sysfs */
-       gigaset_init_dev_sysfs(interface);
+       if (!gigaset_start(cs))
+               goto error;
+
        return 0;
 
 error:
        freeurbs(cs);
+       usb_set_intfdata(interface, NULL);
        gigaset_unassign(cs);
        return -ENODEV;
 }
@@ -2245,23 +2194,22 @@ static void gigaset_disconnect(struct usb_interface *interface)
        struct cardstate *cs;
        struct bas_cardstate *ucs;
 
-       /* clear device sysfs */
-       gigaset_free_dev_sysfs(interface);
-
        cs = usb_get_intfdata(interface);
-       usb_set_intfdata(interface, NULL);
 
-       IFNULLRET(cs);
        ucs = cs->hw.bas;
-       IFNULLRET(ucs);
 
-       info("disconnecting GigaSet base");
+       dev_info(cs->dev, "disconnecting Gigaset base\n");
        gigaset_stop(cs);
        freeurbs(cs);
+       usb_set_intfdata(interface, NULL);
        kfree(ucs->rcvbuf);
        ucs->rcvbuf = NULL;
        ucs->rcvbuf_size = 0;
        atomic_set(&ucs->basstate, 0);
+       usb_put_dev(ucs->udev);
+       ucs->interface = NULL;
+       ucs->udev = NULL;
+       cs->dev = NULL;
        gigaset_unassign(cs);
 }
 
@@ -2293,13 +2241,14 @@ static int __init bas_gigaset_init(void)
 
        /* allocate memory for our driver state and intialize it */
        if ((driver = gigaset_initdriver(GIGASET_MINOR, GIGASET_MINORS,
-                                      GIGASET_MODULENAME, GIGASET_DEVNAME,
-                                      GIGASET_DEVFSNAME, &gigops,
-                                      THIS_MODULE)) == NULL)
+                                      GIGASET_MODULENAME, GIGASET_DEVNAME,
+                                      GIGASET_DEVFSNAME, &gigops,
+                                      THIS_MODULE)) == NULL)
                goto error;
 
        /* allocate memory for our device state and intialize it */
-       cardstate = gigaset_initcs(driver, 2, 0, 0, cidmode, GIGASET_MODULENAME);
+       cardstate = gigaset_initcs(driver, 2, 0, 0, cidmode,
+                                  GIGASET_MODULENAME);
        if (!cardstate)
                goto error;
 
@@ -2329,19 +2278,18 @@ error:  if (cardstate)
 static void __exit bas_gigaset_exit(void)
 {
        gigaset_blockdriver(driver); /* => probe will fail
-                                     * => no gigaset_start any more
-                                     */
+                                     * => no gigaset_start any more
+                                     */
 
        gigaset_shutdown(cardstate);
        /* from now on, no isdn callback should be possible */
 
        if (atomic_read(&cardstate->hw.bas->basstate) & BS_ATOPEN) {
-               dbg(DEBUG_ANY, "closing AT channel");
+               gig_dbg(DEBUG_ANY, "closing AT channel");
                if (req_submit(cardstate->bcs,
-                              HD_CLOSE_ATCHANNEL, 0, BAS_TIMEOUT) >= 0) {
-                       /* successfully submitted - wait for completion */
-                       //wait_event_interruptible(cs->initwait, !cs->hw.bas->pending);
-                       //FIXME need own wait queue? wakeup?
+                              HD_CLOSE_ATCHANNEL, 0, BAS_TIMEOUT) >= 0) {
+                       /* successfully submitted */
+                       //FIXME wait for completion?
                }
        }
 
index 64371995c1a97fa5b91943258fd3080817458ab9..749b3da1236e382e4ee2840f7d3e89da6bcd2e44 100644 (file)
@@ -1,7 +1,7 @@
 /*
  * Stuff used by all variants of the driver
  *
- * Copyright (c) 2001 by Stefan Eilers <Eilers.Stefan@epost.de>,
+ * Copyright (c) 2001 by Stefan Eilers,
  *                       Hansjoerg Lipp <hjlipp@web.de>,
  *                       Tilman Schmidt <tilman@imap.cc>.
  *
  *     published by the Free Software Foundation; either version 2 of
  *     the License, or (at your option) any later version.
  * =====================================================================
- * ToDo: ...
- * =====================================================================
- * Version: $Id: common.c,v 1.104.4.22 2006/02/04 18:28:16 hjlipp Exp $
- * =====================================================================
  */
 
 #include "gigaset.h"
@@ -23,7 +19,7 @@
 #include <linux/moduleparam.h>
 
 /* Version Information */
-#define DRIVER_AUTHOR "Hansjoerg Lipp <hjlipp@web.de>, Tilman Schmidt <tilman@imap.cc>, Stefan Eilers <Eilers.Stefan@epost.de>"
+#define DRIVER_AUTHOR "Hansjoerg Lipp <hjlipp@web.de>, Tilman Schmidt <tilman@imap.cc>, Stefan Eilers"
 #define DRIVER_DESC "Driver for Gigaset 307x"
 
 /* Module parameters */
@@ -32,21 +28,10 @@ EXPORT_SYMBOL_GPL(gigaset_debuglevel);
 module_param_named(debug, gigaset_debuglevel, int, S_IRUGO|S_IWUSR);
 MODULE_PARM_DESC(debug, "debug level");
 
-/*======================================================================
-  Prototypes of internal functions
- */
-
-//static void gigaset_process_response(int resp_code, int parameter,
-//                                     struct at_state_t *at_state,
-//                                     unsigned char ** pstring);
-static struct cardstate *alloc_cs(struct gigaset_driver *drv);
-static void free_cs(struct cardstate *cs);
-static void make_valid(struct cardstate *cs, unsigned mask);
-static void make_invalid(struct cardstate *cs, unsigned mask);
-
-#define VALID_MINOR       0x01
-#define VALID_ID          0x02
-#define ASSIGNED          0x04
+/* driver state flags */
+#define VALID_MINOR    0x01
+#define VALID_ID       0x02
+#define ASSIGNED       0x04
 
 /* bitwise byte inversion table */
 __u8 gigaset_invtab[256] = {
@@ -86,42 +71,40 @@ __u8 gigaset_invtab[256] = {
 EXPORT_SYMBOL_GPL(gigaset_invtab);
 
 void gigaset_dbg_buffer(enum debuglevel level, const unsigned char *msg,
-                        size_t len, const unsigned char *buf, int from_user)
+                       size_t len, const unsigned char *buf)
 {
        unsigned char outbuf[80];
-       unsigned char inbuf[80 - 1];
-       size_t numin;
-       const unsigned char *in;
+       unsigned char c;
        size_t space = sizeof outbuf - 1;
        unsigned char *out = outbuf;
+       size_t numin = len;
 
-       if (!from_user) {
-               in = buf;
-               numin = len;
-       } else {
-               numin = len < sizeof inbuf ? len : sizeof inbuf;
-               in = inbuf;
-               if (copy_from_user(inbuf, (const unsigned char __user *) buf, numin)) {
-                       strncpy(inbuf, "<FAULT>", sizeof inbuf);
-                       numin = sizeof "<FAULT>" - 1;
+       while (numin--) {
+               c = *buf++;
+               if (c == '~' || c == '^' || c == '\\') {
+                       if (!space--)
+                               break;
+                       *out++ = '\\';
                }
-       }
-
-       for (; numin && space; --numin, ++in) {
-               --space;
-               if (*in >= 32)
-                       *out++ = *in;
-               else {
+               if (c & 0x80) {
+                       if (!space--)
+                               break;
+                       *out++ = '~';
+                       c ^= 0x80;
+               }
+               if (c < 0x20 || c == 0x7f) {
+                       if (!space--)
+                               break;
                        *out++ = '^';
-                       if (space) {
-                               *out++ = '@' + *in;
-                               --space;
-                       }
+                       c ^= 0x40;
                }
+               if (!space--)
+                       break;
+               *out++ = c;
        }
        *out = 0;
 
-       dbg(level, "%s (%u bytes): %s", msg, (unsigned) len, outbuf);
+       gig_dbg(level, "%s (%u bytes): %s", msg, (unsigned) len, outbuf);
 }
 EXPORT_SYMBOL_GPL(gigaset_dbg_buffer);
 
@@ -146,11 +129,6 @@ int gigaset_enterconfigmode(struct cardstate *cs)
 {
        int i, r;
 
-       if (!atomic_read(&cs->connected)) {
-               err("not connected!");
-               return -1;
-       }
-
        cs->control_state = TIOCM_RTS; //FIXME
 
        r = setflags(cs, TIOCM_DTR, 200);
@@ -174,7 +152,7 @@ int gigaset_enterconfigmode(struct cardstate *cs)
        return 0;
 
 error:
-       err("error %d on setuartbits!\n", -r);
+       dev_err(cs->dev, "error %d on setuartbits\n", -r);
        cs->control_state = TIOCM_RTS|TIOCM_DTR; // FIXME is this a good value?
        cs->ops->set_modem_ctrl(cs, 0, TIOCM_RTS|TIOCM_DTR);
 
@@ -187,13 +165,13 @@ static int test_timeout(struct at_state_t *at_state)
                return 0;
 
        if (--at_state->timer_expires) {
-               dbg(DEBUG_MCMD, "decreased timer of %p to %lu",
-                   at_state, at_state->timer_expires);
+               gig_dbg(DEBUG_MCMD, "decreased timer of %p to %lu",
+                       at_state, at_state->timer_expires);
                return 0;
        }
 
        if (!gigaset_add_event(at_state->cs, at_state, EV_TIMEOUT, NULL,
-                              atomic_read(&at_state->timer_index), NULL)) {
+                              at_state->timer_index, NULL)) {
                //FIXME what should we do?
        }
 
@@ -221,10 +199,10 @@ static void timer_tick(unsigned long data)
                if (test_timeout(at_state))
                        timeout = 1;
 
-       if (atomic_read(&cs->running)) {
-               mod_timer(&cs->timer, jiffies + GIG_TICK);
+       if (cs->running) {
+               mod_timer(&cs->timer, jiffies + msecs_to_jiffies(GIG_TICK));
                if (timeout) {
-                       dbg(DEBUG_CMD, "scheduling timeout");
+                       gig_dbg(DEBUG_CMD, "scheduling timeout");
                        tasklet_schedule(&cs->event_tasklet);
                }
        }
@@ -238,13 +216,14 @@ int gigaset_get_channel(struct bc_state *bcs)
 
        spin_lock_irqsave(&bcs->cs->lock, flags);
        if (bcs->use_count) {
-               dbg(DEBUG_ANY, "could not allocate channel %d", bcs->channel);
+               gig_dbg(DEBUG_ANY, "could not allocate channel %d",
+                       bcs->channel);
                spin_unlock_irqrestore(&bcs->cs->lock, flags);
                return 0;
        }
        ++bcs->use_count;
        bcs->busy = 1;
-       dbg(DEBUG_ANY, "allocated channel %d", bcs->channel);
+       gig_dbg(DEBUG_ANY, "allocated channel %d", bcs->channel);
        spin_unlock_irqrestore(&bcs->cs->lock, flags);
        return 1;
 }
@@ -255,13 +234,13 @@ void gigaset_free_channel(struct bc_state *bcs)
 
        spin_lock_irqsave(&bcs->cs->lock, flags);
        if (!bcs->busy) {
-               dbg(DEBUG_ANY, "could not free channel %d", bcs->channel);
+               gig_dbg(DEBUG_ANY, "could not free channel %d", bcs->channel);
                spin_unlock_irqrestore(&bcs->cs->lock, flags);
                return;
        }
        --bcs->use_count;
        bcs->busy = 0;
-       dbg(DEBUG_ANY, "freed channel %d", bcs->channel);
+       gig_dbg(DEBUG_ANY, "freed channel %d", bcs->channel);
        spin_unlock_irqrestore(&bcs->cs->lock, flags);
 }
 
@@ -274,14 +253,14 @@ int gigaset_get_channels(struct cardstate *cs)
        for (i = 0; i < cs->channels; ++i)
                if (cs->bcs[i].use_count) {
                        spin_unlock_irqrestore(&cs->lock, flags);
-                       dbg(DEBUG_ANY, "could not allocated all channels");
+                       gig_dbg(DEBUG_ANY, "could not allocate all channels");
                        return 0;
                }
        for (i = 0; i < cs->channels; ++i)
                ++cs->bcs[i].use_count;
        spin_unlock_irqrestore(&cs->lock, flags);
 
-       dbg(DEBUG_ANY, "allocated all channels");
+       gig_dbg(DEBUG_ANY, "allocated all channels");
 
        return 1;
 }
@@ -291,7 +270,7 @@ void gigaset_free_channels(struct cardstate *cs)
        unsigned long flags;
        int i;
 
-       dbg(DEBUG_ANY, "unblocking all channels");
+       gig_dbg(DEBUG_ANY, "unblocking all channels");
        spin_lock_irqsave(&cs->lock, flags);
        for (i = 0; i < cs->channels; ++i)
                --cs->bcs[i].use_count;
@@ -303,7 +282,7 @@ void gigaset_block_channels(struct cardstate *cs)
        unsigned long flags;
        int i;
 
-       dbg(DEBUG_ANY, "blocking all channels");
+       gig_dbg(DEBUG_ANY, "blocking all channels");
        spin_lock_irqsave(&cs->lock, flags);
        for (i = 0; i < cs->channels; ++i)
                ++cs->bcs[i].use_count;
@@ -314,25 +293,27 @@ static void clear_events(struct cardstate *cs)
 {
        struct event_t *ev;
        unsigned head, tail;
+       unsigned long flags;
 
-       /* no locking needed (no reader/writer allowed) */
+       spin_lock_irqsave(&cs->ev_lock, flags);
 
-       head = atomic_read(&cs->ev_head);
-       tail = atomic_read(&cs->ev_tail);
+       head = cs->ev_head;
+       tail = cs->ev_tail;
 
        while (tail != head) {
                ev = cs->events + head;
                kfree(ev->ptr);
-
                head = (head + 1) % MAX_EVENTS;
        }
 
-       atomic_set(&cs->ev_head, tail);
+       cs->ev_head = tail;
+
+       spin_unlock_irqrestore(&cs->ev_lock, flags);
 }
 
 struct event_t *gigaset_add_event(struct cardstate *cs,
-                                  struct at_state_t *at_state, int type,
-                                  void *ptr, int parameter, void *arg)
+                                 struct at_state_t *at_state, int type,
+                                 void *ptr, int parameter, void *arg)
 {
        unsigned long flags;
        unsigned next, tail;
@@ -340,9 +321,9 @@ struct event_t *gigaset_add_event(struct cardstate *cs,
 
        spin_lock_irqsave(&cs->ev_lock, flags);
 
-       tail = atomic_read(&cs->ev_tail);
+       tail = cs->ev_tail;
        next = (tail + 1) % MAX_EVENTS;
-       if (unlikely(next == atomic_read(&cs->ev_head)))
+       if (unlikely(next == cs->ev_head))
                err("event queue full");
        else {
                event = cs->events + tail;
@@ -352,7 +333,7 @@ struct event_t *gigaset_add_event(struct cardstate *cs,
                event->ptr = ptr;
                event->arg = arg;
                event->parameter = parameter;
-               atomic_set(&cs->ev_tail, next);
+               cs->ev_tail = next;
        }
 
        spin_unlock_irqrestore(&cs->ev_lock, flags);
@@ -391,14 +372,14 @@ static void gigaset_freebcs(struct bc_state *bcs)
 {
        int i;
 
-       dbg(DEBUG_INIT, "freeing bcs[%d]->hw", bcs->channel);
+       gig_dbg(DEBUG_INIT, "freeing bcs[%d]->hw", bcs->channel);
        if (!bcs->cs->ops->freebcshw(bcs)) {
-               dbg(DEBUG_INIT, "failed");
+               gig_dbg(DEBUG_INIT, "failed");
        }
 
-       dbg(DEBUG_INIT, "clearing bcs[%d]->at_state", bcs->channel);
+       gig_dbg(DEBUG_INIT, "clearing bcs[%d]->at_state", bcs->channel);
        clear_at_state(&bcs->at_state);
-       dbg(DEBUG_INIT, "freeing bcs[%d]->skb", bcs->channel);
+       gig_dbg(DEBUG_INIT, "freeing bcs[%d]->skb", bcs->channel);
 
        if (bcs->skb)
                dev_kfree_skb(bcs->skb);
@@ -408,6 +389,52 @@ static void gigaset_freebcs(struct bc_state *bcs)
        }
 }
 
+static struct cardstate *alloc_cs(struct gigaset_driver *drv)
+{
+       unsigned long flags;
+       unsigned i;
+       static struct cardstate *ret = NULL;
+
+       spin_lock_irqsave(&drv->lock, flags);
+       for (i = 0; i < drv->minors; ++i) {
+               if (!(drv->flags[i] & VALID_MINOR)) {
+                       drv->flags[i] = VALID_MINOR;
+                       ret = drv->cs + i;
+               }
+               if (ret)
+                       break;
+       }
+       spin_unlock_irqrestore(&drv->lock, flags);
+       return ret;
+}
+
+static void free_cs(struct cardstate *cs)
+{
+       unsigned long flags;
+       struct gigaset_driver *drv = cs->driver;
+       spin_lock_irqsave(&drv->lock, flags);
+       drv->flags[cs->minor_index] = 0;
+       spin_unlock_irqrestore(&drv->lock, flags);
+}
+
+static void make_valid(struct cardstate *cs, unsigned mask)
+{
+       unsigned long flags;
+       struct gigaset_driver *drv = cs->driver;
+       spin_lock_irqsave(&drv->lock, flags);
+       drv->flags[cs->minor_index] |= mask;
+       spin_unlock_irqrestore(&drv->lock, flags);
+}
+
+static void make_invalid(struct cardstate *cs, unsigned mask)
+{
+       unsigned long flags;
+       struct gigaset_driver *drv = cs->driver;
+       spin_lock_irqsave(&drv->lock, flags);
+       drv->flags[cs->minor_index] &= ~mask;
+       spin_unlock_irqrestore(&drv->lock, flags);
+}
+
 void gigaset_freecs(struct cardstate *cs)
 {
        int i;
@@ -416,7 +443,7 @@ void gigaset_freecs(struct cardstate *cs)
        if (!cs)
                return;
 
-       down(&cs->sem);
+       mutex_lock(&cs->mutex);
 
        if (!cs->bcs)
                goto f_cs;
@@ -424,8 +451,9 @@ void gigaset_freecs(struct cardstate *cs)
                goto f_bcs;
 
        spin_lock_irqsave(&cs->lock, flags);
-       atomic_set(&cs->running, 0);
-       spin_unlock_irqrestore(&cs->lock, flags); /* event handler and timer are not rescheduled below */
+       cs->running = 0;
+       spin_unlock_irqrestore(&cs->lock, flags); /* event handler and timer are
+                                                    not rescheduled below */
 
        tasklet_kill(&cs->event_tasklet);
        del_timer_sync(&cs->timer);
@@ -434,7 +462,7 @@ void gigaset_freecs(struct cardstate *cs)
        default:
                gigaset_if_free(cs);
 
-               dbg(DEBUG_INIT, "clearing hw");
+               gig_dbg(DEBUG_INIT, "clearing hw");
                cs->ops->freecshw(cs);
 
                //FIXME cmdbuf
@@ -443,36 +471,36 @@ void gigaset_freecs(struct cardstate *cs)
        case 2: /* error in initcshw */
                /* Deregister from LL */
                make_invalid(cs, VALID_ID);
-               dbg(DEBUG_INIT, "clearing iif");
+               gig_dbg(DEBUG_INIT, "clearing iif");
                gigaset_i4l_cmd(cs, ISDN_STAT_UNLOAD);
 
                /* fall through */
        case 1: /* error when regestering to LL */
-               dbg(DEBUG_INIT, "clearing at_state");
+               gig_dbg(DEBUG_INIT, "clearing at_state");
                clear_at_state(&cs->at_state);
                dealloc_at_states(cs);
 
                /* fall through */
        case 0: /* error in one call to initbcs */
                for (i = 0; i < cs->channels; ++i) {
-                       dbg(DEBUG_INIT, "clearing bcs[%d]", i);
+                       gig_dbg(DEBUG_INIT, "clearing bcs[%d]", i);
                        gigaset_freebcs(cs->bcs + i);
                }
 
                clear_events(cs);
-               dbg(DEBUG_INIT, "freeing inbuf");
+               gig_dbg(DEBUG_INIT, "freeing inbuf");
                kfree(cs->inbuf);
        }
-f_bcs: dbg(DEBUG_INIT, "freeing bcs[]");
+f_bcs: gig_dbg(DEBUG_INIT, "freeing bcs[]");
        kfree(cs->bcs);
-f_cs:  dbg(DEBUG_INIT, "freeing cs");
-       up(&cs->sem);
+f_cs:  gig_dbg(DEBUG_INIT, "freeing cs");
+       mutex_unlock(&cs->mutex);
        free_cs(cs);
 }
 EXPORT_SYMBOL_GPL(gigaset_freecs);
 
 void gigaset_at_init(struct at_state_t *at_state, struct bc_state *bcs,
-                     struct cardstate *cs, int cid)
+                    struct cardstate *cs, int cid)
 {
        int i;
 
@@ -482,8 +510,8 @@ void gigaset_at_init(struct at_state_t *at_state, struct bc_state *bcs,
        at_state->pending_commands = 0;
        at_state->timer_expires = 0;
        at_state->timer_active = 0;
-       atomic_set(&at_state->timer_index, 0);
-       atomic_set(&at_state->seq_index, 0);
+       at_state->timer_index = 0;
+       at_state->seq_index = 0;
        at_state->ConState = 0;
        for (i = 0; i < STR_NUM; ++i)
                at_state->str_var[i] = NULL;
@@ -501,7 +529,7 @@ void gigaset_at_init(struct at_state_t *at_state, struct bc_state *bcs,
 
 
 static void gigaset_inbuf_init(struct inbuf_t *inbuf, struct bc_state *bcs,
-                               struct cardstate *cs, int inputstate)
+                              struct cardstate *cs, int inputstate)
 /* inbuf->read must be allocated before! */
 {
        atomic_set(&inbuf->head, 0);
@@ -512,9 +540,50 @@ static void gigaset_inbuf_init(struct inbuf_t *inbuf, struct bc_state *bcs,
        inbuf->inputstate = inputstate;
 }
 
+/* append received bytes to inbuf */
+int gigaset_fill_inbuf(struct inbuf_t *inbuf, const unsigned char *src,
+                      unsigned numbytes)
+{
+       unsigned n, head, tail, bytesleft;
+
+       gig_dbg(DEBUG_INTR, "received %u bytes", numbytes);
+
+       if (!numbytes)
+               return 0;
+
+       bytesleft = numbytes;
+       tail = atomic_read(&inbuf->tail);
+       head = atomic_read(&inbuf->head);
+       gig_dbg(DEBUG_INTR, "buffer state: %u -> %u", head, tail);
+
+       while (bytesleft) {
+               if (head > tail)
+                       n = head - 1 - tail;
+               else if (head == 0)
+                       n = (RBUFSIZE-1) - tail;
+               else
+                       n = RBUFSIZE - tail;
+               if (!n) {
+                       dev_err(inbuf->cs->dev,
+                               "buffer overflow (%u bytes lost)", bytesleft);
+                       break;
+               }
+               if (n > bytesleft)
+                       n = bytesleft;
+               memcpy(inbuf->data + tail, src, n);
+               bytesleft -= n;
+               tail = (tail + n) % RBUFSIZE;
+               src += n;
+       }
+       gig_dbg(DEBUG_INTR, "setting tail to %u", tail);
+       atomic_set(&inbuf->tail, tail);
+       return numbytes != bytesleft;
+}
+EXPORT_SYMBOL_GPL(gigaset_fill_inbuf);
+
 /* Initialize the b-channel structure */
 static struct bc_state *gigaset_initbcs(struct bc_state *bcs,
-                                        struct cardstate *cs, int channel)
+                                       struct cardstate *cs, int channel)
 {
        int i;
 
@@ -526,7 +595,7 @@ static struct bc_state *gigaset_initbcs(struct bc_state *bcs,
        bcs->trans_down = 0;
        bcs->trans_up = 0;
 
-       dbg(DEBUG_INIT, "setting up bcs[%d]->at_state", channel);
+       gig_dbg(DEBUG_INIT, "setting up bcs[%d]->at_state", channel);
        gigaset_at_init(&bcs->at_state, bcs, cs, -1);
 
        bcs->rcvbytes = 0;
@@ -535,7 +604,7 @@ static struct bc_state *gigaset_initbcs(struct bc_state *bcs,
        bcs->emptycount = 0;
 #endif
 
-       dbg(DEBUG_INIT, "allocating bcs[%d]->skb", channel);
+       gig_dbg(DEBUG_INIT, "allocating bcs[%d]->skb", channel);
        bcs->fcs = PPP_INITFCS;
        bcs->inputstate = 0;
        if (cs->ignoreframes) {
@@ -544,7 +613,7 @@ static struct bc_state *gigaset_initbcs(struct bc_state *bcs,
        } else if ((bcs->skb = dev_alloc_skb(SBUFSIZE + HW_HDR_LEN)) != NULL)
                skb_reserve(bcs->skb, HW_HDR_LEN);
        else {
-               warn("could not allocate skb");
+               dev_warn(cs->dev, "could not allocate skb\n");
                bcs->inputstate |= INS_skip_frame;
        }
 
@@ -559,14 +628,13 @@ static struct bc_state *gigaset_initbcs(struct bc_state *bcs,
        for (i = 0; i < AT_NUM; ++i)
                bcs->commands[i] = NULL;
 
-       dbg(DEBUG_INIT, "  setting up bcs[%d]->hw", channel);
+       gig_dbg(DEBUG_INIT, "  setting up bcs[%d]->hw", channel);
        if (cs->ops->initbcshw(bcs))
                return bcs;
 
-//error:
-       dbg(DEBUG_INIT, "  failed");
+       gig_dbg(DEBUG_INIT, "  failed");
 
-       dbg(DEBUG_INIT, "  freeing bcs[%d]->skb", channel);
+       gig_dbg(DEBUG_INIT, "  freeing bcs[%d]->skb", channel);
        if (bcs->skb)
                dev_kfree_skb(bcs->skb);
 
@@ -578,9 +646,10 @@ static struct bc_state *gigaset_initbcs(struct bc_state *bcs,
  * Calls hardware dependent gigaset_initcshw() function
  * Calls B channel initialization function gigaset_initbcs() for each B channel
  * parameters:
- *      drv            hardware driver the device belongs to
+ *     drv             hardware driver the device belongs to
  *     channels        number of B channels supported by device
- *     onechannel      !=0: B channel data and AT commands share one communication channel
+ *     onechannel      !=0: B channel data and AT commands share one
+ *                          communication channel
  *                     ==0: B channels have separate communication channels
  *     ignoreframes    number of frames to ignore after setting up B channel
  *     cidmode         !=0: start in CallID mode
@@ -593,17 +662,18 @@ struct cardstate *gigaset_initcs(struct gigaset_driver *drv, int channels,
                                 int cidmode, const char *modulename)
 {
        struct cardstate *cs = NULL;
+       unsigned long flags;
        int i;
 
-       dbg(DEBUG_INIT, "allocating cs");
+       gig_dbg(DEBUG_INIT, "allocating cs");
        cs = alloc_cs(drv);
        if (!cs)
                goto error;
-       dbg(DEBUG_INIT, "allocating bcs[0..%d]", channels - 1);
+       gig_dbg(DEBUG_INIT, "allocating bcs[0..%d]", channels - 1);
        cs->bcs = kmalloc(channels * sizeof(struct bc_state), GFP_KERNEL);
        if (!cs->bcs)
                goto error;
-       dbg(DEBUG_INIT, "allocating inbuf");
+       gig_dbg(DEBUG_INIT, "allocating inbuf");
        cs->inbuf = kmalloc(sizeof(struct inbuf_t), GFP_KERNEL);
        if (!cs->inbuf)
                goto error;
@@ -613,19 +683,23 @@ struct cardstate *gigaset_initcs(struct gigaset_driver *drv, int channels,
        cs->onechannel = onechannel;
        cs->ignoreframes = ignoreframes;
        INIT_LIST_HEAD(&cs->temp_at_states);
-       atomic_set(&cs->running, 0);
+       cs->running = 0;
        init_timer(&cs->timer); /* clear next & prev */
        spin_lock_init(&cs->ev_lock);
-       atomic_set(&cs->ev_tail, 0);
-       atomic_set(&cs->ev_head, 0);
-       init_MUTEX_LOCKED(&cs->sem);
-       tasklet_init(&cs->event_tasklet, &gigaset_handle_event, (unsigned long) cs);
+       cs->ev_tail = 0;
+       cs->ev_head = 0;
+       mutex_init(&cs->mutex);
+       mutex_lock(&cs->mutex);
+
+       tasklet_init(&cs->event_tasklet, &gigaset_handle_event,
+                    (unsigned long) cs);
        atomic_set(&cs->commands_pending, 0);
        cs->cur_at_seq = 0;
        cs->gotfwver = -1;
        cs->open_count = 0;
+       cs->dev = NULL;
        cs->tty = NULL;
-       atomic_set(&cs->cidmode, cidmode != 0);
+       cs->cidmode = cidmode != 0;
 
        //if(onechannel) { //FIXME
                cs->tabnocid = gigaset_tab_nocid_m10x;
@@ -642,50 +716,43 @@ struct cardstate *gigaset_initcs(struct gigaset_driver *drv, int channels,
        atomic_set(&cs->mstate, MS_UNINITIALIZED);
 
        for (i = 0; i < channels; ++i) {
-               dbg(DEBUG_INIT, "setting up bcs[%d].read", i);
+               gig_dbg(DEBUG_INIT, "setting up bcs[%d].read", i);
                if (!gigaset_initbcs(cs->bcs + i, cs, i))
                        goto error;
        }
 
        ++cs->cs_init;
 
-       dbg(DEBUG_INIT, "setting up at_state");
+       gig_dbg(DEBUG_INIT, "setting up at_state");
        spin_lock_init(&cs->lock);
        gigaset_at_init(&cs->at_state, NULL, cs, 0);
        cs->dle = 0;
        cs->cbytes = 0;
 
-       dbg(DEBUG_INIT, "setting up inbuf");
+       gig_dbg(DEBUG_INIT, "setting up inbuf");
        if (onechannel) {                       //FIXME distinction necessary?
                gigaset_inbuf_init(cs->inbuf, cs->bcs, cs, INS_command);
        } else
                gigaset_inbuf_init(cs->inbuf, NULL,    cs, INS_command);
 
-       atomic_set(&cs->connected, 0);
+       cs->connected = 0;
+       cs->isdn_up = 0;
 
-       dbg(DEBUG_INIT, "setting up cmdbuf");
+       gig_dbg(DEBUG_INIT, "setting up cmdbuf");
        cs->cmdbuf = cs->lastcmdbuf = NULL;
        spin_lock_init(&cs->cmdlock);
        cs->curlen = 0;
        cs->cmdbytes = 0;
 
-       /*
-        * Tell the ISDN4Linux subsystem (the LL) that
-        * a driver for a USB-Device is available !
-        * If this is done, "isdnctrl" is able to bind a device for this driver even
-        * if no physical usb-device is currently connected.
-        * But this device will just be accessable if a physical USB device is connected
-        * (via "gigaset_probe") .
-        */
-       dbg(DEBUG_INIT, "setting up iif");
+       gig_dbg(DEBUG_INIT, "setting up iif");
        if (!gigaset_register_to_LL(cs, modulename)) {
-               err("register_isdn=>error");
+               err("register_isdn failed");
                goto error;
        }
 
        make_valid(cs, VALID_ID);
        ++cs->cs_init;
-       dbg(DEBUG_INIT, "setting up hw");
+       gig_dbg(DEBUG_INIT, "setting up hw");
        if (!cs->ops->initcshw(cs))
                goto error;
 
@@ -693,27 +760,29 @@ struct cardstate *gigaset_initcs(struct gigaset_driver *drv, int channels,
 
        gigaset_if_init(cs);
 
-       atomic_set(&cs->running, 1);
-       cs->timer.data = (unsigned long) cs;
-       cs->timer.function = timer_tick;
-       cs->timer.expires = jiffies + GIG_TICK;
+       spin_lock_irqsave(&cs->lock, flags);
+       cs->running = 1;
+       spin_unlock_irqrestore(&cs->lock, flags);
+       setup_timer(&cs->timer, timer_tick, (unsigned long) cs);
+       cs->timer.expires = jiffies + msecs_to_jiffies(GIG_TICK);
        /* FIXME: can jiffies increase too much until the timer is added?
         * Same problem(?) with mod_timer() in timer_tick(). */
        add_timer(&cs->timer);
 
-       dbg(DEBUG_INIT, "cs initialized!");
-       up(&cs->sem);
+       gig_dbg(DEBUG_INIT, "cs initialized");
+       mutex_unlock(&cs->mutex);
        return cs;
 
 error: if (cs)
-               up(&cs->sem);
-       dbg(DEBUG_INIT, "failed");
+               mutex_unlock(&cs->mutex);
+       gig_dbg(DEBUG_INIT, "failed");
        gigaset_freecs(cs);
        return NULL;
 }
 EXPORT_SYMBOL_GPL(gigaset_initcs);
 
-/* ReInitialize the b-channel structure */ /* e.g. called on hangup, disconnect */
+/* ReInitialize the b-channel structure */
+/* e.g. called on hangup, disconnect */
 void gigaset_bcs_reinit(struct bc_state *bcs)
 {
        struct sk_buff *skb;
@@ -723,12 +792,12 @@ void gigaset_bcs_reinit(struct bc_state *bcs)
        while ((skb = skb_dequeue(&bcs->squeue)) != NULL)
                dev_kfree_skb(skb);
 
-       spin_lock_irqsave(&cs->lock, flags); //FIXME
+       spin_lock_irqsave(&cs->lock, flags);
        clear_at_state(&bcs->at_state);
        bcs->at_state.ConState = 0;
        bcs->at_state.timer_active = 0;
        bcs->at_state.timer_expires = 0;
-       bcs->at_state.cid = -1;                     /* No CID defined */
+       bcs->at_state.cid = -1;                 /* No CID defined */
        spin_unlock_irqrestore(&cs->lock, flags);
 
        bcs->inputstate = 0;
@@ -803,11 +872,14 @@ static void cleanup_cs(struct cardstate *cs)
 
 int gigaset_start(struct cardstate *cs)
 {
-       if (down_interruptible(&cs->sem))
+       unsigned long flags;
+
+       if (mutex_lock_interruptible(&cs->mutex))
                return 0;
-       //info("USB device for Gigaset 307x now attached to Dev %d", ucs->minor);
 
-       atomic_set(&cs->connected, 1);
+       spin_lock_irqsave(&cs->lock, flags);
+       cs->connected = 1;
+       spin_unlock_irqrestore(&cs->lock, flags);
 
        if (atomic_read(&cs->mstate) != MS_LOCKED) {
                cs->ops->set_modem_ctrl(cs, 0, TIOCM_DTR|TIOCM_RTS);
@@ -826,23 +898,26 @@ int gigaset_start(struct cardstate *cs)
                goto error;
        }
 
-       dbg(DEBUG_CMD, "scheduling START");
+       gig_dbg(DEBUG_CMD, "scheduling START");
        gigaset_schedule_event(cs);
 
        wait_event(cs->waitqueue, !cs->waiting);
 
-       up(&cs->sem);
+       /* set up device sysfs */
+       gigaset_init_dev_sysfs(cs);
+
+       mutex_unlock(&cs->mutex);
        return 1;
 
 error:
-       up(&cs->sem);
+       mutex_unlock(&cs->mutex);
        return 0;
 }
 EXPORT_SYMBOL_GPL(gigaset_start);
 
 void gigaset_shutdown(struct cardstate *cs)
 {
-       down(&cs->sem);
+       mutex_lock(&cs->mutex);
 
        cs->waiting = 1;
 
@@ -851,11 +926,11 @@ void gigaset_shutdown(struct cardstate *cs)
                goto exit;
        }
 
-       dbg(DEBUG_CMD, "scheduling SHUTDOWN");
+       gig_dbg(DEBUG_CMD, "scheduling SHUTDOWN");
        gigaset_schedule_event(cs);
 
        if (wait_event_interruptible(cs->waitqueue, !cs->waiting)) {
-               warn("aborted");
+               warn("%s: aborted", __func__);
                //FIXME
        }
 
@@ -872,15 +947,13 @@ void gigaset_shutdown(struct cardstate *cs)
        cleanup_cs(cs);
 
 exit:
-       up(&cs->sem);
+       mutex_unlock(&cs->mutex);
 }
 EXPORT_SYMBOL_GPL(gigaset_shutdown);
 
 void gigaset_stop(struct cardstate *cs)
 {
-       down(&cs->sem);
-
-       atomic_set(&cs->connected, 0);
+       mutex_lock(&cs->mutex);
 
        cs->waiting = 1;
 
@@ -889,21 +962,21 @@ void gigaset_stop(struct cardstate *cs)
                goto exit;
        }
 
-       dbg(DEBUG_CMD, "scheduling STOP");
+       gig_dbg(DEBUG_CMD, "scheduling STOP");
        gigaset_schedule_event(cs);
 
        if (wait_event_interruptible(cs->waitqueue, !cs->waiting)) {
-               warn("aborted");
+               warn("%s: aborted", __func__);
                //FIXME
        }
 
-       /* Tell the LL that the device is not available .. */
-       gigaset_i4l_cmd(cs, ISDN_STAT_STOP); // FIXME move to event layer?
+       /* clear device sysfs */
+       gigaset_free_dev_sysfs(cs);
 
        cleanup_cs(cs);
 
 exit:
-       up(&cs->sem);
+       mutex_unlock(&cs->mutex);
 }
 EXPORT_SYMBOL_GPL(gigaset_stop);
 
@@ -947,31 +1020,25 @@ void gigaset_debugdrivers(void)
 
        spin_lock_irqsave(&driver_lock, flags);
        list_for_each_entry(drv, &drivers, list) {
-               dbg(DEBUG_DRIVER, "driver %p", drv);
+               gig_dbg(DEBUG_DRIVER, "driver %p", drv);
                spin_lock(&drv->lock);
                for (i = 0; i < drv->minors; ++i) {
-                       dbg(DEBUG_DRIVER, "  index %u", i);
-                       dbg(DEBUG_DRIVER, "    flags 0x%02x", drv->flags[i]);
+                       gig_dbg(DEBUG_DRIVER, "  index %u", i);
+                       gig_dbg(DEBUG_DRIVER, "    flags 0x%02x",
+                               drv->flags[i]);
                        cs = drv->cs + i;
-                       dbg(DEBUG_DRIVER, "    cardstate %p", cs);
-                       dbg(DEBUG_DRIVER, "    minor_index %u", cs->minor_index);
-                       dbg(DEBUG_DRIVER, "    driver %p", cs->driver);
-                       dbg(DEBUG_DRIVER, "    i4l id %d", cs->myid);
+                       gig_dbg(DEBUG_DRIVER, "    cardstate %p", cs);
+                       gig_dbg(DEBUG_DRIVER, "    minor_index %u",
+                               cs->minor_index);
+                       gig_dbg(DEBUG_DRIVER, "    driver %p", cs->driver);
+                       gig_dbg(DEBUG_DRIVER, "    i4l id %d", cs->myid);
                }
                spin_unlock(&drv->lock);
        }
        spin_unlock_irqrestore(&driver_lock, flags);
 }
-EXPORT_SYMBOL_GPL(gigaset_debugdrivers);
-
-struct cardstate *gigaset_get_cs_by_tty(struct tty_struct *tty)
-{
-       if (tty->index < 0 || tty->index >= tty->driver->num)
-               return NULL;
-       return gigaset_get_cs_by_minor(tty->index + tty->driver->minor_start);
-}
 
-struct cardstate *gigaset_get_cs_by_minor(unsigned minor)
+static struct cardstate *gigaset_get_cs_by_minor(unsigned minor)
 {
        unsigned long flags;
        static struct cardstate *ret = NULL;
@@ -994,6 +1061,13 @@ struct cardstate *gigaset_get_cs_by_minor(unsigned minor)
        return ret;
 }
 
+struct cardstate *gigaset_get_cs_by_tty(struct tty_struct *tty)
+{
+       if (tty->index < 0 || tty->index >= tty->driver->num)
+               return NULL;
+       return gigaset_get_cs_by_minor(tty->index + tty->driver->minor_start);
+}
+
 void gigaset_freedriver(struct gigaset_driver *drv)
 {
        unsigned long flags;
@@ -1014,20 +1088,20 @@ EXPORT_SYMBOL_GPL(gigaset_freedriver);
 /* gigaset_initdriver
  * Allocate and initialize gigaset_driver structure. Initialize interface.
  * parameters:
- *      minor           First minor number
- *      minors          Number of minors this driver can handle
- *      procname        Name of the driver (e.g. for /proc/tty/drivers, path in /proc/driver)
- *      devname         Name of the device files (prefix without minor number)
- *      devfsname       Devfs name of the device files without %d
+ *     minor           First minor number
+ *     minors          Number of minors this driver can handle
+ *     procname        Name of the driver
+ *     devname         Name of the device files (prefix without minor number)
+ *     devfsname       Devfs name of the device files without %d
  * return value:
- *      Pointer to the gigaset_driver structure on success, NULL on failure.
+ *     Pointer to the gigaset_driver structure on success, NULL on failure.
  */
 struct gigaset_driver *gigaset_initdriver(unsigned minor, unsigned minors,
-                                          const char *procname,
-                                          const char *devname,
-                                          const char *devfsname,
-                                          const struct gigaset_ops *ops,
-                                          struct module *owner)
+                                         const char *procname,
+                                         const char *devname,
+                                         const char *devfsname,
+                                         const struct gigaset_ops *ops,
+                                         struct module *owner)
 {
        struct gigaset_driver *drv;
        unsigned long flags;
@@ -1036,8 +1110,9 @@ struct gigaset_driver *gigaset_initdriver(unsigned minor, unsigned minors,
        drv = kmalloc(sizeof *drv, GFP_KERNEL);
        if (!drv)
                return NULL;
+
        if (!try_module_get(owner))
-               return NULL;
+               goto out1;
 
        drv->cs = NULL;
        drv->have_tty = 0;
@@ -1051,10 +1126,11 @@ struct gigaset_driver *gigaset_initdriver(unsigned minor, unsigned minors,
 
        drv->cs = kmalloc(minors * sizeof *drv->cs, GFP_KERNEL);
        if (!drv->cs)
-               goto out1;
+               goto out2;
+
        drv->flags = kmalloc(minors * sizeof *drv->flags, GFP_KERNEL);
        if (!drv->flags)
-               goto out2;
+               goto out3;
 
        for (i = 0; i < minors; ++i) {
                drv->flags[i] = 0;
@@ -1071,61 +1147,16 @@ struct gigaset_driver *gigaset_initdriver(unsigned minor, unsigned minors,
 
        return drv;
 
-out2:
+out3:
        kfree(drv->cs);
+out2:
+       module_put(owner);
 out1:
        kfree(drv);
-       module_put(owner);
        return NULL;
 }
 EXPORT_SYMBOL_GPL(gigaset_initdriver);
 
-static struct cardstate *alloc_cs(struct gigaset_driver *drv)
-{
-       unsigned long flags;
-       unsigned i;
-       static struct cardstate *ret = NULL;
-
-       spin_lock_irqsave(&drv->lock, flags);
-       for (i = 0; i < drv->minors; ++i) {
-               if (!(drv->flags[i] & VALID_MINOR)) {
-                       drv->flags[i] = VALID_MINOR;
-                       ret = drv->cs + i;
-               }
-               if (ret)
-                       break;
-       }
-       spin_unlock_irqrestore(&drv->lock, flags);
-       return ret;
-}
-
-static void free_cs(struct cardstate *cs)
-{
-       unsigned long flags;
-       struct gigaset_driver *drv = cs->driver;
-       spin_lock_irqsave(&drv->lock, flags);
-       drv->flags[cs->minor_index] = 0;
-       spin_unlock_irqrestore(&drv->lock, flags);
-}
-
-static void make_valid(struct cardstate *cs, unsigned mask)
-{
-       unsigned long flags;
-       struct gigaset_driver *drv = cs->driver;
-       spin_lock_irqsave(&drv->lock, flags);
-       drv->flags[cs->minor_index] |= mask;
-       spin_unlock_irqrestore(&drv->lock, flags);
-}
-
-static void make_invalid(struct cardstate *cs, unsigned mask)
-{
-       unsigned long flags;
-       struct gigaset_driver *drv = cs->driver;
-       spin_lock_irqsave(&drv->lock, flags);
-       drv->flags[cs->minor_index] &= ~mask;
-       spin_unlock_irqrestore(&drv->lock, flags);
-}
-
 /* For drivers without fixed assignment device<->cardstate (usb) */
 struct cardstate *gigaset_getunassignedcs(struct gigaset_driver *drv)
 {
index fdcb80bb21c7c44a05cd05c9b8827bf279bdb241..1ba3424a286b6fc7aa3a0896ea36749a249b7e5d 100644 (file)
@@ -1,7 +1,7 @@
 /*
  * Stuff used by all variants of the driver
  *
- * Copyright (c) 2001 by Stefan Eilers <Eilers.Stefan@epost.de>,
+ * Copyright (c) 2001 by Stefan Eilers,
  *                       Hansjoerg Lipp <hjlipp@web.de>,
  *                       Tilman Schmidt <tilman@imap.cc>.
  *
  *     published by the Free Software Foundation; either version 2 of
  *     the License, or (at your option) any later version.
  * =====================================================================
- * ToDo: ...
- * =====================================================================
- * Version: $Id: ev-layer.c,v 1.4.2.18 2006/02/04 18:28:16 hjlipp Exp $
- * =====================================================================
  */
 
 #include "gigaset.h"
 
 /* ========================================================== */
 /* bit masks for pending commands */
-#define PC_INIT       0x004
-#define PC_DLE0       0x008
-#define PC_DLE1       0x010
-#define PC_CID        0x080
-#define PC_NOCID      0x100
-#define PC_HUP        0x002
-#define PC_DIAL       0x001
-#define PC_ACCEPT     0x040
-#define PC_SHUTDOWN   0x020
-#define PC_CIDMODE    0x200
-#define PC_UMMODE     0x400
+#define PC_DIAL                0x001
+#define PC_HUP         0x002
+#define PC_INIT                0x004
+#define PC_DLE0                0x008
+#define PC_DLE1                0x010
+#define PC_SHUTDOWN    0x020
+#define PC_ACCEPT      0x040
+#define PC_CID         0x080
+#define PC_NOCID       0x100
+#define PC_CIDMODE     0x200
+#define PC_UMMODE      0x400
 
 /* types of modem responses */
-#define RT_NOTHING 0
-#define RT_ZSAU    1
-#define RT_RING    2
-#define RT_NUMBER  3
-#define RT_STRING  4
-#define RT_HEX     5
-#define RT_ZCAU    6
+#define RT_NOTHING     0
+#define RT_ZSAU                1
+#define RT_RING                2
+#define RT_NUMBER      3
+#define RT_STRING      4
+#define RT_HEX         5
+#define RT_ZCAU                6
 
 /* Possible ASCII responses */
-#define RSP_OK           0
-//#define RSP_BUSY       1
-//#define RSP_CONNECT    2
-#define RSP_ZGCI         3
-#define RSP_RING         4
-#define RSP_ZAOC         5
-#define RSP_ZCSTR        6
-#define RSP_ZCFGT        7
-#define RSP_ZCFG         8
-#define RSP_ZCCR         9
-#define RSP_EMPTY        10
-#define RSP_ZLOG         11
-#define RSP_ZCAU         12
-#define RSP_ZMWI         13
-#define RSP_ZABINFO      14
-#define RSP_ZSMLSTCHG    15
-#define RSP_VAR          100
-#define RSP_ZSAU         (RSP_VAR + VAR_ZSAU)
-#define RSP_ZDLE         (RSP_VAR + VAR_ZDLE)
-#define RSP_ZVLS         (RSP_VAR + VAR_ZVLS)
-#define RSP_ZCTP         (RSP_VAR + VAR_ZCTP)
-#define RSP_STR          (RSP_VAR + VAR_NUM)
-#define RSP_NMBR         (RSP_STR + STR_NMBR)
-#define RSP_ZCPN         (RSP_STR + STR_ZCPN)
-#define RSP_ZCON         (RSP_STR + STR_ZCON)
-#define RSP_ZBC          (RSP_STR + STR_ZBC)
-#define RSP_ZHLC         (RSP_STR + STR_ZHLC)
-#define RSP_ERROR       -1       /* ERROR              */
-#define RSP_WRONG_CID   -2       /* unknown cid in cmd */
-//#define RSP_EMPTY     -3
-#define RSP_UNKNOWN     -4       /* unknown response   */
-#define RSP_FAIL        -5       /* internal error     */
-#define RSP_INVAL       -6       /* invalid response   */
-
-#define RSP_NONE        -19
-#define RSP_STRING      -20
-#define RSP_NULL        -21
-//#define RSP_RETRYFAIL -22
-//#define RSP_RETRY     -23
-//#define RSP_SKIP      -24
-#define RSP_INIT        -27
-#define RSP_ANY         -26
-#define RSP_LAST        -28
-#define RSP_NODEV       -9
+#define RSP_OK         0
+//#define RSP_BUSY     1
+//#define RSP_CONNECT  2
+#define RSP_ZGCI       3
+#define RSP_RING       4
+#define RSP_ZAOC       5
+#define RSP_ZCSTR      6
+#define RSP_ZCFGT      7
+#define RSP_ZCFG       8
+#define RSP_ZCCR       9
+#define RSP_EMPTY      10
+#define RSP_ZLOG       11
+#define RSP_ZCAU       12
+#define RSP_ZMWI       13
+#define RSP_ZABINFO    14
+#define RSP_ZSMLSTCHG  15
+#define RSP_VAR                100
+#define RSP_ZSAU       (RSP_VAR + VAR_ZSAU)
+#define RSP_ZDLE       (RSP_VAR + VAR_ZDLE)
+#define RSP_ZVLS       (RSP_VAR + VAR_ZVLS)
+#define RSP_ZCTP       (RSP_VAR + VAR_ZCTP)
+#define RSP_STR                (RSP_VAR + VAR_NUM)
+#define RSP_NMBR       (RSP_STR + STR_NMBR)
+#define RSP_ZCPN       (RSP_STR + STR_ZCPN)
+#define RSP_ZCON       (RSP_STR + STR_ZCON)
+#define RSP_ZBC                (RSP_STR + STR_ZBC)
+#define RSP_ZHLC       (RSP_STR + STR_ZHLC)
+#define RSP_ERROR      -1      /* ERROR              */
+#define RSP_WRONG_CID  -2      /* unknown cid in cmd */
+//#define RSP_EMPTY    -3
+#define RSP_UNKNOWN    -4      /* unknown response   */
+#define RSP_FAIL       -5      /* internal error     */
+#define RSP_INVAL      -6      /* invalid response   */
+
+#define RSP_NONE       -19
+#define RSP_STRING     -20
+#define RSP_NULL       -21
+//#define RSP_RETRYFAIL        -22
+//#define RSP_RETRY    -23
+//#define RSP_SKIP     -24
+#define RSP_INIT       -27
+#define RSP_ANY                -26
+#define RSP_LAST       -28
+#define RSP_NODEV      -9
 
 /* actions for process_response */
 #define ACT_NOTHING            0
 #define ACT_DISCONNECT         20
 #define ACT_CONNECT            21
 #define ACT_REMOTEREJECT       22
-#define ACT_CONNTIMEOUT         23
+#define ACT_CONNTIMEOUT                23
 #define ACT_REMOTEHUP          24
 #define ACT_ABORTHUP           25
 #define ACT_ICALL              26
 #define ACT_ERROR              35
 #define ACT_ABORTCID           36
 #define ACT_ZCAU               37
-#define ACT_NOTIFY_BC_DOWN      38
-#define ACT_NOTIFY_BC_UP        39
-#define ACT_DIAL                40
-#define ACT_ACCEPT              41
-#define ACT_PROTO_L2            42
-#define ACT_HUP                 43
-#define ACT_IF_LOCK             44
-#define ACT_START               45
-#define ACT_STOP                46
-#define ACT_FAKEDLE0            47
-#define ACT_FAKEHUP             48
-#define ACT_FAKESDOWN           49
-#define ACT_SHUTDOWN            50
-#define ACT_PROC_CIDMODE        51
-#define ACT_UMODESET            52
-#define ACT_FAILUMODE           53
-#define ACT_CMODESET            54
-#define ACT_FAILCMODE           55
-#define ACT_IF_VER              56
+#define ACT_NOTIFY_BC_DOWN     38
+#define ACT_NOTIFY_BC_UP       39
+#define ACT_DIAL               40
+#define ACT_ACCEPT             41
+#define ACT_PROTO_L2           42
+#define ACT_HUP                        43
+#define ACT_IF_LOCK            44
+#define ACT_START              45
+#define ACT_STOP               46
+#define ACT_FAKEDLE0           47
+#define ACT_FAKEHUP            48
+#define ACT_FAKESDOWN          49
+#define ACT_SHUTDOWN           50
+#define ACT_PROC_CIDMODE       51
+#define ACT_UMODESET           52
+#define ACT_FAILUMODE          53
+#define ACT_CMODESET           54
+#define ACT_FAILCMODE          55
+#define ACT_IF_VER             56
 #define ACT_CMD                        100
 
 /* at command sequences */
-#define SEQ_NONE      0
-#define SEQ_INIT      100
-#define SEQ_DLE0      200
-#define SEQ_DLE1      250
-#define SEQ_CID       300
-#define SEQ_NOCID     350
-#define SEQ_HUP       400
-#define SEQ_DIAL      600
-#define SEQ_ACCEPT    720
-#define SEQ_SHUTDOWN  500
-#define SEQ_CIDMODE   10
-#define SEQ_UMMODE    11
+#define SEQ_NONE       0
+#define SEQ_INIT       100
+#define SEQ_DLE0       200
+#define SEQ_DLE1       250
+#define SEQ_CID                300
+#define SEQ_NOCID      350
+#define SEQ_HUP                400
+#define SEQ_DIAL       600
+#define SEQ_ACCEPT     720
+#define SEQ_SHUTDOWN   500
+#define SEQ_CIDMODE    10
+#define SEQ_UMMODE     11
 
 
 // 100: init, 200: dle0, 250:dle1, 300: get cid (dial), 350: "hup" (no cid), 400: hup, 500: reset, 600: dial, 700: ring
@@ -175,7 +171,7 @@ struct reply_t gigaset_tab_nocid_m10x[]= /* with dle mode */
        //                                                  {ACT_TIMEOUT}},
 
        {RSP_INIT,     -1, -1,SEQ_INIT,           100, INIT_TIMEOUT,
-                                                         {ACT_TIMEOUT}},                /* wait until device is ready */
+                                                         {ACT_TIMEOUT}},                /* wait until device is ready */
 
        {EV_TIMEOUT,  100,100, -1,                101, 3, {0},             "Z\r"},       /* device in transparent mode? try to initialize it. */
        {RSP_OK,      101,103, -1,                120, 5, {ACT_GETSTRING}, "+GMR\r"},    /* get version */
@@ -190,8 +186,8 @@ struct reply_t gigaset_tab_nocid_m10x[]= /* with dle mode */
        {RSP_ERROR,   108,108, -1,                  0, 0, {ACT_FAILINIT}},
 
        {EV_TIMEOUT,  108,108, -1,                105, 2, {ACT_SETDLE0,
-                                                          ACT_HUPMODEM,
-                                                          ACT_TIMEOUT}},                /* still timeout => connection in unimodem mode? */
+                                                          ACT_HUPMODEM,
+                                                          ACT_TIMEOUT}},                /* still timeout => connection in unimodem mode? */
        {EV_TIMEOUT,  105,105, -1,                103, 5, {0},             "Z\r"},
 
        {RSP_ERROR,   102,102, -1,                107, 5, {0},             "^GETPRE\r"}, /* ERROR on ATZ => maybe in config mode? */
@@ -393,7 +389,7 @@ struct reply_t gigaset_tab_cid_m10x[] = /* for M10x */
 
 
 #if 0
-static struct reply_t tab_nocid[]= /* no dle mode */ //FIXME aenderungen uebernehmen
+static struct reply_t tab_nocid[]= /* no dle mode */ //FIXME
 {
        /* resp_code, min_ConState, max_ConState, parameter, new_ConState, timeout, action, command */
 
@@ -401,7 +397,7 @@ static struct reply_t tab_nocid[]= /* no dle mode */ //FIXME aenderungen ueberne
        {RSP_LAST,0,0,0,0,0,0}
 };
 
-static struct reply_t tab_cid[] = /* no dle mode */ //FIXME aenderungen uebernehmen
+static struct reply_t tab_cid[] = /* no dle mode */ //FIXME
 {
        /* resp_code, min_ConState, max_ConState, parameter, new_ConState, timeout, action, command */
 
@@ -412,30 +408,30 @@ static struct reply_t tab_cid[] = /* no dle mode */ //FIXME aenderungen ueberneh
 
 static struct resp_type_t resp_type[]=
 {
-       /*{"",          RSP_EMPTY,  RT_NOTHING},*/
-       {"OK",        RSP_OK,     RT_NOTHING},
-       {"ERROR",     RSP_ERROR,  RT_NOTHING},
-       {"ZSAU",      RSP_ZSAU,   RT_ZSAU},
-       {"ZCAU",      RSP_ZCAU,   RT_ZCAU},
-       {"RING",      RSP_RING,   RT_RING},
-       {"ZGCI",      RSP_ZGCI,   RT_NUMBER},
-       {"ZVLS",      RSP_ZVLS,   RT_NUMBER},
-       {"ZCTP",      RSP_ZCTP,   RT_NUMBER},
-       {"ZDLE",      RSP_ZDLE,   RT_NUMBER},
-       {"ZCFGT",     RSP_ZCFGT,  RT_NUMBER},
-       {"ZCCR",      RSP_ZCCR,   RT_NUMBER},
-       {"ZMWI",      RSP_ZMWI,   RT_NUMBER},
-       {"ZHLC",      RSP_ZHLC,   RT_STRING},
-       {"ZBC",       RSP_ZBC,    RT_STRING},
-       {"NMBR",      RSP_NMBR,   RT_STRING},
-       {"ZCPN",      RSP_ZCPN,   RT_STRING},
-       {"ZCON",      RSP_ZCON,   RT_STRING},
-       {"ZAOC",      RSP_ZAOC,   RT_STRING},
-       {"ZCSTR",     RSP_ZCSTR,  RT_STRING},
-       {"ZCFG",      RSP_ZCFG,   RT_HEX},
-       {"ZLOG",      RSP_ZLOG,   RT_NOTHING},
-       {"ZABINFO",   RSP_ZABINFO, RT_NOTHING},
-       {"ZSMLSTCHG", RSP_ZSMLSTCHG, RT_NOTHING},
+       /*{"",          RSP_EMPTY,      RT_NOTHING},*/
+       {"OK",          RSP_OK,         RT_NOTHING},
+       {"ERROR",       RSP_ERROR,      RT_NOTHING},
+       {"ZSAU",        RSP_ZSAU,       RT_ZSAU},
+       {"ZCAU",        RSP_ZCAU,       RT_ZCAU},
+       {"RING",        RSP_RING,       RT_RING},
+       {"ZGCI",        RSP_ZGCI,       RT_NUMBER},
+       {"ZVLS",        RSP_ZVLS,       RT_NUMBER},
+       {"ZCTP",        RSP_ZCTP,       RT_NUMBER},
+       {"ZDLE",        RSP_ZDLE,       RT_NUMBER},
+       {"ZCFGT",       RSP_ZCFGT,      RT_NUMBER},
+       {"ZCCR",        RSP_ZCCR,       RT_NUMBER},
+       {"ZMWI",        RSP_ZMWI,       RT_NUMBER},
+       {"ZHLC",        RSP_ZHLC,       RT_STRING},
+       {"ZBC",         RSP_ZBC,        RT_STRING},
+       {"NMBR",        RSP_NMBR,       RT_STRING},
+       {"ZCPN",        RSP_ZCPN,       RT_STRING},
+       {"ZCON",        RSP_ZCON,       RT_STRING},
+       {"ZAOC",        RSP_ZAOC,       RT_STRING},
+       {"ZCSTR",       RSP_ZCSTR,      RT_STRING},
+       {"ZCFG",        RSP_ZCFG,       RT_HEX},
+       {"ZLOG",        RSP_ZLOG,       RT_NOTHING},
+       {"ZABINFO",     RSP_ZABINFO,    RT_NOTHING},
+       {"ZSMLSTCHG",   RSP_ZSMLSTCHG,  RT_NOTHING},
        {NULL,0,0}
 };
 
@@ -446,9 +442,7 @@ static int isdn_getnum(char *p)
 {
        int v = -1;
 
-       IFNULLRETVAL(p, -1);
-
-       dbg(DEBUG_TRANSCMD, "string: %s", p);
+       gig_dbg(DEBUG_TRANSCMD, "string: %s", p);
 
        while (*p >= '0' && *p <= '9')
                v = ((v < 0) ? 0 : (v * 10)) + (int) ((*p++) - '0');
@@ -465,9 +459,7 @@ static int isdn_gethex(char *p)
        int v = 0;
        int c;
 
-       IFNULLRETVAL(p, -1);
-
-       dbg(DEBUG_TRANSCMD, "string: %s", p);
+       gig_dbg(DEBUG_TRANSCMD, "string: %s", p);
 
        if (!*p)
                return -1;
@@ -490,14 +482,6 @@ static int isdn_gethex(char *p)
        return v;
 }
 
-static inline void new_index(atomic_t *index, int max)
-{
-       if (atomic_read(index) == max)  //FIXME race?
-               atomic_set(index, 0);
-       else
-               atomic_inc(index);
-}
-
 /* retrieve CID from parsed response
  * returns 0 if no CID, -1 if invalid CID, or CID value 1..65535
  */
@@ -536,16 +520,14 @@ void gigaset_handle_modem_response(struct cardstate *cs)
        int cid;
        int rawstring;
 
-       IFNULLRET(cs);
-
        len = cs->cbytes;
        if (!len) {
                /* ignore additional LFs/CRs (M10x config mode or cx100) */
-               dbg(DEBUG_MCMD, "skipped EOL [%02X]", cs->respdata[len]);
+               gig_dbg(DEBUG_MCMD, "skipped EOL [%02X]", cs->respdata[len]);
                return;
        }
        cs->respdata[len] = 0;
-       dbg(DEBUG_TRANSCMD, "raw string: '%s'", cs->respdata);
+       gig_dbg(DEBUG_TRANSCMD, "raw string: '%s'", cs->respdata);
        argv[0] = cs->respdata;
        params = 1;
        if (cs->at_state.getstring) {
@@ -561,7 +543,8 @@ void gigaset_handle_modem_response(struct cardstate *cs)
                        case ',':
                        case '=':
                                if (params > MAX_REC_PARAMS) {
-                                       warn("too many parameters in response");
+                                       dev_warn(cs->dev,
+                                          "too many parameters in response\n");
                                        /* need last parameter (might be CID) */
                                        params--;
                                }
@@ -572,33 +555,33 @@ void gigaset_handle_modem_response(struct cardstate *cs)
                cid = params > 1 ? cid_of_response(argv[params-1]) : 0;
                if (cid < 0) {
                        gigaset_add_event(cs, &cs->at_state, RSP_INVAL,
-                                         NULL, 0, NULL);
+                                         NULL, 0, NULL);
                        return;
                }
 
                for (j = 1; j < params; ++j)
                        argv[j][-1] = 0;
 
-               dbg(DEBUG_TRANSCMD, "CMD received: %s", argv[0]);
+               gig_dbg(DEBUG_TRANSCMD, "CMD received: %s", argv[0]);
                if (cid) {
                        --params;
-                       dbg(DEBUG_TRANSCMD, "CID: %s", argv[params]);
+                       gig_dbg(DEBUG_TRANSCMD, "CID: %s", argv[params]);
                }
-               dbg(DEBUG_TRANSCMD, "available params: %d", params - 1);
+               gig_dbg(DEBUG_TRANSCMD, "available params: %d", params - 1);
                for (j = 1; j < params; j++)
-                       dbg(DEBUG_TRANSCMD, "param %d: %s", j, argv[j]);
+                       gig_dbg(DEBUG_TRANSCMD, "param %d: %s", j, argv[j]);
        }
 
        spin_lock_irqsave(&cs->ev_lock, flags);
-       head = atomic_read(&cs->ev_head);
-       tail = atomic_read(&cs->ev_tail);
+       head = cs->ev_head;
+       tail = cs->ev_tail;
 
        abort = 1;
        curarg = 0;
        while (curarg < params) {
                next = (tail + 1) % MAX_EVENTS;
                if (unlikely(next == head)) {
-                       err("event queue full");
+                       dev_err(cs->dev, "event queue full\n");
                        break;
                }
 
@@ -619,8 +602,9 @@ void gigaset_handle_modem_response(struct cardstate *cs)
 
                        if (!rt->response) {
                                event->type = RSP_UNKNOWN;
-                               warn("unknown modem response: %s",
-                                    argv[curarg]);
+                               dev_warn(cs->dev,
+                                        "unknown modem response: %s\n",
+                                        argv[curarg]);
                                break;
                        }
 
@@ -636,7 +620,8 @@ void gigaset_handle_modem_response(struct cardstate *cs)
                        break;
                case RT_RING:
                        if (!cid) {
-                               err("received RING without CID!");
+                               dev_err(cs->dev,
+                                       "received RING without CID!\n");
                                event->type = RSP_INVAL;
                                abort = 1;
                        } else {
@@ -664,27 +649,25 @@ void gigaset_handle_modem_response(struct cardstate *cs)
                                event->parameter = ZSAU_DISCONNECT_REQ;
                        else {
                                event->parameter = ZSAU_UNKNOWN;
-                               warn("%s: unknown parameter %s after ZSAU",
-                                    __func__, argv[curarg]);
+                               dev_warn(cs->dev,
+                                       "%s: unknown parameter %s after ZSAU\n",
+                                        __func__, argv[curarg]);
                        }
                        ++curarg;
                        break;
                case RT_STRING:
                        if (curarg < params) {
-                               len = strlen(argv[curarg]) + 1;
-                               event->ptr = kmalloc(len, GFP_ATOMIC);
-                               if (event->ptr)
-                                       memcpy(event->ptr, argv[curarg], len);
-                               else
-                                       err("no memory for string!");
+                               event->ptr = kstrdup(argv[curarg], GFP_ATOMIC);
+                               if (!event->ptr)
+                                       dev_err(cs->dev, "out of memory\n");
                                ++curarg;
                        }
 #ifdef CONFIG_GIGASET_DEBUG
                        if (!event->ptr)
-                               dbg(DEBUG_CMD, "string==NULL");
+                               gig_dbg(DEBUG_CMD, "string==NULL");
                        else
-                               dbg(DEBUG_CMD,
-                                   "string==%s", (char *) event->ptr);
+                               gig_dbg(DEBUG_CMD, "string==%s",
+                                       (char *) event->ptr);
 #endif
                        break;
                case RT_ZCAU:
@@ -694,7 +677,7 @@ void gigaset_handle_modem_response(struct cardstate *cs)
                                j = isdn_gethex(argv[curarg + 1]);
                                if (i >= 0 && i < 256 && j >= 0 && j < 256)
                                        event->parameter = (unsigned) i << 8
-                                                          | j;
+                                                          | j;
                                curarg += 2;
                        } else
                                curarg = params - 1;
@@ -712,7 +695,7 @@ void gigaset_handle_modem_response(struct cardstate *cs)
                        } else
                                event->parameter = -1;
 #ifdef CONFIG_GIGASET_DEBUG
-                       dbg(DEBUG_CMD, "parameter==%d", event->parameter);
+                       gig_dbg(DEBUG_CMD, "parameter==%d", event->parameter);
 #endif
                        break;
                }
@@ -724,12 +707,13 @@ void gigaset_handle_modem_response(struct cardstate *cs)
                        break;
        }
 
-       atomic_set(&cs->ev_tail, tail);
+       cs->ev_tail = tail;
        spin_unlock_irqrestore(&cs->ev_lock, flags);
 
        if (curarg != params)
-               dbg(DEBUG_ANY, "invalid number of processed parameters: %d/%d",
-                   curarg, params);
+               gig_dbg(DEBUG_ANY,
+                       "invalid number of processed parameters: %d/%d",
+                       curarg, params);
 }
 EXPORT_SYMBOL_GPL(gigaset_handle_modem_response);
 
@@ -739,23 +723,19 @@ EXPORT_SYMBOL_GPL(gigaset_handle_modem_response);
 static void disconnect(struct at_state_t **at_state_p)
 {
        unsigned long flags;
-       struct bc_state *bcs;
-       struct cardstate *cs;
+       struct bc_state *bcs = (*at_state_p)->bcs;
+       struct cardstate *cs = (*at_state_p)->cs;
 
-       IFNULLRET(at_state_p);
-       IFNULLRET(*at_state_p);
-       bcs = (*at_state_p)->bcs;
-       cs = (*at_state_p)->cs;
-       IFNULLRET(cs);
-
-       new_index(&(*at_state_p)->seq_index, MAX_SEQ_INDEX);
+       spin_lock_irqsave(&cs->lock, flags);
+       ++(*at_state_p)->seq_index;
 
        /* revert to selected idle mode */
-       if (!atomic_read(&cs->cidmode)) {
+       if (!cs->cidmode) {
                cs->at_state.pending_commands |= PC_UMMODE;
                atomic_set(&cs->commands_pending, 1); //FIXME
-               dbg(DEBUG_CMD, "Scheduling PC_UMMODE");
+               gig_dbg(DEBUG_CMD, "Scheduling PC_UMMODE");
        }
+       spin_unlock_irqrestore(&cs->lock, flags);
 
        if (bcs) {
                /* B channel assigned: invoke hardware specific handler */
@@ -777,7 +757,7 @@ static void disconnect(struct at_state_t **at_state_p)
  * The structure should be freed by calling disconnect() after use.
  */
 static inline struct at_state_t *get_free_channel(struct cardstate *cs,
-                                                  int cid)
+                                                 int cid)
 /* cids: >0: siemens-cid
          0: without cid
         -1: no cid assigned yet
@@ -826,7 +806,7 @@ static void init_failed(struct cardstate *cs, int mode)
 static void schedule_init(struct cardstate *cs, int state)
 {
        if (cs->at_state.pending_commands & PC_INIT) {
-               dbg(DEBUG_CMD, "not scheduling PC_INIT again");
+               gig_dbg(DEBUG_CMD, "not scheduling PC_INIT again");
                return;
        }
        atomic_set(&cs->mstate, state);
@@ -834,52 +814,56 @@ static void schedule_init(struct cardstate *cs, int state)
        gigaset_block_channels(cs);
        cs->at_state.pending_commands |= PC_INIT;
        atomic_set(&cs->commands_pending, 1);
-       dbg(DEBUG_CMD, "Scheduling PC_INIT");
+       gig_dbg(DEBUG_CMD, "Scheduling PC_INIT");
 }
 
-/* Add "AT" to a command, add the cid, dle encode it, send the result to the hardware. */
+/* Add "AT" to a command, add the cid, dle encode it, send the result to the
+   hardware. */
 static void send_command(struct cardstate *cs, const char *cmd, int cid,
-                         int dle, gfp_t kmallocflags)
+                        int dle, gfp_t kmallocflags)
 {
        size_t cmdlen, buflen;
        char *cmdpos, *cmdbuf, *cmdtail;
 
        cmdlen = strlen(cmd);
        buflen = 11 + cmdlen;
+       if (unlikely(buflen <= cmdlen)) {
+               dev_err(cs->dev, "integer overflow in buflen\n");
+               return;
+       }
 
-       if (likely(buflen > cmdlen)) {
-               cmdbuf = kmalloc(buflen, kmallocflags);
-               if (likely(cmdbuf != NULL)) {
-                       cmdpos = cmdbuf + 9;
-                       cmdtail = cmdpos + cmdlen;
-                       memcpy(cmdpos, cmd, cmdlen);
-
-                       if (cid > 0 && cid <= 65535) {
-                               do {
-                                       *--cmdpos = '0' + cid % 10;
-                                       cid /= 10;
-                                       ++cmdlen;
-                               } while (cid);
-                       }
+       cmdbuf = kmalloc(buflen, kmallocflags);
+       if (unlikely(!cmdbuf)) {
+               dev_err(cs->dev, "out of memory\n");
+               return;
+       }
 
-                       cmdlen += 2;
-                       *--cmdpos = 'T';
-                       *--cmdpos = 'A';
+       cmdpos = cmdbuf + 9;
+       cmdtail = cmdpos + cmdlen;
+       memcpy(cmdpos, cmd, cmdlen);
 
-                       if (dle) {
-                               cmdlen += 4;
-                               *--cmdpos = '(';
-                               *--cmdpos = 0x10;
-                               *cmdtail++ = 0x10;
-                               *cmdtail++ = ')';
-                       }
+       if (cid > 0 && cid <= 65535) {
+               do {
+                       *--cmdpos = '0' + cid % 10;
+                       cid /= 10;
+                       ++cmdlen;
+               } while (cid);
+       }
 
-                       cs->ops->write_cmd(cs, cmdpos, cmdlen, NULL);
-                       kfree(cmdbuf);
-               } else
-                       err("no memory for command buffer");
-       } else
-               err("overflow in buflen");
+       cmdlen += 2;
+       *--cmdpos = 'T';
+       *--cmdpos = 'A';
+
+       if (dle) {
+               cmdlen += 4;
+               *--cmdpos = '(';
+               *--cmdpos = 0x10;
+               *cmdtail++ = 0x10;
+               *cmdtail++ = ')';
+       }
+
+       cs->ops->write_cmd(cs, cmdpos, cmdlen, NULL);
+       kfree(cmdbuf);
 }
 
 static struct at_state_t *at_state_from_cid(struct cardstate *cs, int cid)
@@ -910,9 +894,6 @@ static struct at_state_t *at_state_from_cid(struct cardstate *cs, int cid)
 
 static void bchannel_down(struct bc_state *bcs)
 {
-       IFNULLRET(bcs);
-       IFNULLRET(bcs->cs);
-
        if (bcs->chstate & CHS_B_UP) {
                bcs->chstate &= ~CHS_B_UP;
                gigaset_i4l_channel_cmd(bcs, ISDN_STAT_BHUP);
@@ -930,16 +911,15 @@ static void bchannel_down(struct bc_state *bcs)
 
 static void bchannel_up(struct bc_state *bcs)
 {
-       IFNULLRET(bcs);
-
        if (!(bcs->chstate & CHS_D_UP)) {
-               notice("%s: D channel not up", __func__);
+               dev_notice(bcs->cs->dev, "%s: D channel not up\n", __func__);
                bcs->chstate |= CHS_D_UP;
                gigaset_i4l_channel_cmd(bcs, ISDN_STAT_DCONN);
        }
 
        if (bcs->chstate & CHS_B_UP) {
-               notice("%s: B channel already up", __func__);
+               dev_notice(bcs->cs->dev, "%s: B channel already up\n",
+                          __func__);
                return;
        }
 
@@ -947,17 +927,21 @@ static void bchannel_up(struct bc_state *bcs)
        gigaset_i4l_channel_cmd(bcs, ISDN_STAT_BCONN);
 }
 
-static void start_dial(struct at_state_t *at_state, void *data, int seq_index)
+static void start_dial(struct at_state_t *at_state, void *data, unsigned seq_index)
 {
        struct bc_state *bcs = at_state->bcs;
        struct cardstate *cs = at_state->cs;
        int retval;
+       unsigned long flags;
 
        bcs->chstate |= CHS_NOTIFY_LL;
-       //atomic_set(&bcs->status, BCS_INIT);
 
-       if (atomic_read(&at_state->seq_index) != seq_index)
+       spin_lock_irqsave(&cs->lock, flags);
+       if (at_state->seq_index != seq_index) {
+               spin_unlock_irqrestore(&cs->lock, flags);
                goto error;
+       }
+       spin_unlock_irqrestore(&cs->lock, flags);
 
        retval = gigaset_isdn_setup_dial(at_state, data);
        if (retval != 0)
@@ -965,20 +949,14 @@ static void start_dial(struct at_state_t *at_state, void *data, int seq_index)
 
 
        at_state->pending_commands |= PC_CID;
-       dbg(DEBUG_CMD, "Scheduling PC_CID");
-//#ifdef GIG_MAYINITONDIAL
-//     if (atomic_read(&cs->MState) == MS_UNKNOWN) {
-//             cs->at_state.pending_commands |= PC_INIT;
-//             dbg(DEBUG_CMD, "Scheduling PC_INIT");
-//     }
-//#endif
-       atomic_set(&cs->commands_pending, 1); //FIXME
+       gig_dbg(DEBUG_CMD, "Scheduling PC_CID");
+       atomic_set(&cs->commands_pending, 1);
        return;
 
 error:
        at_state->pending_commands |= PC_NOCID;
-       dbg(DEBUG_CMD, "Scheduling PC_NOCID");
-       atomic_set(&cs->commands_pending, 1); //FIXME
+       gig_dbg(DEBUG_CMD, "Scheduling PC_NOCID");
+       atomic_set(&cs->commands_pending, 1);
        return;
 }
 
@@ -991,13 +969,13 @@ static void start_accept(struct at_state_t *at_state)
 
        if (retval == 0) {
                at_state->pending_commands |= PC_ACCEPT;
-               dbg(DEBUG_CMD, "Scheduling PC_ACCEPT");
-               atomic_set(&cs->commands_pending, 1); //FIXME
+               gig_dbg(DEBUG_CMD, "Scheduling PC_ACCEPT");
+               atomic_set(&cs->commands_pending, 1);
        } else {
                //FIXME
                at_state->pending_commands |= PC_HUP;
-               dbg(DEBUG_CMD, "Scheduling PC_HUP");
-               atomic_set(&cs->commands_pending, 1); //FIXME
+               gig_dbg(DEBUG_CMD, "Scheduling PC_HUP");
+               atomic_set(&cs->commands_pending, 1);
        }
 }
 
@@ -1008,9 +986,10 @@ static void do_start(struct cardstate *cs)
        if (atomic_read(&cs->mstate) != MS_LOCKED)
                schedule_init(cs, MS_INIT);
 
+       cs->isdn_up = 1;
        gigaset_i4l_cmd(cs, ISDN_STAT_RUN);
-                                       // FIXME: not in locked mode
-                                       // FIXME 2: only after init sequence
+                                       // FIXME: not in locked mode
+                                       // FIXME 2: only after init sequence
 
        cs->waiting = 0;
        wake_up(&cs->waitqueue);
@@ -1023,6 +1002,12 @@ static void finish_shutdown(struct cardstate *cs)
                atomic_set(&cs->mode, M_UNKNOWN);
        }
 
+       /* Tell the LL that the device is not available .. */
+       if (cs->isdn_up) {
+               cs->isdn_up = 0;
+               gigaset_i4l_cmd(cs, ISDN_STAT_STOP);
+       }
+
        /* The rest is done by cleanup_cs () in user mode. */
 
        cs->cmd_result = -ENODEV;
@@ -1037,15 +1022,20 @@ static void do_shutdown(struct cardstate *cs)
        if (atomic_read(&cs->mstate) == MS_READY) {
                atomic_set(&cs->mstate, MS_SHUTDOWN);
                cs->at_state.pending_commands |= PC_SHUTDOWN;
-               atomic_set(&cs->commands_pending, 1); //FIXME
-               dbg(DEBUG_CMD, "Scheduling PC_SHUTDOWN"); //FIXME
-               //gigaset_schedule_event(cs); //FIXME
+               atomic_set(&cs->commands_pending, 1);
+               gig_dbg(DEBUG_CMD, "Scheduling PC_SHUTDOWN");
        } else
                finish_shutdown(cs);
 }
 
 static void do_stop(struct cardstate *cs)
 {
+       unsigned long flags;
+
+       spin_lock_irqsave(&cs->lock, flags);
+       cs->connected = 0;
+       spin_unlock_irqrestore(&cs->lock, flags);
+
        do_shutdown(cs);
 }
 
@@ -1069,9 +1059,11 @@ static int reinit_and_retry(struct cardstate *cs, int channel)
                        return 0;
 
        if (channel < 0)
-               warn("Could not enter cid mode. Reinit device and try again.");
+               dev_warn(cs->dev,
+                   "Could not enter cid mode. Reinit device and try again.\n");
        else {
-               warn("Could not get a call id. Reinit device and try again.");
+               dev_warn(cs->dev,
+                   "Could not get a call id. Reinit device and try again.\n");
                cs->bcs[channel].at_state.pending_commands |= PC_CID;
        }
        schedule_init(cs, MS_INIT);
@@ -1079,7 +1071,7 @@ static int reinit_and_retry(struct cardstate *cs, int channel)
 }
 
 static int at_state_invalid(struct cardstate *cs,
-                            struct at_state_t *test_ptr)
+                           struct at_state_t *test_ptr)
 {
        unsigned long flags;
        unsigned channel;
@@ -1116,7 +1108,7 @@ static void handle_icall(struct cardstate *cs, struct bc_state *bcs,
        case ICALL_ACCEPT:
                break;
        default:
-               err("internal error: disposition=%d", retval);
+               dev_err(cs->dev, "internal error: disposition=%d\n", retval);
                /* --v-- fall through --v-- */
        case ICALL_IGNORE:
        case ICALL_REJECT:
@@ -1160,7 +1152,6 @@ static int do_lock(struct cardstate *cs)
        mode = atomic_read(&cs->mode);
        atomic_set(&cs->mstate, MS_LOCKED);
        atomic_set(&cs->mode, M_UNKNOWN);
-       //FIXME reset card state / at states / bcs states
 
        return mode;
 }
@@ -1173,8 +1164,7 @@ static int do_unlock(struct cardstate *cs)
        atomic_set(&cs->mstate, MS_UNINITIALIZED);
        atomic_set(&cs->mode, M_UNKNOWN);
        gigaset_free_channels(cs);
-       //FIXME reset card state / at states / bcs states
-       if (atomic_read(&cs->connected))
+       if (cs->connected)
                schedule_init(cs, MS_INIT);
 
        return 0;
@@ -1203,21 +1193,23 @@ static void do_action(int action, struct cardstate *cs,
                at_state->waiting = 1;
                break;
        case ACT_INIT:
-               //FIXME setup everything
                cs->at_state.pending_commands &= ~PC_INIT;
                cs->cur_at_seq = SEQ_NONE;
                atomic_set(&cs->mode, M_UNIMODEM);
-               if (!atomic_read(&cs->cidmode)) {
+               spin_lock_irqsave(&cs->lock, flags);
+               if (!cs->cidmode) {
+                       spin_unlock_irqrestore(&cs->lock, flags);
                        gigaset_free_channels(cs);
                        atomic_set(&cs->mstate, MS_READY);
                        break;
                }
+               spin_unlock_irqrestore(&cs->lock, flags);
                cs->at_state.pending_commands |= PC_CIDMODE;
-               atomic_set(&cs->commands_pending, 1); //FIXME
-               dbg(DEBUG_CMD, "Scheduling PC_CIDMODE");
+               atomic_set(&cs->commands_pending, 1);
+               gig_dbg(DEBUG_CMD, "Scheduling PC_CIDMODE");
                break;
        case ACT_FAILINIT:
-               warn("Could not initialize the device.");
+               dev_warn(cs->dev, "Could not initialize the device.\n");
                cs->dle = 0;
                init_failed(cs, M_UNKNOWN);
                cs->cur_at_seq = SEQ_NONE;
@@ -1273,8 +1265,8 @@ static void do_action(int action, struct cardstate *cs,
                /* get fresh AT state structure for new CID */
                at_state2 = get_free_channel(cs, ev->parameter);
                if (!at_state2) {
-                       warn("RING ignored: "
-                            "could not allocate channel structure");
+                       dev_warn(cs->dev,
+                       "RING ignored: could not allocate channel structure\n");
                        break;
                }
 
@@ -1302,7 +1294,7 @@ static void do_action(int action, struct cardstate *cs,
                at_state = *p_at_state;
                break;
        case ACT_FAILSDOWN:
-               warn("Could not shut down the device.");
+               dev_warn(cs->dev, "Could not shut down the device.\n");
                /* fall through */
        case ACT_FAKESDOWN:
        case ACT_SDOWN:
@@ -1355,7 +1347,7 @@ static void do_action(int action, struct cardstate *cs,
                break;
        case ACT_ABORTHUP:
                cs->cur_at_seq = SEQ_NONE;
-               warn("Could not hang up.");
+               dev_warn(cs->dev, "Could not hang up.\n");
                at_state->cid = -1;
                if (bcs && cs->onechannel)
                        at_state->pending_commands |= PC_DLE0;
@@ -1367,14 +1359,15 @@ static void do_action(int action, struct cardstate *cs,
                break;
        case ACT_FAILDLE0:
                cs->cur_at_seq = SEQ_NONE;
-               warn("Could not leave DLE mode.");
+               dev_warn(cs->dev, "Could not leave DLE mode.\n");
                at_state2 = &cs->bcs[cs->curchannel].at_state;
                disconnect(&at_state2);
                schedule_init(cs, MS_RECOVER);
                break;
        case ACT_FAILDLE1:
                cs->cur_at_seq = SEQ_NONE;
-               warn("Could not enter DLE mode. Try to hang up.");
+               dev_warn(cs->dev,
+                        "Could not enter DLE mode. Trying to hang up.\n");
                channel = cs->curchannel;
                cs->bcs[channel].at_state.pending_commands |= PC_HUP;
                atomic_set(&cs->commands_pending, 1);
@@ -1395,7 +1388,8 @@ static void do_action(int action, struct cardstate *cs,
                cs->cur_at_seq = SEQ_NONE;
                channel = cs->curchannel;
                if (!reinit_and_retry(cs, channel)) {
-                       warn("Could not get a call id. Dialing not possible");
+                       dev_warn(cs->dev,
+                                "Could not get a call ID. Cannot dial.\n");
                        at_state2 = &cs->bcs[channel].at_state;
                        disconnect(&at_state2);
                }
@@ -1428,7 +1422,8 @@ static void do_action(int action, struct cardstate *cs,
                at_state->pending_commands |= PC_HUP;
                atomic_set(&cs->commands_pending, 1);
                break;
-       case ACT_GETSTRING: /* warning: RING, ZDLE, ... are not handled properly any more */
+       case ACT_GETSTRING: /* warning: RING, ZDLE, ...
+                              are not handled properly anymore */
                at_state->getstring = 1;
                break;
        case ACT_SETVER:
@@ -1469,16 +1464,16 @@ static void do_action(int action, struct cardstate *cs,
        case ACT_GOTVER:
                if (cs->gotfwver == 0) {
                        cs->gotfwver = 1;
-                       dbg(DEBUG_ANY,
-                           "firmware version %02d.%03d.%02d.%02d",
-                           cs->fwver[0], cs->fwver[1],
-                           cs->fwver[2], cs->fwver[3]);
+                       gig_dbg(DEBUG_ANY,
+                               "firmware version %02d.%03d.%02d.%02d",
+                               cs->fwver[0], cs->fwver[1],
+                               cs->fwver[2], cs->fwver[3]);
                        break;
                }
                /* fall through */
        case ACT_FAILVER:
                cs->gotfwver = -1;
-               err("could not read firmware version.");
+               dev_err(cs->dev, "could not read firmware version.\n");
                break;
 #ifdef CONFIG_GIGASET_DEBUG
        case ACT_ERROR:
@@ -1496,16 +1491,16 @@ static void do_action(int action, struct cardstate *cs,
                break;
 #endif
        case ACT_DEBUG:
-               dbg(DEBUG_ANY, "%s: resp_code %d in ConState %d",
+               gig_dbg(DEBUG_ANY, "%s: resp_code %d in ConState %d",
                        __func__, ev->type, at_state->ConState);
                break;
        case ACT_WARN:
-               warn("%s: resp_code %d in ConState %d!",
-                       __func__, ev->type, at_state->ConState);
+               dev_warn(cs->dev, "%s: resp_code %d in ConState %d!\n",
+                        __func__, ev->type, at_state->ConState);
                break;
        case ACT_ZCAU:
-               warn("cause code %04x in connection state %d.",
-                    ev->parameter, at_state->ConState);
+               dev_warn(cs->dev, "cause code %04x in connection state %d.\n",
+                        ev->parameter, at_state->ConState);
                break;
 
        /* events from the LL */
@@ -1516,14 +1511,14 @@ static void do_action(int action, struct cardstate *cs,
                start_accept(at_state);
                break;
        case ACT_PROTO_L2:
-               dbg(DEBUG_CMD,
-                   "set protocol to %u", (unsigned) ev->parameter);
+               gig_dbg(DEBUG_CMD, "set protocol to %u",
+                       (unsigned) ev->parameter);
                at_state->bcs->proto2 = ev->parameter;
                break;
        case ACT_HUP:
                at_state->pending_commands |= PC_HUP;
-               atomic_set(&cs->commands_pending, 1); //FIXME
-               dbg(DEBUG_CMD, "Scheduling PC_HUP");
+               atomic_set(&cs->commands_pending, 1);
+               gig_dbg(DEBUG_CMD, "Scheduling PC_HUP");
                break;
 
        /* hotplug events */
@@ -1555,17 +1550,19 @@ static void do_action(int action, struct cardstate *cs,
 
        /* events from the proc file system */ // FIXME without ACT_xxxx?
        case ACT_PROC_CIDMODE:
-               if (ev->parameter != atomic_read(&cs->cidmode)) {
-                       atomic_set(&cs->cidmode, ev->parameter);
+               spin_lock_irqsave(&cs->lock, flags);
+               if (ev->parameter != cs->cidmode) {
+                       cs->cidmode = ev->parameter;
                        if (ev->parameter) {
                                cs->at_state.pending_commands |= PC_CIDMODE;
-                               dbg(DEBUG_CMD, "Scheduling PC_CIDMODE");
+                               gig_dbg(DEBUG_CMD, "Scheduling PC_CIDMODE");
                        } else {
                                cs->at_state.pending_commands |= PC_UMMODE;
-                               dbg(DEBUG_CMD, "Scheduling PC_UMMODE");
+                               gig_dbg(DEBUG_CMD, "Scheduling PC_UMMODE");
                        }
                        atomic_set(&cs->commands_pending, 1);
                }
+               spin_unlock_irqrestore(&cs->lock, flags);
                cs->waiting = 0;
                wake_up(&cs->waitqueue);
                break;
@@ -1590,7 +1587,7 @@ static void do_action(int action, struct cardstate *cs,
                                *p_resp_code = RSP_NULL;
                        }
                } else
-                       err("%s: action==%d!", __func__, action);
+                       dev_err(cs->dev, "%s: action==%d!\n", __func__, action);
        }
 }
 
@@ -1609,47 +1606,46 @@ static void process_event(struct cardstate *cs, struct event_t *ev)
        int curact;
        unsigned long flags;
 
-       IFNULLRET(cs);
-       IFNULLRET(ev);
-
        if (ev->cid >= 0) {
                at_state = at_state_from_cid(cs, ev->cid);
                if (!at_state) {
                        gigaset_add_event(cs, &cs->at_state, RSP_WRONG_CID,
-                                         NULL, 0, NULL);
+                                         NULL, 0, NULL);
                        return;
                }
        } else {
                at_state = ev->at_state;
                if (at_state_invalid(cs, at_state)) {
-                       dbg(DEBUG_ANY,
-                           "event for invalid at_state %p", at_state);
+                       gig_dbg(DEBUG_ANY, "event for invalid at_state %p",
+                               at_state);
                        return;
                }
        }
 
-       dbg(DEBUG_CMD,
-           "connection state %d, event %d", at_state->ConState, ev->type);
+       gig_dbg(DEBUG_CMD, "connection state %d, event %d",
+               at_state->ConState, ev->type);
 
        bcs = at_state->bcs;
        sendcid = at_state->cid;
 
        /* Setting the pointer to the dial array */
        rep = at_state->replystruct;
-       IFNULLRET(rep);
 
+       spin_lock_irqsave(&cs->lock, flags);
        if (ev->type == EV_TIMEOUT) {
-               if (ev->parameter != atomic_read(&at_state->timer_index)
+               if (ev->parameter != at_state->timer_index
                    || !at_state->timer_active) {
                        ev->type = RSP_NONE; /* old timeout */
-                       dbg(DEBUG_ANY, "old timeout");
+                       gig_dbg(DEBUG_ANY, "old timeout");
                } else if (!at_state->waiting)
-                       dbg(DEBUG_ANY, "timeout occured");
+                       gig_dbg(DEBUG_ANY, "timeout occurred");
                else
-                       dbg(DEBUG_ANY, "stopped waiting");
+                       gig_dbg(DEBUG_ANY, "stopped waiting");
        }
+       spin_unlock_irqrestore(&cs->lock, flags);
 
-       /* if the response belongs to a variable in at_state->int_var[VAR_XXXX] or at_state->str_var[STR_XXXX], set it */
+       /* if the response belongs to a variable in at_state->int_var[VAR_XXXX]
+          or at_state->str_var[STR_XXXX], set it */
        if (ev->type >= RSP_VAR && ev->type < RSP_VAR + VAR_NUM) {
                index = ev->type - RSP_VAR;
                at_state->int_var[index] = ev->parameter;
@@ -1657,20 +1653,22 @@ static void process_event(struct cardstate *cs, struct event_t *ev)
                index = ev->type - RSP_STR;
                kfree(at_state->str_var[index]);
                at_state->str_var[index] = ev->ptr;
-               ev->ptr = NULL; /* prevent process_events() from deallocating ptr */
+               ev->ptr = NULL; /* prevent process_events() from
+                                  deallocating ptr */
        }
 
        if (ev->type == EV_TIMEOUT || ev->type == RSP_STRING)
                at_state->getstring = 0;
 
-       /* Search row in dial array which matches modem response and current constate */
+       /* Search row in dial array which matches modem response and current
+          constate */
        for (;; rep++) {
                rcode = rep->resp_code;
-               /* dbg (DEBUG_ANY, "rcode %d", rcode); */
                if (rcode == RSP_LAST) {
                        /* found nothing...*/
-                       warn("%s: rcode=RSP_LAST: resp_code %d in ConState %d!",
-                               __func__, ev->type, at_state->ConState);
+                       dev_warn(cs->dev, "%s: rcode=RSP_LAST: "
+                                       "resp_code %d in ConState %d!\n",
+                                __func__, ev->type, at_state->ConState);
                        return;
                }
                if ((rcode == RSP_ANY || rcode == ev->type)
@@ -1706,14 +1704,14 @@ static void process_event(struct cardstate *cs, struct event_t *ev)
                } else {
                        /* Send command to modem if not NULL... */
                        if (p_command/*rep->command*/) {
-                               if (atomic_read(&cs->connected))
+                               if (cs->connected)
                                        send_command(cs, p_command,
-                                                    sendcid, cs->dle,
-                                                    GFP_ATOMIC);
+                                                    sendcid, cs->dle,
+                                                    GFP_ATOMIC);
                                else
                                        gigaset_add_event(cs, at_state,
-                                                         RSP_NODEV,
-                                                         NULL, 0, NULL);
+                                                         RSP_NODEV,
+                                                         NULL, 0, NULL);
                        }
 
                        spin_lock_irqsave(&cs->lock, flags);
@@ -1723,8 +1721,7 @@ static void process_event(struct cardstate *cs, struct event_t *ev)
                        } else if (rep->timeout > 0) { /* new timeout */
                                at_state->timer_expires = rep->timeout * 10;
                                at_state->timer_active = 1;
-                               new_index(&at_state->timer_index,
-                                         MAX_TIMER_INDEX);
+                               ++at_state->timer_index;
                        }
                        spin_unlock_irqrestore(&cs->lock, flags);
                }
@@ -1744,17 +1741,16 @@ static void process_command_flags(struct cardstate *cs)
        struct bc_state *bcs;
        int i;
        int sequence;
-
-       IFNULLRET(cs);
+       unsigned long flags;
 
        atomic_set(&cs->commands_pending, 0);
 
        if (cs->cur_at_seq) {
-               dbg(DEBUG_CMD, "not searching scheduled commands: busy");
+               gig_dbg(DEBUG_CMD, "not searching scheduled commands: busy");
                return;
        }
 
-       dbg(DEBUG_CMD, "searching scheduled commands");
+       gig_dbg(DEBUG_CMD, "searching scheduled commands");
 
        sequence = SEQ_NONE;
 
@@ -1795,8 +1791,9 @@ static void process_command_flags(struct cardstate *cs)
        }
 
        /* only switch back to unimodem mode, if no commands are pending and no channels are up */
+       spin_lock_irqsave(&cs->lock, flags);
        if (cs->at_state.pending_commands == PC_UMMODE
-           && !atomic_read(&cs->cidmode)
+           && !cs->cidmode
            && list_empty(&cs->temp_at_states)
            && atomic_read(&cs->mode) == M_CID) {
                sequence = SEQ_UMMODE;
@@ -1810,6 +1807,7 @@ static void process_command_flags(struct cardstate *cs)
                        }
                }
        }
+       spin_unlock_irqrestore(&cs->lock, flags);
        cs->at_state.pending_commands &= ~PC_UMMODE;
        if (sequence != SEQ_NONE) {
                schedule_sequence(cs, at_state, sequence);
@@ -1865,11 +1863,7 @@ static void process_command_flags(struct cardstate *cs)
        if (cs->at_state.pending_commands & PC_CIDMODE) {
                cs->at_state.pending_commands &= ~PC_CIDMODE;
                if (atomic_read(&cs->mode) == M_UNIMODEM) {
-#if 0
-                       cs->retry_count = 2;
-#else
                        cs->retry_count = 1;
-#endif
                        schedule_sequence(cs, &cs->at_state, SEQ_CIDMODE);
                        return;
                }
@@ -1897,7 +1891,7 @@ static void process_command_flags(struct cardstate *cs)
                        switch (atomic_read(&cs->mode)) {
                        case M_UNIMODEM:
                                cs->at_state.pending_commands |= PC_CIDMODE;
-                               dbg(DEBUG_CMD, "Scheduling PC_CIDMODE");
+                               gig_dbg(DEBUG_CMD, "Scheduling PC_CIDMODE");
                                atomic_set(&cs->commands_pending, 1);
                                return;
 #ifdef GIG_MAYINITONDIAL
@@ -1926,18 +1920,21 @@ static void process_events(struct cardstate *cs)
        int i;
        int check_flags = 0;
        int was_busy;
+       unsigned long flags;
 
-       /* no locking needed (only one reader) */
-       head = atomic_read(&cs->ev_head);
+       spin_lock_irqsave(&cs->ev_lock, flags);
+       head = cs->ev_head;
 
        for (i = 0; i < 2 * MAX_EVENTS; ++i) {
-               tail = atomic_read(&cs->ev_tail);
+               tail = cs->ev_tail;
                if (tail == head) {
                        if (!check_flags && !atomic_read(&cs->commands_pending))
                                break;
                        check_flags = 0;
+                       spin_unlock_irqrestore(&cs->ev_lock, flags);
                        process_command_flags(cs);
-                       tail = atomic_read(&cs->ev_tail);
+                       spin_lock_irqsave(&cs->ev_lock, flags);
+                       tail = cs->ev_tail;
                        if (tail == head) {
                                if (!atomic_read(&cs->commands_pending))
                                        break;
@@ -1947,18 +1944,23 @@ static void process_events(struct cardstate *cs)
 
                ev = cs->events + head;
                was_busy = cs->cur_at_seq != SEQ_NONE;
+               spin_unlock_irqrestore(&cs->ev_lock, flags);
                process_event(cs, ev);
+               spin_lock_irqsave(&cs->ev_lock, flags);
                kfree(ev->ptr);
                ev->ptr = NULL;
                if (was_busy && cs->cur_at_seq == SEQ_NONE)
                        check_flags = 1;
 
                head = (head + 1) % MAX_EVENTS;
-               atomic_set(&cs->ev_head, head);
+               cs->ev_head = head;
        }
 
+       spin_unlock_irqrestore(&cs->ev_lock, flags);
+
        if (i == 2 * MAX_EVENTS) {
-               err("infinite loop in process_events; aborting.");
+               dev_err(cs->dev,
+                       "infinite loop in process_events; aborting.\n");
        }
 }
 
@@ -1970,12 +1972,9 @@ void gigaset_handle_event(unsigned long data)
 {
        struct cardstate *cs = (struct cardstate *) data;
 
-       IFNULLRET(cs);
-       IFNULLRET(cs->inbuf);
-
        /* handle incoming data on control/common channel */
        if (atomic_read(&cs->inbuf->head) != atomic_read(&cs->inbuf->tail)) {
-               dbg(DEBUG_INTR, "processing new data");
+               gig_dbg(DEBUG_INTR, "processing new data");
                cs->ops->handle_input(cs->inbuf);
        }
 
index 729edcdb6dacdf7d2d7e7b1d87a3b6e50097306c..9d21ba8757b04ea6b97c104739d8eb7191596e18 100644 (file)
@@ -1,11 +1,16 @@
-/* Siemens Gigaset 307x driver
+/*
+ * Siemens Gigaset 307x driver
  * Common header file for all connection variants
  *
- * Written by Stefan Eilers <Eilers.Stefan@epost.de>
+ * Written by Stefan Eilers
  *        and Hansjoerg Lipp <hjlipp@web.de>
  *
- * Version: $Id: gigaset.h,v 1.97.4.26 2006/02/04 18:28:16 hjlipp Exp $
- * ===========================================================================
+ * =====================================================================
+ *     This program is free software; you can redistribute it and/or
+ *     modify it under the terms of the GNU General Public License as
+ *     published by the Free Software Foundation; either version 2 of
+ *     the License, or (at your option) any later version.
+ * =====================================================================
  */
 
 #ifndef GIGASET_H
@@ -15,7 +20,6 @@
 #include <linux/kernel.h>
 #include <linux/compiler.h>
 #include <linux/types.h>
-#include <asm/atomic.h>
 #include <linux/spinlock.h>
 #include <linux/isdnif.h>
 #include <linux/usb.h>
 #include <linux/tty.h>
 #include <linux/tty_driver.h>
 #include <linux/list.h>
+#include <asm/atomic.h>
 
 #define GIG_VERSION {0,5,0,0}
 #define GIG_COMPAT  {0,4,0,0}
 
-#define MAX_REC_PARAMS 10                         /* Max. number of params in response string */
-#define MAX_RESP_SIZE 512                         /* Max. size of a response string */
-#define HW_HDR_LEN 2                              /* Header size used to store ack info */
+#define MAX_REC_PARAMS 10      /* Max. number of params in response string */
+#define MAX_RESP_SIZE 512      /* Max. size of a response string */
+#define HW_HDR_LEN 2           /* Header size used to store ack info */
 
-#define MAX_EVENTS 64                          /* size of event queue */
+#define MAX_EVENTS 64          /* size of event queue */
 
 #define RBUFSIZE 8192
-#define SBUFSIZE 4096                          /* sk_buff payload size */
+#define SBUFSIZE 4096          /* sk_buff payload size */
 
-#define MAX_BUF_SIZE (SBUFSIZE - 2)            /* Max. size of a data packet from LL */
-#define TRANSBUFSIZE 768                       /* bytes per skb for transparent receive */
+#define TRANSBUFSIZE 768       /* bytes per skb for transparent receive */
+#define MAX_BUF_SIZE (SBUFSIZE - 2)    /* Max. size of a data packet from LL */
 
 /* compile time options */
 #define GIG_MAJOR 0
 #define GIG_RETRYCID
 #define GIG_X75
 
-#define MAX_TIMER_INDEX 1000
-#define MAX_SEQ_INDEX   1000
-
-#define GIG_TICK (HZ / 10)
+#define GIG_TICK 100           /* in milliseconds */
 
 /* timeout values (unit: 1 sec) */
 #define INIT_TIMEOUT 1
 
 #define MAXACT 3
 
-#define IFNULL(a)         if (unlikely(!(a)))
-#define IFNULLRET(a)      if (unlikely(!(a))) {err("%s==NULL at %s:%d!", #a, __FILE__, __LINE__); return; }
-#define IFNULLRETVAL(a,b) if (unlikely(!(a))) {err("%s==NULL at %s:%d!", #a, __FILE__, __LINE__); return (b); }
-#define IFNULLCONT(a)     if (unlikely(!(a))) {err("%s==NULL at %s:%d!", #a, __FILE__, __LINE__); continue; }
-#define IFNULLGOTO(a,b)   if (unlikely(!(a))) {err("%s==NULL at %s:%d!", #a, __FILE__, __LINE__); goto b; }
-
 extern int gigaset_debuglevel; /* "needs" cast to (enum debuglevel) */
 
-/* any combination of these can be given with the 'debug=' parameter to insmod, e.g.
- * 'insmod usb_gigaset.o debug=0x2c' will set DEBUG_OPEN, DEBUG_CMD and DEBUG_INTR. */
+/* any combination of these can be given with the 'debug=' parameter to insmod,
+ * e.g. 'insmod usb_gigaset.o debug=0x2c' will set DEBUG_OPEN, DEBUG_CMD and
+ * DEBUG_INTR.
+ */
 enum debuglevel { /* up to 24 bits (atomic_t) */
        DEBUG_REG         = 0x0002, /* serial port I/O register operations */
        DEBUG_OPEN        = 0x0004, /* open/close serial port */
        DEBUG_INTR        = 0x0008, /* interrupt processing */
-       DEBUG_INTR_DUMP   = 0x0010, /* Activating hexdump debug output on interrupt
-                                     requests, not available as run-time option */
+       DEBUG_INTR_DUMP   = 0x0010, /* Activating hexdump debug output on
+                                      interrupt requests, not available as
+                                      run-time option */
        DEBUG_CMD         = 0x00020, /* sent/received LL commands */
        DEBUG_STREAM      = 0x00040, /* application data stream I/O events */
        DEBUG_STREAM_DUMP = 0x00080, /* application data stream content */
        DEBUG_LLDATA      = 0x00100, /* sent/received LL data */
-       DEBUG_INTR_0      = 0x00200, /* serial port output interrupt processing */
+       DEBUG_INTR_0      = 0x00200, /* serial port interrupt processing */
        DEBUG_DRIVER      = 0x00400, /* driver structure */
        DEBUG_HDLC        = 0x00800, /* M10x HDLC processing */
        DEBUG_WRITE       = 0x01000, /* M105 data write */
-       DEBUG_TRANSCMD    = 0x02000, /*AT-COMMANDS+RESPONSES*/
-       DEBUG_MCMD        = 0x04000, /*COMMANDS THAT ARE SENT VERY OFTEN*/
-       DEBUG_INIT        = 0x08000, /* (de)allocation+initialization of data structures */
+       DEBUG_TRANSCMD    = 0x02000, /* AT-COMMANDS+RESPONSES */
+       DEBUG_MCMD        = 0x04000, /* COMMANDS THAT ARE SENT VERY OFTEN */
+       DEBUG_INIT        = 0x08000, /* (de)allocation+initialization of data
+                                       structures */
        DEBUG_LOCK        = 0x10000, /* semaphore operations */
        DEBUG_OUTPUT      = 0x20000, /* output to device */
-       DEBUG_ISO         = 0x40000, /* isochronous transfers */
+       DEBUG_ISO         = 0x40000, /* isochronous transfers */
        DEBUG_IF          = 0x80000, /* character device operations */
-       DEBUG_USBREQ      = 0x100000, /* USB communication (except payload data) */
-       DEBUG_LOCKCMD     = 0x200000, /* AT commands and responses when MS_LOCKED */
+       DEBUG_USBREQ      = 0x100000, /* USB communication (except payload
+                                        data) */
+       DEBUG_LOCKCMD     = 0x200000, /* AT commands and responses when
+                                        MS_LOCKED */
 
-       DEBUG_ANY         = 0x3fffff, /* print message if any of the others is activated */
+       DEBUG_ANY         = 0x3fffff, /* print message if any of the others is
+                                        activated */
 };
 
-#ifdef CONFIG_GIGASET_DEBUG
-#define DEBUG_DEFAULT (DEBUG_INIT | DEBUG_TRANSCMD | DEBUG_CMD | DEBUG_USBREQ)
-//#define DEBUG_DEFAULT (DEBUG_LOCK | DEBUG_INIT | DEBUG_TRANSCMD | DEBUG_CMD | DEBUF_IF | DEBUG_DRIVER | DEBUG_OUTPUT | DEBUG_INTR)
-#else
-#define DEBUG_DEFAULT 0
+/* missing from linux/device.h ... */
+#ifndef dev_notice
+#define dev_notice(dev, format, arg...)                \
+       dev_printk(KERN_NOTICE , dev , format , ## arg)
 #endif
 
-/* redefine syslog macros to prepend module name instead of entire source path */
-/* The space before the comma in ", ##" is needed by gcc 2.95 */
+/* Kernel message macros for situations where dev_printk and friends cannot be
+ * used for lack of reliable access to a device structure.
+ * linux/usb.h already contains these but in an obsolete form which clutters
+ * the log needlessly, and according to the USB maintainer those should be
+ * removed rather than fixed anyway.
+ */
+#undef err
 #undef info
-#define info(format, arg...) printk(KERN_INFO "%s: " format "\n", THIS_MODULE ? THIS_MODULE->name : "gigaset_hw" , ## arg)
-
-#undef notice
-#define notice(format, arg...) printk(KERN_NOTICE "%s: " format "\n", THIS_MODULE ? THIS_MODULE->name : "gigaset_hw" , ## arg)
-
 #undef warn
-#define warn(format, arg...) printk(KERN_WARNING "%s: " format "\n", THIS_MODULE ? THIS_MODULE->name : "gigaset_hw" , ## arg)
+#undef notice
 
-#undef err
-#define err(format, arg...) printk(KERN_ERR "%s: " format "\n", THIS_MODULE ? THIS_MODULE->name : "gigaset_hw" , ## arg)
+#define err(format, arg...) printk(KERN_ERR KBUILD_MODNAME ": " \
+       format "\n" , ## arg)
+#define info(format, arg...) printk(KERN_INFO KBUILD_MODNAME ": " \
+       format "\n" , ## arg)
+#define warn(format, arg...) printk(KERN_WARNING KBUILD_MODNAME ": " \
+       format "\n" , ## arg)
+#define notice(format, arg...) printk(KERN_NOTICE KBUILD_MODNAME ": " \
+       format "\n" , ## arg)
 
-#undef dbg
 #ifdef CONFIG_GIGASET_DEBUG
-#define dbg(level, format, arg...) do { if (unlikely(((enum debuglevel)gigaset_debuglevel) & (level))) \
-       printk(KERN_DEBUG "%s: " format "\n", THIS_MODULE ? THIS_MODULE->name : "gigaset_hw" , ## arg); } while (0)
+
+#define gig_dbg(level, format, arg...) \
+       do { \
+               if (unlikely(((enum debuglevel)gigaset_debuglevel) & (level))) \
+                       printk(KERN_DEBUG KBUILD_MODNAME ": " format "\n", \
+                              ## arg); \
+       } while (0)
+#define DEBUG_DEFAULT (DEBUG_INIT | DEBUG_TRANSCMD | DEBUG_CMD | DEBUG_USBREQ)
+
 #else
-#define dbg(level, format, arg...) do {} while (0)
+
+#define gig_dbg(level, format, arg...) do {} while (0)
+#define DEBUG_DEFAULT 0
+
 #endif
 
 void gigaset_dbg_buffer(enum debuglevel level, const unsigned char *msg,
-                        size_t len, const unsigned char *buf, int from_user);
+                       size_t len, const unsigned char *buf);
 
 /* connection state */
 #define ZSAU_NONE                      0
@@ -148,13 +165,14 @@ void gigaset_dbg_buffer(enum debuglevel level, const unsigned char *msg,
 #define ZSAU_UNKNOWN                   -1
 
 /* USB control transfer requests */
-#define OUT_VENDOR_REQ                 (USB_DIR_OUT | USB_TYPE_VENDOR | USB_RECIP_ENDPOINT)
-#define IN_VENDOR_REQ                  (USB_DIR_IN | USB_TYPE_VENDOR | USB_RECIP_ENDPOINT)
+#define OUT_VENDOR_REQ (USB_DIR_OUT | USB_TYPE_VENDOR | USB_RECIP_ENDPOINT)
+#define IN_VENDOR_REQ  (USB_DIR_IN | USB_TYPE_VENDOR | USB_RECIP_ENDPOINT)
 
 /* int-in-events 3070 */
 #define HD_B1_FLOW_CONTROL             0x80
 #define HD_B2_FLOW_CONTROL             0x81
-#define HD_RECEIVEATDATA_ACK           (0x35)          // 3070         // att: HD_RECEIVE>>AT<<DATA_ACK
+#define HD_RECEIVEATDATA_ACK           (0x35)          // 3070
+                                               // att: HD_RECEIVE>>AT<<DATA_ACK
 #define HD_READY_SEND_ATDATA           (0x36)          // 3070
 #define HD_OPEN_ATCHANNEL_ACK          (0x37)          // 3070
 #define HD_CLOSE_ATCHANNEL_ACK         (0x38)          // 3070
@@ -181,17 +199,18 @@ void gigaset_dbg_buffer(enum debuglevel level, const unsigned char *msg,
 #define        HD_CLOSE_ATCHANNEL              (0x29)          // 3070
 
 /* USB frames for isochronous transfer */
-#define BAS_FRAMETIME  1               /* number of milliseconds between frames */
-#define BAS_NUMFRAMES  8               /* number of frames per URB */
-#define BAS_MAXFRAME   16              /* allocated bytes per frame */
-#define BAS_NORMFRAME  8               /* send size without flow control */
-#define BAS_HIGHFRAME  10              /* "    "    with positive flow control */
-#define BAS_LOWFRAME   5               /* "    "    with negative flow control */
-#define BAS_CORRFRAMES 4               /* flow control multiplicator */
-
-#define BAS_INBUFSIZE  (BAS_MAXFRAME * BAS_NUMFRAMES) /* size of isochronous input buffer per URB */
-#define BAS_OUTBUFSIZE 4096            /* size of common isochronous output buffer */
-#define BAS_OUTBUFPAD  BAS_MAXFRAME    /* size of pad area for isochronous output buffer */
+#define BAS_FRAMETIME  1       /* number of milliseconds between frames */
+#define BAS_NUMFRAMES  8       /* number of frames per URB */
+#define BAS_MAXFRAME   16      /* allocated bytes per frame */
+#define BAS_NORMFRAME  8       /* send size without flow control */
+#define BAS_HIGHFRAME  10      /* "    "    with positive flow control */
+#define BAS_LOWFRAME   5       /* "    "    with negative flow control */
+#define BAS_CORRFRAMES 4       /* flow control multiplicator */
+
+#define BAS_INBUFSIZE  (BAS_MAXFRAME * BAS_NUMFRAMES)
+                                       /* size of isoc in buf per URB */
+#define BAS_OUTBUFSIZE 4096            /* size of common isoc out buffer */
+#define BAS_OUTBUFPAD  BAS_MAXFRAME    /* size of pad area for isoc out buf */
 
 #define BAS_INURBS     3
 #define BAS_OUTURBS    3
@@ -207,40 +226,40 @@ void gigaset_dbg_buffer(enum debuglevel level, const unsigned char *msg,
 #define AT_NUM         7
 
 /* variables in struct at_state_t */
-#define VAR_ZSAU   0
-#define VAR_ZDLE   1
-#define VAR_ZVLS   2
-#define VAR_ZCTP   3
-#define VAR_NUM    4
-
-#define STR_NMBR   0
-#define STR_ZCPN   1
-#define STR_ZCON   2
-#define STR_ZBC    3
-#define STR_ZHLC   4
-#define STR_NUM    5
-
-#define EV_TIMEOUT      -105
-#define EV_IF_VER       -106
-#define EV_PROC_CIDMODE -107
-#define EV_SHUTDOWN     -108
-#define EV_START        -110
-#define EV_STOP         -111
-#define EV_IF_LOCK      -112
-#define EV_PROTO_L2     -113
-#define EV_ACCEPT       -114
-#define EV_DIAL         -115
-#define EV_HUP          -116
-#define EV_BC_OPEN      -117
-#define EV_BC_CLOSED    -118
+#define VAR_ZSAU       0
+#define VAR_ZDLE       1
+#define VAR_ZVLS       2
+#define VAR_ZCTP       3
+#define VAR_NUM                4
+
+#define STR_NMBR       0
+#define STR_ZCPN       1
+#define STR_ZCON       2
+#define STR_ZBC                3
+#define STR_ZHLC       4
+#define STR_NUM                5
+
+#define EV_TIMEOUT     -105
+#define EV_IF_VER      -106
+#define EV_PROC_CIDMODE        -107
+#define EV_SHUTDOWN    -108
+#define EV_START       -110
+#define EV_STOP                -111
+#define EV_IF_LOCK     -112
+#define EV_PROTO_L2    -113
+#define EV_ACCEPT      -114
+#define EV_DIAL                -115
+#define EV_HUP         -116
+#define EV_BC_OPEN     -117
+#define EV_BC_CLOSED   -118
 
 /* input state */
-#define INS_command     0x0001
-#define INS_DLE_char    0x0002
-#define INS_byte_stuff  0x0004
-#define INS_have_data   0x0008
-#define INS_skip_frame  0x0010
-#define INS_DLE_command 0x0020
+#define INS_command    0x0001
+#define INS_DLE_char   0x0002
+#define INS_byte_stuff 0x0004
+#define INS_have_data  0x0008
+#define INS_skip_frame 0x0010
+#define INS_DLE_command        0x0020
 #define INS_flag_hunt  0x0040
 
 /* channel state */
@@ -248,27 +267,27 @@ void gigaset_dbg_buffer(enum debuglevel level, const unsigned char *msg,
 #define CHS_B_UP       0x02
 #define CHS_NOTIFY_LL  0x04
 
-#define ICALL_REJECT  0
-#define ICALL_ACCEPT  1
-#define ICALL_IGNORE  2
+#define ICALL_REJECT   0
+#define ICALL_ACCEPT   1
+#define ICALL_IGNORE   2
 
 /* device state */
-#define MS_UNINITIALIZED        0
-#define MS_INIT                 1
-#define MS_LOCKED               2
-#define MS_SHUTDOWN             3
-#define MS_RECOVER              4
-#define MS_READY                5
+#define MS_UNINITIALIZED       0
+#define MS_INIT                        1
+#define MS_LOCKED              2
+#define MS_SHUTDOWN            3
+#define MS_RECOVER             4
+#define MS_READY               5
 
 /* mode */
-#define M_UNKNOWN       0
-#define M_CONFIG        1
-#define M_UNIMODEM      2
-#define M_CID           3
+#define M_UNKNOWN      0
+#define M_CONFIG       1
+#define M_UNIMODEM     2
+#define M_CID          3
 
 /* start mode */
-#define SM_LOCKED       0
-#define SM_ISDN         1 /* default */
+#define SM_LOCKED      0
+#define SM_ISDN                1 /* default */
 
 struct gigaset_ops;
 struct gigaset_driver;
@@ -283,27 +302,26 @@ struct ser_bc_state;
 struct bas_bc_state;
 
 struct reply_t {
-       int     resp_code;      /* RSP_XXXX */
-       int     min_ConState;   /* <0 => ignore */
-       int     max_ConState;   /* <0 => ignore */
-       int     parameter;      /* e.g. ZSAU_XXXX <0: ignore*/
-       int     new_ConState;   /* <0 => ignore */
-       int     timeout;        /* >0 => *HZ; <=0 => TOUT_XXXX*/
-       int     action[MAXACT]; /* ACT_XXXX */
-       char *command;        /* NULL==none */
+       int     resp_code;      /* RSP_XXXX */
+       int     min_ConState;   /* <0 => ignore */
+       int     max_ConState;   /* <0 => ignore */
+       int     parameter;      /* e.g. ZSAU_XXXX <0: ignore*/
+       int     new_ConState;   /* <0 => ignore */
+       int     timeout;        /* >0 => *HZ; <=0 => TOUT_XXXX*/
+       int     action[MAXACT]; /* ACT_XXXX */
+       char    *command;       /* NULL==none */
 };
 
 extern struct reply_t gigaset_tab_cid_m10x[];
 extern struct reply_t gigaset_tab_nocid_m10x[];
 
 struct inbuf_t {
-       unsigned char           *rcvbuf;                /* usb-gigaset receive buffer */
+       unsigned char           *rcvbuf;        /* usb-gigaset receive buffer */
        struct bc_state         *bcs;
-       struct cardstate *cs;
-       int inputstate;
-
-       atomic_t head, tail;
-       unsigned char data[RBUFSIZE];
+       struct cardstate        *cs;
+       int                     inputstate;
+       atomic_t                head, tail;
+       unsigned char           data[RBUFSIZE];
 };
 
 /* isochronous write buffer structure
@@ -319,16 +337,9 @@ struct inbuf_t {
  *   if writesem <= 0, data[write..read-1] is currently being written to
  * - idle contains the byte value to repeat when the end of valid data is
  *   reached; if nextread==write (buffer contains no data to send), either the
- *   BAS_OUTBUFPAD bytes immediately before data[write] (if write>=BAS_OUTBUFPAD)
- *   or those of the pad area (if write<BAS_OUTBUFPAD) are also filled with that
- *   value
- * - optionally, the following statistics on the buffer's usage can be collected:
- *   maxfill: maximum number of bytes occupied
- *   idlefills: number of times a frame of idle bytes is prepared
- *   emptygets: number of times the buffer was empty when a data frame was requested
- *   backtoback: number of times two data packets were entered into the buffer
- *    without intervening idle flags
- *   nakedback: set if no idle flags have been inserted since the last data packet
+ *   BAS_OUTBUFPAD bytes immediately before data[write] (if
+ *   write>=BAS_OUTBUFPAD) or those of the pad area (if write<BAS_OUTBUFPAD)
+ *   are also filled with that value
  */
 struct isowbuf_t {
        atomic_t        read;
@@ -358,34 +369,28 @@ struct isow_urbctx_t {
  * it is currently assigned a B channel
  */
 struct at_state_t {
-       struct list_head        list;
-       int                     waiting;
-       int                     getstring;
-       atomic_t                timer_index;
+       struct list_head        list;
+       int                     waiting;
+       int                     getstring;
+       unsigned                timer_index;
        unsigned long           timer_expires;
        int                     timer_active;
-       unsigned int            ConState;                           /* State of connection */
-       struct reply_t          *replystruct;
-       int                     cid;
-       int                     int_var[VAR_NUM];   /* see VAR_XXXX */
-       char                    *str_var[STR_NUM];  /* see STR_XXXX */
-       unsigned                pending_commands;   /* see PC_XXXX */
-       atomic_t                seq_index;
-
-       struct cardstate    *cs;
-       struct bc_state         *bcs;
+       unsigned int            ConState;       /* State of connection */
+       struct reply_t          *replystruct;
+       int                     cid;
+       int                     int_var[VAR_NUM];       /* see VAR_XXXX */
+       char                    *str_var[STR_NUM];      /* see STR_XXXX */
+       unsigned                pending_commands;       /* see PC_XXXX */
+       unsigned                seq_index;
+
+       struct cardstate        *cs;
+       struct bc_state         *bcs;
 };
 
 struct resp_type_t {
        unsigned char   *response;
-       int             resp_code;           /* RSP_XXXX */
-       int             type;                /* RT_XXXX */
-};
-
-struct prot_skb {
-       atomic_t                empty;
-       struct semaphore        *sem;
-       struct sk_buff          *skb;
+       int             resp_code;      /* RSP_XXXX */
+       int             type;           /* RT_XXXX */
 };
 
 struct event_t {
@@ -398,29 +403,29 @@ struct event_t {
 
 /* This buffer holds all information about the used B-Channel */
 struct bc_state {
-       struct sk_buff *tx_skb;                        /* Current transfer buffer to modem */
-       struct sk_buff_head squeue;                    /* B-Channel send Queue */
+       struct sk_buff *tx_skb;         /* Current transfer buffer to modem */
+       struct sk_buff_head squeue;     /* B-Channel send Queue */
 
        /* Variables for debugging .. */
-       int corrupted;                                   /* Counter for corrupted packages */
-       int trans_down;                                  /* Counter of packages (downstream) */
-       int trans_up;                                    /* Counter of packages (upstream) */
+       int corrupted;                  /* Counter for corrupted packages */
+       int trans_down;                 /* Counter of packages (downstream) */
+       int trans_up;                   /* Counter of packages (upstream) */
 
        struct at_state_t at_state;
        unsigned long rcvbytes;
 
        __u16 fcs;
        struct sk_buff *skb;
-       int inputstate; /* see INS_XXXX */
+       int inputstate;                 /* see INS_XXXX */
 
        int channel;
 
        struct cardstate *cs;
 
-       unsigned chstate;                       /* bitmap (CHS_*) */
+       unsigned chstate;               /* bitmap (CHS_*) */
        int ignore;
-       unsigned        proto2;                 /* Layer 2 protocol (ISDN_PROTO_L2_*) */
-       char            *commands[AT_NUM]; /* see AT_XXXX */
+       unsigned proto2;                /* Layer 2 protocol (ISDN_PROTO_L2_*) */
+       char *commands[AT_NUM];         /* see AT_XXXX */
 
 #ifdef CONFIG_GIGASET_DEBUG
        int emptycount;
@@ -428,37 +433,39 @@ struct bc_state {
        int busy;
        int use_count;
 
-       /* hardware drivers */
+       /* private data of hardware drivers */
        union {
-               struct ser_bc_state *ser;                /* private data of serial hardware driver */
-               struct usb_bc_state *usb;                /* private data of usb hardware driver */
-               struct bas_bc_state *bas;
+               struct ser_bc_state *ser;       /* serial hardware driver */
+               struct usb_bc_state *usb;       /* usb hardware driver (m105) */
+               struct bas_bc_state *bas;       /* usb hardware driver (base) */
        } hw;
 };
 
 struct cardstate {
        struct gigaset_driver *driver;
        unsigned minor_index;
+       struct device *dev;
 
        const struct gigaset_ops *ops;
 
        /* Stuff to handle communication */
-       //wait_queue_head_t initwait;
        wait_queue_head_t waitqueue;
        int waiting;
-       atomic_t mode;                       /* see M_XXXX */
-       atomic_t mstate;                     /* Modem state: see MS_XXXX */
-                                            /* only changed by the event layer */
+       atomic_t mode;                  /* see M_XXXX */
+       atomic_t mstate;                /* Modem state: see MS_XXXX */
+                                       /* only changed by the event layer */
        int cmd_result;
 
        int channels;
-       struct bc_state *bcs;                /* Array of struct bc_state */
+       struct bc_state *bcs;           /* Array of struct bc_state */
 
-       int onechannel;                      /* data and commands transmitted in one stream (M10x) */
+       int onechannel;                 /* data and commands transmitted in one
+                                          stream (M10x) */
 
        spinlock_t lock;
-       struct at_state_t at_state;          /* at_state_t for cid == 0 */
-       struct list_head temp_at_states;     /* list of temporary "struct at_state_t"s without B channel */
+       struct at_state_t at_state;     /* at_state_t for cid == 0 */
+       struct list_head temp_at_states;/* list of temporary "struct
+                                          at_state_t"s without B channel */
 
        struct inbuf_t *inbuf;
 
@@ -474,58 +481,69 @@ struct cardstate {
        unsigned fwver[4];
        int gotfwver;
 
-       atomic_t running;                    /* !=0 if events are handled */
-       atomic_t connected;                  /* !=0 if hardware is connected */
+       unsigned running;               /* !=0 if events are handled */
+       unsigned connected;             /* !=0 if hardware is connected */
+       unsigned isdn_up;               /* !=0 after ISDN_STAT_RUN */
 
-       atomic_t cidmode;
+       unsigned cidmode;
 
-       int myid;                            /* id for communication with LL */
+       int myid;                       /* id for communication with LL */
        isdn_if iif;
 
        struct reply_t *tabnocid;
        struct reply_t *tabcid;
        int cs_init;
-       int ignoreframes;                    /* frames to ignore after setting up the B channel */
-       struct semaphore sem;                /* locks this structure: */
-                                            /*   connected is not changed, */
-                                            /*   hardware_up is not changed, */
-                                            /*   MState is not changed to or from MS_LOCKED */
+       int ignoreframes;               /* frames to ignore after setting up the
+                                          B channel */
+       struct mutex mutex;             /* locks this structure:
+                                        *   connected is not changed,
+                                        *   hardware_up is not changed,
+                                        *   MState is not changed to or from
+                                        *   MS_LOCKED */
 
        struct timer_list timer;
        int retry_count;
-       int dle;                             /* !=0 if modem commands/responses are dle encoded */
-       int cur_at_seq;                      /* sequence of AT commands being processed */
-       int curchannel;                      /* channel, those commands are meant for */
-       atomic_t commands_pending;           /* flag(s) in xxx.commands_pending have been set */
-       struct tasklet_struct event_tasklet; /* tasklet for serializing AT commands. Scheduled
-                                             *   -> for modem reponses (and incomming data for M10x)
-                                             *   -> on timeout
-                                             *   -> after setting bits in xxx.at_state.pending_command
-                                             *      (e.g. command from LL) */
-       struct tasklet_struct write_tasklet; /* tasklet for serial output
-                                             * (not used in base driver) */
+       int dle;                        /* !=0 if modem commands/responses are
+                                          dle encoded */
+       int cur_at_seq;                 /* sequence of AT commands being
+                                          processed */
+       int curchannel;                 /* channel those commands are meant
+                                          for */
+       atomic_t commands_pending;      /* flag(s) in xxx.commands_pending have
+                                          been set */
+       struct tasklet_struct event_tasklet;
+                                       /* tasklet for serializing AT commands.
+                                        * Scheduled
+                                        *   -> for modem reponses (and
+                                        *      incoming data for M10x)
+                                        *   -> on timeout
+                                        *   -> after setting bits in
+                                        *      xxx.at_state.pending_command
+                                        *      (e.g. command from LL) */
+       struct tasklet_struct write_tasklet;
+                                       /* tasklet for serial output
+                                        * (not used in base driver) */
 
        /* event queue */
        struct event_t events[MAX_EVENTS];
-       atomic_t ev_tail, ev_head;
+       unsigned ev_tail, ev_head;
        spinlock_t ev_lock;
 
        /* current modem response */
        unsigned char respdata[MAX_RESP_SIZE];
        unsigned cbytes;
 
-       /* hardware drivers */
+       /* private data of hardware drivers */
        union {
-               struct usb_cardstate *usb; /* private data of USB hardware driver */
-               struct ser_cardstate *ser; /* private data of serial hardware driver */
-               struct bas_cardstate *bas; /* private data of base hardware driver */
+               struct usb_cardstate *usb; /* USB hardware driver (m105) */
+               struct ser_cardstate *ser; /* serial hardware driver */
+               struct bas_cardstate *bas; /* USB hardware driver (base) */
        } hw;
 };
 
 struct gigaset_driver {
        struct list_head list;
-       spinlock_t lock;                       /* locks minor tables and blocked */
-       //struct semaphore sem;                /* locks this structure */
+       spinlock_t lock;                /* locks minor tables and blocked */
        struct tty_driver *tty;
        unsigned have_tty;
        unsigned minor;
@@ -553,37 +571,42 @@ struct bas_bc_state {
        struct isow_urbctx_t    isoouturbs[BAS_OUTURBS];
        struct isow_urbctx_t    *isooutdone, *isooutfree, *isooutovfl;
        struct isowbuf_t        *isooutbuf;
-       unsigned numsub;                        /* submitted URB counter (for diagnostic messages only) */
+       unsigned numsub;                /* submitted URB counter
+                                          (for diagnostic messages only) */
        struct tasklet_struct   sent_tasklet;
 
        /* isochronous input state */
        spinlock_t isoinlock;
        struct urb *isoinurbs[BAS_INURBS];
        unsigned char isoinbuf[BAS_INBUFSIZE * BAS_INURBS];
-       struct urb *isoindone;                  /* completed isoc read URB */
-       int loststatus;                         /* status of dropped URB */
-       unsigned isoinlost;                     /* number of bytes lost */
-       /* state of bit unstuffing algorithm (in addition to BC_state.inputstate) */
-       unsigned seqlen;                        /* number of '1' bits not yet unstuffed */
-       unsigned inbyte, inbits;                /* collected bits for next byte */
+       struct urb *isoindone;          /* completed isoc read URB */
+       int loststatus;                 /* status of dropped URB */
+       unsigned isoinlost;             /* number of bytes lost */
+       /* state of bit unstuffing algorithm
+          (in addition to BC_state.inputstate) */
+       unsigned seqlen;                /* number of '1' bits not yet
+                                          unstuffed */
+       unsigned inbyte, inbits;        /* collected bits for next byte */
        /* statistics */
-       unsigned goodbytes;                     /* bytes correctly received */
-       unsigned alignerrs;                     /* frames with incomplete byte at end */
-       unsigned fcserrs;                       /* FCS errors */
-       unsigned frameerrs;                     /* framing errors */
-       unsigned giants;                        /* long frames */
-       unsigned runts;                         /* short frames */
-       unsigned aborts;                        /* HDLC aborts */
-       unsigned shared0s;                      /* '0' bits shared between flags */
-       unsigned stolen0s;                      /* '0' stuff bits also serving as leading flag bits */
+       unsigned goodbytes;             /* bytes correctly received */
+       unsigned alignerrs;             /* frames with incomplete byte at end */
+       unsigned fcserrs;               /* FCS errors */
+       unsigned frameerrs;             /* framing errors */
+       unsigned giants;                /* long frames */
+       unsigned runts;                 /* short frames */
+       unsigned aborts;                /* HDLC aborts */
+       unsigned shared0s;              /* '0' bits shared between flags */
+       unsigned stolen0s;              /* '0' stuff bits also serving as
+                                          leading flag bits */
        struct tasklet_struct rcvd_tasklet;
 };
 
 struct gigaset_ops {
-       /* Called from ev-layer.c/interface.c for sending AT commands to the device */
+       /* Called from ev-layer.c/interface.c for sending AT commands to the
+          device */
        int (*write_cmd)(struct cardstate *cs,
-                        const unsigned char *buf, int len,
-                        struct tasklet_struct *wake_tasklet);
+                        const unsigned char *buf, int len,
+                        struct tasklet_struct *wake_tasklet);
 
        /* Called from interface.c for additional device control */
        int (*write_room)(struct cardstate *cs);
@@ -604,7 +627,8 @@ struct gigaset_ops {
        /* Called by gigaset_freecs() for freeing bcs->hw.xxx */
        int (*freebcshw)(struct bc_state *bcs);
 
-       /* Called by gigaset_stop() or gigaset_bchannel_down() for resetting bcs->hw.xxx */
+       /* Called by gigaset_stop() or gigaset_bchannel_down() for resetting
+          bcs->hw.xxx */
        void (*reinitbcshw)(struct bc_state *bcs);
 
        /* Called by gigaset_initcs() for setting up cs->hw.xxx */
@@ -613,13 +637,10 @@ struct gigaset_ops {
        /* Called by gigaset_freecs() for freeing cs->hw.xxx */
        void (*freecshw)(struct cardstate *cs);
 
-       ///* Called by gigaset_stop() for killing URBs, shutting down the device, ...
-       //   hardwareup: ==0: don't try to shut down the device, hardware is really not accessible
-       //             !=0: hardware still up */
-       //void (*stophw)(struct cardstate *cs, int hardwareup);
-
-       /* Called from common.c/interface.c for additional serial port control */
-       int (*set_modem_ctrl)(struct cardstate *cs, unsigned old_state, unsigned new_state);
+       /* Called from common.c/interface.c for additional serial port
+          control */
+       int (*set_modem_ctrl)(struct cardstate *cs, unsigned old_state,
+                             unsigned new_state);
        int (*baud_rate)(struct cardstate *cs, unsigned cflag);
        int (*set_line_ctrl)(struct cardstate *cs, unsigned cflag);
 
@@ -639,7 +660,7 @@ struct gigaset_ops {
  * <DLE_FLAG>:  0x10
  * <EVENT>:     ((a-z)* | (A-Z)* | (0-10)*)+
  */
-#define DLE_FLAG       0x10
+#define DLE_FLAG       0x10
 
 /* ===========================================================================
  *  Functions implemented in asyncdata.c
@@ -667,7 +688,8 @@ void gigaset_isoc_input(struct inbuf_t *inbuf);
 
 /* Called from bas-gigaset.c to process a block of data
  * received through the isochronous channel */
-void gigaset_isoc_receive(unsigned char *src, unsigned count, struct bc_state *bcs);
+void gigaset_isoc_receive(unsigned char *src, unsigned count,
+                         struct bc_state *bcs);
 
 /* Called from bas-gigaset.c to put a block of data
  * into the isochronous output buffer */
@@ -703,7 +725,7 @@ static inline void gigaset_isdn_rcv_err(struct bc_state *bcs)
        isdn_ctrl response;
 
        /* error -> LL */
-       dbg(DEBUG_CMD, "sending L1ERR");
+       gig_dbg(DEBUG_CMD, "sending L1ERR");
        response.driver = bcs->cs->myid;
        response.command = ISDN_STAT_L1ERR;
        response.arg = bcs->channel;
@@ -727,8 +749,8 @@ void gigaset_handle_modem_response(struct cardstate *cs);
  */
 
 /* initialize sysfs for device */
-void gigaset_init_dev_sysfs(struct usb_interface *interface);
-void gigaset_free_dev_sysfs(struct usb_interface *interface);
+void gigaset_init_dev_sysfs(struct cardstate *cs);
+void gigaset_free_dev_sysfs(struct cardstate *cs);
 
 /* ===========================================================================
  *  Functions implemented in common.c/gigaset.h
@@ -736,7 +758,7 @@ void gigaset_free_dev_sysfs(struct usb_interface *interface);
 
 void gigaset_bcs_reinit(struct bc_state *bcs);
 void gigaset_at_init(struct at_state_t *at_state, struct bc_state *bcs,
-                     struct cardstate *cs, int cid);
+                    struct cardstate *cs, int cid);
 int gigaset_get_channel(struct bc_state *bcs);
 void gigaset_free_channel(struct bc_state *bcs);
 int gigaset_get_channels(struct cardstate *cs);
@@ -745,16 +767,15 @@ void gigaset_block_channels(struct cardstate *cs);
 
 /* Allocate and initialize driver structure. */
 struct gigaset_driver *gigaset_initdriver(unsigned minor, unsigned minors,
-                                          const char *procname,
-                                          const char *devname,
-                                          const char *devfsname,
-                                          const struct gigaset_ops *ops,
-                                          struct module *owner);
+                                         const char *procname,
+                                         const char *devname,
+                                         const char *devfsname,
+                                         const struct gigaset_ops *ops,
+                                         struct module *owner);
 
 /* Deallocate driver structure. */
 void gigaset_freedriver(struct gigaset_driver *drv);
 void gigaset_debugdrivers(void);
-struct cardstate *gigaset_get_cs_by_minor(unsigned minor);
 struct cardstate *gigaset_get_cs_by_tty(struct tty_struct *tty);
 struct cardstate *gigaset_get_cs_by_id(int id);
 
@@ -763,7 +784,8 @@ struct cardstate *gigaset_getunassignedcs(struct gigaset_driver *drv);
 void gigaset_unassign(struct cardstate *cs);
 void gigaset_blockdriver(struct gigaset_driver *drv);
 
-/* Allocate and initialize card state. Calls hardware dependent gigaset_init[b]cs(). */
+/* Allocate and initialize card state. Calls hardware dependent
+   gigaset_init[b]cs(). */
 struct cardstate *gigaset_initcs(struct gigaset_driver *drv, int channels,
                                 int onechannel, int ignoreframes,
                                 int cidmode, const char *modulename);
@@ -788,8 +810,8 @@ void gigaset_skb_sent(struct bc_state *bcs, struct sk_buff *skb);
  * ptr must be kmalloc()ed (and not be freed by the caller).
  */
 struct event_t *gigaset_add_event(struct cardstate *cs,
-                                  struct at_state_t *at_state, int type,
-                                  void *ptr, int parameter, void *arg);
+                                 struct at_state_t *at_state, int type,
+                                 void *ptr, int parameter, void *arg);
 
 /* Called on CONFIG1 command from frontend. */
 int gigaset_enterconfigmode(struct cardstate *cs); //0: success <0: errorcode
@@ -799,7 +821,7 @@ static inline void gigaset_schedule_event(struct cardstate *cs)
 {
        unsigned long flags;
        spin_lock_irqsave(&cs->lock, flags);
-       if (atomic_read(&cs->running))
+       if (cs->running)
                tasklet_schedule(&cs->event_tasklet);
        spin_unlock_irqrestore(&cs->lock, flags);
 }
@@ -810,7 +832,7 @@ static inline void gigaset_bchannel_down(struct bc_state *bcs)
 {
        gigaset_add_event(bcs->cs, &bcs->at_state, EV_BC_CLOSED, NULL, 0, NULL);
 
-       dbg(DEBUG_CMD, "scheduling BC_CLOSED");
+       gig_dbg(DEBUG_CMD, "scheduling BC_CLOSED");
        gigaset_schedule_event(bcs->cs);
 }
 
@@ -820,36 +842,19 @@ static inline void gigaset_bchannel_up(struct bc_state *bcs)
 {
        gigaset_add_event(bcs->cs, &bcs->at_state, EV_BC_OPEN, NULL, 0, NULL);
 
-       dbg(DEBUG_CMD, "scheduling BC_OPEN");
+       gig_dbg(DEBUG_CMD, "scheduling BC_OPEN");
        gigaset_schedule_event(bcs->cs);
 }
 
 /* handling routines for sk_buff */
 /* ============================= */
 
-/* private version of __skb_put()
- * append 'len' bytes to the content of 'skb', already knowing that the
- * existing buffer can accomodate them
- * returns a pointer to the location where the new bytes should be copied to
- * This function does not take any locks so it must be called with the
- * appropriate locks held only.
- */
-static inline unsigned char *gigaset_skb_put_quick(struct sk_buff *skb,
-                                                   unsigned int len)
-{
-       unsigned char *tmp = skb->tail;
-       /*SKB_LINEAR_ASSERT(skb);*/             /* not needed here */
-       skb->tail += len;
-       skb->len += len;
-       return tmp;
-}
-
 /* pass received skb to LL
  * Warning: skb must not be accessed anymore!
  */
 static inline void gigaset_rcv_skb(struct sk_buff *skb,
-                                   struct cardstate *cs,
-                                   struct bc_state *bcs)
+                                  struct cardstate *cs,
+                                  struct bc_state *bcs)
 {
        cs->iif.rcvcallb_skb(cs->myid, bcs->channel, skb);
        bcs->trans_down++;
@@ -859,8 +864,8 @@ static inline void gigaset_rcv_skb(struct sk_buff *skb,
  * Warning: skb must not be accessed anymore!
  */
 static inline void gigaset_rcv_error(struct sk_buff *procskb,
-                                     struct cardstate *cs,
-                                     struct bc_state *bcs)
+                                    struct cardstate *cs,
+                                    struct bc_state *bcs)
 {
        if (procskb)
                dev_kfree_skb(procskb);
@@ -877,46 +882,9 @@ static inline void gigaset_rcv_error(struct sk_buff *procskb,
 /* bitwise byte inversion table */
 extern __u8 gigaset_invtab[];  /* in common.c */
 
-
 /* append received bytes to inbuf */
-static inline int gigaset_fill_inbuf(struct inbuf_t *inbuf,
-                                     const unsigned char *src,
-                                     unsigned numbytes)
-{
-       unsigned n, head, tail, bytesleft;
-
-       dbg(DEBUG_INTR, "received %u bytes", numbytes);
-
-       if (!numbytes)
-               return 0;
-
-       bytesleft = numbytes;
-       tail = atomic_read(&inbuf->tail);
-       head = atomic_read(&inbuf->head);
-       dbg(DEBUG_INTR, "buffer state: %u -> %u", head, tail);
-
-       while (bytesleft) {
-               if (head > tail)
-                       n = head - 1 - tail;
-               else if (head == 0)
-                       n = (RBUFSIZE-1) - tail;
-               else
-                       n = RBUFSIZE - tail;
-               if (!n) {
-                       err("buffer overflow (%u bytes lost)", bytesleft);
-                       break;
-               }
-               if (n > bytesleft)
-                       n = bytesleft;
-               memcpy(inbuf->data + tail, src, n);
-               bytesleft -= n;
-               tail = (tail + n) % RBUFSIZE;
-               src += n;
-       }
-       dbg(DEBUG_INTR, "setting tail to %u", tail);
-       atomic_set(&inbuf->tail, tail);
-       return numbytes != bytesleft;
-}
+int gigaset_fill_inbuf(struct inbuf_t *inbuf, const unsigned char *src,
+                      unsigned numbytes);
 
 /* ===========================================================================
  *  Functions implemented in interface.c
@@ -924,7 +892,7 @@ static inline int gigaset_fill_inbuf(struct inbuf_t *inbuf,
 
 /* initialize interface */
 void gigaset_if_initdriver(struct gigaset_driver *drv, const char *procname,
-                           const char *devname, const char *devfsname);
+                          const char *devname, const char *devfsname);
 /* release interface */
 void gigaset_if_freedriver(struct gigaset_driver *drv);
 /* add minor */
@@ -933,6 +901,6 @@ void gigaset_if_init(struct cardstate *cs);
 void gigaset_if_free(struct cardstate *cs);
 /* device received data */
 void gigaset_if_receive(struct cardstate *cs,
-                        unsigned char *buffer, size_t len);
+                       unsigned char *buffer, size_t len);
 
 #endif
index 731a675f21b0b005d27adb9f443984dbae48106b..0815dbfb8291119f6beb58558cdd9290d66c9128 100644 (file)
@@ -1,9 +1,9 @@
 /*
  * Stuff used by all variants of the driver
  *
- * Copyright (c) 2001 by Stefan Eilers (Eilers.Stefan@epost.de),
- *                       Hansjoerg Lipp (hjlipp@web.de),
- *                       Tilman Schmidt (tilman@imap.cc).
+ * Copyright (c) 2001 by Stefan Eilers,
+ *                       Hansjoerg Lipp <hjlipp@web.de>,
+ *                       Tilman Schmidt <tilman@imap.cc>.
  *
  * =====================================================================
  *     This program is free software; you can redistribute it and/or
  *     published by the Free Software Foundation; either version 2 of
  *     the License, or (at your option) any later version.
  * =====================================================================
- * ToDo: ...
- * =====================================================================
- * Version: $Id: i4l.c,v 1.3.2.9 2006/02/04 18:28:16 hjlipp Exp $
- * =====================================================================
  */
 
 #include "gigaset.h"
 
-/* == Handling of I4L IO ============================================================================*/
+/* == Handling of I4L IO =====================================================*/
 
 /* writebuf_from_LL
  * called by LL to transmit data on an open channel
  * parameters:
  *     driverID        driver ID as assigned by LL
  *     channel         channel number
- *     ack             if != 0 LL wants to be notified on completion via statcallb(ISDN_STAT_BSENT)
+ *     ack             if != 0 LL wants to be notified on completion via
+ *                     statcallb(ISDN_STAT_BSENT)
  *     skb             skb containing data to send
  * return value:
  *     number of accepted bytes
  *     0 if temporarily unable to accept data (out of buffer space)
  *     <0 on error (eg. -EINVAL)
  */
-static int writebuf_from_LL(int driverID, int channel, int ack, struct sk_buff *skb)
+static int writebuf_from_LL(int driverID, int channel, int ack,
+                           struct sk_buff *skb)
 {
        struct cardstate *cs;
        struct bc_state *bcs;
@@ -54,31 +52,28 @@ static int writebuf_from_LL(int driverID, int channel, int ack, struct sk_buff *
        bcs = &cs->bcs[channel];
        len = skb->len;
 
-       dbg(DEBUG_LLDATA,
-           "Receiving data from LL (id: %d, channel: %d, ack: %d, size: %d)",
-           driverID, channel, ack, len);
+       gig_dbg(DEBUG_LLDATA,
+               "Receiving data from LL (id: %d, ch: %d, ack: %d, sz: %d)",
+               driverID, channel, ack, len);
 
        if (!len) {
                if (ack)
-                       warn("not ACKing empty packet from LL");
+                       notice("%s: not ACKing empty packet", __func__);
                return 0;
        }
        if (len > MAX_BUF_SIZE) {
-               err("%s: packet too large (%d bytes)", __func__, channel);
+               err("%s: packet too large (%d bytes)", __func__, len);
                return -EINVAL;
        }
 
-       if (!atomic_read(&cs->connected))
-               return -ENODEV;
-
        skblen = ack ? len : 0;
        skb->head[0] = skblen & 0xff;
        skb->head[1] = skblen >> 8;
-       dbg(DEBUG_MCMD, "skb: len=%u, skblen=%u: %02x %02x", len, skblen,
-            (unsigned) skb->head[0], (unsigned) skb->head[1]);
+       gig_dbg(DEBUG_MCMD, "skb: len=%u, skblen=%u: %02x %02x",
+               len, skblen, (unsigned) skb->head[0], (unsigned) skb->head[1]);
 
        /* pass to device-specific module */
-       return cs->ops->send_skb(bcs, skb);
+       return cs->ops->send_skb(bcs, skb); //FIXME cs->ops->send_skb() must handle !cs->connected correctly
 }
 
 void gigaset_skb_sent(struct bc_state *bcs, struct sk_buff *skb)
@@ -89,14 +84,14 @@ void gigaset_skb_sent(struct bc_state *bcs, struct sk_buff *skb)
        ++bcs->trans_up;
 
        if (skb->len)
-               warn("%s: skb->len==%d", __func__, skb->len);
+               dev_warn(bcs->cs->dev, "%s: skb->len==%d\n",
+                        __func__, skb->len);
 
        len = (unsigned char) skb->head[0] |
              (unsigned) (unsigned char) skb->head[1] << 8;
        if (len) {
-               dbg(DEBUG_MCMD,
-                   "Acknowledge sending to LL (id: %d, channel: %d size: %u)",
-                   bcs->cs->myid, bcs->channel, len);
+               gig_dbg(DEBUG_MCMD, "ACKing to LL (id: %d, ch: %d, sz: %u)",
+                       bcs->cs->myid, bcs->channel, len);
 
                response.driver = bcs->cs->myid;
                response.command = ISDN_STAT_BSENT;
@@ -119,15 +114,12 @@ static int command_from_LL(isdn_ctrl *cntrl)
        struct bc_state *bcs;
        int retval = 0;
        struct setup_parm *sp;
+       unsigned param;
+       unsigned long flags;
 
-       //dbg(DEBUG_ANY, "Gigaset_HW: Receiving command");
        gigaset_debugdrivers();
 
-       /* Terminate this call if no device is present. Bt if the command is "ISDN_CMD_LOCK" or
-        * "ISDN_CMD_UNLOCK" then execute it due to the fact that they are device independent !
-        */
-       //FIXME "remove test for &connected"
-       if ((!cs || !atomic_read(&cs->connected))) {
+       if (!cs) {
                warn("LL tried to access unknown device with nr. %d",
                     cntrl->driver);
                return -ENODEV;
@@ -135,29 +127,30 @@ static int command_from_LL(isdn_ctrl *cntrl)
 
        switch (cntrl->command) {
        case ISDN_CMD_IOCTL:
-
-               dbg(DEBUG_ANY, "ISDN_CMD_IOCTL (driver:%d,arg: %ld)",
-                   cntrl->driver, cntrl->arg);
+               gig_dbg(DEBUG_ANY, "ISDN_CMD_IOCTL (driver: %d, arg: %ld)",
+                       cntrl->driver, cntrl->arg);
 
                warn("ISDN_CMD_IOCTL is not supported.");
                return -EINVAL;
 
        case ISDN_CMD_DIAL:
-               dbg(DEBUG_ANY, "ISDN_CMD_DIAL (driver: %d, channel: %ld, "
-                   "phone: %s,ownmsn: %s, si1: %d, si2: %d)",
-                   cntrl->driver, cntrl->arg,
-                   cntrl->parm.setup.phone, cntrl->parm.setup.eazmsn,
-                   cntrl->parm.setup.si1, cntrl->parm.setup.si2);
+               gig_dbg(DEBUG_ANY,
+                       "ISDN_CMD_DIAL (driver: %d, ch: %ld, "
+                       "phone: %s, ownmsn: %s, si1: %d, si2: %d)",
+                       cntrl->driver, cntrl->arg,
+                       cntrl->parm.setup.phone, cntrl->parm.setup.eazmsn,
+                       cntrl->parm.setup.si1, cntrl->parm.setup.si2);
 
                if (cntrl->arg >= cs->channels) {
-                       err("invalid channel (%d)", (int) cntrl->arg);
+                       err("ISDN_CMD_DIAL: invalid channel (%d)",
+                           (int) cntrl->arg);
                        return -EINVAL;
                }
 
                bcs = cs->bcs + cntrl->arg;
 
                if (!gigaset_get_channel(bcs)) {
-                       err("channel not free");
+                       err("ISDN_CMD_DIAL: channel not free");
                        return -EBUSY;
                }
 
@@ -169,42 +162,46 @@ static int command_from_LL(isdn_ctrl *cntrl)
                }
                *sp = cntrl->parm.setup;
 
-               if (!gigaset_add_event(cs, &bcs->at_state, EV_DIAL, sp,
-                                      atomic_read(&bcs->at_state.seq_index),
-                                      NULL)) {
+               spin_lock_irqsave(&cs->lock, flags);
+               param = bcs->at_state.seq_index;
+               spin_unlock_irqrestore(&cs->lock, flags);
+
+               if (!gigaset_add_event(cs, &bcs->at_state, EV_DIAL, sp, param,
+                                      NULL)) {
                        //FIXME what should we do?
                        kfree(sp);
                        gigaset_free_channel(bcs);
                        return -ENOMEM;
                }
 
-               dbg(DEBUG_CMD, "scheduling DIAL");
+               gig_dbg(DEBUG_CMD, "scheduling DIAL");
                gigaset_schedule_event(cs);
                break;
        case ISDN_CMD_ACCEPTD: //FIXME
-               dbg(DEBUG_ANY, "ISDN_CMD_ACCEPTD");
+               gig_dbg(DEBUG_ANY, "ISDN_CMD_ACCEPTD");
 
                if (cntrl->arg >= cs->channels) {
-                       err("invalid channel (%d)", (int) cntrl->arg);
+                       err("ISDN_CMD_ACCEPTD: invalid channel (%d)",
+                           (int) cntrl->arg);
                        return -EINVAL;
                }
 
                if (!gigaset_add_event(cs, &cs->bcs[cntrl->arg].at_state,
-                                      EV_ACCEPT, NULL, 0, NULL)) {
+                                      EV_ACCEPT, NULL, 0, NULL)) {
                        //FIXME what should we do?
                        return -ENOMEM;
                }
 
-               dbg(DEBUG_CMD, "scheduling ACCEPT");
+               gig_dbg(DEBUG_CMD, "scheduling ACCEPT");
                gigaset_schedule_event(cs);
 
                break;
        case ISDN_CMD_ACCEPTB:
-               dbg(DEBUG_ANY, "ISDN_CMD_ACCEPTB");
+               gig_dbg(DEBUG_ANY, "ISDN_CMD_ACCEPTB");
                break;
        case ISDN_CMD_HANGUP:
-               dbg(DEBUG_ANY,
-                   "ISDN_CMD_HANGUP (channel: %d)", (int) cntrl->arg);
+               gig_dbg(DEBUG_ANY, "ISDN_CMD_HANGUP (ch: %d)",
+                       (int) cntrl->arg);
 
                if (cntrl->arg >= cs->channels) {
                        err("ISDN_CMD_HANGUP: invalid channel (%u)",
@@ -213,66 +210,68 @@ static int command_from_LL(isdn_ctrl *cntrl)
                }
 
                if (!gigaset_add_event(cs, &cs->bcs[cntrl->arg].at_state,
-                                      EV_HUP, NULL, 0, NULL)) {
+                                      EV_HUP, NULL, 0, NULL)) {
                        //FIXME what should we do?
                        return -ENOMEM;
                }
 
-               dbg(DEBUG_CMD, "scheduling HUP");
+               gig_dbg(DEBUG_CMD, "scheduling HUP");
                gigaset_schedule_event(cs);
 
                break;
-       case ISDN_CMD_CLREAZ:               /* Do not signal incoming signals */ //FIXME
-               dbg(DEBUG_ANY, "ISDN_CMD_CLREAZ");
+       case ISDN_CMD_CLREAZ: /* Do not signal incoming signals */ //FIXME
+               gig_dbg(DEBUG_ANY, "ISDN_CMD_CLREAZ");
                break;
-       case ISDN_CMD_SETEAZ:               /* Signal incoming calls for given MSN */ //FIXME
-               dbg(DEBUG_ANY,
-                   "ISDN_CMD_SETEAZ (id:%d, channel: %ld, number: %s)",
-                   cntrl->driver, cntrl->arg, cntrl->parm.num);
+       case ISDN_CMD_SETEAZ: /* Signal incoming calls for given MSN */ //FIXME
+               gig_dbg(DEBUG_ANY,
+                       "ISDN_CMD_SETEAZ (id: %d, ch: %ld, number: %s)",
+                       cntrl->driver, cntrl->arg, cntrl->parm.num);
                break;
-       case ISDN_CMD_SETL2:                /* Set L2 to given protocol */
-               dbg(DEBUG_ANY, "ISDN_CMD_SETL2 (Channel: %ld, Proto: %lx)",
-                    cntrl->arg & 0xff, (cntrl->arg >> 8));
+       case ISDN_CMD_SETL2: /* Set L2 to given protocol */
+               gig_dbg(DEBUG_ANY, "ISDN_CMD_SETL2 (ch: %ld, proto: %lx)",
+                       cntrl->arg & 0xff, (cntrl->arg >> 8));
 
                if ((cntrl->arg & 0xff) >= cs->channels) {
-                       err("invalid channel (%u)",
+                       err("ISDN_CMD_SETL2: invalid channel (%u)",
                            (unsigned) cntrl->arg & 0xff);
                        return -EINVAL;
                }
 
                if (!gigaset_add_event(cs, &cs->bcs[cntrl->arg & 0xff].at_state,
-                                      EV_PROTO_L2, NULL, cntrl->arg >> 8,
-                                      NULL)) {
+                                      EV_PROTO_L2, NULL, cntrl->arg >> 8,
+                                      NULL)) {
                        //FIXME what should we do?
                        return -ENOMEM;
                }
 
-               dbg(DEBUG_CMD, "scheduling PROTO_L2");
+               gig_dbg(DEBUG_CMD, "scheduling PROTO_L2");
                gigaset_schedule_event(cs);
                break;
-       case ISDN_CMD_SETL3:              /* Set L3 to given protocol */
-               dbg(DEBUG_ANY, "ISDN_CMD_SETL3 (Channel: %ld, Proto: %lx)",
-                    cntrl->arg & 0xff, (cntrl->arg >> 8));
+       case ISDN_CMD_SETL3: /* Set L3 to given protocol */
+               gig_dbg(DEBUG_ANY, "ISDN_CMD_SETL3 (ch: %ld, proto: %lx)",
+                       cntrl->arg & 0xff, (cntrl->arg >> 8));
 
                if ((cntrl->arg & 0xff) >= cs->channels) {
-                       err("invalid channel (%u)",
+                       err("ISDN_CMD_SETL3: invalid channel (%u)",
                            (unsigned) cntrl->arg & 0xff);
                        return -EINVAL;
                }
 
                if (cntrl->arg >> 8 != ISDN_PROTO_L3_TRANS) {
-                       err("invalid protocol %lu", cntrl->arg >> 8);
+                       err("ISDN_CMD_SETL3: invalid protocol %lu",
+                           cntrl->arg >> 8);
                        return -EINVAL;
                }
 
                break;
        case ISDN_CMD_PROCEED:
-               dbg(DEBUG_ANY, "ISDN_CMD_PROCEED"); //FIXME
+               gig_dbg(DEBUG_ANY, "ISDN_CMD_PROCEED"); //FIXME
                break;
        case ISDN_CMD_ALERT:
-               dbg(DEBUG_ANY, "ISDN_CMD_ALERT"); //FIXME
+               gig_dbg(DEBUG_ANY, "ISDN_CMD_ALERT"); //FIXME
                if (cntrl->arg >= cs->channels) {
-                       err("invalid channel (%d)", (int) cntrl->arg);
+                       err("ISDN_CMD_ALERT: invalid channel (%d)",
+                           (int) cntrl->arg);
                        return -EINVAL;
                }
                //bcs = cs->bcs + cntrl->arg;
@@ -280,32 +279,31 @@ static int command_from_LL(isdn_ctrl *cntrl)
                // FIXME
                break;
        case ISDN_CMD_REDIR:
-               dbg(DEBUG_ANY, "ISDN_CMD_REDIR"); //FIXME
+               gig_dbg(DEBUG_ANY, "ISDN_CMD_REDIR"); //FIXME
                break;
        case ISDN_CMD_PROT_IO:
-               dbg(DEBUG_ANY, "ISDN_CMD_PROT_IO");
+               gig_dbg(DEBUG_ANY, "ISDN_CMD_PROT_IO");
                break;
        case ISDN_CMD_FAXCMD:
-               dbg(DEBUG_ANY, "ISDN_CMD_FAXCMD");
+               gig_dbg(DEBUG_ANY, "ISDN_CMD_FAXCMD");
                break;
        case ISDN_CMD_GETL2:
-               dbg(DEBUG_ANY, "ISDN_CMD_GETL2");
+               gig_dbg(DEBUG_ANY, "ISDN_CMD_GETL2");
                break;
        case ISDN_CMD_GETL3:
-               dbg(DEBUG_ANY, "ISDN_CMD_GETL3");
+               gig_dbg(DEBUG_ANY, "ISDN_CMD_GETL3");
                break;
        case ISDN_CMD_GETEAZ:
-               dbg(DEBUG_ANY, "ISDN_CMD_GETEAZ");
+               gig_dbg(DEBUG_ANY, "ISDN_CMD_GETEAZ");
                break;
        case ISDN_CMD_SETSIL:
-               dbg(DEBUG_ANY, "ISDN_CMD_SETSIL");
+               gig_dbg(DEBUG_ANY, "ISDN_CMD_SETSIL");
                break;
        case ISDN_CMD_GETSIL:
-               dbg(DEBUG_ANY, "ISDN_CMD_GETSIL");
+               gig_dbg(DEBUG_ANY, "ISDN_CMD_GETSIL");
                break;
        default:
-               err("unknown command %d from LL",
-                    cntrl->command);
+               err("unknown command %d from LL", cntrl->command);
                return -EINVAL;
        }
 
@@ -350,7 +348,8 @@ int gigaset_isdn_setup_dial(struct at_state_t *at_state, void *data)
                proto = 2; /* 0: Bitsynchron, 1: HDLC, 2: voice */
                break;
        default:
-               err("invalid protocol: %u", bcs->proto2);
+               dev_err(bcs->cs->dev, "%s: invalid L2 protocol: %u\n",
+                       __func__, bcs->proto2);
                return -EINVAL;
        }
 
@@ -378,7 +377,7 @@ int gigaset_isdn_setup_dial(struct at_state_t *at_state, void *data)
                bcs->commands[i] = NULL;
                if (length[i] &&
                    !(bcs->commands[i] = kmalloc(length[i], GFP_ATOMIC))) {
-                       err("out of memory");
+                       dev_err(bcs->cs->dev, "out of memory\n");
                        return -ENOMEM;
                }
        }
@@ -396,10 +395,14 @@ int gigaset_isdn_setup_dial(struct at_state_t *at_state, void *data)
        }
 
        if (bcs->commands[AT_MSN])
-               snprintf(bcs->commands[AT_MSN], length[AT_MSN], "^SMSN=%s\r", sp->eazmsn);
-       snprintf(bcs->commands[AT_BC   ], length[AT_BC   ], "^SBC=%s\r", bc);
-       snprintf(bcs->commands[AT_PROTO], length[AT_PROTO], "^SBPR=%u\r", proto);
-       snprintf(bcs->commands[AT_ISO  ], length[AT_ISO  ], "^SISO=%u\r", (unsigned)bcs->channel + 1);
+               snprintf(bcs->commands[AT_MSN], length[AT_MSN],
+                        "^SMSN=%s\r", sp->eazmsn);
+       snprintf(bcs->commands[AT_BC   ], length[AT_BC   ],
+                "^SBC=%s\r", bc);
+       snprintf(bcs->commands[AT_PROTO], length[AT_PROTO],
+                "^SBPR=%u\r", proto);
+       snprintf(bcs->commands[AT_ISO  ], length[AT_ISO  ],
+                "^SISO=%u\r", (unsigned)bcs->channel + 1);
 
        return 0;
 }
@@ -419,7 +422,8 @@ int gigaset_isdn_setup_accept(struct at_state_t *at_state)
                proto = 2; /* 0: Bitsynchron, 1: HDLC, 2: voice */
                break;
        default:
-               err("invalid protocol: %u", bcs->proto2);
+               dev_err(at_state->cs->dev, "%s: invalid protocol: %u\n",
+                       __func__, bcs->proto2);
                return -EINVAL;
        }
 
@@ -436,13 +440,15 @@ int gigaset_isdn_setup_accept(struct at_state_t *at_state)
                bcs->commands[i] = NULL;
                if (length[i] &&
                    !(bcs->commands[i] = kmalloc(length[i], GFP_ATOMIC))) {
-                       err("out of memory");
+                       dev_err(at_state->cs->dev, "out of memory\n");
                        return -ENOMEM;
                }
        }
 
-       snprintf(bcs->commands[AT_PROTO], length[AT_PROTO], "^SBPR=%u\r", proto);
-       snprintf(bcs->commands[AT_ISO  ], length[AT_ISO  ], "^SISO=%u\r", (unsigned) bcs->channel + 1);
+       snprintf(bcs->commands[AT_PROTO], length[AT_PROTO],
+                "^SBPR=%u\r", proto);
+       snprintf(bcs->commands[AT_ISO  ], length[AT_ISO  ],
+                "^SISO=%u\r", (unsigned) bcs->channel + 1);
 
        return 0;
 }
@@ -473,7 +479,7 @@ int gigaset_isdn_icall(struct at_state_t *at_state)
                response.parm.setup.si1 = 1;
                response.parm.setup.si2 = 2;
        } else {
-               warn("RING ignored - unsupported BC %s",
+               dev_warn(cs->dev, "RING ignored - unsupported BC %s\n",
                     at_state->str_var[STR_ZBC]);
                return ICALL_IGNORE;
        }
@@ -491,18 +497,17 @@ int gigaset_isdn_icall(struct at_state_t *at_state)
                response.parm.setup.eazmsn[0] = 0;
 
        if (!bcs) {
-               notice("no channel for incoming call");
-               dbg(DEBUG_CMD, "Sending ICALLW");
+               dev_notice(cs->dev, "no channel for incoming call\n");
                response.command = ISDN_STAT_ICALLW;
                response.arg = 0; //FIXME
        } else {
-               dbg(DEBUG_CMD, "Sending ICALL");
+               gig_dbg(DEBUG_CMD, "Sending ICALL");
                response.command = ISDN_STAT_ICALL;
                response.arg = bcs->channel; //FIXME
        }
        response.driver = cs->myid;
        retval = cs->iif.statcallb(&response);
-       dbg(DEBUG_CMD, "Response: %d", retval);
+       gig_dbg(DEBUG_CMD, "Response: %d", retval);
        switch (retval) {
        case 0: /* no takers */
                return ICALL_IGNORE;
@@ -512,7 +517,8 @@ int gigaset_isdn_icall(struct at_state_t *at_state)
        case 2: /* reject */
                return ICALL_REJECT;
        case 3: /* incomplete */
-               warn("LL requested unsupported feature: Incomplete Number");
+               dev_warn(cs->dev,
+                      "LL requested unsupported feature: Incomplete Number\n");
                return ICALL_IGNORE;
        case 4: /* proceeding */
                /* Gigaset will send ALERTING anyway.
@@ -520,10 +526,11 @@ int gigaset_isdn_icall(struct at_state_t *at_state)
                 */
                return ICALL_ACCEPT;
        case 5: /* deflect */
-               warn("LL requested unsupported feature: Call Deflection");
+               dev_warn(cs->dev,
+                        "LL requested unsupported feature: Call Deflection\n");
                return ICALL_IGNORE;
        default:
-               err("LL error %d on ICALL", retval);
+               dev_err(cs->dev, "LL error %d on ICALL\n", retval);
                return ICALL_IGNORE;
        }
 }
@@ -533,7 +540,7 @@ int gigaset_register_to_LL(struct cardstate *cs, const char *isdnid)
 {
        isdn_if *iif = &cs->iif;
 
-       dbg(DEBUG_ANY, "Register driver capabilities to LL");
+       gig_dbg(DEBUG_ANY, "Register driver capabilities to LL");
 
        //iif->id[sizeof(iif->id) - 1]=0;
        //strncpy(iif->id, isdnid, sizeof(iif->id) - 1);
@@ -542,26 +549,26 @@ int gigaset_register_to_LL(struct cardstate *cs, const char *isdnid)
                return -ENOMEM; //FIXME EINVAL/...??
 
        iif->owner = THIS_MODULE;
-       iif->channels = cs->channels;                        /* I am supporting just one channel *//* I was supporting...*/
+       iif->channels = cs->channels;
        iif->maxbufsize = MAX_BUF_SIZE;
-       iif->features = ISDN_FEATURE_L2_TRANS |   /* Our device is very advanced, therefore */
+       iif->features = ISDN_FEATURE_L2_TRANS |
                ISDN_FEATURE_L2_HDLC |
 #ifdef GIG_X75
                ISDN_FEATURE_L2_X75I |
 #endif
                ISDN_FEATURE_L3_TRANS |
                ISDN_FEATURE_P_EURO;
-       iif->hl_hdrlen = HW_HDR_LEN;              /* Area for storing ack */
+       iif->hl_hdrlen = HW_HDR_LEN;            /* Area for storing ack */
        iif->command = command_from_LL;
        iif->writebuf_skb = writebuf_from_LL;
-       iif->writecmd = NULL;                     /* Don't support isdnctrl */
-       iif->readstat = NULL;                     /* Don't support isdnctrl */
-       iif->rcvcallb_skb = NULL;                 /* Will be set by LL */
-       iif->statcallb = NULL;                    /* Will be set by LL */
+       iif->writecmd = NULL;                   /* Don't support isdnctrl */
+       iif->readstat = NULL;                   /* Don't support isdnctrl */
+       iif->rcvcallb_skb = NULL;               /* Will be set by LL */
+       iif->statcallb = NULL;                  /* Will be set by LL */
 
        if (!register_isdn(iif))
                return 0;
 
-       cs->myid = iif->channels;                 /* Set my device id */
+       cs->myid = iif->channels;               /* Set my device id */
        return 1;
 }
index 3a81d9c65141b17d40490c0cbd0b339c71a187b1..08e4c4eea14d985ecc186e99cc434f76b1334faf 100644 (file)
@@ -9,8 +9,6 @@
  *    published by the Free Software Foundation; either version 2 of
  *    the License, or (at your option) any later version.
  * =====================================================================
- * Version: $Id: interface.c,v 1.14.4.15 2006/02/04 18:28:16 hjlipp Exp $
- * =====================================================================
  */
 
 #include "gigaset.h"
@@ -24,7 +22,7 @@ static int if_lock(struct cardstate *cs, int *arg)
 {
        int cmd = *arg;
 
-       dbg(DEBUG_IF, "%u: if_lock (%d)", cs->minor_index, cmd);
+       gig_dbg(DEBUG_IF, "%u: if_lock (%d)", cs->minor_index, cmd);
 
        if (cmd > 1)
                return -EINVAL;
@@ -35,7 +33,7 @@ static int if_lock(struct cardstate *cs, int *arg)
        }
 
        if (!cmd && atomic_read(&cs->mstate) == MS_LOCKED
-           && atomic_read(&cs->connected)) {
+           && cs->connected) {
                cs->ops->set_modem_ctrl(cs, 0, TIOCM_DTR|TIOCM_RTS);
                cs->ops->baud_rate(cs, B115200);
                cs->ops->set_line_ctrl(cs, CS8);
@@ -44,12 +42,12 @@ static int if_lock(struct cardstate *cs, int *arg)
 
        cs->waiting = 1;
        if (!gigaset_add_event(cs, &cs->at_state, EV_IF_LOCK,
-                              NULL, cmd, NULL)) {
+                              NULL, cmd, NULL)) {
                cs->waiting = 0;
                return -ENOMEM;
        }
 
-       dbg(DEBUG_CMD, "scheduling IF_LOCK");
+       gig_dbg(DEBUG_CMD, "scheduling IF_LOCK");
        gigaset_schedule_event(cs);
 
        wait_event(cs->waitqueue, !cs->waiting);
@@ -68,7 +66,7 @@ static int if_version(struct cardstate *cs, unsigned arg[4])
        static const unsigned compat[4] = GIG_COMPAT;
        unsigned cmd = arg[0];
 
-       dbg(DEBUG_IF, "%u: if_version (%d)", cs->minor_index, cmd);
+       gig_dbg(DEBUG_IF, "%u: if_version (%d)", cs->minor_index, cmd);
 
        switch (cmd) {
        case GIGVER_DRIVER:
@@ -80,12 +78,12 @@ static int if_version(struct cardstate *cs, unsigned arg[4])
        case GIGVER_FWBASE:
                cs->waiting = 1;
                if (!gigaset_add_event(cs, &cs->at_state, EV_IF_VER,
-                                      NULL, 0, arg)) {
+                                      NULL, 0, arg)) {
                        cs->waiting = 0;
                        return -ENOMEM;
                }
 
-               dbg(DEBUG_CMD, "scheduling IF_VER");
+               gig_dbg(DEBUG_CMD, "scheduling IF_VER");
                gigaset_schedule_event(cs);
 
                wait_event(cs->waitqueue, !cs->waiting);
@@ -101,7 +99,7 @@ static int if_version(struct cardstate *cs, unsigned arg[4])
 
 static int if_config(struct cardstate *cs, int *arg)
 {
-       dbg(DEBUG_IF, "%u: if_config (%d)", cs->minor_index, *arg);
+       gig_dbg(DEBUG_IF, "%u: if_config (%d)", cs->minor_index, *arg);
 
        if (*arg != 1)
                return -EINVAL;
@@ -109,6 +107,11 @@ static int if_config(struct cardstate *cs, int *arg)
        if (atomic_read(&cs->mstate) != MS_LOCKED)
                return -EBUSY;
 
+       if (!cs->connected) {
+               err("not connected!");
+               return -ENODEV;
+       }
+
        *arg = 0;
        return gigaset_enterconfigmode(cs);
 }
@@ -119,7 +122,7 @@ static int if_config(struct cardstate *cs, int *arg)
 static int  if_open(struct tty_struct *tty, struct file *filp);
 static void if_close(struct tty_struct *tty, struct file *filp);
 static int  if_ioctl(struct tty_struct *tty, struct file *file,
-                     unsigned int cmd, unsigned long arg);
+                    unsigned int cmd, unsigned long arg);
 static int  if_write_room(struct tty_struct *tty);
 static int  if_chars_in_buffer(struct tty_struct *tty);
 static void if_throttle(struct tty_struct *tty);
@@ -127,9 +130,9 @@ static void if_unthrottle(struct tty_struct *tty);
 static void if_set_termios(struct tty_struct *tty, struct termios *old);
 static int  if_tiocmget(struct tty_struct *tty, struct file *file);
 static int  if_tiocmset(struct tty_struct *tty, struct file *file,
-                        unsigned int set, unsigned int clear);
+                       unsigned int set, unsigned int clear);
 static int  if_write(struct tty_struct *tty,
-                     const unsigned char *buf, int count);
+                    const unsigned char *buf, int count);
 
 static struct tty_operations if_ops = {
        .open =                 if_open,
@@ -153,8 +156,8 @@ static int if_open(struct tty_struct *tty, struct file *filp)
        struct cardstate *cs;
        unsigned long flags;
 
-       dbg(DEBUG_IF, "%d+%d: %s()", tty->driver->minor_start, tty->index,
-           __FUNCTION__);
+       gig_dbg(DEBUG_IF, "%d+%d: %s()",
+               tty->driver->minor_start, tty->index, __func__);
 
        tty->driver_data = NULL;
 
@@ -162,7 +165,7 @@ static int if_open(struct tty_struct *tty, struct file *filp)
        if (!cs)
                return -ENODEV;
 
-       if (down_interruptible(&cs->sem))
+       if (mutex_lock_interruptible(&cs->mutex))
                return -ERESTARTSYS; // FIXME -EINTR?
        tty->driver_data = cs;
 
@@ -173,10 +176,9 @@ static int if_open(struct tty_struct *tty, struct file *filp)
                cs->tty = tty;
                spin_unlock_irqrestore(&cs->lock, flags);
                tty->low_latency = 1; //FIXME test
-               //FIXME
        }
 
-       up(&cs->sem);
+       mutex_unlock(&cs->mutex);
        return 0;
 }
 
@@ -187,30 +189,29 @@ static void if_close(struct tty_struct *tty, struct file *filp)
 
        cs = (struct cardstate *) tty->driver_data;
        if (!cs) {
-               err("cs==NULL in %s", __FUNCTION__);
+               err("cs==NULL in %s", __func__);
                return;
        }
 
-       dbg(DEBUG_IF, "%u: %s()", cs->minor_index, __FUNCTION__);
+       gig_dbg(DEBUG_IF, "%u: %s()", cs->minor_index, __func__);
 
-       down(&cs->sem);
+       mutex_lock(&cs->mutex);
 
        if (!cs->open_count)
-               warn("%s: device not opened", __FUNCTION__);
+               warn("%s: device not opened", __func__);
        else {
                if (!--cs->open_count) {
                        spin_lock_irqsave(&cs->lock, flags);
                        cs->tty = NULL;
                        spin_unlock_irqrestore(&cs->lock, flags);
-                       //FIXME
                }
        }
 
-       up(&cs->sem);
+       mutex_unlock(&cs->mutex);
 }
 
 static int if_ioctl(struct tty_struct *tty, struct file *file,
-                    unsigned int cmd, unsigned long arg)
+                   unsigned int cmd, unsigned long arg)
 {
        struct cardstate *cs;
        int retval = -ENODEV;
@@ -220,17 +221,17 @@ static int if_ioctl(struct tty_struct *tty, struct file *file,
 
        cs = (struct cardstate *) tty->driver_data;
        if (!cs) {
-               err("cs==NULL in %s", __FUNCTION__);
+               err("cs==NULL in %s", __func__);
                return -ENODEV;
        }
 
-       dbg(DEBUG_IF, "%u: %s(0x%x)", cs->minor_index, __FUNCTION__, cmd);
+       gig_dbg(DEBUG_IF, "%u: %s(0x%x)", cs->minor_index, __func__, cmd);
 
-       if (down_interruptible(&cs->sem))
+       if (mutex_lock_interruptible(&cs->mutex))
                return -ERESTARTSYS; // FIXME -EINTR?
 
        if (!cs->open_count)
-               warn("%s: device not opened", __FUNCTION__);
+               warn("%s: device not opened", __func__);
        else {
                retval = 0;
                switch (cmd) {
@@ -250,37 +251,40 @@ static int if_ioctl(struct tty_struct *tty, struct file *file,
                        break;
                case GIGASET_BRKCHARS:
                        //FIXME test if MS_LOCKED
-                       gigaset_dbg_buffer(DEBUG_IF, "GIGASET_BRKCHARS",
-                                          6, (const unsigned char *) arg, 1);
-                       if (!atomic_read(&cs->connected)) {
-                               dbg(DEBUG_ANY, "can't communicate with unplugged device");
+                       if (!cs->connected) {
+                               gig_dbg(DEBUG_ANY,
+                                   "can't communicate with unplugged device");
                                retval = -ENODEV;
                                break;
                        }
                        retval = copy_from_user(&buf,
-                                               (const unsigned char __user *) arg, 6)
-                                ? -EFAULT : 0;
-                       if (retval >= 0)
+                                       (const unsigned char __user *) arg, 6)
+                               ? -EFAULT : 0;
+                       if (retval >= 0) {
+                               gigaset_dbg_buffer(DEBUG_IF, "GIGASET_BRKCHARS",
+                                               6, (const unsigned char *) arg);
                                retval = cs->ops->brkchars(cs, buf);
+                       }
                        break;
                case GIGASET_VERSION:
-                       retval = copy_from_user(version, (unsigned __user *) arg,
-                                               sizeof version) ? -EFAULT : 0;
+                       retval = copy_from_user(version,
+                                       (unsigned __user *) arg, sizeof version)
+                               ? -EFAULT : 0;
                        if (retval >= 0)
                                retval = if_version(cs, version);
                        if (retval >= 0)
-                               retval = copy_to_user((unsigned __user *) arg, version,
-                                                     sizeof version)
-                                        ? -EFAULT : 0;
+                               retval = copy_to_user((unsigned __user *) arg,
+                                                     version, sizeof version)
+                                       ? -EFAULT : 0;
                        break;
-               default:
-                       dbg(DEBUG_ANY, "%s: arg not supported - 0x%04x",
-                           __FUNCTION__, cmd);
+               default:
+                       gig_dbg(DEBUG_ANY, "%s: arg not supported - 0x%04x",
+                               __func__, cmd);
                        retval = -ENOIOCTLCMD;
                }
        }
 
-       up(&cs->sem);
+       mutex_unlock(&cs->mutex);
 
        return retval;
 }
@@ -292,25 +296,25 @@ static int if_tiocmget(struct tty_struct *tty, struct file *file)
 
        cs = (struct cardstate *) tty->driver_data;
        if (!cs) {
-               err("cs==NULL in %s", __FUNCTION__);
+               err("cs==NULL in %s", __func__);
                return -ENODEV;
        }
 
-       dbg(DEBUG_IF, "%u: %s()", cs->minor_index, __FUNCTION__);
+       gig_dbg(DEBUG_IF, "%u: %s()", cs->minor_index, __func__);
 
-       if (down_interruptible(&cs->sem))
+       if (mutex_lock_interruptible(&cs->mutex))
                return -ERESTARTSYS; // FIXME -EINTR?
 
        // FIXME read from device?
        retval = cs->control_state & (TIOCM_RTS|TIOCM_DTR);
 
-       up(&cs->sem);
+       mutex_unlock(&cs->mutex);
 
        return retval;
 }
 
 static int if_tiocmset(struct tty_struct *tty, struct file *file,
-                       unsigned int set, unsigned int clear)
+                      unsigned int set, unsigned int clear)
 {
        struct cardstate *cs;
        int retval;
@@ -318,18 +322,18 @@ static int if_tiocmset(struct tty_struct *tty, struct file *file,
 
        cs = (struct cardstate *) tty->driver_data;
        if (!cs) {
-               err("cs==NULL in %s", __FUNCTION__);
+               err("cs==NULL in %s", __func__);
                return -ENODEV;
        }
 
-       dbg(DEBUG_IF,
-           "%u: %s(0x%x, 0x%x)", cs->minor_index, __FUNCTION__, set, clear);
+       gig_dbg(DEBUG_IF, "%u: %s(0x%x, 0x%x)",
+               cs->minor_index, __func__, set, clear);
 
-       if (down_interruptible(&cs->sem))
+       if (mutex_lock_interruptible(&cs->mutex))
                return -ERESTARTSYS; // FIXME -EINTR?
 
-       if (!atomic_read(&cs->connected)) {
-               dbg(DEBUG_ANY, "can't communicate with unplugged device");
+       if (!cs->connected) {
+               gig_dbg(DEBUG_ANY, "can't communicate with unplugged device");
                retval = -ENODEV;
        } else {
                mc = (cs->control_state | set) & ~clear & (TIOCM_RTS|TIOCM_DTR);
@@ -337,7 +341,7 @@ static int if_tiocmset(struct tty_struct *tty, struct file *file,
                cs->control_state = mc;
        }
 
-       up(&cs->sem);
+       mutex_unlock(&cs->mutex);
 
        return retval;
 }
@@ -349,29 +353,29 @@ static int if_write(struct tty_struct *tty, const unsigned char *buf, int count)
 
        cs = (struct cardstate *) tty->driver_data;
        if (!cs) {
-               err("cs==NULL in %s", __FUNCTION__);
+               err("cs==NULL in %s", __func__);
                return -ENODEV;
        }
 
-       dbg(DEBUG_IF, "%u: %s()", cs->minor_index, __FUNCTION__);
+       gig_dbg(DEBUG_IF, "%u: %s()", cs->minor_index, __func__);
 
-       if (down_interruptible(&cs->sem))
+       if (mutex_lock_interruptible(&cs->mutex))
                return -ERESTARTSYS; // FIXME -EINTR?
 
        if (!cs->open_count)
-               warn("%s: device not opened", __FUNCTION__);
+               warn("%s: device not opened", __func__);
        else if (atomic_read(&cs->mstate) != MS_LOCKED) {
                warn("can't write to unlocked device");
                retval = -EBUSY;
-       } else if (!atomic_read(&cs->connected)) {
-               dbg(DEBUG_ANY, "can't write to unplugged device");
+       } else if (!cs->connected) {
+               gig_dbg(DEBUG_ANY, "can't write to unplugged device");
                retval = -EBUSY; //FIXME
        } else {
                retval = cs->ops->write_cmd(cs, buf, count,
-                                           &cs->if_wake_tasklet);
+                                           &cs->if_wake_tasklet);
        }
 
-       up(&cs->sem);
+       mutex_unlock(&cs->mutex);
 
        return retval;
 }
@@ -383,27 +387,27 @@ static int if_write_room(struct tty_struct *tty)
 
        cs = (struct cardstate *) tty->driver_data;
        if (!cs) {
-               err("cs==NULL in %s", __FUNCTION__);
+               err("cs==NULL in %s", __func__);
                return -ENODEV;
        }
 
-       dbg(DEBUG_IF, "%u: %s()", cs->minor_index, __FUNCTION__);
+       gig_dbg(DEBUG_IF, "%u: %s()", cs->minor_index, __func__);
 
-       if (down_interruptible(&cs->sem))
+       if (mutex_lock_interruptible(&cs->mutex))
                return -ERESTARTSYS; // FIXME -EINTR?
 
        if (!cs->open_count)
-               warn("%s: device not opened", __FUNCTION__);
+               warn("%s: device not opened", __func__);
        else if (atomic_read(&cs->mstate) != MS_LOCKED) {
                warn("can't write to unlocked device");
                retval = -EBUSY; //FIXME
-       } else if (!atomic_read(&cs->connected)) {
-               dbg(DEBUG_ANY, "can't write to unplugged device");
+       } else if (!cs->connected) {
+               gig_dbg(DEBUG_ANY, "can't write to unplugged device");
                retval = -EBUSY; //FIXME
        } else
                retval = cs->ops->write_room(cs);
 
-       up(&cs->sem);
+       mutex_unlock(&cs->mutex);
 
        return retval;
 }
@@ -415,27 +419,27 @@ static int if_chars_in_buffer(struct tty_struct *tty)
 
        cs = (struct cardstate *) tty->driver_data;
        if (!cs) {
-               err("cs==NULL in %s", __FUNCTION__);
+               err("cs==NULL in %s", __func__);
                return -ENODEV;
        }
 
-       dbg(DEBUG_IF, "%u: %s()", cs->minor_index, __FUNCTION__);
+       gig_dbg(DEBUG_IF, "%u: %s()", cs->minor_index, __func__);
 
-       if (down_interruptible(&cs->sem))
+       if (mutex_lock_interruptible(&cs->mutex))
                return -ERESTARTSYS; // FIXME -EINTR?
 
        if (!cs->open_count)
-               warn("%s: device not opened", __FUNCTION__);
+               warn("%s: device not opened", __func__);
        else if (atomic_read(&cs->mstate) != MS_LOCKED) {
                warn("can't write to unlocked device");
                retval = -EBUSY;
-       } else if (!atomic_read(&cs->connected)) {
-               dbg(DEBUG_ANY, "can't write to unplugged device");
+       } else if (!cs->connected) {
+               gig_dbg(DEBUG_ANY, "can't write to unplugged device");
                retval = -EBUSY; //FIXME
        } else
                retval = cs->ops->chars_in_buffer(cs);
 
-       up(&cs->sem);
+       mutex_unlock(&cs->mutex);
 
        return retval;
 }
@@ -446,21 +450,21 @@ static void if_throttle(struct tty_struct *tty)
 
        cs = (struct cardstate *) tty->driver_data;
        if (!cs) {
-               err("cs==NULL in %s", __FUNCTION__);
+               err("cs==NULL in %s", __func__);
                return;
        }
 
-       dbg(DEBUG_IF, "%u: %s()", cs->minor_index, __FUNCTION__);
+       gig_dbg(DEBUG_IF, "%u: %s()", cs->minor_index, __func__);
 
-       down(&cs->sem);
+       mutex_lock(&cs->mutex);
 
        if (!cs->open_count)
-               warn("%s: device not opened", __FUNCTION__);
+               warn("%s: device not opened", __func__);
        else {
                //FIXME
        }
 
-       up(&cs->sem);
+       mutex_unlock(&cs->mutex);
 }
 
 static void if_unthrottle(struct tty_struct *tty)
@@ -469,21 +473,21 @@ static void if_unthrottle(struct tty_struct *tty)
 
        cs = (struct cardstate *) tty->driver_data;
        if (!cs) {
-               err("cs==NULL in %s", __FUNCTION__);
+               err("cs==NULL in %s", __func__);
                return;
        }
 
-       dbg(DEBUG_IF, "%u: %s()", cs->minor_index, __FUNCTION__);
+       gig_dbg(DEBUG_IF, "%u: %s()", cs->minor_index, __func__);
 
-       down(&cs->sem);
+       mutex_lock(&cs->mutex);
 
        if (!cs->open_count)
-               warn("%s: device not opened", __FUNCTION__);
+               warn("%s: device not opened", __func__);
        else {
                //FIXME
        }
 
-       up(&cs->sem);
+       mutex_unlock(&cs->mutex);
 }
 
 static void if_set_termios(struct tty_struct *tty, struct termios *old)
@@ -496,21 +500,21 @@ static void if_set_termios(struct tty_struct *tty, struct termios *old)
 
        cs = (struct cardstate *) tty->driver_data;
        if (!cs) {
-               err("cs==NULL in %s", __FUNCTION__);
+               err("cs==NULL in %s", __func__);
                return;
        }
 
-       dbg(DEBUG_IF, "%u: %s()", cs->minor_index, __FUNCTION__);
+       gig_dbg(DEBUG_IF, "%u: %s()", cs->minor_index, __func__);
 
-       down(&cs->sem);
+       mutex_lock(&cs->mutex);
 
        if (!cs->open_count) {
-               warn("%s: device not opened", __FUNCTION__);
+               warn("%s: device not opened", __func__);
                goto out;
        }
 
-       if (!atomic_read(&cs->connected)) {
-               dbg(DEBUG_ANY, "can't communicate with unplugged device");
+       if (!cs->connected) {
+               gig_dbg(DEBUG_ANY, "can't communicate with unplugged device");
                goto out;
        }
 
@@ -518,8 +522,8 @@ static void if_set_termios(struct tty_struct *tty, struct termios *old)
        iflag = tty->termios->c_iflag;
        cflag = tty->termios->c_cflag;
        old_cflag = old ? old->c_cflag : cflag; //FIXME?
-       dbg(DEBUG_IF, "%u: iflag %x cflag %x old %x", cs->minor_index,
-           iflag, cflag, old_cflag);
+       gig_dbg(DEBUG_IF, "%u: iflag %x cflag %x old %x",
+               cs->minor_index, iflag, cflag, old_cflag);
 
        /* get a local copy of the current port settings */
        control_state = cs->control_state;
@@ -531,14 +535,15 @@ static void if_set_termios(struct tty_struct *tty, struct termios *old)
         * Premature optimization is the root of all evil.
         */
 
-        /* reassert DTR and (maybe) RTS on transition from B0 */
+       /* reassert DTR and (maybe) RTS on transition from B0 */
        if ((old_cflag & CBAUD) == B0) {
                new_state = control_state | TIOCM_DTR;
                /* don't set RTS if using hardware flow control */
                if (!(old_cflag & CRTSCTS))
                        new_state |= TIOCM_RTS;
-               dbg(DEBUG_IF, "%u: from B0 - set DTR%s", cs->minor_index,
-                   (new_state & TIOCM_RTS) ? " only" : "/RTS");
+               gig_dbg(DEBUG_IF, "%u: from B0 - set DTR%s",
+                       cs->minor_index,
+                       (new_state & TIOCM_RTS) ? " only" : "/RTS");
                cs->ops->set_modem_ctrl(cs, control_state, new_state);
                control_state = new_state;
        }
@@ -547,7 +552,7 @@ static void if_set_termios(struct tty_struct *tty, struct termios *old)
 
        if ((cflag & CBAUD) == B0) {
                /* Drop RTS and DTR */
-               dbg(DEBUG_IF, "%u: to B0 - drop DTR/RTS", cs->minor_index);
+               gig_dbg(DEBUG_IF, "%u: to B0 - drop DTR/RTS", cs->minor_index);
                new_state = control_state & ~(TIOCM_DTR | TIOCM_RTS);
                cs->ops->set_modem_ctrl(cs, control_state, new_state);
                control_state = new_state;
@@ -567,15 +572,17 @@ static void if_set_termios(struct tty_struct *tty, struct termios *old)
         * Just do what we have seen with SniffUSB on Win98.
         */
        /* Drop DTR/RTS if no flow control otherwise assert */
-       dbg(DEBUG_IF, "%u: control_state %x", cs->minor_index, control_state);
+       gig_dbg(DEBUG_IF, "%u: control_state %x",
+               cs->minor_index, control_state);
        new_state = control_state;
        if ((iflag & IXOFF) || (iflag & IXON) || (cflag & CRTSCTS))
                new_state |= TIOCM_DTR | TIOCM_RTS;
        else
                new_state &= ~(TIOCM_DTR | TIOCM_RTS);
        if (new_state != control_state) {
-               dbg(DEBUG_IF, "%u: new_state %x", cs->minor_index, new_state);
-               gigaset_set_modem_ctrl(cs, control_state, new_state); // FIXME: mct_u232.c sets the old state here. is this a bug?
+               gig_dbg(DEBUG_IF, "%u: new_state %x",
+                       cs->minor_index, new_state);
+               gigaset_set_modem_ctrl(cs, control_state, new_state);
                control_state = new_state;
        }
 #endif
@@ -584,7 +591,7 @@ static void if_set_termios(struct tty_struct *tty, struct termios *old)
        cs->control_state = control_state;
 
 out:
-       up(&cs->sem);
+       mutex_unlock(&cs->mutex);
 }
 
 
@@ -600,7 +607,7 @@ static void if_wake(unsigned long data)
 
        if ((tty->flags & (1 << TTY_DO_WRITE_WAKEUP)) &&
            tty->ldisc.write_wakeup) {
-               dbg(DEBUG_IF, "write wakeup call");
+               gig_dbg(DEBUG_IF, "write wakeup call");
                tty->ldisc.write_wakeup(tty);
        }
 
@@ -635,14 +642,14 @@ void gigaset_if_free(struct cardstate *cs)
 }
 
 void gigaset_if_receive(struct cardstate *cs,
-                        unsigned char *buffer, size_t len)
+                       unsigned char *buffer, size_t len)
 {
        unsigned long flags;
        struct tty_struct *tty;
 
        spin_lock_irqsave(&cs->lock, flags);
        if ((tty = cs->tty) == NULL)
-               dbg(DEBUG_ANY, "receive on closed device");
+               gig_dbg(DEBUG_ANY, "receive on closed device");
        else {
                tty_buffer_request_room(tty, len);
                tty_insert_flip_string(tty, buffer, len);
@@ -655,13 +662,13 @@ EXPORT_SYMBOL_GPL(gigaset_if_receive);
 /* gigaset_if_initdriver
  * Initialize tty interface.
  * parameters:
- *      drv             Driver
- *      procname        Name of the driver (e.g. for /proc/tty/drivers)
- *      devname         Name of the device files (prefix without minor number)
- *      devfsname       Devfs name of the device files without %d
+ *     drv             Driver
+ *     procname        Name of the driver (e.g. for /proc/tty/drivers)
+ *     devname         Name of the device files (prefix without minor number)
+ *     devfsname       Devfs name of the device files without %d
  */
 void gigaset_if_initdriver(struct gigaset_driver *drv, const char *procname,
-                           const char *devname, const char *devfsname)
+                          const char *devname, const char *devfsname)
 {
        unsigned minors = drv->minors;
        int ret;
@@ -696,7 +703,7 @@ void gigaset_if_initdriver(struct gigaset_driver *drv, const char *procname,
                warn("failed to register tty driver (error %d)", ret);
                goto error;
        }
-       dbg(DEBUG_IF, "tty driver initialized");
+       gig_dbg(DEBUG_IF, "tty driver initialized");
        drv->have_tty = 1;
        return;
 
index 5744eb91b315b0fa3d3b2cdb01ac520d7635e5c9..45f017ed6e8caf093bca94fc9422c9bb87cafff5 100644 (file)
  *     published by the Free Software Foundation; either version 2 of
  *     the License, or (at your option) any later version.
  * =====================================================================
- * ToDo: ...
- * =====================================================================
- * Version: $Id: isocdata.c,v 1.2.2.5 2005/11/13 23:05:19 hjlipp Exp $
- * =====================================================================
  */
 
 #include "gigaset.h"
@@ -87,14 +83,14 @@ static inline int isowbuf_startwrite(struct isowbuf_t *iwb)
 {
        if (!atomic_dec_and_test(&iwb->writesem)) {
                atomic_inc(&iwb->writesem);
-               dbg(DEBUG_ISO,
-                   "%s: couldn't acquire iso write semaphore", __func__);
+               gig_dbg(DEBUG_ISO, "%s: couldn't acquire iso write semaphore",
+                       __func__);
                return 0;
        }
 #ifdef CONFIG_GIGASET_DEBUG
-       dbg(DEBUG_ISO,
-           "%s: acquired iso write semaphore, data[write]=%02x, nbits=%d",
-           __func__, iwb->data[atomic_read(&iwb->write)], iwb->wbits);
+       gig_dbg(DEBUG_ISO,
+               "%s: acquired iso write semaphore, data[write]=%02x, nbits=%d",
+               __func__, iwb->data[atomic_read(&iwb->write)], iwb->wbits);
 #endif
        return 1;
 }
@@ -147,7 +143,7 @@ static inline void isowbuf_putflag(struct isowbuf_t *iwb)
        /* recover the idle flag byte */
        write = atomic_read(&iwb->write);
        iwb->idle = iwb->data[write];
-       dbg(DEBUG_ISO, "idle fill byte %02x", iwb->idle);
+       gig_dbg(DEBUG_ISO, "idle fill byte %02x", iwb->idle);
        /* mask extraneous bits in buffer */
        iwb->data[write] &= (1 << iwb->wbits) - 1;
 }
@@ -166,15 +162,14 @@ int gigaset_isowbuf_getbytes(struct isowbuf_t *iwb, int size)
        read = atomic_read(&iwb->nextread);
        write = atomic_read(&iwb->write);
        if (likely(read == write)) {
-               //dbg(DEBUG_STREAM, "%s: send buffer empty", __func__);
                /* return idle frame */
                return read < BAS_OUTBUFPAD ?
-                       BAS_OUTBUFSIZE : read - BAS_OUTBUFPAD;
+                       BAS_OUTBUFSIZE : read - BAS_OUTBUFPAD;
        }
 
        limit = read + size;
-       dbg(DEBUG_STREAM,
-           "%s: read=%d write=%d limit=%d", __func__, read, write, limit);
+       gig_dbg(DEBUG_STREAM, "%s: read=%d write=%d limit=%d",
+               __func__, read, write, limit);
 #ifdef CONFIG_GIGASET_DEBUG
        if (unlikely(size < 0 || size > BAS_OUTBUFPAD)) {
                err("invalid size %d", size);
@@ -196,11 +191,12 @@ int gigaset_isowbuf_getbytes(struct isowbuf_t *iwb, int size)
                                return -EBUSY;
                        /* write position could have changed */
                        if (limit >= (write = atomic_read(&iwb->write))) {
-                               pbyte = iwb->data[write]; /* save partial byte */
+                               pbyte = iwb->data[write]; /* save
+                                                            partial byte */
                                limit = write + BAS_OUTBUFPAD;
-                               dbg(DEBUG_STREAM,
-                                   "%s: filling %d->%d with %02x",
-                                   __func__, write, limit, iwb->idle);
+                               gig_dbg(DEBUG_STREAM,
+                                       "%s: filling %d->%d with %02x",
+                                       __func__, write, limit, iwb->idle);
                                if (write + BAS_OUTBUFPAD < BAS_OUTBUFSIZE)
                                        memset(iwb->data + write, iwb->idle,
                                               BAS_OUTBUFPAD);
@@ -211,9 +207,11 @@ int gigaset_isowbuf_getbytes(struct isowbuf_t *iwb, int size)
                                               - write);
                                        limit = 0;
                                }
-                               dbg(DEBUG_STREAM, "%s: restoring %02x at %d",
-                                   __func__, pbyte, limit);
-                               iwb->data[limit] = pbyte; /* restore partial byte */
+                               gig_dbg(DEBUG_STREAM,
+                                       "%s: restoring %02x at %d",
+                                       __func__, pbyte, limit);
+                               iwb->data[limit] = pbyte; /* restore
+                                                            partial byte */
                                atomic_set(&iwb->write, limit);
                        }
                        isowbuf_donewrite(iwb);
@@ -242,19 +240,17 @@ int gigaset_isowbuf_getbytes(struct isowbuf_t *iwb, int size)
  * write hex bytes to syslog for debugging
  */
 static inline void dump_bytes(enum debuglevel level, const char *tag,
-                              unsigned char *bytes, int count)
+                             unsigned char *bytes, int count)
 {
 #ifdef CONFIG_GIGASET_DEBUG
        unsigned char c;
        static char dbgline[3 * 32 + 1];
        static const char hexdigit[] = "0123456789abcdef";
        int i = 0;
-       IFNULLRET(tag);
-       IFNULLRET(bytes);
        while (count-- > 0) {
                if (i > sizeof(dbgline) - 4) {
                        dbgline[i] = '\0';
-                       dbg(level, "%s:%s", tag, dbgline);
+                       gig_dbg(level, "%s:%s", tag, dbgline);
                        i = 0;
                }
                c = *bytes++;
@@ -264,7 +260,7 @@ static inline void dump_bytes(enum debuglevel level, const char *tag,
                dbgline[i++] = hexdigit[c & 0x0f];
        }
        dbgline[i] = '\0';
-       dbg(level, "%s:%s", tag, dbgline);
+       gig_dbg(level, "%s:%s", tag, dbgline);
 #endif
 }
 
@@ -380,7 +376,7 @@ static u16 stufftab[5 * 256] = {
  */
 
 static inline int hdlc_bitstuff_byte(struct isowbuf_t *iwb, unsigned char cin,
-                                     int ones)
+                                    int ones)
 {
        u16 stuff;
        int shiftinc, newones;
@@ -422,7 +418,7 @@ static inline int hdlc_bitstuff_byte(struct isowbuf_t *iwb, unsigned char cin,
  */
 
 static inline int hdlc_buildframe(struct isowbuf_t *iwb,
-                                  unsigned char *in, int count)
+                                 unsigned char *in, int count)
 {
        int ones;
        u16 fcs;
@@ -431,8 +427,8 @@ static inline int hdlc_buildframe(struct isowbuf_t *iwb,
 
        if (isowbuf_freebytes(iwb) < count + count / 5 + 6 ||
            !isowbuf_startwrite(iwb)) {
-               dbg(DEBUG_ISO, "%s: %d bytes free -> -EAGAIN",
-                   __func__, isowbuf_freebytes(iwb));
+               gig_dbg(DEBUG_ISO, "%s: %d bytes free -> -EAGAIN",
+                       __func__, isowbuf_freebytes(iwb));
                return -EAGAIN;
        }
 
@@ -484,11 +480,11 @@ static inline int trans_buildframe(struct isowbuf_t *iwb,
 
        if (isowbuf_freebytes(iwb) < count ||
            !isowbuf_startwrite(iwb)) {
-               dbg(DEBUG_ISO, "can't put %d bytes", count);
+               gig_dbg(DEBUG_ISO, "can't put %d bytes", count);
                return -EAGAIN;
        }
 
-       dbg(DEBUG_STREAM, "put %d bytes", count);
+       gig_dbg(DEBUG_STREAM, "put %d bytes", count);
        write = atomic_read(&iwb->write);
        do {
                c = gigaset_invtab[*in++];
@@ -508,11 +504,13 @@ int gigaset_isoc_buildframe(struct bc_state *bcs, unsigned char *in, int len)
        switch (bcs->proto2) {
        case ISDN_PROTO_L2_HDLC:
                result = hdlc_buildframe(bcs->hw.bas->isooutbuf, in, len);
-               dbg(DEBUG_ISO, "%s: %d bytes HDLC -> %d", __func__, len, result);
+               gig_dbg(DEBUG_ISO, "%s: %d bytes HDLC -> %d",
+                       __func__, len, result);
                break;
        default:                        /* assume transparent */
                result = trans_buildframe(bcs->hw.bas->isooutbuf, in, len);
-               dbg(DEBUG_ISO, "%s: %d bytes trans -> %d", __func__, len, result);
+               gig_dbg(DEBUG_ISO, "%s: %d bytes trans -> %d",
+                       __func__, len, result);
        }
        return result;
 }
@@ -528,13 +526,13 @@ static inline void hdlc_putbyte(unsigned char c, struct bc_state *bcs)
                return;
        }
        if (unlikely(bcs->skb->len == SBUFSIZE)) {
-               warn("received oversized packet discarded");
+               dev_warn(bcs->cs->dev, "received oversized packet discarded\n");
                bcs->hw.bas->giants++;
                dev_kfree_skb_any(bcs->skb);
                bcs->skb = NULL;
                return;
        }
-       *gigaset_skb_put_quick(bcs->skb, 1) = c;
+       *__skb_put(bcs->skb, 1) = c;
 }
 
 /* hdlc_flush
@@ -549,7 +547,7 @@ static inline void hdlc_flush(struct bc_state *bcs)
                if ((bcs->skb = dev_alloc_skb(SBUFSIZE + HW_HDR_LEN)) != NULL)
                        skb_reserve(bcs->skb, HW_HDR_LEN);
                else
-                       err("could not allocate skb");
+                       dev_err(bcs->cs->dev, "could not allocate skb\n");
        }
 
        /* reset packet state */
@@ -571,23 +569,25 @@ static inline void hdlc_done(struct bc_state *bcs)
 
        if ((procskb = bcs->skb) == NULL) {
                /* previous error */
-               dbg(DEBUG_ISO, "%s: skb=NULL", __func__);
+               gig_dbg(DEBUG_ISO, "%s: skb=NULL", __func__);
                gigaset_rcv_error(NULL, bcs->cs, bcs);
        } else if (procskb->len < 2) {
-               notice("received short frame (%d octets)", procskb->len);
+               dev_notice(bcs->cs->dev, "received short frame (%d octets)\n",
+                          procskb->len);
                bcs->hw.bas->runts++;
                gigaset_rcv_error(procskb, bcs->cs, bcs);
        } else if (bcs->fcs != PPP_GOODFCS) {
-               notice("frame check error (0x%04x)", bcs->fcs);
+               dev_notice(bcs->cs->dev, "frame check error (0x%04x)\n",
+                          bcs->fcs);
                bcs->hw.bas->fcserrs++;
                gigaset_rcv_error(procskb, bcs->cs, bcs);
        } else {
                procskb->len -= 2;              /* subtract FCS */
                procskb->tail -= 2;
-               dbg(DEBUG_ISO,
-                   "%s: good frame (%d octets)", __func__, procskb->len);
+               gig_dbg(DEBUG_ISO, "%s: good frame (%d octets)",
+                       __func__, procskb->len);
                dump_bytes(DEBUG_STREAM,
-                          "rcv data", procskb->data, procskb->len);
+                          "rcv data", procskb->data, procskb->len);
                bcs->hw.bas->goodbytes += procskb->len;
                gigaset_rcv_skb(procskb, bcs->cs, bcs);
        }
@@ -595,7 +595,7 @@ static inline void hdlc_done(struct bc_state *bcs)
        if ((bcs->skb = dev_alloc_skb(SBUFSIZE + HW_HDR_LEN)) != NULL)
                skb_reserve(bcs->skb, HW_HDR_LEN);
        else
-               err("could not allocate skb");
+               dev_err(bcs->cs->dev, "could not allocate skb\n");
        bcs->fcs = PPP_INITFCS;
 }
 
@@ -610,14 +610,14 @@ static inline void hdlc_frag(struct bc_state *bcs, unsigned inbits)
                return;
        }
 
-       notice("received partial byte (%d bits)", inbits);
+       dev_notice(bcs->cs->dev, "received partial byte (%d bits)\n", inbits);
        bcs->hw.bas->alignerrs++;
        gigaset_rcv_error(bcs->skb, bcs->cs, bcs);
 
        if ((bcs->skb = dev_alloc_skb(SBUFSIZE + HW_HDR_LEN)) != NULL)
                skb_reserve(bcs->skb, HW_HDR_LEN);
        else
-               err("could not allocate skb");
+               dev_err(bcs->cs->dev, "could not allocate skb\n");
        bcs->fcs = PPP_INITFCS;
 }
 
@@ -659,16 +659,12 @@ static unsigned char bitcounts[256] = {
  *     bcs     receiving B channel structure
  */
 static inline void hdlc_unpack(unsigned char *src, unsigned count,
-                               struct bc_state *bcs)
+                              struct bc_state *bcs)
 {
-       struct bas_bc_state *ubc;
+       struct bas_bc_state *ubc = bcs->hw.bas;
        int inputstate;
        unsigned seqlen, inbyte, inbits;
 
-       IFNULLRET(bcs);
-       ubc = bcs->hw.bas;
-       IFNULLRET(ubc);
-
        /* load previous state:
         * inputstate = set of flag bits:
         * - INS_flag_hunt: no complete opening flag received since connection setup or last abort
@@ -856,7 +852,7 @@ static inline void hdlc_unpack(unsigned char *src, unsigned count,
  *     bcs     receiving B channel structure
  */
 static inline void trans_receive(unsigned char *src, unsigned count,
-                                 struct bc_state *bcs)
+                                struct bc_state *bcs)
 {
        struct sk_buff *skb;
        int dobytes;
@@ -870,7 +866,7 @@ static inline void trans_receive(unsigned char *src, unsigned count,
        if (unlikely((skb = bcs->skb) == NULL)) {
                bcs->skb = skb = dev_alloc_skb(SBUFSIZE + HW_HDR_LEN);
                if (!skb) {
-                       err("could not allocate skb");
+                       dev_err(bcs->cs->dev, "could not allocate skb\n");
                        return;
                }
                skb_reserve(skb, HW_HDR_LEN);
@@ -888,7 +884,8 @@ static inline void trans_receive(unsigned char *src, unsigned count,
                        gigaset_rcv_skb(skb, bcs->cs, bcs);
                        bcs->skb = skb = dev_alloc_skb(SBUFSIZE + HW_HDR_LEN);
                        if (!skb) {
-                               err("could not allocate skb");
+                               dev_err(bcs->cs->dev,
+                                       "could not allocate skb\n");
                                return;
                        }
                        skb_reserve(bcs->skb, HW_HDR_LEN);
@@ -921,8 +918,8 @@ static void cmd_loop(unsigned char *src, int numbytes, struct inbuf_t *inbuf)
                case '\r':
                case '\n':
                        /* end of line */
-                       dbg(DEBUG_TRANSCMD, "%s: End of Command (%d Bytes)",
-                           __func__, cbytes);
+                       gig_dbg(DEBUG_TRANSCMD, "%s: End of Command (%d Bytes)",
+                               __func__, cbytes);
                        cs->cbytes = cbytes;
                        gigaset_handle_modem_response(cs);
                        cbytes = 0;
@@ -932,7 +929,7 @@ static void cmd_loop(unsigned char *src, int numbytes, struct inbuf_t *inbuf)
                        if (cbytes < MAX_RESP_SIZE - 1)
                                cbytes++;
                        else
-                               warn("response too large");
+                               dev_warn(cs->dev, "response too large\n");
                }
        }
 
@@ -951,27 +948,27 @@ void gigaset_isoc_input(struct inbuf_t *inbuf)
 
        head = atomic_read(&inbuf->head);
        while (head != (tail = atomic_read(&inbuf->tail))) {
-               dbg(DEBUG_INTR, "buffer state: %u -> %u", head, tail);
+               gig_dbg(DEBUG_INTR, "buffer state: %u -> %u", head, tail);
                if (head > tail)
                        tail = RBUFSIZE;
                src = inbuf->data + head;
                numbytes = tail - head;
-               dbg(DEBUG_INTR, "processing %u bytes", numbytes);
+               gig_dbg(DEBUG_INTR, "processing %u bytes", numbytes);
 
                if (atomic_read(&cs->mstate) == MS_LOCKED) {
                        gigaset_dbg_buffer(DEBUG_LOCKCMD, "received response",
-                                          numbytes, src, 0);
+                                          numbytes, src);
                        gigaset_if_receive(inbuf->cs, src, numbytes);
                } else {
                        gigaset_dbg_buffer(DEBUG_CMD, "received response",
-                                          numbytes, src, 0);
+                                          numbytes, src);
                        cmd_loop(src, numbytes, inbuf);
                }
 
                head += numbytes;
                if (head == RBUFSIZE)
                        head = 0;
-               dbg(DEBUG_INTR, "setting head to %u", head);
+               gig_dbg(DEBUG_INTR, "setting head to %u", head);
                atomic_set(&inbuf->head, head);
        }
 }
@@ -992,18 +989,18 @@ void gigaset_isoc_input(struct inbuf_t *inbuf)
  */
 int gigaset_isoc_send_skb(struct bc_state *bcs, struct sk_buff *skb)
 {
-       int len;
-
-       IFNULLRETVAL(bcs, -EFAULT);
-       IFNULLRETVAL(skb, -EFAULT);
-       len = skb->len;
+       int len = skb->len;
+       unsigned long flags;
 
        skb_queue_tail(&bcs->squeue, skb);
-       dbg(DEBUG_ISO,
-           "%s: skb queued, qlen=%d", __func__, skb_queue_len(&bcs->squeue));
+       gig_dbg(DEBUG_ISO, "%s: skb queued, qlen=%d",
+               __func__, skb_queue_len(&bcs->squeue));
 
        /* tasklet submits URB if necessary */
-       tasklet_schedule(&bcs->hw.bas->sent_tasklet);
+       spin_lock_irqsave(&bcs->cs->lock, flags);
+       if (bcs->cs->connected)
+               tasklet_schedule(&bcs->hw.bas->sent_tasklet);
+       spin_unlock_irqrestore(&bcs->cs->lock, flags);
 
        return len;     /* ok so far */
 }
index c6915fa2be6cc87afae8e23d43066214d1f11f21..d267a636b53c63cbd9558b73e57474248d5f9a16 100644 (file)
@@ -1,7 +1,7 @@
 /*
  * Stuff used by all variants of the driver
  *
- * Copyright (c) 2001 by Stefan Eilers <Eilers.Stefan@epost.de>,
+ * Copyright (c) 2001 by Stefan Eilers,
  *                       Hansjoerg Lipp <hjlipp@web.de>,
  *                       Tilman Schmidt <tilman@imap.cc>.
  *
  *     published by the Free Software Foundation; either version 2 of
  *     the License, or (at your option) any later version.
  * =====================================================================
- * ToDo: ...
- * =====================================================================
- * Version: $Id: proc.c,v 1.5.2.13 2006/02/04 18:28:16 hjlipp Exp $
- * =====================================================================
  */
 
 #include "gigaset.h"
 #include <linux/ctype.h>
 
-static ssize_t show_cidmode(struct device *dev, struct device_attribute *attr, char *buf)
+static ssize_t show_cidmode(struct device *dev, struct device_attribute *attr,
+                           char *buf)
 {
-       struct usb_interface *intf = to_usb_interface(dev);
-       struct cardstate *cs = usb_get_intfdata(intf);
-       return sprintf(buf, "%d\n", atomic_read(&cs->cidmode)); // FIXME use scnprintf for 13607 bit architectures (if PAGE_SIZE==4096)
+       int ret;
+       unsigned long flags;
+       struct cardstate *cs = dev_get_drvdata(dev);
+
+       spin_lock_irqsave(&cs->lock, flags);
+       ret = sprintf(buf, "%u\n", cs->cidmode);
+       spin_unlock_irqrestore(&cs->lock, flags);
+
+       return ret;
 }
 
-static ssize_t set_cidmode(struct device *dev, struct device_attribute *attr, const char *buf, size_t count)
+static ssize_t set_cidmode(struct device *dev, struct device_attribute *attr,
+                          const char *buf, size_t count)
 {
-       struct usb_interface *intf = to_usb_interface(dev);
-       struct cardstate *cs = usb_get_intfdata(intf);
+       struct cardstate *cs = dev_get_drvdata(dev);
        long int value;
        char *end;
 
@@ -41,23 +44,23 @@ static ssize_t set_cidmode(struct device *dev, struct device_attribute *attr, co
        if (value < 0 || value > 1)
                        return -EINVAL;
 
-       if (down_interruptible(&cs->sem))
+       if (mutex_lock_interruptible(&cs->mutex))
                return -ERESTARTSYS; // FIXME -EINTR?
 
        cs->waiting = 1;
        if (!gigaset_add_event(cs, &cs->at_state, EV_PROC_CIDMODE,
-                              NULL, value, NULL)) {
+                              NULL, value, NULL)) {
                cs->waiting = 0;
-               up(&cs->sem);
+               mutex_unlock(&cs->mutex);
                return -ENOMEM;
        }
 
-       dbg(DEBUG_CMD, "scheduling PROC_CIDMODE");
+       gig_dbg(DEBUG_CMD, "scheduling PROC_CIDMODE");
        gigaset_schedule_event(cs);
 
        wait_event(cs->waitqueue, !cs->waiting);
 
-       up(&cs->sem);
+       mutex_unlock(&cs->mutex);
 
        return count;
 }
@@ -65,17 +68,15 @@ static ssize_t set_cidmode(struct device *dev, struct device_attribute *attr, co
 static DEVICE_ATTR(cidmode, S_IRUGO|S_IWUSR, show_cidmode, set_cidmode);
 
 /* free sysfs for device */
-void gigaset_free_dev_sysfs(struct usb_interface *interface)
+void gigaset_free_dev_sysfs(struct cardstate *cs)
 {
-       dbg(DEBUG_INIT, "removing sysfs entries");
-       device_remove_file(&interface->dev, &dev_attr_cidmode);
+       gig_dbg(DEBUG_INIT, "removing sysfs entries");
+       device_remove_file(cs->dev, &dev_attr_cidmode);
 }
-EXPORT_SYMBOL_GPL(gigaset_free_dev_sysfs);
 
 /* initialize sysfs for device */
-void gigaset_init_dev_sysfs(struct usb_interface *interface)
+void gigaset_init_dev_sysfs(struct cardstate *cs)
 {
-       dbg(DEBUG_INIT, "setting up sysfs");
-       device_create_file(&interface->dev, &dev_attr_cidmode);
+       gig_dbg(DEBUG_INIT, "setting up sysfs");
+       device_create_file(cs->dev, &dev_attr_cidmode);
 }
-EXPORT_SYMBOL_GPL(gigaset_init_dev_sysfs);
index 323fc7349dec11350989c795100d9e466ce3de28..bfb73fd5077e85aa148a48dbbf5165f5185c5c19 100644 (file)
@@ -1,7 +1,7 @@
 /*
  * USB driver for Gigaset 307x directly or using M105 Data.
  *
- * Copyright (c) 2001 by Stefan Eilers <Eilers.Stefan@epost.de>
+ * Copyright (c) 2001 by Stefan Eilers
  *                   and Hansjoerg Lipp <hjlipp@web.de>.
  *
  * This driver was derived from the USB skeleton driver by
  *     published by the Free Software Foundation; either version 2 of
  *     the License, or (at your option) any later version.
  * =====================================================================
- * ToDo: ...
- * =====================================================================
- * Version: $Id: usb-gigaset.c,v 1.85.4.18 2006/02/04 18:28:16 hjlipp Exp $
- * =====================================================================
  */
 
 #include "gigaset.h"
@@ -29,7 +25,7 @@
 #include <linux/moduleparam.h>
 
 /* Version Information */
-#define DRIVER_AUTHOR "Hansjoerg Lipp <hjlipp@web.de>, Stefan Eilers <Eilers.Stefan@epost.de>"
+#define DRIVER_AUTHOR "Hansjoerg Lipp <hjlipp@web.de>, Stefan Eilers"
 #define DRIVER_DESC "USB Driver for Gigaset 307x using M105"
 
 /* Module parameters */
@@ -62,10 +58,6 @@ static struct usb_device_id gigaset_table [] = {
 
 MODULE_DEVICE_TABLE(usb, gigaset_table);
 
-/* Get a minor range for your devices from the usb maintainer */
-#define USB_SKEL_MINOR_BASE    200
-
-
 /*
  * Control requests (empty fields: 00)
  *
@@ -114,7 +106,7 @@ MODULE_DEVICE_TABLE(usb, gigaset_table);
  */
 
 static int gigaset_probe(struct usb_interface *interface,
-                         const struct usb_device_id *id);
+                        const struct usb_device_id *id);
 static void gigaset_disconnect(struct usb_interface *interface);
 
 static struct gigaset_driver *driver = NULL;
@@ -122,29 +114,29 @@ static struct cardstate *cardstate = NULL;
 
 /* usb specific object needed to register this driver with the usb subsystem */
 static struct usb_driver gigaset_usb_driver = {
-       .name =         GIGASET_MODULENAME,
-       .probe =        gigaset_probe,
-       .disconnect =   gigaset_disconnect,
-       .id_table =     gigaset_table,
+       .name =         GIGASET_MODULENAME,
+       .probe =        gigaset_probe,
+       .disconnect =   gigaset_disconnect,
+       .id_table =     gigaset_table,
 };
 
 struct usb_cardstate {
-       struct usb_device       *udev;                  /* save off the usb device pointer */
-       struct usb_interface    *interface;             /* the interface for this device */
-       atomic_t                busy;                   /* bulk output in progress */
-
-       /* Output buffer for commands (M105: and data)*/
-       unsigned char           *bulk_out_buffer;       /* the buffer to send data */
-       int                     bulk_out_size;          /* the size of the send buffer */
-       __u8                    bulk_out_endpointAddr;  /* the address of the bulk out endpoint */
-       struct urb              *bulk_out_urb;          /* the urb used to transmit data */
-
-       /* Input buffer for command responses (M105: and data)*/
-       int                     rcvbuf_size;            /* the size of the receive buffer */
-       struct urb              *read_urb;              /* the urb used to receive data */
-       __u8                    int_in_endpointAddr;    /* the address of the bulk in endpoint */
-
-       char                    bchars[6];              /* req. 0x19 */
+       struct usb_device       *udev;          /* usb device pointer */
+       struct usb_interface    *interface;     /* interface for this device */
+       atomic_t                busy;           /* bulk output in progress */
+
+       /* Output buffer */
+       unsigned char           *bulk_out_buffer;
+       int                     bulk_out_size;
+       __u8                    bulk_out_endpointAddr;
+       struct urb              *bulk_out_urb;
+
+       /* Input buffer */
+       int                     rcvbuf_size;
+       struct urb              *read_urb;
+       __u8                    int_in_endpointAddr;
+
+       char                    bchars[6];              /* for request 0x19 */
 };
 
 struct usb_bc_state {};
@@ -157,19 +149,20 @@ static inline unsigned tiocm_to_gigaset(unsigned state)
 #ifdef CONFIG_GIGASET_UNDOCREQ
 /* WARNING: EXPERIMENTAL! */
 static int gigaset_set_modem_ctrl(struct cardstate *cs, unsigned old_state,
-                                  unsigned new_state)
+                                 unsigned new_state)
 {
+       struct usb_device *udev = cs->hw.usb->udev;
        unsigned mask, val;
        int r;
 
        mask = tiocm_to_gigaset(old_state ^ new_state);
        val = tiocm_to_gigaset(new_state);
 
-       dbg(DEBUG_USBREQ, "set flags 0x%02x with mask 0x%02x", val, mask);
-       r = usb_control_msg(cs->hw.usb->udev,
-                           usb_sndctrlpipe(cs->hw.usb->udev, 0), 7, 0x41,
-                           (val & 0xff) | ((mask & 0xff) << 8), 0,
-                           NULL, 0, 2000 /*timeout??*/); // don't use this in an interrupt/BH
+       gig_dbg(DEBUG_USBREQ, "set flags 0x%02x with mask 0x%02x", val, mask);
+       // don't use this in an interrupt/BH
+       r = usb_control_msg(udev, usb_sndctrlpipe(udev, 0), 7, 0x41,
+                           (val & 0xff) | ((mask & 0xff) << 8), 0,
+                           NULL, 0, 2000 /* timeout? */);
        if (r < 0)
                return r;
        //..
@@ -178,30 +171,29 @@ static int gigaset_set_modem_ctrl(struct cardstate *cs, unsigned old_state,
 
 static int set_value(struct cardstate *cs, u8 req, u16 val)
 {
+       struct usb_device *udev = cs->hw.usb->udev;
        int r, r2;
 
-       dbg(DEBUG_USBREQ, "request %02x (%04x)", (unsigned)req, (unsigned)val);
-       r = usb_control_msg(cs->hw.usb->udev,
-                           usb_sndctrlpipe(cs->hw.usb->udev, 0), 0x12, 0x41,
-                           0xf /*?*/, 0,
-                           NULL, 0, 2000 /*?*/); /* no idea, what this does */
+       gig_dbg(DEBUG_USBREQ, "request %02x (%04x)",
+               (unsigned)req, (unsigned)val);
+       r = usb_control_msg(udev, usb_sndctrlpipe(udev, 0), 0x12, 0x41,
+                           0xf /*?*/, 0, NULL, 0, 2000 /*?*/);
+                           /* no idea what this does */
        if (r < 0) {
-               err("error %d on request 0x12", -r);
+               dev_err(&udev->dev, "error %d on request 0x12\n", -r);
                return r;
        }
 
-       r = usb_control_msg(cs->hw.usb->udev,
-                           usb_sndctrlpipe(cs->hw.usb->udev, 0), req, 0x41,
-                           val, 0,
-                           NULL, 0, 2000 /*?*/);
+       r = usb_control_msg(udev, usb_sndctrlpipe(udev, 0), req, 0x41,
+                           val, 0, NULL, 0, 2000 /*?*/);
        if (r < 0)
-               err("error %d on request 0x%02x", -r, (unsigned)req);
+               dev_err(&udev->dev, "error %d on request 0x%02x\n",
+                       -r, (unsigned)req);
 
-       r2 = usb_control_msg(cs->hw.usb->udev,
-                            usb_sndctrlpipe(cs->hw.usb->udev, 0), 0x19, 0x41,
-                            0, 0, cs->hw.usb->bchars, 6, 2000 /*?*/);
+       r2 = usb_control_msg(udev, usb_sndctrlpipe(udev, 0), 0x19, 0x41,
+                            0, 0, cs->hw.usb->bchars, 6, 2000 /*?*/);
        if (r2 < 0)
-               err("error %d on request 0x19", -r2);
+               dev_err(&udev->dev, "error %d on request 0x19\n", -r2);
 
        return r < 0 ? r : (r2 < 0 ? r2 : 0);
 }
@@ -229,8 +221,8 @@ static int gigaset_baud_rate(struct cardstate *cs, unsigned cflag)
        case B115200: rate =  115200; break;
        default:
                rate =  9600;
-               err("unsupported baudrate request 0x%x,"
-                   " using default of B9600", cflag);
+               dev_err(cs->dev, "unsupported baudrate request 0x%x,"
+                       " using default of B9600\n", cflag);
        }
 
        val = 0x383fff / rate + 1;
@@ -259,7 +251,7 @@ static int gigaset_set_line_ctrl(struct cardstate *cs, unsigned cflag)
        case CS8:
                val |= 8 << 8; break;
        default:
-               err("CSIZE was not CS5-CS8, using default of 8");
+               dev_err(cs->dev, "CSIZE was not CS5-CS8, using default of 8\n");
                val |= 8 << 8;
                break;
        }
@@ -277,7 +269,7 @@ static int gigaset_set_line_ctrl(struct cardstate *cs, unsigned cflag)
 
 #else
 static int gigaset_set_modem_ctrl(struct cardstate *cs, unsigned old_state,
-                                  unsigned new_state)
+                                 unsigned new_state)
 {
        return -EINVAL;
 }
@@ -309,15 +301,12 @@ static int gigaset_close_bchannel(struct bc_state *bcs)
        return 0;
 }
 
-//void send_ack_to_LL(void *data);
 static int write_modem(struct cardstate *cs);
 static int send_cb(struct cardstate *cs, struct cmdbuf_t *cb);
 
 
-/* Handling of send queue. If there is already a skb opened, put data to
- * the transfer buffer by calling "write_modem". Otherwise take a new skb out of the queue.
- * This function will be called by the ISR via "transmit_chars" (USB: B-Channel Bulk callback handler
- * via immediate task queue) or by writebuf_from_LL if the LL wants to transmit data.
+/* Write tasklet handler: Continue sending current skb, or send command, or
+ * start sending an skb from the send queue.
  */
 static void gigaset_modem_fill(unsigned long data)
 {
@@ -327,10 +316,10 @@ static void gigaset_modem_fill(unsigned long data)
        unsigned long flags;
        int again;
 
-       dbg(DEBUG_OUTPUT, "modem_fill");
+       gig_dbg(DEBUG_OUTPUT, "modem_fill");
 
        if (atomic_read(&cs->hw.usb->busy)) {
-               dbg(DEBUG_OUTPUT, "modem_fill: busy");
+               gig_dbg(DEBUG_OUTPUT, "modem_fill: busy");
                return;
        }
 
@@ -341,26 +330,27 @@ static void gigaset_modem_fill(unsigned long data)
                        cb = cs->cmdbuf;
                        spin_unlock_irqrestore(&cs->cmdlock, flags);
                        if (cb) { /* commands to send? */
-                               dbg(DEBUG_OUTPUT, "modem_fill: cb");
+                               gig_dbg(DEBUG_OUTPUT, "modem_fill: cb");
                                if (send_cb(cs, cb) < 0) {
-                                       dbg(DEBUG_OUTPUT,
-                                           "modem_fill: send_cb failed");
-                                       again = 1; /* no callback will be called! */
+                                       gig_dbg(DEBUG_OUTPUT,
+                                               "modem_fill: send_cb failed");
+                                       again = 1; /* no callback will be
+                                                     called! */
                                }
                        } else { /* skbs to send? */
                                bcs->tx_skb = skb_dequeue(&bcs->squeue);
                                if (bcs->tx_skb)
-                                       dbg(DEBUG_INTR,
-                                           "Dequeued skb (Adr: %lx)!",
-                                           (unsigned long) bcs->tx_skb);
+                                       gig_dbg(DEBUG_INTR,
+                                               "Dequeued skb (Adr: %lx)!",
+                                               (unsigned long) bcs->tx_skb);
                        }
                }
 
                if (bcs->tx_skb) {
-                       dbg(DEBUG_OUTPUT, "modem_fill: tx_skb");
+                       gig_dbg(DEBUG_OUTPUT, "modem_fill: tx_skb");
                        if (write_modem(cs) < 0) {
-                               dbg(DEBUG_OUTPUT,
-                                   "modem_fill: write_modem failed");
+                               gig_dbg(DEBUG_OUTPUT,
+                                       "modem_fill: write_modem failed");
                                // FIXME should we tell the LL?
                                again = 1; /* no callback will be called! */
                        }
@@ -371,88 +361,85 @@ static void gigaset_modem_fill(unsigned long data)
 /**
  *     gigaset_read_int_callback
  *
- *      It is called if the data was received from the device. This is almost similiar to
- *      the interrupt service routine in the serial device.
+ *     It is called if the data was received from the device.
  */
 static void gigaset_read_int_callback(struct urb *urb, struct pt_regs *regs)
 {
+       struct inbuf_t *inbuf = urb->context;
+       struct cardstate *cs = inbuf->cs;
        int resubmit = 0;
        int r;
-       struct cardstate *cs;
        unsigned numbytes;
        unsigned char *src;
-       //unsigned long flags;
-       struct inbuf_t *inbuf;
-
-       IFNULLRET(urb);
-       inbuf = (struct inbuf_t *) urb->context;
-       IFNULLRET(inbuf);
-       //spin_lock_irqsave(&inbuf->lock, flags);
-       cs = inbuf->cs;
-       IFNULLGOTO(cs, exit);
-       IFNULLGOTO(cardstate, exit);
-
-       if (!atomic_read(&cs->connected)) {
-               err("%s: disconnected", __func__);
-               goto exit;
-       }
+       unsigned long flags;
 
        if (!urb->status) {
+               if (!cs->connected) {
+                       err("%s: disconnected", __func__); /* should never happen */
+                       return;
+               }
+
                numbytes = urb->actual_length;
 
                if (numbytes) {
                        src = inbuf->rcvbuf;
                        if (unlikely(*src))
-                               warn("%s: There was no leading 0, but 0x%02x!",
-                                    __func__, (unsigned) *src);
+                               dev_warn(cs->dev,
+                                   "%s: There was no leading 0, but 0x%02x!\n",
+                                        __func__, (unsigned) *src);
                        ++src; /* skip leading 0x00 */
                        --numbytes;
                        if (gigaset_fill_inbuf(inbuf, src, numbytes)) {
-                               dbg(DEBUG_INTR, "%s-->BH", __func__);
+                               gig_dbg(DEBUG_INTR, "%s-->BH", __func__);
                                gigaset_schedule_event(inbuf->cs);
                        }
                } else
-                       dbg(DEBUG_INTR, "Received zero block length");
+                       gig_dbg(DEBUG_INTR, "Received zero block length");
                resubmit = 1;
        } else {
                /* The urb might have been killed. */
-               dbg(DEBUG_ANY, "%s - nonzero read bulk status received: %d",
-                   __func__, urb->status);
-               if (urb->status != -ENOENT) /* not killed */
+               gig_dbg(DEBUG_ANY, "%s - nonzero read bulk status received: %d",
+                       __func__, urb->status);
+               if (urb->status != -ENOENT) { /* not killed */
+                       if (!cs->connected) {
+                               err("%s: disconnected", __func__); /* should never happen */
+                               return;
+                       }
                        resubmit = 1;
+               }
        }
-exit:
-       //spin_unlock_irqrestore(&inbuf->lock, flags);
+
        if (resubmit) {
-               r = usb_submit_urb(urb, SLAB_ATOMIC);
+               spin_lock_irqsave(&cs->lock, flags);
+               r = cs->connected ? usb_submit_urb(urb, SLAB_ATOMIC) : -ENODEV;
+               spin_unlock_irqrestore(&cs->lock, flags);
                if (r)
-                       err("error %d when resubmitting urb.", -r);
+                       dev_err(cs->dev, "error %d when resubmitting urb.\n",
+                               -r);
        }
 }
 
 
-/* This callback routine is called when data was transmitted to a B-Channel.
- * Therefore it has to check if there is still data to transmit. This
- * happens by calling modem_fill via task queue.
- *
- */
+/* This callback routine is called when data was transmitted to the device. */
 static void gigaset_write_bulk_callback(struct urb *urb, struct pt_regs *regs)
 {
-       struct cardstate *cs = (struct cardstate *) urb->context;
+       struct cardstate *cs = urb->context;
+       unsigned long flags;
 
-       IFNULLRET(cs);
-#ifdef CONFIG_GIGASET_DEBUG
-       if (!atomic_read(&cs->connected)) {
-               err("%s:not connected", __func__);
-               return;
-       }
-#endif
        if (urb->status)
-               err("bulk transfer failed (status %d)", -urb->status); /* That's all we can do. Communication problems
-                                                                          are handeled by timeouts or network protocols */
+               dev_err(cs->dev, "bulk transfer failed (status %d)\n",
+                       -urb->status);
+               /* That's all we can do. Communication problems
+                  are handled by timeouts or network protocols. */
 
-       atomic_set(&cs->hw.usb->busy, 0);
-       tasklet_schedule(&cs->write_tasklet);
+       spin_lock_irqsave(&cs->lock, flags);
+       if (!cs->connected) {
+               err("%s: not connected", __func__);
+       } else {
+               atomic_set(&cs->hw.usb->busy, 0);
+               tasklet_schedule(&cs->write_tasklet);
+       }
+       spin_unlock_irqrestore(&cs->lock, flags);
 }
 
 static int send_cb(struct cardstate *cs, struct cmdbuf_t *cb)
@@ -469,8 +456,8 @@ static int send_cb(struct cardstate *cs, struct cmdbuf_t *cb)
 
                        spin_lock_irqsave(&cs->cmdlock, flags);
                        cs->cmdbytes -= cs->curlen;
-                       dbg(DEBUG_OUTPUT, "send_cb: sent %u bytes, %u left",
-                           cs->curlen, cs->cmdbytes);
+                       gig_dbg(DEBUG_OUTPUT, "send_cb: sent %u bytes, %u left",
+                               cs->curlen, cs->cmdbytes);
                        cs->cmdbuf = cb = cb->next;
                        if (cb) {
                                cb->prev = NULL;
@@ -487,52 +474,51 @@ static int send_cb(struct cardstate *cs, struct cmdbuf_t *cb)
                }
                if (cb) {
                        count = min(cb->len, ucs->bulk_out_size);
+                       gig_dbg(DEBUG_OUTPUT, "send_cb: send %d bytes", count);
+
                        usb_fill_bulk_urb(ucs->bulk_out_urb, ucs->udev,
-                                         usb_sndbulkpipe(ucs->udev,
-                                            ucs->bulk_out_endpointAddr & 0x0f),
-                                         cb->buf + cb->offset, count,
-                                         gigaset_write_bulk_callback, cs);
+                                         usb_sndbulkpipe(ucs->udev,
+                                            ucs->bulk_out_endpointAddr & 0x0f),
+                                         cb->buf + cb->offset, count,
+                                         gigaset_write_bulk_callback, cs);
 
                        cb->offset += count;
                        cb->len -= count;
                        atomic_set(&ucs->busy, 1);
-                       dbg(DEBUG_OUTPUT, "send_cb: send %d bytes", count);
 
-                       status = usb_submit_urb(ucs->bulk_out_urb, SLAB_ATOMIC);
+                       spin_lock_irqsave(&cs->lock, flags);
+                       status = cs->connected ? usb_submit_urb(ucs->bulk_out_urb, SLAB_ATOMIC) : -ENODEV;
+                       spin_unlock_irqrestore(&cs->lock, flags);
+
                        if (status) {
                                atomic_set(&ucs->busy, 0);
-                               err("could not submit urb (error %d).",
+                               err("could not submit urb (error %d)\n",
                                    -status);
-                               cb->len = 0; /* skip urb => remove cb+wakeup in next loop cycle */
+                               cb->len = 0; /* skip urb => remove cb+wakeup
+                                               in next loop cycle */
                        }
                }
-       } while (cb && status); /* bei Fehler naechster Befehl //FIXME: ist das OK? */
+       } while (cb && status); /* next command on error */
 
        return status;
 }
 
-/* Write string into transbuf and send it to modem.
- */
+/* Send command to device. */
 static int gigaset_write_cmd(struct cardstate *cs, const unsigned char *buf,
-                             int len, struct tasklet_struct *wake_tasklet)
+                            int len, struct tasklet_struct *wake_tasklet)
 {
        struct cmdbuf_t *cb;
        unsigned long flags;
 
        gigaset_dbg_buffer(atomic_read(&cs->mstate) != MS_LOCKED ?
-                            DEBUG_TRANSCMD : DEBUG_LOCKCMD,
-                          "CMD Transmit", len, buf, 0);
-
-       if (!atomic_read(&cs->connected)) {
-               err("%s: not connected", __func__);
-               return -ENODEV;
-       }
+                            DEBUG_TRANSCMD : DEBUG_LOCKCMD,
+                          "CMD Transmit", len, buf);
 
        if (len <= 0)
                return 0;
 
        if (!(cb = kmalloc(sizeof(struct cmdbuf_t) + len, GFP_ATOMIC))) {
-               err("%s: out of memory", __func__);
+               dev_err(cs->dev, "%s: out of memory\n", __func__);
                return -ENOMEM;
        }
 
@@ -554,7 +540,10 @@ static int gigaset_write_cmd(struct cardstate *cs, const unsigned char *buf,
        cs->lastcmdbuf = cb;
        spin_unlock_irqrestore(&cs->cmdlock, flags);
 
-       tasklet_schedule(&cs->write_tasklet);
+       spin_lock_irqsave(&cs->lock, flags);
+       if (cs->connected)
+               tasklet_schedule(&cs->write_tasklet);
+       spin_unlock_irqrestore(&cs->lock, flags);
        return len;
 }
 
@@ -578,11 +567,12 @@ static int gigaset_chars_in_buffer(struct cardstate *cs)
 static int gigaset_brkchars(struct cardstate *cs, const unsigned char buf[6])
 {
 #ifdef CONFIG_GIGASET_UNDOCREQ
-       gigaset_dbg_buffer(DEBUG_USBREQ, "brkchars", 6, buf, 0);
+       struct usb_device *udev = cs->hw.usb->udev;
+
+       gigaset_dbg_buffer(DEBUG_USBREQ, "brkchars", 6, buf);
        memcpy(cs->hw.usb->bchars, buf, 6);
-       return usb_control_msg(cs->hw.usb->udev,
-                              usb_sndctrlpipe(cs->hw.usb->udev, 0), 0x19, 0x41,
-                              0, 0, &buf, 6, 2000);
+       return usb_control_msg(udev, usb_sndctrlpipe(udev, 0), 0x19, 0x41,
+                              0, 0, &buf, 6, 2000);
 #else
        return -EINVAL;
 #endif
@@ -604,7 +594,6 @@ static int gigaset_initbcshw(struct bc_state *bcs)
        if (!bcs->hw.usb)
                return 0;
 
-       //bcs->hw.usb->trans_flg = READY_TO_TRNSMIT; /* B-Channel ready to transmit */
        return 1;
 }
 
@@ -614,7 +603,6 @@ static void gigaset_reinitbcshw(struct bc_state *bcs)
 
 static void gigaset_freecshw(struct cardstate *cs)
 {
-       //FIXME
        tasklet_kill(&cs->write_tasklet);
        kfree(cs->hw.usb);
 }
@@ -639,33 +627,21 @@ static int gigaset_initcshw(struct cardstate *cs)
        //ucs->urb_cmd_out = NULL;
        ucs->read_urb = NULL;
        tasklet_init(&cs->write_tasklet,
-                    &gigaset_modem_fill, (unsigned long) cs);
+                    &gigaset_modem_fill, (unsigned long) cs);
 
        return 1;
 }
 
-/* Writes the data of the current open skb into the modem.
- * We have to protect against multiple calls until the
- * callback handler () is called , due to the fact that we
- * are just allowed to send data once to an endpoint. Therefore
- * we using "trans_flg" to synchonize ...
- */
+/* Send data from current skb to the device. */
 static int write_modem(struct cardstate *cs)
 {
-       int ret;
+       int ret = 0;
        int count;
        struct bc_state *bcs = &cs->bcs[0]; /* only one channel */
        struct usb_cardstate *ucs = cs->hw.usb;
-       //unsigned long flags;
-
-       IFNULLRETVAL(bcs->tx_skb, -EINVAL);
-
-       dbg(DEBUG_WRITE, "len: %d...", bcs->tx_skb->len);
+       unsigned long flags;
 
-       ret = -ENODEV;
-       IFNULLGOTO(ucs->bulk_out_buffer, error);
-       IFNULLGOTO(ucs->bulk_out_urb, error);
-       ret = 0;
+       gig_dbg(DEBUG_WRITE, "len: %d...", bcs->tx_skb->len);
 
        if (!bcs->tx_skb->len) {
                dev_kfree_skb_any(bcs->tx_skb);
@@ -679,40 +655,42 @@ static int write_modem(struct cardstate *cs)
        count = min(bcs->tx_skb->len, (unsigned) ucs->bulk_out_size);
        memcpy(ucs->bulk_out_buffer, bcs->tx_skb->data, count);
        skb_pull(bcs->tx_skb, count);
-
-       usb_fill_bulk_urb(ucs->bulk_out_urb, ucs->udev,
-                         usb_sndbulkpipe(ucs->udev,
-                                         ucs->bulk_out_endpointAddr & 0x0f),
-                         ucs->bulk_out_buffer, count,
-                         gigaset_write_bulk_callback, cs);
        atomic_set(&ucs->busy, 1);
-       dbg(DEBUG_OUTPUT, "write_modem: send %d bytes", count);
+       gig_dbg(DEBUG_OUTPUT, "write_modem: send %d bytes", count);
+
+       spin_lock_irqsave(&cs->lock, flags);
+       if (cs->connected) {
+               usb_fill_bulk_urb(ucs->bulk_out_urb, ucs->udev,
+                                 usb_sndbulkpipe(ucs->udev,
+                                                 ucs->bulk_out_endpointAddr & 0x0f),
+                                 ucs->bulk_out_buffer, count,
+                                 gigaset_write_bulk_callback, cs);
+               ret = usb_submit_urb(ucs->bulk_out_urb, SLAB_ATOMIC);
+       } else {
+               ret = -ENODEV;
+       }
+       spin_unlock_irqrestore(&cs->lock, flags);
 
-       ret = usb_submit_urb(ucs->bulk_out_urb, SLAB_ATOMIC);
        if (ret) {
-               err("could not submit urb (error %d).", -ret);
+               err("could not submit urb (error %d)\n", -ret);
                atomic_set(&ucs->busy, 0);
        }
+
        if (!bcs->tx_skb->len) {
                /* skb sent completely */
                gigaset_skb_sent(bcs, bcs->tx_skb); //FIXME also, when ret<0?
 
-               dbg(DEBUG_INTR,
-                   "kfree skb (Adr: %lx)!", (unsigned long) bcs->tx_skb);
+               gig_dbg(DEBUG_INTR, "kfree skb (Adr: %lx)!",
+                       (unsigned long) bcs->tx_skb);
                dev_kfree_skb_any(bcs->tx_skb);
                bcs->tx_skb = NULL;
        }
 
        return ret;
-error:
-       dev_kfree_skb_any(bcs->tx_skb);
-       bcs->tx_skb = NULL;
-       return ret;
-
 }
 
 static int gigaset_probe(struct usb_interface *interface,
-                         const struct usb_device_id *id)
+                        const struct usb_device_id *id)
 {
        int retval;
        struct usb_device *udev = interface_to_usbdev(interface);
@@ -720,16 +698,14 @@ static int gigaset_probe(struct usb_interface *interface,
        struct usb_host_interface *hostif;
        struct cardstate *cs = NULL;
        struct usb_cardstate *ucs = NULL;
-       //struct usb_interface_descriptor *iface_desc;
        struct usb_endpoint_descriptor *endpoint;
-       //isdn_ctrl command;
        int buffer_size;
        int alt;
-       //unsigned long flags;
 
-       info("%s: Check if device matches .. (Vendor: 0x%x, Product: 0x%x)",
-           __func__, le16_to_cpu(udev->descriptor.idVendor),
-           le16_to_cpu(udev->descriptor.idProduct));
+       gig_dbg(DEBUG_ANY,
+               "%s: Check if device matches .. (Vendor: 0x%x, Product: 0x%x)",
+               __func__, le16_to_cpu(udev->descriptor.idVendor),
+               le16_to_cpu(udev->descriptor.idProduct));
 
        retval = -ENODEV; //FIXME
 
@@ -744,7 +720,7 @@ static int gigaset_probe(struct usb_interface *interface,
        ifnum = hostif->desc.bInterfaceNumber; // FIXME ?
 
        if (alt != 0 || ifnum != 0) {
-               warn("ifnum %d, alt %d", ifnum, alt);
+               dev_warn(&udev->dev, "ifnum %d, alt %d\n", ifnum, alt);
                return -ENODEV;
        }
 
@@ -752,42 +728,29 @@ static int gigaset_probe(struct usb_interface *interface,
         *
         */
        if (hostif->desc.bInterfaceClass != 255) {
-               info("%s: Device matched, but iface_desc[%d]->bInterfaceClass==%d !",
-                      __func__, ifnum, hostif->desc.bInterfaceClass);
+               dev_info(&udev->dev,
+               "%s: Device matched but iface_desc[%d]->bInterfaceClass==%d!\n",
+                        __func__, ifnum, hostif->desc.bInterfaceClass);
                return -ENODEV;
        }
 
-       info("%s: Device matched ... !", __func__);
+       dev_info(&udev->dev, "%s: Device matched ... !\n", __func__);
 
        cs = gigaset_getunassignedcs(driver);
        if (!cs) {
-               warn("No free cardstate!");
+               dev_warn(&udev->dev, "no free cardstate\n");
                return -ENODEV;
        }
        ucs = cs->hw.usb;
 
-#if 0
-       if (usb_set_configuration(udev, udev->config[0].desc.bConfigurationValue) < 0) {
-               warn("set_configuration failed");
-               goto error;
-       }
-
-
-       if (usb_set_interface(udev, ifnum/*==0*/, alt/*==0*/) < 0) {
-               warn("usb_set_interface failed, device %d interface %d altsetting %d",
-                    udev->devnum, ifnum, alt);
-               goto error;
-       }
-#endif
+       /* save off device structure ptrs for later use */
+       usb_get_dev(udev);
+       ucs->udev = udev;
+       ucs->interface = interface;
+       cs->dev = &interface->dev;
 
-       /* set up the endpoint information */
-       /* check out the endpoints */
-       /* We will get 2 endpoints: One for sending commands to the device (bulk out) and one to
-        * poll messages from the device(int in).
-        * Therefore we will have an almost similiar situation as with our serial port handler.
-        * If an connection will be established, we will have to create data in/out pipes
-        * dynamically...
-        */
+       /* save address of controller structure */
+       usb_set_intfdata(interface, cs); // dev_set_drvdata(&interface->dev, cs);
 
        endpoint = &hostif->endpoint[0].desc;
 
@@ -796,14 +759,14 @@ static int gigaset_probe(struct usb_interface *interface,
        ucs->bulk_out_endpointAddr = endpoint->bEndpointAddress;
        ucs->bulk_out_buffer = kmalloc(buffer_size, GFP_KERNEL);
        if (!ucs->bulk_out_buffer) {
-               err("Couldn't allocate bulk_out_buffer");
+               dev_err(cs->dev, "Couldn't allocate bulk_out_buffer\n");
                retval = -ENOMEM;
                goto error;
        }
 
        ucs->bulk_out_urb = usb_alloc_urb(0, SLAB_KERNEL);
        if (!ucs->bulk_out_urb) {
-               err("Couldn't allocate bulk_out_buffer");
+               dev_err(cs->dev, "Couldn't allocate bulk_out_urb\n");
                retval = -ENOMEM;
                goto error;
        }
@@ -811,12 +774,10 @@ static int gigaset_probe(struct usb_interface *interface,
        endpoint = &hostif->endpoint[1].desc;
 
        atomic_set(&ucs->busy, 0);
-       ucs->udev = udev;
-       ucs->interface = interface;
 
        ucs->read_urb = usb_alloc_urb(0, SLAB_KERNEL);
        if (!ucs->read_urb) {
-               err("No free urbs available");
+               dev_err(cs->dev, "No free urbs available\n");
                retval = -ENOMEM;
                goto error;
        }
@@ -825,38 +786,33 @@ static int gigaset_probe(struct usb_interface *interface,
        ucs->int_in_endpointAddr = endpoint->bEndpointAddress;
        cs->inbuf[0].rcvbuf = kmalloc(buffer_size, GFP_KERNEL);
        if (!cs->inbuf[0].rcvbuf) {
-               err("Couldn't allocate rcvbuf");
+               dev_err(cs->dev, "Couldn't allocate rcvbuf\n");
                retval = -ENOMEM;
                goto error;
        }
        /* Fill the interrupt urb and send it to the core */
        usb_fill_int_urb(ucs->read_urb, udev,
-                        usb_rcvintpipe(udev,
-                                       endpoint->bEndpointAddress & 0x0f),
-                        cs->inbuf[0].rcvbuf, buffer_size,
-                        gigaset_read_int_callback,
-                        cs->inbuf + 0, endpoint->bInterval);
+                        usb_rcvintpipe(udev,
+                                       endpoint->bEndpointAddress & 0x0f),
+                        cs->inbuf[0].rcvbuf, buffer_size,
+                        gigaset_read_int_callback,
+                        cs->inbuf + 0, endpoint->bInterval);
 
        retval = usb_submit_urb(ucs->read_urb, SLAB_KERNEL);
        if (retval) {
-               err("Could not submit URB!");
+               dev_err(cs->dev, "Could not submit URB (error %d)\n", -retval);
                goto error;
        }
 
        /* tell common part that the device is ready */
        if (startmode == SM_LOCKED)
                atomic_set(&cs->mstate, MS_LOCKED);
+
        if (!gigaset_start(cs)) {
                tasklet_kill(&cs->write_tasklet);
                retval = -ENODEV; //FIXME
                goto error;
        }
-
-       /* save address of controller structure */
-       usb_set_intfdata(interface, cs);
-
-       /* set up device sysfs */
-       gigaset_init_dev_sysfs(interface);
        return 0;
 
 error:
@@ -868,48 +824,45 @@ error:
        kfree(cs->inbuf[0].rcvbuf);
        if (ucs->read_urb != NULL)
                usb_free_urb(ucs->read_urb);
+       usb_set_intfdata(interface, NULL);
        ucs->read_urb = ucs->bulk_out_urb = NULL;
        cs->inbuf[0].rcvbuf = ucs->bulk_out_buffer = NULL;
+       usb_put_dev(ucs->udev);
+       ucs->udev = NULL;
+       ucs->interface = NULL;
        gigaset_unassign(cs);
        return retval;
 }
 
-/**
- *     skel_disconnect
- */
 static void gigaset_disconnect(struct usb_interface *interface)
 {
        struct cardstate *cs;
        struct usb_cardstate *ucs;
 
        cs = usb_get_intfdata(interface);
-
-       /* clear device sysfs */
-       gigaset_free_dev_sysfs(interface);
-
-       usb_set_intfdata(interface, NULL);
        ucs = cs->hw.usb;
        usb_kill_urb(ucs->read_urb);
-       //info("GigaSet USB device #%d will be disconnected", minor);
 
        gigaset_stop(cs);
 
+       usb_set_intfdata(interface, NULL);
        tasklet_kill(&cs->write_tasklet);
 
-       usb_kill_urb(ucs->bulk_out_urb);  /* FIXME: nur, wenn noetig */
-       //usb_kill_urb(ucs->urb_cmd_out);  /* FIXME: nur, wenn noetig */
+       usb_kill_urb(ucs->bulk_out_urb);        /* FIXME: only if active? */
 
        kfree(ucs->bulk_out_buffer);
        if (ucs->bulk_out_urb != NULL)
                usb_free_urb(ucs->bulk_out_urb);
-       //if(ucs->urb_cmd_out != NULL)
-       //      usb_free_urb(ucs->urb_cmd_out);
        kfree(cs->inbuf[0].rcvbuf);
        if (ucs->read_urb != NULL)
                usb_free_urb(ucs->read_urb);
-       ucs->read_urb = ucs->bulk_out_urb/*=ucs->urb_cmd_out*/=NULL;
+       ucs->read_urb = ucs->bulk_out_urb = NULL;
        cs->inbuf[0].rcvbuf = ucs->bulk_out_buffer = NULL;
 
+       usb_put_dev(ucs->udev);
+       ucs->interface = NULL;
+       ucs->udev = NULL;
+       cs->dev = NULL;
        gigaset_unassign(cs);
 }
 
@@ -942,9 +895,9 @@ static int __init usb_gigaset_init(void)
 
        /* allocate memory for our driver state and intialize it */
        if ((driver = gigaset_initdriver(GIGASET_MINOR, GIGASET_MINORS,
-                                      GIGASET_MODULENAME, GIGASET_DEVNAME,
-                                      GIGASET_DEVFSNAME, &ops,
-                                      THIS_MODULE)) == NULL)
+                                      GIGASET_MODULENAME, GIGASET_DEVNAME,
+                                      GIGASET_DEVFSNAME, &ops,
+                                      THIS_MODULE)) == NULL)
                goto error;
 
        /* allocate memory for our device state and intialize it */
@@ -981,8 +934,8 @@ error:      if (cardstate)
 static void __exit usb_gigaset_exit(void)
 {
        gigaset_blockdriver(driver); /* => probe will fail
-                                     * => no gigaset_start any more
-                                     */
+                                     * => no gigaset_start any more
+                                     */
 
        gigaset_shutdown(cardstate);
        /* from now on, no isdn callback should be possible */
index a0927d1b7a0c994f96cd213b0a0c4040901268f2..918742271c79f6e617bec47ab38bcca52eda3483 100644 (file)
@@ -109,7 +109,7 @@ isdn_ppp_free(isdn_net_local * lp)
 {
        struct ippp_struct *is;
 
-       if (lp->ppp_slot < 0 || lp->ppp_slot > ISDN_MAX_CHANNELS) {
+       if (lp->ppp_slot < 0 || lp->ppp_slot >= ISDN_MAX_CHANNELS) {
                printk(KERN_ERR "%s: ppp_slot(%d) out of range\n",
                        __FUNCTION__, lp->ppp_slot);
                return 0;
@@ -126,7 +126,7 @@ isdn_ppp_free(isdn_net_local * lp)
        lp->netdev->pb->ref_ct--;
        spin_unlock(&lp->netdev->pb->lock);
 #endif /* CONFIG_ISDN_MPP */
-       if (lp->ppp_slot < 0 || lp->ppp_slot > ISDN_MAX_CHANNELS) {
+       if (lp->ppp_slot < 0 || lp->ppp_slot >= ISDN_MAX_CHANNELS) {
                printk(KERN_ERR "%s: ppp_slot(%d) now invalid\n",
                        __FUNCTION__, lp->ppp_slot);
                return 0;
@@ -279,7 +279,7 @@ isdn_ppp_open(int min, struct file *file)
        int slot;
        struct ippp_struct *is;
 
-       if (min < 0 || min > ISDN_MAX_CHANNELS)
+       if (min < 0 || min >= ISDN_MAX_CHANNELS)
                return -ENODEV;
 
        slot = isdn_ppp_get_slot();
@@ -1042,7 +1042,7 @@ isdn_ppp_push_higher(isdn_net_dev * net_dev, isdn_net_local * lp, struct sk_buff
        if (lp->master) { // FIXME?
                mlp = (isdn_net_local *) lp->master->priv;
                slot = mlp->ppp_slot;
-               if (slot < 0 || slot > ISDN_MAX_CHANNELS) {
+               if (slot < 0 || slot >= ISDN_MAX_CHANNELS) {
                        printk(KERN_ERR "isdn_ppp_push_higher: master->ppp_slot(%d)\n",
                                lp->ppp_slot);
                        goto drop_packet;
@@ -1264,7 +1264,7 @@ isdn_ppp_xmit(struct sk_buff *skb, struct net_device *netdev)
        /* we have our lp locked from now on */
 
        slot = lp->ppp_slot;
-       if (slot < 0 || slot > ISDN_MAX_CHANNELS) {
+       if (slot < 0 || slot >= ISDN_MAX_CHANNELS) {
                printk(KERN_ERR "isdn_ppp_xmit: lp->ppp_slot(%d)\n",
                        lp->ppp_slot);
                kfree_skb(skb);
@@ -1603,7 +1603,7 @@ static void isdn_ppp_mp_receive(isdn_net_dev * net_dev, isdn_net_local * lp,
        mp = net_dev->pb;
         stats = &mp->stats;
        slot = lp->ppp_slot;
-       if (slot < 0 || slot > ISDN_MAX_CHANNELS) {
+       if (slot < 0 || slot >= ISDN_MAX_CHANNELS) {
                printk(KERN_ERR "%s: lp->ppp_slot(%d)\n",
                        __FUNCTION__, lp->ppp_slot);
                stats->frame_drops++;
@@ -1640,7 +1640,7 @@ static void isdn_ppp_mp_receive(isdn_net_dev * net_dev, isdn_net_local * lp,
        is->last_link_seqno = minseq = newseq;
        for (lpq = net_dev->queue;;) {
                slot = lpq->ppp_slot;
-               if (slot < 0 || slot > ISDN_MAX_CHANNELS) {
+               if (slot < 0 || slot >= ISDN_MAX_CHANNELS) {
                        printk(KERN_ERR "%s: lpq->ppp_slot(%d)\n",
                                __FUNCTION__, lpq->ppp_slot);
                } else {
@@ -2648,7 +2648,7 @@ static void isdn_ppp_receive_ccp(isdn_net_dev *net_dev, isdn_net_local *lp,
 
        printk(KERN_DEBUG "Received CCP frame from peer slot(%d)\n",
                lp->ppp_slot);
-       if (lp->ppp_slot < 0 || lp->ppp_slot > ISDN_MAX_CHANNELS) {
+       if (lp->ppp_slot < 0 || lp->ppp_slot >= ISDN_MAX_CHANNELS) {
                printk(KERN_ERR "%s: lp->ppp_slot(%d) out of range\n",
                        __FUNCTION__, lp->ppp_slot);
                return;
@@ -2658,7 +2658,7 @@ static void isdn_ppp_receive_ccp(isdn_net_dev *net_dev, isdn_net_local *lp,
 
        if(lp->master) {
                int slot = ((isdn_net_local *) (lp->master->priv))->ppp_slot;
-               if (slot < 0 || slot > ISDN_MAX_CHANNELS) {
+               if (slot < 0 || slot >= ISDN_MAX_CHANNELS) {
                        printk(KERN_ERR "%s: slot(%d) out of range\n",
                                __FUNCTION__, slot);
                        return;
@@ -2845,7 +2845,7 @@ static void isdn_ppp_send_ccp(isdn_net_dev *net_dev, isdn_net_local *lp, struct
 
        if (lp->master) {
                slot = ((isdn_net_local *) (lp->master->priv))->ppp_slot;
-               if (slot < 0 || slot > ISDN_MAX_CHANNELS) {
+               if (slot < 0 || slot >= ISDN_MAX_CHANNELS) {
                        printk(KERN_ERR "%s: slot(%d) out of range\n",
                                __FUNCTION__, slot);
                        return;
index 2c4f20b7f021591dea1495a057c0f988cce7093b..3f5b647945426d5db0c1ffa7793b6fa8dc37e482 100644 (file)
@@ -14,13 +14,7 @@ config LEDS_CLASS
          This option enables the led sysfs class in /sys/class/leds.  You'll
          need this to do anything useful with LEDs.  If unsure, say N.
 
-config LEDS_TRIGGERS
-       bool "LED Trigger support"
-       depends NEW_LEDS
-       help
-         This option enables trigger support for the leds class.
-         These triggers allow kernel events to drive the LEDs and can
-         be configured via sysfs. If unsure, say Y.
+comment "LED drivers"
 
 config LEDS_CORGI
        tristate "LED Support for the Sharp SL-C7x0 series"
@@ -59,6 +53,23 @@ config LEDS_TOSA
          This option enables support for the LEDs on Sharp Zaurus
          SL-6000 series.
 
+config LEDS_S3C24XX
+       tristate "LED Support for Samsung S3C24XX GPIO LEDs"
+       depends on LEDS_CLASS && ARCH_S3C2410
+       help
+         This option enables support for LEDs connected to GPIO lines
+         on Samsung S3C24XX series CPUs, such as the S3C2410 and S3C2440.
+
+comment "LED Triggers"
+
+config LEDS_TRIGGERS
+       bool "LED Trigger support"
+       depends NEW_LEDS
+       help
+         This option enables trigger support for the leds class.
+         These triggers allow kernel events to drive the LEDs and can
+         be configured via sysfs. If unsure, say Y.
+
 config LEDS_TRIGGER_TIMER
        tristate "LED Timer Trigger"
        depends LEDS_TRIGGERS
@@ -67,7 +78,7 @@ config LEDS_TRIGGER_TIMER
          via sysfs. If unsure, say Y.
 
 config LEDS_TRIGGER_IDE_DISK
-       bool "LED Timer Trigger"
+       bool "LED IDE Disk Trigger"
        depends LEDS_TRIGGERS && BLK_DEV_IDEDISK
        help
          This allows LEDs to be controlled by IDE disk activity.
index 40699d3cabbf377898aa9e566d794068ee7dc775..40f042633bf541e2cf4bf7ca9c42452a9d4b2ff5 100644 (file)
@@ -10,6 +10,7 @@ obj-$(CONFIG_LEDS_LOCOMO)             += leds-locomo.o
 obj-$(CONFIG_LEDS_SPITZ)               += leds-spitz.o
 obj-$(CONFIG_LEDS_IXP4XX)              += leds-ixp4xx-gpio.o
 obj-$(CONFIG_LEDS_TOSA)                        += leds-tosa.o
+obj-$(CONFIG_LEDS_S3C24XX)             += leds-s3c24xx.o
 
 # LED Triggers
 obj-$(CONFIG_LEDS_TRIGGER_TIMER)       += ledtrig-timer.o
diff --git a/drivers/leds/leds-s3c24xx.c b/drivers/leds/leds-s3c24xx.c
new file mode 100644 (file)
index 0000000..650cf72
--- /dev/null
@@ -0,0 +1,163 @@
+/* drivers/leds/leds-s3c24xx.c
+ *
+ * (c) 2006 Simtec Electronics
+ *     http://armlinux.simtec.co.uk/
+ *     Ben Dooks <ben@simtec.co.uk>
+ *
+ * S3C24XX - LEDs GPIO driver
+ *
+ * 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 <linux/config.h>
+#include <linux/kernel.h>
+#include <linux/init.h>
+#include <linux/platform_device.h>
+#include <linux/leds.h>
+
+#include <asm/arch/hardware.h>
+#include <asm/arch/regs-gpio.h>
+#include <asm/arch/leds-gpio.h>
+
+/* our context */
+
+struct s3c24xx_gpio_led {
+       struct led_classdev              cdev;
+       struct s3c24xx_led_platdata     *pdata;
+};
+
+static inline struct s3c24xx_gpio_led *pdev_to_gpio(struct platform_device *dev)
+{
+       return platform_get_drvdata(dev);
+}
+
+static inline struct s3c24xx_gpio_led *to_gpio(struct led_classdev *led_cdev)
+{
+       return container_of(led_cdev, struct s3c24xx_gpio_led, cdev);
+}
+
+static void s3c24xx_led_set(struct led_classdev *led_cdev,
+                           enum led_brightness value)
+{
+       struct s3c24xx_gpio_led *led = to_gpio(led_cdev);
+       struct s3c24xx_led_platdata *pd = led->pdata;
+
+       /* there will be a sort delay between setting the output and
+        * going from output to input when using tristate. */
+
+       s3c2410_gpio_setpin(pd->gpio, (value ? 1 : 0) ^
+                           (pd->flags & S3C24XX_LEDF_ACTLOW));
+
+       if (pd->flags & S3C24XX_LEDF_TRISTATE)
+               s3c2410_gpio_cfgpin(pd->gpio,
+                                   value ? S3C2410_GPIO_OUTPUT : S3C2410_GPIO_INPUT);
+
+}
+
+static int s3c24xx_led_remove(struct platform_device *dev)
+{
+       struct s3c24xx_gpio_led *led = pdev_to_gpio(dev);
+
+       led_classdev_unregister(&led->cdev);
+       kfree(led);
+
+       return 0;
+}
+
+static int s3c24xx_led_probe(struct platform_device *dev)
+{
+       struct s3c24xx_led_platdata *pdata = dev->dev.platform_data;
+       struct s3c24xx_gpio_led *led;
+       int ret;
+
+       led = kzalloc(sizeof(struct s3c24xx_gpio_led), GFP_KERNEL);
+       if (led == NULL) {
+               dev_err(&dev->dev, "No memory for device\n");
+               return -ENOMEM;
+       }
+
+       platform_set_drvdata(dev, led);
+
+       led->cdev.brightness_set = s3c24xx_led_set;
+       led->cdev.default_trigger = pdata->def_trigger;
+       led->cdev.name = pdata->name;
+
+       led->pdata = pdata;
+
+       /* no point in having a pull-up if we are always driving */
+
+       if (pdata->flags & S3C24XX_LEDF_TRISTATE) {
+               s3c2410_gpio_setpin(pdata->gpio, 0);
+               s3c2410_gpio_cfgpin(pdata->gpio, S3C2410_GPIO_INPUT);
+       } else {
+               s3c2410_gpio_pullup(pdata->gpio, 0);
+               s3c2410_gpio_setpin(pdata->gpio, 0);
+               s3c2410_gpio_cfgpin(pdata->gpio, S3C2410_GPIO_OUTPUT);
+       }
+
+       /* register our new led device */
+
+       ret = led_classdev_register(&dev->dev, &led->cdev);
+       if (ret < 0) {
+               dev_err(&dev->dev, "led_classdev_register failed\n");
+               goto exit_err1;
+       }
+
+       return 0;
+
+ exit_err1:
+       kfree(led);
+       return ret;
+}
+
+
+#ifdef CONFIG_PM
+static int s3c24xx_led_suspend(struct platform_device *dev, pm_message_t state)
+{
+       struct s3c24xx_gpio_led *led = pdev_to_gpio(dev);
+
+       led_classdev_suspend(&led->cdev);
+       return 0;
+}
+
+static int s3c24xx_led_resume(struct platform_device *dev)
+{
+       struct s3c24xx_gpio_led *led = pdev_to_gpio(dev);
+
+       led_classdev_resume(&led->cdev);
+       return 0;
+}
+#else
+#define s3c24xx_led_suspend NULL
+#define s3c24xx_led_resume NULL
+#endif
+
+static struct platform_driver s3c24xx_led_driver = {
+       .probe          = s3c24xx_led_probe,
+       .remove         = s3c24xx_led_remove,
+       .suspend        = s3c24xx_led_suspend,
+       .resume         = s3c24xx_led_resume,
+       .driver         = {
+               .name           = "s3c24xx_led",
+               .owner          = THIS_MODULE,
+       },
+};
+
+static int __init s3c24xx_led_init(void)
+{
+       return platform_driver_register(&s3c24xx_led_driver);
+}
+
+static void __exit s3c24xx_led_exit(void)
+{
+       platform_driver_unregister(&s3c24xx_led_driver);
+}
+
+module_init(s3c24xx_led_init);
+module_exit(s3c24xx_led_exit);
+
+MODULE_AUTHOR("Ben Dooks <ben@simtec.co.uk>");
+MODULE_DESCRIPTION("S3C24XX LED driver");
+MODULE_LICENSE("GPL");
index fd2aae150ccc5c4104ed434fc78e18cb6f9d78be..ac25a48362acab47ea103fa176b39590ed5c2e42 100644 (file)
@@ -139,11 +139,12 @@ config MD_RAID5_RESHAPE
          is online.  However it is still EXPERIMENTAL code.  It should
          work, but please be sure that you have backups.
 
-         You will need a version of mdadm newer than 2.3.1.   During the
-         early stage of reshape there is a critical section where live data
-         is being over-written.  A crash during this time needs extra care
-         for recovery.  The newer mdadm takes a copy of the data in the
-         critical section and will restore it, if necessary, after a crash.
+         You will need mdadm verion 2.4.1 or later to use this
+         feature safely.  During the early stage of reshape there is
+         a critical section where live data is being over-written.  A
+         crash during this time needs extra care for recovery.  The
+         newer mdadm takes a copy of the data in the critical section
+         and will restore it, if necessary, after a crash.
 
          The mdadm usage is e.g.
               mdadm --grow /dev/md1 --raid-disks=6
index 1ed5152db45060b9ec1ce224b1c3ebb30cb3fe1d..d7316b829a62687a4c29372a893d2684121fb3a3 100644 (file)
@@ -163,6 +163,7 @@ void md_new_event(mddev_t *mddev)
 {
        atomic_inc(&md_event_count);
        wake_up(&md_event_waiters);
+       sysfs_notify(&mddev->kobj, NULL, "sync_action");
 }
 EXPORT_SYMBOL_GPL(md_new_event);
 
@@ -278,11 +279,6 @@ static inline int mddev_lock(mddev_t * mddev)
        return mutex_lock_interruptible(&mddev->reconfig_mutex);
 }
 
-static inline void mddev_lock_uninterruptible(mddev_t * mddev)
-{
-       mutex_lock(&mddev->reconfig_mutex);
-}
-
 static inline int mddev_trylock(mddev_t * mddev)
 {
        return mutex_trylock(&mddev->reconfig_mutex);
@@ -2457,9 +2453,11 @@ md_attr_show(struct kobject *kobj, struct attribute *attr, char *page)
 
        if (!entry->show)
                return -EIO;
-       mddev_lock(mddev);
-       rv = entry->show(mddev, page);
-       mddev_unlock(mddev);
+       rv = mddev_lock(mddev);
+       if (!rv) {
+               rv = entry->show(mddev, page);
+               mddev_unlock(mddev);
+       }
        return rv;
 }
 
@@ -2473,9 +2471,11 @@ md_attr_store(struct kobject *kobj, struct attribute *attr,
 
        if (!entry->store)
                return -EIO;
-       mddev_lock(mddev);
-       rv = entry->store(mddev, page, length);
-       mddev_unlock(mddev);
+       rv = mddev_lock(mddev);
+       if (!rv) {
+               rv = entry->store(mddev, page, length);
+               mddev_unlock(mddev);
+       }
        return rv;
 }
 
@@ -4340,8 +4340,9 @@ static int md_seq_show(struct seq_file *seq, void *v)
                return 0;
        }
 
-       if (mddev_lock(mddev)!=0) 
+       if (mddev_lock(mddev) < 0)
                return -EINTR;
+
        if (mddev->pers || mddev->raid_disks || !list_empty(&mddev->disks)) {
                seq_printf(seq, "%s : %sactive", mdname(mddev),
                                                mddev->pers ? "" : "in");
index 4092a5e37ffce0f0207a5e75a7e166cae2baee54..b3ea2d63db9b04a5e7161a85f469711b4817cd16 100644 (file)
@@ -84,4 +84,4 @@ obj-$(CONFIG_USB_IBMCAM)        += usbvideo/
 obj-$(CONFIG_USB_KONICAWC)      += usbvideo/
 obj-$(CONFIG_USB_VICAM)         += usbvideo/
 
-EXTRA_CFLAGS += -I$(srctree)/drivers/media/dvb/dvb-core
+EXTRA_CFLAGS += -Idrivers/media/dvb/dvb-core
index 94350f21cdc0a5c71fabe31aded4a5aa6fbb5b2b..db641a36b197afc10495f573bb9a9e20b17ad8c9 100644 (file)
@@ -9,4 +9,4 @@ bttv-objs      :=      bttv-driver.o bttv-cards.o bttv-if.o \
 obj-$(CONFIG_VIDEO_BT848) += bttv.o
 
 EXTRA_CFLAGS += -I$(src)/..
-EXTRA_CFLAGS += -I$(srctree)/drivers/media/dvb/dvb-core
+EXTRA_CFLAGS += -Idrivers/media/dvb/dvb-core
index 32a896c23d1e418677158848fa1fe3e86769cb7b..6e8665be8954f4699e783719bdb8f25df5b687bf 100644 (file)
@@ -3,4 +3,4 @@ cx25840-objs    := cx25840-core.o cx25840-audio.o cx25840-firmware.o \
 
 obj-$(CONFIG_VIDEO_CX25840) += cx25840.o
 
-EXTRA_CFLAGS += -I$(src)/..
+EXTRA_CFLAGS += -Idrivers/media/video
index 6482b9aa6a1fa08b634a7f38e34a10f49b89d781..0dcd09b9b727aa0a43b9191c70011c9b60e1e716 100644 (file)
@@ -8,9 +8,9 @@ obj-$(CONFIG_VIDEO_CX88_DVB) += cx88-dvb.o
 obj-$(CONFIG_VIDEO_CX88_ALSA) += cx88-alsa.o
 obj-$(CONFIG_VIDEO_CX88_VP3054) += cx88-vp3054-i2c.o
 
-EXTRA_CFLAGS += -I$(src)/..
-EXTRA_CFLAGS += -I$(srctree)/drivers/media/dvb/dvb-core
-EXTRA_CFLAGS += -I$(srctree)/drivers/media/dvb/frontends
+EXTRA_CFLAGS += -Idrivers/media/video
+EXTRA_CFLAGS += -Idrivers/media/dvb/dvb-core
+EXTRA_CFLAGS += -Idrivers/media/dvb/frontends
 
 extra-cflags-$(CONFIG_VIDEO_BUF_DVB) += -DHAVE_VIDEO_BUF_DVB=1
 extra-cflags-$(CONFIG_DVB_CX22702)   += -DHAVE_CX22702=1
index da457a05b0dd4a9a68af9804ab883924254c287d..826d0e3407535cee83680c68700272f3999544fd 100644 (file)
@@ -3,4 +3,4 @@ em28xx-objs     := em28xx-video.o em28xx-i2c.o em28xx-cards.o em28xx-core.o \
 
 obj-$(CONFIG_VIDEO_EM28XX) += em28xx.o
 
-EXTRA_CFLAGS += -I$(src)/..
+EXTRA_CFLAGS += -Idrivers/media/video
index 1ba998424bbdcb376fbf6901028f765031aa1e32..be7b9ee697d6ceb1aa41358f7887b35e32e5c2cb 100644 (file)
@@ -11,9 +11,9 @@ obj-$(CONFIG_VIDEO_SAA7134_OSS) += saa7134-oss.o
 
 obj-$(CONFIG_VIDEO_SAA7134_DVB) += saa7134-dvb.o
 
-EXTRA_CFLAGS += -I$(src)/..
-EXTRA_CFLAGS += -I$(srctree)/drivers/media/dvb/dvb-core
-EXTRA_CFLAGS += -I$(srctree)/drivers/media/dvb/frontends
+EXTRA_CFLAGS += -Idrivers/media/video
+EXTRA_CFLAGS += -Idrivers/media/dvb/dvb-core
+EXTRA_CFLAGS += -Idrivers/media/dvb/frontends
 
 extra-cflags-$(CONFIG_VIDEO_BUF_DVB) += -DHAVE_VIDEO_BUF_DVB=1
 extra-cflags-$(CONFIG_DVB_MT352)     += -DHAVE_MT352=1
index c98571c9d5a639df1470003475f07c281580727f..13de05532e0ac7015ae7d5c98780d09a300070e9 100644 (file)
@@ -32,6 +32,7 @@
 #include <linux/interrupt.h>
 #include <linux/delay.h>
 #include <linux/mutex.h>
+#include <linux/dma-mapping.h>
 
 #include "saa7134-reg.h"
 #include "saa7134.h"
@@ -870,7 +871,7 @@ static int __devinit saa7134_initdev(struct pci_dev *pci_dev,
               pci_name(pci_dev), dev->pci_rev, pci_dev->irq,
               dev->pci_lat,pci_resource_start(pci_dev,0));
        pci_set_master(pci_dev);
-       if (!pci_dma_supported(pci_dev,0xffffffff)) {
+       if (!pci_dma_supported(pci_dev, DMA_32BIT_MASK)) {
                printk("%s: Oops: no 32bit PCI DMA ???\n",dev->name);
                err = -EIO;
                goto fail1;
index 010d4a39269b8c55dc39eab53516f4a68636f44c..e9716b10acea68dba88d3c29b9a96dd220efeb21 100644 (file)
@@ -366,7 +366,15 @@ mptsas_sas_enclosure_pg0(MPT_ADAPTER *ioc, struct mptsas_enclosure *enclosure,
 static int
 mptsas_slave_configure(struct scsi_device *sdev)
 {
-       sas_read_port_mode_page(sdev);
+       struct Scsi_Host        *host = sdev->host;
+       MPT_SCSI_HOST           *hd = (MPT_SCSI_HOST *)host->hostdata;
+
+       /*
+        * RAID volumes placed beyond the last expected port.
+        * Ignore sending sas mode pages in that case..
+        */
+       if (sdev->channel < hd->ioc->num_ports)
+               sas_read_port_mode_page(sdev);
 
        return mptscsih_slave_configure(sdev);
 }
index dd628cb51e312e0a109fad6e13b7d1cda7ca06bb..7fac438b5c32cbc376a9dc4945247a767a42fc55 100644 (file)
@@ -129,8 +129,8 @@ config MTDRAM_ABS_POS
          allocating space from Linux's available memory. Otherwise, leave
          this set to zero. Most people will want to leave this as zero.
 
-config MTD_BLKMTD
-       tristate "MTD emulation using block device"
+config MTD_BLOCK2MTD
+       tristate "MTD using block device"
        depends on MTD
        help
          This driver allows a block device to appear as an MTD. It would
@@ -141,15 +141,6 @@ config MTD_BLKMTD
          Testing MTD users (eg JFFS2) on large media and media that might
          be removed during a write (using the floppy drive).
 
-config MTD_BLOCK2MTD
-       tristate "MTD using block device (rewrite)"
-       depends on MTD && EXPERIMENTAL
-       help
-         This driver is basically the same at MTD_BLKMTD above, but
-         experienced some interface changes plus serious speedups.  In
-         the long term, it should replace MTD_BLKMTD.  Right now, you
-         shouldn't entrust important data to it yet.
-
 comment "Disk-On-Chip Device Drivers"
 
 config MTD_DOC2000
index 7c5ed2178380119b074f738ea14d5e6b5fd1e345..b6573670316f198e02b3df9d0eafc12fc5e96d48 100644 (file)
@@ -21,7 +21,6 @@ obj-$(CONFIG_MTD_PMC551)      += pmc551.o
 obj-$(CONFIG_MTD_MS02NV)       += ms02-nv.o
 obj-$(CONFIG_MTD_MTDRAM)       += mtdram.o
 obj-$(CONFIG_MTD_LART)         += lart.o
-obj-$(CONFIG_MTD_BLKMTD)       += blkmtd.o
 obj-$(CONFIG_MTD_BLOCK2MTD)    += block2mtd.o
 obj-$(CONFIG_MTD_DATAFLASH)    += mtd_dataflash.o
 obj-$(CONFIG_MTD_M25P80)       += m25p80.o
diff --git a/drivers/mtd/devices/blkmtd.c b/drivers/mtd/devices/blkmtd.c
deleted file mode 100644 (file)
index 79f2e1f..0000000
+++ /dev/null
@@ -1,819 +0,0 @@
-/*
- * $Id: blkmtd.c,v 1.27 2005/11/07 11:14:24 gleixner Exp $
- *
- * blkmtd.c - use a block device as a fake MTD
- *
- * Author: Simon Evans <spse@secret.org.uk>
- *
- * Copyright (C) 2001,2002 Simon Evans
- *
- * Licence: GPL
- *
- * How it works:
- *     The driver uses raw/io to read/write the device and the page
- *     cache to cache access. Writes update the page cache with the
- *     new data and mark it dirty and add the page into a BIO which
- *     is then written out.
- *
- *     It can be loaded Read-Only to prevent erases and writes to the
- *     medium.
- *
- */
-
-#include <linux/config.h>
-#include <linux/module.h>
-#include <linux/fs.h>
-#include <linux/blkdev.h>
-#include <linux/bio.h>
-#include <linux/pagemap.h>
-#include <linux/list.h>
-#include <linux/init.h>
-#include <linux/mount.h>
-#include <linux/mtd/mtd.h>
-#include <linux/mutex.h>
-
-#define err(format, arg...) printk(KERN_ERR "blkmtd: " format "\n" , ## arg)
-#define info(format, arg...) printk(KERN_INFO "blkmtd: " format "\n" , ## arg)
-#define warn(format, arg...) printk(KERN_WARNING "blkmtd: " format "\n" , ## arg)
-#define crit(format, arg...) printk(KERN_CRIT "blkmtd: " format "\n" , ## arg)
-
-
-/* Default erase size in K, always make it a multiple of PAGE_SIZE */
-#define CONFIG_MTD_BLKDEV_ERASESIZE (128 << 10)        /* 128KiB */
-#define VERSION "$Revision: 1.27 $"
-
-/* Info for the block device */
-struct blkmtd_dev {
-       struct list_head list;
-       struct block_device *blkdev;
-       struct mtd_info mtd_info;
-       struct mutex wrbuf_mutex;
-};
-
-
-/* Static info about the MTD, used in cleanup_module */
-static LIST_HEAD(blkmtd_device_list);
-
-
-static void blkmtd_sync(struct mtd_info *mtd);
-
-#define MAX_DEVICES 4
-
-/* Module parameters passed by insmod/modprobe */
-static char *device[MAX_DEVICES];    /* the block device to use */
-static int erasesz[MAX_DEVICES];     /* optional default erase size */
-static int ro[MAX_DEVICES];          /* optional read only flag */
-static int sync;
-
-
-MODULE_LICENSE("GPL");
-MODULE_AUTHOR("Simon Evans <spse@secret.org.uk>");
-MODULE_DESCRIPTION("Emulate an MTD using a block device");
-module_param_array(device, charp, NULL, 0);
-MODULE_PARM_DESC(device, "block device to use");
-module_param_array(erasesz, int, NULL, 0);
-MODULE_PARM_DESC(erasesz, "optional erase size to use in KiB. eg 4=4KiB.");
-module_param_array(ro, bool, NULL, 0);
-MODULE_PARM_DESC(ro, "1=Read only, writes and erases cause errors");
-module_param(sync, bool, 0);
-MODULE_PARM_DESC(sync, "1=Synchronous writes");
-
-
-/* completion handler for BIO reads */
-static int bi_read_complete(struct bio *bio, unsigned int bytes_done, int error)
-{
-       if (bio->bi_size)
-               return 1;
-
-       complete((struct completion*)bio->bi_private);
-       return 0;
-}
-
-
-/* completion handler for BIO writes */
-static int bi_write_complete(struct bio *bio, unsigned int bytes_done, int error)
-{
-       const int uptodate = test_bit(BIO_UPTODATE, &bio->bi_flags);
-       struct bio_vec *bvec = bio->bi_io_vec + bio->bi_vcnt - 1;
-
-       if (bio->bi_size)
-               return 1;
-
-       if(!uptodate)
-               err("bi_write_complete: not uptodate\n");
-
-       do {
-               struct page *page = bvec->bv_page;
-               DEBUG(3, "Cleaning up page %ld\n", page->index);
-               if (--bvec >= bio->bi_io_vec)
-                       prefetchw(&bvec->bv_page->flags);
-
-               if (uptodate) {
-                       SetPageUptodate(page);
-               } else {
-                       ClearPageUptodate(page);
-                       SetPageError(page);
-               }
-               clear_page_dirty(page);
-               unlock_page(page);
-               page_cache_release(page);
-       } while (bvec >= bio->bi_io_vec);
-
-       complete((struct completion*)bio->bi_private);
-       return 0;
-}
-
-
-/* read one page from the block device */
-static int blkmtd_readpage(struct blkmtd_dev *dev, struct page *page)
-{
-       struct bio *bio;
-       struct completion event;
-       int err = -ENOMEM;
-
-       if(PageUptodate(page)) {
-               DEBUG(2, "blkmtd: readpage page %ld is already upto date\n", page->index);
-               unlock_page(page);
-               return 0;
-       }
-
-       ClearPageUptodate(page);
-       ClearPageError(page);
-
-       bio = bio_alloc(GFP_KERNEL, 1);
-       if(bio) {
-               init_completion(&event);
-               bio->bi_bdev = dev->blkdev;
-               bio->bi_sector = page->index << (PAGE_SHIFT-9);
-               bio->bi_private = &event;
-               bio->bi_end_io = bi_read_complete;
-               if(bio_add_page(bio, page, PAGE_SIZE, 0) == PAGE_SIZE) {
-                       submit_bio(READ_SYNC, bio);
-                       wait_for_completion(&event);
-                       err = test_bit(BIO_UPTODATE, &bio->bi_flags) ? 0 : -EIO;
-                       bio_put(bio);
-               }
-       }
-
-       if(err)
-               SetPageError(page);
-       else
-               SetPageUptodate(page);
-       flush_dcache_page(page);
-       unlock_page(page);
-       return err;
-}
-
-
-/* write out the current BIO and wait for it to finish */
-static int blkmtd_write_out(struct bio *bio)
-{
-       struct completion event;
-       int err;
-
-       if(!bio->bi_vcnt) {
-               bio_put(bio);
-               return 0;
-       }
-
-       init_completion(&event);
-       bio->bi_private = &event;
-       bio->bi_end_io = bi_write_complete;
-       submit_bio(WRITE_SYNC, bio);
-       wait_for_completion(&event);
-       DEBUG(3, "submit_bio completed, bi_vcnt = %d\n", bio->bi_vcnt);
-       err = test_bit(BIO_UPTODATE, &bio->bi_flags) ? 0 : -EIO;
-       bio_put(bio);
-       return err;
-}
-
-
-/**
- * blkmtd_add_page - add a page to the current BIO
- * @bio: bio to add to (NULL to alloc initial bio)
- * @blkdev: block device
- * @page: page to add
- * @pagecnt: pages left to add
- *
- * Adds a page to the current bio, allocating it if necessary. If it cannot be
- * added, the current bio is written out and a new one is allocated. Returns
- * the new bio to add or NULL on error
- */
-static struct bio *blkmtd_add_page(struct bio *bio, struct block_device *blkdev,
-                                  struct page *page, int pagecnt)
-{
-
- retry:
-       if(!bio) {
-               bio = bio_alloc(GFP_KERNEL, pagecnt);
-               if(!bio)
-                       return NULL;
-               bio->bi_sector = page->index << (PAGE_SHIFT-9);
-               bio->bi_bdev = blkdev;
-       }
-
-       if(bio_add_page(bio, page, PAGE_SIZE, 0) != PAGE_SIZE) {
-               blkmtd_write_out(bio);
-               bio = NULL;
-               goto retry;
-       }
-       return bio;
-}
-
-
-/**
- * write_pages - write block of data to device via the page cache
- * @dev: device to write to
- * @buf: data source or NULL if erase (output is set to 0xff)
- * @to: offset into output device
- * @len: amount to data to write
- * @retlen: amount of data written
- *
- * Grab pages from the page cache and fill them with the source data.
- * Non page aligned start and end result in a readin of the page and
- * part of the page being modified. Pages are added to the bio and then written
- * out.
- */
-static int write_pages(struct blkmtd_dev *dev, const u_char *buf, loff_t to,
-                   size_t len, size_t *retlen)
-{
-       int pagenr, offset;
-       size_t start_len = 0, end_len;
-       int pagecnt = 0;
-       int err = 0;
-       struct bio *bio = NULL;
-       size_t thislen = 0;
-
-       pagenr = to >> PAGE_SHIFT;
-       offset = to & ~PAGE_MASK;
-
-       DEBUG(2, "blkmtd: write_pages: buf = %p to = %ld len = %zd pagenr = %d offset = %d\n",
-             buf, (long)to, len, pagenr, offset);
-
-       /* see if we have to do a partial write at the start */
-       if(offset) {
-               start_len = ((offset + len) > PAGE_SIZE) ? PAGE_SIZE - offset : len;
-               len -= start_len;
-       }
-
-       /* calculate the length of the other two regions */
-       end_len = len & ~PAGE_MASK;
-       len -= end_len;
-
-       if(start_len)
-               pagecnt++;
-
-       if(len)
-               pagecnt += len >> PAGE_SHIFT;
-
-       if(end_len)
-               pagecnt++;
-
-       mutex_lock(&dev->wrbuf_mutex);
-
-       DEBUG(3, "blkmtd: write: start_len = %zd len = %zd end_len = %zd pagecnt = %d\n",
-             start_len, len, end_len, pagecnt);
-
-       if(start_len) {
-               /* do partial start region */
-               struct page *page;
-
-               DEBUG(3, "blkmtd: write: doing partial start, page = %d len = %zd offset = %d\n",
-                     pagenr, start_len, offset);
-
-               BUG_ON(!buf);
-               page = read_cache_page(dev->blkdev->bd_inode->i_mapping, pagenr, (filler_t *)blkmtd_readpage, dev);
-               lock_page(page);
-               if(PageDirty(page)) {
-                       err("to = %lld start_len = %zd len = %zd end_len = %zd pagenr = %d\n",
-                           to, start_len, len, end_len, pagenr);
-                       BUG();
-               }
-               memcpy(page_address(page)+offset, buf, start_len);
-               set_page_dirty(page);
-               SetPageUptodate(page);
-               buf += start_len;
-               thislen = start_len;
-               bio = blkmtd_add_page(bio, dev->blkdev, page, pagecnt);
-               if(!bio) {
-                       err = -ENOMEM;
-                       err("bio_add_page failed\n");
-                       goto write_err;
-               }
-               pagecnt--;
-               pagenr++;
-       }
-
-       /* Now do the main loop to a page aligned, n page sized output */
-       if(len) {
-               int pagesc = len >> PAGE_SHIFT;
-               DEBUG(3, "blkmtd: write: whole pages start = %d, count = %d\n",
-                     pagenr, pagesc);
-               while(pagesc) {
-                       struct page *page;
-
-                       /* see if page is in the page cache */
-                       DEBUG(3, "blkmtd: write: grabbing page %d from page cache\n", pagenr);
-                       page = grab_cache_page(dev->blkdev->bd_inode->i_mapping, pagenr);
-                       if(PageDirty(page)) {
-                               BUG();
-                       }
-                       if(!page) {
-                               warn("write: cannot grab cache page %d", pagenr);
-                               err = -ENOMEM;
-                               goto write_err;
-                       }
-                       if(!buf) {
-                               memset(page_address(page), 0xff, PAGE_SIZE);
-                       } else {
-                               memcpy(page_address(page), buf, PAGE_SIZE);
-                               buf += PAGE_SIZE;
-                       }
-                       bio = blkmtd_add_page(bio, dev->blkdev, page, pagecnt);
-                       if(!bio) {
-                               err = -ENOMEM;
-                               err("bio_add_page failed\n");
-                               goto write_err;
-                       }
-                       pagenr++;
-                       pagecnt--;
-                       set_page_dirty(page);
-                       SetPageUptodate(page);
-                       pagesc--;
-                       thislen += PAGE_SIZE;
-               }
-       }
-
-       if(end_len) {
-               /* do the third region */
-               struct page *page;
-               DEBUG(3, "blkmtd: write: doing partial end, page = %d len = %zd\n",
-                     pagenr, end_len);
-               BUG_ON(!buf);
-               page = read_cache_page(dev->blkdev->bd_inode->i_mapping, pagenr, (filler_t *)blkmtd_readpage, dev);
-               lock_page(page);
-               if(PageDirty(page)) {
-                       err("to = %lld start_len = %zd len = %zd end_len = %zd pagenr = %d\n",
-                           to, start_len, len, end_len, pagenr);
-                       BUG();
-               }
-               memcpy(page_address(page), buf, end_len);
-               set_page_dirty(page);
-               SetPageUptodate(page);
-               DEBUG(3, "blkmtd: write: writing out partial end\n");
-               thislen += end_len;
-               bio = blkmtd_add_page(bio, dev->blkdev, page, pagecnt);
-               if(!bio) {
-                       err = -ENOMEM;
-                       err("bio_add_page failed\n");
-                       goto write_err;
-               }
-               pagenr++;
-       }
-
-       DEBUG(3, "blkmtd: write: got %d vectors to write\n", bio->bi_vcnt);
- write_err:
-       if(bio)
-               blkmtd_write_out(bio);
-
-       DEBUG(2, "blkmtd: write: end, retlen = %zd, err = %d\n", *retlen, err);
-       mutex_unlock(&dev->wrbuf_mutex);
-
-       if(retlen)
-               *retlen = thislen;
-       return err;
-}
-
-
-/* erase a specified part of the device */
-static int blkmtd_erase(struct mtd_info *mtd, struct erase_info *instr)
-{
-       struct blkmtd_dev *dev = mtd->priv;
-       struct mtd_erase_region_info *einfo = mtd->eraseregions;
-       int numregions = mtd->numeraseregions;
-       size_t from;
-       u_long len;
-       int err = -EIO;
-       size_t retlen;
-
-       instr->state = MTD_ERASING;
-       from = instr->addr;
-       len = instr->len;
-
-       /* check erase region has valid start and length */
-       DEBUG(2, "blkmtd: erase: dev = `%s' from = 0x%zx len = 0x%lx\n",
-             mtd->name+9, from, len);
-       while(numregions) {
-               DEBUG(3, "blkmtd: checking erase region = 0x%08X size = 0x%X num = 0x%x\n",
-                     einfo->offset, einfo->erasesize, einfo->numblocks);
-               if(from >= einfo->offset
-                  && from < einfo->offset + (einfo->erasesize * einfo->numblocks)) {
-                       if(len == einfo->erasesize
-                          && ( (from - einfo->offset) % einfo->erasesize == 0))
-                               break;
-               }
-               numregions--;
-               einfo++;
-       }
-
-       if(!numregions) {
-               /* Not a valid erase block */
-               err("erase: invalid erase request 0x%lX @ 0x%08zX", len, from);
-               instr->state = MTD_ERASE_FAILED;
-               err = -EIO;
-       }
-
-       if(instr->state != MTD_ERASE_FAILED) {
-               /* do the erase */
-               DEBUG(3, "Doing erase from = %zd len = %ld\n", from, len);
-               err = write_pages(dev, NULL, from, len, &retlen);
-               if(err || retlen != len) {
-                       err("erase failed err = %d", err);
-                       instr->state = MTD_ERASE_FAILED;
-               } else {
-                       instr->state = MTD_ERASE_DONE;
-               }
-       }
-
-       DEBUG(3, "blkmtd: erase: checking callback\n");
-       mtd_erase_callback(instr);
-       DEBUG(2, "blkmtd: erase: finished (err = %d)\n", err);
-       return err;
-}
-
-
-/* read a range of the data via the page cache */
-static int blkmtd_read(struct mtd_info *mtd, loff_t from, size_t len,
-                      size_t *retlen, u_char *buf)
-{
-       struct blkmtd_dev *dev = mtd->priv;
-       int err = 0;
-       int offset;
-       int pagenr, pages;
-       size_t thislen = 0;
-
-       DEBUG(2, "blkmtd: read: dev = `%s' from = %lld len = %zd buf = %p\n",
-             mtd->name+9, from, len, buf);
-
-       if(from > mtd->size)
-               return -EINVAL;
-       if(from + len > mtd->size)
-               len = mtd->size - from;
-
-       pagenr = from >> PAGE_SHIFT;
-       offset = from - (pagenr << PAGE_SHIFT);
-
-       pages = (offset+len+PAGE_SIZE-1) >> PAGE_SHIFT;
-       DEBUG(3, "blkmtd: read: pagenr = %d offset = %d, pages = %d\n",
-             pagenr, offset, pages);
-
-       while(pages) {
-               struct page *page;
-               int cpylen;
-
-               DEBUG(3, "blkmtd: read: looking for page: %d\n", pagenr);
-               page = read_cache_page(dev->blkdev->bd_inode->i_mapping, pagenr, (filler_t *)blkmtd_readpage, dev);
-               if(IS_ERR(page)) {
-                       err = -EIO;
-                       goto readerr;
-               }
-
-               cpylen = (PAGE_SIZE > len) ? len : PAGE_SIZE;
-               if(offset+cpylen > PAGE_SIZE)
-                       cpylen = PAGE_SIZE-offset;
-
-               memcpy(buf + thislen, page_address(page) + offset, cpylen);
-               offset = 0;
-               len -= cpylen;
-               thislen += cpylen;
-               pagenr++;
-               pages--;
-               if(!PageDirty(page))
-                       page_cache_release(page);
-       }
-
- readerr:
-       if(retlen)
-               *retlen = thislen;
-       DEBUG(2, "blkmtd: end read: retlen = %zd, err = %d\n", thislen, err);
-       return err;
-}
-
-
-/* write data to the underlying device */
-static int blkmtd_write(struct mtd_info *mtd, loff_t to, size_t len,
-                       size_t *retlen, const u_char *buf)
-{
-       struct blkmtd_dev *dev = mtd->priv;
-       int err;
-
-       if(!len)
-               return 0;
-
-       DEBUG(2, "blkmtd: write: dev = `%s' to = %lld len = %zd buf = %p\n",
-             mtd->name+9, to, len, buf);
-
-       if(to >= mtd->size) {
-               return -ENOSPC;
-       }
-
-       if(to + len > mtd->size) {
-               len = mtd->size - to;
-       }
-
-       err = write_pages(dev, buf, to, len, retlen);
-       if(err > 0)
-               err = 0;
-       DEBUG(2, "blkmtd: write: end, err = %d\n", err);
-       return err;
-}
-
-
-/* sync the device - wait until the write queue is empty */
-static void blkmtd_sync(struct mtd_info *mtd)
-{
-       /* Currently all writes are synchronous */
-}
-
-
-static void free_device(struct blkmtd_dev *dev)
-{
-       DEBUG(2, "blkmtd: free_device() dev = %p\n", dev);
-       if(dev) {
-               kfree(dev->mtd_info.eraseregions);
-               kfree(dev->mtd_info.name);
-               if(dev->blkdev) {
-                       invalidate_inode_pages(dev->blkdev->bd_inode->i_mapping);
-                       close_bdev_excl(dev->blkdev);
-               }
-               kfree(dev);
-       }
-}
-
-
-/* For a given size and initial erase size, calculate the number
- * and size of each erase region. Goes round the loop twice,
- * once to find out how many regions, then allocates space,
- * then round the loop again to fill it in.
- */
-static struct mtd_erase_region_info *calc_erase_regions(
-       size_t erase_size, size_t total_size, int *regions)
-{
-       struct mtd_erase_region_info *info = NULL;
-
-       DEBUG(2, "calc_erase_regions, es = %zd size = %zd regions = %d\n",
-             erase_size, total_size, *regions);
-       /* Make any user specified erasesize be a power of 2
-          and at least PAGE_SIZE */
-       if(erase_size) {
-               int es = erase_size;
-               erase_size = 1;
-               while(es != 1) {
-                       es >>= 1;
-                       erase_size <<= 1;
-               }
-               if(erase_size < PAGE_SIZE)
-                       erase_size = PAGE_SIZE;
-       } else {
-               erase_size = CONFIG_MTD_BLKDEV_ERASESIZE;
-       }
-
-       *regions = 0;
-
-       do {
-               int tot_size = total_size;
-               int er_size = erase_size;
-               int count = 0, offset = 0, regcnt = 0;
-
-               while(tot_size) {
-                       count = tot_size / er_size;
-                       if(count) {
-                               tot_size = tot_size % er_size;
-                               if(info) {
-                                       DEBUG(2, "adding to erase info off=%d er=%d cnt=%d\n",
-                                             offset, er_size, count);
-                                       (info+regcnt)->offset = offset;
-                                       (info+regcnt)->erasesize = er_size;
-                                       (info+regcnt)->numblocks = count;
-                                       (*regions)++;
-                               }
-                               regcnt++;
-                               offset += (count * er_size);
-                       }
-                       while(er_size > tot_size)
-                               er_size >>= 1;
-               }
-               if(info == NULL) {
-                       info = kmalloc(regcnt * sizeof(struct mtd_erase_region_info), GFP_KERNEL);
-                       if(!info)
-                               break;
-               }
-       } while(!(*regions));
-       DEBUG(2, "calc_erase_regions done, es = %zd size = %zd regions = %d\n",
-             erase_size, total_size, *regions);
-       return info;
-}
-
-
-static struct blkmtd_dev *add_device(char *devname, int readonly, int erase_size)
-{
-       struct block_device *bdev;
-       int mode;
-       struct blkmtd_dev *dev;
-
-       if(!devname)
-               return NULL;
-
-       /* Get a handle on the device */
-
-
-#ifdef MODULE
-       mode = (readonly) ? O_RDONLY : O_RDWR;
-       bdev = open_bdev_excl(devname, mode, NULL);
-#else
-       mode = (readonly) ? FMODE_READ : FMODE_WRITE;
-       bdev = open_by_devnum(name_to_dev_t(devname), mode);
-#endif
-       if(IS_ERR(bdev)) {
-               err("error: cannot open device %s", devname);
-               DEBUG(2, "blkmtd: opening bdev returned %ld\n", PTR_ERR(bdev));
-               return NULL;
-       }
-
-       DEBUG(1, "blkmtd: found a block device major = %d, minor = %d\n",
-             MAJOR(bdev->bd_dev), MINOR(bdev->bd_dev));
-
-       if(MAJOR(bdev->bd_dev) == MTD_BLOCK_MAJOR) {
-               err("attempting to use an MTD device as a block device");
-               blkdev_put(bdev);
-               return NULL;
-       }
-
-       dev = kmalloc(sizeof(struct blkmtd_dev), GFP_KERNEL);
-       if(dev == NULL) {
-               blkdev_put(bdev);
-               return NULL;
-       }
-
-       memset(dev, 0, sizeof(struct blkmtd_dev));
-       dev->blkdev = bdev;
-       if(!readonly) {
-               mutex_init(&dev->wrbuf_mutex);
-       }
-
-       dev->mtd_info.size = dev->blkdev->bd_inode->i_size & PAGE_MASK;
-
-       /* Setup the MTD structure */
-       /* make the name contain the block device in */
-       dev->mtd_info.name = kmalloc(sizeof("blkmtd: ") + strlen(devname), GFP_KERNEL);
-       if(dev->mtd_info.name == NULL)
-               goto devinit_err;
-
-       sprintf(dev->mtd_info.name, "blkmtd: %s", devname);
-       dev->mtd_info.eraseregions = calc_erase_regions(erase_size, dev->mtd_info.size,
-                                                       &dev->mtd_info.numeraseregions);
-       if(dev->mtd_info.eraseregions == NULL)
-               goto devinit_err;
-
-       dev->mtd_info.erasesize = dev->mtd_info.eraseregions->erasesize;
-       DEBUG(1, "blkmtd: init: found %d erase regions\n",
-             dev->mtd_info.numeraseregions);
-
-       if(readonly) {
-               dev->mtd_info.type = MTD_ROM;
-               dev->mtd_info.flags = MTD_CAP_ROM;
-       } else {
-               dev->mtd_info.type = MTD_RAM;
-               dev->mtd_info.flags = MTD_CAP_RAM;
-               dev->mtd_info.erase = blkmtd_erase;
-               dev->mtd_info.write = blkmtd_write;
-               dev->mtd_info.writev = default_mtd_writev;
-               dev->mtd_info.sync = blkmtd_sync;
-       }
-       dev->mtd_info.read = blkmtd_read;
-       dev->mtd_info.readv = default_mtd_readv;
-       dev->mtd_info.priv = dev;
-       dev->mtd_info.owner = THIS_MODULE;
-
-       list_add(&dev->list, &blkmtd_device_list);
-       if (add_mtd_device(&dev->mtd_info)) {
-               /* Device didnt get added, so free the entry */
-               list_del(&dev->list);
-               goto devinit_err;
-       } else {
-               info("mtd%d: [%s] erase_size = %dKiB %s",
-                    dev->mtd_info.index, dev->mtd_info.name + strlen("blkmtd: "),
-                    dev->mtd_info.erasesize >> 10,
-                    readonly ? "(read-only)" : "");
-       }
-
-       return dev;
-
- devinit_err:
-       free_device(dev);
-       return NULL;
-}
-
-
-/* Cleanup and exit - sync the device and kill of the kernel thread */
-static void __devexit cleanup_blkmtd(void)
-{
-       struct list_head *temp1, *temp2;
-
-       /* Remove the MTD devices */
-       list_for_each_safe(temp1, temp2, &blkmtd_device_list) {
-               struct blkmtd_dev *dev = list_entry(temp1, struct blkmtd_dev,
-                                                   list);
-               blkmtd_sync(&dev->mtd_info);
-               del_mtd_device(&dev->mtd_info);
-               info("mtd%d: [%s] removed", dev->mtd_info.index,
-                    dev->mtd_info.name + strlen("blkmtd: "));
-               list_del(&dev->list);
-               free_device(dev);
-       }
-}
-
-#ifndef MODULE
-
-/* Handle kernel boot params */
-
-
-static int __init param_blkmtd_device(char *str)
-{
-       int i;
-
-       for(i = 0; i < MAX_DEVICES; i++) {
-               device[i] = str;
-               DEBUG(2, "blkmtd: device setup: %d = %s\n", i, device[i]);
-               strsep(&str, ",");
-       }
-       return 1;
-}
-
-
-static int __init param_blkmtd_erasesz(char *str)
-{
-       int i;
-       for(i = 0; i < MAX_DEVICES; i++) {
-               char *val = strsep(&str, ",");
-               if(val)
-                       erasesz[i] = simple_strtoul(val, NULL, 0);
-               DEBUG(2, "blkmtd: erasesz setup: %d = %d\n", i, erasesz[i]);
-       }
-
-       return 1;
-}
-
-
-static int __init param_blkmtd_ro(char *str)
-{
-       int i;
-       for(i = 0; i < MAX_DEVICES; i++) {
-               char *val = strsep(&str, ",");
-               if(val)
-                       ro[i] = simple_strtoul(val, NULL, 0);
-               DEBUG(2, "blkmtd: ro setup: %d = %d\n", i, ro[i]);
-       }
-
-       return 1;
-}
-
-
-static int __init param_blkmtd_sync(char *str)
-{
-       if(str[0] == '1')
-               sync = 1;
-       return 1;
-}
-
-__setup("blkmtd_device=", param_blkmtd_device);
-__setup("blkmtd_erasesz=", param_blkmtd_erasesz);
-__setup("blkmtd_ro=", param_blkmtd_ro);
-__setup("blkmtd_sync=", param_blkmtd_sync);
-
-#endif
-
-
-/* Startup */
-static int __init init_blkmtd(void)
-{
-       int i;
-
-       info("version " VERSION);
-       /* Check args - device[0] is the bare minimum*/
-       if(!device[0]) {
-               err("error: missing `device' name\n");
-               return -EINVAL;
-       }
-
-       for(i = 0; i < MAX_DEVICES; i++)
-               add_device(device[i], ro[i], erasesz[i] << 10);
-
-       if(list_empty(&blkmtd_device_list))
-               return -EINVAL;
-
-       return 0;
-}
-
-module_init(init_blkmtd);
-module_exit(cleanup_blkmtd);
index c4e12b5cbb92c2f4cb2412e7ece8d22151c902df..3d306681919e12bdc923ae95c1e282faa724dbad 100644 (file)
@@ -2,6 +2,7 @@
  *
  * Copyright (C) 2002 David S. Miller (davem@redhat.com)
  * Fixed by Pekka Pietikainen (pp@ee.oulu.fi)
+ * Copyright (C) 2006 Broadcom Corporation.
  *
  * Distribute under GPL.
  */
@@ -28,8 +29,8 @@
 
 #define DRV_MODULE_NAME                "b44"
 #define PFX DRV_MODULE_NAME    ": "
-#define DRV_MODULE_VERSION     "0.97"
-#define DRV_MODULE_RELDATE     "Nov 30, 2005"
+#define DRV_MODULE_VERSION     "1.00"
+#define DRV_MODULE_RELDATE     "Apr 7, 2006"
 
 #define B44_DEF_MSG_ENABLE       \
        (NETIF_MSG_DRV          | \
@@ -136,7 +137,7 @@ static inline unsigned long br32(const struct b44 *bp, unsigned long reg)
        return readl(bp->regs + reg);
 }
 
-static inline void bw32(const struct b44 *bp, 
+static inline void bw32(const struct b44 *bp,
                        unsigned long reg, unsigned long val)
 {
        writel(val, bp->regs + reg);
@@ -286,13 +287,13 @@ static void __b44_cam_write(struct b44 *bp, unsigned char *data, int index)
        val |= ((u32) data[4]) <<  8;
        val |= ((u32) data[5]) <<  0;
        bw32(bp, B44_CAM_DATA_LO, val);
-       val = (CAM_DATA_HI_VALID | 
+       val = (CAM_DATA_HI_VALID |
               (((u32) data[0]) << 8) |
               (((u32) data[1]) << 0));
        bw32(bp, B44_CAM_DATA_HI, val);
        bw32(bp, B44_CAM_CTRL, (CAM_CTRL_WRITE |
                            (index << CAM_CTRL_INDEX_SHIFT)));
-       b44_wait_bit(bp, B44_CAM_CTRL, CAM_CTRL_BUSY, 100, 1);  
+       b44_wait_bit(bp, B44_CAM_CTRL, CAM_CTRL_BUSY, 100, 1);
 }
 
 static inline void __b44_disable_ints(struct b44 *bp)
@@ -410,25 +411,18 @@ static void __b44_set_flow_ctrl(struct b44 *bp, u32 pause_flags)
 
 static void b44_set_flow_ctrl(struct b44 *bp, u32 local, u32 remote)
 {
-       u32 pause_enab = bp->flags & (B44_FLAG_TX_PAUSE |
-                                     B44_FLAG_RX_PAUSE);
+       u32 pause_enab = 0;
 
-       if (local & ADVERTISE_PAUSE_CAP) {
-               if (local & ADVERTISE_PAUSE_ASYM) {
-                       if (remote & LPA_PAUSE_CAP)
-                               pause_enab |= (B44_FLAG_TX_PAUSE |
-                                              B44_FLAG_RX_PAUSE);
-                       else if (remote & LPA_PAUSE_ASYM)
-                               pause_enab |= B44_FLAG_RX_PAUSE;
-               } else {
-                       if (remote & LPA_PAUSE_CAP)
-                               pause_enab |= (B44_FLAG_TX_PAUSE |
-                                              B44_FLAG_RX_PAUSE);
-               }
-       } else if (local & ADVERTISE_PAUSE_ASYM) {
-               if ((remote & LPA_PAUSE_CAP) &&
-                   (remote & LPA_PAUSE_ASYM))
-                       pause_enab |= B44_FLAG_TX_PAUSE;
+       /* The driver supports only rx pause by default because
+          the b44 mac tx pause mechanism generates excessive
+          pause frames.
+          Use ethtool to turn on b44 tx pause if necessary.
+        */
+       if ((local & ADVERTISE_PAUSE_CAP) &&
+           (local & ADVERTISE_PAUSE_ASYM)){
+               if ((remote & LPA_PAUSE_ASYM) &&
+                   !(remote & LPA_PAUSE_CAP))
+                       pause_enab |= B44_FLAG_RX_PAUSE;
        }
 
        __b44_set_flow_ctrl(bp, pause_enab);
@@ -1063,7 +1057,7 @@ static int b44_change_mtu(struct net_device *dev, int new_mtu)
        spin_unlock_irq(&bp->lock);
 
        b44_enable_ints(bp);
-       
+
        return 0;
 }
 
@@ -1381,7 +1375,7 @@ static void b44_init_hw(struct b44 *bp)
        bw32(bp, B44_DMARX_ADDR, bp->rx_ring_dma + bp->dma_offset);
 
        bw32(bp, B44_DMARX_PTR, bp->rx_pending);
-       bp->rx_prod = bp->rx_pending;   
+       bp->rx_prod = bp->rx_pending;
 
        bw32(bp, B44_MIB_CTRL, MIB_CTRL_CLR_ON_READ);
 
@@ -1553,9 +1547,9 @@ static void __b44_set_rx_mode(struct net_device *dev)
                        val |= RXCONFIG_ALLMULTI;
                else
                        i = __b44_load_mcast(bp, dev);
-               
+
                for (; i < 64; i++) {
-                       __b44_cam_write(bp, zero, i);                   
+                       __b44_cam_write(bp, zero, i);
                }
                bw32(bp, B44_RXCONFIG, val);
                val = br32(bp, B44_CAM_CTRL);
@@ -1737,7 +1731,7 @@ static int b44_set_ringparam(struct net_device *dev,
        spin_unlock_irq(&bp->lock);
 
        b44_enable_ints(bp);
-       
+
        return 0;
 }
 
@@ -1782,7 +1776,7 @@ static int b44_set_pauseparam(struct net_device *dev,
        spin_unlock_irq(&bp->lock);
 
        b44_enable_ints(bp);
-       
+
        return 0;
 }
 
@@ -1898,7 +1892,7 @@ static int __devinit b44_get_invariants(struct b44 *bp)
        bp->core_unit = ssb_core_unit(bp);
        bp->dma_offset = SB_PCI_DMA;
 
-       /* XXX - really required? 
+       /* XXX - really required?
           bp->flags |= B44_FLAG_BUGGY_TXPTR;
          */
 out:
@@ -1946,7 +1940,7 @@ static int __devinit b44_init_one(struct pci_dev *pdev,
                       "aborting.\n");
                goto err_out_free_res;
        }
-       
+
        err = pci_set_consistent_dma_mask(pdev, (u64) B44_DMA_MASK);
        if (err) {
                printk(KERN_ERR PFX "No usable DMA configuration, "
@@ -2041,9 +2035,9 @@ static int __devinit b44_init_one(struct pci_dev *pdev,
 
        pci_save_state(bp->pdev);
 
-       /* Chip reset provides power to the b44 MAC & PCI cores, which 
+       /* Chip reset provides power to the b44 MAC & PCI cores, which
         * is necessary for MAC register access.
-        */ 
+        */
        b44_chip_reset(bp);
 
        printk(KERN_INFO "%s: Broadcom 4400 10/100BaseT Ethernet ", dev->name);
@@ -2091,10 +2085,10 @@ static int b44_suspend(struct pci_dev *pdev, pm_message_t state)
 
        del_timer_sync(&bp->timer);
 
-       spin_lock_irq(&bp->lock); 
+       spin_lock_irq(&bp->lock);
 
        b44_halt(bp);
-       netif_carrier_off(bp->dev); 
+       netif_carrier_off(bp->dev);
        netif_device_detach(bp->dev);
        b44_free_rings(bp);
 
index 2671da20a49673d3d44c2774ae930dc0927db09e..5ca99e26660af7f9b32f873e06bd3efd9ea4a313 100644 (file)
@@ -63,7 +63,7 @@
 /* Time in jiffies before concluding the transmitter is hung. */
 #define TX_TIMEOUT  (5*HZ)
 
-static char version[] __devinitdata =
+static const char version[] __devinitdata =
        "Broadcom NetXtreme II Gigabit Ethernet Driver " DRV_MODULE_NAME " v" DRV_MODULE_VERSION " (" DRV_MODULE_RELDATE ")\n";
 
 MODULE_AUTHOR("Michael Chan <mchan@broadcom.com>");
index 91e927827c433b1ac7b3c8d5188fca12a35389d6..54c78d94f48bea75ba0eb68d8279085f8a973e72 100644 (file)
@@ -4,7 +4,7 @@
 
 obj-$(CONFIG_CHELSIO_T1) += cxgb.o
 
-EXTRA_CFLAGS += -I$(TOPDIR)/drivers/net/chelsio $(DEBUG_FLAGS)
+EXTRA_CFLAGS += -Idrivers/net/chelsio $(DEBUG_FLAGS)
 
 
 cxgb-objs := cxgb2.o espi.o pm3393.o sge.o subr.o mv88x201x.o
diff --git a/drivers/net/hydra.h b/drivers/net/hydra.h
deleted file mode 100644 (file)
index 3741414..0000000
+++ /dev/null
@@ -1,177 +0,0 @@
-/*     $Linux: hydra.h,v 1.0 1994/10/26 02:03:47 cgd Exp $     */
-
-/*
- * Copyright (c) 1994 Timo Rossi
- * All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- * 1. Redistributions of source code must retain the above copyright
- *    notice, this list of conditions and the following disclaimer.
- * 2. Redistributions in binary form must reproduce the above copyright
- *    notice, this list of conditions and the following disclaimer in the
- *    documentation and/or other materials provided with the distribution.
- * 3. All advertising materials mentioning features or use of this software
- *    must display the following acknowledgement:
- *      This product includes software developed by  Timo Rossi
- * 4. The name of the author may not be used to endorse or promote products
- *    derived from this software without specific prior written permission
- *
- * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``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 AUTHOR 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.
- */
-
-/*
- * The Hydra Systems card uses the National Semiconductor
- * 8390 NIC (Network Interface Controller) chip, located
- * at card base address + 0xffe1. NIC registers are accessible
- * only at odd byte addresses, so the register offsets must
- * be multiplied by two.
- *
- * Card address PROM is located at card base + 0xffc0 (even byte addresses)
- *
- * RAM starts at the card base address, and is 16K or 64K.
- * The current Amiga NetBSD hydra driver is hardwired for 16K.
- * It seems that the RAM should be accessed as words or longwords only.
- *
- */
-
-/* adapted for Linux by Topi Kanerva 03/29/95
-   with original author's permission          */
-
-#define HYDRA_NIC_BASE 0xffe1
-
-/* Page0 registers */
-
-#define NIC_CR     0       /* Command register   */
-#define NIC_PSTART (1*2)   /* Page start (write) */
-#define NIC_PSTOP  (2*2)   /* Page stop (write)  */
-#define NIC_BNDRY  (3*2)   /* Boundary pointer   */
-#define NIC_TSR    (4*2)   /* Transmit status (read) */
-#define NIC_TPSR   (4*2)   /* Transmit page start (write) */
-#define NIC_NCR    (5*2)   /* Number of collisions, read  */
-#define NIC_TBCR0  (5*2)   /* Transmit byte count low (write)  */
-#define NIC_FIFO   (6*2)   /* FIFO reg. (read)   */
-#define NIC_TBCR1  (6*2)   /* Transmit byte count high (write) */
-#define NIC_ISR    (7*2)   /* Interrupt status register */
-#define NIC_RBCR0  (0xa*2) /* Remote byte count low (write)  */
-#define NIC_RBCR1  (0xb*2) /* Remote byte count high (write) */
-#define NIC_RSR    (0xc*2) /* Receive status (read)  */
-#define NIC_RCR    (0xc*2) /* Receive config (write) */
-#define NIC_CNTR0  (0xd*2) /* Frame alignment error count (read) */
-#define NIC_TCR    (0xd*2) /* Transmit config (write)  */
-#define NIC_CNTR1  (0xe*2) /* CRC error counter (read) */
-#define NIC_DCR    (0xe*2) /* Data config (write) */
-#define NIC_CNTR2  (0xf*2) /* missed packet counter (read) */
-#define NIC_IMR    (0xf*2) /* Interrupt mask reg. (write)  */
-
-/* Page1 registers */
-
-#define NIC_PAR0   (1*2)   /* Physical address */
-#define NIC_PAR1   (2*2)
-#define NIC_PAR2   (3*2)
-#define NIC_PAR3   (4*2)
-#define NIC_PAR4   (5*2)
-#define NIC_PAR5   (6*2)
-#define NIC_CURR   (7*2)   /* Current RX ring-buffer page */
-#define NIC_MAR0   (8*2)   /* Multicast address */
-#define NIC_MAR1   (9*2)
-#define NIC_MAR2   (0xa*2)
-#define NIC_MAR3   (0xb*2)
-#define NIC_MAR4   (0xc*2)
-#define NIC_MAR5   (0xd*2)
-#define NIC_MAR6   (0xe*2)
-#define NIC_MAR7   (0xf*2)
-
-/* Command register definitions */
-
-#define CR_STOP   0x01 /* Stop -- software reset command */
-#define CR_START  0x02 /* Start */
-#define CR_TXP   0x04 /* Transmit packet */
-
-#define CR_RD0    0x08 /* Remote DMA cmd */
-#define CR_RD1    0x10
-#define CR_RD2    0x20
-
-#define CR_NODMA  CR_RD2
-
-#define CR_PS0    0x40 /* Page select */
-#define CR_PS1    0x80
-
-#define CR_PAGE0  0
-#define CR_PAGE1  CR_PS0
-#define CR_PAGE2  CR_PS1
-
-/* Interrupt status reg. definitions */
-
-#define ISR_PRX   0x01 /* Packet received without errors */
-#define ISR_PTX   0x02 /* Packet transmitted without errors */
-#define ISR_RXE   0x04 /* Receive error  */
-#define ISR_TXE   0x08 /* Transmit error */
-#define ISR_OVW   0x10 /* Ring buffer overrun */
-#define ISR_CNT   0x20 /* Counter overflow    */
-#define ISR_RDC   0x40 /* Remote DMA compile */
-#define ISR_RST   0x80 /* Reset status      */
-
-/* Data config reg. definitions */
-
-#define DCR_WTS   0x01 /* Word transfer select  */
-#define DCR_BOS   0x02 /* Byte order select     */
-#define DCR_LAS   0x04 /* Long address select   */
-#define DCR_LS    0x08 /* Loopback select       */
-#define DCR_AR    0x10 /* Auto-init remote      */
-#define DCR_FT0   0x20 /* FIFO threshold select */
-#define DCR_FT1   0x40
-
-/* Transmit config reg. definitions */
-
-#define TCR_CRC  0x01 /* Inhibit CRC */
-#define TCR_LB0  0x02 /* Loopback control */
-#define TCR_LB1  0x04
-#define TCR_ATD  0x08 /* Auto transmit disable */
-#define TCR_OFST 0x10 /* Collision offset enable */
-
-/* Transmit status reg. definitions */
-
-#define TSR_PTX  0x01 /* Packet transmitted */
-#define TSR_COL  0x04 /* Transmit collided */
-#define TSR_ABT  0x08 /* Transmit aborted */
-#define TSR_CRS  0x10 /* Carrier sense lost */
-#define TSR_FU   0x20 /* FIFO underrun */
-#define TSR_CDH  0x40 /* CD Heartbeat */
-#define TSR_OWC  0x80 /* Out of Window Collision */
-
-/* Receiver config register definitions */
-
-#define RCR_SEP  0x01 /* Save errored packets */
-#define RCR_AR   0x02 /* Accept runt packets */
-#define RCR_AB   0x04 /* Accept broadcast */
-#define RCR_AM   0x08 /* Accept multicast */
-#define RCR_PRO  0x10 /* Promiscuous mode */
-#define RCR_MON  0x20 /* Monitor mode */
-
-/* Receiver status register definitions */
-
-#define RSR_PRX  0x01 /* Packet received without error */
-#define RSR_CRC  0x02 /* CRC error */
-#define RSR_FAE  0x04 /* Frame alignment error */
-#define RSR_FO   0x08 /* FIFO overrun */
-#define RSR_MPA  0x10 /* Missed packet */
-#define RSR_PHY  0x20 /* Physical address */
-#define RSR_DIS  0x40 /* Received disabled */
-#define RSR_DFR  0x80 /* Deferring (jabber) */
-
-/* Hydra System card address PROM offset */
-
-#define HYDRA_ADDRPROM 0xffc0
-
-
index 6e2ec56cde0b1042d4c5b65289295abeca74a4a8..96bdb73c2283bb3cbcd8bcdc964062f660b5f15d 100644 (file)
@@ -1,7 +1,7 @@
 /*****************************************************************************
  *
  * Filename:      irda-usb.c
- * Version:       0.9b
+ * Version:       0.10
  * Description:   IrDA-USB Driver
  * Status:        Experimental 
  * Author:        Dag Brattli <dag@brattli.net>
@@ -9,6 +9,9 @@
  *     Copyright (C) 2000, Roman Weissgaerber <weissg@vienna.at>
  *      Copyright (C) 2001, Dag Brattli <dag@brattli.net>
  *      Copyright (C) 2001, Jean Tourrilhes <jt@hpl.hp.com>
+ *      Copyright (C) 2004, SigmaTel, Inc. <irquality@sigmatel.com>
+ *      Copyright (C) 2005, Milan Beno <beno@pobox.sk>
+ *      Copyright (C) 2006, Nick Fedchik <nick@fedchik.org.ua>
  *          
  *     This program is free software; you can redistribute it and/or modify
  *     it under the terms of the GNU General Public License as published by
@@ -61,6 +64,7 @@
 #include <linux/slab.h>
 #include <linux/rtnetlink.h>
 #include <linux/usb.h>
+#include <linux/firmware.h>
 
 #include "irda-usb.h"
 
@@ -78,8 +82,12 @@ static struct usb_device_id dongles[] = {
        { USB_DEVICE(0x50f, 0x180), .driver_info = IUC_SPEED_BUG | IUC_NO_WINDOW },
        /* Extended Systems, Inc.,  XTNDAccess IrDA USB (ESI-9685) */
        { USB_DEVICE(0x8e9, 0x100), .driver_info = IUC_SPEED_BUG | IUC_NO_WINDOW },
+       /* SigmaTel STIR4210/4220/4116 USB IrDA (VFIR) Bridge */
+       { USB_DEVICE(0x66f, 0x4210), .driver_info = IUC_STIR_4210 | IUC_SPEED_BUG },
+       { USB_DEVICE(0x66f, 0x4220), .driver_info = IUC_STIR_4210 | IUC_SPEED_BUG },
+       { USB_DEVICE(0x66f, 0x4116), .driver_info = IUC_STIR_4210 | IUC_SPEED_BUG },
        { .match_flags = USB_DEVICE_ID_MATCH_INT_CLASS |
-                      USB_DEVICE_ID_MATCH_INT_SUBCLASS,
+         USB_DEVICE_ID_MATCH_INT_SUBCLASS,
          .bInterfaceClass = USB_CLASS_APP_SPEC,
          .bInterfaceSubClass = USB_CLASS_IRDA,
          .driver_info = IUC_DEFAULT, },
@@ -99,6 +107,7 @@ MODULE_DEVICE_TABLE(usb, dongles);
 
 /*------------------------------------------------------------------*/
 
+static void irda_usb_init_qos(struct irda_usb_cb *self) ;
 static struct irda_class_desc *irda_usb_find_class_desc(struct usb_interface *intf);
 static void irda_usb_disconnect(struct usb_interface *intf);
 static void irda_usb_change_speed_xbofs(struct irda_usb_cb *self);
@@ -141,7 +150,24 @@ static void irda_usb_build_header(struct irda_usb_cb *self,
                                  __u8 *header,
                                  int   force)
 {
-       /* Set the negotiated link speed */
+       /* Here we check if we have an STIR421x chip,
+        * and if either speed or xbofs (or both) needs
+        * to be changed.
+        */
+       if (self->capability & IUC_STIR_4210 &&
+           ((self->new_speed != -1) || (self->new_xbofs != -1))) {
+
+               /* With STIR421x, speed and xBOFs must be set at the same
+                * time, even if only one of them changes.
+                */
+               if (self->new_speed == -1)
+                       self->new_speed = self->speed ;
+
+               if (self->new_xbofs == -1)
+                       self->new_xbofs = self->xbofs ;
+       }
+
+       /* Set the link speed */
        if (self->new_speed != -1) {
                /* Hum... Ugly hack :-(
                 * Some device are not compliant with the spec and change
@@ -191,7 +217,11 @@ static void irda_usb_build_header(struct irda_usb_cb *self,
                        *header = SPEED_4000000;
                        self->new_xbofs = 0;
                        break;
-               }
+               case 16000000:
+                       *header = SPEED_16000000;
+                       self->new_xbofs = 0;
+                       break;
+               }
        } else
                /* No change */
                *header = 0;
@@ -235,6 +265,32 @@ static void irda_usb_build_header(struct irda_usb_cb *self,
        }
 }
 
+/*
+*   calculate turnaround time for SigmaTel header
+*/
+static __u8 get_turnaround_time(struct sk_buff *skb)
+{
+       int turnaround_time = irda_get_mtt(skb);
+
+       if ( turnaround_time == 0 )
+               return 0;
+       else if ( turnaround_time <= 10 )
+               return 1;
+       else if ( turnaround_time <= 50 )
+               return 2;
+       else if ( turnaround_time <= 100 )
+               return 3;
+       else if ( turnaround_time <= 500 )
+               return 4;
+       else if ( turnaround_time <= 1000 )
+               return 5;
+       else if ( turnaround_time <= 5000 )
+               return 6;
+       else
+               return 7;
+}
+
+
 /*------------------------------------------------------------------*/
 /*
  * Send a command to change the speed of the dongle
@@ -262,12 +318,18 @@ static void irda_usb_change_speed_xbofs(struct irda_usb_cb *self)
        /* Set the new speed and xbofs in this fake frame */
        irda_usb_build_header(self, frame, 1);
 
+       if ( self->capability & IUC_STIR_4210 ) {
+               if (frame[0] == 0) return ; // do nothing if no change
+               frame[1] = 0; // other parameters don't change here
+               frame[2] = 0;
+       }
+
        /* Submit the 0 length IrDA frame to trigger new speed settings */
         usb_fill_bulk_urb(urb, self->usbdev,
                      usb_sndbulkpipe(self->usbdev, self->bulk_out_ep),
                       frame, IRDA_USB_SPEED_MTU,
                       speed_bulk_callback, self);
-       urb->transfer_buffer_length = USB_IRDA_HEADER;
+       urb->transfer_buffer_length = self->header_length;
        urb->transfer_flags = 0;
 
        /* Irq disabled -> GFP_ATOMIC */
@@ -383,16 +445,35 @@ static int irda_usb_hard_xmit(struct sk_buff *skb, struct net_device *netdev)
         * allocation will be done lower in skb_push().
         * Also, we don't use directly skb_cow(), because it require
         * headroom >= 16, which force unnecessary copies - Jean II */
-       if (skb_headroom(skb) < USB_IRDA_HEADER) {
+       if (skb_headroom(skb) < self->header_length) {
                IRDA_DEBUG(0, "%s(), Insuficient skb headroom.\n", __FUNCTION__);
-               if (skb_cow(skb, USB_IRDA_HEADER)) {
+               if (skb_cow(skb, self->header_length)) {
                        IRDA_WARNING("%s(), failed skb_cow() !!!\n", __FUNCTION__);
                        goto drop;
                }
        }
 
        /* Change setting for next frame */
-       irda_usb_build_header(self, skb_push(skb, USB_IRDA_HEADER), 0);
+
+       if ( self->capability & IUC_STIR_4210 ) {
+               __u8 turnaround_time;
+               __u8* frame;
+               turnaround_time = get_turnaround_time( skb );
+               frame= skb_push(skb, self->header_length);
+               irda_usb_build_header(self, frame, 0);
+               frame[2] = turnaround_time;
+               if ((skb->len != 0) &&
+                   ((skb->len % 128) == 0) &&
+                   ((skb->len % 512) != 0)) {
+                       /* add extra byte for special SigmaTel feature */
+                       frame[1] = 1;
+                       skb_put(skb, 1);
+               } else {
+                       frame[1] = 0;
+               }
+       } else {
+               irda_usb_build_header(self, skb_push(skb, self->header_length), 0);
+       }
 
        /* FIXME: Make macro out of this one */
        ((struct irda_skb_cb *)skb->cb)->context = self;
@@ -795,7 +876,7 @@ static void irda_usb_receive(struct urb *urb, struct pt_regs *regs)
        }
        
        /* Check for empty frames */
-       if (urb->actual_length <= USB_IRDA_HEADER) {
+       if (urb->actual_length <= self->header_length) {
                IRDA_WARNING("%s(), empty frame!\n", __FUNCTION__);
                goto done;
        }
@@ -816,7 +897,11 @@ static void irda_usb_receive(struct urb *urb, struct pt_regs *regs)
        docopy = (urb->actual_length < IRDA_RX_COPY_THRESHOLD);
 
        /* Allocate a new skb */
-       newskb = dev_alloc_skb(docopy ? urb->actual_length : IRDA_SKB_MAX_MTU);
+       if ( self->capability & IUC_STIR_4210 )
+               newskb = dev_alloc_skb(docopy ? urb->actual_length : IRDA_SKB_MAX_MTU + USB_IRDA_SIGMATEL_HEADER);
+       else
+               newskb = dev_alloc_skb(docopy ? urb->actual_length : IRDA_SKB_MAX_MTU);
+
        if (!newskb)  {
                self->stats.rx_dropped++;
                /* We could deliver the current skb, but this would stall
@@ -845,7 +930,7 @@ static void irda_usb_receive(struct urb *urb, struct pt_regs *regs)
 
        /* Set proper length on skb & remove USB-IrDA header */
        skb_put(dataskb, urb->actual_length);
-       skb_pull(dataskb, USB_IRDA_HEADER);
+       skb_pull(dataskb, self->header_length);
 
        /* Ask the networking layer to queue the packet for the IrDA stack */
        dataskb->dev = self->netdev;
@@ -937,6 +1022,191 @@ static int irda_usb_is_receiving(struct irda_usb_cb *self)
        return 0; /* For now */
 }
 
+
+#define STIR421X_PATCH_PRODUCT_VERSION_STR       "Product Version: "
+#define STIR421X_PATCH_COMPONENT_VERSION_STR     "Component Version: "
+#define STIR421X_PATCH_DATA_TAG_STR              "STMP"
+#define STIR421X_PATCH_FILE_VERSION_MAX_OFFSET   512     /* version info is before here */
+#define STIR421X_PATCH_FILE_IMAGE_MAX_OFFSET     512     /* patch image starts before here */
+#define STIR421X_PATCH_FILE_END_OF_HEADER_TAG    0x1A    /* marks end of patch file header (PC DOS text file EOF character) */
+
+/*
+ * Known firmware patches for STIR421x dongles
+ */
+static char * stir421x_patches[] = {
+       "42101001.sb",
+       "42101002.sb",
+};
+
+static int stir421x_get_patch_version(unsigned char * patch, const unsigned long patch_len)
+{
+       unsigned int version_offset;
+       unsigned long version_major, version_minor, version_build;
+       unsigned char * version_start;
+       int version_found = 0;
+
+       for (version_offset = 0;
+            version_offset < STIR421X_PATCH_FILE_END_OF_HEADER_TAG;
+            version_offset++) {
+               if (!memcmp(patch + version_offset,
+                           STIR421X_PATCH_PRODUCT_VERSION_STR,
+                           sizeof(STIR421X_PATCH_PRODUCT_VERSION_STR) - 1)) {
+                                   version_found = 1;
+                                   version_start = patch +
+                                           version_offset +
+                                           sizeof(STIR421X_PATCH_PRODUCT_VERSION_STR) - 1;
+                                   break;
+               }
+       }
+
+       /* We couldn't find a product version on this patch */
+       if (!version_found)
+               return -EINVAL;
+
+       /* Let's check if the product version is dotted */
+       if (version_start[3] != '.' ||
+           version_start[7] != '.')
+               return -EINVAL;
+
+       version_major = simple_strtoul(version_start, NULL, 10);
+       version_minor = simple_strtoul(version_start + 4, NULL, 10);
+       version_build = simple_strtoul(version_start + 8, NULL, 10);
+
+       IRDA_DEBUG(2, "%s(), Major: %ld Minor: %ld Build: %ld\n",
+                  __FUNCTION__,
+                  version_major, version_minor, version_build);
+
+       return (((version_major) << 12) +
+               ((version_minor) << 8) +
+               ((version_build / 10) << 4) +
+               (version_build % 10));
+
+}
+
+
+static int stir421x_upload_patch (struct irda_usb_cb *self,
+                                 unsigned char * patch,
+                                 const unsigned int patch_len)
+{
+    int retval = 0;
+    int actual_len;
+    unsigned int i = 0, download_amount = 0;
+    unsigned char * patch_chunk;
+
+    IRDA_DEBUG (2, "%s(), Uploading STIR421x Patch\n", __FUNCTION__);
+
+    patch_chunk = kzalloc(STIR421X_MAX_PATCH_DOWNLOAD_SIZE, GFP_KERNEL);
+    if (patch_chunk == NULL)
+           return -ENOMEM;
+
+    /* break up patch into 1023-byte sections */
+    for (i = 0; retval >= 0 && i < patch_len; i += download_amount) {
+           download_amount = patch_len - i;
+           if (download_amount > STIR421X_MAX_PATCH_DOWNLOAD_SIZE)
+                   download_amount = STIR421X_MAX_PATCH_DOWNLOAD_SIZE;
+
+           /* download the patch section */
+           memcpy(patch_chunk, patch + i, download_amount);
+
+           retval = usb_bulk_msg (self->usbdev,
+                                  usb_sndbulkpipe (self->usbdev,
+                                                   self->bulk_out_ep),
+                                  patch_chunk, download_amount,
+                                  &actual_len, msecs_to_jiffies (500));
+           IRDA_DEBUG (2, "%s(), Sent %u bytes\n", __FUNCTION__,
+                       actual_len);
+           if (retval == 0)
+                   mdelay(10);
+    }
+
+    kfree(patch_chunk);
+
+    if (i != patch_len) {
+           IRDA_ERROR ("%s(), Pushed %d bytes (!= patch_len (%d))\n",
+                      __FUNCTION__, i, patch_len);
+           retval = -EIO;
+    }
+
+    if (retval < 0)
+           /* todo - mark device as not ready */
+           IRDA_ERROR ("%s(), STIR421x patch upload failed (%d)\n",
+                       __FUNCTION__, retval);
+
+    return retval;
+}
+
+
+static int stir421x_patch_device(struct irda_usb_cb *self)
+{
+       unsigned int i, patch_found = 0, data_found = 0, data_offset;
+       int patch_version, ret = 0;
+       const struct firmware *fw_entry;
+
+       for (i = 0; i < ARRAY_SIZE(stir421x_patches); i++) {
+               if(request_firmware(&fw_entry, stir421x_patches[i], &self->usbdev->dev) != 0) {
+                       IRDA_ERROR( "%s(), Patch %s is not available\n", __FUNCTION__, stir421x_patches[i]);
+                       continue;
+               }
+
+                /* We found a patch from userspace */
+               patch_version = stir421x_get_patch_version (fw_entry->data, fw_entry->size);
+
+               if (patch_version < 0) {
+                       /* Couldn't fetch a version, let's move on to the next file */
+                       IRDA_ERROR("%s(), version parsing failed\n", __FUNCTION__);
+                       ret = patch_version;
+                       release_firmware(fw_entry);
+                       continue;
+               }
+
+               if (patch_version != self->usbdev->descriptor.bcdDevice) {
+                       /* Patch version and device don't match */
+                       IRDA_ERROR ("%s(), wrong patch version (%d <-> %d)\n",
+                                   __FUNCTION__,
+                                   patch_version, self->usbdev->descriptor.bcdDevice);
+                       ret = -EINVAL;
+                       release_firmware(fw_entry);
+                       continue;
+               }
+
+               /* If we're here, we've found a correct patch */
+               patch_found = 1;
+               break;
+
+       }
+
+       /* We couldn't find a valid firmware, let's leave */
+       if (!patch_found)
+               return ret;
+
+       /* The actual image starts after the "STMP" keyword */
+       for (data_offset = 0; data_offset < STIR421X_PATCH_FILE_IMAGE_MAX_OFFSET; data_offset++) {
+               if (!memcmp(fw_entry->data + data_offset,
+                           STIR421X_PATCH_DATA_TAG_STR,
+                           sizeof(STIR421X_PATCH_FILE_IMAGE_MAX_OFFSET))) {
+                       IRDA_DEBUG(2, "%s(), found patch data for STIR421x at offset %d\n",
+                                  __FUNCTION__, data_offset);
+                       data_found = 1;
+                       break;
+               }
+       }
+
+       /* We couldn't find "STMP" from the header */
+       if (!data_found)
+               return -EINVAL;
+
+       /* Let's upload the patch to the target */
+       ret = stir421x_upload_patch(self,
+                                   &fw_entry->data[data_offset + sizeof(STIR421X_PATCH_FILE_IMAGE_MAX_OFFSET)],
+                                   fw_entry->size - (data_offset + sizeof(STIR421X_PATCH_FILE_IMAGE_MAX_OFFSET)));
+
+       release_firmware(fw_entry);
+
+       return ret;
+
+}
+
+
 /********************** IRDA DEVICE CALLBACKS **********************/
 /*
  * Main calls from the IrDA/Network subsystem.
@@ -972,6 +1242,11 @@ static int irda_usb_net_open(struct net_device *netdev)
                return -1;
        }
 
+       if(self->needspatch) {
+               IRDA_WARNING("%s(), device needs patch\n", __FUNCTION__) ;
+               return -EIO ;
+       }
+
        /* Initialise default speed and xbofs value
         * (IrLAP will change that soon) */
        self->speed = -1;
@@ -1050,7 +1325,7 @@ static int irda_usb_net_close(struct net_device *netdev)
        del_timer(&self->rx_defer_timer);
 
        /* Deallocate all the Rx path buffers (URBs and skb) */
-       for (i = 0; i < IU_MAX_RX_URBS; i++) {
+       for (i = 0; i < self->max_rx_urb; i++) {
                struct urb *urb = self->rx_urb[i];
                struct sk_buff *skb = (struct sk_buff *) urb->context;
                /* Cancel the receive command */
@@ -1426,8 +1701,22 @@ static int irda_usb_probe(struct usb_interface *intf,
        spin_lock_init(&self->lock);
        init_timer(&self->rx_defer_timer);
 
+       self->capability = id->driver_info;
+       self->needspatch = ((self->capability & IUC_STIR_4210) != 0) ;
+
        /* Create all of the needed urbs */
-       for (i = 0; i < IU_MAX_RX_URBS; i++) {
+       if (self->capability & IUC_STIR_4210) {
+               self->max_rx_urb = IU_SIGMATEL_MAX_RX_URBS;
+               self->header_length = USB_IRDA_SIGMATEL_HEADER;
+       } else {
+               self->max_rx_urb = IU_MAX_RX_URBS;
+               self->header_length = USB_IRDA_HEADER;
+       }
+
+       self->rx_urb = kzalloc(self->max_rx_urb * sizeof(struct urb *),
+                               GFP_KERNEL);
+
+       for (i = 0; i < self->max_rx_urb; i++) {
                self->rx_urb[i] = usb_alloc_urb(0, GFP_KERNEL);
                if (!self->rx_urb[i]) {
                        goto err_out_1;
@@ -1479,17 +1768,28 @@ static int irda_usb_probe(struct usb_interface *intf,
                goto err_out_3;
        }
 
+       self->usbdev = dev;
+
        /* Find IrDA class descriptor */
        irda_desc = irda_usb_find_class_desc(intf);
        ret = -ENODEV;
        if (irda_desc == NULL)
                goto err_out_3;
 
+       if (self->needspatch) {
+               ret = usb_control_msg (self->usbdev, usb_sndctrlpipe (self->usbdev, 0),
+                                      0x02, 0x40, 0, 0, 0, 0, msecs_to_jiffies(500));
+               if (ret < 0) {
+                       IRDA_DEBUG (0, "usb_control_msg failed %d\n", ret);
+                       goto err_out_3;
+               } else {
+                       mdelay(10);
+               }
+       }
+
        self->irda_desc =  irda_desc;
        self->present = 1;
        self->netopen = 0;
-       self->capability = id->driver_info;
-       self->usbdev = dev;
        self->usbintf = intf;
 
        /* Allocate the buffer for speed changes */
@@ -1508,8 +1808,32 @@ static int irda_usb_probe(struct usb_interface *intf,
 
        IRDA_MESSAGE("IrDA: Registered device %s\n", net->name);
        usb_set_intfdata(intf, self);
+
+       if (self->needspatch) {
+               /* Now we fetch and upload the firmware patch */
+               ret = stir421x_patch_device(self);
+               self->needspatch = (ret < 0);
+               if (ret < 0) {
+                       printk("patch_device failed\n");
+                       goto err_out_5;
+               }
+
+               /* replace IrDA class descriptor with what patched device is now reporting */
+               irda_desc = irda_usb_find_class_desc (self->usbintf);
+               if (irda_desc == NULL) {
+                       ret = -ENODEV;
+                       goto err_out_5;
+               }
+               if (self->irda_desc)
+                       kfree (self->irda_desc);
+               self->irda_desc = irda_desc;
+               irda_usb_init_qos(self);
+       }
+
        return 0;
 
+err_out_5:
+       unregister_netdev(self->netdev);
 err_out_4:
        kfree(self->speed_buff);
 err_out_3:
@@ -1518,7 +1842,7 @@ err_out_3:
 err_out_2:
        usb_free_urb(self->tx_urb);
 err_out_1:
-       for (i = 0; i < IU_MAX_RX_URBS; i++) {
+       for (i = 0; i < self->max_rx_urb; i++) {
                if (self->rx_urb[i])
                        usb_free_urb(self->rx_urb[i]);
        }
@@ -1571,7 +1895,7 @@ static void irda_usb_disconnect(struct usb_interface *intf)
                /*netif_device_detach(self->netdev);*/
                netif_stop_queue(self->netdev);
                /* Stop all the receive URBs. Must be synchronous. */
-               for (i = 0; i < IU_MAX_RX_URBS; i++)
+               for (i = 0; i < self->max_rx_urb; i++)
                        usb_kill_urb(self->rx_urb[i]);
                /* Cancel Tx and speed URB.
                 * Make sure it's synchronous to avoid races. */
@@ -1586,8 +1910,9 @@ static void irda_usb_disconnect(struct usb_interface *intf)
        self->usbintf = NULL;
 
        /* Clean up our urbs */
-       for (i = 0; i < IU_MAX_RX_URBS; i++)
+       for (i = 0; i < self->max_rx_urb; i++)
                usb_free_urb(self->rx_urb[i]);
+       kfree(self->rx_urb);
        /* Clean up Tx and speed URB */
        usb_free_urb(self->tx_urb);
        usb_free_urb(self->speed_urb);
@@ -1648,6 +1973,6 @@ module_exit(usb_irda_cleanup);
  */
 module_param(qos_mtt_bits, int, 0);
 MODULE_PARM_DESC(qos_mtt_bits, "Minimum Turn Time");
-MODULE_AUTHOR("Roman Weissgaerber <weissg@vienna.at>, Dag Brattli <dag@brattli.net> and Jean Tourrilhes <jt@hpl.hp.com>");
-MODULE_DESCRIPTION("IrDA-USB Dongle Driver"); 
+MODULE_AUTHOR("Roman Weissgaerber <weissg@vienna.at>, Dag Brattli <dag@brattli.net>, Jean Tourrilhes <jt@hpl.hp.com> and Nick Fedchik <nick@fedchik.org.ua>");
+MODULE_DESCRIPTION("IrDA-USB Dongle Driver");
 MODULE_LICENSE("GPL");
index 4026af42dd47da4336f1a6ef50d3c49fa7cbbdf6..d833db52cebf2921333f9d5c19e0ceaa79063832 100644 (file)
@@ -1,7 +1,7 @@
 /*****************************************************************************
  *
  * Filename:      irda-usb.h
- * Version:       0.9b
+ * Version:       0.10
  * Description:   IrDA-USB Driver
  * Status:        Experimental 
  * Author:        Dag Brattli <dag@brattli.net>
@@ -9,6 +9,9 @@
  *     Copyright (C) 2001, Roman Weissgaerber <weissg@vienna.at>
  *      Copyright (C) 2000, Dag Brattli <dag@brattli.net>
  *      Copyright (C) 2001, Jean Tourrilhes <jt@hpl.hp.com>
+ *      Copyright (C) 2004, SigmaTel, Inc. <irquality@sigmatel.com>
+ *      Copyright (C) 2005, Milan Beno <beno@pobox.sk>
+ *      Copyright (C) 2006, Nick FEdchik <nick@fedchik.org.ua>
  *          
  *     This program is free software; you can redistribute it and/or modify
  *     it under the terms of the GNU General Public License as published by
@@ -31,6 +34,9 @@
 #include <net/irda/irda.h>
 #include <net/irda/irda_device.h>      /* struct irlap_cb */
 
+#define PATCH_FILE_SIZE_MAX     65536
+#define PATCH_FILE_SIZE_MIN     80
+
 #define RX_COPY_THRESHOLD 200
 #define IRDA_USB_MAX_MTU 2051
 #define IRDA_USB_SPEED_MTU 64          /* Weird, but work like this */
 /* Inbound header */
 #define MEDIA_BUSY    0x80
 
-#define SPEED_2400    0x01
-#define SPEED_9600    0x02
-#define SPEED_19200   0x03
-#define SPEED_38400   0x04
-#define SPEED_57600   0x05
-#define SPEED_115200  0x06
-#define SPEED_576000  0x07
-#define SPEED_1152000 0x08
-#define SPEED_4000000 0x09
+#define SPEED_2400     0x01
+#define SPEED_9600     0x02
+#define SPEED_19200    0x03
+#define SPEED_38400    0x04
+#define SPEED_57600    0x05
+#define SPEED_115200   0x06
+#define SPEED_576000   0x07
+#define SPEED_1152000  0x08
+#define SPEED_4000000  0x09
+#define SPEED_16000000 0x0a
 
 /* Basic capabilities */
 #define IUC_DEFAULT    0x00    /* Basic device compliant with 1.0 spec */
 #define IUC_SMALL_PKT  0x10    /* Device doesn't behave with big Rx packets */
 #define IUC_MAX_WINDOW 0x20    /* Device underestimate the Rx window */
 #define IUC_MAX_XBOFS  0x40    /* Device need more xbofs than advertised */
+#define IUC_STIR_4210  0x80    /* SigmaTel 4210/4220/4116 VFIR */
 
 /* USB class definitions */
-#define USB_IRDA_HEADER   0x01
-#define USB_CLASS_IRDA    0x02 /* USB_CLASS_APP_SPEC subclass */ 
-#define USB_DT_IRDA       0x21
+#define USB_IRDA_HEADER            0x01
+#define USB_CLASS_IRDA             0x02 /* USB_CLASS_APP_SPEC subclass */
+#define USB_DT_IRDA                0x21
+#define USB_IRDA_SIGMATEL_HEADER   0x03
+#define IU_SIGMATEL_MAX_RX_URBS    (IU_MAX_ACTIVE_RX_URBS + USB_IRDA_SIGMATEL_HEADER)
 
 struct irda_class_desc {
        __u8  bLength;
@@ -123,6 +133,7 @@ struct irda_class_desc {
  * (6.2.5, USB-IrDA class spec 1.0) */
 
 #define IU_REQ_GET_CLASS_DESC  0x06
+#define STIR421X_MAX_PATCH_DOWNLOAD_SIZE 1023
 
 struct irda_usb_cb {
        struct irda_class_desc *irda_desc;
@@ -136,7 +147,8 @@ struct irda_usb_cb {
        __u16 bulk_out_mtu;             /* Max Tx packet size in bytes */
        __u8  bulk_int_ep;              /* Interrupt Endpoint assignments */
 
-       struct urb *rx_urb[IU_MAX_RX_URBS];     /* URBs used to receive data frames */
+       __u8  max_rx_urb;
+       struct urb **rx_urb;            /* URBs used to receive data frames */
        struct urb *idle_rx_urb;        /* Pointer to idle URB in Rx path */
        struct urb *tx_urb;             /* URB used to send data frames */
        struct urb *speed_urb;          /* URB used to send speed commands */
@@ -157,6 +169,9 @@ struct irda_usb_cb {
        __u32 speed;                    /* Current speed */
        __s32 new_speed;                /* speed we need to set */
 
+       __u8 header_length;             /* USB-IrDA frame header size */
+       int needspatch;                 /* device needs firmware patch */
+
        struct timer_list rx_defer_timer;       /* Wait for Rx error to clear */
 };
 
index ec94ecdb103dcfa508ce105a1b9e2bf805c76317..58f76cefbc8394c0a82fb33eaa8119a7c7480e00 100644 (file)
@@ -11,6 +11,7 @@
  *     Copyright (c) 2002      Daniele Peri
  *     All Rights Reserved.
  *     Copyright (c) 2002      Jean Tourrilhes
+ *     Copyright (c) 2006      Linus Walleij
  *
  *
  * Based on smc-ircc.c:
@@ -61,6 +62,9 @@
 
 #include <linux/spinlock.h>
 #include <linux/pm.h>
+#ifdef CONFIG_PCI
+#include <linux/pci.h>
+#endif
 
 #include <net/irda/wrapper.h>
 #include <net/irda/irda.h>
@@ -100,6 +104,22 @@ MODULE_PARM_DESC(ircc_transceiver, "Transceiver type");
 
 /* Types */
 
+#ifdef CONFIG_PCI
+struct smsc_ircc_subsystem_configuration {
+       unsigned short vendor; /* PCI vendor ID */
+       unsigned short device; /* PCI vendor ID */
+       unsigned short subvendor; /* PCI subsystem vendor ID */
+       unsigned short subdevice; /* PCI sybsystem device ID */
+       unsigned short sir_io; /* I/O port for SIR */
+       unsigned short fir_io; /* I/O port for FIR */
+       unsigned char  fir_irq; /* FIR IRQ */
+       unsigned char  fir_dma; /* FIR DMA */
+       unsigned short cfg_base; /* I/O port for chip configuration */
+       int (*preconfigure)(struct pci_dev *dev, struct smsc_ircc_subsystem_configuration *conf); /* Preconfig function */
+       const char *name;       /* name shown as info */
+};
+#endif
+
 struct smsc_transceiver {
        char *name;
        void (*set_for_speed)(int fir_base, u32 speed);
@@ -202,6 +222,18 @@ static int __init smsc_superio_flat(const struct smsc_chip *chips, unsigned shor
 static int __init smsc_superio_paged(const struct smsc_chip *chips, unsigned short cfg_base, char *type);
 static int __init smsc_superio_fdc(unsigned short cfg_base);
 static int __init smsc_superio_lpc(unsigned short cfg_base);
+#ifdef CONFIG_PCI
+static int __init preconfigure_smsc_chip(struct smsc_ircc_subsystem_configuration *conf);
+static int __init preconfigure_through_82801(struct pci_dev *dev, struct smsc_ircc_subsystem_configuration *conf);
+static void __init preconfigure_ali_port(struct pci_dev *dev,
+                                        unsigned short port);
+static int __init preconfigure_through_ali(struct pci_dev *dev, struct smsc_ircc_subsystem_configuration *conf);
+static int __init smsc_ircc_preconfigure_subsystems(unsigned short ircc_cfg,
+                                                   unsigned short ircc_fir,
+                                                   unsigned short ircc_sir,
+                                                   unsigned char ircc_dma,
+                                                   unsigned char ircc_irq);
+#endif
 
 /* Transceivers specific functions */
 
@@ -353,6 +385,13 @@ static int __init smsc_ircc_init(void)
                return ret;
        }
 
+#ifdef CONFIG_PCI
+       if (smsc_ircc_preconfigure_subsystems(ircc_cfg, ircc_fir, ircc_sir, ircc_dma, ircc_irq) < 0) {
+               /* Ignore errors from preconfiguration */
+               IRDA_ERROR("%s, Preconfiguration failed !\n", driver_name);
+       }
+#endif
+
        dev_count = 0;
 
        if (ircc_fir > 0 && ircc_sir > 0) {
@@ -2285,6 +2324,490 @@ static int __init smsc_superio_lpc(unsigned short cfg_base)
        return ret;
 }
 
+/*
+ * Look for some specific subsystem setups that need
+ * pre-configuration not properly done by the BIOS (especially laptops)
+ * This code is based in part on smcinit.c, tosh1800-smcinit.c
+ * and tosh2450-smcinit.c. The table lists the device entries
+ * for ISA bridges with an LPC (Low Pin Count) controller which
+ * handles the communication with the SMSC device. After the LPC
+ * controller is initialized through PCI, the SMSC device is initialized
+ * through a dedicated port in the ISA port-mapped I/O area, this latter
+ * area is used to configure the SMSC device with default
+ * SIR and FIR I/O ports, DMA and IRQ. Different vendors have
+ * used different sets of parameters and different control port
+ * addresses making a subsystem device table necessary.
+ */
+#ifdef CONFIG_PCI
+#define PCIID_VENDOR_INTEL 0x8086
+#define PCIID_VENDOR_ALI 0x10b9
+static struct smsc_ircc_subsystem_configuration subsystem_configurations[] __devinitdata = {
+       {
+               .vendor = PCIID_VENDOR_INTEL, /* Intel 82801DBM LPC bridge */
+               .device = 0x24cc,
+               .subvendor = 0x103c,
+               .subdevice = 0x088c,
+               /* Quite certain these are the same for nc8000 as for nc6000 */
+               .sir_io = 0x02f8,
+               .fir_io = 0x0130,
+               .fir_irq = 0x05,
+               .fir_dma = 0x03,
+               .cfg_base = 0x004e,
+               .preconfigure = preconfigure_through_82801,
+               .name = "HP nc8000",
+       },
+       {
+               .vendor = PCIID_VENDOR_INTEL, /* Intel 82801DBM LPC bridge */
+               .device = 0x24cc,
+               .subvendor = 0x103c,
+               .subdevice = 0x0890,
+               .sir_io = 0x02f8,
+               .fir_io = 0x0130,
+               .fir_irq = 0x05,
+               .fir_dma = 0x03,
+               .cfg_base = 0x004e,
+               .preconfigure = preconfigure_through_82801,
+               .name = "HP nc6000",
+       },
+       {
+               /* Intel 82801DB/DBL (ICH4/ICH4-L) LPC Interface Bridge */
+               .vendor = PCIID_VENDOR_INTEL,
+               .device = 0x24c0,
+               .subvendor = 0x1179,
+               .subdevice = 0xffff, /* 0xffff is "any" */
+               .sir_io = 0x03f8,
+               .fir_io = 0x0130,
+               .fir_irq = 0x07,
+               .fir_dma = 0x01,
+               .cfg_base = 0x002e,
+               .preconfigure = preconfigure_through_82801,
+               .name = "Toshiba laptop with Intel 82801DB/DBL LPC bridge",
+       },
+       {
+               .vendor = PCIID_VENDOR_INTEL, /* Intel 82801CAM ISA bridge */
+               .device = 0x248c,
+               .subvendor = 0x1179,
+               .subdevice = 0xffff, /* 0xffff is "any" */
+               .sir_io = 0x03f8,
+               .fir_io = 0x0130,
+               .fir_irq = 0x03,
+               .fir_dma = 0x03,
+               .cfg_base = 0x002e,
+               .preconfigure = preconfigure_through_82801,
+               .name = "Toshiba laptop with Intel 82801CAM ISA bridge",
+       },
+       {
+               /* 82801DBM (ICH4-M) LPC Interface Bridge */
+               .vendor = PCIID_VENDOR_INTEL,
+               .device = 0x24cc,
+               .subvendor = 0x1179,
+               .subdevice = 0xffff, /* 0xffff is "any" */
+               .sir_io = 0x03f8,
+               .fir_io = 0x0130,
+               .fir_irq = 0x03,
+               .fir_dma = 0x03,
+               .cfg_base = 0x002e,
+               .preconfigure = preconfigure_through_82801,
+               .name = "Toshiba laptop with Intel 8281DBM LPC bridge",
+       },
+       {
+               /* ALi M1533/M1535 PCI to ISA Bridge [Aladdin IV/V/V+] */
+               .vendor = PCIID_VENDOR_ALI,
+               .device = 0x1533,
+               .subvendor = 0x1179,
+               .subdevice = 0xffff, /* 0xffff is "any" */
+               .sir_io = 0x02e8,
+               .fir_io = 0x02f8,
+               .fir_irq = 0x07,
+               .fir_dma = 0x03,
+               .cfg_base = 0x002e,
+               .preconfigure = preconfigure_through_ali,
+               .name = "Toshiba laptop with ALi ISA bridge",
+       },
+       { } // Terminator
+};
+
+
+/*
+ * This sets up the basic SMSC parameters
+ * (FIR port, SIR port, FIR DMA, FIR IRQ)
+ * through the chip configuration port.
+ */
+static int __init preconfigure_smsc_chip(struct
+                                        smsc_ircc_subsystem_configuration
+                                        *conf)
+{
+       unsigned short iobase = conf->cfg_base;
+       unsigned char tmpbyte;
+
+       outb(LPC47N227_CFGACCESSKEY, iobase); // enter configuration state
+       outb(SMSCSIOFLAT_DEVICEID_REG, iobase); // set for device ID
+       tmpbyte = inb(iobase +1); // Read device ID
+       IRDA_DEBUG(0,
+                  "Detected Chip id: 0x%02x, setting up registers...\n",
+                  tmpbyte);
+
+       /* Disable UART1 and set up SIR I/O port */
+       outb(0x24, iobase);  // select CR24 - UART1 base addr
+       outb(0x00, iobase + 1); // disable UART1
+       outb(SMSCSIOFLAT_UART2BASEADDR_REG, iobase);  // select CR25 - UART2 base addr
+       outb( (conf->sir_io >> 2), iobase + 1); // bits 2-9 of 0x3f8
+       tmpbyte = inb(iobase + 1);
+       if (tmpbyte != (conf->sir_io >> 2) ) {
+               IRDA_WARNING("ERROR: could not configure SIR ioport.\n");
+               IRDA_WARNING("Try to supply ircc_cfg argument.\n");
+               return -ENXIO;
+       }
+
+       /* Set up FIR IRQ channel for UART2 */
+       outb(SMSCSIOFLAT_UARTIRQSELECT_REG, iobase); // select CR28 - UART1,2 IRQ select
+       tmpbyte = inb(iobase + 1);
+       tmpbyte &= SMSCSIOFLAT_UART1IRQSELECT_MASK; // Do not touch the UART1 portion
+       tmpbyte |= (conf->fir_irq & SMSCSIOFLAT_UART2IRQSELECT_MASK);
+       outb(tmpbyte, iobase + 1);
+       tmpbyte = inb(iobase + 1) & SMSCSIOFLAT_UART2IRQSELECT_MASK;
+       if (tmpbyte != conf->fir_irq) {
+               IRDA_WARNING("ERROR: could not configure FIR IRQ channel.\n");
+               return -ENXIO;
+       }
+
+       /* Set up FIR I/O port */
+       outb(SMSCSIOFLAT_FIRBASEADDR_REG, iobase);  // CR2B - SCE (FIR) base addr
+       outb((conf->fir_io >> 3), iobase + 1);
+       tmpbyte = inb(iobase + 1);
+       if (tmpbyte != (conf->fir_io >> 3) ) {
+               IRDA_WARNING("ERROR: could not configure FIR I/O port.\n");
+               return -ENXIO;
+       }
+
+       /* Set up FIR DMA channel */
+       outb(SMSCSIOFLAT_FIRDMASELECT_REG, iobase);  // CR2C - SCE (FIR) DMA select
+       outb((conf->fir_dma & LPC47N227_FIRDMASELECT_MASK), iobase + 1); // DMA
+       tmpbyte = inb(iobase + 1) & LPC47N227_FIRDMASELECT_MASK;
+       if (tmpbyte != (conf->fir_dma & LPC47N227_FIRDMASELECT_MASK)) {
+               IRDA_WARNING("ERROR: could not configure FIR DMA channel.\n");
+               return -ENXIO;
+       }
+
+       outb(SMSCSIOFLAT_UARTMODE0C_REG, iobase);  // CR0C - UART mode
+       tmpbyte = inb(iobase + 1);
+       tmpbyte &= ~SMSCSIOFLAT_UART2MODE_MASK |
+               SMSCSIOFLAT_UART2MODE_VAL_IRDA;
+       outb(tmpbyte, iobase + 1); // enable IrDA (HPSIR) mode, high speed
+
+       outb(LPC47N227_APMBOOTDRIVE_REG, iobase);  // CR07 - Auto Pwr Mgt/boot drive sel
+       tmpbyte = inb(iobase + 1);
+       outb(tmpbyte | LPC47N227_UART2AUTOPWRDOWN_MASK, iobase + 1); // enable UART2 autopower down
+
+       /* This one was not part of tosh1800 */
+       outb(0x0a, iobase);  // CR0a - ecp fifo / ir mux
+       tmpbyte = inb(iobase + 1);
+       outb(tmpbyte | 0x40, iobase + 1); // send active device to ir port
+
+       outb(LPC47N227_UART12POWER_REG, iobase);  // CR02 - UART 1,2 power
+       tmpbyte = inb(iobase + 1);
+       outb(tmpbyte | LPC47N227_UART2POWERDOWN_MASK, iobase + 1); // UART2 power up mode, UART1 power down
+
+       outb(LPC47N227_FDCPOWERVALIDCONF_REG, iobase);  // CR00 - FDC Power/valid config cycle
+       tmpbyte = inb(iobase + 1);
+       outb(tmpbyte | LPC47N227_VALID_MASK, iobase + 1); // valid config cycle done
+
+       outb(LPC47N227_CFGEXITKEY, iobase);  // Exit configuration
+
+       return 0;
+}
+
+/* 82801CAM generic registers */
+#define VID 0x00
+#define DID 0x02
+#define PIRQ_A_D_ROUT 0x60
+#define SIRQ_CNTL 0x64
+#define PIRQ_E_H_ROUT 0x68
+#define PCI_DMA_C 0x90
+/* LPC-specific registers */
+#define COM_DEC 0xe0
+#define GEN1_DEC 0xe4
+#define LPC_EN 0xe6
+#define GEN2_DEC 0xec
+/*
+ * Sets up the I/O range using the 82801CAM ISA bridge, 82801DBM LPC bridge
+ * or Intel 82801DB/DBL (ICH4/ICH4-L) LPC Interface Bridge.
+ * They all work the same way!
+ */
+static int __init preconfigure_through_82801(struct pci_dev *dev,
+                                            struct
+                                            smsc_ircc_subsystem_configuration
+                                            *conf)
+{
+       unsigned short tmpword;
+       unsigned char tmpbyte;
+
+       IRDA_MESSAGE("Setting up Intel 82801 controller and SMSC device\n");
+       /*
+        * Select the range for the COMA COM port (SIR)
+        * Register COM_DEC:
+        * Bit 7: reserved
+        * Bit 6-4, COMB decode range
+        * Bit 3: reserved
+        * Bit 2-0, COMA decode range
+        *
+        * Decode ranges:
+        *   000 = 0x3f8-0x3ff (COM1)
+        *   001 = 0x2f8-0x2ff (COM2)
+        *   010 = 0x220-0x227
+        *   011 = 0x228-0x22f
+        *   100 = 0x238-0x23f
+        *   101 = 0x2e8-0x2ef (COM4)
+        *   110 = 0x338-0x33f
+        *   111 = 0x3e8-0x3ef (COM3)
+        */
+       pci_read_config_byte(dev, COM_DEC, &tmpbyte);
+       tmpbyte &= 0xf8; /* mask COMA bits */
+       switch(conf->sir_io) {
+       case 0x3f8:
+               tmpbyte |= 0x00;
+               break;
+       case 0x2f8:
+               tmpbyte |= 0x01;
+               break;
+       case 0x220:
+               tmpbyte |= 0x02;
+               break;
+       case 0x228:
+               tmpbyte |= 0x03;
+               break;
+       case 0x238:
+               tmpbyte |= 0x04;
+               break;
+       case 0x2e8:
+               tmpbyte |= 0x05;
+               break;
+       case 0x338:
+               tmpbyte |= 0x06;
+               break;
+       case 0x3e8:
+               tmpbyte |= 0x07;
+               break;
+       default:
+               tmpbyte |= 0x01; /* COM2 default */
+       }
+       IRDA_DEBUG(1, "COM_DEC (write): 0x%02x\n", tmpbyte);
+       pci_write_config_byte(dev, COM_DEC, tmpbyte);
+
+       /* Enable Low Pin Count interface */
+       pci_read_config_word(dev, LPC_EN, &tmpword);
+       /* These seem to be set up at all times,
+        * just make sure it is properly set.
+        */
+       switch(conf->cfg_base) {
+       case 0x04e:
+               tmpword |= 0x2000;
+               break;
+       case 0x02e:
+               tmpword |= 0x1000;
+               break;
+       case 0x062:
+               tmpword |= 0x0800;
+               break;
+       case 0x060:
+               tmpword |= 0x0400;
+               break;
+       default:
+               IRDA_WARNING("Uncommon I/O base address: 0x%04x\n",
+                            conf->cfg_base);
+               break;
+       }
+       tmpword &= 0xfffd; /* disable LPC COMB */
+       tmpword |= 0x0001; /* set bit 0 : enable LPC COMA addr range (GEN2) */
+       IRDA_DEBUG(1, "LPC_EN (write): 0x%04x\n", tmpword);
+       pci_write_config_word(dev, LPC_EN, tmpword);
+
+       /*
+        * Configure LPC DMA channel
+        * PCI_DMA_C bits:
+        * Bit 15-14: DMA channel 7 select
+        * Bit 13-12: DMA channel 6 select
+        * Bit 11-10: DMA channel 5 select
+        * Bit 9-8:   Reserved
+        * Bit 7-6:   DMA channel 3 select
+        * Bit 5-4:   DMA channel 2 select
+        * Bit 3-2:   DMA channel 1 select
+        * Bit 1-0:   DMA channel 0 select
+        *  00 = Reserved value
+        *  01 = PC/PCI DMA
+        *  10 = Reserved value
+        *  11 = LPC I/F DMA
+        */
+       pci_read_config_word(dev, PCI_DMA_C, &tmpword);
+       switch(conf->fir_dma) {
+       case 0x07:
+               tmpword |= 0xc000;
+               break;
+       case 0x06:
+               tmpword |= 0x3000;
+               break;
+       case 0x05:
+               tmpword |= 0x0c00;
+               break;
+       case 0x03:
+               tmpword |= 0x00c0;
+               break;
+       case 0x02:
+               tmpword |= 0x0030;
+               break;
+       case 0x01:
+               tmpword |= 0x000c;
+               break;
+       case 0x00:
+               tmpword |= 0x0003;
+               break;
+       default:
+               break; /* do not change settings */
+       }
+       IRDA_DEBUG(1, "PCI_DMA_C (write): 0x%04x\n", tmpword);
+       pci_write_config_word(dev, PCI_DMA_C, tmpword);
+
+       /*
+        * GEN2_DEC bits:
+        * Bit 15-4: Generic I/O range
+        * Bit 3-1: reserved (read as 0)
+        * Bit 0: enable GEN2 range on LPC I/F
+        */
+       tmpword = conf->fir_io & 0xfff8;
+       tmpword |= 0x0001;
+       IRDA_DEBUG(1, "GEN2_DEC (write): 0x%04x\n", tmpword);
+       pci_write_config_word(dev, GEN2_DEC, tmpword);
+
+       /* Pre-configure chip */
+       return preconfigure_smsc_chip(conf);
+}
+
+/*
+ * Pre-configure a certain port on the ALi 1533 bridge.
+ * This is based on reverse-engineering since ALi does not
+ * provide any data sheet for the 1533 chip.
+ */
+static void __init preconfigure_ali_port(struct pci_dev *dev,
+                                        unsigned short port)
+{
+       unsigned char reg;
+       /* These bits obviously control the different ports */
+       unsigned char mask;
+       unsigned char tmpbyte;
+
+       switch(port) {
+       case 0x0130:
+       case 0x0178:
+               reg = 0xb0;
+               mask = 0x80;
+               break;
+       case 0x03f8:
+               reg = 0xb4;
+               mask = 0x80;
+               break;
+       case 0x02f8:
+               reg = 0xb4;
+               mask = 0x30;
+               break;
+       case 0x02e8:
+               reg = 0xb4;
+               mask = 0x08;
+               break;
+       default:
+               IRDA_ERROR("Failed to configure unsupported port on ALi 1533 bridge: 0x%04x\n", port);
+               return;
+       }
+
+       pci_read_config_byte(dev, reg, &tmpbyte);
+       /* Turn on the right bits */
+       tmpbyte |= mask;
+       pci_write_config_byte(dev, reg, tmpbyte);
+       IRDA_MESSAGE("Activated ALi 1533 ISA bridge port 0x%04x.\n", port);
+       return;
+}
+
+static int __init preconfigure_through_ali(struct pci_dev *dev,
+                                          struct
+                                          smsc_ircc_subsystem_configuration
+                                          *conf)
+{
+       /* Configure the two ports on the ALi 1533 */
+       preconfigure_ali_port(dev, conf->sir_io);
+       preconfigure_ali_port(dev, conf->fir_io);
+
+       /* Pre-configure chip */
+       return preconfigure_smsc_chip(conf);
+}
+
+static int __init smsc_ircc_preconfigure_subsystems(unsigned short ircc_cfg,
+                                                   unsigned short ircc_fir,
+                                                   unsigned short ircc_sir,
+                                                   unsigned char ircc_dma,
+                                                   unsigned char ircc_irq)
+{
+       struct pci_dev *dev = NULL;
+       unsigned short ss_vendor = 0x0000;
+       unsigned short ss_device = 0x0000;
+       int ret = 0;
+
+       dev = pci_get_device(PCI_ANY_ID, PCI_ANY_ID, dev);
+
+       while (dev != NULL) {
+               struct smsc_ircc_subsystem_configuration *conf;
+
+               /*
+                * Cache the subsystem vendor/device:
+                * some manufacturers fail to set this for all components,
+                * so we save it in case there is just 0x0000 0x0000 on the
+                * device we want to check.
+                */
+               if (dev->subsystem_vendor != 0x0000U) {
+                       ss_vendor = dev->subsystem_vendor;
+                       ss_device = dev->subsystem_device;
+               }
+               conf = subsystem_configurations;
+               for( ; conf->subvendor; conf++) {
+                       if(conf->vendor == dev->vendor &&
+                          conf->device == dev->device &&
+                          conf->subvendor == ss_vendor &&
+                          /* Sometimes these are cached values */
+                          (conf->subdevice == ss_device ||
+                           conf->subdevice == 0xffff)) {
+                               struct smsc_ircc_subsystem_configuration
+                                       tmpconf;
+
+                               memcpy(&tmpconf, conf,
+                                      sizeof(struct smsc_ircc_subsystem_configuration));
+
+                               /*
+                                * Override the default values with anything
+                                * passed in as parameter
+                                */
+                               if (ircc_cfg != 0)
+                                       tmpconf.cfg_base = ircc_cfg;
+                               if (ircc_fir != 0)
+                                       tmpconf.fir_io = ircc_fir;
+                               if (ircc_sir != 0)
+                                       tmpconf.sir_io = ircc_sir;
+                               if (ircc_dma != 0xff)
+                                       tmpconf.fir_dma = ircc_dma;
+                               if (ircc_irq != 0xff)
+                                       tmpconf.fir_irq = ircc_irq;
+
+                               IRDA_MESSAGE("Detected unconfigured %s SMSC IrDA chip, pre-configuring device.\n", conf->name);
+                               if (conf->preconfigure)
+                                       ret = conf->preconfigure(dev, &tmpconf);
+                               else
+                                       ret = -ENODEV;
+                       }
+               }
+               dev = pci_get_device(PCI_ANY_ID, PCI_ANY_ID, dev);
+       }
+
+       return ret;
+}
+#endif // CONFIG_PCI
+
 /************************************************
  *
  * Transceivers specific functions
index f9f77e4f59650d8ae8ba2a34d1c842b3ade11760..cfd67d812f0db4094fd86d35e205873d0ac5b5e6 100644 (file)
@@ -357,18 +357,20 @@ ixgb_probe(struct pci_dev *pdev,
        if((err = pci_enable_device(pdev)))
                return err;
 
-       if(!(err = pci_set_dma_mask(pdev, DMA_64BIT_MASK))) {
+       if(!(err = pci_set_dma_mask(pdev, DMA_64BIT_MASK)) &&
+          !(err = pci_set_consistent_dma_mask(pdev, DMA_64BIT_MASK))) {
                pci_using_dac = 1;
        } else {
-               if((err = pci_set_dma_mask(pdev, DMA_32BIT_MASK))) {
+               if((err = pci_set_dma_mask(pdev, DMA_32BIT_MASK)) ||
+                  (err = pci_set_consistent_dma_mask(pdev, DMA_32BIT_MASK))) {
                        IXGB_ERR("No usable DMA configuration, aborting\n");
-                       return err;
+                       goto err_dma_mask;
                }
                pci_using_dac = 0;
        }
 
        if((err = pci_request_regions(pdev, ixgb_driver_name)))
-               return err;
+               goto err_request_regions;
 
        pci_set_master(pdev);
 
@@ -502,6 +504,9 @@ err_ioremap:
        free_netdev(netdev);
 err_alloc_etherdev:
        pci_release_regions(pdev);
+err_request_regions:
+err_dma_mask:
+       pci_disable_device(pdev);
        return err;
 }
 
index 9f2661355a4acf3973e55b15d0ba24ba9d112959..ea62a3e7d5860e51f2338b13463c87cf6cfd3656 100644 (file)
@@ -281,10 +281,16 @@ static void mv643xx_eth_tx_timeout_task(struct net_device *dev)
 {
        struct mv643xx_private *mp = netdev_priv(dev);
 
-       netif_device_detach(dev);
+       if (!netif_running(dev))
+               return;
+
+       netif_stop_queue(dev);
+
        eth_port_reset(mp->port_num);
        eth_port_start(dev);
-       netif_device_attach(dev);
+
+       if (mp->tx_ring_size - mp->tx_desc_count >= MAX_DESCS_PER_SKB)
+               netif_wake_queue(dev);
 }
 
 /**
@@ -552,9 +558,9 @@ static irqreturn_t mv643xx_eth_int_handler(int irq, void *dev_id,
 #else
        if (eth_int_cause & ETH_INT_CAUSE_RX)
                mv643xx_eth_receive_queue(dev, INT_MAX);
+#endif
        if (eth_int_cause_ext & ETH_INT_CAUSE_TX)
                mv643xx_eth_free_completed_tx_descs(dev);
-#endif
 
        /*
         * If no real interrupt occured, exit.
@@ -1186,7 +1192,12 @@ static int mv643xx_eth_start_xmit(struct sk_buff *skb, struct net_device *dev)
 
        BUG_ON(netif_queue_stopped(dev));
        BUG_ON(skb == NULL);
-       BUG_ON(mp->tx_ring_size - mp->tx_desc_count < MAX_DESCS_PER_SKB);
+
+       if (mp->tx_ring_size - mp->tx_desc_count < MAX_DESCS_PER_SKB) {
+               printk(KERN_ERR "%s: transmit with queue full\n", dev->name);
+               netif_stop_queue(dev);
+               return 1;
+       }
 
        if (has_tiny_unaligned_frags(skb)) {
                if ((skb_linearize(skb, GFP_ATOMIC) != 0)) {
index 7826afbb9db91e009d1cd8d259f8d50024fe80f8..90627756d6fa47bbe93ce363af1d6ced2307fba4 100644 (file)
@@ -238,7 +238,7 @@ static int full_duplex[MAX_UNITS];
 #define NATSEMI_RX_LIMIT       2046    /* maximum supported by hardware */
 
 /* These identify the driver base version and may not be removed. */
-static char version[] __devinitdata =
+static const char version[] __devinitdata =
   KERN_INFO DRV_NAME " dp8381x driver, version "
       DRV_VERSION ", " DRV_RELDATE "\n"
   KERN_INFO "  originally by Donald Becker <becker@scyld.com>\n"
index 08b218c5bfbc372186f8102a4d112cedde2ea938..93c494bcd18d67beaf035473f37a77dd7c45171b 100644 (file)
@@ -226,7 +226,7 @@ struct net_device * __init ne_probe(int unit)
        netdev_boot_setup_check(dev);
 
 #ifdef CONFIG_TOSHIBA_RBTX4938
-       dev->base_addr = 0x07f20280;
+       dev->base_addr = RBTX4938_RTL_8019_BASE;
        dev->irq = RBTX4938_RTL_8019_IRQ;
 #endif
        err = do_ne_probe(dev);
index 75b35ad760de3cf78fa7b3939a9902c301261731..66e74f7402610f5ac9ad769457f01b5254d1b27e 100644 (file)
@@ -87,6 +87,7 @@ static void write_msg(struct console *con, const char *msg, unsigned int len)
 }
 
 static struct console netconsole = {
+       .name = "netcon",
        .flags = CON_ENABLED | CON_PRINTBUFFER,
        .write = write_msg
 };
index 56233afcb2b3db0334e88a1275c4f8ca41011dbf..448a09488529f59ca3727ce5d89c8ba3903d3c32 100644 (file)
@@ -1560,7 +1560,7 @@ static void ei_receive(struct net_device *dev)
 
 static void ei_rx_overrun(struct net_device *dev)
 {
-       axnet_dev_t *info = (axnet_dev_t *)dev;
+       axnet_dev_t *info = PRIV(dev);
        long e8390_base = dev->base_addr;
        unsigned char was_txing, must_resend = 0;
        struct ei_device *ei_local = (struct ei_device *) netdev_priv(dev);
index 35dbf05c7f063d96ddd56711362938892474f2e1..a70c2b0cc10425c9d0b23ffba57f2c7fa185a86c 100644 (file)
@@ -78,6 +78,8 @@ static const struct pci_device_id skge_id_table[] = {
        { PCI_DEVICE(PCI_VENDOR_ID_SYSKONNECT, PCI_DEVICE_ID_SYSKONNECT_GE) },
        { PCI_DEVICE(PCI_VENDOR_ID_SYSKONNECT, PCI_DEVICE_ID_SYSKONNECT_YU) },
        { PCI_DEVICE(PCI_VENDOR_ID_DLINK, PCI_DEVICE_ID_DLINK_DGE510T), },
+       { PCI_DEVICE(PCI_VENDOR_ID_DLINK, 0x4b00) },
+       { PCI_DEVICE(PCI_VENDOR_ID_DLINK, 0x4b01) },
        { PCI_DEVICE(PCI_VENDOR_ID_MARVELL, 0x4320) },
        { PCI_DEVICE(PCI_VENDOR_ID_MARVELL, 0x5005) }, /* Belkin */
        { PCI_DEVICE(PCI_VENDOR_ID_CNET, PCI_DEVICE_ID_CNET_GIGACARD) },
index 68f9c206a6205d1e35398ff7cf72d62a4f2558c3..67b0eab16589e57e96f473c11937b63a97e31556 100644 (file)
@@ -99,8 +99,6 @@ MODULE_PARM_DESC(disable_msi, "Disable Message Signaled Interrupt (MSI)");
 static const struct pci_device_id sky2_id_table[] = {
        { PCI_DEVICE(PCI_VENDOR_ID_SYSKONNECT, 0x9000) },
        { PCI_DEVICE(PCI_VENDOR_ID_SYSKONNECT, 0x9E00) },
-       { PCI_DEVICE(PCI_VENDOR_ID_DLINK, 0x4b00) },
-       { PCI_DEVICE(PCI_VENDOR_ID_DLINK, 0x4b01) },
        { PCI_DEVICE(PCI_VENDOR_ID_MARVELL, 0x4340) },
        { PCI_DEVICE(PCI_VENDOR_ID_MARVELL, 0x4341) },
        { PCI_DEVICE(PCI_VENDOR_ID_MARVELL, 0x4342) },
@@ -579,8 +577,8 @@ static void sky2_mac_init(struct sky2_hw *hw, unsigned port)
        reg = gma_read16(hw, port, GM_PHY_ADDR);
        gma_write16(hw, port, GM_PHY_ADDR, reg | GM_PAR_MIB_CLR);
 
-       for (i = 0; i < GM_MIB_CNT_SIZE; i++)
-               gma_read16(hw, port, GM_MIB_CNT_BASE + 8 * i);
+       for (i = GM_MIB_CNT_BASE; i <= GM_MIB_CNT_END; i += 4)
+               gma_read16(hw, port, i);
        gma_write16(hw, port, GM_PHY_ADDR, reg);
 
        /* transmit control */
index 62532b4e45c5ea53abf9b308a56365063c0fe74b..89dd18cd12f0b7b74df391f0565a142c3f3c2383 100644 (file)
@@ -1375,7 +1375,7 @@ enum {
        GM_PHY_ADDR     = 0x0088,       /* 16 bit r/w   GPHY Address Register */
 /* MIB Counters */
        GM_MIB_CNT_BASE = 0x0100,       /* Base Address of MIB Counters */
-       GM_MIB_CNT_SIZE = 256,
+       GM_MIB_CNT_END  = 0x025C,       /* Last MIB counter */
 };
 
 
index 45ad036733e2135986b05a985b687b60e8e4cca6..9b7805be21dab116f0dd205efbc7022f6a5feb25 100644 (file)
@@ -335,7 +335,7 @@ do { \
 
 
 /* These identify the driver base version and may not be removed. */
-static char version[] __devinitdata =
+static const char version[] __devinitdata =
 KERN_INFO "starfire.c:v1.03 7/26/2000  Written by Donald Becker <becker@scyld.com>\n"
 KERN_INFO " (unofficial 2.2/2.4 kernel port, version " DRV_VERSION ", " DRV_RELDATE ")\n";
 
index cb0aba95d4e32c56a339c979a24340d3b1954d55..046371ee5bbe25a5d98da69f6ff28612c9dc959d 100644 (file)
@@ -275,7 +275,7 @@ static int bcm5411_init(struct mii_phy* phy)
        return 0;
 }
 
-static int bcm5411_suspend(struct mii_phy* phy)
+static int generic_suspend(struct mii_phy* phy)
 {
        phy_write(phy, MII_BMCR, BMCR_PDOWN);
 
@@ -738,7 +738,7 @@ static struct mii_phy_def bcm5401_phy_def = {
 /* Broadcom BCM 5411 */
 static struct mii_phy_ops bcm5411_phy_ops = {
        .init           = bcm5411_init,
-       .suspend        = bcm5411_suspend,
+       .suspend        = generic_suspend,
        .setup_aneg     = bcm54xx_setup_aneg,
        .setup_forced   = bcm54xx_setup_forced,
        .poll_link      = genmii_poll_link,
@@ -757,7 +757,7 @@ static struct mii_phy_def bcm5411_phy_def = {
 /* Broadcom BCM 5421 */
 static struct mii_phy_ops bcm5421_phy_ops = {
        .init           = bcm5421_init,
-       .suspend        = bcm5411_suspend,
+       .suspend        = generic_suspend,
        .setup_aneg     = bcm54xx_setup_aneg,
        .setup_forced   = bcm54xx_setup_forced,
        .poll_link      = genmii_poll_link,
@@ -776,7 +776,7 @@ static struct mii_phy_def bcm5421_phy_def = {
 /* Broadcom BCM 5421 built-in K2 */
 static struct mii_phy_ops bcm5421k2_phy_ops = {
        .init           = bcm5421_init,
-       .suspend        = bcm5411_suspend,
+       .suspend        = generic_suspend,
        .setup_aneg     = bcm54xx_setup_aneg,
        .setup_forced   = bcm54xx_setup_forced,
        .poll_link      = genmii_poll_link,
@@ -795,7 +795,7 @@ static struct mii_phy_def bcm5421k2_phy_def = {
 /* Broadcom BCM 5462 built-in Vesta */
 static struct mii_phy_ops bcm5462V_phy_ops = {
        .init           = bcm5421_init,
-       .suspend        = bcm5411_suspend,
+       .suspend        = generic_suspend,
        .setup_aneg     = bcm54xx_setup_aneg,
        .setup_forced   = bcm54xx_setup_forced,
        .poll_link      = genmii_poll_link,
@@ -816,6 +816,7 @@ static struct mii_phy_def bcm5462V_phy_def = {
  * would be useful here) --BenH.
  */
 static struct mii_phy_ops marvell_phy_ops = {
+       .suspend        = generic_suspend,
        .setup_aneg     = marvell_setup_aneg,
        .setup_forced   = marvell_setup_forced,
        .poll_link      = genmii_poll_link,
index 0b5358072172a9f0c95d008ea21447aa59ca0595..73e271e59c6a20c4401c3aaef08fb98642787286 100644 (file)
@@ -497,21 +497,20 @@ static void tg3_write_mem(struct tg3 *tp, u32 off, u32 val)
        unsigned long flags;
 
        spin_lock_irqsave(&tp->indirect_lock, flags);
-       pci_write_config_dword(tp->pdev, TG3PCI_MEM_WIN_BASE_ADDR, off);
-       pci_write_config_dword(tp->pdev, TG3PCI_MEM_WIN_DATA, val);
+       if (tp->tg3_flags & TG3_FLAG_SRAM_USE_CONFIG) {
+               pci_write_config_dword(tp->pdev, TG3PCI_MEM_WIN_BASE_ADDR, off);
+               pci_write_config_dword(tp->pdev, TG3PCI_MEM_WIN_DATA, val);
 
-       /* Always leave this as zero. */
-       pci_write_config_dword(tp->pdev, TG3PCI_MEM_WIN_BASE_ADDR, 0);
-       spin_unlock_irqrestore(&tp->indirect_lock, flags);
-}
+               /* Always leave this as zero. */
+               pci_write_config_dword(tp->pdev, TG3PCI_MEM_WIN_BASE_ADDR, 0);
+       } else {
+               tw32_f(TG3PCI_MEM_WIN_BASE_ADDR, off);
+               tw32_f(TG3PCI_MEM_WIN_DATA, val);
 
-static void tg3_write_mem_fast(struct tg3 *tp, u32 off, u32 val)
-{
-       /* If no workaround is needed, write to mem space directly */
-       if (tp->write32 != tg3_write_indirect_reg32)
-               tw32(NIC_SRAM_WIN_BASE + off, val);
-       else
-               tg3_write_mem(tp, off, val);
+               /* Always leave this as zero. */
+               tw32_f(TG3PCI_MEM_WIN_BASE_ADDR, 0);
+       }
+       spin_unlock_irqrestore(&tp->indirect_lock, flags);
 }
 
 static void tg3_read_mem(struct tg3 *tp, u32 off, u32 *val)
@@ -519,11 +518,19 @@ static void tg3_read_mem(struct tg3 *tp, u32 off, u32 *val)
        unsigned long flags;
 
        spin_lock_irqsave(&tp->indirect_lock, flags);
-       pci_write_config_dword(tp->pdev, TG3PCI_MEM_WIN_BASE_ADDR, off);
-       pci_read_config_dword(tp->pdev, TG3PCI_MEM_WIN_DATA, val);
+       if (tp->tg3_flags & TG3_FLAG_SRAM_USE_CONFIG) {
+               pci_write_config_dword(tp->pdev, TG3PCI_MEM_WIN_BASE_ADDR, off);
+               pci_read_config_dword(tp->pdev, TG3PCI_MEM_WIN_DATA, val);
 
-       /* Always leave this as zero. */
-       pci_write_config_dword(tp->pdev, TG3PCI_MEM_WIN_BASE_ADDR, 0);
+               /* Always leave this as zero. */
+               pci_write_config_dword(tp->pdev, TG3PCI_MEM_WIN_BASE_ADDR, 0);
+       } else {
+               tw32_f(TG3PCI_MEM_WIN_BASE_ADDR, off);
+               *val = tr32(TG3PCI_MEM_WIN_DATA);
+
+               /* Always leave this as zero. */
+               tw32_f(TG3PCI_MEM_WIN_BASE_ADDR, 0);
+       }
        spin_unlock_irqrestore(&tp->indirect_lock, flags);
 }
 
@@ -1367,12 +1374,12 @@ static int tg3_set_power_state(struct tg3 *tp, pci_power_t state)
                }
        }
 
+       tg3_write_sig_post_reset(tp, RESET_KIND_SHUTDOWN);
+
        /* Finally, set the new power state. */
        pci_write_config_word(tp->pdev, pm + PCI_PM_CTRL, power_control);
        udelay(100);    /* Delay after power state change */
 
-       tg3_write_sig_post_reset(tp, RESET_KIND_SHUTDOWN);
-
        return 0;
 }
 
@@ -5828,10 +5835,14 @@ static int tg3_reset_hw(struct tg3 *tp)
                          GRC_MODE_NO_TX_PHDR_CSUM |
                          GRC_MODE_NO_RX_PHDR_CSUM);
        tp->grc_mode |= GRC_MODE_HOST_SENDBDS;
-       if (tp->tg3_flags & TG3_FLAG_NO_TX_PSEUDO_CSUM)
-               tp->grc_mode |= GRC_MODE_NO_TX_PHDR_CSUM;
-       if (tp->tg3_flags & TG3_FLAG_NO_RX_PSEUDO_CSUM)
-               tp->grc_mode |= GRC_MODE_NO_RX_PHDR_CSUM;
+
+       /* Pseudo-header checksum is done by hardware logic and not
+        * the offload processers, so make the chip do the pseudo-
+        * header checksums on receive.  For transmit it is more
+        * convenient to do the pseudo-header checksum in software
+        * as Linux does that on transmit for us in all cases.
+        */
+       tp->grc_mode |= GRC_MODE_NO_TX_PHDR_CSUM;
 
        tw32(GRC_MODE,
             tp->grc_mode |
@@ -6535,11 +6546,11 @@ static void tg3_timer(unsigned long __opaque)
                if (tp->tg3_flags & TG3_FLAG_ENABLE_ASF) {
                        u32 val;
 
-                       tg3_write_mem_fast(tp, NIC_SRAM_FW_CMD_MBOX,
-                                          FWCMD_NICDRV_ALIVE2);
-                       tg3_write_mem_fast(tp, NIC_SRAM_FW_CMD_LEN_MBOX, 4);
+                       tg3_write_mem(tp, NIC_SRAM_FW_CMD_MBOX,
+                                     FWCMD_NICDRV_ALIVE2);
+                       tg3_write_mem(tp, NIC_SRAM_FW_CMD_LEN_MBOX, 4);
                        /* 5 seconds timeout */
-                       tg3_write_mem_fast(tp, NIC_SRAM_FW_CMD_DATA_MBOX, 5);
+                       tg3_write_mem(tp, NIC_SRAM_FW_CMD_DATA_MBOX, 5);
                        val = tr32(GRC_RX_CPU_EVENT);
                        val |= (1 << 14);
                        tw32(GRC_RX_CPU_EVENT, val);
@@ -8034,9 +8045,13 @@ static int tg3_test_nvram(struct tg3 *tp)
                for (i = 0; i < size; i++)
                        csum8 += buf8[i];
 
-               if (csum8 == 0)
-                       return 0;
-               return -EIO;
+               if (csum8 == 0) {
+                       err = 0;
+                       goto out;
+               }
+
+               err = -EIO;
+               goto out;
        }
 
        /* Bootstrap checksum at offset 0x10 */
@@ -9531,8 +9546,11 @@ static void __devinit tg3_get_eeprom_hw_cfg(struct tg3 *tp)
        tp->led_ctrl = LED_CTRL_MODE_PHY_1;
 
        /* Do not even try poking around in here on Sun parts.  */
-       if (tp->tg3_flags2 & TG3_FLG2_SUN_570X)
+       if (tp->tg3_flags2 & TG3_FLG2_SUN_570X) {
+               /* All SUN chips are built-in LOMs. */
+               tp->tg3_flags |= TG3_FLAG_EEPROM_WRITE_PROT;
                return;
+       }
 
        tg3_read_mem(tp, NIC_SRAM_DATA_SIG, &val);
        if (val == NIC_SRAM_DATA_SIG_MAGIC) {
@@ -9630,9 +9648,7 @@ static void __devinit tg3_get_eeprom_hw_cfg(struct tg3 *tp)
                    tp->pdev->subsystem_vendor == PCI_VENDOR_ID_DELL)
                        tp->led_ctrl = LED_CTRL_MODE_PHY_2;
 
-               if ((GET_ASIC_REV(tp->pci_chip_rev_id) != ASIC_REV_5700) &&
-                   (GET_ASIC_REV(tp->pci_chip_rev_id) != ASIC_REV_5701) &&
-                   (nic_cfg & NIC_SRAM_DATA_CFG_EEPROM_WP))
+               if (nic_cfg & NIC_SRAM_DATA_CFG_EEPROM_WP)
                        tp->tg3_flags |= TG3_FLAG_EEPROM_WRITE_PROT;
 
                if (nic_cfg & NIC_SRAM_DATA_CFG_ASF_ENABLE) {
@@ -10257,6 +10273,13 @@ static int __devinit tg3_get_invariants(struct tg3 *tp)
                pci_write_config_word(tp->pdev, PCI_COMMAND, pci_cmd);
        }
 
+       if (tp->write32 == tg3_write_indirect_reg32 ||
+           ((tp->tg3_flags & TG3_FLAG_PCIX_MODE) &&
+            (GET_ASIC_REV(tp->pci_chip_rev_id) == ASIC_REV_5700 ||
+             GET_ASIC_REV(tp->pci_chip_rev_id) == ASIC_REV_5701)) ||
+           (tp->tg3_flags2 & TG3_FLG2_SUN_570X))
+               tp->tg3_flags |= TG3_FLAG_SRAM_USE_CONFIG;
+
        /* Get eeprom hw config before calling tg3_set_power_state().
         * In particular, the TG3_FLAG_EEPROM_WRITE_PROT flag must be
         * determined before calling tg3_set_power_state() so that
@@ -10299,15 +10322,6 @@ static int __devinit tg3_get_invariants(struct tg3 *tp)
        if (tp->pci_chip_rev_id == CHIPREV_ID_5700_B0)
                tp->tg3_flags |= TG3_FLAG_BROKEN_CHECKSUMS;
 
-       /* Pseudo-header checksum is done by hardware logic and not
-        * the offload processers, so make the chip do the pseudo-
-        * header checksums on receive.  For transmit it is more
-        * convenient to do the pseudo-header checksum in software
-        * as Linux does that on transmit for us in all cases.
-        */
-       tp->tg3_flags |= TG3_FLAG_NO_TX_PSEUDO_CSUM;
-       tp->tg3_flags &= ~TG3_FLAG_NO_RX_PSEUDO_CSUM;
-
        /* Derive initial jumbo mode from MTU assigned in
         * ether_setup() via the alloc_etherdev() call
         */
index c43cc3264202593e6c15a4180e05053a5247b1c1..8c8b987d12508d521ed14d391ee1defc64a9d655 100644 (file)
@@ -2171,8 +2171,7 @@ struct tg3 {
 #define TG3_FLAG_PCIX_MODE             0x00020000
 #define TG3_FLAG_PCI_HIGH_SPEED                0x00040000
 #define TG3_FLAG_PCI_32BIT             0x00080000
-#define TG3_FLAG_NO_TX_PSEUDO_CSUM     0x00100000
-#define TG3_FLAG_NO_RX_PSEUDO_CSUM     0x00200000
+#define TG3_FLAG_SRAM_USE_CONFIG       0x00100000
 #define TG3_FLAG_SERDES_WOL_CAP                0x00400000
 #define TG3_FLAG_JUMBO_RING_ENABLE     0x00800000
 #define TG3_FLAG_10_100_ONLY           0x01000000
index c1ce87a5f8d3aacc01373cf122f0cec850a67570..d9258d42090c30e93fa56a3e1cab1be0d739d375 100644 (file)
@@ -134,7 +134,7 @@ static const int multicast_filter_limit = 32;
 #include "typhoon.h"
 #include "typhoon-firmware.h"
 
-static char version[] __devinitdata =
+static const char version[] __devinitdata =
     "typhoon.c: version " DRV_MODULE_VERSION " (" DRV_MODULE_RELDATE ")\n";
 
 MODULE_AUTHOR("David Dillow <dave@thedillows.org>");
index a9b2150909d60f03c42690a2ddb645d0d87dd17d..6a23964c1317469f35200dc8d0a1deb3f654e15d 100644 (file)
@@ -469,7 +469,7 @@ struct rhine_private {
        struct sk_buff *tx_skbuff[TX_RING_SIZE];
        dma_addr_t tx_skbuff_dma[TX_RING_SIZE];
 
-       /* Tx bounce buffers */
+       /* Tx bounce buffers (Rhine-I only) */
        unsigned char *tx_buf[TX_RING_SIZE];
        unsigned char *tx_bufs;
        dma_addr_t tx_bufs_dma;
@@ -1043,7 +1043,8 @@ static void alloc_tbufs(struct net_device* dev)
                rp->tx_ring[i].desc_length = cpu_to_le32(TXDESC);
                next += sizeof(struct tx_desc);
                rp->tx_ring[i].next_desc = cpu_to_le32(next);
-               rp->tx_buf[i] = &rp->tx_bufs[i * PKT_BUF_SZ];
+               if (rp->quirks & rqRhineI)
+                       rp->tx_buf[i] = &rp->tx_bufs[i * PKT_BUF_SZ];
        }
        rp->tx_ring[i-1].next_desc = cpu_to_le32(rp->tx_ring_dma);
 
@@ -1091,7 +1092,7 @@ static void rhine_check_media(struct net_device *dev, unsigned int init_media)
 }
 
 /* Called after status of force_media possibly changed */
-void rhine_set_carrier(struct mii_if_info *mii)
+static void rhine_set_carrier(struct mii_if_info *mii)
 {
        if (mii->force_media) {
                /* autoneg is off: Link is always assumed to be up */
index 883cf7da10fcb0f41ab9e4f5fd16626213f7a620..b5328b0ff927d6b063815a81aea7c388b2241e58 100644 (file)
@@ -410,103 +410,6 @@ config WAN_ROUTER_DRIVERS
 
          If unsure, say N.
 
-config VENDOR_SANGOMA
-       tristate "Sangoma WANPIPE(tm) multiprotocol cards"
-       depends on WAN_ROUTER_DRIVERS && WAN_ROUTER && (PCI || ISA) && BROKEN
-       ---help---
-         Driver for S514-PCI/ISA Synchronous Data Link Adapters (SDLA).
-
-         WANPIPE from Sangoma Technologies Inc. <http://www.sangoma.com/>
-         is a family of intelligent multiprotocol WAN adapters with data
-         transfer rates up to 4Mbps. Cards support:
-
-         - X.25, Frame Relay, PPP, Cisco HDLC protocols.
-
-         - API for protocols like HDLC (LAPB), HDLC Streaming, X.25,
-         Frame Relay and BiSync.
-
-         - Ethernet Bridging over Frame Relay protocol.
-
-         - MULTILINK PPP
-
-         - Async PPP (Modem Dialup)
-
-         The next questions will ask you about the protocols you want
-         the driver to support.
-
-         If you have one or more of these cards, say M to this option;
-         and read <file:Documentation/networking/wan-router.txt>.
-
-         To compile this driver as a module, choose M here: the
-         module will be called wanpipe.
-
-config WANPIPE_CHDLC
-       bool "WANPIPE Cisco HDLC support"
-       depends on VENDOR_SANGOMA
-       ---help---
-         Connect a WANPIPE card to a leased line using the Cisco HDLC.
-
-         - Supports Dual Port Cisco HDLC on the S514-PCI/S508-ISA cards
-         which allows user to build applications using the HDLC streaming API.
-
-         - CHDLC Streaming MULTILINK PPP that can bind multiple WANPIPE T1
-         cards into a single logical channel.
-
-         Say Y and the Cisco HDLC support, HDLC streaming API and
-         MULTILINK PPP will be included in the driver.
-
-config WANPIPE_FR
-       bool "WANPIPE Frame Relay support"
-       depends on VENDOR_SANGOMA
-       help
-         Connect a WANPIPE card to a Frame Relay network, or use Frame Relay
-         API to develop custom applications.
-
-         Contains the Ethernet Bridging over Frame Relay feature, where
-         a WANPIPE frame relay link can be directly connected to the Linux
-         kernel bridge. The Frame Relay option is supported on S514-PCI
-         and S508-ISA cards.
-
-         Say Y and the Frame Relay support will be included in the driver.
-
-config WANPIPE_X25
-       bool "WANPIPE X.25 support"
-       depends on VENDOR_SANGOMA
-       help
-         Connect a WANPIPE card to an X.25 network.
-
-         Includes the X.25 API support for custom applications over the
-         X.25 protocol. The X.25 option is supported on S514-PCI and
-         S508-ISA cards.
-
-         Say Y and the X.25 support will be included in the driver.
-
-config WANPIPE_PPP
-       bool "WANPIPE PPP support"
-       depends on VENDOR_SANGOMA
-       help
-         Connect a WANPIPE card to a leased line using Point-to-Point
-         Protocol (PPP).
-
-         The PPP option is supported on S514-PCI/S508-ISA cards.
-
-         Say Y and the PPP support will be included in the driver.
-
-config WANPIPE_MULTPPP
-       bool "WANPIPE Multi-Port PPP support"
-       depends on VENDOR_SANGOMA
-       help
-         Connect a WANPIPE card to a leased line using Point-to-Point
-         Protocol (PPP).
-
-         Uses in-kernel SyncPPP protocol over the Sangoma HDLC Streaming
-         adapter. In this case each Sangoma adapter port can support an
-         independent PPP connection. For example, a single Quad-Port PCI
-         adapter can support up to four independent PPP links. The PPP
-         option is supported on S514-PCI/S508-ISA cards.
-
-         Say Y and the Multi-Port PPP support will be included in the driver.
-
 config CYCLADES_SYNC
        tristate "Cyclom 2X(tm) cards (EXPERIMENTAL)"
        depends on WAN_ROUTER_DRIVERS && (PCI || ISA)
index ce6c56b903e797b49e9de9c343a826533aa329eb..823c6d5ab90d8e0143ed2266d29e769bf04cd06c 100644 (file)
@@ -5,14 +5,6 @@
 # Rewritten to use lists instead of if-statements.
 #
 
-wanpipe-y                      := sdlamain.o sdla_ft1.o
-wanpipe-$(CONFIG_WANPIPE_X25)  += sdla_x25.o
-wanpipe-$(CONFIG_WANPIPE_FR)   += sdla_fr.o
-wanpipe-$(CONFIG_WANPIPE_CHDLC)        += sdla_chdlc.o
-wanpipe-$(CONFIG_WANPIPE_PPP)  += sdla_ppp.o
-wanpipe-$(CONFIG_WANPIPE_MULTPPP) += wanpipe_multppp.o
-wanpipe-objs                   := $(wanpipe-y)
-
 cyclomx-y                       := cycx_main.o
 cyclomx-$(CONFIG_CYCLOMX_X25)  += cycx_x25.o
 cyclomx-objs                   := $(cyclomx-y)  
@@ -43,11 +35,6 @@ obj-$(CONFIG_LANMEDIA)               += lmc/
 
 obj-$(CONFIG_DLCI)             += dlci.o 
 obj-$(CONFIG_SDLA)             += sdla.o
-ifeq ($(CONFIG_WANPIPE_MULTPPP),y)
-  obj-$(CONFIG_VENDOR_SANGOMA) += sdladrv.o wanpipe.o syncppp.o        
-else
-  obj-$(CONFIG_VENDOR_SANGOMA) += sdladrv.o wanpipe.o
-endif
 obj-$(CONFIG_CYCLADES_SYNC)    += cycx_drv.o cyclomx.o
 obj-$(CONFIG_LAPBETHER)                += lapbether.o
 obj-$(CONFIG_SBNI)             += sbni.o
diff --git a/drivers/net/wan/sdla_chdlc.c b/drivers/net/wan/sdla_chdlc.c
deleted file mode 100644 (file)
index 496d292..0000000
+++ /dev/null
@@ -1,4428 +0,0 @@
-/*****************************************************************************
-* sdla_chdlc.c WANPIPE(tm) Multiprotocol WAN Link Driver. Cisco HDLC module.
-*
-* Authors:     Nenad Corbic <ncorbic@sangoma.com>
-*              Gideon Hack  
-*
-* Copyright:   (c) 1995-2001 Sangoma Technologies Inc.
-*
-*              This program is free software; you can redistribute it and/or
-*              modify it under the terms of the GNU General Public License
-*              as published by the Free Software Foundation; either version
-*              2 of the License, or (at your option) any later version.
-* ============================================================================
-* Feb 28, 2001  Nenad Corbic   Updated if_tx_timeout() routine for 
-*                              2.4.X kernels.
-* Jan 25, 2001  Nenad Corbic   Added a TTY Sync serial driver over the
-*                              HDLC streaming protocol
-*                              Added a TTY Async serial driver over the
-*                              Async protocol.
-* Dec 15, 2000  Nenad Corbic    Updated for 2.4.X Kernel support
-* Nov 13, 2000  Nenad Corbic    Added true interface type encoding option.
-*                              Tcpdump doesn't support CHDLC inteface
-*                              types, to fix this "true type" option will set
-*                              the interface type to RAW IP mode.
-* Nov 07, 2000  Nenad Corbic   Added security features for UDP debugging:
-*                               Deny all and specify allowed requests.
-* Jun 20, 2000  Nenad Corbic   Fixed the API IP ERROR bug. Caused by the 
-*                               latest update.
-* May 09, 2000 Nenad Corbic    Option to bring down an interface
-*                               upon disconnect.
-* Mar 23, 2000  Nenad Corbic   Improved task queue, bh handling.
-* Mar 16, 2000 Nenad Corbic    Fixed the SLARP Dynamic IP addressing.
-* Mar 06, 2000  Nenad Corbic   Bug Fix: corrupted mbox recovery.
-* Feb 10, 2000  Gideon Hack     Added ASYNC support.
-* Feb 09, 2000  Nenad Corbic    Fixed two shutdown bugs in update() and
-*                               if_stats() functions.
-* Jan 24, 2000  Nenad Corbic    Fixed a startup wanpipe state racing,  
-*                               condition between if_open and isr. 
-* Jan 10, 2000  Nenad Corbic    Added new socket API support.
-* Dev 15, 1999  Nenad Corbic    Fixed up header files for 2.0.X kernels
-* Nov 20, 1999  Nenad Corbic   Fixed zero length API bug.
-* Sep 30, 1999  Nenad Corbic    Fixed dynamic IP and route setup.
-* Sep 23, 1999  Nenad Corbic    Added SMP support, fixed tracing 
-* Sep 13, 1999  Nenad Corbic   Split up Port 0 and 1 into separate devices.
-* Jun 02, 1999  Gideon Hack     Added support for the S514 adapter.
-* Oct 30, 1998 Jaspreet Singh  Added Support for CHDLC API (HDLC STREAMING).
-* Oct 28, 1998 Jaspreet Singh  Added Support for Dual Port CHDLC.
-* Aug 07, 1998 David Fong      Initial version.
-*****************************************************************************/
-
-#include <linux/module.h>
-#include <linux/kernel.h>      /* printk(), and other useful stuff */
-#include <linux/stddef.h>      /* offsetof(), etc. */
-#include <linux/errno.h>       /* return codes */
-#include <linux/string.h>      /* inline memset(), etc. */
-#include <linux/slab.h>        /* kmalloc(), kfree() */
-#include <linux/wanrouter.h>   /* WAN router definitions */
-#include <linux/wanpipe.h>     /* WANPIPE common user API definitions */
-#include <linux/if_arp.h>      /* ARPHRD_* defines */
-
-
-#include <asm/uaccess.h>
-#include <linux/inetdevice.h>
-#include <linux/netdevice.h>
-
-#include <linux/in.h>          /* sockaddr_in */
-#include <linux/inet.h>        
-#include <linux/if.h>
-#include <asm/byteorder.h>     /* htons(), etc. */
-#include <linux/sdlapci.h>
-#include <asm/io.h>
-
-#include <linux/sdla_chdlc.h>          /* CHDLC firmware API definitions */
-#include <linux/sdla_asy.h>            /* CHDLC (async) API definitions */
-
-#include <linux/if_wanpipe_common.h>    /* Socket Driver common area */
-#include <linux/if_wanpipe.h>          
-
-/* TTY Includes */
-#include <linux/tty.h>
-#include <linux/tty_flip.h>
-#include <linux/serial.h>
-
-
-/****** Defines & Macros ****************************************************/
-
-/* reasons for enabling the timer interrupt on the adapter */
-#define TMR_INT_ENABLED_UDP            0x01
-#define TMR_INT_ENABLED_UPDATE         0x02
-#define TMR_INT_ENABLED_CONFIG         0x10
-
-#define MAX_IP_ERRORS  10
-
-#define TTY_CHDLC_MAX_MTU      2000
-#define        CHDLC_DFLT_DATA_LEN     1500            /* default MTU */
-#define CHDLC_HDR_LEN          1
-
-#define CHDLC_API 0x01
-
-#define PORT(x)   (x == 0 ? "PRIMARY" : "SECONDARY" )
-#define MAX_BH_BUFF    10
-
-//#define PRINT_DEBUG
-#ifdef PRINT_DEBUG
-#define dbg_printk(format, a...) printk(format, ## a)
-#else
-#define dbg_printk(format, a...)
-#endif  
-
-/******Data Structures*****************************************************/
-
-/* This structure is placed in the private data area of the device structure.
- * The card structure used to occupy the private area but now the following 
- * structure will incorporate the card structure along with CHDLC specific data
- */
-
-typedef struct chdlc_private_area
-{
-       wanpipe_common_t common;
-       sdla_t          *card;
-       int             TracingEnabled;         /* For enabling Tracing */
-       unsigned long   curr_trace_addr;        /* Used for Tracing */
-       unsigned long   start_trace_addr;
-       unsigned long   end_trace_addr;
-       unsigned long   base_addr_trace_buffer;
-       unsigned long   end_addr_trace_buffer;
-       unsigned short  number_trace_elements;
-       unsigned        available_buffer_space;
-       unsigned long   router_start_time;
-       unsigned char   route_status;
-       unsigned char   route_removed;
-       unsigned long   tick_counter;           /* For 5s timeout counter */
-       unsigned long   router_up_time;
-        u32             IP_address;            /* IP addressing */
-        u32             IP_netmask;
-       u32             ip_local;
-       u32             ip_remote;
-       u32             ip_local_tmp;
-       u32             ip_remote_tmp;
-       u8              ip_error;
-       u8              config_chdlc;
-       u8              config_chdlc_timeout;
-       unsigned char  mc;                      /* Mulitcast support on/off */
-       unsigned short udp_pkt_lgth;            /* udp packet processing */
-       char udp_pkt_src;
-       char udp_pkt_data[MAX_LGTH_UDP_MGNT_PKT];
-       unsigned short timer_int_enabled;
-       char update_comms_stats;                /* updating comms stats */
-
-       bh_data_t *bh_head;               /* Circular buffer for chdlc_bh */
-       unsigned long  tq_working;
-       volatile int  bh_write;
-       volatile int  bh_read;
-       atomic_t  bh_buff_used;
-       
-       unsigned char interface_down;
-
-       /* Polling work queue entry. Each interface
-         * has its own work queue entry, which is used
-         * to defer events from the interrupt */
-       struct work_struct poll_work;
-       struct timer_list poll_delay_timer;
-
-       u8 gateway;
-       u8 true_if_encoding;
-       //FIXME: add driver stats as per frame relay!
-
-} chdlc_private_area_t;
-
-/* Route Status options */
-#define NO_ROUTE       0x00
-#define ADD_ROUTE      0x01
-#define ROUTE_ADDED    0x02
-#define REMOVE_ROUTE   0x03
-
-
-/* variable for keeping track of enabling/disabling FT1 monitor status */
-static int rCount = 0;
-
-/* variable for tracking how many interfaces to open for WANPIPE on the
-   two ports */
-
-extern void disable_irq(unsigned int);
-extern void enable_irq(unsigned int);
-
-/****** Function Prototypes *************************************************/
-/* WAN link driver entry points. These are called by the WAN router module. */
-static int update(struct wan_device* wandev);
-static int new_if(struct wan_device* wandev, struct net_device* dev,
-                 wanif_conf_t* conf);
-
-/* Network device interface */
-static int if_init(struct net_device* dev);
-static int if_open(struct net_device* dev);
-static int if_close(struct net_device* dev);
-static int if_header(struct sk_buff* skb, struct net_device* dev,
-                    unsigned short type, void* daddr, void* saddr,
-                    unsigned len);
-
-static int if_rebuild_hdr (struct sk_buff *skb);
-static struct net_device_stats* if_stats(struct net_device* dev);
-  
-static int if_send(struct sk_buff* skb, struct net_device* dev);
-
-/* CHDLC Firmware interface functions */
-static int chdlc_configure     (sdla_t* card, void* data);
-static int chdlc_comm_enable   (sdla_t* card);
-static int chdlc_read_version  (sdla_t* card, char* str);
-static int chdlc_set_intr_mode         (sdla_t* card, unsigned mode);
-static int chdlc_send (sdla_t* card, void* data, unsigned len);
-static int chdlc_read_comm_err_stats (sdla_t* card);
-static int chdlc_read_op_stats (sdla_t* card);
-static int chdlc_error (sdla_t *card, int err, CHDLC_MAILBOX_STRUCT *mb);
-
-
-static int chdlc_disable_comm_shutdown (sdla_t *card);
-static void if_tx_timeout(struct net_device *dev);
-
-/* Miscellaneous CHDLC Functions */
-static int set_chdlc_config (sdla_t* card);
-static void init_chdlc_tx_rx_buff( sdla_t* card);
-static int process_chdlc_exception(sdla_t *card);
-static int process_global_exception(sdla_t *card);
-static int update_comms_stats(sdla_t* card,
-        chdlc_private_area_t* chdlc_priv_area);
-static int configure_ip (sdla_t* card);
-static int unconfigure_ip (sdla_t* card);
-static void process_route(sdla_t *card);
-static void port_set_state (sdla_t *card, int);
-static int config_chdlc (sdla_t *card);
-static void disable_comm (sdla_t *card);
-
-static void trigger_chdlc_poll(struct net_device *dev);
-static void chdlc_poll(struct net_device *dev);
-static void chdlc_poll_delay (unsigned long dev_ptr);
-
-
-/* Miscellaneous asynchronous interface Functions */
-static int set_asy_config (sdla_t* card);
-static int asy_comm_enable (sdla_t* card);
-
-/* Interrupt handlers */
-static void wpc_isr (sdla_t* card);
-static void rx_intr (sdla_t* card);
-static void timer_intr(sdla_t *);
-
-/* Bottom half handlers */
-static void chdlc_work(struct net_device *dev);
-static int chdlc_work_cleanup(struct net_device *dev);
-static int bh_enqueue(struct net_device *dev, struct sk_buff *skb);
-
-/* Miscellaneous functions */
-static int chk_bcast_mcast_addr(sdla_t* card, struct net_device* dev,
-                               struct sk_buff *skb);
-static int reply_udp( unsigned char *data, unsigned int mbox_len );
-static int intr_test( sdla_t* card);
-static int udp_pkt_type( struct sk_buff *skb , sdla_t* card);
-static int store_udp_mgmt_pkt(char udp_pkt_src, sdla_t* card,
-                                struct sk_buff *skb, struct net_device* dev,
-                                chdlc_private_area_t* chdlc_priv_area);
-static int process_udp_mgmt_pkt(sdla_t* card, struct net_device* dev,  
-                               chdlc_private_area_t* chdlc_priv_area);
-static unsigned short calc_checksum (char *, int);
-static void s508_lock (sdla_t *card, unsigned long *smp_flags);
-static void s508_unlock (sdla_t *card, unsigned long *smp_flags);
-
-
-static int  Intr_test_counter;
-
-/* TTY Global Definitions */
-
-#define NR_PORTS 4
-#define WAN_TTY_MAJOR 226
-#define WAN_TTY_MINOR 0
-
-#define WAN_CARD(port) (tty_card_map[port])
-#define MIN_PORT 0
-#define MAX_PORT NR_PORTS-1 
-
-#define CRC_LENGTH 2
-
-static int wanpipe_tty_init(sdla_t *card);
-static void wanpipe_tty_receive(sdla_t *, unsigned, unsigned int);
-static void wanpipe_tty_trigger_poll(sdla_t *card);
-
-static struct tty_driver serial_driver;
-static int tty_init_cnt=0;
-
-static struct serial_state rs_table[NR_PORTS];
-
-static char tty_driver_mode=WANOPT_TTY_SYNC;
-
-static char *opt_decode[] = {"NONE","CRTSCTS","XONXOFF-RX",
-                            "CRTSCTS XONXOFF-RX","XONXOFF-TX",
-                            "CRTSCTS XONXOFF-TX","CRTSCTS XONXOFF"};
-static char *p_decode[] = {"NONE","ODD","EVEN"};
-
-static void* tty_card_map[NR_PORTS] = {NULL,NULL,NULL,NULL};
-
-
-/****** Public Functions ****************************************************/
-
-/*============================================================================
- * Cisco HDLC protocol initialization routine.
- *
- * This routine is called by the main WANPIPE module during setup.  At this
- * point adapter is completely initialized and firmware is running.
- *  o read firmware version (to make sure it's alive)
- *  o configure adapter
- *  o initialize protocol-specific fields of the adapter data space.
- *
- * Return:     0       o.k.
- *             < 0     failure.
- */
-int wpc_init (sdla_t* card, wandev_conf_t* conf)
-{
-       unsigned char port_num;
-       int err;
-       unsigned long max_permitted_baud = 0;
-       SHARED_MEMORY_INFO_STRUCT *flags;
-
-       union
-               {
-               char str[80];
-               } u;
-       volatile CHDLC_MAILBOX_STRUCT* mb;
-       CHDLC_MAILBOX_STRUCT* mb1;
-       unsigned long timeout;
-
-       /* Verify configuration ID */
-       if (conf->config_id != WANCONFIG_CHDLC) {
-               printk(KERN_INFO "%s: invalid configuration ID %u!\n",
-                                 card->devname, conf->config_id);
-               return -EINVAL;
-       }
-
-       /* Find out which Port to use */
-       if ((conf->comm_port == WANOPT_PRI) || (conf->comm_port == WANOPT_SEC)){
-               if (card->next){
-
-                       if (conf->comm_port != card->next->u.c.comm_port){
-                               card->u.c.comm_port = conf->comm_port;
-                       }else{
-                               printk(KERN_INFO "%s: ERROR - %s port used!\n",
-                                       card->wandev.name, PORT(conf->comm_port));
-                               return -EINVAL;
-                       }
-               }else{
-                       card->u.c.comm_port = conf->comm_port;
-               }
-       }else{
-               printk(KERN_INFO "%s: ERROR - Invalid Port Selected!\n",
-                                       card->wandev.name);
-               return -EINVAL;
-       }
-       
-
-       /* Initialize protocol-specific fields */
-       if(card->hw.type != SDLA_S514){
-
-               if (card->u.c.comm_port == WANOPT_PRI){ 
-                       card->mbox  = (void *) card->hw.dpmbase;
-               }else{
-                       card->mbox  = (void *) card->hw.dpmbase + 
-                               SEC_BASE_ADDR_MB_STRUCT - PRI_BASE_ADDR_MB_STRUCT;
-               }       
-       }else{ 
-               /* for a S514 adapter, set a pointer to the actual mailbox in the */
-               /* allocated virtual memory area */
-               if (card->u.c.comm_port == WANOPT_PRI){
-                       card->mbox = (void *) card->hw.dpmbase + PRI_BASE_ADDR_MB_STRUCT;
-               }else{
-                       card->mbox = (void *) card->hw.dpmbase + SEC_BASE_ADDR_MB_STRUCT;
-               }       
-       }
-
-       mb = mb1 = card->mbox;
-
-       if (!card->configured){
-
-               /* The board will place an 'I' in the return code to indicate that it is
-               ready to accept commands.  We expect this to be completed in less
-               than 1 second. */
-
-               timeout = jiffies;
-               while (mb->return_code != 'I')  /* Wait 1s for board to initialize */
-                       if ((jiffies - timeout) > 1*HZ) break;
-
-               if (mb->return_code != 'I') {
-                       printk(KERN_INFO
-                               "%s: Initialization not completed by adapter\n",
-                               card->devname);
-                       printk(KERN_INFO "Please contact Sangoma representative.\n");
-                       return -EIO;
-               }
-       }
-
-       /* Read firmware version.  Note that when adapter initializes, it
-        * clears the mailbox, so it may appear that the first command was
-        * executed successfully when in fact it was merely erased. To work
-        * around this, we execute the first command twice.
-        */
-
-       if (chdlc_read_version(card, u.str))
-               return -EIO;
-
-       printk(KERN_INFO "%s: Running Cisco HDLC firmware v%s\n",
-               card->devname, u.str); 
-
-       card->isr                       = &wpc_isr;
-       card->poll                      = NULL;
-       card->exec                      = NULL;
-       card->wandev.update             = &update;
-       card->wandev.new_if             = &new_if;
-       card->wandev.del_if             = NULL;
-       card->wandev.udp_port           = conf->udp_port;
-       card->disable_comm              = &disable_comm;
-       card->wandev.new_if_cnt = 0;
-
-       /* reset the number of times the 'update()' proc has been called */
-       card->u.c.update_call_count = 0;
-       
-       card->wandev.ttl = conf->ttl;
-       card->wandev.interface = conf->interface; 
-
-       if ((card->u.c.comm_port == WANOPT_SEC && conf->interface == WANOPT_V35)&&
-           card->hw.type != SDLA_S514){
-               printk(KERN_INFO "%s: ERROR - V35 Interface not supported on S508 %s port \n",
-                       card->devname, PORT(card->u.c.comm_port));
-               return -EIO;
-       }
-
-       card->wandev.clocking = conf->clocking;
-
-       port_num = card->u.c.comm_port;
-
-       /* in API mode, we can configure for "receive only" buffering */
-       if(card->hw.type == SDLA_S514) {
-               card->u.c.receive_only = conf->receive_only;
-               if(conf->receive_only) {
-                       printk(KERN_INFO
-                               "%s: Configured for 'receive only' mode\n",
-                                card->devname);
-               }
-       }
-
-       /* Setup Port Bps */
-
-       if(card->wandev.clocking) {
-               if((port_num == WANOPT_PRI) || card->u.c.receive_only) {
-                       /* For Primary Port 0 */
-                               max_permitted_baud =
-                               (card->hw.type == SDLA_S514) ?
-                               PRI_MAX_BAUD_RATE_S514 : 
-                               PRI_MAX_BAUD_RATE_S508;
-
-               }else if(port_num == WANOPT_SEC) {
-                       /* For Secondary Port 1 */
-                        max_permitted_baud =
-                               (card->hw.type == SDLA_S514) ?
-                                SEC_MAX_BAUD_RATE_S514 :
-                                SEC_MAX_BAUD_RATE_S508;
-                        }
-  
-                       if(conf->bps > max_permitted_baud) {
-                               conf->bps = max_permitted_baud;
-                               printk(KERN_INFO "%s: Baud too high!\n",
-                                       card->wandev.name);
-                               printk(KERN_INFO "%s: Baud rate set to %lu bps\n", 
-                                       card->wandev.name, max_permitted_baud);
-                       }
-                       card->wandev.bps = conf->bps;
-       }else{
-               card->wandev.bps = 0;
-       }
-
-       /* Setup the Port MTU */
-       if((port_num == WANOPT_PRI) || card->u.c.receive_only) {
-
-               /* For Primary Port 0 */
-               card->wandev.mtu =
-                       (conf->mtu >= MIN_LGTH_CHDLC_DATA_CFG) ?
-                       min_t(unsigned int, conf->mtu, PRI_MAX_NO_DATA_BYTES_IN_FRAME) :
-                       CHDLC_DFLT_DATA_LEN;
-       } else if(port_num == WANOPT_SEC) { 
-               /* For Secondary Port 1 */
-               card->wandev.mtu =
-                       (conf->mtu >= MIN_LGTH_CHDLC_DATA_CFG) ?
-                       min_t(unsigned int, conf->mtu, SEC_MAX_NO_DATA_BYTES_IN_FRAME) :
-                       CHDLC_DFLT_DATA_LEN;
-       }
-
-       /* Set up the interrupt status area */
-       /* Read the CHDLC Configuration and obtain: 
-        *      Ptr to shared memory infor struct
-         * Use this pointer to calculate the value of card->u.c.flags !
-        */
-       mb1->buffer_length = 0;
-       mb1->command = READ_CHDLC_CONFIGURATION;
-       err = sdla_exec(mb1) ? mb1->return_code : CMD_TIMEOUT;
-       if(err != COMMAND_OK) {
-                if(card->hw.type != SDLA_S514)
-                       enable_irq(card->hw.irq);
-
-               chdlc_error(card, err, mb1);
-               return -EIO;
-       }
-
-       if(card->hw.type == SDLA_S514){
-                       card->u.c.flags = (void *)(card->hw.dpmbase +
-                               (((CHDLC_CONFIGURATION_STRUCT *)mb1->data)->
-                       ptr_shared_mem_info_struct));
-        }else{
-                card->u.c.flags = (void *)(card->hw.dpmbase +
-                        (((CHDLC_CONFIGURATION_STRUCT *)mb1->data)->
-                       ptr_shared_mem_info_struct % SDLA_WINDOWSIZE));
-       }
-
-       flags = card->u.c.flags;
-       
-       /* This is for the ports link state */
-       card->wandev.state = WAN_DUALPORT;
-       card->u.c.state = WAN_DISCONNECTED;
-
-
-       if (!card->wandev.piggyback){   
-               int err;
-
-               /* Perform interrupt testing */
-               err = intr_test(card);
-
-               if(err || (Intr_test_counter < MAX_INTR_TEST_COUNTER)) { 
-                       printk(KERN_INFO "%s: Interrupt test failed (%i)\n",
-                                       card->devname, Intr_test_counter);
-                       printk(KERN_INFO "%s: Please choose another interrupt\n",
-                                       card->devname);
-                       return -EIO;
-               }
-               
-               printk(KERN_INFO "%s: Interrupt test passed (%i)\n", 
-                               card->devname, Intr_test_counter);
-               card->configured = 1;
-       }
-
-       if ((card->tty_opt=conf->tty) == WANOPT_YES){
-               int err;
-               card->tty_minor = conf->tty_minor;
-
-               /* On ASYNC connections internal clocking 
-                * is mandatory */
-               if ((card->u.c.async_mode = conf->tty_mode)){
-                       card->wandev.clocking = 1;
-               }
-               err=wanpipe_tty_init(card);
-               if (err){
-                       return err;
-               }
-       }else{
-       
-
-               if (chdlc_set_intr_mode(card, APP_INT_ON_TIMER)){
-                       printk (KERN_INFO "%s: "
-                               "Failed to set interrupt triggers!\n",
-                               card->devname);
-                       return -EIO;    
-               }
-       
-               /* Mask the Timer interrupt */
-               flags->interrupt_info_struct.interrupt_permission &= 
-                       ~APP_INT_ON_TIMER;
-       }
-
-       /* If we are using CHDLC in backup mode, this flag will
-        * indicate not to look for IP addresses in config_chdlc()*/
-       card->u.c.backup = conf->backup;
-       
-       printk(KERN_INFO "\n");
-
-       return 0;
-}
-
-/******* WAN Device Driver Entry Points *************************************/
-
-/*============================================================================
- * Update device status & statistics
- * This procedure is called when updating the PROC file system and returns
- * various communications statistics. These statistics are accumulated from 3 
- * different locations:
- *     1) The 'if_stats' recorded for the device.
- *     2) Communication error statistics on the adapter.
- *      3) CHDLC operational statistics on the adapter.
- * The board level statistics are read during a timer interrupt. Note that we 
- * read the error and operational statistics during consecitive timer ticks so
- * as to minimize the time that we are inside the interrupt handler.
- *
- */
-static int update(struct wan_device* wandev)
-{
-       sdla_t* card = wandev->private;
-       struct net_device* dev;
-        volatile chdlc_private_area_t* chdlc_priv_area;
-        SHARED_MEMORY_INFO_STRUCT *flags;
-       unsigned long timeout;
-
-       /* sanity checks */
-       if((wandev == NULL) || (wandev->private == NULL))
-               return -EFAULT;
-       
-       if(wandev->state == WAN_UNCONFIGURED)
-               return -ENODEV;
-
-       /* more sanity checks */
-        if(!card->u.c.flags)
-                return -ENODEV;
-
-       if(test_bit(PERI_CRIT, (void*)&card->wandev.critical))
-                return -EAGAIN;
-
-       if((dev=card->wandev.dev) == NULL)
-               return -ENODEV;
-
-       if((chdlc_priv_area=dev->priv) == NULL)
-               return -ENODEV;
-
-       flags = card->u.c.flags;
-               if(chdlc_priv_area->update_comms_stats){
-               return -EAGAIN;
-       }
-                       
-       /* we will need 2 timer interrupts to complete the */
-       /* reading of the statistics */
-       chdlc_priv_area->update_comms_stats = 2;
-               flags->interrupt_info_struct.interrupt_permission |= APP_INT_ON_TIMER;
-       chdlc_priv_area->timer_int_enabled = TMR_INT_ENABLED_UPDATE;
-  
-       /* wait a maximum of 1 second for the statistics to be updated */ 
-        timeout = jiffies;
-        for(;;) {
-               if(chdlc_priv_area->update_comms_stats == 0)
-                       break;
-                if ((jiffies - timeout) > (1 * HZ)){
-                       chdlc_priv_area->update_comms_stats = 0;
-                       chdlc_priv_area->timer_int_enabled &=
-                               ~TMR_INT_ENABLED_UPDATE; 
-                       return -EAGAIN;
-               }
-        }
-
-       return 0;
-}
-
-
-/*============================================================================
- * Create new logical channel.
- * This routine is called by the router when ROUTER_IFNEW IOCTL is being
- * handled.
- * o parse media- and hardware-specific configuration
- * o make sure that a new channel can be created
- * o allocate resources, if necessary
- * o prepare network device structure for registaration.
- *
- * Return:     0       o.k.
- *             < 0     failure (channel will not be created)
- */
-static int new_if(struct wan_device* wandev, struct net_device* dev,
-                 wanif_conf_t* conf)
-{
-       sdla_t* card = wandev->private;
-       chdlc_private_area_t* chdlc_priv_area;
-
-
-       printk(KERN_INFO "%s: Configuring Interface: %s\n",
-                       card->devname, conf->name);
-       if ((conf->name[0] == '\0') || (strlen(conf->name) > WAN_IFNAME_SZ)) {
-               printk(KERN_INFO "%s: Invalid interface name!\n",
-                       card->devname);
-               return -EINVAL;
-       }
-               
-       /* allocate and initialize private data */
-       chdlc_priv_area = kmalloc(sizeof(chdlc_private_area_t), GFP_KERNEL);
-       
-       if(chdlc_priv_area == NULL) 
-               return -ENOMEM;
-
-       memset(chdlc_priv_area, 0, sizeof(chdlc_private_area_t));
-
-       chdlc_priv_area->card = card; 
-       chdlc_priv_area->common.sk = NULL;
-       chdlc_priv_area->common.func = NULL;    
-
-       /* initialize data */
-       strcpy(card->u.c.if_name, conf->name);
-
-       if(card->wandev.new_if_cnt > 0) {
-                kfree(chdlc_priv_area);
-               return -EEXIST;
-       }
-
-       card->wandev.new_if_cnt++;
-
-       chdlc_priv_area->TracingEnabled = 0;
-       chdlc_priv_area->route_status = NO_ROUTE;
-       chdlc_priv_area->route_removed = 0;
-
-       card->u.c.async_mode = conf->async_mode;
-       
-       /* setup for asynchronous mode */
-       if(conf->async_mode) {
-               printk(KERN_INFO "%s: Configuring for asynchronous mode\n",
-                       wandev->name);
-
-               if(card->u.c.comm_port == WANOPT_PRI) {
-                       printk(KERN_INFO
-                               "%s:Asynchronous mode on secondary port only\n",
-                                       wandev->name);
-                       kfree(chdlc_priv_area);
-                       return -EINVAL;
-               }
-
-               if(strcmp(conf->usedby, "WANPIPE") == 0) {
-                       printk(KERN_INFO
-                                "%s: Running in WANIPE Async Mode\n",                                                          wandev->name);
-                       card->u.c.usedby = WANPIPE;
-               }else{
-                       card->u.c.usedby = API;
-               }
-
-               if(!card->wandev.clocking) {
-                       printk(KERN_INFO
-                               "%s: Asynch. clocking must be 'Internal'\n",
-                               wandev->name);
-                       kfree(chdlc_priv_area);
-                       return -EINVAL;
-               }
-
-               if((card->wandev.bps < MIN_ASY_BAUD_RATE) ||
-                       (card->wandev.bps > MAX_ASY_BAUD_RATE)) {
-                       printk(KERN_INFO "%s: Selected baud rate is invalid.\n",
-                               wandev->name);
-                       printk(KERN_INFO "Must be between %u and %u bps.\n",
-                               MIN_ASY_BAUD_RATE, MAX_ASY_BAUD_RATE);
-                       kfree(chdlc_priv_area);
-                       return -EINVAL;
-               }
-
-               card->u.c.api_options = 0;
-                if (conf->asy_data_trans == WANOPT_YES) {
-                        card->u.c.api_options |= ASY_RX_DATA_TRANSPARENT;
-                }
-               
-               card->u.c.protocol_options = 0;
-               if (conf->rts_hs_for_receive == WANOPT_YES) {
-                       card->u.c.protocol_options |= ASY_RTS_HS_FOR_RX;
-               }
-                if (conf->xon_xoff_hs_for_receive == WANOPT_YES) {
-                        card->u.c.protocol_options |= ASY_XON_XOFF_HS_FOR_RX;
-                }
-                if (conf->xon_xoff_hs_for_transmit == WANOPT_YES) {
-                        card->u.c.protocol_options |= ASY_XON_XOFF_HS_FOR_TX;
-                }
-                if (conf->dcd_hs_for_transmit == WANOPT_YES) {
-                        card->u.c.protocol_options |= ASY_DCD_HS_FOR_TX;
-                }
-                if (conf->cts_hs_for_transmit == WANOPT_YES) {
-                        card->u.c.protocol_options |= ASY_CTS_HS_FOR_TX;
-                }
-
-               card->u.c.tx_bits_per_char = conf->tx_bits_per_char;
-                card->u.c.rx_bits_per_char = conf->rx_bits_per_char;
-                card->u.c.stop_bits = conf->stop_bits;
-               card->u.c.parity = conf->parity;
-               card->u.c.break_timer = conf->break_timer;
-               card->u.c.inter_char_timer = conf->inter_char_timer;
-               card->u.c.rx_complete_length = conf->rx_complete_length;
-               card->u.c.xon_char = conf->xon_char;
-
-       } else {        /* setup for synchronous mode */
-
-               card->u.c.protocol_options = 0;
-               if (conf->ignore_dcd == WANOPT_YES){
-                       card->u.c.protocol_options |= IGNORE_DCD_FOR_LINK_STAT;
-               }
-               if (conf->ignore_cts == WANOPT_YES){
-                       card->u.c.protocol_options |= IGNORE_CTS_FOR_LINK_STAT;
-               }
-
-               if (conf->ignore_keepalive == WANOPT_YES) {
-                       card->u.c.protocol_options |=
-                               IGNORE_KPALV_FOR_LINK_STAT;
-                       card->u.c.kpalv_tx  = MIN_Tx_KPALV_TIMER; 
-                       card->u.c.kpalv_rx  = MIN_Rx_KPALV_TIMER; 
-                       card->u.c.kpalv_err = MIN_KPALV_ERR_TOL; 
-
-               } else {   /* Do not ignore keepalives */
-                       card->u.c.kpalv_tx =
-                               ((conf->keepalive_tx_tmr - MIN_Tx_KPALV_TIMER)
-                               >= 0) ?
-                               min_t(unsigned int, conf->keepalive_tx_tmr,MAX_Tx_KPALV_TIMER) :
-                               DEFAULT_Tx_KPALV_TIMER;
-
-                       card->u.c.kpalv_rx =
-                               ((conf->keepalive_rx_tmr - MIN_Rx_KPALV_TIMER)
-                               >= 0) ?
-                               min_t(unsigned int, conf->keepalive_rx_tmr,MAX_Rx_KPALV_TIMER) :
-                               DEFAULT_Rx_KPALV_TIMER;
-
-                       card->u.c.kpalv_err =
-                               ((conf->keepalive_err_margin-MIN_KPALV_ERR_TOL)
-                               >= 0) ?
-                               min_t(unsigned int, conf->keepalive_err_margin,
-                               MAX_KPALV_ERR_TOL) : 
-                               DEFAULT_KPALV_ERR_TOL;
-               }
-
-               /* Setup slarp timer to control delay between slarps */
-               card->u.c.slarp_timer = 
-                       ((conf->slarp_timer - MIN_SLARP_REQ_TIMER) >= 0) ?
-                       min_t(unsigned int, conf->slarp_timer, MAX_SLARP_REQ_TIMER) :
-                       DEFAULT_SLARP_REQ_TIMER;
-
-               if (conf->hdlc_streaming == WANOPT_YES) {
-                       printk(KERN_INFO "%s: Enabling HDLC STREAMING Mode\n",
-                               wandev->name);
-                       card->u.c.protocol_options = HDLC_STREAMING_MODE;
-               }
-
-               if ((chdlc_priv_area->true_if_encoding = conf->true_if_encoding) == WANOPT_YES){
-                       printk(KERN_INFO 
-                               "%s: Enabling, true interface type encoding.\n",
-                               card->devname);
-               }
-               
-               /* Setup wanpipe as a router (WANPIPE) or as an API */
-               if( strcmp(conf->usedby, "WANPIPE") == 0) {
-
-                       printk(KERN_INFO "%s: Running in WANPIPE mode!\n",
-                               wandev->name);
-                       card->u.c.usedby = WANPIPE;
-
-                       /* Option to bring down the interface when 
-                        * the link goes down */
-                       if (conf->if_down){
-                               set_bit(DYN_OPT_ON,&chdlc_priv_area->interface_down);
-                               printk(KERN_INFO 
-                                "%s: Dynamic interface configuration enabled\n",
-                                  card->devname);
-                       } 
-
-               } else if( strcmp(conf->usedby, "API") == 0) {
-                       card->u.c.usedby = API;
-                       printk(KERN_INFO "%s: Running in API mode !\n",
-                               wandev->name);
-               }
-       }
-
-       /* Tells us that if this interface is a
-         * gateway or not */
-       if ((chdlc_priv_area->gateway = conf->gateway) == WANOPT_YES){
-               printk(KERN_INFO "%s: Interface %s is set as a gateway.\n",
-                       card->devname,card->u.c.if_name);
-       }
-
-       /* Get Multicast Information */
-       chdlc_priv_area->mc = conf->mc;
-
-       /* prepare network device data space for registration */
-       strcpy(dev->name,card->u.c.if_name);
-
-       dev->init = &if_init;
-       dev->priv = chdlc_priv_area;
-
-       /* Initialize the polling work routine */
-       INIT_WORK(&chdlc_priv_area->poll_work, (void*)(void*)chdlc_poll, dev);
-
-       /* Initialize the polling delay timer */
-       init_timer(&chdlc_priv_area->poll_delay_timer);
-       chdlc_priv_area->poll_delay_timer.data = (unsigned long)dev;
-       chdlc_priv_area->poll_delay_timer.function = chdlc_poll_delay;
-       
-       printk(KERN_INFO "\n");
-
-       return 0;
-}
-
-
-/****** Network Device Interface ********************************************/
-
-/*============================================================================
- * Initialize Linux network interface.
- *
- * This routine is called only once for each interface, during Linux network
- * interface registration.  Returning anything but zero will fail interface
- * registration.
- */
-static int if_init(struct net_device* dev)
-{
-       chdlc_private_area_t* chdlc_priv_area = dev->priv;
-       sdla_t* card = chdlc_priv_area->card;
-       struct wan_device* wandev = &card->wandev;
-
-       /* Initialize device driver entry points */
-       dev->open               = &if_open;
-       dev->stop               = &if_close;
-       dev->hard_header        = &if_header;
-       dev->rebuild_header     = &if_rebuild_hdr;
-       dev->hard_start_xmit    = &if_send;
-       dev->get_stats          = &if_stats;
-       dev->tx_timeout         = &if_tx_timeout;
-       dev->watchdog_timeo     = TX_TIMEOUT;
-       
-       /* Initialize media-specific parameters */
-       dev->flags              |= IFF_POINTOPOINT;
-       dev->flags              |= IFF_NOARP;
-
-       /* Enable Mulitcasting if user selected */
-       if (chdlc_priv_area->mc == WANOPT_YES){
-               dev->flags      |= IFF_MULTICAST;
-       }
-       
-       if (chdlc_priv_area->true_if_encoding){
-               dev->type       = ARPHRD_HDLC; /* This breaks the tcpdump */
-       }else{
-               dev->type       = ARPHRD_PPP;
-       }
-       
-       dev->mtu                = card->wandev.mtu;
-       /* for API usage, add the API header size to the requested MTU size */
-       if(card->u.c.usedby == API) {
-               dev->mtu += sizeof(api_tx_hdr_t);
-       }
-       dev->hard_header_len    = CHDLC_HDR_LEN;
-
-       /* Initialize hardware parameters */
-       dev->irq        = wandev->irq;
-       dev->dma        = wandev->dma;
-       dev->base_addr  = wandev->ioport;
-       dev->mem_start  = wandev->maddr;
-       dev->mem_end    = wandev->maddr + wandev->msize - 1;
-
-       /* Set transmit buffer queue length 
-        * If too low packets will not be retransmitted 
-         * by stack.
-        */
-        dev->tx_queue_len = 100;
-       SET_MODULE_OWNER(dev);
-   
-       return 0;
-}
-
-/*============================================================================
- * Open network interface.
- * o enable communications and interrupts.
- * o prevent module from unloading by incrementing use count
- *
- * Return 0 if O.k. or errno.
- */
-static int if_open(struct net_device* dev)
-{
-       chdlc_private_area_t* chdlc_priv_area = dev->priv;
-       sdla_t* card = chdlc_priv_area->card;
-       struct timeval tv;
-       int err = 0;
-
-       /* Only one open per interface is allowed */
-
-       if (netif_running(dev))
-               return -EBUSY;
-
-       /* Initialize the work queue entry */
-       chdlc_priv_area->tq_working=0;
-
-       INIT_WORK(&chdlc_priv_area->common.wanpipe_work,
-                       (void *)(void *)chdlc_work, dev);
-
-       /* Allocate and initialize BH circular buffer */
-       /* Add 1 to MAX_BH_BUFF so we don't have test with (MAX_BH_BUFF-1) */
-       chdlc_priv_area->bh_head = kmalloc((sizeof(bh_data_t)*(MAX_BH_BUFF+1)),GFP_ATOMIC);
-       memset(chdlc_priv_area->bh_head,0,(sizeof(bh_data_t)*(MAX_BH_BUFF+1)));
-       atomic_set(&chdlc_priv_area->bh_buff_used, 0);
-       do_gettimeofday(&tv);
-       chdlc_priv_area->router_start_time = tv.tv_sec;
-
-       netif_start_queue(dev);
-
-       wanpipe_open(card);
-
-       /* TTY is configured during wanpipe_set_termios
-        * call, not here */
-       if (card->tty_opt)
-               return err;
-       
-       set_bit(0,&chdlc_priv_area->config_chdlc);
-       chdlc_priv_area->config_chdlc_timeout=jiffies;
-
-       /* Start the CHDLC configuration after 1sec delay.
-        * This will give the interface initilization time
-        * to finish its configuration */
-       mod_timer(&chdlc_priv_area->poll_delay_timer, jiffies + HZ);
-       return err;
-}
-
-/*============================================================================
- * Close network interface.
- * o if this is the last close, then disable communications and interrupts.
- * o reset flags.
- */
-static int if_close(struct net_device* dev)
-{
-       chdlc_private_area_t* chdlc_priv_area = dev->priv;
-       sdla_t* card = chdlc_priv_area->card;
-
-       if (chdlc_priv_area->bh_head){
-               int i;
-               struct sk_buff *skb;
-       
-               for (i=0; i<(MAX_BH_BUFF+1); i++){
-                       skb = ((bh_data_t *)&chdlc_priv_area->bh_head[i])->skb;
-                       if (skb != NULL){
-                               dev_kfree_skb_any(skb);
-                       }
-               }
-               kfree(chdlc_priv_area->bh_head);
-               chdlc_priv_area->bh_head=NULL;
-       }
-
-       netif_stop_queue(dev);
-       wanpipe_close(card);
-       del_timer(&chdlc_priv_area->poll_delay_timer);
-       return 0;
-}
-
-static void disable_comm (sdla_t *card)
-{
-       SHARED_MEMORY_INFO_STRUCT *flags = card->u.c.flags;
-       
-       if (card->u.c.comm_enabled){
-               chdlc_disable_comm_shutdown (card);
-       }else{
-               flags->interrupt_info_struct.interrupt_permission = 0;  
-       }
-
-       if (!tty_init_cnt)
-               return;
-
-       if (card->tty_opt){
-               struct serial_state * state;
-               if (!(--tty_init_cnt)){
-                       int e1;
-                       serial_driver.refcount=0;
-                       
-                       if ((e1 = tty_unregister_driver(&serial_driver)))
-                               printk("SERIAL: failed to unregister serial driver (%d)\n",
-                                      e1);
-                       printk(KERN_INFO "%s: Unregistering TTY Driver, Major %i\n",
-                                       card->devname,WAN_TTY_MAJOR);
-               }
-               card->tty=NULL;
-               tty_card_map[card->tty_minor]=NULL;
-               state = &rs_table[card->tty_minor];
-               memset(state, 0, sizeof(*state));
-       }
-       return;
-}
-
-
-/*============================================================================
- * Build media header.
- *
- * The trick here is to put packet type (Ethertype) into 'protocol' field of
- * the socket buffer, so that we don't forget it.  If packet type is not
- * supported, set skb->protocol to 0 and discard packet later.
- *
- * Return:     media header length.
- */
-static int if_header(struct sk_buff* skb, struct net_device* dev,
-                    unsigned short type, void* daddr, void* saddr,
-                    unsigned len)
-{
-       skb->protocol = htons(type);
-
-       return CHDLC_HDR_LEN;
-}
-
-
-/*============================================================================
- * Handle transmit timeout event from netif watchdog
- */
-static void if_tx_timeout(struct net_device *dev)
-{
-       chdlc_private_area_t* chan = dev->priv;
-       sdla_t *card = chan->card;
-       
-       /* If our device stays busy for at least 5 seconds then we will
-        * kick start the device by making dev->tbusy = 0.  We expect
-        * that our device never stays busy more than 5 seconds. So this                 
-        * is only used as a last resort.
-        */
-
-       ++card->wandev.stats.collisions;
-
-       printk (KERN_INFO "%s: Transmit timed out on %s\n", card->devname,dev->name);
-       netif_wake_queue (dev);
-}
-
-
-
-/*============================================================================
- * Re-build media header.
- *
- * Return:     1       physical address resolved.
- *             0       physical address not resolved
- */
-static int if_rebuild_hdr (struct sk_buff *skb)
-{
-       return 1;
-}
-
-
-/*============================================================================
- * Send a packet on a network interface.
- * o set tbusy flag (marks start of the transmission) to block a timer-based
- *   transmit from overlapping.
- * o check link state. If link is not up, then drop the packet.
- * o execute adapter send command.
- * o free socket buffer
- *
- * Return:     0       complete (socket buffer must be freed)
- *             non-0   packet may be re-transmitted (tbusy must be set)
- *
- * Notes:
- * 1. This routine is called either by the protocol stack or by the "net
- *    bottom half" (with interrupts enabled).
- * 2. Setting tbusy flag will inhibit further transmit requests from the
- *    protocol stack and can be used for flow control with protocol layer.
- */
-static int if_send(struct sk_buff* skb, struct net_device* dev)
-{
-       chdlc_private_area_t *chdlc_priv_area = dev->priv;
-       sdla_t *card = chdlc_priv_area->card;
-       SHARED_MEMORY_INFO_STRUCT *flags = card->u.c.flags;
-       INTERRUPT_INFORMATION_STRUCT *chdlc_int = &flags->interrupt_info_struct;
-       int udp_type = 0;
-       unsigned long smp_flags;
-       int err=0;
-
-       netif_stop_queue(dev);
-       
-       if (skb == NULL){
-               /* If we get here, some higher layer thinks we've missed an
-                * tx-done interrupt.
-                */
-               printk(KERN_INFO "%s: interface %s got kicked!\n",
-                       card->devname, dev->name);
-
-               netif_wake_queue(dev);
-               return 0;
-       }
-
-       if (ntohs(skb->protocol) != htons(PVC_PROT)){
-
-               /* check the udp packet type */
-               
-               udp_type = udp_pkt_type(skb, card);
-
-               if (udp_type == UDP_CPIPE_TYPE){
-                        if(store_udp_mgmt_pkt(UDP_PKT_FRM_STACK, card, skb, dev,
-                                chdlc_priv_area)){
-                               chdlc_int->interrupt_permission |=
-                                       APP_INT_ON_TIMER;
-                       }
-                       netif_start_queue(dev);
-                       return 0;
-               }
-
-               /* check to see if the source IP address is a broadcast or */
-               /* multicast IP address */
-                if(chk_bcast_mcast_addr(card, dev, skb)){
-                       ++card->wandev.stats.tx_dropped;
-                       dev_kfree_skb_any(skb);
-                       netif_start_queue(dev);
-                       return 0;
-               }
-        }
-
-       /* Lock the 508 Card: SMP is supported */
-       if(card->hw.type != SDLA_S514){
-               s508_lock(card,&smp_flags);
-       } 
-
-       if(test_and_set_bit(SEND_CRIT, (void*)&card->wandev.critical)) {
-       
-               printk(KERN_INFO "%s: Critical in if_send: %lx\n",
-                                       card->wandev.name,card->wandev.critical);
-                ++card->wandev.stats.tx_dropped;
-               netif_start_queue(dev);
-               goto if_send_exit_crit;
-       }
-
-       if(card->u.c.state != WAN_CONNECTED){
-                       ++card->wandev.stats.tx_dropped;
-               netif_start_queue(dev);
-               
-       }else if(!skb->protocol){
-               ++card->wandev.stats.tx_errors;
-               netif_start_queue(dev);
-               
-       }else {
-               void* data = skb->data;
-               unsigned len = skb->len;
-               unsigned char attr;
-
-               /* If it's an API packet pull off the API
-                * header. Also check that the packet size
-                * is larger than the API header
-                */
-               if (card->u.c.usedby == API){
-                       api_tx_hdr_t* api_tx_hdr;
-
-                       /* discard the frame if we are configured for */
-                       /* 'receive only' mode or if there is no data */
-                       if (card->u.c.receive_only ||
-                               (len <= sizeof(api_tx_hdr_t))) {
-                               
-                               ++card->wandev.stats.tx_dropped;
-                               netif_start_queue(dev);
-                               goto if_send_exit_crit;
-                       }
-                               
-                       api_tx_hdr = (api_tx_hdr_t *)data;
-                       attr = api_tx_hdr->attr;
-                       data += sizeof(api_tx_hdr_t);
-                       len -= sizeof(api_tx_hdr_t);
-               }
-
-               if(chdlc_send(card, data, len)) {
-                       netif_stop_queue(dev);
-               }else{
-                       ++card->wandev.stats.tx_packets;
-                        card->wandev.stats.tx_bytes += len;
-                       
-                       netif_start_queue(dev);
-                       
-                       dev->trans_start = jiffies;
-               }       
-       }
-
-if_send_exit_crit:
-       
-       if (!(err=netif_queue_stopped(dev))) {
-               dev_kfree_skb_any(skb);
-       }else{
-               chdlc_priv_area->tick_counter = jiffies;
-               chdlc_int->interrupt_permission |= APP_INT_ON_TX_FRAME;
-       }
-
-       clear_bit(SEND_CRIT, (void*)&card->wandev.critical);
-       if(card->hw.type != SDLA_S514){
-               s508_unlock(card,&smp_flags);
-       }
-       
-       return err;
-}
-
-
-/*============================================================================
- * Check to see if the packet to be transmitted contains a broadcast or
- * multicast source IP address.
- */
-
-static int chk_bcast_mcast_addr(sdla_t *card, struct net_device* dev,
-                               struct sk_buff *skb)
-{
-       u32 src_ip_addr;
-        u32 broadcast_ip_addr = 0;
-        struct in_device *in_dev;
-
-        /* read the IP source address from the outgoing packet */
-        src_ip_addr = *(u32 *)(skb->data + 12);
-
-       /* read the IP broadcast address for the device */
-        in_dev = dev->ip_ptr;
-        if(in_dev != NULL) {
-                struct in_ifaddr *ifa= in_dev->ifa_list;
-                if(ifa != NULL)
-                        broadcast_ip_addr = ifa->ifa_broadcast;
-                else
-                        return 0;
-        }
-        /* check if the IP Source Address is a Broadcast address */
-        if((dev->flags & IFF_BROADCAST) && (src_ip_addr == broadcast_ip_addr)) {
-                printk(KERN_INFO "%s: Broadcast Source Address silently discarded\n",
-                               card->devname);
-                return 1;
-        } 
-
-        /* check if the IP Source Address is a Multicast address */
-        if((ntohl(src_ip_addr) >= 0xE0000001) &&
-               (ntohl(src_ip_addr) <= 0xFFFFFFFE)) {
-                printk(KERN_INFO "%s: Multicast Source Address silently discarded\n",
-                               card->devname);
-                return 1;
-        }
-
-        return 0;
-}
-
-
-/*============================================================================
- * Reply to UDP Management system.
- * Return length of reply.
- */
-static int reply_udp( unsigned char *data, unsigned int mbox_len )
-{
-
-       unsigned short len, udp_length, temp, ip_length;
-       unsigned long ip_temp;
-       int even_bound = 0;
-       chdlc_udp_pkt_t *c_udp_pkt = (chdlc_udp_pkt_t *)data;
-        
-       /* Set length of packet */
-       len = sizeof(ip_pkt_t)+ 
-             sizeof(udp_pkt_t)+
-             sizeof(wp_mgmt_t)+
-             sizeof(cblock_t)+
-             sizeof(trace_info_t)+ 
-             mbox_len;
-
-       /* fill in UDP reply */
-       c_udp_pkt->wp_mgmt.request_reply = UDPMGMT_REPLY;
-   
-       /* fill in UDP length */
-       udp_length = sizeof(udp_pkt_t)+ 
-                    sizeof(wp_mgmt_t)+
-                    sizeof(cblock_t)+
-                    sizeof(trace_info_t)+
-                    mbox_len; 
-
-       /* put it on an even boundary */
-       if ( udp_length & 0x0001 ) {
-               udp_length += 1;
-               len += 1;
-               even_bound = 1;
-       }  
-
-       temp = (udp_length<<8)|(udp_length>>8);
-       c_udp_pkt->udp_pkt.udp_length = temp;
-                
-       /* swap UDP ports */
-       temp = c_udp_pkt->udp_pkt.udp_src_port;
-       c_udp_pkt->udp_pkt.udp_src_port = 
-                       c_udp_pkt->udp_pkt.udp_dst_port; 
-       c_udp_pkt->udp_pkt.udp_dst_port = temp;
-
-       /* add UDP pseudo header */
-       temp = 0x1100;
-       *((unsigned short *)(c_udp_pkt->data+mbox_len+even_bound)) = temp;      
-       temp = (udp_length<<8)|(udp_length>>8);
-       *((unsigned short *)(c_udp_pkt->data+mbox_len+even_bound+2)) = temp;
-
-                
-       /* calculate UDP checksum */
-       c_udp_pkt->udp_pkt.udp_checksum = 0;
-       c_udp_pkt->udp_pkt.udp_checksum = calc_checksum(&data[UDP_OFFSET],udp_length+UDP_OFFSET);
-
-       /* fill in IP length */
-       ip_length = len;
-       temp = (ip_length<<8)|(ip_length>>8);
-       c_udp_pkt->ip_pkt.total_length = temp;
-  
-       /* swap IP addresses */
-       ip_temp = c_udp_pkt->ip_pkt.ip_src_address;
-       c_udp_pkt->ip_pkt.ip_src_address = c_udp_pkt->ip_pkt.ip_dst_address;
-       c_udp_pkt->ip_pkt.ip_dst_address = ip_temp;
-
-       /* fill in IP checksum */
-       c_udp_pkt->ip_pkt.hdr_checksum = 0;
-       c_udp_pkt->ip_pkt.hdr_checksum = calc_checksum(data,sizeof(ip_pkt_t));
-
-       return len;
-
-} /* reply_udp */
-
-unsigned short calc_checksum (char *data, int len)
-{
-       unsigned short temp; 
-       unsigned long sum=0;
-       int i;
-
-       for( i = 0; i <len; i+=2 ) {
-               memcpy(&temp,&data[i],2);
-               sum += (unsigned long)temp;
-       }
-
-       while (sum >> 16 ) {
-               sum = (sum & 0xffffUL) + (sum >> 16);
-       }
-
-       temp = (unsigned short)sum;
-       temp = ~temp;
-
-       if( temp == 0 ) 
-               temp = 0xffff;
-
-       return temp;    
-}
-
-
-/*============================================================================
- * Get ethernet-style interface statistics.
- * Return a pointer to struct enet_statistics.
- */
-static struct net_device_stats* if_stats(struct net_device* dev)
-{
-       sdla_t *my_card;
-       chdlc_private_area_t* chdlc_priv_area;
-
-       if ((chdlc_priv_area=dev->priv) == NULL)
-               return NULL;
-
-       my_card = chdlc_priv_area->card;
-       return &my_card->wandev.stats; 
-}
-
-
-/****** Cisco HDLC Firmware Interface Functions *******************************/
-
-/*============================================================================
- * Read firmware code version.
- *     Put code version as ASCII string in str. 
- */
-static int chdlc_read_version (sdla_t* card, char* str)
-{
-       CHDLC_MAILBOX_STRUCT* mb = card->mbox;
-       int len;
-       char err;
-       mb->buffer_length = 0;
-       mb->command = READ_CHDLC_CODE_VERSION;
-       err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT;
-
-       if(err != COMMAND_OK) {
-               chdlc_error(card,err,mb);
-       }
-       else if (str) {  /* is not null */
-               len = mb->buffer_length;
-               memcpy(str, mb->data, len);
-               str[len] = '\0';
-       }
-       return (err);
-}
-
-/*-----------------------------------------------------------------------------
- *  Configure CHDLC firmware.
- */
-static int chdlc_configure (sdla_t* card, void* data)
-{
-       int err;
-       CHDLC_MAILBOX_STRUCT *mailbox = card->mbox;
-       int data_length = sizeof(CHDLC_CONFIGURATION_STRUCT);
-       
-       mailbox->buffer_length = data_length;  
-       memcpy(mailbox->data, data, data_length);
-       mailbox->command = SET_CHDLC_CONFIGURATION;
-       err = sdla_exec(mailbox) ? mailbox->return_code : CMD_TIMEOUT;
-       
-       if (err != COMMAND_OK) chdlc_error (card, err, mailbox);
-                           
-       return err;
-}
-
-
-/*============================================================================
- * Set interrupt mode -- HDLC Version.
- */
-
-static int chdlc_set_intr_mode (sdla_t* card, unsigned mode)
-{
-       CHDLC_MAILBOX_STRUCT* mb = card->mbox;
-       CHDLC_INT_TRIGGERS_STRUCT* int_data =
-                (CHDLC_INT_TRIGGERS_STRUCT *)mb->data;
-       int err;
-
-       int_data->CHDLC_interrupt_triggers      = mode;
-       int_data->IRQ                           = card->hw.irq;
-       int_data->interrupt_timer               = 1;
-   
-       mb->buffer_length = sizeof(CHDLC_INT_TRIGGERS_STRUCT);
-       mb->command = SET_CHDLC_INTERRUPT_TRIGGERS;
-       err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT;
-       if (err != COMMAND_OK)
-               chdlc_error (card, err, mb);
-       return err;
-}
-
-
-/*===========================================================
- * chdlc_disable_comm_shutdown
- *
- * Shutdown() disables the communications. We must
- * have a sparate functions, because we must not
- * call chdlc_error() hander since the private
- * area has already been replaced */
-
-static int chdlc_disable_comm_shutdown (sdla_t *card)
-{
-       CHDLC_MAILBOX_STRUCT* mb = card->mbox;
-       CHDLC_INT_TRIGGERS_STRUCT* int_data =
-                (CHDLC_INT_TRIGGERS_STRUCT *)mb->data;
-       int err;
-
-       /* Disable Interrutps */
-       int_data->CHDLC_interrupt_triggers      = 0;
-       int_data->IRQ                           = card->hw.irq;
-       int_data->interrupt_timer               = 1;
-   
-       mb->buffer_length = sizeof(CHDLC_INT_TRIGGERS_STRUCT);
-       mb->command = SET_CHDLC_INTERRUPT_TRIGGERS;
-       err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT;
-
-       /* Disable Communications */
-
-       if (card->u.c.async_mode) {
-               mb->command = DISABLE_ASY_COMMUNICATIONS;
-       }else{
-               mb->command = DISABLE_CHDLC_COMMUNICATIONS;
-       }
-       
-       mb->buffer_length = 0;
-       err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT;
-       
-       card->u.c.comm_enabled = 0;
-       
-       return 0;
-}
-
-/*============================================================================
- * Enable communications.
- */
-
-static int chdlc_comm_enable (sdla_t* card)
-{
-       int err;
-       CHDLC_MAILBOX_STRUCT* mb = card->mbox;
-
-       mb->buffer_length = 0;
-       mb->command = ENABLE_CHDLC_COMMUNICATIONS;
-       err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT;
-       if (err != COMMAND_OK)
-               chdlc_error(card, err, mb);
-       else
-               card->u.c.comm_enabled = 1;
-       
-       return err;
-}
-
-/*============================================================================
- * Read communication error statistics.
- */
-static int chdlc_read_comm_err_stats (sdla_t* card)
-{
-        int err;
-        CHDLC_MAILBOX_STRUCT* mb = card->mbox;
-
-        mb->buffer_length = 0;
-        mb->command = READ_COMMS_ERROR_STATS;
-        err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT;
-        if (err != COMMAND_OK)
-                chdlc_error(card,err,mb);
-        return err;
-}
-
-
-/*============================================================================
- * Read CHDLC operational statistics.
- */
-static int chdlc_read_op_stats (sdla_t* card)
-{
-        int err;
-        CHDLC_MAILBOX_STRUCT* mb = card->mbox;
-
-        mb->buffer_length = 0;
-        mb->command = READ_CHDLC_OPERATIONAL_STATS;
-        err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT;
-        if (err != COMMAND_OK)
-                chdlc_error(card,err,mb);
-        return err;
-}
-
-
-/*============================================================================
- * Update communications error and general packet statistics.
- */
-static int update_comms_stats(sdla_t* card,
-       chdlc_private_area_t* chdlc_priv_area)
-{
-        CHDLC_MAILBOX_STRUCT* mb = card->mbox;
-       COMMS_ERROR_STATS_STRUCT* err_stats;
-        CHDLC_OPERATIONAL_STATS_STRUCT *op_stats;
-
-       /* on the first timer interrupt, read the comms error statistics */
-       if(chdlc_priv_area->update_comms_stats == 2) {
-               if(chdlc_read_comm_err_stats(card))
-                       return 1;
-               err_stats = (COMMS_ERROR_STATS_STRUCT *)mb->data;
-               card->wandev.stats.rx_over_errors = 
-                               err_stats->Rx_overrun_err_count;
-               card->wandev.stats.rx_crc_errors = 
-                               err_stats->CRC_err_count;
-               card->wandev.stats.rx_frame_errors = 
-                               err_stats->Rx_abort_count;
-               card->wandev.stats.rx_fifo_errors = 
-                               err_stats->Rx_dis_pri_bfrs_full_count; 
-               card->wandev.stats.rx_missed_errors =
-                               card->wandev.stats.rx_fifo_errors;
-               card->wandev.stats.tx_aborted_errors =
-                               err_stats->sec_Tx_abort_count;
-       }
-
-        /* on the second timer interrupt, read the operational statistics */
-       else {
-               if(chdlc_read_op_stats(card))
-                       return 1;
-               op_stats = (CHDLC_OPERATIONAL_STATS_STRUCT *)mb->data;
-               card->wandev.stats.rx_length_errors =
-                       (op_stats->Rx_Data_discard_short_count +
-                       op_stats->Rx_Data_discard_long_count);
-       }
-
-       return 0;
-}
-
-/*============================================================================
- * Send packet.
- *     Return: 0 - o.k.
- *             1 - no transmit buffers available
- */
-static int chdlc_send (sdla_t* card, void* data, unsigned len)
-{
-       CHDLC_DATA_TX_STATUS_EL_STRUCT *txbuf = card->u.c.txbuf;
-
-       if (txbuf->opp_flag)
-               return 1;
-       
-       sdla_poke(&card->hw, txbuf->ptr_data_bfr, data, len);
-
-       txbuf->frame_length = len;
-       txbuf->opp_flag = 1;            /* start transmission */
-       
-       /* Update transmit buffer control fields */
-       card->u.c.txbuf = ++txbuf;
-       
-       if ((void*)txbuf > card->u.c.txbuf_last)
-               card->u.c.txbuf = card->u.c.txbuf_base;
-       
-       return 0;
-}
-
-/****** Firmware Error Handler **********************************************/
-
-/*============================================================================
- * Firmware error handler.
- *     This routine is called whenever firmware command returns non-zero
- *     return code.
- *
- * Return zero if previous command has to be cancelled.
- */
-static int chdlc_error (sdla_t *card, int err, CHDLC_MAILBOX_STRUCT *mb)
-{
-       unsigned cmd = mb->command;
-
-       switch (err) {
-
-       case CMD_TIMEOUT:
-               printk(KERN_INFO "%s: command 0x%02X timed out!\n",
-                       card->devname, cmd);
-               break;
-
-       case S514_BOTH_PORTS_SAME_CLK_MODE:
-               if(cmd == SET_CHDLC_CONFIGURATION) {
-                       printk(KERN_INFO
-                        "%s: Configure both ports for the same clock source\n",
-                               card->devname);
-                       break;
-               }
-
-       default:
-               printk(KERN_INFO "%s: command 0x%02X returned 0x%02X!\n",
-                       card->devname, cmd, err);
-       }
-
-       return 0;
-}
-
-
-/********** Bottom Half Handlers ********************************************/
-
-/* NOTE: There is no API, BH support for Kernels lower than 2.2.X.
- *       DO NOT INSERT ANY CODE HERE, NOTICE THE 
- *       PREPROCESSOR STATEMENT ABOVE, UNLESS YOU KNOW WHAT YOU ARE
- *       DOING */
-
-static void chdlc_work(struct net_device * dev)
-{
-       chdlc_private_area_t* chan = dev->priv;
-       sdla_t *card = chan->card;
-       struct sk_buff *skb;
-
-       if (atomic_read(&chan->bh_buff_used) == 0){
-               clear_bit(0, &chan->tq_working);
-               return;
-       }
-
-       while (atomic_read(&chan->bh_buff_used)){
-
-               skb  = ((bh_data_t *)&chan->bh_head[chan->bh_read])->skb;
-
-               if (skb != NULL){
-
-                       if (chan->common.sk == NULL || chan->common.func == NULL){
-                               ++card->wandev.stats.rx_dropped;
-                               dev_kfree_skb_any(skb);
-                               chdlc_work_cleanup(dev);
-                               continue;
-                       }
-
-                       if (chan->common.func(skb,dev,chan->common.sk) != 0){
-                               /* Sock full cannot send, queue us for another
-                                 * try */
-                               atomic_set(&chan->common.receive_block,1);
-                               return;
-                       }else{
-                               chdlc_work_cleanup(dev);
-                       }
-               }else{
-                       chdlc_work_cleanup(dev);
-               }
-       }       
-       clear_bit(0, &chan->tq_working);
-
-       return;
-}
-
-static int chdlc_work_cleanup(struct net_device *dev)
-{
-       chdlc_private_area_t* chan = dev->priv;
-
-       ((bh_data_t *)&chan->bh_head[chan->bh_read])->skb = NULL;
-
-       if (chan->bh_read == MAX_BH_BUFF){
-               chan->bh_read=0;
-       }else{
-               ++chan->bh_read;        
-       }
-
-       atomic_dec(&chan->bh_buff_used);
-       return 0;
-}
-
-
-
-static int bh_enqueue(struct net_device *dev, struct sk_buff *skb)
-{
-       /* Check for full */
-       chdlc_private_area_t* chan = dev->priv;
-       sdla_t *card = chan->card;
-
-       if (atomic_read(&chan->bh_buff_used) == (MAX_BH_BUFF+1)){
-               ++card->wandev.stats.rx_dropped;
-               dev_kfree_skb_any(skb);
-               return 1; 
-       }
-
-       ((bh_data_t *)&chan->bh_head[chan->bh_write])->skb = skb;
-
-       if (chan->bh_write == MAX_BH_BUFF){
-               chan->bh_write=0;
-       }else{
-               ++chan->bh_write;
-       }
-
-       atomic_inc(&chan->bh_buff_used);
-
-       return 0;
-}
-
-/* END OF API BH Support */
-
-
-/****** Interrupt Handlers **************************************************/
-
-/*============================================================================
- * Cisco HDLC interrupt service routine.
- */
-static void wpc_isr (sdla_t* card)
-{
-       struct net_device* dev;
-       SHARED_MEMORY_INFO_STRUCT* flags = NULL;
-       int i;
-       sdla_t *my_card;
-
-
-       /* Check for which port the interrupt has been generated
-        * Since Secondary Port is piggybacking on the Primary
-         * the check must be done here. 
-        */
-
-       flags = card->u.c.flags;
-       if (!flags->interrupt_info_struct.interrupt_type){
-               /* Check for a second port (piggybacking) */
-               if ((my_card = card->next)){
-                       flags = my_card->u.c.flags;
-                       if (flags->interrupt_info_struct.interrupt_type){
-                               card = my_card;
-                               card->isr(card);
-                               return;
-                       }
-               }
-       }
-
-       flags = card->u.c.flags;
-       card->in_isr = 1;
-       dev = card->wandev.dev;
-       
-       /* If we get an interrupt with no network device, stop the interrupts
-        * and issue an error */
-       if (!card->tty_opt && !dev && 
-           flags->interrupt_info_struct.interrupt_type != 
-               COMMAND_COMPLETE_APP_INT_PEND){
-
-               goto isr_done;
-       }
-       
-       /* if critical due to peripheral operations
-        * ie. update() or getstats() then reset the interrupt and
-        * wait for the board to retrigger.
-        */
-       if(test_bit(PERI_CRIT, (void*)&card->wandev.critical)) {
-               printk(KERN_INFO "ISR CRIT TO PERI\n");
-               goto isr_done;
-       }
-
-       /* On a 508 Card, if critical due to if_send 
-         * Major Error !!! */
-       if(card->hw.type != SDLA_S514) {
-               if(test_bit(SEND_CRIT, (void*)&card->wandev.critical)) {
-                       printk(KERN_INFO "%s: Critical while in ISR: %lx\n",
-                               card->devname, card->wandev.critical);
-                       card->in_isr = 0;
-                       flags->interrupt_info_struct.interrupt_type = 0;
-                       return;
-               }
-       }
-
-       switch(flags->interrupt_info_struct.interrupt_type) {
-
-       case RX_APP_INT_PEND:   /* 0x01: receive interrupt */
-               rx_intr(card);
-               break;
-
-       case TX_APP_INT_PEND:   /* 0x02: transmit interrupt */
-               flags->interrupt_info_struct.interrupt_permission &=
-                        ~APP_INT_ON_TX_FRAME;
-
-               if (card->tty_opt){
-                       wanpipe_tty_trigger_poll(card);
-                       break;
-               }
-
-               if (dev && netif_queue_stopped(dev)){
-                       if (card->u.c.usedby == API){
-                               netif_start_queue(dev);
-                               wakeup_sk_bh(dev);
-                       }else{
-                               netif_wake_queue(dev);
-                       }
-               }
-               break;
-
-       case COMMAND_COMPLETE_APP_INT_PEND:/* 0x04: cmd cplt */
-               ++ Intr_test_counter;
-               break;
-
-       case CHDLC_EXCEP_COND_APP_INT_PEND:     /* 0x20 */
-               process_chdlc_exception(card);
-               break;
-
-       case GLOBAL_EXCEP_COND_APP_INT_PEND:
-               process_global_exception(card);
-               break;
-
-       case TIMER_APP_INT_PEND:
-               timer_intr(card);
-               break;
-
-       default:
-               printk(KERN_INFO "%s: spurious interrupt 0x%02X!\n", 
-                       card->devname,
-                       flags->interrupt_info_struct.interrupt_type);
-               printk(KERN_INFO "Code name: ");
-               for(i = 0; i < 4; i ++)
-                       printk(KERN_INFO "%c",
-                               flags->global_info_struct.codename[i]); 
-               printk(KERN_INFO "\nCode version: ");
-               for(i = 0; i < 4; i ++)
-                       printk(KERN_INFO "%c", 
-                               flags->global_info_struct.codeversion[i]); 
-               printk(KERN_INFO "\n"); 
-               break;
-       }
-
-isr_done:
-
-       card->in_isr = 0;
-       flags->interrupt_info_struct.interrupt_type = 0;
-       return;
-}
-
-/*============================================================================
- * Receive interrupt handler.
- */
-static void rx_intr (sdla_t* card)
-{
-       struct net_device *dev;
-       chdlc_private_area_t *chdlc_priv_area;
-       SHARED_MEMORY_INFO_STRUCT *flags = card->u.c.flags;
-       CHDLC_DATA_RX_STATUS_EL_STRUCT *rxbuf = card->u.c.rxmb;
-       struct sk_buff *skb;
-       unsigned len;
-       unsigned addr = rxbuf->ptr_data_bfr;
-       void *buf;
-       int i,udp_type;
-
-       if (rxbuf->opp_flag != 0x01) {
-               printk(KERN_INFO 
-                       "%s: corrupted Rx buffer @ 0x%X, flag = 0x%02X!\n", 
-                       card->devname, (unsigned)rxbuf, rxbuf->opp_flag);
-                printk(KERN_INFO "Code name: ");
-                for(i = 0; i < 4; i ++)
-                        printk(KERN_INFO "%c",
-                                flags->global_info_struct.codename[i]);
-                printk(KERN_INFO "\nCode version: ");
-                for(i = 0; i < 4; i ++)
-                        printk(KERN_INFO "%c",
-                                flags->global_info_struct.codeversion[i]);
-                printk(KERN_INFO "\n");
-
-
-               /* Bug Fix: Mar 6 2000
-                 * If we get a corrupted mailbox, it measn that driver 
-                 * is out of sync with the firmware. There is no recovery.
-                 * If we don't turn off all interrupts for this card
-                 * the machine will crash. 
-                 */
-               printk(KERN_INFO "%s: Critical router failure ...!!!\n", card->devname);
-               printk(KERN_INFO "Please contact Sangoma Technologies !\n");
-               chdlc_set_intr_mode(card,0);    
-               return;
-       }
-
-       len  = rxbuf->frame_length;
-
-       if (card->tty_opt){
-
-               if (rxbuf->error_flag){ 
-                       goto rx_exit;
-               }
-
-               if (len <= CRC_LENGTH){
-                       goto rx_exit;
-               }
-               
-               if (!card->u.c.async_mode){
-                       len -= CRC_LENGTH;
-               }
-
-               wanpipe_tty_receive(card,addr,len);
-               goto rx_exit;
-       }
-
-       dev = card->wandev.dev;
-
-       if (!dev){
-               goto rx_exit;
-       }
-
-       if (!netif_running(dev))
-               goto rx_exit;
-
-       chdlc_priv_area = dev->priv;
-
-       
-       /* Allocate socket buffer */
-       skb = dev_alloc_skb(len);
-
-       if (skb == NULL) {
-               printk(KERN_INFO "%s: no socket buffers available!\n",
-                                       card->devname);
-               ++card->wandev.stats.rx_dropped;
-               goto rx_exit;
-       }
-
-       /* Copy data to the socket buffer */
-       if((addr + len) > card->u.c.rx_top + 1) {
-               unsigned tmp = card->u.c.rx_top - addr + 1;
-               buf = skb_put(skb, tmp);
-               sdla_peek(&card->hw, addr, buf, tmp);
-               addr = card->u.c.rx_base;
-               len -= tmp;
-       }
-               
-       buf = skb_put(skb, len);
-       sdla_peek(&card->hw, addr, buf, len);
-
-       skb->protocol = htons(ETH_P_IP);
-
-       card->wandev.stats.rx_packets ++;
-       card->wandev.stats.rx_bytes += skb->len;
-       udp_type = udp_pkt_type( skb, card );
-
-       if(udp_type == UDP_CPIPE_TYPE) {
-               if(store_udp_mgmt_pkt(UDP_PKT_FRM_NETWORK,
-                                     card, skb, dev, chdlc_priv_area)) {
-                       flags->interrupt_info_struct.
-                                               interrupt_permission |= 
-                                                       APP_INT_ON_TIMER; 
-               }
-       } else if(card->u.c.usedby == API) {
-
-               api_rx_hdr_t* api_rx_hdr;
-                       skb_push(skb, sizeof(api_rx_hdr_t));
-                api_rx_hdr = (api_rx_hdr_t*)&skb->data[0x00];
-               api_rx_hdr->error_flag = rxbuf->error_flag;
-               api_rx_hdr->time_stamp = rxbuf->time_stamp;
-
-                skb->protocol = htons(PVC_PROT);
-               skb->mac.raw  = skb->data;
-               skb->dev      = dev;
-                       skb->pkt_type = WAN_PACKET_DATA;
-
-               bh_enqueue(dev, skb);
-
-               if (!test_and_set_bit(0,&chdlc_priv_area->tq_working))
-                       wanpipe_queue_work(&chdlc_priv_area->common.wanpipe_work);
-       }else{
-               /* FIXME: we should check to see if the received packet is a 
-                          multicast packet so that we can increment the multicast 
-                          statistic
-                          ++ chdlc_priv_area->if_stats.multicast;
-               */
-                       /* Pass it up the protocol stack */
-       
-                skb->dev = dev;
-                skb->mac.raw  = skb->data;
-                netif_rx(skb);
-                dev->last_rx = jiffies;
-       }
-
-rx_exit:
-       /* Release buffer element and calculate a pointer to the next one */
-       rxbuf->opp_flag = 0x00;
-       card->u.c.rxmb = ++ rxbuf;
-       if((void*)rxbuf > card->u.c.rxbuf_last){
-               card->u.c.rxmb = card->u.c.rxbuf_base;
-       }
-}
-
-/*============================================================================
- * Timer interrupt handler.
- * The timer interrupt is used for two purposes:
- *    1) Processing udp calls from 'cpipemon'.
- *    2) Reading board-level statistics for updating the proc file system.
- */
-void timer_intr(sdla_t *card)
-{
-        struct net_device* dev;
-        chdlc_private_area_t* chdlc_priv_area = NULL;
-        SHARED_MEMORY_INFO_STRUCT* flags = NULL;
-
-        if ((dev = card->wandev.dev)==NULL){
-               flags = card->u.c.flags;
-                flags->interrupt_info_struct.interrupt_permission &=
-                        ~APP_INT_ON_TIMER;
-               return;
-       }
-       
-        chdlc_priv_area = dev->priv;
-
-       if (chdlc_priv_area->timer_int_enabled & TMR_INT_ENABLED_CONFIG) {
-               if (!config_chdlc(card)){
-                       chdlc_priv_area->timer_int_enabled &= ~TMR_INT_ENABLED_CONFIG;
-               }
-       }
-
-       /* process a udp call if pending */
-               if(chdlc_priv_area->timer_int_enabled & TMR_INT_ENABLED_UDP) {
-                       process_udp_mgmt_pkt(card, dev,
-                       chdlc_priv_area);
-               chdlc_priv_area->timer_int_enabled &= ~TMR_INT_ENABLED_UDP;
-        }
-
-       /* read the communications statistics if required */
-       if(chdlc_priv_area->timer_int_enabled & TMR_INT_ENABLED_UPDATE) {
-               update_comms_stats(card, chdlc_priv_area);
-                if(!(-- chdlc_priv_area->update_comms_stats)) {
-                       chdlc_priv_area->timer_int_enabled &= 
-                               ~TMR_INT_ENABLED_UPDATE;
-               }
-        }
-
-       /* only disable the timer interrupt if there are no udp or statistic */
-       /* updates pending */
-        if(!chdlc_priv_area->timer_int_enabled) {
-                flags = card->u.c.flags;
-                flags->interrupt_info_struct.interrupt_permission &=
-                        ~APP_INT_ON_TIMER;
-        }
-}
-
-/*------------------------------------------------------------------------------
-  Miscellaneous Functions
-       - set_chdlc_config() used to set configuration options on the board
-------------------------------------------------------------------------------*/
-
-static int set_chdlc_config(sdla_t* card)
-{
-       CHDLC_CONFIGURATION_STRUCT cfg;
-
-       memset(&cfg, 0, sizeof(CHDLC_CONFIGURATION_STRUCT));
-
-       if(card->wandev.clocking){
-               cfg.baud_rate = card->wandev.bps;
-       }
-               
-       cfg.line_config_options = (card->wandev.interface == WANOPT_RS232) ?
-               INTERFACE_LEVEL_RS232 : INTERFACE_LEVEL_V35;
-
-       cfg.modem_config_options        = 0;
-       cfg.modem_status_timer          = 100;
-
-       cfg.CHDLC_protocol_options      = card->u.c.protocol_options;
-
-       if (card->tty_opt){
-               cfg.CHDLC_API_options   = DISCARD_RX_ERROR_FRAMES;
-       }
-       
-       cfg.percent_data_buffer_for_Tx  = (card->u.c.receive_only) ? 0 : 50;
-       cfg.CHDLC_statistics_options    = (CHDLC_TX_DATA_BYTE_COUNT_STAT |
-               CHDLC_RX_DATA_BYTE_COUNT_STAT);
-       
-       if (card->tty_opt){
-               card->wandev.mtu = TTY_CHDLC_MAX_MTU;
-       }
-       cfg.max_CHDLC_data_field_length = card->wandev.mtu;
-       cfg.transmit_keepalive_timer    = card->u.c.kpalv_tx;
-       cfg.receive_keepalive_timer     = card->u.c.kpalv_rx;
-       cfg.keepalive_error_tolerance   = card->u.c.kpalv_err;
-       cfg.SLARP_request_timer         = card->u.c.slarp_timer;
-
-       if (cfg.SLARP_request_timer) {
-               cfg.IP_address          = 0;
-               cfg.IP_netmask          = 0;
-               
-       }else if (card->wandev.dev){
-               struct net_device *dev = card->wandev.dev;
-               chdlc_private_area_t *chdlc_priv_area = dev->priv;
-               
-                struct in_device *in_dev = dev->ip_ptr;
-
-               if(in_dev != NULL) {
-                       struct in_ifaddr *ifa = in_dev->ifa_list;
-
-                       if (ifa != NULL ) {
-                               cfg.IP_address  = ntohl(ifa->ifa_local);
-                               cfg.IP_netmask  = ntohl(ifa->ifa_mask); 
-                               chdlc_priv_area->IP_address = ntohl(ifa->ifa_local);
-                               chdlc_priv_area->IP_netmask = ntohl(ifa->ifa_mask); 
-                       }
-               }
-
-               /* FIXME: We must re-think this message in next release
-               if((cfg.IP_address & 0x000000FF) > 2) {
-                       printk(KERN_WARNING "\n");
-                       printk(KERN_WARNING "  WARNING:%s configured with an\n",
-                               card->devname);
-                       printk(KERN_WARNING "  invalid local IP address.\n");
-                        printk(KERN_WARNING "  Slarp pragmatics will fail.\n");
-                        printk(KERN_WARNING "  IP address should be of the\n");
-                       printk(KERN_WARNING "  format A.B.C.1 or A.B.C.2.\n");
-               }
-               */              
-       }
-       
-       return chdlc_configure(card, &cfg);
-}
-
-
-/*-----------------------------------------------------------------------------
-   set_asy_config() used to set asynchronous configuration options on the board
-------------------------------------------------------------------------------*/
-
-static int set_asy_config(sdla_t* card)
-{
-
-        ASY_CONFIGURATION_STRUCT cfg;
-       CHDLC_MAILBOX_STRUCT *mailbox = card->mbox;
-       int err;
-
-       memset(&cfg, 0, sizeof(ASY_CONFIGURATION_STRUCT));
-
-       if(card->wandev.clocking)
-               cfg.baud_rate = card->wandev.bps;
-
-       cfg.line_config_options = (card->wandev.interface == WANOPT_RS232) ?
-               INTERFACE_LEVEL_RS232 : INTERFACE_LEVEL_V35;
-
-       cfg.modem_config_options        = 0;
-       cfg.asy_API_options             = card->u.c.api_options;
-       cfg.asy_protocol_options        = card->u.c.protocol_options;
-       cfg.Tx_bits_per_char            = card->u.c.tx_bits_per_char;
-       cfg.Rx_bits_per_char            = card->u.c.rx_bits_per_char;
-       cfg.stop_bits                   = card->u.c.stop_bits;
-       cfg.parity                      = card->u.c.parity;
-       cfg.break_timer                 = card->u.c.break_timer;
-       cfg.asy_Rx_inter_char_timer     = card->u.c.inter_char_timer; 
-       cfg.asy_Rx_complete_length      = card->u.c.rx_complete_length; 
-       cfg.XON_char                    = card->u.c.xon_char;
-       cfg.XOFF_char                   = card->u.c.xoff_char;
-       cfg.asy_statistics_options      = (CHDLC_TX_DATA_BYTE_COUNT_STAT |
-               CHDLC_RX_DATA_BYTE_COUNT_STAT);
-
-       mailbox->buffer_length = sizeof(ASY_CONFIGURATION_STRUCT);
-       memcpy(mailbox->data, &cfg, mailbox->buffer_length);
-       mailbox->command = SET_ASY_CONFIGURATION;
-       err = sdla_exec(mailbox) ? mailbox->return_code : CMD_TIMEOUT;
-       if (err != COMMAND_OK) 
-               chdlc_error (card, err, mailbox);
-       return err;
-}
-
-/*============================================================================
- * Enable asynchronous communications.
- */
-
-static int asy_comm_enable (sdla_t* card)
-{
-
-       int err;
-       CHDLC_MAILBOX_STRUCT* mb = card->mbox;
-
-       mb->buffer_length = 0;
-       mb->command = ENABLE_ASY_COMMUNICATIONS;
-       err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT;
-       if (err != COMMAND_OK && card->wandev.dev)
-               chdlc_error(card, err, mb);
-       
-       if (!err)
-               card->u.c.comm_enabled = 1;
-
-       return err;
-}
-
-/*============================================================================
- * Process global exception condition
- */
-static int process_global_exception(sdla_t *card)
-{
-       CHDLC_MAILBOX_STRUCT* mbox = card->mbox;
-       int err;
-
-       mbox->buffer_length = 0;
-       mbox->command = READ_GLOBAL_EXCEPTION_CONDITION;
-       err = sdla_exec(mbox) ? mbox->return_code : CMD_TIMEOUT;
-
-       if(err != CMD_TIMEOUT ){
-       
-               switch(mbox->return_code) {
-         
-               case EXCEP_MODEM_STATUS_CHANGE:
-
-                       printk(KERN_INFO "%s: Modem status change\n",
-                               card->devname);
-
-                       switch(mbox->data[0] & (DCD_HIGH | CTS_HIGH)) {
-                               case (DCD_HIGH):
-                                       printk(KERN_INFO "%s: DCD high, CTS low\n",card->devname);
-                                       break;
-                               case (CTS_HIGH):
-                                        printk(KERN_INFO "%s: DCD low, CTS high\n",card->devname); 
-                                       break;
-                                case ((DCD_HIGH | CTS_HIGH)):
-                                        printk(KERN_INFO "%s: DCD high, CTS high\n",card->devname);
-                                        break;
-                               default:
-                                        printk(KERN_INFO "%s: DCD low, CTS low\n",card->devname);
-                                        break;
-                       }
-                       break;
-
-                case EXCEP_TRC_DISABLED:
-                        printk(KERN_INFO "%s: Line trace disabled\n",
-                               card->devname);
-                        break;
-
-               case EXCEP_IRQ_TIMEOUT:
-                       printk(KERN_INFO "%s: IRQ timeout occurred\n",
-                               card->devname); 
-                       break;
-
-               case 0x17:
-                       if (card->tty_opt){
-                               if (card->tty && card->tty_open){ 
-                                       printk(KERN_INFO 
-                                               "%s: Modem Hangup Exception: Hanging Up!\n",
-                                               card->devname);
-                                       tty_hangup(card->tty);
-                               }
-                               break;
-                       }
-
-                       /* If TTY is not used just drop throught */
-                       
-                default:
-                        printk(KERN_INFO "%s: Global exception %x\n",
-                               card->devname, mbox->return_code);
-                        break;
-                }
-       }
-       return 0;
-}
-
-
-/*============================================================================
- * Process chdlc exception condition
- */
-static int process_chdlc_exception(sdla_t *card)
-{
-       CHDLC_MAILBOX_STRUCT* mb = card->mbox;
-       int err;
-
-       mb->buffer_length = 0;
-       mb->command = READ_CHDLC_EXCEPTION_CONDITION;
-       err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT;
-       if(err != CMD_TIMEOUT) {
-       
-               switch (err) {
-
-               case EXCEP_LINK_ACTIVE:
-                       port_set_state(card, WAN_CONNECTED);
-                       trigger_chdlc_poll(card->wandev.dev);
-                       break;
-
-               case EXCEP_LINK_INACTIVE_MODEM:
-                       port_set_state(card, WAN_DISCONNECTED);
-                       unconfigure_ip(card);
-                       trigger_chdlc_poll(card->wandev.dev);
-                       break;
-
-               case EXCEP_LINK_INACTIVE_KPALV:
-                       port_set_state(card, WAN_DISCONNECTED);
-                       printk(KERN_INFO "%s: Keepalive timer expired.\n",
-                                               card->devname);
-                       unconfigure_ip(card);
-                       trigger_chdlc_poll(card->wandev.dev);
-                       break;
-
-               case EXCEP_IP_ADDRESS_DISCOVERED:
-                       if (configure_ip(card)) 
-                               return -1;
-                       break;
-
-               case EXCEP_LOOPBACK_CONDITION:
-                       printk(KERN_INFO "%s: Loopback Condition Detected.\n",
-                                               card->devname);
-                       break;
-
-               case NO_CHDLC_EXCEP_COND_TO_REPORT:
-                       printk(KERN_INFO "%s: No exceptions reported.\n",
-                                               card->devname);
-                       break;
-               }
-
-       }
-       return 0;
-}
-
-
-/*============================================================================
- * Configure IP from SLARP negotiation
- * This adds dynamic routes when SLARP has provided valid addresses
- */
-
-static int configure_ip (sdla_t* card)
-{
-       struct net_device *dev = card->wandev.dev;
-        chdlc_private_area_t *chdlc_priv_area;
-        char err;
-
-       if (!dev)
-               return 0;
-
-       chdlc_priv_area = dev->priv;
-       
-       
-        /* set to discover */
-        if(card->u.c.slarp_timer != 0x00) {
-               CHDLC_MAILBOX_STRUCT* mb = card->mbox;
-               CHDLC_CONFIGURATION_STRUCT *cfg;
-
-               mb->buffer_length = 0;
-               mb->command = READ_CHDLC_CONFIGURATION;
-               err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT;
-       
-               if(err != COMMAND_OK) {
-                       chdlc_error(card,err,mb);
-                       return -1;
-               }
-
-               cfg = (CHDLC_CONFIGURATION_STRUCT *)mb->data;
-                chdlc_priv_area->IP_address = cfg->IP_address;
-                chdlc_priv_area->IP_netmask = cfg->IP_netmask;
-
-               /* Set flag to add route */
-               chdlc_priv_area->route_status = ADD_ROUTE;
-
-               /* The idea here is to add the route in the poll routine.
-               This way, we aren't in interrupt context when adding routes */
-               trigger_chdlc_poll(dev);
-        }
-
-       return 0;
-}
-
-
-/*============================================================================
- * Un-Configure IP negotiated by SLARP
- * This removes dynamic routes when the link becomes inactive.
- */
-
-static int unconfigure_ip (sdla_t* card)
-{
-       struct net_device *dev = card->wandev.dev;
-       chdlc_private_area_t *chdlc_priv_area;
-
-       if (!dev)
-               return 0;
-
-       chdlc_priv_area= dev->priv;
-       
-       if (chdlc_priv_area->route_status == ROUTE_ADDED) {
-
-               /* Note: If this function is called, the 
-                 * port state has been DISCONNECTED.  This state
-                 * change will trigger a poll_disconnected 
-                 * function, that will check for this condition. 
-                */
-               chdlc_priv_area->route_status = REMOVE_ROUTE;
-
-       }
-       return 0;
-}
-
-/*============================================================================
- * Routine to add/remove routes 
- * Called like a polling routine when Routes are flagged to be added/removed.
- */
-
-static void process_route (sdla_t *card)
-{
-        struct net_device *dev = card->wandev.dev;
-        unsigned char port_num;
-        chdlc_private_area_t *chdlc_priv_area = NULL;
-       u32 local_IP_addr = 0;
-       u32 remote_IP_addr = 0;
-       u32 IP_netmask, IP_addr;
-        int err = 0;
-       struct in_device *in_dev;
-       mm_segment_t fs;
-       struct ifreq if_info;
-        struct sockaddr_in *if_data1, *if_data2;
-       
-        chdlc_priv_area = dev->priv;
-        port_num = card->u.c.comm_port;
-
-       /* Bug Fix Mar 16 2000
-        * AND the IP address to the Mask before checking
-         * the last two bits. */
-
-       if((chdlc_priv_area->route_status == ADD_ROUTE) &&
-               ((chdlc_priv_area->IP_address & ~chdlc_priv_area->IP_netmask) > 2)) {
-
-               printk(KERN_INFO "%s: Dynamic route failure.\n",card->devname);
-
-                if(card->u.c.slarp_timer) {
-                       u32 addr_net = htonl(chdlc_priv_area->IP_address);
-
-                       printk(KERN_INFO "%s: Bad IP address %u.%u.%u.%u received\n",
-                               card->devname,
-                              NIPQUAD(addr_net));
-                        printk(KERN_INFO "%s: from remote station.\n",
-                               card->devname);
-
-                }else{ 
-                       u32 addr_net = htonl(chdlc_priv_area->IP_address);
-
-                        printk(KERN_INFO "%s: Bad IP address %u.%u.%u.%u issued\n",
-                              card->devname,
-                              NIPQUAD(addr_net));
-                        printk(KERN_INFO "%s: to remote station. Local\n",
-                               card->devname);
-                       printk(KERN_INFO "%s: IP address must be A.B.C.1\n",
-                               card->devname);
-                       printk(KERN_INFO "%s: or A.B.C.2.\n",card->devname);
-               }
-
-               /* remove the route due to the IP address error condition */
-               chdlc_priv_area->route_status = REMOVE_ROUTE;
-               err = 1;
-       }
-
-       /* If we are removing a route with bad IP addressing, then use the */
-       /* locally configured IP addresses */
-        if((chdlc_priv_area->route_status == REMOVE_ROUTE) && err) {
-
-               /* do not remove a bad route that has already been removed */
-               if(chdlc_priv_area->route_removed) {
-                       return;
-               }
-
-                in_dev = dev->ip_ptr;
-
-                if(in_dev != NULL) {
-                        struct in_ifaddr *ifa = in_dev->ifa_list;
-                        if (ifa != NULL ) {
-                                local_IP_addr = ifa->ifa_local;
-                                IP_netmask  = ifa->ifa_mask;
-                        }
-                }
-       }else{ 
-                       /* According to Cisco HDLC, if the point-to-point address is
-                  A.B.C.1, then we are the opposite (A.B.C.2), and vice-versa.
-               */
-               IP_netmask = ntohl(chdlc_priv_area->IP_netmask);
-               remote_IP_addr = ntohl(chdlc_priv_area->IP_address);
-       
-
-               /* If Netmask is 255.255.255.255 the local address
-                 * calculation will fail. Default it back to 255.255.255.0 */
-               if (IP_netmask == 0xffffffff)
-                       IP_netmask &= 0x00ffffff;
-
-               /* Bug Fix Mar 16 2000
-                * AND the Remote IP address with IP netmask, instead
-                 * of static netmask of 255.255.255.0 */
-               local_IP_addr = (remote_IP_addr & IP_netmask) +
-                       (~remote_IP_addr & ntohl(0x0003));
-
-               if(!card->u.c.slarp_timer) {
-                       IP_addr = local_IP_addr;
-                       local_IP_addr = remote_IP_addr;
-                       remote_IP_addr = IP_addr;
-                       }
-       }
-
-        fs = get_fs();                  /* Save file system  */
-        set_fs(get_ds());               /* Get user space block */
-
-        /* Setup a structure for adding/removing routes */
-        memset(&if_info, 0, sizeof(if_info));
-        strcpy(if_info.ifr_name, dev->name);
-
-       switch (chdlc_priv_area->route_status) {
-
-       case ADD_ROUTE:
-
-               if(!card->u.c.slarp_timer) {
-                       if_data2 = (struct sockaddr_in *)&if_info.ifr_dstaddr;
-                       if_data2->sin_addr.s_addr = remote_IP_addr;
-                       if_data2->sin_family = AF_INET;
-                       err = devinet_ioctl(SIOCSIFDSTADDR, &if_info);
-               } else { 
-                       if_data1 = (struct sockaddr_in *)&if_info.ifr_addr;
-                       if_data1->sin_addr.s_addr = local_IP_addr;
-                       if_data1->sin_family = AF_INET;
-                       if(!(err = devinet_ioctl(SIOCSIFADDR, &if_info))){
-                               if_data2 = (struct sockaddr_in *)&if_info.ifr_dstaddr;
-                               if_data2->sin_addr.s_addr = remote_IP_addr;
-                               if_data2->sin_family = AF_INET;
-                               err = devinet_ioctl(SIOCSIFDSTADDR, &if_info);
-                       }
-               }
-
-               if(err) {
-                       printk(KERN_INFO "%s: Add route %u.%u.%u.%u failed (%d)\n", 
-                               card->devname, NIPQUAD(remote_IP_addr), err);
-               } else {
-                       ((chdlc_private_area_t *)dev->priv)->route_status = ROUTE_ADDED;
-                       printk(KERN_INFO "%s: Dynamic route added.\n",
-                               card->devname);
-                       printk(KERN_INFO "%s:    Local IP addr : %u.%u.%u.%u\n",
-                               card->devname, NIPQUAD(local_IP_addr));
-                       printk(KERN_INFO "%s:    Remote IP addr: %u.%u.%u.%u\n",
-                               card->devname, NIPQUAD(remote_IP_addr));
-                       chdlc_priv_area->route_removed = 0;
-               }
-               break;
-
-
-       case REMOVE_ROUTE:
-       
-               /* Change the local ip address of the interface to 0.
-                * This will also delete the destination route.
-                */
-               if(!card->u.c.slarp_timer) {
-                       if_data2 = (struct sockaddr_in *)&if_info.ifr_dstaddr;
-                       if_data2->sin_addr.s_addr = 0;
-                       if_data2->sin_family = AF_INET;
-                       err = devinet_ioctl(SIOCSIFDSTADDR, &if_info);
-               } else {
-                       if_data1 = (struct sockaddr_in *)&if_info.ifr_addr;
-                       if_data1->sin_addr.s_addr = 0;
-                       if_data1->sin_family = AF_INET;
-                       err = devinet_ioctl(SIOCSIFADDR,&if_info);
-               
-               }
-               if(err) {
-                       printk(KERN_INFO
-                               "%s: Remove route %u.%u.%u.%u failed, (err %d)\n",
-                                       card->devname, NIPQUAD(remote_IP_addr),
-                                       err);
-               } else {
-                       ((chdlc_private_area_t *)dev->priv)->route_status =
-                               NO_ROUTE;
-                        printk(KERN_INFO "%s: Dynamic route removed: %u.%u.%u.%u\n",
-                                        card->devname, NIPQUAD(local_IP_addr)); 
-                       chdlc_priv_area->route_removed = 1;
-               }
-               break;
-       }
-
-        set_fs(fs);                     /* Restore file system */
-
-}
-
-
-/*=============================================================================
- * Store a UDP management packet for later processing.
- */
-
-static int store_udp_mgmt_pkt(char udp_pkt_src, sdla_t* card,
-                             struct sk_buff *skb, struct net_device* dev,
-                             chdlc_private_area_t* chdlc_priv_area)
-{
-       int udp_pkt_stored = 0;
-
-       if(!chdlc_priv_area->udp_pkt_lgth &&
-         (skb->len <= MAX_LGTH_UDP_MGNT_PKT)) {
-               chdlc_priv_area->udp_pkt_lgth = skb->len;
-               chdlc_priv_area->udp_pkt_src = udp_pkt_src;
-                       memcpy(chdlc_priv_area->udp_pkt_data, skb->data, skb->len);
-               chdlc_priv_area->timer_int_enabled = TMR_INT_ENABLED_UDP;
-               udp_pkt_stored = 1;
-       }
-
-       if(udp_pkt_src == UDP_PKT_FRM_STACK){
-               dev_kfree_skb_any(skb);
-       }else{
-                dev_kfree_skb_any(skb);
-       }
-               
-       return(udp_pkt_stored);
-}
-
-
-/*=============================================================================
- * Process UDP management packet.
- */
-
-static int process_udp_mgmt_pkt(sdla_t* card, struct net_device* dev,
-                               chdlc_private_area_t* chdlc_priv_area ) 
-{
-       unsigned char *buf;
-       unsigned int frames, len;
-       struct sk_buff *new_skb;
-       unsigned short buffer_length, real_len;
-       unsigned long data_ptr;
-       unsigned data_length;
-       int udp_mgmt_req_valid = 1;
-       CHDLC_MAILBOX_STRUCT *mb = card->mbox;
-       SHARED_MEMORY_INFO_STRUCT *flags = card->u.c.flags;
-       chdlc_udp_pkt_t *chdlc_udp_pkt;
-       struct timeval tv;
-       int err;
-       char ut_char;
-
-       chdlc_udp_pkt = (chdlc_udp_pkt_t *) chdlc_priv_area->udp_pkt_data;
-
-       if(chdlc_priv_area->udp_pkt_src == UDP_PKT_FRM_NETWORK){
-
-               /* Only these commands are support for remote debugging.
-                * All others are not */
-               switch(chdlc_udp_pkt->cblock.command) {
-
-                       case READ_GLOBAL_STATISTICS:
-                       case READ_MODEM_STATUS:  
-                       case READ_CHDLC_LINK_STATUS:
-                       case CPIPE_ROUTER_UP_TIME:
-                       case READ_COMMS_ERROR_STATS:
-                       case READ_CHDLC_OPERATIONAL_STATS:
-
-                       /* These two commands are executed for
-                        * each request */
-                       case READ_CHDLC_CONFIGURATION:
-                       case READ_CHDLC_CODE_VERSION:
-                               udp_mgmt_req_valid = 1;
-                               break;
-                       default:
-                               udp_mgmt_req_valid = 0;
-                               break;
-               } 
-       }
-       
-       if(!udp_mgmt_req_valid) {
-
-               /* set length to 0 */
-               chdlc_udp_pkt->cblock.buffer_length = 0;
-
-               /* set return code */
-               chdlc_udp_pkt->cblock.return_code = 0xCD;
-
-               if (net_ratelimit()){   
-                       printk(KERN_INFO 
-                       "%s: Warning, Illegal UDP command attempted from network: %x\n",
-                       card->devname,chdlc_udp_pkt->cblock.command);
-               }
-
-       } else {
-               unsigned long trace_status_cfg_addr = 0;
-               TRACE_STATUS_EL_CFG_STRUCT trace_cfg_struct;
-               TRACE_STATUS_ELEMENT_STRUCT trace_element_struct;
-
-               switch(chdlc_udp_pkt->cblock.command) {
-
-               case CPIPE_ENABLE_TRACING:
-                    if (!chdlc_priv_area->TracingEnabled) {
-
-                       /* OPERATE_DATALINE_MONITOR */
-
-                       mb->buffer_length = sizeof(LINE_TRACE_CONFIG_STRUCT);
-                       mb->command = SET_TRACE_CONFIGURATION;
-
-                       ((LINE_TRACE_CONFIG_STRUCT *)mb->data)->
-                               trace_config = TRACE_ACTIVE;
-                       /* Trace delay mode is not used because it slows
-                          down transfer and results in a standoff situation
-                          when there is a lot of data */
-
-                       /* Configure the Trace based on user inputs */
-                       ((LINE_TRACE_CONFIG_STRUCT *)mb->data)->trace_config |= 
-                                       chdlc_udp_pkt->data[0];
-
-                       ((LINE_TRACE_CONFIG_STRUCT *)mb->data)->
-                          trace_deactivation_timer = 4000;
-
-
-                       err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT;
-                       if (err != COMMAND_OK) {
-                               chdlc_error(card,err,mb);
-                               card->TracingEnabled = 0;
-                               chdlc_udp_pkt->cblock.return_code = err;
-                               mb->buffer_length = 0;
-                               break;
-                       } 
-
-                       /* Get the base address of the trace element list */
-                       mb->buffer_length = 0;
-                       mb->command = READ_TRACE_CONFIGURATION;
-                       err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT;
-
-                       if (err != COMMAND_OK) {
-                               chdlc_error(card,err,mb);
-                               chdlc_priv_area->TracingEnabled = 0;
-                               chdlc_udp_pkt->cblock.return_code = err;
-                               mb->buffer_length = 0;
-                               break;
-                       }       
-
-                       trace_status_cfg_addr =((LINE_TRACE_CONFIG_STRUCT *)
-                               mb->data) -> ptr_trace_stat_el_cfg_struct;
-
-                       sdla_peek(&card->hw, trace_status_cfg_addr,
-                                &trace_cfg_struct, sizeof(trace_cfg_struct));
-                   
-                       chdlc_priv_area->start_trace_addr = trace_cfg_struct.
-                               base_addr_trace_status_elements;
-
-                       chdlc_priv_area->number_trace_elements = 
-                                       trace_cfg_struct.number_trace_status_elements;
-
-                       chdlc_priv_area->end_trace_addr = (unsigned long)
-                                       ((TRACE_STATUS_ELEMENT_STRUCT *)
-                                        chdlc_priv_area->start_trace_addr + 
-                                        (chdlc_priv_area->number_trace_elements - 1));
-
-                       chdlc_priv_area->base_addr_trace_buffer = 
-                                       trace_cfg_struct.base_addr_trace_buffer;
-
-                       chdlc_priv_area->end_addr_trace_buffer = 
-                                       trace_cfg_struct.end_addr_trace_buffer;
-
-                       chdlc_priv_area->curr_trace_addr = 
-                                       trace_cfg_struct.next_trace_element_to_use;
-
-                       chdlc_priv_area->available_buffer_space = 2000 - 
-                                                                 sizeof(ip_pkt_t) -
-                                                                 sizeof(udp_pkt_t) -
-                                                                 sizeof(wp_mgmt_t) -
-                                                                 sizeof(cblock_t) -
-                                                                 sizeof(trace_info_t); 
-                    }
-                    chdlc_udp_pkt->cblock.return_code = COMMAND_OK;
-                    mb->buffer_length = 0;
-                    chdlc_priv_area->TracingEnabled = 1;
-                    break;
-          
-
-               case CPIPE_DISABLE_TRACING:
-                    if (chdlc_priv_area->TracingEnabled) {
-
-                       /* OPERATE_DATALINE_MONITOR */
-                       mb->buffer_length = sizeof(LINE_TRACE_CONFIG_STRUCT);
-                       mb->command = SET_TRACE_CONFIGURATION;
-                       ((LINE_TRACE_CONFIG_STRUCT *)mb->data)->
-                               trace_config = TRACE_INACTIVE;
-                       err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT;
-                    }          
-
-                    chdlc_priv_area->TracingEnabled = 0;
-                    chdlc_udp_pkt->cblock.return_code = COMMAND_OK;
-                    mb->buffer_length = 0;
-                    break;
-          
-
-               case CPIPE_GET_TRACE_INFO:
-
-                    if (!chdlc_priv_area->TracingEnabled) {
-                       chdlc_udp_pkt->cblock.return_code = 1;
-                       mb->buffer_length = 0;
-                       break;
-                    }
-
-                    chdlc_udp_pkt->trace_info.ismoredata = 0x00;
-                    buffer_length = 0; /* offset of packet already occupied */
-
-                    for (frames=0; frames < chdlc_priv_area->number_trace_elements; frames++){
-
-                       trace_pkt_t *trace_pkt = (trace_pkt_t *)
-                               &chdlc_udp_pkt->data[buffer_length];
-
-                       sdla_peek(&card->hw, chdlc_priv_area->curr_trace_addr,
-                                 (unsigned char *)&trace_element_struct,
-                                 sizeof(TRACE_STATUS_ELEMENT_STRUCT));
-
-                       if (trace_element_struct.opp_flag == 0x00) {
-                               break;
-                       }
-
-                       /* get pointer to real data */
-                       data_ptr = trace_element_struct.ptr_data_bfr;
-
-                       /* See if there is actual data on the trace buffer */
-                       if (data_ptr){
-                               data_length = trace_element_struct.trace_length;
-                       }else{
-                               data_length = 0;
-                               chdlc_udp_pkt->trace_info.ismoredata = 0x01;
-                       }
-       
-                       if( (chdlc_priv_area->available_buffer_space - buffer_length)
-                               < ( sizeof(trace_pkt_t) + data_length) ) {
-
-                            /* indicate there are more frames on board & exit */
-                               chdlc_udp_pkt->trace_info.ismoredata = 0x01;
-                                       break;
-                         }
-
-                       trace_pkt->status = trace_element_struct.trace_type;
-
-                       trace_pkt->time_stamp =
-                               trace_element_struct.trace_time_stamp;
-
-                       trace_pkt->real_length =
-                               trace_element_struct.trace_length;
-
-                       /* see if we can fit the frame into the user buffer */
-                       real_len = trace_pkt->real_length;
-
-                       if (data_ptr == 0) {
-                               trace_pkt->data_avail = 0x00;
-                       } else {
-                               unsigned tmp = 0;
-
-                               /* get the data from circular buffer
-                                   must check for end of buffer */
-                               trace_pkt->data_avail = 0x01;
-
-                               if ((data_ptr + real_len) >
-                                            chdlc_priv_area->end_addr_trace_buffer + 1){
-
-                                       tmp = chdlc_priv_area->end_addr_trace_buffer - data_ptr + 1;
-                                       sdla_peek(&card->hw, data_ptr,
-                                                 trace_pkt->data,tmp);
-                                       data_ptr = chdlc_priv_area->base_addr_trace_buffer;
-                               }
-       
-                               sdla_peek(&card->hw, data_ptr,
-                                         &trace_pkt->data[tmp], real_len - tmp);
-                       }       
-
-                       /* zero the opp flag to show we got the frame */
-                       ut_char = 0x00;
-                       sdla_poke(&card->hw, chdlc_priv_area->curr_trace_addr, &ut_char, 1);
-
-                               /* now move onto the next frame */
-                               chdlc_priv_area->curr_trace_addr += sizeof(TRACE_STATUS_ELEMENT_STRUCT);
-
-                               /* check if we went over the last address */
-                       if ( chdlc_priv_area->curr_trace_addr > chdlc_priv_area->end_trace_addr ) {
-                               chdlc_priv_area->curr_trace_addr = chdlc_priv_area->start_trace_addr;
-                               }
-
-                       if(trace_pkt->data_avail == 0x01) {
-                               buffer_length += real_len - 1;
-                       }
-        
-                       /* for the header */
-                       buffer_length += sizeof(trace_pkt_t);
-
-                    }  /* For Loop */
-
-                    if (frames == chdlc_priv_area->number_trace_elements){
-                       chdlc_udp_pkt->trace_info.ismoredata = 0x01;
-                    }
-                    chdlc_udp_pkt->trace_info.num_frames = frames;
-                
-                    mb->buffer_length = buffer_length;
-                    chdlc_udp_pkt->cblock.buffer_length = buffer_length; 
-                
-                    chdlc_udp_pkt->cblock.return_code = COMMAND_OK; 
-                    
-                    break;
-
-
-               case CPIPE_FT1_READ_STATUS:
-                       ((unsigned char *)chdlc_udp_pkt->data )[0] =
-                               flags->FT1_info_struct.parallel_port_A_input;
-
-                       ((unsigned char *)chdlc_udp_pkt->data )[1] =
-                               flags->FT1_info_struct.parallel_port_B_input;
-                               
-                       chdlc_udp_pkt->cblock.return_code = COMMAND_OK;
-                       chdlc_udp_pkt->cblock.buffer_length = 2;
-                       mb->buffer_length = 2;
-                       break;
-
-               case CPIPE_ROUTER_UP_TIME:
-                       do_gettimeofday( &tv );
-                       chdlc_priv_area->router_up_time = tv.tv_sec - 
-                                       chdlc_priv_area->router_start_time;
-                       *(unsigned long *)&chdlc_udp_pkt->data = 
-                                       chdlc_priv_area->router_up_time;        
-                       mb->buffer_length = sizeof(unsigned long);
-                       chdlc_udp_pkt->cblock.buffer_length = sizeof(unsigned long);
-                       chdlc_udp_pkt->cblock.return_code = COMMAND_OK;
-                       break;
-
-               case FT1_MONITOR_STATUS_CTRL:
-                       /* Enable FT1 MONITOR STATUS */
-                       if ((chdlc_udp_pkt->data[0] & ENABLE_READ_FT1_STATUS) ||  
-                               (chdlc_udp_pkt->data[0] & ENABLE_READ_FT1_OP_STATS)) {
-                       
-                               if( rCount++ != 0 ) {
-                                       chdlc_udp_pkt->cblock.
-                                       return_code = COMMAND_OK;
-                                       mb->buffer_length = 1;
-                                       break;
-                               }
-                       }
-
-                       /* Disable FT1 MONITOR STATUS */
-                       if( chdlc_udp_pkt->data[0] == 0) {
-
-                               if( --rCount != 0) {
-                                       chdlc_udp_pkt->cblock.
-                                       return_code = COMMAND_OK;
-                                       mb->buffer_length = 1;
-                                       break;
-                               } 
-                       }       
-                       goto dflt_1;
-
-               default:
-dflt_1:
-                       /* it's a board command */
-                       mb->command = chdlc_udp_pkt->cblock.command;
-                       mb->buffer_length = chdlc_udp_pkt->cblock.buffer_length;
-                       if (mb->buffer_length) {
-                               memcpy(&mb->data, (unsigned char *) chdlc_udp_pkt->
-                                                       data, mb->buffer_length);
-                       } 
-                       /* run the command on the board */
-                       err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT;
-                       if (err != COMMAND_OK) {
-                               break;
-                       }
-
-                       /* copy the result back to our buffer */
-                       memcpy(&chdlc_udp_pkt->cblock, mb, sizeof(cblock_t)); 
-                       
-                       if (mb->buffer_length) {
-                               memcpy(&chdlc_udp_pkt->data, &mb->data, 
-                                                               mb->buffer_length); 
-                       }
-
-               } /* end of switch */
-       } /* end of else */
-
-       /* Fill UDP TTL */
-       chdlc_udp_pkt->ip_pkt.ttl = card->wandev.ttl; 
-
-       len = reply_udp(chdlc_priv_area->udp_pkt_data, mb->buffer_length);
-       
-
-       if(chdlc_priv_area->udp_pkt_src == UDP_PKT_FRM_NETWORK){
-
-               /* Must check if we interrupted if_send() routine. The
-                * tx buffers might be used. If so drop the packet */
-               if (!test_bit(SEND_CRIT,&card->wandev.critical)) {
-               
-                       if(!chdlc_send(card, chdlc_priv_area->udp_pkt_data, len)) {
-                               ++ card->wandev.stats.tx_packets;
-                               card->wandev.stats.tx_bytes += len;
-                       }
-               }
-       } else {        
-       
-               /* Pass it up the stack
-                  Allocate socket buffer */
-               if ((new_skb = dev_alloc_skb(len)) != NULL) {
-                       /* copy data into new_skb */
-
-                       buf = skb_put(new_skb, len);
-                       memcpy(buf, chdlc_priv_area->udp_pkt_data, len);
-
-                       /* Decapsulate pkt and pass it up the protocol stack */
-                       new_skb->protocol = htons(ETH_P_IP);
-                       new_skb->dev = dev;
-                       new_skb->mac.raw  = new_skb->data;
-       
-                       netif_rx(new_skb);
-                       dev->last_rx = jiffies;
-               } else {
-               
-                       printk(KERN_INFO "%s: no socket buffers available!\n",
-                                       card->devname);
-               }
-       }
-       chdlc_priv_area->udp_pkt_lgth = 0;
-       
-       return 0;
-}
-
-/*============================================================================
- * Initialize Receive and Transmit Buffers.
- */
-
-static void init_chdlc_tx_rx_buff( sdla_t* card)
-{
-       CHDLC_MAILBOX_STRUCT* mb = card->mbox;
-       CHDLC_TX_STATUS_EL_CFG_STRUCT *tx_config;
-       CHDLC_RX_STATUS_EL_CFG_STRUCT *rx_config;
-       char err;
-       
-       mb->buffer_length = 0;
-       mb->command = READ_CHDLC_CONFIGURATION;
-       err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT;
-
-       if(err != COMMAND_OK) {
-               if (card->wandev.dev){
-                       chdlc_error(card,err,mb);
-               }
-               return;
-       }
-
-       if(card->hw.type == SDLA_S514) {
-               tx_config = (CHDLC_TX_STATUS_EL_CFG_STRUCT *)(card->hw.dpmbase +
-                (((CHDLC_CONFIGURATION_STRUCT *)mb->data)->
-                            ptr_CHDLC_Tx_stat_el_cfg_struct));
-               rx_config = (CHDLC_RX_STATUS_EL_CFG_STRUCT *)(card->hw.dpmbase +
-                (((CHDLC_CONFIGURATION_STRUCT *)mb->data)->
-                            ptr_CHDLC_Rx_stat_el_cfg_struct));
-
-                       /* Setup Head and Tails for buffers */
-               card->u.c.txbuf_base = (void *)(card->hw.dpmbase +
-                tx_config->base_addr_Tx_status_elements);
-               card->u.c.txbuf_last = 
-               (CHDLC_DATA_TX_STATUS_EL_STRUCT *)  
-                card->u.c.txbuf_base +
-               (tx_config->number_Tx_status_elements - 1);
-
-               card->u.c.rxbuf_base = (void *)(card->hw.dpmbase +
-                rx_config->base_addr_Rx_status_elements);
-               card->u.c.rxbuf_last =
-               (CHDLC_DATA_RX_STATUS_EL_STRUCT *)
-                card->u.c.rxbuf_base +
-               (rx_config->number_Rx_status_elements - 1);
-
-               /* Set up next pointer to be used */
-               card->u.c.txbuf = (void *)(card->hw.dpmbase +
-                tx_config->next_Tx_status_element_to_use);
-               card->u.c.rxmb = (void *)(card->hw.dpmbase +
-                rx_config->next_Rx_status_element_to_use);
-       }
-        else {
-                tx_config = (CHDLC_TX_STATUS_EL_CFG_STRUCT *)(card->hw.dpmbase +
-                       (((CHDLC_CONFIGURATION_STRUCT *)mb->data)->
-                       ptr_CHDLC_Tx_stat_el_cfg_struct % SDLA_WINDOWSIZE));
-
-                rx_config = (CHDLC_RX_STATUS_EL_CFG_STRUCT *)(card->hw.dpmbase +
-                       (((CHDLC_CONFIGURATION_STRUCT *)mb->data)->
-                       ptr_CHDLC_Rx_stat_el_cfg_struct % SDLA_WINDOWSIZE));
-
-                /* Setup Head and Tails for buffers */
-                card->u.c.txbuf_base = (void *)(card->hw.dpmbase +
-               (tx_config->base_addr_Tx_status_elements % SDLA_WINDOWSIZE));
-                card->u.c.txbuf_last =
-               (CHDLC_DATA_TX_STATUS_EL_STRUCT *)card->u.c.txbuf_base
-               + (tx_config->number_Tx_status_elements - 1);
-                card->u.c.rxbuf_base = (void *)(card->hw.dpmbase +
-               (rx_config->base_addr_Rx_status_elements % SDLA_WINDOWSIZE));
-                card->u.c.rxbuf_last = 
-               (CHDLC_DATA_RX_STATUS_EL_STRUCT *)card->u.c.rxbuf_base
-               + (rx_config->number_Rx_status_elements - 1);
-
-                 /* Set up next pointer to be used */
-                card->u.c.txbuf = (void *)(card->hw.dpmbase +
-               (tx_config->next_Tx_status_element_to_use % SDLA_WINDOWSIZE));
-                card->u.c.rxmb = (void *)(card->hw.dpmbase +
-               (rx_config->next_Rx_status_element_to_use % SDLA_WINDOWSIZE));
-        }
-
-        /* Setup Actual Buffer Start and end addresses */
-        card->u.c.rx_base = rx_config->base_addr_Rx_buffer;
-        card->u.c.rx_top  = rx_config->end_addr_Rx_buffer;
-
-}
-
-/*=============================================================================
- * Perform Interrupt Test by running READ_CHDLC_CODE_VERSION command MAX_INTR
- * _TEST_COUNTER times.
- */
-static int intr_test( sdla_t* card)
-{
-       CHDLC_MAILBOX_STRUCT* mb = card->mbox;
-       int err,i;
-
-       Intr_test_counter = 0;
-       
-       err = chdlc_set_intr_mode(card, APP_INT_ON_COMMAND_COMPLETE);
-
-       if (err == CMD_OK) { 
-               for (i = 0; i < MAX_INTR_TEST_COUNTER; i ++) {  
-                       mb->buffer_length  = 0;
-                       mb->command = READ_CHDLC_CODE_VERSION;
-                       err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT;
-                       if (err != CMD_OK) 
-                               chdlc_error(card, err, mb);
-               }
-       }
-       else {
-               return err;
-       }
-
-       err = chdlc_set_intr_mode(card, 0);
-
-       if (err != CMD_OK)
-               return err;
-
-       return 0;
-}
-
-/*==============================================================================
- * Determine what type of UDP call it is. CPIPEAB ?
- */
-static int udp_pkt_type(struct sk_buff *skb, sdla_t* card)
-{
-        chdlc_udp_pkt_t *chdlc_udp_pkt = (chdlc_udp_pkt_t *)skb->data;
-
-#ifdef _WAN_UDP_DEBUG
-               printk(KERN_INFO "SIG %s = %s\n\
-                                 UPP %x = %x\n\
-                                 PRT %x = %x\n\
-                                 REQ %i = %i\n\
-                                 36 th = %x 37th = %x\n",
-                                 chdlc_udp_pkt->wp_mgmt.signature,
-                                 UDPMGMT_SIGNATURE,
-                                 chdlc_udp_pkt->udp_pkt.udp_dst_port,
-                                 ntohs(card->wandev.udp_port),
-                                 chdlc_udp_pkt->ip_pkt.protocol,
-                                 UDPMGMT_UDP_PROTOCOL,
-                                 chdlc_udp_pkt->wp_mgmt.request_reply,
-                                 UDPMGMT_REQUEST,
-                                 skb->data[36], skb->data[37]);
-#endif 
-               
-       if (!strncmp(chdlc_udp_pkt->wp_mgmt.signature,UDPMGMT_SIGNATURE,8) &&
-          (chdlc_udp_pkt->udp_pkt.udp_dst_port == ntohs(card->wandev.udp_port)) &&
-          (chdlc_udp_pkt->ip_pkt.protocol == UDPMGMT_UDP_PROTOCOL) &&
-          (chdlc_udp_pkt->wp_mgmt.request_reply == UDPMGMT_REQUEST)) {
-
-               return UDP_CPIPE_TYPE;
-
-       }else{ 
-               return UDP_INVALID_TYPE;
-       }
-}
-
-/*============================================================================
- * Set PORT state.
- */
-static void port_set_state (sdla_t *card, int state)
-{
-        if (card->u.c.state != state)
-        {
-                switch (state)
-                {
-                case WAN_CONNECTED:
-                        printk (KERN_INFO "%s: Link connected!\n",
-                                card->devname);
-                       break;
-
-                case WAN_CONNECTING:
-                        printk (KERN_INFO "%s: Link connecting...\n",
-                                card->devname);
-                        break;
-
-                case WAN_DISCONNECTED:
-                        printk (KERN_INFO "%s: Link disconnected!\n",
-                                card->devname);
-                        break;
-                }
-
-                card->wandev.state = card->u.c.state = state;
-               if (card->wandev.dev){
-                       struct net_device *dev = card->wandev.dev;
-                       chdlc_private_area_t *chdlc_priv_area = dev->priv;
-                       chdlc_priv_area->common.state = state;
-               }
-        }
-}
-
-/*===========================================================================
- * config_chdlc
- *
- *     Configure the chdlc protocol and enable communications.         
- *
- *     The if_open() function binds this function to the poll routine.
- *      Therefore, this function will run every time the chdlc interface
- *      is brought up. We cannot run this function from the if_open 
- *      because if_open does not have access to the remote IP address.
- *      
- *     If the communications are not enabled, proceed to configure
- *      the card and enable communications.
- *
- *      If the communications are enabled, it means that the interface
- *      was shutdown by ether the user or driver. In this case, we 
- *      have to check that the IP addresses have not changed.  If
- *      the IP addresses have changed, we have to reconfigure the firmware
- *      and update the changed IP addresses.  Otherwise, just exit.
- *
- */
-
-static int config_chdlc (sdla_t *card)
-{
-       struct net_device *dev = card->wandev.dev;
-       chdlc_private_area_t *chdlc_priv_area = dev->priv;
-       SHARED_MEMORY_INFO_STRUCT *flags = card->u.c.flags;
-
-       if (card->u.c.comm_enabled){
-
-               /* Jun 20. 2000: NC
-                * IP addresses are not used in the API mode */
-               
-               if ((chdlc_priv_area->ip_local_tmp != chdlc_priv_area->ip_local ||
-                    chdlc_priv_area->ip_remote_tmp != chdlc_priv_area->ip_remote) && 
-                    card->u.c.usedby == WANPIPE) {
-                       
-                       /* The IP addersses have changed, we must
-                         * stop the communications and reconfigure
-                         * the card. Reason: the firmware must know
-                         * the local and remote IP addresses. */
-                       disable_comm(card);
-                       port_set_state(card, WAN_DISCONNECTED);
-                       printk(KERN_INFO 
-                               "%s: IP addresses changed!\n",
-                                       card->devname);
-                       printk(KERN_INFO 
-                               "%s: Restarting communications ...\n",
-                                       card->devname);
-               }else{ 
-                       /* IP addresses are the same and the link is up, 
-                         * we don't have to do anything here. Therefore, exit */
-                       return 0;
-               }
-       }
-
-       chdlc_priv_area->ip_local = chdlc_priv_area->ip_local_tmp;
-       chdlc_priv_area->ip_remote = chdlc_priv_area->ip_remote_tmp;
-
-
-       /* Setup the Board for asynchronous mode */
-       if (card->u.c.async_mode){
-               
-               if (set_asy_config(card)) {
-                       printk (KERN_INFO "%s: Failed CHDLC Async configuration!\n",
-                               card->devname);
-                       return 0;
-               }
-       }else{
-               /* Setup the Board for CHDLC */
-               if (set_chdlc_config(card)) {
-                       printk (KERN_INFO "%s: Failed CHDLC configuration!\n",
-                               card->devname);
-                       return 0;
-               }
-       }
-
-       /* Set interrupt mode and mask */
-        if (chdlc_set_intr_mode(card, APP_INT_ON_RX_FRAME |
-                               APP_INT_ON_GLOBAL_EXCEP_COND |
-                               APP_INT_ON_TX_FRAME |
-                               APP_INT_ON_CHDLC_EXCEP_COND | APP_INT_ON_TIMER)){
-               printk (KERN_INFO "%s: Failed to set interrupt triggers!\n",
-                               card->devname);
-               return 0;       
-        }
-       
-
-       /* Mask the Transmit and Timer interrupt */
-       flags->interrupt_info_struct.interrupt_permission &= 
-               ~(APP_INT_ON_TX_FRAME | APP_INT_ON_TIMER);
-
-       /* In TTY mode, receive interrupt will be enabled during
-        * wanpipe_tty_open() operation */
-       if (card->tty_opt){
-               flags->interrupt_info_struct.interrupt_permission &= ~APP_INT_ON_RX_FRAME;
-       }
-
-       /* Enable communications */
-       if (card->u.c.async_mode){
-               if (asy_comm_enable(card) != 0) {
-                       printk(KERN_INFO "%s: Failed to enable async commnunication!\n",
-                                       card->devname);
-                       flags->interrupt_info_struct.interrupt_permission = 0;
-                       card->u.c.comm_enabled=0;
-                       chdlc_set_intr_mode(card,0);
-                       return 0;
-               }
-        }else{ 
-               if (chdlc_comm_enable(card) != 0) {
-                       printk(KERN_INFO "%s: Failed to enable chdlc communications!\n",
-                                       card->devname);
-                       flags->interrupt_info_struct.interrupt_permission = 0;
-                       card->u.c.comm_enabled=0;
-                       chdlc_set_intr_mode(card,0);
-                       return 0;
-               }
-       }
-
-       /* Initialize Rx/Tx buffer control fields */
-       init_chdlc_tx_rx_buff(card);
-       port_set_state(card, WAN_CONNECTING);
-       return 0; 
-}
-
-
-/*============================================================
- * chdlc_poll
- *     
- * Rationale:
- *     We cannot manipulate the routing tables, or
- *      ip addresses withing the interrupt. Therefore
- *      we must perform such actons outside an interrupt 
- *      at a later time. 
- *
- * Description:        
- *     CHDLC polling routine, responsible for 
- *             shutting down interfaces upon disconnect
- *             and adding/removing routes. 
- *      
- * Usage:        
- *     This function is executed for each CHDLC  
- *     interface through a tq_schedule bottom half.
- *      
- *      trigger_chdlc_poll() function is used to kick
- *      the chldc_poll routine.  
- */
-
-static void chdlc_poll(struct net_device *dev)
-{
-       chdlc_private_area_t *chdlc_priv_area;
-       sdla_t *card;
-       u8 check_gateway=0;     
-       SHARED_MEMORY_INFO_STRUCT* flags;
-
-       
-       if (!dev || (chdlc_priv_area=dev->priv) == NULL)
-               return;
-
-       card = chdlc_priv_area->card;
-       flags = card->u.c.flags;
-       
-       /* (Re)Configuraiton is in progress, stop what you are 
-        * doing and get out */
-       if (test_bit(PERI_CRIT,&card->wandev.critical)){
-               clear_bit(POLL_CRIT,&card->wandev.critical);
-               return;
-       }
-       
-       /* if_open() function has triggered the polling routine
-        * to determine the configured IP addresses.  Once the
-        * addresses are found, trigger the chdlc configuration */
-       if (test_bit(0,&chdlc_priv_area->config_chdlc)){
-
-               chdlc_priv_area->ip_local_tmp  = get_ip_address(dev,WAN_LOCAL_IP);
-               chdlc_priv_area->ip_remote_tmp = get_ip_address(dev,WAN_POINTOPOINT_IP);
-       
-              /* Jun 20. 2000 Bug Fix
-               * Only perform this check in WANPIPE mode, since
-               * IP addresses are not used in the API mode. */
-       
-               if (chdlc_priv_area->ip_local_tmp == chdlc_priv_area->ip_remote_tmp && 
-                   card->u.c.slarp_timer == 0x00 && 
-                   !card->u.c.backup && 
-                   card->u.c.usedby == WANPIPE){
-
-                       if (++chdlc_priv_area->ip_error > MAX_IP_ERRORS){
-                               printk(KERN_INFO "\n%s: --- WARNING ---\n",
-                                               card->devname);
-                               printk(KERN_INFO 
-                               "%s: The local IP address is the same as the\n",
-                                               card->devname);
-                               printk(KERN_INFO 
-                               "%s: Point-to-Point IP address.\n",
-                                               card->devname);
-                               printk(KERN_INFO "%s: --- WARNING ---\n\n",
-                                               card->devname);
-                       }else{
-                               clear_bit(POLL_CRIT,&card->wandev.critical);
-                               chdlc_priv_area->poll_delay_timer.expires = jiffies+HZ;
-                               add_timer(&chdlc_priv_area->poll_delay_timer);
-                               return;
-                       }
-               }
-
-               clear_bit(0,&chdlc_priv_area->config_chdlc);
-               clear_bit(POLL_CRIT,&card->wandev.critical);
-               
-               chdlc_priv_area->timer_int_enabled |= TMR_INT_ENABLED_CONFIG;
-               flags->interrupt_info_struct.interrupt_permission |= APP_INT_ON_TIMER;
-               return;
-       }
-       /* Dynamic interface implementation, as well as dynamic
-        * routing.  */
-       
-       switch (card->u.c.state){
-
-       case WAN_DISCONNECTED:
-
-               /* If the dynamic interface configuration is on, and interface 
-                * is up, then bring down the netowrk interface */
-               
-               if (test_bit(DYN_OPT_ON,&chdlc_priv_area->interface_down) && 
-                   !test_bit(DEV_DOWN,  &chdlc_priv_area->interface_down) &&           
-                   card->wandev.dev->flags & IFF_UP){  
-
-                       printk(KERN_INFO "%s: Interface %s down.\n",
-                               card->devname,card->wandev.dev->name);
-                       change_dev_flags(card->wandev.dev,(card->wandev.dev->flags&~IFF_UP));
-                       set_bit(DEV_DOWN,&chdlc_priv_area->interface_down);
-                       chdlc_priv_area->route_status = NO_ROUTE;
-
-               }else{
-                       /* We need to check if the local IP address is
-                                * zero. If it is, we shouldn't try to remove it.
-                        */
-
-                       if (card->wandev.dev->flags & IFF_UP && 
-                           get_ip_address(card->wandev.dev,WAN_LOCAL_IP) && 
-                           chdlc_priv_area->route_status != NO_ROUTE &&
-                           card->u.c.slarp_timer){
-
-                               process_route(card);
-                       }
-               }
-               break;
-
-       case WAN_CONNECTED:
-
-               /* In SMP machine this code can execute before the interface
-                * comes up.  In this case, we must make sure that we do not
-                * try to bring up the interface before dev_open() is finished */
-
-
-               /* DEV_DOWN will be set only when we bring down the interface
-                * for the very first time. This way we know that it was us
-                * that brought the interface down */
-               
-               if (test_bit(DYN_OPT_ON,&chdlc_priv_area->interface_down) &&
-                   test_bit(DEV_DOWN,  &chdlc_priv_area->interface_down) &&
-                   !(card->wandev.dev->flags & IFF_UP)){
-                       
-                       printk(KERN_INFO "%s: Interface %s up.\n",
-                               card->devname,card->wandev.dev->name);
-                       change_dev_flags(card->wandev.dev,(card->wandev.dev->flags|IFF_UP));
-                       clear_bit(DEV_DOWN,&chdlc_priv_area->interface_down);
-                       check_gateway=1;
-               }
-
-               if (chdlc_priv_area->route_status == ADD_ROUTE && 
-                   card->u.c.slarp_timer){ 
-
-                       process_route(card);
-                       check_gateway=1;
-               }
-
-               if (chdlc_priv_area->gateway && check_gateway)
-                       add_gateway(card,dev);
-
-               break;
-       }       
-
-       clear_bit(POLL_CRIT,&card->wandev.critical);
-}
-
-/*============================================================
- * trigger_chdlc_poll
- *
- * Description:
- *     Add a chdlc_poll() work entry into the keventd work queue
- *      for a specific dlci/interface.  This will kick
- *      the fr_poll() routine at a later time. 
- *
- * Usage:
- *     Interrupts use this to defer a taks to 
- *      a polling routine.
- *
- */    
-static void trigger_chdlc_poll(struct net_device *dev)
-{
-       chdlc_private_area_t *chdlc_priv_area;
-       sdla_t *card;
-
-       if (!dev)
-               return;
-       
-       if ((chdlc_priv_area = dev->priv)==NULL)
-               return;
-
-       card = chdlc_priv_area->card;
-       
-       if (test_and_set_bit(POLL_CRIT,&card->wandev.critical)){
-               return;
-       }
-       if (test_bit(PERI_CRIT,&card->wandev.critical)){
-               return; 
-       }
-       schedule_work(&chdlc_priv_area->poll_work);
-}
-
-
-static void chdlc_poll_delay (unsigned long dev_ptr)
-{
-       struct net_device *dev = (struct net_device *)dev_ptr;
-       trigger_chdlc_poll(dev);
-}
-
-
-void s508_lock (sdla_t *card, unsigned long *smp_flags)
-{
-       spin_lock_irqsave(&card->wandev.lock, *smp_flags);
-        if (card->next){
-               spin_lock(&card->next->wandev.lock);
-       }
-}
-
-void s508_unlock (sdla_t *card, unsigned long *smp_flags)
-{
-        if (card->next){
-               spin_unlock(&card->next->wandev.lock);
-        }
-        spin_unlock_irqrestore(&card->wandev.lock, *smp_flags);
-}
-
-//*********** TTY SECTION ****************
-
-static void wanpipe_tty_trigger_tx_irq(sdla_t *card)
-{
-       SHARED_MEMORY_INFO_STRUCT *flags = card->u.c.flags;
-       INTERRUPT_INFORMATION_STRUCT *chdlc_int = &flags->interrupt_info_struct;
-       chdlc_int->interrupt_permission |= APP_INT_ON_TX_FRAME;
-}
-
-static void wanpipe_tty_trigger_poll(sdla_t *card)
-{
-       schedule_work(&card->tty_work);
-}
-
-static void tty_poll_work (void* data)
-{
-       sdla_t *card = (sdla_t*)data;
-       struct tty_struct *tty;
-
-       if ((tty=card->tty)==NULL)
-               return;
-       
-       tty_wakeup(tty);
-#if defined(SERIAL_HAVE_POLL_WAIT)
-       wake_up_interruptible(&tty->poll_wait);
-#endif 
-       return;
-}
-
-static void wanpipe_tty_close(struct tty_struct *tty, struct file * filp)
-{
-       sdla_t *card;
-       unsigned long smp_flags;
-       
-       if (!tty || !tty->driver_data){
-               return;
-       }
-       
-       card = (sdla_t*)tty->driver_data;
-       
-       if (!card)
-               return;
-
-       printk(KERN_INFO "%s: Closing TTY Driver!\n",
-                       card->devname);
-
-       /* Sanity Check */
-       if (!card->tty_open)
-               return;
-       
-       wanpipe_close(card);
-       if (--card->tty_open == 0){
-
-               lock_adapter_irq(&card->wandev.lock,&smp_flags);        
-               card->tty=NULL;
-               chdlc_disable_comm_shutdown(card);
-               unlock_adapter_irq(&card->wandev.lock,&smp_flags);
-
-               kfree(card->tty_buf);
-               card->tty_buf = NULL;                   
-               kfree(card->tty_rx);
-               card->tty_rx = NULL;
-       }
-       return;
-}
-static int wanpipe_tty_open(struct tty_struct *tty, struct file * filp)
-{
-       unsigned long smp_flags;
-       sdla_t *card;
-       
-       if (!tty){
-               return -ENODEV;
-       }
-       
-       if (!tty->driver_data){
-               int port;
-               port = tty->index;
-               if ((port < 0) || (port >= NR_PORTS)) 
-                       return -ENODEV;
-               
-               tty->driver_data = WAN_CARD(port);
-               if (!tty->driver_data)
-                       return -ENODEV;
-       }
-
-       card = (sdla_t*)tty->driver_data;
-
-       if (!card){
-               lock_adapter_irq(&card->wandev.lock,&smp_flags);        
-               card->tty=NULL;
-               unlock_adapter_irq(&card->wandev.lock,&smp_flags);
-               return -ENODEV;
-       }
-
-       printk(KERN_INFO "%s: Opening TTY Driver!\n",
-                       card->devname);
-
-       if (card->tty_open == 0){
-               lock_adapter_irq(&card->wandev.lock,&smp_flags);        
-               card->tty=tty;
-               unlock_adapter_irq(&card->wandev.lock,&smp_flags);
-
-               if (!card->tty_buf){
-                       card->tty_buf = kmalloc(TTY_CHDLC_MAX_MTU, GFP_KERNEL);
-                       if (!card->tty_buf){
-                               card->tty_buf=NULL;
-                               card->tty=NULL;
-                               return -ENOMEM; 
-                       }
-               }
-
-               if (!card->tty_rx){
-                       card->tty_rx = kmalloc(TTY_CHDLC_MAX_MTU, GFP_KERNEL);
-                       if (!card->tty_rx){
-                               /* Free the buffer above */
-                               kfree(card->tty_buf);
-                               card->tty_buf=NULL;
-                               card->tty=NULL;
-                               return -ENOMEM; 
-                       }
-               }
-       }
-
-       ++card->tty_open;
-       wanpipe_open(card);
-       return 0;
-}
-
-static int wanpipe_tty_write(struct tty_struct * tty, const unsigned char *buf, int count)
-{
-       unsigned long smp_flags=0;
-       sdla_t *card=NULL;
-
-       if (!tty){
-               dbg_printk(KERN_INFO "NO TTY in Write\n");
-               return -ENODEV;
-       }
-
-       card = (sdla_t *)tty->driver_data;
-                       
-       if (!card){
-               dbg_printk(KERN_INFO "No Card in TTY Write\n");
-               return -ENODEV;
-       }       
-
-       if (count > card->wandev.mtu){
-               dbg_printk(KERN_INFO "Frame too big in Write %i Max: %i\n",
-                               count,card->wandev.mtu);
-               return -EINVAL;
-       }
-       
-       if (card->wandev.state != WAN_CONNECTED){
-               dbg_printk(KERN_INFO "Card not connected in TTY Write\n");
-               return -EINVAL;
-       }
-
-       /* Lock the 508 Card: SMP is supported */
-       if(card->hw.type != SDLA_S514){
-               s508_lock(card,&smp_flags);
-       } 
-       
-       if (test_and_set_bit(SEND_CRIT,(void*)&card->wandev.critical)){
-               printk(KERN_INFO "%s: Critical in TTY Write\n",
-                               card->devname);
-               
-               /* Lock the 508 Card: SMP is supported */
-               if(card->hw.type != SDLA_S514)
-                       s508_unlock(card,&smp_flags);
-               
-               return -EINVAL; 
-       }
-       
-       if (chdlc_send(card,(void*)buf,count)){
-               dbg_printk(KERN_INFO "%s: Failed to send, retry later: kernel!\n",
-                               card->devname);
-               clear_bit(SEND_CRIT,(void*)&card->wandev.critical);
-
-               wanpipe_tty_trigger_tx_irq(card);
-               
-               if(card->hw.type != SDLA_S514)
-                       s508_unlock(card,&smp_flags);
-               return 0;
-       }
-       dbg_printk(KERN_INFO "%s: Packet sent OK: %i\n",card->devname,count);
-       clear_bit(SEND_CRIT,(void*)&card->wandev.critical);
-       
-       if(card->hw.type != SDLA_S514)
-               s508_unlock(card,&smp_flags);
-
-       return count;
-}
-
-static void wanpipe_tty_receive(sdla_t *card, unsigned addr, unsigned int len)
-{
-       unsigned offset=0;
-       unsigned olen=len;
-       char fp=0;
-       struct tty_struct *tty;
-       int i;
-       struct tty_ldisc *ld;
-       
-       if (!card->tty_open){
-               dbg_printk(KERN_INFO "%s: TTY not open during receive\n",
-                               card->devname);
-               return;
-       }
-       
-       if ((tty=card->tty) == NULL){
-               dbg_printk(KERN_INFO "%s: No TTY on receive\n",
-                               card->devname);
-               return;
-       }
-       
-       if (!tty->driver_data){
-               dbg_printk(KERN_INFO "%s: No Driver Data, or Flip on receive\n",
-                               card->devname);
-               return;
-       }
-       
-
-       if (card->u.c.async_mode){
-               if ((tty->flip.count+len) >= TTY_FLIPBUF_SIZE){
-                       if (net_ratelimit()){
-                               printk(KERN_INFO 
-                                       "%s: Received packet size too big: %i bytes, Max: %i!\n",
-                                       card->devname,len,TTY_FLIPBUF_SIZE);
-                       }
-                       return;
-               }
-
-               
-               if((addr + len) > card->u.c.rx_top + 1) {
-                       offset = card->u.c.rx_top - addr + 1;
-                       
-                       sdla_peek(&card->hw, addr, tty->flip.char_buf_ptr, offset);
-                       
-                       addr = card->u.c.rx_base;
-                       len -= offset;
-                       
-                       tty->flip.char_buf_ptr+=offset;
-                       tty->flip.count+=offset;
-                       for (i=0;i<offset;i++){
-                               *tty->flip.flag_buf_ptr = 0;
-                               tty->flip.flag_buf_ptr++;
-                       }
-               }
-               
-               sdla_peek(&card->hw, addr, tty->flip.char_buf_ptr, len);
-                       
-               tty->flip.char_buf_ptr+=len;
-               card->tty->flip.count+=len;
-               for (i=0;i<len;i++){
-                       *tty->flip.flag_buf_ptr = 0;
-                       tty->flip.flag_buf_ptr++;
-               }
-
-               tty->low_latency=1;
-               tty_flip_buffer_push(tty);
-       }else{
-               if (!card->tty_rx){     
-                       if (net_ratelimit()){
-                               printk(KERN_INFO 
-                               "%s: Receive sync buffer not available!\n",
-                                card->devname);
-                       }
-                       return;
-               }
-       
-               if (len > TTY_CHDLC_MAX_MTU){
-                       if (net_ratelimit()){
-                               printk(KERN_INFO 
-                               "%s: Received packet size too big: %i bytes, Max: %i!\n",
-                                       card->devname,len,TTY_FLIPBUF_SIZE);
-                       }
-                       return;
-               }
-
-               
-               if((addr + len) > card->u.c.rx_top + 1) {
-                       offset = card->u.c.rx_top - addr + 1;
-                       
-                       sdla_peek(&card->hw, addr, card->tty_rx, offset);
-                       
-                       addr = card->u.c.rx_base;
-                       len -= offset;
-               }
-               sdla_peek(&card->hw, addr, card->tty_rx+offset, len);
-               ld = tty_ldisc_ref(tty);
-               if (ld) {
-                       if (ld->receive_buf)
-                               ld->receive_buf(tty,card->tty_rx,&fp,olen);
-                       tty_ldisc_deref(ld);
-               }else{
-                       if (net_ratelimit()){
-                               printk(KERN_INFO 
-                                       "%s: NO TTY Sync line discipline!\n",
-                                       card->devname);
-                       }
-               }
-       }
-
-       dbg_printk(KERN_INFO "%s: Received Data %i\n",card->devname,olen);
-       return;
-}
-
-#if 0
-static int wanpipe_tty_ioctl(struct tty_struct *tty, struct file * file,
-                   unsigned int cmd, unsigned long arg)
-{
-       return -ENOIOCTLCMD;
-}
-#endif
-
-static void wanpipe_tty_stop(struct tty_struct *tty)
-{
-       return;
-}
-
-static void wanpipe_tty_start(struct tty_struct *tty)
-{
-       return;
-}
-
-static int config_tty (sdla_t *card)
-{
-       SHARED_MEMORY_INFO_STRUCT *flags = card->u.c.flags;
-
-       /* Setup the Board for asynchronous mode */
-       if (card->u.c.async_mode){
-               
-               if (set_asy_config(card)) {
-                       printk (KERN_INFO "%s: Failed CHDLC Async configuration!\n",
-                               card->devname);
-                       return -EINVAL;
-               }
-       }else{
-               /* Setup the Board for CHDLC */
-               if (set_chdlc_config(card)) {
-                       printk (KERN_INFO "%s: Failed CHDLC configuration!\n",
-                               card->devname);
-                       return -EINVAL;
-               }
-       }
-
-       /* Set interrupt mode and mask */
-        if (chdlc_set_intr_mode(card, APP_INT_ON_RX_FRAME |
-                               APP_INT_ON_GLOBAL_EXCEP_COND |
-                               APP_INT_ON_TX_FRAME |
-                               APP_INT_ON_CHDLC_EXCEP_COND | APP_INT_ON_TIMER)){
-               printk (KERN_INFO "%s: Failed to set interrupt triggers!\n",
-                               card->devname);
-               return -EINVAL; 
-        }
-       
-
-       /* Mask the Transmit and Timer interrupt */
-       flags->interrupt_info_struct.interrupt_permission &= 
-               ~(APP_INT_ON_TX_FRAME | APP_INT_ON_TIMER);
-
-       
-       /* Enable communications */
-       if (card->u.c.async_mode){
-               if (asy_comm_enable(card) != 0) {
-                       printk(KERN_INFO "%s: Failed to enable async commnunication!\n",
-                                       card->devname);
-                       flags->interrupt_info_struct.interrupt_permission = 0;
-                       card->u.c.comm_enabled=0;
-                       chdlc_set_intr_mode(card,0);
-                       return -EINVAL;
-               }
-        }else{ 
-               if (chdlc_comm_enable(card) != 0) {
-                       printk(KERN_INFO "%s: Failed to enable chdlc communications!\n",
-                                       card->devname);
-                       flags->interrupt_info_struct.interrupt_permission = 0;
-                       card->u.c.comm_enabled=0;
-                       chdlc_set_intr_mode(card,0);
-                       return -EINVAL;
-               }
-       }
-
-       /* Initialize Rx/Tx buffer control fields */
-       init_chdlc_tx_rx_buff(card);
-       port_set_state(card, WAN_CONNECTING);
-       return 0; 
-}
-
-
-static int change_speed(sdla_t *card, struct tty_struct *tty,
-                        struct termios *old_termios)
-{
-       int     baud, ret=0;
-       unsigned cflag; 
-       int     dbits,sbits,parity,handshaking;
-
-       cflag = tty->termios->c_cflag;
-
-       /* There is always one stop bit */
-       sbits=WANOPT_ONE;
-       
-       /* Parity is defaulted to NONE */
-       parity = WANOPT_NONE;
-
-       handshaking=0;
-       
-       /* byte size and parity */
-       switch (cflag & CSIZE) {
-             case CS5: dbits = 5; break;
-             case CS6: dbits = 6; break;
-             case CS7: dbits = 7; break;
-             case CS8: dbits = 8; break;
-             /* Never happens, but GCC is too dumb to figure it out */
-             default:  dbits = 8; break;
-       }
-       
-       /* One more stop bit should be supported, thus increment
-        * the number of stop bits Max=2 */
-       if (cflag & CSTOPB) {
-               sbits = WANOPT_TWO;
-       }
-       if (cflag & PARENB) {
-               parity = WANOPT_EVEN;
-       }
-       if (cflag & PARODD){
-               parity = WANOPT_ODD;
-       }
-
-       /* Determine divisor based on baud rate */
-       baud = tty_get_baud_rate(tty);
-
-       if (!baud)
-               baud = 9600;    /* B0 transition handled in rs_set_termios */
-
-       if (cflag & CRTSCTS) {
-               handshaking|=ASY_RTS_HS_FOR_RX;
-       }
-       
-       if (I_IGNPAR(tty))
-               parity = WANOPT_NONE;
-
-       if (I_IXOFF(tty)){
-               handshaking|=ASY_XON_XOFF_HS_FOR_RX;
-               handshaking|=ASY_XON_XOFF_HS_FOR_TX;
-       }
-
-       if (I_IXON(tty)){
-               handshaking|=ASY_XON_XOFF_HS_FOR_RX;
-               handshaking|=ASY_XON_XOFF_HS_FOR_TX;
-       }
-
-       if (card->u.c.async_mode){
-               if (card->wandev.bps != baud)
-                       ret=1;
-               card->wandev.bps = baud;
-       }
-
-       if (card->u.c.async_mode){
-               if (card->u.c.protocol_options != handshaking)
-                       ret=1;
-               card->u.c.protocol_options = handshaking;
-
-               if (card->u.c.tx_bits_per_char != dbits)
-                       ret=1;
-               card->u.c.tx_bits_per_char = dbits;
-
-               if (card->u.c.rx_bits_per_char != dbits)
-                       ret=1;
-               card->u.c.rx_bits_per_char = dbits;
-               
-               if (card->u.c.stop_bits != sbits)
-                       ret=1;
-               card->u.c.stop_bits = sbits;
-
-               if (card->u.c.parity != parity)
-                       ret=1;
-               card->u.c.parity = parity;      
-
-               card->u.c.break_timer = 50;
-               card->u.c.inter_char_timer = 10;
-               card->u.c.rx_complete_length = 100;
-               card->u.c.xon_char = 0xFE;
-       }else{
-               card->u.c.protocol_options = HDLC_STREAMING_MODE;
-       }
-       
-       return ret;
-}
-
-       
-static void wanpipe_tty_set_termios(struct tty_struct *tty, struct termios *old_termios)
-{
-       sdla_t *card;
-       int err=1;
-
-       if (!tty){
-               return;
-       }
-
-       card = (sdla_t *)tty->driver_data;
-                       
-       if (!card)
-               return;
-
-       if (change_speed(card, tty, old_termios) || !card->u.c.comm_enabled){
-               unsigned long smp_flags;
-               
-               if (card->u.c.comm_enabled){
-                       lock_adapter_irq(&card->wandev.lock,&smp_flags);
-                       chdlc_disable_comm_shutdown(card);
-                       unlock_adapter_irq(&card->wandev.lock,&smp_flags);
-               }
-               lock_adapter_irq(&card->wandev.lock,&smp_flags);
-               err = config_tty(card);
-               unlock_adapter_irq(&card->wandev.lock,&smp_flags);
-               if (card->u.c.async_mode){
-                       printk(KERN_INFO "%s: TTY Async Configuration:\n"
-                                "   Baud        =%i\n"
-                                "   Handshaking =%s\n"
-                                "   Tx Dbits    =%i\n"
-                                "   Rx Dbits    =%i\n"
-                                "   Parity      =%s\n"
-                                "   Stop Bits   =%i\n",
-                                card->devname,
-                                card->wandev.bps,
-                                opt_decode[card->u.c.protocol_options],
-                                card->u.c.tx_bits_per_char,
-                                card->u.c.rx_bits_per_char,
-                                p_decode[card->u.c.parity] ,
-                                card->u.c.stop_bits);
-               }else{
-                       printk(KERN_INFO "%s: TTY Sync Configuration:\n"
-                                "   Baud        =%i\n"
-                                "   Protocol    =HDLC_STREAMING\n",
-                                card->devname,card->wandev.bps);
-               }
-               if (!err){
-                       port_set_state(card,WAN_CONNECTED);
-               }else{
-                       port_set_state(card,WAN_DISCONNECTED);
-               }
-       }
-       return;
-}
-
-static void wanpipe_tty_put_char(struct tty_struct *tty, unsigned char ch)
-{
-       sdla_t *card;
-       unsigned long smp_flags=0;
-
-       if (!tty){
-               return;
-       }
-       
-       card = (sdla_t *)tty->driver_data;
-                       
-       if (!card)
-               return;
-
-       if (card->wandev.state != WAN_CONNECTED)
-               return;
-
-       if(card->hw.type != SDLA_S514)
-               s508_lock(card,&smp_flags);
-       
-       if (test_and_set_bit(SEND_CRIT,(void*)&card->wandev.critical)){
-               
-               wanpipe_tty_trigger_tx_irq(card);
-
-               if(card->hw.type != SDLA_S514)
-                       s508_unlock(card,&smp_flags);
-               return;
-       }
-
-       if (chdlc_send(card,(void*)&ch,1)){
-               wanpipe_tty_trigger_tx_irq(card);
-               dbg_printk("%s: Failed to TX char!\n",card->devname);
-       }
-       
-       dbg_printk("%s: Char TX OK\n",card->devname);
-       
-       clear_bit(SEND_CRIT,(void*)&card->wandev.critical);
-       
-       if(card->hw.type != SDLA_S514)
-               s508_unlock(card,&smp_flags);
-       
-       return;
-}
-
-static void wanpipe_tty_flush_chars(struct tty_struct *tty)
-{
-       return;
-}
-
-static void wanpipe_tty_flush_buffer(struct tty_struct *tty)
-{
-       if (!tty)
-               return;
-       
-#if defined(SERIAL_HAVE_POLL_WAIT)
-       wake_up_interruptible(&tty->poll_wait);
-#endif
-       tty_wakeup(tty);
-       return;
-}
-
-/*
- * This function is used to send a high-priority XON/XOFF character to
- * the device
- */
-static void wanpipe_tty_send_xchar(struct tty_struct *tty, char ch)
-{
-       return;
-}
-
-
-static int wanpipe_tty_chars_in_buffer(struct tty_struct *tty)
-{
-       return 0;
-}
-
-
-static int wanpipe_tty_write_room(struct tty_struct *tty)
-{
-       sdla_t *card;
-
-       printk(KERN_INFO "TTY Write Room\n");
-       
-       if (!tty){
-               return 0;
-       }
-
-       card = (sdla_t *)tty->driver_data;
-       if (!card)
-               return 0;
-
-       if (card->wandev.state != WAN_CONNECTED)
-               return 0;
-       
-       return SEC_MAX_NO_DATA_BYTES_IN_FRAME;
-}
-
-
-static int set_modem_status(sdla_t *card, unsigned char data)
-{
-       CHDLC_MAILBOX_STRUCT *mb = card->mbox;
-       int err;
-
-       mb->buffer_length=1;
-       mb->command=SET_MODEM_STATUS;
-       mb->data[0]=data;
-       err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT;
-       if (err != COMMAND_OK) 
-               chdlc_error (card, err, mb);
-       
-       return err;
-}
-
-static void wanpipe_tty_hangup(struct tty_struct *tty)
-{
-       sdla_t *card;
-       unsigned long smp_flags;
-
-       printk(KERN_INFO "TTY Hangup!\n");
-       
-       if (!tty){
-               return;
-       }
-
-       card = (sdla_t *)tty->driver_data;
-       if (!card)
-               return;
-
-       lock_adapter_irq(&card->wandev.lock,&smp_flags);
-       set_modem_status(card,0);
-       unlock_adapter_irq(&card->wandev.lock,&smp_flags);
-       return;
-}
-
-static void wanpipe_tty_break(struct tty_struct *tty, int break_state)
-{
-       return;
-}
-
-static void wanpipe_tty_wait_until_sent(struct tty_struct *tty, int timeout)
-{
-       return;
-}
-
-static void wanpipe_tty_throttle(struct tty_struct * tty)
-{
-       return;
-}
-
-static void wanpipe_tty_unthrottle(struct tty_struct * tty)
-{
-       return;
-}
-
-int wanpipe_tty_read_proc(char *page, char **start, off_t off, int count,
-                int *eof, void *data)
-{
-       return 0;
-}
-
-/*
- * The serial driver boot-time initialization code!
- */
-int wanpipe_tty_init(sdla_t *card)
-{
-       struct serial_state * state;
-       
-       /* Initialize the tty_driver structure */
-
-       if (card->tty_minor < 0 || card->tty_minor > NR_PORTS){
-               printk(KERN_INFO "%s: Illegal Minor TTY number (0-4): %i\n",
-                               card->devname,card->tty_minor);
-               return -EINVAL;
-       }
-
-       if (WAN_CARD(card->tty_minor)){
-               printk(KERN_INFO "%s: TTY Minor %i, already in use\n",
-                               card->devname,card->tty_minor);
-               return -EBUSY;
-       }
-
-       if (tty_init_cnt==0){
-               
-               printk(KERN_INFO "%s: TTY %s Driver Init: Major %i, Minor Range %i-%i\n",
-                               card->devname,
-                               card->u.c.async_mode ? "ASYNC" : "SYNC",
-                               WAN_TTY_MAJOR,MIN_PORT,MAX_PORT);
-               
-               tty_driver_mode = card->u.c.async_mode;
-               
-               memset(&serial_driver, 0, sizeof(struct tty_driver));
-               serial_driver.magic = TTY_DRIVER_MAGIC;
-               serial_driver.owner = THIS_MODULE;
-               serial_driver.driver_name = "wanpipe_tty"; 
-               serial_driver.name = "ttyW";
-               serial_driver.major = WAN_TTY_MAJOR;
-               serial_driver.minor_start = WAN_TTY_MINOR;
-               serial_driver.num = NR_PORTS; 
-               serial_driver.type = TTY_DRIVER_TYPE_SERIAL;
-               serial_driver.subtype = SERIAL_TYPE_NORMAL;
-               
-               serial_driver.init_termios = tty_std_termios;
-               serial_driver.init_termios.c_cflag =
-                       B9600 | CS8 | CREAD | HUPCL | CLOCAL;
-               serial_driver.flags = TTY_DRIVER_REAL_RAW;
-               
-               serial_driver.refcount = 1;     /* !@!@^#^&!! */
-
-               serial_driver.open = wanpipe_tty_open;
-               serial_driver.close = wanpipe_tty_close;
-               serial_driver.write = wanpipe_tty_write;
-               
-               serial_driver.put_char = wanpipe_tty_put_char;
-               serial_driver.flush_chars = wanpipe_tty_flush_chars;
-               serial_driver.write_room = wanpipe_tty_write_room;
-               serial_driver.chars_in_buffer = wanpipe_tty_chars_in_buffer;
-               serial_driver.flush_buffer = wanpipe_tty_flush_buffer;
-               //serial_driver.ioctl = wanpipe_tty_ioctl;
-               serial_driver.throttle = wanpipe_tty_throttle;
-               serial_driver.unthrottle = wanpipe_tty_unthrottle;
-               serial_driver.send_xchar = wanpipe_tty_send_xchar;
-               serial_driver.set_termios = wanpipe_tty_set_termios;
-               serial_driver.stop = wanpipe_tty_stop;
-               serial_driver.start = wanpipe_tty_start;
-               serial_driver.hangup = wanpipe_tty_hangup;
-               serial_driver.break_ctl = wanpipe_tty_break;
-               serial_driver.wait_until_sent = wanpipe_tty_wait_until_sent;
-               serial_driver.read_proc = wanpipe_tty_read_proc;
-               
-               if (tty_register_driver(&serial_driver)){
-                       printk(KERN_INFO "%s: Failed to register serial driver!\n",
-                                       card->devname);
-               }
-       }
-
-
-       /* The subsequent ports must comply to the initial configuration */
-       if (tty_driver_mode != card->u.c.async_mode){
-               printk(KERN_INFO "%s: Error: TTY Driver operation mode mismatch!\n",
-                               card->devname);
-               printk(KERN_INFO "%s: The TTY driver is configured for %s!\n",
-                               card->devname, tty_driver_mode ? "ASYNC" : "SYNC");
-               return -EINVAL;
-       }
-       
-       tty_init_cnt++;
-       
-       printk(KERN_INFO "%s: Initializing TTY %s Driver Minor %i\n",
-                       card->devname,
-                       tty_driver_mode ? "ASYNC" : "SYNC",
-                       card->tty_minor);
-       
-       tty_card_map[card->tty_minor] = card;
-       state = &rs_table[card->tty_minor];
-       
-       state->magic = SSTATE_MAGIC;
-       state->line = 0;
-       state->type = PORT_UNKNOWN;
-       state->custom_divisor = 0;
-       state->close_delay = 5*HZ/10;
-       state->closing_wait = 30*HZ;
-       state->icount.cts = state->icount.dsr = 
-               state->icount.rng = state->icount.dcd = 0;
-       state->icount.rx = state->icount.tx = 0;
-       state->icount.frame = state->icount.parity = 0;
-       state->icount.overrun = state->icount.brk = 0;
-       state->irq = card->wandev.irq; 
-
-       INIT_WORK(&card->tty_work, tty_poll_work, (void*)card);
-       return 0;
-}
-
-
-MODULE_LICENSE("GPL");
-
-/****** End ****************************************************************/
diff --git a/drivers/net/wan/sdla_fr.c b/drivers/net/wan/sdla_fr.c
deleted file mode 100644 (file)
index 7f1ce9d..0000000
+++ /dev/null
@@ -1,5061 +0,0 @@
-/*****************************************************************************
-* sdla_fr.c    WANPIPE(tm) Multiprotocol WAN Link Driver. Frame relay module.
-*
-* Author(s):   Nenad Corbic  <ncorbic@sangoma.com>
-*              Gideon Hack
-*
-* Copyright:   (c) 1995-2001 Sangoma Technologies Inc.
-*
-*              This program is free software; you can redistribute it and/or
-*              modify it under the terms of the GNU General Public License
-*              as published by the Free Software Foundation; either version
-*              2 of the License, or (at your option) any later version.
-* ============================================================================
-* Nov 23, 2000  Nenad Corbic    o Added support for 2.4.X kernels
-* Nov 15, 2000  David Rokavarg  
-*               Nenad Corbic   o Added frame relay bridging support.
-*                                Original code from Mark Wells and Kristian Hoffmann has
-*                                been integrated into the frame relay driver.
-* Nov 13, 2000  Nenad Corbic    o Added true interface type encoding option.
-*                                Tcpdump doesn't support Frame Relay inteface
-*                                types, to fix this true type option will set
-*                                the interface type to RAW IP mode.
-* Nov 07, 2000  Nenad Corbic   o Added security features for UDP debugging:
-*                                 Deny all and specify allowed requests.
-* Nov 06, 2000  Nenad Corbic   o Wanpipe interfaces conform to raw packet interfaces.  
-*                                 Moved the if_header into the if_send() routine.
-*                                 The if_header() was breaking the libpcap 
-*                                 support. i.e. support for tcpdump, ethereal ...
-* Oct 12. 2000  Nenad Corbic    o Added error message in fr_configure
-* Jul 31, 2000  Nenad Corbic   o Fixed the Router UP Time.
-* Apr 28, 2000  Nenad Corbic   o Added the option to shutdown an interface
-*                                 when the channel gets disconnected.
-* Apr 28, 2000  Nenad Corbic   o Added M.Grants patch: disallow duplicate
-*                                 interface setups. 
-* Apr 25, 2000  Nenad Corbic   o Added M.Grants patch: dynamically add/remove 
-*                                 new dlcis/interfaces.
-* Mar 23, 2000  Nenad Corbic   o Improved task queue, bh handling.
-* Mar 16, 2000 Nenad Corbic    o Added Inverse ARP support
-* Mar 13, 2000  Nenad Corbic   o Added new socket API support.
-* Mar 06, 2000  Nenad Corbic   o Bug Fix: corrupted mbox recovery.
-* Feb 24, 2000  Nenad Corbic    o Fixed up FT1 UDP debugging problem.
-* Dev 15, 1999  Nenad Corbic    o Fixed up header files for 2.0.X kernels
-*
-* Nov 08, 1999  Nenad Corbic    o Combined all debug UDP calls into one function
-*                               o Removed the ARP support. This has to be done
-*                                 in the next version.
-*                               o Only a Node can implement NO signalling.
-*                                 Initialize DLCI during if_open() if NO 
-*                                signalling.
-*                              o Took out IPX support, implement in next
-*                                 version
-* Sep 29, 1999  Nenad Corbic   o Added SMP support and changed the update
-*                                 function to use timer interrupt.
-*                              o Fixed the CIR bug:  Set the value of BC
-*                                 to CIR when the CIR is enabled.
-*                              o Updated comments, statistics and tracing.
-* Jun 02, 1999 Gideon Hack     o Updated for S514 support.
-* Sep 18, 1998 Jaspreet Singh  o Updated for 2.2.X kernels.
-* Jul 31, 1998 Jaspreet Singh  o Removed wpf_poll routine.  The channel/DLCI 
-*                                status is received through an event interrupt.
-* Jul 08, 1998 David Fong      o Added inverse ARP support.
-* Mar 26, 1997 Jaspreet Singh  o Returning return codes for failed UDP cmds.
-* Jan 28, 1997 Jaspreet Singh  o Improved handling of inactive DLCIs.
-* Dec 30, 1997 Jaspreet Singh  o Replaced dev_tint() with mark_bh(NET_BH)
-* Dec 16, 1997 Jaspreet Singh  o Implemented Multiple IPX support.
-* Nov 26, 1997 Jaspreet Singh  o Improved load sharing with multiple boards
-*                              o Added Cli() to protect enabling of interrupts
-*                                while polling is called.
-* Nov 24, 1997 Jaspreet Singh  o Added counters to avoid enabling of interrupts
-*                                when they have been disabled by another
-*                                interface or routine (eg. wpf_poll).
-* Nov 06, 1997 Jaspreet Singh  o Added INTR_TEST_MODE to avoid polling 
-*                                routine disable interrupts during interrupt
-*                                testing.
-* Oct 20, 1997  Jaspreet Singh  o Added hooks in for Router UP time.
-* Oct 16, 1997  Jaspreet Singh  o The critical flag is used to maintain flow
-*                                 control by avoiding RACE conditions.  The
-*                                 cli() and restore_flags() are taken out.
-*                                 The fr_channel structure is appended for 
-*                                 Driver Statistics.
-* Oct 15, 1997  Farhan Thawar    o updated if_send() and receive for IPX
-* Aug 29, 1997  Farhan Thawar    o Removed most of the cli() and sti()
-*                                o Abstracted the UDP management stuff
-*                                o Now use tbusy and critical more intelligently
-* Jul 21, 1997  Jaspreet Singh  o Can configure T391, T392, N391, N392 & N393
-*                                 through router.conf.
-*                               o Protected calls to sdla_peek() by adDing 
-*                                 save_flags(), cli() and restore_flags().
-*                               o Added error message for Inactive DLCIs in
-*                                 fr_event() and update_chan_state().
-*                               o Fixed freeing up of buffers using kfree() 
-*                                 when packets are received.
-* Jul 07, 1997 Jaspreet Singh   o Added configurable TTL for UDP packets 
-*                               o Added ability to discard multicast and 
-*                                 broadcast source addressed packets
-* Jun 27, 1997 Jaspreet Singh   o Added FT1 monitor capabilities 
-*                                 New case (0x44) statement in if_send routine 
-*                                 Added a global variable rCount to keep track
-*                                 of FT1 status enabled on the board.
-* May 29, 1997 Jaspreet Singh   o Fixed major Flow Control Problem
-*                                 With multiple boards a problem was seen where
-*                                 the second board always stopped transmitting
-*                                 packet after running for a while. The code
-*                                 got into a stage where the interrupts were
-*                                 disabled and dev->tbusy was set to 1.
-*                                 This caused the If_send() routine to get into
-*                                  the if clause for it(0,dev->tbusy) 
-*                                 forever.
-*                                 The code got into this stage due to an 
-*                                 interrupt occurring within the if clause for 
-*                                 set_bit(0,dev->tbusy).  Since an interrupt 
-*                                 disables furhter transmit interrupt and 
-*                                 makes dev->tbusy = 0, this effect was undone 
-*                                  by making dev->tbusy = 1 in the if clause.
-*                                 The Fix checks to see if Transmit interrupts
-*                                 are disabled then do not make dev->tbusy = 1
-*                                 Introduced a global variable: int_occur and
-*                                 added tx_int_enabled in the wan_device 
-*                                 structure.   
-* May 21, 1997  Jaspreet Singh   o Fixed UDP Management for multiple
-*                                  boards.
-*
-* Apr 25, 1997  Farhan Thawar    o added UDP Management stuff
-*                                o fixed bug in if_send() and tx_intr() to
-*                                  sleep and wakeup all devices
-* Mar 11, 1997  Farhan Thawar   Version 3.1.1
-*                                o fixed (+1) bug in fr508_rx_intr()
-*                                o changed if_send() to return 0 if
-*                                  wandev.critical() is true
-*                                o free socket buffer in if_send() if
-*                                  returning 0 
-*                                o added tx_intr() routine
-* Jan 30, 1997 Gene Kozin      Version 3.1.0
-*                               o implemented exec() entry point
-*                               o fixed a bug causing driver configured as
-*                                 a FR switch to be stuck in WAN_
-*                                 mode
-* Jan 02, 1997 Gene Kozin      Initial version.
-*****************************************************************************/
-
-#include <linux/module.h>
-#include <linux/kernel.h>      /* printk(), and other useful stuff */
-#include <linux/stddef.h>      /* offsetof(), etc. */
-#include <linux/errno.h>       /* return codes */
-#include <linux/string.h>      /* inline memset(), etc. */
-#include <linux/slab.h>        /* kmalloc(), kfree() */
-#include <linux/wanrouter.h>   /* WAN router definitions */
-#include <linux/wanpipe.h>     /* WANPIPE common user API definitions */
-#include <linux/workqueue.h>
-#include <linux/if_arp.h>      /* ARPHRD_* defines */
-#include <asm/byteorder.h>     /* htons(), etc. */
-#include <asm/io.h>            /* for inb(), outb(), etc. */
-#include <linux/time.h>                /* for do_gettimeofday */       
-#include <linux/in.h>          /* sockaddr_in */
-#include <linux/jiffies.h>     /* time_after() macro */
-#include <asm/errno.h>
-
-#include <linux/ip.h>
-#include <linux/if.h>
-
-#include <linux/if_wanpipe_common.h>   /* Wanpipe Socket */
-#include <linux/if_wanpipe.h>  
-
-#include <linux/sdla_fr.h>             /* frame relay firmware API definitions */
-
-#include <asm/uaccess.h>
-#include <linux/inetdevice.h>
-#include <linux/netdevice.h>
-
-#include <net/route.h>                 /* Dynamic Route Creation */
-#include <linux/etherdevice.h>         /* eth_type_trans() used for bridging */
-#include <linux/random.h>
-
-/****** Defines & Macros ****************************************************/
-
-#define        MAX_CMD_RETRY   10              /* max number of firmware retries */
-
-#define        FR_HEADER_LEN   8               /* max encapsulation header size */
-#define        FR_CHANNEL_MTU  1500            /* unfragmented logical channel MTU */
-
-/* Q.922 frame types */
-#define        Q922_UI         0x03            /* Unnumbered Info frame */
-#define        Q922_XID        0xAF            
-
-/* DLCI configured or not */
-#define DLCI_NOT_CONFIGURED    0x00
-#define DLCI_CONFIG_PENDING    0x01
-#define DLCI_CONFIGURED                0x02
-
-/* CIR enabled or not */
-#define CIR_ENABLED    0x00
-#define CIR_DISABLED   0x01
-
-#define FRAME_RELAY_API 1
-#define MAX_BH_BUFF    10
-
-/* For handle_IPXWAN() */
-#define CVHexToAscii(b) (((unsigned char)(b) > (unsigned char)9) ? ((unsigned char)'A' + ((unsigned char)(b) - (unsigned char)10)) : ((unsigned char)'0' + (unsigned char)(b)))
-/****** Data Structures *****************************************************/
-
-/* This is an extention of the 'struct device' we create for each network
- * interface to keep the rest of channel-specific data.
- */
-typedef struct fr_channel
-{
-       wanpipe_common_t common;
-       char name[WAN_IFNAME_SZ+1];     /* interface name, ASCIIZ */
-       unsigned dlci_configured  ;     /* check whether configured or not */
-       unsigned cir_status;            /* check whether CIR enabled or not */
-       unsigned dlci;                  /* logical channel number */
-       unsigned cir;                   /* committed information rate */
-       unsigned bc;                    /* committed burst size */
-       unsigned be;                    /* excess burst size */
-       unsigned mc;                    /* multicast support on or off */
-       unsigned tx_int_status;         /* Transmit Interrupt Status */ 
-       unsigned short pkt_length;      /* Packet Length */
-       unsigned long router_start_time;/* Router start time in seconds */
-       unsigned long tick_counter;     /* counter for transmit time out */
-       char dev_pending_devtint;       /* interface pending dev_tint() */
-       void *dlci_int_interface;       /* pointer to the DLCI Interface */ 
-       unsigned long IB_addr;          /* physical address of Interface Byte */
-       unsigned long state_tick;       /* time of the last state change */
-       unsigned char enable_IPX;       /* Enable/Disable the use of IPX */
-       unsigned long network_number;   /* Internal Network Number for IPX*/
-       sdla_t *card;                   /* -> owner */
-       unsigned route_flag;            /* Add/Rem dest addr in route tables */
-       unsigned inarp;                 /* Inverse Arp Request status */ 
-       long inarp_ready;               /* Ready to send requests */
-       int inarp_interval;             /* Time between InArp Requests */
-       unsigned long inarp_tick;       /* InArp jiffies tick counter */
-       long interface_down;            /* Bring interface down on disconnect */
-       struct net_device_stats ifstats;        /* interface statistics */
-       if_send_stat_t drvstats_if_send;
-        rx_intr_stat_t drvstats_rx_intr;
-        pipe_mgmt_stat_t drvstats_gen;
-       unsigned long router_up_time;
-
-       unsigned short transmit_length;
-       struct sk_buff *delay_skb;
-
-       bh_data_t *bh_head;               /* Circular buffer for chdlc_bh */
-       unsigned long  tq_working;
-       volatile int  bh_write;
-       volatile int  bh_read;
-       atomic_t  bh_buff_used;
-
-       /* Polling task queue. Each interface
-         * has its own task queue, which is used
-         * to defer events from the interrupt */
-       struct work_struct fr_poll_work;
-       struct timer_list fr_arp_timer;
-
-       u32 ip_local;
-       u32 ip_remote;
-       long config_dlci;
-       long unconfig_dlci;
-
-       /* Whether this interface should be setup as a gateway.
-        * Used by dynamic route setup code */
-       u8  gateway;
-
-       /* True interface type */
-       u8 true_if_encoding;
-       u8 fr_header[FR_HEADER_LEN];
-       char fr_header_len;
-
-} fr_channel_t;
-
-/* Route Flag options */
-#define NO_ROUTE       0x00
-#define ADD_ROUTE      0x01
-#define ROUTE_ADDED    0x02
-#define REMOVE_ROUTE   0x03
-#define ARP_REQ                0x04
-
-/* inarp options */
-#define INARP_NONE             0x00
-#define INARP_REQUEST          0x01
-#define INARP_CONFIGURED       0x02
-
-/* reasons for enabling the timer interrupt on the adapter */
-#define TMR_INT_ENABLED_UDP    0x01
-#define TMR_INT_ENABLED_UPDATE         0x02
-#define TMR_INT_ENABLED_ARP    0x04
-#define TMR_INT_ENABLED_UPDATE_STATE   0x08
-#define TMR_INT_ENABLED_CONFIG 0x10
-#define TMR_INT_ENABLED_UNCONFIG       0x20
-
-
-typedef struct dlci_status
-{
-       unsigned short dlci     PACKED;
-       unsigned char state     PACKED;
-} dlci_status_t;
-
-typedef struct dlci_IB_mapping
-{
-       unsigned short dlci             PACKED;
-       unsigned long  addr_value       PACKED;
-} dlci_IB_mapping_t;
-
-/* This structure is used for DLCI list Tx interrupt mode.  It is used to
-   enable interrupt bit and set the packet length for transmission
- */
-typedef struct fr_dlci_interface 
-{
-       unsigned char gen_interrupt     PACKED;
-       unsigned short packet_length    PACKED;
-       unsigned char reserved          PACKED;
-} fr_dlci_interface_t; 
-
-/* variable for keeping track of enabling/disabling FT1 monitor status */
-static int rCount = 0;
-
-extern void disable_irq(unsigned int);
-extern void enable_irq(unsigned int);
-
-/* variable for keeping track of number of interrupts generated during 
- * interrupt test routine 
- */
-static int Intr_test_counter;
-
-/****** Function Prototypes *************************************************/
-
-/* WAN link driver entry points. These are called by the WAN router module. */
-static int update(struct wan_device *wandev);
-static int new_if(struct wan_device *wandev, struct net_device *dev,
-                 wanif_conf_t *conf);
-static int del_if(struct wan_device *wandev, struct net_device *dev);
-static void disable_comm (sdla_t *card);
-
-/* WANPIPE-specific entry points */
-static int wpf_exec(struct sdla *card, void *u_cmd, void *u_data);
-
-/* Network device interface */
-static int if_init(struct net_device *dev);
-static int if_open(struct net_device *dev);
-static int if_close(struct net_device *dev);
-
-static void if_tx_timeout(struct net_device *dev);
-
-static int if_rebuild_hdr (struct sk_buff *skb);
-
-static int if_send(struct sk_buff *skb, struct net_device *dev);
-static int chk_bcast_mcast_addr(sdla_t *card, struct net_device* dev,
-                                struct sk_buff *skb);
-static struct net_device_stats *if_stats(struct net_device *dev);
-
-/* Interrupt handlers */
-static void fr_isr(sdla_t *card);
-static void rx_intr(sdla_t *card);
-static void tx_intr(sdla_t *card);
-static void timer_intr(sdla_t *card);
-static void spur_intr(sdla_t *card);
-
-/* Frame relay firmware interface functions */
-static int fr_read_version(sdla_t *card, char *str);
-static int fr_configure(sdla_t *card, fr_conf_t *conf);
-static int fr_dlci_configure(sdla_t *card, fr_dlc_conf_t *conf, unsigned dlci);
-static int fr_init_dlci (sdla_t *card, fr_channel_t *chan);
-static int fr_set_intr_mode (sdla_t *card, unsigned mode, unsigned mtu, unsigned short timeout);
-static int fr_comm_enable(sdla_t *card);
-static void fr_comm_disable(sdla_t *card);
-static int fr_get_err_stats(sdla_t *card);
-static int fr_get_stats(sdla_t *card);
-static int fr_add_dlci(sdla_t *card, int dlci);
-static int fr_activate_dlci(sdla_t *card, int dlci);
-static int fr_delete_dlci (sdla_t* card, int dlci);
-static int fr_issue_isf(sdla_t *card, int isf);
-static int fr_send(sdla_t *card, int dlci, unsigned char attr, int len,
-       void *buf);
-static int fr_send_data_header(sdla_t *card, int dlci, unsigned char attr, int len,
-       void *buf,unsigned char hdr_len);
-static unsigned int fr_send_hdr(sdla_t *card, int dlci, unsigned int offset);
-
-static int check_dlci_config (sdla_t *card, fr_channel_t *chan);
-static void initialize_rx_tx_buffers (sdla_t *card);
-
-
-/* Firmware asynchronous event handlers */
-static int fr_event(sdla_t *card, int event, fr_mbox_t *mbox);
-static int fr_modem_failure(sdla_t *card, fr_mbox_t *mbox);
-static int fr_dlci_change(sdla_t *card, fr_mbox_t *mbox);
-
-/* Miscellaneous functions */
-static int update_chan_state(struct net_device *dev);
-static void set_chan_state(struct net_device *dev, int state);
-static struct net_device *find_channel(sdla_t *card, unsigned dlci);
-static int is_tx_ready(sdla_t *card, fr_channel_t *chan);
-static unsigned int dec_to_uint(unsigned char *str, int len);
-static int reply_udp( unsigned char *data, unsigned int mbox_len );
-
-static int intr_test( sdla_t* card );
-static void init_chan_statistics( fr_channel_t* chan );
-static void init_global_statistics( sdla_t* card );
-static void read_DLCI_IB_mapping( sdla_t* card, fr_channel_t* chan );
-static int setup_for_delayed_transmit(struct net_device* dev,
-                                     struct sk_buff *skb);
-
-struct net_device *move_dev_to_next(sdla_t *card, struct net_device *dev);
-static int check_tx_status(sdla_t *card, struct net_device *dev);
-
-/* Frame Relay Socket API */
-static void trigger_fr_bh (fr_channel_t *);
-static void fr_bh(struct net_device *dev);
-static int fr_bh_cleanup(struct net_device *dev);
-static int bh_enqueue(struct net_device *dev, struct sk_buff *skb);
-
-static void trigger_fr_poll(struct net_device *dev);
-static void fr_poll(struct net_device *dev);
-//static void add_gateway(struct net_device *dev);
-
-static void trigger_unconfig_fr(struct net_device *dev);
-static void unconfig_fr (sdla_t *);
-
-static void trigger_config_fr (sdla_t *);
-static void config_fr (sdla_t *);
-
-
-/* Inverse ARP and Dynamic routing functions */
-int process_ARP(arphdr_1490_t *ArpPacket, sdla_t *card, struct net_device *dev);
-int is_arp(void *buf);
-int send_inarp_request(sdla_t *card, struct net_device *dev);
-
-static void trigger_fr_arp(struct net_device *dev);
-static void fr_arp (unsigned long data);
-
-
-/* Udp management functions */
-static int process_udp_mgmt_pkt(sdla_t *card);
-static int udp_pkt_type( struct sk_buff *skb, sdla_t *card );
-static int store_udp_mgmt_pkt(int udp_type, char udp_pkt_src, sdla_t* card,
-                                struct sk_buff *skb, int dlci);
-
-/* IPX functions */
-static void switch_net_numbers(unsigned char *sendpacket,
-       unsigned long network_number, unsigned char incoming);
-
-static int handle_IPXWAN(unsigned char *sendpacket, char *devname,
-       unsigned char enable_IPX, unsigned long network_number);
-
-/* Lock Functions: SMP supported */
-void   s508_s514_unlock(sdla_t *card, unsigned long *smp_flags);
-void   s508_s514_lock(sdla_t *card, unsigned long *smp_flags);
-
-unsigned short calc_checksum (char *, int);
-static int setup_fr_header(struct sk_buff *skb,
-                          struct net_device* dev, char op_mode);
-
-
-/****** Public Functions ****************************************************/
-
-/*============================================================================
- * Frame relay protocol initialization routine.
- *
- * This routine is called by the main WANPIPE module during setup.  At this
- * point adapter is completely initialized and firmware is running.
- *  o read firmware version (to make sure it's alive)
- *  o configure adapter
- *  o initialize protocol-specific fields of the adapter data space.
- *
- * Return:     0       o.k.
- *             < 0     failure.
- */
-int wpf_init(sdla_t *card, wandev_conf_t *conf)
-{
-
-       int err;
-       fr508_flags_t* flags;
-
-       union
-       {
-               char str[80];
-               fr_conf_t cfg;
-       } u;
-
-       fr_buf_info_t* buf_info;
-       int i;
-
-
-       printk(KERN_INFO "\n");
-
-       /* Verify configuration ID */
-       if (conf->config_id != WANCONFIG_FR) {
-               
-               printk(KERN_INFO "%s: invalid configuration ID %u!\n",
-                       card->devname, conf->config_id);
-               return -EINVAL;
-       
-       }
-
-       /* Initialize protocol-specific fields of adapter data space */
-       switch (card->hw.fwid) {
-       
-               case SFID_FR508:
-                       card->mbox  = (void*)(card->hw.dpmbase + 
-                                       FR508_MBOX_OFFS);
-                       card->flags = (void*)(card->hw.dpmbase + 
-                                       FR508_FLAG_OFFS);
-                       if(card->hw.type == SDLA_S514) {
-                               card->mbox += FR_MB_VECTOR;
-                                card->flags += FR_MB_VECTOR;
-                       }
-                        card->isr = &fr_isr;
-                       break;
-
-               default:
-                       return -EINVAL;
-       }
-
-       flags = card->flags;
-
-       /* Read firmware version.  Note that when adapter initializes, it
-        * clears the mailbox, so it may appear that the first command was
-        * executed successfully when in fact it was merely erased. To work
-        * around this, we execute the first command twice.
-        */
-
-       if (fr_read_version(card, NULL) || fr_read_version(card, u.str))
-               return -EIO;
-
-       printk(KERN_INFO "%s: running frame relay firmware v%s\n",
-               card->devname, u.str);
-
-       /* Adjust configuration */
-       conf->mtu += FR_HEADER_LEN;
-       conf->mtu = (conf->mtu >= MIN_LGTH_FR_DATA_CFG) ?
-                       min_t(unsigned int, conf->mtu, FR_MAX_NO_DATA_BYTES_IN_FRAME) :
-                        FR_CHANNEL_MTU + FR_HEADER_LEN;
-     
-       conf->bps = min_t(unsigned int, conf->bps, 2048000);
-
-       /* Initialze the configuration structure sent to the board to zero */
-       memset(&u.cfg, 0, sizeof(u.cfg));
-
-       memset(card->u.f.dlci_to_dev_map, 0, sizeof(card->u.f.dlci_to_dev_map));
-       
-       /* Configure adapter firmware */
-
-       u.cfg.mtu       = conf->mtu;
-       u.cfg.kbps      = conf->bps / 1000;
-
-       u.cfg.cir_fwd = u.cfg.cir_bwd = 16;
-        u.cfg.bc_fwd  = u.cfg.bc_bwd = 16;
-       
-       u.cfg.options   = 0x0000;
-       printk(KERN_INFO "%s: Global CIR enabled by Default\n", card->devname);
-       
-       switch (conf->u.fr.signalling) {
-
-               case WANOPT_FR_ANSI:
-                       u.cfg.options = 0x0000; 
-                       break;          
-       
-               case WANOPT_FR_Q933:    
-                       u.cfg.options |= 0x0200; 
-                       break;
-       
-               case WANOPT_FR_LMI:     
-                       u.cfg.options |= 0x0400; 
-                       break;
-
-               case WANOPT_NO:
-                       u.cfg.options |= 0x0800; 
-                       break;
-               default:
-                       printk(KERN_INFO "%s: Illegal Signalling option\n",
-                                       card->wandev.name);
-                       return -EINVAL;
-       }
-
-
-       card->wandev.signalling = conf->u.fr.signalling;
-
-       if (conf->station == WANOPT_CPE) {
-
-
-               if (conf->u.fr.signalling == WANOPT_NO){
-                       printk(KERN_INFO 
-                               "%s: ERROR - For NO signalling, station must be set to Node!",
-                                        card->devname);
-                       return -EINVAL;
-               }
-
-               u.cfg.station = 0;
-               u.cfg.options |= 0x8000;        /* auto config DLCI */
-               card->u.f.dlci_num  = 0;
-       
-       } else {
-
-               u.cfg.station = 1;      /* switch emulation mode */
-
-               /* For switch emulation we have to create a list of dlci(s)
-                * that will be sent to be global SET_DLCI_CONFIGURATION 
-                * command in fr_configure() routine. 
-                */
-
-               card->u.f.dlci_num  = min_t(unsigned int, max_t(unsigned int, conf->u.fr.dlci_num, 1), 100);
-       
-               for ( i = 0; i < card->u.f.dlci_num; i++) {
-
-                       card->u.f.node_dlci[i] = (unsigned short) 
-                               conf->u.fr.dlci[i] ? conf->u.fr.dlci[i] : 16;
-       
-               }
-       }
-
-       if (conf->clocking == WANOPT_INTERNAL)
-               u.cfg.port |= 0x0001;
-
-       if (conf->interface == WANOPT_RS232)
-               u.cfg.port |= 0x0002;
-
-       if (conf->u.fr.t391)
-               u.cfg.t391 = min_t(unsigned int, conf->u.fr.t391, 30);
-       else
-               u.cfg.t391 = 5;
-
-       if (conf->u.fr.t392)
-               u.cfg.t392 = min_t(unsigned int, conf->u.fr.t392, 30);
-       else
-               u.cfg.t392 = 15;
-
-       if (conf->u.fr.n391)
-               u.cfg.n391 = min_t(unsigned int, conf->u.fr.n391, 255);
-       else
-               u.cfg.n391 = 2;
-
-       if (conf->u.fr.n392)
-               u.cfg.n392 = min_t(unsigned int, conf->u.fr.n392, 10);
-       else
-               u.cfg.n392 = 3; 
-
-       if (conf->u.fr.n393)
-               u.cfg.n393 = min_t(unsigned int, conf->u.fr.n393, 10);
-       else
-               u.cfg.n393 = 4;
-
-       if (fr_configure(card, &u.cfg))
-               return -EIO;
-
-       if (card->hw.type == SDLA_S514) {
-       
-                buf_info = (void*)(card->hw.dpmbase + FR_MB_VECTOR +
-                       FR508_RXBC_OFFS);
-
-                card->rxmb = (void*)(buf_info->rse_next + card->hw.dpmbase);
-
-                card->u.f.rxmb_base =
-                        (void*)(buf_info->rse_base + card->hw.dpmbase); 
-
-                card->u.f.rxmb_last =
-                        (void*)(buf_info->rse_base +
-                        (buf_info->rse_num - 1) * sizeof(fr_rx_buf_ctl_t) +
-                        card->hw.dpmbase);
-       }else{  
-               buf_info = (void*)(card->hw.dpmbase + FR508_RXBC_OFFS);
-
-               card->rxmb = (void*)(buf_info->rse_next -
-                       FR_MB_VECTOR + card->hw.dpmbase);
-               
-               card->u.f.rxmb_base =
-                       (void*)(buf_info->rse_base -
-                       FR_MB_VECTOR + card->hw.dpmbase);
-               
-               card->u.f.rxmb_last =
-                       (void*)(buf_info->rse_base +
-                       (buf_info->rse_num - 1) * sizeof(fr_rx_buf_ctl_t) -
-                       FR_MB_VECTOR + card->hw.dpmbase);
-       }
-
-       card->u.f.rx_base = buf_info->buf_base;
-       card->u.f.rx_top  = buf_info->buf_top;
-
-       card->u.f.tx_interrupts_pending = 0;
-
-       card->wandev.mtu        = conf->mtu;
-       card->wandev.bps        = conf->bps;
-       card->wandev.interface  = conf->interface;
-       card->wandev.clocking   = conf->clocking;
-       card->wandev.station    = conf->station;
-       card->poll              = NULL; 
-       card->exec              = &wpf_exec;
-       card->wandev.update     = &update;
-       card->wandev.new_if     = &new_if;
-       card->wandev.del_if     = &del_if;
-       card->wandev.state      = WAN_DISCONNECTED;
-       card->wandev.ttl        = conf->ttl;
-        card->wandev.udp_port  = conf->udp_port;       
-       card->disable_comm      = &disable_comm;        
-       card->u.f.arp_dev       = NULL;
-
-       /* Intialize global statistics for a card */
-       init_global_statistics( card );
-
-        card->TracingEnabled          = 0;
-
-       /* Interrupt Test */
-       Intr_test_counter = 0;
-       card->intr_mode = INTR_TEST_MODE;
-       err = intr_test( card );
-
-       printk(KERN_INFO "%s: End of Interrupt Test rc=0x%x  count=%i\n",
-                       card->devname,err,Intr_test_counter); 
-       
-       if (err || (Intr_test_counter < MAX_INTR_TEST_COUNTER)) {
-               printk(KERN_ERR "%s: Interrupt Test Failed, Counter: %i\n", 
-                       card->devname, Intr_test_counter);
-               printk(KERN_ERR "Please choose another interrupt\n");
-               err = -EIO;
-               return err;
-       }
-
-       printk(KERN_INFO "%s: Interrupt Test Passed, Counter: %i\n",
-                       card->devname, Intr_test_counter);
-
-
-       /* Apr 28 2000. Nenad Corbic
-        * Enable commnunications here, not in if_open or new_if, since
-         * interfaces come down when the link is disconnected. 
-         */
-        
-       /* If you enable comms and then set ints, you get a Tx int as you
-        * perform the SET_INT_TRIGGERS command. So, we only set int
-        * triggers and then adjust the interrupt mask (to disable Tx ints)
-        * before enabling comms. 
-        */     
-        if (fr_set_intr_mode(card, (FR_INTR_RXRDY | FR_INTR_TXRDY |
-               FR_INTR_DLC | FR_INTR_TIMER | FR_INTR_TX_MULT_DLCIs) ,
-               card->wandev.mtu, 0)) {
-               return -EIO;
-       }
-
-       flags->imask &= ~(FR_INTR_TXRDY | FR_INTR_TIMER);
-       if (fr_comm_enable(card)) {
-               return -EIO;
-       }       
-       wanpipe_set_state(card, WAN_CONNECTED);
-       spin_lock_init(&card->u.f.if_send_lock);
-       
-       printk(KERN_INFO "\n");
-
-        return 0;
-}
-
-/******* WAN Device Driver Entry Points *************************************/
-
-/*============================================================================
- * Update device status & statistics.
- */
-static int update(struct wan_device* wandev)
-{
-       volatile sdla_t* card;
-       unsigned long timeout;
-       fr508_flags_t* flags;
-
-       /* sanity checks */
-       if ((wandev == NULL) || (wandev->private == NULL))
-               return -EFAULT;
-
-       if (wandev->state == WAN_UNCONFIGURED)
-               return -ENODEV;
-
-       card = wandev->private;
-       flags = card->flags;
-
-
-       card->u.f.update_comms_stats = 1;
-       card->u.f.timer_int_enabled |= TMR_INT_ENABLED_UPDATE;
-       flags->imask |= FR_INTR_TIMER;
-               timeout = jiffies;
-               for(;;) {
-               if(card->u.f.update_comms_stats == 0)
-                       break;
-                if (time_after(jiffies, timeout + 1 * HZ)){
-                       card->u.f.update_comms_stats = 0;
-                       return -EAGAIN;
-               }
-        }
-
-       return 0;
-}
-
-/*============================================================================
- * Create new logical channel.
- * This routine is called by the router when ROUTER_IFNEW IOCTL is being
- * handled.
- * o parse media- and hardware-specific configuration
- * o make sure that a new channel can be created
- * o allocate resources, if necessary
- * o prepare network device structure for registaration.
- *
- * Return:     0       o.k.
- *             < 0     failure (channel will not be created)
- */
-static int new_if(struct wan_device* wandev, struct net_device* dev,
-                 wanif_conf_t* conf)
-{
-       sdla_t* card = wandev->private;
-       fr_channel_t* chan;
-       int dlci = 0;
-       int err = 0;
-
-       
-       if ((conf->name[0] == '\0') || (strlen(conf->name) > WAN_IFNAME_SZ)) {
-               
-               printk(KERN_INFO "%s: Invalid interface name!\n",
-                       card->devname);
-               return -EINVAL;
-       }
-
-       /* allocate and initialize private data */
-       chan = kmalloc(sizeof(fr_channel_t), GFP_KERNEL);
-
-       if (chan == NULL)
-               return -ENOMEM;
-
-       memset(chan, 0, sizeof(fr_channel_t));
-       strcpy(chan->name, conf->name);
-       chan->card = card;
-
-       /* verify media address */
-       if (isdigit(conf->addr[0])) {
-
-               dlci = dec_to_uint(conf->addr, 0);
-
-               if (dlci && (dlci <= HIGHEST_VALID_DLCI)) {
-               
-                       chan->dlci = dlci;
-               
-               } else {
-               
-                       printk(KERN_ERR
-                               "%s: Invalid DLCI %u on interface %s!\n",
-                               wandev->name, dlci, chan->name);
-                       err = -EINVAL;
-               }
-
-       } else {
-               printk(KERN_ERR
-                       "%s: Invalid media address on interface %s!\n",
-                       wandev->name, chan->name);
-               err = -EINVAL;
-       }
-
-       if ((chan->true_if_encoding = conf->true_if_encoding) == WANOPT_YES){
-               printk(KERN_INFO 
-                       "%s: Enabling, true interface type encoding.\n",
-                       card->devname);
-       }
-       
-
-
-    /* Setup wanpipe as a router (WANPIPE) even if it is
-        * a bridged DLCI, or as an API 
-        */
-        if (strcmp(conf->usedby, "WANPIPE")  == 0  || 
-           strcmp(conf->usedby, "BRIDGE")   == 0  ||
-           strcmp(conf->usedby, "BRIDGE_N") == 0){
-               
-               if(strcmp(conf->usedby, "WANPIPE") == 0){
-                       chan->common.usedby = WANPIPE;
-                       
-                       printk(KERN_INFO "%s: Running in WANPIPE mode.\n", 
-                                       card->devname);
-                       
-               }else if(strcmp(conf->usedby, "BRIDGE") == 0){
-                       
-                       chan->common.usedby = BRIDGE;
-                       
-                       printk(KERN_INFO "%s: Running in WANPIPE (BRIDGE) mode.\n", 
-                                       card->devname);
-               }else if( strcmp(conf->usedby, "BRIDGE_N") == 0 ){
-                       
-                       chan->common.usedby = BRIDGE_NODE;
-               
-                       printk(KERN_INFO "%s: Running in WANPIPE (BRIDGE_NODE) mode.\n", 
-                                       card->devname);
-               }
-
-               if (!err){
-                       /* Dynamic interface configuration option.
-                        * On disconnect, if the options is selected,
-                        * the interface will be brought down */
-                       if (conf->if_down == WANOPT_YES){ 
-                               set_bit(DYN_OPT_ON,&chan->interface_down);
-                               printk(KERN_INFO 
-                                   "%s: Dynamic interface configuration enabled.\n",
-                                       card->devname);
-                       }
-               }
-
-        } else if(strcmp(conf->usedby, "API") == 0){
-
-                chan->common.usedby = API;
-                printk(KERN_INFO "%s: Running in API mode.\n",
-                       wandev->name);
-        }
-
-       if (err) {
-               
-               kfree(chan);
-               return err;
-       }
-
-       /* place cir,be,bc and other channel specific information into the
-        * chan structure 
-         */
-       if (conf->cir) {
-
-               chan->cir = max_t(unsigned int, 1,
-                               min_t(unsigned int, conf->cir, 512));
-               chan->cir_status = CIR_ENABLED; 
-
-               
-               /* If CIR is enabled, force BC to equal CIR
-                 * this solves number of potential problems if CIR is 
-                 * set and BC is not 
-                */
-               chan->bc = chan->cir;
-
-               if (conf->be){
-                       chan->be = max_t(unsigned int,
-                                      0, min_t(unsigned int, conf->be, 511));
-               }else{  
-                       conf->be = 0;
-               }
-
-               printk (KERN_INFO "%s: CIR enabled for DLCI %i \n",
-                               wandev->name,chan->dlci);
-               printk (KERN_INFO "%s:     CIR = %i ; BC = %i ; BE = %i\n",
-                               wandev->name,chan->cir,chan->bc,chan->be);
-
-
-       }else{
-               chan->cir_status = CIR_DISABLED;
-               printk (KERN_INFO "%s: CIR disabled for DLCI %i\n",
-                               wandev->name,chan->dlci);
-       }
-
-       chan->mc = conf->mc;
-
-       if (conf->inarp == WANOPT_YES){
-               printk(KERN_INFO "%s: Inverse ARP Support Enabled\n",card->devname);
-               chan->inarp = conf->inarp ? INARP_REQUEST : INARP_NONE;
-               chan->inarp_interval = conf->inarp_interval ? conf->inarp_interval : 10;
-       }else{
-               printk(KERN_INFO "%s: Inverse ARP Support Disabled\n",card->devname);
-               chan->inarp = INARP_NONE;
-               chan->inarp_interval = 10;
-       }
-
-
-       chan->dlci_configured = DLCI_NOT_CONFIGURED;    
-
-
-       /*FIXME: IPX disabled in this WANPIPE version */
-       if (conf->enable_IPX == WANOPT_YES){
-               printk(KERN_INFO "%s: ERROR - This version of WANPIPE doesn't support IPX\n",
-                               card->devname);
-               kfree(chan);
-               return -EINVAL;
-       }else{
-               chan->enable_IPX = WANOPT_NO;
-       }       
-
-       if (conf->network_number){
-               chan->network_number = conf->network_number;
-       }else{
-               chan->network_number = 0xDEADBEEF;
-       }
-
-       chan->route_flag = NO_ROUTE;
-       
-       init_chan_statistics(chan);
-
-       chan->transmit_length = 0;
-
-       /* prepare network device data space for registration */
-       strcpy(dev->name,chan->name);
-       
-       dev->init = &if_init;
-       dev->priv = chan;
-
-       /* Initialize FR Polling Task Queue
-         * We need a poll routine for each network
-         * interface. 
-         */
-       INIT_WORK(&chan->fr_poll_work, (void *)fr_poll, dev);
-
-       init_timer(&chan->fr_arp_timer);
-       chan->fr_arp_timer.data=(unsigned long)dev;
-       chan->fr_arp_timer.function = fr_arp;
-
-       wandev->new_if_cnt++;
-
-       /* Tells us that if this interface is a
-         * gateway or not */
-       if ((chan->gateway = conf->gateway) == WANOPT_YES){
-               printk(KERN_INFO "%s: Interface %s is set as a gateway.\n",
-                       card->devname,dev->name);
-       }
-
-       /* M. Grant Patch Apr 28 2000 
-         * Disallow duplicate dlci configurations. */
-       if (card->u.f.dlci_to_dev_map[chan->dlci] != NULL) {
-               kfree(chan);
-               return -EBUSY;
-       }
-
-       /* Configure this dlci at a later date, when
-         * the interface comes up. i.e. when if_open() 
-         * executes */
-       set_bit(0,&chan->config_dlci);
-       
-       printk(KERN_INFO "\n");
-
-       return 0;
-}
-
-/*============================================================================
- * Delete logical channel.
- */
-static int del_if(struct wan_device* wandev, struct net_device* dev)
-{
-       fr_channel_t* chan = dev->priv;
-       unsigned long smp_flags=0;
-
-       /* This interface is dead, make sure the 
-        * ARP timer is stopped */
-       del_timer(&chan->fr_arp_timer);
-       
-       /* If we are a NODE, we must unconfigure this DLCI
-        * Trigger an unconfigure command that will
-        * be executed in timer interrupt. We must wait
-        * for the command to complete. */
-       trigger_unconfig_fr(dev);
-
-       lock_adapter_irq(&wandev->lock, &smp_flags);
-       wandev->new_if_cnt--;
-       unlock_adapter_irq(&wandev->lock, &smp_flags);
-
-       return 0;
-}
-
-
-/*=====================================================================
- * disable_comm
- *
- * Description:
- *     Disable communications.
- *     This code runs in shutdown (sdlamain.c)
- *      under critical flag. Therefore it is not
- *      necessary to set a critical flag here 
- *
- * Usage:
- *     Commnunications are disabled only on a card
- *      shutdown.
- */
-
-static void disable_comm (sdla_t *card)
-{
-       printk(KERN_INFO "%s: Disabling Communications!\n",
-                       card->devname);
-       fr_comm_disable(card);
-}
-
-/****** WANPIPE-specific entry points ***************************************/
-
-/*============================================================================
- * Execute adapter interface command.
- */
-static int wpf_exec (struct sdla* card, void* u_cmd, void* u_data)
-{
-       fr_mbox_t* mbox = card->mbox;
-       int retry = MAX_CMD_RETRY;
-       int err, len;
-       fr_cmd_t cmd;
-
-       if(copy_from_user((void*)&cmd, u_cmd, sizeof(cmd)))
-               return -EFAULT;
-       
-       /* execute command */
-       do
-       {
-               memcpy(&mbox->cmd, &cmd, sizeof(cmd));
-               
-               if (cmd.length){
-                       if( copy_from_user((void*)&mbox->data, u_data, cmd.length))
-                               return -EFAULT;
-               }
-               
-               if (sdla_exec(mbox))
-                       err = mbox->cmd.result;
-
-               else return -EIO;
-       
-       } while (err && retry-- && fr_event(card, err, mbox));
-
-       /* return result */
-       if (copy_to_user(u_cmd, (void*)&mbox->cmd, sizeof(fr_cmd_t)))
-               return -EFAULT;
-
-       len = mbox->cmd.length;
-
-       if (len && u_data && !copy_to_user(u_data, (void*)&mbox->data, len))
-               return -EFAULT;
-       return 0;
-}
-
-/****** Network Device Interface ********************************************/
-
-/*============================================================================
- * Initialize Linux network interface.
- *
- * This routine is called only once for each interface, during Linux network
- * interface registration.  Returning anything but zero will fail interface
- * registration.
- */
-static int if_init(struct net_device* dev)
-{
-       fr_channel_t* chan = dev->priv;
-       sdla_t* card = chan->card;
-       struct wan_device* wandev = &card->wandev;
-
-       /* Initialize device driver entry points */
-       dev->open               = &if_open;
-       dev->stop               = &if_close;
-       dev->hard_header        = NULL;
-       dev->rebuild_header     = &if_rebuild_hdr;
-       dev->hard_start_xmit    = &if_send;
-       dev->get_stats          = &if_stats;
-       dev->tx_timeout         = &if_tx_timeout;
-       dev->watchdog_timeo     = TX_TIMEOUT;
-       
-       if (chan->common.usedby == WANPIPE || chan->common.usedby == API){
-
-               /* Initialize media-specific parameters */
-               if (chan->true_if_encoding){
-                       dev->type               = ARPHRD_DLCI;  /* This breaks tcpdump */
-               }else{
-                       dev->type               = ARPHRD_PPP;   /* ARP h/w type */
-               }
-               
-               dev->flags              |= IFF_POINTOPOINT;
-               dev->flags              |= IFF_NOARP;
-
-               /* Enable Multicast addressing */
-               if (chan->mc == WANOPT_YES){
-                       dev->flags      |= IFF_MULTICAST;
-               }
-
-               dev->mtu                = wandev->mtu - FR_HEADER_LEN;
-               /* For an API, the maximum number of bytes that the stack will pass
-                  to the driver is (dev->mtu + dev->hard_header_len). So, adjust the
-                  mtu so that a frame of maximum size can be transmitted by the API. 
-               */
-               if(chan->common.usedby == API) {
-                       dev->mtu += (sizeof(api_tx_hdr_t) - FR_HEADER_LEN);
-               }
-               
-               dev->hard_header_len    = FR_HEADER_LEN;/* media header length */
-               dev->addr_len           = 2;            /* hardware address length */
-               *(unsigned short*)dev->dev_addr = htons(chan->dlci);
-
-               /* Set transmit buffer queue length */
-               dev->tx_queue_len = 100;
-
-       }else{
-
-               /* Setup the interface for Bridging */
-               int hw_addr=0;
-               ether_setup(dev);
-               
-               /* Use a random number to generate the MAC address */
-               memcpy(dev->dev_addr, "\xFE\xFC\x00\x00\x00\x00", 6);
-               get_random_bytes(&hw_addr, sizeof(hw_addr));
-               *(int *)(dev->dev_addr + 2) += hw_addr;
-       }
-               
-       /* Initialize hardware parameters (just for reference) */
-       dev->irq        = wandev->irq;
-       dev->dma        = wandev->dma;
-       dev->base_addr  = wandev->ioport;
-       dev->mem_start  = wandev->maddr;
-       dev->mem_end    = wandev->maddr + wandev->msize - 1;
-       SET_MODULE_OWNER(dev);
-
-       return 0;
-}
-
-/*============================================================================
- * Open network interface.
- * o if this is the first open, then enable communications and interrupts.
- * o prevent module from unloading by incrementing use count
- *
- * Return 0 if O.k. or errno.
- */
-static int if_open(struct net_device* dev)
-{
-       fr_channel_t* chan = dev->priv;
-       sdla_t* card = chan->card;
-       int err = 0;
-       struct timeval tv;
-
-       if (netif_running(dev))
-               return -EBUSY;
-       
-       /* Initialize the task queue */
-       chan->tq_working=0;
-
-       INIT_WORK(&chan->common.wanpipe_work, (void *)fr_bh, dev);
-
-       /* Allocate and initialize BH circular buffer */
-       chan->bh_head = kmalloc((sizeof(bh_data_t)*MAX_BH_BUFF),GFP_ATOMIC);
-       memset(chan->bh_head,0,(sizeof(bh_data_t)*MAX_BH_BUFF));
-       atomic_set(&chan->bh_buff_used, 0);
-
-       netif_start_queue(dev);
-
-       wanpipe_open(card);
-       do_gettimeofday( &tv );
-       chan->router_start_time = tv.tv_sec;
-       
-       if (test_bit(0,&chan->config_dlci)){
-               trigger_config_fr (card);
-       }else if (chan->inarp == INARP_REQUEST){
-               trigger_fr_arp(dev);
-       }
-       
-       return err;
-}
-
-/*============================================================================
- * Close network interface.
- * o if this is the last open, then disable communications and interrupts.
- * o reset flags.
- */
-static int if_close(struct net_device* dev)
-{
-       fr_channel_t* chan = dev->priv;
-       sdla_t* card = chan->card;
-
-       if (chan->inarp == INARP_CONFIGURED) {
-               chan->inarp = INARP_REQUEST;
-       }
-
-       netif_stop_queue(dev);
-       wanpipe_close(card);
-
-       return 0;
-}
-
-/*============================================================================
- * Re-build media header.
- *
- * Return:     1       physical address resolved.
- *             0       physical address not resolved
- */
-static int if_rebuild_hdr (struct sk_buff* skb)
-{
-       struct net_device *dev = skb->dev;
-       fr_channel_t* chan = dev->priv;
-       sdla_t* card = chan->card;
-
-       printk(KERN_INFO "%s: rebuild_header() called for interface %s!\n",
-               card->devname, dev->name);
-       return 1;
-}
-
-/*============================================================================
- * Handle transmit timeout event from netif watchdog
- */
-static void if_tx_timeout(struct net_device *dev)
-{
-       fr_channel_t* chan = dev->priv;
-       sdla_t *card = chan->card;
-
-       /* If our device stays busy for at least 5 seconds then we will
-        * kick start the device by making dev->tbusy = 0.  We expect
-        * that our device never stays busy more than 5 seconds. So this                 
-        * is only used as a last resort.
-        */
-
-       chan->drvstats_if_send.if_send_tbusy++;
-       ++chan->ifstats.collisions;
-
-       printk (KERN_INFO "%s: Transmit timed out on %s\n", 
-                       card->devname, dev->name);
-       chan->drvstats_if_send.if_send_tbusy_timeout++;
-       netif_wake_queue (dev);
-
-}
-
-
-/*============================================================================
- * Send a packet on a network interface.
- * o set tbusy flag (marks start of the transmission) to block a timer-based
- *   transmit from overlapping.
- * o set critical flag when accessing board.
- * o check link state. If link is not up, then drop the packet.
- * o check channel status. If it's down then initiate a call.
- * o pass a packet to corresponding WAN device.
- * o free socket buffer
- *
- * Return:     0       complete (socket buffer must be freed)
- *             non-0   packet may be re-transmitted (tbusy must be set)
- *
- * Notes:
- * 1. This routine is called either by the protocol stack or by the "net
- *    bottom half" (with interrupts enabled).
- * 
- * 2. Using netif_start_queue() and netif_stop_queue()
- *    will inhibit further transmit requests from the protocol stack 
- *    and can be used for flow control with protocol layer.
- */
-static int if_send(struct sk_buff* skb, struct net_device* dev)
-{
-       fr_channel_t* chan = dev->priv;
-       sdla_t* card = chan->card;
-        int err;
-       unsigned char *sendpacket;
-       fr508_flags_t* adptr_flags = card->flags;
-       int udp_type;
-       long delay_tx_queued = 0;
-       unsigned long smp_flags=0;
-       unsigned char attr = 0;
-
-       chan->drvstats_if_send.if_send_entry++;
-
-       netif_stop_queue(dev);
-       
-        if (skb == NULL) {             
-               /* if we get here, some higher layer thinks we've missed an
-                * tx-done interrupt.
-                */
-               printk(KERN_INFO "%s: interface %s got kicked!\n", 
-                       card->devname, dev->name);
-               chan->drvstats_if_send.if_send_skb_null ++;
-
-               netif_wake_queue(dev);
-               return 0;
-       }
-
-       /* If a peripheral task is running just drop packets */
-       if (test_bit(PERI_CRIT, &card->wandev.critical)){
-               
-               printk(KERN_INFO "%s: Critical in if_send(): Peripheral running!\n",
-                               card->devname);
-               
-               dev_kfree_skb_any(skb);
-               netif_start_queue(dev);
-               return 0;
-       }
-
-       /* We must set the 'tbusy' flag if we already have a packet queued for
-          transmission in the transmit interrupt handler. However, we must
-          ensure that the transmit interrupt does not reset the 'tbusy' flag
-          just before we set it, as this will result in a "transmit timeout".
-       */
-       set_bit(SEND_TXIRQ_CRIT, (void*)&card->wandev.critical);
-        if(chan->transmit_length) {
-               netif_stop_queue(dev);
-               chan->tick_counter = jiffies;
-               clear_bit(SEND_TXIRQ_CRIT, (void*)&card->wandev.critical);
-               return 1;
-       }
-               clear_bit(SEND_TXIRQ_CRIT, (void*)&card->wandev.critical);
-       /* Move the if_header() code to here. By inserting frame
-        * relay header in if_header() we would break the
-        * tcpdump and other packet sniffers */
-       chan->fr_header_len = setup_fr_header(skb,dev,chan->common.usedby);
-       if (chan->fr_header_len < 0 ){
-               ++chan->ifstats.tx_dropped;
-               ++card->wandev.stats.tx_dropped;
-               
-               dev_kfree_skb_any(skb);
-               netif_start_queue(dev); 
-               return 0;
-       }
-
-       sendpacket = skb->data;
-
-       udp_type = udp_pkt_type(skb, card);
-
-        if(udp_type != UDP_INVALID_TYPE) {
-               if(store_udp_mgmt_pkt(udp_type, UDP_PKT_FRM_STACK, card, skb,
-                        chan->dlci)) {
-                        adptr_flags->imask |= FR_INTR_TIMER;
-                        if (udp_type == UDP_FPIPE_TYPE){
-                                chan->drvstats_if_send.
-                                       if_send_PIPE_request ++;
-                       }
-                }
-               netif_start_queue(dev);
-               return 0;
-       }
-
-       //FIXME: can we do better than sendpacket[2]?
-       if ((chan->common.usedby == WANPIPE) && (sendpacket[2] == 0x45)) {
-               
-                       /* check to see if the source IP address is a broadcast or */
-                /* multicast IP address */
-                if(chk_bcast_mcast_addr(card, dev, skb)){
-                       ++chan->ifstats.tx_dropped;
-                       ++card->wandev.stats.tx_dropped;
-                       dev_kfree_skb_any(skb);
-                       netif_start_queue(dev);
-                       return 0;
-               }
-       }
-
-       
-       /* Lock the S514/S508 card: SMP Supported */
-       s508_s514_lock(card,&smp_flags);
-
-       if (test_and_set_bit(SEND_CRIT, (void*)&card->wandev.critical)) {
-               
-               chan->drvstats_if_send.if_send_critical_non_ISR ++;
-               chan->ifstats.tx_dropped ++;
-               printk(KERN_INFO "%s Critical in IF_SEND: if_send() already running!\n", 
-                               card->devname);
-               goto if_send_start_and_exit;
-       }
-       
-       /* API packet check: minimum packet size must be greater than 
-        * 16 byte API header */
-       if((chan->common.usedby == API) && (skb->len <= sizeof(api_tx_hdr_t))) {
-               ++chan->ifstats.tx_dropped;
-               ++card->wandev.stats.tx_dropped;
-           
-               
-               goto if_send_start_and_exit;
-
-       }else{
-               /* During API transmission, get rid of the API header */
-               if (chan->common.usedby == API) {
-                       api_tx_hdr_t* api_tx_hdr;
-                       api_tx_hdr = (api_tx_hdr_t*)&skb->data[0x00];
-                       attr = api_tx_hdr->attr;
-                       skb_pull(skb,sizeof(api_tx_hdr_t));
-               }
-       }
-
-       if (card->wandev.state != WAN_CONNECTED) {
-               chan->drvstats_if_send.if_send_wan_disconnected ++;
-               ++chan->ifstats.tx_dropped;
-               ++card->wandev.stats.tx_dropped;
-       
-       } else if (chan->common.state != WAN_CONNECTED) {
-               chan->drvstats_if_send.if_send_dlci_disconnected ++;
-
-               /* Update the DLCI state in timer interrupt */
-               card->u.f.timer_int_enabled |= TMR_INT_ENABLED_UPDATE_STATE;    
-               adptr_flags->imask |= FR_INTR_TIMER;
-
-               ++chan->ifstats.tx_dropped;
-               ++card->wandev.stats.tx_dropped;
-               
-       } else if (!is_tx_ready(card, chan)) {
-               /* No tx buffers available, store for delayed transmit */
-               if (!setup_for_delayed_transmit(dev, skb)){
-                       set_bit(1,&delay_tx_queued);
-               }
-               chan->drvstats_if_send.if_send_no_bfrs++;
-               
-       } else if (!skb->protocol) {
-               /* No protocols drop packet */
-               chan->drvstats_if_send.if_send_protocol_error ++;
-               ++card->wandev.stats.tx_errors;
-       
-       } else if (test_bit(ARP_CRIT,&card->wandev.critical)){
-               /* We are trying to send an ARP Packet, block IP data until
-                * ARP is sent */
-               ++chan->ifstats.tx_dropped;
-               ++card->wandev.stats.tx_dropped;
-               
-       } else {
-               //FIXME: IPX is not implemented in this version of Frame Relay ?
-               if((chan->common.usedby == WANPIPE) &&
-                       sendpacket[1] == 0x00 &&
-                       sendpacket[2] == 0x80 &&
-                       sendpacket[6] == 0x81 &&
-                       sendpacket[7] == 0x37) {
-                       
-                       if( chan->enable_IPX ) {
-                               switch_net_numbers(sendpacket, 
-                                               chan->network_number, 0);
-                       } else {
-                               //FIXME: Take this out when IPX is fixed 
-                               printk(KERN_INFO 
-                               "%s: WARNING: Unsupported IPX data in send, packet dropped\n",
-                                       card->devname);
-                       }
-                       
-               }else{
-                       err = fr_send_data_header(card, chan->dlci, attr, skb->len, skb->data, chan->fr_header_len);
-                       if (err) {
-                               switch(err) {
-                               case FRRES_CIR_OVERFLOW:
-                               case FRRES_BUFFER_OVERFLOW:
-                                       if (!setup_for_delayed_transmit(dev, skb)){
-                                               set_bit(1,&delay_tx_queued);
-                                       }
-                                       chan->drvstats_if_send.
-                                               if_send_adptr_bfrs_full ++;
-                                       break;
-                                       
-                               case FRRES_TOO_LONG:
-                                       if (net_ratelimit()){
-                                               printk(KERN_INFO 
-                                               "%s: Error: Frame too long, transmission failed %i\n",
-                                                card->devname, (unsigned int)skb->len);
-                                       }
-                                       /* Drop down to default */
-                               default:
-                                       chan->drvstats_if_send.
-                                               if_send_dlci_disconnected ++;
-                                       ++chan->ifstats.tx_dropped;
-                                       ++card->wandev.stats.tx_dropped;
-                                       break;
-                               }
-                       } else {
-                               chan->drvstats_if_send.
-                                       if_send_bfr_passed_to_adptr++;
-                               ++chan->ifstats.tx_packets;
-                               ++card->wandev.stats.tx_packets;
-                               
-                                chan->ifstats.tx_bytes += skb->len;
-                                card->wandev.stats.tx_bytes += skb->len;
-                               dev->trans_start = jiffies;
-                       }
-               }
-       }
-
-if_send_start_and_exit:
-
-       netif_start_queue(dev);
-       
-       /* If we queued the packet for transmission, we must not
-        * deallocate it. The packet is unlinked from the IP stack
-        * not copied. Therefore, we must keep the original packet */
-       if (!test_bit(1,&delay_tx_queued)) {
-                dev_kfree_skb_any(skb);
-       }else{
-               adptr_flags->imask |= FR_INTR_TXRDY;
-               card->u.f.tx_interrupts_pending ++;
-       }
-
-        clear_bit(SEND_CRIT, (void*)&card->wandev.critical);
-
-       s508_s514_unlock(card,&smp_flags);
-
-       return 0;
-}
-
-
-
-/*============================================================================
- * Setup so that a frame can be transmitted on the occurrence of a transmit
- * interrupt.
- */
-static int setup_for_delayed_transmit(struct net_device* dev,
-                                     struct sk_buff *skb)
-{
-        fr_channel_t* chan = dev->priv;
-        sdla_t* card = chan->card;
-        fr_dlci_interface_t* dlci_interface;
-       int len = skb->len;
-
-       /* Check that the dlci is properly configured,
-         * before using tx interrupt */
-       if (!chan->dlci_int_interface){
-               if (net_ratelimit()){ 
-                       printk(KERN_INFO 
-                               "%s: ERROR on DLCI %i: Not configured properly !\n",
-                                       card->devname, chan->dlci);
-                       printk(KERN_INFO "%s: Please contact Sangoma Technologies\n",
-                                       card->devname);
-               }
-               return 1;
-       }
-               
-       dlci_interface = chan->dlci_int_interface;
-
-        if(chan->transmit_length) {
-                printk(KERN_INFO "%s: Big mess in setup_for_del...\n",
-                               card->devname);
-                return 1;
-        }
-
-       if(len > FR_MAX_NO_DATA_BYTES_IN_FRAME) {
-               //FIXME: increment some statistic */
-               return 1;
-       }
-
-        chan->transmit_length = len;
-       chan->delay_skb = skb;
-        
-        dlci_interface->gen_interrupt |= FR_INTR_TXRDY;
-        dlci_interface->packet_length = len;
-
-       /* Turn on TX interrupt at the end of if_send */
-       return 0;
-}
-
-
-/*============================================================================
- * Check to see if the packet to be transmitted contains a broadcast or
- * multicast source IP address.
- * Return 0 if not broadcast/multicast address, otherwise return 1.
- */
-
-static int chk_bcast_mcast_addr(sdla_t *card, struct net_device* dev,
-                                struct sk_buff *skb)
-{
-        u32 src_ip_addr;
-        u32 broadcast_ip_addr = 0;
-        struct in_device *in_dev;
-        fr_channel_t* chan = dev->priv;
-        /* read the IP source address from the outgoing packet */
-        src_ip_addr = *(u32 *)(skb->data + 14);
-
-        /* read the IP broadcast address for the device */
-        in_dev = dev->ip_ptr;
-        if(in_dev != NULL) {
-                struct in_ifaddr *ifa= in_dev->ifa_list;
-                if(ifa != NULL)
-                        broadcast_ip_addr = ifa->ifa_broadcast;
-                else
-                        return 0;
-        }
-
-        /* check if the IP Source Address is a Broadcast address */
-        if((dev->flags & IFF_BROADCAST) && (src_ip_addr == broadcast_ip_addr)) {
-                printk(KERN_INFO
-                        "%s: Broadcast Source Address silently discarded\n",
-                        card->devname);
-                return 1;
-        }
-
-        /* check if the IP Source Address is a Multicast address */
-        if((chan->mc == WANOPT_NO) && (ntohl(src_ip_addr) >= 0xE0000001) &&
-                (ntohl(src_ip_addr) <= 0xFFFFFFFE)) {
-                printk(KERN_INFO
-                        "%s: Multicast Source Address silently discarded\n",
-                        card->devname);
-                return 1;
-        }
-
-        return 0;
-}
-
-/*============================================================================
- * Reply to UDP Management system.
- * Return nothing.
- */
-static int reply_udp( unsigned char *data, unsigned int mbox_len ) 
-{
-       unsigned short len, udp_length, temp, ip_length;
-       unsigned long ip_temp;
-       int even_bound = 0;
-
-  
-       fr_udp_pkt_t *fr_udp_pkt = (fr_udp_pkt_t *)data; 
-
-       /* Set length of packet */
-       len = //sizeof(fr_encap_hdr_t)+
-             sizeof(ip_pkt_t)+ 
-             sizeof(udp_pkt_t)+
-             sizeof(wp_mgmt_t)+
-             sizeof(cblock_t)+
-             mbox_len;
-
-       /* fill in UDP reply */
-       fr_udp_pkt->wp_mgmt.request_reply = UDPMGMT_REPLY;
-  
-       /* fill in UDP length */
-       udp_length = sizeof(udp_pkt_t)+ 
-                    sizeof(wp_mgmt_t)+
-                    sizeof(cblock_t)+
-                    mbox_len; 
-
-
-       /* put it on an even boundary */
-       if ( udp_length & 0x0001 ) {
-               udp_length += 1;
-               len += 1;
-               even_bound = 1;
-       }
-
-       temp = (udp_length<<8)|(udp_length>>8);
-       fr_udp_pkt->udp_pkt.udp_length = temp;
-        
-       /* swap UDP ports */
-       temp = fr_udp_pkt->udp_pkt.udp_src_port;
-       fr_udp_pkt->udp_pkt.udp_src_port = 
-                       fr_udp_pkt->udp_pkt.udp_dst_port; 
-       fr_udp_pkt->udp_pkt.udp_dst_port = temp;
-
-
-
-       /* add UDP pseudo header */
-       temp = 0x1100;
-       *((unsigned short *)
-               (fr_udp_pkt->data+mbox_len+even_bound)) = temp; 
-       temp = (udp_length<<8)|(udp_length>>8);
-       *((unsigned short *)
-               (fr_udp_pkt->data+mbox_len+even_bound+2)) = temp;
-                
-       /* calculate UDP checksum */
-       fr_udp_pkt->udp_pkt.udp_checksum = 0;
-
-       fr_udp_pkt->udp_pkt.udp_checksum = 
-               calc_checksum(&data[UDP_OFFSET/*+sizeof(fr_encap_hdr_t)*/],
-                             udp_length+UDP_OFFSET);
-
-       /* fill in IP length */
-       ip_length = udp_length + sizeof(ip_pkt_t);
-       temp = (ip_length<<8)|(ip_length>>8);
-       fr_udp_pkt->ip_pkt.total_length = temp;
-  
-       /* swap IP addresses */
-       ip_temp = fr_udp_pkt->ip_pkt.ip_src_address;
-       fr_udp_pkt->ip_pkt.ip_src_address = 
-                               fr_udp_pkt->ip_pkt.ip_dst_address;
-       fr_udp_pkt->ip_pkt.ip_dst_address = ip_temp;
-
-                
-       /* fill in IP checksum */
-       fr_udp_pkt->ip_pkt.hdr_checksum = 0;
-       fr_udp_pkt->ip_pkt.hdr_checksum = 
-               calc_checksum(&data[/*sizeof(fr_encap_hdr_t)*/0],
-                             sizeof(ip_pkt_t));
-
-       return len;
-} /* reply_udp */
-
-unsigned short calc_checksum (char *data, int len)
-{
-       unsigned short temp; 
-       unsigned long sum=0;
-       int i;
-
-       for( i = 0; i <len; i+=2 ) {
-               memcpy(&temp,&data[i],2);
-               sum += (unsigned long)temp;
-       }
-
-       while (sum >> 16 ) {
-               sum = (sum & 0xffffUL) + (sum >> 16);
-       }
-
-       temp = (unsigned short)sum;
-       temp = ~temp;
-
-       if( temp == 0 ) 
-               temp = 0xffff;
-
-       return temp;    
-}
-
-/*
-   If incoming is 0 (outgoing)- if the net numbers is ours make it 0
-   if incoming is 1 - if the net number is 0 make it ours 
-
-*/
-static void switch_net_numbers(unsigned char *sendpacket, unsigned long network_number, unsigned char incoming)
-{
-       unsigned long pnetwork_number;
-
-       pnetwork_number = (unsigned long)((sendpacket[14] << 24) + 
-                         (sendpacket[15] << 16) + (sendpacket[16] << 8) + 
-                         sendpacket[17]);
-
-       if (!incoming) {
-               /* If the destination network number is ours, make it 0 */
-               if( pnetwork_number == network_number) {
-                       sendpacket[14] = sendpacket[15] = sendpacket[16] = 
-                                        sendpacket[17] = 0x00;
-               }
-       } else {
-               /* If the incoming network is 0, make it ours */
-               if( pnetwork_number == 0) {
-                       sendpacket[14] = (unsigned char)(network_number >> 24);
-                       sendpacket[15] = (unsigned char)((network_number & 
-                                        0x00FF0000) >> 16);
-                       sendpacket[16] = (unsigned char)((network_number & 
-                                        0x0000FF00) >> 8);
-                       sendpacket[17] = (unsigned char)(network_number & 
-                                        0x000000FF);
-               }
-       }
-
-
-       pnetwork_number = (unsigned long)((sendpacket[26] << 24) + 
-                         (sendpacket[27] << 16) + (sendpacket[28] << 8) + 
-                         sendpacket[29]);
-
-       if( !incoming ) {
-               /* If the source network is ours, make it 0 */
-               if( pnetwork_number == network_number) {
-                       sendpacket[26] = sendpacket[27] = sendpacket[28] = 
-                                        sendpacket[29] = 0x00;
-               }
-       } else {
-               /* If the source network is 0, make it ours */
-               if( pnetwork_number == 0 ) {
-                       sendpacket[26] = (unsigned char)(network_number >> 24);
-                       sendpacket[27] = (unsigned char)((network_number & 
-                                        0x00FF0000) >> 16);
-                       sendpacket[28] = (unsigned char)((network_number & 
-                                        0x0000FF00) >> 8);
-                       sendpacket[29] = (unsigned char)(network_number & 
-                                        0x000000FF);
-               }
-       }
-} /* switch_net_numbers */
-
-/*============================================================================
- * Get ethernet-style interface statistics.
- * Return a pointer to struct enet_statistics.
- */
-static struct net_device_stats *if_stats(struct net_device *dev)
-{
-       fr_channel_t* chan = dev->priv;
-       
-       if(chan == NULL)
-               return NULL;
-
-       return &chan->ifstats;
-}
-
-/****** Interrupt Handlers **************************************************/
-
-/*============================================================================
- * fr_isr:     S508 frame relay interrupt service routine.
- *
- * Description:
- *     Frame relay main interrupt service route. This
- *      function check the interrupt type and takes
- *      the appropriate action.
- */
-static void fr_isr (sdla_t* card)
-{
-       fr508_flags_t* flags = card->flags;
-       char *ptr = &flags->iflag;
-       int i,err;
-       fr_mbox_t* mbox = card->mbox;
-
-       /* This flag prevents nesting of interrupts.  See sdla_isr() routine
-         * in sdlamain.c.  */
-       card->in_isr = 1;
-       
-       ++card->statistics.isr_entry;
-
-
-       /* All peripheral (configuraiton, re-configuration) events
-        * take presidence over the ISR.  Thus, retrigger */
-       if (test_bit(PERI_CRIT, (void*)&card->wandev.critical)) {
-               ++card->statistics.isr_already_critical;
-               goto fr_isr_exit;
-       }
-       
-        if(card->hw.type != SDLA_S514) {
-               if (test_bit(SEND_CRIT, (void*)&card->wandev.critical)) {
-                        printk(KERN_INFO "%s: Critical while in ISR: If Send Running!\n",
-                                card->devname);
-                       ++card->statistics.isr_already_critical;
-                       goto fr_isr_exit;
-               }
-       }
-
-       switch (flags->iflag) {
-
-                case FR_INTR_RXRDY:  /* receive interrupt */
-                       ++card->statistics.isr_rx;
-                       rx_intr(card);
-                       break;
-
-
-                case FR_INTR_TXRDY:  /* transmit interrupt */
-                       ++ card->statistics.isr_tx; 
-                       tx_intr(card); 
-                       break;
-
-                case FR_INTR_READY:    
-                       Intr_test_counter++;
-                       ++card->statistics.isr_intr_test;
-                       break;  
-
-                case FR_INTR_DLC: /* Event interrupt occurred */
-                       mbox->cmd.command = FR_READ_STATUS;
-                       mbox->cmd.length = 0;
-                       err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-                       if (err)
-                               fr_event(card, err, mbox);
-                       break;
-
-                case FR_INTR_TIMER:  /* Timer interrupt */
-                       timer_intr(card);
-                       break;
-       
-               default:
-                       ++card->statistics.isr_spurious;
-                       spur_intr(card);
-                       printk(KERN_INFO "%s: Interrupt Type 0x%02X!\n", 
-                               card->devname, flags->iflag);
-           
-                       printk(KERN_INFO "%s: ID Bytes = ",card->devname);
-                       for(i = 0; i < 8; i ++)
-                               printk(KERN_INFO "0x%02X ", *(ptr + 0x28 + i));
-                       printk(KERN_INFO "\n"); 
-            
-                       break;
-       }
-
-fr_isr_exit:
-       
-       card->in_isr = 0;
-       flags->iflag = 0;
-       return;
-}
-
-
-
-/*===========================================================
- * rx_intr     Receive interrupt handler.
- *
- * Description
- *     Upon receiveing an interrupt: 
- *     1. Check that the firmware is in sync with 
- *                the driver. 
- *      2. Find an appropriate network interface
- *         based on the received dlci number.
- *     3. Check that the netowrk interface exists
- *         and that it's setup properly.
- *     4. Copy the data into an skb buffer.
- *     5. Check the packet type and take
- *         appropriate acton: UPD, API, ARP or Data.
- */
-
-static void rx_intr (sdla_t* card)
-{
-       fr_rx_buf_ctl_t* frbuf = card->rxmb;
-       fr508_flags_t* flags = card->flags;
-       fr_channel_t* chan;
-       char *ptr = &flags->iflag;
-       struct sk_buff* skb;
-       struct net_device* dev;
-       void* buf;
-       unsigned dlci, len, offs, len_incl_hdr;
-       int i, udp_type;        
-
-
-       /* Check that firmware buffers are in sync */
-       if (frbuf->flag != 0x01) {
-
-               printk(KERN_INFO 
-                       "%s: corrupted Rx buffer @ 0x%X, flag = 0x%02X!\n", 
-                       card->devname, (unsigned)frbuf, frbuf->flag);
-      
-               printk(KERN_INFO "%s: ID Bytes = ",card->devname);
-               for(i = 0; i < 8; i ++)
-                       printk(KERN_INFO "0x%02X ", *(ptr + 0x28 + i));
-               printk(KERN_INFO "\n");
-       
-               ++card->statistics.rx_intr_corrupt_rx_bfr;
-
-               /* Bug Fix: Mar 6 2000
-                 * If we get a corrupted mailbox, it means that driver 
-                 * is out of sync with the firmware. There is no recovery.
-                 * If we don't turn off all interrupts for this card
-                 * the machine will crash. 
-                 */
-               printk(KERN_INFO "%s: Critical router failure ...!!!\n", card->devname);
-               printk(KERN_INFO "Please contact Sangoma Technologies !\n");
-               fr_set_intr_mode(card, 0, 0, 0);        
-               return;
-       }
-
-       len  = frbuf->length;
-       dlci = frbuf->dlci;
-       offs = frbuf->offset;
-
-       /* Find the network interface for this packet */
-       dev = find_channel(card, dlci);
-   
-
-       /* Check that the network interface is active and
-         * properly setup */
-       if (dev == NULL) {
-               if( net_ratelimit()) { 
-                       printk(KERN_INFO "%s: received data on unconfigured DLCI %d!\n",
-                                                card->devname, dlci);
-               }
-               ++card->statistics.rx_intr_on_orphaned_DLCI; 
-               ++card->wandev.stats.rx_dropped;
-               goto rx_done;
-       }
-
-       if ((chan = dev->priv) == NULL){
-               if( net_ratelimit()) { 
-                       printk(KERN_INFO "%s: received data on unconfigured DLCI %d!\n",
-                                                card->devname, dlci);
-               }
-               ++card->statistics.rx_intr_on_orphaned_DLCI; 
-               ++card->wandev.stats.rx_dropped;
-               goto rx_done;
-       }
-
-       skb = dev_alloc_skb(len); 
-
-       if (!netif_running(dev) || (skb == NULL)){
-
-               ++chan->ifstats.rx_dropped;
-       
-               if(skb == NULL) {
-                       if (net_ratelimit()) { 
-                               printk(KERN_INFO 
-                                       "%s: no socket buffers available!\n", 
-                                               card->devname);
-                       }
-                       chan->drvstats_rx_intr.rx_intr_no_socket ++;
-               } 
-
-               if (!netif_running(dev)){
-                       chan->drvstats_rx_intr.
-                               rx_intr_dev_not_started ++;
-                       if (skb){
-                               dev_kfree_skb_any(skb);
-                       }
-               }
-               goto rx_done;
-       }
-
-       /* Copy data from the board into the socket buffer */
-       if ((offs + len) > card->u.f.rx_top + 1) {
-               unsigned tmp = card->u.f.rx_top - offs + 1;
-
-               buf = skb_put(skb, tmp);
-               sdla_peek(&card->hw, offs, buf, tmp);
-               offs = card->u.f.rx_base;
-               len -= tmp;
-       }
-
-       buf = skb_put(skb, len);
-       sdla_peek(&card->hw, offs, buf, len);
-
-
-       /* We got the packet from the bard. 
-         * Check the packet type and take appropriate action */
-
-       udp_type = udp_pkt_type( skb, card );
-
-       if(udp_type != UDP_INVALID_TYPE) {
-
-               /* UDP Debug packet received, store the
-                * packet and handle it in timer interrupt */
-
-               skb_pull(skb, 1); 
-               if (wanrouter_type_trans(skb, dev)){ 
-                       if(store_udp_mgmt_pkt(udp_type,UDP_PKT_FRM_NETWORK,card,skb,dlci)){
-
-                               flags->imask |= FR_INTR_TIMER;
-
-                               if (udp_type == UDP_FPIPE_TYPE){
-                                       ++chan->drvstats_rx_intr.rx_intr_PIPE_request;
-                               }
-                       }
-               }
-
-       }else if (chan->common.usedby == API) {
-
-               /* We are in API mode. 
-                 * Add an API header to the RAW packet
-                 * and queue it into a circular buffer.
-                 * Then kick the fr_bh() bottom half handler */
-
-               api_rx_hdr_t* api_rx_hdr;
-               chan->drvstats_rx_intr.rx_intr_bfr_passed_to_stack ++;
-               chan->ifstats.rx_packets ++;
-               card->wandev.stats.rx_packets ++;
-
-               chan->ifstats.rx_bytes += skb->len;
-               card->wandev.stats.rx_bytes += skb->len;
-
-               skb_push(skb, sizeof(api_rx_hdr_t));
-               api_rx_hdr = (api_rx_hdr_t*)&skb->data[0x00];
-               api_rx_hdr->attr = frbuf->attr;
-               api_rx_hdr->time_stamp = frbuf->tmstamp;
-
-               skb->protocol = htons(ETH_P_IP);
-               skb->mac.raw  = skb->data;
-               skb->dev      = dev;
-               skb->pkt_type = WAN_PACKET_DATA;
-
-               bh_enqueue(dev, skb);
-
-               trigger_fr_bh(chan);
-
-       }else if (handle_IPXWAN(skb->data,chan->name,chan->enable_IPX, chan->network_number)){
-
-               //FIXME: Frame Relay IPX is not supported, Yet !
-               //if (chan->enable_IPX) {
-               //      fr_send(card, dlci, 0, skb->len,skb->data);
-               //}
-               dev_kfree_skb_any(skb);
-
-       } else if (is_arp(skb->data)) {
-
-               /* ARP support enabled Mar 16 2000 
-                * Process incoming ARP reply/request, setup
-                * dynamic routes. */ 
-
-               if (process_ARP((arphdr_1490_t *)skb->data, card, dev)) {
-                       if (net_ratelimit()){  
-                               printk (KERN_INFO 
-                                  "%s: Error processing ARP Packet.\n", 
-                                       card->devname);
-                       }
-               }
-               dev_kfree_skb_any(skb);
-
-       } else if (skb->data[0] != 0x03) {
-
-               if (net_ratelimit()) { 
-                       printk(KERN_INFO "%s: Non IETF packet discarded.\n", 
-                               card->devname);
-               }
-               dev_kfree_skb_any(skb);
-
-       } else {
-
-               len_incl_hdr = skb->len;
-               /* Decapsulate packet and pass it up the
-                  protocol stack */
-               skb->dev = dev;
-               
-               if (chan->common.usedby == BRIDGE || chan->common.usedby == BRIDGE_NODE){
-               
-                       /* Make sure it's an Ethernet frame, otherwise drop it */
-                       if (!memcmp(skb->data, "\x03\x00\x80\x00\x80\xC2\x00\x07", 8)) {
-                               skb_pull(skb, 8);
-                               skb->protocol=eth_type_trans(skb,dev);
-                       }else{
-                               ++chan->drvstats_rx_intr.rx_intr_bfr_not_passed_to_stack;
-                               ++chan->ifstats.rx_errors;
-                               ++card->wandev.stats.rx_errors;
-                               goto rx_done;
-                       }
-               }else{
-               
-                       /* remove hardware header */
-                       buf = skb_pull(skb, 1); 
-                       
-                       if (!wanrouter_type_trans(skb, dev)) {
-                               
-                               /* can't decapsulate packet */
-                               dev_kfree_skb_any(skb);
-
-                               ++chan->drvstats_rx_intr.rx_intr_bfr_not_passed_to_stack;
-                               ++chan->ifstats.rx_errors;
-                               ++card->wandev.stats.rx_errors;
-                               goto rx_done;   
-                       }
-                       skb->mac.raw = skb->data;
-               } 
-               
-
-               /* Send a packet up the IP stack */
-               skb->dev->last_rx = jiffies;
-               netif_rx(skb);
-               ++chan->drvstats_rx_intr.rx_intr_bfr_passed_to_stack;
-               ++chan->ifstats.rx_packets;
-               ++card->wandev.stats.rx_packets;
-
-               chan->ifstats.rx_bytes += len_incl_hdr;
-               card->wandev.stats.rx_bytes += len_incl_hdr;
-       }
-
-rx_done:
-
-               /* Release buffer element and calculate a pointer to the next one */ 
-               frbuf->flag = 0;
-       card->rxmb = ++frbuf;
-       if ((void*)frbuf > card->u.f.rxmb_last)
-               card->rxmb = card->u.f.rxmb_base;
-
-}
-
-/*==================================================================
- * tx_intr:    Transmit interrupt handler.
- *
- * Rationale:
- *      If the board is busy transmitting, if_send() will
- *      buffers a single packet and turn on
- *      the tx interrupt. Tx interrupt will be called
- *      by the board, once the firmware can send more
- *      data. Thus, no polling is required.     
- *
- * Description:
- *     Tx interrupt is called for each 
- *      configured dlci channel. Thus: 
- *     1. Obtain the netowrk interface based on the
- *         dlci number.
- *      2. Check that network interface is up and
- *         properly setup.
- *     3. Check for a buffered packet.
- *      4. Transmit the packet.
- *     5. If we are in WANPIPE mode, mark the 
- *         NET_BH handler. 
- *      6. If we are in API mode, kick
- *         the AF_WANPIPE socket for more data. 
- *        
- */
-static void tx_intr(sdla_t *card)
-{
-        fr508_flags_t* flags = card->flags;
-        fr_tx_buf_ctl_t* bctl;
-        struct net_device* dev;
-        fr_channel_t* chan;
-
-        if(card->hw.type == SDLA_S514){
-                bctl = (void*)(flags->tse_offs + card->hw.dpmbase);
-        }else{
-                bctl = (void*)(flags->tse_offs - FR_MB_VECTOR +
-                        card->hw.dpmbase);
-       }
-
-        /* Find the structure and make it unbusy */
-        dev = find_channel(card, flags->dlci);
-       if (dev == NULL){
-               printk(KERN_INFO "NO DEV IN TX Interrupt\n");   
-               goto end_of_tx_intr;
-       }
-
-        if ((chan = dev->priv) == NULL){
-               printk(KERN_INFO "NO CHAN IN TX Interrupt\n");  
-               goto end_of_tx_intr;
-       }
-
-        if(!chan->transmit_length || !chan->delay_skb) {
-                printk(KERN_INFO "%s: tx int error - transmit length zero\n",
-                               card->wandev.name);
-                goto end_of_tx_intr;
-        }
-
-       /* If the 'if_send()' procedure is currently checking the 'tbusy'
-          status, then we cannot transmit. Instead, we configure the microcode
-          so as to re-issue this transmit interrupt at a later stage. 
-       */
-       if (test_bit(SEND_TXIRQ_CRIT, (void*)&card->wandev.critical)) {
-
-               fr_dlci_interface_t* dlci_interface = chan->dlci_int_interface;
-               bctl->flag = 0xA0;
-               dlci_interface->gen_interrupt |= FR_INTR_TXRDY;
-               return;
-
-       }else{
-               bctl->dlci = flags->dlci;
-               bctl->length = chan->transmit_length+chan->fr_header_len;
-               sdla_poke(&card->hw, 
-                         fr_send_hdr(card,bctl->dlci,bctl->offset), 
-                         chan->delay_skb->data,
-                         chan->delay_skb->len);
-               bctl->flag = 0xC0;
-
-               ++chan->ifstats.tx_packets;
-               ++card->wandev.stats.tx_packets;
-               chan->ifstats.tx_bytes += chan->transmit_length;
-               card->wandev.stats.tx_bytes += chan->transmit_length;
-
-               /* We must free an sk buffer, which we used
-                * for delayed transmission; Otherwise, the sock
-                * will run out of memory */
-                dev_kfree_skb_any(chan->delay_skb);
-
-               chan->delay_skb = NULL;                         
-               chan->transmit_length = 0;
-
-               dev->trans_start = jiffies;
-
-               if (netif_queue_stopped(dev)){
-                       /* If using API, than wakeup socket BH handler */
-                       if (chan->common.usedby == API){
-                               netif_start_queue(dev);
-                               wakeup_sk_bh(dev);
-                       }else{
-                               netif_wake_queue(dev);
-                       }
-               }
-       }
-
-end_of_tx_intr:
-
-       /* if any other interfaces have transmit interrupts pending, 
-        * do not disable the global transmit interrupt */
-       if(!(-- card->u.f.tx_interrupts_pending))
-                       flags->imask &= ~FR_INTR_TXRDY;
-
-
-}
-
-
-/*============================================================================
- * timer_intr: Timer interrupt handler.
- *
- * Rationale:
- *     All commans must be executed within the timer
- *      interrupt since no two commands should execute
- *      at the same time.
- *
- * Description:
- *     The timer interrupt is used to:
- *     1. Processing udp calls from 'fpipemon'.
- *     2. Processing update calls from /proc file system
- *     3. Reading board-level statistics for 
- *         updating the proc file system.
- *     4. Sending inverse ARP request packets.
- *     5. Configure a dlci/channel.
- *     6. Unconfigure a dlci/channel. (Node only)
- */
-
-static void timer_intr(sdla_t *card)
-{
-       fr508_flags_t* flags = card->flags;
-
-       /* UDP Debuging: fpipemon call */
-        if (card->u.f.timer_int_enabled & TMR_INT_ENABLED_UDP) {
-               if(card->u.f.udp_type == UDP_FPIPE_TYPE) {
-                       if(process_udp_mgmt_pkt(card)) {
-                               card->u.f.timer_int_enabled &=
-                                       ~TMR_INT_ENABLED_UDP;
-                       }
-               }
-        }
-
-       /* /proc update call : triggered from update() */
-       if (card->u.f.timer_int_enabled & TMR_INT_ENABLED_UPDATE) {
-               fr_get_err_stats(card);
-               fr_get_stats(card);
-               card->u.f.update_comms_stats = 0;
-               card->u.f.timer_int_enabled &= ~TMR_INT_ENABLED_UPDATE;
-       }
-
-       /* Update the channel state call.  This is call is
-         * triggered by if_send() function */
-       if (card->u.f.timer_int_enabled & TMR_INT_ENABLED_UPDATE_STATE){
-               struct net_device *dev;
-               if (card->wandev.state == WAN_CONNECTED){
-                       for (dev = card->wandev.dev; dev;
-                            dev = *((struct net_device **)dev->priv)){
-                               fr_channel_t *chan = dev->priv; 
-                               if (chan->common.state != WAN_CONNECTED){
-                                       update_chan_state(dev);
-                               }
-                       }
-               }
-               card->u.f.timer_int_enabled &= ~TMR_INT_ENABLED_UPDATE_STATE;
-       }
-
-       /* configure a dlci/channel */
-       if (card->u.f.timer_int_enabled & TMR_INT_ENABLED_CONFIG){
-               config_fr(card);
-               card->u.f.timer_int_enabled &= ~TMR_INT_ENABLED_CONFIG;
-       }
-
-       /* unconfigure a dlci/channel */
-       if (card->u.f.timer_int_enabled & TMR_INT_ENABLED_UNCONFIG){
-               unconfig_fr(card);
-               card->u.f.timer_int_enabled &= ~TMR_INT_ENABLED_UNCONFIG;
-       }
-
-       
-       /* Transmit ARP packets */
-       if (card->u.f.timer_int_enabled & TMR_INT_ENABLED_ARP){
-               int i=0;
-               struct net_device *dev;
-
-               if (card->u.f.arp_dev == NULL)
-                       card->u.f.arp_dev = card->wandev.dev;
-
-               dev = card->u.f.arp_dev;
-
-               for (;;){ 
-
-                       fr_channel_t *chan = dev->priv;
-
-                       /* If the interface is brought down cancel sending In-ARPs */
-                       if (!(dev->flags&IFF_UP)){
-                               clear_bit(0,&chan->inarp_ready);        
-                       }
-
-                       if (test_bit(0,&chan->inarp_ready)){
-
-                               if (check_tx_status(card,dev)){
-                                       set_bit(ARP_CRIT,&card->wandev.critical);
-                                       break;
-                               }
-
-                               if (!send_inarp_request(card,dev)){
-                                       trigger_fr_arp(dev);
-                                       chan->inarp_tick = jiffies;
-                               }
-
-                               clear_bit(0,&chan->inarp_ready);
-                               dev = move_dev_to_next(card,dev);
-                               break;
-                       }
-                       dev = move_dev_to_next(card,dev);
-
-                       if (++i == card->wandev.new_if_cnt){
-                               card->u.f.timer_int_enabled &= ~TMR_INT_ENABLED_ARP;
-                               break;
-                       }
-               }
-               card->u.f.arp_dev = dev;
-       }
-
-        if(!card->u.f.timer_int_enabled)
-                flags->imask &= ~FR_INTR_TIMER;
-}
-
-
-/*============================================================================
- * spur_intr:  Spurious interrupt handler.
- * 
- * Description:
- *     We don't know this interrupt.
- *      Print a warning.
- */
-
-static void spur_intr (sdla_t* card)
-{
-       if (net_ratelimit()){ 
-               printk(KERN_INFO "%s: spurious interrupt!\n", card->devname);
-       }
-}
-
-
-//FIXME: Fix the IPX in next version
-/*===========================================================================
- *  Return 0 for non-IPXWAN packet
- *         1 for IPXWAN packet or IPX is not enabled!
- *  FIXME: Use a IPX structure here not offsets
- */
-static int handle_IPXWAN(unsigned char *sendpacket, 
-                        char *devname, unsigned char enable_IPX, 
-                        unsigned long network_number)
-{
-       int i;
-
-       if( sendpacket[1] == 0x00 && sendpacket[2] == 0x80 &&
-           sendpacket[6] == 0x81 && sendpacket[7] == 0x37) { 
-
-               /* It's an IPX packet */
-               if (!enable_IPX){
-                       /* Return 1 so we don't pass it up the stack. */
-                       //FIXME: Take this out when IPX is fixed
-                       if (net_ratelimit()){ 
-                               printk (KERN_INFO 
-                               "%s: WARNING: Unsupported IPX packet received and dropped\n",
-                                       devname);
-                       }
-                       return 1;
-               }
-       } else {
-               /* It's not IPX so return and pass it up the stack. */
-               return 0;
-       }
-
-       if( sendpacket[24] == 0x90 && sendpacket[25] == 0x04){
-               /* It's IPXWAN */
-
-               if( sendpacket[10] == 0x02 && sendpacket[42] == 0x00){
-
-                       /* It's a timer request packet */
-                       printk(KERN_INFO "%s: Received IPXWAN Timer Request packet\n",
-                                       devname);
-
-                       /* Go through the routing options and answer no to every
-                        * option except Unnumbered RIP/SAP
-                        */
-                       for(i = 49; sendpacket[i] == 0x00; i += 5){
-                               /* 0x02 is the option for Unnumbered RIP/SAP */
-                               if( sendpacket[i + 4] != 0x02){
-                                       sendpacket[i + 1] = 0;
-                               }
-                       }
-
-                       /* Skip over the extended Node ID option */
-                       if( sendpacket[i] == 0x04 ){
-                               i += 8;
-                       }
-
-                       /* We also want to turn off all header compression opt.
-                        */
-                       for(; sendpacket[i] == 0x80 ;){
-                               sendpacket[i + 1] = 0;
-                               i += (sendpacket[i + 2] << 8) + (sendpacket[i + 3]) + 4;
-                       }
-
-                       /* Set the packet type to timer response */
-                       sendpacket[42] = 0x01;
-
-                       printk(KERN_INFO "%s: Sending IPXWAN Timer Response\n",
-                                       devname);
-
-               } else if( sendpacket[42] == 0x02 ){
-
-                       /* This is an information request packet */
-                       printk(KERN_INFO 
-                               "%s: Received IPXWAN Information Request packet\n",
-                                               devname);
-
-                       /* Set the packet type to information response */
-                       sendpacket[42] = 0x03;
-
-                       /* Set the router name */
-                       sendpacket[59] = 'F';
-                       sendpacket[60] = 'P';
-                       sendpacket[61] = 'I';
-                       sendpacket[62] = 'P';
-                       sendpacket[63] = 'E';
-                       sendpacket[64] = '-';
-                       sendpacket[65] = CVHexToAscii(network_number >> 28);
-                       sendpacket[66] = CVHexToAscii((network_number & 0x0F000000)>> 24);
-                       sendpacket[67] = CVHexToAscii((network_number & 0x00F00000)>> 20);
-                       sendpacket[68] = CVHexToAscii((network_number & 0x000F0000)>> 16);
-                       sendpacket[69] = CVHexToAscii((network_number & 0x0000F000)>> 12);
-                       sendpacket[70] = CVHexToAscii((network_number & 0x00000F00)>> 8);
-                       sendpacket[71] = CVHexToAscii((network_number & 0x000000F0)>> 4);
-                       sendpacket[72] = CVHexToAscii(network_number & 0x0000000F);
-                       for(i = 73; i < 107; i+= 1)
-                       {
-                               sendpacket[i] = 0;
-                       }
-
-                       printk(KERN_INFO "%s: Sending IPXWAN Information Response packet\n",
-                                       devname);
-               } else {
-
-                       printk(KERN_INFO "%s: Unknown IPXWAN packet!\n",devname);
-                       return 0;
-               }
-
-               /* Set the WNodeID to our network address */
-               sendpacket[43] = (unsigned char)(network_number >> 24);
-               sendpacket[44] = (unsigned char)((network_number & 0x00FF0000) >> 16);
-               sendpacket[45] = (unsigned char)((network_number & 0x0000FF00) >> 8);
-               sendpacket[46] = (unsigned char)(network_number & 0x000000FF);
-
-               return 1;
-       }
-
-       /* If we get here, it's an IPX-data packet so it'll get passed up the 
-        * stack.
-        * switch the network numbers 
-        */
-       switch_net_numbers(sendpacket, network_number ,1);
-       return 0;
-}
-/*============================================================================
- * process_route
- * 
- * Rationale:
- *     If the interface goes down, or we receive an ARP request,
- *      we have to change the network interface ip addresses.
- *     This cannot be done within the interrupt.
- *
- * Description:
- *
- *     This routine is called as a polling routine to dynamically 
- *     add/delete routes negotiated by inverse ARP.  It is in this 
- *     "task" because we don't want routes to be added while in 
- *      interrupt context.
- *
- * Usage:
- *     This function is called by fr_poll() polling funtion.
- */
-
-static void process_route(struct net_device *dev)
-{
-       fr_channel_t *chan = dev->priv;
-       sdla_t *card = chan->card;
-
-       struct ifreq if_info;
-       struct sockaddr_in *if_data;
-       mm_segment_t fs = get_fs();
-       u32 ip_tmp;
-       int err;
-
-
-       switch(chan->route_flag){
-
-       case ADD_ROUTE:
-                               
-               /* Set remote addresses */
-               memset(&if_info, 0, sizeof(if_info));
-               strcpy(if_info.ifr_name, dev->name);
-
-               set_fs(get_ds());     /* get user space block */ 
-               
-               if_data = (struct sockaddr_in *)&if_info.ifr_dstaddr;
-               if_data->sin_addr.s_addr = chan->ip_remote;
-               if_data->sin_family = AF_INET;
-               err = devinet_ioctl( SIOCSIFDSTADDR, &if_info );
-
-               set_fs(fs);           /* restore old block */
-
-               if (err) {
-                       printk(KERN_INFO 
-                               "%s: Route Add failed.  Error: %d\n", 
-                                       card->devname,err);
-                       printk(KERN_INFO "%s: Address: %u.%u.%u.%u\n",
-                               chan->name, NIPQUAD(chan->ip_remote));
-
-               }else {
-                       printk(KERN_INFO "%s: Route Added Successfully: %u.%u.%u.%u\n",
-                               card->devname,NIPQUAD(chan->ip_remote));
-                       chan->route_flag = ROUTE_ADDED;
-               }
-               break;
-
-       case REMOVE_ROUTE:
-
-               /* Set remote addresses */
-               memset(&if_info, 0, sizeof(if_info));
-               strcpy(if_info.ifr_name, dev->name);
-
-               ip_tmp = get_ip_address(dev,WAN_POINTOPOINT_IP);        
-
-               set_fs(get_ds());     /* get user space block */ 
-               
-               if_data = (struct sockaddr_in *)&if_info.ifr_dstaddr;
-               if_data->sin_addr.s_addr = 0;
-               if_data->sin_family = AF_INET;
-               err = devinet_ioctl( SIOCSIFDSTADDR, &if_info );
-
-               set_fs(fs);    
-               
-               if (err) {
-                       printk(KERN_INFO 
-                               "%s: Deleting of route failed.  Error: %d\n", 
-                                       card->devname,err);
-                       printk(KERN_INFO "%s: Address: %u.%u.%u.%u\n",
-                               dev->name,NIPQUAD(chan->ip_remote) );
-
-               } else {
-                       printk(KERN_INFO "%s: Route Removed Sucessfuly: %u.%u.%u.%u\n", 
-                               card->devname,NIPQUAD(ip_tmp));
-                       chan->route_flag = NO_ROUTE;
-               }
-               break;
-
-       } /* Case Statement */
-
-}
-
-
-
-/****** Frame Relay Firmware-Specific Functions *****************************/
-
-/*============================================================================
- * Read firmware code version.
- * o fill string str with firmware version info. 
- */
-static int fr_read_version (sdla_t* card, char* str)
-{
-       fr_mbox_t* mbox = card->mbox;
-       int retry = MAX_CMD_RETRY;
-       int err;
-
-       do
-       {
-               mbox->cmd.command = FR_READ_CODE_VERSION;
-               mbox->cmd.length = 0;
-               err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-       } while (err && retry-- && fr_event(card, err, mbox));
-       
-       if (!err && str) {
-               int len = mbox->cmd.length;
-               memcpy(str, mbox->data, len);
-               str[len] = '\0';
-       }
-       return err;
-}
-
-/*============================================================================
- * Set global configuration.
- */
-static int fr_configure (sdla_t* card, fr_conf_t *conf)
-{
-       fr_mbox_t* mbox = card->mbox;
-       int retry = MAX_CMD_RETRY;
-       int dlci_num = card->u.f.dlci_num;
-       int err, i;
-
-       do
-       {
-               memcpy(mbox->data, conf, sizeof(fr_conf_t));
-
-               if (dlci_num) for (i = 0; i < dlci_num; ++i)
-                       ((fr_conf_t*)mbox->data)->dlci[i] = 
-                                       card->u.f.node_dlci[i]; 
-               
-               mbox->cmd.command = FR_SET_CONFIG;
-               mbox->cmd.length =
-                       sizeof(fr_conf_t) + dlci_num * sizeof(short);
-
-               err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-       
-       } while (err && retry-- && fr_event(card, err, mbox));
-
-       /*NC Oct 12 2000 */
-       if (err != CMD_OK){
-               printk(KERN_ERR "%s: Frame Relay Configuration Failed: rc=0x%x\n",
-                               card->devname,err);
-       }
-       
-       return err;
-}
-
-/*============================================================================
- * Set DLCI configuration.
- */
-static int fr_dlci_configure (sdla_t* card, fr_dlc_conf_t *conf, unsigned dlci)
-{
-       fr_mbox_t* mbox = card->mbox;
-       int retry = MAX_CMD_RETRY;
-       int err;
-
-       do
-       {
-               memcpy(mbox->data, conf, sizeof(fr_dlc_conf_t));
-               mbox->cmd.dlci = (unsigned short) dlci; 
-               mbox->cmd.command = FR_SET_CONFIG;
-               mbox->cmd.length = sizeof(fr_dlc_conf_t);
-               err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-       } while (err && retry--);
-       
-       return err;
-}
-/*============================================================================
- * Set interrupt mode.
- */
-static int fr_set_intr_mode (sdla_t* card, unsigned mode, unsigned mtu,
-       unsigned short timeout)
-{
-       fr_mbox_t* mbox = card->mbox;
-       fr508_intr_ctl_t* ictl = (void*)mbox->data;
-       int retry = MAX_CMD_RETRY;
-       int err;
-
-       do
-       {
-               memset(ictl, 0, sizeof(fr508_intr_ctl_t));
-               ictl->mode   = mode;
-               ictl->tx_len = mtu;
-               ictl->irq    = card->hw.irq;
-
-               /* indicate timeout on timer */
-               if (mode & 0x20) ictl->timeout = timeout; 
-
-               mbox->cmd.length = sizeof(fr508_intr_ctl_t);
-               mbox->cmd.command = FR_SET_INTR_MODE;
-               err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-
-       } while (err && retry-- && fr_event(card, err, mbox));
-       
-       return err;
-}
-
-/*============================================================================
- * Enable communications.
- */
-static int fr_comm_enable (sdla_t* card)
-{
-       fr_mbox_t* mbox = card->mbox;
-       int retry = MAX_CMD_RETRY;
-       int err;
-
-       do
-       {
-               mbox->cmd.command = FR_COMM_ENABLE;
-               mbox->cmd.length = 0;
-               err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-       } while (err && retry-- && fr_event(card, err, mbox));
-       
-       return err;
-}
-
-/*============================================================================
- * fr_comm_disable 
- *
- * Warning: This functin is called by the shutdown() procedure. It is void
- *          since dev->priv are has already been deallocated and no
- *          error checking is possible using fr_event() function.
- */
-static void fr_comm_disable (sdla_t* card)
-{
-       fr_mbox_t* mbox = card->mbox;
-       int retry = MAX_CMD_RETRY;
-       int err;
-
-       do {
-       mbox->cmd.command = FR_SET_MODEM_STATUS;
-       mbox->cmd.length = 1;
-       mbox->data[0] = 0;
-       err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-       } while (err && retry--);
-       
-       retry = MAX_CMD_RETRY;
-       
-       do
-       {
-               mbox->cmd.command = FR_COMM_DISABLE;
-               mbox->cmd.length = 0;
-               err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-       } while (err && retry--);
-
-       return;
-}
-
-
-
-/*============================================================================
- * Get communications error statistics. 
- */
-static int fr_get_err_stats (sdla_t* card)
-{
-       fr_mbox_t* mbox = card->mbox;
-       int retry = MAX_CMD_RETRY;
-       int err;
-
-
-       do
-       {
-               mbox->cmd.command = FR_READ_ERROR_STATS;
-               mbox->cmd.length = 0;
-               mbox->cmd.dlci = 0;
-               err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-       } while (err && retry-- && fr_event(card, err, mbox));
-
-       if (!err) {
-               fr_comm_stat_t* stats = (void*)mbox->data;
-               card->wandev.stats.rx_over_errors    = stats->rx_overruns;
-               card->wandev.stats.rx_crc_errors     = stats->rx_bad_crc;
-               card->wandev.stats.rx_missed_errors  = stats->rx_aborts;
-               card->wandev.stats.rx_length_errors  = stats->rx_too_long;
-               card->wandev.stats.tx_aborted_errors = stats->tx_aborts;
-       
-       }
-
-       return err;
-}
-
-/*============================================================================
- * Get statistics. 
- */
-static int fr_get_stats (sdla_t* card)
-{
-       fr_mbox_t* mbox = card->mbox;
-       int retry = MAX_CMD_RETRY;
-       int err;
-
-
-       do
-       {
-               mbox->cmd.command = FR_READ_STATISTICS;
-               mbox->cmd.length = 0;
-               mbox->cmd.dlci = 0;
-               err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-       } while (err && retry-- && fr_event(card, err, mbox));
-
-       if (!err) {
-               fr_link_stat_t* stats = (void*)mbox->data;
-               card->wandev.stats.rx_frame_errors = stats->rx_bad_format;
-               card->wandev.stats.rx_dropped =
-                       stats->rx_dropped + stats->rx_dropped2;
-       }
-
-       return err;
-}
-
-/*============================================================================
- * Add DLCI(s) (Access Node only!).
- * This routine will perform the ADD_DLCIs command for the specified DLCI.
- */
-static int fr_add_dlci (sdla_t* card, int dlci)
-{
-       fr_mbox_t* mbox = card->mbox;
-       int retry = MAX_CMD_RETRY;
-       int err;
-
-       do
-       {
-               unsigned short* dlci_list = (void*)mbox->data;
-
-               mbox->cmd.length  = sizeof(short);
-               dlci_list[0] = dlci;
-               mbox->cmd.command = FR_ADD_DLCI;
-               err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-
-       } while (err && retry-- && fr_event(card, err, mbox));
-       
-       return err;
-}
-
-/*============================================================================
- * Activate DLCI(s) (Access Node only!). 
- * This routine will perform the ACTIVATE_DLCIs command with a DLCI number. 
- */
-static int fr_activate_dlci (sdla_t* card, int dlci)
-{
-       fr_mbox_t* mbox = card->mbox;
-       int retry = MAX_CMD_RETRY;
-       int err;
-
-       do
-       {
-               unsigned short* dlci_list = (void*)mbox->data;
-
-               mbox->cmd.length  = sizeof(short);
-               dlci_list[0] = dlci;
-               mbox->cmd.command = FR_ACTIVATE_DLCI;
-               err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-
-       } while (err && retry-- && fr_event(card, err, mbox));
-       
-       return err;
-}
-
-/*============================================================================
- * Delete DLCI(s) (Access Node only!). 
- * This routine will perform the DELETE_DLCIs command with a DLCI number. 
- */
-static int fr_delete_dlci (sdla_t* card, int dlci)
-{
-       fr_mbox_t* mbox = card->mbox;
-       int retry = MAX_CMD_RETRY;
-       int err;
-
-       do
-       {
-               unsigned short* dlci_list = (void*)mbox->data;
-
-               mbox->cmd.length  = sizeof(short);
-               dlci_list[0] = dlci;
-               mbox->cmd.command = FR_DELETE_DLCI;
-               err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-
-       } while (err && retry-- && fr_event(card, err, mbox));
-       
-       return err;
-}
-
-
-
-/*============================================================================
- * Issue in-channel signalling frame. 
- */
-static int fr_issue_isf (sdla_t* card, int isf)
-{
-       fr_mbox_t* mbox = card->mbox;
-       int retry = MAX_CMD_RETRY;
-       int err;
-
-       do
-       {
-               mbox->data[0] = isf;
-               mbox->cmd.length  = 1;
-               mbox->cmd.command = FR_ISSUE_IS_FRAME;
-               err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-       } while (err && retry-- && fr_event(card, err, mbox));
-       
-       return err;
-}
-
-
-static unsigned int fr_send_hdr (sdla_t*card, int dlci, unsigned int offset)
-{
-       struct net_device *dev = find_channel(card,dlci);       
-       fr_channel_t *chan;
-
-       if (!dev || !(chan=dev->priv))
-               return offset;
-       
-       if (chan->fr_header_len){
-               sdla_poke(&card->hw, offset, chan->fr_header, chan->fr_header_len);
-       }
-       
-       return offset+chan->fr_header_len;
-}
-
-/*============================================================================
- * Send a frame on a selected DLCI.  
- */
-static int fr_send_data_header (sdla_t* card, int dlci, unsigned char attr, int len,
-       void *buf, unsigned char hdr_len)
-{
-       fr_mbox_t* mbox = card->mbox + 0x800;
-       int retry = MAX_CMD_RETRY;
-       int err;
-
-       do
-       {
-               mbox->cmd.dlci    = dlci;
-               mbox->cmd.attr    = attr;
-               mbox->cmd.length  = len+hdr_len;
-               mbox->cmd.command = FR_WRITE;
-               err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-       } while (err && retry-- && fr_event(card, err, mbox));
-
-       if (!err) {
-               fr_tx_buf_ctl_t* frbuf;
-                       if(card->hw.type == SDLA_S514)
-                       frbuf = (void*)(*(unsigned long*)mbox->data +
-                               card->hw.dpmbase);
-               else
-                       frbuf = (void*)(*(unsigned long*)mbox->data -
-                               FR_MB_VECTOR + card->hw.dpmbase);
-
-               sdla_poke(&card->hw, fr_send_hdr(card,dlci,frbuf->offset), buf, len);
-               frbuf->flag = 0x01;
-       }
-
-       return err;
-}
-
-static int fr_send (sdla_t* card, int dlci, unsigned char attr, int len,
-       void *buf)
-{
-       fr_mbox_t* mbox = card->mbox + 0x800;
-       int retry = MAX_CMD_RETRY;
-       int err;
-
-       do
-       {
-               mbox->cmd.dlci    = dlci;
-               mbox->cmd.attr    = attr;
-               mbox->cmd.length  = len;
-               mbox->cmd.command = FR_WRITE;
-               err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-       } while (err && retry-- && fr_event(card, err, mbox));
-
-       if (!err) {
-               fr_tx_buf_ctl_t* frbuf;
-                       if(card->hw.type == SDLA_S514)
-                       frbuf = (void*)(*(unsigned long*)mbox->data +
-                               card->hw.dpmbase);
-               else
-                       frbuf = (void*)(*(unsigned long*)mbox->data -
-                               FR_MB_VECTOR + card->hw.dpmbase);
-
-               sdla_poke(&card->hw, frbuf->offset, buf, len);
-               frbuf->flag = 0x01;
-       }
-
-       return err;
-}
-
-
-/****** Firmware Asynchronous Event Handlers ********************************/
-
-/*============================================================================
- * Main asyncronous event/error handler.
- *     This routine is called whenever firmware command returns non-zero
- *     return code.
- *
- * Return zero if previous command has to be cancelled.
- */
-static int fr_event (sdla_t *card, int event, fr_mbox_t* mbox)
-{
-       fr508_flags_t* flags = card->flags;
-       char *ptr = &flags->iflag;
-       int i;
-
-       switch (event) {
-
-               case FRRES_MODEM_FAILURE:
-                       return fr_modem_failure(card, mbox);
-
-               case FRRES_CHANNEL_DOWN: {
-                       struct net_device *dev;
-
-                       /* Remove all routes from associated DLCI's */
-                       for (dev = card->wandev.dev; dev;
-                            dev = *((struct net_device **)dev->priv)) {
-                               fr_channel_t *chan = dev->priv;
-                               if (chan->route_flag == ROUTE_ADDED) {
-                                       chan->route_flag = REMOVE_ROUTE;
-                               }
-
-                               if (chan->inarp == INARP_CONFIGURED) {
-                                       chan->inarp = INARP_REQUEST;
-                               }
-
-                               /* If the link becomes disconnected then,
-                                 * all channels will be disconnected
-                                 * as well.
-                                 */
-                               set_chan_state(dev,WAN_DISCONNECTED);
-                       }
-                               
-                       wanpipe_set_state(card, WAN_DISCONNECTED);
-                       return 1;
-                       }
-
-               case FRRES_CHANNEL_UP: {
-                       struct net_device *dev;
-
-                       /* FIXME: Only startup devices that are on the list */
-                       
-                       for (dev = card->wandev.dev; dev;
-                            dev = *((struct net_device **)dev->priv)) {
-                               
-                               set_chan_state(dev,WAN_CONNECTED);
-                       }
-
-                       wanpipe_set_state(card, WAN_CONNECTED);
-                       return 1;
-                       }
-
-               case FRRES_DLCI_CHANGE:
-                       return fr_dlci_change(card, mbox);
-
-               case FRRES_DLCI_MISMATCH:
-                       printk(KERN_INFO "%s: DLCI list mismatch!\n", 
-                               card->devname);
-                       return 1;
-
-               case CMD_TIMEOUT:
-                       printk(KERN_ERR "%s: command 0x%02X timed out!\n",
-                               card->devname, mbox->cmd.command);
-                       printk(KERN_INFO "%s: ID Bytes = ",card->devname);
-                       for(i = 0; i < 8; i ++)
-                               printk(KERN_INFO "0x%02X ", *(ptr + 0x18 + i));
-                       printk(KERN_INFO "\n"); 
-            
-                       break;
-
-               case FRRES_DLCI_INACTIVE:
-                       break;
-               case FRRES_CIR_OVERFLOW:
-                       break;
-                       
-               case FRRES_BUFFER_OVERFLOW:
-                       break; 
-                       
-               default:
-                       printk(KERN_INFO "%s: command 0x%02X returned 0x%02X!\n"
-                               , card->devname, mbox->cmd.command, event);
-       }
-
-       return 0;
-}
-
-/*============================================================================
- * Handle modem error.
- *
- * Return zero if previous command has to be cancelled.
- */
-static int fr_modem_failure (sdla_t *card, fr_mbox_t* mbox)
-{
-       printk(KERN_INFO "%s: physical link down! (modem error 0x%02X)\n",
-               card->devname, mbox->data[0]);
-
-       switch (mbox->cmd.command){
-               case FR_WRITE:
-       
-               case FR_READ:
-                       return 0;
-       }
-       
-       return 1;
-}
-
-/*============================================================================
- * Handle DLCI status change.
- *
- * Return zero if previous command has to be cancelled.
- */
-static int fr_dlci_change (sdla_t *card, fr_mbox_t* mbox)
-{
-       dlci_status_t* status = (void*)mbox->data;
-       int cnt = mbox->cmd.length / sizeof(dlci_status_t);
-       fr_channel_t *chan;
-       struct net_device* dev2;
-       
-
-       for (; cnt; --cnt, ++status) {
-
-               unsigned short dlci= status->dlci;
-               struct net_device* dev = find_channel(card, dlci);
-               
-               if (dev == NULL){
-                       printk(KERN_INFO 
-                               "%s: CPE contains unconfigured DLCI= %d\n", 
-                               card->devname, dlci);   
-
-                      printk(KERN_INFO
-                                "%s: unconfigured DLCI %d reported by network\n"
-                                , card->devname, dlci);
-               }else{
-                       if (status->state == FR_LINK_INOPER) {
-                               printk(KERN_INFO
-                                       "%s: DLCI %u is inactive!\n",
-                                       card->devname, dlci);
-
-                               if (dev && netif_running(dev))
-                                       set_chan_state(dev, WAN_DISCONNECTED);
-                       }
-       
-                       if (status->state & FR_DLCI_DELETED) {
-
-                               printk(KERN_INFO
-                                       "%s: DLCI %u has been deleted!\n",
-                                       card->devname, dlci);
-
-                               if (dev && netif_running(dev)){
-
-                                       fr_channel_t *chan = dev->priv;
-
-                                       if (chan->route_flag == ROUTE_ADDED) {
-                                               chan->route_flag = REMOVE_ROUTE;
-                                               /* The state change will trigger
-                                                 * the fr polling routine */
-                                       }
-
-                                       if (chan->inarp == INARP_CONFIGURED) {
-                                               chan->inarp = INARP_REQUEST;
-                                       }
-
-                                       set_chan_state(dev, WAN_DISCONNECTED);
-                               }
-
-                       } else if (status->state & FR_DLCI_ACTIVE) {
-
-                               chan = dev->priv;
-                       
-                               /* This flag is used for configuring specific 
-                                  DLCI(s) when they become active.
-                               */ 
-                               chan->dlci_configured = DLCI_CONFIG_PENDING;
-       
-                               set_chan_state(dev, WAN_CONNECTED);
-               
-                       }
-               }
-       }
-       
-       for (dev2 = card->wandev.dev; dev2;
-            dev2 = *((struct net_device **)dev2->priv)){
-               
-               chan = dev2->priv;
-       
-               if (chan->dlci_configured == DLCI_CONFIG_PENDING) {
-                       if (fr_init_dlci(card, chan)){
-                               return 1;
-                       }
-               }
-
-       }
-       return 1;
-}
-
-
-static int fr_init_dlci (sdla_t *card, fr_channel_t *chan)
-{
-       fr_dlc_conf_t cfg;
-       
-       memset(&cfg, 0, sizeof(cfg));
-
-       if ( chan->cir_status == CIR_DISABLED) {
-
-               cfg.cir_fwd = cfg.cir_bwd  = 16;
-               cfg.bc_fwd = cfg.bc_bwd = 16;
-               cfg.conf_flags = 0x0001;        
-
-       }else if (chan->cir_status == CIR_ENABLED) {
-       
-               cfg.cir_fwd = cfg.cir_bwd = chan->cir;
-               cfg.bc_fwd  = cfg.bc_bwd  = chan->bc;
-               cfg.be_fwd  = cfg.be_bwd  = chan->be;
-               cfg.conf_flags = 0x0000;
-       }
-       
-       if (fr_dlci_configure( card, &cfg , chan->dlci)){
-               printk(KERN_INFO 
-                       "%s: DLCI Configure failed for %d\n",
-                               card->devname, chan->dlci);
-               return 1;       
-       }
-       
-       chan->dlci_configured = DLCI_CONFIGURED;
-
-       /* Read the interface byte mapping into the channel 
-        * structure.
-        */
-       read_DLCI_IB_mapping( card, chan );
-
-       return 0;
-}
-/******* Miscellaneous ******************************************************/
-
-/*============================================================================
- * Update channel state. 
- */
-static int update_chan_state(struct net_device* dev)
-{
-       fr_channel_t* chan = dev->priv;
-       sdla_t* card = chan->card;
-       fr_mbox_t* mbox = card->mbox;
-       int retry = MAX_CMD_RETRY;
-       int err;
-
-       do
-       {
-               mbox->cmd.command = FR_LIST_ACTIVE_DLCI;
-               mbox->cmd.length = 0;
-               err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-       } while (err && retry-- && fr_event(card, err, mbox));
-
-       if (!err) {
-               
-               unsigned short* list = (void*)mbox->data;
-               int cnt = mbox->cmd.length / sizeof(short);
-               
-               err=1;
-               
-               for (; cnt; --cnt, ++list) {
-
-                       if (*list == chan->dlci) {
-                               set_chan_state(dev, WAN_CONNECTED);
-
-
-                               /* May 23 2000. NC
-                                * When a dlci is added or restarted,
-                                 * the dlci_int_interface pointer must
-                                * be reinitialized.  */
-                               if (!chan->dlci_int_interface){
-                                       err=fr_init_dlci (card,chan);
-                               }
-                               break;
-                       }
-               }
-       }
-
-       return err;
-}
-
-/*============================================================================
- * Set channel state.
- */
-static void set_chan_state(struct net_device* dev, int state)
-{
-       fr_channel_t* chan = dev->priv;
-       sdla_t* card = chan->card;
-
-       if (chan->common.state != state) {
-
-               switch (state) {
-
-                       case WAN_CONNECTED:
-                               printk(KERN_INFO
-                                       "%s: Interface %s: DLCI %d connected\n",
-                                       card->devname, dev->name, chan->dlci);
-
-                               /* If the interface was previoulsy down,
-                                 * bring it up, since the channel is active */
-
-                               trigger_fr_poll (dev);
-                               trigger_fr_arp  (dev);
-                               break;
-
-                       case WAN_CONNECTING:
-                               printk(KERN_INFO 
-                                     "%s: Interface %s: DLCI %d connecting\n",
-                                       card->devname, dev->name, chan->dlci);
-                               break;
-
-                       case WAN_DISCONNECTED:
-                               printk (KERN_INFO 
-                                   "%s: Interface %s: DLCI %d disconnected!\n",
-                                       card->devname, dev->name, chan->dlci);
-                       
-                               /* If the interface is up, bring it down,
-                                 * since the channel is now disconnected */
-                               trigger_fr_poll (dev);
-                               break;
-               }
-
-               chan->common.state = state;
-       }
-
-       chan->state_tick = jiffies;
-}
-
-/*============================================================================
- * Find network device by its channel number.
- *
- * We need this critical flag because we change
- * the dlci_to_dev_map outside the interrupt.
- *
- * NOTE: del_if() functions updates this array, it uses
- *       the spin locks to avoid corruption.
- */
-static struct net_device* find_channel(sdla_t* card, unsigned dlci)
-{
-       if(dlci > HIGHEST_VALID_DLCI)
-               return NULL;
-
-       return(card->u.f.dlci_to_dev_map[dlci]);
-}
-
-/*============================================================================
- * Check to see if a frame can be sent. If no transmit buffers available,
- * enable transmit interrupts.
- *
- * Return:     1 - Tx buffer(s) available
- *             0 - no buffers available
- */
-static int is_tx_ready (sdla_t* card, fr_channel_t* chan)
-{
-       unsigned char sb;
-
-        if(card->hw.type == SDLA_S514)
-               return 1;
-
-       sb = inb(card->hw.port);
-       if (sb & 0x02) 
-               return 1;
-
-       return 0;
-}
-
-/*============================================================================
- * Convert decimal string to unsigned integer.
- * If len != 0 then only 'len' characters of the string are converted.
- */
-static unsigned int dec_to_uint (unsigned char* str, int len)
-{
-       unsigned val;
-
-       if (!len) 
-               len = strlen(str);
-
-       for (val = 0; len && isdigit(*str); ++str, --len)
-               val = (val * 10) + (*str - (unsigned)'0');
-
-       return val;
-}
-
-
-
-/*=============================================================================
- * Store a UDP management packet for later processing.
- */
-
-static int store_udp_mgmt_pkt(int udp_type, char udp_pkt_src, sdla_t* card,
-                                struct sk_buff *skb, int dlci)
-{
-        int udp_pkt_stored = 0;
-       
-       struct net_device *dev = find_channel(card, dlci);
-       fr_channel_t *chan;
-       
-       if (!dev || !(chan=dev->priv))
-               return 1;
-       
-        if(!card->u.f.udp_pkt_lgth && (skb->len <= MAX_LGTH_UDP_MGNT_PKT)){
-                card->u.f.udp_pkt_lgth = skb->len + chan->fr_header_len;
-                card->u.f.udp_type = udp_type;
-                card->u.f.udp_pkt_src = udp_pkt_src;
-                card->u.f.udp_dlci = dlci;
-                memcpy(card->u.f.udp_pkt_data, skb->data, skb->len);
-                card->u.f.timer_int_enabled |= TMR_INT_ENABLED_UDP;
-                udp_pkt_stored = 1;
-
-        }else{
-                printk(KERN_INFO "ERROR: UDP packet not stored for DLCI %d\n", 
-                                                       dlci);
-       }
-
-        if(udp_pkt_src == UDP_PKT_FRM_STACK){
-                dev_kfree_skb_any(skb);
-       }else{
-                dev_kfree_skb_any(skb);
-       }
-               
-        return(udp_pkt_stored);
-}
-
-
-/*==============================================================================
- * Process UDP call of type FPIPE8ND
- */
-static int process_udp_mgmt_pkt(sdla_t* card)
-{
-
-       int c_retry = MAX_CMD_RETRY;
-       unsigned char *buf;
-       unsigned char frames;
-       unsigned int len;
-       unsigned short buffer_length;
-       struct sk_buff *new_skb;
-       fr_mbox_t* mbox = card->mbox;
-       int err;
-       struct timeval tv;
-       int udp_mgmt_req_valid = 1;
-        struct net_device* dev;
-        fr_channel_t* chan;
-        fr_udp_pkt_t *fr_udp_pkt;
-       unsigned short num_trc_els;
-       fr_trc_el_t* ptr_trc_el;
-       fr_trc_el_t trc_el;
-       fpipemon_trc_t* fpipemon_trc;
-
-       char udp_pkt_src = card->u.f.udp_pkt_src; 
-       int dlci = card->u.f.udp_dlci;
-
-       /* Find network interface for this packet */
-       dev = find_channel(card, dlci);
-       if (!dev){
-               card->u.f.udp_pkt_lgth = 0;
-               return 1;
-       }
-        if ((chan = dev->priv) == NULL){
-               card->u.f.udp_pkt_lgth = 0;
-               return 1;
-       }
-
-       /* If the UDP packet is from the network, we are going to have to 
-          transmit a response. Before doing so, we must check to see that
-          we are not currently transmitting a frame (in 'if_send()') and
-          that we are not already in a 'delayed transmit' state.
-       */
-       if(udp_pkt_src == UDP_PKT_FRM_NETWORK) {
-               if (check_tx_status(card,dev)){
-                       card->u.f.udp_pkt_lgth = 0;
-                       return 1;
-               }
-        }
-
-        fr_udp_pkt = (fr_udp_pkt_t *)card->u.f.udp_pkt_data;
-
-       if(udp_pkt_src == UDP_PKT_FRM_NETWORK) {
-       
-               switch(fr_udp_pkt->cblock.command) {
-
-                       case FR_READ_MODEM_STATUS:
-                       case FR_READ_STATUS:
-                       case FPIPE_ROUTER_UP_TIME:
-                       case FR_READ_ERROR_STATS:
-                       case FPIPE_DRIVER_STAT_GEN:
-                       case FR_READ_STATISTICS:
-                       case FR_READ_ADD_DLC_STATS:
-                       case FR_READ_CONFIG:
-                       case FR_READ_CODE_VERSION:
-                               udp_mgmt_req_valid = 1;
-                               break;
-                       default:
-                               udp_mgmt_req_valid = 0;
-                               break;
-               }
-       }
-
-       if(!udp_mgmt_req_valid) {
-               /* set length to 0 */
-               fr_udp_pkt->cblock.length = 0;
-               /* set return code */
-               fr_udp_pkt->cblock.result = 0xCD; 
-               
-               chan->drvstats_gen.UDP_PIPE_mgmt_direction_err ++;
-
-               if (net_ratelimit()){   
-                       printk(KERN_INFO 
-                       "%s: Warning, Illegal UDP command attempted from network: %x\n",
-                       card->devname,fr_udp_pkt->cblock.command);
-               }
-               
-       } else {   
-           
-               switch(fr_udp_pkt->cblock.command) {
-
-               case FPIPE_ENABLE_TRACING:
-                       if(!card->TracingEnabled) {
-                               do {
-                                               mbox->cmd.command = FR_SET_TRACE_CONFIG;
-                                               mbox->cmd.length = 1;
-                                       mbox->cmd.dlci = 0x00;
-                                       mbox->data[0] = fr_udp_pkt->data[0] | 
-                                               RESET_TRC;
-                                       err = sdla_exec(mbox) ? 
-                                                       mbox->cmd.result : CMD_TIMEOUT;
-                                       } while (err && c_retry-- && fr_event(card, err,
-                                        mbox));
-
-                               if(err) {
-                                       card->TracingEnabled = 0;
-                                       /* set the return code */
-                                       fr_udp_pkt->cblock.result =
-                                               mbox->cmd.result;
-                                       mbox->cmd.length = 0;
-                                       break;
-                               }
-
-                               sdla_peek(&card->hw, NO_TRC_ELEMENTS_OFF,
-                                               &num_trc_els, 2);
-                               sdla_peek(&card->hw, BASE_TRC_ELEMENTS_OFF,
-                                               &card->u.f.trc_el_base, 4);
-                               card->u.f.curr_trc_el = card->u.f.trc_el_base;
-                               card->u.f.trc_el_last = card->u.f.curr_trc_el +
-                                                       ((num_trc_els - 1) * 
-                                                       sizeof(fr_trc_el_t));
-   
-                               /* Calculate the maximum trace data area in */
-                               /* the UDP packet */
-                               card->u.f.trc_bfr_space=(MAX_LGTH_UDP_MGNT_PKT -
-                                       //sizeof(fr_encap_hdr_t) -
-                                       sizeof(ip_pkt_t) -
-                                       sizeof(udp_pkt_t) -
-                                       sizeof(wp_mgmt_t) -
-                                       sizeof(cblock_t));
-
-                               /* set return code */
-                               fr_udp_pkt->cblock.result = 0;
-                       
-                       } else {
-                               /* set return code to line trace already 
-                                  enabled */
-                               fr_udp_pkt->cblock.result = 1;
-                       }
-
-                       mbox->cmd.length = 0;
-                       card->TracingEnabled = 1;
-                       break;
-
-
-                case FPIPE_DISABLE_TRACING:
-                       if(card->TracingEnabled) {
-                       
-                               do {
-                                       mbox->cmd.command = FR_SET_TRACE_CONFIG;
-                                       mbox->cmd.length = 1;
-                                       mbox->cmd.dlci = 0x00;
-                                       mbox->data[0] = ~ACTIVATE_TRC;
-                                       err = sdla_exec(mbox) ? 
-                                                       mbox->cmd.result : CMD_TIMEOUT;
-                               } while (err && c_retry-- && fr_event(card, err, mbox));
-                       }
-
-                       /* set return code */
-                       fr_udp_pkt->cblock.result = 0;
-                       mbox->cmd.length = 0;
-                       card->TracingEnabled = 0;
-                       break;
-
-                case FPIPE_GET_TRACE_INFO:
-
-                       /* Line trace cannot be performed on the 502 */
-                        if(!card->TracingEnabled) {
-                                /* set return code */
-                                fr_udp_pkt->cblock.result = 1;
-                                mbox->cmd.length = 0;
-                                break;
-                        }
-
-                       ptr_trc_el = (void *)card->u.f.curr_trc_el;
-
-                        buffer_length = 0;
-                       fr_udp_pkt->data[0x00] = 0x00;
-
-                        for(frames = 0; frames < MAX_FRMS_TRACED; frames ++) {
-
-                                sdla_peek(&card->hw, (unsigned long)ptr_trc_el,
-                                         (void *)&trc_el.flag,
-                                         sizeof(fr_trc_el_t));
-                                if(trc_el.flag == 0x00) {
-                                        break;
-                               }
-                                if((card->u.f.trc_bfr_space - buffer_length)
-                                        < sizeof(fpipemon_trc_hdr_t)) { 
-                                        fr_udp_pkt->data[0x00] |= MORE_TRC_DATA;
-                                        break;
-                                }
-
-                               fpipemon_trc = 
-                                       (fpipemon_trc_t *)&fr_udp_pkt->data[buffer_length]; 
-                               fpipemon_trc->fpipemon_trc_hdr.status =
-                                       trc_el.attr;
-                               fpipemon_trc->fpipemon_trc_hdr.tmstamp =
-                                       trc_el.tmstamp;
-                               fpipemon_trc->fpipemon_trc_hdr.length = 
-                                       trc_el.length;
-
-                                if(!trc_el.offset || !trc_el.length) {
-
-                                       fpipemon_trc->fpipemon_trc_hdr.data_passed = 0x00;
-
-                               }else if((trc_el.length + sizeof(fpipemon_trc_hdr_t) + 1) >
-                                       (card->u.f.trc_bfr_space - buffer_length)){
-
-                                        fpipemon_trc->fpipemon_trc_hdr.data_passed = 0x00;
-                                       fr_udp_pkt->data[0x00] |= MORE_TRC_DATA;
-                                }else {
-                                        fpipemon_trc->fpipemon_trc_hdr.data_passed = 0x01;
-                                        sdla_peek(&card->hw, trc_el.offset,
-                                                 fpipemon_trc->data,
-                                                 trc_el.length);
-                               }                       
-
-                                trc_el.flag = 0x00;
-                                sdla_poke(&card->hw, (unsigned long)ptr_trc_el,
-                                         &trc_el.flag, 1);
-                               
-                               ptr_trc_el ++;
-                               if((void *)ptr_trc_el > card->u.f.trc_el_last)
-                                       ptr_trc_el = (void*)card->u.f.trc_el_base;
-
-                               buffer_length += sizeof(fpipemon_trc_hdr_t);
-                                       if(fpipemon_trc->fpipemon_trc_hdr.data_passed) {
-                                               buffer_length += trc_el.length;
-                                       }
-
-                               if(fr_udp_pkt->data[0x00] & MORE_TRC_DATA) {
-                                       break;
-                               }
-                        }
-                      
-                       if(frames == MAX_FRMS_TRACED) {
-                               fr_udp_pkt->data[0x00] |= MORE_TRC_DATA;
-                       }
-             
-                       card->u.f.curr_trc_el = (void *)ptr_trc_el;
-
-                        /* set the total number of frames passed */
-                       fr_udp_pkt->data[0x00] |=
-                               ((frames << 1) & (MAX_FRMS_TRACED << 1));
-
-                        /* set the data length and return code */
-                       fr_udp_pkt->cblock.length = mbox->cmd.length = buffer_length;
-                        fr_udp_pkt->cblock.result = 0;
-                        break;
-
-                case FPIPE_FT1_READ_STATUS:
-                       sdla_peek(&card->hw, 0xF020,
-                               &fr_udp_pkt->data[0x00] , 2);
-                       fr_udp_pkt->cblock.length = mbox->cmd.length = 2;
-                       fr_udp_pkt->cblock.result = 0;
-                       break;
-
-               case FPIPE_FLUSH_DRIVER_STATS:
-                       init_chan_statistics(chan);
-                       init_global_statistics(card);
-                       mbox->cmd.length = 0;
-                       break;
-               
-               case FPIPE_ROUTER_UP_TIME:
-                       do_gettimeofday(&tv);
-                       chan->router_up_time = tv.tv_sec - 
-                                               chan->router_start_time;
-                       *(unsigned long *)&fr_udp_pkt->data =
-                               chan->router_up_time;   
-                       mbox->cmd.length = fr_udp_pkt->cblock.length = 4;
-                       fr_udp_pkt->cblock.result = 0;
-                       break;
-
-               case FPIPE_DRIVER_STAT_IFSEND:
-                       memcpy(fr_udp_pkt->data,
-                               &chan->drvstats_if_send.if_send_entry,
-                               sizeof(if_send_stat_t));
-                       mbox->cmd.length = fr_udp_pkt->cblock.length =sizeof(if_send_stat_t);   
-                       fr_udp_pkt->cblock.result = 0;
-                       break;
-       
-               case FPIPE_DRIVER_STAT_INTR:
-
-                       memcpy(fr_udp_pkt->data,
-                                &card->statistics.isr_entry,
-                                sizeof(global_stats_t));
-
-                        memcpy(&fr_udp_pkt->data[sizeof(global_stats_t)],
-                                &chan->drvstats_rx_intr.rx_intr_no_socket,
-                                sizeof(rx_intr_stat_t));
-
-                       mbox->cmd.length = fr_udp_pkt->cblock.length = 
-                                       sizeof(global_stats_t) +
-                                       sizeof(rx_intr_stat_t);
-                       fr_udp_pkt->cblock.result = 0;
-                       break;
-
-               case FPIPE_DRIVER_STAT_GEN:
-                        memcpy(fr_udp_pkt->data,
-                                &chan->drvstats_gen.UDP_PIPE_mgmt_kmalloc_err,
-                                sizeof(pipe_mgmt_stat_t));
-
-                        memcpy(&fr_udp_pkt->data[sizeof(pipe_mgmt_stat_t)],
-                               &card->statistics, sizeof(global_stats_t));
-
-                        mbox->cmd.length = fr_udp_pkt->cblock.length = sizeof(global_stats_t)+
-                                                     sizeof(rx_intr_stat_t);
-                       fr_udp_pkt->cblock.result = 0;
-                        break;
-
-
-               case FR_FT1_STATUS_CTRL:
-                       if(fr_udp_pkt->data[0] == 1) {
-                               if(rCount++ != 0 ){
-                                       fr_udp_pkt->cblock.result = 0;
-                                       mbox->cmd.length = 1;
-                                       break;
-                               } 
-                       }
-           
-                       /* Disable FT1 MONITOR STATUS */
-                        if(fr_udp_pkt->data[0] == 0) {
-                               if( --rCount != 0) {
-                                        fr_udp_pkt->cblock.result = 0;
-                                       mbox->cmd.length = 1;
-                                       break;
-                               } 
-                       }  
-                       goto udp_mgmt_dflt;
-
-                       
-               default:
-udp_mgmt_dflt:
-                       do {
-                               memcpy(&mbox->cmd,
-                                       &fr_udp_pkt->cblock.command,
-                                       sizeof(fr_cmd_t));
-                               if(mbox->cmd.length) {
-                                       memcpy(&mbox->data,
-                                               (char *)fr_udp_pkt->data,
-                                               mbox->cmd.length);
-                               }
-                               
-                               err = sdla_exec(mbox) ? mbox->cmd.result : 
-                                       CMD_TIMEOUT;
-                       } while (err && c_retry-- && fr_event(card, err, mbox));
-
-                       if(!err)
-                               chan->drvstats_gen.
-                                       UDP_PIPE_mgmt_adptr_cmnd_OK ++;
-                       else
-                                chan->drvstats_gen.
-                                       UDP_PIPE_mgmt_adptr_cmnd_timeout ++;
-
-                               /* copy the result back to our buffer */
-                       memcpy(&fr_udp_pkt->cblock.command,
-                               &mbox->cmd, sizeof(fr_cmd_t));
-
-                               if(mbox->cmd.length) {
-                                       memcpy(&fr_udp_pkt->data,
-                                       &mbox->data, mbox->cmd.length);
-                       }
-               } 
-        }
-   
-        /* Fill UDP TTL */
-        fr_udp_pkt->ip_pkt.ttl = card->wandev.ttl;
-        len = reply_udp(card->u.f.udp_pkt_data, mbox->cmd.length);
-
-        if(udp_pkt_src == UDP_PKT_FRM_NETWORK) {
-
-               chan->fr_header_len=2;
-               chan->fr_header[0]=Q922_UI;
-               chan->fr_header[1]=NLPID_IP;
-                       
-               err = fr_send_data_header(card, dlci, 0, len, 
-                       card->u.f.udp_pkt_data,chan->fr_header_len);
-               if (err){ 
-                       chan->drvstats_gen.UDP_PIPE_mgmt_adptr_send_passed ++;
-               }else{
-                       chan->drvstats_gen.UDP_PIPE_mgmt_adptr_send_failed ++;
-               }
-               
-       } else {
-               /* Allocate socket buffer */
-               if((new_skb = dev_alloc_skb(len)) != NULL) {
-
-                       /* copy data into new_skb */
-                       buf = skb_put(new_skb, len);
-                       memcpy(buf, card->u.f.udp_pkt_data, len);
-        
-                       chan->drvstats_gen.
-                               UDP_PIPE_mgmt_passed_to_stack ++;
-                       new_skb->dev = dev;
-                       new_skb->protocol = htons(ETH_P_IP);
-                       new_skb->mac.raw = new_skb->data;
-                       netif_rx(new_skb);
-               
-               } else {
-                       chan->drvstats_gen.UDP_PIPE_mgmt_no_socket ++;
-                       printk(KERN_INFO 
-                       "%s: UDP mgmt cmnd, no socket buffers available!\n", 
-                       card->devname);
-               }
-        }
-
-       card->u.f.udp_pkt_lgth = 0;
-
-       return 1;
-}
-
-/*==============================================================================
- * Send Inverse ARP Request
- */
-
-int send_inarp_request(sdla_t *card, struct net_device *dev)
-{
-       int err=0;
-
-       arphdr_1490_t *ArpPacket;
-       arphdr_fr_t *arphdr;
-       fr_channel_t *chan = dev->priv;
-       struct in_device *in_dev;
-
-       in_dev = dev->ip_ptr;
-
-       if(in_dev != NULL ) {   
-
-               ArpPacket = kmalloc(sizeof(arphdr_1490_t) + sizeof(arphdr_fr_t), GFP_ATOMIC);
-               /* SNAP Header indicating ARP */
-               ArpPacket->control      = 0x03;
-               ArpPacket->pad          = 0x00;
-               ArpPacket->NLPID        = 0x80;
-               ArpPacket->OUI[0]       = 0;
-               ArpPacket->OUI[1]       = 0;
-               ArpPacket->OUI[2]       = 0;
-               ArpPacket->PID          = 0x0608;
-
-               arphdr = (arphdr_fr_t *)(ArpPacket + 1); // Go to ARP Packet
-
-               /* InARP request */             
-               arphdr->ar_hrd = 0x0F00;        /* Frame Relay HW type */
-               arphdr->ar_pro = 0x0008;        /* IP Protocol         */
-               arphdr->ar_hln = 2;             /* HW addr length      */
-               arphdr->ar_pln = 4;             /* IP addr length      */
-               arphdr->ar_op = htons(0x08);    /* InARP Request       */
-               arphdr->ar_sha = 0;             /* src HW DLCI - Doesn't matter */
-               if(in_dev->ifa_list != NULL)
-                       arphdr->ar_sip = in_dev->ifa_list->ifa_local;  /* Local Address       */else
-                       arphdr->ar_sip = 0;
-               arphdr->ar_tha = 0;             /* dst HW DLCI - Doesn't matter */
-               arphdr->ar_tip = 0;             /* Remote Address -- what we want */
-
-               err = fr_send(card, chan->dlci, 0, sizeof(arphdr_1490_t) + sizeof(arphdr_fr_t),
-                                       (void *)ArpPacket);
-
-               if (!err){
-                       printk(KERN_INFO "\n%s: Sending InARP request on DLCI %d.\n", 
-                               card->devname, chan->dlci);
-                       clear_bit(ARP_CRIT,&card->wandev.critical);
-               }
-
-               kfree(ArpPacket);
-       }else{
-               printk(KERN_INFO "%s: INARP ERROR: %s doesn't have a local IP address!\n",
-                               card->devname,dev->name);
-               return 1;
-       }
-
-       return 0;
-}
-       
-
-/*==============================================================================
- * Check packet for ARP Type
- */
-
-int is_arp(void *buf)
-{
-       arphdr_1490_t *arphdr = (arphdr_1490_t *)buf;
-       
-       if (arphdr->pad   == 0x00  &&
-           arphdr->NLPID == 0x80  &&
-           arphdr->PID   == 0x0608) 
-               return 1;
-       else return 0;
-}
-
-/*==============================================================================
- * Process ARP Packet Type
- */
-
-int process_ARP(arphdr_1490_t *ArpPacket, sdla_t *card, struct net_device* dev)
-{
-
-
-       arphdr_fr_t *arphdr = (arphdr_fr_t *)(ArpPacket + 1); /* Skip header */
-       fr_rx_buf_ctl_t* frbuf = card->rxmb;
-       struct in_device *in_dev;
-       fr_channel_t *chan = dev->priv;         
-       
-       /* Before we transmit ARP packet, we must check 
-        * to see that we are not currently transmitting a 
-        * frame (in 'if_send()') and that we are not 
-        * already in a 'delayed transmit' state. */
-       if (check_tx_status(card,dev)){
-               if (net_ratelimit()){   
-                       printk(KERN_INFO "%s: Disabling comminication to process ARP\n",
-                                       card->devname);
-               }
-               set_bit(ARP_CRIT,&card->wandev.critical);
-               return 0;
-       }
-
-       in_dev = dev->ip_ptr;
-
-       /* Check that IP addresses exist for our network address */
-       if (in_dev == NULL || in_dev->ifa_list == NULL) 
-               return -1;
-
-       switch (ntohs(arphdr->ar_op)) {
-
-       case 0x08:  // Inverse ARP request  -- Send Reply, add route.
-                       
-               /* Check for valid Address */
-               printk(KERN_INFO "%s: Recvd PtP addr -InArp Req: %u.%u.%u.%u\n", 
-                       card->devname, NIPQUAD(arphdr->ar_sip));
-
-
-               /* Check that the network address is the same as ours, only
-                 * if the netowrk mask is not 255.255.255.255. Otherwise
-                 * this check would not make sense */
-
-               if (in_dev->ifa_list->ifa_mask != 0xFFFFFFFF && 
-                   (in_dev->ifa_list->ifa_mask & arphdr->ar_sip) != 
-                   (in_dev->ifa_list->ifa_mask & in_dev->ifa_list->ifa_local)){
-                       printk(KERN_INFO 
-                               "%s: Invalid PtP address. %u.%u.%u.%u  InARP ignored.\n", 
-                                       card->devname,NIPQUAD(arphdr->ar_sip));
-
-                       printk(KERN_INFO "%s: mask %u.%u.%u.%u\n", 
-                               card->devname, NIPQUAD(in_dev->ifa_list->ifa_mask));
-                               printk(KERN_INFO "%s: local %u.%u.%u.%u\n", 
-                               card->devname,NIPQUAD(in_dev->ifa_list->ifa_local));
-                       return -1;
-               }
-
-               if (in_dev->ifa_list->ifa_local == arphdr->ar_sip){
-                       printk(KERN_INFO 
-                               "%s: Local addr = PtP addr.  InARP ignored.\n", 
-                                       card->devname);
-                       return -1;
-               }
-       
-               arphdr->ar_op = htons(0x09);    /* InARP Reply */
-
-               /* Set addresses */
-               arphdr->ar_tip = arphdr->ar_sip;
-               arphdr->ar_sip = in_dev->ifa_list->ifa_local;
-
-               chan->ip_local = in_dev->ifa_list->ifa_local;
-               chan->ip_remote = arphdr->ar_sip;
-
-               fr_send(card, frbuf->dlci, 0, frbuf->length, (void *)ArpPacket);
-
-               if (test_bit(ARP_CRIT,&card->wandev.critical)){
-                       if (net_ratelimit()){   
-                               printk(KERN_INFO "%s: ARP Processed Enabling Communication!\n",
-                                       card->devname);
-                       }
-               }
-               clear_bit(ARP_CRIT,&card->wandev.critical);
-               
-               chan->ip_local = in_dev->ifa_list->ifa_local;
-               chan->ip_remote = arphdr->ar_sip;
-
-               /* Add Route Flag */
-               /* The route will be added in the polling routine so
-                  that it is not interrupt context. */
-
-               chan->route_flag = ADD_ROUTE;
-               trigger_fr_poll (dev);
-
-               break;
-
-       case 0x09:  // Inverse ARP reply
-
-               /* Check for valid Address */
-               printk(KERN_INFO "%s: Recvd PtP addr %u.%u.%u.%u -InArp Reply\n", 
-                               card->devname, NIPQUAD(arphdr->ar_sip));
-
-
-               /* Compare network addresses, only if network mask
-                 * is not 255.255.255.255  It would not make sense
-                 * to perform this test if the mask was all 1's */
-
-               if (in_dev->ifa_list->ifa_mask != 0xffffffff &&
-                   (in_dev->ifa_list->ifa_mask & arphdr->ar_sip) != 
-                       (in_dev->ifa_list->ifa_mask & in_dev->ifa_list->ifa_local)) {
-
-                       printk(KERN_INFO "%s: Invalid PtP address.  InARP ignored.\n", 
-                                       card->devname);
-                       return -1;
-               }
-
-               /* Make sure that the received IP address is not
-                 * the same as our own local address */
-               if (in_dev->ifa_list->ifa_local == arphdr->ar_sip) {
-                       printk(KERN_INFO "%s: Local addr = PtP addr.  InARP ignored.\n", 
-                               card->devname);
-                       return -1;
-               }                       
-
-               chan->ip_local  = in_dev->ifa_list->ifa_local;
-               chan->ip_remote = arphdr->ar_sip;
-
-               /* Add Route Flag */
-               /* The route will be added in the polling routine so
-                  that it is not interrupt context. */
-
-               chan->route_flag = ADD_ROUTE;
-               chan->inarp = INARP_CONFIGURED;
-               trigger_fr_poll(dev);
-               
-               break;
-       default:
-               break; // ARP's and RARP's -- Shouldn't happen.
-       }
-
-       return 0;       
-}
-
-
-/*============================================================
- * trigger_fr_arp
- *
- * Description:
- *     Add an fr_arp() task into a arp
- *      timer handler for a specific dlci/interface.  
- *      This will kick the fr_arp() routine 
- *      within the specified time interval. 
- *
- * Usage:
- *     This timer is used to send ARP requests at
- *      certain time intervals. 
- *     Called by an interrupt to request an action
- *      at a later date.
- */    
-
-static void trigger_fr_arp(struct net_device *dev)
-{
-       fr_channel_t* chan = dev->priv;
-
-       mod_timer(&chan->fr_arp_timer, jiffies + chan->inarp_interval * HZ);
-       return;
-}
-
-
-
-/*==============================================================================
- * ARP Request Action
- *
- *     This funciton is called by timer interrupt to send an arp request
- *      to the remote end.
- */
-
-static void fr_arp (unsigned long data)
-{
-       struct net_device *dev = (struct net_device *)data;
-       fr_channel_t *chan = dev->priv;
-       volatile sdla_t *card = chan->card;
-       fr508_flags_t* flags = card->flags;
-
-       /* Send ARP packets for all devs' until
-         * ARP state changes to CONFIGURED */
-
-       if (chan->inarp == INARP_REQUEST &&
-           chan->common.state == WAN_CONNECTED && 
-           card->wandev.state == WAN_CONNECTED){
-               set_bit(0,&chan->inarp_ready);
-               card->u.f.timer_int_enabled |= TMR_INT_ENABLED_ARP;
-               flags->imask |= FR_INTR_TIMER;  
-       }
-       return;
-}
-       
-
-/*==============================================================================
- * Perform the Interrupt Test by running the READ_CODE_VERSION command MAX_INTR_
- * TEST_COUNTER times.
- */
-static int intr_test( sdla_t* card )
-{
-       fr_mbox_t* mb = card->mbox;
-       int err,i;
-
-        err = fr_set_intr_mode(card, FR_INTR_READY, card->wandev.mtu, 0 );
-       
-       if (err == CMD_OK) {
-
-               for ( i = 0; i < MAX_INTR_TEST_COUNTER; i++ ) {
-                       /* Run command READ_CODE_VERSION */
-                       mb->cmd.length  = 0;
-                       mb->cmd.command = FR_READ_CODE_VERSION;
-                       err = sdla_exec(mb) ? mb->cmd.result : CMD_TIMEOUT;
-                       if (err != CMD_OK) 
-                               fr_event(card, err, mb);
-               }
-       
-       } else {
-               return err;     
-       }
-
-       err = fr_set_intr_mode( card, 0, card->wandev.mtu, 0 );
-
-       if( err != CMD_OK ) 
-               return err;
-
-       return 0;
-}
-
-/*==============================================================================
- * Determine what type of UDP call it is. FPIPE8ND ?
- */
-static int udp_pkt_type( struct sk_buff *skb, sdla_t* card )
-{
-       fr_udp_pkt_t *fr_udp_pkt = (fr_udp_pkt_t *)skb->data;
-
-       /* Quick HACK */
-       
-       
-        if((fr_udp_pkt->ip_pkt.protocol == UDPMGMT_UDP_PROTOCOL) &&
-               (fr_udp_pkt->ip_pkt.ver_inet_hdr_length == 0x45) &&
-               (fr_udp_pkt->udp_pkt.udp_dst_port == 
-               ntohs(card->wandev.udp_port)) &&
-               (fr_udp_pkt->wp_mgmt.request_reply == 
-               UDPMGMT_REQUEST)) {
-                        if(!strncmp(fr_udp_pkt->wp_mgmt.signature,
-                                UDPMGMT_FPIPE_SIGNATURE, 8)){
-                                return UDP_FPIPE_TYPE;
-                       }
-       }
-        return UDP_INVALID_TYPE;
-}
-
-
-/*==============================================================================
- * Initializes the Statistics values in the fr_channel structure.
- */
-void init_chan_statistics( fr_channel_t* chan)
-{
-        memset(&chan->drvstats_if_send.if_send_entry, 0,
-               sizeof(if_send_stat_t));
-        memset(&chan->drvstats_rx_intr.rx_intr_no_socket, 0,
-                sizeof(rx_intr_stat_t));
-        memset(&chan->drvstats_gen.UDP_PIPE_mgmt_kmalloc_err, 0,
-                sizeof(pipe_mgmt_stat_t));
-}
-       
-/*==============================================================================
- * Initializes the Statistics values in the Sdla_t structure.
- */
-void init_global_statistics( sdla_t* card )
-{
-       /* Intialize global statistics for a card */
-        memset(&card->statistics.isr_entry, 0, sizeof(global_stats_t));
-}
-
-static void read_DLCI_IB_mapping( sdla_t* card, fr_channel_t* chan )
-{
-       fr_mbox_t* mbox = card->mbox;
-       int retry = MAX_CMD_RETRY;      
-       dlci_IB_mapping_t* result; 
-       int err, counter, found;        
-
-       do {
-               mbox->cmd.command = FR_READ_DLCI_IB_MAPPING;
-               mbox->cmd.length = 0;   
-               err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-       } while (err && retry-- && fr_event(card, err, mbox));
-
-       if( mbox->cmd.result != 0){
-               printk(KERN_INFO "%s: Read DLCI IB Mapping failed\n", 
-                       chan->name);
-       }
-
-       counter = mbox->cmd.length / sizeof(dlci_IB_mapping_t);
-       result = (void *)mbox->data;
-       
-       found = 0;
-       for (; counter; --counter, ++result) {
-               if ( result->dlci == chan->dlci ) {
-                       chan->IB_addr = result->addr_value;
-                       if(card->hw.type == SDLA_S514){
-                               chan->dlci_int_interface =
-                                       (void*)(card->hw.dpmbase +
-                                       chan->IB_addr);
-                               }else{ 
-                               chan->dlci_int_interface = 
-                                       (void*)(card->hw.dpmbase + 
-                                       (chan->IB_addr & 0x00001FFF));
-
-                       }
-                       found = 1;
-                       break;  
-               } 
-       }
-       if (!found)
-               printk( KERN_INFO "%s: DLCI %d not found by IB MAPPING cmd\n", 
-               card->devname, chan->dlci);
-}
-
-
-
-void s508_s514_lock(sdla_t *card, unsigned long *smp_flags)
-{
-       if (card->hw.type != SDLA_S514){
-
-               spin_lock_irqsave(&card->wandev.lock, *smp_flags);
-       }else{
-               spin_lock(&card->u.f.if_send_lock);
-       }
-       return;
-}
-
-
-void s508_s514_unlock(sdla_t *card, unsigned long *smp_flags)
-{
-       if (card->hw.type != SDLA_S514){
-
-               spin_unlock_irqrestore (&card->wandev.lock, *smp_flags);
-       }else{
-               spin_unlock(&card->u.f.if_send_lock);
-       }
-       return;
-}
-
-
-
-/*----------------------------------------------------------------------
-                  RECEIVE INTERRUPT: BOTTOM HALF HANDLERS 
- ----------------------------------------------------------------------*/
-
-
-/*========================================================
- * bh_enqueue
- *
- * Description:
- *     Insert a received packet into a circular
- *      rx queue.  This packet will be picked up 
- *      by fr_bh() and sent up the stack to the
- *      user.
- *             
- * Usage: 
- *     This function is called by rx interrupt,
- *      in API mode.
- *
- */
-
-static int bh_enqueue(struct net_device *dev, struct sk_buff *skb)
-{
-       /* Check for full */
-       fr_channel_t* chan = dev->priv;
-       sdla_t *card = chan->card;
-
-
-       if (atomic_read(&chan->bh_buff_used) == MAX_BH_BUFF){
-               ++card->wandev.stats.rx_dropped;
-               dev_kfree_skb_any(skb);
-               return 1; 
-       }
-
-       ((bh_data_t *)&chan->bh_head[chan->bh_write])->skb = skb;
-
-       if (chan->bh_write == (MAX_BH_BUFF-1)){
-               chan->bh_write=0;
-       }else{
-               ++chan->bh_write;
-       }
-
-       atomic_inc(&chan->bh_buff_used);
-
-       return 0;
-}
-
-
-/*========================================================
- * trigger_fr_bh
- *
- * Description:
- *     Kick the fr_bh() handler
- *
- * Usage:
- *     rx interrupt calls this function during
- *      the API mode. 
- */
-
-static void trigger_fr_bh (fr_channel_t *chan)
-{
-       if (!test_and_set_bit(0,&chan->tq_working)){
-               wanpipe_queue_work(&chan->common.wanpipe_work);
-       }
-}
-
-
-/*========================================================
- * fr_bh
- *
- * Description:
- *     Frame relay receive BH handler. 
- *     Dequeue data from the BH circular 
- *     buffer and pass it up the API sock.
- *             
- * Rationale: 
- *     This fuction is used to offload the 
- *     rx_interrupt during API operation mode.  
- *     The fr_bh() function executes for each 
- *     dlci/interface.  
- * 
- *      Once receive interrupt copies data from the
- *      card into an skb buffer, the skb buffer
- *     is appended to a circular BH buffer.
- *     Then the interrupt kicks fr_bh() to finish the
- *      job at a later time (not within the interrupt).
- *       
- * Usage:
- *     Interrupts use this to defer a task to 
- *      a polling routine.
- *
- */    
-
-static void fr_bh(struct net_device * dev)
-{
-       fr_channel_t* chan = dev->priv;
-       sdla_t *card = chan->card;
-       struct sk_buff *skb;
-
-       if (atomic_read(&chan->bh_buff_used) == 0){
-               clear_bit(0, &chan->tq_working);
-               return;
-       }
-
-       while (atomic_read(&chan->bh_buff_used)){
-
-               if (chan->common.sk == NULL || chan->common.func == NULL){
-                       clear_bit(0, &chan->tq_working);
-                       return;
-               }
-
-               skb  = ((bh_data_t *)&chan->bh_head[chan->bh_read])->skb;
-
-               if (skb != NULL){
-
-                       if (chan->common.sk == NULL || chan->common.func == NULL){
-                               ++card->wandev.stats.rx_dropped;
-                               ++chan->ifstats.rx_dropped;
-                               dev_kfree_skb_any(skb);
-                               fr_bh_cleanup(dev);
-                               continue;
-                       }
-
-                       if (chan->common.func(skb,dev,chan->common.sk) != 0){
-                               /* Sock full cannot send, queue us for
-                                 * another try */
-                               atomic_set(&chan->common.receive_block,1);
-                               return;
-                       }else{
-                               fr_bh_cleanup(dev);
-                       }
-               }else{
-                       fr_bh_cleanup(dev);
-               }
-       }       
-       clear_bit(0, &chan->tq_working);
-
-       return;
-}
-
-static int fr_bh_cleanup(struct net_device *dev)
-{
-       fr_channel_t* chan = dev->priv;
-
-       ((bh_data_t *)&chan->bh_head[chan->bh_read])->skb = NULL;
-
-       if (chan->bh_read == (MAX_BH_BUFF-1)){
-               chan->bh_read=0;
-       }else{
-               ++chan->bh_read;        
-       }
-
-       atomic_dec(&chan->bh_buff_used);
-       return 0;
-}
-
-
-/*----------------------------------------------------------------------
-               POLL BH HANDLERS AND KICK ROUTINES 
- ----------------------------------------------------------------------*/
-
-/*============================================================
- * trigger_fr_poll
- *
- * Description:
- *     Add a fr_poll() task into a tq_scheduler bh handler
- *      for a specific dlci/interface.  This will kick
- *      the fr_poll() routine at a later time. 
- *
- * Usage:
- *     Interrupts use this to defer a taks to 
- *      a polling routine.
- *
- */    
-static void trigger_fr_poll(struct net_device *dev)
-{
-       fr_channel_t* chan = dev->priv;
-       schedule_work(&chan->fr_poll_work);
-       return;
-}
-
-
-/*============================================================
- * fr_poll
- *     
- * Rationale:
- *     We cannot manipulate the routing tables, or
- *      ip addresses withing the interrupt. Therefore
- *      we must perform such actons outside an interrupt 
- *      at a later time. 
- *
- * Description:        
- *     Frame relay polling routine, responsible for 
- *             shutting down interfaces upon disconnect
- *             and adding/removing routes. 
- *      
- * Usage:        
- *     This function is executed for each frame relay
- *     dlci/interface through a tq_schedule bottom half.
- *      
- *      trigger_fr_poll() function is used to kick
- *      the fr_poll routine.  
- */
-
-static void fr_poll(struct net_device *dev)
-{
-
-       fr_channel_t* chan;
-       sdla_t *card;
-       u8 check_gateway=0;
-
-       if (!dev || (chan = dev->priv) == NULL)
-               return;
-
-       card = chan->card;
-       
-       /* (Re)Configuraiton is in progress, stop what you are 
-        * doing and get out */
-       if (test_bit(PERI_CRIT,&card->wandev.critical)){
-               return;
-       }
-
-       switch (chan->common.state){
-
-       case WAN_DISCONNECTED:
-
-               if (test_bit(DYN_OPT_ON,&chan->interface_down) &&
-                   !test_bit(DEV_DOWN, &chan->interface_down) &&
-                   dev->flags&IFF_UP){
-
-                       printk(KERN_INFO "%s: Interface %s is Down.\n", 
-                               card->devname,dev->name);
-                       change_dev_flags(dev,dev->flags&~IFF_UP);
-                       set_bit(DEV_DOWN, &chan->interface_down);
-                       chan->route_flag = NO_ROUTE;
-                       
-               }else{
-                       if (chan->inarp != INARP_NONE)
-                               process_route(dev);     
-               }
-               break;
-
-       case WAN_CONNECTED:
-
-               if (test_bit(DYN_OPT_ON,&chan->interface_down) &&
-                   test_bit(DEV_DOWN, &chan->interface_down) &&
-                   !(dev->flags&IFF_UP)){
-
-                       printk(KERN_INFO "%s: Interface %s is Up.\n", 
-                                       card->devname,dev->name);
-
-                       change_dev_flags(dev,dev->flags|IFF_UP);
-                       clear_bit(DEV_DOWN, &chan->interface_down);
-                       check_gateway=1;
-               }
-
-               if (chan->inarp != INARP_NONE){
-                       process_route(dev);
-                       check_gateway=1;
-               }
-
-               if (chan->gateway && check_gateway)
-                       add_gateway(card,dev);
-
-               break;
-
-       }
-
-       return; 
-}
-
-/*==============================================================
- * check_tx_status
- *
- * Rationale:
- *     We cannot transmit from an interrupt while
- *      the if_send is transmitting data.  Therefore,
- *      we must check whether the tx buffers are
- *      begin used, before we transmit from an
- *      interrupt.     
- * 
- * Description:        
- *     Checks whether it's safe to use the transmit 
- *      buffers. 
- *
- * Usage:
- *     ARP and UDP handling routines use this function
- *      because, they need to transmit data during
- *      an interrupt.
- */
-
-static int check_tx_status(sdla_t *card, struct net_device *dev)
-{
-
-       if (card->hw.type == SDLA_S514){
-               if (test_bit(SEND_CRIT, (void*)&card->wandev.critical) ||
-                       test_bit(SEND_TXIRQ_CRIT, (void*)&card->wandev.critical)) {
-                       return 1;
-               }
-       }
-
-       if (netif_queue_stopped(dev) || (card->u.f.tx_interrupts_pending))
-               return 1; 
-
-       return 0;
-}
-
-/*===============================================================
- * move_dev_to_next
- *  
- * Description:
- *     Move the dev pointer to the next location in the
- *      link list.  Check if we are at the end of the 
- *      list, if so start from the begining.
- *
- * Usage:
- *     Timer interrupt uses this function to efficiently
- *      step through the devices that need to send ARP data.
- *
- */
-
-struct net_device *move_dev_to_next(sdla_t *card, struct net_device *dev)
-{
-       if (card->wandev.new_if_cnt != 1){
-               if (!*((struct net_device **)dev->priv))
-                       return card->wandev.dev;
-               else
-                       return *((struct net_device **)dev->priv);
-       }
-       return dev;
-}
-
-/*==============================================================
- * trigger_config_fr
- *
- * Rationale:
- *     All commands must be performed inside of a  
- *      interrupt.   
- *
- * Description:
- *     Kick the config_fr() routine throught the
- *      timer interrupt.
- */
-
-
-static void trigger_config_fr (sdla_t *card)
-{
-       fr508_flags_t* flags = card->flags;
-
-       card->u.f.timer_int_enabled |= TMR_INT_ENABLED_CONFIG;
-       flags->imask |= FR_INTR_TIMER;
-}
-
-
-/*==============================================================
- * config_fr
- *
- * Rationale:
- *     All commands must be performed inside of a  
- *      interrupt.  
- &
- * Description:        
- *     Configure a DLCI. This function is executed
- *      by a timer_interrupt.  The if_open() function
- *      triggers it.
- *
- * Usage:
- *     new_if() collects all data necessary to
- *      configure the DLCI. It sets the chan->dlci_ready 
- *      bit.  When the if_open() function is executed
- *      it checks this bit, and if its set it triggers
- *      the timer interrupt to execute the config_fr()
- *      function.
- */
-
-static void config_fr (sdla_t *card)
-{
-       struct net_device *dev;
-       fr_channel_t *chan;
-
-       for (dev = card->wandev.dev; dev;
-            dev = *((struct net_device **)dev->priv)) {
-       
-               if ((chan=dev->priv) == NULL)
-                       continue;
-               
-               if (!test_bit(0,&chan->config_dlci))
-                       continue;
-
-               clear_bit(0,&chan->config_dlci);
-
-               /* If signalling is set to NO, then setup 
-                * DLCI addresses right away.  Don't have to wait for
-                * link to connect. 
-                */
-               if (card->wandev.signalling == WANOPT_NO){
-                       printk(KERN_INFO "%s: Signalling set to NO: Mapping DLCI's\n",
-                                       card->wandev.name);
-                       if (fr_init_dlci(card,chan)){
-                               printk(KERN_INFO "%s: ERROR: Failed to configure DLCI %i !\n",
-                                       card->devname, chan->dlci);
-                               return;
-                       }
-               }
-
-               if (card->wandev.station == WANOPT_CPE) {
-       
-                       update_chan_state(dev); 
-                       
-                       /* CPE: issue full status enquiry */
-                       fr_issue_isf(card, FR_ISF_FSE);
-
-               } else {        
-                       /* FR switch: activate DLCI(s) */
-       
-                       /* For Switch emulation we have to ADD and ACTIVATE
-                        * the DLCI(s) that were configured with the SET_DLCI_
-                        * CONFIGURATION command. Add and Activate will fail if
-                        * DLCI specified is not included in the list.
-                        *
-                        * Also If_open is called once for each interface. But
-                        * it does not get in here for all the interface. So
-                        * we have to pass the entire list of DLCI(s) to add 
-                        * activate routines.  
-                        */ 
-                       
-                       if (!check_dlci_config (card, chan)){
-                               fr_add_dlci(card, chan->dlci);
-                               fr_activate_dlci(card, chan->dlci);
-                       }
-               }
-
-               card->u.f.dlci_to_dev_map[chan->dlci] = dev;
-       }
-       return;
-}
-
-
-/*==============================================================
- * config_fr
- *
- * Rationale:
- *     All commands must be executed during an interrupt.
- * 
- * Description:        
- *     Trigger uncofig_fr() function through 
- *      the timer interrupt.
- *
- */
-
-static void trigger_unconfig_fr(struct net_device *dev)
-{
-       fr_channel_t *chan = dev->priv;
-       volatile sdla_t *card = chan->card;
-       unsigned long timeout;
-       fr508_flags_t* flags = card->flags;
-       int reset_critical=0;
-       
-       if (test_bit(PERI_CRIT,(void*)&card->wandev.critical)){
-               clear_bit(PERI_CRIT,(void*)&card->wandev.critical);
-               reset_critical=1;
-       }
-               
-       /* run unconfig_dlci() function 
-         * throught the timer interrupt */
-       set_bit(0,(void*)&chan->unconfig_dlci);
-       card->u.f.timer_int_enabled |= TMR_INT_ENABLED_UNCONFIG;
-       flags->imask |= FR_INTR_TIMER;
-
-       /* Wait for the command to complete */
-       timeout = jiffies;
-       for(;;) {
-
-               if(!(card->u.f.timer_int_enabled & TMR_INT_ENABLED_UNCONFIG))
-                       break;
-
-               if (time_after(jiffies, timeout + 1 * HZ)){
-                       card->u.f.timer_int_enabled &= ~TMR_INT_ENABLED_UNCONFIG;
-                       printk(KERN_INFO "%s: Failed to delete DLCI %i\n",
-                               card->devname,chan->dlci);
-                       break;
-               }
-       }
-
-       if (reset_critical){
-               set_bit(PERI_CRIT,(void*)&card->wandev.critical);
-       }
-}
-
-/*==============================================================
- * unconfig_fr
- *
- * Rationale:
- *     All commands must be executed during an interrupt.
- * 
- * Description:        
- *     Remove the dlci from firmware.
- *     This funciton is used in NODE shutdown.
- */
-
-static void unconfig_fr (sdla_t *card)
-{
-       struct net_device *dev;
-       fr_channel_t *chan;
-
-       for (dev = card->wandev.dev; dev;
-            dev = *((struct net_device **)dev->priv)){
-       
-               if ((chan=dev->priv) == NULL)
-                       continue;
-               
-               if (!test_bit(0,&chan->unconfig_dlci))
-                       continue;
-
-               clear_bit(0,&chan->unconfig_dlci);
-
-               if (card->wandev.station == WANOPT_NODE){
-                       printk(KERN_INFO "%s: Unconfiguring DLCI %i\n",
-                                       card->devname,chan->dlci);
-                       fr_delete_dlci(card,chan->dlci);
-               }
-               card->u.f.dlci_to_dev_map[chan->dlci] = NULL;
-       }
-}
-
-static int setup_fr_header(struct sk_buff *skb, struct net_device* dev,
-                          char op_mode)
-{
-       fr_channel_t *chan=dev->priv;
-
-       if (op_mode == WANPIPE) {
-               chan->fr_header[0]=Q922_UI;
-               
-               switch (htons(skb->protocol)){
-               case ETH_P_IP:
-                       chan->fr_header[1]=NLPID_IP;
-                       break;
-               default:
-                       return -EINVAL;
-               }
-                       
-               return 2;
-       }
-
-       /* If we are in bridging mode, we must apply
-        * an Ethernet header
-        */
-       if (op_mode == BRIDGE || op_mode == BRIDGE_NODE) {
-               /* Encapsulate the packet as a bridged Ethernet frame. */
-#ifdef DEBUG
-               printk(KERN_INFO "%s: encapsulating skb for frame relay\n", 
-                       dev->name);
-#endif
-               chan->fr_header[0] = 0x03;
-               chan->fr_header[1] = 0x00;
-               chan->fr_header[2] = 0x80;
-               chan->fr_header[3] = 0x00;
-               chan->fr_header[4] = 0x80;
-               chan->fr_header[5] = 0xC2;
-               chan->fr_header[6] = 0x00;
-               chan->fr_header[7] = 0x07;
-
-               /* Yuck. */
-               skb->protocol = ETH_P_802_3;
-               return 8;
-       }
-               
-       return 0;
-}
-
-
-static int check_dlci_config (sdla_t *card, fr_channel_t *chan)
-{
-       fr_mbox_t* mbox = card->mbox;
-       int err=0;
-       fr_conf_t *conf=NULL;
-       unsigned short dlci_num = chan->dlci;
-       int dlci_offset=0;
-       struct net_device *dev = NULL;
-       
-       mbox->cmd.command = FR_READ_CONFIG;
-       mbox->cmd.length = 0;
-       mbox->cmd.dlci = dlci_num;      
-
-       err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-       
-       if (err == CMD_OK){
-               return 0;
-       }
-
-       for (dev = card->wandev.dev; dev;
-            dev=*((struct net_device **)dev->priv))
-               set_chan_state(dev,WAN_DISCONNECTED);
-       
-       printk(KERN_INFO "DLCI %i Not configured, configuring\n",dlci_num);
-       
-       mbox->cmd.command = FR_COMM_DISABLE;
-       mbox->cmd.length = 0;
-       err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-       if (err != CMD_OK){
-               fr_event(card, err, mbox);
-               return 2;
-       }
-
-       printk(KERN_INFO "Disabled Communications \n");
-       
-       mbox->cmd.command = FR_READ_CONFIG;
-       mbox->cmd.length = 0;
-       mbox->cmd.dlci = 0;     
-
-       err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-       
-       if (err != CMD_OK){
-               fr_event(card, err, mbox);
-               return 2;
-       }
-       
-       conf = (fr_conf_t *)mbox->data;
-
-       dlci_offset=0;
-       for (dev = card->wandev.dev; dev;
-            dev = *((struct net_device **)dev->priv)) {
-               fr_channel_t *chan_tmp = dev->priv;
-               conf->dlci[dlci_offset] = chan_tmp->dlci;               
-               dlci_offset++;
-       }
-       
-       printk(KERN_INFO "Got Fr configuration Buffer Length is %x Dlci %i Dlci Off %i\n",
-               mbox->cmd.length,
-               mbox->cmd.length > 0x20 ? conf->dlci[0] : -1, 
-               dlci_offset );
-       
-       mbox->cmd.length = 0x20 + dlci_offset*2;
-
-       mbox->cmd.command = FR_SET_CONFIG;
-       mbox->cmd.dlci = 0; 
-
-       err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-
-       if (err != CMD_OK){
-               fr_event(card, err, mbox);
-               return 2;
-       }
-
-       initialize_rx_tx_buffers (card);
-
-       
-       printk(KERN_INFO "Configuraiton Succeded for new DLCI %i\n",dlci_num);
-
-       if (fr_comm_enable (card)){
-               return 2;
-       }
-
-       printk(KERN_INFO "Enabling Communications \n");
-
-       for (dev = card->wandev.dev; dev;
-            dev = *((struct net_device **)dev->priv)) {
-               fr_channel_t *chan_tmp = dev->priv;
-               fr_init_dlci(card,chan_tmp);
-               fr_add_dlci(card, chan_tmp->dlci);
-               fr_activate_dlci(card, chan_tmp->dlci);
-       }
-
-       printk(KERN_INFO "END OF CONFIGURAITON %i\n",dlci_num);
-       
-       return 1;
-}
-
-static void initialize_rx_tx_buffers (sdla_t *card)
-{
-       fr_buf_info_t* buf_info;
-       
-       if (card->hw.type == SDLA_S514) {
-       
-                buf_info = (void*)(card->hw.dpmbase + FR_MB_VECTOR +
-                       FR508_RXBC_OFFS);
-
-                card->rxmb = (void*)(buf_info->rse_next + card->hw.dpmbase);
-
-                card->u.f.rxmb_base =
-                        (void*)(buf_info->rse_base + card->hw.dpmbase); 
-
-                card->u.f.rxmb_last =
-                        (void*)(buf_info->rse_base +
-                        (buf_info->rse_num - 1) * sizeof(fr_rx_buf_ctl_t) +
-                        card->hw.dpmbase);
-       }else{  
-               buf_info = (void*)(card->hw.dpmbase + FR508_RXBC_OFFS);
-
-               card->rxmb = (void*)(buf_info->rse_next -
-                       FR_MB_VECTOR + card->hw.dpmbase);
-               
-               card->u.f.rxmb_base =
-                       (void*)(buf_info->rse_base -
-                       FR_MB_VECTOR + card->hw.dpmbase);
-               
-               card->u.f.rxmb_last =
-                       (void*)(buf_info->rse_base +
-                       (buf_info->rse_num - 1) * sizeof(fr_rx_buf_ctl_t) -
-                       FR_MB_VECTOR + card->hw.dpmbase);
-       }
-
-       card->u.f.rx_base = buf_info->buf_base;
-       card->u.f.rx_top  = buf_info->buf_top;
-
-       card->u.f.tx_interrupts_pending = 0;
-
-       return;
-}
-
-       
-
-MODULE_LICENSE("GPL");
-
-/****** End *****************************************************************/
diff --git a/drivers/net/wan/sdla_ft1.c b/drivers/net/wan/sdla_ft1.c
deleted file mode 100644 (file)
index 9d6528a..0000000
+++ /dev/null
@@ -1,345 +0,0 @@
-/*****************************************************************************
-* sdla_chdlc.c WANPIPE(tm) Multiprotocol WAN Link Driver. Cisco HDLC module.
-*
-* Authors:     Nenad Corbic <ncorbic@sangoma.com>
-*              Gideon Hack  
-*
-* Copyright:   (c) 1995-1999 Sangoma Technologies Inc.
-*
-*              This program is free software; you can redistribute it and/or
-*              modify it under the terms of the GNU General Public License
-*              as published by the Free Software Foundation; either version
-*              2 of the License, or (at your option) any later version.
-* ============================================================================
-* Sep 30, 1999  Nenad Corbic    Fixed dynamic IP and route setup.
-* Sep 23, 1999  Nenad Corbic    Added SMP support, fixed tracing 
-* Sep 13, 1999  Nenad Corbic   Split up Port 0 and 1 into separate devices.
-* Jun 02, 1999  Gideon Hack     Added support for the S514 adapter.
-* Oct 30, 1998 Jaspreet Singh  Added Support for CHDLC API (HDLC STREAMING).
-* Oct 28, 1998 Jaspreet Singh  Added Support for Dual Port CHDLC.
-* Aug 07, 1998 David Fong      Initial version.
-*****************************************************************************/
-
-#include <linux/module.h>
-#include <linux/kernel.h>      /* printk(), and other useful stuff */
-#include <linux/stddef.h>      /* offsetof(), etc. */
-#include <linux/errno.h>       /* return codes */
-#include <linux/string.h>      /* inline memset(), etc. */
-#include <linux/slab.h>                /* kmalloc(), kfree() */
-#include <linux/wanrouter.h>   /* WAN router definitions */
-#include <linux/wanpipe.h>     /* WANPIPE common user API definitions */
-#include <linux/if_arp.h>      /* ARPHRD_* defines */
-#include <linux/jiffies.h>     /* time_after() macro */
-
-#include <linux/inetdevice.h>
-#include <asm/uaccess.h>
-
-#include <linux/in.h>          /* sockaddr_in */
-#include <linux/inet.h>        
-#include <linux/if.h>
-#include <asm/byteorder.h>     /* htons(), etc. */
-#include <linux/sdlapci.h>
-#include <asm/io.h>
-
-#include <linux/sdla_chdlc.h>          /* CHDLC firmware API definitions */
-
-/****** Defines & Macros ****************************************************/
-
-/* reasons for enabling the timer interrupt on the adapter */
-#define TMR_INT_ENABLED_UDP    0x0001
-#define TMR_INT_ENABLED_UPDATE 0x0002
-#define        CHDLC_DFLT_DATA_LEN     1500            /* default MTU */
-#define CHDLC_HDR_LEN          1
-
-#define IFF_POINTTOPOINT 0x10
-
-#define WANPIPE 0x00
-#define API    0x01
-#define CHDLC_API 0x01
-
-#define PORT(x)   (x == 0 ? "PRIMARY" : "SECONDARY" )
-
-/******Data Structures*****************************************************/
-
-/* This structure is placed in the private data area of the device structure.
- * The card structure used to occupy the private area but now the following 
- * structure will incorporate the card structure along with CHDLC specific data
- */
-
-typedef struct chdlc_private_area
-{
-       struct net_device *slave;
-       sdla_t          *card;
-       int             TracingEnabled;         /* For enabling Tracing */
-       unsigned long   curr_trace_addr;        /* Used for Tracing */
-       unsigned long   start_trace_addr;
-       unsigned long   end_trace_addr;
-       unsigned long   base_addr_trace_buffer;
-       unsigned long   end_addr_trace_buffer;
-       unsigned short  number_trace_elements;
-       unsigned        available_buffer_space;
-       unsigned long   router_start_time;
-       unsigned char   route_status;
-       unsigned char   route_removed;
-       unsigned long   tick_counter;           /* For 5s timeout counter */
-       unsigned long   router_up_time;
-        u32             IP_address;            /* IP addressing */
-        u32             IP_netmask;
-       unsigned char  mc;                      /* Mulitcast support on/off */
-       unsigned short udp_pkt_lgth;            /* udp packet processing */
-       char udp_pkt_src;
-       char udp_pkt_data[MAX_LGTH_UDP_MGNT_PKT];
-       unsigned short timer_int_enabled;
-       char update_comms_stats;                /* updating comms stats */
-       //FIXME: add driver stats as per frame relay!
-
-} chdlc_private_area_t;
-
-/* Route Status options */
-#define NO_ROUTE       0x00
-#define ADD_ROUTE      0x01
-#define ROUTE_ADDED    0x02
-#define REMOVE_ROUTE   0x03
-
-
-/****** Function Prototypes *************************************************/
-/* WAN link driver entry points. These are called by the WAN router module. */
-static int wpft1_exec (struct sdla *card, void *u_cmd, void *u_data);
-static int chdlc_read_version (sdla_t* card, char* str);
-static int chdlc_error (sdla_t *card, int err, CHDLC_MAILBOX_STRUCT *mb);
-
-/****** Public Functions ****************************************************/
-
-/*============================================================================
- * Cisco HDLC protocol initialization routine.
- *
- * This routine is called by the main WANPIPE module during setup.  At this
- * point adapter is completely initialized and firmware is running.
- *  o read firmware version (to make sure it's alive)
- *  o configure adapter
- *  o initialize protocol-specific fields of the adapter data space.
- *
- * Return:     0       o.k.
- *             < 0     failure.
- */
-int wpft1_init (sdla_t* card, wandev_conf_t* conf)
-{
-       unsigned char port_num;
-       int err;
-
-       union
-               {
-               char str[80];
-               } u;
-       volatile CHDLC_MAILBOX_STRUCT* mb;
-       CHDLC_MAILBOX_STRUCT* mb1;
-       unsigned long timeout;
-
-       /* Verify configuration ID */
-       if (conf->config_id != WANCONFIG_CHDLC) {
-               printk(KERN_INFO "%s: invalid configuration ID %u!\n",
-                                 card->devname, conf->config_id);
-               return -EINVAL;
-       }
-
-       /* Use primary port */
-       card->u.c.comm_port = 0;
-       
-
-       /* Initialize protocol-specific fields */
-       if(card->hw.type != SDLA_S514){
-               card->mbox  = (void *) card->hw.dpmbase;
-       }else{ 
-               card->mbox = (void *) card->hw.dpmbase + PRI_BASE_ADDR_MB_STRUCT;
-       }
-
-       mb = mb1 = card->mbox;
-
-       if (!card->configured){
-
-               /* The board will place an 'I' in the return code to indicate that it is
-               ready to accept commands.  We expect this to be completed in less
-               than 1 second. */
-
-               timeout = jiffies;
-               while (mb->return_code != 'I')  /* Wait 1s for board to initialize */
-                       if (time_after(jiffies, timeout + 1*HZ)) break;
-
-               if (mb->return_code != 'I') {
-                       printk(KERN_INFO
-                               "%s: Initialization not completed by adapter\n",
-                               card->devname);
-                       printk(KERN_INFO "Please contact Sangoma representative.\n");
-                       return -EIO;
-               }
-       }
-
-       /* Read firmware version.  Note that when adapter initializes, it
-        * clears the mailbox, so it may appear that the first command was
-        * executed successfully when in fact it was merely erased. To work
-        * around this, we execute the first command twice.
-        */
-
-       if (chdlc_read_version(card, u.str))
-               return -EIO;
-
-       printk(KERN_INFO "%s: Running FT1 Configuration firmware v%s\n",
-               card->devname, u.str); 
-
-       card->isr                       = NULL;
-       card->poll                      = NULL;
-       card->exec                      = &wpft1_exec;
-       card->wandev.update             = NULL;
-       card->wandev.new_if             = NULL;
-       card->wandev.del_if             = NULL;
-       card->wandev.state              = WAN_DUALPORT;
-       card->wandev.udp_port           = conf->udp_port;
-
-       card->wandev.new_if_cnt = 0;
-
-       /* This is for the ports link state */
-       card->u.c.state = WAN_DISCONNECTED;
-       
-       /* reset the number of times the 'update()' proc has been called */
-       card->u.c.update_call_count = 0;
-       
-       card->wandev.ttl = 0x7F;
-       card->wandev.interface = 0; 
-
-       card->wandev.clocking = 0;
-
-       port_num = card->u.c.comm_port;
-
-       /* Setup Port Bps */
-
-               card->wandev.bps = 0;
-
-       card->wandev.mtu = MIN_LGTH_CHDLC_DATA_CFG;
-
-       /* Set up the interrupt status area */
-       /* Read the CHDLC Configuration and obtain: 
-        *      Ptr to shared memory infor struct
-         * Use this pointer to calculate the value of card->u.c.flags !
-        */
-       mb1->buffer_length = 0;
-       mb1->command = READ_CHDLC_CONFIGURATION;
-       err = sdla_exec(mb1) ? mb1->return_code : CMD_TIMEOUT;
-       if(err != COMMAND_OK) {
-               chdlc_error(card, err, mb1);
-               return -EIO;
-       }
-
-       if(card->hw.type == SDLA_S514){
-                       card->u.c.flags = (void *)(card->hw.dpmbase +
-                               (((CHDLC_CONFIGURATION_STRUCT *)mb1->data)->
-                       ptr_shared_mem_info_struct));
-        }else{
-                card->u.c.flags = (void *)(card->hw.dpmbase +
-                        (((CHDLC_CONFIGURATION_STRUCT *)mb1->data)->
-                       ptr_shared_mem_info_struct % SDLA_WINDOWSIZE));
-       }
-
-       card->wandev.state = WAN_FT1_READY;
-       printk(KERN_INFO "%s: FT1 Config Ready !\n",card->devname);
-
-       return 0;
-}
-
-static int wpft1_exec(sdla_t *card, void *u_cmd, void *u_data)
-{
-       CHDLC_MAILBOX_STRUCT* mbox = card->mbox;
-       int len;
-
-       if (copy_from_user((void*)&mbox->command, u_cmd, sizeof(ft1_exec_cmd_t))){
-               return -EFAULT;
-       }
-
-       len = mbox->buffer_length;
-
-       if (len) {
-               if( copy_from_user((void*)&mbox->data, u_data, len)){
-                       return -EFAULT;
-               }
-       }
-
-       /* execute command */
-       if (!sdla_exec(mbox)){
-               return -EIO;
-       }
-
-       /* return result */
-       if( copy_to_user(u_cmd, (void*)&mbox->command, sizeof(ft1_exec_cmd_t))){
-               return -EFAULT;
-       }
-
-       len = mbox->buffer_length;
-
-       if (len && u_data && copy_to_user(u_data, (void*)&mbox->data, len)){
-               return -EFAULT;
-       }
-
-       return 0;
-
-}
-
-/*============================================================================
- * Read firmware code version.
- *     Put code version as ASCII string in str. 
- */
-static int chdlc_read_version (sdla_t* card, char* str)
-{
-       CHDLC_MAILBOX_STRUCT* mb = card->mbox;
-       int len;
-       char err;
-       mb->buffer_length = 0;
-       mb->command = READ_CHDLC_CODE_VERSION;
-       err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT;
-
-       if(err != COMMAND_OK) {
-               chdlc_error(card,err,mb);
-       }
-       else if (str) {  /* is not null */
-               len = mb->buffer_length;
-               memcpy(str, mb->data, len);
-               str[len] = '\0';
-       }
-       return (err);
-}
-
-/*============================================================================
- * Firmware error handler.
- *     This routine is called whenever firmware command returns non-zero
- *     return code.
- *
- * Return zero if previous command has to be cancelled.
- */
-static int chdlc_error (sdla_t *card, int err, CHDLC_MAILBOX_STRUCT *mb)
-{
-       unsigned cmd = mb->command;
-
-       switch (err) {
-
-       case CMD_TIMEOUT:
-               printk(KERN_ERR "%s: command 0x%02X timed out!\n",
-                       card->devname, cmd);
-               break;
-
-       case S514_BOTH_PORTS_SAME_CLK_MODE:
-               if(cmd == SET_CHDLC_CONFIGURATION) {
-                       printk(KERN_INFO
-                        "%s: Configure both ports for the same clock source\n",
-                               card->devname);
-                       break;
-               }
-
-       default:
-               printk(KERN_INFO "%s: command 0x%02X returned 0x%02X!\n",
-                       card->devname, cmd, err);
-       }
-
-       return 0;
-}
-
-MODULE_LICENSE("GPL");
diff --git a/drivers/net/wan/sdla_ppp.c b/drivers/net/wan/sdla_ppp.c
deleted file mode 100644 (file)
index a4b489c..0000000
+++ /dev/null
@@ -1,3430 +0,0 @@
-/*****************************************************************************
-* sdla_ppp.c   WANPIPE(tm) Multiprotocol WAN Link Driver. PPP module.
-*
-* Author:      Nenad Corbic <ncorbic@sangoma.com>
-*
-* Copyright:   (c) 1995-2001 Sangoma Technologies Inc.
-*
-*              This program is free software; you can redistribute it and/or
-*              modify it under the terms of the GNU General Public License
-*              as published by the Free Software Foundation; either version
-*              2 of the License, or (at your option) any later version.
-* ============================================================================
-* Feb 28, 2001  Nenad Corbic   o Updated if_tx_timeout() routine for 
-*                                2.4.X kernels.
-* Nov 29, 2000  Nenad Corbic   o Added the 2.4.x kernel support:
-*                                get_ip_address() function has moved
-*                                into the ppp_poll() routine. It cannot
-*                                be called from an interrupt.
-* Nov 07, 2000  Nenad Corbic   o Added security features for UDP debugging:
-*                                 Deny all and specify allowed requests.
-* May 02, 2000  Nenad Corbic   o Added the dynamic interface shutdown
-*                                 option. When the link goes down, the
-*                                 network interface IFF_UP flag is reset.
-* Mar 06, 2000  Nenad Corbic   o Bug Fix: corrupted mbox recovery.
-* Feb 25, 2000  Nenad Corbic    o Fixed the FT1 UDP debugger problem.
-* Feb 09, 2000  Nenad Coribc    o Shutdown bug fix. update() was called
-*                                 with NULL dev pointer: no check.
-* Jan 24, 2000  Nenad Corbic    o Disabled use of CMD complete inter.
-* Dev 15, 1999  Nenad Corbic    o Fixed up header files for 2.0.X kernels
-* Oct 25, 1999  Nenad Corbic    o Support for 2.0.X kernels
-*                                 Moved dynamic route processing into 
-*                                 a polling routine.
-* Oct 07, 1999  Nenad Corbic    o Support for S514 PCI card.  
-*               Gideon Hack     o UPD and Updates executed using timer interrupt
-* Sep 10, 1999  Nenad Corbic    o Fixed up the /proc statistics
-* Jul 20, 1999  Nenad Corbic    o Remove the polling routines and use 
-*                                 interrupts instead.
-* Sep 17, 1998 Jaspreet Singh  o Updates for 2.2.X Kernels.
-* Aug 13, 1998 Jaspreet Singh  o Improved Line Tracing.
-* Jun 22, 1998 David Fong      o Added remote IP address assignment
-* Mar 15, 1998 Alan Cox        o 2.1.8x basic port.
-* Apr 16, 1998 Jaspreet Singh  o using htons() for the IPX protocol.
-* Dec 09, 1997 Jaspreet Singh  o Added PAP and CHAP.
-*                              o Implemented new routines like 
-*                                ppp_set_inbnd_auth(), ppp_set_outbnd_auth(),
-*                                tokenize() and strstrip().
-* Nov 27, 1997 Jaspreet Singh  o Added protection against enabling of irqs 
-*                                while they have been disabled.
-* Nov 24, 1997  Jaspreet Singh  o Fixed another RACE condition caused by
-*                                 disabling and enabling of irqs.
-*                               o Added new counters for stats on disable/enable
-*                                 IRQs.
-* Nov 10, 1997 Jaspreet Singh  o Initialized 'skb->mac.raw' to 'skb->data'
-*                                before every netif_rx().
-*                              o Free up the device structure in del_if().
-* Nov 07, 1997 Jaspreet Singh  o Changed the delay to zero for Line tracing
-*                                command.
-* Oct 20, 1997         Jaspreet Singh  o Added hooks in for Router UP time.
-* Oct 16, 1997 Jaspreet Singh  o The critical flag is used to maintain flow
-*                                control by avoiding RACE conditions.  The 
-*                                cli() and restore_flags() are taken out.
-*                                A new structure, "ppp_private_area", is added 
-*                                to provide Driver Statistics.   
-* Jul 21, 1997         Jaspreet Singh  o Protected calls to sdla_peek() by adding 
-*                                save_flags(), cli() and restore_flags().
-* Jul 07, 1997 Jaspreet Singh  o Added configurable TTL for UDP packets
-*                              o Added ability to discard mulitcast and
-*                                broacast source addressed packets.
-* Jun 27, 1997         Jaspreet Singh  o Added FT1 monitor capabilities
-*                                New case (0x25) statement in if_send routine.
-*                                Added a global variable rCount to keep track
-*                                of FT1 status enabled on the board.
-* May 22, 1997 Jaspreet Singh  o Added change in the PPP_SET_CONFIG command for
-*                              508 card to reflect changes in the new 
-*                              ppp508.sfm for supporting:continous transmission
-*                              of Configure-Request packets without receiving a
-*                              reply                           
-*                              OR-ed 0x300 to conf_flags 
-*                              o Changed connect_tmout from 900 to 0
-* May 21, 1997 Jaspreet Singh  o Fixed UDP Management for multiple boards
-* Apr 25, 1997  Farhan Thawar    o added UDP Management stuff
-* Mar 11, 1997  Farhan Thawar   Version 3.1.1
-*                                o fixed (+1) bug in rx_intr()
-*                                o changed if_send() to return 0 if
-*                                  wandev.critical() is true
-*                                o free socket buffer in if_send() if
-*                                  returning 0 
-* Jan 15, 1997 Gene Kozin      Version 3.1.0
-*                               o implemented exec() entry point
-* Jan 06, 1997 Gene Kozin      Initial version.
-*****************************************************************************/
-
-#include <linux/module.h>
-#include <linux/kernel.h>      /* printk(), and other useful stuff */
-#include <linux/stddef.h>      /* offsetof(), etc. */
-#include <linux/errno.h>       /* return codes */
-#include <linux/string.h>      /* inline memset(), etc. */
-#include <linux/slab.h>        /* kmalloc(), kfree() */
-#include <linux/wanrouter.h>   /* WAN router definitions */
-#include <linux/wanpipe.h>     /* WANPIPE common user API definitions */
-#include <linux/if_arp.h>      /* ARPHRD_* defines */
-#include <asm/byteorder.h>     /* htons(), etc. */
-#include <linux/in.h>          /* sockaddr_in */
-#include <linux/jiffies.h>     /* time_after() macro */
-
-
-#include <asm/uaccess.h>
-#include <linux/inetdevice.h>
-#include <linux/netdevice.h>
-
-#include <linux/if.h>
-#include <linux/sdla_ppp.h>            /* PPP firmware API definitions */
-#include <linux/sdlasfm.h>             /* S514 Type Definition */
-/****** Defines & Macros ****************************************************/
-
-#define        PPP_DFLT_MTU    1500            /* default MTU */
-#define        PPP_MAX_MTU     4000            /* maximum MTU */
-#define PPP_HDR_LEN    1
-
-#define MAX_IP_ERRORS 100 
-
-#define        CONNECT_TIMEOUT (90*HZ)         /* link connection timeout */
-#define        HOLD_DOWN_TIME  (5*HZ)          /* link hold down time : Changed from 30 to 5 */
-
-/* For handle_IPXWAN() */
-#define CVHexToAscii(b) (((unsigned char)(b) > (unsigned char)9) ? ((unsigned char)'A' + ((unsigned char)(b) - (unsigned char)10)) : ((unsigned char)'0' + (unsigned char)(b)))
-
-/* Macro for enabling/disabling debugging comments */
-//#define NEX_DEBUG
-#ifdef NEX_DEBUG
-#define NEX_PRINTK(format, a...) printk(format, ## a)
-#else
-#define NEX_PRINTK(format, a...)
-#endif /* NEX_DEBUG */ 
-
-#define DCD(a)   ( a & 0x08 ? "HIGH" : "LOW" )
-#define CTS(a)   ( a & 0x20 ? "HIGH" : "LOW" )
-#define LCP(a)   ( a == 0x09 ? "OPEN" : "CLOSED" )
-#define IP(a)    ( a == 0x09 ? "ENABLED" : "DISABLED" )
-
-#define TMR_INT_ENABLED_UPDATE         0x01
-#define TMR_INT_ENABLED_PPP_EVENT      0x02
-#define TMR_INT_ENABLED_UDP            0x04
-#define TMR_INT_ENABLED_CONFIG         0x20
-
-/* Set Configuraton Command Definitions */
-#define PERCENT_TX_BUFF                        60
-#define TIME_BETWEEN_CONF_REQ                  30
-#define TIME_BETWEEN_PAP_CHAP_REQ      30
-#define WAIT_PAP_CHAP_WITHOUT_REPLY     300
-#define WAIT_AFTER_DCD_CTS_LOW          5
-#define TIME_DCD_CTS_LOW_AFTER_LNK_DOWN 10
-#define WAIT_DCD_HIGH_AFTER_ENABLE_COMM 900
-#define MAX_CONF_REQ_WITHOUT_REPLY      10
-#define MAX_TERM_REQ_WITHOUT_REPLY      2
-#define NUM_CONF_NAK_WITHOUT_REPLY      5
-#define NUM_AUTH_REQ_WITHOUT_REPLY      10
-
-#define END_OFFSET 0x1F0
-
-
-/******Data Structures*****************************************************/
-
-/* This structure is placed in the private data area of the device structure.
- * The card structure used to occupy the private area but now the following 
- * structure will incorporate the card structure along with PPP specific data
- */
-  
-typedef struct ppp_private_area
-{
-       struct net_device *slave;
-       sdla_t* card;   
-       unsigned long router_start_time;        /*router start time in sec */
-       unsigned long tick_counter;             /*used for 5 second counter*/
-       unsigned mc;                            /*multicast support on or off*/
-       unsigned char enable_IPX;
-       unsigned long network_number;
-       unsigned char pap;
-       unsigned char chap;
-       unsigned char sysname[31];              /* system name for in-bnd auth*/
-       unsigned char userid[511];              /* list of user ids */
-       unsigned char passwd[511];              /* list of passwords */
-       unsigned protocol;                      /* SKB Protocol */
-       u32 ip_local;                           /* Local IP Address */
-       u32 ip_remote;                          /* remote IP Address */
-
-       u32 ip_local_tmp;
-       u32 ip_remote_tmp;
-       
-       unsigned char timer_int_enabled;        /* Who enabled the timer inter*/
-       unsigned char update_comms_stats;       /* Used by update function */
-       unsigned long curr_trace_addr;          /* Trace information */
-       unsigned long start_trace_addr;
-       unsigned long end_trace_addr;
-
-       unsigned char interface_down;           /* Brind down interface when channel 
-                                                   goes down */
-       unsigned long config_wait_timeout;      /* After if_open() if in dynamic if mode,
-                                                  wait a few seconds before configuring */
-       
-       unsigned short udp_pkt_lgth;
-       char  udp_pkt_src;
-       char  udp_pkt_data[MAX_LGTH_UDP_MGNT_PKT];
-
-       /* PPP specific statistics */
-
-       if_send_stat_t if_send_stat;
-       rx_intr_stat_t rx_intr_stat;
-       pipe_mgmt_stat_t pipe_mgmt_stat;
-
-       unsigned long router_up_time; 
-
-       /* Polling work queue entry. Each interface
-         * has its own work queue entry, which is used
-         * to defer events from the interrupt */
-       struct work_struct poll_work;
-       struct timer_list poll_delay_timer;
-
-       u8 gateway;
-       u8 config_ppp;
-       u8 ip_error;
-       
-}ppp_private_area_t;
-
-/* variable for keeping track of enabling/disabling FT1 monitor status */
-static int rCount = 0;
-
-extern void disable_irq(unsigned int);
-extern void enable_irq(unsigned int);
-
-/****** Function Prototypes *************************************************/
-
-/* WAN link driver entry points. These are called by the WAN router module. */
-static int update(struct wan_device *wandev);
-static int new_if(struct wan_device *wandev, struct net_device *dev,
-                 wanif_conf_t *conf);
-static int del_if(struct wan_device *wandev, struct net_device *dev);
-
-/* WANPIPE-specific entry points */
-static int wpp_exec (struct sdla *card, void *u_cmd, void *u_data);
-
-/* Network device interface */
-static int if_init(struct net_device *dev);
-static int if_open(struct net_device *dev);
-static int if_close(struct net_device *dev);
-static int if_header(struct sk_buff *skb, struct net_device *dev,
-                    unsigned short type, 
-                    void *daddr, void *saddr, unsigned len);
-
-static void if_tx_timeout(struct net_device *dev);
-
-static int if_rebuild_hdr(struct sk_buff *skb);
-static struct net_device_stats *if_stats(struct net_device *dev);
-static int if_send(struct sk_buff *skb, struct net_device *dev);
-
-
-/* PPP firmware interface functions */
-static int ppp_read_version(sdla_t *card, char *str);
-static int ppp_set_outbnd_auth(sdla_t *card, ppp_private_area_t *ppp_priv_area);
-static int ppp_set_inbnd_auth(sdla_t *card, ppp_private_area_t *ppp_priv_area);
-static int ppp_configure(sdla_t *card, void *data);
-static int ppp_set_intr_mode(sdla_t *card, unsigned char mode);
-static int ppp_comm_enable(sdla_t *card);
-static int ppp_comm_disable(sdla_t *card);
-static int ppp_comm_disable_shutdown(sdla_t *card);
-static int ppp_get_err_stats(sdla_t *card);
-static int ppp_send(sdla_t *card, void *data, unsigned len, unsigned proto);
-static int ppp_error(sdla_t *card, int err, ppp_mbox_t *mb);
-
-static void wpp_isr(sdla_t *card);
-static void rx_intr(sdla_t *card);
-static void event_intr(sdla_t *card);
-static void timer_intr(sdla_t *card);
-
-/* Background polling routines */
-static void process_route(sdla_t *card);
-static void retrigger_comm(sdla_t *card);
-
-/* Miscellaneous functions */
-static int read_info( sdla_t *card );
-static int read_connection_info (sdla_t *card);
-static void remove_route( sdla_t *card );
-static int config508(struct net_device *dev, sdla_t *card);
-static void show_disc_cause(sdla_t * card, unsigned cause);
-static int reply_udp( unsigned char *data, unsigned int mbox_len );
-static void process_udp_mgmt_pkt(sdla_t *card, struct net_device *dev, 
-                               ppp_private_area_t *ppp_priv_area);
-static void init_ppp_tx_rx_buff( sdla_t *card );
-static int intr_test( sdla_t *card );
-static int udp_pkt_type( struct sk_buff *skb , sdla_t *card);
-static void init_ppp_priv_struct( ppp_private_area_t *ppp_priv_area);
-static void init_global_statistics( sdla_t *card );
-static int tokenize(char *str, char **tokens);
-static char* strstrip(char *str, char *s);
-static int chk_bcast_mcast_addr(sdla_t* card, struct net_device* dev,
-                               struct sk_buff *skb);
-
-static int config_ppp (sdla_t *);
-static void ppp_poll(struct net_device *dev);
-static void trigger_ppp_poll(struct net_device *dev);
-static void ppp_poll_delay (unsigned long dev_ptr);
-
-
-static int Read_connection_info;
-static int Intr_test_counter;
-static unsigned short available_buffer_space;
-
-
-/* IPX functions */
-static void switch_net_numbers(unsigned char *sendpacket, unsigned long network_number, 
-                              unsigned char incoming);
-static int handle_IPXWAN(unsigned char *sendpacket, char *devname, unsigned char enable_PX, 
-                        unsigned long network_number, unsigned short proto);
-
-/* Lock Functions */
-static void s508_lock (sdla_t *card, unsigned long *smp_flags);
-static void s508_unlock (sdla_t *card, unsigned long *smp_flags);
-
-static int store_udp_mgmt_pkt(char udp_pkt_src, sdla_t* card,
-                                struct sk_buff *skb, struct net_device* dev,
-                                ppp_private_area_t* ppp_priv_area );
-static unsigned short calc_checksum (char *data, int len);
-static void disable_comm (sdla_t *card);
-static int detect_and_fix_tx_bug (sdla_t *card);
-
-/****** Public Functions ****************************************************/
-
-/*============================================================================
- * PPP protocol initialization routine.
- *
- * This routine is called by the main WANPIPE module during setup.  At this
- * point adapter is completely initialized and firmware is running.
- *  o read firmware version (to make sure it's alive)
- *  o configure adapter
- *  o initialize protocol-specific fields of the adapter data space.
- *
- * Return:     0       o.k.
- *             < 0     failure.
- */
-int wpp_init(sdla_t *card, wandev_conf_t *conf)
-{
-       ppp_flags_t *flags;
-       union
-       {
-               char str[80];
-       } u;
-
-       /* Verify configuration ID */
-       if (conf->config_id != WANCONFIG_PPP) {
-               
-               printk(KERN_INFO "%s: invalid configuration ID %u!\n",
-                       card->devname, conf->config_id);
-               return -EINVAL;
-
-       }
-
-       /* Initialize miscellaneous pointers to structures on the adapter */
-       switch (card->hw.type) {
-
-               case SDLA_S508:
-                       card->mbox =(void*)(card->hw.dpmbase + PPP508_MB_OFFS);
-                       card->flags=(void*)(card->hw.dpmbase + PPP508_FLG_OFFS);
-                       break;
-               
-               case SDLA_S514:
-                       card->mbox =(void*)(card->hw.dpmbase + PPP514_MB_OFFS);
-                       card->flags=(void*)(card->hw.dpmbase + PPP514_FLG_OFFS);
-                       break;
-
-               default:
-                       return -EINVAL;
-
-       }
-       flags = card->flags;
-
-       /* Read firmware version.  Note that when adapter initializes, it
-        * clears the mailbox, so it may appear that the first command was
-        * executed successfully when in fact it was merely erased. To work
-        * around this, we execute the first command twice.
-        */
-       if (ppp_read_version(card, NULL) || ppp_read_version(card, u.str))
-               return -EIO;
-       
-       printk(KERN_INFO "%s: running PPP firmware v%s\n",card->devname, u.str); 
-       /* Adjust configuration and set defaults */
-       card->wandev.mtu = (conf->mtu) ?
-               min_t(unsigned int, conf->mtu, PPP_MAX_MTU) : PPP_DFLT_MTU;
-
-       card->wandev.bps        = conf->bps;
-       card->wandev.interface  = conf->interface;
-       card->wandev.clocking   = conf->clocking;
-       card->wandev.station    = conf->station;
-       card->isr               = &wpp_isr;
-       card->poll              = NULL; 
-       card->exec              = &wpp_exec;
-       card->wandev.update     = &update;
-       card->wandev.new_if     = &new_if;
-       card->wandev.del_if     = &del_if;
-        card->wandev.udp_port   = conf->udp_port;
-       card->wandev.ttl        = conf->ttl;
-       card->wandev.state      = WAN_DISCONNECTED;
-       card->disable_comm      = &disable_comm;
-       card->irq_dis_if_send_count = 0;
-        card->irq_dis_poll_count = 0;
-       card->u.p.authenticator = conf->u.ppp.authenticator;
-       card->u.p.ip_mode       = conf->u.ppp.ip_mode ?
-                                conf->u.ppp.ip_mode : WANOPT_PPP_STATIC;
-        card->TracingEnabled    = 0;
-       Read_connection_info    = 1;
-
-       /* initialize global statistics */
-       init_global_statistics( card );
-
-
-
-       if (!card->configured){
-               int err;
-
-               Intr_test_counter = 0;
-               err = intr_test(card);
-
-               if(err || (Intr_test_counter < MAX_INTR_TEST_COUNTER)) {
-                       printk("%s: Interrupt Test Failed, Counter: %i\n", 
-                               card->devname, Intr_test_counter);
-                       printk( "%s: Please choose another interrupt\n",card->devname);
-                       return -EIO;
-               }
-               
-               printk(KERN_INFO "%s: Interrupt Test Passed, Counter: %i\n", 
-                       card->devname, Intr_test_counter);
-               card->configured = 1;
-       }
-
-       ppp_set_intr_mode(card, PPP_INTR_TIMER); 
-
-       /* Turn off the transmit and timer interrupt */
-       flags->imask &= ~PPP_INTR_TIMER;
-
-       printk(KERN_INFO "\n");
-
-       return 0;
-}
-
-/******* WAN Device Driver Entry Points *************************************/
-
-/*============================================================================
- * Update device status & statistics.
- */
-static int update(struct wan_device *wandev)
-{
-       sdla_t* card = wandev->private;
-       struct net_device* dev;
-        volatile ppp_private_area_t *ppp_priv_area;
-       ppp_flags_t *flags = card->flags;
-       unsigned long timeout;
-
-       /* sanity checks */
-       if ((wandev == NULL) || (wandev->private == NULL))
-               return -EFAULT;
-       
-       if (wandev->state == WAN_UNCONFIGURED)
-               return -ENODEV;
-       
-       /* Shutdown bug fix. This function can be
-         * called with NULL dev pointer during
-         * shutdown 
-        */
-       if ((dev=card->wandev.dev) == NULL){
-               return -ENODEV;
-       }
-
-       if ((ppp_priv_area=dev->priv) == NULL){
-               return -ENODEV;
-       }
-       
-       ppp_priv_area->update_comms_stats = 2;
-       ppp_priv_area->timer_int_enabled |= TMR_INT_ENABLED_UPDATE;
-       flags->imask |= PPP_INTR_TIMER; 
-       
-       /* wait a maximum of 1 second for the statistics to be updated */ 
-        timeout = jiffies;
-        for(;;) {
-               if(ppp_priv_area->update_comms_stats == 0){
-                       break;
-               }
-                if (time_after(jiffies, timeout + 1 * HZ)){
-                       ppp_priv_area->update_comms_stats = 0;
-                       ppp_priv_area->timer_int_enabled &=
-                               ~TMR_INT_ENABLED_UPDATE; 
-                       return -EAGAIN;
-               }
-        }
-
-       return 0;
-}
-
-/*============================================================================
- * Create new logical channel.
- * This routine is called by the router when ROUTER_IFNEW IOCTL is being
- * handled.
- * o parse media- and hardware-specific configuration
- * o make sure that a new channel can be created
- * o allocate resources, if necessary
- * o prepare network device structure for registaration.
- *
- * Return:     0       o.k.
- *             < 0     failure (channel will not be created)
- */
-static int new_if(struct wan_device *wandev, struct net_device *dev,
-                 wanif_conf_t *conf)
-{
-       sdla_t *card = wandev->private;
-       ppp_private_area_t *ppp_priv_area;
-
-       if (wandev->ndev)
-               return -EEXIST;
-       
-
-       printk(KERN_INFO "%s: Configuring Interface: %s\n",
-                       card->devname, conf->name);
-
-       if ((conf->name[0] == '\0') || (strlen(conf->name) > WAN_IFNAME_SZ)) {
-
-               printk(KERN_INFO "%s: Invalid interface name!\n",
-                       card->devname);
-               return -EINVAL;
-
-       }
-
-       /* allocate and initialize private data */
-       ppp_priv_area = kmalloc(sizeof(ppp_private_area_t), GFP_KERNEL);
-       
-       if( ppp_priv_area == NULL )
-               return  -ENOMEM;
-       
-       memset(ppp_priv_area, 0, sizeof(ppp_private_area_t));
-       
-       ppp_priv_area->card = card; 
-       
-       /* initialize data */
-       strcpy(card->u.p.if_name, conf->name);
-
-       /* initialize data in ppp_private_area structure */
-       
-       init_ppp_priv_struct( ppp_priv_area );
-
-       ppp_priv_area->mc = conf->mc;
-       ppp_priv_area->pap = conf->pap;
-       ppp_priv_area->chap = conf->chap;
-
-       /* Option to bring down the interface when 
-         * the link goes down */
-       if (conf->if_down){
-               set_bit(DYN_OPT_ON,&ppp_priv_area->interface_down);
-               printk("%s: Dynamic interface configuration enabled\n",
-                       card->devname);
-       } 
-
-       /* If no user ids are specified */
-       if(!strlen(conf->userid) && (ppp_priv_area->pap||ppp_priv_area->chap)){
-               kfree(ppp_priv_area);
-               return -EINVAL;
-       }
-
-       /* If no passwords are specified */
-       if(!strlen(conf->passwd) && (ppp_priv_area->pap||ppp_priv_area->chap)){
-               kfree(ppp_priv_area);
-               return -EINVAL;
-       }
-
-       if(strlen(conf->sysname) > 31){
-               kfree(ppp_priv_area);
-               return -EINVAL;
-       }
-
-       /* If no system name is specified */
-       if(!strlen(conf->sysname) && (card->u.p.authenticator)){
-               kfree(ppp_priv_area);
-               return -EINVAL;
-       }
-
-       /* copy the data into the ppp private structure */
-       memcpy(ppp_priv_area->userid, conf->userid, strlen(conf->userid));
-       memcpy(ppp_priv_area->passwd, conf->passwd, strlen(conf->passwd));
-       memcpy(ppp_priv_area->sysname, conf->sysname, strlen(conf->sysname));
-
-       
-       ppp_priv_area->enable_IPX = conf->enable_IPX;
-       if (conf->network_number){
-               ppp_priv_area->network_number = conf->network_number;
-       }else{
-               ppp_priv_area->network_number = 0xDEADBEEF;
-       }
-
-       /* Tells us that if this interface is a
-         * gateway or not */
-       if ((ppp_priv_area->gateway = conf->gateway) == WANOPT_YES){
-               printk(KERN_INFO "%s: Interface %s is set as a gateway.\n",
-                       card->devname,card->u.p.if_name);
-       }
-
-       /* prepare network device data space for registration */
-       strcpy(dev->name,card->u.p.if_name);
-       
-       dev->init = &if_init;
-       dev->priv = ppp_priv_area;
-       dev->mtu = min_t(unsigned int, dev->mtu, card->wandev.mtu);
-
-       /* Initialize the polling work routine */
-       INIT_WORK(&ppp_priv_area->poll_work, (void*)(void*)ppp_poll, dev);
-
-       /* Initialize the polling delay timer */
-       init_timer(&ppp_priv_area->poll_delay_timer);
-       ppp_priv_area->poll_delay_timer.data = (unsigned long)dev;
-       ppp_priv_area->poll_delay_timer.function = ppp_poll_delay;
-       
-       
-       /* Since we start with dummy IP addresses we can say
-        * that route exists */
-       printk(KERN_INFO "\n");
-
-       return 0;
-}
-
-/*============================================================================
- * Delete logical channel.
- */
-static int del_if(struct wan_device *wandev, struct net_device *dev)
-{
-       return 0;
-}
-
-static void disable_comm (sdla_t *card)
-{
-       ppp_comm_disable_shutdown(card);
-       return;
-}
-
-/****** WANPIPE-specific entry points ***************************************/
-
-/*============================================================================
- * Execute adapter interface command.
- */
-
-//FIXME: Why do we need this ????
-static int wpp_exec(struct sdla *card, void *u_cmd, void *u_data)
-{
-       ppp_mbox_t *mbox = card->mbox;
-       int len;
-
-       if (copy_from_user((void*)&mbox->cmd, u_cmd, sizeof(ppp_cmd_t)))
-               return -EFAULT;
-
-       len = mbox->cmd.length;
-
-       if (len) {
-
-               if( copy_from_user((void*)&mbox->data, u_data, len))
-                       return -EFAULT;
-
-       }
-
-       /* execute command */
-       if (!sdla_exec(mbox))
-               return -EIO;
-
-       /* return result */
-       if( copy_to_user(u_cmd, (void*)&mbox->cmd, sizeof(ppp_cmd_t)))
-               return -EFAULT;
-       len = mbox->cmd.length;
-
-       if (len && u_data && copy_to_user(u_data, (void*)&mbox->data, len))
-               return -EFAULT;
-
-       return 0;
-}
-
-/****** Network Device Interface ********************************************/
-
-/*============================================================================
- * Initialize Linux network interface.
- *
- * This routine is called only once for each interface, during Linux network
- * interface registration.  Returning anything but zero will fail interface
- * registration.
- */
-static int if_init(struct net_device *dev)
-{
-       ppp_private_area_t *ppp_priv_area = dev->priv;
-       sdla_t *card = ppp_priv_area->card;
-       struct wan_device *wandev = &card->wandev;
-
-       /* Initialize device driver entry points */
-       dev->open               = &if_open;
-       dev->stop               = &if_close;
-       dev->hard_header        = &if_header;
-       dev->rebuild_header     = &if_rebuild_hdr;
-       dev->hard_start_xmit    = &if_send;
-       dev->get_stats          = &if_stats;
-       dev->tx_timeout         = &if_tx_timeout;
-       dev->watchdog_timeo     = TX_TIMEOUT;
-
-       /* Initialize media-specific parameters */
-       dev->type               = ARPHRD_PPP;   /* ARP h/w type */
-       dev->flags              |= IFF_POINTOPOINT;
-       dev->flags              |= IFF_NOARP;
-
-       /* Enable Mulitcasting if specified by user*/
-       if (ppp_priv_area->mc == WANOPT_YES){
-               dev->flags      |= IFF_MULTICAST;
-       }
-
-       dev->mtu                = wandev->mtu;
-       dev->hard_header_len    = PPP_HDR_LEN;  /* media header length */
-
-       /* Initialize hardware parameters (just for reference) */
-       dev->irq                = wandev->irq;
-       dev->dma                = wandev->dma;
-       dev->base_addr          = wandev->ioport;
-       dev->mem_start          = wandev->maddr;
-       dev->mem_end            = wandev->maddr + wandev->msize - 1;
-
-        /* Set transmit buffer queue length */
-        dev->tx_queue_len = 100;
-       SET_MODULE_OWNER(dev);
-   
-       return 0;
-}
-
-/*============================================================================
- * Open network interface.
- * o enable communications and interrupts.
- * o prevent module from unloading by incrementing use count
- *
- * Return 0 if O.k. or errno.
- */
-static int if_open(struct net_device *dev)
-{
-       ppp_private_area_t *ppp_priv_area = dev->priv;
-       sdla_t *card = ppp_priv_area->card;
-       struct timeval tv;
-       //unsigned long smp_flags;
-
-       if (netif_running(dev))
-               return -EBUSY;
-
-       wanpipe_open(card);
-
-       netif_start_queue(dev);
-       
-       do_gettimeofday( &tv );
-       ppp_priv_area->router_start_time = tv.tv_sec;
-
-       /* We cannot configure the card here because we don't
-        * have access to the interface IP addresses.
-         * Once the interface initilization is complete, we will be
-         * able to access the IP addresses.  Therefore,
-         * configure the ppp link in the poll routine */
-       set_bit(0,&ppp_priv_area->config_ppp);
-       ppp_priv_area->config_wait_timeout=jiffies;
-
-       /* Start the PPP configuration after 1sec delay.
-        * This will give the interface initilization time
-        * to finish its configuration */
-       mod_timer(&ppp_priv_area->poll_delay_timer, jiffies + HZ);
-       return 0;
-}
-
-/*============================================================================
- * Close network interface.
- * o if this is the last open, then disable communications and interrupts.
- * o reset flags.
- */
-static int if_close(struct net_device *dev)
-{
-       ppp_private_area_t *ppp_priv_area = dev->priv;
-       sdla_t *card = ppp_priv_area->card;
-
-       netif_stop_queue(dev);
-       wanpipe_close(card);
-
-       del_timer (&ppp_priv_area->poll_delay_timer);
-       return 0;
-}
-
-/*============================================================================
- * Build media header.
- *
- * The trick here is to put packet type (Ethertype) into 'protocol' field of
- * the socket buffer, so that we don't forget it.  If packet type is not
- * supported, set skb->protocol to 0 and discard packet later.
- *
- * Return:     media header length.
- */
-static int if_header(struct sk_buff *skb, struct net_device *dev,
-       unsigned short type, void *daddr, void *saddr, unsigned len)
-{
-       switch (type)
-       {
-               case ETH_P_IP:
-               case ETH_P_IPX:
-                       skb->protocol = htons(type);
-                       break;
-
-               default:
-                       skb->protocol = 0;
-       }
-
-       return PPP_HDR_LEN;
-}
-
-/*============================================================================
- * Re-build media header.
- *
- * Return:     1       physical address resolved.
- *             0       physical address not resolved
- */
-static int if_rebuild_hdr (struct sk_buff *skb)
-{
-       struct net_device *dev = skb->dev;
-       ppp_private_area_t *ppp_priv_area = dev->priv;
-       sdla_t *card = ppp_priv_area->card;
-
-       printk(KERN_INFO "%s: rebuild_header() called for interface %s!\n",
-               card->devname, dev->name);
-       return 1;
-}
-
-/*============================================================================
- * Handle transmit timeout event from netif watchdog
- */
-static void if_tx_timeout(struct net_device *dev)
-{
-       ppp_private_area_t* chan = dev->priv;
-       sdla_t *card = chan->card;
-       
-       /* If our device stays busy for at least 5 seconds then we will
-        * kick start the device by making dev->tbusy = 0.  We expect
-        * that our device never stays busy more than 5 seconds. So this                 
-        * is only used as a last resort.
-        */
-
-       ++ chan->if_send_stat.if_send_tbusy;
-       ++card->wandev.stats.collisions;
-
-       printk (KERN_INFO "%s: Transmit timed out on %s\n", card->devname,dev->name);
-       ++chan->if_send_stat.if_send_tbusy_timeout;
-       netif_wake_queue (dev);
-}
-
-
-
-/*============================================================================
- * Send a packet on a network interface.
- * o set tbusy flag (marks start of the transmission) to block a timer-based
- *   transmit from overlapping.
- * o check link state. If link is not up, then drop the packet.
- * o execute adapter send command.
- * o free socket buffer
- *
- * Return:     0       complete (socket buffer must be freed)
- *             non-0   packet may be re-transmitted (tbusy must be set)
- *
- * Notes:
- * 1. This routine is called either by the protocol stack or by the "net
- *    bottom half" (with interrupts enabled).
- * 2. Setting tbusy flag will inhibit further transmit requests from the
- *    protocol stack and can be used for flow control with protocol layer.
- */
-static int if_send (struct sk_buff *skb, struct net_device *dev)
-{
-       ppp_private_area_t *ppp_priv_area = dev->priv;
-       sdla_t *card = ppp_priv_area->card;
-       unsigned char *sendpacket;
-       unsigned long smp_flags;
-       ppp_flags_t *flags = card->flags;
-       int udp_type;
-       int err=0;
-       
-       ++ppp_priv_area->if_send_stat.if_send_entry;
-
-       netif_stop_queue(dev);
-       
-       if (skb == NULL) {
-
-               /* If we get here, some higher layer thinks we've missed an
-                * tx-done interrupt.
-                */
-               printk(KERN_INFO "%s: interface %s got kicked!\n",
-                       card->devname, dev->name);
-               
-               ++ppp_priv_area->if_send_stat.if_send_skb_null;
-       
-               netif_wake_queue(dev);
-               return 0;
-       }
-
-       sendpacket = skb->data;
-
-       udp_type = udp_pkt_type( skb, card );
-
-
-       if (udp_type == UDP_PTPIPE_TYPE){
-               if(store_udp_mgmt_pkt(UDP_PKT_FRM_STACK, card, skb, dev,
-                                     ppp_priv_area)){
-                       flags->imask |= PPP_INTR_TIMER;
-               }
-               ++ppp_priv_area->if_send_stat.if_send_PIPE_request;
-               netif_start_queue(dev);
-               return 0;
-       }
-
-       /* Check for broadcast and multicast addresses 
-        * If found, drop (deallocate) a packet and return.
-        */
-       if(chk_bcast_mcast_addr(card, dev, skb)){
-               ++card->wandev.stats.tx_dropped;
-               dev_kfree_skb_any(skb);
-               netif_start_queue(dev);
-               return 0;
-       }
-
-
-       if(card->hw.type != SDLA_S514){
-               s508_lock(card,&smp_flags);
-       }
-
-       if (test_and_set_bit(SEND_CRIT, (void*)&card->wandev.critical)) {
-
-               printk(KERN_INFO "%s: Critical in if_send: %lx\n",
-                               card->wandev.name,card->wandev.critical);
-               
-               ++card->wandev.stats.tx_dropped;
-               ++ppp_priv_area->if_send_stat.if_send_critical_non_ISR;
-               netif_start_queue(dev);
-               goto if_send_exit_crit;
-       }
-
-       if (card->wandev.state != WAN_CONNECTED) {
-
-               ++ppp_priv_area->if_send_stat.if_send_wan_disconnected;
-               ++card->wandev.stats.tx_dropped;
-               netif_start_queue(dev);
-               
-       } else if (!skb->protocol) {
-               ++ppp_priv_area->if_send_stat.if_send_protocol_error;
-               ++card->wandev.stats.tx_errors;
-               netif_start_queue(dev);
-               
-       } else {
-
-               /*If it's IPX change the network numbers to 0 if they're ours.*/
-               if( skb->protocol == htons(ETH_P_IPX) ) {
-                       if(ppp_priv_area->enable_IPX) {
-                               switch_net_numbers( skb->data, 
-                                       ppp_priv_area->network_number, 0);
-                       } else {
-                               ++card->wandev.stats.tx_dropped;
-                               netif_start_queue(dev);
-                               goto if_send_exit_crit;
-                       }
-               }
-
-               if (ppp_send(card, skb->data, skb->len, skb->protocol)) {
-                       netif_stop_queue(dev);
-                       ++ppp_priv_area->if_send_stat.if_send_adptr_bfrs_full;
-                       ++ppp_priv_area->if_send_stat.if_send_tx_int_enabled;
-               } else {
-                       ++ppp_priv_area->if_send_stat.if_send_bfr_passed_to_adptr;
-                       ++card->wandev.stats.tx_packets;
-                       card->wandev.stats.tx_bytes += skb->len;
-                       netif_start_queue(dev);
-                       dev->trans_start = jiffies;
-               }
-       }
-       
-if_send_exit_crit:
-       
-       if (!(err=netif_queue_stopped(dev))){
-               dev_kfree_skb_any(skb);
-       }else{
-               ppp_priv_area->tick_counter = jiffies;
-               flags->imask |= PPP_INTR_TXRDY; /* unmask Tx interrupts */
-       }
-       
-       clear_bit(SEND_CRIT,&card->wandev.critical);
-       if(card->hw.type != SDLA_S514){ 
-               s508_unlock(card,&smp_flags);
-       }
-
-       return err;
-}
-
-
-/*=============================================================================
- * Store a UDP management packet for later processing.
- */
-
-static int store_udp_mgmt_pkt(char udp_pkt_src, sdla_t* card,
-                                struct sk_buff *skb, struct net_device* dev,
-                                ppp_private_area_t* ppp_priv_area )
-{
-       int udp_pkt_stored = 0;
-
-       if(!ppp_priv_area->udp_pkt_lgth && (skb->len<=MAX_LGTH_UDP_MGNT_PKT)){
-               ppp_priv_area->udp_pkt_lgth = skb->len;
-               ppp_priv_area->udp_pkt_src = udp_pkt_src;
-                       memcpy(ppp_priv_area->udp_pkt_data, skb->data, skb->len);
-               ppp_priv_area->timer_int_enabled |= TMR_INT_ENABLED_UDP;
-               ppp_priv_area->protocol = skb->protocol;
-               udp_pkt_stored = 1;
-       }else{
-               if (skb->len > MAX_LGTH_UDP_MGNT_PKT){
-                       printk(KERN_INFO "%s: PIPEMON UDP request too long : %i\n",
-                               card->devname, skb->len);
-               }else{
-                       printk(KERN_INFO "%s: PIPEMON UPD request already pending\n",
-                               card->devname);
-               }
-               ppp_priv_area->udp_pkt_lgth = 0;
-       }
-
-       if(udp_pkt_src == UDP_PKT_FRM_STACK){
-               dev_kfree_skb_any(skb);
-       }else{
-                dev_kfree_skb_any(skb);
-       }
-
-       return(udp_pkt_stored);
-}
-
-
-
-/*============================================================================
- * Reply to UDP Management system.
- * Return length of reply.
- */
-static int reply_udp( unsigned char *data, unsigned int mbox_len ) 
-{
-       unsigned short len, udp_length, temp, ip_length;
-       unsigned long ip_temp;
-       int even_bound = 0;
-       ppp_udp_pkt_t *p_udp_pkt = (ppp_udp_pkt_t *)data;
-       /* Set length of packet */
-       len = sizeof(ip_pkt_t)+ 
-             sizeof(udp_pkt_t)+
-             sizeof(wp_mgmt_t)+
-             sizeof(cblock_t)+
-             mbox_len;
-
-       /* fill in UDP reply */
-       p_udp_pkt->wp_mgmt.request_reply = UDPMGMT_REPLY; 
-
-       /* fill in UDP length */
-       udp_length = sizeof(udp_pkt_t)+ 
-                    sizeof(wp_mgmt_t)+
-                    sizeof(cblock_t)+
-                    mbox_len; 
-  
-       /* put it on an even boundary */
-       if ( udp_length & 0x0001 ) {
-               udp_length += 1;
-               len += 1;
-               even_bound=1;
-       } 
-       
-       temp = (udp_length<<8)|(udp_length>>8);
-       p_udp_pkt->udp_pkt.udp_length = temp;           
-
-       /* swap UDP ports */
-       temp = p_udp_pkt->udp_pkt.udp_src_port;
-       p_udp_pkt->udp_pkt.udp_src_port = 
-                       p_udp_pkt->udp_pkt.udp_dst_port; 
-       p_udp_pkt->udp_pkt.udp_dst_port = temp;
-
-
-       /* add UDP pseudo header */
-       temp = 0x1100;
-       *((unsigned short *)(p_udp_pkt->data+mbox_len+even_bound)) = temp;
-       temp = (udp_length<<8)|(udp_length>>8);
-       *((unsigned short *)(p_udp_pkt->data+mbox_len+even_bound+2)) = temp;
-       /* calculate UDP checksum */
-       p_udp_pkt->udp_pkt.udp_checksum = 0;
-       p_udp_pkt->udp_pkt.udp_checksum = 
-               calc_checksum(&data[UDP_OFFSET],udp_length+UDP_OFFSET);
-
-       /* fill in IP length */
-       ip_length = udp_length + sizeof(ip_pkt_t);
-       temp = (ip_length<<8)|(ip_length>>8);
-       p_udp_pkt->ip_pkt.total_length = temp;
-       /* swap IP addresses */
-       ip_temp = p_udp_pkt->ip_pkt.ip_src_address;
-       p_udp_pkt->ip_pkt.ip_src_address = p_udp_pkt->ip_pkt.ip_dst_address;
-       p_udp_pkt->ip_pkt.ip_dst_address = ip_temp;
-
-       /* fill in IP checksum */
-       p_udp_pkt->ip_pkt.hdr_checksum = 0;
-       p_udp_pkt->ip_pkt.hdr_checksum = calc_checksum(data,sizeof(ip_pkt_t));
-
-       return len;
-
-} /* reply_udp */
-
-unsigned short calc_checksum (char *data, int len)
-{
-       unsigned short temp; 
-       unsigned long sum=0;
-       int i;
-
-       for( i = 0; i <len; i+=2 ) {
-               memcpy(&temp,&data[i],2);
-               sum += (unsigned long)temp;
-       }
-
-       while (sum >> 16 ) {
-               sum = (sum & 0xffffUL) + (sum >> 16);
-       }
-
-       temp = (unsigned short)sum;
-       temp = ~temp;
-
-       if( temp == 0 ) 
-               temp = 0xffff;
-
-       return temp;    
-}
-
-/*
-   If incoming is 0 (outgoing)- if the net numbers is ours make it 0
-   if incoming is 1 - if the net number is 0 make it ours 
-
-*/
-static void switch_net_numbers(unsigned char *sendpacket, unsigned long network_number, unsigned char incoming)
-{
-       unsigned long pnetwork_number;
-
-       pnetwork_number = (unsigned long)((sendpacket[6] << 24) + 
-                         (sendpacket[7] << 16) + (sendpacket[8] << 8) + 
-                         sendpacket[9]);
-
-       if (!incoming) {
-               //If the destination network number is ours, make it 0
-               if( pnetwork_number == network_number) {
-                       sendpacket[6] = sendpacket[7] = sendpacket[8] = 
-                                        sendpacket[9] = 0x00;
-               }
-       } else {
-               //If the incoming network is 0, make it ours
-               if( pnetwork_number == 0) {
-                       sendpacket[6] = (unsigned char)(network_number >> 24);
-                       sendpacket[7] = (unsigned char)((network_number & 
-                                        0x00FF0000) >> 16);
-                       sendpacket[8] = (unsigned char)((network_number & 
-                                        0x0000FF00) >> 8);
-                       sendpacket[9] = (unsigned char)(network_number & 
-                                        0x000000FF);
-               }
-       }
-
-
-       pnetwork_number = (unsigned long)((sendpacket[18] << 24) + 
-                         (sendpacket[19] << 16) + (sendpacket[20] << 8) + 
-                         sendpacket[21]);
-
-       if( !incoming ) {
-               //If the source network is ours, make it 0
-               if( pnetwork_number == network_number) {
-                       sendpacket[18] = sendpacket[19] = sendpacket[20] = 
-                                        sendpacket[21] = 0x00;
-               }
-       } else {
-               //If the source network is 0, make it ours
-               if( pnetwork_number == 0 ) {
-                       sendpacket[18] = (unsigned char)(network_number >> 24);
-                       sendpacket[19] = (unsigned char)((network_number & 
-                                        0x00FF0000) >> 16);
-                       sendpacket[20] = (unsigned char)((network_number & 
-                                        0x0000FF00) >> 8);
-                       sendpacket[21] = (unsigned char)(network_number & 
-                                        0x000000FF);
-               }
-       }
-} /* switch_net_numbers */
-
-/*============================================================================
- * Get ethernet-style interface statistics.
- * Return a pointer to struct net_device_stats.
- */
-static struct net_device_stats *if_stats(struct net_device *dev)
-{
-
-       ppp_private_area_t *ppp_priv_area = dev->priv;
-       sdla_t* card;
-       
-       if( ppp_priv_area == NULL )
-               return NULL;
-
-       card = ppp_priv_area->card;
-       return &card->wandev.stats;
-}
-
-/****** PPP Firmware Interface Functions ************************************/
-
-/*============================================================================
- * Read firmware code version.
- *     Put code version as ASCII string in str. 
- */
-static int ppp_read_version(sdla_t *card, char *str)
-{
-       ppp_mbox_t *mb = card->mbox;
-       int err;
-
-       memset(&mb->cmd, 0, sizeof(ppp_cmd_t));
-       mb->cmd.command = PPP_READ_CODE_VERSION;
-       err = sdla_exec(mb) ? mb->cmd.result : CMD_TIMEOUT;
-
-       if (err != CMD_OK)
-               ppp_error(card, err, mb);
-
-       else if (str) {
-
-               int len = mb->cmd.length;
-
-               memcpy(str, mb->data, len);
-               str[len] = '\0';
-
-       }
-
-       return err;
-}
-/*===========================================================================
- * Set Out-Bound Authentication.
-*/
-static int ppp_set_outbnd_auth (sdla_t *card, ppp_private_area_t *ppp_priv_area)
-{
-       ppp_mbox_t *mb = card->mbox;
-       int err;
-
-       memset(&mb->cmd, 0, sizeof(ppp_cmd_t));
-       memset(&mb->data, 0, (strlen(ppp_priv_area->userid) + 
-                                       strlen(ppp_priv_area->passwd) + 2 ) );
-       memcpy(mb->data, ppp_priv_area->userid, strlen(ppp_priv_area->userid));
-       memcpy((mb->data + strlen(ppp_priv_area->userid) + 1), 
-               ppp_priv_area->passwd, strlen(ppp_priv_area->passwd));  
-       
-       mb->cmd.length  = strlen(ppp_priv_area->userid) + 
-                                       strlen(ppp_priv_area->passwd) + 2 ;
-       
-       mb->cmd.command = PPP_SET_OUTBOUND_AUTH;
-
-       err = sdla_exec(mb) ? mb->cmd.result : CMD_TIMEOUT;
-
-       if (err != CMD_OK)
-               ppp_error(card, err, mb);
-
-       return err;
-}
-
-/*===========================================================================
- * Set In-Bound Authentication.
-*/
-static int ppp_set_inbnd_auth (sdla_t *card, ppp_private_area_t *ppp_priv_area)
-{
-       ppp_mbox_t *mb = card->mbox;
-       int err, i;
-       char* user_tokens[32];
-       char* pass_tokens[32];
-       int userids, passwds;
-       int add_ptr;
-
-       memset(&mb->cmd, 0, sizeof(ppp_cmd_t));
-       memset(&mb->data, 0, 1008);
-       memcpy(mb->data, ppp_priv_area->sysname, 
-                                               strlen(ppp_priv_area->sysname));
-       
-       /* Parse the userid string and the password string and build a string
-          to copy it to the data area of the command structure.   The string
-          will look like "SYS_NAME<NULL>USER1<NULL>PASS1<NULL>USER2<NULL>PASS2
-          ....<NULL> " 
-        */
-       userids = tokenize( ppp_priv_area->userid, user_tokens);
-       passwds = tokenize( ppp_priv_area->passwd, pass_tokens);
-       
-       if (userids != passwds){
-               printk(KERN_INFO "%s: Number of passwords does not equal the number of user ids\n", card->devname);
-               return 1;       
-       }
-
-       add_ptr = strlen(ppp_priv_area->sysname) + 1;
-       for (i=0; i<userids; i++){
-               memcpy((mb->data + add_ptr), user_tokens[i], 
-                                                       strlen(user_tokens[i]));
-               memcpy((mb->data + add_ptr + strlen(user_tokens[i]) + 1), 
-                                       pass_tokens[i], strlen(pass_tokens[i]));
-               add_ptr = add_ptr + strlen(user_tokens[i]) + 1 + 
-                                               strlen(pass_tokens[i]) + 1;
-       }
-
-       mb->cmd.length  = add_ptr + 1;
-       mb->cmd.command = PPP_SET_INBOUND_AUTH;
-
-       err = sdla_exec(mb) ? mb->cmd.result : CMD_TIMEOUT;
-
-       if (err != CMD_OK)
-               ppp_error(card, err, mb);
-
-       return err;
-}
-
-
-/*============================================================================
- * Tokenize string.
- *      Parse a string of the following syntax:
- *              <arg1>,<arg2>,...
- *      and fill array of tokens with pointers to string elements.
- *
- */
-static int tokenize (char *str, char **tokens)
-{
-        int cnt = 0;
-
-        tokens[0] = strsep(&str, "/");
-        while (tokens[cnt] && (cnt < 32 - 1))
-        {
-                tokens[cnt] = strstrip(tokens[cnt], " \t");
-                tokens[++cnt] = strsep(&str, "/");
-        }
-       return cnt;
-}
-
-/*============================================================================
- * Strip leading and trailing spaces off the string str.
- */
-static char* strstrip (char *str, char* s)
-{
-        char *eos = str + strlen(str);          /* -> end of string */
-
-        while (*str && strchr(s, *str))
-                ++str                           /* strip leading spaces */
-        ;
-        while ((eos > str) && strchr(s, *(eos - 1)))
-                --eos                           /* strip trailing spaces */
-        ;
-        *eos = '\0';
-        return str;
-}
-/*============================================================================
- * Configure PPP firmware.
- */
-static int ppp_configure(sdla_t *card, void *data)
-{
-       ppp_mbox_t *mb = card->mbox;
-       int data_len = sizeof(ppp508_conf_t); 
-       int err;
-
-       memset(&mb->cmd, 0, sizeof(ppp_cmd_t));
-       memcpy(mb->data, data, data_len);
-       mb->cmd.length  = data_len;
-       mb->cmd.command = PPP_SET_CONFIG;
-       err = sdla_exec(mb) ? mb->cmd.result : CMD_TIMEOUT;
-
-       if (err != CMD_OK) 
-               ppp_error(card, err, mb);
-       
-       return err;
-}
-
-/*============================================================================
- * Set interrupt mode.
- */
-static int ppp_set_intr_mode(sdla_t *card, unsigned char mode)
-{
-       ppp_mbox_t *mb = card->mbox;
-        ppp_intr_info_t *ppp_intr_data = (ppp_intr_info_t *) &mb->data[0];
-       int err;
-
-       memset(&mb->cmd, 0, sizeof(ppp_cmd_t));
-       ppp_intr_data->i_enable = mode;
-
-       ppp_intr_data->irq = card->hw.irq;
-       mb->cmd.length = 2;
-
-       /* If timer has been enabled, set the timer delay to 1sec */
-       if (mode & 0x80){
-                       ppp_intr_data->timer_len = 250; //5;//100; //250;
-                mb->cmd.length = 4;
-        }
-       
-       mb->cmd.command = PPP_SET_INTR_FLAGS;
-       err = sdla_exec(mb) ? mb->cmd.result : CMD_TIMEOUT;
-       
-       if (err != CMD_OK) 
-               ppp_error(card, err, mb);
-               
-
-       return err;
-}
-
-/*============================================================================
- * Enable communications.
- */
-static int ppp_comm_enable(sdla_t *card)
-{
-       ppp_mbox_t *mb = card->mbox;
-       int err;
-
-       memset(&mb->cmd, 0, sizeof(ppp_cmd_t));
-       mb->cmd.command = PPP_COMM_ENABLE;
-       err = sdla_exec(mb) ? mb->cmd.result : CMD_TIMEOUT;
-       
-       if (err != CMD_OK) 
-               ppp_error(card, err, mb);
-       else    
-               card->u.p.comm_enabled = 1;     
-
-       return err;
-}
-
-/*============================================================================
- * Disable communications.
- */
-static int ppp_comm_disable(sdla_t *card)
-{
-       ppp_mbox_t *mb = card->mbox;
-       int err;
-
-       memset(&mb->cmd, 0, sizeof(ppp_cmd_t));
-       mb->cmd.command = PPP_COMM_DISABLE;
-       err = sdla_exec(mb) ? mb->cmd.result : CMD_TIMEOUT;
-       if (err != CMD_OK) 
-               ppp_error(card, err, mb);
-       else
-               card->u.p.comm_enabled = 0;
-
-       return err;
-}
-
-static int ppp_comm_disable_shutdown(sdla_t *card)
-{
-       ppp_mbox_t *mb = card->mbox;
-       ppp_intr_info_t *ppp_intr_data;
-       int err;
-
-       if (!mb){
-               return 1;
-       }
-       
-       ppp_intr_data = (ppp_intr_info_t *) &mb->data[0];
-       
-       /* Disable all interrupts */
-       memset(&mb->cmd, 0, sizeof(ppp_cmd_t));
-       ppp_intr_data->i_enable = 0;
-
-       ppp_intr_data->irq = card->hw.irq;
-       mb->cmd.length = 2;
-
-       mb->cmd.command = PPP_SET_INTR_FLAGS;
-       err = sdla_exec(mb) ? mb->cmd.result : CMD_TIMEOUT;
-
-       /* Disable communicatinons */
-       memset(&mb->cmd, 0, sizeof(ppp_cmd_t));
-       mb->cmd.command = PPP_COMM_DISABLE;
-       err = sdla_exec(mb) ? mb->cmd.result : CMD_TIMEOUT;
-
-       card->u.p.comm_enabled = 0;
-
-       return 0;
-}
-
-
-
-/*============================================================================
- * Get communications error statistics.
- */
-static int ppp_get_err_stats(sdla_t *card)
-{
-       ppp_mbox_t *mb = card->mbox;
-       int err;
-
-       memset(&mb->cmd, 0, sizeof(ppp_cmd_t));
-       mb->cmd.command = PPP_READ_ERROR_STATS;
-       err = sdla_exec(mb) ? mb->cmd.result : CMD_TIMEOUT;
-       
-       if (err == CMD_OK) {
-               
-               ppp_err_stats_t* stats = (void*)mb->data;
-               card->wandev.stats.rx_over_errors    = stats->rx_overrun;
-               card->wandev.stats.rx_crc_errors     = stats->rx_bad_crc;
-               card->wandev.stats.rx_missed_errors  = stats->rx_abort;
-               card->wandev.stats.rx_length_errors  = stats->rx_lost;
-               card->wandev.stats.tx_aborted_errors = stats->tx_abort;
-       
-       } else 
-               ppp_error(card, err, mb);
-       
-       return err;
-}
-
-/*============================================================================
- * Send packet.
- *     Return: 0 - o.k.
- *             1 - no transmit buffers available
- */
-static int ppp_send (sdla_t *card, void *data, unsigned len, unsigned proto)
-{
-       ppp_buf_ctl_t *txbuf = card->u.p.txbuf;
-
-       if (txbuf->flag)
-                return 1;
-       
-       sdla_poke(&card->hw, txbuf->buf.ptr, data, len);
-
-       txbuf->length = len;            /* frame length */
-       
-       if (proto == htons(ETH_P_IPX))
-               txbuf->proto = 0x01;    /* protocol ID */
-       else
-               txbuf->proto = 0x00;    /* protocol ID */
-       
-       txbuf->flag = 1;                /* start transmission */
-
-       /* Update transmit buffer control fields */
-       card->u.p.txbuf = ++txbuf;
-
-       if ((void*)txbuf > card->u.p.txbuf_last)
-               card->u.p.txbuf = card->u.p.txbuf_base;
-
-       return 0;
-}
-
-/****** Firmware Error Handler **********************************************/
-
-/*============================================================================
- * Firmware error handler.
- *     This routine is called whenever firmware command returns non-zero
- *     return code.
- *
- * Return zero if previous command has to be cancelled.
- */
-static int ppp_error(sdla_t *card, int err, ppp_mbox_t *mb)
-{
-       unsigned cmd = mb->cmd.command;
-
-       switch (err) {
-
-               case CMD_TIMEOUT:
-                       printk(KERN_ERR "%s: command 0x%02X timed out!\n",
-                               card->devname, cmd);
-                       break;
-
-               default:
-                       printk(KERN_INFO "%s: command 0x%02X returned 0x%02X!\n"
-                               , card->devname, cmd, err);
-       }
-
-       return 0;
-}
-
-/****** Interrupt Handlers **************************************************/
-
-/*============================================================================
- * PPP interrupt service routine.
- */
-static void wpp_isr (sdla_t *card)
-{
-       ppp_flags_t *flags = card->flags;
-       char *ptr = &flags->iflag;
-       struct net_device *dev = card->wandev.dev;
-       int i;
-
-       card->in_isr = 1;
-       ++card->statistics.isr_entry;
-
-       if (!dev && flags->iflag != PPP_INTR_CMD){
-               card->in_isr = 0;
-               flags->iflag = 0;
-               return;
-       }
-       
-       if (test_bit(PERI_CRIT, (void*)&card->wandev.critical)) {
-               card->in_isr = 0;
-               flags->iflag = 0;
-               return;
-       }
-       
-       
-       if(card->hw.type != SDLA_S514){
-               if (test_bit(SEND_CRIT, (void*)&card->wandev.critical)) {
-                       ++card->statistics.isr_already_critical;
-                       printk (KERN_INFO "%s: Critical while in ISR!\n",
-                                       card->devname);
-                       card->in_isr = 0;
-                       flags->iflag = 0;
-                       return;
-               }
-       }
-
-       switch (flags->iflag) {
-
-               case PPP_INTR_RXRDY:    /* receive interrupt  0x01  (bit 0)*/
-                       ++card->statistics.isr_rx;
-                       rx_intr(card);
-                       break;
-
-               case PPP_INTR_TXRDY:    /* transmit interrupt  0x02 (bit 1)*/
-                       ++card->statistics.isr_tx;
-                       flags->imask &= ~PPP_INTR_TXRDY;
-                       netif_wake_queue(dev);
-                       break;
-
-               case PPP_INTR_CMD:      /* interface command completed */
-                       ++Intr_test_counter;
-                       ++card->statistics.isr_intr_test;
-                       break;
-
-               case PPP_INTR_MODEM:    /* modem status change (DCD, CTS) 0x04 (bit 2)*/
-               case PPP_INTR_DISC:     /* Data link disconnected 0x10  (bit 4)*/       
-               case PPP_INTR_OPEN:     /* Data link open 0x20  (bit 5)*/
-               case PPP_INTR_DROP_DTR: /* DTR drop timeout expired  0x40 bit 6 */
-                       event_intr(card);
-                       break;
-       
-               case PPP_INTR_TIMER:
-                       timer_intr(card);
-                       break;   
-
-               default:        /* unexpected interrupt */
-                       ++card->statistics.isr_spurious;
-                       printk(KERN_INFO "%s: spurious interrupt 0x%02X!\n", 
-                               card->devname, flags->iflag);
-                       printk(KERN_INFO "%s: ID Bytes = ",card->devname);
-                       for(i = 0; i < 8; i ++)
-                               printk(KERN_INFO "0x%02X ", *(ptr + 0x28 + i));
-                       printk(KERN_INFO "\n"); 
-       }
-       
-       card->in_isr = 0;
-       flags->iflag = 0;
-       return;
-}
-
-/*============================================================================
- * Receive interrupt handler.
- */
-static void rx_intr(sdla_t *card)
-{
-       ppp_buf_ctl_t *rxbuf = card->rxmb;
-       struct net_device *dev = card->wandev.dev;
-       ppp_private_area_t *ppp_priv_area;
-       struct sk_buff *skb;
-       unsigned len;
-       void *buf;
-       int i;
-        ppp_flags_t *flags = card->flags;
-        char *ptr = &flags->iflag;
-       int udp_type;
-       
-
-       if (rxbuf->flag != 0x01) {
-
-               printk(KERN_INFO 
-                       "%s: corrupted Rx buffer @ 0x%X, flag = 0x%02X!\n", 
-                       card->devname, (unsigned)rxbuf, rxbuf->flag);
-       
-               printk(KERN_INFO "%s: ID Bytes = ",card->devname);
-               
-               for(i = 0; i < 8; i ++)
-                       printk(KERN_INFO "0x%02X ", *(ptr + 0x28 + i));
-               printk(KERN_INFO "\n"); 
-               
-               ++card->statistics.rx_intr_corrupt_rx_bfr;
-
-
-               /* Bug Fix: Mar 6 2000
-                 * If we get a corrupted mailbox, it means that driver 
-                 * is out of sync with the firmware. There is no recovery.
-                 * If we don't turn off all interrupts for this card
-                 * the machine will crash. 
-                 */
-               printk(KERN_INFO "%s: Critical router failure ...!!!\n", card->devname);
-               printk(KERN_INFO "Please contact Sangoma Technologies !\n");
-               ppp_set_intr_mode(card,0);
-               return;
-       }
-      
-       if (dev && netif_running(dev) && dev->priv){
-       
-               len  = rxbuf->length;
-               ppp_priv_area = dev->priv;
-
-               /* Allocate socket buffer */
-               skb = dev_alloc_skb(len);
-
-               if (skb != NULL) {
-               
-                       /* Copy data to the socket buffer */
-                       unsigned addr = rxbuf->buf.ptr;
-
-                       if ((addr + len) > card->u.p.rx_top + 1) {
-                       
-                               unsigned tmp = card->u.p.rx_top - addr + 1;
-                               buf = skb_put(skb, tmp);
-                               sdla_peek(&card->hw, addr, buf, tmp);
-                               addr = card->u.p.rx_base;
-                               len -= tmp;
-                       }
-                       buf = skb_put(skb, len);
-                       sdla_peek(&card->hw, addr, buf, len);
-
-                       /* Decapsulate packet */
-                       switch (rxbuf->proto) {
-       
-                               case 0x00:
-                                       skb->protocol = htons(ETH_P_IP);
-                                       break;
-
-                               case 0x01:
-                                       skb->protocol = htons(ETH_P_IPX);
-                                       break;
-                       }
-
-                       udp_type = udp_pkt_type( skb, card );
-
-                       if (udp_type == UDP_PTPIPE_TYPE){
-
-                               /* Handle a UDP Request in Timer Interrupt */
-                               if(store_udp_mgmt_pkt(UDP_PKT_FRM_NETWORK, card, skb, dev,
-                                                       ppp_priv_area)){
-                                       flags->imask |= PPP_INTR_TIMER;
-                               }
-                               ++ppp_priv_area->rx_intr_stat.rx_intr_PIPE_request;
-
-
-                       } else if (handle_IPXWAN(skb->data,card->devname, 
-                                                ppp_priv_area->enable_IPX, 
-                                                ppp_priv_area->network_number, 
-                                                skb->protocol)) {
-                       
-                               /* Handle an IPXWAN packet */
-                               if( ppp_priv_area->enable_IPX) {
-                                       
-                                       /* Make sure we are not already sending */
-                                       if (!test_bit(SEND_CRIT, &card->wandev.critical)){
-                                               ppp_send(card, skb->data, skb->len, htons(ETH_P_IPX));
-                                       }
-                                       dev_kfree_skb_any(skb);
-
-                               } else {
-                                       ++card->wandev.stats.rx_dropped;
-                               }
-                       } else {
-                               /* Pass data up the protocol stack */
-                               skb->dev = dev;
-                               skb->mac.raw  = skb->data;
-
-                               ++card->wandev.stats.rx_packets;
-                               card->wandev.stats.rx_bytes += skb->len;
-                               ++ppp_priv_area->rx_intr_stat.rx_intr_bfr_passed_to_stack;      
-                               netif_rx(skb);
-                               dev->last_rx = jiffies;
-                       }
-
-               } else {
-       
-                       if (net_ratelimit()){
-                               printk(KERN_INFO "%s: no socket buffers available!\n",
-                                       card->devname);
-                       }
-                       ++card->wandev.stats.rx_dropped;
-                       ++ppp_priv_area->rx_intr_stat.rx_intr_no_socket;
-               }
-
-       } else {
-               ++card->statistics.rx_intr_dev_not_started;
-       }
-
-       /* Release buffer element and calculate a pointer to the next one */
-       rxbuf->flag = 0x00;
-       card->rxmb = ++rxbuf;
-       if ((void*)rxbuf > card->u.p.rxbuf_last)
-               card->rxmb = card->u.p.rxbuf_base;
-}
-
-
-void event_intr (sdla_t *card)
-{
-
-       struct net_device* dev = card->wandev.dev;
-        ppp_private_area_t* ppp_priv_area = dev->priv;
-       volatile ppp_flags_t *flags = card->flags;
-
-       switch (flags->iflag){
-
-               case PPP_INTR_MODEM:    /* modem status change (DCD, CTS) 0x04  (bit 2)*/
-
-                       if (net_ratelimit()){
-                               printk (KERN_INFO "%s: Modem status: DCD=%s CTS=%s\n",
-                                       card->devname, DCD(flags->mstatus), CTS(flags->mstatus));
-                       }
-                       break;
-
-               case PPP_INTR_DISC:     /* Data link disconnected 0x10  (bit 4)*/       
-
-                       NEX_PRINTK (KERN_INFO "Data link disconnected intr Cause %X\n",
-                                              flags->disc_cause);
-
-                       if (flags->disc_cause &
-                               (PPP_LOCAL_TERMINATION | PPP_DCD_CTS_DROP |
-                               PPP_REMOTE_TERMINATION)) {
-
-                               if (card->u.p.ip_mode == WANOPT_PPP_PEER) { 
-                                       set_bit(0,&Read_connection_info);
-                               }
-                               wanpipe_set_state(card, WAN_DISCONNECTED);
-
-                               show_disc_cause(card, flags->disc_cause);
-                               ppp_priv_area->timer_int_enabled |= TMR_INT_ENABLED_PPP_EVENT;
-                               flags->imask |= PPP_INTR_TIMER;
-                               trigger_ppp_poll(dev);
-                       }
-                       break;
-
-               case PPP_INTR_OPEN:     /* Data link open 0x20  (bit 5)*/
-
-                       NEX_PRINTK (KERN_INFO "%s: PPP Link Open, LCP=%s IP=%s\n",
-                                       card->devname,LCP(flags->lcp_state),
-                                       IP(flags->ip_state));
-
-                       if (flags->lcp_state == 0x09 && 
-                           (flags->ip_state == 0x09 || flags->ipx_state == 0x09)){
-
-                                /* Initialize the polling timer and set the state
-                                 * to WAN_CONNNECTED */
-
-
-                               /* BUG FIX: When the protocol restarts, during heavy 
-                                 * traffic, board tx buffers and driver tx buffers
-                                 * can go out of sync.  This checks the condition
-                                 * and if the tx buffers are out of sync, the 
-                                 * protocols are restarted. 
-                                 * I don't know why the board tx buffer is out
-                                 * of sync. It could be that a packets is tx
-                                 * while the link is down, but that is not 
-                                 * possible. The other possiblility is that the
-                                 * firmware doesn't reinitialize properly.
-                                 * FIXME: A better fix should be found.
-                                 */ 
-                               if (detect_and_fix_tx_bug(card)){
-
-                                       ppp_comm_disable(card);
-
-                                       wanpipe_set_state(card, WAN_DISCONNECTED);
-
-                                       ppp_priv_area->timer_int_enabled |= 
-                                               TMR_INT_ENABLED_PPP_EVENT;
-                                       flags->imask |= PPP_INTR_TIMER;
-                                       break;  
-                               }
-
-                               card->state_tick = jiffies;
-                               wanpipe_set_state(card, WAN_CONNECTED);
-
-                               NEX_PRINTK(KERN_INFO "CON: L Tx: %lx  B Tx: %lx || L Rx %lx B Rx %lx\n",
-                                       (unsigned long)card->u.p.txbuf, *card->u.p.txbuf_next,
-                                       (unsigned long)card->rxmb, *card->u.p.rxbuf_next);
-
-                               /* Tell timer interrupt that PPP event occurred */
-                               ppp_priv_area->timer_int_enabled |= TMR_INT_ENABLED_PPP_EVENT;
-                               flags->imask |= PPP_INTR_TIMER;
-
-                               /* If we are in PEER mode, we must first obtain the
-                                * IP information and then go into the poll routine */
-                               if (card->u.p.ip_mode != WANOPT_PPP_PEER){      
-                                       trigger_ppp_poll(dev);
-                               }
-                       }
-                       break;
-
-               case PPP_INTR_DROP_DTR:         /* DTR drop timeout expired  0x40 bit 6 */
-
-                       NEX_PRINTK(KERN_INFO "DTR Drop Timeout Interrrupt \n"); 
-
-                       if (card->u.p.ip_mode == WANOPT_PPP_PEER) { 
-                               set_bit(0,&Read_connection_info);
-                       }
-               
-                       wanpipe_set_state(card, WAN_DISCONNECTED);
-
-                       show_disc_cause(card, flags->disc_cause);
-                       ppp_priv_area->timer_int_enabled |= TMR_INT_ENABLED_PPP_EVENT;
-                       flags->imask |= PPP_INTR_TIMER;
-                       trigger_ppp_poll(dev);
-                       break;
-               
-               default:
-                       printk(KERN_INFO "%s: Error, Invalid PPP Event\n",card->devname);
-       }
-}
-
-
-
-/* TIMER INTERRUPT */
-
-void timer_intr (sdla_t *card)
-{
-
-        struct net_device* dev = card->wandev.dev;
-        ppp_private_area_t* ppp_priv_area = dev->priv;
-       ppp_flags_t *flags = card->flags;
-
-
-       if (ppp_priv_area->timer_int_enabled & TMR_INT_ENABLED_CONFIG){
-               if (!config_ppp(card)){
-                       ppp_priv_area->timer_int_enabled &= 
-                                       ~TMR_INT_ENABLED_CONFIG;        
-               }
-       }
-
-       /* Update statistics */
-       if (ppp_priv_area->timer_int_enabled & TMR_INT_ENABLED_UPDATE){
-               ppp_get_err_stats(card);
-                if(!(--ppp_priv_area->update_comms_stats)){
-                       ppp_priv_area->timer_int_enabled &= 
-                               ~TMR_INT_ENABLED_UPDATE;
-               }
-       }
-
-       /* PPIPEMON UDP request */
-
-       if (ppp_priv_area->timer_int_enabled & TMR_INT_ENABLED_UDP){
-               process_udp_mgmt_pkt(card,dev, ppp_priv_area);
-               ppp_priv_area->timer_int_enabled &= ~TMR_INT_ENABLED_UDP;
-       }
-
-       /* PPP Event */
-       if (ppp_priv_area->timer_int_enabled & TMR_INT_ENABLED_PPP_EVENT){
-
-               if (card->wandev.state == WAN_DISCONNECTED){
-                       retrigger_comm(card);
-               }
-
-               /* If the state is CONNECTING, it means that communicatins were
-                * enabled. When the remote side enables its comminication we
-                * should get an interrupt PPP_INTR_OPEN, thus turn off polling 
-                */
-
-               else if (card->wandev.state == WAN_CONNECTING){
-                       /* Turn off the timer interrupt */
-                       ppp_priv_area->timer_int_enabled &= ~TMR_INT_ENABLED_PPP_EVENT;
-               }
-
-               /* If state is connected and we are in PEER mode 
-                * poll for an IP address which will be provided by remote end.
-                */
-               else if ((card->wandev.state == WAN_CONNECTED && 
-                         card->u.p.ip_mode == WANOPT_PPP_PEER) && 
-                         test_bit(0,&Read_connection_info)){
-
-                       card->state_tick = jiffies;
-                       if (read_connection_info (card)){
-                               printk(KERN_INFO "%s: Failed to read PEER IP Addresses\n",
-                                       card->devname);
-                       }else{
-                               clear_bit(0,&Read_connection_info);
-                               set_bit(1,&Read_connection_info);
-                               trigger_ppp_poll(dev);
-                       }
-               }else{
-                       //FIXME Put the comment back int
-                       ppp_priv_area->timer_int_enabled &= ~TMR_INT_ENABLED_PPP_EVENT;
-               }
-
-       }/* End of PPP_EVENT */
-
-
-       /* Only disable the timer interrupt if there are no udp, statistic */
-       /* updates or events pending */
-        if(!ppp_priv_area->timer_int_enabled) {
-                flags->imask &= ~PPP_INTR_TIMER;
-        }
-}
-
-
-static int handle_IPXWAN(unsigned char *sendpacket, char *devname, unsigned char enable_IPX, unsigned long network_number, unsigned short proto)
-{
-       int i;
-
-       if( proto == htons(ETH_P_IPX) ) {
-               //It's an IPX packet
-               if(!enable_IPX) {
-                       //Return 1 so we don't pass it up the stack.
-                       return 1;
-               }
-       } else {
-               //It's not IPX so pass it up the stack.
-               return 0;
-       }
-
-       if( sendpacket[16] == 0x90 &&
-           sendpacket[17] == 0x04)
-       {
-               //It's IPXWAN
-
-               if( sendpacket[2] == 0x02 &&
-                   sendpacket[34] == 0x00)
-               {
-                       //It's a timer request packet
-                       printk(KERN_INFO "%s: Received IPXWAN Timer Request packet\n",devname);
-
-                       //Go through the routing options and answer no to every
-                       //option except Unnumbered RIP/SAP
-                       for(i = 41; sendpacket[i] == 0x00; i += 5)
-                       {
-                               //0x02 is the option for Unnumbered RIP/SAP
-                               if( sendpacket[i + 4] != 0x02)
-                               {
-                                       sendpacket[i + 1] = 0;
-                               }
-                       }
-
-                       //Skip over the extended Node ID option
-                       if( sendpacket[i] == 0x04 )
-                       {
-                               i += 8;
-                       }
-
-                       //We also want to turn off all header compression opt.
-                       for(; sendpacket[i] == 0x80 ;)
-                       {
-                               sendpacket[i + 1] = 0;
-                               i += (sendpacket[i + 2] << 8) + (sendpacket[i + 3]) + 4;
-                       }
-
-                       //Set the packet type to timer response
-                       sendpacket[34] = 0x01;
-
-                       printk(KERN_INFO "%s: Sending IPXWAN Timer Response\n",devname);
-               }
-               else if( sendpacket[34] == 0x02 )
-               {
-                       //This is an information request packet
-                       printk(KERN_INFO "%s: Received IPXWAN Information Request packet\n",devname);
-
-                       //Set the packet type to information response
-                       sendpacket[34] = 0x03;
-
-                       //Set the router name
-                       sendpacket[51] = 'P';
-                       sendpacket[52] = 'T';
-                       sendpacket[53] = 'P';
-                       sendpacket[54] = 'I';
-                       sendpacket[55] = 'P';
-                       sendpacket[56] = 'E';
-                       sendpacket[57] = '-';
-                       sendpacket[58] = CVHexToAscii(network_number >> 28);
-                       sendpacket[59] = CVHexToAscii((network_number & 0x0F000000)>> 24);
-                       sendpacket[60] = CVHexToAscii((network_number & 0x00F00000)>> 20);
-                       sendpacket[61] = CVHexToAscii((network_number & 0x000F0000)>> 16);
-                       sendpacket[62] = CVHexToAscii((network_number & 0x0000F000)>> 12);
-                       sendpacket[63] = CVHexToAscii((network_number & 0x00000F00)>> 8);
-                       sendpacket[64] = CVHexToAscii((network_number & 0x000000F0)>> 4);
-                       sendpacket[65] = CVHexToAscii(network_number & 0x0000000F);
-                       for(i = 66; i < 99; i+= 1)
-                       {
-                               sendpacket[i] = 0;
-                       }
-
-                       printk(KERN_INFO "%s: Sending IPXWAN Information Response packet\n",devname);
-               }
-               else
-               {
-                       printk(KERN_INFO "%s: Unknown IPXWAN packet!\n",devname);
-                       return 0;
-               }
-
-               //Set the WNodeID to our network address
-               sendpacket[35] = (unsigned char)(network_number >> 24);
-               sendpacket[36] = (unsigned char)((network_number & 0x00FF0000) >> 16);
-               sendpacket[37] = (unsigned char)((network_number & 0x0000FF00) >> 8);
-               sendpacket[38] = (unsigned char)(network_number & 0x000000FF);
-
-               return 1;
-       } else {
-               //If we get here it's an IPX-data packet, so it'll get passed up the stack.
-
-               //switch the network numbers
-               switch_net_numbers(sendpacket, network_number, 1);      
-               return 0;
-       }
-}
-
-/****** Background Polling Routines  ****************************************/
-
-/* All polling functions are invoked by the TIMER interrupt in the wpp_isr 
- * routine.  
- */
-
-/*============================================================================
- * Monitor active link phase.
- */
-static void process_route (sdla_t *card)
-{
-       ppp_flags_t *flags = card->flags;
-       struct net_device *dev = card->wandev.dev;
-       ppp_private_area_t *ppp_priv_area = dev->priv;
-       
-       if ((card->u.p.ip_mode == WANOPT_PPP_PEER) &&
-           (flags->ip_state == 0x09)){ 
-
-               /* We get ip_local from the firmware in PEER mode.
-                * Therefore, if ip_local is 0, we failed to obtain
-                * the remote IP address. */
-               if (ppp_priv_area->ip_local == 0) 
-                       return;
-               
-               printk(KERN_INFO "%s: IPCP State Opened.\n", card->devname);
-               if (read_info( card )) {
-                       printk(KERN_INFO 
-                               "%s: An error occurred in IP assignment.\n", 
-                               card->devname);
-               } else {
-                       struct in_device *in_dev = dev->ip_ptr;
-                       if (in_dev != NULL ) {
-                               struct in_ifaddr *ifa = in_dev->ifa_list;
-
-                               printk(KERN_INFO "%s: Assigned Lcl. Addr: %u.%u.%u.%u\n", 
-                                       card->devname, NIPQUAD(ifa->ifa_local));
-                               printk(KERN_INFO "%s: Assigned Rmt. Addr: %u.%u.%u.%u\n", 
-                                               card->devname, NIPQUAD(ifa->ifa_address));
-                       }else{
-                               printk(KERN_INFO 
-                               "%s: Error: Failed to add a route for PPP interface %s\n",
-                                       card->devname,dev->name);       
-                       }
-               }
-       }
-}
-
-/*============================================================================
- * Monitor physical link disconnected phase.
- *  o if interface is up and the hold-down timeout has expired, then retry
- *    connection.
- */
-static void retrigger_comm(sdla_t *card)
-{
-       struct net_device *dev = card->wandev.dev;
-
-       if (dev && ((jiffies - card->state_tick) > HOLD_DOWN_TIME)) {
-
-               wanpipe_set_state(card, WAN_CONNECTING);
-
-               if(ppp_comm_enable(card) == CMD_OK){
-                       init_ppp_tx_rx_buff( card );
-               }                
-       }
-}
-
-/****** Miscellaneous Functions *********************************************/
-
-/*============================================================================
- * Configure S508 adapter.
- */
-static int config508(struct net_device *dev, sdla_t *card)
-{
-       ppp508_conf_t cfg;
-       struct in_device *in_dev = dev->ip_ptr;
-       ppp_private_area_t *ppp_priv_area = dev->priv;
-
-       /* Prepare PPP configuration structure */
-       memset(&cfg, 0, sizeof(ppp508_conf_t));
-
-       if (card->wandev.clocking)
-               cfg.line_speed = card->wandev.bps;
-
-       if (card->wandev.interface == WANOPT_RS232)
-               cfg.conf_flags |= INTERFACE_LEVEL_RS232;
-
-
-        cfg.conf_flags         |= DONT_TERMINATE_LNK_MAX_CONFIG; /*send Configure-Request packets forever*/
-       cfg.txbuf_percent       = PERCENT_TX_BUFF;      /* % of Tx bufs */
-       cfg.mtu_local           = card->wandev.mtu;
-       cfg.mtu_remote          = card->wandev.mtu;                  /*    Default   */
-       cfg.restart_tmr         = TIME_BETWEEN_CONF_REQ;             /*    30 = 3sec */
-       cfg.auth_rsrt_tmr       = TIME_BETWEEN_PAP_CHAP_REQ;         /*    30 = 3sec */
-       cfg.auth_wait_tmr       = WAIT_PAP_CHAP_WITHOUT_REPLY;       /*   300 = 30s  */
-       cfg.mdm_fail_tmr        = WAIT_AFTER_DCD_CTS_LOW;            /*     5 = 0.5s */
-       cfg.dtr_drop_tmr        = TIME_DCD_CTS_LOW_AFTER_LNK_DOWN;   /*    10 = 1s   */
-       cfg.connect_tmout       = WAIT_DCD_HIGH_AFTER_ENABLE_COMM;   /*   900 = 90s  */
-       cfg.conf_retry          = MAX_CONF_REQ_WITHOUT_REPLY;        /*    10 = 1s   */
-       cfg.term_retry          = MAX_TERM_REQ_WITHOUT_REPLY;        /*     2 times  */
-       cfg.fail_retry          = NUM_CONF_NAK_WITHOUT_REPLY;        /*     5 times  */
-       cfg.auth_retry          = NUM_AUTH_REQ_WITHOUT_REPLY;        /*     10 times */   
-
-
-       if( !card->u.p.authenticator ) {
-               printk(KERN_INFO "%s: Device is not configured as an authenticator\n", 
-                               card->devname);
-               cfg.auth_options = NO_AUTHENTICATION;
-       }else{
-               printk(KERN_INFO "%s: Device is configured as an authenticator\n", 
-                               card->devname);
-               cfg.auth_options = INBOUND_AUTH;
-       }
-
-       if( ppp_priv_area->pap == WANOPT_YES){
-               cfg.auth_options |=PAP_AUTH;
-               printk(KERN_INFO "%s: Pap enabled\n", card->devname);
-       }
-       if( ppp_priv_area->chap == WANOPT_YES){
-               cfg.auth_options |= CHAP_AUTH;
-               printk(KERN_INFO "%s: Chap enabled\n", card->devname);
-       }
-
-
-       if (ppp_priv_area->enable_IPX == WANOPT_YES){
-               printk(KERN_INFO "%s: Enabling IPX Protocol\n",card->devname);
-               cfg.ipx_options         = ENABLE_IPX | ROUTING_PROT_DEFAULT;
-       }else{
-               cfg.ipx_options         = DISABLE_IPX;
-       }
-
-       switch (card->u.p.ip_mode) {
-       
-               case WANOPT_PPP_STATIC:
-
-                       printk(KERN_INFO "%s: PPP IP Mode: STATIC\n",card->devname);
-                       cfg.ip_options          = L_AND_R_IP_NO_ASSIG | 
-                                                           ENABLE_IP;
-                       cfg.ip_local            = in_dev->ifa_list->ifa_local;
-                       cfg.ip_remote           = in_dev->ifa_list->ifa_address;
-                       /* Debugging code used to check that IP addresses
-                         * obtained from the kernel are correct */
-
-                        NEX_PRINTK(KERN_INFO "Local %u.%u.%u.%u Remote %u.%u.%u.%u Name %s\n",
-                                       NIPQUAD(ip_local),NIPQUAD(ip_remote), dev->name);
-                       break;
-
-               case WANOPT_PPP_HOST:
-
-                       printk(KERN_INFO "%s: PPP IP Mode: HOST\n",card->devname);
-                       cfg.ip_options          = L_IP_LOCAL_ASSIG |
-                                                 R_IP_LOCAL_ASSIG | 
-                                                 ENABLE_IP;
-                       cfg.ip_local            = in_dev->ifa_list->ifa_local;
-                       cfg.ip_remote           = in_dev->ifa_list->ifa_address;
-                       /* Debugging code used to check that IP addresses
-                         * obtained from the kernel are correct */
-                        NEX_PRINTK (KERN_INFO "Local %u.%u.%u.%u Remote %u.%u.%u.%u Name %s\n",
-                                       NIPQUAD(ip_local),NIPQUAD(ip_remote), dev->name);
-                       
-                       break;
-       
-               case WANOPT_PPP_PEER:
-
-                       printk(KERN_INFO "%s: PPP IP Mode: PEER\n",card->devname);
-                       cfg.ip_options          = L_IP_REMOTE_ASSIG | 
-                                                 R_IP_REMOTE_ASSIG | 
-                                                         ENABLE_IP;
-                       cfg.ip_local            = 0x00;
-                       cfg.ip_remote           = 0x00;
-                       break;
-
-               default:
-                       printk(KERN_INFO "%s: ERROR: Unsupported PPP Mode Selected\n",
-                                       card->devname);
-                       printk(KERN_INFO "%s:        PPP IP Modes: STATIC, PEER or HOST\n",
-                                       card->devname); 
-                       return 1;
-       }
-
-       return ppp_configure(card, &cfg);
-}
-
-/*============================================================================
- * Show disconnection cause.
- */
-static void show_disc_cause(sdla_t *card, unsigned cause)
-{
-       if (cause & 0x0802) 
-
-               printk(KERN_INFO "%s: link terminated by peer\n", 
-                       card->devname);
-
-       else if (cause & 0x0004) 
-
-               printk(KERN_INFO "%s: link terminated by user\n", 
-                       card->devname);
-
-       else if (cause & 0x0008) 
-
-               printk(KERN_INFO "%s: authentication failed\n", card->devname);
-       
-       else if (cause & 0x0010) 
-
-               printk(KERN_INFO 
-                       "%s: authentication protocol negotiation failed\n", 
-                       card->devname);
-
-       else if (cause & 0x0020) 
-               
-               printk(KERN_INFO
-               "%s: peer's request for authentication rejected\n",
-               card->devname);
-
-       else if (cause & 0x0040) 
-       
-               printk(KERN_INFO "%s: MRU option rejected by peer\n", 
-               card->devname);
-
-       else if (cause & 0x0080) 
-       
-               printk(KERN_INFO "%s: peer's MRU was too small\n", 
-               card->devname);
-
-       else if (cause & 0x0100) 
-
-               printk(KERN_INFO "%s: failed to negotiate peer's LCP options\n",
-               card->devname);
-
-       else if (cause & 0x0200) 
-               
-               printk(KERN_INFO "%s: failed to negotiate peer's IPCP options\n"
-               , card->devname);
-
-       else if (cause & 0x0400) 
-
-               printk(KERN_INFO 
-                       "%s: failed to negotiate peer's IPXCP options\n",
-                       card->devname);
-}
-
-/*=============================================================================
- * Process UDP call of type PTPIPEAB.
- */
-static void process_udp_mgmt_pkt(sdla_t *card, struct net_device *dev, 
-                                ppp_private_area_t *ppp_priv_area ) 
-{
-       unsigned char buf2[5];
-       unsigned char *buf;
-       unsigned int frames, len;
-       struct sk_buff *new_skb;
-       unsigned short data_length, buffer_length, real_len;
-       unsigned long data_ptr;
-       int udp_mgmt_req_valid = 1;
-       ppp_mbox_t *mbox = card->mbox;
-       struct timeval tv;
-       int err;
-       ppp_udp_pkt_t *ppp_udp_pkt = (ppp_udp_pkt_t*)&ppp_priv_area->udp_pkt_data;
-
-       memcpy(&buf2, &card->wandev.udp_port, 2 );
-
-
-       if(ppp_priv_area->udp_pkt_src == UDP_PKT_FRM_NETWORK) {
-
-               switch(ppp_udp_pkt->cblock.command) {
-
-                       case PPIPE_GET_IBA_DATA:
-                       case PPP_READ_CONFIG:
-                       case PPP_GET_CONNECTION_INFO:
-                       case PPIPE_ROUTER_UP_TIME:
-                       case PPP_READ_STATISTICS:
-                       case PPP_READ_ERROR_STATS:
-                       case PPP_READ_PACKET_STATS:
-                       case PPP_READ_LCP_STATS:
-                       case PPP_READ_IPCP_STATS:
-                       case PPP_READ_IPXCP_STATS:
-                       case PPP_READ_PAP_STATS:
-                       case PPP_READ_CHAP_STATS:
-                       case PPP_READ_CODE_VERSION:
-                               udp_mgmt_req_valid = 1;
-                               break;
-                          
-                       default:
-                               udp_mgmt_req_valid = 0;
-                               break;
-               } 
-       }
-       
-       if(!udp_mgmt_req_valid) {
-           
-               /* set length to 0 */
-               ppp_udp_pkt->cblock.length = 0x00;
-
-               /* set return code */
-               ppp_udp_pkt->cblock.result = 0xCD; 
-               ++ppp_priv_area->pipe_mgmt_stat.UDP_PIPE_mgmt_direction_err;
-       
-               if (net_ratelimit()){   
-                       printk(KERN_INFO 
-                       "%s: Warning, Illegal UDP command attempted from network: %x\n",
-                       card->devname,ppp_udp_pkt->cblock.command);
-               }
-       } else {
-               /* Initialize the trace element */
-               trace_element_t trace_element;              
-
-               switch (ppp_udp_pkt->cblock.command){
-
-               /* PPIPE_ENABLE_TRACING */
-               case PPIPE_ENABLE_TRACING:
-                       if (!card->TracingEnabled) {
-                       
-                               /* OPERATE_DATALINE_MONITOR */
-                               mbox->cmd.command = PPP_DATALINE_MONITOR;
-                               mbox->cmd.length = 0x01;
-                               mbox->data[0] = ppp_udp_pkt->data[0];
-                               err = sdla_exec(mbox) ? 
-                                       mbox->cmd.result : CMD_TIMEOUT;
-          
-                               if (err != CMD_OK) { 
-                                       
-                                       ppp_error(card, err, mbox);
-                                       card->TracingEnabled = 0;
-                               
-                                       /* set the return code */
-
-                                       ppp_udp_pkt->cblock.result = mbox->cmd.result;
-                                       mbox->cmd.length = 0;
-                                       break;
-                               } 
-
-                               sdla_peek(&card->hw, 0xC000, &buf2, 2);
-                   
-                               ppp_priv_area->curr_trace_addr = 0;
-                               memcpy(&ppp_priv_area->curr_trace_addr, &buf2, 2);
-                               ppp_priv_area->start_trace_addr = 
-                                               ppp_priv_area->curr_trace_addr;
-                               ppp_priv_area->end_trace_addr = 
-                                       ppp_priv_area->start_trace_addr + END_OFFSET;
-                       
-                               /* MAX_SEND_BUFFER_SIZE - 28 (IP header) 
-                                  - 32 (ppipemon CBLOCK) */
-                               available_buffer_space = MAX_LGTH_UDP_MGNT_PKT - 
-                                                        sizeof(ip_pkt_t)-
-                                                        sizeof(udp_pkt_t)-
-                                                        sizeof(wp_mgmt_t)-
-                                                        sizeof(cblock_t);
-                       }
-                       ppp_udp_pkt->cblock.result = 0;
-                       mbox->cmd.length = 0;
-                       card->TracingEnabled = 1;
-                       break;
-          
-               /* PPIPE_DISABLE_TRACING */
-               case PPIPE_DISABLE_TRACING:
-                       
-                       if(card->TracingEnabled) {
-                       
-                               /* OPERATE_DATALINE_MONITOR */
-                               mbox->cmd.command = 0x33;
-                               mbox->cmd.length = 1;
-                               mbox->data[0] = 0x00;
-                               err = sdla_exec(mbox) ? 
-                                       mbox->cmd.result : CMD_TIMEOUT;
-                 
-                       } 
-               
-                       /*set return code*/
-                       ppp_udp_pkt->cblock.result = 0;
-                       mbox->cmd.length = 0;
-                       card->TracingEnabled = 0;
-                       break;
-          
-               /* PPIPE_GET_TRACE_INFO */
-               case PPIPE_GET_TRACE_INFO:
-
-                       if(!card->TracingEnabled) {
-                               /* set return code */
-                               ppp_udp_pkt->cblock.result = 1;
-                               mbox->cmd.length = 0;
-                       }                   
-
-                       buffer_length = 0;
-                       
-                       /* frames < 62, where 62 is the number of trace
-                          information elements.  There is in total 496
-                          bytes of space and each trace information
-                          element is 8 bytes. 
-                        */
-                       for ( frames=0; frames<62; frames++) {
-       
-                               trace_pkt_t *trace_pkt = (trace_pkt_t *)
-                                       &ppp_udp_pkt->data[buffer_length];
-       
-                               /* Read the whole trace packet */
-                               sdla_peek(&card->hw, ppp_priv_area->curr_trace_addr, 
-                                         &trace_element, sizeof(trace_element_t));
-       
-                               /* no data on board so exit */
-                               if( trace_element.opp_flag == 0x00 ) 
-                                       break;
-             
-                               data_ptr = trace_element.trace_data_ptr;
-
-                               /* See if there is actual data on the trace buffer */
-                               if (data_ptr){
-                                       data_length = trace_element.trace_length;
-                               }else{
-                                       data_length = 0;
-                                       ppp_udp_pkt->data[0] |= 0x02;
-                               }
-
-                               //FIXME: Do we need this check
-                               if ((available_buffer_space - buffer_length) 
-                                    < (sizeof(trace_element_t)+1)){
-                                       
-                                       /*indicate we have more frames 
-                                        * on board and exit 
-                                        */
-                                       ppp_udp_pkt->data[0] |= 0x02;
-                                       break;
-                               }
-                               
-                               trace_pkt->status = trace_element.trace_type;
-                               trace_pkt->time_stamp = trace_element.trace_time_stamp;
-                               trace_pkt->real_length = trace_element.trace_length;
-
-                               real_len = trace_element.trace_length;  
-                               
-                               if(data_ptr == 0){
-                                       trace_pkt->data_avail = 0x00;
-                               }else{
-                                       /* we can take it next time */
-                                       if ((available_buffer_space - buffer_length)<
-                                               (real_len + sizeof(trace_pkt_t))){
-                                       
-                                               ppp_udp_pkt->data[0] |= 0x02;
-                                               break;
-                                       } 
-                                       trace_pkt->data_avail = 0x01;
-                               
-                                       /* get the data */
-                                       sdla_peek(&card->hw, data_ptr, 
-                                                 &trace_pkt->data,
-                                                 real_len);
-                               }       
-                               /* zero the opp flag to 
-                                  show we got the frame */
-                               buf2[0] = 0x00;
-                               sdla_poke(&card->hw, ppp_priv_area->curr_trace_addr,
-                                         &buf2, 1);
-
-                               /* now move onto the next 
-                                  frame */
-                               ppp_priv_area->curr_trace_addr += 8;
-
-                               /* check if we passed the last address */
-                               if ( ppp_priv_area->curr_trace_addr >= 
-                                       ppp_priv_area->end_trace_addr){
-
-                                       ppp_priv_area->curr_trace_addr = 
-                                               ppp_priv_area->start_trace_addr;
-                               }
-                               /* update buffer length and make sure its even */ 
-
-                               if ( trace_pkt->data_avail == 0x01 ) {
-                                       buffer_length += real_len - 1;
-                               }
-                               /* for the header */
-                               buffer_length += 8;
-
-                               if( buffer_length & 0x0001 )
-                                       buffer_length += 1;
-                       }
-
-                       /* ok now set the total number of frames passed
-                          in the high 5 bits */
-                       ppp_udp_pkt->data[0] |= (frames << 2);
-        
-                       /* set the data length */
-                       mbox->cmd.length = buffer_length;
-                       ppp_udp_pkt->cblock.length = buffer_length;
-        
-                       /* set return code */
-                       ppp_udp_pkt->cblock.result = 0;
-                       break;
-
-               /* PPIPE_GET_IBA_DATA */
-               case PPIPE_GET_IBA_DATA:
-               
-                       mbox->cmd.length = 0x09;
-               
-                       sdla_peek(&card->hw, 0xF003, &ppp_udp_pkt->data, 
-                                       mbox->cmd.length);
-               
-                       /* set the length of the data */
-                       ppp_udp_pkt->cblock.length = 0x09;
-
-                       /* set return code */
-                       ppp_udp_pkt->cblock.result = 0x00;
-                       ppp_udp_pkt->cblock.result = 0;
-                       break;
-
-               /* PPIPE_FT1_READ_STATUS */
-               case PPIPE_FT1_READ_STATUS:
-                       sdla_peek(&card->hw, 0xF020, &ppp_udp_pkt->data[0], 2);
-                       ppp_udp_pkt->cblock.length = mbox->cmd.length = 2;
-                       ppp_udp_pkt->cblock.result = 0;
-                       break;
-               
-               case PPIPE_FLUSH_DRIVER_STATS:   
-                       init_ppp_priv_struct( ppp_priv_area );
-                       init_global_statistics( card );
-                       mbox->cmd.length = 0;
-                       ppp_udp_pkt->cblock.result = 0;
-                       break;
-
-               
-               case PPIPE_ROUTER_UP_TIME:
-
-                       do_gettimeofday( &tv );
-                       ppp_priv_area->router_up_time = tv.tv_sec - 
-                                       ppp_priv_area->router_start_time;
-                       *(unsigned long *)&ppp_udp_pkt->data = ppp_priv_area->router_up_time;
-                       mbox->cmd.length = 4;
-                       ppp_udp_pkt->cblock.result = 0;
-                       break;
-
-                               /* PPIPE_DRIVER_STATISTICS */   
-               case PPIPE_DRIVER_STAT_IFSEND:
-                       memcpy(&ppp_udp_pkt->data, &ppp_priv_area->if_send_stat, 
-                               sizeof(if_send_stat_t));
-
-
-                       ppp_udp_pkt->cblock.result = 0;
-                       ppp_udp_pkt->cblock.length = sizeof(if_send_stat_t);
-                       mbox->cmd.length = sizeof(if_send_stat_t);      
-                       break;
-
-               case PPIPE_DRIVER_STAT_INTR:
-                       memcpy(&ppp_udp_pkt->data, &card->statistics, 
-                               sizeof(global_stats_t));
-
-                       memcpy(&ppp_udp_pkt->data+sizeof(global_stats_t),
-                               &ppp_priv_area->rx_intr_stat,
-                               sizeof(rx_intr_stat_t));
-
-                       ppp_udp_pkt->cblock.result = 0;
-                       ppp_udp_pkt->cblock.length = sizeof(global_stats_t)+
-                                                    sizeof(rx_intr_stat_t);
-                       mbox->cmd.length = ppp_udp_pkt->cblock.length;
-                       break;
-
-               case PPIPE_DRIVER_STAT_GEN:
-                       memcpy( &ppp_udp_pkt->data,
-                               &ppp_priv_area->pipe_mgmt_stat,
-                               sizeof(pipe_mgmt_stat_t));
-
-                       memcpy(&ppp_udp_pkt->data+sizeof(pipe_mgmt_stat_t), 
-                              &card->statistics, sizeof(global_stats_t));
-
-                       ppp_udp_pkt->cblock.result = 0;
-                       ppp_udp_pkt->cblock.length = sizeof(global_stats_t)+
-                                                    sizeof(rx_intr_stat_t);
-                       mbox->cmd.length = ppp_udp_pkt->cblock.length;
-                       break;
-
-
-               /* FT1 MONITOR STATUS */
-               case FT1_MONITOR_STATUS_CTRL:
-       
-                       /* Enable FT1 MONITOR STATUS */
-                       if( ppp_udp_pkt->data[0] == 1) {
-                       
-                               if( rCount++ != 0 ) {
-                                       ppp_udp_pkt->cblock.result = 0;
-                                       mbox->cmd.length = 1;
-                                       break;
-                               }       
-                       }
-
-                       /* Disable FT1 MONITOR STATUS */
-                       if( ppp_udp_pkt->data[0] == 0) {
-
-                               if( --rCount != 0) {
-                                       ppp_udp_pkt->cblock.result = 0;
-                                       mbox->cmd.length = 1;
-                                       break;
-                               } 
-                       }       
-                       goto udp_dflt_cmd;
-                       
-               /* WARNING: FIXME: This should be fixed.
-                * The FT1 Status Ctrl doesn't have a break
-                 * statment.  Thus, no code must be inserted
-                 * HERE: between default and above case statement */
-
-               default:
-udp_dflt_cmd:
-               
-                       /* it's a board command */
-                       mbox->cmd.command = ppp_udp_pkt->cblock.command;
-                       mbox->cmd.length = ppp_udp_pkt->cblock.length;
-                       if(mbox->cmd.length) {
-                               memcpy(&mbox->data,(unsigned char *)ppp_udp_pkt->data,
-                                      mbox->cmd.length);
-                       } 
-                 
-                       /* run the command on the board */
-                       err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-               
-                       if (err != CMD_OK) {
-               
-                               ppp_error(card, err, mbox);
-                               ++ppp_priv_area->pipe_mgmt_stat.
-                                        UDP_PIPE_mgmt_adptr_cmnd_timeout;
-                               break;
-                       }
-                 
-                       ++ppp_priv_area->pipe_mgmt_stat.UDP_PIPE_mgmt_adptr_cmnd_OK;
-               
-                       /* copy the result back to our buffer */
-                       memcpy(&ppp_udp_pkt->cblock,mbox, sizeof(cblock_t));
-                 
-                       if(mbox->cmd.length) {
-                               memcpy(&ppp_udp_pkt->data,&mbox->data,mbox->cmd.length);
-                       } 
-
-               } /* end of switch */
-       } /* end of else */
-
-       /* Fill UDP TTL */
-       ppp_udp_pkt->ip_pkt.ttl = card->wandev.ttl; 
-       len = reply_udp(ppp_priv_area->udp_pkt_data, mbox->cmd.length);
-
-       if (ppp_priv_area->udp_pkt_src == UDP_PKT_FRM_NETWORK) {
-
-               /* Make sure we are not already sending */
-               if (!test_bit(SEND_CRIT,&card->wandev.critical)){
-                       ++ppp_priv_area->pipe_mgmt_stat.UDP_PIPE_mgmt_passed_to_adptr;
-                       ppp_send(card,ppp_priv_area->udp_pkt_data,len,ppp_priv_area->protocol);
-               }
-
-       } else {        
-       
-               /* Pass it up the stack
-                  Allocate socket buffer */
-               if ((new_skb = dev_alloc_skb(len)) != NULL) {
-               
-                       /* copy data into new_skb */
-
-                       buf = skb_put(new_skb, len);
-                       memcpy(buf,ppp_priv_area->udp_pkt_data, len);
-
-                       ++ppp_priv_area->pipe_mgmt_stat.UDP_PIPE_mgmt_passed_to_stack;
-                       
-                       /* Decapsulate packet and pass it up the protocol 
-                          stack */
-                       new_skb->protocol = htons(ETH_P_IP);
-                       new_skb->dev = dev;
-                       new_skb->mac.raw  = new_skb->data;
-                       netif_rx(new_skb);
-                       dev->last_rx = jiffies;
-               
-               } else {
-               
-                       ++ppp_priv_area->pipe_mgmt_stat.UDP_PIPE_mgmt_no_socket;
-                       printk(KERN_INFO "no socket buffers available!\n");
-               }
-       }       
-
-       ppp_priv_area->udp_pkt_lgth = 0;
-       
-       return; 
-}
-
-/*=============================================================================
- * Initial the ppp_private_area structure.
- */
-static void init_ppp_priv_struct( ppp_private_area_t *ppp_priv_area )
-{
-
-       memset(&ppp_priv_area->if_send_stat, 0, sizeof(if_send_stat_t));
-       memset(&ppp_priv_area->rx_intr_stat, 0, sizeof(rx_intr_stat_t));
-       memset(&ppp_priv_area->pipe_mgmt_stat, 0, sizeof(pipe_mgmt_stat_t));    
-}
-
-/*============================================================================
- * Initialize Global Statistics
- */
-static void init_global_statistics( sdla_t *card )
-{
-       memset(&card->statistics, 0, sizeof(global_stats_t));
-}
-
-/*============================================================================
- * Initialize Receive and Transmit Buffers.
- */
-static void init_ppp_tx_rx_buff( sdla_t *card )
-{
-       ppp508_buf_info_t* info;
-
-       if (card->hw.type == SDLA_S514) {
-               
-               info = (void*)(card->hw.dpmbase + PPP514_BUF_OFFS);
-
-                       card->u.p.txbuf_base = (void*)(card->hw.dpmbase +
-                       info->txb_ptr);
-
-                card->u.p.txbuf_last = (ppp_buf_ctl_t*)card->u.p.txbuf_base +
-                        (info->txb_num - 1);
-
-                card->u.p.rxbuf_base = (void*)(card->hw.dpmbase +
-                        info->rxb_ptr);
-
-                card->u.p.rxbuf_last = (ppp_buf_ctl_t*)card->u.p.rxbuf_base +
-                        (info->rxb_num - 1);
-
-       } else {
-               
-               info = (void*)(card->hw.dpmbase + PPP508_BUF_OFFS);
-
-               card->u.p.txbuf_base = (void*)(card->hw.dpmbase +
-                       (info->txb_ptr - PPP508_MB_VECT));
-
-               card->u.p.txbuf_last = (ppp_buf_ctl_t*)card->u.p.txbuf_base +
-                       (info->txb_num - 1);
-
-               card->u.p.rxbuf_base = (void*)(card->hw.dpmbase +
-                       (info->rxb_ptr - PPP508_MB_VECT));
-
-               card->u.p.rxbuf_last = (ppp_buf_ctl_t*)card->u.p.rxbuf_base +
-                       (info->rxb_num - 1);
-       }
-
-       card->u.p.txbuf_next = (unsigned long*)&info->txb_nxt; 
-       card->u.p.rxbuf_next = (unsigned long*)&info->rxb1_ptr;
-
-       card->u.p.rx_base = info->rxb_base;
-        card->u.p.rx_top  = info->rxb_end;
-      
-       card->u.p.txbuf = card->u.p.txbuf_base;
-       card->rxmb = card->u.p.rxbuf_base;
-
-}
-
-/*=============================================================================
- * Read Connection Information (ie for Remote IP address assginment).
- * Called when ppp interface connected.
- */
-static int read_info( sdla_t *card )
-{
-       struct net_device *dev = card->wandev.dev;
-       ppp_private_area_t *ppp_priv_area = dev->priv;
-       int err;
-
-       struct ifreq if_info;
-       struct sockaddr_in *if_data1, *if_data2;
-       mm_segment_t fs;
-
-       /* Set Local and remote addresses */
-       memset(&if_info, 0, sizeof(if_info));
-       strcpy(if_info.ifr_name, dev->name);
-
-
-       fs = get_fs();
-       set_fs(get_ds());     /* get user space block */ 
-
-       /* Change the local and remote ip address of the interface.
-        * This will also add in the destination route.
-        */     
-       if_data1 = (struct sockaddr_in *)&if_info.ifr_addr;
-       if_data1->sin_addr.s_addr = ppp_priv_area->ip_local;
-       if_data1->sin_family = AF_INET;
-       err = devinet_ioctl( SIOCSIFADDR, &if_info );
-       if_data2 = (struct sockaddr_in *)&if_info.ifr_dstaddr;
-       if_data2->sin_addr.s_addr = ppp_priv_area->ip_remote;
-       if_data2->sin_family = AF_INET;
-       err = devinet_ioctl( SIOCSIFDSTADDR, &if_info );
-
-       set_fs(fs);           /* restore old block */
-       
-       if (err) {
-               printk (KERN_INFO "%s: Adding of route failed: %i\n",
-                       card->devname,err);
-               printk (KERN_INFO "%s:  Local : %u.%u.%u.%u\n",
-                       card->devname,NIPQUAD(ppp_priv_area->ip_local));
-               printk (KERN_INFO "%s:  Remote: %u.%u.%u.%u\n",
-                       card->devname,NIPQUAD(ppp_priv_area->ip_remote));
-       }
-       return err;
-}
-
-/*=============================================================================
- * Remove Dynamic Route.
- * Called when ppp interface disconnected.
- */
-
-static void remove_route( sdla_t *card )
-{
-
-       struct net_device *dev = card->wandev.dev;
-       long ip_addr;
-       int err;
-
-        mm_segment_t fs;
-       struct ifreq if_info;
-       struct sockaddr_in *if_data1;
-        struct in_device *in_dev = dev->ip_ptr;
-        struct in_ifaddr *ifa = in_dev->ifa_list;      
-
-       ip_addr = ifa->ifa_local;
-
-       /* Set Local and remote addresses */
-       memset(&if_info, 0, sizeof(if_info));
-       strcpy(if_info.ifr_name, dev->name);
-
-       fs = get_fs();
-               set_fs(get_ds());     /* get user space block */ 
-
-       /* Change the local ip address of the interface to 0.
-        * This will also delete the destination route.
-        */     
-       if_data1 = (struct sockaddr_in *)&if_info.ifr_addr;
-       if_data1->sin_addr.s_addr = 0;
-       if_data1->sin_family = AF_INET;
-       err = devinet_ioctl( SIOCSIFADDR, &if_info );
-
-        set_fs(fs);           /* restore old block */
-
-       
-       if (err) {
-               printk (KERN_INFO "%s: Deleting dynamic route failed %d!\n",
-                        card->devname, err);
-               return;
-       }else{
-               printk (KERN_INFO "%s: PPP Deleting dynamic route %u.%u.%u.%u successfuly\n",
-                       card->devname, NIPQUAD(ip_addr));
-       }
-       return;
-}
-
-/*=============================================================================
- * Perform the Interrupt Test by running the READ_CODE_VERSION command MAX_INTR
- * _TEST_COUNTER times.
- */
-static int intr_test( sdla_t *card )
-{
-       ppp_mbox_t *mb = card->mbox;
-       int err,i;
-
-       err = ppp_set_intr_mode( card, 0x08 );
-       
-       if (err == CMD_OK) { 
-               
-               for (i = 0; i < MAX_INTR_TEST_COUNTER; i ++) {  
-                       /* Run command READ_CODE_VERSION */
-                       memset(&mb->cmd, 0, sizeof(ppp_cmd_t));
-                       mb->cmd.length  = 0;
-                       mb->cmd.command = PPP_READ_CODE_VERSION;
-                       err = sdla_exec(mb) ? mb->cmd.result : CMD_TIMEOUT;
-                       if (err != CMD_OK) 
-                               ppp_error(card, err, mb);
-               }
-       }
-       else return err;
-
-       err = ppp_set_intr_mode( card, 0 );
-       if (err != CMD_OK) 
-               return err;
-
-       return 0;
-}
-
-/*==============================================================================
- * Determine what type of UDP call it is. DRVSTATS or PTPIPEAB ?
- */
-static int udp_pkt_type( struct sk_buff *skb, sdla_t *card )
-{
-       unsigned char *sendpacket;
-       unsigned char buf2[5]; 
-       ppp_udp_pkt_t *ppp_udp_pkt = (ppp_udp_pkt_t *)skb->data; 
-       
-       sendpacket = skb->data;
-       memcpy(&buf2, &card->wandev.udp_port, 2);
-       
-       if(     ppp_udp_pkt->ip_pkt.ver_inet_hdr_length  == 0x45 &&        /* IP packet */ 
-               sendpacket[9]  == 0x11 &&        /* UDP packet */
-               sendpacket[22] == buf2[1] &&     /* UDP Port */
-               sendpacket[23] == buf2[0] &&
-               sendpacket[36] == 0x01 ) {
-       
-               if (    sendpacket[28] == 0x50 &&    /* PTPIPEAB: Signature */ 
-                       sendpacket[29] == 0x54 &&      
-                       sendpacket[30] == 0x50 &&      
-                       sendpacket[31] == 0x49 &&      
-                       sendpacket[32] == 0x50 &&      
-                       sendpacket[33] == 0x45 &&      
-                       sendpacket[34] == 0x41 &&      
-                       sendpacket[35] == 0x42 ){ 
-
-                       return UDP_PTPIPE_TYPE;
-       
-               } else if(sendpacket[28] == 0x44 &&  /* DRVSTATS: Signature */
-                       sendpacket[29] == 0x52 &&      
-                       sendpacket[30] == 0x56 &&      
-                       sendpacket[31] == 0x53 &&      
-                       sendpacket[32] == 0x54 &&      
-                       sendpacket[33] == 0x41 &&      
-                       sendpacket[34] == 0x54 &&      
-                       sendpacket[35] == 0x53 ){
-       
-                       return UDP_DRVSTATS_TYPE;
-
-               } else
-                       return UDP_INVALID_TYPE;
-
-       } else
-               return UDP_INVALID_TYPE;
-
-}
-
-/*============================================================================
- * Check to see if the packet to be transmitted contains a broadcast or
- * multicast source IP address.
- */
-
-static int chk_bcast_mcast_addr(sdla_t *card, struct net_device* dev,
-                               struct sk_buff *skb)
-{
-       u32 src_ip_addr;
-        u32 broadcast_ip_addr = 0;
-        struct in_device *in_dev;
-
-        /* read the IP source address from the outgoing packet */
-        src_ip_addr = *(u32 *)(skb->data + 12);
-
-       /* read the IP broadcast address for the device */
-        in_dev = dev->ip_ptr;
-        if(in_dev != NULL) {
-                struct in_ifaddr *ifa= in_dev->ifa_list;
-                if(ifa != NULL)
-                        broadcast_ip_addr = ifa->ifa_broadcast;
-                else
-                        return 0;
-        }
-        /* check if the IP Source Address is a Broadcast address */
-        if((dev->flags & IFF_BROADCAST) && (src_ip_addr == broadcast_ip_addr)) {
-                printk(KERN_INFO "%s: Broadcast Source Address silently discarded\n",
-                               card->devname);
-                return 1;
-        } 
-
-        /* check if the IP Source Address is a Multicast address */
-        if((ntohl(src_ip_addr) >= 0xE0000001) &&
-               (ntohl(src_ip_addr) <= 0xFFFFFFFE)) {
-                printk(KERN_INFO "%s: Multicast Source Address silently discarded\n",
-                               card->devname);
-                return 1;
-        }
-
-        return 0;
-}
-
-void s508_lock (sdla_t *card, unsigned long *smp_flags)
-{
-       spin_lock_irqsave(&card->wandev.lock, *smp_flags);
-}
-
-void s508_unlock (sdla_t *card, unsigned long *smp_flags)
-{
-        spin_unlock_irqrestore(&card->wandev.lock, *smp_flags);
-}
-
-static int read_connection_info (sdla_t *card)
-{
-       ppp_mbox_t *mb = card->mbox;
-       struct net_device *dev = card->wandev.dev;
-       ppp_private_area_t *ppp_priv_area = dev->priv;
-       ppp508_connect_info_t *ppp508_connect_info;
-       int err;
-
-       memset(&mb->cmd, 0, sizeof(ppp_cmd_t));
-       mb->cmd.length  = 0;
-       mb->cmd.command = PPP_GET_CONNECTION_INFO;
-       err = sdla_exec(mb) ? mb->cmd.result : CMD_TIMEOUT;
-
-       if (err != CMD_OK) { 
-               ppp_error(card, err, mb);
-               ppp_priv_area->ip_remote = 0;
-               ppp_priv_area->ip_local = 0;
-       }
-       else {
-               ppp508_connect_info = (ppp508_connect_info_t *)mb->data;
-               ppp_priv_area->ip_remote = ppp508_connect_info->ip_remote;
-               ppp_priv_area->ip_local = ppp508_connect_info->ip_local;
-
-               NEX_PRINTK(KERN_INFO "READ CONNECTION GOT IP ADDRESS %x, %x\n",
-                               ppp_priv_area->ip_remote,
-                               ppp_priv_area->ip_local);
-       }
-
-       return err;
-}
-
-/*===============================================================================
- * config_ppp
- *
- *     Configure the ppp protocol and enable communications.           
- *
- *     The if_open function binds this function to the poll routine.
- *      Therefore, this function will run every time the ppp interface
- *      is brought up.  
- *      
- *     If the communications are not enabled, proceed to configure
- *      the card and enable communications.
- *
- *      If the communications are enabled, it means that the interface
- *      was shutdown by ether the user or driver. In this case, we 
- *      have to check that the IP addresses have not changed.  If
- *      the IP addresses changed, we have to reconfigure the firmware
- *      and update the changed IP addresses.  Otherwise, just exit.
- */
-static int config_ppp (sdla_t *card)
-{
-
-       struct net_device *dev = card->wandev.dev;
-       ppp_flags_t *flags = card->flags;
-       ppp_private_area_t *ppp_priv_area = dev->priv;
-
-       if (card->u.p.comm_enabled){
-
-               if (ppp_priv_area->ip_local_tmp != ppp_priv_area->ip_local ||
-                   ppp_priv_area->ip_remote_tmp != ppp_priv_area->ip_remote){
-                       
-                       /* The IP addersses have changed, we must
-                         * stop the communications and reconfigure
-                         * the card. Reason: the firmware must know
-                         * the local and remote IP addresses. */
-                       disable_comm(card);
-                       wanpipe_set_state(card, WAN_DISCONNECTED);
-                       printk(KERN_INFO 
-                               "%s: IP addresses changed!\n",
-                                       card->devname);
-                       printk(KERN_INFO "%s: Restarting communications ...\n",
-                                       card->devname);
-               }else{ 
-                       /* IP addresses are the same and the link is up, 
-                         * we don't have to do anything here. Therefore, exit */
-                       return 0;
-               }
-       }
-
-       /* Record the new IP addreses */
-       ppp_priv_area->ip_local = ppp_priv_area->ip_local_tmp;
-       ppp_priv_area->ip_remote = ppp_priv_area->ip_remote_tmp;
-
-       if (config508(dev, card)){
-               printk(KERN_INFO "%s: Failed to configure PPP device\n",
-                       card->devname);
-               return 0;
-       }
-
-       if (ppp_set_intr_mode(card, PPP_INTR_RXRDY|
-                                       PPP_INTR_TXRDY|
-                                       PPP_INTR_MODEM|
-                                       PPP_INTR_DISC |
-                                       PPP_INTR_OPEN |
-                                       PPP_INTR_DROP_DTR |
-                                       PPP_INTR_TIMER)) {
-
-               printk(KERN_INFO "%s: Failed to configure board interrupts !\n", 
-                       card->devname);
-               return 0;
-       }
-
-        /* Turn off the transmit and timer interrupt */
-       flags->imask &= ~(PPP_INTR_TXRDY | PPP_INTR_TIMER) ;
-
-
-       /* If you are not the authenticator and any one of the protocol is 
-        * enabled then we call the set_out_bound_authentication.
-        */
-       if ( !card->u.p.authenticator  && (ppp_priv_area->pap || ppp_priv_area->chap)) {
-               if ( ppp_set_outbnd_auth(card, ppp_priv_area) ){
-                       printk(KERN_INFO "%s: Outbound authentication failed !\n",
-                               card->devname);
-                       return 0;
-               }
-       } 
-       
-       /* If you are the authenticator and any one of the protocol is enabled
-        * then we call the set_in_bound_authentication.
-        */
-       if (card->u.p.authenticator && (ppp_priv_area->pap || ppp_priv_area->chap)){
-               if (ppp_set_inbnd_auth(card, ppp_priv_area)){
-                       printk(KERN_INFO "%s: Inbound authentication failed !\n",
-                               card->devname); 
-                       return 0;
-               }
-       }
-
-       /* If we fail to enable communications here it's OK,
-        * since the DTR timer will cause a disconnected, which
-        * will retrigger communication in timer_intr() */
-       if (ppp_comm_enable(card) == CMD_OK) {
-               wanpipe_set_state(card, WAN_CONNECTING);
-               init_ppp_tx_rx_buff(card);
-       }
-
-       return 0; 
-}
-
-/*============================================================
- * ppp_poll
- *     
- * Rationale:
- *     We cannot manipulate the routing tables, or
- *      ip addresses withing the interrupt. Therefore
- *      we must perform such actons outside an interrupt 
- *      at a later time. 
- *
- * Description:        
- *     PPP polling routine, responsible for 
- *             shutting down interfaces upon disconnect
- *             and adding/removing routes. 
- *      
- * Usage:        
- *     This function is executed for each ppp  
- *     interface through a tq_schedule bottom half.
- *      
- *      trigger_ppp_poll() function is used to kick
- *      the ppp_poll routine.  
- */
-static void ppp_poll(struct net_device *dev)
-{
-       ppp_private_area_t *ppp_priv_area;      
-       sdla_t *card;
-       u8 check_gateway=0;
-       ppp_flags_t *flags;
-
-       if (!dev || (ppp_priv_area = dev->priv) == NULL)
-               return;
-
-       card = ppp_priv_area->card;
-       flags = card->flags;
-
-       /* Shutdown is in progress, stop what you are 
-        * doing and get out */
-       if (test_bit(PERI_CRIT,&card->wandev.critical)){
-               clear_bit(POLL_CRIT,&card->wandev.critical);
-               return;
-       }
-
-       /* if_open() function has triggered the polling routine
-        * to determine the configured IP addresses.  Once the
-        * addresses are found, trigger the chdlc configuration */
-       if (test_bit(0,&ppp_priv_area->config_ppp)){
-
-               ppp_priv_area->ip_local_tmp  = get_ip_address(dev,WAN_LOCAL_IP);
-               ppp_priv_area->ip_remote_tmp = get_ip_address(dev,WAN_POINTOPOINT_IP);
-
-               if (ppp_priv_area->ip_local_tmp == ppp_priv_area->ip_remote_tmp && 
-                   card->u.p.ip_mode == WANOPT_PPP_HOST){
-                       
-                       if (++ppp_priv_area->ip_error > MAX_IP_ERRORS){
-                               printk(KERN_INFO "\n%s: --- WARNING ---\n",
-                                               card->devname);
-                               printk(KERN_INFO "%s: The local IP address is the same as the\n",
-                                               card->devname);
-                               printk(KERN_INFO "%s: Point-to-Point IP address.\n",
-                                               card->devname);
-                               printk(KERN_INFO "%s: --- WARNING ---\n\n",
-                                               card->devname);
-                       }else{
-                               clear_bit(POLL_CRIT,&card->wandev.critical);
-                               ppp_priv_area->poll_delay_timer.expires = jiffies+HZ;
-                               add_timer(&ppp_priv_area->poll_delay_timer);
-                               return;
-                       }
-               }
-
-               ppp_priv_area->timer_int_enabled |= TMR_INT_ENABLED_CONFIG;
-               flags->imask |= PPP_INTR_TIMER; 
-               ppp_priv_area->ip_error=0;      
-               
-               clear_bit(0,&ppp_priv_area->config_ppp);
-               clear_bit(POLL_CRIT,&card->wandev.critical);
-               return;
-       }
-
-       /* Dynamic interface implementation, as well as dynamic
-        * routing.  */
-       
-       switch (card->wandev.state) {
-       
-       case WAN_DISCONNECTED:
-
-               /* If the dynamic interface configuration is on, and interface 
-                * is up, then bring down the netowrk interface */
-
-               if (test_bit(DYN_OPT_ON,&ppp_priv_area->interface_down) &&
-                   !test_bit(DEV_DOWN,&ppp_priv_area->interface_down)  &&      
-                   card->wandev.dev->flags & IFF_UP){  
-
-                       printk(KERN_INFO "%s: Interface %s down.\n",
-                               card->devname,card->wandev.dev->name);
-                       change_dev_flags(card->wandev.dev,
-                                       (card->wandev.dev->flags&~IFF_UP));
-                       set_bit(DEV_DOWN,&ppp_priv_area->interface_down);
-               }else{
-                       /* We need to check if the local IP address is
-                                * zero. If it is, we shouldn't try to remove it.
-                        * For some reason the kernel crashes badly if 
-                        * we try to remove the route twice */
-
-                       if (card->wandev.dev->flags & IFF_UP && 
-                           get_ip_address(card->wandev.dev,WAN_LOCAL_IP) &&
-                           card->u.p.ip_mode == WANOPT_PPP_PEER){
-
-                               remove_route(card);
-                       }
-               }
-               break;
-
-       case WAN_CONNECTED:
-               
-               /* In SMP machine this code can execute before the interface
-                * comes up.  In this case, we must make sure that we do not
-                * try to bring up the interface before dev_open() is finished */
-
-
-               /* DEV_DOWN will be set only when we bring down the interface
-                * for the very first time. This way we know that it was us
-                * that brought the interface down */
-               
-               if (test_bit(DYN_OPT_ON,&ppp_priv_area->interface_down) &&
-                   test_bit(DEV_DOWN,  &ppp_priv_area->interface_down) &&
-                   !(card->wandev.dev->flags & IFF_UP)){
-                       
-                       printk(KERN_INFO "%s: Interface %s up.\n",
-                               card->devname,card->wandev.dev->name);
-                       
-                       change_dev_flags(card->wandev.dev,(card->wandev.dev->flags|IFF_UP));
-                       clear_bit(DEV_DOWN,&ppp_priv_area->interface_down);
-                       check_gateway=1;
-               }
-
-               if ((card->u.p.ip_mode == WANOPT_PPP_PEER) && 
-                   test_bit(1,&Read_connection_info)) { 
-                       
-                       process_route(card);
-                       clear_bit(1,&Read_connection_info);
-                       check_gateway=1;
-               }
-
-               if (ppp_priv_area->gateway && check_gateway)
-                       add_gateway(card,dev);
-
-               break;
-       }
-       clear_bit(POLL_CRIT,&card->wandev.critical);
-       return;
-}
-
-/*============================================================
- * trigger_ppp_poll
- *
- * Description:
- *     Add a ppp_poll() task into a tq_scheduler bh handler
- *      for a specific interface.  This will kick
- *      the ppp_poll() routine at a later time. 
- *
- * Usage:
- *     Interrupts use this to defer a taks to 
- *      a polling routine.
- *
- */    
-
-static void trigger_ppp_poll(struct net_device *dev)
-{
-       ppp_private_area_t *ppp_priv_area;
-       if ((ppp_priv_area=dev->priv) != NULL){         
-               
-               sdla_t *card = ppp_priv_area->card;
-
-               if (test_bit(PERI_CRIT,&card->wandev.critical)){
-                       return;
-               }
-               
-               if (test_and_set_bit(POLL_CRIT,&card->wandev.critical)){
-                       return;
-               }
-
-               schedule_work(&ppp_priv_area->poll_work);
-       }
-       return;
-}
-
-static void ppp_poll_delay (unsigned long dev_ptr)
-{
-       struct net_device *dev = (struct net_device *)dev_ptr;
-       trigger_ppp_poll(dev);
-}
-
-/*============================================================
- * detect_and_fix_tx_bug
- *
- * Description:
- *     On connect, if the board tx buffer ptr is not the same
- *      as the driver tx buffer ptr, we found a firmware bug.
- *      Report the bug to the above layer.  To fix the
- *      error restart communications again.
- *
- * Usage:
- *
- */    
-
-static int detect_and_fix_tx_bug (sdla_t *card)
-{
-       if (((unsigned long)card->u.p.txbuf_base&0xFFF) != ((*card->u.p.txbuf_next)&0xFFF)){
-               NEX_PRINTK(KERN_INFO "Major Error, Fix the bug\n");
-               return 1;
-       }
-       return 0;
-}
-
-MODULE_LICENSE("GPL");
-
-/****** End *****************************************************************/
diff --git a/drivers/net/wan/sdla_x25.c b/drivers/net/wan/sdla_x25.c
deleted file mode 100644 (file)
index 63f846d..0000000
+++ /dev/null
@@ -1,5497 +0,0 @@
-/*****************************************************************************
-* sdla_x25.c   WANPIPE(tm) Multiprotocol WAN Link Driver.  X.25 module.
-*
-* Author:      Nenad Corbic    <ncorbic@sangoma.com>
-*
-* Copyright:   (c) 1995-2001 Sangoma Technologies Inc.
-*
-*              This program is free software; you can redistribute it and/or
-*              modify it under the terms of the GNU General Public License
-*              as published by the Free Software Foundation; either version
-*              2 of the License, or (at your option) any later version.
-* ============================================================================
-* Apr 03, 2001  Nenad Corbic    o Fixed the rx_skb=NULL bug in x25 in rx_intr().
-* Dec 26, 2000  Nenad Corbic    o Added a new polling routine, that uses
-*                                  a kernel timer (more efficient).
-* Dec 25, 2000  Nenad Corbic    o Updated for 2.4.X kernel
-* Jul 26, 2000  Nenad Corbic    o Increased the local packet buffering
-*                                 for API to 4096+header_size. 
-* Jul 17, 2000  Nenad Corbic    o Fixed the x25 startup bug. Enable 
-*                                 communications only after all interfaces
-*                                 come up.  HIGH SVC/PVC is used to calculate
-*                                 the number of channels.
-*                                  Enable protocol only after all interfaces
-*                                  are enabled.
-* Jul 10, 2000 Nenad Corbic     o Fixed the M_BIT bug. 
-* Apr 25, 2000  Nenad Corbic    o Pass Modem messages to the API.
-*                                  Disable idle timeout in X25 API.
-* Apr 14, 2000  Nenad Corbic    o Fixed: Large LCN number support.
-*                                  Maximum LCN number is 4095.
-*                                  Maximum number of X25 channels is 255.
-* Apr 06, 2000  Nenad Corbic    o Added SMP Support.
-* Mar 29, 2000  Nenad Corbic    o Added support for S514 PCI Card
-* Mar 23, 2000  Nenad Corbic    o Improved task queue, BH handling.
-* Mar 14, 2000  Nenad Corbic    o Updated Protocol Violation handling
-*                                  routines.  Bug Fix.
-* Mar 10, 2000  Nenad Corbic    o Bug Fix: corrupted mbox recovery.
-* Mar 09, 2000  Nenad Corbic     o Fixed the auto HDLC bug.
-* Mar 08, 2000 Nenad Corbic     o Fixed LAPB HDLC startup problems.
-*                                  Application must bring the link up 
-*                                  before tx/rx, and bring the 
-*                                  link down on close().
-* Mar 06, 2000 Nenad Corbic     o Added an option for logging call setup 
-*                                  information. 
-* Feb 29, 2000  Nenad Corbic    o Added support for LAPB HDLC API
-* Feb 25, 2000  Nenad Corbic     o Fixed the modem failure handling.
-*                                  No Modem OOB message will be passed 
-*                                  to the user.
-* Feb 21, 2000  Nenad Corbic    o Added Xpipemon Debug Support
-* Dec 30, 1999         Nenad Corbic     o Socket based X25API 
-* Sep 17, 1998 Jaspreet Singh   o Updates for 2.2.X  kernel
-* Mar 15, 1998 Alan Cox         o 2.1.x porting
-* Dec 19, 1997 Jaspreet Singh   o Added multi-channel IPX support
-* Nov 27, 1997 Jaspreet Singh   o Added protection against enabling of irqs
-*                                 when they are disabled.
-* Nov 17, 1997  Farhan Thawar    o Added IPX support
-*                               o Changed if_send() to now buffer packets when
-*                                 the board is busy
-*                               o Removed queueing of packets via the polling
-*                                 routing
-*                               o Changed if_send() critical flags to properly
-*                                 handle race conditions
-* Nov 06, 1997  Farhan Thawar    o Added support for SVC timeouts
-*                               o Changed PVC encapsulation to ETH_P_IP
-* Jul 21, 1997  Jaspreet Singh  o Fixed freeing up of buffers using kfree()
-*                                 when packets are received.
-* Mar 11, 1997  Farhan Thawar   Version 3.1.1
-*                                o added support for V35
-*                                o changed if_send() to return 0 if
-*                                  wandev.critical() is true
-*                                o free socket buffer in if_send() if
-*                                  returning 0
-*                                o added support for single '@' address to
-*                                  accept all incoming calls
-*                                o fixed bug in set_chan_state() to disconnect
-* Jan 15, 1997 Gene Kozin      Version 3.1.0
-*                               o implemented exec() entry point
-* Jan 07, 1997 Gene Kozin      Initial version.
-*****************************************************************************/
-
-/*======================================================
- *     Includes 
- *=====================================================*/
-
-#include <linux/module.h>
-#include <linux/kernel.h>      /* printk(), and other useful stuff */
-#include <linux/stddef.h>      /* offsetof(), etc. */
-#include <linux/errno.h>       /* return codes */
-#include <linux/string.h>      /* inline memset(), etc. */
-#include <linux/ctype.h>
-#include <linux/slab.h>        /* kmalloc(), kfree() */
-#include <linux/wanrouter.h>   /* WAN router definitions */
-#include <linux/wanpipe.h>     /* WANPIPE common user API definitions */
-#include <linux/workqueue.h>
-#include <linux/jiffies.h>     /* time_after() macro */
-#include <asm/byteorder.h>     /* htons(), etc. */
-#include <asm/atomic.h>
-#include <linux/delay.h>       /* Experimental delay */
-
-#include <asm/uaccess.h>
-
-#include <linux/if.h>
-#include <linux/if_arp.h>
-#include <linux/sdla_x25.h>    /* X.25 firmware API definitions */
-#include <linux/if_wanpipe_common.h>
-#include <linux/if_wanpipe.h>
-
-
-/*======================================================
- *     Defines & Macros 
- *=====================================================*/
-
-
-#define        CMD_OK          0               /* normal firmware return code */
-#define        CMD_TIMEOUT     0xFF            /* firmware command timed out */
-#define        MAX_CMD_RETRY   10              /* max number of firmware retries */
-
-#define        X25_CHAN_MTU    4096            /* unfragmented logical channel MTU */
-#define        X25_HRDHDR_SZ   7               /* max encapsulation header size */
-#define        X25_CONCT_TMOUT (90*HZ)         /* link connection timeout */
-#define        X25_RECON_TMOUT (10*HZ)         /* link connection timeout */
-#define        CONNECT_TIMEOUT (90*HZ)         /* link connection timeout */
-#define        HOLD_DOWN_TIME  (30*HZ)         /* link hold down time */
-#define MAX_BH_BUFF    10
-#define M_BIT          0x01    
-
-//#define PRINT_DEBUG 1
-#ifdef PRINT_DEBUG
-#define DBG_PRINTK(format, a...) printk(format, ## a)
-#else
-#define DBG_PRINTK(format, a...)
-#endif  
-
-#define TMR_INT_ENABLED_POLL_ACTIVE      0x01
-#define TMR_INT_ENABLED_POLL_CONNECT_ON  0x02
-#define TMR_INT_ENABLED_POLL_CONNECT_OFF 0x04
-#define TMR_INT_ENABLED_POLL_DISCONNECT  0x08
-#define TMR_INT_ENABLED_CMD_EXEC        0x10
-#define TMR_INT_ENABLED_UPDATE          0x20
-#define TMR_INT_ENABLED_UDP_PKT                 0x40
-
-#define MAX_X25_ADDR_SIZE      16
-#define MAX_X25_DATA_SIZE      129
-#define MAX_X25_FACL_SIZE      110
-
-#define TRY_CMD_AGAIN  2
-#define DELAY_RESULT    1
-#define RETURN_RESULT   0
-
-#define DCD(x) (x & 0x03 ? "HIGH" : "LOW")
-#define CTS(x) (x & 0x05 ? "HIGH" : "LOW")
-
-
-/* Driver will not write log messages about 
- * modem status if defined.*/
-#define MODEM_NOT_LOG 1
-
-/*==================================================== 
- *     For IPXWAN 
- *===================================================*/
-
-#define CVHexToAscii(b) (((unsigned char)(b) > (unsigned char)9) ? ((unsigned char)'A' + ((unsigned char)(b) - (unsigned char)10)) : ((unsigned char)'0' + (unsigned char)(b)))
-
-
-/*====================================================
- *           MEMORY DEBUGGING FUNCTION
- *====================================================
-
-#define KMEM_SAFETYZONE 8
-
-static void * dbg_kmalloc(unsigned int size, int prio, int line) {
-       int i = 0;
-       void * v = kmalloc(size+sizeof(unsigned int)+2*KMEM_SAFETYZONE*8,prio);
-       char * c1 = v;  
-       c1 += sizeof(unsigned int);
-       *((unsigned int *)v) = size;
-
-       for (i = 0; i < KMEM_SAFETYZONE; i++) {
-               c1[0] = 'D'; c1[1] = 'E'; c1[2] = 'A'; c1[3] = 'D';
-               c1[4] = 'B'; c1[5] = 'E'; c1[6] = 'E'; c1[7] = 'F';
-               c1 += 8;
-       }
-       c1 += size;
-       for (i = 0; i < KMEM_SAFETYZONE; i++) {
-               c1[0] = 'M'; c1[1] = 'U'; c1[2] = 'N'; c1[3] = 'G';
-               c1[4] = 'W'; c1[5] = 'A'; c1[6] = 'L'; c1[7] = 'L';
-               c1 += 8;
-       }
-       v = ((char *)v) + sizeof(unsigned int) + KMEM_SAFETYZONE*8;
-       printk(KERN_INFO "line %d  kmalloc(%d,%d) = %p\n",line,size,prio,v);
-       return v;
-}
-static void dbg_kfree(void * v, int line) {
-       unsigned int * sp = (unsigned int *)(((char *)v) - (sizeof(unsigned int) + KMEM_SAFETYZONE*8));
-       unsigned int size = *sp;
-       char * c1 = ((char *)v) - KMEM_SAFETYZONE*8;
-       int i = 0;
-       for (i = 0; i < KMEM_SAFETYZONE; i++) {
-               if (   c1[0] != 'D' || c1[1] != 'E' || c1[2] != 'A' || c1[3] != 'D'
-                   || c1[4] != 'B' || c1[5] != 'E' || c1[6] != 'E' || c1[7] != 'F') {
-                       printk(KERN_INFO "kmalloced block at %p has been corrupted (underrun)!\n",v);
-                       printk(KERN_INFO " %4x: %2x %2x %2x %2x %2x %2x %2x %2x\n", i*8,
-                                       c1[0],c1[1],c1[2],c1[3],c1[4],c1[5],c1[6],c1[7] );
-               }
-               c1 += 8;
-       }
-       c1 += size;
-       for (i = 0; i < KMEM_SAFETYZONE; i++) {
-               if (   c1[0] != 'M' || c1[1] != 'U' || c1[2] != 'N' || c1[3] != 'G'
-                   || c1[4] != 'W' || c1[5] != 'A' || c1[6] != 'L' || c1[7] != 'L'
-                  ) {
-                       printk(KERN_INFO "kmalloced block at %p has been corrupted (overrun):\n",v);
-                       printk(KERN_INFO " %4x: %2x %2x %2x %2x %2x %2x %2x %2x\n", i*8,
-                                       c1[0],c1[1],c1[2],c1[3],c1[4],c1[5],c1[6],c1[7] );
-               }
-               c1 += 8;
-       }
-       printk(KERN_INFO "line %d  kfree(%p)\n",line,v);
-       v = ((char *)v) - (sizeof(unsigned int) + KMEM_SAFETYZONE*8);
-       kfree(v);
-}
-
-#define kmalloc(x,y) dbg_kmalloc(x,y,__LINE__)
-#define kfree(x) dbg_kfree(x,__LINE__)
-
-==============================================================*/
-
-
-
-/*===============================================
- *     Data Structures 
- *===============================================*/
-
-
-/*========================================================
- * Name:       x25_channel
- *
- * Purpose:    To hold private informaton for each  
- *              logical channel.
- *             
- * Rationale:          Per-channel debugging is possible if each 
- *              channel has its own private area.
- *     
- * Assumptions:
- *
- * Description:        This is an extention of the struct net_device
- *              we create for each network interface to keep 
- *              the rest of X.25 channel-specific data. 
- *
- * Construct:  Typedef
- */
-typedef struct x25_channel
-{
-       wanpipe_common_t common;        /* common area for x25api and socket */
-       char name[WAN_IFNAME_SZ+1];     /* interface name, ASCIIZ */
-       char addr[WAN_ADDRESS_SZ+1];    /* media address, ASCIIZ */
-       unsigned tx_pkt_size;
-       unsigned short protocol;        /* ethertype, 0 - multiplexed */
-       char drop_sequence;             /* mark sequence for dropping */
-       unsigned long state_tick;       /* time of the last state change */
-       unsigned idle_timeout;          /* sec, before disconnecting */
-       unsigned long i_timeout_sofar;  /* # of sec's we've been idle */
-       unsigned hold_timeout;          /* sec, before re-connecting */
-       unsigned long tick_counter;     /* counter for transmit time out */
-       char devtint;                   /* Weather we should dev_tint() */
-       struct sk_buff* rx_skb;         /* receive socket buffer */
-       struct sk_buff* tx_skb;         /* transmit socket buffer */
-
-       bh_data_t *bh_head;               /* Circular buffer for x25api_bh */
-       unsigned long  tq_working;
-       volatile int  bh_write;
-       volatile int  bh_read;
-       atomic_t  bh_buff_used;
-
-       sdla_t* card;                   /* -> owner */
-       struct net_device *dev;         /* -> bound devce */
-
-       int ch_idx;
-       unsigned char enable_IPX;
-       unsigned long network_number;
-       struct net_device_stats ifstats;        /* interface statistics */
-       unsigned short transmit_length;
-       unsigned short tx_offset;
-       char transmit_buffer[X25_CHAN_MTU+sizeof(x25api_hdr_t)];
-
-       if_send_stat_t   if_send_stat;
-        rx_intr_stat_t   rx_intr_stat;
-        pipe_mgmt_stat_t pipe_mgmt_stat;    
-
-       unsigned long router_start_time; /* Router start time in seconds */
-       unsigned long router_up_time;
-       
-} x25_channel_t;
-
-/* FIXME Take this out */
-
-#ifdef NEX_OLD_CALL_INFO
-typedef struct x25_call_info
-{
-       char dest[17];                  PACKED;/* ASCIIZ destination address */
-       char src[17];                   PACKED;/* ASCIIZ source address */
-       char nuser;                     PACKED;/* number of user data bytes */
-       unsigned char user[127];        PACKED;/* user data */
-       char nfacil;                    PACKED;/* number of facilities */
-       struct
-       {
-               unsigned char code;     PACKED;
-               unsigned char parm;     PACKED;
-       } facil[64];                            /* facilities */
-} x25_call_info_t;
-#else
-typedef struct x25_call_info
-{
-       char dest[MAX_X25_ADDR_SIZE]            PACKED;/* ASCIIZ destination address */
-       char src[MAX_X25_ADDR_SIZE]             PACKED;/* ASCIIZ source address */
-       unsigned char nuser                     PACKED;
-       unsigned char user[MAX_X25_DATA_SIZE]   PACKED;/* user data */
-       unsigned char nfacil                    PACKED;
-       unsigned char facil[MAX_X25_FACL_SIZE]  PACKED;
-       unsigned short lcn                      PACKED;
-} x25_call_info_t;
-#endif
-
-
-  
-/*===============================================
- *     Private Function Prototypes
- *==============================================*/
-
-
-/*================================================= 
- * WAN link driver entry points. These are 
- * called by the WAN router module.
- */
-static int update(struct wan_device* wandev);
-static int new_if(struct wan_device* wandev, struct net_device* dev,
-                 wanif_conf_t* conf);
-static int del_if(struct wan_device* wandev, struct net_device* dev);
-static void disable_comm (sdla_t* card);
-static void disable_comm_shutdown(sdla_t *card);
-
-
-
-/*================================================= 
- *     WANPIPE-specific entry points 
- */
-static int wpx_exec (struct sdla* card, void* u_cmd, void* u_data);
-static void x25api_bh(struct net_device *dev);
-static int x25api_bh_cleanup(struct net_device *dev);
-static int bh_enqueue(struct net_device *dev, struct sk_buff *skb);
-
-
-/*=================================================  
- *     Network device interface 
- */
-static int if_init(struct net_device* dev);
-static int if_open(struct net_device* dev);
-static int if_close(struct net_device* dev);
-static int if_header(struct sk_buff* skb, struct net_device* dev,
-       unsigned short type, void* daddr, void* saddr, unsigned len);
-static int if_rebuild_hdr (struct sk_buff* skb);
-static int if_send(struct sk_buff* skb, struct net_device* dev);
-static struct net_device_stats *if_stats(struct net_device* dev);
-
-static void if_tx_timeout(struct net_device *dev);
-
-/*=================================================  
- *     Interrupt handlers 
- */
-static void wpx_isr    (sdla_t *);
-static void rx_intr    (sdla_t *);
-static void tx_intr    (sdla_t *);
-static void status_intr        (sdla_t *);
-static void event_intr (sdla_t *);
-static void spur_intr  (sdla_t *);
-static void timer_intr  (sdla_t *);
-
-static int tx_intr_send(sdla_t *card, struct net_device *dev);
-static struct net_device *move_dev_to_next(sdla_t *card,
-                                          struct net_device *dev);
-
-/*=================================================  
- *     Background polling routines 
- */
-static void wpx_poll (sdla_t* card);
-static void poll_disconnected (sdla_t* card);
-static void poll_connecting (sdla_t* card);
-static void poll_active (sdla_t* card);
-static void trigger_x25_poll(sdla_t *card);
-static void x25_timer_routine(unsigned long data);
-
-
-
-/*=================================================  
- *     X.25 firmware interface functions 
- */
-static int x25_get_version (sdla_t* card, char* str);
-static int x25_configure (sdla_t* card, TX25Config* conf);
-static int hdlc_configure (sdla_t* card, TX25Config* conf);
-static int set_hdlc_level (sdla_t* card);
-static int x25_get_err_stats (sdla_t* card);
-static int x25_get_stats (sdla_t* card);
-static int x25_set_intr_mode (sdla_t* card, int mode);
-static int x25_close_hdlc (sdla_t* card);
-static int x25_open_hdlc (sdla_t* card);
-static int x25_setup_hdlc (sdla_t* card);
-static int x25_set_dtr (sdla_t* card, int dtr);
-static int x25_get_chan_conf (sdla_t* card, x25_channel_t* chan);
-static int x25_place_call (sdla_t* card, x25_channel_t* chan);
-static int x25_accept_call (sdla_t* card, int lcn, int qdm);
-static int x25_clear_call (sdla_t* card, int lcn, int cause, int diagn);
-static int x25_send (sdla_t* card, int lcn, int qdm, int len, void* buf);
-static int x25_fetch_events (sdla_t* card);
-static int x25_error (sdla_t* card, int err, int cmd, int lcn);
-
-/*=================================================  
- *     X.25 asynchronous event handlers 
- */
-static int incoming_call (sdla_t* card, int cmd, int lcn, TX25Mbox* mb);
-static int call_accepted (sdla_t* card, int cmd, int lcn, TX25Mbox* mb);
-static int call_cleared (sdla_t* card, int cmd, int lcn, TX25Mbox* mb);
-static int timeout_event (sdla_t* card, int cmd, int lcn, TX25Mbox* mb);
-static int restart_event (sdla_t* card, int cmd, int lcn, TX25Mbox* mb);
-
-
-/*=================================================  
- *     Miscellaneous functions 
- */
-static int connect (sdla_t* card);
-static int disconnect (sdla_t* card);
-static struct net_device* get_dev_by_lcn(struct wan_device* wandev,
-                                        unsigned lcn);
-static int chan_connect(struct net_device* dev);
-static int chan_disc(struct net_device* dev);
-static void set_chan_state(struct net_device* dev, int state);
-static int chan_send(struct net_device *dev, void* buff, unsigned data_len,
-                    unsigned char tx_intr);
-static unsigned char bps_to_speed_code (unsigned long bps);
-static unsigned int dec_to_uint (unsigned char* str, int len);
-static unsigned int hex_to_uint (unsigned char*, int);
-static void parse_call_info (unsigned char*, x25_call_info_t*);
-static struct net_device *find_channel(sdla_t *card, unsigned lcn);
-static void bind_lcn_to_dev(sdla_t *card, struct net_device *dev, unsigned lcn);
-static void setup_for_delayed_transmit(struct net_device *dev,
-                                      void *buf, unsigned len);
-
-
-/*=================================================  
- *      X25 API Functions 
- */
-static int wanpipe_pull_data_in_skb(sdla_t *card, struct net_device *dev,
-                                   struct sk_buff **);
-static void timer_intr_exec(sdla_t *, unsigned char);
-static int execute_delayed_cmd(sdla_t *card, struct net_device *dev,
-                              mbox_cmd_t *usr_cmd, char bad_cmd);
-static int api_incoming_call (sdla_t*, TX25Mbox *, int);
-static int alloc_and_init_skb_buf (sdla_t *,struct sk_buff **, int);
-static void send_delayed_cmd_result(sdla_t *card, struct net_device *dev,
-                                   TX25Mbox* mbox);
-static int clear_confirm_event (sdla_t *, TX25Mbox*);
-static void send_oob_msg (sdla_t *card, struct net_device *dev, TX25Mbox *mbox);
-static int timer_intr_cmd_exec(sdla_t *card);
-static void api_oob_event (sdla_t *card,TX25Mbox *mbox);
-static int check_bad_command(sdla_t *card, struct net_device *dev);
-static int channel_disconnect(sdla_t* card, struct net_device *dev);
-static void hdlc_link_down (sdla_t*);
-
-/*=================================================
- *     XPIPEMON Functions
- */
-static int process_udp_mgmt_pkt(sdla_t *);
-static int udp_pkt_type( struct sk_buff *, sdla_t*);
-static int reply_udp( unsigned char *, unsigned int); 
-static void init_x25_channel_struct( x25_channel_t *);
-static void init_global_statistics( sdla_t *);
-static int store_udp_mgmt_pkt(int udp_type, char udp_pkt_src, sdla_t *card,
-                             struct net_device *dev,
-                             struct sk_buff *skb, int lcn);
-static unsigned short calc_checksum (char *, int);
-
-
-
-/*================================================= 
- *     IPX functions 
- */
-static void switch_net_numbers(unsigned char *, unsigned long, unsigned char);
-static int handle_IPXWAN(unsigned char *, char *, unsigned char , 
-                        unsigned long , unsigned short );
-
-extern void disable_irq(unsigned int);
-extern void enable_irq(unsigned int);
-
-static void S508_S514_lock(sdla_t *, unsigned long *);
-static void S508_S514_unlock(sdla_t *, unsigned long *);
-
-
-/*=================================================  
- *     Global Variables 
- *=================================================*/
-
-
-
-/*================================================= 
- *     Public Functions 
- *=================================================*/
-
-
-
-
-/*===================================================================
- * wpx_init:   X.25 Protocol Initialization routine.
- *
- * Purpose:    To initialize the protocol/firmware.
- * 
- * Rationale:  This function is called by setup() function, in
- *              sdlamain.c, to dynamically setup the x25 protocol.
- *             This is the first protocol specific function, which
- *              executes once on startup.
- *                
- * Description:        This procedure initializes the x25 firmware and
- *             sets up the mailbox, transmit and receive buffer
- *              pointers. It also initializes all debugging structures
- *              and sets up the X25 environment.
- *
- *             Sets up hardware options defined by user in [wanpipe#] 
- *             section of wanpipe#.conf configuration file. 
- *
- *             At this point adapter is completely initialized 
- *             and X.25 firmware is running.
- *             o read firmware version (to make sure it's alive)
- *             o configure adapter
- *             o initialize protocol-specific fields of the 
- *                adapter data space.
- *
- * Called by:  setup() function in sdlamain.c
- *
- * Assumptions:        None
- *
- * Warnings:   None
- *
- * Return:     0       o.k.
- *             < 0     failure.
- */
-
-int wpx_init (sdla_t* card, wandev_conf_t* conf)
-{
-       union{
-               char str[80];
-               TX25Config cfg;
-       } u;
-
-       /* Verify configuration ID */
-       if (conf->config_id != WANCONFIG_X25){
-               printk(KERN_INFO "%s: invalid configuration ID %u!\n",
-                       card->devname, conf->config_id)
-               ;
-               return -EINVAL;
-       }
-
-       /* Initialize protocol-specific fields */
-       card->mbox  = (void*)(card->hw.dpmbase + X25_MBOX_OFFS);
-       card->rxmb  = (void*)(card->hw.dpmbase + X25_RXMBOX_OFFS);
-       card->flags = (void*)(card->hw.dpmbase + X25_STATUS_OFFS);
-
-       /* Initialize for S514 Card */
-       if(card->hw.type == SDLA_S514) {
-               card->mbox += X25_MB_VECTOR;
-               card->flags += X25_MB_VECTOR;
-               card->rxmb += X25_MB_VECTOR;
-       }
-
-
-       /* Read firmware version.  Note that when adapter initializes, it
-        * clears the mailbox, so it may appear that the first command was
-        * executed successfully when in fact it was merely erased. To work
-        * around this, we execute the first command twice.
-        */
-       if (x25_get_version(card, NULL) || x25_get_version(card, u.str))
-               return -EIO;
-
-
-       /* X25 firmware can run ether in X25 or LAPB HDLC mode.
-         * Check the user defined option and configure accordingly */
-       if (conf->u.x25.LAPB_hdlc_only == WANOPT_YES){
-               if (set_hdlc_level(card) != CMD_OK){
-                       return -EIO;    
-               }else{
-                       printk(KERN_INFO "%s: running LAP_B HDLC firmware v%s\n",
-                               card->devname, u.str);
-               }
-               card->u.x.LAPB_hdlc = 1;
-       }else{
-               printk(KERN_INFO "%s: running X.25 firmware v%s\n",
-                               card->devname, u.str);
-               card->u.x.LAPB_hdlc = 0;
-       }
-
-       /* Configure adapter. Here we set resonable defaults, then parse
-        * device configuration structure and set configuration options.
-        * Most configuration options are verified and corrected (if
-        * necessary) since we can't rely on the adapter to do so.
-        */
-       memset(&u.cfg, 0, sizeof(u.cfg));
-       u.cfg.t1                = 3;
-       u.cfg.n2                = 10;
-       u.cfg.autoHdlc          = 1;            /* automatic HDLC connection */
-       u.cfg.hdlcWindow        = 7;
-       u.cfg.pktWindow         = 2;
-       u.cfg.station           = 1;            /* DTE */
-       u.cfg.options           = 0x0090;       /* disable D-bit pragmatics */
-       u.cfg.ccittCompat       = 1988;
-       u.cfg.t10t20            = 30;
-       u.cfg.t11t21            = 30;
-       u.cfg.t12t22            = 30;
-       u.cfg.t13t23            = 30;
-       u.cfg.t16t26            = 30;
-       u.cfg.t28               = 30;
-       u.cfg.r10r20            = 5;
-       u.cfg.r12r22            = 5;
-       u.cfg.r13r23            = 5;
-       u.cfg.responseOpt       = 1;            /* RR's after every packet */
-
-       if (card->u.x.LAPB_hdlc){
-               u.cfg.hdlcMTU = 1027;
-       }
-
-       if (conf->u.x25.x25_conf_opt){
-               u.cfg.options = conf->u.x25.x25_conf_opt;
-       }
-
-       if (conf->clocking != WANOPT_EXTERNAL)
-               u.cfg.baudRate = bps_to_speed_code(conf->bps);
-
-       if (conf->station != WANOPT_DTE){
-               u.cfg.station = 0;              /* DCE mode */
-       }
-
-        if (conf->interface != WANOPT_RS232 ){
-               u.cfg.hdlcOptions |= 0x80;      /* V35 mode */
-       } 
-
-       /* adjust MTU */
-       if (!conf->mtu || (conf->mtu >= 1024))
-               card->wandev.mtu = 1024;
-       else if (conf->mtu >= 512)
-               card->wandev.mtu = 512;
-       else if (conf->mtu >= 256)
-               card->wandev.mtu = 256;
-       else if (conf->mtu >= 128)
-               card->wandev.mtu = 128;
-       else 
-               card->wandev.mtu = 64;
-
-       u.cfg.defPktSize = u.cfg.pktMTU = card->wandev.mtu;
-
-       if (conf->u.x25.hi_pvc){
-               card->u.x.hi_pvc = min_t(unsigned int, conf->u.x25.hi_pvc, MAX_LCN_NUM);
-               card->u.x.lo_pvc = min_t(unsigned int, conf->u.x25.lo_pvc, card->u.x.hi_pvc);
-       }
-
-       if (conf->u.x25.hi_svc){
-               card->u.x.hi_svc = min_t(unsigned int, conf->u.x25.hi_svc, MAX_LCN_NUM);
-               card->u.x.lo_svc = min_t(unsigned int, conf->u.x25.lo_svc, card->u.x.hi_svc);
-       }
-
-       /* Figure out the total number of channels to configure */
-       card->u.x.num_of_ch = 0;
-       if (card->u.x.hi_svc != 0){
-               card->u.x.num_of_ch = (card->u.x.hi_svc - card->u.x.lo_svc) + 1;
-       }
-       if (card->u.x.hi_pvc != 0){
-               card->u.x.num_of_ch += (card->u.x.hi_pvc - card->u.x.lo_pvc) + 1;
-       }
-
-       if (card->u.x.num_of_ch == 0){
-               printk(KERN_INFO "%s: ERROR, Minimum number of PVC/SVC channels is 1 !\n"
-                                "%s: Please set the Lowest/Highest PVC/SVC values !\n",
-                                card->devname,card->devname);
-               return -ECHRNG;
-       }
-       
-       u.cfg.loPVC = card->u.x.lo_pvc;
-       u.cfg.hiPVC = card->u.x.hi_pvc;
-       u.cfg.loTwoWaySVC = card->u.x.lo_svc;
-       u.cfg.hiTwoWaySVC = card->u.x.hi_svc;
-
-       if (conf->u.x25.hdlc_window)
-               u.cfg.hdlcWindow = min_t(unsigned int, conf->u.x25.hdlc_window, 7);
-       if (conf->u.x25.pkt_window)
-               u.cfg.pktWindow = min_t(unsigned int, conf->u.x25.pkt_window, 7);
-
-       if (conf->u.x25.t1)
-               u.cfg.t1 = min_t(unsigned int, conf->u.x25.t1, 30);
-       if (conf->u.x25.t2)
-               u.cfg.t2 = min_t(unsigned int, conf->u.x25.t2, 29);
-       if (conf->u.x25.t4)
-               u.cfg.t4 = min_t(unsigned int, conf->u.x25.t4, 240);
-       if (conf->u.x25.n2)
-               u.cfg.n2 = min_t(unsigned int, conf->u.x25.n2, 30);
-
-       if (conf->u.x25.t10_t20)
-               u.cfg.t10t20 = min_t(unsigned int, conf->u.x25.t10_t20,255);
-       if (conf->u.x25.t11_t21)
-               u.cfg.t11t21 = min_t(unsigned int, conf->u.x25.t11_t21,255);
-       if (conf->u.x25.t12_t22)
-               u.cfg.t12t22 = min_t(unsigned int, conf->u.x25.t12_t22,255);
-       if (conf->u.x25.t13_t23)        
-               u.cfg.t13t23 = min_t(unsigned int, conf->u.x25.t13_t23,255);
-       if (conf->u.x25.t16_t26)
-               u.cfg.t16t26 = min_t(unsigned int, conf->u.x25.t16_t26, 255);
-       if (conf->u.x25.t28)
-               u.cfg.t28 = min_t(unsigned int, conf->u.x25.t28, 255);
-
-       if (conf->u.x25.r10_r20)
-               u.cfg.r10r20 = min_t(unsigned int, conf->u.x25.r10_r20,250);
-       if (conf->u.x25.r12_r22)
-               u.cfg.r12r22 = min_t(unsigned int, conf->u.x25.r12_r22,250);
-       if (conf->u.x25.r13_r23)
-               u.cfg.r13r23 = min_t(unsigned int, conf->u.x25.r13_r23,250);
-
-
-       if (conf->u.x25.ccitt_compat)
-               u.cfg.ccittCompat = conf->u.x25.ccitt_compat;
-
-       /* initialize adapter */
-       if (card->u.x.LAPB_hdlc){
-               if (hdlc_configure(card, &u.cfg) != CMD_OK)
-                       return -EIO;
-       }else{
-               if (x25_configure(card, &u.cfg) != CMD_OK)
-                       return -EIO;
-       }
-
-       if ((x25_close_hdlc(card) != CMD_OK) ||         /* close HDLC link */
-           (x25_set_dtr(card, 0) != CMD_OK))           /* drop DTR */
-               return -EIO;
-
-       /* Initialize protocol-specific fields of adapter data space */
-       card->wandev.bps        = conf->bps;
-       card->wandev.interface  = conf->interface;
-       card->wandev.clocking   = conf->clocking;
-       card->wandev.station    = conf->station;
-       card->isr               = &wpx_isr;
-       card->poll              = NULL; //&wpx_poll;
-       card->disable_comm      = &disable_comm;
-       card->exec              = &wpx_exec;
-       card->wandev.update     = &update;
-       card->wandev.new_if     = &new_if;
-       card->wandev.del_if     = &del_if;
-
-       /* WARNING: This function cannot exit with an error
-        *          after the change of state */
-       card->wandev.state      = WAN_DISCONNECTED;
-       
-       card->wandev.enable_tx_int = 0;
-       card->irq_dis_if_send_count = 0;
-        card->irq_dis_poll_count = 0;
-       card->u.x.tx_dev = NULL;
-       card->u.x.no_dev = 0;
-
-
-       /* Configure for S514 PCI Card */
-       if (card->hw.type == SDLA_S514) {
-               card->u.x.hdlc_buf_status = 
-                       (volatile unsigned char *)
-                               (card->hw.dpmbase + X25_MB_VECTOR+ X25_MISC_HDLC_BITS);
-       }else{
-               card->u.x.hdlc_buf_status = 
-                       (volatile unsigned char *)(card->hw.dpmbase + X25_MISC_HDLC_BITS); 
-       }
-
-       card->u.x.poll_device=NULL;
-       card->wandev.udp_port = conf->udp_port;
-
-       /* Enable or disable call setup logging */
-       if (conf->u.x25.logging == WANOPT_YES){
-               printk(KERN_INFO "%s: Enabling Call Logging.\n",
-                       card->devname);
-               card->u.x.logging = 1;
-       }else{  
-               card->u.x.logging = 0;
-       }
-
-       /* Enable or disable modem status reporting */
-       if (conf->u.x25.oob_on_modem == WANOPT_YES){
-               printk(KERN_INFO "%s: Enabling OOB on Modem change.\n",
-                       card->devname);
-               card->u.x.oob_on_modem = 1;
-       }else{
-               card->u.x.oob_on_modem = 0;
-       }
-       
-       init_global_statistics(card);   
-
-       INIT_WORK(&card->u.x.x25_poll_work, (void *)wpx_poll, card);
-
-       init_timer(&card->u.x.x25_timer);
-       card->u.x.x25_timer.data = (unsigned long)card;
-       card->u.x.x25_timer.function = x25_timer_routine;
-       
-       return 0;
-}
-
-/*=========================================================
- *     WAN Device Driver Entry Points 
- *========================================================*/
-
-/*============================================================
- * Name:       update(),  Update device status & statistics.
- *
- * Purpose:    To provide debugging and statitical
- *              information to the /proc file system.
- *              /proc/net/wanrouter/wanpipe#
- *                     
- * Rationale:  The /proc file system is used to collect
- *              information about the kernel and drivers.
- *              Using the /proc file system the user
- *              can see exactly what the sangoma drivers are
- *              doing. And in what state they are in. 
- *                
- * Description: Collect all driver statistical information
- *              and pass it to the top laywer. 
- *             
- *             Since we have to execute a debugging command, 
- *              to obtain firmware statitics, we trigger a 
- *              UPDATE function within the timer interrtup.
- *              We wait until the timer update is complete.
- *              Once complete return the appropriate return
- *              code to indicate that the update was successful.
- *              
- * Called by:  device_stat() in wanmain.c
- *
- * Assumptions:        
- *
- * Warnings:   This function will degrade the performance
- *              of the router, since it uses the mailbox. 
- *
- * Return:     0       OK
- *             <0      Failed (or busy).
- */
-
-static int update(struct wan_device* wandev)
-{
-       volatile sdla_t* card;
-       TX25Status* status;
-       unsigned long timeout;
-
-       /* sanity checks */
-       if ((wandev == NULL) || (wandev->private == NULL))
-               return -EFAULT;
-
-       if (wandev->state == WAN_UNCONFIGURED)
-               return -ENODEV;
-
-       if (test_bit(SEND_CRIT, (void*)&wandev->critical))
-               return -EAGAIN;
-
-       if (!wandev->dev)
-               return -ENODEV;
-       
-       card = wandev->private;
-       status = card->flags;
-
-       card->u.x.timer_int_enabled |= TMR_INT_ENABLED_UPDATE;
-       status->imask |= INTR_ON_TIMER;
-       timeout = jiffies;      
-
-       for (;;){
-               if (!(card->u.x.timer_int_enabled & TMR_INT_ENABLED_UPDATE)){   
-                       break;
-               }
-               if (time_after(jiffies, timeout + 1*HZ)){
-                       card->u.x.timer_int_enabled &= ~TMR_INT_ENABLED_UPDATE;
-                       return -EAGAIN;
-               }
-       }
-       return 0;
-}
-
-
-/*===================================================================
- * Name:       new_if
- *
- * Purpose:    To allocate and initialize resources for a 
- *              new logical channel.  
- * 
- * Rationale:  A new channel can be added dynamically via
- *              ioctl call.
- *                
- * Description:        Allocate a private channel structure, x25_channel_t.
- *             Parse the user interface options from wanpipe#.conf 
- *             configuration file. 
- *             Bind the private are into the network device private
- *              area pointer (dev->priv).
- *             Prepare the network device structure for registration.
- *
- * Called by:  ROUTER_IFNEW Ioctl call, from wanrouter_ioctl() 
- *              (wanmain.c)
- *
- * Assumptions: None
- *
- * Warnings:   None
- *
- * Return:     0       Ok
- *             <0      Failed (channel will not be created)
- */
-static int new_if(struct wan_device* wandev, struct net_device* dev,
-                 wanif_conf_t* conf)
-{
-       sdla_t* card = wandev->private;
-       x25_channel_t* chan;
-       int err = 0;
-
-       if ((conf->name[0] == '\0') || (strlen(conf->name) > WAN_IFNAME_SZ)){
-               printk(KERN_INFO "%s: invalid interface name!\n",
-                       card->devname);
-               return -EINVAL;
-       }
-
-       if(card->wandev.new_if_cnt++ > 0 && card->u.x.LAPB_hdlc) {
-               printk(KERN_INFO "%s: Error: Running LAPB HDLC Mode !\n",
-                                               card->devname);
-               printk(KERN_INFO 
-                       "%s: Maximum number of network interfaces must be one !\n",
-                                               card->devname);
-               return -EEXIST;
-       }
-
-       /* allocate and initialize private data */
-       chan = kmalloc(sizeof(x25_channel_t), GFP_ATOMIC);
-       if (chan == NULL){
-               return -ENOMEM;
-       }
-       
-       memset(chan, 0, sizeof(x25_channel_t));
-
-       /* Bug Fix: Seg Err on PVC startup
-        * It must be here since bind_lcn_to_dev expects 
-        * it bellow */
-       dev->priv = chan;
-       
-       strcpy(chan->name, conf->name);
-       chan->card = card;
-       chan->dev = dev;
-       chan->common.sk = NULL;
-       chan->common.func = NULL;
-       chan->common.rw_bind = 0;
-       chan->tx_skb = chan->rx_skb = NULL;
-
-       /* verify media address */
-       if (conf->addr[0] == '@'){              /* SVC */
-               chan->common.svc = 1;
-               strncpy(chan->addr, &conf->addr[1], WAN_ADDRESS_SZ);
-
-               /* Set channel timeouts (default if not specified) */
-               chan->idle_timeout = (conf->idle_timeout) ? 
-                                       conf->idle_timeout : 90;
-               chan->hold_timeout = (conf->hold_timeout) ? 
-                                       conf->hold_timeout : 10;
-
-       }else if (isdigit(conf->addr[0])){      /* PVC */
-               int lcn = dec_to_uint(conf->addr, 0);
-
-               if ((lcn >= card->u.x.lo_pvc) && (lcn <= card->u.x.hi_pvc)){
-                       bind_lcn_to_dev (card, dev, lcn);
-               }else{
-                       printk(KERN_ERR
-                               "%s: PVC %u is out of range on interface %s!\n",
-                               wandev->name, lcn, chan->name);
-                       err = -EINVAL;
-               }
-       }else{
-               printk(KERN_ERR
-                       "%s: invalid media address on interface %s!\n",
-                       wandev->name, chan->name);
-               err = -EINVAL;
-       }
-
-       if(strcmp(conf->usedby, "WANPIPE") == 0){
-                printk(KERN_INFO "%s: Running in WANPIPE mode %s\n",
-                       wandev->name, chan->name);
-                chan->common.usedby = WANPIPE;
-               chan->protocol = htons(ETH_P_IP);
-
-        }else if(strcmp(conf->usedby, "API") == 0){
-               chan->common.usedby = API;
-                printk(KERN_INFO "%s: Running in API mode %s\n",
-                       wandev->name, chan->name);
-               chan->protocol = htons(X25_PROT);
-       }
-
-
-       if (err){
-               kfree(chan);
-               dev->priv = NULL;
-               return err;
-       }
-       
-       chan->enable_IPX = conf->enable_IPX;
-       
-       if (chan->enable_IPX)
-               chan->protocol = htons(ETH_P_IPX);
-       
-       if (conf->network_number)
-               chan->network_number = conf->network_number;
-       else
-               chan->network_number = 0xDEADBEEF;
-
-       /* prepare network device data space for registration */
-       strcpy(dev->name,chan->name);
-
-       dev->init = &if_init;
-
-       init_x25_channel_struct(chan);
-
-       return 0;
-}
-
-/*===================================================================
- * Name:       del_if(),  Remove a logical channel.     
- *
- * Purpose:    To dynamically remove a logical channel.
- * 
- * Rationale:  Each logical channel should be dynamically
- *              removable. This functin is called by an 
- *              IOCTL_IFDEL ioctl call or shutdown(). 
- *                
- * Description: Do nothing.
- *
- * Called by:  IOCTL_IFDEL : wanrouter_ioctl() from wanmain.c
- *              shutdown() from sdlamain.c
- *
- * Assumptions: 
- *
- * Warnings:
- *
- * Return:     0 Ok. Void function.
- */
-
-//FIXME Del IF Should be taken out now.
-
-static int del_if(struct wan_device* wandev, struct net_device* dev)
-{
-       return 0;
-}
-
-
-/*============================================================
- * Name:       wpx_exec
- *
- * Description:        Execute adapter interface command.
- *             This option is currently dissabled.
- *===========================================================*/
-
-static int wpx_exec (struct sdla* card, void* u_cmd, void* u_data)
-{
-        return 0;
-}
-
-/*============================================================
- * Name:       disable_comm    
- *
- * Description:        Disable communications during shutdown.
- *              Dont check return code because there is 
- *              nothing we can do about it.  
- *
- * Warning:    Dev and private areas are gone at this point.
- *===========================================================*/
-
-static void disable_comm(sdla_t* card)
-{
-       disable_comm_shutdown(card);
-       del_timer(&card->u.x.x25_timer);
-       return;
-}
-
-
-/*============================================================
- *     Network Device Interface 
- *===========================================================*/
-
-/*===================================================================
- * Name:       if_init(),   Netowrk Interface Initialization    
- *
- * Purpose:    To initialize a network interface device structure.
- * 
- * Rationale:  During network interface startup, the if_init
- *              is called by the kernel to initialize the
- *              netowrk device structure.  Thus a driver
- *              can customze a network device. 
- *                
- * Description:        Initialize the netowrk device call back
- *              routines.  This is where we tell the kernel
- *              which function to use when it wants to send
- *              via our interface. 
- *             Furthermore, we initialize the device flags, 
- *              MTU and physical address of the board.
- *
- * Called by:  Kernel (/usr/src/linux/net/core/dev.c)
- *             (dev->init())
- *
- * Assumptions: None
- *     
- * Warnings:   None
- *
- * Return:     0       Ok : Void function.
- */
-static int if_init(struct net_device* dev)
-{
-       x25_channel_t* chan = dev->priv;
-       sdla_t* card = chan->card;
-       struct wan_device* wandev = &card->wandev;
-
-       /* Initialize device driver entry points */
-       dev->open               = &if_open;
-       dev->stop               = &if_close;
-       dev->hard_header        = &if_header;
-       dev->rebuild_header     = &if_rebuild_hdr;
-       dev->hard_start_xmit    = &if_send;
-       dev->get_stats          = &if_stats;
-       dev->tx_timeout         = &if_tx_timeout;
-       dev->watchdog_timeo     = TX_TIMEOUT;
-
-       /* Initialize media-specific parameters */
-       dev->type               = ARPHRD_PPP;           /* ARP h/w type */
-       dev->flags              |= IFF_POINTOPOINT;
-       dev->flags              |= IFF_NOARP;
-
-       if (chan->common.usedby == API){
-               dev->mtu        = X25_CHAN_MTU+sizeof(x25api_hdr_t);
-       }else{
-               dev->mtu        = card->wandev.mtu;     
-       }
-       
-       dev->hard_header_len    = X25_HRDHDR_SZ; /* media header length */
-       dev->addr_len           = 2;            /* hardware address length */
-       
-       if (!chan->common.svc){
-               *(unsigned short*)dev->dev_addr = htons(chan->common.lcn);
-       }
-       
-       /* Initialize hardware parameters (just for reference) */
-       dev->irq        = wandev->irq;
-       dev->dma        = wandev->dma;
-       dev->base_addr  = wandev->ioport;
-       dev->mem_start  = (unsigned long)wandev->maddr;
-       dev->mem_end    = wandev->maddr + wandev->msize - 1;
-
-        /* Set transmit buffer queue length */
-        dev->tx_queue_len = 100;
-       SET_MODULE_OWNER(dev);
-
-       /* FIXME Why are we doing this */
-       set_chan_state(dev, WAN_DISCONNECTED);
-       return 0;
-}
-
-
-/*===================================================================
- * Name:       if_open(),   Open/Bring up the Netowrk Interface 
- *
- * Purpose:    To bring up a network interface.
- * 
- * Rationale:  
- *                
- * Description:        Open network interface.
- *             o prevent module from unloading by incrementing use count
- *             o if link is disconnected then initiate connection
- *
- * Called by:  Kernel (/usr/src/linux/net/core/dev.c)
- *             (dev->open())
- *
- * Assumptions: None
- *     
- * Warnings:   None
- *
- * Return:     0       Ok
- *             <0      Failure: Interface will not come up.
- */
-
-static int if_open(struct net_device* dev)
-{
-       x25_channel_t* chan = dev->priv;
-       sdla_t* card = chan->card;
-       struct timeval tv;
-       unsigned long smp_flags;
-       
-       if (netif_running(dev))
-               return -EBUSY;
-
-       chan->tq_working = 0;
-
-       /* Initialize the workqueue */
-       INIT_WORK(&chan->common.wanpipe_work, (void *)x25api_bh, dev);
-
-       /* Allocate and initialize BH circular buffer */
-       /* Add 1 to MAX_BH_BUFF so we don't have test with (MAX_BH_BUFF-1) */
-       chan->bh_head = kmalloc((sizeof(bh_data_t)*(MAX_BH_BUFF+1)),GFP_ATOMIC);
-
-       if (chan->bh_head == NULL){
-               printk(KERN_INFO "%s: ERROR, failed to allocate memory ! BH_BUFFERS !\n",
-                               card->devname);
-
-               return -ENOBUFS;
-       }
-       memset(chan->bh_head,0,(sizeof(bh_data_t)*(MAX_BH_BUFF+1)));
-       atomic_set(&chan->bh_buff_used, 0);
-
-       /* Increment the number of interfaces */
-       ++card->u.x.no_dev;
-       
-       wanpipe_open(card);
-
-       /* LAPB protocol only uses one interface, thus
-        * start the protocol after it comes up. */
-       if (card->u.x.LAPB_hdlc){
-               if (card->open_cnt == 1){
-                       TX25Status* status = card->flags;
-                       S508_S514_lock(card, &smp_flags);
-                       x25_set_intr_mode(card, INTR_ON_TIMER); 
-                       status->imask &= ~INTR_ON_TIMER;
-                       S508_S514_unlock(card, &smp_flags);
-               }
-       }else{
-               /* X25 can have multiple interfaces thus, start the 
-                * protocol once all interfaces are up */
-
-               //FIXME: There is a bug here. If interface is
-               //brought down and up, it will try to enable comm.
-               if (card->open_cnt == card->u.x.num_of_ch){
-
-                       S508_S514_lock(card, &smp_flags);
-                       connect(card);
-                       S508_S514_unlock(card, &smp_flags);
-
-                       mod_timer(&card->u.x.x25_timer, jiffies + HZ);
-               }
-       }
-       /* Device is not up until the we are in connected state */
-       do_gettimeofday( &tv );
-       chan->router_start_time = tv.tv_sec;
-
-       netif_start_queue(dev);
-
-       return 0;
-}
-
-/*===================================================================
- * Name:       if_close(),   Close/Bring down the Netowrk Interface 
- *
- * Purpose:    To bring down a network interface.
- * 
- * Rationale:  
- *                
- * Description:        Close network interface.
- *             o decrement use module use count
- *
- * Called by:  Kernel (/usr/src/linux/net/core/dev.c)
- *             (dev->close())
- *             ifconfig <name> down: will trigger the kernel
- *              which will call this function.
- *
- * Assumptions: None
- *     
- * Warnings:   None
- *
- * Return:     0       Ok
- *             <0      Failure: Interface will not exit properly.
- */
-static int if_close(struct net_device* dev)
-{
-       x25_channel_t* chan = dev->priv;
-       sdla_t* card = chan->card;
-       unsigned long smp_flags;
-       
-       netif_stop_queue(dev);
-
-       if ((chan->common.state == WAN_CONNECTED) || 
-           (chan->common.state == WAN_CONNECTING)){
-               S508_S514_lock(card, &smp_flags);
-               chan_disc(dev);
-               S508_S514_unlock(card, &smp_flags);
-       }
-
-       wanpipe_close(card);
-
-       S508_S514_lock(card, &smp_flags);
-       if (chan->bh_head){
-               int i;
-               struct sk_buff *skb;
-       
-               for (i=0; i<(MAX_BH_BUFF+1); i++){
-                       skb = ((bh_data_t *)&chan->bh_head[i])->skb;
-                       if (skb != NULL){
-                               dev_kfree_skb_any(skb);
-                       }
-               }
-               kfree(chan->bh_head);
-               chan->bh_head=NULL;
-       }
-       S508_S514_unlock(card, &smp_flags);
-
-       /* If this is the last close, disconnect physical link */
-       if (!card->open_cnt){
-               S508_S514_lock(card, &smp_flags);
-               disconnect(card);
-               x25_set_intr_mode(card, 0);
-               S508_S514_unlock(card, &smp_flags);
-       }
-       
-       /* Decrement the number of interfaces */
-       --card->u.x.no_dev;
-       return 0;
-}
-
-/*======================================================================
- *     Build media header.
- *     o encapsulate packet according to encapsulation type.
- *
- *     The trick here is to put packet type (Ethertype) into 'protocol' 
- *      field of the socket buffer, so that we don't forget it.  
- *      If encapsulation fails, set skb->protocol to 0 and discard 
- *      packet later.
- *
- *     Return:         media header length.
- *======================================================================*/
-
-static int if_header(struct sk_buff* skb, struct net_device* dev,
-                    unsigned short type, void* daddr, void* saddr,
-                    unsigned len)
-{
-       x25_channel_t* chan = dev->priv;
-       int hdr_len = dev->hard_header_len;
-       
-       skb->protocol = htons(type);
-       if (!chan->protocol){
-               hdr_len = wanrouter_encapsulate(skb, dev, type);
-               if (hdr_len < 0){
-                       hdr_len = 0;
-                       skb->protocol = htons(0);
-               }
-       }
-       return hdr_len;
-}
-
-/*===============================================================
- *     Re-build media header.
- *
- *     Return:         1       physical address resolved.
- *                     0       physical address not resolved
- *==============================================================*/
-
-static int if_rebuild_hdr (struct sk_buff* skb)
-{
-       struct net_device *dev = skb->dev; 
-       x25_channel_t* chan = dev->priv;
-       sdla_t* card = chan->card;
-
-       printk(KERN_INFO "%s: rebuild_header() called for interface %s!\n",
-               card->devname, dev->name);
-       return 1;
-}
-
-
-/*============================================================================
- * Handle transmit timeout event from netif watchdog
- */
-static void if_tx_timeout(struct net_device *dev)
-{
-       x25_channel_t* chan = dev->priv;
-       sdla_t *card = chan->card;
-
-       /* If our device stays busy for at least 5 seconds then we will
-        * kick start the device by making dev->tbusy = 0.  We expect
-        * that our device never stays busy more than 5 seconds. So this                 
-        * is only used as a last resort.
-        */
-
-       ++chan->if_send_stat.if_send_tbusy_timeout;
-       printk (KERN_INFO "%s: Transmit timed out on %s\n", 
-                       card->devname, dev->name);
-       netif_wake_queue (dev);
-}
-
-
-/*=========================================================================
- *     Send a packet on a network interface.
- *     o set tbusy flag (marks start of the transmission).
- *     o check link state. If link is not up, then drop the packet.
- *     o check channel status. If it's down then initiate a call.
- *     o pass a packet to corresponding WAN device.
- *     o free socket buffer
- *
- *     Return: 0       complete (socket buffer must be freed)
- *             non-0   packet may be re-transmitted (tbusy must be set)
- *
- *     Notes:
- *     1. This routine is called either by the protocol stack or by the "net
- *     bottom half" (with interrupts enabled).
- *     2. Setting tbusy flag will inhibit further transmit requests from the
- *     protocol stack and can be used for flow control with protocol layer.
- *
- *========================================================================*/
-
-static int if_send(struct sk_buff* skb, struct net_device* dev)
-{
-       x25_channel_t* chan = dev->priv;
-       sdla_t* card = chan->card;
-       TX25Status* status = card->flags;
-       int udp_type;
-       unsigned long smp_flags=0;
-
-       ++chan->if_send_stat.if_send_entry;
-
-       netif_stop_queue(dev);
-
-       /* No need to check frame length, since socket code
-         * will perform the check for us */
-
-       chan->tick_counter = jiffies;
-       
-       /* Critical region starts here */
-       S508_S514_lock(card, &smp_flags);
-       
-       if (test_and_set_bit(SEND_CRIT, (void*)&card->wandev.critical)){
-               printk(KERN_INFO "Hit critical in if_send()! %lx\n",card->wandev.critical);
-               goto if_send_crit_exit;
-       }
-       
-       udp_type = udp_pkt_type(skb, card);
-
-        if(udp_type != UDP_INVALID_TYPE) {
-
-                if(store_udp_mgmt_pkt(udp_type, UDP_PKT_FRM_STACK, card, dev, skb,
-                        chan->common.lcn)) {
-
-                        status->imask |= INTR_ON_TIMER;
-                        if (udp_type == UDP_XPIPE_TYPE){
-                                chan->if_send_stat.if_send_PIPE_request++;
-                       }
-                       }
-               netif_start_queue(dev);
-               clear_bit(SEND_CRIT,(void*)&card->wandev.critical);
-               S508_S514_unlock(card, &smp_flags);
-               return 0;
-       }
-
-       if (chan->transmit_length){
-               //FIXME: This check doesn't make sense any more
-               if (chan->common.state != WAN_CONNECTED){
-                       chan->transmit_length=0;
-                       atomic_set(&chan->common.driver_busy,0);
-               }else{
-                       netif_stop_queue(dev);
-                       ++card->u.x.tx_interrupts_pending;
-                       status->imask |= INTR_ON_TX_FRAME;
-                       clear_bit(SEND_CRIT,(void*)&card->wandev.critical);
-                       S508_S514_unlock(card, &smp_flags);
-                       return 1;
-               }
-       }
-
-       if (card->wandev.state != WAN_CONNECTED){
-               ++chan->ifstats.tx_dropped;
-               ++card->wandev.stats.tx_dropped;
-               ++chan->if_send_stat.if_send_wan_disconnected;  
-               
-       }else if ( chan->protocol && (chan->protocol != skb->protocol)){
-               printk(KERN_INFO
-                       "%s: unsupported Ethertype 0x%04X on interface %s!\n",
-                       chan->name, htons(skb->protocol), dev->name);
-               
-               printk(KERN_INFO "PROTO %Xn", htons(chan->protocol));
-               ++chan->ifstats.tx_errors;
-               ++chan->ifstats.tx_dropped;
-               ++card->wandev.stats.tx_dropped;
-               ++chan->if_send_stat.if_send_protocol_error;
-               
-       }else switch (chan->common.state){
-
-               case WAN_DISCONNECTED:
-                       /* Try to establish connection. If succeded, then start
-                        * transmission, else drop a packet.
-                        */
-                       if (chan->common.usedby == API){
-                               ++chan->ifstats.tx_dropped;
-                               ++card->wandev.stats.tx_dropped;
-                               break;
-                       }else{
-                               if (chan_connect(dev) != 0){
-                                       ++chan->ifstats.tx_dropped;
-                                       ++card->wandev.stats.tx_dropped;
-                                       break;
-                               }
-                       }
-                       /* fall through */
-
-               case WAN_CONNECTED:
-                       if( skb->protocol == htons(ETH_P_IPX)) {
-                               if(chan->enable_IPX) {
-                                       switch_net_numbers( skb->data, 
-                                               chan->network_number, 0);
-                               } else {
-                                       ++card->wandev.stats.tx_dropped;
-                                       ++chan->ifstats.tx_dropped;
-                                       ++chan->if_send_stat.if_send_protocol_error;
-                                       goto if_send_crit_exit;
-                               }
-                       }
-                       /* We never drop here, if cannot send than, copy
-                        * a packet into a transmit buffer 
-                         */
-                       chan_send(dev, skb->data, skb->len, 0);
-                       break;
-
-               default:
-                       ++chan->ifstats.tx_dropped;     
-                       ++card->wandev.stats.tx_dropped;
-                       break;
-       }
-
-
-if_send_crit_exit:
-       
-               dev_kfree_skb_any(skb);
-
-       netif_start_queue(dev);
-       clear_bit(SEND_CRIT,(void*)&card->wandev.critical);
-       S508_S514_unlock(card, &smp_flags);
-       return 0;
-}
-
-/*============================================================================
- * Setup so that a frame can be transmitted on the occurrence of a transmit
- * interrupt.
- *===========================================================================*/
-
-static void setup_for_delayed_transmit(struct net_device* dev, void* buf,
-                                      unsigned len)
-{
-        x25_channel_t* chan = dev->priv;
-        sdla_t* card = chan->card;
-       TX25Status* status = card->flags;
-
-       ++chan->if_send_stat.if_send_adptr_bfrs_full;
-
-        if(chan->transmit_length) {
-                printk(KERN_INFO "%s: Error, transmit length set in delayed transmit!\n",
-                               card->devname);
-                return;
-        }
-
-       if (chan->common.usedby == API){
-               if (len > X25_CHAN_MTU+sizeof(x25api_hdr_t)) {
-                       ++chan->ifstats.tx_dropped;     
-                       ++card->wandev.stats.tx_dropped;
-                       printk(KERN_INFO "%s: Length is too big for delayed transmit\n",
-                               card->devname);
-                       return;
-               }
-       }else{
-               if (len > X25_MAX_DATA) {
-                       ++chan->ifstats.tx_dropped;     
-                       ++card->wandev.stats.tx_dropped;
-                       printk(KERN_INFO "%s: Length is too big for delayed transmit\n",
-                               card->devname);
-                       return;
-               }
-       }
-
-        chan->transmit_length = len;
-       atomic_set(&chan->common.driver_busy,1);
-        memcpy(chan->transmit_buffer, buf, len);
-
-       ++chan->if_send_stat.if_send_tx_int_enabled;
-
-       /* Enable Transmit Interrupt */
-       ++card->u.x.tx_interrupts_pending;
-        status->imask |= INTR_ON_TX_FRAME;
-}
-
-
-/*===============================================================
- * net_device_stats
- *
- *     Get ethernet-style interface statistics.
- *     Return a pointer to struct enet_statistics.
- *
- *==============================================================*/
-static struct net_device_stats *if_stats(struct net_device* dev)
-{
-       x25_channel_t *chan = dev->priv;
-
-       if(chan == NULL)
-               return NULL;
-
-       return &chan->ifstats;
-}
-
-
-/*
- *     Interrupt Handlers 
- */
-
-/*
- * X.25 Interrupt Service Routine.
- */
-
-static void wpx_isr (sdla_t* card)
-{
-       TX25Status* status = card->flags;
-
-       card->in_isr = 1;
-       ++card->statistics.isr_entry;
-
-       if (test_bit(PERI_CRIT,(void*)&card->wandev.critical)){
-               card->in_isr=0;
-               status->iflags = 0;
-               return;
-       }
-       
-       if (test_bit(SEND_CRIT, (void*)&card->wandev.critical)){
-
-               printk(KERN_INFO "%s: wpx_isr: wandev.critical set to 0x%02lx, int type = 0x%02x\n", 
-                       card->devname, card->wandev.critical, status->iflags);
-               card->in_isr = 0;
-               status->iflags = 0;
-               return;
-       }
-
-       /* For all interrupts set the critical flag to CRITICAL_RX_INTR.
-         * If the if_send routine is called with this flag set it will set
-         * the enable transmit flag to 1. (for a delayed interrupt)
-         */
-       switch (status->iflags){
-
-               case RX_INTR_PENDING:           /* receive interrupt */
-                       rx_intr(card);
-                       break;
-
-               case TX_INTR_PENDING:           /* transmit interrupt */
-                       tx_intr(card);
-                       break;
-
-               case MODEM_INTR_PENDING:        /* modem status interrupt */
-                       status_intr(card);
-                       break;
-
-               case X25_ASY_TRANS_INTR_PENDING:        /* network event interrupt */
-                       event_intr(card);
-                       break;
-
-               case TIMER_INTR_PENDING:
-                       timer_intr(card);
-                       break;
-
-               default:                /* unwanted interrupt */
-                       spur_intr(card);
-       }
-
-       card->in_isr = 0;
-       status->iflags = 0;     /* clear interrupt condition */
-}
-
-/*
- *     Receive interrupt handler.
- *     This routine handles fragmented IP packets using M-bit according to the
- *     RFC1356.
- *     o map ligical channel number to network interface.
- *     o allocate socket buffer or append received packet to the existing one.
- *     o if M-bit is reset (i.e. it's the last packet in a sequence) then 
- *     decapsulate packet and pass socket buffer to the protocol stack.
- *
- *     Notes:
- *     1. When allocating a socket buffer, if M-bit is set then more data is
- *     coming and we have to allocate buffer for the maximum IP packet size
- *     expected on this channel.
- *     2. If something goes wrong and X.25 packet has to be dropped (e.g. no
- *     socket buffers available) the whole packet sequence must be discarded.
- */
-
-static void rx_intr (sdla_t* card)
-{
-       TX25Mbox* rxmb = card->rxmb;
-       unsigned lcn = rxmb->cmd.lcn;
-       struct net_device* dev = find_channel(card,lcn);
-       x25_channel_t* chan;
-       struct sk_buff* skb=NULL;
-
-       if (dev == NULL){
-               /* Invalid channel, discard packet */
-               printk(KERN_INFO "%s: receiving on orphaned LCN %d!\n",
-                       card->devname, lcn);
-               return;
-       }
-
-       chan = dev->priv;
-       chan->i_timeout_sofar = jiffies;
-
-
-       /* Copy the data from the board, into an
-         * skb buffer 
-        */
-       if (wanpipe_pull_data_in_skb(card,dev,&skb)){
-               ++chan->ifstats.rx_dropped;
-               ++card->wandev.stats.rx_dropped;
-               ++chan->rx_intr_stat.rx_intr_no_socket;
-               ++chan->rx_intr_stat.rx_intr_bfr_not_passed_to_stack;
-               return;
-       }
-
-       dev->last_rx = jiffies;         /* timestamp */
-
-
-       /* ------------ API ----------------*/
-
-       if (chan->common.usedby == API){
-
-               if (bh_enqueue(dev, skb)){
-                       ++chan->ifstats.rx_dropped;
-                       ++card->wandev.stats.rx_dropped;
-                       ++chan->rx_intr_stat.rx_intr_bfr_not_passed_to_stack;
-                       dev_kfree_skb_any(skb);
-                       return;
-               }               
-
-               ++chan->ifstats.rx_packets;
-               chan->ifstats.rx_bytes += skb->len;
-               
-
-               chan->rx_skb = NULL;
-               if (!test_and_set_bit(0, &chan->tq_working)){
-                       wanpipe_queue_work(&chan->common.wanpipe_work);
-               }
-               return;
-       }
-
-
-       /* ------------- WANPIPE -------------------*/
-       
-       /* set rx_skb to NULL so we won't access it later when kernel already owns it */
-       chan->rx_skb=NULL;
-       
-       /* Decapsulate packet, if necessary */
-       if (!skb->protocol && !wanrouter_type_trans(skb, dev)){
-               /* can't decapsulate packet */
-                dev_kfree_skb_any(skb);
-               ++chan->ifstats.rx_errors;
-               ++chan->ifstats.rx_dropped;
-               ++card->wandev.stats.rx_dropped;
-               ++chan->rx_intr_stat.rx_intr_bfr_not_passed_to_stack;
-
-       }else{
-               if( handle_IPXWAN(skb->data, chan->name, 
-                                 chan->enable_IPX, chan->network_number, 
-                                 skb->protocol)){
-
-                       if( chan->enable_IPX ){
-                               if(chan_send(dev, skb->data, skb->len,0)){
-                                       chan->tx_skb = skb;
-                               }else{
-                                        dev_kfree_skb_any(skb);
-                                       ++chan->rx_intr_stat.rx_intr_bfr_not_passed_to_stack;
-                               }
-                       }else{
-                               /* increment IPX packet dropped statistic */
-                               ++chan->ifstats.rx_dropped;
-                               ++chan->rx_intr_stat.rx_intr_bfr_not_passed_to_stack;
-                       }
-               }else{
-                       skb->mac.raw = skb->data;
-                       chan->ifstats.rx_bytes += skb->len;
-                       ++chan->ifstats.rx_packets;
-                       ++chan->rx_intr_stat.rx_intr_bfr_passed_to_stack;
-                       netif_rx(skb);
-               }
-       }
-       
-       return;
-}
-
-
-static int wanpipe_pull_data_in_skb(sdla_t *card, struct net_device *dev,
-                                   struct sk_buff **skb)
-{
-       void *bufptr;
-       TX25Mbox* rxmb = card->rxmb;
-       unsigned len = rxmb->cmd.length;        /* packet length */
-       unsigned qdm = rxmb->cmd.qdm;           /* Q,D and M bits */
-       x25_channel_t *chan = dev->priv;
-       struct sk_buff *new_skb = *skb;
-
-       if (chan->common.usedby == WANPIPE){
-               if (chan->drop_sequence){
-                       if (!(qdm & 0x01)){ 
-                               chan->drop_sequence = 0;
-                       }
-                       return 1;
-               }
-               new_skb = chan->rx_skb;
-       }else{
-               /* Add on the API header to the received
-                 * data 
-                */
-               len += sizeof(x25api_hdr_t);
-       }
-
-       if (new_skb == NULL){
-               int bufsize;
-
-               if (chan->common.usedby == WANPIPE){
-                       bufsize = (qdm & 0x01) ? dev->mtu : len;
-               }else{
-                       bufsize = len;
-               }
-
-               /* Allocate new socket buffer */
-               new_skb = dev_alloc_skb(bufsize + dev->hard_header_len);
-               if (new_skb == NULL){
-                       printk(KERN_INFO "%s: no socket buffers available!\n",
-                               card->devname);
-                       chan->drop_sequence = 1;        /* set flag */
-                       ++chan->ifstats.rx_dropped;
-                       return 1;
-               }
-       }
-
-       if (skb_tailroom(new_skb) < len){
-               /* No room for the packet. Call off the whole thing! */
-                dev_kfree_skb_any(new_skb);
-               if (chan->common.usedby == WANPIPE){
-                       chan->rx_skb = NULL;
-                       if (qdm & 0x01){ 
-                               chan->drop_sequence = 1;
-                       }
-               }
-
-               printk(KERN_INFO "%s: unexpectedly long packet sequence "
-                       "on interface %s!\n", card->devname, dev->name);
-               ++chan->ifstats.rx_length_errors;
-               return 1;
-       }
-
-       bufptr = skb_put(new_skb,len);
-
-
-       if (chan->common.usedby == API){
-               /* Fill in the x25api header 
-                */
-               x25api_t * api_data = (x25api_t*)bufptr;
-               api_data->hdr.qdm = rxmb->cmd.qdm;
-               api_data->hdr.cause = rxmb->cmd.cause;
-               api_data->hdr.diagn = rxmb->cmd.diagn;
-               api_data->hdr.length = rxmb->cmd.length;
-               memcpy(api_data->data, rxmb->data, rxmb->cmd.length);
-       }else{
-               memcpy(bufptr, rxmb->data, len);
-       }
-
-       new_skb->dev = dev;
-
-       if (chan->common.usedby == API){
-               new_skb->mac.raw = new_skb->data;
-               new_skb->protocol = htons(X25_PROT);
-               new_skb->pkt_type = WAN_PACKET_DATA;
-       }else{
-               new_skb->protocol = chan->protocol;
-               chan->rx_skb = new_skb;
-       }
-
-       /* If qdm bit is set, more data is coming 
-         * thus, exit and wait for more data before
-         * sending the packet up. (Used by router only) 
-        */
-       if ((qdm & 0x01) && (chan->common.usedby == WANPIPE)) 
-               return 1;       
-
-       *skb = new_skb; 
-
-       return 0;
-}
-
-/*===============================================================
- * tx_intr
- *  
- *     Transmit interrupt handler.
- *     For each dev, check that there is something to send.
- *     If data available, transmit.    
- *
- *===============================================================*/
-
-static void tx_intr (sdla_t* card)
-{
-       struct net_device *dev;
-       TX25Status* status = card->flags;
-       unsigned char more_to_tx=0;
-       x25_channel_t *chan=NULL;
-       int i=0;        
-
-       if (card->u.x.tx_dev == NULL){
-               card->u.x.tx_dev = card->wandev.dev;
-       }
-
-       dev = card->u.x.tx_dev;
-
-       for (;;){
-
-               chan = dev->priv;
-               if (chan->transmit_length){
-                       /* Device was set to transmit, check if the TX
-                         * buffers are available 
-                        */             
-                       if (chan->common.state != WAN_CONNECTED){
-                               chan->transmit_length = 0;
-                               atomic_set(&chan->common.driver_busy,0);
-                               chan->tx_offset=0;
-                               if (netif_queue_stopped(dev)){
-                                       if (chan->common.usedby == API){
-                                               netif_start_queue(dev);
-                                               wakeup_sk_bh(dev);
-                                       }else{
-                                               netif_wake_queue(dev);
-                                       }
-                               }
-                               dev = move_dev_to_next(card,dev);
-                               break;
-                       }                               
-
-                       if ((status->cflags[chan->ch_idx] & 0x40 || card->u.x.LAPB_hdlc) && 
-                            (*card->u.x.hdlc_buf_status & 0x40) ){
-                               /* Tx buffer available, we can send */
-                               
-                               if (tx_intr_send(card, dev)){
-                                       more_to_tx=1;
-                               }
-
-                               /* If more than one interface present, move the
-                                 * device pointer to the next interface, so on the 
-                                 * next TX interrupt we will try sending from it. 
-                                 */
-                               dev = move_dev_to_next(card,dev);
-                               break;
-                       }else{
-                               /* Tx buffers not available, but device set
-                                 * the TX interrupt.  Set more_to_tx and try  
-                                 * to transmit for other devices.
-                                */
-                               more_to_tx=1;
-                               dev = move_dev_to_next(card,dev);
-                       }
-
-               }else{
-                       /* This device was not set to transmit,
-                         * go to next 
-                        */
-                       dev = move_dev_to_next(card,dev);
-               }       
-
-               if (++i == card->u.x.no_dev){
-                       if (!more_to_tx){
-                               DBG_PRINTK(KERN_INFO "%s: Nothing to Send in TX INTR\n",
-                                       card->devname);
-                       }
-                       break;
-               }
-
-       } //End of FOR
-
-       card->u.x.tx_dev = dev;
-       
-       if (!more_to_tx){
-               /* if any other interfaces have transmit interrupts pending, */
-               /* do not disable the global transmit interrupt */
-               if (!(--card->u.x.tx_interrupts_pending)){
-                       status->imask &= ~INTR_ON_TX_FRAME;
-               }
-       }
-       return;
-}
-
-/*===============================================================
- * move_dev_to_next
- *  
- *
- *===============================================================*/
-
-
-struct net_device *move_dev_to_next(sdla_t *card, struct net_device *dev)
-{
-       if (card->u.x.no_dev != 1){
-               if (!*((struct net_device **)dev->priv))
-                       return card->wandev.dev;
-               else
-                       return *((struct net_device **)dev->priv);
-       }
-       return dev;
-}
-
-/*===============================================================
- *  tx_intr_send
- *  
- *
- *===============================================================*/
-
-static int tx_intr_send(sdla_t *card, struct net_device *dev)
-{
-       x25_channel_t* chan = dev->priv; 
-
-       if (chan_send (dev,chan->transmit_buffer,chan->transmit_length,1)){
-                
-                /* Packet was split up due to its size, do not disable
-                 * tx_intr 
-                 */
-               return 1;
-       }
-
-       chan->transmit_length=0;
-       atomic_set(&chan->common.driver_busy,0);
-       chan->tx_offset=0;
-
-       /* If we are in API mode, wakeup the 
-         * sock BH handler, not the NET_BH */
-       if (netif_queue_stopped(dev)){
-               if (chan->common.usedby == API){
-                       netif_start_queue(dev);
-                       wakeup_sk_bh(dev);
-               }else{
-                       netif_wake_queue(dev);
-               }
-       }
-       return 0;
-}
-
-
-/*===============================================================
- * timer_intr
- *  
- *     Timer interrupt handler.
- *     Check who called the timer interrupt and perform
- *      action accordingly.
- *
- *===============================================================*/
-
-static void timer_intr (sdla_t *card)
-{
-       TX25Status* status = card->flags;
-
-       if (card->u.x.timer_int_enabled & TMR_INT_ENABLED_CMD_EXEC){
-
-               if (timer_intr_cmd_exec(card) == 0){
-                       card->u.x.timer_int_enabled &=
-                               ~TMR_INT_ENABLED_CMD_EXEC;
-               }
-
-       }else  if(card->u.x.timer_int_enabled & TMR_INT_ENABLED_UDP_PKT) {
-
-               if ((*card->u.x.hdlc_buf_status & 0x40) && 
-                   card->u.x.udp_type == UDP_XPIPE_TYPE){
-
-                       if(process_udp_mgmt_pkt(card)) {
-                               card->u.x.timer_int_enabled &= 
-                                       ~TMR_INT_ENABLED_UDP_PKT;
-                       }
-               }
-
-       }else if (card->u.x.timer_int_enabled & TMR_INT_ENABLED_POLL_ACTIVE) {
-
-               struct net_device *dev = card->u.x.poll_device;
-               x25_channel_t *chan = NULL;
-
-               if (!dev){
-                       card->u.x.timer_int_enabled &= ~TMR_INT_ENABLED_POLL_ACTIVE;
-                       return;
-               }
-               chan = dev->priv;
-
-               printk(KERN_INFO 
-                       "%s: Closing down Idle link %s on LCN %d\n",
-                                       card->devname,chan->name,chan->common.lcn); 
-               chan->i_timeout_sofar = jiffies;
-               chan_disc(dev); 
-               card->u.x.timer_int_enabled &= ~TMR_INT_ENABLED_POLL_ACTIVE;
-               card->u.x.poll_device=NULL;
-
-       }else if (card->u.x.timer_int_enabled & TMR_INT_ENABLED_POLL_CONNECT_ON) {
-
-               wanpipe_set_state(card, WAN_CONNECTED);
-               if (card->u.x.LAPB_hdlc){
-                       struct net_device *dev = card->wandev.dev;
-                       set_chan_state(dev,WAN_CONNECTED);
-                       send_delayed_cmd_result(card,dev,card->mbox);   
-               }
-
-               /* 0x8F enable all interrupts */
-               x25_set_intr_mode(card, INTR_ON_RX_FRAME|       
-                                       INTR_ON_TX_FRAME|
-                                       INTR_ON_MODEM_STATUS_CHANGE|
-                                       //INTR_ON_COMMAND_COMPLETE|
-                                       X25_ASY_TRANS_INTR_PENDING |
-                                       INTR_ON_TIMER |
-                                       DIRECT_RX_INTR_USAGE
-                               ); 
-
-               status->imask &= ~INTR_ON_TX_FRAME;     /* mask Tx interrupts */
-               card->u.x.timer_int_enabled &= ~TMR_INT_ENABLED_POLL_CONNECT_ON;
-
-       }else if (card->u.x.timer_int_enabled & TMR_INT_ENABLED_POLL_CONNECT_OFF) {
-
-               //printk(KERN_INFO "Poll connect, Turning OFF\n");
-               disconnect(card);
-               card->u.x.timer_int_enabled &= ~TMR_INT_ENABLED_POLL_CONNECT_OFF;
-
-       }else if (card->u.x.timer_int_enabled & TMR_INT_ENABLED_POLL_DISCONNECT) {
-
-               //printk(KERN_INFO "POll disconnect, trying to connect\n");
-               connect(card);
-               card->u.x.timer_int_enabled &= ~TMR_INT_ENABLED_POLL_DISCONNECT;
-
-       }else if (card->u.x.timer_int_enabled & TMR_INT_ENABLED_UPDATE){
-
-               if (*card->u.x.hdlc_buf_status & 0x40){
-                       x25_get_err_stats(card);
-                       x25_get_stats(card);
-                       card->u.x.timer_int_enabled &= ~TMR_INT_ENABLED_UPDATE;
-               }
-       }
-
-       if(!card->u.x.timer_int_enabled){
-               //printk(KERN_INFO "Turning Timer Off \n");
-                status->imask &= ~INTR_ON_TIMER;       
-       }
-}
-
-/*====================================================================
- *     Modem status interrupt handler.
- *===================================================================*/
-static void status_intr (sdla_t* card)
-{
-
-       /* Added to avoid Modem status message flooding */
-       static TX25ModemStatus last_stat;
-
-       TX25Mbox* mbox = card->mbox;
-       TX25ModemStatus *modem_status;
-       struct net_device *dev;
-       x25_channel_t *chan;
-       int err;
-
-       memset(&mbox->cmd, 0, sizeof(TX25Cmd));
-       mbox->cmd.command = X25_READ_MODEM_STATUS;
-       err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-       if (err){ 
-               x25_error(card, err, X25_READ_MODEM_STATUS, 0);
-       }else{
-       
-               modem_status = (TX25ModemStatus*)mbox->data;    
-       
-               /* Check if the last status was the same
-                * if it was, do NOT print message again */
-       
-               if (last_stat.status != modem_status->status){
-
-                       printk(KERN_INFO "%s: Modem Status Change: DCD=%s, CTS=%s\n",
-                               card->devname,DCD(modem_status->status),CTS(modem_status->status));
-
-                       last_stat.status = modem_status->status;
-               
-                       if (card->u.x.oob_on_modem){
-
-                               mbox->cmd.pktType = mbox->cmd.command;
-                               mbox->cmd.result = 0x08;
-
-                               /* Send a OOB to all connected sockets */
-                               for (dev = card->wandev.dev; dev;
-                                    dev = *((struct net_device**)dev->priv)) {
-                                       chan=dev->priv;
-                                       if (chan->common.usedby == API){
-                                               send_oob_msg(card,dev,mbox);                            
-                                       }
-                               }
-
-                               /* The modem OOB message will probably kill the
-                                * the link. If we don't clear the flag here,
-                                * a deadlock could occur */ 
-                               if (atomic_read(&card->u.x.command_busy)){
-                                       atomic_set(&card->u.x.command_busy,0);
-                               }
-                       }
-               }
-       }
-
-       memset(&mbox->cmd, 0, sizeof(TX25Cmd));
-       mbox->cmd.command = X25_HDLC_LINK_STATUS;
-       err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-       if (err){ 
-               x25_error(card, err, X25_HDLC_LINK_STATUS, 0);
-       }
-
-}
-
-/*====================================================================
- *     Network event interrupt handler.
- *===================================================================*/
-static void event_intr (sdla_t* card)
-{
-       x25_fetch_events(card);
-}
-
-/*====================================================================
- *     Spurious interrupt handler.
- *     o print a warning
- *     o        
- *====================================================================*/
-
-static void spur_intr (sdla_t* card)
-{
-       printk(KERN_INFO "%s: spurious interrupt!\n", card->devname);
-}
-
-
-/*
- *     Background Polling Routines  
- */
-
-/*====================================================================
- *     Main polling routine.
- *     This routine is repeatedly called by the WANPIPE 'thread' to allow for
- *     time-dependent housekeeping work.
- *
- *     Notes:
- *     1. This routine may be called on interrupt context with all interrupts
- *     enabled. Beware!
- *====================================================================*/
-
-static void wpx_poll (sdla_t *card)
-{
-       if (!card->wandev.dev){
-               goto wpx_poll_exit;
-       }
-
-       if (card->open_cnt != card->u.x.num_of_ch){
-               goto wpx_poll_exit;
-       }
-       
-       if (test_bit(PERI_CRIT,&card->wandev.critical)){
-               goto wpx_poll_exit;
-       }
-
-       if (test_bit(SEND_CRIT,&card->wandev.critical)){
-               goto wpx_poll_exit;
-       }
-
-       switch(card->wandev.state){
-               case WAN_CONNECTED:
-                       poll_active(card);
-                       break;
-
-               case WAN_CONNECTING:
-                       poll_connecting(card);
-                       break;
-
-               case WAN_DISCONNECTED:
-                       poll_disconnected(card);
-                       break;
-       }
-
-wpx_poll_exit:
-       clear_bit(POLL_CRIT,&card->wandev.critical);
-       return;
-}
-
-static void trigger_x25_poll(sdla_t *card)
-{
-       schedule_work(&card->u.x.x25_poll_work);
-}
-
-/*====================================================================
- *     Handle physical link establishment phase.
- *     o if connection timed out, disconnect the link.
- *===================================================================*/
-
-static void poll_connecting (sdla_t* card)
-{
-       volatile TX25Status* status = card->flags;
-
-       if (status->gflags & X25_HDLC_ABM){
-
-               timer_intr_exec (card, TMR_INT_ENABLED_POLL_CONNECT_ON);
-
-       }else if ((jiffies - card->state_tick) > CONNECT_TIMEOUT){
-
-               timer_intr_exec (card, TMR_INT_ENABLED_POLL_CONNECT_OFF);
-
-       }
-}
-
-/*====================================================================
- *     Handle physical link disconnected phase.
- *     o if hold-down timeout has expired and there are open interfaces, 
- *     connect link.
- *===================================================================*/
-
-static void poll_disconnected (sdla_t* card)
-{
-       struct net_device *dev; 
-       x25_channel_t *chan;
-       TX25Status* status = card->flags;
-
-       if (!card->u.x.LAPB_hdlc && card->open_cnt && 
-           ((jiffies - card->state_tick) > HOLD_DOWN_TIME)){
-               timer_intr_exec(card, TMR_INT_ENABLED_POLL_DISCONNECT);
-       }
-
-
-       if ((dev=card->wandev.dev) == NULL)
-               return;
-
-       if ((chan=dev->priv) == NULL)
-               return;
-
-       if (chan->common.usedby == API && 
-           atomic_read(&chan->common.command) && 
-           card->u.x.LAPB_hdlc){
-
-               if (!(card->u.x.timer_int_enabled & TMR_INT_ENABLED_CMD_EXEC)) 
-                       card->u.x.timer_int_enabled |= TMR_INT_ENABLED_CMD_EXEC;
-
-               if (!(status->imask & INTR_ON_TIMER))
-                       status->imask |= INTR_ON_TIMER;
-       }       
-
-}
-
-/*====================================================================
- *     Handle active link phase.
- *     o fetch X.25 asynchronous events.
- *     o kick off transmission on all interfaces.
- *===================================================================*/
-
-static void poll_active (sdla_t* card)
-{
-       struct net_device* dev;
-       TX25Status* status = card->flags;
-
-       for (dev = card->wandev.dev; dev;
-            dev = *((struct net_device **)dev->priv)){
-               x25_channel_t* chan = dev->priv;
-
-               /* If SVC has been idle long enough, close virtual circuit */
-               if ( chan->common.svc && 
-                    chan->common.state == WAN_CONNECTED &&
-                    chan->common.usedby == WANPIPE ){
-               
-                       if( (jiffies - chan->i_timeout_sofar) / HZ > chan->idle_timeout ){
-                               /* Close svc */
-                               card->u.x.poll_device=dev;
-                               timer_intr_exec (card, TMR_INT_ENABLED_POLL_ACTIVE);
-                       }
-               }
-
-#ifdef PRINT_DEBUG
-               chan->ifstats.tx_compressed = atomic_read(&chan->common.command);
-               chan->ifstats.tx_errors = chan->common.state;
-               chan->ifstats.rx_fifo_errors = atomic_read(&card->u.x.command_busy);
-               ++chan->ifstats.tx_bytes;
-
-               chan->ifstats.rx_fifo_errors=atomic_read(&chan->common.disconnect);
-               chan->ifstats.multicast=atomic_read(&chan->bh_buff_used);
-               chan->ifstats.rx_length_errors=*card->u.x.hdlc_buf_status;
-#endif 
-
-               if (chan->common.usedby == API && 
-                   atomic_read(&chan->common.command) && 
-                   !card->u.x.LAPB_hdlc){
-
-                       if (!(card->u.x.timer_int_enabled & TMR_INT_ENABLED_CMD_EXEC)) 
-                               card->u.x.timer_int_enabled |= TMR_INT_ENABLED_CMD_EXEC;
-
-                       if (!(status->imask & INTR_ON_TIMER))
-                               status->imask |= INTR_ON_TIMER;
-               }       
-
-               if ((chan->common.usedby == API) && 
-                    atomic_read(&chan->common.disconnect)){
-
-                       if (chan->common.state == WAN_DISCONNECTED){
-                               atomic_set(&chan->common.disconnect,0);
-                               return;
-                       }
-
-                       atomic_set(&chan->common.command,X25_CLEAR_CALL);
-                       if (!(card->u.x.timer_int_enabled & TMR_INT_ENABLED_CMD_EXEC)) 
-                               card->u.x.timer_int_enabled |= TMR_INT_ENABLED_CMD_EXEC;
-
-                       if (!(status->imask & INTR_ON_TIMER))
-                               status->imask |= INTR_ON_TIMER;
-               }
-       }
-}
-
-static void timer_intr_exec(sdla_t *card, unsigned char TYPE)
-{
-       TX25Status* status = card->flags;
-       card->u.x.timer_int_enabled |= TYPE;
-       if (!(status->imask & INTR_ON_TIMER))
-               status->imask |= INTR_ON_TIMER;
-}
-
-
-/*==================================================================== 
- * SDLA Firmware-Specific Functions 
- *
- *  Almost all X.25 commands can unexpetedly fail due to so called 'X.25
- *  asynchronous events' such as restart, interrupt, incoming call request,
- *  call clear request, etc.  They can't be ignored and have to be delt with
- *  immediately.  To tackle with this problem we execute each interface 
- *  command in a loop until good return code is received or maximum number 
- *  of retries is reached.  Each interface command returns non-zero return 
- *  code, an asynchronous event/error handler x25_error() is called.
- *====================================================================*/
-
-/*====================================================================
- *     Read X.25 firmware version.
- *             Put code version as ASCII string in str. 
- *===================================================================*/
-
-static int x25_get_version (sdla_t* card, char* str)
-{
-       TX25Mbox* mbox = card->mbox;
-       int retry = MAX_CMD_RETRY;
-       int err;
-
-       do
-       {
-               memset(&mbox->cmd, 0, sizeof(TX25Cmd));
-               mbox->cmd.command = X25_READ_CODE_VERSION;
-               err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-       } while (err && retry-- &&
-                x25_error(card, err, X25_READ_CODE_VERSION, 0));
-
-       if (!err && str)
-       {
-               int len = mbox->cmd.length;
-
-               memcpy(str, mbox->data, len);
-               str[len] = '\0';
-       }
-       return err;
-}
-
-/*====================================================================
- *     Configure adapter.
- *===================================================================*/
-
-static int x25_configure (sdla_t* card, TX25Config* conf)
-{
-       TX25Mbox* mbox = card->mbox;
-       int retry = MAX_CMD_RETRY;
-       int err;
-
-       do{
-               memset(&mbox->cmd, 0, sizeof(TX25Cmd));
-               memcpy(mbox->data, (void*)conf, sizeof(TX25Config));
-               mbox->cmd.length  = sizeof(TX25Config);
-               mbox->cmd.command = X25_SET_CONFIGURATION;
-               err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-       } while (err && retry-- && x25_error(card, err, X25_SET_CONFIGURATION, 0));
-       return err;
-}
-
-/*====================================================================
- *     Configure adapter for HDLC only.
- *===================================================================*/
-
-static int hdlc_configure (sdla_t* card, TX25Config* conf)
-{
-       TX25Mbox* mbox = card->mbox;
-       int retry = MAX_CMD_RETRY;
-       int err;
-
-       do{
-               memset(&mbox->cmd, 0, sizeof(TX25Cmd));
-               memcpy(mbox->data, (void*)conf, sizeof(TX25Config));
-               mbox->cmd.length  = sizeof(TX25Config);
-               mbox->cmd.command = X25_HDLC_SET_CONFIG;
-               err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-       } while (err && retry-- && x25_error(card, err, X25_SET_CONFIGURATION, 0));
-
-       return err;
-}
-
-static int set_hdlc_level (sdla_t* card)
-{
-
-       TX25Mbox* mbox = card->mbox;
-       int retry = MAX_CMD_RETRY;
-       int err;
-
-       do{
-               memset(&mbox->cmd, 0, sizeof(TX25Cmd));
-               mbox->cmd.command = SET_PROTOCOL_LEVEL;
-               mbox->cmd.length = 1;
-               mbox->data[0] = HDLC_LEVEL; //| DO_HDLC_LEVEL_ERROR_CHECKING;   
-               err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-       } while (err && retry-- && x25_error(card, err, SET_PROTOCOL_LEVEL, 0));
-
-       return err;
-}
-
-
-
-/*====================================================================
- * Get communications error statistics.
- *====================================================================*/
-
-static int x25_get_err_stats (sdla_t* card)
-{
-       TX25Mbox* mbox = card->mbox;
-       int retry = MAX_CMD_RETRY;
-       int err;
-
-       do
-       {
-               memset(&mbox->cmd, 0, sizeof(TX25Cmd));
-               mbox->cmd.command = X25_HDLC_READ_COMM_ERR;
-               err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-       } while (err && retry-- && x25_error(card, err, X25_HDLC_READ_COMM_ERR, 0));
-       
-       if (!err)
-       {
-               THdlcCommErr* stats = (void*)mbox->data;
-
-               card->wandev.stats.rx_over_errors    = stats->rxOverrun;
-               card->wandev.stats.rx_crc_errors     = stats->rxBadCrc;
-               card->wandev.stats.rx_missed_errors  = stats->rxAborted;
-               card->wandev.stats.tx_aborted_errors = stats->txAborted;
-       }
-       return err;
-}
-
-/*====================================================================
- *     Get protocol statistics.
- *===================================================================*/
-
-static int x25_get_stats (sdla_t* card)
-{
-       TX25Mbox* mbox = card->mbox;
-       int retry = MAX_CMD_RETRY;
-       int err;
-
-       do
-       {
-               memset(&mbox->cmd, 0, sizeof(TX25Cmd));
-               mbox->cmd.command = X25_READ_STATISTICS;
-               err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-       } while (err && retry-- && x25_error(card, err, X25_READ_STATISTICS, 0)) ;
-       
-       if (!err)
-       {
-               TX25Stats* stats = (void*)mbox->data;
-
-               card->wandev.stats.rx_packets = stats->rxData;
-               card->wandev.stats.tx_packets = stats->txData;
-       }
-       return err;
-}
-
-/*====================================================================
- *     Close HDLC link.
- *===================================================================*/
-
-static int x25_close_hdlc (sdla_t* card)
-{
-       TX25Mbox* mbox = card->mbox;
-       int retry = MAX_CMD_RETRY;
-       int err;
-
-       do
-       {
-               memset(&mbox->cmd, 0, sizeof(TX25Cmd));
-               mbox->cmd.command = X25_HDLC_LINK_CLOSE;
-               err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-       } while (err && retry-- && x25_error(card, err, X25_HDLC_LINK_CLOSE, 0));
-       
-       return err;
-}
-
-
-/*====================================================================
- *     Open HDLC link.
- *===================================================================*/
-
-static int x25_open_hdlc (sdla_t* card)
-{
-       TX25Mbox* mbox = card->mbox;
-       int retry = MAX_CMD_RETRY;
-       int err;
-
-       do
-       {
-               memset(&mbox->cmd, 0, sizeof(TX25Cmd));
-               mbox->cmd.command = X25_HDLC_LINK_OPEN;
-               err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-       } while (err && retry-- && x25_error(card, err, X25_HDLC_LINK_OPEN, 0));
-
-       return err;
-}
-
-/*=====================================================================
- * Setup HDLC link.
- *====================================================================*/
-static int x25_setup_hdlc (sdla_t* card)
-{
-       TX25Mbox* mbox = card->mbox;
-       int retry = MAX_CMD_RETRY;
-       int err;
-
-       do
-       {
-               memset(&mbox->cmd, 0, sizeof(TX25Cmd));
-               mbox->cmd.command = X25_HDLC_LINK_SETUP;
-               err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-       } while (err && retry-- && x25_error(card, err, X25_HDLC_LINK_SETUP, 0));
-       
-       return err;
-}
-
-/*====================================================================
- * Set (raise/drop) DTR.
- *===================================================================*/
-
-static int x25_set_dtr (sdla_t* card, int dtr)
-{
-       TX25Mbox* mbox = card->mbox;
-       int retry = MAX_CMD_RETRY;
-       int err;
-
-       do
-       {
-               memset(&mbox->cmd, 0, sizeof(TX25Cmd));
-               mbox->data[0] = 0;
-               mbox->data[2] = 0;
-               mbox->data[1] = dtr ? 0x02 : 0x01;
-               mbox->cmd.length  = 3;
-               mbox->cmd.command = X25_SET_GLOBAL_VARS;
-               err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-       } while (err && retry-- && x25_error(card, err, X25_SET_GLOBAL_VARS, 0));
-       
-       return err;
-}
-
-/*====================================================================
- *     Set interrupt mode.
- *===================================================================*/
-
-static int x25_set_intr_mode (sdla_t* card, int mode)
-{
-       TX25Mbox* mbox = card->mbox;
-       int retry = MAX_CMD_RETRY;
-       int err;
-
-       do
-       {
-               memset(&mbox->cmd, 0, sizeof(TX25Cmd));
-               mbox->data[0] = mode;
-               if (card->hw.fwid == SFID_X25_508){
-                       mbox->data[1] = card->hw.irq;
-                       mbox->data[2] = 2;
-                       mbox->cmd.length = 3;
-               }else {
-                       mbox->cmd.length  = 1;
-               }
-               mbox->cmd.command = X25_SET_INTERRUPT_MODE;
-               err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-       } while (err && retry-- && x25_error(card, err, X25_SET_INTERRUPT_MODE, 0));
-       
-       return err;
-}
-
-/*====================================================================
- *     Read X.25 channel configuration.
- *===================================================================*/
-
-static int x25_get_chan_conf (sdla_t* card, x25_channel_t* chan)
-{
-       TX25Mbox* mbox = card->mbox;
-       int retry = MAX_CMD_RETRY;
-       int lcn = chan->common.lcn;
-       int err;
-
-       do{
-               memset(&mbox->cmd, 0, sizeof(TX25Cmd));
-               mbox->cmd.lcn     = lcn;
-               mbox->cmd.command = X25_READ_CHANNEL_CONFIG;
-               err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-       } while (err && retry-- && x25_error(card, err, X25_READ_CHANNEL_CONFIG, lcn));
-
-       if (!err)
-       {
-               TX25Status* status = card->flags;
-
-               /* calculate an offset into the array of status bytes */
-               if (card->u.x.hi_svc <= X25_MAX_CHAN){ 
-
-                       chan->ch_idx = lcn - 1;
-
-               }else{
-                       int offset;
-
-                       /* FIX: Apr 14 2000 : Nenad Corbic
-                        * The data field was being compared to 0x1F using
-                         * '&&' instead of '&'. 
-                        * This caused X25API to fail for LCNs greater than 255.
-                        */
-                       switch (mbox->data[0] & 0x1F)
-                       {
-                               case 0x01: 
-                                       offset = status->pvc_map; break;
-                               case 0x03: 
-                                       offset = status->icc_map; break;
-                               case 0x07: 
-                                       offset = status->twc_map; break;
-                               case 0x0B: 
-                                       offset = status->ogc_map; break;
-                               default: 
-                                       offset = 0;
-                       }
-                       chan->ch_idx = lcn - 1 - offset;
-               }
-
-               /* get actual transmit packet size on this channel */
-               switch(mbox->data[1] & 0x38)
-               {
-                       case 0x00: 
-                               chan->tx_pkt_size = 16; 
-                               break;
-                       case 0x08: 
-                               chan->tx_pkt_size = 32; 
-                               break;
-                       case 0x10: 
-                               chan->tx_pkt_size = 64; 
-                               break;
-                       case 0x18: 
-                               chan->tx_pkt_size = 128; 
-                               break;
-                       case 0x20: 
-                               chan->tx_pkt_size = 256; 
-                               break;
-                       case 0x28: 
-                               chan->tx_pkt_size = 512; 
-                               break;
-                       case 0x30: 
-                               chan->tx_pkt_size = 1024; 
-                               break;
-               }
-               if (card->u.x.logging)
-                       printk(KERN_INFO "%s: X.25 packet size on LCN %d is %d.\n",
-                               card->devname, lcn, chan->tx_pkt_size);
-       }
-       return err;
-}
-
-/*====================================================================
- *     Place X.25 call.
- *====================================================================*/
-
-static int x25_place_call (sdla_t* card, x25_channel_t* chan)
-{
-       TX25Mbox* mbox = card->mbox;
-       int retry = MAX_CMD_RETRY;
-       int err;
-       char str[64];
-
-
-       if (chan->protocol == htons(ETH_P_IP)){
-               sprintf(str, "-d%s -uCC", chan->addr);
-       
-       }else if (chan->protocol == htons(ETH_P_IPX)){
-               sprintf(str, "-d%s -u800000008137", chan->addr);
-       
-       }
-       
-       do
-       {
-               memset(&mbox->cmd, 0, sizeof(TX25Cmd));
-               strcpy(mbox->data, str);
-               mbox->cmd.length  = strlen(str);
-               mbox->cmd.command = X25_PLACE_CALL;
-               err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-       } while (err && retry-- && x25_error(card, err, X25_PLACE_CALL, 0));
-
-       if (!err){
-               bind_lcn_to_dev (card, chan->dev, mbox->cmd.lcn);
-       }
-       return err;
-}
-
-/*====================================================================
- *     Accept X.25 call.
- *====================================================================*/
-
-static int x25_accept_call (sdla_t* card, int lcn, int qdm)
-{
-       TX25Mbox* mbox = card->mbox;
-       int retry = MAX_CMD_RETRY;
-       int err;
-
-       do
-       {
-               memset(&mbox->cmd, 0, sizeof(TX25Cmd));
-               mbox->cmd.lcn     = lcn;
-               mbox->cmd.qdm     = qdm;
-               mbox->cmd.command = X25_ACCEPT_CALL;
-               err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-       } while (err && retry-- && x25_error(card, err, X25_ACCEPT_CALL, lcn));
-       
-       return err;
-}
-
-/*====================================================================
- *     Clear X.25 call.
- *====================================================================*/
-
-static int x25_clear_call (sdla_t* card, int lcn, int cause, int diagn)
-{
-       TX25Mbox* mbox = card->mbox;
-       int retry = MAX_CMD_RETRY;
-       int err;
-
-       do
-       {
-               memset(&mbox->cmd, 0, sizeof(TX25Cmd));
-               mbox->cmd.lcn     = lcn;
-               mbox->cmd.cause   = cause;
-               mbox->cmd.diagn   = diagn;
-               mbox->cmd.command = X25_CLEAR_CALL;
-               err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-       } while (err && retry-- && x25_error(card, err, X25_CLEAR_CALL, lcn));
-       
-       return err;
-}
-
-/*====================================================================
- *     Send X.25 data packet.
- *====================================================================*/
-
-static int x25_send (sdla_t* card, int lcn, int qdm, int len, void* buf)
-{
-       TX25Mbox* mbox = card->mbox;
-       int retry = MAX_CMD_RETRY;
-       int err;
-       unsigned char cmd;
-               
-       if (card->u.x.LAPB_hdlc)
-               cmd = X25_HDLC_WRITE;
-       else
-               cmd = X25_WRITE;
-
-       do
-       {
-               memset(&mbox->cmd, 0, sizeof(TX25Cmd));
-               memcpy(mbox->data, buf, len);
-               mbox->cmd.length  = len;
-               mbox->cmd.lcn     = lcn;
-
-               if (card->u.x.LAPB_hdlc){
-                       mbox->cmd.pf = qdm;
-               }else{                  
-                       mbox->cmd.qdm = qdm;
-               }
-
-               mbox->cmd.command = cmd;
-               err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-       } while (err && retry-- && x25_error(card, err, cmd , lcn));
-
-
-       /* If buffers are busy the return code for LAPB HDLC is
-         * 1. The above functions are looking for return code
-         * of X25RES_NOT_READY if busy. */
-
-       if (card->u.x.LAPB_hdlc && err == 1){
-               err = X25RES_NOT_READY;
-       }
-
-       return err;
-}
-
-/*====================================================================
- *     Fetch X.25 asynchronous events.
- *===================================================================*/
-
-static int x25_fetch_events (sdla_t* card)
-{
-       TX25Status* status = card->flags;
-       TX25Mbox* mbox = card->mbox;
-       int err = 0;
-
-       if (status->gflags & 0x20)
-       {
-               memset(&mbox->cmd, 0, sizeof(TX25Cmd));
-               mbox->cmd.command = X25_IS_DATA_AVAILABLE;
-               err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-               if (err) x25_error(card, err, X25_IS_DATA_AVAILABLE, 0);
-       }
-       return err;
-}
-
-/*====================================================================
- *     X.25 asynchronous event/error handler.
- *             This routine is called each time interface command returns 
- *             non-zero return code to handle X.25 asynchronous events and 
- *             common errors. Return non-zero to repeat command or zero to 
- *             cancel it.
- *
- *     Notes:
- *     1. This function may be called recursively, as handling some of the
- *     asynchronous events (e.g. call request) requires execution of the
- *     interface command(s) that, in turn, may also return asynchronous
- *     events.  To avoid re-entrancy problems we copy mailbox to dynamically
- *     allocated memory before processing events.
- *====================================================================*/
-
-static int x25_error (sdla_t* card, int err, int cmd, int lcn)
-{
-       int retry = 1;
-       unsigned dlen = ((TX25Mbox*)card->mbox)->cmd.length;
-       TX25Mbox* mb;
-
-       mb = kmalloc(sizeof(TX25Mbox) + dlen, GFP_ATOMIC);
-       if (mb == NULL)
-       {
-               printk(KERN_ERR "%s: x25_error() out of memory!\n",
-                       card->devname);
-               return 0;
-       }
-       memcpy(mb, card->mbox, sizeof(TX25Mbox) + dlen);
-       switch (err){
-
-       case X25RES_ASYNC_PACKET:       /* X.25 asynchronous packet was received */
-
-               mb->data[dlen] = '\0';
-
-               switch (mb->cmd.pktType & 0x7F){
-
-               case ASE_CALL_RQST:             /* incoming call */
-                       retry = incoming_call(card, cmd, lcn, mb);
-                       break;
-
-               case ASE_CALL_ACCEPTED:         /* connected */
-                       retry = call_accepted(card, cmd, lcn, mb);
-                       break;
-
-               case ASE_CLEAR_RQST:            /* call clear request */
-                       retry = call_cleared(card, cmd, lcn, mb);
-                       break;
-
-               case ASE_RESET_RQST:            /* reset request */
-                       printk(KERN_INFO "%s: X.25 reset request on LCN %d! "
-                               "Cause:0x%02X Diagn:0x%02X\n",
-                               card->devname, mb->cmd.lcn, mb->cmd.cause,
-                               mb->cmd.diagn);
-                       api_oob_event (card,mb);
-                       break;
-
-               case ASE_RESTART_RQST:          /* restart request */
-                       retry = restart_event(card, cmd, lcn, mb);
-                       break;
-
-               case ASE_CLEAR_CONFRM:
-                       if (clear_confirm_event (card,mb))
-                               break;
-
-                       /* I use the goto statement here so if 
-                        * somebody inserts code between the
-                        * case and default, we will not have
-                        * ghost problems */
-
-                       goto dflt_1;
-
-               default:
-dflt_1:
-                       printk(KERN_INFO "%s: X.25 event 0x%02X on LCN %d! "
-                               "Cause:0x%02X Diagn:0x%02X\n",
-                               card->devname, mb->cmd.pktType,
-                               mb->cmd.lcn, mb->cmd.cause, mb->cmd.diagn);
-               }
-               break;
-
-       case X25RES_PROTO_VIOLATION:    /* X.25 protocol violation indication */
-
-               /* Bug Fix: Mar 14 2000
-                 * The Protocol violation error conditions were  
-                 * not handled previously */
-
-               switch (mb->cmd.pktType & 0x7F){
-
-               case PVE_CLEAR_RQST:    /* Clear request */             
-                       retry = call_cleared(card, cmd, lcn, mb);
-                       break;  
-
-               case PVE_RESET_RQST:    /* Reset request */
-                       printk(KERN_INFO "%s: X.25 reset request on LCN %d! "
-                               "Cause:0x%02X Diagn:0x%02X\n",
-                               card->devname, mb->cmd.lcn, mb->cmd.cause,
-                               mb->cmd.diagn);
-                       api_oob_event (card,mb);
-                       break;
-
-               case PVE_RESTART_RQST:  /* Restart request */
-                       retry = restart_event(card, cmd, lcn, mb);
-                       break;
-
-               default :
-                       printk(KERN_INFO
-                               "%s: X.25 protocol violation on LCN %d! "
-                               "Packet:0x%02X Cause:0x%02X Diagn:0x%02X\n",
-                               card->devname, mb->cmd.lcn,
-                               mb->cmd.pktType & 0x7F, mb->cmd.cause, mb->cmd.diagn);
-                       api_oob_event(card,mb);
-               }
-               break;
-
-       case 0x42:      /* X.25 timeout */
-               retry = timeout_event(card, cmd, lcn, mb);
-               break;
-
-       case 0x43:      /* X.25 retry limit exceeded */
-               printk(KERN_INFO
-                       "%s: exceeded X.25 retry limit on LCN %d! "
-                       "Packet:0x%02X Diagn:0x%02X\n", card->devname,
-                       mb->cmd.lcn, mb->cmd.pktType, mb->cmd.diagn)
-               ;
-               break;
-
-       case 0x08:      /* modem failure */
-#ifndef MODEM_NOT_LOG
-               printk(KERN_INFO "%s: modem failure!\n", card->devname);
-#endif /* MODEM_NOT_LOG */
-               api_oob_event(card,mb);
-               break;
-
-       case 0x09:      /* N2 retry limit */
-               printk(KERN_INFO "%s: exceeded HDLC retry limit!\n",
-                       card->devname);
-               api_oob_event(card,mb);
-               break;
-
-       case 0x06:      /* unnumbered frame was received while in ABM */
-               printk(KERN_INFO "%s: received Unnumbered frame 0x%02X!\n",
-                       card->devname, mb->data[0]);
-               api_oob_event(card,mb);
-               break;
-
-       case CMD_TIMEOUT:
-               printk(KERN_ERR "%s: command 0x%02X timed out!\n",
-                       card->devname, cmd)
-               ;
-               retry = 0;      /* abort command */
-               break;
-
-       case X25RES_NOT_READY:
-               retry = 1;
-               break;
-
-       case 0x01:
-               if (card->u.x.LAPB_hdlc)
-                       break;
-
-               if (mb->cmd.command == 0x16)
-                       break;
-               /* I use the goto statement here so if 
-                 * somebody inserts code between the
-                 * case and default, we will not have
-                 * ghost problems */
-               goto dflt_2;
-
-       default:
-dflt_2:
-               printk(KERN_INFO "%s: command 0x%02X returned 0x%02X! Lcn %i\n",
-                       card->devname, cmd, err, mb->cmd.lcn)
-               ;
-               retry = 0;      /* abort command */
-       }
-       kfree(mb);
-       return retry;
-}
-
-/*==================================================================== 
- *     X.25 Asynchronous Event Handlers
- *     These functions are called by the x25_error() and should return 0, if
- *     the command resulting in the asynchronous event must be aborted.
- *====================================================================*/
-
-
-
-/*====================================================================
- *Handle X.25 incoming call request.
- *     RFC 1356 establishes the following rules:
- *     1. The first octet in the Call User Data (CUD) field of the call
- *                request packet contains NLPID identifying protocol encapsulation
- *     2. Calls MUST NOT be accepted unless router supports requested
- *        protocol encapsulation.
- *     3. A diagnostic code 249 defined by ISO/IEC 8208 may be used 
- *        when clearing a call because protocol encapsulation is not 
- *        supported.
- *     4. If an incoming call is received while a call request is 
- *        pending (i.e. call collision has occurred), the incoming call 
- *        shall be rejected and call request shall be retried.
- *====================================================================*/
-
-static int incoming_call (sdla_t* card, int cmd, int lcn, TX25Mbox* mb)
-{
-       struct wan_device* wandev = &card->wandev;
-       int new_lcn = mb->cmd.lcn;
-       struct net_device* dev = get_dev_by_lcn(wandev, new_lcn);
-       x25_channel_t* chan = NULL;
-       int accept = 0;         /* set to '1' if o.k. to accept call */
-       unsigned int user_data;
-       x25_call_info_t* info;
-       
-       /* Make sure there is no call collision */
-       if (dev != NULL)
-       {
-               printk(KERN_INFO
-                       "%s: X.25 incoming call collision on LCN %d!\n",
-                       card->devname, new_lcn);
-
-               x25_clear_call(card, new_lcn, 0, 0);
-               return 1;
-       }
-
-       /* Make sure D bit is not set in call request */
-//FIXME: THIS IS NOT TURE !!!! TAKE IT OUT
-//     if (mb->cmd.qdm & 0x02)
-//     {
-//             printk(KERN_INFO
-//                     "%s: X.25 incoming call on LCN %d with D-bit set!\n",
-//                     card->devname, new_lcn);
-//
-//             x25_clear_call(card, new_lcn, 0, 0);
-//             return 1;
-//     }
-
-       /* Parse call request data */
-       info = kmalloc(sizeof(x25_call_info_t), GFP_ATOMIC);
-       if (info == NULL)
-       {
-               printk(KERN_ERR
-                       "%s: not enough memory to parse X.25 incoming call "
-                       "on LCN %d!\n", card->devname, new_lcn);
-               x25_clear_call(card, new_lcn, 0, 0);
-               return 1;
-       }
-       parse_call_info(mb->data, info);
-
-       if (card->u.x.logging)
-               printk(KERN_INFO "\n%s: X.25 incoming call on LCN %d!\n",
-                       card->devname, new_lcn);
-
-       /* Conver the first two ASCII characters into an
-         * interger. Used to check the incoming protocol 
-         */
-       user_data = hex_to_uint(info->user,2);
-
-       /* Find available channel */
-       for (dev = wandev->dev; dev; dev = *((struct net_device **)dev->priv)) {
-               chan = dev->priv;
-
-               if (chan->common.usedby == API)
-                       continue;
-
-               if (!chan->common.svc || (chan->common.state != WAN_DISCONNECTED))
-                       continue;
-
-               if (user_data == NLPID_IP && chan->protocol != htons(ETH_P_IP)){
-                       printk(KERN_INFO "IP packet but configured for IPX : %x, %x\n",
-                                      htons(chan->protocol), info->user[0]);
-                       continue;
-               }
-       
-               if (user_data == NLPID_SNAP && chan->protocol != htons(ETH_P_IPX)){
-                       printk(KERN_INFO "IPX packet but configured for IP: %x\n",
-                                      htons(chan->protocol));
-                       continue;
-               }
-               if (strcmp(info->src, chan->addr) == 0)
-                       break;
-
-               /* If just an '@' is specified, accept all incoming calls */
-               if (strcmp(chan->addr, "") == 0)
-                       break;
-       }
-
-       if (dev == NULL){
-
-               /* If the call is not for any WANPIPE interfaces
-                 * check to see if there is an API listening queue
-                 * waiting for data. If there is send the packet
-                 * up the stack.
-                 */
-               if (card->sk != NULL && card->func != NULL){
-                       if (api_incoming_call(card,mb,new_lcn)){
-                               x25_clear_call(card, new_lcn, 0, 0);
-                       }
-                       accept = 0;
-               }else{
-                       printk(KERN_INFO "%s: no channels available!\n",
-                               card->devname);
-                       
-                       x25_clear_call(card, new_lcn, 0, 0);
-               }
-
-       }else if (info->nuser == 0){
-
-               printk(KERN_INFO
-                       "%s: no user data in incoming call on LCN %d!\n",
-                       card->devname, new_lcn)
-               ;
-               x25_clear_call(card, new_lcn, 0, 0);
-
-       }else switch (info->user[0]){
-
-               case 0:         /* multiplexed */
-                       chan->protocol = htons(0);
-                       accept = 1;
-                       break;
-
-               case NLPID_IP:  /* IP datagrams */
-                       accept = 1;
-                       break;
-
-               case NLPID_SNAP: /* IPX datagrams */
-                       accept = 1;
-                       break;
-
-               default:
-                       printk(KERN_INFO
-                               "%s: unsupported NLPID 0x%02X in incoming call "
-                               "on LCN %d!\n", card->devname, info->user[0], new_lcn);
-                       x25_clear_call(card, new_lcn, 0, 249);
-       }
-       
-       if (accept && (x25_accept_call(card, new_lcn, 0) == CMD_OK)){
-
-               bind_lcn_to_dev (card, chan->dev, new_lcn);
-               
-               if (x25_get_chan_conf(card, chan) == CMD_OK)
-                       set_chan_state(dev, WAN_CONNECTED);
-               else 
-                       x25_clear_call(card, new_lcn, 0, 0);
-       }
-       kfree(info);
-       return 1;
-}
-
-/*====================================================================
- *     Handle accepted call.
- *====================================================================*/
-
-static int call_accepted (sdla_t* card, int cmd, int lcn, TX25Mbox* mb)
-{
-       unsigned new_lcn = mb->cmd.lcn;
-       struct net_device* dev = find_channel(card, new_lcn);
-       x25_channel_t* chan;
-
-       if (dev == NULL){
-               printk(KERN_INFO
-                       "%s: clearing orphaned connection on LCN %d!\n",
-                       card->devname, new_lcn);
-               x25_clear_call(card, new_lcn, 0, 0);
-               return 1;
-       }
-
-       if (card->u.x.logging)  
-               printk(KERN_INFO "%s: X.25 call accepted on Dev %s and LCN %d!\n",
-                       card->devname, dev->name, new_lcn);
-
-       /* Get channel configuration and notify router */
-       chan = dev->priv;
-       if (x25_get_chan_conf(card, chan) != CMD_OK)
-       {
-               x25_clear_call(card, new_lcn, 0, 0);
-               return 1;
-       }
-
-       set_chan_state(dev, WAN_CONNECTED);
-
-       if (chan->common.usedby == API){
-               send_delayed_cmd_result(card,dev,mb);
-               bind_lcn_to_dev (card, dev, new_lcn);
-       }
-
-       return 1;
-}
-
-/*====================================================================
- *     Handle cleared call.
- *====================================================================*/
-
-static int call_cleared (sdla_t* card, int cmd, int lcn, TX25Mbox* mb)
-{
-       unsigned new_lcn = mb->cmd.lcn;
-       struct net_device* dev = find_channel(card, new_lcn);
-       x25_channel_t *chan;
-       unsigned char old_state;
-
-       if (card->u.x.logging){
-               printk(KERN_INFO "%s: X.25 clear request on LCN %d! Cause:0x%02X "
-               "Diagn:0x%02X\n",
-               card->devname, new_lcn, mb->cmd.cause, mb->cmd.diagn);
-       }
-
-       if (dev == NULL){ 
-               printk(KERN_INFO "%s: X.25 clear request : No device for clear\n",
-                               card->devname);
-               return 1;
-       }
-
-       chan=dev->priv;
-
-       old_state = chan->common.state;
-
-       set_chan_state(dev, WAN_DISCONNECTED);
-
-       if (chan->common.usedby == API){
-
-               switch (old_state){
-               
-               case WAN_CONNECTING:
-                       send_delayed_cmd_result(card,dev,mb);
-                       break;
-               case WAN_CONNECTED:
-                       send_oob_msg(card,dev,mb);                              
-                       break;
-               }
-       }
-       
-       return ((cmd == X25_WRITE) && (lcn == new_lcn)) ? 0 : 1;
-}
-
-/*====================================================================
- *     Handle X.25 restart event.
- *====================================================================*/
-
-static int restart_event (sdla_t* card, int cmd, int lcn, TX25Mbox* mb)
-{
-       struct wan_device* wandev = &card->wandev;
-       struct net_device* dev;
-       x25_channel_t *chan;
-       unsigned char old_state;
-
-       printk(KERN_INFO
-               "%s: X.25 restart request! Cause:0x%02X Diagn:0x%02X\n",
-               card->devname, mb->cmd.cause, mb->cmd.diagn);
-
-       /* down all logical channels */
-       for (dev = wandev->dev; dev; dev = *((struct net_device **)dev->priv)) {
-               chan=dev->priv;
-               old_state = chan->common.state;
-
-               set_chan_state(dev, WAN_DISCONNECTED);
-
-               if (chan->common.usedby == API){
-                       switch (old_state){
-               
-                       case WAN_CONNECTING:
-                               send_delayed_cmd_result(card,dev,mb);
-                               break;
-                       case WAN_CONNECTED:
-                               send_oob_msg(card,dev,mb);                              
-                               break;
-                       }
-               }
-       }
-       return (cmd == X25_WRITE) ? 0 : 1;
-}
-
-/*====================================================================
- * Handle timeout event.
- *====================================================================*/
-
-static int timeout_event (sdla_t* card, int cmd, int lcn, TX25Mbox* mb)
-{
-       unsigned new_lcn = mb->cmd.lcn;
-
-       if (mb->cmd.pktType == 0x05)    /* call request time out */
-       {
-               struct net_device* dev = find_channel(card,new_lcn);
-
-               printk(KERN_INFO "%s: X.25 call timed timeout on LCN %d!\n",
-                       card->devname, new_lcn);
-
-               if (dev){
-                       x25_channel_t *chan = dev->priv;
-                       set_chan_state(dev, WAN_DISCONNECTED);
-
-                       if (chan->common.usedby == API){
-                               send_delayed_cmd_result(card,dev,card->mbox);
-                       }
-               }
-       }else{ 
-               printk(KERN_INFO "%s: X.25 packet 0x%02X timeout on LCN %d!\n",
-               card->devname, mb->cmd.pktType, new_lcn);
-       }
-       return 1;
-}
-
-/* 
- *     Miscellaneous 
- */
-
-/*====================================================================
- *     Establish physical connection.
- *     o open HDLC and raise DTR
- *
- *     Return:         0       connection established
- *                     1       connection is in progress
- *                     <0      error
- *===================================================================*/
-
-static int connect (sdla_t* card)
-{
-       TX25Status* status = card->flags;
-
-       if (x25_open_hdlc(card) || x25_setup_hdlc(card))
-               return -EIO;
-
-       wanpipe_set_state(card, WAN_CONNECTING);
-
-       x25_set_intr_mode(card, INTR_ON_TIMER); 
-       status->imask &= ~INTR_ON_TIMER;
-
-       return 1;
-}
-
-/*
- *     Tear down physical connection.
- *     o close HDLC link
- *     o drop DTR
- *
- *     Return:         0
- *                     <0      error
- */
-
-static int disconnect (sdla_t* card)
-{
-       wanpipe_set_state(card, WAN_DISCONNECTED);
-       x25_set_intr_mode(card, INTR_ON_TIMER); /* disable all interrupt except timer */
-       x25_close_hdlc(card);                   /* close HDLC link */
-       x25_set_dtr(card, 0);                   /* drop DTR */
-       return 0;
-}
-
-/*
- * Find network device by its channel number.
- */
-
-static struct net_device* get_dev_by_lcn(struct wan_device* wandev,
-                                        unsigned lcn)
-{
-       struct net_device* dev;
-
-       for (dev = wandev->dev; dev; dev = *((struct net_device **)dev->priv))
-               if (((x25_channel_t*)dev->priv)->common.lcn == lcn) 
-                       break;
-       return dev;
-}
-
-/*
- *     Initiate connection on the logical channel.
- *     o for PVC we just get channel configuration
- *     o for SVCs place an X.25 call
- *
- *     Return:         0       connected
- *                     >0      connection in progress
- *                     <0      failure
- */
-
-static int chan_connect(struct net_device* dev)
-{
-       x25_channel_t* chan = dev->priv;
-       sdla_t* card = chan->card;
-
-       if (chan->common.svc && chan->common.usedby == WANPIPE){
-               if (!chan->addr[0]){
-                       printk(KERN_INFO "%s: No Destination Address\n",
-                                       card->devname);
-                       return -EINVAL; /* no destination address */
-               }
-               printk(KERN_INFO "%s: placing X.25 call to %s ...\n",
-                       card->devname, chan->addr);
-
-               if (x25_place_call(card, chan) != CMD_OK)
-                       return -EIO;
-
-               set_chan_state(dev, WAN_CONNECTING);
-               return 1;
-       }else{
-               if (x25_get_chan_conf(card, chan) != CMD_OK)
-                       return -EIO;
-
-               set_chan_state(dev, WAN_CONNECTED);
-       }
-       return 0;
-}
-
-/*
- *     Disconnect logical channel.
- *     o if SVC then clear X.25 call
- */
-
-static int chan_disc(struct net_device* dev)
-{
-       x25_channel_t* chan = dev->priv;
-
-       if (chan->common.svc){ 
-               x25_clear_call(chan->card, chan->common.lcn, 0, 0);
-
-               /* For API we disconnect on clear
-                 * confirmation. 
-                 */
-               if (chan->common.usedby == API)
-                       return 0;
-       }
-
-       set_chan_state(dev, WAN_DISCONNECTED);
-       
-       return 0;
-}
-
-/*
- *     Set logical channel state.
- */
-
-static void set_chan_state(struct net_device* dev, int state)
-{
-       x25_channel_t* chan = dev->priv;
-       sdla_t* card = chan->card;
-       unsigned long flags;
-
-       save_flags(flags);
-       cli();
-       if (chan->common.state != state)
-       {
-               switch (state)
-               {
-                       case WAN_CONNECTED:
-                               if (card->u.x.logging){
-                                       printk (KERN_INFO 
-                                               "%s: interface %s connected, lcn %i !\n", 
-                                               card->devname, dev->name,chan->common.lcn);
-                               }
-                               *(unsigned short*)dev->dev_addr = htons(chan->common.lcn);
-                               chan->i_timeout_sofar = jiffies;
-
-                               /* LAPB is PVC Based */
-                               if (card->u.x.LAPB_hdlc)
-                                       chan->common.svc=0;
-                               break;
-
-                       case WAN_CONNECTING:
-                               if (card->u.x.logging){
-                                       printk (KERN_INFO 
-                                               "%s: interface %s connecting, lcn %i ...\n", 
-                                               card->devname, dev->name, chan->common.lcn);
-                               }
-                               break;
-
-                       case WAN_DISCONNECTED:
-                               if (card->u.x.logging){
-                                       printk (KERN_INFO 
-                                               "%s: interface %s disconnected, lcn %i !\n", 
-                                               card->devname, dev->name,chan->common.lcn);
-                               }
-                               atomic_set(&chan->common.disconnect,0);
-                               
-                               if (chan->common.svc) {
-                                       *(unsigned short*)dev->dev_addr = 0;
-                                       card->u.x.svc_to_dev_map[(chan->common.lcn%X25_MAX_CHAN)]=NULL;
-                                       chan->common.lcn = 0;
-                               }
-
-                               if (chan->transmit_length){
-                                       chan->transmit_length=0;
-                                       atomic_set(&chan->common.driver_busy,0);
-                                       chan->tx_offset=0;
-                                       if (netif_queue_stopped(dev)){
-                                               netif_wake_queue(dev);
-                                       }
-                               }
-                               atomic_set(&chan->common.command,0);
-                               break;
-
-                       case WAN_DISCONNECTING:
-                               if (card->u.x.logging){
-                                       printk (KERN_INFO 
-                                       "\n%s: interface %s disconnecting, lcn %i ...\n", 
-                                       card->devname, dev->name,chan->common.lcn);
-                               }
-                               atomic_set(&chan->common.disconnect,0);
-                               break;
-               }
-               chan->common.state = state;
-       }
-       chan->state_tick = jiffies;
-       restore_flags(flags);
-}
-
-/*
- *     Send packet on a logical channel.
- *             When this function is called, tx_skb field of the channel data 
- *             space points to the transmit socket buffer.  When transmission 
- *             is complete, release socket buffer and reset 'tbusy' flag.
- *
- *     Return:         0       - transmission complete
- *                     1       - busy
- *
- *     Notes:
- *     1. If packet length is greater than MTU for this channel, we'll fragment
- *     the packet into 'complete sequence' using M-bit.
- *     2. When transmission is complete, an event notification should be issued
- *     to the router.
- */
-
-static int chan_send(struct net_device* dev, void* buff, unsigned data_len,
-                    unsigned char tx_intr)
-{
-       x25_channel_t* chan = dev->priv;
-       sdla_t* card = chan->card;
-       TX25Status* status = card->flags;
-       unsigned len=0, qdm=0, res=0, orig_len = 0;
-       void *data;
-
-       /* Check to see if channel is ready */
-       if ((!(status->cflags[chan->ch_idx] & 0x40) && !card->u.x.LAPB_hdlc)  || 
-             !(*card->u.x.hdlc_buf_status & 0x40)){ 
-            
-               if (!tx_intr){
-                       setup_for_delayed_transmit (dev, buff, data_len);
-                       return 0;
-               }else{
-                       /* By returning 0 to tx_intr the packet will be dropped */
-                       ++card->wandev.stats.tx_dropped;
-                       ++chan->ifstats.tx_dropped;
-                       printk(KERN_INFO "%s: ERROR, Tx intr could not send, dropping %s:\n", 
-                               card->devname,dev->name);
-                       ++chan->if_send_stat.if_send_bfr_not_passed_to_adptr;
-                       return 0;
-               }
-       }
-
-       if (chan->common.usedby == API){
-               /* Remove the API Header */
-               x25api_hdr_t *api_data = (x25api_hdr_t *)buff;
-
-               /* Set the qdm bits from the packet header 
-                 * User has the option to set the qdm bits
-                 */
-               qdm = api_data->qdm;
-
-               orig_len = len = data_len - sizeof(x25api_hdr_t);
-               data = (unsigned char*)buff + sizeof(x25api_hdr_t);
-       }else{
-               data = buff;
-               orig_len = len = data_len;
-       }       
-
-       if (tx_intr){
-               /* We are in tx_intr, minus the tx_offset from 
-                 * the total length. The tx_offset part of the
-                * data has already been sent. Also, move the 
-                * data pointer to proper offset location.
-                 */
-               len -= chan->tx_offset;
-               data = (unsigned char*)data + chan->tx_offset;
-       }
-               
-       /* Check if the packet length is greater than MTU
-         * If YES: Cut the len to MTU and set the M bit 
-         */
-       if (len > chan->tx_pkt_size && !card->u.x.LAPB_hdlc){
-               len = chan->tx_pkt_size;
-               qdm |= M_BIT;           
-       } 
-
-
-       /* Pass only first three bits of the qdm byte to the send
-         * routine. In case user sets any other bit which might
-         * cause errors. 
-         */
-
-       switch(x25_send(card, chan->common.lcn, (qdm&0x07), len, data)){
-               case 0x00:      /* success */
-                       chan->i_timeout_sofar = jiffies;
-
-                       dev->trans_start=jiffies;
-                       
-                       if ((qdm & M_BIT) && !card->u.x.LAPB_hdlc){
-                               if (!tx_intr){
-                                       /* The M bit was set, which means that part of the
-                                         * packet has been sent. Copy the packet into a buffer
-                                        * and set the offset to len, so on next tx_inter 
-                                        * the packet will be sent using the below offset.
-                                        */
-                                       chan->tx_offset += len;
-
-                                       ++chan->ifstats.tx_packets;
-                                       chan->ifstats.tx_bytes += len;
-                                       
-                                       if (chan->tx_offset < orig_len){
-                                               setup_for_delayed_transmit (dev, buff, data_len);
-                                       }
-                                       res=0;
-                               }else{
-                                       /* We are already in tx_inter, thus data is already
-                                         * in the buffer. Update the offset and wait for
-                                         * next tx_intr. We add on to the offset, since data can
-                                         * be X number of times larger than max data size.
-                                        */
-                                       ++chan->ifstats.tx_packets;
-                                       chan->ifstats.tx_bytes += len;
-                                       
-                                       ++chan->if_send_stat.if_send_bfr_passed_to_adptr;
-                                       chan->tx_offset += len;
-
-                                       /* The user can set the qdm bit as well.
-                                         * If the entire packet was sent and qdm is still
-                                         * set, than it's the user who has set the M bit. In that,
-                                         * case indicate that the packet was send by returning 
-                                        * 0 and wait for a new packet. Otherwise, wait for next
-                                         * tx interrupt to send the rest of the packet */
-
-                                       if (chan->tx_offset < orig_len){
-                                               res=1;
-                                       }else{  
-                                               res=0;
-                                       }
-                               }
-                       }else{
-                               ++chan->ifstats.tx_packets;
-                               chan->ifstats.tx_bytes += len;
-                               ++chan->if_send_stat.if_send_bfr_passed_to_adptr;
-                               res=0;
-                       }
-                       break;
-
-               case 0x33:      /* Tx busy */
-                       if (tx_intr){
-                               printk(KERN_INFO "%s: Tx_intr: Big Error dropping packet %s\n",
-                                               card->devname,dev->name);
-                               ++chan->ifstats.tx_dropped;
-                               ++card->wandev.stats.tx_dropped;
-                               ++chan->if_send_stat.if_send_bfr_not_passed_to_adptr;
-                               res=0;
-                       }else{
-                               DBG_PRINTK(KERN_INFO 
-                                       "%s: Send: Big Error should have tx: storring %s\n",
-                                               card->devname,dev->name);
-                               setup_for_delayed_transmit (dev, buff, data_len);       
-                               res=1;
-                       }
-                       break;
-
-               default:        /* failure */
-                       ++chan->ifstats.tx_errors;
-                       if (tx_intr){
-                               printk(KERN_INFO "%s: Tx_intr: Failure to send, dropping %s\n",
-                                       card->devname,dev->name);
-                               ++chan->ifstats.tx_dropped;
-                               ++card->wandev.stats.tx_dropped;
-                               ++chan->if_send_stat.if_send_bfr_not_passed_to_adptr;
-                               res=0;
-                       }else{
-                               DBG_PRINTK(KERN_INFO "%s: Send: Failure to send !!!, storing %s\n",
-                                       card->devname,dev->name);                       
-                               setup_for_delayed_transmit (dev, buff, data_len);
-                               res=1;
-                       }
-                       break;  
-       }
-       return res;
-}
-
-
-/*
- *     Parse X.25 call request data and fill x25_call_info_t structure.
- */
-
-static void parse_call_info (unsigned char* str, x25_call_info_t* info)
-{
-       memset(info, 0, sizeof(x25_call_info_t));
-       for (; *str; ++str)
-       {
-               int i;
-               unsigned char ch;
-
-               if (*str == '-') switch (str[1]) {
-
-                       /* Take minus 2 off the maximum size so that 
-                         * last byte is 0. This way we can use string
-                         * manipulaton functions on call information.
-                         */
-
-                       case 'd':       /* destination address */
-                               for (i = 0; i < (MAX_X25_ADDR_SIZE-2); ++i){
-                                       ch = str[2+i];
-                                       if (isspace(ch)) break;
-                                       info->dest[i] = ch;
-                               }
-                               break;
-
-                       case 's':       /* source address */
-                               for (i = 0; i < (MAX_X25_ADDR_SIZE-2); ++i){
-                                       ch = str[2+i];
-                                       if (isspace(ch)) break;
-                                       info->src[i] = ch;
-                               }
-                               break;
-
-                       case 'u':       /* user data */
-                               for (i = 0; i < (MAX_X25_DATA_SIZE-2); ++i){
-                                       ch = str[2+i];
-                                       if (isspace(ch)) break;
-                                       info->user[i] = ch; 
-                               }
-                               info->nuser = i;
-                               break;
-
-                       case 'f':       /* facilities */
-                               for (i = 0; i < (MAX_X25_FACL_SIZE-2); ++i){
-                                       ch = str[2+i];
-                                       if (isspace(ch)) break;
-                                       info->facil[i] = ch;
-                               }
-                               info->nfacil = i;
-                               break;
-               }
-       }
-}
-
-/*
- *     Convert line speed in bps to a number used by S502 code.
- */
-
-static unsigned char bps_to_speed_code (unsigned long bps)
-{
-       unsigned char   number;
-
-       if (bps <= 1200)        number = 0x01;
-       else if (bps <= 2400)   number = 0x02;
-       else if (bps <= 4800)   number = 0x03;
-       else if (bps <= 9600)   number = 0x04;
-       else if (bps <= 19200)  number = 0x05;
-       else if (bps <= 38400)  number = 0x06;
-       else if (bps <= 45000)  number = 0x07;
-       else if (bps <= 56000)  number = 0x08;
-       else if (bps <= 64000)  number = 0x09;
-       else if (bps <= 74000)  number = 0x0A;
-       else if (bps <= 112000) number = 0x0B;
-       else if (bps <= 128000) number = 0x0C;
-       else number = 0x0D;
-
-       return number;
-}
-
-/*
- *     Convert decimal string to unsigned integer.
- *     If len != 0 then only 'len' characters of the string are converted.
- */
-
-static unsigned int dec_to_uint (unsigned char* str, int len)
-{
-       unsigned val;
-
-       if (!len) 
-               len = strlen(str);
-
-       for (val = 0; len && isdigit(*str); ++str, --len)
-               val = (val * 10) + (*str - (unsigned)'0');
-       
-       return val;
-}
-
-/*
- *     Convert hex string to unsigned integer.
- *     If len != 0 then only 'len' characters of the string are conferted.
- */
-
-static unsigned int hex_to_uint (unsigned char* str, int len)
-{
-       unsigned val, ch;
-
-       if (!len) 
-               len = strlen(str);
-
-       for (val = 0; len; ++str, --len)
-       {
-               ch = *str;
-               if (isdigit(ch))
-                       val = (val << 4) + (ch - (unsigned)'0');
-               else if (isxdigit(ch))
-                       val = (val << 4) + ((ch & 0xDF) - (unsigned)'A' + 10);
-               else break;
-       }
-       return val;
-}
-
-
-static int handle_IPXWAN(unsigned char *sendpacket, char *devname, unsigned char enable_IPX, unsigned long network_number, unsigned short proto)
-{
-       int i;
-
-       if( proto == ETH_P_IPX) {
-               /* It's an IPX packet */
-               if(!enable_IPX) {
-                       /* Return 1 so we don't pass it up the stack. */
-                       return 1;
-               }
-       } else {
-               /* It's not IPX so pass it up the stack.*/ 
-               return 0;
-       }
-
-       if( sendpacket[16] == 0x90 &&
-           sendpacket[17] == 0x04)
-       {
-               /* It's IPXWAN  */
-
-               if( sendpacket[2] == 0x02 &&
-                   sendpacket[34] == 0x00)
-               {
-                       /* It's a timer request packet */
-                       printk(KERN_INFO "%s: Received IPXWAN Timer Request packet\n",devname);
-
-                       /* Go through the routing options and answer no to every
-                        * option except Unnumbered RIP/SAP
-                        */
-                       for(i = 41; sendpacket[i] == 0x00; i += 5)
-                       {
-                               /* 0x02 is the option for Unnumbered RIP/SAP */
-                               if( sendpacket[i + 4] != 0x02)
-                               {
-                                       sendpacket[i + 1] = 0;
-                               }
-                       }
-
-                       /* Skip over the extended Node ID option */
-                       if( sendpacket[i] == 0x04 )
-                       {
-                               i += 8;
-                       }
-
-                       /* We also want to turn off all header compression opt.                          */ 
-                       for(; sendpacket[i] == 0x80 ;)
-                       {
-                               sendpacket[i + 1] = 0;
-                               i += (sendpacket[i + 2] << 8) + (sendpacket[i + 3]) + 4;
-                       }
-
-                       /* Set the packet type to timer response */
-                       sendpacket[34] = 0x01;
-
-                       printk(KERN_INFO "%s: Sending IPXWAN Timer Response\n",devname);
-               }
-               else if( sendpacket[34] == 0x02 )
-               {
-                       /* This is an information request packet */
-                       printk(KERN_INFO "%s: Received IPXWAN Information Request packet\n",devname);
-
-                       /* Set the packet type to information response */
-                       sendpacket[34] = 0x03;
-
-                       /* Set the router name */
-                       sendpacket[51] = 'X';
-                       sendpacket[52] = 'T';
-                       sendpacket[53] = 'P';
-                       sendpacket[54] = 'I';
-                       sendpacket[55] = 'P';
-                       sendpacket[56] = 'E';
-                       sendpacket[57] = '-';
-                       sendpacket[58] = CVHexToAscii(network_number >> 28);
-                       sendpacket[59] = CVHexToAscii((network_number & 0x0F000000)>> 24);
-                       sendpacket[60] = CVHexToAscii((network_number & 0x00F00000)>> 20);
-                       sendpacket[61] = CVHexToAscii((network_number & 0x000F0000)>> 16);
-                       sendpacket[62] = CVHexToAscii((network_number & 0x0000F000)>> 12);
-                       sendpacket[63] = CVHexToAscii((network_number & 0x00000F00)>> 8);
-                       sendpacket[64] = CVHexToAscii((network_number & 0x000000F0)>> 4);
-                       sendpacket[65] = CVHexToAscii(network_number & 0x0000000F);
-                       for(i = 66; i < 99; i+= 1)
-                       {
-                               sendpacket[i] = 0;
-                       }
-
-                       printk(KERN_INFO "%s: Sending IPXWAN Information Response packet\n",devname);
-               }
-               else
-               {
-                       printk(KERN_INFO "%s: Unknown IPXWAN packet!\n",devname);
-                       return 0;
-               }
-
-               /* Set the WNodeID to our network address */
-               sendpacket[35] = (unsigned char)(network_number >> 24);
-               sendpacket[36] = (unsigned char)((network_number & 0x00FF0000) >> 16);
-               sendpacket[37] = (unsigned char)((network_number & 0x0000FF00) >> 8);
-               sendpacket[38] = (unsigned char)(network_number & 0x000000FF);
-
-               return 1;
-       } else {
-               /*If we get here it's an IPX-data packet, so it'll get passed up the stack.
-                */
-               /* switch the network numbers */
-               switch_net_numbers(sendpacket, network_number, 1);      
-               return 0;
-       }
-}
-
-/*
- *     If incoming is 0 (outgoing)- if the net numbers is ours make it 0
- *     if incoming is 1 - if the net number is 0 make it ours 
- */
-
-static void switch_net_numbers(unsigned char *sendpacket, unsigned long network_number, unsigned char incoming)
-{
-       unsigned long pnetwork_number;
-
-       pnetwork_number = (unsigned long)((sendpacket[6] << 24) + 
-                         (sendpacket[7] << 16) + (sendpacket[8] << 8) + 
-                         sendpacket[9]);
-       
-
-       if (!incoming) {
-               /*If the destination network number is ours, make it 0 */
-               if( pnetwork_number == network_number) {
-                       sendpacket[6] = sendpacket[7] = sendpacket[8] = 
-                                        sendpacket[9] = 0x00;
-               }
-       } else {
-               /* If the incoming network is 0, make it ours */
-               if( pnetwork_number == 0) {
-                       sendpacket[6] = (unsigned char)(network_number >> 24);
-                       sendpacket[7] = (unsigned char)((network_number & 
-                                        0x00FF0000) >> 16);
-                       sendpacket[8] = (unsigned char)((network_number & 
-                                        0x0000FF00) >> 8);
-                       sendpacket[9] = (unsigned char)(network_number & 
-                                        0x000000FF);
-               }
-       }
-
-
-       pnetwork_number = (unsigned long)((sendpacket[18] << 24) + 
-                         (sendpacket[19] << 16) + (sendpacket[20] << 8) + 
-                         sendpacket[21]);
-       
-       
-       if( !incoming ) {
-               /* If the source network is ours, make it 0 */
-               if( pnetwork_number == network_number) {
-                       sendpacket[18] = sendpacket[19] = sendpacket[20] = 
-                                sendpacket[21] = 0x00;
-               }
-       } else {
-               /* If the source network is 0, make it ours */
-               if( pnetwork_number == 0 ) {
-                       sendpacket[18] = (unsigned char)(network_number >> 24);
-                       sendpacket[19] = (unsigned char)((network_number & 
-                                        0x00FF0000) >> 16);
-                       sendpacket[20] = (unsigned char)((network_number & 
-                                        0x0000FF00) >> 8);
-                       sendpacket[21] = (unsigned char)(network_number & 
-                                        0x000000FF);
-               }
-       }
-} /* switch_net_numbers */
-
-
-
-
-/********************* X25API SPECIFIC FUNCTIONS ****************/
-
-
-/*===============================================================
- *  find_channel
- *
- *     Manages the lcn to device map. It increases performance
- *      because it eliminates the need to search through the link  
- *      list for a device which is bounded to a specific lcn.
- *
- *===============================================================*/
-
-
-struct net_device *find_channel(sdla_t *card, unsigned lcn)
-{
-       if (card->u.x.LAPB_hdlc){
-
-               return card->wandev.dev;
-
-       }else{
-               /* We don't know whether the incoming lcn
-                 * is a PVC or an SVC channel. But we do know that
-                 * the lcn cannot be for both the PVC and the SVC
-                 * channel.
-
-                * If the lcn number is greater or equal to 255, 
-                 * take the modulo 255 of that number. We only have
-                 * 255 locations, thus higher numbers must be mapped
-                 * to a number between 0 and 245. 
-
-                * We must separate pvc's and svc's since two don't
-                 * have to be contiguous.  Meaning pvc's can start
-                 * from 1 to 10 and svc's can start from 256 to 266.
-                 * But 256%255 is 1, i.e. CONFLICT.
-                */
-
-
-               /* Highest LCN number must be less or equal to 4096 */
-               if ((lcn <= MAX_LCN_NUM) && (lcn > 0)){
-
-                       if (lcn < X25_MAX_CHAN){
-                               if (card->u.x.svc_to_dev_map[lcn])
-                                       return card->u.x.svc_to_dev_map[lcn];
-
-                               if (card->u.x.pvc_to_dev_map[lcn])
-                                       return card->u.x.pvc_to_dev_map[lcn];
-                       
-                       }else{
-                               int new_lcn = lcn%X25_MAX_CHAN;
-                               if (card->u.x.svc_to_dev_map[new_lcn])
-                                       return card->u.x.svc_to_dev_map[new_lcn];
-
-                               if (card->u.x.pvc_to_dev_map[new_lcn])
-                                       return card->u.x.pvc_to_dev_map[new_lcn];
-                       }
-               }
-               return NULL;
-       }
-}
-
-void bind_lcn_to_dev(sdla_t *card, struct net_device *dev, unsigned lcn)
-{
-       x25_channel_t *chan = dev->priv;
-
-       /* Modulo the lcn number by X25_MAX_CHAN (255)
-        * because the lcn number can be greater than 255 
-         *
-        * We need to split svc and pvc since they don't have
-         * to be contigous. 
-        */
-
-       if (chan->common.svc){
-               card->u.x.svc_to_dev_map[(lcn % X25_MAX_CHAN)] = dev;
-       }else{
-               card->u.x.pvc_to_dev_map[(lcn % X25_MAX_CHAN)] = dev;
-       }
-       chan->common.lcn = lcn;
-}
-
-
-
-/*===============================================================
- * x25api_bh 
- *
- *
- *==============================================================*/
-
-static void x25api_bh(struct net_device* dev)
-{
-       x25_channel_t* chan = dev->priv;
-       sdla_t* card = chan->card;
-       struct sk_buff *skb;
-
-       if (atomic_read(&chan->bh_buff_used) == 0){
-               printk(KERN_INFO "%s: BH Buffer Empty in BH\n",
-                               card->devname);
-               clear_bit(0, &chan->tq_working);
-               return;
-       }
-
-       while (atomic_read(&chan->bh_buff_used)){
-
-               /* If the sock is in the process of unlinking the
-                * driver from the socket, we must get out. 
-                * This never happends but is a sanity check. */
-               if (test_bit(0,&chan->common.common_critical)){
-                       clear_bit(0, &chan->tq_working);
-                       return;
-               }
-               
-               /* If LAPB HDLC, do not drop packets if socket is
-                 * not connected.  Let the buffer fill up and
-                 * turn off rx interrupt */
-               if (card->u.x.LAPB_hdlc){
-                       if (chan->common.sk == NULL || chan->common.func == NULL){
-                               clear_bit(0, &chan->tq_working);                        
-                               return;
-                       }
-               }
-
-               skb  = ((bh_data_t *)&chan->bh_head[chan->bh_read])->skb;
-
-               if (skb == NULL){
-                       printk(KERN_INFO "%s: BH Skb empty for read %i\n",
-                                       card->devname,chan->bh_read);
-               }else{
-                       
-                       if (chan->common.sk == NULL || chan->common.func == NULL){
-                               printk(KERN_INFO "%s: BH: Socket disconnected, dropping\n",
-                                               card->devname);
-                               dev_kfree_skb_any(skb);
-                               x25api_bh_cleanup(dev);
-                               ++chan->ifstats.rx_dropped;
-                               ++chan->rx_intr_stat.rx_intr_bfr_not_passed_to_stack;
-                               continue;
-                       }
-
-
-                       if (chan->common.func(skb,dev,chan->common.sk) != 0){
-                               /* Sock full cannot send, queue us for another
-                                 * try 
-                                */
-                               printk(KERN_INFO "%s: BH: !!! Packet failed to send !!!!! \n",
-                                               card->devname);
-                               atomic_set(&chan->common.receive_block,1);
-                               return;
-                       }else{
-                               x25api_bh_cleanup(dev);
-                               ++chan->rx_intr_stat.rx_intr_bfr_passed_to_stack;
-                       }
-               }
-       }       
-       clear_bit(0, &chan->tq_working);
-
-       return;
-}
-
-/*===============================================================
- * x25api_bh_cleanup 
- *
- *
- *==============================================================*/
-
-static int x25api_bh_cleanup(struct net_device *dev)
-{
-       x25_channel_t* chan = dev->priv;
-       sdla_t *card = chan->card;
-       TX25Status* status = card->flags;
-
-
-       ((bh_data_t *)&chan->bh_head[chan->bh_read])->skb = NULL;
-
-       if (chan->bh_read == MAX_BH_BUFF){
-               chan->bh_read=0;
-       }else{
-               ++chan->bh_read;        
-       }
-
-       /* If the Receive interrupt was off, it means
-         * that we filled up our circular buffer. Check    
-         * that we have space in the buffer. If so 
-         * turn the RX interrupt back on. 
-        */
-       if (!(status->imask & INTR_ON_RX_FRAME)){
-               if (atomic_read(&chan->bh_buff_used) < (MAX_BH_BUFF+1)){
-                       printk(KERN_INFO "%s: BH: Turning on the interrupt\n",
-                                       card->devname);
-                       status->imask |= INTR_ON_RX_FRAME;
-               }
-       }       
-
-       atomic_dec(&chan->bh_buff_used);
-       return 0;
-}
-
-
-/*===============================================================
- * bh_enqueue 
- *
- *
- *==============================================================*/
-
-static int bh_enqueue(struct net_device *dev, struct sk_buff *skb)
-{
-       x25_channel_t* chan = dev->priv;
-       sdla_t *card = chan->card;
-       TX25Status* status = card->flags;
-
-       if (atomic_read(&chan->bh_buff_used) == (MAX_BH_BUFF+1)){
-               printk(KERN_INFO "%s: Bottom half buffer FULL\n",
-                               card->devname);
-               return 1; 
-       }
-
-       ((bh_data_t *)&chan->bh_head[chan->bh_write])->skb = skb;
-
-       if (chan->bh_write == MAX_BH_BUFF){
-               chan->bh_write=0;
-       }else{
-               ++chan->bh_write;
-       }
-
-       atomic_inc(&chan->bh_buff_used);
-
-       if (atomic_read(&chan->bh_buff_used) == (MAX_BH_BUFF+1)){
-               printk(KERN_INFO "%s: Buffer is now full, Turning off RX Intr\n",
-                               card->devname);
-               status->imask &= ~INTR_ON_RX_FRAME;
-       }
-
-       return 0;
-}
-
-
-/*===============================================================
- * timer_intr_cmd_exec
- *  
- *     Called by timer interrupt to execute a command
- *===============================================================*/
-
-static int timer_intr_cmd_exec (sdla_t* card)
-{
-       struct net_device *dev;
-       unsigned char more_to_exec=0;
-       volatile x25_channel_t *chan=NULL;
-       int i=0,bad_cmd=0,err=0;        
-
-       if (card->u.x.cmd_dev == NULL){
-               card->u.x.cmd_dev = card->wandev.dev;
-       }
-
-       dev = card->u.x.cmd_dev;
-
-       for (;;){
-
-               chan = dev->priv;
-               
-               if (atomic_read(&chan->common.command)){ 
-
-                       bad_cmd = check_bad_command(card,dev);
-
-                       if ((!chan->common.mbox || atomic_read(&chan->common.disconnect)) && 
-                            !bad_cmd){
-
-                               /* Socket has died or exited, We must bring the
-                                 * channel down before anybody else tries to 
-                                 * use it */
-                               err = channel_disconnect(card,dev);
-                       }else{
-                               err = execute_delayed_cmd(card, dev,
-                                                        (mbox_cmd_t*)chan->common.mbox,
-                                                         bad_cmd);
-                       }
-
-                       switch (err){
-
-                       case RETURN_RESULT:
-
-                               /* Return the result to the socket without
-                                 * delay. NO_WAIT Command */   
-                               atomic_set(&chan->common.command,0);
-                               if (atomic_read(&card->u.x.command_busy))
-                                       atomic_set(&card->u.x.command_busy,0);
-
-                               send_delayed_cmd_result(card,dev,card->mbox);
-
-                               more_to_exec=0;
-                               break;
-                       case DELAY_RESULT:
-               
-                               /* Wait for the remote to respond, before
-                                 * sending the result up to the socket.
-                                 * WAIT command */
-                               if (atomic_read(&card->u.x.command_busy))
-                                       atomic_set(&card->u.x.command_busy,0);
-                               
-                               atomic_set(&chan->common.command,0);
-                               more_to_exec=0;
-                               break;
-                       default:
-
-                               /* If command could not be executed for
-                                 * some reason (i.e return code 0x33 busy)
-                                 * set the more_to_exec bit which will
-                                 * indicate that this command must be exectued
-                                 * again during next timer interrupt 
-                                */
-                               more_to_exec=1;
-                               if (atomic_read(&card->u.x.command_busy) == 0)
-                                       atomic_set(&card->u.x.command_busy,1);
-                               break;
-                       }
-
-                       bad_cmd=0;
-
-                       /* If flags is set, there are no hdlc buffers,
-                         * thus, wait for the next pass and try the
-                         * same command again. Otherwise, start searching 
-                         * from next device on the next pass. 
-                        */
-                       if (!more_to_exec){
-                               dev = move_dev_to_next(card,dev);
-                       }
-                       break;
-               }else{
-                       /* This device has nothing to execute,
-                         * go to next. 
-                        */
-                       if (atomic_read(&card->u.x.command_busy))
-                                       atomic_set(&card->u.x.command_busy,0);
-                       dev = move_dev_to_next(card,dev);
-               }       
-
-               if (++i == card->u.x.no_dev){
-                       if (!more_to_exec){
-                               DBG_PRINTK(KERN_INFO "%s: Nothing to execute in Timer\n",
-                                       card->devname);
-                               if (atomic_read(&card->u.x.command_busy)){
-                                       atomic_set(&card->u.x.command_busy,0);
-                               }
-                       }
-                       break;
-               }
-
-       } //End of FOR
-
-       card->u.x.cmd_dev = dev;
-       
-       if (more_to_exec){
-               /* If more commands are pending, do not turn off timer 
-                 * interrupt */
-               return 1;
-       }else{
-               /* No more commands, turn off timer interrupt */
-               return 0;
-       }       
-}
-
-/*===============================================================
- * execute_delayed_cmd 
- *
- *     Execute an API command which was passed down from the
- *      sock.  Sock is very limited in which commands it can
- *      execute.  Wait and No Wait commands are supported.  
- *      Place Call, Clear Call and Reset wait commands, where
- *      Accept Call is a no_wait command.
- *
- *===============================================================*/
-
-static int execute_delayed_cmd(sdla_t* card, struct net_device *dev,
-                              mbox_cmd_t *usr_cmd, char bad_cmd)
-{
-       TX25Mbox* mbox = card->mbox;
-       int err;
-       x25_channel_t *chan = dev->priv;
-       int delay=RETURN_RESULT;
-
-       if (!(*card->u.x.hdlc_buf_status & 0x40) && !bad_cmd){
-               return TRY_CMD_AGAIN;
-       }
-
-       /* This way a command is guaranteed to be executed for
-         * a specific lcn, the network interface is bound to. */
-       usr_cmd->cmd.lcn = chan->common.lcn;
-       
-
-       /* If channel is pvc, instead of place call
-         * run x25_channel configuration. If running LAPB HDLC
-         * enable communications. 
-         */
-       if ((!chan->common.svc) && (usr_cmd->cmd.command == X25_PLACE_CALL)){
-
-               if (card->u.x.LAPB_hdlc){
-                       DBG_PRINTK(KERN_INFO "LAPB: Connecting\n");
-                       connect(card);
-                       set_chan_state(dev,WAN_CONNECTING);
-                       return DELAY_RESULT;
-               }else{
-                       DBG_PRINTK(KERN_INFO "%s: PVC is CONNECTING\n",card->devname);
-                       if (x25_get_chan_conf(card, chan) == CMD_OK){
-                               set_chan_state(dev, WAN_CONNECTED);
-                       }else{ 
-                               set_chan_state(dev, WAN_DISCONNECTED);
-                       }
-                       return RETURN_RESULT;
-               }
-       }
-
-       /* Copy the socket mbox command onto the board */
-
-       memcpy(&mbox->cmd, &usr_cmd->cmd, sizeof(TX25Cmd));
-       if (usr_cmd->cmd.length){
-               memcpy(mbox->data, usr_cmd->data, usr_cmd->cmd.length);
-       }
-
-       /* Check if command is bad. We need to copy the cmd into
-         * the buffer regardless since we return the, mbox to
-         * the user */
-       if (bad_cmd){
-               mbox->cmd.result=0x01;
-               return RETURN_RESULT;
-       }
-
-       err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-
-       if (err != CMD_OK && err != X25RES_NOT_READY)
-               x25_error(card, err, usr_cmd->cmd.command, usr_cmd->cmd.lcn);
-
-       if (mbox->cmd.result == X25RES_NOT_READY){
-               return TRY_CMD_AGAIN;
-       }
-
-       switch (mbox->cmd.command){
-
-       case X25_PLACE_CALL:
-               
-               switch (mbox->cmd.result){
-
-               case CMD_OK:
-
-                       /* Check if Place call is a wait command or a 
-                                * no wait command */
-                       if (atomic_read(&chan->common.command) & 0x80)
-                               delay=RETURN_RESULT;
-                       else
-                               delay=DELAY_RESULT;
-               
-
-                       DBG_PRINTK(KERN_INFO "\n%s: PLACE CALL Binding dev %s to lcn %i\n",
-                                       card->devname,dev->name, mbox->cmd.lcn);
-               
-                       bind_lcn_to_dev (card, dev, mbox->cmd.lcn);
-                       set_chan_state(dev, WAN_CONNECTING);
-                       break;
-
-
-               default:
-                       delay=RETURN_RESULT;
-                       set_chan_state(dev, WAN_DISCONNECTED);
-                       break;
-               }
-               break;
-
-       case X25_ACCEPT_CALL: 
-               
-               switch (mbox->cmd.result){
-
-               case CMD_OK:
-
-                       DBG_PRINTK(KERN_INFO "\n%s: ACCEPT Binding dev %s to lcn %i\n",
-                               card->devname,dev->name,mbox->cmd.lcn);
-
-                       bind_lcn_to_dev (card, dev, mbox->cmd.lcn);
-
-                       if (x25_get_chan_conf(card, chan) == CMD_OK){
-
-                               set_chan_state(dev, WAN_CONNECTED);
-                               delay=RETURN_RESULT;
-
-                       }else{ 
-                               if (x25_clear_call(card, usr_cmd->cmd.lcn, 0, 0) == CMD_OK){
-                                       /* if clear is successful, wait for clear confirm 
-                                        */ 
-                                       delay=DELAY_RESULT;
-                               }else{
-                                       /* Do not change the state here. If we fail 
-                                        * the accept the return code is send up 
-                                        *the stack, which will ether retry
-                                                * or clear the call 
-                                        */
-                                       DBG_PRINTK(KERN_INFO 
-                                               "%s: ACCEPT: STATE MAY BE CURRUPTED 2 !!!!!\n",
-                                               card->devname);
-                                       delay=RETURN_RESULT;
-                               }
-                       }
-                       break;
-
-
-               case X25RES_ASYNC_PACKET:
-                       delay=TRY_CMD_AGAIN;
-                       break;
-
-               default: 
-                       DBG_PRINTK(KERN_INFO "%s: ACCEPT FAILED\n",card->devname);
-                       if (x25_clear_call(card, usr_cmd->cmd.lcn, 0, 0) == CMD_OK){
-                               delay=DELAY_RESULT;
-                       }else{
-                               /* Do not change the state here. If we fail the accept. The
-                                 * return code is send up the stack, which will ether retry
-                                 * or clear the call */
-                               DBG_PRINTK(KERN_INFO 
-                                       "%s: ACCEPT: STATE MAY BE CORRUPTED 1 !!!!!\n",
-                                               card->devname);
-                               delay=RETURN_RESULT;
-                       }
-               }
-               break;
-
-       case X25_CLEAR_CALL:
-
-               switch (mbox->cmd.result){
-
-               case CMD_OK:
-                       DBG_PRINTK(KERN_INFO 
-                                       "CALL CLEAR OK: Dev %s Mbox Lcn %i  Chan Lcn %i\n",
-                                       dev->name,mbox->cmd.lcn,chan->common.lcn);
-                       set_chan_state(dev, WAN_DISCONNECTING);
-                       delay = DELAY_RESULT;
-                       break;
-
-               case X25RES_CHANNEL_IN_USE:
-               case X25RES_ASYNC_PACKET:
-                       delay = TRY_CMD_AGAIN;
-                       break;
-                       
-               case X25RES_LINK_NOT_IN_ABM:
-               case X25RES_INVAL_LCN:
-               case X25RES_INVAL_STATE:
-                       set_chan_state(dev, WAN_DISCONNECTED);
-                       delay = RETURN_RESULT;
-                       break;
-               
-               default:
-                       /* If command did not execute because of user
-                         * fault, do not change the state. This will
-                         * signal the socket that clear command failed.
-                         * User can retry or close the socket.
-                         * When socket gets killed, it will set the 
-                         * chan->disconnect which will signal
-                         * driver to clear the call */
-                       printk(KERN_INFO "%s: Clear Command Failed, Rc %x\n",
-                               card->devname,mbox->cmd.command); 
-                       delay = RETURN_RESULT;
-               }
-               break;
-       }       
-
-       return delay;
-}
-
-/*===============================================================
- * api_incoming_call 
- *
- *     Pass an incoming call request up the listening
- *      sock.  If the API sock is not listening reject the
- *      call.
- *
- *===============================================================*/
-
-static int api_incoming_call (sdla_t* card, TX25Mbox *mbox, int lcn)
-{
-       struct sk_buff *skb;
-       int len = sizeof(TX25Cmd)+mbox->cmd.length;
-
-       if (alloc_and_init_skb_buf(card, &skb, len)){
-               printk(KERN_INFO "%s: API incoming call, no memory\n",card->devname);
-               return 1;
-       }
-
-       memcpy(skb_put(skb,len),&mbox->cmd,len);
-
-       skb->mac.raw = skb->data;
-       skb->protocol = htons(X25_PROT);
-       skb->pkt_type = WAN_PACKET_ASYNC;
-
-       if (card->func(skb,card->sk) < 0){
-               printk(KERN_INFO "%s: MAJOR ERROR: Failed to send up place call \n",card->devname);
-                dev_kfree_skb_any(skb);
-               return 1;
-       }
-
-       return 0;
-}
-
-/*===============================================================
- * send_delayed_cmd_result
- *
- *     Wait commands like PLEACE CALL or CLEAR CALL must wait
- *      until the result arrives. This function passes
- *      the result to a waiting sock. 
- *
- *===============================================================*/
-static void send_delayed_cmd_result(sdla_t *card, struct net_device *dev,
-                                   TX25Mbox* mbox)
-{
-       x25_channel_t *chan = dev->priv;
-       mbox_cmd_t *usr_cmd = (mbox_cmd_t *)chan->common.mbox;
-       struct sk_buff *skb;
-       int len=sizeof(unsigned char);
-
-       atomic_set(&chan->common.command,0);
-
-       /* If the sock is in the process of unlinking the
-        * driver from the socket, we must get out. 
-        * This never happends but is a sanity check. */
-       if (test_bit(0,&chan->common.common_critical)){
-               return;
-       }
-
-       if (!usr_cmd || !chan->common.sk || !chan->common.func){
-               DBG_PRINTK(KERN_INFO "Delay result: Sock not bounded sk: %u, func: %u, mbox: %u\n",
-                       (unsigned int)chan->common.sk,
-                       (unsigned int)chan->common.func,
-                       (unsigned int)usr_cmd); 
-               return;
-       }
-
-       memcpy(&usr_cmd->cmd, &mbox->cmd, sizeof(TX25Cmd)); 
-       if (mbox->cmd.length > 0){
-               memcpy(usr_cmd->data, mbox->data, mbox->cmd.length);
-       }
-
-       if (alloc_and_init_skb_buf(card,&skb,len)){
-               printk(KERN_INFO "Delay result: No sock buffers\n");
-               return;
-       }
-
-       memcpy(skb_put(skb,len),&mbox->cmd.command,len);
-       
-       skb->mac.raw = skb->data;
-       skb->pkt_type = WAN_PACKET_CMD;
-                       
-       chan->common.func(skb,dev,chan->common.sk);
-}
-
-/*===============================================================
- * clear_confirm_event
- *
- *     Pass the clear confirmation event up the sock. The
- *      API will disconnect only after the clear confirmation
- *      has been received. 
- *
- *      Depending on the state, clear confirmation could 
- *      be an OOB event, or a result of an API command.
- *===============================================================*/
-
-static int clear_confirm_event (sdla_t *card, TX25Mbox* mb)
-{
-       struct net_device *dev;
-       x25_channel_t *chan;
-       unsigned char old_state;        
-
-       dev = find_channel(card,mb->cmd.lcn);
-       if (!dev){
-               DBG_PRINTK(KERN_INFO "%s: *** GOT CLEAR BUT NO DEV %i\n",
-                               card->devname,mb->cmd.lcn);
-               return 0;
-       }
-
-       chan=dev->priv;
-       DBG_PRINTK(KERN_INFO "%s: GOT CLEAR CONFIRM %s:  Mbox lcn %i  Chan lcn %i\n",
-                       card->devname, dev->name, mb->cmd.lcn, chan->common.lcn);
-
-       /* If not API fall through to default. 
-        * If API, send the result to a waiting
-         * socket.
-        */
-       
-       old_state = chan->common.state;
-       set_chan_state(dev, WAN_DISCONNECTED);
-
-       if (chan->common.usedby == API){
-               switch (old_state) {
-
-               case WAN_DISCONNECTING:
-               case WAN_CONNECTING:
-                       send_delayed_cmd_result(card,dev,mb);
-                       break;
-               case WAN_CONNECTED:
-                       send_oob_msg(card,dev,mb);
-                       break;
-               }
-               return 1;
-       }
-
-       return 0;
-}
-
-/*===============================================================
- * send_oob_msg
- *
- *    Construct an NEM Message and pass it up the connected
- *    sock. If the sock is not bounded discard the NEM.
- *
- *===============================================================*/
-
-static void send_oob_msg(sdla_t *card, struct net_device *dev, TX25Mbox *mbox)
-{
-       x25_channel_t *chan = dev->priv;
-       mbox_cmd_t *usr_cmd = (mbox_cmd_t *)chan->common.mbox;
-       struct sk_buff *skb;
-       int len=sizeof(x25api_hdr_t)+mbox->cmd.length;
-       x25api_t *api_hdr;
-
-       /* If the sock is in the process of unlinking the
-        * driver from the socket, we must get out. 
-        * This never happends but is a sanity check. */
-       if (test_bit(0,&chan->common.common_critical)){
-               return;
-       }
-
-       if (!usr_cmd || !chan->common.sk || !chan->common.func){
-               DBG_PRINTK(KERN_INFO "OOB MSG: Sock not bounded\n"); 
-               return;
-       }
-
-       memcpy(&usr_cmd->cmd, &mbox->cmd, sizeof(TX25Cmd)); 
-       if (mbox->cmd.length > 0){
-               memcpy(usr_cmd->data, mbox->data, mbox->cmd.length);
-       }
-
-       if (alloc_and_init_skb_buf(card,&skb,len)){
-               printk(KERN_INFO "%s: OOB MSG: No sock buffers\n",card->devname);
-               return;
-       }
-
-       api_hdr = (x25api_t*)skb_put(skb,len); 
-       api_hdr->hdr.pktType = mbox->cmd.pktType & 0x7F;
-       api_hdr->hdr.qdm     = mbox->cmd.qdm;
-       api_hdr->hdr.cause   = mbox->cmd.cause;
-       api_hdr->hdr.diagn   = mbox->cmd.diagn;
-       api_hdr->hdr.length  = mbox->cmd.length;
-       api_hdr->hdr.result  = mbox->cmd.result;
-       api_hdr->hdr.lcn     = mbox->cmd.lcn;
-
-       if (mbox->cmd.length > 0){
-               memcpy(api_hdr->data,mbox->data,mbox->cmd.length);
-       }
-       
-       skb->mac.raw = skb->data;
-       skb->pkt_type = WAN_PACKET_ERR;
-                       
-       if (chan->common.func(skb,dev,chan->common.sk) < 0){
-               if (bh_enqueue(dev,skb)){
-                       printk(KERN_INFO "%s: Dropping OOB MSG\n",card->devname);
-                       dev_kfree_skb_any(skb);
-               }
-       }
-
-       DBG_PRINTK(KERN_INFO "%s: OOB MSG OK, %s, lcn %i\n",
-                       card->devname, dev->name, mbox->cmd.lcn);
-}      
-
-/*===============================================================
- *  alloc_and_init_skb_buf 
- *
- *     Allocate and initialize an skb buffer. 
- *
- *===============================================================*/
-
-static int alloc_and_init_skb_buf (sdla_t *card, struct sk_buff **skb, int len)
-{
-       struct sk_buff *new_skb = *skb;
-
-       new_skb = dev_alloc_skb(len + X25_HRDHDR_SZ);
-       if (new_skb == NULL){
-               printk(KERN_INFO "%s: no socket buffers available!\n",
-                       card->devname);
-               return 1;
-       }
-
-       if (skb_tailroom(new_skb) < len){
-               /* No room for the packet. Call off the whole thing! */
-                dev_kfree_skb_any(new_skb);
-               printk(KERN_INFO "%s: Listen: unexpectedly long packet sequence\n"
-                       ,card->devname);
-               *skb = NULL;
-               return 1;
-       }
-
-       *skb = new_skb;
-       return 0;
-
-}
-
-/*===============================================================
- *  api_oob_event 
- *
- *     Send an OOB event up to the sock 
- *
- *===============================================================*/
-
-static void api_oob_event (sdla_t *card,TX25Mbox *mbox)
-{
-       struct net_device *dev = find_channel(card, mbox->cmd.lcn);
-       x25_channel_t *chan;
-
-       if (!dev)
-               return;
-
-       chan=dev->priv;
-
-       if (chan->common.usedby == API)
-               send_oob_msg(card,dev,mbox);
-       
-}
-
-
-
-
-static int channel_disconnect(sdla_t* card, struct net_device *dev)
-{
-
-       int err;
-       x25_channel_t *chan = dev->priv;
-
-       DBG_PRINTK(KERN_INFO "%s: TIMER: %s, Device down disconnecting\n",
-                               card->devname,dev->name);
-
-       if (chan->common.svc){
-               err = x25_clear_call(card,chan->common.lcn,0,0);
-       }else{
-               /* If channel is PVC or LAPB HDLC, there is no call
-                 * to be cleared, thus drop down to the default
-                 * area 
-                */
-               err = 1;
-       }
-
-       switch (err){
-       
-               case X25RES_CHANNEL_IN_USE:     
-               case X25RES_NOT_READY:
-                       err = TRY_CMD_AGAIN;
-                       break;
-               case CMD_OK:
-                       DBG_PRINTK(KERN_INFO "CALL CLEAR OK: Dev %s Chan Lcn %i\n",
-                                               dev->name,chan->common.lcn);
-
-                       set_chan_state(dev,WAN_DISCONNECTING);
-                       atomic_set(&chan->common.command,0);
-                       err = DELAY_RESULT;
-                       break;
-               default:
-                       /* If LAPB HDLC protocol, bring the whole link down
-                         * once the application terminates 
-                        */
-
-                       set_chan_state(dev,WAN_DISCONNECTED);
-
-                       if (card->u.x.LAPB_hdlc){
-                               DBG_PRINTK(KERN_INFO "LAPB: Disconnecting Link\n");
-                               hdlc_link_down (card);
-                       }
-                       atomic_set(&chan->common.command,0);
-                       err = RETURN_RESULT;
-                       break;
-       }
-
-       return err;
-}
-
-static void hdlc_link_down (sdla_t *card)
-{
-       TX25Mbox* mbox = card->mbox;
-       int retry = 5;
-       int err=0;
-
-       do {
-               memset(mbox,0,sizeof(TX25Mbox));
-               mbox->cmd.command = X25_HDLC_LINK_DISC;
-               mbox->cmd.length = 1;
-               mbox->data[0]=0;
-               err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-
-       } while (err && retry-- && x25_error(card, err, X25_HDLC_LINK_DISC, 0));
-
-       if (err)
-               printk(KERN_INFO "%s: Hdlc Link Down Failed %x\n",card->devname,err);
-
-       disconnect (card);
-       
-}
-
-static int check_bad_command(sdla_t* card, struct net_device *dev)
-{
-       x25_channel_t *chan = dev->priv;
-       int bad_cmd = 0;
-
-       switch (atomic_read(&chan->common.command)&0x7F){
-
-               case X25_PLACE_CALL:
-                       if (chan->common.state != WAN_DISCONNECTED)
-                               bad_cmd=1;
-                       break;
-               case X25_CLEAR_CALL:
-                       if (chan->common.state == WAN_DISCONNECTED)
-                               bad_cmd=1;
-                       break;
-               case X25_ACCEPT_CALL:
-                       if (chan->common.state != WAN_CONNECTING)
-                               bad_cmd=1;
-                       break;
-               case X25_RESET:
-                       if (chan->common.state != WAN_CONNECTED)
-                               bad_cmd=1;
-                       break;
-               default:
-                       bad_cmd=1;
-                       break;
-       }
-
-       if (bad_cmd){
-               printk(KERN_INFO "%s: Invalid State, BAD Command %x, dev %s, lcn %i, st %i\n", 
-                       card->devname,atomic_read(&chan->common.command),dev->name, 
-                       chan->common.lcn, chan->common.state);
-       }
-
-       return bad_cmd;
-}
-
-
-
-/*************************** XPIPEMON FUNCTIONS **************************/
-
-/*==============================================================================
- * Process UDP call of type XPIPE
- */
-
-static int process_udp_mgmt_pkt(sdla_t *card)
-{
-       int            c_retry = MAX_CMD_RETRY;
-       unsigned int   len;
-       struct sk_buff *new_skb;
-       TX25Mbox       *mbox = card->mbox;
-       int            err;
-       int            udp_mgmt_req_valid = 1;
-       struct net_device *dev;
-        x25_channel_t  *chan;
-       unsigned short lcn;
-       struct timeval tv;
-       
-
-       x25_udp_pkt_t *x25_udp_pkt;
-       x25_udp_pkt = (x25_udp_pkt_t *)card->u.x.udp_pkt_data;
-
-       dev = card->u.x.udp_dev;
-       chan = dev->priv;
-       lcn = chan->common.lcn;
-
-       switch(x25_udp_pkt->cblock.command) {
-            
-               /* XPIPE_ENABLE_TRACE */
-               case XPIPE_ENABLE_TRACING:
-
-               /* XPIPE_GET_TRACE_INFO */
-               case XPIPE_GET_TRACE_INFO:
-               /* SET FT1 MODE */
-               case XPIPE_SET_FT1_MODE:
-           
-                       if(card->u.x.udp_pkt_src == UDP_PKT_FRM_NETWORK) {
-                               ++chan->pipe_mgmt_stat.UDP_PIPE_mgmt_direction_err;
-                               udp_mgmt_req_valid = 0;
-                               break;
-                       }
-
-               /* XPIPE_FT1_READ_STATUS */
-               case XPIPE_FT1_READ_STATUS:
-
-               /* FT1 MONITOR STATUS */
-               case XPIPE_FT1_STATUS_CTRL:
-                       if(card->hw.fwid !=  SFID_X25_508) {
-                               ++chan->pipe_mgmt_stat.UDP_PIPE_mgmt_adptr_type_err;
-                               udp_mgmt_req_valid = 0;
-                               break;
-                       }
-               default:
-                       break;
-               }
-
-       if(!udp_mgmt_req_valid) {
-               /* set length to 0 */
-               x25_udp_pkt->cblock.length = 0;
-               /* set return code */
-               x25_udp_pkt->cblock.result = (card->hw.fwid != SFID_X25_508) ? 0x1F : 0xCD;
-               
-       } else {   
-        
-               switch (x25_udp_pkt->cblock.command) {
-    
-       
-               case XPIPE_FLUSH_DRIVER_STATS:
-                       init_x25_channel_struct(chan);
-                       init_global_statistics(card);
-                       mbox->cmd.length = 0;
-                       break;
-
-
-               case XPIPE_DRIVER_STAT_IFSEND:
-                       memcpy(x25_udp_pkt->data, &chan->if_send_stat, sizeof(if_send_stat_t));
-                       mbox->cmd.length = sizeof(if_send_stat_t);
-                       x25_udp_pkt->cblock.length =  mbox->cmd.length; 
-                       break;
-       
-               case XPIPE_DRIVER_STAT_INTR:
-                       memcpy(&x25_udp_pkt->data[0], &card->statistics, sizeof(global_stats_t));
-                        memcpy(&x25_udp_pkt->data[sizeof(global_stats_t)],
-                                &chan->rx_intr_stat, sizeof(rx_intr_stat_t));
-                       
-                       mbox->cmd.length = sizeof(global_stats_t) +
-                                       sizeof(rx_intr_stat_t);
-                       x25_udp_pkt->cblock.length =  mbox->cmd.length;
-                       break;
-
-               case XPIPE_DRIVER_STAT_GEN:
-                        memcpy(x25_udp_pkt->data,
-                                &chan->pipe_mgmt_stat.UDP_PIPE_mgmt_kmalloc_err,
-                                sizeof(pipe_mgmt_stat_t));
-
-                        memcpy(&x25_udp_pkt->data[sizeof(pipe_mgmt_stat_t)],
-                               &card->statistics, sizeof(global_stats_t));
-
-                        x25_udp_pkt->cblock.result = 0;
-                        x25_udp_pkt->cblock.length = sizeof(global_stats_t)+
-                                                     sizeof(rx_intr_stat_t);
-                        mbox->cmd.length = x25_udp_pkt->cblock.length;
-                        break;
-
-               case XPIPE_ROUTER_UP_TIME:
-                       do_gettimeofday(&tv);
-                       chan->router_up_time = tv.tv_sec - chan->router_start_time;
-                       *(unsigned long *)&x25_udp_pkt->data = chan->router_up_time;    
-                       x25_udp_pkt->cblock.length = mbox->cmd.length = 4;
-                       x25_udp_pkt->cblock.result = 0;
-                       break;
-       
-               default :
-
-                       do {
-                               memcpy(&mbox->cmd, &x25_udp_pkt->cblock.command, sizeof(TX25Cmd));
-                               if(mbox->cmd.length){ 
-                                       memcpy(&mbox->data, 
-                                              (char *)x25_udp_pkt->data, 
-                                              mbox->cmd.length);
-                               }       
-               
-                               err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-                       } while (err && c_retry-- && x25_error(card, err, mbox->cmd.command, 0));
-
-
-                       if ( err == CMD_OK || 
-                           (err == 1 && 
-                            (mbox->cmd.command == 0x06 || 
-                             mbox->cmd.command == 0x16)  ) ){
-
-                               ++chan->pipe_mgmt_stat.UDP_PIPE_mgmt_adptr_cmnd_OK;
-                       } else {
-                               ++chan->pipe_mgmt_stat.UDP_PIPE_mgmt_adptr_cmnd_timeout;
-                       }
-
-                         /* copy the result back to our buffer */
-                       memcpy(&x25_udp_pkt->cblock.command, &mbox->cmd, sizeof(TX25Cmd));
-
-                       if(mbox->cmd.length) {
-                              memcpy(&x25_udp_pkt->data, &mbox->data, mbox->cmd.length);
-                       }
-                       break;
-
-               } //switch
-
-        }
-    
-        /* Fill UDP TTL */
-
-       x25_udp_pkt->ip_pkt.ttl = card->wandev.ttl;
-        len = reply_udp(card->u.x.udp_pkt_data, mbox->cmd.length);
-
-
-        if(card->u.x.udp_pkt_src == UDP_PKT_FRM_NETWORK) {
-               
-               err = x25_send(card, lcn, 0, len, card->u.x.udp_pkt_data);
-               if (!err) 
-                       ++chan->pipe_mgmt_stat.UDP_PIPE_mgmt_adptr_send_passed;
-               else
-                       ++chan->pipe_mgmt_stat.UDP_PIPE_mgmt_adptr_send_failed;
-       
-       } else {
-
-               /* Allocate socket buffer */
-               if((new_skb = dev_alloc_skb(len)) != NULL) {
-                       void *buf;
-
-                       /* copy data into new_skb */
-                       buf = skb_put(new_skb, len);
-                       memcpy(buf, card->u.x.udp_pkt_data, len);
-        
-                       /* Decapsulate packet and pass it up the protocol 
-                          stack */
-                       new_skb->dev = dev;
-       
-                       if (chan->common.usedby == API)
-                               new_skb->protocol = htons(X25_PROT);
-                       else 
-                               new_skb->protocol = htons(ETH_P_IP);
-       
-                        new_skb->mac.raw = new_skb->data;
-
-                       netif_rx(new_skb);
-                       ++chan->pipe_mgmt_stat.UDP_PIPE_mgmt_passed_to_stack;
-               
-               } else {
-                       ++chan->pipe_mgmt_stat.UDP_PIPE_mgmt_no_socket;
-                       printk(KERN_INFO 
-                       "%s: UDP mgmt cmnd, no socket buffers available!\n", 
-                       card->devname);
-               }
-        }
-
-       card->u.x.udp_pkt_lgth = 0;
-
-       return 1;
-}
-
-
-/*==============================================================================
- * Determine what type of UDP call it is. DRVSTATS or XPIPE8ND ?
- */
-static int udp_pkt_type( struct sk_buff *skb, sdla_t* card )
-{
-       x25_udp_pkt_t *x25_udp_pkt = (x25_udp_pkt_t *)skb->data;
-
-        if((x25_udp_pkt->ip_pkt.protocol == UDPMGMT_UDP_PROTOCOL) &&
-               (x25_udp_pkt->ip_pkt.ver_inet_hdr_length == 0x45) &&
-               (x25_udp_pkt->udp_pkt.udp_dst_port == ntohs(card->wandev.udp_port)) &&
-               (x25_udp_pkt->wp_mgmt.request_reply == UDPMGMT_REQUEST)) {
-
-                        if(!strncmp(x25_udp_pkt->wp_mgmt.signature,
-                                UDPMGMT_XPIPE_SIGNATURE, 8)){
-                                return UDP_XPIPE_TYPE;
-                       }else{
-                               printk(KERN_INFO "%s: UDP Packet, Failed Signature !\n",
-                                       card->devname);
-                       }
-       }
-
-        return UDP_INVALID_TYPE;
-}
-
-
-/*============================================================================
- * Reply to UDP Management system.
- * Return nothing.
- */
-static int reply_udp( unsigned char *data, unsigned int mbox_len ) 
-{
-       unsigned short len, udp_length, temp, ip_length;
-       unsigned long ip_temp;
-       int even_bound = 0;
-
-  
-       x25_udp_pkt_t *x25_udp_pkt = (x25_udp_pkt_t *)data; 
-
-       /* Set length of packet */
-       len = sizeof(ip_pkt_t)+ 
-             sizeof(udp_pkt_t)+
-             sizeof(wp_mgmt_t)+
-             sizeof(cblock_t)+
-             mbox_len;
-
-       /* fill in UDP reply */
-       x25_udp_pkt->wp_mgmt.request_reply = UDPMGMT_REPLY;
-  
-       /* fill in UDP length */
-       udp_length = sizeof(udp_pkt_t)+ 
-                    sizeof(wp_mgmt_t)+
-                    sizeof(cblock_t)+
-                    mbox_len; 
-
-
-       /* put it on an even boundary */
-       if ( udp_length & 0x0001 ) {
-               udp_length += 1;
-               len += 1;
-               even_bound = 1;
-       }
-
-       temp = (udp_length<<8)|(udp_length>>8);
-       x25_udp_pkt->udp_pkt.udp_length = temp;
-        
-       /* swap UDP ports */
-       temp = x25_udp_pkt->udp_pkt.udp_src_port;
-       x25_udp_pkt->udp_pkt.udp_src_port = 
-                       x25_udp_pkt->udp_pkt.udp_dst_port; 
-       x25_udp_pkt->udp_pkt.udp_dst_port = temp;
-
-
-
-       /* add UDP pseudo header */
-       temp = 0x1100;
-       *((unsigned short *)
-               (x25_udp_pkt->data+mbox_len+even_bound)) = temp;        
-       temp = (udp_length<<8)|(udp_length>>8);
-       *((unsigned short *)
-               (x25_udp_pkt->data+mbox_len+even_bound+2)) = temp;
-                
-       /* calculate UDP checksum */
-       x25_udp_pkt->udp_pkt.udp_checksum = 0;
-
-       x25_udp_pkt->udp_pkt.udp_checksum = 
-               calc_checksum(&data[UDP_OFFSET], udp_length+UDP_OFFSET);
-
-       /* fill in IP length */
-       ip_length = len;
-       temp = (ip_length<<8)|(ip_length>>8);
-       x25_udp_pkt->ip_pkt.total_length = temp;
-  
-       /* swap IP addresses */
-       ip_temp = x25_udp_pkt->ip_pkt.ip_src_address;
-       x25_udp_pkt->ip_pkt.ip_src_address = 
-                               x25_udp_pkt->ip_pkt.ip_dst_address;
-       x25_udp_pkt->ip_pkt.ip_dst_address = ip_temp;
-
-                
-       /* fill in IP checksum */
-       x25_udp_pkt->ip_pkt.hdr_checksum = 0;
-       x25_udp_pkt->ip_pkt.hdr_checksum = calc_checksum(data, sizeof(ip_pkt_t));
-
-       return len;
-} /* reply_udp */
-
-unsigned short calc_checksum (char *data, int len)
-{
-       unsigned short temp; 
-       unsigned long sum=0;
-       int i;
-
-       for( i = 0; i <len; i+=2 ) {
-               memcpy(&temp,&data[i],2);
-               sum += (unsigned long)temp;
-       }
-
-       while (sum >> 16 ) {
-               sum = (sum & 0xffffUL) + (sum >> 16);
-       }
-
-       temp = (unsigned short)sum;
-       temp = ~temp;
-
-       if( temp == 0 ) 
-               temp = 0xffff;
-
-       return temp;    
-}
-
-/*=============================================================================
- * Store a UDP management packet for later processing.
- */
-
-static int store_udp_mgmt_pkt(int udp_type, char udp_pkt_src, sdla_t* card,
-                             struct net_device *dev, struct sk_buff *skb,
-                             int lcn)
-{
-        int udp_pkt_stored = 0;
-
-        if(!card->u.x.udp_pkt_lgth && (skb->len <= MAX_LGTH_UDP_MGNT_PKT)){
-                card->u.x.udp_pkt_lgth = skb->len;
-                card->u.x.udp_type = udp_type;
-                card->u.x.udp_pkt_src = udp_pkt_src;
-                card->u.x.udp_lcn = lcn;
-               card->u.x.udp_dev = dev;
-                memcpy(card->u.x.udp_pkt_data, skb->data, skb->len);
-                card->u.x.timer_int_enabled |= TMR_INT_ENABLED_UDP_PKT;
-                udp_pkt_stored = 1;
-
-        }else{
-                printk(KERN_INFO "%s: ERROR: UDP packet not stored for LCN %d\n", 
-                                                       card->devname,lcn);
-       }
-
-        if(udp_pkt_src == UDP_PKT_FRM_STACK){
-                dev_kfree_skb_any(skb);
-       }else{
-                dev_kfree_skb_any(skb);
-       }
-
-        return(udp_pkt_stored);
-}
-
-
-
-/*=============================================================================
- * Initial the ppp_private_area structure.
- */
-static void init_x25_channel_struct( x25_channel_t *chan )
-{
-       memset(&chan->if_send_stat.if_send_entry,0,sizeof(if_send_stat_t));
-       memset(&chan->rx_intr_stat.rx_intr_no_socket,0,sizeof(rx_intr_stat_t));
-       memset(&chan->pipe_mgmt_stat.UDP_PIPE_mgmt_kmalloc_err,0,sizeof(pipe_mgmt_stat_t));
-}
-
-/*============================================================================
- * Initialize Global Statistics
- */
-static void init_global_statistics( sdla_t *card )
-{
-       memset(&card->statistics.isr_entry,0,sizeof(global_stats_t));
-}
-
-
-/*===============================================================
- * SMP Support
- * ==============================================================*/
-
-static void S508_S514_lock(sdla_t *card, unsigned long *smp_flags)
-{
-       spin_lock_irqsave(&card->wandev.lock, *smp_flags);
-}
-static void S508_S514_unlock(sdla_t *card, unsigned long *smp_flags)
-{
-       spin_unlock_irqrestore(&card->wandev.lock, *smp_flags);
-}
-
-/*===============================================================
- * x25_timer_routine
- *
- *     A more efficient polling routine.  Each half a second
- *     queue a polling task. We want to do the polling in a 
- *     task not timer, because timer runs in interrupt time.
- *
- *     FIXME Polling should be rethinked.
- *==============================================================*/
-
-static void x25_timer_routine(unsigned long data)
-{
-       sdla_t *card = (sdla_t*)data;
-
-       if (!card->wandev.dev){
-               printk(KERN_INFO "%s: Stopping the X25 Poll Timer: No Dev.\n",
-                               card->devname);
-               return;
-       }
-
-       if (card->open_cnt != card->u.x.num_of_ch){
-               printk(KERN_INFO "%s: Stopping the X25 Poll Timer: Interface down.\n",
-                               card->devname);
-               return;
-       }
-
-       if (test_bit(PERI_CRIT,&card->wandev.critical)){
-               printk(KERN_INFO "%s: Stopping the X25 Poll Timer: Shutting down.\n",
-                               card->devname);
-               return;
-       }
-       
-       if (!test_and_set_bit(POLL_CRIT,&card->wandev.critical)){
-               trigger_x25_poll(card);
-       }
-       
-       card->u.x.x25_timer.expires=jiffies+(HZ>>1);
-       add_timer(&card->u.x.x25_timer);
-       return;
-}
-
-void disable_comm_shutdown(sdla_t *card)
-{
-       TX25Mbox* mbox = card->mbox;
-       int err;
-
-       /* Turn of interrutps */
-       mbox->data[0] = 0;
-       if (card->hw.fwid == SFID_X25_508){
-               mbox->data[1] = card->hw.irq;
-               mbox->data[2] = 2;
-               mbox->cmd.length = 3;
-       }else {
-               mbox->cmd.length  = 1;
-       }
-       mbox->cmd.command = X25_SET_INTERRUPT_MODE;
-       err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-       if (err)
-               printk(KERN_INFO "INTERRUPT OFF FAIED %x\n",err);
-
-       /* Bring down HDLC */
-       mbox->cmd.command = X25_HDLC_LINK_CLOSE;
-       mbox->cmd.length  = 0;
-       err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-       if (err)
-               printk(KERN_INFO "LINK CLOSED FAILED %x\n",err);
-
-
-       /* Brind down DTR */
-       mbox->data[0] = 0;
-       mbox->data[2] = 0;
-       mbox->data[1] = 0x01;
-       mbox->cmd.length  = 3;
-       mbox->cmd.command = X25_SET_GLOBAL_VARS;
-       err = sdla_exec(mbox) ? mbox->cmd.result : CMD_TIMEOUT;
-       if (err)
-               printk(KERN_INFO "DTR DOWN FAILED %x\n",err);
-
-}
-
-MODULE_LICENSE("GPL");
-
-/****** End *****************************************************************/
diff --git a/drivers/net/wan/sdladrv.c b/drivers/net/wan/sdladrv.c
deleted file mode 100644 (file)
index 032c0f8..0000000
+++ /dev/null
@@ -1,2314 +0,0 @@
-/*****************************************************************************
-* sdladrv.c    SDLA Support Module.  Main module.
-*
-*              This module is a library of common hardware-specific functions
-*              used by all Sangoma drivers.
-*
-* Author:      Gideon Hack     
-*
-* Copyright:   (c) 1995-2000 Sangoma Technologies Inc.
-*
-*              This program is free software; you can redistribute it and/or
-*              modify it under the terms of the GNU General Public License
-*              as published by the Free Software Foundation; either version
-*              2 of the License, or (at your option) any later version.
-* ============================================================================
-* Mar 20, 2001  Nenad Corbic   Added the auto_pci_cfg filed, to support
-*                               the PCISLOT #0. 
-* Apr 04, 2000  Nenad Corbic   Fixed the auto memory detection code.
-*                               The memory test at address 0xC8000.
-* Mar 09, 2000  Nenad Corbic   Added Gideon's Bug Fix: clear pci
-*                               interrupt flags on initial load.
-* Jun 02, 1999  Gideon Hack     Added support for the S514 adapter.
-*                              Updates for Linux 2.2.X kernels.        
-* Sep 17, 1998 Jaspreet Singh  Updates for linux 2.2.X kernels
-* Dec 20, 1996 Gene Kozin      Version 3.0.0. Complete overhaul.
-* Jul 12, 1996 Gene Kozin      Changes for Linux 2.0 compatibility.
-* Jun 12, 1996 Gene Kozin      Added support for S503 card.
-* Apr 30, 1996 Gene Kozin      SDLA hardware interrupt is acknowledged before
-*                              calling protocolspecific ISR.
-*                              Register I/O ports with Linux kernel.
-*                              Miscellaneous bug fixes.
-* Dec 20, 1995 Gene Kozin      Fixed a bug in interrupt routine.
-* Oct 14, 1995 Gene Kozin      Initial version.
-*****************************************************************************/
-
-/*****************************************************************************
- * Notes:
- * ------
- * 1. This code is ment to be system-independent (as much as possible).  To
- *    achive this, various macros are used to hide system-specific interfaces.
- *    To compile this code, one of the following constants must be defined:
- *
- *     Platform        Define
- *     --------        ------
- *     Linux           _LINUX_
- *     SCO Unix        _SCO_UNIX_
- *
- * 2. Supported adapter types:
- *
- *     S502A
- *     ES502A (S502E)
- *     S503
- *     S507
- *     S508 (S509)
- *
- * 3. S502A Notes:
- *
- *     There is no separate DPM window enable/disable control in S502A.  It
- *     opens immediately after a window number it written to the HMCR
- *     register.  To close the window, HMCR has to be written a value
- *     ????1111b (e.g. 0x0F or 0xFF).
- *
- *     S502A DPM window cannot be located at offset E000 (e.g. 0xAE000).
- *
- *     There should be a delay of ??? before reading back S502A status
- *     register.
- *
- * 4. S502E Notes:
- *
- *     S502E has a h/w bug: although default IRQ line state is HIGH, enabling
- *     interrupts by setting bit 1 of the control register (BASE) to '1'
- *     causes it to go LOW! Therefore, disabling interrupts by setting that
- *     bit to '0' causes low-to-high transition on IRQ line (ghosty
- *     interrupt). The same occurs when disabling CPU by resetting bit 0 of
- *     CPU control register (BASE+3) - see the next note.
- *
- *     S502E CPU and DPM control is limited:
- *
- *     o CPU cannot be stopped independently. Resetting bit 0 of the CPUi
- *       control register (BASE+3) shuts the board down entirely, including
- *       DPM;
- *
- *     o DPM access cannot be controlled dynamically. Ones CPU is started,
- *       bit 1 of the control register (BASE) is used to enable/disable IRQ,
- *       so that access to shared memory cannot be disabled while CPU is
- *       running.
- ****************************************************************************/
-
-#define        _LINUX_
-
-#if    defined(_LINUX_)        /****** Linux *******************************/
-
-#include <linux/config.h>
-#include <linux/kernel.h>      /* printk(), and other useful stuff */
-#include <linux/stddef.h>      /* offsetof(), etc. */
-#include <linux/errno.h>       /* return codes */
-#include <linux/string.h>      /* inline memset(), etc. */
-#include <linux/module.h>      /* support for loadable modules */
-#include <linux/jiffies.h>     /* for jiffies, HZ, etc. */
-#include <linux/sdladrv.h>     /* API definitions */
-#include <linux/sdlasfm.h>     /* SDLA firmware module definitions */
-#include <linux/sdlapci.h>     /* SDLA PCI hardware definitions */
-#include <linux/pci.h>         /* PCI defines and function prototypes */
-#include <asm/io.h>            /* for inb(), outb(), etc. */
-
-#define _INB(port)             (inb(port))
-#define _OUTB(port, byte)      (outb((byte),(port)))
-#define        SYSTEM_TICK             jiffies
-
-#include <linux/init.h>
-
-
-#elif  defined(_SCO_UNIX_)     /****** SCO Unix ****************************/
-
-#if    !defined(INKERNEL)
-#error This code MUST be compiled in kernel mode!
-#endif
-#include <sys/sdladrv.h>       /* API definitions */
-#include <sys/sdlasfm.h>       /* SDLA firmware module definitions */
-#include <sys/inline.h>                /* for inb(), outb(), etc. */
-#define _INB(port)             (inb(port))
-#define _OUTB(port, byte)      (outb((port),(byte)))
-#define        SYSTEM_TICK             lbolt
-
-#else
-#error Unknown system type!
-#endif
-
-#define        MOD_VERSION     3
-#define        MOD_RELEASE     0
-
-#define        SDLA_IODELAY    100     /* I/O Rd/Wr delay, 10 works for 486DX2-66 */
-#define        EXEC_DELAY      20      /* shared memory access delay, mks */
-#define        EXEC_TIMEOUT    (HZ*2)  /* command timeout, in ticks */
-
-/* I/O port address range */
-#define S502A_IORANGE  3
-#define S502E_IORANGE  4
-#define S503_IORANGE   3
-#define S507_IORANGE   4
-#define S508_IORANGE   4
-
-/* Maximum amount of memory */
-#define S502_MAXMEM    0x10000L
-#define S503_MAXMEM    0x10000L
-#define S507_MAXMEM    0x40000L
-#define S508_MAXMEM    0x40000L
-
-/* Minimum amount of memory */
-#define S502_MINMEM    0x8000L
-#define S503_MINMEM    0x8000L
-#define S507_MINMEM    0x20000L
-#define S508_MINMEM    0x20000L
-#define NO_PORT         -1
-
-
-
-
-
-/****** Function Prototypes *************************************************/
-
-/* Hardware-specific functions */
-static int sdla_detect (sdlahw_t* hw);
-static int sdla_autodpm        (sdlahw_t* hw);
-static int sdla_setdpm (sdlahw_t* hw);
-static int sdla_load   (sdlahw_t* hw, sfm_t* sfm, unsigned len);
-static int sdla_init   (sdlahw_t* hw);
-static unsigned long sdla_memtest (sdlahw_t* hw);
-static int sdla_bootcfg        (sdlahw_t* hw, sfm_info_t* sfminfo);
-static unsigned char make_config_byte (sdlahw_t* hw);
-static int sdla_start  (sdlahw_t* hw, unsigned addr);
-
-static int init_s502a  (sdlahw_t* hw);
-static int init_s502e  (sdlahw_t* hw);
-static int init_s503   (sdlahw_t* hw);
-static int init_s507   (sdlahw_t* hw);
-static int init_s508   (sdlahw_t* hw);
-            
-static int detect_s502a        (int port);
-static int detect_s502e        (int port);
-static int detect_s503 (int port);
-static int detect_s507 (int port);
-static int detect_s508 (int port);
-static int detect_s514  (sdlahw_t* hw);
-static int find_s514_adapter(sdlahw_t* hw, char find_first_S514_card);
-
-/* Miscellaneous functions */
-static void peek_by_4 (unsigned long src, void* buf, unsigned len);
-static void poke_by_4 (unsigned long dest, void* buf, unsigned len);
-static int calibrate_delay (int mks);
-static int get_option_index (unsigned* optlist, unsigned optval);
-static unsigned check_memregion (void* ptr, unsigned len);
-static unsigned        test_memregion (void* ptr, unsigned len);
-static unsigned short checksum (unsigned char* buf, unsigned len);
-static int init_pci_slot(sdlahw_t *);
-
-static int pci_probe(sdlahw_t *hw);
-
-/****** Global Data **********************************************************
- * Note: All data must be explicitly initialized!!!
- */
-
-static struct pci_device_id sdladrv_pci_tbl[] = {
-       { V3_VENDOR_ID, V3_DEVICE_ID, PCI_ANY_ID, PCI_ANY_ID, },
-       { }                     /* Terminating entry */
-};
-MODULE_DEVICE_TABLE(pci, sdladrv_pci_tbl);
-
-MODULE_LICENSE("GPL");
-
-/* private data */
-static char modname[]  = "sdladrv";
-static char fullname[] = "SDLA Support Module";
-static char copyright[]        = "(c) 1995-1999 Sangoma Technologies Inc.";
-static unsigned        exec_idle;
-
-/* Hardware configuration options.
- * These are arrays of configuration options used by verification routines.
- * The first element of each array is its size (i.e. number of options).
- */
-static unsigned        s502_port_options[] =
-       { 4, 0x250, 0x300, 0x350, 0x360 }
-;
-static unsigned        s503_port_options[] =
-       { 8, 0x250, 0x254, 0x300, 0x304, 0x350, 0x354, 0x360, 0x364 }
-;
-static unsigned        s508_port_options[] =
-       { 8, 0x250, 0x270, 0x280, 0x300, 0x350, 0x360, 0x380, 0x390 }
-;
-
-static unsigned s502a_irq_options[] = { 0 };
-static unsigned s502e_irq_options[] = { 4, 2, 3, 5, 7 };
-static unsigned s503_irq_options[]  = { 5, 2, 3, 4, 5, 7 };
-static unsigned s508_irq_options[]  = { 8, 3, 4, 5, 7, 10, 11, 12, 15 };
-
-static unsigned s502a_dpmbase_options[] =
-{
-       28,
-       0xA0000, 0xA2000, 0xA4000, 0xA6000, 0xA8000, 0xAA000, 0xAC000,
-       0xC0000, 0xC2000, 0xC4000, 0xC6000, 0xC8000, 0xCA000, 0xCC000,
-       0xD0000, 0xD2000, 0xD4000, 0xD6000, 0xD8000, 0xDA000, 0xDC000,
-       0xE0000, 0xE2000, 0xE4000, 0xE6000, 0xE8000, 0xEA000, 0xEC000,
-};
-static unsigned s507_dpmbase_options[] =
-{
-       32,
-       0xA0000, 0xA2000, 0xA4000, 0xA6000, 0xA8000, 0xAA000, 0xAC000, 0xAE000,
-       0xB0000, 0xB2000, 0xB4000, 0xB6000, 0xB8000, 0xBA000, 0xBC000, 0xBE000,
-       0xC0000, 0xC2000, 0xC4000, 0xC6000, 0xC8000, 0xCA000, 0xCC000, 0xCE000,
-       0xE0000, 0xE2000, 0xE4000, 0xE6000, 0xE8000, 0xEA000, 0xEC000, 0xEE000,
-};
-static unsigned s508_dpmbase_options[] =       /* incl. S502E and S503 */
-{
-       32,
-       0xA0000, 0xA2000, 0xA4000, 0xA6000, 0xA8000, 0xAA000, 0xAC000, 0xAE000,
-       0xC0000, 0xC2000, 0xC4000, 0xC6000, 0xC8000, 0xCA000, 0xCC000, 0xCE000,
-       0xD0000, 0xD2000, 0xD4000, 0xD6000, 0xD8000, 0xDA000, 0xDC000, 0xDE000,
-       0xE0000, 0xE2000, 0xE4000, 0xE6000, 0xE8000, 0xEA000, 0xEC000, 0xEE000,
-};
-
-/*
-static unsigned        s502_dpmsize_options[] = { 2, 0x2000, 0x10000 };
-static unsigned        s507_dpmsize_options[] = { 2, 0x2000, 0x4000 };
-static unsigned        s508_dpmsize_options[] = { 1, 0x2000 };
-*/
-
-static unsigned        s502a_pclk_options[] = { 2, 3600, 7200 };
-static unsigned        s502e_pclk_options[] = { 5, 3600, 5000, 7200, 8000, 10000 };
-static unsigned        s503_pclk_options[]  = { 3, 7200, 8000, 10000 };
-static unsigned        s507_pclk_options[]  = { 1, 12288 };
-static unsigned        s508_pclk_options[]  = { 1, 16000 };
-
-/* Host memory control register masks */
-static unsigned char s502a_hmcr[] =
-{
-       0x10, 0x12, 0x14, 0x16, 0x18, 0x1A, 0x1C,       /* A0000 - AC000 */
-       0x20, 0x22, 0x24, 0x26, 0x28, 0x2A, 0x2C,       /* C0000 - CC000 */
-       0x00, 0x02, 0x04, 0x06, 0x08, 0x0A, 0x0C,       /* D0000 - DC000 */
-       0x30, 0x32, 0x34, 0x36, 0x38, 0x3A, 0x3C,       /* E0000 - EC000 */
-};
-static unsigned char s502e_hmcr[] =
-{
-       0x10, 0x12, 0x14, 0x16, 0x18, 0x1A, 0x1C, 0x1E, /* A0000 - AE000 */
-       0x20, 0x22, 0x24, 0x26, 0x28, 0x2A, 0x2C, 0x2E, /* C0000 - CE000 */
-       0x00, 0x02, 0x04, 0x06, 0x08, 0x0A, 0x0C, 0x0E, /* D0000 - DE000 */
-       0x30, 0x32, 0x34, 0x36, 0x38, 0x3A, 0x3C, 0x3E, /* E0000 - EE000 */
-};
-static unsigned char s507_hmcr[] =
-{
-       0x00, 0x02, 0x04, 0x06, 0x08, 0x0A, 0x0C, 0x0E, /* A0000 - AE000 */
-       0x40, 0x42, 0x44, 0x46, 0x48, 0x4A, 0x4C, 0x4E, /* B0000 - BE000 */
-       0x80, 0x82, 0x84, 0x86, 0x88, 0x8A, 0x8C, 0x8E, /* C0000 - CE000 */
-       0xC0, 0xC2, 0xC4, 0xC6, 0xC8, 0xCA, 0xCC, 0xCE, /* E0000 - EE000 */
-};
-static unsigned char s508_hmcr[] =
-{
-       0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, /* A0000 - AE000 */
-       0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, /* C0000 - CE000 */
-       0x08, 0x09, 0x0A, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F, /* D0000 - DE000 */
-       0x18, 0x19, 0x1A, 0x1B, 0x1C, 0x1D, 0x1E, 0x1F, /* E0000 - EE000 */
-};
-
-static unsigned char s507_irqmask[] =
-{
-       0x00, 0x20, 0x40, 0x60, 0x80, 0xA0, 0xC0, 0xE0
-};
-
-static int pci_slot_ar[MAX_S514_CARDS];
-
-/******* Kernel Loadable Module Entry Points ********************************/
-
-/*============================================================================
- * Module 'insert' entry point.
- * o print announcement
- * o initialize static data
- * o calibrate SDLA shared memory access delay.
- *
- * Return:     0       Ok
- *             < 0     error.
- * Context:    process
- */
-
-static int __init sdladrv_init(void)
-{
-       int i=0;
-
-       printk(KERN_INFO "%s v%u.%u %s\n",
-               fullname, MOD_VERSION, MOD_RELEASE, copyright);
-       exec_idle = calibrate_delay(EXEC_DELAY);
-#ifdef WANDEBUG        
-       printk(KERN_DEBUG "%s: exec_idle = %d\n", modname, exec_idle);
-#endif 
-
-       /* Initialize the PCI Card array, which
-         * will store flags, used to mark 
-         * card initialization state */
-       for (i=0; i<MAX_S514_CARDS; i++)
-               pci_slot_ar[i] = 0xFF;
-
-       return 0;
-}
-
-/*============================================================================
- * Module 'remove' entry point.
- * o release all remaining system resources
- */
-static void __exit sdladrv_cleanup(void)
-{
-}
-
-module_init(sdladrv_init);
-module_exit(sdladrv_cleanup);
-
-/******* Kernel APIs ********************************************************/
-
-/*============================================================================
- * Set up adapter.
- * o detect adapter type
- * o verify hardware configuration options
- * o check for hardware conflicts
- * o set up adapter shared memory
- * o test adapter memory
- * o load firmware
- * Return:     0       ok.
- *             < 0     error
- */
-
-EXPORT_SYMBOL(sdla_setup);
-
-int sdla_setup (sdlahw_t* hw, void* sfm, unsigned len)
-{
-       unsigned* irq_opt       = NULL; /* IRQ options */
-       unsigned* dpmbase_opt   = NULL; /* DPM window base options */
-       unsigned* pclk_opt      = NULL; /* CPU clock rate options */
-       int err=0;
-
-       if (sdla_detect(hw)) {
-                if(hw->type != SDLA_S514)
-                        printk(KERN_INFO "%s: no SDLA card found at port 0x%X\n",
-                        modname, hw->port);
-               return -EINVAL;
-       }
-
-       if(hw->type != SDLA_S514) {
-                printk(KERN_INFO "%s: found S%04u card at port 0x%X.\n",
-                modname, hw->type, hw->port);
-
-                hw->dpmsize = SDLA_WINDOWSIZE;
-                switch (hw->type) {
-                case SDLA_S502A:
-                        hw->io_range    = S502A_IORANGE;
-                        irq_opt         = s502a_irq_options;
-                        dpmbase_opt     = s502a_dpmbase_options;
-                        pclk_opt        = s502a_pclk_options;
-                        break;
-
-                case SDLA_S502E:
-                        hw->io_range    = S502E_IORANGE;
-                        irq_opt         = s502e_irq_options;
-                        dpmbase_opt     = s508_dpmbase_options;
-                        pclk_opt        = s502e_pclk_options;
-                        break;
-
-                case SDLA_S503:
-                        hw->io_range    = S503_IORANGE;
-                        irq_opt         = s503_irq_options;
-                        dpmbase_opt     = s508_dpmbase_options;
-                        pclk_opt        = s503_pclk_options;
-                        break;
-
-                case SDLA_S507:
-                        hw->io_range    = S507_IORANGE;
-                        irq_opt         = s508_irq_options;
-                        dpmbase_opt     = s507_dpmbase_options;
-                        pclk_opt        = s507_pclk_options;
-                        break;
-
-                case SDLA_S508:
-                        hw->io_range    = S508_IORANGE;
-                        irq_opt         = s508_irq_options;
-                        dpmbase_opt     = s508_dpmbase_options;
-                        pclk_opt        = s508_pclk_options;
-                        break;
-                }
-
-                /* Verify IRQ configuration options */
-                if (!get_option_index(irq_opt, hw->irq)) {
-                        printk(KERN_INFO "%s: IRQ %d is invalid!\n",
-                               modname, hw->irq);
-                      return -EINVAL;
-                } 
-
-                /* Verify CPU clock rate configuration options */
-                if (hw->pclk == 0)
-                        hw->pclk = pclk_opt[1];  /* use default */
-        
-                else if (!get_option_index(pclk_opt, hw->pclk)) {
-                        printk(KERN_INFO "%s: CPU clock %u is invalid!\n",
-                               modname, hw->pclk);
-                        return -EINVAL;
-                } 
-                printk(KERN_INFO "%s: assuming CPU clock rate of %u kHz.\n",
-                       modname, hw->pclk);
-
-                /* Setup adapter dual-port memory window and test memory */
-                if (hw->dpmbase == 0) {
-                        err = sdla_autodpm(hw);
-                        if (err) {
-                                printk(KERN_INFO
-                               "%s: can't find available memory region!\n",
-                                       modname);
-                                return err;
-                        }
-                }
-                else if (!get_option_index(dpmbase_opt,
-                       virt_to_phys(hw->dpmbase))) {
-                        printk(KERN_INFO
-                               "%s: memory address 0x%lX is invalid!\n",
-                               modname, virt_to_phys(hw->dpmbase));
-                        return -EINVAL;
-                }               
-                else if (sdla_setdpm(hw)) {
-                        printk(KERN_INFO
-                       "%s: 8K memory region at 0x%lX is not available!\n",
-                               modname, virt_to_phys(hw->dpmbase));
-                        return -EINVAL;
-                } 
-                printk(KERN_INFO
-                       "%s: dual-port memory window is set at 0x%lX.\n",
-                               modname, virt_to_phys(hw->dpmbase));
-
-
-               /* If we find memory in 0xE**** Memory region, 
-                 * warn the user to disable the SHADOW RAM.  
-                 * Since memory corruption can occur if SHADOW is
-                 * enabled. This can causes random crashes ! */
-               if (virt_to_phys(hw->dpmbase) >= 0xE0000){
-                       printk(KERN_WARNING "\n%s: !!!!!!!!  WARNING !!!!!!!!\n",modname);
-                       printk(KERN_WARNING "%s: WANPIPE is using 0x%lX memory region !!!\n",
-                                               modname, virt_to_phys(hw->dpmbase));
-                       printk(KERN_WARNING "         Please disable the SHADOW RAM, otherwise\n");
-                       printk(KERN_WARNING "         your system might crash randomly from time to time !\n");
-                       printk(KERN_WARNING "%s: !!!!!!!!  WARNING !!!!!!!!\n\n",modname);
-               }
-        }
-
-       else {
-               hw->memory = test_memregion((void*)hw->dpmbase, 
-                       MAX_SIZEOF_S514_MEMORY);
-               if(hw->memory < (256 * 1024)) {
-                       printk(KERN_INFO
-                               "%s: error in testing S514 memory (0x%lX)\n",
-                               modname, hw->memory);
-                       sdla_down(hw);
-                       return -EINVAL;
-               }
-       }
-    
-       printk(KERN_INFO "%s: found %luK bytes of on-board memory\n",
-               modname, hw->memory / 1024);
-
-       /* Load firmware. If loader fails then shut down adapter */
-       err = sdla_load(hw, sfm, len);
-       if (err) sdla_down(hw);         /* shutdown adapter */
-
-       return err;
-} 
-
-/*============================================================================
- * Shut down SDLA: disable shared memory access and interrupts, stop CPU, etc.
- */
-
-EXPORT_SYMBOL(sdla_down);
-
-int sdla_down (sdlahw_t* hw)
-{
-       unsigned port = hw->port;
-       int i;
-        unsigned char CPU_no;
-        u32 int_config, int_status;
-
-        if(!port && (hw->type != SDLA_S514))
-                return -EFAULT;
-
-       switch (hw->type) {
-       case SDLA_S502A:
-               _OUTB(port, 0x08);              /* halt CPU */
-               _OUTB(port, 0x08);
-               _OUTB(port, 0x08);
-               hw->regs[0] = 0x08;
-               _OUTB(port + 1, 0xFF);          /* close memory window */
-               hw->regs[1] = 0xFF;
-               break;
-
-       case SDLA_S502E:
-               _OUTB(port + 3, 0);             /* stop CPU */
-               _OUTB(port, 0);                 /* reset board */
-               for (i = 0; i < S502E_IORANGE; ++i)
-                       hw->regs[i] = 0
-               ;
-               break;
-
-       case SDLA_S503:
-       case SDLA_S507:
-       case SDLA_S508:
-               _OUTB(port, 0);                 /* reset board logic */
-               hw->regs[0] = 0;
-               break;
-
-       case SDLA_S514:
-               /* halt the adapter */
-                *(char *)hw->vector = S514_CPU_HALT;
-               CPU_no = hw->S514_cpu_no[0];
-
-               /* disable the PCI IRQ and disable memory access */
-                pci_read_config_dword(hw->pci_dev, PCI_INT_CONFIG, &int_config);
-               int_config &= (CPU_no == S514_CPU_A) ? ~PCI_DISABLE_IRQ_CPU_A : ~PCI_DISABLE_IRQ_CPU_B;
-                pci_write_config_dword(hw->pci_dev, PCI_INT_CONFIG, int_config);
-               read_S514_int_stat(hw, &int_status);
-               S514_intack(hw, int_status);
-               if(CPU_no == S514_CPU_A)
-                        pci_write_config_dword(hw->pci_dev, PCI_MAP0_DWORD,
-                               PCI_CPU_A_MEM_DISABLE);
-               else
-                        pci_write_config_dword(hw->pci_dev, PCI_MAP1_DWORD,
-                               PCI_CPU_B_MEM_DISABLE);
-
-               /* free up the allocated virtual memory */
-               iounmap((void *)hw->dpmbase);
-               iounmap((void *)hw->vector);
-               break;
-
-
-       default:
-               return -EINVAL;
-       }
-       return 0;
-}
-
-/*============================================================================
- * Map shared memory window into SDLA address space.
- */
-
-EXPORT_SYMBOL(sdla_mapmem);
-
-int sdla_mapmem (sdlahw_t* hw, unsigned long addr)
-{
-       unsigned port = hw->port;
-       register int tmp;
-
-       switch (hw->type) {
-       case SDLA_S502A:
-       case SDLA_S502E:
-               if (addr < S502_MAXMEM) { /* verify parameter */
-                       tmp = addr >> 13;       /* convert to register mask */
-                       _OUTB(port + 2, tmp);
-                       hw->regs[2] = tmp;
-               }
-               else return -EINVAL;
-               break;
-
-       case SDLA_S503:
-               if (addr < S503_MAXMEM) { /* verify parameter */
-                       tmp = (hw->regs[0] & 0x8F) | ((addr >> 9) & 0x70);
-                       _OUTB(port, tmp);
-                       hw->regs[0] = tmp;
-               }
-               else return -EINVAL;
-               break;
-
-       case SDLA_S507:
-               if (addr < S507_MAXMEM) {
-                       if (!(_INB(port) & 0x02))
-                               return -EIO;
-                       tmp = addr >> 13;       /* convert to register mask */
-                       _OUTB(port + 2, tmp);
-                       hw->regs[2] = tmp;
-               }
-               else return -EINVAL;
-               break;
-
-       case SDLA_S508:
-               if (addr < S508_MAXMEM) {
-                       tmp = addr >> 13;       /* convert to register mask */
-                       _OUTB(port + 2, tmp);
-                       hw->regs[2] = tmp;
-               }
-               else return -EINVAL;
-               break;
-
-       case SDLA_S514:
-               return 0;
-
-       default:
-               return -EINVAL;
-       }
-       hw->vector = addr & 0xFFFFE000L;
-       return 0;
-}
-
-/*============================================================================
- * Enable interrupt generation.
- */
-
-static int sdla_inten (sdlahw_t* hw)
-{
-       unsigned port = hw->port;
-       int tmp, i;
-
-       switch (hw->type) {
-       case SDLA_S502E:
-               /* Note thar interrupt control operations on S502E are allowed
-                * only if CPU is enabled (bit 0 of status register is set).
-                */
-               if (_INB(port) & 0x01) {
-                       _OUTB(port, 0x02);      /* bit1 = 1, bit2 = 0 */
-                       _OUTB(port, 0x06);      /* bit1 = 1, bit2 = 1 */
-                       hw->regs[0] = 0x06;
-               }
-               else return -EIO;
-               break;
-
-       case SDLA_S503:
-               tmp = hw->regs[0] | 0x04;
-               _OUTB(port, tmp);
-               hw->regs[0] = tmp;              /* update mirror */
-               for (i = 0; i < SDLA_IODELAY; ++i);     /* delay */
-               if (!(_INB(port) & 0x02))               /* verify */
-                       return -EIO;
-               break;
-
-       case SDLA_S508:
-               tmp = hw->regs[0] | 0x10;
-               _OUTB(port, tmp);
-               hw->regs[0] = tmp;              /* update mirror */
-               for (i = 0; i < SDLA_IODELAY; ++i);     /* delay */
-               if (!(_INB(port + 1) & 0x10))           /* verify */
-                       return -EIO;
-               break;
-
-       case SDLA_S502A:
-       case SDLA_S507:
-               break;
-
-        case SDLA_S514:
-                break;
-
-       default:
-               return -EINVAL;
-
-       }
-       return 0;
-}
-
-/*============================================================================
- * Disable interrupt generation.
- */
-
-#if 0
-int sdla_intde (sdlahw_t* hw)
-{
-       unsigned port = hw->port;
-       int tmp, i;
-
-       switch (hw->type) {
-       case SDLA_S502E:
-               /* Notes:
-                *  1) interrupt control operations are allowed only if CPU is
-                *     enabled (bit 0 of status register is set).
-                *  2) disabling interrupts using bit 1 of control register
-                *     causes IRQ line go high, therefore we are going to use
-                *     0x04 instead: lower it to inhibit interrupts to PC.
-                */
-               if (_INB(port) & 0x01) {
-                       _OUTB(port, hw->regs[0] & ~0x04);
-                       hw->regs[0] &= ~0x04;
-               }
-               else return -EIO;
-               break;
-
-       case SDLA_S503:
-               tmp = hw->regs[0] & ~0x04;
-               _OUTB(port, tmp);
-               hw->regs[0] = tmp;                      /* update mirror */
-               for (i = 0; i < SDLA_IODELAY; ++i);     /* delay */
-               if (_INB(port) & 0x02)                  /* verify */
-                       return -EIO;
-               break;
-
-       case SDLA_S508:
-               tmp = hw->regs[0] & ~0x10;
-               _OUTB(port, tmp);
-               hw->regs[0] = tmp;                      /* update mirror */
-               for (i = 0; i < SDLA_IODELAY; ++i);     /* delay */
-               if (_INB(port) & 0x10)                  /* verify */
-                       return -EIO;
-               break;
-
-       case SDLA_S502A:
-       case SDLA_S507:
-               break;
-
-       default:
-               return -EINVAL;
-       }
-       return 0;
-}
-#endif  /*  0  */
-
-/*============================================================================
- * Acknowledge SDLA hardware interrupt.
- */
-
-static int sdla_intack (sdlahw_t* hw)
-{
-       unsigned port = hw->port;
-       int tmp;
-
-       switch (hw->type) {
-       case SDLA_S502E:
-               /* To acknoledge hardware interrupt we have to toggle bit 3 of
-                * control register: \_/
-                * Note that interrupt control operations on S502E are allowed
-                * only if CPU is enabled (bit 1 of status register is set).
-                */
-               if (_INB(port) & 0x01) {
-                       tmp = hw->regs[0] & ~0x04;
-                       _OUTB(port, tmp);
-                       tmp |= 0x04;
-                       _OUTB(port, tmp);
-                       hw->regs[0] = tmp;
-               }
-               else return -EIO;
-               break;
-
-       case SDLA_S503:
-               if (_INB(port) & 0x04) {
-                       tmp = hw->regs[0] & ~0x08;
-                       _OUTB(port, tmp);
-                       tmp |= 0x08;
-                       _OUTB(port, tmp);
-                       hw->regs[0] = tmp;
-               }
-               break;
-
-       case SDLA_S502A:
-       case SDLA_S507:
-       case SDLA_S508:
-       break;
-
-       default:
-               return -EINVAL;
-       }
-       return 0;
-}
-
-
-/*============================================================================
- * Acknowledge S514 hardware interrupt.
- */
-
-EXPORT_SYMBOL(S514_intack);
-
-void S514_intack (sdlahw_t* hw, u32 int_status)
-{
-        pci_write_config_dword(hw->pci_dev, PCI_INT_STATUS, int_status);
-}
-
-
-/*============================================================================
- * Read the S514 hardware interrupt status.
- */
-
-EXPORT_SYMBOL(read_S514_int_stat);
-
-void read_S514_int_stat (sdlahw_t* hw, u32* int_status)
-{
-       pci_read_config_dword(hw->pci_dev, PCI_INT_STATUS, int_status);
-}
-
-
-/*============================================================================
- * Generate an interrupt to adapter's CPU.
- */
-
-#if 0
-int sdla_intr (sdlahw_t* hw)
-{
-       unsigned port = hw->port;
-
-       switch (hw->type) {
-       case SDLA_S502A:
-               if (!(_INB(port) & 0x40)) {
-                       _OUTB(port, 0x10);              /* issue NMI to CPU */
-                       hw->regs[0] = 0x10;
-               }
-               else return -EIO;
-               break;
-
-       case SDLA_S507:
-               if ((_INB(port) & 0x06) == 0x06) {
-                       _OUTB(port + 3, 0);
-               }
-               else return -EIO;
-               break;
-
-       case SDLA_S508:
-               if (_INB(port + 1) & 0x02) {
-                       _OUTB(port, 0x08);
-               }
-               else return -EIO;
-               break;
-
-       case SDLA_S502E:
-       case SDLA_S503:
-       default:
-               return -EINVAL;
-       }
-       return 0;
-}
-#endif  /*  0  */
-
-/*============================================================================
- * Execute Adapter Command.
- * o Set exec flag.
- * o Busy-wait until flag is reset.
- * o Return number of loops made, or 0 if command timed out.
- */
-
-EXPORT_SYMBOL(sdla_exec);
-
-int sdla_exec (void* opflag)
-{
-       volatile unsigned char* flag = opflag;
-       unsigned long tstop;
-       int nloops;
-
-       if(readb(flag) != 0x00) {
-               printk(KERN_INFO
-                       "WANPIPE: opp flag set on entry to sdla_exec\n");
-               return 0;
-       }
-       
-       writeb(0x01, flag);
-
-       tstop = SYSTEM_TICK + EXEC_TIMEOUT;
-
-       for (nloops = 1; (readb(flag) == 0x01); ++ nloops) {
-               unsigned delay = exec_idle;
-               while (-- delay);                       /* delay */
-               if (SYSTEM_TICK > tstop) return 0;      /* time is up! */
-       }
-       return nloops;
-}
-
-/*============================================================================
- * Read absolute adapter memory.
- * Transfer data from adapter's memory to data buffer.
- *
- * Note:
- * Care should be taken when crossing dual-port memory window boundary.
- * This function is not atomic, so caller must disable interrupt if
- * interrupt routines are accessing adapter shared memory.
- */
-
-EXPORT_SYMBOL(sdla_peek);
-
-int sdla_peek (sdlahw_t* hw, unsigned long addr, void* buf, unsigned len)
-{
-
-       if (addr + len > hw->memory)    /* verify arguments */
-               return -EINVAL;
-
-        if(hw->type == SDLA_S514) {    /* copy data for the S514 adapter */
-                peek_by_4 ((unsigned long)hw->dpmbase + addr, buf, len);
-                return 0;
-       }
-
-        else {                         /* copy data for the S508 adapter */
-               unsigned long oldvec = hw->vector;
-               unsigned winsize = hw->dpmsize;
-               unsigned curpos, curlen;   /* current offset and block size */
-               unsigned long curvec;      /* current DPM window vector */
-               int err = 0;
-
-                while (len && !err) {
-                        curpos = addr % winsize;  /* current window offset */
-                        curvec = addr - curpos;   /* current window vector */
-                        curlen = (len > (winsize - curpos)) ?
-                               (winsize - curpos) : len;
-                        /* Relocate window and copy block of data */
-                        err = sdla_mapmem(hw, curvec);
-                        peek_by_4 ((unsigned long)hw->dpmbase + curpos, buf,
-                               curlen);
-                        addr       += curlen;
-                        buf         = (char*)buf + curlen;
-                        len        -= curlen;
-                }
-
-                /* Restore DPM window position */
-                sdla_mapmem(hw, oldvec);
-                return err;
-        }
-}
-
-
-/*============================================================================
- * Read data from adapter's memory to a data buffer in 4-byte chunks.
- * Note that we ensure that the SDLA memory address is on a 4-byte boundary
- * before we begin moving the data in 4-byte chunks.
-*/
-
-static void peek_by_4 (unsigned long src, void* buf, unsigned len)
-{
-
-        /* byte copy data until we get to a 4-byte boundary */
-        while (len && (src & 0x03)) {
-                *(char *)buf ++ = readb(src ++);
-                len --;
-        }
-
-        /* copy data in 4-byte chunks */
-        while (len >= 4) {
-                *(unsigned long *)buf = readl(src);
-                buf += 4;
-                src += 4;
-                len -= 4;
-        }
-
-        /* byte copy any remaining data */
-        while (len) {
-                *(char *)buf ++ = readb(src ++);
-                len --;
-        }
-}
-
-
-/*============================================================================
- * Write Absolute Adapter Memory.
- * Transfer data from data buffer to adapter's memory.
- *
- * Note:
- * Care should be taken when crossing dual-port memory window boundary.
- * This function is not atomic, so caller must disable interrupt if
- * interrupt routines are accessing adapter shared memory.
- */
-
-EXPORT_SYMBOL(sdla_poke);
-int sdla_poke (sdlahw_t* hw, unsigned long addr, void* buf, unsigned len)
-{
-
-       if (addr + len > hw->memory)    /* verify arguments */
-               return -EINVAL;
-   
-        if(hw->type == SDLA_S514) {    /* copy data for the S514 adapter */
-                poke_by_4 ((unsigned long)hw->dpmbase + addr, buf, len);
-                return 0;
-       }
-       
-       else {                          /* copy data for the S508 adapter */
-               unsigned long oldvec = hw->vector;
-               unsigned winsize = hw->dpmsize;
-               unsigned curpos, curlen;     /* current offset and block size */
-               unsigned long curvec;        /* current DPM window vector */
-               int err = 0;
-
-               while (len && !err) {
-                        curpos = addr % winsize;    /* current window offset */
-                        curvec = addr - curpos;     /* current window vector */
-                        curlen = (len > (winsize - curpos)) ?
-                               (winsize - curpos) : len;
-                        /* Relocate window and copy block of data */
-                        sdla_mapmem(hw, curvec);
-                        poke_by_4 ((unsigned long)hw->dpmbase + curpos, buf,
-                               curlen);
-                       addr       += curlen;
-                        buf         = (char*)buf + curlen;
-                        len        -= curlen;
-                }
-
-                /* Restore DPM window position */
-                sdla_mapmem(hw, oldvec);
-                return err;
-        }
-}
-
-
-/*============================================================================
- * Write from a data buffer to adapter's memory in 4-byte chunks.
- * Note that we ensure that the SDLA memory address is on a 4-byte boundary
- * before we begin moving the data in 4-byte chunks.
-*/
-
-static void poke_by_4 (unsigned long dest, void* buf, unsigned len)
-{
-
-        /* byte copy data until we get to a 4-byte boundary */
-        while (len && (dest & 0x03)) {
-                writeb (*(char *)buf ++, dest ++);
-                len --;
-        }
-
-        /* copy data in 4-byte chunks */
-        while (len >= 4) {
-                writel (*(unsigned long *)buf, dest);
-                dest += 4;
-                buf += 4;
-                len -= 4;
-        }
-
-        /* byte copy any remaining data */
-        while (len) {
-                writeb (*(char *)buf ++ , dest ++);
-                len --;
-        }
-}
-
-
-#ifdef DONT_COMPIPLE_THIS
-#endif /* DONT_COMPIPLE_THIS */
-
-/****** Hardware-Specific Functions *****************************************/
-
-/*============================================================================
- * Detect adapter type.
- * o if adapter type is specified then call detection routine for that adapter
- *   type.  Otherwise call detection routines for every adapter types until
- *   adapter is detected.
- *
- * Notes:
- * 1) Detection tests are destructive! Adapter will be left in shutdown state
- *    after the test.
- */
-static int sdla_detect (sdlahw_t* hw)
-{
-       unsigned port = hw->port;
-       int err = 0;
-
-       if (!port && (hw->type != SDLA_S514))
-               return -EFAULT;
-
-       switch (hw->type) {
-       case SDLA_S502A:
-               if (!detect_s502a(port)) err = -ENODEV;
-               break;
-
-       case SDLA_S502E:
-               if (!detect_s502e(port)) err = -ENODEV;
-               break;
-
-       case SDLA_S503:
-               if (!detect_s503(port)) err = -ENODEV;
-               break;
-
-       case SDLA_S507:
-               if (!detect_s507(port)) err = -ENODEV;
-               break;
-
-       case SDLA_S508:
-               if (!detect_s508(port)) err = -ENODEV;
-               break;
-
-       case SDLA_S514:
-                if (!detect_s514(hw)) err = -ENODEV;
-               break;
-
-       default:
-               if (detect_s502a(port))
-                       hw->type = SDLA_S502A;
-               else if (detect_s502e(port))
-                       hw->type = SDLA_S502E;
-               else if (detect_s503(port))
-                       hw->type = SDLA_S503;
-               else if (detect_s507(port))
-                       hw->type = SDLA_S507;
-               else if (detect_s508(port))
-                       hw->type = SDLA_S508;
-               else err = -ENODEV;
-       }
-       return err;
-}
-
-/*============================================================================
- * Autoselect memory region. 
- * o try all available DMP address options from the top down until success.
- */
-static int sdla_autodpm (sdlahw_t* hw)
-{
-       int i, err = -EINVAL;
-       unsigned* opt;
-
-       switch (hw->type) {
-       case SDLA_S502A:
-               opt = s502a_dpmbase_options;
-               break;
-
-       case SDLA_S502E:
-       case SDLA_S503:
-       case SDLA_S508:
-               opt = s508_dpmbase_options;
-               break;
-
-       case SDLA_S507:
-               opt = s507_dpmbase_options;
-               break;
-
-       default:
-               return -EINVAL;
-       }
-
-       /* Start testing from 8th position, address
-         * 0xC8000 from the 508 address table. 
-         * We don't want to test A**** addresses, since
-         * they are usually used for Video */
-       for (i = 8; i <= opt[0] && err; i++) {
-               hw->dpmbase = phys_to_virt(opt[i]);
-               err = sdla_setdpm(hw);
-       }
-       return err;
-}
-
-/*============================================================================
- * Set up adapter dual-port memory window. 
- * o shut down adapter
- * o make sure that no physical memory exists in this region, i.e entire
- *   region reads 0xFF and is not writable when adapter is shut down.
- * o initialize adapter hardware
- * o make sure that region is usable with SDLA card, i.e. we can write to it
- *   when adapter is configured.
- */
-static int sdla_setdpm (sdlahw_t* hw)
-{
-       int err;
-
-       /* Shut down card and verify memory region */
-       sdla_down(hw);
-       if (check_memregion(hw->dpmbase, hw->dpmsize))
-               return -EINVAL;
-
-       /* Initialize adapter and test on-board memory segment by segment.
-        * If memory size appears to be less than shared memory window size,
-        * assume that memory region is unusable.
-        */
-       err = sdla_init(hw);
-       if (err) return err;
-
-       if (sdla_memtest(hw) < hw->dpmsize) {   /* less than window size */
-               sdla_down(hw);
-               return -EIO;
-       }
-       sdla_mapmem(hw, 0L);    /* set window vector at bottom */
-       return 0;
-}
-
-/*============================================================================
- * Load adapter from the memory image of the SDLA firmware module. 
- * o verify firmware integrity and compatibility
- * o start adapter up
- */
-static int sdla_load (sdlahw_t* hw, sfm_t* sfm, unsigned len)
-{
-
-       int i;
-
-       /* Verify firmware signature */
-       if (strcmp(sfm->signature, SFM_SIGNATURE)) {
-               printk(KERN_INFO "%s: not SDLA firmware!\n",
-                       modname);
-               return -EINVAL;
-       }
-
-       /* Verify firmware module format version */
-       if (sfm->version != SFM_VERSION) {
-               printk(KERN_INFO
-                       "%s: firmware format %u rejected! Expecting %u.\n",
-                       modname, sfm->version, SFM_VERSION);
-               return -EINVAL;
-       }
-
-       /* Verify firmware module length and checksum */
-       if ((len - offsetof(sfm_t, image) != sfm->info.codesize) ||
-               (checksum((void*)&sfm->info,
-               sizeof(sfm_info_t) + sfm->info.codesize) != sfm->checksum)) {
-               printk(KERN_INFO "%s: firmware corrupted!\n", modname);
-               return -EINVAL;
-       }
-
-       /* Announce */
-       printk(KERN_INFO "%s: loading %s (ID=%u)...\n", modname,
-               (sfm->descr[0] != '\0') ? sfm->descr : "unknown firmware",
-               sfm->info.codeid);
-
-       if(hw->type == SDLA_S514)
-               printk(KERN_INFO "%s: loading S514 adapter, CPU %c\n",
-                       modname, hw->S514_cpu_no[0]);
-
-       /* Scan through the list of compatible adapters and make sure our
-        * adapter type is listed.
-        */
-       for (i = 0;
-            (i < SFM_MAX_SDLA) && (sfm->info.adapter[i] != hw->type);
-            ++i);
-       
-       if (i == SFM_MAX_SDLA) {
-               printk(KERN_INFO "%s: firmware is not compatible with S%u!\n",
-                       modname, hw->type);
-               return -EINVAL;
-       }
-
-
-       /* Make sure there is enough on-board memory */
-       if (hw->memory < sfm->info.memsize) {
-               printk(KERN_INFO
-                       "%s: firmware needs %lu bytes of on-board memory!\n",
-                       modname, sfm->info.memsize);
-               return -EINVAL;
-       }
-
-       /* Move code onto adapter */
-       if (sdla_poke(hw, sfm->info.codeoffs, sfm->image, sfm->info.codesize)) {
-               printk(KERN_INFO "%s: failed to load code segment!\n",
-                       modname);
-               return -EIO;
-       }
-
-       /* Prepare boot-time configuration data and kick-off CPU */
-       sdla_bootcfg(hw, &sfm->info);
-       if (sdla_start(hw, sfm->info.startoffs)) {
-               printk(KERN_INFO "%s: Damn... Adapter won't start!\n",
-                       modname);
-               return -EIO;
-       }
-
-       /* position DPM window over the mailbox and enable interrupts */
-        if (sdla_mapmem(hw, sfm->info.winoffs) || sdla_inten(hw)) {
-               printk(KERN_INFO "%s: adapter hardware failure!\n",
-                       modname);
-               return -EIO;
-       }
-       hw->fwid = sfm->info.codeid;            /* set firmware ID */
-       return 0;
-}
-
-/*============================================================================
- * Initialize SDLA hardware: setup memory window, IRQ, etc.
- */
-static int sdla_init (sdlahw_t* hw)
-{
-       int i;
-
-       for (i = 0; i < SDLA_MAXIORANGE; ++i)
-               hw->regs[i] = 0;
-
-       switch (hw->type) {
-       case SDLA_S502A: return init_s502a(hw);
-       case SDLA_S502E: return init_s502e(hw);
-       case SDLA_S503:  return init_s503(hw);
-       case SDLA_S507:  return init_s507(hw);
-       case SDLA_S508:  return init_s508(hw);
-       }
-       return -EINVAL;
-}
-
-/*============================================================================
- * Test adapter on-board memory.
- * o slide DPM window from the bottom up and test adapter memory segment by
- *   segment.
- * Return adapter memory size.
- */
-static unsigned long sdla_memtest (sdlahw_t* hw)
-{
-       unsigned long memsize;
-       unsigned winsize;
-
-       for (memsize = 0, winsize = hw->dpmsize;
-            !sdla_mapmem(hw, memsize) &&
-               (test_memregion(hw->dpmbase, winsize) == winsize)
-            ;
-            memsize += winsize)
-       ;
-       hw->memory = memsize;
-       return memsize;
-}
-
-/*============================================================================
- * Prepare boot-time firmware configuration data.
- * o position DPM window
- * o initialize configuration data area
- */
-static int sdla_bootcfg (sdlahw_t* hw, sfm_info_t* sfminfo)
-{
-       unsigned char* data;
-
-       if (!sfminfo->datasize) return 0;       /* nothing to do */
-
-       if (sdla_mapmem(hw, sfminfo->dataoffs) != 0)
-               return -EIO;
-
-       if(hw->type == SDLA_S514)
-                data = (void*)(hw->dpmbase + sfminfo->dataoffs);
-        else
-                data = (void*)((u8 *)hw->dpmbase +
-                        (sfminfo->dataoffs - hw->vector));
-
-       memset_io (data, 0, sfminfo->datasize);
-
-       writeb (make_config_byte(hw), &data[0x00]);
-
-       switch (sfminfo->codeid) {
-       case SFID_X25_502:
-       case SFID_X25_508:
-                writeb (3, &data[0x01]);        /* T1 timer */
-                writeb (10, &data[0x03]);       /* N2 */
-                writeb (7, &data[0x06]);        /* HDLC window size */
-                writeb (1, &data[0x0B]);        /* DTE */
-                writeb (2, &data[0x0C]);        /* X.25 packet window size */
-                writew (128, &data[0x0D]);     /* default X.25 data size */
-                writew (128, &data[0x0F]);     /* maximum X.25 data size */
-               break;
-       }
-       return 0;
-}
-
-/*============================================================================
- * Prepare configuration byte identifying adapter type and CPU clock rate.
- */
-static unsigned char make_config_byte (sdlahw_t* hw)
-{
-       unsigned char byte = 0;
-
-       switch (hw->pclk) {
-               case 5000:  byte = 0x01; break;
-               case 7200:  byte = 0x02; break;
-               case 8000:  byte = 0x03; break;
-               case 10000: byte = 0x04; break;
-               case 16000: byte = 0x05; break;
-       }
-
-       switch (hw->type) {
-               case SDLA_S502E: byte |= 0x80; break;
-               case SDLA_S503:  byte |= 0x40; break;
-       }
-       return byte;
-}
-
-/*============================================================================
- * Start adapter's CPU.
- * o calculate a pointer to adapter's cold boot entry point
- * o position DPM window
- * o place boot instruction (jp addr) at cold boot entry point
- * o start CPU
- */
-static int sdla_start (sdlahw_t* hw, unsigned addr)
-{
-       unsigned port = hw->port;
-       unsigned char *bootp;
-       int err, tmp, i;
-
-       if (!port && (hw->type != SDLA_S514)) return -EFAULT;
-
-       switch (hw->type) {
-       case SDLA_S502A:
-               bootp = hw->dpmbase;
-               bootp += 0x66;
-               break;
-
-       case SDLA_S502E:
-       case SDLA_S503:
-       case SDLA_S507:
-       case SDLA_S508:
-       case SDLA_S514:
-               bootp = hw->dpmbase;
-               break;
-
-       default:
-               return -EINVAL;
-       }
-
-       err = sdla_mapmem(hw, 0);
-       if (err) return err;
-
-       writeb (0xC3, bootp);   /* Z80: 'jp' opcode */
-       bootp ++;
-       writew (addr, bootp);
-
-       switch (hw->type) {
-       case SDLA_S502A:
-               _OUTB(port, 0x10);              /* issue NMI to CPU */
-               hw->regs[0] = 0x10;
-               break;
-
-       case SDLA_S502E:
-               _OUTB(port + 3, 0x01);          /* start CPU */
-               hw->regs[3] = 0x01;
-               for (i = 0; i < SDLA_IODELAY; ++i);
-               if (_INB(port) & 0x01) {        /* verify */
-                       /*
-                        * Enabling CPU changes functionality of the
-                        * control register, so we have to reset its
-                        * mirror.
-                        */
-                       _OUTB(port, 0);         /* disable interrupts */
-                       hw->regs[0] = 0;
-               }
-               else return -EIO;
-               break;
-
-       case SDLA_S503:
-               tmp = hw->regs[0] | 0x09;       /* set bits 0 and 3 */
-               _OUTB(port, tmp);
-               hw->regs[0] = tmp;              /* update mirror */
-               for (i = 0; i < SDLA_IODELAY; ++i);
-               if (!(_INB(port) & 0x01))       /* verify */
-                       return -EIO;
-               break;
-
-       case SDLA_S507:
-               tmp = hw->regs[0] | 0x02;
-               _OUTB(port, tmp);
-               hw->regs[0] = tmp;              /* update mirror */
-               for (i = 0; i < SDLA_IODELAY; ++i);
-               if (!(_INB(port) & 0x04))       /* verify */
-                       return -EIO;
-               break;
-
-       case SDLA_S508:
-               tmp = hw->regs[0] | 0x02;
-               _OUTB(port, tmp);
-               hw->regs[0] = tmp;      /* update mirror */
-               for (i = 0; i < SDLA_IODELAY; ++i);
-               if (!(_INB(port + 1) & 0x02))   /* verify */
-                       return -EIO;
-               break;
-
-       case SDLA_S514:
-               writeb (S514_CPU_START, hw->vector);
-               break;
-
-       default:
-               return -EINVAL;
-       }
-       return 0;
-}
-
-/*============================================================================
- * Initialize S502A adapter.
- */
-static int init_s502a (sdlahw_t* hw)
-{
-       unsigned port = hw->port;
-       int tmp, i;
-
-       if (!detect_s502a(port))
-               return -ENODEV;
-
-       hw->regs[0] = 0x08;
-       hw->regs[1] = 0xFF;
-
-       /* Verify configuration options */
-       i = get_option_index(s502a_dpmbase_options, virt_to_phys(hw->dpmbase));
-       if (i == 0)
-               return -EINVAL;
-
-       tmp = s502a_hmcr[i - 1];
-       switch (hw->dpmsize) {
-       case 0x2000:
-               tmp |= 0x01;
-               break;
-
-       case 0x10000L:
-               break;
-
-       default:
-               return -EINVAL;
-       }
-
-       /* Setup dual-port memory window (this also enables memory access) */
-       _OUTB(port + 1, tmp);
-       hw->regs[1] = tmp;
-       hw->regs[0] = 0x08;
-       return 0;
-}
-
-/*============================================================================
- * Initialize S502E adapter.
- */
-static int init_s502e (sdlahw_t* hw)
-{
-       unsigned port = hw->port;
-       int tmp, i;
-
-       if (!detect_s502e(port))
-               return -ENODEV;
-
-       /* Verify configuration options */
-       i = get_option_index(s508_dpmbase_options, virt_to_phys(hw->dpmbase));
-       if (i == 0)
-               return -EINVAL;
-
-       tmp = s502e_hmcr[i - 1];
-       switch (hw->dpmsize) {
-       case 0x2000:
-               tmp |= 0x01;
-               break;
-
-       case 0x10000L:
-               break;
-
-       default:
-               return -EINVAL;
-       }
-
-       /* Setup dual-port memory window */
-       _OUTB(port + 1, tmp);
-       hw->regs[1] = tmp;
-
-       /* Enable memory access */
-       _OUTB(port, 0x02);
-       hw->regs[0] = 0x02;
-       for (i = 0; i < SDLA_IODELAY; ++i);     /* delay */
-       return (_INB(port) & 0x02) ? 0 : -EIO;
-}
-
-/*============================================================================
- * Initialize S503 adapter.
- * ---------------------------------------------------------------------------
- */
-static int init_s503 (sdlahw_t* hw)
-{
-       unsigned port = hw->port;
-       int tmp, i;
-
-       if (!detect_s503(port))
-               return -ENODEV;
-
-       /* Verify configuration options */
-       i = get_option_index(s508_dpmbase_options, virt_to_phys(hw->dpmbase));
-       if (i == 0)
-               return -EINVAL;
-
-       tmp = s502e_hmcr[i - 1];
-       switch (hw->dpmsize) {
-       case 0x2000:
-               tmp |= 0x01;
-               break;
-
-       case 0x10000L:
-               break;
-
-       default:
-               return -EINVAL;
-       }
-
-       /* Setup dual-port memory window */
-       _OUTB(port + 1, tmp);
-       hw->regs[1] = tmp;
-
-       /* Enable memory access */
-       _OUTB(port, 0x02);
-       hw->regs[0] = 0x02;     /* update mirror */
-       return 0;
-}
-
-/*============================================================================
- * Initialize S507 adapter.
- */
-static int init_s507 (sdlahw_t* hw)
-{
-       unsigned port = hw->port;
-       int tmp, i;
-
-       if (!detect_s507(port))
-               return -ENODEV;
-
-       /* Verify configuration options */
-       i = get_option_index(s507_dpmbase_options, virt_to_phys(hw->dpmbase));
-       if (i == 0)
-               return -EINVAL;
-
-       tmp = s507_hmcr[i - 1];
-       switch (hw->dpmsize) {
-       case 0x2000:
-               tmp |= 0x01;
-               break;
-
-       case 0x10000L:
-               break;
-
-       default:
-               return -EINVAL;
-       }
-
-       /* Enable adapter's logic */
-       _OUTB(port, 0x01);
-       hw->regs[0] = 0x01;
-       for (i = 0; i < SDLA_IODELAY; ++i);     /* delay */
-       if (!(_INB(port) & 0x20))
-               return -EIO;
-
-       /* Setup dual-port memory window */
-       _OUTB(port + 1, tmp);
-       hw->regs[1] = tmp;
-
-       /* Enable memory access */
-       tmp = hw->regs[0] | 0x04;
-       if (hw->irq) {
-               i = get_option_index(s508_irq_options, hw->irq);
-               if (i) tmp |= s507_irqmask[i - 1];
-       }
-       _OUTB(port, tmp);
-       hw->regs[0] = tmp;              /* update mirror */
-       for (i = 0; i < SDLA_IODELAY; ++i);     /* delay */
-       return (_INB(port) & 0x08) ? 0 : -EIO;
-}
-
-/*============================================================================
- * Initialize S508 adapter.
- */
-static int init_s508 (sdlahw_t* hw)
-{
-       unsigned port = hw->port;
-       int tmp, i;
-
-       if (!detect_s508(port))
-               return -ENODEV;
-
-       /* Verify configuration options */
-       i = get_option_index(s508_dpmbase_options, virt_to_phys(hw->dpmbase));
-       if (i == 0)
-               return -EINVAL;
-
-       /* Setup memory configuration */
-       tmp = s508_hmcr[i - 1];
-       _OUTB(port + 1, tmp);
-       hw->regs[1] = tmp;
-
-       /* Enable memory access */
-       _OUTB(port, 0x04);
-       hw->regs[0] = 0x04;             /* update mirror */
-       for (i = 0; i < SDLA_IODELAY; ++i);     /* delay */
-       return (_INB(port + 1) & 0x04) ? 0 : -EIO;
-}
-
-/*============================================================================
- * Detect S502A adapter.
- *     Following tests are used to detect S502A adapter:
- *     1. All registers other than status (BASE) should read 0xFF
- *     2. After writing 00001000b to control register, status register should
- *        read 01000000b.
- *     3. After writing 0 to control register, status register should still
- *        read  01000000b.
- *     4. After writing 00000100b to control register, status register should
- *        read 01000100b.
- *     Return 1 if detected o.k. or 0 if failed.
- *     Note:   This test is destructive! Adapter will be left in shutdown
- *             state after the test.
- */
-static int detect_s502a (int port)
-{
-       int i, j;
-
-       if (!get_option_index(s502_port_options, port))
-               return 0;
-       
-       for (j = 1; j < SDLA_MAXIORANGE; ++j) {
-               if (_INB(port + j) != 0xFF)
-                       return 0;
-               for (i = 0; i < SDLA_IODELAY; ++i);     /* delay */
-       }
-
-       _OUTB(port, 0x08);                      /* halt CPU */
-       _OUTB(port, 0x08);
-       _OUTB(port, 0x08);
-       for (i = 0; i < SDLA_IODELAY; ++i);     /* delay */
-       if (_INB(port) != 0x40)
-               return 0;
-       _OUTB(port, 0x00);
-       for (i = 0; i < SDLA_IODELAY; ++i);     /* delay */
-       if (_INB(port) != 0x40)
-               return 0;
-       _OUTB(port, 0x04);
-       for (i = 0; i < SDLA_IODELAY; ++i);     /* delay */
-       if (_INB(port) != 0x44)
-               return 0;
-
-       /* Reset adapter */
-       _OUTB(port, 0x08);
-       _OUTB(port, 0x08);
-       _OUTB(port, 0x08);
-       _OUTB(port + 1, 0xFF);
-       return 1;
-}
-
-/*============================================================================
- * Detect S502E adapter.
- *     Following tests are used to verify adapter presence:
- *     1. All registers other than status (BASE) should read 0xFF.
- *     2. After writing 0 to CPU control register (BASE+3), status register
- *        (BASE) should read 11111000b.
- *     3. After writing 00000100b to port BASE (set bit 2), status register
- *        (BASE) should read 11111100b.
- *     Return 1 if detected o.k. or 0 if failed.
- *     Note:   This test is destructive! Adapter will be left in shutdown
- *             state after the test.
- */
-static int detect_s502e (int port)
-{
-       int i, j;
-
-       if (!get_option_index(s502_port_options, port))
-               return 0;
-       for (j = 1; j < SDLA_MAXIORANGE; ++j) {
-               if (_INB(port + j) != 0xFF)
-                       return 0;
-               for (i = 0; i < SDLA_IODELAY; ++i);     /* delay */
-       }
-
-       _OUTB(port + 3, 0);                     /* CPU control reg. */
-       for (i = 0; i < SDLA_IODELAY; ++i);     /* delay */
-       if (_INB(port) != 0xF8)                 /* read status */
-               return 0;
-       _OUTB(port, 0x04);                      /* set bit 2 */
-       for (i = 0; i < SDLA_IODELAY; ++i);     /* delay */
-       if (_INB(port) != 0xFC)                 /* verify */
-               return 0;
-
-       /* Reset adapter */
-       _OUTB(port, 0);
-       return 1;
-}
-
-/*============================================================================
- * Detect s503 adapter.
- *     Following tests are used to verify adapter presence:
- *     1. All registers other than status (BASE) should read 0xFF.
- *     2. After writing 0 to control register (BASE), status register (BASE)
- *        should read 11110000b.
- *     3. After writing 00000100b (set bit 2) to control register (BASE),
- *        status register should read 11110010b.
- *     Return 1 if detected o.k. or 0 if failed.
- *     Note:   This test is destructive! Adapter will be left in shutdown
- *             state after the test.
- */
-static int detect_s503 (int port)
-{
-       int i, j;
-
-       if (!get_option_index(s503_port_options, port))
-               return 0;
-       for (j = 1; j < SDLA_MAXIORANGE; ++j) {
-               if (_INB(port + j) != 0xFF)
-                       return 0;
-               for (i = 0; i < SDLA_IODELAY; ++i);     /* delay */
-       }
-
-       _OUTB(port, 0);                         /* reset control reg.*/
-       for (i = 0; i < SDLA_IODELAY; ++i);     /* delay */
-       if (_INB(port) != 0xF0)                 /* read status */
-               return 0;
-       _OUTB(port, 0x04);                      /* set bit 2 */
-       for (i = 0; i < SDLA_IODELAY; ++i);     /* delay */
-       if (_INB(port) != 0xF2)                 /* verify */
-               return 0;
-
-       /* Reset adapter */
-       _OUTB(port, 0);
-       return 1;
-}
-
-/*============================================================================
- * Detect s507 adapter.
- *     Following tests are used to detect s507 adapter:
- *     1. All ports should read the same value.
- *     2. After writing 0x00 to control register, status register should read
- *        ?011000?b.
- *     3. After writing 0x01 to control register, status register should read
- *        ?011001?b.
- *     Return 1 if detected o.k. or 0 if failed.
- *     Note:   This test is destructive! Adapter will be left in shutdown
- *             state after the test.
- */
-static int detect_s507 (int port)
-{
-       int tmp, i, j;
-
-       if (!get_option_index(s508_port_options, port))
-               return 0;
-       tmp = _INB(port);
-       for (j = 1; j < S507_IORANGE; ++j) {
-               if (_INB(port + j) != tmp)
-                       return 0;
-               for (i = 0; i < SDLA_IODELAY; ++i);     /* delay */
-       }
-
-       _OUTB(port, 0x00);
-       for (i = 0; i < SDLA_IODELAY; ++i);     /* delay */
-       if ((_INB(port) & 0x7E) != 0x30)
-               return 0;
-       _OUTB(port, 0x01);
-       for (i = 0; i < SDLA_IODELAY; ++i);     /* delay */
-       if ((_INB(port) & 0x7E) != 0x32)
-               return 0;
-
-       /* Reset adapter */
-       _OUTB(port, 0x00);
-       return 1;
-}
-
-/*============================================================================
- * Detect s508 adapter.
- *     Following tests are used to detect s508 adapter:
- *     1. After writing 0x00 to control register, status register should read
- *        ??000000b.
- *     2. After writing 0x10 to control register, status register should read
- *        ??010000b
- *     Return 1 if detected o.k. or 0 if failed.
- *     Note:   This test is destructive! Adapter will be left in shutdown
- *             state after the test.
- */
-static int detect_s508 (int port)
-{
-       int i;
-
-       if (!get_option_index(s508_port_options, port))
-               return 0;
-       _OUTB(port, 0x00);
-       for (i = 0; i < SDLA_IODELAY; ++i);     /* delay */
-       if ((_INB(port + 1) & 0x3F) != 0x00)
-               return 0;
-       _OUTB(port, 0x10);
-       for (i = 0; i < SDLA_IODELAY; ++i);     /* delay */
-       if ((_INB(port + 1) & 0x3F) != 0x10)
-               return 0;
-
-       /* Reset adapter */
-       _OUTB(port, 0x00);
-       return 1;
-}
-
-/*============================================================================
- * Detect s514 PCI adapter.
- *      Return 1 if detected o.k. or 0 if failed.
- *      Note:   This test is destructive! Adapter will be left in shutdown
- *              state after the test.
- */
-static int detect_s514 (sdlahw_t* hw)
-{
-       unsigned char CPU_no, slot_no, auto_slot_cfg;
-       int number_S514_cards = 0;
-       u32 S514_mem_base_addr = 0;
-       u32 ut_u32;
-       struct pci_dev *pci_dev;
-
-
-#ifndef CONFIG_PCI
-        printk(KERN_INFO "%s: Linux not compiled for PCI usage!\n", modname);
-        return 0;
-#endif
-
-       /*
-       The 'setup()' procedure in 'sdlamain.c' passes the CPU number and the
-       slot number defined in 'router.conf' via the 'port' definition.
-       */
-       CPU_no = hw->S514_cpu_no[0];
-       slot_no = hw->S514_slot_no;
-       auto_slot_cfg = hw->auto_pci_cfg;
-
-       if (auto_slot_cfg){
-               printk(KERN_INFO "%s: srch... S514 card, CPU %c, Slot=Auto\n",
-               modname, CPU_no);
-
-       }else{
-               printk(KERN_INFO "%s: srch... S514 card, CPU %c, Slot #%d\n",
-               modname, CPU_no, slot_no);
-       }
-       
-       /* check to see that CPU A or B has been selected in 'router.conf' */
-       switch(CPU_no) {
-               case S514_CPU_A:
-               case S514_CPU_B:
-                       break;
-       
-               default:
-                       printk(KERN_INFO "%s: S514 CPU definition invalid.\n", 
-                               modname);
-                       printk(KERN_INFO "Must be 'A' or 'B'\n");
-                       return 0;
-       }
-
-       number_S514_cards = find_s514_adapter(hw, 0);
-       if(!number_S514_cards)
-               return 0;
-
-       /* we are using a single S514 adapter with a slot of 0 so re-read the */        
-       /* location of this adapter */
-       if((number_S514_cards == 1) && auto_slot_cfg) { 
-               number_S514_cards = find_s514_adapter(hw, 1);
-               if(!number_S514_cards) {
-                       printk(KERN_INFO "%s: Error finding PCI card\n",
-                               modname);
-                       return 0;
-               }
-       }
-
-       pci_dev = hw->pci_dev;
-       /* read the physical memory base address */
-       S514_mem_base_addr = (CPU_no == S514_CPU_A) ? 
-               (pci_dev->resource[1].start) :
-               (pci_dev->resource[2].start);
-       
-       printk(KERN_INFO "%s: S514 PCI memory at 0x%X\n",
-               modname, S514_mem_base_addr);
-       if(!S514_mem_base_addr) {
-               if(CPU_no == S514_CPU_B)
-                       printk(KERN_INFO "%s: CPU #B not present on the card\n",                                modname);
-               else
-                       printk(KERN_INFO "%s: No PCI memory allocated to card\n",                               modname);
-               return 0;
-       }
-
-       /* enable the PCI memory */
-       pci_read_config_dword(pci_dev, 
-               (CPU_no == S514_CPU_A) ? PCI_MAP0_DWORD : PCI_MAP1_DWORD,
-               &ut_u32);
-       pci_write_config_dword(pci_dev,
-               (CPU_no == S514_CPU_A) ? PCI_MAP0_DWORD : PCI_MAP1_DWORD,
-               (ut_u32 | PCI_MEMORY_ENABLE));
-
-       /* check the IRQ allocated and enable IRQ usage */
-       if(!(hw->irq = pci_dev->irq)) {
-               printk(KERN_INFO "%s: IRQ not allocated to S514 adapter\n",
-                       modname);
-                return 0;
-       }
-
-       /* BUG FIX : Mar 6 2000
-        * On a initial loading of the card, we must check
-         * and clear PCI interrupt bits, due to a reset
-         * problem on some other boards.  i.e. An interrupt
-         * might be pending, even after system bootup, 
-         * in which case, when starting wanrouter the machine
-         * would crash. 
-        */
-       if (init_pci_slot(hw))
-               return 0;
-
-        pci_read_config_dword(pci_dev, PCI_INT_CONFIG, &ut_u32);
-        ut_u32 |= (CPU_no == S514_CPU_A) ?
-                PCI_ENABLE_IRQ_CPU_A : PCI_ENABLE_IRQ_CPU_B;
-        pci_write_config_dword(pci_dev, PCI_INT_CONFIG, ut_u32);
-
-       printk(KERN_INFO "%s: IRQ %d allocated to the S514 card\n",
-               modname, hw->irq);
-
-       /* map the physical PCI memory to virtual memory */
-       hw->dpmbase = ioremap((unsigned long)S514_mem_base_addr,
-               (unsigned long)MAX_SIZEOF_S514_MEMORY);
-       /* map the physical control register memory to virtual memory */
-       hw->vector = (unsigned long)ioremap(
-               (unsigned long)(S514_mem_base_addr + S514_CTRL_REG_BYTE),
-               (unsigned long)16);
-     
-        if(!hw->dpmbase || !hw->vector) {
-               printk(KERN_INFO "%s: PCI virtual memory allocation failed\n",
-                       modname);
-                return 0;
-       }
-
-       /* halt the adapter */
-       writeb (S514_CPU_HALT, hw->vector);     
-
-       return 1;
-}
-
-/*============================================================================
- * Find the S514 PCI adapter in the PCI bus.
- *      Return the number of S514 adapters found (0 if no adapter found).
- */
-static int find_s514_adapter(sdlahw_t* hw, char find_first_S514_card)
-{
-        unsigned char slot_no;
-        int number_S514_cards = 0;
-       char S514_found_in_slot = 0;
-        u16 PCI_subsys_vendor;
-
-        struct pci_dev *pci_dev = NULL;
-       slot_no = hw->S514_slot_no;
-  
-       while ((pci_dev = pci_find_device(V3_VENDOR_ID, V3_DEVICE_ID, pci_dev))
-               != NULL) {
-                
-               pci_read_config_word(pci_dev, PCI_SUBSYS_VENDOR_WORD,
-                        &PCI_subsys_vendor);
-                
-               if(PCI_subsys_vendor != SANGOMA_SUBSYS_VENDOR)
-                       continue;
-               
-               hw->pci_dev = pci_dev;
-               
-               if(find_first_S514_card)
-                       return(1);
-               
-                number_S514_cards ++;
-                
-               printk(KERN_INFO
-                       "%s: S514 card found, slot #%d (devfn 0x%X)\n",
-                        modname, ((pci_dev->devfn >> 3) & PCI_DEV_SLOT_MASK),
-                       pci_dev->devfn);
-               
-               if (hw->auto_pci_cfg){
-                       hw->S514_slot_no = ((pci_dev->devfn >> 3) & PCI_DEV_SLOT_MASK);
-                       slot_no = hw->S514_slot_no;
-                       
-               }else if (((pci_dev->devfn >> 3) & PCI_DEV_SLOT_MASK) == slot_no){
-                        S514_found_in_slot = 1;
-                        break;
-                }
-        }
-
-       /* if no S514 adapter has been found, then exit */
-        if (!number_S514_cards) {
-                printk(KERN_INFO "%s: Error, no S514 adapters found\n", modname);
-                return 0;
-        }
-        /* if more than one S514 card has been found, then the user must have */        /* defined a slot number so that the correct adapter is used */
-        else if ((number_S514_cards > 1) && hw->auto_pci_cfg) {
-                printk(KERN_INFO "%s: Error, PCI Slot autodetect Failed! \n"
-                                "%s:        More than one S514 adapter found.\n"
-                                "%s:        Disable the Autodetect feature and supply\n"
-                                "%s:        the PCISLOT numbers for each card.\n",
-                        modname,modname,modname,modname);
-                return 0;
-        }
-        /* if the user has specified a slot number and the S514 adapter has */
-        /* not been found in that slot, then exit */
-        else if (!hw->auto_pci_cfg && !S514_found_in_slot) {
-                printk(KERN_INFO
-                       "%s: Error, S514 card not found in specified slot #%d\n",
-                        modname, slot_no);
-                return 0;
-        }
-
-       return (number_S514_cards);
-}
-
-
-
-/******* Miscellaneous ******************************************************/
-
-/*============================================================================
- * Calibrate SDLA memory access delay.
- * Count number of idle loops made within 1 second and then calculate the
- * number of loops that should be made to achive desired delay.
- */
-static int calibrate_delay (int mks)
-{
-       unsigned int delay;
-       unsigned long stop;
-
-       for (delay = 0, stop = SYSTEM_TICK + HZ; SYSTEM_TICK < stop; ++delay);
-       return (delay/(1000000L/mks) + 1);
-}
-
-/*============================================================================
- * Get option's index into the options list.
- *     Return option's index (1 .. N) or zero if option is invalid.
- */
-static int get_option_index (unsigned* optlist, unsigned optval)
-{
-       int i;
-
-       for (i = 1; i <= optlist[0]; ++i)
-               if ( optlist[i] == optval)
-                       return i;
-       return 0;
-}
-
-/*============================================================================
- * Check memory region to see if it's available. 
- * Return:     0       ok.
- */
-static unsigned check_memregion (void* ptr, unsigned len)
-{
-       volatile unsigned char* p = ptr;
-
-        for (; len && (readb (p) == 0xFF); --len, ++p) {
-                writeb (0, p);          /* attempt to write 0 */
-                if (readb(p) != 0xFF) { /* still has to read 0xFF */
-                        writeb (0xFF, p);/* restore original value */
-                        break;          /* not good */
-                }
-        }
-
-       return len;
-}
-
-/*============================================================================
- * Test memory region.
- * Return:     size of the region that passed the test.
- * Note:       Region size must be multiple of 2 !
- */
-static unsigned test_memregion (void* ptr, unsigned len)
-{
-       volatile unsigned short* w_ptr;
-       unsigned len_w = len >> 1;      /* region len in words */
-       unsigned i;
-
-        for (i = 0, w_ptr = ptr; i < len_w; ++i, ++w_ptr)
-                writew (0xAA55, w_ptr);
-        
-       for (i = 0, w_ptr = ptr; i < len_w; ++i, ++w_ptr)
-                if (readw (w_ptr) != 0xAA55) {
-                        len_w = i;
-                        break;
-                }
-
-        for (i = 0, w_ptr = ptr; i < len_w; ++i, ++w_ptr)
-                writew (0x55AA, w_ptr);
-        
-        for (i = 0, w_ptr = ptr; i < len_w; ++i, ++w_ptr)
-                if (readw(w_ptr) != 0x55AA) {
-                        len_w = i;
-                        break;
-                }
-        
-        for (i = 0, w_ptr = ptr; i < len_w; ++i, ++w_ptr)
-               writew (0, w_ptr);
-
-        return len_w << 1;
-}
-
-/*============================================================================
- * Calculate 16-bit CRC using CCITT polynomial.
- */
-static unsigned short checksum (unsigned char* buf, unsigned len)
-{
-       unsigned short crc = 0;
-       unsigned mask, flag;
-
-       for (; len; --len, ++buf) {
-               for (mask = 0x80; mask; mask >>= 1) {
-                       flag = (crc & 0x8000);
-                       crc <<= 1;
-                       crc |= ((*buf & mask) ? 1 : 0);
-                       if (flag) crc ^= 0x1021;
-               }
-       }
-       return crc;
-}
-
-static int init_pci_slot(sdlahw_t *hw)
-{
-
-       u32 int_status;
-       int volatile found=0;
-       int i=0;
-
-       /* Check if this is a very first load for a specific
-         * pci card. If it is, clear the interrput bits, and
-         * set the flag indicating that this card was initialized.
-        */
-       
-       for (i=0; (i<MAX_S514_CARDS) && !found; i++){
-               if (pci_slot_ar[i] == hw->S514_slot_no){
-                       found=1;
-                       break;
-               }
-               if (pci_slot_ar[i] == 0xFF){
-                       break;
-               }
-       }
-
-       if (!found){
-               read_S514_int_stat(hw,&int_status);
-               S514_intack(hw,int_status);
-               if (i == MAX_S514_CARDS){
-                       printk(KERN_INFO "%s: Critical Error !!!\n",modname);
-                       printk(KERN_INFO 
-                               "%s: Number of Sangoma PCI cards exceeded maximum limit.\n",
-                                       modname);
-                       printk(KERN_INFO "Please contact Sangoma Technologies\n");
-                       return 1;
-               }
-               pci_slot_ar[i] = hw->S514_slot_no;
-       }
-       return 0;
-}
-
-static int pci_probe(sdlahw_t *hw)
-{
-
-        unsigned char slot_no;
-        int number_S514_cards = 0;
-        u16 PCI_subsys_vendor;
-       u16 PCI_card_type;
-
-        struct pci_dev *pci_dev = NULL;
-       struct pci_bus *bus = NULL;
-       slot_no = 0;
-  
-       while ((pci_dev = pci_find_device(V3_VENDOR_ID, V3_DEVICE_ID, pci_dev))
-               != NULL) {
-               
-                pci_read_config_word(pci_dev, PCI_SUBSYS_VENDOR_WORD,
-                        &PCI_subsys_vendor);
-               
-                if(PCI_subsys_vendor != SANGOMA_SUBSYS_VENDOR)
-                       continue;
-
-               pci_read_config_word(pci_dev, PCI_CARD_TYPE,
-                        &PCI_card_type);
-       
-               bus = pci_dev->bus;
-               
-               /* A dual cpu card can support up to 4 physical connections,
-                * where a single cpu card can support up to 2 physical
-                * connections.  The FT1 card can only support a single 
-                * connection, however we cannot distinguish between a Single
-                * CPU card and an FT1 card. */
-               if (PCI_card_type == S514_DUAL_CPU){
-                       number_S514_cards += 4;
-                        printk(KERN_INFO
-                               "wanpipe: S514-PCI card found, cpu(s) 2, bus #%d, slot #%d, irq #%d\n",
-                               bus->number,((pci_dev->devfn >> 3) & PCI_DEV_SLOT_MASK),
-                               pci_dev->irq);
-               }else{
-                       number_S514_cards += 2;
-                       printk(KERN_INFO
-                               "wanpipe: S514-PCI card found, cpu(s) 1, bus #%d, slot #%d, irq #%d\n",
-                               bus->number,((pci_dev->devfn >> 3) & PCI_DEV_SLOT_MASK),
-                               pci_dev->irq);
-               }
-        }
-
-       return number_S514_cards;
-
-}
-
-
-
-EXPORT_SYMBOL(wanpipe_hw_probe);
-
-unsigned wanpipe_hw_probe(void)
-{
-       sdlahw_t hw;
-       unsigned* opt = s508_port_options; 
-       unsigned cardno=0;
-       int i;
-       
-       memset(&hw, 0, sizeof(hw));
-       
-       for (i = 1; i <= opt[0]; i++) {
-               if (detect_s508(opt[i])){
-                       /* S508 card can support up to two physical links */
-                       cardno+=2;
-                       printk(KERN_INFO "wanpipe: S508-ISA card found, port 0x%x\n",opt[i]);
-               }
-       }
-
-      #ifdef CONFIG_PCI
-       hw.S514_slot_no = 0;
-       cardno += pci_probe(&hw);
-      #else
-       printk(KERN_INFO "wanpipe: Warning, Kernel not compiled for PCI support!\n");
-       printk(KERN_INFO "wanpipe: PCI Hardware Probe Failed!\n");
-      #endif
-
-       return cardno;
-}
-
-/****** End *****************************************************************/
diff --git a/drivers/net/wan/sdlamain.c b/drivers/net/wan/sdlamain.c
deleted file mode 100644 (file)
index 7a8b22a..0000000
+++ /dev/null
@@ -1,1346 +0,0 @@
-/****************************************************************************
-* sdlamain.c   WANPIPE(tm) Multiprotocol WAN Link Driver.  Main module.
-*
-* Author:      Nenad Corbic    <ncorbic@sangoma.com>
-*              Gideon Hack     
-*
-* Copyright:   (c) 1995-2000 Sangoma Technologies Inc.
-*
-*              This program is free software; you can redistribute it and/or
-*              modify it under the terms of the GNU General Public License
-*              as published by the Free Software Foundation; either version
-*              2 of the License, or (at your option) any later version.
-* ============================================================================
-* Dec 22, 2000  Nenad Corbic   Updated for 2.4.X kernels.
-*                              Removed the polling routine.
-* Nov 13, 2000  Nenad Corbic   Added hw probing on module load and dynamic
-*                              device allocation. 
-* Nov 7,  2000  Nenad Corbic   Fixed the Multi-Port PPP for kernels
-*                               2.2.16 and above.
-* Aug 2,  2000  Nenad Corbic   Block the Multi-Port PPP from running on
-*                              kernels 2.2.16 or greater.  The SyncPPP 
-*                              has changed.
-* Jul 25, 2000  Nenad Corbic   Updated the Piggiback support for MultPPPP.
-* Jul 13, 2000 Nenad Corbic    Added Multi-PPP support.
-* Feb 02, 2000  Nenad Corbic    Fixed up piggyback probing and selection.
-* Sep 23, 1999  Nenad Corbic    Added support for SMP
-* Sep 13, 1999  Nenad Corbic   Each port is treated as a separate device.
-* Jun 02, 1999  Gideon Hack     Added support for the S514 adapter.
-*                              Updates for Linux 2.2.X kernels.
-* Sep 17, 1998 Jaspreet Singh  Updated for 2.1.121+ kernel
-* Nov 28, 1997 Jaspreet Singh  Changed DRV_RELEASE to 1
-* Nov 10, 1997 Jaspreet Singh  Changed sti() to restore_flags();
-* Nov 06, 1997         Jaspreet Singh  Changed DRV_VERSION to 4 and DRV_RELEASE to 0
-* Oct 20, 1997         Jaspreet Singh  Modified sdla_isr routine so that card->in_isr
-*                              assignments are taken out and placed in the
-*                              sdla_ppp.c, sdla_fr.c and sdla_x25.c isr
-*                              routines. Took out 'wandev->tx_int_enabled' and
-*                              replaced it with 'wandev->enable_tx_int'. 
-* May 29, 1997 Jaspreet Singh  Flow Control Problem
-*                              added "wandev->tx_int_enabled=1" line in the
-*                              init module. This line initializes the flag for 
-*                              preventing Interrupt disabled with device set to
-*                              busy
-* Jan 15, 1997 Gene Kozin      Version 3.1.0
-*                               o added UDP management stuff
-* Jan 02, 1997 Gene Kozin      Initial version.
-*****************************************************************************/
-
-#include <linux/config.h>      /* OS configuration options */
-#include <linux/stddef.h>      /* offsetof(), etc. */
-#include <linux/errno.h>       /* return codes */
-#include <linux/string.h>      /* inline memset(), etc. */
-#include <linux/init.h>
-#include <linux/slab.h>        /* kmalloc(), kfree() */
-#include <linux/kernel.h>      /* printk(), and other useful stuff */
-#include <linux/module.h>      /* support for loadable modules */
-#include <linux/ioport.h>      /* request_region(), release_region() */
-#include <linux/wanrouter.h>   /* WAN router definitions */
-#include <linux/wanpipe.h>     /* WANPIPE common user API definitions */
-#include <linux/rcupdate.h>
-
-#include <linux/in.h>
-#include <asm/io.h>            /* phys_to_virt() */
-#include <linux/pci.h>
-#include <linux/sdlapci.h>
-#include <linux/if_wanpipe_common.h>
-
-#include <asm/uaccess.h>       /* kernel <-> user copy */
-#include <linux/inetdevice.h>
-
-#include <linux/ip.h>
-#include <net/route.h>
-#define KMEM_SAFETYZONE 8
-
-
-#ifndef CONFIG_WANPIPE_FR
-  #define wpf_init(a,b) (-EPROTONOSUPPORT) 
-#endif
-
-#ifndef CONFIG_WANPIPE_CHDLC
- #define wpc_init(a,b) (-EPROTONOSUPPORT) 
-#endif
-
-#ifndef CONFIG_WANPIPE_X25
- #define wpx_init(a,b) (-EPROTONOSUPPORT) 
-#endif
-#ifndef CONFIG_WANPIPE_PPP
- #define wpp_init(a,b) (-EPROTONOSUPPORT) 
-#endif
-
-#ifndef CONFIG_WANPIPE_MULTPPP 
- #define wsppp_init(a,b) (-EPROTONOSUPPORT) 
-#endif
-/***********FOR DEBUGGING PURPOSES*********************************************
-static void * dbg_kmalloc(unsigned int size, int prio, int line) {
-       int i = 0;
-       void * v = kmalloc(size+sizeof(unsigned int)+2*KMEM_SAFETYZONE*8,prio);
-       char * c1 = v;  
-       c1 += sizeof(unsigned int);
-       *((unsigned int *)v) = size;
-
-       for (i = 0; i < KMEM_SAFETYZONE; i++) {
-               c1[0] = 'D'; c1[1] = 'E'; c1[2] = 'A'; c1[3] = 'D';
-               c1[4] = 'B'; c1[5] = 'E'; c1[6] = 'E'; c1[7] = 'F';
-               c1 += 8;
-       }
-       c1 += size;
-       for (i = 0; i < KMEM_SAFETYZONE; i++) {
-               c1[0] = 'M'; c1[1] = 'U'; c1[2] = 'N'; c1[3] = 'G';
-               c1[4] = 'W'; c1[5] = 'A'; c1[6] = 'L'; c1[7] = 'L';
-               c1 += 8;
-       }
-       v = ((char *)v) + sizeof(unsigned int) + KMEM_SAFETYZONE*8;
-       printk(KERN_INFO "line %d  kmalloc(%d,%d) = %p\n",line,size,prio,v);
-       return v;
-}
-static void dbg_kfree(void * v, int line) {
-       unsigned int * sp = (unsigned int *)(((char *)v) - (sizeof(unsigned int) + KMEM_SAFETYZONE*8));
-       unsigned int size = *sp;
-       char * c1 = ((char *)v) - KMEM_SAFETYZONE*8;
-       int i = 0;
-       for (i = 0; i < KMEM_SAFETYZONE; i++) {
-               if (   c1[0] != 'D' || c1[1] != 'E' || c1[2] != 'A' || c1[3] != 'D'
-                   || c1[4] != 'B' || c1[5] != 'E' || c1[6] != 'E' || c1[7] != 'F') {
-                       printk(KERN_INFO "kmalloced block at %p has been corrupted (underrun)!\n",v);
-                       printk(KERN_INFO " %4x: %2x %2x %2x %2x %2x %2x %2x %2x\n", i*8,
-                                       c1[0],c1[1],c1[2],c1[3],c1[4],c1[5],c1[6],c1[7] );
-               }
-               c1 += 8;
-       }
-       c1 += size;
-       for (i = 0; i < KMEM_SAFETYZONE; i++) {
-               if (   c1[0] != 'M' || c1[1] != 'U' || c1[2] != 'N' || c1[3] != 'G'
-                   || c1[4] != 'W' || c1[5] != 'A' || c1[6] != 'L' || c1[7] != 'L'
-                  ) {
-                       printk(KERN_INFO "kmalloced block at %p has been corrupted (overrun):\n",v);
-                       printk(KERN_INFO " %4x: %2x %2x %2x %2x %2x %2x %2x %2x\n", i*8,
-                                       c1[0],c1[1],c1[2],c1[3],c1[4],c1[5],c1[6],c1[7] );
-               }
-               c1 += 8;
-       }
-       printk(KERN_INFO "line %d  kfree(%p)\n",line,v);
-       v = ((char *)v) - (sizeof(unsigned int) + KMEM_SAFETYZONE*8);
-       kfree(v);
-}
-
-#define kmalloc(x,y) dbg_kmalloc(x,y,__LINE__)
-#define kfree(x) dbg_kfree(x,__LINE__)
-******************************************************************************/
-
-
-
-/****** Defines & Macros ****************************************************/
-
-#ifdef _DEBUG_
-#define        STATIC
-#else
-#define        STATIC          static
-#endif
-
-#define        DRV_VERSION     5               /* version number */
-#define        DRV_RELEASE     0               /* release (minor version) number */
-#define        MAX_CARDS       16              /* max number of adapters */
-
-#ifndef        CONFIG_WANPIPE_CARDS            /* configurable option */
-#define        CONFIG_WANPIPE_CARDS 1
-#endif
-
-#define        CMD_OK          0               /* normal firmware return code */
-#define        CMD_TIMEOUT     0xFF            /* firmware command timed out */
-#define        MAX_CMD_RETRY   10              /* max number of firmware retries */
-/****** Function Prototypes *************************************************/
-
-extern void disable_irq(unsigned int);
-extern void enable_irq(unsigned int);
-/* WAN link driver entry points */
-static int setup(struct wan_device* wandev, wandev_conf_t* conf);
-static int shutdown(struct wan_device* wandev);
-static int ioctl(struct wan_device* wandev, unsigned cmd, unsigned long arg);
-
-/* IOCTL handlers */
-static int ioctl_dump  (sdla_t* card, sdla_dump_t* u_dump);
-static int ioctl_exec  (sdla_t* card, sdla_exec_t* u_exec, int);
-
-/* Miscellaneous functions */
-STATIC irqreturn_t sdla_isr    (int irq, void* dev_id, struct pt_regs *regs);
-static void release_hw  (sdla_t *card);
-
-static int check_s508_conflicts (sdla_t* card,wandev_conf_t* conf, int*);
-static int check_s514_conflicts (sdla_t* card,wandev_conf_t* conf, int*);
-
-
-/****** Global Data **********************************************************
- * Note: All data must be explicitly initialized!!!
- */
-
-/* private data */
-static char drvname[]  = "wanpipe";
-static char fullname[] = "WANPIPE(tm) Multiprotocol Driver";
-static char copyright[]        = "(c) 1995-2000 Sangoma Technologies Inc.";
-static int ncards; 
-static sdla_t* card_array;             /* adapter data space */
-
-/* Wanpipe's own workqueue, used for all API's.
- * All protocol specific tasks will be inserted
- * into the "wanpipe_wq" workqueue. 
-
- * The kernel workqueue mechanism will execute
- * all pending tasks in the "wanpipe_wq" workqueue.
- */
-
-struct workqueue_struct *wanpipe_wq;
-DECLARE_WORK(wanpipe_work, NULL, NULL);
-
-static int wanpipe_bh_critical;
-
-/******* Kernel Loadable Module Entry Points ********************************/
-
-/*============================================================================
- * Module 'insert' entry point.
- * o print announcement
- * o allocate adapter data space
- * o initialize static data
- * o register all cards with WAN router
- * o calibrate SDLA shared memory access delay.
- *
- * Return:     0       Ok
- *             < 0     error.
- * Context:    process
- */
-static int __init wanpipe_init(void)
-{
-       int cnt, err = 0;
-
-       printk(KERN_INFO "%s v%u.%u %s\n",
-               fullname, DRV_VERSION, DRV_RELEASE, copyright);
-
-       wanpipe_wq = create_workqueue("wanpipe_wq");
-       if (!wanpipe_wq)
-               return -ENOMEM;
-
-       /* Probe for wanpipe cards and return the number found */
-       printk(KERN_INFO "wanpipe: Probing for WANPIPE hardware.\n");
-       ncards = wanpipe_hw_probe();
-       if (ncards){
-               printk(KERN_INFO "wanpipe: Allocating maximum %i devices: wanpipe%i - wanpipe%i.\n",ncards,1,ncards);
-       }else{
-               printk(KERN_INFO "wanpipe: No S514/S508 cards found, unloading modules!\n");
-               destroy_workqueue(wanpipe_wq);
-               return -ENODEV;
-       }
-       
-       /* Verify number of cards and allocate adapter data space */
-       card_array = kmalloc(sizeof(sdla_t) * ncards, GFP_KERNEL);
-       if (card_array == NULL) {
-               destroy_workqueue(wanpipe_wq);
-               return -ENOMEM;
-       }
-
-       memset(card_array, 0, sizeof(sdla_t) * ncards);
-
-       /* Register adapters with WAN router */
-       for (cnt = 0; cnt < ncards; ++ cnt) {
-               sdla_t* card = &card_array[cnt];
-               struct wan_device* wandev = &card->wandev;
-
-               card->next = NULL;
-               sprintf(card->devname, "%s%d", drvname, cnt + 1);
-               wandev->magic    = ROUTER_MAGIC;
-               wandev->name     = card->devname;
-               wandev->private  = card;
-               wandev->enable_tx_int = 0;
-               wandev->setup    = &setup;
-               wandev->shutdown = &shutdown;
-               wandev->ioctl    = &ioctl;
-               err = register_wan_device(wandev);
-               if (err) {
-                       printk(KERN_INFO
-                               "%s: %s registration failed with error %d!\n",
-                               drvname, card->devname, err);
-                       break;
-               }
-       }
-       if (cnt){
-               ncards = cnt;   /* adjust actual number of cards */
-       }else {
-               kfree(card_array);
-               destroy_workqueue(wanpipe_wq);
-               printk(KERN_INFO "IN Init Module: NO Cards registered\n");
-               err = -ENODEV;
-       }
-
-       return err;
-}
-
-/*============================================================================
- * Module 'remove' entry point.
- * o unregister all adapters from the WAN router
- * o release all remaining system resources
- */
-static void __exit wanpipe_cleanup(void)
-{
-       int i;
-
-       if (!ncards)
-               return;
-               
-       for (i = 0; i < ncards; ++i) {
-               sdla_t* card = &card_array[i];
-               unregister_wan_device(card->devname);
-       }
-       destroy_workqueue(wanpipe_wq);
-       kfree(card_array);
-
-       printk(KERN_INFO "\nwanpipe: WANPIPE Modules Unloaded.\n");
-}
-
-module_init(wanpipe_init);
-module_exit(wanpipe_cleanup);
-
-/******* WAN Device Driver Entry Points *************************************/
-
-/*============================================================================
- * Setup/configure WAN link driver.
- * o check adapter state
- * o make sure firmware is present in configuration
- * o make sure I/O port and IRQ are specified
- * o make sure I/O region is available
- * o allocate interrupt vector
- * o setup SDLA hardware
- * o call appropriate routine to perform protocol-specific initialization
- * o mark I/O region as used
- * o if this is the first active card, then schedule background task
- *
- * This function is called when router handles ROUTER_SETUP IOCTL. The
- * configuration structure is in kernel memory (including extended data, if
- * any).
- */
-static int setup(struct wan_device* wandev, wandev_conf_t* conf)
-{
-       sdla_t* card;
-       int err = 0;
-       int irq=0;
-
-       /* Sanity checks */
-       if ((wandev == NULL) || (wandev->private == NULL) || (conf == NULL)){
-               printk(KERN_INFO 
-                     "%s: Failed Sdlamain Setup wandev %u, card %u, conf %u !\n",
-                     wandev->name,
-                     (unsigned int)wandev,(unsigned int)wandev->private,
-                     (unsigned int)conf); 
-               return -EFAULT;
-       }
-
-       printk(KERN_INFO "%s: Starting WAN Setup\n", wandev->name);
-
-       card = wandev->private;
-       if (wandev->state != WAN_UNCONFIGURED){
-               printk(KERN_INFO "%s: failed sdlamain setup, busy!\n",
-                       wandev->name);
-               return -EBUSY;          /* already configured */
-       }
-
-       printk(KERN_INFO "\nProcessing WAN device %s...\n", wandev->name);
-
-       /* Initialize the counters for each wandev 
-        * Used for counting number of times new_if and 
-         * del_if get called.
-        */
-       wandev->del_if_cnt = 0;
-       wandev->new_if_cnt = 0;
-       wandev->config_id  = conf->config_id;
-
-       if (!conf->data_size || (conf->data == NULL)) {
-               printk(KERN_INFO
-                       "%s: firmware not found in configuration data!\n",
-                       wandev->name);
-               return -EINVAL;
-       }
-
-       /* Check for resource conflicts and setup the
-        * card for piggibacking if necessary */
-       if(!conf->S514_CPU_no[0]) {
-               if ((err=check_s508_conflicts(card,conf,&irq)) != 0){
-                       return err;
-               }
-       }else {
-               if ((err=check_s514_conflicts(card,conf,&irq)) != 0){
-                       return err;
-               }
-       }
-
-       /* If the current card has already been configured
-         * or it's a piggyback card, do not try to allocate
-         * resources.
-        */
-       if (!card->wandev.piggyback && !card->configured){
-
-               /* Configure hardware, load firmware, etc. */
-               memset(&card->hw, 0, sizeof(sdlahw_t));
-
-               /* for an S514 adapter, pass the CPU number and the slot number read */
-               /* from 'router.conf' to the 'sdla_setup()' function via the 'port' */
-               /* parameter */
-               if (conf->S514_CPU_no[0]){
-
-                       card->hw.S514_cpu_no[0] = conf->S514_CPU_no[0];
-                       card->hw.S514_slot_no = conf->PCI_slot_no;
-                       card->hw.auto_pci_cfg = conf->auto_pci_cfg;
-
-                       if (card->hw.auto_pci_cfg == WANOPT_YES){
-                               printk(KERN_INFO "%s: Setting CPU to %c and Slot to Auto\n",
-                               card->devname, card->hw.S514_cpu_no[0]);
-                       }else{
-                               printk(KERN_INFO "%s: Setting CPU to %c and Slot to %i\n",
-                               card->devname, card->hw.S514_cpu_no[0], card->hw.S514_slot_no);
-                       }
-
-               }else{
-                       /* 508 Card io port and irq initialization */
-                       card->hw.port = conf->ioport;
-                       card->hw.irq = (conf->irq == 9) ? 2 : conf->irq;
-               }
-
-
-               /* Compute the virtual address of the card in kernel space */
-               if(conf->maddr){
-                       card->hw.dpmbase = phys_to_virt(conf->maddr);
-               }else{  
-                       card->hw.dpmbase = (void *)conf->maddr;
-               }
-                       
-               card->hw.dpmsize = SDLA_WINDOWSIZE;
-               
-               /* set the adapter type if using an S514 adapter */
-               card->hw.type = (conf->S514_CPU_no[0]) ? SDLA_S514 : conf->hw_opt[0]; 
-               card->hw.pclk = conf->hw_opt[1];
-
-               err = sdla_setup(&card->hw, conf->data, conf->data_size);
-               if (err){
-                       printk(KERN_INFO "%s: Hardware setup Failed %i\n",
-                                       card->devname,err);
-                       return err;
-               }
-
-               if(card->hw.type != SDLA_S514)
-                       irq = (conf->irq == 2) ? 9 : conf->irq; /* IRQ2 -> IRQ9 */
-               else
-                       irq = card->hw.irq;
-
-               /* request an interrupt vector - note that interrupts may be shared */
-               /* when using the S514 PCI adapter */
-               
-                       if(request_irq(irq, sdla_isr, 
-                     (card->hw.type == SDLA_S514) ? SA_SHIRQ : 0, 
-                      wandev->name, card)){
-
-                       printk(KERN_INFO "%s: Can't reserve IRQ %d!\n", wandev->name, irq);
-                       return -EINVAL;
-               }
-
-       }else{
-               printk(KERN_INFO "%s: Card Configured %lu or Piggybacking %i!\n",
-                       wandev->name,card->configured,card->wandev.piggyback);
-       } 
-
-
-       if (!card->configured){
-
-               /* Initialize the Spin lock */
-               printk(KERN_INFO "%s: Initializing for SMP\n",wandev->name);
-
-               /* Piggyback spin lock has already been initialized,
-                * in check_s514/s508_conflicts() */
-               if (!card->wandev.piggyback){
-                       spin_lock_init(&card->wandev.lock);
-               }
-               
-               /* Intialize WAN device data space */
-               wandev->irq       = irq;
-               wandev->dma       = 0;
-               if(card->hw.type != SDLA_S514){ 
-                       wandev->ioport = card->hw.port;
-               }else{
-                       wandev->S514_cpu_no[0] = card->hw.S514_cpu_no[0];
-                       wandev->S514_slot_no = card->hw.S514_slot_no;
-               }
-               wandev->maddr     = (unsigned long)card->hw.dpmbase;
-               wandev->msize     = card->hw.dpmsize;
-               wandev->hw_opt[0] = card->hw.type;
-               wandev->hw_opt[1] = card->hw.pclk;
-               wandev->hw_opt[2] = card->hw.memory;
-               wandev->hw_opt[3] = card->hw.fwid;
-       }
-
-       /* Protocol-specific initialization */
-       switch (card->hw.fwid) {
-
-       case SFID_X25_502:
-       case SFID_X25_508:
-               printk(KERN_INFO "%s: Starting X.25 Protocol Init.\n",
-                               card->devname);
-               err = wpx_init(card, conf);
-               break;
-       case SFID_FR502:
-       case SFID_FR508:
-               printk(KERN_INFO "%s: Starting Frame Relay Protocol Init.\n",
-                               card->devname);
-               err = wpf_init(card, conf);
-               break;
-       case SFID_PPP502:
-       case SFID_PPP508:
-               printk(KERN_INFO "%s: Starting PPP Protocol Init.\n",
-                               card->devname);
-               err = wpp_init(card, conf);
-               break;
-               
-       case SFID_CHDLC508:
-       case SFID_CHDLC514:
-               if (conf->ft1){         
-                       printk(KERN_INFO "%s: Starting FT1 CSU/DSU Config Driver.\n",
-                               card->devname);
-                       err = wpft1_init(card, conf);
-                       break;
-                       
-               }else if (conf->config_id == WANCONFIG_MPPP){
-                       printk(KERN_INFO "%s: Starting Multi-Port PPP Protocol Init.\n",
-                                       card->devname);
-                       err = wsppp_init(card,conf);
-                       break;
-
-               }else{
-                       printk(KERN_INFO "%s: Starting CHDLC Protocol Init.\n",
-                                       card->devname);
-                       err = wpc_init(card, conf);
-                       break;
-               }
-       default:
-               printk(KERN_INFO "%s: Error, Firmware is not supported %X %X!\n",
-                       wandev->name,card->hw.fwid,SFID_CHDLC508);
-               err = -EPROTONOSUPPORT;
-       }
-
-       if (err != 0){
-               if (err == -EPROTONOSUPPORT){
-                       printk(KERN_INFO 
-                               "%s: Error, Protocol selected has not been compiled!\n",
-                                       card->devname);
-                       printk(KERN_INFO 
-                               "%s:        Re-configure the kernel and re-build the modules!\n",
-                                       card->devname);
-               }
-               
-               release_hw(card);
-               wandev->state = WAN_UNCONFIGURED;
-               return err;
-       }
-
-
-       /* Reserve I/O region and schedule background task */
-        if(card->hw.type != SDLA_S514 && !card->wandev.piggyback)
-               if (!request_region(card->hw.port, card->hw.io_range, 
-                               wandev->name)) {
-                       printk(KERN_WARNING "port 0x%04x busy\n", card->hw.port);
-                       release_hw(card);
-                       wandev->state = WAN_UNCONFIGURED;
-                       return -EBUSY;
-         }
-
-       /* Only use the polling routine for the X25 protocol */
-       
-       card->wandev.critical=0;
-       return 0;
-}
-
-/*================================================================== 
- * configure_s508_card
- * 
- * For a S508 adapter, check for a possible configuration error in that
- * we are loading an adapter in the same IO port as a previously loaded S508
- * card.
- */ 
-
-static int check_s508_conflicts (sdla_t* card,wandev_conf_t* conf, int *irq)
-{
-       unsigned long smp_flags;
-       int i;
-       
-       if (conf->ioport <= 0) {
-               printk(KERN_INFO
-               "%s: can't configure without I/O port address!\n",
-               card->wandev.name);
-               return -EINVAL;
-       }
-
-       if (conf->irq <= 0) {
-               printk(KERN_INFO "%s: can't configure without IRQ!\n",
-               card->wandev.name);
-               return -EINVAL;
-       }
-
-       if (test_bit(0,&card->configured))
-               return 0;
-
-
-       /* Check for already loaded card with the same IO port and IRQ 
-        * If found, copy its hardware configuration and use its
-        * resources (i.e. piggybacking)
-        */
-       
-       for (i = 0; i < ncards; i++) {
-               sdla_t *nxt_card = &card_array[i];
-
-               /* Skip the current card ptr */
-               if (nxt_card == card)   
-                       continue;
-
-
-               /* Find a card that is already configured with the
-                * same IO Port */
-               if ((nxt_card->hw.type == SDLA_S508) &&
-                   (nxt_card->hw.port == conf->ioport) && 
-                   (nxt_card->next == NULL)){
-                       
-                       /* We found a card the card that has same configuration
-                        * as us. This means, that we must setup this card in 
-                        * piggibacking mode. However, only CHDLC and MPPP protocol
-                        * support this setup */
-               
-                       if ((conf->config_id == WANCONFIG_CHDLC || 
-                            conf->config_id == WANCONFIG_MPPP) &&
-                           (nxt_card->wandev.config_id == WANCONFIG_CHDLC || 
-                            nxt_card->wandev.config_id == WANCONFIG_MPPP)){ 
-                               
-                               *irq = nxt_card->hw.irq;
-                               memcpy(&card->hw, &nxt_card->hw, sizeof(sdlahw_t));
-                       
-                               /* The master could already be running, we must
-                                * set this as a critical area */
-                               lock_adapter_irq(&nxt_card->wandev.lock, &smp_flags);
-
-                               nxt_card->next = card;
-                               card->next = nxt_card;
-
-                               card->wandev.piggyback = WANOPT_YES;
-
-                               /* We must initialise the piggiback spin lock here
-                                * since isr will try to lock card->next if it
-                                * exists */
-                               spin_lock_init(&card->wandev.lock);
-                               
-                               unlock_adapter_irq(&nxt_card->wandev.lock, &smp_flags);
-                               break;
-                       }else{
-                               /* Trying to run piggibacking with a wrong protocol */
-                               printk(KERN_INFO "%s: ERROR: Resource busy, ioport: 0x%x\n"
-                                                "%s:        This protocol doesn't support\n"
-                                                "%s:        multi-port operation!\n",
-                                                card->devname,nxt_card->hw.port,
-                                                card->devname,card->devname);
-                               return -EEXIST;
-                       }
-               }
-       }
-       
-
-       /* Make sure I/O port region is available only if we are the
-        * master device.  If we are running in piggybacking mode, 
-        * we will use the resources of the master card. */
-       if (!card->wandev.piggyback) {
-               struct resource *rr =
-                       request_region(conf->ioport, SDLA_MAXIORANGE, "sdlamain");
-               release_region(conf->ioport, SDLA_MAXIORANGE);
-
-               if (!rr) {
-                       printk(KERN_INFO
-                               "%s: I/O region 0x%X - 0x%X is in use!\n",
-                               card->wandev.name, conf->ioport,
-                               conf->ioport + SDLA_MAXIORANGE - 1);
-                       return -EINVAL;
-               }
-       }
-
-       return 0;
-}
-
-/*================================================================== 
- * configure_s514_card
- * 
- * For a S514 adapter, check for a possible configuration error in that
- * we are loading an adapter in the same slot as a previously loaded S514
- * card.
- */ 
-
-
-static int check_s514_conflicts(sdla_t* card,wandev_conf_t* conf, int *irq)
-{
-       unsigned long smp_flags;
-       int i;
-       
-       if (test_bit(0,&card->configured))
-               return 0;
-
-       
-       /* Check for already loaded card with the same IO port and IRQ 
-        * If found, copy its hardware configuration and use its
-        * resources (i.e. piggybacking)
-        */
-
-       for (i = 0; i < ncards; i ++) {
-       
-               sdla_t* nxt_card = &card_array[i];
-               if(nxt_card == card)
-                       continue;
-               
-               if((nxt_card->hw.type == SDLA_S514) &&
-                  (nxt_card->hw.S514_slot_no == conf->PCI_slot_no) &&
-                  (nxt_card->hw.S514_cpu_no[0] == conf->S514_CPU_no[0])&&
-                  (nxt_card->next == NULL)){
-
-
-                       if ((conf->config_id == WANCONFIG_CHDLC || 
-                            conf->config_id == WANCONFIG_MPPP) &&
-                           (nxt_card->wandev.config_id == WANCONFIG_CHDLC || 
-                            nxt_card->wandev.config_id == WANCONFIG_MPPP)){ 
-                               
-                               *irq = nxt_card->hw.irq;
-                               memcpy(&card->hw, &nxt_card->hw, sizeof(sdlahw_t));
-       
-                               /* The master could already be running, we must
-                                * set this as a critical area */
-                               lock_adapter_irq(&nxt_card->wandev.lock,&smp_flags);
-                               nxt_card->next = card;
-                               card->next = nxt_card;
-
-                               card->wandev.piggyback = WANOPT_YES;
-
-                               /* We must initialise the piggiback spin lock here
-                                * since isr will try to lock card->next if it
-                                * exists */
-                               spin_lock_init(&card->wandev.lock);
-
-                               unlock_adapter_irq(&nxt_card->wandev.lock,&smp_flags);
-
-                       }else{
-                               /* Trying to run piggibacking with a wrong protocol */
-                               printk(KERN_INFO "%s: ERROR: Resource busy: CPU %c PCISLOT %i\n"
-                                                "%s:        This protocol doesn't support\n"
-                                                "%s:        multi-port operation!\n",
-                                                card->devname,
-                                                conf->S514_CPU_no[0],conf->PCI_slot_no,
-                                                card->devname,card->devname);
-                               return -EEXIST;
-                       }
-               }
-       }
-
-       return 0;
-}
-
-
-
-/*============================================================================
- * Shut down WAN link driver. 
- * o shut down adapter hardware
- * o release system resources.
- *
- * This function is called by the router when device is being unregistered or
- * when it handles ROUTER_DOWN IOCTL.
- */
-static int shutdown(struct wan_device* wandev)
-{
-       sdla_t *card;
-       int err=0;
-       
-       /* sanity checks */
-       if ((wandev == NULL) || (wandev->private == NULL)){
-               return -EFAULT;
-       }
-               
-       if (wandev->state == WAN_UNCONFIGURED){
-               return 0;
-       }
-
-       card = wandev->private;
-
-       if (card->tty_opt){
-               if (card->tty_open){
-                       printk(KERN_INFO 
-                               "%s: Shutdown Failed: TTY is still open\n",
-                                 card->devname);
-                       return -EBUSY;
-               }
-       }
-       
-       wandev->state = WAN_UNCONFIGURED;
-
-       set_bit(PERI_CRIT,(void*)&wandev->critical);
-       
-       /* In case of piggibacking, make sure that 
-         * we never try to shutdown both devices at the same
-         * time, because they depend on one another */
-       
-       if (card->disable_comm){
-               card->disable_comm(card);
-       }
-
-       /* Release Resources */
-       release_hw(card);
-
-        /* only free the allocated I/O range if not an S514 adapter */
-       if (wandev->hw_opt[0] != SDLA_S514 && !card->configured){
-               release_region(card->hw.port, card->hw.io_range);
-       }
-
-       if (!card->configured){
-               memset(&card->hw, 0, sizeof(sdlahw_t));
-               if (card->next){
-                       memset(&card->next->hw, 0, sizeof(sdlahw_t));
-               }
-       }
-       
-
-       clear_bit(PERI_CRIT,(void*)&wandev->critical);
-       return err;
-}
-
-static void release_hw (sdla_t *card)
-{
-       sdla_t *nxt_card;
-
-       
-       /* Check if next device exists */
-       if (card->next){
-               nxt_card = card->next;
-               /* If next device is down then release resources */
-               if (nxt_card->wandev.state == WAN_UNCONFIGURED){
-                       if (card->wandev.piggyback){
-                               /* If this device is piggyback then use
-                                 * information of the master device 
-                                */
-                               printk(KERN_INFO "%s: Piggyback shutting down\n",card->devname);
-                               sdla_down(&card->next->hw);
-                                       free_irq(card->wandev.irq, card->next);
-                               card->configured = 0;
-                               card->next->configured = 0;
-                               card->wandev.piggyback = 0;
-                       }else{
-                               /* Master device shutting down */
-                               printk(KERN_INFO "%s: Master shutting down\n",card->devname);
-                               sdla_down(&card->hw);
-                               free_irq(card->wandev.irq, card);
-                               card->configured = 0;
-                               card->next->configured = 0;
-                       }
-               }else{
-                       printk(KERN_INFO "%s: Device still running %i\n",
-                               nxt_card->devname,nxt_card->wandev.state);
-
-                       card->configured = 1;
-               }
-       }else{
-               printk(KERN_INFO "%s: Master shutting down\n",card->devname);
-               sdla_down(&card->hw);
-                       free_irq(card->wandev.irq, card);
-               card->configured = 0;
-       }
-       return;
-}
-
-
-/*============================================================================
- * Driver I/O control. 
- * o verify arguments
- * o perform requested action
- *
- * This function is called when router handles one of the reserved user
- * IOCTLs.  Note that 'arg' stil points to user address space.
- */
-static int ioctl(struct wan_device* wandev, unsigned cmd, unsigned long arg)
-{
-       sdla_t* card;
-       int err;
-
-       /* sanity checks */
-       if ((wandev == NULL) || (wandev->private == NULL))
-               return -EFAULT;
-       if (wandev->state == WAN_UNCONFIGURED)
-               return -ENODEV;
-
-       card = wandev->private;
-
-       if(card->hw.type != SDLA_S514){
-               disable_irq(card->hw.irq);
-       }
-
-       if (test_bit(SEND_CRIT, (void*)&wandev->critical)) {
-               return -EAGAIN;
-       }
-       
-       switch (cmd) {
-       case WANPIPE_DUMP:
-               err = ioctl_dump(wandev->private, (void*)arg);
-               break;
-
-       case WANPIPE_EXEC:
-               err = ioctl_exec(wandev->private, (void*)arg, cmd);
-               break;
-       default:
-               err = -EINVAL;
-       }
-       return err;
-}
-
-/****** Driver IOCTL Handlers ***********************************************/
-
-/*============================================================================
- * Dump adapter memory to user buffer.
- * o verify request structure
- * o copy request structure to kernel data space
- * o verify length/offset
- * o verify user buffer
- * o copy adapter memory image to user buffer
- *
- * Note: when dumping memory, this routine switches curent dual-port memory
- *      vector, so care must be taken to avoid racing conditions.
- */
-static int ioctl_dump (sdla_t* card, sdla_dump_t* u_dump)
-{
-       sdla_dump_t dump;
-       unsigned winsize;
-       unsigned long oldvec;   /* DPM window vector */
-       unsigned long smp_flags;
-       int err = 0;
-
-       if(copy_from_user((void*)&dump, (void*)u_dump, sizeof(sdla_dump_t)))
-               return -EFAULT;
-               
-       if ((dump.magic != WANPIPE_MAGIC) ||
-           (dump.offset + dump.length > card->hw.memory))
-               return -EINVAL;
-       
-       winsize = card->hw.dpmsize;
-
-       if(card->hw.type != SDLA_S514) {
-
-               lock_adapter_irq(&card->wandev.lock, &smp_flags);
-               
-                oldvec = card->hw.vector;
-                while (dump.length) {
-                       /* current offset */                            
-                        unsigned pos = dump.offset % winsize;
-                       /* current vector */
-                        unsigned long vec = dump.offset - pos;
-                        unsigned len = (dump.length > (winsize - pos)) ?
-                               (winsize - pos) : dump.length;
-                       /* relocate window */
-                        if (sdla_mapmem(&card->hw, vec) != 0) {
-                                err = -EIO;
-                                break;
-                        }
-                       
-                        if(copy_to_user((void *)dump.ptr,
-                                (u8 *)card->hw.dpmbase + pos, len)){ 
-                               
-                               unlock_adapter_irq(&card->wandev.lock, &smp_flags);
-                               return -EFAULT;
-                       }
-
-                        dump.length     -= len;
-                        dump.offset     += len;
-                        dump.ptr         = (char*)dump.ptr + len;
-                }
-               
-                sdla_mapmem(&card->hw, oldvec);/* restore DPM window position */
-               unlock_adapter_irq(&card->wandev.lock, &smp_flags);
-        
-       }else {
-
-               if(copy_to_user((void *)dump.ptr,
-                              (u8 *)card->hw.dpmbase + dump.offset, dump.length)){
-                       return -EFAULT;
-               }
-       }
-
-       return err;
-}
-
-/*============================================================================
- * Execute adapter firmware command.
- * o verify request structure
- * o copy request structure to kernel data space
- * o call protocol-specific 'exec' function
- */
-static int ioctl_exec (sdla_t* card, sdla_exec_t* u_exec, int cmd)
-{
-       sdla_exec_t exec;
-       int err=0;
-
-       if (card->exec == NULL && cmd == WANPIPE_EXEC){
-               return -ENODEV;
-       }
-
-       if(copy_from_user((void*)&exec, (void*)u_exec, sizeof(sdla_exec_t)))
-               return -EFAULT;
-
-       if ((exec.magic != WANPIPE_MAGIC) || (exec.cmd == NULL))
-               return -EINVAL;
-
-       switch (cmd) {
-               case WANPIPE_EXEC:      
-                       err = card->exec(card, exec.cmd, exec.data);
-                       break;
-       }       
-       return err;
-}
-
-/******* Miscellaneous ******************************************************/
-
-/*============================================================================
- * SDLA Interrupt Service Routine.
- * o acknowledge SDLA hardware interrupt.
- * o call protocol-specific interrupt service routine, if any.
- */
-STATIC irqreturn_t sdla_isr (int irq, void* dev_id, struct pt_regs *regs)
-{
-#define        card    ((sdla_t*)dev_id)
-
-       if(card->hw.type == SDLA_S514) {        /* handle interrrupt on S514 */
-                u32 int_status;
-                unsigned char CPU_no = card->hw.S514_cpu_no[0];
-                unsigned char card_found_for_IRQ;
-               u8 IRQ_count = 0;
-
-               for(;;) {
-
-                       read_S514_int_stat(&card->hw, &int_status);
-
-                       /* check if the interrupt is for this device */
-                       if(!((unsigned char)int_status &
-                               (IRQ_CPU_A | IRQ_CPU_B)))
-                               return IRQ_HANDLED;
-
-                       /* if the IRQ is for both CPUs on the same adapter, */
-                       /* then alter the interrupt status so as to handle */
-                       /* one CPU at a time */
-                       if(((unsigned char)int_status & (IRQ_CPU_A | IRQ_CPU_B))
-                               == (IRQ_CPU_A | IRQ_CPU_B)) {
-                               int_status &= (CPU_no == S514_CPU_A) ?
-                                       ~IRQ_CPU_B : ~IRQ_CPU_A;
-                       }
-                       card_found_for_IRQ = 0;
-
-                       /* check to see that the CPU number for this device */
-                       /* corresponds to the interrupt status read */
-                       switch (CPU_no) {
-                               case S514_CPU_A:
-                                       if((unsigned char)int_status &
-                                               IRQ_CPU_A)
-                                        card_found_for_IRQ = 1;
-                                break;
-
-                               case S514_CPU_B:
-                                       if((unsigned char)int_status &
-                                               IRQ_CPU_B)
-                                        card_found_for_IRQ = 1;
-                                break;
-                       }
-
-                       /* exit if the interrupt is for another CPU on the */
-                       /* same IRQ */
-                       if(!card_found_for_IRQ)
-                               return IRQ_HANDLED;
-
-                               if (!card || 
-                          (card->wandev.state == WAN_UNCONFIGURED && !card->configured)){
-                                       printk(KERN_INFO
-                                               "Received IRQ %d for CPU #%c\n",
-                                               irq, CPU_no);
-                                       printk(KERN_INFO
-                                               "IRQ for unconfigured adapter\n");
-                                       S514_intack(&card->hw, int_status);
-                                       return IRQ_HANDLED;
-                               }
-
-                       if (card->in_isr) {
-                               printk(KERN_INFO
-                                       "%s: interrupt re-entrancy on IRQ %d\n",
-                                               card->devname, card->wandev.irq);
-                               S514_intack(&card->hw, int_status);
-                               return IRQ_HANDLED;
-                               }
-
-                       spin_lock(&card->wandev.lock);
-                       if (card->next){
-                               spin_lock(&card->next->wandev.lock);
-                       }
-                               
-                       S514_intack(&card->hw, int_status);
-                               if (card->isr)
-                               card->isr(card);
-
-                       if (card->next){
-                               spin_unlock(&card->next->wandev.lock);
-                       }
-                       spin_unlock(&card->wandev.lock);
-
-                       /* handle a maximum of two interrupts (one for each */
-                       /* CPU on the adapter) before returning */  
-                       if((++ IRQ_count) == 2)
-                               return IRQ_HANDLED;
-               }
-       }
-
-       else {                  /* handle interrupt on S508 adapter */
-
-               if (!card || ((card->wandev.state == WAN_UNCONFIGURED) && !card->configured))
-                       return IRQ_HANDLED;
-
-               if (card->in_isr) {
-                       printk(KERN_INFO
-                               "%s: interrupt re-entrancy on IRQ %d!\n",
-                               card->devname, card->wandev.irq);
-                       return IRQ_HANDLED;
-               }
-
-               spin_lock(&card->wandev.lock);
-               if (card->next){
-                       spin_lock(&card->next->wandev.lock);
-               }
-       
-               sdla_intack(&card->hw);
-               if (card->isr)
-                       card->isr(card);
-               
-               if (card->next){
-                       spin_unlock(&card->next->wandev.lock);
-               }
-               spin_unlock(&card->wandev.lock);
-
-       }
-        return IRQ_HANDLED;
-#undef card
-}
-
-/*============================================================================
- * This routine is called by the protocol-specific modules when network
- * interface is being open.  The only reason we need this, is because we
- * have to call MOD_INC_USE_COUNT, but cannot include 'module.h' where it's
- * defined more than once into the same kernel module.
- */
-void wanpipe_open (sdla_t* card)
-{
-       ++card->open_cnt;
-}
-
-/*============================================================================
- * This routine is called by the protocol-specific modules when network
- * interface is being closed.  The only reason we need this, is because we
- * have to call MOD_DEC_USE_COUNT, but cannot include 'module.h' where it's
- * defined more than once into the same kernel module.
- */
-void wanpipe_close (sdla_t* card)
-{
-       --card->open_cnt;
-}
-
-/*============================================================================
- * Set WAN device state.
- */
-void wanpipe_set_state (sdla_t* card, int state)
-{
-       if (card->wandev.state != state) {
-               switch (state) {
-               case WAN_CONNECTED:
-                       printk (KERN_INFO "%s: link connected!\n",
-                               card->devname);
-                       break;
-
-               case WAN_CONNECTING:
-                       printk (KERN_INFO "%s: link connecting...\n",
-                               card->devname);
-                       break;
-
-               case WAN_DISCONNECTED:
-                       printk (KERN_INFO "%s: link disconnected!\n",
-                               card->devname);
-                       break;
-               }
-               card->wandev.state = state;
-       }
-       card->state_tick = jiffies;
-}
-
-sdla_t * wanpipe_find_card (char *name)
-{
-       int cnt;
-       for (cnt = 0; cnt < ncards; ++ cnt) {
-               sdla_t* card = &card_array[cnt];
-               if (!strcmp(card->devname,name))
-                       return card;
-       }
-       return NULL;
-}
-
-sdla_t * wanpipe_find_card_num (int num)
-{
-       if (num < 1 || num > ncards)
-               return NULL;    
-       num--;
-       return &card_array[num];
-}
-
-/*
- * @work_pointer:      work_struct to be done;
- *                     should already have PREPARE_WORK() or
- *                       INIT_WORK() done on it by caller;
- */
-void wanpipe_queue_work (struct work_struct *work_pointer)
-{
-       if (test_and_set_bit(1, (void*)&wanpipe_bh_critical))
-               printk(KERN_INFO "CRITICAL IN QUEUING WORK\n");
-
-       queue_work(wanpipe_wq, work_pointer);
-       clear_bit(1,(void*)&wanpipe_bh_critical);
-}
-
-void wakeup_sk_bh(struct net_device *dev)
-{
-       wanpipe_common_t *chan = dev->priv;
-
-       if (test_bit(0,&chan->common_critical))
-               return;
-       
-       if (chan->sk && chan->tx_timer){
-               chan->tx_timer->expires=jiffies+1;
-               add_timer(chan->tx_timer);
-       }
-}
-
-int change_dev_flags(struct net_device *dev, unsigned flags)
-{
-       struct ifreq if_info;
-       mm_segment_t fs = get_fs();
-       int err;
-
-       memset(&if_info, 0, sizeof(if_info));
-       strcpy(if_info.ifr_name, dev->name);
-       if_info.ifr_flags = flags;      
-
-       set_fs(get_ds());     /* get user space block */ 
-       err = devinet_ioctl(SIOCSIFFLAGS, &if_info);
-       set_fs(fs);
-
-       return err;
-}
-
-unsigned long get_ip_address(struct net_device *dev, int option)
-{
-       
-       struct in_ifaddr *ifaddr;
-       struct in_device *in_dev;
-       unsigned long addr = 0;
-
-       rcu_read_lock();
-       if ((in_dev = __in_dev_get_rcu(dev)) == NULL){
-               goto out;
-       }
-
-       if ((ifaddr = in_dev->ifa_list)== NULL ){
-               goto out;
-       }
-       
-       switch (option){
-
-       case WAN_LOCAL_IP:
-               addr = ifaddr->ifa_local;
-               break;
-       
-       case WAN_POINTOPOINT_IP:
-               addr = ifaddr->ifa_address;
-               break;  
-
-       case WAN_NETMASK_IP:
-               addr = ifaddr->ifa_mask;
-               break;
-
-       case WAN_BROADCAST_IP:
-               addr = ifaddr->ifa_broadcast;
-               break;
-       default:
-               break;
-       }
-
-out:
-       rcu_read_unlock();
-       return addr;
-}      
-
-void add_gateway(sdla_t *card, struct net_device *dev)
-{
-       mm_segment_t oldfs;
-       struct rtentry route;
-       int res;
-
-       memset((char*)&route,0,sizeof(struct rtentry));
-
-       ((struct sockaddr_in *)
-               &(route.rt_dst))->sin_addr.s_addr = 0;
-       ((struct sockaddr_in *)
-               &(route.rt_dst))->sin_family = AF_INET;
-
-       ((struct sockaddr_in *)
-               &(route.rt_genmask))->sin_addr.s_addr = 0;
-       ((struct sockaddr_in *) 
-               &(route.rt_genmask)) ->sin_family = AF_INET;
-
-
-       route.rt_flags = 0;  
-       route.rt_dev = dev->name;
-
-       oldfs = get_fs();
-       set_fs(get_ds());
-       res = ip_rt_ioctl(SIOCADDRT,&route);
-       set_fs(oldfs);
-
-       if (res == 0){
-               printk(KERN_INFO "%s: Gateway added for %s\n",
-                       card->devname,dev->name);
-       }
-
-       return;
-}
-
-MODULE_LICENSE("GPL");
-
-/****** End *********************************************************/
diff --git a/drivers/net/wan/wanpipe_multppp.c b/drivers/net/wan/wanpipe_multppp.c
deleted file mode 100644 (file)
index 812a118..0000000
+++ /dev/null
@@ -1,2358 +0,0 @@
-/*****************************************************************************
-* wanpipe_multppp.c Multi-Port PPP driver module.
-*
-* Authors:     Nenad Corbic <ncorbic@sangoma.com>
-*
-* Copyright:   (c) 1995-2001 Sangoma Technologies Inc.
-*
-*              This program is free software; you can redistribute it and/or
-*              modify it under the terms of the GNU General Public License
-*              as published by the Free Software Foundation; either version
-*              2 of the License, or (at your option) any later version.
-* ============================================================================
-* Dec 15 2000   Updated for 2.4.X kernel
-* Nov 15 2000   Fixed the SyncPPP support for kernels 2.2.16 and higher.
-*              The pppstruct has changed.
-* Jul 13 2000  Using the kernel Syncppp module on top of RAW Wanpipe CHDLC
-*              module.
-*****************************************************************************/
-
-#include <linux/module.h>
-#include <linux/kernel.h>      /* printk(), and other useful stuff */
-#include <linux/stddef.h>      /* offsetof(), etc. */
-#include <linux/errno.h>       /* return codes */
-#include <linux/string.h>      /* inline memset(), etc. */
-#include <linux/slab.h>        /* kmalloc(), kfree() */
-#include <linux/wanrouter.h>   /* WAN router definitions */
-#include <linux/wanpipe.h>     /* WANPIPE common user API definitions */
-#include <linux/if_arp.h>      /* ARPHRD_* defines */
-#include <linux/jiffies.h>     /* time_after() macro */
-
-#include <linux/in.h>          /* sockaddr_in */
-#include <linux/inet.h>        
-#include <linux/if.h>
-#include <asm/byteorder.h>     /* htons(), etc. */
-#include <linux/sdlapci.h>
-#include <asm/io.h>
-
-#include <linux/sdla_chdlc.h>          /* CHDLC firmware API definitions */
-#include <linux/sdla_asy.h>            /* CHDLC (async) API definitions */
-
-#include <linux/if_wanpipe_common.h>    /* Socket Driver common area */
-#include <linux/if_wanpipe.h>          
-
-
-#include <linux/inetdevice.h>
-#include <asm/uaccess.h>
-
-#include <net/syncppp.h>
-
-
-/****** Defines & Macros ****************************************************/
-
-#ifdef _DEBUG_
-#define        STATIC
-#else
-#define        STATIC          static
-#endif
-
-/* reasons for enabling the timer interrupt on the adapter */
-#define TMR_INT_ENABLED_UDP    0x01
-#define TMR_INT_ENABLED_UPDATE 0x02
-#define TMR_INT_ENABLED_CONFIG  0x04
-#define        CHDLC_DFLT_DATA_LEN     1500            /* default MTU */
-#define CHDLC_HDR_LEN          1
-
-#define IFF_POINTTOPOINT 0x10
-
-#define CHDLC_API 0x01
-
-#define PORT(x)   (x == 0 ? "PRIMARY" : "SECONDARY" )
-#define MAX_BH_BUFF    10
-
-#define CRC_LENGTH     2 
-#define PPP_HEADER_LEN         4
-/******Data Structures*****************************************************/
-
-/* This structure is placed in the private data area of the device structure.
- * The card structure used to occupy the private area but now the following 
- * structure will incorporate the card structure along with CHDLC specific data
- */
-
-typedef struct chdlc_private_area
-{
-       void *if_ptr;                           /* General Pointer used by SPPP */
-       wanpipe_common_t common;
-       sdla_t          *card;
-       int             TracingEnabled;         /* For enabling Tracing */
-       unsigned long   curr_trace_addr;        /* Used for Tracing */
-       unsigned long   start_trace_addr;
-       unsigned long   end_trace_addr;
-       unsigned long   base_addr_trace_buffer;
-       unsigned long   end_addr_trace_buffer;
-       unsigned short  number_trace_elements;
-       unsigned        available_buffer_space;
-       unsigned long   router_start_time;
-       unsigned char   route_status;
-       unsigned char   route_removed;
-       unsigned long   tick_counter;           /* For 5s timeout counter */
-       unsigned long   router_up_time;
-        u32             IP_address;            /* IP addressing */
-        u32             IP_netmask;
-       unsigned char  mc;                      /* Mulitcast support on/off */
-       unsigned short udp_pkt_lgth;            /* udp packet processing */
-       char udp_pkt_src;
-       char udp_pkt_data[MAX_LGTH_UDP_MGNT_PKT];
-       unsigned short timer_int_enabled;
-       char update_comms_stats;                /* updating comms stats */
-
-       //FIXME: add driver stats as per frame relay!
-
-} chdlc_private_area_t;
-
-/* Route Status options */
-#define NO_ROUTE       0x00
-#define ADD_ROUTE      0x01
-#define ROUTE_ADDED    0x02
-#define REMOVE_ROUTE   0x03
-
-
-/* variable for keeping track of enabling/disabling FT1 monitor status */
-static int rCount = 0;
-
-/* variable for tracking how many interfaces to open for WANPIPE on the
-   two ports */
-
-extern void disable_irq(unsigned int);
-extern void enable_irq(unsigned int);
-
-/****** Function Prototypes *************************************************/
-/* WAN link driver entry points. These are called by the WAN router module. */
-static int update(struct wan_device* wandev);
-static int new_if(struct wan_device* wandev, struct net_device* dev,
-                 wanif_conf_t* conf);
-static int del_if(struct wan_device* wandev, struct net_device* dev);
-
-/* Network device interface */
-static int if_init(struct net_device* dev);
-static int if_open(struct net_device* dev);
-static int if_close(struct net_device* dev);
-static int if_send(struct sk_buff* skb, struct net_device* dev);
-static struct net_device_stats* if_stats(struct net_device* dev);
-
-static void if_tx_timeout(struct net_device *dev);
-
-/* CHDLC Firmware interface functions */
-static int chdlc_configure     (sdla_t* card, void* data);
-static int chdlc_comm_enable   (sdla_t* card);
-static int chdlc_comm_disable  (sdla_t* card);
-static int chdlc_read_version  (sdla_t* card, char* str);
-static int chdlc_set_intr_mode         (sdla_t* card, unsigned mode);
-static int chdlc_send (sdla_t* card, void* data, unsigned len);
-static int chdlc_read_comm_err_stats (sdla_t* card);
-static int chdlc_read_op_stats (sdla_t* card);
-static int config_chdlc (sdla_t *card);
-
-
-/* Miscellaneous CHDLC Functions */
-static int set_chdlc_config (sdla_t* card);
-static void init_chdlc_tx_rx_buff(sdla_t* card, struct net_device *dev);
-static int chdlc_error (sdla_t *card, int err, CHDLC_MAILBOX_STRUCT *mb);
-static int process_chdlc_exception(sdla_t *card);
-static int process_global_exception(sdla_t *card);
-static int update_comms_stats(sdla_t* card,
-        chdlc_private_area_t* chdlc_priv_area);
-static void port_set_state (sdla_t *card, int);
-
-/* Interrupt handlers */
-static void wsppp_isr (sdla_t* card);
-static void rx_intr (sdla_t* card);
-static void timer_intr(sdla_t *);
-
-/* Miscellaneous functions */
-static int reply_udp( unsigned char *data, unsigned int mbox_len );
-static int intr_test( sdla_t* card);
-static int udp_pkt_type( struct sk_buff *skb , sdla_t* card);
-static int store_udp_mgmt_pkt(char udp_pkt_src, sdla_t* card,
-                             struct sk_buff *skb, struct net_device* dev,
-                             chdlc_private_area_t* chdlc_priv_area);
-static int process_udp_mgmt_pkt(sdla_t* card, struct net_device* dev,  
-                               chdlc_private_area_t* chdlc_priv_area);
-static unsigned short calc_checksum (char *, int);
-static void s508_lock (sdla_t *card, unsigned long *smp_flags);
-static void s508_unlock (sdla_t *card, unsigned long *smp_flags);
-static void send_ppp_term_request(struct net_device *dev);
-
-
-static int  Intr_test_counter;
-/****** Public Functions ****************************************************/
-
-/*============================================================================
- * Cisco HDLC protocol initialization routine.
- *
- * This routine is called by the main WANPIPE module during setup.  At this
- * point adapter is completely initialized and firmware is running.
- *  o read firmware version (to make sure it's alive)
- *  o configure adapter
- *  o initialize protocol-specific fields of the adapter data space.
- *
- * Return:     0       o.k.
- *             < 0     failure.
- */
-int wsppp_init (sdla_t* card, wandev_conf_t* conf)
-{
-       unsigned char port_num;
-       int err;
-       unsigned long max_permitted_baud = 0;
-       SHARED_MEMORY_INFO_STRUCT *flags;
-
-       union
-               {
-               char str[80];
-               } u;
-       volatile CHDLC_MAILBOX_STRUCT* mb;
-       CHDLC_MAILBOX_STRUCT* mb1;
-       unsigned long timeout;
-
-       /* Verify configuration ID */
-       if (conf->config_id != WANCONFIG_MPPP) {
-               printk(KERN_INFO "%s: invalid configuration ID %u!\n",
-                                 card->devname, conf->config_id);
-               return -EINVAL;
-       }
-
-       /* Find out which Port to use */
-       if ((conf->comm_port == WANOPT_PRI) || (conf->comm_port == WANOPT_SEC)){
-               if (card->next){
-
-                       if (conf->comm_port != card->next->u.c.comm_port){
-                               card->u.c.comm_port = conf->comm_port;
-                       }else{
-                               printk(KERN_ERR "%s: ERROR - %s port used!\n",
-                                       card->wandev.name, PORT(conf->comm_port));
-                               return -EINVAL;
-                       }
-               }else{
-                       card->u.c.comm_port = conf->comm_port;
-               }
-       }else{
-               printk(KERN_ERR "%s: ERROR - Invalid Port Selected!\n",
-                                       card->wandev.name);
-               return -EINVAL;
-       }
-       
-
-       /* Initialize protocol-specific fields */
-       if(card->hw.type != SDLA_S514){
-
-               if (card->u.c.comm_port == WANOPT_PRI){ 
-                       card->mbox  = (void *) card->hw.dpmbase;
-               }else{
-                       card->mbox  = (void *) card->hw.dpmbase + 
-                               SEC_BASE_ADDR_MB_STRUCT - PRI_BASE_ADDR_MB_STRUCT;
-               }       
-       }else{ 
-               /* for a S514 adapter, set a pointer to the actual mailbox in the */
-               /* allocated virtual memory area */
-               if (card->u.c.comm_port == WANOPT_PRI){
-                       card->mbox = (void *) card->hw.dpmbase + PRI_BASE_ADDR_MB_STRUCT;
-               }else{
-                       card->mbox = (void *) card->hw.dpmbase + SEC_BASE_ADDR_MB_STRUCT;
-               }       
-       }
-
-       mb = mb1 = card->mbox;
-
-       if (!card->configured){
-
-               /* The board will place an 'I' in the return code to indicate that it is
-               ready to accept commands.  We expect this to be completed in less
-               than 1 second. */
-
-               timeout = jiffies + 1 * HZ;
-               while (mb->return_code != 'I')  /* Wait 1s for board to initialize */
-                       if (time_after(jiffies, timeout)) break;
-
-               if (mb->return_code != 'I') {
-                       printk(KERN_INFO
-                               "%s: Initialization not completed by adapter\n",
-                               card->devname);
-                       printk(KERN_INFO "Please contact Sangoma representative.\n");
-                       return -EIO;
-               }
-       }
-
-       /* Read firmware version.  Note that when adapter initializes, it
-        * clears the mailbox, so it may appear that the first command was
-        * executed successfully when in fact it was merely erased. To work
-        * around this, we execute the first command twice.
-        */
-
-       if (chdlc_read_version(card, u.str))
-               return -EIO;
-
-       printk(KERN_INFO "%s: Running Raw CHDLC firmware v%s\n" 
-                        "%s: for Multi-Port PPP protocol.\n",
-                       card->devname,u.str,card->devname); 
-
-       card->isr                       = &wsppp_isr;
-       card->poll                      = NULL;
-       card->exec                      = NULL;
-       card->wandev.update             = &update;
-       card->wandev.new_if             = &new_if;
-       card->wandev.del_if             = &del_if;
-       card->wandev.udp_port           = conf->udp_port;
-
-       card->wandev.new_if_cnt = 0;
-
-       /* reset the number of times the 'update()' proc has been called */
-       card->u.c.update_call_count = 0;
-       
-       card->wandev.ttl = conf->ttl;
-       card->wandev.interface = conf->interface; 
-
-       if ((card->u.c.comm_port == WANOPT_SEC && conf->interface == WANOPT_V35)&&
-           card->hw.type != SDLA_S514){
-               printk(KERN_INFO "%s: ERROR - V35 Interface not supported on S508 %s port \n",
-                       card->devname, PORT(card->u.c.comm_port));
-               return -EIO;
-       }
-
-
-       card->wandev.clocking = conf->clocking;
-
-       port_num = card->u.c.comm_port;
-
-       /* Setup Port Bps */
-
-       if(card->wandev.clocking) {
-               if((port_num == WANOPT_PRI) || card->u.c.receive_only) {
-                       /* For Primary Port 0 */
-                               max_permitted_baud =
-                               (card->hw.type == SDLA_S514) ?
-                               PRI_MAX_BAUD_RATE_S514 : 
-                               PRI_MAX_BAUD_RATE_S508;
-               }
-               else if(port_num == WANOPT_SEC) {
-                       /* For Secondary Port 1 */
-                        max_permitted_baud =
-                               (card->hw.type == SDLA_S514) ?
-                                SEC_MAX_BAUD_RATE_S514 :
-                                SEC_MAX_BAUD_RATE_S508;
-                        }
-  
-                       if(conf->bps > max_permitted_baud) {
-                               conf->bps = max_permitted_baud;
-                               printk(KERN_INFO "%s: Baud too high!\n",
-                                       card->wandev.name);
-                               printk(KERN_INFO "%s: Baud rate set to %lu bps\n", 
-                                       card->wandev.name, max_permitted_baud);
-                       }
-                             
-                       card->wandev.bps = conf->bps;
-       }else{
-               card->wandev.bps = 0;
-       }
-
-       /* Setup the Port MTU */
-       if((port_num == WANOPT_PRI) || card->u.c.receive_only) {
-
-               /* For Primary Port 0 */
-               card->wandev.mtu =
-                       (conf->mtu >= MIN_LGTH_CHDLC_DATA_CFG) ?
-                       min_t(unsigned int, conf->mtu, PRI_MAX_NO_DATA_BYTES_IN_FRAME) :
-                       CHDLC_DFLT_DATA_LEN;
-       } else if(port_num == WANOPT_SEC) { 
-               /* For Secondary Port 1 */
-               card->wandev.mtu =
-                       (conf->mtu >= MIN_LGTH_CHDLC_DATA_CFG) ?
-                       min_t(unsigned int, conf->mtu, SEC_MAX_NO_DATA_BYTES_IN_FRAME) :
-                       CHDLC_DFLT_DATA_LEN;
-       }
-
-       /* Add on a PPP Header */
-       card->wandev.mtu += PPP_HEADER_LEN;
-
-       /* Set up the interrupt status area */
-       /* Read the CHDLC Configuration and obtain: 
-        *      Ptr to shared memory infor struct
-         * Use this pointer to calculate the value of card->u.c.flags !
-        */
-       mb1->buffer_length = 0;
-       mb1->command = READ_CHDLC_CONFIGURATION;
-       err = sdla_exec(mb1) ? mb1->return_code : CMD_TIMEOUT;
-       if(err != COMMAND_OK) {
-               clear_bit(1, (void*)&card->wandev.critical);
-
-                if(card->hw.type != SDLA_S514)
-                       enable_irq(card->hw.irq);
-
-               chdlc_error(card, err, mb1);
-               return -EIO;
-       }
-
-       if(card->hw.type == SDLA_S514){
-                       card->u.c.flags = (void *)(card->hw.dpmbase +
-                               (((CHDLC_CONFIGURATION_STRUCT *)mb1->data)->
-                       ptr_shared_mem_info_struct));
-        }else{
-                card->u.c.flags = (void *)(card->hw.dpmbase +
-                        (((CHDLC_CONFIGURATION_STRUCT *)mb1->data)->
-                       ptr_shared_mem_info_struct % SDLA_WINDOWSIZE));
-       }
-       
-       flags = card->u.c.flags;
-       
-       /* This is for the ports link state */
-       card->wandev.state = WAN_DUALPORT;
-       card->u.c.state = WAN_DISCONNECTED;
-
-
-       if (!card->wandev.piggyback){
-               err = intr_test(card);
-
-               if(err || (Intr_test_counter < MAX_INTR_TEST_COUNTER)) { 
-                       printk(KERN_ERR "%s: Interrupt test failed (%i)\n",
-                                       card->devname, Intr_test_counter);
-                       printk(KERN_ERR "%s: Please choose another interrupt\n",
-                                       card->devname);
-                       return  -EIO;
-               }
-                       
-               printk(KERN_INFO "%s: Interrupt test passed (%i)\n", 
-                               card->devname, Intr_test_counter);
-       }
-
-
-       if (chdlc_set_intr_mode(card, APP_INT_ON_TIMER)){
-               printk (KERN_INFO "%s: Failed to set interrupt triggers!\n",
-                               card->devname);
-               return -EIO;    
-        }
-       
-       /* Mask the Timer interrupt */
-       flags->interrupt_info_struct.interrupt_permission &= 
-               ~APP_INT_ON_TIMER;
-
-       printk(KERN_INFO "\n");
-
-       return 0;
-}
-
-/******* WAN Device Driver Entry Points *************************************/
-
-/*============================================================================
- * Update device status & statistics
- * This procedure is called when updating the PROC file system and returns
- * various communications statistics. These statistics are accumulated from 3 
- * different locations:
- *     1) The 'if_stats' recorded for the device.
- *     2) Communication error statistics on the adapter.
- *      3) CHDLC operational statistics on the adapter.
- * The board level statistics are read during a timer interrupt. Note that we 
- * read the error and operational statistics during consecitive timer ticks so
- * as to minimize the time that we are inside the interrupt handler.
- *
- */
-static int update(struct wan_device* wandev)
-{
-       sdla_t* card = wandev->private;
-       struct net_device* dev;
-        volatile chdlc_private_area_t* chdlc_priv_area;
-        SHARED_MEMORY_INFO_STRUCT *flags;
-       unsigned long timeout;
-
-       /* sanity checks */
-       if((wandev == NULL) || (wandev->private == NULL))
-               return -EFAULT;
-       
-       if(wandev->state == WAN_UNCONFIGURED)
-               return -ENODEV;
-
-       /* more sanity checks */
-        if(!card->u.c.flags)
-                return -ENODEV;
-
-       if((dev=card->wandev.dev) == NULL)
-               return -ENODEV;
-
-       if((chdlc_priv_area=dev->priv) == NULL)
-               return -ENODEV;
-
-       flags = card->u.c.flags;
-
-               if(chdlc_priv_area->update_comms_stats){
-               return -EAGAIN;
-       }
-                       
-       /* we will need 2 timer interrupts to complete the */
-       /* reading of the statistics */
-       chdlc_priv_area->update_comms_stats = 2;
-               flags->interrupt_info_struct.interrupt_permission |= APP_INT_ON_TIMER;
-       chdlc_priv_area->timer_int_enabled = TMR_INT_ENABLED_UPDATE;
-  
-       /* wait a maximum of 1 second for the statistics to be updated */ 
-        timeout = jiffies + 1 * HZ;
-        for(;;) {
-               if(chdlc_priv_area->update_comms_stats == 0)
-                       break;
-                if (time_after(jiffies, timeout)){
-                       chdlc_priv_area->update_comms_stats = 0;
-                       chdlc_priv_area->timer_int_enabled &=
-                               ~TMR_INT_ENABLED_UPDATE; 
-                       return -EAGAIN;
-               }
-        }
-
-       return 0;
-}
-
-
-/*============================================================================
- * Create new logical channel.
- * This routine is called by the router when ROUTER_IFNEW IOCTL is being
- * handled.
- * o parse media- and hardware-specific configuration
- * o make sure that a new channel can be created
- * o allocate resources, if necessary
- * o prepare network device structure for registaration.
- *
- * Return:     0       o.k.
- *             < 0     failure (channel will not be created)
- */
-static int new_if(struct wan_device* wandev, struct net_device* pdev,
-                 wanif_conf_t* conf)
-{
-
-       struct ppp_device *pppdev = (struct ppp_device *)pdev;
-       struct net_device *dev = NULL;
-       struct sppp *sp;
-       sdla_t* card = wandev->private;
-       chdlc_private_area_t* chdlc_priv_area;
-       
-       if ((conf->name[0] == '\0') || (strlen(conf->name) > WAN_IFNAME_SZ)) {
-               printk(KERN_INFO "%s: invalid interface name!\n",
-                       card->devname);
-               return -EINVAL;
-       }
-               
-       /* allocate and initialize private data */
-       chdlc_priv_area = kmalloc(sizeof(chdlc_private_area_t), GFP_KERNEL);
-       
-       if(chdlc_priv_area == NULL) 
-               return -ENOMEM;
-
-       memset(chdlc_priv_area, 0, sizeof(chdlc_private_area_t));
-
-       chdlc_priv_area->card = card; 
-
-       /* initialize data */
-       strcpy(card->u.c.if_name, conf->name);
-
-       if(card->wandev.new_if_cnt > 0) {
-                kfree(chdlc_priv_area);
-               return -EEXIST;
-       }
-
-       card->wandev.new_if_cnt++;
-
-       chdlc_priv_area->TracingEnabled = 0;
-
-       //We don't need this any more
-       chdlc_priv_area->route_status = NO_ROUTE;
-       chdlc_priv_area->route_removed = 0;
-
-       printk(KERN_INFO "%s: Firmware running in HDLC STREAMING Mode\n",
-               wandev->name);
-       
-       /* Setup wanpipe as a router (WANPIPE) or as an API */
-       if( strcmp(conf->usedby, "WANPIPE") == 0) {
-               printk(KERN_INFO "%s: Driver running in WANPIPE mode!\n",
-                       wandev->name);
-               card->u.c.usedby = WANPIPE;
-       } else {
-               printk(KERN_INFO 
-                       "%s: API Mode is not supported for SyncPPP!\n",
-                       wandev->name);
-               kfree(chdlc_priv_area);
-               return -EINVAL;
-       }
-
-       /* Get Multicast Information */
-       chdlc_priv_area->mc = conf->mc;
-
-
-       chdlc_priv_area->if_ptr = pppdev;
-
-       /* prepare network device data space for registration */
-
-       strcpy(dev->name,card->u.c.if_name);
-
-       /* Attach PPP protocol layer to pppdev
-        * The sppp_attach() will initilize the dev structure
-         * and setup ppp layer protocols.
-         * All we have to do is to bind in:
-         *        if_open(), if_close(), if_send() and get_stats() functions.
-         */
-       sppp_attach(pppdev);
-       dev = pppdev->dev;
-       sp = &pppdev->sppp;
-       
-       /* Enable PPP Debugging */
-       // FIXME Fix this up somehow
-       //sp->pp_flags |= PP_DEBUG;     
-       sp->pp_flags &= ~PP_CISCO;
-
-       dev->init = &if_init;
-       dev->priv = chdlc_priv_area;
-       
-       return 0;
-}
-
-
-
-
-/*============================================================================
- * Delete logical channel.
- */
-static int del_if(struct wan_device* wandev, struct net_device* dev)
-{
-       chdlc_private_area_t *chdlc_priv_area = dev->priv;
-       sdla_t *card = chdlc_priv_area->card;
-       unsigned long smp_lock;
-       
-       /* Detach the PPP layer */
-       printk(KERN_INFO "%s: Detaching SyncPPP Module from %s\n",
-                       wandev->name,dev->name);
-
-       lock_adapter_irq(&wandev->lock,&smp_lock);
-
-       sppp_detach(dev);
-       chdlc_priv_area->if_ptr=NULL;
-       
-       chdlc_set_intr_mode(card, 0);
-       if (card->u.c.comm_enabled)
-               chdlc_comm_disable(card);
-       unlock_adapter_irq(&wandev->lock,&smp_lock);
-       
-       port_set_state(card, WAN_DISCONNECTED);
-
-       return 0;
-}
-
-
-/****** Network Device Interface ********************************************/
-
-/*============================================================================
- * Initialize Linux network interface.
- *
- * This routine is called only once for each interface, during Linux network
- * interface registration.  Returning anything but zero will fail interface
- * registration.
- */
-static int if_init(struct net_device* dev)
-{
-       chdlc_private_area_t* chdlc_priv_area = dev->priv;
-       sdla_t* card = chdlc_priv_area->card;
-       struct wan_device* wandev = &card->wandev;
-       
-       /* NOTE: Most of the dev initialization was
-         *       done in sppp_attach(), called by new_if() 
-         *       function. All we have to do here is
-         *       to link four major routines below. 
-         */
-
-       /* Initialize device driver entry points */
-       dev->open               = &if_open;
-       dev->stop               = &if_close;
-       dev->hard_start_xmit    = &if_send;
-       dev->get_stats          = &if_stats;
-       dev->tx_timeout         = &if_tx_timeout;
-       dev->watchdog_timeo     = TX_TIMEOUT;
-
-
-       /* Initialize hardware parameters */
-       dev->irq        = wandev->irq;
-       dev->dma        = wandev->dma;
-       dev->base_addr  = wandev->ioport;
-       dev->mem_start  = wandev->maddr;
-       dev->mem_end    = wandev->maddr + wandev->msize - 1;
-
-       /* Set transmit buffer queue length 
-         * If we over fill this queue the packets will
-         * be droped by the kernel.
-         * sppp_attach() sets this to 10, but
-         * 100 will give us more room at low speeds.
-        */
-        dev->tx_queue_len = 100;
-   
-       return 0;
-}
-
-
-/*============================================================================
- * Handle transmit timeout event from netif watchdog
- */
-static void if_tx_timeout(struct net_device *dev)
-{
-       chdlc_private_area_t* chan = dev->priv;
-       sdla_t *card = chan->card;
-       
-       /* If our device stays busy for at least 5 seconds then we will
-        * kick start the device by making dev->tbusy = 0.  We expect
-        * that our device never stays busy more than 5 seconds. So this                 
-        * is only used as a last resort.
-        */
-
-       ++card->wandev.stats.collisions;
-
-       printk (KERN_INFO "%s: Transmit timed out on %s\n", card->devname,dev->name);
-       netif_wake_queue (dev);
-}
-
-
-/*============================================================================
- * Open network interface.
- * o enable communications and interrupts.
- * o prevent module from unloading by incrementing use count
- *
- * Return 0 if O.k. or errno.
- */
-static int if_open(struct net_device* dev)
-{
-       chdlc_private_area_t* chdlc_priv_area = dev->priv;
-       sdla_t* card = chdlc_priv_area->card;
-       struct timeval tv;
-       SHARED_MEMORY_INFO_STRUCT *flags = card->u.c.flags;
-
-       /* Only one open per interface is allowed */
-       if (netif_running(dev))
-               return -EBUSY;
-
-       /* Start PPP Layer */
-       if (sppp_open(dev)){
-               return -EIO;
-       }
-
-       do_gettimeofday(&tv);
-       chdlc_priv_area->router_start_time = tv.tv_sec;
-       netif_start_queue(dev);
-       
-       wanpipe_open(card);
-
-       chdlc_priv_area->timer_int_enabled |= TMR_INT_ENABLED_CONFIG;
-       flags->interrupt_info_struct.interrupt_permission |= APP_INT_ON_TIMER;
-       return 0;
-}
-
-/*============================================================================
- * Close network interface.
- * o if this is the last close, then disable communications and interrupts.
- * o reset flags.
- */
-static int if_close(struct net_device* dev)
-{
-       chdlc_private_area_t* chdlc_priv_area = dev->priv;
-       sdla_t* card = chdlc_priv_area->card;
-
-       /* Stop the PPP Layer */
-       sppp_close(dev);
-       netif_stop_queue(dev);
-
-       wanpipe_close(card);
-       
-       return 0;
-}
-
-/*============================================================================
- * Send a packet on a network interface.
- * o set tbusy flag (marks start of the transmission) to block a timer-based
- *   transmit from overlapping.
- * o check link state. If link is not up, then drop the packet.
- * o execute adapter send command.
- * o free socket buffer
- *
- * Return:     0       complete (socket buffer must be freed)
- *             non-0   packet may be re-transmitted (tbusy must be set)
- *
- * Notes:
- * 1. This routine is called either by the protocol stack or by the "net
- *    bottom half" (with interrupts enabled).
- * 2. Setting tbusy flag will inhibit further transmit requests from the
- *    protocol stack and can be used for flow control with protocol layer.
- */
-static int if_send(struct sk_buff* skb, struct net_device* dev)
-{
-       chdlc_private_area_t *chdlc_priv_area = dev->priv;
-       sdla_t *card = chdlc_priv_area->card;
-       SHARED_MEMORY_INFO_STRUCT *flags = card->u.c.flags;
-       INTERRUPT_INFORMATION_STRUCT *chdlc_int = &flags->interrupt_info_struct;
-       int udp_type = 0;
-       unsigned long smp_flags;
-       int err=0;
-
-       netif_stop_queue(dev);
-
-       
-       if (skb == NULL){
-               /* If we get here, some higher layer thinks we've missed an
-                * tx-done interrupt.
-                */
-               printk(KERN_INFO "%s: Received NULL skb buffer! interface %s got kicked!\n",
-                       card->devname, dev->name);
-
-               netif_wake_queue(dev);
-               return 0;
-       }
-
-       if (ntohs(skb->protocol) != htons(PVC_PROT)){
-               /* check the udp packet type */
-               
-               udp_type = udp_pkt_type(skb, card);
-               if (udp_type == UDP_CPIPE_TYPE){
-                        if(store_udp_mgmt_pkt(UDP_PKT_FRM_STACK, card, skb, dev,
-                                chdlc_priv_area)){
-                               chdlc_int->interrupt_permission |=
-                                       APP_INT_ON_TIMER;
-                       }
-                       netif_start_queue(dev);
-                       return 0;
-               }
-        }
-
-       /* Lock the 508 Card: SMP is supported */
-       if(card->hw.type != SDLA_S514){
-               s508_lock(card,&smp_flags);
-       } 
-
-       if (test_and_set_bit(SEND_CRIT, (void*)&card->wandev.critical)){
-       
-               printk(KERN_INFO "%s: Critical in if_send: %lx\n",
-                                       card->wandev.name,card->wandev.critical);
-                ++card->wandev.stats.tx_dropped;
-               netif_start_queue(dev);
-               goto if_send_crit_exit;
-       }
-
-       if (card->wandev.state != WAN_CONNECTED){
-               ++card->wandev.stats.tx_dropped;
-               netif_start_queue(dev);
-               goto if_send_crit_exit;
-       }
-       
-       if (chdlc_send(card, skb->data, skb->len)){
-               netif_stop_queue(dev);
-
-       }else{
-               ++card->wandev.stats.tx_packets;
-                       card->wandev.stats.tx_bytes += skb->len;
-               dev->trans_start = jiffies;
-               netif_start_queue(dev);
-       }       
-
-if_send_crit_exit:
-       if (!(err=netif_queue_stopped(dev))){
-                dev_kfree_skb_any(skb);
-       }else{
-               chdlc_priv_area->tick_counter = jiffies;
-               chdlc_int->interrupt_permission |= APP_INT_ON_TX_FRAME;
-       }
-
-       clear_bit(SEND_CRIT, (void*)&card->wandev.critical);
-       if(card->hw.type != SDLA_S514){
-               s508_unlock(card,&smp_flags);
-       }
-
-       return err;
-}
-
-
-/*============================================================================
- * Reply to UDP Management system.
- * Return length of reply.
- */
-static int reply_udp( unsigned char *data, unsigned int mbox_len )
-{
-
-       unsigned short len, udp_length, temp, ip_length;
-       unsigned long ip_temp;
-       int even_bound = 0;
-       chdlc_udp_pkt_t *c_udp_pkt = (chdlc_udp_pkt_t *)data;
-        
-       /* Set length of packet */
-       len = sizeof(ip_pkt_t)+ 
-             sizeof(udp_pkt_t)+
-             sizeof(wp_mgmt_t)+
-             sizeof(cblock_t)+
-             sizeof(trace_info_t)+ 
-             mbox_len;
-
-       /* fill in UDP reply */
-       c_udp_pkt->wp_mgmt.request_reply = UDPMGMT_REPLY;
-   
-       /* fill in UDP length */
-       udp_length = sizeof(udp_pkt_t)+ 
-                    sizeof(wp_mgmt_t)+
-                    sizeof(cblock_t)+
-                    sizeof(trace_info_t)+
-                    mbox_len; 
-
-       /* put it on an even boundary */
-       if ( udp_length & 0x0001 ) {
-               udp_length += 1;
-               len += 1;
-               even_bound = 1;
-       }  
-
-       temp = (udp_length<<8)|(udp_length>>8);
-       c_udp_pkt->udp_pkt.udp_length = temp;
-                
-       /* swap UDP ports */
-       temp = c_udp_pkt->udp_pkt.udp_src_port;
-       c_udp_pkt->udp_pkt.udp_src_port = 
-                       c_udp_pkt->udp_pkt.udp_dst_port; 
-       c_udp_pkt->udp_pkt.udp_dst_port = temp;
-
-       /* add UDP pseudo header */
-       temp = 0x1100;
-       *((unsigned short *)(c_udp_pkt->data+mbox_len+even_bound)) = temp;      
-       temp = (udp_length<<8)|(udp_length>>8);
-       *((unsigned short *)(c_udp_pkt->data+mbox_len+even_bound+2)) = temp;
-
-                
-       /* calculate UDP checksum */
-       c_udp_pkt->udp_pkt.udp_checksum = 0;
-       c_udp_pkt->udp_pkt.udp_checksum = calc_checksum(&data[UDP_OFFSET],udp_length+UDP_OFFSET);
-
-       /* fill in IP length */
-       ip_length = len;
-       temp = (ip_length<<8)|(ip_length>>8);
-       c_udp_pkt->ip_pkt.total_length = temp;
-  
-       /* swap IP addresses */
-       ip_temp = c_udp_pkt->ip_pkt.ip_src_address;
-       c_udp_pkt->ip_pkt.ip_src_address = c_udp_pkt->ip_pkt.ip_dst_address;
-       c_udp_pkt->ip_pkt.ip_dst_address = ip_temp;
-
-       /* fill in IP checksum */
-       c_udp_pkt->ip_pkt.hdr_checksum = 0;
-       c_udp_pkt->ip_pkt.hdr_checksum = calc_checksum(data,sizeof(ip_pkt_t));
-
-       return len;
-
-} /* reply_udp */
-
-unsigned short calc_checksum (char *data, int len)
-{
-       unsigned short temp; 
-       unsigned long sum=0;
-       int i;
-
-       for( i = 0; i <len; i+=2 ) {
-               memcpy(&temp,&data[i],2);
-               sum += (unsigned long)temp;
-       }
-
-       while (sum >> 16 ) {
-               sum = (sum & 0xffffUL) + (sum >> 16);
-       }
-
-       temp = (unsigned short)sum;
-       temp = ~temp;
-
-       if( temp == 0 ) 
-               temp = 0xffff;
-
-       return temp;    
-}
-
-
-/*============================================================================
- * Get ethernet-style interface statistics.
- * Return a pointer to struct enet_statistics.
- */
-static struct net_device_stats* if_stats(struct net_device* dev)
-{
-       sdla_t *my_card;
-       chdlc_private_area_t* chdlc_priv_area;
-
-       /* Shutdown bug fix. In del_if() we kill
-         * dev->priv pointer. This function, gets
-         * called after del_if(), thus check
-         * if pointer has been deleted */
-       if ((chdlc_priv_area=dev->priv) == NULL)
-               return NULL;
-
-       my_card = chdlc_priv_area->card;
-       return &my_card->wandev.stats; 
-}
-
-
-/****** Cisco HDLC Firmware Interface Functions *******************************/
-
-/*============================================================================
- * Read firmware code version.
- *     Put code version as ASCII string in str. 
- */
-static int chdlc_read_version (sdla_t* card, char* str)
-{
-       CHDLC_MAILBOX_STRUCT* mb = card->mbox;
-       int len;
-       char err;
-       mb->buffer_length = 0;
-       mb->command = READ_CHDLC_CODE_VERSION;
-       err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT;
-
-       if(err != COMMAND_OK) {
-               chdlc_error(card,err,mb);
-       }
-       else if (str) {  /* is not null */
-               len = mb->buffer_length;
-               memcpy(str, mb->data, len);
-               str[len] = '\0';
-       }
-       return (err);
-}
-
-/*-----------------------------------------------------------------------------
- *  Configure CHDLC firmware.
- */
-static int chdlc_configure (sdla_t* card, void* data)
-{
-       int err;
-       CHDLC_MAILBOX_STRUCT *mailbox = card->mbox;
-       int data_length = sizeof(CHDLC_CONFIGURATION_STRUCT);
-       
-       mailbox->buffer_length = data_length;  
-       memcpy(mailbox->data, data, data_length);
-       mailbox->command = SET_CHDLC_CONFIGURATION;
-       err = sdla_exec(mailbox) ? mailbox->return_code : CMD_TIMEOUT;
-       
-       if (err != COMMAND_OK) chdlc_error (card, err, mailbox);
-                           
-       return err;
-}
-
-
-/*============================================================================
- * Set interrupt mode -- HDLC Version.
- */
-
-static int chdlc_set_intr_mode (sdla_t* card, unsigned mode)
-{
-       CHDLC_MAILBOX_STRUCT* mb = card->mbox;
-       CHDLC_INT_TRIGGERS_STRUCT* int_data =
-                (CHDLC_INT_TRIGGERS_STRUCT *)mb->data;
-       int err;
-
-       int_data->CHDLC_interrupt_triggers      = mode;
-       int_data->IRQ                           = card->hw.irq;
-       int_data->interrupt_timer               = 1;
-   
-       mb->buffer_length = sizeof(CHDLC_INT_TRIGGERS_STRUCT);
-       mb->command = SET_CHDLC_INTERRUPT_TRIGGERS;
-       err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT;
-       if (err != COMMAND_OK)
-               chdlc_error (card, err, mb);
-       return err;
-}
-
-
-/*============================================================================
- * Enable communications.
- */
-
-static int chdlc_comm_enable (sdla_t* card)
-{
-       int err;
-       CHDLC_MAILBOX_STRUCT* mb = card->mbox;
-
-       mb->buffer_length = 0;
-       mb->command = ENABLE_CHDLC_COMMUNICATIONS;
-       err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT;
-       if (err != COMMAND_OK)
-               chdlc_error(card, err, mb);
-       else
-               card->u.c.comm_enabled=1;
-
-       return err;
-}
-
-/*============================================================================
- * Disable communications and Drop the Modem lines (DCD and RTS).
- */
-static int chdlc_comm_disable (sdla_t* card)
-{
-       int err;
-       CHDLC_MAILBOX_STRUCT* mb = card->mbox;
-
-       mb->buffer_length = 0;
-       mb->command = DISABLE_CHDLC_COMMUNICATIONS;
-       err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT;
-       if (err != COMMAND_OK)
-               chdlc_error(card,err,mb);
-
-       return err;
-}
-
-/*============================================================================
- * Read communication error statistics.
- */
-static int chdlc_read_comm_err_stats (sdla_t* card)
-{
-        int err;
-        CHDLC_MAILBOX_STRUCT* mb = card->mbox;
-
-        mb->buffer_length = 0;
-        mb->command = READ_COMMS_ERROR_STATS;
-        err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT;
-        if (err != COMMAND_OK)
-                chdlc_error(card,err,mb);
-        return err;
-}
-
-
-/*============================================================================
- * Read CHDLC operational statistics.
- */
-static int chdlc_read_op_stats (sdla_t* card)
-{
-        int err;
-        CHDLC_MAILBOX_STRUCT* mb = card->mbox;
-
-        mb->buffer_length = 0;
-        mb->command = READ_CHDLC_OPERATIONAL_STATS;
-        err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT;
-        if (err != COMMAND_OK)
-                chdlc_error(card,err,mb);
-        return err;
-}
-
-
-/*============================================================================
- * Update communications error and general packet statistics.
- */
-static int update_comms_stats(sdla_t* card,
-       chdlc_private_area_t* chdlc_priv_area)
-{
-        CHDLC_MAILBOX_STRUCT* mb = card->mbox;
-       COMMS_ERROR_STATS_STRUCT* err_stats;
-        CHDLC_OPERATIONAL_STATS_STRUCT *op_stats;
-
-       /* on the first timer interrupt, read the comms error statistics */
-       if(chdlc_priv_area->update_comms_stats == 2) {
-               if(chdlc_read_comm_err_stats(card))
-                       return 1;
-               err_stats = (COMMS_ERROR_STATS_STRUCT *)mb->data;
-               card->wandev.stats.rx_over_errors = 
-                               err_stats->Rx_overrun_err_count;
-               card->wandev.stats.rx_crc_errors = 
-                               err_stats->CRC_err_count;
-               card->wandev.stats.rx_frame_errors = 
-                               err_stats->Rx_abort_count;
-               card->wandev.stats.rx_fifo_errors = 
-                               err_stats->Rx_dis_pri_bfrs_full_count; 
-               card->wandev.stats.rx_missed_errors =
-                               card->wandev.stats.rx_fifo_errors;
-               card->wandev.stats.tx_aborted_errors =
-                               err_stats->sec_Tx_abort_count;
-       }
-
-        /* on the second timer interrupt, read the operational statistics */
-       else {
-               if(chdlc_read_op_stats(card))
-                       return 1;
-               op_stats = (CHDLC_OPERATIONAL_STATS_STRUCT *)mb->data;
-               card->wandev.stats.rx_length_errors =
-                       (op_stats->Rx_Data_discard_short_count +
-                       op_stats->Rx_Data_discard_long_count);
-       }
-
-       return 0;
-}
-
-/*============================================================================
- * Send packet.
- *     Return: 0 - o.k.
- *             1 - no transmit buffers available
- */
-static int chdlc_send (sdla_t* card, void* data, unsigned len)
-{
-       CHDLC_DATA_TX_STATUS_EL_STRUCT *txbuf = card->u.c.txbuf;
-
-       if (txbuf->opp_flag)
-               return 1;
-       
-       sdla_poke(&card->hw, txbuf->ptr_data_bfr, data, len);
-
-       txbuf->frame_length = len;
-       txbuf->opp_flag = 1;            /* start transmission */
-       
-       /* Update transmit buffer control fields */
-       card->u.c.txbuf = ++txbuf;
-
-       if ((void*)txbuf > card->u.c.txbuf_last)
-               card->u.c.txbuf = card->u.c.txbuf_base;
-
-       return 0;
-}
-
-/****** Firmware Error Handler **********************************************/
-
-/*============================================================================
- * Firmware error handler.
- *     This routine is called whenever firmware command returns non-zero
- *     return code.
- *
- * Return zero if previous command has to be cancelled.
- */
-static int chdlc_error (sdla_t *card, int err, CHDLC_MAILBOX_STRUCT *mb)
-{
-       unsigned cmd = mb->command;
-
-       switch (err) {
-
-       case CMD_TIMEOUT:
-               printk(KERN_ERR "%s: command 0x%02X timed out!\n",
-                       card->devname, cmd);
-               break;
-
-       case S514_BOTH_PORTS_SAME_CLK_MODE:
-               if(cmd == SET_CHDLC_CONFIGURATION) {
-                       printk(KERN_INFO
-                        "%s: Configure both ports for the same clock source\n",
-                               card->devname);
-                       break;
-               }
-
-       default:
-               printk(KERN_INFO "%s: command 0x%02X returned 0x%02X!\n",
-                       card->devname, cmd, err);
-       }
-
-       return 0;
-}
-
-/****** Interrupt Handlers **************************************************/
-
-/*============================================================================
- * Cisco HDLC interrupt service routine.
- */
-STATIC void wsppp_isr (sdla_t* card)
-{
-       struct net_device* dev;
-       SHARED_MEMORY_INFO_STRUCT* flags = NULL;
-       int i;
-       sdla_t *my_card;
-
-
-       /* Check for which port the interrupt has been generated
-        * Since Secondary Port is piggybacking on the Primary
-         * the check must be done here. 
-        */
-
-       flags = card->u.c.flags;
-       if (!flags->interrupt_info_struct.interrupt_type){
-               /* Check for a second port (piggybacking) */
-               if((my_card = card->next)){
-                       flags = my_card->u.c.flags;
-                       if (flags->interrupt_info_struct.interrupt_type){
-                               card = my_card;
-                               card->isr(card);
-                               return;
-                       }
-               }
-       }
-
-       dev = card->wandev.dev;
-       card->in_isr = 1;
-       flags = card->u.c.flags;
-               
-       /* If we get an interrupt with no network device, stop the interrupts
-        * and issue an error */
-       if ((!dev || !dev->priv) && flags->interrupt_info_struct.interrupt_type != 
-               COMMAND_COMPLETE_APP_INT_PEND){
-               goto isr_done;
-       }
-
-       
-       /* if critical due to peripheral operations
-        * ie. update() or getstats() then reset the interrupt and
-        * wait for the board to retrigger.
-        */
-       if(test_bit(PERI_CRIT, (void*)&card->wandev.critical)) {
-               flags->interrupt_info_struct.
-                                       interrupt_type = 0;
-               goto isr_done;
-       }
-
-
-       /* On a 508 Card, if critical due to if_send 
-         * Major Error !!!
-        */
-       if(card->hw.type != SDLA_S514) {
-               if(test_bit(0, (void*)&card->wandev.critical)) {
-                       printk(KERN_INFO "%s: Critical while in ISR: %lx\n",
-                               card->devname, card->wandev.critical);
-                       goto isr_done;
-               }
-       }
-
-       switch(flags->interrupt_info_struct.interrupt_type) {
-
-               case RX_APP_INT_PEND:   /* 0x01: receive interrupt */
-                       rx_intr(card);
-                       break;
-
-               case TX_APP_INT_PEND:   /* 0x02: transmit interrupt */
-                       flags->interrupt_info_struct.interrupt_permission &=
-                                ~APP_INT_ON_TX_FRAME;
-
-                       netif_wake_queue(dev);
-                       break;
-
-               case COMMAND_COMPLETE_APP_INT_PEND:/* 0x04: cmd cplt */
-                       ++ Intr_test_counter;
-                       break;
-
-               case CHDLC_EXCEP_COND_APP_INT_PEND:     /* 0x20 */
-                       process_chdlc_exception(card);
-                       break;
-
-               case GLOBAL_EXCEP_COND_APP_INT_PEND:
-                       process_global_exception(card);
-                       break;
-
-               case TIMER_APP_INT_PEND:
-                       timer_intr(card);
-                       break;
-
-               default:
-                       printk(KERN_INFO "%s: spurious interrupt 0x%02X!\n", 
-                               card->devname,
-                               flags->interrupt_info_struct.interrupt_type);
-                       printk(KERN_INFO "Code name: ");
-                       for(i = 0; i < 4; i ++)
-                               printk(KERN_INFO "%c",
-                                       flags->global_info_struct.codename[i]); 
-                       printk(KERN_INFO "\nCode version: ");
-                       for(i = 0; i < 4; i ++)
-                               printk(KERN_INFO "%c", 
-                                       flags->global_info_struct.codeversion[i]); 
-                       printk(KERN_INFO "\n"); 
-                       break;
-       }
-
-isr_done:
-       card->in_isr = 0;
-       flags->interrupt_info_struct.interrupt_type = 0;
-}
-
-/*============================================================================
- * Receive interrupt handler.
- */
-static void rx_intr (sdla_t* card)
-{
-       struct net_device *dev;
-       chdlc_private_area_t *chdlc_priv_area;
-       SHARED_MEMORY_INFO_STRUCT *flags = card->u.c.flags;
-       CHDLC_DATA_RX_STATUS_EL_STRUCT *rxbuf = card->u.c.rxmb;
-       struct sk_buff *skb;
-       unsigned len;
-       unsigned addr = rxbuf->ptr_data_bfr;
-       void *buf;
-       int i,udp_type;
-       
-       if (rxbuf->opp_flag != 0x01) {
-               printk(KERN_INFO 
-                       "%s: corrupted Rx buffer @ 0x%X, flag = 0x%02X!\n", 
-                       card->devname, (unsigned)rxbuf, rxbuf->opp_flag);
-                printk(KERN_INFO "Code name: ");
-                for(i = 0; i < 4; i ++)
-                        printk(KERN_INFO "%c",
-                                flags->global_info_struct.codename[i]);
-                printk(KERN_INFO "\nCode version: ");
-                for(i = 0; i < 4; i ++)
-                        printk(KERN_INFO "%c",
-                                flags->global_info_struct.codeversion[i]);
-                printk(KERN_INFO "\n");
-
-
-               /* Bug Fix: Mar 6 2000
-                 * If we get a corrupted mailbox, it measn that driver 
-                 * is out of sync with the firmware. There is no recovery.
-                 * If we don't turn off all interrupts for this card
-                 * the machine will crash. 
-                 */
-               printk(KERN_INFO "%s: Critical router failure ...!!!\n", card->devname);
-               printk(KERN_INFO "Please contact Sangoma Technologies !\n");
-               chdlc_set_intr_mode(card,0);    
-               return;
-       }
-
-       dev = card->wandev.dev;
-
-       if (!dev){ 
-               goto rx_exit;
-       }
-       
-       if (!netif_running(dev)){
-               goto rx_exit;
-       }
-
-       chdlc_priv_area = dev->priv;
-
-       if (rxbuf->error_flag){ 
-               goto rx_exit;
-       }
-       /* Take off two CRC bytes */
-
-       if (rxbuf->frame_length < 7 || rxbuf->frame_length > 1506 ){
-               goto rx_exit;
-       }       
-
-       len = rxbuf->frame_length - CRC_LENGTH;
-
-       /* Allocate socket buffer */
-       skb = dev_alloc_skb(len);
-
-       if (skb == NULL) {
-               if (net_ratelimit()){
-                       printk(KERN_INFO "%s: no socket buffers available!\n",
-                                               card->devname);
-               }
-               ++card->wandev.stats.rx_dropped;
-               goto rx_exit;
-       }
-
-       /* Copy data to the socket buffer */
-       if((addr + len) > card->u.c.rx_top + 1) {
-               unsigned tmp = card->u.c.rx_top - addr + 1;
-               buf = skb_put(skb, tmp);
-               sdla_peek(&card->hw, addr, buf, tmp);
-               addr = card->u.c.rx_base;
-               len -= tmp;
-       }
-               
-       buf = skb_put(skb, len);
-       sdla_peek(&card->hw, addr, buf, len);
-
-       skb->protocol = htons(ETH_P_WAN_PPP);
-
-       card->wandev.stats.rx_packets ++;
-       card->wandev.stats.rx_bytes += skb->len;
-       udp_type = udp_pkt_type( skb, card );
-
-       if(udp_type == UDP_CPIPE_TYPE) {
-               if(store_udp_mgmt_pkt(UDP_PKT_FRM_NETWORK,
-                                     card, skb, dev, chdlc_priv_area)) {
-                       flags->interrupt_info_struct.
-                                               interrupt_permission |= 
-                                                       APP_INT_ON_TIMER; 
-               }
-       }else{
-                       /* Pass it up the protocol stack */
-                skb->dev = dev;
-                skb->mac.raw  = skb->data;
-                netif_rx(skb);
-                dev->last_rx = jiffies;
-       }
-
-rx_exit:
-       /* Release buffer element and calculate a pointer to the next one */
-       rxbuf->opp_flag = 0x00;
-       card->u.c.rxmb = ++ rxbuf;
-       if((void*)rxbuf > card->u.c.rxbuf_last){
-               card->u.c.rxmb = card->u.c.rxbuf_base;
-       }
-}
-
-/*============================================================================
- * Timer interrupt handler.
- * The timer interrupt is used for two purposes:
- *    1) Processing udp calls from 'cpipemon'.
- *    2) Reading board-level statistics for updating the proc file system.
- */
-void timer_intr(sdla_t *card)
-{
-        struct net_device* dev;
-        chdlc_private_area_t* chdlc_priv_area = NULL;
-        SHARED_MEMORY_INFO_STRUCT* flags = NULL;
-
-        dev = card->wandev.dev; 
-        chdlc_priv_area = dev->priv;
-
-       if (chdlc_priv_area->timer_int_enabled & TMR_INT_ENABLED_CONFIG) {
-               if (!config_chdlc(card)){
-                       chdlc_priv_area->timer_int_enabled &= ~TMR_INT_ENABLED_CONFIG;
-               }
-       }
-       
-       /* process a udp call if pending */
-               if(chdlc_priv_area->timer_int_enabled & TMR_INT_ENABLED_UDP) {
-                       process_udp_mgmt_pkt(card, dev,
-                       chdlc_priv_area);
-               chdlc_priv_area->timer_int_enabled &= ~TMR_INT_ENABLED_UDP;
-        }
-       
-
-       /* read the communications statistics if required */
-       if(chdlc_priv_area->timer_int_enabled & TMR_INT_ENABLED_UPDATE) {
-               update_comms_stats(card, chdlc_priv_area);
-                if(!(-- chdlc_priv_area->update_comms_stats)) {
-                       chdlc_priv_area->timer_int_enabled &= 
-                               ~TMR_INT_ENABLED_UPDATE;
-               }
-        }
-
-       /* only disable the timer interrupt if there are no udp or statistic */
-       /* updates pending */
-        if(!chdlc_priv_area->timer_int_enabled) {
-                flags = card->u.c.flags;
-                flags->interrupt_info_struct.interrupt_permission &=
-                        ~APP_INT_ON_TIMER;
-        }
-}
-
-/*------------------------------------------------------------------------------
-  Miscellaneous Functions
-       - set_chdlc_config() used to set configuration options on the board
-------------------------------------------------------------------------------*/
-
-static int set_chdlc_config(sdla_t* card)
-{
-
-       CHDLC_CONFIGURATION_STRUCT cfg;
-
-       memset(&cfg, 0, sizeof(CHDLC_CONFIGURATION_STRUCT));
-
-       if(card->wandev.clocking)
-               cfg.baud_rate = card->wandev.bps;
-
-       cfg.line_config_options = (card->wandev.interface == WANOPT_RS232) ?
-               INTERFACE_LEVEL_RS232 : INTERFACE_LEVEL_V35;
-
-       cfg.modem_config_options        = 0;
-       //API OPTIONS
-       cfg.CHDLC_API_options           = DISCARD_RX_ERROR_FRAMES;
-       cfg.modem_status_timer          = 100;
-       cfg.CHDLC_protocol_options      = HDLC_STREAMING_MODE;
-       cfg.percent_data_buffer_for_Tx  = 50;
-       cfg.CHDLC_statistics_options    = (CHDLC_TX_DATA_BYTE_COUNT_STAT |
-               CHDLC_RX_DATA_BYTE_COUNT_STAT);
-       cfg.max_CHDLC_data_field_length = card->wandev.mtu;
-
-       cfg.transmit_keepalive_timer    = 0;
-       cfg.receive_keepalive_timer     = 0;
-       cfg.keepalive_error_tolerance   = 0;
-       cfg.SLARP_request_timer         = 0;
-
-       cfg.IP_address          = 0;
-       cfg.IP_netmask          = 0;
-       
-       return chdlc_configure(card, &cfg);
-}
-
-/*============================================================================
- * Process global exception condition
- */
-static int process_global_exception(sdla_t *card)
-{
-       CHDLC_MAILBOX_STRUCT* mbox = card->mbox;
-       int err;
-
-       mbox->buffer_length = 0;
-       mbox->command = READ_GLOBAL_EXCEPTION_CONDITION;
-       err = sdla_exec(mbox) ? mbox->return_code : CMD_TIMEOUT;
-
-       if(err != CMD_TIMEOUT ){
-       
-               switch(mbox->return_code) {
-         
-               case EXCEP_MODEM_STATUS_CHANGE:
-
-                       printk(KERN_INFO "%s: Modem status change\n",
-                               card->devname);
-
-                       switch(mbox->data[0] & (DCD_HIGH | CTS_HIGH)) {
-                               case (DCD_HIGH):
-                                       printk(KERN_INFO "%s: DCD high, CTS low\n",card->devname);
-                                       break;
-                               case (CTS_HIGH):
-                                        printk(KERN_INFO "%s: DCD low, CTS high\n",card->devname);
-                                        break;
-                                case ((DCD_HIGH | CTS_HIGH)):
-                                        printk(KERN_INFO "%s: DCD high, CTS high\n",card->devname);
-                                        break;
-                               default:
-                                        printk(KERN_INFO "%s: DCD low, CTS low\n",card->devname);
-                                        break;
-                       }
-
-                       if (!(mbox->data[0] & DCD_HIGH) || !(mbox->data[0] & DCD_HIGH)){
-                               //printk(KERN_INFO "Sending TERM Request Manually !\n");
-                               send_ppp_term_request(card->wandev.dev);
-                       }       
-                       break;
-
-                case EXCEP_TRC_DISABLED:
-                        printk(KERN_INFO "%s: Line trace disabled\n",
-                               card->devname);
-                        break;
-
-               case EXCEP_IRQ_TIMEOUT:
-                       printk(KERN_INFO "%s: IRQ timeout occurred\n",
-                               card->devname); 
-                       break;
-
-                default:
-                        printk(KERN_INFO "%s: Global exception %x\n",
-                               card->devname, mbox->return_code);
-                        break;
-                }
-       }
-       return 0;
-}
-
-
-/*============================================================================
- * Process chdlc exception condition
- */
-static int process_chdlc_exception(sdla_t *card)
-{
-       CHDLC_MAILBOX_STRUCT* mb = card->mbox;
-       int err;
-
-       mb->buffer_length = 0;
-       mb->command = READ_CHDLC_EXCEPTION_CONDITION;
-       err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT;
-       if(err != CMD_TIMEOUT) {
-       
-               switch (err) {
-
-               case EXCEP_LINK_ACTIVE:
-                       port_set_state(card, WAN_CONNECTED);
-                       break;
-
-               case EXCEP_LINK_INACTIVE_MODEM:
-                       port_set_state(card, WAN_DISCONNECTED);
-                       break;
-
-               case EXCEP_LOOPBACK_CONDITION:
-                       printk(KERN_INFO "%s: Loopback Condition Detected.\n",
-                                               card->devname);
-                       break;
-
-               case NO_CHDLC_EXCEP_COND_TO_REPORT:
-                       printk(KERN_INFO "%s: No exceptions reported.\n",
-                                               card->devname);
-                       break;
-               default:
-                       printk(KERN_INFO "%s: Exception Condition %x!\n",
-                                       card->devname,err);
-                       break;
-               }
-
-       }
-       return 0;
-}
-
-
-/*=============================================================================
- * Store a UDP management packet for later processing.
- */
-
-static int store_udp_mgmt_pkt(char udp_pkt_src, sdla_t* card,
-                             struct sk_buff *skb, struct net_device* dev,
-                             chdlc_private_area_t* chdlc_priv_area )
-{
-       int udp_pkt_stored = 0;
-
-       if(!chdlc_priv_area->udp_pkt_lgth &&
-         (skb->len <= MAX_LGTH_UDP_MGNT_PKT)) {
-               chdlc_priv_area->udp_pkt_lgth = skb->len;
-               chdlc_priv_area->udp_pkt_src = udp_pkt_src;
-                       memcpy(chdlc_priv_area->udp_pkt_data, skb->data, skb->len);
-               chdlc_priv_area->timer_int_enabled = TMR_INT_ENABLED_UDP;
-               udp_pkt_stored = 1;
-       }
-
-       if(udp_pkt_src == UDP_PKT_FRM_STACK)
-               dev_kfree_skb_any(skb);
-       else
-                dev_kfree_skb_any(skb);
-       
-       return(udp_pkt_stored);
-}
-
-
-/*=============================================================================
- * Process UDP management packet.
- */
-
-static int process_udp_mgmt_pkt(sdla_t* card, struct net_device* dev,
-                               chdlc_private_area_t* chdlc_priv_area ) 
-{
-       unsigned char *buf;
-       unsigned int frames, len;
-       struct sk_buff *new_skb;
-       unsigned short buffer_length, real_len;
-       unsigned long data_ptr;
-       unsigned data_length;
-       int udp_mgmt_req_valid = 1;
-       CHDLC_MAILBOX_STRUCT *mb = card->mbox;
-       SHARED_MEMORY_INFO_STRUCT *flags = card->u.c.flags;
-       chdlc_udp_pkt_t *chdlc_udp_pkt;
-       struct timeval tv;
-       int err;
-       char ut_char;
-
-       chdlc_udp_pkt = (chdlc_udp_pkt_t *) chdlc_priv_area->udp_pkt_data;
-
-       if(chdlc_priv_area->udp_pkt_src == UDP_PKT_FRM_NETWORK) {
-
-               switch(chdlc_udp_pkt->cblock.command) {
-                       case READ_GLOBAL_STATISTICS:
-                       case READ_MODEM_STATUS:  
-                       case READ_CHDLC_LINK_STATUS:
-                       case CPIPE_ROUTER_UP_TIME:
-                       case READ_COMMS_ERROR_STATS:
-                       case READ_CHDLC_OPERATIONAL_STATS:
-
-                       /* These two commands are executed for
-                        * each request */
-                       case READ_CHDLC_CONFIGURATION:
-                       case READ_CHDLC_CODE_VERSION:
-                               udp_mgmt_req_valid = 1;
-                               break;
-                       default:
-                               udp_mgmt_req_valid = 0;
-                               break;
-               } 
-       }
-       
-       if(!udp_mgmt_req_valid) {
-
-               /* set length to 0 */
-               chdlc_udp_pkt->cblock.buffer_length = 0;
-
-               /* set return code */
-               chdlc_udp_pkt->cblock.return_code = 0xCD;
-
-               if (net_ratelimit()){   
-                       printk(KERN_INFO 
-                       "%s: Warning, Illegal UDP command attempted from network: %x\n",
-                       card->devname,chdlc_udp_pkt->cblock.command);
-               }
-
-       } else {
-               unsigned long trace_status_cfg_addr = 0;
-               TRACE_STATUS_EL_CFG_STRUCT trace_cfg_struct;
-               TRACE_STATUS_ELEMENT_STRUCT trace_element_struct;
-
-               switch(chdlc_udp_pkt->cblock.command) {
-
-               case CPIPE_ENABLE_TRACING:
-                    if (!chdlc_priv_area->TracingEnabled) {
-
-                       /* OPERATE_DATALINE_MONITOR */
-
-                       mb->buffer_length = sizeof(LINE_TRACE_CONFIG_STRUCT);
-                       mb->command = SET_TRACE_CONFIGURATION;
-
-                       ((LINE_TRACE_CONFIG_STRUCT *)mb->data)->
-                               trace_config = TRACE_ACTIVE;
-                       /* Trace delay mode is not used because it slows
-                          down transfer and results in a standoff situation
-                          when there is a lot of data */
-
-                       /* Configure the Trace based on user inputs */
-                       ((LINE_TRACE_CONFIG_STRUCT *)mb->data)->trace_config |= 
-                                       chdlc_udp_pkt->data[0];
-
-                       ((LINE_TRACE_CONFIG_STRUCT *)mb->data)->
-                          trace_deactivation_timer = 4000;
-
-
-                       err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT;
-                       if (err != COMMAND_OK) {
-                               chdlc_error(card,err,mb);
-                               card->TracingEnabled = 0;
-                               chdlc_udp_pkt->cblock.return_code = err;
-                               mb->buffer_length = 0;
-                               break;
-                       } 
-
-                       /* Get the base address of the trace element list */
-                       mb->buffer_length = 0;
-                       mb->command = READ_TRACE_CONFIGURATION;
-                       err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT;
-
-                       if (err != COMMAND_OK) {
-                               chdlc_error(card,err,mb);
-                               chdlc_priv_area->TracingEnabled = 0;
-                               chdlc_udp_pkt->cblock.return_code = err;
-                               mb->buffer_length = 0;
-                               break;
-                       }       
-
-                       trace_status_cfg_addr =((LINE_TRACE_CONFIG_STRUCT *)
-                               mb->data) -> ptr_trace_stat_el_cfg_struct;
-
-                       sdla_peek(&card->hw, trace_status_cfg_addr,
-                                &trace_cfg_struct, sizeof(trace_cfg_struct));
-                   
-                       chdlc_priv_area->start_trace_addr = trace_cfg_struct.
-                               base_addr_trace_status_elements;
-
-                       chdlc_priv_area->number_trace_elements = 
-                                       trace_cfg_struct.number_trace_status_elements;
-
-                       chdlc_priv_area->end_trace_addr = (unsigned long)
-                                       ((TRACE_STATUS_ELEMENT_STRUCT *)
-                                        chdlc_priv_area->start_trace_addr + 
-                                        (chdlc_priv_area->number_trace_elements - 1));
-
-                       chdlc_priv_area->base_addr_trace_buffer = 
-                                       trace_cfg_struct.base_addr_trace_buffer;
-
-                       chdlc_priv_area->end_addr_trace_buffer = 
-                                       trace_cfg_struct.end_addr_trace_buffer;
-
-                       chdlc_priv_area->curr_trace_addr = 
-                                       trace_cfg_struct.next_trace_element_to_use;
-
-                       chdlc_priv_area->available_buffer_space = 2000 - 
-                                                                 sizeof(ip_pkt_t) -
-                                                                 sizeof(udp_pkt_t) -
-                                                                 sizeof(wp_mgmt_t) -
-                                                                 sizeof(cblock_t) -
-                                                                 sizeof(trace_info_t); 
-                    }
-                    chdlc_udp_pkt->cblock.return_code = COMMAND_OK;
-                    mb->buffer_length = 0;
-                    chdlc_priv_area->TracingEnabled = 1;
-                    break;
-          
-
-               case CPIPE_DISABLE_TRACING:
-                    if (chdlc_priv_area->TracingEnabled) {
-
-                       /* OPERATE_DATALINE_MONITOR */
-                       mb->buffer_length = sizeof(LINE_TRACE_CONFIG_STRUCT);
-                       mb->command = SET_TRACE_CONFIGURATION;
-                       ((LINE_TRACE_CONFIG_STRUCT *)mb->data)->
-                               trace_config = TRACE_INACTIVE;
-                       err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT;
-                    }          
-
-                    chdlc_priv_area->TracingEnabled = 0;
-                    chdlc_udp_pkt->cblock.return_code = COMMAND_OK;
-                    mb->buffer_length = 0;
-                    break;
-          
-
-               case CPIPE_GET_TRACE_INFO:
-
-                    if (!chdlc_priv_area->TracingEnabled) {
-                       chdlc_udp_pkt->cblock.return_code = 1;
-                       mb->buffer_length = 0;
-                       break;
-                    }
-
-                    chdlc_udp_pkt->trace_info.ismoredata = 0x00;
-                    buffer_length = 0; /* offset of packet already occupied */
-
-                    for (frames=0; frames < chdlc_priv_area->number_trace_elements; frames++){
-
-                       trace_pkt_t *trace_pkt = (trace_pkt_t *)
-                               &chdlc_udp_pkt->data[buffer_length];
-
-                       sdla_peek(&card->hw, chdlc_priv_area->curr_trace_addr,
-                                 (unsigned char *)&trace_element_struct,
-                                 sizeof(TRACE_STATUS_ELEMENT_STRUCT));
-
-                       if (trace_element_struct.opp_flag == 0x00) {
-                               break;
-                       }
-
-                       /* get pointer to real data */
-                       data_ptr = trace_element_struct.ptr_data_bfr;
-
-                       /* See if there is actual data on the trace buffer */
-                       if (data_ptr){
-                               data_length = trace_element_struct.trace_length;
-                       }else{
-                               data_length = 0;
-                               chdlc_udp_pkt->trace_info.ismoredata = 0x01;
-                       }
-       
-                       if( (chdlc_priv_area->available_buffer_space - buffer_length)
-                               < ( sizeof(trace_pkt_t) + data_length) ) {
-
-                            /* indicate there are more frames on board & exit */
-                               chdlc_udp_pkt->trace_info.ismoredata = 0x01;
-                                       break;
-                         }
-
-                       trace_pkt->status = trace_element_struct.trace_type;
-
-                       trace_pkt->time_stamp =
-                               trace_element_struct.trace_time_stamp;
-
-                       trace_pkt->real_length =
-                               trace_element_struct.trace_length;
-
-                       /* see if we can fit the frame into the user buffer */
-                       real_len = trace_pkt->real_length;
-
-                       if (data_ptr == 0) {
-                               trace_pkt->data_avail = 0x00;
-                       } else {
-                               unsigned tmp = 0;
-
-                               /* get the data from circular buffer
-                                   must check for end of buffer */
-                               trace_pkt->data_avail = 0x01;
-
-                               if ((data_ptr + real_len) >
-                                            chdlc_priv_area->end_addr_trace_buffer + 1){
-
-                                       tmp = chdlc_priv_area->end_addr_trace_buffer - data_ptr + 1;
-                                       sdla_peek(&card->hw, data_ptr,
-                                                 trace_pkt->data,tmp);
-                                       data_ptr = chdlc_priv_area->base_addr_trace_buffer;
-                               }
-       
-                               sdla_peek(&card->hw, data_ptr,
-                                         &trace_pkt->data[tmp], real_len - tmp);
-                       }       
-
-                       /* zero the opp flag to show we got the frame */
-                       ut_char = 0x00;
-                       sdla_poke(&card->hw, chdlc_priv_area->curr_trace_addr, &ut_char, 1);
-
-                               /* now move onto the next frame */
-                               chdlc_priv_area->curr_trace_addr += sizeof(TRACE_STATUS_ELEMENT_STRUCT);
-
-                               /* check if we went over the last address */
-                       if ( chdlc_priv_area->curr_trace_addr > chdlc_priv_area->end_trace_addr ) {
-                               chdlc_priv_area->curr_trace_addr = chdlc_priv_area->start_trace_addr;
-                               }
-
-                       if(trace_pkt->data_avail == 0x01) {
-                               buffer_length += real_len - 1;
-                       }
-        
-                       /* for the header */
-                       buffer_length += sizeof(trace_pkt_t);
-
-                    }  /* For Loop */
-
-                    if (frames == chdlc_priv_area->number_trace_elements){
-                       chdlc_udp_pkt->trace_info.ismoredata = 0x01;
-                    }
-                    chdlc_udp_pkt->trace_info.num_frames = frames;
-                
-                    mb->buffer_length = buffer_length;
-                    chdlc_udp_pkt->cblock.buffer_length = buffer_length; 
-                
-                    chdlc_udp_pkt->cblock.return_code = COMMAND_OK; 
-                    
-                    break;
-
-
-               case CPIPE_FT1_READ_STATUS:
-                       ((unsigned char *)chdlc_udp_pkt->data )[0] =
-                               flags->FT1_info_struct.parallel_port_A_input;
-
-                       ((unsigned char *)chdlc_udp_pkt->data )[1] =
-                               flags->FT1_info_struct.parallel_port_B_input;
-                                
-                       chdlc_udp_pkt->cblock.return_code = COMMAND_OK;
-                       mb->buffer_length = 2;
-                       break;
-               
-               case CPIPE_ROUTER_UP_TIME:
-                       do_gettimeofday( &tv );
-                       chdlc_priv_area->router_up_time = tv.tv_sec - 
-                                       chdlc_priv_area->router_start_time;
-                       *(unsigned long *)&chdlc_udp_pkt->data = 
-                                       chdlc_priv_area->router_up_time;        
-                       mb->buffer_length = sizeof(unsigned long);
-                       break;
-
-               case FT1_MONITOR_STATUS_CTRL:
-                       /* Enable FT1 MONITOR STATUS */
-                       if ((chdlc_udp_pkt->data[0] & ENABLE_READ_FT1_STATUS) ||  
-                               (chdlc_udp_pkt->data[0] & ENABLE_READ_FT1_OP_STATS)) {
-                       
-                               if( rCount++ != 0 ) {
-                                       chdlc_udp_pkt->cblock.
-                                       return_code = COMMAND_OK;
-                                       mb->buffer_length = 1;
-                                       break;
-                               }
-                       }
-
-                       /* Disable FT1 MONITOR STATUS */
-                       if( chdlc_udp_pkt->data[0] == 0) {
-
-                               if( --rCount != 0) {
-                                       chdlc_udp_pkt->cblock.
-                                       return_code = COMMAND_OK;
-                                       mb->buffer_length = 1;
-                                       break;
-                               } 
-                       }       
-       
-               default:
-                       /* it's a board command */
-                       mb->command = chdlc_udp_pkt->cblock.command;
-                       mb->buffer_length = chdlc_udp_pkt->cblock.buffer_length;
-                       if (mb->buffer_length) {
-                               memcpy(&mb->data, (unsigned char *) chdlc_udp_pkt->
-                                                       data, mb->buffer_length);
-                       } 
-                       /* run the command on the board */
-                       err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT;
-                       if (err != COMMAND_OK) {
-                               break;
-                       }
-
-                       /* copy the result back to our buffer */
-                       memcpy(&chdlc_udp_pkt->cblock, mb, sizeof(cblock_t)); 
-                       
-                       if (mb->buffer_length) {
-                               memcpy(&chdlc_udp_pkt->data, &mb->data, 
-                                                               mb->buffer_length); 
-                       }
-
-               } /* end of switch */
-       } /* end of else */
-
-       /* Fill UDP TTL */
-       chdlc_udp_pkt->ip_pkt.ttl = card->wandev.ttl; 
-
-       len = reply_udp(chdlc_priv_area->udp_pkt_data, mb->buffer_length);
-       
-       if(chdlc_priv_area->udp_pkt_src == UDP_PKT_FRM_NETWORK) {
-               if(!chdlc_send(card, chdlc_priv_area->udp_pkt_data, len)) {
-                       ++ card->wandev.stats.tx_packets;
-                       card->wandev.stats.tx_bytes += len;
-               }
-       } else {        
-       
-               /* Pass it up the stack
-                  Allocate socket buffer */
-               if ((new_skb = dev_alloc_skb(len)) != NULL) {
-                       /* copy data into new_skb */
-
-                       buf = skb_put(new_skb, len);
-                       memcpy(buf, chdlc_priv_area->udp_pkt_data, len);
-
-                       /* Decapsulate pkt and pass it up the protocol stack */
-                       new_skb->protocol = htons(ETH_P_IP);
-                       new_skb->dev = dev;
-                       new_skb->mac.raw  = new_skb->data;
-       
-                       netif_rx(new_skb);
-                       dev->last_rx = jiffies;
-               } else {
-               
-                       printk(KERN_INFO "%s: no socket buffers available!\n",
-                                       card->devname);
-               }
-       }
-       chdlc_priv_area->udp_pkt_lgth = 0;
-       
-       return 0;
-}
-
-/*============================================================================
- * Initialize Receive and Transmit Buffers.
- */
-
-static void init_chdlc_tx_rx_buff(sdla_t* card, struct net_device *dev)
-{
-       CHDLC_MAILBOX_STRUCT* mb = card->mbox;
-       CHDLC_TX_STATUS_EL_CFG_STRUCT *tx_config;
-       CHDLC_RX_STATUS_EL_CFG_STRUCT *rx_config;
-       char err;
-       
-       mb->buffer_length = 0;
-       mb->command = READ_CHDLC_CONFIGURATION;
-       err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT;
-
-       if(err != COMMAND_OK) {
-               chdlc_error(card,err,mb);
-               return;
-       }
-
-       if(card->hw.type == SDLA_S514) {
-               tx_config = (CHDLC_TX_STATUS_EL_CFG_STRUCT *)(card->hw.dpmbase +
-                (((CHDLC_CONFIGURATION_STRUCT *)mb->data)->
-                            ptr_CHDLC_Tx_stat_el_cfg_struct));
-               rx_config = (CHDLC_RX_STATUS_EL_CFG_STRUCT *)(card->hw.dpmbase +
-                (((CHDLC_CONFIGURATION_STRUCT *)mb->data)->
-                            ptr_CHDLC_Rx_stat_el_cfg_struct));
-
-                       /* Setup Head and Tails for buffers */
-               card->u.c.txbuf_base = (void *)(card->hw.dpmbase +
-                tx_config->base_addr_Tx_status_elements);
-               card->u.c.txbuf_last = 
-               (CHDLC_DATA_TX_STATUS_EL_STRUCT *)  
-                card->u.c.txbuf_base +
-               (tx_config->number_Tx_status_elements - 1);
-
-               card->u.c.rxbuf_base = (void *)(card->hw.dpmbase +
-                rx_config->base_addr_Rx_status_elements);
-               card->u.c.rxbuf_last =
-               (CHDLC_DATA_RX_STATUS_EL_STRUCT *)
-                card->u.c.rxbuf_base +
-               (rx_config->number_Rx_status_elements - 1);
-
-               /* Set up next pointer to be used */
-               card->u.c.txbuf = (void *)(card->hw.dpmbase +
-                tx_config->next_Tx_status_element_to_use);
-               card->u.c.rxmb = (void *)(card->hw.dpmbase +
-                rx_config->next_Rx_status_element_to_use);
-       }
-        else {
-                tx_config = (CHDLC_TX_STATUS_EL_CFG_STRUCT *)(card->hw.dpmbase +
-                       (((CHDLC_CONFIGURATION_STRUCT *)mb->data)->
-                       ptr_CHDLC_Tx_stat_el_cfg_struct % SDLA_WINDOWSIZE));
-
-                rx_config = (CHDLC_RX_STATUS_EL_CFG_STRUCT *)(card->hw.dpmbase +
-                       (((CHDLC_CONFIGURATION_STRUCT *)mb->data)->
-                       ptr_CHDLC_Rx_stat_el_cfg_struct % SDLA_WINDOWSIZE));
-
-                /* Setup Head and Tails for buffers */
-                card->u.c.txbuf_base = (void *)(card->hw.dpmbase +
-               (tx_config->base_addr_Tx_status_elements % SDLA_WINDOWSIZE));
-                card->u.c.txbuf_last =
-               (CHDLC_DATA_TX_STATUS_EL_STRUCT *)card->u.c.txbuf_base
-               + (tx_config->number_Tx_status_elements - 1);
-                card->u.c.rxbuf_base = (void *)(card->hw.dpmbase +
-               (rx_config->base_addr_Rx_status_elements % SDLA_WINDOWSIZE));
-                card->u.c.rxbuf_last = 
-               (CHDLC_DATA_RX_STATUS_EL_STRUCT *)card->u.c.rxbuf_base
-               + (rx_config->number_Rx_status_elements - 1);
-
-                 /* Set up next pointer to be used */
-                card->u.c.txbuf = (void *)(card->hw.dpmbase +
-               (tx_config->next_Tx_status_element_to_use % SDLA_WINDOWSIZE));
-                card->u.c.rxmb = (void *)(card->hw.dpmbase +
-               (rx_config->next_Rx_status_element_to_use % SDLA_WINDOWSIZE));
-        }
-
-        /* Setup Actual Buffer Start and end addresses */
-        card->u.c.rx_base = rx_config->base_addr_Rx_buffer;
-        card->u.c.rx_top  = rx_config->end_addr_Rx_buffer;
-
-}
-
-/*=============================================================================
- * Perform Interrupt Test by running READ_CHDLC_CODE_VERSION command MAX_INTR
- * _TEST_COUNTER times.
- */
-static int intr_test( sdla_t* card)
-{
-       CHDLC_MAILBOX_STRUCT* mb = card->mbox;
-       int err,i;
-
-       Intr_test_counter = 0;
-
-       /* The critical flag is unset because during initialization (if_open) 
-        * we want the interrupts to be enabled so that when the wpc_isr is
-        * called it does not exit due to critical flag set.
-        */ 
-
-       err = chdlc_set_intr_mode(card, APP_INT_ON_COMMAND_COMPLETE);
-
-       if (err == CMD_OK) { 
-               for (i = 0; i < MAX_INTR_TEST_COUNTER; i ++) {  
-                       mb->buffer_length  = 0;
-                       mb->command = READ_CHDLC_CODE_VERSION;
-                       err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT;
-               }
-       }
-       else {
-               return err;
-       }
-
-       err = chdlc_set_intr_mode(card, 0);
-
-       if (err != CMD_OK)
-               return err;
-
-       return 0;
-}
-
-/*==============================================================================
- * Determine what type of UDP call it is. CPIPEAB ?
- */
-static int udp_pkt_type(struct sk_buff *skb, sdla_t* card)
-{
-        chdlc_udp_pkt_t *chdlc_udp_pkt = (chdlc_udp_pkt_t *)skb->data;
-
-       if (!strncmp(chdlc_udp_pkt->wp_mgmt.signature,UDPMGMT_SIGNATURE,8) &&
-          (chdlc_udp_pkt->udp_pkt.udp_dst_port == ntohs(card->wandev.udp_port)) &&
-          (chdlc_udp_pkt->ip_pkt.protocol == UDPMGMT_UDP_PROTOCOL) &&
-          (chdlc_udp_pkt->wp_mgmt.request_reply == UDPMGMT_REQUEST)) {
-               return UDP_CPIPE_TYPE;
-       }
-       else return UDP_INVALID_TYPE;
-}
-
-/*============================================================================
- * Set PORT state.
- */
-static void port_set_state (sdla_t *card, int state)
-{
-       struct net_device *dev = card->wandev.dev;
-       chdlc_private_area_t *chdlc_priv_area = dev->priv;
-
-        if (card->u.c.state != state)
-        {
-                switch (state)
-                {
-                case WAN_CONNECTED:
-                        printk (KERN_INFO "%s: HDLC link connected!\n",
-                                card->devname);
-                      break;
-
-                case WAN_CONNECTING:
-                        printk (KERN_INFO "%s: HDLC link connecting...\n",
-                                card->devname);
-                        break;
-
-                case WAN_DISCONNECTED:
-                        printk (KERN_INFO "%s: HDLC link disconnected!\n",
-                                card->devname);
-                        break;
-                }
-
-                card->wandev.state = card->u.c.state = state;
-               chdlc_priv_area->common.state = state;
-        }
-}
-
-void s508_lock (sdla_t *card, unsigned long *smp_flags)
-{
-       spin_lock_irqsave(&card->wandev.lock, *smp_flags);
-        if (card->next){
-               /* It is ok to use spin_lock here, since we
-                * already turned off interrupts */
-               spin_lock(&card->next->wandev.lock);
-       }
-}
-
-void s508_unlock (sdla_t *card, unsigned long *smp_flags)
-{
-       if (card->next){
-               spin_unlock(&card->next->wandev.lock);
-       }
-       spin_unlock_irqrestore(&card->wandev.lock, *smp_flags);
-}
-
-
-
-/*===========================================================================
- * config_chdlc
- *
- *     Configure the chdlc protocol and enable communications.         
- *
- *     The if_open() function binds this function to the poll routine.
- *      Therefore, this function will run every time the chdlc interface
- *      is brought up. We cannot run this function from the if_open 
- *      because if_open does not have access to the remote IP address.
- *      
- *     If the communications are not enabled, proceed to configure
- *      the card and enable communications.
- *
- *      If the communications are enabled, it means that the interface
- *      was shutdown by ether the user or driver. In this case, we 
- *      have to check that the IP addresses have not changed.  If
- *      the IP addresses have changed, we have to reconfigure the firmware
- *      and update the changed IP addresses.  Otherwise, just exit.
- *
- */
-
-static int config_chdlc (sdla_t *card)
-{
-       struct net_device *dev = card->wandev.dev;
-       SHARED_MEMORY_INFO_STRUCT *flags = card->u.c.flags;
-
-       if (card->u.c.comm_enabled){
-               chdlc_comm_disable(card);
-               port_set_state(card, WAN_DISCONNECTED);
-       }
-
-       if (set_chdlc_config(card)) {
-               printk(KERN_INFO "%s: CHDLC Configuration Failed!\n",
-                               card->devname);
-               return 0;
-       }
-       init_chdlc_tx_rx_buff(card, dev);
-
-       /* Set interrupt mode and mask */
-        if (chdlc_set_intr_mode(card, APP_INT_ON_RX_FRAME |
-                               APP_INT_ON_GLOBAL_EXCEP_COND |
-                               APP_INT_ON_TX_FRAME |
-                               APP_INT_ON_CHDLC_EXCEP_COND | APP_INT_ON_TIMER)){
-               printk (KERN_INFO "%s: Failed to set interrupt triggers!\n",
-                               card->devname);
-               return 0;       
-        }
-       
-
-       /* Mask the Transmit and Timer interrupt */
-       flags->interrupt_info_struct.interrupt_permission &= 
-               ~(APP_INT_ON_TX_FRAME | APP_INT_ON_TIMER);
-
-
-       if (chdlc_comm_enable(card) != 0) {
-               printk(KERN_INFO "%s: Failed to enable chdlc communications!\n",
-                               card->devname);
-               flags->interrupt_info_struct.interrupt_permission = 0;
-               card->u.c.comm_enabled=0;
-               chdlc_set_intr_mode(card,0);
-               return 0;
-       }
-
-       /* Initialize Rx/Tx buffer control fields */
-       port_set_state(card, WAN_CONNECTING);
-       return 0; 
-}
-
-
-static void send_ppp_term_request(struct net_device *dev)
-{
-       struct sk_buff *new_skb;
-       unsigned char *buf;
-
-       if ((new_skb = dev_alloc_skb(8)) != NULL) {
-               /* copy data into new_skb */
-
-               buf = skb_put(new_skb, 8);
-               sprintf(buf,"%c%c%c%c%c%c%c%c", 0xFF,0x03,0xC0,0x21,0x05,0x98,0x00,0x07);
-
-               /* Decapsulate pkt and pass it up the protocol stack */
-               new_skb->protocol = htons(ETH_P_WAN_PPP);
-               new_skb->dev = dev;
-               new_skb->mac.raw  = new_skb->data;
-
-               netif_rx(new_skb);
-               dev->last_rx = jiffies;
-       }
-}
-
-
-MODULE_LICENSE("GPL");
-
-/****** End ****************************************************************/
index bad09ebdb50b9622d6b635a9301a886d98d878f5..e0874cbfefea36ff0a16b8943437f9b9f2ed5a67 100644 (file)
@@ -6,7 +6,7 @@ menu "Wireless LAN (non-hamradio)"
        depends on NETDEVICES
 
 config NET_RADIO
-       bool "Wireless LAN drivers (non-hamradio)"
+       bool "Wireless LAN drivers (non-hamradio) & Wireless Extensions"
        select WIRELESS_EXT
        ---help---
          Support for wireless LANs and everything having to do with radio,
index 108d9fed8f0761f2487b8505c85f8c959bc47794..00764ddd74d8fc5593339107cd149fac3fec8ed1 100644 (file)
@@ -3139,6 +3139,7 @@ static irqreturn_t airo_interrupt ( int irq, void* dev_id, struct pt_regs *regs)
                }
                if ( status & EV_LINK ) {
                        union iwreq_data        wrqu;
+                       int scan_forceloss = 0;
                        /* The link status has changed, if you want to put a
                           monitor hook in, do it here.  (Remember that
                           interrupts are still disabled!)
@@ -3157,7 +3158,8 @@ static irqreturn_t airo_interrupt ( int irq, void* dev_id, struct pt_regs *regs)
                          code) */
 #define AUTHFAIL 0x0300 /* Authentication failure (low byte is reason
                           code) */
-#define ASSOCIATED 0x0400 /* Assocatied */
+#define ASSOCIATED 0x0400 /* Associated */
+#define REASSOCIATED 0x0600 /* Reassociated?  Only on firmware >= 5.30.17 */
 #define RC_RESERVED 0 /* Reserved return code */
 #define RC_NOREASON 1 /* Unspecified reason */
 #define RC_AUTHINV 2 /* Previous authentication invalid */
@@ -3174,44 +3176,30 @@ static irqreturn_t airo_interrupt ( int irq, void* dev_id, struct pt_regs *regs)
                          leaving BSS */
 #define RC_NOAUTH 9 /* Station requesting (Re)Association is not
                       Authenticated with the responding station */
-                       if (newStatus != ASSOCIATED) {
-                               if (auto_wep && !apriv->expires) {
-                                       apriv->expires = RUN_AT(3*HZ);
-                                       wake_up_interruptible(&apriv->thr_wait);
-                               }
-                       } else {
-                               struct task_struct *task = apriv->task;
+                       if (newStatus == FORCELOSS && apriv->scan_timeout > 0)
+                               scan_forceloss = 1;
+                       if(newStatus == ASSOCIATED || newStatus == REASSOCIATED) {
                                if (auto_wep)
                                        apriv->expires = 0;
-                               if (task)
-                                       wake_up_process (task);
+                               if (apriv->task)
+                                       wake_up_process (apriv->task);
                                set_bit(FLAG_UPDATE_UNI, &apriv->flags);
                                set_bit(FLAG_UPDATE_MULTI, &apriv->flags);
-                       }
-                       /* Question : is ASSOCIATED the only status
-                        * that is valid ? We want to catch handover
-                        * and reassociations as valid status
-                        * Jean II */
-                       if(newStatus == ASSOCIATED) {
-#if 0
-                               /* FIXME: Grabbing scan results here
-                                * seems to be too early???  Just wait for
-                                * timeout instead. */
-                               if (apriv->scan_timeout > 0) {
-                                       set_bit(JOB_SCAN_RESULTS, &apriv->flags);
-                                       wake_up_interruptible(&apriv->thr_wait);
-                               }
-#endif
+
                                if (down_trylock(&apriv->sem) != 0) {
                                        set_bit(JOB_EVENT, &apriv->flags);
                                        wake_up_interruptible(&apriv->thr_wait);
                                } else
                                        airo_send_event(dev);
-                       } else {
-                               memset(wrqu.ap_addr.sa_data, '\0', ETH_ALEN);
-                               wrqu.ap_addr.sa_family = ARPHRD_ETHER;
+                       } else if (!scan_forceloss) {
+                               if (auto_wep && !apriv->expires) {
+                                       apriv->expires = RUN_AT(3*HZ);
+                                       wake_up_interruptible(&apriv->thr_wait);
+                               }
 
                                /* Send event to user space */
+                               memset(wrqu.ap_addr.sa_data, '\0', ETH_ALEN);
+                               wrqu.ap_addr.sa_family = ARPHRD_ETHER;
                                wireless_send_event(dev, SIOCGIWAP, &wrqu,NULL);
                        }
                }
@@ -7136,10 +7124,10 @@ static int airo_set_scan(struct net_device *dev,
                goto out;
 
        /* Initiate a scan command */
+       ai->scan_timeout = RUN_AT(3*HZ);
        memset(&cmd, 0, sizeof(cmd));
        cmd.cmd=CMD_LISTBSS;
        issuecommand(ai, &cmd, &rsp);
-       ai->scan_timeout = RUN_AT(3*HZ);
        wake = 1;
 
 out:
index 87afa6878f26c98a79e8800982a2f7ae8bfb20ed..8606c88886fca9237fd8b3f4bd774fca8aa7e02c 100644 (file)
@@ -3463,6 +3463,7 @@ static void atmel_command_irq(struct atmel_private *priv)
        u8 status = atmel_rmem8(priv, atmel_co(priv, CMD_BLOCK_STATUS_OFFSET));
        u8 command = atmel_rmem8(priv, atmel_co(priv, CMD_BLOCK_COMMAND_OFFSET));
        int fast_scan;
+       union iwreq_data wrqu;
 
        if (status == CMD_STATUS_IDLE ||
            status == CMD_STATUS_IN_PROGRESS)
@@ -3487,6 +3488,7 @@ static void atmel_command_irq(struct atmel_private *priv)
                        atmel_scan(priv, 1);
                } else {
                        int bss_index = retrieve_bss(priv);
+                       int notify_scan_complete = 1;
                        if (bss_index != -1) {
                                atmel_join_bss(priv, bss_index);
                        } else if (priv->operating_mode == IW_MODE_ADHOC &&
@@ -3495,8 +3497,14 @@ static void atmel_command_irq(struct atmel_private *priv)
                        } else {
                                priv->fast_scan = !fast_scan;
                                atmel_scan(priv, 1);
+                               notify_scan_complete = 0;
                        }
                        priv->site_survey_state = SITE_SURVEY_COMPLETED;
+                       if (notify_scan_complete) {
+                               wrqu.data.length = 0;
+                               wrqu.data.flags = 0;
+                               wireless_send_event(priv->dev, SIOCGIWSCAN, &wrqu, NULL);
+                       }
                }
                break;
 
@@ -3509,6 +3517,9 @@ static void atmel_command_irq(struct atmel_private *priv)
                priv->site_survey_state = SITE_SURVEY_COMPLETED;
                if (priv->station_is_associated) {
                        atmel_enter_state(priv, STATION_STATE_READY);
+                       wrqu.data.length = 0;
+                       wrqu.data.flags = 0;
+                       wireless_send_event(priv->dev, SIOCGIWSCAN, &wrqu, NULL);
                } else {
                        atmel_scan(priv, 1);
                }
index 418465600a77e8dd491ac6fee0d95255190013ce..25ea4748f0b9a3ea3d800e84c1bc395dd04c371c 100644 (file)
@@ -17,8 +17,11 @@ config BCM43XX_DEBUG
 
 config BCM43XX_DMA
        bool
+       depends on BCM43XX
+
 config BCM43XX_PIO
        bool
+       depends on BCM43XX
 
 choice
        prompt "BCM43xx data transfer mode"
index dcadd295de4f6fa42aeb51d85e6a2286eb1bfa64..2e83083935e1d9bd90570975c5cb771b62055a1e 100644 (file)
@@ -15,7 +15,6 @@
 
 #include "bcm43xx_debugfs.h"
 #include "bcm43xx_leds.h"
-#include "bcm43xx_sysfs.h"
 
 
 #define PFX                            KBUILD_MODNAME ": "
@@ -638,8 +637,6 @@ struct bcm43xx_key {
 };
 
 struct bcm43xx_private {
-       struct bcm43xx_sysfs sysfs;
-
        struct ieee80211_device *ieee;
        struct ieee80211softmac_device *softmac;
 
@@ -772,6 +769,20 @@ struct bcm43xx_private * bcm43xx_priv(struct net_device *dev)
        return ieee80211softmac_priv(dev);
 }
 
+struct device;
+
+static inline
+struct bcm43xx_private * dev_to_bcm(struct device *dev)
+{
+       struct net_device *net_dev;
+       struct bcm43xx_private *bcm;
+
+       net_dev = dev_get_drvdata(dev);
+       bcm = bcm43xx_priv(net_dev);
+
+       return bcm;
+}
+
 
 /* Helper function, which returns a boolean.
  * TRUE, if PIO is used; FALSE, if DMA is used.
index d2c3401e9b70438fba9cb46f6794d115fdca8c41..35a4fcb6d9233bc0887255ccc30ab08d336f9599 100644 (file)
@@ -452,12 +452,12 @@ void bcm43xx_printk_dump(const char *data,
        size_t i;
        char c;
 
-       printk(KERN_INFO PFX "Data dump (%s, %u bytes):",
+       printk(KERN_INFO PFX "Data dump (%s, %zd bytes):",
               description, size);
        for (i = 0; i < size; i++) {
                c = data[i];
                if (i % 8 == 0)
-                       printk("\n" KERN_INFO PFX "0x%08x:  0x%02x, ", i, c & 0xff);
+                       printk("\n" KERN_INFO PFX "0x%08zx:  0x%02x, ", i, c & 0xff);
                else
                        printk("0x%02x, ", c & 0xff);
        }
@@ -472,12 +472,12 @@ void bcm43xx_printk_bitdump(const unsigned char *data,
        int j;
        const unsigned char *d;
 
-       printk(KERN_INFO PFX "*** Bitdump (%s, %u bytes, %s) ***",
+       printk(KERN_INFO PFX "*** Bitdump (%s, %zd bytes, %s) ***",
               description, bytes, msb_to_lsb ? "MSB to LSB" : "LSB to MSB");
        for (i = 0; i < bytes; i++) {
                d = data + i;
                if (i % 8 == 0)
-                       printk("\n" KERN_INFO PFX "0x%08x:  ", i);
+                       printk("\n" KERN_INFO PFX "0x%08zx:  ", i);
                if (msb_to_lsb) {
                        for (j = 7; j >= 0; j--) {
                                if (*d & (1 << j))
index c3681b8f09b42f81cf2d4848c1a12c03fa7856c1..bbecba02e69775671187f84b9e19611f9c00fe19 100644 (file)
@@ -196,8 +196,9 @@ static int alloc_ringmemory(struct bcm43xx_dmaring *ring)
        }
        if (ring->dmabase + BCM43xx_DMA_RINGMEMSIZE > BCM43xx_DMA_BUSADDRMAX) {
                printk(KERN_ERR PFX ">>>FATAL ERROR<<<  DMA RINGMEMORY >1G "
-                                   "(0x%08x, len: %lu)\n",
-                      ring->dmabase, BCM43xx_DMA_RINGMEMSIZE);
+                                   "(0x%llx, len: %lu)\n",
+                               (unsigned long long)ring->dmabase,
+                               BCM43xx_DMA_RINGMEMSIZE);
                dma_free_coherent(dev, BCM43xx_DMA_RINGMEMSIZE,
                                  ring->vbase, ring->dmabase);
                return -ENOMEM;
@@ -307,8 +308,8 @@ static int setup_rx_descbuffer(struct bcm43xx_dmaring *ring,
                unmap_descbuffer(ring, dmaaddr, ring->rx_buffersize, 0);
                dev_kfree_skb_any(skb);
                printk(KERN_ERR PFX ">>>FATAL ERROR<<<  DMA RX SKB >1G "
-                                   "(0x%08x, len: %u)\n",
-                      dmaaddr, ring->rx_buffersize);
+                                   "(0x%llx, len: %u)\n",
+                       (unsigned long long)dmaaddr, ring->rx_buffersize);
                return -ENOMEM;
        }
        meta->skb = skb;
@@ -729,8 +730,8 @@ static int dma_tx_fragment(struct bcm43xx_dmaring *ring,
        if (unlikely(meta->dmaaddr + skb->len > BCM43xx_DMA_BUSADDRMAX)) {
                return_slot(ring, slot);
                printk(KERN_ERR PFX ">>>FATAL ERROR<<<  DMA TX SKB >1G "
-                                   "(0x%08x, len: %u)\n",
-                      meta->dmaaddr, skb->len);
+                                   "(0x%llx, len: %u)\n",
+                       (unsigned long long)meta->dmaaddr, skb->len);
                return -ENOMEM;
        }
 
index c37371fc9e01a4c818f2402606d9aa9739c764a7..9a06e61df0a253c4fed8e0df22af350e8979e58f 100644 (file)
@@ -52,6 +52,7 @@
 #include "bcm43xx_wx.h"
 #include "bcm43xx_ethtool.h"
 #include "bcm43xx_xmit.h"
+#include "bcm43xx_sysfs.h"
 
 
 MODULE_DESCRIPTION("Broadcom BCM43xx wireless driver");
@@ -3522,6 +3523,7 @@ static inline int bcm43xx_tx(struct bcm43xx_private *bcm,
                err = bcm43xx_pio_tx(bcm, txb);
        else
                err = bcm43xx_dma_tx(bcm, txb);
+       bcm->net_dev->trans_start = jiffies;
 
        return err;
 }
index 0a66f43ca0c01a1089fccaa3b66bf1bb28661c0e..33137165727f7c69c054a9507324beda7fcd2830 100644 (file)
@@ -2151,6 +2151,7 @@ int bcm43xx_phy_init_tssi2dbm_table(struct bcm43xx_private *bcm)
                                phy->tssi2dbm = NULL;
                                printk(KERN_ERR PFX "Could not generate "
                                                    "tssi2dBm table\n");
+                               kfree(dyn_tssi2dbm);
                                return -ENODEV;
                        }
                phy->tssi2dbm = dyn_tssi2dbm;
index 3c92b62807c56afafd5a88a04b8ab8d3f29ccdbb..6569da3a7a395987f8be1e5a6a285580343066fa 100644 (file)
 #include "bcm43xx_main.h"
 
 
+/* Get the Slow Clock Source */
+static int bcm43xx_pctl_get_slowclksrc(struct bcm43xx_private *bcm)
+{
+       u32 tmp;
+       int err;
+
+       assert(bcm->current_core == &bcm->core_chipcommon);
+       if (bcm->current_core->rev < 6) {
+               if (bcm->bustype == BCM43xx_BUSTYPE_PCMCIA ||
+                   bcm->bustype == BCM43xx_BUSTYPE_SB)
+                       return BCM43xx_PCTL_CLKSRC_XTALOS;
+               if (bcm->bustype == BCM43xx_BUSTYPE_PCI) {
+                       err = bcm43xx_pci_read_config32(bcm, BCM43xx_PCTL_OUT, &tmp);
+                       assert(!err);
+                       if (tmp & 0x10)
+                               return BCM43xx_PCTL_CLKSRC_PCI;
+                       return BCM43xx_PCTL_CLKSRC_XTALOS;
+               }
+       }
+       if (bcm->current_core->rev < 10) {
+               tmp = bcm43xx_read32(bcm, BCM43xx_CHIPCOMMON_SLOWCLKCTL);
+               tmp &= 0x7;
+               if (tmp == 0)
+                       return BCM43xx_PCTL_CLKSRC_LOPWROS;
+               if (tmp == 1)
+                       return BCM43xx_PCTL_CLKSRC_XTALOS;
+               if (tmp == 2)
+                       return BCM43xx_PCTL_CLKSRC_PCI;
+       }
+
+       return BCM43xx_PCTL_CLKSRC_XTALOS;
+}
+
 /* Get max/min slowclock frequency
  * as described in http://bcm-specs.sipsolutions.net/PowerControl
  */
 static int bcm43xx_pctl_clockfreqlimit(struct bcm43xx_private *bcm,
                                       int get_max)
 {
-       int limit = 0;
+       int limit;
+       int clocksrc;
        int divisor;
-       int selection;
-       int err;
        u32 tmp;
-       struct bcm43xx_coreinfo *old_core;
 
-       if (!(bcm->chipcommon_capabilities & BCM43xx_CAPABILITIES_PCTL))
-               goto out;
-       old_core = bcm->current_core;
-       err = bcm43xx_switch_core(bcm, &bcm->core_chipcommon);
-       if (err)
-               goto out;
+       assert(bcm->chipcommon_capabilities & BCM43xx_CAPABILITIES_PCTL);
+       assert(bcm->current_core == &bcm->core_chipcommon);
 
+       clocksrc = bcm43xx_pctl_get_slowclksrc(bcm);
        if (bcm->current_core->rev < 6) {
-               if ((bcm->bustype == BCM43xx_BUSTYPE_PCMCIA) ||
-                       (bcm->bustype == BCM43xx_BUSTYPE_SB)) {
-                       selection = 1;
+               switch (clocksrc) {
+               case BCM43xx_PCTL_CLKSRC_PCI:
+                       divisor = 64;
+                       break;
+               case BCM43xx_PCTL_CLKSRC_XTALOS:
                        divisor = 32;
-               } else {
-                       err = bcm43xx_pci_read_config32(bcm, BCM43xx_PCTL_OUT, &tmp);
-                       if (err) {
-                               printk(KERN_ERR PFX "clockfreqlimit pcicfg read failure\n");
-                               goto out_switchback;
-                       }
-                       if (tmp & 0x10) {
-                               /* PCI */
-                               selection = 2;
-                               divisor = 64;
-                       } else {
-                               /* XTAL */
-                               selection = 1;
-                               divisor = 32;
-                       }
+                       break;
+               default:
+                       assert(0);
+                       divisor = 1;
                }
        } else if (bcm->current_core->rev < 10) {
-               selection = (tmp & 0x07);
-               if (selection) {
+               switch (clocksrc) {
+               case BCM43xx_PCTL_CLKSRC_LOPWROS:
+                       divisor = 1;
+                       break;
+               case BCM43xx_PCTL_CLKSRC_XTALOS:
+               case BCM43xx_PCTL_CLKSRC_PCI:
                        tmp = bcm43xx_read32(bcm, BCM43xx_CHIPCOMMON_SLOWCLKCTL);
-                       divisor = 4 * (1 + ((tmp & 0xFFFF0000) >> 16));
-               } else
+                       divisor = ((tmp & 0xFFFF0000) >> 16) + 1;
+                       divisor *= 4;
+                       break;
+               default:
+                       assert(0);
                        divisor = 1;
+               }
        } else {
                tmp = bcm43xx_read32(bcm, BCM43xx_CHIPCOMMON_SYSCLKCTL);
-               divisor = 4 * (1 + ((tmp & 0xFFFF0000) >> 16));
-               selection = 1;
+               divisor = ((tmp & 0xFFFF0000) >> 16) + 1;
+               divisor *= 4;
        }
-       
-       switch (selection) {
-       case 0:
-               /* LPO */
+
+       switch (clocksrc) {
+       case BCM43xx_PCTL_CLKSRC_LOPWROS:
                if (get_max)
                        limit = 43000;
                else
                        limit = 25000;
                break;
-       case 1:
-               /* XTAL */
+       case BCM43xx_PCTL_CLKSRC_XTALOS:
                if (get_max)
                        limit = 20200000;
                else
                        limit = 19800000;
                break;
-       case 2:
-               /* PCI */
+       case BCM43xx_PCTL_CLKSRC_PCI:
                if (get_max)
                        limit = 34000000;
                else
@@ -113,17 +137,14 @@ static int bcm43xx_pctl_clockfreqlimit(struct bcm43xx_private *bcm,
                break;
        default:
                assert(0);
+               limit = 0;
        }
        limit /= divisor;
 
-out_switchback:
-       err = bcm43xx_switch_core(bcm, old_core);
-       assert(err == 0);
-
-out:
        return limit;
 }
 
+
 /* init power control
  * as described in http://bcm-specs.sipsolutions.net/PowerControl
  */
index 5f63640810bdc01302d85dc734645b6b7ff3061b..c966ab3a5a8c9f806a7dcb8dd2cb4db910c873e0 100644 (file)
 
 #include <linux/types.h>
 
+/* Clock sources */
+enum {
+       /* PCI clock */
+       BCM43xx_PCTL_CLKSRC_PCI,
+       /* Crystal slow clock oscillator */
+       BCM43xx_PCTL_CLKSRC_XTALOS,
+       /* Low power oscillator */
+       BCM43xx_PCTL_CLKSRC_LOPWROS,
+};
 
 struct bcm43xx_private;
 
index c44d890b949b149f5346ea7d0205f2bd08b3fd12..b438f48e891d185c2933828ee2b9080de3097564 100644 (file)
@@ -71,14 +71,46 @@ static int get_boolean(const char *buf, size_t count)
        return -EINVAL;
 }
 
+static int sprom2hex(const u16 *sprom, char *buf, size_t buf_len)
+{
+       int i, pos = 0;
+
+       for (i = 0; i < BCM43xx_SPROM_SIZE; i++) {
+               pos += snprintf(buf + pos, buf_len - pos - 1,
+                               "%04X", swab16(sprom[i]) & 0xFFFF);
+       }
+       pos += snprintf(buf + pos, buf_len - pos - 1, "\n");
+
+       return pos + 1;
+}
+
+static int hex2sprom(u16 *sprom, const char *dump, size_t len)
+{
+       char tmp[5] = { 0 };
+       int cnt = 0;
+       unsigned long parsed;
+
+       if (len < BCM43xx_SPROM_SIZE * sizeof(u16) * 2)
+               return -EINVAL;
+
+       while (cnt < BCM43xx_SPROM_SIZE) {
+               memcpy(tmp, dump, 4);
+               dump += 4;
+               parsed = simple_strtoul(tmp, NULL, 16);
+               sprom[cnt++] = swab16((u16)parsed);
+       }
+
+       return 0;
+}
+
 static ssize_t bcm43xx_attr_sprom_show(struct device *dev,
                                       struct device_attribute *attr,
                                       char *buf)
 {
-       struct bcm43xx_private *bcm = devattr_to_bcm(attr, attr_sprom);
+       struct bcm43xx_private *bcm = dev_to_bcm(dev);
        u16 *sprom;
        unsigned long flags;
-       int i, err;
+       int err;
 
        if (!capable(CAP_NET_ADMIN))
                return -EPERM;
@@ -91,55 +123,53 @@ static ssize_t bcm43xx_attr_sprom_show(struct device *dev,
        bcm43xx_lock_mmio(bcm, flags);
        assert(bcm->initialized);
        err = bcm43xx_sprom_read(bcm, sprom);
-       if (!err) {
-               for (i = 0; i < BCM43xx_SPROM_SIZE; i++) {
-                       buf[i * 2] = sprom[i] & 0x00FF;
-                       buf[i * 2 + 1] = (sprom[i] & 0xFF00) >> 8;
-               }
-       }
+       if (!err)
+               err = sprom2hex(sprom, buf, PAGE_SIZE);
        bcm43xx_unlock_mmio(bcm, flags);
        kfree(sprom);
 
-       return err ? err : BCM43xx_SPROM_SIZE * sizeof(u16);
+       return err;
 }
 
 static ssize_t bcm43xx_attr_sprom_store(struct device *dev,
                                        struct device_attribute *attr,
                                        const char *buf, size_t count)
 {
-       struct bcm43xx_private *bcm = devattr_to_bcm(attr, attr_sprom);
+       struct bcm43xx_private *bcm = dev_to_bcm(dev);
        u16 *sprom;
        unsigned long flags;
-       int i, err;
+       int err;
 
        if (!capable(CAP_NET_ADMIN))
                return -EPERM;
 
-       if (count != BCM43xx_SPROM_SIZE * sizeof(u16))
-               return -EINVAL;
        sprom = kmalloc(BCM43xx_SPROM_SIZE * sizeof(*sprom),
                        GFP_KERNEL);
        if (!sprom)
                return -ENOMEM;
-       for (i = 0; i < BCM43xx_SPROM_SIZE; i++) {
-               sprom[i] = buf[i * 2] & 0xFF;
-               sprom[i] |= ((u16)(buf[i * 2 + 1] & 0xFF)) << 8;
-       }
+       err = hex2sprom(sprom, buf, count);
+       if (err)
+               goto out_kfree;
        bcm43xx_lock_mmio(bcm, flags);
        assert(bcm->initialized);
        err = bcm43xx_sprom_write(bcm, sprom);
        bcm43xx_unlock_mmio(bcm, flags);
+out_kfree:
        kfree(sprom);
 
        return err ? err : count;
 
 }
 
+static DEVICE_ATTR(sprom, 0600,
+                  bcm43xx_attr_sprom_show,
+                  bcm43xx_attr_sprom_store);
+
 static ssize_t bcm43xx_attr_interfmode_show(struct device *dev,
                                            struct device_attribute *attr,
                                            char *buf)
 {
-       struct bcm43xx_private *bcm = devattr_to_bcm(attr, attr_interfmode);
+       struct bcm43xx_private *bcm = dev_to_bcm(dev);
        unsigned long flags;
        int err;
        ssize_t count = 0;
@@ -175,7 +205,7 @@ static ssize_t bcm43xx_attr_interfmode_store(struct device *dev,
                                             struct device_attribute *attr,
                                             const char *buf, size_t count)
 {
-       struct bcm43xx_private *bcm = devattr_to_bcm(attr, attr_interfmode);
+       struct bcm43xx_private *bcm = dev_to_bcm(dev);
        unsigned long flags;
        int err;
        int mode;
@@ -215,11 +245,15 @@ static ssize_t bcm43xx_attr_interfmode_store(struct device *dev,
        return err ? err : count;
 }
 
+static DEVICE_ATTR(interference, 0644,
+                  bcm43xx_attr_interfmode_show,
+                  bcm43xx_attr_interfmode_store);
+
 static ssize_t bcm43xx_attr_preamble_show(struct device *dev,
                                          struct device_attribute *attr,
                                          char *buf)
 {
-       struct bcm43xx_private *bcm = devattr_to_bcm(attr, attr_preamble);
+       struct bcm43xx_private *bcm = dev_to_bcm(dev);
        unsigned long flags;
        int err;
        ssize_t count;
@@ -245,7 +279,7 @@ static ssize_t bcm43xx_attr_preamble_store(struct device *dev,
                                           struct device_attribute *attr,
                                           const char *buf, size_t count)
 {
-       struct bcm43xx_private *bcm = devattr_to_bcm(attr, attr_preamble);
+       struct bcm43xx_private *bcm = dev_to_bcm(dev);
        unsigned long flags;
        int err;
        int value;
@@ -267,56 +301,41 @@ static ssize_t bcm43xx_attr_preamble_store(struct device *dev,
        return err ? err : count;
 }
 
+static DEVICE_ATTR(shortpreamble, 0644,
+                  bcm43xx_attr_preamble_show,
+                  bcm43xx_attr_preamble_store);
+
 int bcm43xx_sysfs_register(struct bcm43xx_private *bcm)
 {
        struct device *dev = &bcm->pci_dev->dev;
-       struct bcm43xx_sysfs *sysfs = &bcm->sysfs;
        int err;
 
        assert(bcm->initialized);
 
-       sysfs->attr_sprom.attr.name = "sprom";
-       sysfs->attr_sprom.attr.owner = THIS_MODULE;
-       sysfs->attr_sprom.attr.mode = 0600;
-       sysfs->attr_sprom.show = bcm43xx_attr_sprom_show;
-       sysfs->attr_sprom.store = bcm43xx_attr_sprom_store;
-       err = device_create_file(dev, &sysfs->attr_sprom);
+       err = device_create_file(dev, &dev_attr_sprom);
        if (err)
                goto out;
-
-       sysfs->attr_interfmode.attr.name = "interference";
-       sysfs->attr_interfmode.attr.owner = THIS_MODULE;
-       sysfs->attr_interfmode.attr.mode = 0600;
-       sysfs->attr_interfmode.show = bcm43xx_attr_interfmode_show;
-       sysfs->attr_interfmode.store = bcm43xx_attr_interfmode_store;
-       err = device_create_file(dev, &sysfs->attr_interfmode);
+       err = device_create_file(dev, &dev_attr_interference);
        if (err)
                goto err_remove_sprom;
-
-       sysfs->attr_preamble.attr.name = "shortpreamble";
-       sysfs->attr_preamble.attr.owner = THIS_MODULE;
-       sysfs->attr_preamble.attr.mode = 0600;
-       sysfs->attr_preamble.show = bcm43xx_attr_preamble_show;
-       sysfs->attr_preamble.store = bcm43xx_attr_preamble_store;
-       err = device_create_file(dev, &sysfs->attr_preamble);
+       err = device_create_file(dev, &dev_attr_shortpreamble);
        if (err)
                goto err_remove_interfmode;
 
 out:
        return err;
 err_remove_interfmode:
-       device_remove_file(dev, &sysfs->attr_interfmode);
+       device_remove_file(dev, &dev_attr_interference);
 err_remove_sprom:
-       device_remove_file(dev, &sysfs->attr_sprom);
+       device_remove_file(dev, &dev_attr_sprom);
        goto out;
 }
 
 void bcm43xx_sysfs_unregister(struct bcm43xx_private *bcm)
 {
        struct device *dev = &bcm->pci_dev->dev;
-       struct bcm43xx_sysfs *sysfs = &bcm->sysfs;
 
-       device_remove_file(dev, &sysfs->attr_preamble);
-       device_remove_file(dev, &sysfs->attr_interfmode);
-       device_remove_file(dev, &sysfs->attr_sprom);
+       device_remove_file(dev, &dev_attr_shortpreamble);
+       device_remove_file(dev, &dev_attr_interference);
+       device_remove_file(dev, &dev_attr_sprom);
 }
index 57f14514e3e073d6fc56cb895a2c128487088e83..cc701df71e2a0637bce01d67cefe3ce6e858f5d8 100644 (file)
@@ -1,22 +1,6 @@
 #ifndef BCM43xx_SYSFS_H_
 #define BCM43xx_SYSFS_H_
 
-#include <linux/device.h>
-
-
-struct bcm43xx_sysfs {
-       struct device_attribute attr_sprom;
-       struct device_attribute attr_interfmode;
-       struct device_attribute attr_preamble;
-};
-
-#define devattr_to_bcm(attr, attr_name)        ({                              \
-       struct bcm43xx_sysfs *__s; struct bcm43xx_private *__p;         \
-       __s = container_of((attr), struct bcm43xx_sysfs, attr_name);    \
-       __p = container_of(__s, struct bcm43xx_private, sysfs);         \
-       __p;                                                            \
-                                       })
-
 struct bcm43xx_private;
 
 int bcm43xx_sysfs_register(struct bcm43xx_private *bcm);
index 3daee828ef4b7a78ad68a6e4cb3ddfb8d148c768..3edbb481a0a035ebd957decbe43a76cad3c294e6 100644 (file)
@@ -962,22 +962,22 @@ static const struct iw_priv_args bcm43xx_priv_wx_args[] = {
        {
                .cmd            = PRIV_WX_SET_SHORTPREAMBLE,
                .set_args       = IW_PRIV_TYPE_INT | IW_PRIV_SIZE_FIXED | 1,
-               .name           = "set_shortpreambl",
+               .name           = "set_shortpreamb",
        },
        {
                .cmd            = PRIV_WX_GET_SHORTPREAMBLE,
                .get_args       = IW_PRIV_TYPE_CHAR | IW_PRIV_SIZE_FIXED | MAX_WX_STRING,
-               .name           = "get_shortpreambl",
+               .name           = "get_shortpreamb",
        },
        {
                .cmd            = PRIV_WX_SET_SWENCRYPTION,
                .set_args       = IW_PRIV_TYPE_INT | IW_PRIV_SIZE_FIXED | 1,
-               .name           = "set_swencryption",
+               .name           = "set_swencrypt",
        },
        {
                .cmd            = PRIV_WX_GET_SWENCRYPTION,
                .get_args       = IW_PRIV_TYPE_CHAR | IW_PRIV_SIZE_FIXED | MAX_WX_STRING,
-               .name           = "get_swencryption",
+               .name           = "get_swencrypt",
        },
        {
                .cmd            = PRIV_WX_SPROM_WRITE,
index 8dfdfbd5966c5b1b95e54617009eab26fa55dd6b..06523e2a8471f0be0a3fd5e2ef09625283667596 100644 (file)
@@ -390,7 +390,7 @@ static struct iw_statistics *orinoco_get_wireless_stats(struct net_device *dev)
                }
        } else {
                struct {
-                       __le16 qual, signal, noise;
+                       __le16 qual, signal, noise, unused;
                } __attribute__ ((packed)) cq;
 
                err = HERMES_READ_RECORD(hw, USER_BAP,
index d5890027f8af86b0c11f5bf5222eba4fd8f01b05..48bbf32fd9802cb76e72eb1c8d8707e3d24d2357 100644 (file)
@@ -97,7 +97,7 @@ static struct superio_struct {        /* For Super-IO chips autodetection */
        int io;
        int irq;
        int dma;
-} superios[NR_SUPERIOS] __devinitdata = { {0,},};
+} superios[NR_SUPERIOS] = { {0,},};
 
 static int user_specified;
 #if defined(CONFIG_PARPORT_PC_SUPERIO) || \
@@ -1557,7 +1557,7 @@ static int __devinit get_superio_dma (struct parport *p)
        return PARPORT_DMA_NONE;
 }
 
-static int __devinit get_superio_irq (struct parport *p)
+static int get_superio_irq (struct parport *p)
 {
        int i=0;
         while( (superios[i].io != p->base) && (i<NR_SUPERIOS))
@@ -1579,7 +1579,7 @@ static int __devinit get_superio_irq (struct parport *p)
  *                         this shall always be the case!)
  *
  */
-static int __devinit parport_SPP_supported(struct parport *pb)
+static int parport_SPP_supported(struct parport *pb)
 {
        unsigned char r, w;
 
@@ -1660,7 +1660,7 @@ static int __devinit parport_SPP_supported(struct parport *pb)
  * two bits of ECR aren't writable, so we check by writing ECR and
  * reading it back to see if it's what we expect.
  */
-static int __devinit parport_ECR_present(struct parport *pb)
+static int parport_ECR_present(struct parport *pb)
 {
        struct parport_pc_private *priv = pb->private_data;
        unsigned char r = 0xc;
@@ -1712,7 +1712,7 @@ static int __devinit parport_ECR_present(struct parport *pb)
  * be misdetected here is rather academic. 
  */
 
-static int __devinit parport_PS2_supported(struct parport *pb)
+static int parport_PS2_supported(struct parport *pb)
 {
        int ok = 0;
   
@@ -1868,7 +1868,7 @@ static int __devinit parport_ECP_supported(struct parport *pb)
 }
 #endif
 
-static int __devinit parport_ECPPS2_supported(struct parport *pb)
+static int parport_ECPPS2_supported(struct parport *pb)
 {
        const struct parport_pc_private *priv = pb->private_data;
        int result;
@@ -1886,7 +1886,7 @@ static int __devinit parport_ECPPS2_supported(struct parport *pb)
 
 /* EPP mode detection  */
 
-static int __devinit parport_EPP_supported(struct parport *pb)
+static int parport_EPP_supported(struct parport *pb)
 {
        const struct parport_pc_private *priv = pb->private_data;
 
@@ -1931,7 +1931,7 @@ static int __devinit parport_EPP_supported(struct parport *pb)
        return 1;
 }
 
-static int __devinit parport_ECPEPP_supported(struct parport *pb)
+static int parport_ECPEPP_supported(struct parport *pb)
 {
        struct parport_pc_private *priv = pb->private_data;
        int result;
@@ -2073,7 +2073,7 @@ static int __devinit irq_probe_SPP(struct parport *pb)
  * When ECP is available we can autoprobe for IRQs.
  * NOTE: If we can autoprobe it, we can register the IRQ.
  */
-static int __devinit parport_irq_probe(struct parport *pb)
+static int parport_irq_probe(struct parport *pb)
 {
        struct parport_pc_private *priv = pb->private_data;
 
@@ -2779,7 +2779,7 @@ static struct parport_pc_pci {
        /* If set, this is called after probing for ports.  If 'failed'
         * is non-zero we couldn't use any of the ports. */
        void (*postinit_hook) (struct pci_dev *pdev, int failed);
-} cards[] __devinitdata = {
+} cards[] = {
        /* siig_1p_10x */               { 1, { { 2, 3 }, } },
        /* siig_2p_10x */               { 2, { { 2, 3 }, { 4, 5 }, } },
        /* siig_1p_20x */               { 1, { { 0, 1 }, } },
index d121644646b9e53a377ebd6916a8dec04a7405da..98b83a85c60e2d462fe92e4e39de2e6f0e977945 100644 (file)
@@ -100,8 +100,6 @@ static struct pci_device_id parport_serial_pci_tbl[] = {
          PCI_ANY_ID, PCI_ANY_ID, 0, 0, netmos_9xx5_combo },
        { PCI_VENDOR_ID_NETMOS, PCI_DEVICE_ID_NETMOS_9835,
          PCI_ANY_ID, PCI_ANY_ID, 0, 0, netmos_9xx5_combo },
-       { PCI_VENDOR_ID_NETMOS, PCI_DEVICE_ID_NETMOS_9835,
-         PCI_ANY_ID, PCI_ANY_ID, 0, 0, netmos_9xx5_combo },
        { PCI_VENDOR_ID_NETMOS, PCI_DEVICE_ID_NETMOS_9845,
          PCI_ANY_ID, PCI_ANY_ID, 0, 0, netmos_9xx5_combo },
        { PCI_VENDOR_ID_NETMOS, PCI_DEVICE_ID_NETMOS_9855,
index 6e79f5675b0d9b804a8c8465e07f0884d59dc63a..638004546700a9dd809a887914be8a4fe3f681e6 100644 (file)
@@ -360,9 +360,6 @@ static int __init rpaphp_init(void)
        while ((dn = of_find_node_by_type(dn, "pci")))
                rpaphp_add_slot(dn);
 
-       if (!num_slots)
-               return -ENODEV;
-
        return 0;
 }
 
index a77e79c8c82ef74ffe73f6dd606c5b598125ec50..2087a397ef16768d09498ab326a300b12ec14744 100644 (file)
@@ -504,6 +504,201 @@ void pci_scan_msi_device(struct pci_dev *dev)
                nr_reserved_vectors++;
 }
 
+#ifdef CONFIG_PM
+int pci_save_msi_state(struct pci_dev *dev)
+{
+       int pos, i = 0;
+       u16 control;
+       struct pci_cap_saved_state *save_state;
+       u32 *cap;
+
+       pos = pci_find_capability(dev, PCI_CAP_ID_MSI);
+       if (pos <= 0 || dev->no_msi)
+               return 0;
+
+       pci_read_config_word(dev, msi_control_reg(pos), &control);
+       if (!(control & PCI_MSI_FLAGS_ENABLE))
+               return 0;
+
+       save_state = kzalloc(sizeof(struct pci_cap_saved_state) + sizeof(u32) * 5,
+               GFP_KERNEL);
+       if (!save_state) {
+               printk(KERN_ERR "Out of memory in pci_save_msi_state\n");
+               return -ENOMEM;
+       }
+       cap = &save_state->data[0];
+
+       pci_read_config_dword(dev, pos, &cap[i++]);
+       control = cap[0] >> 16;
+       pci_read_config_dword(dev, pos + PCI_MSI_ADDRESS_LO, &cap[i++]);
+       if (control & PCI_MSI_FLAGS_64BIT) {
+               pci_read_config_dword(dev, pos + PCI_MSI_ADDRESS_HI, &cap[i++]);
+               pci_read_config_dword(dev, pos + PCI_MSI_DATA_64, &cap[i++]);
+       } else
+               pci_read_config_dword(dev, pos + PCI_MSI_DATA_32, &cap[i++]);
+       if (control & PCI_MSI_FLAGS_MASKBIT)
+               pci_read_config_dword(dev, pos + PCI_MSI_MASK_BIT, &cap[i++]);
+       disable_msi_mode(dev, pos, PCI_CAP_ID_MSI);
+       save_state->cap_nr = PCI_CAP_ID_MSI;
+       pci_add_saved_cap(dev, save_state);
+       return 0;
+}
+
+void pci_restore_msi_state(struct pci_dev *dev)
+{
+       int i = 0, pos;
+       u16 control;
+       struct pci_cap_saved_state *save_state;
+       u32 *cap;
+
+       save_state = pci_find_saved_cap(dev, PCI_CAP_ID_MSI);
+       pos = pci_find_capability(dev, PCI_CAP_ID_MSI);
+       if (!save_state || pos <= 0)
+               return;
+       cap = &save_state->data[0];
+
+       control = cap[i++] >> 16;
+       pci_write_config_dword(dev, pos + PCI_MSI_ADDRESS_LO, cap[i++]);
+       if (control & PCI_MSI_FLAGS_64BIT) {
+               pci_write_config_dword(dev, pos + PCI_MSI_ADDRESS_HI, cap[i++]);
+               pci_write_config_dword(dev, pos + PCI_MSI_DATA_64, cap[i++]);
+       } else
+               pci_write_config_dword(dev, pos + PCI_MSI_DATA_32, cap[i++]);
+       if (control & PCI_MSI_FLAGS_MASKBIT)
+               pci_write_config_dword(dev, pos + PCI_MSI_MASK_BIT, cap[i++]);
+       pci_write_config_word(dev, pos + PCI_MSI_FLAGS, control);
+       enable_msi_mode(dev, pos, PCI_CAP_ID_MSI);
+       pci_remove_saved_cap(save_state);
+       kfree(save_state);
+}
+
+int pci_save_msix_state(struct pci_dev *dev)
+{
+       int pos;
+       u16 control;
+       struct pci_cap_saved_state *save_state;
+
+       pos = pci_find_capability(dev, PCI_CAP_ID_MSIX);
+       if (pos <= 0 || dev->no_msi)
+               return 0;
+
+       pci_read_config_word(dev, msi_control_reg(pos), &control);
+       if (!(control & PCI_MSIX_FLAGS_ENABLE))
+               return 0;
+       save_state = kzalloc(sizeof(struct pci_cap_saved_state) + sizeof(u16),
+               GFP_KERNEL);
+       if (!save_state) {
+               printk(KERN_ERR "Out of memory in pci_save_msix_state\n");
+               return -ENOMEM;
+       }
+       *((u16 *)&save_state->data[0]) = control;
+
+       disable_msi_mode(dev, pos, PCI_CAP_ID_MSIX);
+       save_state->cap_nr = PCI_CAP_ID_MSIX;
+       pci_add_saved_cap(dev, save_state);
+       return 0;
+}
+
+void pci_restore_msix_state(struct pci_dev *dev)
+{
+       u16 save;
+       int pos;
+       int vector, head, tail = 0;
+       void __iomem *base;
+       int j;
+       struct msg_address address;
+       struct msg_data data;
+       struct msi_desc *entry;
+       int temp;
+       struct pci_cap_saved_state *save_state;
+
+       save_state = pci_find_saved_cap(dev, PCI_CAP_ID_MSIX);
+       if (!save_state)
+               return;
+       save = *((u16 *)&save_state->data[0]);
+       pci_remove_saved_cap(save_state);
+       kfree(save_state);
+
+       pos = pci_find_capability(dev, PCI_CAP_ID_MSIX);
+       if (pos <= 0)
+               return;
+
+       /* route the table */
+       temp = dev->irq;
+       if (msi_lookup_vector(dev, PCI_CAP_ID_MSIX))
+               return;
+       vector = head = dev->irq;
+       while (head != tail) {
+               entry = msi_desc[vector];
+               base = entry->mask_base;
+               j = entry->msi_attrib.entry_nr;
+
+               msi_address_init(&address);
+               msi_data_init(&data, vector);
+
+               address.lo_address.value &= MSI_ADDRESS_DEST_ID_MASK;
+               address.lo_address.value |= entry->msi_attrib.current_cpu <<
+                                       MSI_TARGET_CPU_SHIFT;
+
+               writel(address.lo_address.value,
+                       base + j * PCI_MSIX_ENTRY_SIZE +
+                       PCI_MSIX_ENTRY_LOWER_ADDR_OFFSET);
+               writel(address.hi_address,
+                       base + j * PCI_MSIX_ENTRY_SIZE +
+                       PCI_MSIX_ENTRY_UPPER_ADDR_OFFSET);
+               writel(*(u32*)&data,
+                       base + j * PCI_MSIX_ENTRY_SIZE +
+                       PCI_MSIX_ENTRY_DATA_OFFSET);
+
+               tail = msi_desc[vector]->link.tail;
+               vector = tail;
+       }
+       dev->irq = temp;
+
+       pci_write_config_word(dev, msi_control_reg(pos), save);
+       enable_msi_mode(dev, pos, PCI_CAP_ID_MSIX);
+}
+#endif
+
+static void msi_register_init(struct pci_dev *dev, struct msi_desc *entry)
+{
+       struct msg_address address;
+       struct msg_data data;
+       int pos, vector = dev->irq;
+       u16 control;
+
+       pos = pci_find_capability(dev, PCI_CAP_ID_MSI);
+       pci_read_config_word(dev, msi_control_reg(pos), &control);
+       /* Configure MSI capability structure */
+       msi_address_init(&address);
+       msi_data_init(&data, vector);
+       entry->msi_attrib.current_cpu = ((address.lo_address.u.dest_id >>
+                               MSI_TARGET_CPU_SHIFT) & MSI_TARGET_CPU_MASK);
+       pci_write_config_dword(dev, msi_lower_address_reg(pos),
+                       address.lo_address.value);
+       if (is_64bit_address(control)) {
+               pci_write_config_dword(dev,
+                       msi_upper_address_reg(pos), address.hi_address);
+               pci_write_config_word(dev,
+                       msi_data_reg(pos, 1), *((u32*)&data));
+       } else
+               pci_write_config_word(dev,
+                       msi_data_reg(pos, 0), *((u32*)&data));
+       if (entry->msi_attrib.maskbit) {
+               unsigned int maskbits, temp;
+               /* All MSIs are unmasked by default, Mask them all */
+               pci_read_config_dword(dev,
+                       msi_mask_bits_reg(pos, is_64bit_address(control)),
+                       &maskbits);
+               temp = (1 << multi_msi_capable(control));
+               temp = ((temp - 1) & ~temp);
+               maskbits |= temp;
+               pci_write_config_dword(dev,
+                       msi_mask_bits_reg(pos, is_64bit_address(control)),
+                       maskbits);
+       }
+}
+
 /**
  * msi_capability_init - configure device's MSI capability structure
  * @dev: pointer to the pci_dev data structure of MSI device function
@@ -516,8 +711,6 @@ void pci_scan_msi_device(struct pci_dev *dev)
 static int msi_capability_init(struct pci_dev *dev)
 {
        struct msi_desc *entry;
-       struct msg_address address;
-       struct msg_data data;
        int pos, vector;
        u16 control;
 
@@ -549,33 +742,8 @@ static int msi_capability_init(struct pci_dev *dev)
        /* Replace with MSI handler */
        irq_handler_init(PCI_CAP_ID_MSI, vector, entry->msi_attrib.maskbit);
        /* Configure MSI capability structure */
-       msi_address_init(&address);
-       msi_data_init(&data, vector);
-       entry->msi_attrib.current_cpu = ((address.lo_address.u.dest_id >>
-                               MSI_TARGET_CPU_SHIFT) & MSI_TARGET_CPU_MASK);
-       pci_write_config_dword(dev, msi_lower_address_reg(pos),
-                       address.lo_address.value);
-       if (is_64bit_address(control)) {
-               pci_write_config_dword(dev,
-                       msi_upper_address_reg(pos), address.hi_address);
-               pci_write_config_word(dev,
-                       msi_data_reg(pos, 1), *((u32*)&data));
-       } else
-               pci_write_config_word(dev,
-                       msi_data_reg(pos, 0), *((u32*)&data));
-       if (entry->msi_attrib.maskbit) {
-               unsigned int maskbits, temp;
-               /* All MSIs are unmasked by default, Mask them all */
-               pci_read_config_dword(dev,
-                       msi_mask_bits_reg(pos, is_64bit_address(control)),
-                       &maskbits);
-               temp = (1 << multi_msi_capable(control));
-               temp = ((temp - 1) & ~temp);
-               maskbits |= temp;
-               pci_write_config_dword(dev,
-                       msi_mask_bits_reg(pos, is_64bit_address(control)),
-                       maskbits);
-       }
+       msi_register_init(dev, entry);
+
        attach_msi_entry(entry, vector);
        /* Set MSI enabled bits  */
        enable_msi_mode(dev, pos, PCI_CAP_ID_MSI);
@@ -731,6 +899,7 @@ int pci_enable_msi(struct pci_dev* dev)
                        vector_irq[dev->irq] = -1;
                        nr_released_vectors--;
                        spin_unlock_irqrestore(&msi_lock, flags);
+                       msi_register_init(dev, msi_desc[dev->irq]);
                        enable_msi_mode(dev, pos, PCI_CAP_ID_MSI);
                        return 0;
                }
index f22f69ac644549600efee1280778343ece67b3c7..1456759936c59410f0af1aaab1d91d81c4e5f34f 100644 (file)
@@ -271,10 +271,12 @@ static int pci_device_suspend(struct device * dev, pm_message_t state)
        struct pci_driver * drv = pci_dev->driver;
        int i = 0;
 
-       if (drv && drv->suspend)
+       if (drv && drv->suspend) {
                i = drv->suspend(pci_dev, state);
-       else
+               suspend_report_result(drv->suspend, i);
+       } else {
                pci_save_state(pci_dev);
+       }
        return i;
 }
 
index bea1ad1ad5ba8d52c12f4f39d526889c914bf5fd..2329f941a0dcd11fa1f18c13f5129347c91581f7 100644 (file)
@@ -307,9 +307,11 @@ pci_set_power_state(struct pci_dev *dev, pci_power_t state)
         * Can enter D0 from any state, but if we can only go deeper 
         * to sleep if we're already in a low power state
         */
-       if (state != PCI_D0 && dev->current_state > state)
+       if (state != PCI_D0 && dev->current_state > state) {
+               printk(KERN_ERR "%s(): %s: state=%d, current state=%d\n",
+                       __FUNCTION__, pci_name(dev), state, dev->current_state);
                return -EINVAL;
-       else if (dev->current_state == state) 
+       } else if (dev->current_state == state)
                return 0;        /* we're already there */
 
        /* find PCI PM capability in list */
@@ -444,6 +446,10 @@ pci_save_state(struct pci_dev *dev)
        /* XXX: 100% dword access ok here? */
        for (i = 0; i < 16; i++)
                pci_read_config_dword(dev, i * 4,&dev->saved_config_space[i]);
+       if ((i = pci_save_msi_state(dev)) != 0)
+               return i;
+       if ((i = pci_save_msix_state(dev)) != 0)
+               return i;
        return 0;
 }
 
@@ -458,6 +464,8 @@ pci_restore_state(struct pci_dev *dev)
 
        for (i = 0; i < 16; i++)
                pci_write_config_dword(dev,i * 4, dev->saved_config_space[i]);
+       pci_restore_msi_state(dev);
+       pci_restore_msix_state(dev);
        return 0;
 }
 
index 8f3fb47ea671997a223189fc1cde878eb2ebff33..30630cbe2fe32c1d65465186b15ad8d083a031ff 100644 (file)
@@ -55,6 +55,17 @@ void pci_no_msi(void);
 static inline void disable_msi_mode(struct pci_dev *dev, int pos, int type) { }
 static inline void pci_no_msi(void) { }
 #endif
+#if defined(CONFIG_PCI_MSI) && defined(CONFIG_PM)
+int pci_save_msi_state(struct pci_dev *dev);
+int pci_save_msix_state(struct pci_dev *dev);
+void pci_restore_msi_state(struct pci_dev *dev);
+void pci_restore_msix_state(struct pci_dev *dev);
+#else
+static inline int pci_save_msi_state(struct pci_dev *dev) { return 0; }
+static inline int pci_save_msix_state(struct pci_dev *dev) { return 0; }
+static inline void pci_restore_msi_state(struct pci_dev *dev) {}
+static inline void pci_restore_msix_state(struct pci_dev *dev) {}
+#endif
 
 extern int pcie_mch_quirk;
 extern struct device_attribute pci_dev_attrs[];
index 4970f47be72c55241eec95961abfb96a8f2f32f1..c42ae2cf8d64a262036381bd07ebb66b5d1b1cf8 100644 (file)
@@ -592,7 +592,7 @@ static void __init quirk_amd_8131_ioapic(struct pci_dev *dev)
                 pci_write_config_byte( dev, AMD8131_MISC, tmp);
         }
 } 
-DECLARE_PCI_FIXUP_FINAL(PCI_VENDOR_ID_AMD, PCI_DEVICE_ID_AMD_8131_APIC,         quirk_amd_8131_ioapic ); 
+DECLARE_PCI_FIXUP_FINAL(PCI_VENDOR_ID_AMD, PCI_DEVICE_ID_AMD_8131_BRIDGE, quirk_amd_8131_ioapic);
 
 static void __init quirk_svw_msi(struct pci_dev *dev)
 {
@@ -864,6 +864,35 @@ static void __init quirk_eisa_bridge(struct pci_dev *dev)
 }
 DECLARE_PCI_FIXUP_HEADER(PCI_VENDOR_ID_INTEL,  PCI_DEVICE_ID_INTEL_82375,      quirk_eisa_bridge );
 
+/*
+ * On the MSI-K8T-Neo2Fir Board, the internal Soundcard is disabled
+ * when a PCI-Soundcard is added. The BIOS only gives Options
+ * "Disabled" and "AUTO". This Quirk Sets the corresponding
+ * Register-Value to enable the Soundcard.
+ */
+static void __init k8t_sound_hostbridge(struct pci_dev *dev)
+{
+       unsigned char val;
+
+       printk(KERN_INFO "PCI: Quirk-MSI-K8T Soundcard On\n");
+       pci_read_config_byte(dev, 0x50, &val);
+       if (val == 0x88 || val == 0xc8) {
+               pci_write_config_byte(dev, 0x50, val & (~0x40));
+
+               /* Verify the Change for Status output */
+               pci_read_config_byte(dev, 0x50, &val);
+               if (val & 0x40)
+                       printk(KERN_INFO "PCI: MSI-K8T soundcard still off\n");
+               else
+                       printk(KERN_INFO "PCI: MSI-K8T soundcard on\n");
+       } else {
+               printk(KERN_INFO "PCI: Unexpected Value in PCI-Register: "
+                                       "no Change!\n");
+       }
+
+}
+DECLARE_PCI_FIXUP_HEADER(PCI_VENDOR_ID_VIA, PCI_DEVICE_ID_VIA_8237, k8t_sound_hostbridge);
+
 /*
  * On ASUS P4B boards, the SMBus PCI Device within the ICH2/4 southbridge
  * is not activated. The myth is that Asus said that they do not want the
@@ -921,6 +950,7 @@ static void __init asus_hides_smbus_hostbridge(struct pci_dev *dev)
                if (dev->device == PCI_DEVICE_ID_INTEL_82915GM_HB) {
                        switch (dev->subsystem_device) {
                        case 0x1882: /* M6V notebook */
+                       case 0x1977: /* A6VA notebook */
                                asus_hides_smbus = 1;
                        }
                }
@@ -999,6 +1029,7 @@ DECLARE_PCI_FIXUP_HEADER(PCI_VENDOR_ID_INTEL,      PCI_DEVICE_ID_INTEL_82801BA_0,  asu
 DECLARE_PCI_FIXUP_HEADER(PCI_VENDOR_ID_INTEL,  PCI_DEVICE_ID_INTEL_82801CA_12, asus_hides_smbus_lpc );
 DECLARE_PCI_FIXUP_HEADER(PCI_VENDOR_ID_INTEL,  PCI_DEVICE_ID_INTEL_82801DB_12, asus_hides_smbus_lpc );
 DECLARE_PCI_FIXUP_HEADER(PCI_VENDOR_ID_INTEL,  PCI_DEVICE_ID_INTEL_82801EB_0,  asus_hides_smbus_lpc );
+DECLARE_PCI_FIXUP_HEADER(PCI_VENDOR_ID_INTEL,  PCI_DEVICE_ID_INTEL_ICH6_1,     asus_hides_smbus_lpc );
 
 static void __init asus_hides_smbus_lpc_ich6(struct pci_dev *dev)
 {
index 67cc5f7d0c90634c42726f9157f4c1460dfb4d71..a4d50940ebebf0f652de3163077d312e30e39269 100644 (file)
@@ -28,8 +28,6 @@
 #include <asm/arch/gpio.h>
 
 
-#define        CF_SIZE         0x30000000      /* CS5+CS6: unavailable */
-
 /*
  * A0..A10 work in each range; A23 indicates I/O space;  A25 is CFRNW;
  * some other bit in {A24,A22..A11} is nREG to flag memory access
@@ -76,7 +74,8 @@ static irqreturn_t at91_cf_irq(int irq, void *_cf, struct pt_regs *r)
                /* kick pccard as needed */
                if (present != cf->present) {
                        cf->present = present;
-                       pr_debug("%s: card %s\n", driver_name, present ? "present" : "gone");
+                       pr_debug("%s: card %s\n", driver_name,
+                                       present ? "present" : "gone");
                        pcmcia_parse_events(&cf->socket, SS_DETECT);
                }
        }
@@ -93,7 +92,7 @@ static int at91_cf_get_status(struct pcmcia_socket *s, u_int *sp)
 
        cf = container_of(s, struct at91_cf_socket, socket);
 
-       /* NOTE: we assume 3VCARD, not XVCARD...  */
+       /* NOTE: CF is always 3VCARD */
        if (at91_cf_present(cf)) {
                int rdy = cf->board->irq_pin;   /* RDY/nIRQ */
                int vcc = cf->board->vcc_pin;
@@ -109,7 +108,8 @@ static int at91_cf_get_status(struct pcmcia_socket *s, u_int *sp)
        return 0;
 }
 
-static int at91_cf_set_socket(struct pcmcia_socket *sock, struct socket_state_t *s)
+static int
+at91_cf_set_socket(struct pcmcia_socket *sock, struct socket_state_t *s)
 {
        struct at91_cf_socket   *cf;
 
@@ -184,7 +184,8 @@ static int at91_cf_set_io_map(struct pcmcia_socket *s, struct pccard_io_map *io)
 }
 
 /* pcmcia layer maps/unmaps mem regions */
-static int at91_cf_set_mem_map(struct pcmcia_socket *s, struct pccard_mem_map *map)
+static int
+at91_cf_set_mem_map(struct pcmcia_socket *s, struct pccard_mem_map *map)
 {
        struct at91_cf_socket   *cf;
 
@@ -218,12 +219,17 @@ static int __init at91_cf_probe(struct device *dev)
        struct at91_cf_socket   *cf;
        struct at91_cf_data     *board = dev->platform_data;
        struct platform_device  *pdev = to_platform_device(dev);
+       struct resource         *io;
        unsigned int            csa;
        int                     status;
 
        if (!board || !board->det_pin || !board->rst_pin)
                return -ENODEV;
 
+       io = platform_get_resource(pdev, IORESOURCE_MEM, 0);
+       if (!io)
+               return -ENODEV;
+
        cf = kcalloc(1, sizeof *cf, GFP_KERNEL);
        if (!cf)
                return -ENOMEM;
@@ -250,10 +256,14 @@ static int __init at91_cf_probe(struct device *dev)
         * REVISIT:  these timings are in terms of MCK cycles, so
         * when MCK changes (cpufreq etc) so must these values...
         */
-       at91_sys_write(AT91_SMC_CSR(4), AT91_SMC_ACSS_STD | AT91_SMC_DBW_16 | AT91_SMC_BAT | AT91_SMC_WSEN
-                               | AT91_SMC_NWS_(32)             /* wait states */
-                               | AT91_SMC_RWSETUP_(6)          /* setup time */
-                               | AT91_SMC_RWHOLD_(4)           /* hold time */
+       at91_sys_write(AT91_SMC_CSR(4),
+                                 AT91_SMC_ACSS_STD
+                               | AT91_SMC_DBW_16
+                               | AT91_SMC_BAT
+                               | AT91_SMC_WSEN
+                               | AT91_SMC_NWS_(32)     /* wait states */
+                               | AT91_SMC_RWSETUP_(6)  /* setup time */
+                               | AT91_SMC_RWHOLD_(4)   /* hold time */
        );
 
        /* must be a GPIO; ergo must trigger on both edges */
@@ -274,8 +284,7 @@ static int __init at91_cf_probe(struct device *dev)
                if (status < 0)
                        goto fail0a;
                cf->socket.pci_irq = board->irq_pin;
-       }
-       else
+       } else
                cf->socket.pci_irq = NR_IRQS + 1;
 
        /* pcmcia layer only remaps "real" memory not iospace */
@@ -284,7 +293,8 @@ static int __init at91_cf_probe(struct device *dev)
                goto fail1;
 
        /* reserve CS4, CS5, and CS6 regions; but use just CS4 */
-       if (!request_mem_region(AT91_CF_BASE, CF_SIZE, driver_name))
+       if (!request_mem_region(io->start, io->end + 1 - io->start,
+                               driver_name))
                goto fail1;
 
        pr_info("%s: irqs det #%d, io #%d\n", driver_name,
@@ -297,7 +307,7 @@ static int __init at91_cf_probe(struct device *dev)
        cf->socket.features = SS_CAP_PCCARD | SS_CAP_STATIC_MAP
                                | SS_CAP_MEM_ALIGN;
        cf->socket.map_size = SZ_2K;
-       cf->socket.io[0].NumPorts = SZ_2K;
+       cf->socket.io[0].res = io;
 
        status = pcmcia_register_socket(&cf->socket);
        if (status < 0)
@@ -307,7 +317,7 @@ static int __init at91_cf_probe(struct device *dev)
 
 fail2:
        iounmap((void __iomem *) cf->socket.io_offset);
-       release_mem_region(AT91_CF_BASE, CF_SIZE);
+       release_mem_region(io->start, io->end + 1 - io->start);
 fail1:
        if (board->irq_pin)
                free_irq(board->irq_pin, cf);
@@ -321,14 +331,15 @@ fail0:
 
 static int __exit at91_cf_remove(struct device *dev)
 {
-       struct at91_cf_socket *cf = dev_get_drvdata(dev);
-       unsigned int csa;
+       struct at91_cf_socket   *cf = dev_get_drvdata(dev);
+       struct resource         *io = cf->socket.io[0].res;
+       unsigned int            csa;
 
        pcmcia_unregister_socket(&cf->socket);
        free_irq(cf->board->irq_pin, cf);
        free_irq(cf->board->det_pin, cf);
        iounmap((void __iomem *) cf->socket.io_offset);
-       release_mem_region(AT91_CF_BASE, CF_SIZE);
+       release_mem_region(io->start, io->end + 1 - io->start);
 
        csa = at91_sys_read(AT91_EBI_CSA);
        at91_sys_write(AT91_EBI_CSA, csa & ~AT91_EBI_CS4A);
@@ -342,8 +353,8 @@ static struct device_driver at91_cf_driver = {
        .bus            = &platform_bus_type,
        .probe          = at91_cf_probe,
        .remove         = __exit_p(at91_cf_remove),
-       .suspend        = pcmcia_socket_dev_suspend,
-       .resume         = pcmcia_socket_dev_resume,
+       .suspend        = pcmcia_socket_dev_suspend,
+       .resume         = pcmcia_socket_dev_resume,
 };
 
 /*--------------------------------------------------------------------------*/
index fd3647368955f1f68aa8dad0f99ed25994b8ed15..b7b9e149c5b9c73278b095ca99a368af8e8eac51 100644 (file)
 #include "soc_common.h"
 
 #define        NO_KEEP_VS 0x0001
-
-/* PCMCIA to Scoop linkage
-
-   There is no easy way to link multiple scoop devices into one
-   single entity for the pxa2xx_pcmcia device so this structure
-   is used which is setup by the platform code
-*/
-struct scoop_pcmcia_config *platform_scoop_config;
 #define SCOOP_DEV platform_scoop_config->devs
 
 static void sharpsl_pcmcia_init_reset(struct soc_pcmcia_socket *skt)
index c4256aa32bcb0cc296624301cc8087aabfdac350..6fff109bdab606e98eb188f70a4b4a1dcafe6415 100644 (file)
@@ -479,7 +479,7 @@ int pnp_auto_config_dev(struct pnp_dev *dev)
 int pnp_start_dev(struct pnp_dev *dev)
 {
        if (!pnp_can_write(dev)) {
-               pnp_info("Device %s does not supported activation.", dev->dev.bus_id);
+               pnp_info("Device %s does not support activation.", dev->dev.bus_id);
                return -EINVAL;
        }
 
@@ -503,7 +503,7 @@ int pnp_start_dev(struct pnp_dev *dev)
 int pnp_stop_dev(struct pnp_dev *dev)
 {
        if (!pnp_can_disable(dev)) {
-               pnp_info("Device %s does not supported disabling.", dev->dev.bus_id);
+               pnp_info("Device %s does not support disabling.", dev->dev.bus_id);
                return -EINVAL;
        }
        if (dev->protocol->disable(dev)<0) {
index 929dd8090578b07213ddb22733d585ab0f2d0668..65d090dbef460e70ccb4aae266e08ff8ba7576c7 100644 (file)
@@ -147,6 +147,16 @@ config RTC_DRV_SA1100
          To compile this driver as a module, choose M here: the
          module will be called rtc-sa1100.
 
+config RTC_DRV_VR41XX
+       tristate "NEC VR41XX"
+       depends on RTC_CLASS && CPU_VR41XX
+       help
+         If you say Y here you will get access to the real time clock
+         built into your NEC VR41XX CPU.
+
+         To compile this driver as a module, choose M here: the
+         module will be called rtc-vr41xx.
+
 config RTC_DRV_TEST
        tristate "Test driver/device"
        depends on RTC_CLASS
index 8d4c7fe88d58538bf66f3af267542e62cd889725..a9ca0f1716868154f9e5419754864543108f07e6 100644 (file)
@@ -19,3 +19,4 @@ obj-$(CONFIG_RTC_DRV_RS5C372) += rtc-rs5c372.o
 obj-$(CONFIG_RTC_DRV_M48T86)   += rtc-m48t86.o
 obj-$(CONFIG_RTC_DRV_EP93XX)   += rtc-ep93xx.o
 obj-$(CONFIG_RTC_DRV_SA1100)   += rtc-sa1100.o
+obj-$(CONFIG_RTC_DRV_VR41XX)   += rtc-vr41xx.o
index 8533936d50d86137383004ab75d0bdd67cfd4fc1..413c7d54ea10f19b9eeb5fa695b21b8ab7f11c66 100644 (file)
@@ -96,6 +96,8 @@ exit_idr:
        idr_remove(&rtc_idr, id);
 
 exit:
+       dev_err(dev, "rtc core: unable to register %s, err = %d\n",
+                       name, err);
        return ERR_PTR(err);
 }
 EXPORT_SYMBOL_GPL(rtc_device_register);
index 358695a416f32ec5f0da804e8c9efd5693e438ea..9be81fd4737c20c11cbcc4c2e466a41331c01434 100644 (file)
@@ -1,6 +1,8 @@
 /*
  * An rtc/i2c driver for the Dallas DS1672
- * Copyright 2005 Alessandro Zummo
+ * Copyright 2005-06 Tower Technologies
+ *
+ * Author: Alessandro Zummo <a.zummo@towertech.it>
  *
  * 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
@@ -11,7 +13,7 @@
 #include <linux/i2c.h>
 #include <linux/rtc.h>
 
-#define DRV_VERSION "0.2"
+#define DRV_VERSION "0.3"
 
 /* Addresses to scan: none. This chip cannot be detected. */
 static unsigned short normal_i2c[] = { I2C_CLIENT_END };
@@ -25,6 +27,7 @@ I2C_CLIENT_INSMOD;
 #define DS1672_REG_CONTROL     4
 #define DS1672_REG_TRICKLE     5
 
+#define DS1672_REG_CONTROL_EOSC        0x80
 
 /* Prototypes */
 static int ds1672_probe(struct i2c_adapter *adapter, int address, int kind);
@@ -53,8 +56,7 @@ static int ds1672_get_datetime(struct i2c_client *client, struct rtc_time *tm)
 
        dev_dbg(&client->dev,
                "%s: raw read data - counters=%02x,%02x,%02x,%02x\n"
-               __FUNCTION__,
-               buf[0], buf[1], buf[2], buf[3]);
+               __FUNCTION__, buf[0], buf[1], buf[2], buf[3]);
 
        time = (buf[3] << 24) | (buf[2] << 16) | (buf[1] << 8) | buf[0];
 
@@ -62,8 +64,7 @@ static int ds1672_get_datetime(struct i2c_client *client, struct rtc_time *tm)
 
        dev_dbg(&client->dev, "%s: tm is secs=%d, mins=%d, hours=%d, "
                "mday=%d, mon=%d, year=%d, wday=%d\n",
-               __FUNCTION__,
-               tm->tm_sec, tm->tm_min, tm->tm_hour,
+               __FUNCTION__, tm->tm_sec, tm->tm_min, tm->tm_hour,
                tm->tm_mday, tm->tm_mon, tm->tm_year, tm->tm_wday);
 
        return 0;
@@ -72,16 +73,17 @@ static int ds1672_get_datetime(struct i2c_client *client, struct rtc_time *tm)
 static int ds1672_set_mmss(struct i2c_client *client, unsigned long secs)
 {
        int xfer;
-       unsigned char buf[5];
+       unsigned char buf[6];
 
        buf[0] = DS1672_REG_CNT_BASE;
        buf[1] = secs & 0x000000FF;
        buf[2] = (secs & 0x0000FF00) >> 8;
        buf[3] = (secs & 0x00FF0000) >> 16;
        buf[4] = (secs & 0xFF000000) >> 24;
+       buf[5] = 0;     /* set control reg to enable counting */
 
-       xfer = i2c_master_send(client, buf, 5);
-       if (xfer != 5) {
+       xfer = i2c_master_send(client, buf, 6);
+       if (xfer != 6) {
                dev_err(&client->dev, "%s: send: %d\n", __FUNCTION__, xfer);
                return -EIO;
        }
@@ -120,6 +122,40 @@ static int ds1672_rtc_set_mmss(struct device *dev, unsigned long secs)
        return ds1672_set_mmss(to_i2c_client(dev), secs);
 }
 
+static int ds1672_get_control(struct i2c_client *client, u8 *status)
+{
+       unsigned char addr = DS1672_REG_CONTROL;
+
+       struct i2c_msg msgs[] = {
+               { client->addr, 0, 1, &addr },          /* setup read ptr */
+               { client->addr, I2C_M_RD, 1, status },  /* read control */
+       };
+
+       /* read control register */
+       if ((i2c_transfer(client->adapter, &msgs[0], 2)) != 2) {
+               dev_err(&client->dev, "%s: read error\n", __FUNCTION__);
+               return -EIO;
+       }
+
+       return 0;
+}
+
+/* following are the sysfs callback functions */
+static ssize_t show_control(struct device *dev, struct device_attribute *attr, char *buf)
+{
+       struct i2c_client *client = to_i2c_client(dev);
+       u8 control;
+       int err;
+
+       err = ds1672_get_control(client, &control);
+       if (err)
+               return err;
+
+       return sprintf(buf, "%s\n", (control & DS1672_REG_CONTROL_EOSC)
+                                       ? "disabled" : "enabled");
+}
+static DEVICE_ATTR(control, S_IRUGO, show_control, NULL);
+
 static struct rtc_class_ops ds1672_rtc_ops = {
        .read_time      = ds1672_rtc_read_time,
        .set_time       = ds1672_rtc_set_time,
@@ -128,7 +164,6 @@ static struct rtc_class_ops ds1672_rtc_ops = {
 
 static int ds1672_attach(struct i2c_adapter *adapter)
 {
-       dev_dbg(&adapter->dev, "%s\n", __FUNCTION__);
        return i2c_probe(adapter, &addr_data, ds1672_probe);
 }
 
@@ -137,8 +172,6 @@ static int ds1672_detach(struct i2c_client *client)
        int err;
        struct rtc_device *rtc = i2c_get_clientdata(client);
 
-       dev_dbg(&client->dev, "%s\n", __FUNCTION__);
-
        if (rtc)
                rtc_device_unregister(rtc);
 
@@ -162,6 +195,7 @@ static struct i2c_driver ds1672_driver = {
 static int ds1672_probe(struct i2c_adapter *adapter, int address, int kind)
 {
        int err = 0;
+       u8 control;
        struct i2c_client *client;
        struct rtc_device *rtc;
 
@@ -195,13 +229,23 @@ static int ds1672_probe(struct i2c_adapter *adapter, int address, int kind)
 
        if (IS_ERR(rtc)) {
                err = PTR_ERR(rtc);
-               dev_err(&client->dev,
-                       "unable to register the class device\n");
                goto exit_detach;
        }
 
        i2c_set_clientdata(client, rtc);
 
+       /* read control register */
+       err = ds1672_get_control(client, &control);
+       if (err)
+               goto exit_detach;
+
+       if (control & DS1672_REG_CONTROL_EOSC)
+               dev_warn(&client->dev, "Oscillator not enabled. "
+                                       "Set time to enable.\n");
+
+       /* Register sysfs hooks */
+       device_create_file(&client->dev, &dev_attr_control);
+
        return 0;
 
 exit_detach:
index 0dd80ea686a9b62320014589424b1e1ca8fbff9d..e1a1169e46649f4be8c8917f5a1a9b6cc7230615 100644 (file)
@@ -67,7 +67,6 @@ static int ep93xx_rtc_proc(struct device *dev, struct seq_file *seq)
 
        ep93xx_get_swcomp(dev, &preload, &delete);
 
-       seq_printf(seq, "24hr\t\t: yes\n");
        seq_printf(seq, "preload\t\t: %d\n", preload);
        seq_printf(seq, "delete\t\t: %d\n", delete);
 
@@ -110,7 +109,6 @@ static int __devinit ep93xx_rtc_probe(struct platform_device *dev)
                                &dev->dev, &ep93xx_rtc_ops, THIS_MODULE);
 
        if (IS_ERR(rtc)) {
-               dev_err(&dev->dev, "unable to register\n");
                return PTR_ERR(rtc);
        }
 
index db445c872b1b91cee87787c5905b00f0c9a502b8..f6e7ee04f3dc634002383f84438db3ad937b91c5 100644 (file)
@@ -23,7 +23,7 @@
 #define M48T86_REG_SECALRM     0x01
 #define M48T86_REG_MIN         0x02
 #define M48T86_REG_MINALRM     0x03
-#define M48T86_REG_HOUR        0x04
+#define M48T86_REG_HOUR                0x04
 #define M48T86_REG_HOURALRM    0x05
 #define M48T86_REG_DOW         0x06 /* 1 = sunday */
 #define M48T86_REG_DOM         0x07
@@ -127,9 +127,6 @@ static int m48t86_rtc_proc(struct device *dev, struct seq_file *seq)
 
        reg = ops->readb(M48T86_REG_B);
 
-       seq_printf(seq, "24hr\t\t: %s\n",
-                (reg & M48T86_REG_B_H24) ? "yes" : "no");
-
        seq_printf(seq, "mode\t\t: %s\n",
                 (reg & M48T86_REG_B_DM) ? "binary" : "bcd");
 
@@ -154,10 +151,8 @@ static int __devinit m48t86_rtc_probe(struct platform_device *dev)
        struct rtc_device *rtc = rtc_device_register("m48t86",
                                &dev->dev, &m48t86_rtc_ops, THIS_MODULE);
 
-       if (IS_ERR(rtc)) {
-               dev_err(&dev->dev, "unable to register\n");
+       if (IS_ERR(rtc))
                return PTR_ERR(rtc);
-       }
 
        platform_set_drvdata(dev, rtc);
 
index d857d45bdbe85dc90e8d5e5752843e1e9d8f984e..ba9a583b7b6817ff073b4c70a5a93910fdc89fe0 100644 (file)
@@ -227,14 +227,7 @@ static int pcf8563_rtc_set_time(struct device *dev, struct rtc_time *tm)
        return pcf8563_set_datetime(to_i2c_client(dev), tm);
 }
 
-static int pcf8563_rtc_proc(struct device *dev, struct seq_file *seq)
-{
-       seq_printf(seq, "24hr\t\t: yes\n");
-       return 0;
-}
-
 static struct rtc_class_ops pcf8563_rtc_ops = {
-       .proc           = pcf8563_rtc_proc,
        .read_time      = pcf8563_rtc_read_time,
        .set_time       = pcf8563_rtc_set_time,
 };
@@ -297,8 +290,6 @@ static int pcf8563_probe(struct i2c_adapter *adapter, int address, int kind)
 
        if (IS_ERR(rtc)) {
                err = PTR_ERR(rtc);
-               dev_err(&client->dev,
-                       "unable to register the class device\n");
                goto exit_detach;
        }
 
@@ -321,8 +312,6 @@ static int pcf8563_detach(struct i2c_client *client)
        int err;
        struct rtc_device *rtc = i2c_get_clientdata(client);
 
-       dev_dbg(&client->dev, "%s\n", __FUNCTION__);
-
        if (rtc)
                rtc_device_unregister(rtc);
 
index 90b8a97a091988801823e41124ddbb60ba4f24cf..cef5f5a3bbf9298233e25a2da7ba9dcc464133b2 100644 (file)
@@ -71,6 +71,8 @@ static int rtc_proc_show(struct seq_file *seq, void *offset)
                                alrm.pending ? "yes" : "no");
        }
 
+       seq_printf(seq, "24hr\t\t: yes\n");
+
        if (ops->proc)
                ops->proc(class_dev->dev, seq);
 
index 396c8681f66c7153b636a92482e068c7dd7762a7..7553d797603fd86d78a266d578765e439ea5aced 100644 (file)
@@ -151,9 +151,8 @@ static int rs5c372_rtc_proc(struct device *dev, struct seq_file *seq)
 {
        int err, osc, trim;
 
-       seq_printf(seq, "24hr\t\t: yes\n");
-
-       if ((err = rs5c372_get_trim(to_i2c_client(dev), &osc, &trim)) == 0) {
+       err = rs5c372_get_trim(to_i2c_client(dev), &osc, &trim);
+       if (err == 0) {
                seq_printf(seq, "%d.%03d KHz\n", osc / 1000, osc % 1000);
                seq_printf(seq, "trim\t: %d\n", trim);
        }
@@ -170,30 +169,31 @@ static struct rtc_class_ops rs5c372_rtc_ops = {
 static ssize_t rs5c372_sysfs_show_trim(struct device *dev,
                                struct device_attribute *attr, char *buf)
 {
-       int trim;
+       int err, trim;
 
-       if (rs5c372_get_trim(to_i2c_client(dev), NULL, &trim) == 0)
-               return sprintf(buf, "0x%2x\n", trim);
+       err = rs5c372_get_trim(to_i2c_client(dev), NULL, &trim);
+       if (err)
+               return err;
 
-       return 0;
+       return sprintf(buf, "0x%2x\n", trim);
 }
 static DEVICE_ATTR(trim, S_IRUGO, rs5c372_sysfs_show_trim, NULL);
 
 static ssize_t rs5c372_sysfs_show_osc(struct device *dev,
                                struct device_attribute *attr, char *buf)
 {
-       int osc;
+       int err, osc;
 
-       if (rs5c372_get_trim(to_i2c_client(dev), &osc, NULL) == 0)
-               return sprintf(buf, "%d.%03d KHz\n", osc / 1000, osc % 1000);
+       err = rs5c372_get_trim(to_i2c_client(dev), &osc, NULL);
+       if (err)
+               return err;
 
-       return 0;
+       return sprintf(buf, "%d.%03d KHz\n", osc / 1000, osc % 1000);
 }
 static DEVICE_ATTR(osc, S_IRUGO, rs5c372_sysfs_show_osc, NULL);
 
 static int rs5c372_attach(struct i2c_adapter *adapter)
 {
-       dev_dbg(&adapter->dev, "%s\n", __FUNCTION__);
        return i2c_probe(adapter, &addr_data, rs5c372_probe);
 }
 
@@ -233,8 +233,6 @@ static int rs5c372_probe(struct i2c_adapter *adapter, int address, int kind)
 
        if (IS_ERR(rtc)) {
                err = PTR_ERR(rtc);
-               dev_err(&client->dev,
-                       "unable to register the class device\n");
                goto exit_detach;
        }
 
@@ -260,8 +258,6 @@ static int rs5c372_detach(struct i2c_client *client)
        int err;
        struct rtc_device *rtc = i2c_get_clientdata(client);
 
-       dev_dbg(&client->dev, "%s\n", __FUNCTION__);
-
        if (rtc)
                rtc_device_unregister(rtc);
 
index 83b2bb480a16da8586d67fc1275499efc8a82d94..a23ec54989f6dbad436d1d91397b542511136346 100644 (file)
@@ -160,19 +160,19 @@ static int sa1100_rtc_open(struct device *dev)
        ret = request_irq(IRQ_RTC1Hz, sa1100_rtc_interrupt, SA_INTERRUPT,
                                "rtc 1Hz", dev);
        if (ret) {
-               printk(KERN_ERR "rtc: IRQ%d already in use.\n", IRQ_RTC1Hz);
+               dev_err(dev, "IRQ %d already in use.\n", IRQ_RTC1Hz);
                goto fail_ui;
        }
        ret = request_irq(IRQ_RTCAlrm, sa1100_rtc_interrupt, SA_INTERRUPT,
                                "rtc Alrm", dev);
        if (ret) {
-               printk(KERN_ERR "rtc: IRQ%d already in use.\n", IRQ_RTCAlrm);
+               dev_err(dev, "IRQ %d already in use.\n", IRQ_RTCAlrm);
                goto fail_ai;
        }
        ret = request_irq(IRQ_OST1, timer1_interrupt, SA_INTERRUPT,
                                "rtc timer", dev);
        if (ret) {
-               printk(KERN_ERR "rtc: IRQ%d already in use.\n", IRQ_OST1);
+               dev_err(dev, "IRQ %d already in use.\n", IRQ_OST1);
                goto fail_pi;
        }
        return 0;
@@ -332,7 +332,7 @@ static int sa1100_rtc_probe(struct platform_device *pdev)
         */
        if (RTTR == 0) {
                RTTR = RTC_DEF_DIVIDER + (RTC_DEF_TRIM << 16);
-               printk(KERN_WARNING "rtc: warning: initializing default clock divider/trim value\n");
+               dev_warn(&pdev->dev, "warning: initializing default clock divider/trim value\n");
                /* The current RTC value probably doesn't make sense either */
                RCNR = 0;
        }
@@ -340,15 +340,11 @@ static int sa1100_rtc_probe(struct platform_device *pdev)
        rtc = rtc_device_register(pdev->name, &pdev->dev, &sa1100_rtc_ops,
                                THIS_MODULE);
 
-       if (IS_ERR(rtc)) {
-               dev_err(&pdev->dev, "Unable to register the RTC device\n");
+       if (IS_ERR(rtc))
                return PTR_ERR(rtc);
-       }
 
        platform_set_drvdata(pdev, rtc);
 
-       dev_info(&pdev->dev, "SA11xx/PXA2xx RTC Registered\n");
-
        return 0;
 }
 
index 43d107487820aea0adaff9aae941881bc7d093f9..e1f7e8e86daffee9f96737442ef9d840904f6a0e 100644 (file)
@@ -49,7 +49,6 @@ static int test_rtc_proc(struct device *dev, struct seq_file *seq)
 {
        struct platform_device *plat_dev = to_platform_device(dev);
 
-       seq_printf(seq, "24hr\t\t: yes\n");
        seq_printf(seq, "test\t\t: yes\n");
        seq_printf(seq, "id\t\t: %d\n", plat_dev->id);
 
@@ -120,8 +119,6 @@ static int test_probe(struct platform_device *plat_dev)
                                                &test_rtc_ops, THIS_MODULE);
        if (IS_ERR(rtc)) {
                err = PTR_ERR(rtc);
-               dev_err(&plat_dev->dev,
-                       "unable to register the class device\n");
                return err;
        }
        device_create_file(&plat_dev->dev, &dev_attr_irq);
diff --git a/drivers/rtc/rtc-vr41xx.c b/drivers/rtc/rtc-vr41xx.c
new file mode 100644 (file)
index 0000000..4d49fd5
--- /dev/null
@@ -0,0 +1,471 @@
+/*
+ *  Driver for NEC VR4100 series Real Time Clock unit.
+ *
+ *  Copyright (C) 2003-2006  Yoichi Yuasa <yoichi_yuasa@tripeaks.co.jp>
+ *
+ *  This program is free software; you can redistribute it and/or modify
+ *  it under the terms of the GNU General Public License as published by
+ *  the Free Software Foundation; either version 2 of the License, or
+ *  (at your option) any later version.
+ *
+ *  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., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+ */
+#include <linux/fs.h>
+#include <linux/init.h>
+#include <linux/ioport.h>
+#include <linux/irq.h>
+#include <linux/module.h>
+#include <linux/platform_device.h>
+#include <linux/rtc.h>
+#include <linux/spinlock.h>
+#include <linux/types.h>
+
+#include <asm/div64.h>
+#include <asm/io.h>
+#include <asm/uaccess.h>
+#include <asm/vr41xx/vr41xx.h>
+
+MODULE_AUTHOR("Yoichi Yuasa <yoichi_yuasa@tripeaks.co.jp>");
+MODULE_DESCRIPTION("NEC VR4100 series RTC driver");
+MODULE_LICENSE("GPL");
+
+#define RTC1_TYPE1_START       0x0b0000c0UL
+#define RTC1_TYPE1_END         0x0b0000dfUL
+#define RTC2_TYPE1_START       0x0b0001c0UL
+#define RTC2_TYPE1_END         0x0b0001dfUL
+
+#define RTC1_TYPE2_START       0x0f000100UL
+#define RTC1_TYPE2_END         0x0f00011fUL
+#define RTC2_TYPE2_START       0x0f000120UL
+#define RTC2_TYPE2_END         0x0f00013fUL
+
+#define RTC1_SIZE              0x20
+#define RTC2_SIZE              0x20
+
+/* RTC 1 registers */
+#define ETIMELREG              0x00
+#define ETIMEMREG              0x02
+#define ETIMEHREG              0x04
+/* RFU */
+#define ECMPLREG               0x08
+#define ECMPMREG               0x0a
+#define ECMPHREG               0x0c
+/* RFU */
+#define RTCL1LREG              0x10
+#define RTCL1HREG              0x12
+#define RTCL1CNTLREG           0x14
+#define RTCL1CNTHREG           0x16
+#define RTCL2LREG              0x18
+#define RTCL2HREG              0x1a
+#define RTCL2CNTLREG           0x1c
+#define RTCL2CNTHREG           0x1e
+
+/* RTC 2 registers */
+#define TCLKLREG               0x00
+#define TCLKHREG               0x02
+#define TCLKCNTLREG            0x04
+#define TCLKCNTHREG            0x06
+/* RFU */
+#define RTCINTREG              0x1e
+ #define TCLOCK_INT            0x08
+ #define RTCLONG2_INT          0x04
+ #define RTCLONG1_INT          0x02
+ #define ELAPSEDTIME_INT       0x01
+
+#define RTC_FREQUENCY          32768
+#define MAX_PERIODIC_RATE      6553
+#define MAX_USER_PERIODIC_RATE 64
+
+static void __iomem *rtc1_base;
+static void __iomem *rtc2_base;
+
+#define rtc1_read(offset)              readw(rtc1_base + (offset))
+#define rtc1_write(offset, value)      writew((value), rtc1_base + (offset))
+
+#define rtc2_read(offset)              readw(rtc2_base + (offset))
+#define rtc2_write(offset, value)      writew((value), rtc2_base + (offset))
+
+static unsigned long epoch = 1970;     /* Jan 1 1970 00:00:00 */
+
+static spinlock_t rtc_lock = SPIN_LOCK_UNLOCKED;
+static char rtc_name[] = "RTC";
+static unsigned long periodic_frequency;
+static unsigned long periodic_count;
+
+struct resource rtc_resource[2] = {
+       {       .name   = rtc_name,
+               .flags  = IORESOURCE_MEM,       },
+       {       .name   = rtc_name,
+               .flags  = IORESOURCE_MEM,       },
+};
+
+static inline unsigned long read_elapsed_second(void)
+{
+
+       unsigned long first_low, first_mid, first_high;
+
+       unsigned long second_low, second_mid, second_high;
+
+       do {
+               first_low = rtc1_read(ETIMELREG);
+               first_mid = rtc1_read(ETIMEMREG);
+               first_high = rtc1_read(ETIMEHREG);
+               second_low = rtc1_read(ETIMELREG);
+               second_mid = rtc1_read(ETIMEMREG);
+               second_high = rtc1_read(ETIMEHREG);
+       } while (first_low != second_low || first_mid != second_mid ||
+                first_high != second_high);
+
+       return (first_high << 17) | (first_mid << 1) | (first_low >> 15);
+}
+
+static inline void write_elapsed_second(unsigned long sec)
+{
+       spin_lock_irq(&rtc_lock);
+
+       rtc1_write(ETIMELREG, (uint16_t)(sec << 15));
+       rtc1_write(ETIMEMREG, (uint16_t)(sec >> 1));
+       rtc1_write(ETIMEHREG, (uint16_t)(sec >> 17));
+
+       spin_unlock_irq(&rtc_lock);
+}
+
+static void vr41xx_rtc_release(struct device *dev)
+{
+
+       spin_lock_irq(&rtc_lock);
+
+       rtc1_write(ECMPLREG, 0);
+       rtc1_write(ECMPMREG, 0);
+       rtc1_write(ECMPHREG, 0);
+       rtc1_write(RTCL1LREG, 0);
+       rtc1_write(RTCL1HREG, 0);
+
+       spin_unlock_irq(&rtc_lock);
+
+       disable_irq(ELAPSEDTIME_IRQ);
+       disable_irq(RTCLONG1_IRQ);
+}
+
+static int vr41xx_rtc_read_time(struct device *dev, struct rtc_time *time)
+{
+       unsigned long epoch_sec, elapsed_sec;
+
+       epoch_sec = mktime(epoch, 1, 1, 0, 0, 0);
+       elapsed_sec = read_elapsed_second();
+
+       rtc_time_to_tm(epoch_sec + elapsed_sec, time);
+
+       return 0;
+}
+
+static int vr41xx_rtc_set_time(struct device *dev, struct rtc_time *time)
+{
+       unsigned long epoch_sec, current_sec;
+
+       epoch_sec = mktime(epoch, 1, 1, 0, 0, 0);
+       current_sec = mktime(time->tm_year + 1900, time->tm_mon + 1, time->tm_mday,
+                            time->tm_hour, time->tm_min, time->tm_sec);
+
+       write_elapsed_second(current_sec - epoch_sec);
+
+       return 0;
+}
+
+static int vr41xx_rtc_read_alarm(struct device *dev, struct rtc_wkalrm *wkalrm)
+{
+       unsigned long low, mid, high;
+       struct rtc_time *time = &wkalrm->time;
+
+       spin_lock_irq(&rtc_lock);
+
+       low = rtc1_read(ECMPLREG);
+       mid = rtc1_read(ECMPMREG);
+       high = rtc1_read(ECMPHREG);
+
+       spin_unlock_irq(&rtc_lock);
+
+       rtc_time_to_tm((high << 17) | (mid << 1) | (low >> 15), time);
+
+       return 0;
+}
+
+static int vr41xx_rtc_set_alarm(struct device *dev, struct rtc_wkalrm *wkalrm)
+{
+       unsigned long alarm_sec;
+       struct rtc_time *time = &wkalrm->time;
+
+       alarm_sec = mktime(time->tm_year + 1900, time->tm_mon + 1, time->tm_mday,
+                          time->tm_hour, time->tm_min, time->tm_sec);
+
+       spin_lock_irq(&rtc_lock);
+
+       rtc1_write(ECMPLREG, (uint16_t)(alarm_sec << 15));
+       rtc1_write(ECMPMREG, (uint16_t)(alarm_sec >> 1));
+       rtc1_write(ECMPHREG, (uint16_t)(alarm_sec >> 17));
+
+       spin_unlock_irq(&rtc_lock);
+
+       return 0;
+}
+
+static int vr41xx_rtc_ioctl(struct device *dev, unsigned int cmd, unsigned long arg)
+{
+       unsigned long count;
+
+       switch (cmd) {
+       case RTC_AIE_ON:
+               enable_irq(ELAPSEDTIME_IRQ);
+               break;
+       case RTC_AIE_OFF:
+               disable_irq(ELAPSEDTIME_IRQ);
+               break;
+       case RTC_PIE_ON:
+               enable_irq(RTCLONG1_IRQ);
+               break;
+       case RTC_PIE_OFF:
+               disable_irq(RTCLONG1_IRQ);
+               break;
+       case RTC_IRQP_READ:
+               return put_user(periodic_frequency, (unsigned long __user *)arg);
+               break;
+       case RTC_IRQP_SET:
+               if (arg > MAX_PERIODIC_RATE)
+                       return -EINVAL;
+
+               if (arg > MAX_USER_PERIODIC_RATE && capable(CAP_SYS_RESOURCE) == 0)
+                       return -EACCES;
+
+               periodic_frequency = arg;
+
+               count = RTC_FREQUENCY;
+               do_div(count, arg);
+
+               periodic_count = count;
+
+               spin_lock_irq(&rtc_lock);
+
+               rtc1_write(RTCL1LREG, count);
+               rtc1_write(RTCL1HREG, count >> 16);
+
+               spin_unlock_irq(&rtc_lock);
+               break;
+       case RTC_EPOCH_READ:
+               return put_user(epoch, (unsigned long __user *)arg);
+       case RTC_EPOCH_SET:
+               /* Doesn't support before 1900 */
+               if (arg < 1900)
+                       return -EINVAL;
+
+               if (capable(CAP_SYS_TIME) == 0)
+                       return -EACCES;
+
+               epoch = arg;
+               break;
+       default:
+               return -EINVAL;
+       }
+
+       return 0;
+}
+
+static irqreturn_t elapsedtime_interrupt(int irq, void *dev_id, struct pt_regs *regs)
+{
+       struct platform_device *pdev = (struct platform_device *)dev_id;
+       struct rtc_device *rtc = platform_get_drvdata(pdev);
+
+       rtc2_write(RTCINTREG, ELAPSEDTIME_INT);
+
+       rtc_update_irq(&rtc->class_dev, 1, RTC_AF);
+
+       return IRQ_HANDLED;
+}
+
+static irqreturn_t rtclong1_interrupt(int irq, void *dev_id, struct pt_regs *regs)
+{
+       struct platform_device *pdev = (struct platform_device *)dev_id;
+       struct rtc_device *rtc = platform_get_drvdata(pdev);
+       unsigned long count = periodic_count;
+
+       rtc2_write(RTCINTREG, RTCLONG1_INT);
+
+       rtc1_write(RTCL1LREG, count);
+       rtc1_write(RTCL1HREG, count >> 16);
+
+       rtc_update_irq(&rtc->class_dev, 1, RTC_PF);
+
+       return IRQ_HANDLED;
+}
+
+static struct rtc_class_ops vr41xx_rtc_ops = {
+       .release        = vr41xx_rtc_release,
+       .ioctl          = vr41xx_rtc_ioctl,
+       .read_time      = vr41xx_rtc_read_time,
+       .set_time       = vr41xx_rtc_set_time,
+       .read_alarm     = vr41xx_rtc_read_alarm,
+       .set_alarm      = vr41xx_rtc_set_alarm,
+};
+
+static int __devinit rtc_probe(struct platform_device *pdev)
+{
+       struct rtc_device *rtc;
+       unsigned int irq;
+       int retval;
+
+       if (pdev->num_resources != 2)
+               return -EBUSY;
+
+       rtc1_base = ioremap(pdev->resource[0].start, RTC1_SIZE);
+       if (rtc1_base == NULL)
+               return -EBUSY;
+
+       rtc2_base = ioremap(pdev->resource[1].start, RTC2_SIZE);
+       if (rtc2_base == NULL) {
+               iounmap(rtc1_base);
+               rtc1_base = NULL;
+               return -EBUSY;
+       }
+
+       rtc = rtc_device_register(rtc_name, &pdev->dev, &vr41xx_rtc_ops, THIS_MODULE);
+       if (IS_ERR(rtc)) {
+               iounmap(rtc1_base);
+               iounmap(rtc2_base);
+               rtc1_base = NULL;
+               rtc2_base = NULL;
+               return PTR_ERR(rtc);
+       }
+
+       spin_lock_irq(&rtc_lock);
+
+       rtc1_write(ECMPLREG, 0);
+       rtc1_write(ECMPMREG, 0);
+       rtc1_write(ECMPHREG, 0);
+       rtc1_write(RTCL1LREG, 0);
+       rtc1_write(RTCL1HREG, 0);
+
+       spin_unlock_irq(&rtc_lock);
+
+       irq = ELAPSEDTIME_IRQ;
+       retval = request_irq(irq, elapsedtime_interrupt, SA_INTERRUPT,
+                            "elapsed_time", pdev);
+       if (retval == 0) {
+               irq = RTCLONG1_IRQ;
+               retval = request_irq(irq, rtclong1_interrupt, SA_INTERRUPT,
+                                    "rtclong1", pdev);
+       }
+
+       if (retval < 0) {
+               printk(KERN_ERR "rtc: IRQ%d is busy\n", irq);
+               rtc_device_unregister(rtc);
+               if (irq == RTCLONG1_IRQ)
+                       free_irq(ELAPSEDTIME_IRQ, NULL);
+               iounmap(rtc1_base);
+               iounmap(rtc2_base);
+               rtc1_base = NULL;
+               rtc2_base = NULL;
+               return retval;
+       }
+
+       platform_set_drvdata(pdev, rtc);
+
+       disable_irq(ELAPSEDTIME_IRQ);
+       disable_irq(RTCLONG1_IRQ);
+
+       printk(KERN_INFO "rtc: Real Time Clock of NEC VR4100 series\n");
+
+       return 0;
+}
+
+static int __devexit rtc_remove(struct platform_device *pdev)
+{
+       struct rtc_device *rtc;
+
+       rtc = platform_get_drvdata(pdev);
+       if (rtc != NULL)
+               rtc_device_unregister(rtc);
+
+       platform_set_drvdata(pdev, NULL);
+
+       free_irq(ELAPSEDTIME_IRQ, NULL);
+       free_irq(RTCLONG1_IRQ, NULL);
+       if (rtc1_base != NULL)
+               iounmap(rtc1_base);
+       if (rtc2_base != NULL)
+               iounmap(rtc2_base);
+
+       return 0;
+}
+
+static struct platform_device *rtc_platform_device;
+
+static struct platform_driver rtc_platform_driver = {
+       .probe          = rtc_probe,
+       .remove         = __devexit_p(rtc_remove),
+       .driver         = {
+               .name   = rtc_name,
+               .owner  = THIS_MODULE,
+       },
+};
+
+static int __init vr41xx_rtc_init(void)
+{
+       int retval;
+
+       switch (current_cpu_data.cputype) {
+       case CPU_VR4111:
+       case CPU_VR4121:
+               rtc_resource[0].start = RTC1_TYPE1_START;
+               rtc_resource[0].end = RTC1_TYPE1_END;
+               rtc_resource[1].start = RTC2_TYPE1_START;
+               rtc_resource[1].end = RTC2_TYPE1_END;
+               break;
+       case CPU_VR4122:
+       case CPU_VR4131:
+       case CPU_VR4133:
+               rtc_resource[0].start = RTC1_TYPE2_START;
+               rtc_resource[0].end = RTC1_TYPE2_END;
+               rtc_resource[1].start = RTC2_TYPE2_START;
+               rtc_resource[1].end = RTC2_TYPE2_END;
+               break;
+       default:
+               return -ENODEV;
+               break;
+       }
+
+       rtc_platform_device = platform_device_alloc("RTC", -1);
+       if (rtc_platform_device == NULL)
+               return -ENOMEM;
+
+       retval = platform_device_add_resources(rtc_platform_device,
+                               rtc_resource, ARRAY_SIZE(rtc_resource));
+
+       if (retval == 0)
+               retval = platform_device_add(rtc_platform_device);
+
+       if (retval < 0) {
+               platform_device_put(rtc_platform_device);
+               return retval;
+       }
+
+       retval = platform_driver_register(&rtc_platform_driver);
+       if (retval < 0)
+               platform_device_unregister(rtc_platform_device);
+
+       return retval;
+}
+
+static void __exit vr41xx_rtc_exit(void)
+{
+       platform_driver_unregister(&rtc_platform_driver);
+       platform_device_unregister(rtc_platform_device);
+}
+
+module_init(vr41xx_rtc_init);
+module_exit(vr41xx_rtc_exit);
index 621d17afc0d96efde20b135b236bb959e236483f..788b6d1f8f2fd282cac69e6b8a5c0e9a3698c9f2 100644 (file)
@@ -19,7 +19,7 @@
 #include <linux/rtc.h>
 #include <linux/delay.h>
 
-#define DRV_VERSION "1.0.6"
+#define DRV_VERSION "1.0.7"
 
 /* Addresses to scan: none. This chip is located at
  * 0x6f and uses a two bytes register addressing.
@@ -451,8 +451,6 @@ static int x1205_rtc_proc(struct device *dev, struct seq_file *seq)
 {
        int err, dtrim, atrim;
 
-       seq_printf(seq, "24hr\t\t: yes\n");
-
        if ((err = x1205_get_dtrim(to_i2c_client(dev), &dtrim)) == 0)
                seq_printf(seq, "digital_trim\t: %d ppm\n", dtrim);
 
@@ -473,30 +471,31 @@ static struct rtc_class_ops x1205_rtc_ops = {
 static ssize_t x1205_sysfs_show_atrim(struct device *dev,
                                struct device_attribute *attr, char *buf)
 {
-       int atrim;
+       int err, atrim;
 
-       if (x1205_get_atrim(to_i2c_client(dev), &atrim) == 0)
-               return sprintf(buf, "%d.%02d pF\n",
-                       atrim / 1000, atrim % 1000);
-       return 0;
+       err = x1205_get_atrim(to_i2c_client(dev), &atrim);
+       if (err)
+               return err;
+
+       return sprintf(buf, "%d.%02d pF\n", atrim / 1000, atrim % 1000);
 }
 static DEVICE_ATTR(atrim, S_IRUGO, x1205_sysfs_show_atrim, NULL);
 
 static ssize_t x1205_sysfs_show_dtrim(struct device *dev,
                                struct device_attribute *attr, char *buf)
 {
-       int dtrim;
+       int err, dtrim;
 
-       if (x1205_get_dtrim(to_i2c_client(dev), &dtrim) == 0)
-               return sprintf(buf, "%d ppm\n", dtrim);
+       err = x1205_get_dtrim(to_i2c_client(dev), &dtrim);
+       if (err)
+               return err;
 
-       return 0;
+       return sprintf(buf, "%d ppm\n", dtrim);
 }
 static DEVICE_ATTR(dtrim, S_IRUGO, x1205_sysfs_show_dtrim, NULL);
 
 static int x1205_attach(struct i2c_adapter *adapter)
 {
-       dev_dbg(&adapter->dev, "%s\n", __FUNCTION__);
        return i2c_probe(adapter, &addr_data, x1205_probe);
 }
 
@@ -545,8 +544,6 @@ static int x1205_probe(struct i2c_adapter *adapter, int address, int kind)
 
        if (IS_ERR(rtc)) {
                err = PTR_ERR(rtc);
-               dev_err(&client->dev,
-                       "unable to register the class device\n");
                goto exit_detach;
        }
 
@@ -585,8 +582,6 @@ static int x1205_detach(struct i2c_client *client)
        int err;
        struct rtc_device *rtc = i2c_get_clientdata(client);
 
-       dev_dbg(&client->dev, "%s\n", __FUNCTION__);
-
        if (rtc)
                rtc_device_unregister(rtc);
 
index 0a9f12c4e91154b57d73dd39e58ade8a6663c34e..a3bfebcf31efeb72f3a6de690d82f412eaa5218b 100644 (file)
@@ -1257,25 +1257,28 @@ __dasd_start_head(struct dasd_device * device)
        if (list_empty(&device->ccw_queue))
                return;
        cqr = list_entry(device->ccw_queue.next, struct dasd_ccw_req, list);
-        /* check FAILFAST */
+       if (cqr->status != DASD_CQR_QUEUED)
+               return;
+       /* Non-temporary stop condition will trigger fail fast */
        if (device->stopped & ~DASD_STOPPED_PENDING &&
            test_bit(DASD_CQR_FLAGS_FAILFAST, &cqr->flags) &&
            (!dasd_eer_enabled(device))) {
                cqr->status = DASD_CQR_FAILED;
                dasd_schedule_bh(device);
+               return;
        }
-       if ((cqr->status == DASD_CQR_QUEUED) &&
-           (!device->stopped)) {
-               /* try to start the first I/O that can be started */
-               rc = device->discipline->start_IO(cqr);
-               if (rc == 0)
-                       dasd_set_timer(device, cqr->expires);
-               else if (rc == -EACCES) {
-                       dasd_schedule_bh(device);
-               } else
-                       /* Hmpf, try again in 1/2 sec */
-                       dasd_set_timer(device, 50);
-       }
+       /* Don't try to start requests if device is stopped */
+       if (device->stopped)
+               return;
+
+       rc = device->discipline->start_IO(cqr);
+       if (rc == 0)
+               dasd_set_timer(device, cqr->expires);
+       else if (rc == -EACCES) {
+               dasd_schedule_bh(device);
+       } else
+               /* Hmpf, try again in 1/2 sec */
+               dasd_set_timer(device, 50);
 }
 
 /*
@@ -1968,7 +1971,7 @@ int
 dasd_generic_set_offline (struct ccw_device *cdev)
 {
        struct dasd_device *device;
-       int max_count;
+       int max_count, open_count;
 
        device = dasd_device_from_cdev(cdev);
        if (IS_ERR(device))
@@ -1985,10 +1988,16 @@ dasd_generic_set_offline (struct ccw_device *cdev)
         * in the other openers.
         */
        max_count = device->bdev ? 0 : -1;
-       if (atomic_read(&device->open_count) > max_count) {
-               printk (KERN_WARNING "Can't offline dasd device with open"
-                       " count = %i.\n",
-                       atomic_read(&device->open_count));
+       open_count = (int) atomic_read(&device->open_count);
+       if (open_count > max_count) {
+               if (open_count > 0)
+                       printk (KERN_WARNING "Can't offline dasd device with "
+                               "open count = %i.\n",
+                               open_count);
+               else
+                       printk (KERN_WARNING "%s",
+                               "Can't offline dasd device due to internal "
+                               "use\n");
                clear_bit(DASD_FLAG_OFFLINE, &device->flags);
                dasd_put_device(device);
                return -EBUSY;
index 1aa3c261718a6813f34105e42db85ce7c054513f..ad23aede356c63254f8aa215284425fd71b51a54 100644 (file)
@@ -294,23 +294,40 @@ out_error:
 #endif                         /* CONFIG_DASD_PROFILE */
 }
 
+/*
+ * Create dasd proc-fs entries.
+ * In case creation failed, cleanup and return -ENOENT.
+ */
 int
 dasd_proc_init(void)
 {
        dasd_proc_root_entry = proc_mkdir("dasd", &proc_root);
+       if (!dasd_proc_root_entry)
+               goto out_nodasd;
        dasd_proc_root_entry->owner = THIS_MODULE;
        dasd_devices_entry = create_proc_entry("devices",
                                               S_IFREG | S_IRUGO | S_IWUSR,
                                               dasd_proc_root_entry);
+       if (!dasd_devices_entry)
+               goto out_nodevices;
        dasd_devices_entry->proc_fops = &dasd_devices_file_ops;
        dasd_devices_entry->owner = THIS_MODULE;
        dasd_statistics_entry = create_proc_entry("statistics",
                                                  S_IFREG | S_IRUGO | S_IWUSR,
                                                  dasd_proc_root_entry);
+       if (!dasd_statistics_entry)
+               goto out_nostatistics;
        dasd_statistics_entry->read_proc = dasd_statistics_read;
        dasd_statistics_entry->write_proc = dasd_statistics_write;
        dasd_statistics_entry->owner = THIS_MODULE;
        return 0;
+
+ out_nostatistics:
+       remove_proc_entry("devices", dasd_proc_root_entry);
+ out_nodevices:
+       remove_proc_entry("dasd", &proc_root);
+ out_nodasd:
+       return -ENOENT;
 }
 
 void
index 6badd84034094f7db6b6fdaf450c11799d60265f..d4d2ff0a9da2003eb7ed8cd0d2b70dc0ae827c3b 100644 (file)
@@ -54,7 +54,7 @@ kbd_alloc(void) {
        if (!kbd)
                goto out;
        kbd->key_maps = kzalloc(sizeof(key_maps), GFP_KERNEL);
-       if (!key_maps)
+       if (!kbd->key_maps)
                goto out_kbd;
        for (i = 0; i < ARRAY_SIZE(key_maps); i++) {
                if (key_maps[i]) {
index 5c65cf3e5cc02506261d3e970a267b346df0d20b..b70d926902424dd9943c8dbfbc1c8353a03b7804 100644 (file)
@@ -432,8 +432,8 @@ tapeblock_ioctl(
 ) {
        int rc;
        int minor;
-       struct gendisk *disk = inode->i_bdev->bd_disk;
-       struct tape_device *device = disk->private_data;
+       struct gendisk *disk;
+       struct tape_device *device;
 
        rc     = 0;
        disk   = inode->i_bdev->bd_disk;
index 389ee2c0f4435e9966c6ddc4d492e7217d611c11..e6e4086d3224bf077ff2025c53953a2b371c722b 100644 (file)
@@ -210,18 +210,14 @@ tape_state_set(struct tape_device *device, enum tape_state newstate)
                return;
        }
        DBF_EVENT(4, "ts. dev:  %x\n", device->first_minor);
-       if (device->tape_state < TO_SIZE && device->tape_state >= 0)
-               str = tape_state_verbose[device->tape_state];
-       else
-               str = "UNKNOWN TS";
-       DBF_EVENT(4, "old ts:   %s\n", str);
-       if (device->tape_state < TO_SIZE && device->tape_state >=0 )
+       DBF_EVENT(4, "old ts:\t\n");
+       if (device->tape_state < TS_SIZE && device->tape_state >=0 )
                str = tape_state_verbose[device->tape_state];
        else
                str = "UNKNOWN TS";
        DBF_EVENT(4, "%s\n", str);
        DBF_EVENT(4, "new ts:\t\n");
-       if (newstate < TO_SIZE && newstate >= 0)
+       if (newstate < TS_SIZE && newstate >= 0)
                str = tape_state_verbose[newstate];
        else
                str = "UNKNOWN TS";
index cb8e2e672b68664680dddf99832ec9940d980f66..0960bef7b199ca6c45868f6e746dee1a862550ac 100644 (file)
@@ -414,11 +414,11 @@ cio_ignore_proc_init (void)
        entry = create_proc_entry ("cio_ignore", S_IFREG | S_IRUGO | S_IWUSR,
                                   &proc_root);
        if (!entry)
-               return 0;
+               return -ENOENT;
 
        entry->proc_fops = &cio_ignore_proc_fops;
 
-       return 1;
+       return 0;
 }
 
 __initcall (cio_ignore_proc_init);
index cbb86fa5f293b71a244b37c4d9a39d323665e46c..5b20d8c9c0257eec01184b8de15eb4bd2167dd12 100644 (file)
@@ -67,7 +67,7 @@ cio_debug_init (void)
                goto out_unregister;
        debug_register_view (cio_debug_msg_id, &debug_sprintf_view);
        debug_set_level (cio_debug_msg_id, 2);
-       cio_debug_trace_id = debug_register ("cio_trace", 16, 4, 8);
+       cio_debug_trace_id = debug_register ("cio_trace", 16, 4, 16);
        if (!cio_debug_trace_id)
                goto out_unregister;
        debug_register_view (cio_debug_trace_id, &debug_hex_ascii_view);
index 6af8b27d366b07d5c87555c805fdc4d05d8ddcb3..f88844adae1ba432e58e8f1d3744415062dab1e7 100644 (file)
@@ -3,6 +3,11 @@
 
 #include <asm/debug.h>
 
+/* for use of debug feature */
+extern debug_info_t *cio_debug_msg_id;
+extern debug_info_t *cio_debug_trace_id;
+extern debug_info_t *cio_debug_crw_id;
+
 #define CIO_TRACE_EVENT(imp, txt) do { \
                debug_text_event(cio_debug_trace_id, imp, txt); \
        } while (0)
                debug_sprintf_event(cio_debug_crw_id, imp , ##args); \
        } while (0)
 
-#define CIO_HEX_EVENT(imp, args...) do { \
-                debug_event(cio_debug_trace_id, imp, ##args); \
-        } while (0)
+static inline void
+CIO_HEX_EVENT(int level, void *data, int length)
+{
+       while (length > 0) {
+               debug_event(cio_debug_trace_id, level, data, length);
+               length -= cio_debug_trace_id->buf_size;
+               data += cio_debug_trace_id->buf_size;
+       }
+}
 
 #define CIO_DEBUG(printk_level,event_level,msg...) ({ \
        if (cio_show_msg) printk(printk_level msg); \
        CIO_MSG_EVENT (event_level, msg); \
 })
 
-/* for use of debug feature */
-extern debug_info_t *cio_debug_msg_id;
-extern debug_info_t *cio_debug_trace_id;
-extern debug_info_t *cio_debug_crw_id;
-
 #endif
index 0d2b447c50ed6e9cea185bf4810a18858dd1ddc5..caeb6d246e578eb0732feb99def77729f1980877 100644 (file)
@@ -65,6 +65,7 @@
    2.26.02.005 - Fix use_sg == 0 mapping on systems with 4GB or higher.
    2.26.02.006 - Fix 9550SX pchip reset timeout.
                  Add big endian support.
+   2.26.02.007 - Disable local interrupts during kmap/unmap_atomic().
 */
 
 #include <linux/module.h>
@@ -88,7 +89,7 @@
 #include "3w-9xxx.h"
 
 /* Globals */
-#define TW_DRIVER_VERSION "2.26.02.006"
+#define TW_DRIVER_VERSION "2.26.02.007"
 static TW_Device_Extension *twa_device_extension_list[TW_MAX_SLOT];
 static unsigned int twa_device_extension_count;
 static int twa_major = -1;
@@ -1942,9 +1943,13 @@ static void twa_scsiop_execute_scsi_complete(TW_Device_Extension *tw_dev, int re
                }
                if (tw_dev->srb[request_id]->use_sg == 1) {
                        struct scatterlist *sg = (struct scatterlist *)tw_dev->srb[request_id]->request_buffer;
-                       char *buf = kmap_atomic(sg->page, KM_IRQ0) + sg->offset;
+                       char *buf;
+                       unsigned long flags = 0;
+                       local_irq_save(flags);
+                       buf = kmap_atomic(sg->page, KM_IRQ0) + sg->offset;
                        memcpy(buf, tw_dev->generic_buffer_virt[request_id], sg->length);
                        kunmap_atomic(buf - sg->offset, KM_IRQ0);
+                       local_irq_restore(flags);
                }
        }
 } /* End twa_scsiop_execute_scsi_complete() */
index 25f678d0780b2e1bb2dcf12a767b8607739db150..e8e41e6eb42a91f5eb07fadb02135c9deadeeb39 100644 (file)
@@ -1508,10 +1508,12 @@ static void tw_transfer_internal(TW_Device_Extension *tw_dev, int request_id,
        struct scsi_cmnd *cmd = tw_dev->srb[request_id];
        void *buf;
        unsigned int transfer_len;
+       unsigned long flags = 0;
 
        if (cmd->use_sg) {
                struct scatterlist *sg =
                        (struct scatterlist *)cmd->request_buffer;
+               local_irq_save(flags);
                buf = kmap_atomic(sg->page, KM_IRQ0) + sg->offset;
                transfer_len = min(sg->length, len);
        } else {
@@ -1526,6 +1528,7 @@ static void tw_transfer_internal(TW_Device_Extension *tw_dev, int request_id,
 
                sg = (struct scatterlist *)cmd->request_buffer;
                kunmap_atomic(buf - sg->offset, KM_IRQ0);
+               local_irq_restore(flags);
        }
 }
 
index 4035920ce3d8078c4aa33bfbfbbc87a2ecc1be96..3e7302692dbe3aa963ae3c957bc5df5f54fb2f48 100644 (file)
@@ -1079,7 +1079,7 @@ config SCSI_SYM53C8XX_DMA_ADDRESSING_MODE
          memory using PCI DAC cycles.
 
 config SCSI_SYM53C8XX_DEFAULT_TAGS
-       int "default tagged command queue depth"
+       int "Default tagged command queue depth"
        depends on SCSI_SYM53C8XX_2
        default "16"
        help
@@ -1090,7 +1090,7 @@ config SCSI_SYM53C8XX_DEFAULT_TAGS
          exceed CONFIG_SCSI_SYM53C8XX_MAX_TAGS.
 
 config SCSI_SYM53C8XX_MAX_TAGS
-       int "maximum number of queued commands"
+       int "Maximum number of queued commands"
        depends on SCSI_SYM53C8XX_2
        default "64"
        help
@@ -1099,13 +1099,14 @@ config SCSI_SYM53C8XX_MAX_TAGS
          possible. The driver supports up to 256 queued commands per device.
          This value is used as a compiled-in hard limit.
 
-config SCSI_SYM53C8XX_IOMAPPED
-       bool "use port IO"
+config SCSI_SYM53C8XX_MMIO
+       bool "Use memory mapped IO"
        depends on SCSI_SYM53C8XX_2
+       default y
        help
-         If you say Y here, the driver will use port IO to access
-         the card.  This is significantly slower then using memory
-         mapped IO.  Most people should answer N.
+         Memory mapped IO is faster than Port IO.  Most people should
+         answer Y here, but some machines may have problems.  If you have
+         to answer N here, please report the problem to the maintainer.
 
 config SCSI_IPR
        tristate "IBM Power Linux RAID adapter support"
@@ -1309,15 +1310,6 @@ config SCSI_QLOGIC_FAS
          To compile this driver as a module, choose M here: the
          module will be called qlogicfas.
 
-config SCSI_QLOGIC_FC
-       tristate "Qlogic ISP FC SCSI support"
-       depends on PCI && SCSI
-       help
-         This is a driver for the QLogic ISP2100 SCSI-FCP host adapter.
-
-         To compile this driver as a module, choose M here: the
-         module will be called qlogicfc.
-
 config SCSI_QLOGIC_FC_FIRMWARE
        bool "Include loadable firmware in driver"
        depends on SCSI_QLOGIC_FC
index e513c3158ad90ea7ecc5eef8cea0da146bbc11d6..81803a16f986d13d7b0aab7419e2bf0cd11d2477 100644 (file)
@@ -78,7 +78,6 @@ obj-$(CONFIG_SCSI_NCR_Q720)   += NCR_Q720_mod.o
 obj-$(CONFIG_SCSI_SYM53C416)   += sym53c416.o
 obj-$(CONFIG_SCSI_QLOGIC_FAS)  += qlogicfas408.o       qlogicfas.o
 obj-$(CONFIG_PCMCIA_QLOGIC)    += qlogicfas408.o
-obj-$(CONFIG_SCSI_QLOGIC_FC)   += qlogicfc.o 
 obj-$(CONFIG_SCSI_QLOGIC_1280) += qla1280.o 
 obj-$(CONFIG_SCSI_QLA_FC)      += qla2xxx/
 obj-$(CONFIG_SCSI_LPFC)                += lpfc/
index 8df4a0ea3761598d4f9f40ca7a658a277a49e7ea..642a3b4e5937619ca175a0a7d8b5da703270f3e5 100644 (file)
@@ -149,20 +149,20 @@ static int dacmode = -1;
 
 static int commit = -1;
 
-module_param(nondasd, int, 0);
+module_param(nondasd, int, S_IRUGO|S_IWUSR);
 MODULE_PARM_DESC(nondasd, "Control scanning of hba for nondasd devices. 0=off, 1=on");
-module_param(dacmode, int, 0);
+module_param(dacmode, int, S_IRUGO|S_IWUSR);
 MODULE_PARM_DESC(dacmode, "Control whether dma addressing is using 64 bit DAC. 0=off, 1=on");
-module_param(commit, int, 0);
+module_param(commit, int, S_IRUGO|S_IWUSR);
 MODULE_PARM_DESC(commit, "Control whether a COMMIT_CONFIG is issued to the adapter for foreign arrays.\nThis is typically needed in systems that do not have a BIOS. 0=off, 1=on");
 
 int numacb = -1;
 module_param(numacb, int, S_IRUGO|S_IWUSR);
-MODULE_PARM_DESC(numacb, "Request a limit to the number of adapter control blocks (FIB) allocated. Valid\nvalues are 512 and down. Default is to use suggestion from Firmware.");
+MODULE_PARM_DESC(numacb, "Request a limit to the number of adapter control blocks (FIB) allocated. Valid values are 512 and down. Default is to use suggestion from Firmware.");
 
 int acbsize = -1;
 module_param(acbsize, int, S_IRUGO|S_IWUSR);
-MODULE_PARM_DESC(acbsize, "Request a specific adapter control block (FIB) size. Valid values are 512,\n2048, 4096 and 8192. Default is to use suggestion from Firmware.");
+MODULE_PARM_DESC(acbsize, "Request a specific adapter control block (FIB) size. Valid values are 512, 2048, 4096 and 8192. Default is to use suggestion from Firmware.");
 /**
  *     aac_get_config_status   -       check the adapter configuration
  *     @common: adapter to query
@@ -387,6 +387,7 @@ static void get_container_name_callback(void *context, struct fib * fibptr)
        struct scsi_cmnd * scsicmd;
 
        scsicmd = (struct scsi_cmnd *) context;
+       scsicmd->SCp.phase = AAC_OWNER_MIDLEVEL;
 
        dprintk((KERN_DEBUG "get_container_name_callback[cpu %d]: t = %ld.\n", smp_processor_id(), jiffies));
        if (fibptr == NULL)
@@ -453,8 +454,10 @@ static int aac_get_container_name(struct scsi_cmnd * scsicmd, int cid)
        /*
         *      Check that the command queued to the controller
         */
-       if (status == -EINPROGRESS) 
+       if (status == -EINPROGRESS) {
+               scsicmd->SCp.phase = AAC_OWNER_FIRMWARE;
                return 0;
+       }
                
        printk(KERN_WARNING "aac_get_container_name: aac_fib_send failed with status: %d.\n", status);
        aac_fib_complete(cmd_fibcontext);
@@ -907,9 +910,10 @@ static void io_callback(void *context, struct fib * fibptr)
        u32 cid;
 
        scsicmd = (struct scsi_cmnd *) context;
+       scsicmd->SCp.phase = AAC_OWNER_MIDLEVEL;
 
        dev = (struct aac_dev *)scsicmd->device->host->hostdata;
-       cid = ID_LUN_TO_CONTAINER(scsicmd->device->id, scsicmd->device->lun);
+       cid = scmd_id(scsicmd);
 
        if (nblank(dprintk(x))) {
                u64 lba;
@@ -1151,8 +1155,10 @@ static int aac_read(struct scsi_cmnd * scsicmd, int cid)
        /*
         *      Check that the command queued to the controller
         */
-       if (status == -EINPROGRESS) 
+       if (status == -EINPROGRESS) {
+               scsicmd->SCp.phase = AAC_OWNER_FIRMWARE;
                return 0;
+       }
                
        printk(KERN_WARNING "aac_read: aac_fib_send failed with status: %d.\n", status);
        /*
@@ -1318,8 +1324,8 @@ static int aac_write(struct scsi_cmnd * scsicmd, int cid)
        /*
         *      Check that the command queued to the controller
         */
-       if (status == -EINPROGRESS)
-       {
+       if (status == -EINPROGRESS) {
+               scsicmd->SCp.phase = AAC_OWNER_FIRMWARE;
                return 0;
        }
 
@@ -1341,6 +1347,7 @@ static void synchronize_callback(void *context, struct fib *fibptr)
        struct scsi_cmnd *cmd;
 
        cmd = context;
+       cmd->SCp.phase = AAC_OWNER_MIDLEVEL;
 
        dprintk((KERN_DEBUG "synchronize_callback[cpu %d]: t = %ld.\n", 
                                smp_processor_id(), jiffies));
@@ -1354,7 +1361,7 @@ static void synchronize_callback(void *context, struct fib *fibptr)
        else {
                struct scsi_device *sdev = cmd->device;
                struct aac_dev *dev = (struct aac_dev *)sdev->host->hostdata;
-               u32 cid = ID_LUN_TO_CONTAINER(sdev->id, sdev->lun);
+               u32 cid = sdev_id(sdev);
                printk(KERN_WARNING 
                     "synchronize_callback: synchronize failed, status = %d\n",
                     le32_to_cpu(synchronizereply->status));
@@ -1386,12 +1393,12 @@ static int aac_synchronize(struct scsi_cmnd *scsicmd, int cid)
        unsigned long flags;
 
        /*
-        * Wait for all commands to complete to this specific
-        * target (block).
+        * Wait for all outstanding queued commands to complete to this
+        * specific target (block).
         */
        spin_lock_irqsave(&sdev->list_lock, flags);
        list_for_each_entry(cmd, &sdev->cmd_list, list)
-               if (cmd != scsicmd && cmd->serial_number != 0) {
+               if (cmd != scsicmd && cmd->SCp.phase == AAC_OWNER_FIRMWARE) {
                        ++active;
                        break;
                }
@@ -1434,8 +1441,10 @@ static int aac_synchronize(struct scsi_cmnd *scsicmd, int cid)
        /*
         *      Check that the command queued to the controller
         */
-       if (status == -EINPROGRESS)
+       if (status == -EINPROGRESS) {
+               scsicmd->SCp.phase = AAC_OWNER_FIRMWARE;
                return 0;
+       }
 
        printk(KERN_WARNING 
                "aac_synchronize: aac_fib_send failed with status: %d.\n", status);
@@ -1458,7 +1467,6 @@ int aac_scsi_cmd(struct scsi_cmnd * scsicmd)
        struct Scsi_Host *host = scsicmd->device->host;
        struct aac_dev *dev = (struct aac_dev *)host->hostdata;
        struct fsa_dev_info *fsa_dev_ptr = dev->fsa_dev;
-       int ret;
        
        /*
         *      If the bus, id or lun is out of range, return fail
@@ -1466,13 +1474,14 @@ int aac_scsi_cmd(struct scsi_cmnd * scsicmd)
         *      itself.
         */
        if (scmd_id(scsicmd) != host->this_id) {
-               if ((scsicmd->device->channel == CONTAINER_CHANNEL)) {
-                       if( (scsicmd->device->id >= dev->maximum_num_containers) || (scsicmd->device->lun != 0)){ 
+               if ((scmd_channel(scsicmd) == CONTAINER_CHANNEL)) {
+                       if((scmd_id(scsicmd) >= dev->maximum_num_containers) ||
+                                       (scsicmd->device->lun != 0)) {
                                scsicmd->result = DID_NO_CONNECT << 16;
                                scsicmd->scsi_done(scsicmd);
                                return 0;
                        }
-                       cid = ID_LUN_TO_CONTAINER(scsicmd->device->id, scsicmd->device->lun);
+                       cid = scmd_id(scsicmd);
 
                        /*
                         *      If the target container doesn't exist, it may have
@@ -1548,7 +1557,7 @@ int aac_scsi_cmd(struct scsi_cmnd * scsicmd)
        {
                struct inquiry_data inq_data;
 
-               dprintk((KERN_DEBUG "INQUIRY command, ID: %d.\n", scsicmd->device->id));
+               dprintk((KERN_DEBUG "INQUIRY command, ID: %d.\n", scmd_id(scsicmd)));
                memset(&inq_data, 0, sizeof (struct inquiry_data));
 
                inq_data.inqd_ver = 2;  /* claim compliance to SCSI-2 */
@@ -1598,13 +1607,14 @@ int aac_scsi_cmd(struct scsi_cmnd * scsicmd)
                cp[11] = 0;
                cp[12] = 0;
                aac_internal_transfer(scsicmd, cp, 0,
-                 min((unsigned int)scsicmd->cmnd[13], sizeof(cp)));
+                 min_t(size_t, scsicmd->cmnd[13], sizeof(cp)));
                if (sizeof(cp) < scsicmd->cmnd[13]) {
                        unsigned int len, offset = sizeof(cp);
 
                        memset(cp, 0, offset);
                        do {
-                               len = min(scsicmd->cmnd[13]-offset, sizeof(cp));
+                               len = min_t(size_t, scsicmd->cmnd[13] - offset,
+                                               sizeof(cp));
                                aac_internal_transfer(scsicmd, cp, offset, len);
                        } while ((offset += len) < scsicmd->cmnd[13]);
                }
@@ -1728,24 +1738,19 @@ int aac_scsi_cmd(struct scsi_cmnd * scsicmd)
                         *      containers to /dev/sd device names
                         */
                         
-                       spin_unlock_irq(host->host_lock);
                        if (scsicmd->request->rq_disk)
                                strlcpy(fsa_dev_ptr[cid].devname,
                                scsicmd->request->rq_disk->disk_name,
                                min(sizeof(fsa_dev_ptr[cid].devname),
                                sizeof(scsicmd->request->rq_disk->disk_name) + 1));
-                       ret = aac_read(scsicmd, cid);
-                       spin_lock_irq(host->host_lock);
-                       return ret;
+
+                       return aac_read(scsicmd, cid);
 
                case WRITE_6:
                case WRITE_10:
                case WRITE_12:
                case WRITE_16:
-                       spin_unlock_irq(host->host_lock);
-                       ret = aac_write(scsicmd, cid);
-                       spin_lock_irq(host->host_lock);
-                       return ret;
+                       return aac_write(scsicmd, cid);
 
                case SYNCHRONIZE_CACHE:
                        /* Issue FIB to tell Firmware to flush it's cache */
@@ -1778,7 +1783,7 @@ static int query_disk(struct aac_dev *dev, void __user *arg)
        if (copy_from_user(&qd, arg, sizeof (struct aac_query_disk)))
                return -EFAULT;
        if (qd.cnum == -1)
-               qd.cnum = ID_LUN_TO_CONTAINER(qd.id, qd.lun);
+               qd.cnum = qd.id;
        else if ((qd.bus == -1) && (qd.id == -1) && (qd.lun == -1)) 
        {
                if (qd.cnum < 0 || qd.cnum >= dev->maximum_num_containers)
@@ -1890,6 +1895,7 @@ static void aac_srb_callback(void *context, struct fib * fibptr)
        struct scsi_cmnd *scsicmd;
 
        scsicmd = (struct scsi_cmnd *) context;
+       scsicmd->SCp.phase = AAC_OWNER_MIDLEVEL;
        dev = (struct aac_dev *)scsicmd->device->host->hostdata;
 
        if (fibptr == NULL)
@@ -2068,14 +2074,13 @@ static int aac_send_srb_fib(struct scsi_cmnd* scsicmd)
        u32 timeout;
 
        dev = (struct aac_dev *)scsicmd->device->host->hostdata;
-       if (scsicmd->device->id >= dev->maximum_num_physicals || 
+       if (scmd_id(scsicmd) >= dev->maximum_num_physicals ||
                        scsicmd->device->lun > 7) {
                scsicmd->result = DID_NO_CONNECT << 16;
                scsicmd->scsi_done(scsicmd);
                return 0;
        }
 
-       dev = (struct aac_dev *)scsicmd->device->host->hostdata;
        switch(scsicmd->sc_data_direction){
        case DMA_TO_DEVICE:
                flag = SRB_DataOut;
@@ -2103,8 +2108,8 @@ static int aac_send_srb_fib(struct scsi_cmnd* scsicmd)
 
        srbcmd = (struct aac_srb*) fib_data(cmd_fibcontext);
        srbcmd->function = cpu_to_le32(SRBF_ExecuteScsi);
-       srbcmd->channel  = cpu_to_le32(aac_logical_to_phys(scsicmd->device->channel));
-       srbcmd->id   = cpu_to_le32(scsicmd->device->id);
+       srbcmd->channel  = cpu_to_le32(aac_logical_to_phys(scmd_channel(scsicmd)));
+       srbcmd->id   = cpu_to_le32(scmd_id(scsicmd));
        srbcmd->lun      = cpu_to_le32(scsicmd->device->lun);
        srbcmd->flags    = cpu_to_le32(flag);
        timeout = scsicmd->timeout_per_command/HZ;
@@ -2161,7 +2166,8 @@ static int aac_send_srb_fib(struct scsi_cmnd* scsicmd)
        /*
         *      Check that the command queued to the controller
         */
-       if (status == -EINPROGRESS){
+       if (status == -EINPROGRESS) {
+               scsicmd->SCp.phase = AAC_OWNER_FIRMWARE;
                return 0;
        }
 
@@ -2192,8 +2198,6 @@ static unsigned long aac_build_sg(struct scsi_cmnd* scsicmd, struct sgmap* psg)
                        scsicmd->sc_data_direction);
                psg->count = cpu_to_le32(sg_count);
 
-               byte_count = 0;
-
                for (i = 0; i < sg_count; i++) {
                        psg->sg[i].addr = cpu_to_le32(sg_dma_address(sg));
                        psg->sg[i].count = cpu_to_le32(sg_dma_len(sg));
@@ -2249,18 +2253,17 @@ static unsigned long aac_build_sg64(struct scsi_cmnd* scsicmd, struct sgmap64* p
 
                sg_count = pci_map_sg(dev->pdev, sg, scsicmd->use_sg,
                        scsicmd->sc_data_direction);
-               psg->count = cpu_to_le32(sg_count);
-
-               byte_count = 0;
 
                for (i = 0; i < sg_count; i++) {
+                       int count = sg_dma_len(sg);
                        addr = sg_dma_address(sg);
                        psg->sg[i].addr[0] = cpu_to_le32(addr & 0xffffffff);
                        psg->sg[i].addr[1] = cpu_to_le32(addr>>32);
-                       psg->sg[i].count = cpu_to_le32(sg_dma_len(sg));
-                       byte_count += sg_dma_len(sg);
+                       psg->sg[i].count = cpu_to_le32(count);
+                       byte_count += count;
                        sg++;
                }
+               psg->count = cpu_to_le32(sg_count);
                /* hba wants the size to be exact */
                if(byte_count > scsicmd->request_bufflen){
                        u32 temp = le32_to_cpu(psg->sg[i-1].count) - 
@@ -2275,16 +2278,15 @@ static unsigned long aac_build_sg64(struct scsi_cmnd* scsicmd, struct sgmap64* p
                }
        }
        else if(scsicmd->request_bufflen) {
-               u64 addr; 
-               addr = pci_map_single(dev->pdev,
+               scsicmd->SCp.dma_handle = pci_map_single(dev->pdev,
                                scsicmd->request_buffer,
                                scsicmd->request_bufflen,
                                scsicmd->sc_data_direction);
+               addr = scsicmd->SCp.dma_handle;
                psg->count = cpu_to_le32(1);
                psg->sg[0].addr[0] = cpu_to_le32(addr & 0xffffffff);
                psg->sg[0].addr[1] = cpu_to_le32(addr >> 32);
                psg->sg[0].count = cpu_to_le32(scsicmd->request_bufflen);  
-               scsicmd->SCp.dma_handle = addr;
                byte_count = scsicmd->request_bufflen;
        }
        return byte_count;
index 9ce7002bd070508b438d4064ae6cbed2b912a0cb..f773b0dcfc9500efeb39c206ea1e9dd701bfeffb 100644 (file)
  *              D E F I N E S
  *----------------------------------------------------------------------------*/
 
+#ifndef AAC_DRIVER_BUILD
+# define AAC_DRIVER_BUILD 2409
+# define AAC_DRIVER_BRANCH "-mh1"
+#endif
 #define MAXIMUM_NUM_CONTAINERS 32
 
 #define AAC_NUM_MGT_FIB         8
@@ -25,7 +29,6 @@
  * These macros convert from physical channels to virtual channels
  */
 #define CONTAINER_CHANNEL              (0)
-#define ID_LUN_TO_CONTAINER(id, lun)   (id)
 #define CONTAINER_TO_CHANNEL(cont)     (CONTAINER_CHANNEL)
 #define CONTAINER_TO_ID(cont)          (cont)
 #define CONTAINER_TO_LUN(cont)         (0)
@@ -789,6 +792,7 @@ struct fsa_dev_info {
        u64             size;
        u32             type;
        u32             config_waiting_on;
+       unsigned long   config_waiting_stamp;
        u16             queue_depth;
        u8              config_needed;
        u8              valid;
@@ -1771,6 +1775,11 @@ static inline u32 cap_to_cyls(sector_t capacity, u32 divisor)
 }
 
 struct scsi_cmnd;
+/* SCp.phase values */
+#define AAC_OWNER_MIDLEVEL     0x101
+#define AAC_OWNER_LOWLEVEL     0x102
+#define AAC_OWNER_ERROR_HANDLER        0x103
+#define AAC_OWNER_FIRMWARE     0x106
 
 const char *aac_driverinfo(struct Scsi_Host *);
 struct fib *aac_fib_alloc(struct aac_dev *dev);
index 47fefca72695d02f3959b7a4e5c846a9c611c9bf..9f75144e5247e1a9a4ed5501fd0ffc6d9d3c4304 100644 (file)
@@ -38,6 +38,8 @@
 #include <linux/completion.h>
 #include <linux/dma-mapping.h>
 #include <linux/blkdev.h>
+#include <linux/delay.h>
+#include <linux/kthread.h>
 #include <asm/semaphore.h>
 #include <asm/uaccess.h>
 
@@ -293,6 +295,16 @@ return_fib:
                status = 0;
        } else {
                spin_unlock_irqrestore(&dev->fib_lock, flags);
+               /* If someone killed the AIF aacraid thread, restart it */
+               status = !dev->aif_thread;
+               if (status && dev->queues && dev->fsa_dev) {
+                       /* Be paranoid, be very paranoid! */
+                       kthread_stop(dev->thread);
+                       ssleep(1);
+                       dev->aif_thread = 0;
+                       dev->thread = kthread_run(aac_command_thread, dev, dev->name);
+                       ssleep(1);
+               }
                if (f.wait) {
                        if(down_interruptible(&fibctx->wait_sem) < 0) {
                                status = -EINTR;
index c7f80ec7abde11dd324d56a8d4245e6a05907afb..9f9f4aae23c02a498ad55a6af9b2a9cd249cffe1 100644 (file)
@@ -767,9 +767,9 @@ void aac_printf(struct aac_dev *dev, u32 val)
                if (cp[length] != 0)
                        cp[length] = 0;
                if (level == LOG_AAC_HIGH_ERROR)
-                       printk(KERN_WARNING "aacraid:%s", cp);
+                       printk(KERN_WARNING "%s:%s", dev->name, cp);
                else
-                       printk(KERN_INFO "aacraid:%s", cp);
+                       printk(KERN_INFO "%s:%s", dev->name, cp);
        }
        memset(cp, 0,  256);
 }
@@ -784,6 +784,7 @@ void aac_printf(struct aac_dev *dev, u32 val)
  *     dispatches it to the appropriate routine for handling.
  */
 
+#define AIF_SNIFF_TIMEOUT      (30*HZ)
 static void aac_handle_aif(struct aac_dev * dev, struct fib * fibptr)
 {
        struct hw_fib * hw_fib = fibptr->hw_fib;
@@ -837,6 +838,7 @@ static void aac_handle_aif(struct aac_dev * dev, struct fib * fibptr)
                                if (device) {
                                        dev->fsa_dev[container].config_needed = CHANGE;
                                        dev->fsa_dev[container].config_waiting_on = AifEnConfigChange;
+                                       dev->fsa_dev[container].config_waiting_stamp = jiffies;
                                        scsi_device_put(device);
                                }
                        }
@@ -849,13 +851,15 @@ static void aac_handle_aif(struct aac_dev * dev, struct fib * fibptr)
                if (container != (u32)-1) {
                        if (container >= dev->maximum_num_containers)
                                break;
-                       if (dev->fsa_dev[container].config_waiting_on ==
-                           le32_to_cpu(*(u32 *)aifcmd->data))
+                       if ((dev->fsa_dev[container].config_waiting_on ==
+                           le32_to_cpu(*(u32 *)aifcmd->data)) &&
+                        time_before(jiffies, dev->fsa_dev[container].config_waiting_stamp + AIF_SNIFF_TIMEOUT))
                                dev->fsa_dev[container].config_waiting_on = 0;
                } else for (container = 0;
                    container < dev->maximum_num_containers; ++container) {
-                       if (dev->fsa_dev[container].config_waiting_on ==
-                           le32_to_cpu(*(u32 *)aifcmd->data))
+                       if ((dev->fsa_dev[container].config_waiting_on ==
+                           le32_to_cpu(*(u32 *)aifcmd->data)) &&
+                        time_before(jiffies, dev->fsa_dev[container].config_waiting_stamp + AIF_SNIFF_TIMEOUT))
                                dev->fsa_dev[container].config_waiting_on = 0;
                }
                break;
@@ -872,6 +876,7 @@ static void aac_handle_aif(struct aac_dev * dev, struct fib * fibptr)
                        dev->fsa_dev[container].config_needed = ADD;
                        dev->fsa_dev[container].config_waiting_on =
                                AifEnConfigChange;
+                       dev->fsa_dev[container].config_waiting_stamp = jiffies;
                        break;
 
                /*
@@ -884,6 +889,7 @@ static void aac_handle_aif(struct aac_dev * dev, struct fib * fibptr)
                        dev->fsa_dev[container].config_needed = DELETE;
                        dev->fsa_dev[container].config_waiting_on =
                                AifEnConfigChange;
+                       dev->fsa_dev[container].config_waiting_stamp = jiffies;
                        break;
 
                /*
@@ -894,11 +900,13 @@ static void aac_handle_aif(struct aac_dev * dev, struct fib * fibptr)
                        container = le32_to_cpu(((u32 *)aifcmd->data)[1]);
                        if (container >= dev->maximum_num_containers)
                                break;
-                       if (dev->fsa_dev[container].config_waiting_on)
+                       if (dev->fsa_dev[container].config_waiting_on &&
+                        time_before(jiffies, dev->fsa_dev[container].config_waiting_stamp + AIF_SNIFF_TIMEOUT))
                                break;
                        dev->fsa_dev[container].config_needed = CHANGE;
                        dev->fsa_dev[container].config_waiting_on =
                                AifEnConfigChange;
+                       dev->fsa_dev[container].config_waiting_stamp = jiffies;
                        break;
 
                case AifEnConfigChange:
@@ -913,13 +921,15 @@ static void aac_handle_aif(struct aac_dev * dev, struct fib * fibptr)
                if (container != (u32)-1) {
                        if (container >= dev->maximum_num_containers)
                                break;
-                       if (dev->fsa_dev[container].config_waiting_on ==
-                           le32_to_cpu(*(u32 *)aifcmd->data))
+                       if ((dev->fsa_dev[container].config_waiting_on ==
+                           le32_to_cpu(*(u32 *)aifcmd->data)) &&
+                        time_before(jiffies, dev->fsa_dev[container].config_waiting_stamp + AIF_SNIFF_TIMEOUT))
                                dev->fsa_dev[container].config_waiting_on = 0;
                } else for (container = 0;
                    container < dev->maximum_num_containers; ++container) {
-                       if (dev->fsa_dev[container].config_waiting_on ==
-                           le32_to_cpu(*(u32 *)aifcmd->data))
+                       if ((dev->fsa_dev[container].config_waiting_on ==
+                           le32_to_cpu(*(u32 *)aifcmd->data)) &&
+                        time_before(jiffies, dev->fsa_dev[container].config_waiting_stamp + AIF_SNIFF_TIMEOUT))
                                dev->fsa_dev[container].config_waiting_on = 0;
                }
                break;
@@ -946,6 +956,8 @@ static void aac_handle_aif(struct aac_dev * dev, struct fib * fibptr)
                                dev->fsa_dev[container].config_waiting_on =
                                        AifEnContainerChange;
                                dev->fsa_dev[container].config_needed = ADD;
+                               dev->fsa_dev[container].config_waiting_stamp =
+                                       jiffies;
                        }
                }
                if ((((u32 *)aifcmd->data)[1] == cpu_to_le32(AifJobCtrZero))
@@ -961,6 +973,8 @@ static void aac_handle_aif(struct aac_dev * dev, struct fib * fibptr)
                                dev->fsa_dev[container].config_waiting_on =
                                        AifEnContainerChange;
                                dev->fsa_dev[container].config_needed = DELETE;
+                               dev->fsa_dev[container].config_waiting_stamp =
+                                       jiffies;
                        }
                }
                break;
@@ -969,8 +983,9 @@ static void aac_handle_aif(struct aac_dev * dev, struct fib * fibptr)
        device_config_needed = NOTHING;
        for (container = 0; container < dev->maximum_num_containers;
            ++container) {
-               if ((dev->fsa_dev[container].config_waiting_on == 0)
-                && (dev->fsa_dev[container].config_needed != NOTHING)) {
+               if ((dev->fsa_dev[container].config_waiting_on == 0) &&
+                       (dev->fsa_dev[container].config_needed != NOTHING) &&
+                       time_before(jiffies, dev->fsa_dev[container].config_waiting_stamp + AIF_SNIFF_TIMEOUT)) {
                        device_config_needed =
                                dev->fsa_dev[container].config_needed;
                        dev->fsa_dev[container].config_needed = NOTHING;
index 720330778648a99309e0a8381260561ad003025a..6ef89c99dd12cf5eabbc241c6fe38f7013a84298 100644 (file)
  * Abstract: Linux Driver entry module for Adaptec RAID Array Controller
  */
 
-#define AAC_DRIVER_VERSION             "1.1-4"
-#ifndef AAC_DRIVER_BRANCH
-#define AAC_DRIVER_BRANCH              ""
-#endif
-#define AAC_DRIVER_BUILD_DATE          __DATE__ " " __TIME__
-#define AAC_DRIVERNAME                 "aacraid"
 
 #include <linux/compat.h>
 #include <linux/blkdev.h>
 
 #include "aacraid.h"
 
+#define AAC_DRIVER_VERSION             "1.1-5"
+#ifndef AAC_DRIVER_BRANCH
+#define AAC_DRIVER_BRANCH              ""
+#endif
+#define AAC_DRIVER_BUILD_DATE          __DATE__ " " __TIME__
+#define AAC_DRIVERNAME                 "aacraid"
+
 #ifdef AAC_DRIVER_BUILD
 #define _str(x) #x
 #define str(x) _str(x)
@@ -73,7 +74,7 @@
 MODULE_AUTHOR("Red Hat Inc and Adaptec");
 MODULE_DESCRIPTION("Dell PERC2, 2/Si, 3/Si, 3/Di, "
                   "Adaptec Advanced Raid Products, "
-                  "and HP NetRAID-4M SCSI driver");
+                  "HP NetRAID-4M, IBM ServeRAID & ICP SCSI driver");
 MODULE_LICENSE("GPL");
 MODULE_VERSION(AAC_DRIVER_FULL_VERSION);
 
@@ -243,6 +244,7 @@ static struct aac_driver_ident aac_drivers[] = {
 static int aac_queuecommand(struct scsi_cmnd *cmd, void (*done)(struct scsi_cmnd *))
 {
        cmd->scsi_done = done;
+       cmd->SCp.phase = AAC_OWNER_LOWLEVEL;
        return (aac_scsi_cmd(cmd) ? FAILED : 0);
 } 
 
@@ -471,7 +473,8 @@ static int aac_eh_reset(struct scsi_cmnd* cmd)
                __shost_for_each_device(dev, host) {
                        spin_lock_irqsave(&dev->list_lock, flags);
                        list_for_each_entry(command, &dev->cmd_list, list) {
-                               if (command->serial_number) {
+                               if ((command != cmd) &&
+                                   (command->SCp.phase == AAC_OWNER_FIRMWARE)) {
                                        active++;
                                        break;
                                }
@@ -569,12 +572,12 @@ static long aac_compat_do_ioctl(struct aac_dev *dev, unsigned cmd, unsigned long
                
                f = compat_alloc_user_space(sizeof(*f));
                ret = 0;
-               if (clear_user(f, sizeof(*f) != sizeof(*f)))
+               if (clear_user(f, sizeof(*f)) != sizeof(*f))
                        ret = -EFAULT;
                if (copy_in_user(f, (void __user *)arg, sizeof(struct fib_ioctl) - sizeof(u32)))
                        ret = -EFAULT;
                if (!ret)
-                       ret = aac_do_ioctl(dev, cmd, (void __user *)arg);
+                       ret = aac_do_ioctl(dev, cmd, f);
                break;
        }
 
@@ -687,6 +690,18 @@ static ssize_t aac_show_serial_number(struct class_device *class_dev,
        return len;
 }
 
+static ssize_t aac_show_max_channel(struct class_device *class_dev, char *buf)
+{
+       return snprintf(buf, PAGE_SIZE, "%d\n",
+         class_to_shost(class_dev)->max_channel);
+}
+
+static ssize_t aac_show_max_id(struct class_device *class_dev, char *buf)
+{
+       return snprintf(buf, PAGE_SIZE, "%d\n",
+         class_to_shost(class_dev)->max_id);
+}
+
 
 static struct class_device_attribute aac_model = {
        .attr = {
@@ -730,6 +745,20 @@ static struct class_device_attribute aac_serial_number = {
        },
        .show = aac_show_serial_number,
 };
+static struct class_device_attribute aac_max_channel = {
+       .attr = {
+               .name = "max_channel",
+               .mode = S_IRUGO,
+       },
+       .show = aac_show_max_channel,
+};
+static struct class_device_attribute aac_max_id = {
+       .attr = {
+               .name = "max_id",
+               .mode = S_IRUGO,
+       },
+       .show = aac_show_max_id,
+};
 
 static struct class_device_attribute *aac_attrs[] = {
        &aac_model,
@@ -738,6 +767,8 @@ static struct class_device_attribute *aac_attrs[] = {
        &aac_monitor_version,
        &aac_bios_version,
        &aac_serial_number,
+       &aac_max_channel,
+       &aac_max_id,
        NULL
 };
 
@@ -775,6 +806,7 @@ static struct scsi_host_template aac_driver_template = {
        .cmd_per_lun                    = AAC_NUM_IO_FIB, 
 #endif 
        .use_clustering                 = ENABLE_CLUSTERING,
+       .emulated                       = 1,
 };
 
 
@@ -798,10 +830,11 @@ static int __devinit aac_probe_one(struct pci_dev *pdev,
        error = pci_enable_device(pdev);
        if (error)
                goto out;
+       error = -ENODEV;
 
        if (pci_set_dma_mask(pdev, DMA_32BIT_MASK) || 
                        pci_set_consistent_dma_mask(pdev, DMA_32BIT_MASK))
-               goto out;
+               goto out_disable_pdev;
        /*
         * If the quirk31 bit is set, the adapter needs adapter
         * to driver communication memory to be allocated below 2gig
@@ -809,7 +842,7 @@ static int __devinit aac_probe_one(struct pci_dev *pdev,
        if (aac_drivers[index].quirks & AAC_QUIRK_31BIT) 
                if (pci_set_dma_mask(pdev, DMA_31BIT_MASK) ||
                                pci_set_consistent_dma_mask(pdev, DMA_31BIT_MASK))
-                       goto out;
+                       goto out_disable_pdev;
        
        pci_set_master(pdev);
 
@@ -904,9 +937,9 @@ static int __devinit aac_probe_one(struct pci_dev *pdev,
         * physical channels are address by their actual physical number+1
         */
        if (aac->nondasd_support == 1)
-               shost->max_channel = aac->maximum_num_channels + 1;
+               shost->max_channel = aac->maximum_num_channels;
        else
-               shost->max_channel = 1;
+               shost->max_channel = 0;
 
        aac_get_config_status(aac);
        aac_get_containers(aac);
@@ -1020,7 +1053,8 @@ static int __init aac_init(void)
 
 static void __exit aac_exit(void)
 {
-       unregister_chrdev(aac_cfg_major, "aac");
+       if (aac_cfg_major > -1)
+               unregister_chrdev(aac_cfg_major, "aac");
        pci_unregister_driver(&aac_pci_driver);
 }
 
index e9b775d6bec9b54b5827e0d82c41665adc3182a5..7a23e027eb782911b58d9f109d799a3143dda884 100644 (file)
@@ -183,7 +183,7 @@ static int rkt_sync_cmd(struct aac_dev *dev, u32 command,
                /*
                 *      Yield the processor in case we are slow 
                 */
-               schedule_timeout_uninterruptible(1);
+               msleep(1);
        }
        if (ok != 1) {
                /*
@@ -343,7 +343,7 @@ static int aac_rkt_check_health(struct aac_dev *dev)
                  NULL, NULL, NULL, NULL, NULL);
                pci_free_consistent(dev->pdev, sizeof(struct POSTSTATUS),
                  post, paddr);
-                if ((buffer[0] == '0') && (buffer[1] == 'x')) {
+                if ((buffer[0] == '0') && ((buffer[1] == 'x') || (buffer[1] == 'X'))) {
                         ret = (buffer[2] <= '9') ? (buffer[2] - '0') : (buffer[2] - 'A' + 10);
                         ret <<= 4;
                         ret += (buffer[3] <= '9') ? (buffer[3] - '0') : (buffer[3] - 'A' + 10);
index 6998bc877dd685726b0c20c1c467ed57d1fe677a..729b9eb268c24ea0d103da98e4e3a965b4c75c70 100644 (file)
@@ -183,7 +183,7 @@ static int rx_sync_cmd(struct aac_dev *dev, u32 command,
                /*
                 *      Yield the processor in case we are slow 
                 */
-               schedule_timeout_uninterruptible(1);
+               msleep(1);
        }
        if (ok != 1) {
                /*
@@ -342,7 +342,7 @@ static int aac_rx_check_health(struct aac_dev *dev)
                  NULL, NULL, NULL, NULL, NULL);
                pci_free_consistent(dev->pdev, sizeof(struct POSTSTATUS),
                  post, paddr);
-               if ((buffer[0] == '0') && (buffer[1] == 'x')) {
+               if ((buffer[0] == '0') && ((buffer[1] == 'x') || (buffer[1] == 'X'))) {
                        ret = (buffer[2] <= '9') ? (buffer[2] - '0') : (buffer[2] - 'A' + 10);
                        ret <<= 4;
                        ret += (buffer[3] <= '9') ? (buffer[3] - '0') : (buffer[3] - 'A' + 10);
index 466f05cfbf0ce280596ec955f2e1ec7605ba227f..a534549082057972ee2df5e0575b32b139e986fd 100644 (file)
@@ -189,7 +189,7 @@ static int sa_sync_cmd(struct aac_dev *dev, u32 command,
                        ok = 1;
                        break;
                }
-               schedule_timeout_uninterruptible(1);
+               msleep(1);
        }
 
        if (ok != 1)
index 1bd82c4e52a0da80d1939a3b92ccce98fb222bf1..b4f8fb1d628b9d95ec70a28ffb81008eefb8f4d0 100644 (file)
@@ -207,7 +207,6 @@ static struct scsi_host_template ahci_sht = {
        .name                   = DRV_NAME,
        .ioctl                  = ata_scsi_ioctl,
        .queuecommand           = ata_scsi_queuecmd,
-       .eh_strategy_handler    = ata_scsi_error,
        .can_queue              = ATA_DEF_QUEUE,
        .this_id                = ATA_SHT_THIS_ID,
        .sg_tablesize           = AHCI_MAX_SG,
index 1d11f7e77564e9d83379532bc892d06da4b7a4e4..bb5166da4358ba5efb940049eb7e92250225ab68 100644 (file)
@@ -372,7 +372,7 @@ typedef enum {
        AHD_CURRENT_SENSING   = 0x40000,
        AHD_SCB_CONFIG_USED   = 0x80000,/* No SEEPROM but SCB had info. */
        AHD_HP_BOARD          = 0x100000,
-       AHD_RESET_POLL_ACTIVE = 0x200000,
+       AHD_BUS_RESET_ACTIVE  = 0x200000,
        AHD_UPDATE_PEND_CMDS  = 0x400000,
        AHD_RUNNING_QOUTFIFO  = 0x800000,
        AHD_HAD_FIRST_SEL     = 0x1000000
@@ -589,7 +589,7 @@ typedef enum {
        SCB_PACKETIZED          = 0x00800,
        SCB_EXPECT_PPR_BUSFREE  = 0x01000,
        SCB_PKT_SENSE           = 0x02000,
-       SCB_CMDPHASE_ABORT      = 0x04000,
+       SCB_EXTERNAL_RESET      = 0x04000,/* Device was reset externally */
        SCB_ON_COL_LIST         = 0x08000,
        SCB_SILENT              = 0x10000 /*
                                           * Be quiet about transmission type
index 326a622262352ea78aef9eed737365442eed025e..08771f6f68594f0cb3524937b9573eb3a81056a3 100644 (file)
@@ -207,7 +207,6 @@ static void         ahd_add_scb_to_free_list(struct ahd_softc *ahd,
 static u_int           ahd_rem_wscb(struct ahd_softc *ahd, u_int scbid,
                                     u_int prev, u_int next, u_int tid);
 static void            ahd_reset_current_bus(struct ahd_softc *ahd);
-static ahd_callback_t  ahd_reset_poll;
 static ahd_callback_t  ahd_stat_timer;
 #ifdef AHD_DUMP_SEQ
 static void            ahd_dumpseq(struct ahd_softc *ahd);
@@ -1054,12 +1053,10 @@ ahd_handle_seqint(struct ahd_softc *ahd, u_int intstat)
                         * If a target takes us into the command phase
                         * assume that it has been externally reset and
                         * has thus lost our previous packetized negotiation
-                        * agreement.  Since we have not sent an identify
-                        * message and may not have fully qualified the
-                        * connection, we change our command to TUR, assert
-                        * ATN and ABORT the task when we go to message in
-                        * phase.  The OSM will see the REQUEUE_REQUEST
-                        * status and retry the command.
+                        * agreement.
+                        * Revert to async/narrow transfers until we
+                        * can renegotiate with the device and notify
+                        * the OSM about the reset.
                         */
                        scbid = ahd_get_scbptr(ahd);
                        scb = ahd_lookup_scb(ahd, scbid);
@@ -1086,31 +1083,15 @@ ahd_handle_seqint(struct ahd_softc *ahd, u_int intstat)
                        ahd_set_syncrate(ahd, &devinfo, /*period*/0,
                                         /*offset*/0, /*ppr_options*/0,
                                         AHD_TRANS_ACTIVE, /*paused*/TRUE);
-                       ahd_outb(ahd, SCB_CDB_STORE, 0);
-                       ahd_outb(ahd, SCB_CDB_STORE+1, 0);
-                       ahd_outb(ahd, SCB_CDB_STORE+2, 0);
-                       ahd_outb(ahd, SCB_CDB_STORE+3, 0);
-                       ahd_outb(ahd, SCB_CDB_STORE+4, 0);
-                       ahd_outb(ahd, SCB_CDB_STORE+5, 0);
-                       ahd_outb(ahd, SCB_CDB_LEN, 6);
-                       scb->hscb->control &= ~(TAG_ENB|SCB_TAG_TYPE);
-                       scb->hscb->control |= MK_MESSAGE;
-                       ahd_outb(ahd, SCB_CONTROL, scb->hscb->control);
-                       ahd_outb(ahd, MSG_OUT, HOST_MSG);
-                       ahd_outb(ahd, SAVED_SCSIID, scb->hscb->scsiid);
-                       /*
-                        * The lun is 0, regardless of the SCB's lun
-                        * as we have not sent an identify message.
-                        */
-                       ahd_outb(ahd, SAVED_LUN, 0);
-                       ahd_outb(ahd, SEQ_FLAGS, 0);
-                       ahd_assert_atn(ahd);
-                       scb->flags &= ~SCB_PACKETIZED;
-                       scb->flags |= SCB_ABORT|SCB_CMDPHASE_ABORT;
+                       scb->flags |= SCB_EXTERNAL_RESET;
                        ahd_freeze_devq(ahd, scb);
                        ahd_set_transaction_status(scb, CAM_REQUEUE_REQ);
                        ahd_freeze_scb(scb);
 
+                       /* Notify XPT */
+                       ahd_send_async(ahd, devinfo.channel, devinfo.target,
+                                      CAM_LUN_WILDCARD, AC_SENT_BDR, NULL);
+
                        /*
                         * Allow the sequencer to continue with
                         * non-pack processing.
@@ -1534,6 +1515,18 @@ ahd_handle_scsiint(struct ahd_softc *ahd, u_int intstat)
        lqistat1 = ahd_inb(ahd, LQISTAT1);
        lqostat0 = ahd_inb(ahd, LQOSTAT0);
        busfreetime = ahd_inb(ahd, SSTAT2) & BUSFREETIME;
+
+       /*
+        * Ignore external resets after a bus reset.
+        */
+       if (((status & SCSIRSTI) != 0) && (ahd->flags & AHD_BUS_RESET_ACTIVE))
+               return;
+
+       /*
+        * Clear bus reset flag
+        */
+       ahd->flags &= ~AHD_BUS_RESET_ACTIVE;
+
        if ((status0 & (SELDI|SELDO)) != 0) {
                u_int simode0;
 
@@ -2207,22 +2200,6 @@ ahd_handle_nonpkt_busfree(struct ahd_softc *ahd)
                        if (sent_msg == MSG_ABORT_TAG)
                                tag = SCB_GET_TAG(scb);
 
-                       if ((scb->flags & SCB_CMDPHASE_ABORT) != 0) {
-                               /*
-                                * This abort is in response to an
-                                * unexpected switch to command phase
-                                * for a packetized connection.  Since
-                                * the identify message was never sent,
-                                * "saved lun" is 0.  We really want to
-                                * abort only the SCB that encountered
-                                * this error, which could have a different
-                                * lun.  The SCB will be retried so the OS
-                                * will see the UA after renegotiating to
-                                * packetized.
-                                */
-                               tag = SCB_GET_TAG(scb);
-                               saved_lun = scb->hscb->lun;
-                       }
                        found = ahd_abort_scbs(ahd, target, 'A', saved_lun,
                                               tag, ROLE_INITIATOR,
                                               CAM_REQ_ABORTED);
@@ -7847,6 +7824,17 @@ ahd_reset_channel(struct ahd_softc *ahd, char channel, int initiate_reset)
        int     found;
        u_int   fifo;
        u_int   next_fifo;
+       uint8_t scsiseq;
+
+       /*
+        * Check if the last bus reset is cleared
+        */
+       if (ahd->flags & AHD_BUS_RESET_ACTIVE) {
+               printf("%s: bus reset still active\n",
+                      ahd_name(ahd));
+               return 0;
+       }
+       ahd->flags |= AHD_BUS_RESET_ACTIVE;
 
        ahd->pending_device = NULL;
 
@@ -7860,6 +7848,12 @@ ahd_reset_channel(struct ahd_softc *ahd, char channel, int initiate_reset)
        /* Make sure the sequencer is in a safe location. */
        ahd_clear_critical_section(ahd);
 
+       /*
+        * Run our command complete fifos to ensure that we perform
+        * completion processing on any commands that 'completed'
+        * before the reset occurred.
+        */
+       ahd_run_qoutfifo(ahd);
 #ifdef AHD_TARGET_MODE
        if ((ahd->flags & AHD_TARGETROLE) != 0) {
                ahd_run_tqinfifo(ahd, /*paused*/TRUE);
@@ -7924,30 +7918,14 @@ ahd_reset_channel(struct ahd_softc *ahd, char channel, int initiate_reset)
        ahd_clear_fifo(ahd, 1);
 
        /*
-        * Revert to async/narrow transfers until we renegotiate.
+        * Reenable selections
         */
-       max_scsiid = (ahd->features & AHD_WIDE) ? 15 : 7;
-       for (target = 0; target <= max_scsiid; target++) {
-
-               if (ahd->enabled_targets[target] == NULL)
-                       continue;
-               for (initiator = 0; initiator <= max_scsiid; initiator++) {
-                       struct ahd_devinfo devinfo;
-
-                       ahd_compile_devinfo(&devinfo, target, initiator,
-                                           CAM_LUN_WILDCARD,
-                                           'A', ROLE_UNKNOWN);
-                       ahd_set_width(ahd, &devinfo, MSG_EXT_WDTR_BUS_8_BIT,
-                                     AHD_TRANS_CUR, /*paused*/TRUE);
-                       ahd_set_syncrate(ahd, &devinfo, /*period*/0,
-                                        /*offset*/0, /*ppr_options*/0,
-                                        AHD_TRANS_CUR, /*paused*/TRUE);
-               }
-       }
+       ahd_outb(ahd, SIMODE1, ahd_inb(ahd, SIMODE1) | ENSCSIRST);
+       scsiseq = ahd_inb(ahd, SCSISEQ_TEMPLATE);
+       ahd_outb(ahd, SCSISEQ1, scsiseq & (ENSELI|ENRSELI|ENAUTOATNP));
 
-#ifdef AHD_TARGET_MODE
        max_scsiid = (ahd->features & AHD_WIDE) ? 15 : 7;
-
+#ifdef AHD_TARGET_MODE
        /*
         * Send an immediate notify ccb to all target more peripheral
         * drivers affected by this action.
@@ -7975,51 +7953,31 @@ ahd_reset_channel(struct ahd_softc *ahd, char channel, int initiate_reset)
        /* Notify the XPT that a bus reset occurred */
        ahd_send_async(ahd, devinfo.channel, CAM_TARGET_WILDCARD,
                       CAM_LUN_WILDCARD, AC_BUS_RESET, NULL);
-       ahd_restart(ahd);
+
        /*
-        * Freeze the SIMQ until our poller can determine that
-        * the bus reset has really gone away.  We set the initial
-        * timer to 0 to have the check performed as soon as possible
-        * from the timer context.
+        * Revert to async/narrow transfers until we renegotiate.
         */
-       if ((ahd->flags & AHD_RESET_POLL_ACTIVE) == 0) {
-               ahd->flags |= AHD_RESET_POLL_ACTIVE;
-               ahd_freeze_simq(ahd);
-               ahd_timer_reset(&ahd->reset_timer, 0, ahd_reset_poll, ahd);
-       }
-       return (found);
-}
+       for (target = 0; target <= max_scsiid; target++) {
 
+               if (ahd->enabled_targets[target] == NULL)
+                       continue;
+               for (initiator = 0; initiator <= max_scsiid; initiator++) {
+                       struct ahd_devinfo devinfo;
 
-#define AHD_RESET_POLL_US 1000
-static void
-ahd_reset_poll(void *arg)
-{
-       struct  ahd_softc *ahd = arg;
-       u_int   scsiseq1;
-       u_long  s;
-       
-       ahd_lock(ahd, &s);
-       ahd_pause(ahd);
-       ahd_update_modes(ahd);
-       ahd_set_modes(ahd, AHD_MODE_SCSI, AHD_MODE_SCSI);
-       ahd_outb(ahd, CLRSINT1, CLRSCSIRSTI);
-       if ((ahd_inb(ahd, SSTAT1) & SCSIRSTI) != 0) {
-               ahd_timer_reset(&ahd->reset_timer, AHD_RESET_POLL_US,
-                               ahd_reset_poll, ahd);
-               ahd_unpause(ahd);
-               ahd_unlock(ahd, &s);
-               return;
+                       ahd_compile_devinfo(&devinfo, target, initiator,
+                                           CAM_LUN_WILDCARD,
+                                           'A', ROLE_UNKNOWN);
+                       ahd_set_width(ahd, &devinfo, MSG_EXT_WDTR_BUS_8_BIT,
+                                     AHD_TRANS_CUR, /*paused*/TRUE);
+                       ahd_set_syncrate(ahd, &devinfo, /*period*/0,
+                                        /*offset*/0, /*ppr_options*/0,
+                                        AHD_TRANS_CUR, /*paused*/TRUE);
+               }
        }
 
-       /* Reset is now low.  Complete chip reinitialization. */
-       ahd_outb(ahd, SIMODE1, ahd_inb(ahd, SIMODE1) | ENSCSIRST);
-       scsiseq1 = ahd_inb(ahd, SCSISEQ_TEMPLATE);
-       ahd_outb(ahd, SCSISEQ1, scsiseq1 & (ENSELI|ENRSELI|ENAUTOATNP));
-       ahd_unpause(ahd);
-       ahd->flags &= ~AHD_RESET_POLL_ACTIVE;
-       ahd_unlock(ahd, &s);
-       ahd_release_simq(ahd);
+       ahd_restart(ahd);
+
+       return (found);
 }
 
 /**************************** Statistics Processing ***************************/
index bcced0a417e690967c0630b01b5c997e08e46106..66e4a47bb9ee3fe85d72f6c2e0679d759dbd1fd6 100644 (file)
@@ -782,6 +782,7 @@ ahd_linux_bus_reset(struct scsi_cmnd *cmd)
 {
        struct ahd_softc *ahd;
        int    found;
+       unsigned long flags;
 
        ahd = *(struct ahd_softc **)cmd->device->host->hostdata;
 #ifdef AHD_DEBUG
@@ -789,8 +790,11 @@ ahd_linux_bus_reset(struct scsi_cmnd *cmd)
                printf("%s: Bus reset called for cmd %p\n",
                       ahd_name(ahd), cmd);
 #endif
+       ahd_lock(ahd, &flags);
+
        found = ahd_reset_channel(ahd, scmd_channel(cmd) + 'A',
                                  /*initiate reset*/TRUE);
+       ahd_unlock(ahd, &flags);
 
        if (bootverbose)
                printf("%s: SCSI bus reset delivered. "
index 24e71b5551722221a7c8a2ee86b66a04f2b08ecb..6dc88149f9f1537e0e20b708696a2949f053bac2 100644 (file)
@@ -209,7 +209,6 @@ static struct scsi_host_template piix_sht = {
        .name                   = DRV_NAME,
        .ioctl                  = ata_scsi_ioctl,
        .queuecommand           = ata_scsi_queuecmd,
-       .eh_strategy_handler    = ata_scsi_error,
        .can_queue              = ATA_DEF_QUEUE,
        .this_id                = ATA_SHT_THIS_ID,
        .sg_tablesize           = LIBATA_MAX_PRD,
index ef57f253031c60043d6ac72d24697f46254a1c5c..dfcb96f3e60ce2782a39fffc415010ef54c272d0 100644 (file)
@@ -294,18 +294,6 @@ struct Scsi_Host *scsi_host_alloc(struct scsi_host_template *sht, int privsize)
        if (sht->unchecked_isa_dma && privsize)
                gfp_mask |= __GFP_DMA;
 
-        /* Check to see if this host has any error handling facilities */
-        if (!sht->eh_strategy_handler && !sht->eh_abort_handler &&
-           !sht->eh_device_reset_handler && !sht->eh_bus_reset_handler &&
-            !sht->eh_host_reset_handler) {
-               printk(KERN_ERR "ERROR: SCSI host `%s' has no error handling\n"
-                               "ERROR: This is not a safe way to run your "
-                                       "SCSI host\n"
-                               "ERROR: The error handling must be added to "
-                               "this driver\n", sht->proc_name);
-               dump_stack();
-        }
-
        shost = kzalloc(sizeof(struct Scsi_Host) + privsize, gfp_mask);
        if (!shost)
                return NULL;
index eaefeddb2b4ad48aa57e124a6eef2dfefeaf472a..0a8ad37ae8998407528f8c710e9ecb9b1cb82828 100644 (file)
@@ -168,7 +168,7 @@ static void release_event_pool(struct event_pool *pool,
                        ++in_use;
                if (pool->events[i].ext_list) {
                        dma_free_coherent(hostdata->dev,
-                                 SG_ALL * sizeof(struct memory_descriptor),
+                                 SG_ALL * sizeof(struct srp_direct_buf),
                                  pool->events[i].ext_list,
                                  pool->events[i].ext_list_token);
                }
@@ -284,40 +284,37 @@ static void set_srp_direction(struct scsi_cmnd *cmd,
                              struct srp_cmd *srp_cmd, 
                              int numbuf)
 {
+       u8 fmt;
+
        if (numbuf == 0)
                return;
        
-       if (numbuf == 1) {
+       if (numbuf == 1)
+               fmt = SRP_DATA_DESC_DIRECT;
+       else {
+               fmt = SRP_DATA_DESC_INDIRECT;
+               numbuf = min(numbuf, MAX_INDIRECT_BUFS);
+
                if (cmd->sc_data_direction == DMA_TO_DEVICE)
-                       srp_cmd->data_out_format = SRP_DIRECT_BUFFER;
-               else 
-                       srp_cmd->data_in_format = SRP_DIRECT_BUFFER;
-       } else {
-               if (cmd->sc_data_direction == DMA_TO_DEVICE) {
-                       srp_cmd->data_out_format = SRP_INDIRECT_BUFFER;
-                       srp_cmd->data_out_count =
-                               numbuf < MAX_INDIRECT_BUFS ?
-                                       numbuf: MAX_INDIRECT_BUFS;
-               } else {
-                       srp_cmd->data_in_format = SRP_INDIRECT_BUFFER;
-                       srp_cmd->data_in_count =
-                               numbuf < MAX_INDIRECT_BUFS ?
-                                       numbuf: MAX_INDIRECT_BUFS;
-               }
+                       srp_cmd->data_out_desc_cnt = numbuf;
+               else
+                       srp_cmd->data_in_desc_cnt = numbuf;
        }
+
+       if (cmd->sc_data_direction == DMA_TO_DEVICE)
+               srp_cmd->buf_fmt = fmt << 4;
+       else
+               srp_cmd->buf_fmt = fmt;
 }
 
-static void unmap_sg_list(int num_entries, 
+static void unmap_sg_list(int num_entries,
                struct device *dev,
-               struct memory_descriptor *md)
-{ 
+               struct srp_direct_buf *md)
+{
        int i;
 
-       for (i = 0; i < num_entries; ++i) {
-               dma_unmap_single(dev,
-                       md[i].virtual_address,
-                       md[i].length, DMA_BIDIRECTIONAL);
-       }
+       for (i = 0; i < num_entries; ++i)
+               dma_unmap_single(dev, md[i].va, md[i].len, DMA_BIDIRECTIONAL);
 }
 
 /**
@@ -330,23 +327,26 @@ static void unmap_cmd_data(struct srp_cmd *cmd,
                           struct srp_event_struct *evt_struct,
                           struct device *dev)
 {
-       if ((cmd->data_out_format == SRP_NO_BUFFER) &&
-           (cmd->data_in_format == SRP_NO_BUFFER))
+       u8 out_fmt, in_fmt;
+
+       out_fmt = cmd->buf_fmt >> 4;
+       in_fmt = cmd->buf_fmt & ((1U << 4) - 1);
+
+       if (out_fmt == SRP_NO_DATA_DESC && in_fmt == SRP_NO_DATA_DESC)
                return;
-       else if ((cmd->data_out_format == SRP_DIRECT_BUFFER) ||
-                (cmd->data_in_format == SRP_DIRECT_BUFFER)) {
-               struct memory_descriptor *data =
-                       (struct memory_descriptor *)cmd->additional_data;
-               dma_unmap_single(dev, data->virtual_address, data->length,
-                                DMA_BIDIRECTIONAL);
+       else if (out_fmt == SRP_DATA_DESC_DIRECT ||
+                in_fmt == SRP_DATA_DESC_DIRECT) {
+               struct srp_direct_buf *data =
+                       (struct srp_direct_buf *) cmd->add_data;
+               dma_unmap_single(dev, data->va, data->len, DMA_BIDIRECTIONAL);
        } else {
-               struct indirect_descriptor *indirect =
-                       (struct indirect_descriptor *)cmd->additional_data;
-               int num_mapped = indirect->head.length / 
-                       sizeof(indirect->list[0]);
+               struct srp_indirect_buf *indirect =
+                       (struct srp_indirect_buf *) cmd->add_data;
+               int num_mapped = indirect->table_desc.len /
+                       sizeof(struct srp_direct_buf);
 
                if (num_mapped <= MAX_INDIRECT_BUFS) {
-                       unmap_sg_list(num_mapped, dev, &indirect->list[0]);
+                       unmap_sg_list(num_mapped, dev, &indirect->desc_list[0]);
                        return;
                }
 
@@ -356,17 +356,17 @@ static void unmap_cmd_data(struct srp_cmd *cmd,
 
 static int map_sg_list(int num_entries, 
                       struct scatterlist *sg,
-                      struct memory_descriptor *md)
+                      struct srp_direct_buf *md)
 {
        int i;
        u64 total_length = 0;
 
        for (i = 0; i < num_entries; ++i) {
-               struct memory_descriptor *descr = md + i;
+               struct srp_direct_buf *descr = md + i;
                struct scatterlist *sg_entry = &sg[i];
-               descr->virtual_address = sg_dma_address(sg_entry);
-               descr->length = sg_dma_len(sg_entry);
-               descr->memory_handle = 0;
+               descr->va = sg_dma_address(sg_entry);
+               descr->len = sg_dma_len(sg_entry);
+               descr->key = 0;
                total_length += sg_dma_len(sg_entry);
        }
        return total_length;
@@ -389,10 +389,10 @@ static int map_sg_data(struct scsi_cmnd *cmd,
        int sg_mapped;
        u64 total_length = 0;
        struct scatterlist *sg = cmd->request_buffer;
-       struct memory_descriptor *data =
-           (struct memory_descriptor *)srp_cmd->additional_data;
-       struct indirect_descriptor *indirect =
-           (struct indirect_descriptor *)data;
+       struct srp_direct_buf *data =
+               (struct srp_direct_buf *) srp_cmd->add_data;
+       struct srp_indirect_buf *indirect =
+               (struct srp_indirect_buf *) data;
 
        sg_mapped = dma_map_sg(dev, sg, cmd->use_sg, DMA_BIDIRECTIONAL);
 
@@ -403,9 +403,9 @@ static int map_sg_data(struct scsi_cmnd *cmd,
 
        /* special case; we can use a single direct descriptor */
        if (sg_mapped == 1) {
-               data->virtual_address = sg_dma_address(&sg[0]);
-               data->length = sg_dma_len(&sg[0]);
-               data->memory_handle = 0;
+               data->va = sg_dma_address(&sg[0]);
+               data->len = sg_dma_len(&sg[0]);
+               data->key = 0;
                return 1;
        }
 
@@ -416,25 +416,26 @@ static int map_sg_data(struct scsi_cmnd *cmd,
                return 0;
        }
 
-       indirect->head.virtual_address = 0;
-       indirect->head.length = sg_mapped * sizeof(indirect->list[0]);
-       indirect->head.memory_handle = 0;
+       indirect->table_desc.va = 0;
+       indirect->table_desc.len = sg_mapped * sizeof(struct srp_direct_buf);
+       indirect->table_desc.key = 0;
 
        if (sg_mapped <= MAX_INDIRECT_BUFS) {
-               total_length = map_sg_list(sg_mapped, sg, &indirect->list[0]);
-               indirect->total_length = total_length;
+               total_length = map_sg_list(sg_mapped, sg,
+                                          &indirect->desc_list[0]);
+               indirect->len = total_length;
                return 1;
        }
 
        /* get indirect table */
        if (!evt_struct->ext_list) {
-               evt_struct->ext_list =(struct memory_descriptor*)
+               evt_struct->ext_list = (struct srp_direct_buf *)
                        dma_alloc_coherent(dev, 
-                               SG_ALL * sizeof(struct memory_descriptor),
-                               &evt_struct->ext_list_token, 0);
+                                          SG_ALL * sizeof(struct srp_direct_buf),
+                                          &evt_struct->ext_list_token, 0);
                if (!evt_struct->ext_list) {
-                   printk(KERN_ERR
-                       "ibmvscsi: Can't allocate memory for indirect table\n");
+                       printk(KERN_ERR
+                              "ibmvscsi: Can't allocate memory for indirect table\n");
                        return 0;
                        
                }
@@ -442,11 +443,11 @@ static int map_sg_data(struct scsi_cmnd *cmd,
 
        total_length = map_sg_list(sg_mapped, sg, evt_struct->ext_list);        
 
-       indirect->total_length = total_length;
-       indirect->head.virtual_address = evt_struct->ext_list_token;
-       indirect->head.length = sg_mapped * sizeof(indirect->list[0]);
-       memcpy(indirect->list, evt_struct->ext_list,
-               MAX_INDIRECT_BUFS * sizeof(struct memory_descriptor));
+       indirect->len = total_length;
+       indirect->table_desc.va = evt_struct->ext_list_token;
+       indirect->table_desc.len = sg_mapped * sizeof(indirect->desc_list[0]);
+       memcpy(indirect->desc_list, evt_struct->ext_list,
+              MAX_INDIRECT_BUFS * sizeof(struct srp_direct_buf));
        
        return 1;
 }
@@ -463,20 +464,20 @@ static int map_sg_data(struct scsi_cmnd *cmd,
 static int map_single_data(struct scsi_cmnd *cmd,
                           struct srp_cmd *srp_cmd, struct device *dev)
 {
-       struct memory_descriptor *data =
-           (struct memory_descriptor *)srp_cmd->additional_data;
+       struct srp_direct_buf *data =
+               (struct srp_direct_buf *) srp_cmd->add_data;
 
-       data->virtual_address =
+       data->va =
                dma_map_single(dev, cmd->request_buffer,
                               cmd->request_bufflen,
                               DMA_BIDIRECTIONAL);
-       if (dma_mapping_error(data->virtual_address)) {
+       if (dma_mapping_error(data->va)) {
                printk(KERN_ERR
                       "ibmvscsi: Unable to map request_buffer for command!\n");
                return 0;
        }
-       data->length = cmd->request_bufflen;
-       data->memory_handle = 0;
+       data->len = cmd->request_bufflen;
+       data->key = 0;
 
        set_srp_direction(cmd, srp_cmd, 1);
 
@@ -548,7 +549,7 @@ static int ibmvscsi_send_srp_event(struct srp_event_struct *evt_struct,
 
        /* Copy the IU into the transfer area */
        *evt_struct->xfer_iu = evt_struct->iu;
-       evt_struct->xfer_iu->srp.generic.tag = (u64)evt_struct;
+       evt_struct->xfer_iu->srp.rsp.tag = (u64)evt_struct;
 
        /* Add this to the sent list.  We need to do this 
         * before we actually send 
@@ -586,27 +587,27 @@ static void handle_cmd_rsp(struct srp_event_struct *evt_struct)
        struct srp_rsp *rsp = &evt_struct->xfer_iu->srp.rsp;
        struct scsi_cmnd *cmnd = evt_struct->cmnd;
 
-       if (unlikely(rsp->type != SRP_RSP_TYPE)) {
+       if (unlikely(rsp->opcode != SRP_RSP)) {
                if (printk_ratelimit())
                        printk(KERN_WARNING 
                               "ibmvscsi: bad SRP RSP type %d\n",
-                              rsp->type);
+                              rsp->opcode);
        }
        
        if (cmnd) {
                cmnd->result = rsp->status;
                if (((cmnd->result >> 1) & 0x1f) == CHECK_CONDITION)
                        memcpy(cmnd->sense_buffer,
-                              rsp->sense_and_response_data,
-                              rsp->sense_data_list_length);
+                              rsp->data,
+                              rsp->sense_data_len);
                unmap_cmd_data(&evt_struct->iu.srp.cmd, 
                               evt_struct, 
                               evt_struct->hostdata->dev);
 
-               if (rsp->doover)
-                       cmnd->resid = rsp->data_out_residual_count;
-               else if (rsp->diover)
-                       cmnd->resid = rsp->data_in_residual_count;
+               if (rsp->flags & SRP_RSP_FLAG_DOOVER)
+                       cmnd->resid = rsp->data_out_res_cnt;
+               else if (rsp->flags & SRP_RSP_FLAG_DIOVER)
+                       cmnd->resid = rsp->data_in_res_cnt;
        }
 
        if (evt_struct->cmnd_done)
@@ -633,10 +634,11 @@ static int ibmvscsi_queuecommand(struct scsi_cmnd *cmnd,
 {
        struct srp_cmd *srp_cmd;
        struct srp_event_struct *evt_struct;
-       struct indirect_descriptor *indirect;
+       struct srp_indirect_buf *indirect;
        struct ibmvscsi_host_data *hostdata =
                (struct ibmvscsi_host_data *)&cmnd->device->host->hostdata;
        u16 lun = lun_from_dev(cmnd->device);
+       u8 out_fmt, in_fmt;
 
        evt_struct = get_event_struct(&hostdata->pool);
        if (!evt_struct)
@@ -644,8 +646,8 @@ static int ibmvscsi_queuecommand(struct scsi_cmnd *cmnd,
 
        /* Set up the actual SRP IU */
        srp_cmd = &evt_struct->iu.srp.cmd;
-       memset(srp_cmd, 0x00, sizeof(*srp_cmd));
-       srp_cmd->type = SRP_CMD_TYPE;
+       memset(srp_cmd, 0x00, SRP_MAX_IU_LEN);
+       srp_cmd->opcode = SRP_CMD;
        memcpy(srp_cmd->cdb, cmnd->cmnd, sizeof(cmnd->cmnd));
        srp_cmd->lun = ((u64) lun) << 48;
 
@@ -664,13 +666,15 @@ static int ibmvscsi_queuecommand(struct scsi_cmnd *cmnd,
        evt_struct->cmnd_done = done;
 
        /* Fix up dma address of the buffer itself */
-       indirect = (struct indirect_descriptor *)srp_cmd->additional_data;
-       if (((srp_cmd->data_out_format == SRP_INDIRECT_BUFFER) ||
-           (srp_cmd->data_in_format == SRP_INDIRECT_BUFFER)) &&
-           (indirect->head.virtual_address == 0)) {
-               indirect->head.virtual_address = evt_struct->crq.IU_data_ptr +
-                   offsetof(struct srp_cmd, additional_data) +
-                   offsetof(struct indirect_descriptor, list);
+       indirect = (struct srp_indirect_buf *) srp_cmd->add_data;
+       out_fmt = srp_cmd->buf_fmt >> 4;
+       in_fmt = srp_cmd->buf_fmt & ((1U << 4) - 1);
+       if ((in_fmt == SRP_DATA_DESC_INDIRECT ||
+            out_fmt == SRP_DATA_DESC_INDIRECT) &&
+           indirect->table_desc.va == 0) {
+               indirect->table_desc.va = evt_struct->crq.IU_data_ptr +
+                       offsetof(struct srp_cmd, add_data) +
+                       offsetof(struct srp_indirect_buf, desc_list);
        }
 
        return ibmvscsi_send_srp_event(evt_struct, hostdata);
@@ -780,10 +784,10 @@ static void send_mad_adapter_info(struct ibmvscsi_host_data *hostdata)
 static void login_rsp(struct srp_event_struct *evt_struct)
 {
        struct ibmvscsi_host_data *hostdata = evt_struct->hostdata;
-       switch (evt_struct->xfer_iu->srp.generic.type) {
-       case SRP_LOGIN_RSP_TYPE:        /* it worked! */
+       switch (evt_struct->xfer_iu->srp.login_rsp.opcode) {
+       case SRP_LOGIN_RSP:     /* it worked! */
                break;
-       case SRP_LOGIN_REJ_TYPE:        /* refused! */
+       case SRP_LOGIN_REJ:     /* refused! */
                printk(KERN_INFO "ibmvscsi: SRP_LOGIN_REJ reason %u\n",
                       evt_struct->xfer_iu->srp.login_rej.reason);
                /* Login failed.  */
@@ -792,7 +796,7 @@ static void login_rsp(struct srp_event_struct *evt_struct)
        default:
                printk(KERN_ERR
                       "ibmvscsi: Invalid login response typecode 0x%02x!\n",
-                      evt_struct->xfer_iu->srp.generic.type);
+                      evt_struct->xfer_iu->srp.login_rsp.opcode);
                /* Login failed.  */
                atomic_set(&hostdata->request_limit, -1);
                return;
@@ -800,17 +804,17 @@ static void login_rsp(struct srp_event_struct *evt_struct)
 
        printk(KERN_INFO "ibmvscsi: SRP_LOGIN succeeded\n");
 
-       if (evt_struct->xfer_iu->srp.login_rsp.request_limit_delta >
+       if (evt_struct->xfer_iu->srp.login_rsp.req_lim_delta >
            (max_requests - 2))
-               evt_struct->xfer_iu->srp.login_rsp.request_limit_delta =
+               evt_struct->xfer_iu->srp.login_rsp.req_lim_delta =
                    max_requests - 2;
 
        /* Now we know what the real request-limit is */
        atomic_set(&hostdata->request_limit,
-                  evt_struct->xfer_iu->srp.login_rsp.request_limit_delta);
+                  evt_struct->xfer_iu->srp.login_rsp.req_lim_delta);
 
        hostdata->host->can_queue =
-           evt_struct->xfer_iu->srp.login_rsp.request_limit_delta - 2;
+           evt_struct->xfer_iu->srp.login_rsp.req_lim_delta - 2;
 
        if (hostdata->host->can_queue < 1) {
                printk(KERN_ERR "ibmvscsi: Invalid request_limit_delta\n");
@@ -849,18 +853,19 @@ static int send_srp_login(struct ibmvscsi_host_data *hostdata)
 
        login = &evt_struct->iu.srp.login_req;
        memset(login, 0x00, sizeof(struct srp_login_req));
-       login->type = SRP_LOGIN_REQ_TYPE;
-       login->max_requested_initiator_to_target_iulen = sizeof(union srp_iu);
-       login->required_buffer_formats = 0x0006;
+       login->opcode = SRP_LOGIN_REQ;
+       login->req_it_iu_len = sizeof(union srp_iu);
+       login->req_buf_fmt = SRP_BUF_FORMAT_DIRECT | SRP_BUF_FORMAT_INDIRECT;
        
+       spin_lock_irqsave(hostdata->host->host_lock, flags);
        /* Start out with a request limit of 1, since this is negotiated in
         * the login request we are just sending
         */
        atomic_set(&hostdata->request_limit, 1);
 
-       spin_lock_irqsave(hostdata->host->host_lock, flags);
        rc = ibmvscsi_send_srp_event(evt_struct, hostdata);
        spin_unlock_irqrestore(hostdata->host->host_lock, flags);
+       printk("ibmvscsic: sent SRP login\n");
        return rc;
 };
 
@@ -928,13 +933,13 @@ static int ibmvscsi_eh_abort_handler(struct scsi_cmnd *cmd)
        
        /* Set up an abort SRP command */
        memset(tsk_mgmt, 0x00, sizeof(*tsk_mgmt));
-       tsk_mgmt->type = SRP_TSK_MGMT_TYPE;
+       tsk_mgmt->opcode = SRP_TSK_MGMT;
        tsk_mgmt->lun = ((u64) lun) << 48;
-       tsk_mgmt->task_mgmt_flags = 0x01;       /* ABORT TASK */
-       tsk_mgmt->managed_task_tag = (u64) found_evt;
+       tsk_mgmt->tsk_mgmt_func = SRP_TSK_ABORT_TASK;
+       tsk_mgmt->task_tag = (u64) found_evt;
 
        printk(KERN_INFO "ibmvscsi: aborting command. lun 0x%lx, tag 0x%lx\n",
-              tsk_mgmt->lun, tsk_mgmt->managed_task_tag);
+              tsk_mgmt->lun, tsk_mgmt->task_tag);
 
        evt->sync_srp = &srp_rsp;
        init_completion(&evt->comp);
@@ -948,25 +953,25 @@ static int ibmvscsi_eh_abort_handler(struct scsi_cmnd *cmd)
        wait_for_completion(&evt->comp);
 
        /* make sure we got a good response */
-       if (unlikely(srp_rsp.srp.generic.type != SRP_RSP_TYPE)) {
+       if (unlikely(srp_rsp.srp.rsp.opcode != SRP_RSP)) {
                if (printk_ratelimit())
                        printk(KERN_WARNING 
                               "ibmvscsi: abort bad SRP RSP type %d\n",
-                              srp_rsp.srp.generic.type);
+                              srp_rsp.srp.rsp.opcode);
                return FAILED;
        }
 
-       if (srp_rsp.srp.rsp.rspvalid)
-               rsp_rc = *((int *)srp_rsp.srp.rsp.sense_and_response_data);
+       if (srp_rsp.srp.rsp.flags & SRP_RSP_FLAG_RSPVALID)
+               rsp_rc = *((int *)srp_rsp.srp.rsp.data);
        else
                rsp_rc = srp_rsp.srp.rsp.status;
 
        if (rsp_rc) {
                if (printk_ratelimit())
                        printk(KERN_WARNING 
-                      "ibmvscsi: abort code %d for task tag 0x%lx\n",
+                              "ibmvscsi: abort code %d for task tag 0x%lx\n",
                               rsp_rc,
-                              tsk_mgmt->managed_task_tag);
+                              tsk_mgmt->task_tag);
                return FAILED;
        }
 
@@ -987,13 +992,13 @@ static int ibmvscsi_eh_abort_handler(struct scsi_cmnd *cmd)
                spin_unlock_irqrestore(hostdata->host->host_lock, flags);
                printk(KERN_INFO
                       "ibmvscsi: aborted task tag 0x%lx completed\n",
-                      tsk_mgmt->managed_task_tag);
+                      tsk_mgmt->task_tag);
                return SUCCESS;
        }
 
        printk(KERN_INFO
               "ibmvscsi: successfully aborted task tag 0x%lx\n",
-              tsk_mgmt->managed_task_tag);
+              tsk_mgmt->task_tag);
 
        cmd->result = (DID_ABORT << 16);
        list_del(&found_evt->list);
@@ -1040,9 +1045,9 @@ static int ibmvscsi_eh_device_reset_handler(struct scsi_cmnd *cmd)
 
        /* Set up a lun reset SRP command */
        memset(tsk_mgmt, 0x00, sizeof(*tsk_mgmt));
-       tsk_mgmt->type = SRP_TSK_MGMT_TYPE;
+       tsk_mgmt->opcode = SRP_TSK_MGMT;
        tsk_mgmt->lun = ((u64) lun) << 48;
-       tsk_mgmt->task_mgmt_flags = 0x08;       /* LUN RESET */
+       tsk_mgmt->tsk_mgmt_func = SRP_TSK_LUN_RESET;
 
        printk(KERN_INFO "ibmvscsi: resetting device. lun 0x%lx\n",
               tsk_mgmt->lun);
@@ -1059,16 +1064,16 @@ static int ibmvscsi_eh_device_reset_handler(struct scsi_cmnd *cmd)
        wait_for_completion(&evt->comp);
 
        /* make sure we got a good response */
-       if (unlikely(srp_rsp.srp.generic.type != SRP_RSP_TYPE)) {
+       if (unlikely(srp_rsp.srp.rsp.opcode != SRP_RSP)) {
                if (printk_ratelimit())
                        printk(KERN_WARNING 
                               "ibmvscsi: reset bad SRP RSP type %d\n",
-                              srp_rsp.srp.generic.type);
+                              srp_rsp.srp.rsp.opcode);
                return FAILED;
        }
 
-       if (srp_rsp.srp.rsp.rspvalid)
-               rsp_rc = *((int *)srp_rsp.srp.rsp.sense_and_response_data);
+       if (srp_rsp.srp.rsp.flags & SRP_RSP_FLAG_RSPVALID)
+               rsp_rc = *((int *)srp_rsp.srp.rsp.data);
        else
                rsp_rc = srp_rsp.srp.rsp.status;
 
@@ -1076,8 +1081,7 @@ static int ibmvscsi_eh_device_reset_handler(struct scsi_cmnd *cmd)
                if (printk_ratelimit())
                        printk(KERN_WARNING 
                               "ibmvscsi: reset code %d for task tag 0x%lx\n",
-                      rsp_rc,
-                              tsk_mgmt->managed_task_tag);
+                              rsp_rc, tsk_mgmt->task_tag);
                return FAILED;
        }
 
@@ -1179,6 +1183,7 @@ void ibmvscsi_handle_crq(struct viosrp_crq *crq,
                        /* We need to re-setup the interpartition connection */
                        printk(KERN_INFO
                               "ibmvscsi: Re-enabling adapter!\n");
+                       atomic_set(&hostdata->request_limit, -1);
                        purge_requests(hostdata, DID_REQUEUE);
                        if (ibmvscsi_reenable_crq_queue(&hostdata->queue,
                                                        hostdata) == 0)
@@ -1226,7 +1231,7 @@ void ibmvscsi_handle_crq(struct viosrp_crq *crq,
        }
 
        if (crq->format == VIOSRP_SRP_FORMAT)
-               atomic_add(evt_struct->xfer_iu->srp.rsp.request_limit_delta,
+               atomic_add(evt_struct->xfer_iu->srp.rsp.req_lim_delta,
                           &hostdata->request_limit);
 
        if (evt_struct->done)
index 4550d71e474475bec487075c96d1c7aed7df8d88..5c6d93582929813c75bc46ff2686a6f6163c2149 100644 (file)
@@ -68,7 +68,7 @@ struct srp_event_struct {
        void (*cmnd_done) (struct scsi_cmnd *);
        struct completion comp;
        union viosrp_iu *sync_srp;
-       struct memory_descriptor *ext_list;
+       struct srp_direct_buf *ext_list;
        dma_addr_t ext_list_token;
 };
 
index 892e8ed630915584a0ab1f45613375b160b55113..1a9992bdfef85ef944886e4a3f9fb334f34ed64f 100644 (file)
@@ -34,7 +34,6 @@
 #include <linux/dma-mapping.h>
 #include <linux/interrupt.h>
 #include "ibmvscsi.h"
-#include "srp.h"
 
 static char partition_name[97] = "UNKNOWN";
 static unsigned int partition_number = -1;
diff --git a/drivers/scsi/ibmvscsi/srp.h b/drivers/scsi/ibmvscsi/srp.h
deleted file mode 100644 (file)
index 7d8e4c4..0000000
+++ /dev/null
@@ -1,227 +0,0 @@
-/*****************************************************************************/
-/* srp.h -- SCSI RDMA Protocol definitions                                   */
-/*                                                                           */
-/* Written By: Colin Devilbis, IBM Corporation                               */
-/*                                                                           */
-/* Copyright (C) 2003 IBM Corporation                                        */
-/*                                                                           */
-/* This program is free software; you can redistribute it and/or modify      */
-/* it under the terms of the GNU General Public License as published by      */
-/* the Free Software Foundation; either version 2 of the License, or         */
-/* (at your option) any later version.                                       */
-/*                                                                           */
-/* 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., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA */
-/*                                                                           */
-/*                                                                           */
-/* This file contains structures and definitions for the SCSI RDMA Protocol  */
-/* (SRP) as defined in the T10 standard available at www.t10.org.  This      */
-/* file was based on the 16a version of the standard                         */
-/*                                                                           */
-/*****************************************************************************/
-#ifndef SRP_H
-#define SRP_H
-
-#define SRP_VERSION "16.a"
-
-#define PACKED __attribute__((packed))
-
-enum srp_types {
-       SRP_LOGIN_REQ_TYPE = 0x00,
-       SRP_LOGIN_RSP_TYPE = 0xC0,
-       SRP_LOGIN_REJ_TYPE = 0xC2,
-       SRP_I_LOGOUT_TYPE = 0x03,
-       SRP_T_LOGOUT_TYPE = 0x80,
-       SRP_TSK_MGMT_TYPE = 0x01,
-       SRP_CMD_TYPE = 0x02,
-       SRP_RSP_TYPE = 0xC1,
-       SRP_CRED_REQ_TYPE = 0x81,
-       SRP_CRED_RSP_TYPE = 0x41,
-       SRP_AER_REQ_TYPE = 0x82,
-       SRP_AER_RSP_TYPE = 0x42
-};
-
-enum srp_descriptor_formats {
-       SRP_NO_BUFFER = 0x00,
-       SRP_DIRECT_BUFFER = 0x01,
-       SRP_INDIRECT_BUFFER = 0x02
-};
-
-struct memory_descriptor {
-       u64 virtual_address;
-       u32 memory_handle;
-       u32 length;
-};
-
-struct indirect_descriptor {
-       struct memory_descriptor head;
-       u32 total_length;
-       struct memory_descriptor list[1] PACKED;
-};
-
-struct srp_generic {
-       u8 type;
-       u8 reserved1[7];
-       u64 tag;
-};
-
-struct srp_login_req {
-       u8 type;
-       u8 reserved1[7];
-       u64 tag;
-       u32 max_requested_initiator_to_target_iulen;
-       u32 reserved2;
-       u16 required_buffer_formats;
-       u8 reserved3:6;
-       u8 multi_channel_action:2;
-       u8 reserved4;
-       u32 reserved5;
-       u8 initiator_port_identifier[16];
-       u8 target_port_identifier[16];
-};
-
-struct srp_login_rsp {
-       u8 type;
-       u8 reserved1[3];
-       u32 request_limit_delta;
-       u64 tag;
-       u32 max_initiator_to_target_iulen;
-       u32 max_target_to_initiator_iulen;
-       u16 supported_buffer_formats;
-       u8 reserved2:6;
-       u8 multi_channel_result:2;
-       u8 reserved3;
-       u8 reserved4[24];
-};
-
-struct srp_login_rej {
-       u8 type;
-       u8 reserved1[3];
-       u32 reason;
-       u64 tag;
-       u64 reserved2;
-       u16 supported_buffer_formats;
-       u8 reserved3[6];
-};
-
-struct srp_i_logout {
-       u8 type;
-       u8 reserved1[7];
-       u64 tag;
-};
-
-struct srp_t_logout {
-       u8 type;
-       u8 reserved1[3];
-       u32 reason;
-       u64 tag;
-};
-
-struct srp_tsk_mgmt {
-       u8 type;
-       u8 reserved1[7];
-       u64 tag;
-       u32 reserved2;
-       u64 lun PACKED;
-       u8 reserved3;
-       u8 reserved4;
-       u8 task_mgmt_flags;
-       u8 reserved5;
-       u64 managed_task_tag;
-       u64 reserved6;
-};
-
-struct srp_cmd {
-       u8 type;
-       u32 reserved1 PACKED;
-       u8 data_out_format:4;
-       u8 data_in_format:4;
-       u8 data_out_count;
-       u8 data_in_count;
-       u64 tag;
-       u32 reserved2;
-       u64 lun PACKED;
-       u8 reserved3;
-       u8 reserved4:5;
-       u8 task_attribute:3;
-       u8 reserved5;
-       u8 additional_cdb_len;
-       u8 cdb[16];
-       u8 additional_data[0x100 - 0x30];
-};
-
-struct srp_rsp {
-       u8 type;
-       u8 reserved1[3];
-       u32 request_limit_delta;
-       u64 tag;
-       u16 reserved2;
-       u8 reserved3:2;
-       u8 diunder:1;
-       u8 diover:1;
-       u8 dounder:1;
-       u8 doover:1;
-       u8 snsvalid:1;
-       u8 rspvalid:1;
-       u8 status;
-       u32 data_in_residual_count;
-       u32 data_out_residual_count;
-       u32 sense_data_list_length;
-       u32 response_data_list_length;
-       u8 sense_and_response_data[18];
-};
-
-struct srp_cred_req {
-       u8 type;
-       u8 reserved1[3];
-       u32 request_limit_delta;
-       u64 tag;
-};
-
-struct srp_cred_rsp {
-       u8 type;
-       u8 reserved1[7];
-       u64 tag;
-};
-
-struct srp_aer_req {
-       u8 type;
-       u8 reserved1[3];
-       u32 request_limit_delta;
-       u64 tag;
-       u32 reserved2;
-       u64 lun;
-       u32 sense_data_list_length;
-       u32 reserved3;
-       u8 sense_data[20];
-};
-
-struct srp_aer_rsp {
-       u8 type;
-       u8 reserved1[7];
-       u64 tag;
-};
-
-union srp_iu {
-       struct srp_generic generic;
-       struct srp_login_req login_req;
-       struct srp_login_rsp login_rsp;
-       struct srp_login_rej login_rej;
-       struct srp_i_logout i_logout;
-       struct srp_t_logout t_logout;
-       struct srp_tsk_mgmt tsk_mgmt;
-       struct srp_cmd cmd;
-       struct srp_rsp rsp;
-       struct srp_cred_req cred_req;
-       struct srp_cred_rsp cred_rsp;
-       struct srp_aer_req aer_req;
-       struct srp_aer_rsp aer_rsp;
-};
-
-#endif
index 6a6bba8a2f3472430a0794c3032ca2db96d36f47..90f1a61283adaeb527f038a193b4e635776a1057 100644 (file)
 /*****************************************************************************/
 #ifndef VIOSRP_H
 #define VIOSRP_H
-#include "srp.h"
+#include <scsi/srp.h>
+
+#define SRP_VERSION "16.a"
+#define SRP_MAX_IU_LEN 256
+
+union srp_iu {
+       struct srp_login_req login_req;
+       struct srp_login_rsp login_rsp;
+       struct srp_login_rej login_rej;
+       struct srp_i_logout i_logout;
+       struct srp_t_logout t_logout;
+       struct srp_tsk_mgmt tsk_mgmt;
+       struct srp_cmd cmd;
+       struct srp_rsp rsp;
+       u8 reserved[SRP_MAX_IU_LEN];
+};
 
 enum viosrp_crq_formats {
        VIOSRP_SRP_FORMAT = 0x01,
index 5890e5f92d820c6fcf6c18e983636933bc45d313..8b80e59c8c524c39a8d268b84393de0808555130 100644 (file)
@@ -164,29 +164,6 @@ MODULE_PARM_DESC(auto_create, "Auto-create single device RAID 0 arrays when init
 MODULE_LICENSE("GPL");
 MODULE_VERSION(IPR_DRIVER_VERSION);
 
-static const char *ipr_gpdd_dev_end_states[] = {
-       "Command complete",
-       "Terminated by host",
-       "Terminated by device reset",
-       "Terminated by bus reset",
-       "Unknown",
-       "Command not started"
-};
-
-static const char *ipr_gpdd_dev_bus_phases[] = {
-       "Bus free",
-       "Arbitration",
-       "Selection",
-       "Message out",
-       "Command",
-       "Message in",
-       "Data out",
-       "Data in",
-       "Status",
-       "Reselection",
-       "Unknown"
-};
-
 /*  A constant array of IOASCs/URCs/Error Messages */
 static const
 struct ipr_error_table_t ipr_error_table[] = {
@@ -869,8 +846,8 @@ static void ipr_handle_config_change(struct ipr_ioa_cfg *ioa_cfg,
 
        if (hostrcb->hcam.notify_type == IPR_HOST_RCB_NOTIF_TYPE_REM_ENTRY) {
                if (res->sdev) {
-                       res->sdev->hostdata = NULL;
                        res->del_from_ml = 1;
+                       res->cfgte.res_handle = IPR_INVALID_RES_HANDLE;
                        if (ioa_cfg->allow_ml_add_del)
                                schedule_work(&ioa_cfg->work_q);
                } else
@@ -1356,8 +1333,8 @@ static void ipr_handle_log_data(struct ipr_ioa_cfg *ioa_cfg,
                return;
 
        if (ipr_is_device(&hostrcb->hcam.u.error.failing_dev_res_addr)) {
-               ipr_res_err(ioa_cfg, hostrcb->hcam.u.error.failing_dev_res_addr,
-                           "%s\n", ipr_error_table[error_index].error);
+               ipr_ra_err(ioa_cfg, hostrcb->hcam.u.error.failing_dev_res_addr,
+                          "%s\n", ipr_error_table[error_index].error);
        } else {
                dev_err(&ioa_cfg->pdev->dev, "%s\n",
                        ipr_error_table[error_index].error);
@@ -2107,7 +2084,6 @@ restart:
                                did_work = 1;
                                sdev = res->sdev;
                                if (!scsi_device_get(sdev)) {
-                                       res->sdev = NULL;
                                        list_move_tail(&res->queue, &ioa_cfg->free_res_q);
                                        spin_unlock_irqrestore(ioa_cfg->host->host_lock, lock_flags);
                                        scsi_remove_device(sdev);
@@ -2124,6 +2100,7 @@ restart:
                        bus = res->cfgte.res_addr.bus;
                        target = res->cfgte.res_addr.target;
                        lun = res->cfgte.res_addr.lun;
+                       res->add_to_ml = 0;
                        spin_unlock_irqrestore(ioa_cfg->host->host_lock, lock_flags);
                        scsi_add_device(ioa_cfg->host, bus, target, lun);
                        spin_lock_irqsave(ioa_cfg->host->host_lock, lock_flags);
@@ -3214,7 +3191,7 @@ static int ipr_slave_configure(struct scsi_device *sdev)
                        sdev->timeout = IPR_VSET_RW_TIMEOUT;
                        blk_queue_max_sectors(sdev->request_queue, IPR_VSET_MAX_SECTORS);
                }
-               if (IPR_IS_DASD_DEVICE(res->cfgte.std_inq_data))
+               if (ipr_is_vset_device(res) || ipr_is_scsi_disk(res))
                        sdev->allow_restart = 1;
                scsi_adjust_queue_depth(sdev, 0, sdev->host->cmd_per_lun);
        }
@@ -3303,6 +3280,44 @@ static int ipr_eh_host_reset(struct scsi_cmnd * cmd)
        return rc;
 }
 
+/**
+ * ipr_device_reset - Reset the device
+ * @ioa_cfg:   ioa config struct
+ * @res:               resource entry struct
+ *
+ * This function issues a device reset to the affected device.
+ * If the device is a SCSI device, a LUN reset will be sent
+ * to the device first. If that does not work, a target reset
+ * will be sent.
+ *
+ * Return value:
+ *     0 on success / non-zero on failure
+ **/
+static int ipr_device_reset(struct ipr_ioa_cfg *ioa_cfg,
+                           struct ipr_resource_entry *res)
+{
+       struct ipr_cmnd *ipr_cmd;
+       struct ipr_ioarcb *ioarcb;
+       struct ipr_cmd_pkt *cmd_pkt;
+       u32 ioasc;
+
+       ENTER;
+       ipr_cmd = ipr_get_free_ipr_cmnd(ioa_cfg);
+       ioarcb = &ipr_cmd->ioarcb;
+       cmd_pkt = &ioarcb->cmd_pkt;
+
+       ioarcb->res_handle = res->cfgte.res_handle;
+       cmd_pkt->request_type = IPR_RQTYPE_IOACMD;
+       cmd_pkt->cdb[0] = IPR_RESET_DEVICE;
+
+       ipr_send_blocking_cmd(ipr_cmd, ipr_timeout, IPR_DEVICE_RESET_TIMEOUT);
+       ioasc = be32_to_cpu(ipr_cmd->ioasa.ioasc);
+       list_add_tail(&ipr_cmd->queue, &ioa_cfg->free_q);
+
+       LEAVE;
+       return (IPR_IOASC_SENSE_KEY(ioasc) ? -EIO : 0);
+}
+
 /**
  * ipr_eh_dev_reset - Reset the device
  * @scsi_cmd:  scsi command struct
@@ -3319,8 +3334,7 @@ static int __ipr_eh_dev_reset(struct scsi_cmnd * scsi_cmd)
        struct ipr_cmnd *ipr_cmd;
        struct ipr_ioa_cfg *ioa_cfg;
        struct ipr_resource_entry *res;
-       struct ipr_cmd_pkt *cmd_pkt;
-       u32 ioasc;
+       int rc;
 
        ENTER;
        ioa_cfg = (struct ipr_ioa_cfg *) scsi_cmd->device->host->hostdata;
@@ -3347,25 +3361,12 @@ static int __ipr_eh_dev_reset(struct scsi_cmnd * scsi_cmd)
        }
 
        res->resetting_device = 1;
-
-       ipr_cmd = ipr_get_free_ipr_cmnd(ioa_cfg);
-
-       ipr_cmd->ioarcb.res_handle = res->cfgte.res_handle;
-       cmd_pkt = &ipr_cmd->ioarcb.cmd_pkt;
-       cmd_pkt->request_type = IPR_RQTYPE_IOACMD;
-       cmd_pkt->cdb[0] = IPR_RESET_DEVICE;
-
-       ipr_sdev_err(scsi_cmd->device, "Resetting device\n");
-       ipr_send_blocking_cmd(ipr_cmd, ipr_timeout, IPR_DEVICE_RESET_TIMEOUT);
-
-       ioasc = be32_to_cpu(ipr_cmd->ioasa.ioasc);
-
+       scmd_printk(KERN_ERR, scsi_cmd, "Resetting device\n");
+       rc = ipr_device_reset(ioa_cfg, res);
        res->resetting_device = 0;
 
-       list_add_tail(&ipr_cmd->queue, &ioa_cfg->free_q);
-
        LEAVE;
-       return (IPR_IOASC_SENSE_KEY(ioasc) ? FAILED : SUCCESS);
+       return (rc ? FAILED : SUCCESS);
 }
 
 static int ipr_eh_dev_reset(struct scsi_cmnd * cmd)
@@ -3440,7 +3441,7 @@ static void ipr_abort_timeout(struct ipr_cmnd *ipr_cmd)
                return;
        }
 
-       ipr_sdev_err(ipr_cmd->u.sdev, "Abort timed out. Resetting bus\n");
+       sdev_printk(KERN_ERR, ipr_cmd->u.sdev, "Abort timed out. Resetting bus.\n");
        reset_cmd = ipr_get_free_ipr_cmnd(ioa_cfg);
        ipr_cmd->sibling = reset_cmd;
        reset_cmd->sibling = ipr_cmd;
@@ -3504,7 +3505,8 @@ static int ipr_cancel_op(struct scsi_cmnd * scsi_cmd)
        cmd_pkt->cdb[0] = IPR_CANCEL_ALL_REQUESTS;
        ipr_cmd->u.sdev = scsi_cmd->device;
 
-       ipr_sdev_err(scsi_cmd->device, "Aborting command: %02X\n", scsi_cmd->cmnd[0]);
+       scmd_printk(KERN_ERR, scsi_cmd, "Aborting command: %02X\n",
+                   scsi_cmd->cmnd[0]);
        ipr_send_blocking_cmd(ipr_cmd, ipr_abort_timeout, IPR_CANCEL_ALL_TIMEOUT);
        ioasc = be32_to_cpu(ipr_cmd->ioasa.ioasc);
 
@@ -3815,8 +3817,8 @@ static void ipr_erp_done(struct ipr_cmnd *ipr_cmd)
 
        if (IPR_IOASC_SENSE_KEY(ioasc) > 0) {
                scsi_cmd->result |= (DID_ERROR << 16);
-               ipr_sdev_err(scsi_cmd->device,
-                            "Request Sense failed with IOASC: 0x%08X\n", ioasc);
+               scmd_printk(KERN_ERR, scsi_cmd,
+                           "Request Sense failed with IOASC: 0x%08X\n", ioasc);
        } else {
                memcpy(scsi_cmd->sense_buffer, ipr_cmd->sense_buffer,
                       SCSI_SENSE_BUFFERSIZE);
@@ -3938,6 +3940,7 @@ static void ipr_erp_cancel_all(struct ipr_cmnd *ipr_cmd)
  * ipr_dump_ioasa - Dump contents of IOASA
  * @ioa_cfg:   ioa config struct
  * @ipr_cmd:   ipr command struct
+ * @res:               resource entry struct
  *
  * This function is invoked by the interrupt handler when ops
  * fail. It will log the IOASA if appropriate. Only called
@@ -3947,7 +3950,7 @@ static void ipr_erp_cancel_all(struct ipr_cmnd *ipr_cmd)
  *     none
  **/
 static void ipr_dump_ioasa(struct ipr_ioa_cfg *ioa_cfg,
-                          struct ipr_cmnd *ipr_cmd)
+                          struct ipr_cmnd *ipr_cmd, struct ipr_resource_entry *res)
 {
        int i;
        u16 data_len;
@@ -3975,16 +3978,7 @@ static void ipr_dump_ioasa(struct ipr_ioa_cfg *ioa_cfg,
                        return;
        }
 
-       ipr_sdev_err(ipr_cmd->scsi_cmd->device, "%s\n",
-                    ipr_error_table[error_index].error);
-
-       if ((ioasa->u.gpdd.end_state <= ARRAY_SIZE(ipr_gpdd_dev_end_states)) &&
-           (ioasa->u.gpdd.bus_phase <=  ARRAY_SIZE(ipr_gpdd_dev_bus_phases))) {
-               ipr_sdev_err(ipr_cmd->scsi_cmd->device,
-                            "Device End state: %s Phase: %s\n",
-                            ipr_gpdd_dev_end_states[ioasa->u.gpdd.end_state],
-                            ipr_gpdd_dev_bus_phases[ioasa->u.gpdd.bus_phase]);
-       }
+       ipr_res_err(ioa_cfg, res, "%s\n", ipr_error_table[error_index].error);
 
        if (sizeof(struct ipr_ioasa) < be16_to_cpu(ioasa->ret_stat_len))
                data_len = sizeof(struct ipr_ioasa);
@@ -4141,7 +4135,7 @@ static void ipr_erp_start(struct ipr_ioa_cfg *ioa_cfg,
        }
 
        if (ipr_is_gscsi(res))
-               ipr_dump_ioasa(ioa_cfg, ipr_cmd);
+               ipr_dump_ioasa(ioa_cfg, ipr_cmd, res);
        else
                ipr_gen_sense(ipr_cmd);
 
@@ -4540,7 +4534,7 @@ static int ipr_set_supported_devs(struct ipr_cmnd *ipr_cmd)
        ipr_cmd->job_step = ipr_ioa_reset_done;
 
        list_for_each_entry_continue(res, &ioa_cfg->used_res_q, queue) {
-               if (!IPR_IS_DASD_DEVICE(res->cfgte.std_inq_data))
+               if (!ipr_is_scsi_disk(res))
                        continue;
 
                ipr_cmd->u.res = res;
@@ -4980,7 +4974,7 @@ static int ipr_init_res_table(struct ipr_cmnd *ipr_cmd)
        list_for_each_entry_safe(res, temp, &old_res, queue) {
                if (res->sdev) {
                        res->del_from_ml = 1;
-                       res->sdev->hostdata = NULL;
+                       res->cfgte.res_handle = IPR_INVALID_RES_HANDLE;
                        list_move_tail(&res->queue, &ioa_cfg->used_res_q);
                } else {
                        list_move_tail(&res->queue, &ioa_cfg->free_res_q);
index fd360bfe56dda32627d97babf3a1d92d2d000b54..1ad24df69d704d910cadc555e10fe03167cc12a1 100644 (file)
@@ -36,8 +36,8 @@
 /*
  * Literals
  */
-#define IPR_DRIVER_VERSION "2.1.2"
-#define IPR_DRIVER_DATE "(February 8, 2006)"
+#define IPR_DRIVER_VERSION "2.1.3"
+#define IPR_DRIVER_DATE "(March 29, 2006)"
 
 /*
  * IPR_MAX_CMD_PER_LUN: This defines the maximum number of outstanding
 #define IPR_MAX_SCSI_RATE(width) ((320 * 10) / ((width) / 8))
 
 #define IPR_IOA_RES_HANDLE                             0xffffffff
+#define IPR_INVALID_RES_HANDLE                 0
 #define IPR_IOA_RES_ADDR                               0x00ffffff
 
 /*
@@ -1191,30 +1192,17 @@ struct ipr_ucode_image_header {
  */
 #define ipr_err(...) printk(KERN_ERR IPR_NAME ": "__VA_ARGS__)
 #define ipr_info(...) printk(KERN_INFO IPR_NAME ": "__VA_ARGS__)
-#define ipr_crit(...) printk(KERN_CRIT IPR_NAME ": "__VA_ARGS__)
-#define ipr_warn(...) printk(KERN_WARNING IPR_NAME": "__VA_ARGS__)
 #define ipr_dbg(...) IPR_DBG_CMD(printk(KERN_INFO IPR_NAME ": "__VA_ARGS__))
 
-#define ipr_sdev_printk(level, sdev, fmt, args...) \
-       sdev_printk(level, sdev, fmt, ## args)
+#define ipr_ra_printk(level, ioa_cfg, ra, fmt, ...) \
+       printk(level IPR_NAME ": %d:%d:%d:%d: " fmt, (ioa_cfg)->host->host_no, \
+               (ra).bus, (ra).target, (ra).lun, ##__VA_ARGS__)
 
-#define ipr_sdev_err(sdev, fmt, ...) \
-       ipr_sdev_printk(KERN_ERR, sdev, fmt, ##__VA_ARGS__)
-
-#define ipr_sdev_info(sdev, fmt, ...) \
-       ipr_sdev_printk(KERN_INFO, sdev, fmt, ##__VA_ARGS__)
-
-#define ipr_sdev_dbg(sdev, fmt, ...) \
-       IPR_DBG_CMD(ipr_sdev_printk(KERN_INFO, sdev, fmt, ##__VA_ARGS__))
-
-#define ipr_res_printk(level, ioa_cfg, res, fmt, ...) \
-       printk(level IPR_NAME ": %d:%d:%d:%d: " fmt, ioa_cfg->host->host_no, \
-               res.bus, res.target, res.lun, ##__VA_ARGS__)
+#define ipr_ra_err(ioa_cfg, ra, fmt, ...) \
+       ipr_ra_printk(KERN_ERR, ioa_cfg, ra, fmt, ##__VA_ARGS__)
 
 #define ipr_res_err(ioa_cfg, res, fmt, ...) \
-       ipr_res_printk(KERN_ERR, ioa_cfg, res, fmt, ##__VA_ARGS__)
-#define ipr_res_dbg(ioa_cfg, res, fmt, ...) \
-       IPR_DBG_CMD(ipr_res_printk(KERN_INFO, ioa_cfg, res, fmt, ##__VA_ARGS__))
+       ipr_ra_err(ioa_cfg, (res)->cfgte.res_addr, fmt, ##__VA_ARGS__)
 
 #define ipr_phys_res_err(ioa_cfg, res, fmt, ...)                       \
 {                                                                      \
@@ -1303,6 +1291,22 @@ static inline int ipr_is_gscsi(struct ipr_resource_entry *res)
                return 0;
 }
 
+/**
+ * ipr_is_scsi_disk - Determine if a resource is a SCSI disk
+ * @res:       resource entry struct
+ *
+ * Return value:
+ *     1 if SCSI disk / 0 if not SCSI disk
+ **/
+static inline int ipr_is_scsi_disk(struct ipr_resource_entry *res)
+{
+       if (ipr_is_af_dasd_device(res) ||
+           (ipr_is_gscsi(res) && IPR_IS_DASD_DEVICE(res->cfgte.std_inq_data)))
+               return 1;
+       else
+               return 0;
+}
+
 /**
  * ipr_is_naca_model - Determine if a resource is using NACA queueing model
  * @res:       resource entry struct
index e63c1ff1e10256ed2b023341c098978a690ad0b8..bd147207f25d4ea8b216102f260b95911938e0d3 100644 (file)
@@ -4938,7 +4938,6 @@ EXPORT_SYMBOL_GPL(ata_busy_sleep);
 EXPORT_SYMBOL_GPL(ata_port_queue_task);
 EXPORT_SYMBOL_GPL(ata_scsi_ioctl);
 EXPORT_SYMBOL_GPL(ata_scsi_queuecmd);
-EXPORT_SYMBOL_GPL(ata_scsi_error);
 EXPORT_SYMBOL_GPL(ata_scsi_slave_config);
 EXPORT_SYMBOL_GPL(ata_scsi_release);
 EXPORT_SYMBOL_GPL(ata_host_intr);
index 53f5b0d9161c002c141d525c8fe3bae44a51b6af..a0289ec3e283bd532c802c05c5cba0958305828a 100644 (file)
@@ -53,6 +53,7 @@
 typedef unsigned int (*ata_xlat_func_t)(struct ata_queued_cmd *qc, const u8 *scsicmd);
 static struct ata_device *
 ata_scsi_find_dev(struct ata_port *ap, const struct scsi_device *scsidev);
+static void ata_scsi_error(struct Scsi_Host *host);
 enum scsi_eh_timer_return ata_scsi_timed_out(struct scsi_cmnd *cmd);
 
 #define RW_RECOVERY_MPAGE 0x1
@@ -99,6 +100,7 @@ static const u8 def_control_mpage[CONTROL_MPAGE_LEN] = {
  * It just needs the eh_timed_out hook.
  */
 struct scsi_transport_template ata_scsi_transport_template = {
+       .eh_strategy_handler    = ata_scsi_error,
        .eh_timed_out           = ata_scsi_timed_out,
 };
 
@@ -772,12 +774,9 @@ enum scsi_eh_timer_return ata_scsi_timed_out(struct scsi_cmnd *cmd)
  *
  *     LOCKING:
  *     Inherited from SCSI layer (none, can sleep)
- *
- *     RETURNS:
- *     Zero.
  */
 
-int ata_scsi_error(struct Scsi_Host *host)
+static void ata_scsi_error(struct Scsi_Host *host)
 {
        struct ata_port *ap;
        unsigned long flags;
@@ -805,7 +804,6 @@ int ata_scsi_error(struct Scsi_Host *host)
        spin_unlock_irqrestore(&ap->host_set->lock, flags);
 
        DPRINTK("EXIT\n");
-       return 0;
 }
 
 static void ata_eh_scsidone(struct scsi_cmnd *scmd)
index 1c755b14521a9ecf71f228e202f8485983552917..bac8cbae06fe9a99aed6f996c230215881d34d3d 100644 (file)
@@ -60,7 +60,6 @@ extern int ata_cmd_ioctl(struct scsi_device *scsidev, void __user *arg);
 extern struct scsi_transport_template ata_scsi_transport_template;
 
 extern void ata_scsi_scan_host(struct ata_port *ap);
-extern int ata_scsi_error(struct Scsi_Host *host);
 extern unsigned int ata_scsiop_inq_std(struct ata_scsi_args *args, u8 *rbuf,
                               unsigned int buflen);
 
index 3c85c4b66e195c2e3f7c169710cbf1fad945e55f..5cda16cfacb030be42d043761ba16d076e145e3d 100644 (file)
@@ -143,7 +143,6 @@ static struct scsi_host_template adma_ata_sht = {
        .name                   = DRV_NAME,
        .ioctl                  = ata_scsi_ioctl,
        .queuecommand           = ata_scsi_queuecmd,
-       .eh_strategy_handler    = ata_scsi_error,
        .can_queue              = ATA_DEF_QUEUE,
        .this_id                = ATA_SHT_THIS_ID,
        .sg_tablesize           = LIBATA_MAX_PRD,
diff --git a/drivers/scsi/qlogicfc.c b/drivers/scsi/qlogicfc.c
deleted file mode 100644 (file)
index 52b224a..0000000
+++ /dev/null
@@ -1,2228 +0,0 @@
-/*
- * QLogic ISP2x00 SCSI-FCP
- * Written by Erik H. Moe, ehm@cris.com
- * Copyright 1995, Erik H. Moe
- *
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by the
- * Free Software Foundation; either version 2, or (at your option) any
- * later version.
- *
- * 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.
- */
-
-/* Renamed and updated to 1.3.x by Michael Griffith <grif@cs.ucr.edu> */
-
-/* This is a version of the isp1020 driver which was modified by
- * Chris Loveland <cwl@iol.unh.edu> to support the isp2100 and isp2200
- *
- * Big endian support and dynamic DMA mapping added
- * by Jakub Jelinek <jakub@redhat.com>.
- *
- * Conversion to final pci64 DMA interfaces
- * by David S. Miller <davem@redhat.com>.
- */
-
-/*
- * $Date: 1995/09/22 02:23:15 $
- * $Revision: 0.5 $
- *
- * $Log: isp1020.c,v $
- * Revision 0.5  1995/09/22  02:23:15  root
- * do auto request sense
- *
- * Revision 0.4  1995/08/07  04:44:33  root
- * supply firmware with driver.
- * numerous bug fixes/general cleanup of code.
- *
- * Revision 0.3  1995/07/16  16:15:39  root
- * added reset/abort code.
- *
- * Revision 0.2  1995/06/29  03:14:19  root
- * fixed biosparam.
- * added queue protocol.
- *
- * Revision 0.1  1995/06/25  01:55:45  root
- * Initial release.
- *
- */
-
-#include <linux/blkdev.h>
-#include <linux/kernel.h>
-#include <linux/string.h>
-#include <linux/ioport.h>
-#include <linux/sched.h>
-#include <linux/types.h>
-#include <linux/pci.h>
-#include <linux/delay.h>
-#include <linux/unistd.h>
-#include <linux/spinlock.h>
-#include <linux/interrupt.h>
-#include <linux/dma-mapping.h>
-#include <linux/jiffies.h>
-#include <asm/io.h>
-#include <asm/irq.h>
-#include "scsi.h"
-#include <scsi/scsi_host.h>
-
-#define pci64_dma_hi32(a) ((u32) (0xffffffff & (((u64)(a))>>32)))
-#define pci64_dma_lo32(a) ((u32) (0xffffffff & (((u64)(a)))))
-#define pci64_dma_build(hi,lo) \
-       ((dma_addr_t)(((u64)(lo))|(((u64)(hi))<<32)))
-
-/*
- * With the qlogic interface, every queue slot can hold a SCSI
- * command with up to 2 scatter/gather entries.  If we need more
- * than 2 entries, continuation entries can be used that hold
- * another 5 entries each.  Unlike for other drivers, this means
- * that the maximum number of scatter/gather entries we can
- * support at any given time is a function of the number of queue
- * slots available.  That is, host->can_queue and host->sg_tablesize
- * are dynamic and _not_ independent.  This all works fine because
- * requests are queued serially and the scatter/gather limit is
- * determined for each queue request anew.
- */
-
-#define DATASEGS_PER_COMMAND 2
-#define DATASEGS_PER_CONT 5
-
-#define QLOGICFC_REQ_QUEUE_LEN 255     /* must be power of two - 1 */
-#define QLOGICFC_MAX_SG(ql)    (DATASEGS_PER_COMMAND + (((ql) > 0) ? DATASEGS_PER_CONT*((ql) - 1) : 0))
-#define QLOGICFC_CMD_PER_LUN    8
-
-/* Configuration section **************************************************** */
-
-/* Set the following macro to 1 to reload the ISP2x00's firmware.  This is
-   version 1.17.30 of the isp2100's firmware and version 2.00.40 of the 
-   isp2200's firmware. 
-*/
-
-#define USE_NVRAM_DEFAULTS      1
-
-#define ISP2x00_PORTDB          1
-
-/* Set the following to 1 to include fabric support, fabric support is 
- * currently not as well tested as the other aspects of the driver */
-
-#define ISP2x00_FABRIC          1
-
-/*  Macros used for debugging */
-#define DEBUG_ISP2x00          0
-#define DEBUG_ISP2x00_INT      0
-#define DEBUG_ISP2x00_INTR     0
-#define DEBUG_ISP2x00_SETUP    0
-#define DEBUG_ISP2x00_FABRIC    0
-#define TRACE_ISP              0 
-
-
-#define DEFAULT_LOOP_COUNT     1000000000
-
-#define ISP_TIMEOUT (2*HZ)
-/* End Configuration section ************************************************ */
-
-#include <linux/module.h>
-
-#if TRACE_ISP
-
-#define TRACE_BUF_LEN  (32*1024)
-
-struct {
-       u_long next;
-       struct {
-               u_long time;
-               u_int index;
-               u_int addr;
-               u_char *name;
-       } buf[TRACE_BUF_LEN];
-} trace;
-
-#define TRACE(w, i, a)                                         \
-{                                                              \
-       unsigned long flags;                                    \
-                                                               \
-       save_flags(flags);                                      \
-       cli();                                                  \
-       trace.buf[trace.next].name  = (w);                      \
-       trace.buf[trace.next].time  = jiffies;                  \
-       trace.buf[trace.next].index = (i);                      \
-       trace.buf[trace.next].addr  = (long) (a);               \
-       trace.next = (trace.next + 1) & (TRACE_BUF_LEN - 1);    \
-       restore_flags(flags);                                   \
-}
-
-#else
-#define TRACE(w, i, a)
-#endif
-
-#if DEBUG_ISP2x00_FABRIC
-#define DEBUG_FABRIC(x)        x
-#else
-#define DEBUG_FABRIC(x)
-#endif                         /* DEBUG_ISP2x00_FABRIC */
-
-
-#if DEBUG_ISP2x00
-#define ENTER(x)       printk("isp2x00 : entering %s()\n", x);
-#define LEAVE(x)       printk("isp2x00 : leaving %s()\n", x);
-#define DEBUG(x)       x
-#else
-#define ENTER(x)
-#define LEAVE(x)
-#define DEBUG(x)
-#endif                         /* DEBUG_ISP2x00 */
-
-#if DEBUG_ISP2x00_INTR
-#define ENTER_INTR(x)  printk("isp2x00 : entering %s()\n", x);
-#define LEAVE_INTR(x)  printk("isp2x00 : leaving %s()\n", x);
-#define DEBUG_INTR(x)  x
-#else
-#define ENTER_INTR(x)
-#define LEAVE_INTR(x)
-#define DEBUG_INTR(x)
-#endif                         /* DEBUG ISP2x00_INTR */
-
-
-#define ISP2100_REV_ID1               1
-#define ISP2100_REV_ID3        3
-#define ISP2200_REV_ID5        5
-
-/* host configuration and control registers */
-#define HOST_HCCR      0xc0    /* host command and control */
-
-/* pci bus interface registers */
-#define FLASH_BIOS_ADDR        0x00
-#define FLASH_BIOS_DATA        0x02
-#define ISP_CTRL_STATUS        0x06    /* configuration register #1 */
-#define PCI_INTER_CTL  0x08    /* pci interrupt control */
-#define PCI_INTER_STS  0x0a    /* pci interrupt status */
-#define PCI_SEMAPHORE  0x0c    /* pci semaphore */
-#define PCI_NVRAM      0x0e    /* pci nvram interface */
-
-/* mailbox registers */
-#define MBOX0          0x10    /* mailbox 0 */
-#define MBOX1          0x12    /* mailbox 1 */
-#define MBOX2          0x14    /* mailbox 2 */
-#define MBOX3          0x16    /* mailbox 3 */
-#define MBOX4          0x18    /* mailbox 4 */
-#define MBOX5          0x1a    /* mailbox 5 */
-#define MBOX6          0x1c    /* mailbox 6 */
-#define MBOX7          0x1e    /* mailbox 7 */
-
-/* mailbox command complete status codes */
-#define MBOX_COMMAND_COMPLETE          0x4000
-#define INVALID_COMMAND                        0x4001
-#define HOST_INTERFACE_ERROR           0x4002
-#define TEST_FAILED                    0x4003
-#define COMMAND_ERROR                  0x4005
-#define COMMAND_PARAM_ERROR            0x4006
-#define PORT_ID_USED                    0x4007
-#define LOOP_ID_USED                    0x4008
-#define ALL_IDS_USED                    0x4009
-
-/* async event status codes */
-#define RESET_DETECTED                 0x8001
-#define SYSTEM_ERROR                   0x8002
-#define REQUEST_TRANSFER_ERROR         0x8003
-#define RESPONSE_TRANSFER_ERROR                0x8004
-#define REQUEST_QUEUE_WAKEUP           0x8005
-#define LIP_OCCURRED                     0x8010
-#define LOOP_UP                         0x8011
-#define LOOP_DOWN                       0x8012
-#define LIP_RECEIVED                    0x8013
-#define PORT_DB_CHANGED                 0x8014
-#define CHANGE_NOTIFICATION             0x8015
-#define SCSI_COMMAND_COMPLETE           0x8020
-#define POINT_TO_POINT_UP               0x8030
-#define CONNECTION_MODE                 0x8036
-
-struct Entry_header {
-       u_char entry_type;
-       u_char entry_cnt;
-       u_char sys_def_1;
-       u_char flags;
-};
-
-/* entry header type commands */
-#define ENTRY_COMMAND          0x19
-#define ENTRY_CONTINUATION     0x0a
-
-#define ENTRY_STATUS           0x03
-#define ENTRY_MARKER           0x04
-
-
-/* entry header flag definitions */
-#define EFLAG_BUSY             2
-#define EFLAG_BAD_HEADER       4
-#define EFLAG_BAD_PAYLOAD      8
-
-struct dataseg {
-       u_int d_base;
-       u_int d_base_hi;
-       u_int d_count;
-};
-
-struct Command_Entry {
-       struct Entry_header hdr;
-       u_int handle;
-       u_char target_lun;
-       u_char target_id;
-       u_short expanded_lun;
-       u_short control_flags;
-       u_short rsvd2;
-       u_short time_out;
-       u_short segment_cnt;
-       u_char cdb[16];
-       u_int total_byte_cnt;
-       struct dataseg dataseg[DATASEGS_PER_COMMAND];
-};
-
-/* command entry control flag definitions */
-#define CFLAG_NODISC           0x01
-#define CFLAG_HEAD_TAG         0x02
-#define CFLAG_ORDERED_TAG      0x04
-#define CFLAG_SIMPLE_TAG       0x08
-#define CFLAG_TAR_RTN          0x10
-#define CFLAG_READ             0x20
-#define CFLAG_WRITE            0x40
-
-struct Continuation_Entry {
-       struct Entry_header hdr;
-       struct dataseg dataseg[DATASEGS_PER_CONT];
-};
-
-struct Marker_Entry {
-       struct Entry_header hdr;
-       u_int reserved;
-       u_char target_lun;
-       u_char target_id;
-       u_char modifier;
-       u_char expanded_lun;
-       u_char rsvds[52];
-};
-
-/* marker entry modifier definitions */
-#define SYNC_DEVICE    0
-#define SYNC_TARGET    1
-#define SYNC_ALL       2
-
-struct Status_Entry {
-       struct Entry_header hdr;
-       u_int handle;
-       u_short scsi_status;
-       u_short completion_status;
-       u_short state_flags;
-       u_short status_flags;
-       u_short res_info_len;
-       u_short req_sense_len;
-       u_int residual;
-       u_char res_info[8];
-       u_char req_sense_data[32];
-};
-
-/* status entry completion status definitions */
-#define CS_COMPLETE                    0x0000
-#define CS_DMA_ERROR                   0x0002
-#define CS_RESET_OCCURRED              0x0004
-#define CS_ABORTED                     0x0005
-#define CS_TIMEOUT                     0x0006
-#define CS_DATA_OVERRUN                        0x0007
-#define CS_DATA_UNDERRUN               0x0015
-#define CS_QUEUE_FULL                  0x001c
-#define CS_PORT_UNAVAILABLE             0x0028
-#define CS_PORT_LOGGED_OUT              0x0029
-#define CS_PORT_CONFIG_CHANGED         0x002a
-
-/* status entry state flag definitions */
-#define SF_SENT_CDB                    0x0400
-#define SF_TRANSFERRED_DATA            0x0800
-#define SF_GOT_STATUS                  0x1000
-
-/* status entry status flag definitions */
-#define STF_BUS_RESET                  0x0008
-#define STF_DEVICE_RESET               0x0010
-#define STF_ABORTED                    0x0020
-#define STF_TIMEOUT                    0x0040
-
-/* interrupt control commands */
-#define ISP_EN_INT                     0x8000
-#define ISP_EN_RISC                    0x0008
-
-/* host control commands */
-#define HCCR_NOP                       0x0000
-#define HCCR_RESET                     0x1000
-#define HCCR_PAUSE                     0x2000
-#define HCCR_RELEASE                   0x3000
-#define HCCR_SINGLE_STEP               0x4000
-#define HCCR_SET_HOST_INTR             0x5000
-#define HCCR_CLEAR_HOST_INTR           0x6000
-#define HCCR_CLEAR_RISC_INTR           0x7000
-#define HCCR_BP_ENABLE                 0x8000
-#define HCCR_BIOS_DISABLE              0x9000
-#define HCCR_TEST_MODE                 0xf000
-
-#define RISC_BUSY                      0x0004
-
-/* mailbox commands */
-#define MBOX_NO_OP                     0x0000
-#define MBOX_LOAD_RAM                  0x0001
-#define MBOX_EXEC_FIRMWARE             0x0002
-#define MBOX_DUMP_RAM                  0x0003
-#define MBOX_WRITE_RAM_WORD            0x0004
-#define MBOX_READ_RAM_WORD             0x0005
-#define MBOX_MAILBOX_REG_TEST          0x0006
-#define MBOX_VERIFY_CHECKSUM           0x0007
-#define MBOX_ABOUT_FIRMWARE            0x0008
-#define MBOX_LOAD_RISC_RAM              0x0009
-#define MBOX_DUMP_RISC_RAM              0x000a
-#define MBOX_CHECK_FIRMWARE            0x000e
-#define MBOX_INIT_REQ_QUEUE            0x0010
-#define MBOX_INIT_RES_QUEUE            0x0011
-#define MBOX_EXECUTE_IOCB              0x0012
-#define MBOX_WAKE_UP                   0x0013
-#define MBOX_STOP_FIRMWARE             0x0014
-#define MBOX_ABORT_IOCB                        0x0015
-#define MBOX_ABORT_DEVICE              0x0016
-#define MBOX_ABORT_TARGET              0x0017
-#define MBOX_BUS_RESET                 0x0018
-#define MBOX_STOP_QUEUE                        0x0019
-#define MBOX_START_QUEUE               0x001a
-#define MBOX_SINGLE_STEP_QUEUE         0x001b
-#define MBOX_ABORT_QUEUE               0x001c
-#define MBOX_GET_DEV_QUEUE_STATUS      0x001d
-#define MBOX_GET_FIRMWARE_STATUS       0x001f
-#define MBOX_GET_INIT_SCSI_ID          0x0020
-#define MBOX_GET_RETRY_COUNT           0x0022
-#define MBOX_GET_TARGET_PARAMS         0x0028
-#define MBOX_GET_DEV_QUEUE_PARAMS      0x0029
-#define MBOX_SET_RETRY_COUNT           0x0032
-#define MBOX_SET_TARGET_PARAMS         0x0038
-#define MBOX_SET_DEV_QUEUE_PARAMS      0x0039
-#define MBOX_EXECUTE_IOCB64             0x0054
-#define MBOX_INIT_FIRMWARE              0x0060
-#define MBOX_GET_INIT_CB                0x0061
-#define MBOX_INIT_LIP                  0x0062
-#define MBOX_GET_POS_MAP                0x0063
-#define MBOX_GET_PORT_DB                0x0064
-#define MBOX_CLEAR_ACA                  0x0065
-#define MBOX_TARGET_RESET               0x0066
-#define MBOX_CLEAR_TASK_SET             0x0067
-#define MBOX_ABORT_TASK_SET             0x0068
-#define MBOX_GET_FIRMWARE_STATE         0x0069
-#define MBOX_GET_PORT_NAME              0x006a
-#define MBOX_SEND_SNS                   0x006e
-#define MBOX_PORT_LOGIN                 0x006f
-#define MBOX_SEND_CHANGE_REQUEST        0x0070
-#define MBOX_PORT_LOGOUT                0x0071
-
-/*
- *     Firmware if needed (note this is a hack, it belongs in a separate
- *     module.
- */
-#ifdef CONFIG_SCSI_QLOGIC_FC_FIRMWARE
-#include "qlogicfc_asm.c"
-#else
-static unsigned short risc_code_addr01 = 0x1000 ;
-#endif
-
-/* Each element in mbox_param is an 8 bit bitmap where each bit indicates
-   if that mbox should be copied as input.  For example 0x2 would mean
-   only copy mbox1. */
-
-static const u_char mbox_param[] =
-{
-       0x01,                   /* MBOX_NO_OP */
-       0x1f,                   /* MBOX_LOAD_RAM */
-       0x03,                   /* MBOX_EXEC_FIRMWARE */
-       0x1f,                   /* MBOX_DUMP_RAM */
-       0x07,                   /* MBOX_WRITE_RAM_WORD */
-       0x03,                   /* MBOX_READ_RAM_WORD */
-       0xff,                   /* MBOX_MAILBOX_REG_TEST */
-       0x03,                   /* MBOX_VERIFY_CHECKSUM */
-       0x01,                   /* MBOX_ABOUT_FIRMWARE */
-       0xff,                   /* MBOX_LOAD_RISC_RAM */
-       0xff,                   /* MBOX_DUMP_RISC_RAM */
-       0x00,                   /* 0x000b */
-       0x00,                   /* 0x000c */
-       0x00,                   /* 0x000d */
-       0x01,                   /* MBOX_CHECK_FIRMWARE */
-       0x00,                   /* 0x000f */
-       0x1f,                   /* MBOX_INIT_REQ_QUEUE */
-       0x2f,                   /* MBOX_INIT_RES_QUEUE */
-       0x0f,                   /* MBOX_EXECUTE_IOCB */
-       0x03,                   /* MBOX_WAKE_UP */
-       0x01,                   /* MBOX_STOP_FIRMWARE */
-       0x0f,                   /* MBOX_ABORT_IOCB */
-       0x03,                   /* MBOX_ABORT_DEVICE */
-       0x07,                   /* MBOX_ABORT_TARGET */
-       0x03,                   /* MBOX_BUS_RESET */
-       0x03,                   /* MBOX_STOP_QUEUE */
-       0x03,                   /* MBOX_START_QUEUE */
-       0x03,                   /* MBOX_SINGLE_STEP_QUEUE */
-       0x03,                   /* MBOX_ABORT_QUEUE */
-       0x03,                   /* MBOX_GET_DEV_QUEUE_STATUS */
-       0x00,                   /* 0x001e */
-       0x01,                   /* MBOX_GET_FIRMWARE_STATUS */
-       0x01,                   /* MBOX_GET_INIT_SCSI_ID */
-       0x00,                   /* 0x0021 */
-       0x01,                   /* MBOX_GET_RETRY_COUNT */
-       0x00,                   /* 0x0023 */
-       0x00,                   /* 0x0024 */
-       0x00,                   /* 0x0025 */
-       0x00,                   /* 0x0026 */
-       0x00,                   /* 0x0027 */
-       0x03,                   /* MBOX_GET_TARGET_PARAMS */
-       0x03,                   /* MBOX_GET_DEV_QUEUE_PARAMS */
-       0x00,                   /* 0x002a */
-       0x00,                   /* 0x002b */
-       0x00,                   /* 0x002c */
-       0x00,                   /* 0x002d */
-       0x00,                   /* 0x002e */
-       0x00,                   /* 0x002f */
-       0x00,                   /* 0x0030 */
-       0x00,                   /* 0x0031 */
-       0x07,                   /* MBOX_SET_RETRY_COUNT */
-       0x00,                   /* 0x0033 */
-       0x00,                   /* 0x0034 */
-       0x00,                   /* 0x0035 */
-       0x00,                   /* 0x0036 */
-       0x00,                   /* 0x0037 */
-       0x0f,                   /* MBOX_SET_TARGET_PARAMS */
-       0x0f,                   /* MBOX_SET_DEV_QUEUE_PARAMS */
-       0x00,                   /* 0x003a */
-       0x00,                   /* 0x003b */
-       0x00,                   /* 0x003c */
-       0x00,                   /* 0x003d */
-       0x00,                   /* 0x003e */
-       0x00,                   /* 0x003f */
-       0x00,                   /* 0x0040 */
-       0x00,                   /* 0x0041 */
-       0x00,                   /* 0x0042 */
-       0x00,                   /* 0x0043 */
-       0x00,                   /* 0x0044 */
-       0x00,                   /* 0x0045 */
-       0x00,                   /* 0x0046 */
-       0x00,                   /* 0x0047 */
-       0x00,                   /* 0x0048 */
-       0x00,                   /* 0x0049 */
-       0x00,                   /* 0x004a */
-       0x00,                   /* 0x004b */
-       0x00,                   /* 0x004c */
-       0x00,                   /* 0x004d */
-       0x00,                   /* 0x004e */
-       0x00,                   /* 0x004f */
-       0x00,                   /* 0x0050 */
-       0x00,                   /* 0x0051 */
-       0x00,                   /* 0x0052 */
-       0x00,                   /* 0x0053 */
-       0xcf,                   /* MBOX_EXECUTE_IOCB64 */
-       0x00,                   /* 0x0055 */
-       0x00,                   /* 0x0056 */
-       0x00,                   /* 0x0057 */
-       0x00,                   /* 0x0058 */
-       0x00,                   /* 0x0059 */
-       0x00,                   /* 0x005a */
-       0x00,                   /* 0x005b */
-       0x00,                   /* 0x005c */
-       0x00,                   /* 0x005d */
-       0x00,                   /* 0x005e */
-       0x00,                   /* 0x005f */
-       0xff,                   /* MBOX_INIT_FIRMWARE */
-       0xcd,                   /* MBOX_GET_INIT_CB */
-       0x01,                   /* MBOX_INIT_LIP */
-       0xcd,                   /* MBOX_GET_POS_MAP */
-       0xcf,                   /* MBOX_GET_PORT_DB */
-       0x03,                   /* MBOX_CLEAR_ACA */
-       0x03,                   /* MBOX_TARGET_RESET */
-       0x03,                   /* MBOX_CLEAR_TASK_SET */
-       0x03,                   /* MBOX_ABORT_TASK_SET */
-       0x01,                   /* MBOX_GET_FIRMWARE_STATE */
-       0x03,                   /* MBOX_GET_PORT_NAME */
-       0x00,                   /* 0x006b */
-       0x00,                   /* 0x006c */
-       0x00,                   /* 0x006d */
-       0xcf,                   /* MBOX_SEND_SNS */
-       0x0f,                   /* MBOX_PORT_LOGIN */
-       0x03,                   /* MBOX_SEND_CHANGE_REQUEST */
-       0x03,                   /* MBOX_PORT_LOGOUT */
-};
-
-#define MAX_MBOX_COMMAND       (sizeof(mbox_param)/sizeof(u_short))
-
-
-struct id_name_map {
-       u64 wwn;
-       u_char loop_id;
-};
-
-struct sns_cb {
-       u_short len;
-       u_short res1;
-       u_int response_low;
-       u_int response_high;
-       u_short sub_len;
-       u_short res2;
-       u_char data[44];
-};
-
-/* address of instance of this struct is passed to adapter to initialize things
- */
-struct init_cb {
-       u_char version;
-       u_char reseverd1[1];
-       u_short firm_opts;
-       u_short max_frame_len;
-       u_short max_iocb;
-       u_short exec_throttle;
-       u_char retry_cnt;
-       u_char retry_delay;
-       u_short node_name[4];
-       u_short hard_addr;
-       u_char reserved2[10];
-       u_short req_queue_out;
-       u_short res_queue_in;
-       u_short req_queue_len;
-       u_short res_queue_len;
-       u_int req_queue_addr_lo;
-       u_int req_queue_addr_high;
-       u_int res_queue_addr_lo;
-       u_int res_queue_addr_high;
-        /* the rest of this structure only applies to the isp2200 */
-        u_short lun_enables;
-        u_char cmd_resource_cnt;
-        u_char notify_resource_cnt;
-        u_short timeout;
-        u_short reserved3;
-        u_short add_firm_opts;
-        u_char res_accum_timer;
-        u_char irq_delay_timer;
-        u_short special_options;
-        u_short reserved4[13];
-};
-
-/*
- * The result queue can be quite a bit smaller since continuation entries
- * do not show up there:
- */
-#define RES_QUEUE_LEN          ((QLOGICFC_REQ_QUEUE_LEN + 1) / 8 - 1)
-#define QUEUE_ENTRY_LEN                64
-
-#if ISP2x00_FABRIC
-#define QLOGICFC_MAX_ID    0xff
-#else
-#define QLOGICFC_MAX_ID    0x7d
-#endif
-
-#define QLOGICFC_MAX_LUN       128
-#define QLOGICFC_MAX_LOOP_ID   0x7d
-
-/* the following connection options only apply to the 2200.  i have only
- * had success with LOOP_ONLY and P2P_ONLY.
- */
-
-#define LOOP_ONLY              0
-#define P2P_ONLY               1
-#define LOOP_PREFERED          2
-#define P2P_PREFERED           3
-
-#define CONNECTION_PREFERENCE  LOOP_ONLY
-
-/* adapter_state values */
-#define AS_FIRMWARE_DEAD      -1
-#define AS_LOOP_DOWN           0
-#define AS_LOOP_GOOD           1
-#define AS_REDO_FABRIC_PORTDB  2
-#define AS_REDO_LOOP_PORTDB    4
-
-#define RES_SIZE       ((RES_QUEUE_LEN + 1)*QUEUE_ENTRY_LEN)
-#define REQ_SIZE       ((QLOGICFC_REQ_QUEUE_LEN + 1)*QUEUE_ENTRY_LEN)
-
-struct isp2x00_hostdata {
-       u_char revision;
-       struct pci_dev *pci_dev;
-       /* result and request queues (shared with isp2x00): */
-       u_int req_in_ptr;       /* index of next request slot */
-       u_int res_out_ptr;      /* index of next result slot */
-
-       /* this is here so the queues are nicely aligned */
-       long send_marker;       /* do we need to send a marker? */
-
-       char * res;
-       char * req;
-       struct init_cb control_block;
-       int adapter_state;
-       unsigned long int tag_ages[QLOGICFC_MAX_ID + 1];
-       Scsi_Cmnd *handle_ptrs[QLOGICFC_REQ_QUEUE_LEN + 1];
-       unsigned long handle_serials[QLOGICFC_REQ_QUEUE_LEN + 1];
-       struct id_name_map port_db[QLOGICFC_MAX_ID + 1];
-       u_char mbox_done;
-       u64 wwn;
-       u_int port_id;
-       u_char queued;
-       u_char host_id;
-        struct timer_list explore_timer;
-       struct id_name_map tempmap[QLOGICFC_MAX_ID + 1];
-};
-
-
-/* queue length's _must_ be power of two: */
-#define QUEUE_DEPTH(in, out, ql)       ((in - out) & (ql))
-#define REQ_QUEUE_DEPTH(in, out)       QUEUE_DEPTH(in, out,                 \
-                                                   QLOGICFC_REQ_QUEUE_LEN)
-#define RES_QUEUE_DEPTH(in, out)       QUEUE_DEPTH(in, out, RES_QUEUE_LEN)
-
-static void isp2x00_enable_irqs(struct Scsi_Host *);
-static void isp2x00_disable_irqs(struct Scsi_Host *);
-static int isp2x00_init(struct Scsi_Host *);
-static int isp2x00_reset_hardware(struct Scsi_Host *);
-static int isp2x00_mbox_command(struct Scsi_Host *, u_short[]);
-static int isp2x00_return_status(Scsi_Cmnd *, struct Status_Entry *);
-static void isp2x00_intr_handler(int, void *, struct pt_regs *);
-static irqreturn_t do_isp2x00_intr_handler(int, void *, struct pt_regs *);
-static int isp2x00_make_portdb(struct Scsi_Host *);
-
-#if ISP2x00_FABRIC
-static int isp2x00_init_fabric(struct Scsi_Host *, struct id_name_map *, int);
-#endif
-
-#if USE_NVRAM_DEFAULTS
-static int isp2x00_get_nvram_defaults(struct Scsi_Host *, struct init_cb *);
-static u_short isp2x00_read_nvram_word(struct Scsi_Host *, u_short);
-#endif
-
-#if DEBUG_ISP2x00
-static void isp2x00_print_scsi_cmd(Scsi_Cmnd *);
-#endif
-
-#if DEBUG_ISP2x00_INTR
-static void isp2x00_print_status_entry(struct Status_Entry *);
-#endif
-
-static inline void isp2x00_enable_irqs(struct Scsi_Host *host)
-{
-       outw(ISP_EN_INT | ISP_EN_RISC, host->io_port + PCI_INTER_CTL);
-}
-
-
-static inline void isp2x00_disable_irqs(struct Scsi_Host *host)
-{
-       outw(0x0, host->io_port + PCI_INTER_CTL);
-}
-
-
-static int isp2x00_detect(struct scsi_host_template * tmpt)
-{
-       int hosts = 0;
-       unsigned long wait_time;
-       struct Scsi_Host *host = NULL;
-       struct isp2x00_hostdata *hostdata;
-       struct pci_dev *pdev;
-       unsigned short device_ids[2];
-       dma_addr_t busaddr;
-       int i;
-
-
-       ENTER("isp2x00_detect");
-
-               device_ids[0] = PCI_DEVICE_ID_QLOGIC_ISP2100;
-       device_ids[1] = PCI_DEVICE_ID_QLOGIC_ISP2200;
-
-       tmpt->proc_name = "isp2x00";
-
-       for (i=0; i<2; i++){
-               pdev = NULL;
-               while ((pdev = pci_find_device(PCI_VENDOR_ID_QLOGIC, device_ids[i], pdev))) {
-                       if (pci_enable_device(pdev))
-                               continue;
-
-                       /* Try to configure DMA attributes. */
-                       if (pci_set_dma_mask(pdev, DMA_64BIT_MASK) &&
-                           pci_set_dma_mask(pdev, DMA_32BIT_MASK))
-                                       continue;
-
-                       host = scsi_register(tmpt, sizeof(struct isp2x00_hostdata));
-                       if (!host) {
-                               printk("qlogicfc%d : could not register host.\n", hosts);
-                               continue;
-                       }
-                       host->max_id = QLOGICFC_MAX_ID + 1;
-                       host->max_lun = QLOGICFC_MAX_LUN;
-                       hostdata = (struct isp2x00_hostdata *) host->hostdata;
-
-                       memset(hostdata, 0, sizeof(struct isp2x00_hostdata));
-                       hostdata->pci_dev = pdev;
-                       hostdata->res = pci_alloc_consistent(pdev, RES_SIZE + REQ_SIZE, &busaddr);
-
-                       if (!hostdata->res){
-                               printk("qlogicfc%d : could not allocate memory for request and response queue.\n", hosts);
-                               scsi_unregister(host);
-                               continue;
-                       }
-                       hostdata->req = hostdata->res + (RES_QUEUE_LEN + 1)*QUEUE_ENTRY_LEN;
-                       hostdata->queued = 0;
-                       /* set up the control block */
-                       hostdata->control_block.version = 0x1;
-                       hostdata->control_block.firm_opts = cpu_to_le16(0x800e);
-                       hostdata->control_block.max_frame_len = cpu_to_le16(2048);
-                       hostdata->control_block.max_iocb = cpu_to_le16(QLOGICFC_REQ_QUEUE_LEN);
-                       hostdata->control_block.exec_throttle = cpu_to_le16(QLOGICFC_CMD_PER_LUN);
-                       hostdata->control_block.retry_delay = 5;
-                       hostdata->control_block.retry_cnt = 1;
-                       hostdata->control_block.node_name[0] = cpu_to_le16(0x0020);
-                       hostdata->control_block.node_name[1] = cpu_to_le16(0xE000);
-                       hostdata->control_block.node_name[2] = cpu_to_le16(0x008B);
-                       hostdata->control_block.node_name[3] = cpu_to_le16(0x0000);
-                       hostdata->control_block.hard_addr = cpu_to_le16(0x0003);
-                       hostdata->control_block.req_queue_len = cpu_to_le16(QLOGICFC_REQ_QUEUE_LEN + 1);
-                       hostdata->control_block.res_queue_len = cpu_to_le16(RES_QUEUE_LEN + 1);
-                       hostdata->control_block.res_queue_addr_lo = cpu_to_le32(pci64_dma_lo32(busaddr));
-                       hostdata->control_block.res_queue_addr_high = cpu_to_le32(pci64_dma_hi32(busaddr));
-                       hostdata->control_block.req_queue_addr_lo = cpu_to_le32(pci64_dma_lo32(busaddr + RES_SIZE));
-                       hostdata->control_block.req_queue_addr_high = cpu_to_le32(pci64_dma_hi32(busaddr + RES_SIZE));
-
-
-                       hostdata->control_block.add_firm_opts |= cpu_to_le16(CONNECTION_PREFERENCE<<4);
-                       hostdata->adapter_state = AS_LOOP_DOWN;
-                       hostdata->explore_timer.data = 1;
-                       hostdata->host_id = hosts;
-
-                       if (isp2x00_init(host) || isp2x00_reset_hardware(host)) {
-                               pci_free_consistent (pdev, RES_SIZE + REQ_SIZE, hostdata->res, busaddr);
-                               scsi_unregister(host);
-                               continue;
-                       }
-                       host->this_id = 0;
-
-                       if (request_irq(host->irq, do_isp2x00_intr_handler, SA_INTERRUPT | SA_SHIRQ, "qlogicfc", host)) {
-                               printk("qlogicfc%d : interrupt %d already in use\n",
-                                      hostdata->host_id, host->irq);
-                               pci_free_consistent (pdev, RES_SIZE + REQ_SIZE, hostdata->res, busaddr);
-                               scsi_unregister(host);
-                               continue;
-                       }
-                       if (!request_region(host->io_port, 0xff, "qlogicfc")) {
-                               printk("qlogicfc%d : i/o region 0x%lx-0x%lx already "
-                                      "in use\n",
-                                      hostdata->host_id, host->io_port, host->io_port + 0xff);
-                               free_irq(host->irq, host);
-                               pci_free_consistent (pdev, RES_SIZE + REQ_SIZE, hostdata->res, busaddr);
-                               scsi_unregister(host);
-                               continue;
-                       }
-
-                       outw(0x0, host->io_port + PCI_SEMAPHORE);
-                       outw(HCCR_CLEAR_RISC_INTR, host->io_port + HOST_HCCR);
-                       isp2x00_enable_irqs(host);
-                       /* wait for the loop to come up */
-                       for (wait_time = jiffies + 10 * HZ; time_before(jiffies, wait_time) && hostdata->adapter_state == AS_LOOP_DOWN;) {
-                               barrier();
-                               cpu_relax();
-                       }
-                       if (hostdata->adapter_state == AS_LOOP_DOWN) {
-                               printk("qlogicfc%d : link is not up\n", hostdata->host_id);
-                       }
-                       hosts++;
-                       hostdata->explore_timer.data = 0;
-               }
-       }
-
-
-       /* this busy loop should not be needed but the isp2x00 seems to need 
-          some time before recognizing it is attached to a fabric */
-
-#if ISP2x00_FABRIC
-       if (hosts) {
-               for (wait_time = jiffies + 5 * HZ; time_before(jiffies, wait_time);) {
-                       barrier();
-                       cpu_relax();
-               }
-       }
-#endif
-
-       LEAVE("isp2x00_detect");
-
-       return hosts;
-}
-
-
-static int isp2x00_make_portdb(struct Scsi_Host *host)
-{
-
-       short param[8];
-       int i, j;
-       struct isp2x00_hostdata *hostdata;
-
-       isp2x00_disable_irqs(host);
-
-       hostdata = (struct isp2x00_hostdata *) host->hostdata;
-       memset(hostdata->tempmap, 0, sizeof(hostdata->tempmap));
-
-#if ISP2x00_FABRIC
-       for (i = 0x81; i < QLOGICFC_MAX_ID; i++) {
-               param[0] = MBOX_PORT_LOGOUT;
-               param[1] = i << 8;
-               param[2] = 0;
-               param[3] = 0;
-
-               isp2x00_mbox_command(host, param);
-
-               if (param[0] != MBOX_COMMAND_COMPLETE) {
-
-                       DEBUG_FABRIC(printk("qlogicfc%d : logout failed %x  %x\n", hostdata->host_id, i, param[0]));
-               }
-       }
-#endif
-
-
-       param[0] = MBOX_GET_INIT_SCSI_ID;
-
-       isp2x00_mbox_command(host, param);
-
-       if (param[0] == MBOX_COMMAND_COMPLETE) {
-               hostdata->port_id = ((u_int) param[3]) << 16;
-               hostdata->port_id |= param[2];
-               hostdata->tempmap[0].loop_id = param[1];
-               hostdata->tempmap[0].wwn = hostdata->wwn;
-       }
-       else {
-               printk("qlogicfc%d : error getting scsi id.\n", hostdata->host_id);
-       }
-
-        for (i = 0; i <=QLOGICFC_MAX_ID; i++)
-                hostdata->tempmap[i].loop_id = hostdata->tempmap[0].loop_id;
-   
-        for (i = 0, j = 1; i <= QLOGICFC_MAX_LOOP_ID; i++) {
-                param[0] = MBOX_GET_PORT_NAME;
-               param[1] = (i << 8) & 0xff00;
-
-               isp2x00_mbox_command(host, param);
-
-               if (param[0] == MBOX_COMMAND_COMPLETE) {
-                       hostdata->tempmap[j].loop_id = i;
-                       hostdata->tempmap[j].wwn = ((u64) (param[2] & 0xff)) << 56;
-                       hostdata->tempmap[j].wwn |= ((u64) ((param[2] >> 8) & 0xff)) << 48;
-                       hostdata->tempmap[j].wwn |= ((u64) (param[3] & 0xff)) << 40;
-                       hostdata->tempmap[j].wwn |= ((u64) ((param[3] >> 8) & 0xff)) << 32;
-                       hostdata->tempmap[j].wwn |= ((u64) (param[6] & 0xff)) << 24;
-                       hostdata->tempmap[j].wwn |= ((u64) ((param[6] >> 8) & 0xff)) << 16;
-                       hostdata->tempmap[j].wwn |= ((u64) (param[7] & 0xff)) << 8;
-                       hostdata->tempmap[j].wwn |= ((u64) ((param[7] >> 8) & 0xff));
-
-                       j++;
-
-               }
-       }
-
-
-#if ISP2x00_FABRIC
-       isp2x00_init_fabric(host, hostdata->tempmap, j);
-#endif
-
-       for (i = 0; i <= QLOGICFC_MAX_ID; i++) {
-               if (hostdata->tempmap[i].wwn != hostdata->port_db[i].wwn) {
-                       for (j = 0; j <= QLOGICFC_MAX_ID; j++) {
-                               if (hostdata->tempmap[j].wwn == hostdata->port_db[i].wwn) {
-                                       hostdata->port_db[i].loop_id = hostdata->tempmap[j].loop_id;
-                                       break;
-                               }
-                       }
-                       if (j == QLOGICFC_MAX_ID + 1)
-                               hostdata->port_db[i].loop_id = hostdata->tempmap[0].loop_id;
-
-                       for (j = 0; j <= QLOGICFC_MAX_ID; j++) {
-                               if (hostdata->port_db[j].wwn == hostdata->tempmap[i].wwn || !hostdata->port_db[j].wwn) {
-                                       break;
-                               }
-                       }
-                       if (j == QLOGICFC_MAX_ID + 1)
-                               printk("qlogicfc%d : Too many scsi devices, no more room in port map.\n", hostdata->host_id);
-                       if (!hostdata->port_db[j].wwn) {
-                               hostdata->port_db[j].loop_id = hostdata->tempmap[i].loop_id;
-                               hostdata->port_db[j].wwn = hostdata->tempmap[i].wwn;
-                       }
-               } else
-                       hostdata->port_db[i].loop_id = hostdata->tempmap[i].loop_id;
-
-       }
-
-       isp2x00_enable_irqs(host);
-
-       return 0;
-}
-
-
-#if ISP2x00_FABRIC
-
-#define FABRIC_PORT          0x7e
-#define FABRIC_CONTROLLER    0x7f
-#define FABRIC_SNS           0x80
-
-int isp2x00_init_fabric(struct Scsi_Host *host, struct id_name_map *port_db, int cur_scsi_id)
-{
-
-       u_short param[8];
-       u64 wwn;
-       int done = 0;
-       u_short loop_id = 0x81;
-       u_short scsi_id = cur_scsi_id;
-       u_int port_id;
-       struct sns_cb *req;
-       u_char *sns_response;
-       dma_addr_t busaddr;
-       struct isp2x00_hostdata *hostdata;
-
-       hostdata = (struct isp2x00_hostdata *) host->hostdata;
-       
-       DEBUG_FABRIC(printk("qlogicfc%d : Checking for a fabric.\n", hostdata->host_id));
-       param[0] = MBOX_GET_PORT_NAME;
-       param[1] = (u16)FABRIC_PORT << 8;
-
-       isp2x00_mbox_command(host, param);
-
-       if (param[0] != MBOX_COMMAND_COMPLETE) {
-               DEBUG_FABRIC(printk("qlogicfc%d : fabric check result %x\n", hostdata->host_id, param[0]));
-               return 0;
-       }
-       printk("qlogicfc%d : Fabric found.\n", hostdata->host_id);
-
-       req = (struct sns_cb *)pci_alloc_consistent(hostdata->pci_dev, sizeof(*req) + 608, &busaddr);
-       
-       if (!req){
-               printk("qlogicfc%d : Could not allocate DMA resources for fabric initialization\n", hostdata->host_id);
-               return 0;
-       }
-       sns_response = (u_char *)(req + 1);
-
-       if (hostdata->adapter_state & AS_REDO_LOOP_PORTDB){
-               memset(req, 0, sizeof(*req));
-       
-               req->len = cpu_to_le16(8);
-               req->response_low = cpu_to_le32(pci64_dma_lo32(busaddr + sizeof(*req)));
-               req->response_high = cpu_to_le32(pci64_dma_hi32(busaddr + sizeof(*req)));
-               req->sub_len = cpu_to_le16(22);
-               req->data[0] = 0x17;
-               req->data[1] = 0x02;
-               req->data[8] = (u_char) (hostdata->port_id & 0xff);
-               req->data[9] = (u_char) (hostdata->port_id >> 8 & 0xff);
-               req->data[10] = (u_char) (hostdata->port_id >> 16 & 0xff);
-               req->data[13] = 0x01;
-               param[0] = MBOX_SEND_SNS;
-               param[1] = 30;
-               param[2] = pci64_dma_lo32(busaddr) >> 16;
-               param[3] = pci64_dma_lo32(busaddr);
-               param[6] = pci64_dma_hi32(busaddr) >> 16;
-               param[7] = pci64_dma_hi32(busaddr);
-
-               isp2x00_mbox_command(host, param);
-       
-               if (param[0] != MBOX_COMMAND_COMPLETE)
-                       printk("qlogicfc%d : error sending RFC-4\n", hostdata->host_id);
-       }
-
-       port_id = hostdata->port_id;
-       while (!done) {
-               memset(req, 0, sizeof(*req));
-
-               req->len = cpu_to_le16(304);
-               req->response_low = cpu_to_le32(pci64_dma_lo32(busaddr + sizeof(*req)));
-               req->response_high = cpu_to_le32(pci64_dma_hi32(busaddr + sizeof(*req)));
-               req->sub_len = cpu_to_le16(6);
-               req->data[0] = 0x00;
-               req->data[1] = 0x01;
-               req->data[8] = (u_char) (port_id & 0xff);
-               req->data[9] = (u_char) (port_id >> 8 & 0xff);
-               req->data[10] = (u_char) (port_id >> 16 & 0xff);
-
-               param[0] = MBOX_SEND_SNS;
-               param[1] = 14;
-               param[2] = pci64_dma_lo32(busaddr) >> 16;
-               param[3] = pci64_dma_lo32(busaddr);
-               param[6] = pci64_dma_hi32(busaddr) >> 16;
-               param[7] = pci64_dma_hi32(busaddr);
-
-               isp2x00_mbox_command(host, param);
-
-               if (param[0] == MBOX_COMMAND_COMPLETE) {
-                       DEBUG_FABRIC(printk("qlogicfc%d : found node %02x%02x%02x%02x%02x%02x%02x%02x ", hostdata->host_id, sns_response[20], sns_response[21], sns_response[22], sns_response[23], sns_response[24], sns_response[25], sns_response[26], sns_response[27]));
-                       DEBUG_FABRIC(printk("  port id: %02x%02x%02x\n", sns_response[17], sns_response[18], sns_response[19]));
-                       port_id = ((u_int) sns_response[17]) << 16;
-                       port_id |= ((u_int) sns_response[18]) << 8;
-                       port_id |= ((u_int) sns_response[19]);
-                       wwn = ((u64) sns_response[20]) << 56;
-                       wwn |= ((u64) sns_response[21]) << 48;
-                       wwn |= ((u64) sns_response[22]) << 40;
-                       wwn |= ((u64) sns_response[23]) << 32;
-                       wwn |= ((u64) sns_response[24]) << 24;
-                       wwn |= ((u64) sns_response[25]) << 16;
-                       wwn |= ((u64) sns_response[26]) << 8;
-                       wwn |= ((u64) sns_response[27]);
-                       if (hostdata->port_id >> 8 != port_id >> 8) {
-                               DEBUG_FABRIC(printk("qlogicfc%d : adding a fabric port: %x\n", hostdata->host_id, port_id));
-                               param[0] = MBOX_PORT_LOGIN;
-                               param[1] = loop_id << 8;
-                               param[2] = (u_short) (port_id >> 16);
-                               param[3] = (u_short) (port_id);
-
-                               isp2x00_mbox_command(host, param);
-
-                               if (param[0] == MBOX_COMMAND_COMPLETE) {
-                                       port_db[scsi_id].wwn = wwn;
-                                       port_db[scsi_id].loop_id = loop_id;
-                                       loop_id++;
-                                       scsi_id++;
-                               } else {
-                                       printk("qlogicfc%d : Error performing port login %x\n", hostdata->host_id, param[0]);
-                                       DEBUG_FABRIC(printk("qlogicfc%d : loop_id: %x\n", hostdata->host_id, loop_id));
-                                       param[0] = MBOX_PORT_LOGOUT;
-                                       param[1] = loop_id << 8;
-                                       param[2] = 0;
-                                       param[3] = 0;
-
-                                       isp2x00_mbox_command(host, param);
-                                       
-                               }
-
-                       }
-                       if (hostdata->port_id == port_id)
-                               done = 1;
-               } else {
-                       printk("qlogicfc%d : Get All Next failed %x.\n", hostdata->host_id, param[0]);
-                       pci_free_consistent(hostdata->pci_dev, sizeof(*req) + 608, req, busaddr);
-                       return 0;
-               }
-       }
-
-       pci_free_consistent(hostdata->pci_dev, sizeof(*req) + 608, req, busaddr);
-       return 1;
-}
-
-#endif                         /* ISP2x00_FABRIC */
-
-
-static int isp2x00_release(struct Scsi_Host *host)
-{
-       struct isp2x00_hostdata *hostdata;
-       dma_addr_t busaddr;
-
-       ENTER("isp2x00_release");
-
-       hostdata = (struct isp2x00_hostdata *) host->hostdata;
-
-       outw(0x0, host->io_port + PCI_INTER_CTL);
-       free_irq(host->irq, host);
-
-       release_region(host->io_port, 0xff);
-
-       busaddr = pci64_dma_build(le32_to_cpu(hostdata->control_block.res_queue_addr_high),
-                                 le32_to_cpu(hostdata->control_block.res_queue_addr_lo));
-       pci_free_consistent(hostdata->pci_dev, RES_SIZE + REQ_SIZE, hostdata->res, busaddr);
-
-       LEAVE("isp2x00_release");
-
-       return 0;
-}
-
-
-static const char *isp2x00_info(struct Scsi_Host *host)
-{
-       static char buf[80];
-       struct isp2x00_hostdata *hostdata;
-       ENTER("isp2x00_info");
-
-       hostdata = (struct isp2x00_hostdata *) host->hostdata;
-       sprintf(buf,
-               "QLogic ISP%04x SCSI on PCI bus %02x device %02x irq %d base 0x%lx",
-               hostdata->pci_dev->device, hostdata->pci_dev->bus->number, hostdata->pci_dev->devfn, host->irq,
-               host->io_port);
-
-
-       LEAVE("isp2x00_info");
-
-       return buf;
-}
-
-
-/*
- * The middle SCSI layer ensures that queuecommand never gets invoked
- * concurrently with itself or the interrupt handler (though the
- * interrupt handler may call this routine as part of
- * request-completion handling).
- */
-static int isp2x00_queuecommand(Scsi_Cmnd * Cmnd, void (*done) (Scsi_Cmnd *))
-{
-       int i, sg_count, n, num_free;
-       u_int in_ptr, out_ptr;
-       struct dataseg *ds;
-       struct scatterlist *sg;
-       struct Command_Entry *cmd;
-       struct Continuation_Entry *cont;
-       struct Scsi_Host *host;
-       struct isp2x00_hostdata *hostdata;
-
-       ENTER("isp2x00_queuecommand");
-
-       host = Cmnd->device->host;
-       hostdata = (struct isp2x00_hostdata *) host->hostdata;
-       Cmnd->scsi_done = done;
-
-       DEBUG(isp2x00_print_scsi_cmd(Cmnd));
-
-       if (hostdata->adapter_state & AS_REDO_FABRIC_PORTDB || hostdata->adapter_state & AS_REDO_LOOP_PORTDB) {
-               isp2x00_make_portdb(host);
-               hostdata->adapter_state = AS_LOOP_GOOD;
-               printk("qlogicfc%d : Port Database\n", hostdata->host_id);
-               for (i = 0; hostdata->port_db[i].wwn != 0; i++) {
-                       printk("wwn: %08x%08x  scsi_id: %x  loop_id: ", (u_int) (hostdata->port_db[i].wwn >> 32), (u_int) hostdata->port_db[i].wwn, i);
-                       if (hostdata->port_db[i].loop_id != hostdata->port_db[0].loop_id || i == 0)
-                               printk("%x", hostdata->port_db[i].loop_id);
-                       else
-                               printk("Not Available");
-                       printk("\n");
-               }
-       }
-       if (hostdata->adapter_state == AS_FIRMWARE_DEAD) {
-               printk("qlogicfc%d : The firmware is dead, just return.\n", hostdata->host_id);
-               host->max_id = 0;
-               return 0;
-       }
-
-       out_ptr = inw(host->io_port + MBOX4);
-       in_ptr = hostdata->req_in_ptr;
-
-       DEBUG(printk("qlogicfc%d : request queue depth %d\n", hostdata->host_id,
-                    REQ_QUEUE_DEPTH(in_ptr, out_ptr)));
-
-       cmd = (struct Command_Entry *) &hostdata->req[in_ptr*QUEUE_ENTRY_LEN];
-       in_ptr = (in_ptr + 1) & QLOGICFC_REQ_QUEUE_LEN;
-       if (in_ptr == out_ptr) {
-               DEBUG(printk("qlogicfc%d : request queue overflow\n", hostdata->host_id));
-               return 1;
-       }
-       if (hostdata->send_marker) {
-               struct Marker_Entry *marker;
-
-               TRACE("queue marker", in_ptr, 0);
-
-               DEBUG(printk("qlogicfc%d : adding marker entry\n", hostdata->host_id));
-               marker = (struct Marker_Entry *) cmd;
-               memset(marker, 0, sizeof(struct Marker_Entry));
-
-               marker->hdr.entry_type = ENTRY_MARKER;
-               marker->hdr.entry_cnt = 1;
-               marker->modifier = SYNC_ALL;
-
-               hostdata->send_marker = 0;
-
-               if (((in_ptr + 1) & QLOGICFC_REQ_QUEUE_LEN) == out_ptr) {
-                       outw(in_ptr, host->io_port + MBOX4);
-                       hostdata->req_in_ptr = in_ptr;
-                       DEBUG(printk("qlogicfc%d : request queue overflow\n", hostdata->host_id));
-                       return 1;
-               }
-               cmd = (struct Command_Entry *) &hostdata->req[in_ptr*QUEUE_ENTRY_LEN];
-               in_ptr = (in_ptr + 1) & QLOGICFC_REQ_QUEUE_LEN;
-       }
-       TRACE("queue command", in_ptr, Cmnd);
-
-       memset(cmd, 0, sizeof(struct Command_Entry));
-
-       /* find a free handle mapping slot */
-       for (i = in_ptr; i != (in_ptr - 1) && hostdata->handle_ptrs[i]; i = ((i + 1) % (QLOGICFC_REQ_QUEUE_LEN + 1)));
-
-       if (!hostdata->handle_ptrs[i]) {
-               cmd->handle = cpu_to_le32(i);
-               hostdata->handle_ptrs[i] = Cmnd;
-               hostdata->handle_serials[i] = Cmnd->serial_number;
-       } else {
-               printk("qlogicfc%d : no handle slots, this should not happen.\n", hostdata->host_id);
-               printk("hostdata->queued is %x, in_ptr: %x\n", hostdata->queued, in_ptr);
-               for (i = 0; i <= QLOGICFC_REQ_QUEUE_LEN; i++){
-                       if (!hostdata->handle_ptrs[i]){
-                               printk("slot %d has %p\n", i, hostdata->handle_ptrs[i]);
-                       }
-               }
-               return 1;
-       }
-
-       cmd->hdr.entry_type = ENTRY_COMMAND;
-       cmd->hdr.entry_cnt = 1;
-       cmd->target_lun = Cmnd->device->lun;
-       cmd->expanded_lun = cpu_to_le16(Cmnd->device->lun);
-#if ISP2x00_PORTDB
-       cmd->target_id = hostdata->port_db[Cmnd->device->id].loop_id;
-#else
-       cmd->target_id = Cmnd->target;
-#endif
-       cmd->total_byte_cnt = cpu_to_le32(Cmnd->request_bufflen);
-       cmd->time_out = 0;
-       memcpy(cmd->cdb, Cmnd->cmnd, Cmnd->cmd_len);
-
-       if (Cmnd->use_sg) {
-               sg = (struct scatterlist *) Cmnd->request_buffer;
-               sg_count = pci_map_sg(hostdata->pci_dev, sg, Cmnd->use_sg, Cmnd->sc_data_direction);
-               cmd->segment_cnt = cpu_to_le16(sg_count);
-               ds = cmd->dataseg;
-               /* fill in first two sg entries: */
-               n = sg_count;
-               if (n > DATASEGS_PER_COMMAND)
-                       n = DATASEGS_PER_COMMAND;
-
-               for (i = 0; i < n; i++) {
-                       ds[i].d_base = cpu_to_le32(pci64_dma_lo32(sg_dma_address(sg)));
-                       ds[i].d_base_hi = cpu_to_le32(pci64_dma_hi32(sg_dma_address(sg)));
-                       ds[i].d_count = cpu_to_le32(sg_dma_len(sg));
-                       ++sg;
-               }
-               sg_count -= DATASEGS_PER_COMMAND;
-
-               while (sg_count > 0) {
-                       ++cmd->hdr.entry_cnt;
-                       cont = (struct Continuation_Entry *)
-                           &hostdata->req[in_ptr*QUEUE_ENTRY_LEN];
-                       memset(cont, 0, sizeof(struct Continuation_Entry));
-                       in_ptr = (in_ptr + 1) & QLOGICFC_REQ_QUEUE_LEN;
-                       if (in_ptr == out_ptr) {
-                               DEBUG(printk("qlogicfc%d : unexpected request queue overflow\n", hostdata->host_id));
-                               return 1;
-                       }
-                       TRACE("queue continuation", in_ptr, 0);
-                       cont->hdr.entry_type = ENTRY_CONTINUATION;
-                       ds = cont->dataseg;
-                       n = sg_count;
-                       if (n > DATASEGS_PER_CONT)
-                               n = DATASEGS_PER_CONT;
-                       for (i = 0; i < n; ++i) {
-                               ds[i].d_base = cpu_to_le32(pci64_dma_lo32(sg_dma_address(sg)));
-                               ds[i].d_base_hi = cpu_to_le32(pci64_dma_hi32(sg_dma_address(sg)));
-                               ds[i].d_count = cpu_to_le32(sg_dma_len(sg));
-                               ++sg;
-                       }
-                       sg_count -= n;
-               }
-       } else if (Cmnd->request_bufflen && Cmnd->sc_data_direction != PCI_DMA_NONE) {
-               struct page *page = virt_to_page(Cmnd->request_buffer);
-               unsigned long offset = offset_in_page(Cmnd->request_buffer);
-               dma_addr_t busaddr = pci_map_page(hostdata->pci_dev,
-                                                 page, offset,
-                                                 Cmnd->request_bufflen,
-                                                 Cmnd->sc_data_direction);
-               Cmnd->SCp.dma_handle = busaddr;
-
-               cmd->dataseg[0].d_base = cpu_to_le32(pci64_dma_lo32(busaddr));
-               cmd->dataseg[0].d_base_hi = cpu_to_le32(pci64_dma_hi32(busaddr));
-               cmd->dataseg[0].d_count = cpu_to_le32(Cmnd->request_bufflen);
-               cmd->segment_cnt = cpu_to_le16(1);
-       } else {
-               cmd->dataseg[0].d_base = 0;
-               cmd->dataseg[0].d_base_hi = 0;
-               cmd->segment_cnt = cpu_to_le16(1); /* Shouldn't this be 0? */
-       }
-
-       if (Cmnd->sc_data_direction == DMA_TO_DEVICE)
-               cmd->control_flags = cpu_to_le16(CFLAG_WRITE);
-       else 
-               cmd->control_flags = cpu_to_le16(CFLAG_READ);
-
-       if (Cmnd->device->tagged_supported) {
-               if (time_after(jiffies, hostdata->tag_ages[Cmnd->device->id] + (2 * ISP_TIMEOUT))) {
-                       cmd->control_flags |= cpu_to_le16(CFLAG_ORDERED_TAG);
-                       hostdata->tag_ages[Cmnd->device->id] = jiffies;
-               } else
-                       switch (Cmnd->tag) {
-                       case HEAD_OF_QUEUE_TAG:
-                               cmd->control_flags |= cpu_to_le16(CFLAG_HEAD_TAG);
-                               break;
-                       case ORDERED_QUEUE_TAG:
-                               cmd->control_flags |= cpu_to_le16(CFLAG_ORDERED_TAG);
-                               break;
-                       default:
-                               cmd->control_flags |= cpu_to_le16(CFLAG_SIMPLE_TAG);
-                               break;
-               }
-       }
-       /*
-        * TEST_UNIT_READY commands from scsi_scan will fail due to "overlapped
-        * commands attempted" unless we setup at least a simple queue (midlayer 
-        * will embelish this once it can do an INQUIRY command to the device)
-        */
-       else
-               cmd->control_flags |= cpu_to_le16(CFLAG_SIMPLE_TAG);
-       outw(in_ptr, host->io_port + MBOX4);
-       hostdata->req_in_ptr = in_ptr;
-
-       hostdata->queued++;
-
-       num_free = QLOGICFC_REQ_QUEUE_LEN - REQ_QUEUE_DEPTH(in_ptr, out_ptr);
-       num_free = (num_free > 2) ? num_free - 2 : 0;
-       host->can_queue = host->host_busy + num_free;
-       if (host->can_queue > QLOGICFC_REQ_QUEUE_LEN)
-               host->can_queue = QLOGICFC_REQ_QUEUE_LEN;
-       host->sg_tablesize = QLOGICFC_MAX_SG(num_free);
-
-       LEAVE("isp2x00_queuecommand");
-
-       return 0;
-}
-
-
-/* we have received an event, such as a lip or an RSCN, which may mean that
- * our port database is incorrect so the port database must be recreated.
- */
-static void redo_port_db(unsigned long arg)
-{
-
-        struct Scsi_Host * host = (struct Scsi_Host *) arg;
-       struct isp2x00_hostdata * hostdata;
-       unsigned long flags;
-       int i;
-
-       hostdata = (struct isp2x00_hostdata *) host->hostdata;
-       hostdata->explore_timer.data = 0;
-       del_timer(&hostdata->explore_timer);
-
-       spin_lock_irqsave(host->host_lock, flags);
-
-       if (hostdata->adapter_state & AS_REDO_FABRIC_PORTDB || hostdata->adapter_state & AS_REDO_LOOP_PORTDB) {
-               isp2x00_make_portdb(host);
-               printk("qlogicfc%d : Port Database\n", hostdata->host_id);
-               for (i = 0; hostdata->port_db[i].wwn != 0; i++) {
-                       printk("wwn: %08x%08x  scsi_id: %x  loop_id: ", (u_int) (hostdata->port_db[i].wwn >> 32), (u_int) hostdata->port_db[i].wwn, i);
-                       if (hostdata->port_db[i].loop_id != hostdata->port_db[0].loop_id || i == 0)
-                               printk("%x", hostdata->port_db[i].loop_id);
-                       else
-                               printk("Not Available");
-                       printk("\n");
-               }
-               
-               for (i = 0; i < QLOGICFC_REQ_QUEUE_LEN; i++){ 
-                       if (hostdata->handle_ptrs[i] && (hostdata->port_db[hostdata->handle_ptrs[i]->device->id].loop_id > QLOGICFC_MAX_LOOP_ID || hostdata->adapter_state & AS_REDO_LOOP_PORTDB)){
-                                if (hostdata->port_db[hostdata->handle_ptrs[i]->device->id].loop_id != hostdata->port_db[0].loop_id){
-                                       Scsi_Cmnd *Cmnd = hostdata->handle_ptrs[i];
-
-                                        if (Cmnd->use_sg)
-                                                pci_unmap_sg(hostdata->pci_dev,
-                                                             (struct scatterlist *)Cmnd->buffer,
-                                                             Cmnd->use_sg,
-                                                             Cmnd->sc_data_direction);
-                                        else if (Cmnd->request_bufflen &&
-                                                 Cmnd->sc_data_direction != PCI_DMA_NONE) {
-                                                pci_unmap_page(hostdata->pci_dev,
-                                                               Cmnd->SCp.dma_handle,
-                                                               Cmnd->request_bufflen,
-                                                               Cmnd->sc_data_direction);
-                                        }
-
-                                        hostdata->handle_ptrs[i]->result = DID_SOFT_ERROR << 16;
-
-                                        if (hostdata->handle_ptrs[i]->scsi_done){
-                                          (*hostdata->handle_ptrs[i]->scsi_done) (hostdata->handle_ptrs[i]);
-                                        }
-                                        else printk("qlogicfc%d : done is null?\n", hostdata->host_id);
-                                        hostdata->handle_ptrs[i] = NULL;
-                                        hostdata->handle_serials[i] = 0;
-                               }
-                       }
-               }
-               
-               hostdata->adapter_state = AS_LOOP_GOOD;
-       }
-
-       spin_unlock_irqrestore(host->host_lock, flags);
-
-}
-
-#define ASYNC_EVENT_INTERRUPT  0x01
-
-irqreturn_t do_isp2x00_intr_handler(int irq, void *dev_id, struct pt_regs *regs)
-{
-       struct Scsi_Host *host = dev_id;
-       unsigned long flags;
-
-       spin_lock_irqsave(host->host_lock, flags);
-       isp2x00_intr_handler(irq, dev_id, regs);
-       spin_unlock_irqrestore(host->host_lock, flags);
-
-       return IRQ_HANDLED;
-}
-
-void isp2x00_intr_handler(int irq, void *dev_id, struct pt_regs *regs)
-{
-       Scsi_Cmnd *Cmnd;
-       struct Status_Entry *sts;
-       struct Scsi_Host *host = dev_id;
-       struct isp2x00_hostdata *hostdata;
-       u_int in_ptr, out_ptr, handle, num_free;
-       u_short status;
-
-       ENTER_INTR("isp2x00_intr_handler");
-
-       hostdata = (struct isp2x00_hostdata *) host->hostdata;
-
-       DEBUG_INTR(printk("qlogicfc%d : interrupt on line %d\n", hostdata->host_id, irq));
-
-       if (!(inw(host->io_port + PCI_INTER_STS) & 0x08)) {
-               /* spurious interrupts can happen legally */
-               DEBUG_INTR(printk("qlogicfc%d : got spurious interrupt\n", hostdata->host_id));
-               return;
-       }
-       in_ptr = inw(host->io_port + MBOX5);
-       out_ptr = hostdata->res_out_ptr;
-
-       if ((inw(host->io_port + PCI_SEMAPHORE) & ASYNC_EVENT_INTERRUPT)) {
-               status = inw(host->io_port + MBOX0);
-
-               DEBUG_INTR(printk("qlogicfc%d : mbox completion status: %x\n",
-                                 hostdata->host_id, status));
-
-               switch (status) {
-               case LOOP_UP:
-               case POINT_TO_POINT_UP:
-                       printk("qlogicfc%d : Link is Up\n", hostdata->host_id);
-                       hostdata->adapter_state = AS_REDO_FABRIC_PORTDB | AS_REDO_LOOP_PORTDB;
-                       break;
-               case LOOP_DOWN:
-                       printk("qlogicfc%d : Link is Down\n", hostdata->host_id);
-                       hostdata->adapter_state = AS_LOOP_DOWN;
-                       break;
-               case CONNECTION_MODE:
-                       printk("received CONNECTION_MODE irq %x\n", inw(host->io_port + MBOX1));
-                       break;
-               case CHANGE_NOTIFICATION:
-                       printk("qlogicfc%d : RSCN Received\n", hostdata->host_id);
-                       if (hostdata->adapter_state == AS_LOOP_GOOD)
-                               hostdata->adapter_state = AS_REDO_FABRIC_PORTDB;
-                       break;                  
-               case LIP_OCCURRED:
-               case LIP_RECEIVED:
-                       printk("qlogicfc%d : Loop Reinitialized\n", hostdata->host_id);
-                       if (hostdata->adapter_state == AS_LOOP_GOOD)
-                               hostdata->adapter_state = AS_REDO_LOOP_PORTDB;
-                       break;
-               case SYSTEM_ERROR:
-                       printk("qlogicfc%d : The firmware just choked.\n", hostdata->host_id);
-                       hostdata->adapter_state = AS_FIRMWARE_DEAD;
-                       break;
-               case SCSI_COMMAND_COMPLETE:
-                       handle = inw(host->io_port + MBOX1) | (inw(host->io_port + MBOX2) << 16);
-                       Cmnd = hostdata->handle_ptrs[handle];
-                       hostdata->handle_ptrs[handle] = NULL;
-                       hostdata->handle_serials[handle] = 0;
-                       hostdata->queued--;
-                       if (Cmnd != NULL) {
-                               if (Cmnd->use_sg)
-                                       pci_unmap_sg(hostdata->pci_dev,
-                                                    (struct scatterlist *)Cmnd->buffer,
-                                                    Cmnd->use_sg,
-                                                    Cmnd->sc_data_direction);
-                               else if (Cmnd->request_bufflen &&
-                                        Cmnd->sc_data_direction != PCI_DMA_NONE)
-                                       pci_unmap_page(hostdata->pci_dev,
-                                                      Cmnd->SCp.dma_handle,
-                                                      Cmnd->request_bufflen,
-                                                      Cmnd->sc_data_direction);
-                               Cmnd->result = 0x0;
-                               (*Cmnd->scsi_done) (Cmnd);
-                       } else
-                               printk("qlogicfc%d.c : got a null value out of handle_ptrs, this sucks\n", hostdata->host_id);
-                       break;
-               case MBOX_COMMAND_COMPLETE:
-               case INVALID_COMMAND:
-               case HOST_INTERFACE_ERROR:
-               case TEST_FAILED:
-               case COMMAND_ERROR:
-               case COMMAND_PARAM_ERROR:
-               case PORT_ID_USED:
-               case LOOP_ID_USED:
-               case ALL_IDS_USED:
-                       hostdata->mbox_done = 1;
-                       outw(HCCR_CLEAR_RISC_INTR, host->io_port + HOST_HCCR);
-                       return;
-               default:
-                       printk("qlogicfc%d : got an unknown status? %x\n", hostdata->host_id, status);
-               }
-               if ((hostdata->adapter_state & AS_REDO_LOOP_PORTDB || hostdata->adapter_state & AS_REDO_FABRIC_PORTDB) && hostdata->explore_timer.data == 0){
-                        hostdata->explore_timer.function = redo_port_db;
-                       hostdata->explore_timer.data = (unsigned long)host;
-                       hostdata->explore_timer.expires = jiffies + (HZ/4);
-                       init_timer(&hostdata->explore_timer);
-                       add_timer(&hostdata->explore_timer);
-               }
-               outw(0x0, host->io_port + PCI_SEMAPHORE);
-       } else {
-               DEBUG_INTR(printk("qlogicfc%d : response queue update\n", hostdata->host_id));
-               DEBUG_INTR(printk("qlogicfc%d : response queue depth %d\n", hostdata->host_id, RES_QUEUE_DEPTH(in_ptr, out_ptr)));
-
-               while (out_ptr != in_ptr) {
-                       unsigned le_hand;
-                       sts = (struct Status_Entry *) &hostdata->res[out_ptr*QUEUE_ENTRY_LEN];
-                       out_ptr = (out_ptr + 1) & RES_QUEUE_LEN;
-                 
-                       TRACE("done", out_ptr, Cmnd);
-                       DEBUG_INTR(isp2x00_print_status_entry(sts));
-                       le_hand = le32_to_cpu(sts->handle);
-                       if (sts->hdr.entry_type == ENTRY_STATUS && (Cmnd = hostdata->handle_ptrs[le_hand])) {
-                               Cmnd->result = isp2x00_return_status(Cmnd, sts);
-                               hostdata->queued--;
-
-                               if (Cmnd->use_sg)
-                                       pci_unmap_sg(hostdata->pci_dev,
-                                                    (struct scatterlist *)Cmnd->buffer, Cmnd->use_sg,
-                                                    Cmnd->sc_data_direction);
-                               else if (Cmnd->request_bufflen && Cmnd->sc_data_direction != PCI_DMA_NONE)
-                                       pci_unmap_page(hostdata->pci_dev,
-                                                      Cmnd->SCp.dma_handle,
-                                                      Cmnd->request_bufflen,
-                                                      Cmnd->sc_data_direction);
-
-                               /* 
-                                * if any of the following are true we do not
-                                * call scsi_done.  if the status is CS_ABORTED
-                                * we don't have to call done because the upper
-                                * level should already know its aborted.
-                                */
-                               if (hostdata->handle_serials[le_hand] != Cmnd->serial_number 
-                                   || le16_to_cpu(sts->completion_status) == CS_ABORTED){
-                                       hostdata->handle_serials[le_hand] = 0;
-                                       hostdata->handle_ptrs[le_hand] = NULL;
-                                       outw(out_ptr, host->io_port + MBOX5);
-                                       continue;
-                               }
-                               /*
-                                * if we get back an error indicating the port
-                                * is not there or if the link is down and 
-                                * this is a device that used to be there 
-                                * allow the command to timeout.
-                                * the device may well be back in a couple of
-                                * seconds.
-                                */
-                               if ((hostdata->adapter_state == AS_LOOP_DOWN || sts->completion_status == cpu_to_le16(CS_PORT_UNAVAILABLE) || sts->completion_status == cpu_to_le16(CS_PORT_LOGGED_OUT) || sts->completion_status == cpu_to_le16(CS_PORT_CONFIG_CHANGED)) && hostdata->port_db[Cmnd->device->id].wwn){
-                                       outw(out_ptr, host->io_port + MBOX5);
-                                       continue;
-                               }
-                       } else {
-                               outw(out_ptr, host->io_port + MBOX5);
-                               continue;
-                       }
-
-                       hostdata->handle_ptrs[le_hand] = NULL;
-
-                       if (sts->completion_status == cpu_to_le16(CS_RESET_OCCURRED)
-                           || (sts->status_flags & cpu_to_le16(STF_BUS_RESET)))
-                               hostdata->send_marker = 1;
-
-                       if (le16_to_cpu(sts->scsi_status) & 0x0200)
-                               memcpy(Cmnd->sense_buffer, sts->req_sense_data,
-                                      sizeof(Cmnd->sense_buffer));
-
-                       outw(out_ptr, host->io_port + MBOX5);
-
-                       if (Cmnd->scsi_done != NULL) {
-                               (*Cmnd->scsi_done) (Cmnd);
-                       } else
-                               printk("qlogicfc%d : Ouch, scsi done is NULL\n", hostdata->host_id);
-               }
-               hostdata->res_out_ptr = out_ptr;
-       }
-
-
-       out_ptr = inw(host->io_port + MBOX4);
-       in_ptr = hostdata->req_in_ptr;
-
-       num_free = QLOGICFC_REQ_QUEUE_LEN - REQ_QUEUE_DEPTH(in_ptr, out_ptr);
-       num_free = (num_free > 2) ? num_free - 2 : 0;
-       host->can_queue = host->host_busy + num_free;
-       if (host->can_queue > QLOGICFC_REQ_QUEUE_LEN)
-               host->can_queue = QLOGICFC_REQ_QUEUE_LEN;
-       host->sg_tablesize = QLOGICFC_MAX_SG(num_free);
-
-       outw(HCCR_CLEAR_RISC_INTR, host->io_port + HOST_HCCR);
-       LEAVE_INTR("isp2x00_intr_handler");
-}
-
-
-static int isp2x00_return_status(Scsi_Cmnd *Cmnd, struct Status_Entry *sts)
-{
-       int host_status = DID_ERROR;
-#if DEBUG_ISP2x00_INTR
-       static char *reason[] =
-       {
-               "DID_OK",
-               "DID_NO_CONNECT",
-               "DID_BUS_BUSY",
-               "DID_TIME_OUT",
-               "DID_BAD_TARGET",
-               "DID_ABORT",
-               "DID_PARITY",
-               "DID_ERROR",
-               "DID_RESET",
-               "DID_BAD_INTR"
-       };
-#endif                         /* DEBUG_ISP2x00_INTR */
-
-       ENTER("isp2x00_return_status");
-
-       DEBUG(printk("qlogicfc : completion status = 0x%04x\n",
-                    le16_to_cpu(sts->completion_status)));
-
-       switch (le16_to_cpu(sts->completion_status)) {
-       case CS_COMPLETE:
-               host_status = DID_OK;
-               break;
-       case CS_DMA_ERROR:
-               host_status = DID_ERROR;
-               break;
-       case CS_RESET_OCCURRED:
-               host_status = DID_RESET;
-               break;
-       case CS_ABORTED:
-               host_status = DID_ABORT;
-               break;
-       case CS_TIMEOUT:
-               host_status = DID_TIME_OUT;
-               break;
-       case CS_DATA_OVERRUN:
-               host_status = DID_ERROR;
-               break;
-       case CS_DATA_UNDERRUN:
-               if (Cmnd->underflow <= (Cmnd->request_bufflen - le32_to_cpu(sts->residual)))
-                       host_status = DID_OK;
-               else
-                       host_status = DID_ERROR;
-               break;
-       case CS_PORT_UNAVAILABLE:
-       case CS_PORT_LOGGED_OUT:
-       case CS_PORT_CONFIG_CHANGED:
-               host_status = DID_BAD_TARGET;
-               break;
-       case CS_QUEUE_FULL:
-               host_status = DID_ERROR;
-               break;
-       default:
-               printk("qlogicfc : unknown completion status 0x%04x\n",
-                      le16_to_cpu(sts->completion_status));
-               host_status = DID_ERROR;
-               break;
-       }
-
-       DEBUG_INTR(printk("qlogicfc : host status (%s) scsi status %x\n",
-                         reason[host_status], le16_to_cpu(sts->scsi_status)));
-
-       LEAVE("isp2x00_return_status");
-
-       return (le16_to_cpu(sts->scsi_status) & STATUS_MASK) | (host_status << 16);
-}
-
-
-static int isp2x00_abort(Scsi_Cmnd * Cmnd)
-{
-       u_short param[8];
-       int i;
-       struct Scsi_Host *host;
-       struct isp2x00_hostdata *hostdata;
-       int return_status = SUCCESS;
-
-       ENTER("isp2x00_abort");
-
-       host = Cmnd->device->host;
-       hostdata = (struct isp2x00_hostdata *) host->hostdata;
-
-       for (i = 0; i < QLOGICFC_REQ_QUEUE_LEN; i++)
-               if (hostdata->handle_ptrs[i] == Cmnd)
-                       break;
-
-       if (i == QLOGICFC_REQ_QUEUE_LEN){
-               return SUCCESS;
-       }
-
-       isp2x00_disable_irqs(host);
-
-       param[0] = MBOX_ABORT_IOCB;
-#if ISP2x00_PORTDB
-       param[1] = (((u_short) hostdata->port_db[Cmnd->device->id].loop_id) << 8) | Cmnd->device->lun;
-#else
-       param[1] = (((u_short) Cmnd->target) << 8) | Cmnd->lun;
-#endif
-       param[2] = i & 0xffff;
-       param[3] = i >> 16;
-
-       isp2x00_mbox_command(host, param);
-
-       if (param[0] != MBOX_COMMAND_COMPLETE) {
-               printk("qlogicfc%d : scsi abort failure: %x\n", hostdata->host_id, param[0]);
-               if (param[0] == 0x4005)
-                       Cmnd->result = DID_ERROR << 16;
-               if (param[0] == 0x4006)
-                       Cmnd->result = DID_BAD_TARGET << 16;
-               return_status = FAILED;
-       }
-
-       if (return_status != SUCCESS){
-               param[0] = MBOX_GET_FIRMWARE_STATE;
-               isp2x00_mbox_command(host, param);
-               printk("qlogicfc%d : abort failed\n", hostdata->host_id);
-               printk("qlogicfc%d : firmware status is %x %x\n", hostdata->host_id, param[0], param[1]);
-       }
-
-       isp2x00_enable_irqs(host);
-
-       LEAVE("isp2x00_abort");
-
-       return return_status;
-}
-
-
-static int isp2x00_biosparam(struct scsi_device *sdev, struct block_device *n,
-               sector_t capacity, int ip[])
-{
-       int size = capacity;
-
-       ENTER("isp2x00_biosparam");
-
-       ip[0] = 64;
-       ip[1] = 32;
-       ip[2] = size >> 11;
-       if (ip[2] > 1024) {
-               ip[0] = 255;
-               ip[1] = 63;
-               ip[2] = size / (ip[0] * ip[1]);
-       }
-       LEAVE("isp2x00_biosparam");
-
-       return 0;
-}
-
-static int isp2x00_reset_hardware(struct Scsi_Host *host)
-{
-       u_short param[8];
-       struct isp2x00_hostdata *hostdata;
-       int loop_count;
-       dma_addr_t busaddr;
-
-       ENTER("isp2x00_reset_hardware");
-
-       hostdata = (struct isp2x00_hostdata *) host->hostdata;
-
-       /*
-        *      This cannot be right - PCI writes are posted
-        *      (apparently this is hardware design flaw not software ?)
-        */
-        
-       outw(0x01, host->io_port + ISP_CTRL_STATUS);
-       udelay(100);
-       outw(HCCR_RESET, host->io_port + HOST_HCCR);
-       udelay(100);
-       outw(HCCR_RELEASE, host->io_port + HOST_HCCR);
-       outw(HCCR_BIOS_DISABLE, host->io_port + HOST_HCCR);
-
-       loop_count = DEFAULT_LOOP_COUNT;
-       while (--loop_count && inw(host->io_port + HOST_HCCR) == RISC_BUSY) {
-               barrier();
-               cpu_relax();
-       }
-       if (!loop_count)
-               printk("qlogicfc%d : reset_hardware loop timeout\n", hostdata->host_id);
-
-
-
-#if DEBUG_ISP2x00
-       printk("qlogicfc%d : mbox 0 0x%04x \n", hostdata->host_id,  inw(host->io_port + MBOX0));
-       printk("qlogicfc%d : mbox 1 0x%04x \n", hostdata->host_id,  inw(host->io_port + MBOX1));
-       printk("qlogicfc%d : mbox 2 0x%04x \n", hostdata->host_id,  inw(host->io_port + MBOX2));
-       printk("qlogicfc%d : mbox 3 0x%04x \n", hostdata->host_id,  inw(host->io_port + MBOX3));
-       printk("qlogicfc%d : mbox 4 0x%04x \n", hostdata->host_id,  inw(host->io_port + MBOX4));
-       printk("qlogicfc%d : mbox 5 0x%04x \n", hostdata->host_id,  inw(host->io_port + MBOX5));
-       printk("qlogicfc%d : mbox 6 0x%04x \n", hostdata->host_id,  inw(host->io_port + MBOX6));
-       printk("qlogicfc%d : mbox 7 0x%04x \n", hostdata->host_id,  inw(host->io_port + MBOX7));
-#endif                         /* DEBUG_ISP2x00 */
-
-       DEBUG(printk("qlogicfc%d : verifying checksum\n", hostdata->host_id));
-
-#if defined(CONFIG_SCSI_QLOGIC_FC_FIRMWARE)
-       {
-               int i;
-               unsigned short * risc_code = NULL;
-               unsigned short risc_code_len = 0;
-               if (hostdata->pci_dev->device == PCI_DEVICE_ID_QLOGIC_ISP2100){
-                       risc_code = risc_code2100;
-                       risc_code_len = risc_code_length2100;
-               }
-               else if (hostdata->pci_dev->device == PCI_DEVICE_ID_QLOGIC_ISP2200){
-                       risc_code = risc_code2200;
-                       risc_code_len = risc_code_length2200;
-               }
-
-               for (i = 0; i < risc_code_len; i++) {
-                       param[0] = MBOX_WRITE_RAM_WORD;
-                       param[1] = risc_code_addr01 + i;
-                       param[2] = risc_code[i];
-
-                       isp2x00_mbox_command(host, param);
-
-                       if (param[0] != MBOX_COMMAND_COMPLETE) {
-                               printk("qlogicfc%d : firmware load failure\n", hostdata->host_id);
-                               return 1;
-                       }
-               }
-       }
-#endif                         /* RELOAD_FIRMWARE */
-
-       param[0] = MBOX_VERIFY_CHECKSUM;
-       param[1] = risc_code_addr01;
-
-       isp2x00_mbox_command(host, param);
-
-       if (param[0] != MBOX_COMMAND_COMPLETE) {
-               printk("qlogicfc%d : ram checksum failure\n", hostdata->host_id);
-               return 1;
-       }
-       DEBUG(printk("qlogicfc%d : executing firmware\n", hostdata->host_id));
-
-       param[0] = MBOX_EXEC_FIRMWARE;
-       param[1] = risc_code_addr01;
-
-       isp2x00_mbox_command(host, param);
-
-       param[0] = MBOX_ABOUT_FIRMWARE;
-
-       isp2x00_mbox_command(host, param);
-
-       if (param[0] != MBOX_COMMAND_COMPLETE) {
-               printk("qlogicfc%d : about firmware failure\n", hostdata->host_id);
-               return 1;
-       }
-       DEBUG(printk("qlogicfc%d : firmware major revision %d\n", hostdata->host_id,  param[1]));
-       DEBUG(printk("qlogicfc%d : firmware minor revision %d\n", hostdata->host_id,  param[2]));
-
-#ifdef USE_NVRAM_DEFAULTS
-
-       if (isp2x00_get_nvram_defaults(host, &hostdata->control_block) != 0) {
-               printk("qlogicfc%d : Could not read from NVRAM\n", hostdata->host_id);
-       }
-#endif
-
-       hostdata->wwn = (u64) (cpu_to_le16(hostdata->control_block.node_name[0])) << 56;
-       hostdata->wwn |= (u64) (cpu_to_le16(hostdata->control_block.node_name[0]) & 0xff00) << 48;
-       hostdata->wwn |= (u64) (cpu_to_le16(hostdata->control_block.node_name[1]) & 0xff00) << 24;
-       hostdata->wwn |= (u64) (cpu_to_le16(hostdata->control_block.node_name[1]) & 0x00ff) << 48;
-       hostdata->wwn |= (u64) (cpu_to_le16(hostdata->control_block.node_name[2]) & 0x00ff) << 24;
-       hostdata->wwn |= (u64) (cpu_to_le16(hostdata->control_block.node_name[2]) & 0xff00) << 8;
-       hostdata->wwn |= (u64) (cpu_to_le16(hostdata->control_block.node_name[3]) & 0x00ff) << 8;
-       hostdata->wwn |= (u64) (cpu_to_le16(hostdata->control_block.node_name[3]) & 0xff00) >> 8;
-
-       /* FIXME: If the DMA transfer goes one way only, this should use
-        *        PCI_DMA_TODEVICE and below as well.
-        */
-       busaddr = pci_map_page(hostdata->pci_dev,
-                              virt_to_page(&hostdata->control_block),
-                              offset_in_page(&hostdata->control_block),
-                              sizeof(hostdata->control_block),
-                              PCI_DMA_BIDIRECTIONAL);
-
-       param[0] = MBOX_INIT_FIRMWARE;
-       param[2] = (u_short) (pci64_dma_lo32(busaddr) >> 16);
-       param[3] = (u_short) (pci64_dma_lo32(busaddr) & 0xffff);
-       param[4] = 0;
-       param[5] = 0;
-       param[6] = (u_short) (pci64_dma_hi32(busaddr) >> 16);
-       param[7] = (u_short) (pci64_dma_hi32(busaddr) & 0xffff);
-       isp2x00_mbox_command(host, param);
-       if (param[0] != MBOX_COMMAND_COMPLETE) {
-               printk("qlogicfc%d.c: Ouch 0x%04x\n", hostdata->host_id,  param[0]);
-               pci_unmap_page(hostdata->pci_dev, busaddr,
-                              sizeof(hostdata->control_block),
-                              PCI_DMA_BIDIRECTIONAL);
-               return 1;
-       }
-       param[0] = MBOX_GET_FIRMWARE_STATE;
-       isp2x00_mbox_command(host, param);
-       if (param[0] != MBOX_COMMAND_COMPLETE) {
-               printk("qlogicfc%d.c: 0x%04x\n", hostdata->host_id,  param[0]);
-               pci_unmap_page(hostdata->pci_dev, busaddr,
-                              sizeof(hostdata->control_block),
-                              PCI_DMA_BIDIRECTIONAL);
-               return 1;
-       }
-
-       pci_unmap_page(hostdata->pci_dev, busaddr,
-                      sizeof(hostdata->control_block),
-                      PCI_DMA_BIDIRECTIONAL);
-       LEAVE("isp2x00_reset_hardware");
-
-       return 0;
-}
-
-#ifdef USE_NVRAM_DEFAULTS
-
-static int isp2x00_get_nvram_defaults(struct Scsi_Host *host, struct init_cb *control_block)
-{
-
-       u_short value;
-       if (isp2x00_read_nvram_word(host, 0) != 0x5349)
-               return 1;
-
-       value = isp2x00_read_nvram_word(host, 8);
-       control_block->node_name[0] = cpu_to_le16(isp2x00_read_nvram_word(host, 9));
-       control_block->node_name[1] = cpu_to_le16(isp2x00_read_nvram_word(host, 10));
-       control_block->node_name[2] = cpu_to_le16(isp2x00_read_nvram_word(host, 11));
-       control_block->node_name[3] = cpu_to_le16(isp2x00_read_nvram_word(host, 12));
-       control_block->hard_addr = cpu_to_le16(isp2x00_read_nvram_word(host, 13));
-
-       return 0;
-
-}
-
-#endif
-
-static int isp2x00_init(struct Scsi_Host *sh)
-{
-       u_long io_base;
-       struct isp2x00_hostdata *hostdata;
-       u_char revision;
-       u_int irq;
-       u_short command;
-       struct pci_dev *pdev;
-
-
-       ENTER("isp2x00_init");
-
-       hostdata = (struct isp2x00_hostdata *) sh->hostdata;
-       pdev = hostdata->pci_dev;
-
-       if (pci_read_config_word(pdev, PCI_COMMAND, &command)
-         || pci_read_config_byte(pdev, PCI_CLASS_REVISION, &revision)) {
-               printk("qlogicfc%d : error reading PCI configuration\n", hostdata->host_id);
-               return 1;
-       }
-       io_base = pci_resource_start(pdev, 0);
-       irq = pdev->irq;
-
-
-       if (pdev->vendor != PCI_VENDOR_ID_QLOGIC) {
-               printk("qlogicfc%d : 0x%04x is not QLogic vendor ID\n", hostdata->host_id, 
-                      pdev->vendor);
-               return 1;
-       }
-       if (pdev->device != PCI_DEVICE_ID_QLOGIC_ISP2100 && pdev->device != PCI_DEVICE_ID_QLOGIC_ISP2200) {
-               printk("qlogicfc%d : 0x%04x does not match ISP2100 or ISP2200 device id\n", hostdata->host_id, 
-                      pdev->device);
-               return 1;
-       }
-       if (!(command & PCI_COMMAND_IO) ||
-           !(pdev->resource[0].flags & IORESOURCE_IO)) {
-               printk("qlogicfc%d : i/o mapping is disabled\n", hostdata->host_id);
-               return 1;
-       }
-
-       pci_set_master(pdev);
-       if (revision != ISP2100_REV_ID1 && revision != ISP2100_REV_ID3 && revision != ISP2200_REV_ID5)
-               printk("qlogicfc%d : new isp2x00 revision ID (%d)\n", hostdata->host_id,  revision);
-
-
-       hostdata->revision = revision;
-
-       sh->irq = irq;
-       sh->io_port = io_base;
-
-       LEAVE("isp2x00_init");
-
-       return 0;
-}
-
-#if USE_NVRAM_DEFAULTS
-
-#define NVRAM_DELAY() udelay(10)       /* 10 microsecond delay */
-
-
-u_short isp2x00_read_nvram_word(struct Scsi_Host * host, u_short byte)
-{
-       int i;
-       u_short value, output, input;
-
-       outw(0x2, host->io_port + PCI_NVRAM);
-       NVRAM_DELAY();
-       outw(0x3, host->io_port + PCI_NVRAM);
-       NVRAM_DELAY();
-
-       byte &= 0xff;
-       byte |= 0x0600;
-       for (i = 10; i >= 0; i--) {
-               output = ((byte >> i) & 0x1) ? 0x4 : 0x0;
-               outw(output | 0x2, host->io_port + PCI_NVRAM);
-               NVRAM_DELAY();
-               outw(output | 0x3, host->io_port + PCI_NVRAM);
-               NVRAM_DELAY();
-               outw(output | 0x2, host->io_port + PCI_NVRAM);
-               NVRAM_DELAY();
-       }
-
-       for (i = 0xf, value = 0; i >= 0; i--) {
-               value <<= 1;
-               outw(0x3, host->io_port + PCI_NVRAM);
-               NVRAM_DELAY();
-               input = inw(host->io_port + PCI_NVRAM);
-               NVRAM_DELAY();
-               outw(0x2, host->io_port + PCI_NVRAM);
-               NVRAM_DELAY();
-               if (input & 0x8)
-                       value |= 1;
-       }
-
-       outw(0x0, host->io_port + PCI_NVRAM);
-       NVRAM_DELAY();
-
-       return value;
-}
-
-
-#endif                         /* USE_NVRAM_DEFAULTS */
-
-
-
-/*
- * currently, this is only called during initialization or abort/reset,
- * at which times interrupts are disabled, so polling is OK, I guess...
- */
-static int isp2x00_mbox_command(struct Scsi_Host *host, u_short param[])
-{
-       int loop_count;
-       struct isp2x00_hostdata *hostdata = (struct isp2x00_hostdata *) host->hostdata;
-
-       if (mbox_param[param[0]] == 0 || hostdata->adapter_state == AS_FIRMWARE_DEAD)
-               return 1;
-
-       loop_count = DEFAULT_LOOP_COUNT;
-       while (--loop_count && inw(host->io_port + HOST_HCCR) & 0x0080) {
-               barrier();
-               cpu_relax();
-       }
-       if (!loop_count) {
-               printk("qlogicfc%d : mbox_command loop timeout #1\n", hostdata->host_id);
-               param[0] = 0x4006;
-               hostdata->adapter_state = AS_FIRMWARE_DEAD;
-               return 1;
-       }
-       hostdata->mbox_done = 0;
-
-       if (mbox_param[param[0]] == 0)
-               printk("qlogicfc%d : invalid mbox command\n", hostdata->host_id);
-
-       if (mbox_param[param[0]] & 0x80)
-               outw(param[7], host->io_port + MBOX7);
-       if (mbox_param[param[0]] & 0x40)
-               outw(param[6], host->io_port + MBOX6);
-       if (mbox_param[param[0]] & 0x20)
-               outw(param[5], host->io_port + MBOX5);
-       if (mbox_param[param[0]] & 0x10)
-               outw(param[4], host->io_port + MBOX4);
-       if (mbox_param[param[0]] & 0x08)
-               outw(param[3], host->io_port + MBOX3);
-       if (mbox_param[param[0]] & 0x04)
-               outw(param[2], host->io_port + MBOX2);
-       if (mbox_param[param[0]] & 0x02)
-               outw(param[1], host->io_port + MBOX1);
-       if (mbox_param[param[0]] & 0x01)
-               outw(param[0], host->io_port + MBOX0);
-
-
-       outw(HCCR_SET_HOST_INTR, host->io_port + HOST_HCCR);
-
-       while (1) {
-               loop_count = DEFAULT_LOOP_COUNT;
-               while (--loop_count && !(inw(host->io_port + PCI_INTER_STS) & 0x08)) { 
-                       barrier();
-                       cpu_relax();
-               }
-
-               if (!loop_count) {
-                       hostdata->adapter_state = AS_FIRMWARE_DEAD;
-                       printk("qlogicfc%d : mbox_command loop timeout #2\n", hostdata->host_id);
-                       break;
-               }
-               isp2x00_intr_handler(host->irq, host, NULL);
-
-               if (hostdata->mbox_done == 1)
-                       break;
-
-       }
-
-       loop_count = DEFAULT_LOOP_COUNT;
-       while (--loop_count && inw(host->io_port + MBOX0) == 0x04) {
-               barrier();
-               cpu_relax();
-       }
-       if (!loop_count)
-               printk("qlogicfc%d : mbox_command loop timeout #3\n", hostdata->host_id);
-
-       param[7] = inw(host->io_port + MBOX7);
-       param[6] = inw(host->io_port + MBOX6);
-       param[5] = inw(host->io_port + MBOX5);
-       param[4] = inw(host->io_port + MBOX4);
-       param[3] = inw(host->io_port + MBOX3);
-       param[2] = inw(host->io_port + MBOX2);
-       param[1] = inw(host->io_port + MBOX1);
-       param[0] = inw(host->io_port + MBOX0);
-
-
-       outw(0x0, host->io_port + PCI_SEMAPHORE);
-
-       if (inw(host->io_port + HOST_HCCR) & 0x0080) {
-               hostdata->adapter_state = AS_FIRMWARE_DEAD;
-               printk("qlogicfc%d : mbox op is still pending\n", hostdata->host_id);
-       }
-       return 0;
-}
-
-#if DEBUG_ISP2x00_INTR
-
-void isp2x00_print_status_entry(struct Status_Entry *status)
-{
-       printk("qlogicfc : entry count = 0x%02x, type = 0x%02x, flags = 0x%02x\n", 
-       status->hdr.entry_cnt, status->hdr.entry_type, status->hdr.flags);
-       printk("qlogicfc : scsi status = 0x%04x, completion status = 0x%04x\n",
-              le16_to_cpu(status->scsi_status), le16_to_cpu(status->completion_status));
-       printk("qlogicfc : state flags = 0x%04x, status flags = 0x%04x\n", 
-              le16_to_cpu(status->state_flags), le16_to_cpu(status->status_flags));
-       printk("qlogicfc : response info length = 0x%04x, request sense length = 0x%04x\n",
-              le16_to_cpu(status->res_info_len), le16_to_cpu(status->req_sense_len));
-       printk("qlogicfc : residual transfer length = 0x%08x, response = 0x%02x\n", le32_to_cpu(status->residual), status->res_info[3]);
-
-}
-
-#endif                         /* DEBUG_ISP2x00_INTR */
-
-
-#if DEBUG_ISP2x00
-
-void isp2x00_print_scsi_cmd(Scsi_Cmnd * cmd)
-{
-       int i;
-
-       printk("qlogicfc : target = 0x%02x, lun = 0x%02x, cmd_len = 0x%02x\n", 
-              cmd->target, cmd->lun, cmd->cmd_len);
-       printk("qlogicfc : command = ");
-       for (i = 0; i < cmd->cmd_len; i++)
-               printk("0x%02x ", cmd->cmnd[i]);
-       printk("\n");
-}
-
-#endif                         /* DEBUG_ISP2x00 */
-
-MODULE_LICENSE("GPL");
-
-static struct scsi_host_template driver_template = {
-        .detect                 = isp2x00_detect,
-        .release                = isp2x00_release,
-        .info                   = isp2x00_info,
-        .queuecommand           = isp2x00_queuecommand,
-        .eh_abort_handler       = isp2x00_abort,
-        .bios_param             = isp2x00_biosparam,
-        .can_queue              = QLOGICFC_REQ_QUEUE_LEN,
-        .this_id                = -1,
-        .sg_tablesize           = QLOGICFC_MAX_SG(QLOGICFC_REQ_QUEUE_LEN),
-       .cmd_per_lun            = QLOGICFC_CMD_PER_LUN,
-        .use_clustering         = ENABLE_CLUSTERING,
-};
-#include "scsi_module.c"
diff --git a/drivers/scsi/qlogicfc_asm.c b/drivers/scsi/qlogicfc_asm.c
deleted file mode 100644 (file)
index b1d4510..0000000
+++ /dev/null
@@ -1,9751 +0,0 @@
-/************************************************************************
- *                                                                     *
- *      --- ISP2100 Fabric Initiator/Target Firmware ---               *
- *                   with expanded LUN addressing                       *
- *                   and FcTape (FCP-2) support                         *
- *                                                                     *
- *                                                                     *
- ************************************************************************
-  Copyright (C) 2000 and 2001 Qlogic Corporation 
-  (www.qlogic.com)
-
-  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.
-************************************************************************/
-
-/*
- *     Firmware Version 1.19.16 (10:36 Nov 02, 2000)
- */
-
-static unsigned short risc_code_addr01 = 0x1000 ;
-
-static unsigned short risc_code_length2100 = 0x9260;
-static unsigned short risc_code2100[] = {
-       0x0078, 0x102d, 0x0000, 0x9260, 0x0000, 0x0001, 0x0013, 0x0010,
-       0x0017, 0x2043, 0x4f50, 0x5952, 0x4947, 0x4854, 0x2031, 0x3939,
-       0x3920, 0x514c, 0x4f47, 0x4943, 0x2043, 0x4f52, 0x504f, 0x5241,
-       0x5449, 0x4f4e, 0x2049, 0x5350, 0x3231, 0x3030, 0x2046, 0x6972,
-       0x6d77, 0x6172, 0x6520, 0x2056, 0x6572, 0x7369, 0x6f6e, 0x2030,
-       0x312e, 0x3139, 0x2020, 0x2020, 0x2400, 0x2091, 0x2000, 0x20c1,
-       0x0021, 0x2039, 0xffff, 0x2019, 0xaaaa, 0x2760, 0x2069, 0x7fff,
-       0x20c1, 0x0020, 0x2c2c, 0x2d34, 0x2762, 0x236a, 0x2c24, 0x2d04,
-       0x266a, 0x2562, 0xa406, 0x00c0, 0x1052, 0x20c1, 0x0021, 0x2c2c,
-       0x2362, 0x2c04, 0x2562, 0xa306, 0x0040, 0x1052, 0x20c1, 0x0020,
-       0x2039, 0x8fff, 0x20a1, 0xaa00, 0x2708, 0x810d, 0x810d, 0x810d,
-       0x810d, 0xa18c, 0x000f, 0x2001, 0x000a, 0xa112, 0xa00e, 0x21a8,
-       0x41a4, 0x3400, 0x8211, 0x00c0, 0x105f, 0x2708, 0x3400, 0xa102,
-       0x0040, 0x106f, 0x0048, 0x106f, 0x20a8, 0xa00e, 0x41a4, 0x20a1,
-       0xa260, 0x2009, 0x0000, 0x20a9, 0x07a0, 0x41a4, 0x3400, 0x20c9,
-       0xa7ff, 0x2059, 0x0000, 0x2b78, 0x7823, 0x0004, 0x2089, 0x255d,
-       0x2051, 0xa300, 0x2a70, 0x775e, 0xa786, 0x8fff, 0x0040, 0x1092,
-       0x705b, 0xca00, 0x7057, 0xc9f1, 0x7063, 0x0200, 0x7067, 0x0200,
-       0x0078, 0x109a, 0x7057, 0xba01, 0x7063, 0x0100, 0x7067, 0x0100,
-       0x705b, 0xba00, 0x1078, 0x12df, 0x1078, 0x13c0, 0x1078, 0x1569,
-       0x1078, 0x1ca4, 0x1078, 0x4229, 0x1078, 0x74cf, 0x1078, 0x134b,
-       0x1078, 0x2a3f, 0x1078, 0x4da2, 0x1078, 0x48b2, 0x1078, 0x57df,
-       0x1078, 0x21f7, 0x1078, 0x5abf, 0x1078, 0x5369, 0x1078, 0x210d,
-       0x1078, 0x21d4, 0x2091, 0x3009, 0x7823, 0x0000, 0x0090, 0x10cf,
-       0x7820, 0xa086, 0x0002, 0x00c0, 0x10cf, 0x7823, 0x4000, 0x0068,
-       0x10c7, 0x781b, 0x0001, 0x2091, 0x5000, 0x2091, 0x4080, 0x2a70,
-       0x7003, 0x0000, 0x2001, 0x017f, 0x2003, 0x0000, 0x2a70, 0x7000,
-       0xa08e, 0x0003, 0x00c0, 0x10ef, 0x1078, 0x35bc, 0x1078, 0x2a67,
-       0x1078, 0x4df2, 0x1078, 0x4a75, 0x2009, 0x0100, 0x2104, 0xa082,
-       0x0002, 0x0048, 0x10f3, 0x1078, 0x57fb, 0x0078, 0x10d6, 0x1079,
-       0x10f7, 0x0078, 0x10dc, 0x1078, 0x6fa9, 0x0078, 0x10eb, 0x1101,
-       0x1102, 0x11be, 0x10ff, 0x1246, 0x12dc, 0x12dd, 0x12de, 0x1078,
-       0x1328, 0x007c, 0x127e, 0x0f7e, 0x2091, 0x8000, 0x7000, 0xa086,
-       0x0001, 0x00c0, 0x1198, 0x1078, 0x3a43, 0x2079, 0x0100, 0x7844,
-       0xa005, 0x00c0, 0x1198, 0x2011, 0x4129, 0x1078, 0x58d4, 0x1078,
-       0x1ab1, 0x780f, 0x00ff, 0x7840, 0xa084, 0xfffb, 0x7842, 0x2011,
-       0x8010, 0x73c0, 0x1078, 0x3579, 0x2001, 0xffff, 0x1078, 0x5975,
-       0x7238, 0xc284, 0x723a, 0x2001, 0xa30c, 0x2014, 0xc2ac, 0x2202,
-       0x1078, 0x6db5, 0x2011, 0x0004, 0x1078, 0x8a59, 0x1078, 0x47ce,
-       0x1078, 0x4211, 0x0040, 0x1144, 0x7083, 0x0001, 0x70bb, 0x0000,
-       0x1078, 0x3bf5, 0x0078, 0x1198, 0x1078, 0x4897, 0x0040, 0x114d,
-       0x7a0c, 0xc2b4, 0x7a0e, 0x0078, 0x1159, 0x1078, 0x8ddf, 0x70c8,
-       0xd09c, 0x00c0, 0x1159, 0x7094, 0xa005, 0x0040, 0x1159, 0x1078,
-       0x41f5, 0x70d3, 0x0000, 0x70cf, 0x0000, 0x72c8, 0x2079, 0xa351,
-       0x7804, 0xd0ac, 0x0040, 0x1165, 0xc295, 0x72ca, 0xa296, 0x0004,
-       0x0040, 0x1186, 0x2011, 0x0001, 0x1078, 0x8a59, 0x708f, 0x0000,
-       0x7093, 0xffff, 0x7003, 0x0002, 0x0f7f, 0x1078, 0x260d, 0x2011,
-       0x0005, 0x1078, 0x6ef2, 0x1078, 0x6109, 0x0c7e, 0x2061, 0x0100,
-       0x60e3, 0x0008, 0x0c7f, 0x127f, 0x0078, 0x119a, 0x708f, 0x0000,
-       0x7093, 0xffff, 0x7003, 0x0002, 0x2011, 0x0005, 0x1078, 0x6ef2,
-       0x1078, 0x6109, 0x0c7e, 0x2061, 0x0100, 0x60e3, 0x0008, 0x0c7f,
-       0x0f7f, 0x127f, 0x007c, 0x0c7e, 0x20a9, 0x0082, 0x2009, 0x007e,
-       0x017e, 0x027e, 0x037e, 0x2110, 0x027e, 0x2019, 0x0029, 0x1078,
-       0x71e0, 0x027f, 0x1078, 0xa190, 0x037f, 0x027f, 0x017f, 0x1078,
-       0x2921, 0x8108, 0x00f0, 0x11a0, 0x0c7f, 0x706b, 0x0000, 0x706c,
-       0xa084, 0x00ff, 0x706e, 0x7097, 0x0000, 0x007c, 0x127e, 0x2091,
-       0x8000, 0x7000, 0xa086, 0x0002, 0x00c0, 0x1244, 0x7090, 0xa086,
-       0xffff, 0x0040, 0x11d1, 0x1078, 0x260d, 0x1078, 0x6109, 0x0078,
-       0x1244, 0x70c8, 0xd09c, 0x0040, 0x11fd, 0xd084, 0x0040, 0x11fd,
-       0x0f7e, 0x2079, 0x0100, 0x790c, 0xc1b5, 0x790e, 0x0f7f, 0xd08c,
-       0x0040, 0x11fd, 0x70cc, 0xa086, 0xffff, 0x0040, 0x11f9, 0x1078,
-       0x278a, 0x1078, 0x6109, 0x70c8, 0xd094, 0x00c0, 0x1244, 0x2011,
-       0x0001, 0x2019, 0x0000, 0x1078, 0x27c2, 0x1078, 0x6109, 0x0078,
-       0x1244, 0x70d0, 0xa005, 0x00c0, 0x1244, 0x708c, 0xa005, 0x00c0,
-       0x1244, 0x1078, 0x4897, 0x00c0, 0x1244, 0x2001, 0xa352, 0x2004,
-       0xd0ac, 0x0040, 0x1227, 0x157e, 0x0c7e, 0x20a9, 0x007f, 0x2009,
-       0x0000, 0x017e, 0x1078, 0x4501, 0x00c0, 0x121a, 0x6000, 0xd0ec,
-       0x00c0, 0x1222, 0x017f, 0x8108, 0x00f0, 0x1211, 0x0c7f, 0x157f,
-       0x0078, 0x1227, 0x017f, 0x0c7f, 0x157f, 0x0078, 0x1244, 0x7003,
-       0x0003, 0x7093, 0xffff, 0x2001, 0x0000, 0x1078, 0x2480, 0x1078,
-       0x35f7, 0x2001, 0xa5ac, 0x2004, 0xa086, 0x0005, 0x00c0, 0x123c,
-       0x2011, 0x0000, 0x1078, 0x6ef2, 0x2011, 0x0000, 0x1078, 0x6efc,
-       0x1078, 0x6109, 0x1078, 0x61d3, 0x127f, 0x007c, 0x017e, 0x0f7e,
-       0x127e, 0x2091, 0x8000, 0x2079, 0x0100, 0x2009, 0x00f7, 0x1078,
-       0x41de, 0x7940, 0xa18c, 0x0010, 0x7942, 0x7924, 0xd1b4, 0x0040,
-       0x125b, 0x7827, 0x0040, 0xd19c, 0x0040, 0x1260, 0x7827, 0x0008,
-       0x007e, 0x037e, 0x157e, 0xa006, 0x1078, 0x5975, 0x7900, 0xa18a,
-       0x0003, 0x0050, 0x1289, 0x7954, 0xd1ac, 0x00c0, 0x1289, 0x2009,
-       0x00f8, 0x1078, 0x41de, 0x7843, 0x0090, 0x7843, 0x0010, 0x20a9,
-       0x09c4, 0x7820, 0xd09c, 0x00c0, 0x1281, 0x7824, 0xd0ac, 0x00c0,
-       0x12ca, 0x00f0, 0x1279, 0x2001, 0x0001, 0x1078, 0x2480, 0x0078,
-       0x12d5, 0x7853, 0x0000, 0x782f, 0x0020, 0x20a9, 0x0050, 0x00e0,
-       0x128f, 0x2091, 0x6000, 0x00f0, 0x128f, 0x7853, 0x0400, 0x782f,
-       0x0000, 0x2009, 0x00f8, 0x1078, 0x41de, 0x20a9, 0x000e, 0x0005,
-       0x00f0, 0x129f, 0x7853, 0x1400, 0x7843, 0x0090, 0x7843, 0x0010,
-       0x2019, 0x61a8, 0x7854, 0x0005, 0x0005, 0xd08c, 0x0040, 0x12b4,
-       0x7824, 0xd0ac, 0x00c0, 0x12ca, 0x8319, 0x00c0, 0x12aa, 0x2009,
-       0xa331, 0x2104, 0x8000, 0x200a, 0xa084, 0xfff0, 0x0040, 0x12c4,
-       0x200b, 0x0000, 0x1078, 0x251e, 0x2001, 0x0001, 0x1078, 0x2480,
-       0x0078, 0x12d3, 0x2001, 0xa331, 0x2003, 0x0000, 0x7828, 0xc09d,
-       0x782a, 0x7827, 0x0048, 0x7853, 0x0400, 0x157f, 0x037f, 0x007f,
-       0x127f, 0x0f7f, 0x017f, 0x007c, 0x007c, 0x007c, 0x007c, 0x2a70,
-       0x2009, 0x0100, 0x2104, 0xa082, 0x0002, 0x0048, 0x12eb, 0x704f,
-       0xffff, 0x0078, 0x12ed, 0x704f, 0x0000, 0x7053, 0xffff, 0x706b,
-       0x0000, 0x706f, 0x0000, 0x1078, 0x8ddf, 0x2061, 0xa58c, 0x6003,
-       0x0909, 0x6007, 0x0000, 0x600b, 0x8800, 0x600f, 0x0200, 0x6013,
-       0x00ff, 0x6017, 0x0003, 0x601b, 0x0000, 0x601f, 0x07d0, 0x2061,
-       0xa594, 0x6003, 0x8000, 0x6007, 0x0000, 0x600b, 0x0000, 0x600f,
-       0x0200, 0x6013, 0x00ff, 0x6017, 0x0000, 0x601b, 0x0001, 0x601f,
-       0x0000, 0x2061, 0xa5a3, 0x6003, 0x514c, 0x6007, 0x4f47, 0x600b,
-       0x4943, 0x600f, 0x2020, 0x2001, 0xa325, 0x2003, 0x0000, 0x007c,
-       0x2091, 0x8000, 0x0068, 0x132a, 0x007e, 0x017e, 0x2079, 0x0000,
-       0x7818, 0xd084, 0x00c0, 0x1330, 0x017f, 0x792e, 0x007f, 0x782a,
-       0x007f, 0x7826, 0x3900, 0x783a, 0x7823, 0x8002, 0x781b, 0x0001,
-       0x2091, 0x5000, 0x2091, 0x4080, 0x2079, 0xa300, 0x7803, 0x0005,
-       0x0078, 0x1348, 0x007c, 0x2071, 0xa300, 0x7158, 0x712e, 0x2021,
-       0x0001, 0xa190, 0x002d, 0xa298, 0x002d, 0x0048, 0x1361, 0x705c,
-       0xa302, 0x00c8, 0x1361, 0x220a, 0x2208, 0x2310, 0x8420, 0x0078,
-       0x1353, 0x200b, 0x0000, 0x74a6, 0x74aa, 0x007c, 0x0e7e, 0x127e,
-       0x2091, 0x8000, 0x2071, 0xa300, 0x70a8, 0xa0ea, 0x0010, 0x00c8,
-       0x1374, 0xa06e, 0x0078, 0x137e, 0x8001, 0x70aa, 0x702c, 0x2068,
-       0x2d04, 0x702e, 0x206b, 0x0000, 0x6807, 0x0000, 0x127f, 0x0e7f,
-       0x007c, 0x0e7e, 0x2071, 0xa300, 0x127e, 0x2091, 0x8000, 0x70a8,
-       0x8001, 0x00c8, 0x138e, 0xa06e, 0x0078, 0x1397, 0x70aa, 0x702c,
-       0x2068, 0x2d04, 0x702e, 0x206b, 0x0000, 0x6807, 0x0000, 0x127f,
-       0x0e7f, 0x007c, 0x0e7e, 0x127e, 0x2091, 0x8000, 0x2071, 0xa300,
-       0x702c, 0x206a, 0x2d00, 0x702e, 0x70a8, 0x8000, 0x70aa, 0x127f,
-       0x0e7f, 0x007c, 0x8dff, 0x0040, 0x13b6, 0x6804, 0x6807, 0x0000,
-       0x007e, 0x1078, 0x139a, 0x0d7f, 0x0078, 0x13aa, 0x007c, 0x0e7e,
-       0x2071, 0xa300, 0x70a8, 0xa08a, 0x0010, 0xa00d, 0x0e7f, 0x007c,
-       0x0e7e, 0x2071, 0xa5d0, 0x7007, 0x0000, 0x701b, 0x0000, 0x701f,
-       0x0000, 0x2071, 0x0000, 0x7010, 0xa085, 0x8004, 0x7012, 0x0e7f,
-       0x007c, 0x0e7e, 0x2270, 0x700b, 0x0000, 0x2071, 0xa5d0, 0x7018,
-       0xa088, 0xa5d9, 0x220a, 0x8000, 0xa084, 0x0007, 0x701a, 0x7004,
-       0xa005, 0x00c0, 0x13e9, 0x0f7e, 0x2079, 0x0010, 0x1078, 0x13fa,
-       0x0f7f, 0x0e7f, 0x007c, 0x0e7e, 0x2071, 0xa5d0, 0x7004, 0xa005,
-       0x00c0, 0x13f8, 0x0f7e, 0x2079, 0x0010, 0x1078, 0x13fa, 0x0f7f,
-       0x0e7f, 0x007c, 0x7000, 0x0079, 0x13fd, 0x1401, 0x146b, 0x1488,
-       0x1488, 0x7018, 0x711c, 0xa106, 0x00c0, 0x1409, 0x7007, 0x0000,
-       0x007c, 0x0d7e, 0xa180, 0xa5d9, 0x2004, 0x700a, 0x2068, 0x8108,
-       0xa18c, 0x0007, 0x711e, 0x7803, 0x0026, 0x6824, 0x7832, 0x6828,
-       0x7836, 0x682c, 0x783a, 0x6830, 0x783e, 0x6810, 0x700e, 0x680c,
-       0x7016, 0x6804, 0x0d7f, 0xd084, 0x0040, 0x142b, 0x7007, 0x0001,
-       0x1078, 0x1430, 0x007c, 0x7007, 0x0002, 0x1078, 0x1446, 0x007c,
-       0x017e, 0x027e, 0x710c, 0x2011, 0x0040, 0xa182, 0x0040, 0x00c8,
-       0x143b, 0x2110, 0xa006, 0x700e, 0x7212, 0x8203, 0x7822, 0x7803,
-       0x0020, 0x7803, 0x0041, 0x027f, 0x017f, 0x007c, 0x017e, 0x027e,
-       0x137e, 0x147e, 0x157e, 0x7014, 0x2098, 0x20a1, 0x0014, 0x7803,
-       0x0026, 0x710c, 0x2011, 0x0040, 0xa182, 0x0040, 0x00c8, 0x145a,
-       0x2110, 0xa006, 0x700e, 0x22a8, 0x53a6, 0x8203, 0x7822, 0x7803,
-       0x0020, 0x3300, 0x7016, 0x7803, 0x0001, 0x157f, 0x147f, 0x137f,
-       0x027f, 0x017f, 0x007c, 0x137e, 0x147e, 0x157e, 0x2099, 0xa3f9,
-       0x20a1, 0x0018, 0x20a9, 0x0008, 0x53a3, 0x7803, 0x0020, 0x127e,
-       0x2091, 0x8000, 0x7803, 0x0041, 0x7007, 0x0003, 0x7000, 0xc084,
-       0x7002, 0x700b, 0xa3f4, 0x127f, 0x157f, 0x147f, 0x137f, 0x007c,
-       0x137e, 0x147e, 0x157e, 0x2001, 0xa428, 0x209c, 0x20a1, 0x0014,
-       0x7803, 0x0026, 0x2001, 0xa429, 0x20ac, 0x53a6, 0x2099, 0xa42a,
-       0x20a1, 0x0018, 0x20a9, 0x0008, 0x53a3, 0x7803, 0x0020, 0x127e,
-       0x2091, 0x8000, 0x7803, 0x0001, 0x7007, 0x0004, 0x7000, 0xc08c,
-       0x7002, 0x700b, 0xa425, 0x127f, 0x157f, 0x147f, 0x137f, 0x007c,
-       0x017e, 0x0e7e, 0x2071, 0xa5d0, 0x0f7e, 0x2079, 0x0010, 0x7904,
-       0x7803, 0x0002, 0xd1fc, 0x0040, 0x14c2, 0xa18c, 0x0700, 0x7004,
-       0x1079, 0x14c6, 0x0f7f, 0x0e7f, 0x017f, 0x007c, 0x13fa, 0x14ce,
-       0x14fb, 0x1523, 0x1556, 0x14cc, 0x0078, 0x14cc, 0xa18c, 0x0700,
-       0x00c0, 0x14f4, 0x137e, 0x147e, 0x157e, 0x7014, 0x20a0, 0x2099,
-       0x0014, 0x7803, 0x0040, 0x7010, 0x20a8, 0x53a5, 0x3400, 0x7016,
-       0x157f, 0x147f, 0x137f, 0x700c, 0xa005, 0x0040, 0x1510, 0x1078,
-       0x1430, 0x007c, 0x7008, 0xa080, 0x0002, 0x2003, 0x0100, 0x7007,
-       0x0000, 0x1078, 0x13fa, 0x007c, 0x7008, 0xa080, 0x0002, 0x2003,
-       0x0200, 0x0078, 0x14ef, 0xa18c, 0x0700, 0x00c0, 0x1506, 0x700c,
-       0xa005, 0x0040, 0x1510, 0x1078, 0x1446, 0x007c, 0x7008, 0xa080,
-       0x0002, 0x2003, 0x0200, 0x7007, 0x0000, 0x1078, 0x13fa, 0x007c,
-       0x0d7e, 0x7008, 0x2068, 0x7830, 0x6826, 0x7834, 0x682a, 0x7838,
-       0x682e, 0x783c, 0x6832, 0x680b, 0x0100, 0x0d7f, 0x7007, 0x0000,
-       0x1078, 0x13fa, 0x007c, 0xa18c, 0x0700, 0x00c0, 0x1550, 0x137e,
-       0x147e, 0x157e, 0x2001, 0xa3f7, 0x2004, 0xa080, 0x000d, 0x20a0,
-       0x2099, 0x0014, 0x7803, 0x0040, 0x20a9, 0x0020, 0x53a5, 0x2001,
-       0xa3f9, 0x2004, 0xd0bc, 0x0040, 0x1546, 0x2001, 0xa402, 0x2004,
-       0xa080, 0x000d, 0x20a0, 0x20a9, 0x0020, 0x53a5, 0x157f, 0x147f,
-       0x137f, 0x7007, 0x0000, 0x1078, 0x4e9b, 0x1078, 0x13fa, 0x007c,
-       0x2011, 0x8003, 0x1078, 0x3579, 0x0078, 0x1554, 0xa18c, 0x0700,
-       0x00c0, 0x1563, 0x2001, 0xa427, 0x2003, 0x0100, 0x7007, 0x0000,
-       0x1078, 0x13fa, 0x007c, 0x2011, 0x8004, 0x1078, 0x3579, 0x0078,
-       0x1567, 0x127e, 0x2091, 0x2100, 0x2079, 0x0030, 0x2071, 0xa5e1,
-       0x7803, 0x0004, 0x7003, 0x0000, 0x700f, 0xa5e7, 0x7013, 0xa5e7,
-       0x780f, 0x0076, 0x7803, 0x0004, 0x127f, 0x007c, 0x6934, 0xa184,
-       0x0007, 0x0079, 0x1583, 0x158b, 0x15d1, 0x158b, 0x158b, 0x158b,
-       0x15b6, 0x159a, 0x158f, 0xa085, 0x0001, 0x0078, 0x15eb, 0x684c,
-       0xd0bc, 0x0040, 0x158b, 0x6860, 0x682e, 0x685c, 0x682a, 0x6858,
-       0x0078, 0x15d9, 0xa18c, 0x00ff, 0xa186, 0x001e, 0x00c0, 0x158b,
-       0x684c, 0xd0bc, 0x0040, 0x158b, 0x6860, 0x682e, 0x685c, 0x682a,
-       0x6804, 0x681a, 0xa080, 0x000d, 0x2004, 0xa084, 0x000f, 0xa080,
-       0x2015, 0x2004, 0x6832, 0x6858, 0x0078, 0x15e1, 0xa18c, 0x00ff,
-       0xa186, 0x0015, 0x00c0, 0x158b, 0x684c, 0xd0ac, 0x0040, 0x158b,
-       0x6804, 0x681a, 0xa080, 0x000d, 0x2004, 0xa084, 0x000f, 0xa080,
-       0x2015, 0x2004, 0x6832, 0xa006, 0x682e, 0x682a, 0x6858, 0x0078,
-       0x15e1, 0x684c, 0xd0ac, 0x0040, 0x158b, 0xa006, 0x682e, 0x682a,
-       0x6858, 0xa18c, 0x000f, 0xa188, 0x2015, 0x210c, 0x6932, 0x2d08,
-       0x691a, 0x6826, 0x684c, 0xc0dd, 0x684e, 0xa006, 0x680a, 0x697c,
-       0x6912, 0x6980, 0x6916, 0x007c, 0x20e1, 0x0007, 0x20e1, 0x2000,
-       0x2001, 0x020a, 0x2004, 0x82ff, 0x0040, 0x160e, 0xa280, 0x0004,
-       0x0d7e, 0x206c, 0x684c, 0xd0dc, 0x00c0, 0x160a, 0x1078, 0x157e,
-       0x0040, 0x160a, 0x0d7f, 0xa280, 0x0000, 0x2003, 0x0002, 0xa016,
-       0x0078, 0x160e, 0x6808, 0x8000, 0x680a, 0x0d7f, 0x127e, 0x047e,
-       0x037e, 0x027e, 0x2091, 0x2100, 0x027f, 0x037f, 0x047f, 0x7000,
-       0xa005, 0x00c0, 0x1622, 0x7206, 0x2001, 0x1643, 0x007e, 0x2260,
-       0x0078, 0x17be, 0x710c, 0x220a, 0x8108, 0x230a, 0x8108, 0x240a,
-       0x8108, 0xa182, 0xa602, 0x0048, 0x162f, 0x2009, 0xa5e7, 0x710e,
-       0x7010, 0xa102, 0xa082, 0x0009, 0x0040, 0x163a, 0xa080, 0x001b,
-       0x00c0, 0x163d, 0x2009, 0x0138, 0x200a, 0x7000, 0xa005, 0x00c0,
-       0x1643, 0x1078, 0x179f, 0x127f, 0x007c, 0x127e, 0x027e, 0x037e,
-       0x0c7e, 0x007e, 0x2091, 0x2100, 0x007f, 0x047f, 0x037f, 0x027f,
-       0x0d7e, 0x0c7e, 0x2460, 0x6110, 0x2168, 0x6a62, 0x6b5e, 0xa005,
-       0x0040, 0x16cf, 0x6808, 0xa005, 0x0040, 0x173c, 0x7000, 0xa005,
-       0x00c0, 0x1664, 0x0078, 0x16c4, 0x700c, 0x7110, 0xa106, 0x00c0,
-       0x1745, 0x7004, 0xa406, 0x00c0, 0x16c4, 0x2001, 0x0005, 0x2004,
-       0xd08c, 0x0040, 0x1681, 0x047e, 0x1078, 0x18e2, 0x047f, 0x2460,
-       0x6010, 0xa080, 0x0002, 0x2004, 0xa005, 0x0040, 0x173c, 0x0078,
-       0x165e, 0x2001, 0x0207, 0x2004, 0xd09c, 0x00c0, 0x166d, 0x7804,
-       0xa084, 0x6000, 0x0040, 0x1692, 0xa086, 0x6000, 0x0040, 0x1692,
-       0x0078, 0x166d, 0x7100, 0xa186, 0x0002, 0x00c0, 0x16b2, 0x0e7e,
-       0x2b68, 0x6818, 0x2060, 0x1078, 0x1fea, 0x2804, 0xac70, 0x6034,
-       0xd09c, 0x00c0, 0x16a7, 0x7108, 0x720c, 0x0078, 0x16a9, 0x7110,
-       0x7214, 0x6810, 0xa100, 0x6812, 0x6814, 0xa201, 0x6816, 0x0e7f,
-       0x0078, 0x16b6, 0xa186, 0x0001, 0x00c0, 0x16be, 0x7820, 0x6910,
-       0xa100, 0x6812, 0x7824, 0x6914, 0xa101, 0x6816, 0x7803, 0x0004,
-       0x7003, 0x0000, 0x7004, 0x2060, 0x6100, 0xa18e, 0x0004, 0x00c0,
-       0x1745, 0x2009, 0x0048, 0x1078, 0x756c, 0x0078, 0x1745, 0x6808,
-       0xa005, 0x0040, 0x173c, 0x7000, 0xa005, 0x00c0, 0x16d9, 0x0078,
-       0x173c, 0x700c, 0x7110, 0xa106, 0x00c0, 0x16e2, 0x7004, 0xa406,
-       0x00c0, 0x173c, 0x2001, 0x0005, 0x2004, 0xd08c, 0x0040, 0x16f6,
-       0x047e, 0x1078, 0x18e2, 0x047f, 0x2460, 0x6010, 0xa080, 0x0002,
-       0x2004, 0xa005, 0x0040, 0x173c, 0x0078, 0x16d3, 0x2001, 0x0207,
-       0x2004, 0xd09c, 0x00c0, 0x16e2, 0x2001, 0x0005, 0x2004, 0xd08c,
-       0x00c0, 0x16e8, 0x7804, 0xa084, 0x6000, 0x0040, 0x170d, 0xa086,
-       0x6000, 0x0040, 0x170d, 0x0078, 0x16e2, 0x7007, 0x0000, 0xa016,
-       0x2218, 0x7000, 0xa08e, 0x0001, 0x0040, 0x172e, 0xa08e, 0x0002,
-       0x00c0, 0x173c, 0x0c7e, 0x0e7e, 0x6818, 0x2060, 0x1078, 0x1fea,
-       0x2804, 0xac70, 0x6034, 0xd09c, 0x00c0, 0x172a, 0x7308, 0x720c,
-       0x0078, 0x172c, 0x7310, 0x7214, 0x0e7f, 0x0c7f, 0x7820, 0xa318,
-       0x7824, 0xa211, 0x6810, 0xa300, 0x6812, 0x6814, 0xa201, 0x6816,
-       0x7803, 0x0004, 0x7003, 0x0000, 0x6100, 0xa18e, 0x0004, 0x00c0,
-       0x1745, 0x2009, 0x0048, 0x1078, 0x756c, 0x0c7f, 0x0d7f, 0x127f,
-       0x007c, 0x0f7e, 0x0e7e, 0x027e, 0x037e, 0x047e, 0x1078, 0x1af7,
-       0x027e, 0x2071, 0xa5e1, 0x7000, 0xa086, 0x0000, 0x0040, 0x1790,
-       0x7004, 0xac06, 0x00c0, 0x1781, 0x2079, 0x0030, 0x7000, 0xa086,
-       0x0003, 0x0040, 0x1781, 0x7804, 0xd0fc, 0x00c0, 0x177d, 0x2001,
-       0x0207, 0x2004, 0xd09c, 0x00c0, 0x1763, 0x7803, 0x0004, 0x7804,
-       0xd0ac, 0x00c0, 0x176f, 0x7803, 0x0002, 0x7803, 0x0009, 0x7003,
-       0x0003, 0x7007, 0x0000, 0x0078, 0x1781, 0x1078, 0x18e2, 0x0078,
-       0x1753, 0x157e, 0x20a9, 0x0009, 0x2009, 0xa5e7, 0x2104, 0xac06,
-       0x00c0, 0x178b, 0x200a, 0xa188, 0x0003, 0x00f0, 0x1786, 0x157f,
-       0x027f, 0x2001, 0x015d, 0x201c, 0x831a, 0x2302, 0x2001, 0x0138,
-       0x2202, 0x047f, 0x037f, 0x027f, 0x0e7f, 0x0f7f, 0x007c, 0x700c,
-       0x7110, 0xa106, 0x00c0, 0x17a7, 0x7003, 0x0000, 0x007c, 0x2104,
-       0x7006, 0x2060, 0x8108, 0x211c, 0x8108, 0x2124, 0x8108, 0xa182,
-       0xa602, 0x0048, 0x17b5, 0x2009, 0xa5e7, 0x7112, 0x700c, 0xa106,
-       0x00c0, 0x17be, 0x2001, 0x0138, 0x2003, 0x0008, 0x8cff, 0x00c0,
-       0x17c5, 0x1078, 0x1b22, 0x0078, 0x1823, 0x6010, 0x2068, 0x2d58,
-       0x6828, 0xa406, 0x00c0, 0x17d0, 0x682c, 0xa306, 0x0040, 0x17fe,
-       0x601c, 0xa086, 0x0008, 0x0040, 0x17fe, 0x6024, 0xd0f4, 0x00c0,
-       0x17fa, 0xd0d4, 0x0040, 0x17f6, 0x6038, 0xa402, 0x6034, 0xa303,
-       0x0040, 0x17e4, 0x00c8, 0x17f6, 0x643a, 0x6336, 0x6c2a, 0x6b2e,
-       0x047e, 0x037e, 0x2400, 0x6c7c, 0xa402, 0x6812, 0x2300, 0x6b80,
-       0xa303, 0x6816, 0x037f, 0x047f, 0x0078, 0x17fa, 0x1078, 0x8d8e,
-       0x0040, 0x17c1, 0x1078, 0x2035, 0x00c0, 0x17c1, 0x0c7e, 0x7004,
-       0x2060, 0x6024, 0xc0d4, 0x6026, 0x0c7f, 0x684c, 0xd0f4, 0x0040,
-       0x180f, 0x6817, 0xffff, 0x6813, 0xffff, 0x0078, 0x17c1, 0x6824,
-       0x2050, 0x6818, 0x2060, 0x6830, 0x2040, 0x6034, 0xa0cc, 0x000f,
-       0x2009, 0x0011, 0x1078, 0x1824, 0x0040, 0x1822, 0x2009, 0x0001,
-       0x1078, 0x1824, 0x2d58, 0x007c, 0x8aff, 0x0040, 0x18bb, 0xa03e,
-       0x2730, 0x6850, 0xd0fc, 0x00c0, 0x1846, 0xd0f4, 0x00c0, 0x1856,
-       0x0d7e, 0x2804, 0xac68, 0x2900, 0x0079, 0x1836, 0x189d, 0x185d,
-       0x185d, 0x189d, 0x189d, 0x1895, 0x189d, 0x185d, 0x189d, 0x1863,
-       0x1863, 0x189d, 0x189d, 0x189d, 0x188c, 0x1863, 0xc0fc, 0x6852,
-       0x6b6c, 0x6a70, 0x6d1c, 0x6c20, 0x0d7e, 0xd99c, 0x0040, 0x18a0,
-       0x2804, 0xac68, 0x6f08, 0x6e0c, 0x0078, 0x18a0, 0xc0f4, 0x6852,
-       0x6b6c, 0x6a70, 0x0d7e, 0x0078, 0x18a7, 0x6b08, 0x6a0c, 0x6d00,
-       0x6c04, 0x0078, 0x18a0, 0x7b0c, 0xd3bc, 0x0040, 0x1884, 0x7004,
-       0x0e7e, 0x2070, 0x701c, 0x0e7f, 0xa086, 0x0008, 0x00c0, 0x1884,
-       0x7b08, 0xa39c, 0x0fff, 0x2d20, 0x0d7f, 0x0d7e, 0x6a14, 0x82ff,
-       0x00c0, 0x187f, 0x6810, 0xa302, 0x0048, 0x187f, 0x6b10, 0x2011,
-       0x0000, 0x2468, 0x0078, 0x1886, 0x6b10, 0x6a14, 0x6d00, 0x6c04,
-       0x6f08, 0x6e0c, 0x0078, 0x18a0, 0x0d7f, 0x0d7e, 0x6834, 0xa084,
-       0x00ff, 0xa086, 0x001e, 0x00c0, 0x189d, 0x0d7f, 0x1078, 0x1fd1,
-       0x00c0, 0x1824, 0xa00e, 0x0078, 0x18bb, 0x0d7f, 0x1078, 0x1328,
-       0x7b22, 0x7a26, 0x7d32, 0x7c36, 0x7f3a, 0x7e3e, 0x7902, 0x7000,
-       0x8000, 0x7002, 0x0d7f, 0x6828, 0xa300, 0x682a, 0x682c, 0xa201,
-       0x682e, 0x2300, 0x6b10, 0xa302, 0x6812, 0x2200, 0x6a14, 0xa203,
-       0x6816, 0x1078, 0x1fd1, 0x007c, 0x1078, 0x1328, 0x1078, 0x1c52,
-       0x7004, 0x2060, 0x0d7e, 0x6010, 0x2068, 0x7003, 0x0000, 0x1078,
-       0x1ac6, 0x1078, 0x8a44, 0x0040, 0x18db, 0x6808, 0x8001, 0x680a,
-       0x697c, 0x6912, 0x6980, 0x6916, 0x682b, 0xffff, 0x682f, 0xffff,
-       0x6850, 0xc0bd, 0x6852, 0x0d7f, 0x1078, 0x8758, 0x0078, 0x1aad,
-       0x1078, 0x1328, 0x127e, 0x2091, 0x2100, 0x007e, 0x017e, 0x2b68,
-       0x6818, 0x2060, 0x7904, 0x7803, 0x0002, 0xa184, 0x0700, 0x00c0,
-       0x18be, 0xa184, 0x0003, 0xa086, 0x0003, 0x0040, 0x18e0, 0x7000,
-       0x0079, 0x18fa, 0x1902, 0x1904, 0x1a06, 0x1a84, 0x1a9b, 0x1902,
-       0x1902, 0x1902, 0x1078, 0x1328, 0x8001, 0x7002, 0xa184, 0x0880,
-       0x00c0, 0x1919, 0x8aff, 0x0040, 0x199b, 0x2009, 0x0001, 0x1078,
-       0x1824, 0x0040, 0x1aad, 0x2009, 0x0001, 0x1078, 0x1824, 0x0078,
-       0x1aad, 0x7803, 0x0004, 0x7003, 0x0000, 0xd1bc, 0x00c0, 0x1979,
-       0x027e, 0x037e, 0x7808, 0xd0ec, 0x00c0, 0x1930, 0x7c20, 0x7d24,
-       0x7e30, 0x7f34, 0x7803, 0x0009, 0x7003, 0x0004, 0x0078, 0x1932,
-       0x1078, 0x1b9f, 0x6b28, 0x6a2c, 0x2400, 0x686e, 0xa31a, 0x2500,
-       0x6872, 0xa213, 0x6b2a, 0x6a2e, 0x0c7e, 0x7004, 0x2060, 0x6024,
-       0xd0f4, 0x00c0, 0x1945, 0x633a, 0x6236, 0x0c7f, 0x2400, 0x6910,
-       0xa100, 0x6812, 0x2500, 0x6914, 0xa101, 0x6816, 0x037f, 0x027f,
-       0x2600, 0x681e, 0x2700, 0x6822, 0x1078, 0x1fea, 0x2a00, 0x6826,
-       0x2c00, 0x681a, 0x2800, 0x6832, 0x6850, 0xc0fd, 0x6852, 0x6808,
-       0x8001, 0x680a, 0x00c0, 0x196e, 0x684c, 0xd0e4, 0x0040, 0x196e,
-       0x7004, 0x2060, 0x2009, 0x0048, 0x1078, 0x756c, 0x7000, 0xa086,
-       0x0004, 0x0040, 0x1aad, 0x7003, 0x0000, 0x1078, 0x179f, 0x0078,
-       0x1aad, 0x057e, 0x7d0c, 0xd5bc, 0x00c0, 0x1980, 0x1078, 0xa20c,
-       0x057f, 0x1078, 0x1ac6, 0x0f7e, 0x7004, 0x2078, 0x1078, 0x4893,
-       0x0040, 0x198d, 0x7824, 0xc0f5, 0x7826, 0x0f7f, 0x682b, 0xffff,
-       0x682f, 0xffff, 0x6808, 0x8001, 0x680a, 0x697c, 0x6912, 0x6980,
-       0x6916, 0x0078, 0x1aad, 0x7004, 0x0c7e, 0x2060, 0x6024, 0x0c7f,
-       0xd0f4, 0x0040, 0x19a8, 0x6808, 0x8001, 0x680a, 0x0078, 0x1aad,
-       0x684c, 0xc0f5, 0x684e, 0x7814, 0xa005, 0x00c0, 0x19c0, 0x7003,
-       0x0000, 0x6808, 0x8001, 0x680a, 0x00c0, 0x19bc, 0x7004, 0x2060,
-       0x2009, 0x0048, 0x1078, 0x756c, 0x1078, 0x179f, 0x0078, 0x1aad,
-       0x7814, 0x6910, 0xa102, 0x6812, 0x6914, 0xa183, 0x0000, 0x6816,
-       0x7814, 0x7908, 0xa18c, 0x0fff, 0xa188, 0x0007, 0x8114, 0x8214,
-       0x8214, 0xa10a, 0x8104, 0x8004, 0x8004, 0xa20a, 0x810b, 0x810b,
-       0x810b, 0x1078, 0x1b4d, 0x7803, 0x0004, 0x780f, 0xffff, 0x7803,
-       0x0001, 0x7804, 0xd0fc, 0x0040, 0x19e1, 0x7803, 0x0002, 0x7803,
-       0x0004, 0x780f, 0x0076, 0x7004, 0x7007, 0x0000, 0x2060, 0x2009,
-       0x0048, 0x1078, 0x756c, 0x1078, 0x1b81, 0x0040, 0x19bc, 0x7908,
-       0xd1ec, 0x00c0, 0x19ff, 0x2009, 0x0009, 0x0078, 0x1a01, 0x2009,
-       0x0019, 0x7902, 0x7003, 0x0003, 0x0078, 0x1aad, 0x8001, 0x7002,
-       0xd194, 0x0040, 0x1a18, 0x7804, 0xd0fc, 0x00c0, 0x18ea, 0x8aff,
-       0x0040, 0x1aad, 0x2009, 0x0001, 0x1078, 0x1824, 0x0078, 0x1aad,
-       0xa184, 0x0880, 0x00c0, 0x1a25, 0x8aff, 0x0040, 0x1aad, 0x2009,
-       0x0001, 0x1078, 0x1824, 0x0078, 0x1aad, 0x7803, 0x0004, 0x7003,
-       0x0000, 0xd1bc, 0x00c0, 0x1a65, 0x027e, 0x037e, 0x7808, 0xd0ec,
-       0x00c0, 0x1a38, 0x7803, 0x0009, 0x7003, 0x0004, 0x0078, 0x1a3a,
-       0x1078, 0x1b9f, 0x6b28, 0x6a2c, 0x1078, 0x1fea, 0x0d7e, 0x0f7e,
-       0x2d78, 0x2804, 0xac68, 0x6034, 0xd09c, 0x00c0, 0x1a55, 0x6808,
-       0x2008, 0xa31a, 0x680c, 0xa213, 0x7810, 0xa100, 0x7812, 0x690c,
-       0x7814, 0xa101, 0x7816, 0x0078, 0x1a61, 0x6810, 0x2008, 0xa31a,
-       0x6814, 0xa213, 0x7810, 0xa100, 0x7812, 0x6914, 0x7814, 0xa101,
-       0x7816, 0x0f7f, 0x0d7f, 0x0078, 0x1934, 0x057e, 0x7d0c, 0x1078,
-       0xa20c, 0x057f, 0x1078, 0x1ac6, 0x0f7e, 0x7004, 0x2078, 0x1078,
-       0x4893, 0x0040, 0x1a76, 0x7824, 0xc0f5, 0x7826, 0x0f7f, 0x682b,
-       0xffff, 0x682f, 0xffff, 0x6808, 0x8001, 0x680a, 0x697c, 0x6912,
-       0x6980, 0x6916, 0x0078, 0x1aad, 0x7803, 0x0004, 0x7003, 0x0000,
-       0x7004, 0xa00d, 0x0040, 0x1a97, 0x6808, 0x8001, 0x680a, 0x00c0,
-       0x1a97, 0x7004, 0x2060, 0x2009, 0x0048, 0x1078, 0x756c, 0x1078,
-       0x179f, 0x0078, 0x1aad, 0x7803, 0x0004, 0x7003, 0x0000, 0x7004,
-       0x2060, 0x6010, 0xa005, 0x0040, 0x1a97, 0x2068, 0x6808, 0x8000,
-       0x680a, 0x6c28, 0x6b2c, 0x1078, 0x17be, 0x017f, 0x007f, 0x127f,
-       0x007c, 0x127e, 0x2091, 0x2100, 0x7000, 0xa086, 0x0003, 0x00c0,
-       0x1ac4, 0x700c, 0x7110, 0xa106, 0x0040, 0x1ac4, 0x20e1, 0x9028,
-       0x700f, 0xa5e7, 0x7013, 0xa5e7, 0x127f, 0x007c, 0x0c7e, 0x1078,
-       0x1af7, 0x20e1, 0x9028, 0x700c, 0x7110, 0xa106, 0x0040, 0x1aed,
-       0x2104, 0xa005, 0x0040, 0x1ada, 0x2060, 0x6010, 0x2060, 0x6008,
-       0x8001, 0x600a, 0xa188, 0x0003, 0xa182, 0xa602, 0x0048, 0x1ae2,
-       0x2009, 0xa5e7, 0x7112, 0x700c, 0xa106, 0x00c0, 0x1acb, 0x2001,
-       0x0138, 0x2003, 0x0008, 0x0078, 0x1acb, 0x2001, 0x015d, 0x200c,
-       0x810a, 0x2102, 0x2001, 0x0138, 0x2202, 0x0c7f, 0x007c, 0x2001,
-       0x0138, 0x2014, 0x2003, 0x0000, 0x2021, 0xb015, 0x2001, 0x0141,
-       0x201c, 0xd3dc, 0x00c0, 0x1b14, 0x2001, 0x0109, 0x201c, 0xa39c,
-       0x0048, 0x00c0, 0x1b14, 0x2001, 0x0111, 0x201c, 0x83ff, 0x00c0,
-       0x1b14, 0x8421, 0x00c0, 0x1afe, 0x007c, 0x2011, 0x0201, 0x2009,
-       0x003c, 0x2204, 0xa005, 0x00c0, 0x1b21, 0x8109, 0x00c0, 0x1b19,
-       0x007c, 0x007c, 0x1078, 0x1b15, 0x0040, 0x1b4a, 0x7908, 0xd1ec,
-       0x00c0, 0x1b3a, 0x1078, 0x1b81, 0x0040, 0x1b3a, 0x7803, 0x0009,
-       0x7904, 0xd1fc, 0x0040, 0x1b30, 0x7803, 0x0006, 0x1078, 0x1b15,
-       0x0040, 0x1b4a, 0x780c, 0xd0a4, 0x00c0, 0x1b4a, 0x7007, 0x0000,
-       0x1078, 0x1b81, 0x0040, 0x1b4c, 0x7803, 0x0019, 0x7003, 0x0003,
-       0x0078, 0x1b4c, 0x1078, 0x1ac6, 0x007c, 0x0e7e, 0x2071, 0x0200,
-       0x7808, 0xa084, 0xf000, 0xa10d, 0x1078, 0x1af7, 0x2019, 0x5000,
-       0x8319, 0x0040, 0x1b6b, 0x2001, 0xa602, 0x2004, 0xa086, 0x0000,
-       0x0040, 0x1b6b, 0x2001, 0x0021, 0xd0fc, 0x0040, 0x1b58, 0x1078,
-       0x1e5d, 0x0078, 0x1b56, 0x20e1, 0x7000, 0x7324, 0x7420, 0x7028,
-       0x7028, 0x7426, 0x7037, 0x0001, 0x810f, 0x712e, 0x702f, 0x0100,
-       0x7037, 0x0008, 0x7326, 0x7422, 0x2001, 0x0138, 0x2202, 0x0e7f,
-       0x007c, 0x7908, 0xa18c, 0x0fff, 0xa182, 0x0009, 0x0048, 0x1b8c,
-       0xa085, 0x0001, 0x0078, 0x1b9e, 0x2001, 0x020a, 0x81ff, 0x0040,
-       0x1b97, 0x20e1, 0x6000, 0x200c, 0x200c, 0x200c, 0x200c, 0x20e1,
-       0x7000, 0x200c, 0x200c, 0x7003, 0x0000, 0xa006, 0x007c, 0x7c20,
-       0x7d24, 0x7e30, 0x7f34, 0x700c, 0x7110, 0xa106, 0x0040, 0x1c24,
-       0x7004, 0x017e, 0x210c, 0xa106, 0x017f, 0x0040, 0x1c24, 0x0d7e,
-       0x0c7e, 0x216c, 0x2d00, 0xa005, 0x0040, 0x1c22, 0x6824, 0xd0d4,
-       0x00c0, 0x1c22, 0x6810, 0x2068, 0x6850, 0xd0fc, 0x0040, 0x1bec,
-       0x8108, 0x2104, 0x6b2c, 0xa306, 0x00c0, 0x1c22, 0x8108, 0x2104,
-       0x6a28, 0xa206, 0x00c0, 0x1c22, 0x6850, 0xc0fc, 0xc0f5, 0x6852,
-       0x686c, 0x7822, 0x6870, 0x7826, 0x681c, 0x7832, 0x6820, 0x7836,
-       0x6818, 0x2060, 0x6034, 0xd09c, 0x0040, 0x1be7, 0x6830, 0x2004,
-       0xac68, 0x6808, 0x783a, 0x680c, 0x783e, 0x0078, 0x1c20, 0xa006,
-       0x783a, 0x783e, 0x0078, 0x1c20, 0x8108, 0x2104, 0xa005, 0x00c0,
-       0x1c22, 0x8108, 0x2104, 0xa005, 0x00c0, 0x1c22, 0x6850, 0xc0f5,
-       0x6852, 0x6830, 0x2004, 0x6918, 0xa160, 0xa180, 0x000d, 0x2004,
-       0xd09c, 0x00c0, 0x1c12, 0x6008, 0x7822, 0x686e, 0x600c, 0x7826,
-       0x6872, 0x6000, 0x7832, 0x6004, 0x7836, 0xa006, 0x783a, 0x783e,
-       0x0078, 0x1c20, 0x6010, 0x7822, 0x686e, 0x6014, 0x7826, 0x6872,
-       0x6000, 0x7832, 0x6004, 0x7836, 0x6008, 0x783a, 0x600c, 0x783e,
-       0x7803, 0x0011, 0x0c7f, 0x0d7f, 0x007c, 0x0f7e, 0x0e7e, 0x017e,
-       0x027e, 0x2071, 0xa5e1, 0x2079, 0x0030, 0x2011, 0x0050, 0x7000,
-       0xa086, 0x0000, 0x0040, 0x1c4d, 0x8211, 0x0040, 0x1c4b, 0x2001,
-       0x0005, 0x2004, 0xd08c, 0x0040, 0x1c34, 0x7904, 0xa18c, 0x0780,
-       0x017e, 0x1078, 0x18e2, 0x017f, 0x81ff, 0x00c0, 0x1c4b, 0x2011,
-       0x0050, 0x0078, 0x1c2f, 0xa085, 0x0001, 0x027f, 0x017f, 0x0e7f,
-       0x0f7f, 0x007c, 0x7803, 0x0004, 0x2009, 0x0064, 0x7804, 0xd0ac,
-       0x0040, 0x1ca3, 0x8109, 0x00c0, 0x1c56, 0x2009, 0x0100, 0x210c,
-       0xa18a, 0x0003, 0x1048, 0x1328, 0x1078, 0x1f75, 0x0e7e, 0x0f7e,
-       0x2071, 0xa5d0, 0x2079, 0x0010, 0x7004, 0xa086, 0x0000, 0x0040,
-       0x1c9b, 0x7800, 0x007e, 0x7820, 0x007e, 0x7830, 0x007e, 0x7834,
-       0x007e, 0x7838, 0x007e, 0x783c, 0x007e, 0x7803, 0x0004, 0x7823,
-       0x0000, 0x0005, 0x0005, 0x2079, 0x0030, 0x7804, 0xd0ac, 0x10c0,
-       0x1328, 0x2079, 0x0010, 0x007f, 0x783e, 0x007f, 0x783a, 0x007f,
-       0x7836, 0x007f, 0x7832, 0x007f, 0x7822, 0x007f, 0x7802, 0x0f7f,
-       0x0e7f, 0x0078, 0x1ca1, 0x0f7f, 0x0e7f, 0x7804, 0xd0ac, 0x10c0,
-       0x1328, 0x1078, 0x61d3, 0x007c, 0x0e7e, 0x2071, 0xa602, 0x7003,
-       0x0000, 0x0e7f, 0x007c, 0x0d7e, 0xa280, 0x0004, 0x206c, 0x694c,
-       0xd1dc, 0x00c0, 0x1d26, 0x6934, 0xa184, 0x0007, 0x0079, 0x1cb8,
-       0x1cc0, 0x1d11, 0x1cc0, 0x1cc0, 0x1cc0, 0x1cf6, 0x1cd3, 0x1cc2,
-       0x1078, 0x1328, 0x684c, 0xd0b4, 0x0040, 0x1e34, 0x6860, 0x682e,
-       0x6816, 0x685c, 0x682a, 0x6812, 0x687c, 0x680a, 0x6880, 0x680e,
-       0x6958, 0x0078, 0x1d19, 0x6834, 0xa084, 0x00ff, 0xa086, 0x001e,
-       0x00c0, 0x1cc0, 0x684c, 0xd0b4, 0x0040, 0x1e34, 0x6860, 0x682e,
-       0x6816, 0x685c, 0x682a, 0x6812, 0x687c, 0x680a, 0x6880, 0x680e,
-       0x6804, 0x681a, 0xa080, 0x000d, 0x2004, 0xa084, 0x000f, 0xa080,
-       0x2015, 0x2004, 0x6832, 0x6958, 0x0078, 0x1d22, 0xa18c, 0x00ff,
-       0xa186, 0x0015, 0x00c0, 0x1d26, 0x684c, 0xd0b4, 0x0040, 0x1e34,
-       0x6804, 0x681a, 0xa080, 0x000d, 0x2004, 0xa084, 0x000f, 0xa080,
-       0x2015, 0x2004, 0x6832, 0x6958, 0xa006, 0x682e, 0x682a, 0x0078,
-       0x1d22, 0x684c, 0xd0b4, 0x0040, 0x18bc, 0x6958, 0xa006, 0x682e,
-       0x682a, 0x2d00, 0x681a, 0x6834, 0xa084, 0x000f, 0xa080, 0x2015,
-       0x2004, 0x6832, 0x6926, 0x684c, 0xc0dd, 0x684e, 0x0d7f, 0x007c,
-       0x0f7e, 0x2079, 0x0020, 0x7804, 0xd0fc, 0x10c0, 0x1e5d, 0x0e7e,
-       0x0d7e, 0x2071, 0xa602, 0x7000, 0xa005, 0x00c0, 0x1dab, 0x0c7e,
-       0x7206, 0xa280, 0x0004, 0x205c, 0x7004, 0x2068, 0x7803, 0x0004,
-       0x6818, 0x0d7e, 0x2068, 0x686c, 0x7812, 0x6890, 0x0f7e, 0x20e1,
-       0x9040, 0x2079, 0x0200, 0x781a, 0x2079, 0x0100, 0x8004, 0x78d6,
-       0x0f7f, 0x0d7f, 0x2b68, 0x6824, 0x2050, 0x6818, 0x2060, 0x6830,
-       0x2040, 0x6034, 0xa0cc, 0x000f, 0x6908, 0x2001, 0x04fd, 0x2004,
-       0xa086, 0x0007, 0x0040, 0x1d6d, 0xa184, 0x0007, 0x0040, 0x1d6d,
-       0x017e, 0x2009, 0x0008, 0xa102, 0x017f, 0xa108, 0x791a, 0x7116,
-       0x701e, 0x680c, 0xa081, 0x0000, 0x781e, 0x701a, 0xa006, 0x700e,
-       0x7012, 0x7004, 0x692c, 0x6814, 0xa106, 0x00c0, 0x1d84, 0x6928,
-       0x6810, 0xa106, 0x0040, 0x1d91, 0x037e, 0x047e, 0x6b14, 0x6c10,
-       0x1078, 0x2035, 0x047f, 0x037f, 0x0040, 0x1d91, 0x0c7f, 0x0078,
-       0x1dab, 0x8aff, 0x00c0, 0x1d99, 0x0c7f, 0xa085, 0x0001, 0x0078,
-       0x1dab, 0x127e, 0x2091, 0x8000, 0x2079, 0x0020, 0x2009, 0x0001,
-       0x1078, 0x1daf, 0x0040, 0x1da8, 0x2009, 0x0001, 0x1078, 0x1daf,
-       0x127f, 0x0c7f, 0xa006, 0x0d7f, 0x0e7f, 0x0f7f, 0x007c, 0x077e,
-       0x067e, 0x057e, 0x047e, 0x037e, 0x027e, 0x8aff, 0x0040, 0x1e2d,
-       0x700c, 0x7214, 0xa23a, 0x7010, 0x7218, 0xa203, 0x0048, 0x1e2c,
-       0xa705, 0x0040, 0x1e2c, 0xa03e, 0x2730, 0x6850, 0xd0fc, 0x00c0,
-       0x1ddf, 0x0d7e, 0x2804, 0xac68, 0x2900, 0x0079, 0x1dcf, 0x1e0e,
-       0x1def, 0x1def, 0x1e0e, 0x1e0e, 0x1e06, 0x1e0e, 0x1def, 0x1e0e,
-       0x1df5, 0x1df5, 0x1e0e, 0x1e0e, 0x1e0e, 0x1dfd, 0x1df5, 0xc0fc,
-       0x6852, 0x6b6c, 0x6a70, 0x6d1c, 0x6c20, 0xd99c, 0x0040, 0x1e12,
-       0x0d7e, 0x2804, 0xac68, 0x6f08, 0x6e0c, 0x0078, 0x1e11, 0x6b08,
-       0x6a0c, 0x6d00, 0x6c04, 0x0078, 0x1e11, 0x6b10, 0x6a14, 0x6d00,
-       0x6c04, 0x6f08, 0x6e0c, 0x0078, 0x1e11, 0x0d7f, 0x0d7e, 0x6834,
-       0xa084, 0x00ff, 0xa086, 0x001e, 0x00c0, 0x1e0e, 0x0d7f, 0x1078,
-       0x1fd1, 0x00c0, 0x1db5, 0xa00e, 0x0078, 0x1e2d, 0x0d7f, 0x1078,
-       0x1328, 0x0d7f, 0x7b22, 0x7a26, 0x7d32, 0x7c36, 0x7f3a, 0x7e3e,
-       0x7902, 0x7000, 0x8000, 0x7002, 0x6828, 0xa300, 0x682a, 0x682c,
-       0xa201, 0x682e, 0x700c, 0xa300, 0x700e, 0x7010, 0xa201, 0x7012,
-       0x1078, 0x1fd1, 0x0078, 0x1e2d, 0xa006, 0x027f, 0x037f, 0x047f,
-       0x057f, 0x067f, 0x077f, 0x007c, 0x1078, 0x1328, 0x027e, 0x2001,
-       0x0105, 0x2003, 0x0010, 0x20e1, 0x9040, 0x7803, 0x0004, 0x7003,
-       0x0000, 0x7004, 0x2060, 0x0d7e, 0x6010, 0x2068, 0x1078, 0x8a44,
-       0x0040, 0x1e4d, 0x6850, 0xc0bd, 0x6852, 0x0d7f, 0x1078, 0x8758,
-       0x20e1, 0x9040, 0x1078, 0x719a, 0x2011, 0x0000, 0x1078, 0x6efc,
-       0x1078, 0x61d3, 0x027f, 0x0078, 0x1f29, 0x127e, 0x2091, 0x2200,
-       0x007e, 0x017e, 0x0f7e, 0x0e7e, 0x0d7e, 0x0c7e, 0x2079, 0x0020,
-       0x2071, 0xa602, 0x2b68, 0x6818, 0x2060, 0x7904, 0x7803, 0x0002,
-       0xa184, 0x0700, 0x00c0, 0x1e36, 0x7000, 0x0079, 0x1e77, 0x1f29,
-       0x1e7b, 0x1ef6, 0x1f27, 0x8001, 0x7002, 0xd19c, 0x00c0, 0x1e8f,
-       0x8aff, 0x0040, 0x1eae, 0x2009, 0x0001, 0x1078, 0x1daf, 0x0040,
-       0x1f29, 0x2009, 0x0001, 0x1078, 0x1daf, 0x0078, 0x1f29, 0x7803,
-       0x0004, 0xd194, 0x0040, 0x1e9f, 0x6850, 0xc0fc, 0x6852, 0x8aff,
-       0x00c0, 0x1ea4, 0x684c, 0xc0f5, 0x684e, 0x0078, 0x1ea4, 0x1078,
-       0x1fea, 0x6850, 0xc0fd, 0x6852, 0x2a00, 0x6826, 0x2c00, 0x681a,
-       0x2800, 0x6832, 0x7003, 0x0000, 0x0078, 0x1f29, 0x711c, 0x81ff,
-       0x0040, 0x1ec4, 0x7918, 0x7922, 0x7827, 0x0000, 0x7803, 0x0001,
-       0x7000, 0x8000, 0x7002, 0x700c, 0xa100, 0x700e, 0x7010, 0xa081,
-       0x0000, 0x7012, 0x0078, 0x1f29, 0x0f7e, 0x027e, 0x781c, 0x007e,
-       0x7818, 0x007e, 0x2079, 0x0100, 0x7a14, 0xa284, 0x0004, 0xa085,
-       0x0012, 0x7816, 0x037e, 0x2019, 0x1000, 0x8319, 0x1040, 0x1328,
-       0x7820, 0xd0bc, 0x00c0, 0x1ed5, 0x037f, 0x79c8, 0x007f, 0xa102,
-       0x017f, 0x007e, 0x017e, 0x79c4, 0x007f, 0xa103, 0x78c6, 0x007f,
-       0x78ca, 0xa284, 0x0004, 0xa085, 0x0012, 0x7816, 0x027f, 0x0f7f,
-       0x7803, 0x0008, 0x7003, 0x0000, 0x0078, 0x1f29, 0x8001, 0x7002,
-       0xd194, 0x0040, 0x1f0b, 0x7804, 0xd0fc, 0x00c0, 0x1e6d, 0xd19c,
-       0x00c0, 0x1f25, 0x8aff, 0x0040, 0x1f29, 0x2009, 0x0001, 0x1078,
-       0x1daf, 0x0078, 0x1f29, 0x027e, 0x037e, 0x6b28, 0x6a2c, 0x1078,
-       0x1fea, 0x0d7e, 0x2804, 0xac68, 0x6034, 0xd09c, 0x00c0, 0x1f1e,
-       0x6808, 0xa31a, 0x680c, 0xa213, 0x0078, 0x1f22, 0x6810, 0xa31a,
-       0x6814, 0xa213, 0x0d7f, 0x0078, 0x1e9f, 0x0078, 0x1e9f, 0x1078,
-       0x1328, 0x0c7f, 0x0d7f, 0x0e7f, 0x0f7f, 0x017f, 0x007f, 0x127f,
-       0x007c, 0x0f7e, 0x0e7e, 0x2071, 0xa602, 0x7000, 0xa086, 0x0000,
-       0x0040, 0x1f72, 0x2079, 0x0020, 0x017e, 0x2009, 0x0207, 0x210c,
-       0xd194, 0x0040, 0x1f4f, 0x2009, 0x020c, 0x210c, 0xa184, 0x0003,
-       0x0040, 0x1f4f, 0x20e1, 0x9040, 0x2001, 0x020c, 0x2102, 0x2009,
-       0x0206, 0x2104, 0x2009, 0x0203, 0x210c, 0xa106, 0x00c0, 0x1f5a,
-       0x20e1, 0x9040, 0x7804, 0xd0fc, 0x0040, 0x1f3d, 0x1078, 0x1e5d,
-       0x7000, 0xa086, 0x0000, 0x00c0, 0x1f3d, 0x017f, 0x7803, 0x0004,
-       0x7804, 0xd0ac, 0x00c0, 0x1f68, 0x20e1, 0x9040, 0x7803, 0x0002,
-       0x7003, 0x0000, 0x0e7f, 0x0f7f, 0x007c, 0x027e, 0x0c7e, 0x0d7e,
-       0x0e7e, 0x0f7e, 0x2071, 0xa602, 0x2079, 0x0020, 0x7000, 0xa086,
-       0x0000, 0x0040, 0x1fae, 0x7004, 0x2060, 0x6010, 0x2068, 0x1078,
-       0x8a44, 0x0040, 0x1f98, 0x6850, 0xc0b5, 0x6852, 0x680c, 0x7a1c,
-       0xa206, 0x00c0, 0x1f98, 0x6808, 0x7a18, 0xa206, 0x0040, 0x1fb4,
-       0x2001, 0x0105, 0x2003, 0x0010, 0x20e1, 0x9040, 0x7803, 0x0004,
-       0x7003, 0x0000, 0x7004, 0x2060, 0x1078, 0x8758, 0x20e1, 0x9040,
-       0x1078, 0x719a, 0x2011, 0x0000, 0x1078, 0x6efc, 0x0f7f, 0x0e7f,
-       0x0d7f, 0x0c7f, 0x027f, 0x007c, 0x6810, 0x6a14, 0xa205, 0x00c0,
-       0x1f98, 0x684c, 0xc0dc, 0x684e, 0x2c10, 0x1078, 0x1cab, 0x2001,
-       0x0105, 0x2003, 0x0010, 0x20e1, 0x9040, 0x7803, 0x0004, 0x7003,
-       0x0000, 0x2069, 0xa5ab, 0x6833, 0x0000, 0x683f, 0x0000, 0x0078,
-       0x1fae, 0x8840, 0x2804, 0xa005, 0x00c0, 0x1fe5, 0x6004, 0xa005,
-       0x0040, 0x1fe7, 0x681a, 0x2060, 0x6034, 0xa084, 0x000f, 0xa080,
-       0x2015, 0x2044, 0x88ff, 0x1040, 0x1328, 0x8a51, 0x007c, 0x2051,
-       0x0000, 0x007c, 0x8a50, 0x8841, 0x2804, 0xa005, 0x00c0, 0x2004,
-       0x2c00, 0xad06, 0x0040, 0x1ff9, 0x6000, 0xa005, 0x00c0, 0x1ff9,
-       0x2d00, 0x2060, 0x681a, 0x6034, 0xa084, 0x000f, 0xa080, 0x2025,
-       0x2044, 0x88ff, 0x1040, 0x1328, 0x007c, 0x0000, 0x0011, 0x0015,
-       0x0019, 0x001d, 0x0021, 0x0025, 0x0029, 0x0000, 0x000f, 0x0015,
-       0x001b, 0x0021, 0x0027, 0x0000, 0x0000, 0x0000, 0x200a, 0x2006,
-       0x0000, 0x0000, 0x2014, 0x0000, 0x200a, 0x0000, 0x2011, 0x200e,
-       0x0000, 0x0000, 0x0000, 0x2014, 0x2011, 0x0000, 0x200c, 0x200c,
-       0x0000, 0x0000, 0x2014, 0x0000, 0x200c, 0x0000, 0x2012, 0x2012,
-       0x0000, 0x0000, 0x0000, 0x2014, 0x2012, 0x0a7e, 0x097e, 0x087e,
-       0x6b2e, 0x6c2a, 0x6858, 0xa055, 0x0040, 0x20d8, 0x2d60, 0x6034,
-       0xa0cc, 0x000f, 0xa9c0, 0x2015, 0xa986, 0x0007, 0x0040, 0x2050,
-       0xa986, 0x000e, 0x0040, 0x2050, 0xa986, 0x000f, 0x00c0, 0x2054,
-       0x605c, 0xa422, 0x6060, 0xa31a, 0x2804, 0xa045, 0x00c0, 0x2062,
-       0x0050, 0x205c, 0x0078, 0x20d8, 0x6004, 0xa065, 0x0040, 0x20d8,
-       0x0078, 0x203f, 0x2804, 0xa005, 0x0040, 0x2080, 0xac68, 0xd99c,
-       0x00c0, 0x2070, 0x6808, 0xa422, 0x680c, 0xa31b, 0x0078, 0x2074,
-       0x6810, 0xa422, 0x6814, 0xa31b, 0x0048, 0x209f, 0x2300, 0xa405,
-       0x0040, 0x2086, 0x8a51, 0x0040, 0x20d8, 0x8840, 0x0078, 0x2062,
-       0x6004, 0xa065, 0x0040, 0x20d8, 0x0078, 0x203f, 0x8a51, 0x0040,
-       0x20d8, 0x8840, 0x2804, 0xa005, 0x00c0, 0x2099, 0x6004, 0xa065,
-       0x0040, 0x20d8, 0x6034, 0xa0cc, 0x000f, 0xa9c0, 0x2015, 0x2804,
-       0x2040, 0x2b68, 0x6850, 0xc0fc, 0x6852, 0x0078, 0x20cc, 0x8422,
-       0x8420, 0x831a, 0xa399, 0x0000, 0x0d7e, 0x2b68, 0x6c6e, 0x6b72,
-       0x0d7f, 0xd99c, 0x00c0, 0x20ba, 0x6908, 0x2400, 0xa122, 0x690c,
-       0x2300, 0xa11b, 0x1048, 0x1328, 0x6800, 0xa420, 0x6804, 0xa319,
-       0x0078, 0x20c6, 0x6910, 0x2400, 0xa122, 0x6914, 0x2300, 0xa11b,
-       0x1048, 0x1328, 0x6800, 0xa420, 0x6804, 0xa319, 0x2b68, 0x6c1e,
-       0x6b22, 0x6850, 0xc0fd, 0x6852, 0x2c00, 0x681a, 0x2800, 0x6832,
-       0x2a00, 0x6826, 0x007f, 0x007f, 0x007f, 0xa006, 0x0078, 0x20dd,
-       0x087f, 0x097f, 0x0a7f, 0xa085, 0x0001, 0x007c, 0x2001, 0x0005,
-       0x2004, 0xa084, 0x0007, 0x0079, 0x20e5, 0x20ed, 0x20ee, 0x20f1,
-       0x20f4, 0x20f9, 0x20fc, 0x2101, 0x2106, 0x007c, 0x1078, 0x1e5d,
-       0x007c, 0x1078, 0x18e2, 0x007c, 0x1078, 0x18e2, 0x1078, 0x1e5d,
-       0x007c, 0x1078, 0x14b0, 0x007c, 0x1078, 0x1e5d, 0x1078, 0x14b0,
-       0x007c, 0x1078, 0x18e2, 0x1078, 0x14b0, 0x007c, 0x1078, 0x18e2,
-       0x1078, 0x1e5d, 0x1078, 0x14b0, 0x007c, 0x127e, 0x2091, 0x2300,
-       0x2079, 0x0200, 0x2071, 0xa880, 0x2069, 0xa300, 0x2009, 0x0004,
-       0x7912, 0x7817, 0x0004, 0x1078, 0x24b5, 0x781b, 0x0002, 0x20e1,
-       0x8700, 0x127f, 0x007c, 0x127e, 0x2091, 0x2300, 0x781c, 0xa084,
-       0x0007, 0x0079, 0x212b, 0x214f, 0x2133, 0x2137, 0x213b, 0x2141,
-       0x2145, 0x2149, 0x214d, 0x1078, 0x5372, 0x0078, 0x214f, 0x1078,
-       0x53b3, 0x0078, 0x214f, 0x1078, 0x5372, 0x1078, 0x53b3, 0x0078,
-       0x214f, 0x1078, 0x2151, 0x0078, 0x214f, 0x1078, 0x2151, 0x0078,
-       0x214f, 0x1078, 0x2151, 0x0078, 0x214f, 0x1078, 0x2151, 0x127f,
-       0x007c, 0x007e, 0x017e, 0x027e, 0x7930, 0xa184, 0x0003, 0x0040,
-       0x215d, 0x20e1, 0x9040, 0x0078, 0x2186, 0xa184, 0x0030, 0x0040,
-       0x216e, 0x6a00, 0xa286, 0x0003, 0x00c0, 0x2168, 0x0078, 0x216a,
-       0x1078, 0x4171, 0x20e1, 0x9010, 0x0078, 0x2186, 0xa184, 0x00c0,
-       0x0040, 0x2180, 0x0e7e, 0x037e, 0x047e, 0x057e, 0x2071, 0xa5e1,
-       0x1078, 0x1ac6, 0x057f, 0x047f, 0x037f, 0x0e7f, 0x0078, 0x2186,
-       0xa184, 0x0300, 0x0040, 0x2186, 0x20e1, 0x9020, 0x7932, 0x027f,
-       0x017f, 0x007f, 0x007c, 0x017e, 0x0e7e, 0x0f7e, 0x2071, 0xa300,
-       0x7128, 0x2001, 0xa58f, 0x2102, 0x2001, 0xa597, 0x2102, 0xa182,
-       0x0211, 0x00c8, 0x219f, 0x2009, 0x0008, 0x0078, 0x21c9, 0xa182,
-       0x0259, 0x00c8, 0x21a7, 0x2009, 0x0007, 0x0078, 0x21c9, 0xa182,
-       0x02c1, 0x00c8, 0x21af, 0x2009, 0x0006, 0x0078, 0x21c9, 0xa182,
-       0x0349, 0x00c8, 0x21b7, 0x2009, 0x0005, 0x0078, 0x21c9, 0xa182,
-       0x0421, 0x00c8, 0x21bf, 0x2009, 0x0004, 0x0078, 0x21c9, 0xa182,
-       0x0581, 0x00c8, 0x21c7, 0x2009, 0x0003, 0x0078, 0x21c9, 0x2009,
-       0x0002, 0x2079, 0x0200, 0x7912, 0x7817, 0x0004, 0x1078, 0x24b5,
-       0x0f7f, 0x0e7f, 0x017f, 0x007c, 0x127e, 0x2091, 0x2200, 0x2061,
-       0x0100, 0x2071, 0xa300, 0x6024, 0x6026, 0x6053, 0x0030, 0x6033,
-       0x00ef, 0x60e7, 0x0000, 0x60eb, 0x00ef, 0x60e3, 0x0008, 0x604b,
-       0xf7f7, 0x6043, 0x0000, 0x602f, 0x0080, 0x602f, 0x0000, 0x6007,
-       0x0eaf, 0x600f, 0x00ff, 0x602b, 0x002f, 0x127f, 0x007c, 0x2001,
-       0xa32f, 0x2003, 0x0000, 0x2001, 0xa32e, 0x2003, 0x0001, 0x007c,
-       0x127e, 0x2091, 0x2200, 0x007e, 0x017e, 0x027e, 0x6124, 0xa184,
-       0x002c, 0x00c0, 0x220f, 0xa184, 0x0007, 0x0079, 0x2215, 0xa195,
-       0x0004, 0xa284, 0x0007, 0x0079, 0x2215, 0x2241, 0x221d, 0x2221,
-       0x2225, 0x222b, 0x222f, 0x2235, 0x223b, 0x1078, 0x5ad2, 0x0078,
-       0x2241, 0x1078, 0x5bc1, 0x0078, 0x2241, 0x1078, 0x5bc1, 0x1078,
-       0x5ad2, 0x0078, 0x2241, 0x1078, 0x2246, 0x0078, 0x2241, 0x1078,
-       0x5ad2, 0x1078, 0x2246, 0x0078, 0x2241, 0x1078, 0x5bc1, 0x1078,
-       0x2246, 0x0078, 0x2241, 0x1078, 0x5bc1, 0x1078, 0x5ad2, 0x1078,
-       0x2246, 0x027f, 0x017f, 0x007f, 0x127f, 0x007c, 0x6124, 0xd1ac,
-       0x0040, 0x2342, 0x017e, 0x047e, 0x0c7e, 0x644c, 0xa486, 0xf0f0,
-       0x00c0, 0x2259, 0x2061, 0x0100, 0x644a, 0x6043, 0x0090, 0x6043,
-       0x0010, 0x74c2, 0xa48c, 0xff00, 0x7034, 0xd084, 0x0040, 0x2271,
-       0xa186, 0xf800, 0x00c0, 0x2271, 0x7038, 0xd084, 0x00c0, 0x2271,
-       0xc085, 0x703a, 0x037e, 0x2418, 0x2011, 0x8016, 0x1078, 0x3579,
-       0x037f, 0xa196, 0xff00, 0x0040, 0x22b3, 0x6030, 0xa084, 0x00ff,
-       0x810f, 0xa116, 0x0040, 0x22b3, 0x7130, 0xd184, 0x00c0, 0x22b3,
-       0x2011, 0xa352, 0x2214, 0xd2ec, 0x0040, 0x228e, 0xc18d, 0x7132,
-       0x2011, 0xa352, 0x2214, 0xd2ac, 0x00c0, 0x22b3, 0x6240, 0xa294,
-       0x0010, 0x0040, 0x229a, 0x6248, 0xa294, 0xff00, 0xa296, 0xff00,
-       0x0040, 0x22b3, 0x7030, 0xd08c, 0x0040, 0x2305, 0x7034, 0xd08c,
-       0x00c0, 0x22aa, 0x2001, 0xa30c, 0x200c, 0xd1ac, 0x00c0, 0x2305,
-       0xc1ad, 0x2102, 0x037e, 0x73c0, 0x2011, 0x8013, 0x1078, 0x3579,
-       0x037f, 0x0078, 0x2305, 0x7034, 0xd08c, 0x00c0, 0x22bf, 0x2001,
-       0xa30c, 0x200c, 0xd1ac, 0x00c0, 0x2305, 0xc1ad, 0x2102, 0x037e,
-       0x73c0, 0x2011, 0x8013, 0x1078, 0x3579, 0x037f, 0x7130, 0xc185,
-       0x7132, 0x2011, 0xa352, 0x220c, 0xd1a4, 0x0040, 0x22e9, 0x017e,
-       0x2009, 0x0001, 0x2011, 0x0100, 0x1078, 0x5a6d, 0x2019, 0x000e,
-       0x1078, 0x9e3b, 0xa484, 0x00ff, 0xa080, 0x293f, 0x200c, 0xa18c,
-       0xff00, 0x810f, 0x8127, 0xa006, 0x2009, 0x000e, 0x1078, 0x9ec0,
-       0x017f, 0xd1ac, 0x00c0, 0x22f6, 0x017e, 0x2009, 0x0000, 0x2019,
-       0x0004, 0x1078, 0x27e2, 0x017f, 0x0078, 0x2305, 0x157e, 0x20a9,
-       0x007f, 0x2009, 0x0000, 0x1078, 0x4501, 0x00c0, 0x2301, 0x1078,
-       0x4235, 0x8108, 0x00f0, 0x22fb, 0x157f, 0x0c7f, 0x047f, 0x0f7e,
-       0x2079, 0xa5be, 0x783c, 0xa086, 0x0000, 0x0040, 0x2317, 0x6027,
-       0x0004, 0x783f, 0x0000, 0x2079, 0x0140, 0x7803, 0x0000, 0x0f7f,
-       0x2011, 0x0003, 0x1078, 0x6ef2, 0x2011, 0x0002, 0x1078, 0x6efc,
-       0x1078, 0x6dda, 0x1078, 0x595a, 0x037e, 0x2019, 0x0000, 0x1078,
-       0x6e6c, 0x037f, 0x60e3, 0x0000, 0x017f, 0x2001, 0xa300, 0x2014,
-       0xa296, 0x0004, 0x00c0, 0x233a, 0xd19c, 0x00c0, 0x233a, 0x6228,
-       0xc29d, 0x622a, 0x2003, 0x0001, 0x2001, 0xa321, 0x2003, 0x0000,
-       0x6027, 0x0020, 0xd194, 0x0040, 0x2426, 0x0f7e, 0x2079, 0xa5be,
-       0x783c, 0xa086, 0x0001, 0x00c0, 0x2366, 0x017e, 0x6027, 0x0004,
-       0x783f, 0x0000, 0x2079, 0x0140, 0x7803, 0x1000, 0x7803, 0x0000,
-       0x2079, 0xa5ab, 0x7807, 0x0000, 0x7833, 0x0000, 0x1078, 0x6109,
-       0x1078, 0x61d3, 0x017f, 0x0f7f, 0x0078, 0x2426, 0x0f7f, 0x017e,
-       0x3900, 0xa082, 0xa6cd, 0x00c8, 0x2371, 0x017e, 0x1078, 0x728a,
-       0x017f, 0x6220, 0xd2b4, 0x0040, 0x23dc, 0x1078, 0x595a, 0x1078,
-       0x6c41, 0x6027, 0x0004, 0x0f7e, 0x2019, 0xa5b4, 0x2304, 0xa07d,
-       0x0040, 0x23b2, 0x7804, 0xa086, 0x0032, 0x00c0, 0x23b2, 0x0d7e,
-       0x0c7e, 0x0e7e, 0x2069, 0x0140, 0x618c, 0x6288, 0x7818, 0x608e,
-       0x7808, 0x608a, 0x6043, 0x0002, 0x2001, 0x0003, 0x8001, 0x00c0,
-       0x2396, 0x6043, 0x0000, 0x6803, 0x1000, 0x6803, 0x0000, 0x618e,
-       0x628a, 0x1078, 0x6010, 0x1078, 0x6109, 0x7810, 0x2070, 0x7037,
-       0x0103, 0x2f60, 0x1078, 0x753d, 0x0e7f, 0x0c7f, 0x0d7f, 0x0f7f,
-       0x017f, 0x007c, 0x0f7f, 0x0d7e, 0x2069, 0x0140, 0x6804, 0xa084,
-       0x4000, 0x0040, 0x23bf, 0x6803, 0x1000, 0x6803, 0x0000, 0x0d7f,
-       0x0c7e, 0x2061, 0xa5ab, 0x6028, 0xa09a, 0x00c8, 0x00c8, 0x23cf,
-       0x8000, 0x602a, 0x0c7f, 0x1078, 0x6c33, 0x0078, 0x2425, 0x2019,
-       0xa5b4, 0x2304, 0xa065, 0x0040, 0x23d9, 0x2009, 0x0027, 0x1078,
-       0x756c, 0x0c7f, 0x0078, 0x2425, 0xd2bc, 0x0040, 0x2425, 0x1078,
-       0x5967, 0x6017, 0x0010, 0x6027, 0x0004, 0x0d7e, 0x2069, 0x0140,
-       0x6804, 0xa084, 0x4000, 0x0040, 0x23f1, 0x6803, 0x1000, 0x6803,
-       0x0000, 0x0d7f, 0x0c7e, 0x2061, 0xa5ab, 0x6044, 0xa09a, 0x00c8,
-       0x00c8, 0x2414, 0x8000, 0x6046, 0x603c, 0x0c7f, 0xa005, 0x0040,
-       0x2425, 0x2009, 0x07d0, 0x1078, 0x595f, 0xa080, 0x0007, 0x2004,
-       0xa086, 0x0006, 0x00c0, 0x2410, 0x6017, 0x0012, 0x0078, 0x2425,
-       0x6017, 0x0016, 0x0078, 0x2425, 0x037e, 0x2019, 0x0001, 0x1078,
-       0x6e6c, 0x037f, 0x2019, 0xa5ba, 0x2304, 0xa065, 0x0040, 0x2424,
-       0x2009, 0x004f, 0x1078, 0x756c, 0x0c7f, 0x017f, 0xd19c, 0x0040,
-       0x247c, 0x7034, 0xd0ac, 0x00c0, 0x2457, 0x017e, 0x157e, 0x6027,
-       0x0008, 0x602f, 0x0020, 0x20a9, 0x000a, 0x00f0, 0x2435, 0x602f,
-       0x0000, 0x6150, 0xa185, 0x1400, 0x6052, 0x20a9, 0x0320, 0x00e0,
-       0x243f, 0x2091, 0x6000, 0x6020, 0xd09c, 0x00c0, 0x244e, 0x157f,
-       0x6152, 0x017f, 0x6027, 0x0008, 0x0078, 0x247c, 0x1078, 0x250d,
-       0x00f0, 0x243f, 0x157f, 0x6152, 0x017f, 0x6027, 0x0008, 0x017e,
-       0x6028, 0xc09c, 0x602a, 0x2011, 0x0003, 0x1078, 0x6ef2, 0x2011,
-       0x0002, 0x1078, 0x6efc, 0x1078, 0x6dda, 0x1078, 0x595a, 0x037e,
-       0x2019, 0x0000, 0x1078, 0x6e6c, 0x037f, 0x60e3, 0x0000, 0x1078,
-       0xa22a, 0x1078, 0xa248, 0x2001, 0xa300, 0x2003, 0x0004, 0x6027,
-       0x0008, 0x1078, 0x1246, 0x017f, 0xa18c, 0xffd0, 0x6126, 0x007c,
-       0x007e, 0x017e, 0x027e, 0x0e7e, 0x0f7e, 0x127e, 0x2091, 0x8000,
-       0x2071, 0xa300, 0x71b8, 0x70ba, 0xa116, 0x0040, 0x24ae, 0x81ff,
-       0x0040, 0x2498, 0x2011, 0x8011, 0x1078, 0x3579, 0x0078, 0x24ae,
-       0x2011, 0x8012, 0x1078, 0x3579, 0x2001, 0xa371, 0x2004, 0xd0fc,
-       0x00c0, 0x24ae, 0x037e, 0x0c7e, 0x2061, 0x0100, 0x2019, 0x0028,
-       0x2009, 0x0000, 0x1078, 0x27e2, 0x0c7f, 0x037f, 0x127f, 0x0f7f,
-       0x0e7f, 0x027f, 0x017f, 0x007f, 0x007c, 0x0c7e, 0x0f7e, 0x007e,
-       0x027e, 0x2061, 0x0100, 0xa190, 0x24d1, 0x2204, 0x60f2, 0x2011,
-       0x24de, 0x6000, 0xa082, 0x0003, 0x00c8, 0x24ca, 0x2001, 0x00ff,
-       0x0078, 0x24cb, 0x2204, 0x60ee, 0x027f, 0x007f, 0x0f7f, 0x0c7f,
-       0x007c, 0x0840, 0x0840, 0x0840, 0x0580, 0x0420, 0x0348, 0x02c0,
-       0x0258, 0x0210, 0x01a8, 0x01a8, 0x01a8, 0x01a8, 0x0140, 0x00f8,
-       0x00d0, 0x00b0, 0x00a0, 0x2028, 0xa18c, 0x00ff, 0x2130, 0xa094,
-       0xff00, 0x00c0, 0x24ee, 0x81ff, 0x0040, 0x24f2, 0x1078, 0x5623,
-       0x0078, 0x24f9, 0xa080, 0x293f, 0x200c, 0xa18c, 0xff00, 0x810f,
-       0xa006, 0x007c, 0xa080, 0x293f, 0x200c, 0xa18c, 0x00ff, 0x007c,
-       0x0c7e, 0x2061, 0xa300, 0x6030, 0x0040, 0x2509, 0xc09d, 0x0078,
-       0x250a, 0xc09c, 0x6032, 0x0c7f, 0x007c, 0x007e, 0x157e, 0x0f7e,
-       0x2079, 0x0100, 0x20a9, 0x000a, 0x7854, 0xd08c, 0x00c0, 0x251a,
-       0x00f0, 0x2514, 0x0f7f, 0x157f, 0x007f, 0x007c, 0x0c7e, 0x007e,
-       0x2061, 0x0100, 0x6030, 0x007e, 0x6048, 0x007e, 0x60e4, 0x007e,
-       0x60e8, 0x007e, 0x6050, 0x007e, 0x60f0, 0x007e, 0x60ec, 0x007e,
-       0x600c, 0x007e, 0x6004, 0x007e, 0x6028, 0x007e, 0x60e0, 0x007e,
-       0x602f, 0x0100, 0x602f, 0x0000, 0x0005, 0x0005, 0x0005, 0x0005,
-       0x602f, 0x0040, 0x602f, 0x0000, 0x007f, 0x60e2, 0x007f, 0x602a,
-       0x007f, 0x6006, 0x007f, 0x600e, 0x007f, 0x60ee, 0x007f, 0x60f2,
-       0x007f, 0x6052, 0x007f, 0x60ea, 0x007f, 0x60e6, 0x007f, 0x604a,
-       0x007f, 0x6032, 0x007f, 0x0c7f, 0x007c, 0x257d, 0x2581, 0x2585,
-       0x258b, 0x2591, 0x2597, 0x259d, 0x25a5, 0x25ad, 0x25b3, 0x25b9,
-       0x25c1, 0x25c9, 0x25d1, 0x25d9, 0x25e3, 0x25ed, 0x25ed, 0x25ed,
-       0x25ed, 0x25ed, 0x25ed, 0x25ed, 0x25ed, 0x25ed, 0x25ed, 0x25ed,
-       0x25ed, 0x25ed, 0x25ed, 0x25ed, 0x25ed, 0x107e, 0x007e, 0x0078,
-       0x2606, 0x107e, 0x007e, 0x0078, 0x2606, 0x107e, 0x007e, 0x1078,
-       0x2200, 0x0078, 0x2606, 0x107e, 0x007e, 0x1078, 0x2200, 0x0078,
-       0x2606, 0x107e, 0x007e, 0x1078, 0x20de, 0x0078, 0x2606, 0x107e,
-       0x007e, 0x1078, 0x20de, 0x0078, 0x2606, 0x107e, 0x007e, 0x1078,
-       0x2200, 0x1078, 0x20de, 0x0078, 0x2606, 0x107e, 0x007e, 0x1078,
-       0x2200, 0x1078, 0x20de, 0x0078, 0x2606, 0x107e, 0x007e, 0x1078,
-       0x2123, 0x0078, 0x2606, 0x107e, 0x007e, 0x1078, 0x2123, 0x0078,
-       0x2606, 0x107e, 0x007e, 0x1078, 0x2200, 0x1078, 0x2123, 0x0078,
-       0x2606, 0x107e, 0x007e, 0x1078, 0x2200, 0x1078, 0x2123, 0x0078,
-       0x2606, 0x107e, 0x007e, 0x1078, 0x20de, 0x1078, 0x2123, 0x0078,
-       0x2606, 0x107e, 0x007e, 0x1078, 0x20de, 0x1078, 0x2123, 0x0078,
-       0x2606, 0x107e, 0x007e, 0x1078, 0x2200, 0x1078, 0x20de, 0x1078,
-       0x2123, 0x0078, 0x2606, 0x107e, 0x007e, 0x1078, 0x2200, 0x1078,
-       0x20de, 0x1078, 0x2123, 0x0078, 0x2606, 0x0005, 0x0078, 0x25ed,
-       0xb084, 0x003c, 0x8004, 0x8004, 0x0079, 0x25f6, 0x2606, 0x2583,
-       0x2587, 0x258d, 0x2593, 0x2599, 0x259f, 0x25a7, 0x25af, 0x25b5,
-       0x25bb, 0x25c3, 0x25cb, 0x25d3, 0x25db, 0x25e5, 0x0008, 0x25f0,
-       0x007f, 0x107f, 0x2091, 0x8001, 0x007c, 0x0c7e, 0x027e, 0x047e,
-       0x2021, 0x0000, 0x1078, 0x4897, 0x00c0, 0x2705, 0x70c8, 0xd09c,
-       0x0040, 0x2624, 0xd084, 0x00c0, 0x2624, 0xd0bc, 0x00c0, 0x2705,
-       0x1078, 0x2709, 0x0078, 0x2705, 0xd094, 0x0040, 0x262b, 0x7093,
-       0xffff, 0x0078, 0x2705, 0x2001, 0x010c, 0x203c, 0x7280, 0xd284,
-       0x0040, 0x2694, 0xd28c, 0x00c0, 0x2694, 0x037e, 0x7390, 0xa38e,
-       0xffff, 0x0040, 0x263e, 0x83ff, 0x00c0, 0x2640, 0x2019, 0x0001,
-       0x8314, 0xa2e0, 0xa9c0, 0x2c04, 0xa38c, 0x0001, 0x0040, 0x264d,
-       0xa084, 0xff00, 0x8007, 0x0078, 0x264f, 0xa084, 0x00ff, 0xa70e,
-       0x0040, 0x2689, 0xa08e, 0x0000, 0x0040, 0x2689, 0xa08e, 0x00ff,
-       0x00c0, 0x2666, 0x7230, 0xd284, 0x00c0, 0x268f, 0x7280, 0xc28d,
-       0x7282, 0x7093, 0xffff, 0x037f, 0x0078, 0x2694, 0x2009, 0x0000,
-       0x1078, 0x24e3, 0x1078, 0x4499, 0x00c0, 0x268c, 0x6004, 0xa084,
-       0x00ff, 0xa086, 0x0006, 0x00c0, 0x2683, 0x7030, 0xd08c, 0x0040,
-       0x267d, 0x6000, 0xd0bc, 0x0040, 0x2683, 0x1078, 0x271f, 0x0040,
-       0x268c, 0x0078, 0x2689, 0x1078, 0x2857, 0x1078, 0x274c, 0x0040,
-       0x268c, 0x8318, 0x0078, 0x2640, 0x7392, 0x0078, 0x2691, 0x7093,
-       0xffff, 0x037f, 0x0078, 0x2705, 0xa780, 0x293f, 0x203c, 0xa7bc,
-       0xff00, 0x873f, 0x2041, 0x007e, 0x7090, 0xa096, 0xffff, 0x00c0,
-       0x26a6, 0x2009, 0x0000, 0x28a8, 0x0078, 0x26b2, 0xa812, 0x0048,
-       0x26ae, 0x2008, 0xa802, 0x20a8, 0x0078, 0x26b2, 0x7093, 0xffff,
-       0x0078, 0x2705, 0x2700, 0x157e, 0x017e, 0xa106, 0x0040, 0x26f9,
-       0xc484, 0x1078, 0x4501, 0x0040, 0x26c3, 0x1078, 0x4499, 0x00c0,
-       0x2702, 0x0078, 0x26c4, 0xc485, 0x6004, 0xa084, 0x00ff, 0xa086,
-       0x0006, 0x00c0, 0x26d3, 0x7030, 0xd08c, 0x0040, 0x26f1, 0x6000,
-       0xd0bc, 0x00c0, 0x26f1, 0x7280, 0xd28c, 0x0040, 0x26e9, 0x6004,
-       0xa084, 0x00ff, 0xa082, 0x0006, 0x0048, 0x26f9, 0xd484, 0x00c0,
-       0x26e5, 0x1078, 0x44bc, 0x0078, 0x26e7, 0x1078, 0x2921, 0x0078,
-       0x26f9, 0x1078, 0x2857, 0x1078, 0x274c, 0x0040, 0x2702, 0x0078,
-       0x26f9, 0x1078, 0x28ec, 0x0040, 0x26f9, 0x1078, 0x271f, 0x0040,
-       0x2702, 0x017f, 0x8108, 0x157f, 0x00f0, 0x26b2, 0x7093, 0xffff,
-       0x0078, 0x2705, 0x017f, 0x157f, 0x7192, 0x047f, 0x027f, 0x0c7f,
-       0x007c, 0x0c7e, 0x017e, 0x7093, 0x0000, 0x2009, 0x007e, 0x1078,
-       0x4499, 0x00c0, 0x271c, 0x1078, 0x2857, 0x1078, 0x274c, 0x0040,
-       0x271c, 0x70c8, 0xc0bd, 0x70ca, 0x017f, 0x0c7f, 0x007c, 0x017e,
-       0x077e, 0x0d7e, 0x0c7e, 0x2c68, 0x2001, 0xa356, 0x2004, 0xa084,
-       0x00ff, 0x6842, 0x1078, 0x74d7, 0x0040, 0x2747, 0x2d00, 0x601a,
-       0x601f, 0x0001, 0x2001, 0x0000, 0x1078, 0x442b, 0x2001, 0x0000,
-       0x1078, 0x443f, 0x127e, 0x2091, 0x8000, 0x708c, 0x8000, 0x708e,
-       0x127f, 0x2009, 0x0004, 0x1078, 0x756c, 0xa085, 0x0001, 0x0c7f,
-       0x0d7f, 0x077f, 0x017f, 0x007c, 0x017e, 0x077e, 0x0d7e, 0x0c7e,
-       0x2c68, 0x2001, 0xa356, 0x2004, 0xa084, 0x00ff, 0x6842, 0x1078,
-       0x74d7, 0x0040, 0x2785, 0x2d00, 0x601a, 0x6800, 0xc0c4, 0x6802,
-       0x68a0, 0xa086, 0x007e, 0x0040, 0x276e, 0x6804, 0xa084, 0x00ff,
-       0xa086, 0x0006, 0x00c0, 0x276e, 0x1078, 0x2813, 0x601f, 0x0001,
-       0x2001, 0x0000, 0x1078, 0x442b, 0x2001, 0x0002, 0x1078, 0x443f,
-       0x127e, 0x2091, 0x8000, 0x708c, 0x8000, 0x708e, 0x127f, 0x2009,
-       0x0002, 0x1078, 0x756c, 0xa085, 0x0001, 0x0c7f, 0x0d7f, 0x077f,
-       0x017f, 0x007c, 0x0c7e, 0x027e, 0x2009, 0x0080, 0x1078, 0x4499,
-       0x00c0, 0x2798, 0x1078, 0x279b, 0x0040, 0x2798, 0x70cf, 0xffff,
-       0x027f, 0x0c7f, 0x007c, 0x017e, 0x077e, 0x0d7e, 0x0c7e, 0x2c68,
-       0x1078, 0x74d7, 0x0040, 0x27bd, 0x2d00, 0x601a, 0x601f, 0x0001,
-       0x2001, 0x0000, 0x1078, 0x442b, 0x2001, 0x0002, 0x1078, 0x443f,
-       0x127e, 0x2091, 0x8000, 0x70d0, 0x8000, 0x70d2, 0x127f, 0x2009,
-       0x0002, 0x1078, 0x756c, 0xa085, 0x0001, 0x0c7f, 0x0d7f, 0x077f,
-       0x017f, 0x007c, 0x0c7e, 0x0d7e, 0x127e, 0x2091, 0x8000, 0x2009,
-       0x007f, 0x1078, 0x4499, 0x00c0, 0x27de, 0x2c68, 0x1078, 0x74d7,
-       0x0040, 0x27de, 0x2d00, 0x601a, 0x6312, 0x601f, 0x0001, 0x620a,
-       0x2009, 0x0022, 0x1078, 0x756c, 0xa085, 0x0001, 0x127f, 0x0d7f,
-       0x0c7f, 0x007c, 0x0e7e, 0x0c7e, 0x067e, 0x037e, 0x027e, 0x1078,
-       0x5d60, 0x1078, 0x5d02, 0x1078, 0x7ddf, 0x2130, 0x81ff, 0x0040,
-       0x27f7, 0x20a9, 0x007e, 0x2009, 0x0000, 0x0078, 0x27fb, 0x20a9,
-       0x007f, 0x2009, 0x0000, 0x017e, 0x1078, 0x4501, 0x00c0, 0x2804,
-       0x1078, 0x471b, 0x1078, 0x4235, 0x017f, 0x8108, 0x00f0, 0x27fb,
-       0x86ff, 0x00c0, 0x280d, 0x1078, 0x119b, 0x027f, 0x037f, 0x067f,
-       0x0c7f, 0x0e7f, 0x007c, 0x0e7e, 0x0c7e, 0x037e, 0x027e, 0x017e,
-       0x6218, 0x2270, 0x72a0, 0x027e, 0x2019, 0x0029, 0x1078, 0x5d53,
-       0x077e, 0x2039, 0x0000, 0x1078, 0x5c78, 0x2c08, 0x1078, 0x9c38,
-       0x077f, 0x017f, 0x2e60, 0x1078, 0x471b, 0x6210, 0x6314, 0x1078,
-       0x4235, 0x6212, 0x6316, 0x017f, 0x027f, 0x037f, 0x0c7f, 0x0e7f,
-       0x007c, 0x0e7e, 0x007e, 0x6018, 0xa080, 0x0028, 0x2004, 0xd0bc,
-       0x00c0, 0x284d, 0x2071, 0xa300, 0x708c, 0xa005, 0x0040, 0x284a,
-       0x8001, 0x708e, 0x007f, 0x0e7f, 0x007c, 0x2071, 0xa300, 0x70d0,
-       0xa005, 0x0040, 0x284a, 0x8001, 0x70d2, 0x0078, 0x284a, 0x6000,
-       0xc08c, 0x6002, 0x007c, 0x0f7e, 0x0e7e, 0x0c7e, 0x037e, 0x027e,
-       0x017e, 0x157e, 0x2178, 0x81ff, 0x00c0, 0x286a, 0x20a9, 0x0001,
-       0x0078, 0x2885, 0x2001, 0xa352, 0x2004, 0xd0c4, 0x0040, 0x2881,
-       0xd0a4, 0x0040, 0x2881, 0x047e, 0x6018, 0xa080, 0x0028, 0x2024,
-       0xa4a4, 0x00ff, 0x8427, 0xa006, 0x2009, 0x002d, 0x1078, 0x9ec0,
-       0x047f, 0x20a9, 0x00ff, 0x2011, 0x0000, 0x027e, 0xa28e, 0x007e,
-       0x0040, 0x28c9, 0xa28e, 0x007f, 0x0040, 0x28c9, 0xa28e, 0x0080,
-       0x0040, 0x28c9, 0xa288, 0xa434, 0x210c, 0x81ff, 0x0040, 0x28c9,
-       0x8fff, 0x1040, 0x28d5, 0x0c7e, 0x2160, 0x2001, 0x0001, 0x1078,
-       0x48a2, 0x0c7f, 0x2019, 0x0029, 0x1078, 0x5d53, 0x077e, 0x2039,
-       0x0000, 0x1078, 0x5c78, 0x0c7e, 0x027e, 0x2160, 0x6204, 0xa294,
-       0x00ff, 0xa286, 0x0006, 0x00c0, 0x28b9, 0x6007, 0x0404, 0x0078,
-       0x28be, 0x2001, 0x0004, 0x8007, 0xa215, 0x6206, 0x027f, 0x0c7f,
-       0x017e, 0x2c08, 0x1078, 0x9c38, 0x017f, 0x077f, 0x2160, 0x1078,
-       0x471b, 0x027f, 0x8210, 0x00f0, 0x2885, 0x157f, 0x017f, 0x027f,
-       0x037f, 0x0c7f, 0x0e7f, 0x0f7f, 0x007c, 0x047e, 0x027e, 0x017e,
-       0x2001, 0xa352, 0x2004, 0xd0c4, 0x0040, 0x28e8, 0xd0a4, 0x0040,
-       0x28e8, 0xa006, 0x2220, 0x8427, 0x2009, 0x0029, 0x1078, 0x9ec0,
-       0x017f, 0x027f, 0x047f, 0x007c, 0x017e, 0x027e, 0x037e, 0x0c7e,
-       0x7280, 0x82ff, 0x0040, 0x291a, 0xa290, 0xa352, 0x2214, 0xd2ac,
-       0x00c0, 0x291a, 0x2100, 0x1078, 0x24fa, 0x81ff, 0x0040, 0x291c,
-       0x2019, 0x0001, 0x8314, 0xa2e0, 0xa9c0, 0x2c04, 0xd384, 0x0040,
-       0x290e, 0xa084, 0xff00, 0x8007, 0x0078, 0x2910, 0xa084, 0x00ff,
-       0xa116, 0x0040, 0x291c, 0xa096, 0x00ff, 0x0040, 0x291a, 0x8318,
-       0x0078, 0x2902, 0xa085, 0x0001, 0x0c7f, 0x037f, 0x027f, 0x017f,
-       0x007c, 0x017e, 0x0c7e, 0x127e, 0x2091, 0x8000, 0xa180, 0xa434,
-       0x2004, 0xa065, 0x0040, 0x293b, 0x017e, 0x0c7e, 0x1078, 0x8ec0,
-       0x017f, 0x1040, 0x1328, 0x611a, 0x1078, 0x2813, 0x1078, 0x753d,
-       0x017f, 0x1078, 0x44bc, 0x127f, 0x0c7f, 0x017f, 0x007c, 0x7eef,
-       0x7de8, 0x7ce4, 0x80e2, 0x7be1, 0x80e0, 0x80dc, 0x80da, 0x7ad9,
-       0x80d6, 0x80d5, 0x80d4, 0x80d3, 0x80d2, 0x80d1, 0x79ce, 0x78cd,
-       0x80cc, 0x80cb, 0x80ca, 0x80c9, 0x80c7, 0x80c6, 0x77c5, 0x76c3,
-       0x80bc, 0x80ba, 0x75b9, 0x80b6, 0x74b5, 0x73b4, 0x72b3, 0x80b2,
-       0x80b1, 0x80ae, 0x71ad, 0x80ac, 0x70ab, 0x6faa, 0x6ea9, 0x80a7,
-       0x6da6, 0x6ca5, 0x6ba3, 0x6a9f, 0x699e, 0x689d, 0x809b, 0x8098,
-       0x6797, 0x6690, 0x658f, 0x6488, 0x6384, 0x6282, 0x8081, 0x8080,
-       0x617c, 0x607a, 0x8079, 0x5f76, 0x8075, 0x8074, 0x8073, 0x8072,
-       0x8071, 0x806e, 0x5e6d, 0x806c, 0x5d6b, 0x5c6a, 0x5b69, 0x8067,
-       0x5a66, 0x5965, 0x5863, 0x575c, 0x565a, 0x5559, 0x8056, 0x8055,
-       0x5454, 0x5353, 0x5252, 0x5151, 0x504e, 0x4f4d, 0x804c, 0x804b,
-       0x4e4a, 0x4d49, 0x8047, 0x4c46, 0x8045, 0x8043, 0x803c, 0x803a,
-       0x8039, 0x8036, 0x4b35, 0x8034, 0x4a33, 0x4932, 0x4831, 0x802e,
-       0x472d, 0x462c, 0x452b, 0x442a, 0x4329, 0x4227, 0x8026, 0x8025,
-       0x4123, 0x401f, 0x3f1e, 0x3e1d, 0x3d1b, 0x3c18, 0x8017, 0x8010,
-       0x3b0f, 0x3a08, 0x8004, 0x3902, 0x8001, 0x8000, 0x8000, 0x3800,
-       0x3700, 0x3600, 0x8000, 0x3500, 0x8000, 0x8000, 0x8000, 0x3400,
-       0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x3300, 0x3200,
-       0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x3100, 0x3000,
-       0x8000, 0x8000, 0x2f00, 0x8000, 0x2e00, 0x2d00, 0x2c00, 0x8000,
-       0x8000, 0x8000, 0x2b00, 0x8000, 0x2a00, 0x2900, 0x2800, 0x8000,
-       0x2700, 0x2600, 0x2500, 0x2400, 0x2300, 0x2200, 0x8000, 0x8000,
-       0x2100, 0x2000, 0x1f00, 0x1e00, 0x1d00, 0x1c00, 0x8000, 0x8000,
-       0x1b00, 0x1a00, 0x8000, 0x1900, 0x8000, 0x8000, 0x8000, 0x8000,
-       0x8000, 0x8000, 0x1800, 0x8000, 0x1700, 0x1600, 0x1500, 0x8000,
-       0x1400, 0x1300, 0x1200, 0x1100, 0x1000, 0x0f00, 0x8000, 0x8000,
-       0x0e00, 0x0d00, 0x0c00, 0x0b00, 0x0a00, 0x0900, 0x8000, 0x8000,
-       0x0800, 0x0700, 0x8000, 0x0600, 0x8000, 0x8000, 0x8000, 0x0500,
-       0x0400, 0x0300, 0x8000, 0x0200, 0x8000, 0x8000, 0x8000, 0x0100,
-       0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x0000, 0x8000,
-       0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000,
-       0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x2071,
-       0xa381, 0x7003, 0x0002, 0xa006, 0x7012, 0x7016, 0x703a, 0x703e,
-       0x7033, 0xa391, 0x7037, 0xa391, 0x7007, 0x0001, 0x2061, 0xa3d1,
-       0x6003, 0x0002, 0x007c, 0x0090, 0x2a66, 0x0068, 0x2a66, 0x2071,
-       0xa381, 0x2b78, 0x7818, 0xd084, 0x00c0, 0x2a66, 0x2a60, 0x7820,
-       0xa08e, 0x0069, 0x00c0, 0x2b56, 0x0079, 0x2aea, 0x007c, 0x2071,
-       0xa381, 0x7004, 0x0079, 0x2a6c, 0x2a70, 0x2a71, 0x2a7b, 0x2a8d,
-       0x007c, 0x0090, 0x2a7a, 0x0068, 0x2a7a, 0x2b78, 0x7818, 0xd084,
-       0x0040, 0x2a99, 0x007c, 0x2b78, 0x2061, 0xa3d1, 0x6008, 0xa08e,
-       0x0100, 0x0040, 0x2a88, 0xa086, 0x0200, 0x0040, 0x2b4e, 0x007c,
-       0x7014, 0x2068, 0x2a60, 0x7018, 0x007a, 0x7010, 0x2068, 0x6834,
-       0xa086, 0x0103, 0x0040, 0x2a95, 0x007c, 0x2a60, 0x2b78, 0x7018,
-       0x007a, 0x2a60, 0x7820, 0xa08a, 0x0040, 0x00c8, 0x2aa2, 0x61b8,
-       0x0079, 0x2aaa, 0x2100, 0xa08a, 0x003f, 0x00c8, 0x2b4a, 0x61b8,
-       0x0079, 0x2aea, 0x2b2c, 0x2b5e, 0x2b66, 0x2b6a, 0x2b72, 0x2b78,
-       0x2b7c, 0x2b88, 0x2b8c, 0x2b96, 0x2b9a, 0x2b4a, 0x2b4a, 0x2b4a,
-       0x2b9e, 0x2b4a, 0x2bae, 0x2bc5, 0x2bdc, 0x2c58, 0x2c5d, 0x2c8a,
-       0x2ce4, 0x2cf5, 0x2d13, 0x2d54, 0x2d5e, 0x2d6b, 0x2d7e, 0x2d9d,
-       0x2da6, 0x2de3, 0x2de9, 0x2b4a, 0x2e05, 0x2b4a, 0x2b4a, 0x2b4a,
-       0x2b4a, 0x2b4a, 0x2e0c, 0x2e16, 0x2b4a, 0x2b4a, 0x2b4a, 0x2b4a,
-       0x2b4a, 0x2b4a, 0x2b4a, 0x2b4a, 0x2e1e, 0x2b4a, 0x2b4a, 0x2b4a,
-       0x2b4a, 0x2b4a, 0x2e30, 0x2e47, 0x2b4a, 0x2b4a, 0x2b4a, 0x2b4a,
-       0x2b4a, 0x2b4a, 0x2e59, 0x2eb0, 0x2f0e, 0x2f1f, 0x2b4a, 0x2b4a,
-       0x2b4a, 0x38f1, 0x2b4a, 0x2b4a, 0x2b4a, 0x2b4a, 0x2b4a, 0x2b4a,
-       0x2b4a, 0x2b4a, 0x2b96, 0x2b9a, 0x2f36, 0x2b4a, 0x2f43, 0x397d,
-       0x39da, 0x2b4a, 0x2b4a, 0x2b4a, 0x2b4a, 0x2b4a, 0x2b4a, 0x2b4a,
-       0x2b4a, 0x2b4a, 0x2f90, 0x30c5, 0x30e1, 0x30ed, 0x3150, 0x31a9,
-       0x31b4, 0x31f3, 0x3202, 0x3211, 0x3214, 0x2f47, 0x3238, 0x3284,
-       0x3291, 0x33a2, 0x34cd, 0x34f7, 0x3604, 0x3614, 0x3621, 0x365b,
-       0x372a, 0x2b4a, 0x2b4a, 0x2b4a, 0x2b4a, 0x3792, 0x37ae, 0x3828,
-       0x38e2, 0x713c, 0x0078, 0x2b2c, 0x2021, 0x4000, 0x1078, 0x3553,
-       0x127e, 0x2091, 0x8000, 0x0068, 0x2b39, 0x7818, 0xd084, 0x0040,
-       0x2b3c, 0x127f, 0x0078, 0x2b30, 0x7c22, 0x7926, 0x7a2a, 0x7b2e,
-       0x781b, 0x0001, 0x2091, 0x4080, 0x7007, 0x0001, 0x2091, 0x5000,
-       0x127f, 0x007c, 0x2021, 0x4001, 0x0078, 0x2b2e, 0x2021, 0x4002,
-       0x0078, 0x2b2e, 0x2021, 0x4003, 0x0078, 0x2b2e, 0x2021, 0x4005,
-       0x0078, 0x2b2e, 0x2021, 0x4006, 0x0078, 0x2b2e, 0xa02e, 0x2520,
-       0x7b28, 0x7a2c, 0x7824, 0x7930, 0x0078, 0x3562, 0x7823, 0x0004,
-       0x7824, 0x007a, 0xa02e, 0x2520, 0x7b28, 0x7a2c, 0x7824, 0x7930,
-       0x0078, 0x3566, 0x7924, 0x7828, 0x2114, 0x200a, 0x0078, 0x2b2c,
-       0x7924, 0x2114, 0x0078, 0x2b2c, 0x2099, 0x0009, 0x20a1, 0x0009,
-       0x20a9, 0x0007, 0x53a3, 0x7924, 0x7a28, 0x7b2c, 0x0078, 0x2b2c,
-       0x7824, 0x2060, 0x0078, 0x2ba0, 0x2009, 0x0001, 0x2011, 0x0013,
-       0x2019, 0x0010, 0x783b, 0x0017, 0x0078, 0x2b2c, 0x7d38, 0x7c3c,
-       0x0078, 0x2b60, 0x7d38, 0x7c3c, 0x0078, 0x2b6c, 0x2061, 0x1000,
-       0x610c, 0xa006, 0x2c14, 0xa200, 0x8c60, 0x8109, 0x00c0, 0x2ba2,
-       0x2010, 0xa005, 0x0040, 0x2b2c, 0x0078, 0x2b52, 0x2069, 0xa351,
-       0x7824, 0x7930, 0xa11a, 0x00c8, 0x2b5a, 0x8019, 0x0040, 0x2b5a,
-       0x684a, 0x6942, 0x782c, 0x6852, 0x7828, 0x6856, 0xa006, 0x685a,
-       0x685e, 0x1078, 0x4dbd, 0x0078, 0x2b2c, 0x2069, 0xa351, 0x7824,
-       0x7934, 0xa11a, 0x00c8, 0x2b5a, 0x8019, 0x0040, 0x2b5a, 0x684e,
-       0x6946, 0x782c, 0x6862, 0x7828, 0x6866, 0xa006, 0x686a, 0x686e,
-       0x1078, 0x494d, 0x0078, 0x2b2c, 0xa02e, 0x2520, 0x81ff, 0x00c0,
-       0x2b56, 0x7924, 0x7b28, 0x7a2c, 0x20a9, 0x0005, 0x20a1, 0xa388,
-       0x41a1, 0x1078, 0x3518, 0x0040, 0x2b56, 0x2009, 0x0020, 0x1078,
-       0x3562, 0x701b, 0x2bf4, 0x007c, 0x6834, 0x2008, 0xa084, 0x00ff,
-       0xa096, 0x0011, 0x0040, 0x2c00, 0xa096, 0x0019, 0x00c0, 0x2b56,
-       0x810f, 0xa18c, 0x00ff, 0x0040, 0x2b56, 0x710e, 0x700c, 0x8001,
-       0x0040, 0x2c31, 0x700e, 0x1078, 0x3518, 0x0040, 0x2b56, 0x2009,
-       0x0020, 0x2061, 0xa3d1, 0x6224, 0x6328, 0x642c, 0x6530, 0xa290,
-       0x0040, 0xa399, 0x0000, 0xa4a1, 0x0000, 0xa5a9, 0x0000, 0x1078,
-       0x3562, 0x701b, 0x2c24, 0x007c, 0x6834, 0xa084, 0x00ff, 0xa096,
-       0x0002, 0x0040, 0x2c2f, 0xa096, 0x000a, 0x00c0, 0x2b56, 0x0078,
-       0x2c06, 0x7010, 0x2068, 0x6838, 0xc0fd, 0x683a, 0x1078, 0x436e,
-       0x00c0, 0x2c3f, 0x7007, 0x0003, 0x701b, 0x2c41, 0x007c, 0x1078,
-       0x4a60, 0x127e, 0x2091, 0x8000, 0x20a9, 0x0005, 0x2099, 0xa388,
-       0x530a, 0x2100, 0xa210, 0xa399, 0x0000, 0xa4a1, 0x0000, 0xa5a9,
-       0x0000, 0xad80, 0x000d, 0x2009, 0x0020, 0x127f, 0x0078, 0x3566,
-       0x61a0, 0x7824, 0x60a2, 0x0078, 0x2b2c, 0x2091, 0x8000, 0x7823,
-       0x4000, 0x7827, 0x4953, 0x782b, 0x5020, 0x782f, 0x2020, 0x2009,
-       0x017f, 0x2104, 0x7832, 0x3f00, 0x7836, 0x2061, 0x0100, 0x6200,
-       0x2061, 0x0200, 0x603c, 0x8007, 0xa205, 0x783a, 0x2009, 0x04fd,
-       0x2104, 0x783e, 0x781b, 0x0001, 0x2091, 0x5000, 0x2091, 0x4080,
-       0x2071, 0x0010, 0x20c1, 0x00f0, 0xa08a, 0x0003, 0x00c8, 0x0427,
-       0x0078, 0x0423, 0x81ff, 0x00c0, 0x2b56, 0x7924, 0x810f, 0xa18c,
-       0x00ff, 0x1078, 0x4501, 0x00c0, 0x2b5a, 0x7e38, 0xa684, 0x3fff,
-       0xa082, 0x4000, 0x0048, 0x2c9e, 0x0078, 0x2b5a, 0x7c28, 0x7d2c,
-       0x1078, 0x46d6, 0xd28c, 0x00c0, 0x2ca9, 0x1078, 0x466a, 0x0078,
-       0x2cab, 0x1078, 0x46a4, 0x00c0, 0x2cd5, 0x2061, 0xaa00, 0x127e,
-       0x2091, 0x8000, 0x6000, 0xa086, 0x0000, 0x0040, 0x2cc3, 0x6010,
-       0xa06d, 0x0040, 0x2cc3, 0x683c, 0xa406, 0x00c0, 0x2cc3, 0x6840,
-       0xa506, 0x0040, 0x2cce, 0x127f, 0xace0, 0x0010, 0x2001, 0xa315,
-       0x2004, 0xac02, 0x00c8, 0x2b56, 0x0078, 0x2caf, 0x1078, 0x8758,
-       0x127f, 0x0040, 0x2b56, 0x0078, 0x2b2c, 0xa00e, 0x2001, 0x0005,
-       0x1078, 0x4a60, 0x127e, 0x2091, 0x8000, 0x1078, 0x8cc0, 0x1078,
-       0x4982, 0x127f, 0x0078, 0x2b2c, 0x81ff, 0x00c0, 0x2b56, 0x1078,
-       0x3530, 0x0040, 0x2b5a, 0x1078, 0x45a7, 0x0040, 0x2b56, 0x1078,
-       0x46e4, 0x0040, 0x2b56, 0x0078, 0x2b2c, 0x81ff, 0x00c0, 0x2b56,
-       0x1078, 0x3542, 0x0040, 0x2b5a, 0x1078, 0x475f, 0x0040, 0x2b56,
-       0x2019, 0x0005, 0x1078, 0x4705, 0x0040, 0x2b56, 0x7828, 0xa08a,
-       0x1000, 0x00c8, 0x2b5a, 0x8003, 0x800b, 0x810b, 0xa108, 0x1078,
-       0x58e1, 0x0078, 0x2b2c, 0x127e, 0x2091, 0x8000, 0x81ff, 0x0040,
-       0x2d1d, 0x2009, 0x0001, 0x0078, 0x2d4e, 0x2029, 0x00ff, 0x644c,
-       0x2400, 0xa506, 0x0040, 0x2d48, 0x2508, 0x1078, 0x4501, 0x00c0,
-       0x2d48, 0x1078, 0x475f, 0x00c0, 0x2d33, 0x2009, 0x0002, 0x62a8,
-       0x2518, 0x0078, 0x2d4e, 0x2019, 0x0004, 0x1078, 0x4705, 0x00c0,
-       0x2d3d, 0x2009, 0x0006, 0x0078, 0x2d4e, 0x7824, 0xa08a, 0x1000,
-       0x00c8, 0x2d51, 0x8003, 0x800b, 0x810b, 0xa108, 0x1078, 0x58e1,
-       0x8529, 0x00c8, 0x2d20, 0x127f, 0x0078, 0x2b2c, 0x127f, 0x0078,
-       0x2b56, 0x127f, 0x0078, 0x2b5a, 0x1078, 0x3530, 0x0040, 0x2b5a,
-       0x1078, 0x461b, 0x1078, 0x46d6, 0x0078, 0x2b2c, 0x81ff, 0x00c0,
-       0x2b56, 0x1078, 0x3530, 0x0040, 0x2b5a, 0x1078, 0x460a, 0x1078,
-       0x46d6, 0x0078, 0x2b2c, 0x81ff, 0x00c0, 0x2b56, 0x1078, 0x3530,
-       0x0040, 0x2b5a, 0x1078, 0x46a7, 0x0040, 0x2b56, 0x1078, 0x43c1,
-       0x1078, 0x4663, 0x1078, 0x46d6, 0x0078, 0x2b2c, 0x1078, 0x3530,
-       0x0040, 0x2b5a, 0x1078, 0x45a7, 0x0040, 0x2b56, 0x62a0, 0x2019,
-       0x0005, 0x0c7e, 0x1078, 0x471b, 0x0c7f, 0x1078, 0x5d53, 0x077e,
-       0x2039, 0x0000, 0x1078, 0x5c78, 0x2009, 0x0000, 0x1078, 0x9c38,
-       0x077f, 0x1078, 0x46d6, 0x0078, 0x2b2c, 0x1078, 0x3530, 0x0040,
-       0x2b5a, 0x1078, 0x46d6, 0x2208, 0x0078, 0x2b2c, 0x157e, 0x0d7e,
-       0x0e7e, 0x2069, 0xa413, 0x6810, 0x6914, 0xa10a, 0x00c8, 0x2db2,
-       0x2009, 0x0000, 0x6816, 0x2011, 0x0000, 0x2019, 0x0000, 0x20a9,
-       0x00ff, 0x2069, 0xa434, 0x2d04, 0xa075, 0x0040, 0x2dc7, 0x704c,
-       0x1078, 0x2dd1, 0xa210, 0x7080, 0x1078, 0x2dd1, 0xa318, 0x8d68,
-       0x00f0, 0x2dbb, 0x2300, 0xa218, 0x0e7f, 0x0d7f, 0x157f, 0x0078,
-       0x2b2c, 0x0f7e, 0x017e, 0xa07d, 0x0040, 0x2de0, 0x2001, 0x0000,
-       0x8000, 0x2f0c, 0x81ff, 0x0040, 0x2de0, 0x2178, 0x0078, 0x2dd8,
-       0x017f, 0x0f7f, 0x007c, 0x2069, 0xa413, 0x6910, 0x62a4, 0x0078,
-       0x2b2c, 0x81ff, 0x00c0, 0x2b56, 0x614c, 0xa190, 0x293f, 0x2214,
-       0xa294, 0x00ff, 0x606c, 0xa084, 0xff00, 0xa215, 0x6368, 0x67c8,
-       0xd79c, 0x0040, 0x2dff, 0x2031, 0x0001, 0x0078, 0x2e01, 0x2031,
-       0x0000, 0x7e3a, 0x7f3e, 0x0078, 0x2b2c, 0x613c, 0x6240, 0x2019,
-       0xa5a0, 0x231c, 0x0078, 0x2b2c, 0x127e, 0x2091, 0x8000, 0x6134,
-       0xa006, 0x2010, 0x2018, 0x127f, 0x0078, 0x2b2c, 0x1078, 0x3542,
-       0x0040, 0x2b5a, 0x6244, 0x6338, 0x0078, 0x2b2c, 0x613c, 0x6240,
-       0x7824, 0x603e, 0x7b28, 0x6342, 0x2069, 0xa351, 0x831f, 0xa305,
-       0x6816, 0x782c, 0x2069, 0xa5a0, 0x2d1c, 0x206a, 0x0078, 0x2b2c,
-       0x017e, 0x127e, 0x2091, 0x8000, 0x7824, 0x6036, 0xd094, 0x0040,
-       0x2e43, 0x7828, 0xa085, 0x0001, 0x2009, 0xa5a9, 0x200a, 0x2001,
-       0xffff, 0x1078, 0x5975, 0x127f, 0x017f, 0x0078, 0x2b2c, 0x1078,
-       0x3542, 0x0040, 0x2b5a, 0x7828, 0xa00d, 0x0040, 0x2b5a, 0x782c,
-       0xa005, 0x0040, 0x2b5a, 0x6244, 0x6146, 0x6338, 0x603a, 0x0078,
-       0x2b2c, 0x2001, 0xa300, 0x2004, 0xa086, 0x0003, 0x00c0, 0x2b56,
-       0x0c7e, 0x2061, 0x0100, 0x7924, 0x810f, 0xa18c, 0x00ff, 0xa196,
-       0x00ff, 0x00c0, 0x2e70, 0x6030, 0xa085, 0xff00, 0x0078, 0x2e7f,
-       0xa182, 0x007f, 0x00c8, 0x2ea9, 0xa188, 0x293f, 0x210c, 0xa18c,
-       0x00ff, 0x6030, 0xa116, 0x0040, 0x2ea9, 0x810f, 0xa105, 0x127e,
-       0x2091, 0x8000, 0x007e, 0x1078, 0x74d7, 0x007f, 0x0040, 0x2ea5,
-       0x601a, 0x600b, 0xbc09, 0x601f, 0x0001, 0x1078, 0x3518, 0x0040,
-       0x2eac, 0x6837, 0x0000, 0x7007, 0x0003, 0x6833, 0x0000, 0x6838,
-       0xc0fd, 0x683a, 0x701b, 0x2f07, 0x2d00, 0x6012, 0x2009, 0x0032,
-       0x1078, 0x756c, 0x127f, 0x0c7f, 0x007c, 0x127f, 0x0c7f, 0x0078,
-       0x2b56, 0x0c7f, 0x0078, 0x2b5a, 0x1078, 0x753d, 0x0078, 0x2ea5,
-       0x2001, 0xa300, 0x2004, 0xa086, 0x0003, 0x00c0, 0x2b56, 0x0c7e,
-       0x2061, 0x0100, 0x7924, 0x810f, 0xa18c, 0x00ff, 0xa196, 0x00ff,
-       0x00c0, 0x2ec7, 0x6030, 0xa085, 0xff00, 0x0078, 0x2ed6, 0xa182,
-       0x007f, 0x00c8, 0x2f00, 0xa188, 0x293f, 0x210c, 0xa18c, 0x00ff,
-       0x6030, 0xa116, 0x0040, 0x2f00, 0x810f, 0xa105, 0x127e, 0x2091,
-       0x8000, 0x007e, 0x1078, 0x74d7, 0x007f, 0x0040, 0x2efc, 0x601a,
-       0x600b, 0xbc05, 0x601f, 0x0001, 0x1078, 0x3518, 0x0040, 0x2f03,
-       0x6837, 0x0000, 0x7007, 0x0003, 0x6833, 0x0000, 0x6838, 0xc0fd,
-       0x683a, 0x701b, 0x2f07, 0x2d00, 0x6012, 0x2009, 0x0032, 0x1078,
-       0x756c, 0x127f, 0x0c7f, 0x007c, 0x127f, 0x0c7f, 0x0078, 0x2b56,
-       0x0c7f, 0x0078, 0x2b5a, 0x1078, 0x753d, 0x0078, 0x2efc, 0x6830,
-       0xa086, 0x0100, 0x0040, 0x2b56, 0x0078, 0x2b2c, 0x2061, 0xa62d,
-       0x127e, 0x2091, 0x8000, 0x6000, 0xd084, 0x0040, 0x2f1c, 0x6104,
-       0x6208, 0x127f, 0x0078, 0x2b2c, 0x127f, 0x0078, 0x2b5a, 0x81ff,
-       0x00c0, 0x2b56, 0x127e, 0x2091, 0x8000, 0x6244, 0x6060, 0xa202,
-       0x0048, 0x2f33, 0xa085, 0x0001, 0x1078, 0x2500, 0x1078, 0x3bf5,
-       0x127f, 0x0078, 0x2b2c, 0x127f, 0x0078, 0x2b5a, 0x127e, 0x2091,
-       0x8000, 0x20a9, 0x0011, 0x2001, 0xa340, 0x20a0, 0xa006, 0x40a4,
-       0x127f, 0x0078, 0x2b2c, 0x7d38, 0x7c3c, 0x0078, 0x2bde, 0x7824,
-       0xa09c, 0x00ff, 0xa39a, 0x0003, 0x00c8, 0x2b56, 0x624c, 0xa084,
-       0xff00, 0x8007, 0xa206, 0x00c0, 0x2f5f, 0x2001, 0xa340, 0x2009,
-       0x000c, 0x7a2c, 0x7b28, 0x7c3c, 0x7d38, 0x0078, 0x3566, 0x81ff,
-       0x00c0, 0x2b56, 0x1078, 0x3542, 0x0040, 0x2b5a, 0x6004, 0xa084,
-       0x00ff, 0xa086, 0x0006, 0x00c0, 0x2b56, 0x0c7e, 0x1078, 0x3518,
-       0x0c7f, 0x0040, 0x2b56, 0x6837, 0x0000, 0x6838, 0xc0fd, 0x683a,
-       0x1078, 0x8b85, 0x0040, 0x2b56, 0x7007, 0x0003, 0x701b, 0x2f81,
-       0x007c, 0x6830, 0xa086, 0x0100, 0x0040, 0x2b56, 0xad80, 0x000e,
-       0x2009, 0x000c, 0x7a2c, 0x7b28, 0x7c3c, 0x7d38, 0x0078, 0x3566,
-       0x1078, 0x3518, 0x0040, 0x2b56, 0x1078, 0x421a, 0x2009, 0x001c,
-       0x7a2c, 0x7b28, 0x7c3c, 0x7d38, 0x1078, 0x3562, 0x701b, 0x2fa1,
-       0x007c, 0xade8, 0x000d, 0x6800, 0xa005, 0x0040, 0x2b5a, 0x6804,
-       0xd0ac, 0x0040, 0x2fae, 0xd0a4, 0x0040, 0x2b5a, 0xd094, 0x0040,
-       0x2fb9, 0x0c7e, 0x2061, 0x0100, 0x6104, 0xa18c, 0xffdf, 0x6106,
-       0x0c7f, 0xd08c, 0x0040, 0x2fc4, 0x0c7e, 0x2061, 0x0100, 0x6104,
-       0xa18d, 0x0010, 0x6106, 0x0c7f, 0x2009, 0x0100, 0x210c, 0xa18a,
-       0x0002, 0x0048, 0x2fd9, 0xd084, 0x0040, 0x2fd9, 0x6a28, 0xa28a,
-       0x007f, 0x00c8, 0x2b5a, 0xa288, 0x293f, 0x210c, 0xa18c, 0x00ff,
-       0x6152, 0xd0dc, 0x0040, 0x2fe2, 0x6828, 0xa08a, 0x007f, 0x00c8,
-       0x2b5a, 0x604e, 0x6808, 0xa08a, 0x0100, 0x0048, 0x2b5a, 0xa08a,
-       0x0841, 0x00c8, 0x2b5a, 0xa084, 0x0007, 0x00c0, 0x2b5a, 0x680c,
-       0xa005, 0x0040, 0x2b5a, 0x6810, 0xa005, 0x0040, 0x2b5a, 0x6848,
-       0x6940, 0xa10a, 0x00c8, 0x2b5a, 0x8001, 0x0040, 0x2b5a, 0x684c,
-       0x6944, 0xa10a, 0x00c8, 0x2b5a, 0x8001, 0x0040, 0x2b5a, 0x6804,
-       0xd0fc, 0x0040, 0x3038, 0x1078, 0x3518, 0x0040, 0x2b56, 0x2009,
-       0x0014, 0x7a2c, 0x7b28, 0x7c3c, 0x7d38, 0xa290, 0x0038, 0xa399,
-       0x0000, 0x1078, 0x3562, 0x701b, 0x301e, 0x007c, 0xade8, 0x000d,
-       0x20a9, 0x0014, 0x2d98, 0x2069, 0xa36d, 0x2da0, 0x53a3, 0x7010,
-       0xa0e8, 0x000d, 0x2001, 0xa371, 0x200c, 0xd1e4, 0x0040, 0x3038,
-       0x0c7e, 0x2061, 0x0100, 0x6004, 0xa085, 0x0b00, 0x6006, 0x0c7f,
-       0x20a9, 0x001c, 0x2d98, 0x2069, 0xa351, 0x2da0, 0x53a3, 0x6814,
-       0xa08c, 0x00ff, 0x613e, 0x8007, 0xa084, 0x00ff, 0x6042, 0x1078,
-       0x4dbd, 0x1078, 0x48dd, 0x1078, 0x494d, 0x6000, 0xa086, 0x0000,
-       0x00c0, 0x30c3, 0x6808, 0x602a, 0x1078, 0x218b, 0x6818, 0x691c,
-       0x6a20, 0x6b24, 0x8007, 0x810f, 0x8217, 0x831f, 0x6016, 0x611a,
-       0x621e, 0x6322, 0x6c04, 0xd4f4, 0x0040, 0x3070, 0x6830, 0x6934,
-       0x6a38, 0x6b3c, 0x8007, 0x810f, 0x8217, 0x831f, 0x0078, 0x3072,
-       0xa084, 0xf0ff, 0x6006, 0x610a, 0x620e, 0x6312, 0x1078, 0x59a8,
-       0x6904, 0xd1fc, 0x0040, 0x30a5, 0x0c7e, 0x2009, 0x0000, 0x20a9,
-       0x0001, 0x6b70, 0xd384, 0x0040, 0x30a2, 0x0078, 0x308c, 0x839d,
-       0x00c8, 0x30a2, 0x3508, 0x8109, 0x1078, 0x5364, 0x6878, 0x6016,
-       0x6874, 0x2008, 0xa084, 0xff00, 0x8007, 0x600a, 0xa184, 0x00ff,
-       0x6006, 0x8108, 0x00c0, 0x30a0, 0x6003, 0x0003, 0x0078, 0x30a2,
-       0x6003, 0x0001, 0x00f0, 0x3087, 0x0c7f, 0x0c7e, 0x2061, 0x0100,
-       0x602f, 0x0040, 0x602f, 0x0000, 0x0c7f, 0x1078, 0x3784, 0x0040,
-       0x30b3, 0x1078, 0x2500, 0x60bc, 0xa005, 0x0040, 0x30bf, 0x6003,
-       0x0001, 0x2091, 0x301d, 0x1078, 0x4171, 0x0078, 0x30c3, 0x6003,
-       0x0004, 0x2091, 0x301d, 0x0078, 0x2b2c, 0x6000, 0xa086, 0x0000,
-       0x0040, 0x2b56, 0x2069, 0xa351, 0x7830, 0x6842, 0x7834, 0x6846,
-       0x6804, 0xd0fc, 0x0040, 0x30d8, 0x2009, 0x0030, 0x0078, 0x30da,
-       0x2009, 0x001c, 0x2d00, 0x7a2c, 0x7b28, 0x7c3c, 0x7d38, 0x0078,
-       0x3566, 0xa006, 0x1078, 0x2500, 0x81ff, 0x00c0, 0x2b56, 0x1078,
-       0x421a, 0x1078, 0x4171, 0x0078, 0x2b2c, 0x81ff, 0x00c0, 0x2b56,
-       0x6180, 0x81ff, 0x0040, 0x3107, 0x703f, 0x0000, 0x2001, 0xa9c0,
-       0x2009, 0x0040, 0x7a2c, 0x7b28, 0x7c3c, 0x7d38, 0x127e, 0x2091,
-       0x8000, 0x1078, 0x3566, 0x701b, 0x2b29, 0x127f, 0x007c, 0x703f,
-       0x0001, 0x0d7e, 0x2069, 0xa9c0, 0x20a9, 0x0040, 0x20a1, 0xa9c0,
-       0x2019, 0xffff, 0x43a4, 0x654c, 0xa588, 0x293f, 0x210c, 0xa18c,
-       0x00ff, 0x216a, 0xa00e, 0x2011, 0x0002, 0x2100, 0xa506, 0x0040,
-       0x3139, 0x1078, 0x4501, 0x00c0, 0x3139, 0x6014, 0x821c, 0x0048,
-       0x3131, 0xa398, 0xa9c0, 0xa085, 0xff00, 0x8007, 0x201a, 0x0078,
-       0x3138, 0xa398, 0xa9c0, 0x2324, 0xa4a4, 0xff00, 0xa405, 0x201a,
-       0x8210, 0x8108, 0xa182, 0x0080, 0x00c8, 0x3140, 0x0078, 0x311d,
-       0x8201, 0x8007, 0x2d0c, 0xa105, 0x206a, 0x0d7f, 0x20a9, 0x0040,
-       0x20a1, 0xa9c0, 0x2099, 0xa9c0, 0x1078, 0x41be, 0x0078, 0x30f6,
-       0x1078, 0x3542, 0x0040, 0x2b5a, 0x0c7e, 0x1078, 0x3518, 0x0c7f,
-       0x00c0, 0x315e, 0x2009, 0x0002, 0x0078, 0x2b56, 0x2001, 0xa352,
-       0x2004, 0xd0b4, 0x0040, 0x3185, 0x6000, 0xd08c, 0x00c0, 0x3185,
-       0x6004, 0xa084, 0x00ff, 0xa086, 0x0006, 0x00c0, 0x3185, 0x6837,
-       0x0000, 0x6838, 0xc0fd, 0x683a, 0x1078, 0x8bd9, 0x00c0, 0x317c,
-       0x2009, 0x0003, 0x0078, 0x2b56, 0x7007, 0x0003, 0x701b, 0x3181,
-       0x007c, 0x1078, 0x3542, 0x0040, 0x2b5a, 0x20a9, 0x002b, 0x2c98,
-       0xade8, 0x0002, 0x2da0, 0x53a3, 0x20a9, 0x0004, 0xac80, 0x0006,
-       0x2098, 0xad80, 0x0006, 0x20a0, 0x1078, 0x41be, 0x20a9, 0x0004,
-       0xac80, 0x000a, 0x2098, 0xad80, 0x000a, 0x20a0, 0x1078, 0x41be,
-       0x2d00, 0x2009, 0x002b, 0x7a2c, 0x7b28, 0x7c3c, 0x7d38, 0x0078,
-       0x3566, 0x81ff, 0x00c0, 0x2b56, 0x1078, 0x3530, 0x0040, 0x2b5a,
-       0x1078, 0x46ef, 0x0078, 0x2b2c, 0x81ff, 0x00c0, 0x2b56, 0x7828,
-       0xa08a, 0x1000, 0x00c8, 0x2b5a, 0x1078, 0x3542, 0x0040, 0x2b5a,
-       0x1078, 0x475f, 0x0040, 0x2b56, 0x2019, 0x0004, 0x1078, 0x4705,
-       0x7924, 0x810f, 0x7a28, 0x1078, 0x31cf, 0x0078, 0x2b2c, 0xa186,
-       0x00ff, 0x0040, 0x31d7, 0x1078, 0x31e7, 0x0078, 0x31e6, 0x2029,
-       0x007e, 0x2061, 0xa300, 0x644c, 0x2400, 0xa506, 0x0040, 0x31e3,
-       0x2508, 0x1078, 0x31e7, 0x8529, 0x00c8, 0x31dc, 0x007c, 0x1078,
-       0x4501, 0x00c0, 0x31f2, 0x2200, 0x8003, 0x800b, 0x810b, 0xa108,
-       0x1078, 0x58e1, 0x007c, 0x81ff, 0x00c0, 0x2b56, 0x1078, 0x3530,
-       0x0040, 0x2b5a, 0x1078, 0x45a7, 0x0040, 0x2b56, 0x1078, 0x46fa,
-       0x0078, 0x2b2c, 0x81ff, 0x00c0, 0x2b56, 0x1078, 0x3530, 0x0040,
-       0x2b5a, 0x1078, 0x45a7, 0x0040, 0x2b56, 0x1078, 0x46e4, 0x0078,
-       0x2b2c, 0x6100, 0x0078, 0x2b2c, 0x1078, 0x3542, 0x0040, 0x2b5a,
-       0x2001, 0xa300, 0x2004, 0xa086, 0x0003, 0x00c0, 0x2b56, 0x0d7e,
-       0xace8, 0x000a, 0x7924, 0xd184, 0x0040, 0x3228, 0xace8, 0x0006,
-       0x680c, 0x8007, 0x783e, 0x6808, 0x8007, 0x783a, 0x6b04, 0x831f,
-       0x6a00, 0x8217, 0x0d7f, 0x6100, 0xa18c, 0x0200, 0x0078, 0x2b2c,
-       0xa006, 0x1078, 0x2500, 0x7824, 0xa084, 0x00ff, 0xa086, 0x00ff,
-       0x0040, 0x3245, 0x81ff, 0x00c0, 0x2b56, 0x1078, 0x421a, 0x7828,
-       0xa08a, 0x1000, 0x00c8, 0x2b5a, 0x7924, 0xa18c, 0xff00, 0x810f,
-       0xa186, 0x00ff, 0x0040, 0x325b, 0xa182, 0x007f, 0x00c8, 0x2b5a,
-       0x2100, 0x1078, 0x24fa, 0x027e, 0x0c7e, 0x127e, 0x2091, 0x8000,
-       0x2061, 0xa5be, 0x601b, 0x0000, 0x601f, 0x0000, 0x2061, 0x0100,
-       0x6030, 0xa084, 0x00ff, 0x810f, 0xa105, 0x604a, 0x6043, 0x0090,
-       0x6043, 0x0010, 0x2009, 0x002d, 0x2011, 0x4196, 0x1078, 0x596c,
-       0x7924, 0xa18c, 0xff00, 0x810f, 0x7a28, 0x1078, 0x31cf, 0x127f,
-       0x0c7f, 0x027f, 0x0078, 0x2b2c, 0x7924, 0xa18c, 0xff00, 0x810f,
-       0x0c7e, 0x1078, 0x4499, 0x2c08, 0x0c7f, 0x00c0, 0x2b5a, 0x0078,
-       0x2b2c, 0x81ff, 0x0040, 0x3298, 0x2009, 0x0001, 0x0078, 0x2b56,
-       0x60c8, 0xd09c, 0x00c0, 0x32a0, 0x2009, 0x0005, 0x0078, 0x2b56,
-       0x1078, 0x3518, 0x00c0, 0x32a8, 0x2009, 0x0002, 0x0078, 0x2b56,
-       0x7924, 0x7a2c, 0x7b28, 0x7c3c, 0x7d38, 0x1078, 0x3562, 0x701b,
-       0x32b2, 0x007c, 0x2009, 0x0080, 0x1078, 0x4501, 0x00c0, 0x32bf,
-       0x6004, 0xa084, 0x00ff, 0xa086, 0x0006, 0x0040, 0x32c3, 0x2021,
-       0x400a, 0x0078, 0x2b2e, 0x0d7e, 0xade8, 0x000d, 0x6900, 0x6a08,
-       0x6b0c, 0x6c10, 0x6d14, 0x6e18, 0x6820, 0xa0be, 0x0100, 0x0040,
-       0x3336, 0xa0be, 0x0112, 0x0040, 0x3336, 0xa0be, 0x0113, 0x0040,
-       0x3336, 0xa0be, 0x0114, 0x0040, 0x3336, 0xa0be, 0x0117, 0x0040,
-       0x3336, 0xa0be, 0x011a, 0x0040, 0x3336, 0xa0be, 0x0121, 0x0040,
-       0x332c, 0xa0be, 0x0131, 0x0040, 0x332c, 0xa0be, 0x0171, 0x0040,
-       0x3336, 0xa0be, 0x0173, 0x0040, 0x3336, 0xa0be, 0x01a1, 0x00c0,
-       0x32fe, 0x6830, 0x8007, 0x6832, 0x0078, 0x333c, 0xa0be, 0x0212,
-       0x0040, 0x3332, 0xa0be, 0x0213, 0x0040, 0x3332, 0xa0be, 0x0214,
-       0x0040, 0x3324, 0xa0be, 0x0217, 0x0040, 0x331e, 0xa0be, 0x021a,
-       0x00c0, 0x3317, 0x6838, 0x8007, 0x683a, 0x0078, 0x3336, 0xa0be,
-       0x0300, 0x0040, 0x3336, 0x0d7f, 0x0078, 0x2b5a, 0xad80, 0x0010,
-       0x20a9, 0x0007, 0x1078, 0x337e, 0xad80, 0x000e, 0x20a9, 0x0001,
-       0x1078, 0x337e, 0x0078, 0x3336, 0xad80, 0x000c, 0x1078, 0x338c,
-       0x0078, 0x333c, 0xad80, 0x000e, 0x1078, 0x338c, 0xad80, 0x000c,
-       0x20a9, 0x0001, 0x1078, 0x337e, 0x0c7e, 0x1078, 0x3518, 0x0040,
-       0x336f, 0x6838, 0xc0fd, 0x683a, 0x6837, 0x0119, 0x6853, 0x0000,
-       0x684f, 0x0020, 0x685b, 0x0001, 0x810b, 0x697e, 0x6883, 0x0000,
-       0x6a86, 0x6b8a, 0x6c8e, 0x6d92, 0x6996, 0x689b, 0x0000, 0x0c7f,
-       0x0d7f, 0x6837, 0x0000, 0x6838, 0xc0fd, 0x683a, 0x6823, 0x0000,
-       0x6804, 0x2068, 0x1078, 0x8ba1, 0x00c0, 0x336a, 0x2009, 0x0003,
-       0x0078, 0x2b56, 0x7007, 0x0003, 0x701b, 0x3375, 0x007c, 0x0c7f,
-       0x0d7f, 0x2009, 0x0002, 0x0078, 0x2b56, 0x6820, 0xa086, 0x8001,
-       0x00c0, 0x2b2c, 0x2009, 0x0004, 0x0078, 0x2b56, 0x017e, 0x2008,
-       0x2044, 0x8000, 0x204c, 0x8000, 0x290a, 0x8108, 0x280a, 0x8108,
-       0x00f0, 0x3380, 0x017f, 0x007c, 0x017e, 0x0a7e, 0x0b7e, 0x2008,
-       0x2044, 0x8000, 0x204c, 0x8000, 0x2054, 0x8000, 0x205c, 0x2b0a,
-       0x8108, 0x2a0a, 0x8108, 0x290a, 0x8108, 0x280a, 0x0b7f, 0x0a7f,
-       0x017f, 0x007c, 0x81ff, 0x0040, 0x33a9, 0x2009, 0x0001, 0x0078,
-       0x2b56, 0x7924, 0x2140, 0xa18c, 0xff00, 0x810f, 0xa182, 0x0080,
-       0x0048, 0x2b5a, 0xa182, 0x00ff, 0x00c8, 0x2b5a, 0x7a2c, 0x7b28,
-       0x6068, 0xa306, 0x00c0, 0x33c4, 0x606c, 0xa24e, 0x0040, 0x2b5a,
-       0xa9cc, 0xff00, 0x0040, 0x2b5a, 0x0c7e, 0x1078, 0x346d, 0x2c68,
-       0x0c7f, 0x0040, 0x33fc, 0xa0c6, 0x4000, 0x00c0, 0x33e2, 0x0c7e,
-       0x007e, 0x2d60, 0x2009, 0x0000, 0x1078, 0x47cb, 0x00c0, 0x33d9,
-       0xc185, 0x6000, 0xd0bc, 0x0040, 0x33de, 0xc18d, 0x007f, 0x0c7f,
-       0x0078, 0x33f9, 0xa0c6, 0x4007, 0x00c0, 0x33e9, 0x2408, 0x0078,
-       0x33f9, 0xa0c6, 0x4008, 0x00c0, 0x33f1, 0x2708, 0x2610, 0x0078,
-       0x33f9, 0xa0c6, 0x4009, 0x00c0, 0x33f7, 0x0078, 0x33f9, 0x2001,
-       0x4006, 0x2020, 0x0078, 0x2b2e, 0x2d00, 0x7022, 0x017e, 0x0b7e,
-       0x0c7e, 0x0e7e, 0x2c70, 0x1078, 0x74d7, 0x0040, 0x3442, 0x2d00,
-       0x601a, 0x2001, 0xa356, 0x2004, 0xa084, 0x00ff, 0x6842, 0x2e58,
-       0x0e7f, 0x0e7e, 0x0c7e, 0x1078, 0x3518, 0x0c7f, 0x2b70, 0x00c0,
-       0x3423, 0x1078, 0x753d, 0x0e7f, 0x0c7f, 0x0b7f, 0x017f, 0x2009,
-       0x0002, 0x0078, 0x2b56, 0x6837, 0x0000, 0x2d00, 0x6012, 0x6833,
-       0x0000, 0x6838, 0xc0fd, 0x683a, 0x127e, 0x2091, 0x8000, 0x1078,
-       0x2813, 0x127f, 0x601f, 0x0001, 0x2001, 0x0000, 0x1078, 0x442b,
-       0x2001, 0x0002, 0x1078, 0x443f, 0x2009, 0x0002, 0x1078, 0x756c,
-       0xa085, 0x0001, 0x0e7f, 0x0c7f, 0x0b7f, 0x017f, 0x00c0, 0x344c,
-       0x2009, 0x0003, 0x0078, 0x2b56, 0x7007, 0x0003, 0x701b, 0x3451,
-       0x007c, 0x6830, 0xa086, 0x0100, 0x7020, 0x2060, 0x00c0, 0x345f,
-       0x2009, 0x0004, 0x6204, 0xa294, 0x00ff, 0x0078, 0x2b56, 0x2009,
-       0x0000, 0x1078, 0x47cb, 0x00c0, 0x3466, 0xc185, 0x6000, 0xd0bc,
-       0x0040, 0x346b, 0xc18d, 0x0078, 0x2b2c, 0x0e7e, 0x0d7e, 0x2029,
-       0x0000, 0x2021, 0x0080, 0x20a9, 0x007f, 0x2071, 0xa4b4, 0x2e04,
-       0xa005, 0x00c0, 0x3482, 0x2100, 0xa406, 0x00c0, 0x34b3, 0x2428,
-       0x0078, 0x34b3, 0x2068, 0x6f10, 0x2700, 0xa306, 0x00c0, 0x34a4,
-       0x6e14, 0x2600, 0xa206, 0x00c0, 0x34a4, 0x2400, 0xa106, 0x00c0,
-       0x34a0, 0x2d60, 0xd884, 0x0040, 0x34c8, 0x6004, 0xa084, 0x00ff,
-       0xa086, 0x0006, 0x00c0, 0x34c8, 0x2001, 0x4000, 0x0078, 0x34c9,
-       0x2001, 0x4007, 0x0078, 0x34c9, 0x2400, 0xa106, 0x00c0, 0x34b3,
-       0x6e14, 0x87ff, 0x00c0, 0x34af, 0x86ff, 0x0040, 0x347f, 0x2001,
-       0x4008, 0x0078, 0x34c9, 0x8420, 0x8e70, 0x00f0, 0x3477, 0x85ff,
-       0x00c0, 0x34c2, 0x2001, 0x4009, 0x0078, 0x34c9, 0x2001, 0x0001,
-       0x0078, 0x34c9, 0x1078, 0x4499, 0x00c0, 0x34be, 0x6312, 0x6216,
-       0xa006, 0xa005, 0x0d7f, 0x0e7f, 0x007c, 0x81ff, 0x00c0, 0x2b56,
-       0x1078, 0x3518, 0x0040, 0x2b56, 0x6837, 0x0000, 0x6838, 0xc0fd,
-       0x683a, 0x7824, 0xa005, 0x0040, 0x2b5a, 0xa096, 0x00ff, 0x0040,
-       0x34e5, 0xa092, 0x0004, 0x00c8, 0x2b5a, 0x2010, 0x2d18, 0x1078,
-       0x27c2, 0x0040, 0x2b56, 0x7007, 0x0003, 0x701b, 0x34f0, 0x007c,
-       0x6830, 0xa086, 0x0100, 0x0040, 0x2b56, 0x0078, 0x2b2c, 0x7924,
-       0xa18c, 0xff00, 0x810f, 0xa182, 0x0080, 0x0048, 0x2b5a, 0xa182,
-       0x00ff, 0x00c8, 0x2b5a, 0x127e, 0x2091, 0x8000, 0x1078, 0x8a89,
-       0x00c0, 0x3515, 0xa190, 0xa434, 0x2204, 0xa065, 0x0040, 0x3515,
-       0x1078, 0x4235, 0x127f, 0x0078, 0x2b2c, 0x127f, 0x0078, 0x2b56,
-       0x1078, 0x1381, 0x0040, 0x352f, 0xa006, 0x6802, 0x7010, 0xa005,
-       0x00c0, 0x3527, 0x2d00, 0x7012, 0x7016, 0x0078, 0x352d, 0x7014,
-       0x6802, 0x2060, 0x2d00, 0x6006, 0x7016, 0xad80, 0x000d, 0x007c,
-       0x7924, 0x810f, 0xa18c, 0x00ff, 0x1078, 0x4501, 0x00c0, 0x353f,
-       0x7e28, 0xa684, 0x3fff, 0xa082, 0x4000, 0x0048, 0x3540, 0xa066,
-       0x8cff, 0x007c, 0x7e24, 0x860f, 0xa18c, 0x00ff, 0x1078, 0x4501,
-       0x00c0, 0x3550, 0xa6b4, 0x00ff, 0xa682, 0x4000, 0x0048, 0x3551,
-       0xa066, 0x8cff, 0x007c, 0x017e, 0x7110, 0x81ff, 0x0040, 0x355e,
-       0x2168, 0x6904, 0x1078, 0x139a, 0x0078, 0x3555, 0x7112, 0x7116,
-       0x017f, 0x007c, 0x2031, 0x0001, 0x0078, 0x3568, 0x2031, 0x0000,
-       0x2061, 0xa3d1, 0x6606, 0x6112, 0x600e, 0x6226, 0x632a, 0x642e,
-       0x6532, 0x2c10, 0x1078, 0x13d1, 0x7007, 0x0002, 0x701b, 0x2b2c,
-       0x007c, 0x0f7e, 0x127e, 0x2091, 0x8000, 0x2079, 0x0000, 0x2001,
-       0xa38f, 0x2004, 0xa005, 0x00c0, 0x3594, 0x0068, 0x3594, 0x7818,
-       0xd084, 0x00c0, 0x3594, 0x7a22, 0x7b26, 0x7c2a, 0x781b, 0x0001,
-       0x2091, 0x4080, 0x0078, 0x35b9, 0x017e, 0x0c7e, 0x0e7e, 0x2071,
-       0xa381, 0x7138, 0xa182, 0x0008, 0x0048, 0x35a2, 0x7030, 0x2060,
-       0x0078, 0x35b3, 0x7030, 0xa0e0, 0x0008, 0xac82, 0xa3d1, 0x0048,
-       0x35ab, 0x2061, 0xa391, 0x2c00, 0x7032, 0x81ff, 0x00c0, 0x35b1,
-       0x7036, 0x8108, 0x713a, 0x2262, 0x6306, 0x640a, 0x0e7f, 0x0c7f,
-       0x017f, 0x127f, 0x0f7f, 0x007c, 0x0e7e, 0x2071, 0xa381, 0x7038,
-       0xa005, 0x0040, 0x35f5, 0x127e, 0x2091, 0x8000, 0x0068, 0x35f4,
-       0x0f7e, 0x2079, 0x0000, 0x7818, 0xd084, 0x00c0, 0x35f3, 0x0c7e,
-       0x7034, 0x2060, 0x2c04, 0x7822, 0x6004, 0x7826, 0x6008, 0x782a,
-       0x781b, 0x0001, 0x2091, 0x4080, 0x7038, 0x8001, 0x703a, 0xa005,
-       0x00c0, 0x35e9, 0x7033, 0xa391, 0x7037, 0xa391, 0x0c7f, 0x0078,
-       0x35f3, 0xac80, 0x0008, 0xa0fa, 0xa3d1, 0x0048, 0x35f1, 0x2001,
-       0xa391, 0x7036, 0x0c7f, 0x0f7f, 0x127f, 0x0e7f, 0x007c, 0x027e,
-       0x2001, 0xa352, 0x2004, 0xd0c4, 0x0040, 0x3602, 0x2011, 0x8014,
-       0x1078, 0x3579, 0x027f, 0x007c, 0x81ff, 0x00c0, 0x2b56, 0x127e,
-       0x2091, 0x8000, 0x6030, 0xc08d, 0xc085, 0xc0ac, 0x6032, 0x1078,
-       0x4171, 0x127f, 0x0078, 0x2b2c, 0x7824, 0x2008, 0xa18c, 0xfffd,
-       0x00c0, 0x361f, 0x61d4, 0xa10d, 0x61d6, 0x0078, 0x2b2c, 0x0078,
-       0x2b5a, 0x81ff, 0x00c0, 0x2b56, 0x6000, 0xa086, 0x0003, 0x00c0,
-       0x2b56, 0x2001, 0xa352, 0x2004, 0xd0ac, 0x00c0, 0x2b56, 0x1078,
-       0x3542, 0x0040, 0x2b5a, 0x6004, 0xa084, 0x00ff, 0xa086, 0x0006,
-       0x00c0, 0x363e, 0x7828, 0xa005, 0x0040, 0x2b2c, 0x0c7e, 0x1078,
-       0x3518, 0x0c7f, 0x0040, 0x2b56, 0x6837, 0x0000, 0x6833, 0x0000,
-       0x6838, 0xc0fd, 0x683a, 0x1078, 0x8c4d, 0x0040, 0x2b56, 0x7007,
-       0x0003, 0x701b, 0x3654, 0x007c, 0x6830, 0xa086, 0x0100, 0x0040,
-       0x2b56, 0x0078, 0x2b2c, 0x2001, 0xa300, 0x2004, 0xa086, 0x0003,
-       0x00c0, 0x2b56, 0x7f24, 0x7a2c, 0x7b28, 0x7c3c, 0x7d38, 0x1078,
-       0x3518, 0x0040, 0x2b56, 0x2009, 0x0000, 0x2031, 0x0000, 0x7023,
-       0x0000, 0x702f, 0x0000, 0xad80, 0x0005, 0x7026, 0x20a0, 0x1078,
-       0x4501, 0x00c0, 0x36d8, 0x6004, 0xa0c4, 0x00ff, 0xa8c6, 0x0006,
-       0x0040, 0x3688, 0xa0c4, 0xff00, 0xa8c6, 0x0600, 0x00c0, 0x36d8,
-       0x2001, 0xa352, 0x2004, 0xd0ac, 0x00c0, 0x3695, 0x1078, 0x47cb,
-       0x00c0, 0x3695, 0xd79c, 0x0040, 0x36d8, 0xd794, 0x00c0, 0x369b,
-       0xd784, 0x0040, 0x36a7, 0xac80, 0x0006, 0x2098, 0x3400, 0x20a9,
-       0x0004, 0x53a3, 0x1078, 0x338c, 0xd794, 0x0040, 0x36b0, 0xac80,
-       0x000a, 0x2098, 0x3400, 0x20a9, 0x0004, 0x53a3, 0x1078, 0x338c,
-       0x21a2, 0xd794, 0x0040, 0x36d0, 0xac80, 0x0000, 0x2098, 0x94a0,
-       0x20a9, 0x0002, 0x53a3, 0xac80, 0x0003, 0x20a6, 0x94a0, 0xac80,
-       0x0004, 0x2098, 0x3400, 0x20a9, 0x0002, 0x53a3, 0x1078, 0x337e,
-       0xac80, 0x0026, 0x2098, 0x20a9, 0x0002, 0x53a3, 0x0078, 0x36d1,
-       0x94a0, 0xd794, 0x0040, 0x36d6, 0xa6b0, 0x000b, 0xa6b0, 0x0005,
-       0x8108, 0xd78c, 0x0040, 0x36e2, 0xa186, 0x0100, 0x0040, 0x36f3,
-       0x0078, 0x36e6, 0xa186, 0x007e, 0x0040, 0x36f3, 0xd794, 0x0040,
-       0x36ed, 0xa686, 0x0020, 0x0078, 0x36ef, 0xa686, 0x0028, 0x0040,
-       0x36fc, 0x0078, 0x3677, 0x86ff, 0x00c0, 0x36fa, 0x7120, 0x810b,
-       0x0078, 0x2b2c, 0x702f, 0x0001, 0x711e, 0x7020, 0xa600, 0x7022,
-       0x772a, 0x2061, 0xa3d1, 0x6007, 0x0000, 0x6612, 0x7024, 0x600e,
-       0x6226, 0x632a, 0x642e, 0x6532, 0x2c10, 0x1078, 0x13d1, 0x7007,
-       0x0002, 0x701b, 0x3714, 0x007c, 0x702c, 0xa005, 0x00c0, 0x3726,
-       0x711c, 0x7024, 0x20a0, 0x7728, 0x2031, 0x0000, 0x2061, 0xa3d1,
-       0x6224, 0x6328, 0x642c, 0x6530, 0x0078, 0x3677, 0x7120, 0x810b,
-       0x0078, 0x2b2c, 0x2029, 0x007e, 0x7924, 0x7a28, 0x7b2c, 0x7c38,
-       0xa184, 0xff00, 0x8007, 0xa0e2, 0x0020, 0x0048, 0x2b5a, 0xa502,
-       0x0048, 0x2b5a, 0xa184, 0x00ff, 0xa0e2, 0x0020, 0x0048, 0x2b5a,
-       0xa502, 0x0048, 0x2b5a, 0xa284, 0xff00, 0x8007, 0xa0e2, 0x0020,
-       0x0048, 0x2b5a, 0xa502, 0x0048, 0x2b5a, 0xa284, 0x00ff, 0xa0e2,
-       0x0020, 0x0048, 0x2b5a, 0xa502, 0x0048, 0x2b5a, 0xa384, 0xff00,
-       0x8007, 0xa0e2, 0x0020, 0x0048, 0x2b5a, 0xa502, 0x0048, 0x2b5a,
-       0xa384, 0x00ff, 0xa0e2, 0x0020, 0x0048, 0x2b5a, 0xa502, 0x0048,
-       0x2b5a, 0xa484, 0xff00, 0x8007, 0xa0e2, 0x0020, 0x0048, 0x2b5a,
-       0xa502, 0x0048, 0x2b5a, 0xa484, 0x00ff, 0xa0e2, 0x0020, 0x0048,
-       0x2b5a, 0xa502, 0x0048, 0x2b5a, 0x2061, 0xa5a3, 0x6102, 0x6206,
-       0x630a, 0x640e, 0x0078, 0x2b2c, 0x007e, 0x2001, 0xa352, 0x2004,
-       0xd0cc, 0x007f, 0x007c, 0x007e, 0x2001, 0xa371, 0x2004, 0xd0bc,
-       0x007f, 0x007c, 0x6160, 0x7a24, 0x6300, 0x82ff, 0x00c0, 0x379b,
-       0x7926, 0x0078, 0x2b2c, 0x83ff, 0x00c0, 0x2b5a, 0x2001, 0xfff0,
-       0xa200, 0x00c8, 0x2b5a, 0x2019, 0xffff, 0x6064, 0xa302, 0xa200,
-       0x0048, 0x2b5a, 0x7926, 0x6262, 0x0078, 0x2b2c, 0x2001, 0xa300,
-       0x2004, 0xa086, 0x0003, 0x00c0, 0x2b56, 0x7c28, 0x7d24, 0x7e38,
-       0x7f2c, 0x1078, 0x3518, 0x0040, 0x2b56, 0x2009, 0x0000, 0x2019,
-       0x0000, 0x7023, 0x0000, 0x702f, 0x0000, 0xad80, 0x0003, 0x7026,
-       0x20a0, 0xa1e0, 0xa434, 0x2c64, 0x8cff, 0x0040, 0x37e8, 0x6004,
-       0xa084, 0x00ff, 0xa086, 0x0006, 0x0040, 0x37dd, 0x6004, 0xa084,
-       0xff00, 0xa086, 0x0600, 0x00c0, 0x37e8, 0x6014, 0x20a2, 0x94a0,
-       0x6010, 0x8007, 0xa105, 0x8007, 0x20a2, 0x94a0, 0xa398, 0x0002,
-       0x8108, 0xa182, 0x00ff, 0x0040, 0x37f3, 0xa386, 0x002a, 0x0040,
-       0x37fc, 0x0078, 0x37c9, 0x83ff, 0x00c0, 0x37fa, 0x7120, 0x810c,
-       0x0078, 0x2b2c, 0x702f, 0x0001, 0x711e, 0x7020, 0xa300, 0x7022,
-       0x2061, 0xa3d1, 0x6007, 0x0000, 0x6312, 0x7024, 0x600e, 0x6426,
-       0x652a, 0x662e, 0x6732, 0x2c10, 0x1078, 0x13d1, 0x7007, 0x0002,
-       0x701b, 0x3813, 0x007c, 0x702c, 0xa005, 0x00c0, 0x3824, 0x711c,
-       0x7024, 0x20a0, 0x2019, 0x0000, 0x2061, 0xa3d1, 0x6424, 0x6528,
-       0x662c, 0x6730, 0x0078, 0x37c9, 0x7120, 0x810c, 0x0078, 0x2b2c,
-       0x81ff, 0x00c0, 0x2b56, 0x60c8, 0xd09c, 0x0040, 0x2b56, 0x1078,
-       0x3518, 0x0040, 0x2b56, 0x7924, 0x7a2c, 0x7b28, 0x7c3c, 0x7d38,
-       0x1078, 0x3562, 0x701b, 0x383d, 0x007c, 0x0d7e, 0xade8, 0x000d,
-       0x6828, 0xa0be, 0x7000, 0x0040, 0x3850, 0xa0be, 0x7100, 0x0040,
-       0x3850, 0xa0be, 0x7200, 0x0040, 0x3850, 0x0d7f, 0x0078, 0x2b5a,
-       0x6820, 0x6924, 0x1078, 0x24e3, 0x00c0, 0x387b, 0x1078, 0x4499,
-       0x00c0, 0x387b, 0x7122, 0x6612, 0x6516, 0x6e18, 0x0c7e, 0x1078,
-       0x3518, 0x0040, 0x387b, 0x1078, 0x3518, 0x0040, 0x387b, 0x0c7f,
-       0x0d7f, 0x6837, 0x0000, 0x6838, 0xc0fd, 0x683a, 0x6823, 0x0000,
-       0x6804, 0x2068, 0x1078, 0x8bbd, 0x0040, 0x2b56, 0x7007, 0x0003,
-       0x701b, 0x387e, 0x007c, 0x0d7f, 0x0078, 0x2b56, 0x7120, 0x1078,
-       0x2921, 0x6820, 0xa086, 0x8001, 0x0040, 0x2b56, 0x2d00, 0x701e,
-       0x6804, 0xa080, 0x0002, 0x007e, 0x20a9, 0x002a, 0x2098, 0x20a0,
-       0x1078, 0x41be, 0x007f, 0xade8, 0x000d, 0x6a08, 0x6b0c, 0x6c10,
-       0x6d14, 0x2061, 0xa3d1, 0x6007, 0x0000, 0x6e00, 0x6f28, 0xa7c6,
-       0x7000, 0x00c0, 0x38a5, 0x0078, 0x38a9, 0xa7c6, 0x7100, 0x00c0,
-       0x38b1, 0xa6c2, 0x0004, 0x0048, 0x2b5a, 0x2009, 0x0004, 0x0078,
-       0x3566, 0xa7c6, 0x7200, 0x00c0, 0x2b5a, 0xa6c2, 0x0054, 0x0048,
-       0x2b5a, 0x600e, 0x6013, 0x002a, 0x6226, 0x632a, 0x642e, 0x6532,
-       0x2c10, 0x1078, 0x13d1, 0x7007, 0x0002, 0x701b, 0x38c8, 0x007c,
-       0x701c, 0x2068, 0x6804, 0xa080, 0x0001, 0x2004, 0xa080, 0x0002,
-       0x007e, 0x20a9, 0x002a, 0x2098, 0x20a0, 0x1078, 0x41be, 0x007f,
-       0x2009, 0x002a, 0x2061, 0xa3d1, 0x6224, 0x6328, 0x642c, 0x6530,
-       0x0078, 0x3566, 0x81ff, 0x00c0, 0x2b56, 0x1078, 0x3530, 0x0040,
-       0x2b5a, 0x1078, 0x45a7, 0x0040, 0x2b56, 0x1078, 0x4710, 0x0078,
-       0x2b2c, 0x7824, 0xd084, 0x0040, 0x3150, 0x1078, 0x3542, 0x0040,
-       0x2b5a, 0x0c7e, 0x1078, 0x3518, 0x0c7f, 0x00c0, 0x3903, 0x2009,
-       0x0002, 0x0078, 0x2b56, 0x6004, 0xa084, 0x00ff, 0xa086, 0x0006,
-       0x0040, 0x3910, 0xa08e, 0x0004, 0x0040, 0x3910, 0xa08e, 0x0005,
-       0x00c0, 0x3934, 0x2001, 0xa352, 0x2004, 0xd0b4, 0x0040, 0x3185,
-       0x6000, 0xd08c, 0x00c0, 0x3185, 0x6837, 0x0000, 0x6838, 0xc0fd,
-       0x683a, 0x1078, 0x8bd9, 0x00c0, 0x3929, 0x2009, 0x0003, 0x0078,
-       0x2b56, 0x7007, 0x0003, 0x701b, 0x392e, 0x007c, 0x1078, 0x3542,
-       0x0040, 0x2b5a, 0x0078, 0x3185, 0x2009, 0xa32e, 0x210c, 0x81ff,
-       0x0040, 0x393e, 0x2009, 0x0001, 0x0078, 0x2b56, 0x2001, 0xa300,
-       0x2004, 0xa086, 0x0003, 0x0040, 0x3949, 0x2009, 0x0007, 0x0078,
-       0x2b56, 0x2001, 0xa352, 0x2004, 0xd0ac, 0x0040, 0x3953, 0x2009,
-       0x0008, 0x0078, 0x2b56, 0x609c, 0xd0a4, 0x00c0, 0x395a, 0xd0ac,
-       0x00c0, 0x3185, 0x6837, 0x0000, 0x6833, 0x0000, 0x6838, 0xc0fd,
-       0x683a, 0x1078, 0x8c4d, 0x00c0, 0x3969, 0x2009, 0x0003, 0x0078,
-       0x2b56, 0x7007, 0x0003, 0x701b, 0x396e, 0x007c, 0x6830, 0xa086,
-       0x0100, 0x00c0, 0x3977, 0x2009, 0x0004, 0x0078, 0x2b56, 0x1078,
-       0x3542, 0x0040, 0x2b5a, 0x0078, 0x3912, 0x81ff, 0x2009, 0x0001,
-       0x00c0, 0x2b56, 0x6000, 0xa086, 0x0003, 0x2009, 0x0007, 0x00c0,
-       0x2b56, 0x2001, 0xa352, 0x2004, 0xd0ac, 0x2009, 0x0008, 0x00c0,
-       0x2b56, 0x1078, 0x3542, 0x0040, 0x2b5a, 0x6004, 0xa084, 0x00ff,
-       0xa086, 0x0006, 0x2009, 0x0009, 0x00c0, 0x2b56, 0x0c7e, 0x1078,
-       0x3518, 0x0c7f, 0x2009, 0x0002, 0x0040, 0x2b56, 0x6837, 0x0000,
-       0x6833, 0x0000, 0x6838, 0xc0fd, 0x683a, 0x7928, 0xa194, 0xff00,
-       0xa18c, 0x00ff, 0xa006, 0x82ff, 0x00c0, 0x39bc, 0xc0ed, 0x6952,
-       0x792c, 0x6956, 0x0078, 0x39c5, 0xa28e, 0x0100, 0x00c0, 0x2b5a,
-       0xc0e5, 0x6853, 0x0000, 0x6857, 0x0000, 0x683e, 0x1078, 0x8df6,
-       0x2009, 0x0003, 0x0040, 0x2b56, 0x7007, 0x0003, 0x701b, 0x39d1,
-       0x007c, 0x6830, 0xa086, 0x0100, 0x2009, 0x0004, 0x0040, 0x2b56,
-       0x0078, 0x2b2c, 0x81ff, 0x2009, 0x0001, 0x00c0, 0x2b56, 0x6000,
-       0xa086, 0x0003, 0x2009, 0x0007, 0x00c0, 0x2b56, 0x1078, 0x3542,
-       0x0040, 0x2b5a, 0x6004, 0xa084, 0x00ff, 0xa086, 0x0006, 0x2009,
-       0x0009, 0x00c0, 0x2b56, 0x0c7e, 0x1078, 0x3518, 0x0c7f, 0x2009,
-       0x0002, 0x0040, 0x2b56, 0xad80, 0x000f, 0x2009, 0x0008, 0x7a2c,
-       0x7b28, 0x7c3c, 0x7d38, 0x1078, 0x3562, 0x701b, 0x3a08, 0x007c,
-       0x0d7e, 0xade8, 0x000f, 0x6800, 0xa086, 0x0500, 0x00c0, 0x3a1b,
-       0x6804, 0xa005, 0x00c0, 0x3a1b, 0x6808, 0xa084, 0xff00, 0x00c0,
-       0x3a1b, 0x0078, 0x3a1e, 0x0d7f, 0x00c0, 0x2b5a, 0x0d7f, 0x6837,
-       0x0000, 0x6833, 0x0000, 0x6838, 0xc0fd, 0x683a, 0x0c7e, 0x1078,
-       0x3542, 0x00c0, 0x3a2e, 0x0c7f, 0x0078, 0x2b5a, 0x1078, 0x8e52,
-       0x2009, 0x0003, 0x0c7f, 0x0040, 0x2b56, 0x7007, 0x0003, 0x701b,
-       0x3a3a, 0x007c, 0x6830, 0xa086, 0x0100, 0x2009, 0x0004, 0x0040,
-       0x2b56, 0x0078, 0x2b2c, 0x127e, 0x0c7e, 0x0e7e, 0x2061, 0x0100,
-       0x2071, 0xa300, 0x6044, 0xd0a4, 0x00c0, 0x3a6c, 0xd084, 0x0040,
-       0x3a55, 0x1078, 0x3bcc, 0x0078, 0x3a68, 0xd08c, 0x0040, 0x3a5c,
-       0x1078, 0x3ae3, 0x0078, 0x3a68, 0xd094, 0x0040, 0x3a63, 0x1078,
-       0x3ab7, 0x0078, 0x3a68, 0xd09c, 0x0040, 0x3a68, 0x1078, 0x3a76,
-       0x0e7f, 0x0c7f, 0x127f, 0x007c, 0x017e, 0x6128, 0xd19c, 0x00c0,
-       0x3a73, 0xc19d, 0x612a, 0x017f, 0x0078, 0x3a68, 0x624c, 0xa286,
-       0xf0f0, 0x00c0, 0x3a87, 0x6048, 0xa086, 0xf0f0, 0x0040, 0x3a87,
-       0x624a, 0x6043, 0x0090, 0x6043, 0x0010, 0x0078, 0x3ab6, 0xa294,
-       0xff00, 0xa296, 0xf700, 0x0040, 0x3a9c, 0x7134, 0xd1a4, 0x00c0,
-       0x3a9c, 0x6240, 0xa294, 0x0010, 0x0040, 0x3a9c, 0x2009, 0x00f7,
-       0x1078, 0x41de, 0x0078, 0x3ab6, 0x6043, 0x0040, 0x6043, 0x0000,
-       0x7073, 0x0000, 0x708b, 0x0001, 0x70af, 0x0000, 0x70cb, 0x0000,
-       0x2009, 0xa9c0, 0x200b, 0x0000, 0x7083, 0x0000, 0x7077, 0x000f,
-       0x2009, 0x000f, 0x2011, 0x4122, 0x1078, 0x596c, 0x007c, 0x157e,
-       0x7074, 0xa005, 0x00c0, 0x3ae1, 0x2011, 0x4122, 0x1078, 0x58d4,
-       0x6040, 0xa094, 0x0010, 0xa285, 0x0020, 0x6042, 0x20a9, 0x00c8,
-       0x6044, 0xd08c, 0x00c0, 0x3ada, 0x00f0, 0x3ac8, 0x6242, 0x7087,
-       0x0000, 0x6040, 0xa094, 0x0010, 0xa285, 0x0080, 0x6042, 0x6242,
-       0x0078, 0x3ae1, 0x6242, 0x7087, 0x0000, 0x707b, 0x0000, 0x0078,
-       0x3ae1, 0x157f, 0x007c, 0x7078, 0xa08a, 0x0003, 0x00c8, 0x3aec,
-       0x1079, 0x3aef, 0x0078, 0x3aee, 0x1078, 0x1328, 0x007c, 0x3af2,
-       0x3b41, 0x3bcb, 0x0f7e, 0x707b, 0x0001, 0x20e1, 0xa000, 0x20e1,
-       0x8700, 0x1078, 0x218b, 0x20e1, 0x9080, 0x20e1, 0x4000, 0x2079,
-       0xa800, 0x207b, 0x2200, 0x7807, 0x00ef, 0x780b, 0x0000, 0x780f,
-       0x00ef, 0x7813, 0x0138, 0x7817, 0x0000, 0x781b, 0x0000, 0x781f,
-       0x0000, 0x7823, 0xffff, 0x7827, 0xffff, 0x782b, 0x0000, 0x782f,
-       0x0000, 0x2079, 0xa80c, 0x207b, 0x1101, 0x7807, 0x0000, 0x2099,
-       0xa305, 0x20a1, 0xa80e, 0x20a9, 0x0004, 0x53a3, 0x2079, 0xa812,
-       0x207b, 0x0000, 0x7807, 0x0000, 0x2099, 0xa800, 0x20a1, 0x020b,
-       0x20a9, 0x0014, 0x53a6, 0x60c3, 0x000c, 0x600f, 0x0000, 0x1078,
-       0x4158, 0x0f7f, 0x707f, 0x0000, 0x6043, 0x0008, 0x6043, 0x0000,
-       0x007c, 0x0d7e, 0x707c, 0x707f, 0x0000, 0xa025, 0x0040, 0x3bb5,
-       0x6020, 0xd0b4, 0x00c0, 0x3bb3, 0x7188, 0x81ff, 0x0040, 0x3ba2,
-       0xa486, 0x000c, 0x00c0, 0x3bad, 0xa480, 0x0018, 0x8004, 0x20a8,
-       0x2011, 0xa880, 0x2019, 0xa800, 0x220c, 0x2304, 0xa106, 0x00c0,
-       0x3b79, 0x8210, 0x8318, 0x00f0, 0x3b5c, 0x6043, 0x0004, 0x608b,
-       0xbc94, 0x608f, 0xf0f0, 0x6043, 0x0006, 0x707b, 0x0002, 0x7087,
-       0x0002, 0x2009, 0x07d0, 0x2011, 0x4129, 0x1078, 0x596c, 0x0078,
-       0x3bb3, 0x2069, 0xa880, 0x6930, 0xa18e, 0x1101, 0x00c0, 0x3bad,
-       0x6834, 0xa005, 0x00c0, 0x3bad, 0x6900, 0xa18c, 0x00ff, 0x00c0,
-       0x3b8d, 0x6804, 0xa005, 0x0040, 0x3ba2, 0x2011, 0xa88e, 0x2019,
-       0xa305, 0x20a9, 0x0004, 0x220c, 0x2304, 0xa102, 0x0048, 0x3ba0,
-       0x00c0, 0x3bad, 0x8210, 0x8318, 0x00f0, 0x3b93, 0x0078, 0x3bad,
-       0x708b, 0x0000, 0x20e1, 0x9080, 0x20e1, 0x4000, 0x2099, 0xa880,
-       0x20a1, 0x020b, 0x20a9, 0x0014, 0x53a6, 0x6043, 0x0008, 0x6043,
-       0x0000, 0x0078, 0x3bb5, 0x0d7f, 0x007c, 0x6020, 0xd0b4, 0x00c0,
-       0x3bb3, 0x60c3, 0x000c, 0x2011, 0xa5b5, 0x2013, 0x0000, 0x707f,
-       0x0000, 0x20e1, 0x9080, 0x60a3, 0x0056, 0x60a7, 0x9575, 0x1078,
-       0x6c38, 0x0078, 0x3bb3, 0x007c, 0x7084, 0xa08a, 0x001d, 0x00c8,
-       0x3bd5, 0x1079, 0x3bd8, 0x0078, 0x3bd7, 0x1078, 0x1328, 0x007c,
-       0x3c02, 0x3c11, 0x3c40, 0x3c59, 0x3c85, 0x3cb1, 0x3cdd, 0x3d13,
-       0x3d3f, 0x3d67, 0x3daa, 0x3dd4, 0x3df6, 0x3e0c, 0x3e32, 0x3e45,
-       0x3e4e, 0x3e7e, 0x3eaa, 0x3ed6, 0x3f02, 0x3f38, 0x3f7d, 0x3fac,
-       0x3fce, 0x4010, 0x4036, 0x404f, 0x4050, 0x0c7e, 0x2061, 0xa300,
-       0x6003, 0x0007, 0x2061, 0x0100, 0x6004, 0xa084, 0xfff9, 0x6006,
-       0x0c7f, 0x007c, 0x608b, 0xbc94, 0x608f, 0xf0f0, 0x6043, 0x0002,
-       0x7087, 0x0001, 0x2009, 0x07d0, 0x2011, 0x4129, 0x1078, 0x596c,
-       0x007c, 0x0f7e, 0x707c, 0xa086, 0x0014, 0x00c0, 0x3c3e, 0x6043,
-       0x0000, 0x6020, 0xd0b4, 0x00c0, 0x3c3e, 0x2079, 0xa880, 0x7a30,
-       0xa296, 0x1102, 0x00c0, 0x3c3c, 0x7834, 0xa005, 0x00c0, 0x3c3c,
-       0x7a38, 0xd2fc, 0x0040, 0x3c32, 0x70ac, 0xa005, 0x00c0, 0x3c32,
-       0x70af, 0x0001, 0x2011, 0x4129, 0x1078, 0x58d4, 0x7087, 0x0010,
-       0x1078, 0x3e4e, 0x0078, 0x3c3e, 0x1078, 0x4171, 0x0f7f, 0x007c,
-       0x7087, 0x0003, 0x6043, 0x0004, 0x2011, 0x4129, 0x1078, 0x58d4,
-       0x1078, 0x41c6, 0x20a3, 0x1102, 0x20a3, 0x0000, 0x20a9, 0x000a,
-       0x20a3, 0x0000, 0x00f0, 0x3c50, 0x60c3, 0x0014, 0x1078, 0x4158,
-       0x007c, 0x0f7e, 0x707c, 0xa005, 0x0040, 0x3c83, 0x2011, 0x4129,
-       0x1078, 0x58d4, 0xa086, 0x0014, 0x00c0, 0x3c81, 0x2079, 0xa880,
-       0x7a30, 0xa296, 0x1102, 0x00c0, 0x3c81, 0x7834, 0xa005, 0x00c0,
-       0x3c81, 0x7a38, 0xd2fc, 0x0040, 0x3c7b, 0x70ac, 0xa005, 0x00c0,
-       0x3c7b, 0x70af, 0x0001, 0x7087, 0x0004, 0x1078, 0x3c85, 0x0078,
-       0x3c83, 0x1078, 0x4171, 0x0f7f, 0x007c, 0x7087, 0x0005, 0x1078,
-       0x41c6, 0x20a3, 0x1103, 0x20a3, 0x0000, 0x3430, 0x2011, 0xa88e,
-       0x1078, 0x4211, 0x00c0, 0x3ca3, 0x7070, 0xa005, 0x00c0, 0x3ca3,
-       0x714c, 0xa186, 0xffff, 0x0040, 0x3ca3, 0x1078, 0x40ea, 0x0040,
-       0x3ca3, 0x1078, 0x41f5, 0x20a9, 0x0008, 0x2298, 0x26a0, 0x53a6,
-       0x20a3, 0x0000, 0x20a3, 0x0000, 0x60c3, 0x0014, 0x1078, 0x4158,
-       0x007c, 0x0f7e, 0x707c, 0xa005, 0x0040, 0x3cdb, 0x2011, 0x4129,
-       0x1078, 0x58d4, 0xa086, 0x0014, 0x00c0, 0x3cd9, 0x2079, 0xa880,
-       0x7a30, 0xa296, 0x1103, 0x00c0, 0x3cd9, 0x7834, 0xa005, 0x00c0,
-       0x3cd9, 0x7a38, 0xd2fc, 0x0040, 0x3cd3, 0x70ac, 0xa005, 0x00c0,
-       0x3cd3, 0x70af, 0x0001, 0x7087, 0x0006, 0x1078, 0x3cdd, 0x0078,
-       0x3cdb, 0x1078, 0x4171, 0x0f7f, 0x007c, 0x7087, 0x0007, 0x1078,
-       0x41c6, 0x20a3, 0x1104, 0x20a3, 0x0000, 0x3430, 0x2011, 0xa88e,
-       0x1078, 0x4211, 0x00c0, 0x3d05, 0x7070, 0xa005, 0x00c0, 0x3d05,
-       0x7150, 0xa186, 0xffff, 0x0040, 0x3d05, 0xa180, 0x293f, 0x200c,
-       0xa18c, 0xff00, 0x810f, 0x1078, 0x40ea, 0x0040, 0x3d05, 0x1078,
-       0x378b, 0x0040, 0x3d05, 0x1078, 0x2500, 0x20a9, 0x0008, 0x2298,
-       0x26a0, 0x53a6, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x60c3, 0x0014,
-       0x1078, 0x4158, 0x007c, 0x0f7e, 0x707c, 0xa005, 0x0040, 0x3d3d,
-       0x2011, 0x4129, 0x1078, 0x58d4, 0xa086, 0x0014, 0x00c0, 0x3d3b,
-       0x2079, 0xa880, 0x7a30, 0xa296, 0x1104, 0x00c0, 0x3d3b, 0x7834,
-       0xa005, 0x00c0, 0x3d3b, 0x7a38, 0xd2fc, 0x0040, 0x3d35, 0x70ac,
-       0xa005, 0x00c0, 0x3d35, 0x70af, 0x0001, 0x7087, 0x0008, 0x1078,
-       0x3d3f, 0x0078, 0x3d3d, 0x1078, 0x4171, 0x0f7f, 0x007c, 0x7087,
-       0x0009, 0x1078, 0x41c6, 0x20a3, 0x1105, 0x20a3, 0x0100, 0x3430,
-       0x1078, 0x4211, 0x00c0, 0x3d58, 0x7070, 0xa005, 0x00c0, 0x3d58,
-       0x1078, 0x4051, 0x00c0, 0x3d62, 0xa085, 0x0001, 0x1078, 0x2500,
-       0x20a9, 0x0008, 0x2099, 0xa88e, 0x26a0, 0x53a6, 0x20a3, 0x0000,
-       0x20a3, 0x0000, 0x60c3, 0x0014, 0x1078, 0x4158, 0x007c, 0x0f7e,
-       0x707c, 0xa005, 0x0040, 0x3da8, 0x2011, 0x4129, 0x1078, 0x58d4,
-       0xa086, 0x0014, 0x00c0, 0x3da6, 0x2079, 0xa880, 0x7a30, 0xa296,
-       0x1105, 0x00c0, 0x3da6, 0x7834, 0x2011, 0x0100, 0xa21e, 0x00c0,
-       0x3d91, 0x7a38, 0xd2fc, 0x0040, 0x3d8b, 0x70ac, 0xa005, 0x00c0,
-       0x3d8b, 0x70af, 0x0001, 0x7087, 0x000a, 0x1078, 0x3daa, 0x0078,
-       0x3da8, 0xa005, 0x00c0, 0x3da6, 0x7a38, 0xd2fc, 0x0040, 0x3d9e,
-       0x70ac, 0xa005, 0x00c0, 0x3d9e, 0x70af, 0x0001, 0x7083, 0x0000,
-       0x7087, 0x000e, 0x1078, 0x3e32, 0x0078, 0x3da8, 0x1078, 0x4171,
-       0x0f7f, 0x007c, 0x7087, 0x000b, 0x2011, 0xa80e, 0x22a0, 0x20a9,
-       0x0040, 0x2019, 0xffff, 0x43a4, 0x20a9, 0x0002, 0x2009, 0x0000,
-       0x41a4, 0x1078, 0x41c6, 0x20a3, 0x1106, 0x20a3, 0x0000, 0x1078,
-       0x4211, 0x0040, 0x3dc7, 0x2013, 0x0000, 0x0078, 0x3dcb, 0x6030,
-       0xa085, 0x0100, 0x2012, 0x2298, 0x20a9, 0x0042, 0x53a6, 0x60c3,
-       0x0084, 0x1078, 0x4158, 0x007c, 0x0f7e, 0x707c, 0xa005, 0x0040,
-       0x3df4, 0x2011, 0x4129, 0x1078, 0x58d4, 0xa086, 0x0084, 0x00c0,
-       0x3df2, 0x2079, 0xa880, 0x7a30, 0xa296, 0x1106, 0x00c0, 0x3df2,
-       0x7834, 0xa005, 0x00c0, 0x3df2, 0x7087, 0x000c, 0x1078, 0x3df6,
-       0x0078, 0x3df4, 0x1078, 0x4171, 0x0f7f, 0x007c, 0x7087, 0x000d,
-       0x1078, 0x41c6, 0x20a3, 0x1107, 0x20a3, 0x0000, 0x2099, 0xa88e,
-       0x20a9, 0x0040, 0x53a6, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x60c3,
-       0x0084, 0x1078, 0x4158, 0x007c, 0x0f7e, 0x707c, 0xa005, 0x0040,
-       0x3e30, 0x2011, 0x4129, 0x1078, 0x58d4, 0xa086, 0x0084, 0x00c0,
-       0x3e2e, 0x2079, 0xa880, 0x7a30, 0xa296, 0x1107, 0x00c0, 0x3e2e,
-       0x7834, 0xa005, 0x00c0, 0x3e2e, 0x7083, 0x0001, 0x1078, 0x41b8,
-       0x7087, 0x000e, 0x1078, 0x3e32, 0x0078, 0x3e30, 0x1078, 0x4171,
-       0x0f7f, 0x007c, 0x7087, 0x000f, 0x707f, 0x0000, 0x608b, 0xbc85,
-       0x608f, 0xb5b5, 0x6043, 0x0005, 0x6043, 0x0004, 0x2009, 0x07d0,
-       0x2011, 0x4129, 0x1078, 0x58c7, 0x007c, 0x707c, 0xa005, 0x0040,
-       0x3e4d, 0x2011, 0x4129, 0x1078, 0x58d4, 0x007c, 0x7087, 0x0011,
-       0x1078, 0x4211, 0x00c0, 0x3e67, 0x7168, 0x81ff, 0x0040, 0x3e67,
-       0x2009, 0x0000, 0x706c, 0xa084, 0x00ff, 0x1078, 0x24e3, 0xa186,
-       0x0080, 0x0040, 0x3e67, 0x2011, 0xa88e, 0x1078, 0x40ea, 0x20e1,
-       0x9080, 0x20e1, 0x4000, 0x2099, 0xa880, 0x20a1, 0x020b, 0x747c,
-       0xa480, 0x0018, 0xa080, 0x0007, 0xa084, 0x03f8, 0x8004, 0x20a8,
-       0x53a6, 0x60c3, 0x0014, 0x1078, 0x4158, 0x007c, 0x0f7e, 0x707c,
-       0xa005, 0x0040, 0x3ea8, 0x2011, 0x4129, 0x1078, 0x58d4, 0xa086,
-       0x0014, 0x00c0, 0x3ea6, 0x2079, 0xa880, 0x7a30, 0xa296, 0x1103,
-       0x00c0, 0x3ea6, 0x7834, 0xa005, 0x00c0, 0x3ea6, 0x7a38, 0xd2fc,
-       0x0040, 0x3ea0, 0x70ac, 0xa005, 0x00c0, 0x3ea0, 0x70af, 0x0001,
-       0x7087, 0x0012, 0x1078, 0x3eaa, 0x0078, 0x3ea8, 0x1078, 0x4171,
-       0x0f7f, 0x007c, 0x7087, 0x0013, 0x1078, 0x41d2, 0x20a3, 0x1103,
-       0x20a3, 0x0000, 0x3430, 0x2011, 0xa88e, 0x1078, 0x4211, 0x00c0,
-       0x3ec8, 0x7070, 0xa005, 0x00c0, 0x3ec8, 0x714c, 0xa186, 0xffff,
-       0x0040, 0x3ec8, 0x1078, 0x40ea, 0x0040, 0x3ec8, 0x1078, 0x41f5,
-       0x20a9, 0x0008, 0x2298, 0x26a0, 0x53a6, 0x20a3, 0x0000, 0x20a3,
-       0x0000, 0x60c3, 0x0014, 0x1078, 0x4158, 0x007c, 0x0f7e, 0x707c,
-       0xa005, 0x0040, 0x3f00, 0x2011, 0x4129, 0x1078, 0x58d4, 0xa086,
-       0x0014, 0x00c0, 0x3efe, 0x2079, 0xa880, 0x7a30, 0xa296, 0x1104,
-       0x00c0, 0x3efe, 0x7834, 0xa005, 0x00c0, 0x3efe, 0x7a38, 0xd2fc,
-       0x0040, 0x3ef8, 0x70ac, 0xa005, 0x00c0, 0x3ef8, 0x70af, 0x0001,
-       0x7087, 0x0014, 0x1078, 0x3f02, 0x0078, 0x3f00, 0x1078, 0x4171,
-       0x0f7f, 0x007c, 0x7087, 0x0015, 0x1078, 0x41d2, 0x20a3, 0x1104,
-       0x20a3, 0x0000, 0x3430, 0x2011, 0xa88e, 0x1078, 0x4211, 0x00c0,
-       0x3f2a, 0x7070, 0xa005, 0x00c0, 0x3f2a, 0x7150, 0xa186, 0xffff,
-       0x0040, 0x3f2a, 0xa180, 0x293f, 0x200c, 0xa18c, 0xff00, 0x810f,
-       0x1078, 0x40ea, 0x0040, 0x3f2a, 0x1078, 0x378b, 0x0040, 0x3f2a,
-       0x1078, 0x2500, 0x20a9, 0x0008, 0x2298, 0x26a0, 0x53a6, 0x20a3,
-       0x0000, 0x20a3, 0x0000, 0x60c3, 0x0014, 0x1078, 0x4158, 0x007c,
-       0x0f7e, 0x707c, 0xa005, 0x0040, 0x3f7b, 0x2011, 0x4129, 0x1078,
-       0x58d4, 0xa086, 0x0014, 0x00c0, 0x3f79, 0x2079, 0xa880, 0x7a30,
-       0xa296, 0x1105, 0x00c0, 0x3f79, 0x7834, 0x2011, 0x0100, 0xa21e,
-       0x00c0, 0x3f5e, 0x7a38, 0xd2fc, 0x0040, 0x3f5c, 0x70ac, 0xa005,
-       0x00c0, 0x3f5c, 0x70af, 0x0001, 0x0078, 0x3f6d, 0xa005, 0x00c0,
-       0x3f79, 0x7a38, 0xd2fc, 0x0040, 0x3f6b, 0x70ac, 0xa005, 0x00c0,
-       0x3f6b, 0x70af, 0x0001, 0x7083, 0x0000, 0x7a38, 0xd2f4, 0x0040,
-       0x3f73, 0x70cb, 0x0008, 0x7087, 0x0016, 0x1078, 0x3f7d, 0x0078,
-       0x3f7b, 0x1078, 0x4171, 0x0f7f, 0x007c, 0x20e1, 0x9080, 0x20e1,
-       0x4000, 0x2099, 0xa880, 0x20a1, 0x020b, 0x20a9, 0x000e, 0x53a6,
-       0x3430, 0x2011, 0xa88e, 0x7087, 0x0017, 0x1078, 0x4211, 0x00c0,
-       0x3f9d, 0x7070, 0xa005, 0x00c0, 0x3f9d, 0x1078, 0x4051, 0x00c0,
-       0x3fa7, 0xa085, 0x0001, 0x1078, 0x2500, 0x20a9, 0x0008, 0x2099,
-       0xa88e, 0x26a0, 0x53a6, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x60c3,
-       0x0014, 0x1078, 0x4158, 0x007c, 0x0f7e, 0x707c, 0xa005, 0x0040,
-       0x3fcc, 0x2011, 0x4129, 0x1078, 0x58d4, 0xa086, 0x0084, 0x00c0,
-       0x3fca, 0x2079, 0xa880, 0x7a30, 0xa296, 0x1106, 0x00c0, 0x3fca,
-       0x7834, 0xa005, 0x00c0, 0x3fca, 0x7087, 0x0018, 0x1078, 0x3fce,
-       0x0078, 0x3fcc, 0x1078, 0x4171, 0x0f7f, 0x007c, 0x7087, 0x0019,
-       0x1078, 0x41d2, 0x20a3, 0x1106, 0x20a3, 0x0000, 0x3430, 0x2099,
-       0xa88e, 0x2039, 0xa80e, 0x27a0, 0x20a9, 0x0040, 0x53a3, 0x1078,
-       0x4211, 0x00c0, 0x4002, 0x2728, 0x2514, 0x8207, 0xa084, 0x00ff,
-       0x8000, 0x2018, 0xa294, 0x00ff, 0x8007, 0xa205, 0x202a, 0x6030,
-       0x2310, 0x8214, 0xa2a0, 0xa80e, 0x2414, 0xa38c, 0x0001, 0x0040,
-       0x3ffd, 0xa294, 0xff00, 0x0078, 0x4000, 0xa294, 0x00ff, 0x8007,
-       0xa215, 0x2222, 0x2798, 0x26a0, 0x20a9, 0x0040, 0x53a6, 0x20a3,
-       0x0000, 0x20a3, 0x0000, 0x60c3, 0x0084, 0x1078, 0x4158, 0x007c,
-       0x0f7e, 0x707c, 0xa005, 0x0040, 0x4034, 0x2011, 0x4129, 0x1078,
-       0x58d4, 0xa086, 0x0084, 0x00c0, 0x4032, 0x2079, 0xa880, 0x7a30,
-       0xa296, 0x1107, 0x00c0, 0x4032, 0x7834, 0xa005, 0x00c0, 0x4032,
-       0x7083, 0x0001, 0x1078, 0x41b8, 0x7087, 0x001a, 0x1078, 0x4036,
-       0x0078, 0x4034, 0x1078, 0x4171, 0x0f7f, 0x007c, 0x7087, 0x001b,
-       0x20e1, 0x9080, 0x20e1, 0x4000, 0x2099, 0xa880, 0x20a1, 0x020b,
-       0x747c, 0xa480, 0x0018, 0xa080, 0x0007, 0xa084, 0x03f8, 0x8004,
-       0x20a8, 0x53a6, 0x60c3, 0x0084, 0x1078, 0x4158, 0x007c, 0x007c,
-       0x007c, 0x087e, 0x097e, 0x2029, 0xa352, 0x252c, 0x20a9, 0x0008,
-       0x2041, 0xa80e, 0x28a0, 0x2099, 0xa88e, 0x53a3, 0x20a9, 0x0008,
-       0x2011, 0x0007, 0xd5d4, 0x0040, 0x4067, 0x2011, 0x0000, 0x2800,
-       0xa200, 0x200c, 0xa1a6, 0xffff, 0x00c0, 0x4079, 0xd5d4, 0x0040,
-       0x4074, 0x8210, 0x0078, 0x4075, 0x8211, 0x00f0, 0x4067, 0x0078,
-       0x40e1, 0x82ff, 0x00c0, 0x408b, 0xd5d4, 0x0040, 0x4085, 0xa1a6,
-       0x3fff, 0x0040, 0x4071, 0x0078, 0x4089, 0xa1a6, 0x3fff, 0x0040,
-       0x40e1, 0xa18d, 0xc000, 0x20a9, 0x0010, 0x2019, 0x0001, 0xd5d4,
-       0x0040, 0x4094, 0x2019, 0x0010, 0x2120, 0xd5d4, 0x0040, 0x409b,
-       0x8423, 0x0078, 0x409c, 0x8424, 0x00c8, 0x40a9, 0xd5d4, 0x0040,
-       0x40a4, 0x8319, 0x0078, 0x40a5, 0x8318, 0x00f0, 0x4095, 0x0078,
-       0x40e1, 0x23a8, 0x2021, 0x0001, 0x8426, 0x8425, 0x00f0, 0x40ad,
-       0x2328, 0x8529, 0xa2be, 0x0007, 0x0040, 0x40c1, 0x007e, 0x2039,
-       0x0007, 0x2200, 0xa73a, 0x007f, 0x27a8, 0xa5a8, 0x0010, 0x00f0,
-       0x40bd, 0x754e, 0xa5c8, 0x293f, 0x292c, 0xa5ac, 0x00ff, 0x6532,
-       0x60e7, 0x0000, 0x65ea, 0x706b, 0x0000, 0x756e, 0x2018, 0x2304,
-       0xa405, 0x201a, 0x7073, 0x0001, 0x26a0, 0x2898, 0x20a9, 0x0008,
-       0x53a6, 0x20a3, 0x0000, 0x20a3, 0x0000, 0xa085, 0x0001, 0x0078,
-       0x40e7, 0xa006, 0x0078, 0x40e7, 0xa006, 0x1078, 0x1328, 0x097f,
-       0x087f, 0x007c, 0x2118, 0x2021, 0x0000, 0x2001, 0x0007, 0xa39a,
-       0x0010, 0x0048, 0x40f7, 0x8420, 0x8001, 0x0078, 0x40ef, 0x2118,
-       0x84ff, 0x0040, 0x4100, 0xa39a, 0x0010, 0x8421, 0x00c0, 0x40fb,
-       0x2021, 0x0001, 0x83ff, 0x0040, 0x4109, 0x8423, 0x8319, 0x00c0,
-       0x4105, 0xa238, 0x2704, 0xa42c, 0x00c0, 0x4121, 0xa405, 0x203a,
-       0x714e, 0xa1a0, 0x293f, 0x242c, 0xa5ac, 0x00ff, 0x6532, 0x60e7,
-       0x0000, 0x65ea, 0x706b, 0x0000, 0x756e, 0x7073, 0x0001, 0xa084,
-       0x0000, 0x007c, 0x0e7e, 0x2071, 0xa300, 0x7077, 0x0000, 0x0e7f,
-       0x007c, 0x0e7e, 0x0f7e, 0x2001, 0x0002, 0x1078, 0x5975, 0x2079,
-       0x0100, 0x2071, 0x0140, 0x1078, 0x6c41, 0x7004, 0xa084, 0x4000,
-       0x0040, 0x413e, 0x7003, 0x1000, 0x7003, 0x0000, 0x127e, 0x2091,
-       0x8000, 0x2071, 0xa321, 0x2073, 0x0000, 0x7840, 0x027e, 0x017e,
-       0x2009, 0x00f7, 0x1078, 0x41de, 0x017f, 0xa094, 0x0010, 0xa285,
-       0x0080, 0x7842, 0x7a42, 0x027f, 0x127f, 0x0f7f, 0x0e7f, 0x007c,
-       0x127e, 0x2091, 0x8000, 0x2011, 0xa5b5, 0x2013, 0x0000, 0x707f,
-       0x0000, 0x127f, 0x20e1, 0x9080, 0x60a3, 0x0056, 0x60a7, 0x9575,
-       0x1078, 0x6c38, 0x2009, 0x07d0, 0x2011, 0x4129, 0x1078, 0x596c,
-       0x007c, 0x017e, 0x027e, 0x0c7e, 0x127e, 0x2091, 0x8000, 0x2009,
-       0x00f7, 0x1078, 0x41de, 0x2061, 0xa5be, 0x601b, 0x0000, 0x601f,
-       0x0000, 0x2061, 0xa300, 0x6003, 0x0001, 0x2061, 0x0100, 0x6043,
-       0x0090, 0x6043, 0x0010, 0x2009, 0x002d, 0x2011, 0x4196, 0x1078,
-       0x58c7, 0x127f, 0x0c7f, 0x027f, 0x017f, 0x007c, 0x0e7e, 0x007e,
-       0x127e, 0x2091, 0x8000, 0x2001, 0x0001, 0x1078, 0x5975, 0x2071,
-       0x0100, 0x1078, 0x6c41, 0x2071, 0x0140, 0x7004, 0xa084, 0x4000,
-       0x0040, 0x41ae, 0x7003, 0x1000, 0x7003, 0x0000, 0x2001, 0x0001,
-       0x1078, 0x2480, 0x1078, 0x4171, 0x127f, 0x007f, 0x0e7f, 0x007c,
-       0x20a9, 0x0040, 0x20a1, 0xa9c0, 0x2099, 0xa88e, 0x3304, 0x8007,
-       0x20a2, 0x9398, 0x94a0, 0x00f0, 0x41be, 0x007c, 0x20e1, 0x9080,
-       0x20e1, 0x4000, 0x2099, 0xa800, 0x20a1, 0x020b, 0x20a9, 0x000c,
-       0x53a6, 0x007c, 0x20e1, 0x9080, 0x20e1, 0x4000, 0x2099, 0xa880,
-       0x20a1, 0x020b, 0x20a9, 0x000c, 0x53a6, 0x007c, 0x0c7e, 0x007e,
-       0x2061, 0x0100, 0x810f, 0x2001, 0xa32e, 0x2004, 0xa005, 0x00c0,
-       0x41ef, 0x6030, 0xa084, 0x00ff, 0xa105, 0x0078, 0x41f1, 0xa185,
-       0x00f7, 0x604a, 0x007f, 0x0c7f, 0x007c, 0x017e, 0x047e, 0x2001,
-       0xa352, 0x2004, 0xd0a4, 0x0040, 0x4208, 0xa006, 0x2020, 0x2009,
-       0x002a, 0x1078, 0x9ec0, 0x2001, 0xa30c, 0x200c, 0xc195, 0x2102,
-       0x2019, 0x002a, 0x2009, 0x0000, 0x1078, 0x27e2, 0x047f, 0x017f,
-       0x007c, 0x007e, 0x2001, 0xa30c, 0x2004, 0xd09c, 0x0040, 0x4218,
-       0x007f, 0x007c, 0x007e, 0x017e, 0x127e, 0x2091, 0x8000, 0x2001,
-       0x0101, 0x200c, 0xa18d, 0x0006, 0x2102, 0x127f, 0x017f, 0x007f,
-       0x007c, 0x157e, 0x20a9, 0x00ff, 0x2009, 0xa434, 0xa006, 0x200a,
-       0x8108, 0x00f0, 0x422f, 0x157f, 0x007c, 0x0d7e, 0x037e, 0x157e,
-       0x137e, 0x147e, 0x2069, 0xa351, 0xa006, 0x6002, 0x6007, 0x0707,
-       0x600a, 0x600e, 0x6012, 0xa198, 0x293f, 0x231c, 0xa39c, 0x00ff,
-       0x6316, 0x20a9, 0x0004, 0xac98, 0x0006, 0x23a0, 0x40a4, 0x20a9,
-       0x0004, 0xac98, 0x000a, 0x23a0, 0x40a4, 0x603e, 0x6042, 0x604e,
-       0x6052, 0x6056, 0x605a, 0x605e, 0x6062, 0x6066, 0x606a, 0x606e,
-       0x6072, 0x6076, 0x607a, 0x607e, 0x6082, 0x6086, 0x608a, 0x608e,
-       0x6092, 0x6096, 0x609a, 0x609e, 0x60ae, 0x61a2, 0x0d7e, 0x60a4,
-       0xa06d, 0x0040, 0x4275, 0x1078, 0x139a, 0x60a7, 0x0000, 0x60a8,
-       0xa06d, 0x0040, 0x427d, 0x1078, 0x139a, 0x60ab, 0x0000, 0x0d7f,
-       0xa006, 0x604a, 0x6810, 0x603a, 0x680c, 0x6046, 0x6814, 0xa084,
-       0x00ff, 0x6042, 0x147f, 0x137f, 0x157f, 0x037f, 0x0d7f, 0x007c,
-       0x127e, 0x2091, 0x8000, 0x6944, 0x6e48, 0xa684, 0x3fff, 0xa082,
-       0x4000, 0x00c8, 0x4361, 0xa18c, 0xff00, 0x810f, 0xa182, 0x00ff,
-       0x00c8, 0x4367, 0x2001, 0xa30c, 0x2004, 0xa084, 0x0003, 0x0040,
-       0x42c2, 0x2001, 0xa30c, 0x2004, 0xd084, 0x00c0, 0x4342, 0xa188,
-       0xa434, 0x2104, 0xa065, 0x0040, 0x4342, 0x6004, 0xa084, 0x00ff,
-       0xa08e, 0x0006, 0x00c0, 0x4342, 0x6000, 0xd0c4, 0x0040, 0x4342,
-       0x0078, 0x42cf, 0xa188, 0xa434, 0x2104, 0xa065, 0x0040, 0x4326,
-       0x6004, 0xa084, 0x00ff, 0xa08e, 0x0006, 0x00c0, 0x432c, 0x60a4,
-       0xa00d, 0x0040, 0x42d7, 0x1078, 0x4749, 0x0040, 0x4320, 0x60a8,
-       0xa00d, 0x0040, 0x42f1, 0x1078, 0x479a, 0x00c0, 0x42f1, 0x694c,
-       0xd1fc, 0x00c0, 0x42e7, 0x1078, 0x441c, 0x0078, 0x431b, 0x1078,
-       0x43d6, 0x694c, 0xd1ec, 0x00c0, 0x431b, 0x1078, 0x460a, 0x0078,
-       0x431b, 0x694c, 0xa184, 0xa000, 0x0040, 0x430b, 0xd1ec, 0x0040,
-       0x4304, 0xd1fc, 0x0040, 0x4300, 0x1078, 0x461b, 0x0078, 0x4307,
-       0x1078, 0x461b, 0x0078, 0x430b, 0xd1fc, 0x0040, 0x430b, 0x1078,
-       0x43d6, 0x0078, 0x431b, 0x6050, 0xa00d, 0x0040, 0x4316, 0x2d00,
-       0x200a, 0x6803, 0x0000, 0x6052, 0x0078, 0x431b, 0x2d00, 0x6052,
-       0x604e, 0x6803, 0x0000, 0x1078, 0x5c17, 0xa006, 0x127f, 0x007c,
-       0x2001, 0x0005, 0x2009, 0x0000, 0x0078, 0x436b, 0x2001, 0x0028,
-       0x2009, 0x0000, 0x0078, 0x436b, 0xa082, 0x0006, 0x00c8, 0x4342,
-       0x60a0, 0xd0bc, 0x00c0, 0x433e, 0x6100, 0xd1fc, 0x0040, 0x42cf,
-       0x2001, 0x0029, 0x2009, 0x1000, 0x0078, 0x436b, 0x2001, 0x0028,
-       0x0078, 0x435d, 0x2009, 0xa30c, 0x210c, 0xd18c, 0x0040, 0x434c,
-       0x2001, 0x0004, 0x0078, 0x435d, 0xd184, 0x0040, 0x4353, 0x2001,
-       0x0004, 0x0078, 0x435d, 0x2001, 0x0029, 0x6100, 0xd1fc, 0x0040,
-       0x435d, 0x2009, 0x1000, 0x0078, 0x436b, 0x2009, 0x0000, 0x0078,
-       0x436b, 0x2001, 0x0029, 0x2009, 0x0000, 0x0078, 0x436b, 0x2001,
-       0x0029, 0x2009, 0x0000, 0xa005, 0x127f, 0x007c, 0x6944, 0x6e48,
-       0xa684, 0x3fff, 0xa082, 0x4000, 0x00c8, 0x43bb, 0xa18c, 0xff00,
-       0x810f, 0xa182, 0x00ff, 0x00c8, 0x43a1, 0xa188, 0xa434, 0x2104,
-       0xa065, 0x0040, 0x43a1, 0x6004, 0xa084, 0x00ff, 0xa08e, 0x0006,
-       0x00c0, 0x43a7, 0x684c, 0xd0ec, 0x0040, 0x4394, 0x1078, 0x461b,
-       0x1078, 0x43d6, 0x0078, 0x439c, 0x1078, 0x43d6, 0x684c, 0xd0fc,
-       0x0040, 0x439c, 0x1078, 0x460a, 0x1078, 0x4663, 0xa006, 0x0078,
-       0x43bf, 0x2001, 0x0028, 0x2009, 0x0000, 0x0078, 0x43bf, 0xa082,
-       0x0006, 0x00c8, 0x43b5, 0x6100, 0xd1fc, 0x0040, 0x438a, 0x2001,
-       0x0029, 0x2009, 0x1000, 0x0078, 0x43bf, 0x2001, 0x0029, 0x2009,
-       0x0000, 0x0078, 0x43bf, 0x2001, 0x0029, 0x2009, 0x0000, 0xa005,
-       0x007c, 0x127e, 0x2091, 0x8000, 0x6050, 0xa00d, 0x0040, 0x43cf,
-       0x2d00, 0x200a, 0x6803, 0x0000, 0x6052, 0x127f, 0x007c, 0x2d00,
-       0x6052, 0x604e, 0x6803, 0x0000, 0x0078, 0x43cd, 0x127e, 0x2091,
-       0x8000, 0x604c, 0xa005, 0x0040, 0x43ec, 0x0e7e, 0x2071, 0xa5ab,
-       0x7004, 0xa086, 0x0002, 0x0040, 0x43f3, 0x0e7f, 0x604c, 0x6802,
-       0x2d00, 0x604e, 0x127f, 0x007c, 0x2d00, 0x6052, 0x604e, 0x6803,
-       0x0000, 0x0078, 0x43ea, 0x701c, 0xac06, 0x00c0, 0x43e5, 0x604c,
-       0x2070, 0x7000, 0x6802, 0x2d00, 0x7002, 0x0e7f, 0x127f, 0x007c,
-       0x127e, 0x2091, 0x8000, 0x604c, 0xa06d, 0x0040, 0x440e, 0x6800,
-       0xa005, 0x00c0, 0x440c, 0x6052, 0x604e, 0xad05, 0x127f, 0x007c,
-       0x604c, 0xa06d, 0x0040, 0x441b, 0x6800, 0xa005, 0x00c0, 0x4419,
-       0x6052, 0x604e, 0xad05, 0x007c, 0x6803, 0x0000, 0x6084, 0xa00d,
-       0x0040, 0x4426, 0x2d00, 0x200a, 0x6086, 0x007c, 0x2d00, 0x6086,
-       0x6082, 0x0078, 0x4425, 0x127e, 0x0c7e, 0x027e, 0x2091, 0x8000,
-       0x6218, 0x2260, 0x6200, 0xa005, 0x0040, 0x4439, 0xc285, 0x0078,
-       0x443a, 0xc284, 0x6202, 0x027f, 0x0c7f, 0x127f, 0x007c, 0x127e,
-       0x0c7e, 0x2091, 0x8000, 0x6218, 0x2260, 0x6204, 0x007e, 0xa086,
-       0x0006, 0x00c0, 0x445e, 0x609c, 0xd0ac, 0x0040, 0x445e, 0x2001,
-       0xa352, 0x2004, 0xd0a4, 0x0040, 0x445e, 0xa284, 0xff00, 0x8007,
-       0xa086, 0x0007, 0x00c0, 0x445e, 0x2011, 0x0600, 0x007f, 0xa294,
-       0xff00, 0xa215, 0x6206, 0x007e, 0xa086, 0x0006, 0x00c0, 0x446e,
-       0x6290, 0x82ff, 0x00c0, 0x446e, 0x1078, 0x1328, 0x007f, 0x0c7f,
-       0x127f, 0x007c, 0x127e, 0x0c7e, 0x2091, 0x8000, 0x6218, 0x2260,
-       0x6204, 0x007e, 0xa086, 0x0006, 0x00c0, 0x4490, 0x609c, 0xd0a4,
-       0x0040, 0x4490, 0x2001, 0xa352, 0x2004, 0xd0ac, 0x00c0, 0x4490,
-       0xa284, 0x00ff, 0xa086, 0x0007, 0x00c0, 0x4490, 0x2011, 0x0006,
-       0x007f, 0xa294, 0x00ff, 0x8007, 0xa215, 0x6206, 0x0c7f, 0x127f,
-       0x007c, 0x027e, 0xa182, 0x00ff, 0x0048, 0x44a2, 0xa085, 0x0001,
-       0x0078, 0x44ba, 0xa190, 0xa434, 0x2204, 0xa065, 0x00c0, 0x44b9,
-       0x017e, 0x0d7e, 0x1078, 0x1366, 0x2d60, 0x0d7f, 0x017f, 0x0040,
-       0x449e, 0x2c00, 0x2012, 0x60a7, 0x0000, 0x60ab, 0x0000, 0x1078,
-       0x4235, 0xa006, 0x027f, 0x007c, 0x127e, 0x2091, 0x8000, 0x027e,
-       0xa182, 0x00ff, 0x0048, 0x44c8, 0xa085, 0x0001, 0x0078, 0x44fe,
-       0x0d7e, 0xa190, 0xa434, 0x2204, 0xa06d, 0x0040, 0x44fc, 0x2013,
-       0x0000, 0x0d7e, 0x0c7e, 0x2d60, 0x60a4, 0xa06d, 0x0040, 0x44da,
-       0x1078, 0x139a, 0x60a8, 0xa06d, 0x0040, 0x44e0, 0x1078, 0x139a,
-       0x0c7f, 0x0d7f, 0x0d7e, 0x0c7e, 0x68ac, 0x2060, 0x8cff, 0x0040,
-       0x44f8, 0x600c, 0x007e, 0x6010, 0x2068, 0x1078, 0x8a44, 0x0040,
-       0x44f3, 0x1078, 0x13aa, 0x1078, 0x753d, 0x0c7f, 0x0078, 0x44e6,
-       0x0c7f, 0x0d7f, 0x1078, 0x139a, 0x0d7f, 0xa006, 0x027f, 0x127f,
-       0x007c, 0x017e, 0xa182, 0x00ff, 0x0048, 0x450a, 0xa085, 0x0001,
-       0x0078, 0x4511, 0xa188, 0xa434, 0x2104, 0xa065, 0x0040, 0x4506,
-       0xa006, 0x017f, 0x007c, 0x0d7e, 0x157e, 0x137e, 0x147e, 0x600b,
-       0x0000, 0x600f, 0x0000, 0x6000, 0xc08c, 0x6002, 0x2069, 0xa88e,
-       0x6808, 0x605e, 0x6810, 0x6062, 0x6138, 0xa10a, 0x0048, 0x4529,
-       0x603a, 0x6814, 0x6066, 0x2099, 0xa896, 0xac88, 0x000a, 0x21a0,
-       0x20a9, 0x0004, 0x53a3, 0x2099, 0xa89a, 0xac88, 0x0006, 0x21a0,
-       0x20a9, 0x0004, 0x53a3, 0x2069, 0xa8ae, 0x6808, 0x606a, 0x690c,
-       0x616e, 0x6810, 0x6072, 0x6818, 0x6076, 0xa182, 0x0211, 0x00c8,
-       0x454d, 0x2009, 0x0008, 0x0078, 0x4577, 0xa182, 0x0259, 0x00c8,
-       0x4555, 0x2009, 0x0007, 0x0078, 0x4577, 0xa182, 0x02c1, 0x00c8,
-       0x455d, 0x2009, 0x0006, 0x0078, 0x4577, 0xa182, 0x0349, 0x00c8,
-       0x4565, 0x2009, 0x0005, 0x0078, 0x4577, 0xa182, 0x0421, 0x00c8,
-       0x456d, 0x2009, 0x0004, 0x0078, 0x4577, 0xa182, 0x0581, 0x00c8,
-       0x4575, 0x2009, 0x0003, 0x0078, 0x4577, 0x2009, 0x0002, 0x6192,
-       0x147f, 0x137f, 0x157f, 0x0d7f, 0x007c, 0x017e, 0x027e, 0x0e7e,
-       0x2071, 0xa88d, 0x2e04, 0x6896, 0x2071, 0xa88e, 0x7004, 0x689a,
-       0x701c, 0x689e, 0x6a00, 0x2009, 0xa371, 0x210c, 0xd0bc, 0x0040,
-       0x4597, 0xd1ec, 0x0040, 0x4597, 0xc2ad, 0x0078, 0x4598, 0xc2ac,
-       0xd0c4, 0x0040, 0x45a1, 0xd1e4, 0x0040, 0x45a1, 0xc2bd, 0x0078,
-       0x45a2, 0xc2bc, 0x6a02, 0x0e7f, 0x027f, 0x017f, 0x007c, 0x0d7e,
-       0x127e, 0x2091, 0x8000, 0x60a4, 0xa06d, 0x0040, 0x45cb, 0x6900,
-       0x81ff, 0x00c0, 0x45df, 0x6a04, 0xa282, 0x0010, 0x00c8, 0x45e4,
-       0xad88, 0x0004, 0x20a9, 0x0010, 0x2104, 0xa086, 0xffff, 0x0040,
-       0x45c6, 0x8108, 0x00f0, 0x45bc, 0x1078, 0x1328, 0x260a, 0x8210,
-       0x6a06, 0x0078, 0x45df, 0x1078, 0x1381, 0x0040, 0x45e4, 0x2d00,
-       0x60a6, 0x6803, 0x0000, 0xad88, 0x0004, 0x20a9, 0x0010, 0x200b,
-       0xffff, 0x8108, 0x00f0, 0x45d7, 0x6807, 0x0001, 0x6e12, 0xa085,
-       0x0001, 0x127f, 0x0d7f, 0x007c, 0xa006, 0x0078, 0x45e1, 0x127e,
-       0x2091, 0x8000, 0x0d7e, 0x60a4, 0xa00d, 0x0040, 0x4607, 0x2168,
-       0x6800, 0xa005, 0x00c0, 0x4603, 0x1078, 0x4749, 0x00c0, 0x4607,
-       0x200b, 0xffff, 0x6804, 0xa08a, 0x0002, 0x0048, 0x4603, 0x8001,
-       0x6806, 0x0078, 0x4607, 0x1078, 0x139a, 0x60a7, 0x0000, 0x0d7f,
-       0x127f, 0x007c, 0x127e, 0x2091, 0x8000, 0x1078, 0x47af, 0x0078,
-       0x4613, 0x1078, 0x43c1, 0x1078, 0x46a7, 0x00c0, 0x4611, 0x1078,
-       0x4663, 0x127f, 0x007c, 0x0d7e, 0x127e, 0x2091, 0x8000, 0x60a8,
-       0xa06d, 0x0040, 0x463f, 0x6950, 0x81ff, 0x00c0, 0x4653, 0x6a54,
-       0xa282, 0x0010, 0x00c8, 0x4660, 0xad88, 0x0018, 0x20a9, 0x0010,
-       0x2104, 0xa086, 0xffff, 0x0040, 0x463a, 0x8108, 0x00f0, 0x4630,
-       0x1078, 0x1328, 0x260a, 0x8210, 0x6a56, 0x0078, 0x4653, 0x1078,
-       0x1381, 0x0040, 0x4660, 0x2d00, 0x60aa, 0x6853, 0x0000, 0xad88,
-       0x0018, 0x20a9, 0x0010, 0x200b, 0xffff, 0x8108, 0x00f0, 0x464b,
-       0x6857, 0x0001, 0x6e62, 0x0078, 0x4657, 0x1078, 0x441c, 0x1078,
-       0x466d, 0x00c0, 0x4655, 0xa085, 0x0001, 0x127f, 0x0d7f, 0x007c,
-       0xa006, 0x0078, 0x465d, 0x127e, 0x2091, 0x8000, 0x1078, 0x5c17,
-       0x127f, 0x007c, 0xa01e, 0x0078, 0x466f, 0x2019, 0x0001, 0xa00e,
-       0x127e, 0x2091, 0x8000, 0x604c, 0x2068, 0x6000, 0xd0dc, 0x00c0,
-       0x468d, 0x8dff, 0x0040, 0x46a2, 0x83ff, 0x0040, 0x4685, 0x6848,
-       0xa606, 0x0040, 0x4692, 0x0078, 0x468d, 0x683c, 0xa406, 0x00c0,
-       0x468d, 0x6840, 0xa506, 0x0040, 0x4692, 0x2d08, 0x6800, 0x2068,
-       0x0078, 0x4679, 0x6a00, 0x604c, 0xad06, 0x00c0, 0x469a, 0x624e,
-       0x0078, 0x469d, 0xa180, 0x0000, 0x2202, 0x82ff, 0x00c0, 0x46a2,
-       0x6152, 0x8dff, 0x127f, 0x007c, 0xa01e, 0x0078, 0x46a9, 0x2019,
-       0x0001, 0xa00e, 0x6080, 0x2068, 0x8dff, 0x0040, 0x46d5, 0x83ff,
-       0x0040, 0x46b8, 0x6848, 0xa606, 0x0040, 0x46c5, 0x0078, 0x46c0,
-       0x683c, 0xa406, 0x00c0, 0x46c0, 0x6840, 0xa506, 0x0040, 0x46c5,
-       0x2d08, 0x6800, 0x2068, 0x0078, 0x46ac, 0x6a00, 0x6080, 0xad06,
-       0x00c0, 0x46cd, 0x6282, 0x0078, 0x46d0, 0xa180, 0x0000, 0x2202,
-       0x82ff, 0x00c0, 0x46d5, 0x6186, 0x8dff, 0x007c, 0xa016, 0x1078,
-       0x4742, 0x00c0, 0x46dd, 0x2011, 0x0001, 0x1078, 0x4793, 0x00c0,
-       0x46e3, 0xa295, 0x0002, 0x007c, 0x1078, 0x47cb, 0x0040, 0x46ec,
-       0x1078, 0x8b12, 0x0078, 0x46ee, 0xa085, 0x0001, 0x007c, 0x1078,
-       0x47cb, 0x0040, 0x46f7, 0x1078, 0x8aaa, 0x0078, 0x46f9, 0xa085,
-       0x0001, 0x007c, 0x1078, 0x47cb, 0x0040, 0x4702, 0x1078, 0x8af4,
-       0x0078, 0x4704, 0xa085, 0x0001, 0x007c, 0x1078, 0x47cb, 0x0040,
-       0x470d, 0x1078, 0x8ac6, 0x0078, 0x470f, 0xa085, 0x0001, 0x007c,
-       0x1078, 0x47cb, 0x0040, 0x4718, 0x1078, 0x8b30, 0x0078, 0x471a,
-       0xa085, 0x0001, 0x007c, 0x127e, 0x007e, 0x0d7e, 0x2091, 0x8000,
-       0x6080, 0xa06d, 0x0040, 0x473a, 0x6800, 0x007e, 0x6837, 0x0103,
-       0x6b4a, 0x6847, 0x0000, 0x1078, 0x8cb8, 0x007e, 0x6000, 0xd0fc,
-       0x0040, 0x4734, 0x1078, 0xa18c, 0x007f, 0x1078, 0x4982, 0x007f,
-       0x0078, 0x4721, 0x6083, 0x0000, 0x6087, 0x0000, 0x0d7f, 0x007f,
-       0x127f, 0x007c, 0x60a4, 0xa00d, 0x00c0, 0x4749, 0xa085, 0x0001,
-       0x007c, 0x0e7e, 0x2170, 0x7000, 0xa005, 0x00c0, 0x475c, 0x20a9,
-       0x0010, 0xae88, 0x0004, 0x2104, 0xa606, 0x0040, 0x475c, 0x8108,
-       0x00f0, 0x4753, 0xa085, 0x0001, 0xa006, 0x0e7f, 0x007c, 0x0d7e,
-       0x127e, 0x2091, 0x8000, 0x60a4, 0xa06d, 0x00c0, 0x476d, 0x1078,
-       0x1381, 0x0040, 0x477f, 0x2d00, 0x60a6, 0x6803, 0x0001, 0x6807,
-       0x0000, 0xad88, 0x0004, 0x20a9, 0x0010, 0x200b, 0xffff, 0x8108,
-       0x00f0, 0x4775, 0xa085, 0x0001, 0x127f, 0x0d7f, 0x007c, 0xa006,
-       0x0078, 0x477c, 0x0d7e, 0x127e, 0x2091, 0x8000, 0x60a4, 0xa06d,
-       0x0040, 0x4790, 0x60a7, 0x0000, 0x1078, 0x139a, 0xa085, 0x0001,
-       0x127f, 0x0d7f, 0x007c, 0x60a8, 0xa00d, 0x00c0, 0x479a, 0xa085,
-       0x0001, 0x007c, 0x0e7e, 0x2170, 0x7050, 0xa005, 0x00c0, 0x47ad,
-       0x20a9, 0x0010, 0xae88, 0x0018, 0x2104, 0xa606, 0x0040, 0x47ad,
-       0x8108, 0x00f0, 0x47a4, 0xa085, 0x0001, 0x0e7f, 0x007c, 0x127e,
-       0x2091, 0x8000, 0x1078, 0x4793, 0x00c0, 0x47c9, 0x200b, 0xffff,
-       0x0d7e, 0x60a8, 0x2068, 0x6854, 0xa08a, 0x0002, 0x0048, 0x47c4,
-       0x8001, 0x6856, 0x0078, 0x47c8, 0x1078, 0x139a, 0x60ab, 0x0000,
-       0x0d7f, 0x127f, 0x007c, 0x609c, 0xd0a4, 0x007c, 0x0f7e, 0x71ac,
-       0x81ff, 0x00c0, 0x47e9, 0x71c8, 0xd19c, 0x0040, 0x47e9, 0x2001,
-       0x007e, 0xa080, 0xa434, 0x2004, 0xa07d, 0x0040, 0x47e9, 0x7804,
-       0xa084, 0x00ff, 0xa086, 0x0006, 0x00c0, 0x47e9, 0x7800, 0xc0ed,
-       0x7802, 0x2079, 0xa351, 0x7804, 0xd0a4, 0x0040, 0x480f, 0x157e,
-       0x0c7e, 0x20a9, 0x007f, 0x2009, 0x0000, 0x017e, 0x1078, 0x4501,
-       0x00c0, 0x4809, 0x6004, 0xa084, 0xff00, 0x8007, 0xa096, 0x0004,
-       0x0040, 0x4806, 0xa086, 0x0006, 0x00c0, 0x4809, 0x6000, 0xc0ed,
-       0x6002, 0x017f, 0x8108, 0x00f0, 0x47f5, 0x0c7f, 0x157f, 0x1078,
-       0x4897, 0x0040, 0x4818, 0x2001, 0xa59f, 0x200c, 0x0078, 0x4820,
-       0x2079, 0xa351, 0x7804, 0xd0a4, 0x0040, 0x4824, 0x2009, 0x07d0,
-       0x2011, 0x4826, 0x1078, 0x596c, 0x0f7f, 0x007c, 0x2011, 0x4826,
-       0x1078, 0x58d4, 0x1078, 0x4897, 0x0040, 0x484e, 0x2001, 0xa4b2,
-       0x2004, 0xa080, 0x0000, 0x200c, 0xc1ec, 0x2102, 0x2001, 0xa352,
-       0x2004, 0xd0a4, 0x0040, 0x4842, 0x2009, 0x07d0, 0x2011, 0x4826,
-       0x1078, 0x596c, 0x0e7e, 0x2071, 0xa300, 0x706b, 0x0000, 0x706f,
-       0x0000, 0x1078, 0x260d, 0x0e7f, 0x0078, 0x4886, 0x157e, 0x0c7e,
-       0x20a9, 0x007f, 0x2009, 0x0000, 0x017e, 0x1078, 0x4501, 0x00c0,
-       0x4880, 0x6000, 0xd0ec, 0x0040, 0x4880, 0x047e, 0x62a0, 0xa294,
-       0x00ff, 0x8227, 0xa006, 0x2009, 0x0029, 0x1078, 0x9ec0, 0x6000,
-       0xc0e5, 0xc0ec, 0x6002, 0x6004, 0xa084, 0x00ff, 0xa085, 0x0700,
-       0x6006, 0x2019, 0x0029, 0x1078, 0x5d53, 0x077e, 0x2039, 0x0000,
-       0x1078, 0x5c78, 0x2009, 0x0000, 0x1078, 0x9c38, 0x077f, 0x047f,
-       0x017f, 0x8108, 0x00f0, 0x4854, 0x0c7f, 0x157f, 0x007c, 0x0c7e,
-       0x6018, 0x2060, 0x6000, 0xc0ec, 0x6002, 0x0c7f, 0x007c, 0x7818,
-       0x2004, 0xd0ac, 0x007c, 0x7818, 0x2004, 0xd0bc, 0x007c, 0x0f7e,
-       0x2001, 0xa4b2, 0x2004, 0xa07d, 0x0040, 0x48a0, 0x7800, 0xd0ec,
-       0x0f7f, 0x007c, 0x127e, 0x027e, 0x2091, 0x8000, 0x6200, 0xa005,
-       0x0040, 0x48ad, 0xc2fd, 0x0078, 0x48ae, 0xc2fc, 0x6202, 0x027f,
-       0x127f, 0x007c, 0x2071, 0xa413, 0x7003, 0x0001, 0x7007, 0x0000,
-       0x7013, 0x0000, 0x7017, 0x0000, 0x701b, 0x0000, 0x701f, 0x0000,
-       0x700b, 0x0000, 0x704b, 0x0001, 0x704f, 0x0000, 0x705b, 0x0020,
-       0x705f, 0x0040, 0x707f, 0x0000, 0x2071, 0xa57c, 0x7003, 0xa413,
-       0x7007, 0x0000, 0x700b, 0x0000, 0x700f, 0xa55c, 0x7013, 0x0020,
-       0x7017, 0x0040, 0x7037, 0x0000, 0x007c, 0x017e, 0x0e7e, 0x2071,
-       0xa534, 0xa00e, 0x7186, 0x718a, 0x7097, 0x0001, 0x2001, 0xa352,
-       0x2004, 0xd0fc, 0x00c0, 0x48f7, 0x2001, 0xa352, 0x2004, 0xa00e,
-       0xd09c, 0x0040, 0x48f4, 0x8108, 0x7102, 0x0078, 0x494a, 0x2001,
-       0xa371, 0x200c, 0xa184, 0x000f, 0x2009, 0xa372, 0x210c, 0x0079,
-       0x4901, 0x48ec, 0x4922, 0x492a, 0x4935, 0x493b, 0x48ec, 0x48ec,
-       0x48ec, 0x4911, 0x48ec, 0x48ec, 0x48ec, 0x48ec, 0x48ec, 0x48ec,
-       0x48ec, 0x7003, 0x0004, 0x137e, 0x147e, 0x157e, 0x2099, 0xa375,
-       0x20a1, 0xa585, 0x20a9, 0x0004, 0x53a3, 0x157f, 0x147f, 0x137f,
-       0x0078, 0x494a, 0x708f, 0x0005, 0x7007, 0x0122, 0x2001, 0x0002,
-       0x0078, 0x4930, 0x708f, 0x0002, 0x7007, 0x0121, 0x2001, 0x0003,
-       0x7002, 0x7097, 0x0001, 0x0078, 0x4947, 0x7007, 0x0122, 0x2001,
-       0x0002, 0x0078, 0x493f, 0x7007, 0x0121, 0x2001, 0x0003, 0x7002,
-       0xa006, 0x7096, 0x708e, 0xa184, 0xff00, 0x8007, 0x709a, 0xa184,
-       0x00ff, 0x7092, 0x0e7f, 0x017f, 0x007c, 0x0e7e, 0x2071, 0xa413,
-       0x684c, 0xa005, 0x00c0, 0x495b, 0x7028, 0xc085, 0x702a, 0xa085,
-       0x0001, 0x0078, 0x4980, 0x6a60, 0x7236, 0x6b64, 0x733a, 0x6868,
-       0x703e, 0x7076, 0x686c, 0x7042, 0x707a, 0x684c, 0x702e, 0x6844,
-       0x7032, 0x2009, 0x000d, 0x200a, 0x700b, 0x0000, 0x8007, 0x8006,
-       0x8006, 0xa08c, 0x003f, 0xa084, 0xffc0, 0xa210, 0x2100, 0xa319,
-       0x726e, 0x7372, 0x7028, 0xc084, 0x702a, 0x7007, 0x0001, 0xa006,
-       0x0e7f, 0x007c, 0x0e7e, 0x027e, 0x6838, 0xd0fc, 0x00c0, 0x49d8,
-       0x6804, 0xa00d, 0x0040, 0x499e, 0x0d7e, 0x2071, 0xa300, 0xa016,
-       0x702c, 0x2168, 0x6904, 0x206a, 0x8210, 0x2d00, 0x81ff, 0x00c0,
-       0x4991, 0x702e, 0x70a8, 0xa200, 0x70aa, 0x0d7f, 0x2071, 0xa413,
-       0x701c, 0xa005, 0x00c0, 0x49ea, 0x0068, 0x49e8, 0x2071, 0xa534,
-       0x7200, 0x82ff, 0x0040, 0x49e8, 0x6934, 0xa186, 0x0103, 0x00c0,
-       0x49fb, 0x6948, 0x6844, 0xa105, 0x00c0, 0x49db, 0x2009, 0x8020,
-       0x2200, 0x0079, 0x49bb, 0x49e8, 0x49c0, 0x4a18, 0x4a26, 0x49e8,
-       0x2071, 0x0000, 0x7018, 0xd084, 0x00c0, 0x49e8, 0x7122, 0x683c,
-       0x7026, 0x6840, 0x702a, 0x701b, 0x0001, 0x2091, 0x4080, 0x2071,
-       0xa300, 0x702c, 0x206a, 0x2d00, 0x702e, 0x70a8, 0x8000, 0x70aa,
-       0x027f, 0x0e7f, 0x007c, 0x6844, 0xa086, 0x0100, 0x00c0, 0x49e8,
-       0x6868, 0xa005, 0x00c0, 0x49e8, 0x2009, 0x8020, 0x0078, 0x49b8,
-       0x2071, 0xa413, 0x2d08, 0x206b, 0x0000, 0x7010, 0x8000, 0x7012,
-       0x7018, 0xa06d, 0x711a, 0x0040, 0x49f8, 0x6902, 0x0078, 0x49f9,
-       0x711e, 0x0078, 0x49d8, 0xa18c, 0x00ff, 0xa186, 0x0017, 0x0040,
-       0x4a09, 0xa186, 0x001e, 0x0040, 0x4a09, 0xa18e, 0x001f, 0x00c0,
-       0x49e8, 0x684c, 0xd0cc, 0x0040, 0x49e8, 0x6850, 0xa084, 0x00ff,
-       0xa086, 0x0001, 0x00c0, 0x49e8, 0x2009, 0x8021, 0x0078, 0x49b8,
-       0x7084, 0x8008, 0xa092, 0x001e, 0x00c8, 0x49e8, 0x7186, 0xae90,
-       0x0003, 0xa210, 0x683c, 0x2012, 0x0078, 0x4a36, 0x7084, 0x8008,
-       0xa092, 0x000f, 0x00c8, 0x49e8, 0x7186, 0xae90, 0x0003, 0x8003,
-       0xa210, 0x683c, 0x2012, 0x8210, 0x6840, 0x2012, 0x7088, 0xa10a,
-       0x0048, 0x49cf, 0x718c, 0x7084, 0xa10a, 0x0048, 0x49cf, 0x2071,
-       0x0000, 0x7018, 0xd084, 0x00c0, 0x49cf, 0x2071, 0xa534, 0x7000,
-       0xa086, 0x0002, 0x00c0, 0x4a56, 0x1078, 0x4cd2, 0x2071, 0x0000,
-       0x701b, 0x0001, 0x2091, 0x4080, 0x0078, 0x49cf, 0x1078, 0x4cfd,
-       0x2071, 0x0000, 0x701b, 0x0001, 0x2091, 0x4080, 0x0078, 0x49cf,
-       0x007e, 0x684c, 0x007e, 0x6837, 0x0103, 0x20a9, 0x001c, 0xad80,
-       0x0011, 0x20a0, 0x2001, 0x0000, 0x40a4, 0x007f, 0xa084, 0x00ff,
-       0x684e, 0x007f, 0x684a, 0x6952, 0x007c, 0x2071, 0xa413, 0x7004,
-       0x0079, 0x4a7a, 0x4a84, 0x4a95, 0x4ca3, 0x4ca4, 0x4ccb, 0x4cd1,
-       0x4a85, 0x4c91, 0x4c32, 0x4cb4, 0x007c, 0x127e, 0x2091, 0x8000,
-       0x0068, 0x4a94, 0x2009, 0x000d, 0x7030, 0x200a, 0x2091, 0x4080,
-       0x7007, 0x0001, 0x700b, 0x0000, 0x127f, 0x2069, 0xa5be, 0x6844,
-       0xa005, 0x0050, 0x4abd, 0x00c0, 0x4abd, 0x127e, 0x2091, 0x8000,
-       0x2069, 0x0000, 0x6934, 0x2001, 0xa41f, 0x2004, 0xa10a, 0x0040,
-       0x4ab8, 0x0068, 0x4abc, 0x2069, 0x0000, 0x6818, 0xd084, 0x00c0,
-       0x4abc, 0x2009, 0x8040, 0x6922, 0x681b, 0x0001, 0x2091, 0x4080,
-       0x2069, 0xa5be, 0x6847, 0xffff, 0x127f, 0x2069, 0xa300, 0x6844,
-       0x6960, 0xa102, 0x2069, 0xa534, 0x688a, 0x6984, 0x701c, 0xa06d,
-       0x0040, 0x4acf, 0x81ff, 0x0040, 0x4b17, 0x0078, 0x4ae5, 0x81ff,
-       0x0040, 0x4be9, 0x2071, 0xa534, 0x7184, 0x7088, 0xa10a, 0x00c8,
-       0x4ae5, 0x7190, 0x2071, 0xa5be, 0x7040, 0xa005, 0x0040, 0x4ae5,
-       0x00d0, 0x4be9, 0x7142, 0x0078, 0x4be9, 0x2071, 0xa534, 0x718c,
-       0x127e, 0x2091, 0x8000, 0x7084, 0xa10a, 0x0048, 0x4c06, 0x0068,
-       0x4b9b, 0x2071, 0x0000, 0x7018, 0xd084, 0x00c0, 0x4b9b, 0x2001,
-       0xffff, 0x2071, 0xa5be, 0x7042, 0x2071, 0xa534, 0x7000, 0xa086,
-       0x0002, 0x00c0, 0x4b0d, 0x1078, 0x4cd2, 0x2071, 0x0000, 0x701b,
-       0x0001, 0x2091, 0x4080, 0x0078, 0x4b9b, 0x1078, 0x4cfd, 0x2071,
-       0x0000, 0x701b, 0x0001, 0x2091, 0x4080, 0x0078, 0x4b9b, 0x2071,
-       0xa534, 0x7000, 0xa005, 0x0040, 0x4bc8, 0x6934, 0xa186, 0x0103,
-       0x00c0, 0x4b9e, 0x684c, 0xd0bc, 0x00c0, 0x4bc8, 0x6948, 0x6844,
-       0xa105, 0x00c0, 0x4bbb, 0x2009, 0x8020, 0x2071, 0xa534, 0x7000,
-       0x0079, 0x4b32, 0x4bc8, 0x4b80, 0x4b58, 0x4b6a, 0x4b37, 0x137e,
-       0x147e, 0x157e, 0x2099, 0xa375, 0x20a1, 0xa585, 0x20a9, 0x0004,
-       0x53a3, 0x157f, 0x147f, 0x137f, 0x2071, 0xa57c, 0xad80, 0x000f,
-       0x700e, 0x7013, 0x0002, 0x7007, 0x0002, 0x700b, 0x0000, 0x2e10,
-       0x1078, 0x13d1, 0x2071, 0xa413, 0x7007, 0x0009, 0x0078, 0x4be9,
-       0x7084, 0x8008, 0xa092, 0x001e, 0x00c8, 0x4be9, 0xae90, 0x0003,
-       0xa210, 0x683c, 0x2012, 0x7186, 0x2071, 0xa413, 0x1078, 0x4d5b,
-       0x0078, 0x4be9, 0x7084, 0x8008, 0xa092, 0x000f, 0x00c8, 0x4be9,
-       0xae90, 0x0003, 0x8003, 0xa210, 0x683c, 0x2012, 0x8210, 0x6840,
-       0x2012, 0x7186, 0x2071, 0xa413, 0x1078, 0x4d5b, 0x0078, 0x4be9,
-       0x127e, 0x2091, 0x8000, 0x0068, 0x4b9b, 0x2071, 0x0000, 0x7018,
-       0xd084, 0x00c0, 0x4b9b, 0x7122, 0x683c, 0x7026, 0x6840, 0x702a,
-       0x701b, 0x0001, 0x2091, 0x4080, 0x127f, 0x2071, 0xa413, 0x1078,
-       0x4d5b, 0x0078, 0x4be9, 0x127f, 0x0078, 0x4be9, 0xa18c, 0x00ff,
-       0xa186, 0x0017, 0x0040, 0x4bac, 0xa186, 0x001e, 0x0040, 0x4bac,
-       0xa18e, 0x001f, 0x00c0, 0x4bc8, 0x684c, 0xd0cc, 0x0040, 0x4bc8,
-       0x6850, 0xa084, 0x00ff, 0xa086, 0x0001, 0x00c0, 0x4bc8, 0x2009,
-       0x8021, 0x0078, 0x4b2d, 0x6844, 0xa086, 0x0100, 0x00c0, 0x4bc8,
-       0x6868, 0xa005, 0x00c0, 0x4bc8, 0x2009, 0x8020, 0x0078, 0x4b2d,
-       0x2071, 0xa413, 0x1078, 0x4d6f, 0x0040, 0x4be9, 0x2071, 0xa413,
-       0x700f, 0x0001, 0x6934, 0xa184, 0x00ff, 0xa086, 0x0003, 0x00c0,
-       0x4be0, 0x810f, 0xa18c, 0x00ff, 0x8101, 0x0040, 0x4be0, 0x710e,
-       0x7007, 0x0003, 0x1078, 0x4d8f, 0x7050, 0xa086, 0x0100, 0x0040,
-       0x4ca4, 0x127e, 0x2091, 0x8000, 0x2071, 0xa413, 0x7008, 0xa086,
-       0x0001, 0x00c0, 0x4c04, 0x0068, 0x4c04, 0x2009, 0x000d, 0x7030,
-       0x200a, 0x2091, 0x4080, 0x700b, 0x0000, 0x7004, 0xa086, 0x0006,
-       0x00c0, 0x4c04, 0x7007, 0x0001, 0x127f, 0x007c, 0x2071, 0xa413,
-       0x1078, 0x4d6f, 0x0040, 0x4c2f, 0x2071, 0xa534, 0x7084, 0x700a,
-       0x20a9, 0x0020, 0x2099, 0xa535, 0x20a1, 0xa55c, 0x53a3, 0x7087,
-       0x0000, 0x2071, 0xa413, 0x2069, 0xa57c, 0x706c, 0x6826, 0x7070,
-       0x682a, 0x7074, 0x682e, 0x7078, 0x6832, 0x2d10, 0x1078, 0x13d1,
-       0x7007, 0x0008, 0x2001, 0xffff, 0x2071, 0xa5be, 0x7042, 0x127f,
-       0x0078, 0x4be9, 0x2069, 0xa57c, 0x6808, 0xa08e, 0x0000, 0x0040,
-       0x4c90, 0xa08e, 0x0200, 0x0040, 0x4c8e, 0xa08e, 0x0100, 0x00c0,
-       0x4c90, 0x127e, 0x2091, 0x8000, 0x0068, 0x4c8b, 0x2069, 0x0000,
-       0x6818, 0xd084, 0x00c0, 0x4c8b, 0x702c, 0x7130, 0x8108, 0xa102,
-       0x0048, 0x4c59, 0xa00e, 0x7034, 0x706e, 0x7038, 0x7072, 0x0078,
-       0x4c63, 0x706c, 0xa080, 0x0040, 0x706e, 0x00c8, 0x4c63, 0x7070,
-       0xa081, 0x0000, 0x7072, 0x7132, 0x6936, 0x700b, 0x0000, 0x2001,
-       0xa559, 0x2004, 0xa005, 0x00c0, 0x4c82, 0x6934, 0x2069, 0xa534,
-       0x689c, 0x699e, 0x2069, 0xa5be, 0xa102, 0x00c0, 0x4c7b, 0x6844,
-       0xa005, 0x00d0, 0x4c89, 0x2001, 0xa55a, 0x200c, 0x810d, 0x6946,
-       0x0078, 0x4c89, 0x2009, 0x8040, 0x6922, 0x681b, 0x0001, 0x2091,
-       0x4080, 0x7007, 0x0001, 0x127f, 0x0078, 0x4c90, 0x7007, 0x0005,
-       0x007c, 0x701c, 0xa06d, 0x0040, 0x4ca2, 0x1078, 0x4d6f, 0x0040,
-       0x4ca2, 0x7007, 0x0003, 0x1078, 0x4d8f, 0x7050, 0xa086, 0x0100,
-       0x0040, 0x4ca4, 0x007c, 0x007c, 0x7050, 0xa09e, 0x0100, 0x00c0,
-       0x4cad, 0x7007, 0x0004, 0x0078, 0x4ccb, 0xa086, 0x0200, 0x00c0,
-       0x4cb3, 0x7007, 0x0005, 0x007c, 0x2001, 0xa57e, 0x2004, 0xa08e,
-       0x0100, 0x00c0, 0x4cc0, 0x7007, 0x0001, 0x1078, 0x4d5b, 0x007c,
-       0xa08e, 0x0000, 0x0040, 0x4cbf, 0xa08e, 0x0200, 0x00c0, 0x4cbf,
-       0x7007, 0x0005, 0x007c, 0x1078, 0x4d25, 0x7006, 0x1078, 0x4d5b,
-       0x007c, 0x007c, 0x0e7e, 0x157e, 0x2071, 0xa534, 0x7184, 0x81ff,
-       0x0040, 0x4cfa, 0xa006, 0x7086, 0xae80, 0x0003, 0x2071, 0x0000,
-       0x21a8, 0x2014, 0x7226, 0x8000, 0x0070, 0x4cf7, 0x2014, 0x722a,
-       0x8000, 0x0070, 0x4cf7, 0x2014, 0x722e, 0x8000, 0x0070, 0x4cf7,
-       0x2014, 0x723a, 0x8000, 0x0070, 0x4cf7, 0x2014, 0x723e, 0xa180,
-       0x8030, 0x7022, 0x157f, 0x0e7f, 0x007c, 0x0e7e, 0x157e, 0x2071,
-       0xa534, 0x7184, 0x81ff, 0x0040, 0x4d22, 0xa006, 0x7086, 0xae80,
-       0x0003, 0x2071, 0x0000, 0x21a8, 0x2014, 0x7226, 0x8000, 0x2014,
-       0x722a, 0x8000, 0x0070, 0x4d1b, 0x2014, 0x723a, 0x8000, 0x2014,
-       0x723e, 0x0078, 0x4d1f, 0x2001, 0x8020, 0x0078, 0x4d21, 0x2001,
-       0x8042, 0x7022, 0x157f, 0x0e7f, 0x007c, 0x702c, 0x7130, 0x8108,
-       0xa102, 0x0048, 0x4d32, 0xa00e, 0x7034, 0x706e, 0x7038, 0x7072,
-       0x0078, 0x4d3c, 0x706c, 0xa080, 0x0040, 0x706e, 0x00c8, 0x4d3c,
-       0x7070, 0xa081, 0x0000, 0x7072, 0x7132, 0x700c, 0x8001, 0x700e,
-       0x00c0, 0x4d52, 0x127e, 0x2091, 0x8000, 0x0068, 0x4d55, 0x2001,
-       0x000d, 0x2102, 0x2091, 0x4080, 0x2001, 0x0001, 0x700b, 0x0000,
-       0x127f, 0x007c, 0x2001, 0x0007, 0x007c, 0x2001, 0x0006, 0x700b,
-       0x0001, 0x127f, 0x007c, 0x701c, 0xa06d, 0x0040, 0x4d6e, 0x127e,
-       0x2091, 0x8000, 0x7010, 0x8001, 0x7012, 0x2d04, 0x701e, 0xa005,
-       0x00c0, 0x4d6b, 0x701a, 0x127f, 0x1078, 0x139a, 0x007c, 0x2019,
-       0x000d, 0x2304, 0x230c, 0xa10e, 0x0040, 0x4d7e, 0x2304, 0x230c,
-       0xa10e, 0x0040, 0x4d7e, 0xa006, 0x0078, 0x4d8e, 0x732c, 0x8319,
-       0x7130, 0xa102, 0x00c0, 0x4d88, 0x2300, 0xa005, 0x0078, 0x4d8e,
-       0x0048, 0x4d8d, 0xa302, 0x0078, 0x4d8e, 0x8002, 0x007c, 0x2d00,
-       0x7026, 0xa080, 0x000d, 0x7056, 0x7053, 0x0000, 0x127e, 0x2091,
-       0x8000, 0x2009, 0xa5d0, 0x2104, 0xc08d, 0x200a, 0x127f, 0x1078,
-       0x13eb, 0x007c, 0x2071, 0xa3e1, 0x7003, 0x0000, 0x7007, 0x0000,
-       0x700f, 0x0000, 0x702b, 0x0001, 0x704f, 0x0000, 0x7053, 0x0001,
-       0x705f, 0x0020, 0x7063, 0x0040, 0x7083, 0x0000, 0x708b, 0x0000,
-       0x708f, 0x0001, 0x70bf, 0x0000, 0x007c, 0x0e7e, 0x2071, 0xa3e1,
-       0x6848, 0xa005, 0x00c0, 0x4dcb, 0x7028, 0xc085, 0x702a, 0xa085,
-       0x0001, 0x0078, 0x4df0, 0x6a50, 0x7236, 0x6b54, 0x733a, 0x6858,
-       0x703e, 0x707a, 0x685c, 0x7042, 0x707e, 0x6848, 0x702e, 0x6840,
-       0x7032, 0x2009, 0x000c, 0x200a, 0x8007, 0x8006, 0x8006, 0xa08c,
-       0x003f, 0xa084, 0xffc0, 0xa210, 0x2100, 0xa319, 0x7272, 0x7376,
-       0x7028, 0xc084, 0x702a, 0x7007, 0x0001, 0x700f, 0x0000, 0xa006,
-       0x0e7f, 0x007c, 0x2b78, 0x2071, 0xa3e1, 0x7004, 0x1079, 0x4e50,
-       0x700c, 0x0079, 0x4dfb, 0x4e00, 0x4df5, 0x4df5, 0x4df5, 0x4df5,
-       0x007c, 0x700c, 0x0079, 0x4e04, 0x4e09, 0x4e4e, 0x4e4e, 0x4e4f,
-       0x4e4f, 0x7830, 0x7930, 0xa106, 0x0040, 0x4e13, 0x7830, 0x7930,
-       0xa106, 0x00c0, 0x4e39, 0x7030, 0xa10a, 0x0040, 0x4e39, 0x00c8,
-       0x4e1b, 0x712c, 0xa10a, 0xa18a, 0x0002, 0x00c8, 0x4e3a, 0x1078,
-       0x1366, 0x0040, 0x4e39, 0x2d00, 0x705a, 0x7063, 0x0040, 0x2001,
-       0x0003, 0x7057, 0x0000, 0x127e, 0x007e, 0x2091, 0x8000, 0x2009,
-       0xa5d0, 0x2104, 0xc085, 0x200a, 0x007f, 0x700e, 0x127f, 0x1078,
-       0x13eb, 0x007c, 0x1078, 0x1366, 0x0040, 0x4e39, 0x2d00, 0x705a,
-       0x1078, 0x1366, 0x00c0, 0x4e46, 0x0078, 0x4e25, 0x2d00, 0x7086,
-       0x7063, 0x0080, 0x2001, 0x0004, 0x0078, 0x4e29, 0x007c, 0x007c,
-       0x4e61, 0x4e62, 0x4e99, 0x4e9a, 0x4e4e, 0x4ed0, 0x4ed5, 0x4f0c,
-       0x4f0d, 0x4f28, 0x4f29, 0x4f2a, 0x4f2b, 0x4f2c, 0x4f2d, 0x4fad,
-       0x4fd7, 0x007c, 0x700c, 0x0079, 0x4e65, 0x4e6a, 0x4e6d, 0x4e7d,
-       0x4e98, 0x4e98, 0x1078, 0x4e01, 0x007c, 0x127e, 0x8001, 0x700e,
-       0x7058, 0x007e, 0x1078, 0x5348, 0x0040, 0x4e7a, 0x2091, 0x8000,
-       0x1078, 0x4e01, 0x0d7f, 0x0078, 0x4e86, 0x127e, 0x8001, 0x700e,
-       0x1078, 0x5348, 0x7058, 0x2068, 0x7084, 0x705a, 0x6803, 0x0000,
-       0x6807, 0x0000, 0x6834, 0xa084, 0x00ff, 0xa08a, 0x0020, 0x00c8,
-       0x4e95, 0x1079, 0x4eb0, 0x127f, 0x007c, 0x127f, 0x1078, 0x4f2e,
-       0x007c, 0x007c, 0x007c, 0x0e7e, 0x2071, 0xa3e1, 0x700c, 0x0079,
-       0x4ea1, 0x4ea6, 0x4ea6, 0x4ea6, 0x4ea8, 0x4eac, 0x0e7f, 0x007c,
-       0x700f, 0x0001, 0x0078, 0x4eae, 0x700f, 0x0002, 0x0e7f, 0x007c,
-       0x4f2e, 0x4f2e, 0x4f4a, 0x4f2e, 0x5080, 0x4f2e, 0x4f2e, 0x4f2e,
-       0x4f2e, 0x4f2e, 0x4f4a, 0x50ca, 0x5117, 0x5170, 0x5186, 0x4f2e,
-       0x4f2e, 0x4f66, 0x4f4a, 0x4f2e, 0x4f2e, 0x4f87, 0x5245, 0x5263,
-       0x4f2e, 0x4f66, 0x4f2e, 0x4f2e, 0x4f2e, 0x4f2e, 0x4f7c, 0x5263,
-       0x7020, 0x2068, 0x1078, 0x139a, 0x007c, 0x700c, 0x0079, 0x4ed8,
-       0x4edd, 0x4ee0, 0x4ef0, 0x4f0b, 0x4f0b, 0x1078, 0x4e01, 0x007c,
-       0x127e, 0x8001, 0x700e, 0x7058, 0x007e, 0x1078, 0x5348, 0x0040,
-       0x4eed, 0x2091, 0x8000, 0x1078, 0x4e01, 0x0d7f, 0x0078, 0x4ef9,
-       0x127e, 0x8001, 0x700e, 0x1078, 0x5348, 0x7058, 0x2068, 0x7084,
-       0x705a, 0x6803, 0x0000, 0x6807, 0x0000, 0x6834, 0xa084, 0x00ff,
-       0xa08a, 0x001a, 0x00c8, 0x4f08, 0x1079, 0x4f0e, 0x127f, 0x007c,
-       0x127f, 0x1078, 0x4f2e, 0x007c, 0x007c, 0x007c, 0x4f2e, 0x4f4a,
-       0x506a, 0x4f2e, 0x4f4a, 0x4f2e, 0x4f4a, 0x4f4a, 0x4f2e, 0x4f4a,
-       0x506a, 0x4f4a, 0x4f4a, 0x4f4a, 0x4f4a, 0x4f4a, 0x4f2e, 0x4f4a,
-       0x506a, 0x4f2e, 0x4f2e, 0x4f4a, 0x4f2e, 0x4f2e, 0x4f2e, 0x4f4a,
-       0x007c, 0x007c, 0x007c, 0x007c, 0x007c, 0x007c, 0x7007, 0x0001,
-       0x6838, 0xa084, 0x00ff, 0xc0d5, 0x683a, 0x127e, 0x2091, 0x8000,
-       0x1078, 0x4982, 0x127f, 0x007c, 0x7007, 0x0001, 0x6838, 0xa084,
-       0x00ff, 0xc0e5, 0x683a, 0x127e, 0x2091, 0x8000, 0x1078, 0x4982,
-       0x127f, 0x007c, 0x7007, 0x0001, 0x6838, 0xa084, 0x00ff, 0xc0ed,
-       0x683a, 0x127e, 0x2091, 0x8000, 0x1078, 0x4982, 0x127f, 0x007c,
-       0x7007, 0x0001, 0x6838, 0xa084, 0x00ff, 0xc0dd, 0x683a, 0x127e,
-       0x2091, 0x8000, 0x1078, 0x4982, 0x127f, 0x007c, 0x6834, 0x8007,
-       0xa084, 0x00ff, 0x0040, 0x4f3c, 0x8001, 0x00c0, 0x4f73, 0x7007,
-       0x0001, 0x0078, 0x5049, 0x7007, 0x0006, 0x7012, 0x2d00, 0x7016,
-       0x701a, 0x704b, 0x5049, 0x007c, 0x684c, 0xa084, 0x00c0, 0xa086,
-       0x00c0, 0x00c0, 0x4f87, 0x7007, 0x0001, 0x0078, 0x5280, 0x2d00,
-       0x7016, 0x701a, 0x20a9, 0x0004, 0xa080, 0x0024, 0x2098, 0x20a1,
-       0xa40c, 0x53a3, 0x6858, 0x7012, 0xa082, 0x0401, 0x00c8, 0x4f58,
-       0x6884, 0xa08a, 0x0002, 0x00c8, 0x4f58, 0x82ff, 0x00c0, 0x4fa9,
-       0x6888, 0x698c, 0xa105, 0x0040, 0x4fa9, 0x2001, 0x5019, 0x0078,
-       0x4fac, 0xa280, 0x500f, 0x2004, 0x70c6, 0x7010, 0xa015, 0x0040,
-       0x4ff7, 0x1078, 0x1366, 0x00c0, 0x4fb8, 0x7007, 0x000f, 0x007c,
-       0x2d00, 0x7022, 0x70c4, 0x2060, 0x6000, 0x6836, 0x6004, 0xad00,
-       0x7096, 0x6008, 0xa20a, 0x00c8, 0x4fc7, 0xa00e, 0x2200, 0x7112,
-       0x620c, 0x8003, 0x800b, 0xa296, 0x0004, 0x0040, 0x4fd0, 0xa108,
-       0x719a, 0x810b, 0x719e, 0xae90, 0x0022, 0x1078, 0x13d1, 0x7090,
-       0xa08e, 0x0100, 0x0040, 0x4feb, 0xa086, 0x0200, 0x0040, 0x4fe3,
-       0x7007, 0x0010, 0x007c, 0x7020, 0x2068, 0x1078, 0x139a, 0x7014,
-       0x2068, 0x0078, 0x4f58, 0x7020, 0x2068, 0x7018, 0x6802, 0x6807,
-       0x0000, 0x2d08, 0x2068, 0x6906, 0x711a, 0x0078, 0x4fad, 0x7014,
-       0x2068, 0x7007, 0x0001, 0x6884, 0xa005, 0x00c0, 0x5006, 0x6888,
-       0x698c, 0xa105, 0x0040, 0x5006, 0x1078, 0x501d, 0x6834, 0xa084,
-       0x00ff, 0xa086, 0x001e, 0x0040, 0x5280, 0x0078, 0x5049, 0x5011,
-       0x5015, 0x0002, 0x0011, 0x0007, 0x0004, 0x000a, 0x000f, 0x0005,
-       0x0006, 0x000a, 0x0011, 0x0005, 0x0004, 0x0f7e, 0x0e7e, 0x0c7e,
-       0x077e, 0x067e, 0x6f88, 0x6e8c, 0x6804, 0x2060, 0xacf0, 0x0021,
-       0xacf8, 0x0027, 0x2009, 0x0005, 0x700c, 0x7816, 0x7008, 0x7812,
-       0x7004, 0x7806, 0x7000, 0x7802, 0x7e0e, 0x7f0a, 0x8109, 0x0040,
-       0x503f, 0xaef2, 0x0004, 0xaffa, 0x0006, 0x0078, 0x502c, 0x6004,
-       0xa065, 0x00c0, 0x5026, 0x067f, 0x077f, 0x0c7f, 0x0e7f, 0x0f7f,
-       0x007c, 0x2009, 0xa32e, 0x210c, 0x81ff, 0x00c0, 0x5064, 0x6838,
-       0xa084, 0x00ff, 0x683a, 0x1078, 0x4290, 0x00c0, 0x5058, 0x007c,
-       0x1078, 0x4a60, 0x127e, 0x2091, 0x8000, 0x1078, 0x8cb8, 0x1078,
-       0x4982, 0x127f, 0x0078, 0x5057, 0x2001, 0x0028, 0x2009, 0x0000,
-       0x0078, 0x5058, 0x7018, 0x6802, 0x2d08, 0x2068, 0x6906, 0x711a,
-       0x7010, 0x8001, 0x7012, 0x0040, 0x5079, 0x7007, 0x0006, 0x0078,
-       0x507f, 0x7014, 0x2068, 0x7007, 0x0001, 0x7048, 0x107a, 0x007c,
-       0x7007, 0x0001, 0x6944, 0x810f, 0xa18c, 0x00ff, 0x6848, 0xa084,
-       0x00ff, 0x20a9, 0x0001, 0xa096, 0x0001, 0x0040, 0x50a9, 0x2009,
-       0x0000, 0x20a9, 0x00ff, 0xa096, 0x0002, 0x0040, 0x50a9, 0xa005,
-       0x00c0, 0x50bc, 0x6944, 0x810f, 0xa18c, 0x00ff, 0x1078, 0x4501,
-       0x00c0, 0x50bc, 0x067e, 0x6e50, 0x1078, 0x45e7, 0x067f, 0x0078,
-       0x50bc, 0x047e, 0x2011, 0xa30c, 0x2224, 0xc484, 0xc48c, 0x2412,
-       0x047f, 0x0c7e, 0x1078, 0x4501, 0x00c0, 0x50b8, 0x1078, 0x4782,
-       0x8108, 0x00f0, 0x50b2, 0x0c7f, 0x684c, 0xd084, 0x00c0, 0x50c3,
-       0x1078, 0x139a, 0x007c, 0x127e, 0x2091, 0x8000, 0x1078, 0x4982,
-       0x127f, 0x007c, 0x127e, 0x2091, 0x8000, 0x7007, 0x0001, 0x2001,
-       0xa352, 0x2004, 0xd0a4, 0x0040, 0x510e, 0x2061, 0xa62d, 0x6100,
-       0xd184, 0x0040, 0x50ee, 0x6858, 0xa084, 0x00ff, 0x00c0, 0x5111,
-       0x6000, 0xd084, 0x0040, 0x510e, 0x6004, 0xa005, 0x00c0, 0x5114,
-       0x6003, 0x0000, 0x600b, 0x0000, 0x0078, 0x510b, 0x2011, 0x0001,
-       0x6860, 0xa005, 0x00c0, 0x50f6, 0x2001, 0x001e, 0x8000, 0x6016,
-       0x6858, 0xa084, 0x00ff, 0x0040, 0x510e, 0x6006, 0x6858, 0x8007,
-       0xa084, 0x00ff, 0x0040, 0x510e, 0x600a, 0x6858, 0x8000, 0x00c0,
-       0x510a, 0xc28d, 0x6202, 0x127f, 0x0078, 0x5337, 0x127f, 0x0078,
-       0x532f, 0x127f, 0x0078, 0x5327, 0x127f, 0x0078, 0x532b, 0x127e,
-       0x2091, 0x8000, 0x7007, 0x0001, 0x2001, 0xa352, 0x2004, 0xd0a4,
-       0x0040, 0x516d, 0x2061, 0xa62d, 0x6000, 0xd084, 0x0040, 0x516d,
-       0x6204, 0x6308, 0xd08c, 0x00c0, 0x515f, 0x6c48, 0xa484, 0x0003,
-       0x0040, 0x5145, 0x6958, 0xa18c, 0x00ff, 0x8001, 0x00c0, 0x513e,
-       0x2100, 0xa210, 0x0048, 0x516a, 0x0078, 0x5145, 0x8001, 0x00c0,
-       0x516a, 0x2100, 0xa212, 0x0048, 0x516a, 0xa484, 0x000c, 0x0040,
-       0x515f, 0x6958, 0x810f, 0xa18c, 0x00ff, 0xa082, 0x0004, 0x00c0,
-       0x5157, 0x2100, 0xa318, 0x0048, 0x516a, 0x0078, 0x515f, 0xa082,
-       0x0004, 0x00c0, 0x516a, 0x2100, 0xa31a, 0x0048, 0x516a, 0x6860,
-       0xa005, 0x0040, 0x5165, 0x8000, 0x6016, 0x6206, 0x630a, 0x127f,
-       0x0078, 0x5337, 0x127f, 0x0078, 0x5333, 0x127f, 0x0078, 0x532f,
-       0x127e, 0x2091, 0x8000, 0x7007, 0x0001, 0x2061, 0xa62d, 0x6300,
-       0xd38c, 0x00c0, 0x5180, 0x6308, 0x8318, 0x0048, 0x5183, 0x630a,
-       0x127f, 0x0078, 0x5345, 0x127f, 0x0078, 0x5333, 0x127e, 0x0c7e,
-       0x2091, 0x8000, 0x7007, 0x0001, 0x684c, 0xd0ac, 0x0040, 0x519a,
-       0x0c7e, 0x2061, 0xa62d, 0x6000, 0xa084, 0xfcff, 0x6002, 0x0c7f,
-       0x0078, 0x51c9, 0x6858, 0xa005, 0x0040, 0x51e0, 0x685c, 0xa065,
-       0x0040, 0x51dc, 0x2001, 0xa32e, 0x2004, 0xa005, 0x0040, 0x51ac,
-       0x1078, 0x8c01, 0x0078, 0x51ba, 0x6013, 0x0400, 0x6037, 0x0000,
-       0x694c, 0xd1a4, 0x0040, 0x51b6, 0x6950, 0x6136, 0x2009, 0x0041,
-       0x1078, 0x756c, 0x6958, 0xa18c, 0xff00, 0xa186, 0x2000, 0x00c0,
-       0x51c9, 0x027e, 0x2009, 0x0000, 0x2011, 0xfdff, 0x1078, 0x5a6d,
-       0x027f, 0x684c, 0xd0c4, 0x0040, 0x51d8, 0x2061, 0xa62d, 0x6000,
-       0xd08c, 0x00c0, 0x51d8, 0x6008, 0x8000, 0x0048, 0x51dc, 0x600a,
-       0x0c7f, 0x127f, 0x0078, 0x5337, 0x0c7f, 0x127f, 0x0078, 0x532f,
-       0x6954, 0xa186, 0x0045, 0x0040, 0x5213, 0xa186, 0x002a, 0x00c0,
-       0x51f0, 0x2001, 0xa30c, 0x200c, 0xc194, 0x2102, 0x0078, 0x51c9,
-       0xa186, 0x0020, 0x0040, 0x5209, 0xa186, 0x0029, 0x0040, 0x51fc,
-       0xa186, 0x002d, 0x00c0, 0x51dc, 0x6944, 0xa18c, 0xff00, 0x810f,
-       0x1078, 0x4501, 0x00c0, 0x51c9, 0x6000, 0xc0e4, 0x6002, 0x0078,
-       0x51c9, 0x685c, 0xa065, 0x0040, 0x51dc, 0x2001, 0xa5a1, 0x2004,
-       0x6016, 0x0078, 0x51c9, 0x685c, 0xa065, 0x0040, 0x51dc, 0x0e7e,
-       0x6860, 0xa075, 0x2001, 0xa32e, 0x2004, 0xa005, 0x0040, 0x522b,
-       0x1078, 0x8c01, 0x8eff, 0x0040, 0x5228, 0x2e60, 0x1078, 0x8c01,
-       0x0e7f, 0x0078, 0x51c9, 0x6024, 0xc0dc, 0xc0d5, 0x6026, 0x2e60,
-       0x6007, 0x003a, 0x6870, 0xa005, 0x0040, 0x523c, 0x6007, 0x003b,
-       0x6874, 0x602a, 0x6878, 0x6012, 0x6003, 0x0001, 0x1078, 0x5bf8,
-       0x1078, 0x6109, 0x0e7f, 0x0078, 0x51c9, 0x2061, 0xa62d, 0x6000,
-       0xd084, 0x0040, 0x525f, 0xd08c, 0x00c0, 0x5345, 0x2091, 0x8000,
-       0x6204, 0x8210, 0x0048, 0x5259, 0x6206, 0x2091, 0x8001, 0x0078,
-       0x5345, 0x2091, 0x8001, 0x6853, 0x0016, 0x0078, 0x533e, 0x6853,
-       0x0007, 0x0078, 0x533e, 0x6834, 0x8007, 0xa084, 0x00ff, 0x00c0,
-       0x526d, 0x1078, 0x4f3c, 0x0078, 0x527f, 0x2030, 0x8001, 0x00c0,
-       0x5277, 0x7007, 0x0001, 0x1078, 0x5280, 0x0078, 0x527f, 0x7007,
-       0x0006, 0x7012, 0x2d00, 0x7016, 0x701a, 0x704b, 0x5280, 0x007c,
-       0x0e7e, 0x127e, 0x2091, 0x8000, 0x2009, 0xa32e, 0x210c, 0x81ff,
-       0x00c0, 0x530b, 0x2009, 0xa30c, 0x210c, 0xd194, 0x00c0, 0x5315,
-       0x6848, 0x2070, 0xae82, 0xaa00, 0x0048, 0x52fb, 0x2001, 0xa315,
-       0x2004, 0xae02, 0x00c8, 0x52fb, 0x2061, 0xa62d, 0x6100, 0xa184,
-       0x0301, 0xa086, 0x0001, 0x00c0, 0x52de, 0x711c, 0xa186, 0x0006,
-       0x00c0, 0x52e6, 0x7018, 0xa005, 0x0040, 0x530b, 0x2004, 0xd0e4,
-       0x00c0, 0x530f, 0x7024, 0xd0dc, 0x00c0, 0x5319, 0x6853, 0x0000,
-       0x6803, 0x0000, 0x2d08, 0x7010, 0xa005, 0x00c0, 0x52ca, 0x7112,
-       0x684c, 0xd0f4, 0x00c0, 0x531d, 0x2e60, 0x1078, 0x59b6, 0x127f,
-       0x0e7f, 0x007c, 0x2068, 0x6800, 0xa005, 0x00c0, 0x52ca, 0x6902,
-       0x2168, 0x684c, 0xd0f4, 0x00c0, 0x531d, 0x127f, 0x0e7f, 0x007c,
-       0x127f, 0x0e7f, 0x6853, 0x0006, 0x0078, 0x533e, 0xd184, 0x0040,
-       0x52d8, 0xd1c4, 0x00c0, 0x52ff, 0x0078, 0x5303, 0x6944, 0xa18c,
-       0xff00, 0x810f, 0x1078, 0x4501, 0x00c0, 0x530f, 0x6000, 0xd0e4,
-       0x00c0, 0x530f, 0x711c, 0xa186, 0x0007, 0x00c0, 0x52fb, 0x6853,
-       0x0002, 0x0078, 0x5311, 0x6853, 0x0008, 0x0078, 0x5311, 0x6853,
-       0x000e, 0x0078, 0x5311, 0x6853, 0x0017, 0x0078, 0x5311, 0x6853,
-       0x0035, 0x0078, 0x5311, 0x6853, 0x0028, 0x0078, 0x5311, 0x6853,
-       0x0029, 0x127f, 0x0e7f, 0x0078, 0x533e, 0x6853, 0x002a, 0x0078,
-       0x5311, 0x6853, 0x0045, 0x0078, 0x5311, 0x2e60, 0x2019, 0x0002,
-       0x6017, 0x0014, 0x1078, 0x9a6a, 0x127f, 0x0e7f, 0x007c, 0x2009,
-       0x003e, 0x0078, 0x5339, 0x2009, 0x0004, 0x0078, 0x5339, 0x2009,
-       0x0006, 0x0078, 0x5339, 0x2009, 0x0016, 0x0078, 0x5339, 0x2009,
-       0x0001, 0x6854, 0xa084, 0xff00, 0xa105, 0x6856, 0x2091, 0x8000,
-       0x1078, 0x4982, 0x2091, 0x8001, 0x007c, 0x1078, 0x139a, 0x007c,
-       0x702c, 0x7130, 0x8108, 0xa102, 0x0048, 0x5355, 0xa00e, 0x7034,
-       0x7072, 0x7038, 0x7076, 0x0078, 0x5361, 0x7070, 0xa080, 0x0040,
-       0x7072, 0x00c8, 0x5361, 0x7074, 0xa081, 0x0000, 0x7076, 0xa085,
-       0x0001, 0x7932, 0x7132, 0x007c, 0x0d7e, 0x1078, 0x59ad, 0x0d7f,
-       0x007c, 0x0d7e, 0x2011, 0x0004, 0x2204, 0xa085, 0x8002, 0x2012,
-       0x0d7f, 0x007c, 0x20e1, 0x0002, 0x3d08, 0x20e1, 0x2000, 0x3d00,
-       0xa084, 0x7000, 0x0040, 0x5380, 0xa086, 0x1000, 0x00c0, 0x53ac,
-       0x20e1, 0x0000, 0x3d00, 0xa094, 0xff00, 0x8217, 0xa084, 0xf000,
-       0xa086, 0x3000, 0x00c0, 0x5390, 0x1078, 0x5570, 0x0078, 0x53a7,
-       0x20e1, 0x0004, 0x3d60, 0xd1bc, 0x00c0, 0x5397, 0x3e60, 0xac84,
-       0x000f, 0x00c0, 0x53ac, 0xac82, 0xaa00, 0x0048, 0x53ac, 0x6854,
-       0xac02, 0x00c8, 0x53ac, 0x2009, 0x0047, 0x1078, 0x756c, 0x7a1c,
-       0xd284, 0x00c0, 0x5372, 0x007c, 0xa016, 0x1078, 0x15ec, 0x0078,
-       0x53a7, 0x0078, 0x53ac, 0x781c, 0xd08c, 0x0040, 0x53db, 0x157e,
-       0x137e, 0x147e, 0x20e1, 0x3000, 0x3d20, 0x3e28, 0xa584, 0x0076,
-       0x00c0, 0x53f1, 0xa484, 0x7000, 0xa086, 0x1000, 0x00c0, 0x53e0,
-       0x1078, 0x540c, 0x0040, 0x53f1, 0x20e1, 0x3000, 0x7828, 0x7828,
-       0x1078, 0x542a, 0x147f, 0x137f, 0x157f, 0x2009, 0xa5b3, 0x2104,
-       0xa005, 0x00c0, 0x53dc, 0x007c, 0x1078, 0x6109, 0x0078, 0x53db,
-       0xa484, 0x7000, 0x00c0, 0x53f1, 0x1078, 0x540c, 0x0040, 0x5403,
-       0x7000, 0xa084, 0xff00, 0xa086, 0x8100, 0x0040, 0x53cc, 0x0078,
-       0x5403, 0x1078, 0xa1ee, 0xd5a4, 0x0040, 0x53ff, 0x1078, 0x1af7,
-       0x20e1, 0x9010, 0x2001, 0x0138, 0x2202, 0x0078, 0x5407, 0x1078,
-       0x540c, 0x687f, 0x0000, 0x20e1, 0x3000, 0x7828, 0x7828, 0x147f,
-       0x137f, 0x157f, 0x0078, 0x53db, 0xa484, 0x01ff, 0x687e, 0xa005,
-       0x0040, 0x541e, 0xa080, 0x001f, 0xa084, 0x03f8, 0x80ac, 0x20e1,
-       0x1000, 0x2ea0, 0x2099, 0x020a, 0x53a5, 0x007c, 0x20a9, 0x000c,
-       0x20e1, 0x1000, 0x2ea0, 0x2099, 0x020a, 0x53a5, 0xa085, 0x0001,
-       0x0078, 0x541d, 0x7000, 0xa084, 0xff00, 0xa08c, 0xf000, 0x8007,
-       0xa196, 0x0000, 0x00c0, 0x5437, 0x0078, 0x567c, 0x007c, 0xa196,
-       0x2000, 0x00c0, 0x5448, 0x6900, 0xa18e, 0x0001, 0x00c0, 0x5444,
-       0x1078, 0x3a43, 0x0078, 0x5436, 0x1078, 0x5450, 0x0078, 0x5436,
-       0xa196, 0x8000, 0x00c0, 0x5436, 0x1078, 0x570c, 0x0078, 0x5436,
-       0x0c7e, 0x7110, 0xa18c, 0xff00, 0x810f, 0xa196, 0x0001, 0x0040,
-       0x545d, 0xa196, 0x0023, 0x00c0, 0x5568, 0xa08e, 0x0023, 0x00c0,
-       0x5492, 0x1078, 0x57b2, 0x0040, 0x5568, 0x7124, 0x610a, 0x7030,
-       0xa08e, 0x0200, 0x00c0, 0x5476, 0x7034, 0xa005, 0x00c0, 0x5568,
-       0x2009, 0x0015, 0x1078, 0x756c, 0x0078, 0x5568, 0xa08e, 0x0214,
-       0x0040, 0x547e, 0xa08e, 0x0210, 0x00c0, 0x5484, 0x2009, 0x0015,
-       0x1078, 0x756c, 0x0078, 0x5568, 0xa08e, 0x0100, 0x00c0, 0x5568,
-       0x7034, 0xa005, 0x00c0, 0x5568, 0x2009, 0x0016, 0x1078, 0x756c,
-       0x0078, 0x5568, 0xa08e, 0x0022, 0x00c0, 0x5568, 0x7030, 0xa08e,
-       0x0300, 0x00c0, 0x54a3, 0x7034, 0xa005, 0x00c0, 0x5568, 0x2009,
-       0x0017, 0x0078, 0x5534, 0xa08e, 0x0500, 0x00c0, 0x54af, 0x7034,
-       0xa005, 0x00c0, 0x5568, 0x2009, 0x0018, 0x0078, 0x5534, 0xa08e,
-       0x2010, 0x00c0, 0x54b7, 0x2009, 0x0019, 0x0078, 0x5534, 0xa08e,
-       0x2110, 0x00c0, 0x54bf, 0x2009, 0x001a, 0x0078, 0x5534, 0xa08e,
-       0x5200, 0x00c0, 0x54cb, 0x7034, 0xa005, 0x00c0, 0x5568, 0x2009,
-       0x001b, 0x0078, 0x5534, 0xa08e, 0x5000, 0x00c0, 0x54d7, 0x7034,
-       0xa005, 0x00c0, 0x5568, 0x2009, 0x001c, 0x0078, 0x5534, 0xa08e,
-       0x1300, 0x00c0, 0x54df, 0x2009, 0x0034, 0x0078, 0x5534, 0xa08e,
-       0x1200, 0x00c0, 0x54eb, 0x7034, 0xa005, 0x00c0, 0x5568, 0x2009,
-       0x0024, 0x0078, 0x5534, 0xa08c, 0xff00, 0xa18e, 0x2400, 0x00c0,
-       0x54f5, 0x2009, 0x002d, 0x0078, 0x5534, 0xa08c, 0xff00, 0xa18e,
-       0x5300, 0x00c0, 0x54ff, 0x2009, 0x002a, 0x0078, 0x5534, 0xa08e,
-       0x0f00, 0x00c0, 0x5507, 0x2009, 0x0020, 0x0078, 0x5534, 0xa08e,
-       0x5300, 0x00c0, 0x550d, 0x0078, 0x552a, 0xa08e, 0x6104, 0x00c0,
-       0x552a, 0x2011, 0xa88d, 0x8208, 0x2204, 0xa082, 0x0004, 0x20a8,
-       0x95ac, 0x95ac, 0x2011, 0x8015, 0x211c, 0x8108, 0x047e, 0x2124,
-       0x1078, 0x3579, 0x047f, 0x8108, 0x00f0, 0x551a, 0x2009, 0x0023,
-       0x0078, 0x5534, 0xa08e, 0x6000, 0x00c0, 0x5532, 0x2009, 0x003f,
-       0x0078, 0x5534, 0x2009, 0x001d, 0x017e, 0x2011, 0xa883, 0x2204,
-       0x8211, 0x220c, 0x1078, 0x24e3, 0x00c0, 0x556a, 0x1078, 0x4499,
-       0x00c0, 0x556a, 0x6612, 0x6516, 0x86ff, 0x0040, 0x555a, 0x017f,
-       0x017e, 0xa186, 0x0017, 0x00c0, 0x555a, 0x6868, 0xa606, 0x00c0,
-       0x555a, 0x686c, 0xa506, 0xa084, 0xff00, 0x00c0, 0x555a, 0x6000,
-       0xc0f5, 0x6002, 0x0c7e, 0x1078, 0x74d7, 0x0040, 0x556d, 0x017f,
-       0x611a, 0x601f, 0x0004, 0x7120, 0x610a, 0x017f, 0x1078, 0x756c,
-       0x0c7f, 0x007c, 0x017f, 0x0078, 0x5568, 0x0c7f, 0x0078, 0x556a,
-       0x0c7e, 0x1078, 0x55d4, 0x00c0, 0x55d2, 0xa184, 0xff00, 0x8007,
-       0xa086, 0x0008, 0x00c0, 0x55d2, 0xa28e, 0x0033, 0x00c0, 0x55a3,
-       0x1078, 0x57b2, 0x0040, 0x55d2, 0x7124, 0x610a, 0x7030, 0xa08e,
-       0x0200, 0x00c0, 0x5595, 0x7034, 0xa005, 0x00c0, 0x55d2, 0x2009,
-       0x0015, 0x1078, 0x756c, 0x0078, 0x55d2, 0xa08e, 0x0100, 0x00c0,
-       0x55d2, 0x7034, 0xa005, 0x00c0, 0x55d2, 0x2009, 0x0016, 0x1078,
-       0x756c, 0x0078, 0x55d2, 0xa28e, 0x0032, 0x00c0, 0x55d2, 0x7030,
-       0xa08e, 0x1400, 0x00c0, 0x55d2, 0x2009, 0x0038, 0x017e, 0x2011,
-       0xa883, 0x2204, 0x8211, 0x220c, 0x1078, 0x24e3, 0x00c0, 0x55d1,
-       0x1078, 0x4499, 0x00c0, 0x55d1, 0x6612, 0x6516, 0x0c7e, 0x1078,
-       0x74d7, 0x0040, 0x55d0, 0x017f, 0x611a, 0x601f, 0x0004, 0x7120,
-       0x610a, 0x017f, 0x1078, 0x756c, 0x1078, 0x6109, 0x0078, 0x55d2,
-       0x0c7f, 0x017f, 0x0c7f, 0x007c, 0x0f7e, 0x0d7e, 0x027e, 0x017e,
-       0x137e, 0x147e, 0x157e, 0x3c00, 0x007e, 0x2079, 0x0030, 0x2069,
-       0x0200, 0x1078, 0x1c25, 0x00c0, 0x5615, 0x1078, 0x1b15, 0x0040,
-       0x561f, 0x7908, 0xa18c, 0x1fff, 0xa182, 0x0011, 0x00c8, 0x561f,
-       0x20a9, 0x000c, 0x20e1, 0x0000, 0x2ea0, 0x2099, 0x020a, 0x53a5,
-       0x20e1, 0x2000, 0x2001, 0x020a, 0x2004, 0x7a0c, 0x7808, 0xa080,
-       0x0007, 0xa084, 0x1ff8, 0xa08a, 0x0140, 0x10c8, 0x1328, 0x80ac,
-       0x20e1, 0x6000, 0x2099, 0x020a, 0x53a5, 0x20e1, 0x7000, 0x6828,
-       0x6828, 0x7803, 0x0004, 0xa294, 0x0070, 0x007f, 0x20e0, 0x157f,
-       0x147f, 0x137f, 0x017f, 0x027f, 0x0d7f, 0x0f7f, 0x007c, 0xa085,
-       0x0001, 0x0078, 0x5615, 0x047e, 0x0e7e, 0x0d7e, 0x2028, 0x2130,
-       0xa696, 0x00ff, 0x00c0, 0x5644, 0xa596, 0xfffd, 0x00c0, 0x5634,
-       0x2009, 0x007f, 0x0078, 0x5677, 0xa596, 0xfffe, 0x00c0, 0x563c,
-       0x2009, 0x007e, 0x0078, 0x5677, 0xa596, 0xfffc, 0x00c0, 0x5644,
-       0x2009, 0x0080, 0x0078, 0x5677, 0x2011, 0x0000, 0x2021, 0x0081,
-       0x20a9, 0x007e, 0x2071, 0xa4b5, 0x2e1c, 0x83ff, 0x00c0, 0x5656,
-       0x82ff, 0x00c0, 0x566b, 0x2410, 0x0078, 0x566b, 0x2368, 0x6f10,
-       0x007e, 0x2100, 0xa706, 0x007f, 0x6b14, 0x00c0, 0x5665, 0xa346,
-       0x00c0, 0x5665, 0x2408, 0x0078, 0x5677, 0x87ff, 0x00c0, 0x566b,
-       0x83ff, 0x0040, 0x5650, 0x8420, 0x8e70, 0x00f0, 0x564c, 0x82ff,
-       0x00c0, 0x5676, 0xa085, 0x0001, 0x0078, 0x5678, 0x2208, 0xa006,
-       0x0d7f, 0x0e7f, 0x047f, 0x007c, 0xa084, 0x0007, 0x0079, 0x5681,
-       0x007c, 0x5689, 0x5689, 0x5689, 0x57c8, 0x5689, 0x568a, 0x56a3,
-       0x56f3, 0x007c, 0x7110, 0xd1bc, 0x0040, 0x56a2, 0x7120, 0x2160,
-       0xac8c, 0x000f, 0x00c0, 0x56a2, 0xac8a, 0xaa00, 0x0048, 0x56a2,
-       0x6854, 0xac02, 0x00c8, 0x56a2, 0x7124, 0x610a, 0x2009, 0x0046,
-       0x1078, 0x756c, 0x007c, 0x0c7e, 0x7110, 0xd1bc, 0x00c0, 0x56f1,
-       0x2011, 0xa883, 0x2204, 0x8211, 0x220c, 0x1078, 0x24e3, 0x00c0,
-       0x56f1, 0x1078, 0x4499, 0x00c0, 0x56f1, 0x6612, 0x6516, 0x6000,
-       0xd0ec, 0x00c0, 0x56f1, 0x6204, 0xa294, 0xff00, 0x8217, 0xa286,
-       0x0006, 0x00c0, 0x56d6, 0x0c7e, 0x1078, 0x74d7, 0x017f, 0x0040,
-       0x56f1, 0x611a, 0x601f, 0x0006, 0x7120, 0x610a, 0x7130, 0x6122,
-       0x2009, 0x0044, 0x1078, 0x756c, 0x0078, 0x56f1, 0x0c7e, 0x1078,
-       0x74d7, 0x017f, 0x0040, 0x56f1, 0x611a, 0x601f, 0x0004, 0x7120,
-       0x610a, 0xa286, 0x0004, 0x00c0, 0x56e9, 0x6007, 0x0005, 0x0078,
-       0x56eb, 0x6007, 0x0001, 0x6003, 0x0001, 0x1078, 0x5c45, 0x1078,
-       0x6109, 0x0c7f, 0x007c, 0x7110, 0xd1bc, 0x0040, 0x570b, 0x7020,
-       0x2060, 0xac84, 0x000f, 0x00c0, 0x570b, 0xac82, 0xaa00, 0x0048,
-       0x570b, 0x6854, 0xac02, 0x00c8, 0x570b, 0x7124, 0x610a, 0x2009,
-       0x0045, 0x1078, 0x756c, 0x007c, 0x7110, 0xa18c, 0xff00, 0x810f,
-       0xa18e, 0x0000, 0x00c0, 0x571c, 0xa084, 0x000f, 0xa08a, 0x0006,
-       0x00c8, 0x571c, 0x1079, 0x571d, 0x007c, 0x5723, 0x5724, 0x5723,
-       0x5723, 0x5794, 0x57a3, 0x007c, 0x7110, 0xd1bc, 0x0040, 0x572c,
-       0x702c, 0xd084, 0x0040, 0x5793, 0x700c, 0x7108, 0x1078, 0x24e3,
-       0x00c0, 0x5793, 0x1078, 0x4499, 0x00c0, 0x5793, 0x6612, 0x6516,
-       0x6204, 0x7110, 0xd1bc, 0x0040, 0x575e, 0xa28c, 0x00ff, 0xa186,
-       0x0004, 0x0040, 0x5747, 0xa186, 0x0006, 0x00c0, 0x5784, 0x0c7e,
-       0x1078, 0x57b2, 0x0c7f, 0x0040, 0x5793, 0x0c7e, 0x1078, 0x74d7,
-       0x017f, 0x0040, 0x5793, 0x611a, 0x601f, 0x0002, 0x7120, 0x610a,
-       0x2009, 0x0088, 0x1078, 0x756c, 0x0078, 0x5793, 0xa28c, 0x00ff,
-       0xa186, 0x0006, 0x0040, 0x5773, 0xa186, 0x0004, 0x0040, 0x5773,
-       0xa294, 0xff00, 0x8217, 0xa286, 0x0004, 0x0040, 0x5773, 0xa286,
-       0x0006, 0x00c0, 0x5784, 0x0c7e, 0x1078, 0x74d7, 0x017f, 0x0040,
-       0x5793, 0x611a, 0x601f, 0x0005, 0x7120, 0x610a, 0x2009, 0x0088,
-       0x1078, 0x756c, 0x0078, 0x5793, 0x0c7e, 0x1078, 0x74d7, 0x017f,
-       0x0040, 0x5793, 0x611a, 0x601f, 0x0004, 0x7120, 0x610a, 0x2009,
-       0x0001, 0x1078, 0x756c, 0x007c, 0x7110, 0xd1bc, 0x0040, 0x57a2,
-       0x1078, 0x57b2, 0x0040, 0x57a2, 0x7124, 0x610a, 0x2009, 0x0089,
-       0x1078, 0x756c, 0x007c, 0x7110, 0xd1bc, 0x0040, 0x57b1, 0x1078,
-       0x57b2, 0x0040, 0x57b1, 0x7124, 0x610a, 0x2009, 0x008a, 0x1078,
-       0x756c, 0x007c, 0x7020, 0x2060, 0xac84, 0x000f, 0x00c0, 0x57c5,
-       0xac82, 0xaa00, 0x0048, 0x57c5, 0x2001, 0xa315, 0x2004, 0xac02,
-       0x00c8, 0x57c5, 0xa085, 0x0001, 0x007c, 0xa006, 0x0078, 0x57c4,
-       0x7110, 0xd1bc, 0x00c0, 0x57de, 0x7024, 0x2060, 0xac84, 0x000f,
-       0x00c0, 0x57de, 0xac82, 0xaa00, 0x0048, 0x57de, 0x6854, 0xac02,
-       0x00c8, 0x57de, 0x2009, 0x0051, 0x1078, 0x756c, 0x007c, 0x2071,
-       0xa5be, 0x7003, 0x0003, 0x700f, 0x0361, 0xa006, 0x701a, 0x7012,
-       0x7017, 0xaa00, 0x7007, 0x0000, 0x7026, 0x702b, 0x6c4e, 0x7032,
-       0x7037, 0x6ca0, 0x703b, 0x0002, 0x703f, 0x0000, 0x7043, 0xffff,
-       0x7047, 0xffff, 0x007c, 0x2071, 0xa5be, 0x00e0, 0x58c1, 0x2091,
-       0x6000, 0x700c, 0x8001, 0x700e, 0x00c0, 0x5873, 0x700f, 0x0361,
-       0x7007, 0x0001, 0x127e, 0x2091, 0x8000, 0x7138, 0x8109, 0x713a,
-       0x00c0, 0x5871, 0x703b, 0x0002, 0x2009, 0x0100, 0x2104, 0xa082,
-       0x0003, 0x00c8, 0x5871, 0x703c, 0xa086, 0x0001, 0x00c0, 0x584e,
-       0x0d7e, 0x2069, 0x0140, 0x6804, 0xa084, 0x4000, 0x0040, 0x582c,
-       0x6803, 0x1000, 0x0078, 0x5833, 0x6804, 0xa084, 0x1000, 0x0040,
-       0x5833, 0x6803, 0x0100, 0x6803, 0x0000, 0x703f, 0x0000, 0x2069,
-       0xa5ab, 0x6804, 0xa082, 0x0006, 0x00c0, 0x5840, 0x6807, 0x0000,
-       0x6830, 0xa082, 0x0003, 0x00c0, 0x5847, 0x6833, 0x0000, 0x1078,
-       0x6109, 0x1078, 0x61d3, 0x0d7f, 0x0078, 0x5871, 0x0d7e, 0x2069,
-       0xa300, 0x6944, 0x6860, 0xa102, 0x00c8, 0x5870, 0x2069, 0xa5ab,
-       0x6804, 0xa086, 0x0000, 0x00c0, 0x5870, 0x6830, 0xa086, 0x0000,
-       0x00c0, 0x5870, 0x703f, 0x0001, 0x6807, 0x0006, 0x6833, 0x0003,
-       0x2069, 0x0100, 0x6830, 0x689e, 0x2069, 0x0140, 0x6803, 0x0600,
-       0x0d7f, 0x0078, 0x5876, 0x127e, 0x2091, 0x8000, 0x7024, 0xa00d,
-       0x0040, 0x588e, 0x7020, 0x8001, 0x7022, 0x00c0, 0x588e, 0x7023,
-       0x0009, 0x8109, 0x7126, 0xa186, 0x03e8, 0x00c0, 0x5889, 0x7028,
-       0x107a, 0x81ff, 0x00c0, 0x588e, 0x7028, 0x107a, 0x7030, 0xa00d,
-       0x0040, 0x589f, 0x702c, 0x8001, 0x702e, 0x00c0, 0x589f, 0x702f,
-       0x0009, 0x8109, 0x7132, 0x00c0, 0x589f, 0x7034, 0x107a, 0x7040,
-       0xa005, 0x0040, 0x58a7, 0x0050, 0x58a7, 0x8001, 0x7042, 0x7044,
-       0xa005, 0x0040, 0x58af, 0x0050, 0x58af, 0x8001, 0x7046, 0x7018,
-       0xa00d, 0x0040, 0x58c0, 0x7008, 0x8001, 0x700a, 0x00c0, 0x58c0,
-       0x700b, 0x0009, 0x8109, 0x711a, 0x00c0, 0x58c0, 0x701c, 0x107a,
-       0x127f, 0x7004, 0x0079, 0x58c4, 0x58eb, 0x58ec, 0x5908, 0x0e7e,
-       0x2071, 0xa5be, 0x7018, 0xa005, 0x00c0, 0x58d2, 0x711a, 0x721e,
-       0x700b, 0x0009, 0x0e7f, 0x007c, 0x0e7e, 0x007e, 0x2071, 0xa5be,
-       0x701c, 0xa206, 0x00c0, 0x58de, 0x701a, 0x701e, 0x007f, 0x0e7f,
-       0x007c, 0x0e7e, 0x2071, 0xa5be, 0x6088, 0xa102, 0x0048, 0x58e9,
-       0x618a, 0x0e7f, 0x007c, 0x007c, 0x7110, 0x1078, 0x4501, 0x00c0,
-       0x58fe, 0x6088, 0x8001, 0x0048, 0x58fe, 0x608a, 0x00c0, 0x58fe,
-       0x127e, 0x2091, 0x8000, 0x1078, 0x6109, 0x127f, 0x8108, 0xa182,
-       0x00ff, 0x0048, 0x5906, 0xa00e, 0x7007, 0x0002, 0x7112, 0x007c,
-       0x7014, 0x2060, 0x127e, 0x2091, 0x8000, 0x603c, 0xa005, 0x0040,
-       0x5917, 0x8001, 0x603e, 0x00c0, 0x5917, 0x1078, 0x8cd7, 0x6014,
-       0xa005, 0x0040, 0x5941, 0x8001, 0x6016, 0x00c0, 0x5941, 0x611c,
-       0xa186, 0x0003, 0x0040, 0x5928, 0xa186, 0x0006, 0x00c0, 0x593f,
-       0x6010, 0x2068, 0x6854, 0xa08a, 0x199a, 0x0048, 0x593f, 0xa082,
-       0x1999, 0x6856, 0xa08a, 0x199a, 0x0048, 0x5938, 0x2001, 0x1999,
-       0x8003, 0x800b, 0x810b, 0xa108, 0x6116, 0x0078, 0x5941, 0x1078,
-       0x8810, 0x127f, 0xac88, 0x0010, 0x7116, 0x2001, 0xca00, 0xa102,
-       0x0048, 0x594e, 0x7017, 0xaa00, 0x7007, 0x0000, 0x007c, 0x0e7e,
-       0x2071, 0xa5be, 0x7027, 0x07d0, 0x7023, 0x0009, 0x703b, 0x0002,
-       0x0e7f, 0x007c, 0x2001, 0xa5c7, 0x2003, 0x0000, 0x007c, 0x0e7e,
-       0x2071, 0xa5be, 0x7132, 0x702f, 0x0009, 0x0e7f, 0x007c, 0x2011,
-       0xa5ca, 0x2013, 0x0000, 0x007c, 0x0e7e, 0x2071, 0xa5be, 0x711a,
-       0x721e, 0x700b, 0x0009, 0x0e7f, 0x007c, 0x027e, 0x0e7e, 0x0f7e,
-       0x2079, 0xa300, 0x7a34, 0xd294, 0x0040, 0x59a4, 0x2071, 0xa5aa,
-       0x2e14, 0xa0fe, 0x0000, 0x0040, 0x5991, 0xa0fe, 0x0001, 0x0040,
-       0x5995, 0xa0fe, 0x0002, 0x00c0, 0x59a0, 0xa292, 0x0085, 0x0078,
-       0x5997, 0xa292, 0x0005, 0x0078, 0x5997, 0xa292, 0x0002, 0x2272,
-       0x0040, 0x599c, 0x00c8, 0x59a4, 0x2011, 0x8037, 0x1078, 0x3579,
-       0x2011, 0xa5a9, 0x2204, 0x2072, 0x0f7f, 0x0e7f, 0x027f, 0x007c,
-       0x0c7e, 0x2061, 0xa62d, 0x0c7f, 0x007c, 0xa184, 0x000f, 0x8003,
-       0x8003, 0x8003, 0xa080, 0xa62d, 0x2060, 0x007c, 0x6854, 0xa08a,
-       0x199a, 0x0048, 0x59bd, 0x2001, 0x1999, 0xa005, 0x00c0, 0x59cc,
-       0x0c7e, 0x2061, 0xa62d, 0x6014, 0x0c7f, 0xa005, 0x00c0, 0x59d1,
-       0x2001, 0x001e, 0x0078, 0x59d1, 0xa08e, 0xffff, 0x00c0, 0x59d1,
-       0xa006, 0x8003, 0x800b, 0x810b, 0xa108, 0x6116, 0x684c, 0xa08c,
-       0x00c0, 0xa18e, 0x00c0, 0x0040, 0x5a24, 0xd0b4, 0x00c0, 0x59e8,
-       0xd0bc, 0x00c0, 0x5a14, 0x2009, 0x0006, 0x1078, 0x5a43, 0x007c,
-       0xd0fc, 0x0040, 0x59f3, 0xa084, 0x0003, 0x0040, 0x59f3, 0xa086,
-       0x0003, 0x00c0, 0x5a3c, 0x6024, 0xd0d4, 0x0040, 0x59fd, 0xc0d4,
-       0x6026, 0x6860, 0x602a, 0x685c, 0x602e, 0x2009, 0xa373, 0x2104,
-       0xd084, 0x0040, 0x5a0f, 0x6118, 0xa188, 0x0027, 0x2104, 0xd08c,
-       0x00c0, 0x5a0f, 0x2009, 0x0042, 0x1078, 0x756c, 0x007c, 0x2009,
-       0x0043, 0x1078, 0x756c, 0x007c, 0xd0fc, 0x0040, 0x5a1f, 0xa084,
-       0x0003, 0x0040, 0x5a1f, 0xa086, 0x0003, 0x00c0, 0x5a3c, 0x2009,
-       0x0042, 0x1078, 0x756c, 0x007c, 0xd0fc, 0x0040, 0x5a32, 0xa084,
-       0x0003, 0xa08e, 0x0002, 0x0040, 0x5a36, 0x2009, 0x0041, 0x1078,
-       0x756c, 0x007c, 0x1078, 0x5a41, 0x0078, 0x5a31, 0x2009, 0x0043,
-       0x1078, 0x756c, 0x0078, 0x5a31, 0x2009, 0x0004, 0x1078, 0x5a43,
-       0x007c, 0x2009, 0x0001, 0x0d7e, 0x6010, 0xa0ec, 0xf000, 0x0040,
-       0x5a6b, 0x2068, 0x6952, 0x6800, 0x6012, 0xa186, 0x0001, 0x00c0,
-       0x5a65, 0x694c, 0xa18c, 0x8100, 0xa18e, 0x8100, 0x00c0, 0x5a65,
-       0x0c7e, 0x2061, 0xa62d, 0x6200, 0xd28c, 0x00c0, 0x5a64, 0x6204,
-       0x8210, 0x0048, 0x5a64, 0x6206, 0x0c7f, 0x1078, 0x4982, 0x6010,
-       0xa06d, 0x10c0, 0x59b6, 0x0d7f, 0x007c, 0x157e, 0x0c7e, 0x2061,
-       0xa62d, 0x6000, 0x81ff, 0x0040, 0x5a78, 0xa205, 0x0078, 0x5a79,
-       0xa204, 0x6002, 0x0c7f, 0x157f, 0x007c, 0x6800, 0xd08c, 0x00c0,
-       0x5a89, 0x6808, 0xa005, 0x0040, 0x5a89, 0x8001, 0x680a, 0xa085,
-       0x0001, 0x007c, 0x20a9, 0x0010, 0xa006, 0x8004, 0x8086, 0x818e,
-       0x00c8, 0x5a93, 0xa200, 0x00f0, 0x5a8e, 0x8086, 0x818e, 0x007c,
-       0x157e, 0x20a9, 0x0010, 0xa005, 0x0040, 0x5ab9, 0xa11a, 0x00c8,
-       0x5ab9, 0x8213, 0x818d, 0x0048, 0x5aac, 0xa11a, 0x00c8, 0x5aad,
-       0x00f0, 0x5aa1, 0x0078, 0x5ab1, 0xa11a, 0x2308, 0x8210, 0x00f0,
-       0x5aa1, 0x007e, 0x3200, 0xa084, 0xf7ff, 0x2080, 0x007f, 0x157f,
-       0x007c, 0x007e, 0x3200, 0xa085, 0x0800, 0x0078, 0x5ab5, 0x127e,
-       0x2091, 0x2200, 0x2079, 0xa5ab, 0x127f, 0x0d7e, 0x2069, 0xa5ab,
-       0x6803, 0x0005, 0x2069, 0x0004, 0x2d04, 0xa085, 0x8001, 0x206a,
-       0x0d7f, 0x007c, 0x0c7e, 0x6027, 0x0001, 0x7804, 0xa084, 0x0007,
-       0x0079, 0x5ada, 0x5ae4, 0x5b09, 0x5b64, 0x5aea, 0x5b09, 0x5ae4,
-       0x5ae2, 0x5ae2, 0x1078, 0x1328, 0x1078, 0x595a, 0x1078, 0x6109,
-       0x0c7f, 0x007c, 0x62c0, 0x82ff, 0x00c0, 0x5af0, 0x0c7f, 0x007c,
-       0x2011, 0x4129, 0x1078, 0x58d4, 0x7828, 0xa092, 0x00c8, 0x00c8,
-       0x5aff, 0x8000, 0x782a, 0x1078, 0x4168, 0x0078, 0x5aee, 0x1078,
-       0x4129, 0x7807, 0x0003, 0x7827, 0x0000, 0x782b, 0x0000, 0x0078,
-       0x5aee, 0x1078, 0x595a, 0x3c00, 0x007e, 0x2011, 0x0209, 0x20e1,
-       0x4000, 0x2214, 0x007f, 0x20e0, 0x82ff, 0x0040, 0x5b27, 0x62c0,
-       0x82ff, 0x00c0, 0x5b27, 0x782b, 0x0000, 0x7824, 0xa065, 0x1040,
-       0x1328, 0x2009, 0x0013, 0x1078, 0x756c, 0x0c7f, 0x007c, 0x3900,
-       0xa082, 0xa6cd, 0x00c8, 0x5b2e, 0x1078, 0x728a, 0x0c7e, 0x7824,
-       0xa065, 0x1040, 0x1328, 0x7804, 0xa086, 0x0004, 0x0040, 0x5ba9,
-       0x7828, 0xa092, 0x2710, 0x00c8, 0x5b44, 0x8000, 0x782a, 0x0c7f,
-       0x1078, 0x6c33, 0x0078, 0x5b25, 0x6104, 0xa186, 0x0003, 0x00c0,
-       0x5b5b, 0x0e7e, 0x2071, 0xa300, 0x70d4, 0x0e7f, 0xd08c, 0x0040,
-       0x5b5b, 0x0c7e, 0x0e7e, 0x2061, 0x0100, 0x2071, 0xa300, 0x1078,
-       0x4171, 0x0e7f, 0x0c7f, 0x1078, 0xa241, 0x2009, 0x0014, 0x1078,
-       0x756c, 0x0c7f, 0x0078, 0x5b25, 0x2001, 0xa5c7, 0x2003, 0x0000,
-       0x62c0, 0x82ff, 0x00c0, 0x5b78, 0x782b, 0x0000, 0x7824, 0xa065,
-       0x1040, 0x1328, 0x2009, 0x0013, 0x1078, 0x75c3, 0x0c7f, 0x007c,
-       0x0c7e, 0x0d7e, 0x3900, 0xa082, 0xa6cd, 0x00c8, 0x5b81, 0x1078,
-       0x728a, 0x7824, 0xa005, 0x1040, 0x1328, 0x781c, 0xa06d, 0x1040,
-       0x1328, 0x6800, 0xc0dc, 0x6802, 0x7924, 0x2160, 0x1078, 0x753d,
-       0x693c, 0x81ff, 0x1040, 0x1328, 0x8109, 0x693e, 0x6854, 0xa015,
-       0x0040, 0x5b9d, 0x7a1e, 0x0078, 0x5b9f, 0x7918, 0x791e, 0x7807,
-       0x0000, 0x7827, 0x0000, 0x0d7f, 0x0c7f, 0x1078, 0x6109, 0x0078,
-       0x5b76, 0x6104, 0xa186, 0x0002, 0x0040, 0x5bb4, 0xa186, 0x0004,
-       0x0040, 0x5bb4, 0x0078, 0x5b38, 0x7808, 0xac06, 0x0040, 0x5b38,
-       0x1078, 0x6010, 0x1078, 0x5c45, 0x0c7f, 0x1078, 0x6109, 0x0078,
-       0x5b25, 0x0c7e, 0x6027, 0x0002, 0x62c8, 0x82ff, 0x00c0, 0x5bdb,
-       0x62c4, 0x82ff, 0x00c0, 0x5bdb, 0x793c, 0xa1e5, 0x0000, 0x0040,
-       0x5bd5, 0x2009, 0x0049, 0x1078, 0x756c, 0x2011, 0xa5ca, 0x2013,
-       0x0000, 0x0c7f, 0x007c, 0x3908, 0xa192, 0xa6cd, 0x00c8, 0x5be2,
-       0x1078, 0x728a, 0x6017, 0x0010, 0x793c, 0x81ff, 0x0040, 0x5bd5,
-       0x793c, 0xa188, 0x0007, 0x210c, 0xa18e, 0x0006, 0x00c0, 0x5bf4,
-       0x6017, 0x0012, 0x0078, 0x5bd9, 0x6017, 0x0016, 0x0078, 0x5bd9,
-       0x007e, 0x017e, 0x0c7e, 0x127e, 0x2091, 0x8000, 0x600f, 0x0000,
-       0x2c08, 0x2061, 0xa5ab, 0x6020, 0x8000, 0x6022, 0x6010, 0xa005,
-       0x0040, 0x5c13, 0xa080, 0x0003, 0x2102, 0x6112, 0x127f, 0x0c7f,
-       0x017f, 0x007f, 0x007c, 0x6116, 0x6112, 0x0078, 0x5c0e, 0x0d7e,
-       0x2069, 0xa5ab, 0x6000, 0xd0d4, 0x0040, 0x5c2c, 0x6820, 0x8000,
-       0x6822, 0xa086, 0x0001, 0x00c0, 0x5c27, 0x2c00, 0x681e, 0x6804,
-       0xa084, 0x0007, 0x0079, 0x6111, 0xc0d5, 0x6002, 0x6818, 0xa005,
-       0x0040, 0x5c3e, 0x6056, 0x605b, 0x0000, 0x007e, 0x2c00, 0x681a,
-       0x0d7f, 0x685a, 0x2069, 0xa5ab, 0x0078, 0x5c1e, 0x6056, 0x605a,
-       0x2c00, 0x681a, 0x681e, 0x0078, 0x5c1e, 0x007e, 0x017e, 0x0c7e,
-       0x127e, 0x2091, 0x8000, 0x600f, 0x0000, 0x2c08, 0x2061, 0xa5ab,
-       0x6020, 0x8000, 0x6022, 0x6008, 0xa005, 0x0040, 0x5c60, 0xa080,
-       0x0003, 0x2102, 0x610a, 0x127f, 0x0c7f, 0x017f, 0x007f, 0x007c,
-       0x610e, 0x610a, 0x0078, 0x5c5b, 0x0c7e, 0x600f, 0x0000, 0x2c08,
-       0x2061, 0xa5ab, 0x6034, 0xa005, 0x0040, 0x5c74, 0xa080, 0x0003,
-       0x2102, 0x6136, 0x0c7f, 0x007c, 0x613a, 0x6136, 0x0078, 0x5c72,
-       0x0f7e, 0x0e7e, 0x0d7e, 0x0c7e, 0x067e, 0x027e, 0x017e, 0x007e,
-       0x127e, 0x2071, 0xa5ab, 0x7638, 0x2660, 0x2678, 0x2091, 0x8000,
-       0x8cff, 0x0040, 0x5ced, 0x6018, 0xa080, 0x0028, 0x2004, 0xa206,
-       0x00c0, 0x5ce8, 0x87ff, 0x0040, 0x5c99, 0x6020, 0xa106, 0x00c0,
-       0x5ce8, 0x703c, 0xac06, 0x00c0, 0x5cab, 0x037e, 0x2019, 0x0001,
-       0x1078, 0x6e6c, 0x7033, 0x0000, 0x703f, 0x0000, 0x7043, 0x0000,
-       0x7047, 0x0000, 0x037f, 0x7038, 0xac36, 0x00c0, 0x5cb1, 0x660c,
-       0x763a, 0x7034, 0xac36, 0x00c0, 0x5cbf, 0x2c00, 0xaf36, 0x0040,
-       0x5cbd, 0x2f00, 0x7036, 0x0078, 0x5cbf, 0x7037, 0x0000, 0x660c,
-       0x067e, 0x2c00, 0xaf06, 0x0040, 0x5cc8, 0x7e0e, 0x0078, 0x5cc9,
-       0x2678, 0x600f, 0x0000, 0x1078, 0x8a44, 0x0040, 0x5ce3, 0x6010,
-       0x2068, 0x601c, 0xa086, 0x0003, 0x00c0, 0x5cf7, 0x6837, 0x0103,
-       0x6b4a, 0x6847, 0x0000, 0x1078, 0x8cb8, 0x1078, 0xa181, 0x1078,
-       0x4982, 0x1078, 0x8bf4, 0x1078, 0x8c01, 0x0c7f, 0x0078, 0x5c88,
-       0x2c78, 0x600c, 0x2060, 0x0078, 0x5c88, 0x127f, 0x007f, 0x017f,
-       0x027f, 0x067f, 0x0c7f, 0x0d7f, 0x0e7f, 0x0f7f, 0x007c, 0x601c,
-       0xa086, 0x0006, 0x00c0, 0x5cd6, 0x1078, 0xa181, 0x1078, 0x9e70,
-       0x0078, 0x5ce3, 0x007e, 0x067e, 0x0c7e, 0x0d7e, 0x0f7e, 0x2031,
-       0x0000, 0x127e, 0x2091, 0x8000, 0x2079, 0xa5ab, 0x7838, 0xa065,
-       0x0040, 0x5d41, 0x600c, 0x007e, 0x600f, 0x0000, 0x783c, 0xac06,
-       0x00c0, 0x5d28, 0x037e, 0x2019, 0x0001, 0x1078, 0x6e6c, 0x7833,
-       0x0000, 0x783f, 0x0000, 0x7843, 0x0000, 0x7847, 0x0000, 0x037f,
-       0x1078, 0x8a44, 0x0040, 0x5d3c, 0x6010, 0x2068, 0x601c, 0xa086,
-       0x0003, 0x00c0, 0x5d4a, 0x6837, 0x0103, 0x6b4a, 0x6847, 0x0000,
-       0x1078, 0x4982, 0x1078, 0x8bf4, 0x1078, 0x8c01, 0x007f, 0x0078,
-       0x5d0f, 0x7e3a, 0x7e36, 0x127f, 0x0f7f, 0x0d7f, 0x0c7f, 0x067f,
-       0x007f, 0x007c, 0x601c, 0xa086, 0x0006, 0x00c0, 0x5d33, 0x1078,
-       0x9e70, 0x0078, 0x5d3c, 0x017e, 0x027e, 0x087e, 0x2041, 0x0000,
-       0x1078, 0x5d6d, 0x1078, 0x5e21, 0x087f, 0x027f, 0x017f, 0x007c,
-       0x0f7e, 0x127e, 0x2079, 0xa5ab, 0x2091, 0x8000, 0x1078, 0x5ebc,
-       0x1078, 0x5f32, 0x127f, 0x0f7f, 0x007c, 0x0f7e, 0x0e7e, 0x0d7e,
-       0x0c7e, 0x067e, 0x017e, 0x007e, 0x127e, 0x2091, 0x8000, 0x2071,
-       0xa5ab, 0x7614, 0x2660, 0x2678, 0x8cff, 0x0040, 0x5e01, 0x6018,
-       0xa080, 0x0028, 0x2004, 0xa206, 0x00c0, 0x5dfc, 0x88ff, 0x0040,
-       0x5d8d, 0x6020, 0xa106, 0x00c0, 0x5dfc, 0x7024, 0xac06, 0x00c0,
-       0x5dbd, 0x2069, 0x0100, 0x68c0, 0xa005, 0x0040, 0x5db8, 0x1078,
-       0x595a, 0x1078, 0x6c41, 0x68c3, 0x0000, 0x1078, 0x7188, 0x7027,
-       0x0000, 0x037e, 0x2069, 0x0140, 0x6b04, 0xa384, 0x1000, 0x0040,
-       0x5dad, 0x6803, 0x0100, 0x6803, 0x0000, 0x2069, 0x0100, 0x6824,
-       0xd084, 0x0040, 0x5db5, 0x6827, 0x0001, 0x037f, 0x0078, 0x5dbd,
-       0x6003, 0x0009, 0x630a, 0x0078, 0x5dfc, 0x7014, 0xac36, 0x00c0,
-       0x5dc3, 0x660c, 0x7616, 0x7010, 0xac36, 0x00c0, 0x5dd1, 0x2c00,
-       0xaf36, 0x0040, 0x5dcf, 0x2f00, 0x7012, 0x0078, 0x5dd1, 0x7013,
-       0x0000, 0x660c, 0x067e, 0x2c00, 0xaf06, 0x0040, 0x5dda, 0x7e0e,
-       0x0078, 0x5ddb, 0x2678, 0x600f, 0x0000, 0x6010, 0x2068, 0x1078,
-       0x8a44, 0x0040, 0x5df5, 0x601c, 0xa086, 0x0003, 0x00c0, 0x5e0a,
-       0x6837, 0x0103, 0x6b4a, 0x6847, 0x0000, 0x1078, 0x8cb8, 0x1078,
-       0xa181, 0x1078, 0x4982, 0x1078, 0x8bf4, 0x1078, 0x8c01, 0x1078,
-       0x7045, 0x0c7f, 0x0078, 0x5d7c, 0x2c78, 0x600c, 0x2060, 0x0078,
-       0x5d7c, 0x127f, 0x007f, 0x017f, 0x067f, 0x0c7f, 0x0d7f, 0x0e7f,
-       0x0f7f, 0x007c, 0x601c, 0xa086, 0x0006, 0x00c0, 0x5e15, 0x1078,
-       0xa181, 0x1078, 0x9e70, 0x0078, 0x5df5, 0x601c, 0xa086, 0x0002,
-       0x00c0, 0x5df5, 0x6004, 0xa086, 0x0085, 0x0040, 0x5de8, 0x0078,
-       0x5df5, 0x0c7e, 0x007e, 0x127e, 0x2091, 0x8000, 0xa280, 0xa434,
-       0x2004, 0xa065, 0x0040, 0x5eb8, 0x0f7e, 0x0e7e, 0x0d7e, 0x067e,
-       0x2071, 0xa5ab, 0x6654, 0x7018, 0xac06, 0x00c0, 0x5e38, 0x761a,
-       0x701c, 0xac06, 0x00c0, 0x5e44, 0x86ff, 0x00c0, 0x5e43, 0x7018,
-       0x701e, 0x0078, 0x5e44, 0x761e, 0x6058, 0xa07d, 0x0040, 0x5e49,
-       0x7e56, 0xa6ed, 0x0000, 0x0040, 0x5e4f, 0x2f00, 0x685a, 0x6057,
-       0x0000, 0x605b, 0x0000, 0x6000, 0xc0d4, 0xc0dc, 0x6002, 0x1078,
-       0x4410, 0x0040, 0x5eb4, 0x7624, 0x86ff, 0x0040, 0x5ea2, 0xa680,
-       0x0004, 0x2004, 0xad06, 0x00c0, 0x5ea2, 0x0d7e, 0x2069, 0x0100,
-       0x68c0, 0xa005, 0x0040, 0x5e99, 0x1078, 0x595a, 0x1078, 0x6c41,
-       0x68c3, 0x0000, 0x1078, 0x7188, 0x7027, 0x0000, 0x037e, 0x2069,
-       0x0140, 0x6b04, 0xa384, 0x1000, 0x0040, 0x5e82, 0x6803, 0x0100,
-       0x6803, 0x0000, 0x2069, 0x0100, 0x6824, 0xd084, 0x0040, 0x5e8a,
-       0x6827, 0x0001, 0x037f, 0x0d7f, 0x0c7e, 0x603c, 0xa005, 0x0040,
-       0x5e93, 0x8001, 0x603e, 0x2660, 0x1078, 0x8c01, 0x0c7f, 0x0078,
-       0x5ea2, 0x0d7f, 0x0c7e, 0x2660, 0x6003, 0x0009, 0x630a, 0x0c7f,
-       0x0078, 0x5e57, 0x8dff, 0x0040, 0x5eb0, 0x6837, 0x0103, 0x6b4a,
-       0x6847, 0x0000, 0x1078, 0x8cb8, 0x1078, 0xa181, 0x1078, 0x4982,
-       0x1078, 0x7045, 0x0078, 0x5e57, 0x067f, 0x0d7f, 0x0e7f, 0x0f7f,
-       0x127f, 0x007f, 0x0c7f, 0x007c, 0x007e, 0x067e, 0x0c7e, 0x0d7e,
-       0x2031, 0x0000, 0x7814, 0xa065, 0x0040, 0x5f16, 0x600c, 0x007e,
-       0x600f, 0x0000, 0x7824, 0xac06, 0x00c0, 0x5efb, 0x2069, 0x0100,
-       0x68c0, 0xa005, 0x0040, 0x5ef5, 0x1078, 0x595a, 0x1078, 0x6c41,
-       0x68c3, 0x0000, 0x1078, 0x7188, 0x7827, 0x0000, 0x037e, 0x2069,
-       0x0140, 0x6b04, 0xa384, 0x1000, 0x0040, 0x5eea, 0x6803, 0x0100,
-       0x6803, 0x0000, 0x2069, 0x0100, 0x6824, 0xd084, 0x0040, 0x5ef2,
-       0x6827, 0x0001, 0x037f, 0x0078, 0x5efb, 0x6003, 0x0009, 0x630a,
-       0x2c30, 0x0078, 0x5f13, 0x6010, 0x2068, 0x1078, 0x8a44, 0x0040,
-       0x5f0f, 0x601c, 0xa086, 0x0003, 0x00c0, 0x5f1d, 0x6837, 0x0103,
-       0x6b4a, 0x6847, 0x0000, 0x1078, 0x4982, 0x1078, 0x8bf4, 0x1078,
-       0x8c01, 0x1078, 0x7045, 0x007f, 0x0078, 0x5ec3, 0x7e16, 0x7e12,
-       0x0d7f, 0x0c7f, 0x067f, 0x007f, 0x007c, 0x601c, 0xa086, 0x0006,
-       0x00c0, 0x5f26, 0x1078, 0x9e70, 0x0078, 0x5f0f, 0x601c, 0xa086,
-       0x0002, 0x00c0, 0x5f0f, 0x6004, 0xa086, 0x0085, 0x0040, 0x5f06,
-       0x0078, 0x5f0f, 0x007e, 0x067e, 0x0c7e, 0x0d7e, 0x7818, 0xa065,
-       0x0040, 0x5fa0, 0x6054, 0x007e, 0x6057, 0x0000, 0x605b, 0x0000,
-       0x6000, 0xc0d4, 0xc0dc, 0x6002, 0x1078, 0x4410, 0x0040, 0x5f9d,
-       0x7e24, 0x86ff, 0x0040, 0x5f8f, 0xa680, 0x0004, 0x2004, 0xad06,
-       0x00c0, 0x5f8f, 0x0d7e, 0x2069, 0x0100, 0x68c0, 0xa005, 0x0040,
-       0x5f86, 0x1078, 0x595a, 0x1078, 0x6c41, 0x68c3, 0x0000, 0x1078,
-       0x7188, 0x7827, 0x0000, 0x037e, 0x2069, 0x0140, 0x6b04, 0xa384,
-       0x1000, 0x0040, 0x5f6f, 0x6803, 0x0100, 0x6803, 0x0000, 0x2069,
-       0x0100, 0x6824, 0xd084, 0x0040, 0x5f77, 0x6827, 0x0001, 0x037f,
-       0x0d7f, 0x0c7e, 0x603c, 0xa005, 0x0040, 0x5f80, 0x8001, 0x603e,
-       0x2660, 0x1078, 0x8c01, 0x0c7f, 0x0078, 0x5f8f, 0x0d7f, 0x0c7e,
-       0x2660, 0x6003, 0x0009, 0x630a, 0x0c7f, 0x0078, 0x5f44, 0x8dff,
-       0x0040, 0x5f99, 0x6837, 0x0103, 0x6b4a, 0x6847, 0x0000, 0x1078,
-       0x4982, 0x1078, 0x7045, 0x0078, 0x5f44, 0x007f, 0x0078, 0x5f37,
-       0x781e, 0x781a, 0x0d7f, 0x0c7f, 0x067f, 0x007f, 0x007c, 0x0e7e,
-       0x0d7e, 0x067e, 0x6000, 0xd0dc, 0x0040, 0x5fc4, 0x604c, 0xa06d,
-       0x0040, 0x5fc4, 0x6848, 0xa606, 0x00c0, 0x5fc4, 0x2071, 0xa5ab,
-       0x7024, 0xa035, 0x0040, 0x5fc4, 0xa080, 0x0004, 0x2004, 0xad06,
-       0x00c0, 0x5fc4, 0x1078, 0x5fc8, 0x067f, 0x0d7f, 0x0e7f, 0x007c,
-       0x0f7e, 0x2079, 0x0100, 0x78c0, 0xa005, 0x00c0, 0x5fd7, 0x0c7e,
-       0x2660, 0x6003, 0x0009, 0x630a, 0x0c7f, 0x0078, 0x600e, 0x1078,
-       0x6c41, 0x78c3, 0x0000, 0x1078, 0x7188, 0x7027, 0x0000, 0x037e,
-       0x2079, 0x0140, 0x7b04, 0xa384, 0x1000, 0x0040, 0x5feb, 0x7803,
-       0x0100, 0x7803, 0x0000, 0x2079, 0x0100, 0x7824, 0xd084, 0x0040,
-       0x5ff3, 0x7827, 0x0001, 0x1078, 0x7188, 0x037f, 0x1078, 0x4410,
-       0x0c7e, 0x603c, 0xa005, 0x0040, 0x5fff, 0x8001, 0x603e, 0x2660,
-       0x1078, 0x753d, 0x0c7f, 0x6837, 0x0103, 0x6b4a, 0x6847, 0x0000,
-       0x1078, 0x8cb8, 0x1078, 0x4982, 0x1078, 0x7045, 0x0f7f, 0x007c,
-       0x0e7e, 0x0c7e, 0x2071, 0xa5ab, 0x7004, 0xa084, 0x0007, 0x0079,
-       0x6019, 0x6023, 0x6026, 0x603f, 0x605b, 0x60a0, 0x6023, 0x6023,
-       0x6021, 0x1078, 0x1328, 0x0c7f, 0x0e7f, 0x007c, 0x7024, 0xa065,
-       0x0040, 0x6034, 0x7020, 0x8001, 0x7022, 0x600c, 0xa015, 0x0040,
-       0x603b, 0x7216, 0x600f, 0x0000, 0x7007, 0x0000, 0x7027, 0x0000,
-       0x0c7f, 0x0e7f, 0x007c, 0x7216, 0x7212, 0x0078, 0x6034, 0x6018,
-       0x2060, 0x1078, 0x4410, 0x6000, 0xc0dc, 0x6002, 0x7020, 0x8001,
-       0x7022, 0x0040, 0x6050, 0x6054, 0xa015, 0x0040, 0x6057, 0x721e,
-       0x7007, 0x0000, 0x7027, 0x0000, 0x0c7f, 0x0e7f, 0x007c, 0x7218,
-       0x721e, 0x0078, 0x6050, 0x7024, 0xa065, 0x0040, 0x609d, 0x700c,
-       0xac06, 0x00c0, 0x6072, 0x1078, 0x7045, 0x600c, 0xa015, 0x0040,
-       0x606e, 0x720e, 0x600f, 0x0000, 0x0078, 0x609b, 0x720e, 0x720a,
-       0x0078, 0x609b, 0x7014, 0xac06, 0x00c0, 0x6085, 0x1078, 0x7045,
-       0x600c, 0xa015, 0x0040, 0x6081, 0x7216, 0x600f, 0x0000, 0x0078,
-       0x609b, 0x7216, 0x7212, 0x0078, 0x609b, 0x6018, 0x2060, 0x1078,
-       0x4410, 0x6000, 0xc0dc, 0x6002, 0x1078, 0x7045, 0x701c, 0xa065,
-       0x0040, 0x609b, 0x6054, 0xa015, 0x0040, 0x6099, 0x721e, 0x0078,
-       0x609b, 0x7218, 0x721e, 0x7027, 0x0000, 0x0c7f, 0x0e7f, 0x007c,
-       0x7024, 0xa065, 0x0040, 0x60ad, 0x1078, 0x7045, 0x600c, 0xa015,
-       0x0040, 0x60b4, 0x720e, 0x600f, 0x0000, 0x1078, 0x7188, 0x7027,
-       0x0000, 0x0c7f, 0x0e7f, 0x007c, 0x720e, 0x720a, 0x0078, 0x60ad,
-       0x0d7e, 0x2069, 0xa5ab, 0x6830, 0xa084, 0x0003, 0x0079, 0x60c0,
-       0x60c6, 0x60c8, 0x60ee, 0x60c6, 0x1078, 0x1328, 0x0d7f, 0x007c,
-       0x0c7e, 0x6840, 0xa086, 0x0001, 0x0040, 0x60e4, 0x683c, 0xa065,
-       0x0040, 0x60d9, 0x600c, 0xa015, 0x0040, 0x60e0, 0x6a3a, 0x600f,
-       0x0000, 0x6833, 0x0000, 0x683f, 0x0000, 0x0c7f, 0x0d7f, 0x007c,
-       0x683a, 0x6836, 0x0078, 0x60d9, 0x6843, 0x0000, 0x6838, 0xa065,
-       0x0040, 0x60d9, 0x6003, 0x0003, 0x0078, 0x60d9, 0x0c7e, 0x6843,
-       0x0000, 0x6847, 0x0000, 0x683c, 0xa065, 0x0040, 0x6106, 0x600c,
-       0xa015, 0x0040, 0x6102, 0x6a3a, 0x600f, 0x0000, 0x683f, 0x0000,
-       0x0078, 0x6106, 0x683f, 0x0000, 0x683a, 0x6836, 0x0c7f, 0x0d7f,
-       0x007c, 0x0d7e, 0x2069, 0xa5ab, 0x6804, 0xa084, 0x0007, 0x0079,
-       0x6111, 0x611b, 0x61c2, 0x61c2, 0x61c2, 0x61c2, 0x61c4, 0x61c2,
-       0x6119, 0x1078, 0x1328, 0x6820, 0xa005, 0x00c0, 0x6121, 0x0d7f,
-       0x007c, 0x0c7e, 0x680c, 0xa065, 0x0040, 0x6130, 0x6807, 0x0004,
-       0x6826, 0x682b, 0x0000, 0x1078, 0x620a, 0x0c7f, 0x0d7f, 0x007c,
-       0x6814, 0xa065, 0x0040, 0x613e, 0x6807, 0x0001, 0x6826, 0x682b,
-       0x0000, 0x1078, 0x620a, 0x0c7f, 0x0d7f, 0x007c, 0x0e7e, 0x037e,
-       0x6a1c, 0xa2f5, 0x0000, 0x0040, 0x61bd, 0x704c, 0xa00d, 0x0040,
-       0x614d, 0x7088, 0xa005, 0x0040, 0x6165, 0x7054, 0xa075, 0x0040,
-       0x6156, 0xa20e, 0x0040, 0x61bd, 0x0078, 0x615b, 0x6818, 0xa20e,
-       0x0040, 0x61bd, 0x2070, 0x704c, 0xa00d, 0x0040, 0x614d, 0x7088,
-       0xa005, 0x00c0, 0x614d, 0x2e00, 0x681e, 0x733c, 0x7038, 0xa302,
-       0x00c8, 0x614d, 0x1078, 0x750c, 0x0040, 0x61bd, 0x8318, 0x733e,
-       0x6112, 0x2e10, 0x621a, 0xa180, 0x0014, 0x2004, 0xa084, 0x00ff,
-       0x6032, 0xa180, 0x0014, 0x2003, 0x0000, 0xa180, 0x0015, 0x2004,
-       0xa08a, 0x199a, 0x0048, 0x6186, 0x2001, 0x1999, 0x8003, 0x801b,
-       0x831b, 0xa318, 0x6316, 0x037f, 0x0f7e, 0x2c78, 0x71a0, 0xd1bc,
-       0x0040, 0x619f, 0x7100, 0xd1f4, 0x0040, 0x619b, 0x7114, 0xa18c,
-       0x00ff, 0x0078, 0x61a4, 0x2009, 0x0000, 0x0078, 0x61a4, 0xa1e0,
-       0x293f, 0x2c0c, 0xa18c, 0x00ff, 0x2061, 0x0100, 0x619a, 0x1078,
-       0x679b, 0x7300, 0xc3dd, 0x7302, 0x6807, 0x0002, 0x2f18, 0x6b26,
-       0x682b, 0x0000, 0x781f, 0x0003, 0x7803, 0x0001, 0x7807, 0x0040,
-       0x0f7f, 0x0e7f, 0x0c7f, 0x0d7f, 0x007c, 0x037f, 0x0e7f, 0x0c7f,
-       0x0078, 0x61bb, 0x0d7f, 0x007c, 0x0c7e, 0x680c, 0xa065, 0x0040,
-       0x61d0, 0x6807, 0x0004, 0x6826, 0x682b, 0x0000, 0x1078, 0x620a,
-       0x0c7f, 0x0d7f, 0x007c, 0x0f7e, 0x0d7e, 0x2069, 0xa5ab, 0x6830,
-       0xa086, 0x0000, 0x00c0, 0x61f1, 0x6838, 0xa07d, 0x0040, 0x61f1,
-       0x6833, 0x0001, 0x683e, 0x6847, 0x0000, 0x127e, 0x0f7e, 0x2091,
-       0x2200, 0x027f, 0x1078, 0x1d28, 0x00c0, 0x61f4, 0x127f, 0x1078,
-       0x6ae5, 0x0d7f, 0x0f7f, 0x007c, 0x127f, 0x6843, 0x0000, 0x7803,
-       0x0002, 0x780c, 0xa015, 0x0040, 0x6206, 0x6a3a, 0x780f, 0x0000,
-       0x6833, 0x0000, 0x683f, 0x0000, 0x0078, 0x61f1, 0x683a, 0x6836,
-       0x0078, 0x6200, 0x601c, 0xa084, 0x000f, 0x1079, 0x6210, 0x007c,
-       0x6219, 0x621e, 0x663f, 0x6758, 0x621e, 0x663f, 0x6758, 0x6219,
-       0x621e, 0x1078, 0x6010, 0x1078, 0x6109, 0x007c, 0x157e, 0x137e,
-       0x147e, 0x0c7e, 0x0f7e, 0x6004, 0xa08a, 0x0044, 0x10c8, 0x1328,
-       0x6118, 0x2178, 0x79a0, 0xd1bc, 0x0040, 0x623b, 0x7900, 0xd1f4,
-       0x0040, 0x6237, 0x7914, 0xa18c, 0x00ff, 0x0078, 0x6240, 0x2009,
-       0x0000, 0x0078, 0x6240, 0xa1f8, 0x293f, 0x2f0c, 0xa18c, 0x00ff,
-       0x2c78, 0x2061, 0x0100, 0x619a, 0xa08a, 0x0040, 0x00c8, 0x6292,
-       0x1079, 0x6250, 0x0f7f, 0x0c7f, 0x147f, 0x137f, 0x157f, 0x007c,
-       0x62f8, 0x6340, 0x6368, 0x6403, 0x6433, 0x643b, 0x6462, 0x6473,
-       0x6484, 0x648c, 0x64a4, 0x648c, 0x650f, 0x6473, 0x6530, 0x6538,
-       0x6484, 0x6538, 0x6549, 0x6290, 0x6290, 0x6290, 0x6290, 0x6290,
-       0x6290, 0x6290, 0x6290, 0x6290, 0x6290, 0x6290, 0x6d05, 0x6d2a,
-       0x6d3f, 0x6d62, 0x6d83, 0x6462, 0x6290, 0x6462, 0x648c, 0x6290,
-       0x6368, 0x6403, 0x6290, 0x72ac, 0x648c, 0x6290, 0x72cc, 0x648c,
-       0x6290, 0x6290, 0x62f3, 0x62a1, 0x6290, 0x72f1, 0x7368, 0x7450,
-       0x6290, 0x7461, 0x645c, 0x747d, 0x6290, 0x6d98, 0x6290, 0x6290,
-       0x1078, 0x1328, 0x2100, 0x1079, 0x629b, 0x0f7f, 0x0c7f, 0x147f,
-       0x137f, 0x157f, 0x007c, 0x629f, 0x629f, 0x629f, 0x62d5, 0x1078,
-       0x1328, 0x0d7e, 0x20a1, 0x020b, 0x1078, 0x6567, 0x7810, 0x2068,
-       0x20a3, 0x2414, 0x20a3, 0x0018, 0x20a3, 0x0800, 0x683c, 0x20a2,
-       0x20a3, 0x0000, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x20a3, 0x0000,
-       0x6850, 0x20a2, 0x6854, 0x20a2, 0x20a3, 0x0000, 0x20a3, 0x0000,
-       0x60c3, 0x0018, 0x1078, 0x6c2d, 0x0d7f, 0x007c, 0x0d7e, 0x7818,
-       0x2068, 0x68a0, 0xa082, 0x007e, 0x0048, 0x62d2, 0xa085, 0x0001,
-       0x0d7f, 0x007c, 0xa006, 0x0078, 0x62d0, 0x0d7e, 0x20a1, 0x020b,
-       0x1078, 0x6567, 0x20a3, 0x0500, 0x20a3, 0x0000, 0x7810, 0xa0e8,
-       0x000f, 0x6808, 0x20a2, 0x680c, 0x20a2, 0x6810, 0x20a2, 0x6814,
-       0x20a2, 0x6818, 0x20a2, 0x681c, 0x20a2, 0x60c3, 0x0010, 0x1078,
-       0x6c2d, 0x0d7f, 0x007c, 0x6030, 0x609a, 0x1078, 0x6c2d, 0x007c,
-       0x20a1, 0x020b, 0x1078, 0x6567, 0x20a3, 0x5200, 0x20a3, 0x0000,
-       0x0d7e, 0x2069, 0xa351, 0x6804, 0xd084, 0x0040, 0x6312, 0x6828,
-       0x20a3, 0x0000, 0x017e, 0x1078, 0x24fa, 0x21a2, 0x017f, 0x0d7f,
-       0x0078, 0x6317, 0x0d7f, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x20a9,
-       0x0004, 0x2099, 0xa305, 0x53a6, 0x20a9, 0x0004, 0x2099, 0xa301,
-       0x53a6, 0x7818, 0xa080, 0x0028, 0x2004, 0xa082, 0x007f, 0x0048,
-       0x6331, 0x2001, 0xa31a, 0x20a6, 0x2001, 0xa31b, 0x20a6, 0x0078,
-       0x6337, 0x20a3, 0x0000, 0x6030, 0xa084, 0x00ff, 0x20a2, 0x20a3,
-       0x0000, 0x20a3, 0x0000, 0x60c3, 0x001c, 0x1078, 0x6c2d, 0x007c,
-       0x20a1, 0x020b, 0x1078, 0x6567, 0x20a3, 0x0500, 0x20a3, 0x0000,
-       0x7818, 0xa080, 0x0028, 0x2004, 0xa082, 0x007f, 0x0048, 0x6358,
-       0x2001, 0xa31a, 0x20a6, 0x2001, 0xa31b, 0x20a6, 0x0078, 0x635e,
-       0x20a3, 0x0000, 0x6030, 0xa084, 0x00ff, 0x20a2, 0x20a9, 0x0004,
-       0x2099, 0xa305, 0x53a6, 0x60c3, 0x0010, 0x1078, 0x6c2d, 0x007c,
-       0x20a1, 0x020b, 0x1078, 0x6567, 0x0c7e, 0x7818, 0x2060, 0x2001,
-       0x0000, 0x1078, 0x48a2, 0x0c7f, 0x7818, 0xa080, 0x0028, 0x2004,
-       0xa086, 0x007e, 0x00c0, 0x6383, 0x20a3, 0x0400, 0x620c, 0xc2b4,
-       0x620e, 0x0078, 0x6385, 0x20a3, 0x0300, 0x20a3, 0x0000, 0x7818,
-       0xa080, 0x0028, 0x2004, 0xa086, 0x007e, 0x00c0, 0x63d2, 0x2099,
-       0xa58c, 0x33a6, 0x9398, 0x33a6, 0x9398, 0x3304, 0xa084, 0x3fff,
-       0x20a2, 0x9398, 0x33a6, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x20a3,
-       0x0000, 0x20a3, 0x0000, 0x20a9, 0x0004, 0x2099, 0xa305, 0x53a6,
-       0x20a9, 0x0004, 0x2099, 0xa301, 0x53a6, 0x20a9, 0x0010, 0x20a3,
-       0x0000, 0x00f0, 0x63af, 0x2099, 0xa594, 0x3304, 0xc0dd, 0x20a2,
-       0x2001, 0xa371, 0x2004, 0xd0e4, 0x0040, 0x63ca, 0x20a3, 0x0000,
-       0x20a3, 0x0000, 0x9398, 0x9398, 0x9398, 0x33a6, 0x20a9, 0x0004,
-       0x0078, 0x63cc, 0x20a9, 0x0007, 0x20a3, 0x0000, 0x00f0, 0x63cc,
-       0x0078, 0x63f2, 0x2099, 0xa58c, 0x20a9, 0x0008, 0x53a6, 0x20a9,
-       0x0004, 0x2099, 0xa305, 0x53a6, 0x20a9, 0x0004, 0x2099, 0xa301,
-       0x53a6, 0x20a9, 0x0008, 0x20a3, 0x0000, 0x00f0, 0x63e3, 0x20a9,
-       0x0008, 0x20a3, 0x0000, 0x00f0, 0x63e9, 0x2099, 0xa594, 0x20a9,
-       0x0008, 0x53a6, 0x20a9, 0x0008, 0x20a3, 0x0000, 0x00f0, 0x63f4,
-       0x20a9, 0x000a, 0x20a3, 0x0000, 0x00f0, 0x63fa, 0x60c3, 0x0074,
-       0x1078, 0x6c2d, 0x007c, 0x20a1, 0x020b, 0x1078, 0x6567, 0x20a3,
-       0x2010, 0x20a3, 0x0014, 0x20a3, 0x0800, 0x20a3, 0x2000, 0xa006,
-       0x20a2, 0x20a2, 0x20a2, 0x20a2, 0x20a2, 0x0f7e, 0x2079, 0xa351,
-       0x7904, 0x0f7f, 0xd1ac, 0x00c0, 0x641f, 0xa085, 0x0020, 0xd1a4,
-       0x0040, 0x6424, 0xa085, 0x0010, 0xa085, 0x0002, 0x0d7e, 0x0078,
-       0x64ed, 0x20a2, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x60c3, 0x0014,
-       0x1078, 0x6c2d, 0x007c, 0x20a1, 0x020b, 0x1078, 0x6567, 0x20a3,
-       0x5000, 0x0078, 0x6385, 0x20a1, 0x020b, 0x1078, 0x6567, 0x20a3,
-       0x2110, 0x20a3, 0x0014, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x20a3,
-       0x0000, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x20a3,
-       0x0000, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x60c3,
-       0x0014, 0x1078, 0x6c2d, 0x007c, 0x20a1, 0x020b, 0x1078, 0x65ef,
-       0x0078, 0x6466, 0x20a1, 0x020b, 0x1078, 0x65f8, 0x20a3, 0x0200,
-       0x20a3, 0x0000, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x60c3, 0x0004,
-       0x1078, 0x6c2d, 0x007c, 0x20a1, 0x020b, 0x1078, 0x65f8, 0x20a3,
-       0x0100, 0x20a3, 0x0000, 0x20a3, 0x0003, 0x20a3, 0x2a00, 0x60c3,
-       0x0008, 0x1078, 0x6c2d, 0x007c, 0x20a1, 0x020b, 0x1078, 0x65f8,
-       0x20a3, 0x0200, 0x0078, 0x6385, 0x20a1, 0x020b, 0x1078, 0x65f8,
-       0x20a3, 0x0100, 0x20a3, 0x0000, 0x7828, 0xa005, 0x0040, 0x649b,
-       0x20a2, 0x0078, 0x649d, 0x20a3, 0x0003, 0x7810, 0x20a2, 0x60c3,
-       0x0008, 0x1078, 0x6c2d, 0x007c, 0x0d7e, 0x20a1, 0x020b, 0x1078,
-       0x65f8, 0x20a3, 0x0210, 0x20a3, 0x0014, 0x20a3, 0x0800, 0x7818,
-       0x2068, 0x6894, 0xa086, 0x0014, 0x00c0, 0x64ca, 0x6998, 0xa184,
-       0xc000, 0x00c0, 0x64c6, 0xd1ec, 0x0040, 0x64c2, 0x20a3, 0x2100,
-       0x0078, 0x64cc, 0x20a3, 0x0100, 0x0078, 0x64cc, 0x20a3, 0x0400,
-       0x0078, 0x64cc, 0x20a3, 0x0700, 0xa006, 0x20a2, 0x20a2, 0x20a2,
-       0x20a2, 0x20a2, 0x0f7e, 0x2079, 0xa351, 0x7904, 0x0f7f, 0xd1ac,
-       0x00c0, 0x64dc, 0xa085, 0x0020, 0xd1a4, 0x0040, 0x64e1, 0xa085,
-       0x0010, 0x2009, 0xa373, 0x210c, 0xd184, 0x0040, 0x64eb, 0x699c,
-       0xd18c, 0x0040, 0x64ed, 0xa085, 0x0002, 0x027e, 0x2009, 0xa371,
-       0x210c, 0xd1e4, 0x0040, 0x64fb, 0xc0c5, 0xa094, 0x0030, 0xa296,
-       0x0010, 0x0040, 0x6505, 0xd1ec, 0x0040, 0x6505, 0xa094, 0x0030,
-       0xa296, 0x0010, 0x0040, 0x6505, 0xc0bd, 0x027f, 0x20a2, 0x20a2,
-       0x20a2, 0x60c3, 0x0014, 0x1078, 0x6c2d, 0x0d7f, 0x007c, 0x20a1,
-       0x020b, 0x1078, 0x65f8, 0x20a3, 0x0210, 0x20a3, 0x0014, 0x20a3,
-       0x0000, 0x20a3, 0x0100, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x20a3,
-       0x0000, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x20a3,
-       0x0000, 0x20a3, 0x0000, 0x60c3, 0x0014, 0x1078, 0x6c2d, 0x007c,
-       0x20a1, 0x020b, 0x1078, 0x65f8, 0x20a3, 0x0200, 0x0078, 0x62fe,
-       0x20a1, 0x020b, 0x1078, 0x65f8, 0x20a3, 0x0100, 0x20a3, 0x0000,
-       0x20a3, 0x0003, 0x20a3, 0x2a00, 0x60c3, 0x0008, 0x1078, 0x6c2d,
-       0x007c, 0x20e1, 0x9080, 0x20e1, 0x4000, 0x20a1, 0x020b, 0x1078,
-       0x65f8, 0x20a3, 0x0100, 0x20a3, 0x0000, 0x20a3, 0x000b, 0x20a3,
-       0x0000, 0x60c3, 0x0008, 0x1078, 0x6c2d, 0x007c, 0x027e, 0x037e,
-       0x047e, 0x2019, 0x3200, 0x2021, 0x0800, 0x0078, 0x656e, 0x027e,
-       0x037e, 0x047e, 0x2019, 0x2200, 0x2021, 0x0100, 0x20e1, 0x9080,
-       0x20e1, 0x4000, 0x7818, 0xa080, 0x0028, 0x2014, 0xa286, 0x007e,
-       0x00c0, 0x6581, 0xa385, 0x00ff, 0x20a2, 0x20a3, 0xfffe, 0x0078,
-       0x65b6, 0xa286, 0x007f, 0x00c0, 0x658d, 0x0d7e, 0xa385, 0x00ff,
-       0x20a2, 0x20a3, 0xfffd, 0x0078, 0x65a4, 0xd2bc, 0x0040, 0x65ac,
-       0xa286, 0x0080, 0x0d7e, 0x00c0, 0x659c, 0xa385, 0x00ff, 0x20a2,
-       0x20a3, 0xfffc, 0x0078, 0x65a4, 0xa2e8, 0xa434, 0x2d6c, 0x6810,
-       0xa305, 0x20a2, 0x6814, 0x20a2, 0x2069, 0xa31a, 0x2da6, 0x8d68,
-       0x2da6, 0x0d7f, 0x0078, 0x65ba, 0x0d7e, 0xa2e8, 0xa434, 0x2d6c,
-       0x6810, 0xa305, 0x20a2, 0x6814, 0x20a2, 0x0d7f, 0x20a3, 0x0000,
-       0x6230, 0x22a2, 0xa485, 0x0029, 0x20a2, 0x047f, 0x037f, 0x20a3,
-       0x0000, 0x1078, 0x6c1c, 0x22a2, 0x20a3, 0x0000, 0x2fa2, 0x20a3,
-       0xffff, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x027f, 0x007c, 0x027e,
-       0x20e1, 0x9080, 0x20e1, 0x4000, 0x20a3, 0x02ff, 0x2011, 0xfffc,
-       0x22a2, 0x0d7e, 0x2069, 0xa31a, 0x2da6, 0x8d68, 0x2da6, 0x0d7f,
-       0x20a3, 0x2029, 0x20a3, 0x0000, 0x0078, 0x65c1, 0x20a3, 0x0100,
-       0x20a3, 0x0000, 0x20a3, 0xfc02, 0x20a3, 0x0000, 0x007c, 0x027e,
-       0x037e, 0x047e, 0x2019, 0x3300, 0x2021, 0x0800, 0x0078, 0x65ff,
-       0x027e, 0x037e, 0x047e, 0x2019, 0x2300, 0x2021, 0x0100, 0x20e1,
-       0x9080, 0x20e1, 0x4000, 0x7818, 0xa080, 0x0028, 0x2004, 0xa092,
-       0x007e, 0x0048, 0x661c, 0x0d7e, 0xa0e8, 0xa434, 0x2d6c, 0x6810,
-       0xa305, 0x20a2, 0x6814, 0x20a2, 0x2069, 0xa31a, 0x2da6, 0x8d68,
-       0x2da6, 0x0d7f, 0x0078, 0x662a, 0x0d7e, 0xa0e8, 0xa434, 0x2d6c,
-       0x6810, 0xa305, 0x20a2, 0x6814, 0x20a2, 0x0d7f, 0x20a3, 0x0000,
-       0x6230, 0x22a2, 0xa485, 0x0098, 0x20a2, 0x20a3, 0x0000, 0x047f,
-       0x037f, 0x1078, 0x6c1c, 0x22a2, 0x20a3, 0x0000, 0x7a08, 0x22a2,
-       0x2fa2, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x027f, 0x007c, 0x0c7e,
-       0x0f7e, 0x6004, 0xa08a, 0x0085, 0x1048, 0x1328, 0xa08a, 0x008c,
-       0x10c8, 0x1328, 0x6118, 0x2178, 0x79a0, 0xd1bc, 0x0040, 0x665d,
-       0x7900, 0xd1f4, 0x0040, 0x6659, 0x7914, 0xa18c, 0x00ff, 0x0078,
-       0x6662, 0x2009, 0x0000, 0x0078, 0x6662, 0xa1f8, 0x293f, 0x2f0c,
-       0xa18c, 0x00ff, 0x2c78, 0x2061, 0x0100, 0x619a, 0xa082, 0x0085,
-       0x1079, 0x666d, 0x0f7f, 0x0c7f, 0x007c, 0x6676, 0x6681, 0x669c,
-       0x6674, 0x6674, 0x6674, 0x6676, 0x1078, 0x1328, 0x147e, 0x20a1,
-       0x020b, 0x1078, 0x66af, 0x60c3, 0x0000, 0x1078, 0x6c2d, 0x147f,
-       0x007c, 0x147e, 0x20a1, 0x020b, 0x1078, 0x66e3, 0x20a3, 0x0000,
-       0x20a3, 0x0000, 0x7808, 0x20a2, 0x7810, 0x20a2, 0x20a3, 0x0000,
-       0x20a3, 0xffff, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x60c3, 0x000c,
-       0x1078, 0x6c2d, 0x147f, 0x007c, 0x147e, 0x20a1, 0x020b, 0x1078,
-       0x6724, 0x20a3, 0x0003, 0x20a3, 0x0300, 0x20a3, 0x0000, 0x20a3,
-       0x0000, 0x60c3, 0x0004, 0x1078, 0x6c2d, 0x147f, 0x007c, 0x027e,
-       0x20e1, 0x9080, 0x20e1, 0x4000, 0x7818, 0xa080, 0x0028, 0x2004,
-       0xa092, 0x007e, 0x0048, 0x66ce, 0x0d7e, 0xa0e8, 0xa434, 0x2d6c,
-       0x6810, 0xa085, 0x8100, 0x20a2, 0x6814, 0x20a2, 0x2069, 0xa31a,
-       0x2da6, 0x8d68, 0x2da6, 0x0d7f, 0x0078, 0x66dd, 0x0d7e, 0xa0e8,
-       0xa434, 0x2d6c, 0x6810, 0xa085, 0x8100, 0x20a2, 0x6814, 0x20a2,
-       0x0d7f, 0x20a3, 0x0000, 0x6230, 0x22a2, 0x20a3, 0x0009, 0x20a3,
-       0x0000, 0x0078, 0x65c1, 0x027e, 0x20e1, 0x9080, 0x20e1, 0x4000,
-       0x7818, 0xa080, 0x0028, 0x2004, 0xa092, 0x007e, 0x0048, 0x6702,
-       0x0d7e, 0xa0e8, 0xa434, 0x2d6c, 0x6810, 0xa085, 0x8400, 0x20a2,
-       0x6814, 0x20a2, 0x2069, 0xa31a, 0x2da6, 0x8d68, 0x2da6, 0x0d7f,
-       0x0078, 0x6711, 0x0d7e, 0xa0e8, 0xa434, 0x2d6c, 0x6810, 0xa085,
-       0x8400, 0x20a2, 0x6814, 0x20a2, 0x0d7f, 0x20a3, 0x0000, 0x6230,
-       0x22a2, 0x20a3, 0x0099, 0x20a3, 0x0000, 0x1078, 0x6c1c, 0x22a2,
-       0x20a3, 0x0000, 0x7a08, 0x22a2, 0x7a10, 0x22a2, 0x20a3, 0x0000,
-       0x20a3, 0x0000, 0x027f, 0x007c, 0x027e, 0x20e1, 0x9080, 0x20e1,
-       0x4000, 0x7818, 0xa080, 0x0028, 0x2004, 0xa092, 0x007e, 0x0048,
-       0x6743, 0x0d7e, 0xa0e8, 0xa434, 0x2d6c, 0x6810, 0xa085, 0x8500,
-       0x20a2, 0x6814, 0x20a2, 0x2069, 0xa31a, 0x2da6, 0x8d68, 0x2da6,
-       0x0d7f, 0x0078, 0x6752, 0x0d7e, 0xa0e8, 0xa434, 0x2d6c, 0x6810,
-       0xa085, 0x8500, 0x20a2, 0x6814, 0x20a2, 0x0d7f, 0x20a3, 0x0000,
-       0x6230, 0x22a2, 0x20a3, 0x0099, 0x20a3, 0x0000, 0x0078, 0x6715,
-       0x0c7e, 0x0f7e, 0x2c78, 0x7804, 0xa08a, 0x0040, 0x1048, 0x1328,
-       0xa08a, 0x0053, 0x10c8, 0x1328, 0x7918, 0x2160, 0x61a0, 0xd1bc,
-       0x0040, 0x6777, 0x6100, 0xd1f4, 0x0040, 0x6773, 0x6114, 0xa18c,
-       0x00ff, 0x0078, 0x677c, 0x2009, 0x0000, 0x0078, 0x677c, 0xa1e0,
-       0x293f, 0x2c0c, 0xa18c, 0x00ff, 0x2061, 0x0100, 0x619a, 0xa082,
-       0x0040, 0x1079, 0x6786, 0x0f7f, 0x0c7f, 0x007c, 0x679b, 0x68a9,
-       0x684a, 0x6a59, 0x6799, 0x6799, 0x6799, 0x6799, 0x6799, 0x6799,
-       0x6799, 0x6f5e, 0x6f6f, 0x6f80, 0x6f91, 0x6799, 0x748e, 0x6799,
-       0x6f4d, 0x1078, 0x1328, 0x0d7e, 0x157e, 0x147e, 0x780b, 0xffff,
-       0x20a1, 0x020b, 0x1078, 0x6806, 0x7910, 0x2168, 0x6948, 0x7922,
-       0x21a2, 0xa016, 0x22a2, 0x22a2, 0x22a2, 0x694c, 0xa184, 0x000f,
-       0x00c0, 0x67b6, 0x2001, 0x0005, 0x0078, 0x67c0, 0xd184, 0x0040,
-       0x67bd, 0x2001, 0x0004, 0x0078, 0x67c0, 0xa084, 0x0006, 0x8004,
-       0x017e, 0x2008, 0x7830, 0xa084, 0x00ff, 0x8007, 0xa105, 0x017f,
-       0x20a2, 0xd1ac, 0x0040, 0x67d0, 0x20a3, 0x0002, 0x0078, 0x67dc,
-       0xd1b4, 0x0040, 0x67d7, 0x20a3, 0x0001, 0x0078, 0x67dc, 0x20a3,
-       0x0000, 0x2230, 0x0078, 0x67de, 0x6a80, 0x6e7c, 0x20a9, 0x0008,
-       0xad80, 0x0017, 0x200c, 0x810f, 0x21a2, 0x8000, 0x00f0, 0x67e2,
-       0x22a2, 0x26a2, 0x60c3, 0x0020, 0x20e1, 0x9080, 0x6014, 0xa084,
-       0x0004, 0xa085, 0x0009, 0x6016, 0x2001, 0xa5c7, 0x2003, 0x07d0,
-       0x2001, 0xa5c6, 0x2003, 0x0009, 0x2001, 0xa5cc, 0x2003, 0x0002,
-       0x1078, 0x157e, 0x147f, 0x157f, 0x0d7f, 0x007c, 0x20e1, 0x9080,
-       0x20e1, 0x4000, 0x7a18, 0xa280, 0x0023, 0x2014, 0x8210, 0xa294,
-       0x00ff, 0x2202, 0x8217, 0x7818, 0xa080, 0x0028, 0x2004, 0xd0bc,
-       0x0040, 0x682c, 0x0d7e, 0xa0e8, 0xa434, 0x2d6c, 0x6810, 0xa085,
-       0x0600, 0x20a2, 0x6814, 0x20a2, 0x2069, 0xa31a, 0x2da6, 0x8d68,
-       0x2da6, 0x0d7f, 0x0078, 0x683b, 0x0d7e, 0xa0e8, 0xa434, 0x2d6c,
-       0x6810, 0xa085, 0x0600, 0x20a2, 0x6814, 0x20a2, 0x0d7f, 0x20a3,
-       0x0000, 0x6130, 0x21a2, 0x20a3, 0x0829, 0x20a3, 0x0000, 0x22a2,
-       0x20a3, 0x0000, 0x2fa2, 0x20a3, 0xffff, 0x20a3, 0x0000, 0x20a3,
-       0x0000, 0x007c, 0x0d7e, 0x157e, 0x137e, 0x147e, 0x20a1, 0x020b,
-       0x1078, 0x686a, 0x7810, 0x2068, 0x6860, 0x20a2, 0x685c, 0x20a2,
-       0x6880, 0x20a2, 0x687c, 0x20a2, 0xa006, 0x20a2, 0x20a2, 0x20a2,
-       0x20a2, 0x60c3, 0x000c, 0x1078, 0x6c2d, 0x147f, 0x137f, 0x157f,
-       0x0d7f, 0x007c, 0x027e, 0x20e1, 0x9080, 0x20e1, 0x4000, 0x7818,
-       0xa080, 0x0028, 0x2004, 0xd0bc, 0x0040, 0x6888, 0x0d7e, 0xa0e8,
-       0xa434, 0x2d6c, 0x6810, 0xa085, 0x0500, 0x20a2, 0x6814, 0x20a2,
-       0x2069, 0xa31a, 0x2da6, 0x8d68, 0x2da6, 0x0d7f, 0x0078, 0x6897,
-       0x0d7e, 0xa0e8, 0xa434, 0x2d6c, 0x6810, 0xa085, 0x0500, 0x20a2,
-       0x6814, 0x20a2, 0x0d7f, 0x20a3, 0x0000, 0x6230, 0x22a2, 0x20a3,
-       0x0889, 0x20a3, 0x0000, 0x1078, 0x6c1c, 0x22a2, 0x20a3, 0x0000,
-       0x7a08, 0x22a2, 0x2fa2, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x027f,
-       0x007c, 0x0d7e, 0x157e, 0x137e, 0x147e, 0x7810, 0xa06d, 0x1078,
-       0x488f, 0x0040, 0x68bd, 0x684c, 0xa084, 0x2020, 0xa086, 0x2020,
-       0x00c0, 0x68bd, 0x7824, 0xc0cd, 0x7826, 0x20a1, 0x020b, 0x1078,
-       0x6a12, 0xa016, 0x22a2, 0x22a2, 0x22a2, 0x22a2, 0x22a2, 0x7810,
-       0xa084, 0xf000, 0x00c0, 0x68d4, 0x7810, 0xa084, 0x0700, 0x8007,
-       0x1079, 0x68dc, 0x0078, 0x68d7, 0xa006, 0x1079, 0x68dc, 0x147f,
-       0x137f, 0x157f, 0x0d7f, 0x007c, 0x68e6, 0x697e, 0x6989, 0x69b3,
-       0x69c7, 0x69e3, 0x69ee, 0x68e4, 0x1078, 0x1328, 0x017e, 0x037e,
-       0x694c, 0xa18c, 0x0003, 0x0040, 0x68f1, 0xa186, 0x0003, 0x00c0,
-       0x6900, 0x6b78, 0x7824, 0xd0cc, 0x0040, 0x68f7, 0xc3e5, 0x23a2,
-       0x6868, 0x20a2, 0x6864, 0x20a2, 0x037f, 0x017f, 0x0078, 0x69be,
-       0xa186, 0x0001, 0x10c0, 0x1328, 0x6b78, 0x7824, 0xd0cc, 0x0040,
-       0x690a, 0xc3e5, 0x23a2, 0x6868, 0x20a2, 0x6864, 0x20a2, 0x22a2,
-       0x6874, 0x20a2, 0x22a2, 0x687c, 0x20a2, 0x2009, 0x0018, 0xa384,
-       0x0300, 0x0040, 0x6978, 0xd3c4, 0x0040, 0x6920, 0x687c, 0xa108,
-       0xd3cc, 0x0040, 0x6925, 0x6874, 0xa108, 0x157e, 0x20a9, 0x000d,
-       0xad80, 0x0020, 0x201c, 0x831f, 0x23a2, 0x8000, 0x00f0, 0x692a,
-       0x157f, 0x22a2, 0x22a2, 0x22a2, 0xa184, 0x0003, 0x0040, 0x6978,
-       0x20a1, 0x020b, 0x20e1, 0x9080, 0x20e1, 0x4000, 0x007e, 0x7818,
-       0xa080, 0x0028, 0x2004, 0xd0bc, 0x0040, 0x6958, 0x0d7e, 0xa0e8,
-       0xa434, 0x2d6c, 0x6810, 0xa085, 0x0700, 0x20a2, 0x6814, 0x20a2,
-       0x2069, 0xa31a, 0x2da6, 0x8d68, 0x2da6, 0x0d7f, 0x0078, 0x6967,
-       0x0d7e, 0xa0e8, 0xa434, 0x2d6c, 0x6810, 0xa085, 0x0700, 0x20a2,
-       0x6814, 0x20a2, 0x0d7f, 0x20a3, 0x0000, 0x6230, 0x22a2, 0x007f,
-       0x7b24, 0xd3cc, 0x0040, 0x6970, 0x20a3, 0x0889, 0x0078, 0x6972,
-       0x20a3, 0x0898, 0x20a2, 0x1078, 0x6c1c, 0x22a2, 0x20a3, 0x0000,
-       0x61c2, 0x037f, 0x017f, 0x1078, 0x6c2d, 0x007c, 0x2011, 0x0008,
-       0x7824, 0xd0cc, 0x0040, 0x6985, 0xc2e5, 0x22a2, 0xa016, 0x0078,
-       0x69bc, 0x2011, 0x0302, 0x7824, 0xd0cc, 0x0040, 0x6990, 0xc2e5,
-       0x22a2, 0xa016, 0x22a2, 0x22a2, 0x22a2, 0x20a3, 0x0012, 0x22a2,
-       0x20a3, 0x0008, 0x22a2, 0x22a2, 0x22a2, 0x22a2, 0x20a3, 0x7000,
-       0x20a3, 0x0500, 0x22a2, 0x20a3, 0x000a, 0x22a2, 0x22a2, 0x20a3,
-       0x2500, 0x22a2, 0x22a2, 0x22a2, 0x22a2, 0x22a2, 0x60c3, 0x0032,
-       0x1078, 0x6c2d, 0x007c, 0x2011, 0x0028, 0x7824, 0xd0cc, 0x0040,
-       0x69ba, 0xc2e5, 0x22a2, 0xa016, 0x22a2, 0x22a2, 0x22a2, 0x22a2,
-       0x22a2, 0x22a2, 0x60c3, 0x0018, 0x1078, 0x6c2d, 0x007c, 0x2011,
-       0x0100, 0x7824, 0xd0cc, 0x0040, 0x69ce, 0xc2e5, 0x22a2, 0xa016,
-       0x22a2, 0x22a2, 0x22a2, 0x22a2, 0x22a2, 0x20a3, 0x0008, 0x22a2,
-       0x7834, 0xa084, 0x00ff, 0x20a2, 0x22a2, 0x22a2, 0x60c3, 0x0020,
-       0x1078, 0x6c2d, 0x007c, 0x2011, 0x0008, 0x7824, 0xd0cc, 0x0040,
-       0x69ea, 0xc2e5, 0x22a2, 0xa016, 0x0078, 0x69bc, 0x037e, 0x7b10,
-       0xa384, 0xff00, 0x7812, 0xa384, 0x00ff, 0x8001, 0x00c0, 0x6a01,
-       0x7824, 0xd0cc, 0x0040, 0x69fd, 0xc2e5, 0x22a2, 0x037f, 0x0078,
-       0x69bc, 0x047e, 0x2021, 0x0800, 0x007e, 0x7824, 0xd0cc, 0x007f,
-       0x0040, 0x6a0b, 0xc4e5, 0x24a2, 0x047f, 0x22a2, 0x20a2, 0x037f,
-       0x0078, 0x69be, 0x027e, 0x20e1, 0x9080, 0x20e1, 0x4000, 0x7818,
-       0xa080, 0x0028, 0x2004, 0xd0bc, 0x0040, 0x6a30, 0x0d7e, 0xa0e8,
-       0xa434, 0x2d6c, 0x6810, 0xa085, 0x0700, 0x20a2, 0x6814, 0x20a2,
-       0x2069, 0xa31a, 0x2da6, 0x8d68, 0x2da6, 0x0d7f, 0x0078, 0x6a3f,
-       0x0d7e, 0xa0e8, 0xa434, 0x2d6c, 0x6810, 0xa085, 0x0700, 0x20a2,
-       0x6814, 0x20a2, 0x0d7f, 0x20a3, 0x0000, 0x6230, 0x22a2, 0x7824,
-       0xd0cc, 0x0040, 0x6a47, 0x20a3, 0x0889, 0x0078, 0x6a49, 0x20a3,
-       0x0898, 0x20a3, 0x0000, 0x1078, 0x6c1c, 0x22a2, 0x20a3, 0x0000,
-       0x7a08, 0x22a2, 0x2fa2, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x027f,
-       0x007c, 0x0d7e, 0x157e, 0x137e, 0x147e, 0x017e, 0x037e, 0x7810,
-       0xa084, 0x0700, 0x8007, 0x1079, 0x6a6c, 0x037f, 0x017f, 0x147f,
-       0x137f, 0x157f, 0x0d7f, 0x007c, 0x6a74, 0x6a74, 0x6a76, 0x6a74,
-       0x6a74, 0x6a74, 0x6a9b, 0x6a74, 0x1078, 0x1328, 0x7910, 0xa18c,
-       0xf8ff, 0xa18d, 0x0600, 0x7912, 0x20a1, 0x020b, 0x2009, 0x0003,
-       0x1078, 0x6aa5, 0x0d7e, 0x2069, 0xa351, 0x6804, 0xd0bc, 0x0040,
-       0x6a90, 0x682c, 0xa084, 0x00ff, 0x8007, 0x20a2, 0x0078, 0x6a92,
-       0x20a3, 0x3f00, 0x0d7f, 0x22a2, 0x22a2, 0x22a2, 0x60c3, 0x0001,
-       0x1078, 0x6c2d, 0x007c, 0x20a1, 0x020b, 0x2009, 0x0003, 0x1078,
-       0x6aa5, 0x20a3, 0x7f00, 0x0078, 0x6a93, 0x027e, 0x20e1, 0x9080,
-       0x20e1, 0x4000, 0x7818, 0xa080, 0x0028, 0x2004, 0xd0bc, 0x0040,
-       0x6ac3, 0x0d7e, 0xa0e8, 0xa434, 0x2d6c, 0x6810, 0xa085, 0x0100,
-       0x20a2, 0x6814, 0x20a2, 0x2069, 0xa31a, 0x2da6, 0x8d68, 0x2da6,
-       0x0d7f, 0x0078, 0x6ad2, 0x0d7e, 0xa0e8, 0xa434, 0x2d6c, 0x6810,
-       0xa085, 0x0100, 0x20a2, 0x6814, 0x20a2, 0x0d7f, 0x20a3, 0x0000,
-       0x6230, 0x22a2, 0x20a3, 0x0888, 0xa18d, 0x0008, 0x21a2, 0x1078,
-       0x6c1c, 0x22a2, 0x20a3, 0x0000, 0x7a08, 0x22a2, 0x2fa2, 0x20a3,
-       0x0000, 0x20a3, 0x0000, 0x027f, 0x007c, 0x0e7e, 0x0d7e, 0x0c7e,
-       0x057e, 0x047e, 0x037e, 0x2061, 0x0100, 0x2071, 0xa300, 0x6130,
-       0x7818, 0x2068, 0x68a0, 0x2028, 0xd0bc, 0x00c0, 0x6afc, 0x6910,
-       0x6a14, 0x6430, 0x0078, 0x6b00, 0x6910, 0x6a14, 0x7368, 0x746c,
-       0x781c, 0xa086, 0x0006, 0x0040, 0x6b5f, 0xd5bc, 0x0040, 0x6b10,
-       0xa185, 0x0100, 0x6062, 0x6266, 0x636a, 0x646e, 0x0078, 0x6b17,
-       0xa185, 0x0100, 0x6062, 0x6266, 0x606b, 0x0000, 0x646e, 0x6073,
-       0x0809, 0x6077, 0x0008, 0x688c, 0x8000, 0xa084, 0x00ff, 0x688e,
-       0x8007, 0x607a, 0x607f, 0x0000, 0x2f00, 0x6082, 0x7808, 0x6086,
-       0x7810, 0x2070, 0x7014, 0x608a, 0x7010, 0x608e, 0x700c, 0x60c6,
-       0x7008, 0x60ca, 0x686c, 0x60ce, 0x60ab, 0x0036, 0x60af, 0x95d5,
-       0x60d7, 0x0000, 0xa582, 0x0080, 0x0048, 0x6b49, 0x6a00, 0xd2f4,
-       0x0040, 0x6b47, 0x6a14, 0xa294, 0x00ff, 0x0078, 0x6b49, 0x2011,
-       0x0000, 0x629e, 0x6017, 0x0016, 0x2009, 0x07d0, 0x60c4, 0xa084,
-       0xfff0, 0xa005, 0x0040, 0x6b56, 0x2009, 0x1b58, 0x1078, 0x595f,
-       0x037f, 0x047f, 0x057f, 0x0c7f, 0x0d7f, 0x0e7f, 0x007c, 0x7810,
-       0x2070, 0x704c, 0xa084, 0x0003, 0xa086, 0x0002, 0x0040, 0x6bb7,
-       0xd5bc, 0x0040, 0x6b73, 0xa185, 0x0100, 0x6062, 0x6266, 0x636a,
-       0x646e, 0x0078, 0x6b7a, 0xa185, 0x0100, 0x6062, 0x6266, 0x606b,
-       0x0000, 0x646e, 0x6073, 0x0880, 0x6077, 0x0008, 0x688c, 0x8000,
-       0xa084, 0x00ff, 0x688e, 0x8007, 0x607a, 0x607f, 0x0000, 0x2f00,
-       0x6086, 0x7808, 0x6082, 0x7060, 0x608a, 0x705c, 0x608e, 0x7080,
-       0x60c6, 0x707c, 0x60ca, 0x707c, 0x792c, 0xa108, 0x792e, 0x7080,
-       0x7928, 0xa109, 0x792a, 0x686c, 0x60ce, 0x60ab, 0x0036, 0x60af,
-       0x95d5, 0x60d7, 0x0000, 0xa582, 0x0080, 0x0048, 0x6bb2, 0x6a00,
-       0xd2f4, 0x0040, 0x6bb0, 0x6a14, 0xa294, 0x00ff, 0x0078, 0x6bb2,
-       0x2011, 0x0000, 0x629e, 0x6017, 0x0012, 0x0078, 0x6b4c, 0xd5bc,
-       0x0040, 0x6bc2, 0xa185, 0x0700, 0x6062, 0x6266, 0x636a, 0x646e,
-       0x0078, 0x6bc9, 0xa185, 0x0700, 0x6062, 0x6266, 0x606b, 0x0000,
-       0x646e, 0x1078, 0x488f, 0x0040, 0x6bdf, 0x0d7e, 0x7810, 0xa06d,
-       0x684c, 0x0d7f, 0xa084, 0x2020, 0xa086, 0x2020, 0x00c0, 0x6bdf,
-       0x7824, 0xc0cd, 0x7826, 0x6073, 0x0889, 0x0078, 0x6be1, 0x6073,
-       0x0898, 0x6077, 0x0000, 0x688c, 0x8000, 0xa084, 0x00ff, 0x688e,
-       0x8007, 0x607a, 0x607f, 0x0000, 0x2f00, 0x6086, 0x7808, 0x6082,
-       0x7014, 0x608a, 0x7010, 0x608e, 0x700c, 0x60c6, 0x7008, 0x60ca,
-       0x686c, 0x60ce, 0x60ab, 0x0036, 0x60af, 0x95d5, 0x60d7, 0x0000,
-       0xa582, 0x0080, 0x0048, 0x6c0f, 0x6a00, 0xd2f4, 0x0040, 0x6c0d,
-       0x6a14, 0xa294, 0x00ff, 0x0078, 0x6c0f, 0x2011, 0x0000, 0x629e,
-       0x7824, 0xd0cc, 0x0040, 0x6c18, 0x6017, 0x0016, 0x0078, 0x6b4c,
-       0x6017, 0x0012, 0x0078, 0x6b4c, 0x7a18, 0xa280, 0x0023, 0x2014,
-       0x8210, 0xa294, 0x00ff, 0x2202, 0x8217, 0x007c, 0x0d7e, 0x2069,
-       0xa5ab, 0x6843, 0x0001, 0x0d7f, 0x007c, 0x20e1, 0x9080, 0x60a3,
-       0x0056, 0x60a7, 0x9575, 0x1078, 0x6c38, 0x1078, 0x594f, 0x007c,
-       0x007e, 0x6014, 0xa084, 0x0004, 0xa085, 0x0009, 0x6016, 0x007f,
-       0x007c, 0x007e, 0x0c7e, 0x2061, 0x0100, 0x6014, 0xa084, 0x0004,
-       0xa085, 0x0008, 0x6016, 0x0c7f, 0x007f, 0x007c, 0x0c7e, 0x0d7e,
-       0x017e, 0x027e, 0x2061, 0x0100, 0x2069, 0x0140, 0x6904, 0xa194,
-       0x4000, 0x0040, 0x6c89, 0x1078, 0x6c41, 0x6803, 0x1000, 0x6803,
-       0x0000, 0x0c7e, 0x2061, 0xa5ab, 0x6128, 0xa192, 0x00c8, 0x00c8,
-       0x6c76, 0x8108, 0x612a, 0x6124, 0x0c7f, 0x81ff, 0x0040, 0x6c84,
-       0x1078, 0x594f, 0x1078, 0x6c38, 0x0078, 0x6c84, 0x6124, 0xa1e5,
-       0x0000, 0x0040, 0x6c81, 0x1078, 0xa241, 0x2009, 0x0014, 0x1078,
-       0x756c, 0x0c7f, 0x0078, 0x6c84, 0x027f, 0x017f, 0x0d7f, 0x0c7f,
-       0x007c, 0x2001, 0xa5c7, 0x2004, 0xa005, 0x00c0, 0x6c84, 0x0c7e,
-       0x2061, 0xa5ab, 0x6128, 0xa192, 0x0003, 0x00c8, 0x6c76, 0x8108,
-       0x612a, 0x0c7f, 0x1078, 0x594f, 0x1078, 0x4171, 0x0078, 0x6c84,
-       0x0c7e, 0x0d7e, 0x0e7e, 0x017e, 0x027e, 0x1078, 0x5967, 0x2071,
-       0xa5ab, 0x713c, 0x81ff, 0x0040, 0x6cca, 0x2061, 0x0100, 0x2069,
-       0x0140, 0x6904, 0xa194, 0x4000, 0x0040, 0x6cd0, 0x6803, 0x1000,
-       0x6803, 0x0000, 0x037e, 0x2019, 0x0001, 0x1078, 0x6e6c, 0x037f,
-       0x713c, 0x2160, 0x1078, 0xa241, 0x2009, 0x004a, 0x1078, 0x756c,
-       0x0078, 0x6cca, 0x027f, 0x017f, 0x0e7f, 0x0d7f, 0x0c7f, 0x007c,
-       0x0078, 0x6cba, 0x0e7e, 0x0d7e, 0x0c7e, 0x067e, 0x057e, 0x047e,
-       0x007e, 0x127e, 0x2091, 0x8000, 0x6018, 0x2068, 0x6ca0, 0x2071,
-       0xa5ab, 0x7018, 0x2068, 0x8dff, 0x0040, 0x6cfc, 0x68a0, 0xa406,
-       0x0040, 0x6cee, 0x6854, 0x2068, 0x0078, 0x6ce3, 0x6010, 0x2060,
-       0x643c, 0x6540, 0x6e48, 0x2d60, 0x1078, 0x466a, 0x0040, 0x6cfc,
-       0x1078, 0x7045, 0xa085, 0x0001, 0x127f, 0x007f, 0x047f, 0x057f,
-       0x067f, 0x0c7f, 0x0d7f, 0x0e7f, 0x007c, 0x20a1, 0x020b, 0x1078,
-       0x6567, 0x20a3, 0x1200, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x781c,
-       0xa086, 0x0004, 0x00c0, 0x6d17, 0x6098, 0x0078, 0x6d18, 0x6030,
-       0x20a2, 0x7834, 0x20a2, 0x7838, 0x20a2, 0x20a9, 0x0010, 0xa006,
-       0x20a2, 0x00f0, 0x6d20, 0x20a2, 0x20a2, 0x60c3, 0x002c, 0x1078,
-       0x6c2d, 0x007c, 0x157e, 0x147e, 0x20a1, 0x020b, 0x1078, 0x6567,
-       0x20a3, 0x0f00, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x7808, 0x20a2,
-       0x60c3, 0x0008, 0x1078, 0x6c2d, 0x147f, 0x157f, 0x007c, 0x157e,
-       0x147e, 0x20a1, 0x020b, 0x1078, 0x65f8, 0x20a3, 0x0200, 0x20a3,
-       0x0000, 0x20a9, 0x0006, 0x2011, 0xa340, 0x2019, 0xa341, 0x23a6,
-       0x22a6, 0xa398, 0x0002, 0xa290, 0x0002, 0x00f0, 0x6d4f, 0x20a3,
-       0x0000, 0x20a3, 0x0000, 0x60c3, 0x001c, 0x1078, 0x6c2d, 0x147f,
-       0x157f, 0x007c, 0x157e, 0x147e, 0x017e, 0x027e, 0x20a1, 0x020b,
-       0x1078, 0x65cf, 0x1078, 0x65e6, 0x7810, 0xa080, 0x0000, 0x2004,
-       0xa080, 0x0015, 0x2098, 0x7808, 0xa088, 0x0002, 0x21a8, 0x53a6,
-       0xa080, 0x0004, 0x8003, 0x60c2, 0x1078, 0x6c2d, 0x027f, 0x017f,
-       0x147f, 0x157f, 0x007c, 0x157e, 0x147e, 0x20a1, 0x020b, 0x1078,
-       0x6567, 0x20a3, 0x6200, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x7808,
-       0x20a2, 0x60c3, 0x0008, 0x1078, 0x6c2d, 0x147f, 0x157f, 0x007c,
-       0x157e, 0x147e, 0x017e, 0x027e, 0x20a1, 0x020b, 0x1078, 0x6567,
-       0x7810, 0xa080, 0x0000, 0x2004, 0xa080, 0x0017, 0x2098, 0x7808,
-       0xa088, 0x0002, 0x21a8, 0x53a6, 0x8003, 0x60c2, 0x1078, 0x6c2d,
-       0x027f, 0x017f, 0x147f, 0x157f, 0x007c, 0x0e7e, 0x0c7e, 0x007e,
-       0x127e, 0x2091, 0x8000, 0x2071, 0xa5ab, 0x700c, 0x2060, 0x8cff,
-       0x0040, 0x6dd1, 0x1078, 0x8c3b, 0x00c0, 0x6dc8, 0x1078, 0x7a05,
-       0x600c, 0x007e, 0x1078, 0x753d, 0x1078, 0x7045, 0x0c7f, 0x0078,
-       0x6dbf, 0x700f, 0x0000, 0x700b, 0x0000, 0x127f, 0x007f, 0x0c7f,
-       0x0e7f, 0x007c, 0x127e, 0x157e, 0x0f7e, 0x0e7e, 0x0d7e, 0x0c7e,
-       0x027e, 0x017e, 0x007e, 0x2091, 0x8000, 0x2069, 0x0100, 0x2079,
-       0x0140, 0x2071, 0xa5ab, 0x7024, 0x2060, 0x8cff, 0x0040, 0x6e2a,
-       0x1078, 0x6c41, 0x68c3, 0x0000, 0x1078, 0x595a, 0x2009, 0x0013,
-       0x1078, 0x756c, 0x20a9, 0x01f4, 0x6824, 0xd094, 0x0040, 0x6e0d,
-       0x6827, 0x0004, 0x7804, 0xa084, 0x4000, 0x0040, 0x6e1f, 0x7803,
-       0x1000, 0x7803, 0x0000, 0x0078, 0x6e1f, 0xd084, 0x0040, 0x6e14,
-       0x6827, 0x0001, 0x0078, 0x6e16, 0x00f0, 0x6dfc, 0x7804, 0xa084,
-       0x1000, 0x0040, 0x6e1f, 0x7803, 0x0100, 0x7803, 0x0000, 0x6824,
-       0x007f, 0x017f, 0x027f, 0x0c7f, 0x0d7f, 0x0e7f, 0x0f7f, 0x157f,
-       0x127f, 0x007c, 0x2001, 0xa300, 0x2004, 0xa096, 0x0001, 0x0040,
-       0x6e62, 0xa096, 0x0004, 0x0040, 0x6e62, 0x6817, 0x0008, 0x68c3,
-       0x0000, 0x2011, 0x4129, 0x1078, 0x58d4, 0x20a9, 0x01f4, 0x6824,
-       0xd094, 0x0040, 0x6e50, 0x6827, 0x0004, 0x7804, 0xa084, 0x4000,
-       0x0040, 0x6e62, 0x7803, 0x1000, 0x7803, 0x0000, 0x0078, 0x6e62,
-       0xd084, 0x0040, 0x6e57, 0x6827, 0x0001, 0x0078, 0x6e59, 0x00f0,
-       0x6e3f, 0x7804, 0xa084, 0x1000, 0x0040, 0x6e62, 0x7803, 0x0100,
-       0x7803, 0x0000, 0x007f, 0x017f, 0x027f, 0x0c7f, 0x0d7f, 0x0e7f,
-       0x0f7f, 0x157f, 0x127f, 0x007c, 0x127e, 0x157e, 0x0f7e, 0x0e7e,
-       0x0d7e, 0x0c7e, 0x027e, 0x017e, 0x007e, 0x2091, 0x8000, 0x2069,
-       0x0100, 0x2079, 0x0140, 0x2071, 0xa5ab, 0x703c, 0x2060, 0x8cff,
-       0x0040, 0x6ee8, 0x6817, 0x0010, 0x2009, 0x00fa, 0x8109, 0x00c0,
-       0x6e86, 0x68c7, 0x0000, 0x68cb, 0x0008, 0x1078, 0x5967, 0x1078,
-       0x1f31, 0x047e, 0x057e, 0x2009, 0x017f, 0x212c, 0x200b, 0x00a5,
-       0x2021, 0x0169, 0x2404, 0xa084, 0x000f, 0xa086, 0x0004, 0x00c0,
-       0x6eb7, 0x68c7, 0x0000, 0x68cb, 0x0008, 0x0e7e, 0x0f7e, 0x2079,
-       0x0020, 0x2071, 0xa602, 0x6814, 0xa084, 0x0004, 0xa085, 0x0012,
-       0x6816, 0x7803, 0x0008, 0x7003, 0x0000, 0x0f7f, 0x0e7f, 0x250a,
-       0x057f, 0x047f, 0xa39d, 0x0000, 0x00c0, 0x6ec2, 0x2009, 0x0049,
-       0x1078, 0x756c, 0x20a9, 0x03e8, 0x6824, 0xd094, 0x0040, 0x6ed5,
-       0x6827, 0x0004, 0x7804, 0xa084, 0x4000, 0x0040, 0x6ee7, 0x7803,
-       0x1000, 0x7803, 0x0000, 0x0078, 0x6ee7, 0xd08c, 0x0040, 0x6edc,
-       0x6827, 0x0002, 0x0078, 0x6ede, 0x00f0, 0x6ec4, 0x7804, 0xa084,
-       0x1000, 0x0040, 0x6ee7, 0x7803, 0x0100, 0x7803, 0x0000, 0x6824,
-       0x007f, 0x017f, 0x027f, 0x0c7f, 0x0d7f, 0x0e7f, 0x0f7f, 0x157f,
-       0x127f, 0x007c, 0x0d7e, 0x127e, 0x2091, 0x8000, 0x2069, 0xa5ab,
-       0x6a06, 0x127f, 0x0d7f, 0x007c, 0x0d7e, 0x127e, 0x2091, 0x8000,
-       0x2069, 0xa5ab, 0x6a32, 0x127f, 0x0d7f, 0x007c, 0x0f7e, 0x0e7e,
-       0x0c7e, 0x067e, 0x007e, 0x127e, 0x2071, 0xa5ab, 0x7614, 0x2660,
-       0x2678, 0x2091, 0x8000, 0x8cff, 0x0040, 0x6f46, 0x601c, 0xa206,
-       0x00c0, 0x6f41, 0x7014, 0xac36, 0x00c0, 0x6f20, 0x660c, 0x7616,
-       0x7010, 0xac36, 0x00c0, 0x6f2e, 0x2c00, 0xaf36, 0x0040, 0x6f2c,
-       0x2f00, 0x7012, 0x0078, 0x6f2e, 0x7013, 0x0000, 0x660c, 0x067e,
-       0x2c00, 0xaf06, 0x0040, 0x6f37, 0x7e0e, 0x0078, 0x6f38, 0x2678,
-       0x600f, 0x0000, 0x1078, 0x8c01, 0x1078, 0x7045, 0x0c7f, 0x0078,
-       0x6f13, 0x2c78, 0x600c, 0x2060, 0x0078, 0x6f13, 0x127f, 0x007f,
-       0x067f, 0x0c7f, 0x0e7f, 0x0f7f, 0x007c, 0x157e, 0x147e, 0x20a1,
-       0x020b, 0x1078, 0x6806, 0x7810, 0x20a2, 0xa006, 0x20a2, 0x20a2,
-       0x20a2, 0x20a2, 0x20a3, 0x1000, 0x0078, 0x6fa0, 0x157e, 0x147e,
-       0x20a1, 0x020b, 0x1078, 0x6806, 0x7810, 0x20a2, 0xa006, 0x20a2,
-       0x20a2, 0x20a2, 0x20a2, 0x20a3, 0x4000, 0x0078, 0x6fa0, 0x157e,
-       0x147e, 0x20a1, 0x020b, 0x1078, 0x6806, 0x7810, 0x20a2, 0xa006,
-       0x20a2, 0x20a2, 0x20a2, 0x20a2, 0x20a3, 0x2000, 0x0078, 0x6fa0,
-       0x157e, 0x147e, 0x20a1, 0x020b, 0x1078, 0x6806, 0x7810, 0x20a2,
-       0xa006, 0x20a2, 0x20a2, 0x20a2, 0x20a2, 0x20a3, 0x0400, 0x0078,
-       0x6fa0, 0x157e, 0x147e, 0x20a1, 0x020b, 0x1078, 0x6806, 0x7810,
-       0x20a2, 0xa006, 0x20a2, 0x20a2, 0x20a2, 0x20a2, 0x20a3, 0x0200,
-       0x1078, 0x7050, 0x60c3, 0x0020, 0x1078, 0x6c2d, 0x147f, 0x157f,
-       0x007c, 0x127e, 0x0c7e, 0x2091, 0x8000, 0x2061, 0x0100, 0x6120,
-       0xd1b4, 0x00c0, 0x6fb8, 0xd1bc, 0x00c0, 0x7002, 0x0078, 0x7042,
-       0x2009, 0x017f, 0x200b, 0x00a1, 0x157e, 0x007e, 0x0d7e, 0x2069,
-       0x0140, 0x20a9, 0x001e, 0x2009, 0x0169, 0x6804, 0xa084, 0x4000,
-       0x0040, 0x6ff9, 0x6020, 0xd0b4, 0x0040, 0x6ff9, 0x6024, 0xd094,
-       0x00c0, 0x6ff9, 0x2104, 0xa084, 0x000f, 0xa086, 0x0004, 0x00c0,
-       0x6ff9, 0x00f0, 0x6fc5, 0x027e, 0x6198, 0xa18c, 0x00ff, 0x8107,
-       0x6130, 0xa18c, 0x00ff, 0xa10d, 0x6088, 0x628c, 0x618e, 0x608b,
-       0xbc91, 0x6043, 0x0001, 0x6043, 0x0000, 0x608a, 0x628e, 0x6024,
-       0xd094, 0x00c0, 0x6ff8, 0x6a04, 0xa294, 0x4000, 0x00c0, 0x6fef,
-       0x027f, 0x0d7f, 0x007f, 0x157f, 0x2009, 0x017f, 0x200b, 0x0000,
-       0x0078, 0x7042, 0x2009, 0x017f, 0x200b, 0x00a1, 0x157e, 0x007e,
-       0x0d7e, 0x2069, 0x0140, 0x20a9, 0x001e, 0x2009, 0x0169, 0x6804,
-       0xa084, 0x4000, 0x0040, 0x703b, 0x6020, 0xd0bc, 0x0040, 0x703b,
-       0x2104, 0xa084, 0x000f, 0xa086, 0x0004, 0x00c0, 0x703b, 0x00f0,
-       0x700f, 0x027e, 0x6164, 0xa18c, 0x00ff, 0x8107, 0x6130, 0xa18c,
-       0x00ff, 0xa10d, 0x6088, 0x628c, 0x608b, 0xbc91, 0x618e, 0x6043,
-       0x0001, 0x6043, 0x0000, 0x608a, 0x628e, 0x6a04, 0xa294, 0x4000,
-       0x00c0, 0x7035, 0x027f, 0x0d7f, 0x007f, 0x157f, 0x2009, 0x017f,
-       0x200b, 0x0000, 0x0c7f, 0x127f, 0x007c, 0x0e7e, 0x2071, 0xa5ab,
-       0x7020, 0xa005, 0x0040, 0x704e, 0x8001, 0x7022, 0x0e7f, 0x007c,
-       0x20a9, 0x0008, 0x20a2, 0x00f0, 0x7052, 0x20a2, 0x20a2, 0x007c,
-       0x0f7e, 0x0e7e, 0x0d7e, 0x0c7e, 0x077e, 0x067e, 0x007e, 0x127e,
-       0x2091, 0x8000, 0x2071, 0xa5ab, 0x7614, 0x2660, 0x2678, 0x2039,
-       0x0001, 0x87ff, 0x0040, 0x70f4, 0x8cff, 0x0040, 0x70f4, 0x601c,
-       0xa086, 0x0006, 0x00c0, 0x70ef, 0x88ff, 0x0040, 0x707f, 0x2800,
-       0xac06, 0x00c0, 0x70ef, 0x2039, 0x0000, 0x0078, 0x708a, 0x6018,
-       0xa206, 0x00c0, 0x70ef, 0x85ff, 0x0040, 0x708a, 0x6020, 0xa106,
-       0x00c0, 0x70ef, 0x7024, 0xac06, 0x00c0, 0x70ba, 0x2069, 0x0100,
-       0x68c0, 0xa005, 0x0040, 0x70b5, 0x1078, 0x595a, 0x6817, 0x0008,
-       0x68c3, 0x0000, 0x1078, 0x7188, 0x7027, 0x0000, 0x037e, 0x2069,
-       0x0140, 0x6b04, 0xa384, 0x1000, 0x0040, 0x70aa, 0x6803, 0x0100,
-       0x6803, 0x0000, 0x2069, 0x0100, 0x6824, 0xd084, 0x0040, 0x70b2,
-       0x6827, 0x0001, 0x037f, 0x0078, 0x70ba, 0x6003, 0x0009, 0x630a,
-       0x0078, 0x70ef, 0x7014, 0xac36, 0x00c0, 0x70c0, 0x660c, 0x7616,
-       0x7010, 0xac36, 0x00c0, 0x70ce, 0x2c00, 0xaf36, 0x0040, 0x70cc,
-       0x2f00, 0x7012, 0x0078, 0x70ce, 0x7013, 0x0000, 0x660c, 0x067e,
-       0x2c00, 0xaf06, 0x0040, 0x70d7, 0x7e0e, 0x0078, 0x70d8, 0x2678,
-       0x89ff, 0x00c0, 0x70e7, 0x600f, 0x0000, 0x6010, 0x2068, 0x1078,
-       0x8a44, 0x0040, 0x70e5, 0x1078, 0x9e70, 0x1078, 0x8c01, 0x1078,
-       0x7045, 0x88ff, 0x00c0, 0x70fe, 0x0c7f, 0x0078, 0x7069, 0x2c78,
-       0x600c, 0x2060, 0x0078, 0x7069, 0xa006, 0x127f, 0x007f, 0x067f,
-       0x077f, 0x0c7f, 0x0d7f, 0x0e7f, 0x0f7f, 0x007c, 0x6017, 0x0000,
-       0x0c7f, 0xa8c5, 0x0001, 0x0078, 0x70f5, 0x0f7e, 0x0e7e, 0x0d7e,
-       0x0c7e, 0x067e, 0x027e, 0x007e, 0x127e, 0x2091, 0x8000, 0x2071,
-       0xa5ab, 0x7638, 0x2660, 0x2678, 0x8cff, 0x0040, 0x7177, 0x601c,
-       0xa086, 0x0006, 0x00c0, 0x7172, 0x87ff, 0x0040, 0x7125, 0x2700,
-       0xac06, 0x00c0, 0x7172, 0x0078, 0x7130, 0x6018, 0xa206, 0x00c0,
-       0x7172, 0x85ff, 0x0040, 0x7130, 0x6020, 0xa106, 0x00c0, 0x7172,
-       0x703c, 0xac06, 0x00c0, 0x7142, 0x037e, 0x2019, 0x0001, 0x1078,
-       0x6e6c, 0x7033, 0x0000, 0x703f, 0x0000, 0x7043, 0x0000, 0x7047,
-       0x0000, 0x037f, 0x7038, 0xac36, 0x00c0, 0x7148, 0x660c, 0x763a,
-       0x7034, 0xac36, 0x00c0, 0x7156, 0x2c00, 0xaf36, 0x0040, 0x7154,
-       0x2f00, 0x7036, 0x0078, 0x7156, 0x7037, 0x0000, 0x660c, 0x067e,
-       0x2c00, 0xaf06, 0x0040, 0x715f, 0x7e0e, 0x0078, 0x7160, 0x2678,
-       0x600f, 0x0000, 0x6010, 0x2068, 0x1078, 0x8a44, 0x0040, 0x716a,
-       0x1078, 0x9e70, 0x1078, 0x8c01, 0x87ff, 0x00c0, 0x7181, 0x0c7f,
-       0x0078, 0x7114, 0x2c78, 0x600c, 0x2060, 0x0078, 0x7114, 0xa006,
-       0x127f, 0x007f, 0x027f, 0x067f, 0x0c7f, 0x0d7f, 0x0e7f, 0x0f7f,
-       0x007c, 0x6017, 0x0000, 0x0c7f, 0xa7bd, 0x0001, 0x0078, 0x7178,
-       0x0e7e, 0x2071, 0xa5ab, 0x2001, 0xa300, 0x2004, 0xa086, 0x0002,
-       0x00c0, 0x7196, 0x7007, 0x0005, 0x0078, 0x7198, 0x7007, 0x0000,
-       0x0e7f, 0x007c, 0x0f7e, 0x0e7e, 0x0c7e, 0x067e, 0x027e, 0x007e,
-       0x127e, 0x2091, 0x8000, 0x2071, 0xa5ab, 0x2c10, 0x7638, 0x2660,
-       0x2678, 0x8cff, 0x0040, 0x71d8, 0x2200, 0xac06, 0x00c0, 0x71d3,
-       0x7038, 0xac36, 0x00c0, 0x71b6, 0x660c, 0x763a, 0x7034, 0xac36,
-       0x00c0, 0x71c4, 0x2c00, 0xaf36, 0x0040, 0x71c2, 0x2f00, 0x7036,
-       0x0078, 0x71c4, 0x7037, 0x0000, 0x660c, 0x2c00, 0xaf06, 0x0040,
-       0x71cc, 0x7e0e, 0x0078, 0x71cd, 0x2678, 0x600f, 0x0000, 0xa085,
-       0x0001, 0x0078, 0x71d8, 0x2c78, 0x600c, 0x2060, 0x0078, 0x71a9,
-       0x127f, 0x007f, 0x027f, 0x067f, 0x0c7f, 0x0e7f, 0x0f7f, 0x007c,
-       0x0f7e, 0x0e7e, 0x0d7e, 0x0c7e, 0x067e, 0x007e, 0x127e, 0x2091,
-       0x8000, 0x2071, 0xa5ab, 0x760c, 0x2660, 0x2678, 0x8cff, 0x0040,
-       0x7279, 0x6018, 0xa080, 0x0028, 0x2004, 0xa206, 0x00c0, 0x7274,
-       0x7024, 0xac06, 0x00c0, 0x721f, 0x2069, 0x0100, 0x68c0, 0xa005,
-       0x0040, 0x724d, 0x1078, 0x6c41, 0x68c3, 0x0000, 0x1078, 0x7188,
-       0x7027, 0x0000, 0x037e, 0x2069, 0x0140, 0x6b04, 0xa384, 0x1000,
-       0x0040, 0x7216, 0x6803, 0x0100, 0x6803, 0x0000, 0x2069, 0x0100,
-       0x6824, 0xd084, 0x0040, 0x721e, 0x6827, 0x0001, 0x037f, 0x700c,
-       0xac36, 0x00c0, 0x7225, 0x660c, 0x760e, 0x7008, 0xac36, 0x00c0,
-       0x7233, 0x2c00, 0xaf36, 0x0040, 0x7231, 0x2f00, 0x700a, 0x0078,
-       0x7233, 0x700b, 0x0000, 0x660c, 0x067e, 0x2c00, 0xaf06, 0x0040,
-       0x723c, 0x7e0e, 0x0078, 0x723d, 0x2678, 0x600f, 0x0000, 0x1078,
-       0x8c27, 0x00c0, 0x7251, 0x1078, 0x2839, 0x1078, 0x8c3b, 0x00c0,
-       0x726d, 0x1078, 0x7a05, 0x0078, 0x726d, 0x1078, 0x7188, 0x0078,
-       0x721f, 0x1078, 0x8c3b, 0x00c0, 0x7259, 0x1078, 0x7a05, 0x0078,
-       0x726d, 0x6010, 0x2068, 0x1078, 0x8a44, 0x0040, 0x726d, 0x601c,
-       0xa086, 0x0003, 0x00c0, 0x7281, 0x6837, 0x0103, 0x6b4a, 0x6847,
-       0x0000, 0x1078, 0x4982, 0x1078, 0x8bf4, 0x1078, 0x8c01, 0x1078,
-       0x7045, 0x0c7f, 0x0078, 0x71ee, 0x2c78, 0x600c, 0x2060, 0x0078,
-       0x71ee, 0x127f, 0x007f, 0x067f, 0x0c7f, 0x0d7f, 0x0e7f, 0x0f7f,
-       0x007c, 0x601c, 0xa086, 0x0006, 0x00c0, 0x726d, 0x1078, 0x9e70,
-       0x0078, 0x726d, 0x037e, 0x157e, 0x137e, 0x147e, 0x3908, 0xa006,
-       0xa190, 0x0020, 0x221c, 0xa39e, 0x260c, 0x00c0, 0x729b, 0x8210,
-       0x8000, 0x0078, 0x7292, 0xa005, 0x0040, 0x72a7, 0x20a9, 0x0020,
-       0x2198, 0x8211, 0xa282, 0x0020, 0x20c8, 0x20a0, 0x53a3, 0x147f,
-       0x137f, 0x157f, 0x037f, 0x007c, 0x0d7e, 0x20a1, 0x020b, 0x1078,
-       0x65f8, 0x20a3, 0x0200, 0x20a3, 0x0014, 0x60c3, 0x0014, 0x20a3,
-       0x0000, 0x20a3, 0x0000, 0x2099, 0xa5a3, 0x20a9, 0x0004, 0x53a6,
-       0x20a3, 0x0004, 0x20a3, 0x7878, 0x20a3, 0x0000, 0x20a3, 0x0000,
-       0x1078, 0x6c2d, 0x0d7f, 0x007c, 0x20a1, 0x020b, 0x1078, 0x65f8,
-       0x20a3, 0x0214, 0x20a3, 0x0018, 0x20a3, 0x0800, 0x7810, 0xa084,
-       0xff00, 0x20a2, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x20a3, 0x0000,
-       0x20a3, 0x0000, 0x7810, 0xa084, 0x00ff, 0x20a2, 0x7828, 0x20a2,
-       0x20a3, 0x0000, 0x20a3, 0x0000, 0x60c3, 0x0018, 0x1078, 0x6c2d,
-       0x007c, 0x0d7e, 0x017e, 0x2f68, 0x2009, 0x0035, 0x1078, 0x8ef5,
-       0x00c0, 0x7361, 0x20a1, 0x020b, 0x1078, 0x6567, 0x20a3, 0x1300,
-       0x20a3, 0x0000, 0x7828, 0x2068, 0x681c, 0xa086, 0x0003, 0x0040,
-       0x733d, 0x7818, 0xa080, 0x0028, 0x2014, 0xa286, 0x007e, 0x00c0,
-       0x7317, 0x20a3, 0x00ff, 0x20a3, 0xfffe, 0x0078, 0x7352, 0xa286,
-       0x007f, 0x00c0, 0x7321, 0x20a3, 0x00ff, 0x20a3, 0xfffd, 0x0078,
-       0x7352, 0xd2bc, 0x0040, 0x7337, 0xa286, 0x0080, 0x00c0, 0x732e,
-       0x20a3, 0x00ff, 0x20a3, 0xfffc, 0x0078, 0x7352, 0xa2e8, 0xa434,
-       0x2d6c, 0x6810, 0x20a2, 0x6814, 0x20a2, 0x0078, 0x7352, 0x20a3,
-       0x0000, 0x6098, 0x20a2, 0x0078, 0x7352, 0x7818, 0xa080, 0x0028,
-       0x2004, 0xa082, 0x007e, 0x0048, 0x734e, 0x0d7e, 0x2069, 0xa31a,
-       0x2da6, 0x8d68, 0x2da6, 0x0d7f, 0x0078, 0x7352, 0x20a3, 0x0000,
-       0x6030, 0x20a2, 0x7834, 0x20a2, 0x7838, 0x20a2, 0x20a3, 0x0000,
-       0x20a3, 0x0000, 0x60c3, 0x000c, 0x1078, 0x6c2d, 0x017f, 0x0d7f,
-       0x007c, 0x7817, 0x0001, 0x7803, 0x0006, 0x017f, 0x0d7f, 0x007c,
-       0x0d7e, 0x027e, 0x7928, 0x2168, 0x691c, 0xa186, 0x0006, 0x0040,
-       0x738a, 0xa186, 0x0003, 0x0040, 0x73e5, 0xa186, 0x0005, 0x0040,
-       0x73c8, 0xa186, 0x0004, 0x0040, 0x73b8, 0xa186, 0x0008, 0x0040,
-       0x73d2, 0x7807, 0x0037, 0x7813, 0x1700, 0x1078, 0x7450, 0x027f,
-       0x0d7f, 0x007c, 0x1078, 0x740d, 0x2009, 0x4000, 0x6800, 0x0079,
-       0x7391, 0x73a4, 0x73b2, 0x73a6, 0x73b2, 0x73ad, 0x73a4, 0x73a4,
-       0x73b2, 0x73b2, 0x73b2, 0x73b2, 0x73a4, 0x73a4, 0x73a4, 0x73a4,
-       0x73a4, 0x73b2, 0x73a4, 0x73b2, 0x1078, 0x1328, 0x6824, 0xd0e4,
-       0x0040, 0x73ad, 0xd0cc, 0x0040, 0x73b0, 0xa00e, 0x0078, 0x73b2,
-       0x2009, 0x2000, 0x6828, 0x20a2, 0x682c, 0x20a2, 0x0078, 0x7403,
-       0x1078, 0x740d, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x2009, 0x4000,
-       0x6a00, 0xa286, 0x0002, 0x00c0, 0x73c6, 0xa00e, 0x0078, 0x7403,
-       0x1078, 0x740d, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x2009, 0x4000,
-       0x0078, 0x7403, 0x1078, 0x740d, 0x20a3, 0x0000, 0x20a3, 0x0000,
-       0x2009, 0x4000, 0xa286, 0x0005, 0x0040, 0x73e2, 0xa286, 0x0002,
-       0x00c0, 0x73e3, 0xa00e, 0x0078, 0x7403, 0x1078, 0x740d, 0x6810,
-       0x2068, 0x697c, 0x6810, 0xa112, 0x6980, 0x6814, 0xa103, 0x20a2,
-       0x22a2, 0x7928, 0xa180, 0x0000, 0x2004, 0xa08e, 0x0002, 0x0040,
-       0x7401, 0xa08e, 0x0004, 0x0040, 0x7401, 0x2009, 0x4000, 0x0078,
-       0x7403, 0x2009, 0x0000, 0x21a2, 0x20a3, 0x0000, 0x60c3, 0x0018,
-       0x1078, 0x6c2d, 0x027f, 0x0d7f, 0x007c, 0x037e, 0x047e, 0x057e,
-       0x067e, 0x20a1, 0x020b, 0x1078, 0x65f8, 0xa006, 0x20a3, 0x0200,
-       0x20a2, 0x7934, 0x21a2, 0x7938, 0x21a2, 0x7818, 0xa080, 0x0028,
-       0x2004, 0xa092, 0x007e, 0x0048, 0x7433, 0x0d7e, 0x2069, 0xa31a,
-       0x2d2c, 0x8d68, 0x2d34, 0xa0e8, 0xa434, 0x2d6c, 0x6b10, 0x6c14,
-       0x0d7f, 0x0078, 0x7439, 0x2019, 0x0000, 0x6498, 0x2029, 0x0000,
-       0x6630, 0x7828, 0xa080, 0x0007, 0x2004, 0xa086, 0x0003, 0x00c0,
-       0x7447, 0x25a2, 0x26a2, 0x23a2, 0x24a2, 0x0078, 0x744b, 0x23a2,
-       0x24a2, 0x25a2, 0x26a2, 0x067f, 0x057f, 0x047f, 0x037f, 0x007c,
-       0x20a1, 0x020b, 0x1078, 0x65f8, 0x20a3, 0x0100, 0x20a3, 0x0000,
-       0x20a3, 0x0009, 0x7810, 0x20a2, 0x60c3, 0x0008, 0x1078, 0x6c2d,
-       0x007c, 0x20a1, 0x020b, 0x1078, 0x655e, 0x20a3, 0x1400, 0x20a3,
-       0x0000, 0x7834, 0x20a2, 0x7838, 0x20a2, 0x7828, 0x20a2, 0x782c,
-       0x20a2, 0x7830, 0xa084, 0x00ff, 0x8007, 0x20a2, 0x20a3, 0x0000,
-       0x60c3, 0x0010, 0x1078, 0x6c2d, 0x007c, 0x20a1, 0x020b, 0x1078,
-       0x65ef, 0x20a3, 0x0100, 0x20a3, 0x0000, 0x7828, 0x20a2, 0x7810,
-       0x20a2, 0x60c3, 0x0008, 0x1078, 0x6c2d, 0x007c, 0x147e, 0x20a1,
-       0x020b, 0x1078, 0x7499, 0x60c3, 0x0000, 0x1078, 0x6c2d, 0x147f,
-       0x007c, 0x20e1, 0x9080, 0x20e1, 0x4000, 0x7818, 0xa080, 0x0028,
-       0x2004, 0xd0bc, 0x0040, 0x74b6, 0x0d7e, 0xa0e8, 0xa434, 0x2d6c,
-       0x6810, 0xa085, 0x0300, 0x20a2, 0x6814, 0x20a2, 0x2069, 0xa31a,
-       0x2da6, 0x8d68, 0x2da6, 0x0d7f, 0x0078, 0x74be, 0x20a3, 0x0300,
-       0x6298, 0x22a2, 0x20a3, 0x0000, 0x6230, 0x22a2, 0x20a3, 0x0819,
-       0x20a3, 0x0000, 0x1078, 0x6c1c, 0x22a2, 0x20a3, 0x0000, 0x2fa2,
-       0x7a08, 0x22a2, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x007c, 0x2061,
-       0xaa00, 0x2a70, 0x7060, 0x7046, 0x704b, 0xaa00, 0x007c, 0x0e7e,
-       0x127e, 0x2071, 0xa300, 0x2091, 0x8000, 0x7544, 0xa582, 0x0010,
-       0x0048, 0x7509, 0x7048, 0x2060, 0x6000, 0xa086, 0x0000, 0x0040,
-       0x74f5, 0xace0, 0x0010, 0x7054, 0xac02, 0x00c8, 0x74f1, 0x0078,
-       0x74e4, 0x2061, 0xaa00, 0x0078, 0x74e4, 0x6003, 0x0008, 0x8529,
-       0x7546, 0xaca8, 0x0010, 0x7054, 0xa502, 0x00c8, 0x7505, 0x754a,
-       0xa085, 0x0001, 0x127f, 0x0e7f, 0x007c, 0x704b, 0xaa00, 0x0078,
-       0x7500, 0xa006, 0x0078, 0x7502, 0x0e7e, 0x2071, 0xa300, 0x7544,
-       0xa582, 0x0010, 0x0048, 0x753a, 0x7048, 0x2060, 0x6000, 0xa086,
-       0x0000, 0x0040, 0x7527, 0xace0, 0x0010, 0x7054, 0xac02, 0x00c8,
-       0x7523, 0x0078, 0x7516, 0x2061, 0xaa00, 0x0078, 0x7516, 0x6003,
-       0x0008, 0x8529, 0x7546, 0xaca8, 0x0010, 0x7054, 0xa502, 0x00c8,
-       0x7536, 0x754a, 0xa085, 0x0001, 0x0e7f, 0x007c, 0x704b, 0xaa00,
-       0x0078, 0x7532, 0xa006, 0x0078, 0x7534, 0xac82, 0xaa00, 0x1048,
-       0x1328, 0x2001, 0xa315, 0x2004, 0xac02, 0x10c8, 0x1328, 0xa006,
-       0x6006, 0x600a, 0x600e, 0x6012, 0x6016, 0x601a, 0x601f, 0x0000,
-       0x6003, 0x0000, 0x6022, 0x6026, 0x602a, 0x602e, 0x6032, 0x6036,
-       0x603a, 0x603e, 0x2061, 0xa300, 0x6044, 0x8000, 0x6046, 0xa086,
-       0x0001, 0x0040, 0x7564, 0x007c, 0x127e, 0x2091, 0x8000, 0x1078,
-       0x6109, 0x127f, 0x0078, 0x7563, 0x601c, 0xa084, 0x000f, 0x0079,
-       0x7571, 0x757a, 0x758b, 0x75a7, 0x75c3, 0x8f2d, 0x8f49, 0x8f65,
-       0x757a, 0x758b, 0xa186, 0x0013, 0x00c0, 0x7583, 0x1078, 0x6010,
-       0x1078, 0x6109, 0x007c, 0xa18e, 0x0047, 0x00c0, 0x758a, 0xa016,
-       0x1078, 0x15ec, 0x007c, 0x067e, 0x6000, 0xa0b2, 0x0010, 0x10c8,
-       0x1328, 0x1079, 0x7595, 0x067f, 0x007c, 0x75a5, 0x7891, 0x7a34,
-       0x75a5, 0x7ab8, 0x75df, 0x75a5, 0x75a5, 0x7823, 0x7e6d, 0x75a5,
-       0x75a5, 0x75a5, 0x75a5, 0x75a5, 0x75a5, 0x1078, 0x1328, 0x067e,
-       0x6000, 0xa0b2, 0x0010, 0x10c8, 0x1328, 0x1079, 0x75b1, 0x067f,
-       0x007c, 0x75c1, 0x8522, 0x75c1, 0x75c1, 0x75c1, 0x75c1, 0x75c1,
-       0x75c1, 0x84c5, 0x86a8, 0x75c1, 0x8552, 0x85d8, 0x8552, 0x85d8,
-       0x75c1, 0x1078, 0x1328, 0x067e, 0x6000, 0xa0b2, 0x0010, 0x10c8,
-       0x1328, 0x1079, 0x75cd, 0x067f, 0x007c, 0x75dd, 0x7eb4, 0x7f81,
-       0x80c6, 0x8242, 0x75dd, 0x75dd, 0x75dd, 0x7e8d, 0x846d, 0x8471,
-       0x75dd, 0x75dd, 0x75dd, 0x75dd, 0x84a1, 0x1078, 0x1328, 0xa1b6,
-       0x0015, 0x00c0, 0x75e7, 0x1078, 0x753d, 0x0078, 0x75ed, 0xa1b6,
-       0x0016, 0x10c0, 0x1328, 0x1078, 0x753d, 0x007c, 0x20a9, 0x000e,
-       0x2e98, 0x6010, 0x20a0, 0x53a3, 0x20a9, 0x0006, 0x3310, 0x3420,
-       0x9398, 0x94a0, 0x3318, 0x3428, 0x222e, 0x2326, 0xa290, 0x0002,
-       0xa5a8, 0x0002, 0xa398, 0x0002, 0xa4a0, 0x0002, 0x00f0, 0x75fc,
-       0x0e7e, 0x1078, 0x8a44, 0x0040, 0x7613, 0x6010, 0x2070, 0x7007,
-       0x0000, 0x7037, 0x0103, 0x0e7f, 0x1078, 0x753d, 0x007c, 0x0d7e,
-       0x037e, 0x7330, 0xa386, 0x0200, 0x00c0, 0x7624, 0x6018, 0x2068,
-       0x6813, 0x00ff, 0x6817, 0xfffd, 0x6010, 0xa005, 0x0040, 0x762e,
-       0x2068, 0x6807, 0x0000, 0x6837, 0x0103, 0x6b32, 0x1078, 0x753d,
-       0x037f, 0x0d7f, 0x007c, 0x017e, 0x20a9, 0x002a, 0xae80, 0x000c,
-       0x2098, 0x6010, 0xa080, 0x0002, 0x20a0, 0x53a3, 0x20a9, 0x002a,
-       0x6010, 0xa080, 0x0001, 0x2004, 0xa080, 0x0002, 0x20a0, 0x53a3,
-       0x0e7e, 0x6010, 0x2004, 0x2070, 0x7037, 0x0103, 0x0e7f, 0x1078,
-       0x753d, 0x017f, 0x007c, 0x0e7e, 0x0d7e, 0x603f, 0x0000, 0x2c68,
-       0x017e, 0x2009, 0x0035, 0x1078, 0x8ef5, 0x017f, 0x00c0, 0x766f,
-       0x027e, 0x6228, 0x2268, 0x027f, 0x2071, 0xa88c, 0x6b1c, 0xa386,
-       0x0003, 0x0040, 0x7673, 0xa386, 0x0006, 0x0040, 0x7677, 0x1078,
-       0x753d, 0x0078, 0x7679, 0x1078, 0x767c, 0x0078, 0x7679, 0x1078,
-       0x771e, 0x0d7f, 0x0e7f, 0x007c, 0x0f7e, 0x6810, 0x2078, 0xa186,
-       0x0015, 0x0040, 0x7705, 0xa18e, 0x0016, 0x00c0, 0x771c, 0x700c,
-       0xa084, 0xff00, 0xa086, 0x1700, 0x00c0, 0x76e0, 0x8fff, 0x0040,
-       0x771a, 0x6808, 0xa086, 0xffff, 0x00c0, 0x7709, 0x784c, 0xa084,
-       0x0060, 0xa086, 0x0020, 0x00c0, 0x76a7, 0x797c, 0x7810, 0xa106,
-       0x00c0, 0x7709, 0x7980, 0x7814, 0xa106, 0x00c0, 0x7709, 0x1078,
-       0x8bf4, 0x6830, 0x7852, 0x784c, 0xc0dc, 0xc0f4, 0xc0d4, 0x784e,
-       0x027e, 0xa00e, 0x6a14, 0x2001, 0x000a, 0x1078, 0x5a98, 0x7854,
-       0xa20a, 0x0048, 0x76bc, 0x8011, 0x7a56, 0x82ff, 0x027f, 0x00c0,
-       0x76c8, 0x0c7e, 0x2d60, 0x1078, 0x8832, 0x0c7f, 0x0078, 0x771a,
-       0x0c7e, 0x0d7e, 0x2f68, 0x6838, 0xd0fc, 0x00c0, 0x76d3, 0x1078,
-       0x4290, 0x0078, 0x76d5, 0x1078, 0x436e, 0x0d7f, 0x0c7f, 0x00c0,
-       0x7709, 0x0c7e, 0x2d60, 0x1078, 0x753d, 0x0c7f, 0x0078, 0x771a,
-       0x7008, 0xa086, 0x000b, 0x00c0, 0x76fa, 0x6018, 0x200c, 0xc1bc,
-       0x2102, 0x0c7e, 0x2d60, 0x7853, 0x0003, 0x6007, 0x0085, 0x6003,
-       0x000b, 0x601f, 0x0002, 0x1078, 0x5bf8, 0x1078, 0x6109, 0x0c7f,
-       0x0078, 0x771a, 0x700c, 0xa086, 0x2a00, 0x00c0, 0x7709, 0x2001,
-       0xa5a2, 0x2004, 0x683e, 0x0078, 0x771a, 0x1078, 0x7739, 0x0078,
-       0x771c, 0x8fff, 0x1040, 0x1328, 0x0c7e, 0x0d7e, 0x2d60, 0x2f68,
-       0x684b, 0x0003, 0x1078, 0x8726, 0x1078, 0x8bf4, 0x1078, 0x8c01,
-       0x0d7f, 0x0c7f, 0x1078, 0x753d, 0x0f7f, 0x007c, 0xa186, 0x0015,
-       0x00c0, 0x7728, 0x2001, 0xa5a2, 0x2004, 0x683e, 0x0078, 0x7736,
-       0xa18e, 0x0016, 0x00c0, 0x7738, 0x0c7e, 0x2d00, 0x2060, 0x1078,
-       0xa134, 0x1078, 0x5a41, 0x1078, 0x753d, 0x0c7f, 0x1078, 0x753d,
-       0x007c, 0x027e, 0x037e, 0x047e, 0x7228, 0x7c80, 0x7b7c, 0xd2f4,
-       0x0040, 0x7748, 0x2001, 0xa5a2, 0x2004, 0x683e, 0x0078, 0x77ac,
-       0x0c7e, 0x2d60, 0x1078, 0x874a, 0x0c7f, 0x6804, 0xa086, 0x0050,
-       0x00c0, 0x7760, 0x0c7e, 0x2d00, 0x2060, 0x6003, 0x0001, 0x6007,
-       0x0050, 0x1078, 0x5bf8, 0x1078, 0x6109, 0x0c7f, 0x0078, 0x77ac,
-       0x6800, 0xa086, 0x000f, 0x0040, 0x7782, 0x8fff, 0x1040, 0x1328,
-       0x6824, 0xd0dc, 0x00c0, 0x7782, 0x6800, 0xa086, 0x0004, 0x00c0,
-       0x7787, 0x784c, 0xd0ac, 0x0040, 0x7787, 0x784c, 0xc0dc, 0xc0f4,
-       0x784e, 0x7850, 0xc0f4, 0xc0fc, 0x7852, 0x2001, 0x0001, 0x682e,
-       0x0078, 0x77a6, 0x2001, 0x0007, 0x682e, 0x0078, 0x77a6, 0x784c,
-       0xd0b4, 0x00c0, 0x7794, 0xd0ac, 0x0040, 0x7782, 0x784c, 0xd0f4,
-       0x00c0, 0x7782, 0x0078, 0x7775, 0xd2ec, 0x00c0, 0x7782, 0x7024,
-       0xa306, 0x00c0, 0x779f, 0x7020, 0xa406, 0x0040, 0x7782, 0x7020,
-       0x6836, 0x7024, 0x683a, 0x2001, 0x0005, 0x682e, 0x1078, 0x8d2b,
-       0x1078, 0x6109, 0x0078, 0x77ae, 0x1078, 0x753d, 0x047f, 0x037f,
-       0x027f, 0x007c, 0x0e7e, 0x0d7e, 0x027e, 0x6034, 0x2068, 0x6a1c,
-       0xa286, 0x0007, 0x0040, 0x7806, 0xa286, 0x0002, 0x0040, 0x7806,
-       0xa286, 0x0000, 0x0040, 0x7806, 0x6808, 0x6338, 0xa306, 0x00c0,
-       0x7806, 0x2071, 0xa88c, 0xa186, 0x0015, 0x0040, 0x7800, 0xa18e,
-       0x0016, 0x00c0, 0x77e8, 0x6030, 0xa084, 0x00ff, 0xa086, 0x0001,
-       0x00c0, 0x77e8, 0x700c, 0xa086, 0x2a00, 0x00c0, 0x77e8, 0x6034,
-       0xa080, 0x0009, 0x200c, 0xc1dd, 0xc1f5, 0x2102, 0x0078, 0x7800,
-       0x0c7e, 0x6034, 0x2060, 0x6010, 0x2068, 0x1078, 0x8a44, 0x1040,
-       0x1328, 0x6853, 0x0003, 0x6007, 0x0085, 0x6003, 0x000b, 0x601f,
-       0x0002, 0x1078, 0x5bf8, 0x1078, 0x6109, 0x0c7f, 0x0078, 0x7806,
-       0x6034, 0x2068, 0x2001, 0xa5a2, 0x2004, 0x683e, 0x1078, 0x753d,
-       0x027f, 0x0d7f, 0x0e7f, 0x007c, 0x0d7e, 0x20a9, 0x000e, 0x2e98,
-       0x6010, 0x20a0, 0x53a3, 0xa1b6, 0x0015, 0x00c0, 0x7820, 0x6018,
-       0x2068, 0x7038, 0x680a, 0x703c, 0x680e, 0x6800, 0xc08d, 0x6802,
-       0x0d7f, 0x0078, 0x7608, 0x2100, 0xa1b2, 0x0044, 0x10c8, 0x1328,
-       0xa1b2, 0x0040, 0x00c8, 0x7888, 0x0079, 0x782e, 0x787c, 0x7870,
-       0x787c, 0x787c, 0x787c, 0x787c, 0x786e, 0x786e, 0x786e, 0x786e,
-       0x786e, 0x786e, 0x786e, 0x786e, 0x786e, 0x786e, 0x786e, 0x786e,
-       0x786e, 0x786e, 0x786e, 0x786e, 0x786e, 0x786e, 0x786e, 0x786e,
-       0x786e, 0x786e, 0x786e, 0x786e, 0x786e, 0x787c, 0x786e, 0x787c,
-       0x787c, 0x786e, 0x786e, 0x786e, 0x786e, 0x786e, 0x787c, 0x786e,
-       0x786e, 0x786e, 0x786e, 0x786e, 0x786e, 0x786e, 0x786e, 0x786e,
-       0x787c, 0x787c, 0x786e, 0x786e, 0x786e, 0x786e, 0x786e, 0x786e,
-       0x786e, 0x786e, 0x786e, 0x787c, 0x786e, 0x786e, 0x1078, 0x1328,
-       0x6003, 0x0001, 0x6106, 0x1078, 0x5c45, 0x127e, 0x2091, 0x8000,
-       0x1078, 0x6109, 0x127f, 0x007c, 0x6003, 0x0001, 0x6106, 0x1078,
-       0x5c45, 0x127e, 0x2091, 0x8000, 0x1078, 0x6109, 0x127f, 0x007c,
-       0x2600, 0x0079, 0x788b, 0x788f, 0x788f, 0x788f, 0x787c, 0x1078,
-       0x1328, 0x6004, 0xa0b2, 0x0044, 0x10c8, 0x1328, 0xa1b6, 0x0013,
-       0x00c0, 0x78a1, 0xa0b2, 0x0040, 0x00c8, 0x79fb, 0x2008, 0x0079,
-       0x7941, 0xa1b6, 0x0027, 0x00c0, 0x78fe, 0x1078, 0x6010, 0x6004,
-       0x1078, 0x8c27, 0x0040, 0x78be, 0x1078, 0x8c3b, 0x0040, 0x78f6,
-       0xa08e, 0x0021, 0x0040, 0x78fa, 0xa08e, 0x0022, 0x0040, 0x78f6,
-       0xa08e, 0x003d, 0x0040, 0x78fa, 0x0078, 0x78f1, 0x1078, 0x2839,
-       0x2001, 0x0007, 0x1078, 0x443f, 0x6018, 0xa080, 0x0028, 0x200c,
-       0x1078, 0x7a05, 0xa186, 0x007e, 0x00c0, 0x78d3, 0x2001, 0xa332,
-       0x2014, 0xc285, 0x2202, 0x017e, 0x027e, 0x037e, 0x2110, 0x2019,
-       0x0028, 0x1078, 0x5d53, 0x077e, 0x2039, 0x0000, 0x1078, 0x5c78,
-       0x0c7e, 0x6018, 0xa065, 0x0040, 0x78e7, 0x1078, 0x471b, 0x0c7f,
-       0x2c08, 0x1078, 0x9c38, 0x077f, 0x037f, 0x027f, 0x017f, 0x1078,
-       0x44bc, 0x1078, 0x753d, 0x1078, 0x6109, 0x007c, 0x1078, 0x7a05,
-       0x0078, 0x78f1, 0x1078, 0x7a28, 0x0078, 0x78f1, 0xa186, 0x0014,
-       0x00c0, 0x78f5, 0x1078, 0x6010, 0x1078, 0x2813, 0x1078, 0x8c27,
-       0x00c0, 0x791d, 0x1078, 0x2839, 0x6018, 0xa080, 0x0028, 0x200c,
-       0x1078, 0x7a05, 0xa186, 0x007e, 0x00c0, 0x791b, 0x2001, 0xa332,
-       0x200c, 0xc185, 0x2102, 0x0078, 0x78f1, 0x1078, 0x8c3b, 0x00c0,
-       0x7925, 0x1078, 0x7a05, 0x0078, 0x78f1, 0x6004, 0xa08e, 0x0032,
-       0x00c0, 0x7936, 0x0e7e, 0x0f7e, 0x2071, 0xa381, 0x2079, 0x0000,
-       0x1078, 0x2b56, 0x0f7f, 0x0e7f, 0x0078, 0x78f1, 0x6004, 0xa08e,
-       0x0021, 0x0040, 0x7921, 0xa08e, 0x0022, 0x1040, 0x7a05, 0x0078,
-       0x78f1, 0x7983, 0x7985, 0x7989, 0x798d, 0x7991, 0x7995, 0x7981,
-       0x7981, 0x7981, 0x7981, 0x7981, 0x7981, 0x7981, 0x7981, 0x7981,
-       0x7981, 0x7981, 0x7981, 0x7981, 0x7981, 0x7981, 0x7981, 0x7981,
-       0x7981, 0x7981, 0x7981, 0x7981, 0x7981, 0x7981, 0x7981, 0x7999,
-       0x79ab, 0x7981, 0x79ad, 0x79ab, 0x7981, 0x7981, 0x7981, 0x7981,
-       0x7981, 0x79ab, 0x79ab, 0x7981, 0x7981, 0x7981, 0x7981, 0x7981,
-       0x7981, 0x7981, 0x7981, 0x79de, 0x79ab, 0x7981, 0x79a5, 0x7981,
-       0x7981, 0x7981, 0x79a7, 0x7981, 0x7981, 0x7981, 0x79ab, 0x7981,
-       0x7981, 0x1078, 0x1328, 0x0078, 0x79ab, 0x2001, 0x000b, 0x0078,
-       0x79b8, 0x2001, 0x0003, 0x0078, 0x79b8, 0x2001, 0x0005, 0x0078,
-       0x79b8, 0x2001, 0x0001, 0x0078, 0x79b8, 0x2001, 0x0009, 0x0078,
-       0x79b8, 0x1078, 0x6010, 0x6003, 0x0005, 0x2001, 0xa5a2, 0x2004,
-       0x603e, 0x1078, 0x6109, 0x0078, 0x79b7, 0x0078, 0x79ab, 0x0078,
-       0x79ab, 0x1078, 0x443f, 0x0078, 0x79f0, 0x1078, 0x6010, 0x6003,
-       0x0004, 0x2001, 0xa5a0, 0x2004, 0x6016, 0x1078, 0x6109, 0x007c,
-       0x1078, 0x443f, 0x1078, 0x6010, 0x2001, 0xa5a2, 0x2004, 0x603e,
-       0x6003, 0x0002, 0x037e, 0x2019, 0xa35c, 0x2304, 0xa084, 0xff00,
-       0x00c0, 0x79cf, 0x2019, 0xa5a0, 0x231c, 0x0078, 0x79d8, 0x8007,
-       0xa09a, 0x0004, 0x0048, 0x79ca, 0x8003, 0x801b, 0x831b, 0xa318,
-       0x6316, 0x037f, 0x1078, 0x6109, 0x0078, 0x79b7, 0x0e7e, 0x0f7e,
-       0x2071, 0xa381, 0x2079, 0x0000, 0x1078, 0x2b56, 0x0f7f, 0x0e7f,
-       0x1078, 0x6010, 0x1078, 0x753d, 0x1078, 0x6109, 0x0078, 0x79b7,
-       0x1078, 0x6010, 0x6003, 0x0002, 0x2001, 0xa5a0, 0x2004, 0x6016,
-       0x1078, 0x6109, 0x007c, 0x2600, 0x2008, 0x0079, 0x79ff, 0x7a03,
-       0x7a03, 0x7a03, 0x79f0, 0x1078, 0x1328, 0x0e7e, 0x1078, 0x8a44,
-       0x0040, 0x7a21, 0x6010, 0x2070, 0x7038, 0xd0fc, 0x0040, 0x7a21,
-       0x7007, 0x0000, 0x017e, 0x6004, 0xa08e, 0x0021, 0x0040, 0x7a23,
-       0xa08e, 0x003d, 0x0040, 0x7a23, 0x017f, 0x7037, 0x0103, 0x7033,
-       0x0100, 0x0e7f, 0x007c, 0x017f, 0x1078, 0x7a28, 0x0078, 0x7a21,
-       0x0e7e, 0xacf0, 0x0004, 0x2e74, 0x7000, 0x2070, 0x7037, 0x0103,
-       0x7023, 0x8001, 0x0e7f, 0x007c, 0x0d7e, 0x6618, 0x2668, 0x6804,
-       0xa084, 0x00ff, 0x0d7f, 0xa0b2, 0x000c, 0x10c8, 0x1328, 0x6604,
-       0xa6b6, 0x0043, 0x00c0, 0x7a48, 0x1078, 0x8e6d, 0x0078, 0x7aa7,
-       0x6604, 0xa6b6, 0x0033, 0x00c0, 0x7a51, 0x1078, 0x8e11, 0x0078,
-       0x7aa7, 0x6604, 0xa6b6, 0x0028, 0x00c0, 0x7a5a, 0x1078, 0x8c6a,
-       0x0078, 0x7aa7, 0x6604, 0xa6b6, 0x0029, 0x00c0, 0x7a63, 0x1078,
-       0x8c84, 0x0078, 0x7aa7, 0x6604, 0xa6b6, 0x001f, 0x00c0, 0x7a6c,
-       0x1078, 0x75ee, 0x0078, 0x7aa7, 0x6604, 0xa6b6, 0x0000, 0x00c0,
-       0x7a75, 0x1078, 0x780c, 0x0078, 0x7aa7, 0x6604, 0xa6b6, 0x0022,
-       0x00c0, 0x7a7e, 0x1078, 0x7617, 0x0078, 0x7aa7, 0x6604, 0xa6b6,
-       0x0035, 0x00c0, 0x7a87, 0x1078, 0x7653, 0x0078, 0x7aa7, 0x6604,
-       0xa6b6, 0x0039, 0x00c0, 0x7a90, 0x1078, 0x77b2, 0x0078, 0x7aa7,
-       0x6604, 0xa6b6, 0x003d, 0x00c0, 0x7a99, 0x1078, 0x7633, 0x0078,
-       0x7aa7, 0xa1b6, 0x0015, 0x00c0, 0x7aa1, 0x1079, 0x7aac, 0x0078,
-       0x7aa7, 0xa1b6, 0x0016, 0x00c0, 0x7aa8, 0x1079, 0x7bfd, 0x007c,
-       0x1078, 0x7583, 0x0078, 0x7aa7, 0x7ad0, 0x7ad3, 0x7ad0, 0x7b1e,
-       0x7ad0, 0x7b91, 0x7c09, 0x7ad0, 0x7ad0, 0x7bd5, 0x7ad0, 0x7beb,
-       0xa1b6, 0x0048, 0x0040, 0x7ac4, 0x20e1, 0x0005, 0x3d18, 0x3e20,
-       0x2c10, 0x1078, 0x15ec, 0x007c, 0x0e7e, 0xacf0, 0x0004, 0x2e74,
-       0x7000, 0x2070, 0x7037, 0x0103, 0x0e7f, 0x1078, 0x753d, 0x007c,
-       0x0005, 0x0005, 0x007c, 0x0e7e, 0x2071, 0xa300, 0x707c, 0xa086,
-       0x0074, 0x00c0, 0x7b07, 0x1078, 0x9c0c, 0x00c0, 0x7af9, 0x0d7e,
-       0x6018, 0x2068, 0x7030, 0xd08c, 0x0040, 0x7aec, 0x6800, 0xd0bc,
-       0x0040, 0x7aec, 0xc0c5, 0x6802, 0x1078, 0x7b0b, 0x0d7f, 0x2001,
-       0x0006, 0x1078, 0x443f, 0x1078, 0x2839, 0x1078, 0x753d, 0x0078,
-       0x7b09, 0x2001, 0x000a, 0x1078, 0x443f, 0x1078, 0x2839, 0x6003,
-       0x0001, 0x6007, 0x0001, 0x1078, 0x5c45, 0x0078, 0x7b09, 0x1078,
-       0x7b81, 0x0e7f, 0x007c, 0x6800, 0xd084, 0x0040, 0x7b1d, 0x2001,
-       0x0000, 0x1078, 0x442b, 0x2069, 0xa351, 0x6804, 0xd0a4, 0x0040,
-       0x7b1d, 0x2001, 0x0006, 0x1078, 0x4472, 0x007c, 0x0d7e, 0x2011,
-       0xa31f, 0x2204, 0xa086, 0x0074, 0x00c0, 0x7b7d, 0x6018, 0x2068,
-       0x6aa0, 0xa286, 0x007e, 0x00c0, 0x7b31, 0x1078, 0x7d17, 0x0078,
-       0x7b7f, 0x1078, 0x7d0d, 0x6018, 0x2068, 0xa080, 0x0028, 0x2014,
-       0xa286, 0x0080, 0x00c0, 0x7b55, 0x6813, 0x00ff, 0x6817, 0xfffc,
-       0x6010, 0xa005, 0x0040, 0x7b4b, 0x2068, 0x6807, 0x0000, 0x6837,
-       0x0103, 0x6833, 0x0200, 0x2001, 0x0006, 0x1078, 0x443f, 0x1078,
-       0x2839, 0x1078, 0x753d, 0x0078, 0x7b7f, 0x0e7e, 0x2071, 0xa332,
-       0x2e04, 0xd09c, 0x0040, 0x7b70, 0x2071, 0xa880, 0x7108, 0x720c,
-       0xa18c, 0x00ff, 0x00c0, 0x7b68, 0xa284, 0xff00, 0x0040, 0x7b70,
-       0x6018, 0x2070, 0x70a0, 0xd0bc, 0x00c0, 0x7b70, 0x7112, 0x7216,
-       0x0e7f, 0x2001, 0x0004, 0x1078, 0x443f, 0x6003, 0x0001, 0x6007,
-       0x0003, 0x1078, 0x5c45, 0x0078, 0x7b7f, 0x1078, 0x7b81, 0x0d7f,
-       0x007c, 0x2001, 0xa300, 0x2004, 0xa086, 0x0003, 0x0040, 0x7b8c,
-       0x2001, 0x0007, 0x1078, 0x443f, 0x1078, 0x2839, 0x1078, 0x753d,
-       0x007c, 0x0e7e, 0x2071, 0xa300, 0x707c, 0xa086, 0x0014, 0x00c0,
-       0x7bcf, 0x7000, 0xa086, 0x0003, 0x00c0, 0x7ba4, 0x6010, 0xa005,
-       0x00c0, 0x7ba4, 0x1078, 0x35f7, 0x0d7e, 0x6018, 0x2068, 0x1078,
-       0x457d, 0x1078, 0x7b0b, 0x0d7f, 0x1078, 0x7dba, 0x00c0, 0x7bcf,
-       0x0d7e, 0x6018, 0x2068, 0x6890, 0x0d7f, 0xa005, 0x0040, 0x7bcf,
-       0x2001, 0x0006, 0x1078, 0x443f, 0x0e7e, 0x6010, 0xa005, 0x0040,
-       0x7bc8, 0x2070, 0x7007, 0x0000, 0x7037, 0x0103, 0x7033, 0x0200,
-       0x0e7f, 0x1078, 0x2839, 0x1078, 0x753d, 0x0078, 0x7bd3, 0x1078,
-       0x7a05, 0x1078, 0x7b81, 0x0e7f, 0x007c, 0x2011, 0xa31f, 0x2204,
-       0xa086, 0x0014, 0x00c0, 0x7be8, 0x2001, 0x0002, 0x1078, 0x443f,
-       0x6003, 0x0001, 0x6007, 0x0001, 0x1078, 0x5c45, 0x0078, 0x7bea,
-       0x1078, 0x7b81, 0x007c, 0x2011, 0xa31f, 0x2204, 0xa086, 0x0004,
-       0x00c0, 0x7bfa, 0x2001, 0x0007, 0x1078, 0x443f, 0x1078, 0x753d,
-       0x0078, 0x7bfc, 0x1078, 0x7b81, 0x007c, 0x7ad0, 0x7c11, 0x7ad0,
-       0x7c4e, 0x7ad0, 0x7cc0, 0x7c09, 0x7ad0, 0x7ad0, 0x7cd5, 0x7ad0,
-       0x7ce8, 0x6604, 0xa6b6, 0x001e, 0x00c0, 0x7c10, 0x1078, 0x753d,
-       0x007c, 0x0d7e, 0x0c7e, 0x1078, 0x7cfb, 0x00c0, 0x7c27, 0x2001,
-       0x0000, 0x1078, 0x442b, 0x2001, 0x0002, 0x1078, 0x443f, 0x6003,
-       0x0001, 0x6007, 0x0002, 0x1078, 0x5c45, 0x0078, 0x7c4b, 0x2009,
-       0xa88e, 0x2104, 0xa086, 0x0009, 0x00c0, 0x7c3c, 0x6018, 0x2068,
-       0x6840, 0xa084, 0x00ff, 0xa005, 0x0040, 0x7c49, 0x8001, 0x6842,
-       0x6017, 0x000a, 0x0078, 0x7c4b, 0x2009, 0xa88f, 0x2104, 0xa084,
-       0xff00, 0xa086, 0x1900, 0x00c0, 0x7c49, 0x1078, 0x753d, 0x0078,
-       0x7c4b, 0x1078, 0x7b81, 0x0c7f, 0x0d7f, 0x007c, 0x1078, 0x7d0a,
-       0x00c0, 0x7c62, 0x2001, 0x0000, 0x1078, 0x442b, 0x2001, 0x0002,
-       0x1078, 0x443f, 0x6003, 0x0001, 0x6007, 0x0002, 0x1078, 0x5c45,
-       0x0078, 0x7c8e, 0x1078, 0x7a05, 0x2009, 0xa88e, 0x2134, 0xa6b4,
-       0x00ff, 0xa686, 0x0005, 0x0040, 0x7c8f, 0xa686, 0x000b, 0x0040,
-       0x7c8c, 0x2009, 0xa88f, 0x2104, 0xa084, 0xff00, 0x00c0, 0x7c7c,
-       0xa686, 0x0009, 0x0040, 0x7c8f, 0xa086, 0x1900, 0x00c0, 0x7c8c,
-       0xa686, 0x0009, 0x0040, 0x7c8f, 0x2001, 0x0004, 0x1078, 0x443f,
-       0x1078, 0x753d, 0x0078, 0x7c8e, 0x1078, 0x7b81, 0x007c, 0x0d7e,
-       0x6010, 0x2068, 0x1078, 0x8a44, 0x0040, 0x7c9d, 0x6838, 0xd0fc,
-       0x0040, 0x7c9d, 0x0d7f, 0x0078, 0x7c8c, 0x6018, 0x2068, 0x6840,
-       0xa084, 0x00ff, 0xa005, 0x0040, 0x7cae, 0x8001, 0x6842, 0x6017,
-       0x000a, 0x6007, 0x0016, 0x0d7f, 0x0078, 0x7c8e, 0x68a0, 0xa086,
-       0x007e, 0x00c0, 0x7cbb, 0x0e7e, 0x2071, 0xa300, 0x1078, 0x41f5,
-       0x0e7f, 0x0078, 0x7cbd, 0x1078, 0x2813, 0x0d7f, 0x0078, 0x7c8c,
-       0x1078, 0x7d0a, 0x00c0, 0x7cd0, 0x2001, 0x0004, 0x1078, 0x443f,
-       0x6003, 0x0001, 0x6007, 0x0003, 0x1078, 0x5c45, 0x0078, 0x7cd4,
-       0x1078, 0x7a05, 0x1078, 0x7b81, 0x007c, 0x1078, 0x7d0a, 0x00c0,
-       0x7ce5, 0x2001, 0x0008, 0x1078, 0x443f, 0x6003, 0x0001, 0x6007,
-       0x0005, 0x1078, 0x5c45, 0x0078, 0x7ce7, 0x1078, 0x7b81, 0x007c,
-       0x1078, 0x7d0a, 0x00c0, 0x7cf8, 0x2001, 0x000a, 0x1078, 0x443f,
-       0x6003, 0x0001, 0x6007, 0x0001, 0x1078, 0x5c45, 0x0078, 0x7cfa,
-       0x1078, 0x7b81, 0x007c, 0x2009, 0xa88e, 0x2104, 0xa086, 0x0003,
-       0x00c0, 0x7d09, 0x2009, 0xa88f, 0x2104, 0xa084, 0xff00, 0xa086,
-       0x2a00, 0x007c, 0xa085, 0x0001, 0x007c, 0x0c7e, 0x017e, 0xac88,
-       0x0006, 0x2164, 0x1078, 0x4513, 0x017f, 0x0c7f, 0x007c, 0x0f7e,
-       0x0e7e, 0x0d7e, 0x037e, 0x017e, 0x6018, 0x2068, 0x2071, 0xa332,
-       0x2e04, 0xa085, 0x0003, 0x2072, 0x1078, 0x7d8b, 0x0040, 0x7d50,
-       0x2001, 0xa352, 0x2004, 0xd0a4, 0x0040, 0x7d39, 0xa006, 0x2020,
-       0x2009, 0x002a, 0x1078, 0x9ec0, 0x2001, 0xa30c, 0x200c, 0xc195,
-       0x2102, 0x2019, 0x002a, 0x2009, 0x0001, 0x1078, 0x27e2, 0x2071,
-       0xa300, 0x1078, 0x260d, 0x0c7e, 0x157e, 0x20a9, 0x0081, 0x2009,
-       0x007f, 0x1078, 0x2921, 0x8108, 0x00f0, 0x7d49, 0x157f, 0x0c7f,
-       0x1078, 0x7d0d, 0x6813, 0x00ff, 0x6817, 0xfffe, 0x2071, 0xa880,
-       0x2079, 0x0100, 0x2e04, 0xa084, 0x00ff, 0x2069, 0xa31a, 0x206a,
-       0x78e6, 0x007e, 0x8e70, 0x2e04, 0x2069, 0xa31b, 0x206a, 0x78ea,
-       0xa084, 0xff00, 0x017f, 0xa105, 0x2009, 0xa325, 0x200a, 0x2069,
-       0xa88e, 0x2071, 0xa59c, 0x6810, 0x2072, 0x6814, 0x7006, 0x6818,
-       0x700a, 0x681c, 0x700e, 0x1078, 0x8da9, 0x2001, 0x0006, 0x1078,
-       0x443f, 0x1078, 0x2839, 0x1078, 0x753d, 0x017f, 0x037f, 0x0d7f,
-       0x0e7f, 0x0f7f, 0x007c, 0x027e, 0x037e, 0x0e7e, 0x157e, 0x2019,
-       0xa325, 0x231c, 0x83ff, 0x0040, 0x7db5, 0x2071, 0xa880, 0x2e14,
-       0xa294, 0x00ff, 0x7004, 0xa084, 0xff00, 0xa205, 0xa306, 0x00c0,
-       0x7db5, 0x2011, 0xa896, 0xad98, 0x000a, 0x20a9, 0x0004, 0x1078,
-       0x7e55, 0x00c0, 0x7db5, 0x2011, 0xa89a, 0xad98, 0x0006, 0x20a9,
-       0x0004, 0x1078, 0x7e55, 0x00c0, 0x7db5, 0x157f, 0x0e7f, 0x037f,
-       0x027f, 0x007c, 0x0e7e, 0x2071, 0xa88c, 0x7004, 0xa086, 0x0014,
-       0x00c0, 0x7ddd, 0x7008, 0xa086, 0x0800, 0x00c0, 0x7ddd, 0x700c,
-       0xd0ec, 0x0040, 0x7ddb, 0xa084, 0x0f00, 0xa086, 0x0100, 0x00c0,
-       0x7ddb, 0x7024, 0xd0a4, 0x00c0, 0x7dd8, 0xd0ac, 0x0040, 0x7ddb,
-       0xa006, 0x0078, 0x7ddd, 0xa085, 0x0001, 0x0e7f, 0x007c, 0x0e7e,
-       0x0d7e, 0x0c7e, 0x077e, 0x057e, 0x047e, 0x027e, 0x007e, 0x127e,
-       0x2091, 0x8000, 0x2029, 0xa5b4, 0x252c, 0x2021, 0xa5ba, 0x2424,
-       0x2061, 0xaa00, 0x2071, 0xa300, 0x7244, 0x7060, 0xa202, 0x00c8,
-       0x7e43, 0x1078, 0x9ee5, 0x0040, 0x7e3b, 0x671c, 0xa786, 0x0001,
-       0x0040, 0x7e3b, 0xa786, 0x0007, 0x0040, 0x7e3b, 0x2500, 0xac06,
-       0x0040, 0x7e3b, 0x2400, 0xac06, 0x0040, 0x7e3b, 0x0c7e, 0x6000,
-       0xa086, 0x0004, 0x00c0, 0x7e16, 0x1078, 0x1749, 0xa786, 0x0008,
-       0x00c0, 0x7e25, 0x1078, 0x8c3b, 0x00c0, 0x7e25, 0x0c7f, 0x1078,
-       0x7a05, 0x1078, 0x8c01, 0x0078, 0x7e3b, 0x6010, 0x2068, 0x1078,
-       0x8a44, 0x0040, 0x7e38, 0xa786, 0x0003, 0x00c0, 0x7e4d, 0x6837,
-       0x0103, 0x6b4a, 0x6847, 0x0000, 0x1078, 0x4982, 0x1078, 0x8bf4,
-       0x1078, 0x8c01, 0x0c7f, 0xace0, 0x0010, 0x7054, 0xac02, 0x00c8,
-       0x7e43, 0x0078, 0x7df4, 0x127f, 0x007f, 0x027f, 0x047f, 0x057f,
-       0x077f, 0x0c7f, 0x0d7f, 0x0e7f, 0x007c, 0xa786, 0x0006, 0x00c0,
-       0x7e2f, 0x1078, 0x9e70, 0x0078, 0x7e38, 0x220c, 0x2304, 0xa106,
-       0x00c0, 0x7e60, 0x8210, 0x8318, 0x00f0, 0x7e55, 0xa006, 0x007c,
-       0x2304, 0xa102, 0x0048, 0x7e68, 0x2001, 0x0001, 0x0078, 0x7e6a,
-       0x2001, 0x0000, 0xa18d, 0x0001, 0x007c, 0x6004, 0xa08a, 0x0044,
-       0x10c8, 0x1328, 0x1078, 0x8c27, 0x0040, 0x7e7c, 0x1078, 0x8c3b,
-       0x0040, 0x7e89, 0x0078, 0x7e82, 0x1078, 0x2839, 0x1078, 0x8c3b,
-       0x0040, 0x7e89, 0x1078, 0x6010, 0x1078, 0x753d, 0x1078, 0x6109,
-       0x007c, 0x1078, 0x7a05, 0x0078, 0x7e82, 0xa182, 0x0040, 0x0079,
-       0x7e91, 0x7ea4, 0x7ea4, 0x7ea4, 0x7ea4, 0x7ea4, 0x7ea4, 0x7ea4,
-       0x7ea4, 0x7ea4, 0x7ea4, 0x7ea4, 0x7ea6, 0x7ea6, 0x7ea6, 0x7ea6,
-       0x7ea4, 0x7ea4, 0x7ea4, 0x7ea6, 0x1078, 0x1328, 0x600b, 0xffff,
-       0x6003, 0x0001, 0x6106, 0x1078, 0x5bf8, 0x127e, 0x2091, 0x8000,
-       0x1078, 0x6109, 0x127f, 0x007c, 0xa186, 0x0013, 0x00c0, 0x7ebd,
-       0x6004, 0xa082, 0x0040, 0x0079, 0x7f48, 0xa186, 0x0027, 0x00c0,
-       0x7edf, 0x1078, 0x6010, 0x1078, 0x2813, 0x0d7e, 0x6110, 0x2168,
-       0x1078, 0x8a44, 0x0040, 0x7ed9, 0x6837, 0x0103, 0x684b, 0x0029,
-       0x6847, 0x0000, 0x694c, 0xc1c5, 0x694e, 0x1078, 0x4982, 0x1078,
-       0x8bf4, 0x0d7f, 0x1078, 0x753d, 0x1078, 0x6109, 0x007c, 0xa186,
-       0x0014, 0x00c0, 0x7ee8, 0x6004, 0xa082, 0x0040, 0x0079, 0x7f10,
-       0xa186, 0x0046, 0x0040, 0x7ef4, 0xa186, 0x0045, 0x0040, 0x7ef4,
-       0xa186, 0x0047, 0x10c0, 0x1328, 0x2001, 0x0109, 0x2004, 0xd084,
-       0x0040, 0x7f0d, 0x127e, 0x2091, 0x2200, 0x007e, 0x017e, 0x027e,
-       0x1078, 0x5ad2, 0x027f, 0x017f, 0x007f, 0x127f, 0x6000, 0xa086,
-       0x0002, 0x00c0, 0x7f0d, 0x0078, 0x7f81, 0x1078, 0x7583, 0x007c,
-       0x7f25, 0x7f23, 0x7f23, 0x7f23, 0x7f23, 0x7f23, 0x7f23, 0x7f23,
-       0x7f23, 0x7f23, 0x7f23, 0x7f41, 0x7f41, 0x7f41, 0x7f41, 0x7f23,
-       0x7f41, 0x7f23, 0x7f41, 0x1078, 0x1328, 0x1078, 0x6010, 0x0d7e,
-       0x6110, 0x2168, 0x1078, 0x8a44, 0x0040, 0x7f3b, 0x6837, 0x0103,
-       0x684b, 0x0006, 0x6847, 0x0000, 0x6850, 0xc0ec, 0x6852, 0x1078,
-       0x4982, 0x1078, 0x8bf4, 0x0d7f, 0x1078, 0x753d, 0x1078, 0x6109,
-       0x007c, 0x1078, 0x6010, 0x1078, 0x753d, 0x1078, 0x6109, 0x007c,
-       0x7f5d, 0x7f5b, 0x7f5b, 0x7f5b, 0x7f5b, 0x7f5b, 0x7f5b, 0x7f5b,
-       0x7f5b, 0x7f5b, 0x7f5b, 0x7f6f, 0x7f6f, 0x7f6f, 0x7f6f, 0x7f5b,
-       0x7f7a, 0x7f5b, 0x7f6f, 0x1078, 0x1328, 0x1078, 0x6010, 0x2001,
-       0xa5a2, 0x2004, 0x603e, 0x6003, 0x0002, 0x1078, 0x6109, 0x6010,
-       0xa088, 0x0013, 0x2104, 0xa085, 0x0400, 0x200a, 0x007c, 0x1078,
-       0x6010, 0x2001, 0xa5a2, 0x2004, 0x603e, 0x6003, 0x000f, 0x1078,
-       0x6109, 0x007c, 0x1078, 0x6010, 0x1078, 0x753d, 0x1078, 0x6109,
-       0x007c, 0xa182, 0x0040, 0x0079, 0x7f85, 0x7f98, 0x7f98, 0x7f98,
-       0x7f98, 0x7f98, 0x7f9a, 0x8095, 0x80b7, 0x7f98, 0x7f98, 0x7f98,
-       0x7f98, 0x7f98, 0x7f98, 0x7f98, 0x7f98, 0x7f98, 0x7f98, 0x7f98,
-       0x1078, 0x1328, 0x0e7e, 0x0d7e, 0x603f, 0x0000, 0x2071, 0xa880,
-       0x7124, 0x610a, 0x2071, 0xa88c, 0x6110, 0x2168, 0x7614, 0xa6b4,
-       0x0fff, 0x86ff, 0x0040, 0x8058, 0xa68c, 0x0c00, 0x0040, 0x7fd1,
-       0x0f7e, 0x2c78, 0x1078, 0x4893, 0x0f7f, 0x0040, 0x7fcd, 0x684c,
-       0xd0ac, 0x0040, 0x7fcd, 0x6024, 0xd0dc, 0x00c0, 0x7fcd, 0x6850,
-       0xd0bc, 0x00c0, 0x7fcd, 0x7318, 0x6814, 0xa306, 0x00c0, 0x806f,
-       0x731c, 0x6810, 0xa306, 0x00c0, 0x806f, 0x7318, 0x6b62, 0x731c,
-       0x6b5e, 0xa68c, 0x00ff, 0xa186, 0x0002, 0x0040, 0x8004, 0xa186,
-       0x0028, 0x00c0, 0x7fe1, 0x1078, 0x8c15, 0x684b, 0x001c, 0x0078,
-       0x8006, 0xd6dc, 0x0040, 0x7ffd, 0x684b, 0x0015, 0x684c, 0xd0ac,
-       0x0040, 0x7ffb, 0x6914, 0x6a10, 0x2100, 0xa205, 0x0040, 0x7ffb,
-       0x7018, 0xa106, 0x00c0, 0x7ff8, 0x701c, 0xa206, 0x0040, 0x7ffb,
-       0x6962, 0x6a5e, 0xc6dc, 0x0078, 0x8006, 0xd6d4, 0x0040, 0x8004,
-       0x684b, 0x0007, 0x0078, 0x8006, 0x684b, 0x0000, 0x6837, 0x0103,
-       0x6e46, 0xa01e, 0xd6c4, 0x0040, 0x802f, 0xa686, 0x0100, 0x00c0,
-       0x801a, 0x2001, 0xa899, 0x2004, 0xa005, 0x00c0, 0x801a, 0xc6c4,
-       0x0078, 0x7fa9, 0x7328, 0x732c, 0x6b56, 0x83ff, 0x0040, 0x802f,
-       0xa38a, 0x0009, 0x0048, 0x8026, 0x2019, 0x0008, 0x037e, 0x2308,
-       0x2019, 0xa898, 0xad90, 0x0019, 0x1078, 0x8739, 0x037f, 0xd6cc,
-       0x0040, 0x8085, 0x7124, 0x695a, 0x81ff, 0x0040, 0x8085, 0xa192,
-       0x0021, 0x00c8, 0x8046, 0x2071, 0xa898, 0x831c, 0x2300, 0xae18,
-       0xad90, 0x001d, 0x1078, 0x8739, 0x0078, 0x8085, 0x6838, 0xd0fc,
-       0x0040, 0x804f, 0x2009, 0x0020, 0x695a, 0x0078, 0x803b, 0x0f7e,
-       0x2d78, 0x1078, 0x86d1, 0x0f7f, 0x1078, 0x8726, 0x0078, 0x8087,
-       0x0f7e, 0x2c78, 0x1078, 0x4893, 0x0f7f, 0x0040, 0x8075, 0x684c,
-       0xd0ac, 0x0040, 0x8075, 0x6024, 0xd0dc, 0x00c0, 0x8075, 0x6850,
-       0xd0bc, 0x00c0, 0x8075, 0x684c, 0xd0f4, 0x00c0, 0x8075, 0x1078,
-       0x8cfa, 0x0d7f, 0x0e7f, 0x0078, 0x8094, 0x684b, 0x0000, 0x6837,
-       0x0103, 0x6e46, 0x684c, 0xd0ac, 0x0040, 0x8085, 0x6810, 0x6914,
-       0xa115, 0x0040, 0x8085, 0x1078, 0x8233, 0x1078, 0x4982, 0x6218,
-       0x2268, 0x6a3c, 0x8211, 0x6a3e, 0x1078, 0x8cc4, 0x0d7f, 0x0e7f,
-       0x00c0, 0x8094, 0x1078, 0x753d, 0x007c, 0x0f7e, 0x6003, 0x0003,
-       0x2079, 0xa88c, 0x7c04, 0x7b00, 0x7e0c, 0x7d08, 0x6010, 0x2078,
-       0x784c, 0xd0ac, 0x0040, 0x80a8, 0x6003, 0x0002, 0x0f7f, 0x007c,
-       0x7c12, 0x7b16, 0x7e0a, 0x7d0e, 0x0f7f, 0x603f, 0x0000, 0x2c10,
-       0x1078, 0x1cab, 0x1078, 0x5c64, 0x1078, 0x61d3, 0x007c, 0x2001,
-       0xa5a2, 0x2004, 0x603e, 0x6003, 0x0004, 0x6110, 0x20e1, 0x0005,
-       0x3d18, 0x3e20, 0x2c10, 0x1078, 0x15ec, 0x007c, 0xa182, 0x0040,
-       0x0079, 0x80ca, 0x80dd, 0x80dd, 0x80dd, 0x80dd, 0x80dd, 0x80df,
-       0x8182, 0x80dd, 0x80dd, 0x8198, 0x8209, 0x80dd, 0x80dd, 0x80dd,
-       0x80dd, 0x8218, 0x80dd, 0x80dd, 0x80dd, 0x1078, 0x1328, 0x077e,
-       0x0f7e, 0x0e7e, 0x0d7e, 0x2071, 0xa88c, 0x6110, 0x2178, 0x7614,
-       0xa6b4, 0x0fff, 0x7e46, 0x7f4c, 0xc7e5, 0x7f4e, 0x6218, 0x2268,
-       0x6a3c, 0x8211, 0x6a3e, 0x86ff, 0x0040, 0x817d, 0xa694, 0xff00,
-       0xa284, 0x0c00, 0x0040, 0x8100, 0x7018, 0x7862, 0x701c, 0x785e,
-       0xa284, 0x0300, 0x0040, 0x817d, 0x1078, 0x1381, 0x1040, 0x1328,
-       0x2d00, 0x784a, 0x7f4c, 0xc7cd, 0x7f4e, 0x6837, 0x0103, 0x7838,
-       0x683a, 0x783c, 0x683e, 0x7840, 0x6842, 0x6e46, 0xa68c, 0x0c00,
-       0x0040, 0x811e, 0x7318, 0x6b62, 0x731c, 0x6b5e, 0xa68c, 0x00ff,
-       0xa186, 0x0002, 0x0040, 0x813a, 0xa186, 0x0028, 0x00c0, 0x812c,
-       0x684b, 0x001c, 0x0078, 0x813c, 0xd6dc, 0x0040, 0x8133, 0x684b,
-       0x0015, 0x0078, 0x813c, 0xd6d4, 0x0040, 0x813a, 0x684b, 0x0007,
-       0x0078, 0x813c, 0x684b, 0x0000, 0x6f4e, 0x7850, 0x6852, 0x7854,
-       0x6856, 0xa01e, 0xd6c4, 0x0040, 0x815a, 0x7328, 0x732c, 0x6b56,
-       0x83ff, 0x0040, 0x815a, 0xa38a, 0x0009, 0x0048, 0x8151, 0x2019,
-       0x0008, 0x037e, 0x2308, 0x2019, 0xa898, 0xad90, 0x0019, 0x1078,
-       0x8739, 0x037f, 0xd6cc, 0x0040, 0x817d, 0x7124, 0x695a, 0x81ff,
-       0x0040, 0x817d, 0xa192, 0x0021, 0x00c8, 0x8171, 0x2071, 0xa898,
-       0x831c, 0x2300, 0xae18, 0xad90, 0x001d, 0x1078, 0x8739, 0x0078,
-       0x817d, 0x7838, 0xd0fc, 0x0040, 0x817a, 0x2009, 0x0020, 0x695a,
-       0x0078, 0x8166, 0x2d78, 0x1078, 0x86d1, 0x0d7f, 0x0e7f, 0x0f7f,
-       0x077f, 0x007c, 0x0f7e, 0x6003, 0x0003, 0x2079, 0xa88c, 0x7c04,
-       0x7b00, 0x7e0c, 0x7d08, 0x6010, 0x2078, 0x7c12, 0x7b16, 0x7e0a,
-       0x7d0e, 0x0f7f, 0x2c10, 0x1078, 0x1cab, 0x1078, 0x6c26, 0x007c,
-       0x0d7e, 0x0f7e, 0x2c78, 0x1078, 0x4893, 0x0f7f, 0x0040, 0x81a4,
-       0x2001, 0xa5a2, 0x2004, 0x603e, 0x6003, 0x0002, 0x1078, 0x60b8,
-       0x1078, 0x61d3, 0x6110, 0x2168, 0x694c, 0xd1e4, 0x0040, 0x8207,
-       0xd1cc, 0x0040, 0x81de, 0x6948, 0x6838, 0xd0fc, 0x0040, 0x81d6,
-       0x017e, 0x684c, 0x007e, 0x6850, 0x007e, 0xad90, 0x000d, 0xa198,
-       0x000d, 0x2009, 0x0020, 0x157e, 0x21a8, 0x2304, 0x2012, 0x8318,
-       0x8210, 0x00f0, 0x81c5, 0x157f, 0x007f, 0x6852, 0x007f, 0x684e,
-       0x017f, 0x2168, 0x1078, 0x13aa, 0x0078, 0x8201, 0x017e, 0x1078,
-       0x13aa, 0x0d7f, 0x1078, 0x8726, 0x0078, 0x8201, 0x6837, 0x0103,
-       0x6944, 0xa184, 0x00ff, 0xa0b6, 0x0002, 0x0040, 0x81fd, 0xa086,
-       0x0028, 0x00c0, 0x81ef, 0x684b, 0x001c, 0x0078, 0x81ff, 0xd1dc,
-       0x0040, 0x81f6, 0x684b, 0x0015, 0x0078, 0x81ff, 0xd1d4, 0x0040,
-       0x81fd, 0x684b, 0x0007, 0x0078, 0x81ff, 0x684b, 0x0000, 0x1078,
-       0x4982, 0x1078, 0x8cc4, 0x00c0, 0x8207, 0x1078, 0x753d, 0x0d7f,
-       0x007c, 0x2019, 0x0001, 0x1078, 0x6e6c, 0x6003, 0x0002, 0x2001,
-       0xa5a2, 0x2004, 0x603e, 0x1078, 0x60b8, 0x1078, 0x61d3, 0x007c,
-       0x1078, 0x60b8, 0x1078, 0x2813, 0x0d7e, 0x6110, 0x2168, 0x1078,
-       0x8a44, 0x0040, 0x822d, 0x6837, 0x0103, 0x684b, 0x0029, 0x6847,
-       0x0000, 0x1078, 0x4982, 0x1078, 0x8bf4, 0x0d7f, 0x1078, 0x753d,
-       0x1078, 0x61d3, 0x007c, 0x684b, 0x0015, 0xd1fc, 0x0040, 0x823f,
-       0x684b, 0x0007, 0x8002, 0x8000, 0x810a, 0xa189, 0x0000, 0x6962,
-       0x685e, 0x007c, 0xa182, 0x0040, 0x0079, 0x8246, 0x8259, 0x8259,
-       0x8259, 0x8259, 0x8259, 0x825b, 0x8259, 0x8333, 0x833f, 0x8259,
-       0x8259, 0x8259, 0x8259, 0x8259, 0x8259, 0x8259, 0x8259, 0x8259,
-       0x8259, 0x1078, 0x1328, 0x077e, 0x0f7e, 0x0e7e, 0x0d7e, 0x2071,
-       0xa88c, 0x6110, 0x2178, 0x7614, 0xa6b4, 0x0fff, 0x0f7e, 0x2c78,
-       0x1078, 0x4893, 0x0f7f, 0x0040, 0x827e, 0xa684, 0x00ff, 0x00c0,
-       0x827e, 0x6024, 0xd0f4, 0x00c0, 0x827a, 0x7808, 0xa086, 0x0000,
-       0x00c0, 0x827e, 0x1078, 0x8cfa, 0x0078, 0x832e, 0x7e46, 0x7f4c,
-       0xc7e5, 0x7f4e, 0x6218, 0x2268, 0x6a3c, 0x8211, 0x6a3e, 0x86ff,
-       0x0040, 0x8323, 0xa694, 0xff00, 0xa284, 0x0c00, 0x0040, 0x8294,
-       0x7018, 0x7862, 0x701c, 0x785e, 0xa284, 0x0300, 0x0040, 0x8320,
-       0xa686, 0x0100, 0x00c0, 0x82a6, 0x2001, 0xa899, 0x2004, 0xa005,
-       0x00c0, 0x82a6, 0xc6c4, 0x7e46, 0x0078, 0x8287, 0x1078, 0x1381,
-       0x1040, 0x1328, 0x2d00, 0x784a, 0x7f4c, 0xa7bd, 0x0200, 0x7f4e,
-       0x6837, 0x0103, 0x7838, 0x683a, 0x783c, 0x683e, 0x7840, 0x6842,
-       0x6e46, 0xa68c, 0x0c00, 0x0040, 0x82c1, 0x7318, 0x6b62, 0x731c,
-       0x6b5e, 0xa68c, 0x00ff, 0xa186, 0x0002, 0x0040, 0x82dd, 0xa186,
-       0x0028, 0x00c0, 0x82cf, 0x684b, 0x001c, 0x0078, 0x82df, 0xd6dc,
-       0x0040, 0x82d6, 0x684b, 0x0015, 0x0078, 0x82df, 0xd6d4, 0x0040,
-       0x82dd, 0x684b, 0x0007, 0x0078, 0x82df, 0x684b, 0x0000, 0x6f4e,
-       0x7850, 0x6852, 0x7854, 0x6856, 0xa01e, 0xd6c4, 0x0040, 0x82fd,
-       0x7328, 0x732c, 0x6b56, 0x83ff, 0x0040, 0x82fd, 0xa38a, 0x0009,
-       0x0048, 0x82f4, 0x2019, 0x0008, 0x037e, 0x2308, 0x2019, 0xa898,
-       0xad90, 0x0019, 0x1078, 0x8739, 0x037f, 0xd6cc, 0x0040, 0x8320,
-       0x7124, 0x695a, 0x81ff, 0x0040, 0x8320, 0xa192, 0x0021, 0x00c8,
-       0x8314, 0x2071, 0xa898, 0x831c, 0x2300, 0xae18, 0xad90, 0x001d,
-       0x1078, 0x8739, 0x0078, 0x8320, 0x7838, 0xd0fc, 0x0040, 0x831d,
-       0x2009, 0x0020, 0x695a, 0x0078, 0x8309, 0x2d78, 0x1078, 0x86d1,
-       0xd6dc, 0x00c0, 0x8326, 0xa006, 0x0078, 0x832c, 0x2001, 0x0001,
-       0x2071, 0xa88c, 0x7218, 0x731c, 0x1078, 0x1645, 0x0d7f, 0x0e7f,
-       0x0f7f, 0x077f, 0x007c, 0x2001, 0xa5a2, 0x2004, 0x603e, 0x20e1,
-       0x0005, 0x3d18, 0x3e20, 0x2c10, 0x1078, 0x15ec, 0x007c, 0x2001,
-       0xa5a2, 0x2004, 0x603e, 0x0d7e, 0x6003, 0x0002, 0x6110, 0x2168,
-       0x694c, 0xd1e4, 0x0040, 0x846b, 0x603f, 0x0000, 0x0f7e, 0x2c78,
-       0x1078, 0x4893, 0x0f7f, 0x0040, 0x8385, 0x6814, 0x6910, 0xa115,
-       0x0040, 0x8385, 0x6a60, 0xa206, 0x00c0, 0x8362, 0x685c, 0xa106,
-       0x0040, 0x8385, 0x684c, 0xc0e4, 0x684e, 0x6847, 0x0000, 0x6863,
-       0x0000, 0x685f, 0x0000, 0x6024, 0xd0f4, 0x00c0, 0x837a, 0x697c,
-       0x6810, 0xa102, 0x603a, 0x6980, 0x6814, 0xa103, 0x6036, 0x6024,
-       0xc0f5, 0x6026, 0x0d7e, 0x6018, 0x2068, 0x683c, 0x8000, 0x683e,
-       0x0d7f, 0x1078, 0x8cfa, 0x0078, 0x846b, 0x694c, 0xd1cc, 0x0040,
-       0x8430, 0x6948, 0x6838, 0xd0fc, 0x0040, 0x83ea, 0x017e, 0x684c,
-       0x007e, 0x6850, 0x007e, 0x0f7e, 0x2178, 0x7944, 0xa184, 0x00ff,
-       0xa0b6, 0x0002, 0x0040, 0x83bf, 0xa086, 0x0028, 0x00c0, 0x83a6,
-       0x684b, 0x001c, 0x784b, 0x001c, 0x0078, 0x83ca, 0xd1dc, 0x0040,
-       0x83b6, 0x684b, 0x0015, 0x784b, 0x0015, 0x1078, 0x8ea5, 0x0040,
-       0x83b4, 0x7944, 0xc1dc, 0x7946, 0x0078, 0x83ca, 0xd1d4, 0x0040,
-       0x83bf, 0x684b, 0x0007, 0x784b, 0x0007, 0x0078, 0x83ca, 0x684c,
-       0xd0ac, 0x0040, 0x83ca, 0x6810, 0x6914, 0xa115, 0x0040, 0x83ca,
-       0x1078, 0x8233, 0x6848, 0x784a, 0x6860, 0x7862, 0x685c, 0x785e,
-       0xad90, 0x000d, 0xaf98, 0x000d, 0x2009, 0x0020, 0x157e, 0x21a8,
-       0x2304, 0x2012, 0x8318, 0x8210, 0x00f0, 0x83d8, 0x157f, 0x0f7f,
-       0x007f, 0x6852, 0x007f, 0x684e, 0x017f, 0x2168, 0x1078, 0x13aa,
-       0x0078, 0x8465, 0x017e, 0x0f7e, 0x2178, 0x7944, 0xa184, 0x00ff,
-       0xa0b6, 0x0002, 0x0040, 0x8417, 0xa086, 0x0028, 0x00c0, 0x83fe,
-       0x684b, 0x001c, 0x784b, 0x001c, 0x0078, 0x8422, 0xd1dc, 0x0040,
-       0x840e, 0x684b, 0x0015, 0x784b, 0x0015, 0x1078, 0x8ea5, 0x0040,
-       0x840c, 0x7944, 0xc1dc, 0x7946, 0x0078, 0x8422, 0xd1d4, 0x0040,
-       0x8417, 0x684b, 0x0007, 0x784b, 0x0007, 0x0078, 0x8422, 0x684c,
-       0xd0ac, 0x0040, 0x8422, 0x6810, 0x6914, 0xa115, 0x0040, 0x8422,
-       0x1078, 0x8233, 0x6860, 0x7862, 0x685c, 0x785e, 0x684c, 0x784e,
-       0x0f7f, 0x1078, 0x13aa, 0x0d7f, 0x1078, 0x8726, 0x0078, 0x8465,
-       0x6837, 0x0103, 0x6944, 0xa184, 0x00ff, 0xa0b6, 0x0002, 0x0040,
-       0x8456, 0xa086, 0x0028, 0x00c0, 0x8441, 0x684b, 0x001c, 0x0078,
-       0x8463, 0xd1dc, 0x0040, 0x844f, 0x684b, 0x0015, 0x1078, 0x8ea5,
-       0x0040, 0x844d, 0x6944, 0xc1dc, 0x6946, 0x0078, 0x8463, 0xd1d4,
-       0x0040, 0x8456, 0x684b, 0x0007, 0x0078, 0x8463, 0x684b, 0x0000,
-       0x684c, 0xd0ac, 0x0040, 0x8463, 0x6810, 0x6914, 0xa115, 0x0040,
-       0x8463, 0x1078, 0x8233, 0x1078, 0x4982, 0x1078, 0x8cc4, 0x00c0,
-       0x846b, 0x1078, 0x753d, 0x0d7f, 0x007c, 0x1078, 0x6010, 0x0078,
-       0x8473, 0x1078, 0x60b8, 0x1078, 0x8a44, 0x0040, 0x8492, 0x0d7e,
-       0x6110, 0x2168, 0x6837, 0x0103, 0x2009, 0xa30c, 0x210c, 0xd18c,
-       0x00c0, 0x849d, 0xd184, 0x00c0, 0x8499, 0x6108, 0x694a, 0xa18e,
-       0x0029, 0x00c0, 0x848d, 0x1078, 0xa181, 0x6847, 0x0000, 0x1078,
-       0x4982, 0x0d7f, 0x1078, 0x753d, 0x1078, 0x6109, 0x1078, 0x61d3,
-       0x007c, 0x684b, 0x0004, 0x0078, 0x848d, 0x684b, 0x0004, 0x0078,
-       0x848d, 0xa182, 0x0040, 0x0079, 0x84a5, 0x84b8, 0x84b8, 0x84b8,
-       0x84b8, 0x84b8, 0x84ba, 0x84b8, 0x84bd, 0x84b8, 0x84b8, 0x84b8,
-       0x84b8, 0x84b8, 0x84b8, 0x84b8, 0x84b8, 0x84b8, 0x84b8, 0x84b8,
-       0x1078, 0x1328, 0x1078, 0x753d, 0x007c, 0x007e, 0x027e, 0xa016,
-       0x1078, 0x15ec, 0x027f, 0x007f, 0x007c, 0xa182, 0x0085, 0x0079,
-       0x84c9, 0x84d2, 0x84d0, 0x84d0, 0x84de, 0x84d0, 0x84d0, 0x84d0,
-       0x1078, 0x1328, 0x6003, 0x0001, 0x6106, 0x1078, 0x5bf8, 0x127e,
-       0x2091, 0x8000, 0x1078, 0x6109, 0x127f, 0x007c, 0x027e, 0x057e,
-       0x0d7e, 0x0e7e, 0x2071, 0xa880, 0x7224, 0x6212, 0x7220, 0x1078,
-       0x8a30, 0x0040, 0x8503, 0x2268, 0x6800, 0xa086, 0x0000, 0x0040,
-       0x8503, 0x6018, 0x6d18, 0xa52e, 0x00c0, 0x8503, 0x0c7e, 0x2d60,
-       0x1078, 0x874a, 0x0c7f, 0x0040, 0x8503, 0x6803, 0x0002, 0x6007,
-       0x0086, 0x0078, 0x8505, 0x6007, 0x0087, 0x6003, 0x0001, 0x1078,
-       0x5bf8, 0x1078, 0x6109, 0x0f7e, 0x2278, 0x1078, 0x4893, 0x0f7f,
-       0x0040, 0x851d, 0x6824, 0xd0ec, 0x0040, 0x851d, 0x0c7e, 0x2260,
-       0x603f, 0x0000, 0x1078, 0x8cfa, 0x0c7f, 0x0e7f, 0x0d7f, 0x057f,
-       0x027f, 0x007c, 0xa186, 0x0013, 0x00c0, 0x8533, 0x6004, 0xa08a,
-       0x0085, 0x1048, 0x1328, 0xa08a, 0x008c, 0x10c8, 0x1328, 0xa082,
-       0x0085, 0x0079, 0x8542, 0xa186, 0x0027, 0x0040, 0x853b, 0xa186,
-       0x0014, 0x10c0, 0x1328, 0x1078, 0x6010, 0x1078, 0x8c01, 0x1078,
-       0x6109, 0x007c, 0x8549, 0x854b, 0x854b, 0x8549, 0x8549, 0x8549,
-       0x8549, 0x1078, 0x1328, 0x1078, 0x6010, 0x1078, 0x8c01, 0x1078,
-       0x6109, 0x007c, 0xa186, 0x0013, 0x00c0, 0x855c, 0x6004, 0xa082,
-       0x0085, 0x2008, 0x0078, 0x8597, 0xa186, 0x0027, 0x00c0, 0x857f,
-       0x1078, 0x6010, 0x1078, 0x2813, 0x0d7e, 0x6010, 0x2068, 0x1078,
-       0x8a44, 0x0040, 0x8575, 0x6837, 0x0103, 0x6847, 0x0000, 0x684b,
-       0x0029, 0x1078, 0x4982, 0x1078, 0x8bf4, 0x0d7f, 0x1078, 0x753d,
-       0x1078, 0x6109, 0x007c, 0x1078, 0x7583, 0x0078, 0x857a, 0xa186,
-       0x0014, 0x00c0, 0x857b, 0x1078, 0x6010, 0x0d7e, 0x6010, 0x2068,
-       0x1078, 0x8a44, 0x0040, 0x8575, 0x6837, 0x0103, 0x6847, 0x0000,
-       0x684b, 0x0006, 0x6850, 0xc0ec, 0x6852, 0x0078, 0x8571, 0x0079,
-       0x8599, 0x85a2, 0x85a0, 0x85a0, 0x85a0, 0x85a0, 0x85a0, 0x85bd,
-       0x1078, 0x1328, 0x1078, 0x6010, 0x6030, 0xa08c, 0xff00, 0x810f,
-       0xa186, 0x0039, 0x0040, 0x85b0, 0xa186, 0x0035, 0x00c0, 0x85b4,
-       0x2001, 0xa5a0, 0x0078, 0x85b6, 0x2001, 0xa5a1, 0x2004, 0x6016,
-       0x6003, 0x000c, 0x1078, 0x6109, 0x007c, 0x1078, 0x6010, 0x6030,
-       0xa08c, 0xff00, 0x810f, 0xa186, 0x0039, 0x0040, 0x85cb, 0xa186,
-       0x0035, 0x00c0, 0x85cf, 0x2001, 0xa5a0, 0x0078, 0x85d1, 0x2001,
-       0xa5a1, 0x2004, 0x6016, 0x6003, 0x000e, 0x1078, 0x6109, 0x007c,
-       0xa182, 0x008c, 0x00c8, 0x85e2, 0xa182, 0x0085, 0x0048, 0x85e2,
-       0x0079, 0x85e5, 0x1078, 0x7583, 0x007c, 0x85ec, 0x85ec, 0x85ec,
-       0x85ec, 0x85ee, 0x8643, 0x85ec, 0x1078, 0x1328, 0x0f7e, 0x2c78,
-       0x1078, 0x4893, 0x0f7f, 0x0040, 0x8601, 0x6030, 0xa08c, 0xff00,
-       0x810f, 0xa186, 0x0039, 0x0040, 0x865a, 0xa186, 0x0035, 0x0040,
-       0x865a, 0x0d7e, 0x1078, 0x8bf4, 0x1078, 0x8a44, 0x0040, 0x8625,
-       0x6010, 0x2068, 0x6837, 0x0103, 0x6850, 0xd0b4, 0x0040, 0x8616,
-       0x684b, 0x0006, 0xc0ec, 0x6852, 0x0078, 0x8621, 0xd0bc, 0x0040,
-       0x861d, 0x684b, 0x0002, 0x0078, 0x8621, 0x684b, 0x0005, 0x1078,
-       0x8cc0, 0x6847, 0x0000, 0x1078, 0x4982, 0x2c68, 0x1078, 0x74d7,
-       0x0040, 0x863e, 0x6003, 0x0001, 0x6007, 0x001e, 0x2009, 0xa88e,
-       0x210c, 0x6136, 0x2009, 0xa88f, 0x210c, 0x613a, 0x6918, 0x611a,
-       0x6920, 0x6122, 0x601f, 0x0001, 0x1078, 0x5bf8, 0x2d60, 0x1078,
-       0x753d, 0x0d7f, 0x007c, 0x0f7e, 0x2c78, 0x1078, 0x4893, 0x0f7f,
-       0x0040, 0x8680, 0x6030, 0xa08c, 0xff00, 0x810f, 0xa186, 0x0035,
-       0x0040, 0x865a, 0xa186, 0x001e, 0x0040, 0x865a, 0xa186, 0x0039,
-       0x00c0, 0x8680, 0x0d7e, 0x2c68, 0x1078, 0x8ef5, 0x00c0, 0x86a4,
-       0x1078, 0x74d7, 0x0040, 0x867d, 0x6106, 0x6003, 0x0001, 0x601f,
-       0x0001, 0x6918, 0x611a, 0x6928, 0x612a, 0x692c, 0x612e, 0x6930,
-       0xa18c, 0x00ff, 0x6132, 0x6934, 0x6136, 0x6938, 0x613a, 0x6920,
-       0x6122, 0x1078, 0x5bf8, 0x1078, 0x6109, 0x2d60, 0x0078, 0x86a4,
-       0x0d7e, 0x6010, 0x2068, 0x1078, 0x8a44, 0x0040, 0x86a4, 0x6837,
-       0x0103, 0x6850, 0xd0b4, 0x0040, 0x8693, 0xc0ec, 0x6852, 0x684b,
-       0x0006, 0x0078, 0x869e, 0xd0bc, 0x0040, 0x869a, 0x684b, 0x0002,
-       0x0078, 0x869e, 0x684b, 0x0005, 0x1078, 0x8cc0, 0x6847, 0x0000,
-       0x1078, 0x4982, 0x1078, 0x8bf4, 0x0d7f, 0x1078, 0x753d, 0x007c,
-       0x017e, 0x0d7e, 0x6010, 0x2068, 0x1078, 0x8a44, 0x0040, 0x86b8,
-       0x6837, 0x0103, 0x684b, 0x0028, 0x6847, 0x0000, 0x1078, 0x4982,
-       0x0d7f, 0x017f, 0xa186, 0x0013, 0x0040, 0x86ca, 0xa186, 0x0014,
-       0x0040, 0x86ca, 0xa186, 0x0027, 0x0040, 0x86ca, 0x1078, 0x7583,
-       0x0078, 0x86d0, 0x1078, 0x6010, 0x1078, 0x8c01, 0x1078, 0x6109,
-       0x007c, 0x057e, 0x067e, 0x0d7e, 0x0f7e, 0x2029, 0x0001, 0xa182,
-       0x0101, 0x00c8, 0x86dd, 0x0078, 0x86df, 0x2009, 0x0100, 0x2130,
-       0x2069, 0xa898, 0x831c, 0x2300, 0xad18, 0x2009, 0x0020, 0xaf90,
-       0x001d, 0x1078, 0x8739, 0xa6b2, 0x0020, 0x7804, 0xa06d, 0x0040,
-       0x86f3, 0x1078, 0x13aa, 0x1078, 0x1381, 0x0040, 0x871d, 0x8528,
-       0x6837, 0x0110, 0x683b, 0x0000, 0x2d20, 0x7c06, 0xa68a, 0x003d,
-       0x00c8, 0x8709, 0x2608, 0xad90, 0x000f, 0x1078, 0x8739, 0x0078,
-       0x871d, 0xa6b2, 0x003c, 0x2009, 0x003c, 0x2d78, 0xad90, 0x000f,
-       0x1078, 0x8739, 0x0078, 0x86f3, 0x0f7f, 0x852f, 0xa5ad, 0x0003,
-       0x7d36, 0xa5ac, 0x0000, 0x0078, 0x8722, 0x0f7f, 0x852f, 0xa5ad,
-       0x0003, 0x7d36, 0x0d7f, 0x067f, 0x057f, 0x007c, 0x0f7e, 0x8dff,
-       0x0040, 0x8737, 0x6804, 0xa07d, 0x0040, 0x8735, 0x6807, 0x0000,
-       0x1078, 0x4982, 0x2f68, 0x0078, 0x872a, 0x1078, 0x4982, 0x0f7f,
-       0x007c, 0x157e, 0xa184, 0x0001, 0x0040, 0x873f, 0x8108, 0x810c,
-       0x21a8, 0x2304, 0x8007, 0x2012, 0x8318, 0x8210, 0x00f0, 0x8741,
-       0x157f, 0x007c, 0x067e, 0x127e, 0x2091, 0x8000, 0x2031, 0x0001,
-       0x601c, 0xa084, 0x000f, 0x1079, 0x8766, 0x127f, 0x067f, 0x007c,
-       0x127e, 0x2091, 0x8000, 0x067e, 0x2031, 0x0000, 0x601c, 0xa084,
-       0x000f, 0x1079, 0x8766, 0x067f, 0x127f, 0x007c, 0x8780, 0x876e,
-       0x877b, 0x879c, 0x876e, 0x877b, 0x879c, 0x877b, 0x1078, 0x1328,
-       0x037e, 0x2019, 0x0010, 0x1078, 0x9a6a, 0x601f, 0x0006, 0x6003,
-       0x0007, 0x037f, 0x007c, 0xa006, 0x007c, 0xa085, 0x0001, 0x007c,
-       0x0d7e, 0x86ff, 0x00c0, 0x8797, 0x6010, 0x2068, 0x1078, 0x8a44,
-       0x0040, 0x8799, 0xa00e, 0x2001, 0x0005, 0x1078, 0x4a60, 0x1078,
-       0x8cc0, 0x1078, 0x4982, 0x1078, 0x753d, 0xa085, 0x0001, 0x0d7f,
-       0x007c, 0xa006, 0x0078, 0x8797, 0x6000, 0xa08a, 0x0010, 0x10c8,
-       0x1328, 0x1079, 0x87a4, 0x007c, 0x87b4, 0x87d4, 0x87b6, 0x87f7,
-       0x87d0, 0x87b4, 0x877b, 0x8780, 0x8780, 0x877b, 0x877b, 0x877b,
-       0x877b, 0x877b, 0x877b, 0x877b, 0x1078, 0x1328, 0x86ff, 0x00c0,
-       0x87cd, 0x0d7e, 0x6010, 0x2068, 0x1078, 0x8a44, 0x0040, 0x87c2,
-       0x1078, 0x8cc0, 0x0d7f, 0x6007, 0x0085, 0x6003, 0x000b, 0x601f,
-       0x0002, 0x1078, 0x5bf8, 0x1078, 0x6109, 0xa085, 0x0001, 0x007c,
-       0x1078, 0x1749, 0x0078, 0x87b6, 0x0e7e, 0x2071, 0xa5ab, 0x7024,
-       0xac06, 0x00c0, 0x87dd, 0x1078, 0x6dda, 0x601c, 0xa084, 0x000f,
-       0xa086, 0x0006, 0x00c0, 0x87ef, 0x087e, 0x097e, 0x2049, 0x0001,
-       0x2c40, 0x1078, 0x7058, 0x097f, 0x087f, 0x0078, 0x87f1, 0x1078,
-       0x6cd2, 0x0e7f, 0x00c0, 0x87b6, 0x1078, 0x877b, 0x007c, 0x037e,
-       0x0e7e, 0x2071, 0xa5ab, 0x703c, 0xac06, 0x00c0, 0x8807, 0x2019,
-       0x0000, 0x1078, 0x6e6c, 0x0e7f, 0x037f, 0x0078, 0x87b6, 0x1078,
-       0x719a, 0x0e7f, 0x037f, 0x00c0, 0x87b6, 0x1078, 0x877b, 0x007c,
-       0x0c7e, 0x601c, 0xa084, 0x000f, 0x1079, 0x8818, 0x0c7f, 0x007c,
-       0x8827, 0x8895, 0x89cd, 0x8832, 0x8c01, 0x8827, 0x9a5b, 0x753d,
-       0x8895, 0x1078, 0x8c3b, 0x00c0, 0x8827, 0x1078, 0x7a05, 0x007c,
-       0x1078, 0x6010, 0x1078, 0x6109, 0x1078, 0x753d, 0x007c, 0x6017,
-       0x0001, 0x007c, 0x6010, 0xa080, 0x0019, 0x2c02, 0x6000, 0xa08a,
-       0x0010, 0x10c8, 0x1328, 0x1079, 0x883e, 0x007c, 0x884e, 0x8850,
-       0x8872, 0x8884, 0x8891, 0x884e, 0x8827, 0x8827, 0x8827, 0x8884,
-       0x8884, 0x884e, 0x884e, 0x884e, 0x884e, 0x888e, 0x1078, 0x1328,
-       0x0e7e, 0x6010, 0x2070, 0x7050, 0xc0b5, 0x7052, 0x2071, 0xa5ab,
-       0x7024, 0xac06, 0x0040, 0x886e, 0x1078, 0x6cd2, 0x6007, 0x0085,
-       0x6003, 0x000b, 0x601f, 0x0002, 0x2001, 0xa5a1, 0x2004, 0x6016,
-       0x1078, 0x5bf8, 0x1078, 0x6109, 0x0e7f, 0x007c, 0x6017, 0x0001,
-       0x0078, 0x886c, 0x0d7e, 0x6010, 0x2068, 0x6850, 0xc0b5, 0x6852,
-       0x0d7f, 0x6007, 0x0085, 0x6003, 0x000b, 0x601f, 0x0002, 0x1078,
-       0x5bf8, 0x1078, 0x6109, 0x007c, 0x0d7e, 0x6017, 0x0001, 0x6010,
-       0x2068, 0x6850, 0xc0b5, 0x6852, 0x0d7f, 0x007c, 0x1078, 0x753d,
-       0x007c, 0x1078, 0x1749, 0x0078, 0x8872, 0x6000, 0xa08a, 0x0010,
-       0x10c8, 0x1328, 0x1079, 0x889d, 0x007c, 0x88ad, 0x882f, 0x88af,
-       0x88ad, 0x88af, 0x88af, 0x8828, 0x88ad, 0x8821, 0x8821, 0x88ad,
-       0x88ad, 0x88ad, 0x88ad, 0x88ad, 0x88ad, 0x1078, 0x1328, 0x0d7e,
-       0x6018, 0x2068, 0x6804, 0xa084, 0x00ff, 0x0d7f, 0xa08a, 0x000c,
-       0x10c8, 0x1328, 0x1079, 0x88bd, 0x007c, 0x88c9, 0x8971, 0x88cb,
-       0x890b, 0x88cb, 0x890b, 0x88cb, 0x88d8, 0x88c9, 0x890b, 0x88c9,
-       0x88f5, 0x1078, 0x1328, 0x6004, 0xa08e, 0x0016, 0x0040, 0x8906,
-       0xa08e, 0x0004, 0x0040, 0x8906, 0xa08e, 0x0002, 0x0040, 0x8906,
-       0x6004, 0x1078, 0x8c3b, 0x0040, 0x898c, 0xa08e, 0x0021, 0x0040,
-       0x8990, 0xa08e, 0x0022, 0x0040, 0x898c, 0xa08e, 0x003d, 0x0040,
-       0x8990, 0xa08e, 0x0039, 0x0040, 0x8994, 0xa08e, 0x0035, 0x0040,
-       0x8994, 0xa08e, 0x001e, 0x0040, 0x8908, 0xa08e, 0x0001, 0x00c0,
-       0x8904, 0x0d7e, 0x6018, 0x2068, 0x6804, 0xa084, 0x00ff, 0x0d7f,
-       0xa086, 0x0006, 0x0040, 0x8906, 0x1078, 0x2813, 0x1078, 0x7a05,
-       0x1078, 0x8c01, 0x007c, 0x0c7e, 0x0d7e, 0x6104, 0xa186, 0x0016,
-       0x0040, 0x8961, 0xa186, 0x0002, 0x00c0, 0x8934, 0x6018, 0x2068,
-       0x68a0, 0xd0bc, 0x00c0, 0x89b8, 0x6840, 0xa084, 0x00ff, 0xa005,
-       0x0040, 0x8934, 0x8001, 0x6842, 0x6013, 0x0000, 0x601f, 0x0007,
-       0x6017, 0x0398, 0x1078, 0x74d7, 0x0040, 0x8934, 0x2d00, 0x601a,
-       0x601f, 0x0001, 0x0078, 0x8961, 0x0d7f, 0x0c7f, 0x6004, 0xa08e,
-       0x0002, 0x00c0, 0x8952, 0x6018, 0xa080, 0x0028, 0x2004, 0xa086,
-       0x007e, 0x00c0, 0x8952, 0x2009, 0xa332, 0x2104, 0xc085, 0x200a,
-       0x0e7e, 0x2071, 0xa300, 0x1078, 0x41f5, 0x0e7f, 0x1078, 0x7a05,
-       0x0078, 0x8956, 0x1078, 0x7a05, 0x1078, 0x2813, 0x0e7e, 0x127e,
-       0x2091, 0x8000, 0x1078, 0x2839, 0x127f, 0x0e7f, 0x1078, 0x8c01,
-       0x007c, 0x2001, 0x0002, 0x1078, 0x443f, 0x6003, 0x0001, 0x6007,
-       0x0002, 0x1078, 0x5c45, 0x1078, 0x6109, 0x0d7f, 0x0c7f, 0x0078,
-       0x8960, 0x0c7e, 0x0d7e, 0x6104, 0xa186, 0x0016, 0x0040, 0x8961,
-       0x6018, 0x2068, 0x6840, 0xa084, 0x00ff, 0xa005, 0x0040, 0x8934,
-       0x8001, 0x6842, 0x6003, 0x0001, 0x1078, 0x5c45, 0x1078, 0x6109,
-       0x0d7f, 0x0c7f, 0x0078, 0x8960, 0x1078, 0x7a05, 0x0078, 0x8908,
-       0x1078, 0x7a28, 0x0078, 0x8908, 0x0d7e, 0x2c68, 0x6104, 0x1078,
-       0x8ef5, 0x0d7f, 0x0040, 0x89a0, 0x1078, 0x753d, 0x0078, 0x89b7,
-       0x6004, 0x8007, 0x6130, 0xa18c, 0x00ff, 0xa105, 0x6032, 0x6007,
-       0x0085, 0x6003, 0x000b, 0x601f, 0x0002, 0x6038, 0x600a, 0x2001,
-       0xa5a1, 0x2004, 0x6016, 0x1078, 0x5bf8, 0x1078, 0x6109, 0x007c,
-       0x0d7f, 0x0c7f, 0x1078, 0x7a05, 0x1078, 0x2813, 0x0e7e, 0x127e,
-       0x2091, 0x8000, 0x1078, 0x2839, 0x6013, 0x0000, 0x601f, 0x0007,
-       0x6017, 0x0398, 0x127f, 0x0e7f, 0x007c, 0x6000, 0xa08a, 0x0010,
-       0x10c8, 0x1328, 0x1079, 0x89d5, 0x007c, 0x89e5, 0x89e5, 0x89e5,
-       0x89e5, 0x89e5, 0x89e5, 0x89e5, 0x89e5, 0x89e5, 0x8827, 0x89e5,
-       0x882f, 0x89e7, 0x882f, 0x89f5, 0x89e5, 0x1078, 0x1328, 0x6004,
-       0xa086, 0x008b, 0x0040, 0x89f5, 0x6007, 0x008b, 0x6003, 0x000d,
-       0x1078, 0x5bf8, 0x1078, 0x6109, 0x007c, 0x1078, 0x8bf4, 0x1078,
-       0x8a44, 0x0040, 0x8a2d, 0x1078, 0x2813, 0x0d7e, 0x1078, 0x8a44,
-       0x0040, 0x8a0f, 0x6010, 0x2068, 0x6837, 0x0103, 0x684b, 0x0006,
-       0x6847, 0x0000, 0x6850, 0xc0ed, 0x6852, 0x1078, 0x4982, 0x2c68,
-       0x1078, 0x74d7, 0x0040, 0x8a1d, 0x6818, 0x601a, 0x0c7e, 0x2d60,
-       0x1078, 0x8c01, 0x0c7f, 0x0078, 0x8a1e, 0x2d60, 0x0d7f, 0x6013,
-       0x0000, 0x601f, 0x0001, 0x6007, 0x0001, 0x6003, 0x0001, 0x1078,
-       0x5c45, 0x1078, 0x6109, 0x0078, 0x8a2f, 0x1078, 0x8c01, 0x007c,
-       0xa284, 0x000f, 0x00c0, 0x8a41, 0xa282, 0xaa00, 0x0048, 0x8a41,
-       0x2001, 0xa315, 0x2004, 0xa202, 0x00c8, 0x8a41, 0xa085, 0x0001,
-       0x007c, 0xa006, 0x0078, 0x8a40, 0x027e, 0x0e7e, 0x2071, 0xa300,
-       0x6210, 0x7058, 0xa202, 0x0048, 0x8a56, 0x705c, 0xa202, 0x00c8,
-       0x8a56, 0xa085, 0x0001, 0x0e7f, 0x027f, 0x007c, 0xa006, 0x0078,
-       0x8a53, 0x0e7e, 0x0c7e, 0x037e, 0x007e, 0x127e, 0x2091, 0x8000,
-       0x2061, 0xaa00, 0x2071, 0xa300, 0x7344, 0x7060, 0xa302, 0x00c8,
-       0x8a83, 0x601c, 0xa206, 0x00c0, 0x8a7b, 0x1078, 0x8d66, 0x0040,
-       0x8a7b, 0x1078, 0x8c3b, 0x00c0, 0x8a77, 0x1078, 0x7a05, 0x0c7e,
-       0x1078, 0x753d, 0x0c7f, 0xace0, 0x0010, 0x7054, 0xac02, 0x00c8,
-       0x8a83, 0x0078, 0x8a64, 0x127f, 0x007f, 0x037f, 0x0c7f, 0x0e7f,
-       0x007c, 0x0e7e, 0x0c7e, 0x017e, 0xa188, 0xa434, 0x210c, 0x81ff,
-       0x0040, 0x8aa1, 0x2061, 0xaa00, 0x2071, 0xa300, 0x017e, 0x1078,
-       0x74d7, 0x017f, 0x0040, 0x8aa4, 0x611a, 0x1078, 0x2813, 0x1078,
-       0x753d, 0xa006, 0x0078, 0x8aa6, 0xa085, 0x0001, 0x017f, 0x0c7f,
-       0x0e7f, 0x007c, 0x0c7e, 0x057e, 0x127e, 0x2091, 0x8000, 0x0c7e,
-       0x1078, 0x74d7, 0x057f, 0x0040, 0x8ac3, 0x6612, 0x651a, 0x601f,
-       0x0003, 0x2009, 0x004b, 0x1078, 0x756c, 0xa085, 0x0001, 0x127f,
-       0x057f, 0x0c7f, 0x007c, 0xa006, 0x0078, 0x8abf, 0x0c7e, 0x057e,
-       0x127e, 0x2091, 0x8000, 0x62a0, 0x0c7e, 0x1078, 0x74d7, 0x057f,
-       0x0040, 0x8af1, 0x6013, 0x0000, 0x651a, 0x601f, 0x0003, 0x0c7e,
-       0x2560, 0x1078, 0x471b, 0x0c7f, 0x1078, 0x5d53, 0x077e, 0x2039,
-       0x0000, 0x1078, 0x5c78, 0x2c08, 0x1078, 0x9c38, 0x077f, 0x2009,
-       0x004c, 0x1078, 0x756c, 0xa085, 0x0001, 0x127f, 0x057f, 0x0c7f,
-       0x007c, 0xa006, 0x0078, 0x8aed, 0x0f7e, 0x0c7e, 0x047e, 0x0c7e,
-       0x1078, 0x74d7, 0x2c78, 0x0c7f, 0x0040, 0x8b0e, 0x7e12, 0x2c00,
-       0x781a, 0x781f, 0x0003, 0x2021, 0x0005, 0x1078, 0x8b4e, 0x2f60,
-       0x2009, 0x004d, 0x1078, 0x756c, 0xa085, 0x0001, 0x047f, 0x0c7f,
-       0x0f7f, 0x007c, 0x0f7e, 0x0c7e, 0x047e, 0x0c7e, 0x1078, 0x74d7,
-       0x2c78, 0x0c7f, 0x0040, 0x8b2c, 0x7e12, 0x2c00, 0x781a, 0x781f,
-       0x0003, 0x2021, 0x0005, 0x1078, 0x8b4e, 0x2f60, 0x2009, 0x004e,
-       0x1078, 0x756c, 0xa085, 0x0001, 0x047f, 0x0c7f, 0x0f7f, 0x007c,
-       0x0f7e, 0x0c7e, 0x047e, 0x0c7e, 0x1078, 0x74d7, 0x2c78, 0x0c7f,
-       0x0040, 0x8b4a, 0x7e12, 0x2c00, 0x781a, 0x781f, 0x0003, 0x2021,
-       0x0004, 0x1078, 0x8b4e, 0x2f60, 0x2009, 0x0052, 0x1078, 0x756c,
-       0xa085, 0x0001, 0x047f, 0x0c7f, 0x0f7f, 0x007c, 0x097e, 0x077e,
-       0x127e, 0x2091, 0x8000, 0x1078, 0x46a7, 0x0040, 0x8b5b, 0x2001,
-       0x8b53, 0x0078, 0x8b61, 0x1078, 0x466d, 0x0040, 0x8b6a, 0x2001,
-       0x8b5b, 0x007e, 0xa00e, 0x2400, 0x1078, 0x4a60, 0x1078, 0x4982,
-       0x007f, 0x007a, 0x2418, 0x1078, 0x5fa7, 0x62a0, 0x087e, 0x2041,
-       0x0001, 0x2039, 0x0001, 0x2608, 0x1078, 0x5d6d, 0x087f, 0x1078,
-       0x5c78, 0x2f08, 0x2648, 0x1078, 0x9c38, 0x613c, 0x81ff, 0x1040,
-       0x5e21, 0x127f, 0x077f, 0x097f, 0x007c, 0x0c7e, 0x127e, 0x2091,
-       0x8000, 0x0c7e, 0x1078, 0x74d7, 0x017f, 0x0040, 0x8b9e, 0x660a,
-       0x611a, 0x601f, 0x0001, 0x2d00, 0x6012, 0x2009, 0x001f, 0x1078,
-       0x756c, 0xa085, 0x0001, 0x127f, 0x0c7f, 0x007c, 0xa006, 0x0078,
-       0x8b9b, 0x0c7e, 0x127e, 0x2091, 0x8000, 0x0c7e, 0x1078, 0x74d7,
-       0x017f, 0x0040, 0x8bba, 0x660a, 0x611a, 0x601f, 0x0008, 0x2d00,
-       0x6012, 0x2009, 0x0021, 0x1078, 0x756c, 0xa085, 0x0001, 0x127f,
-       0x0c7f, 0x007c, 0xa006, 0x0078, 0x8bb7, 0x0c7e, 0x127e, 0x2091,
-       0x8000, 0x0c7e, 0x1078, 0x74d7, 0x017f, 0x0040, 0x8bd6, 0x660a,
-       0x611a, 0x601f, 0x0001, 0x2d00, 0x6012, 0x2009, 0x003d, 0x1078,
-       0x756c, 0xa085, 0x0001, 0x127f, 0x0c7f, 0x007c, 0xa006, 0x0078,
-       0x8bd3, 0x0c7e, 0x127e, 0x2091, 0x8000, 0x0c7e, 0x1078, 0x74d7,
-       0x017f, 0x0040, 0x8bf1, 0x611a, 0x601f, 0x0001, 0x2d00, 0x6012,
-       0x2009, 0x0000, 0x1078, 0x756c, 0xa085, 0x0001, 0x127f, 0x0c7f,
-       0x007c, 0xa006, 0x0078, 0x8bee, 0x027e, 0x0d7e, 0x6218, 0x2268,
-       0x6a3c, 0x82ff, 0x0040, 0x8bfe, 0x8211, 0x6a3e, 0x0d7f, 0x027f,
-       0x007c, 0x007e, 0x6000, 0xa086, 0x0000, 0x0040, 0x8c13, 0x6013,
-       0x0000, 0x601f, 0x0007, 0x2001, 0xa5a1, 0x2004, 0x6016, 0x1078,
-       0xa134, 0x603f, 0x0000, 0x007f, 0x007c, 0x067e, 0x0c7e, 0x0d7e,
-       0x2031, 0xa352, 0x2634, 0xd6e4, 0x0040, 0x8c23, 0x6618, 0x2660,
-       0x6e48, 0x1078, 0x461b, 0x0d7f, 0x0c7f, 0x067f, 0x007c, 0x007e,
-       0x017e, 0x6004, 0xa08e, 0x0002, 0x0040, 0x8c38, 0xa08e, 0x0003,
-       0x0040, 0x8c38, 0xa08e, 0x0004, 0x0040, 0x8c38, 0xa085, 0x0001,
-       0x017f, 0x007f, 0x007c, 0x007e, 0x0d7e, 0x6010, 0xa06d, 0x0040,
-       0x8c48, 0x6838, 0xd0fc, 0x0040, 0x8c48, 0xa006, 0x0078, 0x8c4a,
-       0xa085, 0x0001, 0x0d7f, 0x007f, 0x007c, 0x0c7e, 0x127e, 0x2091,
-       0x8000, 0x0c7e, 0x1078, 0x74d7, 0x017f, 0x0040, 0x8c67, 0x611a,
-       0x601f, 0x0001, 0x2d00, 0x6012, 0x1078, 0x2813, 0x2009, 0x0028,
-       0x1078, 0x756c, 0xa085, 0x0001, 0x127f, 0x0c7f, 0x007c, 0xa006,
-       0x0078, 0x8c64, 0xa186, 0x0015, 0x00c0, 0x8c7f, 0x2011, 0xa31f,
-       0x2204, 0xa086, 0x0074, 0x00c0, 0x8c7f, 0x1078, 0x7d0d, 0x6003,
-       0x0001, 0x6007, 0x0029, 0x1078, 0x5c45, 0x0078, 0x8c83, 0x1078,
-       0x7a05, 0x1078, 0x753d, 0x007c, 0xa186, 0x0016, 0x00c0, 0x8c8e,
-       0x2001, 0x0004, 0x1078, 0x443f, 0x0078, 0x8caf, 0xa186, 0x0015,
-       0x00c0, 0x8cb3, 0x2011, 0xa31f, 0x2204, 0xa086, 0x0014, 0x00c0,
-       0x8cb3, 0x0d7e, 0x6018, 0x2068, 0x1078, 0x457d, 0x0d7f, 0x1078,
-       0x7dba, 0x00c0, 0x8cb3, 0x0d7e, 0x6018, 0x2068, 0x6890, 0x0d7f,
-       0xa005, 0x0040, 0x8cb3, 0x2001, 0x0006, 0x1078, 0x443f, 0x1078,
-       0x7608, 0x0078, 0x8cb7, 0x1078, 0x7a05, 0x1078, 0x753d, 0x007c,
-       0x6848, 0xa086, 0x0005, 0x00c0, 0x8cbf, 0x1078, 0x8cc0, 0x007c,
-       0x6850, 0xc0ad, 0x6852, 0x007c, 0x0e7e, 0x2071, 0xa88c, 0x7014,
-       0xd0e4, 0x0040, 0x8cd5, 0x6013, 0x0000, 0x6003, 0x0001, 0x6007,
-       0x0050, 0x1078, 0x5bf8, 0x1078, 0x6109, 0x0e7f, 0x007c, 0x0c7e,
-       0x0f7e, 0x2c78, 0x1078, 0x4893, 0x0f7f, 0x0040, 0x8ce4, 0x601c,
-       0xa084, 0x000f, 0x1079, 0x8ce6, 0x0c7f, 0x007c, 0x8827, 0x8cf1,
-       0x8cf4, 0x8cf7, 0x9f00, 0x9f1c, 0x9f1f, 0x8827, 0x8827, 0x1078,
-       0x1328, 0x0005, 0x0005, 0x007c, 0x0005, 0x0005, 0x007c, 0x1078,
-       0x8cfa, 0x007c, 0x0f7e, 0x2c78, 0x1078, 0x4893, 0x0040, 0x8d29,
-       0x1078, 0x74d7, 0x00c0, 0x8d0a, 0x2001, 0xa5a2, 0x2004, 0x783e,
-       0x0078, 0x8d29, 0x7818, 0x601a, 0x781c, 0xa086, 0x0003, 0x0040,
-       0x8d17, 0x7808, 0x6036, 0x2f00, 0x603a, 0x0078, 0x8d1b, 0x7808,
-       0x603a, 0x2f00, 0x6036, 0x602a, 0x601f, 0x0001, 0x6007, 0x0035,
-       0x6003, 0x0001, 0x7920, 0x6122, 0x1078, 0x5bf8, 0x1078, 0x6109,
-       0x2f60, 0x0f7f, 0x007c, 0x017e, 0x0f7e, 0x682c, 0x6032, 0xa08e,
-       0x0001, 0x0040, 0x8d3c, 0xa086, 0x0005, 0x0040, 0x8d40, 0xa006,
-       0x602a, 0x602e, 0x0078, 0x8d51, 0x6824, 0xc0f4, 0xc0d5, 0x6826,
-       0x6810, 0x2078, 0x787c, 0x6938, 0xa102, 0x7880, 0x6934, 0xa103,
-       0x00c8, 0x8d37, 0x6834, 0x602a, 0x6838, 0xa084, 0xfffc, 0x683a,
-       0x602e, 0x2d00, 0x6036, 0x6808, 0x603a, 0x6918, 0x611a, 0x6920,
-       0x6122, 0x601f, 0x0001, 0x6007, 0x0039, 0x6003, 0x0001, 0x1078,
-       0x5bf8, 0x6803, 0x0002, 0x0f7f, 0x017f, 0x007c, 0x007e, 0x017e,
-       0x6004, 0xa08e, 0x0034, 0x0040, 0x8d8b, 0xa08e, 0x0035, 0x0040,
-       0x8d8b, 0xa08e, 0x0036, 0x0040, 0x8d8b, 0xa08e, 0x0037, 0x0040,
-       0x8d8b, 0xa08e, 0x0038, 0x0040, 0x8d8b, 0xa08e, 0x0039, 0x0040,
-       0x8d8b, 0xa08e, 0x003a, 0x0040, 0x8d8b, 0xa08e, 0x003b, 0x0040,
-       0x8d8b, 0xa085, 0x0001, 0x017f, 0x007f, 0x007c, 0x0f7e, 0x2c78,
-       0x1078, 0x4893, 0x00c0, 0x8d98, 0xa085, 0x0001, 0x0078, 0x8da7,
-       0x6024, 0xd0f4, 0x00c0, 0x8da6, 0xc0f5, 0x6026, 0x6010, 0x2078,
-       0x7828, 0x603a, 0x782c, 0x6036, 0x1078, 0x1749, 0xa006, 0x0f7f,
-       0x007c, 0x007e, 0x017e, 0x027e, 0x037e, 0x0e7e, 0x2001, 0xa59c,
-       0x200c, 0x8000, 0x2014, 0x2001, 0x0032, 0x1078, 0x5a98, 0x2001,
-       0xa5a0, 0x82ff, 0x00c0, 0x8dbe, 0x2011, 0x0002, 0x2202, 0x2001,
-       0xa59e, 0x200c, 0x8000, 0x2014, 0x2071, 0xa58c, 0x711a, 0x721e,
-       0x2001, 0x0064, 0x1078, 0x5a98, 0x2001, 0xa5a1, 0x82ff, 0x00c0,
-       0x8dd3, 0x2011, 0x0002, 0x2202, 0x2009, 0xa5a2, 0xa280, 0x000a,
-       0x200a, 0x0e7f, 0x037f, 0x027f, 0x017f, 0x007f, 0x007c, 0x007e,
-       0x0e7e, 0x2001, 0xa5a0, 0x2003, 0x0028, 0x2001, 0xa5a1, 0x2003,
-       0x0014, 0x2071, 0xa58c, 0x701b, 0x0000, 0x701f, 0x07d0, 0x2001,
-       0xa5a2, 0x2003, 0x001e, 0x0e7f, 0x007f, 0x007c, 0x0c7e, 0x127e,
-       0x2091, 0x8000, 0x0c7e, 0x1078, 0x74d7, 0x017f, 0x0040, 0x8e0e,
-       0x611a, 0x601f, 0x0001, 0x2d00, 0x6012, 0x2009, 0x0033, 0x1078,
-       0x756c, 0xa085, 0x0001, 0x127f, 0x0c7f, 0x007c, 0xa006, 0x0078,
-       0x8e0b, 0x0d7e, 0x0e7e, 0x0f7e, 0x2071, 0xa300, 0xa186, 0x0015,
-       0x00c0, 0x8e40, 0x707c, 0xa086, 0x0018, 0x00c0, 0x8e40, 0x6010,
-       0x2068, 0x6a3c, 0xd2e4, 0x00c0, 0x8e34, 0x2c78, 0x1078, 0x62c6,
-       0x0040, 0x8e48, 0x7068, 0x6a50, 0xa206, 0x00c0, 0x8e3c, 0x706c,
-       0x6a54, 0xa206, 0x00c0, 0x8e3c, 0x6218, 0xa290, 0x0028, 0x2214,
-       0x2009, 0x0000, 0x1078, 0x285b, 0x1078, 0x7608, 0x0078, 0x8e44,
-       0x1078, 0x7a05, 0x1078, 0x753d, 0x0f7f, 0x0e7f, 0x0d7f, 0x007c,
-       0x704c, 0xa080, 0x293f, 0x2004, 0x6a54, 0xa206, 0x0040, 0x8e34,
-       0x0078, 0x8e3c, 0x0c7e, 0x127e, 0x2091, 0x8000, 0x0c7e, 0x1078,
-       0x74d7, 0x017f, 0x0040, 0x8e6a, 0x611a, 0x601f, 0x0001, 0x2d00,
-       0x6012, 0x2009, 0x0043, 0x1078, 0x756c, 0xa085, 0x0001, 0x127f,
-       0x0c7f, 0x007c, 0xa006, 0x0078, 0x8e67, 0x0d7e, 0x0e7e, 0x0f7e,
-       0x2071, 0xa300, 0xa186, 0x0015, 0x00c0, 0x8e93, 0x707c, 0xa086,
-       0x0004, 0x00c0, 0x8e93, 0x6010, 0xa0e8, 0x000f, 0x2c78, 0x1078,
-       0x62c6, 0x0040, 0x8e9b, 0x7068, 0x6a08, 0xa206, 0x00c0, 0x8e8f,
-       0x706c, 0x6a0c, 0xa206, 0x00c0, 0x8e8f, 0x1078, 0x2813, 0x1078,
-       0x7608, 0x0078, 0x8e97, 0x1078, 0x7a05, 0x1078, 0x753d, 0x0f7f,
-       0x0e7f, 0x0d7f, 0x007c, 0x704c, 0xa080, 0x293f, 0x2004, 0x6a0c,
-       0xa206, 0x0040, 0x8e8d, 0x0078, 0x8e8f, 0x017e, 0x027e, 0x684c,
-       0xd0ac, 0x0040, 0x8ebd, 0x6914, 0x6a10, 0x2100, 0xa205, 0x0040,
-       0x8ebd, 0x6860, 0xa106, 0x00c0, 0x8eb9, 0x685c, 0xa206, 0x0040,
-       0x8ebd, 0x6962, 0x6a5e, 0xa085, 0x0001, 0x027f, 0x017f, 0x007c,
-       0x0e7e, 0x127e, 0x2071, 0xa300, 0x2091, 0x8000, 0x7544, 0xa582,
-       0x0001, 0x0048, 0x8ef2, 0x7048, 0x2060, 0x6000, 0xa086, 0x0000,
-       0x0040, 0x8ede, 0xace0, 0x0010, 0x7054, 0xac02, 0x00c8, 0x8eda,
-       0x0078, 0x8ecd, 0x2061, 0xaa00, 0x0078, 0x8ecd, 0x6003, 0x0008,
-       0x8529, 0x7546, 0xaca8, 0x0010, 0x7054, 0xa502, 0x00c8, 0x8eee,
-       0x754a, 0xa085, 0x0001, 0x127f, 0x0e7f, 0x007c, 0x704b, 0xaa00,
-       0x0078, 0x8ee9, 0xa006, 0x0078, 0x8eeb, 0x0c7e, 0x027e, 0x017e,
-       0xa186, 0x0035, 0x0040, 0x8eff, 0x6a34, 0x0078, 0x8f00, 0x6a28,
-       0x1078, 0x8a30, 0x0040, 0x8f29, 0x2260, 0x611c, 0xa186, 0x0003,
-       0x0040, 0x8f0e, 0xa186, 0x0006, 0x00c0, 0x8f25, 0x6834, 0xa206,
-       0x0040, 0x8f1d, 0x6838, 0xa206, 0x00c0, 0x8f25, 0x6108, 0x6834,
-       0xa106, 0x00c0, 0x8f25, 0x0078, 0x8f22, 0x6008, 0x6938, 0xa106,
-       0x00c0, 0x8f25, 0x6018, 0x6918, 0xa106, 0x017f, 0x027f, 0x0c7f,
-       0x007c, 0xa085, 0x0001, 0x0078, 0x8f25, 0x067e, 0x6000, 0xa0b2,
-       0x0010, 0x10c8, 0x1328, 0x1079, 0x8f37, 0x067f, 0x007c, 0x8f47,
-       0x93bb, 0x94d3, 0x8f47, 0x8f47, 0x8f47, 0x8f47, 0x8f47, 0x8f81,
-       0x955e, 0x8f47, 0x8f47, 0x8f47, 0x8f47, 0x8f47, 0x8f47, 0x1078,
-       0x1328, 0x067e, 0x6000, 0xa0b2, 0x0010, 0x10c8, 0x1328, 0x1079,
-       0x8f53, 0x067f, 0x007c, 0x8f63, 0x99f6, 0x8f63, 0x8f63, 0x8f63,
-       0x8f63, 0x8f63, 0x8f63, 0x99b4, 0x9a44, 0x8f63, 0xa053, 0xa087,
-       0xa053, 0xa087, 0x8f63, 0x1078, 0x1328, 0x067e, 0x6000, 0xa0b2,
-       0x0010, 0x10c8, 0x1328, 0x1079, 0x8f6f, 0x067f, 0x007c, 0x8f7f,
-       0x969f, 0x976a, 0x9798, 0x9813, 0x8f7f, 0x9919, 0x98c1, 0x956a,
-       0x9988, 0x999e, 0x8f7f, 0x8f7f, 0x8f7f, 0x8f7f, 0x8f7f, 0x1078,
-       0x1328, 0xa1b2, 0x0044, 0x10c8, 0x1328, 0x2100, 0x0079, 0x8f88,
-       0x8fc8, 0x919a, 0x8fc8, 0x8fc8, 0x8fc8, 0x91a2, 0x8fc8, 0x8fc8,
-       0x8fc8, 0x8fc8, 0x8fc8, 0x8fc8, 0x8fc8, 0x8fc8, 0x8fc8, 0x8fc8,
-       0x8fc8, 0x8fc8, 0x8fc8, 0x8fc8, 0x8fc8, 0x8fc8, 0x8fc8, 0x8fca,
-       0x902d, 0x9038, 0x9081, 0x909c, 0x911b, 0x918b, 0x8fc8, 0x8fc8,
-       0x91a6, 0x8fc8, 0x8fc8, 0x91b5, 0x91bc, 0x8fc8, 0x8fc8, 0x8fc8,
-       0x8fc8, 0x8fc8, 0x91ea, 0x8fc8, 0x8fc8, 0x91f5, 0x8fc8, 0x8fc8,
-       0x8fc8, 0x8fc8, 0x8fc8, 0x8fc8, 0x920a, 0x8fc8, 0x8fc8, 0x8fc8,
-       0x9291, 0x8fc8, 0x8fc8, 0x8fc8, 0x8fc8, 0x8fc8, 0x8fc8, 0x9305,
-       0x1078, 0x1328, 0x1078, 0x4897, 0x00c0, 0x8fd7, 0x2001, 0xa332,
-       0x2004, 0xa084, 0x0009, 0xa086, 0x0008, 0x00c0, 0x8fdf, 0x6007,
-       0x0009, 0x602b, 0x0009, 0x6013, 0x0000, 0x0078, 0x9195, 0x1078,
-       0x4887, 0x0e7e, 0x0c7e, 0x037e, 0x027e, 0x017e, 0x6218, 0x2270,
-       0x72a0, 0x027e, 0x2019, 0x0029, 0x1078, 0x5d53, 0x077e, 0x2039,
-       0x0000, 0x1078, 0x5c78, 0x2c08, 0x1078, 0x9c38, 0x077f, 0x017f,
-       0x2e60, 0x1078, 0x471b, 0x017f, 0x027f, 0x037f, 0x0c7f, 0x0e7f,
-       0x6618, 0x0c7e, 0x2660, 0x1078, 0x4513, 0x0c7f, 0xa6b0, 0x0001,
-       0x2634, 0xa684, 0x00ff, 0xa082, 0x0006, 0x0048, 0x901f, 0x1078,
-       0x9b6c, 0x00c0, 0x907b, 0x1078, 0x9afd, 0x00c0, 0x901b, 0x6007,
-       0x0008, 0x0078, 0x9195, 0x6007, 0x0009, 0x0078, 0x9195, 0x1078,
-       0x9d45, 0x0040, 0x9029, 0x1078, 0x9b6c, 0x0040, 0x9013, 0x0078,
-       0x907b, 0x6013, 0x1900, 0x0078, 0x901b, 0x6106, 0x1078, 0x9aa8,
-       0x6007, 0x0006, 0x0078, 0x9195, 0x6007, 0x0007, 0x0078, 0x9195,
-       0x1078, 0xa0bf, 0x00c0, 0x9340, 0x0d7e, 0x6618, 0x2668, 0x6e04,
-       0xa6b4, 0xff00, 0x8637, 0xa686, 0x0006, 0x0040, 0x905d, 0xa686,
-       0x0004, 0x0040, 0x905d, 0x6e04, 0xa6b4, 0x00ff, 0xa686, 0x0006,
-       0x0040, 0x905d, 0xa686, 0x0004, 0x0040, 0x905d, 0xa686, 0x0005,
-       0x0040, 0x905d, 0x0d7f, 0x0078, 0x907b, 0x1078, 0x9bd2, 0x00c0,
-       0x9076, 0xa686, 0x0006, 0x00c0, 0x906f, 0x027e, 0x6218, 0xa290,
-       0x0028, 0x2214, 0x2009, 0x0000, 0x1078, 0x285b, 0x027f, 0x1078,
-       0x457d, 0x6007, 0x000a, 0x0d7f, 0x0078, 0x9195, 0x6007, 0x000b,
-       0x0d7f, 0x0078, 0x9195, 0x1078, 0x2813, 0x6007, 0x0001, 0x0078,
-       0x9195, 0x1078, 0xa0bf, 0x00c0, 0x9340, 0x6618, 0x0d7e, 0x2668,
-       0x6e04, 0x0d7f, 0xa686, 0x0707, 0x0040, 0x907b, 0x027e, 0x6218,
-       0xa290, 0x0028, 0x2214, 0x2009, 0x0000, 0x1078, 0x285b, 0x027f,
-       0x6007, 0x000c, 0x0078, 0x9195, 0x1078, 0x4897, 0x00c0, 0x90a9,
-       0x2001, 0xa332, 0x2004, 0xa084, 0x0009, 0xa086, 0x0008, 0x00c0,
-       0x90b1, 0x6007, 0x0009, 0x602b, 0x0009, 0x6013, 0x0000, 0x0078,
-       0x9195, 0x1078, 0x4887, 0x6618, 0xa6b0, 0x0001, 0x2634, 0xa684,
-       0x00ff, 0xa082, 0x0006, 0x0048, 0x90f5, 0xa6b4, 0xff00, 0x8637,
-       0xa686, 0x0004, 0x0040, 0x90c8, 0xa686, 0x0006, 0x00c0, 0x907b,
-       0x1078, 0x9be1, 0x00c0, 0x90d0, 0x6007, 0x000e, 0x0078, 0x9195,
-       0x047e, 0x6418, 0xa4a0, 0x0028, 0x2424, 0xa4a4, 0x00ff, 0x8427,
-       0x047e, 0x1078, 0x2813, 0x047f, 0x017e, 0xa006, 0x2009, 0xa352,
-       0x210c, 0xd1a4, 0x0040, 0x90ef, 0x2009, 0x0029, 0x1078, 0x9ec0,
-       0x6018, 0x0d7e, 0x2068, 0x6800, 0xc0e5, 0x6802, 0x0d7f, 0x017f,
-       0x047f, 0x6007, 0x0001, 0x0078, 0x9195, 0x2001, 0x0001, 0x1078,
-       0x442b, 0x157e, 0x017e, 0x027e, 0x037e, 0x20a9, 0x0004, 0x2019,
-       0xa305, 0x2011, 0xa890, 0x1078, 0x7e55, 0x037f, 0x027f, 0x017f,
-       0x157f, 0xa005, 0x0040, 0x9115, 0xa6b4, 0xff00, 0x8637, 0xa686,
-       0x0006, 0x0040, 0x90c8, 0x0078, 0x907b, 0x6013, 0x1900, 0x6007,
-       0x0009, 0x0078, 0x9195, 0x1078, 0x4897, 0x00c0, 0x9128, 0x2001,
-       0xa332, 0x2004, 0xa084, 0x0009, 0xa086, 0x0008, 0x00c0, 0x9130,
-       0x6007, 0x0009, 0x602b, 0x0009, 0x6013, 0x0000, 0x0078, 0x9195,
-       0x1078, 0x4887, 0x6618, 0xa6b0, 0x0001, 0x2634, 0xa684, 0x00ff,
-       0xa082, 0x0006, 0x0048, 0x9178, 0xa6b4, 0xff00, 0x8637, 0xa686,
-       0x0004, 0x0040, 0x9147, 0xa686, 0x0006, 0x00c0, 0x907b, 0x1078,
-       0x9c0c, 0x00c0, 0x9153, 0x1078, 0x9afd, 0x00c0, 0x9153, 0x6007,
-       0x0010, 0x0078, 0x9195, 0x047e, 0x6418, 0xa4a0, 0x0028, 0x2424,
-       0xa4a4, 0x00ff, 0x8427, 0x047e, 0x1078, 0x2813, 0x047f, 0x017e,
-       0xa006, 0x2009, 0xa352, 0x210c, 0xd1a4, 0x0040, 0x9172, 0x2009,
-       0x0029, 0x1078, 0x9ec0, 0x6018, 0x0d7e, 0x2068, 0x6800, 0xc0e5,
-       0x6802, 0x0d7f, 0x017f, 0x047f, 0x6007, 0x0001, 0x0078, 0x9195,
-       0x1078, 0x9d45, 0x0040, 0x9185, 0xa6b4, 0xff00, 0x8637, 0xa686,
-       0x0006, 0x0040, 0x9147, 0x0078, 0x907b, 0x6013, 0x1900, 0x6007,
-       0x0009, 0x0078, 0x9195, 0x1078, 0xa0bf, 0x00c0, 0x9340, 0x1078,
-       0x9343, 0x00c0, 0x907b, 0x6007, 0x0012, 0x6003, 0x0001, 0x1078,
-       0x5c45, 0x007c, 0x6007, 0x0001, 0x6003, 0x0001, 0x1078, 0x5c45,
-       0x0078, 0x9199, 0x6007, 0x0005, 0x0078, 0x919c, 0x1078, 0xa0bf,
-       0x00c0, 0x9340, 0x1078, 0x9343, 0x00c0, 0x907b, 0x6007, 0x0020,
-       0x6003, 0x0001, 0x1078, 0x5c45, 0x007c, 0x6007, 0x0023, 0x6003,
-       0x0001, 0x1078, 0x5c45, 0x007c, 0x1078, 0xa0bf, 0x00c0, 0x9340,
-       0x1078, 0x9343, 0x00c0, 0x907b, 0x017e, 0x027e, 0x2011, 0xa890,
-       0x2214, 0x2c08, 0x1078, 0x9e8c, 0x00c0, 0x91de, 0x2160, 0x6007,
-       0x0026, 0x6013, 0x1700, 0x2011, 0xa889, 0x2214, 0xa296, 0xffff,
-       0x00c0, 0x91e3, 0x6007, 0x0025, 0x0078, 0x91e3, 0x1078, 0x753d,
-       0x2160, 0x6007, 0x0025, 0x6003, 0x0001, 0x1078, 0x5c45, 0x027f,
-       0x017f, 0x007c, 0x6106, 0x1078, 0x9363, 0x6007, 0x002b, 0x0078,
-       0x9195, 0x6007, 0x002c, 0x0078, 0x9195, 0x1078, 0xa0bf, 0x00c0,
-       0x9340, 0x1078, 0x9343, 0x00c0, 0x907b, 0x6106, 0x1078, 0x9368,
-       0x00c0, 0x9206, 0x6007, 0x002e, 0x0078, 0x9195, 0x6007, 0x002f,
-       0x0078, 0x9195, 0x0e7e, 0x0d7e, 0x0c7e, 0x6018, 0xa080, 0x0001,
-       0x200c, 0xa184, 0x00ff, 0xa086, 0x0006, 0x0040, 0x9223, 0xa184,
-       0xff00, 0x8007, 0xa086, 0x0006, 0x0040, 0x9223, 0x0c7f, 0x0d7f,
-       0x0e7f, 0x0078, 0x919a, 0x2001, 0xa371, 0x2004, 0xd0e4, 0x0040,
-       0x928d, 0x2071, 0xa88c, 0x7010, 0x6036, 0x7014, 0x603a, 0x7108,
-       0x720c, 0x2001, 0xa352, 0x2004, 0xd0a4, 0x0040, 0x9241, 0x6018,
-       0x2068, 0x6810, 0xa106, 0x00c0, 0x9241, 0x6814, 0xa206, 0x0040,
-       0x9265, 0x2001, 0xa352, 0x2004, 0xd0ac, 0x00c0, 0x9281, 0x2069,
-       0xa300, 0x686c, 0xa206, 0x00c0, 0x9281, 0x6868, 0xa106, 0x00c0,
-       0x9281, 0x7210, 0x1078, 0x8a30, 0x0040, 0x9287, 0x1078, 0x9f31,
-       0x0040, 0x9287, 0x622a, 0x6007, 0x0036, 0x6003, 0x0001, 0x1078,
-       0x5bf8, 0x0c7f, 0x0d7f, 0x0e7f, 0x007c, 0x7214, 0xa286, 0xffff,
-       0x0040, 0x9277, 0x1078, 0x8a30, 0x0040, 0x9287, 0xa280, 0x0002,
-       0x2004, 0x7110, 0xa106, 0x00c0, 0x9287, 0x0078, 0x9252, 0x7210,
-       0x2c08, 0x1078, 0x9e8c, 0x2c10, 0x2160, 0x0040, 0x9287, 0x0078,
-       0x9252, 0x6007, 0x0037, 0x6013, 0x1500, 0x0078, 0x925d, 0x6007,
-       0x0037, 0x6013, 0x1700, 0x0078, 0x925d, 0x6007, 0x0012, 0x0078,
-       0x925d, 0x6018, 0xa080, 0x0001, 0x2004, 0xa084, 0xff00, 0x8007,
-       0xa086, 0x0006, 0x00c0, 0x919a, 0x0e7e, 0x0d7e, 0x0c7e, 0x2001,
-       0xa371, 0x2004, 0xd0e4, 0x0040, 0x92fd, 0x2069, 0xa300, 0x2071,
-       0xa88c, 0x7008, 0x6036, 0x720c, 0x623a, 0xa286, 0xffff, 0x00c0,
-       0x92ba, 0x7208, 0x0c7e, 0x2c08, 0x1078, 0x9e8c, 0x2c10, 0x0c7f,
-       0x0040, 0x92f1, 0x1078, 0x8a30, 0x0040, 0x92f1, 0x0c7e, 0x027e,
-       0x2260, 0x1078, 0x874a, 0x027f, 0x0c7f, 0x7118, 0xa18c, 0xff00,
-       0x810f, 0xa186, 0x0001, 0x0040, 0x92db, 0xa186, 0x0005, 0x0040,
-       0x92d5, 0xa186, 0x0007, 0x00c0, 0x92e5, 0xa280, 0x0004, 0x2004,
-       0xa005, 0x0040, 0x92e5, 0x057e, 0x7510, 0x7614, 0x1078, 0x9f46,
-       0x057f, 0x0c7f, 0x0d7f, 0x0e7f, 0x007c, 0x6007, 0x003b, 0x602b,
-       0x0009, 0x6013, 0x2a00, 0x6003, 0x0001, 0x1078, 0x5bf8, 0x0078,
-       0x92e1, 0x6007, 0x003b, 0x602b, 0x0009, 0x6013, 0x1700, 0x6003,
-       0x0001, 0x1078, 0x5bf8, 0x0078, 0x92e1, 0x6007, 0x003b, 0x602b,
-       0x000b, 0x6013, 0x0000, 0x0078, 0x925d, 0x0e7e, 0x027e, 0x1078,
-       0x4897, 0x0040, 0x933a, 0x1078, 0x4887, 0x1078, 0xa148, 0x00c0,
-       0x9338, 0x2071, 0xa300, 0x70c8, 0xc085, 0x70ca, 0x0f7e, 0x2079,
-       0x0100, 0x7294, 0xa284, 0x00ff, 0x706a, 0x78e6, 0xa284, 0xff00,
-       0x726c, 0xa205, 0x706e, 0x78ea, 0x0f7f, 0x70d3, 0x0000, 0x2001,
-       0xa352, 0x2004, 0xd0a4, 0x0040, 0x9331, 0x2011, 0xa5c4, 0x2013,
-       0x07d0, 0xd0ac, 0x00c0, 0x933a, 0x1078, 0x260d, 0x0078, 0x933a,
-       0x1078, 0xa178, 0x027f, 0x0e7f, 0x1078, 0x753d, 0x0078, 0x9199,
-       0x1078, 0x753d, 0x007c, 0x0d7e, 0x067e, 0x6618, 0x2668, 0x6e04,
-       0xa6b4, 0xff00, 0x8637, 0xa686, 0x0006, 0x0040, 0x9360, 0xa686,
-       0x0004, 0x0040, 0x9360, 0x6e04, 0xa6b4, 0x00ff, 0xa686, 0x0006,
-       0x0040, 0x9360, 0xa686, 0x0004, 0x0040, 0x9360, 0xa085, 0x0001,
-       0x067f, 0x0d7f, 0x007c, 0x0d7e, 0x1078, 0x9397, 0x0d7f, 0x007c,
-       0x0d7e, 0x1078, 0x93a6, 0x00c0, 0x9390, 0x680c, 0xa08c, 0xff00,
-       0x6820, 0xa084, 0x00ff, 0xa115, 0x6212, 0x6824, 0x602a, 0xd1e4,
-       0x0040, 0x937e, 0x2009, 0x0001, 0x0078, 0x938c, 0xd1ec, 0x0040,
-       0x9390, 0x6920, 0xa18c, 0x00ff, 0x6824, 0x1078, 0x24e3, 0x00c0,
-       0x9390, 0x2110, 0x2009, 0x0000, 0x1078, 0x285b, 0x0078, 0x9394,
-       0xa085, 0x0001, 0x0078, 0x9395, 0xa006, 0x0d7f, 0x007c, 0x2069,
-       0xa88d, 0x6800, 0xa082, 0x0010, 0x00c8, 0x93a4, 0x6013, 0x0000,
-       0xa085, 0x0001, 0x0078, 0x93a5, 0xa006, 0x007c, 0x6013, 0x0000,
-       0x2069, 0xa88c, 0x6808, 0xa084, 0xff00, 0xa086, 0x0800, 0x00c0,
-       0x93ba, 0x6800, 0xa084, 0x00ff, 0xa08e, 0x0014, 0x0040, 0x93ba,
-       0xa08e, 0x0010, 0x007c, 0x6004, 0xa0b2, 0x0044, 0x10c8, 0x1328,
-       0xa1b6, 0x0013, 0x00c0, 0x93c7, 0x2008, 0x0079, 0x93da, 0xa1b6,
-       0x0027, 0x0040, 0x93cf, 0xa1b6, 0x0014, 0x10c0, 0x1328, 0x2001,
-       0x0007, 0x1078, 0x4472, 0x1078, 0x6010, 0x1078, 0x8c01, 0x1078,
-       0x6109, 0x007c, 0x941a, 0x941c, 0x941a, 0x941a, 0x941a, 0x941c,
-       0x9424, 0x94ae, 0x9471, 0x94ae, 0x9485, 0x94ae, 0x9424, 0x94ae,
-       0x94a6, 0x94ae, 0x94a6, 0x94ae, 0x94ae, 0x941a, 0x941a, 0x941a,
-       0x941a, 0x941a, 0x941a, 0x941a, 0x941a, 0x941a, 0x941a, 0x941a,
-       0x941c, 0x941a, 0x94ae, 0x941a, 0x941a, 0x94ae, 0x941a, 0x94ae,
-       0x94ae, 0x941a, 0x941a, 0x941a, 0x941a, 0x94ae, 0x94ae, 0x941a,
-       0x94ae, 0x94ae, 0x941a, 0x941a, 0x941a, 0x941a, 0x941a, 0x941c,
-       0x94ae, 0x94ae, 0x941a, 0x941a, 0x94ae, 0x94ae, 0x941a, 0x941a,
-       0x941a, 0x941a, 0x1078, 0x1328, 0x1078, 0x6010, 0x6003, 0x0002,
-       0x1078, 0x6109, 0x0078, 0x94b4, 0x0f7e, 0x2079, 0xa351, 0x7804,
-       0x0f7f, 0xd0ac, 0x00c0, 0x94ae, 0x2001, 0x0000, 0x1078, 0x442b,
-       0x6018, 0xa080, 0x0004, 0x2004, 0xa086, 0x00ff, 0x0040, 0x94ae,
-       0x0c7e, 0x6018, 0x2060, 0x6000, 0xd0f4, 0x00c0, 0x9448, 0x6010,
-       0xa005, 0x0040, 0x9448, 0x0c7f, 0x1078, 0x35f7, 0x0078, 0x94ae,
-       0x0c7f, 0x2001, 0xa300, 0x2004, 0xa086, 0x0002, 0x00c0, 0x9457,
-       0x0f7e, 0x2079, 0xa300, 0x788c, 0x8000, 0x788e, 0x0f7f, 0x2001,
-       0x0002, 0x1078, 0x443f, 0x1078, 0x6010, 0x601f, 0x0001, 0x6003,
-       0x0001, 0x6007, 0x0002, 0x1078, 0x5c45, 0x1078, 0x6109, 0x0c7e,
-       0x6118, 0x2160, 0x2009, 0x0001, 0x1078, 0x58e1, 0x0c7f, 0x0078,
-       0x94b4, 0x6618, 0x0d7e, 0x2668, 0x6e04, 0x0d7f, 0xa6b4, 0xff00,
-       0x8637, 0xa686, 0x0006, 0x0040, 0x94ae, 0xa686, 0x0004, 0x0040,
-       0x94ae, 0x2001, 0x0004, 0x0078, 0x94ac, 0x2001, 0xa300, 0x2004,
-       0xa086, 0x0003, 0x00c0, 0x948e, 0x1078, 0x35f7, 0x2001, 0x0006,
-       0x1078, 0x94b5, 0x6618, 0x0d7e, 0x2668, 0x6e04, 0x0d7f, 0xa6b4,
-       0xff00, 0x8637, 0xa686, 0x0006, 0x0040, 0x94ae, 0x2001, 0x0006,
-       0x0078, 0x94ac, 0x2001, 0x0004, 0x0078, 0x94ac, 0x2001, 0x0006,
-       0x1078, 0x94b5, 0x0078, 0x94ae, 0x1078, 0x4472, 0x1078, 0x6010,
-       0x1078, 0x753d, 0x1078, 0x6109, 0x007c, 0x017e, 0x0d7e, 0x6118,
-       0x2168, 0x6900, 0xd184, 0x0040, 0x94d0, 0x6104, 0xa18e, 0x000a,
-       0x00c0, 0x94c8, 0x699c, 0xd1a4, 0x00c0, 0x94c8, 0x2001, 0x0007,
-       0x1078, 0x443f, 0x2001, 0x0000, 0x1078, 0x442b, 0x1078, 0x2839,
-       0x0d7f, 0x017f, 0x007c, 0x0d7e, 0x6618, 0x2668, 0x6804, 0xa084,
-       0xff00, 0x8007, 0x0d7f, 0xa0b2, 0x000c, 0x10c8, 0x1328, 0xa1b6,
-       0x0015, 0x00c0, 0x94e7, 0x1079, 0x94ee, 0x0078, 0x94ed, 0xa1b6,
-       0x0016, 0x10c0, 0x1328, 0x1079, 0x94fa, 0x007c, 0x7ad0, 0x7ad0,
-       0x7ad0, 0x7ad0, 0x7ad0, 0x7ad0, 0x9547, 0x9506, 0x7ad0, 0x7ad0,
-       0x7ad0, 0x7ad0, 0x7ad0, 0x7ad0, 0x7ad0, 0x7ad0, 0x7ad0, 0x7ad0,
-       0x9547, 0x954f, 0x7ad0, 0x7ad0, 0x7ad0, 0x7ad0, 0x0f7e, 0x2079,
-       0xa351, 0x7804, 0xd0ac, 0x00c0, 0x952d, 0x6018, 0xa07d, 0x0040,
-       0x952d, 0x7800, 0xd0f4, 0x00c0, 0x9519, 0x7810, 0xa005, 0x00c0,
-       0x952d, 0x2001, 0x0000, 0x1078, 0x442b, 0x2001, 0x0002, 0x1078,
-       0x443f, 0x601f, 0x0001, 0x6003, 0x0001, 0x6007, 0x0002, 0x1078,
-       0x5c45, 0x1078, 0x6109, 0x0078, 0x9545, 0x2011, 0xa883, 0x2204,
-       0x8211, 0x220c, 0x1078, 0x24e3, 0x00c0, 0x9545, 0x0c7e, 0x1078,
-       0x4501, 0x0040, 0x9540, 0x0c7f, 0x1078, 0x753d, 0x0078, 0x9545,
-       0x1078, 0x4235, 0x0c7f, 0x1078, 0x753d, 0x0f7f, 0x007c, 0x6604,
-       0xa6b6, 0x001e, 0x00c0, 0x954e, 0x1078, 0x753d, 0x007c, 0x1078,
-       0x7d0a, 0x00c0, 0x955b, 0x6003, 0x0001, 0x6007, 0x0001, 0x1078,
-       0x5c45, 0x0078, 0x955d, 0x1078, 0x753d, 0x007c, 0x6004, 0xa08a,
-       0x0044, 0x10c8, 0x1328, 0x1078, 0x6010, 0x1078, 0x8c01, 0x1078,
-       0x6109, 0x007c, 0xa182, 0x0040, 0x0079, 0x956e, 0x9581, 0x9581,
-       0x9581, 0x9581, 0x9583, 0x9581, 0x9581, 0x9581, 0x9581, 0x9581,
-       0x9581, 0x9581, 0x9581, 0x9581, 0x9581, 0x9581, 0x9581, 0x9581,
-       0x9581, 0x1078, 0x1328, 0x0d7e, 0x0e7e, 0x0f7e, 0x157e, 0x047e,
-       0x027e, 0x6218, 0xa280, 0x002b, 0x2004, 0xa005, 0x0040, 0x9594,
-       0x2021, 0x0000, 0x1078, 0xa111, 0x6106, 0x2071, 0xa880, 0x7444,
-       0xa4a4, 0xff00, 0x0040, 0x95eb, 0xa486, 0x2000, 0x00c0, 0x95a6,
-       0x2009, 0x0001, 0x2011, 0x0200, 0x1078, 0x5a6d, 0x1078, 0x1381,
-       0x1040, 0x1328, 0x6003, 0x0007, 0x2d00, 0x6837, 0x010d, 0x6803,
-       0x0000, 0x683b, 0x0000, 0x6c5a, 0x2c00, 0x685e, 0x6008, 0x68b2,
-       0x6018, 0x2078, 0x78a0, 0x8007, 0x7130, 0x694a, 0x017e, 0xa084,
-       0xff00, 0x6846, 0x684f, 0x0000, 0x6857, 0x0036, 0x1078, 0x4982,
-       0x017f, 0xa486, 0x2000, 0x00c0, 0x95d3, 0x2019, 0x0017, 0x1078,
-       0x9e3b, 0x0078, 0x9645, 0xa486, 0x0400, 0x00c0, 0x95dd, 0x2019,
-       0x0002, 0x1078, 0x9dec, 0x0078, 0x9645, 0xa486, 0x0200, 0x00c0,
-       0x95e3, 0x1078, 0x9dd1, 0xa486, 0x1000, 0x00c0, 0x95e9, 0x1078,
-       0x9e20, 0x0078, 0x9645, 0x2069, 0xa62d, 0x6a00, 0xd284, 0x0040,
-       0x969b, 0xa284, 0x0300, 0x00c0, 0x9693, 0x6804, 0xa005, 0x0040,
-       0x9683, 0x2d78, 0x6003, 0x0007, 0x1078, 0x1366, 0x0040, 0x964c,
-       0x7800, 0xd08c, 0x00c0, 0x9607, 0x7804, 0x8001, 0x7806, 0x6013,
-       0x0000, 0x6803, 0x0000, 0x6837, 0x0116, 0x683b, 0x0000, 0x6008,
-       0x68b2, 0x2c00, 0x684a, 0x6018, 0x2078, 0x78a0, 0x8007, 0x7130,
-       0x6986, 0x6846, 0x6853, 0x003d, 0x7244, 0xa294, 0x0003, 0xa286,
-       0x0002, 0x00c0, 0x9627, 0x684f, 0x0040, 0x0078, 0x9631, 0xa286,
-       0x0001, 0x00c0, 0x962f, 0x684f, 0x0080, 0x0078, 0x9631, 0x684f,
-       0x0000, 0x20a9, 0x000a, 0x2001, 0xa890, 0xad90, 0x0015, 0x200c,
-       0x810f, 0x2112, 0x8000, 0x8210, 0x00f0, 0x9637, 0x200c, 0x6982,
-       0x8000, 0x200c, 0x697e, 0x1078, 0x4982, 0x027f, 0x047f, 0x157f,
-       0x0f7f, 0x0e7f, 0x0d7f, 0x007c, 0x6013, 0x0100, 0x6003, 0x0001,
-       0x6007, 0x0041, 0x1078, 0x5bf8, 0x1078, 0x6109, 0x0078, 0x9645,
-       0x2069, 0xa892, 0x2d04, 0xa084, 0xff00, 0xa086, 0x1200, 0x00c0,
-       0x9677, 0x2069, 0xa880, 0x686c, 0xa084, 0x00ff, 0x017e, 0x6110,
-       0xa18c, 0x0700, 0xa10d, 0x6112, 0x017f, 0x6003, 0x0001, 0x6007,
-       0x0043, 0x1078, 0x5bf8, 0x1078, 0x6109, 0x0078, 0x9645, 0x6013,
-       0x0200, 0x6003, 0x0001, 0x6007, 0x0041, 0x1078, 0x5bf8, 0x1078,
-       0x6109, 0x0078, 0x9645, 0x6013, 0x0300, 0x0078, 0x9689, 0x6013,
-       0x0100, 0x6003, 0x0001, 0x6007, 0x0041, 0x1078, 0x5bf8, 0x1078,
-       0x6109, 0x0078, 0x9645, 0x6013, 0x0500, 0x0078, 0x9689, 0x6013,
-       0x0600, 0x0078, 0x9658, 0x6013, 0x0200, 0x0078, 0x9658, 0xa186,
-       0x0013, 0x00c0, 0x96b1, 0x6004, 0xa08a, 0x0040, 0x1048, 0x1328,
-       0xa08a, 0x0053, 0x10c8, 0x1328, 0xa082, 0x0040, 0x2008, 0x0079,
-       0x9725, 0xa186, 0x0051, 0x0040, 0x96be, 0xa186, 0x0047, 0x00c0,
-       0x96d7, 0x6004, 0xa086, 0x0041, 0x0040, 0x96e5, 0x2001, 0x0109,
-       0x2004, 0xd084, 0x0040, 0x96e5, 0x127e, 0x2091, 0x2200, 0x007e,
-       0x017e, 0x027e, 0x1078, 0x5ad2, 0x027f, 0x017f, 0x007f, 0x127f,
-       0x6000, 0xa086, 0x0002, 0x00c0, 0x96e5, 0x0078, 0x976a, 0xa186,
-       0x0027, 0x0040, 0x96df, 0xa186, 0x0014, 0x10c0, 0x1328, 0x6004,
-       0xa082, 0x0040, 0x2008, 0x0079, 0x96e8, 0x1078, 0x7583, 0x007c,
-       0x96fb, 0x96fd, 0x96fd, 0x96fb, 0x96fb, 0x96fb, 0x96fb, 0x96fb,
-       0x96fb, 0x96fb, 0x96fb, 0x96fb, 0x96fb, 0x96fb, 0x96fb, 0x96fb,
-       0x96fb, 0x96fb, 0x96fb, 0x1078, 0x1328, 0x1078, 0x6010, 0x1078,
-       0x6109, 0x037e, 0x0d7e, 0x6010, 0xa06d, 0x0040, 0x9722, 0xad84,
-       0xf000, 0x0040, 0x9722, 0x6003, 0x0002, 0x6018, 0x2004, 0xd0bc,
-       0x00c0, 0x9722, 0x2019, 0x0004, 0x1078, 0x9e70, 0x6013, 0x0000,
-       0x6014, 0xa005, 0x00c0, 0x9720, 0x2001, 0xa5a1, 0x2004, 0x6016,
-       0x6003, 0x0007, 0x0d7f, 0x037f, 0x007c, 0x9738, 0x9757, 0x9741,
-       0x9764, 0x9738, 0x9738, 0x9738, 0x9738, 0x9738, 0x9738, 0x9738,
-       0x9738, 0x9738, 0x9738, 0x9738, 0x9738, 0x9738, 0x9738, 0x9738,
-       0x1078, 0x1328, 0x6010, 0xa088, 0x0013, 0x2104, 0xa085, 0x0400,
-       0x200a, 0x1078, 0x6010, 0x6010, 0xa080, 0x0013, 0x2004, 0xd0b4,
-       0x0040, 0x9752, 0x6003, 0x0007, 0x2009, 0x0043, 0x1078, 0x756c,
-       0x0078, 0x9754, 0x6003, 0x0002, 0x1078, 0x6109, 0x007c, 0x1078,
-       0x6010, 0x1078, 0xa0c6, 0x00c0, 0x9761, 0x1078, 0x5a41, 0x1078,
-       0x753d, 0x1078, 0x6109, 0x007c, 0x1078, 0x6010, 0x2009, 0x0041,
-       0x0078, 0x98c1, 0xa182, 0x0040, 0x0079, 0x976e, 0x9781, 0x9783,
-       0x9781, 0x9781, 0x9781, 0x9781, 0x9781, 0x9784, 0x9781, 0x9781,
-       0x9781, 0x9781, 0x9781, 0x9781, 0x9781, 0x9781, 0x9781, 0x978f,
-       0x9781, 0x1078, 0x1328, 0x007c, 0x6003, 0x0004, 0x6110, 0x20e1,
-       0x0005, 0x3d18, 0x3e20, 0x2c10, 0x1078, 0x15ec, 0x007c, 0x0d7e,
-       0x1078, 0x5a41, 0x0d7f, 0x1078, 0xa134, 0x1078, 0x753d, 0x007c,
-       0xa182, 0x0040, 0x0079, 0x979c, 0x97af, 0x97af, 0x97af, 0x97af,
-       0x97af, 0x97af, 0x97af, 0x97b1, 0x97af, 0x97b4, 0x97df, 0x97af,
-       0x97af, 0x97af, 0x97af, 0x97df, 0x97af, 0x97af, 0x97af, 0x1078,
-       0x1328, 0x1078, 0x7583, 0x007c, 0x1078, 0x60b8, 0x1078, 0x61d3,
-       0x6010, 0x0d7e, 0x2068, 0x684c, 0xd0fc, 0x0040, 0x97ca, 0xa08c,
-       0x0003, 0xa18e, 0x0002, 0x0040, 0x97d2, 0x2009, 0x0041, 0x0d7f,
-       0x0078, 0x98c1, 0x6003, 0x0007, 0x6017, 0x0000, 0x1078, 0x5a41,
-       0x0d7f, 0x007c, 0x1078, 0xa0c6, 0x0040, 0x97d8, 0x0d7f, 0x007c,
-       0x1078, 0x5a41, 0x1078, 0x753d, 0x0d7f, 0x0078, 0x97d1, 0x037e,
-       0x1078, 0x60b8, 0x1078, 0x61d3, 0x6010, 0x0d7e, 0x2068, 0x6018,
-       0x2004, 0xd0bc, 0x0040, 0x97ff, 0x684c, 0xa084, 0x0003, 0xa086,
-       0x0002, 0x0040, 0x97fb, 0x687c, 0x632c, 0xa31a, 0x632e, 0x6880,
-       0x6328, 0xa31b, 0x632a, 0x6003, 0x0002, 0x0078, 0x9810, 0x2019,
-       0x0004, 0x1078, 0x9e70, 0x6014, 0xa005, 0x00c0, 0x980c, 0x2001,
-       0xa5a1, 0x2004, 0x8003, 0x6016, 0x6013, 0x0000, 0x6003, 0x0007,
-       0x0d7f, 0x037f, 0x007c, 0xa186, 0x0013, 0x00c0, 0x9821, 0x6004,
-       0xa086, 0x0042, 0x10c0, 0x1328, 0x1078, 0x6010, 0x1078, 0x6109,
-       0x007c, 0xa186, 0x0027, 0x0040, 0x9829, 0xa186, 0x0014, 0x00c0,
-       0x9839, 0x6004, 0xa086, 0x0042, 0x10c0, 0x1328, 0x2001, 0x0007,
-       0x1078, 0x4472, 0x1078, 0x6010, 0x1078, 0x8c01, 0x1078, 0x6109,
-       0x007c, 0xa182, 0x0040, 0x0079, 0x983d, 0x9850, 0x9850, 0x9850,
-       0x9850, 0x9850, 0x9850, 0x9850, 0x9852, 0x985e, 0x9850, 0x9850,
-       0x9850, 0x9850, 0x9850, 0x9850, 0x9850, 0x9850, 0x9850, 0x9850,
-       0x1078, 0x1328, 0x037e, 0x047e, 0x20e1, 0x0005, 0x3d18, 0x3e20,
-       0x2c10, 0x1078, 0x15ec, 0x047f, 0x037f, 0x007c, 0x6010, 0x0d7e,
-       0x2068, 0x6810, 0x6a14, 0x6118, 0x210c, 0xd1bc, 0x0040, 0x987d,
-       0x6124, 0xd1f4, 0x00c0, 0x987d, 0x007e, 0x047e, 0x057e, 0x6c7c,
-       0xa422, 0x6d80, 0x2200, 0xa52b, 0x602c, 0xa420, 0x642e, 0x6028,
-       0xa529, 0x652a, 0x057f, 0x047f, 0x007f, 0xa20d, 0x00c0, 0x9891,
-       0x684c, 0xd0fc, 0x0040, 0x9889, 0x2009, 0x0041, 0x0d7f, 0x0078,
-       0x98c1, 0x6003, 0x0007, 0x6017, 0x0000, 0x1078, 0x5a41, 0x0d7f,
-       0x007c, 0x007e, 0x0f7e, 0x2c78, 0x1078, 0x4893, 0x0f7f, 0x007f,
-       0x0040, 0x989e, 0x6003, 0x0002, 0x0d7f, 0x007c, 0x2009, 0xa30d,
-       0x210c, 0xd19c, 0x0040, 0x98a8, 0x6003, 0x0007, 0x0078, 0x98aa,
-       0x6003, 0x0006, 0x1078, 0x98b0, 0x1078, 0x5a43, 0x0d7f, 0x007c,
-       0xd2fc, 0x0040, 0x98bc, 0x8002, 0x8000, 0x8212, 0xa291, 0x0000,
-       0x2009, 0x0009, 0x0078, 0x98be, 0x2009, 0x0015, 0x6a6a, 0x6866,
-       0x007c, 0xa182, 0x0040, 0x0048, 0x98c7, 0x0079, 0x98d4, 0xa186,
-       0x0013, 0x0040, 0x98cf, 0xa186, 0x0014, 0x10c0, 0x1328, 0x6024,
-       0xd0dc, 0x1040, 0x1328, 0x007c, 0x98e7, 0x98ee, 0x98fa, 0x9906,
-       0x98e7, 0x98e7, 0x98e7, 0x9915, 0x98e7, 0x98e9, 0x98e9, 0x98e7,
-       0x98e7, 0x98e7, 0x98e7, 0x98e7, 0x98e7, 0x98e7, 0x98e7, 0x1078,
-       0x1328, 0x6024, 0xd0dc, 0x1040, 0x1328, 0x007c, 0x6003, 0x0001,
-       0x6106, 0x1078, 0x5bf8, 0x127e, 0x2091, 0x8000, 0x1078, 0x6109,
-       0x127f, 0x007c, 0x6003, 0x0001, 0x6106, 0x1078, 0x5bf8, 0x127e,
-       0x2091, 0x8000, 0x1078, 0x6109, 0x127f, 0x007c, 0x6003, 0x0003,
-       0x6106, 0x2c10, 0x1078, 0x1cab, 0x127e, 0x2091, 0x8000, 0x1078,
-       0x5c64, 0x1078, 0x61d3, 0x127f, 0x007c, 0xa016, 0x1078, 0x15ec,
-       0x007c, 0x127e, 0x2091, 0x8000, 0x037e, 0x0d7e, 0xa182, 0x0040,
-       0x1079, 0x9926, 0x0d7f, 0x037f, 0x127f, 0x007c, 0x9936, 0x9938,
-       0x994d, 0x996c, 0x9936, 0x9936, 0x9936, 0x9984, 0x9936, 0x9936,
-       0x9936, 0x9936, 0x9936, 0x9936, 0x9936, 0x9936, 0x1078, 0x1328,
-       0x6010, 0x2068, 0x684c, 0xd0fc, 0x0040, 0x9962, 0xa09c, 0x0003,
-       0xa39e, 0x0003, 0x0040, 0x9962, 0x6003, 0x0001, 0x6106, 0x1078,
-       0x5bf8, 0x1078, 0x6109, 0x0078, 0x9987, 0x6010, 0x2068, 0x684c,
-       0xd0fc, 0x0040, 0x9962, 0xa09c, 0x0003, 0xa39e, 0x0003, 0x0040,
-       0x9962, 0x6003, 0x0001, 0x6106, 0x1078, 0x5bf8, 0x1078, 0x6109,
-       0x0078, 0x9987, 0x6013, 0x0000, 0x6017, 0x0000, 0x2019, 0x0004,
-       0x1078, 0x9e70, 0x0078, 0x9987, 0x6010, 0x2068, 0x684c, 0xd0fc,
-       0x0040, 0x9962, 0xa09c, 0x0003, 0xa39e, 0x0003, 0x0040, 0x9962,
-       0x6003, 0x0003, 0x6106, 0x2c10, 0x1078, 0x1cab, 0x1078, 0x5c64,
-       0x1078, 0x61d3, 0x0078, 0x9987, 0xa016, 0x1078, 0x15ec, 0x007c,
-       0x1078, 0x6010, 0x6110, 0x81ff, 0x0040, 0x9999, 0x0d7e, 0x2168,
-       0x1078, 0xa181, 0x037e, 0x2019, 0x0029, 0x1078, 0x9e70, 0x037f,
-       0x0d7f, 0x1078, 0x8c01, 0x1078, 0x6109, 0x007c, 0x1078, 0x60b8,
-       0x6110, 0x81ff, 0x0040, 0x99af, 0x0d7e, 0x2168, 0x1078, 0xa181,
-       0x037e, 0x2019, 0x0029, 0x1078, 0x9e70, 0x037f, 0x0d7f, 0x1078,
-       0x8c01, 0x1078, 0x61d3, 0x007c, 0xa182, 0x0085, 0x0079, 0x99b8,
-       0x99c1, 0x99bf, 0x99bf, 0x99cd, 0x99bf, 0x99bf, 0x99bf, 0x1078,
-       0x1328, 0x6003, 0x000b, 0x6106, 0x1078, 0x5bf8, 0x127e, 0x2091,
-       0x8000, 0x1078, 0x6109, 0x127f, 0x007c, 0x027e, 0x0e7e, 0x1078,
-       0xa0bf, 0x0040, 0x99d7, 0x1078, 0x753d, 0x0078, 0x99f3, 0x2071,
-       0xa880, 0x7224, 0x6212, 0x7220, 0x1078, 0x9d10, 0x0040, 0x99e4,
-       0x6007, 0x0086, 0x0078, 0x99ed, 0x6007, 0x0087, 0x7224, 0xa296,
-       0xffff, 0x00c0, 0x99ed, 0x6007, 0x0086, 0x6003, 0x0001, 0x1078,
-       0x5bf8, 0x1078, 0x6109, 0x0e7f, 0x027f, 0x007c, 0xa186, 0x0013,
-       0x00c0, 0x9a07, 0x6004, 0xa08a, 0x0085, 0x1048, 0x1328, 0xa08a,
-       0x008c, 0x10c8, 0x1328, 0xa082, 0x0085, 0x0079, 0x9a1e, 0xa186,
-       0x0027, 0x0040, 0x9a13, 0xa186, 0x0014, 0x0040, 0x9a13, 0x1078,
-       0x7583, 0x0078, 0x9a1d, 0x2001, 0x0007, 0x1078, 0x4472, 0x1078,
-       0x6010, 0x1078, 0x8c01, 0x1078, 0x6109, 0x007c, 0x9a25, 0x9a27,
-       0x9a27, 0x9a25, 0x9a25, 0x9a25, 0x9a25, 0x1078, 0x1328, 0x1078,
-       0x6010, 0x1078, 0x8c01, 0x1078, 0x6109, 0x007c, 0xa182, 0x0085,
-       0x1048, 0x1328, 0xa182, 0x008c, 0x10c8, 0x1328, 0xa182, 0x0085,
-       0x0079, 0x9a3a, 0x9a41, 0x9a41, 0x9a41, 0x9a43, 0x9a41, 0x9a41,
-       0x9a41, 0x1078, 0x1328, 0x007c, 0xa186, 0x0013, 0x0040, 0x9a54,
-       0xa186, 0x0014, 0x0040, 0x9a54, 0xa186, 0x0027, 0x0040, 0x9a54,
-       0x1078, 0x7583, 0x0078, 0x9a5a, 0x1078, 0x6010, 0x1078, 0x8c01,
-       0x1078, 0x6109, 0x007c, 0x037e, 0x1078, 0xa134, 0x603f, 0x0000,
-       0x2019, 0x000b, 0x1078, 0x9a6a, 0x601f, 0x0006, 0x6003, 0x0007,
-       0x037f, 0x007c, 0x127e, 0x037e, 0x2091, 0x8000, 0x087e, 0x2c40,
-       0x097e, 0x2049, 0x0000, 0x1078, 0x7058, 0x097f, 0x087f, 0x00c0,
-       0x9aa5, 0x077e, 0x2c38, 0x1078, 0x7105, 0x077f, 0x00c0, 0x9aa5,
-       0x6000, 0xa086, 0x0000, 0x0040, 0x9aa5, 0x601c, 0xa086, 0x0007,
-       0x0040, 0x9aa5, 0x0d7e, 0x6000, 0xa086, 0x0004, 0x00c0, 0x9a96,
-       0x1078, 0xa134, 0x601f, 0x0007, 0x1078, 0x1749, 0x6010, 0x2068,
-       0x1078, 0x8a44, 0x0040, 0x9a9e, 0x1078, 0x9e70, 0x0d7f, 0x6013,
-       0x0000, 0x1078, 0xa134, 0x601f, 0x0007, 0x037f, 0x127f, 0x007c,
-       0x0f7e, 0x0c7e, 0x037e, 0x157e, 0x2079, 0xa880, 0x7938, 0x783c,
-       0x1078, 0x24e3, 0x00c0, 0x9af6, 0x017e, 0x0c7e, 0x1078, 0x4501,
-       0x00c0, 0x9af6, 0x2011, 0xa890, 0xac98, 0x000a, 0x20a9, 0x0004,
-       0x1078, 0x7e55, 0x00c0, 0x9af6, 0x017f, 0x027f, 0x027e, 0x017e,
-       0x2019, 0x0029, 0x1078, 0x71e0, 0x1078, 0x5d53, 0x077e, 0x2039,
-       0x0000, 0x1078, 0x5c78, 0x077f, 0x017f, 0x077e, 0x2039, 0x0000,
-       0x1078, 0x9c38, 0x077f, 0x1078, 0x471b, 0x027e, 0x6204, 0xa294,
-       0xff00, 0x8217, 0xa286, 0x0006, 0x0040, 0x9aea, 0xa286, 0x0004,
-       0x00c0, 0x9aed, 0x62a0, 0x1078, 0x28d5, 0x027f, 0x017f, 0x1078,
-       0x4235, 0x6612, 0x6516, 0xa006, 0x0078, 0x9af8, 0x0c7f, 0x017f,
-       0x157f, 0x037f, 0x0c7f, 0x0f7f, 0x007c, 0x0c7e, 0x0d7e, 0x0e7e,
-       0x017e, 0x2009, 0xa31f, 0x2104, 0xa086, 0x0074, 0x00c0, 0x9b60,
-       0x2069, 0xa88e, 0x690c, 0xa182, 0x0100, 0x0048, 0x9b50, 0x6908,
-       0xa184, 0x8000, 0x0040, 0x9b5c, 0x6018, 0x2070, 0x7010, 0xa084,
-       0x00ff, 0x0040, 0x9b1f, 0x7000, 0xd0f4, 0x0040, 0x9b23, 0xa184,
-       0x0800, 0x0040, 0x9b5c, 0x6910, 0xa18a, 0x0001, 0x0048, 0x9b54,
-       0x6914, 0x2069, 0xa8ae, 0x6904, 0x81ff, 0x00c0, 0x9b48, 0x690c,
-       0xa182, 0x0100, 0x0048, 0x9b50, 0x6908, 0x81ff, 0x00c0, 0x9b4c,
-       0x6910, 0xa18a, 0x0001, 0x0048, 0x9b54, 0x6918, 0xa18a, 0x0001,
-       0x0048, 0x9b5c, 0x0078, 0x9b66, 0x6013, 0x0100, 0x0078, 0x9b62,
-       0x6013, 0x0300, 0x0078, 0x9b62, 0x6013, 0x0500, 0x0078, 0x9b62,
-       0x6013, 0x0700, 0x0078, 0x9b62, 0x6013, 0x0900, 0x0078, 0x9b62,
-       0x6013, 0x0b00, 0x0078, 0x9b62, 0x6013, 0x0f00, 0x0078, 0x9b62,
-       0x6013, 0x2d00, 0xa085, 0x0001, 0x0078, 0x9b67, 0xa006, 0x017f,
-       0x0e7f, 0x0d7f, 0x0c7f, 0x007c, 0x0c7e, 0x0d7e, 0x027e, 0x037e,
-       0x157e, 0x6218, 0x2268, 0x6b04, 0xa394, 0x00ff, 0xa286, 0x0006,
-       0x0040, 0x9b90, 0xa286, 0x0004, 0x0040, 0x9b90, 0xa394, 0xff00,
-       0x8217, 0xa286, 0x0006, 0x0040, 0x9b90, 0xa286, 0x0004, 0x0040,
-       0x9b90, 0x0c7e, 0x2d60, 0x1078, 0x4513, 0x0c7f, 0x0078, 0x9bcb,
-       0x2011, 0xa896, 0xad98, 0x000a, 0x20a9, 0x0004, 0x1078, 0x7e55,
-       0x00c0, 0x9bcc, 0x2011, 0xa89a, 0xad98, 0x0006, 0x20a9, 0x0004,
-       0x1078, 0x7e55, 0x00c0, 0x9bcc, 0x047e, 0x017e, 0x6aa0, 0xa294,
-       0x00ff, 0x8227, 0xa006, 0x2009, 0xa352, 0x210c, 0xd1a4, 0x0040,
-       0x9bb8, 0x2009, 0x0029, 0x1078, 0x9ec0, 0x6800, 0xc0e5, 0x6802,
-       0x2019, 0x0029, 0x1078, 0x5d53, 0x077e, 0x2039, 0x0000, 0x1078,
-       0x5c78, 0x2c08, 0x1078, 0x9c38, 0x077f, 0x2001, 0x0007, 0x1078,
-       0x4472, 0x017f, 0x047f, 0xa006, 0x157f, 0x037f, 0x027f, 0x0d7f,
-       0x0c7f, 0x007c, 0x0d7e, 0x2069, 0xa88e, 0x6800, 0xa086, 0x0800,
-       0x0040, 0x9bde, 0x6013, 0x0000, 0x0078, 0x9bdf, 0xa006, 0x0d7f,
-       0x007c, 0x0c7e, 0x0f7e, 0x017e, 0x027e, 0x037e, 0x157e, 0x2079,
-       0xa88c, 0x7930, 0x7834, 0x1078, 0x24e3, 0x00c0, 0x9c05, 0x1078,
-       0x4501, 0x00c0, 0x9c05, 0x2011, 0xa890, 0xac98, 0x000a, 0x20a9,
-       0x0004, 0x1078, 0x7e55, 0x00c0, 0x9c05, 0x2011, 0xa894, 0xac98,
-       0x0006, 0x20a9, 0x0004, 0x1078, 0x7e55, 0x157f, 0x037f, 0x027f,
-       0x017f, 0x0f7f, 0x0c7f, 0x007c, 0x0c7e, 0x007e, 0x017e, 0x027e,
-       0x037e, 0x157e, 0x2011, 0xa883, 0x2204, 0x8211, 0x220c, 0x1078,
-       0x24e3, 0x00c0, 0x9c31, 0x1078, 0x4501, 0x00c0, 0x9c31, 0x2011,
-       0xa896, 0xac98, 0x000a, 0x20a9, 0x0004, 0x1078, 0x7e55, 0x00c0,
-       0x9c31, 0x2011, 0xa89a, 0xac98, 0x0006, 0x20a9, 0x0004, 0x1078,
-       0x7e55, 0x157f, 0x037f, 0x027f, 0x017f, 0x007f, 0x0c7f, 0x007c,
-       0x0e7e, 0x0c7e, 0x087e, 0x077e, 0x067e, 0x057e, 0x047e, 0x027e,
-       0x127e, 0x2091, 0x8000, 0x2740, 0x2029, 0xa5b4, 0x252c, 0x2021,
-       0xa5ba, 0x2424, 0x2061, 0xaa00, 0x2071, 0xa300, 0x7644, 0x7060,
-       0x81ff, 0x0040, 0x9c59, 0x8001, 0xa602, 0x00c8, 0x9cc3, 0x0078,
-       0x9c5c, 0xa606, 0x0040, 0x9cc3, 0x2100, 0xac06, 0x0040, 0x9cb9,
-       0x1078, 0x9ee5, 0x0040, 0x9cb9, 0x671c, 0xa786, 0x0001, 0x0040,
-       0x9cde, 0xa786, 0x0004, 0x0040, 0x9cde, 0xa786, 0x0007, 0x0040,
-       0x9cb9, 0x2500, 0xac06, 0x0040, 0x9cb9, 0x2400, 0xac06, 0x0040,
-       0x9cb9, 0x1078, 0x9ef9, 0x00c0, 0x9cb9, 0x88ff, 0x0040, 0x9c84,
-       0x6020, 0xa906, 0x00c0, 0x9cb9, 0x0d7e, 0x6000, 0xa086, 0x0004,
-       0x00c0, 0x9c8e, 0x017e, 0x1078, 0x1749, 0x017f, 0xa786, 0x0008,
-       0x00c0, 0x9c9d, 0x1078, 0x8c3b, 0x00c0, 0x9c9d, 0x1078, 0x7a05,
-       0x0d7f, 0x1078, 0x8c01, 0x0078, 0x9cb9, 0x6010, 0x2068, 0x1078,
-       0x8a44, 0x0040, 0x9cb6, 0xa786, 0x0003, 0x00c0, 0x9ccd, 0x6837,
-       0x0103, 0x6b4a, 0x6847, 0x0000, 0x1078, 0xa181, 0x017e, 0x1078,
-       0x8cb8, 0x1078, 0x4982, 0x017f, 0x1078, 0x8bf4, 0x0d7f, 0x1078,
-       0x8c01, 0xace0, 0x0010, 0x2001, 0xa315, 0x2004, 0xac02, 0x00c8,
-       0x9cc3, 0x0078, 0x9c4c, 0x127f, 0x027f, 0x047f, 0x057f, 0x067f,
-       0x077f, 0x087f, 0x0c7f, 0x0e7f, 0x007c, 0xa786, 0x0006, 0x00c0,
-       0x9ca7, 0xa386, 0x0005, 0x0040, 0x9cdb, 0x1078, 0xa181, 0x1078,
-       0x9e70, 0x0078, 0x9cb6, 0x0d7f, 0x0078, 0x9cb9, 0x1078, 0x9ef9,
-       0x00c0, 0x9cb9, 0x81ff, 0x0040, 0x9cb9, 0xa180, 0x0001, 0x2004,
-       0xa086, 0x0018, 0x0040, 0x9cf3, 0xa180, 0x0001, 0x2004, 0xa086,
-       0x002d, 0x00c0, 0x9cb9, 0x6000, 0xa086, 0x0002, 0x00c0, 0x9cb9,
-       0x1078, 0x8c27, 0x0040, 0x9d04, 0x1078, 0x8c3b, 0x00c0, 0x9cb9,
-       0x1078, 0x7a05, 0x0078, 0x9d0c, 0x1078, 0x2839, 0x1078, 0x8c3b,
-       0x00c0, 0x9d0c, 0x1078, 0x7a05, 0x1078, 0x8c01, 0x0078, 0x9cb9,
-       0x0c7e, 0x0e7e, 0x017e, 0x2c08, 0x2170, 0x1078, 0x9e8c, 0x017f,
-       0x0040, 0x9d1f, 0x601c, 0xa084, 0x000f, 0x1079, 0x9d22, 0x0e7f,
-       0x0c7f, 0x007c, 0x9d2a, 0x9d2a, 0x9d2a, 0x9d2a, 0x9d2a, 0x9d2a,
-       0x9d2c, 0x9d2a, 0xa006, 0x007c, 0x047e, 0x017e, 0x7018, 0xa080,
-       0x0028, 0x2024, 0xa4a4, 0x00ff, 0x8427, 0x2c00, 0x2009, 0x0020,
-       0x1078, 0x9ec0, 0x017f, 0x047f, 0x037e, 0x2019, 0x0002, 0x1078,
-       0x9a6a, 0x037f, 0xa085, 0x0001, 0x007c, 0x2001, 0x0001, 0x1078,
-       0x442b, 0x157e, 0x017e, 0x027e, 0x037e, 0x20a9, 0x0004, 0x2019,
-       0xa305, 0x2011, 0xa896, 0x1078, 0x7e55, 0x037f, 0x027f, 0x017f,
-       0x157f, 0xa005, 0x007c, 0x0f7e, 0x0e7e, 0x0c7e, 0x087e, 0x077e,
-       0x067e, 0x027e, 0x127e, 0x2091, 0x8000, 0x2740, 0x2061, 0xaa00,
-       0x2079, 0x0001, 0x8fff, 0x0040, 0x9dc3, 0x2071, 0xa300, 0x7644,
-       0x7060, 0x8001, 0xa602, 0x00c8, 0x9dc3, 0x88ff, 0x0040, 0x9d7e,
-       0x2800, 0xac06, 0x00c0, 0x9db9, 0x2079, 0x0000, 0x1078, 0x9ee5,
-       0x0040, 0x9db9, 0x2400, 0xac06, 0x0040, 0x9db9, 0x671c, 0xa786,
-       0x0006, 0x00c0, 0x9db9, 0xa786, 0x0007, 0x0040, 0x9db9, 0x88ff,
-       0x00c0, 0x9d9d, 0x6018, 0xa206, 0x00c0, 0x9db9, 0x85ff, 0x0040,
-       0x9d9d, 0x6020, 0xa106, 0x00c0, 0x9db9, 0x0d7e, 0x6000, 0xa086,
-       0x0004, 0x00c0, 0x9da9, 0x1078, 0xa134, 0x601f, 0x0007, 0x1078,
-       0x1749, 0x6010, 0x2068, 0x1078, 0x8a44, 0x0040, 0x9db3, 0x047e,
-       0x1078, 0x9e70, 0x047f, 0x0d7f, 0x1078, 0x8c01, 0x88ff, 0x00c0,
-       0x9dcd, 0xace0, 0x0010, 0x2001, 0xa315, 0x2004, 0xac02, 0x00c8,
-       0x9dc3, 0x0078, 0x9d6a, 0xa006, 0x127f, 0x027f, 0x067f, 0x077f,
-       0x087f, 0x0c7f, 0x0e7f, 0x0f7f, 0x007c, 0xa8c5, 0x0001, 0x0078,
-       0x9dc4, 0x077e, 0x057e, 0x087e, 0x2041, 0x0000, 0x2029, 0x0001,
-       0x2c20, 0x2019, 0x0002, 0x6218, 0x097e, 0x2049, 0x0000, 0x1078,
-       0x7058, 0x097f, 0x087f, 0x2039, 0x0000, 0x1078, 0x7105, 0x1078,
-       0x9d5b, 0x057f, 0x077f, 0x007c, 0x027e, 0x047e, 0x057e, 0x077e,
-       0x0c7e, 0x157e, 0x2c20, 0x2128, 0x20a9, 0x007f, 0x2009, 0x0000,
-       0x017e, 0x037e, 0x1078, 0x4501, 0x00c0, 0x9e14, 0x2c10, 0x057e,
-       0x087e, 0x2041, 0x0000, 0x2508, 0x2029, 0x0001, 0x097e, 0x2049,
-       0x0000, 0x1078, 0x7058, 0x097f, 0x087f, 0x2039, 0x0000, 0x1078,
-       0x7105, 0x1078, 0x9d5b, 0x057f, 0x037f, 0x017f, 0x8108, 0x00f0,
-       0x9df8, 0x157f, 0x0c7f, 0x077f, 0x057f, 0x047f, 0x027f, 0x007c,
-       0x077e, 0x057e, 0x6218, 0x087e, 0x2041, 0x0000, 0x2029, 0x0001,
-       0x2019, 0x0048, 0x097e, 0x2049, 0x0000, 0x1078, 0x7058, 0x097f,
-       0x087f, 0x2039, 0x0000, 0x1078, 0x7105, 0x2c20, 0x1078, 0x9d5b,
-       0x057f, 0x077f, 0x007c, 0x027e, 0x047e, 0x057e, 0x077e, 0x0c7e,
-       0x157e, 0x2c20, 0x20a9, 0x007f, 0x2009, 0x0000, 0x017e, 0x037e,
-       0x1078, 0x4501, 0x00c0, 0x9e64, 0x2c10, 0x087e, 0x2041, 0x0000,
-       0x2828, 0x047e, 0x2021, 0x0001, 0x1078, 0xa111, 0x047f, 0x097e,
-       0x2049, 0x0000, 0x1078, 0x7058, 0x097f, 0x087f, 0x2039, 0x0000,
-       0x1078, 0x7105, 0x1078, 0x9d5b, 0x037f, 0x017f, 0x8108, 0x00f0,
-       0x9e46, 0x157f, 0x0c7f, 0x077f, 0x057f, 0x047f, 0x027f, 0x007c,
-       0x017e, 0x0f7e, 0xad82, 0xca00, 0x0048, 0x9e89, 0xad82, 0xffff,
-       0x00c8, 0x9e89, 0x6800, 0xa07d, 0x0040, 0x9e86, 0x6803, 0x0000,
-       0x6b52, 0x1078, 0x4982, 0x2f68, 0x0078, 0x9e7a, 0x6b52, 0x1078,
-       0x4982, 0x0f7f, 0x017f, 0x007c, 0x0e7e, 0x047e, 0x037e, 0x2061,
-       0xaa00, 0x2071, 0xa300, 0x7444, 0x7060, 0x8001, 0xa402, 0x00c8,
-       0x9ebb, 0x2100, 0xac06, 0x0040, 0x9ead, 0x6000, 0xa086, 0x0000,
-       0x0040, 0x9ead, 0x6008, 0xa206, 0x00c0, 0x9ead, 0x6018, 0xa1a0,
-       0x0006, 0x2424, 0xa406, 0x0040, 0x9eb7, 0xace0, 0x0010, 0x2001,
-       0xa315, 0x2004, 0xac02, 0x00c8, 0x9ebb, 0x0078, 0x9e91, 0xa085,
-       0x0001, 0x0078, 0x9ebc, 0xa006, 0x037f, 0x047f, 0x0e7f, 0x007c,
-       0x0d7e, 0x007e, 0x1078, 0x1381, 0x007f, 0x1040, 0x1328, 0x6837,
-       0x010d, 0x685e, 0x027e, 0x2010, 0x1078, 0x8a30, 0x2001, 0x0000,
-       0x0040, 0x9ed6, 0x2200, 0xa080, 0x0008, 0x2004, 0x027f, 0x684a,
-       0x6956, 0x6c46, 0x684f, 0x0000, 0xa006, 0x68b2, 0x6802, 0x683a,
-       0x685a, 0x1078, 0x4982, 0x0d7f, 0x007c, 0x6700, 0xa786, 0x0000,
-       0x0040, 0x9ef8, 0xa786, 0x0001, 0x0040, 0x9ef8, 0xa786, 0x000a,
-       0x0040, 0x9ef8, 0xa786, 0x0009, 0x0040, 0x9ef8, 0xa085, 0x0001,
-       0x007c, 0x0e7e, 0x6018, 0x2070, 0x70a0, 0xa206, 0x0e7f, 0x007c,
-       0x017e, 0x6004, 0xa08e, 0x001e, 0x00c0, 0x9f1a, 0x8007, 0x6130,
-       0xa18c, 0x00ff, 0xa105, 0x6032, 0x6007, 0x0085, 0x6003, 0x000b,
-       0x601f, 0x0005, 0x2001, 0xa5a1, 0x2004, 0x6016, 0x1078, 0x5bf8,
-       0x1078, 0x6109, 0x017f, 0x007c, 0x0005, 0x0005, 0x007c, 0x6024,
-       0xd0e4, 0x0040, 0x9f30, 0xd0cc, 0x0040, 0x9f2a, 0x1078, 0x8cfa,
-       0x0078, 0x9f30, 0x1078, 0xa134, 0x1078, 0x5a41, 0x1078, 0x753d,
-       0x007c, 0xa280, 0x0007, 0x2004, 0xa084, 0x000f, 0x0079, 0x9f38,
-       0x9f41, 0x9f41, 0x9f41, 0x9f43, 0x9f41, 0x9f43, 0x9f43, 0x9f41,
-       0x9f43, 0xa006, 0x007c, 0xa085, 0x0001, 0x007c, 0xa280, 0x0007,
-       0x2004, 0xa084, 0x000f, 0x0079, 0x9f4d, 0x9f56, 0x9f56, 0x9f56,
-       0x9f56, 0x9f56, 0x9f56, 0x9f61, 0x9f56, 0x9f56, 0x6007, 0x003b,
-       0x602b, 0x0009, 0x6013, 0x2a00, 0x6003, 0x0001, 0x1078, 0x5bf8,
-       0x007c, 0x0c7e, 0x2260, 0x1078, 0xa134, 0x603f, 0x0000, 0x6024,
-       0xc0f4, 0xc0cc, 0x6026, 0x0c7f, 0x0d7e, 0x2268, 0xa186, 0x0007,
-       0x00c0, 0x9fc2, 0x6810, 0xa005, 0x0040, 0x9f7f, 0xa080, 0x0013,
-       0x2004, 0xd0fc, 0x00c0, 0x9f7f, 0x0d7f, 0x0078, 0x9f56, 0x6007,
-       0x003a, 0x6003, 0x0001, 0x1078, 0x5bf8, 0x1078, 0x6109, 0x0c7e,
-       0x2d60, 0x6100, 0xa186, 0x0002, 0x00c0, 0xa050, 0x6010, 0xa005,
-       0x00c0, 0x9f99, 0x6000, 0xa086, 0x0007, 0x10c0, 0x1328, 0x0078,
-       0xa050, 0xa08c, 0xf000, 0x00c0, 0x9fa5, 0x0078, 0x9fa5, 0x2068,
-       0x6800, 0xa005, 0x00c0, 0x9f9f, 0x2d00, 0xa080, 0x0013, 0x2004,
-       0xa084, 0x0003, 0xa086, 0x0002, 0x00c0, 0x9fbe, 0x6010, 0x2068,
-       0x684c, 0xc0dc, 0xc0f4, 0x684e, 0x6850, 0xc0f4, 0xc0fc, 0x6852,
-       0x2009, 0x0043, 0x1078, 0x98c1, 0x0078, 0xa050, 0x2009, 0x0041,
-       0x0078, 0xa04a, 0xa186, 0x0005, 0x00c0, 0xa009, 0x6810, 0xa080,
-       0x0013, 0x2004, 0xd0bc, 0x00c0, 0x9fd0, 0x0d7f, 0x0078, 0x9f56,
-       0xd0b4, 0x0040, 0x9fd8, 0xd0fc, 0x1040, 0x1328, 0x0078, 0x9f72,
-       0x6007, 0x003a, 0x6003, 0x0001, 0x1078, 0x5bf8, 0x1078, 0x6109,
-       0x0c7e, 0x2d60, 0x6100, 0xa186, 0x0002, 0x0040, 0x9feb, 0xa186,
-       0x0004, 0x00c0, 0xa050, 0x2071, 0xa5e1, 0x7000, 0xa086, 0x0003,
-       0x00c0, 0x9ff8, 0x7004, 0xac06, 0x00c0, 0x9ff8, 0x7003, 0x0000,
-       0x6810, 0xa080, 0x0013, 0x200c, 0xc1f4, 0xc1dc, 0x2102, 0x8000,
-       0x200c, 0xc1f4, 0xc1fc, 0xc1bc, 0x2102, 0x2009, 0x0042, 0x0078,
-       0xa04a, 0x037e, 0x0d7e, 0x0d7e, 0x1078, 0x1381, 0x037f, 0x1040,
-       0x1328, 0x6837, 0x010d, 0x6803, 0x0000, 0x683b, 0x0000, 0x685b,
-       0x0000, 0x6b5e, 0x6857, 0x0045, 0x2c00, 0x6862, 0x6034, 0x6872,
-       0x2360, 0x6024, 0xc0dd, 0x6026, 0x6018, 0xa080, 0x0028, 0x2004,
-       0xa084, 0x00ff, 0x8007, 0x6320, 0x6b4a, 0x6846, 0x684f, 0x0000,
-       0x6d6a, 0x6e66, 0x686f, 0x0001, 0x1078, 0x4982, 0x2019, 0x0045,
-       0x6008, 0x2068, 0x1078, 0x9a6a, 0x2d00, 0x600a, 0x601f, 0x0006,
-       0x6003, 0x0007, 0x6017, 0x0000, 0x603f, 0x0000, 0x0d7f, 0x037f,
-       0x0078, 0xa051, 0x603f, 0x0000, 0x6003, 0x0007, 0x1078, 0x98c1,
-       0x0c7f, 0x0d7f, 0x007c, 0xa186, 0x0013, 0x00c0, 0xa05d, 0x6004,
-       0xa082, 0x0085, 0x2008, 0x0079, 0xa077, 0xa186, 0x0027, 0x00c0,
-       0xa070, 0x1078, 0x6010, 0x037e, 0x0d7e, 0x6010, 0x2068, 0x2019,
-       0x0004, 0x1078, 0x9e70, 0x0d7f, 0x037f, 0x1078, 0x6109, 0x007c,
-       0xa186, 0x0014, 0x0040, 0xa061, 0x1078, 0x7583, 0x007c, 0xa080,
-       0xa07e, 0xa07e, 0xa07e, 0xa07e, 0xa07e, 0xa080, 0x1078, 0x1328,
-       0x1078, 0x6010, 0x6003, 0x000c, 0x1078, 0x6109, 0x007c, 0xa182,
-       0x008c, 0x00c8, 0xa091, 0xa182, 0x0085, 0x0048, 0xa091, 0x0079,
-       0xa094, 0x1078, 0x7583, 0x007c, 0xa09b, 0xa09b, 0xa09b, 0xa09b,
-       0xa09d, 0xa0bc, 0xa09b, 0x1078, 0x1328, 0x0d7e, 0x2c68, 0x1078,
-       0x74d7, 0x0040, 0xa0b7, 0x6003, 0x0001, 0x6007, 0x001e, 0x2009,
-       0xa88e, 0x210c, 0x6136, 0x2009, 0xa88f, 0x210c, 0x613a, 0x600b,
-       0xffff, 0x6918, 0x611a, 0x601f, 0x0004, 0x1078, 0x5bf8, 0x2d60,
-       0x1078, 0x753d, 0x0d7f, 0x007c, 0x1078, 0x753d, 0x007c, 0x0e7e,
-       0x6018, 0x2070, 0x7000, 0xd0ec, 0x0e7f, 0x007c, 0x6010, 0xa080,
-       0x0013, 0x200c, 0xd1ec, 0x0040, 0xa110, 0x2001, 0xa371, 0x2004,
-       0xd0ec, 0x0040, 0xa110, 0x6003, 0x0002, 0x6024, 0xc0e5, 0x6026,
-       0xd1ac, 0x0040, 0xa0ee, 0x0f7e, 0x2c78, 0x1078, 0x488f, 0x0f7f,
-       0x0040, 0xa0ee, 0x2001, 0xa5a2, 0x2004, 0x603e, 0x2009, 0xa371,
-       0x210c, 0xd1f4, 0x00c0, 0xa10e, 0x0078, 0xa100, 0x2009, 0xa371,
-       0x210c, 0xd1f4, 0x0040, 0xa0fa, 0x6024, 0xc0e4, 0x6026, 0xa006,
-       0x0078, 0xa110, 0x2001, 0xa5a2, 0x200c, 0x8103, 0xa100, 0x603e,
-       0x6018, 0xa088, 0x002b, 0x2104, 0xa005, 0x0040, 0xa10b, 0xa088,
-       0x0003, 0x0078, 0xa103, 0x2c0a, 0x600f, 0x0000, 0xa085, 0x0001,
-       0x007c, 0x017e, 0x0c7e, 0x0e7e, 0x6120, 0xa2f0, 0x002b, 0x2e04,
-       0x2060, 0x8cff, 0x0040, 0xa130, 0x84ff, 0x00c0, 0xa123, 0x6020,
-       0xa106, 0x00c0, 0xa12b, 0x600c, 0x2072, 0x1078, 0x5a41, 0x1078,
-       0x753d, 0x0078, 0xa12d, 0xacf0, 0x0003, 0x2e64, 0x0078, 0xa119,
-       0x0e7f, 0x0c7f, 0x017f, 0x007c, 0x0d7e, 0x6018, 0xa0e8, 0x002b,
-       0x2d04, 0xa005, 0x0040, 0xa146, 0xac06, 0x0040, 0xa144, 0x2d04,
-       0xa0e8, 0x0003, 0x0078, 0xa138, 0x600c, 0x206a, 0x0d7f, 0x007c,
-       0x027e, 0x037e, 0x157e, 0x2011, 0xa325, 0x2204, 0xa084, 0x00ff,
-       0x2019, 0xa88e, 0x2334, 0xa636, 0x00c0, 0xa174, 0x8318, 0x2334,
-       0x2204, 0xa084, 0xff00, 0xa636, 0x00c0, 0xa174, 0x2011, 0xa890,
-       0x6018, 0xa098, 0x000a, 0x20a9, 0x0004, 0x1078, 0x7e55, 0x00c0,
-       0xa174, 0x2011, 0xa894, 0x6018, 0xa098, 0x0006, 0x20a9, 0x0004,
-       0x1078, 0x7e55, 0x00c0, 0xa174, 0x157f, 0x037f, 0x027f, 0x007c,
-       0x0e7e, 0x2071, 0xa300, 0x1078, 0x41f5, 0x1078, 0x260d, 0x0e7f,
-       0x007c, 0x0e7e, 0x6018, 0x2070, 0x7000, 0xd0fc, 0x0040, 0xa18a,
-       0x1078, 0xa18c, 0x0e7f, 0x007c, 0x6850, 0xc0e5, 0x6852, 0x007c,
-       0x0e7e, 0x0c7e, 0x077e, 0x067e, 0x057e, 0x047e, 0x027e, 0x017e,
-       0x127e, 0x2091, 0x8000, 0x2029, 0xa5b4, 0x252c, 0x2021, 0xa5ba,
-       0x2424, 0x2061, 0xaa00, 0x2071, 0xa300, 0x7644, 0x7060, 0xa606,
-       0x0040, 0xa1e4, 0x671c, 0xa786, 0x0001, 0x0040, 0xa1b3, 0xa786,
-       0x0008, 0x00c0, 0xa1da, 0x2500, 0xac06, 0x0040, 0xa1da, 0x2400,
-       0xac06, 0x0040, 0xa1da, 0x1078, 0x9ee5, 0x0040, 0xa1da, 0x1078,
-       0x9ef9, 0x00c0, 0xa1da, 0x6000, 0xa086, 0x0004, 0x00c0, 0xa1cc,
-       0x017e, 0x1078, 0x1749, 0x017f, 0x1078, 0x8c27, 0x00c0, 0xa1d2,
-       0x1078, 0x2839, 0x1078, 0x8c3b, 0x00c0, 0xa1d8, 0x1078, 0x7a05,
-       0x1078, 0x8c01, 0xace0, 0x0010, 0x2001, 0xa315, 0x2004, 0xac02,
-       0x00c8, 0xa1e4, 0x0078, 0xa1a3, 0x127f, 0x017f, 0x027f, 0x047f,
-       0x057f, 0x067f, 0x077f, 0x0c7f, 0x0e7f, 0x007c, 0x127e, 0x007e,
-       0x0e7e, 0x2091, 0x8000, 0x2071, 0xa340, 0xd5a4, 0x0040, 0xa1fb,
-       0x7034, 0x8000, 0x7036, 0xd5b4, 0x0040, 0xa201, 0x7030, 0x8000,
-       0x7032, 0xd5ac, 0x0040, 0xa208, 0x2071, 0xa34a, 0x1078, 0xa237,
-       0x0e7f, 0x007f, 0x127f, 0x007c, 0x127e, 0x007e, 0x0e7e, 0x2091,
-       0x8000, 0x2071, 0xa340, 0xd5a4, 0x0040, 0xa219, 0x7034, 0x8000,
-       0x7036, 0xd5b4, 0x0040, 0xa21f, 0x7030, 0x8000, 0x7032, 0xd5ac,
-       0x0040, 0xa226, 0x2071, 0xa34a, 0x1078, 0xa237, 0x0e7f, 0x007f,
-       0x127f, 0x007c, 0x127e, 0x007e, 0x0e7e, 0x2091, 0x8000, 0x2071,
-       0xa342, 0x1078, 0xa237, 0x0e7f, 0x007f, 0x127f, 0x007c, 0x2e04,
-       0x8000, 0x2072, 0x00c8, 0xa240, 0x8e70, 0x2e04, 0x8000, 0x2072,
-       0x007c, 0x0e7e, 0x2071, 0xa340, 0x1078, 0xa237, 0x0e7f, 0x007c,
-       0x0e7e, 0x2071, 0xa344, 0x1078, 0xa237, 0x0e7f, 0x007c, 0x0001,
-       0x0002, 0x0004, 0x0008, 0x0010, 0x0020, 0x0040, 0x0080, 0x0100,
-       0x0200, 0x0400, 0x0800, 0x1000, 0x2000, 0x4000, 0x8000, 0x6286
-};
-
-/************************************************************************
- *                                                                     *
- *               --- ISP2200 Initiator/Target Firmware ---              *
- *             with Fabric (Public Loop), Point-point, and              *
- *             expanded LUN addressing for FCTAPE                       *
- *                                                                     *
- ************************************************************************
-  Copyright (C) 2000 and 2100 Qlogic Corporation 
-  (www.qlogic.com)
-
-  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.
-************************************************************************/
-
-/*
- *     Firmware Version 2.01.27 (11:07 Dec 18, 2000)
- */
-
-static unsigned short risc_code_length2200 = 0x9cbf;
-static unsigned short risc_code2200[] = { 
-       0x0470, 0x0000, 0x0000, 0x9cbf, 0x0000, 0x0002, 0x0001, 0x001b,
-       0x0017, 0x2043, 0x4f50, 0x5952, 0x4947, 0x4854, 0x2031, 0x3939,
-       0x3920, 0x514c, 0x4f47, 0x4943, 0x2043, 0x4f52, 0x504f, 0x5241,
-       0x5449, 0x4f4e, 0x2049, 0x5350, 0x3232, 0x3030, 0x2046, 0x6972,
-       0x6d77, 0x6172, 0x6520, 0x2056, 0x6572, 0x7369, 0x6f6e, 0x2030,
-       0x322e, 0x3031, 0x2e32, 0x3720, 0x2020, 0x2020, 0x2400, 0x20c1,
-       0x0005, 0x2001, 0x017f, 0x2003, 0x0000, 0x20c9, 0xb1ff, 0x2091,
-       0x2000, 0x2059, 0x0000, 0x2b78, 0x7823, 0x0004, 0x2089, 0x27b5,
-       0x2051, 0xad00, 0x2a70, 0x2029, 0xe400, 0x2031, 0xffff, 0x2039,
-       0xe3e9, 0x2021, 0x0200, 0x0804, 0x1449, 0x20a1, 0xacbf, 0xa00e,
-       0x20a9, 0x0741, 0x41a4, 0x3400, 0x755e, 0x7662, 0x775a, 0x7466,
-       0x746a, 0x20a1, 0xb400, 0x7160, 0x810d, 0x810d, 0x810d, 0x810d,
-       0xa18c, 0x000f, 0x2001, 0x000b, 0xa112, 0xa00e, 0x21a8, 0x41a4,
-       0x3400, 0x8211, 0x1dd8, 0x7160, 0x3400, 0xa102, 0x0120, 0x0218,
-       0x20a8, 0xa00e, 0x41a4, 0x3800, 0xd08c, 0x01d8, 0x2009, 0xad00,
-       0x810d, 0x810d, 0x810d, 0x810d, 0xa18c, 0x000f, 0x2001, 0x0001,
-       0xa112, 0x20a1, 0x1000, 0xa00e, 0x21a8, 0x41a4, 0x8211, 0x1de0,
-       0x2009, 0xad00, 0x3400, 0xa102, 0x0120, 0x0218, 0x20a8, 0xa00e,
-       0x41a4, 0x080c, 0x13fc, 0x080c, 0x1613, 0x080c, 0x17ac, 0x080c,
-       0x1e67, 0x080c, 0x492e, 0x080c, 0x801a, 0x080c, 0x159c, 0x080c,
-       0x2ce6, 0x080c, 0x5a01, 0x080c, 0x5045, 0x080c, 0x6487, 0x080c,
-       0x236a, 0x080c, 0x6686, 0x080c, 0x5fae, 0x080c, 0x226b, 0x080c,
-       0x2338, 0x2091, 0x3009, 0x7823, 0x0000, 0x1004, 0x10c5, 0x7820,
-       0xa086, 0x0002, 0x1150, 0x7823, 0x4000, 0x0e04, 0x10bd, 0x781b,
-       0x0001, 0x2091, 0x5000, 0x2091, 0x4080, 0x2a70, 0x7003, 0x0000,
-       0x2a70, 0x7000, 0xa08e, 0x0003, 0x1158, 0x080c, 0x3c98, 0x080c,
-       0x2d0d, 0x080c, 0x5a4f, 0x080c, 0x51f4, 0x080c, 0x64a2, 0x0c80,
-       0x000b, 0x0c98, 0x10e4, 0x10e5, 0x1203, 0x10e2, 0x12cc, 0x13f9,
-       0x13fa, 0x13fb, 0x080c, 0x14f6, 0x0005, 0x0126, 0x00f6, 0x2091,
-       0x8000, 0x7000, 0xa086, 0x0001, 0x1904, 0x11d1, 0x080c, 0x1569,
-       0x080c, 0x574f, 0x0150, 0x080c, 0x5775, 0x1580, 0x2079, 0x0100,
-       0x7828, 0xa085, 0x1800, 0x782a, 0x0448, 0x080c, 0x569a, 0x7000,
-       0xa086, 0x0001, 0x1904, 0x11d1, 0x7088, 0xa086, 0x0028, 0x1904,
-       0x11d1, 0x2079, 0x0100, 0x7827, 0xffff, 0x7a28, 0xa295, 0x1e2f,
-       0x7a2a, 0x2011, 0x566e, 0x080c, 0x650d, 0x2011, 0x567b, 0x080c,
-       0x650d, 0x2011, 0x481b, 0x080c, 0x650d, 0x2011, 0x8030, 0x2019,
-       0x0000, 0x7087, 0x0000, 0x080c, 0x1d0f, 0x00e8, 0x080c, 0x41d1,
-       0x2079, 0x0100, 0x7844, 0xa005, 0x1904, 0x11d1, 0x2011, 0x481b,
-       0x080c, 0x650d, 0x2011, 0x567b, 0x080c, 0x650d, 0x080c, 0x1d0f,
-       0x2001, 0xaf8c, 0x2004, 0x780e, 0x7840, 0xa084, 0xfffb, 0x7842,
-       0x2011, 0x8010, 0x73c8, 0x080c, 0x3c5c, 0x7238, 0xc284, 0x723a,
-       0x2001, 0xad0c, 0x200c, 0xc1ac, 0x2102, 0x080c, 0x79bd, 0x2011,
-       0x0004, 0x080c, 0x959c, 0x080c, 0x4f71, 0x080c, 0x574f, 0x0158,
-       0x080c, 0x4917, 0x0140, 0x7087, 0x0001, 0x70c3, 0x0000, 0x080c,
-       0x436e, 0x0804, 0x11d1, 0x080c, 0x502d, 0x0120, 0x7a0c, 0xc2b4,
-       0x7a0e, 0x0050, 0x080c, 0x9937, 0x70d0, 0xd09c, 0x1128, 0x709c,
-       0xa005, 0x0110, 0x080c, 0x48f5, 0x70db, 0x0000, 0x70d7, 0x0000,
-       0x72d0, 0x080c, 0x574f, 0x1178, 0x2011, 0x0000, 0x0016, 0x080c,
-       0x2744, 0x2019, 0xaf8e, 0x211a, 0x001e, 0x704f, 0xffff, 0x7053,
-       0x00ef, 0x7073, 0x0000, 0x2079, 0xad51, 0x7804, 0xd0ac, 0x0108,
-       0xc295, 0x72d2, 0x080c, 0x574f, 0x0118, 0xa296, 0x0004, 0x0508,
-       0x2011, 0x0001, 0x080c, 0x959c, 0x7097, 0x0000, 0x709b, 0xffff,
-       0x7003, 0x0002, 0x00fe, 0x080c, 0x28fa, 0x2011, 0x0005, 0x080c,
-       0x7adf, 0x080c, 0x6c50, 0x080c, 0x574f, 0x0148, 0x00c6, 0x2061,
-       0x0100, 0x0016, 0x080c, 0x2744, 0x61e2, 0x001e, 0x00ce, 0x012e,
-       0x00d0, 0x7097, 0x0000, 0x709b, 0xffff, 0x7003, 0x0002, 0x2011,
-       0x0005, 0x080c, 0x7adf, 0x080c, 0x6c50, 0x080c, 0x574f, 0x0148,
-       0x00c6, 0x2061, 0x0100, 0x0016, 0x080c, 0x2744, 0x61e2, 0x001e,
-       0x00ce, 0x00fe, 0x012e, 0x0005, 0x00c6, 0x080c, 0x574f, 0x1118,
-       0x20a9, 0x0100, 0x0010, 0x20a9, 0x0082, 0x080c, 0x574f, 0x1118,
-       0x2009, 0x0000, 0x0010, 0x2009, 0x007e, 0x0016, 0x0026, 0x0036,
-       0x2110, 0x0026, 0x2019, 0x0029, 0x080c, 0x7cf4, 0x002e, 0x080c,
-       0xac07, 0x003e, 0x002e, 0x001e, 0x080c, 0x2bc9, 0x8108, 0x1f04,
-       0x11e5, 0x00ce, 0x706f, 0x0000, 0x7070, 0xa084, 0x00ff, 0x7072,
-       0x709f, 0x0000, 0x0005, 0x0126, 0x2091, 0x8000, 0x7000, 0xa086,
-       0x0002, 0x1904, 0x12ca, 0x7098, 0xa086, 0xffff, 0x0130, 0x080c,
-       0x28fa, 0x080c, 0x6c50, 0x0804, 0x12ca, 0x70d0, 0xd0ac, 0x1110,
-       0xd09c, 0x0540, 0xd084, 0x0530, 0x0006, 0x0016, 0x2001, 0x0103,
-       0x2009, 0xaf8c, 0x210c, 0x2102, 0x001e, 0x000e, 0xd08c, 0x01d0,
-       0x70d4, 0xa086, 0xffff, 0x0190, 0x080c, 0x2a56, 0x080c, 0x6c50,
-       0x70d0, 0xd094, 0x1904, 0x12ca, 0x2011, 0x0001, 0x2019, 0x0000,
-       0x080c, 0x2a8c, 0x080c, 0x6c50, 0x0804, 0x12ca, 0x70d8, 0xa005,
-       0x1904, 0x12ca, 0x7094, 0xa005, 0x1904, 0x12ca, 0x70d0, 0xd0a4,
-       0x0118, 0xd0b4, 0x0904, 0x12ca, 0x080c, 0x502d, 0x1904, 0x12ca,
-       0x2001, 0xad52, 0x2004, 0xd0ac, 0x01c8, 0x0156, 0x00c6, 0x20a9,
-       0x007f, 0x2009, 0x0000, 0x0016, 0x080c, 0x4cdc, 0x1118, 0x6000,
-       0xd0ec, 0x1138, 0x001e, 0x8108, 0x1f04, 0x125b, 0x00ce, 0x015e,
-       0x0028, 0x001e, 0x00ce, 0x015e, 0x0804, 0x12ca, 0x0006, 0x0016,
-       0x2001, 0x0103, 0x2009, 0xaf8c, 0x210c, 0x2102, 0x001e, 0x000e,
-       0xa006, 0x2009, 0x0700, 0x20a9, 0x0002, 0x20a1, 0xafb5, 0x40a1,
-       0x706c, 0x8007, 0x7170, 0x810f, 0x20a9, 0x0002, 0x40a1, 0x2009,
-       0x0000, 0x080c, 0x14dc, 0x2001, 0x0000, 0x810f, 0x20a9, 0x0002,
-       0x40a1, 0xa006, 0x2009, 0x0200, 0x20a9, 0x0002, 0x20a1, 0xafc5,
-       0x40a1, 0x7030, 0xc08c, 0x7032, 0x7003, 0x0003, 0x709b, 0xffff,
-       0x080c, 0x1562, 0xa006, 0x080c, 0x261e, 0x080c, 0x3cce, 0x00f6,
-       0x2079, 0x0100, 0x080c, 0x5775, 0x0150, 0x080c, 0x574f, 0x7828,
-       0x0118, 0xa084, 0xe1ff, 0x0010, 0xa084, 0xffdf, 0x782a, 0x00fe,
-       0x2001, 0xafc8, 0x2004, 0xa086, 0x0005, 0x1120, 0x2011, 0x0000,
-       0x080c, 0x7adf, 0x2011, 0x0000, 0x080c, 0x7ae9, 0x080c, 0x6c50,
-       0x080c, 0x6d0d, 0x012e, 0x0005, 0x0016, 0x0046, 0x00f6, 0x0126,
-       0x2091, 0x8000, 0x2079, 0x0100, 0x2009, 0xad33, 0x2104, 0xa005,
-       0x1110, 0x080c, 0x2770, 0x2009, 0x00f7, 0x080c, 0x48de, 0x7940,
-       0xa18c, 0x0010, 0x7942, 0x7924, 0xd1b4, 0x0110, 0x7827, 0x0040,
-       0xd19c, 0x0110, 0x7827, 0x0008, 0x0006, 0x0036, 0x0156, 0x7954,
-       0xd1ac, 0x1904, 0x133a, 0x080c, 0x5761, 0x0158, 0x080c, 0x5775,
-       0x1128, 0x2001, 0xaf9d, 0x2003, 0x0000, 0x0070, 0x080c, 0x5757,
-       0x0dc0, 0x2001, 0xaf9d, 0x2003, 0xaaaa, 0x2001, 0xaf9e, 0x2003,
-       0x0001, 0x080c, 0x569a, 0x0058, 0x080c, 0x574f, 0x0140, 0x2009,
-       0x00f8, 0x080c, 0x48de, 0x7843, 0x0090, 0x7843, 0x0010, 0x20a9,
-       0x09c4, 0x7820, 0xd09c, 0x1138, 0x080c, 0x574f, 0x0138, 0x7824,
-       0xd0ac, 0x1904, 0x13e0, 0x1f04, 0x1319, 0x0070, 0x7824, 0x080c,
-       0x576b, 0x0118, 0xd0ac, 0x1904, 0x13e0, 0xa084, 0x1800, 0x0d98,
-       0x7003, 0x0001, 0x0804, 0x13e0, 0x2001, 0x0001, 0x080c, 0x261e,
-       0x0804, 0x13ef, 0x7850, 0xa084, 0x0180, 0x7852, 0x782f, 0x0020,
-       0x20a9, 0x0046, 0x1d04, 0x1342, 0x2091, 0x6000, 0x1f04, 0x1342,
-       0x7850, 0xa084, 0x0180, 0xa085, 0x0400, 0x7852, 0x782f, 0x0000,
-       0x080c, 0x5761, 0x0158, 0x080c, 0x5775, 0x1128, 0x2001, 0xaf9d,
-       0x2003, 0x0000, 0x0070, 0x080c, 0x5757, 0x0dc0, 0x2001, 0xaf9d,
-       0x2003, 0xaaaa, 0x2001, 0xaf9e, 0x2003, 0x0001, 0x080c, 0x569a,
-       0x0020, 0x2009, 0x00f8, 0x080c, 0x48de, 0x20a9, 0x000e, 0xe000,
-       0x1f04, 0x136f, 0x7850, 0xa084, 0x0180, 0xa085, 0x1400, 0x7852,
-       0x080c, 0x574f, 0x0120, 0x7843, 0x0090, 0x7843, 0x0010, 0x2021,
-       0xe678, 0x2019, 0xea60, 0x7820, 0xd09c, 0x1558, 0x080c, 0x574f,
-       0x05b8, 0x7824, 0xd0ac, 0x1904, 0x13e0, 0x080c, 0x5775, 0x1508,
-       0x0046, 0x2021, 0x0190, 0x8421, 0x1df0, 0x004e, 0x8421, 0x11c8,
-       0x7827, 0x0048, 0x20a9, 0x01f4, 0x1d04, 0x139c, 0x2091, 0x6000,
-       0x1f04, 0x139c, 0x7824, 0xa084, 0x0068, 0x15a8, 0x2001, 0xaf9d,
-       0x2003, 0xaaaa, 0x2001, 0xaf9e, 0x2003, 0x0001, 0x7003, 0x0001,
-       0x0478, 0x8319, 0x1980, 0x2009, 0xad33, 0x2104, 0x8000, 0x200a,
-       0xa084, 0xfff0, 0x0120, 0x200b, 0x0000, 0x080c, 0x2770, 0x00d8,
-       0x080c, 0x5761, 0x1140, 0xa4a2, 0x0064, 0x1128, 0x080c, 0x5726,
-       0x7003, 0x0001, 0x00a8, 0x7827, 0x1800, 0xe000, 0xe000, 0x7824,
-       0x080c, 0x576b, 0x0110, 0xd0ac, 0x1158, 0xa084, 0x1800, 0x09c8,
-       0x7003, 0x0001, 0x0028, 0x2001, 0x0001, 0x080c, 0x261e, 0x0048,
-       0x2001, 0xad33, 0x2003, 0x0000, 0x7827, 0x0048, 0x7828, 0xc09d,
-       0x782a, 0x7850, 0xa084, 0x0180, 0xa085, 0x0400, 0x7852, 0x015e,
-       0x003e, 0x000e, 0x080c, 0x1539, 0x012e, 0x00fe, 0x004e, 0x001e,
-       0x0005, 0x0005, 0x0005, 0x0005, 0x2a70, 0x2001, 0xaf9d, 0x2003,
-       0x0000, 0x7087, 0x0000, 0x2009, 0x0100, 0x2104, 0xa082, 0x0002,
-       0x0218, 0x704f, 0xffff, 0x0010, 0x704f, 0x0000, 0x7057, 0xffff,
-       0x706f, 0x0000, 0x7073, 0x0000, 0x080c, 0x9937, 0x2061, 0xaf8d,
-       0x6003, 0x0909, 0x6007, 0x0000, 0x600b, 0x8800, 0x600f, 0x0200,
-       0x6013, 0x00ff, 0x6017, 0x0003, 0x601b, 0x0000, 0x601f, 0x07d0,
-       0x2061, 0xaf95, 0x6003, 0x8000, 0x6007, 0x0000, 0x600b, 0x0000,
-       0x600f, 0x0200, 0x6013, 0x00ff, 0x6017, 0x0000, 0x601b, 0x0001,
-       0x601f, 0x0000, 0x2061, 0xafa6, 0x6003, 0x514c, 0x6007, 0x4f47,
-       0x600b, 0x4943, 0x600f, 0x2020, 0x2001, 0xad27, 0x2003, 0x0000,
-       0x0005, 0x04a0, 0x2011, 0x0000, 0x81ff, 0x0570, 0xa186, 0x0001,
-       0x1148, 0x2031, 0x8fff, 0x2039, 0xcc01, 0x2021, 0x0100, 0x2029,
-       0xcc00, 0x00e8, 0xa186, 0x0002, 0x1118, 0x2011, 0x0000, 0x00b8,
-       0xa186, 0x0005, 0x1118, 0x2011, 0x0001, 0x0088, 0xa186, 0x0009,
-       0x1118, 0x2011, 0x0002, 0x0058, 0xa186, 0x000a, 0x1118, 0x2011,
-       0x0002, 0x0028, 0xa186, 0x0055, 0x1110, 0x2011, 0x0003, 0x3800,
-       0xa084, 0xfffc, 0xa205, 0x20c0, 0x0804, 0x104d, 0xa00e, 0x2011,
-       0x0003, 0x2019, 0x1485, 0x0804, 0x14d6, 0x2019, 0xaaaa, 0x2061,
-       0xffff, 0x2c14, 0x2362, 0xe000, 0xe000, 0x2c04, 0xa306, 0x2262,
-       0x1110, 0xc1b5, 0xc1a5, 0x2011, 0x0000, 0x2019, 0x1498, 0x04f0,
-       0x2019, 0xaaaa, 0x2061, 0xffff, 0x2c14, 0x2362, 0xe000, 0xe000,
-       0x2c1c, 0x2061, 0x7fff, 0xe000, 0xe000, 0x2c04, 0x2061, 0xffff,
-       0x2262, 0xa306, 0x0110, 0xc18d, 0x0008, 0xc185, 0x2011, 0x0002,
-       0x2019, 0x14b3, 0x0418, 0x2061, 0xffff, 0x2019, 0xaaaa, 0x2c14,
-       0x2362, 0xe000, 0xe000, 0x2c04, 0x2262, 0xa306, 0x1180, 0x2c14,
-       0x2362, 0xe000, 0xe000, 0x2c1c, 0x2061, 0x7fff, 0x2c04, 0x2061,
-       0xffff, 0x2262, 0xa306, 0x1110, 0xc195, 0x0008, 0xc19d, 0x2011,
-       0x0001, 0x2019, 0x14d4, 0x0010, 0x0804, 0x144a, 0x3800, 0xa084,
-       0xfffc, 0xa205, 0x20c0, 0x0837, 0x2011, 0x0000, 0x080c, 0x4cdc,
-       0x1178, 0x6004, 0xa0c4, 0x00ff, 0xa8c6, 0x0006, 0x0128, 0xa0c4,
-       0xff00, 0xa8c6, 0x0600, 0x1120, 0xa186, 0x0080, 0x0108, 0x8210,
-       0x8108, 0xa186, 0x0100, 0x1d50, 0x2208, 0x0005, 0x2091, 0x8000,
-       0x0e04, 0x14f8, 0x0006, 0x0016, 0x2079, 0x0000, 0x7818, 0xd084,
-       0x1de8, 0x001e, 0x792e, 0x000e, 0x782a, 0x000e, 0x7826, 0x3900,
-       0x783a, 0x7823, 0x8002, 0x781b, 0x0001, 0x2091, 0x5000, 0x0126,
-       0x0156, 0x0146, 0x20a9, 0x0010, 0x20a1, 0xb0c8, 0x2091, 0x2000,
-       0x40a1, 0x20a9, 0x0010, 0x2091, 0x2200, 0x40a1, 0x20a9, 0x0010,
-       0x2091, 0x2400, 0x40a1, 0x20a9, 0x0010, 0x2091, 0x2600, 0x40a1,
-       0x20a9, 0x0010, 0x2091, 0x2800, 0x40a1, 0x014e, 0x015e, 0x012e,
-       0x2079, 0xad00, 0x7803, 0x0005, 0x2091, 0x4080, 0x04c9, 0x0cf8,
-       0x0005, 0x0006, 0x080c, 0x1584, 0x1518, 0x00f6, 0x2079, 0xad23,
-       0x2f04, 0x8000, 0x207a, 0xa082, 0x000f, 0x0258, 0xa006, 0x207a,
-       0x2079, 0xad25, 0x2f04, 0xa084, 0x0001, 0xa086, 0x0001, 0x207a,
-       0x0070, 0x2079, 0xad25, 0x2f7c, 0x8fff, 0x1128, 0x2001, 0x0c03,
-       0x2003, 0x0040, 0x0020, 0x2001, 0x0c03, 0x2003, 0x00c0, 0x00fe,
-       0x000e, 0x0005, 0x0409, 0x1120, 0x2001, 0x0c03, 0x2003, 0x0080,
-       0x0005, 0x00d1, 0x1120, 0x2001, 0x0c03, 0x2003, 0x0040, 0x0005,
-       0x0006, 0x0091, 0x1178, 0x2001, 0x0c03, 0x2003, 0x0040, 0x2009,
-       0x0fff, 0x00a1, 0x2001, 0x0c03, 0x2003, 0x0080, 0x2009, 0x0fff,
-       0x0069, 0x0c88, 0x000e, 0x0005, 0x00c6, 0x2061, 0x0c00, 0x2c04,
-       0xa084, 0x00ff, 0xa086, 0x00aa, 0x00ce, 0x0005, 0x0156, 0x0126,
-       0xa18c, 0x0fff, 0x21a8, 0x1d04, 0x1593, 0x2091, 0x6000, 0x1f04,
-       0x1593, 0x012e, 0x015e, 0x0005, 0x2071, 0xad00, 0x715c, 0x712e,
-       0x2021, 0x0001, 0xa190, 0x0030, 0xa298, 0x0030, 0x0240, 0x7060,
-       0xa302, 0x1228, 0x220a, 0x2208, 0x2310, 0x8420, 0x0ca8, 0x3800,
-       0xd08c, 0x0148, 0x7060, 0xa086, 0xad00, 0x0128, 0x7063, 0xad00,
-       0x2011, 0x1000, 0x0c48, 0x200b, 0x0000, 0x74ae, 0x74b2, 0x0005,
-       0x00e6, 0x0126, 0x2091, 0x8000, 0x2071, 0xad00, 0x70b0, 0xa0ea,
-       0x0010, 0x0268, 0x8001, 0x70b2, 0x702c, 0x2068, 0x2d04, 0x702e,
-       0x206b, 0x0000, 0x6807, 0x0000, 0x012e, 0x00ee, 0x0005, 0xa06e,
-       0x0cd8, 0x00e6, 0x2071, 0xad00, 0x0126, 0x2091, 0x8000, 0x70b0,
-       0x8001, 0x0260, 0x70b2, 0x702c, 0x2068, 0x2d04, 0x702e, 0x206b,
-       0x0000, 0x6807, 0x0000, 0x012e, 0x00ee, 0x0005, 0xa06e, 0x0cd8,
-       0x00e6, 0x0126, 0x2091, 0x8000, 0x2071, 0xad00, 0x702c, 0x206a,
-       0x2d00, 0x702e, 0x70b0, 0x8000, 0x70b2, 0x012e, 0x00ee, 0x0005,
-       0x8dff, 0x0138, 0x6804, 0x6807, 0x0000, 0x0006, 0x0c49, 0x00de,
-       0x0cb8, 0x0005, 0x00e6, 0x2071, 0xad00, 0x70b0, 0xa08a, 0x0010,
-       0xa00d, 0x00ee, 0x0005, 0x00e6, 0x2071, 0xafec, 0x7007, 0x0000,
-       0x701b, 0x0000, 0x701f, 0x0000, 0x2071, 0x0000, 0x7010, 0xa085,
-       0x8004, 0x7012, 0x00ee, 0x0005, 0x00e6, 0x2270, 0x700b, 0x0000,
-       0x2071, 0xafec, 0x7018, 0xa088, 0xaff5, 0x220a, 0x8000, 0xa084,
-       0x0007, 0x701a, 0x7004, 0xa005, 0x1128, 0x00f6, 0x2079, 0x0010,
-       0x0081, 0x00fe, 0x00ee, 0x0005, 0x00e6, 0x2071, 0xafec, 0x7004,
-       0xa005, 0x1128, 0x00f6, 0x2079, 0x0010, 0x0019, 0x00fe, 0x00ee,
-       0x0005, 0x7000, 0x0002, 0x164f, 0x16b3, 0x16d0, 0x16d0, 0x7018,
-       0x711c, 0xa106, 0x1118, 0x7007, 0x0000, 0x0005, 0x00d6, 0xa180,
-       0xaff5, 0x2004, 0x700a, 0x2068, 0x8108, 0xa18c, 0x0007, 0x711e,
-       0x7803, 0x0026, 0x6824, 0x7832, 0x6828, 0x7836, 0x682c, 0x783a,
-       0x6830, 0x783e, 0x6810, 0x700e, 0x680c, 0x7016, 0x6804, 0x00de,
-       0xd084, 0x0120, 0x7007, 0x0001, 0x0029, 0x0005, 0x7007, 0x0002,
-       0x00b1, 0x0005, 0x0016, 0x0026, 0x710c, 0x2011, 0x0040, 0xa182,
-       0x0040, 0x1210, 0x2110, 0xa006, 0x700e, 0x7212, 0x8203, 0x7822,
-       0x7803, 0x0020, 0x7803, 0x0041, 0x002e, 0x001e, 0x0005, 0x0016,
-       0x0026, 0x0136, 0x0146, 0x0156, 0x7014, 0x2098, 0x20a1, 0x0014,
-       0x7803, 0x0026, 0x710c, 0x2011, 0x0040, 0xa182, 0x0040, 0x1210,
-       0x2110, 0xa006, 0x700e, 0x22a8, 0x53a6, 0x8203, 0x7822, 0x7803,
-       0x0020, 0x3300, 0x7016, 0x7803, 0x0001, 0x015e, 0x014e, 0x013e,
-       0x002e, 0x001e, 0x0005, 0x0136, 0x0146, 0x0156, 0x2099, 0xadf9,
-       0x20a1, 0x0018, 0x20a9, 0x0008, 0x53a3, 0x7803, 0x0020, 0x0126,
-       0x2091, 0x8000, 0x7803, 0x0041, 0x7007, 0x0003, 0x7000, 0xc084,
-       0x7002, 0x700b, 0xadf4, 0x012e, 0x015e, 0x014e, 0x013e, 0x0005,
-       0x0136, 0x0146, 0x0156, 0x2001, 0xae28, 0x209c, 0x20a1, 0x0014,
-       0x7803, 0x0026, 0x2001, 0xae29, 0x20ac, 0x53a6, 0x2099, 0xae2a,
-       0x20a1, 0x0018, 0x20a9, 0x0008, 0x53a3, 0x7803, 0x0020, 0x0126,
-       0x2091, 0x8000, 0x7803, 0x0001, 0x7007, 0x0004, 0x7000, 0xc08c,
-       0x7002, 0x700b, 0xae25, 0x012e, 0x015e, 0x014e, 0x013e, 0x0005,
-       0x0016, 0x00e6, 0x2071, 0xafec, 0x00f6, 0x2079, 0x0010, 0x7904,
-       0x7803, 0x0002, 0xd1fc, 0x0120, 0xa18c, 0x0700, 0x7004, 0x0023,
-       0x00fe, 0x00ee, 0x001e, 0x0005, 0x1649, 0x1713, 0x1741, 0x176b,
-       0x179b, 0x1712, 0x0cf8, 0xa18c, 0x0700, 0x1528, 0x0136, 0x0146,
-       0x0156, 0x7014, 0x20a0, 0x2099, 0x0014, 0x7803, 0x0040, 0x7010,
-       0x20a8, 0x53a5, 0x3400, 0x7016, 0x015e, 0x014e, 0x013e, 0x700c,
-       0xa005, 0x0570, 0x7830, 0x7832, 0x7834, 0x7836, 0x080c, 0x167a,
-       0x0005, 0x7008, 0xa080, 0x0002, 0x2003, 0x0100, 0x7007, 0x0000,
-       0x080c, 0x1649, 0x0005, 0x7008, 0xa080, 0x0002, 0x2003, 0x0200,
-       0x0ca8, 0xa18c, 0x0700, 0x1150, 0x700c, 0xa005, 0x0188, 0x7830,
-       0x7832, 0x7834, 0x7836, 0x080c, 0x168f, 0x0005, 0x7008, 0xa080,
-       0x0002, 0x2003, 0x0200, 0x7007, 0x0000, 0x080c, 0x1649, 0x0005,
-       0x00d6, 0x7008, 0x2068, 0x7830, 0x6826, 0x7834, 0x682a, 0x7838,
-       0x682e, 0x783c, 0x6832, 0x680b, 0x0100, 0x00de, 0x7007, 0x0000,
-       0x080c, 0x1649, 0x0005, 0xa18c, 0x0700, 0x1540, 0x0136, 0x0146,
-       0x0156, 0x2001, 0xadf7, 0x2004, 0xa080, 0x000d, 0x20a0, 0x2099,
-       0x0014, 0x7803, 0x0040, 0x20a9, 0x0020, 0x53a5, 0x2001, 0xadf9,
-       0x2004, 0xd0bc, 0x0148, 0x2001, 0xae02, 0x2004, 0xa080, 0x000d,
-       0x20a0, 0x20a9, 0x0020, 0x53a5, 0x015e, 0x014e, 0x013e, 0x7007,
-       0x0000, 0x080c, 0x5ae6, 0x080c, 0x1649, 0x0005, 0x2011, 0x8003,
-       0x080c, 0x3c5c, 0x0cf8, 0xa18c, 0x0700, 0x1148, 0x2001, 0xae27,
-       0x2003, 0x0100, 0x7007, 0x0000, 0x080c, 0x1649, 0x0005, 0x2011,
-       0x8004, 0x080c, 0x3c5c, 0x0cf8, 0x0126, 0x2091, 0x2200, 0x2079,
-       0x0030, 0x2071, 0xaffd, 0x7003, 0x0000, 0x700f, 0xb003, 0x7013,
-       0xb003, 0x780f, 0x00f6, 0x7803, 0x0004, 0x012e, 0x0005, 0x6934,
-       0xa184, 0x0007, 0x0002, 0x17cb, 0x1809, 0x17cb, 0x17cb, 0x17cb,
-       0x17f1, 0x17d8, 0x17cf, 0xa085, 0x0001, 0x0804, 0x1823, 0x684c,
-       0xd0bc, 0x0dc8, 0x6860, 0x682e, 0x685c, 0x682a, 0x6858, 0x04c8,
-       0xa18c, 0x00ff, 0xa186, 0x001e, 0x1d70, 0x684c, 0xd0bc, 0x0d58,
-       0x6860, 0x682e, 0x685c, 0x682a, 0x6804, 0x681a, 0xa080, 0x000d,
-       0x2004, 0xa084, 0x000f, 0xa080, 0x2186, 0x2005, 0x6832, 0x6858,
-       0x0440, 0xa18c, 0x00ff, 0xa186, 0x0015, 0x19a8, 0x684c, 0xd0ac,
-       0x0990, 0x6804, 0x681a, 0xa080, 0x000d, 0x2004, 0xa084, 0x000f,
-       0xa080, 0x2186, 0x2005, 0x6832, 0xa006, 0x682e, 0x682a, 0x6858,
-       0x0080, 0x684c, 0xd0ac, 0x0904, 0x17cb, 0xa006, 0x682e, 0x682a,
-       0x6858, 0xa18c, 0x000f, 0xa188, 0x2186, 0x210d, 0x6932, 0x2d08,
-       0x691a, 0x6826, 0x684c, 0xc0dd, 0x684e, 0xa006, 0x680a, 0x697c,
-       0x6912, 0x6980, 0x6916, 0x0005, 0x20e1, 0x0007, 0x20e1, 0x2000,
-       0x2001, 0x020a, 0x2004, 0x82ff, 0x01a8, 0xa280, 0x0004, 0x00d6,
-       0x206c, 0x684c, 0xd0dc, 0x1150, 0x080c, 0x17bf, 0x0138, 0x00de,
-       0xa280, 0x0000, 0x2003, 0x0002, 0xa016, 0x0020, 0x6808, 0x8000,
-       0x680a, 0x00de, 0x0126, 0x0046, 0x0036, 0x0026, 0x2091, 0x2200,
-       0x002e, 0x003e, 0x004e, 0x7000, 0xa005, 0x01d0, 0x710c, 0x220a,
-       0x8108, 0x230a, 0x8108, 0x240a, 0x8108, 0xa182, 0xb01e, 0x0210,
-       0x2009, 0xb003, 0x710e, 0x7010, 0xa102, 0xa082, 0x0009, 0x0118,
-       0xa080, 0x001b, 0x1118, 0x2009, 0x0138, 0x200a, 0x012e, 0x0005,
-       0x7206, 0x2001, 0x1866, 0x0006, 0x2260, 0x0804, 0x197a, 0x0126,
-       0x0026, 0x0036, 0x00c6, 0x0006, 0x2091, 0x2200, 0x000e, 0x004e,
-       0x003e, 0x002e, 0x00d6, 0x00c6, 0x2460, 0x6110, 0x2168, 0x6a62,
-       0x6b5e, 0xa005, 0x0904, 0x18c8, 0x6808, 0xa005, 0x0904, 0x18ff,
-       0x7000, 0xa005, 0x1108, 0x0488, 0x700c, 0x7110, 0xa106, 0x1904,
-       0x1907, 0x7004, 0xa406, 0x1548, 0x2001, 0x0005, 0x2004, 0xd08c,
-       0x0168, 0x0046, 0x080c, 0x1a6c, 0x004e, 0x2460, 0x6010, 0xa080,
-       0x0002, 0x2004, 0xa005, 0x0904, 0x18ff, 0x0c10, 0x2001, 0x0207,
-       0x2004, 0xd09c, 0x1d48, 0x7804, 0xa084, 0x6000, 0x0120, 0xa086,
-       0x6000, 0x0108, 0x0c08, 0x7818, 0x6812, 0x781c, 0x6816, 0x7803,
-       0x0004, 0x7003, 0x0000, 0x7004, 0x2060, 0x6100, 0xa18e, 0x0004,
-       0x1904, 0x1907, 0x2009, 0x0048, 0x080c, 0x80a7, 0x0804, 0x1907,
-       0x6808, 0xa005, 0x05a0, 0x7000, 0xa005, 0x0588, 0x700c, 0x7110,
-       0xa106, 0x1118, 0x7004, 0xa406, 0x1550, 0x2001, 0x0005, 0x2004,
-       0xd08c, 0x0160, 0x0046, 0x080c, 0x1a6c, 0x004e, 0x2460, 0x6010,
-       0xa080, 0x0002, 0x2004, 0xa005, 0x01d0, 0x0c28, 0x2001, 0x0207,
-       0x2004, 0xd09c, 0x1d50, 0x2001, 0x0005, 0x2004, 0xd08c, 0x1d50,
-       0x7804, 0xa084, 0x6000, 0x0118, 0xa086, 0x6000, 0x19f0, 0x7818,
-       0x6812, 0x781c, 0x6816, 0x7803, 0x0004, 0x7003, 0x0000, 0x6100,
-       0xa18e, 0x0004, 0x1120, 0x2009, 0x0048, 0x080c, 0x80a7, 0x00ce,
-       0x00de, 0x012e, 0x0005, 0x00f6, 0x00e6, 0x0026, 0x0036, 0x0046,
-       0x0056, 0x080c, 0x1d86, 0x0026, 0x0056, 0x2071, 0xaffd, 0x7000,
-       0xa086, 0x0000, 0x0580, 0x7004, 0xac06, 0x11f8, 0x2079, 0x0030,
-       0x7000, 0xa086, 0x0003, 0x01c8, 0x7804, 0xd0fc, 0x1198, 0x2001,
-       0x0207, 0x2004, 0xd09c, 0x1dc0, 0x7803, 0x0004, 0x7804, 0xd0ac,
-       0x1de8, 0x7803, 0x0002, 0x7803, 0x0009, 0x7003, 0x0003, 0x7007,
-       0x0000, 0x0018, 0x080c, 0x1a6c, 0x08d0, 0x0156, 0x20a9, 0x0009,
-       0x2009, 0xb003, 0x2104, 0xac06, 0x1108, 0x200a, 0xa188, 0x0003,
-       0x1f04, 0x1942, 0x015e, 0x005e, 0x002e, 0x2001, 0x015d, 0x201c,
-       0x831a, 0x2302, 0x2001, 0x0160, 0x2502, 0x2001, 0x0138, 0x2202,
-       0x005e, 0x004e, 0x003e, 0x002e, 0x00ee, 0x00fe, 0x0005, 0x700c,
-       0x7110, 0xa106, 0x0904, 0x19dd, 0x2104, 0x7006, 0x2060, 0x8108,
-       0x211c, 0x8108, 0x2124, 0x8108, 0xa182, 0xb01e, 0x0210, 0x2009,
-       0xb003, 0x7112, 0x700c, 0xa106, 0x1128, 0x080c, 0x2744, 0x2001,
-       0x0138, 0x2102, 0x8cff, 0x0588, 0x6010, 0x2068, 0x2d58, 0x6828,
-       0xa406, 0x1580, 0x682c, 0xa306, 0x1568, 0x7004, 0x2060, 0x6020,
-       0xc0d4, 0x6022, 0x684c, 0xd0f4, 0x0128, 0x6817, 0xffff, 0x6813,
-       0xffff, 0x00d8, 0x6850, 0xd0f4, 0x1130, 0x7803, 0x0004, 0x6810,
-       0x781a, 0x6814, 0x781e, 0x6824, 0x2050, 0x6818, 0x2060, 0x6830,
-       0x2040, 0x6034, 0xa0cc, 0x000f, 0x2009, 0x0011, 0x04c9, 0x0118,
-       0x2009, 0x0001, 0x04a9, 0x2d58, 0x0005, 0x080c, 0x1ced, 0x0904,
-       0x195f, 0x0cd0, 0x6020, 0xd0d4, 0x01b8, 0x6038, 0xa402, 0x6034,
-       0xa303, 0x0108, 0x1288, 0x643a, 0x6336, 0x6c2a, 0x6b2e, 0x0046,
-       0x0036, 0x2400, 0x6c7c, 0xa402, 0x6812, 0x2300, 0x6b80, 0xa303,
-       0x6816, 0x003e, 0x004e, 0x0018, 0x080c, 0x98cb, 0x09f0, 0x601c,
-       0xa08e, 0x0008, 0x0904, 0x1985, 0xa08e, 0x000a, 0x0904, 0x1985,
-       0x080c, 0x21a6, 0x1990, 0x0804, 0x1985, 0x7003, 0x0000, 0x0005,
-       0x8aff, 0x0904, 0x1a46, 0xa03e, 0x2730, 0x6850, 0xd0fc, 0x11b8,
-       0xd0f4, 0x1528, 0x00d6, 0x2805, 0xac68, 0x2900, 0x0002, 0x1a30,
-       0x1a15, 0x1a15, 0x1a30, 0x1a30, 0x1a29, 0x1a30, 0x1a15, 0x1a30,
-       0x1a1a, 0x1a1a, 0x1a30, 0x1a30, 0x1a30, 0x1a21, 0x1a1a, 0x7803,
-       0x0004, 0xc0fc, 0x6852, 0x6b6c, 0x6a70, 0x6d1c, 0x6c20, 0x00d6,
-       0xd99c, 0x0548, 0x2805, 0xac68, 0x6f08, 0x6e0c, 0x0420, 0xc0f4,
-       0x6852, 0x6b6c, 0x6a70, 0x00d6, 0x0428, 0x6b08, 0x6a0c, 0x6d00,
-       0x6c04, 0x00c8, 0x6b10, 0x6a14, 0x6d00, 0x6c04, 0x6f08, 0x6e0c,
-       0x0090, 0x00de, 0x00d6, 0x6834, 0xa084, 0x00ff, 0xa086, 0x001e,
-       0x1138, 0x00de, 0x080c, 0x2148, 0x1904, 0x19e0, 0xa00e, 0x00b0,
-       0x00de, 0x080c, 0x14f6, 0x7b22, 0x7a26, 0x7d32, 0x7c36, 0x7f3a,
-       0x7e3e, 0x7902, 0x7000, 0x8000, 0x7002, 0x00de, 0x6828, 0xa300,
-       0x682a, 0x682c, 0xa201, 0x682e, 0x080c, 0x2148, 0x0005, 0x080c,
-       0x14f6, 0x080c, 0x1e1a, 0x7004, 0x2060, 0x00d6, 0x6010, 0x2068,
-       0x7003, 0x0000, 0x080c, 0x1d22, 0x080c, 0x9596, 0x0170, 0x6808,
-       0x8001, 0x680a, 0x697c, 0x6912, 0x6980, 0x6916, 0x682b, 0xffff,
-       0x682f, 0xffff, 0x6850, 0xc0bd, 0x6852, 0x00de, 0x080c, 0x929c,
-       0x0804, 0x1c5e, 0x080c, 0x14f6, 0x0126, 0x2091, 0x2200, 0x0006,
-       0x0016, 0x2b68, 0x6818, 0x2060, 0x7904, 0x7803, 0x0002, 0xa184,
-       0x0700, 0x1978, 0xa184, 0x0003, 0xa086, 0x0003, 0x0d58, 0x7000,
-       0x0002, 0x1a89, 0x1a8f, 0x1b92, 0x1c39, 0x1c4d, 0x1a89, 0x1a89,
-       0x1a89, 0x7804, 0xd09c, 0x1904, 0x1c5e, 0x080c, 0x14f6, 0x8001,
-       0x7002, 0xa184, 0x0880, 0x1190, 0xd19c, 0x1904, 0x1b20, 0x8aff,
-       0x0904, 0x1b20, 0x2009, 0x0001, 0x080c, 0x19e0, 0x0904, 0x1c5e,
-       0x2009, 0x0001, 0x080c, 0x19e0, 0x0804, 0x1c5e, 0x7803, 0x0004,
-       0x7003, 0x0000, 0xd1bc, 0x1904, 0x1b00, 0x0026, 0x0036, 0x7c20,
-       0x7d24, 0x7e30, 0x7f34, 0x7818, 0x6812, 0x781c, 0x6816, 0x2001,
-       0x0201, 0x2004, 0xa005, 0x0140, 0x7808, 0xd0ec, 0x1128, 0x7803,
-       0x0009, 0x7003, 0x0004, 0x0010, 0x080c, 0x1c62, 0x6b28, 0x6a2c,
-       0x2400, 0x686e, 0xa31a, 0x2500, 0x6872, 0xa213, 0x6b2a, 0x6a2e,
-       0x00c6, 0x7004, 0x2060, 0x6020, 0xd0f4, 0x1110, 0x633a, 0x6236,
-       0x00ce, 0x003e, 0x002e, 0x6e1e, 0x6f22, 0x080c, 0x215e, 0x2a00,
-       0x6826, 0x2c00, 0x681a, 0x2800, 0x6832, 0x6850, 0xc0fd, 0x6852,
-       0x6808, 0x8001, 0x680a, 0x1148, 0x684c, 0xd0e4, 0x0130, 0x7004,
-       0x2060, 0x2009, 0x0048, 0x080c, 0x80a7, 0x7000, 0xa086, 0x0004,
-       0x0904, 0x1c5e, 0x7003, 0x0000, 0x080c, 0x195f, 0x0804, 0x1c5e,
-       0x0056, 0x7d0c, 0xd5bc, 0x1110, 0x080c, 0xac73, 0x005e, 0x080c,
-       0x1d22, 0x00f6, 0x7004, 0x2078, 0x080c, 0x5029, 0x0118, 0x7820,
-       0xc0f5, 0x7822, 0x00fe, 0x682b, 0xffff, 0x682f, 0xffff, 0x6808,
-       0x8001, 0x680a, 0x697c, 0x791a, 0x6980, 0x791e, 0x0804, 0x1c5e,
-       0x7004, 0x00c6, 0x2060, 0x6020, 0x00ce, 0xd0f4, 0x0128, 0x6808,
-       0x8001, 0x680a, 0x0804, 0x1c5e, 0x7818, 0x6812, 0x7a1c, 0x6a16,
-       0xd19c, 0x0160, 0xa205, 0x0150, 0x7004, 0xa080, 0x0007, 0x2004,
-       0xa084, 0xfffd, 0xa086, 0x0008, 0x1904, 0x1aa6, 0x684c, 0xc0f5,
-       0x684e, 0x7814, 0xa005, 0x1180, 0x7003, 0x0000, 0x6808, 0x8001,
-       0x680a, 0x1130, 0x7004, 0x2060, 0x2009, 0x0048, 0x080c, 0x80a7,
-       0x080c, 0x195f, 0x0804, 0x1c5e, 0x7818, 0x6812, 0x781c, 0x6816,
-       0x7814, 0x7908, 0xa18c, 0x0fff, 0xa188, 0x0007, 0x8114, 0x8214,
-       0x8214, 0xa10a, 0x8104, 0x8004, 0x8004, 0xa20a, 0x810b, 0x810b,
-       0x810b, 0x080c, 0x1da5, 0x7803, 0x0004, 0x780f, 0xffff, 0x7803,
-       0x0001, 0x7804, 0xd0fc, 0x0de8, 0x7803, 0x0002, 0x7803, 0x0004,
-       0x780f, 0x00f6, 0x7004, 0x7007, 0x0000, 0x2060, 0x2009, 0x0048,
-       0x080c, 0x80a7, 0x080c, 0x1dd7, 0x0958, 0x7908, 0xd1ec, 0x1118,
-       0x2009, 0x0009, 0x0010, 0x2009, 0x0019, 0x7902, 0x7003, 0x0003,
-       0x0804, 0x1c5e, 0x8001, 0x7002, 0xd194, 0x01a8, 0x7804, 0xd0fc,
-       0x1904, 0x1c2c, 0xd09c, 0x0130, 0x7804, 0xd0fc, 0x1904, 0x1a74,
-       0xd09c, 0x11a8, 0x8aff, 0x0904, 0x1c5e, 0x2009, 0x0001, 0x080c,
-       0x19e0, 0x0804, 0x1c5e, 0xa184, 0x0888, 0x1148, 0x8aff, 0x0904,
-       0x1c5e, 0x2009, 0x0001, 0x080c, 0x19e0, 0x0804, 0x1c5e, 0x7818,
-       0x6812, 0x7a1c, 0x6a16, 0xa205, 0x0904, 0x1b3e, 0x7803, 0x0004,
-       0x7003, 0x0000, 0xd1bc, 0x1904, 0x1c0f, 0x6834, 0xa084, 0x00ff,
-       0xa086, 0x0029, 0x1118, 0xd19c, 0x1904, 0x1b3e, 0x0026, 0x0036,
-       0x7c20, 0x7d24, 0x7e30, 0x7f34, 0x7818, 0x6812, 0x781c, 0x6816,
-       0x2001, 0x0201, 0x2004, 0xa005, 0x0140, 0x7808, 0xd0ec, 0x1128,
-       0x7803, 0x0009, 0x7003, 0x0004, 0x0020, 0x0016, 0x080c, 0x1c62,
-       0x001e, 0x6b28, 0x6a2c, 0x080c, 0x215e, 0x00d6, 0x2805, 0xac68,
-       0x6034, 0xd09c, 0x1128, 0x6808, 0xa31a, 0x680c, 0xa213, 0x0020,
-       0x6810, 0xa31a, 0x6814, 0xa213, 0x00de, 0xd194, 0x0904, 0x1ac8,
-       0x2a00, 0x6826, 0x2c00, 0x681a, 0x2800, 0x6832, 0x6808, 0x8001,
-       0x680a, 0x6b2a, 0x6a2e, 0x003e, 0x002e, 0x0804, 0x1b50, 0x0056,
-       0x7d0c, 0x080c, 0xac73, 0x005e, 0x080c, 0x1d22, 0x00f6, 0x7004,
-       0x2078, 0x080c, 0x5029, 0x0118, 0x7820, 0xc0f5, 0x7822, 0x00fe,
-       0x682b, 0xffff, 0x682f, 0xffff, 0x6808, 0x8001, 0x680a, 0x697c,
-       0x791a, 0x6980, 0x791e, 0x0490, 0x7804, 0xd09c, 0x0904, 0x1a74,
-       0x7c20, 0x7824, 0xa405, 0x1904, 0x1a74, 0x7803, 0x0002, 0x0804,
-       0x1bb7, 0x7803, 0x0004, 0x7003, 0x0000, 0x7004, 0xa00d, 0x0150,
-       0x6808, 0x8001, 0x680a, 0x1130, 0x7004, 0x2060, 0x2009, 0x0048,
-       0x080c, 0x80a7, 0x080c, 0x195f, 0x0088, 0x7803, 0x0004, 0x7003,
-       0x0000, 0x7004, 0x2060, 0x6010, 0xa005, 0x0da0, 0x2068, 0x6808,
-       0x8000, 0x680a, 0x6c28, 0x6b2c, 0x080c, 0x197a, 0x001e, 0x000e,
-       0x012e, 0x0005, 0x700c, 0x7110, 0xa106, 0x0904, 0x1ce1, 0x7004,
-       0x0016, 0x210c, 0xa106, 0x001e, 0x0904, 0x1ce1, 0x00d6, 0x00c6,
-       0x216c, 0x2d00, 0xa005, 0x0904, 0x1cdf, 0x6820, 0xd0d4, 0x1904,
-       0x1cdf, 0x6810, 0x2068, 0x6850, 0xd0fc, 0x0558, 0x8108, 0x2104,
-       0x6b2c, 0xa306, 0x1904, 0x1cdf, 0x8108, 0x2104, 0x6a28, 0xa206,
-       0x1904, 0x1cdf, 0x6850, 0xc0fc, 0xc0f5, 0x6852, 0x686c, 0x7822,
-       0x6870, 0x7826, 0x681c, 0x7832, 0x6820, 0x7836, 0x6818, 0x2060,
-       0x6034, 0xd09c, 0x0150, 0x6830, 0x2005, 0x00d6, 0xac68, 0x6808,
-       0x783a, 0x680c, 0x783e, 0x00de, 0x04a0, 0xa006, 0x783a, 0x783e,
-       0x0480, 0x8108, 0x2104, 0xa005, 0x1590, 0x8108, 0x2104, 0xa005,
-       0x1570, 0x6850, 0xc0f5, 0x6852, 0x6830, 0x2005, 0x6918, 0xa160,
-       0xa180, 0x000d, 0x2004, 0xd09c, 0x1170, 0x6008, 0x7822, 0x686e,
-       0x600c, 0x7826, 0x6872, 0x6000, 0x7832, 0x6004, 0x7836, 0xa006,
-       0x783a, 0x783e, 0x0070, 0x6010, 0x7822, 0x686e, 0x6014, 0x7826,
-       0x6872, 0x6000, 0x7832, 0x6004, 0x7836, 0x6008, 0x783a, 0x600c,
-       0x783e, 0x6810, 0x781a, 0x6814, 0x781e, 0x7803, 0x0011, 0x00ce,
-       0x00de, 0x0005, 0x2011, 0x0201, 0x2009, 0x003c, 0x2204, 0xa005,
-       0x1118, 0x8109, 0x1dd8, 0x0005, 0x0005, 0x0ca1, 0x01e0, 0x7908,
-       0xd1ec, 0x1160, 0x080c, 0x1dd7, 0x0148, 0x7803, 0x0009, 0x7904,
-       0xd1fc, 0x0de8, 0x7803, 0x0006, 0x0c29, 0x0168, 0x780c, 0xd0a4,
-       0x1150, 0x7007, 0x0000, 0x080c, 0x1dd7, 0x0140, 0x7803, 0x0019,
-       0x7003, 0x0003, 0x0018, 0x00b1, 0xa085, 0x0001, 0x0005, 0x0126,
-       0x2091, 0x2200, 0x7000, 0xa086, 0x0003, 0x1150, 0x700c, 0x7110,
-       0xa106, 0x0130, 0x20e1, 0x9028, 0x700f, 0xb003, 0x7013, 0xb003,
-       0x012e, 0x0005, 0x00c6, 0x080c, 0x574f, 0x1550, 0x2001, 0x0160,
-       0x2003, 0x0000, 0x2001, 0x0138, 0x2003, 0x0000, 0x2011, 0x00c8,
-       0xe000, 0xe000, 0x8211, 0x1de0, 0x080c, 0x1d7e, 0x700c, 0x7110,
-       0xa106, 0x0190, 0x2104, 0xa005, 0x0130, 0x2060, 0x6010, 0x2060,
-       0x6008, 0x8001, 0x600a, 0xa188, 0x0003, 0xa182, 0xb01e, 0x0210,
-       0x2009, 0xb003, 0x7112, 0x0c50, 0x080c, 0x57d1, 0x00ce, 0x0005,
-       0x04a9, 0x20e1, 0x9028, 0x700c, 0x7110, 0xa106, 0x01d0, 0x2104,
-       0xa005, 0x0130, 0x2060, 0x6010, 0x2060, 0x6008, 0x8001, 0x600a,
-       0xa188, 0x0003, 0xa182, 0xb01e, 0x0210, 0x2009, 0xb003, 0x7112,
-       0x700c, 0xa106, 0x1d40, 0x080c, 0x2744, 0x2001, 0x0138, 0x2102,
-       0x0c10, 0x2001, 0x015d, 0x200c, 0x810a, 0x2102, 0x2001, 0x0160,
-       0x2502, 0x2001, 0x0138, 0x2202, 0x00ce, 0x0005, 0x20e1, 0x9028,
-       0x2001, 0x015d, 0x200c, 0x810a, 0x2102, 0x0005, 0x2001, 0x0138,
-       0x2014, 0x2003, 0x0000, 0x2001, 0x0160, 0x202c, 0x2003, 0x0000,
-       0x2021, 0xb015, 0x2001, 0x0141, 0x201c, 0xd3dc, 0x1168, 0x2001,
-       0x0109, 0x201c, 0xa39c, 0x0048, 0x1138, 0x2001, 0x0111, 0x201c,
-       0x83ff, 0x1110, 0x8421, 0x1d70, 0x0005, 0x00e6, 0x2071, 0x0200,
-       0x7808, 0xa084, 0xf000, 0xa10d, 0x08c9, 0x2019, 0x5000, 0x8319,
-       0x0168, 0x2001, 0xb01e, 0x2004, 0xa086, 0x0000, 0x0138, 0x2001,
-       0x0021, 0xd0fc, 0x0da0, 0x080c, 0x1ff4, 0x0c78, 0x20e1, 0x7000,
-       0x7324, 0x7420, 0x7028, 0x7028, 0x7426, 0x7037, 0x0001, 0x810f,
-       0x712e, 0x702f, 0x0100, 0x7037, 0x0008, 0x7326, 0x7422, 0x2001,
-       0x0160, 0x2502, 0x2001, 0x0138, 0x2202, 0x00ee, 0x0005, 0x7908,
-       0xa18c, 0x0fff, 0xa182, 0x0009, 0x0218, 0xa085, 0x0001, 0x0088,
-       0x2001, 0x020a, 0x81ff, 0x0130, 0x20e1, 0x6000, 0x200c, 0x200c,
-       0x200c, 0x200c, 0x20e1, 0x7000, 0x200c, 0x200c, 0x7003, 0x0000,
-       0xa006, 0x0005, 0x00f6, 0x00e6, 0x0016, 0x0026, 0x2071, 0xaffd,
-       0x2079, 0x0030, 0x2011, 0x0050, 0x7000, 0xa086, 0x0000, 0x01a8,
-       0x8211, 0x0188, 0x2001, 0x0005, 0x2004, 0xd08c, 0x0dc8, 0x7904,
-       0xa18c, 0x0780, 0x0016, 0x080c, 0x1a6c, 0x001e, 0x81ff, 0x1118,
-       0x2011, 0x0050, 0x0c48, 0xa085, 0x0001, 0x002e, 0x001e, 0x00ee,
-       0x00fe, 0x0005, 0x7803, 0x0004, 0x2009, 0x0064, 0x7804, 0xd0ac,
-       0x0904, 0x1e66, 0x8109, 0x1dd0, 0x2009, 0x0100, 0x210c, 0xa18a,
-       0x0003, 0x0a0c, 0x14f6, 0x080c, 0x20f2, 0x00e6, 0x00f6, 0x2071,
-       0xafec, 0x2079, 0x0010, 0x7004, 0xa086, 0x0000, 0x0538, 0x7800,
-       0x0006, 0x7820, 0x0006, 0x7830, 0x0006, 0x7834, 0x0006, 0x7838,
-       0x0006, 0x783c, 0x0006, 0x7803, 0x0004, 0xe000, 0xe000, 0x2079,
-       0x0030, 0x7804, 0xd0ac, 0x190c, 0x14f6, 0x2079, 0x0010, 0x000e,
-       0x783e, 0x000e, 0x783a, 0x000e, 0x7836, 0x000e, 0x7832, 0x000e,
-       0x7822, 0x000e, 0x7802, 0x00fe, 0x00ee, 0x0030, 0x00fe, 0x00ee,
-       0x7804, 0xd0ac, 0x190c, 0x14f6, 0x080c, 0x6d0d, 0x0005, 0x00e6,
-       0x2071, 0xb01e, 0x7003, 0x0000, 0x00ee, 0x0005, 0x00d6, 0xa280,
-       0x0004, 0x206c, 0x694c, 0xd1dc, 0x1904, 0x1ee4, 0x6934, 0xa184,
-       0x0007, 0x0002, 0x1e82, 0x1ecf, 0x1e82, 0x1e82, 0x1e82, 0x1eb6,
-       0x1e95, 0x1e84, 0x080c, 0x14f6, 0x684c, 0xd0b4, 0x0904, 0x1fcc,
-       0x6860, 0x682e, 0x6816, 0x685c, 0x682a, 0x6812, 0x687c, 0x680a,
-       0x6880, 0x680e, 0x6958, 0x0804, 0x1ed7, 0x6834, 0xa084, 0x00ff,
-       0xa086, 0x001e, 0x1d38, 0x684c, 0xd0b4, 0x0904, 0x1fcc, 0x6860,
-       0x682e, 0x6816, 0x685c, 0x682a, 0x6812, 0x687c, 0x680a, 0x6880,
-       0x680e, 0x6804, 0x681a, 0xa080, 0x000d, 0x2004, 0xa084, 0x000f,
-       0xa080, 0x2186, 0x2005, 0x6832, 0x6958, 0x0450, 0xa18c, 0x00ff,
-       0xa186, 0x0015, 0x1548, 0x684c, 0xd0b4, 0x0904, 0x1fcc, 0x6804,
-       0x681a, 0xa080, 0x000d, 0x2004, 0xa084, 0x000f, 0xa080, 0x2186,
-       0x2005, 0x6832, 0x6958, 0xa006, 0x682e, 0x682a, 0x0088, 0x684c,
-       0xd0b4, 0x0904, 0x1a47, 0x6958, 0xa006, 0x682e, 0x682a, 0x2d00,
-       0x681a, 0x6834, 0xa084, 0x000f, 0xa080, 0x2186, 0x2005, 0x6832,
-       0x6926, 0x684c, 0xc0dd, 0x684e, 0x00de, 0x0005, 0x00f6, 0x2079,
-       0x0020, 0x7804, 0xd0fc, 0x190c, 0x1ff4, 0x00e6, 0x00d6, 0x2071,
-       0xb01e, 0x7000, 0xa005, 0x1904, 0x1f4c, 0x00c6, 0x7206, 0xa280,
-       0x0004, 0x205c, 0x7004, 0x2068, 0x7803, 0x0004, 0x6818, 0x00d6,
-       0x2068, 0x686c, 0x7812, 0x6890, 0x00f6, 0x20e1, 0x9040, 0x2079,
-       0x0200, 0x781a, 0x2079, 0x0100, 0x8004, 0x78d6, 0x00fe, 0x00de,
-       0x2b68, 0x6824, 0x2050, 0x6818, 0x2060, 0x6830, 0x2040, 0x6034,
-       0xa0cc, 0x000f, 0x6908, 0x791a, 0x7116, 0x680c, 0x781e, 0x701a,
-       0xa006, 0x700e, 0x7012, 0x7004, 0x692c, 0x6814, 0xa106, 0x1120,
-       0x6928, 0x6810, 0xa106, 0x0158, 0x0036, 0x0046, 0x6b14, 0x6c10,
-       0x080c, 0x21a6, 0x004e, 0x003e, 0x0110, 0x00ce, 0x00a8, 0x8aff,
-       0x1120, 0x00ce, 0xa085, 0x0001, 0x0078, 0x0126, 0x2091, 0x8000,
-       0x2079, 0x0020, 0x2009, 0x0001, 0x0059, 0x0118, 0x2009, 0x0001,
-       0x0039, 0x012e, 0x00ce, 0xa006, 0x00de, 0x00ee, 0x00fe, 0x0005,
-       0x0076, 0x0066, 0x0056, 0x0046, 0x0036, 0x0026, 0x8aff, 0x0904,
-       0x1fc5, 0x700c, 0x7214, 0xa23a, 0x7010, 0x7218, 0xa203, 0x0a04,
-       0x1fc4, 0xa705, 0x0904, 0x1fc4, 0xa03e, 0x2730, 0x6850, 0xd0fc,
-       0x11a8, 0x00d6, 0x2805, 0xac68, 0x2900, 0x0002, 0x1fa7, 0x1f8c,
-       0x1f8c, 0x1fa7, 0x1fa7, 0x1fa0, 0x1fa7, 0x1f8c, 0x1fa7, 0x1f91,
-       0x1f91, 0x1fa7, 0x1fa7, 0x1fa7, 0x1f98, 0x1f91, 0xc0fc, 0x6852,
-       0x6b6c, 0x6a70, 0x6d1c, 0x6c20, 0xd99c, 0x0528, 0x00d6, 0x2805,
-       0xac68, 0x6f08, 0x6e0c, 0x00f0, 0x6b08, 0x6a0c, 0x6d00, 0x6c04,
-       0x00c8, 0x6b10, 0x6a14, 0x6d00, 0x6c04, 0x6f08, 0x6e0c, 0x0090,
-       0x00de, 0x00d6, 0x6834, 0xa084, 0x00ff, 0xa086, 0x001e, 0x1138,
-       0x00de, 0x080c, 0x2148, 0x1904, 0x1f56, 0xa00e, 0x00f0, 0x00de,
-       0x080c, 0x14f6, 0x00de, 0x7b22, 0x7a26, 0x7d32, 0x7c36, 0x7f3a,
-       0x7e3e, 0x7902, 0x7000, 0x8000, 0x7002, 0x6828, 0xa300, 0x682a,
-       0x682c, 0xa201, 0x682e, 0x700c, 0xa300, 0x700e, 0x7010, 0xa201,
-       0x7012, 0x080c, 0x2148, 0x0008, 0xa006, 0x002e, 0x003e, 0x004e,
-       0x005e, 0x006e, 0x007e, 0x0005, 0x080c, 0x14f6, 0x0026, 0x2001,
-       0x0105, 0x2003, 0x0010, 0x20e1, 0x9040, 0x7803, 0x0004, 0x7003,
-       0x0000, 0x7004, 0x2060, 0x00d6, 0x6010, 0x2068, 0x080c, 0x9596,
-       0x0118, 0x6850, 0xc0bd, 0x6852, 0x00de, 0x080c, 0x929c, 0x20e1,
-       0x9040, 0x080c, 0x7cb8, 0x2011, 0x0000, 0x080c, 0x7ae9, 0x080c,
-       0x6d0d, 0x002e, 0x0804, 0x20ad, 0x0126, 0x2091, 0x2400, 0x0006,
-       0x0016, 0x00f6, 0x00e6, 0x00d6, 0x00c6, 0x2079, 0x0020, 0x2071,
-       0xb01e, 0x2b68, 0x6818, 0x2060, 0x7904, 0x7803, 0x0002, 0xa184,
-       0x0700, 0x1920, 0x7000, 0x0002, 0x20ad, 0x2010, 0x2080, 0x20ab,
-       0x8001, 0x7002, 0xd19c, 0x1170, 0x8aff, 0x05d0, 0x2009, 0x0001,
-       0x080c, 0x1f50, 0x0904, 0x20ad, 0x2009, 0x0001, 0x080c, 0x1f50,
-       0x0804, 0x20ad, 0x7803, 0x0004, 0xd194, 0x0148, 0x6850, 0xc0fc,
-       0x6852, 0x8aff, 0x11d8, 0x684c, 0xc0f5, 0x684e, 0x00b8, 0x0026,
-       0x0036, 0x6b28, 0x6a2c, 0x7820, 0x686e, 0xa31a, 0x7824, 0x6872,
-       0xa213, 0x7830, 0x681e, 0x7834, 0x6822, 0x6b2a, 0x6a2e, 0x003e,
-       0x002e, 0x080c, 0x215e, 0x6850, 0xc0fd, 0x6852, 0x2a00, 0x6826,
-       0x2c00, 0x681a, 0x2800, 0x6832, 0x7003, 0x0000, 0x0804, 0x20ad,
-       0x00f6, 0x0026, 0x781c, 0x0006, 0x7818, 0x0006, 0x2079, 0x0100,
-       0x7a14, 0xa284, 0x0184, 0xa085, 0x0012, 0x7816, 0x0036, 0x2019,
-       0x1000, 0x8319, 0x090c, 0x14f6, 0x7820, 0xd0bc, 0x1dd0, 0x003e,
-       0x79c8, 0x000e, 0xa102, 0x001e, 0x0006, 0x0016, 0x79c4, 0x000e,
-       0xa103, 0x78c6, 0x000e, 0x78ca, 0xa284, 0x0184, 0xa085, 0x0012,
-       0x7816, 0x002e, 0x00fe, 0x7803, 0x0008, 0x7003, 0x0000, 0x0468,
-       0x8001, 0x7002, 0xd194, 0x0168, 0x7804, 0xd0fc, 0x1904, 0x2004,
-       0xd19c, 0x11f8, 0x8aff, 0x0508, 0x2009, 0x0001, 0x080c, 0x1f50,
-       0x00e0, 0x0026, 0x0036, 0x6b28, 0x6a2c, 0x080c, 0x215e, 0x00d6,
-       0x2805, 0xac68, 0x6034, 0xd09c, 0x1128, 0x6808, 0xa31a, 0x680c,
-       0xa213, 0x0020, 0x6810, 0xa31a, 0x6814, 0xa213, 0x00de, 0x0804,
-       0x2033, 0x0804, 0x202f, 0x080c, 0x14f6, 0x00ce, 0x00de, 0x00ee,
-       0x00fe, 0x001e, 0x000e, 0x012e, 0x0005, 0x00f6, 0x00e6, 0x2071,
-       0xb01e, 0x7000, 0xa086, 0x0000, 0x0590, 0x2079, 0x0020, 0x0016,
-       0x2009, 0x0207, 0x210c, 0xd194, 0x0158, 0x2009, 0x020c, 0x210c,
-       0xa184, 0x0003, 0x0128, 0x20e1, 0x9040, 0x2001, 0x020c, 0x2102,
-       0x2009, 0x0206, 0x2104, 0x2009, 0x0203, 0x210c, 0xa106, 0x1110,
-       0x20e1, 0x9040, 0x7804, 0xd0fc, 0x0d18, 0x080c, 0x1ff4, 0x7000,
-       0xa086, 0x0000, 0x19e8, 0x001e, 0x7803, 0x0004, 0x7804, 0xd0ac,
-       0x1de8, 0x20e1, 0x9040, 0x7803, 0x0002, 0x7003, 0x0000, 0x00ee,
-       0x00fe, 0x0005, 0x0026, 0x00c6, 0x00d6, 0x00e6, 0x00f6, 0x2071,
-       0xb01e, 0x2079, 0x0020, 0x7000, 0xa086, 0x0000, 0x0540, 0x7004,
-       0x2060, 0x6010, 0x2068, 0x080c, 0x9596, 0x0158, 0x6850, 0xc0b5,
-       0x6852, 0x680c, 0x7a1c, 0xa206, 0x1120, 0x6808, 0x7a18, 0xa206,
-       0x01e0, 0x2001, 0x0105, 0x2003, 0x0010, 0x20e1, 0x9040, 0x7803,
-       0x0004, 0x7003, 0x0000, 0x7004, 0x2060, 0x080c, 0x929c, 0x20e1,
-       0x9040, 0x080c, 0x7cb8, 0x2011, 0x0000, 0x080c, 0x7ae9, 0x00fe,
-       0x00ee, 0x00de, 0x00ce, 0x002e, 0x0005, 0x6810, 0x6a14, 0xa205,
-       0x1d00, 0x684c, 0xc0dc, 0x684e, 0x2c10, 0x080c, 0x1e6e, 0x2001,
-       0x0105, 0x2003, 0x0010, 0x20e1, 0x9040, 0x7803, 0x0004, 0x7003,
-       0x0000, 0x2069, 0xafc7, 0x6833, 0x0000, 0x683f, 0x0000, 0x08f8,
-       0x8840, 0x2805, 0xa005, 0x1170, 0x6004, 0xa005, 0x0168, 0x681a,
-       0x2060, 0x6034, 0xa084, 0x000f, 0xa080, 0x2186, 0x2045, 0x88ff,
-       0x090c, 0x14f6, 0x8a51, 0x0005, 0x2050, 0x0005, 0x8a50, 0x8841,
-       0x2805, 0xa005, 0x1190, 0x2c00, 0xad06, 0x0120, 0x6000, 0xa005,
-       0x1108, 0x2d00, 0x2060, 0x681a, 0x6034, 0xa084, 0x000f, 0xa080,
-       0x2196, 0x2045, 0x88ff, 0x090c, 0x14f6, 0x0005, 0x0000, 0x0011,
-       0x0015, 0x0019, 0x001d, 0x0021, 0x0025, 0x0029, 0x0000, 0x000f,
-       0x0015, 0x001b, 0x0021, 0x0027, 0x0000, 0x0000, 0x0000, 0x217b,
-       0x2177, 0x0000, 0x0000, 0x2185, 0x0000, 0x217b, 0x0000, 0x2182,
-       0x217f, 0x0000, 0x0000, 0x0000, 0x2185, 0x2182, 0x0000, 0x217d,
-       0x217d, 0x0000, 0x0000, 0x2185, 0x0000, 0x217d, 0x0000, 0x2183,
-       0x2183, 0x0000, 0x0000, 0x0000, 0x2185, 0x2183, 0x00a6, 0x0096,
-       0x0086, 0x6b2e, 0x6c2a, 0x6858, 0xa055, 0x0904, 0x2237, 0x2d60,
-       0x6034, 0xa0cc, 0x000f, 0xa9c0, 0x2186, 0xa986, 0x0007, 0x0130,
-       0xa986, 0x000e, 0x0118, 0xa986, 0x000f, 0x1120, 0x605c, 0xa422,
-       0x6060, 0xa31a, 0x2805, 0xa045, 0x1140, 0x0310, 0x0804, 0x2237,
-       0x6004, 0xa065, 0x0904, 0x2237, 0x0c18, 0x2805, 0xa005, 0x01a8,
-       0xac68, 0xd99c, 0x1128, 0x6808, 0xa422, 0x680c, 0xa31b, 0x0020,
-       0x6810, 0xa422, 0x6814, 0xa31b, 0x0620, 0x2300, 0xa405, 0x0150,
-       0x8a51, 0x0904, 0x2237, 0x8840, 0x0c40, 0x6004, 0xa065, 0x0904,
-       0x2237, 0x0830, 0x8a51, 0x0904, 0x2237, 0x8840, 0x2805, 0xa005,
-       0x1158, 0x6004, 0xa065, 0x0904, 0x2237, 0x6034, 0xa0cc, 0x000f,
-       0xa9c0, 0x2186, 0x2805, 0x2040, 0x2b68, 0x6850, 0xc0fc, 0x6852,
-       0x0458, 0x8422, 0x8420, 0x831a, 0xa399, 0x0000, 0x00d6, 0x2b68,
-       0x6c6e, 0x6b72, 0x00de, 0xd99c, 0x1168, 0x6908, 0x2400, 0xa122,
-       0x690c, 0x2300, 0xa11b, 0x0a0c, 0x14f6, 0x6800, 0xa420, 0x6804,
-       0xa319, 0x0060, 0x6910, 0x2400, 0xa122, 0x6914, 0x2300, 0xa11b,
-       0x0a0c, 0x14f6, 0x6800, 0xa420, 0x6804, 0xa319, 0x2b68, 0x6c1e,
-       0x6b22, 0x6850, 0xc0fd, 0x6852, 0x2c00, 0x681a, 0x2800, 0x6832,
-       0x2a00, 0x6826, 0x000e, 0x000e, 0x000e, 0xa006, 0x0028, 0x008e,
-       0x009e, 0x00ae, 0xa085, 0x0001, 0x0005, 0x2001, 0x0005, 0x2004,
-       0xa084, 0x0007, 0x0002, 0x224b, 0x224c, 0x224f, 0x2252, 0x2257,
-       0x225a, 0x225f, 0x2264, 0x0005, 0x080c, 0x1ff4, 0x0005, 0x080c,
-       0x1a6c, 0x0005, 0x080c, 0x1a6c, 0x080c, 0x1ff4, 0x0005, 0x080c,
-       0x16f8, 0x0005, 0x080c, 0x1ff4, 0x080c, 0x16f8, 0x0005, 0x080c,
-       0x1a6c, 0x080c, 0x16f8, 0x0005, 0x080c, 0x1a6c, 0x080c, 0x1ff4,
-       0x080c, 0x16f8, 0x0005, 0x0126, 0x2091, 0x2600, 0x2079, 0x0200,
-       0x2071, 0xb280, 0x2069, 0xad00, 0x2009, 0x0004, 0x7912, 0x7817,
-       0x0004, 0x080c, 0x2651, 0x781b, 0x0002, 0x20e1, 0x9080, 0x20e1,
-       0x4000, 0x20a9, 0x0080, 0x782f, 0x0000, 0x1f04, 0x2283, 0x20e1,
-       0x9080, 0x783b, 0x001f, 0x20e1, 0x8700, 0x012e, 0x0005, 0x0126,
-       0x2091, 0x2600, 0x781c, 0xd0a4, 0x190c, 0x2335, 0xa084, 0x0007,
-       0x0002, 0x22b3, 0x22a1, 0x22a4, 0x22a7, 0x22ac, 0x22ae, 0x22b0,
-       0x22b2, 0x080c, 0x5fb7, 0x0078, 0x080c, 0x5ff0, 0x0060, 0x080c,
-       0x5fb7, 0x080c, 0x5ff0, 0x0038, 0x0041, 0x0028, 0x0031, 0x0018,
-       0x0021, 0x0008, 0x0011, 0x012e, 0x0005, 0x0006, 0x0016, 0x0026,
-       0x7930, 0xa184, 0x0003, 0x0118, 0x20e1, 0x9040, 0x04a0, 0xa184,
-       0x0030, 0x01e0, 0x6a00, 0xa286, 0x0003, 0x1108, 0x00a0, 0x080c,
-       0x574f, 0x1178, 0x2001, 0xaf9e, 0x2003, 0x0001, 0x2001, 0xad00,
-       0x2003, 0x0001, 0xa085, 0x0001, 0x080c, 0x5793, 0x080c, 0x569a,
-       0x0010, 0x080c, 0x485e, 0x20e1, 0x9010, 0x00a8, 0xa184, 0x00c0,
-       0x0168, 0x00e6, 0x0036, 0x0046, 0x0056, 0x2071, 0xaffd, 0x080c,
-       0x1d22, 0x005e, 0x004e, 0x003e, 0x00ee, 0x0028, 0xa184, 0x0300,
-       0x0110, 0x20e1, 0x9020, 0x7932, 0x002e, 0x001e, 0x000e, 0x0005,
-       0x0016, 0x00e6, 0x00f6, 0x2071, 0xad00, 0x7128, 0x2001, 0xaf90,
-       0x2102, 0x2001, 0xaf98, 0x2102, 0xa182, 0x0211, 0x1218, 0x2009,
-       0x0008, 0x0400, 0xa182, 0x0259, 0x1218, 0x2009, 0x0007, 0x00d0,
-       0xa182, 0x02c1, 0x1218, 0x2009, 0x0006, 0x00a0, 0xa182, 0x0349,
-       0x1218, 0x2009, 0x0005, 0x0070, 0xa182, 0x0421, 0x1218, 0x2009,
-       0x0004, 0x0040, 0xa182, 0x0581, 0x1218, 0x2009, 0x0003, 0x0010,
-       0x2009, 0x0002, 0x2079, 0x0200, 0x7912, 0x7817, 0x0004, 0x080c,
-       0x2651, 0x00fe, 0x00ee, 0x001e, 0x0005, 0x7938, 0x080c, 0x14f6,
-       0x0126, 0x2091, 0x2800, 0x2061, 0x0100, 0x2071, 0xad00, 0x6024,
-       0x6026, 0x6053, 0x0030, 0x080c, 0x2690, 0x6050, 0xa084, 0xfe7f,
-       0x6052, 0x2009, 0x00ef, 0x6132, 0x6136, 0x080c, 0x26a0, 0x60e7,
-       0x0000, 0x61ea, 0x60e3, 0x0008, 0x604b, 0xf7f7, 0x6043, 0x0000,
-       0x602f, 0x0080, 0x602f, 0x0000, 0x6007, 0x0e9f, 0x601b, 0x001e,
-       0x600f, 0x00ff, 0x2001, 0xaf8c, 0x2003, 0x00ff, 0x602b, 0x002f,
-       0x012e, 0x0005, 0x2001, 0xad31, 0x2003, 0x0000, 0x2001, 0xad30,
-       0x2003, 0x0001, 0x0005, 0x0126, 0x2091, 0x2800, 0x0006, 0x0016,
-       0x0026, 0x6124, 0xa184, 0x1e2c, 0x1118, 0xa184, 0x0007, 0x002a,
-       0xa195, 0x0004, 0xa284, 0x0007, 0x0002, 0x23a7, 0x238d, 0x2390,
-       0x2393, 0x2398, 0x239a, 0x239e, 0x23a2, 0x080c, 0x6699, 0x00b8,
-       0x080c, 0x6774, 0x00a0, 0x080c, 0x6774, 0x080c, 0x6699, 0x0078,
-       0x0099, 0x0068, 0x080c, 0x6699, 0x0079, 0x0048, 0x080c, 0x6774,
-       0x0059, 0x0028, 0x080c, 0x6774, 0x080c, 0x6699, 0x0029, 0x002e,
-       0x001e, 0x000e, 0x012e, 0x0005, 0x6124, 0xd19c, 0x1904, 0x25bf,
-       0x080c, 0x574f, 0x0578, 0x7000, 0xa086, 0x0003, 0x0198, 0x6024,
-       0xa084, 0x1800, 0x0178, 0x080c, 0x5775, 0x0118, 0x080c, 0x5761,
-       0x1148, 0x6027, 0x0020, 0x6043, 0x0000, 0x2001, 0xaf9d, 0x2003,
-       0xaaaa, 0x0458, 0x080c, 0x5775, 0x15d0, 0x6024, 0xa084, 0x1800,
-       0x1108, 0x04a8, 0x2001, 0xaf9d, 0x2003, 0xaaaa, 0x2001, 0xaf9e,
-       0x2003, 0x0001, 0x2001, 0xad00, 0x2003, 0x0001, 0x080c, 0x569a,
-       0x0804, 0x25bf, 0xd1ac, 0x1518, 0x6024, 0xd0dc, 0x1170, 0xd0e4,
-       0x1188, 0xd0d4, 0x11a0, 0xd0cc, 0x0130, 0x7088, 0xa086, 0x0028,
-       0x1110, 0x080c, 0x58da, 0x0804, 0x25bf, 0x2001, 0xaf9e, 0x2003,
-       0x0000, 0x0048, 0x2001, 0xaf9e, 0x2003, 0x0002, 0x0020, 0x080c,
-       0x584d, 0x0804, 0x25bf, 0x080c, 0x597a, 0x0804, 0x25bf, 0xd1ac,
-       0x0904, 0x2507, 0x080c, 0x574f, 0x11d8, 0x6027, 0x0020, 0x0006,
-       0x0026, 0x0036, 0x080c, 0x576b, 0x1170, 0x2001, 0xaf9e, 0x2003,
-       0x0001, 0x2001, 0xad00, 0x2003, 0x0001, 0x080c, 0x569a, 0x003e,
-       0x002e, 0x000e, 0x0005, 0x003e, 0x002e, 0x000e, 0x080c, 0x5726,
-       0x0016, 0x0046, 0x00c6, 0x644c, 0xa486, 0xf0f0, 0x1138, 0x2061,
-       0x0100, 0x644a, 0x6043, 0x0090, 0x6043, 0x0010, 0x74ca, 0xa48c,
-       0xff00, 0x7034, 0xd084, 0x0178, 0xa186, 0xf800, 0x1160, 0x7038,
-       0xd084, 0x1148, 0xc085, 0x703a, 0x0036, 0x2418, 0x2011, 0x8016,
-       0x080c, 0x3c5c, 0x003e, 0xa196, 0xff00, 0x05b8, 0x7050, 0xa084,
-       0x00ff, 0x810f, 0xa116, 0x0588, 0x7130, 0xd184, 0x1570, 0x2011,
-       0xad52, 0x2214, 0xd2ec, 0x0138, 0xc18d, 0x7132, 0x2011, 0xad52,
-       0x2214, 0xd2ac, 0x1510, 0x6240, 0xa294, 0x0010, 0x0130, 0x6248,
-       0xa294, 0xff00, 0xa296, 0xff00, 0x01c0, 0x7030, 0xd08c, 0x0904,
-       0x24d2, 0x7034, 0xd08c, 0x1140, 0x2001, 0xad0c, 0x200c, 0xd1ac,
-       0x1904, 0x24d2, 0xc1ad, 0x2102, 0x0036, 0x73c8, 0x2011, 0x8013,
-       0x080c, 0x3c5c, 0x003e, 0x0804, 0x24d2, 0x7034, 0xd08c, 0x1140,
-       0x2001, 0xad0c, 0x200c, 0xd1ac, 0x1904, 0x24d2, 0xc1ad, 0x2102,
-       0x0036, 0x73c8, 0x2011, 0x8013, 0x080c, 0x3c5c, 0x003e, 0x7130,
-       0xc185, 0x7132, 0x2011, 0xad52, 0x220c, 0xd1a4, 0x01d0, 0x0016,
-       0x2009, 0x0001, 0x2011, 0x0100, 0x080c, 0x663f, 0x2019, 0x000e,
-       0x080c, 0xa8eb, 0xa484, 0x00ff, 0xa080, 0x2be6, 0x200d, 0xa18c,
-       0xff00, 0x810f, 0x8127, 0xa006, 0x2009, 0x000e, 0x080c, 0xa96c,
-       0x001e, 0xd1ac, 0x1148, 0x0016, 0x2009, 0x0000, 0x2019, 0x0004,
-       0x080c, 0x2aac, 0x001e, 0x0070, 0x0156, 0x20a9, 0x007f, 0x2009,
-       0x0000, 0x080c, 0x4cdc, 0x1110, 0x080c, 0x493a, 0x8108, 0x1f04,
-       0x24c9, 0x015e, 0x00ce, 0x004e, 0x2011, 0x0003, 0x080c, 0x7adf,
-       0x2011, 0x0002, 0x080c, 0x7ae9, 0x080c, 0x79e1, 0x080c, 0x6581,
-       0x0036, 0x2019, 0x0000, 0x080c, 0x7a64, 0x003e, 0x60e3, 0x0000,
-       0x001e, 0x2001, 0xad00, 0x2014, 0xa296, 0x0004, 0x1128, 0xd19c,
-       0x1118, 0x6228, 0xc29d, 0x622a, 0x2003, 0x0001, 0x2001, 0xad22,
-       0x2003, 0x0000, 0x6027, 0x0020, 0x080c, 0x5775, 0x1140, 0x0016,
-       0x2009, 0x07d0, 0x2011, 0x567b, 0x080c, 0x6593, 0x001e, 0xd194,
-       0x0904, 0x25bf, 0x0016, 0x6220, 0xd2b4, 0x0904, 0x2570, 0x080c,
-       0x6581, 0x080c, 0x7834, 0x6027, 0x0004, 0x00f6, 0x2019, 0xafd0,
-       0x2304, 0xa07d, 0x0570, 0x7804, 0xa086, 0x0032, 0x1550, 0x00d6,
-       0x00c6, 0x00e6, 0x2069, 0x0140, 0x618c, 0x6288, 0x7818, 0x608e,
-       0x7808, 0x608a, 0x6043, 0x0002, 0x2001, 0x0003, 0x8001, 0x1df0,
-       0x6043, 0x0000, 0x6803, 0x1000, 0x6803, 0x0000, 0x618e, 0x628a,
-       0x080c, 0x6b73, 0x080c, 0x6c50, 0x7810, 0x2070, 0x7037, 0x0103,
-       0x2f60, 0x080c, 0x8078, 0x00ee, 0x00ce, 0x00de, 0x00fe, 0x001e,
-       0x0005, 0x00fe, 0x00d6, 0x2069, 0x0140, 0x6804, 0xa084, 0x4000,
-       0x0120, 0x6803, 0x1000, 0x6803, 0x0000, 0x00de, 0x00c6, 0x2061,
-       0xafc7, 0x6028, 0xa09a, 0x00c8, 0x1238, 0x8000, 0x602a, 0x00ce,
-       0x080c, 0x7827, 0x0804, 0x25be, 0x2019, 0xafd0, 0x2304, 0xa065,
-       0x0120, 0x2009, 0x0027, 0x080c, 0x80a7, 0x00ce, 0x0804, 0x25be,
-       0xd2bc, 0x0904, 0x25be, 0x080c, 0x658e, 0x6014, 0xa084, 0x0184,
-       0xa085, 0x0010, 0x6016, 0x6027, 0x0004, 0x00d6, 0x2069, 0x0140,
-       0x6804, 0xa084, 0x4000, 0x0120, 0x6803, 0x1000, 0x6803, 0x0000,
-       0x00de, 0x00c6, 0x2061, 0xafc7, 0x6044, 0xa09a, 0x00c8, 0x12f0,
-       0x8000, 0x6046, 0x603c, 0x00ce, 0xa005, 0x0540, 0x2009, 0x07d0,
-       0x080c, 0x6586, 0xa080, 0x0007, 0x2004, 0xa086, 0x0006, 0x1138,
-       0x6114, 0xa18c, 0x0184, 0xa18d, 0x0012, 0x6116, 0x00b8, 0x6114,
-       0xa18c, 0x0184, 0xa18d, 0x0016, 0x6116, 0x0080, 0x0036, 0x2019,
-       0x0001, 0x080c, 0x7a64, 0x003e, 0x2019, 0xafd6, 0x2304, 0xa065,
-       0x0120, 0x2009, 0x004f, 0x080c, 0x80a7, 0x00ce, 0x001e, 0xd19c,
-       0x0904, 0x261a, 0x7034, 0xd0ac, 0x1560, 0x0016, 0x0156, 0x6027,
-       0x0008, 0x602f, 0x0020, 0x20a9, 0x0006, 0x1d04, 0x25cd, 0x2091,
-       0x6000, 0x1f04, 0x25cd, 0x602f, 0x0000, 0x6150, 0xa185, 0x1400,
-       0x6052, 0x20a9, 0x0366, 0x1d04, 0x25db, 0x2091, 0x6000, 0x6020,
-       0xd09c, 0x1130, 0x015e, 0x6152, 0x001e, 0x6027, 0x0008, 0x0490,
-       0x080c, 0x2760, 0x1f04, 0x25db, 0x015e, 0x6152, 0x001e, 0x6027,
-       0x0008, 0x0016, 0x6028, 0xc09c, 0x602a, 0x2011, 0x0003, 0x080c,
-       0x7adf, 0x2011, 0x0002, 0x080c, 0x7ae9, 0x080c, 0x79e1, 0x080c,
-       0x6581, 0x0036, 0x2019, 0x0000, 0x080c, 0x7a64, 0x003e, 0x60e3,
-       0x0000, 0x080c, 0xac8d, 0x080c, 0xaca8, 0xa085, 0x0001, 0x080c,
-       0x5793, 0x2001, 0xad00, 0x2003, 0x0004, 0x6027, 0x0008, 0x080c,
-       0x12cc, 0x001e, 0xa18c, 0xffd0, 0x6126, 0x0005, 0x0006, 0x0016,
-       0x0026, 0x00e6, 0x00f6, 0x0126, 0x2091, 0x8000, 0x2071, 0xad00,
-       0x71c0, 0x70c2, 0xa116, 0x01f0, 0x81ff, 0x0128, 0x2011, 0x8011,
-       0x080c, 0x3c5c, 0x00b8, 0x2011, 0x8012, 0x080c, 0x3c5c, 0x2001,
-       0xad71, 0x2004, 0xd0fc, 0x1170, 0x0036, 0x00c6, 0x080c, 0x26eb,
-       0x2061, 0x0100, 0x2019, 0x0028, 0x2009, 0x0000, 0x080c, 0x2aac,
-       0x00ce, 0x003e, 0x012e, 0x00fe, 0x00ee, 0x002e, 0x001e, 0x000e,
-       0x0005, 0x00c6, 0x00f6, 0x0006, 0x0026, 0x2061, 0x0100, 0xa190,
-       0x2664, 0x2205, 0x60f2, 0x2011, 0x2671, 0x2205, 0x60ee, 0x002e,
-       0x000e, 0x00fe, 0x00ce, 0x0005, 0x0840, 0x0840, 0x0840, 0x0580,
-       0x0420, 0x0348, 0x02c0, 0x0258, 0x0210, 0x01a8, 0x01a8, 0x01a8,
-       0x01a8, 0x0140, 0x00f8, 0x00d0, 0x00b0, 0x00a0, 0x2028, 0xa18c,
-       0x00ff, 0x2130, 0xa094, 0xff00, 0x1110, 0x81ff, 0x0118, 0x080c,
-       0x6278, 0x0038, 0xa080, 0x2be6, 0x200d, 0xa18c, 0xff00, 0x810f,
-       0xa006, 0x0005, 0xa080, 0x2be6, 0x200d, 0xa18c, 0x00ff, 0x0005,
-       0x00d6, 0x2069, 0x0140, 0x2001, 0xad14, 0x2003, 0x00ef, 0x20a9,
-       0x0010, 0xa006, 0x6852, 0x6856, 0x1f04, 0x269b, 0x00de, 0x0005,
-       0x0006, 0x00d6, 0x0026, 0x2069, 0x0140, 0x2001, 0xad14, 0x2102,
-       0x8114, 0x8214, 0x8214, 0x8214, 0x20a9, 0x0010, 0x6853, 0x0000,
-       0xa006, 0x82ff, 0x1128, 0xa184, 0x000f, 0xa080, 0xacae, 0x2005,
-       0x6856, 0x8211, 0x1f04, 0x26b0, 0x002e, 0x00de, 0x000e, 0x0005,
-       0x00c6, 0x2061, 0xad00, 0x6030, 0x0110, 0xc09d, 0x0008, 0xc09c,
-       0x6032, 0x00ce, 0x0005, 0x0156, 0x00d6, 0x0026, 0x0016, 0x0006,
-       0x2069, 0x0140, 0x6980, 0xa116, 0x0180, 0xa112, 0x1230, 0x8212,
-       0x8210, 0x22a8, 0x2001, 0x0402, 0x0018, 0x22a8, 0x2001, 0x0404,
-       0x680e, 0x1f04, 0x26e0, 0x680f, 0x0000, 0x000e, 0x001e, 0x002e,
-       0x00de, 0x015e, 0x0005, 0x2001, 0xad52, 0x2004, 0xd0c4, 0x0150,
-       0xd0a4, 0x0140, 0xa006, 0x0046, 0x2020, 0x2009, 0x002e, 0x080c,
-       0xa96c, 0x004e, 0x0005, 0x00f6, 0x0016, 0x0026, 0x2079, 0x0140,
-       0x78c4, 0xd0dc, 0x0548, 0xa084, 0x0700, 0xa08e, 0x0300, 0x1520,
-       0x2011, 0x0000, 0x2009, 0x0002, 0x2300, 0xa080, 0x0020, 0x2018,
-       0x2300, 0x080c, 0x6665, 0x2011, 0x0030, 0x2200, 0x8007, 0xa085,
-       0x004c, 0x78c2, 0x2009, 0x0204, 0x210c, 0x2200, 0xa100, 0x2009,
-       0x0138, 0x200a, 0x080c, 0x574f, 0x1118, 0x2009, 0xaf8e, 0x200a,
-       0x002e, 0x001e, 0x00fe, 0x0005, 0x78c3, 0x0000, 0x0cc8, 0x0126,
-       0x2091, 0x2800, 0x0006, 0x0016, 0x0026, 0x2001, 0x0170, 0x200c,
-       0x8000, 0x2014, 0xa184, 0x0003, 0x0110, 0x0804, 0x1a6a, 0x002e,
-       0x001e, 0x000e, 0x012e, 0x0005, 0x0006, 0x2001, 0x0100, 0x2004,
-       0xa082, 0x0005, 0x000e, 0x0268, 0x2001, 0x0170, 0x200c, 0xa18c,
-       0x00ff, 0xa18e, 0x004c, 0x1128, 0x200c, 0xa18c, 0xff00, 0x810f,
-       0x0010, 0x2009, 0x0000, 0x2001, 0x0204, 0x2004, 0xa108, 0x0005,
-       0x0006, 0x0156, 0x00f6, 0x2079, 0x0100, 0x20a9, 0x000a, 0x7854,
-       0xd08c, 0x1110, 0x1f04, 0x2767, 0x00fe, 0x015e, 0x000e, 0x0005,
-       0x0016, 0x00c6, 0x0006, 0x2061, 0x0100, 0x6030, 0x0006, 0x6048,
-       0x0006, 0x60e4, 0x0006, 0x60e8, 0x0006, 0x6050, 0x0006, 0x60f0,
-       0x0006, 0x60ec, 0x0006, 0x600c, 0x0006, 0x6004, 0x0006, 0x6028,
-       0x0006, 0x60e0, 0x0006, 0x602f, 0x0100, 0x602f, 0x0000, 0xe000,
-       0xe000, 0xe000, 0xe000, 0x602f, 0x0040, 0x602f, 0x0000, 0x000e,
-       0x60e2, 0x000e, 0x602a, 0x000e, 0x6006, 0x000e, 0x600e, 0x000e,
-       0x60ee, 0x000e, 0x60f2, 0x000e, 0x6052, 0x000e, 0x60ea, 0x000e,
-       0x60e6, 0x000e, 0x604a, 0x000e, 0x6032, 0x6036, 0x2008, 0x080c,
-       0x26a0, 0x000e, 0x00ce, 0x001e, 0x0005, 0x2845, 0x2849, 0x284d,
-       0x2853, 0x2859, 0x285f, 0x2865, 0x286d, 0x2875, 0x287b, 0x2881,
-       0x2889, 0x2891, 0x2899, 0x28a1, 0x28ab, 0x28b5, 0x28b5, 0x28b5,
-       0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5,
-       0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5,
-       0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5,
-       0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5,
-       0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5,
-       0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b7, 0x28b7, 0x28bc,
-       0x28bc, 0x28c3, 0x28c3, 0x28ca, 0x28ca, 0x28d3, 0x28d3, 0x28da,
-       0x28da, 0x28e3, 0x28e3, 0x28ec, 0x28ec, 0x28b5, 0x28b5, 0x28b5,
-       0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5,
-       0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5,
-       0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5,
-       0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5,
-       0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5,
-       0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5,
-       0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5,
-       0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x28b5, 0x0106, 0x0006, 0x0804,
-       0x28f7, 0x0106, 0x0006, 0x0804, 0x28f7, 0x0106, 0x0006, 0x080c,
-       0x2373, 0x0804, 0x28f7, 0x0106, 0x0006, 0x080c, 0x2373, 0x0804,
-       0x28f7, 0x0106, 0x0006, 0x080c, 0x223d, 0x0804, 0x28f7, 0x0106,
-       0x0006, 0x080c, 0x223d, 0x0804, 0x28f7, 0x0106, 0x0006, 0x080c,
-       0x2373, 0x080c, 0x223d, 0x0804, 0x28f7, 0x0106, 0x0006, 0x080c,
-       0x2373, 0x080c, 0x223d, 0x0804, 0x28f7, 0x0106, 0x0006, 0x080c,
-       0x228f, 0x0804, 0x28f7, 0x0106, 0x0006, 0x080c, 0x228f, 0x0804,
-       0x28f7, 0x0106, 0x0006, 0x080c, 0x2373, 0x080c, 0x228f, 0x0804,
-       0x28f7, 0x0106, 0x0006, 0x080c, 0x2373, 0x080c, 0x228f, 0x0804,
-       0x28f7, 0x0106, 0x0006, 0x080c, 0x223d, 0x080c, 0x228f, 0x0804,
-       0x28f7, 0x0106, 0x0006, 0x080c, 0x223d, 0x080c, 0x228f, 0x0804,
-       0x28f7, 0x0106, 0x0006, 0x080c, 0x2373, 0x080c, 0x223d, 0x080c,
-       0x228f, 0x0804, 0x28f7, 0x0106, 0x0006, 0x080c, 0x2373, 0x080c,
-       0x223d, 0x080c, 0x228f, 0x0804, 0x28f7, 0xe000, 0x0cf0, 0x0106,
-       0x0006, 0x080c, 0x272f, 0x04d8, 0x0106, 0x0006, 0x080c, 0x272f,
-       0x080c, 0x2373, 0x04a0, 0x0106, 0x0006, 0x080c, 0x272f, 0x080c,
-       0x223d, 0x0468, 0x0106, 0x0006, 0x080c, 0x272f, 0x080c, 0x2373,
-       0x080c, 0x223d, 0x0420, 0x0106, 0x0006, 0x080c, 0x272f, 0x080c,
-       0x228f, 0x00e8, 0x0106, 0x0006, 0x080c, 0x272f, 0x080c, 0x2373,
-       0x080c, 0x228f, 0x00a0, 0x0106, 0x0006, 0x080c, 0x272f, 0x080c,
-       0x223d, 0x080c, 0x228f, 0x0058, 0x0106, 0x0006, 0x080c, 0x272f,
-       0x080c, 0x2373, 0x080c, 0x223d, 0x080c, 0x228f, 0x0000, 0x000e,
-       0x010e, 0x000d, 0x00c6, 0x0026, 0x0046, 0x2021, 0x0000, 0x080c,
-       0x502d, 0x1904, 0x29d4, 0x72d0, 0x2001, 0xaf9d, 0x2004, 0xa005,
-       0x1110, 0xd29c, 0x0148, 0xd284, 0x1138, 0xd2bc, 0x1904, 0x29d4,
-       0x080c, 0x29d8, 0x0804, 0x29d4, 0x080c, 0x574f, 0x1120, 0x709b,
-       0xffff, 0x0804, 0x29d4, 0xd294, 0x0120, 0x709b, 0xffff, 0x0804,
-       0x29d4, 0x2001, 0xad14, 0x203c, 0x7284, 0xd284, 0x0904, 0x2976,
-       0xd28c, 0x1904, 0x2976, 0x0036, 0x7398, 0xa38e, 0xffff, 0x1110,
-       0x2019, 0x0001, 0x8314, 0xa2e0, 0xb3c0, 0x2c04, 0xa38c, 0x0001,
-       0x0120, 0xa084, 0xff00, 0x8007, 0x0010, 0xa084, 0x00ff, 0xa70e,
-       0x0560, 0xa08e, 0x0000, 0x0548, 0xa08e, 0x00ff, 0x1150, 0x7230,
-       0xd284, 0x1538, 0x7284, 0xc28d, 0x7286, 0x709b, 0xffff, 0x003e,
-       0x0428, 0x2009, 0x0000, 0x080c, 0x2676, 0x080c, 0x4c80, 0x11b8,
-       0x6004, 0xa084, 0x00ff, 0xa086, 0x0006, 0x1150, 0x7030, 0xd08c,
-       0x0118, 0x6000, 0xd0bc, 0x0120, 0x080c, 0x29eb, 0x0140, 0x0028,
-       0x080c, 0x2b1a, 0x080c, 0x2a19, 0x0110, 0x8318, 0x0818, 0x739a,
-       0x0010, 0x709b, 0xffff, 0x003e, 0x0804, 0x29d4, 0xa780, 0x2be6,
-       0x203d, 0xa7bc, 0xff00, 0x873f, 0x2041, 0x007e, 0x7098, 0xa096,
-       0xffff, 0x1120, 0x2009, 0x0000, 0x28a8, 0x0050, 0xa812, 0x0220,
-       0x2008, 0xa802, 0x20a8, 0x0020, 0x709b, 0xffff, 0x0804, 0x29d4,
-       0x2700, 0x0156, 0x0016, 0xa106, 0x05a0, 0xc484, 0x080c, 0x4cdc,
-       0x0120, 0x080c, 0x4c80, 0x15a8, 0x0008, 0xc485, 0x6004, 0xa084,
-       0x00ff, 0xa086, 0x0006, 0x1130, 0x7030, 0xd08c, 0x01e8, 0x6000,
-       0xd0bc, 0x11d0, 0x7284, 0xd28c, 0x0188, 0x6004, 0xa084, 0x00ff,
-       0xa082, 0x0006, 0x02b0, 0xd484, 0x1118, 0x080c, 0x4c9f, 0x0028,
-       0x080c, 0x2b9c, 0x0170, 0x080c, 0x2bc9, 0x0058, 0x080c, 0x2b1a,
-       0x080c, 0x2a19, 0x0170, 0x0028, 0x080c, 0x2b9c, 0x0110, 0x0419,
-       0x0140, 0x001e, 0x8108, 0x015e, 0x1f04, 0x2990, 0x709b, 0xffff,
-       0x0018, 0x001e, 0x015e, 0x719a, 0x004e, 0x002e, 0x00ce, 0x0005,
-       0x00c6, 0x0016, 0x709b, 0x0000, 0x2009, 0x007e, 0x080c, 0x4c80,
-       0x1138, 0x080c, 0x2b1a, 0x04a9, 0x0118, 0x70d0, 0xc0bd, 0x70d2,
-       0x001e, 0x00ce, 0x0005, 0x0016, 0x0076, 0x00d6, 0x00c6, 0x2c68,
-       0x2001, 0xad56, 0x2004, 0xa084, 0x00ff, 0x6842, 0x080c, 0x9807,
-       0x01d8, 0x2d00, 0x601a, 0x080c, 0x9956, 0x601f, 0x0001, 0x2001,
-       0x0000, 0x080c, 0x4c1e, 0x2001, 0x0000, 0x080c, 0x4c30, 0x0126,
-       0x2091, 0x8000, 0x7094, 0x8000, 0x7096, 0x012e, 0x2009, 0x0004,
-       0x080c, 0x80a7, 0xa085, 0x0001, 0x00ce, 0x00de, 0x007e, 0x001e,
-       0x0005, 0x0016, 0x0076, 0x00d6, 0x00c6, 0x2c68, 0x2001, 0xad56,
-       0x2004, 0xa084, 0x00ff, 0x6842, 0x080c, 0x9807, 0x0550, 0x2d00,
-       0x601a, 0x6800, 0xc0c4, 0x6802, 0x68a0, 0xa086, 0x007e, 0x0140,
-       0x6804, 0xa084, 0x00ff, 0xa086, 0x0006, 0x1110, 0x080c, 0x2ad9,
-       0x080c, 0x9956, 0x601f, 0x0001, 0x2001, 0x0000, 0x080c, 0x4c1e,
-       0x2001, 0x0002, 0x080c, 0x4c30, 0x0126, 0x2091, 0x8000, 0x7094,
-       0x8000, 0x7096, 0x012e, 0x2009, 0x0002, 0x080c, 0x80a7, 0xa085,
-       0x0001, 0x00ce, 0x00de, 0x007e, 0x001e, 0x0005, 0x00c6, 0x0026,
-       0x2009, 0x0080, 0x080c, 0x4c80, 0x1120, 0x0031, 0x0110, 0x70d7,
-       0xffff, 0x002e, 0x00ce, 0x0005, 0x0016, 0x0076, 0x00d6, 0x00c6,
-       0x2c68, 0x080c, 0x8022, 0x01d8, 0x2d00, 0x601a, 0x080c, 0x9956,
-       0x601f, 0x0001, 0x2001, 0x0000, 0x080c, 0x4c1e, 0x2001, 0x0002,
-       0x080c, 0x4c30, 0x0126, 0x2091, 0x8000, 0x70d8, 0x8000, 0x70da,
-       0x012e, 0x2009, 0x0002, 0x080c, 0x80a7, 0xa085, 0x0001, 0x00ce,
-       0x00de, 0x007e, 0x001e, 0x0005, 0x00c6, 0x00d6, 0x0126, 0x2091,
-       0x8000, 0x2009, 0x007f, 0x080c, 0x4c80, 0x1190, 0x2c68, 0x080c,
-       0x8022, 0x0170, 0x2d00, 0x601a, 0x6312, 0x601f, 0x0001, 0x620a,
-       0x080c, 0x9956, 0x2009, 0x0022, 0x080c, 0x80a7, 0xa085, 0x0001,
-       0x012e, 0x00de, 0x00ce, 0x0005, 0x00e6, 0x00c6, 0x0066, 0x0036,
-       0x0026, 0x080c, 0x68f3, 0x080c, 0x689d, 0x080c, 0x8a15, 0x2130,
-       0x81ff, 0x0128, 0x20a9, 0x007e, 0x2009, 0x0000, 0x0020, 0x20a9,
-       0x007f, 0x2009, 0x0000, 0x0016, 0x080c, 0x4cdc, 0x1120, 0x080c,
-       0x4ecf, 0x080c, 0x493a, 0x001e, 0x8108, 0x1f04, 0x2ac3, 0x86ff,
-       0x1110, 0x080c, 0x11d4, 0x002e, 0x003e, 0x006e, 0x00ce, 0x00ee,
-       0x0005, 0x00e6, 0x00c6, 0x0036, 0x0026, 0x0016, 0x6218, 0x2270,
-       0x72a0, 0x0026, 0x2019, 0x0029, 0x080c, 0x68e7, 0x0076, 0x2039,
-       0x0000, 0x080c, 0x681d, 0x2c08, 0x080c, 0xa712, 0x007e, 0x001e,
-       0x2e60, 0x080c, 0x4ecf, 0x6210, 0x6314, 0x080c, 0x493a, 0x6212,
-       0x6316, 0x001e, 0x002e, 0x003e, 0x00ce, 0x00ee, 0x0005, 0x00e6,
-       0x0006, 0x6018, 0xa080, 0x0028, 0x2004, 0xa086, 0x0080, 0x0150,
-       0x2071, 0xad00, 0x7094, 0xa005, 0x0110, 0x8001, 0x7096, 0x000e,
-       0x00ee, 0x0005, 0x2071, 0xad00, 0x70d8, 0xa005, 0x0dc0, 0x8001,
-       0x70da, 0x0ca8, 0x6000, 0xc08c, 0x6002, 0x0005, 0x00f6, 0x00e6,
-       0x00c6, 0x0036, 0x0026, 0x0016, 0x0156, 0x2178, 0x81ff, 0x1118,
-       0x20a9, 0x0001, 0x0098, 0x2001, 0xad52, 0x2004, 0xd0c4, 0x0150,
-       0xd0a4, 0x0140, 0xa006, 0x0046, 0x2020, 0x2009, 0x002d, 0x080c,
-       0xa96c, 0x004e, 0x20a9, 0x00ff, 0x2011, 0x0000, 0x0026, 0xa28e,
-       0x007e, 0x05c8, 0xa28e, 0x007f, 0x05b0, 0xa28e, 0x0080, 0x0598,
-       0xa288, 0xae34, 0x210c, 0x81ff, 0x0570, 0x8fff, 0x05c1, 0x00c6,
-       0x2160, 0x2001, 0x0001, 0x080c, 0x5037, 0x00ce, 0x2019, 0x0029,
-       0x080c, 0x68e7, 0x0076, 0x2039, 0x0000, 0x080c, 0x681d, 0x00c6,
-       0x0026, 0x2160, 0x6204, 0xa294, 0x00ff, 0xa286, 0x0006, 0x1118,
-       0x6007, 0x0404, 0x0028, 0x2001, 0x0004, 0x8007, 0xa215, 0x6206,
-       0x002e, 0x00ce, 0x0016, 0x2c08, 0x080c, 0xa712, 0x001e, 0x007e,
-       0x2160, 0x080c, 0x4ecf, 0x002e, 0x8210, 0x1f04, 0x2b3e, 0x015e,
-       0x001e, 0x002e, 0x003e, 0x00ce, 0x00ee, 0x00fe, 0x0005, 0x0046,
-       0x0026, 0x0016, 0x2001, 0xad52, 0x2004, 0xd0c4, 0x0148, 0xd0a4,
-       0x0138, 0xa006, 0x2220, 0x8427, 0x2009, 0x0029, 0x080c, 0xa96c,
-       0x001e, 0x002e, 0x004e, 0x0005, 0x0016, 0x0026, 0x0036, 0x00c6,
-       0x7284, 0x82ff, 0x01f8, 0x2011, 0xad52, 0x2214, 0xd2ac, 0x11d0,
-       0x2100, 0x080c, 0x268a, 0x81ff, 0x01b8, 0x2019, 0x0001, 0x8314,
-       0xa2e0, 0xb3c0, 0x2c04, 0xd384, 0x0120, 0xa084, 0xff00, 0x8007,
-       0x0010, 0xa084, 0x00ff, 0xa116, 0x0138, 0xa096, 0x00ff, 0x0110,
-       0x8318, 0x0c68, 0xa085, 0x0001, 0x00ce, 0x003e, 0x002e, 0x001e,
-       0x0005, 0x0016, 0x00c6, 0x0126, 0x2091, 0x8000, 0xa180, 0xae34,
-       0x2004, 0xa065, 0x0178, 0x0016, 0x00c6, 0x080c, 0x9807, 0x001e,
-       0x090c, 0x14f6, 0x611a, 0x080c, 0x2ad9, 0x080c, 0x8078, 0x001e,
-       0x080c, 0x4c9f, 0x012e, 0x00ce, 0x001e, 0x0005, 0x7eef, 0x7de8,
-       0x7ce4, 0x80e2, 0x7be1, 0x80e0, 0x80dc, 0x80da, 0x7ad9, 0x80d6,
-       0x80d5, 0x80d4, 0x80d3, 0x80d2, 0x80d1, 0x79ce, 0x78cd, 0x80cc,
-       0x80cb, 0x80ca, 0x80c9, 0x80c7, 0x80c6, 0x77c5, 0x76c3, 0x80bc,
-       0x80ba, 0x75b9, 0x80b6, 0x74b5, 0x73b4, 0x72b3, 0x80b2, 0x80b1,
-       0x80ae, 0x71ad, 0x80ac, 0x70ab, 0x6faa, 0x6ea9, 0x80a7, 0x6da6,
-       0x6ca5, 0x6ba3, 0x6a9f, 0x699e, 0x689d, 0x809b, 0x8098, 0x6797,
-       0x6690, 0x658f, 0x6488, 0x6384, 0x6282, 0x8081, 0x8080, 0x617c,
-       0x607a, 0x8079, 0x5f76, 0x8075, 0x8074, 0x8073, 0x8072, 0x8071,
-       0x806e, 0x5e6d, 0x806c, 0x5d6b, 0x5c6a, 0x5b69, 0x8067, 0x5a66,
-       0x5965, 0x5863, 0x575c, 0x565a, 0x5559, 0x8056, 0x8055, 0x5454,
-       0x5353, 0x5252, 0x5151, 0x504e, 0x4f4d, 0x804c, 0x804b, 0x4e4a,
-       0x4d49, 0x8047, 0x4c46, 0x8045, 0x8043, 0x803c, 0x803a, 0x8039,
-       0x8036, 0x4b35, 0x8034, 0x4a33, 0x4932, 0x4831, 0x802e, 0x472d,
-       0x462c, 0x452b, 0x442a, 0x4329, 0x4227, 0x8026, 0x8025, 0x4123,
-       0x401f, 0x3f1e, 0x3e1d, 0x3d1b, 0x3c18, 0x8017, 0x8010, 0x3b0f,
-       0x3a08, 0x8004, 0x3902, 0x8001, 0x8000, 0x8000, 0x3800, 0x3700,
-       0x3600, 0x8000, 0x3500, 0x8000, 0x8000, 0x8000, 0x3400, 0x8000,
-       0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x3300, 0x3200, 0x8000,
-       0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x3100, 0x3000, 0x8000,
-       0x8000, 0x2f00, 0x8000, 0x2e00, 0x2d00, 0x2c00, 0x8000, 0x8000,
-       0x8000, 0x2b00, 0x8000, 0x2a00, 0x2900, 0x2800, 0x8000, 0x2700,
-       0x2600, 0x2500, 0x2400, 0x2300, 0x2200, 0x8000, 0x8000, 0x2100,
-       0x2000, 0x1f00, 0x1e00, 0x1d00, 0x1c00, 0x8000, 0x8000, 0x1b00,
-       0x1a00, 0x8000, 0x1900, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000,
-       0x8000, 0x1800, 0x8000, 0x1700, 0x1600, 0x1500, 0x8000, 0x1400,
-       0x1300, 0x1200, 0x1100, 0x1000, 0x0f00, 0x8000, 0x8000, 0x0e00,
-       0x0d00, 0x0c00, 0x0b00, 0x0a00, 0x0900, 0x8000, 0x8000, 0x0800,
-       0x0700, 0x8000, 0x0600, 0x8000, 0x8000, 0x8000, 0x0500, 0x0400,
-       0x0300, 0x8000, 0x0200, 0x8000, 0x8000, 0x8000, 0x0100, 0x8000,
-       0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x0000, 0x8000, 0x8000,
-       0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000,
-       0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x2071, 0xad81,
-       0x7003, 0x0002, 0xa006, 0x7012, 0x7016, 0x703a, 0x703e, 0x7033,
-       0xad91, 0x7037, 0xad91, 0x7007, 0x0001, 0x2061, 0xadd1, 0x6003,
-       0x0002, 0x0005, 0x1004, 0x2d0c, 0x0e04, 0x2d0c, 0x2071, 0xad81,
-       0x2b78, 0x7818, 0xd084, 0x1140, 0x2a60, 0x7820, 0xa08e, 0x0069,
-       0x1904, 0x2df1, 0x0804, 0x2d8a, 0x0005, 0x2071, 0xad81, 0x7004,
-       0x0002, 0x2d15, 0x2d16, 0x2d1f, 0x2d30, 0x0005, 0x1004, 0x2d1e,
-       0x0e04, 0x2d1e, 0x2b78, 0x7818, 0xd084, 0x01e8, 0x0005, 0x2b78,
-       0x2061, 0xadd1, 0x6008, 0xa08e, 0x0100, 0x0128, 0xa086, 0x0200,
-       0x0904, 0x2deb, 0x0005, 0x7014, 0x2068, 0x2a60, 0x7018, 0x0807,
-       0x7010, 0x2068, 0x6834, 0xa086, 0x0103, 0x0108, 0x0005, 0x2a60,
-       0x2b78, 0x7018, 0x0807, 0x2a60, 0x7820, 0xa08a, 0x0040, 0x1210,
-       0x61c0, 0x0042, 0x2100, 0xa08a, 0x003f, 0x1a04, 0x2de8, 0x61c0,
-       0x0804, 0x2d8a, 0x2dcc, 0x2df7, 0x2dff, 0x2e03, 0x2e0b, 0x2e11,
-       0x2e15, 0x2e21, 0x2e24, 0x2e2e, 0x2e31, 0x2de8, 0x2de8, 0x2de8,
-       0x2e34, 0x2de8, 0x2e43, 0x2e5a, 0x2e71, 0x2ee8, 0x2eed, 0x2f16,
-       0x2f67, 0x2f78, 0x2f96, 0x2fcd, 0x2fd7, 0x2fe4, 0x2ff7, 0x3018,
-       0x3021, 0x3057, 0x305d, 0x2de8, 0x3086, 0x2de8, 0x2de8, 0x2de8,
-       0x2de8, 0x2de8, 0x308d, 0x3097, 0x2de8, 0x2de8, 0x2de8, 0x2de8,
-       0x2de8, 0x2de8, 0x2de8, 0x2de8, 0x309f, 0x2de8, 0x2de8, 0x2de8,
-       0x2de8, 0x2de8, 0x30b1, 0x30b9, 0x2de8, 0x2de8, 0x2de8, 0x2de8,
-       0x2de8, 0x2de8, 0x0002, 0x30cb, 0x311f, 0x317a, 0x318a, 0x2de8,
-       0x31a4, 0x35cb, 0x3fbb, 0x2de8, 0x2de8, 0x2de8, 0x2de8, 0x2de8,
-       0x2de8, 0x2de8, 0x2de8, 0x2e2e, 0x2e31, 0x35cd, 0x2de8, 0x35da,
-       0x403c, 0x4097, 0x40fb, 0x2de8, 0x415a, 0x4180, 0x419f, 0x2de8,
-       0x2de8, 0x2de8, 0x2de8, 0x35de, 0x376b, 0x3785, 0x37a3, 0x3804,
-       0x3858, 0x3863, 0x389a, 0x38a9, 0x38b8, 0x38bb, 0x38de, 0x3928,
-       0x398e, 0x399b, 0x3a9c, 0x3bb3, 0x3bdc, 0x3cda, 0x3cfc, 0x3d08,
-       0x3d41, 0x3e05, 0x2de8, 0x2de8, 0x2de8, 0x2de8, 0x3e6d, 0x3e88,
-       0x3efa, 0x3fac, 0x713c, 0x0000, 0x2021, 0x4000, 0x080c, 0x3c39,
-       0x0126, 0x2091, 0x8000, 0x0e04, 0x2dd8, 0x7818, 0xd084, 0x0110,
-       0x012e, 0x0cb0, 0x7c22, 0x7926, 0x7a2a, 0x7b2e, 0x781b, 0x0001,
-       0x2091, 0x4080, 0x7007, 0x0001, 0x2091, 0x5000, 0x012e, 0x0005,
-       0x2021, 0x4001, 0x0c18, 0x2021, 0x4002, 0x0c00, 0x2021, 0x4003,
-       0x08e8, 0x2021, 0x4005, 0x08d0, 0x2021, 0x4006, 0x08b8, 0xa02e,
-       0x2520, 0x7b28, 0x7a2c, 0x7824, 0x7930, 0x0804, 0x3c46, 0x7823,
-       0x0004, 0x7824, 0x0807, 0xa02e, 0x2520, 0x7b28, 0x7a2c, 0x7824,
-       0x7930, 0x0804, 0x3c49, 0x7924, 0x7828, 0x2114, 0x200a, 0x0804,
-       0x2dcc, 0x7924, 0x2114, 0x0804, 0x2dcc, 0x2099, 0x0009, 0x20a1,
-       0x0009, 0x20a9, 0x0007, 0x53a3, 0x7924, 0x7a28, 0x7b2c, 0x0804,
-       0x2dcc, 0x7824, 0x2060, 0x0090, 0x2009, 0x0002, 0x2011, 0x0001,
-       0x2019, 0x001b, 0x783b, 0x0017, 0x0804, 0x2dcc, 0x7d38, 0x7c3c,
-       0x0840, 0x7d38, 0x7c3c, 0x0888, 0x2061, 0x1000, 0xe10c, 0xa006,
-       0x2c15, 0xa200, 0x8c60, 0x8109, 0x1dd8, 0x2010, 0xa005, 0x0904,
-       0x2dcc, 0x0804, 0x2dee, 0x2069, 0xad51, 0x7824, 0x7930, 0xa11a,
-       0x1a04, 0x2df4, 0x8019, 0x0904, 0x2df4, 0x684a, 0x6942, 0x782c,
-       0x6852, 0x7828, 0x6856, 0xa006, 0x685a, 0x685e, 0x080c, 0x5a1c,
-       0x0804, 0x2dcc, 0x2069, 0xad51, 0x7824, 0x7934, 0xa11a, 0x1a04,
-       0x2df4, 0x8019, 0x0904, 0x2df4, 0x684e, 0x6946, 0x782c, 0x6862,
-       0x7828, 0x6866, 0xa006, 0x686a, 0x686e, 0x080c, 0x50d9, 0x0804,
-       0x2dcc, 0xa02e, 0x2520, 0x81ff, 0x1904, 0x2df1, 0x7924, 0x7b28,
-       0x7a2c, 0x20a9, 0x0005, 0x20a1, 0xad88, 0x41a1, 0x080c, 0x3c05,
-       0x0904, 0x2df1, 0x2009, 0x0020, 0x080c, 0x3c46, 0x701b, 0x2e89,
-       0x0005, 0x6834, 0x2008, 0xa084, 0x00ff, 0xa096, 0x0011, 0x0120,
-       0xa096, 0x0019, 0x1904, 0x2df1, 0x810f, 0xa18c, 0x00ff, 0x0904,
-       0x2df1, 0x710e, 0x700c, 0x8001, 0x0528, 0x700e, 0x080c, 0x3c05,
-       0x0904, 0x2df1, 0x2009, 0x0020, 0x2061, 0xadd1, 0x6224, 0x6328,
-       0x642c, 0x6530, 0xa290, 0x0040, 0xa399, 0x0000, 0xa4a1, 0x0000,
-       0xa5a9, 0x0000, 0x080c, 0x3c46, 0x701b, 0x2eb7, 0x0005, 0x6834,
-       0xa084, 0x00ff, 0xa096, 0x0002, 0x0120, 0xa096, 0x000a, 0x1904,
-       0x2df1, 0x08c0, 0x7010, 0x2068, 0x6838, 0xc0fd, 0x683a, 0x080c,
-       0x4b7c, 0x1128, 0x7007, 0x0003, 0x701b, 0x2ed1, 0x0005, 0x080c,
-       0x51df, 0x0126, 0x2091, 0x8000, 0x20a9, 0x0005, 0x2099, 0xad88,
-       0x530a, 0x2100, 0xa210, 0xa399, 0x0000, 0xa4a1, 0x0000, 0xa5a9,
-       0x0000, 0xad80, 0x000d, 0x2009, 0x0020, 0x012e, 0x0804, 0x3c49,
-       0x61a8, 0x7824, 0x60aa, 0x0804, 0x2dcc, 0x2091, 0x8000, 0x7823,
-       0x4000, 0x7827, 0x4953, 0x782b, 0x5020, 0x782f, 0x2020, 0x2009,
-       0x017f, 0x2104, 0x7832, 0x3f00, 0x7836, 0x2061, 0x0100, 0x6200,
-       0x2061, 0x0200, 0x603c, 0x8007, 0xa205, 0x783a, 0x2009, 0x04fd,
-       0x2104, 0x783e, 0x781b, 0x0001, 0x2091, 0x5000, 0x2091, 0x4080,
-       0x2071, 0x0010, 0x20c1, 0x00f0, 0x0804, 0x0427, 0x81ff, 0x1904,
-       0x2df1, 0x7924, 0x810f, 0xa18c, 0x00ff, 0x080c, 0x4cdc, 0x1904,
-       0x2df4, 0x7e38, 0xa684, 0x3fff, 0xa082, 0x4000, 0x0210, 0x0804,
-       0x2df4, 0x7c28, 0x7d2c, 0x080c, 0x4e96, 0xd28c, 0x1118, 0x080c,
-       0x4e41, 0x0010, 0x080c, 0x4e6f, 0x1518, 0x2061, 0xb400, 0x0126,
-       0x2091, 0x8000, 0x6000, 0xa086, 0x0000, 0x0148, 0x6010, 0xa06d,
-       0x0130, 0x683c, 0xa406, 0x1118, 0x6840, 0xa506, 0x0150, 0x012e,
-       0xace0, 0x0018, 0x2001, 0xad16, 0x2004, 0xac02, 0x1a04, 0x2df1,
-       0x0c30, 0x080c, 0x929c, 0x012e, 0x0904, 0x2df1, 0x0804, 0x2dcc,
-       0xa00e, 0x2001, 0x0005, 0x080c, 0x51df, 0x0126, 0x2091, 0x8000,
-       0x080c, 0x9803, 0x080c, 0x510c, 0x012e, 0x0804, 0x2dcc, 0x81ff,
-       0x1904, 0x2df1, 0x080c, 0x3c1a, 0x0904, 0x2df4, 0x080c, 0x4d96,
-       0x0904, 0x2df1, 0x080c, 0x4ea2, 0x0904, 0x2df1, 0x0804, 0x2dcc,
-       0x81ff, 0x1904, 0x2df1, 0x080c, 0x3c2a, 0x0904, 0x2df4, 0x080c,
-       0x4f0d, 0x0904, 0x2df1, 0x2019, 0x0005, 0x080c, 0x4ebd, 0x0904,
-       0x2df1, 0x7828, 0xa08a, 0x1000, 0x1a04, 0x2df4, 0x8003, 0x800b,
-       0x810b, 0xa108, 0x080c, 0x6519, 0x0804, 0x2dcc, 0x0126, 0x2091,
-       0x8000, 0x81ff, 0x0118, 0x2009, 0x0001, 0x0448, 0x2029, 0x00ff,
-       0x644c, 0x2400, 0xa506, 0x01f0, 0x2508, 0x080c, 0x4cdc, 0x11d0,
-       0x080c, 0x4f0d, 0x1128, 0x2009, 0x0002, 0x62b0, 0x2518, 0x00b8,
-       0x2019, 0x0004, 0x080c, 0x4ebd, 0x1118, 0x2009, 0x0006, 0x0078,
-       0x7824, 0xa08a, 0x1000, 0x1270, 0x8003, 0x800b, 0x810b, 0xa108,
-       0x080c, 0x6519, 0x8529, 0x1ae8, 0x012e, 0x0804, 0x2dcc, 0x012e,
-       0x0804, 0x2df1, 0x012e, 0x0804, 0x2df4, 0x080c, 0x3c1a, 0x0904,
-       0x2df4, 0x080c, 0x4dfc, 0x080c, 0x4e96, 0x0804, 0x2dcc, 0x81ff,
-       0x1904, 0x2df1, 0x080c, 0x3c1a, 0x0904, 0x2df4, 0x080c, 0x4ded,
-       0x080c, 0x4e96, 0x0804, 0x2dcc, 0x81ff, 0x1904, 0x2df1, 0x080c,
-       0x3c1a, 0x0904, 0x2df4, 0x080c, 0x4e71, 0x0904, 0x2df1, 0x080c,
-       0x4bc0, 0x080c, 0x4e3a, 0x080c, 0x4e96, 0x0804, 0x2dcc, 0x080c,
-       0x3c1a, 0x0904, 0x2df4, 0x080c, 0x4d96, 0x0904, 0x2df1, 0x62a0,
-       0x2019, 0x0005, 0x00c6, 0x080c, 0x4ecf, 0x2061, 0x0000, 0x080c,
-       0x68e7, 0x0076, 0x2039, 0x0000, 0x080c, 0x681d, 0x2009, 0x0000,
-       0x080c, 0xa712, 0x007e, 0x00ce, 0x080c, 0x4e96, 0x0804, 0x2dcc,
-       0x080c, 0x3c1a, 0x0904, 0x2df4, 0x080c, 0x4e96, 0x2208, 0x0804,
-       0x2dcc, 0x0156, 0x00d6, 0x00e6, 0x2069, 0xae13, 0x6810, 0x6914,
-       0xa10a, 0x1210, 0x2009, 0x0000, 0x6816, 0x2011, 0x0000, 0x2019,
-       0x0000, 0x20a9, 0x007e, 0x2069, 0xae34, 0x2d04, 0xa075, 0x0130,
-       0x704c, 0x0071, 0xa210, 0x7080, 0x0059, 0xa318, 0x8d68, 0x1f04,
-       0x3035, 0x2300, 0xa218, 0x00ee, 0x00de, 0x015e, 0x0804, 0x2dcc,
-       0x00f6, 0x0016, 0xa07d, 0x0140, 0x2001, 0x0000, 0x8000, 0x2f0c,
-       0x81ff, 0x0110, 0x2178, 0x0cd0, 0x001e, 0x00fe, 0x0005, 0x2069,
-       0xae13, 0x6910, 0x62ac, 0x0804, 0x2dcc, 0x81ff, 0x1904, 0x2df1,
-       0x614c, 0xa190, 0x2be6, 0x2215, 0xa294, 0x00ff, 0x636c, 0x83ff,
-       0x0108, 0x6270, 0x67d0, 0xd79c, 0x0118, 0x2031, 0x0001, 0x0090,
-       0xd7ac, 0x0118, 0x2031, 0x0003, 0x0068, 0xd7a4, 0x0118, 0x2031,
-       0x0002, 0x0040, 0x080c, 0x574f, 0x1118, 0x2031, 0x0004, 0x0010,
-       0x2031, 0x0000, 0x7e3a, 0x7f3e, 0x0804, 0x2dcc, 0x613c, 0x6240,
-       0x2019, 0xafa3, 0x231c, 0x0804, 0x2dcc, 0x0126, 0x2091, 0x8000,
-       0x6134, 0xa006, 0x2010, 0x2018, 0x012e, 0x0804, 0x2dcc, 0x080c,
-       0x3c2a, 0x0904, 0x2df4, 0x6244, 0x6338, 0x0804, 0x2dcc, 0x613c,
-       0x6240, 0x7824, 0x603e, 0x7b28, 0x6342, 0x2069, 0xad51, 0x831f,
-       0xa305, 0x6816, 0x782c, 0x2069, 0xafa3, 0x2d1c, 0x206a, 0x0804,
-       0x2dcc, 0x0126, 0x2091, 0x8000, 0x7824, 0x6036, 0x012e, 0x0804,
-       0x2dcc, 0x080c, 0x3c2a, 0x0904, 0x2df4, 0x7828, 0xa00d, 0x0904,
-       0x2df4, 0x782c, 0xa005, 0x0904, 0x2df4, 0x6244, 0x6146, 0x6338,
-       0x603a, 0x0804, 0x2dcc, 0x2001, 0xad00, 0x2004, 0xa086, 0x0003,
-       0x1904, 0x2df1, 0x00c6, 0x2061, 0x0100, 0x7924, 0x810f, 0xa18c,
-       0x00ff, 0xa196, 0x00ff, 0x1130, 0x2001, 0xad14, 0x2004, 0xa085,
-       0xff00, 0x0078, 0xa182, 0x007f, 0x16a0, 0xa188, 0x2be6, 0x210d,
-       0xa18c, 0x00ff, 0x2001, 0xad14, 0x2004, 0xa116, 0x0550, 0x810f,
-       0xa105, 0x0126, 0x2091, 0x8000, 0x0006, 0x080c, 0x8022, 0x000e,
-       0x01e0, 0x601a, 0x600b, 0xbc09, 0x601f, 0x0001, 0x080c, 0x3c05,
-       0x01d8, 0x6837, 0x0000, 0x7007, 0x0003, 0x6833, 0x0000, 0x6838,
-       0xc0fd, 0x683a, 0x701b, 0x3173, 0x2d00, 0x6012, 0x2009, 0x0032,
-       0x080c, 0x80a7, 0x012e, 0x00ce, 0x0005, 0x012e, 0x00ce, 0x0804,
-       0x2df1, 0x00ce, 0x0804, 0x2df4, 0x080c, 0x8078, 0x0cb0, 0x2001,
-       0xad00, 0x2004, 0xa086, 0x0003, 0x1904, 0x2df1, 0x00c6, 0x2061,
-       0x0100, 0x7924, 0x810f, 0xa18c, 0x00ff, 0xa196, 0x00ff, 0x1130,
-       0x2001, 0xad14, 0x2004, 0xa085, 0xff00, 0x0078, 0xa182, 0x007f,
-       0x16a0, 0xa188, 0x2be6, 0x210d, 0xa18c, 0x00ff, 0x2001, 0xad14,
-       0x2004, 0xa116, 0x0550, 0x810f, 0xa105, 0x0126, 0x2091, 0x8000,
-       0x0006, 0x080c, 0x8022, 0x000e, 0x01e0, 0x601a, 0x600b, 0xbc05,
-       0x601f, 0x0001, 0x080c, 0x3c05, 0x01d8, 0x6837, 0x0000, 0x7007,
-       0x0003, 0x6833, 0x0000, 0x6838, 0xc0fd, 0x683a, 0x701b, 0x3173,
-       0x2d00, 0x6012, 0x2009, 0x0032, 0x080c, 0x80a7, 0x012e, 0x00ce,
-       0x0005, 0x012e, 0x00ce, 0x0804, 0x2df1, 0x00ce, 0x0804, 0x2df4,
-       0x080c, 0x8078, 0x0cb0, 0x6830, 0xa086, 0x0100, 0x0904, 0x2df1,
-       0x0804, 0x2dcc, 0x2061, 0xb048, 0x0126, 0x2091, 0x8000, 0x6000,
-       0xd084, 0x0128, 0x6104, 0x6208, 0x012e, 0x0804, 0x2dcc, 0x012e,
-       0x0804, 0x2df4, 0x81ff, 0x1904, 0x2df1, 0x080c, 0x574f, 0x0904,
-       0x2df1, 0x0126, 0x2091, 0x8000, 0x6244, 0x6064, 0xa202, 0x0248,
-       0xa085, 0x0001, 0x080c, 0x26c0, 0x080c, 0x436e, 0x012e, 0x0804,
-       0x2dcc, 0x012e, 0x0804, 0x2df4, 0x0126, 0x2091, 0x8000, 0x7824,
-       0xa084, 0x0007, 0x0002, 0x31b6, 0x31bf, 0x31c6, 0x31b3, 0x31b3,
-       0x31b3, 0x31b3, 0x31b3, 0x012e, 0x0804, 0x2df4, 0x2009, 0x0114,
-       0x2104, 0xa085, 0x0800, 0x200a, 0x080c, 0x332f, 0x0070, 0x2009,
-       0x010b, 0x200b, 0x0010, 0x080c, 0x332f, 0x0038, 0x81ff, 0x0128,
-       0x012e, 0x2021, 0x400b, 0x0804, 0x2dce, 0x0086, 0x0096, 0x00a6,
-       0x00b6, 0x00c6, 0x00d6, 0x00e6, 0x00f6, 0x2009, 0x0101, 0x210c,
-       0x0016, 0x2001, 0x0138, 0x200c, 0x2003, 0x0001, 0x0016, 0x2001,
-       0x007a, 0x2034, 0x2001, 0x007b, 0x202c, 0xa006, 0x2048, 0x2050,
-       0x2058, 0x080c, 0x3570, 0x080c, 0x34da, 0xa03e, 0x2720, 0x00f6,
-       0x00e6, 0x00c6, 0x2d60, 0x2071, 0xb01e, 0x2079, 0x0020, 0x00d6,
-       0x2069, 0x0000, 0x6824, 0xd0b4, 0x0140, 0x2001, 0x007d, 0x2004,
-       0x783e, 0x2001, 0x007c, 0x2004, 0x783a, 0x00de, 0x2011, 0x0001,
-       0x080c, 0x3486, 0x080c, 0x3486, 0x00ce, 0x00ee, 0x00fe, 0x080c,
-       0x33d5, 0x080c, 0x34ae, 0x080c, 0x342b, 0x080c, 0x3394, 0x080c,
-       0x33c5, 0x00f6, 0x2079, 0x0100, 0x7824, 0xd094, 0x0530, 0x7814,
-       0xa084, 0x0184, 0xa085, 0x0010, 0x7816, 0x2079, 0x0140, 0x080c,
-       0x330d, 0x1110, 0x00fe, 0x0430, 0x7804, 0xd0dc, 0x0dc0, 0x2079,
-       0x0100, 0x7827, 0x0086, 0x7814, 0xa084, 0x0184, 0xa085, 0x0032,
-       0x7816, 0x080c, 0x330d, 0x1110, 0x00fe, 0x00a0, 0x7824, 0xd0bc,
-       0x0dc0, 0x7827, 0x0080, 0xa026, 0x7c16, 0x7824, 0xd0ac, 0x0130,
-       0x8b58, 0x080c, 0x3317, 0x00fe, 0x0804, 0x32d7, 0x00fe, 0x080c,
-       0x330d, 0x1150, 0x8948, 0x2001, 0x007a, 0x2602, 0x2001, 0x007b,
-       0x2502, 0x080c, 0x3317, 0x0088, 0x87ff, 0x0140, 0x2001, 0x0201,
-       0x2004, 0xa005, 0x1904, 0x3211, 0x8739, 0x0038, 0x2001, 0xaffd,
-       0x2004, 0xa086, 0x0000, 0x1904, 0x3211, 0x2001, 0x0033, 0x2003,
-       0x00f6, 0x8631, 0x1208, 0x8529, 0x2500, 0xa605, 0x0904, 0x32d7,
-       0x7824, 0xd0bc, 0x0128, 0x2900, 0xaa05, 0xab05, 0x1904, 0x32d7,
-       0x6033, 0x000d, 0x2001, 0x0030, 0x2003, 0x0004, 0x7824, 0xd0ac,
-       0x1148, 0x2001, 0xaffd, 0x2003, 0x0003, 0x2001, 0x0030, 0x2003,
-       0x0009, 0x0040, 0x6027, 0x0001, 0x2001, 0x0075, 0x2004, 0xa005,
-       0x0108, 0x6026, 0x2c00, 0x601a, 0x20e1, 0x9040, 0x2d00, 0x681a,
-       0x6833, 0x000d, 0x7824, 0xd0a4, 0x1180, 0x6827, 0x0000, 0x00c6,
-       0x20a9, 0x0004, 0x2061, 0x0020, 0x6003, 0x0008, 0x2001, 0x0203,
-       0x2004, 0x1f04, 0x32ac, 0x00ce, 0x0040, 0x6827, 0x0001, 0x2001,
-       0x0074, 0x2004, 0xa005, 0x0108, 0x6826, 0x00f6, 0x00c6, 0x2079,
-       0x0100, 0x2061, 0x0020, 0x7827, 0x0002, 0x2001, 0x0072, 0x2004,
-       0xa084, 0xfff8, 0x601a, 0x0006, 0x2001, 0x0073, 0x2004, 0x601e,
-       0x78c6, 0x000e, 0x78ca, 0x00ce, 0x00fe, 0x0804, 0x31ef, 0x2061,
-       0x0100, 0x6027, 0x0002, 0x001e, 0x61e2, 0x001e, 0x6106, 0x7824,
-       0xa084, 0x0003, 0xa086, 0x0002, 0x0188, 0x20e1, 0x9028, 0x6050,
-       0xa084, 0xf7ef, 0x6052, 0x602f, 0x0000, 0x602c, 0xc0ac, 0x602e,
-       0x604b, 0xf7f7, 0x6043, 0x0090, 0x6043, 0x0010, 0x2908, 0x2a10,
-       0x2b18, 0x2b00, 0xaa05, 0xa905, 0x00fe, 0x00ee, 0x00de, 0x00ce,
-       0x00be, 0x00ae, 0x009e, 0x008e, 0x1118, 0x012e, 0x0804, 0x2dcc,
-       0x012e, 0x2021, 0x400c, 0x0804, 0x2dce, 0xa085, 0x0001, 0x1d04,
-       0x3316, 0x2091, 0x6000, 0x8420, 0xa486, 0x0064, 0x0005, 0x2001,
-       0x0105, 0x2003, 0x0010, 0x2001, 0x0030, 0x2003, 0x0004, 0x2001,
-       0x0020, 0x2003, 0x0004, 0x2001, 0xaffd, 0x2003, 0x0000, 0x2001,
-       0xb01e, 0x2003, 0x0000, 0x20e1, 0xf000, 0xa026, 0x0005, 0x00f6,
-       0x2079, 0x0100, 0x2001, 0xad14, 0x200c, 0x7932, 0x7936, 0x080c,
-       0x26a0, 0x7850, 0xa084, 0x0980, 0xa085, 0x0030, 0x7852, 0x2019,
-       0x01f4, 0x8319, 0x1df0, 0xa084, 0x0980, 0x7852, 0x782c, 0xc0ad,
-       0x782e, 0x20a9, 0x0046, 0x1d04, 0x334b, 0x2091, 0x6000, 0x1f04,
-       0x334b, 0x7850, 0xa085, 0x0400, 0x7852, 0x2001, 0x0009, 0x2004,
-       0xa084, 0x0003, 0xa086, 0x0001, 0x1118, 0x782c, 0xc0ac, 0x782e,
-       0x784b, 0xf7f7, 0x7843, 0x0090, 0x7843, 0x0010, 0x20a9, 0x000e,
-       0xe000, 0x1f04, 0x3368, 0x7850, 0xa085, 0x1400, 0x7852, 0x2019,
-       0x61a8, 0x7854, 0xe000, 0xe000, 0xd08c, 0x1110, 0x8319, 0x1dc8,
-       0x7827, 0x0048, 0x7850, 0xa085, 0x0400, 0x7852, 0x7843, 0x0040,
-       0x2019, 0x01f4, 0xe000, 0xe000, 0x8319, 0x1de0, 0x2001, 0x0140,
-       0x2003, 0x0100, 0x7827, 0x0020, 0x7843, 0x0000, 0x2003, 0x0000,
-       0x7827, 0x0048, 0x00fe, 0x0005, 0x7824, 0xd0ac, 0x11c8, 0x00f6,
-       0x00e6, 0x2071, 0xaffd, 0x2079, 0x0030, 0x2001, 0x0201, 0x2004,
-       0xa005, 0x0160, 0x7000, 0xa086, 0x0000, 0x1140, 0x0051, 0xd0bc,
-       0x0108, 0x8738, 0x7003, 0x0003, 0x7803, 0x0019, 0x00ee, 0x00fe,
-       0x0005, 0x780c, 0xa08c, 0x0070, 0x0178, 0x2009, 0x007a, 0x260a,
-       0x2009, 0x007b, 0x250a, 0xd0b4, 0x0108, 0x8a50, 0xd0ac, 0x0108,
-       0x8948, 0xd0a4, 0x0108, 0x8b58, 0x0005, 0x00f6, 0x2079, 0x0200,
-       0x781c, 0xd084, 0x0140, 0x20e1, 0x0007, 0x20e1, 0x2000, 0x2001,
-       0x020a, 0x2004, 0x0ca8, 0x00fe, 0x0005, 0x00e6, 0x2071, 0x0100,
-       0x2009, 0xad14, 0x210c, 0x716e, 0x7063, 0x0100, 0x7166, 0x719e,
-       0x706b, 0x0000, 0x7073, 0x0809, 0x7077, 0x0008, 0x7078, 0xa080,
-       0x0100, 0x707a, 0x7080, 0x8000, 0x7082, 0x7087, 0xaaaa, 0xa006,
-       0x708a, 0x708e, 0x707e, 0x70d6, 0x70ab, 0x0036, 0x70af, 0x95d5,
-       0x7027, 0x0080, 0x7014, 0xa084, 0x0184, 0xa085, 0x0032, 0x7016,
-       0x080c, 0x34ae, 0x080c, 0x330d, 0x1110, 0x8421, 0x0028, 0x7024,
-       0xd0bc, 0x0db0, 0x7027, 0x0080, 0x00f6, 0x00e6, 0x2071, 0xaffd,
-       0x2079, 0x0030, 0x00d6, 0x2069, 0x0000, 0x6824, 0xd0b4, 0x0120,
-       0x683c, 0x783e, 0x6838, 0x783a, 0x00de, 0x2011, 0x0011, 0x080c,
-       0x3486, 0x2011, 0x0001, 0x080c, 0x3486, 0x00ee, 0x00fe, 0x7017,
-       0x0000, 0x00ee, 0x0005, 0x00f6, 0x00e6, 0x2071, 0xaffd, 0x2079,
-       0x0030, 0x7904, 0xd1fc, 0x0904, 0x3483, 0x7803, 0x0002, 0xa026,
-       0xd19c, 0x1904, 0x347f, 0x7000, 0x0002, 0x3483, 0x3441, 0x3465,
-       0x347f, 0xd1bc, 0x1150, 0xd1dc, 0x1150, 0x8001, 0x7002, 0x2011,
-       0x0001, 0x04e1, 0x05c0, 0x04d1, 0x04b0, 0x780f, 0x0000, 0x7820,
-       0x7924, 0x7803, 0x0004, 0x7822, 0x7926, 0x2001, 0x0201, 0x200c,
-       0x81ff, 0x0de8, 0x080c, 0x33b1, 0x2009, 0x0001, 0x7808, 0xd0ec,
-       0x0110, 0x2009, 0x0011, 0x7902, 0x00f0, 0x8001, 0x7002, 0xa184,
-       0x0880, 0x1138, 0x7804, 0xd0fc, 0x1940, 0x2011, 0x0001, 0x00b1,
-       0x0090, 0x6030, 0xa092, 0x0004, 0xa086, 0x0009, 0x1120, 0x6000,
-       0x601a, 0x2011, 0x0025, 0x6232, 0xd1dc, 0x1988, 0x0870, 0x7803,
-       0x0004, 0x7003, 0x0000, 0x00ee, 0x00fe, 0x0005, 0x6024, 0xa005,
-       0x0520, 0x8001, 0x6026, 0x6018, 0x6130, 0xa140, 0x2804, 0x7832,
-       0x8840, 0x2804, 0x7836, 0x8840, 0x2804, 0x7822, 0x8840, 0x2804,
-       0x7826, 0x8840, 0x7a02, 0x7000, 0x8000, 0x7002, 0x6018, 0xa802,
-       0xa08a, 0x0029, 0x1138, 0x6018, 0xa080, 0x0001, 0x2004, 0x601a,
-       0x2001, 0x000d, 0x6032, 0xa085, 0x0001, 0x0005, 0x00f6, 0x00e6,
-       0x00c6, 0x2071, 0xb01e, 0x2079, 0x0020, 0x7904, 0xd1fc, 0x01f0,
-       0x7803, 0x0002, 0x2d60, 0xa026, 0x7000, 0x0002, 0x34d6, 0x34c1,
-       0x34cd, 0x8001, 0x7002, 0xd19c, 0x1188, 0x2011, 0x0001, 0x080c,
-       0x3486, 0x0160, 0x080c, 0x3486, 0x0048, 0x8001, 0x7002, 0x7804,
-       0xd0fc, 0x1d30, 0x2011, 0x0001, 0x080c, 0x3486, 0x00ce, 0x00ee,
-       0x00fe, 0x0005, 0x00f6, 0x00e6, 0x00c6, 0x2061, 0x0200, 0x601b,
-       0x0004, 0x2061, 0x0100, 0x60cf, 0x0400, 0x6004, 0xc0ac, 0xa085,
-       0x0200, 0x6006, 0x2001, 0x0074, 0x2004, 0xa005, 0x01f8, 0x2038,
-       0x2001, 0x0076, 0x2024, 0x2001, 0x0077, 0x201c, 0x080c, 0x3c05,
-       0x6833, 0x000d, 0x6f26, 0x2d00, 0x681a, 0xa78a, 0x0007, 0x0220,
-       0x2138, 0x2009, 0x0007, 0x0010, 0x2708, 0xa03e, 0x6818, 0xa080,
-       0x000d, 0x04a1, 0x1d90, 0x2d00, 0x681a, 0x0088, 0x080c, 0x3c05,
-       0x6833, 0x000d, 0x2070, 0x6827, 0x0001, 0x2d00, 0x681a, 0x2001,
-       0x0076, 0x2004, 0x2072, 0x2001, 0x0077, 0x2004, 0x7006, 0x2061,
-       0x0020, 0x2079, 0x0100, 0x6013, 0x0400, 0x20e1, 0x9040, 0x2001,
-       0x0072, 0x2004, 0xa084, 0xfff8, 0x700a, 0x601a, 0x0006, 0x2001,
-       0x0073, 0x2004, 0x700e, 0x601e, 0x78c6, 0x000e, 0x78ca, 0xa006,
-       0x603a, 0x603e, 0x00ce, 0x00ee, 0x00fe, 0x0005, 0x00e6, 0x2071,
-       0x0010, 0x20a0, 0x2099, 0x0014, 0x7003, 0x0026, 0x7432, 0x7336,
-       0xa006, 0x703a, 0x703e, 0x810b, 0x810b, 0x21a8, 0x810b, 0x7122,
-       0x7003, 0x0041, 0x7004, 0xd0fc, 0x0de8, 0x7003, 0x0002, 0x7003,
-       0x0040, 0x53a5, 0x7430, 0x7334, 0x87ff, 0x0180, 0x00c6, 0x00d6,
-       0x2d60, 0x00c6, 0x080c, 0x3c05, 0x00ce, 0x6018, 0x2070, 0x2d00,
-       0x7006, 0x601a, 0x00de, 0x00ce, 0xa085, 0x0001, 0x00ee, 0x0005,
-       0x00e6, 0x2001, 0x0075, 0x2004, 0xa005, 0x0508, 0x2038, 0x2001,
-       0x0078, 0x2024, 0x2001, 0x0079, 0x201c, 0x080c, 0x3c05, 0x2d60,
-       0x6833, 0x000d, 0x6f26, 0x2d00, 0x681a, 0xa78a, 0x0007, 0x0220,
-       0x2138, 0x2009, 0x0007, 0x0010, 0x2708, 0xa03e, 0x6818, 0xa080,
-       0x000d, 0x080c, 0x353e, 0x1d88, 0x2d00, 0x681a, 0x00e0, 0x080c,
-       0x3c05, 0x2d60, 0x6033, 0x000d, 0x2070, 0x6027, 0x0001, 0x2c00,
-       0x601a, 0x2001, 0x0078, 0x2004, 0x2072, 0x2001, 0x0079, 0x2004,
-       0x7006, 0x2001, 0x0072, 0x2004, 0xa084, 0xfff8, 0x700a, 0x2001,
-       0x0073, 0x2004, 0x700e, 0x2001, 0x0030, 0x2003, 0x0004, 0x7824,
-       0xd0ac, 0x1178, 0x2001, 0x0101, 0x200c, 0xc1ed, 0x2102, 0x6027,
-       0x0000, 0x2001, 0xaffd, 0x2003, 0x0003, 0x2001, 0x0030, 0x2003,
-       0x0009, 0x00ee, 0x0005, 0x0804, 0x2dcc, 0x0126, 0x2091, 0x8000,
-       0x20a9, 0x0011, 0x2001, 0xad40, 0x20a0, 0xa006, 0x40a4, 0x012e,
-       0x0804, 0x2dcc, 0x7d38, 0x7c3c, 0x0804, 0x2e73, 0x080c, 0x3c05,
-       0x0904, 0x2df1, 0x080c, 0x574f, 0x0110, 0x080c, 0x491f, 0x2009,
-       0x001c, 0x7a2c, 0x7b28, 0x7c3c, 0x7d38, 0x080c, 0x3c46, 0x701b,
-       0x35f2, 0x0005, 0xade8, 0x000d, 0x6800, 0xa005, 0x0904, 0x2df4,
-       0x6804, 0xd0ac, 0x0118, 0xd0a4, 0x0904, 0x2df4, 0xd094, 0x00c6,
-       0x2061, 0x0100, 0x6104, 0x0138, 0x6200, 0xa292, 0x0005, 0x0218,
-       0xa18c, 0xffdf, 0x0010, 0xa18d, 0x0020, 0x6106, 0x00ce, 0xd08c,
-       0x00c6, 0x2061, 0x0100, 0x6104, 0x0118, 0xa18d, 0x0010, 0x0010,
-       0xa18c, 0xffef, 0x6106, 0x00ce, 0x2009, 0x0100, 0x210c, 0xa18a,
-       0x0002, 0x0268, 0xd084, 0x0158, 0x6a28, 0xa28a, 0x007f, 0x1a04,
-       0x2df4, 0xa288, 0x2be6, 0x210d, 0xa18c, 0x00ff, 0x6156, 0xd0dc,
-       0x0130, 0x6828, 0xa08a, 0x007f, 0x1a04, 0x2df4, 0x604e, 0x6808,
-       0xa08a, 0x0100, 0x0a04, 0x2df4, 0xa08a, 0x0841, 0x1a04, 0x2df4,
-       0xa084, 0x0007, 0x1904, 0x2df4, 0x680c, 0xa005, 0x0904, 0x2df4,
-       0x6810, 0xa005, 0x0904, 0x2df4, 0x6848, 0x6940, 0xa10a, 0x1a04,
-       0x2df4, 0x8001, 0x0904, 0x2df4, 0x684c, 0x6944, 0xa10a, 0x1a04,
-       0x2df4, 0x8001, 0x0904, 0x2df4, 0x6804, 0xd0fc, 0x0560, 0x080c,
-       0x3c05, 0x0904, 0x2df1, 0x2009, 0x0014, 0x7a2c, 0x7b28, 0x7c3c,
-       0x7d38, 0xa290, 0x0038, 0xa399, 0x0000, 0x080c, 0x3c46, 0x701b,
-       0x3672, 0x0005, 0xade8, 0x000d, 0x20a9, 0x0014, 0x2d98, 0x2069,
-       0xad6d, 0x2da0, 0x53a3, 0x7010, 0xa0e8, 0x000d, 0x2001, 0xad71,
-       0x200c, 0xd1e4, 0x0140, 0x00c6, 0x2061, 0x0100, 0x6004, 0xa085,
-       0x0b00, 0x6006, 0x00ce, 0x20a9, 0x001c, 0x2d98, 0x2069, 0xad51,
-       0x2da0, 0x53a3, 0x6814, 0xa08c, 0x00ff, 0x613e, 0x8007, 0xa084,
-       0x00ff, 0x6042, 0x080c, 0x5a1c, 0x080c, 0x5070, 0x080c, 0x50d9,
-       0x6000, 0xa086, 0x0000, 0x1904, 0x3755, 0x6808, 0x602a, 0x080c,
-       0x22f8, 0x0006, 0x2001, 0x0100, 0x2004, 0xa082, 0x0005, 0x000e,
-       0x0268, 0x2009, 0x0170, 0x200b, 0x0080, 0xe000, 0xe000, 0x200b,
-       0x0000, 0x0036, 0x6b08, 0x080c, 0x26fb, 0x003e, 0x6818, 0x691c,
-       0x6a20, 0x6b24, 0x8007, 0x810f, 0x8217, 0x831f, 0x6016, 0x611a,
-       0x621e, 0x6322, 0x6c04, 0xd4f4, 0x0148, 0x6830, 0x6934, 0x6a38,
-       0x6b3c, 0x8007, 0x810f, 0x8217, 0x831f, 0x0010, 0xa084, 0xf0ff,
-       0x6006, 0x610a, 0x620e, 0x6312, 0x8007, 0x810f, 0x8217, 0x831f,
-       0x20a9, 0x0004, 0x20a1, 0xafad, 0x40a1, 0x080c, 0x659c, 0x6904,
-       0xd1fc, 0x0520, 0x00c6, 0x2009, 0x0000, 0x20a9, 0x0001, 0x6b70,
-       0xd384, 0x01c8, 0x0020, 0x839d, 0x12b0, 0x3508, 0x8109, 0x080c,
-       0x5fa9, 0x6878, 0x6016, 0x6874, 0x2008, 0xa084, 0xff00, 0x8007,
-       0x600a, 0xa184, 0x00ff, 0x6006, 0x8108, 0x1118, 0x6003, 0x0003,
-       0x0010, 0x6003, 0x0001, 0x1f04, 0x36f3, 0x00ce, 0x2069, 0xad51,
-       0x2001, 0xaf9d, 0x6a80, 0xa294, 0x0030, 0xa28e, 0x0000, 0x0170,
-       0xa28e, 0x0010, 0x0118, 0xa28e, 0x0020, 0x0140, 0x2003, 0xaaaa,
-       0x080c, 0x2744, 0x2001, 0xaf8e, 0x2102, 0x0008, 0x2102, 0x00c6,
-       0x2061, 0x0100, 0x602f, 0x0040, 0x602f, 0x0000, 0x00ce, 0x080c,
-       0x574f, 0x0128, 0x080c, 0x3e5f, 0x0110, 0x080c, 0x26c0, 0x60c4,
-       0xa005, 0x01b0, 0x6003, 0x0001, 0x2009, 0x373f, 0x00c0, 0x080c,
-       0x574f, 0x1158, 0x2011, 0x566e, 0x080c, 0x650d, 0x2001, 0xaf9e,
-       0x2003, 0x0000, 0x080c, 0x569a, 0x0040, 0x080c, 0x485e, 0x0028,
-       0x6003, 0x0004, 0x2009, 0x3755, 0x0010, 0x0804, 0x2dcc, 0x2001,
-       0x0100, 0x2004, 0xa082, 0x0005, 0x0258, 0x2001, 0x0170, 0x2004,
-       0xa084, 0x00ff, 0xa086, 0x004c, 0x1118, 0x2091, 0x309d, 0x0817,
-       0x2091, 0x301d, 0x0817, 0x6000, 0xa086, 0x0000, 0x0904, 0x2df1,
-       0x2069, 0xad51, 0x7830, 0x6842, 0x7834, 0x6846, 0x6804, 0xd0fc,
-       0x0118, 0x2009, 0x0030, 0x0010, 0x2009, 0x001c, 0x2d00, 0x7a2c,
-       0x7b28, 0x7c3c, 0x7d38, 0x0804, 0x3c49, 0xa006, 0x080c, 0x26c0,
-       0x81ff, 0x1904, 0x2df1, 0x080c, 0x574f, 0x1178, 0x2001, 0xaf9e,
-       0x2003, 0x0001, 0x2001, 0xad00, 0x2003, 0x0001, 0xa085, 0x0001,
-       0x080c, 0x5793, 0x080c, 0x569a, 0x0020, 0x080c, 0x491f, 0x080c,
-       0x485e, 0x0804, 0x2dcc, 0x81ff, 0x1904, 0x2df1, 0x080c, 0x574f,
-       0x1110, 0x0804, 0x2df1, 0x6184, 0x81ff, 0x0198, 0x703f, 0x0000,
-       0x2001, 0xb3c0, 0x2009, 0x0040, 0x7a2c, 0x7b28, 0x7c3c, 0x7d38,
-       0x0126, 0x2091, 0x8000, 0x080c, 0x3c49, 0x701b, 0x2dca, 0x012e,
-       0x0005, 0x703f, 0x0001, 0x00d6, 0x2069, 0xb3c0, 0x20a9, 0x0040,
-       0x20a1, 0xb3c0, 0x2019, 0xffff, 0x43a4, 0x654c, 0xa588, 0x2be6,
-       0x210d, 0xa18c, 0x00ff, 0x216a, 0xa00e, 0x2011, 0x0002, 0x2100,
-       0xa506, 0x01a8, 0x080c, 0x4cdc, 0x1190, 0x6014, 0x821c, 0x0238,
-       0xa398, 0xb3c0, 0xa085, 0xff00, 0x8007, 0x201a, 0x0038, 0xa398,
-       0xb3c0, 0x2324, 0xa4a4, 0xff00, 0xa405, 0x201a, 0x8210, 0x8108,
-       0xa182, 0x0080, 0x1208, 0x0c18, 0x8201, 0x8007, 0x2d0c, 0xa105,
-       0x206a, 0x00de, 0x20a9, 0x0040, 0x20a1, 0xb3c0, 0x2099, 0xb3c0,
-       0x080c, 0x48be, 0x0804, 0x37b0, 0x080c, 0x3c2a, 0x0904, 0x2df4,
-       0x00c6, 0x080c, 0x3c05, 0x00ce, 0x1120, 0x2009, 0x0002, 0x0804,
-       0x2df1, 0x2001, 0xad52, 0x2004, 0xd0b4, 0x01f0, 0x6000, 0xd08c,
-       0x11d8, 0x6004, 0xa084, 0x00ff, 0xa086, 0x0006, 0x11a8, 0x6837,
-       0x0000, 0x6838, 0xc0fd, 0x683a, 0x080c, 0x970b, 0x1120, 0x2009,
-       0x0003, 0x0804, 0x2df1, 0x7007, 0x0003, 0x701b, 0x3830, 0x0005,
-       0x080c, 0x3c2a, 0x0904, 0x2df4, 0x20a9, 0x002b, 0x2c98, 0xade8,
-       0x0002, 0x2da0, 0x53a3, 0x20a9, 0x0004, 0xac80, 0x0006, 0x2098,
-       0xad80, 0x0006, 0x20a0, 0x080c, 0x48be, 0x20a9, 0x0004, 0xac80,
-       0x000a, 0x2098, 0xad80, 0x000a, 0x20a0, 0x080c, 0x48be, 0x2d00,
-       0x2009, 0x002b, 0x7a2c, 0x7b28, 0x7c3c, 0x7d38, 0x0804, 0x3c49,
-       0x81ff, 0x1904, 0x2df1, 0x080c, 0x3c1a, 0x0904, 0x2df4, 0x080c,
-       0x4eab, 0x0804, 0x2dcc, 0x81ff, 0x1904, 0x2df1, 0x7828, 0xa08a,
-       0x1000, 0x1a04, 0x2df4, 0x080c, 0x3c2a, 0x0904, 0x2df4, 0x080c,
-       0x4f0d, 0x0904, 0x2df1, 0x2019, 0x0004, 0x080c, 0x4ebd, 0x7924,
-       0x810f, 0x7a28, 0x0011, 0x0804, 0x2dcc, 0xa186, 0x00ff, 0x0110,
-       0x0071, 0x0060, 0x2029, 0x007e, 0x2061, 0xad00, 0x644c, 0x2400,
-       0xa506, 0x0110, 0x2508, 0x0019, 0x8529, 0x1ec8, 0x0005, 0x080c,
-       0x4cdc, 0x1138, 0x2200, 0x8003, 0x800b, 0x810b, 0xa108, 0x080c,
-       0x6519, 0x0005, 0x81ff, 0x1904, 0x2df1, 0x080c, 0x3c1a, 0x0904,
-       0x2df4, 0x080c, 0x4d96, 0x0904, 0x2df1, 0x080c, 0x4eb4, 0x0804,
-       0x2dcc, 0x81ff, 0x1904, 0x2df1, 0x080c, 0x3c1a, 0x0904, 0x2df4,
-       0x080c, 0x4d96, 0x0904, 0x2df1, 0x080c, 0x4ea2, 0x0804, 0x2dcc,
-       0x6100, 0x0804, 0x2dcc, 0x080c, 0x3c2a, 0x0904, 0x2df4, 0x2001,
-       0xad00, 0x2004, 0xa086, 0x0003, 0x1904, 0x2df1, 0x00d6, 0xace8,
-       0x000a, 0x7924, 0xd184, 0x0110, 0xace8, 0x0006, 0x680c, 0x8007,
-       0x783e, 0x6808, 0x8007, 0x783a, 0x6b04, 0x831f, 0x6a00, 0x8217,
-       0x00de, 0x6100, 0xa18c, 0x0200, 0x0804, 0x2dcc, 0x7824, 0xa09c,
-       0x00ff, 0xa39a, 0x0003, 0x1a04, 0x2df1, 0x624c, 0xa294, 0x00ff,
-       0xa084, 0xff00, 0x8007, 0xa206, 0x1150, 0x2001, 0xad40, 0x2009,
-       0x000c, 0x7a2c, 0x7b28, 0x7c3c, 0x7d38, 0x0804, 0x3c49, 0x81ff,
-       0x1904, 0x2df1, 0x080c, 0x3c2a, 0x0904, 0x2df4, 0x6004, 0xa084,
-       0x00ff, 0xa086, 0x0006, 0x1904, 0x2df1, 0x00c6, 0x080c, 0x3c05,
-       0x00ce, 0x0904, 0x2df1, 0x6837, 0x0000, 0x6838, 0xc0fd, 0x683a,
-       0x080c, 0x96b7, 0x0904, 0x2df1, 0x7007, 0x0003, 0x701b, 0x3919,
-       0x0005, 0x6830, 0xa086, 0x0100, 0x0904, 0x2df1, 0xad80, 0x000e,
-       0x2009, 0x000c, 0x7a2c, 0x7b28, 0x7c3c, 0x7d38, 0x0804, 0x3c49,
-       0xa006, 0x080c, 0x26c0, 0x7824, 0xa084, 0x00ff, 0xa086, 0x00ff,
-       0x0118, 0x81ff, 0x1904, 0x2df1, 0x080c, 0x574f, 0x0110, 0x080c,
-       0x491f, 0x7828, 0xa08a, 0x1000, 0x1a04, 0x2df4, 0x7924, 0xa18c,
-       0xff00, 0x810f, 0xa186, 0x00ff, 0x0138, 0xa182, 0x007f, 0x1a04,
-       0x2df4, 0x2100, 0x080c, 0x268a, 0x0026, 0x00c6, 0x0126, 0x2091,
-       0x8000, 0x2061, 0xafda, 0x601b, 0x0000, 0x601f, 0x0000, 0x080c,
-       0x574f, 0x1178, 0x2001, 0xaf9e, 0x2003, 0x0001, 0x2001, 0xad00,
-       0x2003, 0x0001, 0xa085, 0x0001, 0x080c, 0x5793, 0x080c, 0x569a,
-       0x00a0, 0x2061, 0x0100, 0x2001, 0xad14, 0x2004, 0xa084, 0x00ff,
-       0x810f, 0xa105, 0x604a, 0x6043, 0x0090, 0x6043, 0x0010, 0x2009,
-       0x002d, 0x2011, 0x4883, 0x080c, 0x6593, 0x7924, 0xa18c, 0xff00,
-       0x810f, 0x080c, 0x574f, 0x1110, 0x2009, 0x00ff, 0x7a28, 0x080c,
-       0x387d, 0x012e, 0x00ce, 0x002e, 0x0804, 0x2dcc, 0x7924, 0xa18c,
-       0xff00, 0x810f, 0x00c6, 0x080c, 0x4c80, 0x2c08, 0x00ce, 0x1904,
-       0x2df4, 0x0804, 0x2dcc, 0x81ff, 0x0120, 0x2009, 0x0001, 0x0804,
-       0x2df1, 0x60d0, 0xd0ac, 0x1130, 0xd09c, 0x1120, 0x2009, 0x0005,
-       0x0804, 0x2df1, 0x080c, 0x3c05, 0x1120, 0x2009, 0x0002, 0x0804,
-       0x2df1, 0x7924, 0x7a2c, 0x7b28, 0x7c3c, 0x7d38, 0x080c, 0x3c46,
-       0x701b, 0x39bb, 0x0005, 0x2009, 0x0080, 0x080c, 0x4cdc, 0x1130,
-       0x6004, 0xa084, 0x00ff, 0xa086, 0x0006, 0x0120, 0x2021, 0x400a,
-       0x0804, 0x2dce, 0x00d6, 0xade8, 0x000d, 0x6900, 0x6a08, 0x6b0c,
-       0x6c10, 0x6d14, 0x6e18, 0x6820, 0xa0be, 0x0100, 0x0904, 0x3a32,
-       0xa0be, 0x0112, 0x0904, 0x3a32, 0xa0be, 0x0113, 0x0904, 0x3a32,
-       0xa0be, 0x0114, 0x0904, 0x3a32, 0xa0be, 0x0117, 0x0904, 0x3a32,
-       0xa0be, 0x011a, 0x0904, 0x3a32, 0xa0be, 0x011c, 0x0904, 0x3a32,
-       0xa0be, 0x0121, 0x05b0, 0xa0be, 0x0131, 0x0598, 0xa0be, 0x0171,
-       0x05c8, 0xa0be, 0x0173, 0x05b0, 0xa0be, 0x01a1, 0x1120, 0x6830,
-       0x8007, 0x6832, 0x04a8, 0xa0be, 0x0212, 0x0540, 0xa0be, 0x0213,
-       0x0528, 0xa0be, 0x0214, 0x01b0, 0xa0be, 0x0217, 0x0168, 0xa0be,
-       0x021a, 0x1120, 0x6838, 0x8007, 0x683a, 0x00e0, 0xa0be, 0x0300,
-       0x01c8, 0x00de, 0x0804, 0x2df4, 0xad80, 0x0010, 0x20a9, 0x0007,
-       0x080c, 0x3a78, 0xad80, 0x000e, 0x20a9, 0x0001, 0x080c, 0x3a78,
-       0x0048, 0xad80, 0x000c, 0x080c, 0x3a86, 0x0050, 0xad80, 0x000e,
-       0x080c, 0x3a86, 0xad80, 0x000c, 0x20a9, 0x0001, 0x080c, 0x3a78,
-       0x00c6, 0x080c, 0x3c05, 0x0568, 0x6838, 0xc0fd, 0x683a, 0x6837,
-       0x0119, 0x6853, 0x0000, 0x684f, 0x0020, 0x685b, 0x0001, 0x810b,
-       0x697e, 0x6883, 0x0000, 0x6a86, 0x6b8a, 0x6c8e, 0x6d92, 0x6996,
-       0x689b, 0x0000, 0x00ce, 0x00de, 0x6837, 0x0000, 0x6838, 0xc0fd,
-       0x683a, 0x6823, 0x0000, 0x6804, 0x2068, 0x080c, 0x96d3, 0x1120,
-       0x2009, 0x0003, 0x0804, 0x2df1, 0x7007, 0x0003, 0x701b, 0x3a6f,
-       0x0005, 0x00ce, 0x00de, 0x2009, 0x0002, 0x0804, 0x2df1, 0x6820,
-       0xa086, 0x8001, 0x1904, 0x2dcc, 0x2009, 0x0004, 0x0804, 0x2df1,
-       0x0016, 0x2008, 0x2044, 0x8000, 0x204c, 0x8000, 0x290a, 0x8108,
-       0x280a, 0x8108, 0x1f04, 0x3a7a, 0x001e, 0x0005, 0x0016, 0x00a6,
-       0x00b6, 0x2008, 0x2044, 0x8000, 0x204c, 0x8000, 0x2054, 0x8000,
-       0x205c, 0x2b0a, 0x8108, 0x2a0a, 0x8108, 0x290a, 0x8108, 0x280a,
-       0x00be, 0x00ae, 0x001e, 0x0005, 0x81ff, 0x0120, 0x2009, 0x0001,
-       0x0804, 0x2df1, 0x7924, 0x2140, 0xa18c, 0xff00, 0x810f, 0x60d0,
-       0xd0ac, 0x1120, 0xa182, 0x0080, 0x0a04, 0x2df4, 0xa182, 0x00ff,
-       0x1a04, 0x2df4, 0x7a2c, 0x7b28, 0x606c, 0xa306, 0x1140, 0x6070,
-       0xa24e, 0x0904, 0x2df4, 0xa9cc, 0xff00, 0x0904, 0x2df4, 0x00c6,
-       0x080c, 0x3b58, 0x2c68, 0x00ce, 0x0538, 0xa0c6, 0x4000, 0x1180,
-       0x00c6, 0x0006, 0x2d60, 0x2009, 0x0000, 0x080c, 0x4f6e, 0x1108,
-       0xc185, 0x6000, 0xd0bc, 0x0108, 0xc18d, 0x000e, 0x00ce, 0x0088,
-       0xa0c6, 0x4007, 0x1110, 0x2408, 0x0060, 0xa0c6, 0x4008, 0x1118,
-       0x2708, 0x2610, 0x0030, 0xa0c6, 0x4009, 0x1108, 0x0010, 0x2001,
-       0x4006, 0x2020, 0x0804, 0x2dce, 0x2d00, 0x7022, 0x0016, 0x00b6,
-       0x00c6, 0x00e6, 0x2c70, 0x080c, 0x8022, 0x05d8, 0x2d00, 0x601a,
-       0x080c, 0x9956, 0x2e58, 0x00ee, 0x00e6, 0x00c6, 0x080c, 0x3c05,
-       0x00ce, 0x2b70, 0x1150, 0x080c, 0x8078, 0x00ee, 0x00ce, 0x00be,
-       0x001e, 0x2009, 0x0002, 0x0804, 0x2df1, 0x6837, 0x0000, 0x683b,
-       0x0000, 0x2d00, 0x6012, 0x6833, 0x0000, 0x6838, 0xc0fd, 0xd88c,
-       0x0108, 0xc0f5, 0x683a, 0x0126, 0x2091, 0x8000, 0x080c, 0x2ad9,
-       0x012e, 0x601f, 0x0001, 0x2001, 0x0000, 0x080c, 0x4c1e, 0x2001,
-       0x0002, 0x080c, 0x4c30, 0x2009, 0x0002, 0x080c, 0x80a7, 0xa085,
-       0x0001, 0x00ee, 0x00ce, 0x00be, 0x001e, 0x1120, 0x2009, 0x0003,
-       0x0804, 0x2df1, 0x7007, 0x0003, 0x701b, 0x3b3f, 0x0005, 0x6830,
-       0xa086, 0x0100, 0x7020, 0x2060, 0x1138, 0x2009, 0x0004, 0x6204,
-       0xa294, 0x00ff, 0x0804, 0x2df1, 0x2009, 0x0000, 0x080c, 0x4f6e,
-       0x1108, 0xc185, 0x6000, 0xd0bc, 0x0108, 0xc18d, 0x0804, 0x2dcc,
-       0x00e6, 0x00d6, 0x2029, 0x0000, 0x2001, 0xad34, 0x2004, 0xd0ac,
-       0x0138, 0x2021, 0x0000, 0x20a9, 0x00ff, 0x2071, 0xae34, 0x0030,
-       0x2021, 0x0080, 0x20a9, 0x007f, 0x2071, 0xaeb4, 0x2e04, 0xa005,
-       0x1130, 0x2100, 0xa406, 0x1548, 0x2428, 0xc5fd, 0x0430, 0x2068,
-       0x6f10, 0x2700, 0xa306, 0x11b0, 0x6e14, 0x2600, 0xa206, 0x1190,
-       0x2400, 0xa106, 0x1160, 0x2d60, 0xd884, 0x0540, 0x6004, 0xa084,
-       0x00ff, 0xa086, 0x0006, 0x1510, 0x2001, 0x4000, 0x0400, 0x2001,
-       0x4007, 0x00e8, 0x2400, 0xa106, 0x1140, 0x6e14, 0x87ff, 0x1110,
-       0x86ff, 0x09d0, 0x2001, 0x4008, 0x0090, 0x8420, 0x8e70, 0x1f04,
-       0x3b6e, 0x85ff, 0x1130, 0x2001, 0x4009, 0x0048, 0x2001, 0x0001,
-       0x0030, 0x080c, 0x4c80, 0x1dd0, 0x6312, 0x6216, 0xa006, 0xa005,
-       0x00de, 0x00ee, 0x0005, 0x81ff, 0x1904, 0x2df1, 0x080c, 0x3c05,
-       0x0904, 0x2df1, 0x6837, 0x0000, 0x6838, 0xc0fd, 0x683a, 0x7824,
-       0xa005, 0x0904, 0x2df4, 0xa096, 0x00ff, 0x0120, 0xa092, 0x0004,
-       0x1a04, 0x2df4, 0x2010, 0x2d18, 0x080c, 0x2a8c, 0x0904, 0x2df1,
-       0x7007, 0x0003, 0x701b, 0x3bd5, 0x0005, 0x6830, 0xa086, 0x0100,
-       0x0904, 0x2df1, 0x0804, 0x2dcc, 0x7924, 0xa18c, 0xff00, 0x810f,
-       0x60d0, 0xd0ac, 0x1120, 0xa182, 0x0080, 0x0a04, 0x2df4, 0xa182,
-       0x00ff, 0x1a04, 0x2df4, 0x0126, 0x2091, 0x8000, 0x080c, 0x95c6,
-       0x1188, 0xa190, 0xae34, 0x2204, 0xa065, 0x0160, 0x080c, 0x493a,
-       0x2001, 0xad34, 0x2004, 0xd0ac, 0x0110, 0x6017, 0x0000, 0x012e,
-       0x0804, 0x2dcc, 0x012e, 0x0804, 0x2df1, 0x080c, 0x15d9, 0x0188,
-       0xa006, 0x6802, 0x7010, 0xa005, 0x1120, 0x2d00, 0x7012, 0x7016,
-       0x0030, 0x7014, 0x6802, 0x2060, 0x2d00, 0x6006, 0x7016, 0xad80,
-       0x000d, 0x0005, 0x7924, 0x810f, 0xa18c, 0x00ff, 0x080c, 0x4cdc,
-       0x1130, 0x7e28, 0xa684, 0x3fff, 0xa082, 0x4000, 0x0208, 0xa066,
-       0x8cff, 0x0005, 0x7e24, 0x860f, 0xa18c, 0x00ff, 0x080c, 0x4cdc,
-       0x1128, 0xa6b4, 0x00ff, 0xa682, 0x4000, 0x0208, 0xa066, 0x8cff,
-       0x0005, 0x0016, 0x7110, 0x81ff, 0x0128, 0x2168, 0x6904, 0x080c,
-       0x15f0, 0x0cc8, 0x7112, 0x7116, 0x001e, 0x0005, 0x2031, 0x0001,
-       0x0010, 0x2031, 0x0000, 0x2061, 0xadd1, 0x6606, 0x6112, 0x600e,
-       0x6226, 0x632a, 0x642e, 0x6532, 0x2c10, 0x080c, 0x1624, 0x7007,
-       0x0002, 0x701b, 0x2dcc, 0x0005, 0x00f6, 0x0126, 0x2091, 0x8000,
-       0x2079, 0x0000, 0x2001, 0xad8f, 0x2004, 0xa005, 0x1168, 0x0e04,
-       0x3c74, 0x7818, 0xd084, 0x1140, 0x7a22, 0x7b26, 0x7c2a, 0x781b,
-       0x0001, 0x2091, 0x4080, 0x0408, 0x0016, 0x00c6, 0x00e6, 0x2071,
-       0xad81, 0x7138, 0xa182, 0x0010, 0x0218, 0x7030, 0x2060, 0x0078,
-       0x7030, 0xa0e0, 0x0004, 0xac82, 0xadd1, 0x0210, 0x2061, 0xad91,
-       0x2c00, 0x7032, 0x81ff, 0x1108, 0x7036, 0x8108, 0x713a, 0x2262,
-       0x6306, 0x640a, 0x00ee, 0x00ce, 0x001e, 0x012e, 0x00fe, 0x0005,
-       0x00e6, 0x2071, 0xad81, 0x7038, 0xa005, 0x0570, 0x0126, 0x2091,
-       0x8000, 0x0e04, 0x3ccb, 0x00f6, 0x2079, 0x0000, 0x7818, 0xd084,
-       0x1508, 0x00c6, 0x7034, 0x2060, 0x2c04, 0x7822, 0x6004, 0x7826,
-       0x6008, 0x782a, 0x781b, 0x0001, 0x2091, 0x4080, 0x7038, 0x8001,
-       0x703a, 0xa005, 0x1130, 0x7033, 0xad91, 0x7037, 0xad91, 0x00ce,
-       0x0048, 0xac80, 0x0004, 0xa0fa, 0xadd1, 0x0210, 0x2001, 0xad91,
-       0x7036, 0x00ce, 0x00fe, 0x012e, 0x00ee, 0x0005, 0x0026, 0x2001,
-       0xad52, 0x2004, 0xd0c4, 0x0120, 0x2011, 0x8014, 0x080c, 0x3c5c,
-       0x002e, 0x0005, 0x81ff, 0x1904, 0x2df1, 0x0126, 0x2091, 0x8000,
-       0x6030, 0xc08d, 0xc085, 0xc0ac, 0x6032, 0x080c, 0x574f, 0x1178,
-       0x2001, 0xaf9e, 0x2003, 0x0001, 0x2001, 0xad00, 0x2003, 0x0001,
-       0xa085, 0x0001, 0x080c, 0x5793, 0x080c, 0x569a, 0x0010, 0x080c,
-       0x485e, 0x012e, 0x0804, 0x2dcc, 0x7824, 0x2008, 0xa18c, 0xfffd,
-       0x1128, 0x61dc, 0xa10d, 0x61de, 0x0804, 0x2dcc, 0x0804, 0x2df4,
-       0x81ff, 0x1904, 0x2df1, 0x6000, 0xa086, 0x0003, 0x1904, 0x2df1,
-       0x2001, 0xad52, 0x2004, 0xd0ac, 0x1904, 0x2df1, 0x080c, 0x3c2a,
-       0x0904, 0x2df4, 0x6004, 0xa084, 0x00ff, 0xa086, 0x0006, 0x1120,
-       0x7828, 0xa005, 0x0904, 0x2dcc, 0x00c6, 0x080c, 0x3c05, 0x00ce,
-       0x0904, 0x2df1, 0x6837, 0x0000, 0x6833, 0x0000, 0x6838, 0xc0fd,
-       0x683a, 0x080c, 0x979c, 0x0904, 0x2df1, 0x7007, 0x0003, 0x701b,
-       0x3d3a, 0x0005, 0x6830, 0xa086, 0x0100, 0x0904, 0x2df1, 0x0804,
-       0x2dcc, 0x2001, 0xad00, 0x2004, 0xa086, 0x0003, 0x1904, 0x2df1,
-       0x7f24, 0x7a2c, 0x7b28, 0x7c3c, 0x7d38, 0x080c, 0x3c05, 0x0904,
-       0x2df1, 0x2009, 0x0000, 0x2031, 0x0000, 0x7023, 0x0000, 0x702f,
-       0x0000, 0xad80, 0x0005, 0x7026, 0x20a0, 0x080c, 0x4cdc, 0x1904,
-       0x3db4, 0x6004, 0xa0c4, 0x00ff, 0xa8c6, 0x0006, 0x0130, 0xa0c4,
-       0xff00, 0xa8c6, 0x0600, 0x1904, 0x3db4, 0x2001, 0xad52, 0x2004,
-       0xd0ac, 0x1128, 0x080c, 0x4f6e, 0x1110, 0xd79c, 0x05e8, 0xd794,
-       0x1110, 0xd784, 0x0158, 0xac80, 0x0006, 0x2098, 0x3400, 0x20a9,
-       0x0004, 0x53a3, 0x080c, 0x3a86, 0xd794, 0x0148, 0xac80, 0x000a,
-       0x2098, 0x3400, 0x20a9, 0x0004, 0x53a3, 0x080c, 0x3a86, 0x21a2,
-       0xd794, 0x01d8, 0xac80, 0x0000, 0x2098, 0x94a0, 0x20a9, 0x0002,
-       0x53a3, 0xac80, 0x0003, 0x20a6, 0x94a0, 0xac80, 0x0004, 0x2098,
-       0x3400, 0x20a9, 0x0002, 0x53a3, 0x080c, 0x3a78, 0xac80, 0x0026,
-       0x2098, 0x20a9, 0x0002, 0x53a3, 0x0008, 0x94a0, 0xd794, 0x0110,
-       0xa6b0, 0x000b, 0xa6b0, 0x0005, 0x8108, 0x2001, 0xad34, 0x2004,
-       0xd0ac, 0x0118, 0xa186, 0x0100, 0x0040, 0xd78c, 0x0120, 0xa186,
-       0x0100, 0x0170, 0x0018, 0xa186, 0x007e, 0x0150, 0xd794, 0x0118,
-       0xa686, 0x0020, 0x0010, 0xa686, 0x0028, 0x0150, 0x0804, 0x3d5d,
-       0x86ff, 0x1120, 0x7120, 0x810b, 0x0804, 0x2dcc, 0x702f, 0x0001,
-       0x711e, 0x7020, 0xa600, 0x7022, 0x772a, 0x2061, 0xadd1, 0x6007,
-       0x0000, 0x6612, 0x7024, 0x600e, 0x6226, 0x632a, 0x642e, 0x6532,
-       0x2c10, 0x080c, 0x1624, 0x7007, 0x0002, 0x701b, 0x3df0, 0x0005,
-       0x702c, 0xa005, 0x1170, 0x711c, 0x7024, 0x20a0, 0x7728, 0x2031,
-       0x0000, 0x2061, 0xadd1, 0x6224, 0x6328, 0x642c, 0x6530, 0x0804,
-       0x3d5d, 0x7120, 0x810b, 0x0804, 0x2dcc, 0x2029, 0x007e, 0x7924,
-       0x7a28, 0x7b2c, 0x7c38, 0xa184, 0xff00, 0x8007, 0xa0e2, 0x0020,
-       0x0a04, 0x2df4, 0xa502, 0x0a04, 0x2df4, 0xa184, 0x00ff, 0xa0e2,
-       0x0020, 0x0a04, 0x2df4, 0xa502, 0x0a04, 0x2df4, 0xa284, 0xff00,
-       0x8007, 0xa0e2, 0x0020, 0x0a04, 0x2df4, 0xa502, 0x0a04, 0x2df4,
-       0xa284, 0x00ff, 0xa0e2, 0x0020, 0x0a04, 0x2df4, 0xa502, 0x0a04,
-       0x2df4, 0xa384, 0xff00, 0x8007, 0xa0e2, 0x0020, 0x0a04, 0x2df4,
-       0xa502, 0x0a04, 0x2df4, 0xa384, 0x00ff, 0xa0e2, 0x0020, 0x0a04,
-       0x2df4, 0xa502, 0x0a04, 0x2df4, 0xa484, 0xff00, 0x8007, 0xa0e2,
-       0x0020, 0x0a04, 0x2df4, 0xa502, 0x0a04, 0x2df4, 0xa484, 0x00ff,
-       0xa0e2, 0x0020, 0x0a04, 0x2df4, 0xa502, 0x0a04, 0x2df4, 0x2061,
-       0xafa6, 0x6102, 0x6206, 0x630a, 0x640e, 0x0804, 0x2dcc, 0x0006,
-       0x2001, 0xad52, 0x2004, 0xd0cc, 0x000e, 0x0005, 0x0006, 0x2001,
-       0xad71, 0x2004, 0xd0bc, 0x000e, 0x0005, 0x6164, 0x7a24, 0x6300,
-       0x82ff, 0x1118, 0x7926, 0x0804, 0x2dcc, 0x83ff, 0x1904, 0x2df4,
-       0x2001, 0xfff0, 0xa200, 0x1a04, 0x2df4, 0x2019, 0xffff, 0x6068,
-       0xa302, 0xa200, 0x0a04, 0x2df4, 0x7926, 0x6266, 0x0804, 0x2dcc,
-       0x2001, 0xad00, 0x2004, 0xa086, 0x0003, 0x1904, 0x2df1, 0x7c28,
-       0x7d24, 0x7e38, 0x7f2c, 0x080c, 0x3c05, 0x0904, 0x2df1, 0x2009,
-       0x0000, 0x2019, 0x0000, 0x7023, 0x0000, 0x702f, 0x0000, 0xad80,
-       0x0003, 0x7026, 0x20a0, 0xa1e0, 0xae34, 0x2c64, 0x8cff, 0x01b8,
-       0x6004, 0xa084, 0x00ff, 0xa086, 0x0006, 0x0130, 0x6004, 0xa084,
-       0xff00, 0xa086, 0x0600, 0x1158, 0x6014, 0x20a2, 0x94a0, 0x6010,
-       0x8007, 0xa105, 0x8007, 0x20a2, 0x94a0, 0xa398, 0x0002, 0x8108,
-       0xa182, 0x00ff, 0x0120, 0xa386, 0x002a, 0x0148, 0x08e0, 0x83ff,
-       0x1120, 0x7120, 0x810c, 0x0804, 0x2dcc, 0x702f, 0x0001, 0x711e,
-       0x7020, 0xa300, 0x7022, 0x2061, 0xadd1, 0x6007, 0x0000, 0x6312,
-       0x7024, 0x600e, 0x6426, 0x652a, 0x662e, 0x6732, 0x2c10, 0x080c,
-       0x1624, 0x7007, 0x0002, 0x701b, 0x3ee6, 0x0005, 0x702c, 0xa005,
-       0x1168, 0x711c, 0x7024, 0x20a0, 0x2019, 0x0000, 0x2061, 0xadd1,
-       0x6424, 0x6528, 0x662c, 0x6730, 0x0804, 0x3ea3, 0x7120, 0x810c,
-       0x0804, 0x2dcc, 0x81ff, 0x1904, 0x2df1, 0x60d0, 0xd0ac, 0x1118,
-       0xd09c, 0x0904, 0x2df1, 0x080c, 0x3c05, 0x0904, 0x2df1, 0x7924,
-       0x7a2c, 0x7b28, 0x7c3c, 0x7d38, 0x080c, 0x3c46, 0x701b, 0x3f11,
-       0x0005, 0x00d6, 0xade8, 0x000d, 0x6828, 0xa0be, 0x7000, 0x0148,
-       0xa0be, 0x7100, 0x0130, 0xa0be, 0x7200, 0x0118, 0x00de, 0x0804,
-       0x2df4, 0x6820, 0x6924, 0x080c, 0x2676, 0x1510, 0x080c, 0x4c80,
-       0x11f8, 0x7122, 0x6612, 0x6516, 0x6e18, 0x00c6, 0x080c, 0x3c05,
-       0x01b8, 0x080c, 0x3c05, 0x01a0, 0x00ce, 0x00de, 0x6837, 0x0000,
-       0x6838, 0xc0fd, 0x683a, 0x6823, 0x0000, 0x6804, 0x2068, 0x080c,
-       0x96ef, 0x0904, 0x2df1, 0x7007, 0x0003, 0x701b, 0x3f4b, 0x0005,
-       0x00de, 0x0804, 0x2df1, 0x7120, 0x080c, 0x2bc9, 0x6820, 0xa086,
-       0x8001, 0x0904, 0x2df1, 0x2d00, 0x701e, 0x6804, 0xa080, 0x0002,
-       0x0006, 0x20a9, 0x002a, 0x2098, 0x20a0, 0x080c, 0x48be, 0x000e,
-       0xade8, 0x000d, 0x6a08, 0x6b0c, 0x6c10, 0x6d14, 0x2061, 0xadd1,
-       0x6007, 0x0000, 0x6e00, 0x6f28, 0xa7c6, 0x7000, 0x1108, 0x0018,
-       0xa7c6, 0x7100, 0x1140, 0xa6c2, 0x0004, 0x0a04, 0x2df4, 0x2009,
-       0x0004, 0x0804, 0x3c49, 0xa7c6, 0x7200, 0x1904, 0x2df4, 0xa6c2,
-       0x0054, 0x0a04, 0x2df4, 0x600e, 0x6013, 0x002a, 0x6226, 0x632a,
-       0x642e, 0x6532, 0x2c10, 0x080c, 0x1624, 0x7007, 0x0002, 0x701b,
-       0x3f92, 0x0005, 0x701c, 0x2068, 0x6804, 0xa080, 0x0001, 0x2004,
-       0xa080, 0x0002, 0x0006, 0x20a9, 0x002a, 0x2098, 0x20a0, 0x080c,
-       0x48be, 0x000e, 0x2009, 0x002a, 0x2061, 0xadd1, 0x6224, 0x6328,
-       0x642c, 0x6530, 0x0804, 0x3c49, 0x81ff, 0x1904, 0x2df1, 0x080c,
-       0x3c1a, 0x0904, 0x2df4, 0x080c, 0x4d96, 0x0904, 0x2df1, 0x080c,
-       0x4ec6, 0x0804, 0x2dcc, 0x7824, 0xd084, 0x0904, 0x3804, 0x080c,
-       0x3c2a, 0x0904, 0x2df4, 0x00c6, 0x080c, 0x3c05, 0x00ce, 0x1120,
-       0x2009, 0x0002, 0x0804, 0x2df1, 0x6004, 0xa084, 0x00ff, 0xa086,
-       0x0006, 0x0128, 0xa08e, 0x0004, 0x0110, 0xa08e, 0x0005, 0x1508,
-       0x2001, 0xad52, 0x2004, 0xd0b4, 0x0904, 0x3834, 0x6000, 0xd08c,
-       0x1904, 0x3834, 0x6837, 0x0000, 0x6838, 0xc0fd, 0x683a, 0x080c,
-       0x970b, 0x1120, 0x2009, 0x0003, 0x0804, 0x2df1, 0x7007, 0x0003,
-       0x701b, 0x3ff3, 0x0005, 0x080c, 0x3c2a, 0x0904, 0x2df4, 0x0804,
-       0x3834, 0x2009, 0xad30, 0x210c, 0x81ff, 0x0120, 0x2009, 0x0001,
-       0x0804, 0x2df1, 0x2001, 0xad00, 0x2004, 0xa086, 0x0003, 0x0120,
-       0x2009, 0x0007, 0x0804, 0x2df1, 0x2001, 0xad52, 0x2004, 0xd0ac,
-       0x0120, 0x2009, 0x0008, 0x0804, 0x2df1, 0x609c, 0xd0a4, 0x1118,
-       0xd0ac, 0x1904, 0x3834, 0x6837, 0x0000, 0x6833, 0x0000, 0x6838,
-       0xc0fd, 0x683a, 0x080c, 0x979c, 0x1120, 0x2009, 0x0003, 0x0804,
-       0x2df1, 0x7007, 0x0003, 0x701b, 0x402e, 0x0005, 0x6830, 0xa086,
-       0x0100, 0x1120, 0x2009, 0x0004, 0x0804, 0x2df1, 0x080c, 0x3c2a,
-       0x0904, 0x2df4, 0x0804, 0x3fd8, 0x81ff, 0x2009, 0x0001, 0x1904,
-       0x2df1, 0x6000, 0xa086, 0x0003, 0x2009, 0x0007, 0x1904, 0x2df1,
-       0x2001, 0xad52, 0x2004, 0xd0ac, 0x2009, 0x0008, 0x1904, 0x2df1,
-       0x080c, 0x3c2a, 0x0904, 0x2df4, 0x6004, 0xa084, 0x00ff, 0xa086,
-       0x0006, 0x2009, 0x0009, 0x1904, 0x2df1, 0x00c6, 0x080c, 0x3c05,
-       0x00ce, 0x2009, 0x0002, 0x0904, 0x2df1, 0x6837, 0x0000, 0x6833,
-       0x0000, 0x6838, 0xc0fd, 0x683a, 0x7928, 0xa194, 0xff00, 0xa18c,
-       0x00ff, 0xa006, 0x82ff, 0x1128, 0xc0ed, 0x6952, 0x792c, 0x6956,
-       0x0048, 0xa28e, 0x0100, 0x1904, 0x2df4, 0xc0e5, 0x6853, 0x0000,
-       0x6857, 0x0000, 0x683e, 0x080c, 0x9957, 0x2009, 0x0003, 0x0904,
-       0x2df1, 0x7007, 0x0003, 0x701b, 0x408e, 0x0005, 0x6830, 0xa086,
-       0x0100, 0x2009, 0x0004, 0x0904, 0x2df1, 0x0804, 0x2dcc, 0x81ff,
-       0x2009, 0x0001, 0x1904, 0x2df1, 0x6000, 0xa086, 0x0003, 0x2009,
-       0x0007, 0x1904, 0x2df1, 0x080c, 0x3c2a, 0x0904, 0x2df4, 0x6004,
-       0xa084, 0x00ff, 0xa086, 0x0006, 0x2009, 0x0009, 0x1904, 0x2df1,
-       0x00c6, 0x080c, 0x3c05, 0x00ce, 0x2009, 0x0002, 0x0904, 0x2df1,
-       0xad80, 0x000f, 0x2009, 0x0008, 0x7a2c, 0x7b28, 0x7c3c, 0x7d38,
-       0x080c, 0x3c46, 0x701b, 0x40c5, 0x0005, 0x00d6, 0xade8, 0x000f,
-       0x6800, 0xa086, 0x0500, 0x1140, 0x6804, 0xa005, 0x1128, 0x6808,
-       0xa084, 0xff00, 0x1108, 0x0018, 0x00de, 0x1904, 0x2df4, 0x00de,
-       0x6837, 0x0000, 0x6833, 0x0000, 0x6838, 0xc0fd, 0x683a, 0x00c6,
-       0x080c, 0x3c2a, 0x1118, 0x00ce, 0x0804, 0x2df4, 0x080c, 0x99a6,
-       0x2009, 0x0003, 0x00ce, 0x0904, 0x2df1, 0x7007, 0x0003, 0x701b,
-       0x40f2, 0x0005, 0x6830, 0xa086, 0x0100, 0x2009, 0x0004, 0x0904,
-       0x2df1, 0x0804, 0x2dcc, 0x81ff, 0x0120, 0x2009, 0x0001, 0x0804,
-       0x2df1, 0x6000, 0xa086, 0x0003, 0x0120, 0x2009, 0x0007, 0x0804,
-       0x2df1, 0x7e24, 0x860f, 0xa18c, 0x00ff, 0xa6b4, 0x00ff, 0x080c,
-       0x4cdc, 0x1904, 0x2df4, 0xa186, 0x007f, 0x0150, 0x6004, 0xa084,
-       0x00ff, 0xa086, 0x0006, 0x0120, 0x2009, 0x0009, 0x0804, 0x2df1,
-       0x00c6, 0x080c, 0x3c05, 0x00ce, 0x1120, 0x2009, 0x0002, 0x0804,
-       0x2df1, 0x6837, 0x0000, 0x6838, 0xc0fd, 0x683a, 0x080c, 0x9726,
-       0x1120, 0x2009, 0x0003, 0x0804, 0x2df1, 0x7007, 0x0003, 0x701b,
-       0x413a, 0x0005, 0x6808, 0x8007, 0xa086, 0x0100, 0x1120, 0x2009,
-       0x0004, 0x0804, 0x2df1, 0x68b0, 0x6836, 0x6810, 0x8007, 0xa084,
-       0x00ff, 0x808e, 0x6814, 0x8007, 0xa084, 0x00ff, 0x8086, 0xa080,
-       0x0002, 0xa108, 0xad80, 0x0004, 0x7a2c, 0x7b28, 0x7c3c, 0x7d38,
-       0x0804, 0x3c49, 0x080c, 0x3c05, 0x1120, 0x2009, 0x0002, 0x0804,
-       0x2df1, 0x7924, 0xa194, 0xff00, 0xa18c, 0x00ff, 0x8217, 0x82ff,
-       0x0110, 0x0804, 0x2df4, 0x2009, 0x001a, 0x7a2c, 0x7b28, 0x7c3c,
-       0x7d38, 0x080c, 0x3c46, 0x701b, 0x4176, 0x0005, 0xad80, 0x000d,
-       0x2098, 0x20a9, 0x001a, 0x20a1, 0xafad, 0x53a3, 0x0804, 0x2dcc,
-       0x080c, 0x3c05, 0x1120, 0x2009, 0x0002, 0x0804, 0x2df1, 0x7924,
-       0xa194, 0xff00, 0xa18c, 0x00ff, 0x8217, 0x82ff, 0x0110, 0x0804,
-       0x2df4, 0x2099, 0xafad, 0x20a0, 0x20a9, 0x001a, 0x53a3, 0x2009,
-       0x001a, 0x7a2c, 0x7b28, 0x7c3c, 0x7d38, 0x0804, 0x3c49, 0x7824,
-       0xa08a, 0x1000, 0x1a04, 0x2df4, 0x0126, 0x2091, 0x8000, 0x8003,
-       0x800b, 0x810b, 0xa108, 0x00c6, 0x2061, 0xafda, 0x6142, 0x00ce,
-       0x012e, 0x0804, 0x2dcc, 0x00c6, 0x080c, 0x574f, 0x1188, 0x2001,
-       0xaf9e, 0x2003, 0x0001, 0x2001, 0xad00, 0x2003, 0x0001, 0xa085,
-       0x0001, 0x080c, 0x5793, 0x080c, 0x569a, 0x080c, 0x14f6, 0x0038,
-       0x2061, 0xad00, 0x6030, 0xc09d, 0x6032, 0x080c, 0x485e, 0x00ce,
-       0x0005, 0x0126, 0x00c6, 0x00e6, 0x2061, 0x0100, 0x2071, 0xad00,
-       0x6044, 0xd0a4, 0x11b0, 0xd084, 0x0118, 0x080c, 0x4348, 0x0068,
-       0xd08c, 0x0118, 0x080c, 0x4269, 0x0040, 0xd094, 0x0118, 0x080c,
-       0x423a, 0x0018, 0xd09c, 0x0108, 0x0061, 0x00ee, 0x00ce, 0x012e,
-       0x0005, 0x0016, 0x6128, 0xd19c, 0x1110, 0xc19d, 0x612a, 0x001e,
-       0x0ca0, 0x624c, 0xa286, 0xf0f0, 0x1150, 0x6048, 0xa086, 0xf0f0,
-       0x0130, 0x624a, 0x6043, 0x0090, 0x6043, 0x0010, 0x0490, 0xa294,
-       0xff00, 0xa296, 0xf700, 0x0178, 0x7134, 0xd1a4, 0x1160, 0x6240,
-       0xa295, 0x0100, 0x6242, 0xa294, 0x0010, 0x0128, 0x2009, 0x00f7,
-       0x080c, 0x48de, 0x00f0, 0x6040, 0xa084, 0x0010, 0xa085, 0x0040,
-       0x6042, 0x6043, 0x0000, 0x7077, 0x0000, 0x7093, 0x0001, 0x70b7,
-       0x0000, 0x70d3, 0x0000, 0x2009, 0xb3c0, 0x200b, 0x0000, 0x7087,
-       0x0000, 0x707b, 0x000a, 0x2009, 0x000a, 0x2011, 0x4814, 0x080c,
-       0x6593, 0x0005, 0x0156, 0x2001, 0xad73, 0x2004, 0xd08c, 0x0110,
-       0x704f, 0xffff, 0x7078, 0xa005, 0x1510, 0x2011, 0x4814, 0x080c,
-       0x650d, 0x6040, 0xa094, 0x0010, 0xa285, 0x0020, 0x6042, 0x20a9,
-       0x00c8, 0x6044, 0xd08c, 0x1168, 0x1f04, 0x4251, 0x6242, 0x708b,
-       0x0000, 0x6040, 0xa094, 0x0010, 0xa285, 0x0080, 0x6042, 0x6242,
-       0x0030, 0x6242, 0x708b, 0x0000, 0x707f, 0x0000, 0x0000, 0x015e,
-       0x0005, 0x707c, 0xa08a, 0x0003, 0x1210, 0x0023, 0x0010, 0x080c,
-       0x14f6, 0x0005, 0x4275, 0x42c5, 0x4347, 0x00f6, 0x707f, 0x0001,
-       0x20e1, 0xa000, 0xe000, 0x20e1, 0x8700, 0x080c, 0x22f8, 0x20e1,
-       0x9080, 0x20e1, 0x4000, 0x2079, 0xb200, 0x207b, 0x2200, 0x7807,
-       0x00ef, 0x780b, 0x0000, 0x780f, 0x00ef, 0x7813, 0x0138, 0x7817,
-       0x0000, 0x781b, 0x0000, 0x781f, 0x0000, 0x7823, 0xffff, 0x7827,
-       0xffff, 0x782b, 0x0000, 0x782f, 0x0000, 0x2079, 0xb20c, 0x207b,
-       0x1101, 0x7807, 0x0000, 0x2099, 0xad05, 0x20a1, 0xb20e, 0x20a9,
-       0x0004, 0x53a3, 0x2079, 0xb212, 0x207b, 0x0000, 0x7807, 0x0000,
-       0x2099, 0xb200, 0x20a1, 0x020b, 0x20a9, 0x0014, 0x53a6, 0x60c3,
-       0x000c, 0x600f, 0x0000, 0x080c, 0x4845, 0x00fe, 0x7083, 0x0000,
-       0x6043, 0x0008, 0x6043, 0x0000, 0x0005, 0x00d6, 0x7080, 0x7083,
-       0x0000, 0xa025, 0x0904, 0x432f, 0x6020, 0xd0b4, 0x1904, 0x432d,
-       0x7190, 0x81ff, 0x0904, 0x431d, 0xa486, 0x000c, 0x1904, 0x4328,
-       0xa480, 0x0018, 0x8004, 0x20a8, 0x2011, 0xb280, 0x2019, 0xb200,
-       0x220c, 0x2304, 0xa106, 0x11b8, 0x8210, 0x8318, 0x1f04, 0x42e0,
-       0x6043, 0x0004, 0x608b, 0xbc94, 0x608f, 0xf0f0, 0x6043, 0x0006,
-       0x707f, 0x0002, 0x708b, 0x0002, 0x2009, 0x07d0, 0x2011, 0x481b,
-       0x080c, 0x6593, 0x0490, 0x2069, 0xb280, 0x6930, 0xa18e, 0x1101,
-       0x1538, 0x6834, 0xa005, 0x1520, 0x6900, 0xa18c, 0x00ff, 0x1118,
-       0x6804, 0xa005, 0x0190, 0x2011, 0xb28e, 0x2019, 0xad05, 0x20a9,
-       0x0004, 0x220c, 0x2304, 0xa102, 0x0230, 0x1190, 0x8210, 0x8318,
-       0x1f04, 0x4311, 0x0068, 0x7093, 0x0000, 0x20e1, 0x9080, 0x20e1,
-       0x4000, 0x2099, 0xb280, 0x20a1, 0x020b, 0x20a9, 0x0014, 0x53a6,
-       0x6043, 0x0008, 0x6043, 0x0000, 0x0010, 0x00de, 0x0005, 0x6040,
-       0xa085, 0x0100, 0x6042, 0x6020, 0xd0b4, 0x1db8, 0x60c3, 0x000c,
-       0x2011, 0xafd1, 0x2013, 0x0000, 0x7083, 0x0000, 0x20e1, 0x9080,
-       0x60a3, 0x0056, 0x60a7, 0x9575, 0x080c, 0x782b, 0x0c30, 0x0005,
-       0x7088, 0xa08a, 0x001d, 0x1210, 0x0023, 0x0010, 0x080c, 0x14f6,
-       0x0005, 0x437b, 0x438a, 0x43b2, 0x43cb, 0x43ef, 0x4417, 0x443b,
-       0x446c, 0x4490, 0x44b8, 0x44ef, 0x4517, 0x4533, 0x4549, 0x4569,
-       0x457c, 0x4584, 0x45b1, 0x45d5, 0x45fd, 0x4621, 0x4652, 0x468f,
-       0x46be, 0x46da, 0x4719, 0x4739, 0x4752, 0x4753, 0x00c6, 0x2061,
-       0xad00, 0x6003, 0x0007, 0x2061, 0x0100, 0x6004, 0xa084, 0xfff9,
-       0x6006, 0x00ce, 0x0005, 0x608b, 0xbc94, 0x608f, 0xf0f0, 0x6043,
-       0x0002, 0x708b, 0x0001, 0x2009, 0x07d0, 0x2011, 0x481b, 0x080c,
-       0x6593, 0x0005, 0x00f6, 0x7080, 0xa086, 0x0014, 0x1508, 0x6043,
-       0x0000, 0x6020, 0xd0b4, 0x11e0, 0x2079, 0xb280, 0x7a30, 0xa296,
-       0x1102, 0x11a0, 0x7834, 0xa005, 0x1188, 0x7a38, 0xd2fc, 0x0128,
-       0x70b4, 0xa005, 0x1110, 0x70b7, 0x0001, 0x2011, 0x481b, 0x080c,
-       0x650d, 0x708b, 0x0010, 0x080c, 0x4584, 0x0010, 0x080c, 0x485e,
-       0x00fe, 0x0005, 0x708b, 0x0003, 0x6043, 0x0004, 0x2011, 0x481b,
-       0x080c, 0x650d, 0x080c, 0x48c6, 0x20a3, 0x1102, 0x20a3, 0x0000,
-       0x20a9, 0x000a, 0x20a3, 0x0000, 0x1f04, 0x43c2, 0x60c3, 0x0014,
-       0x080c, 0x4845, 0x0005, 0x00f6, 0x7080, 0xa005, 0x01f0, 0x2011,
-       0x481b, 0x080c, 0x650d, 0xa086, 0x0014, 0x11a8, 0x2079, 0xb280,
-       0x7a30, 0xa296, 0x1102, 0x1178, 0x7834, 0xa005, 0x1160, 0x7a38,
-       0xd2fc, 0x0128, 0x70b4, 0xa005, 0x1110, 0x70b7, 0x0001, 0x708b,
-       0x0004, 0x0029, 0x0010, 0x080c, 0x485e, 0x00fe, 0x0005, 0x708b,
-       0x0005, 0x080c, 0x48c6, 0x20a3, 0x1103, 0x20a3, 0x0000, 0x3430,
-       0x2011, 0xb28e, 0x080c, 0x4917, 0x1160, 0x7074, 0xa005, 0x1148,
-       0x714c, 0xa186, 0xffff, 0x0128, 0x080c, 0x47df, 0x0110, 0x080c,
-       0x48f5, 0x20a9, 0x0008, 0x2298, 0x26a0, 0x53a6, 0x20a3, 0x0000,
-       0x20a3, 0x0000, 0x60c3, 0x0014, 0x080c, 0x4845, 0x0005, 0x00f6,
-       0x7080, 0xa005, 0x01f0, 0x2011, 0x481b, 0x080c, 0x650d, 0xa086,
-       0x0014, 0x11a8, 0x2079, 0xb280, 0x7a30, 0xa296, 0x1103, 0x1178,
-       0x7834, 0xa005, 0x1160, 0x7a38, 0xd2fc, 0x0128, 0x70b4, 0xa005,
-       0x1110, 0x70b7, 0x0001, 0x708b, 0x0006, 0x0029, 0x0010, 0x080c,
-       0x485e, 0x00fe, 0x0005, 0x708b, 0x0007, 0x080c, 0x48c6, 0x20a3,
-       0x1104, 0x20a3, 0x0000, 0x3430, 0x2011, 0xb28e, 0x080c, 0x4917,
-       0x11a8, 0x7074, 0xa005, 0x1190, 0x7154, 0xa186, 0xffff, 0x0170,
-       0xa180, 0x2be6, 0x200d, 0xa18c, 0xff00, 0x810f, 0x080c, 0x47df,
-       0x0128, 0x080c, 0x3e66, 0x0110, 0x080c, 0x26c0, 0x20a9, 0x0008,
-       0x2298, 0x26a0, 0x53a6, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x60c3,
-       0x0014, 0x080c, 0x4845, 0x0005, 0x00f6, 0x7080, 0xa005, 0x01f0,
-       0x2011, 0x481b, 0x080c, 0x650d, 0xa086, 0x0014, 0x11a8, 0x2079,
-       0xb280, 0x7a30, 0xa296, 0x1104, 0x1178, 0x7834, 0xa005, 0x1160,
-       0x7a38, 0xd2fc, 0x0128, 0x70b4, 0xa005, 0x1110, 0x70b7, 0x0001,
-       0x708b, 0x0008, 0x0029, 0x0010, 0x080c, 0x485e, 0x00fe, 0x0005,
-       0x708b, 0x0009, 0x080c, 0x48c6, 0x20a3, 0x1105, 0x20a3, 0x0100,
-       0x3430, 0x080c, 0x4917, 0x1150, 0x7074, 0xa005, 0x1138, 0x080c,
-       0x4754, 0x1170, 0xa085, 0x0001, 0x080c, 0x26c0, 0x20a9, 0x0008,
-       0x2099, 0xb28e, 0x26a0, 0x53a6, 0x20a3, 0x0000, 0x20a3, 0x0000,
-       0x60c3, 0x0014, 0x080c, 0x4845, 0x0010, 0x080c, 0x436e, 0x0005,
-       0x00f6, 0x7080, 0xa005, 0x0588, 0x2011, 0x481b, 0x080c, 0x650d,
-       0xa086, 0x0014, 0x1540, 0x2079, 0xb280, 0x7a30, 0xa296, 0x1105,
-       0x1510, 0x7834, 0x2011, 0x0100, 0xa21e, 0x1160, 0x7a38, 0xd2fc,
-       0x0128, 0x70b4, 0xa005, 0x1110, 0x70b7, 0x0001, 0x708b, 0x000a,
-       0x00b1, 0x0098, 0xa005, 0x1178, 0x7a38, 0xd2fc, 0x0128, 0x70b4,
-       0xa005, 0x1110, 0x70b7, 0x0001, 0x7087, 0x0000, 0x708b, 0x000e,
-       0x080c, 0x4569, 0x0010, 0x080c, 0x485e, 0x00fe, 0x0005, 0x708b,
-       0x000b, 0x2011, 0xb20e, 0x22a0, 0x20a9, 0x0040, 0x2019, 0xffff,
-       0x43a4, 0x20a9, 0x0002, 0x2009, 0x0000, 0x41a4, 0x080c, 0x48c6,
-       0x20a3, 0x1106, 0x20a3, 0x0000, 0x080c, 0x4917, 0x0118, 0x2013,
-       0x0000, 0x0020, 0x7050, 0xa085, 0x0100, 0x2012, 0x2298, 0x20a9,
-       0x0042, 0x53a6, 0x60c3, 0x0084, 0x080c, 0x4845, 0x0005, 0x00f6,
-       0x7080, 0xa005, 0x01b0, 0x2011, 0x481b, 0x080c, 0x650d, 0xa086,
-       0x0084, 0x1168, 0x2079, 0xb280, 0x7a30, 0xa296, 0x1106, 0x1138,
-       0x7834, 0xa005, 0x1120, 0x708b, 0x000c, 0x0029, 0x0010, 0x080c,
-       0x485e, 0x00fe, 0x0005, 0x708b, 0x000d, 0x080c, 0x48c6, 0x20a3,
-       0x1107, 0x20a3, 0x0000, 0x2099, 0xb28e, 0x20a9, 0x0040, 0x53a6,
-       0x20a3, 0x0000, 0x20a3, 0x0000, 0x60c3, 0x0084, 0x080c, 0x4845,
-       0x0005, 0x00f6, 0x7080, 0xa005, 0x01d0, 0x2011, 0x481b, 0x080c,
-       0x650d, 0xa086, 0x0084, 0x1188, 0x2079, 0xb280, 0x7a30, 0xa296,
-       0x1107, 0x1158, 0x7834, 0xa005, 0x1140, 0x7087, 0x0001, 0x080c,
-       0x48b8, 0x708b, 0x000e, 0x0029, 0x0010, 0x080c, 0x485e, 0x00fe,
-       0x0005, 0x708b, 0x000f, 0x7083, 0x0000, 0x608b, 0xbc85, 0x608f,
-       0xb5b5, 0x6043, 0x0005, 0x6043, 0x0004, 0x2009, 0x07d0, 0x2011,
-       0x481b, 0x080c, 0x6501, 0x0005, 0x7080, 0xa005, 0x0120, 0x2011,
-       0x481b, 0x080c, 0x650d, 0x0005, 0x708b, 0x0011, 0x080c, 0x4917,
-       0x1188, 0x716c, 0x81ff, 0x0170, 0x2009, 0x0000, 0x7070, 0xa084,
-       0x00ff, 0x080c, 0x2676, 0xa186, 0x0080, 0x0120, 0x2011, 0xb28e,
-       0x080c, 0x47df, 0x20e1, 0x9080, 0x20e1, 0x4000, 0x2099, 0xb280,
-       0x20a1, 0x020b, 0x7480, 0xa480, 0x0018, 0xa080, 0x0007, 0xa084,
-       0x03f8, 0x8004, 0x20a8, 0x53a6, 0x60c3, 0x0014, 0x080c, 0x4845,
-       0x0005, 0x00f6, 0x7080, 0xa005, 0x01f0, 0x2011, 0x481b, 0x080c,
-       0x650d, 0xa086, 0x0014, 0x11a8, 0x2079, 0xb280, 0x7a30, 0xa296,
-       0x1103, 0x1178, 0x7834, 0xa005, 0x1160, 0x7a38, 0xd2fc, 0x0128,
-       0x70b4, 0xa005, 0x1110, 0x70b7, 0x0001, 0x708b, 0x0012, 0x0029,
-       0x0010, 0x080c, 0x485e, 0x00fe, 0x0005, 0x708b, 0x0013, 0x080c,
-       0x48d2, 0x20a3, 0x1103, 0x20a3, 0x0000, 0x3430, 0x2011, 0xb28e,
-       0x080c, 0x4917, 0x1160, 0x7074, 0xa005, 0x1148, 0x714c, 0xa186,
-       0xffff, 0x0128, 0x080c, 0x47df, 0x0110, 0x080c, 0x48f5, 0x20a9,
-       0x0008, 0x2298, 0x26a0, 0x53a6, 0x20a3, 0x0000, 0x20a3, 0x0000,
-       0x60c3, 0x0014, 0x080c, 0x4845, 0x0005, 0x00f6, 0x7080, 0xa005,
-       0x01f0, 0x2011, 0x481b, 0x080c, 0x650d, 0xa086, 0x0014, 0x11a8,
-       0x2079, 0xb280, 0x7a30, 0xa296, 0x1104, 0x1178, 0x7834, 0xa005,
-       0x1160, 0x7a38, 0xd2fc, 0x0128, 0x70b4, 0xa005, 0x1110, 0x70b7,
-       0x0001, 0x708b, 0x0014, 0x0029, 0x0010, 0x080c, 0x485e, 0x00fe,
-       0x0005, 0x708b, 0x0015, 0x080c, 0x48d2, 0x20a3, 0x1104, 0x20a3,
-       0x0000, 0x3430, 0x2011, 0xb28e, 0x080c, 0x4917, 0x11a8, 0x7074,
-       0xa005, 0x1190, 0x7154, 0xa186, 0xffff, 0x0170, 0xa180, 0x2be6,
-       0x200d, 0xa18c, 0xff00, 0x810f, 0x080c, 0x47df, 0x0128, 0x080c,
-       0x3e66, 0x0110, 0x080c, 0x26c0, 0x20a9, 0x0008, 0x2298, 0x26a0,
-       0x53a6, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x60c3, 0x0014, 0x080c,
-       0x4845, 0x0005, 0x00f6, 0x7080, 0xa005, 0x05b8, 0x2011, 0x481b,
-       0x080c, 0x650d, 0xa086, 0x0014, 0x1570, 0x2079, 0xb280, 0x7a30,
-       0xa296, 0x1105, 0x1540, 0x7834, 0x2011, 0x0100, 0xa21e, 0x1148,
-       0x7a38, 0xd2fc, 0x0128, 0x70b4, 0xa005, 0x1110, 0x70b7, 0x0001,
-       0x0060, 0xa005, 0x11c0, 0x7a38, 0xd2fc, 0x0128, 0x70b4, 0xa005,
-       0x1110, 0x70b7, 0x0001, 0x7087, 0x0000, 0x7a38, 0xd2f4, 0x0138,
-       0x2001, 0xad73, 0x2004, 0xd0a4, 0x1110, 0x70d3, 0x0008, 0x708b,
-       0x0016, 0x0029, 0x0010, 0x080c, 0x485e, 0x00fe, 0x0005, 0x20e1,
-       0x9080, 0x20e1, 0x4000, 0x2099, 0xb280, 0x20a1, 0x020b, 0x20a9,
-       0x000e, 0x53a6, 0x3430, 0x2011, 0xb28e, 0x708b, 0x0017, 0x080c,
-       0x4917, 0x1150, 0x7074, 0xa005, 0x1138, 0x080c, 0x4754, 0x1170,
-       0xa085, 0x0001, 0x080c, 0x26c0, 0x20a9, 0x0008, 0x2099, 0xb28e,
-       0x26a0, 0x53a6, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x60c3, 0x0014,
-       0x080c, 0x4845, 0x0010, 0x080c, 0x436e, 0x0005, 0x00f6, 0x7080,
-       0xa005, 0x01b0, 0x2011, 0x481b, 0x080c, 0x650d, 0xa086, 0x0084,
-       0x1168, 0x2079, 0xb280, 0x7a30, 0xa296, 0x1106, 0x1138, 0x7834,
-       0xa005, 0x1120, 0x708b, 0x0018, 0x0029, 0x0010, 0x080c, 0x485e,
-       0x00fe, 0x0005, 0x708b, 0x0019, 0x080c, 0x48d2, 0x20a3, 0x1106,
-       0x20a3, 0x0000, 0x3430, 0x2099, 0xb28e, 0x2039, 0xb20e, 0x27a0,
-       0x20a9, 0x0040, 0x53a3, 0x080c, 0x4917, 0x11e8, 0x2728, 0x2514,
-       0x8207, 0xa084, 0x00ff, 0x8000, 0x2018, 0xa294, 0x00ff, 0x8007,
-       0xa205, 0x202a, 0x7050, 0x2310, 0x8214, 0xa2a0, 0xb20e, 0x2414,
-       0xa38c, 0x0001, 0x0118, 0xa294, 0xff00, 0x0018, 0xa294, 0x00ff,
-       0x8007, 0xa215, 0x2222, 0x2798, 0x26a0, 0x20a9, 0x0040, 0x53a6,
-       0x20a3, 0x0000, 0x20a3, 0x0000, 0x60c3, 0x0084, 0x080c, 0x4845,
-       0x0005, 0x00f6, 0x7080, 0xa005, 0x01d0, 0x2011, 0x481b, 0x080c,
-       0x650d, 0xa086, 0x0084, 0x1188, 0x2079, 0xb280, 0x7a30, 0xa296,
-       0x1107, 0x1158, 0x7834, 0xa005, 0x1140, 0x7087, 0x0001, 0x080c,
-       0x48b8, 0x708b, 0x001a, 0x0029, 0x0010, 0x080c, 0x485e, 0x00fe,
-       0x0005, 0x708b, 0x001b, 0x20e1, 0x9080, 0x20e1, 0x4000, 0x2099,
-       0xb280, 0x20a1, 0x020b, 0x7480, 0xa480, 0x0018, 0xa080, 0x0007,
-       0xa084, 0x03f8, 0x8004, 0x20a8, 0x53a6, 0x60c3, 0x0084, 0x080c,
-       0x4845, 0x0005, 0x0005, 0x0005, 0x0086, 0x0096, 0x2029, 0xad52,
-       0x252c, 0x20a9, 0x0008, 0x2041, 0xb20e, 0x28a0, 0x2099, 0xb28e,
-       0x53a3, 0x20a9, 0x0008, 0x2011, 0x0007, 0xd5d4, 0x0110, 0x2011,
-       0x0000, 0x2800, 0xa200, 0x200c, 0xa1a6, 0xffff, 0x1148, 0xd5d4,
-       0x0110, 0x8210, 0x0008, 0x8211, 0x1f04, 0x4769, 0x0804, 0x47d7,
-       0x82ff, 0x1160, 0xd5d4, 0x0120, 0xa1a6, 0x3fff, 0x0d90, 0x0020,
-       0xa1a6, 0x3fff, 0x0904, 0x47d7, 0xa18d, 0xc000, 0x20a9, 0x0010,
-       0x2019, 0x0001, 0xd5d4, 0x0110, 0x2019, 0x0010, 0x2120, 0xd5d4,
-       0x0110, 0x8423, 0x0008, 0x8424, 0x1240, 0xd5d4, 0x0110, 0x8319,
-       0x0008, 0x8318, 0x1f04, 0x478f, 0x04d0, 0x23a8, 0x2021, 0x0001,
-       0x8426, 0x8425, 0x1f04, 0x47a1, 0x2328, 0x8529, 0xa2be, 0x0007,
-       0x0158, 0x0006, 0x2039, 0x0007, 0x2200, 0xa73a, 0x000e, 0x27a8,
-       0xa5a8, 0x0010, 0x1f04, 0x47b0, 0x754e, 0xa5c8, 0x2be6, 0x292d,
-       0xa5ac, 0x00ff, 0x7572, 0x6532, 0x6536, 0x0016, 0x2508, 0x080c,
-       0x26a0, 0x001e, 0x60e7, 0x0000, 0x65ea, 0x2018, 0x2304, 0xa405,
-       0x201a, 0x7077, 0x0001, 0x26a0, 0x2898, 0x20a9, 0x0008, 0x53a6,
-       0x20a3, 0x0000, 0x20a3, 0x0000, 0xa085, 0x0001, 0x0028, 0xa006,
-       0x0018, 0xa006, 0x080c, 0x14f6, 0x009e, 0x008e, 0x0005, 0x2118,
-       0x2021, 0x0000, 0x2001, 0x0007, 0xa39a, 0x0010, 0x0218, 0x8420,
-       0x8001, 0x0cd0, 0x2118, 0x84ff, 0x0120, 0xa39a, 0x0010, 0x8421,
-       0x1de0, 0x2021, 0x0001, 0x83ff, 0x0118, 0x8423, 0x8319, 0x1de8,
-       0xa238, 0x2704, 0xa42c, 0x11b8, 0xa405, 0x203a, 0x714e, 0xa1a0,
-       0x2be6, 0x242d, 0xa5ac, 0x00ff, 0x7572, 0x6532, 0x6536, 0x0016,
-       0x2508, 0x080c, 0x26a0, 0x001e, 0x60e7, 0x0000, 0x65ea, 0x7077,
-       0x0001, 0xa084, 0x0000, 0x0005, 0x00e6, 0x2071, 0xad00, 0x707b,
-       0x0000, 0x00ee, 0x0005, 0x00e6, 0x00f6, 0x2079, 0x0100, 0x2071,
-       0x0140, 0x080c, 0x7834, 0x7004, 0xa084, 0x4000, 0x0120, 0x7003,
-       0x1000, 0x7003, 0x0000, 0x0126, 0x2091, 0x8000, 0x2071, 0xad22,
-       0x2073, 0x0000, 0x7840, 0x0026, 0x0016, 0x2009, 0x00f7, 0x080c,
-       0x48de, 0x001e, 0xa094, 0x0010, 0xa285, 0x0080, 0x7842, 0x7a42,
-       0x002e, 0x012e, 0x00fe, 0x00ee, 0x0005, 0x0126, 0x2091, 0x8000,
-       0x2011, 0xafd1, 0x2013, 0x0000, 0x7083, 0x0000, 0x012e, 0x20e1,
-       0x9080, 0x60a3, 0x0056, 0x60a7, 0x9575, 0x080c, 0x782b, 0x2009,
-       0x07d0, 0x2011, 0x481b, 0x080c, 0x6593, 0x0005, 0x0016, 0x0026,
-       0x00c6, 0x0126, 0x2091, 0x8000, 0x2009, 0x00f7, 0x080c, 0x48de,
-       0x2061, 0xafda, 0x601b, 0x0000, 0x601f, 0x0000, 0x2061, 0xad00,
-       0x6003, 0x0001, 0x2061, 0x0100, 0x6043, 0x0090, 0x6043, 0x0010,
-       0x2009, 0x002d, 0x2011, 0x4883, 0x080c, 0x6501, 0x012e, 0x00ce,
-       0x002e, 0x001e, 0x0005, 0x00e6, 0x0006, 0x0126, 0x2091, 0x8000,
-       0x2071, 0x0100, 0x080c, 0x7834, 0x2071, 0x0140, 0x7004, 0xa084,
-       0x4000, 0x0120, 0x7003, 0x1000, 0x7003, 0x0000, 0x080c, 0x5757,
-       0x01a8, 0x080c, 0x5775, 0x1190, 0x2001, 0xaf9d, 0x2003, 0xaaaa,
-       0x0016, 0x080c, 0x2744, 0x2001, 0xaf8e, 0x2102, 0x001e, 0x2001,
-       0xaf9e, 0x2003, 0x0000, 0x080c, 0x569a, 0x0030, 0x2001, 0x0001,
-       0x080c, 0x261e, 0x080c, 0x485e, 0x012e, 0x000e, 0x00ee, 0x0005,
-       0x20a9, 0x0040, 0x20a1, 0xb3c0, 0x2099, 0xb28e, 0x3304, 0x8007,
-       0x20a2, 0x9398, 0x94a0, 0x1f04, 0x48be, 0x0005, 0x20e1, 0x9080,
-       0x20e1, 0x4000, 0x2099, 0xb200, 0x20a1, 0x020b, 0x20a9, 0x000c,
-       0x53a6, 0x0005, 0x20e1, 0x9080, 0x20e1, 0x4000, 0x2099, 0xb280,
-       0x20a1, 0x020b, 0x20a9, 0x000c, 0x53a6, 0x0005, 0x00c6, 0x0006,
-       0x2061, 0x0100, 0x810f, 0x2001, 0xad30, 0x2004, 0xa005, 0x1138,
-       0x2001, 0xad14, 0x2004, 0xa084, 0x00ff, 0xa105, 0x0010, 0xa185,
-       0x00f7, 0x604a, 0x000e, 0x00ce, 0x0005, 0x0016, 0x0046, 0x2001,
-       0xad52, 0x2004, 0xd0a4, 0x0158, 0xa006, 0x2020, 0x2009, 0x002a,
-       0x080c, 0xa96c, 0x2001, 0xad0c, 0x200c, 0xc195, 0x2102, 0x2019,
-       0x002a, 0x2009, 0x0000, 0x080c, 0x2aac, 0x004e, 0x001e, 0x0005,
-       0x080c, 0x485e, 0x708b, 0x0000, 0x7083, 0x0000, 0x0005, 0x0006,
-       0x2001, 0xad0c, 0x2004, 0xd09c, 0x0100, 0x000e, 0x0005, 0x0006,
-       0x0016, 0x0126, 0x2091, 0x8000, 0x2001, 0x0101, 0x200c, 0xa18d,
-       0x0006, 0x2102, 0x012e, 0x001e, 0x000e, 0x0005, 0x0156, 0x20a9,
-       0x00ff, 0x2009, 0xae34, 0xa006, 0x200a, 0x8108, 0x1f04, 0x4934,
-       0x015e, 0x0005, 0x00d6, 0x0036, 0x0156, 0x0136, 0x0146, 0x2069,
-       0xad51, 0xa006, 0x6002, 0x6007, 0x0707, 0x600a, 0x600e, 0x6012,
-       0xa198, 0x2be6, 0x231d, 0xa39c, 0x00ff, 0x6316, 0x20a9, 0x0004,
-       0xac98, 0x0006, 0x23a0, 0x40a4, 0x20a9, 0x0004, 0xac98, 0x000a,
-       0x23a0, 0x40a4, 0x603e, 0x6042, 0x604e, 0x6052, 0x6056, 0x605a,
-       0x605e, 0x6062, 0x6066, 0x606a, 0x606e, 0x6072, 0x6076, 0x607a,
-       0x607e, 0x6082, 0x6086, 0x608a, 0x608e, 0x6092, 0x6096, 0x609a,
-       0x609e, 0x60ae, 0x61a2, 0x00d6, 0x60a4, 0xa06d, 0x0110, 0x080c,
-       0x15f0, 0x60a7, 0x0000, 0x60a8, 0xa06d, 0x0110, 0x080c, 0x15f0,
-       0x60ab, 0x0000, 0x00de, 0xa006, 0x604a, 0x6810, 0x603a, 0x680c,
-       0x6046, 0x6814, 0xa084, 0x00ff, 0x6042, 0x014e, 0x013e, 0x015e,
-       0x003e, 0x00de, 0x0005, 0x0126, 0x2091, 0x8000, 0x6944, 0x6e48,
-       0xa684, 0x3fff, 0xa082, 0x4000, 0x1a04, 0x4a49, 0xa18c, 0xff00,
-       0x810f, 0xa182, 0x00ff, 0x1a04, 0x4a4e, 0x2001, 0xad0c, 0x2004,
-       0xa084, 0x0003, 0x01c0, 0x2001, 0xad0c, 0x2004, 0xd084, 0x1904,
-       0x4a31, 0xa188, 0xae34, 0x2104, 0xa065, 0x0904, 0x4a31, 0x6004,
-       0xa084, 0x00ff, 0xa08e, 0x0006, 0x1904, 0x4a31, 0x6000, 0xd0c4,
-       0x0904, 0x4a31, 0x0068, 0xa188, 0xae34, 0x2104, 0xa065, 0x0904,
-       0x4a15, 0x6004, 0xa084, 0x00ff, 0xa08e, 0x0006, 0x1904, 0x4a1a,
-       0x60a4, 0xa00d, 0x0118, 0x080c, 0x4ef9, 0x05d0, 0x60a8, 0xa00d,
-       0x0188, 0x080c, 0x4f43, 0x1170, 0x694c, 0xd1fc, 0x1118, 0x080c,
-       0x4c11, 0x0448, 0x080c, 0x4bd3, 0x694c, 0xd1ec, 0x1520, 0x080c,
-       0x4ded, 0x0408, 0x694c, 0xa184, 0xa000, 0x0178, 0xd1ec, 0x0140,
-       0xd1fc, 0x0118, 0x080c, 0x4dfc, 0x0028, 0x080c, 0x4dfc, 0x0028,
-       0xd1fc, 0x0118, 0x080c, 0x4bd3, 0x0070, 0x6050, 0xa00d, 0x0130,
-       0x2d00, 0x200a, 0x6803, 0x0000, 0x6052, 0x0028, 0x2d00, 0x6052,
-       0x604e, 0x6803, 0x0000, 0x080c, 0x67c5, 0xa006, 0x012e, 0x0005,
-       0x2001, 0x0005, 0x2009, 0x0000, 0x04e8, 0x2001, 0x0028, 0x2009,
-       0x0000, 0x04c0, 0xa082, 0x0006, 0x12a0, 0x2001, 0xad34, 0x2004,
-       0xd0ac, 0x1160, 0x60a0, 0xd0bc, 0x1148, 0x6100, 0xd1fc, 0x0904,
-       0x49d0, 0x2001, 0x0029, 0x2009, 0x1000, 0x0420, 0x2001, 0x0028,
-       0x00a8, 0x2009, 0xad0c, 0x210c, 0xd18c, 0x0118, 0x2001, 0x0004,
-       0x0068, 0xd184, 0x0118, 0x2001, 0x0004, 0x0040, 0x2001, 0x0029,
-       0x6100, 0xd1fc, 0x0118, 0x2009, 0x1000, 0x0060, 0x2009, 0x0000,
-       0x0048, 0x2001, 0x0029, 0x2009, 0x0000, 0x0020, 0x2001, 0x0029,
-       0x2009, 0x0000, 0xa005, 0x012e, 0x0005, 0x00e6, 0x0126, 0x2091,
-       0x8000, 0x6844, 0x8007, 0xa084, 0x00ff, 0x2008, 0xa182, 0x00ff,
-       0x1a04, 0x4aa8, 0xa188, 0xae34, 0x2104, 0xa065, 0x01c0, 0x6004,
-       0xa084, 0x00ff, 0xa08e, 0x0006, 0x11a8, 0x2c70, 0x080c, 0x8022,
-       0x05e8, 0x2e00, 0x601a, 0x2d00, 0x6012, 0x600b, 0xffff, 0x601f,
-       0x000a, 0x2009, 0x0003, 0x080c, 0x80a7, 0xa006, 0x0460, 0x2001,
-       0x0028, 0x0440, 0xa082, 0x0006, 0x1298, 0x2001, 0xad34, 0x2004,
-       0xd0ac, 0x1158, 0x60a0, 0xd0bc, 0x1140, 0x6100, 0xd1fc, 0x09e8,
-       0x2001, 0x0029, 0x2009, 0x1000, 0x00a8, 0x2001, 0x0028, 0x0090,
-       0x2009, 0xad0c, 0x210c, 0xd18c, 0x0118, 0x2001, 0x0004, 0x0050,
-       0xd184, 0x0118, 0x2001, 0x0004, 0x0028, 0x2001, 0x0029, 0x0010,
-       0x2001, 0x0029, 0xa005, 0x012e, 0x00ee, 0x0005, 0x2001, 0x002c,
-       0x0cc8, 0x00f6, 0x00e6, 0x0126, 0x2091, 0x8000, 0x2011, 0x0000,
-       0x2079, 0xad00, 0x6944, 0xa18c, 0xff00, 0x810f, 0xa182, 0x00ff,
-       0x1a04, 0x4b77, 0x2001, 0xad0c, 0x2004, 0xa084, 0x0003, 0x1904,
-       0x4b65, 0x080c, 0x4cdc, 0x1180, 0x6004, 0xa084, 0x00ff, 0xa082,
-       0x0006, 0x1250, 0x2001, 0xad34, 0x2004, 0xd0ac, 0x1904, 0x4b60,
-       0x60a0, 0xd0bc, 0x1904, 0x4b60, 0x6864, 0xa0c6, 0x006f, 0x0118,
-       0x2008, 0x0804, 0x4b28, 0x6968, 0x2140, 0xa18c, 0xff00, 0x810f,
-       0x78d0, 0xd0ac, 0x1118, 0xa182, 0x0080, 0x06d0, 0xa182, 0x00ff,
-       0x16b8, 0x6a70, 0x6b6c, 0x786c, 0xa306, 0x1160, 0x7870, 0xa24e,
-       0x1118, 0x2208, 0x2310, 0x0460, 0xa9cc, 0xff00, 0x1118, 0x2208,
-       0x2310, 0x0430, 0x080c, 0x3b58, 0x2c70, 0x0550, 0x2009, 0x0000,
-       0x2011, 0x0000, 0xa0c6, 0x4000, 0x1160, 0x0006, 0x2e60, 0x080c,
-       0x4f6e, 0x1108, 0xc185, 0x7000, 0xd0bc, 0x0108, 0xc18d, 0x000e,
-       0x0088, 0xa0c6, 0x4007, 0x1110, 0x2408, 0x0060, 0xa0c6, 0x4008,
-       0x1118, 0x2708, 0x2610, 0x0030, 0xa0c6, 0x4009, 0x1108, 0x0010,
-       0x2001, 0x4006, 0x6866, 0x696a, 0x6a6e, 0x2001, 0x0030, 0x0458,
-       0x080c, 0x8022, 0x1138, 0x2001, 0x4005, 0x2009, 0x0003, 0x2011,
-       0x0000, 0x0c80, 0x2e00, 0x601a, 0x080c, 0x9956, 0x2d00, 0x6012,
-       0x601f, 0x0001, 0xa006, 0xd88c, 0x0110, 0x2001, 0x4000, 0x683a,
-       0x0126, 0x2091, 0x8000, 0x080c, 0x2ad9, 0x012e, 0x2001, 0x0000,
-       0x080c, 0x4c1e, 0x2001, 0x0002, 0x080c, 0x4c30, 0x2009, 0x0002,
-       0x080c, 0x80a7, 0xa006, 0xa005, 0x012e, 0x00ee, 0x00fe, 0x0005,
-       0x2001, 0x0028, 0x2009, 0x0000, 0x0cb0, 0x2009, 0xad0c, 0x210c,
-       0xd18c, 0x0118, 0x2001, 0x0004, 0x0038, 0xd184, 0x0118, 0x2001,
-       0x0004, 0x0010, 0x2001, 0x0029, 0x2009, 0x0000, 0x0c20, 0x2001,
-       0x0029, 0x2009, 0x0000, 0x08f8, 0x6944, 0x6e48, 0xa684, 0x3fff,
-       0xa082, 0x4000, 0x16b8, 0xa18c, 0xff00, 0x810f, 0xa182, 0x00ff,
-       0x12e0, 0xa188, 0xae34, 0x2104, 0xa065, 0x01b8, 0x6004, 0xa084,
-       0x00ff, 0xa08e, 0x0006, 0x11b0, 0x684c, 0xd0ec, 0x0120, 0x080c,
-       0x4dfc, 0x04c9, 0x0030, 0x04b9, 0x684c, 0xd0fc, 0x0110, 0x080c,
-       0x4ded, 0x080c, 0x4e3a, 0xa006, 0x00c8, 0x2001, 0x0028, 0x2009,
-       0x0000, 0x00a0, 0xa082, 0x0006, 0x1240, 0x6100, 0xd1fc, 0x0d20,
-       0x2001, 0x0029, 0x2009, 0x1000, 0x0048, 0x2001, 0x0029, 0x2009,
-       0x0000, 0x0020, 0x2001, 0x0029, 0x2009, 0x0000, 0xa005, 0x0005,
-       0x0126, 0x2091, 0x8000, 0x6050, 0xa00d, 0x0138, 0x2d00, 0x200a,
-       0x6803, 0x0000, 0x6052, 0x012e, 0x0005, 0x2d00, 0x6052, 0x604e,
-       0x6803, 0x0000, 0x0cc0, 0x0126, 0x2091, 0x8000, 0x604c, 0xa005,
-       0x0170, 0x00e6, 0x2071, 0xafc7, 0x7004, 0xa086, 0x0002, 0x0168,
-       0x00ee, 0x604c, 0x6802, 0x2d00, 0x604e, 0x012e, 0x0005, 0x2d00,
-       0x6052, 0x604e, 0x6803, 0x0000, 0x0cc0, 0x701c, 0xac06, 0x1d80,
-       0x604c, 0x2070, 0x7000, 0x6802, 0x2d00, 0x7002, 0x00ee, 0x012e,
-       0x0005, 0x0126, 0x2091, 0x8000, 0x604c, 0xa06d, 0x0130, 0x6800,
-       0xa005, 0x1108, 0x6052, 0x604e, 0xad05, 0x012e, 0x0005, 0x604c,
-       0xa06d, 0x0130, 0x6800, 0xa005, 0x1108, 0x6052, 0x604e, 0xad05,
-       0x0005, 0x6803, 0x0000, 0x6084, 0xa00d, 0x0120, 0x2d00, 0x200a,
-       0x6086, 0x0005, 0x2d00, 0x6086, 0x6082, 0x0cd8, 0x0126, 0x00c6,
-       0x0026, 0x2091, 0x8000, 0x6218, 0x2260, 0x6200, 0xa005, 0x0110,
-       0xc285, 0x0008, 0xc284, 0x6202, 0x002e, 0x00ce, 0x012e, 0x0005,
-       0x0126, 0x00c6, 0x2091, 0x8000, 0x6218, 0x2260, 0x6204, 0x0006,
-       0xa086, 0x0006, 0x1180, 0x609c, 0xd0ac, 0x0168, 0x2001, 0xad52,
-       0x2004, 0xd0a4, 0x0140, 0xa284, 0xff00, 0x8007, 0xa086, 0x0007,
-       0x1110, 0x2011, 0x0600, 0x000e, 0xa294, 0xff00, 0xa215, 0x6206,
-       0x0006, 0xa086, 0x0006, 0x1128, 0x6290, 0x82ff, 0x1110, 0x080c,
-       0x14f6, 0x000e, 0x00ce, 0x012e, 0x0005, 0x0126, 0x00c6, 0x2091,
-       0x8000, 0x6218, 0x2260, 0x6204, 0x0006, 0xa086, 0x0006, 0x1178,
-       0x609c, 0xd0a4, 0x0160, 0x2001, 0xad52, 0x2004, 0xd0ac, 0x1138,
-       0xa284, 0x00ff, 0xa086, 0x0007, 0x1110, 0x2011, 0x0006, 0x000e,
-       0xa294, 0x00ff, 0x8007, 0xa215, 0x6206, 0x00ce, 0x012e, 0x0005,
-       0x0026, 0xa182, 0x00ff, 0x0218, 0xa085, 0x0001, 0x00b0, 0xa190,
-       0xae34, 0x2204, 0xa065, 0x1180, 0x0016, 0x00d6, 0x080c, 0x15c0,
-       0x2d60, 0x00de, 0x001e, 0x0d80, 0x2c00, 0x2012, 0x60a7, 0x0000,
-       0x60ab, 0x0000, 0x080c, 0x493a, 0xa006, 0x002e, 0x0005, 0x0126,
-       0x2091, 0x8000, 0x0026, 0xa182, 0x00ff, 0x0218, 0xa085, 0x0001,
-       0x0480, 0x00d6, 0xa190, 0xae34, 0x2204, 0xa06d, 0x0540, 0x2013,
-       0x0000, 0x00d6, 0x00c6, 0x2d60, 0x60a4, 0xa06d, 0x0110, 0x080c,
-       0x15f0, 0x60a8, 0xa06d, 0x0110, 0x080c, 0x15f0, 0x00ce, 0x00de,
-       0x00d6, 0x00c6, 0x68ac, 0x2060, 0x8cff, 0x0168, 0x600c, 0x0006,
-       0x6010, 0x2068, 0x080c, 0x9596, 0x0110, 0x080c, 0x1600, 0x080c,
-       0x8078, 0x00ce, 0x0c88, 0x00ce, 0x00de, 0x080c, 0x15f0, 0x00de,
-       0xa006, 0x002e, 0x012e, 0x0005, 0x0016, 0xa182, 0x00ff, 0x0218,
-       0xa085, 0x0001, 0x0030, 0xa188, 0xae34, 0x2104, 0xa065, 0x0dc0,
-       0xa006, 0x001e, 0x0005, 0x00d6, 0x0156, 0x0136, 0x0146, 0x600b,
-       0x0000, 0x600f, 0x0000, 0x6000, 0xc08c, 0x6002, 0x080c, 0x574f,
-       0x1538, 0x60a0, 0xa086, 0x007e, 0x2069, 0xb290, 0x0130, 0x2001,
-       0xad34, 0x2004, 0xd0ac, 0x11e0, 0x0098, 0x2d04, 0xd0e4, 0x01c0,
-       0x00d6, 0x2069, 0xb28e, 0x00c6, 0x2061, 0xaf9f, 0x6810, 0x2062,
-       0x6814, 0x6006, 0x6818, 0x600a, 0x681c, 0x600e, 0x00ce, 0x00de,
-       0x8d69, 0x2d04, 0x2069, 0x0140, 0x6886, 0x2069, 0xad00, 0x68a2,
-       0x2069, 0xb28e, 0x6808, 0x605e, 0x6810, 0x6062, 0x6138, 0xa10a,
-       0x0208, 0x603a, 0x6814, 0x6066, 0x2099, 0xb296, 0xac88, 0x000a,
-       0x21a0, 0x20a9, 0x0004, 0x53a3, 0x2099, 0xb29a, 0xac88, 0x0006,
-       0x21a0, 0x20a9, 0x0004, 0x53a3, 0x2069, 0xb2ae, 0x6808, 0x606a,
-       0x690c, 0x616e, 0x6810, 0x6072, 0x6818, 0x6076, 0xa182, 0x0211,
-       0x1218, 0x2009, 0x0008, 0x0400, 0xa182, 0x0259, 0x1218, 0x2009,
-       0x0007, 0x00d0, 0xa182, 0x02c1, 0x1218, 0x2009, 0x0006, 0x00a0,
-       0xa182, 0x0349, 0x1218, 0x2009, 0x0005, 0x0070, 0xa182, 0x0421,
-       0x1218, 0x2009, 0x0004, 0x0040, 0xa182, 0x0581, 0x1218, 0x2009,
-       0x0003, 0x0010, 0x2009, 0x0002, 0x6192, 0x014e, 0x013e, 0x015e,
-       0x00de, 0x0005, 0x0016, 0x0026, 0x00e6, 0x2071, 0xb28d, 0x2e04,
-       0x6896, 0x2071, 0xb28e, 0x7004, 0x689a, 0x701c, 0x689e, 0x6a00,
-       0x2009, 0xad71, 0x210c, 0xd0bc, 0x0120, 0xd1ec, 0x0110, 0xc2ad,
-       0x0008, 0xc2ac, 0xd0c4, 0x0120, 0xd1e4, 0x0110, 0xc2bd, 0x0008,
-       0xc2bc, 0x6a02, 0x00ee, 0x002e, 0x001e, 0x0005, 0x00d6, 0x0126,
-       0x2091, 0x8000, 0x60a4, 0xa06d, 0x01c0, 0x6900, 0x81ff, 0x1540,
-       0x6a04, 0xa282, 0x0010, 0x1648, 0xad88, 0x0004, 0x20a9, 0x0010,
-       0x2104, 0xa086, 0xffff, 0x0128, 0x8108, 0x1f04, 0x4da8, 0x080c,
-       0x14f6, 0x260a, 0x8210, 0x6a06, 0x0098, 0x080c, 0x15d9, 0x01a8,
-       0x2d00, 0x60a6, 0x6803, 0x0000, 0xad88, 0x0004, 0x20a9, 0x0010,
-       0x200b, 0xffff, 0x8108, 0x1f04, 0x4dc0, 0x6807, 0x0001, 0x6e12,
-       0xa085, 0x0001, 0x012e, 0x00de, 0x0005, 0xa006, 0x0cd8, 0x0126,
-       0x2091, 0x8000, 0x00d6, 0x60a4, 0xa00d, 0x01a0, 0x2168, 0x6800,
-       0xa005, 0x1160, 0x080c, 0x4ef9, 0x1168, 0x200b, 0xffff, 0x6804,
-       0xa08a, 0x0002, 0x0218, 0x8001, 0x6806, 0x0020, 0x080c, 0x15f0,
-       0x60a7, 0x0000, 0x00de, 0x012e, 0x0005, 0x0126, 0x2091, 0x8000,
-       0x080c, 0x4f56, 0x0010, 0x080c, 0x4bc0, 0x080c, 0x4e71, 0x1dd8,
-       0x080c, 0x4e3a, 0x012e, 0x0005, 0x00d6, 0x0126, 0x2091, 0x8000,
-       0x60a8, 0xa06d, 0x01c0, 0x6950, 0x81ff, 0x1540, 0x6a54, 0xa282,
-       0x0010, 0x1670, 0xad88, 0x0018, 0x20a9, 0x0010, 0x2104, 0xa086,
-       0xffff, 0x0128, 0x8108, 0x1f04, 0x4e0e, 0x080c, 0x14f6, 0x260a,
-       0x8210, 0x6a56, 0x0098, 0x080c, 0x15d9, 0x01d0, 0x2d00, 0x60aa,
-       0x6853, 0x0000, 0xad88, 0x0018, 0x20a9, 0x0010, 0x200b, 0xffff,
-       0x8108, 0x1f04, 0x4e26, 0x6857, 0x0001, 0x6e62, 0x0010, 0x080c,
-       0x4c11, 0x0089, 0x1de0, 0xa085, 0x0001, 0x012e, 0x00de, 0x0005,
-       0xa006, 0x0cd8, 0x0126, 0x2091, 0x8000, 0x080c, 0x67c5, 0x012e,
-       0x0005, 0xa01e, 0x0010, 0x2019, 0x0001, 0xa00e, 0x0126, 0x2091,
-       0x8000, 0x604c, 0x2068, 0x6000, 0xd0dc, 0x1170, 0x8dff, 0x01e8,
-       0x83ff, 0x0120, 0x6848, 0xa606, 0x0158, 0x0030, 0x683c, 0xa406,
-       0x1118, 0x6840, 0xa506, 0x0120, 0x2d08, 0x6800, 0x2068, 0x0c70,
-       0x6a00, 0x604c, 0xad06, 0x1110, 0x624e, 0x0018, 0xa180, 0x0000,
-       0x2202, 0x82ff, 0x1110, 0x6152, 0x8dff, 0x012e, 0x0005, 0xa01e,
-       0x0010, 0x2019, 0x0001, 0xa00e, 0x6080, 0x2068, 0x8dff, 0x01e8,
-       0x83ff, 0x0120, 0x6848, 0xa606, 0x0158, 0x0030, 0x683c, 0xa406,
-       0x1118, 0x6840, 0xa506, 0x0120, 0x2d08, 0x6800, 0x2068, 0x0c70,
-       0x6a00, 0x6080, 0xad06, 0x1110, 0x6282, 0x0018, 0xa180, 0x0000,
-       0x2202, 0x82ff, 0x1110, 0x6186, 0x8dff, 0x0005, 0xa016, 0x080c,
-       0x4ef3, 0x1110, 0x2011, 0x0001, 0x080c, 0x4f3d, 0x1110, 0xa295,
-       0x0002, 0x0005, 0x080c, 0x4f6e, 0x0118, 0x080c, 0x964b, 0x0010,
-       0xa085, 0x0001, 0x0005, 0x080c, 0x4f6e, 0x0118, 0x080c, 0x95e4,
-       0x0010, 0xa085, 0x0001, 0x0005, 0x080c, 0x4f6e, 0x0118, 0x080c,
-       0x962e, 0x0010, 0xa085, 0x0001, 0x0005, 0x080c, 0x4f6e, 0x0118,
-       0x080c, 0x9600, 0x0010, 0xa085, 0x0001, 0x0005, 0x080c, 0x4f6e,
-       0x0118, 0x080c, 0x9667, 0x0010, 0xa085, 0x0001, 0x0005, 0x0126,
-       0x0006, 0x00d6, 0x2091, 0x8000, 0x6080, 0xa06d, 0x01a0, 0x6800,
-       0x0006, 0x6837, 0x0103, 0x6b4a, 0x6847, 0x0000, 0x080c, 0x97fd,
-       0x0006, 0x6000, 0xd0fc, 0x0110, 0x080c, 0xac03, 0x000e, 0x080c,
-       0x510c, 0x000e, 0x0c50, 0x6083, 0x0000, 0x6087, 0x0000, 0x00de,
-       0x000e, 0x012e, 0x0005, 0x60a4, 0xa00d, 0x1118, 0xa085, 0x0001,
-       0x0005, 0x00e6, 0x2170, 0x7000, 0xa005, 0x1160, 0x20a9, 0x0010,
-       0xae88, 0x0004, 0x2104, 0xa606, 0x0128, 0x8108, 0x1f04, 0x4f02,
-       0xa085, 0x0001, 0xa006, 0x00ee, 0x0005, 0x00d6, 0x0126, 0x2091,
-       0x8000, 0x60a4, 0xa06d, 0x1128, 0x080c, 0x15d9, 0x01a0, 0x2d00,
-       0x60a6, 0x6803, 0x0001, 0x6807, 0x0000, 0xad88, 0x0004, 0x20a9,
-       0x0010, 0x200b, 0xffff, 0x8108, 0x1f04, 0x4f21, 0xa085, 0x0001,
-       0x012e, 0x00de, 0x0005, 0xa006, 0x0cd8, 0x00d6, 0x0126, 0x2091,
-       0x8000, 0x60a4, 0xa06d, 0x0130, 0x60a7, 0x0000, 0x080c, 0x15f0,
-       0xa085, 0x0001, 0x012e, 0x00de, 0x0005, 0x60a8, 0xa00d, 0x1118,
-       0xa085, 0x0001, 0x0005, 0x00e6, 0x2170, 0x7050, 0xa005, 0x1160,
-       0x20a9, 0x0010, 0xae88, 0x0018, 0x2104, 0xa606, 0x0128, 0x8108,
-       0x1f04, 0x4f4c, 0xa085, 0x0001, 0x00ee, 0x0005, 0x0126, 0x2091,
-       0x8000, 0x0c19, 0x1188, 0x200b, 0xffff, 0x00d6, 0x60a8, 0x2068,
-       0x6854, 0xa08a, 0x0002, 0x0218, 0x8001, 0x6856, 0x0020, 0x080c,
-       0x15f0, 0x60ab, 0x0000, 0x00de, 0x012e, 0x0005, 0x609c, 0xd0a4,
-       0x0005, 0x00f6, 0x080c, 0x574f, 0x01b0, 0x71b4, 0x81ff, 0x1198,
-       0x71d0, 0xd19c, 0x0180, 0x2001, 0x007e, 0xa080, 0xae34, 0x2004,
-       0xa07d, 0x0148, 0x7804, 0xa084, 0x00ff, 0xa086, 0x0006, 0x1118,
-       0x7800, 0xc0ed, 0x7802, 0x2079, 0xad51, 0x7804, 0xd0a4, 0x01e8,
-       0x0156, 0x00c6, 0x20a9, 0x007f, 0x2009, 0x0000, 0x0016, 0x080c,
-       0x4cdc, 0x1168, 0x6004, 0xa084, 0xff00, 0x8007, 0xa096, 0x0004,
-       0x0118, 0xa086, 0x0006, 0x1118, 0x6000, 0xc0ed, 0x6002, 0x001e,
-       0x8108, 0x1f04, 0x4f96, 0x00ce, 0x015e, 0x080c, 0x502d, 0x0120,
-       0x2001, 0xafa2, 0x200c, 0x0038, 0x2079, 0xad51, 0x7804, 0xd0a4,
-       0x0130, 0x2009, 0x07d0, 0x2011, 0x4fc1, 0x080c, 0x6593, 0x00fe,
-       0x0005, 0x2011, 0x4fc1, 0x080c, 0x650d, 0x080c, 0x502d, 0x01f0,
-       0x2001, 0xaeb2, 0x2004, 0xa080, 0x0000, 0x200c, 0xc1ec, 0x2102,
-       0x2001, 0xad52, 0x2004, 0xd0a4, 0x0130, 0x2009, 0x07d0, 0x2011,
-       0x4fc1, 0x080c, 0x6593, 0x00e6, 0x2071, 0xad00, 0x706f, 0x0000,
-       0x7073, 0x0000, 0x080c, 0x28fa, 0x00ee, 0x04b0, 0x0156, 0x00c6,
-       0x20a9, 0x007f, 0x2009, 0x0000, 0x0016, 0x080c, 0x4cdc, 0x1530,
-       0x6000, 0xd0ec, 0x0518, 0x0046, 0x62a0, 0xa294, 0x00ff, 0x8227,
-       0xa006, 0x2009, 0x0029, 0x080c, 0xa96c, 0x6000, 0xc0e5, 0xc0ec,
-       0x6002, 0x6004, 0xa084, 0x00ff, 0xa085, 0x0700, 0x6006, 0x2019,
-       0x0029, 0x080c, 0x68e7, 0x0076, 0x2039, 0x0000, 0x080c, 0x681d,
-       0x2009, 0x0000, 0x080c, 0xa712, 0x007e, 0x004e, 0x001e, 0x8108,
-       0x1f04, 0x4fec, 0x00ce, 0x015e, 0x0005, 0x00c6, 0x6018, 0x2060,
-       0x6000, 0xc0ec, 0x6002, 0x00ce, 0x0005, 0x7818, 0x2004, 0xd0ac,
-       0x0005, 0x7818, 0x2004, 0xd0bc, 0x0005, 0x00f6, 0x2001, 0xaeb2,
-       0x2004, 0xa07d, 0x0110, 0x7800, 0xd0ec, 0x00fe, 0x0005, 0x0126,
-       0x0026, 0x2091, 0x8000, 0x6200, 0xa005, 0x0110, 0xc2fd, 0x0008,
-       0xc2fc, 0x6202, 0x002e, 0x012e, 0x0005, 0x2071, 0xae13, 0x7003,
-       0x0001, 0x7007, 0x0000, 0x7013, 0x0000, 0x7017, 0x0000, 0x701b,
-       0x0000, 0x701f, 0x0000, 0x700b, 0x0000, 0x704b, 0x0001, 0x704f,
-       0x0000, 0x705b, 0x0020, 0x705f, 0x0040, 0x707f, 0x0000, 0x2071,
-       0xaf7c, 0x7003, 0xae13, 0x7007, 0x0000, 0x700b, 0x0000, 0x700f,
-       0xaf5c, 0x7013, 0x0020, 0x7017, 0x0040, 0x7037, 0x0000, 0x0005,
-       0x0016, 0x00e6, 0x2071, 0xaf34, 0xa00e, 0x7186, 0x718a, 0x7097,
-       0x0001, 0x2001, 0xad52, 0x2004, 0xd0fc, 0x1150, 0x2001, 0xad52,
-       0x2004, 0xa00e, 0xd09c, 0x0108, 0x8108, 0x7102, 0x0804, 0x50d6,
-       0x2001, 0xad71, 0x200c, 0xa184, 0x000f, 0x2009, 0xad72, 0x210c,
-       0x0002, 0x507e, 0x50b1, 0x50b8, 0x50c2, 0x50c7, 0x507e, 0x507e,
-       0x507e, 0x50a1, 0x507e, 0x507e, 0x507e, 0x507e, 0x507e, 0x507e,
-       0x507e, 0x7003, 0x0004, 0x0136, 0x0146, 0x0156, 0x2099, 0xad75,
-       0x20a1, 0xaf85, 0x20a9, 0x0004, 0x53a3, 0x015e, 0x014e, 0x013e,
-       0x0428, 0x708f, 0x0005, 0x7007, 0x0122, 0x2001, 0x0002, 0x0030,
-       0x708f, 0x0002, 0x7007, 0x0121, 0x2001, 0x0003, 0x7002, 0x7097,
-       0x0001, 0x0088, 0x7007, 0x0122, 0x2001, 0x0002, 0x0020, 0x7007,
-       0x0121, 0x2001, 0x0003, 0x7002, 0xa006, 0x7096, 0x708e, 0xa184,
-       0xff00, 0x8007, 0x709a, 0xa184, 0x00ff, 0x7092, 0x00ee, 0x001e,
-       0x0005, 0x00e6, 0x2071, 0xae13, 0x684c, 0xa005, 0x1130, 0x7028,
-       0xc085, 0x702a, 0xa085, 0x0001, 0x0428, 0x6a60, 0x7236, 0x6b64,
-       0x733a, 0x6868, 0x703e, 0x7076, 0x686c, 0x7042, 0x707a, 0x684c,
-       0x702e, 0x6844, 0x7032, 0x2009, 0x000d, 0x200a, 0x700b, 0x0000,
-       0x8007, 0x8006, 0x8006, 0xa08c, 0x003f, 0xa084, 0xffc0, 0xa210,
-       0x2100, 0xa319, 0x726e, 0x7372, 0x7028, 0xc084, 0x702a, 0x7007,
-       0x0001, 0xa006, 0x00ee, 0x0005, 0x0156, 0x00e6, 0x0026, 0x6838,
-       0xd0fc, 0x1904, 0x5165, 0x6804, 0xa00d, 0x0188, 0x00d6, 0x2071,
-       0xad00, 0xa016, 0x702c, 0x2168, 0x6904, 0x206a, 0x8210, 0x2d00,
-       0x81ff, 0x1dc8, 0x702e, 0x70b0, 0xa200, 0x70b2, 0x00de, 0x2071,
-       0xae13, 0x701c, 0xa005, 0x1904, 0x5175, 0x20a9, 0x0032, 0x0f04,
-       0x5173, 0x0e04, 0x512f, 0x2071, 0xaf34, 0x7200, 0x82ff, 0x05d8,
-       0x6934, 0xa186, 0x0103, 0x1904, 0x5183, 0x6948, 0x6844, 0xa105,
-       0x1540, 0x2009, 0x8020, 0x2200, 0x0002, 0x5173, 0x514a, 0x519b,
-       0x51a7, 0x5173, 0x2071, 0x0000, 0x20a9, 0x0032, 0x0f04, 0x5173,
-       0x7018, 0xd084, 0x1dd8, 0x7122, 0x683c, 0x7026, 0x6840, 0x702a,
-       0x701b, 0x0001, 0x2091, 0x4080, 0x2071, 0xad00, 0x702c, 0x206a,
-       0x2d00, 0x702e, 0x70b0, 0x8000, 0x70b2, 0x002e, 0x00ee, 0x015e,
-       0x0005, 0x6844, 0xa086, 0x0100, 0x1130, 0x6868, 0xa005, 0x1118,
-       0x2009, 0x8020, 0x0880, 0x2071, 0xae13, 0x2d08, 0x206b, 0x0000,
-       0x7010, 0x8000, 0x7012, 0x7018, 0xa06d, 0x711a, 0x0110, 0x6902,
-       0x0008, 0x711e, 0x0c10, 0xa18c, 0x00ff, 0xa186, 0x0017, 0x0130,
-       0xa186, 0x001e, 0x0118, 0xa18e, 0x001f, 0x1d28, 0x684c, 0xd0cc,
-       0x0d10, 0x6850, 0xa084, 0x00ff, 0xa086, 0x0001, 0x19e0, 0x2009,
-       0x8021, 0x0804, 0x5143, 0x7084, 0x8008, 0xa092, 0x001e, 0x1a98,
-       0x7186, 0xae90, 0x0003, 0xa210, 0x683c, 0x2012, 0x0078, 0x7084,
-       0x8008, 0xa092, 0x000f, 0x1a38, 0x7186, 0xae90, 0x0003, 0x8003,
-       0xa210, 0x683c, 0x2012, 0x8210, 0x6840, 0x2012, 0x7088, 0xa10a,
-       0x0a04, 0x515c, 0x718c, 0x7084, 0xa10a, 0x0a04, 0x515c, 0x2071,
-       0x0000, 0x7018, 0xd084, 0x1904, 0x515c, 0x2071, 0xaf34, 0x7000,
-       0xa086, 0x0002, 0x1150, 0x080c, 0x5426, 0x2071, 0x0000, 0x701b,
-       0x0001, 0x2091, 0x4080, 0x0804, 0x515c, 0x080c, 0x5450, 0x2071,
-       0x0000, 0x701b, 0x0001, 0x2091, 0x4080, 0x0804, 0x515c, 0x0006,
-       0x684c, 0x0006, 0x6837, 0x0103, 0x20a9, 0x001c, 0xad80, 0x0011,
-       0x20a0, 0x2001, 0x0000, 0x40a4, 0x000e, 0xa084, 0x00ff, 0x684e,
-       0x000e, 0x684a, 0x6952, 0x0005, 0x2071, 0xae13, 0x7004, 0x0002,
-       0x5202, 0x5213, 0x5411, 0x5412, 0x541f, 0x5425, 0x5203, 0x5402,
-       0x5398, 0x53ee, 0x0005, 0x0126, 0x2091, 0x8000, 0x0e04, 0x5212,
-       0x2009, 0x000d, 0x7030, 0x200a, 0x2091, 0x4080, 0x7007, 0x0001,
-       0x700b, 0x0000, 0x012e, 0x2069, 0xafda, 0x683c, 0xa005, 0x03f8,
-       0x11f0, 0x0126, 0x2091, 0x8000, 0x2069, 0x0000, 0x6934, 0x2001,
-       0xae1f, 0x2004, 0xa10a, 0x0170, 0x0e04, 0x5236, 0x2069, 0x0000,
-       0x6818, 0xd084, 0x1158, 0x2009, 0x8040, 0x6922, 0x681b, 0x0001,
-       0x2091, 0x4080, 0x2069, 0xafda, 0x683f, 0xffff, 0x012e, 0x2069,
-       0xad00, 0x6844, 0x6964, 0xa102, 0x2069, 0xaf34, 0x688a, 0x6984,
-       0x701c, 0xa06d, 0x0120, 0x81ff, 0x0904, 0x528c, 0x00a0, 0x81ff,
-       0x0904, 0x5352, 0x2071, 0xaf34, 0x7184, 0x7088, 0xa10a, 0x1258,
-       0x7190, 0x2071, 0xafda, 0x7038, 0xa005, 0x0128, 0x1b04, 0x5352,
-       0x713a, 0x0804, 0x5352, 0x2071, 0xaf34, 0x718c, 0x0126, 0x2091,
-       0x8000, 0x7084, 0xa10a, 0x0a04, 0x536d, 0x0e04, 0x530e, 0x2071,
-       0x0000, 0x7018, 0xd084, 0x1904, 0x530e, 0x2001, 0xffff, 0x2071,
-       0xafda, 0x703a, 0x2071, 0xaf34, 0x7000, 0xa086, 0x0002, 0x1150,
-       0x080c, 0x5426, 0x2071, 0x0000, 0x701b, 0x0001, 0x2091, 0x4080,
-       0x0804, 0x530e, 0x080c, 0x5450, 0x2071, 0x0000, 0x701b, 0x0001,
-       0x2091, 0x4080, 0x0804, 0x530e, 0x2071, 0xaf34, 0x7000, 0xa005,
-       0x0904, 0x5334, 0x6934, 0xa186, 0x0103, 0x1904, 0x5311, 0x684c,
-       0xd0bc, 0x1904, 0x5334, 0x6948, 0x6844, 0xa105, 0x1904, 0x5329,
-       0x2009, 0x8020, 0x2071, 0xaf34, 0x7000, 0x0002, 0x5334, 0x52f4,
-       0x52cc, 0x52de, 0x52ab, 0x0136, 0x0146, 0x0156, 0x2099, 0xad75,
-       0x20a1, 0xaf85, 0x20a9, 0x0004, 0x53a3, 0x015e, 0x014e, 0x013e,
-       0x2071, 0xaf7c, 0xad80, 0x000f, 0x700e, 0x7013, 0x0002, 0x7007,
-       0x0002, 0x700b, 0x0000, 0x2e10, 0x080c, 0x1624, 0x2071, 0xae13,
-       0x7007, 0x0009, 0x0804, 0x5352, 0x7084, 0x8008, 0xa092, 0x001e,
-       0x1a04, 0x5352, 0xae90, 0x0003, 0xa210, 0x683c, 0x2012, 0x7186,
-       0x2071, 0xae13, 0x080c, 0x54a7, 0x0804, 0x5352, 0x7084, 0x8008,
-       0xa092, 0x000f, 0x1a04, 0x5352, 0xae90, 0x0003, 0x8003, 0xa210,
-       0x683c, 0x2012, 0x8210, 0x6840, 0x2012, 0x7186, 0x2071, 0xae13,
-       0x080c, 0x54a7, 0x0804, 0x5352, 0x0126, 0x2091, 0x8000, 0x0e04,
-       0x530e, 0x2071, 0x0000, 0x7018, 0xd084, 0x1180, 0x7122, 0x683c,
-       0x7026, 0x6840, 0x702a, 0x701b, 0x0001, 0x2091, 0x4080, 0x012e,
-       0x2071, 0xae13, 0x080c, 0x54a7, 0x0804, 0x5352, 0x012e, 0x0804,
-       0x5352, 0xa18c, 0x00ff, 0xa186, 0x0017, 0x0130, 0xa186, 0x001e,
-       0x0118, 0xa18e, 0x001f, 0x11c0, 0x684c, 0xd0cc, 0x01a8, 0x6850,
-       0xa084, 0x00ff, 0xa086, 0x0001, 0x1178, 0x2009, 0x8021, 0x0804,
-       0x52a2, 0x6844, 0xa086, 0x0100, 0x1138, 0x6868, 0xa005, 0x1120,
-       0x2009, 0x8020, 0x0804, 0x52a2, 0x2071, 0xae13, 0x080c, 0x54b9,
-       0x01c8, 0x2071, 0xae13, 0x700f, 0x0001, 0x6934, 0xa184, 0x00ff,
-       0xa086, 0x0003, 0x1130, 0x810f, 0xa18c, 0x00ff, 0x8101, 0x0108,
-       0x710e, 0x7007, 0x0003, 0x080c, 0x54d2, 0x7050, 0xa086, 0x0100,
-       0x0904, 0x5412, 0x0126, 0x2091, 0x8000, 0x2071, 0xae13, 0x7008,
-       0xa086, 0x0001, 0x1180, 0x0e04, 0x536b, 0x2009, 0x000d, 0x7030,
-       0x200a, 0x2091, 0x4080, 0x700b, 0x0000, 0x7004, 0xa086, 0x0006,
-       0x1110, 0x7007, 0x0001, 0x012e, 0x0005, 0x2071, 0xae13, 0x080c,
-       0x54b9, 0x0518, 0x2071, 0xaf34, 0x7084, 0x700a, 0x20a9, 0x0020,
-       0x2099, 0xaf35, 0x20a1, 0xaf5c, 0x53a3, 0x7087, 0x0000, 0x2071,
-       0xae13, 0x2069, 0xaf7c, 0x706c, 0x6826, 0x7070, 0x682a, 0x7074,
-       0x682e, 0x7078, 0x6832, 0x2d10, 0x080c, 0x1624, 0x7007, 0x0008,
-       0x2001, 0xffff, 0x2071, 0xafda, 0x703a, 0x012e, 0x0804, 0x5352,
-       0x2069, 0xaf7c, 0x6808, 0xa08e, 0x0000, 0x0904, 0x53ed, 0xa08e,
-       0x0200, 0x0904, 0x53eb, 0xa08e, 0x0100, 0x1904, 0x53ed, 0x0126,
-       0x2091, 0x8000, 0x0e04, 0x53e9, 0x2069, 0x0000, 0x6818, 0xd084,
-       0x15c0, 0x702c, 0x7130, 0x8108, 0xa102, 0x0230, 0xa00e, 0x7034,
-       0x706e, 0x7038, 0x7072, 0x0048, 0x706c, 0xa080, 0x0040, 0x706e,
-       0x1220, 0x7070, 0xa081, 0x0000, 0x7072, 0x7132, 0x6936, 0x700b,
-       0x0000, 0x2001, 0xaf59, 0x2004, 0xa005, 0x1190, 0x6934, 0x2069,
-       0xaf34, 0x689c, 0x699e, 0x2069, 0xafda, 0xa102, 0x1118, 0x683c,
-       0xa005, 0x1368, 0x2001, 0xaf5a, 0x200c, 0x810d, 0x693e, 0x0038,
-       0x2009, 0x8040, 0x6922, 0x681b, 0x0001, 0x2091, 0x4080, 0x7007,
-       0x0001, 0x012e, 0x0010, 0x7007, 0x0005, 0x0005, 0x2001, 0xaf7e,
-       0x2004, 0xa08e, 0x0100, 0x1128, 0x7007, 0x0001, 0x080c, 0x54a7,
-       0x0005, 0xa08e, 0x0000, 0x0de0, 0xa08e, 0x0200, 0x1dc8, 0x7007,
-       0x0005, 0x0005, 0x701c, 0xa06d, 0x0158, 0x080c, 0x54b9, 0x0140,
-       0x7007, 0x0003, 0x080c, 0x54d2, 0x7050, 0xa086, 0x0100, 0x0110,
-       0x0005, 0x0005, 0x7050, 0xa09e, 0x0100, 0x1118, 0x7007, 0x0004,
-       0x0030, 0xa086, 0x0200, 0x1110, 0x7007, 0x0005, 0x0005, 0x080c,
-       0x5475, 0x7006, 0x080c, 0x54a7, 0x0005, 0x0005, 0x00e6, 0x0156,
-       0x2071, 0xaf34, 0x7184, 0x81ff, 0x0500, 0xa006, 0x7086, 0xae80,
-       0x0003, 0x2071, 0x0000, 0x21a8, 0x2014, 0x7226, 0x8000, 0x0f04,
-       0x544a, 0x2014, 0x722a, 0x8000, 0x0f04, 0x544a, 0x2014, 0x722e,
-       0x8000, 0x0f04, 0x544a, 0x2014, 0x723a, 0x8000, 0x0f04, 0x544a,
-       0x2014, 0x723e, 0xa180, 0x8030, 0x7022, 0x015e, 0x00ee, 0x0005,
-       0x00e6, 0x0156, 0x2071, 0xaf34, 0x7184, 0x81ff, 0x01d8, 0xa006,
-       0x7086, 0xae80, 0x0003, 0x2071, 0x0000, 0x21a8, 0x2014, 0x7226,
-       0x8000, 0x2014, 0x722a, 0x8000, 0x0f04, 0x546c, 0x2014, 0x723a,
-       0x8000, 0x2014, 0x723e, 0x0018, 0x2001, 0x8020, 0x0010, 0x2001,
-       0x8042, 0x7022, 0x015e, 0x00ee, 0x0005, 0x702c, 0x7130, 0x8108,
-       0xa102, 0x0230, 0xa00e, 0x7034, 0x706e, 0x7038, 0x7072, 0x0048,
-       0x706c, 0xa080, 0x0040, 0x706e, 0x1220, 0x7070, 0xa081, 0x0000,
-       0x7072, 0x7132, 0x700c, 0x8001, 0x700e, 0x1180, 0x0126, 0x2091,
-       0x8000, 0x0e04, 0x54a1, 0x2001, 0x000d, 0x2102, 0x2091, 0x4080,
-       0x2001, 0x0001, 0x700b, 0x0000, 0x012e, 0x0005, 0x2001, 0x0007,
-       0x0005, 0x2001, 0x0006, 0x700b, 0x0001, 0x012e, 0x0005, 0x701c,
-       0xa06d, 0x0170, 0x0126, 0x2091, 0x8000, 0x7010, 0x8001, 0x7012,
-       0x2d04, 0x701e, 0xa005, 0x1108, 0x701a, 0x012e, 0x080c, 0x15f0,
-       0x0005, 0x2019, 0x000d, 0x2304, 0x230c, 0xa10e, 0x0130, 0x2304,
-       0x230c, 0xa10e, 0x0110, 0xa006, 0x0060, 0x732c, 0x8319, 0x7130,
-       0xa102, 0x1118, 0x2300, 0xa005, 0x0020, 0x0210, 0xa302, 0x0008,
-       0x8002, 0x0005, 0x2d00, 0x7026, 0xa080, 0x000d, 0x7056, 0x7053,
-       0x0000, 0x0126, 0x2091, 0x8000, 0x2009, 0xafec, 0x2104, 0xc08d,
-       0x200a, 0x012e, 0x080c, 0x163c, 0x0005, 0x7088, 0xa08a, 0x0029,
-       0x1220, 0xa082, 0x001d, 0x0033, 0x0010, 0x080c, 0x14f6, 0x6027,
-       0x1e00, 0x0005, 0x55c1, 0x555b, 0x5571, 0x5595, 0x55b4, 0x55e6,
-       0x55f8, 0x5571, 0x55d2, 0x54ff, 0x552d, 0x54fe, 0x0005, 0x00d6,
-       0x2069, 0x0200, 0x6804, 0xa005, 0x1180, 0x6808, 0xa005, 0x1518,
-       0x708b, 0x0028, 0x2069, 0xafac, 0x2d04, 0x7002, 0x080c, 0x584d,
-       0x6028, 0xa085, 0x0600, 0x602a, 0x00b0, 0x708b, 0x0028, 0x2069,
-       0xafac, 0x2d04, 0x7002, 0x6028, 0xa085, 0x0600, 0x602a, 0x00e6,
-       0x0036, 0x0046, 0x0056, 0x2071, 0xaffd, 0x080c, 0x1d22, 0x005e,
-       0x004e, 0x003e, 0x00ee, 0x00de, 0x0005, 0x00d6, 0x2069, 0x0200,
-       0x6804, 0xa005, 0x1180, 0x6808, 0xa005, 0x1518, 0x708b, 0x0028,
-       0x2069, 0xafac, 0x2d04, 0x7002, 0x080c, 0x58da, 0x6028, 0xa085,
-       0x0600, 0x602a, 0x00b0, 0x708b, 0x0028, 0x2069, 0xafac, 0x2d04,
-       0x7002, 0x6028, 0xa085, 0x0600, 0x602a, 0x00e6, 0x0036, 0x0046,
-       0x0056, 0x2071, 0xaffd, 0x080c, 0x1d22, 0x005e, 0x004e, 0x003e,
-       0x00ee, 0x00de, 0x0005, 0x6803, 0x0090, 0x6124, 0xd1e4, 0x1180,
-       0x080c, 0x5663, 0xd1d4, 0x1150, 0xd1dc, 0x1128, 0xd1cc, 0x0140,
-       0x708b, 0x0020, 0x0028, 0x708b, 0x001d, 0x0010, 0x708b, 0x001f,
-       0x0005, 0x6803, 0x0088, 0x6124, 0xd1cc, 0x11c8, 0xd1dc, 0x11a0,
-       0xd1e4, 0x1178, 0xa184, 0x1e00, 0x11b8, 0x60e3, 0x0001, 0x600c,
-       0xc0b4, 0x600e, 0x080c, 0x577f, 0x6803, 0x0080, 0x708b, 0x0028,
-       0x0058, 0x708b, 0x001e, 0x0040, 0x708b, 0x001d, 0x0028, 0x708b,
-       0x0020, 0x0010, 0x708b, 0x001f, 0x0005, 0x60e3, 0x0001, 0x600c,
-       0xc0b4, 0x600e, 0x080c, 0x577f, 0x6803, 0x0080, 0x6124, 0xd1d4,
-       0x1180, 0xd1dc, 0x1158, 0xd1e4, 0x1130, 0xa184, 0x1e00, 0x1158,
-       0x708b, 0x0028, 0x0040, 0x708b, 0x001e, 0x0028, 0x708b, 0x001d,
-       0x0010, 0x708b, 0x001f, 0x0005, 0x6803, 0x00a0, 0x6124, 0xd1dc,
-       0x1128, 0xd1e4, 0x0128, 0x708b, 0x001e, 0x0010, 0x708b, 0x001d,
-       0x0005, 0x080c, 0x568d, 0x6124, 0xd1dc, 0x1158, 0x080c, 0x5663,
-       0xd1d4, 0x1128, 0xd1e4, 0x0128, 0x708b, 0x001e, 0x0010, 0x708b,
-       0x001f, 0x0005, 0x6803, 0x00a0, 0x6124, 0xd1d4, 0x1160, 0xd1cc,
-       0x1150, 0xd1dc, 0x1128, 0xd1e4, 0x0140, 0x708b, 0x001e, 0x0028,
-       0x708b, 0x001d, 0x0010, 0x708b, 0x0021, 0x0005, 0x080c, 0x568d,
-       0x6124, 0xd1d4, 0x1150, 0xd1dc, 0x1128, 0xd1e4, 0x0140, 0x708b,
-       0x001e, 0x0028, 0x708b, 0x001d, 0x0010, 0x708b, 0x001f, 0x0005,
-       0x6803, 0x0090, 0x6124, 0xd1d4, 0x1178, 0xd1cc, 0x1150, 0xd1dc,
-       0x1128, 0xd1e4, 0x0158, 0x708b, 0x001e, 0x0040, 0x708b, 0x001d,
-       0x0028, 0x708b, 0x0020, 0x0010, 0x708b, 0x001f, 0x0005, 0x0016,
-       0x00c6, 0x00d6, 0x00e6, 0x0126, 0x2061, 0x0100, 0x2069, 0x0140,
-       0x2071, 0xad00, 0x2091, 0x8000, 0x080c, 0x574f, 0x11e8, 0x2001,
-       0xad0c, 0x200c, 0xd1b4, 0x01c0, 0xc1b4, 0x2102, 0x6027, 0x0200,
-       0xe000, 0xe000, 0x6024, 0xd0cc, 0x0158, 0x6803, 0x00a0, 0x2001,
-       0xaf9e, 0x2003, 0x0001, 0x2001, 0xad00, 0x2003, 0x0001, 0x0428,
-       0x6028, 0xc0cd, 0x602a, 0x0408, 0x080c, 0x576b, 0x0150, 0x080c,
-       0x5761, 0x1138, 0x2001, 0x0001, 0x080c, 0x261e, 0x080c, 0x5726,
-       0x00a0, 0x080c, 0x568a, 0x0178, 0x2001, 0x0001, 0x080c, 0x261e,
-       0x7088, 0xa086, 0x001e, 0x0120, 0x7088, 0xa086, 0x0022, 0x1118,
-       0x708b, 0x0025, 0x0010, 0x708b, 0x0021, 0x012e, 0x00ee, 0x00de,
-       0x00ce, 0x001e, 0x0005, 0x0016, 0x0026, 0x2009, 0x0064, 0x2011,
-       0x566e, 0x080c, 0x6501, 0x002e, 0x001e, 0x0005, 0x00e6, 0x00f6,
-       0x0016, 0x080c, 0x7834, 0x2071, 0xad00, 0x080c, 0x560f, 0x001e,
-       0x00fe, 0x00ee, 0x0005, 0x2001, 0xad00, 0x2004, 0xa086, 0x0004,
-       0x0140, 0x2001, 0xaf9d, 0x2003, 0xaaaa, 0x2001, 0xaf9e, 0x2003,
-       0x0000, 0x0005, 0x6020, 0xd09c, 0x0005, 0x6803, 0x00c0, 0x0156,
-       0x20a9, 0x002d, 0x1d04, 0x5692, 0x2091, 0x6000, 0x1f04, 0x5692,
-       0x015e, 0x0005, 0x00c6, 0x00d6, 0x00e6, 0x2061, 0x0100, 0x2069,
-       0x0140, 0x2071, 0xad00, 0x2001, 0xaf9e, 0x200c, 0xa186, 0x0000,
-       0x0158, 0xa186, 0x0001, 0x0158, 0xa186, 0x0002, 0x0158, 0xa186,
-       0x0003, 0x0158, 0x0804, 0x5714, 0x708b, 0x0022, 0x0040, 0x708b,
-       0x0021, 0x0028, 0x708b, 0x0023, 0x0020, 0x708b, 0x0024, 0x6043,
-       0x0000, 0x60e3, 0x0000, 0x6887, 0x0001, 0x2001, 0x0001, 0x080c,
-       0x26cb, 0x0026, 0x2011, 0x0003, 0x080c, 0x7adf, 0x2011, 0x0002,
-       0x080c, 0x7ae9, 0x002e, 0x7000, 0xa08e, 0x0004, 0x0118, 0x602b,
-       0x0028, 0x0010, 0x602b, 0x0020, 0x0156, 0x0126, 0x2091, 0x8000,
-       0x20a9, 0x0005, 0x6024, 0xd0ac, 0x0118, 0x012e, 0x015e, 0x04d0,
-       0x6800, 0xa084, 0x00a0, 0xc0bd, 0x6802, 0x6904, 0xd1d4, 0x1130,
-       0x6803, 0x0100, 0x1f04, 0x56e2, 0x080c, 0x57a0, 0x012e, 0x015e,
-       0x080c, 0x5761, 0x01a8, 0x6044, 0xa005, 0x0168, 0x6050, 0x0006,
-       0xa085, 0x0020, 0x6052, 0x080c, 0x57a0, 0xa006, 0x8001, 0x1df0,
-       0x000e, 0x6052, 0x0028, 0x6804, 0xd0d4, 0x1110, 0x080c, 0x57a0,
-       0x2001, 0xaf9e, 0x2003, 0x0004, 0x080c, 0x54e5, 0x080c, 0x5761,
-       0x0148, 0x6804, 0xd0d4, 0x1130, 0xd0dc, 0x1100, 0x2001, 0xaf9e,
-       0x2003, 0x0000, 0x00ee, 0x00de, 0x00ce, 0x0005, 0x00c6, 0x00d6,
-       0x00e6, 0x2061, 0x0100, 0x2069, 0x0140, 0x2071, 0xad00, 0x2001,
-       0xaf9d, 0x2003, 0x0000, 0x2001, 0xaf8e, 0x2003, 0x0000, 0x708b,
-       0x0000, 0x60e3, 0x0000, 0x6887, 0x0000, 0x2001, 0x0000, 0x080c,
-       0x26cb, 0x6803, 0x0000, 0x6043, 0x0090, 0x6043, 0x0010, 0x6027,
-       0xffff, 0x602b, 0x182f, 0x00ee, 0x00de, 0x00ce, 0x0005, 0x0006,
-       0x2001, 0xaf9d, 0x2004, 0xa086, 0xaaaa, 0x000e, 0x0005, 0x0006,
-       0x2001, 0xad71, 0x2004, 0xa084, 0x0030, 0xa086, 0x0000, 0x000e,
-       0x0005, 0x0006, 0x2001, 0xad71, 0x2004, 0xa084, 0x0030, 0xa086,
-       0x0030, 0x000e, 0x0005, 0x0006, 0x2001, 0xad71, 0x2004, 0xa084,
-       0x0030, 0xa086, 0x0010, 0x000e, 0x0005, 0x0006, 0x2001, 0xad71,
-       0x2004, 0xa084, 0x0030, 0xa086, 0x0020, 0x000e, 0x0005, 0x2001,
-       0xad0c, 0x2004, 0xd0a4, 0x0170, 0x080c, 0x26eb, 0x0036, 0x0016,
-       0x2009, 0x0000, 0x2019, 0x0028, 0x080c, 0x2aac, 0x001e, 0x003e,
-       0xa006, 0x0009, 0x0005, 0x00e6, 0x2071, 0xad0c, 0x2e04, 0x0118,
-       0xa085, 0x0010, 0x0010, 0xa084, 0xffef, 0x2072, 0x00ee, 0x0005,
-       0x6050, 0x0006, 0x60f0, 0x0006, 0x60ec, 0x0006, 0x600c, 0x0006,
-       0x6004, 0x0006, 0x6028, 0x0006, 0x602f, 0x0100, 0x602f, 0x0000,
-       0x602f, 0x0040, 0x602f, 0x0000, 0x000e, 0x602a, 0x000e, 0x6006,
-       0x000e, 0x600e, 0x000e, 0x60ee, 0x000e, 0x60f2, 0x60e3, 0x0000,
-       0x6887, 0x0001, 0x2001, 0x0001, 0x080c, 0x26cb, 0x6800, 0xa084,
-       0x00a0, 0xc0bd, 0x6802, 0x6803, 0x00a0, 0x000e, 0x6052, 0x6050,
-       0x0005, 0x0156, 0x0016, 0x0026, 0x0036, 0x00c6, 0x00d6, 0x00e6,
-       0x2061, 0x0100, 0x2069, 0x0140, 0x2071, 0xad00, 0x6020, 0xa084,
-       0x0080, 0x0138, 0x2001, 0xad0c, 0x200c, 0xc1bd, 0x2102, 0x0804,
-       0x5845, 0x2001, 0xad0c, 0x200c, 0xc1bc, 0x2102, 0x6028, 0xa084,
-       0xe1ff, 0x602a, 0x6027, 0x0200, 0x6803, 0x0090, 0x20a9, 0x0384,
-       0x6024, 0xd0cc, 0x1518, 0x1d04, 0x57f8, 0x2091, 0x6000, 0x1f04,
-       0x57f8, 0x2011, 0x0003, 0x080c, 0x7adf, 0x2011, 0x0002, 0x080c,
-       0x7ae9, 0x080c, 0x79e1, 0x080c, 0x6581, 0x2019, 0x0000, 0x080c,
-       0x7a64, 0x6803, 0x00a0, 0x2001, 0xaf9e, 0x2003, 0x0001, 0x2001,
-       0xad00, 0x2003, 0x0001, 0xa085, 0x0001, 0x0438, 0x60e3, 0x0000,
-       0x2001, 0xaf8e, 0x2004, 0x080c, 0x26cb, 0x60e2, 0x6803, 0x0080,
-       0x20a9, 0x0384, 0x6027, 0x1e00, 0x2009, 0x1e00, 0xe000, 0x6024,
-       0xa10c, 0x0138, 0x1d04, 0x582a, 0x2091, 0x6000, 0x1f04, 0x582a,
-       0x0840, 0x6028, 0xa085, 0x1e00, 0x602a, 0x70a0, 0xa005, 0x1118,
-       0x6887, 0x0001, 0x0008, 0x6886, 0xa006, 0x00ee, 0x00de, 0x00ce,
-       0x003e, 0x002e, 0x001e, 0x015e, 0x0005, 0x0156, 0x0016, 0x0026,
-       0x0036, 0x00c6, 0x00d6, 0x00e6, 0x2061, 0x0100, 0x2071, 0xad00,
-       0x2069, 0x0140, 0x6020, 0xa084, 0x00c0, 0x0120, 0x6884, 0xa005,
-       0x1904, 0x58a1, 0x6803, 0x0088, 0x60e3, 0x0000, 0x6887, 0x0000,
-       0x2001, 0x0000, 0x080c, 0x26cb, 0x2069, 0x0200, 0x6804, 0xa005,
-       0x1118, 0x6808, 0xa005, 0x01c0, 0x6028, 0xa084, 0xfbff, 0x602a,
-       0x6027, 0x0400, 0x2069, 0xafac, 0x7000, 0x206a, 0x708b, 0x0026,
-       0x7003, 0x0001, 0x20a9, 0x0002, 0x1d04, 0x5884, 0x2091, 0x6000,
-       0x1f04, 0x5884, 0x0804, 0x58d2, 0x2069, 0x0140, 0x20a9, 0x0384,
-       0x6027, 0x1e00, 0x2009, 0x1e00, 0xe000, 0x6024, 0xa10c, 0x0530,
-       0xa084, 0x1a00, 0x1518, 0x1d04, 0x5890, 0x2091, 0x6000, 0x1f04,
-       0x5890, 0x2011, 0x0003, 0x080c, 0x7adf, 0x2011, 0x0002, 0x080c,
-       0x7ae9, 0x080c, 0x79e1, 0x080c, 0x6581, 0x2019, 0x0000, 0x080c,
-       0x7a64, 0x6803, 0x00a0, 0x2001, 0xaf9e, 0x2003, 0x0001, 0x2001,
-       0xad00, 0x2003, 0x0001, 0xa085, 0x0001, 0x00a0, 0x6803, 0x0080,
-       0x2069, 0x0140, 0x60e3, 0x0000, 0x70a0, 0xa005, 0x1118, 0x6887,
-       0x0001, 0x0008, 0x6886, 0x2001, 0xaf8e, 0x2004, 0x080c, 0x26cb,
-       0x60e2, 0xa006, 0x00ee, 0x00de, 0x00ce, 0x003e, 0x002e, 0x001e,
-       0x015e, 0x0005, 0x0156, 0x0016, 0x0026, 0x0036, 0x00c6, 0x00d6,
-       0x00e6, 0x2061, 0x0100, 0x2071, 0xad00, 0x6020, 0xa084, 0x00c0,
-       0x01f0, 0x2011, 0x0003, 0x080c, 0x7adf, 0x2011, 0x0002, 0x080c,
-       0x7ae9, 0x080c, 0x79e1, 0x080c, 0x6581, 0x2019, 0x0000, 0x080c,
-       0x7a64, 0x2069, 0x0140, 0x6803, 0x00a0, 0x2001, 0xaf9e, 0x2003,
-       0x0001, 0x2001, 0xad00, 0x2003, 0x0001, 0x0804, 0x5972, 0x2001,
-       0xad0c, 0x200c, 0xd1b4, 0x1150, 0xc1b5, 0x2102, 0x080c, 0x5663,
-       0x2069, 0x0140, 0x6803, 0x0080, 0x60e3, 0x0000, 0x2069, 0x0200,
-       0x6804, 0xa005, 0x1118, 0x6808, 0xa005, 0x01b8, 0x6028, 0xa084,
-       0xfdff, 0x602a, 0x6027, 0x0200, 0x2069, 0xafac, 0x7000, 0x206a,
-       0x708b, 0x0027, 0x7003, 0x0001, 0x20a9, 0x0002, 0x1d04, 0x592e,
-       0x2091, 0x6000, 0x1f04, 0x592e, 0x04e8, 0x6027, 0x1e00, 0x2009,
-       0x1e00, 0xe000, 0x6024, 0xa10c, 0x01c8, 0xa084, 0x1c00, 0x11b0,
-       0x1d04, 0x5935, 0x0006, 0x0016, 0x00c6, 0x00d6, 0x00e6, 0x080c,
-       0x64a2, 0x00ee, 0x00de, 0x00ce, 0x001e, 0x000e, 0x00e6, 0x2071,
-       0xafda, 0x7018, 0x00ee, 0xa005, 0x1d00, 0x01e0, 0x0026, 0x2011,
-       0x566e, 0x080c, 0x650d, 0x002e, 0x2069, 0x0140, 0x60e3, 0x0000,
-       0x70a0, 0xa005, 0x1118, 0x6887, 0x0001, 0x0008, 0x6886, 0x2001,
-       0xaf8e, 0x2004, 0x080c, 0x26cb, 0x60e2, 0x2001, 0xad0c, 0x200c,
-       0xc1b4, 0x2102, 0x00ee, 0x00de, 0x00ce, 0x003e, 0x002e, 0x001e,
-       0x015e, 0x0005, 0x0156, 0x0016, 0x0026, 0x0036, 0x0046, 0x00c6,
-       0x00e6, 0x2061, 0x0100, 0x2071, 0xad00, 0x7130, 0xd184, 0x1180,
-       0x2011, 0xad52, 0x2214, 0xd2ec, 0x0138, 0xc18d, 0x7132, 0x2011,
-       0xad52, 0x2214, 0xd2ac, 0x1120, 0x7030, 0xd08c, 0x0904, 0x59df,
-       0x7130, 0xc185, 0x7132, 0x2011, 0xad52, 0x220c, 0xd1a4, 0x0530,
-       0x0016, 0x2009, 0x0001, 0x2011, 0x0100, 0x080c, 0x663f, 0x2019,
-       0x000e, 0x080c, 0xa8eb, 0x0156, 0x20a9, 0x007f, 0x2009, 0x0000,
-       0xa186, 0x007e, 0x0170, 0xa186, 0x0080, 0x0158, 0x080c, 0x4cdc,
-       0x1140, 0x8127, 0xa006, 0x0016, 0x2009, 0x000e, 0x080c, 0xa96c,
-       0x001e, 0x8108, 0x1f04, 0x59b0, 0x015e, 0x001e, 0xd1ac, 0x1148,
-       0x0016, 0x2009, 0x0000, 0x2019, 0x0004, 0x080c, 0x2aac, 0x001e,
-       0x0070, 0x0156, 0x20a9, 0x007f, 0x2009, 0x0000, 0x080c, 0x4cdc,
-       0x1110, 0x080c, 0x493a, 0x8108, 0x1f04, 0x59d6, 0x015e, 0x2011,
-       0x0003, 0x080c, 0x7adf, 0x2011, 0x0002, 0x080c, 0x7ae9, 0x080c,
-       0x79e1, 0x080c, 0x6581, 0x0036, 0x2019, 0x0000, 0x080c, 0x7a64,
-       0x003e, 0x60e3, 0x0000, 0x2001, 0xad00, 0x2003, 0x0001, 0x080c,
-       0x569a, 0x00ee, 0x00ce, 0x004e, 0x003e, 0x002e, 0x001e, 0x015e,
-       0x0005, 0x2071, 0xade1, 0x7003, 0x0000, 0x7007, 0x0000, 0x700f,
-       0x0000, 0x702b, 0x0001, 0x704f, 0x0000, 0x7053, 0x0001, 0x705f,
-       0x0020, 0x7063, 0x0040, 0x7083, 0x0000, 0x708b, 0x0000, 0x708f,
-       0x0001, 0x70bf, 0x0000, 0x0005, 0x00e6, 0x2071, 0xade1, 0x6848,
-       0xa005, 0x1130, 0x7028, 0xc085, 0x702a, 0xa085, 0x0001, 0x0428,
-       0x6a50, 0x7236, 0x6b54, 0x733a, 0x6858, 0x703e, 0x707a, 0x685c,
-       0x7042, 0x707e, 0x6848, 0x702e, 0x6840, 0x7032, 0x2009, 0x000c,
-       0x200a, 0x8007, 0x8006, 0x8006, 0xa08c, 0x003f, 0xa084, 0xffc0,
-       0xa210, 0x2100, 0xa319, 0x7272, 0x7376, 0x7028, 0xc084, 0x702a,
-       0x7007, 0x0001, 0x700f, 0x0000, 0xa006, 0x00ee, 0x0005, 0x2b78,
-       0x2071, 0xade1, 0x7004, 0x0043, 0x700c, 0x0002, 0x5a5b, 0x5a52,
-       0x5a52, 0x5a52, 0x5a52, 0x0005, 0x5ab1, 0x5ab2, 0x5ae4, 0x5ae5,
-       0x5aaf, 0x5b33, 0x5b38, 0x5b69, 0x5b6a, 0x5b85, 0x5b86, 0x5b87,
-       0x5b88, 0x5b89, 0x5b8a, 0x5c40, 0x5c67, 0x700c, 0x0002, 0x5a74,
-       0x5aaf, 0x5aaf, 0x5ab0, 0x5ab0, 0x7830, 0x7930, 0xa106, 0x0120,
-       0x7830, 0x7930, 0xa106, 0x1510, 0x7030, 0xa10a, 0x01f8, 0x1210,
-       0x712c, 0xa10a, 0xa18a, 0x0002, 0x12d0, 0x080c, 0x15c0, 0x01b0,
-       0x2d00, 0x705a, 0x7063, 0x0040, 0x2001, 0x0003, 0x7057, 0x0000,
-       0x0126, 0x0006, 0x2091, 0x8000, 0x2009, 0xafec, 0x2104, 0xc085,
-       0x200a, 0x000e, 0x700e, 0x012e, 0x080c, 0x163c, 0x0005, 0x080c,
-       0x15c0, 0x0de0, 0x2d00, 0x705a, 0x080c, 0x15c0, 0x1108, 0x0c10,
-       0x2d00, 0x7086, 0x7063, 0x0080, 0x2001, 0x0004, 0x08f8, 0x0005,
-       0x0005, 0x0005, 0x700c, 0x0002, 0x5ab9, 0x5abc, 0x5aca, 0x5ae3,
-       0x5ae3, 0x080c, 0x5a6d, 0x0005, 0x0126, 0x8001, 0x700e, 0x7058,
-       0x0006, 0x080c, 0x5f90, 0x0120, 0x2091, 0x8000, 0x080c, 0x5a6d,
-       0x00de, 0x0048, 0x0126, 0x8001, 0x700e, 0x080c, 0x5f90, 0x7058,
-       0x2068, 0x7084, 0x705a, 0x6803, 0x0000, 0x6807, 0x0000, 0x6834,
-       0xa084, 0x00ff, 0xa08a, 0x003a, 0x1218, 0x00db, 0x012e, 0x0005,
-       0x012e, 0x080c, 0x5b8b, 0x0005, 0x0005, 0x0005, 0x00e6, 0x2071,
-       0xade1, 0x700c, 0x0002, 0x5af0, 0x5af0, 0x5af0, 0x5af2, 0x5af5,
-       0x00ee, 0x0005, 0x700f, 0x0001, 0x0010, 0x700f, 0x0002, 0x00ee,
-       0x0005, 0x5b8b, 0x5b8b, 0x5ba7, 0x5b8b, 0x5d22, 0x5b8b, 0x5b8b,
-       0x5b8b, 0x5b8b, 0x5b8b, 0x5ba7, 0x5d64, 0x5da7, 0x5df0, 0x5e04,
-       0x5b8b, 0x5b8b, 0x5bc3, 0x5ba7, 0x5b8b, 0x5b8b, 0x5c1d, 0x5ead,
-       0x5ec8, 0x5b8b, 0x5bc3, 0x5b8b, 0x5b8b, 0x5b8b, 0x5b8b, 0x5c13,
-       0x5ec8, 0x5b8b, 0x5b8b, 0x5b8b, 0x5b8b, 0x5b8b, 0x5b8b, 0x5b8b,
-       0x5b8b, 0x5b8b, 0x5bd7, 0x5b8b, 0x5b8b, 0x5b8b, 0x5b8b, 0x5b8b,
-       0x5b8b, 0x5b8b, 0x5b8b, 0x5b8b, 0x5b8b, 0x5b8b, 0x5b8b, 0x5b8b,
-       0x5b8b, 0x5b8b, 0x5bec, 0x7020, 0x2068, 0x080c, 0x15f0, 0x0005,
-       0x700c, 0x0002, 0x5b3f, 0x5b42, 0x5b50, 0x5b68, 0x5b68, 0x080c,
-       0x5a6d, 0x0005, 0x0126, 0x8001, 0x700e, 0x7058, 0x0006, 0x080c,
-       0x5f90, 0x0120, 0x2091, 0x8000, 0x080c, 0x5a6d, 0x00de, 0x0048,
-       0x0126, 0x8001, 0x700e, 0x080c, 0x5f90, 0x7058, 0x2068, 0x7084,
-       0x705a, 0x6803, 0x0000, 0x6807, 0x0000, 0x6834, 0xa084, 0x00ff,
-       0xa08a, 0x001a, 0x1218, 0x003b, 0x012e, 0x0005, 0x012e, 0x0419,
-       0x0005, 0x0005, 0x0005, 0x5b8b, 0x5ba7, 0x5d0e, 0x5b8b, 0x5ba7,
-       0x5b8b, 0x5ba7, 0x5ba7, 0x5b8b, 0x5ba7, 0x5d0e, 0x5ba7, 0x5ba7,
-       0x5ba7, 0x5ba7, 0x5ba7, 0x5b8b, 0x5ba7, 0x5d0e, 0x5b8b, 0x5b8b,
-       0x5ba7, 0x5b8b, 0x5b8b, 0x5b8b, 0x5ba7, 0x0005, 0x0005, 0x0005,
-       0x0005, 0x0005, 0x0005, 0x7007, 0x0001, 0x6838, 0xa084, 0x00ff,
-       0xc0d5, 0x683a, 0x0126, 0x2091, 0x8000, 0x080c, 0x510c, 0x012e,
-       0x0005, 0x7007, 0x0001, 0x6838, 0xa084, 0x00ff, 0xc0e5, 0x683a,
-       0x0126, 0x2091, 0x8000, 0x080c, 0x510c, 0x012e, 0x0005, 0x7007,
-       0x0001, 0x6838, 0xa084, 0x00ff, 0xc0ed, 0x683a, 0x0126, 0x2091,
-       0x8000, 0x080c, 0x510c, 0x012e, 0x0005, 0x7007, 0x0001, 0x6838,
-       0xa084, 0x00ff, 0xc0dd, 0x683a, 0x0126, 0x2091, 0x8000, 0x080c,
-       0x510c, 0x012e, 0x0005, 0x6834, 0x8007, 0xa084, 0x00ff, 0x0988,
-       0x8001, 0x1120, 0x7007, 0x0001, 0x0804, 0x5cd0, 0x7007, 0x0006,
-       0x7012, 0x2d00, 0x7016, 0x701a, 0x704b, 0x5cd0, 0x0005, 0x6834,
-       0x8007, 0xa084, 0x00ff, 0x0904, 0x5b99, 0x8001, 0x1120, 0x7007,
-       0x0001, 0x0804, 0x5ced, 0x7007, 0x0006, 0x7012, 0x2d00, 0x7016,
-       0x701a, 0x704b, 0x5ced, 0x0005, 0x6834, 0x8007, 0xa084, 0x00ff,
-       0xa086, 0x0001, 0x1904, 0x5b99, 0x7007, 0x0001, 0x2009, 0xad30,
-       0x210c, 0x81ff, 0x11a8, 0x6838, 0xa084, 0x00ff, 0x683a, 0x6853,
-       0x0000, 0x080c, 0x4ab1, 0x1108, 0x0005, 0x0126, 0x2091, 0x8000,
-       0x6837, 0x0139, 0x684a, 0x6952, 0x080c, 0x510c, 0x012e, 0x0ca0,
-       0x2001, 0x0028, 0x0c90, 0x684c, 0xa084, 0x00c0, 0xa086, 0x00c0,
-       0x1120, 0x7007, 0x0001, 0x0804, 0x5ee0, 0x2d00, 0x7016, 0x701a,
-       0x20a9, 0x0004, 0xa080, 0x0024, 0x2098, 0x20a1, 0xae0c, 0x53a3,
-       0x6858, 0x7012, 0xa082, 0x0401, 0x1a04, 0x5bb5, 0x6a84, 0xa28a,
-       0x0002, 0x1a04, 0x5bb5, 0x82ff, 0x1138, 0x6888, 0x698c, 0xa105,
-       0x0118, 0x2001, 0x5ca3, 0x0018, 0xa280, 0x5c99, 0x2005, 0x70c6,
-       0x7010, 0xa015, 0x0904, 0x5c85, 0x080c, 0x15c0, 0x1118, 0x7007,
-       0x000f, 0x0005, 0x2d00, 0x7022, 0x70c4, 0x2060, 0x2c05, 0x6836,
-       0xe004, 0xad00, 0x7096, 0xe008, 0xa20a, 0x1210, 0xa00e, 0x2200,
-       0x7112, 0xe20c, 0x8003, 0x800b, 0xa296, 0x0004, 0x0108, 0xa108,
-       0x719a, 0x810b, 0x719e, 0xae90, 0x0022, 0x080c, 0x1624, 0x7090,
-       0xa08e, 0x0100, 0x0170, 0xa086, 0x0200, 0x0118, 0x7007, 0x0010,
-       0x0005, 0x7020, 0x2068, 0x080c, 0x15f0, 0x7014, 0x2068, 0x0804,
-       0x5bb5, 0x7020, 0x2068, 0x7018, 0x6802, 0x6807, 0x0000, 0x2d08,
-       0x2068, 0x6906, 0x711a, 0x0804, 0x5c40, 0x7014, 0x2068, 0x7007,
-       0x0001, 0x6884, 0xa005, 0x1128, 0x6888, 0x698c, 0xa105, 0x0108,
-       0x00b1, 0x6834, 0xa084, 0x00ff, 0xa086, 0x001e, 0x0904, 0x5ee0,
-       0x04b8, 0x5c9b, 0x5c9f, 0x0002, 0x0011, 0x0007, 0x0004, 0x000a,
-       0x000f, 0x0005, 0x0006, 0x000a, 0x0011, 0x0005, 0x0004, 0x00f6,
-       0x00e6, 0x00c6, 0x0076, 0x0066, 0x6f88, 0x6e8c, 0x6804, 0x2060,
-       0xacf0, 0x0021, 0xacf8, 0x0027, 0x2009, 0x0005, 0x700c, 0x7816,
-       0x7008, 0x7812, 0x7004, 0x7806, 0x7000, 0x7802, 0x7e0e, 0x7f0a,
-       0x8109, 0x0128, 0xaef2, 0x0004, 0xaffa, 0x0006, 0x0c78, 0x6004,
-       0xa065, 0x1d30, 0x006e, 0x007e, 0x00ce, 0x00ee, 0x00fe, 0x0005,
-       0x2009, 0xad30, 0x210c, 0x81ff, 0x1198, 0x6838, 0xa084, 0x00ff,
-       0x683a, 0x080c, 0x4993, 0x1108, 0x0005, 0x080c, 0x51df, 0x0126,
-       0x2091, 0x8000, 0x080c, 0x97fd, 0x080c, 0x510c, 0x012e, 0x0ca0,
-       0x2001, 0x0028, 0x2009, 0x0000, 0x0c80, 0x2009, 0xad30, 0x210c,
-       0x81ff, 0x11b0, 0x6858, 0xa005, 0x01b0, 0x6838, 0xa084, 0x00ff,
-       0x683a, 0x6853, 0x0000, 0x080c, 0x4a55, 0x1108, 0x0005, 0x0126,
-       0x2091, 0x8000, 0x080c, 0x51df, 0x080c, 0x510c, 0x012e, 0x0cb0,
-       0x2001, 0x0028, 0x0ca0, 0x2001, 0x0000, 0x0c88, 0x7018, 0x6802,
-       0x2d08, 0x2068, 0x6906, 0x711a, 0x7010, 0x8001, 0x7012, 0x0118,
-       0x7007, 0x0006, 0x0030, 0x7014, 0x2068, 0x7007, 0x0001, 0x7048,
-       0x080f, 0x0005, 0x7007, 0x0001, 0x6944, 0x810f, 0xa18c, 0x00ff,
-       0x6848, 0xa084, 0x00ff, 0x20a9, 0x0001, 0xa096, 0x0001, 0x01b0,
-       0x2009, 0x0000, 0x20a9, 0x00ff, 0xa096, 0x0002, 0x0178, 0xa005,
-       0x11f0, 0x6944, 0x810f, 0xa18c, 0x00ff, 0x080c, 0x4cdc, 0x11b8,
-       0x0066, 0x6e50, 0x080c, 0x4dcf, 0x006e, 0x0088, 0x0046, 0x2011,
-       0xad0c, 0x2224, 0xc484, 0x2412, 0x004e, 0x00c6, 0x080c, 0x4cdc,
-       0x1110, 0x080c, 0x4f2d, 0x8108, 0x1f04, 0x5d4e, 0x00ce, 0x684c,
-       0xd084, 0x1118, 0x080c, 0x15f0, 0x0005, 0x0126, 0x2091, 0x8000,
-       0x080c, 0x510c, 0x012e, 0x0005, 0x0126, 0x2091, 0x8000, 0x7007,
-       0x0001, 0x2001, 0xad52, 0x2004, 0xd0a4, 0x0580, 0x2061, 0xb048,
-       0x6100, 0xd184, 0x0178, 0x6858, 0xa084, 0x00ff, 0x1550, 0x6000,
-       0xd084, 0x0520, 0x6004, 0xa005, 0x1538, 0x6003, 0x0000, 0x600b,
-       0x0000, 0x00c8, 0x2011, 0x0001, 0x6860, 0xa005, 0x1110, 0x2001,
-       0x001e, 0x8000, 0x6016, 0x6858, 0xa084, 0x00ff, 0x0178, 0x6006,
-       0x6858, 0x8007, 0xa084, 0x00ff, 0x0148, 0x600a, 0x6858, 0x8000,
-       0x1108, 0xc28d, 0x6202, 0x012e, 0x0804, 0x5f7f, 0x012e, 0x0804,
-       0x5f79, 0x012e, 0x0804, 0x5f73, 0x012e, 0x0804, 0x5f76, 0x0126,
-       0x2091, 0x8000, 0x7007, 0x0001, 0x2001, 0xad52, 0x2004, 0xd0a4,
-       0x05e0, 0x2061, 0xb048, 0x6000, 0xd084, 0x05b8, 0x6204, 0x6308,
-       0xd08c, 0x1530, 0x6c48, 0xa484, 0x0003, 0x0170, 0x6958, 0xa18c,
-       0x00ff, 0x8001, 0x1120, 0x2100, 0xa210, 0x0620, 0x0028, 0x8001,
-       0x1508, 0x2100, 0xa212, 0x02f0, 0xa484, 0x000c, 0x0188, 0x6958,
-       0x810f, 0xa18c, 0x00ff, 0xa082, 0x0004, 0x1120, 0x2100, 0xa318,
-       0x0288, 0x0030, 0xa082, 0x0004, 0x1168, 0x2100, 0xa31a, 0x0250,
-       0x6860, 0xa005, 0x0110, 0x8000, 0x6016, 0x6206, 0x630a, 0x012e,
-       0x0804, 0x5f7f, 0x012e, 0x0804, 0x5f7c, 0x012e, 0x0804, 0x5f79,
-       0x0126, 0x2091, 0x8000, 0x7007, 0x0001, 0x2061, 0xb048, 0x6300,
-       0xd38c, 0x1120, 0x6308, 0x8318, 0x0220, 0x630a, 0x012e, 0x0804,
-       0x5f8d, 0x012e, 0x0804, 0x5f7c, 0x0126, 0x00c6, 0x2091, 0x8000,
-       0x7007, 0x0001, 0x684c, 0xd0ac, 0x0148, 0x00c6, 0x2061, 0xb048,
-       0x6000, 0xa084, 0xfcff, 0x6002, 0x00ce, 0x0448, 0x6858, 0xa005,
-       0x05d0, 0x685c, 0xa065, 0x0598, 0x2001, 0xad30, 0x2004, 0xa005,
-       0x0118, 0x080c, 0x974e, 0x0068, 0x6013, 0x0400, 0x6057, 0x0000,
-       0x694c, 0xd1a4, 0x0110, 0x6950, 0x6156, 0x2009, 0x0041, 0x080c,
-       0x80a7, 0x6958, 0xa18c, 0xff00, 0xa186, 0x2000, 0x1140, 0x0026,
-       0x2009, 0x0000, 0x2011, 0xfdff, 0x080c, 0x663f, 0x002e, 0x684c,
-       0xd0c4, 0x0148, 0x2061, 0xb048, 0x6000, 0xd08c, 0x1120, 0x6008,
-       0x8000, 0x0208, 0x600a, 0x00ce, 0x012e, 0x0804, 0x5f7f, 0x00ce,
-       0x012e, 0x0804, 0x5f79, 0x6954, 0xa186, 0x002e, 0x0d40, 0xa186,
-       0x002d, 0x0d28, 0xa186, 0x0045, 0x0510, 0xa186, 0x002a, 0x1130,
-       0x2001, 0xad0c, 0x200c, 0xc194, 0x2102, 0x08c8, 0xa186, 0x0020,
-       0x0170, 0xa186, 0x0029, 0x1d18, 0x6944, 0xa18c, 0xff00, 0x810f,
-       0x080c, 0x4cdc, 0x1960, 0x6000, 0xc0e4, 0x6002, 0x0840, 0x685c,
-       0xa065, 0x09a8, 0x2001, 0xafa3, 0x2004, 0x6016, 0x0800, 0x685c,
-       0xa065, 0x0968, 0x00e6, 0x6860, 0xa075, 0x2001, 0xad30, 0x2004,
-       0xa005, 0x0150, 0x080c, 0x974e, 0x8eff, 0x0118, 0x2e60, 0x080c,
-       0x974e, 0x00ee, 0x0804, 0x5e3f, 0x6020, 0xc0dc, 0xc0d5, 0x6022,
-       0x2e60, 0x6007, 0x003a, 0x6870, 0xa005, 0x0130, 0x6007, 0x003b,
-       0x6874, 0x602a, 0x6878, 0x6012, 0x6003, 0x0001, 0x080c, 0x67a8,
-       0x080c, 0x6c50, 0x00ee, 0x0804, 0x5e3f, 0x2061, 0xb048, 0x6000,
-       0xd084, 0x0190, 0xd08c, 0x1904, 0x5f8d, 0x0126, 0x2091, 0x8000,
-       0x6204, 0x8210, 0x0220, 0x6206, 0x012e, 0x0804, 0x5f8d, 0x012e,
-       0x6853, 0x0016, 0x0804, 0x5f86, 0x6853, 0x0007, 0x0804, 0x5f86,
-       0x6834, 0x8007, 0xa084, 0x00ff, 0x1118, 0x080c, 0x5b99, 0x0078,
-       0x2030, 0x8001, 0x1120, 0x7007, 0x0001, 0x0051, 0x0040, 0x7007,
-       0x0006, 0x7012, 0x2d00, 0x7016, 0x701a, 0x704b, 0x5ee0, 0x0005,
-       0x00e6, 0x0126, 0x2091, 0x8000, 0x2009, 0xad30, 0x210c, 0x81ff,
-       0x1904, 0x5f5b, 0x2009, 0xad0c, 0x210c, 0xd194, 0x1904, 0x5f63,
-       0x6848, 0x2070, 0xae82, 0xb400, 0x0a04, 0x5f4f, 0x2001, 0xad16,
-       0x2004, 0xae02, 0x1a04, 0x5f4f, 0x2061, 0xb048, 0x6100, 0xa184,
-       0x0301, 0xa086, 0x0001, 0x15a8, 0x711c, 0xa186, 0x0006, 0x15b0,
-       0x7018, 0xa005, 0x0904, 0x5f5b, 0x2004, 0xd0e4, 0x1904, 0x5f5e,
-       0x7020, 0xd0dc, 0x1904, 0x5f66, 0x6853, 0x0000, 0x6803, 0x0000,
-       0x2d08, 0x7010, 0xa005, 0x1158, 0x7112, 0x684c, 0xd0f4, 0x1904,
-       0x5f69, 0x2e60, 0x080c, 0x65aa, 0x012e, 0x00ee, 0x0005, 0x2068,
-       0x6800, 0xa005, 0x1de0, 0x6902, 0x2168, 0x684c, 0xd0f4, 0x15c8,
-       0x012e, 0x00ee, 0x0005, 0x012e, 0x00ee, 0x6853, 0x0006, 0x0804,
-       0x5f86, 0xd184, 0x0dc0, 0xd1c4, 0x11a8, 0x00b8, 0x6944, 0xa18c,
-       0xff00, 0x810f, 0x080c, 0x4cdc, 0x11c8, 0x6000, 0xd0e4, 0x11b0,
-       0x711c, 0xa186, 0x0007, 0x1118, 0x6853, 0x0002, 0x0088, 0x6853,
-       0x0008, 0x0070, 0x6853, 0x000e, 0x0058, 0x6853, 0x0017, 0x0040,
-       0x6853, 0x0035, 0x0028, 0x6853, 0x0028, 0x0010, 0x6853, 0x0029,
-       0x012e, 0x00ee, 0x0418, 0x6853, 0x002a, 0x0cd0, 0x6853, 0x0045,
-       0x0cb8, 0x2e60, 0x2019, 0x0002, 0x6017, 0x0014, 0x080c, 0xa566,
-       0x012e, 0x00ee, 0x0005, 0x2009, 0x003e, 0x0058, 0x2009, 0x0004,
-       0x0040, 0x2009, 0x0006, 0x0028, 0x2009, 0x0016, 0x0010, 0x2009,
-       0x0001, 0x6854, 0xa084, 0xff00, 0xa105, 0x6856, 0x0126, 0x2091,
-       0x8000, 0x080c, 0x510c, 0x012e, 0x0005, 0x080c, 0x15f0, 0x0005,
-       0x702c, 0x7130, 0x8108, 0xa102, 0x0230, 0xa00e, 0x7034, 0x7072,
-       0x7038, 0x7076, 0x0058, 0x7070, 0xa080, 0x0040, 0x7072, 0x1230,
-       0x7074, 0xa081, 0x0000, 0x7076, 0xa085, 0x0001, 0x7932, 0x7132,
-       0x0005, 0x00d6, 0x080c, 0x65a1, 0x00de, 0x0005, 0x00d6, 0x2011,
-       0x0004, 0x2204, 0xa085, 0x8002, 0x2012, 0x00de, 0x0005, 0x20e1,
-       0x0002, 0x3d08, 0x20e1, 0x2000, 0x3d00, 0xa084, 0x7000, 0x0118,
-       0xa086, 0x1000, 0x1540, 0x20e1, 0x0000, 0x3d00, 0xa094, 0xff00,
-       0x8217, 0xa084, 0xf000, 0xa086, 0x3000, 0x1118, 0x080c, 0x61c6,
-       0x00b0, 0x20e1, 0x0004, 0x3d60, 0xd1bc, 0x1108, 0x3e60, 0xac84,
-       0x0007, 0x1188, 0xac82, 0xb400, 0x0270, 0x6858, 0xac02, 0x1258,
-       0x6120, 0xd1f4, 0x1160, 0x2009, 0x0047, 0x080c, 0x80a7, 0x7a1c,
-       0xd284, 0x1968, 0x0005, 0xa016, 0x080c, 0x1824, 0x0cc0, 0x0cd8,
-       0x781c, 0xd08c, 0x0500, 0x0156, 0x0136, 0x0146, 0x20e1, 0x3000,
-       0x3d20, 0x3e28, 0xa584, 0x0076, 0x1530, 0xa484, 0x7000, 0xa086,
-       0x1000, 0x11a8, 0x080c, 0x604e, 0x01f0, 0x20e1, 0x3000, 0x7828,
-       0x7828, 0x080c, 0x606a, 0x014e, 0x013e, 0x015e, 0x2009, 0xafcf,
-       0x2104, 0xa005, 0x1108, 0x0005, 0x080c, 0x6c50, 0x0ce0, 0xa484,
-       0x7000, 0x1518, 0x0499, 0x01b8, 0x7000, 0xa084, 0xff00, 0xa086,
-       0x8100, 0x0d18, 0x0080, 0xd5a4, 0x0158, 0x080c, 0x1d86, 0x20e1,
-       0x9010, 0x2001, 0x0160, 0x2502, 0x2001, 0x0138, 0x2202, 0x0048,
-       0x00e9, 0x6883, 0x0000, 0x080c, 0xac59, 0x20e1, 0x3000, 0x7828,
-       0x7828, 0x014e, 0x013e, 0x015e, 0x08b0, 0x0081, 0x1130, 0x7000,
-       0xa084, 0xff00, 0xa086, 0x8100, 0x1d70, 0x080c, 0xac59, 0x20e1,
-       0x3000, 0x7828, 0x7828, 0x080c, 0x642d, 0x0c58, 0xa484, 0x01ff,
-       0x6882, 0xa005, 0x0160, 0xa080, 0x001f, 0xa084, 0x03f8, 0x80ac,
-       0x20e1, 0x1000, 0x2ea0, 0x2099, 0x020a, 0x53a5, 0x0005, 0x20a9,
-       0x000c, 0x20e1, 0x1000, 0x2ea0, 0x2099, 0x020a, 0x53a5, 0xa085,
-       0x0001, 0x0ca0, 0x7000, 0xa084, 0xff00, 0xa08c, 0xf000, 0x8007,
-       0xa196, 0x0000, 0x1118, 0x0804, 0x62cf, 0x0005, 0xa196, 0x2000,
-       0x1148, 0x6900, 0xa18e, 0x0001, 0x1118, 0x080c, 0x41d1, 0x0ca8,
-       0x0039, 0x0c98, 0xa196, 0x8000, 0x1d80, 0x080c, 0x6372, 0x0c68,
-       0x00c6, 0x6a80, 0x82ff, 0x0904, 0x61c0, 0x7110, 0xa18c, 0xff00,
-       0x810f, 0xa196, 0x0001, 0x0120, 0xa196, 0x0023, 0x1904, 0x61c0,
-       0xa08e, 0x0023, 0x1570, 0x080c, 0x6408, 0x0904, 0x61c0, 0x7124,
-       0x610a, 0x7030, 0xa08e, 0x0200, 0x1150, 0x7034, 0xa005, 0x1904,
-       0x61c0, 0x2009, 0x0015, 0x080c, 0x80a7, 0x0804, 0x61c0, 0xa08e,
-       0x0214, 0x0118, 0xa08e, 0x0210, 0x1130, 0x2009, 0x0015, 0x080c,
-       0x80a7, 0x0804, 0x61c0, 0xa08e, 0x0100, 0x1904, 0x61c0, 0x7034,
-       0xa005, 0x1904, 0x61c0, 0x2009, 0x0016, 0x080c, 0x80a7, 0x0804,
-       0x61c0, 0xa08e, 0x0022, 0x1904, 0x61c0, 0x7030, 0xa08e, 0x0300,
-       0x1580, 0x68d0, 0xd0a4, 0x0528, 0xc0b5, 0x68d2, 0x7100, 0xa18c,
-       0x00ff, 0x696e, 0x7004, 0x6872, 0x00f6, 0x2079, 0x0100, 0x79e6,
-       0x78ea, 0x0006, 0xa084, 0x00ff, 0x0016, 0x2008, 0x080c, 0x26a0,
-       0x7932, 0x7936, 0x001e, 0x000e, 0x00fe, 0x080c, 0x2676, 0x694e,
-       0x703c, 0x00e6, 0x2071, 0x0140, 0x7086, 0x2071, 0xad00, 0x70a2,
-       0x00ee, 0x7034, 0xa005, 0x1904, 0x61c0, 0x2009, 0x0017, 0x0804,
-       0x6193, 0xa08e, 0x0400, 0x1158, 0x7034, 0xa005, 0x1904, 0x61c0,
-       0x68d0, 0xc0a5, 0x68d2, 0x2009, 0x0030, 0x0804, 0x6193, 0xa08e,
-       0x0500, 0x1140, 0x7034, 0xa005, 0x1904, 0x61c0, 0x2009, 0x0018,
-       0x0804, 0x6193, 0xa08e, 0x2010, 0x1120, 0x2009, 0x0019, 0x0804,
-       0x6193, 0xa08e, 0x2110, 0x1120, 0x2009, 0x001a, 0x0804, 0x6193,
-       0xa08e, 0x5200, 0x1140, 0x7034, 0xa005, 0x1904, 0x61c0, 0x2009,
-       0x001b, 0x0804, 0x6193, 0xa08e, 0x5000, 0x1140, 0x7034, 0xa005,
-       0x1904, 0x61c0, 0x2009, 0x001c, 0x0804, 0x6193, 0xa08e, 0x1300,
-       0x1120, 0x2009, 0x0034, 0x0804, 0x6193, 0xa08e, 0x1200, 0x1140,
-       0x7034, 0xa005, 0x1904, 0x61c0, 0x2009, 0x0024, 0x0804, 0x6193,
-       0xa08c, 0xff00, 0xa18e, 0x2400, 0x1118, 0x2009, 0x002d, 0x04d8,
-       0xa08c, 0xff00, 0xa18e, 0x5300, 0x1118, 0x2009, 0x002a, 0x0498,
-       0xa08e, 0x0f00, 0x1118, 0x2009, 0x0020, 0x0468, 0xa08e, 0x5300,
-       0x1108, 0x00d8, 0xa08e, 0x6104, 0x11c0, 0x2011, 0xb28d, 0x8208,
-       0x2204, 0xa082, 0x0004, 0x20a8, 0x95ac, 0x95ac, 0x2011, 0x8015,
-       0x211c, 0x8108, 0x0046, 0x2124, 0x080c, 0x3c5c, 0x004e, 0x8108,
-       0x1f04, 0x6176, 0x2009, 0x0023, 0x0070, 0xa08e, 0x6000, 0x1118,
-       0x2009, 0x003f, 0x0040, 0xa08e, 0x7800, 0x1118, 0x2009, 0x0045,
-       0x0010, 0x2009, 0x001d, 0x0016, 0x2011, 0xb283, 0x2204, 0x8211,
-       0x220c, 0x080c, 0x2676, 0x1530, 0x080c, 0x4c80, 0x1518, 0x6612,
-       0x6516, 0x86ff, 0x0180, 0x001e, 0x0016, 0xa186, 0x0017, 0x1158,
-       0x686c, 0xa606, 0x1140, 0x6870, 0xa506, 0xa084, 0xff00, 0x1118,
-       0x6000, 0xc0f5, 0x6002, 0x00c6, 0x080c, 0x8022, 0x0168, 0x001e,
-       0x611a, 0x601f, 0x0004, 0x7120, 0x610a, 0x001e, 0x080c, 0x80a7,
-       0x00ce, 0x0005, 0x001e, 0x0ce0, 0x00ce, 0x0ce0, 0x00c6, 0x0046,
-       0x080c, 0x6221, 0x1904, 0x621e, 0xa184, 0xff00, 0x8007, 0xa086,
-       0x0008, 0x1904, 0x621e, 0xa28e, 0x0033, 0x11e8, 0x080c, 0x6408,
-       0x0904, 0x621e, 0x7124, 0x610a, 0x7030, 0xa08e, 0x0200, 0x1140,
-       0x7034, 0xa005, 0x15d8, 0x2009, 0x0015, 0x080c, 0x80a7, 0x04b0,
-       0xa08e, 0x0100, 0x1598, 0x7034, 0xa005, 0x1580, 0x2009, 0x0016,
-       0x080c, 0x80a7, 0x0458, 0xa28e, 0x0032, 0x1540, 0x7030, 0xa08e,
-       0x1400, 0x1520, 0x2009, 0x0038, 0x0016, 0x2011, 0xb283, 0x2204,
-       0x8211, 0x220c, 0x080c, 0x2676, 0x11c0, 0x080c, 0x4c80, 0x11a8,
-       0x6612, 0x6516, 0x00c6, 0x080c, 0x8022, 0x0170, 0x001e, 0x611a,
-       0x080c, 0x9956, 0x601f, 0x0004, 0x7120, 0x610a, 0x001e, 0x080c,
-       0x80a7, 0x080c, 0x6c50, 0x0010, 0x00ce, 0x001e, 0x004e, 0x00ce,
-       0x0005, 0x00f6, 0x00d6, 0x0026, 0x0016, 0x0136, 0x0146, 0x0156,
-       0x3c00, 0x0006, 0x2079, 0x0030, 0x2069, 0x0200, 0x080c, 0x1df2,
-       0x1590, 0x080c, 0x1ce2, 0x05c8, 0x04d9, 0x1130, 0x7908, 0xa18c,
-       0x1fff, 0xa182, 0x0011, 0x1688, 0x20a9, 0x000c, 0x20e1, 0x0000,
-       0x2ea0, 0x2099, 0x020a, 0x53a5, 0x20e1, 0x2000, 0x2001, 0x020a,
-       0x2004, 0x7a0c, 0x7808, 0xa080, 0x0007, 0xa084, 0x1ff8, 0x0401,
-       0x1120, 0xa08a, 0x0140, 0x1a0c, 0x14f6, 0x80ac, 0x20e1, 0x6000,
-       0x2099, 0x020a, 0x53a5, 0x20e1, 0x7000, 0x6828, 0x6828, 0x7803,
-       0x0004, 0xa294, 0x0070, 0x000e, 0x20e0, 0x015e, 0x014e, 0x013e,
-       0x001e, 0x002e, 0x00de, 0x00fe, 0x0005, 0xa085, 0x0001, 0x0c98,
-       0x0006, 0x2001, 0x0111, 0x2004, 0xa084, 0x0003, 0x000e, 0x0005,
-       0x0046, 0x00e6, 0x00d6, 0x2028, 0x2130, 0xa696, 0x00ff, 0x1198,
-       0xa596, 0xfffd, 0x1120, 0x2009, 0x007f, 0x0804, 0x62ca, 0xa596,
-       0xfffe, 0x1118, 0x2009, 0x007e, 0x04e8, 0xa596, 0xfffc, 0x1118,
-       0x2009, 0x0080, 0x04b8, 0x2011, 0x0000, 0x2019, 0xad34, 0x231c,
-       0xd3ac, 0x0138, 0x2021, 0x0000, 0x20a9, 0x00ff, 0x2071, 0xae34,
-       0x0030, 0x2021, 0x0081, 0x20a9, 0x007e, 0x2071, 0xaeb5, 0x2e1c,
-       0x83ff, 0x1128, 0x82ff, 0x1198, 0x2410, 0xc2fd, 0x0080, 0x2368,
-       0x6f10, 0x0006, 0x2100, 0xa706, 0x000e, 0x6b14, 0x1120, 0xa346,
-       0x1110, 0x2408, 0x0078, 0x87ff, 0x1110, 0x83ff, 0x0d58, 0x8420,
-       0x8e70, 0x1f04, 0x62a7, 0x82ff, 0x1118, 0xa085, 0x0001, 0x0018,
-       0xc2fc, 0x2208, 0xa006, 0x00de, 0x00ee, 0x004e, 0x0005, 0xa084,
-       0x0007, 0x000a, 0x0005, 0x62db, 0x62db, 0x62db, 0x641a, 0x62db,
-       0x62dc, 0x62f1, 0x635d, 0x0005, 0x7110, 0xd1bc, 0x0188, 0x7120,
-       0x2160, 0xac8c, 0x0007, 0x1160, 0xac8a, 0xb400, 0x0248, 0x6858,
-       0xac02, 0x1230, 0x7124, 0x610a, 0x2009, 0x0046, 0x080c, 0x80a7,
-       0x0005, 0x00c6, 0x7110, 0xd1bc, 0x1904, 0x6344, 0x2011, 0xb283,
-       0x2204, 0x8211, 0x220c, 0x080c, 0x2676, 0x1904, 0x6344, 0x080c,
-       0x4c80, 0x1904, 0x6344, 0x6612, 0x6516, 0x6000, 0xd0ec, 0x15e0,
-       0x6204, 0xa294, 0xff00, 0x8217, 0xa286, 0x0006, 0x0160, 0x080c,
-       0x574f, 0x11d0, 0x6204, 0xa294, 0x00ff, 0xa286, 0x0006, 0x11a0,
-       0xa295, 0x0600, 0x6206, 0x00c6, 0x080c, 0x8022, 0x001e, 0x0530,
-       0x611a, 0x601f, 0x0006, 0x7120, 0x610a, 0x7130, 0x6152, 0x2009,
-       0x0044, 0x080c, 0x80a7, 0x00c0, 0x00c6, 0x080c, 0x8022, 0x001e,
-       0x0198, 0x611a, 0x601f, 0x0004, 0x7120, 0x610a, 0xa286, 0x0004,
-       0x1118, 0x6007, 0x0005, 0x0010, 0x6007, 0x0001, 0x6003, 0x0001,
-       0x080c, 0x67ee, 0x080c, 0x6c50, 0x00ce, 0x0005, 0x00c6, 0x080c,
-       0x9807, 0x001e, 0x0dc8, 0x611a, 0x601f, 0x0006, 0x7120, 0x610a,
-       0x7130, 0x6152, 0x6013, 0x0300, 0x6003, 0x0001, 0x6007, 0x0041,
-       0x080c, 0x67a8, 0x080c, 0x6c50, 0x0c38, 0x7110, 0xd1bc, 0x0188,
-       0x7020, 0x2060, 0xac84, 0x0007, 0x1160, 0xac82, 0xb400, 0x0248,
-       0x6858, 0xac02, 0x1230, 0x7124, 0x610a, 0x2009, 0x0045, 0x080c,
-       0x80a7, 0x0005, 0x7110, 0xa18c, 0xff00, 0x810f, 0xa18e, 0x0000,
-       0x1130, 0xa084, 0x000f, 0xa08a, 0x0006, 0x1208, 0x000b, 0x0005,
-       0x6386, 0x6387, 0x6386, 0x6386, 0x63f0, 0x63fc, 0x0005, 0x7110,
-       0xd1bc, 0x0120, 0x702c, 0xd084, 0x0904, 0x63ef, 0x700c, 0x7108,
-       0x080c, 0x2676, 0x1904, 0x63ef, 0x080c, 0x4c80, 0x1904, 0x63ef,
-       0x6612, 0x6516, 0x6204, 0x7110, 0xd1bc, 0x01f8, 0xa28c, 0x00ff,
-       0xa186, 0x0004, 0x0118, 0xa186, 0x0006, 0x15c8, 0x00c6, 0x080c,
-       0x6408, 0x00ce, 0x0904, 0x63ef, 0x00c6, 0x080c, 0x8022, 0x001e,
-       0x05f0, 0x611a, 0x080c, 0x9956, 0x601f, 0x0002, 0x7120, 0x610a,
-       0x2009, 0x0088, 0x080c, 0x80a7, 0x0490, 0xa28c, 0x00ff, 0xa186,
-       0x0006, 0x0160, 0xa186, 0x0004, 0x0148, 0xa294, 0xff00, 0x8217,
-       0xa286, 0x0004, 0x0118, 0xa286, 0x0006, 0x1188, 0x00c6, 0x080c,
-       0x8022, 0x001e, 0x01e0, 0x611a, 0x080c, 0x9956, 0x601f, 0x0005,
-       0x7120, 0x610a, 0x2009, 0x0088, 0x080c, 0x80a7, 0x0080, 0x00c6,
-       0x080c, 0x8022, 0x001e, 0x0158, 0x611a, 0x080c, 0x9956, 0x601f,
-       0x0004, 0x7120, 0x610a, 0x2009, 0x0001, 0x080c, 0x80a7, 0x0005,
-       0x7110, 0xd1bc, 0x0140, 0x00a1, 0x0130, 0x7124, 0x610a, 0x2009,
-       0x0089, 0x080c, 0x80a7, 0x0005, 0x7110, 0xd1bc, 0x0140, 0x0041,
-       0x0130, 0x7124, 0x610a, 0x2009, 0x008a, 0x080c, 0x80a7, 0x0005,
-       0x7020, 0x2060, 0xac84, 0x0007, 0x1158, 0xac82, 0xb400, 0x0240,
-       0x2001, 0xad16, 0x2004, 0xac02, 0x1218, 0xa085, 0x0001, 0x0005,
-       0xa006, 0x0ce8, 0x7110, 0xd1bc, 0x1178, 0x7024, 0x2060, 0xac84,
-       0x0007, 0x1150, 0xac82, 0xb400, 0x0238, 0x6858, 0xac02, 0x1220,
-       0x2009, 0x0051, 0x080c, 0x80a7, 0x0005, 0x2031, 0x0105, 0x0069,
-       0x0005, 0x2031, 0x0206, 0x0049, 0x0005, 0x2031, 0x0207, 0x0029,
-       0x0005, 0x2031, 0x0213, 0x0009, 0x0005, 0x00c6, 0x00d6, 0x00f6,
-       0x7000, 0xa084, 0xf000, 0xa086, 0xc000, 0x05b0, 0x080c, 0x8022,
-       0x0598, 0x0066, 0x00c6, 0x0046, 0x2011, 0xb283, 0x2204, 0x8211,
-       0x220c, 0x080c, 0x2676, 0x1580, 0x080c, 0x4c80, 0x1568, 0x6612,
-       0x6516, 0x2c00, 0x004e, 0x00ce, 0x601a, 0x080c, 0x9956, 0x080c,
-       0x15d9, 0x01f0, 0x2d00, 0x6056, 0x6803, 0x0000, 0x6837, 0x0000,
-       0x6c3a, 0xadf8, 0x000f, 0x20a9, 0x000e, 0x2fa0, 0x2e98, 0x53a3,
-       0x006e, 0x6612, 0x6007, 0x003e, 0x601f, 0x0001, 0x6003, 0x0001,
-       0x080c, 0x67ee, 0x080c, 0x6c50, 0x00fe, 0x00de, 0x00ce, 0x0005,
-       0x080c, 0x8078, 0x006e, 0x0cc0, 0x004e, 0x00ce, 0x0cc8, 0x2071,
-       0xafda, 0x7003, 0x0003, 0x700f, 0x0361, 0xa006, 0x701a, 0x7012,
-       0x7017, 0xb400, 0x7007, 0x0000, 0x7026, 0x702b, 0x7841, 0x7032,
-       0x7037, 0x789d, 0x703b, 0xffff, 0x703f, 0xffff, 0x7042, 0x7047,
-       0x41b3, 0x0005, 0x2071, 0xafda, 0x1d04, 0x64fc, 0x2091, 0x6000,
-       0x700c, 0x8001, 0x700e, 0x1180, 0x700f, 0x0361, 0x7007, 0x0001,
-       0x0126, 0x2091, 0x8000, 0x7040, 0xa00d, 0x0148, 0x8109, 0x7142,
-       0x1130, 0x7044, 0x080f, 0x0018, 0x0126, 0x2091, 0x8000, 0x7024,
-       0xa00d, 0x0188, 0x7020, 0x8001, 0x7022, 0x1168, 0x7023, 0x0009,
-       0x8109, 0x7126, 0xa186, 0x03e8, 0x1110, 0x7028, 0x080f, 0x81ff,
-       0x1110, 0x7028, 0x080f, 0x7030, 0xa00d, 0x0158, 0x702c, 0x8001,
-       0x702e, 0x1138, 0x702f, 0x0009, 0x8109, 0x7132, 0x1110, 0x7034,
-       0x080f, 0x7038, 0xa005, 0x0118, 0x0310, 0x8001, 0x703a, 0x703c,
-       0xa005, 0x0118, 0x0310, 0x8001, 0x703e, 0x7018, 0xa00d, 0x0158,
-       0x7008, 0x8001, 0x700a, 0x1138, 0x700b, 0x0009, 0x8109, 0x711a,
-       0x1110, 0x701c, 0x080f, 0x012e, 0x7004, 0x0002, 0x6522, 0x6523,
-       0x653b, 0x00e6, 0x2071, 0xafda, 0x7018, 0xa005, 0x1120, 0x711a,
-       0x721e, 0x700b, 0x0009, 0x00ee, 0x0005, 0x00e6, 0x0006, 0x2071,
-       0xafda, 0x701c, 0xa206, 0x1110, 0x701a, 0x701e, 0x000e, 0x00ee,
-       0x0005, 0x00e6, 0x2071, 0xafda, 0x6088, 0xa102, 0x0208, 0x618a,
-       0x00ee, 0x0005, 0x0005, 0x7110, 0x080c, 0x4cdc, 0x1158, 0x6088,
-       0x8001, 0x0240, 0x608a, 0x1130, 0x0126, 0x2091, 0x8000, 0x080c,
-       0x6c50, 0x012e, 0x8108, 0xa182, 0x00ff, 0x0218, 0xa00e, 0x7007,
-       0x0002, 0x7112, 0x0005, 0x7014, 0x2060, 0x0126, 0x2091, 0x8000,
-       0x603c, 0xa005, 0x0128, 0x8001, 0x603e, 0x1110, 0x080c, 0x9846,
-       0x6014, 0xa005, 0x0500, 0x8001, 0x6016, 0x11e8, 0x611c, 0xa186,
-       0x0003, 0x0118, 0xa186, 0x0006, 0x11a0, 0x6010, 0x2068, 0x6854,
-       0xa08a, 0x199a, 0x0270, 0xa082, 0x1999, 0x6856, 0xa08a, 0x199a,
-       0x0210, 0x2001, 0x1999, 0x8003, 0x800b, 0x810b, 0xa108, 0x6116,
-       0x0010, 0x080c, 0x9350, 0x012e, 0xac88, 0x0018, 0x7116, 0x2001,
-       0xe400, 0xa102, 0x0220, 0x7017, 0xb400, 0x7007, 0x0000, 0x0005,
-       0x00e6, 0x2071, 0xafda, 0x7027, 0x07d0, 0x7023, 0x0009, 0x00ee,
-       0x0005, 0x2001, 0xafe3, 0x2003, 0x0000, 0x0005, 0x00e6, 0x2071,
-       0xafda, 0x7132, 0x702f, 0x0009, 0x00ee, 0x0005, 0x2011, 0xafe6,
-       0x2013, 0x0000, 0x0005, 0x00e6, 0x2071, 0xafda, 0x711a, 0x721e,
-       0x700b, 0x0009, 0x00ee, 0x0005, 0x00c6, 0x2061, 0xb048, 0x00ce,
-       0x0005, 0xa184, 0x000f, 0x8003, 0x8003, 0x8003, 0xa080, 0xb048,
-       0x2060, 0x0005, 0x6854, 0xa08a, 0x199a, 0x0210, 0x2001, 0x1999,
-       0xa005, 0x1150, 0x00c6, 0x2061, 0xb048, 0x6014, 0x00ce, 0xa005,
-       0x1138, 0x2001, 0x001e, 0x0020, 0xa08e, 0xffff, 0x1108, 0xa006,
-       0x8003, 0x800b, 0x810b, 0xa108, 0x6116, 0x684c, 0xa08c, 0x00c0,
-       0xa18e, 0x00c0, 0x05b0, 0xd0b4, 0x1138, 0xd0bc, 0x1528, 0x2009,
-       0x0006, 0x080c, 0x661a, 0x0005, 0xd0fc, 0x0130, 0xa084, 0x0003,
-       0x0118, 0xa086, 0x0003, 0x15c0, 0x6020, 0xd0d4, 0x0130, 0xc0d4,
-       0x6022, 0x6860, 0x602a, 0x685c, 0x602e, 0x2009, 0xad73, 0x2104,
-       0xd084, 0x0128, 0x2009, 0x0042, 0x080c, 0x80a7, 0x0005, 0x2009,
-       0x0043, 0x080c, 0x80a7, 0x0005, 0xd0fc, 0x0130, 0xa084, 0x0003,
-       0x0118, 0xa086, 0x0003, 0x11c0, 0x2009, 0x0042, 0x080c, 0x80a7,
-       0x0005, 0xd0fc, 0x0150, 0xa084, 0x0003, 0xa08e, 0x0002, 0x0138,
-       0x2009, 0x0041, 0x080c, 0x80a7, 0x0005, 0x0051, 0x0ce8, 0x2009,
-       0x0043, 0x080c, 0x80a7, 0x0cc0, 0x2009, 0x0004, 0x0019, 0x0005,
-       0x2009, 0x0001, 0x00d6, 0x6010, 0xa0ec, 0xf000, 0x01f0, 0x2068,
-       0x6952, 0x6800, 0x6012, 0xa186, 0x0001, 0x1188, 0x694c, 0xa18c,
-       0x8100, 0xa18e, 0x8100, 0x1158, 0x00c6, 0x2061, 0xb048, 0x6200,
-       0xd28c, 0x1120, 0x6204, 0x8210, 0x0208, 0x6206, 0x00ce, 0x080c,
-       0x510c, 0x6010, 0xa06d, 0x190c, 0x65aa, 0x00de, 0x0005, 0x0156,
-       0x00c6, 0x2061, 0xb048, 0x6000, 0x81ff, 0x0110, 0xa205, 0x0008,
-       0xa204, 0x6002, 0x00ce, 0x015e, 0x0005, 0x6800, 0xd08c, 0x1138,
-       0x6808, 0xa005, 0x0120, 0x8001, 0x680a, 0xa085, 0x0001, 0x0005,
-       0x20a9, 0x0010, 0xa006, 0x8004, 0x8086, 0x818e, 0x1208, 0xa200,
-       0x1f04, 0x665c, 0x8086, 0x818e, 0x0005, 0x0156, 0x20a9, 0x0010,
-       0xa005, 0x01b8, 0xa11a, 0x12a8, 0x8213, 0x818d, 0x0228, 0xa11a,
-       0x1220, 0x1f04, 0x666c, 0x0028, 0xa11a, 0x2308, 0x8210, 0x1f04,
-       0x666c, 0x0006, 0x3200, 0xa084, 0xefff, 0x2080, 0x000e, 0x015e,
-       0x0005, 0x0006, 0x3200, 0xa085, 0x1000, 0x0cb8, 0x0126, 0x2091,
-       0x2800, 0x2079, 0xafc7, 0x012e, 0x00d6, 0x2069, 0xafc7, 0x6803,
-       0x0005, 0x2069, 0x0004, 0x2d04, 0xa085, 0x8001, 0x206a, 0x00de,
-       0x0005, 0x00c6, 0x6027, 0x0001, 0x7804, 0xa084, 0x0007, 0x0002,
-       0x66aa, 0x66cb, 0x671e, 0x66b0, 0x66cb, 0x66aa, 0x66a8, 0x66a8,
-       0x080c, 0x14f6, 0x080c, 0x6581, 0x080c, 0x6c50, 0x00ce, 0x0005,
-       0x62c0, 0x82ff, 0x1110, 0x00ce, 0x0005, 0x2011, 0x481b, 0x080c,
-       0x650d, 0x7828, 0xa092, 0x00c8, 0x1228, 0x8000, 0x782a, 0x080c,
-       0x4855, 0x0c88, 0x080c, 0x481b, 0x7807, 0x0003, 0x7827, 0x0000,
-       0x782b, 0x0000, 0x0c40, 0x080c, 0x6581, 0x3c00, 0x0006, 0x2011,
-       0x0209, 0x20e1, 0x4000, 0x2214, 0x000e, 0x20e0, 0x82ff, 0x0178,
-       0x62c0, 0x82ff, 0x1160, 0x782b, 0x0000, 0x7824, 0xa065, 0x090c,
-       0x14f6, 0x2009, 0x0013, 0x080c, 0x80a7, 0x00ce, 0x0005, 0x3900,
-       0xa082, 0xb0e8, 0x1210, 0x080c, 0x7d8d, 0x00c6, 0x7824, 0xa065,
-       0x090c, 0x14f6, 0x7804, 0xa086, 0x0004, 0x0904, 0x675e, 0x7828,
-       0xa092, 0x2710, 0x1230, 0x8000, 0x782a, 0x00ce, 0x080c, 0x7827,
-       0x0c20, 0x6104, 0xa186, 0x0003, 0x1188, 0x00e6, 0x2071, 0xad00,
-       0x70dc, 0x00ee, 0xd08c, 0x0150, 0x00c6, 0x00e6, 0x2061, 0x0100,
-       0x2071, 0xad00, 0x080c, 0x485e, 0x00ee, 0x00ce, 0x080c, 0xaca2,
-       0x2009, 0x0014, 0x080c, 0x80a7, 0x00ce, 0x0838, 0x2001, 0xafe3,
-       0x2003, 0x0000, 0x62c0, 0x82ff, 0x1160, 0x782b, 0x0000, 0x7824,
-       0xa065, 0x090c, 0x14f6, 0x2009, 0x0013, 0x080c, 0x80fb, 0x00ce,
-       0x0005, 0x00c6, 0x00d6, 0x3900, 0xa082, 0xb0e8, 0x1210, 0x080c,
-       0x7d8d, 0x7824, 0xa005, 0x090c, 0x14f6, 0x781c, 0xa06d, 0x090c,
-       0x14f6, 0x6800, 0xc0dc, 0x6802, 0x7924, 0x2160, 0x080c, 0x8078,
-       0x693c, 0x81ff, 0x090c, 0x14f6, 0x8109, 0x693e, 0x6854, 0xa015,
-       0x0110, 0x7a1e, 0x0010, 0x7918, 0x791e, 0x7807, 0x0000, 0x7827,
-       0x0000, 0x00de, 0x00ce, 0x080c, 0x6c50, 0x0888, 0x6104, 0xa186,
-       0x0002, 0x0128, 0xa186, 0x0004, 0x0110, 0x0804, 0x66f7, 0x7808,
-       0xac06, 0x0904, 0x66f7, 0x080c, 0x6b73, 0x080c, 0x67ee, 0x00ce,
-       0x080c, 0x6c50, 0x0804, 0x66e5, 0x00c6, 0x6027, 0x0002, 0x62c8,
-       0x60c4, 0xa205, 0x1178, 0x793c, 0xa1e5, 0x0000, 0x0130, 0x2009,
-       0x0049, 0x080c, 0x80a7, 0x00ce, 0x0005, 0x2011, 0xafe6, 0x2013,
-       0x0000, 0x0cc8, 0x3908, 0xa192, 0xb0e8, 0x1210, 0x080c, 0x7d8d,
-       0x793c, 0x81ff, 0x0d90, 0x793c, 0xa188, 0x0007, 0x210c, 0xa18e,
-       0x0006, 0x1138, 0x6014, 0xa084, 0x0184, 0xa085, 0x0012, 0x6016,
-       0x0c10, 0x6014, 0xa084, 0x0184, 0xa085, 0x0016, 0x6016, 0x08d8,
-       0x0006, 0x0016, 0x00c6, 0x0126, 0x2091, 0x8000, 0x600f, 0x0000,
-       0x2c08, 0x2061, 0xafc7, 0x6020, 0x8000, 0x6022, 0x6010, 0xa005,
-       0x0148, 0xa080, 0x0003, 0x2102, 0x6112, 0x012e, 0x00ce, 0x001e,
-       0x000e, 0x0005, 0x6116, 0x6112, 0x0cc0, 0x00d6, 0x2069, 0xafc7,
-       0x6000, 0xd0d4, 0x0168, 0x6820, 0x8000, 0x6822, 0xa086, 0x0001,
-       0x1110, 0x2c00, 0x681e, 0x6804, 0xa084, 0x0007, 0x0804, 0x6c56,
-       0xc0d5, 0x6002, 0x6818, 0xa005, 0x0158, 0x6056, 0x605b, 0x0000,
-       0x0006, 0x2c00, 0x681a, 0x00de, 0x685a, 0x2069, 0xafc7, 0x0c18,
-       0x6056, 0x605a, 0x2c00, 0x681a, 0x681e, 0x08e8, 0x0006, 0x0016,
-       0x00c6, 0x0126, 0x2091, 0x8000, 0x600f, 0x0000, 0x2c08, 0x2061,
-       0xafc7, 0x6020, 0x8000, 0x6022, 0x6008, 0xa005, 0x0148, 0xa080,
-       0x0003, 0x2102, 0x610a, 0x012e, 0x00ce, 0x001e, 0x000e, 0x0005,
-       0x610e, 0x610a, 0x0cc0, 0x00c6, 0x600f, 0x0000, 0x2c08, 0x2061,
-       0xafc7, 0x6034, 0xa005, 0x0130, 0xa080, 0x0003, 0x2102, 0x6136,
-       0x00ce, 0x0005, 0x613a, 0x6136, 0x0cd8, 0x00f6, 0x00e6, 0x00d6,
-       0x00c6, 0x0076, 0x0066, 0x0026, 0x0016, 0x0006, 0x0126, 0x2071,
-       0xafc7, 0x7638, 0x2660, 0x2678, 0x2091, 0x8000, 0x8cff, 0x0904,
-       0x6889, 0x6018, 0xa080, 0x0028, 0x2004, 0xa206, 0x1904, 0x6884,
-       0x87ff, 0x0120, 0x6050, 0xa106, 0x1904, 0x6884, 0x703c, 0xac06,
-       0x1170, 0x0036, 0x2019, 0x0001, 0x080c, 0x7a64, 0x7033, 0x0000,
-       0x703f, 0x0000, 0x7043, 0x0000, 0x7047, 0x0000, 0x003e, 0x7038,
-       0xac36, 0x1110, 0x660c, 0x763a, 0x7034, 0xac36, 0x1140, 0x2c00,
-       0xaf36, 0x0118, 0x2f00, 0x7036, 0x0010, 0x7037, 0x0000, 0x660c,
-       0x0066, 0x2c00, 0xaf06, 0x0110, 0x7e0e, 0x0008, 0x2678, 0x600f,
-       0x0000, 0x080c, 0x9596, 0x0198, 0x6010, 0x2068, 0x601c, 0xa086,
-       0x0003, 0x1510, 0x6837, 0x0103, 0x6b4a, 0x6847, 0x0000, 0x080c,
-       0x97fd, 0x080c, 0xabfa, 0x080c, 0x510c, 0x080c, 0x9742, 0x080c,
-       0x974e, 0x00ce, 0x0804, 0x682e, 0x2c78, 0x600c, 0x2060, 0x0804,
-       0x682e, 0x012e, 0x000e, 0x001e, 0x002e, 0x006e, 0x007e, 0x00ce,
-       0x00de, 0x00ee, 0x00fe, 0x0005, 0x601c, 0xa086, 0x0006, 0x19d0,
-       0x080c, 0xabfa, 0x080c, 0xa91f, 0x0c10, 0x0006, 0x0066, 0x00c6,
-       0x00d6, 0x00f6, 0x2031, 0x0000, 0x0126, 0x2091, 0x8000, 0x2079,
-       0xafc7, 0x7838, 0xa065, 0x0558, 0x600c, 0x0006, 0x600f, 0x0000,
-       0x783c, 0xac06, 0x1170, 0x0036, 0x2019, 0x0001, 0x080c, 0x7a64,
-       0x7833, 0x0000, 0x783f, 0x0000, 0x7843, 0x0000, 0x7847, 0x0000,
-       0x003e, 0x080c, 0x9596, 0x0178, 0x6010, 0x2068, 0x601c, 0xa086,
-       0x0003, 0x11b0, 0x6837, 0x0103, 0x6b4a, 0x6847, 0x0000, 0x080c,
-       0x510c, 0x080c, 0x9742, 0x080c, 0x974e, 0x000e, 0x0898, 0x7e3a,
-       0x7e36, 0x012e, 0x00fe, 0x00de, 0x00ce, 0x006e, 0x000e, 0x0005,
-       0x601c, 0xa086, 0x0006, 0x1d30, 0x080c, 0xa91f, 0x0c60, 0x0016,
-       0x0026, 0x0086, 0x2041, 0x0000, 0x0099, 0x080c, 0x69a9, 0x008e,
-       0x002e, 0x001e, 0x0005, 0x00f6, 0x0126, 0x2079, 0xafc7, 0x2091,
-       0x8000, 0x080c, 0x6a36, 0x080c, 0x6aa8, 0x012e, 0x00fe, 0x0005,
-       0x00f6, 0x00e6, 0x00d6, 0x00c6, 0x0066, 0x0016, 0x0006, 0x0126,
-       0x2091, 0x8000, 0x2071, 0xafc7, 0x7614, 0x2660, 0x2678, 0x8cff,
-       0x0904, 0x6985, 0x6018, 0xa080, 0x0028, 0x2004, 0xa206, 0x1904,
-       0x6980, 0x88ff, 0x0120, 0x6050, 0xa106, 0x1904, 0x6980, 0x7024,
-       0xac06, 0x1538, 0x2069, 0x0100, 0x68c0, 0xa005, 0x01f0, 0x080c,
-       0x6581, 0x080c, 0x7834, 0x68c3, 0x0000, 0x080c, 0x7ca8, 0x7027,
-       0x0000, 0x0036, 0x2069, 0x0140, 0x6b04, 0xa384, 0x1000, 0x0120,
-       0x6803, 0x0100, 0x6803, 0x0000, 0x2069, 0x0100, 0x6824, 0xd084,
-       0x0110, 0x6827, 0x0001, 0x003e, 0x0020, 0x6003, 0x0009, 0x630a,
-       0x04b8, 0x7014, 0xac36, 0x1110, 0x660c, 0x7616, 0x7010, 0xac36,
-       0x1140, 0x2c00, 0xaf36, 0x0118, 0x2f00, 0x7012, 0x0010, 0x7013,
-       0x0000, 0x660c, 0x0066, 0x2c00, 0xaf06, 0x0110, 0x7e0e, 0x0008,
-       0x2678, 0x600f, 0x0000, 0x6010, 0x2068, 0x080c, 0x9596, 0x0188,
-       0x601c, 0xa086, 0x0003, 0x1510, 0x6837, 0x0103, 0x6b4a, 0x6847,
-       0x0000, 0x080c, 0x97fd, 0x080c, 0xabfa, 0x080c, 0x510c, 0x080c,
-       0x9742, 0x080c, 0x974e, 0x080c, 0x7b88, 0x00ce, 0x0804, 0x690f,
-       0x2c78, 0x600c, 0x2060, 0x0804, 0x690f, 0x012e, 0x000e, 0x001e,
-       0x006e, 0x00ce, 0x00de, 0x00ee, 0x00fe, 0x0005, 0x601c, 0xa086,
-       0x0006, 0x1128, 0x080c, 0xabfa, 0x080c, 0xa91f, 0x0c10, 0x601c,
-       0xa086, 0x0002, 0x1128, 0x6004, 0xa086, 0x0085, 0x0968, 0x08c8,
-       0x601c, 0xa086, 0x0005, 0x19a8, 0x6004, 0xa086, 0x0085, 0x0d50,
-       0x0880, 0x00c6, 0x0006, 0x0126, 0x2091, 0x8000, 0xa280, 0xae34,
-       0x2004, 0xa065, 0x0904, 0x6a32, 0x00f6, 0x00e6, 0x00d6, 0x0066,
-       0x2071, 0xafc7, 0x6654, 0x7018, 0xac06, 0x1108, 0x761a, 0x701c,
-       0xac06, 0x1130, 0x86ff, 0x1118, 0x7018, 0x701e, 0x0008, 0x761e,
-       0x6058, 0xa07d, 0x0108, 0x7e56, 0xa6ed, 0x0000, 0x0110, 0x2f00,
-       0x685a, 0x6057, 0x0000, 0x605b, 0x0000, 0x6000, 0xc0d4, 0xc0dc,
-       0x6002, 0x080c, 0x4c07, 0x0904, 0x6a2e, 0x7624, 0x86ff, 0x05e8,
-       0xa680, 0x0004, 0x2004, 0xad06, 0x15c0, 0x00d6, 0x2069, 0x0100,
-       0x68c0, 0xa005, 0x0548, 0x080c, 0x6581, 0x080c, 0x7834, 0x68c3,
-       0x0000, 0x080c, 0x7ca8, 0x7027, 0x0000, 0x0036, 0x2069, 0x0140,
-       0x6b04, 0xa384, 0x1000, 0x0120, 0x6803, 0x0100, 0x6803, 0x0000,
-       0x2069, 0x0100, 0x6824, 0xd084, 0x0110, 0x6827, 0x0001, 0x003e,
-       0x00de, 0x00c6, 0x603c, 0xa005, 0x0110, 0x8001, 0x603e, 0x2660,
-       0x080c, 0x974e, 0x00ce, 0x0048, 0x00de, 0x00c6, 0x2660, 0x6003,
-       0x0009, 0x630a, 0x00ce, 0x0804, 0x69d9, 0x8dff, 0x0158, 0x6837,
-       0x0103, 0x6b4a, 0x6847, 0x0000, 0x080c, 0x97fd, 0x080c, 0xabfa,
-       0x080c, 0x510c, 0x080c, 0x7b88, 0x0804, 0x69d9, 0x006e, 0x00de,
-       0x00ee, 0x00fe, 0x012e, 0x000e, 0x00ce, 0x0005, 0x0006, 0x0066,
-       0x00c6, 0x00d6, 0x2031, 0x0000, 0x7814, 0xa065, 0x0904, 0x6a88,
-       0x600c, 0x0006, 0x600f, 0x0000, 0x7824, 0xac06, 0x1540, 0x2069,
-       0x0100, 0x68c0, 0xa005, 0x01f0, 0x080c, 0x6581, 0x080c, 0x7834,
-       0x68c3, 0x0000, 0x080c, 0x7ca8, 0x7827, 0x0000, 0x0036, 0x2069,
-       0x0140, 0x6b04, 0xa384, 0x1000, 0x0120, 0x6803, 0x0100, 0x6803,
-       0x0000, 0x2069, 0x0100, 0x6824, 0xd084, 0x0110, 0x6827, 0x0001,
-       0x003e, 0x0028, 0x6003, 0x0009, 0x630a, 0x2c30, 0x00b0, 0x6010,
-       0x2068, 0x080c, 0x9596, 0x0168, 0x601c, 0xa086, 0x0003, 0x11b8,
-       0x6837, 0x0103, 0x6b4a, 0x6847, 0x0000, 0x080c, 0x510c, 0x080c,
-       0x9742, 0x080c, 0x974e, 0x080c, 0x7b88, 0x000e, 0x0804, 0x6a3d,
-       0x7e16, 0x7e12, 0x00de, 0x00ce, 0x006e, 0x000e, 0x0005, 0x601c,
-       0xa086, 0x0006, 0x1118, 0x080c, 0xa91f, 0x0c58, 0x601c, 0xa086,
-       0x0002, 0x1128, 0x6004, 0xa086, 0x0085, 0x09d0, 0x0c10, 0x601c,
-       0xa086, 0x0005, 0x19f0, 0x6004, 0xa086, 0x0085, 0x0d60, 0x08c8,
-       0x0006, 0x0066, 0x00c6, 0x00d6, 0x7818, 0xa065, 0x0904, 0x6b0e,
-       0x6054, 0x0006, 0x6057, 0x0000, 0x605b, 0x0000, 0x6000, 0xc0d4,
-       0xc0dc, 0x6002, 0x080c, 0x4c07, 0x0904, 0x6b0b, 0x7e24, 0x86ff,
-       0x05e8, 0xa680, 0x0004, 0x2004, 0xad06, 0x15c0, 0x00d6, 0x2069,
-       0x0100, 0x68c0, 0xa005, 0x0548, 0x080c, 0x6581, 0x080c, 0x7834,
-       0x68c3, 0x0000, 0x080c, 0x7ca8, 0x7827, 0x0000, 0x0036, 0x2069,
-       0x0140, 0x6b04, 0xa384, 0x1000, 0x0120, 0x6803, 0x0100, 0x6803,
-       0x0000, 0x2069, 0x0100, 0x6824, 0xd084, 0x0110, 0x6827, 0x0001,
-       0x003e, 0x00de, 0x00c6, 0x603c, 0xa005, 0x0110, 0x8001, 0x603e,
-       0x2660, 0x080c, 0x974e, 0x00ce, 0x0048, 0x00de, 0x00c6, 0x2660,
-       0x6003, 0x0009, 0x630a, 0x00ce, 0x0804, 0x6aba, 0x8dff, 0x0138,
-       0x6837, 0x0103, 0x6b4a, 0x6847, 0x0000, 0x080c, 0x510c, 0x080c,
-       0x7b88, 0x0804, 0x6aba, 0x000e, 0x0804, 0x6aad, 0x781e, 0x781a,
-       0x00de, 0x00ce, 0x006e, 0x000e, 0x0005, 0x00e6, 0x00d6, 0x0066,
-       0x6000, 0xd0dc, 0x0188, 0x604c, 0xa06d, 0x0170, 0x6848, 0xa606,
-       0x1158, 0x2071, 0xafc7, 0x7024, 0xa035, 0x0130, 0xa080, 0x0004,
-       0x2004, 0xad06, 0x1108, 0x0021, 0x006e, 0x00de, 0x00ee, 0x0005,
-       0x00f6, 0x2079, 0x0100, 0x78c0, 0xa005, 0x1138, 0x00c6, 0x2660,
-       0x6003, 0x0009, 0x630a, 0x00ce, 0x04a0, 0x080c, 0x7834, 0x78c3,
-       0x0000, 0x080c, 0x7ca8, 0x7027, 0x0000, 0x0036, 0x2079, 0x0140,
-       0x7b04, 0xa384, 0x1000, 0x0120, 0x7803, 0x0100, 0x7803, 0x0000,
-       0x2079, 0x0100, 0x7824, 0xd084, 0x0110, 0x7827, 0x0001, 0x080c,
-       0x7ca8, 0x003e, 0x080c, 0x4c07, 0x00c6, 0x603c, 0xa005, 0x0110,
-       0x8001, 0x603e, 0x2660, 0x080c, 0x8078, 0x00ce, 0x6837, 0x0103,
-       0x6b4a, 0x6847, 0x0000, 0x080c, 0x97fd, 0x080c, 0x510c, 0x080c,
-       0x7b88, 0x00fe, 0x0005, 0x00e6, 0x00c6, 0x2071, 0xafc7, 0x7004,
-       0xa084, 0x0007, 0x0002, 0x6b85, 0x6b88, 0x6b9e, 0x6bb7, 0x6bf0,
-       0x6b85, 0x6b83, 0x6b83, 0x080c, 0x14f6, 0x00ce, 0x00ee, 0x0005,
-       0x7024, 0xa065, 0x0148, 0x7020, 0x8001, 0x7022, 0x600c, 0xa015,
-       0x0150, 0x7216, 0x600f, 0x0000, 0x7007, 0x0000, 0x7027, 0x0000,
-       0x00ce, 0x00ee, 0x0005, 0x7216, 0x7212, 0x0cb0, 0x6018, 0x2060,
-       0x080c, 0x4c07, 0x6000, 0xc0dc, 0x6002, 0x7020, 0x8001, 0x7022,
-       0x0120, 0x6054, 0xa015, 0x0140, 0x721e, 0x7007, 0x0000, 0x7027,
-       0x0000, 0x00ce, 0x00ee, 0x0005, 0x7218, 0x721e, 0x0cb0, 0x7024,
-       0xa065, 0x0598, 0x700c, 0xac06, 0x1160, 0x080c, 0x7b88, 0x600c,
-       0xa015, 0x0120, 0x720e, 0x600f, 0x0000, 0x0428, 0x720e, 0x720a,
-       0x0410, 0x7014, 0xac06, 0x1160, 0x080c, 0x7b88, 0x600c, 0xa015,
-       0x0120, 0x7216, 0x600f, 0x0000, 0x00b0, 0x7216, 0x7212, 0x0098,
-       0x6018, 0x2060, 0x080c, 0x4c07, 0x6000, 0xc0dc, 0x6002, 0x080c,
-       0x7b88, 0x701c, 0xa065, 0x0138, 0x6054, 0xa015, 0x0110, 0x721e,
-       0x0010, 0x7218, 0x721e, 0x7027, 0x0000, 0x00ce, 0x00ee, 0x0005,
-       0x7024, 0xa065, 0x0140, 0x080c, 0x7b88, 0x600c, 0xa015, 0x0150,
-       0x720e, 0x600f, 0x0000, 0x080c, 0x7ca8, 0x7027, 0x0000, 0x00ce,
-       0x00ee, 0x0005, 0x720e, 0x720a, 0x0cb0, 0x00d6, 0x2069, 0xafc7,
-       0x6830, 0xa084, 0x0003, 0x0002, 0x6c12, 0x6c14, 0x6c38, 0x6c10,
-       0x080c, 0x14f6, 0x00de, 0x0005, 0x00c6, 0x6840, 0xa086, 0x0001,
-       0x01b8, 0x683c, 0xa065, 0x0130, 0x600c, 0xa015, 0x0170, 0x6a3a,
-       0x600f, 0x0000, 0x6833, 0x0000, 0x683f, 0x0000, 0x2011, 0xafe6,
-       0x2013, 0x0000, 0x00ce, 0x00de, 0x0005, 0x683a, 0x6836, 0x0c90,
-       0x6843, 0x0000, 0x6838, 0xa065, 0x0d68, 0x6003, 0x0003, 0x0c50,
-       0x00c6, 0x6843, 0x0000, 0x6847, 0x0000, 0x683c, 0xa065, 0x0168,
-       0x600c, 0xa015, 0x0130, 0x6a3a, 0x600f, 0x0000, 0x683f, 0x0000,
-       0x0020, 0x683f, 0x0000, 0x683a, 0x6836, 0x00ce, 0x00de, 0x0005,
-       0x00d6, 0x2069, 0xafc7, 0x6804, 0xa084, 0x0007, 0x0002, 0x6c61,
-       0x6cfd, 0x6cfd, 0x6cfd, 0x6cfd, 0x6cff, 0x6c5f, 0x6c5f, 0x080c,
-       0x14f6, 0x6820, 0xa005, 0x1110, 0x00de, 0x0005, 0x00c6, 0x680c,
-       0xa065, 0x0150, 0x6807, 0x0004, 0x6826, 0x682b, 0x0000, 0x080c,
-       0x6d49, 0x00ce, 0x00de, 0x0005, 0x6814, 0xa065, 0x0150, 0x6807,
-       0x0001, 0x6826, 0x682b, 0x0000, 0x080c, 0x6d49, 0x00ce, 0x00de,
-       0x0005, 0x00e6, 0x0036, 0x6a1c, 0xa2f5, 0x0000, 0x0904, 0x6cf9,
-       0x704c, 0xa00d, 0x0118, 0x7088, 0xa005, 0x01a0, 0x7054, 0xa075,
-       0x0120, 0xa20e, 0x0904, 0x6cf9, 0x0028, 0x6818, 0xa20e, 0x0904,
-       0x6cf9, 0x2070, 0x704c, 0xa00d, 0x0d88, 0x7088, 0xa005, 0x1d70,
-       0x2e00, 0x681e, 0x733c, 0x7038, 0xa302, 0x1e40, 0x080c, 0x804f,
-       0x0904, 0x6cf9, 0x8318, 0x733e, 0x6112, 0x2e10, 0x621a, 0xa180,
-       0x0014, 0x2004, 0xa084, 0x00ff, 0x605a, 0xa180, 0x0014, 0x2003,
-       0x0000, 0xa180, 0x0015, 0x2004, 0xa08a, 0x199a, 0x0210, 0x2001,
-       0x1999, 0x8003, 0x801b, 0x831b, 0xa318, 0x6316, 0x003e, 0x00f6,
-       0x2c78, 0x71a0, 0x2001, 0xad34, 0x2004, 0xd0ac, 0x1110, 0xd1bc,
-       0x0150, 0x7100, 0xd1f4, 0x0120, 0x7114, 0xa18c, 0x00ff, 0x0040,
-       0x2009, 0x0000, 0x0028, 0xa1e0, 0x2be6, 0x2c0d, 0xa18c, 0x00ff,
-       0x2061, 0x0100, 0x619a, 0x080c, 0x736f, 0x7300, 0xc3dd, 0x7302,
-       0x6807, 0x0002, 0x2f18, 0x6b26, 0x682b, 0x0000, 0x781f, 0x0003,
-       0x7803, 0x0001, 0x7807, 0x0040, 0x00fe, 0x00ee, 0x00ce, 0x00de,
-       0x0005, 0x003e, 0x00ee, 0x00ce, 0x0cd0, 0x00de, 0x0005, 0x00c6,
-       0x680c, 0xa065, 0x0138, 0x6807, 0x0004, 0x6826, 0x682b, 0x0000,
-       0x080c, 0x6d49, 0x00ce, 0x00de, 0x0005, 0x00f6, 0x00d6, 0x2069,
-       0xafc7, 0x6830, 0xa086, 0x0000, 0x11c0, 0x2001, 0xad0c, 0x200c,
-       0xd1bc, 0x1550, 0x6838, 0xa07d, 0x0180, 0x6833, 0x0001, 0x683e,
-       0x6847, 0x0000, 0x0126, 0x00f6, 0x2091, 0x2400, 0x002e, 0x080c,
-       0x1ee6, 0x1130, 0x012e, 0x080c, 0x76a5, 0x00de, 0x00fe, 0x0005,
-       0x012e, 0xe000, 0x6843, 0x0000, 0x7803, 0x0002, 0x780c, 0xa015,
-       0x0140, 0x6a3a, 0x780f, 0x0000, 0x6833, 0x0000, 0x683f, 0x0000,
-       0x0c60, 0x683a, 0x6836, 0x0cc0, 0xc1bc, 0x2102, 0x080c, 0x57d1,
-       0x0888, 0x601c, 0xa084, 0x000f, 0x000b, 0x0005, 0x6d57, 0x6d5c,
-       0x7210, 0x732c, 0x6d5c, 0x7210, 0x732c, 0x6d57, 0x6d5c, 0x080c,
-       0x6b73, 0x080c, 0x6c50, 0x0005, 0x0156, 0x0136, 0x0146, 0x00c6,
-       0x00f6, 0x6004, 0xa08a, 0x0080, 0x1a0c, 0x14f6, 0x6118, 0x2178,
-       0x79a0, 0x2011, 0xad34, 0x2214, 0xd2ac, 0x1110, 0xd1bc, 0x0150,
-       0x7900, 0xd1f4, 0x0120, 0x7914, 0xa18c, 0x00ff, 0x0040, 0x2009,
-       0x0000, 0x0028, 0xa1f8, 0x2be6, 0x2f0d, 0xa18c, 0x00ff, 0x2c78,
-       0x2061, 0x0100, 0x619a, 0xa08a, 0x0040, 0x1a04, 0x6dd0, 0x0033,
-       0x00fe, 0x00ce, 0x014e, 0x013e, 0x015e, 0x0005, 0x6e7c, 0x6ec7,
-       0x6ef4, 0x6fc1, 0x6fef, 0x6ff7, 0x701d, 0x702e, 0x703f, 0x7047,
-       0x705d, 0x7047, 0x70b7, 0x702e, 0x70d8, 0x70e0, 0x703f, 0x70e0,
-       0x70f1, 0x6dce, 0x6dce, 0x6dce, 0x6dce, 0x6dce, 0x6dce, 0x6dce,
-       0x6dce, 0x6dce, 0x6dce, 0x6dce, 0x790d, 0x7932, 0x7947, 0x796a,
-       0x798b, 0x701d, 0x6dce, 0x701d, 0x7047, 0x6dce, 0x6ef4, 0x6fc1,
-       0x6dce, 0x7daa, 0x7047, 0x6dce, 0x7dca, 0x7047, 0x6dce, 0x703f,
-       0x6e75, 0x6de0, 0x6dce, 0x7def, 0x7e64, 0x7f3b, 0x6dce, 0x7f4c,
-       0x7018, 0x7f68, 0x6dce, 0x79a0, 0x7fc3, 0x6dce, 0x080c, 0x14f6,
-       0x2100, 0x0033, 0x00fe, 0x00ce, 0x014e, 0x013e, 0x015e, 0x0005,
-       0x6dde, 0x6dde, 0x6dde, 0x6e14, 0x6e32, 0x6e48, 0x080c, 0x14f6,
-       0x00d6, 0x20a1, 0x020b, 0x080c, 0x710e, 0x7810, 0x2068, 0x20a3,
-       0x2414, 0x20a3, 0x0018, 0x20a3, 0x0800, 0x683c, 0x20a2, 0x20a3,
-       0x0000, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x6850,
-       0x20a2, 0x6854, 0x20a2, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x60c3,
-       0x0018, 0x080c, 0x7821, 0x00de, 0x0005, 0x00d6, 0x7818, 0x2068,
-       0x68a0, 0x2069, 0xad00, 0x6ad0, 0xd2ac, 0x1110, 0xd0bc, 0x0110,
-       0xa085, 0x0001, 0x00de, 0x0005, 0x00d6, 0x20a1, 0x020b, 0x080c,
-       0x710e, 0x20a3, 0x0500, 0x20a3, 0x0000, 0x7810, 0xa0e8, 0x000f,
-       0x6808, 0x20a2, 0x680c, 0x20a2, 0x6810, 0x20a2, 0x6814, 0x20a2,
-       0x6818, 0x20a2, 0x681c, 0x20a2, 0x60c3, 0x0010, 0x080c, 0x7821,
-       0x00de, 0x0005, 0x0156, 0x0146, 0x20a1, 0x020b, 0x080c, 0x710e,
-       0x20a3, 0x7800, 0x20a3, 0x0000, 0x7808, 0x8007, 0x20a2, 0x20a3,
-       0x0000, 0x60c3, 0x0008, 0x080c, 0x7821, 0x014e, 0x015e, 0x0005,
-       0x0156, 0x0146, 0x20a1, 0x020b, 0x080c, 0x71aa, 0x20a3, 0x0200,
-       0x20a3, 0x0000, 0x20a3, 0xdf10, 0x20a3, 0x0034, 0x2099, 0xad05,
-       0x20a9, 0x0004, 0x53a6, 0x2099, 0xad01, 0x20a9, 0x0004, 0x53a6,
-       0x2099, 0xafad, 0x20a9, 0x001a, 0x3304, 0x8007, 0x20a2, 0x9398,
-       0x1f04, 0x6e64, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x60c3, 0x004c,
-       0x080c, 0x7821, 0x014e, 0x015e, 0x0005, 0x2001, 0xad14, 0x2004,
-       0x609a, 0x080c, 0x7821, 0x0005, 0x20a1, 0x020b, 0x080c, 0x710e,
-       0x20a3, 0x5200, 0x20a3, 0x0000, 0x00d6, 0x2069, 0xad51, 0x6804,
-       0xd084, 0x0150, 0x6828, 0x20a3, 0x0000, 0x0016, 0x080c, 0x268a,
-       0x21a2, 0x001e, 0x00de, 0x0028, 0x00de, 0x20a3, 0x0000, 0x20a3,
-       0x0000, 0x20a9, 0x0004, 0x2099, 0xad05, 0x53a6, 0x20a9, 0x0004,
-       0x2099, 0xad01, 0x53a6, 0x2001, 0xad34, 0x2004, 0xd0ac, 0x1138,
-       0x7818, 0xa080, 0x0028, 0x2004, 0xa082, 0x007f, 0x0238, 0x2001,
-       0xad1b, 0x20a6, 0x2001, 0xad1c, 0x20a6, 0x0040, 0x20a3, 0x0000,
-       0x2001, 0xad14, 0x2004, 0xa084, 0x00ff, 0x20a2, 0x20a3, 0x0000,
-       0x20a3, 0x0000, 0x60c3, 0x001c, 0x080c, 0x7821, 0x0005, 0x20a1,
-       0x020b, 0x080c, 0x710e, 0x20a3, 0x0500, 0x20a3, 0x0000, 0x2001,
-       0xad34, 0x2004, 0xd0ac, 0x1138, 0x7818, 0xa080, 0x0028, 0x2004,
-       0xa082, 0x007f, 0x0238, 0x2001, 0xad1b, 0x20a6, 0x2001, 0xad1c,
-       0x20a6, 0x0040, 0x20a3, 0x0000, 0x2001, 0xad14, 0x2004, 0xa084,
-       0x00ff, 0x20a2, 0x20a9, 0x0004, 0x2099, 0xad05, 0x53a6, 0x60c3,
-       0x0010, 0x080c, 0x7821, 0x0005, 0x20a1, 0x020b, 0x080c, 0x710e,
-       0x00c6, 0x7818, 0x2060, 0x2001, 0x0000, 0x080c, 0x5037, 0x00ce,
-       0x7818, 0xa080, 0x0028, 0x2004, 0xa086, 0x007e, 0x1130, 0x20a3,
-       0x0400, 0x620c, 0xc2b4, 0x620e, 0x0010, 0x20a3, 0x0300, 0x20a3,
-       0x0000, 0x7818, 0xa080, 0x0028, 0x2004, 0xa086, 0x007e, 0x1904,
-       0x6f83, 0x2001, 0xad34, 0x2004, 0xd0a4, 0x01c8, 0x2099, 0xaf8d,
-       0x33a6, 0x9398, 0x20a3, 0x0000, 0x9398, 0x3304, 0xa084, 0x2000,
-       0x20a2, 0x9398, 0x33a6, 0x9398, 0x20a3, 0x0000, 0x9398, 0x2001,
-       0x2710, 0x20a2, 0x9398, 0x33a6, 0x9398, 0x33a6, 0x00d0, 0x2099,
-       0xaf8d, 0x33a6, 0x9398, 0x33a6, 0x9398, 0x3304, 0x080c, 0x574f,
-       0x1118, 0xa084, 0x37ff, 0x0010, 0xa084, 0x3fff, 0x20a2, 0x9398,
-       0x33a6, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x20a3,
-       0x0000, 0x20a9, 0x0004, 0x2099, 0xad05, 0x53a6, 0x20a9, 0x0004,
-       0x2099, 0xad01, 0x53a6, 0x20a9, 0x0008, 0x20a3, 0x0000, 0x1f04,
-       0x6f5d, 0x20a9, 0x0008, 0x20a3, 0x0000, 0x1f04, 0x6f63, 0x2099,
-       0xaf95, 0x3304, 0xc0dd, 0x20a2, 0x2001, 0xad71, 0x2004, 0xd0e4,
-       0x0158, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x9398, 0x9398, 0x9398,
-       0x33a6, 0x20a9, 0x0004, 0x0010, 0x20a9, 0x0007, 0x20a3, 0x0000,
-       0x1f04, 0x6f7e, 0x0468, 0x2001, 0xad34, 0x2004, 0xd0a4, 0x0140,
-       0x2001, 0xaf8e, 0x2004, 0x60e3, 0x0000, 0x080c, 0x26cb, 0x60e2,
-       0x2099, 0xaf8d, 0x20a9, 0x0008, 0x53a6, 0x20a9, 0x0004, 0x2099,
-       0xad05, 0x53a6, 0x20a9, 0x0004, 0x2099, 0xad01, 0x53a6, 0x20a9,
-       0x0008, 0x20a3, 0x0000, 0x1f04, 0x6fa1, 0x20a9, 0x0008, 0x20a3,
-       0x0000, 0x1f04, 0x6fa7, 0x2099, 0xaf95, 0x20a9, 0x0008, 0x53a6,
-       0x20a9, 0x0008, 0x20a3, 0x0000, 0x1f04, 0x6fb2, 0x20a9, 0x000a,
-       0x20a3, 0x0000, 0x1f04, 0x6fb8, 0x60c3, 0x0074, 0x080c, 0x7821,
-       0x0005, 0x20a1, 0x020b, 0x080c, 0x710e, 0x20a3, 0x2010, 0x20a3,
-       0x0014, 0x20a3, 0x0800, 0x20a3, 0x2000, 0xa006, 0x20a2, 0x20a2,
-       0x20a2, 0x20a2, 0x20a2, 0x00f6, 0x2079, 0xad51, 0x7904, 0x00fe,
-       0xd1ac, 0x1110, 0xa085, 0x0020, 0xd1a4, 0x0110, 0xa085, 0x0010,
-       0xa085, 0x0002, 0x00d6, 0x0804, 0x7099, 0x20a2, 0x20a3, 0x0000,
-       0x20a3, 0x0000, 0x60c3, 0x0014, 0x080c, 0x7821, 0x0005, 0x20a1,
-       0x020b, 0x080c, 0x710e, 0x20a3, 0x5000, 0x0804, 0x6f0f, 0x20a1,
-       0x020b, 0x080c, 0x710e, 0x20a3, 0x2110, 0x20a3, 0x0014, 0x20a3,
-       0x0000, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x20a3,
-       0x0000, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x20a3,
-       0x0000, 0x20a3, 0x0000, 0x60c3, 0x0014, 0x080c, 0x7821, 0x0005,
-       0x20a1, 0x020b, 0x080c, 0x71a2, 0x0020, 0x20a1, 0x020b, 0x080c,
-       0x71aa, 0x20a3, 0x0200, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x20a3,
-       0x0000, 0x60c3, 0x0004, 0x080c, 0x7821, 0x0005, 0x20a1, 0x020b,
-       0x080c, 0x71aa, 0x20a3, 0x0100, 0x20a3, 0x0000, 0x20a3, 0x0003,
-       0x20a3, 0x2a00, 0x60c3, 0x0008, 0x080c, 0x7821, 0x0005, 0x20a1,
-       0x020b, 0x080c, 0x71aa, 0x20a3, 0x0200, 0x0804, 0x6f0f, 0x20a1,
-       0x020b, 0x080c, 0x71aa, 0x20a3, 0x0100, 0x20a3, 0x0000, 0x7828,
-       0xa005, 0x0110, 0x20a2, 0x0010, 0x20a3, 0x0003, 0x7810, 0x20a2,
-       0x60c3, 0x0008, 0x080c, 0x7821, 0x0005, 0x00d6, 0x20a1, 0x020b,
-       0x080c, 0x71aa, 0x20a3, 0x0210, 0x20a3, 0x0014, 0x20a3, 0x0800,
-       0x7818, 0x2068, 0x6894, 0xa086, 0x0014, 0x1178, 0x6998, 0xa184,
-       0xc000, 0x1140, 0xd1ec, 0x0118, 0x20a3, 0x2100, 0x0040, 0x20a3,
-       0x0100, 0x0028, 0x20a3, 0x0400, 0x0010, 0x20a3, 0x0700, 0xa006,
-       0x20a2, 0x20a2, 0x20a2, 0x20a2, 0x20a2, 0x00f6, 0x2079, 0xad51,
-       0x7904, 0x00fe, 0xd1ac, 0x1110, 0xa085, 0x0020, 0xd1a4, 0x0110,
-       0xa085, 0x0010, 0x2009, 0xad73, 0x210c, 0xd184, 0x1110, 0xa085,
-       0x0002, 0x0026, 0x2009, 0xad71, 0x210c, 0xd1e4, 0x0130, 0xc0c5,
-       0xa094, 0x0030, 0xa296, 0x0010, 0x0140, 0xd1ec, 0x0130, 0xa094,
-       0x0030, 0xa296, 0x0010, 0x0108, 0xc0bd, 0x002e, 0x20a2, 0x20a2,
-       0x20a2, 0x60c3, 0x0014, 0x080c, 0x7821, 0x00de, 0x0005, 0x20a1,
-       0x020b, 0x080c, 0x71aa, 0x20a3, 0x0210, 0x20a3, 0x0014, 0x20a3,
-       0x0000, 0x20a3, 0x0100, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x20a3,
-       0x0000, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x20a3,
-       0x0000, 0x20a3, 0x0000, 0x60c3, 0x0014, 0x080c, 0x7821, 0x0005,
-       0x20a1, 0x020b, 0x080c, 0x71aa, 0x20a3, 0x0200, 0x0804, 0x6e82,
-       0x20a1, 0x020b, 0x080c, 0x71aa, 0x20a3, 0x0100, 0x20a3, 0x0000,
-       0x20a3, 0x0003, 0x20a3, 0x2a00, 0x60c3, 0x0008, 0x080c, 0x7821,
-       0x0005, 0x20e1, 0x9080, 0x20e1, 0x4000, 0x20a1, 0x020b, 0x080c,
-       0x71aa, 0x20a3, 0x0100, 0x20a3, 0x0000, 0x20a3, 0x000b, 0x20a3,
-       0x0000, 0x60c3, 0x0008, 0x080c, 0x7821, 0x0005, 0x0026, 0x0036,
-       0x0046, 0x2019, 0x3200, 0x2021, 0x0800, 0x0038, 0x0026, 0x0036,
-       0x0046, 0x2019, 0x2200, 0x2021, 0x0100, 0x20e1, 0x9080, 0x20e1,
-       0x4000, 0x7818, 0xa080, 0x0028, 0x2014, 0xa286, 0x007e, 0x11a0,
-       0xa385, 0x00ff, 0x20a2, 0x20a3, 0xfffe, 0x20a3, 0x0000, 0x2011,
-       0xad14, 0x2214, 0x2001, 0xaf9d, 0x2004, 0xa005, 0x0118, 0x2011,
-       0xad1c, 0x2214, 0x22a2, 0x04d0, 0xa286, 0x007f, 0x1138, 0x00d6,
-       0xa385, 0x00ff, 0x20a2, 0x20a3, 0xfffd, 0x00c8, 0x2001, 0xad34,
-       0x2004, 0xd0ac, 0x1110, 0xd2bc, 0x01c8, 0xa286, 0x0080, 0x00d6,
-       0x1130, 0xa385, 0x00ff, 0x20a2, 0x20a3, 0xfffc, 0x0040, 0xa2e8,
-       0xae34, 0x2d6c, 0x6810, 0xa305, 0x20a2, 0x6814, 0x20a2, 0x2069,
-       0xad1b, 0x2da6, 0x8d68, 0x2da6, 0x00de, 0x0080, 0x00d6, 0xa2e8,
-       0xae34, 0x2d6c, 0x6810, 0xa305, 0x20a2, 0x6814, 0x20a2, 0x00de,
-       0x20a3, 0x0000, 0x2011, 0xad14, 0x2214, 0x22a2, 0xa485, 0x0029,
-       0x20a2, 0x004e, 0x003e, 0x20a3, 0x0000, 0x080c, 0x7810, 0x22a2,
-       0x20a3, 0x0000, 0x2fa2, 0x20a3, 0xffff, 0x20a3, 0x0000, 0x20a3,
-       0x0000, 0x002e, 0x0005, 0x0026, 0x20e1, 0x9080, 0x20e1, 0x4000,
-       0x20a3, 0x02ff, 0x2011, 0xfffc, 0x22a2, 0x00d6, 0x2069, 0xad1b,
-       0x2da6, 0x8d68, 0x2da6, 0x00de, 0x20a3, 0x2029, 0x20a3, 0x0000,
-       0x08e0, 0x20a3, 0x0100, 0x20a3, 0x0000, 0x20a3, 0xfc02, 0x20a3,
-       0x0000, 0x0005, 0x0026, 0x0036, 0x0046, 0x2019, 0x3300, 0x2021,
-       0x0800, 0x0038, 0x0026, 0x0036, 0x0046, 0x2019, 0x2300, 0x2021,
-       0x0100, 0x20e1, 0x9080, 0x20e1, 0x4000, 0x7818, 0xa080, 0x0028,
-       0x2004, 0x2011, 0xad34, 0x2214, 0xd2ac, 0x1118, 0xa092, 0x007e,
-       0x02d8, 0x00d6, 0xa0e8, 0xae34, 0x2d6c, 0x6810, 0xa305, 0x20a2,
-       0x6814, 0x20a2, 0x6810, 0xa005, 0x1140, 0x6814, 0xa005, 0x1128,
-       0x20a3, 0x00ff, 0x20a3, 0xfffe, 0x0028, 0x2069, 0xad1b, 0x2da6,
-       0x8d68, 0x2da6, 0x00de, 0x0080, 0x00d6, 0xa0e8, 0xae34, 0x2d6c,
-       0x6810, 0xa305, 0x20a2, 0x6814, 0x20a2, 0x00de, 0x20a3, 0x0000,
-       0x2011, 0xad14, 0x2214, 0x22a2, 0xa485, 0x0098, 0x20a2, 0x20a3,
-       0x0000, 0x004e, 0x003e, 0x080c, 0x7810, 0x22a2, 0x20a3, 0x0000,
-       0x7a08, 0x22a2, 0x2fa2, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x002e,
-       0x0005, 0x080c, 0x7810, 0x22a2, 0x20a3, 0x0000, 0x7a08, 0x22a2,
-       0x7810, 0x20a2, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x002e, 0x0005,
-       0x00c6, 0x00f6, 0x6004, 0xa08a, 0x0085, 0x0a0c, 0x14f6, 0xa08a,
-       0x008c, 0x1a0c, 0x14f6, 0x6118, 0x2178, 0x79a0, 0x2011, 0xad34,
-       0x2214, 0xd2ac, 0x1110, 0xd1bc, 0x0150, 0x7900, 0xd1f4, 0x0120,
-       0x7914, 0xa18c, 0x00ff, 0x0040, 0x2009, 0x0000, 0x0028, 0xa1f8,
-       0x2be6, 0x2f0d, 0xa18c, 0x00ff, 0x2c78, 0x2061, 0x0100, 0x619a,
-       0xa082, 0x0085, 0x001b, 0x00fe, 0x00ce, 0x0005, 0x7247, 0x7251,
-       0x726c, 0x7245, 0x7245, 0x7245, 0x7247, 0x080c, 0x14f6, 0x0146,
-       0x20a1, 0x020b, 0x04a1, 0x60c3, 0x0000, 0x080c, 0x7821, 0x014e,
-       0x0005, 0x0146, 0x20a1, 0x020b, 0x080c, 0x72b8, 0x20a3, 0x0000,
-       0x20a3, 0x0000, 0x7808, 0x20a2, 0x7810, 0x20a2, 0x20a3, 0x0000,
-       0x20a3, 0xffff, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x60c3, 0x000c,
-       0x080c, 0x7821, 0x014e, 0x0005, 0x0146, 0x20a1, 0x020b, 0x080c,
-       0x72f2, 0x20a3, 0x0003, 0x20a3, 0x0300, 0x20a3, 0x0000, 0x20a3,
-       0x0000, 0x60c3, 0x0004, 0x080c, 0x7821, 0x014e, 0x0005, 0x0026,
-       0x20e1, 0x9080, 0x20e1, 0x4000, 0x7818, 0xa080, 0x0028, 0x2004,
-       0x2011, 0xad34, 0x2214, 0xd2ac, 0x1118, 0xa092, 0x007e, 0x0288,
-       0x00d6, 0xa0e8, 0xae34, 0x2d6c, 0x6810, 0xa085, 0x8100, 0x20a2,
-       0x6814, 0x20a2, 0x2069, 0xad1b, 0x2da6, 0x8d68, 0x2da6, 0x00de,
-       0x0088, 0x00d6, 0xa0e8, 0xae34, 0x2d6c, 0x6810, 0xa085, 0x8100,
-       0x20a2, 0x6814, 0x20a2, 0x00de, 0x20a3, 0x0000, 0x2011, 0xad14,
-       0x2214, 0x22a2, 0x20a3, 0x0009, 0x20a3, 0x0000, 0x0804, 0x7175,
-       0x0026, 0x20e1, 0x9080, 0x20e1, 0x4000, 0x7818, 0xa080, 0x0028,
-       0x2004, 0x2011, 0xad34, 0x2214, 0xd2ac, 0x1118, 0xa092, 0x007e,
-       0x0288, 0x00d6, 0xa0e8, 0xae34, 0x2d6c, 0x6810, 0xa085, 0x8400,
-       0x20a2, 0x6814, 0x20a2, 0x2069, 0xad1b, 0x2da6, 0x8d68, 0x2da6,
-       0x00de, 0x0088, 0x00d6, 0xa0e8, 0xae34, 0x2d6c, 0x6810, 0xa085,
-       0x8400, 0x20a2, 0x6814, 0x20a2, 0x00de, 0x20a3, 0x0000, 0x2011,
-       0xad14, 0x2214, 0x22a2, 0x2001, 0x0099, 0x20a2, 0x20a3, 0x0000,
-       0x0804, 0x7201, 0x0026, 0x20e1, 0x9080, 0x20e1, 0x4000, 0x7818,
-       0xa080, 0x0028, 0x2004, 0x2011, 0xad34, 0x2214, 0xd2ac, 0x1118,
-       0xa092, 0x007e, 0x0288, 0x00d6, 0xa0e8, 0xae34, 0x2d6c, 0x6810,
-       0xa085, 0x8500, 0x20a2, 0x6814, 0x20a2, 0x2069, 0xad1b, 0x2da6,
-       0x8d68, 0x2da6, 0x00de, 0x0088, 0x00d6, 0xa0e8, 0xae34, 0x2d6c,
-       0x6810, 0xa085, 0x8500, 0x20a2, 0x6814, 0x20a2, 0x00de, 0x20a3,
-       0x0000, 0x2011, 0xad14, 0x2214, 0x22a2, 0x2001, 0x0099, 0x20a2,
-       0x20a3, 0x0000, 0x0804, 0x7201, 0x00c6, 0x00f6, 0x2c78, 0x7804,
-       0xa08a, 0x0040, 0x0a0c, 0x14f6, 0xa08a, 0x0053, 0x1a0c, 0x14f6,
-       0x7918, 0x2160, 0x61a0, 0x2011, 0xad34, 0x2214, 0xd2ac, 0x1110,
-       0xd1bc, 0x0150, 0x6100, 0xd1f4, 0x0120, 0x6114, 0xa18c, 0x00ff,
-       0x0040, 0x2009, 0x0000, 0x0028, 0xa1e0, 0x2be6, 0x2c0d, 0xa18c,
-       0x00ff, 0x2061, 0x0100, 0x619a, 0xa082, 0x0040, 0x001b, 0x00fe,
-       0x00ce, 0x0005, 0x736f, 0x747b, 0x7418, 0x761a, 0x736d, 0x736d,
-       0x736d, 0x736d, 0x736d, 0x736d, 0x736d, 0x7b41, 0x7b51, 0x7b61,
-       0x7b71, 0x736d, 0x7f79, 0x736d, 0x7b30, 0x080c, 0x14f6, 0x00d6,
-       0x0156, 0x0146, 0x780b, 0xffff, 0x20a1, 0x020b, 0x080c, 0x73cf,
-       0x7910, 0x2168, 0x6948, 0x7952, 0x21a2, 0xa016, 0x22a2, 0x22a2,
-       0x22a2, 0x694c, 0xa184, 0x000f, 0x1118, 0x2001, 0x0005, 0x0040,
-       0xd184, 0x0118, 0x2001, 0x0004, 0x0018, 0xa084, 0x0006, 0x8004,
-       0x0016, 0x2008, 0x7858, 0xa084, 0x00ff, 0x8007, 0xa105, 0x001e,
-       0x20a2, 0xd1ac, 0x0118, 0x20a3, 0x0002, 0x0048, 0xd1b4, 0x0118,
-       0x20a3, 0x0001, 0x0020, 0x20a3, 0x0000, 0x2230, 0x0010, 0x6a80,
-       0x6e7c, 0x20a9, 0x0008, 0x0136, 0xad88, 0x0017, 0x2198, 0x20a1,
-       0x021b, 0x53a6, 0x013e, 0x20a1, 0x020b, 0x22a2, 0x26a2, 0x60c3,
-       0x0020, 0x20e1, 0x9080, 0x6014, 0xa084, 0x0004, 0xa085, 0x0009,
-       0x6016, 0x2001, 0xafe3, 0x2003, 0x07d0, 0x2001, 0xafe2, 0x2003,
-       0x0009, 0x080c, 0x17bf, 0x014e, 0x015e, 0x00de, 0x0005, 0x20e1,
-       0x9080, 0x20e1, 0x4000, 0x7a18, 0xa280, 0x0023, 0x2014, 0x8210,
-       0xa294, 0x00ff, 0x2202, 0x8217, 0x7818, 0xa080, 0x0028, 0x2004,
-       0x2019, 0xad34, 0x231c, 0xd3ac, 0x1110, 0xd0bc, 0x0188, 0x00d6,
-       0xa0e8, 0xae34, 0x2d6c, 0x6810, 0xa085, 0x0600, 0x20a2, 0x6814,
-       0x20a2, 0x2069, 0xad1b, 0x2da6, 0x8d68, 0x2da6, 0x00de, 0x0088,
-       0x00d6, 0xa0e8, 0xae34, 0x2d6c, 0x6810, 0xa085, 0x0600, 0x20a2,
-       0x6814, 0x20a2, 0x00de, 0x20a3, 0x0000, 0x2009, 0xad14, 0x210c,
-       0x21a2, 0x20a3, 0x0829, 0x20a3, 0x0000, 0x22a2, 0x20a3, 0x0000,
-       0x2fa2, 0x20a3, 0xffff, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x0005,
-       0x00d6, 0x0156, 0x0136, 0x0146, 0x20a1, 0x020b, 0x00c1, 0x7810,
-       0x2068, 0x6860, 0x20a2, 0x685c, 0x20a2, 0x6880, 0x20a2, 0x687c,
-       0x20a2, 0xa006, 0x20a2, 0x20a2, 0x20a2, 0x20a2, 0x60c3, 0x000c,
-       0x080c, 0x7821, 0x014e, 0x013e, 0x015e, 0x00de, 0x0005, 0x0026,
-       0x20e1, 0x9080, 0x20e1, 0x4000, 0x7818, 0xa080, 0x0028, 0x2004,
-       0x2011, 0xad34, 0x2214, 0xd2ac, 0x1110, 0xd0bc, 0x0188, 0x00d6,
-       0xa0e8, 0xae34, 0x2d6c, 0x6810, 0xa085, 0x0500, 0x20a2, 0x6814,
-       0x20a2, 0x2069, 0xad1b, 0x2da6, 0x8d68, 0x2da6, 0x00de, 0x0088,
-       0x00d6, 0xa0e8, 0xae34, 0x2d6c, 0x6810, 0xa085, 0x0500, 0x20a2,
-       0x6814, 0x20a2, 0x00de, 0x20a3, 0x0000, 0x2011, 0xad14, 0x2214,
-       0x22a2, 0x20a3, 0x0889, 0x20a3, 0x0000, 0x080c, 0x7810, 0x22a2,
-       0x20a3, 0x0000, 0x7a08, 0x22a2, 0x2fa2, 0x20a3, 0x0000, 0x20a3,
-       0x0000, 0x002e, 0x0005, 0x00d6, 0x0156, 0x0136, 0x0146, 0x7810,
-       0xa06d, 0x080c, 0x5025, 0x0148, 0x684c, 0xa084, 0x2020, 0xa086,
-       0x2020, 0x1118, 0x7820, 0xc0cd, 0x7822, 0x20a1, 0x020b, 0x080c,
-       0x75d0, 0xa016, 0x22a2, 0x22a2, 0x22a2, 0x22a2, 0x22a2, 0x7810,
-       0xa084, 0xf000, 0x1130, 0x7810, 0xa084, 0x0700, 0x8007, 0x0043,
-       0x0010, 0xa006, 0x002b, 0x014e, 0x013e, 0x015e, 0x00de, 0x0005,
-       0x74b2, 0x7547, 0x7550, 0x7579, 0x758c, 0x75a7, 0x75b0, 0x74b0,
-       0x080c, 0x14f6, 0x0016, 0x0036, 0x694c, 0xa18c, 0x0003, 0x0118,
-       0xa186, 0x0003, 0x1170, 0x6b78, 0x7820, 0xd0cc, 0x0108, 0xc3e5,
-       0x23a2, 0x6868, 0x20a2, 0x6864, 0x20a2, 0x003e, 0x001e, 0x0804,
-       0x7583, 0xa186, 0x0001, 0x190c, 0x14f6, 0x6b78, 0x7820, 0xd0cc,
-       0x0108, 0xc3e5, 0x23a2, 0x6868, 0x20a2, 0x6864, 0x20a2, 0x22a2,
-       0x6874, 0x20a2, 0x22a2, 0x687c, 0x20a2, 0x2009, 0x0018, 0xa384,
-       0x0300, 0x0904, 0x7541, 0xd3c4, 0x0110, 0x687c, 0xa108, 0xd3cc,
-       0x0110, 0x6874, 0xa108, 0x0156, 0x20a9, 0x000d, 0xad80, 0x0020,
-       0x201c, 0x831f, 0x23a2, 0x8000, 0x1f04, 0x74f0, 0x015e, 0x22a2,
-       0x22a2, 0x22a2, 0xa184, 0x0003, 0x0904, 0x7541, 0x20a1, 0x020b,
-       0x20e1, 0x9080, 0x20e1, 0x4000, 0x0006, 0x7818, 0xa080, 0x0028,
-       0x2004, 0x2011, 0xad34, 0x2214, 0xd2ac, 0x1110, 0xd0bc, 0x0188,
-       0x00d6, 0xa0e8, 0xae34, 0x2d6c, 0x6810, 0xa085, 0x0700, 0x20a2,
-       0x6814, 0x20a2, 0x2069, 0xad1b, 0x2da6, 0x8d68, 0x2da6, 0x00de,
-       0x0088, 0x00d6, 0xa0e8, 0xae34, 0x2d6c, 0x6810, 0xa085, 0x0700,
-       0x20a2, 0x6814, 0x20a2, 0x00de, 0x20a3, 0x0000, 0x2011, 0xad14,
-       0x2214, 0x22a2, 0x000e, 0x7b20, 0xd3cc, 0x0118, 0x20a3, 0x0889,
-       0x0010, 0x20a3, 0x0898, 0x20a2, 0x080c, 0x7810, 0x22a2, 0x20a3,
-       0x0000, 0x61c2, 0x003e, 0x001e, 0x080c, 0x7821, 0x0005, 0x2011,
-       0x0008, 0x7820, 0xd0cc, 0x0108, 0xc2e5, 0x22a2, 0xa016, 0x0488,
-       0x2011, 0x0302, 0x7820, 0xd0cc, 0x0108, 0xc2e5, 0x22a2, 0xa016,
-       0x22a2, 0x22a2, 0x22a2, 0x20a3, 0x0012, 0x22a2, 0x20a3, 0x0008,
-       0x22a2, 0x22a2, 0x22a2, 0x22a2, 0x20a3, 0x7000, 0x20a3, 0x0500,
-       0x22a2, 0x20a3, 0x000a, 0x22a2, 0x22a2, 0x20a3, 0x2500, 0x22a2,
-       0x22a2, 0x22a2, 0x22a2, 0x22a2, 0x60c3, 0x0032, 0x080c, 0x7821,
-       0x0005, 0x2011, 0x0028, 0x7820, 0xd0cc, 0x0108, 0xc2e5, 0x22a2,
-       0xa016, 0x22a2, 0x22a2, 0x22a2, 0x22a2, 0x22a2, 0x22a2, 0x60c3,
-       0x0018, 0x080c, 0x7821, 0x0005, 0x2011, 0x0100, 0x7820, 0xd0cc,
-       0x0108, 0xc2e5, 0x22a2, 0xa016, 0x22a2, 0x22a2, 0x22a2, 0x22a2,
-       0x22a2, 0x20a3, 0x0008, 0x22a2, 0x7854, 0xa084, 0x00ff, 0x20a2,
-       0x22a2, 0x22a2, 0x60c3, 0x0020, 0x080c, 0x7821, 0x0005, 0x2011,
-       0x0008, 0x7820, 0xd0cc, 0x0108, 0xc2e5, 0x22a2, 0xa016, 0x0888,
-       0x0036, 0x7b10, 0xa384, 0xff00, 0x7812, 0xa384, 0x00ff, 0x8001,
-       0x1138, 0x7820, 0xd0cc, 0x0108, 0xc2e5, 0x22a2, 0x003e, 0x0808,
-       0x0046, 0x2021, 0x0800, 0x0006, 0x7820, 0xd0cc, 0x000e, 0x0108,
-       0xc4e5, 0x24a2, 0x004e, 0x22a2, 0x20a2, 0x003e, 0x0804, 0x7583,
-       0x0026, 0x20e1, 0x9080, 0x20e1, 0x4000, 0x7818, 0xa080, 0x0028,
-       0x2004, 0x2011, 0xad34, 0x2214, 0xd2ac, 0x1110, 0xd0bc, 0x0188,
-       0x00d6, 0xa0e8, 0xae34, 0x2d6c, 0x6810, 0xa085, 0x0700, 0x20a2,
-       0x6814, 0x20a2, 0x2069, 0xad1b, 0x2da6, 0x8d68, 0x2da6, 0x00de,
-       0x0088, 0x00d6, 0xa0e8, 0xae34, 0x2d6c, 0x6810, 0xa085, 0x0700,
-       0x20a2, 0x6814, 0x20a2, 0x00de, 0x20a3, 0x0000, 0x2011, 0xad14,
-       0x2214, 0x22a2, 0x7820, 0xd0cc, 0x0118, 0x20a3, 0x0889, 0x0010,
-       0x20a3, 0x0898, 0x20a3, 0x0000, 0x080c, 0x7810, 0x22a2, 0x20a3,
-       0x0000, 0x7a08, 0x22a2, 0x2fa2, 0x20a3, 0x0000, 0x20a3, 0x0000,
-       0x002e, 0x0005, 0x00d6, 0x0156, 0x0136, 0x0146, 0x0016, 0x0036,
-       0x7810, 0xa084, 0x0700, 0x8007, 0x003b, 0x003e, 0x001e, 0x014e,
-       0x013e, 0x015e, 0x00de, 0x0005, 0x7634, 0x7634, 0x7636, 0x7634,
-       0x7634, 0x7634, 0x7658, 0x7634, 0x080c, 0x14f6, 0x7910, 0xa18c,
-       0xf8ff, 0xa18d, 0x0600, 0x7912, 0x20a1, 0x020b, 0x2009, 0x0003,
-       0x00f9, 0x00d6, 0x2069, 0xad51, 0x6804, 0xd0bc, 0x0130, 0x682c,
-       0xa084, 0x00ff, 0x8007, 0x20a2, 0x0010, 0x20a3, 0x3f00, 0x00de,
-       0x22a2, 0x22a2, 0x22a2, 0x60c3, 0x0001, 0x080c, 0x7821, 0x0005,
-       0x20a1, 0x020b, 0x2009, 0x0003, 0x0019, 0x20a3, 0x7f00, 0x0c80,
-       0x0026, 0x20e1, 0x9080, 0x20e1, 0x4000, 0x7818, 0xa080, 0x0028,
-       0x2004, 0x2011, 0xad34, 0x2214, 0xd2ac, 0x1110, 0xd0bc, 0x0188,
-       0x00d6, 0xa0e8, 0xae34, 0x2d6c, 0x6810, 0xa085, 0x0100, 0x20a2,
-       0x6814, 0x20a2, 0x2069, 0xad1b, 0x2da6, 0x8d68, 0x2da6, 0x00de,
-       0x0088, 0x00d6, 0xa0e8, 0xae34, 0x2d6c, 0x6810, 0xa085, 0x0100,
-       0x20a2, 0x6814, 0x20a2, 0x00de, 0x20a3, 0x0000, 0x2011, 0xad14,
-       0x2214, 0x22a2, 0x20a3, 0x0888, 0xa18d, 0x0008, 0x21a2, 0x080c,
-       0x7810, 0x22a2, 0x20a3, 0x0000, 0x7a08, 0x22a2, 0x2fa2, 0x20a3,
-       0x0000, 0x20a3, 0x0000, 0x002e, 0x0005, 0x00e6, 0x00d6, 0x00c6,
-       0x0056, 0x0046, 0x0036, 0x2061, 0x0100, 0x2071, 0xad00, 0x7150,
-       0x7818, 0x2068, 0x68a0, 0x2028, 0x76d0, 0xd6ac, 0x1130, 0xd0bc,
-       0x1120, 0x6910, 0x6a14, 0x7450, 0x0020, 0x6910, 0x6a14, 0x736c,
-       0x7470, 0x781c, 0xa0be, 0x0006, 0x0904, 0x775b, 0xa0be, 0x000a,
-       0x15e8, 0xa185, 0x0200, 0x6062, 0x6266, 0x636a, 0x646e, 0x6073,
-       0x2029, 0x6077, 0x0000, 0x688c, 0x8000, 0xa084, 0x00ff, 0x688e,
-       0x8007, 0x607a, 0x607f, 0x0000, 0x2f00, 0x6082, 0x7808, 0x6086,
-       0x7810, 0x2070, 0x7014, 0x608a, 0x7010, 0x608e, 0x700c, 0x60c6,
-       0x7008, 0x60ca, 0x686c, 0x60ce, 0x60af, 0x95d5, 0x60d7, 0x0000,
-       0x609f, 0x0000, 0x080c, 0x8014, 0x2009, 0x07d0, 0x60c4, 0xa084,
-       0xfff0, 0xa005, 0x0110, 0x2009, 0x1b58, 0x080c, 0x6586, 0x003e,
-       0x004e, 0x005e, 0x00ce, 0x00de, 0x00ee, 0x0005, 0x70d0, 0xd0ac,
-       0x1110, 0xd5bc, 0x0138, 0xa185, 0x0100, 0x6062, 0x6266, 0x636a,
-       0x646e, 0x0038, 0xa185, 0x0100, 0x6062, 0x6266, 0x606b, 0x0000,
-       0x646e, 0x6073, 0x0809, 0x6077, 0x0008, 0x688c, 0x8000, 0xa084,
-       0x00ff, 0x688e, 0x8007, 0x607a, 0x607f, 0x0000, 0x2f00, 0x6082,
-       0x7808, 0x6086, 0x7810, 0x2070, 0x7014, 0x608a, 0x7010, 0x608e,
-       0x700c, 0x60c6, 0x7008, 0x60ca, 0x686c, 0x60ce, 0x60af, 0x95d5,
-       0x60d7, 0x0000, 0xa582, 0x0080, 0x0248, 0x6a00, 0xd2f4, 0x0120,
-       0x6a14, 0xa294, 0x00ff, 0x0010, 0x2011, 0x0000, 0x629e, 0x080c,
-       0x8014, 0x2009, 0x07d0, 0x60c4, 0xa084, 0xfff0, 0xa005, 0x0110,
-       0x2009, 0x1b58, 0x080c, 0x6586, 0x003e, 0x004e, 0x005e, 0x00ce,
-       0x00de, 0x00ee, 0x0005, 0x7810, 0x2070, 0x704c, 0xa084, 0x0003,
-       0xa086, 0x0002, 0x0904, 0x77b1, 0x2001, 0xad34, 0x2004, 0xd0ac,
-       0x1110, 0xd5bc, 0x0138, 0xa185, 0x0100, 0x6062, 0x6266, 0x636a,
-       0x646e, 0x0038, 0xa185, 0x0100, 0x6062, 0x6266, 0x606b, 0x0000,
-       0x646e, 0x6073, 0x0880, 0x6077, 0x0008, 0x688c, 0x8000, 0xa084,
-       0x00ff, 0x688e, 0x8007, 0x607a, 0x7834, 0x607e, 0x2f00, 0x6086,
-       0x7808, 0x6082, 0x7060, 0x608a, 0x705c, 0x608e, 0x7080, 0x60c6,
-       0x707c, 0x60ca, 0x707c, 0x792c, 0xa108, 0x792e, 0x7080, 0x7928,
-       0xa109, 0x792a, 0x686c, 0x60ce, 0x60af, 0x95d5, 0x60d7, 0x0000,
-       0xa582, 0x0080, 0x0248, 0x6a00, 0xd2f4, 0x0120, 0x6a14, 0xa294,
-       0x00ff, 0x0010, 0x2011, 0x0000, 0x629e, 0x080c, 0x8011, 0x0804,
-       0x7749, 0x2001, 0xad34, 0x2004, 0xd0ac, 0x1110, 0xd5bc, 0x0138,
-       0xa185, 0x0700, 0x6062, 0x6266, 0x636a, 0x646e, 0x0038, 0xa185,
-       0x0700, 0x6062, 0x6266, 0x606b, 0x0000, 0x646e, 0x080c, 0x5025,
-       0x0180, 0x00d6, 0x7810, 0xa06d, 0x684c, 0x00de, 0xa084, 0x2020,
-       0xa086, 0x2020, 0x1130, 0x7820, 0xc0cd, 0x7822, 0x6073, 0x0889,
-       0x0010, 0x6073, 0x0898, 0x6077, 0x0000, 0x688c, 0x8000, 0xa084,
-       0x00ff, 0x688e, 0x8007, 0x607a, 0x607f, 0x0000, 0x2f00, 0x6086,
-       0x7808, 0x6082, 0x7014, 0x608a, 0x7010, 0x608e, 0x700c, 0x60c6,
-       0x7008, 0x60ca, 0x686c, 0x60ce, 0x60af, 0x95d5, 0x60d7, 0x0000,
-       0xa582, 0x0080, 0x0248, 0x6a00, 0xd2f4, 0x0120, 0x6a14, 0xa294,
-       0x00ff, 0x0010, 0x2011, 0x0000, 0x629e, 0x7820, 0xd0cc, 0x0120,
-       0x080c, 0x8014, 0x0804, 0x7749, 0x080c, 0x8011, 0x0804, 0x7749,
-       0x7a18, 0xa280, 0x0023, 0x2014, 0x8210, 0xa294, 0x00ff, 0x2202,
-       0x8217, 0x0005, 0x00d6, 0x2069, 0xafc7, 0x6843, 0x0001, 0x00de,
-       0x0005, 0x20e1, 0x9080, 0x60a3, 0x0056, 0x60a7, 0x9575, 0x0019,
-       0x080c, 0x6578, 0x0005, 0x0006, 0x6014, 0xa084, 0x0004, 0xa085,
-       0x0009, 0x6016, 0x000e, 0x0005, 0x0006, 0x00c6, 0x2061, 0x0100,
-       0x6014, 0xa084, 0x0004, 0xa085, 0x0008, 0x6016, 0x00ce, 0x000e,
-       0x0005, 0x00c6, 0x00d6, 0x0016, 0x0026, 0x2061, 0x0100, 0x2069,
-       0x0140, 0x080c, 0x574f, 0x1178, 0x2001, 0xafe3, 0x2004, 0xa005,
-       0x1598, 0x080c, 0x57d1, 0x1118, 0x080c, 0x6578, 0x0468, 0x00c6,
-       0x2061, 0xafc7, 0x00d8, 0x6904, 0xa194, 0x4000, 0x0550, 0x08a1,
-       0x6803, 0x1000, 0x6803, 0x0000, 0x00c6, 0x2061, 0xafc7, 0x6128,
-       0xa192, 0x00c8, 0x1258, 0x8108, 0x612a, 0x6124, 0x00ce, 0x81ff,
-       0x0198, 0x080c, 0x6578, 0x080c, 0x782b, 0x0070, 0x6124, 0xa1e5,
-       0x0000, 0x0140, 0x080c, 0xaca2, 0x2009, 0x0014, 0x080c, 0x80a7,
-       0x080c, 0x6581, 0x00ce, 0x0000, 0x002e, 0x001e, 0x00de, 0x00ce,
-       0x0005, 0x2001, 0xafe3, 0x2004, 0xa005, 0x1db0, 0x00c6, 0x2061,
-       0xafc7, 0x6128, 0xa192, 0x0003, 0x1e08, 0x8108, 0x612a, 0x00ce,
-       0x080c, 0x6578, 0x080c, 0x485e, 0x0c38, 0x00c6, 0x00d6, 0x00e6,
-       0x0016, 0x0026, 0x080c, 0x658e, 0x2071, 0xafc7, 0x713c, 0x81ff,
-       0x0570, 0x2061, 0x0100, 0x2069, 0x0140, 0x080c, 0x574f, 0x1188,
-       0x0036, 0x2019, 0x0001, 0x080c, 0x7a64, 0x003e, 0x713c, 0x2160,
-       0x080c, 0xaca2, 0x2009, 0x004a, 0x080c, 0x80a7, 0x080c, 0x57d1,
-       0x00b0, 0x6904, 0xa194, 0x4000, 0x01c0, 0x6803, 0x1000, 0x6803,
-       0x0000, 0x0036, 0x2019, 0x0001, 0x080c, 0x7a64, 0x003e, 0x713c,
-       0x2160, 0x080c, 0xaca2, 0x2009, 0x004a, 0x080c, 0x80a7, 0x002e,
-       0x001e, 0x00ee, 0x00de, 0x00ce, 0x0005, 0x0c58, 0x00e6, 0x00d6,
-       0x00c6, 0x0066, 0x0056, 0x0046, 0x0006, 0x0126, 0x2091, 0x8000,
-       0x6018, 0x2068, 0x6ca0, 0x2071, 0xafc7, 0x7018, 0x2068, 0x8dff,
-       0x0198, 0x68a0, 0xa406, 0x0118, 0x6854, 0x2068, 0x0cc0, 0x6010,
-       0x2060, 0x643c, 0x6540, 0x6e48, 0x2d60, 0x080c, 0x4e41, 0x0120,
-       0x080c, 0x7b88, 0xa085, 0x0001, 0x012e, 0x000e, 0x004e, 0x005e,
-       0x006e, 0x00ce, 0x00de, 0x00ee, 0x0005, 0x20a1, 0x020b, 0x080c,
-       0x710e, 0x20a3, 0x1200, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x781c,
-       0xa086, 0x0004, 0x1110, 0x6098, 0x0018, 0x2001, 0xad14, 0x2004,
-       0x20a2, 0x7834, 0x20a2, 0x7838, 0x20a2, 0x20a9, 0x0010, 0xa006,
-       0x20a2, 0x1f04, 0x7928, 0x20a2, 0x20a2, 0x60c3, 0x002c, 0x080c,
-       0x7821, 0x0005, 0x0156, 0x0146, 0x20a1, 0x020b, 0x080c, 0x710e,
-       0x20a3, 0x0f00, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x7808, 0x20a2,
-       0x60c3, 0x0008, 0x080c, 0x7821, 0x014e, 0x015e, 0x0005, 0x0156,
-       0x0146, 0x20a1, 0x020b, 0x080c, 0x71aa, 0x20a3, 0x0200, 0x20a3,
-       0x0000, 0x20a9, 0x0006, 0x2011, 0xad40, 0x2019, 0xad41, 0x23a6,
-       0x22a6, 0xa398, 0x0002, 0xa290, 0x0002, 0x1f04, 0x7957, 0x20a3,
-       0x0000, 0x20a3, 0x0000, 0x60c3, 0x001c, 0x080c, 0x7821, 0x014e,
-       0x015e, 0x0005, 0x0156, 0x0146, 0x0016, 0x0026, 0x20a1, 0x020b,
-       0x080c, 0x7183, 0x080c, 0x7199, 0x7810, 0xa080, 0x0000, 0x2004,
-       0xa080, 0x0015, 0x2098, 0x7808, 0xa088, 0x0002, 0x21a8, 0x53a6,
-       0xa080, 0x0004, 0x8003, 0x60c2, 0x080c, 0x7821, 0x002e, 0x001e,
-       0x014e, 0x015e, 0x0005, 0x0156, 0x0146, 0x20a1, 0x020b, 0x080c,
-       0x710e, 0x20a3, 0x6200, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x7808,
-       0x20a2, 0x60c3, 0x0008, 0x080c, 0x7821, 0x014e, 0x015e, 0x0005,
-       0x0156, 0x0146, 0x0016, 0x0026, 0x20a1, 0x020b, 0x080c, 0x710e,
-       0x7810, 0xa080, 0x0000, 0x2004, 0xa080, 0x0017, 0x2098, 0x7808,
-       0xa088, 0x0002, 0x21a8, 0x53a6, 0x8003, 0x60c2, 0x080c, 0x7821,
-       0x002e, 0x001e, 0x014e, 0x015e, 0x0005, 0x00e6, 0x00c6, 0x0006,
-       0x0126, 0x2091, 0x8000, 0x2071, 0xafc7, 0x700c, 0x2060, 0x8cff,
-       0x0178, 0x080c, 0x9789, 0x1110, 0x080c, 0x85f3, 0x600c, 0x0006,
-       0x080c, 0x994e, 0x080c, 0x8078, 0x080c, 0x7b88, 0x00ce, 0x0c78,
-       0x700f, 0x0000, 0x700b, 0x0000, 0x012e, 0x000e, 0x00ce, 0x00ee,
-       0x0005, 0x0126, 0x0156, 0x00f6, 0x00e6, 0x00d6, 0x00c6, 0x0026,
-       0x0016, 0x0006, 0x2091, 0x8000, 0x2069, 0x0100, 0x2079, 0x0140,
-       0x2071, 0xafc7, 0x7024, 0x2060, 0x8cff, 0x05a0, 0x080c, 0x7834,
-       0x68c3, 0x0000, 0x080c, 0x6581, 0x2009, 0x0013, 0x080c, 0x80a7,
-       0x20a9, 0x01f4, 0x6824, 0xd094, 0x0158, 0x6827, 0x0004, 0x7804,
-       0xa084, 0x4000, 0x01a0, 0x7803, 0x1000, 0x7803, 0x0000, 0x0078,
-       0xd084, 0x0118, 0x6827, 0x0001, 0x0010, 0x1f04, 0x7a02, 0x7804,
-       0xa084, 0x1000, 0x0120, 0x7803, 0x0100, 0x7803, 0x0000, 0x6824,
-       0x000e, 0x001e, 0x002e, 0x00ce, 0x00de, 0x00ee, 0x00fe, 0x015e,
-       0x012e, 0x0005, 0x2001, 0xad00, 0x2004, 0xa096, 0x0001, 0x0550,
-       0xa096, 0x0004, 0x0538, 0x6817, 0x0008, 0x68c3, 0x0000, 0x2011,
-       0x481b, 0x080c, 0x650d, 0x20a9, 0x01f4, 0x6824, 0xd094, 0x0158,
-       0x6827, 0x0004, 0x7804, 0xa084, 0x4000, 0x01a0, 0x7803, 0x1000,
-       0x7803, 0x0000, 0x0078, 0xd084, 0x0118, 0x6827, 0x0001, 0x0010,
-       0x1f04, 0x7a3d, 0x7804, 0xa084, 0x1000, 0x0120, 0x7803, 0x0100,
-       0x7803, 0x0000, 0x000e, 0x001e, 0x002e, 0x00ce, 0x00de, 0x00ee,
-       0x00fe, 0x015e, 0x012e, 0x0005, 0x0126, 0x0156, 0x00f6, 0x00e6,
-       0x00d6, 0x00c6, 0x0026, 0x0016, 0x0006, 0x2091, 0x8000, 0x2069,
-       0x0100, 0x2079, 0x0140, 0x2071, 0xafc7, 0x703c, 0x2060, 0x8cff,
-       0x0904, 0x7ad5, 0x6817, 0x0010, 0x2009, 0x00fa, 0x8109, 0x1df0,
-       0x68c7, 0x0000, 0x68cb, 0x0008, 0x080c, 0x658e, 0x080c, 0x20b5,
-       0x0046, 0x2009, 0x017f, 0x200b, 0x00a5, 0x2021, 0x0169, 0x2404,
-       0xa084, 0x000f, 0xa086, 0x0004, 0x11b0, 0x68c7, 0x0000, 0x68cb,
-       0x0008, 0x00e6, 0x00f6, 0x2079, 0x0020, 0x2071, 0xb01e, 0x6814,
-       0xa084, 0x0184, 0xa085, 0x0012, 0x6816, 0x7803, 0x0008, 0x7003,
-       0x0000, 0x00fe, 0x00ee, 0x200b, 0x0000, 0x004e, 0xa39d, 0x0000,
-       0x1120, 0x2009, 0x0049, 0x080c, 0x80a7, 0x20a9, 0x03e8, 0x6824,
-       0xd094, 0x0158, 0x6827, 0x0004, 0x7804, 0xa084, 0x4000, 0x01a0,
-       0x7803, 0x1000, 0x7803, 0x0000, 0x0078, 0xd08c, 0x0118, 0x6827,
-       0x0002, 0x0010, 0x1f04, 0x7ab7, 0x7804, 0xa084, 0x1000, 0x0120,
-       0x7803, 0x0100, 0x7803, 0x0000, 0x6824, 0x000e, 0x001e, 0x002e,
-       0x00ce, 0x00de, 0x00ee, 0x00fe, 0x015e, 0x012e, 0x0005, 0x00d6,
-       0x0126, 0x2091, 0x8000, 0x2069, 0xafc7, 0x6a06, 0x012e, 0x00de,
-       0x0005, 0x00d6, 0x0126, 0x2091, 0x8000, 0x2069, 0xafc7, 0x6a32,
-       0x012e, 0x00de, 0x0005, 0x00f6, 0x00e6, 0x00c6, 0x0066, 0x0006,
-       0x0126, 0x2071, 0xafc7, 0x7614, 0x2660, 0x2678, 0x2091, 0x8000,
-       0x8cff, 0x0538, 0x601c, 0xa206, 0x1500, 0x7014, 0xac36, 0x1110,
-       0x660c, 0x7616, 0x7010, 0xac36, 0x1140, 0x2c00, 0xaf36, 0x0118,
-       0x2f00, 0x7012, 0x0010, 0x7013, 0x0000, 0x660c, 0x0066, 0x2c00,
-       0xaf06, 0x0110, 0x7e0e, 0x0008, 0x2678, 0x600f, 0x0000, 0x080c,
-       0x974e, 0x080c, 0x7b88, 0x00ce, 0x08d8, 0x2c78, 0x600c, 0x2060,
-       0x08b8, 0x012e, 0x000e, 0x006e, 0x00ce, 0x00ee, 0x00fe, 0x0005,
-       0x0156, 0x0146, 0x20a1, 0x020b, 0x080c, 0x73cf, 0x7810, 0x20a2,
-       0xa006, 0x20a2, 0x20a2, 0x20a2, 0x20a2, 0x20a3, 0x1000, 0x0804,
-       0x7b80, 0x0156, 0x0146, 0x20a1, 0x020b, 0x080c, 0x73cf, 0x7810,
-       0x20a2, 0xa006, 0x20a2, 0x20a2, 0x20a2, 0x20a2, 0x20a3, 0x4000,
-       0x0478, 0x0156, 0x0146, 0x20a1, 0x020b, 0x080c, 0x73cf, 0x7810,
-       0x20a2, 0xa006, 0x20a2, 0x20a2, 0x20a2, 0x20a2, 0x20a3, 0x2000,
-       0x00f8, 0x0156, 0x0146, 0x20a1, 0x020b, 0x080c, 0x73cf, 0x7810,
-       0x20a2, 0xa006, 0x20a2, 0x20a2, 0x20a2, 0x20a2, 0x20a3, 0x0400,
-       0x0078, 0x0156, 0x0146, 0x20a1, 0x020b, 0x080c, 0x73cf, 0x7810,
-       0x20a2, 0xa006, 0x20a2, 0x20a2, 0x20a2, 0x20a2, 0x20a3, 0x0200,
-       0x0089, 0x60c3, 0x0020, 0x080c, 0x7821, 0x014e, 0x015e, 0x0005,
-       0x00e6, 0x2071, 0xafc7, 0x7020, 0xa005, 0x0110, 0x8001, 0x7022,
-       0x00ee, 0x0005, 0x20a9, 0x0008, 0x20a2, 0x1f04, 0x7b94, 0x20a2,
-       0x20a2, 0x0005, 0x00f6, 0x00e6, 0x00d6, 0x00c6, 0x0076, 0x0066,
-       0x0006, 0x0126, 0x2091, 0x8000, 0x2071, 0xafc7, 0x7614, 0x2660,
-       0x2678, 0x2039, 0x0001, 0x87ff, 0x0904, 0x7c24, 0x8cff, 0x0904,
-       0x7c24, 0x601c, 0xa086, 0x0006, 0x1904, 0x7c1f, 0x88ff, 0x0138,
-       0x2800, 0xac06, 0x1904, 0x7c1f, 0x2039, 0x0000, 0x0050, 0x6018,
-       0xa206, 0x1904, 0x7c1f, 0x85ff, 0x0120, 0x6050, 0xa106, 0x1904,
-       0x7c1f, 0x7024, 0xac06, 0x1538, 0x2069, 0x0100, 0x68c0, 0xa005,
-       0x01f0, 0x080c, 0x6581, 0x6817, 0x0008, 0x68c3, 0x0000, 0x080c,
-       0x7ca8, 0x7027, 0x0000, 0x0036, 0x2069, 0x0140, 0x6b04, 0xa384,
-       0x1000, 0x0120, 0x6803, 0x0100, 0x6803, 0x0000, 0x2069, 0x0100,
-       0x6824, 0xd084, 0x0110, 0x6827, 0x0001, 0x003e, 0x0020, 0x6003,
-       0x0009, 0x630a, 0x0460, 0x7014, 0xac36, 0x1110, 0x660c, 0x7616,
-       0x7010, 0xac36, 0x1140, 0x2c00, 0xaf36, 0x0118, 0x2f00, 0x7012,
-       0x0010, 0x7013, 0x0000, 0x660c, 0x0066, 0x2c00, 0xaf06, 0x0110,
-       0x7e0e, 0x0008, 0x2678, 0x89ff, 0x1158, 0x600f, 0x0000, 0x6010,
-       0x2068, 0x080c, 0x9596, 0x0110, 0x080c, 0xa91f, 0x080c, 0x974e,
-       0x080c, 0x7b88, 0x88ff, 0x1190, 0x00ce, 0x0804, 0x7bab, 0x2c78,
-       0x600c, 0x2060, 0x0804, 0x7bab, 0xa006, 0x012e, 0x000e, 0x006e,
-       0x007e, 0x00ce, 0x00de, 0x00ee, 0x00fe, 0x0005, 0x6017, 0x0000,
-       0x00ce, 0xa8c5, 0x0001, 0x0c88, 0x00f6, 0x00e6, 0x00d6, 0x00c6,
-       0x0066, 0x0026, 0x0006, 0x0126, 0x2091, 0x8000, 0x2071, 0xafc7,
-       0x7638, 0x2660, 0x2678, 0x8cff, 0x0904, 0x7c98, 0x601c, 0xa086,
-       0x0006, 0x1904, 0x7c93, 0x87ff, 0x0128, 0x2700, 0xac06, 0x1904,
-       0x7c93, 0x0040, 0x6018, 0xa206, 0x15f0, 0x85ff, 0x0118, 0x6050,
-       0xa106, 0x15c8, 0x703c, 0xac06, 0x1170, 0x0036, 0x2019, 0x0001,
-       0x080c, 0x7a64, 0x7033, 0x0000, 0x703f, 0x0000, 0x7043, 0x0000,
-       0x7047, 0x0000, 0x003e, 0x7038, 0xac36, 0x1110, 0x660c, 0x763a,
-       0x7034, 0xac36, 0x1140, 0x2c00, 0xaf36, 0x0118, 0x2f00, 0x7036,
-       0x0010, 0x7037, 0x0000, 0x660c, 0x0066, 0x2c00, 0xaf06, 0x0110,
-       0x7e0e, 0x0008, 0x2678, 0x600f, 0x0000, 0x6010, 0x2068, 0x080c,
-       0x9596, 0x0110, 0x080c, 0xa91f, 0x080c, 0x974e, 0x87ff, 0x1190,
-       0x00ce, 0x0804, 0x7c43, 0x2c78, 0x600c, 0x2060, 0x0804, 0x7c43,
-       0xa006, 0x012e, 0x000e, 0x002e, 0x006e, 0x00ce, 0x00de, 0x00ee,
-       0x00fe, 0x0005, 0x6017, 0x0000, 0x00ce, 0xa7bd, 0x0001, 0x0c88,
-       0x00e6, 0x2071, 0xafc7, 0x2001, 0xad00, 0x2004, 0xa086, 0x0002,
-       0x1118, 0x7007, 0x0005, 0x0010, 0x7007, 0x0000, 0x00ee, 0x0005,
-       0x00f6, 0x00e6, 0x00c6, 0x0066, 0x0026, 0x0006, 0x0126, 0x2091,
-       0x8000, 0x2071, 0xafc7, 0x2c10, 0x7638, 0x2660, 0x2678, 0x8cff,
-       0x0518, 0x2200, 0xac06, 0x11e0, 0x7038, 0xac36, 0x1110, 0x660c,
-       0x763a, 0x7034, 0xac36, 0x1140, 0x2c00, 0xaf36, 0x0118, 0x2f00,
-       0x7036, 0x0010, 0x7037, 0x0000, 0x660c, 0x2c00, 0xaf06, 0x0110,
-       0x7e0e, 0x0008, 0x2678, 0x600f, 0x0000, 0xa085, 0x0001, 0x0020,
-       0x2c78, 0x600c, 0x2060, 0x08d8, 0x012e, 0x000e, 0x002e, 0x006e,
-       0x00ce, 0x00ee, 0x00fe, 0x0005, 0x00f6, 0x00e6, 0x00d6, 0x00c6,
-       0x0066, 0x0006, 0x0126, 0x2091, 0x8000, 0x2071, 0xafc7, 0x760c,
-       0x2660, 0x2678, 0x8cff, 0x0904, 0x7d7e, 0x6018, 0xa080, 0x0028,
-       0x2004, 0xa206, 0x1904, 0x7d79, 0x7024, 0xac06, 0x1508, 0x2069,
-       0x0100, 0x68c0, 0xa005, 0x0904, 0x7d55, 0x080c, 0x7834, 0x68c3,
-       0x0000, 0x080c, 0x7ca8, 0x7027, 0x0000, 0x0036, 0x2069, 0x0140,
-       0x6b04, 0xa384, 0x1000, 0x0120, 0x6803, 0x0100, 0x6803, 0x0000,
-       0x2069, 0x0100, 0x6824, 0xd084, 0x0110, 0x6827, 0x0001, 0x003e,
-       0x700c, 0xac36, 0x1110, 0x660c, 0x760e, 0x7008, 0xac36, 0x1140,
-       0x2c00, 0xaf36, 0x0118, 0x2f00, 0x700a, 0x0010, 0x700b, 0x0000,
-       0x660c, 0x0066, 0x2c00, 0xaf06, 0x0110, 0x7e0e, 0x0008, 0x2678,
-       0x600f, 0x0000, 0x080c, 0x9778, 0x1158, 0x080c, 0x2aff, 0x080c,
-       0x9789, 0x11f0, 0x080c, 0x85f3, 0x00d8, 0x080c, 0x7ca8, 0x08c0,
-       0x080c, 0x9789, 0x1118, 0x080c, 0x85f3, 0x0090, 0x6010, 0x2068,
-       0x080c, 0x9596, 0x0168, 0x601c, 0xa086, 0x0003, 0x11f8, 0x6837,
-       0x0103, 0x6b4a, 0x6847, 0x0000, 0x080c, 0x510c, 0x080c, 0x9742,
-       0x080c, 0x994e, 0x080c, 0x974e, 0x080c, 0x7b88, 0x00ce, 0x0804,
-       0x7d02, 0x2c78, 0x600c, 0x2060, 0x0804, 0x7d02, 0x012e, 0x000e,
-       0x006e, 0x00ce, 0x00de, 0x00ee, 0x00fe, 0x0005, 0x601c, 0xa086,
-       0x0006, 0x1d30, 0x080c, 0xa91f, 0x0c18, 0x0036, 0x0156, 0x0136,
-       0x0146, 0x3908, 0xa006, 0xa190, 0x0020, 0x221c, 0xa39e, 0x28f9,
-       0x1118, 0x8210, 0x8000, 0x0cc8, 0xa005, 0x0138, 0x20a9, 0x0020,
-       0x2198, 0xa110, 0x22a0, 0x22c8, 0x53a3, 0x014e, 0x013e, 0x015e,
-       0x003e, 0x0005, 0x00d6, 0x20a1, 0x020b, 0x080c, 0x71aa, 0x20a3,
-       0x0200, 0x20a3, 0x0014, 0x60c3, 0x0014, 0x20a3, 0x0000, 0x20a3,
-       0x0000, 0x2099, 0xafa6, 0x20a9, 0x0004, 0x53a6, 0x20a3, 0x0004,
-       0x20a3, 0x7878, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x080c, 0x7821,
-       0x00de, 0x0005, 0x20a1, 0x020b, 0x080c, 0x71aa, 0x20a3, 0x0214,
-       0x20a3, 0x0018, 0x20a3, 0x0800, 0x7810, 0xa084, 0xff00, 0x20a2,
-       0x20a3, 0x0000, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x20a3, 0x0000,
-       0x7810, 0xa084, 0x00ff, 0x20a2, 0x7828, 0x20a2, 0x20a3, 0x0000,
-       0x20a3, 0x0000, 0x60c3, 0x0018, 0x080c, 0x7821, 0x0005, 0x00d6,
-       0x0016, 0x2f68, 0x2009, 0x0035, 0x080c, 0x9a34, 0x1904, 0x7e5d,
-       0x20a1, 0x020b, 0x080c, 0x710e, 0x20a3, 0x1300, 0x20a3, 0x0000,
-       0x7828, 0x2068, 0x681c, 0xa086, 0x0003, 0x0580, 0x7818, 0xa080,
-       0x0028, 0x2014, 0x2001, 0xad34, 0x2004, 0xd0ac, 0x11d0, 0xa286,
-       0x007e, 0x1128, 0x20a3, 0x00ff, 0x20a3, 0xfffe, 0x04b8, 0xa286,
-       0x007f, 0x1128, 0x20a3, 0x00ff, 0x20a3, 0xfffd, 0x0478, 0xd2bc,
-       0x0180, 0xa286, 0x0080, 0x1128, 0x20a3, 0x00ff, 0x20a3, 0xfffc,
-       0x0428, 0xa2e8, 0xae34, 0x2d6c, 0x6810, 0x20a2, 0x6814, 0x20a2,
-       0x00e8, 0x20a3, 0x0000, 0x6098, 0x20a2, 0x00c0, 0x2001, 0xad34,
-       0x2004, 0xd0ac, 0x1138, 0x7818, 0xa080, 0x0028, 0x2004, 0xa082,
-       0x007e, 0x0240, 0x00d6, 0x2069, 0xad1b, 0x2da6, 0x8d68, 0x2da6,
-       0x00de, 0x0020, 0x20a3, 0x0000, 0x6034, 0x20a2, 0x7834, 0x20a2,
-       0x7838, 0x20a2, 0x20a3, 0x0000, 0x20a3, 0x0000, 0x60c3, 0x000c,
-       0x080c, 0x7821, 0x001e, 0x00de, 0x0005, 0x7817, 0x0001, 0x7803,
-       0x0006, 0x001e, 0x00de, 0x0005, 0x00d6, 0x0026, 0x7928, 0x2168,
-       0x691c, 0xa186, 0x0006, 0x01c0, 0xa186, 0x0003, 0x0904, 0x7ed3,
-       0xa186, 0x0005, 0x0904, 0x7ebc, 0xa186, 0x0004, 0x05b8, 0xa186,
-       0x0008, 0x0904, 0x7ec4, 0x7807, 0x0037, 0x7813, 0x1700, 0x080c,
-       0x7f3b, 0x002e, 0x00de, 0x0005, 0x080c, 0x7ef7, 0x2009, 0x4000,
-       0x6800, 0x0002, 0x7e9d, 0x7ea8, 0x7e9f, 0x7ea8, 0x7ea4, 0x7e9d,
-       0x7e9d, 0x7ea8, 0x7ea8, 0x7ea8, 0x7ea8, 0x7e9d, 0x7e9d, 0x7e9d,
-       0x7e9d, 0x7e9d, 0x7ea8, 0x7e9d, 0x7ea8, 0x080c, 0x14f6, 0x6820,
-       0xd0e4, 0x0110, 0xd0cc, 0x0110, 0xa00e, 0x0010, 0x2009, 0x2000,
-       0x6828, 0x20a2, 0x682c, 0x20a2, 0x0804, 0x7eed, 0x080c, 0x7ef7,
-       0x20a3, 0x0000, 0x20a3, 0x0000, 0x2009, 0x4000, 0x6a00, 0xa286,
-       0x0002, 0x1108, 0xa00e, 0x0488, 0x04d1, 0x20a3, 0x0000, 0x20a3,
-       0x0000, 0x2009, 0x4000, 0x0448, 0x0491, 0x20a3, 0x0000, 0x20a3,
-       0x0000, 0x2009, 0x4000, 0xa286, 0x0005, 0x0118, 0xa286, 0x0002,
-       0x1108, 0xa00e, 0x00d0, 0x0419, 0x6810, 0x2068, 0x697c, 0x6810,
-       0xa112, 0x6980, 0x6814, 0xa103, 0x20a2, 0x22a2, 0x7928, 0xa180,
-       0x0000, 0x2004, 0xa08e, 0x0002, 0x0130, 0xa08e, 0x0004, 0x0118,
-       0x2009, 0x4000, 0x0010, 0x2009, 0x0000, 0x21a2, 0x20a3, 0x0000,
-       0x60c3, 0x0018, 0x080c, 0x7821, 0x002e, 0x00de, 0x0005, 0x0036,
-       0x0046, 0x0056, 0x0066, 0x20a1, 0x020b, 0x080c, 0x71aa, 0xa006,
-       0x20a3, 0x0200, 0x20a2, 0x7934, 0x21a2, 0x7938, 0x21a2, 0x7818,
-       0xa080, 0x0028, 0x2004, 0x2011, 0xad34, 0x2214, 0xd2ac, 0x1118,
-       0xa092, 0x007e, 0x0268, 0x00d6, 0x2069, 0xad1b, 0x2d2c, 0x8d68,
-       0x2d34, 0xa0e8, 0xae34, 0x2d6c, 0x6b10, 0x6c14, 0x00de, 0x0030,
-       0x2019, 0x0000, 0x6498, 0x2029, 0x0000, 0x6634, 0x7828, 0xa080,
-       0x0007, 0x2004, 0xa086, 0x0003, 0x1128, 0x25a2, 0x26a2, 0x23a2,
-       0x24a2, 0x0020, 0x23a2, 0x24a2, 0x25a2, 0x26a2, 0x006e, 0x005e,
-       0x004e, 0x003e, 0x0005, 0x20a1, 0x020b, 0x080c, 0x71aa, 0x20a3,
-       0x0100, 0x20a3, 0x0000, 0x20a3, 0x0009, 0x7810, 0x20a2, 0x60c3,
-       0x0008, 0x080c, 0x7821, 0x0005, 0x20a1, 0x020b, 0x080c, 0x7106,
-       0x20a3, 0x1400, 0x20a3, 0x0000, 0x7834, 0x20a2, 0x7838, 0x20a2,
-       0x7828, 0x20a2, 0x782c, 0x20a2, 0x7830, 0xa084, 0x00ff, 0x8007,
-       0x20a2, 0x20a3, 0x0000, 0x60c3, 0x0010, 0x080c, 0x7821, 0x0005,
-       0x20a1, 0x020b, 0x080c, 0x71a2, 0x20a3, 0x0100, 0x20a3, 0x0000,
-       0x7828, 0x20a2, 0x7810, 0x20a2, 0x60c3, 0x0008, 0x080c, 0x7821,
-       0x0005, 0x0146, 0x20a1, 0x020b, 0x0031, 0x60c3, 0x0000, 0x080c,
-       0x7821, 0x014e, 0x0005, 0x20e1, 0x9080, 0x20e1, 0x4000, 0x7818,
-       0xa080, 0x0028, 0x2004, 0x2011, 0xad34, 0x2214, 0xd2ac, 0x1110,
-       0xd0bc, 0x0188, 0x00d6, 0xa0e8, 0xae34, 0x2d6c, 0x6810, 0xa085,
-       0x0300, 0x20a2, 0x6814, 0x20a2, 0x2069, 0xad1b, 0x2da6, 0x8d68,
-       0x2da6, 0x00de, 0x0078, 0x00d6, 0xa0e8, 0xae34, 0x2d6c, 0x6810,
-       0xa085, 0x0300, 0x20a2, 0x6814, 0x20a2, 0x00de, 0x20a3, 0x0000,
-       0x6234, 0x22a2, 0x20a3, 0x0819, 0x20a3, 0x0000, 0x080c, 0x7810,
-       0x22a2, 0x20a3, 0x0000, 0x2fa2, 0x7a08, 0x22a2, 0x20a3, 0x0000,
-       0x20a3, 0x0000, 0x0005, 0x20a1, 0x020b, 0x0079, 0x7910, 0x21a2,
-       0x20a3, 0x0000, 0x60c3, 0x0000, 0x20e1, 0x9080, 0x60a7, 0x9575,
-       0x080c, 0x782b, 0x080c, 0x6578, 0x0005, 0x0156, 0x0136, 0x0036,
-       0x00d6, 0x00e6, 0x20e1, 0x9080, 0x20e1, 0x4000, 0x7854, 0x2068,
-       0xadf0, 0x000f, 0x7210, 0xa296, 0x00c0, 0xa294, 0xfffd, 0x7212,
-       0x7214, 0xa294, 0x0300, 0x7216, 0x7100, 0xa194, 0x00ff, 0x7308,
-       0xa384, 0x00ff, 0xa08d, 0xc200, 0x7102, 0xa384, 0xff00, 0xa215,
-       0x720a, 0x7004, 0x720c, 0x700e, 0x7206, 0x20a9, 0x000a, 0x2e98,
-       0x53a6, 0x60a3, 0x0035, 0x6a38, 0xa294, 0x7000, 0xa286, 0x3000,
-       0x0110, 0x60a3, 0x0037, 0x00ee, 0x00de, 0x003e, 0x013e, 0x015e,
-       0x0005, 0x2009, 0x0092, 0x0010, 0x2009, 0x0096, 0x60ab, 0x0036,
-       0x6116, 0x0005, 0x2061, 0xb400, 0x2a70, 0x7064, 0x7046, 0x704b,
-       0xb400, 0x0005, 0x00e6, 0x0126, 0x2071, 0xad00, 0x2091, 0x8000,
-       0x7544, 0xa582, 0x0010, 0x0608, 0x7048, 0x2060, 0x6000, 0xa086,
-       0x0000, 0x0148, 0xace0, 0x0018, 0x7058, 0xac02, 0x1208, 0x0cb0,
-       0x2061, 0xb400, 0x0c98, 0x6003, 0x0008, 0x8529, 0x7546, 0xaca8,
-       0x0018, 0x7058, 0xa502, 0x1230, 0x754a, 0xa085, 0x0001, 0x012e,
-       0x00ee, 0x0005, 0x704b, 0xb400, 0x0cc0, 0xa006, 0x0cc0, 0x00e6,
-       0x2071, 0xad00, 0x7544, 0xa582, 0x0010, 0x0600, 0x7048, 0x2060,
-       0x6000, 0xa086, 0x0000, 0x0148, 0xace0, 0x0018, 0x7058, 0xac02,
-       0x1208, 0x0cb0, 0x2061, 0xb400, 0x0c98, 0x6003, 0x0008, 0x8529,
-       0x7546, 0xaca8, 0x0018, 0x7058, 0xa502, 0x1228, 0x754a, 0xa085,
-       0x0001, 0x00ee, 0x0005, 0x704b, 0xb400, 0x0cc8, 0xa006, 0x0cc8,
-       0xac82, 0xb400, 0x0a0c, 0x14f6, 0x2001, 0xad16, 0x2004, 0xac02,
-       0x1a0c, 0x14f6, 0xa006, 0x6006, 0x600a, 0x600e, 0x6012, 0x6016,
-       0x601a, 0x601f, 0x0000, 0x6003, 0x0000, 0x6052, 0x6056, 0x6022,
-       0x6026, 0x602a, 0x602e, 0x6032, 0x6036, 0x603a, 0x603e, 0x2061,
-       0xad00, 0x6044, 0x8000, 0x6046, 0xa086, 0x0001, 0x0108, 0x0005,
-       0x0126, 0x2091, 0x8000, 0x080c, 0x6c50, 0x012e, 0x0cc0, 0x601c,
-       0xa084, 0x000f, 0x0002, 0x80b6, 0x80c5, 0x80e0, 0x80fb, 0x9a61,
-       0x9a7c, 0x9a97, 0x80b6, 0x80c5, 0x80b6, 0x8116, 0xa186, 0x0013,
-       0x1128, 0x080c, 0x6b73, 0x080c, 0x6c50, 0x0005, 0xa18e, 0x0047,
-       0x1118, 0xa016, 0x080c, 0x1824, 0x0005, 0x0066, 0x6000, 0xa0b2,
-       0x0010, 0x1a0c, 0x14f6, 0x0013, 0x006e, 0x0005, 0x80de, 0x8478,
-       0x862d, 0x80de, 0x86a2, 0x81cf, 0x80de, 0x80de, 0x840a, 0x8a91,
-       0x80de, 0x80de, 0x80de, 0x80de, 0x80de, 0x80de, 0x080c, 0x14f6,
-       0x0066, 0x6000, 0xa0b2, 0x0010, 0x1a0c, 0x14f6, 0x0013, 0x006e,
-       0x0005, 0x80f9, 0x909a, 0x80f9, 0x80f9, 0x80f9, 0x80f9, 0x80f9,
-       0x80f9, 0x9045, 0x9200, 0x80f9, 0x90c7, 0x913e, 0x90c7, 0x913e,
-       0x80f9, 0x080c, 0x14f6, 0x0066, 0x6000, 0xa0b2, 0x0010, 0x1a0c,
-       0x14f6, 0x0013, 0x006e, 0x0005, 0x8114, 0x8ad2, 0x8b98, 0x8cb8,
-       0x8e12, 0x8114, 0x8114, 0x8114, 0x8aac, 0x8ff5, 0x8ff8, 0x8114,
-       0x8114, 0x8114, 0x8114, 0x9022, 0x080c, 0x14f6, 0x0066, 0x6000,
-       0xa0b2, 0x0010, 0x1a0c, 0x14f6, 0x0013, 0x006e, 0x0005, 0x812f,
-       0x812f, 0x812f, 0x8152, 0x81a5, 0x812f, 0x812f, 0x812f, 0x8131,
-       0x812f, 0x812f, 0x812f, 0x812f, 0x812f, 0x812f, 0x812f, 0x080c,
-       0x14f6, 0xa186, 0x0003, 0x190c, 0x14f6, 0x00d6, 0x6003, 0x0003,
-       0x6106, 0x6010, 0x2068, 0x684f, 0x0040, 0x687c, 0x680a, 0x6880,
-       0x680e, 0x6813, 0x0000, 0x6817, 0x0000, 0x00de, 0x2c10, 0x080c,
-       0x1e6e, 0x080c, 0x680b, 0x0126, 0x2091, 0x8000, 0x080c, 0x6d0d,
-       0x012e, 0x0005, 0xa182, 0x0047, 0x0002, 0x815e, 0x815e, 0x8160,
-       0x817f, 0x815e, 0x815e, 0x815e, 0x815e, 0x8191, 0x080c, 0x14f6,
-       0x00d6, 0x0016, 0x080c, 0x6c05, 0x080c, 0x6d0d, 0x6003, 0x0004,
-       0x6110, 0x2168, 0x6854, 0x8003, 0x800b, 0x810b, 0xa108, 0x6116,
-       0x684f, 0x0020, 0x685c, 0x685a, 0x6874, 0x687e, 0x6878, 0x6882,
-       0x6897, 0x0000, 0x689b, 0x0000, 0x001e, 0x00de, 0x0005, 0x080c,
-       0x6c05, 0x00d6, 0x6110, 0x2168, 0x080c, 0x9596, 0x0120, 0x684b,
-       0x0006, 0x080c, 0x510c, 0x00de, 0x080c, 0x8078, 0x080c, 0x6d0d,
-       0x0005, 0x080c, 0x6c05, 0x080c, 0x2ad9, 0x00d6, 0x6110, 0x2168,
-       0x080c, 0x9596, 0x0120, 0x684b, 0x0029, 0x080c, 0x510c, 0x00de,
-       0x080c, 0x8078, 0x080c, 0x6d0d, 0x0005, 0xa182, 0x0047, 0x0002,
-       0x81b3, 0x81c2, 0x81b1, 0x81b1, 0x81b1, 0x81b1, 0x81b1, 0x81b1,
-       0x81b1, 0x080c, 0x14f6, 0x00d6, 0x6010, 0x2068, 0x684c, 0xc0f4,
-       0x684e, 0x00de, 0x20e1, 0x0005, 0x3d18, 0x3e20, 0x2c10, 0x080c,
-       0x1824, 0x0005, 0x00d6, 0x6110, 0x2168, 0x684b, 0x0000, 0x6853,
-       0x0000, 0x080c, 0x510c, 0x00de, 0x080c, 0x8078, 0x0005, 0xa1b6,
-       0x0015, 0x1118, 0x080c, 0x8078, 0x0030, 0xa1b6, 0x0016, 0x190c,
-       0x14f6, 0x080c, 0x8078, 0x0005, 0x20a9, 0x000e, 0x2e98, 0x6010,
-       0x20a0, 0x53a3, 0x20a9, 0x0006, 0x3310, 0x3420, 0x9398, 0x94a0,
-       0x3318, 0x3428, 0x222e, 0x2326, 0xa290, 0x0002, 0xa5a8, 0x0002,
-       0xa398, 0x0002, 0xa4a0, 0x0002, 0x1f04, 0x81ea, 0x00e6, 0x080c,
-       0x9596, 0x0130, 0x6010, 0x2070, 0x7007, 0x0000, 0x7037, 0x0103,
-       0x00ee, 0x080c, 0x8078, 0x0005, 0x00d6, 0x0036, 0x7330, 0xa386,
-       0x0200, 0x1130, 0x6018, 0x2068, 0x6813, 0x00ff, 0x6817, 0xfffd,
-       0x6010, 0xa005, 0x0130, 0x2068, 0x6807, 0x0000, 0x6837, 0x0103,
-       0x6b32, 0x080c, 0x8078, 0x003e, 0x00de, 0x0005, 0x0016, 0x20a9,
-       0x002a, 0xae80, 0x000c, 0x2098, 0x6010, 0xa080, 0x0002, 0x20a0,
-       0x53a3, 0x20a9, 0x002a, 0x6010, 0xa080, 0x0001, 0x2004, 0xa080,
-       0x0002, 0x20a0, 0x53a3, 0x00e6, 0x6010, 0x2004, 0x2070, 0x7037,
-       0x0103, 0x00ee, 0x080c, 0x8078, 0x001e, 0x0005, 0x0016, 0x2009,
-       0x0000, 0x7030, 0xa086, 0x0100, 0x0140, 0x7038, 0xa084, 0x00ff,
-       0x808e, 0x703c, 0xa084, 0x00ff, 0x8086, 0xa080, 0x0004, 0xa108,
-       0x21a8, 0xae80, 0x000c, 0x2098, 0x6010, 0xa080, 0x0002, 0x20a0,
-       0x080c, 0x48be, 0x00e6, 0x080c, 0x9596, 0x0140, 0x6010, 0x2070,
-       0x7007, 0x0000, 0x7034, 0x70b2, 0x7037, 0x0103, 0x00ee, 0x080c,
-       0x8078, 0x001e, 0x0005, 0x00e6, 0x00d6, 0x603f, 0x0000, 0x2c68,
-       0x0016, 0x2009, 0x0035, 0x080c, 0x9a34, 0x001e, 0x1168, 0x0026,
-       0x6228, 0x2268, 0x002e, 0x2071, 0xb28c, 0x6b1c, 0xa386, 0x0003,
-       0x0130, 0xa386, 0x0006, 0x0128, 0x080c, 0x8078, 0x0020, 0x0031,
-       0x0010, 0x080c, 0x8323, 0x00de, 0x00ee, 0x0005, 0x00f6, 0x6810,
-       0x2078, 0xa186, 0x0015, 0x0904, 0x830c, 0xa18e, 0x0016, 0x1904,
-       0x8321, 0x700c, 0xa084, 0xff00, 0xa086, 0x1700, 0x1904, 0x82eb,
-       0x8fff, 0x0904, 0x831f, 0x6808, 0xa086, 0xffff, 0x1904, 0x830e,
-       0x784c, 0xa084, 0x0060, 0xa086, 0x0020, 0x1150, 0x797c, 0x7810,
-       0xa106, 0x1904, 0x830e, 0x7980, 0x7814, 0xa106, 0x1904, 0x830e,
-       0x080c, 0x9742, 0x6858, 0x7852, 0x784c, 0xc0dc, 0xc0f4, 0xc0d4,
-       0x784e, 0x0026, 0xa00e, 0x6a14, 0x2001, 0x000a, 0x080c, 0x6665,
-       0x7854, 0xa20a, 0x0208, 0x8011, 0x7a56, 0x82ff, 0x002e, 0x1138,
-       0x00c6, 0x2d60, 0x080c, 0x9374, 0x00ce, 0x0804, 0x831f, 0x00c6,
-       0x00d6, 0x2f68, 0x6838, 0xd0fc, 0x1118, 0x080c, 0x4993, 0x0010,
-       0x080c, 0x4b7c, 0x00de, 0x00ce, 0x1548, 0x00c6, 0x2d60, 0x080c,
-       0x8078, 0x00ce, 0x04a0, 0x7008, 0xa086, 0x000b, 0x11a0, 0x6018,
-       0x200c, 0xc1bc, 0x2102, 0x00c6, 0x2d60, 0x7853, 0x0003, 0x6007,
-       0x0085, 0x6003, 0x000b, 0x601f, 0x0002, 0x080c, 0x67a8, 0x080c,
-       0x6c50, 0x00ce, 0x00e0, 0x700c, 0xa086, 0x2a00, 0x1138, 0x2001,
-       0xafa5, 0x2004, 0x683e, 0x0098, 0x0471, 0x0098, 0x8fff, 0x090c,
-       0x14f6, 0x00c6, 0x00d6, 0x2d60, 0x2f68, 0x684b, 0x0003, 0x080c,
-       0x926f, 0x080c, 0x9742, 0x080c, 0x974e, 0x00de, 0x00ce, 0x080c,
-       0x8078, 0x00fe, 0x0005, 0xa186, 0x0015, 0x1128, 0x2001, 0xafa5,
-       0x2004, 0x683e, 0x0068, 0xa18e, 0x0016, 0x1160, 0x00c6, 0x2d00,
-       0x2060, 0x080c, 0xabb4, 0x080c, 0x6618, 0x080c, 0x8078, 0x00ce,
-       0x080c, 0x8078, 0x0005, 0x0026, 0x0036, 0x0046, 0x7228, 0x7c80,
-       0x7b7c, 0xd2f4, 0x0130, 0x2001, 0xafa5, 0x2004, 0x683e, 0x0804,
-       0x839d, 0x00c6, 0x2d60, 0x080c, 0x928f, 0x00ce, 0x6804, 0xa086,
-       0x0050, 0x1168, 0x00c6, 0x2d00, 0x2060, 0x6003, 0x0001, 0x6007,
-       0x0050, 0x080c, 0x67a8, 0x080c, 0x6c50, 0x00ce, 0x04f0, 0x6800,
-       0xa086, 0x000f, 0x01c8, 0x8fff, 0x090c, 0x14f6, 0x6820, 0xd0dc,
-       0x1198, 0x6800, 0xa086, 0x0004, 0x1198, 0x784c, 0xd0ac, 0x0180,
-       0x784c, 0xc0dc, 0xc0f4, 0x784e, 0x7850, 0xc0f4, 0xc0fc, 0x7852,
-       0x2001, 0x0001, 0x682e, 0x00e0, 0x2001, 0x0007, 0x682e, 0x00c0,
-       0x784c, 0xd0b4, 0x1130, 0xd0ac, 0x0db8, 0x784c, 0xd0f4, 0x1da0,
-       0x0c38, 0xd2ec, 0x1d88, 0x7024, 0xa306, 0x1118, 0x7020, 0xa406,
-       0x0d58, 0x7020, 0x6836, 0x7024, 0x683a, 0x2001, 0x0005, 0x682e,
-       0x080c, 0x9894, 0x080c, 0x6c50, 0x0010, 0x080c, 0x8078, 0x004e,
-       0x003e, 0x002e, 0x0005, 0x00e6, 0x00d6, 0x0026, 0x6034, 0x2068,
-       0x6a1c, 0xa286, 0x0007, 0x0904, 0x83ee, 0xa286, 0x0002, 0x05f0,
-       0xa286, 0x0000, 0x05d8, 0x6808, 0x6338, 0xa306, 0x15b8, 0x2071,
-       0xb28c, 0xa186, 0x0015, 0x0560, 0xa18e, 0x0016, 0x1190, 0x6030,
-       0xa084, 0x00ff, 0xa086, 0x0001, 0x1160, 0x700c, 0xa086, 0x2a00,
-       0x1140, 0x6034, 0xa080, 0x0008, 0x200c, 0xc1dd, 0xc1f5, 0x2102,
-       0x00b8, 0x00c6, 0x6034, 0x2060, 0x6010, 0x2068, 0x080c, 0x9596,
-       0x090c, 0x14f6, 0x6853, 0x0003, 0x6007, 0x0085, 0x6003, 0x000b,
-       0x601f, 0x0002, 0x080c, 0x67a8, 0x080c, 0x6c50, 0x00ce, 0x0030,
-       0x6034, 0x2070, 0x2001, 0xafa5, 0x2004, 0x703e, 0x080c, 0x8078,
-       0x002e, 0x00de, 0x00ee, 0x0005, 0x00d6, 0x20a9, 0x000e, 0x2e98,
-       0x6010, 0x20a0, 0x53a3, 0xa1b6, 0x0015, 0x1148, 0x6018, 0x2068,
-       0x7038, 0x680a, 0x703c, 0x680e, 0x6800, 0xc08d, 0x6802, 0x00de,
-       0x0804, 0x81f6, 0x2100, 0xa1b2, 0x0080, 0x1a0c, 0x14f6, 0xa1b2,
-       0x0040, 0x1a04, 0x846e, 0x0002, 0x8462, 0x8456, 0x8462, 0x8462,
-       0x8462, 0x8462, 0x8454, 0x8454, 0x8454, 0x8454, 0x8454, 0x8454,
-       0x8454, 0x8454, 0x8454, 0x8454, 0x8454, 0x8454, 0x8454, 0x8454,
-       0x8454, 0x8454, 0x8454, 0x8454, 0x8454, 0x8454, 0x8454, 0x8454,
-       0x8454, 0x8454, 0x8454, 0x8462, 0x8454, 0x8462, 0x8462, 0x8454,
-       0x8454, 0x8454, 0x8454, 0x8454, 0x8462, 0x8454, 0x8454, 0x8454,
-       0x8454, 0x8454, 0x8454, 0x8454, 0x8454, 0x8454, 0x8462, 0x8462,
-       0x8454, 0x8454, 0x8454, 0x8454, 0x8454, 0x8454, 0x8454, 0x8454,
-       0x8454, 0x8462, 0x8454, 0x8454, 0x080c, 0x14f6, 0x6003, 0x0001,
-       0x6106, 0x080c, 0x67ee, 0x0126, 0x2091, 0x8000, 0x080c, 0x6c50,
-       0x012e, 0x0005, 0x6003, 0x0001, 0x6106, 0x080c, 0x67ee, 0x0126,
-       0x2091, 0x8000, 0x080c, 0x6c50, 0x012e, 0x0005, 0x2600, 0x0002,
-       0x8462, 0x8476, 0x8476, 0x8462, 0x8462, 0x8476, 0x080c, 0x14f6,
-       0x6004, 0xa0b2, 0x0080, 0x1a0c, 0x14f6, 0xa1b6, 0x0013, 0x0904,
-       0x8518, 0xa1b6, 0x0027, 0x1904, 0x84de, 0x080c, 0x6b73, 0x6004,
-       0x080c, 0x9778, 0x0188, 0x080c, 0x9789, 0x0904, 0x84d8, 0xa08e,
-       0x0021, 0x0904, 0x84db, 0xa08e, 0x0022, 0x0904, 0x84d8, 0xa08e,
-       0x003d, 0x0904, 0x84db, 0x04a8, 0x080c, 0x2aff, 0x2001, 0x0007,
-       0x080c, 0x4c30, 0x6018, 0xa080, 0x0028, 0x200c, 0x080c, 0x85f3,
-       0xa186, 0x007e, 0x1148, 0x2001, 0xad34, 0x2014, 0xc285, 0x080c,
-       0x574f, 0x1108, 0xc2ad, 0x2202, 0x0016, 0x0026, 0x0036, 0x2110,
-       0x2019, 0x0028, 0x080c, 0x68e7, 0x0076, 0x2039, 0x0000, 0x080c,
-       0x681d, 0x00c6, 0x6018, 0xa065, 0x0110, 0x080c, 0x4ecf, 0x00ce,
-       0x2c08, 0x080c, 0xa712, 0x007e, 0x003e, 0x002e, 0x001e, 0x080c,
-       0x4c9f, 0x080c, 0x994e, 0x080c, 0x8078, 0x080c, 0x6c50, 0x0005,
-       0x080c, 0x85f3, 0x0cb0, 0x080c, 0x8621, 0x0c98, 0xa186, 0x0014,
-       0x1db0, 0x080c, 0x6b73, 0x080c, 0x2ad9, 0x080c, 0x9778, 0x1188,
-       0x080c, 0x2aff, 0x6018, 0xa080, 0x0028, 0x200c, 0x080c, 0x85f3,
-       0xa186, 0x007e, 0x1128, 0x2001, 0xad34, 0x200c, 0xc185, 0x2102,
-       0x08c0, 0x080c, 0x9789, 0x1118, 0x080c, 0x85f3, 0x0890, 0x6004,
-       0xa08e, 0x0032, 0x1158, 0x00e6, 0x00f6, 0x2071, 0xad81, 0x2079,
-       0x0000, 0x080c, 0x2df1, 0x00fe, 0x00ee, 0x0818, 0x6004, 0xa08e,
-       0x0021, 0x0d50, 0xa08e, 0x0022, 0x090c, 0x85f3, 0x0804, 0x84d1,
-       0xa0b2, 0x0040, 0x1a04, 0x85db, 0x2008, 0x0002, 0x8560, 0x8561,
-       0x8564, 0x8567, 0x856a, 0x856d, 0x855e, 0x855e, 0x855e, 0x855e,
-       0x855e, 0x855e, 0x855e, 0x855e, 0x855e, 0x855e, 0x855e, 0x855e,
-       0x855e, 0x855e, 0x855e, 0x855e, 0x855e, 0x855e, 0x855e, 0x855e,
-       0x855e, 0x855e, 0x855e, 0x855e, 0x8570, 0x857f, 0x855e, 0x8581,
-       0x857f, 0x855e, 0x855e, 0x855e, 0x855e, 0x855e, 0x857f, 0x857f,
-       0x855e, 0x855e, 0x855e, 0x855e, 0x855e, 0x855e, 0x855e, 0x855e,
-       0x85bb, 0x857f, 0x855e, 0x857b, 0x855e, 0x855e, 0x855e, 0x857c,
-       0x855e, 0x855e, 0x855e, 0x857f, 0x85b2, 0x855e, 0x080c, 0x14f6,
-       0x00f0, 0x2001, 0x000b, 0x0460, 0x2001, 0x0003, 0x0448, 0x2001,
-       0x0005, 0x0430, 0x2001, 0x0001, 0x0418, 0x2001, 0x0009, 0x0400,
-       0x080c, 0x6b73, 0x6003, 0x0005, 0x2001, 0xafa5, 0x2004, 0x603e,
-       0x080c, 0x6c50, 0x00a0, 0x0018, 0x0010, 0x080c, 0x4c30, 0x0804,
-       0x85cc, 0x080c, 0x6b73, 0x2001, 0xafa3, 0x2004, 0x6016, 0x2001,
-       0xafa5, 0x2004, 0x603e, 0x6003, 0x0004, 0x080c, 0x6c50, 0x0005,
-       0x080c, 0x4c30, 0x080c, 0x6b73, 0x6003, 0x0002, 0x2001, 0xafa5,
-       0x2004, 0x603e, 0x0036, 0x2019, 0xad5c, 0x2304, 0xa084, 0xff00,
-       0x1120, 0x2001, 0xafa3, 0x201c, 0x0040, 0x8007, 0xa09a, 0x0004,
-       0x0ec0, 0x8003, 0x801b, 0x831b, 0xa318, 0x6316, 0x003e, 0x080c,
-       0x6c50, 0x08e8, 0x080c, 0x6b73, 0x080c, 0x994e, 0x080c, 0x8078,
-       0x080c, 0x6c50, 0x08a0, 0x00e6, 0x00f6, 0x2071, 0xad81, 0x2079,
-       0x0000, 0x080c, 0x2df1, 0x00fe, 0x00ee, 0x080c, 0x6b73, 0x080c,
-       0x8078, 0x080c, 0x6c50, 0x0818, 0x080c, 0x6b73, 0x2001, 0xafa5,
-       0x2004, 0x603e, 0x6003, 0x0002, 0x2001, 0xafa3, 0x2004, 0x6016,
-       0x080c, 0x6c50, 0x0005, 0x2600, 0x2008, 0x0002, 0x85e6, 0x85e4,
-       0x85e4, 0x85cc, 0x85cc, 0x85e4, 0x080c, 0x14f6, 0x080c, 0x6b73,
-       0x00d6, 0x6010, 0x2068, 0x080c, 0x15f0, 0x00de, 0x080c, 0x8078,
-       0x080c, 0x6c50, 0x0005, 0x00e6, 0x0026, 0x0016, 0x080c, 0x9596,
-       0x0508, 0x6010, 0x2070, 0x7034, 0xa086, 0x0139, 0x1148, 0x2001,
-       0x0030, 0x2009, 0x0000, 0x2011, 0x4005, 0x080c, 0x9a05, 0x0090,
-       0x7038, 0xd0fc, 0x0178, 0x7007, 0x0000, 0x0016, 0x6004, 0xa08e,
-       0x0021, 0x0160, 0xa08e, 0x003d, 0x0148, 0x001e, 0x7037, 0x0103,
-       0x7033, 0x0100, 0x001e, 0x002e, 0x00ee, 0x0005, 0x001e, 0x0009,
-       0x0cc8, 0x00e6, 0xacf0, 0x0004, 0x2e74, 0x7000, 0x2070, 0x7037,
-       0x0103, 0x7023, 0x8001, 0x00ee, 0x0005, 0x00d6, 0x6618, 0x2668,
-       0x6804, 0xa084, 0x00ff, 0x00de, 0xa0b2, 0x000c, 0x1a0c, 0x14f6,
-       0x6604, 0xa6b6, 0x0043, 0x1120, 0x080c, 0x99c1, 0x0804, 0x8692,
-       0x6604, 0xa6b6, 0x0033, 0x1120, 0x080c, 0x9971, 0x0804, 0x8692,
-       0x6604, 0xa6b6, 0x0028, 0x1120, 0x080c, 0x97b9, 0x0804, 0x8692,
-       0x6604, 0xa6b6, 0x0029, 0x1118, 0x080c, 0x97d0, 0x04d8, 0x6604,
-       0xa6b6, 0x001f, 0x1118, 0x080c, 0x81dc, 0x04a0, 0x6604, 0xa6b6,
-       0x0000, 0x1118, 0x080c, 0x83f4, 0x0468, 0x6604, 0xa6b6, 0x0022,
-       0x1118, 0x080c, 0x8204, 0x0430, 0x6604, 0xa6b6, 0x0035, 0x1118,
-       0x080c, 0x826b, 0x00f8, 0x6604, 0xa6b6, 0x0039, 0x1118, 0x080c,
-       0x83a3, 0x00c0, 0x6604, 0xa6b6, 0x003d, 0x1118, 0x080c, 0x821e,
-       0x0088, 0x6604, 0xa6b6, 0x0044, 0x1118, 0x080c, 0x823e, 0x0050,
-       0xa1b6, 0x0015, 0x1110, 0x0053, 0x0028, 0xa1b6, 0x0016, 0x1118,
-       0x0804, 0x883f, 0x0005, 0x080c, 0x80be, 0x0ce0, 0x86b9, 0x86bc,
-       0x86b9, 0x86fe, 0x86b9, 0x87cc, 0x884d, 0x86b9, 0x86b9, 0x881b,
-       0x86b9, 0x882f, 0xa1b6, 0x0048, 0x0140, 0x20e1, 0x0005, 0x3d18,
-       0x3e20, 0x2c10, 0x080c, 0x1824, 0x0005, 0x00e6, 0xacf0, 0x0004,
-       0x2e74, 0x7000, 0x2070, 0x7037, 0x0103, 0x00ee, 0x080c, 0x8078,
-       0x0005, 0xe000, 0xe000, 0x0005, 0x00e6, 0x2071, 0xad00, 0x7080,
-       0xa086, 0x0074, 0x1530, 0x080c, 0xa6e9, 0x11b0, 0x00d6, 0x6018,
-       0x2068, 0x7030, 0xd08c, 0x0128, 0x6800, 0xd0bc, 0x0110, 0xc0c5,
-       0x6802, 0x00d9, 0x00de, 0x2001, 0x0006, 0x080c, 0x4c30, 0x080c,
-       0x2aff, 0x080c, 0x8078, 0x0078, 0x2001, 0x000a, 0x080c, 0x4c30,
-       0x080c, 0x2aff, 0x6003, 0x0001, 0x6007, 0x0001, 0x080c, 0x67ee,
-       0x0010, 0x080c, 0x87bd, 0x00ee, 0x0005, 0x6800, 0xd084, 0x0168,
-       0x2001, 0x0000, 0x080c, 0x4c1e, 0x2069, 0xad51, 0x6804, 0xd0a4,
-       0x0120, 0x2001, 0x0006, 0x080c, 0x4c5d, 0x0005, 0x00d6, 0x2011,
-       0xad20, 0x2204, 0xa086, 0x0074, 0x1904, 0x87ba, 0x6018, 0x2068,
-       0x6aa0, 0xa286, 0x007e, 0x1120, 0x080c, 0x894d, 0x0804, 0x875e,
-       0x080c, 0x8943, 0x6018, 0x2068, 0xa080, 0x0028, 0x2014, 0xa286,
-       0x0080, 0x11c0, 0x6813, 0x00ff, 0x6817, 0xfffc, 0x6010, 0xa005,
-       0x0138, 0x2068, 0x6807, 0x0000, 0x6837, 0x0103, 0x6833, 0x0200,
-       0x2001, 0x0006, 0x080c, 0x4c30, 0x080c, 0x2aff, 0x080c, 0x8078,
-       0x0804, 0x87bb, 0x00e6, 0x2071, 0xad34, 0x2e04, 0xd09c, 0x0188,
-       0x2071, 0xb280, 0x7108, 0x720c, 0xa18c, 0x00ff, 0x1118, 0xa284,
-       0xff00, 0x0138, 0x6018, 0x2070, 0x70a0, 0xd0bc, 0x1110, 0x7112,
-       0x7216, 0x00ee, 0x6010, 0xa005, 0x0128, 0x2068, 0x6838, 0xd0f4,
-       0x0108, 0x0880, 0x2001, 0x0004, 0x080c, 0x4c30, 0x6003, 0x0001,
-       0x6007, 0x0003, 0x080c, 0x67ee, 0x0804, 0x87bb, 0x685c, 0xd0e4,
-       0x01d0, 0x080c, 0x9903, 0x080c, 0x574f, 0x0110, 0xd0dc, 0x1900,
-       0x2011, 0xad34, 0x2204, 0xc0ad, 0x2012, 0x2001, 0xaf8e, 0x2004,
-       0x00f6, 0x2079, 0x0100, 0x78e3, 0x0000, 0x080c, 0x26cb, 0x78e2,
-       0x00fe, 0x0804, 0x8728, 0x080c, 0x9937, 0x2011, 0xad34, 0x2204,
-       0xc0a5, 0x2012, 0x0006, 0x080c, 0xa801, 0x000e, 0x1904, 0x8728,
-       0xc0b5, 0x2012, 0x2001, 0x0000, 0x080c, 0x4c1e, 0x00c6, 0x2009,
-       0x00ef, 0x00f6, 0x2079, 0x0100, 0x79ea, 0x7932, 0x7936, 0x00fe,
-       0x080c, 0x26a0, 0x00f6, 0x2079, 0xad00, 0x7972, 0x2100, 0x2009,
-       0x0000, 0x080c, 0x2676, 0x794e, 0x00fe, 0x8108, 0x080c, 0x4c80,
-       0x2c00, 0x00ce, 0x1904, 0x8728, 0x601a, 0x2001, 0x0002, 0x080c,
-       0x4c30, 0x601f, 0x0001, 0x6003, 0x0001, 0x6007, 0x0002, 0x080c,
-       0x67ee, 0x0008, 0x0011, 0x00de, 0x0005, 0x2001, 0xad00, 0x2004,
-       0xa086, 0x0003, 0x0120, 0x2001, 0x0007, 0x080c, 0x4c30, 0x080c,
-       0x2aff, 0x080c, 0x8078, 0x0005, 0x00e6, 0x0026, 0x0016, 0x2071,
-       0xad00, 0x7080, 0xa086, 0x0014, 0x15f0, 0x7000, 0xa086, 0x0003,
-       0x1128, 0x6010, 0xa005, 0x1110, 0x080c, 0x3cce, 0x00d6, 0x6018,
-       0x2068, 0x080c, 0x4d72, 0x080c, 0x86ed, 0x00de, 0x080c, 0x89f7,
-       0x1550, 0x00d6, 0x6018, 0x2068, 0x6890, 0x00de, 0xa005, 0x0518,
-       0x2001, 0x0006, 0x080c, 0x4c30, 0x00e6, 0x6010, 0xa075, 0x01a8,
-       0x7034, 0xa084, 0x00ff, 0xa086, 0x0039, 0x1148, 0x2001, 0x0000,
-       0x2009, 0x0000, 0x2011, 0x4000, 0x080c, 0x9a05, 0x0030, 0x7007,
-       0x0000, 0x7037, 0x0103, 0x7033, 0x0200, 0x00ee, 0x080c, 0x2aff,
-       0x080c, 0x8078, 0x0020, 0x080c, 0x85f3, 0x080c, 0x87bd, 0x001e,
-       0x002e, 0x00ee, 0x0005, 0x2011, 0xad20, 0x2204, 0xa086, 0x0014,
-       0x1158, 0x2001, 0x0002, 0x080c, 0x4c30, 0x6003, 0x0001, 0x6007,
-       0x0001, 0x080c, 0x67ee, 0x0010, 0x080c, 0x87bd, 0x0005, 0x2011,
-       0xad20, 0x2204, 0xa086, 0x0004, 0x1138, 0x2001, 0x0007, 0x080c,
-       0x4c30, 0x080c, 0x8078, 0x0010, 0x080c, 0x87bd, 0x0005, 0x000b,
-       0x0005, 0x86b9, 0x8854, 0x86b9, 0x888a, 0x86b9, 0x88ff, 0x884d,
-       0x86b9, 0x86b9, 0x8912, 0x86b9, 0x8922, 0x6604, 0xa6b6, 0x001e,
-       0x1110, 0x080c, 0x8078, 0x0005, 0x00d6, 0x00c6, 0x080c, 0x8932,
-       0x1178, 0x2001, 0x0000, 0x080c, 0x4c1e, 0x2001, 0x0002, 0x080c,
-       0x4c30, 0x6003, 0x0001, 0x6007, 0x0002, 0x080c, 0x67ee, 0x00f8,
-       0x2009, 0xb28e, 0x2104, 0xa086, 0x0009, 0x1160, 0x6018, 0x2068,
-       0x6840, 0xa084, 0x00ff, 0xa005, 0x0180, 0x8001, 0x6842, 0x6017,
-       0x000a, 0x0068, 0x2009, 0xb28f, 0x2104, 0xa084, 0xff00, 0xa086,
-       0x1900, 0x1118, 0x080c, 0x8078, 0x0010, 0x080c, 0x87bd, 0x00ce,
-       0x00de, 0x0005, 0x080c, 0x8940, 0x00d6, 0x2069, 0xaf9d, 0x2d04,
-       0xa005, 0x0168, 0x6018, 0x2068, 0x68a0, 0xa086, 0x007e, 0x1138,
-       0x2069, 0xad1c, 0x2d04, 0x8000, 0x206a, 0x00de, 0x0010, 0x00de,
-       0x0078, 0x2001, 0x0000, 0x080c, 0x4c1e, 0x2001, 0x0002, 0x080c,
-       0x4c30, 0x6003, 0x0001, 0x6007, 0x0002, 0x080c, 0x67ee, 0x0428,
-       0x080c, 0x85f3, 0x2009, 0xb28e, 0x2134, 0xa6b4, 0x00ff, 0xa686,
-       0x0005, 0x01e0, 0xa686, 0x000b, 0x01b0, 0x2009, 0xb28f, 0x2104,
-       0xa084, 0xff00, 0x1118, 0xa686, 0x0009, 0x0180, 0xa086, 0x1900,
-       0x1150, 0xa686, 0x0009, 0x0150, 0x2001, 0x0004, 0x080c, 0x4c30,
-       0x080c, 0x8078, 0x0010, 0x080c, 0x87bd, 0x0005, 0x00d6, 0x6010,
-       0x2068, 0x080c, 0x9596, 0x0128, 0x6838, 0xd0fc, 0x0110, 0x00de,
-       0x0c90, 0x6018, 0x2068, 0x6840, 0xa084, 0x00ff, 0xa005, 0x0140,
-       0x8001, 0x6842, 0x6017, 0x000a, 0x6007, 0x0016, 0x00de, 0x0c28,
-       0x68a0, 0xa086, 0x007e, 0x1138, 0x00e6, 0x2071, 0xad00, 0x080c,
-       0x48f5, 0x00ee, 0x0010, 0x080c, 0x2ad9, 0x00de, 0x08a0, 0x080c,
-       0x8940, 0x1158, 0x2001, 0x0004, 0x080c, 0x4c30, 0x6003, 0x0001,
-       0x6007, 0x0003, 0x080c, 0x67ee, 0x0020, 0x080c, 0x85f3, 0x080c,
-       0x87bd, 0x0005, 0x0469, 0x1158, 0x2001, 0x0008, 0x080c, 0x4c30,
-       0x6003, 0x0001, 0x6007, 0x0005, 0x080c, 0x67ee, 0x0010, 0x080c,
-       0x87bd, 0x0005, 0x00e9, 0x1158, 0x2001, 0x000a, 0x080c, 0x4c30,
-       0x6003, 0x0001, 0x6007, 0x0001, 0x080c, 0x67ee, 0x0010, 0x080c,
-       0x87bd, 0x0005, 0x2009, 0xb28e, 0x2104, 0xa086, 0x0003, 0x1138,
-       0x2009, 0xb28f, 0x2104, 0xa084, 0xff00, 0xa086, 0x2a00, 0x0005,
-       0xa085, 0x0001, 0x0005, 0x00c6, 0x0016, 0xac88, 0x0006, 0x2164,
-       0x080c, 0x4ceb, 0x001e, 0x00ce, 0x0005, 0x00f6, 0x00e6, 0x00d6,
-       0x0036, 0x0016, 0x6018, 0x2068, 0x2071, 0xad34, 0x2e04, 0xa085,
-       0x0003, 0x2072, 0x080c, 0x89cc, 0x0538, 0x2001, 0xad52, 0x2004,
-       0xd0a4, 0x0158, 0xa006, 0x2020, 0x2009, 0x002a, 0x080c, 0xa96c,
-       0x2001, 0xad0c, 0x200c, 0xc195, 0x2102, 0x2019, 0x002a, 0x2009,
-       0x0001, 0x080c, 0x2aac, 0x2071, 0xad00, 0x080c, 0x28fa, 0x00c6,
-       0x0156, 0x20a9, 0x0081, 0x2009, 0x007f, 0x080c, 0x2bc9, 0x8108,
-       0x1f04, 0x897d, 0x015e, 0x00ce, 0x080c, 0x8943, 0x6813, 0x00ff,
-       0x6817, 0xfffe, 0x2071, 0xb280, 0x2079, 0x0100, 0x2e04, 0xa084,
-       0x00ff, 0x2069, 0xad1b, 0x206a, 0x78e6, 0x0006, 0x8e70, 0x2e04,
-       0x2069, 0xad1c, 0x206a, 0x78ea, 0x7832, 0x7836, 0x2010, 0xa084,
-       0xff00, 0x001e, 0xa105, 0x2009, 0xad27, 0x200a, 0x2200, 0xa084,
-       0x00ff, 0x2008, 0x080c, 0x26a0, 0x080c, 0x574f, 0x0170, 0x2069,
-       0xb28e, 0x2071, 0xaf9f, 0x6810, 0x2072, 0x6814, 0x7006, 0x6818,
-       0x700a, 0x681c, 0x700e, 0x080c, 0x9903, 0x0040, 0x2001, 0x0006,
-       0x080c, 0x4c30, 0x080c, 0x2aff, 0x080c, 0x8078, 0x001e, 0x003e,
-       0x00de, 0x00ee, 0x00fe, 0x0005, 0x0026, 0x0036, 0x00e6, 0x0156,
-       0x2019, 0xad27, 0x231c, 0x83ff, 0x01e8, 0x2071, 0xb280, 0x2e14,
-       0xa294, 0x00ff, 0x7004, 0xa084, 0xff00, 0xa205, 0xa306, 0x1190,
-       0x2011, 0xb296, 0xad98, 0x000a, 0x20a9, 0x0004, 0x080c, 0x8a7c,
-       0x1148, 0x2011, 0xb29a, 0xad98, 0x0006, 0x20a9, 0x0004, 0x080c,
-       0x8a7c, 0x1100, 0x015e, 0x00ee, 0x003e, 0x002e, 0x0005, 0x00e6,
-       0x2071, 0xb28c, 0x7004, 0xa086, 0x0014, 0x11a8, 0x7008, 0xa086,
-       0x0800, 0x1188, 0x700c, 0xd0ec, 0x0160, 0xa084, 0x0f00, 0xa086,
-       0x0100, 0x1138, 0x7024, 0xd0a4, 0x1110, 0xd0ac, 0x0110, 0xa006,
-       0x0010, 0xa085, 0x0001, 0x00ee, 0x0005, 0x00e6, 0x00d6, 0x00c6,
-       0x0076, 0x0056, 0x0046, 0x0026, 0x0006, 0x0126, 0x2091, 0x8000,
-       0x2029, 0xafd0, 0x252c, 0x2021, 0xafd6, 0x2424, 0x2061, 0xb400,
-       0x2071, 0xad00, 0x7244, 0x7064, 0xa202, 0x16f0, 0x080c, 0xa990,
-       0x05a0, 0x671c, 0xa786, 0x0001, 0x0580, 0xa786, 0x0007, 0x0568,
-       0x2500, 0xac06, 0x0550, 0x2400, 0xac06, 0x0538, 0x00c6, 0x6000,
-       0xa086, 0x0004, 0x1110, 0x080c, 0x190b, 0xa786, 0x0008, 0x1148,
-       0x080c, 0x9789, 0x1130, 0x00ce, 0x080c, 0x85f3, 0x080c, 0x974e,
-       0x00a0, 0x6010, 0x2068, 0x080c, 0x9596, 0x0160, 0xa786, 0x0003,
-       0x11e8, 0x6837, 0x0103, 0x6b4a, 0x6847, 0x0000, 0x080c, 0x510c,
-       0x080c, 0x9742, 0x080c, 0x974e, 0x00ce, 0xace0, 0x0018, 0x7058,
-       0xac02, 0x1210, 0x0804, 0x8a2a, 0x012e, 0x000e, 0x002e, 0x004e,
-       0x005e, 0x007e, 0x00ce, 0x00de, 0x00ee, 0x0005, 0xa786, 0x0006,
-       0x1d00, 0x080c, 0xa91f, 0x0c30, 0x220c, 0x2304, 0xa106, 0x1130,
-       0x8210, 0x8318, 0x1f04, 0x8a7c, 0xa006, 0x0005, 0x2304, 0xa102,
-       0x0218, 0x2001, 0x0001, 0x0010, 0x2001, 0x0000, 0xa18d, 0x0001,
-       0x0005, 0x6004, 0xa08a, 0x0080, 0x1a0c, 0x14f6, 0x080c, 0x9778,
-       0x0120, 0x080c, 0x9789, 0x0168, 0x0028, 0x080c, 0x2aff, 0x080c,
-       0x9789, 0x0138, 0x080c, 0x6b73, 0x080c, 0x8078, 0x080c, 0x6c50,
-       0x0005, 0x080c, 0x85f3, 0x0cb0, 0xa182, 0x0040, 0x0002, 0x8ac2,
-       0x8ac2, 0x8ac2, 0x8ac2, 0x8ac2, 0x8ac2, 0x8ac2, 0x8ac2, 0x8ac2,
-       0x8ac2, 0x8ac2, 0x8ac4, 0x8ac4, 0x8ac4, 0x8ac4, 0x8ac2, 0x8ac2,
-       0x8ac2, 0x8ac4, 0x080c, 0x14f6, 0x600b, 0xffff, 0x6003, 0x0001,
-       0x6106, 0x080c, 0x67a8, 0x0126, 0x2091, 0x8000, 0x080c, 0x6c50,
-       0x012e, 0x0005, 0xa186, 0x0013, 0x1128, 0x6004, 0xa082, 0x0040,
-       0x0804, 0x8b5e, 0xa186, 0x0027, 0x11e8, 0x080c, 0x6b73, 0x080c,
-       0x2ad9, 0x00d6, 0x6110, 0x2168, 0x080c, 0x9596, 0x0168, 0x6837,
-       0x0103, 0x684b, 0x0029, 0x6847, 0x0000, 0x694c, 0xc1c5, 0x694e,
-       0x080c, 0x510c, 0x080c, 0x9742, 0x00de, 0x080c, 0x8078, 0x080c,
-       0x6c50, 0x0005, 0xa186, 0x0014, 0x1120, 0x6004, 0xa082, 0x0040,
-       0x0428, 0xa186, 0x0046, 0x0138, 0xa186, 0x0045, 0x0120, 0xa186,
-       0x0047, 0x190c, 0x14f6, 0x2001, 0x0109, 0x2004, 0xd084, 0x0198,
-       0x0126, 0x2091, 0x2800, 0x0006, 0x0016, 0x0026, 0x080c, 0x6699,
-       0x002e, 0x001e, 0x000e, 0x012e, 0xe000, 0x6000, 0xa086, 0x0002,
-       0x1110, 0x0804, 0x8b98, 0x080c, 0x80be, 0x0005, 0x0002, 0x8b3c,
-       0x8b3a, 0x8b3a, 0x8b3a, 0x8b3a, 0x8b3a, 0x8b3a, 0x8b3a, 0x8b3a,
-       0x8b3a, 0x8b3a, 0x8b57, 0x8b57, 0x8b57, 0x8b57, 0x8b3a, 0x8b57,
-       0x8b3a, 0x8b57, 0x080c, 0x14f6, 0x080c, 0x6b73, 0x00d6, 0x6110,
-       0x2168, 0x080c, 0x9596, 0x0168, 0x6837, 0x0103, 0x684b, 0x0006,
-       0x6847, 0x0000, 0x6850, 0xc0ec, 0x6852, 0x080c, 0x510c, 0x080c,
-       0x9742, 0x00de, 0x080c, 0x8078, 0x080c, 0x6c50, 0x0005, 0x080c,
-       0x6b73, 0x080c, 0x8078, 0x080c, 0x6c50, 0x0005, 0x0002, 0x8b74,
-       0x8b72, 0x8b72, 0x8b72, 0x8b72, 0x8b72, 0x8b72, 0x8b72, 0x8b72,
-       0x8b72, 0x8b72, 0x8b86, 0x8b86, 0x8b86, 0x8b86, 0x8b72, 0x8b91,
-       0x8b72, 0x8b86, 0x080c, 0x14f6, 0x080c, 0x6b73, 0x2001, 0xafa5,
-       0x2004, 0x603e, 0x6003, 0x0002, 0x080c, 0x6c50, 0x6010, 0xa088,
-       0x0013, 0x2104, 0xa085, 0x0400, 0x200a, 0x0005, 0x080c, 0x6b73,
-       0x2001, 0xafa5, 0x2004, 0x603e, 0x6003, 0x000f, 0x080c, 0x6c50,
-       0x0005, 0x080c, 0x6b73, 0x080c, 0x8078, 0x080c, 0x6c50, 0x0005,
-       0xa182, 0x0040, 0x0002, 0x8bae, 0x8bae, 0x8bae, 0x8bae, 0x8bae,
-       0x8bb0, 0x8c88, 0x8ca9, 0x8bae, 0x8bae, 0x8bae, 0x8bae, 0x8bae,
-       0x8bae, 0x8bae, 0x8bae, 0x8bae, 0x8bae, 0x8bae, 0x080c, 0x14f6,
-       0x00e6, 0x00d6, 0x603f, 0x0000, 0x2071, 0xb280, 0x7124, 0x610a,
-       0x2071, 0xb28c, 0x6110, 0x2168, 0x7614, 0xa6b4, 0x0fff, 0x86ff,
-       0x0904, 0x8c54, 0xa68c, 0x0c00, 0x01e8, 0x00f6, 0x2c78, 0x080c,
-       0x5029, 0x00fe, 0x0198, 0x684c, 0xd0ac, 0x0180, 0x6020, 0xd0dc,
-       0x1168, 0x6850, 0xd0bc, 0x1150, 0x7318, 0x6814, 0xa306, 0x1904,
-       0x8c66, 0x731c, 0x6810, 0xa306, 0x1904, 0x8c66, 0x7318, 0x6b62,
-       0x731c, 0x6b5e, 0xa68c, 0x00ff, 0xa186, 0x0002, 0x0518, 0xa186,
-       0x0028, 0x1128, 0x080c, 0x9767, 0x684b, 0x001c, 0x00e8, 0xd6dc,
-       0x01a0, 0x684b, 0x0015, 0x684c, 0xd0ac, 0x0170, 0x6914, 0x6a10,
-       0x2100, 0xa205, 0x0148, 0x7018, 0xa106, 0x1118, 0x701c, 0xa206,
-       0x0118, 0x6962, 0x6a5e, 0xc6dc, 0x0038, 0xd6d4, 0x0118, 0x684b,
-       0x0007, 0x0010, 0x684b, 0x0000, 0x6837, 0x0103, 0x6e46, 0xa01e,
-       0xd6c4, 0x01f0, 0xa686, 0x0100, 0x1140, 0x2001, 0xb299, 0x2004,
-       0xa005, 0x1118, 0xc6c4, 0x0804, 0x8bbf, 0x7328, 0x732c, 0x6b56,
-       0x83ff, 0x0170, 0xa38a, 0x0009, 0x0210, 0x2019, 0x0008, 0x0036,
-       0x2308, 0x2019, 0xb298, 0xad90, 0x0019, 0x080c, 0x927f, 0x003e,
-       0xd6cc, 0x0904, 0x8c79, 0x7124, 0x695a, 0x81ff, 0x0904, 0x8c79,
-       0xa192, 0x0021, 0x1250, 0x2071, 0xb298, 0x831c, 0x2300, 0xae18,
-       0xad90, 0x001d, 0x080c, 0x927f, 0x04a0, 0x6838, 0xd0fc, 0x0120,
-       0x2009, 0x0020, 0x695a, 0x0c78, 0x00f6, 0x2d78, 0x080c, 0x9224,
-       0x00fe, 0x080c, 0x926f, 0x0438, 0x00f6, 0x2c78, 0x080c, 0x5029,
-       0x00fe, 0x0188, 0x684c, 0xd0ac, 0x0170, 0x6020, 0xd0dc, 0x1158,
-       0x6850, 0xd0bc, 0x1140, 0x684c, 0xd0f4, 0x1128, 0x080c, 0x9866,
-       0x00de, 0x00ee, 0x00e0, 0x684b, 0x0000, 0x6837, 0x0103, 0x6e46,
-       0x684c, 0xd0ac, 0x0130, 0x6810, 0x6914, 0xa115, 0x0110, 0x080c,
-       0x8e04, 0x080c, 0x510c, 0x6218, 0x2268, 0x6a3c, 0x8211, 0x6a3e,
-       0x080c, 0x9834, 0x00de, 0x00ee, 0x1110, 0x080c, 0x8078, 0x0005,
-       0x00f6, 0x6003, 0x0003, 0x2079, 0xb28c, 0x7c04, 0x7b00, 0x7e0c,
-       0x7d08, 0x6010, 0x2078, 0x784c, 0xd0ac, 0x0120, 0x6003, 0x0002,
-       0x00fe, 0x0005, 0x7c12, 0x7b16, 0x7e0a, 0x7d0e, 0x00fe, 0x603f,
-       0x0000, 0x2c10, 0x080c, 0x1e6e, 0x080c, 0x680b, 0x080c, 0x6d0d,
-       0x0005, 0x2001, 0xafa5, 0x2004, 0x603e, 0x6003, 0x0004, 0x6110,
-       0x20e1, 0x0005, 0x3d18, 0x3e20, 0x2c10, 0x080c, 0x1824, 0x0005,
-       0xa182, 0x0040, 0x0002, 0x8cce, 0x8cce, 0x8cce, 0x8cce, 0x8cce,
-       0x8cd0, 0x8d61, 0x8cce, 0x8cce, 0x8d77, 0x8ddb, 0x8cce, 0x8cce,
-       0x8cce, 0x8cce, 0x8dea, 0x8cce, 0x8cce, 0x8cce, 0x080c, 0x14f6,
-       0x0076, 0x00f6, 0x00e6, 0x00d6, 0x2071, 0xb28c, 0x6110, 0x2178,
-       0x7614, 0xa6b4, 0x0fff, 0x7e46, 0x7f4c, 0xc7e5, 0x7f4e, 0x6218,
-       0x2268, 0x6a3c, 0x8211, 0x6a3e, 0x86ff, 0x0904, 0x8d5c, 0xa694,
-       0xff00, 0xa284, 0x0c00, 0x0120, 0x7018, 0x7862, 0x701c, 0x785e,
-       0xa284, 0x0300, 0x0904, 0x8d5c, 0x080c, 0x15d9, 0x090c, 0x14f6,
-       0x2d00, 0x784a, 0x7f4c, 0xc7cd, 0x7f4e, 0x6837, 0x0103, 0x7838,
-       0x683a, 0x783c, 0x683e, 0x7840, 0x6842, 0x6e46, 0xa68c, 0x0c00,
-       0x0120, 0x7318, 0x6b62, 0x731c, 0x6b5e, 0xa68c, 0x00ff, 0xa186,
-       0x0002, 0x0180, 0xa186, 0x0028, 0x1118, 0x684b, 0x001c, 0x0060,
-       0xd6dc, 0x0118, 0x684b, 0x0015, 0x0038, 0xd6d4, 0x0118, 0x684b,
-       0x0007, 0x0010, 0x684b, 0x0000, 0x6f4e, 0x7850, 0x6852, 0x7854,
-       0x6856, 0xa01e, 0xd6c4, 0x0198, 0x7328, 0x732c, 0x6b56, 0x83ff,
-       0x0170, 0xa38a, 0x0009, 0x0210, 0x2019, 0x0008, 0x0036, 0x2308,
-       0x2019, 0xb298, 0xad90, 0x0019, 0x080c, 0x927f, 0x003e, 0xd6cc,
-       0x01d8, 0x7124, 0x695a, 0x81ff, 0x01b8, 0xa192, 0x0021, 0x1250,
-       0x2071, 0xb298, 0x831c, 0x2300, 0xae18, 0xad90, 0x001d, 0x080c,
-       0x927f, 0x0050, 0x7838, 0xd0fc, 0x0120, 0x2009, 0x0020, 0x695a,
-       0x0c78, 0x2d78, 0x080c, 0x9224, 0x00de, 0x00ee, 0x00fe, 0x007e,
-       0x0005, 0x00f6, 0x6003, 0x0003, 0x2079, 0xb28c, 0x7c04, 0x7b00,
-       0x7e0c, 0x7d08, 0x6010, 0x2078, 0x7c12, 0x7b16, 0x7e0a, 0x7d0e,
-       0x00fe, 0x2c10, 0x080c, 0x1e6e, 0x080c, 0x781a, 0x0005, 0x00d6,
-       0x00f6, 0x2c78, 0x080c, 0x5029, 0x00fe, 0x0120, 0x2001, 0xafa5,
-       0x2004, 0x603e, 0x6003, 0x0002, 0x080c, 0x6c05, 0x080c, 0x6d0d,
-       0x6110, 0x2168, 0x694c, 0xd1e4, 0x0904, 0x8dd9, 0xd1cc, 0x0540,
-       0x6948, 0x6838, 0xd0fc, 0x01e8, 0x0016, 0x684c, 0x0006, 0x6850,
-       0x0006, 0xad90, 0x000d, 0xa198, 0x000d, 0x2009, 0x0020, 0x0156,
-       0x21a8, 0x2304, 0x2012, 0x8318, 0x8210, 0x1f04, 0x8da1, 0x015e,
-       0x000e, 0x6852, 0x000e, 0x684e, 0x001e, 0x2168, 0x080c, 0x1600,
-       0x0418, 0x0016, 0x080c, 0x1600, 0x00de, 0x080c, 0x926f, 0x00e0,
-       0x6837, 0x0103, 0x6944, 0xa184, 0x00ff, 0xa0b6, 0x0002, 0x0180,
-       0xa086, 0x0028, 0x1118, 0x684b, 0x001c, 0x0060, 0xd1dc, 0x0118,
-       0x684b, 0x0015, 0x0038, 0xd1d4, 0x0118, 0x684b, 0x0007, 0x0010,
-       0x684b, 0x0000, 0x080c, 0x510c, 0x080c, 0x9834, 0x1110, 0x080c,
-       0x8078, 0x00de, 0x0005, 0x2019, 0x0001, 0x080c, 0x7a64, 0x6003,
-       0x0002, 0x2001, 0xafa5, 0x2004, 0x603e, 0x080c, 0x6c05, 0x080c,
-       0x6d0d, 0x0005, 0x080c, 0x6c05, 0x080c, 0x2ad9, 0x00d6, 0x6110,
-       0x2168, 0x080c, 0x9596, 0x0150, 0x6837, 0x0103, 0x684b, 0x0029,
-       0x6847, 0x0000, 0x080c, 0x510c, 0x080c, 0x9742, 0x00de, 0x080c,
-       0x8078, 0x080c, 0x6d0d, 0x0005, 0x684b, 0x0015, 0xd1fc, 0x0138,
-       0x684b, 0x0007, 0x8002, 0x8000, 0x810a, 0xa189, 0x0000, 0x6962,
-       0x685e, 0x0005, 0xa182, 0x0040, 0x0002, 0x8e28, 0x8e28, 0x8e28,
-       0x8e28, 0x8e28, 0x8e2a, 0x8e28, 0x8ee3, 0x8eef, 0x8e28, 0x8e28,
-       0x8e28, 0x8e28, 0x8e28, 0x8e28, 0x8e28, 0x8e28, 0x8e28, 0x8e28,
-       0x080c, 0x14f6, 0x0076, 0x00f6, 0x00e6, 0x00d6, 0x2071, 0xb28c,
-       0x6110, 0x2178, 0x7614, 0xa6b4, 0x0fff, 0x00f6, 0x2c78, 0x080c,
-       0x5029, 0x00fe, 0x0150, 0xa684, 0x00ff, 0x1138, 0x6020, 0xd0f4,
-       0x0120, 0x080c, 0x9866, 0x0804, 0x8ede, 0x7e46, 0x7f4c, 0xc7e5,
-       0x7f4e, 0x6218, 0x2268, 0x6a3c, 0x8211, 0x6a3e, 0x86ff, 0x0904,
-       0x8ed4, 0xa694, 0xff00, 0xa284, 0x0c00, 0x0120, 0x7018, 0x7862,
-       0x701c, 0x785e, 0xa284, 0x0300, 0x0904, 0x8ed2, 0xa686, 0x0100,
-       0x1140, 0x2001, 0xb299, 0x2004, 0xa005, 0x1118, 0xc6c4, 0x7e46,
-       0x0c28, 0x080c, 0x15d9, 0x090c, 0x14f6, 0x2d00, 0x784a, 0x7f4c,
-       0xa7bd, 0x0200, 0x7f4e, 0x6837, 0x0103, 0x7838, 0x683a, 0x783c,
-       0x683e, 0x7840, 0x6842, 0x6e46, 0xa68c, 0x0c00, 0x0120, 0x7318,
-       0x6b62, 0x731c, 0x6b5e, 0xa68c, 0x00ff, 0xa186, 0x0002, 0x0180,
-       0xa186, 0x0028, 0x1118, 0x684b, 0x001c, 0x0060, 0xd6dc, 0x0118,
-       0x684b, 0x0015, 0x0038, 0xd6d4, 0x0118, 0x684b, 0x0007, 0x0010,
-       0x684b, 0x0000, 0x6f4e, 0x7850, 0x6852, 0x7854, 0x6856, 0xa01e,
-       0xd6c4, 0x0198, 0x7328, 0x732c, 0x6b56, 0x83ff, 0x0170, 0xa38a,
-       0x0009, 0x0210, 0x2019, 0x0008, 0x0036, 0x2308, 0x2019, 0xb298,
-       0xad90, 0x0019, 0x080c, 0x927f, 0x003e, 0xd6cc, 0x01d8, 0x7124,
-       0x695a, 0x81ff, 0x01b8, 0xa192, 0x0021, 0x1250, 0x2071, 0xb298,
-       0x831c, 0x2300, 0xae18, 0xad90, 0x001d, 0x080c, 0x927f, 0x0050,
-       0x7838, 0xd0fc, 0x0120, 0x2009, 0x0020, 0x695a, 0x0c78, 0x2d78,
-       0x080c, 0x9224, 0xd6dc, 0x1110, 0xa006, 0x0030, 0x2001, 0x0001,
-       0x2071, 0xb28c, 0x7218, 0x731c, 0x080c, 0x186f, 0x00de, 0x00ee,
-       0x00fe, 0x007e, 0x0005, 0x2001, 0xafa5, 0x2004, 0x603e, 0x20e1,
-       0x0005, 0x3d18, 0x3e20, 0x2c10, 0x080c, 0x1824, 0x0005, 0x2001,
-       0xafa5, 0x2004, 0x603e, 0x00d6, 0x6003, 0x0002, 0x6110, 0x2168,
-       0x694c, 0xd1e4, 0x0904, 0x8ff3, 0x603f, 0x0000, 0x00f6, 0x2c78,
-       0x080c, 0x5029, 0x00fe, 0x0548, 0x6814, 0x6910, 0xa115, 0x0528,
-       0x6a60, 0xa206, 0x1118, 0x685c, 0xa106, 0x01f8, 0x684c, 0xc0e4,
-       0x684e, 0x6847, 0x0000, 0x6863, 0x0000, 0x685f, 0x0000, 0x697c,
-       0x6810, 0xa102, 0x603a, 0x6980, 0x6814, 0xa103, 0x6036, 0x6020,
-       0xc0f5, 0x6022, 0x00d6, 0x6018, 0x2068, 0x683c, 0x8000, 0x683e,
-       0x00de, 0x080c, 0x9866, 0x0804, 0x8ff3, 0x694c, 0xd1cc, 0x0904,
-       0x8fc3, 0x6948, 0x6838, 0xd0fc, 0x0904, 0x8f88, 0x0016, 0x684c,
-       0x0006, 0x6850, 0x0006, 0x00f6, 0x2178, 0x7944, 0xa184, 0x00ff,
-       0xa0b6, 0x0002, 0x01e0, 0xa086, 0x0028, 0x1128, 0x684b, 0x001c,
-       0x784b, 0x001c, 0x00e8, 0xd1dc, 0x0158, 0x684b, 0x0015, 0x784b,
-       0x0015, 0x080c, 0x99ee, 0x0118, 0x7944, 0xc1dc, 0x7946, 0x0080,
-       0xd1d4, 0x0128, 0x684b, 0x0007, 0x784b, 0x0007, 0x0048, 0x684c,
-       0xd0ac, 0x0130, 0x6810, 0x6914, 0xa115, 0x0110, 0x080c, 0x8e04,
-       0x6848, 0x784a, 0x6860, 0x7862, 0x685c, 0x785e, 0xad90, 0x000d,
-       0xaf98, 0x000d, 0x2009, 0x0020, 0x0156, 0x21a8, 0x2304, 0x2012,
-       0x8318, 0x8210, 0x1f04, 0x8f76, 0x015e, 0x00fe, 0x000e, 0x6852,
-       0x000e, 0x684e, 0x001e, 0x2168, 0x080c, 0x1600, 0x0804, 0x8fee,
-       0x0016, 0x00f6, 0x2178, 0x7944, 0xa184, 0x00ff, 0xa0b6, 0x0002,
-       0x01e0, 0xa086, 0x0028, 0x1128, 0x684b, 0x001c, 0x784b, 0x001c,
-       0x00e8, 0xd1dc, 0x0158, 0x684b, 0x0015, 0x784b, 0x0015, 0x080c,
-       0x99ee, 0x0118, 0x7944, 0xc1dc, 0x7946, 0x0080, 0xd1d4, 0x0128,
-       0x684b, 0x0007, 0x784b, 0x0007, 0x0048, 0x684c, 0xd0ac, 0x0130,
-       0x6810, 0x6914, 0xa115, 0x0110, 0x080c, 0x8e04, 0x6860, 0x7862,
-       0x685c, 0x785e, 0x684c, 0x784e, 0x00fe, 0x080c, 0x1600, 0x00de,
-       0x080c, 0x926f, 0x0458, 0x6837, 0x0103, 0x6944, 0xa184, 0x00ff,
-       0xa0b6, 0x0002, 0x01b0, 0xa086, 0x0028, 0x1118, 0x684b, 0x001c,
-       0x00d8, 0xd1dc, 0x0148, 0x684b, 0x0015, 0x080c, 0x99ee, 0x0118,
-       0x6944, 0xc1dc, 0x6946, 0x0080, 0xd1d4, 0x0118, 0x684b, 0x0007,
-       0x0058, 0x684b, 0x0000, 0x684c, 0xd0ac, 0x0130, 0x6810, 0x6914,
-       0xa115, 0x0110, 0x080c, 0x8e04, 0x080c, 0x510c, 0x080c, 0x9834,
-       0x1110, 0x080c, 0x8078, 0x00de, 0x0005, 0x080c, 0x6b73, 0x0010,
-       0x080c, 0x6c05, 0x080c, 0x9596, 0x01c0, 0x00d6, 0x6110, 0x2168,
-       0x6837, 0x0103, 0x2009, 0xad0c, 0x210c, 0xd18c, 0x11c0, 0xd184,
-       0x1198, 0x6108, 0x694a, 0xa18e, 0x0029, 0x1110, 0x080c, 0xabfa,
-       0x6847, 0x0000, 0x080c, 0x510c, 0x00de, 0x080c, 0x8078, 0x080c,
-       0x6c50, 0x080c, 0x6d0d, 0x0005, 0x684b, 0x0004, 0x0c88, 0x684b,
-       0x0004, 0x0c70, 0xa182, 0x0040, 0x0002, 0x9038, 0x9038, 0x9038,
-       0x9038, 0x9038, 0x903a, 0x9038, 0x903d, 0x9038, 0x9038, 0x9038,
-       0x9038, 0x9038, 0x9038, 0x9038, 0x9038, 0x9038, 0x9038, 0x9038,
-       0x080c, 0x14f6, 0x080c, 0x8078, 0x0005, 0x0006, 0x0026, 0xa016,
-       0x080c, 0x1824, 0x002e, 0x000e, 0x0005, 0xa182, 0x0085, 0x0002,
-       0x9051, 0x904f, 0x904f, 0x905d, 0x904f, 0x904f, 0x904f, 0x080c,
-       0x14f6, 0x6003, 0x0001, 0x6106, 0x080c, 0x67a8, 0x0126, 0x2091,
-       0x8000, 0x080c, 0x6c50, 0x012e, 0x0005, 0x0026, 0x0056, 0x00d6,
-       0x00e6, 0x2071, 0xb280, 0x7224, 0x6212, 0x7220, 0x080c, 0x9586,
-       0x01a0, 0x2268, 0x6800, 0xa086, 0x0000, 0x0178, 0x6018, 0x6d18,
-       0xa52e, 0x1158, 0x00c6, 0x2d60, 0x080c, 0x928f, 0x00ce, 0x0128,
-       0x6803, 0x0002, 0x6007, 0x0086, 0x0010, 0x6007, 0x0087, 0x6003,
-       0x0001, 0x080c, 0x67a8, 0x080c, 0x6c50, 0x00f6, 0x2278, 0x080c,
-       0x5029, 0x00fe, 0x0150, 0x6820, 0xd0ec, 0x0138, 0x00c6, 0x2260,
-       0x603f, 0x0000, 0x080c, 0x9866, 0x00ce, 0x00ee, 0x00de, 0x005e,
-       0x002e, 0x0005, 0xa186, 0x0013, 0x1160, 0x6004, 0xa08a, 0x0085,
-       0x0a0c, 0x14f6, 0xa08a, 0x008c, 0x1a0c, 0x14f6, 0xa082, 0x0085,
-       0x0072, 0xa186, 0x0027, 0x0120, 0xa186, 0x0014, 0x190c, 0x14f6,
-       0x080c, 0x6b73, 0x080c, 0x974e, 0x080c, 0x6c50, 0x0005, 0x90be,
-       0x90c0, 0x90c0, 0x90be, 0x90be, 0x90be, 0x90be, 0x080c, 0x14f6,
-       0x080c, 0x6b73, 0x080c, 0x974e, 0x080c, 0x6c50, 0x0005, 0xa186,
-       0x0013, 0x1128, 0x6004, 0xa082, 0x0085, 0x2008, 0x04a8, 0xa186,
-       0x0027, 0x11e8, 0x080c, 0x6b73, 0x080c, 0x2ad9, 0x00d6, 0x6010,
-       0x2068, 0x080c, 0x9596, 0x0150, 0x6837, 0x0103, 0x6847, 0x0000,
-       0x684b, 0x0029, 0x080c, 0x510c, 0x080c, 0x9742, 0x00de, 0x080c,
-       0x8078, 0x080c, 0x6c50, 0x0005, 0x080c, 0x80be, 0x0ce0, 0xa186,
-       0x0014, 0x1dd0, 0x080c, 0x6b73, 0x00d6, 0x6010, 0x2068, 0x080c,
-       0x9596, 0x0d60, 0x6837, 0x0103, 0x6847, 0x0000, 0x684b, 0x0006,
-       0x6850, 0xc0ec, 0x6852, 0x08f0, 0x0002, 0x910e, 0x910c, 0x910c,
-       0x910c, 0x910c, 0x910c, 0x9126, 0x080c, 0x14f6, 0x080c, 0x6b73,
-       0x6030, 0xa08c, 0xff00, 0x810f, 0xa186, 0x0039, 0x0118, 0xa186,
-       0x0035, 0x1118, 0x2001, 0xafa3, 0x0010, 0x2001, 0xafa4, 0x2004,
-       0x6016, 0x6003, 0x000c, 0x080c, 0x6c50, 0x0005, 0x080c, 0x6b73,
-       0x6030, 0xa08c, 0xff00, 0x810f, 0xa186, 0x0039, 0x0118, 0xa186,
-       0x0035, 0x1118, 0x2001, 0xafa3, 0x0010, 0x2001, 0xafa4, 0x2004,
-       0x6016, 0x6003, 0x000e, 0x080c, 0x6c50, 0x0005, 0xa182, 0x008c,
-       0x1220, 0xa182, 0x0085, 0x0208, 0x001a, 0x080c, 0x80be, 0x0005,
-       0x914f, 0x914f, 0x914f, 0x914f, 0x9151, 0x91a4, 0x914f, 0x080c,
-       0x14f6, 0x00d6, 0x00f6, 0x2c78, 0x080c, 0x5029, 0x00fe, 0x0168,
-       0x6030, 0xa08c, 0xff00, 0x810f, 0xa186, 0x0039, 0x0118, 0xa186,
-       0x0035, 0x1118, 0x00de, 0x0804, 0x91b7, 0x080c, 0x9742, 0x080c,
-       0x9596, 0x01c8, 0x6010, 0x2068, 0x6837, 0x0103, 0x6850, 0xd0b4,
-       0x0128, 0x684b, 0x0006, 0xc0ec, 0x6852, 0x0048, 0xd0bc, 0x0118,
-       0x684b, 0x0002, 0x0020, 0x684b, 0x0005, 0x080c, 0x9803, 0x6847,
-       0x0000, 0x080c, 0x510c, 0x2c68, 0x080c, 0x8022, 0x01c0, 0x6003,
-       0x0001, 0x6007, 0x001e, 0x600b, 0xffff, 0x2009, 0xb28e, 0x210c,
-       0x6136, 0x2009, 0xb28f, 0x210c, 0x613a, 0x6918, 0x611a, 0x080c,
-       0x9956, 0x6950, 0x6152, 0x601f, 0x0001, 0x080c, 0x67a8, 0x2d60,
-       0x080c, 0x8078, 0x00de, 0x0005, 0x00f6, 0x2c78, 0x080c, 0x5029,
-       0x00fe, 0x0598, 0x6030, 0xa08c, 0xff00, 0x810f, 0xa186, 0x0035,
-       0x0130, 0xa186, 0x001e, 0x0118, 0xa186, 0x0039, 0x1530, 0x00d6,
-       0x2c68, 0x080c, 0x9a34, 0x1904, 0x91fc, 0x080c, 0x8022, 0x01d8,
-       0x6106, 0x6003, 0x0001, 0x601f, 0x0001, 0x6918, 0x611a, 0x6928,
-       0x612a, 0x692c, 0x612e, 0x6930, 0xa18c, 0x00ff, 0x6132, 0x6934,
-       0x6136, 0x6938, 0x613a, 0x6950, 0x6152, 0x080c, 0x9956, 0x080c,
-       0x67a8, 0x080c, 0x6c50, 0x2d60, 0x00f8, 0x00d6, 0x6010, 0x2068,
-       0x080c, 0x9596, 0x01c8, 0x6837, 0x0103, 0x6850, 0xd0b4, 0x0128,
-       0xc0ec, 0x6852, 0x684b, 0x0006, 0x0048, 0xd0bc, 0x0118, 0x684b,
-       0x0002, 0x0020, 0x684b, 0x0005, 0x080c, 0x9803, 0x6847, 0x0000,
-       0x080c, 0x510c, 0x080c, 0x9742, 0x00de, 0x080c, 0x8078, 0x0005,
-       0x0016, 0x00d6, 0x6010, 0x2068, 0x080c, 0x9596, 0x0140, 0x6837,
-       0x0103, 0x684b, 0x0028, 0x6847, 0x0000, 0x080c, 0x510c, 0x00de,
-       0x001e, 0xa186, 0x0013, 0x0148, 0xa186, 0x0014, 0x0130, 0xa186,
-       0x0027, 0x0118, 0x080c, 0x80be, 0x0030, 0x080c, 0x6b73, 0x080c,
-       0x974e, 0x080c, 0x6c50, 0x0005, 0x0056, 0x0066, 0x00d6, 0x00f6,
-       0x2029, 0x0001, 0xa182, 0x0101, 0x1208, 0x0010, 0x2009, 0x0100,
-       0x2130, 0x2069, 0xb298, 0x831c, 0x2300, 0xad18, 0x2009, 0x0020,
-       0xaf90, 0x001d, 0x080c, 0x927f, 0xa6b2, 0x0020, 0x7804, 0xa06d,
-       0x0110, 0x080c, 0x1600, 0x080c, 0x15d9, 0x0500, 0x8528, 0x6837,
-       0x0110, 0x683b, 0x0000, 0x2d20, 0x7c06, 0xa68a, 0x003d, 0x1228,
-       0x2608, 0xad90, 0x000f, 0x0459, 0x0088, 0xa6b2, 0x003c, 0x2009,
-       0x003c, 0x2d78, 0xad90, 0x000f, 0x0411, 0x0c28, 0x00fe, 0x852f,
-       0xa5ad, 0x0003, 0x7d36, 0xa5ac, 0x0000, 0x0028, 0x00fe, 0x852f,
-       0xa5ad, 0x0003, 0x7d36, 0x00de, 0x006e, 0x005e, 0x0005, 0x00f6,
-       0x8dff, 0x0158, 0x6804, 0xa07d, 0x0130, 0x6807, 0x0000, 0x080c,
-       0x510c, 0x2f68, 0x0cb8, 0x080c, 0x510c, 0x00fe, 0x0005, 0x0156,
-       0xa184, 0x0001, 0x0108, 0x8108, 0x810c, 0x21a8, 0x2304, 0x8007,
-       0x2012, 0x8318, 0x8210, 0x1f04, 0x9286, 0x015e, 0x0005, 0x0066,
-       0x0126, 0x2091, 0x8000, 0x2031, 0x0001, 0x601c, 0xa084, 0x000f,
-       0x0083, 0x012e, 0x006e, 0x0005, 0x0126, 0x2091, 0x8000, 0x0066,
-       0x2031, 0x0000, 0x601c, 0xa084, 0x000f, 0x001b, 0x006e, 0x012e,
-       0x0005, 0x92c3, 0x92c3, 0x92be, 0x92e5, 0x92b1, 0x92be, 0x92e5,
-       0x92be, 0x080c, 0x14f6, 0x0036, 0x2019, 0x0010, 0x080c, 0xa566,
-       0x601f, 0x0006, 0x6003, 0x0007, 0x003e, 0x0005, 0xa006, 0x0005,
-       0xa085, 0x0001, 0x0005, 0x00d6, 0x86ff, 0x11d8, 0x6010, 0x2068,
-       0x080c, 0x9596, 0x01c0, 0x6834, 0xa086, 0x0139, 0x1128, 0x684b,
-       0x0005, 0x6853, 0x0000, 0x0028, 0xa00e, 0x2001, 0x0005, 0x080c,
-       0x51df, 0x080c, 0x9803, 0x080c, 0x510c, 0x080c, 0x8078, 0xa085,
-       0x0001, 0x00de, 0x0005, 0xa006, 0x0ce0, 0x6000, 0xa08a, 0x0010,
-       0x1a0c, 0x14f6, 0x000b, 0x0005, 0x92fc, 0x9319, 0x92fe, 0x9338,
-       0x9316, 0x92fc, 0x92be, 0x92c3, 0x92c3, 0x92be, 0x92be, 0x92be,
-       0x92be, 0x92be, 0x92be, 0x92be, 0x080c, 0x14f6, 0x86ff, 0x1198,
-       0x00d6, 0x6010, 0x2068, 0x080c, 0x9596, 0x0110, 0x080c, 0x9803,
-       0x00de, 0x6007, 0x0085, 0x6003, 0x000b, 0x601f, 0x0002, 0x080c,
-       0x67a8, 0x080c, 0x6c50, 0xa085, 0x0001, 0x0005, 0x080c, 0x190b,
-       0x0c28, 0x00e6, 0x2071, 0xafc7, 0x7024, 0xac06, 0x1110, 0x080c,
-       0x79e1, 0x601c, 0xa084, 0x000f, 0xa086, 0x0006, 0x1150, 0x0086,
-       0x0096, 0x2049, 0x0001, 0x2c40, 0x080c, 0x7b9a, 0x009e, 0x008e,
-       0x0010, 0x080c, 0x78de, 0x00ee, 0x1948, 0x080c, 0x92be, 0x0005,
-       0x0036, 0x00e6, 0x2071, 0xafc7, 0x703c, 0xac06, 0x1140, 0x2019,
-       0x0000, 0x080c, 0x7a64, 0x00ee, 0x003e, 0x0804, 0x92fe, 0x080c,
-       0x7cb8, 0x00ee, 0x003e, 0x1904, 0x92fe, 0x080c, 0x92be, 0x0005,
-       0x00c6, 0x601c, 0xa084, 0x000f, 0x0013, 0x00ce, 0x0005, 0x9369,
-       0x93d3, 0x9501, 0x9374, 0x974e, 0x9369, 0xa558, 0x8078, 0x93d3,
-       0x9362, 0x955f, 0x080c, 0x14f6, 0x080c, 0x9789, 0x1110, 0x080c,
-       0x85f3, 0x0005, 0x080c, 0x6b73, 0x080c, 0x6c50, 0x080c, 0x8078,
-       0x0005, 0x6017, 0x0001, 0x0005, 0x6010, 0xa080, 0x0019, 0x2c02,
-       0x6000, 0xa08a, 0x0010, 0x1a0c, 0x14f6, 0x000b, 0x0005, 0x938f,
-       0x9391, 0x93b1, 0x93c3, 0x93d0, 0x938f, 0x9369, 0x9369, 0x9369,
-       0x93c3, 0x93c3, 0x938f, 0x938f, 0x938f, 0x938f, 0x93cd, 0x080c,
-       0x14f6, 0x00e6, 0x6010, 0x2070, 0x7050, 0xc0b5, 0x7052, 0x2071,
-       0xafc7, 0x7024, 0xac06, 0x0190, 0x080c, 0x78de, 0x6007, 0x0085,
-       0x6003, 0x000b, 0x601f, 0x0002, 0x2001, 0xafa4, 0x2004, 0x6016,
-       0x080c, 0x67a8, 0x080c, 0x6c50, 0x00ee, 0x0005, 0x6017, 0x0001,
-       0x0cd8, 0x00d6, 0x6010, 0x2068, 0x6850, 0xc0b5, 0x6852, 0x00de,
-       0x6007, 0x0085, 0x6003, 0x000b, 0x601f, 0x0002, 0x080c, 0x67a8,
-       0x080c, 0x6c50, 0x0005, 0x00d6, 0x6017, 0x0001, 0x6010, 0x2068,
-       0x6850, 0xc0b5, 0x6852, 0x00de, 0x0005, 0x080c, 0x8078, 0x0005,
-       0x080c, 0x190b, 0x08f0, 0x6000, 0xa08a, 0x0010, 0x1a0c, 0x14f6,
-       0x000b, 0x0005, 0x93ea, 0x9371, 0x93ec, 0x93ea, 0x93ec, 0x93ec,
-       0x936a, 0x93ea, 0x9364, 0x9364, 0x93ea, 0x93ea, 0x93ea, 0x93ea,
-       0x93ea, 0x93ea, 0x080c, 0x14f6, 0x00d6, 0x6018, 0x2068, 0x6804,
-       0xa084, 0x00ff, 0x00de, 0xa08a, 0x000c, 0x1a0c, 0x14f6, 0x000b,
-       0x0005, 0x9405, 0x94a7, 0x9407, 0x9441, 0x9407, 0x9441, 0x9407,
-       0x9411, 0x9405, 0x9441, 0x9405, 0x942d, 0x080c, 0x14f6, 0x6004,
-       0xa08e, 0x0016, 0x0588, 0xa08e, 0x0004, 0x0570, 0xa08e, 0x0002,
-       0x0558, 0x6004, 0x080c, 0x9789, 0x0904, 0x94c0, 0xa08e, 0x0021,
-       0x0904, 0x94c4, 0xa08e, 0x0022, 0x0904, 0x94c0, 0xa08e, 0x003d,
-       0x0904, 0x94c4, 0xa08e, 0x0039, 0x0904, 0x94c8, 0xa08e, 0x0035,
-       0x0904, 0x94c8, 0xa08e, 0x001e, 0x0188, 0xa08e, 0x0001, 0x1150,
-       0x00d6, 0x6018, 0x2068, 0x6804, 0xa084, 0x00ff, 0x00de, 0xa086,
-       0x0006, 0x0110, 0x080c, 0x2ad9, 0x080c, 0x85f3, 0x080c, 0x974e,
-       0x0005, 0x00c6, 0x00d6, 0x6104, 0xa186, 0x0016, 0x0904, 0x9498,
-       0xa186, 0x0002, 0x1518, 0x6018, 0x2068, 0x2001, 0xad34, 0x2004,
-       0xd0ac, 0x1904, 0x94ea, 0x68a0, 0xd0bc, 0x1904, 0x94ea, 0x6840,
-       0xa084, 0x00ff, 0xa005, 0x0190, 0x8001, 0x6842, 0x6013, 0x0000,
-       0x601f, 0x0007, 0x6017, 0x0398, 0x603f, 0x0000, 0x080c, 0x8022,
-       0x0128, 0x2d00, 0x601a, 0x601f, 0x0001, 0x0450, 0x00de, 0x00ce,
-       0x6004, 0xa08e, 0x0002, 0x11a8, 0x6018, 0xa080, 0x0028, 0x2004,
-       0xa086, 0x007e, 0x1170, 0x2009, 0xad34, 0x2104, 0xc085, 0x200a,
-       0x00e6, 0x2071, 0xad00, 0x080c, 0x48f5, 0x00ee, 0x080c, 0x85f3,
-       0x0020, 0x080c, 0x85f3, 0x080c, 0x2ad9, 0x00e6, 0x0126, 0x2091,
-       0x8000, 0x080c, 0x2aff, 0x012e, 0x00ee, 0x080c, 0x974e, 0x0005,
-       0x2001, 0x0002, 0x080c, 0x4c30, 0x6003, 0x0001, 0x6007, 0x0002,
-       0x080c, 0x67ee, 0x080c, 0x6c50, 0x00de, 0x00ce, 0x0c80, 0x00c6,
-       0x00d6, 0x6104, 0xa186, 0x0016, 0x0d58, 0x6018, 0x2068, 0x6840,
-       0xa084, 0x00ff, 0xa005, 0x0904, 0x946e, 0x8001, 0x6842, 0x6003,
-       0x0001, 0x080c, 0x67ee, 0x080c, 0x6c50, 0x00de, 0x00ce, 0x08b8,
-       0x080c, 0x85f3, 0x0804, 0x943e, 0x080c, 0x8621, 0x0804, 0x943e,
-       0x00d6, 0x2c68, 0x6104, 0x080c, 0x9a34, 0x00de, 0x0118, 0x080c,
-       0x8078, 0x00b8, 0x6004, 0x8007, 0x6130, 0xa18c, 0x00ff, 0xa105,
-       0x6032, 0x6007, 0x0085, 0x6003, 0x000b, 0x601f, 0x0002, 0x6038,
-       0x600a, 0x2001, 0xafa4, 0x2004, 0x6016, 0x080c, 0x67a8, 0x080c,
-       0x6c50, 0x0005, 0x00de, 0x00ce, 0x080c, 0x85f3, 0x080c, 0x2ad9,
-       0x00e6, 0x0126, 0x2091, 0x8000, 0x080c, 0x2aff, 0x6013, 0x0000,
-       0x601f, 0x0007, 0x6017, 0x0398, 0x603f, 0x0000, 0x012e, 0x00ee,
-       0x0005, 0x6000, 0xa08a, 0x0010, 0x1a0c, 0x14f6, 0x000b, 0x0005,
-       0x9518, 0x9518, 0x9518, 0x9518, 0x9518, 0x9518, 0x9518, 0x9518,
-       0x9518, 0x9369, 0x9518, 0x9371, 0x951a, 0x9371, 0x9527, 0x9518,
-       0x080c, 0x14f6, 0x6004, 0xa086, 0x008b, 0x0148, 0x6007, 0x008b,
-       0x6003, 0x000d, 0x080c, 0x67a8, 0x080c, 0x6c50, 0x0005, 0x080c,
-       0x9742, 0x080c, 0x9596, 0x0580, 0x080c, 0x2ad9, 0x00d6, 0x080c,
-       0x9596, 0x0168, 0x6010, 0x2068, 0x6837, 0x0103, 0x684b, 0x0006,
-       0x6847, 0x0000, 0x6850, 0xc0ed, 0x6852, 0x080c, 0x510c, 0x2c68,
-       0x080c, 0x8022, 0x0150, 0x6818, 0x601a, 0x080c, 0x9956, 0x00c6,
-       0x2d60, 0x080c, 0x974e, 0x00ce, 0x0008, 0x2d60, 0x00de, 0x6013,
-       0x0000, 0x601f, 0x0001, 0x6007, 0x0001, 0x6003, 0x0001, 0x080c,
-       0x67ee, 0x080c, 0x6c50, 0x0010, 0x080c, 0x974e, 0x0005, 0x6000,
-       0xa08a, 0x0010, 0x1a0c, 0x14f6, 0x000b, 0x0005, 0x9576, 0x9576,
-       0x9576, 0x9578, 0x9579, 0x9576, 0x9576, 0x9576, 0x9576, 0x9576,
-       0x9576, 0x9576, 0x9576, 0x9576, 0x9576, 0x9576, 0x080c, 0x14f6,
-       0x0005, 0x080c, 0x7cb8, 0x190c, 0x14f6, 0x6110, 0x2168, 0x684b,
-       0x0006, 0x080c, 0x510c, 0x080c, 0x8078, 0x0005, 0xa284, 0x0007,
-       0x1158, 0xa282, 0xb400, 0x0240, 0x2001, 0xad16, 0x2004, 0xa202,
-       0x1218, 0xa085, 0x0001, 0x0005, 0xa006, 0x0ce8, 0x0026, 0x6210,
-       0xa294, 0xf000, 0x002e, 0x0005, 0x00e6, 0x00c6, 0x0036, 0x0006,
-       0x0126, 0x2091, 0x8000, 0x2061, 0xb400, 0x2071, 0xad00, 0x7344,
-       0x7064, 0xa302, 0x12a8, 0x601c, 0xa206, 0x1160, 0x080c, 0x98e3,
-       0x0148, 0x080c, 0x9789, 0x1110, 0x080c, 0x85f3, 0x00c6, 0x080c,
-       0x8078, 0x00ce, 0xace0, 0x0018, 0x7058, 0xac02, 0x1208, 0x0c38,
-       0x012e, 0x000e, 0x003e, 0x00ce, 0x00ee, 0x0005, 0x00e6, 0x00c6,
-       0x0016, 0xa188, 0xae34, 0x210c, 0x81ff, 0x0170, 0x2061, 0xb400,
-       0x2071, 0xad00, 0x0016, 0x080c, 0x8022, 0x001e, 0x0138, 0x611a,
-       0x080c, 0x2ad9, 0x080c, 0x8078, 0xa006, 0x0010, 0xa085, 0x0001,
-       0x001e, 0x00ce, 0x00ee, 0x0005, 0x00c6, 0x0056, 0x0126, 0x2091,
-       0x8000, 0x00c6, 0x080c, 0x8022, 0x005e, 0x0180, 0x6612, 0x651a,
-       0x080c, 0x9956, 0x601f, 0x0003, 0x2009, 0x004b, 0x080c, 0x80a7,
-       0xa085, 0x0001, 0x012e, 0x005e, 0x00ce, 0x0005, 0xa006, 0x0cd0,
-       0x00c6, 0x0056, 0x0126, 0x2091, 0x8000, 0x62a0, 0x00c6, 0x080c,
-       0x8022, 0x005e, 0x0508, 0x6013, 0x0000, 0x651a, 0x080c, 0x9956,
-       0x601f, 0x0003, 0x00c6, 0x2560, 0x080c, 0x4ecf, 0x00ce, 0x080c,
-       0x68e7, 0x0076, 0x2039, 0x0000, 0x080c, 0x681d, 0x2c08, 0x080c,
-       0xa712, 0x007e, 0x2009, 0x004c, 0x080c, 0x80a7, 0xa085, 0x0001,
-       0x012e, 0x005e, 0x00ce, 0x0005, 0xa006, 0x0cd0, 0x00f6, 0x00c6,
-       0x0046, 0x00c6, 0x080c, 0x8022, 0x2c78, 0x00ce, 0x0180, 0x7e12,
-       0x2c00, 0x781a, 0x781f, 0x0003, 0x2021, 0x0005, 0x080c, 0x9683,
-       0x2f60, 0x2009, 0x004d, 0x080c, 0x80a7, 0xa085, 0x0001, 0x004e,
-       0x00ce, 0x00fe, 0x0005, 0x00f6, 0x00c6, 0x0046, 0x00c6, 0x080c,
-       0x8022, 0x2c78, 0x00ce, 0x0178, 0x7e12, 0x2c00, 0x781a, 0x781f,
-       0x0003, 0x2021, 0x0005, 0x0439, 0x2f60, 0x2009, 0x004e, 0x080c,
-       0x80a7, 0xa085, 0x0001, 0x004e, 0x00ce, 0x00fe, 0x0005, 0x00f6,
-       0x00c6, 0x0046, 0x00c6, 0x080c, 0x8022, 0x2c78, 0x00ce, 0x0178,
-       0x7e12, 0x2c00, 0x781a, 0x781f, 0x0003, 0x2021, 0x0004, 0x0059,
-       0x2f60, 0x2009, 0x0052, 0x080c, 0x80a7, 0xa085, 0x0001, 0x004e,
-       0x00ce, 0x00fe, 0x0005, 0x0096, 0x0076, 0x0126, 0x2091, 0x8000,
-       0x080c, 0x4e71, 0x0118, 0x2001, 0x9688, 0x0028, 0x080c, 0x4e43,
-       0x0158, 0x2001, 0x968e, 0x0006, 0xa00e, 0x2400, 0x080c, 0x51df,
-       0x080c, 0x510c, 0x000e, 0x0807, 0x2418, 0x080c, 0x6b15, 0x62a0,
-       0x0086, 0x2041, 0x0001, 0x2039, 0x0001, 0x2608, 0x080c, 0x6900,
-       0x008e, 0x080c, 0x681d, 0x2f08, 0x2648, 0x080c, 0xa712, 0x613c,
-       0x81ff, 0x090c, 0x69a9, 0x012e, 0x007e, 0x009e, 0x0005, 0x00c6,
-       0x0126, 0x2091, 0x8000, 0x00c6, 0x080c, 0x8022, 0x001e, 0x0188,
-       0x660a, 0x611a, 0x080c, 0x9956, 0x601f, 0x0001, 0x2d00, 0x6012,
-       0x2009, 0x001f, 0x080c, 0x80a7, 0xa085, 0x0001, 0x012e, 0x00ce,
-       0x0005, 0xa006, 0x0cd8, 0x00c6, 0x0126, 0x2091, 0x8000, 0x00c6,
-       0x080c, 0x8022, 0x001e, 0x0188, 0x660a, 0x611a, 0x080c, 0x9956,
-       0x601f, 0x0008, 0x2d00, 0x6012, 0x2009, 0x0021, 0x080c, 0x80a7,
-       0xa085, 0x0001, 0x012e, 0x00ce, 0x0005, 0xa006, 0x0cd8, 0x00c6,
-       0x0126, 0x2091, 0x8000, 0x00c6, 0x080c, 0x8022, 0x001e, 0x0188,
-       0x660a, 0x611a, 0x080c, 0x9956, 0x601f, 0x0001, 0x2d00, 0x6012,
-       0x2009, 0x003d, 0x080c, 0x80a7, 0xa085, 0x0001, 0x012e, 0x00ce,
-       0x0005, 0xa006, 0x0cd8, 0x00c6, 0x0126, 0x2091, 0x8000, 0x00c6,
-       0x080c, 0x9807, 0x001e, 0x0180, 0x611a, 0x080c, 0x9956, 0x601f,
-       0x0001, 0x2d00, 0x6012, 0x2009, 0x0000, 0x080c, 0x80a7, 0xa085,
-       0x0001, 0x012e, 0x00ce, 0x0005, 0xa006, 0x0cd8, 0x00c6, 0x0126,
-       0x2091, 0x8000, 0x00c6, 0x080c, 0x8022, 0x001e, 0x0188, 0x660a,
-       0x611a, 0x080c, 0x9956, 0x601f, 0x0001, 0x2d00, 0x6012, 0x2009,
-       0x0044, 0x080c, 0x80a7, 0xa085, 0x0001, 0x012e, 0x00ce, 0x0005,
-       0xa006, 0x0cd8, 0x0026, 0x00d6, 0x6218, 0x2268, 0x6a3c, 0x82ff,
-       0x0110, 0x8211, 0x6a3e, 0x00de, 0x002e, 0x0005, 0x0006, 0x6000,
-       0xa086, 0x0000, 0x0190, 0x6013, 0x0000, 0x601f, 0x0007, 0x2001,
-       0xafa3, 0x2004, 0x0006, 0xa082, 0x0051, 0x000e, 0x0208, 0x8004,
-       0x6016, 0x080c, 0xabb4, 0x603f, 0x0000, 0x000e, 0x0005, 0x0066,
-       0x00c6, 0x00d6, 0x2031, 0xad52, 0x2634, 0xd6e4, 0x0128, 0x6618,
-       0x2660, 0x6e48, 0x080c, 0x4dfc, 0x00de, 0x00ce, 0x006e, 0x0005,
-       0x0006, 0x0016, 0x6004, 0xa08e, 0x0002, 0x0140, 0xa08e, 0x0003,
-       0x0128, 0xa08e, 0x0004, 0x0110, 0xa085, 0x0001, 0x001e, 0x000e,
-       0x0005, 0x0006, 0x00d6, 0x6010, 0xa06d, 0x0148, 0x6834, 0xa086,
-       0x0139, 0x0138, 0x6838, 0xd0fc, 0x0110, 0xa006, 0x0010, 0xa085,
-       0x0001, 0x00de, 0x000e, 0x0005, 0x00c6, 0x0126, 0x2091, 0x8000,
-       0x00c6, 0x080c, 0x8022, 0x001e, 0x0190, 0x611a, 0x080c, 0x9956,
-       0x601f, 0x0001, 0x2d00, 0x6012, 0x080c, 0x2ad9, 0x2009, 0x0028,
-       0x080c, 0x80a7, 0xa085, 0x0001, 0x012e, 0x00ce, 0x0005, 0xa006,
-       0x0cd8, 0xa186, 0x0015, 0x1178, 0x2011, 0xad20, 0x2204, 0xa086,
-       0x0074, 0x1148, 0x080c, 0x8943, 0x6003, 0x0001, 0x6007, 0x0029,
-       0x080c, 0x67ee, 0x0020, 0x080c, 0x85f3, 0x080c, 0x8078, 0x0005,
-       0xa186, 0x0016, 0x1128, 0x2001, 0x0004, 0x080c, 0x4c30, 0x00e8,
-       0xa186, 0x0015, 0x11e8, 0x2011, 0xad20, 0x2204, 0xa086, 0x0014,
-       0x11b8, 0x00d6, 0x6018, 0x2068, 0x080c, 0x4d72, 0x00de, 0x080c,
-       0x89f7, 0x1170, 0x00d6, 0x6018, 0x2068, 0x6890, 0x00de, 0xa005,
-       0x0138, 0x2001, 0x0006, 0x080c, 0x4c30, 0x080c, 0x81f6, 0x0020,
-       0x080c, 0x85f3, 0x080c, 0x8078, 0x0005, 0x6848, 0xa086, 0x0005,
-       0x1108, 0x0009, 0x0005, 0x6850, 0xc0ad, 0x6852, 0x0005, 0x00e6,
-       0x0126, 0x2071, 0xad00, 0x2091, 0x8000, 0x7544, 0xa582, 0x0001,
-       0x0608, 0x7048, 0x2060, 0x6000, 0xa086, 0x0000, 0x0148, 0xace0,
-       0x0018, 0x7058, 0xac02, 0x1208, 0x0cb0, 0x2061, 0xb400, 0x0c98,
-       0x6003, 0x0008, 0x8529, 0x7546, 0xaca8, 0x0018, 0x7058, 0xa502,
-       0x1230, 0x754a, 0xa085, 0x0001, 0x012e, 0x00ee, 0x0005, 0x704b,
-       0xb400, 0x0cc0, 0xa006, 0x0cc0, 0x00e6, 0x2071, 0xb28c, 0x7014,
-       0xd0e4, 0x0150, 0x6013, 0x0000, 0x6003, 0x0001, 0x6007, 0x0050,
-       0x080c, 0x67a8, 0x080c, 0x6c50, 0x00ee, 0x0005, 0x00c6, 0x00f6,
-       0x2c78, 0x080c, 0x5029, 0x00fe, 0x0120, 0x601c, 0xa084, 0x000f,
-       0x0013, 0x00ce, 0x0005, 0x9369, 0x985e, 0x9861, 0x9864, 0xa9a7,
-       0xa9c2, 0xa9c5, 0x9369, 0x9369, 0x080c, 0x14f6, 0xe000, 0xe000,
-       0x0005, 0xe000, 0xe000, 0x0005, 0x0009, 0x0005, 0x00f6, 0x2c78,
-       0x080c, 0x5029, 0x0538, 0x080c, 0x8022, 0x1128, 0x2001, 0xafa5,
-       0x2004, 0x783e, 0x00f8, 0x7818, 0x601a, 0x080c, 0x9956, 0x781c,
-       0xa086, 0x0003, 0x0128, 0x7808, 0x6036, 0x2f00, 0x603a, 0x0020,
-       0x7808, 0x603a, 0x2f00, 0x6036, 0x602a, 0x601f, 0x0001, 0x6007,
-       0x0035, 0x6003, 0x0001, 0x7950, 0x6152, 0x080c, 0x67a8, 0x080c,
-       0x6c50, 0x2f60, 0x00fe, 0x0005, 0x0016, 0x00f6, 0x682c, 0x6032,
-       0xa08e, 0x0001, 0x0138, 0xa086, 0x0005, 0x0140, 0xa006, 0x602a,
-       0x602e, 0x00a0, 0x6820, 0xc0f4, 0xc0d5, 0x6822, 0x6810, 0x2078,
-       0x787c, 0x6938, 0xa102, 0x7880, 0x6934, 0xa103, 0x1e78, 0x6834,
-       0x602a, 0x6838, 0xa084, 0xfffc, 0x683a, 0x602e, 0x2d00, 0x6036,
-       0x6808, 0x603a, 0x6918, 0x611a, 0x6950, 0x6152, 0x601f, 0x0001,
-       0x6007, 0x0039, 0x6003, 0x0001, 0x080c, 0x67a8, 0x6803, 0x0002,
-       0x00fe, 0x001e, 0x0005, 0x00f6, 0x2c78, 0x080c, 0x5029, 0x1118,
-       0xa085, 0x0001, 0x0070, 0x6020, 0xd0f4, 0x1150, 0xc0f5, 0x6022,
-       0x6010, 0x2078, 0x7828, 0x603a, 0x782c, 0x6036, 0x080c, 0x190b,
-       0xa006, 0x00fe, 0x0005, 0x0006, 0x0016, 0x6004, 0xa08e, 0x0034,
-       0x01b8, 0xa08e, 0x0035, 0x01a0, 0xa08e, 0x0036, 0x0188, 0xa08e,
-       0x0037, 0x0170, 0xa08e, 0x0038, 0x0158, 0xa08e, 0x0039, 0x0140,
-       0xa08e, 0x003a, 0x0128, 0xa08e, 0x003b, 0x0110, 0xa085, 0x0001,
-       0x001e, 0x000e, 0x0005, 0x0006, 0x0016, 0x0026, 0x0036, 0x00e6,
-       0x2001, 0xaf9f, 0x200c, 0x8000, 0x2014, 0x2001, 0x0032, 0x080c,
-       0x6665, 0x2001, 0xafa3, 0x82ff, 0x1110, 0x2011, 0x0002, 0x2202,
-       0x2001, 0xafa1, 0x200c, 0x8000, 0x2014, 0x2071, 0xaf8d, 0x711a,
-       0x721e, 0x2001, 0x0064, 0x080c, 0x6665, 0x2001, 0xafa4, 0x82ff,
-       0x1110, 0x2011, 0x0002, 0x2202, 0x2009, 0xafa5, 0xa280, 0x000a,
-       0x200a, 0x00ee, 0x003e, 0x002e, 0x001e, 0x000e, 0x0005, 0x0006,
-       0x00e6, 0x2001, 0xafa3, 0x2003, 0x0028, 0x2001, 0xafa4, 0x2003,
-       0x0014, 0x2071, 0xaf8d, 0x701b, 0x0000, 0x701f, 0x07d0, 0x2001,
-       0xafa5, 0x2003, 0x001e, 0x00ee, 0x000e, 0x0005, 0x00d6, 0x6054,
-       0xa06d, 0x0110, 0x080c, 0x15f0, 0x00de, 0x0005, 0x0005, 0x00c6,
-       0x0126, 0x2091, 0x8000, 0x00c6, 0x080c, 0x8022, 0x001e, 0x0178,
-       0x611a, 0x0ca1, 0x601f, 0x0001, 0x2d00, 0x6012, 0x2009, 0x0033,
-       0x080c, 0x80a7, 0xa085, 0x0001, 0x012e, 0x00ce, 0x0005, 0xa006,
-       0x0cd8, 0x00d6, 0x00e6, 0x00f6, 0x2071, 0xad00, 0xa186, 0x0015,
-       0x1500, 0x7080, 0xa086, 0x0018, 0x11e0, 0x6010, 0x2068, 0x6a3c,
-       0xd2e4, 0x1160, 0x2c78, 0x080c, 0x6e05, 0x01d8, 0x706c, 0x6a50,
-       0xa206, 0x1160, 0x7070, 0x6a54, 0xa206, 0x1140, 0x6218, 0xa290,
-       0x0028, 0x2214, 0x2009, 0x0000, 0x080c, 0x2b1e, 0x080c, 0x81f6,
-       0x0020, 0x080c, 0x85f3, 0x080c, 0x8078, 0x00fe, 0x00ee, 0x00de,
-       0x0005, 0x7050, 0x6a54, 0xa206, 0x0d48, 0x0c80, 0x00c6, 0x0126,
-       0x2091, 0x8000, 0x00c6, 0x080c, 0x8022, 0x001e, 0x0180, 0x611a,
-       0x080c, 0x9956, 0x601f, 0x0001, 0x2d00, 0x6012, 0x2009, 0x0043,
-       0x080c, 0x80a7, 0xa085, 0x0001, 0x012e, 0x00ce, 0x0005, 0xa006,
-       0x0cd8, 0x00d6, 0x00e6, 0x00f6, 0x2071, 0xad00, 0xa186, 0x0015,
-       0x11c0, 0x7080, 0xa086, 0x0004, 0x11a0, 0x6010, 0xa0e8, 0x000f,
-       0x2c78, 0x080c, 0x6e05, 0x01a8, 0x706c, 0x6a08, 0xa206, 0x1130,
-       0x7070, 0x6a0c, 0xa206, 0x1110, 0x080c, 0x2ad9, 0x080c, 0x81f6,
-       0x0020, 0x080c, 0x85f3, 0x080c, 0x8078, 0x00fe, 0x00ee, 0x00de,
-       0x0005, 0x7050, 0x6a0c, 0xa206, 0x0d78, 0x0c80, 0x0016, 0x0026,
-       0x684c, 0xd0ac, 0x0178, 0x6914, 0x6a10, 0x2100, 0xa205, 0x0150,
-       0x6860, 0xa106, 0x1118, 0x685c, 0xa206, 0x0120, 0x6962, 0x6a5e,
-       0xa085, 0x0001, 0x002e, 0x001e, 0x0005, 0x00d6, 0x0036, 0x6310,
-       0x2368, 0x684a, 0x6952, 0xa29e, 0x4000, 0x1188, 0x00c6, 0x6318,
-       0x2360, 0x2009, 0x0000, 0x080c, 0x4f6e, 0x1108, 0xc185, 0x6000,
-       0xd0bc, 0x0108, 0xc18d, 0x6a66, 0x696a, 0x00ce, 0x0080, 0x6a66,
-       0x3918, 0xa398, 0x0006, 0x231c, 0x686b, 0x0004, 0x6b72, 0x00c6,
-       0x6318, 0x2360, 0x6004, 0xa084, 0x00ff, 0x686e, 0x00ce, 0x080c,
-       0x510c, 0x003e, 0x00de, 0x0005, 0x00c6, 0x0026, 0x0016, 0xa186,
-       0x0035, 0x0110, 0x6a34, 0x0008, 0x6a28, 0x080c, 0x9586, 0x01f0,
-       0x2260, 0x611c, 0xa186, 0x0003, 0x0118, 0xa186, 0x0006, 0x1190,
-       0x6834, 0xa206, 0x0140, 0x6838, 0xa206, 0x1160, 0x6108, 0x6834,
-       0xa106, 0x1140, 0x0020, 0x6008, 0x6938, 0xa106, 0x1118, 0x6018,
-       0x6918, 0xa106, 0x001e, 0x002e, 0x00ce, 0x0005, 0xa085, 0x0001,
-       0x0cc8, 0x0066, 0x6000, 0xa0b2, 0x0010, 0x1a0c, 0x14f6, 0x0013,
-       0x006e, 0x0005, 0x9a7a, 0x9eff, 0xa027, 0x9a7a, 0x9a7a, 0x9a7a,
-       0x9a7a, 0x9a7a, 0x9ab2, 0xa0a3, 0x9a7a, 0x9a7a, 0x9a7a, 0x9a7a,
-       0x9a7a, 0x9a7a, 0x080c, 0x14f6, 0x0066, 0x6000, 0xa0b2, 0x0010,
-       0x1a0c, 0x14f6, 0x0013, 0x006e, 0x0005, 0x9a95, 0xa4fd, 0x9a95,
-       0x9a95, 0x9a95, 0x9a95, 0x9a95, 0x9a95, 0xa4c1, 0xa545, 0x9a95,
-       0xaaea, 0xab1a, 0xaaea, 0xab1a, 0x9a95, 0x080c, 0x14f6, 0x0066,
-       0x6000, 0xa0b2, 0x0010, 0x1a0c, 0x14f6, 0x0013, 0x006e, 0x0005,
-       0x9ab0, 0xa1d8, 0xa295, 0xa2c2, 0xa346, 0x9ab0, 0xa433, 0xa3de,
-       0xa0af, 0xa497, 0xa4ac, 0x9ab0, 0x9ab0, 0x9ab0, 0x9ab0, 0x9ab0,
-       0x080c, 0x14f6, 0xa1b2, 0x0080, 0x1a0c, 0x14f6, 0x2100, 0xa1b2,
-       0x0040, 0x1a04, 0x9e79, 0x0002, 0x9afc, 0x9cab, 0x9afc, 0x9afc,
-       0x9afc, 0x9cb2, 0x9afc, 0x9afc, 0x9afc, 0x9afc, 0x9afc, 0x9afc,
-       0x9afc, 0x9afc, 0x9afc, 0x9afc, 0x9afc, 0x9afc, 0x9afc, 0x9afc,
-       0x9afc, 0x9afc, 0x9afc, 0x9afe, 0x9b5a, 0x9b65, 0x9ba6, 0x9bc0,
-       0x9c3e, 0x9c9c, 0x9afc, 0x9afc, 0x9cb5, 0x9afc, 0x9afc, 0x9cc4,
-       0x9ccb, 0x9afc, 0x9afc, 0x9afc, 0x9afc, 0x9afc, 0x9d42, 0x9afc,
-       0x9afc, 0x9d4d, 0x9afc, 0x9afc, 0x9d18, 0x9afc, 0x9afc, 0x9afc,
-       0x9d61, 0x9afc, 0x9afc, 0x9afc, 0x9dd5, 0x9afc, 0x9afc, 0x9afc,
-       0x9afc, 0x9afc, 0x9afc, 0x9e40, 0x080c, 0x14f6, 0x080c, 0x502d,
-       0x1140, 0x2001, 0xad34, 0x2004, 0xa084, 0x0009, 0xa086, 0x0008,
-       0x1140, 0x6007, 0x0009, 0x602b, 0x0009, 0x6013, 0x0000, 0x0804,
-       0x9ca6, 0x080c, 0x501d, 0x00e6, 0x00c6, 0x0036, 0x0026, 0x0016,
-       0x6218, 0x2270, 0x72a0, 0x0026, 0x2019, 0x0029, 0x080c, 0x68e7,
-       0x0076, 0x2039, 0x0000, 0x080c, 0x681d, 0x2c08, 0x080c, 0xa712,
-       0x007e, 0x001e, 0x2e60, 0x080c, 0x4ecf, 0x001e, 0x002e, 0x003e,
-       0x00ce, 0x00ee, 0x6618, 0x00c6, 0x2660, 0x080c, 0x4ceb, 0x00ce,
-       0xa6b0, 0x0001, 0x2634, 0xa684, 0x00ff, 0xa082, 0x0006, 0x0278,
-       0x080c, 0xa656, 0x1904, 0x9ba0, 0x080c, 0xa5f6, 0x1120, 0x6007,
-       0x0008, 0x0804, 0x9ca6, 0x6007, 0x0009, 0x0804, 0x9ca6, 0x080c,
-       0xa801, 0x0128, 0x080c, 0xa656, 0x0d78, 0x0804, 0x9ba0, 0x6013,
-       0x1900, 0x0c88, 0x6106, 0x080c, 0xa5a6, 0x6007, 0x0006, 0x0804,
-       0x9ca6, 0x6007, 0x0007, 0x0804, 0x9ca6, 0x080c, 0xab4e, 0x1904,
-       0x9e76, 0x00d6, 0x6618, 0x2668, 0x6e04, 0xa6b4, 0xff00, 0x8637,
-       0xa686, 0x0006, 0x0188, 0xa686, 0x0004, 0x0170, 0x6e04, 0xa6b4,
-       0x00ff, 0xa686, 0x0006, 0x0140, 0xa686, 0x0004, 0x0128, 0xa686,
-       0x0005, 0x0110, 0x00de, 0x00e0, 0x080c, 0xa6b4, 0x11a0, 0xa686,
-       0x0006, 0x1150, 0x0026, 0x6218, 0xa290, 0x0028, 0x2214, 0x2009,
-       0x0000, 0x080c, 0x2b1e, 0x002e, 0x080c, 0x4d72, 0x6007, 0x000a,
-       0x00de, 0x0804, 0x9ca6, 0x6007, 0x000b, 0x00de, 0x0804, 0x9ca6,
-       0x080c, 0x2ad9, 0x6007, 0x0001, 0x0804, 0x9ca6, 0x080c, 0xab4e,
-       0x1904, 0x9e76, 0x6618, 0x00d6, 0x2668, 0x6e04, 0x00de, 0xa686,
-       0x0707, 0x0d70, 0x0026, 0x6218, 0xa290, 0x0028, 0x2214, 0x2009,
-       0x0000, 0x080c, 0x2b1e, 0x002e, 0x6007, 0x000c, 0x0804, 0x9ca6,
-       0x080c, 0x502d, 0x1140, 0x2001, 0xad34, 0x2004, 0xa084, 0x0009,
-       0xa086, 0x0008, 0x1110, 0x0804, 0x9b09, 0x080c, 0x501d, 0x6618,
-       0xa6b0, 0x0001, 0x2634, 0xa684, 0x00ff, 0xa082, 0x0006, 0x06e8,
-       0x1138, 0x0026, 0x2001, 0x0006, 0x080c, 0x4c5d, 0x002e, 0x0050,
-       0xa6b4, 0xff00, 0x8637, 0xa686, 0x0004, 0x0120, 0xa686, 0x0006,
-       0x1904, 0x9ba0, 0x080c, 0xa6c1, 0x1120, 0x6007, 0x000e, 0x0804,
-       0x9ca6, 0x0046, 0x6418, 0xa4a0, 0x0028, 0x2424, 0xa4a4, 0x00ff,
-       0x8427, 0x0046, 0x080c, 0x2ad9, 0x004e, 0x0016, 0xa006, 0x2009,
-       0xad52, 0x210c, 0xd1a4, 0x0158, 0x2009, 0x0029, 0x080c, 0xa96c,
-       0x6018, 0x00d6, 0x2068, 0x6800, 0xc0e5, 0x6802, 0x00de, 0x001e,
-       0x004e, 0x6007, 0x0001, 0x0804, 0x9ca6, 0x2001, 0x0001, 0x080c,
-       0x4c1e, 0x0156, 0x0016, 0x0026, 0x0036, 0x20a9, 0x0004, 0x2019,
-       0xad05, 0x2011, 0xb290, 0x080c, 0x8a7c, 0x003e, 0x002e, 0x001e,
-       0x015e, 0xa005, 0x0168, 0xa6b4, 0xff00, 0x8637, 0xa682, 0x0004,
-       0x0a04, 0x9ba0, 0xa682, 0x0007, 0x0a04, 0x9bea, 0x0804, 0x9ba0,
-       0x6013, 0x1900, 0x6007, 0x0009, 0x0804, 0x9ca6, 0x080c, 0x502d,
-       0x1140, 0x2001, 0xad34, 0x2004, 0xa084, 0x0009, 0xa086, 0x0008,
-       0x1110, 0x0804, 0x9b09, 0x080c, 0x501d, 0x6618, 0xa6b0, 0x0001,
-       0x2634, 0xa684, 0x00ff, 0xa082, 0x0006, 0x06b0, 0xa6b4, 0xff00,
-       0x8637, 0xa686, 0x0004, 0x0120, 0xa686, 0x0006, 0x1904, 0x9ba0,
-       0x080c, 0xa6e9, 0x1130, 0x080c, 0xa5f6, 0x1118, 0x6007, 0x0010,
-       0x04e8, 0x0046, 0x6418, 0xa4a0, 0x0028, 0x2424, 0xa4a4, 0x00ff,
-       0x8427, 0x0046, 0x080c, 0x2ad9, 0x004e, 0x0016, 0xa006, 0x2009,
-       0xad52, 0x210c, 0xd1a4, 0x0158, 0x2009, 0x0029, 0x080c, 0xa96c,
-       0x6018, 0x00d6, 0x2068, 0x6800, 0xc0e5, 0x6802, 0x00de, 0x001e,
-       0x004e, 0x6007, 0x0001, 0x00d0, 0x080c, 0xa801, 0x0140, 0xa6b4,
-       0xff00, 0x8637, 0xa686, 0x0006, 0x0958, 0x0804, 0x9ba0, 0x6013,
-       0x1900, 0x6007, 0x0009, 0x0050, 0x080c, 0xab4e, 0x1904, 0x9e76,
-       0x080c, 0x9e98, 0x1904, 0x9ba0, 0x6007, 0x0012, 0x6003, 0x0001,
-       0x080c, 0x67ee, 0x0005, 0x6007, 0x0001, 0x6003, 0x0001, 0x080c,
-       0x67ee, 0x0cc0, 0x6007, 0x0005, 0x0cc0, 0x080c, 0xab4e, 0x1904,
-       0x9e76, 0x080c, 0x9e98, 0x1904, 0x9ba0, 0x6007, 0x0020, 0x6003,
-       0x0001, 0x080c, 0x67ee, 0x0005, 0x6007, 0x0023, 0x6003, 0x0001,
-       0x080c, 0x67ee, 0x0005, 0x080c, 0xab4e, 0x1904, 0x9e76, 0x080c,
-       0x9e98, 0x1904, 0x9ba0, 0x0016, 0x0026, 0x2011, 0xb291, 0x2214,
-       0xa286, 0xffff, 0x0190, 0x2c08, 0x080c, 0x9586, 0x01d8, 0x2260,
-       0x2011, 0xb290, 0x2214, 0x6008, 0xa206, 0x11a0, 0x6018, 0xa190,
-       0x0006, 0x2214, 0xa206, 0x01e0, 0x0068, 0x2011, 0xb290, 0x2214,
-       0x2c08, 0x080c, 0xa940, 0x11a0, 0x2011, 0xb291, 0x2214, 0xa286,
-       0xffff, 0x01a0, 0x2160, 0x6007, 0x0026, 0x6013, 0x1700, 0x2011,
-       0xb289, 0x2214, 0xa296, 0xffff, 0x1160, 0x6007, 0x0025, 0x0048,
-       0x601c, 0xa086, 0x0007, 0x1d70, 0x080c, 0x8078, 0x2160, 0x6007,
-       0x0025, 0x6003, 0x0001, 0x080c, 0x67ee, 0x002e, 0x001e, 0x0005,
-       0x2001, 0x0001, 0x080c, 0x4c1e, 0x0156, 0x0016, 0x0026, 0x0036,
-       0x20a9, 0x0004, 0x2019, 0xad05, 0x2011, 0xb296, 0x080c, 0x8a7c,
-       0x003e, 0x002e, 0x001e, 0x015e, 0x0120, 0x6007, 0x0031, 0x0804,
-       0x9ca6, 0x080c, 0x87bd, 0x080c, 0x574f, 0x1158, 0x0006, 0x0026,
-       0x0036, 0x080c, 0x576b, 0x0110, 0x080c, 0x5726, 0x003e, 0x002e,
-       0x000e, 0x0005, 0x6106, 0x080c, 0x9eb4, 0x6007, 0x002b, 0x0804,
-       0x9ca6, 0x6007, 0x002c, 0x0804, 0x9ca6, 0x080c, 0xab4e, 0x1904,
-       0x9e76, 0x080c, 0x9e98, 0x1904, 0x9ba0, 0x6106, 0x080c, 0x9eb8,
-       0x1120, 0x6007, 0x002e, 0x0804, 0x9ca6, 0x6007, 0x002f, 0x0804,
-       0x9ca6, 0x00e6, 0x00d6, 0x00c6, 0x6018, 0xa080, 0x0001, 0x200c,
-       0xa184, 0x00ff, 0xa086, 0x0006, 0x0158, 0xa184, 0xff00, 0x8007,
-       0xa086, 0x0006, 0x0128, 0x00ce, 0x00de, 0x00ee, 0x0804, 0x9cab,
-       0x2001, 0xad71, 0x2004, 0xd0e4, 0x0904, 0x9dd2, 0x2071, 0xb28c,
-       0x7010, 0x6036, 0x7014, 0x603a, 0x7108, 0x720c, 0x2001, 0xad52,
-       0x2004, 0xd0a4, 0x0140, 0x6018, 0x2068, 0x6810, 0xa106, 0x1118,
-       0x6814, 0xa206, 0x01f8, 0x2001, 0xad52, 0x2004, 0xd0ac, 0x1580,
-       0x2069, 0xad00, 0x6870, 0xa206, 0x1558, 0x686c, 0xa106, 0x1540,
-       0x7210, 0x080c, 0x9586, 0x0548, 0x080c, 0xa9d4, 0x0530, 0x622a,
-       0x6007, 0x0036, 0x6003, 0x0001, 0x080c, 0x67a8, 0x00ce, 0x00de,
-       0x00ee, 0x0005, 0x7214, 0xa286, 0xffff, 0x0150, 0x080c, 0x9586,
-       0x01a0, 0xa280, 0x0002, 0x2004, 0x7110, 0xa106, 0x1170, 0x0c08,
-       0x7210, 0x2c08, 0x080c, 0xa940, 0x2c10, 0x2160, 0x0130, 0x08c8,
-       0x6007, 0x0037, 0x6013, 0x1500, 0x08e8, 0x6007, 0x0037, 0x6013,
-       0x1700, 0x08c0, 0x6007, 0x0012, 0x08a8, 0x6018, 0xa080, 0x0001,
-       0x2004, 0xa084, 0xff00, 0x8007, 0xa086, 0x0006, 0x1904, 0x9cab,
-       0x00e6, 0x00d6, 0x00c6, 0x2001, 0xad71, 0x2004, 0xd0e4, 0x0904,
-       0x9e38, 0x2069, 0xad00, 0x2071, 0xb28c, 0x7008, 0x6036, 0x720c,
-       0x623a, 0xa286, 0xffff, 0x1140, 0x7208, 0x00c6, 0x2c08, 0x080c,
-       0xa940, 0x2c10, 0x00ce, 0x0588, 0x080c, 0x9586, 0x0570, 0x00c6,
-       0x0026, 0x2260, 0x080c, 0x928f, 0x002e, 0x00ce, 0x7118, 0xa18c,
-       0xff00, 0x810f, 0xa186, 0x0001, 0x0158, 0xa186, 0x0005, 0x0118,
-       0xa186, 0x0007, 0x1178, 0xa280, 0x0004, 0x2004, 0xa005, 0x0150,
-       0x0056, 0x7510, 0x7614, 0x080c, 0xa9eb, 0x005e, 0x00ce, 0x00de,
-       0x00ee, 0x0005, 0x6007, 0x003b, 0x602b, 0x0009, 0x6013, 0x2a00,
-       0x6003, 0x0001, 0x080c, 0x67a8, 0x0c88, 0x6007, 0x003b, 0x602b,
-       0x0009, 0x6013, 0x1700, 0x6003, 0x0001, 0x080c, 0x67a8, 0x0c30,
-       0x6007, 0x003b, 0x602b, 0x000b, 0x6013, 0x0000, 0x0804, 0x9daa,
-       0x00e6, 0x0026, 0x080c, 0x502d, 0x0558, 0x080c, 0x501d, 0x080c,
-       0xabc5, 0x1520, 0x2071, 0xad00, 0x70d0, 0xc085, 0x70d2, 0x00f6,
-       0x2079, 0x0100, 0x729c, 0xa284, 0x00ff, 0x706e, 0x78e6, 0xa284,
-       0xff00, 0x7270, 0xa205, 0x7072, 0x78ea, 0x00fe, 0x70db, 0x0000,
-       0x2001, 0xad52, 0x2004, 0xd0a4, 0x0120, 0x2011, 0xafe0, 0x2013,
-       0x07d0, 0xd0ac, 0x1128, 0x080c, 0x28fa, 0x0010, 0x080c, 0xabf1,
-       0x002e, 0x00ee, 0x080c, 0x8078, 0x0804, 0x9caa, 0x080c, 0x8078,
-       0x0005, 0x2600, 0x0002, 0x9e81, 0x9e81, 0x9e81, 0x9e81, 0x9e81,
-       0x9e83, 0x080c, 0x14f6, 0x080c, 0xab4e, 0x1d80, 0x0089, 0x1138,
-       0x6007, 0x0045, 0x6003, 0x0001, 0x080c, 0x67ee, 0x0005, 0x080c,
-       0x2ad9, 0x6007, 0x0001, 0x6003, 0x0001, 0x080c, 0x67ee, 0x0005,
-       0x00d6, 0x0066, 0x6618, 0x2668, 0x6e04, 0xa6b4, 0xff00, 0x8637,
-       0xa686, 0x0006, 0x0170, 0xa686, 0x0004, 0x0158, 0x6e04, 0xa6b4,
-       0x00ff, 0xa686, 0x0006, 0x0128, 0xa686, 0x0004, 0x0110, 0xa085,
-       0x0001, 0x006e, 0x00de, 0x0005, 0x00d6, 0x0449, 0x00de, 0x0005,
-       0x00d6, 0x0491, 0x11f0, 0x680c, 0xa08c, 0xff00, 0x6820, 0xa084,
-       0x00ff, 0xa115, 0x6212, 0x6824, 0x602a, 0xd1e4, 0x0118, 0x2009,
-       0x0001, 0x0060, 0xd1ec, 0x0168, 0x6920, 0xa18c, 0x00ff, 0x6824,
-       0x080c, 0x2676, 0x1130, 0x2110, 0x2009, 0x0000, 0x080c, 0x2b1e,
-       0x0018, 0xa085, 0x0001, 0x0008, 0xa006, 0x00de, 0x0005, 0x2069,
-       0xb28d, 0x6800, 0xa082, 0x0010, 0x1228, 0x6013, 0x0000, 0xa085,
-       0x0001, 0x0008, 0xa006, 0x0005, 0x6013, 0x0000, 0x2069, 0xb28c,
-       0x6808, 0xa084, 0xff00, 0xa086, 0x0800, 0x1140, 0x6800, 0xa084,
-       0x00ff, 0xa08e, 0x0014, 0x0110, 0xa08e, 0x0010, 0x0005, 0x6004,
-       0xa0b2, 0x0080, 0x1a0c, 0x14f6, 0xa1b6, 0x0013, 0x1130, 0x2008,
-       0xa1b2, 0x0040, 0x1a04, 0x9ffb, 0x0092, 0xa1b6, 0x0027, 0x0120,
-       0xa1b6, 0x0014, 0x190c, 0x14f6, 0x2001, 0x0007, 0x080c, 0x4c5d,
-       0x080c, 0x6b73, 0x080c, 0x974e, 0x080c, 0x6c50, 0x0005, 0x9f5f,
-       0x9f61, 0x9f5f, 0x9f5f, 0x9f5f, 0x9f61, 0x9f6f, 0x9ff4, 0x9fbf,
-       0x9ff4, 0x9fd0, 0x9ff4, 0x9f6f, 0x9ff4, 0x9fec, 0x9ff4, 0x9fec,
-       0x9ff4, 0x9ff4, 0x9f5f, 0x9f5f, 0x9f5f, 0x9f5f, 0x9f5f, 0x9f5f,
-       0x9f5f, 0x9f5f, 0x9f5f, 0x9f5f, 0x9f5f, 0x9f61, 0x9f5f, 0x9ff4,
-       0x9f5f, 0x9f5f, 0x9ff4, 0x9f5f, 0x9ff1, 0x9ff4, 0x9f5f, 0x9f5f,
-       0x9f5f, 0x9f5f, 0x9ff4, 0x9ff4, 0x9f5f, 0x9ff4, 0x9ff4, 0x9f5f,
-       0x9f69, 0x9f5f, 0x9f5f, 0x9f5f, 0x9f5f, 0x9ff0, 0x9ff4, 0x9f5f,
-       0x9f5f, 0x9ff4, 0x9ff4, 0x9f5f, 0x9f5f, 0x9f5f, 0x9f5f, 0x080c,
-       0x14f6, 0x080c, 0x6b73, 0x6003, 0x0002, 0x080c, 0x6c50, 0x0804,
-       0x9ffa, 0x2001, 0x0000, 0x080c, 0x4c1e, 0x0804, 0x9ff4, 0x00f6,
-       0x2079, 0xad51, 0x7804, 0x00fe, 0xd0ac, 0x1904, 0x9ff4, 0x2001,
-       0x0000, 0x080c, 0x4c1e, 0x6018, 0xa080, 0x0004, 0x2004, 0xa086,
-       0x00ff, 0x1140, 0x00f6, 0x2079, 0xad00, 0x7894, 0x8000, 0x7896,
-       0x00fe, 0x00e0, 0x00c6, 0x6018, 0x2060, 0x6000, 0xd0f4, 0x1140,
-       0x6010, 0xa005, 0x0128, 0x00ce, 0x080c, 0x3cce, 0x0804, 0x9ff4,
-       0x00ce, 0x2001, 0xad00, 0x2004, 0xa086, 0x0002, 0x1138, 0x00f6,
-       0x2079, 0xad00, 0x7894, 0x8000, 0x7896, 0x00fe, 0x2001, 0x0002,
-       0x080c, 0x4c30, 0x080c, 0x6b73, 0x601f, 0x0001, 0x6003, 0x0001,
-       0x6007, 0x0002, 0x080c, 0x67ee, 0x080c, 0x6c50, 0x00c6, 0x6118,
-       0x2160, 0x2009, 0x0001, 0x080c, 0x6519, 0x00ce, 0x04d8, 0x6618,
-       0x00d6, 0x2668, 0x6e04, 0x00de, 0xa6b4, 0xff00, 0x8637, 0xa686,
-       0x0006, 0x0550, 0xa686, 0x0004, 0x0538, 0x2001, 0x0004, 0x0410,
-       0x2001, 0xad00, 0x2004, 0xa086, 0x0003, 0x1110, 0x080c, 0x3cce,
-       0x2001, 0x0006, 0x0489, 0x6618, 0x00d6, 0x2668, 0x6e04, 0x00de,
-       0xa6b4, 0xff00, 0x8637, 0xa686, 0x0006, 0x0170, 0x2001, 0x0006,
-       0x0048, 0x2001, 0x0004, 0x0030, 0x2001, 0x0006, 0x00e9, 0x0020,
-       0x0018, 0x0010, 0x080c, 0x4c5d, 0x080c, 0x6b73, 0x080c, 0x8078,
-       0x080c, 0x6c50, 0x0005, 0x2600, 0x0002, 0xa003, 0xa003, 0xa003,
-       0xa003, 0xa003, 0xa005, 0x080c, 0x14f6, 0x080c, 0x6b73, 0x080c,
-       0x8078, 0x080c, 0x6c50, 0x0005, 0x0016, 0x00d6, 0x6118, 0x2168,
-       0x6900, 0xd184, 0x0188, 0x6104, 0xa18e, 0x000a, 0x1128, 0x699c,
-       0xd1a4, 0x1110, 0x2001, 0x0007, 0x080c, 0x4c30, 0x2001, 0x0000,
-       0x080c, 0x4c1e, 0x080c, 0x2aff, 0x00de, 0x001e, 0x0005, 0x00d6,
-       0x6618, 0x2668, 0x6804, 0xa084, 0xff00, 0x8007, 0x00de, 0xa0b2,
-       0x000c, 0x1a0c, 0x14f6, 0xa1b6, 0x0015, 0x1110, 0x003b, 0x0028,
-       0xa1b6, 0x0016, 0x190c, 0x14f6, 0x006b, 0x0005, 0x86b9, 0x86b9,
-       0x86b9, 0x86b9, 0x86b9, 0x86b9, 0xa08f, 0xa056, 0x86b9, 0x86b9,
-       0x86b9, 0x86b9, 0x86b9, 0x86b9, 0x86b9, 0x86b9, 0x86b9, 0x86b9,
-       0xa08f, 0xa096, 0x86b9, 0x86b9, 0x86b9, 0x86b9, 0x00f6, 0x2079,
-       0xad51, 0x7804, 0xd0ac, 0x11e0, 0x6018, 0xa07d, 0x01c8, 0x7800,
-       0xd0f4, 0x1118, 0x7810, 0xa005, 0x1198, 0x2001, 0x0000, 0x080c,
-       0x4c1e, 0x2001, 0x0002, 0x080c, 0x4c30, 0x601f, 0x0001, 0x6003,
-       0x0001, 0x6007, 0x0002, 0x080c, 0x67ee, 0x080c, 0x6c50, 0x00a8,
-       0x2011, 0xb283, 0x2204, 0x8211, 0x220c, 0x080c, 0x2676, 0x1168,
-       0x00c6, 0x080c, 0x4cdc, 0x0120, 0x00ce, 0x080c, 0x8078, 0x0028,
-       0x080c, 0x493a, 0x00ce, 0x080c, 0x8078, 0x00fe, 0x0005, 0x6604,
-       0xa6b6, 0x001e, 0x1110, 0x080c, 0x8078, 0x0005, 0x080c, 0x8940,
-       0x1138, 0x6003, 0x0001, 0x6007, 0x0001, 0x080c, 0x67ee, 0x0010,
-       0x080c, 0x8078, 0x0005, 0x6004, 0xa08a, 0x0080, 0x1a0c, 0x14f6,
-       0x080c, 0x6b73, 0x080c, 0x974e, 0x080c, 0x6c50, 0x0005, 0xa182,
-       0x0040, 0x0002, 0xa0c5, 0xa0c5, 0xa0c5, 0xa0c5, 0xa0c7, 0xa0c5,
-       0xa0c5, 0xa0c5, 0xa0c5, 0xa0c5, 0xa0c5, 0xa0c5, 0xa0c5, 0xa0c5,
-       0xa0c5, 0xa0c5, 0xa0c5, 0xa0c5, 0xa0c5, 0x080c, 0x14f6, 0x00d6,
-       0x00e6, 0x00f6, 0x0156, 0x0046, 0x0026, 0x6218, 0xa280, 0x002b,
-       0x2004, 0xa005, 0x0120, 0x2021, 0x0000, 0x080c, 0xab96, 0x6106,
-       0x2071, 0xb280, 0x7444, 0xa4a4, 0xff00, 0x0904, 0xa129, 0xa486,
-       0x2000, 0x1130, 0x2009, 0x0001, 0x2011, 0x0200, 0x080c, 0x663f,
-       0x080c, 0x15d9, 0x090c, 0x14f6, 0x6003, 0x0007, 0x2d00, 0x6837,
-       0x010d, 0x6803, 0x0000, 0x683b, 0x0000, 0x6c5a, 0x2c00, 0x685e,
-       0x6008, 0x68b2, 0x6018, 0x2078, 0x78a0, 0x8007, 0x7130, 0x694a,
-       0x0016, 0xa084, 0xff00, 0x6846, 0x684f, 0x0000, 0x6857, 0x0036,
-       0x080c, 0x510c, 0x001e, 0xa486, 0x2000, 0x1130, 0x2019, 0x0017,
-       0x080c, 0xa8eb, 0x0804, 0xa186, 0xa486, 0x0400, 0x1130, 0x2019,
-       0x0002, 0x080c, 0xa89d, 0x0804, 0xa186, 0xa486, 0x0200, 0x1110,
-       0x080c, 0xa882, 0xa486, 0x1000, 0x1110, 0x080c, 0xa8d0, 0x0804,
-       0xa186, 0x2069, 0xb048, 0x6a00, 0xd284, 0x0904, 0xa1d5, 0xa284,
-       0x0300, 0x1904, 0xa1cf, 0x6804, 0xa005, 0x0904, 0xa1c0, 0x2d78,
-       0x6003, 0x0007, 0x080c, 0x15c0, 0x0904, 0xa18d, 0x7800, 0xd08c,
-       0x1118, 0x7804, 0x8001, 0x7806, 0x6013, 0x0000, 0x6803, 0x0000,
-       0x6837, 0x0116, 0x683b, 0x0000, 0x6008, 0x68b2, 0x2c00, 0x684a,
-       0x6018, 0x2078, 0x78a0, 0x8007, 0x7130, 0x6986, 0x6846, 0x7928,
-       0x698a, 0x792c, 0x698e, 0x7930, 0x6992, 0x7934, 0x6996, 0x6853,
-       0x003d, 0x7244, 0xa294, 0x0003, 0xa286, 0x0002, 0x1118, 0x684f,
-       0x0040, 0x0040, 0xa286, 0x0001, 0x1118, 0x684f, 0x0080, 0x0010,
-       0x684f, 0x0000, 0x20a9, 0x000a, 0x2001, 0xb290, 0xad90, 0x0015,
-       0x200c, 0x810f, 0x2112, 0x8000, 0x8210, 0x1f04, 0xa178, 0x200c,
-       0x6982, 0x8000, 0x200c, 0x697e, 0x080c, 0x510c, 0x002e, 0x004e,
-       0x015e, 0x00fe, 0x00ee, 0x00de, 0x0005, 0x6013, 0x0100, 0x6003,
-       0x0001, 0x6007, 0x0041, 0x080c, 0x67a8, 0x080c, 0x6c50, 0x0c70,
-       0x2069, 0xb292, 0x2d04, 0xa084, 0xff00, 0xa086, 0x1200, 0x11a8,
-       0x2069, 0xb280, 0x686c, 0xa084, 0x00ff, 0x0016, 0x6110, 0xa18c,
-       0x0700, 0xa10d, 0x6112, 0x001e, 0x6003, 0x0001, 0x6007, 0x0043,
-       0x080c, 0x67a8, 0x080c, 0x6c50, 0x0888, 0x6013, 0x0200, 0x6003,
-       0x0001, 0x6007, 0x0041, 0x080c, 0x67a8, 0x080c, 0x6c50, 0x0830,
-       0x6013, 0x0300, 0x0010, 0x6013, 0x0100, 0x6003, 0x0001, 0x6007,
-       0x0041, 0x080c, 0x67a8, 0x080c, 0x6c50, 0x0804, 0xa186, 0x6013,
-       0x0500, 0x0c98, 0x6013, 0x0600, 0x0818, 0x6013, 0x0200, 0x0800,
-       0xa186, 0x0013, 0x1170, 0x6004, 0xa08a, 0x0040, 0x0a0c, 0x14f6,
-       0xa08a, 0x0053, 0x1a0c, 0x14f6, 0xa082, 0x0040, 0x2008, 0x0804,
-       0xa252, 0xa186, 0x0051, 0x0138, 0xa186, 0x0047, 0x11d8, 0x6004,
-       0xa086, 0x0041, 0x0518, 0x2001, 0x0109, 0x2004, 0xd084, 0x01f0,
-       0x0126, 0x2091, 0x2800, 0x0006, 0x0016, 0x0026, 0x080c, 0x6699,
-       0x002e, 0x001e, 0x000e, 0x012e, 0x6000, 0xa086, 0x0002, 0x1170,
-       0x0804, 0xa295, 0xa186, 0x0027, 0x0120, 0xa186, 0x0014, 0x190c,
-       0x14f6, 0x6004, 0xa082, 0x0040, 0x2008, 0x001a, 0x080c, 0x80be,
-       0x0005, 0xa22c, 0xa22e, 0xa22e, 0xa22c, 0xa22c, 0xa22c, 0xa22c,
-       0xa22c, 0xa22c, 0xa22c, 0xa22c, 0xa22c, 0xa22c, 0xa22c, 0xa22c,
-       0xa22c, 0xa22c, 0xa22c, 0xa22c, 0x080c, 0x14f6, 0x080c, 0x6b73,
-       0x080c, 0x6c50, 0x0036, 0x00d6, 0x6010, 0xa06d, 0x01c0, 0xad84,
-       0xf000, 0x01a8, 0x6003, 0x0002, 0x6018, 0x2004, 0xd0bc, 0x1178,
-       0x2019, 0x0004, 0x080c, 0xa91f, 0x6013, 0x0000, 0x6014, 0xa005,
-       0x1120, 0x2001, 0xafa4, 0x2004, 0x6016, 0x6003, 0x0007, 0x00de,
-       0x003e, 0x0005, 0x0002, 0xa266, 0xa283, 0xa26f, 0xa28f, 0xa266,
-       0xa266, 0xa266, 0xa266, 0xa266, 0xa266, 0xa266, 0xa266, 0xa266,
-       0xa266, 0xa266, 0xa266, 0xa266, 0xa266, 0xa266, 0x080c, 0x14f6,
-       0x6010, 0xa088, 0x0013, 0x2104, 0xa085, 0x0400, 0x200a, 0x080c,
-       0x6b73, 0x6010, 0xa080, 0x0013, 0x2004, 0xd0b4, 0x0138, 0x6003,
-       0x0007, 0x2009, 0x0043, 0x080c, 0x80a7, 0x0010, 0x6003, 0x0002,
-       0x080c, 0x6c50, 0x0005, 0x080c, 0x6b73, 0x080c, 0xab55, 0x1120,
-       0x080c, 0x6618, 0x080c, 0x8078, 0x080c, 0x6c50, 0x0005, 0x080c,
-       0x6b73, 0x2009, 0x0041, 0x0804, 0xa3de, 0xa182, 0x0040, 0x0002,
-       0xa2ab, 0xa2ad, 0xa2ab, 0xa2ab, 0xa2ab, 0xa2ab, 0xa2ab, 0xa2ae,
-       0xa2ab, 0xa2ab, 0xa2ab, 0xa2ab, 0xa2ab, 0xa2ab, 0xa2ab, 0xa2ab,
-       0xa2ab, 0xa2b9, 0xa2ab, 0x080c, 0x14f6, 0x0005, 0x6003, 0x0004,
-       0x6110, 0x20e1, 0x0005, 0x3d18, 0x3e20, 0x2c10, 0x080c, 0x1824,
-       0x0005, 0x00d6, 0x080c, 0x6618, 0x00de, 0x080c, 0xabb4, 0x080c,
-       0x8078, 0x0005, 0xa182, 0x0040, 0x0002, 0xa2d8, 0xa2d8, 0xa2d8,
-       0xa2d8, 0xa2d8, 0xa2d8, 0xa2d8, 0xa2da, 0xa2d8, 0xa2dd, 0xa316,
-       0xa2d8, 0xa2d8, 0xa2d8, 0xa2d8, 0xa316, 0xa2d8, 0xa2d8, 0xa2d8,
-       0x080c, 0x14f6, 0x080c, 0x80be, 0x0005, 0x2001, 0xad71, 0x2004,
-       0xd0e4, 0x0158, 0x2001, 0x0100, 0x2004, 0xa082, 0x0005, 0x0228,
-       0x2001, 0x011f, 0x2004, 0x6036, 0x0010, 0x6037, 0x0000, 0x080c,
-       0x6c05, 0x080c, 0x6d0d, 0x6010, 0x00d6, 0x2068, 0x684c, 0xd0fc,
-       0x0150, 0xa08c, 0x0003, 0xa18e, 0x0002, 0x0168, 0x2009, 0x0041,
-       0x00de, 0x0804, 0xa3de, 0x6003, 0x0007, 0x6017, 0x0000, 0x080c,
-       0x6618, 0x00de, 0x0005, 0x080c, 0xab55, 0x0110, 0x00de, 0x0005,
-       0x080c, 0x6618, 0x080c, 0x8078, 0x00de, 0x0ca0, 0x0036, 0x080c,
-       0x6c05, 0x080c, 0x6d0d, 0x6010, 0x00d6, 0x2068, 0x6018, 0x2004,
-       0xd0bc, 0x0188, 0x684c, 0xa084, 0x0003, 0xa086, 0x0002, 0x0140,
-       0x687c, 0x632c, 0xa31a, 0x632e, 0x6880, 0x6328, 0xa31b, 0x632a,
-       0x6003, 0x0002, 0x0080, 0x2019, 0x0004, 0x080c, 0xa91f, 0x6014,
-       0xa005, 0x1128, 0x2001, 0xafa4, 0x2004, 0x8003, 0x6016, 0x6013,
-       0x0000, 0x6003, 0x0007, 0x00de, 0x003e, 0x0005, 0xa186, 0x0013,
-       0x1150, 0x6004, 0xa086, 0x0042, 0x190c, 0x14f6, 0x080c, 0x6b73,
-       0x080c, 0x6c50, 0x0005, 0xa186, 0x0027, 0x0118, 0xa186, 0x0014,
-       0x1180, 0x6004, 0xa086, 0x0042, 0x190c, 0x14f6, 0x2001, 0x0007,
-       0x080c, 0x4c5d, 0x080c, 0x6b73, 0x080c, 0x974e, 0x080c, 0x6c50,
-       0x0005, 0xa182, 0x0040, 0x0002, 0xa37f, 0xa37f, 0xa37f, 0xa37f,
-       0xa37f, 0xa37f, 0xa37f, 0xa381, 0xa38d, 0xa37f, 0xa37f, 0xa37f,
-       0xa37f, 0xa37f, 0xa37f, 0xa37f, 0xa37f, 0xa37f, 0xa37f, 0x080c,
-       0x14f6, 0x0036, 0x0046, 0x20e1, 0x0005, 0x3d18, 0x3e20, 0x2c10,
-       0x080c, 0x1824, 0x004e, 0x003e, 0x0005, 0x6010, 0x00d6, 0x2068,
-       0x6810, 0x6a14, 0x0006, 0x0046, 0x0056, 0x6c7c, 0xa422, 0x6d80,
-       0x2200, 0xa52b, 0x602c, 0xa420, 0x642e, 0x6028, 0xa529, 0x652a,
-       0x005e, 0x004e, 0x000e, 0xa20d, 0x1178, 0x684c, 0xd0fc, 0x0120,
-       0x2009, 0x0041, 0x00de, 0x0490, 0x6003, 0x0007, 0x6017, 0x0000,
-       0x080c, 0x6618, 0x00de, 0x0005, 0x0006, 0x00f6, 0x2c78, 0x080c,
-       0x5029, 0x00fe, 0x000e, 0x0120, 0x6003, 0x0002, 0x00de, 0x0005,
-       0x2009, 0xad0d, 0x210c, 0xd19c, 0x0118, 0x6003, 0x0007, 0x0010,
-       0x6003, 0x0006, 0x0021, 0x080c, 0x661a, 0x00de, 0x0005, 0xd2fc,
-       0x0140, 0x8002, 0x8000, 0x8212, 0xa291, 0x0000, 0x2009, 0x0009,
-       0x0010, 0x2009, 0x0015, 0x6a6a, 0x6866, 0x0005, 0xa182, 0x0040,
-       0x0208, 0x0062, 0xa186, 0x0013, 0x0120, 0xa186, 0x0014, 0x190c,
-       0x14f6, 0x6020, 0xd0dc, 0x090c, 0x14f6, 0x0005, 0xa401, 0xa408,
-       0xa414, 0xa420, 0xa401, 0xa401, 0xa401, 0xa42f, 0xa401, 0xa403,
-       0xa403, 0xa401, 0xa401, 0xa401, 0xa401, 0xa403, 0xa401, 0xa403,
-       0xa401, 0x080c, 0x14f6, 0x6020, 0xd0dc, 0x090c, 0x14f6, 0x0005,
-       0x6003, 0x0001, 0x6106, 0x080c, 0x67a8, 0x0126, 0x2091, 0x8000,
-       0x080c, 0x6c50, 0x012e, 0x0005, 0x6003, 0x0001, 0x6106, 0x080c,
-       0x67a8, 0x0126, 0x2091, 0x8000, 0x080c, 0x6c50, 0x012e, 0x0005,
-       0x6003, 0x0003, 0x6106, 0x2c10, 0x080c, 0x1e6e, 0x0126, 0x2091,
-       0x8000, 0x080c, 0x680b, 0x080c, 0x6d0d, 0x012e, 0x0005, 0xa016,
-       0x080c, 0x1824, 0x0005, 0x0126, 0x2091, 0x8000, 0x0036, 0x00d6,
-       0xa182, 0x0040, 0x0023, 0x00de, 0x003e, 0x012e, 0x0005, 0xa44f,
-       0xa451, 0xa463, 0xa47e, 0xa44f, 0xa44f, 0xa44f, 0xa493, 0xa44f,
-       0xa44f, 0xa44f, 0xa44f, 0xa44f, 0xa44f, 0xa44f, 0xa44f, 0x080c,
-       0x14f6, 0x6010, 0x2068, 0x684c, 0xd0fc, 0x01f8, 0xa09c, 0x0003,
-       0xa39e, 0x0003, 0x01d0, 0x6003, 0x0001, 0x6106, 0x080c, 0x67a8,
-       0x080c, 0x6c50, 0x0498, 0x6010, 0x2068, 0x684c, 0xd0fc, 0x0168,
-       0xa09c, 0x0003, 0xa39e, 0x0003, 0x0140, 0x6003, 0x0001, 0x6106,
-       0x080c, 0x67a8, 0x080c, 0x6c50, 0x0408, 0x6013, 0x0000, 0x6017,
-       0x0000, 0x2019, 0x0004, 0x080c, 0xa91f, 0x00c0, 0x6010, 0x2068,
-       0x684c, 0xd0fc, 0x0d90, 0xa09c, 0x0003, 0xa39e, 0x0003, 0x0d68,
-       0x6003, 0x0003, 0x6106, 0x2c10, 0x080c, 0x1e6e, 0x080c, 0x680b,
-       0x080c, 0x6d0d, 0x0018, 0xa016, 0x080c, 0x1824, 0x0005, 0x080c,
-       0x6b73, 0x6110, 0x81ff, 0x0158, 0x00d6, 0x2168, 0x080c, 0xabfa,
-       0x0036, 0x2019, 0x0029, 0x080c, 0xa91f, 0x003e, 0x00de, 0x080c,
-       0x974e, 0x080c, 0x6c50, 0x0005, 0x080c, 0x6c05, 0x6110, 0x81ff,
-       0x0158, 0x00d6, 0x2168, 0x080c, 0xabfa, 0x0036, 0x2019, 0x0029,
-       0x080c, 0xa91f, 0x003e, 0x00de, 0x080c, 0x974e, 0x080c, 0x6d0d,
-       0x0005, 0xa182, 0x0085, 0x0002, 0xa4cd, 0xa4cb, 0xa4cb, 0xa4d9,
-       0xa4cb, 0xa4cb, 0xa4cb, 0x080c, 0x14f6, 0x6003, 0x000b, 0x6106,
-       0x080c, 0x67a8, 0x0126, 0x2091, 0x8000, 0x080c, 0x6c50, 0x012e,
-       0x0005, 0x0026, 0x00e6, 0x080c, 0xab4e, 0x0118, 0x080c, 0x8078,
-       0x00c8, 0x2071, 0xb280, 0x7224, 0x6212, 0x7220, 0x080c, 0xa7ce,
-       0x0118, 0x6007, 0x0086, 0x0040, 0x6007, 0x0087, 0x7224, 0xa296,
-       0xffff, 0x1110, 0x6007, 0x0086, 0x6003, 0x0001, 0x080c, 0x67a8,
-       0x080c, 0x6c50, 0x00ee, 0x002e, 0x0005, 0xa186, 0x0013, 0x1160,
-       0x6004, 0xa08a, 0x0085, 0x0a0c, 0x14f6, 0xa08a, 0x008c, 0x1a0c,
-       0x14f6, 0xa082, 0x0085, 0x00a2, 0xa186, 0x0027, 0x0130, 0xa186,
-       0x0014, 0x0118, 0x080c, 0x80be, 0x0050, 0x2001, 0x0007, 0x080c,
-       0x4c5d, 0x080c, 0x6b73, 0x080c, 0x974e, 0x080c, 0x6c50, 0x0005,
-       0xa527, 0xa529, 0xa529, 0xa527, 0xa527, 0xa527, 0xa527, 0x080c,
-       0x14f6, 0x080c, 0x6b73, 0x080c, 0x974e, 0x080c, 0x6c50, 0x0005,
-       0xa182, 0x0085, 0x0a0c, 0x14f6, 0xa182, 0x008c, 0x1a0c, 0x14f6,
-       0xa182, 0x0085, 0x0002, 0xa542, 0xa542, 0xa542, 0xa544, 0xa542,
-       0xa542, 0xa542, 0x080c, 0x14f6, 0x0005, 0xa186, 0x0013, 0x0148,
-       0xa186, 0x0014, 0x0130, 0xa186, 0x0027, 0x0118, 0x080c, 0x80be,
-       0x0030, 0x080c, 0x6b73, 0x080c, 0x974e, 0x080c, 0x6c50, 0x0005,
-       0x0036, 0x080c, 0xabb4, 0x603f, 0x0000, 0x2019, 0x000b, 0x0031,
-       0x601f, 0x0006, 0x6003, 0x0007, 0x003e, 0x0005, 0x0126, 0x0036,
-       0x2091, 0x8000, 0x0086, 0x2c40, 0x0096, 0x2049, 0x0000, 0x080c,
-       0x7b9a, 0x009e, 0x008e, 0x1578, 0x0076, 0x2c38, 0x080c, 0x7c34,
-       0x007e, 0x1548, 0x6000, 0xa086, 0x0000, 0x0528, 0x601c, 0xa086,
-       0x0007, 0x0508, 0x00d6, 0x6000, 0xa086, 0x0004, 0x1150, 0x080c,
-       0xabb4, 0x601f, 0x0007, 0x2001, 0xafa3, 0x2004, 0x6016, 0x080c,
-       0x190b, 0x6010, 0x2068, 0x080c, 0x9596, 0x0110, 0x080c, 0xa91f,
-       0x00de, 0x6013, 0x0000, 0x080c, 0xabb4, 0x601f, 0x0007, 0x2001,
-       0xafa3, 0x2004, 0x6016, 0x003e, 0x012e, 0x0005, 0x00f6, 0x00c6,
-       0x0036, 0x0156, 0x2079, 0xb280, 0x7938, 0x783c, 0x080c, 0x2676,
-       0x1904, 0xa5f1, 0x0016, 0x00c6, 0x080c, 0x4cdc, 0x15c0, 0x2011,
-       0xb290, 0xac98, 0x000a, 0x20a9, 0x0004, 0x080c, 0x8a7c, 0x1578,
-       0x001e, 0x002e, 0x0026, 0x0016, 0x2019, 0x0029, 0x080c, 0x7cf4,
-       0x080c, 0x68e7, 0x0076, 0x2039, 0x0000, 0x080c, 0x681d, 0x007e,
-       0x001e, 0x0076, 0x2039, 0x0000, 0x080c, 0xa712, 0x007e, 0x080c,
-       0x4ecf, 0x0026, 0x6204, 0xa294, 0xff00, 0x8217, 0xa286, 0x0006,
-       0x0118, 0xa286, 0x0004, 0x1118, 0x62a0, 0x080c, 0x2b87, 0x002e,
-       0x001e, 0x080c, 0x493a, 0x6612, 0x6516, 0xa006, 0x0010, 0x00ce,
-       0x001e, 0x015e, 0x003e, 0x00ce, 0x00fe, 0x0005, 0x00c6, 0x00d6,
-       0x00e6, 0x0016, 0x2009, 0xad20, 0x2104, 0xa086, 0x0074, 0x1904,
-       0xa64b, 0x2069, 0xb28e, 0x690c, 0xa182, 0x0100, 0x06c0, 0x6908,
-       0xa184, 0x8000, 0x05e8, 0x2001, 0xaf9d, 0x2004, 0xa005, 0x1160,
-       0x6018, 0x2070, 0x7010, 0xa084, 0x00ff, 0x0118, 0x7000, 0xd0f4,
-       0x0118, 0xa184, 0x0800, 0x0560, 0x6910, 0xa18a, 0x0001, 0x0610,
-       0x6914, 0x2069, 0xb2ae, 0x6904, 0x81ff, 0x1198, 0x690c, 0xa182,
-       0x0100, 0x02a8, 0x6908, 0x81ff, 0x1178, 0x6910, 0xa18a, 0x0001,
-       0x0288, 0x6918, 0xa18a, 0x0001, 0x0298, 0x00d0, 0x6013, 0x0100,
-       0x00a0, 0x6013, 0x0300, 0x0088, 0x6013, 0x0500, 0x0070, 0x6013,
-       0x0700, 0x0058, 0x6013, 0x0900, 0x0040, 0x6013, 0x0b00, 0x0028,
-       0x6013, 0x0f00, 0x0010, 0x6013, 0x2d00, 0xa085, 0x0001, 0x0008,
-       0xa006, 0x001e, 0x00ee, 0x00de, 0x00ce, 0x0005, 0x00c6, 0x00d6,
-       0x0026, 0x0036, 0x0156, 0x6218, 0x2268, 0x6b04, 0xa394, 0x00ff,
-       0xa286, 0x0006, 0x0190, 0xa286, 0x0004, 0x0178, 0xa394, 0xff00,
-       0x8217, 0xa286, 0x0006, 0x0148, 0xa286, 0x0004, 0x0130, 0x00c6,
-       0x2d60, 0x080c, 0x4ceb, 0x00ce, 0x04c0, 0x2011, 0xb296, 0xad98,
-       0x000a, 0x20a9, 0x0004, 0x080c, 0x8a7c, 0x1580, 0x2011, 0xb29a,
-       0xad98, 0x0006, 0x20a9, 0x0004, 0x080c, 0x8a7c, 0x1538, 0x0046,
-       0x0016, 0x6aa0, 0xa294, 0x00ff, 0x8227, 0xa006, 0x2009, 0xad52,
-       0x210c, 0xd1a4, 0x0138, 0x2009, 0x0029, 0x080c, 0xa96c, 0x6800,
-       0xc0e5, 0x6802, 0x2019, 0x0029, 0x080c, 0x68e7, 0x0076, 0x2039,
-       0x0000, 0x080c, 0x681d, 0x2c08, 0x080c, 0xa712, 0x007e, 0x2001,
-       0x0007, 0x080c, 0x4c5d, 0x001e, 0x004e, 0xa006, 0x015e, 0x003e,
-       0x002e, 0x00de, 0x00ce, 0x0005, 0x00d6, 0x2069, 0xb28e, 0x6800,
-       0xa086, 0x0800, 0x0118, 0x6013, 0x0000, 0x0008, 0xa006, 0x00de,
-       0x0005, 0x00c6, 0x00f6, 0x0016, 0x0026, 0x0036, 0x0156, 0x2079,
-       0xb28c, 0x7930, 0x7834, 0x080c, 0x2676, 0x11a0, 0x080c, 0x4cdc,
-       0x1188, 0x2011, 0xb290, 0xac98, 0x000a, 0x20a9, 0x0004, 0x080c,
-       0x8a7c, 0x1140, 0x2011, 0xb294, 0xac98, 0x0006, 0x20a9, 0x0004,
-       0x080c, 0x8a7c, 0x015e, 0x003e, 0x002e, 0x001e, 0x00fe, 0x00ce,
-       0x0005, 0x00c6, 0x0006, 0x0016, 0x0026, 0x0036, 0x0156, 0x2011,
-       0xb283, 0x2204, 0x8211, 0x220c, 0x080c, 0x2676, 0x11a0, 0x080c,
-       0x4cdc, 0x1188, 0x2011, 0xb296, 0xac98, 0x000a, 0x20a9, 0x0004,
-       0x080c, 0x8a7c, 0x1140, 0x2011, 0xb29a, 0xac98, 0x0006, 0x20a9,
-       0x0004, 0x080c, 0x8a7c, 0x015e, 0x003e, 0x002e, 0x001e, 0x000e,
-       0x00ce, 0x0005, 0x00e6, 0x00c6, 0x0086, 0x0076, 0x0066, 0x0056,
-       0x0046, 0x0026, 0x0126, 0x2091, 0x8000, 0x2740, 0x2029, 0xafd0,
-       0x252c, 0x2021, 0xafd6, 0x2424, 0x2061, 0xb400, 0x2071, 0xad00,
-       0x7644, 0x7064, 0x81ff, 0x0128, 0x8001, 0xa602, 0x1a04, 0xa78e,
-       0x0018, 0xa606, 0x0904, 0xa78e, 0x2100, 0xac06, 0x0904, 0xa785,
-       0x080c, 0xa990, 0x0904, 0xa785, 0x671c, 0xa786, 0x0001, 0x0904,
-       0xa7a5, 0xa786, 0x0004, 0x0904, 0xa7a5, 0xa786, 0x0007, 0x05e8,
-       0x2500, 0xac06, 0x05d0, 0x2400, 0xac06, 0x05b8, 0x080c, 0xa9a0,
-       0x15a0, 0x88ff, 0x0118, 0x6050, 0xa906, 0x1578, 0x00d6, 0x6000,
-       0xa086, 0x0004, 0x1120, 0x0016, 0x080c, 0x190b, 0x001e, 0xa786,
-       0x0008, 0x1148, 0x080c, 0x9789, 0x1130, 0x080c, 0x85f3, 0x00de,
-       0x080c, 0x974e, 0x00d0, 0x6010, 0x2068, 0x080c, 0x9596, 0x0190,
-       0xa786, 0x0003, 0x1528, 0x6837, 0x0103, 0x6b4a, 0x6847, 0x0000,
-       0x080c, 0xabfa, 0x0016, 0x080c, 0x97fd, 0x080c, 0x510c, 0x001e,
-       0x080c, 0x9742, 0x00de, 0x080c, 0x974e, 0xace0, 0x0018, 0x2001,
-       0xad16, 0x2004, 0xac02, 0x1210, 0x0804, 0xa726, 0x012e, 0x002e,
-       0x004e, 0x005e, 0x006e, 0x007e, 0x008e, 0x00ce, 0x00ee, 0x0005,
-       0xa786, 0x0006, 0x19c0, 0xa386, 0x0005, 0x0128, 0x080c, 0xabfa,
-       0x080c, 0xa91f, 0x08f8, 0x00de, 0x0c00, 0x080c, 0xa9a0, 0x19e8,
-       0x81ff, 0x09d8, 0xa180, 0x0001, 0x2004, 0xa086, 0x0018, 0x0130,
-       0xa180, 0x0001, 0x2004, 0xa086, 0x002d, 0x1978, 0x6000, 0xa086,
-       0x0002, 0x1958, 0x080c, 0x9778, 0x0130, 0x080c, 0x9789, 0x1928,
-       0x080c, 0x85f3, 0x0038, 0x080c, 0x2aff, 0x080c, 0x9789, 0x1110,
-       0x080c, 0x85f3, 0x080c, 0x974e, 0x0804, 0xa785, 0x00c6, 0x00e6,
-       0x0016, 0x2c08, 0x2170, 0x080c, 0xa940, 0x001e, 0x0120, 0x601c,
-       0xa084, 0x000f, 0x001b, 0x00ee, 0x00ce, 0x0005, 0xa7e6, 0xa7e6,
-       0xa7e6, 0xa7e6, 0xa7e6, 0xa7e6, 0xa7e8, 0xa7e6, 0xa006, 0x0005,
-       0x0046, 0x0016, 0x7018, 0xa080, 0x0028, 0x2024, 0xa4a4, 0x00ff,
-       0x8427, 0x2c00, 0x2009, 0x0020, 0x080c, 0xa96c, 0x001e, 0x004e,
-       0x0036, 0x2019, 0x0002, 0x080c, 0xa566, 0x003e, 0xa085, 0x0001,
-       0x0005, 0x2001, 0x0001, 0x080c, 0x4c1e, 0x0156, 0x0016, 0x0026,
-       0x0036, 0x20a9, 0x0004, 0x2019, 0xad05, 0x2011, 0xb296, 0x080c,
-       0x8a7c, 0x003e, 0x002e, 0x001e, 0x015e, 0xa005, 0x0005, 0x00f6,
-       0x00e6, 0x00c6, 0x0086, 0x0076, 0x0066, 0x0026, 0x0126, 0x2091,
-       0x8000, 0x2740, 0x2061, 0xb400, 0x2079, 0x0001, 0x8fff, 0x0904,
-       0xa875, 0x2071, 0xad00, 0x7644, 0x7064, 0x8001, 0xa602, 0x1a04,
-       0xa875, 0x88ff, 0x0128, 0x2800, 0xac06, 0x15b0, 0x2079, 0x0000,
-       0x080c, 0xa990, 0x0588, 0x2400, 0xac06, 0x0570, 0x671c, 0xa786,
-       0x0006, 0x1550, 0xa786, 0x0007, 0x0538, 0x88ff, 0x1140, 0x6018,
-       0xa206, 0x1510, 0x85ff, 0x0118, 0x6050, 0xa106, 0x11e8, 0x00d6,
-       0x6000, 0xa086, 0x0004, 0x1150, 0x080c, 0xabb4, 0x601f, 0x0007,
-       0x2001, 0xafa3, 0x2004, 0x6016, 0x080c, 0x190b, 0x6010, 0x2068,
-       0x080c, 0x9596, 0x0120, 0x0046, 0x080c, 0xa91f, 0x004e, 0x00de,
-       0x080c, 0x974e, 0x88ff, 0x1198, 0xace0, 0x0018, 0x2001, 0xad16,
-       0x2004, 0xac02, 0x1210, 0x0804, 0xa826, 0xa006, 0x012e, 0x002e,
-       0x006e, 0x007e, 0x008e, 0x00ce, 0x00ee, 0x00fe, 0x0005, 0xa8c5,
-       0x0001, 0x0ca0, 0x0076, 0x0056, 0x0086, 0x2041, 0x0000, 0x2029,
-       0x0001, 0x2c20, 0x2019, 0x0002, 0x6218, 0x0096, 0x2049, 0x0000,
-       0x080c, 0x7b9a, 0x009e, 0x008e, 0x2039, 0x0000, 0x080c, 0x7c34,
-       0x080c, 0xa817, 0x005e, 0x007e, 0x0005, 0x0026, 0x0046, 0x0056,
-       0x0076, 0x00c6, 0x0156, 0x2c20, 0x2128, 0x20a9, 0x007f, 0x2009,
-       0x0000, 0x0016, 0x0036, 0x080c, 0x4cdc, 0x11b0, 0x2c10, 0x0056,
-       0x0086, 0x2041, 0x0000, 0x2508, 0x2029, 0x0001, 0x0096, 0x2049,
-       0x0000, 0x080c, 0x7b9a, 0x009e, 0x008e, 0x2039, 0x0000, 0x080c,
-       0x7c34, 0x080c, 0xa817, 0x005e, 0x003e, 0x001e, 0x8108, 0x1f04,
-       0xa8a9, 0x015e, 0x00ce, 0x007e, 0x005e, 0x004e, 0x002e, 0x0005,
-       0x0076, 0x0056, 0x6218, 0x0086, 0x2041, 0x0000, 0x2029, 0x0001,
-       0x2019, 0x0048, 0x0096, 0x2049, 0x0000, 0x080c, 0x7b9a, 0x009e,
-       0x008e, 0x2039, 0x0000, 0x080c, 0x7c34, 0x2c20, 0x080c, 0xa817,
-       0x005e, 0x007e, 0x0005, 0x0026, 0x0046, 0x0056, 0x0076, 0x00c6,
-       0x0156, 0x2c20, 0x20a9, 0x007f, 0x2009, 0x0000, 0x0016, 0x0036,
-       0x080c, 0x4cdc, 0x11c0, 0x2c10, 0x0086, 0x2041, 0x0000, 0x2828,
-       0x0046, 0x2021, 0x0001, 0x080c, 0xab96, 0x004e, 0x0096, 0x2049,
-       0x0000, 0x080c, 0x7b9a, 0x009e, 0x008e, 0x2039, 0x0000, 0x080c,
-       0x7c34, 0x080c, 0xa817, 0x003e, 0x001e, 0x8108, 0x1f04, 0xa8f6,
-       0x015e, 0x00ce, 0x007e, 0x005e, 0x004e, 0x002e, 0x0005, 0x0016,
-       0x00f6, 0x3800, 0xd08c, 0x0130, 0xad82, 0x1000, 0x02b0, 0xad82,
-       0xad00, 0x0230, 0xad82, 0xe400, 0x0280, 0xad82, 0xffff, 0x1268,
-       0x6800, 0xa07d, 0x0138, 0x6803, 0x0000, 0x6b52, 0x080c, 0x510c,
-       0x2f68, 0x0cb0, 0x6b52, 0x080c, 0x510c, 0x00fe, 0x001e, 0x0005,
-       0x00e6, 0x0046, 0x0036, 0x2061, 0xb400, 0x2071, 0xad00, 0x7444,
-       0x7064, 0x8001, 0xa402, 0x12d8, 0x2100, 0xac06, 0x0168, 0x6000,
-       0xa086, 0x0000, 0x0148, 0x6008, 0xa206, 0x1130, 0x6018, 0xa1a0,
-       0x0006, 0x2424, 0xa406, 0x0140, 0xace0, 0x0018, 0x2001, 0xad16,
-       0x2004, 0xac02, 0x1220, 0x0c08, 0xa085, 0x0001, 0x0008, 0xa006,
-       0x003e, 0x004e, 0x00ee, 0x0005, 0x00d6, 0x0006, 0x080c, 0x15d9,
-       0x000e, 0x090c, 0x14f6, 0x6837, 0x010d, 0x685e, 0x0026, 0x2010,
-       0x080c, 0x9586, 0x2001, 0x0000, 0x0120, 0x2200, 0xa080, 0x0014,
-       0x2004, 0x002e, 0x684a, 0x6956, 0x6c46, 0x684f, 0x0000, 0xa006,
-       0x68b2, 0x6802, 0x683a, 0x685a, 0x080c, 0x510c, 0x00de, 0x0005,
-       0x6700, 0xa786, 0x0000, 0x0158, 0xa786, 0x0001, 0x0140, 0xa786,
-       0x000a, 0x0128, 0xa786, 0x0009, 0x0110, 0xa085, 0x0001, 0x0005,
-       0x00e6, 0x6018, 0x2070, 0x70a0, 0xa206, 0x00ee, 0x0005, 0x0016,
-       0x6004, 0xa08e, 0x001e, 0x11a0, 0x8007, 0x6130, 0xa18c, 0x00ff,
-       0xa105, 0x6032, 0x6007, 0x0085, 0x6003, 0x000b, 0x601f, 0x0005,
-       0x2001, 0xafa4, 0x2004, 0x6016, 0x080c, 0x67a8, 0x080c, 0x6c50,
-       0x001e, 0x0005, 0xe000, 0xe000, 0x0005, 0x6020, 0xd0e4, 0x0158,
-       0xd0cc, 0x0118, 0x080c, 0x9866, 0x0030, 0x080c, 0xabb4, 0x080c,
-       0x6618, 0x080c, 0x8078, 0x0005, 0xa280, 0x0007, 0x2004, 0xa084,
-       0x000f, 0x0002, 0xa9e3, 0xa9e3, 0xa9e3, 0xa9e8, 0xa9e3, 0xa9e5,
-       0xa9e5, 0xa9e3, 0xa9e5, 0xa006, 0x0005, 0x00c6, 0x2260, 0x00ce,
-       0xa085, 0x0001, 0x0005, 0xa280, 0x0007, 0x2004, 0xa084, 0x000f,
-       0x0002, 0xa9fa, 0xa9fa, 0xa9fa, 0xa9fa, 0xa9fa, 0xa9fa, 0xaa05,
-       0xa9fa, 0xa9fa, 0x6007, 0x003b, 0x602b, 0x0009, 0x6013, 0x2a00,
-       0x6003, 0x0001, 0x080c, 0x67a8, 0x0005, 0x00c6, 0x2260, 0x080c,
-       0xabb4, 0x603f, 0x0000, 0x6020, 0xc0f4, 0xc0cc, 0x6022, 0x6037,
-       0x0000, 0x00ce, 0x00d6, 0x2268, 0xa186, 0x0007, 0x1904, 0xaa60,
-       0x6810, 0xa005, 0x0138, 0xa080, 0x0013, 0x2004, 0xd0fc, 0x1110,
-       0x00de, 0x08c0, 0x6007, 0x003a, 0x6003, 0x0001, 0x080c, 0x67a8,
-       0x080c, 0x6c50, 0x00c6, 0x2d60, 0x6100, 0xa186, 0x0002, 0x1904,
-       0xaae7, 0x6010, 0xa005, 0x1138, 0x6000, 0xa086, 0x0007, 0x190c,
-       0x14f6, 0x0804, 0xaae7, 0xa08c, 0xf000, 0x1130, 0x0028, 0x2068,
-       0x6800, 0xa005, 0x1de0, 0x2d00, 0xa080, 0x0013, 0x2004, 0xa084,
-       0x0003, 0xa086, 0x0002, 0x1180, 0x6010, 0x2068, 0x684c, 0xc0dc,
-       0xc0f4, 0x684e, 0x6850, 0xc0f4, 0xc0fc, 0x6852, 0x2009, 0x0043,
-       0x080c, 0xa3de, 0x0804, 0xaae7, 0x2009, 0x0041, 0x0804, 0xaae1,
-       0xa186, 0x0005, 0x15f0, 0x6810, 0xa080, 0x0013, 0x2004, 0xd0bc,
-       0x1118, 0x00de, 0x0804, 0xa9fa, 0xd0b4, 0x0128, 0xd0fc, 0x090c,
-       0x14f6, 0x0804, 0xaa18, 0x6007, 0x003a, 0x6003, 0x0001, 0x080c,
-       0x67a8, 0x080c, 0x6c50, 0x00c6, 0x2d60, 0x6100, 0xa186, 0x0002,
-       0x0120, 0xa186, 0x0004, 0x1904, 0xaae7, 0x2071, 0xaffd, 0x7000,
-       0xa086, 0x0003, 0x1128, 0x7004, 0xac06, 0x1110, 0x7003, 0x0000,
-       0x6810, 0xa080, 0x0013, 0x200c, 0xc1f4, 0xc1dc, 0x2102, 0x8000,
-       0x200c, 0xc1f4, 0xc1fc, 0xc1bc, 0x2102, 0x2009, 0x0042, 0x0804,
-       0xaae1, 0x0036, 0x00d6, 0x00d6, 0x080c, 0x15d9, 0x003e, 0x090c,
-       0x14f6, 0x6837, 0x010d, 0x6803, 0x0000, 0x683b, 0x0000, 0x685b,
-       0x0000, 0x6b5e, 0x6857, 0x0045, 0x2c00, 0x6862, 0x6034, 0x6872,
-       0x2360, 0x6020, 0xc0dd, 0x6022, 0x6018, 0xa080, 0x0028, 0x2004,
-       0xa084, 0x00ff, 0x8007, 0x6350, 0x6b4a, 0x6846, 0x684f, 0x0000,
-       0x6d6a, 0x6e66, 0x686f, 0x0001, 0x080c, 0x510c, 0x2019, 0x0045,
-       0x6008, 0x2068, 0x080c, 0xa566, 0x2d00, 0x600a, 0x601f, 0x0006,
-       0x6003, 0x0007, 0x6017, 0x0000, 0x603f, 0x0000, 0x00de, 0x003e,
-       0x0038, 0x603f, 0x0000, 0x6003, 0x0007, 0x080c, 0xa3de, 0x00ce,
-       0x00de, 0x0005, 0xa186, 0x0013, 0x1128, 0x6004, 0xa082, 0x0085,
-       0x2008, 0x00c2, 0xa186, 0x0027, 0x1178, 0x080c, 0x6b73, 0x0036,
-       0x00d6, 0x6010, 0x2068, 0x2019, 0x0004, 0x080c, 0xa91f, 0x00de,
-       0x003e, 0x080c, 0x6c50, 0x0005, 0xa186, 0x0014, 0x0d70, 0x080c,
-       0x80be, 0x0005, 0xab13, 0xab11, 0xab11, 0xab11, 0xab11, 0xab11,
-       0xab13, 0x080c, 0x14f6, 0x080c, 0x6b73, 0x6003, 0x000c, 0x080c,
-       0x6c50, 0x0005, 0xa182, 0x008c, 0x1220, 0xa182, 0x0085, 0x0208,
-       0x001a, 0x080c, 0x80be, 0x0005, 0xab2b, 0xab2b, 0xab2b, 0xab2b,
-       0xab2d, 0xab4b, 0xab2b, 0x080c, 0x14f6, 0x00d6, 0x2c68, 0x080c,
-       0x8022, 0x01a0, 0x6003, 0x0001, 0x6007, 0x001e, 0x2009, 0xb28e,
-       0x210c, 0x6136, 0x2009, 0xb28f, 0x210c, 0x613a, 0x600b, 0xffff,
-       0x6918, 0x611a, 0x601f, 0x0004, 0x080c, 0x67a8, 0x2d60, 0x080c,
-       0x8078, 0x00de, 0x0005, 0x080c, 0x8078, 0x0005, 0x00e6, 0x6018,
-       0x2070, 0x7000, 0xd0ec, 0x00ee, 0x0005, 0x6010, 0xa080, 0x0013,
-       0x200c, 0xd1ec, 0x05d0, 0x2001, 0xad71, 0x2004, 0xd0ec, 0x05a8,
-       0x6003, 0x0002, 0x6020, 0xc0e5, 0x6022, 0xd1ac, 0x0180, 0x00f6,
-       0x2c78, 0x080c, 0x5025, 0x00fe, 0x0150, 0x2001, 0xafa5, 0x2004,
-       0x603e, 0x2009, 0xad71, 0x210c, 0xd1f4, 0x11e8, 0x0080, 0x2009,
-       0xad71, 0x210c, 0xd1f4, 0x0128, 0x6020, 0xc0e4, 0x6022, 0xa006,
-       0x00a0, 0x2001, 0xafa5, 0x200c, 0x8103, 0xa100, 0x603e, 0x6018,
-       0xa088, 0x002b, 0x2104, 0xa005, 0x0118, 0xa088, 0x0003, 0x0cd0,
-       0x2c0a, 0x600f, 0x0000, 0xa085, 0x0001, 0x0005, 0x0016, 0x00c6,
-       0x00e6, 0x6150, 0xa2f0, 0x002b, 0x2e04, 0x2060, 0x8cff, 0x0180,
-       0x84ff, 0x1118, 0x6050, 0xa106, 0x1138, 0x600c, 0x2072, 0x080c,
-       0x6618, 0x080c, 0x8078, 0x0010, 0xacf0, 0x0003, 0x2e64, 0x0c70,
-       0x00ee, 0x00ce, 0x001e, 0x0005, 0x00d6, 0x6018, 0xa0e8, 0x002b,
-       0x2d04, 0xa005, 0x0140, 0xac06, 0x0120, 0x2d04, 0xa0e8, 0x0003,
-       0x0cb8, 0x600c, 0x206a, 0x00de, 0x0005, 0x0026, 0x0036, 0x0156,
-       0x2011, 0xad27, 0x2204, 0xa084, 0x00ff, 0x2019, 0xb28e, 0x2334,
-       0xa636, 0x11d8, 0x8318, 0x2334, 0x2204, 0xa084, 0xff00, 0xa636,
-       0x11a0, 0x2011, 0xb290, 0x6018, 0xa098, 0x000a, 0x20a9, 0x0004,
-       0x080c, 0x8a7c, 0x1150, 0x2011, 0xb294, 0x6018, 0xa098, 0x0006,
-       0x20a9, 0x0004, 0x080c, 0x8a7c, 0x1100, 0x015e, 0x003e, 0x002e,
-       0x0005, 0x00e6, 0x2071, 0xad00, 0x080c, 0x48f5, 0x080c, 0x28fa,
-       0x00ee, 0x0005, 0x00e6, 0x6018, 0x2070, 0x7000, 0xd0fc, 0x0108,
-       0x0011, 0x00ee, 0x0005, 0x6850, 0xc0e5, 0x6852, 0x0005, 0x00e6,
-       0x00c6, 0x0076, 0x0066, 0x0056, 0x0046, 0x0026, 0x0016, 0x0126,
-       0x2091, 0x8000, 0x2029, 0xafd0, 0x252c, 0x2021, 0xafd6, 0x2424,
-       0x2061, 0xb400, 0x2071, 0xad00, 0x7644, 0x7064, 0xa606, 0x0578,
-       0x671c, 0xa786, 0x0001, 0x0118, 0xa786, 0x0008, 0x1500, 0x2500,
-       0xac06, 0x01e8, 0x2400, 0xac06, 0x01d0, 0x080c, 0xa990, 0x01b8,
-       0x080c, 0xa9a0, 0x11a0, 0x6000, 0xa086, 0x0004, 0x1120, 0x0016,
-       0x080c, 0x190b, 0x001e, 0x080c, 0x9778, 0x1110, 0x080c, 0x2aff,
-       0x080c, 0x9789, 0x1110, 0x080c, 0x85f3, 0x080c, 0x974e, 0xace0,
-       0x0018, 0x2001, 0xad16, 0x2004, 0xac02, 0x1208, 0x0858, 0x012e,
-       0x001e, 0x002e, 0x004e, 0x005e, 0x006e, 0x007e, 0x00ce, 0x00ee,
-       0x0005, 0x0126, 0x0006, 0x00e6, 0x2091, 0x8000, 0x2071, 0xad40,
-       0xd5a4, 0x0118, 0x7034, 0x8000, 0x7036, 0xd5b4, 0x0118, 0x7030,
-       0x8000, 0x7032, 0xd5ac, 0x0118, 0x2071, 0xad4a, 0x0451, 0x00ee,
-       0x000e, 0x012e, 0x0005, 0x0126, 0x0006, 0x00e6, 0x2091, 0x8000,
-       0x2071, 0xad40, 0xd5a4, 0x0118, 0x7034, 0x8000, 0x7036, 0xd5b4,
-       0x0118, 0x7030, 0x8000, 0x7032, 0xd5ac, 0x0118, 0x2071, 0xad4a,
-       0x0081, 0x00ee, 0x000e, 0x012e, 0x0005, 0x0126, 0x0006, 0x00e6,
-       0x2091, 0x8000, 0x2071, 0xad42, 0x0021, 0x00ee, 0x000e, 0x012e,
-       0x0005, 0x2e04, 0x8000, 0x2072, 0x1220, 0x8e70, 0x2e04, 0x8000,
-       0x2072, 0x0005, 0x00e6, 0x2071, 0xad40, 0x0c99, 0x00ee, 0x0005,
-       0x00e6, 0x2071, 0xad44, 0x0c69, 0x00ee, 0x0005, 0x0001, 0x0002,
-       0x0004, 0x0008, 0x0010, 0x0020, 0x0040, 0x0080, 0x0100, 0x0200,
-       0x0400, 0x0800, 0x1000, 0x2000, 0x4000, 0x8000, 0x8529
-};
-
index fa901fd650856e8f7b241ff5285bcc3ab84c4c6e..d5fdcb9a88425fb3edac03a867a3cce74dd5fb34 100644 (file)
@@ -378,7 +378,6 @@ static struct scsi_host_template mv_sht = {
        .name                   = DRV_NAME,
        .ioctl                  = ata_scsi_ioctl,
        .queuecommand           = ata_scsi_queuecmd,
-       .eh_strategy_handler    = ata_scsi_error,
        .can_queue              = MV_USE_Q_DEPTH,
        .this_id                = ATA_SHT_THIS_ID,
        .sg_tablesize           = MV_MAX_SG_CT / 2,
@@ -748,7 +747,7 @@ static void mv_dump_all_regs(void __iomem *mmio_base, int port,
        mv_dump_mem(mmio_base+0xf00, 0x4);
        mv_dump_mem(mmio_base+0x1d00, 0x6c);
        for (hc = start_hc; hc < start_hc + num_hcs; hc++) {
-               hc_base = mv_hc_base(mmio_base, port >> MV_PORT_HC_SHIFT);
+               hc_base = mv_hc_base(mmio_base, hc);
                DPRINTK("HC regs (HC %i):\n", hc);
                mv_dump_mem(hc_base, 0x1c);
        }
index f77bf183dfab81de3fbd3aa4f61140fa95b47fb7..9f553081b5e832525c8fde6fd33cea2c9058004e 100644 (file)
@@ -201,7 +201,6 @@ static struct scsi_host_template nv_sht = {
        .name                   = DRV_NAME,
        .ioctl                  = ata_scsi_ioctl,
        .queuecommand           = ata_scsi_queuecmd,
-       .eh_strategy_handler    = ata_scsi_error,
        .can_queue              = ATA_DEF_QUEUE,
        .this_id                = ATA_SHT_THIS_ID,
        .sg_tablesize           = LIBATA_MAX_PRD,
index cc928c68a4790e26621214919d0b9db4f1e11918..7eb67a6bdc64ca4a08f3fb3739e63b0b4c6d706d 100644 (file)
@@ -111,7 +111,6 @@ static struct scsi_host_template pdc_ata_sht = {
        .name                   = DRV_NAME,
        .ioctl                  = ata_scsi_ioctl,
        .queuecommand           = ata_scsi_queuecmd,
-       .eh_strategy_handler    = ata_scsi_error,
        .can_queue              = ATA_DEF_QUEUE,
        .this_id                = ATA_SHT_THIS_ID,
        .sg_tablesize           = LIBATA_MAX_PRD,
index 9ffe1ef0d20511eb158fa34a17d05bb672a96877..886f3447dd48b25c669c8d0d99e13181c14e16b1 100644 (file)
@@ -132,7 +132,6 @@ static struct scsi_host_template qs_ata_sht = {
        .name                   = DRV_NAME,
        .ioctl                  = ata_scsi_ioctl,
        .queuecommand           = ata_scsi_queuecmd,
-       .eh_strategy_handler    = ata_scsi_error,
        .can_queue              = ATA_DEF_QUEUE,
        .this_id                = ATA_SHT_THIS_ID,
        .sg_tablesize           = QS_MAX_PRD,
index 18c296c56899151ee966e6dddd25d380bc9d495f..106627299d55f002530bf12ef9e6105614c99175 100644 (file)
@@ -146,7 +146,6 @@ static struct scsi_host_template sil_sht = {
        .name                   = DRV_NAME,
        .ioctl                  = ata_scsi_ioctl,
        .queuecommand           = ata_scsi_queuecmd,
-       .eh_strategy_handler    = ata_scsi_error,
        .can_queue              = ATA_DEF_QUEUE,
        .this_id                = ATA_SHT_THIS_ID,
        .sg_tablesize           = LIBATA_MAX_PRD,
index 068c98a4111bc264401009cbf3cbf4258bdbc48a..f7264fd611c2226bc71e6d8e552478a8eaaf2748 100644 (file)
@@ -281,7 +281,6 @@ static struct scsi_host_template sil24_sht = {
        .name                   = DRV_NAME,
        .ioctl                  = ata_scsi_ioctl,
        .queuecommand           = ata_scsi_queuecmd,
-       .eh_strategy_handler    = ata_scsi_error,
        .can_queue              = ATA_DEF_QUEUE,
        .this_id                = ATA_SHT_THIS_ID,
        .sg_tablesize           = LIBATA_MAX_PRD,
index acc8439dea233dba04dc5cd95633761617c92760..728530df2e0751d3f498a2a96c49b1cd6d3a2cb6 100644 (file)
@@ -87,7 +87,6 @@ static struct scsi_host_template sis_sht = {
        .name                   = DRV_NAME,
        .ioctl                  = ata_scsi_ioctl,
        .queuecommand           = ata_scsi_queuecmd,
-       .eh_strategy_handler    = ata_scsi_error,
        .can_queue              = ATA_DEF_QUEUE,
        .this_id                = ATA_SHT_THIS_ID,
        .sg_tablesize           = ATA_MAX_PRD,
index 724f0ed6a52d210f3d3b5ba99be12e7040887888..53b0d5c0a61f45b4c25f78326c7aad38ff441c42 100644 (file)
@@ -290,7 +290,6 @@ static struct scsi_host_template k2_sata_sht = {
        .name                   = DRV_NAME,
        .ioctl                  = ata_scsi_ioctl,
        .queuecommand           = ata_scsi_queuecmd,
-       .eh_strategy_handler    = ata_scsi_error,
        .can_queue              = ATA_DEF_QUEUE,
        .this_id                = ATA_SHT_THIS_ID,
        .sg_tablesize           = LIBATA_MAX_PRD,
index ae70f60c7c0d03de0733d1eac795eb41debe4f59..4139ad4b1df065fb00d51510207c9e13dfe41332 100644 (file)
@@ -182,7 +182,6 @@ static struct scsi_host_template pdc_sata_sht = {
        .name                   = DRV_NAME,
        .ioctl                  = ata_scsi_ioctl,
        .queuecommand           = ata_scsi_queuecmd,
-       .eh_strategy_handler    = ata_scsi_error,
        .can_queue              = ATA_DEF_QUEUE,
        .this_id                = ATA_SHT_THIS_ID,
        .sg_tablesize           = LIBATA_MAX_PRD,
index 7ac5a5f5a905000d7c4962dad11c81221de753a4..38b52bd3fa3f1d5772ca83a8cb3341c9fad24862 100644 (file)
@@ -81,7 +81,6 @@ static struct scsi_host_template uli_sht = {
        .name                   = DRV_NAME,
        .ioctl                  = ata_scsi_ioctl,
        .queuecommand           = ata_scsi_queuecmd,
-       .eh_strategy_handler    = ata_scsi_error,
        .can_queue              = ATA_DEF_QUEUE,
        .this_id                = ATA_SHT_THIS_ID,
        .sg_tablesize           = LIBATA_MAX_PRD,
index 791bf652ba632905b27271c453a701a87a7932b6..9e7ae4e0db324535b3f34fbe648173abe7dd83de 100644 (file)
@@ -94,7 +94,6 @@ static struct scsi_host_template svia_sht = {
        .name                   = DRV_NAME,
        .ioctl                  = ata_scsi_ioctl,
        .queuecommand           = ata_scsi_queuecmd,
-       .eh_strategy_handler    = ata_scsi_error,
        .can_queue              = ATA_DEF_QUEUE,
        .this_id                = ATA_SHT_THIS_ID,
        .sg_tablesize           = LIBATA_MAX_PRD,
index 836bbbb26ff2c1c37cb76608821156babd9d776c..8a29ce340b472019b914e32ebfbebaa7f9463dc9 100644 (file)
@@ -263,7 +263,6 @@ static struct scsi_host_template vsc_sata_sht = {
        .name                   = DRV_NAME,
        .ioctl                  = ata_scsi_ioctl,
        .queuecommand           = ata_scsi_queuecmd,
-       .eh_strategy_handler    = ata_scsi_error,
        .can_queue              = ATA_DEF_QUEUE,
        .this_id                = ATA_SHT_THIS_ID,
        .sg_tablesize           = LIBATA_MAX_PRD,
index 6913b0623167ca0c6d45d21862213a958cd215cf..73994e2ac2cb73e3636042945511735bbb17a13f 100644 (file)
@@ -565,7 +565,8 @@ int scsi_dispatch_cmd(struct scsi_cmnd *cmd)
        /* 
         * If SCSI-2 or lower, store the LUN value in cmnd.
         */
-       if (cmd->device->scsi_level <= SCSI_2) {
+       if (cmd->device->scsi_level <= SCSI_2 &&
+           cmd->device->scsi_level != SCSI_UNKNOWN) {
                cmd->cmnd[1] = (cmd->cmnd[1] & 0x1f) |
                               (cmd->device->lun << 5 & 0xe0);
        }
@@ -1243,7 +1244,7 @@ static int __init init_scsi(void)
        if (error)
                goto cleanup_sysctl;
 
-       for_each_cpu(i)
+       for_each_possible_cpu(i)
                INIT_LIST_HEAD(&per_cpu(scsi_done_q, i));
 
        printk(KERN_NOTICE "SCSI subsystem initialized\n");
index 84c3937ae8fb506c491fb23bcb23828c5d5eb9db..c750d3399a97835bbf774a6a2ab5e3dece5f330f 100644 (file)
@@ -132,7 +132,9 @@ static struct {
        {"CMD", "CRA-7280", NULL, BLIST_SPARSELUN},     /* CMD RAID Controller */
        {"CNSI", "G7324", NULL, BLIST_SPARSELUN},       /* Chaparral G7324 RAID */
        {"CNSi", "G8324", NULL, BLIST_SPARSELUN},       /* Chaparral G8324 RAID */
-       {"COMPAQ", "LOGICAL VOLUME", NULL, BLIST_FORCELUN},
+       {"COMPAQ", "ARRAY CONTROLLER", NULL, BLIST_SPARSELUN | BLIST_LARGELUN |
+               BLIST_MAX_512 | BLIST_REPORTLUN2},      /* Compaq RA4x00 */
+       {"COMPAQ", "LOGICAL VOLUME", NULL, BLIST_FORCELUN | BLIST_MAX_512}, /* Compaq RA4x00 */
        {"COMPAQ", "CR3500", NULL, BLIST_FORCELUN},
        {"COMPAQ", "MSA1000", NULL, BLIST_SPARSELUN | BLIST_NOSTARTONADD},
        {"COMPAQ", "MSA1000 VOLUME", NULL, BLIST_SPARSELUN | BLIST_NOSTARTONADD},
index 5f0fdfb2618ca40910fb185fd00fb4bdaed770a5..1c75646f9689da6a9d2160744e7e402f8ac27b50 100644 (file)
@@ -1537,8 +1537,8 @@ int scsi_error_handler(void *data)
                 * what we need to do to get it up and online again (if we can).
                 * If we fail, we end up taking the thing offline.
                 */
-               if (shost->hostt->eh_strategy_handler) 
-                       shost->hostt->eh_strategy_handler(shost);
+               if (shost->transportt->eh_strategy_handler)
+                       shost->transportt->eh_strategy_handler(shost);
                else
                        scsi_unjam_host(shost);
 
index 36e930066649127249937b08a59a96f1f348574b..a89aff61d3d8aea71cca5ceab1ef4d18c1df89f6 100644 (file)
@@ -157,180 +157,6 @@ int scsi_set_medium_removal(struct scsi_device *sdev, char state)
 }
 EXPORT_SYMBOL(scsi_set_medium_removal);
 
-/*
- * This interface is deprecated - users should use the scsi generic (sg)
- * interface instead, as this is a more flexible approach to performing
- * generic SCSI commands on a device.
- *
- * The structure that we are passed should look like:
- *
- * struct sdata {
- *  unsigned int inlen;      [i] Length of data to be written to device 
- *  unsigned int outlen;     [i] Length of data to be read from device 
- *  unsigned char cmd[x];    [i] SCSI command (6 <= x <= 12).
- *                           [o] Data read from device starts here.
- *                           [o] On error, sense buffer starts here.
- *  unsigned char wdata[y];  [i] Data written to device starts here.
- * };
- * Notes:
- *   -  The SCSI command length is determined by examining the 1st byte
- *      of the given command. There is no way to override this.
- *   -  Data transfers are limited to PAGE_SIZE (4K on i386, 8K on alpha).
- *   -  The length (x + y) must be at least OMAX_SB_LEN bytes long to
- *      accommodate the sense buffer when an error occurs.
- *      The sense buffer is truncated to OMAX_SB_LEN (16) bytes so that
- *      old code will not be surprised.
- *   -  If a Unix error occurs (e.g. ENOMEM) then the user will receive
- *      a negative return and the Unix error code in 'errno'. 
- *      If the SCSI command succeeds then 0 is returned.
- *      Positive numbers returned are the compacted SCSI error codes (4 
- *      bytes in one int) where the lowest byte is the SCSI status.
- *      See the drivers/scsi/scsi.h file for more information on this.
- *
- */
-#define OMAX_SB_LEN 16         /* Old sense buffer length */
-
-int scsi_ioctl_send_command(struct scsi_device *sdev,
-                           struct scsi_ioctl_command __user *sic)
-{
-       char *buf;
-       unsigned char cmd[MAX_COMMAND_SIZE];
-       unsigned char sense[SCSI_SENSE_BUFFERSIZE];
-       char __user *cmd_in;
-       unsigned char opcode;
-       unsigned int inlen, outlen, cmdlen;
-       unsigned int needed, buf_needed;
-       int timeout, retries, result;
-       int data_direction;
-       gfp_t gfp_mask = GFP_KERNEL;
-
-       if (!sic)
-               return -EINVAL;
-
-       if (sdev->host->unchecked_isa_dma)
-               gfp_mask |= GFP_DMA;
-
-       /*
-        * Verify that we can read at least this much.
-        */
-       if (!access_ok(VERIFY_READ, sic, sizeof(Scsi_Ioctl_Command)))
-               return -EFAULT;
-
-       if(__get_user(inlen, &sic->inlen))
-               return -EFAULT;
-               
-       if(__get_user(outlen, &sic->outlen))
-               return -EFAULT;
-
-       /*
-        * We do not transfer more than MAX_BUF with this interface.
-        * If the user needs to transfer more data than this, they
-        * should use scsi_generics (sg) instead.
-        */
-       if (inlen > MAX_BUF)
-               return -EINVAL;
-       if (outlen > MAX_BUF)
-               return -EINVAL;
-
-       cmd_in = sic->data;
-       if(get_user(opcode, cmd_in))
-               return -EFAULT;
-
-       needed = buf_needed = (inlen > outlen ? inlen : outlen);
-       if (buf_needed) {
-               buf_needed = (buf_needed + 511) & ~511;
-               if (buf_needed > MAX_BUF)
-                       buf_needed = MAX_BUF;
-               buf = kzalloc(buf_needed, gfp_mask);
-               if (!buf)
-                       return -ENOMEM;
-               if (inlen == 0) {
-                       data_direction = DMA_FROM_DEVICE;
-               } else if (outlen == 0 ) {
-                       data_direction = DMA_TO_DEVICE;
-               } else {
-                       /*
-                        * Can this ever happen?
-                        */
-                       data_direction = DMA_BIDIRECTIONAL;
-               }
-
-       } else {
-               buf = NULL;
-               data_direction = DMA_NONE;
-       }
-
-       /*
-        * Obtain the command from the user's address space.
-        */
-       cmdlen = COMMAND_SIZE(opcode);
-       
-       result = -EFAULT;
-
-       if (!access_ok(VERIFY_READ, cmd_in, cmdlen + inlen))
-               goto error;
-
-       if(__copy_from_user(cmd, cmd_in, cmdlen))
-               goto error;
-
-       /*
-        * Obtain the data to be sent to the device (if any).
-        */
-
-       if(inlen && copy_from_user(buf, cmd_in + cmdlen, inlen))
-               goto error;
-
-       switch (opcode) {
-       case SEND_DIAGNOSTIC:
-       case FORMAT_UNIT:
-               timeout = FORMAT_UNIT_TIMEOUT;
-               retries = 1;
-               break;
-       case START_STOP:
-               timeout = START_STOP_TIMEOUT;
-               retries = NORMAL_RETRIES;
-               break;
-       case MOVE_MEDIUM:
-               timeout = MOVE_MEDIUM_TIMEOUT;
-               retries = NORMAL_RETRIES;
-               break;
-       case READ_ELEMENT_STATUS:
-               timeout = READ_ELEMENT_STATUS_TIMEOUT;
-               retries = NORMAL_RETRIES;
-               break;
-       case READ_DEFECT_DATA:
-               timeout = READ_DEFECT_DATA_TIMEOUT;
-               retries = 1;
-               break;
-       default:
-               timeout = IOCTL_NORMAL_TIMEOUT;
-               retries = NORMAL_RETRIES;
-               break;
-       }
-
-       result = scsi_execute(sdev, cmd, data_direction, buf, needed,
-                             sense, timeout, retries, 0);
-
-       /* 
-        * If there was an error condition, pass the info back to the user. 
-        */
-       if (result) {
-               int sb_len = sizeof(*sense);
-
-               sb_len = (sb_len > OMAX_SB_LEN) ? OMAX_SB_LEN : sb_len;
-               if (copy_to_user(cmd_in, sense, sb_len))
-                       result = -EFAULT;
-       } else {
-               if (outlen && copy_to_user(cmd_in, buf, outlen))
-                       result = -EFAULT;
-       }       
-
-error:
-       kfree(buf);
-       return result;
-}
-EXPORT_SYMBOL(scsi_ioctl_send_command);
-
 /*
  * The scsi_ioctl_get_pci() function places into arg the value
  * pci_dev::slot_name (8 characters) for the PCI device (if any).
@@ -409,7 +235,7 @@ int scsi_ioctl(struct scsi_device *sdev, int cmd, void __user *arg)
        case SCSI_IOCTL_SEND_COMMAND:
                if (!capable(CAP_SYS_ADMIN) || !capable(CAP_SYS_RAWIO))
                        return -EACCES;
-               return scsi_ioctl_send_command(sdev, arg);
+               return sg_scsi_ioctl(NULL, sdev->request_queue, NULL, arg);
        case SCSI_IOCTL_DOORLOCK:
                return scsi_set_medium_removal(sdev, SCSI_REMOVAL_PREVENT);
        case SCSI_IOCTL_DOORUNLOCK:
index 8f010a314a3d8b0e9a1e7d795f5badf81718c228..7b0f9a3810d2fba1ac0794f820193e9a832e82ae 100644 (file)
@@ -1479,6 +1479,8 @@ static inline int scsi_host_queue_ready(struct request_queue *q,
 static void scsi_kill_request(struct request *req, request_queue_t *q)
 {
        struct scsi_cmnd *cmd = req->special;
+       struct scsi_device *sdev = cmd->device;
+       struct Scsi_Host *shost = sdev->host;
 
        blkdev_dequeue_request(req);
 
@@ -1491,6 +1493,19 @@ static void scsi_kill_request(struct request *req, request_queue_t *q)
        scsi_init_cmd_errh(cmd);
        cmd->result = DID_NO_CONNECT << 16;
        atomic_inc(&cmd->device->iorequest_cnt);
+
+       /*
+        * SCSI request completion path will do scsi_device_unbusy(),
+        * bump busy counts.  To bump the counters, we need to dance
+        * with the locks as normal issue path does.
+        */
+       sdev->device_busy++;
+       spin_unlock(sdev->request_queue->queue_lock);
+       spin_lock(shost->host_lock);
+       shost->host_busy++;
+       spin_unlock(shost->host_lock);
+       spin_lock(sdev->request_queue->queue_lock);
+
        __scsi_done(cmd);
 }
 
diff --git a/drivers/scsi/scsi_sas_internal.h b/drivers/scsi/scsi_sas_internal.h
new file mode 100644 (file)
index 0000000..d76e6e3
--- /dev/null
@@ -0,0 +1,38 @@
+#ifndef _SCSI_SAS_INTERNAL_H
+#define _SCSI_SAS_INTERNAL_H
+
+#define SAS_HOST_ATTRS         0
+#define SAS_PORT_ATTRS         17
+#define SAS_RPORT_ATTRS                7
+#define SAS_END_DEV_ATTRS      3
+#define SAS_EXPANDER_ATTRS     7
+
+struct sas_internal {
+       struct scsi_transport_template t;
+       struct sas_function_template *f;
+       struct sas_domain_function_template *dft;
+
+       struct class_device_attribute private_host_attrs[SAS_HOST_ATTRS];
+       struct class_device_attribute private_phy_attrs[SAS_PORT_ATTRS];
+       struct class_device_attribute private_rphy_attrs[SAS_RPORT_ATTRS];
+       struct class_device_attribute private_end_dev_attrs[SAS_END_DEV_ATTRS];
+       struct class_device_attribute private_expander_attrs[SAS_EXPANDER_ATTRS];
+
+       struct transport_container phy_attr_cont;
+       struct transport_container rphy_attr_cont;
+       struct transport_container end_dev_attr_cont;
+       struct transport_container expander_attr_cont;
+
+       /*
+        * The array of null terminated pointers to attributes
+        * needed by scsi_sysfs.c
+        */
+       struct class_device_attribute *host_attrs[SAS_HOST_ATTRS + 1];
+       struct class_device_attribute *phy_attrs[SAS_PORT_ATTRS + 1];
+       struct class_device_attribute *rphy_attrs[SAS_RPORT_ATTRS + 1];
+       struct class_device_attribute *end_dev_attrs[SAS_END_DEV_ATTRS + 1];
+       struct class_device_attribute *expander_attrs[SAS_EXPANDER_ATTRS + 1];
+};
+#define to_sas_internal(tmpl)  container_of(tmpl, struct sas_internal, t)
+
+#endif
index f14945996ede5ec514bc0e390b506ffcfaa4d461..1a5474bd11a19d0eb32f434d2556ee64b1bb3c52 100644 (file)
@@ -673,6 +673,7 @@ static int scsi_add_lun(struct scsi_device *sdev, char *inq_result, int *bflags)
        case TYPE_MEDIUM_CHANGER:
        case TYPE_ENCLOSURE:
        case TYPE_COMM:
+       case TYPE_RAID:
        case TYPE_RBC:
                sdev->writeable = 1;
                break;
@@ -737,6 +738,13 @@ static int scsi_add_lun(struct scsi_device *sdev, char *inq_result, int *bflags)
        if (*bflags & BLIST_SELECT_NO_ATN)
                sdev->select_no_atn = 1;
 
+       /*
+        * Maximum 512 sector transfer length
+        * broken RA4x00 Compaq Disk Array
+        */
+       if (*bflags & BLIST_MAX_512)
+               blk_queue_max_sectors(sdev->request_queue, 512);
+
        /*
         * Some devices may not want to have a start command automatically
         * issued when a device is added.
@@ -1123,10 +1131,13 @@ static int scsi_report_lun_scan(struct scsi_target *starget, int bflags,
         * Also allow SCSI-2 if BLIST_REPORTLUN2 is set and host adapter does
         * support more than 8 LUNs.
         */
-       if ((bflags & BLIST_NOREPORTLUN) || 
-            starget->scsi_level < SCSI_2 ||
-           (starget->scsi_level < SCSI_3 && 
-            (!(bflags & BLIST_REPORTLUN2) || shost->max_lun <= 8)) )
+       if (bflags & BLIST_NOREPORTLUN)
+               return 1;
+       if (starget->scsi_level < SCSI_2 &&
+           starget->scsi_level != SCSI_UNKNOWN)
+               return 1;
+       if (starget->scsi_level < SCSI_3 &&
+           (!(bflags & BLIST_REPORTLUN2) || shost->max_lun <= 8))
                return 1;
        if (bflags & BLIST_NOLUN)
                return 0;
index 8db656214b5ca4ba461417b2fe2c315214513d32..95c5478dcdfd4ab4aa09c5095b2f71b39b615571 100644 (file)
@@ -34,6 +34,8 @@
 #include <scsi/scsi_cmnd.h>
 #include "scsi_priv.h"
 
+static int fc_queue_work(struct Scsi_Host *, struct work_struct *);
+
 /*
  * Redefine so that we can have same named attributes in the
  * sdev/starget/host objects.
@@ -213,10 +215,8 @@ fc_bitfield_name_search(remote_port_roles, fc_remote_port_role_names)
 #define FC_MGMTSRVR_PORTID             0x00000a
 
 
-static void fc_shost_remove_rports(void  *data);
 static void fc_timeout_deleted_rport(void *data);
 static void fc_scsi_scan_rport(void *data);
-static void fc_rport_terminate(struct fc_rport  *rport);
 
 /*
  * Attribute counts pre object type...
@@ -288,42 +288,58 @@ static int fc_host_setup(struct transport_container *tc, struct device *dev,
                         struct class_device *cdev)
 {
        struct Scsi_Host *shost = dev_to_shost(dev);
+       struct fc_host_attrs *fc_host = shost_to_fc_host(shost);
 
        /* 
         * Set default values easily detected by the midlayer as
         * failure cases.  The scsi lldd is responsible for initializing
         * all transport attributes to valid values per host.
         */
-       fc_host_node_name(shost) = -1;
-       fc_host_port_name(shost) = -1;
-       fc_host_permanent_port_name(shost) = -1;
-       fc_host_supported_classes(shost) = FC_COS_UNSPECIFIED;
-       memset(fc_host_supported_fc4s(shost), 0,
-               sizeof(fc_host_supported_fc4s(shost)));
-       memset(fc_host_symbolic_name(shost), 0,
-               sizeof(fc_host_symbolic_name(shost)));
-       fc_host_supported_speeds(shost) = FC_PORTSPEED_UNKNOWN;
-       fc_host_maxframe_size(shost) = -1;
-       memset(fc_host_serial_number(shost), 0,
-               sizeof(fc_host_serial_number(shost)));
-
-       fc_host_port_id(shost) = -1;
-       fc_host_port_type(shost) = FC_PORTTYPE_UNKNOWN;
-       fc_host_port_state(shost) = FC_PORTSTATE_UNKNOWN;
-       memset(fc_host_active_fc4s(shost), 0,
-               sizeof(fc_host_active_fc4s(shost)));
-       fc_host_speed(shost) = FC_PORTSPEED_UNKNOWN;
-       fc_host_fabric_name(shost) = -1;
-
-       fc_host_tgtid_bind_type(shost) = FC_TGTID_BIND_BY_WWPN;
-
-       INIT_LIST_HEAD(&fc_host_rports(shost));
-       INIT_LIST_HEAD(&fc_host_rport_bindings(shost));
-       fc_host_next_rport_number(shost) = 0;
-       fc_host_next_target_id(shost) = 0;
-
-       fc_host_flags(shost) = 0;
-       INIT_WORK(&fc_host_rport_del_work(shost), fc_shost_remove_rports, shost);
+       fc_host->node_name = -1;
+       fc_host->port_name = -1;
+       fc_host->permanent_port_name = -1;
+       fc_host->supported_classes = FC_COS_UNSPECIFIED;
+       memset(fc_host->supported_fc4s, 0,
+               sizeof(fc_host->supported_fc4s));
+       memset(fc_host->symbolic_name, 0,
+               sizeof(fc_host->symbolic_name));
+       fc_host->supported_speeds = FC_PORTSPEED_UNKNOWN;
+       fc_host->maxframe_size = -1;
+       memset(fc_host->serial_number, 0,
+               sizeof(fc_host->serial_number));
+
+       fc_host->port_id = -1;
+       fc_host->port_type = FC_PORTTYPE_UNKNOWN;
+       fc_host->port_state = FC_PORTSTATE_UNKNOWN;
+       memset(fc_host->active_fc4s, 0,
+               sizeof(fc_host->active_fc4s));
+       fc_host->speed = FC_PORTSPEED_UNKNOWN;
+       fc_host->fabric_name = -1;
+
+       fc_host->tgtid_bind_type = FC_TGTID_BIND_BY_WWPN;
+
+       INIT_LIST_HEAD(&fc_host->rports);
+       INIT_LIST_HEAD(&fc_host->rport_bindings);
+       fc_host->next_rport_number = 0;
+       fc_host->next_target_id = 0;
+
+       snprintf(fc_host->work_q_name, KOBJ_NAME_LEN, "fc_wq_%d",
+               shost->host_no);
+       fc_host->work_q = create_singlethread_workqueue(
+                                       fc_host->work_q_name);
+       if (!fc_host->work_q)
+               return -ENOMEM;
+
+       snprintf(fc_host->devloss_work_q_name, KOBJ_NAME_LEN, "fc_dl_%d",
+               shost->host_no);
+       fc_host->devloss_work_q = create_singlethread_workqueue(
+                                       fc_host->devloss_work_q_name);
+       if (!fc_host->devloss_work_q) {
+               destroy_workqueue(fc_host->work_q);
+               fc_host->work_q = NULL;
+               return -ENOMEM;
+       }
+
        return 0;
 }
 
@@ -879,9 +895,9 @@ store_fc_private_host_tgtid_bind_type(struct class_device *cdev,
                while (!list_empty(&fc_host_rport_bindings(shost))) {
                        get_list_head_entry(rport,
                                &fc_host_rport_bindings(shost), peers);
-                       spin_unlock_irqrestore(shost->host_lock, flags);
-                       fc_rport_terminate(rport);
-                       spin_lock_irqsave(shost->host_lock, flags);
+                       list_del(&rport->peers);
+                       rport->port_state = FC_PORTSTATE_DELETED;
+                       fc_queue_work(shost, &rport->rport_delete_work);
                }
                spin_unlock_irqrestore(shost->host_lock, flags);
        }
@@ -1262,6 +1278,90 @@ void fc_release_transport(struct scsi_transport_template *t)
 }
 EXPORT_SYMBOL(fc_release_transport);
 
+/**
+ * fc_queue_work - Queue work to the fc_host workqueue.
+ * @shost:     Pointer to Scsi_Host bound to fc_host.
+ * @work:      Work to queue for execution.
+ *
+ * Return value:
+ *     0 on success / != 0 for error
+ **/
+static int
+fc_queue_work(struct Scsi_Host *shost, struct work_struct *work)
+{
+       if (unlikely(!fc_host_work_q(shost))) {
+               printk(KERN_ERR
+                       "ERROR: FC host '%s' attempted to queue work, "
+                       "when no workqueue created.\n", shost->hostt->name);
+               dump_stack();
+
+               return -EINVAL;
+       }
+
+       return queue_work(fc_host_work_q(shost), work);
+}
+
+/**
+ * fc_flush_work - Flush a fc_host's workqueue.
+ * @shost:     Pointer to Scsi_Host bound to fc_host.
+ **/
+static void
+fc_flush_work(struct Scsi_Host *shost)
+{
+       if (!fc_host_work_q(shost)) {
+               printk(KERN_ERR
+                       "ERROR: FC host '%s' attempted to flush work, "
+                       "when no workqueue created.\n", shost->hostt->name);
+               dump_stack();
+               return;
+       }
+
+       flush_workqueue(fc_host_work_q(shost));
+}
+
+/**
+ * fc_queue_devloss_work - Schedule work for the fc_host devloss workqueue.
+ * @shost:     Pointer to Scsi_Host bound to fc_host.
+ * @work:      Work to queue for execution.
+ * @delay:     jiffies to delay the work queuing
+ *
+ * Return value:
+ *     0 on success / != 0 for error
+ **/
+static int
+fc_queue_devloss_work(struct Scsi_Host *shost, struct work_struct *work,
+                               unsigned long delay)
+{
+       if (unlikely(!fc_host_devloss_work_q(shost))) {
+               printk(KERN_ERR
+                       "ERROR: FC host '%s' attempted to queue work, "
+                       "when no workqueue created.\n", shost->hostt->name);
+               dump_stack();
+
+               return -EINVAL;
+       }
+
+       return queue_delayed_work(fc_host_devloss_work_q(shost), work, delay);
+}
+
+/**
+ * fc_flush_devloss - Flush a fc_host's devloss workqueue.
+ * @shost:     Pointer to Scsi_Host bound to fc_host.
+ **/
+static void
+fc_flush_devloss(struct Scsi_Host *shost)
+{
+       if (!fc_host_devloss_work_q(shost)) {
+               printk(KERN_ERR
+                       "ERROR: FC host '%s' attempted to flush work, "
+                       "when no workqueue created.\n", shost->hostt->name);
+               dump_stack();
+               return;
+       }
+
+       flush_workqueue(fc_host_devloss_work_q(shost));
+}
+
 
 /**
  * fc_remove_host - called to terminate any fc_transport-related elements
@@ -1283,36 +1383,103 @@ void
 fc_remove_host(struct Scsi_Host *shost)
 {
        struct fc_rport *rport, *next_rport;
+       struct workqueue_struct *work_q;
+       struct fc_host_attrs *fc_host = shost_to_fc_host(shost);
 
        /* Remove any remote ports */
        list_for_each_entry_safe(rport, next_rport,
-                       &fc_host_rports(shost), peers)
-               fc_rport_terminate(rport);
+                       &fc_host->rports, peers) {
+               list_del(&rport->peers);
+               rport->port_state = FC_PORTSTATE_DELETED;
+               fc_queue_work(shost, &rport->rport_delete_work);
+       }
+
        list_for_each_entry_safe(rport, next_rport,
-                       &fc_host_rport_bindings(shost), peers)
-               fc_rport_terminate(rport);
+                       &fc_host->rport_bindings, peers) {
+               list_del(&rport->peers);
+               rport->port_state = FC_PORTSTATE_DELETED;
+               fc_queue_work(shost, &rport->rport_delete_work);
+       }
+
+       /* flush all scan work items */
+       scsi_flush_work(shost);
+
+       /* flush all stgt delete, and rport delete work items, then kill it  */
+       if (fc_host->work_q) {
+               work_q = fc_host->work_q;
+               fc_host->work_q = NULL;
+               destroy_workqueue(work_q);
+       }
+
+       /* flush all devloss work items, then kill it  */
+       if (fc_host->devloss_work_q) {
+               work_q = fc_host->devloss_work_q;
+               fc_host->devloss_work_q = NULL;
+               destroy_workqueue(work_q);
+       }
 }
 EXPORT_SYMBOL(fc_remove_host);
 
-/*
- * fc_rport_tgt_remove - Removes the scsi target on the remote port
- * @rport:     The remote port to be operated on
- */
+
+/**
+ * fc_starget_delete - called to delete the scsi decendents of an rport
+ *                  (target and all sdevs)
+ *
+ * @data:      remote port to be operated on.
+ **/
 static void
-fc_rport_tgt_remove(struct fc_rport *rport)
+fc_starget_delete(void *data)
 {
+       struct fc_rport *rport = (struct fc_rport *)data;
        struct Scsi_Host *shost = rport_to_shost(rport);
+       unsigned long flags;
 
        scsi_target_unblock(&rport->dev);
 
-       /* Stop anything on the workq */
-       if (!cancel_delayed_work(&rport->dev_loss_work))
-               flush_scheduled_work();
-       scsi_flush_work(shost);
+       spin_lock_irqsave(shost->host_lock, flags);
+       if (rport->flags & FC_RPORT_DEVLOSS_PENDING) {
+               spin_unlock_irqrestore(shost->host_lock, flags);
+               if (!cancel_delayed_work(&rport->dev_loss_work))
+                       fc_flush_devloss(shost);
+               spin_lock_irqsave(shost->host_lock, flags);
+               rport->flags &= ~FC_RPORT_DEVLOSS_PENDING;
+       }
+       spin_unlock_irqrestore(shost->host_lock, flags);
 
        scsi_remove_target(&rport->dev);
 }
 
+
+/**
+ * fc_rport_final_delete - finish rport termination and delete it.
+ *
+ * @data:      remote port to be deleted.
+ **/
+static void
+fc_rport_final_delete(void *data)
+{
+       struct fc_rport *rport = (struct fc_rport *)data;
+       struct device *dev = &rport->dev;
+       struct Scsi_Host *shost = rport_to_shost(rport);
+
+       /* Delete SCSI target and sdevs */
+       if (rport->scsi_target_id != -1)
+               fc_starget_delete(data);
+
+       /*
+        * if a scan is pending, flush the SCSI Host work_q so that 
+        * that we can reclaim the rport scan work element.
+        */
+       if (rport->flags & FC_RPORT_SCAN_PENDING)
+               scsi_flush_work(shost);
+
+       transport_remove_device(dev);
+       device_del(dev);
+       transport_destroy_device(dev);
+       put_device(&shost->shost_gendev);
+}
+
+
 /**
  * fc_rport_create - allocates and creates a remote FC port.
  * @shost:     scsi host the remote port is connected to.
@@ -1330,8 +1497,7 @@ struct fc_rport *
 fc_rport_create(struct Scsi_Host *shost, int channel,
        struct fc_rport_identifiers  *ids)
 {
-       struct fc_host_attrs *fc_host =
-                       (struct fc_host_attrs *)shost->shost_data;
+       struct fc_host_attrs *fc_host = shost_to_fc_host(shost);
        struct fc_internal *fci = to_fc_internal(shost->transportt);
        struct fc_rport *rport;
        struct device *dev;
@@ -1360,6 +1526,8 @@ fc_rport_create(struct Scsi_Host *shost, int channel,
 
        INIT_WORK(&rport->dev_loss_work, fc_timeout_deleted_rport, rport);
        INIT_WORK(&rport->scan_work, fc_scsi_scan_rport, rport);
+       INIT_WORK(&rport->stgt_delete_work, fc_starget_delete, rport);
+       INIT_WORK(&rport->rport_delete_work, fc_rport_final_delete, rport);
 
        spin_lock_irqsave(shost->host_lock, flags);
 
@@ -1368,7 +1536,7 @@ fc_rport_create(struct Scsi_Host *shost, int channel,
                rport->scsi_target_id = fc_host->next_target_id++;
        else
                rport->scsi_target_id = -1;
-       list_add_tail(&rport->peers, &fc_host_rports(shost));
+       list_add_tail(&rport->peers, &fc_host->rports);
        get_device(&shost->shost_gendev);
 
        spin_unlock_irqrestore(shost->host_lock, flags);
@@ -1389,9 +1557,11 @@ fc_rport_create(struct Scsi_Host *shost, int channel,
        transport_add_device(dev);
        transport_configure_device(dev);
 
-       if (rport->roles & FC_RPORT_ROLE_FCP_TARGET)
+       if (rport->roles & FC_RPORT_ROLE_FCP_TARGET) {
                /* initiate a scan of the target */
+               rport->flags |= FC_RPORT_SCAN_PENDING;
                scsi_queue_work(shost, &rport->scan_work);
+       }
 
        return rport;
 
@@ -1451,10 +1621,14 @@ fc_remote_port_add(struct Scsi_Host *shost, int channel,
        struct fc_rport_identifiers  *ids)
 {
        struct fc_internal *fci = to_fc_internal(shost->transportt);
+       struct fc_host_attrs *fc_host = shost_to_fc_host(shost);
        struct fc_rport *rport;
        unsigned long flags;
        int match = 0;
 
+       /* ensure any stgt delete functions are done */
+       fc_flush_work(shost);
+
        /*
         * Search the list of "active" rports, for an rport that has been
         * deleted, but we've held off the real delete while the target
@@ -1462,12 +1636,12 @@ fc_remote_port_add(struct Scsi_Host *shost, int channel,
         */
        spin_lock_irqsave(shost->host_lock, flags);
 
-       list_for_each_entry(rport, &fc_host_rports(shost), peers) {
+       list_for_each_entry(rport, &fc_host->rports, peers) {
 
                if ((rport->port_state == FC_PORTSTATE_BLOCKED) &&
                        (rport->channel == channel)) {
 
-                       switch (fc_host_tgtid_bind_type(shost)) {
+                       switch (fc_host->tgtid_bind_type) {
                        case FC_TGTID_BIND_BY_WWPN:
                        case FC_TGTID_BIND_NONE:
                                if (rport->port_name == ids->port_name)
@@ -1521,27 +1695,34 @@ fc_remote_port_add(struct Scsi_Host *shost, int channel,
                                 * transaction.
                                 */
                                if (!cancel_delayed_work(work))
-                                       flush_scheduled_work();
+                                       fc_flush_devloss(shost);
+
+                               spin_lock_irqsave(shost->host_lock, flags);
+
+                               rport->flags &= ~FC_RPORT_DEVLOSS_PENDING;
 
                                /* initiate a scan of the target */
+                               rport->flags |= FC_RPORT_SCAN_PENDING;
                                scsi_queue_work(shost, &rport->scan_work);
 
+                               spin_unlock_irqrestore(shost->host_lock, flags);
+
                                return rport;
                        }
                }
        }
 
        /* Search the bindings array */
-       if (fc_host_tgtid_bind_type(shost) != FC_TGTID_BIND_NONE) {
+       if (fc_host->tgtid_bind_type != FC_TGTID_BIND_NONE) {
 
                /* search for a matching consistent binding */
 
-               list_for_each_entry(rport, &fc_host_rport_bindings(shost),
+               list_for_each_entry(rport, &fc_host->rport_bindings,
                                        peers) {
                        if (rport->channel != channel)
                                continue;
 
-                       switch (fc_host_tgtid_bind_type(shost)) {
+                       switch (fc_host->tgtid_bind_type) {
                        case FC_TGTID_BIND_BY_WWPN:
                                if (rport->port_name == ids->port_name)
                                        match = 1;
@@ -1559,8 +1740,7 @@ fc_remote_port_add(struct Scsi_Host *shost, int channel,
                        }
 
                        if (match) {
-                               list_move_tail(&rport->peers,
-                                       &fc_host_rports(shost));
+                               list_move_tail(&rport->peers, &fc_host->rports);
                                break;
                        }
                }
@@ -1574,15 +1754,17 @@ fc_remote_port_add(struct Scsi_Host *shost, int channel,
                        rport->roles = ids->roles;
                        rport->port_state = FC_PORTSTATE_ONLINE;
 
-                       spin_unlock_irqrestore(shost->host_lock, flags);
-
                        if (fci->f->dd_fcrport_size)
                                memset(rport->dd_data, 0,
                                                fci->f->dd_fcrport_size);
 
-                       if (rport->roles & FC_RPORT_ROLE_FCP_TARGET)
+                       if (rport->roles & FC_RPORT_ROLE_FCP_TARGET) {
                                /* initiate a scan of the target */
+                               rport->flags |= FC_RPORT_SCAN_PENDING;
                                scsi_queue_work(shost, &rport->scan_work);
+                       }
+
+                       spin_unlock_irqrestore(shost->host_lock, flags);
 
                        return rport;
                }
@@ -1597,30 +1779,6 @@ fc_remote_port_add(struct Scsi_Host *shost, int channel,
 }
 EXPORT_SYMBOL(fc_remote_port_add);
 
-/*
- * fc_rport_terminate - this routine tears down and deallocates a remote port.
- * @rport:     The remote port to be terminated
- *
- * Notes:
- *     This routine assumes no locks are held on entry.
- */
-static void
-fc_rport_terminate(struct fc_rport  *rport)
-{
-       struct Scsi_Host *shost = rport_to_shost(rport);
-       struct device *dev = &rport->dev;
-       unsigned long flags;
-
-       fc_rport_tgt_remove(rport);
-
-       transport_remove_device(dev);
-       device_del(dev);
-       transport_destroy_device(dev);
-       spin_lock_irqsave(shost->host_lock, flags);
-       list_del(&rport->peers);
-       spin_unlock_irqrestore(shost->host_lock, flags);
-       put_device(&shost->shost_gendev);
-}
 
 /**
  * fc_remote_port_delete - notifies the fc transport that a remote
@@ -1675,20 +1833,39 @@ fc_rport_terminate(struct fc_rport  *rport)
 void
 fc_remote_port_delete(struct fc_rport  *rport)
 {
+       struct Scsi_Host *shost = rport_to_shost(rport);
        int timeout = rport->dev_loss_tmo;
+       unsigned long flags;
+
+       /*
+        * No need to flush the fc_host work_q's, as all adds are synchronous.
+        *
+        * We do need to reclaim the rport scan work element, so eventually
+        * (in fc_rport_final_delete()) we'll flush the scsi host work_q if
+        * there's still a scan pending.
+        */
+
+       spin_lock_irqsave(shost->host_lock, flags);
 
        /* If no scsi target id mapping, delete it */
        if (rport->scsi_target_id == -1) {
-               fc_rport_terminate(rport);
+               list_del(&rport->peers);
+               rport->port_state = FC_PORTSTATE_DELETED;
+               fc_queue_work(shost, &rport->rport_delete_work);
+               spin_unlock_irqrestore(shost->host_lock, flags);
                return;
        }
 
+       rport->port_state = FC_PORTSTATE_BLOCKED;
+
+       rport->flags |= FC_RPORT_DEVLOSS_PENDING;
+
+       spin_unlock_irqrestore(shost->host_lock, flags);
+
        scsi_target_block(&rport->dev);
 
        /* cap the length the devices can be blocked until they are deleted */
-       schedule_delayed_work(&rport->dev_loss_work, timeout * HZ);
-
-       rport->port_state = FC_PORTSTATE_BLOCKED;
+       fc_queue_devloss_work(shost, &rport->dev_loss_work, timeout * HZ);
 }
 EXPORT_SYMBOL(fc_remote_port_delete);
 
@@ -1716,8 +1893,7 @@ void
 fc_remote_port_rolechg(struct fc_rport  *rport, u32 roles)
 {
        struct Scsi_Host *shost = rport_to_shost(rport);
-       struct fc_host_attrs *fc_host =
-                       (struct fc_host_attrs *)shost->shost_data;
+       struct fc_host_attrs *fc_host = shost_to_fc_host(shost);
        unsigned long flags;
        int create = 0;
 
@@ -1729,10 +1905,11 @@ fc_remote_port_rolechg(struct fc_rport  *rport, u32 roles)
                } else if (!(rport->roles & FC_RPORT_ROLE_FCP_TARGET))
                        create = 1;
        }
-       spin_unlock_irqrestore(shost->host_lock, flags);
 
        rport->roles = roles;
 
+       spin_unlock_irqrestore(shost->host_lock, flags);
+
        if (create) {
                /*
                 * There may have been a delete timer running on the
@@ -1747,10 +1924,20 @@ fc_remote_port_rolechg(struct fc_rport  *rport, u32 roles)
                 * transaction.
                 */
                if (!cancel_delayed_work(&rport->dev_loss_work))
-                       flush_scheduled_work();
+                       fc_flush_devloss(shost);
+
+               spin_lock_irqsave(shost->host_lock, flags);
+               rport->flags &= ~FC_RPORT_DEVLOSS_PENDING;
+               spin_unlock_irqrestore(shost->host_lock, flags);
+
+               /* ensure any stgt delete functions are done */
+               fc_flush_work(shost);
 
                /* initiate a scan of the target */
+               spin_lock_irqsave(shost->host_lock, flags);
+               rport->flags |= FC_RPORT_SCAN_PENDING;
                scsi_queue_work(shost, &rport->scan_work);
+               spin_unlock_irqrestore(shost->host_lock, flags);
        }
 }
 EXPORT_SYMBOL(fc_remote_port_rolechg);
@@ -1767,22 +1954,24 @@ fc_timeout_deleted_rport(void  *data)
 {
        struct fc_rport *rport = (struct fc_rport *)data;
        struct Scsi_Host *shost = rport_to_shost(rport);
+       struct fc_host_attrs *fc_host = shost_to_fc_host(shost);
        unsigned long flags;
 
        spin_lock_irqsave(shost->host_lock, flags);
 
+       rport->flags &= ~FC_RPORT_DEVLOSS_PENDING;
+
        /*
-        * If the port is ONLINE, then it came back, but was no longer an
-        * FCP target. Thus we need to tear down the scsi_target on it.
+        * If the port is ONLINE, then it came back. Validate it's still an
+        * FCP target. If not, tear down the scsi_target on it.
         */
-       if (rport->port_state == FC_PORTSTATE_ONLINE) {
-               spin_unlock_irqrestore(shost->host_lock, flags);
-
+       if ((rport->port_state == FC_PORTSTATE_ONLINE) &&
+           !(rport->roles & FC_RPORT_ROLE_FCP_TARGET)) {
                dev_printk(KERN_ERR, &rport->dev,
-                       "blocked FC remote port time out: removing target\n");
-
-               fc_rport_tgt_remove(rport);
-
+                       "blocked FC remote port time out: no longer"
+                       " a FCP target, removing starget\n");
+               fc_queue_work(shost, &rport->stgt_delete_work);
+               spin_unlock_irqrestore(shost->host_lock, flags);
                return;
        }
 
@@ -1793,11 +1982,13 @@ fc_timeout_deleted_rport(void  *data)
                return;
        }
 
-       if (fc_host_tgtid_bind_type(shost) == FC_TGTID_BIND_NONE) {
-               spin_unlock_irqrestore(shost->host_lock, flags);
+       if (fc_host->tgtid_bind_type == FC_TGTID_BIND_NONE) {
+               list_del(&rport->peers);
+               rport->port_state = FC_PORTSTATE_DELETED;
                dev_printk(KERN_ERR, &rport->dev,
                        "blocked FC remote port time out: removing target\n");
-               fc_rport_terminate(rport);
+               fc_queue_work(shost, &rport->rport_delete_work);
+               spin_unlock_irqrestore(shost->host_lock, flags);
                return;
        }
 
@@ -1805,7 +1996,7 @@ fc_timeout_deleted_rport(void  *data)
                "blocked FC remote port time out: removing target and "
                "saving binding\n");
 
-       list_move_tail(&rport->peers, &fc_host_rport_bindings(shost));
+       list_move_tail(&rport->peers, &fc_host->rport_bindings);
 
        /*
         * Note: We do not remove or clear the hostdata area. This allows
@@ -1819,10 +2010,10 @@ fc_timeout_deleted_rport(void  *data)
        rport->maxframe_size = -1;
        rport->supported_classes = FC_COS_UNSPECIFIED;
        rport->roles = FC_RPORT_ROLE_UNKNOWN;
-       rport->port_state = FC_PORTSTATE_DELETED;
+       rport->port_state = FC_PORTSTATE_NOTPRESENT;
 
        /* remove the identifiers that aren't used in the consisting binding */
-       switch (fc_host_tgtid_bind_type(shost)) {
+       switch (fc_host->tgtid_bind_type) {
        case FC_TGTID_BIND_BY_WWPN:
                rport->node_name = -1;
                rport->port_id = -1;
@@ -1843,17 +2034,8 @@ fc_timeout_deleted_rport(void  *data)
         * As this only occurs if the remote port (scsi target)
         * went away and didn't come back - we'll remove
         * all attached scsi devices.
-        *
-        * We'll schedule the shost work item to perform the actual removal
-        * to avoid recursion in the different flush calls if we perform
-        * the removal in each target - and there are lots of targets
-        * whose timeouts fire at the same time.
         */
-
-       if ( !(fc_host_flags(shost) & FC_SHOST_RPORT_DEL_SCHEDULED)) {
-               fc_host_flags(shost) |= FC_SHOST_RPORT_DEL_SCHEDULED;
-               scsi_queue_work(shost, &fc_host_rport_del_work(shost));
-       }
+       fc_queue_work(shost, &rport->stgt_delete_work);
 
        spin_unlock_irqrestore(shost->host_lock, flags);
 }
@@ -1870,44 +2052,18 @@ static void
 fc_scsi_scan_rport(void *data)
 {
        struct fc_rport *rport = (struct fc_rport *)data;
-
-       scsi_target_unblock(&rport->dev);
-       scsi_scan_target(&rport->dev, rport->channel, rport->scsi_target_id,
-                       SCAN_WILD_CARD, 1);
-}
-
-
-/**
- * fc_shost_remove_rports - called to remove all rports that are marked
- *                       as in a deleted (not connected) state.
- * 
- * @data:      shost whose rports are to be looked at
- **/
-static void
-fc_shost_remove_rports(void  *data)
-{
-       struct Scsi_Host *shost = (struct Scsi_Host *)data;
-       struct fc_rport *rport, *next_rport;
+       struct Scsi_Host *shost = rport_to_shost(rport);
        unsigned long flags;
 
-       spin_lock_irqsave(shost->host_lock, flags);
-       while (fc_host_flags(shost) & FC_SHOST_RPORT_DEL_SCHEDULED) {
-
-               fc_host_flags(shost) &= ~FC_SHOST_RPORT_DEL_SCHEDULED;
-
-restart_search:
-               list_for_each_entry_safe(rport, next_rport,
-                               &fc_host_rport_bindings(shost), peers) {
-                       if (rport->port_state == FC_PORTSTATE_DELETED) {
-                               rport->port_state = FC_PORTSTATE_NOTPRESENT;
-                               spin_unlock_irqrestore(shost->host_lock, flags);
-                               fc_rport_tgt_remove(rport);
-                               spin_lock_irqsave(shost->host_lock, flags);
-                               goto restart_search;
-                       }
-               }
-
+       if ((rport->port_state == FC_PORTSTATE_ONLINE) &&
+           (rport->roles & FC_RPORT_ROLE_FCP_TARGET)) {
+               scsi_target_unblock(&rport->dev);
+               scsi_scan_target(&rport->dev, rport->channel,
+                       rport->scsi_target_id, SCAN_WILD_CARD, 1);
        }
+
+       spin_lock_irqsave(shost->host_lock, flags);
+       rport->flags &= ~FC_RPORT_SCAN_PENDING;
        spin_unlock_irqrestore(shost->host_lock, flags);
 }
 
index 134c44c8538a4ea372b5993abf28de0282538955..8b6d65e21bae3a23ac362d65ac9b95d57732b6f3 100644 (file)
 #include <scsi/scsi_transport.h>
 #include <scsi/scsi_transport_sas.h>
 
-
-#define SAS_HOST_ATTRS         0
-#define SAS_PORT_ATTRS         17
-#define SAS_RPORT_ATTRS                7
-#define SAS_END_DEV_ATTRS      3
-#define SAS_EXPANDER_ATTRS     7
-
-struct sas_internal {
-       struct scsi_transport_template t;
-       struct sas_function_template *f;
-
-       struct class_device_attribute private_host_attrs[SAS_HOST_ATTRS];
-       struct class_device_attribute private_phy_attrs[SAS_PORT_ATTRS];
-       struct class_device_attribute private_rphy_attrs[SAS_RPORT_ATTRS];
-       struct class_device_attribute private_end_dev_attrs[SAS_END_DEV_ATTRS];
-       struct class_device_attribute private_expander_attrs[SAS_EXPANDER_ATTRS];
-
-       struct transport_container phy_attr_cont;
-       struct transport_container rphy_attr_cont;
-       struct transport_container end_dev_attr_cont;
-       struct transport_container expander_attr_cont;
-
-       /*
-        * The array of null terminated pointers to attributes
-        * needed by scsi_sysfs.c
-        */
-       struct class_device_attribute *host_attrs[SAS_HOST_ATTRS + 1];
-       struct class_device_attribute *phy_attrs[SAS_PORT_ATTRS + 1];
-       struct class_device_attribute *rphy_attrs[SAS_RPORT_ATTRS + 1];
-       struct class_device_attribute *end_dev_attrs[SAS_END_DEV_ATTRS + 1];
-       struct class_device_attribute *expander_attrs[SAS_EXPANDER_ATTRS + 1];
-};
-#define to_sas_internal(tmpl)  container_of(tmpl, struct sas_internal, t)
-
+#include "scsi_sas_internal.h"
 struct sas_host_attrs {
        struct list_head rphy_list;
        struct mutex lock;
@@ -406,8 +373,6 @@ struct sas_phy *sas_phy_alloc(struct device *parent, int number)
        if (!phy)
                return NULL;
 
-       get_device(parent);
-
        phy->number = number;
 
        device_initialize(&phy->dev);
@@ -459,10 +424,7 @@ EXPORT_SYMBOL(sas_phy_add);
 void sas_phy_free(struct sas_phy *phy)
 {
        transport_destroy_device(&phy->dev);
-       put_device(phy->dev.parent);
-       put_device(phy->dev.parent);
-       put_device(phy->dev.parent);
-       kfree(phy);
+       put_device(&phy->dev);
 }
 EXPORT_SYMBOL(sas_phy_free);
 
@@ -484,7 +446,7 @@ sas_phy_delete(struct sas_phy *phy)
        transport_remove_device(dev);
        device_del(dev);
        transport_destroy_device(dev);
-       put_device(dev->parent);
+       put_device(dev);
 }
 EXPORT_SYMBOL(sas_phy_delete);
 
@@ -800,7 +762,6 @@ struct sas_rphy *sas_end_device_alloc(struct sas_phy *parent)
 
        rdev = kzalloc(sizeof(*rdev), GFP_KERNEL);
        if (!rdev) {
-               put_device(&parent->dev);
                return NULL;
        }
 
@@ -836,7 +797,6 @@ struct sas_rphy *sas_expander_alloc(struct sas_phy *parent,
 
        rdev = kzalloc(sizeof(*rdev), GFP_KERNEL);
        if (!rdev) {
-               put_device(&parent->dev);
                return NULL;
        }
 
@@ -885,6 +845,8 @@ int sas_rphy_add(struct sas_rphy *rphy)
            (identify->target_port_protocols &
             (SAS_PROTOCOL_SSP|SAS_PROTOCOL_STP|SAS_PROTOCOL_SATA)))
                rphy->scsi_target_id = sas_host->next_target_id++;
+       else if (identify->device_type == SAS_END_DEVICE)
+               rphy->scsi_target_id = -1;
        mutex_unlock(&sas_host->lock);
 
        if (identify->device_type == SAS_END_DEVICE &&
@@ -910,6 +872,7 @@ EXPORT_SYMBOL(sas_rphy_add);
  */
 void sas_rphy_free(struct sas_rphy *rphy)
 {
+       struct device *dev = &rphy->dev;
        struct Scsi_Host *shost = dev_to_shost(rphy->dev.parent->parent);
        struct sas_host_attrs *sas_host = to_sas_host_attrs(shost);
 
@@ -917,21 +880,9 @@ void sas_rphy_free(struct sas_rphy *rphy)
        list_del(&rphy->list);
        mutex_unlock(&sas_host->lock);
 
-       transport_destroy_device(&rphy->dev);
-       put_device(rphy->dev.parent);
-       put_device(rphy->dev.parent);
-       put_device(rphy->dev.parent);
-       if (rphy->identify.device_type == SAS_END_DEVICE) {
-               struct sas_end_device *edev = rphy_to_end_device(rphy);
-
-               kfree(edev);
-       } else {
-               /* must be expander */
-               struct sas_expander_device *edev =
-                       rphy_to_expander_device(rphy);
+       transport_destroy_device(dev);
 
-               kfree(edev);
-       }
+       put_device(dev);
 }
 EXPORT_SYMBOL(sas_rphy_free);
 
@@ -971,7 +922,7 @@ sas_rphy_delete(struct sas_rphy *rphy)
 
        parent->rphy = NULL;
 
-       put_device(&parent->dev);
+       put_device(dev);
 }
 EXPORT_SYMBOL(sas_rphy_delete);
 
index 7405d0df95dbc3317eafde865dbdb2937e96b47a..b098942445ec0c43a31b041d1d25e943d28ad55e 100644 (file)
@@ -748,6 +748,7 @@ sg_common_write(Sg_fd * sfp, Sg_request * srp,
                /*
                 * most likely out of mem, but could also be a bad map
                 */
+               sg_finish_rem_req(srp);
                return -ENOMEM;
        } else
                return 0;
@@ -1044,7 +1045,7 @@ sg_ioctl(struct inode *inode, struct file *filp,
                        if (!sg_allow_access(opcode, sdp->device->type))
                                return -EPERM;
                }
-               return scsi_ioctl_send_command(sdp->device, p);
+               return sg_scsi_ioctl(filp, sdp->device->request_queue, NULL, p);
        case SG_SET_DEBUG:
                result = get_user(val, ip);
                if (result)
@@ -1798,8 +1799,10 @@ sg_build_direct(Sg_request * srp, Sg_fd * sfp, int dxfer_len)
        res = st_map_user_pages(schp->buffer, mx_sc_elems,
                                (unsigned long)hp->dxferp, dxfer_len, 
                                (SG_DXFER_TO_DEV == hp->dxfer_direction) ? 1 : 0);
-       if (res <= 0)
+       if (res <= 0) {
+               sg_remove_scat(schp);
                return 1;
+       }
        schp->k_use_sg = res;
        schp->dio_in_use = 1;
        hp->info |= SG_INFO_DIRECT_IO;
index 3659dd7b9d760e9a0917a37e083ce3e84097e22d..defccc477d1eec956ec4a6c055bb3684f328d3f4 100644 (file)
@@ -40,7 +40,7 @@
 #ifndef SYM_DEFS_H
 #define SYM_DEFS_H
 
-#define SYM_VERSION "2.2.2"
+#define SYM_VERSION "2.2.3"
 #define SYM_DRIVER_NAME        "sym-" SYM_VERSION
 
 /*
index 1fffd2b3c654d93da2ef9f49d1b4ac929dd3d5a0..9c83b4d39a2687aa3a65bcebed3cc42fdb295f96 100644 (file)
@@ -134,66 +134,17 @@ static void sym2_setup_params(void)
        }
 }
 
-/*
- * We used to try to deal with 64-bit BARs here, but don't any more.
- * There are many parts of this driver which would need to be modified
- * to handle a 64-bit base address, including scripts.  I'm uncomfortable
- * with making those changes when I have no way of testing it, so I'm
- * just going to disable it.
- *
- * Note that some machines (eg HP rx8620 and Superdome) have bus addresses
- * below 4GB and physical addresses above 4GB.  These will continue to work.
- */
-static int __devinit
-pci_get_base_address(struct pci_dev *pdev, int index, unsigned long *basep)
-{
-       u32 tmp;
-       unsigned long base;
-#define PCI_BAR_OFFSET(index) (PCI_BASE_ADDRESS_0 + (index<<2))
-
-       pci_read_config_dword(pdev, PCI_BAR_OFFSET(index++), &tmp);
-       base = tmp;
-       if ((tmp & 0x7) == PCI_BASE_ADDRESS_MEM_TYPE_64) {
-               pci_read_config_dword(pdev, PCI_BAR_OFFSET(index++), &tmp);
-               if (tmp > 0) {
-                       dev_err(&pdev->dev,
-                               "BAR %d is 64-bit, disabling\n", index - 1);
-                       base = 0;
-               }
-       }
-
-       if ((base & PCI_BASE_ADDRESS_SPACE) == PCI_BASE_ADDRESS_SPACE_IO) {
-               base &= PCI_BASE_ADDRESS_IO_MASK;
-       } else {
-               base &= PCI_BASE_ADDRESS_MEM_MASK;
-       }
-
-       *basep = base;
-       return index;
-#undef PCI_BAR_OFFSET
-}
-
 static struct scsi_transport_template *sym2_transport_template = NULL;
 
-/*
- *  Used by the eh thread to wait for command completion.
- *  It is allocated on the eh thread stack.
- */
-struct sym_eh_wait {
-       struct completion done;
-       struct timer_list timer;
-       void (*old_done)(struct scsi_cmnd *);
-       int to_do;
-       int timed_out;
-};
-
 /*
  *  Driver private area in the SCSI command structure.
  */
 struct sym_ucmd {              /* Override the SCSI pointer structure */
-       dma_addr_t data_mapping;
-       u_char  data_mapped;
-       struct sym_eh_wait *eh_wait;
+       dma_addr_t      data_mapping;
+       unsigned char   data_mapped;
+       unsigned char   to_do;                  /* For error handling */
+       void (*old_done)(struct scsi_cmnd *);   /* For error handling */
+       struct completion *eh_done;             /* For error handling */
 };
 
 #define SYM_UCMD_PTR(cmd)  ((struct sym_ucmd *)(&(cmd)->SCp))
@@ -514,8 +465,6 @@ static inline int sym_setup_cdb(struct sym_hcb *np, struct scsi_cmnd *cmd, struc
  */
 int sym_setup_data_and_start(struct sym_hcb *np, struct scsi_cmnd *cmd, struct sym_ccb *cp)
 {
-       struct sym_tcb *tp = &np->target[cp->target];
-       struct sym_lcb *lp = sym_lp(tp, cp->lun);
        u32 lastp, goalp;
        int dir;
 
@@ -596,7 +545,7 @@ int sym_setup_data_and_start(struct sym_hcb *np, struct scsi_cmnd *cmd, struct s
        /*
         *      activate this job.
         */
-       sym_start_next_ccbs(np, lp, 2);
+       sym_put_start_queue(np, cp);
        return 0;
 
 out_abort:
@@ -751,44 +700,22 @@ static void sym53c8xx_timer(unsigned long npref)
  *  What we will do regarding the involved SCSI command.
  */
 #define SYM_EH_DO_IGNORE       0
-#define SYM_EH_DO_COMPLETE     1
 #define SYM_EH_DO_WAIT         2
 
 /*
- *  Our general completion handler.
+ *  scsi_done() alias when error recovery is in progress.
  */
-static void __sym_eh_done(struct scsi_cmnd *cmd, int timed_out)
+static void sym_eh_done(struct scsi_cmnd *cmd)
 {
-       struct sym_eh_wait *ep = SYM_UCMD_PTR(cmd)->eh_wait;
-       if (!ep)
-               return;
-
-       /* Try to avoid a race here (not 100% safe) */
-       if (!timed_out) {
-               ep->timed_out = 0;
-               if (ep->to_do == SYM_EH_DO_WAIT && !del_timer(&ep->timer))
-                       return;
-       }
+       struct sym_ucmd *ucmd = SYM_UCMD_PTR(cmd);
+       BUILD_BUG_ON(sizeof(struct scsi_pointer) < sizeof(struct sym_ucmd));
 
-       /* Revert everything */
-       SYM_UCMD_PTR(cmd)->eh_wait = NULL;
-       cmd->scsi_done = ep->old_done;
+       cmd->scsi_done = ucmd->old_done;
 
-       /* Wake up the eh thread if it wants to sleep */
-       if (ep->to_do == SYM_EH_DO_WAIT)
-               complete(&ep->done);
+       if (ucmd->to_do == SYM_EH_DO_WAIT)
+               complete(ucmd->eh_done);
 }
 
-/*
- *  scsi_done() alias when error recovery is in progress. 
- */
-static void sym_eh_done(struct scsi_cmnd *cmd) { __sym_eh_done(cmd, 0); }
-
-/*
- *  Some timeout handler to avoid waiting too long.
- */
-static void sym_eh_timeout(u_long p) { __sym_eh_done((struct scsi_cmnd *)p, 1); }
-
 /*
  *  Generic method for our eh processing.
  *  The 'op' argument tells what we have to do.
@@ -796,35 +723,31 @@ static void sym_eh_timeout(u_long p) { __sym_eh_done((struct scsi_cmnd *)p, 1);
 static int sym_eh_handler(int op, char *opname, struct scsi_cmnd *cmd)
 {
        struct sym_hcb *np = SYM_SOFTC_PTR(cmd);
+       struct sym_ucmd *ucmd = SYM_UCMD_PTR(cmd);
+       struct Scsi_Host *host = cmd->device->host;
        SYM_QUEHEAD *qp;
        int to_do = SYM_EH_DO_IGNORE;
        int sts = -1;
-       struct sym_eh_wait eh, *ep = &eh;
+       struct completion eh_done;
 
        dev_warn(&cmd->device->sdev_gendev, "%s operation started.\n", opname);
 
+       spin_lock_irq(host->host_lock);
        /* This one is queued in some place -> to wait for completion */
        FOR_EACH_QUEUED_ELEMENT(&np->busy_ccbq, qp) {
                struct sym_ccb *cp = sym_que_entry(qp, struct sym_ccb, link_ccbq);
                if (cp->cmd == cmd) {
                        to_do = SYM_EH_DO_WAIT;
-                       goto prepare;
+                       break;
                }
        }
 
-prepare:
-       /* Prepare stuff to either ignore, complete or wait for completion */
-       switch(to_do) {
-       default:
-       case SYM_EH_DO_IGNORE:
-               break;
-       case SYM_EH_DO_WAIT:
-               init_completion(&ep->done);
-               /* fall through */
-       case SYM_EH_DO_COMPLETE:
-               ep->old_done = cmd->scsi_done;
+       if (to_do == SYM_EH_DO_WAIT) {
+               init_completion(&eh_done);
+               ucmd->old_done = cmd->scsi_done;
+               ucmd->eh_done = &eh_done;
+               wmb();
                cmd->scsi_done = sym_eh_done;
-               SYM_UCMD_PTR(cmd)->eh_wait = ep;
        }
 
        /* Try to proceed the operation we have been asked for */
@@ -851,29 +774,19 @@ prepare:
 
        /* On error, restore everything and cross fingers :) */
        if (sts) {
-               SYM_UCMD_PTR(cmd)->eh_wait = NULL;
-               cmd->scsi_done = ep->old_done;
+               cmd->scsi_done = ucmd->old_done;
                to_do = SYM_EH_DO_IGNORE;
        }
 
-       ep->to_do = to_do;
-       /* Complete the command with locks held as required by the driver */
-       if (to_do == SYM_EH_DO_COMPLETE)
-               sym_xpt_done2(np, cmd, DID_ABORT);
+       ucmd->to_do = to_do;
+       spin_unlock_irq(host->host_lock);
 
-       /* Wait for completion with locks released, as required by kernel */
        if (to_do == SYM_EH_DO_WAIT) {
-               init_timer(&ep->timer);
-               ep->timer.expires = jiffies + (5*HZ);
-               ep->timer.function = sym_eh_timeout;
-               ep->timer.data = (u_long)cmd;
-               ep->timed_out = 1;      /* Be pessimistic for once :) */
-               add_timer(&ep->timer);
-               spin_unlock_irq(np->s.host->host_lock);
-               wait_for_completion(&ep->done);
-               spin_lock_irq(np->s.host->host_lock);
-               if (ep->timed_out)
+               if (!wait_for_completion_timeout(&eh_done, 5*HZ)) {
+                       ucmd->to_do = SYM_EH_DO_IGNORE;
+                       wmb();
                        sts = -2;
+               }
        }
        dev_warn(&cmd->device->sdev_gendev, "%s operation %s.\n", opname,
                        sts==0 ? "complete" :sts==-2 ? "timed-out" : "failed");
@@ -886,46 +799,22 @@ prepare:
  */
 static int sym53c8xx_eh_abort_handler(struct scsi_cmnd *cmd)
 {
-       int rc;
-
-       spin_lock_irq(cmd->device->host->host_lock);
-       rc = sym_eh_handler(SYM_EH_ABORT, "ABORT", cmd);
-       spin_unlock_irq(cmd->device->host->host_lock);
-
-       return rc;
+       return sym_eh_handler(SYM_EH_ABORT, "ABORT", cmd);
 }
 
 static int sym53c8xx_eh_device_reset_handler(struct scsi_cmnd *cmd)
 {
-       int rc;
-
-       spin_lock_irq(cmd->device->host->host_lock);
-       rc = sym_eh_handler(SYM_EH_DEVICE_RESET, "DEVICE RESET", cmd);
-       spin_unlock_irq(cmd->device->host->host_lock);
-
-       return rc;
+       return sym_eh_handler(SYM_EH_DEVICE_RESET, "DEVICE RESET", cmd);
 }
 
 static int sym53c8xx_eh_bus_reset_handler(struct scsi_cmnd *cmd)
 {
-       int rc;
-
-       spin_lock_irq(cmd->device->host->host_lock);
-       rc = sym_eh_handler(SYM_EH_BUS_RESET, "BUS RESET", cmd);
-       spin_unlock_irq(cmd->device->host->host_lock);
-
-       return rc;
+       return sym_eh_handler(SYM_EH_BUS_RESET, "BUS RESET", cmd);
 }
 
 static int sym53c8xx_eh_host_reset_handler(struct scsi_cmnd *cmd)
 {
-       int rc;
-
-       spin_lock_irq(cmd->device->host->host_lock);
-       rc = sym_eh_handler(SYM_EH_HOST_RESET, "HOST RESET", cmd);
-       spin_unlock_irq(cmd->device->host->host_lock);
-
-       return rc;
+       return sym_eh_handler(SYM_EH_HOST_RESET, "HOST RESET", cmd);
 }
 
 /*
@@ -944,15 +833,12 @@ static void sym_tune_dev_queuing(struct sym_tcb *tp, int lun, u_short reqtags)
        if (reqtags > lp->s.scdev_depth)
                reqtags = lp->s.scdev_depth;
 
-       lp->started_limit = reqtags ? reqtags : 2;
-       lp->started_max   = 1;
        lp->s.reqtags     = reqtags;
 
        if (reqtags != oldtags) {
                dev_info(&tp->starget->dev,
                         "tagged command queuing %s, command queue depth %d.\n",
-                         lp->s.reqtags ? "enabled" : "disabled",
-                         lp->started_limit);
+                         lp->s.reqtags ? "enabled" : "disabled", reqtags);
        }
 }
 
@@ -1866,15 +1752,25 @@ static int __devinit sym_set_workarounds(struct sym_device *device)
 static void __devinit
 sym_init_device(struct pci_dev *pdev, struct sym_device *device)
 {
-       int i;
+       int i = 2;
+       struct pci_bus_region bus_addr;
 
        device->host_id = SYM_SETUP_HOST_ID;
        device->pdev = pdev;
 
-       i = pci_get_base_address(pdev, 1, &device->mmio_base);
-       pci_get_base_address(pdev, i, &device->ram_base);
+       pcibios_resource_to_bus(pdev, &bus_addr, &pdev->resource[1]);
+       device->mmio_base = bus_addr.start;
+
+       /*
+        * If the BAR is 64-bit, resource 2 will be occupied by the
+        * upper 32 bits
+        */
+       if (!pdev->resource[i].flags)
+               i++;
+       pcibios_resource_to_bus(pdev, &bus_addr, &pdev->resource[i]);
+       device->ram_base = bus_addr.start;
 
-#ifndef CONFIG_SCSI_SYM53C8XX_IOMAPPED
+#ifdef CONFIG_SCSI_SYM53C8XX_MMIO
        if (device->mmio_base)
                device->s.ioaddr = pci_iomap(pdev, 1,
                                                pci_resource_len(pdev, 1));
@@ -1978,7 +1874,8 @@ static struct scsi_host_template sym2_template = {
        .eh_bus_reset_handler   = sym53c8xx_eh_bus_reset_handler,
        .eh_host_reset_handler  = sym53c8xx_eh_host_reset_handler,
        .this_id                = 7,
-       .use_clustering         = DISABLE_CLUSTERING,
+       .use_clustering         = ENABLE_CLUSTERING,
+       .max_sectors            = 0xFFFF,
 #ifdef SYM_LINUX_PROC_INFO_SUPPORT
        .proc_info              = sym53c8xx_proc_info,
        .proc_name              = NAME53C8XX,
index cc92d0c70cd710ed2ea42c94f54beb38d5d96aa9..a446cda3f64c015d6a8fe1301497b6a888bed6e5 100644 (file)
@@ -68,7 +68,7 @@
  */
 #define        SYM_CONF_TIMER_INTERVAL         ((HZ+1)/2)
 
-#define SYM_OPT_HANDLE_DEVICE_QUEUEING
+#undef SYM_OPT_HANDLE_DEVICE_QUEUEING
 #define SYM_OPT_LIMIT_COMMAND_REORDERING
 
 /*
index 60850cbe3a85ced36ff7f448869845dedee992a4..a671bdc07450ae43363a7cca0ac76af411a73eaa 100644 (file)
@@ -72,7 +72,10 @@ static void sym_printl_hex(u_char *p, int n)
 
 static void sym_print_msg(struct sym_ccb *cp, char *label, u_char *msg)
 {
-       sym_print_addr(cp->cmd, "%s: ", label);
+       if (label)
+               sym_print_addr(cp->cmd, "%s: ", label);
+       else
+               sym_print_addr(cp->cmd, "");
 
        spi_print_msg(msg);
        printf("\n");
@@ -472,7 +475,7 @@ static int sym_getpciclock (struct sym_hcb *np)
  *  calculations more simple.
  */
 #define _5M 5000000
-static u32 div_10M[] = {2*_5M, 3*_5M, 4*_5M, 6*_5M, 8*_5M, 12*_5M, 16*_5M};
+static const u32 div_10M[] = {2*_5M, 3*_5M, 4*_5M, 6*_5M, 8*_5M, 12*_5M, 16*_5M};
 
 /*
  *  Get clock factor and sync divisor for a given 
@@ -644,6 +647,37 @@ static void sym_save_initial_setting (struct sym_hcb *np)
                np->sv_ctest5   = INB(np, nc_ctest5) & 0x24;
 }
 
+/*
+ *  Set SCSI BUS mode.
+ *  - LVD capable chips (895/895A/896/1010) report the current BUS mode
+ *    through the STEST4 IO register.
+ *  - For previous generation chips (825/825A/875), the user has to tell us
+ *    how to check against HVD, since a 100% safe algorithm is not possible.
+ */
+static void sym_set_bus_mode(struct sym_hcb *np, struct sym_nvram *nvram)
+{
+       if (np->scsi_mode)
+               return;
+
+       np->scsi_mode = SMODE_SE;
+       if (np->features & (FE_ULTRA2|FE_ULTRA3))
+               np->scsi_mode = (np->sv_stest4 & SMODE);
+       else if (np->features & FE_DIFF) {
+               if (SYM_SETUP_SCSI_DIFF == 1) {
+                       if (np->sv_scntl3) {
+                               if (np->sv_stest2 & 0x20)
+                                       np->scsi_mode = SMODE_HVD;
+                       } else if (nvram->type == SYM_SYMBIOS_NVRAM) {
+                               if (!(INB(np, nc_gpreg) & 0x08))
+                                       np->scsi_mode = SMODE_HVD;
+                       }
+               } else if (SYM_SETUP_SCSI_DIFF == 2)
+                       np->scsi_mode = SMODE_HVD;
+       }
+       if (np->scsi_mode == SMODE_HVD)
+               np->rv_stest2 |= 0x20;
+}
+
 /*
  *  Prepare io register values used by sym_start_up() 
  *  according to selected and supported features.
@@ -654,10 +688,7 @@ static int sym_prepare_setting(struct Scsi_Host *shost, struct sym_hcb *np, stru
        u32     period;
        int i;
 
-       /*
-        *  Wide ?
-        */
-       np->maxwide     = (np->features & FE_WIDE)? 1 : 0;
+       np->maxwide = (np->features & FE_WIDE) ? 1 : 0;
 
        /*
         *  Guess the frequency of the chip's clock.
@@ -838,6 +869,7 @@ static int sym_prepare_setting(struct Scsi_Host *shost, struct sym_hcb *np, stru
         *  Get parity checking, host ID and verbose mode from NVRAM
         */
        np->myaddr = 255;
+       np->scsi_mode = 0;
        sym_nvram_setup_host(shost, np, nvram);
 
        /*
@@ -854,33 +886,7 @@ static int sym_prepare_setting(struct Scsi_Host *shost, struct sym_hcb *np, stru
         */
        sym_init_burst(np, burst_max);
 
-       /*
-        *  Set SCSI BUS mode.
-        *  - LVD capable chips (895/895A/896/1010) report the 
-        *    current BUS mode through the STEST4 IO register.
-        *  - For previous generation chips (825/825A/875), 
-        *    user has to tell us how to check against HVD, 
-        *    since a 100% safe algorithm is not possible.
-        */
-       np->scsi_mode = SMODE_SE;
-       if (np->features & (FE_ULTRA2|FE_ULTRA3))
-               np->scsi_mode = (np->sv_stest4 & SMODE);
-       else if (np->features & FE_DIFF) {
-               if (SYM_SETUP_SCSI_DIFF == 1) {
-                       if (np->sv_scntl3) {
-                               if (np->sv_stest2 & 0x20)
-                                       np->scsi_mode = SMODE_HVD;
-                       }
-                       else if (nvram->type == SYM_SYMBIOS_NVRAM) {
-                               if (!(INB(np, nc_gpreg) & 0x08))
-                                       np->scsi_mode = SMODE_HVD;
-                       }
-               }
-               else if (SYM_SETUP_SCSI_DIFF == 2)
-                       np->scsi_mode = SMODE_HVD;
-       }
-       if (np->scsi_mode == SMODE_HVD)
-               np->rv_stest2 |= 0x20;
+       sym_set_bus_mode(np, nvram);
 
        /*
         *  Set LED support from SCRIPTS.
@@ -973,8 +979,8 @@ static int sym_prepare_setting(struct Scsi_Host *shost, struct sym_hcb *np, stru
  *
  *  Has to be called with interrupts disabled.
  */
-#ifndef CONFIG_SCSI_SYM53C8XX_IOMAPPED
-static int sym_regtest (struct sym_hcb *np)
+#ifdef CONFIG_SCSI_SYM53C8XX_MMIO
+static int sym_regtest(struct sym_hcb *np)
 {
        register volatile u32 data;
        /*
@@ -992,20 +998,25 @@ static int sym_regtest (struct sym_hcb *np)
 #endif
                printf ("CACHE TEST FAILED: reg dstat-sstat2 readback %x.\n",
                        (unsigned) data);
-               return (0x10);
+               return 0x10;
        }
-       return (0);
+       return 0;
+}
+#else
+static inline int sym_regtest(struct sym_hcb *np)
+{
+       return 0;
 }
 #endif
 
-static int sym_snooptest (struct sym_hcb *np)
+static int sym_snooptest(struct sym_hcb *np)
 {
-       u32     sym_rd, sym_wr, sym_bk, host_rd, host_wr, pc, dstat;
-       int     i, err=0;
-#ifndef CONFIG_SCSI_SYM53C8XX_IOMAPPED
-       err |= sym_regtest (np);
-       if (err) return (err);
-#endif
+       u32 sym_rd, sym_wr, sym_bk, host_rd, host_wr, pc, dstat;
+       int i, err;
+
+       err = sym_regtest(np);
+       if (err)
+               return err;
 restart_test:
        /*
         *  Enable Master Parity Checking as we intend 
@@ -1094,7 +1105,7 @@ restart_test:
                err |= 4;
        }
 
-       return (err);
+       return err;
 }
 
 /*
@@ -1464,7 +1475,7 @@ static int sym_prepare_nego(struct sym_hcb *np, struct sym_ccb *cp, u_char *msgp
 /*
  *  Insert a job into the start queue.
  */
-static void sym_put_start_queue(struct sym_hcb *np, struct sym_ccb *cp)
+void sym_put_start_queue(struct sym_hcb *np, struct sym_ccb *cp)
 {
        u_short qidx;
 
@@ -4481,7 +4492,7 @@ static void sym_int_sir (struct sym_hcb *np)
                        switch (np->msgin [2]) {
                        case M_X_MODIFY_DP:
                                if (DEBUG_FLAGS & DEBUG_POINTER)
-                                       sym_print_msg(cp,"modify DP",np->msgin);
+                                       sym_print_msg(cp, NULL, np->msgin);
                                tmp = (np->msgin[3]<<24) + (np->msgin[4]<<16) + 
                                      (np->msgin[5]<<8)  + (np->msgin[6]);
                                sym_modify_dp(np, tp, cp, tmp);
@@ -4508,7 +4519,7 @@ static void sym_int_sir (struct sym_hcb *np)
                 */
                case M_IGN_RESIDUE:
                        if (DEBUG_FLAGS & DEBUG_POINTER)
-                               sym_print_msg(cp,"ign wide residue", np->msgin);
+                               sym_print_msg(cp, NULL, np->msgin);
                        if (cp->host_flags & HF_SENSE)
                                OUTL_DSP(np, SCRIPTA_BA(np, clrack));
                        else
@@ -4597,7 +4608,8 @@ struct sym_ccb *sym_get_ccb (struct sym_hcb *np, struct scsi_cmnd *cmd, u_char t
                         *  Debugging purpose.
                         */
 #ifndef SYM_OPT_HANDLE_DEVICE_QUEUEING
-                       assert(lp->busy_itl == 0);
+                       if (lp->busy_itl != 0)
+                               goto out_free;
 #endif
                        /*
                         *  Allocate resources for tags if not yet.
@@ -4642,7 +4654,8 @@ struct sym_ccb *sym_get_ccb (struct sym_hcb *np, struct scsi_cmnd *cmd, u_char t
                         *  Debugging purpose.
                         */
 #ifndef SYM_OPT_HANDLE_DEVICE_QUEUEING
-                       assert(lp->busy_itl == 0 && lp->busy_itlq == 0);
+                       if (lp->busy_itl != 0 || lp->busy_itlq != 0)
+                               goto out_free;
 #endif
                        /*
                         *  Count this nexus for this LUN.
index 2456090bb2411734b908bcb7a63fc6700899774d..79ab6a177039956cf6da70a12c160982c0f61620 100644 (file)
@@ -1049,6 +1049,8 @@ int sym_reset_scsi_bus(struct sym_hcb *np, int enab_int);
 struct sym_chip *sym_lookup_chip_table(u_short device_id, u_char revision);
 #ifdef SYM_OPT_HANDLE_DEVICE_QUEUEING
 void sym_start_next_ccbs(struct sym_hcb *np, struct sym_lcb *lp, int maxn);
+#else
+void sym_put_start_queue(struct sym_hcb *np, struct sym_ccb *cp);
 #endif
 void sym_start_up(struct sym_hcb *np, int reason);
 void sym_interrupt(struct sym_hcb *np);
index e9c10c0a30fc057c9c47c49caadd3e557bbbd6a9..321a40f33b5042c93db4baac5ef6300c1f7f1f68 100644 (file)
@@ -1057,7 +1057,6 @@ static void m32r_sio_console_write(struct console *co, const char *s,
 {
        struct uart_sio_port *up = &m32r_sio_ports[co->index];
        unsigned int ier;
-       int i;
 
        /*
         *      First save the UER then disable the interrupts
index 93449a1a0065f5caf493097fa15c5616fe6ed221..0b49ff78efc1293f468a6cd0f80e210e5e7c8509 100644 (file)
@@ -11,6 +11,7 @@
 #include <linux/errno.h>
 #include <linux/module.h>
 #include <linux/pci.h>
+#include <linux/dma-mapping.h>
 #include <linux/interrupt.h>
 #include <linux/spinlock.h>
 #include <linux/delay.h>
@@ -619,9 +620,9 @@ static int ioc3_probe(struct pci_dev *pdev, const struct pci_device_id *pci_id)
        pci_set_master(pdev);
 
 #ifdef USE_64BIT_DMA
-        ret = pci_set_dma_mask(pdev, 0xffffffffffffffffULL);
+        ret = pci_set_dma_mask(pdev, DMA_64BIT_MASK);
         if (!ret) {
-                ret = pci_set_consistent_dma_mask(pdev, 0xffffffffffffffffULL);
+                ret = pci_set_consistent_dma_mask(pdev, DMA_64BIT_MASK);
                 if (ret < 0) {
                         printk(KERN_WARNING "%s: Unable to obtain 64 bit DMA "
                                "for consistent allocations\n",
index 830d2c982670db964f0263b1958617342c3f7f85..b38990adf1cdaf7d15b1a3249350e840461bac6a 100644 (file)
@@ -68,7 +68,7 @@
 
 #include "usbatm.h"
 
-#define EAGLEUSBVERSION "ueagle 1.2"
+#define EAGLEUSBVERSION "ueagle 1.3"
 
 
 /*
@@ -243,7 +243,7 @@ enum {
 #define BULK_TIMEOUT 300
 #define CTRL_TIMEOUT 1000
 
-#define ACK_TIMEOUT msecs_to_jiffies(1500)
+#define ACK_TIMEOUT msecs_to_jiffies(3000)
 
 #define UEA_INTR_IFACE_NO      0
 #define UEA_US_IFACE_NO                1
@@ -314,6 +314,10 @@ struct cmv {
         ((d) & 0xff) << 16 |                                           \
         ((a) & 0xff) << 8  |                                           \
         ((b) & 0xff))
+#define GETSA1(a) ((a >> 8) & 0xff)
+#define GETSA2(a) (a & 0xff)
+#define GETSA3(a) ((a >> 24) & 0xff)
+#define GETSA4(a) ((a >> 16) & 0xff)
 
 #define SA_CNTL MAKESA('C', 'N', 'T', 'L')
 #define SA_DIAG MAKESA('D', 'I', 'A', 'G')
@@ -728,11 +732,12 @@ bad2:
        uea_err(INS_TO_USBDEV(sc), "sending DSP block %u failed\n", i);
        return;
 bad1:
-       uea_err(INS_TO_USBDEV(sc), "invalid DSP page %u requested\n",pageno);
+       uea_err(INS_TO_USBDEV(sc), "invalid DSP page %u requested\n", pageno);
 }
 
 static inline void wake_up_cmv_ack(struct uea_softc *sc)
 {
+       BUG_ON(sc->cmv_ack);
        sc->cmv_ack = 1;
        wake_up(&sc->cmv_ack_wait);
 }
@@ -743,6 +748,9 @@ static inline int wait_cmv_ack(struct uea_softc *sc)
                                                   sc->cmv_ack, ACK_TIMEOUT);
        sc->cmv_ack = 0;
 
+       uea_dbg(INS_TO_USBDEV(sc), "wait_event_timeout : %d ms\n",
+                       jiffies_to_msecs(ret));
+
        if (ret < 0)
                return ret;
 
@@ -791,6 +799,12 @@ static int uea_cmv(struct uea_softc *sc,
        struct cmv cmv;
        int ret;
 
+       uea_enters(INS_TO_USBDEV(sc));
+       uea_vdbg(INS_TO_USBDEV(sc), "Function : %d-%d, Address : %c%c%c%c, "
+                       "offset : 0x%04x, data : 0x%08x\n",
+                       FUNCTION_TYPE(function), FUNCTION_SUBTYPE(function),
+                       GETSA1(address), GETSA2(address), GETSA3(address),
+                       GETSA4(address), offset, data);
        /* we send a request, but we expect a reply */
        sc->cmv_function = function | 0x2;
        sc->cmv_idx++;
@@ -808,7 +822,9 @@ static int uea_cmv(struct uea_softc *sc,
        ret = uea_request(sc, UEA_SET_BLOCK, UEA_MPTX_START, CMV_SIZE, &cmv);
        if (ret < 0)
                return ret;
-       return wait_cmv_ack(sc);
+       ret = wait_cmv_ack(sc);
+       uea_leaves(INS_TO_USBDEV(sc));
+       return ret;
 }
 
 static inline int uea_read_cmv(struct uea_softc *sc,
@@ -922,7 +938,7 @@ static int uea_stat(struct uea_softc *sc)
         * we check the status again in order to detect the failure earlier
         */
        if (sc->stats.phy.flags) {
-               uea_dbg(INS_TO_USBDEV(sc), "Stat flag = %d\n",
+               uea_dbg(INS_TO_USBDEV(sc), "Stat flag = 0x%x\n",
                       sc->stats.phy.flags);
                return 0;
        }
@@ -1063,7 +1079,13 @@ static int uea_start_reset(struct uea_softc *sc)
        uea_enters(INS_TO_USBDEV(sc));
        uea_info(INS_TO_USBDEV(sc), "(re)booting started\n");
 
+       /* mask interrupt */
        sc->booting = 1;
+       /* We need to set this here because, a ack timeout could have occured,
+        * but before we start the reboot, the ack occurs and set this to 1.
+        * So we will failed to wait Ready CMV.
+        */
+       sc->cmv_ack = 0;
        UPDATE_ATM_STAT(signal, ATM_PHY_SIG_LOST);
 
        /* reset statistics */
@@ -1089,6 +1111,7 @@ static int uea_start_reset(struct uea_softc *sc)
 
        msleep(1000);
        sc->cmv_function = MAKEFUNCTION(ADSLDIRECTIVE, MODEMREADY);
+       /* demask interrupt */
        sc->booting = 0;
 
        /* start loading DSP */
@@ -1101,6 +1124,8 @@ static int uea_start_reset(struct uea_softc *sc)
        if (ret < 0)
                return ret;
 
+       uea_vdbg(INS_TO_USBDEV(sc), "Ready CMV received\n");
+
        /* Enter in R-IDLE (cmv) until instructed otherwise */
        ret = uea_write_cmv(sc, SA_CNTL, 0, 1);
        if (ret < 0)
@@ -1121,6 +1146,7 @@ static int uea_start_reset(struct uea_softc *sc)
        }
        /* Enter in R-ACT-REQ */
        ret = uea_write_cmv(sc, SA_CNTL, 0, 2);
+       uea_vdbg(INS_TO_USBDEV(sc), "Entering in R-ACT-REQ state\n");
 out:
        release_firmware(cmvs_fw);
        sc->reset = 0;
@@ -1235,6 +1261,7 @@ static void uea_dispatch_cmv(struct uea_softc *sc, struct cmv* cmv)
 
        if (cmv->bFunction == MAKEFUNCTION(ADSLDIRECTIVE, MODEMREADY)) {
                wake_up_cmv_ack(sc);
+               uea_leaves(INS_TO_USBDEV(sc));
                return;
        }
 
@@ -1249,6 +1276,7 @@ static void uea_dispatch_cmv(struct uea_softc *sc, struct cmv* cmv)
        sc->data = sc->data << 16 | sc->data >> 16;
 
        wake_up_cmv_ack(sc);
+       uea_leaves(INS_TO_USBDEV(sc));
        return;
 
 bad2:
@@ -1256,12 +1284,14 @@ bad2:
                        "Function : %d, Subfunction : %d\n",
                        FUNCTION_TYPE(cmv->bFunction),
                        FUNCTION_SUBTYPE(cmv->bFunction));
+       uea_leaves(INS_TO_USBDEV(sc));
        return;
 
 bad1:
        uea_err(INS_TO_USBDEV(sc), "invalid cmv received, "
                        "wPreamble %d, bDirection %d\n",
                        le16_to_cpu(cmv->wPreamble), cmv->bDirection);
+       uea_leaves(INS_TO_USBDEV(sc));
 }
 
 /*
@@ -1346,7 +1376,7 @@ static int uea_boot(struct uea_softc *sc)
        if (ret < 0) {
                uea_err(INS_TO_USBDEV(sc),
                       "urb submition failed with error %d\n", ret);
-               goto err1;
+               goto err;
        }
 
        sc->kthread = kthread_run(uea_kthread, sc, "ueagle-atm");
@@ -1360,10 +1390,10 @@ static int uea_boot(struct uea_softc *sc)
 
 err2:
        usb_kill_urb(sc->urb_int);
-err1:
-       kfree(intr);
 err:
        usb_free_urb(sc->urb_int);
+       sc->urb_int = NULL;
+       kfree(intr);
        uea_leaves(INS_TO_USBDEV(sc));
        return -ENOMEM;
 }
@@ -1508,7 +1538,7 @@ static ssize_t read_##name(struct device *dev,                    \
        int ret = -ENODEV;                                      \
        struct uea_softc *sc;                                   \
                                                                \
-       mutex_lock(&uea_mutex);                                         \
+       mutex_lock(&uea_mutex);                                 \
        sc = dev_to_uea(dev);                                   \
        if (!sc)                                                \
                goto out;                                       \
@@ -1516,7 +1546,7 @@ static ssize_t read_##name(struct device *dev,                    \
        if (reset)                                              \
                sc->stats.phy.name = 0;                         \
 out:                                                           \
-       mutex_unlock(&uea_mutex);                                       \
+       mutex_unlock(&uea_mutex);                               \
        return ret;                                             \
 }                                                              \
                                                                \
@@ -1643,7 +1673,7 @@ static int uea_bind(struct usbatm_data *usbatm, struct usb_interface *intf,
 
        sc = kzalloc(sizeof(struct uea_softc), GFP_KERNEL);
        if (!sc) {
-               uea_err(INS_TO_USBDEV(sc), "uea_init: not enough memory !\n");
+               uea_err(usb, "uea_init: not enough memory !\n");
                return -ENOMEM;
        }
 
index ff03184da403b1bf015277f9993bd500ba73ca32..a08787e253aaa17176cf786621765a39fced7c4e 100644 (file)
@@ -99,4 +99,11 @@ config USB_OTG_WHITELIST
          normal Linux-USB hosts do (other than the warning), and is
          convenient for many stages of product development.
 
+config USB_OTG_BLACKLIST_HUB
+       bool "Disable external hubs"
+       depends on USB_OTG
+       help
+         If you say Y here, then Linux will refuse to enumerate
+         external hubs.  OTG hosts are allowed to reduce hardware
+         and software costs by not supporting external hubs.
 
index 0d2193b692359b1cf17a615fb03d86bab27898bb..66b78404ab34cfd4786d2742cb40c0c1c81de288 100644 (file)
@@ -213,11 +213,9 @@ int usb_hcd_pci_suspend (struct pci_dev *dev, pm_message_t message)
 
        if (hcd->driver->suspend) {
                retval = hcd->driver->suspend(hcd, message);
-               if (retval) {
-                       dev_dbg (&dev->dev, "PCI pre-suspend fail, %d\n",
-                               retval);
+               suspend_report_result(hcd->driver->suspend, retval);
+               if (retval)
                        goto done;
-               }
        }
        synchronize_irq(dev->irq);
 
@@ -263,6 +261,7 @@ int usb_hcd_pci_suspend (struct pci_dev *dev, pm_message_t message)
                 * some device state (e.g. as part of clock reinit).
                 */
                retval = pci_set_power_state (dev, PCI_D3hot);
+               suspend_report_result(pci_set_power_state, retval);
                if (retval == 0) {
                        int wake = device_can_wakeup(&hcd->self.root_hub->dev);
 
index 8e65f7a237e4f68d09a87074bef6e2ed98679dfb..0c87f73f29332d9bbf71e688b97acaa5ac4a668f 100644 (file)
@@ -836,6 +836,13 @@ static int hub_probe(struct usb_interface *intf, const struct usb_device_id *id)
        desc = intf->cur_altsetting;
        hdev = interface_to_usbdev(intf);
 
+#ifdef CONFIG_USB_OTG_BLACKLIST_HUB
+       if (hdev->parent) {
+               dev_warn(&intf->dev, "ignoring external hub\n");
+               return -ENODEV;
+       }
+#endif
+
        /* Some hubs have a subclass of 1, which AFAICT according to the */
        /*  specs is not defined, but it works */
        if ((desc->desc.bInterfaceSubClass != 0) &&
@@ -1022,7 +1029,6 @@ void usb_set_device_state(struct usb_device *udev,
                recursively_mark_NOTATTACHED(udev);
        spin_unlock_irqrestore(&device_state_lock, flags);
 }
-EXPORT_SYMBOL(usb_set_device_state);
 
 
 #ifdef CONFIG_PM
index d7352aa73b5e55be4b16c05087b73ce8723d5bad..b7fdc1cd134a55a7e04636c0e174eb4465892a08 100644 (file)
@@ -1194,7 +1194,6 @@ EXPORT_SYMBOL(usb_disabled);
 EXPORT_SYMBOL_GPL(usb_get_intf);
 EXPORT_SYMBOL_GPL(usb_put_intf);
 
-EXPORT_SYMBOL(usb_alloc_dev);
 EXPORT_SYMBOL(usb_put_dev);
 EXPORT_SYMBOL(usb_get_dev);
 EXPORT_SYMBOL(usb_hub_tt_clear_buffer);
@@ -1208,7 +1207,6 @@ EXPORT_SYMBOL(usb_ifnum_to_if);
 EXPORT_SYMBOL(usb_altnum_to_altsetting);
 
 EXPORT_SYMBOL(usb_reset_device);
-EXPORT_SYMBOL(usb_disconnect);
 
 EXPORT_SYMBOL(__usb_get_extra_descriptor);
 
index d80f71877d684fbddb46fb6f322dec3e7766b3a3..363b2ad74ae60db025df978abe30aea313033cf3 100644 (file)
@@ -69,11 +69,11 @@ choice
           often need board-specific hooks.
 
 config USB_GADGET_NET2280
-       boolean "NetChip 2280"
+       boolean "NetChip 228x"
        depends on PCI
        select USB_GADGET_DUALSPEED
        help
-          NetChip 2280 is a PCI based USB peripheral controller which
+          NetChip 2280 / 2282 is a PCI based USB peripheral controller which
           supports both full and high speed USB 2.0 data transfers.  
           
           It has six configurable endpoints, as well as endpoint zero
index 865858cfd1c2bdce353262dceea3cc4158d53ad3..b8d0b7825bf360c7a446aaa683e4b0a006cfa75d 100644 (file)
@@ -1709,7 +1709,7 @@ static int __devexit at91udc_remove(struct platform_device *dev)
 }
 
 #ifdef CONFIG_PM
-static int at91udc_suspend(struct platform_device *dev, u32 state, u32 level)
+static int at91udc_suspend(struct platform_device *dev, pm_message_t mesg)
 {
        struct at91_udc *udc = platform_get_drvdata(dev);
 
@@ -1731,7 +1731,7 @@ static int at91udc_suspend(struct platform_device *dev, u32 state, u32 level)
        return 0;
 }
 
-static int at91udc_resume(struct platform_device *dev, u32 level)
+static int at91udc_resume(struct platform_device *dev)
 {
        struct at91_udc *udc = platform_get_drvdata(dev);
 
index c3d8e5c5bf2811a42407c084b0b248c0a9f93874..9c4422ac9de41d25db79c6dfd7c5ddb59ae917aa 100644 (file)
@@ -2338,6 +2338,9 @@ autoconf_fail:
                hs_subset_descriptors();
        }
 
+       device_desc.bMaxPacketSize0 = gadget->ep0->maxpacket;
+       usb_gadget_set_selfpowered (gadget);
+
        /* For now RNDIS is always a second config */
        if (rndis)
                device_desc.bNumConfigurations = 2;
@@ -2361,9 +2364,6 @@ autoconf_fail:
 #endif
 #endif /* DUALSPEED */
 
-       device_desc.bMaxPacketSize0 = gadget->ep0->maxpacket;
-       usb_gadget_set_selfpowered (gadget);
-
        if (gadget->is_otg) {
                otg_descriptor.bmAttributes |= USB_OTG_HNP,
                eth_config.bmAttributes |= USB_CONFIG_ATT_WAKEUP;
index cf3be299e3531a3a8de73f9242004d5e5501fc29..6f887478b148a8b2551c81ea1d3a4900586221b3 100644 (file)
  * requirement amounts to two 16K buffers, size configurable by a parameter.
  * Support is included for both full-speed and high-speed operation.
  *
+ * Note that the driver is slightly non-portable in that it assumes a
+ * single memory/DMA buffer will be useable for bulk-in, bulk-out, and
+ * interrupt-in endpoints.  With most device controllers this isn't an
+ * issue, but there may be some with hardware restrictions that prevent
+ * a buffer from being used by more than one endpoint.
+ *
  * Module options:
  *
  *     file=filename[,filename...]
  * setting are not allowed when the medium is loaded.
  *
  * This gadget driver is heavily based on "Gadget Zero" by David Brownell.
+ * The driver's SCSI command interface was based on the "Information
+ * technology - Small Computer System Interface - 2" document from
+ * X3T9.2 Project 375D, Revision 10L, 7-SEP-93, available at
+ * <http://www.t10.org/ftp/t10/drafts/s2/s2-r10l.pdf>.  The single exception
+ * is opcode 0x23 (READ FORMAT CAPACITIES), which was based on the
+ * "Universal Serial Bus Mass Storage Class UFI Command Specification"
+ * document, Revision 1.0, December 14, 1998, available at
+ * <http://www.usb.org/developers/devclass_docs/usbmass-ufi10.pdf>.
  */
 
 
@@ -334,11 +348,9 @@ MODULE_LICENSE("Dual BSD/GPL");
 
 #define MAX_LUNS       8
 
-       /* Arggh!  There should be a module_param_array_named macro! */
-static char            *file[MAX_LUNS];
-static int             ro[MAX_LUNS];
-
 static struct {
+       char            *file[MAX_LUNS];
+       int             ro[MAX_LUNS];
        int             num_filenames;
        int             num_ros;
        unsigned int    nluns;
@@ -370,10 +382,11 @@ static struct {
        };
 
 
-module_param_array(file, charp, &mod_data.num_filenames, S_IRUGO);
+module_param_array_named(file, mod_data.file, charp, &mod_data.num_filenames,
+               S_IRUGO);
 MODULE_PARM_DESC(file, "names of backing files or devices");
 
-module_param_array(ro, bool, &mod_data.num_ros, S_IRUGO);
+module_param_array_named(ro, mod_data.ro, bool, &mod_data.num_ros, S_IRUGO);
 MODULE_PARM_DESC(ro, "true to force read-only");
 
 module_param_named(luns, mod_data.nluns, uint, S_IRUGO);
@@ -1795,6 +1808,7 @@ static int do_write(struct fsg_dev *fsg)
                         * the bulk-out maxpacket size */
                        bh->outreq->length = bh->bulk_out_intended_length =
                                        amount;
+                       bh->outreq->short_not_ok = 1;
                        start_transfer(fsg, fsg->bulk_out, bh->outreq,
                                        &bh->outreq_busy, &bh->state);
                        fsg->next_buffhd_to_fill = bh->next;
@@ -2398,6 +2412,7 @@ static int throw_away_data(struct fsg_dev *fsg)
                         * the bulk-out maxpacket size */
                        bh->outreq->length = bh->bulk_out_intended_length =
                                        amount;
+                       bh->outreq->short_not_ok = 1;
                        start_transfer(fsg, fsg->bulk_out, bh->outreq,
                                        &bh->outreq_busy, &bh->state);
                        fsg->next_buffhd_to_fill = bh->next;
@@ -3029,6 +3044,7 @@ static int get_next_command(struct fsg_dev *fsg)
 
                /* Queue a request to read a Bulk-only CBW */
                set_bulk_out_req_length(fsg, bh, USB_BULK_CB_WRAP_LEN);
+               bh->outreq->short_not_ok = 1;
                start_transfer(fsg, fsg->bulk_out, bh->outreq,
                                &bh->outreq_busy, &bh->state);
 
@@ -3859,7 +3875,7 @@ static int __init fsg_bind(struct usb_gadget *gadget)
 
        for (i = 0; i < fsg->nluns; ++i) {
                curlun = &fsg->luns[i];
-               curlun->ro = ro[i];
+               curlun->ro = mod_data.ro[i];
                curlun->dev.parent = &gadget->dev;
                curlun->dev.driver = &fsg_driver.driver;
                dev_set_drvdata(&curlun->dev, fsg);
@@ -3876,8 +3892,9 @@ static int __init fsg_bind(struct usb_gadget *gadget)
                        kref_get(&fsg->ref);
                }
 
-               if (file[i] && *file[i]) {
-                       if ((rc = open_backing_file(curlun, file[i])) != 0)
+               if (mod_data.file[i] && *mod_data.file[i]) {
+                       if ((rc = open_backing_file(curlun,
+                                       mod_data.file[i])) != 0)
                                goto out;
                } else if (!mod_data.removable) {
                        ERROR(fsg, "no file given for LUN%d\n", i);
@@ -3953,6 +3970,9 @@ static int __init fsg_bind(struct usb_gadget *gadget)
        for (i = 0; i < NUM_BUFFERS; ++i) {
                struct fsg_buffhd       *bh = &fsg->buffhds[i];
 
+               /* Allocate for the bulk-in endpoint.  We assume that
+                * the buffer will also work with the bulk-out (and
+                * interrupt-in) endpoint. */
                bh->buf = usb_ep_alloc_buffer(fsg->bulk_in, mod_data.buflen,
                                &bh->dma, GFP_KERNEL);
                if (!bh->buf)
index c4081407171f8e7c8b01ea01a70b8bf3355ad003..aa80f0910720b2006e0b9dde609ba7f7f5cb49b4 100644 (file)
 #define gadget_is_musbhsfc(g)  0
 #endif
 
-/* Mentor high speed "dual role" controller, peripheral mode */
-#ifdef CONFIG_USB_GADGET_MUSBHDRC
-#define gadget_is_musbhdrc(g)  !strcmp("musbhdrc_udc", (g)->name)
+/* Mentor high speed "dual role" controller, in peripheral role */
+#ifdef CONFIG_USB_GADGET_MUSB_HDRC
+#define gadget_is_musbhdrc(g)  !strcmp("musb_hdrc", (g)->name)
 #else
 #define gadget_is_musbhdrc(g)  0
 #endif
index 3f618ce6998dbb1b92a604784d96de0b9df29ba1..42b457030b0310420931fc481e6f2d7316f87fd3 100644 (file)
@@ -810,7 +810,7 @@ ep_config (struct file *fd, const char __user *buf, size_t len, loff_t *ptr)
                if (value == 0)
                        data->state = STATE_EP_ENABLED;
                break;
-#ifdef HIGHSPEED
+#ifdef CONFIG_USB_GADGET_DUALSPEED
        case USB_SPEED_HIGH:
                /* fails if caller didn't provide that descriptor... */
                value = usb_ep_enable (ep, &data->hs_desc);
@@ -982,7 +982,7 @@ ep0_read (struct file *fd, char __user *buf, size_t len, loff_t *ptr)
                        /* assume that was SET_CONFIGURATION */
                        if (dev->current_config) {
                                unsigned power;
-#ifdef HIGHSPEED
+#ifdef CONFIG_USB_GADGET_DUALSPEED
                                if (dev->gadget->speed == USB_SPEED_HIGH)
                                        power = dev->hs_config->bMaxPower;
                                else
@@ -1262,7 +1262,7 @@ static struct file_operations ep0_io_operations = {
  * Unrecognized ep0 requests may be handled in user space.
  */
 
-#ifdef HIGHSPEED
+#ifdef CONFIG_USB_GADGET_DUALSPEED
 static void make_qualifier (struct dev_data *dev)
 {
        struct usb_qualifier_descriptor         qual;
@@ -1291,7 +1291,7 @@ static int
 config_buf (struct dev_data *dev, u8 type, unsigned index)
 {
        int             len;
-#ifdef HIGHSPEED
+#ifdef CONFIG_USB_GADGET_DUALSPEED
        int             hs;
 #endif
 
@@ -1299,7 +1299,7 @@ config_buf (struct dev_data *dev, u8 type, unsigned index)
        if (index > 0)
                return -EINVAL;
 
-#ifdef HIGHSPEED
+#ifdef CONFIG_USB_GADGET_DUALSPEED
        hs = (dev->gadget->speed == USB_SPEED_HIGH);
        if (type == USB_DT_OTHER_SPEED_CONFIG)
                hs = !hs;
@@ -1335,12 +1335,12 @@ gadgetfs_setup (struct usb_gadget *gadget, const struct usb_ctrlrequest *ctrl)
                dev->state = STATE_CONNECTED;
                dev->dev->bMaxPacketSize0 = gadget->ep0->maxpacket;
 
-#ifdef HIGHSPEED
+#ifdef CONFIG_USB_GADGET_DUALSPEED
                if (gadget->speed == USB_SPEED_HIGH && dev->hs_config == 0) {
                        ERROR (dev, "no high speed config??\n");
                        return -EINVAL;
                }
-#endif /* HIGHSPEED */
+#endif /* CONFIG_USB_GADGET_DUALSPEED */
 
                INFO (dev, "connected\n");
                event = next_event (dev, GADGETFS_CONNECT);
@@ -1352,11 +1352,11 @@ gadgetfs_setup (struct usb_gadget *gadget, const struct usb_ctrlrequest *ctrl)
                        /* ... down_trylock (&data->lock) ... */
                        if (data->state != STATE_EP_DEFER_ENABLE)
                                continue;
-#ifdef HIGHSPEED
+#ifdef CONFIG_USB_GADGET_DUALSPEED
                        if (gadget->speed == USB_SPEED_HIGH)
                                value = usb_ep_enable (ep, &data->hs_desc);
                        else
-#endif /* HIGHSPEED */
+#endif /* CONFIG_USB_GADGET_DUALSPEED */
                                value = usb_ep_enable (ep, &data->desc);
                        if (value) {
                                ERROR (dev, "deferred %s enable --> %d\n",
@@ -1391,7 +1391,7 @@ gadgetfs_setup (struct usb_gadget *gadget, const struct usb_ctrlrequest *ctrl)
                        value = min (w_length, (u16) sizeof *dev->dev);
                        req->buf = dev->dev;
                        break;
-#ifdef HIGHSPEED
+#ifdef CONFIG_USB_GADGET_DUALSPEED
                case USB_DT_DEVICE_QUALIFIER:
                        if (!dev->hs_config)
                                break;
@@ -1428,7 +1428,7 @@ gadgetfs_setup (struct usb_gadget *gadget, const struct usb_ctrlrequest *ctrl)
                        // user mode expected to disable endpoints
                } else {
                        u8      config, power;
-#ifdef HIGHSPEED
+#ifdef CONFIG_USB_GADGET_DUALSPEED
                        if (gadget->speed == USB_SPEED_HIGH) {
                                config = dev->hs_config->bConfigurationValue;
                                power = dev->hs_config->bMaxPower;
@@ -1728,7 +1728,7 @@ gadgetfs_suspend (struct usb_gadget *gadget)
 }
 
 static struct usb_gadget_driver gadgetfs_driver = {
-#ifdef HIGHSPEED
+#ifdef CONFIG_USB_GADGET_DUALSPEED
        .speed          = USB_SPEED_HIGH,
 #else
        .speed          = USB_SPEED_FULL,
index fb73dc100535c80d2e16de0ea68f62e533e5ab84..6a4b93ad10828da994dd9322b6d87e5345170680 100644 (file)
@@ -26,6 +26,8 @@
  * Copyright (C) 2003 David Brownell
  * Copyright (C) 2003-2005 PLX Technology, Inc.
  *
+ * Modified Seth Levy 2005 PLX Technology, Inc. to provide compatibility with 2282 chip
+ *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License as published by
  * the Free Software Foundation; either version 2 of the License, or
@@ -71,8 +73,8 @@
 #include <asm/unaligned.h>
 
 
-#define        DRIVER_DESC             "PLX NET2280 USB Peripheral Controller"
-#define        DRIVER_VERSION          "2005 Feb 03"
+#define        DRIVER_DESC             "PLX NET228x USB Peripheral Controller"
+#define        DRIVER_VERSION          "2005 Sept 27"
 
 #define        DMA_ADDR_INVALID        (~(dma_addr_t)0)
 #define        EP_DONTUSE              13      /* nonzero */
@@ -118,7 +120,7 @@ module_param (fifo_mode, ushort, 0644);
 /* enable_suspend -- When enabled, the driver will respond to
  * USB suspend requests by powering down the NET2280.  Otherwise,
  * USB suspend requests will be ignored.  This is acceptible for
- * self-powered devices, and helps avoid some quirks.
+ * self-powered devices
  */
 static int enable_suspend = 0;
 
@@ -223,6 +225,11 @@ net2280_enable (struct usb_ep *_ep, const struct usb_endpoint_descriptor *desc)
        ep->is_in = (tmp & USB_DIR_IN) != 0;
        if (!ep->is_in)
                writel ((1 << SET_NAK_OUT_PACKETS), &ep->regs->ep_rsp);
+       else if (dev->pdev->device != 0x2280) {
+               /* Added for 2282, Don't use nak packets on an in endpoint, this was ignored on 2280 */
+               writel ((1 << CLEAR_NAK_OUT_PACKETS)
+                       | (1 << CLEAR_NAK_OUT_PACKETS_MODE), &ep->regs->ep_rsp);
+       }
 
        writel (tmp, &ep->regs->ep_cfg);
 
@@ -232,8 +239,9 @@ net2280_enable (struct usb_ep *_ep, const struct usb_endpoint_descriptor *desc)
                writel (tmp, &dev->regs->pciirqenb0);
 
                tmp = (1 << DATA_PACKET_RECEIVED_INTERRUPT_ENABLE)
-                       | (1 << DATA_PACKET_TRANSMITTED_INTERRUPT_ENABLE)
-                       | readl (&ep->regs->ep_irqenb);
+                       | (1 << DATA_PACKET_TRANSMITTED_INTERRUPT_ENABLE);
+               if (dev->pdev->device == 0x2280)
+                       tmp |= readl (&ep->regs->ep_irqenb);
                writel (tmp, &ep->regs->ep_irqenb);
        } else {                                /* dma, per-request */
                tmp = (1 << (8 + ep->num));     /* completion */
@@ -314,10 +322,18 @@ static void ep_reset (struct net2280_regs __iomem *regs, struct net2280_ep *ep)
        /* init to our chosen defaults, notably so that we NAK OUT
         * packets until the driver queues a read (+note erratum 0112)
         */
-       tmp = (1 << SET_NAK_OUT_PACKETS_MODE)
+       if (!ep->is_in || ep->dev->pdev->device == 0x2280) {
+               tmp = (1 << SET_NAK_OUT_PACKETS_MODE)
                | (1 << SET_NAK_OUT_PACKETS)
                | (1 << CLEAR_EP_HIDE_STATUS_PHASE)
                | (1 << CLEAR_INTERRUPT_MODE);
+       } else {
+               /* added for 2282 */
+               tmp = (1 << CLEAR_NAK_OUT_PACKETS_MODE)
+               | (1 << CLEAR_NAK_OUT_PACKETS)
+               | (1 << CLEAR_EP_HIDE_STATUS_PHASE)
+               | (1 << CLEAR_INTERRUPT_MODE);
+       }
 
        if (ep->num != 0) {
                tmp |= (1 << CLEAR_ENDPOINT_TOGGLE)
@@ -326,14 +342,18 @@ static void ep_reset (struct net2280_regs __iomem *regs, struct net2280_ep *ep)
        writel (tmp, &ep->regs->ep_rsp);
 
        /* scrub most status bits, and flush any fifo state */
-       writel (  (1 << TIMEOUT)
+       if (ep->dev->pdev->device == 0x2280)
+               tmp = (1 << FIFO_OVERFLOW)
+                       | (1 << FIFO_UNDERFLOW);
+       else
+               tmp = 0;
+
+       writel (tmp | (1 << TIMEOUT)
                | (1 << USB_STALL_SENT)
                | (1 << USB_IN_NAK_SENT)
                | (1 << USB_IN_ACK_RCVD)
                | (1 << USB_OUT_PING_NAK_SENT)
                | (1 << USB_OUT_ACK_SENT)
-               | (1 << FIFO_OVERFLOW)
-               | (1 << FIFO_UNDERFLOW)
                | (1 << FIFO_FLUSH)
                | (1 << SHORT_PACKET_OUT_DONE_INTERRUPT)
                | (1 << SHORT_PACKET_TRANSFERRED_INTERRUPT)
@@ -718,7 +738,7 @@ fill_dma_desc (struct net2280_ep *ep, struct net2280_request *req, int valid)
         */
        if (ep->is_in)
                dmacount |= (1 << DMA_DIRECTION);
-       else if ((dmacount % ep->ep.maxpacket) != 0)
+       if ((!ep->is_in && (dmacount % ep->ep.maxpacket) != 0) || ep->dev->pdev->device != 0x2280)
                dmacount |= (1 << END_OF_CHAIN);
 
        req->valid = valid;
@@ -760,9 +780,12 @@ static inline void stop_dma (struct net2280_dma_regs __iomem *dma)
 static void start_queue (struct net2280_ep *ep, u32 dmactl, u32 td_dma)
 {
        struct net2280_dma_regs __iomem *dma = ep->dma;
+       unsigned int tmp = (1 << VALID_BIT) | (ep->is_in << DMA_DIRECTION);
 
-       writel ((1 << VALID_BIT) | (ep->is_in << DMA_DIRECTION),
-                       &dma->dmacount);
+       if (ep->dev->pdev->device != 0x2280)
+               tmp |= (1 << END_OF_CHAIN);
+
+       writel (tmp, &dma->dmacount);
        writel (readl (&dma->dmastat), &dma->dmastat);
 
        writel (td_dma, &dma->dmadesc);
@@ -2110,7 +2133,11 @@ static void handle_ep_small (struct net2280_ep *ep)
        VDEBUG (ep->dev, "%s ack ep_stat %08x, req %p\n",
                        ep->ep.name, t, req ? &req->req : 0);
 #endif
-       writel (t & ~(1 << NAK_OUT_PACKETS), &ep->regs->ep_stat);
+       if (!ep->is_in || ep->dev->pdev->device == 0x2280)
+               writel (t & ~(1 << NAK_OUT_PACKETS), &ep->regs->ep_stat);
+       else
+               /* Added for 2282 */
+               writel (t, &ep->regs->ep_stat);
 
        /* for ep0, monitor token irqs to catch data stage length errors
         * and to synchronize on status.
@@ -2214,7 +2241,8 @@ static void handle_ep_small (struct net2280_ep *ep)
                        if (likely (req)) {
                                req->td->dmacount = 0;
                                t = readl (&ep->regs->ep_avail);
-                               dma_done (ep, req, count, t);
+                               dma_done (ep, req, count,
+                                       (ep->out_overflow || t) ? -EOVERFLOW : 0);
                        }
 
                        /* also flush to prevent erratum 0106 trouble */
@@ -2337,7 +2365,7 @@ static void handle_stat0_irqs (struct net2280 *dev, u32 stat)
                        u32                     raw [2];
                        struct usb_ctrlrequest  r;
                } u;
-               int                             tmp = 0;
+               int                             tmp;
                struct net2280_request          *req;
 
                if (dev->gadget.speed == USB_SPEED_UNKNOWN) {
@@ -2364,14 +2392,19 @@ static void handle_stat0_irqs (struct net2280 *dev, u32 stat)
                }
                ep->stopped = 0;
                dev->protocol_stall = 0;
-               writel (  (1 << TIMEOUT)
+
+               if (ep->dev->pdev->device == 0x2280)
+                       tmp = (1 << FIFO_OVERFLOW)
+                               | (1 << FIFO_UNDERFLOW);
+               else
+                       tmp = 0;
+
+               writel (tmp | (1 << TIMEOUT)
                        | (1 << USB_STALL_SENT)
                        | (1 << USB_IN_NAK_SENT)
                        | (1 << USB_IN_ACK_RCVD)
                        | (1 << USB_OUT_PING_NAK_SENT)
                        | (1 << USB_OUT_ACK_SENT)
-                       | (1 << FIFO_OVERFLOW)
-                       | (1 << FIFO_UNDERFLOW)
                        | (1 << SHORT_PACKET_OUT_DONE_INTERRUPT)
                        | (1 << SHORT_PACKET_TRANSFERRED_INTERRUPT)
                        | (1 << DATA_PACKET_RECEIVED_INTERRUPT)
@@ -2385,6 +2418,8 @@ static void handle_stat0_irqs (struct net2280 *dev, u32 stat)
                cpu_to_le32s (&u.raw [0]);
                cpu_to_le32s (&u.raw [1]);
 
+               tmp = 0;
+
 #define        w_value         le16_to_cpup (&u.r.wValue)
 #define        w_index         le16_to_cpup (&u.r.wIndex)
 #define        w_length        le16_to_cpup (&u.r.wLength)
@@ -2594,10 +2629,17 @@ static void handle_stat1_irqs (struct net2280 *dev, u32 stat)
                writel (stat, &dev->regs->irqstat1);
 
        /* some status we can just ignore */
-       stat &= ~((1 << CONTROL_STATUS_INTERRUPT)
-                       | (1 << SUSPEND_REQUEST_INTERRUPT)
-                       | (1 << RESUME_INTERRUPT)
-                       | (1 << SOF_INTERRUPT));
+       if (dev->pdev->device == 0x2280)
+               stat &= ~((1 << CONTROL_STATUS_INTERRUPT)
+                         | (1 << SUSPEND_REQUEST_INTERRUPT)
+                         | (1 << RESUME_INTERRUPT)
+                         | (1 << SOF_INTERRUPT));
+       else
+               stat &= ~((1 << CONTROL_STATUS_INTERRUPT)
+                         | (1 << RESUME_INTERRUPT)
+                         | (1 << SOF_DOWN_INTERRUPT)
+                         | (1 << SOF_INTERRUPT));
+
        if (!stat)
                return;
        // DEBUG (dev, "irqstat1 %08x\n", stat);
@@ -2939,6 +2981,13 @@ static struct pci_device_id pci_ids [] = { {
        .device =       0x2280,
        .subvendor =    PCI_ANY_ID,
        .subdevice =    PCI_ANY_ID,
+}, {
+       .class =        ((PCI_CLASS_SERIAL_USB << 8) | 0xfe),
+       .class_mask =   ~0,
+       .vendor =       0x17cc,
+       .device =       0x2282,
+       .subvendor =    PCI_ANY_ID,
+       .subdevice =    PCI_ANY_ID,
 
 }, { /* end: all zeroes */ }
 };
index fff4509cf340d2d62c20bb91bd5fb136086d14da..957d6df3401509c7c3c6af1b31874cf5fadf50fa 100644 (file)
  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
  */
 
-/*-------------------------------------------------------------------------*/
-
-/* NET2280 MEMORY MAPPED REGISTERS
- *
- * The register layout came from the chip documentation, and the bit
- * number definitions were extracted from chip specification.
- *
- * Use the shift operator ('<<') to build bit masks, with readl/writel
- * to access the registers through PCI.
- */
-
-/* main registers, BAR0 + 0x0000 */
-struct net2280_regs {
-       // offset 0x0000
-       u32             devinit;
-#define     LOCAL_CLOCK_FREQUENCY                               8
-#define     FORCE_PCI_RESET                                     7
-#define     PCI_ID                                              6
-#define     PCI_ENABLE                                          5
-#define     FIFO_SOFT_RESET                                     4
-#define     CFG_SOFT_RESET                                      3
-#define     PCI_SOFT_RESET                                      2
-#define     USB_SOFT_RESET                                      1
-#define     M8051_RESET                                         0
-       u32             eectl;
-#define     EEPROM_ADDRESS_WIDTH                                23
-#define     EEPROM_CHIP_SELECT_ACTIVE                           22
-#define     EEPROM_PRESENT                                      21
-#define     EEPROM_VALID                                        20
-#define     EEPROM_BUSY                                         19
-#define     EEPROM_CHIP_SELECT_ENABLE                           18
-#define     EEPROM_BYTE_READ_START                              17
-#define     EEPROM_BYTE_WRITE_START                             16
-#define     EEPROM_READ_DATA                                    8
-#define     EEPROM_WRITE_DATA                                   0
-       u32             eeclkfreq;
-       u32             _unused0;
-       // offset 0x0010
-
-       u32             pciirqenb0;             /* interrupt PCI master ... */
-#define     SETUP_PACKET_INTERRUPT_ENABLE                       7
-#define     ENDPOINT_F_INTERRUPT_ENABLE                         6
-#define     ENDPOINT_E_INTERRUPT_ENABLE                         5
-#define     ENDPOINT_D_INTERRUPT_ENABLE                         4
-#define     ENDPOINT_C_INTERRUPT_ENABLE                         3
-#define     ENDPOINT_B_INTERRUPT_ENABLE                         2
-#define     ENDPOINT_A_INTERRUPT_ENABLE                         1
-#define     ENDPOINT_0_INTERRUPT_ENABLE                         0
-       u32             pciirqenb1;
-#define     PCI_INTERRUPT_ENABLE                                31
-#define     POWER_STATE_CHANGE_INTERRUPT_ENABLE                 27
-#define     PCI_ARBITER_TIMEOUT_INTERRUPT_ENABLE                26
-#define     PCI_PARITY_ERROR_INTERRUPT_ENABLE                   25
-#define     PCI_MASTER_ABORT_RECEIVED_INTERRUPT_ENABLE          20
-#define     PCI_TARGET_ABORT_RECEIVED_INTERRUPT_ENABLE          19
-#define     PCI_TARGET_ABORT_ASSERTED_INTERRUPT_ENABLE          18
-#define     PCI_RETRY_ABORT_INTERRUPT_ENABLE                    17
-#define     PCI_MASTER_CYCLE_DONE_INTERRUPT_ENABLE              16
-#define     GPIO_INTERRUPT_ENABLE                               13
-#define     DMA_D_INTERRUPT_ENABLE                              12
-#define     DMA_C_INTERRUPT_ENABLE                              11
-#define     DMA_B_INTERRUPT_ENABLE                              10
-#define     DMA_A_INTERRUPT_ENABLE                              9
-#define     EEPROM_DONE_INTERRUPT_ENABLE                        8
-#define     VBUS_INTERRUPT_ENABLE                               7
-#define     CONTROL_STATUS_INTERRUPT_ENABLE                     6
-#define     ROOT_PORT_RESET_INTERRUPT_ENABLE                    4
-#define     SUSPEND_REQUEST_INTERRUPT_ENABLE                    3
-#define     SUSPEND_REQUEST_CHANGE_INTERRUPT_ENABLE             2
-#define     RESUME_INTERRUPT_ENABLE                             1
-#define     SOF_INTERRUPT_ENABLE                                0
-       u32             cpu_irqenb0;            /* ... or onboard 8051 */
-#define     SETUP_PACKET_INTERRUPT_ENABLE                       7
-#define     ENDPOINT_F_INTERRUPT_ENABLE                         6
-#define     ENDPOINT_E_INTERRUPT_ENABLE                         5
-#define     ENDPOINT_D_INTERRUPT_ENABLE                         4
-#define     ENDPOINT_C_INTERRUPT_ENABLE                         3
-#define     ENDPOINT_B_INTERRUPT_ENABLE                         2
-#define     ENDPOINT_A_INTERRUPT_ENABLE                         1
-#define     ENDPOINT_0_INTERRUPT_ENABLE                         0
-       u32             cpu_irqenb1;
-#define     CPU_INTERRUPT_ENABLE                                31
-#define     POWER_STATE_CHANGE_INTERRUPT_ENABLE                 27
-#define     PCI_ARBITER_TIMEOUT_INTERRUPT_ENABLE                26
-#define     PCI_PARITY_ERROR_INTERRUPT_ENABLE                   25
-#define     PCI_INTA_INTERRUPT_ENABLE                           24
-#define     PCI_PME_INTERRUPT_ENABLE                            23
-#define     PCI_SERR_INTERRUPT_ENABLE                           22
-#define     PCI_PERR_INTERRUPT_ENABLE                           21
-#define     PCI_MASTER_ABORT_RECEIVED_INTERRUPT_ENABLE          20
-#define     PCI_TARGET_ABORT_RECEIVED_INTERRUPT_ENABLE          19
-#define     PCI_RETRY_ABORT_INTERRUPT_ENABLE                    17
-#define     PCI_MASTER_CYCLE_DONE_INTERRUPT_ENABLE              16
-#define     GPIO_INTERRUPT_ENABLE                               13
-#define     DMA_D_INTERRUPT_ENABLE                              12
-#define     DMA_C_INTERRUPT_ENABLE                              11
-#define     DMA_B_INTERRUPT_ENABLE                              10
-#define     DMA_A_INTERRUPT_ENABLE                              9
-#define     EEPROM_DONE_INTERRUPT_ENABLE                        8
-#define     VBUS_INTERRUPT_ENABLE                               7
-#define     CONTROL_STATUS_INTERRUPT_ENABLE                     6
-#define     ROOT_PORT_RESET_INTERRUPT_ENABLE                    4
-#define     SUSPEND_REQUEST_INTERRUPT_ENABLE                    3
-#define     SUSPEND_REQUEST_CHANGE_INTERRUPT_ENABLE             2
-#define     RESUME_INTERRUPT_ENABLE                             1
-#define     SOF_INTERRUPT_ENABLE                                0
-
-       // offset 0x0020
-       u32             _unused1;
-       u32             usbirqenb1;
-#define     USB_INTERRUPT_ENABLE                                31
-#define     POWER_STATE_CHANGE_INTERRUPT_ENABLE                 27
-#define     PCI_ARBITER_TIMEOUT_INTERRUPT_ENABLE                26
-#define     PCI_PARITY_ERROR_INTERRUPT_ENABLE                   25
-#define     PCI_INTA_INTERRUPT_ENABLE                           24
-#define     PCI_PME_INTERRUPT_ENABLE                            23
-#define     PCI_SERR_INTERRUPT_ENABLE                           22
-#define     PCI_PERR_INTERRUPT_ENABLE                           21
-#define     PCI_MASTER_ABORT_RECEIVED_INTERRUPT_ENABLE          20
-#define     PCI_TARGET_ABORT_RECEIVED_INTERRUPT_ENABLE          19
-#define     PCI_RETRY_ABORT_INTERRUPT_ENABLE                    17
-#define     PCI_MASTER_CYCLE_DONE_INTERRUPT_ENABLE              16
-#define     GPIO_INTERRUPT_ENABLE                               13
-#define     DMA_D_INTERRUPT_ENABLE                              12
-#define     DMA_C_INTERRUPT_ENABLE                              11
-#define     DMA_B_INTERRUPT_ENABLE                              10
-#define     DMA_A_INTERRUPT_ENABLE                              9
-#define     EEPROM_DONE_INTERRUPT_ENABLE                        8
-#define     VBUS_INTERRUPT_ENABLE                               7
-#define     CONTROL_STATUS_INTERRUPT_ENABLE                     6
-#define     ROOT_PORT_RESET_INTERRUPT_ENABLE                    4
-#define     SUSPEND_REQUEST_INTERRUPT_ENABLE                    3
-#define     SUSPEND_REQUEST_CHANGE_INTERRUPT_ENABLE             2
-#define     RESUME_INTERRUPT_ENABLE                             1
-#define     SOF_INTERRUPT_ENABLE                                0
-       u32             irqstat0;
-#define     INTA_ASSERTED                                       12
-#define     SETUP_PACKET_INTERRUPT                              7
-#define     ENDPOINT_F_INTERRUPT                                6
-#define     ENDPOINT_E_INTERRUPT                                5
-#define     ENDPOINT_D_INTERRUPT                                4
-#define     ENDPOINT_C_INTERRUPT                                3
-#define     ENDPOINT_B_INTERRUPT                                2
-#define     ENDPOINT_A_INTERRUPT                                1
-#define     ENDPOINT_0_INTERRUPT                                0
-       u32             irqstat1;
-#define     POWER_STATE_CHANGE_INTERRUPT                        27
-#define     PCI_ARBITER_TIMEOUT_INTERRUPT                       26
-#define     PCI_PARITY_ERROR_INTERRUPT                          25
-#define     PCI_INTA_INTERRUPT                                  24
-#define     PCI_PME_INTERRUPT                                   23
-#define     PCI_SERR_INTERRUPT                                  22
-#define     PCI_PERR_INTERRUPT                                  21
-#define     PCI_MASTER_ABORT_RECEIVED_INTERRUPT                 20
-#define     PCI_TARGET_ABORT_RECEIVED_INTERRUPT                 19
-#define     PCI_RETRY_ABORT_INTERRUPT                           17
-#define     PCI_MASTER_CYCLE_DONE_INTERRUPT                     16
-#define     GPIO_INTERRUPT                                      13
-#define     DMA_D_INTERRUPT                                     12
-#define     DMA_C_INTERRUPT                                     11
-#define     DMA_B_INTERRUPT                                     10
-#define     DMA_A_INTERRUPT                                     9
-#define     EEPROM_DONE_INTERRUPT                               8
-#define     VBUS_INTERRUPT                                      7
-#define     CONTROL_STATUS_INTERRUPT                            6
-#define     ROOT_PORT_RESET_INTERRUPT                           4
-#define     SUSPEND_REQUEST_INTERRUPT                           3
-#define     SUSPEND_REQUEST_CHANGE_INTERRUPT                    2
-#define     RESUME_INTERRUPT                                    1
-#define     SOF_INTERRUPT                                       0
-       // offset 0x0030
-       u32             idxaddr;
-       u32             idxdata;
-       u32             fifoctl;
-#define     PCI_BASE2_RANGE                                     16
-#define     IGNORE_FIFO_AVAILABILITY                            3
-#define     PCI_BASE2_SELECT                                    2
-#define     FIFO_CONFIGURATION_SELECT                           0
-       u32             _unused2;
-       // offset 0x0040
-       u32             memaddr;
-#define     START                                               28
-#define     DIRECTION                                           27
-#define     FIFO_DIAGNOSTIC_SELECT                              24
-#define     MEMORY_ADDRESS                                      0
-       u32             memdata0;
-       u32             memdata1;
-       u32             _unused3;
-       // offset 0x0050
-       u32             gpioctl;
-#define     GPIO3_LED_SELECT                                    12
-#define     GPIO3_INTERRUPT_ENABLE                              11
-#define     GPIO2_INTERRUPT_ENABLE                              10
-#define     GPIO1_INTERRUPT_ENABLE                              9
-#define     GPIO0_INTERRUPT_ENABLE                              8
-#define     GPIO3_OUTPUT_ENABLE                                 7
-#define     GPIO2_OUTPUT_ENABLE                                 6
-#define     GPIO1_OUTPUT_ENABLE                                 5
-#define     GPIO0_OUTPUT_ENABLE                                 4
-#define     GPIO3_DATA                                          3
-#define     GPIO2_DATA                                          2
-#define     GPIO1_DATA                                          1
-#define     GPIO0_DATA                                          0
-       u32             gpiostat;
-#define     GPIO3_INTERRUPT                                     3
-#define     GPIO2_INTERRUPT                                     2
-#define     GPIO1_INTERRUPT                                     1
-#define     GPIO0_INTERRUPT                                     0
-} __attribute__ ((packed));
-
-/* usb control, BAR0 + 0x0080 */
-struct net2280_usb_regs {
-       // offset 0x0080
-       u32             stdrsp;
-#define     STALL_UNSUPPORTED_REQUESTS                          31
-#define     SET_TEST_MODE                                       16
-#define     GET_OTHER_SPEED_CONFIGURATION                       15
-#define     GET_DEVICE_QUALIFIER                                14
-#define     SET_ADDRESS                                         13
-#define     ENDPOINT_SET_CLEAR_HALT                             12
-#define     DEVICE_SET_CLEAR_DEVICE_REMOTE_WAKEUP               11
-#define     GET_STRING_DESCRIPTOR_2                             10
-#define     GET_STRING_DESCRIPTOR_1                             9
-#define     GET_STRING_DESCRIPTOR_0                             8
-#define     GET_SET_INTERFACE                                   6
-#define     GET_SET_CONFIGURATION                               5
-#define     GET_CONFIGURATION_DESCRIPTOR                        4
-#define     GET_DEVICE_DESCRIPTOR                               3
-#define     GET_ENDPOINT_STATUS                                 2
-#define     GET_INTERFACE_STATUS                                1
-#define     GET_DEVICE_STATUS                                   0
-       u32             prodvendid;
-#define     PRODUCT_ID                                          16
-#define     VENDOR_ID                                           0
-       u32             relnum;
-       u32             usbctl;
-#define     SERIAL_NUMBER_INDEX                                 16
-#define     PRODUCT_ID_STRING_ENABLE                            13
-#define     VENDOR_ID_STRING_ENABLE                             12
-#define     USB_ROOT_PORT_WAKEUP_ENABLE                         11
-#define     VBUS_PIN                                            10
-#define     TIMED_DISCONNECT                                    9
-#define     SUSPEND_IMMEDIATELY                                 7
-#define     SELF_POWERED_USB_DEVICE                             6
-#define     REMOTE_WAKEUP_SUPPORT                               5
-#define     PME_POLARITY                                        4
-#define     USB_DETECT_ENABLE                                   3
-#define     PME_WAKEUP_ENABLE                                   2
-#define     DEVICE_REMOTE_WAKEUP_ENABLE                         1
-#define     SELF_POWERED_STATUS                                 0
-       // offset 0x0090
-       u32             usbstat;
-#define     HIGH_SPEED                                          7
-#define     FULL_SPEED                                          6
-#define     GENERATE_RESUME                                     5
-#define     GENERATE_DEVICE_REMOTE_WAKEUP                       4
-       u32             xcvrdiag;
-#define     FORCE_HIGH_SPEED_MODE                               31
-#define     FORCE_FULL_SPEED_MODE                               30
-#define     USB_TEST_MODE                                       24
-#define     LINE_STATE                                          16
-#define     TRANSCEIVER_OPERATION_MODE                          2
-#define     TRANSCEIVER_SELECT                                  1
-#define     TERMINATION_SELECT                                  0
-       u32             setup0123;
-       u32             setup4567;
-       // offset 0x0090
-       u32             _unused0;
-       u32             ouraddr;
-#define     FORCE_IMMEDIATE                                     7
-#define     OUR_USB_ADDRESS                                     0
-       u32             ourconfig;
-} __attribute__ ((packed));
-
-/* pci control, BAR0 + 0x0100 */
-struct net2280_pci_regs {
-       // offset 0x0100
-       u32              pcimstctl;
-#define     PCI_ARBITER_PARK_SELECT                             13
-#define     PCI_MULTI LEVEL_ARBITER                             12
-#define     PCI_RETRY_ABORT_ENABLE                              11
-#define     DMA_MEMORY_WRITE_AND_INVALIDATE_ENABLE              10
-#define     DMA_READ_MULTIPLE_ENABLE                            9
-#define     DMA_READ_LINE_ENABLE                                8
-#define     PCI_MASTER_COMMAND_SELECT                           6
-#define         MEM_READ_OR_WRITE                                   0
-#define         IO_READ_OR_WRITE                                    1
-#define         CFG_READ_OR_WRITE                                   2
-#define     PCI_MASTER_START                                    5
-#define     PCI_MASTER_READ_WRITE                               4
-#define         PCI_MASTER_WRITE                                    0
-#define         PCI_MASTER_READ                                     1
-#define     PCI_MASTER_BYTE_WRITE_ENABLES                       0
-       u32              pcimstaddr;
-       u32              pcimstdata;
-       u32              pcimststat;
-#define     PCI_ARBITER_CLEAR                                   2
-#define     PCI_EXTERNAL_ARBITER                                1
-#define     PCI_HOST_MODE                                       0
-} __attribute__ ((packed));
-
-/* dma control, BAR0 + 0x0180 ... array of four structs like this,
- * for channels 0..3.  see also struct net2280_dma:  descriptor
- * that can be loaded into some of these registers.
- */
-struct net2280_dma_regs {      /* [11.7] */
-       // offset 0x0180, 0x01a0, 0x01c0, 0x01e0, 
-       u32             dmactl;
-#define     DMA_SCATTER_GATHER_DONE_INTERRUPT_ENABLE            25
-#define     DMA_CLEAR_COUNT_ENABLE                              21
-#define     DESCRIPTOR_POLLING_RATE                             19
-#define         POLL_CONTINUOUS                                     0
-#define         POLL_1_USEC                                         1
-#define         POLL_100_USEC                                       2
-#define         POLL_1_MSEC                                         3
-#define     DMA_VALID_BIT_POLLING_ENABLE                        18
-#define     DMA_VALID_BIT_ENABLE                                17
-#define     DMA_SCATTER_GATHER_ENABLE                           16
-#define     DMA_OUT_AUTO_START_ENABLE                           4
-#define     DMA_PREEMPT_ENABLE                                  3
-#define     DMA_FIFO_VALIDATE                                   2
-#define     DMA_ENABLE                                          1
-#define     DMA_ADDRESS_HOLD                                    0
-       u32             dmastat;
-#define     DMA_SCATTER_GATHER_DONE_INTERRUPT                   25
-#define     DMA_TRANSACTION_DONE_INTERRUPT                      24
-#define     DMA_ABORT                                           1
-#define     DMA_START                                           0
-       u32             _unused0 [2];
-       // offset 0x0190, 0x01b0, 0x01d0, 0x01f0, 
-       u32             dmacount;
-#define     VALID_BIT                                           31
-#define     DMA_DIRECTION                                       30
-#define     DMA_DONE_INTERRUPT_ENABLE                           29
-#define     END_OF_CHAIN                                        28
-#define         DMA_BYTE_COUNT_MASK                                 ((1<<24)-1)
-#define     DMA_BYTE_COUNT                                      0
-       u32             dmaaddr;
-       u32             dmadesc;
-       u32             _unused1;
-} __attribute__ ((packed));
-
-/* dedicated endpoint registers, BAR0 + 0x0200 */
-
-struct net2280_dep_regs {      /* [11.8] */
-       // offset 0x0200, 0x0210, 0x220, 0x230, 0x240
-       u32             dep_cfg;
-       // offset 0x0204, 0x0214, 0x224, 0x234, 0x244
-       u32             dep_rsp;
-       u32             _unused [2];
-} __attribute__ ((packed));
-
-/* configurable endpoint registers, BAR0 + 0x0300 ... array of seven structs
- * like this, for ep0 then the configurable endpoints A..F
- * ep0 reserved for control; E and F have only 64 bytes of fifo
- */
-struct net2280_ep_regs {       /* [11.9] */
-       // offset 0x0300, 0x0320, 0x0340, 0x0360, 0x0380, 0x03a0, 0x03c0
-       u32             ep_cfg;
-#define     ENDPOINT_BYTE_COUNT                                 16
-#define     ENDPOINT_ENABLE                                     10
-#define     ENDPOINT_TYPE                                       8
-#define     ENDPOINT_DIRECTION                                  7
-#define     ENDPOINT_NUMBER                                     0
-       u32             ep_rsp;
-#define     SET_NAK_OUT_PACKETS                                 15
-#define     SET_EP_HIDE_STATUS_PHASE                            14
-#define     SET_EP_FORCE_CRC_ERROR                              13
-#define     SET_INTERRUPT_MODE                                  12
-#define     SET_CONTROL_STATUS_PHASE_HANDSHAKE                  11
-#define     SET_NAK_OUT_PACKETS_MODE                            10
-#define     SET_ENDPOINT_TOGGLE                                 9
-#define     SET_ENDPOINT_HALT                                   8
-#define     CLEAR_NAK_OUT_PACKETS                               7
-#define     CLEAR_EP_HIDE_STATUS_PHASE                          6
-#define     CLEAR_EP_FORCE_CRC_ERROR                            5
-#define     CLEAR_INTERRUPT_MODE                                4
-#define     CLEAR_CONTROL_STATUS_PHASE_HANDSHAKE                3
-#define     CLEAR_NAK_OUT_PACKETS_MODE                          2
-#define     CLEAR_ENDPOINT_TOGGLE                               1
-#define     CLEAR_ENDPOINT_HALT                                 0
-       u32             ep_irqenb;
-#define     SHORT_PACKET_OUT_DONE_INTERRUPT_ENABLE              6
-#define     SHORT_PACKET_TRANSFERRED_INTERRUPT_ENABLE           5
-#define     DATA_PACKET_RECEIVED_INTERRUPT_ENABLE               3
-#define     DATA_PACKET_TRANSMITTED_INTERRUPT_ENABLE            2
-#define     DATA_OUT_PING_TOKEN_INTERRUPT_ENABLE                1
-#define     DATA_IN_TOKEN_INTERRUPT_ENABLE                      0
-       u32             ep_stat;
-#define     FIFO_VALID_COUNT                                    24
-#define     HIGH_BANDWIDTH_OUT_TRANSACTION_PID                  22
-#define     TIMEOUT                                             21
-#define     USB_STALL_SENT                                      20
-#define     USB_IN_NAK_SENT                                     19
-#define     USB_IN_ACK_RCVD                                     18
-#define     USB_OUT_PING_NAK_SENT                               17
-#define     USB_OUT_ACK_SENT                                    16
-#define     FIFO_OVERFLOW                                       13
-#define     FIFO_UNDERFLOW                                      12
-#define     FIFO_FULL                                           11
-#define     FIFO_EMPTY                                          10
-#define     FIFO_FLUSH                                          9
-#define     SHORT_PACKET_OUT_DONE_INTERRUPT                     6
-#define     SHORT_PACKET_TRANSFERRED_INTERRUPT                  5
-#define     NAK_OUT_PACKETS                                     4
-#define     DATA_PACKET_RECEIVED_INTERRUPT                      3
-#define     DATA_PACKET_TRANSMITTED_INTERRUPT                   2
-#define     DATA_OUT_PING_TOKEN_INTERRUPT                       1
-#define     DATA_IN_TOKEN_INTERRUPT                             0
-       // offset 0x0310, 0x0330, 0x0350, 0x0370, 0x0390, 0x03b0, 0x03d0
-       u32             ep_avail;
-       u32             ep_data;
-       u32             _unused0 [2];
-} __attribute__ ((packed));
+#include <linux/usb/net2280.h>
 
 /*-------------------------------------------------------------------------*/
 
index 51424f66a76599a28193fe59f7950160805fc138..68e3d8f5da8947cb8d28cf17c2056b8829d04190 100644 (file)
@@ -572,9 +572,10 @@ static void source_sink_complete (struct usb_ep *ep, struct usb_request *req)
        switch (status) {
 
        case 0:                         /* normal completion? */
-               if (ep == dev->out_ep)
+               if (ep == dev->out_ep) {
                        check_read_data (dev, ep, req);
-               else
+                       memset (req->buf, 0x55, req->length);
+               } else
                        reinit_write_data (dev, ep, req);
                break;
 
@@ -626,6 +627,8 @@ source_sink_start_ep (struct usb_ep *ep, gfp_t gfp_flags)
 
        if (strcmp (ep->name, EP_IN_NAME) == 0)
                reinit_write_data (ep->driver_data, ep, req);
+       else
+               memset (req->buf, 0x55, req->length);
 
        status = usb_ep_queue (ep, req, gfp_flags);
        if (status) {
index 980030d684d516d3f6eaa5b0ec419938a51b82df..6b7350b52419fc57e925081e21ea9757b6e33ef5 100644 (file)
@@ -20,7 +20,7 @@
 #include <asm/arch/board.h>
 
 #ifndef CONFIG_ARCH_AT91RM9200
-#error "This file is AT91RM9200 bus glue.  CONFIG_ARCH_AT91RM9200 must be defined."
+#error "CONFIG_ARCH_AT91RM9200 must be defined."
 #endif
 
 /* interface and function clocks */
@@ -84,8 +84,6 @@ static int usb_hcd_at91_remove (struct usb_hcd *, struct platform_device *);
  * Allocates basic resources for this USB host controller, and
  * then invokes the start() method for the HCD associated with it
  * through the hotplug entry's driver_data.
- *
- * Store this function in the HCD's struct pci_driver as probe().
  */
 int usb_hcd_at91_probe (const struct hc_driver *driver, struct platform_device *pdev)
 {
@@ -148,7 +146,6 @@ int usb_hcd_at91_probe (const struct hc_driver *driver, struct platform_device *
 }
 
 
-/* may be called without controller electrically present */
 /* may be called with controller, bus, and devices active */
 
 /**
@@ -166,11 +163,11 @@ static int usb_hcd_at91_remove (struct usb_hcd *hcd, struct platform_device *pde
        usb_remove_hcd(hcd);
        at91_stop_hc(pdev);
        iounmap(hcd->regs);
-       release_mem_region(hcd->rsrc_start, hcd->rsrc_len);
+       release_mem_region(hcd->rsrc_start, hcd->rsrc_len);
 
-       clk_put(fclk);
-       clk_put(iclk);
-       fclk = iclk = NULL;
+       clk_put(fclk);
+       clk_put(iclk);
+       fclk = iclk = NULL;
 
        dev_set_drvdata(&pdev->dev, NULL);
        return 0;
@@ -235,8 +232,8 @@ static const struct hc_driver ohci_at91_hc_driver = {
        .hub_control =          ohci_hub_control,
 
 #ifdef CONFIG_PM
-       .hub_suspend =          ohci_hub_suspend,
-       .hub_resume =           ohci_hub_resume,
+       .bus_suspend =          ohci_bus_suspend,
+       .bus_resume =           ohci_bus_resume,
 #endif
        .start_port_reset =     ohci_start_port_reset,
 };
@@ -254,21 +251,21 @@ static int ohci_hcd_at91_drv_remove(struct platform_device *dev)
 }
 
 #ifdef CONFIG_PM
-static int ohci_hcd_at91_drv_suspend(struct platform_device *dev, u32 state, u32 level)
-{
-       printk("%s(%s:%d): not implemented yet\n",
-               __func__, __FILE__, __LINE__);
 
+/* REVISIT suspend/resume look "too" simple here */
+
+static int
+ohci_hcd_at91_drv_suspend(struct platform_device *dev, pm_message_t mesg)
+{
        clk_disable(fclk);
+       clk_disable(iclk);
 
        return 0;
 }
 
-static int ohci_hcd_at91_drv_resume(struct platform_device *dev, u32 state)
+static int ohci_hcd_at91_drv_resume(struct platform_device *dev)
 {
-       printk("%s(%s:%d): not implemented yet\n",
-               __func__, __FILE__, __LINE__);
-
+       clk_enable(iclk);
        clk_enable(fclk);
 
        return 0;
@@ -278,6 +275,8 @@ static int ohci_hcd_at91_drv_resume(struct platform_device *dev, u32 state)
 #define ohci_hcd_at91_drv_resume  NULL
 #endif
 
+MODULE_ALIAS("at91rm9200-ohci");
+
 static struct platform_driver ohci_hcd_at91_driver = {
        .probe          = ohci_hcd_at91_drv_probe,
        .remove         = ohci_hcd_at91_drv_remove,
index 682bf2215660fccb6325dca29f35749bb23e8dbe..1da5de573a6fb22896e1bfffee25fc187ee40c59 100644 (file)
@@ -30,6 +30,7 @@
 /* clock device associated with the hcd */
 
 static struct clk *clk;
+static struct clk *usb_clk;
 
 /* forward definitions */
 
@@ -37,7 +38,7 @@ static void s3c2410_hcd_oc(struct s3c2410_hcd_info *info, int port_oc);
 
 /* conversion functions */
 
-struct s3c2410_hcd_info *to_s3c2410_info(struct usb_hcd *hcd)
+static struct s3c2410_hcd_info *to_s3c2410_info(struct usb_hcd *hcd)
 {
        return hcd->self.controller->platform_data;
 }
@@ -47,6 +48,10 @@ static void s3c2410_start_hc(struct platform_device *dev, struct usb_hcd *hcd)
        struct s3c2410_hcd_info *info = dev->dev.platform_data;
 
        dev_dbg(&dev->dev, "s3c2410_start_hc:\n");
+
+       clk_enable(usb_clk);
+       mdelay(2);                      /* let the bus clock stabilise */
+
        clk_enable(clk);
 
        if (info != NULL) {
@@ -75,6 +80,7 @@ static void s3c2410_stop_hc(struct platform_device *dev)
        }
 
        clk_disable(clk);
+       clk_disable(usb_clk);
 }
 
 /* ohci_s3c2410_hub_status_data
@@ -316,7 +322,8 @@ static void s3c2410_hcd_oc(struct s3c2410_hcd_info *info, int port_oc)
  *
 */
 
-void usb_hcd_s3c2410_remove (struct usb_hcd *hcd, struct platform_device *dev)
+static void
+usb_hcd_s3c2410_remove (struct usb_hcd *hcd, struct platform_device *dev)
 {
        usb_remove_hcd(hcd);
        s3c2410_stop_hc(dev);
@@ -334,8 +341,8 @@ void usb_hcd_s3c2410_remove (struct usb_hcd *hcd, struct platform_device *dev)
  * through the hotplug entry's driver_data.
  *
  */
-int usb_hcd_s3c2410_probe (const struct hc_driver *driver,
-                          struct platform_device *dev)
+static int usb_hcd_s3c2410_probe (const struct hc_driver *driver,
+                                 struct platform_device *dev)
 {
        struct usb_hcd *hcd = NULL;
        int retval;
@@ -353,14 +360,21 @@ int usb_hcd_s3c2410_probe (const struct hc_driver *driver,
        if (!request_mem_region(hcd->rsrc_start, hcd->rsrc_len, hcd_name)) {
                dev_err(&dev->dev, "request_mem_region failed");
                retval = -EBUSY;
-               goto err0;
+               goto err_put;
        }
 
-       clk = clk_get(NULL, "usb-host");
+       clk = clk_get(&dev->dev, "usb-host");
        if (IS_ERR(clk)) {
                dev_err(&dev->dev, "cannot get usb-host clock\n");
                retval = -ENOENT;
-               goto err1;
+               goto err_mem;
+       }
+
+       usb_clk = clk_get(&dev->dev, "upll");
+       if (IS_ERR(usb_clk)) {
+               dev_err(&dev->dev, "cannot get usb-host clock\n");
+               retval = -ENOENT;
+               goto err_clk;
        }
 
        s3c2410_start_hc(dev, hcd);
@@ -369,26 +383,29 @@ int usb_hcd_s3c2410_probe (const struct hc_driver *driver,
        if (!hcd->regs) {
                dev_err(&dev->dev, "ioremap failed\n");
                retval = -ENOMEM;
-               goto err2;
+               goto err_ioremap;
        }
 
        ohci_hcd_init(hcd_to_ohci(hcd));
 
        retval = usb_add_hcd(hcd, dev->resource[1].start, SA_INTERRUPT);
        if (retval != 0)
-               goto err2;
+               goto err_ioremap;
 
        return 0;
 
- err2:
+ err_ioremap:
        s3c2410_stop_hc(dev);
        iounmap(hcd->regs);
+       clk_put(usb_clk);
+
+ err_clk:
        clk_put(clk);
 
- err1:
+ err_mem:
        release_mem_region(hcd->rsrc_start, hcd->rsrc_len);
 
- err0:
+ err_put:
        usb_put_hcd(hcd);
        return retval;
 }
index 9e81c26313f91e90a0b7a06a75b9bd0649041ec2..1045f846fbe2c4cedb5d3ac498488b572246258a 100644 (file)
@@ -15,6 +15,7 @@
 #include <linux/init.h>
 #include <linux/delay.h>
 #include <linux/acpi.h>
+#include "pci-quirks.h"
 
 
 #define UHCI_USBLEGSUP         0xc0            /* legacy support */
diff --git a/drivers/usb/host/pci-quirks.h b/drivers/usb/host/pci-quirks.h
new file mode 100644 (file)
index 0000000..1564edf
--- /dev/null
@@ -0,0 +1,7 @@
+#ifndef __LINUX_USB_PCI_QUIRKS_H
+#define __LINUX_USB_PCI_QUIRKS_H
+
+void uhci_reset_hc(struct pci_dev *pdev, unsigned long base);
+int uhci_check_and_reset_hc(struct pci_dev *pdev, unsigned long base);
+
+#endif  /*  __LINUX_USB_PCI_QUIRKS_H  */
index 4edb8330c440d2a00dd7a0e7bce3ecb13e345433..c0c4db78b590de386af45318b82e23fde5567457 100644 (file)
@@ -50,6 +50,7 @@
 
 #include "../core/hcd.h"
 #include "uhci-hcd.h"
+#include "pci-quirks.h"
 
 /*
  * Version Information
@@ -100,9 +101,6 @@ static void uhci_get_current_frame_number(struct uhci_hcd *uhci);
 #include "uhci-q.c"
 #include "uhci-hub.c"
 
-extern void uhci_reset_hc(struct pci_dev *pdev, unsigned long base);
-extern int uhci_check_and_reset_hc(struct pci_dev *pdev, unsigned long base);
-
 /*
  * Finish up a host controller reset and update the recorded state.
  */
@@ -117,8 +115,7 @@ static void finish_reset(struct uhci_hcd *uhci)
        for (port = 0; port < uhci->rh_numports; ++port)
                outw(0, uhci->io_addr + USBPORTSC1 + (port * 2));
 
-       uhci->port_c_suspend = uhci->suspended_ports =
-                       uhci->resuming_ports = 0;
+       uhci->port_c_suspend = uhci->resuming_ports = 0;
        uhci->rh_state = UHCI_RH_RESET;
        uhci->is_stopped = UHCI_IS_STOPPED;
        uhci_to_hcd(uhci)->state = HC_STATE_HALT;
index 4a69c7eb09bd015c8ae0726f24b64a7de54d5dbf..d5c8f4d928236ba58ef62bd448c506c078f7f9e4 100644 (file)
@@ -415,7 +415,6 @@ struct uhci_hcd {
 
        /* Support for port suspend/resume/reset */
        unsigned long port_c_suspend;           /* Bit-arrays of ports */
-       unsigned long suspended_ports;
        unsigned long resuming_ports;
        unsigned long ports_timeout;            /* Time to stop signalling */
 
index 152971d167695580bc69282091888cc1b962ea90..c8451d9578f16ebd96df6501f058efbca031f24a 100644 (file)
@@ -85,11 +85,10 @@ static void uhci_finish_suspend(struct uhci_hcd *uhci, int port,
 {
        int status;
 
-       if (test_bit(port, &uhci->suspended_ports)) {
+       if (inw(port_addr) & (USBPORTSC_SUSP | USBPORTSC_RD)) {
                CLR_RH_PORTSTAT(USBPORTSC_SUSP | USBPORTSC_RD);
-               clear_bit(port, &uhci->suspended_ports);
-               clear_bit(port, &uhci->resuming_ports);
-               set_bit(port, &uhci->port_c_suspend);
+               if (test_bit(port, &uhci->resuming_ports))
+                       set_bit(port, &uhci->port_c_suspend);
 
                /* The controller won't actually turn off the RD bit until
                 * it has had a chance to send a low-speed EOP sequence,
@@ -97,6 +96,7 @@ static void uhci_finish_suspend(struct uhci_hcd *uhci, int port,
                 * slightly longer for good luck. */
                udelay(4);
        }
+       clear_bit(port, &uhci->resuming_ports);
 }
 
 /* Wait for the UHCI controller in HP's iLO2 server management chip.
@@ -265,8 +265,6 @@ static int uhci_hub_control(struct usb_hcd *hcd, u16 typeReq, u16 wValue,
                        wPortChange |= USB_PORT_STAT_C_SUSPEND;
                        lstatus |= 1;
                }
-               if (test_bit(port, &uhci->suspended_ports))
-                       lstatus |= 2;
                if (test_bit(port, &uhci->resuming_ports))
                        lstatus |= 4;
 
@@ -309,7 +307,6 @@ static int uhci_hub_control(struct usb_hcd *hcd, u16 typeReq, u16 wValue,
 
                switch (wValue) {
                case USB_PORT_FEAT_SUSPEND:
-                       set_bit(port, &uhci->suspended_ports);
                        SET_RH_PORTSTAT(USBPORTSC_SUSP);
                        OK(0);
                case USB_PORT_FEAT_RESET:
@@ -343,8 +340,11 @@ static int uhci_hub_control(struct usb_hcd *hcd, u16 typeReq, u16 wValue,
                        CLR_RH_PORTSTAT(USBPORTSC_PEC);
                        OK(0);
                case USB_PORT_FEAT_SUSPEND:
-                       if (test_bit(port, &uhci->suspended_ports) &&
-                                       !test_and_set_bit(port,
+                       if (!(inw(port_addr) & USBPORTSC_SUSP)) {
+
+                               /* Make certain the port isn't suspended */
+                               uhci_finish_suspend(uhci, port, port_addr);
+                       } else if (!test_and_set_bit(port,
                                                &uhci->resuming_ports)) {
                                SET_RH_PORTSTAT(USBPORTSC_RD);
 
index 5246b35301de9d4e9333d1f14e15e51bea0919b5..650103bc9618434ad769972ebb6db5e8cf76ae01 100644 (file)
@@ -200,45 +200,41 @@ config USB_POWERMATE
          To compile this driver as a module, choose M here: the
          module will be called powermate.
 
-config USB_MTOUCH
-       tristate "MicroTouch USB Touchscreen Driver"
+config USB_TOUCHSCREEN
+       tristate "USB Touchscreen Driver"
        depends on USB && INPUT
        ---help---
-         Say Y here if you want to use a MicroTouch (Now 3M) USB 
-         Touchscreen controller.
+         USB Touchscreen driver for:
+         - eGalax Touchkit USB
+         - PanJit TouchSet USB
+         - 3M MicroTouch USB
+         - ITM
 
-         See <file:Documentation/usb/mtouch.txt> for additional information.
-
-         To compile this driver as a module, choose M here: the
-         module will be called mtouchusb.
-
-config USB_ITMTOUCH
-       tristate "ITM Touch USB Touchscreen Driver"
-       depends on USB && INPUT
-       ---help---
-         Say Y here if you want to use a ITM Touch USB
-         Touchscreen controller.
-
-         This touchscreen is used in LG 1510SF monitors.
+         Have a look at <http://linux.chapter7.ch/touchkit/> for
+         a usage description and the required user-space stuff.
 
          To compile this driver as a module, choose M here: the
-         module will be called itmtouch.
+         module will be called usbtouchscreen.
 
-config USB_EGALAX
-       tristate "eGalax TouchKit USB Touchscreen Driver"
-       depends on USB && INPUT
-       ---help---
-         Say Y here if you want to use a eGalax TouchKit USB
-         Touchscreen controller.
+config USB_TOUCHSCREEN_EGALAX
+       default y
+       bool "eGalax device support" if EMBEDDED
+       depends on USB_TOUCHSCREEN
 
-         The driver has been tested on a Xenarc 700TSV monitor
-         with eGalax touchscreen.
+config USB_TOUCHSCREEN_PANJIT
+       default y
+       bool "PanJit device support" if EMBEDDED
+       depends on USB_TOUCHSCREEN
 
-         Have a look at <http://linux.chapter7.ch/touchkit/> for
-         a usage description and the required user-space stuff.
+config USB_TOUCHSCREEN_3M
+       default y
+       bool "3M/Microtouch device support" if EMBEDDED
+       depends on USB_TOUCHSCREEN
 
-         To compile this driver as a module, choose M here: the
-         module will be called touchkitusb.
+config USB_TOUCHSCREEN_ITM
+       default y
+       bool "ITM device support" if EMBEDDED
+       depends on USB_TOUCHSCREEN
 
 config USB_YEALINK
        tristate "Yealink usb-p1k voip phone"
index d512d9f488fe6aa7528f00e498af073d404d61d7..764114529c56af10071d2dfa94f21717edf34e18 100644 (file)
@@ -37,6 +37,7 @@ obj-$(CONFIG_USB_MOUSE)               += usbmouse.o
 obj-$(CONFIG_USB_MTOUCH)       += mtouchusb.o
 obj-$(CONFIG_USB_ITMTOUCH)     += itmtouch.o
 obj-$(CONFIG_USB_EGALAX)       += touchkitusb.o
+obj-$(CONFIG_USB_TOUCHSCREEN)  += usbtouchscreen.o
 obj-$(CONFIG_USB_POWERMATE)    += powermate.o
 obj-$(CONFIG_USB_WACOM)                += wacom.o
 obj-$(CONFIG_USB_ACECAD)       += acecad.o
index d4bf1701046bbaa5543f216eeaf36c616a607fd6..f419bd82ab7f5bd00fc78979c4e56369d4de77f1 100644 (file)
@@ -1372,6 +1372,11 @@ void hid_close(struct hid_device *hid)
                usb_kill_urb(hid->urbin);
 }
 
+#define USB_VENDOR_ID_PANJIT           0x134c
+
+#define USB_VENDOR_ID_SILVERCREST      0x062a
+#define USB_DEVICE_ID_SILVERCREST_KB   0x0201
+
 /*
  * Initialize all reports
  */
@@ -1655,9 +1660,12 @@ static const struct hid_blacklist {
        { USB_VENDOR_ID_WACOM, USB_DEVICE_ID_WACOM_INTUOS3, HID_QUIRK_IGNORE },
        { USB_VENDOR_ID_WACOM, USB_DEVICE_ID_WACOM_INTUOS3 + 1, HID_QUIRK_IGNORE },
        { USB_VENDOR_ID_WACOM, USB_DEVICE_ID_WACOM_INTUOS3 + 2, HID_QUIRK_IGNORE },
+       { USB_VENDOR_ID_WACOM, USB_DEVICE_ID_WACOM_INTUOS3 + 3, HID_QUIRK_IGNORE },
+       { USB_VENDOR_ID_WACOM, USB_DEVICE_ID_WACOM_INTUOS3 + 4, HID_QUIRK_IGNORE },
        { USB_VENDOR_ID_WACOM, USB_DEVICE_ID_WACOM_INTUOS3 + 5, HID_QUIRK_IGNORE },
        { USB_VENDOR_ID_WACOM, USB_DEVICE_ID_WACOM_CINTIQ, HID_QUIRK_IGNORE },
        { USB_VENDOR_ID_WACOM, USB_DEVICE_ID_WACOM_DTF, HID_QUIRK_IGNORE },
+       { USB_VENDOR_ID_WACOM, USB_DEVICE_ID_WACOM_DTF + 3, HID_QUIRK_IGNORE },
        { USB_VENDOR_ID_WISEGROUP, USB_DEVICE_ID_4_PHIDGETSERVO_20, HID_QUIRK_IGNORE },
        { USB_VENDOR_ID_WISEGROUP, USB_DEVICE_ID_1_PHIDGETSERVO_20, HID_QUIRK_IGNORE },
 
@@ -1675,6 +1683,7 @@ static const struct hid_blacklist {
        { USB_VENDOR_ID_HP, USB_DEVICE_ID_HP_USBHUB_KB, HID_QUIRK_NOGET },
        { USB_VENDOR_ID_TANGTOP, USB_DEVICE_ID_TANGTOP_USBPS2, HID_QUIRK_NOGET },
        { USB_VENDOR_ID_WISEGROUP, USB_DEVICE_ID_DUAL_USB_JOYPAD, HID_QUIRK_NOGET | HID_QUIRK_MULTI_INPUT },
+       { USB_VENDOR_ID_SILVERCREST, USB_DEVICE_ID_SILVERCREST_KB, HID_QUIRK_NOGET },
 
        { USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_POWERMOUSE, HID_QUIRK_2WHEEL_POWERMOUSE },
        { USB_VENDOR_ID_A4TECH, USB_DEVICE_ID_A4TECH_WCP32PU, HID_QUIRK_2WHEEL_MOUSE_HACK_7 },
@@ -1701,6 +1710,11 @@ static const struct hid_blacklist {
        { USB_VENDOR_ID_APPLE, 0x030A, HID_QUIRK_POWERBOOK_HAS_FN },
        { USB_VENDOR_ID_APPLE, 0x030B, HID_QUIRK_POWERBOOK_HAS_FN },
 
+       { USB_VENDOR_ID_PANJIT, 0x0001, HID_QUIRK_IGNORE },
+       { USB_VENDOR_ID_PANJIT, 0x0002, HID_QUIRK_IGNORE },
+       { USB_VENDOR_ID_PANJIT, 0x0003, HID_QUIRK_IGNORE },
+       { USB_VENDOR_ID_PANJIT, 0x0004, HID_QUIRK_IGNORE },
+
        { 0, 0 }
 };
 
index 72e698658b5322570e40a830634999fbca46e6de..d5c91ee67991cf9e4331ad451cca18ca8e67a2c4 100644 (file)
 
 #include "hid.h"
 
-/* Drivers' initializing functions */
-extern int hid_lgff_init(struct hid_device* hid);
-extern int hid_lg3d_init(struct hid_device* hid);
-extern int hid_pid_init(struct hid_device* hid);
-extern int hid_tmff_init(struct hid_device* hid);
-
 /*
  * This table contains pointers to initializers. To add support for new
  * devices, you need to add the USB vendor and product ids here.
index 4e1b784fe5275c48e4e48455a495f44fd6c84abb..9c62837b5b899c2fcb40389725bee142b619db6c 100644 (file)
@@ -533,3 +533,8 @@ static inline int hid_ff_event(struct hid_device *hid, struct input_dev *input,
                return hid->ff_event(hid, input, type, code, value);
        return -ENOSYS;
 }
+
+int hid_lgff_init(struct hid_device* hid);
+int hid_tmff_init(struct hid_device* hid);
+int hid_pid_init(struct hid_device* hid);
+
index b4a051b549d1543d36c6883f83aa21e7ef2cc991..3d911976f378ca9386fe2484cc1b7f177237f26c 100644 (file)
@@ -297,6 +297,8 @@ static void keyspan_check_data(struct usb_keyspan *remote, struct pt_regs *regs)
                        remote->data.bits_left -= 6;
                } else {
                        err("%s - Error in message, invalid toggle.\n", __FUNCTION__);
+                       remote->stage = 0;
+                       return;
                }
 
                keyspan_load_tester(remote, 5);
diff --git a/drivers/usb/input/usbtouchscreen.c b/drivers/usb/input/usbtouchscreen.c
new file mode 100644 (file)
index 0000000..e9a07c1
--- /dev/null
@@ -0,0 +1,605 @@
+/******************************************************************************
+ * usbtouchscreen.c
+ * Driver for USB Touchscreens, supporting those devices:
+ *  - eGalax Touchkit
+ *  - 3M/Microtouch
+ *  - ITM
+ *  - PanJit TouchSet
+ *
+ * Copyright (C) 2004-2006 by Daniel Ritz <daniel.ritz@gmx.ch>
+ * Copyright (C) by Todd E. Johnson (mtouchusb.c)
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License as
+ * published by the Free Software Foundation; either version 2 of the
+ * License, or (at your option) any later version.
+ *
+ * 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., 675 Mass Ave, Cambridge, MA 02139, USA.
+ *
+ * Driver is based on touchkitusb.c
+ * - ITM parts are from itmtouch.c
+ * - 3M parts are from mtouchusb.c
+ * - PanJit parts are from an unmerged driver by Lanslott Gish
+ *
+ *****************************************************************************/
+
+//#define DEBUG
+
+#include <linux/config.h>
+#include <linux/kernel.h>
+#include <linux/slab.h>
+#include <linux/input.h>
+#include <linux/module.h>
+#include <linux/init.h>
+#include <linux/usb.h>
+#include <linux/usb_input.h>
+
+
+#define DRIVER_VERSION         "v0.3"
+#define DRIVER_AUTHOR          "Daniel Ritz <daniel.ritz@gmx.ch>"
+#define DRIVER_DESC            "USB Touchscreen Driver"
+
+static int swap_xy;
+module_param(swap_xy, bool, 0644);
+MODULE_PARM_DESC(swap_xy, "If set X and Y axes are swapped.");
+
+/* device specifc data/functions */
+struct usbtouch_usb;
+struct usbtouch_device_info {
+       int min_xc, max_xc;
+       int min_yc, max_yc;
+       int min_press, max_press;
+       int rept_size;
+       int flags;
+
+       void (*process_pkt) (struct usbtouch_usb *usbtouch, struct pt_regs *regs, unsigned char *pkt, int len);
+       int  (*read_data)   (unsigned char *pkt, int *x, int *y, int *touch, int *press);
+       int  (*init)        (struct usbtouch_usb *usbtouch);
+};
+
+#define USBTOUCH_FLG_BUFFER    0x01
+
+
+/* a usbtouch device */
+struct usbtouch_usb {
+       unsigned char *data;
+       dma_addr_t data_dma;
+       unsigned char *buffer;
+       int buf_len;
+       struct urb *irq;
+       struct usb_device *udev;
+       struct input_dev *input;
+       struct usbtouch_device_info *type;
+       char name[128];
+       char phys[64];
+};
+
+static void usbtouch_process_pkt(struct usbtouch_usb *usbtouch,
+                                 struct pt_regs *regs, unsigned char *pkt, int len);
+
+/* device types */
+enum {
+       DEVTPYE_DUMMY = -1,
+       DEVTYPE_EGALAX,
+       DEVTYPE_PANJIT,
+       DEVTYPE_3M,
+       DEVTYPE_ITM,
+};
+
+static struct usb_device_id usbtouch_devices[] = {
+#ifdef CONFIG_USB_TOUCHSCREEN_EGALAX
+       {USB_DEVICE(0x3823, 0x0001), .driver_info = DEVTYPE_EGALAX},
+       {USB_DEVICE(0x0123, 0x0001), .driver_info = DEVTYPE_EGALAX},
+       {USB_DEVICE(0x0eef, 0x0001), .driver_info = DEVTYPE_EGALAX},
+       {USB_DEVICE(0x0eef, 0x0002), .driver_info = DEVTYPE_EGALAX},
+#endif
+
+#ifdef CONFIG_USB_TOUCHSCREEN_PANJIT
+       {USB_DEVICE(0x134c, 0x0001), .driver_info = DEVTYPE_PANJIT},
+       {USB_DEVICE(0x134c, 0x0002), .driver_info = DEVTYPE_PANJIT},
+       {USB_DEVICE(0x134c, 0x0003), .driver_info = DEVTYPE_PANJIT},
+       {USB_DEVICE(0x134c, 0x0004), .driver_info = DEVTYPE_PANJIT},
+#endif
+
+#ifdef CONFIG_USB_TOUCHSCREEN_3M
+       {USB_DEVICE(0x0596, 0x0001), .driver_info = DEVTYPE_3M},
+#endif
+
+#ifdef CONFIG_USB_TOUCHSCREEN_ITM
+       {USB_DEVICE(0x0403, 0xf9e9), .driver_info = DEVTYPE_ITM},
+#endif
+
+       {}
+};
+
+
+/*****************************************************************************
+ * eGalax part
+ */
+
+#ifdef CONFIG_USB_TOUCHSCREEN_EGALAX
+
+#define EGALAX_PKT_TYPE_MASK           0xFE
+#define EGALAX_PKT_TYPE_REPT           0x80
+#define EGALAX_PKT_TYPE_DIAG           0x0A
+
+static int egalax_read_data(unsigned char *pkt, int *x, int *y, int *touch, int *press)
+{
+       if ((pkt[0] & EGALAX_PKT_TYPE_MASK) != EGALAX_PKT_TYPE_REPT)
+               return 0;
+
+       *x = ((pkt[3] & 0x0F) << 7) | (pkt[4] & 0x7F);
+       *y = ((pkt[1] & 0x0F) << 7) | (pkt[2] & 0x7F);
+       *touch = pkt[0] & 0x01;
+
+       return 1;
+
+}
+
+static int egalax_get_pkt_len(unsigned char *buf)
+{
+       switch (buf[0] & EGALAX_PKT_TYPE_MASK) {
+       case EGALAX_PKT_TYPE_REPT:
+               return 5;
+
+       case EGALAX_PKT_TYPE_DIAG:
+               return buf[1] + 2;
+       }
+
+       return 0;
+}
+
+static void egalax_process(struct usbtouch_usb *usbtouch, struct pt_regs *regs,
+                           unsigned char *pkt, int len)
+{
+       unsigned char *buffer;
+       int pkt_len, buf_len, pos;
+
+       /* if the buffer contains data, append */
+       if (unlikely(usbtouch->buf_len)) {
+               int tmp;
+
+               /* if only 1 byte in buffer, add another one to get length */
+               if (usbtouch->buf_len == 1)
+                       usbtouch->buffer[1] = pkt[0];
+
+               pkt_len = egalax_get_pkt_len(usbtouch->buffer);
+
+               /* unknown packet: drop everything */
+               if (!pkt_len)
+                       return;
+
+               /* append, process */
+               tmp = pkt_len - usbtouch->buf_len;
+               memcpy(usbtouch->buffer + usbtouch->buf_len, pkt, tmp);
+               usbtouch_process_pkt(usbtouch, regs, usbtouch->buffer, pkt_len);
+
+               buffer = pkt + tmp;
+               buf_len = len - tmp;
+       } else {
+               buffer = pkt;
+               buf_len = len;
+       }
+
+       /* only one byte left in buffer */
+       if (unlikely(buf_len == 1)) {
+               usbtouch->buffer[0] = buffer[0];
+               usbtouch->buf_len = 1;
+               return;
+       }
+
+       /* loop over the buffer */
+       pos = 0;
+       while (pos < buf_len) {
+               /* get packet len */
+               pkt_len = egalax_get_pkt_len(buffer + pos);
+
+               /* unknown packet: drop everything */
+               if (unlikely(!pkt_len))
+                       return;
+
+               /* full packet: process */
+               if (likely(pkt_len <= buf_len)) {
+                       usbtouch_process_pkt(usbtouch, regs, buffer + pos, pkt_len);
+               } else {
+                       /* incomplete packet: save in buffer */
+                       memcpy(usbtouch->buffer, buffer + pos, buf_len - pos);
+                       usbtouch->buf_len = buf_len - pos;
+               }
+               pos += pkt_len;
+       }
+}
+#endif
+
+
+/*****************************************************************************
+ * PanJit Part
+ */
+#ifdef CONFIG_USB_TOUCHSCREEN_PANJIT
+static int panjit_read_data(unsigned char *pkt, int *x, int *y, int *touch, int *press)
+{
+       *x = ((pkt[2] & 0x0F) << 8) | pkt[1];
+       *y = ((pkt[4] & 0x0F) << 8) | pkt[3];
+       *touch = pkt[0] & 0x01;
+
+       return 1;
+}
+#endif
+
+
+/*****************************************************************************
+ * 3M/Microtouch Part
+ */
+#ifdef CONFIG_USB_TOUCHSCREEN_3M
+
+#define MTOUCHUSB_ASYNC_REPORT          1
+#define MTOUCHUSB_RESET                 7
+#define MTOUCHUSB_REQ_CTRLLR_ID         10
+
+static int mtouch_read_data(unsigned char *pkt, int *x, int *y, int *touch, int *press)
+{
+       *x = (pkt[8] << 8) | pkt[7];
+       *y = (pkt[10] << 8) | pkt[9];
+       *touch = (pkt[2] & 0x40) ? 1 : 0;
+
+       return 1;
+}
+
+static int mtouch_init(struct usbtouch_usb *usbtouch)
+{
+       int ret;
+
+       ret = usb_control_msg(usbtouch->udev, usb_rcvctrlpipe(usbtouch->udev, 0),
+                             MTOUCHUSB_RESET,
+                             USB_DIR_OUT | USB_TYPE_VENDOR | USB_RECIP_DEVICE,
+                             1, 0, NULL, 0, USB_CTRL_SET_TIMEOUT);
+       dbg("%s - usb_control_msg - MTOUCHUSB_RESET - bytes|err: %d",
+           __FUNCTION__, ret);
+       if (ret < 0)
+               return ret;
+
+       ret = usb_control_msg(usbtouch->udev, usb_rcvctrlpipe(usbtouch->udev, 0),
+                             MTOUCHUSB_ASYNC_REPORT,
+                             USB_DIR_OUT | USB_TYPE_VENDOR | USB_RECIP_DEVICE,
+                             1, 1, NULL, 0, USB_CTRL_SET_TIMEOUT);
+       dbg("%s - usb_control_msg - MTOUCHUSB_ASYNC_REPORT - bytes|err: %d",
+           __FUNCTION__, ret);
+       if (ret < 0)
+               return ret;
+
+       return 0;
+}
+#endif
+
+
+/*****************************************************************************
+ * ITM Part
+ */
+#ifdef CONFIG_USB_TOUCHSCREEN_ITM
+static int itm_read_data(unsigned char *pkt, int *x, int *y, int *touch, int *press)
+{
+       *x = ((pkt[0] & 0x1F) << 7) | (pkt[3] & 0x7F);
+       *x = ((pkt[1] & 0x1F) << 7) | (pkt[4] & 0x7F);
+       *press = ((pkt[2] & 0x1F) << 7) | (pkt[5] & 0x7F);
+       *touch = ~pkt[7] & 0x20;
+
+       return 1;
+}
+#endif
+
+
+/*****************************************************************************
+ * the different device descriptors
+ */
+static struct usbtouch_device_info usbtouch_dev_info[] = {
+#ifdef CONFIG_USB_TOUCHSCREEN_EGALAX
+       [DEVTYPE_EGALAX] = {
+               .min_xc         = 0x0,
+               .max_xc         = 0x07ff,
+               .min_yc         = 0x0,
+               .max_yc         = 0x07ff,
+               .rept_size      = 16,
+               .flags          = USBTOUCH_FLG_BUFFER,
+               .process_pkt    = egalax_process,
+               .read_data      = egalax_read_data,
+       },
+#endif
+
+#ifdef CONFIG_USB_TOUCHSCREEN_PANJIT
+       [DEVTYPE_PANJIT] = {
+               .min_xc         = 0x0,
+               .max_xc         = 0x0fff,
+               .min_yc         = 0x0,
+               .max_yc         = 0x0fff,
+               .rept_size      = 8,
+               .read_data      = panjit_read_data,
+       },
+#endif
+
+#ifdef CONFIG_USB_TOUCHSCREEN_3M
+       [DEVTYPE_3M] = {
+               .min_xc         = 0x0,
+               .max_xc         = 0x4000,
+               .min_yc         = 0x0,
+               .max_yc         = 0x4000,
+               .rept_size      = 11,
+               .read_data      = mtouch_read_data,
+               .init           = mtouch_init,
+       },
+#endif
+
+#ifdef CONFIG_USB_TOUCHSCREEN_ITM
+       [DEVTYPE_ITM] = {
+               .min_xc         = 0x0,
+               .max_xc         = 0x0fff,
+               .min_yc         = 0x0,
+               .max_yc         = 0x0fff,
+               .max_press      = 0xff,
+               .rept_size      = 8,
+               .read_data      = itm_read_data,
+       },
+#endif
+};
+
+
+/*****************************************************************************
+ * Generic Part
+ */
+static void usbtouch_process_pkt(struct usbtouch_usb *usbtouch,
+                                 struct pt_regs *regs, unsigned char *pkt, int len)
+{
+       int x, y, touch, press;
+       struct usbtouch_device_info *type = usbtouch->type;
+
+       if (!type->read_data(pkt, &x, &y, &touch, &press))
+                       return;
+
+       input_regs(usbtouch->input, regs);
+       input_report_key(usbtouch->input, BTN_TOUCH, touch);
+
+       if (swap_xy) {
+               input_report_abs(usbtouch->input, ABS_X, y);
+               input_report_abs(usbtouch->input, ABS_Y, x);
+       } else {
+               input_report_abs(usbtouch->input, ABS_X, x);
+               input_report_abs(usbtouch->input, ABS_Y, y);
+       }
+       if (type->max_press)
+               input_report_abs(usbtouch->input, ABS_PRESSURE, press);
+       input_sync(usbtouch->input);
+}
+
+
+static void usbtouch_irq(struct urb *urb, struct pt_regs *regs)
+{
+       struct usbtouch_usb *usbtouch = urb->context;
+       int retval;
+
+       switch (urb->status) {
+       case 0:
+               /* success */
+               break;
+       case -ETIMEDOUT:
+               /* this urb is timing out */
+               dbg("%s - urb timed out - was the device unplugged?",
+                   __FUNCTION__);
+               return;
+       case -ECONNRESET:
+       case -ENOENT:
+       case -ESHUTDOWN:
+               /* this urb is terminated, clean up */
+               dbg("%s - urb shutting down with status: %d",
+                   __FUNCTION__, urb->status);
+               return;
+       default:
+               dbg("%s - nonzero urb status received: %d",
+                   __FUNCTION__, urb->status);
+               goto exit;
+       }
+
+       usbtouch->type->process_pkt(usbtouch, regs, usbtouch->data, urb->actual_length);
+
+exit:
+       retval = usb_submit_urb(urb, GFP_ATOMIC);
+       if (retval)
+               err("%s - usb_submit_urb failed with result: %d",
+                   __FUNCTION__, retval);
+}
+
+static int usbtouch_open(struct input_dev *input)
+{
+       struct usbtouch_usb *usbtouch = input->private;
+
+       usbtouch->irq->dev = usbtouch->udev;
+
+       if (usb_submit_urb(usbtouch->irq, GFP_KERNEL))
+               return -EIO;
+
+       return 0;
+}
+
+static void usbtouch_close(struct input_dev *input)
+{
+       struct usbtouch_usb *usbtouch = input->private;
+
+       usb_kill_urb(usbtouch->irq);
+}
+
+
+static void usbtouch_free_buffers(struct usb_device *udev,
+                                 struct usbtouch_usb *usbtouch)
+{
+       if (usbtouch->data)
+               usb_buffer_free(udev, usbtouch->type->rept_size,
+                               usbtouch->data, usbtouch->data_dma);
+       kfree(usbtouch->buffer);
+}
+
+
+static int usbtouch_probe(struct usb_interface *intf,
+                         const struct usb_device_id *id)
+{
+       struct usbtouch_usb *usbtouch;
+       struct input_dev *input_dev;
+       struct usb_host_interface *interface;
+       struct usb_endpoint_descriptor *endpoint;
+       struct usb_device *udev = interface_to_usbdev(intf);
+       struct usbtouch_device_info *type;
+       int err;
+
+       interface = intf->cur_altsetting;
+       endpoint = &interface->endpoint[0].desc;
+
+       usbtouch = kzalloc(sizeof(struct usbtouch_usb), GFP_KERNEL);
+       input_dev = input_allocate_device();
+       if (!usbtouch || !input_dev)
+               goto out_free;
+
+       type = &usbtouch_dev_info[id->driver_info];
+       usbtouch->type = type;
+       if (!type->process_pkt)
+               type->process_pkt = usbtouch_process_pkt;
+
+       usbtouch->data = usb_buffer_alloc(udev, type->rept_size,
+                                         SLAB_KERNEL, &usbtouch->data_dma);
+       if (!usbtouch->data)
+               goto out_free;
+
+       if (type->flags & USBTOUCH_FLG_BUFFER) {
+               usbtouch->buffer = kmalloc(type->rept_size, GFP_KERNEL);
+               if (!usbtouch->buffer)
+                       goto out_free_buffers;
+       }
+
+       usbtouch->irq = usb_alloc_urb(0, GFP_KERNEL);
+       if (!usbtouch->irq) {
+               dbg("%s - usb_alloc_urb failed: usbtouch->irq", __FUNCTION__);
+               goto out_free_buffers;
+       }
+
+       usbtouch->udev = udev;
+       usbtouch->input = input_dev;
+
+       if (udev->manufacturer)
+               strlcpy(usbtouch->name, udev->manufacturer, sizeof(usbtouch->name));
+
+       if (udev->product) {
+               if (udev->manufacturer)
+                       strlcat(usbtouch->name, " ", sizeof(usbtouch->name));
+               strlcat(usbtouch->name, udev->product, sizeof(usbtouch->name));
+       }
+
+       if (!strlen(usbtouch->name))
+               snprintf(usbtouch->name, sizeof(usbtouch->name),
+                       "USB Touchscreen %04x:%04x",
+                        le16_to_cpu(udev->descriptor.idVendor),
+                        le16_to_cpu(udev->descriptor.idProduct));
+
+       usb_make_path(udev, usbtouch->phys, sizeof(usbtouch->phys));
+       strlcpy(usbtouch->phys, "/input0", sizeof(usbtouch->phys));
+
+       input_dev->name = usbtouch->name;
+       input_dev->phys = usbtouch->phys;
+       usb_to_input_id(udev, &input_dev->id);
+       input_dev->cdev.dev = &intf->dev;
+       input_dev->private = usbtouch;
+       input_dev->open = usbtouch_open;
+       input_dev->close = usbtouch_close;
+
+       input_dev->evbit[0] = BIT(EV_KEY) | BIT(EV_ABS);
+       input_dev->keybit[LONG(BTN_TOUCH)] = BIT(BTN_TOUCH);
+       input_set_abs_params(input_dev, ABS_X, type->min_xc, type->max_xc, 0, 0);
+       input_set_abs_params(input_dev, ABS_Y, type->min_yc, type->max_yc, 0, 0);
+       if (type->max_press)
+               input_set_abs_params(input_dev, ABS_PRESSURE, type->min_press,
+                                    type->max_press, 0, 0);
+
+       usb_fill_int_urb(usbtouch->irq, usbtouch->udev,
+                        usb_rcvintpipe(usbtouch->udev, 0x81),
+                        usbtouch->data, type->rept_size,
+                        usbtouch_irq, usbtouch, endpoint->bInterval);
+
+       usbtouch->irq->transfer_dma = usbtouch->data_dma;
+       usbtouch->irq->transfer_flags |= URB_NO_TRANSFER_DMA_MAP;
+
+       /* device specific init */
+       if (type->init) {
+               err = type->init(usbtouch);
+               if (err) {
+                       dbg("%s - type->init() failed, err: %d", __FUNCTION__, err);
+                       goto out_free_buffers;
+               }
+       }
+
+       err = input_register_device(usbtouch->input);
+       if (err) {
+               dbg("%s - input_register_device failed, err: %d", __FUNCTION__, err);
+               goto out_free_buffers;
+       }
+
+       usb_set_intfdata(intf, usbtouch);
+
+       return 0;
+
+out_free_buffers:
+       usbtouch_free_buffers(udev, usbtouch);
+out_free:
+       input_free_device(input_dev);
+       kfree(usbtouch);
+       return -ENOMEM;
+}
+
+static void usbtouch_disconnect(struct usb_interface *intf)
+{
+       struct usbtouch_usb *usbtouch = usb_get_intfdata(intf);
+
+       dbg("%s - called", __FUNCTION__);
+
+       if (!usbtouch)
+               return;
+
+       dbg("%s - usbtouch is initialized, cleaning up", __FUNCTION__);
+       usb_set_intfdata(intf, NULL);
+       usb_kill_urb(usbtouch->irq);
+       input_unregister_device(usbtouch->input);
+       usb_free_urb(usbtouch->irq);
+       usbtouch_free_buffers(interface_to_usbdev(intf), usbtouch);
+       kfree(usbtouch);
+}
+
+MODULE_DEVICE_TABLE(usb, usbtouch_devices);
+
+static struct usb_driver usbtouch_driver = {
+       .name           = "usbtouchscreen",
+       .probe          = usbtouch_probe,
+       .disconnect     = usbtouch_disconnect,
+       .id_table       = usbtouch_devices,
+};
+
+static int __init usbtouch_init(void)
+{
+       return usb_register(&usbtouch_driver);
+}
+
+static void __exit usbtouch_cleanup(void)
+{
+       usb_deregister(&usbtouch_driver);
+}
+
+module_init(usbtouch_init);
+module_exit(usbtouch_cleanup);
+
+MODULE_AUTHOR(DRIVER_AUTHOR);
+MODULE_DESCRIPTION(DRIVER_DESC);
+MODULE_LICENSE("GPL");
+
+MODULE_ALIAS("touchkitusb");
+MODULE_ALIAS("itmtouch");
+MODULE_ALIAS("mtouchusb");
index d3e15df9e815ec32d819aa57b9c42544193cae7b..cf84c6096f299721be8c24cb66d8baa9d43aad45 100644 (file)
@@ -9,7 +9,7 @@
  *  Copyright (c) 2000 Daniel Egger            <egger@suse.de>
  *  Copyright (c) 2001 Frederic Lepied         <flepied@mandrakesoft.com>
  *  Copyright (c) 2004 Panagiotis Issaris      <panagiotis.issaris@mech.kuleuven.ac.be>
- *  Copyright (c) 2002-2005 Ping Cheng         <pingc@wacom.com>
+ *  Copyright (c) 2002-2006 Ping Cheng         <pingc@wacom.com>
  *
  *  ChangeLog:
  *      v0.1 (vp)  - Initial release
@@ -56,6 +56,8 @@
  *                - Merged wacom_intuos3_irq into wacom_intuos_irq
  *     v1.44 (pc) - Added support for Graphire4, Cintiq 710, Intuos3 6x11, etc.
  *                - Report Device IDs
+ *     v1.45 (pc) - Added support for DTF 521, Intuos3 12x12 and 12x19
+ *                - Minor data report fix
  */
 
 /*
@@ -78,7 +80,7 @@
 /*
  * Version Information
  */
-#define DRIVER_VERSION "v1.44"
+#define DRIVER_VERSION "v1.45"
 #define DRIVER_AUTHOR "Vojtech Pavlik <vojtech@ucw.cz>"
 #define DRIVER_DESC "USB Wacom Graphire and Wacom Intuos tablet driver"
 #define DRIVER_LICENSE "GPL"
@@ -99,6 +101,8 @@ enum {
        PL,
        INTUOS,
        INTUOS3,
+       INTUOS312,
+       INTUOS319,
        CINTIQ,
        MAX_TYPE
 };
@@ -127,7 +131,19 @@ struct wacom {
        char phys[32];
 };
 
+#define USB_REQ_GET_REPORT     0x01
 #define USB_REQ_SET_REPORT     0x09
+
+static int usb_get_report(struct usb_interface *intf, unsigned char type,
+                               unsigned char id, void *buf, int size)
+{
+       return usb_control_msg(interface_to_usbdev(intf),
+               usb_rcvctrlpipe(interface_to_usbdev(intf), 0),
+               USB_REQ_GET_REPORT, USB_TYPE_CLASS | USB_RECIP_INTERFACE,
+               (type << 8) + id, intf->altsetting[0].desc.bInterfaceNumber,
+               buf, size, 100);
+}
+
 static int usb_set_report(struct usb_interface *intf, unsigned char type,
                                unsigned char id, void *buf, int size)
 {
@@ -206,7 +222,8 @@ static void wacom_pl_irq(struct urb *urb, struct pt_regs *regs)
                        wacom->tool[1] = BTN_TOOL_PEN;
                        id = STYLUS_DEVICE_ID;
                }
-               input_report_key(dev, wacom->tool[1], id); /* report in proximity for tool */
+               input_report_key(dev, wacom->tool[1], prox); /* report in proximity for tool */
+               input_report_abs(dev, ABS_MISC, id); /* report tool id */
                input_report_abs(dev, ABS_X, data[3] | (data[2] << 7) | ((data[1] & 0x03) << 14));
                input_report_abs(dev, ABS_Y, data[6] | (data[5] << 7) | ((data[4] & 0x03) << 14));
                input_report_abs(dev, ABS_PRESSURE, pressure);
@@ -239,7 +256,7 @@ static void wacom_ptu_irq(struct urb *urb, struct pt_regs *regs)
        struct wacom *wacom = urb->context;
        unsigned char *data = wacom->data;
        struct input_dev *dev = wacom->dev;
-       int retval;
+       int retval, id;
 
        switch (urb->status) {
        case 0:
@@ -263,12 +280,15 @@ static void wacom_ptu_irq(struct urb *urb, struct pt_regs *regs)
 
        input_regs(dev, regs);
        if (data[1] & 0x04) {
-               input_report_key(dev, BTN_TOOL_RUBBER, (data[1] & 0x20) ? ERASER_DEVICE_ID : 0);
+               input_report_key(dev, BTN_TOOL_RUBBER, data[1] & 0x20);
                input_report_key(dev, BTN_TOUCH, data[1] & 0x08);
+               id = ERASER_DEVICE_ID;
        } else {
-               input_report_key(dev, BTN_TOOL_PEN, (data[1] & 0x20) ? STYLUS_DEVICE_ID : 0);
+               input_report_key(dev, BTN_TOOL_PEN, data[1] & 0x20);
                input_report_key(dev, BTN_TOUCH, data[1] & 0x01);
+               id = STYLUS_DEVICE_ID;
        }
+       input_report_abs(dev, ABS_MISC, id); /* report tool id */
        input_report_abs(dev, ABS_X, le16_to_cpu(*(__le16 *) &data[2]));
        input_report_abs(dev, ABS_Y, le16_to_cpu(*(__le16 *) &data[4]));
        input_report_abs(dev, ABS_PRESSURE, le16_to_cpu(*(__le16 *) &data[6]));
@@ -312,7 +332,8 @@ static void wacom_penpartner_irq(struct urb *urb, struct pt_regs *regs)
        }
 
        input_regs(dev, regs);
-       input_report_key(dev, BTN_TOOL_PEN, STYLUS_DEVICE_ID);
+       input_report_key(dev, BTN_TOOL_PEN, 1);
+       input_report_abs(dev, ABS_MISC, STYLUS_DEVICE_ID); /* report tool id */
        input_report_abs(dev, ABS_X, le16_to_cpu(*(__le16 *) &data[1]));
        input_report_abs(dev, ABS_Y, le16_to_cpu(*(__le16 *) &data[3]));
        input_report_abs(dev, ABS_PRESSURE, (signed char)data[6] + 127);
@@ -350,6 +371,8 @@ static void wacom_graphire_irq(struct urb *urb, struct pt_regs *regs)
                goto exit;
        }
 
+       if (data[0] == 99) return; /* for Volito tablets */
+
        if (data[0] != 2) {
                dbg("wacom_graphire_irq: received unknown report #%d", data[0]);
                goto exit;
@@ -374,10 +397,10 @@ static void wacom_graphire_irq(struct urb *urb, struct pt_regs *regs)
                        case 2: /* Mouse with wheel */
                                input_report_key(dev, BTN_MIDDLE, data[1] & 0x04);
                                if (wacom->features->type == WACOM_G4) {
-                                       rw = data[7] & 0x04 ? -(data[7] & 0x03) : (data[7] & 0x03);
-                                       input_report_rel(dev, REL_WHEEL, rw);
+                                       rw = data[7] & 0x04 ? (data[7] & 0x03)-4 : (data[7] & 0x03);
+                                       input_report_rel(dev, REL_WHEEL, -rw);
                                } else
-                                       input_report_rel(dev, REL_WHEEL, (signed char) data[6]);
+                                       input_report_rel(dev, REL_WHEEL, -(signed char) data[6]);
                                /* fall through */
 
                        case 3: /* Mouse without wheel */
@@ -406,39 +429,27 @@ static void wacom_graphire_irq(struct urb *urb, struct pt_regs *regs)
                }
        }
 
-       input_report_key(dev, wacom->tool[0], (data[1] & 0x10) ? id : 0);
+       if (data[1] & 0x10)
+               input_report_abs(dev, ABS_MISC, id); /* report tool id */
+       else
+               input_report_abs(dev, ABS_MISC, 0); /* reset tool id */
+       input_report_key(dev, wacom->tool[0], data[1] & 0x10);
        input_sync(dev);
 
        /* send pad data */
        if (wacom->features->type == WACOM_G4) {
-               /* fist time sending pad data */
-               if (wacom->tool[1] != BTN_TOOL_FINGER) {
-                       wacom->id[1] = 0;
-                       wacom->serial[1] = (data[7] & 0x38) >> 2;
-               }
-               if (data[7] & 0xf8) {
+               if ((wacom->serial[1] & 0xc0) != (data[7] & 0xf8)) {
+                       wacom->id[1] = 1;
+                       wacom->serial[1] = (data[7] & 0xf8);
                        input_report_key(dev, BTN_0, (data[7] & 0x40));
                        input_report_key(dev, BTN_4, (data[7] & 0x80));
-                       if (((data[7] & 0x38) >> 2) == (wacom->serial[1] & 0x0e))
-                               /* alter REL_WHEEL value so X apps can get it */
-                               wacom->serial[1] += (wacom->serial[1] & 0x01) ? -1 : 1;
-                       else
-                                wacom->serial[1] = (data[7] & 0x38 ) >> 2;
-
-                       /* don't alter the value when there is no wheel event */
-                       if (wacom->serial[1] == 1)
-                               wacom->serial[1] = 0;
-                       rw = wacom->serial[1];
-                       rw = (rw & 0x08) ? -(rw & 0x07) : (rw & 0x07);
+                       rw = ((data[7] & 0x18) >> 3) - ((data[7] & 0x20) >> 3);
                        input_report_rel(dev, REL_WHEEL, rw);
-                       wacom->tool[1] = BTN_TOOL_FINGER;
-                       wacom->id[1] = data[7] & 0xf8;
-                       input_report_key(dev, wacom->tool[1], 0xf0);
+                       input_report_key(dev, BTN_TOOL_FINGER, 0xf0);
                        input_event(dev, EV_MSC, MSC_SERIAL, 0xf0);
                } else if (wacom->id[1]) {
                        wacom->id[1] = 0;
-                       wacom->serial[1] = 0;
-                       input_report_key(dev, wacom->tool[1], 0);
+                       input_report_key(dev, BTN_TOOL_FINGER, 0);
                        input_event(dev, EV_MSC, MSC_SERIAL, 0xf0);
                }
                input_sync(dev);
@@ -516,21 +527,31 @@ static int wacom_intuos_inout(struct urb *urb)
                        default: /* Unknown tool */
                                wacom->tool[idx] = BTN_TOOL_PEN;
                }
-               input_report_key(dev, wacom->tool[idx], wacom->id[idx]);
-               input_event(dev, EV_MSC, MSC_SERIAL, wacom->serial[idx]);
-               input_sync(dev);
+               if(!((wacom->tool[idx] == BTN_TOOL_LENS) &&
+                               ((wacom->features->type == INTUOS312)
+                                       || (wacom->features->type == INTUOS319)))) {
+                       input_report_abs(dev, ABS_MISC, wacom->id[idx]); /* report tool id */
+                       input_report_key(dev, wacom->tool[idx], 1);
+                       input_event(dev, EV_MSC, MSC_SERIAL, wacom->serial[idx]);
+                       input_sync(dev);
+               }
                return 1;
        }
 
        /* Exit report */
        if ((data[1] & 0xfe) == 0x80) {
                input_report_key(dev, wacom->tool[idx], 0);
+               input_report_abs(dev, ABS_MISC, 0); /* reset tool id */
                input_event(dev, EV_MSC, MSC_SERIAL, wacom->serial[idx]);
                input_sync(dev);
                return 1;
        }
 
-       return 0;
+       if((wacom->tool[idx] == BTN_TOOL_LENS) && ((wacom->features->type == INTUOS312)
+                       || (wacom->features->type == INTUOS319)))
+               return 1;
+       else
+               return 0;
 }
 
 static void wacom_intuos_general(struct urb *urb)
@@ -600,10 +621,9 @@ static void wacom_intuos_irq(struct urb *urb, struct pt_regs *regs)
        /* pad packets. Works as a second tool and is always in prox */
        if (data[0] == 12) {
                /* initiate the pad as a device */
-               if (wacom->tool[1] != BTN_TOOL_FINGER) {
+               if (wacom->tool[1] != BTN_TOOL_FINGER)
                        wacom->tool[1] = BTN_TOOL_FINGER;
-                       input_report_key(dev, wacom->tool[1], 1);
-               }
+
                input_report_key(dev, BTN_0, (data[5] & 0x01));
                input_report_key(dev, BTN_1, (data[5] & 0x02));
                input_report_key(dev, BTN_2, (data[5] & 0x04));
@@ -614,6 +634,11 @@ static void wacom_intuos_irq(struct urb *urb, struct pt_regs *regs)
                input_report_key(dev, BTN_7, (data[6] & 0x08));
                input_report_abs(dev, ABS_RX, ((data[1] & 0x1f) << 8) | data[2]);
                input_report_abs(dev, ABS_RY, ((data[3] & 0x1f) << 8) | data[4]);
+
+               if((data[5] & 0x0f) | (data[6] & 0x0f) | (data[1] & 0x1f) | data[2])
+                       input_report_key(dev, wacom->tool[1], 1);
+               else
+                       input_report_key(dev, wacom->tool[1], 0);
                input_event(dev, EV_MSC, MSC_SERIAL, 0xffffffff);
                input_sync(dev);
                goto exit;
@@ -676,8 +701,8 @@ static void wacom_intuos_irq(struct urb *urb, struct pt_regs *regs)
                        input_report_key(dev, BTN_LEFT,   data[8] & 0x04);
                        input_report_key(dev, BTN_MIDDLE, data[8] & 0x08);
                        input_report_key(dev, BTN_RIGHT,  data[8] & 0x10);
-                       input_report_rel(dev, REL_WHEEL, ((data[8] & 0x02) >> 1)
-                                                - (data[8] & 0x01));
+                       input_report_rel(dev, REL_WHEEL, (data[8] & 0x01)
+                                                - ((data[8] & 0x02) >> 1));
 
                        /* I3 2D mouse side buttons */
                        if (wacom->features->type == INTUOS3) {
@@ -695,7 +720,8 @@ static void wacom_intuos_irq(struct urb *urb, struct pt_regs *regs)
                }
        }
 
-       input_report_key(dev, wacom->tool[idx], wacom->id[idx]);
+       input_report_abs(dev, ABS_MISC, wacom->id[idx]); /* report tool id */
+       input_report_key(dev, wacom->tool[idx], 1);
        input_event(dev, EV_MSC, MSC_SERIAL, wacom->serial[idx]);
        input_sync(dev);
 
@@ -733,7 +759,8 @@ static struct wacom_features wacom_features[] = {
        { "Wacom PL800",         8,   7220,  5780,  511, 32, PL,         wacom_pl_irq },
        { "Wacom PL700",         8,   6758,  5406,  511, 32, PL,         wacom_pl_irq },
        { "Wacom PL510",         8,   6282,  4762,  511, 32, PL,         wacom_pl_irq },
-       { "Wacom PL710",         8,  34080, 27660,  511, 32, PL,         wacom_pl_irq },
+       { "Wacom DTU710",        8,  34080, 27660,  511, 32, PL,         wacom_pl_irq },
+       { "Wacom DTF521",        8,   6282,  4762,  511, 32, PL,         wacom_pl_irq },
        { "Wacom DTF720",        8,   6858,  5506,  511, 32, PL,         wacom_pl_irq },
        { "Wacom Cintiq Partner",8,  20480, 15360,  511, 32, PL,         wacom_ptu_irq },
        { "Wacom Intuos2 4x5",   10, 12700, 10600, 1023, 15, INTUOS,     wacom_intuos_irq },
@@ -744,6 +771,8 @@ static struct wacom_features wacom_features[] = {
        { "Wacom Intuos3 4x5",   10, 25400, 20320, 1023, 15, INTUOS3,    wacom_intuos_irq },
        { "Wacom Intuos3 6x8",   10, 40640, 30480, 1023, 15, INTUOS3,    wacom_intuos_irq },
        { "Wacom Intuos3 9x12",  10, 60960, 45720, 1023, 15, INTUOS3,    wacom_intuos_irq },
+       { "Wacom Intuos3 12x12", 10, 60960, 60960, 1023, 15, INTUOS312,  wacom_intuos_irq },
+       { "Wacom Intuos3 12x19", 10, 97536, 60960, 1023, 15, INTUOS319,  wacom_intuos_irq },
        { "Wacom Intuos3 6x11",  10, 54204, 31750, 1023, 15, INTUOS3,    wacom_intuos_irq },
        { "Wacom Cintiq 21UX",   10, 87200, 65600, 1023, 15, CINTIQ,     wacom_intuos_irq },
        { "Wacom Intuos2 6x8",   10, 20320, 16240, 1023, 15, INTUOS,     wacom_intuos_irq },
@@ -779,6 +808,7 @@ static struct usb_device_id wacom_ids[] = {
        { USB_DEVICE(USB_VENDOR_ID_WACOM, 0x38) },
        { USB_DEVICE(USB_VENDOR_ID_WACOM, 0x39) },
        { USB_DEVICE(USB_VENDOR_ID_WACOM, 0xC0) },
+       { USB_DEVICE(USB_VENDOR_ID_WACOM, 0xC3) },
        { USB_DEVICE(USB_VENDOR_ID_WACOM, 0x03) },
        { USB_DEVICE(USB_VENDOR_ID_WACOM, 0x41) },
        { USB_DEVICE(USB_VENDOR_ID_WACOM, 0x42) },
@@ -788,6 +818,8 @@ static struct usb_device_id wacom_ids[] = {
        { USB_DEVICE(USB_VENDOR_ID_WACOM, 0xB0) },
        { USB_DEVICE(USB_VENDOR_ID_WACOM, 0xB1) },
        { USB_DEVICE(USB_VENDOR_ID_WACOM, 0xB2) },
+       { USB_DEVICE(USB_VENDOR_ID_WACOM, 0xB3) },
+       { USB_DEVICE(USB_VENDOR_ID_WACOM, 0xB4) },
        { USB_DEVICE(USB_VENDOR_ID_WACOM, 0xB5) },
        { USB_DEVICE(USB_VENDOR_ID_WACOM, 0x3F) },
        { USB_DEVICE(USB_VENDOR_ID_WACOM, 0x47) },
@@ -820,7 +852,7 @@ static int wacom_probe(struct usb_interface *intf, const struct usb_device_id *i
        struct usb_endpoint_descriptor *endpoint;
        struct wacom *wacom;
        struct input_dev *input_dev;
-       char rep_data[2] = {0x02, 0x02};
+       char rep_data[2], limit = 0;
 
        wacom = kzalloc(sizeof(struct wacom), GFP_KERNEL);
        input_dev = input_allocate_device();
@@ -857,6 +889,7 @@ static int wacom_probe(struct usb_interface *intf, const struct usb_device_id *i
        input_set_abs_params(input_dev, ABS_X, 0, wacom->features->x_max, 4, 0);
        input_set_abs_params(input_dev, ABS_Y, 0, wacom->features->y_max, 4, 0);
        input_set_abs_params(input_dev, ABS_PRESSURE, 0, wacom->features->pressure_max, 0, 0);
+       input_dev->absbit[LONG(ABS_MISC)] |= BIT(ABS_MISC);
 
        switch (wacom->features->type) {
                case WACOM_G4:
@@ -875,6 +908,8 @@ static int wacom_probe(struct usb_interface *intf, const struct usb_device_id *i
                        break;
 
                case INTUOS3:
+               case INTUOS312:
+               case INTUOS319:
                case CINTIQ:
                        input_dev->keybit[LONG(BTN_DIGI)] |= BIT(BTN_TOOL_FINGER);
                        input_dev->keybit[LONG(BTN_LEFT)] |= BIT(BTN_0) | BIT(BTN_1) | BIT(BTN_2) | BIT(BTN_3) | BIT(BTN_4) | BIT(BTN_5) | BIT(BTN_6) | BIT(BTN_7);
@@ -916,10 +951,13 @@ static int wacom_probe(struct usb_interface *intf, const struct usb_device_id *i
 
        input_register_device(wacom->dev);
 
-       /* ask the tablet to report tablet data */
-       usb_set_report(intf, 3, 2, rep_data, 2);
-       /* repeat once (not sure why the first call often fails) */
-       usb_set_report(intf, 3, 2, rep_data, 2);
+       /* Ask the tablet to report tablet data. Repeat until it succeeds */
+       do {
+               rep_data[0] = 2;
+               rep_data[1] = 2;
+               usb_set_report(intf, 3, 2, rep_data, 2);
+               usb_get_report(intf, 3, 2, rep_data, 2);
+       } while (rep_data[1] != 2 && limit++ < 5);
 
        usb_set_intfdata(intf, wacom);
        return 0;
index 9d59b901841cc46908dde0aea2cb64e218992731..ccc5e8238bd889581b2b445cdb4b26108b5c6644 100644 (file)
@@ -381,6 +381,7 @@ alloc_sglist (int nents, int max, int vary)
 
        for (i = 0; i < nents; i++) {
                char            *buf;
+               unsigned        j;
 
                buf = kzalloc (size, SLAB_KERNEL);
                if (!buf) {
@@ -391,6 +392,16 @@ alloc_sglist (int nents, int max, int vary)
                /* kmalloc pages are always physically contiguous! */
                sg_init_one(&sg[i], buf, size);
 
+               switch (pattern) {
+               case 0:
+                       /* already zeroed */
+                       break;
+               case 1:
+                       for (j = 0; j < size; j++)
+                               *buf++ = (u8) (j % 63);
+                       break;
+               }
+
                if (vary) {
                        size += vary;
                        size %= max;
@@ -425,6 +436,8 @@ static int perform_sglist (
                usb_sg_wait (req);
                retval = req->status;
 
+               /* FIXME check resulting data pattern */
+
                /* FIXME if endpoint halted, clear halt (and log) */
        }
 
index 3094970615cb9c8ce2aefd5013fc0181b2a230f8..12b599a0b53989d69233734c956865eeab006d70 100644 (file)
@@ -37,7 +37,6 @@
 
 #include "usbnet.h"
 
-
 /* ASIX AX8817X based USB 2.0 Ethernet Devices */
 
 #define AX_CMD_SET_SW_MII              0x06
 #define AX_EEPROM_MAGIC                        0xdeadbeef
 
 /* This structure cannot exceed sizeof(unsigned long [5]) AKA 20 bytes */
-struct ax8817x_data {
+struct asix_data {
        u8 multi_filter[AX_MCAST_FILTER_SIZE];
 };
 
@@ -121,7 +120,7 @@ struct ax88172_int_data {
        u16 res3;
 } __attribute__ ((packed));
 
-static int ax8817x_read_cmd(struct usbnet *dev, u8 cmd, u16 value, u16 index,
+static int asix_read_cmd(struct usbnet *dev, u8 cmd, u16 value, u16 index,
                            u16 size, void *data)
 {
        return usb_control_msg(
@@ -136,7 +135,7 @@ static int ax8817x_read_cmd(struct usbnet *dev, u8 cmd, u16 value, u16 index,
                USB_CTRL_GET_TIMEOUT);
 }
 
-static int ax8817x_write_cmd(struct usbnet *dev, u8 cmd, u16 value, u16 index,
+static int asix_write_cmd(struct usbnet *dev, u8 cmd, u16 value, u16 index,
                             u16 size, void *data)
 {
        return usb_control_msg(
@@ -151,19 +150,80 @@ static int ax8817x_write_cmd(struct usbnet *dev, u8 cmd, u16 value, u16 index,
                USB_CTRL_SET_TIMEOUT);
 }
 
-static void ax8817x_async_cmd_callback(struct urb *urb, struct pt_regs *regs)
+static void asix_async_cmd_callback(struct urb *urb, struct pt_regs *regs)
 {
        struct usb_ctrlrequest *req = (struct usb_ctrlrequest *)urb->context;
 
        if (urb->status < 0)
-               printk(KERN_DEBUG "ax8817x_async_cmd_callback() failed with %d",
+               printk(KERN_DEBUG "asix_async_cmd_callback() failed with %d",
                        urb->status);
 
        kfree(req);
        usb_free_urb(urb);
 }
 
-static void ax8817x_status(struct usbnet *dev, struct urb *urb)
+static inline int asix_set_sw_mii(struct usbnet *dev)
+{
+       int ret;
+       ret = asix_write_cmd(dev, AX_CMD_SET_SW_MII, 0x0000, 0, 0, NULL);
+       if (ret < 0)
+               devdbg(dev, "Failed to enable software MII access");
+       return ret;
+}
+
+static inline int asix_set_hw_mii(struct usbnet *dev)
+{
+       int ret;
+       ret = asix_write_cmd(dev, AX_CMD_SET_HW_MII, 0x0000, 0, 0, NULL);
+       if (ret < 0)
+               devdbg(dev, "Failed to enable hardware MII access");
+       return ret;
+}
+
+static inline int asix_get_phyid(struct usbnet *dev)
+{
+       int ret = 0;
+       void *buf;
+
+       buf = kmalloc(2, GFP_KERNEL);
+       if (!buf)
+               goto out1;
+
+       if ((ret = asix_read_cmd(dev, AX_CMD_READ_PHY_ID,
+                                   0, 0, 2, buf)) < 2) {
+               devdbg(dev, "Error reading PHYID register: %02x", ret);
+               goto out2;
+       }
+       ret = *((u8 *)buf + 1);
+out2:
+       kfree(buf);
+out1:
+       return ret;
+}
+
+static int asix_sw_reset(struct usbnet *dev, u8 flags)
+{
+       int ret;
+
+        ret = asix_write_cmd(dev, AX_CMD_SW_RESET, flags, 0, 0, NULL);
+       if (ret < 0)
+               devdbg(dev,"Failed to send software reset: %02x", ret);
+
+       return ret;
+}
+
+static int asix_write_rx_ctl(struct usbnet *dev, u16 mode)
+{
+       int ret;
+
+       ret = asix_write_cmd(dev, AX_CMD_WRITE_RX_CTL, mode, 0, 0, NULL);
+       if (ret < 0)
+                devdbg(dev, "Failed to write RX_CTL mode: %02x", ret);
+
+       return ret;
+}
+
+static void asix_status(struct usbnet *dev, struct urb *urb)
 {
        struct ax88172_int_data *event;
        int link;
@@ -179,12 +239,12 @@ static void ax8817x_status(struct usbnet *dev, struct urb *urb)
                        usbnet_defer_kevent (dev, EVENT_LINK_RESET );
                } else
                        netif_carrier_off(dev->net);
-               devdbg(dev, "ax8817x - Link Status is: %d", link);
+               devdbg(dev, "Link Status is: %d", link);
        }
 }
 
 static void
-ax8817x_write_cmd_async(struct usbnet *dev, u8 cmd, u16 value, u16 index,
+asix_write_cmd_async(struct usbnet *dev, u8 cmd, u16 value, u16 index,
                                    u16 size, void *data)
 {
        struct usb_ctrlrequest *req;
@@ -211,7 +271,7 @@ ax8817x_write_cmd_async(struct usbnet *dev, u8 cmd, u16 value, u16 index,
        usb_fill_control_urb(urb, dev->udev,
                             usb_sndctrlpipe(dev->udev, 0),
                             (void *)req, data, size,
-                            ax8817x_async_cmd_callback, req);
+                            asix_async_cmd_callback, req);
 
        if((status = usb_submit_urb(urb, GFP_ATOMIC)) < 0) {
                deverr(dev, "Error submitting the control message: status=%d",
@@ -221,10 +281,10 @@ ax8817x_write_cmd_async(struct usbnet *dev, u8 cmd, u16 value, u16 index,
        }
 }
 
-static void ax8817x_set_multicast(struct net_device *net)
+static void asix_set_multicast(struct net_device *net)
 {
        struct usbnet *dev = netdev_priv(net);
-       struct ax8817x_data *data = (struct ax8817x_data *)&dev->data;
+       struct asix_data *data = (struct asix_data *)&dev->data;
        u8 rx_ctl = 0x8c;
 
        if (net->flags & IFF_PROMISC) {
@@ -255,53 +315,51 @@ static void ax8817x_set_multicast(struct net_device *net)
                        mc_list = mc_list->next;
                }
 
-               ax8817x_write_cmd_async(dev, AX_CMD_WRITE_MULTI_FILTER, 0, 0,
+               asix_write_cmd_async(dev, AX_CMD_WRITE_MULTI_FILTER, 0, 0,
                                   AX_MCAST_FILTER_SIZE, data->multi_filter);
 
                rx_ctl |= 0x10;
        }
 
-       ax8817x_write_cmd_async(dev, AX_CMD_WRITE_RX_CTL, rx_ctl, 0, 0, NULL);
+       asix_write_cmd_async(dev, AX_CMD_WRITE_RX_CTL, rx_ctl, 0, 0, NULL);
 }
 
-static int ax8817x_mdio_read(struct net_device *netdev, int phy_id, int loc)
+static int asix_mdio_read(struct net_device *netdev, int phy_id, int loc)
 {
        struct usbnet *dev = netdev_priv(netdev);
        u16 res;
-       u8 buf[1];
 
-       ax8817x_write_cmd(dev, AX_CMD_SET_SW_MII, 0, 0, 0, &buf);
-       ax8817x_read_cmd(dev, AX_CMD_READ_MII_REG, phy_id,
+       asix_set_sw_mii(dev);
+       asix_read_cmd(dev, AX_CMD_READ_MII_REG, phy_id,
                                (__u16)loc, 2, (u16 *)&res);
-       ax8817x_write_cmd(dev, AX_CMD_SET_HW_MII, 0, 0, 0, &buf);
+       asix_set_hw_mii(dev);
 
        return res & 0xffff;
 }
 
 /* same as above, but converts resulting value to cpu byte order */
-static int ax8817x_mdio_read_le(struct net_device *netdev, int phy_id, int loc)
+static int asix_mdio_read_le(struct net_device *netdev, int phy_id, int loc)
 {
-       return le16_to_cpu(ax8817x_mdio_read(netdev,phy_id, loc));
+       return le16_to_cpu(asix_mdio_read(netdev,phy_id, loc));
 }
 
 static void
-ax8817x_mdio_write(struct net_device *netdev, int phy_id, int loc, int val)
+asix_mdio_write(struct net_device *netdev, int phy_id, int loc, int val)
 {
        struct usbnet *dev = netdev_priv(netdev);
        u16 res = val;
-       u8 buf[1];
 
-       ax8817x_write_cmd(dev, AX_CMD_SET_SW_MII, 0, 0, 0, &buf);
-       ax8817x_write_cmd(dev, AX_CMD_WRITE_MII_REG, phy_id,
+       asix_set_sw_mii(dev);
+       asix_write_cmd(dev, AX_CMD_WRITE_MII_REG, phy_id,
                                (__u16)loc, 2, (u16 *)&res);
-       ax8817x_write_cmd(dev, AX_CMD_SET_HW_MII, 0, 0, 0, &buf);
+       asix_set_hw_mii(dev);
 }
 
 /* same as above, but converts new value to le16 byte order before writing */
 static void
-ax8817x_mdio_write_le(struct net_device *netdev, int phy_id, int loc, int val)
+asix_mdio_write_le(struct net_device *netdev, int phy_id, int loc, int val)
 {
-       ax8817x_mdio_write( netdev, phy_id, loc, cpu_to_le16(val) );
+       asix_mdio_write( netdev, phy_id, loc, cpu_to_le16(val) );
 }
 
 static int ax88172_link_reset(struct usbnet *dev)
@@ -312,23 +370,23 @@ static int ax88172_link_reset(struct usbnet *dev)
        u8 mode;
 
        mode = AX_MEDIUM_TX_ABORT_ALLOW | AX_MEDIUM_FLOW_CONTROL_EN;
-       lpa = ax8817x_mdio_read_le(dev->net, dev->mii.phy_id, MII_LPA);
-       adv = ax8817x_mdio_read_le(dev->net, dev->mii.phy_id, MII_ADVERTISE);
+       lpa = asix_mdio_read_le(dev->net, dev->mii.phy_id, MII_LPA);
+       adv = asix_mdio_read_le(dev->net, dev->mii.phy_id, MII_ADVERTISE);
        res = mii_nway_result(lpa|adv);
        if (res & LPA_DUPLEX)
                mode |= AX_MEDIUM_FULL_DUPLEX;
-       ax8817x_write_cmd(dev, AX_CMD_WRITE_MEDIUM_MODE, mode, 0, 0, NULL);
+       asix_write_cmd(dev, AX_CMD_WRITE_MEDIUM_MODE, mode, 0, 0, NULL);
 
        return 0;
 }
 
 static void
-ax8817x_get_wol(struct net_device *net, struct ethtool_wolinfo *wolinfo)
+asix_get_wol(struct net_device *net, struct ethtool_wolinfo *wolinfo)
 {
        struct usbnet *dev = netdev_priv(net);
        u8 opt;
 
-       if (ax8817x_read_cmd(dev, AX_CMD_READ_MONITOR_MODE, 0, 0, 1, &opt) < 0) {
+       if (asix_read_cmd(dev, AX_CMD_READ_MONITOR_MODE, 0, 0, 1, &opt) < 0) {
                wolinfo->supported = 0;
                wolinfo->wolopts = 0;
                return;
@@ -344,7 +402,7 @@ ax8817x_get_wol(struct net_device *net, struct ethtool_wolinfo *wolinfo)
 }
 
 static int
-ax8817x_set_wol(struct net_device *net, struct ethtool_wolinfo *wolinfo)
+asix_set_wol(struct net_device *net, struct ethtool_wolinfo *wolinfo)
 {
        struct usbnet *dev = netdev_priv(net);
        u8 opt = 0;
@@ -357,19 +415,19 @@ ax8817x_set_wol(struct net_device *net, struct ethtool_wolinfo *wolinfo)
        if (opt != 0)
                opt |= AX_MONITOR_MODE;
 
-       if (ax8817x_write_cmd(dev, AX_CMD_WRITE_MONITOR_MODE,
+       if (asix_write_cmd(dev, AX_CMD_WRITE_MONITOR_MODE,
                              opt, 0, 0, &buf) < 0)
                return -EINVAL;
 
        return 0;
 }
 
-static int ax8817x_get_eeprom_len(struct net_device *net)
+static int asix_get_eeprom_len(struct net_device *net)
 {
        return AX_EEPROM_LEN;
 }
 
-static int ax8817x_get_eeprom(struct net_device *net,
+static int asix_get_eeprom(struct net_device *net,
                              struct ethtool_eeprom *eeprom, u8 *data)
 {
        struct usbnet *dev = netdev_priv(net);
@@ -386,14 +444,14 @@ static int ax8817x_get_eeprom(struct net_device *net,
 
        /* ax8817x returns 2 bytes from eeprom on read */
        for (i=0; i < eeprom->len / 2; i++) {
-               if (ax8817x_read_cmd(dev, AX_CMD_READ_EEPROM,
+               if (asix_read_cmd(dev, AX_CMD_READ_EEPROM,
                        eeprom->offset + i, 0, 2, &ebuf[i]) < 0)
                        return -EINVAL;
        }
        return 0;
 }
 
-static void ax8817x_get_drvinfo (struct net_device *net,
+static void asix_get_drvinfo (struct net_device *net,
                                 struct ethtool_drvinfo *info)
 {
        /* Inherit standard device info */
@@ -401,14 +459,14 @@ static void ax8817x_get_drvinfo (struct net_device *net,
        info->eedump_len = 0x3e;
 }
 
-static int ax8817x_get_settings(struct net_device *net, struct ethtool_cmd *cmd)
+static int asix_get_settings(struct net_device *net, struct ethtool_cmd *cmd)
 {
        struct usbnet *dev = netdev_priv(net);
 
        return mii_ethtool_gset(&dev->mii,cmd);
 }
 
-static int ax8817x_set_settings(struct net_device *net, struct ethtool_cmd *cmd)
+static int asix_set_settings(struct net_device *net, struct ethtool_cmd *cmd)
 {
        struct usbnet *dev = netdev_priv(net);
 
@@ -418,27 +476,27 @@ static int ax8817x_set_settings(struct net_device *net, struct ethtool_cmd *cmd)
 /* We need to override some ethtool_ops so we require our
    own structure so we don't interfere with other usbnet
    devices that may be connected at the same time. */
-static struct ethtool_ops ax8817x_ethtool_ops = {
-       .get_drvinfo            = ax8817x_get_drvinfo,
+static struct ethtool_ops ax88172_ethtool_ops = {
+       .get_drvinfo            = asix_get_drvinfo,
        .get_link               = ethtool_op_get_link,
        .get_msglevel           = usbnet_get_msglevel,
        .set_msglevel           = usbnet_set_msglevel,
-       .get_wol                = ax8817x_get_wol,
-       .set_wol                = ax8817x_set_wol,
-       .get_eeprom_len         = ax8817x_get_eeprom_len,
-       .get_eeprom             = ax8817x_get_eeprom,
-       .get_settings           = ax8817x_get_settings,
-       .set_settings           = ax8817x_set_settings,
+       .get_wol                = asix_get_wol,
+       .set_wol                = asix_set_wol,
+       .get_eeprom_len         = asix_get_eeprom_len,
+       .get_eeprom             = asix_get_eeprom,
+       .get_settings           = asix_get_settings,
+       .set_settings           = asix_set_settings,
 };
 
-static int ax8817x_ioctl (struct net_device *net, struct ifreq *rq, int cmd)
+static int asix_ioctl (struct net_device *net, struct ifreq *rq, int cmd)
 {
        struct usbnet *dev = netdev_priv(net);
 
        return generic_mii_ioctl(&dev->mii, if_mii(rq), cmd, NULL);
 }
 
-static int ax8817x_bind(struct usbnet *dev, struct usb_interface *intf)
+static int ax88172_bind(struct usbnet *dev, struct usb_interface *intf)
 {
        int ret = 0;
        void *buf;
@@ -455,55 +513,39 @@ static int ax8817x_bind(struct usbnet *dev, struct usb_interface *intf)
 
        /* Toggle the GPIOs in a manufacturer/model specific way */
        for (i = 2; i >= 0; i--) {
-               if ((ret = ax8817x_write_cmd(dev, AX_CMD_WRITE_GPIOS,
+               if ((ret = asix_write_cmd(dev, AX_CMD_WRITE_GPIOS,
                                        (gpio_bits >> (i * 8)) & 0xff, 0, 0,
                                        buf)) < 0)
                        goto out2;
                msleep(5);
        }
 
-       if ((ret = ax8817x_write_cmd(dev, AX_CMD_WRITE_RX_CTL,
-                               0x80, 0, 0, buf)) < 0) {
-               dbg("send AX_CMD_WRITE_RX_CTL failed: %d", ret);
+       if ((ret = asix_write_rx_ctl(dev,0x80)) < 0)
                goto out2;
-       }
 
        /* Get the MAC address */
        memset(buf, 0, ETH_ALEN);
-       if ((ret = ax8817x_read_cmd(dev, AX_CMD_READ_NODE_ID,
+       if ((ret = asix_read_cmd(dev, AX_CMD_READ_NODE_ID,
                                0, 0, 6, buf)) < 0) {
                dbg("read AX_CMD_READ_NODE_ID failed: %d", ret);
                goto out2;
        }
        memcpy(dev->net->dev_addr, buf, ETH_ALEN);
 
-       /* Get the PHY id */
-       if ((ret = ax8817x_read_cmd(dev, AX_CMD_READ_PHY_ID,
-                               0, 0, 2, buf)) < 0) {
-               dbg("error on read AX_CMD_READ_PHY_ID: %02x", ret);
-               goto out2;
-       } else if (ret < 2) {
-               /* this should always return 2 bytes */
-               dbg("AX_CMD_READ_PHY_ID returned less than 2 bytes: ret=%02x",
-                               ret);
-               ret = -EIO;
-               goto out2;
-       }
-
        /* Initialize MII structure */
        dev->mii.dev = dev->net;
-       dev->mii.mdio_read = ax8817x_mdio_read;
-       dev->mii.mdio_write = ax8817x_mdio_write;
+       dev->mii.mdio_read = asix_mdio_read;
+       dev->mii.mdio_write = asix_mdio_write;
        dev->mii.phy_id_mask = 0x3f;
        dev->mii.reg_num_mask = 0x1f;
-       dev->mii.phy_id = *((u8 *)buf + 1);
-       dev->net->do_ioctl = ax8817x_ioctl;
+       dev->mii.phy_id = asix_get_phyid(dev);
+       dev->net->do_ioctl = asix_ioctl;
 
-       dev->net->set_multicast_list = ax8817x_set_multicast;
-       dev->net->ethtool_ops = &ax8817x_ethtool_ops;
+       dev->net->set_multicast_list = asix_set_multicast;
+       dev->net->ethtool_ops = &ax88172_ethtool_ops;
 
-       ax8817x_mdio_write_le(dev->net, dev->mii.phy_id, MII_BMCR, BMCR_RESET);
-       ax8817x_mdio_write_le(dev->net, dev->mii.phy_id, MII_ADVERTISE,
+       asix_mdio_write_le(dev->net, dev->mii.phy_id, MII_BMCR, BMCR_RESET);
+       asix_mdio_write_le(dev->net, dev->mii.phy_id, MII_ADVERTISE,
                ADVERTISE_ALL | ADVERTISE_CSMA | ADVERTISE_PAUSE_CAP);
        mii_nway_restart(&dev->mii);
 
@@ -515,16 +557,16 @@ out1:
 }
 
 static struct ethtool_ops ax88772_ethtool_ops = {
-       .get_drvinfo            = ax8817x_get_drvinfo,
+       .get_drvinfo            = asix_get_drvinfo,
        .get_link               = ethtool_op_get_link,
        .get_msglevel           = usbnet_get_msglevel,
        .set_msglevel           = usbnet_set_msglevel,
-       .get_wol                = ax8817x_get_wol,
-       .set_wol                = ax8817x_set_wol,
-       .get_eeprom_len         = ax8817x_get_eeprom_len,
-       .get_eeprom             = ax8817x_get_eeprom,
-       .get_settings           = ax8817x_get_settings,
-       .set_settings           = ax8817x_set_settings,
+       .get_wol                = asix_get_wol,
+       .set_wol                = asix_set_wol,
+       .get_eeprom_len         = asix_get_eeprom_len,
+       .get_eeprom             = asix_get_eeprom,
+       .get_settings           = asix_get_settings,
+       .set_settings           = asix_set_settings,
 };
 
 static int ax88772_bind(struct usbnet *dev, struct usb_interface *intf)
@@ -541,62 +583,45 @@ static int ax88772_bind(struct usbnet *dev, struct usb_interface *intf)
                goto out1;
        }
 
-       if ((ret = ax8817x_write_cmd(dev, AX_CMD_WRITE_GPIOS,
+       if ((ret = asix_write_cmd(dev, AX_CMD_WRITE_GPIOS,
                                     0x00B0, 0, 0, buf)) < 0)
                goto out2;
 
        msleep(5);
-       if ((ret = ax8817x_write_cmd(dev, AX_CMD_SW_PHY_SELECT,
+       if ((ret = asix_write_cmd(dev, AX_CMD_SW_PHY_SELECT,
                                0x0001, 0, 0, buf)) < 0) {
                dbg("Select PHY #1 failed: %d", ret);
                goto out2;
        }
 
-       if ((ret = ax8817x_write_cmd(dev, AX_CMD_SW_RESET, AX_SWRESET_IPPD,
-                               0, 0, buf)) < 0) {
-               dbg("Failed to power down internal PHY: %d", ret);
+       if ((ret = asix_sw_reset(dev, AX_SWRESET_IPPD)) < 0)
                goto out2;
-       }
 
        msleep(150);
-       if ((ret = ax8817x_write_cmd(dev, AX_CMD_SW_RESET, AX_SWRESET_CLEAR,
-                               0, 0, buf)) < 0) {
-               dbg("Failed to perform software reset: %d", ret);
+       if ((ret = asix_sw_reset(dev, AX_SWRESET_CLEAR)) < 0)
                goto out2;
-       }
 
        msleep(150);
-       if ((ret = ax8817x_write_cmd(dev, AX_CMD_SW_RESET,
-                               AX_SWRESET_IPRL | AX_SWRESET_PRL,
-                               0, 0, buf)) < 0) {
-               dbg("Failed to set Internal/External PHY reset control: %d",
-                                       ret);
+       if ((ret = asix_sw_reset(dev, AX_SWRESET_IPRL | AX_SWRESET_PRL)) < 0)
                goto out2;
-       }
 
        msleep(150);
-       if ((ret = ax8817x_write_cmd(dev, AX_CMD_WRITE_RX_CTL,
-                               0x0000, 0, 0, buf)) < 0) {
-               dbg("Failed to reset RX_CTL: %d", ret);
+       if ((ret = asix_write_rx_ctl(dev, 0x00)) < 0)
                goto out2;
-       }
 
        /* Get the MAC address */
        memset(buf, 0, ETH_ALEN);
-       if ((ret = ax8817x_read_cmd(dev, AX88772_CMD_READ_NODE_ID,
+       if ((ret = asix_read_cmd(dev, AX88772_CMD_READ_NODE_ID,
                                0, 0, ETH_ALEN, buf)) < 0) {
                dbg("Failed to read MAC address: %d", ret);
                goto out2;
        }
        memcpy(dev->net->dev_addr, buf, ETH_ALEN);
 
-       if ((ret = ax8817x_write_cmd(dev, AX_CMD_SET_SW_MII,
-                               0, 0, 0, buf)) < 0) {
-               dbg("Enabling software MII failed: %d", ret);
+       if ((ret = asix_set_sw_mii(dev)) < 0)
                goto out2;
-       }
 
-       if (((ret = ax8817x_read_cmd(dev, AX_CMD_READ_MII_REG,
+       if (((ret = asix_read_cmd(dev, AX_CMD_READ_MII_REG,
                                0x0010, 2, 2, buf)) < 0)
                        || (*((u16 *)buf) != 0x003b)) {
                dbg("Read PHY register 2 must be 0x3b00: %d", ret);
@@ -605,74 +630,49 @@ static int ax88772_bind(struct usbnet *dev, struct usb_interface *intf)
 
        /* Initialize MII structure */
        dev->mii.dev = dev->net;
-       dev->mii.mdio_read = ax8817x_mdio_read;
-       dev->mii.mdio_write = ax8817x_mdio_write;
+       dev->mii.mdio_read = asix_mdio_read;
+       dev->mii.mdio_write = asix_mdio_write;
        dev->mii.phy_id_mask = 0xff;
        dev->mii.reg_num_mask = 0xff;
-       dev->net->do_ioctl = ax8817x_ioctl;
+       dev->net->do_ioctl = asix_ioctl;
+       dev->mii.phy_id = asix_get_phyid(dev);
 
-       /* Get the PHY id */
-       if ((ret = ax8817x_read_cmd(dev, AX_CMD_READ_PHY_ID,
-                       0, 0, 2, buf)) < 0) {
-               dbg("Error reading PHY ID: %02x", ret);
+       if ((ret = asix_sw_reset(dev, AX_SWRESET_PRL)) < 0)
                goto out2;
-       } else if (ret < 2) {
-               /* this should always return 2 bytes */
-               dbg("AX_CMD_READ_PHY_ID returned less than 2 bytes: ret=%02x",
-                   ret);
-               ret = -EIO;
-               goto out2;
-       }
-       dev->mii.phy_id = *((u8 *)buf + 1);
 
-       if ((ret = ax8817x_write_cmd(dev, AX_CMD_SW_RESET, AX_SWRESET_PRL,
-                               0, 0, buf)) < 0) {
-               dbg("Set external PHY reset pin level: %d", ret);
-               goto out2;
-       }
        msleep(150);
-       if ((ret = ax8817x_write_cmd(dev, AX_CMD_SW_RESET,
-                               AX_SWRESET_IPRL | AX_SWRESET_PRL,
-                               0, 0, buf)) < 0) {
-               dbg("Set Internal/External PHY reset control: %d", ret);
+
+       if ((ret = asix_sw_reset(dev, AX_SWRESET_IPRL | AX_SWRESET_PRL)) < 0)
                goto out2;
-       }
-       msleep(150);
 
+       msleep(150);
 
-       dev->net->set_multicast_list = ax8817x_set_multicast;
+       dev->net->set_multicast_list = asix_set_multicast;
        dev->net->ethtool_ops = &ax88772_ethtool_ops;
 
-       ax8817x_mdio_write_le(dev->net, dev->mii.phy_id, MII_BMCR, BMCR_RESET);
-       ax8817x_mdio_write_le(dev->net, dev->mii.phy_id, MII_ADVERTISE,
+       asix_mdio_write_le(dev->net, dev->mii.phy_id, MII_BMCR, BMCR_RESET);
+       asix_mdio_write_le(dev->net, dev->mii.phy_id, MII_ADVERTISE,
                        ADVERTISE_ALL | ADVERTISE_CSMA);
        mii_nway_restart(&dev->mii);
 
-       if ((ret = ax8817x_write_cmd(dev, AX_CMD_WRITE_MEDIUM_MODE,
+       if ((ret = asix_write_cmd(dev, AX_CMD_WRITE_MEDIUM_MODE,
                                AX88772_MEDIUM_DEFAULT, 0, 0, buf)) < 0) {
                dbg("Write medium mode register: %d", ret);
                goto out2;
        }
 
-       if ((ret = ax8817x_write_cmd(dev, AX_CMD_WRITE_IPG0,
+       if ((ret = asix_write_cmd(dev, AX_CMD_WRITE_IPG0,
                                AX88772_IPG0_DEFAULT | AX88772_IPG1_DEFAULT,
                                AX88772_IPG2_DEFAULT, 0, buf)) < 0) {
                dbg("Write IPG,IPG1,IPG2 failed: %d", ret);
                goto out2;
        }
-       if ((ret =
-            ax8817x_write_cmd(dev, AX_CMD_SET_HW_MII, 0, 0, 0, &buf)) < 0) {
-               dbg("Failed to set hardware MII: %02x", ret);
+       if ((ret = asix_set_hw_mii(dev)) < 0)
                goto out2;
-       }
 
        /* Set RX_CTL to default values with 2k buffer, and enable cactus */
-       if ((ret =
-            ax8817x_write_cmd(dev, AX_CMD_WRITE_RX_CTL, 0x0088, 0, 0,
-                              buf)) < 0) {
-               dbg("Reset RX_CTL failed: %d", ret);
+       if ((ret = asix_write_rx_ctl(dev, 0x0088)) < 0)
                goto out2;
-       }
 
        kfree(buf);
 
@@ -794,23 +794,23 @@ static int ax88772_link_reset(struct usbnet *dev)
        u16 mode;
 
        mode = AX88772_MEDIUM_DEFAULT;
-       lpa = ax8817x_mdio_read_le(dev->net, dev->mii.phy_id, MII_LPA);
-       adv = ax8817x_mdio_read_le(dev->net, dev->mii.phy_id, MII_ADVERTISE);
+       lpa = asix_mdio_read_le(dev->net, dev->mii.phy_id, MII_LPA);
+       adv = asix_mdio_read_le(dev->net, dev->mii.phy_id, MII_ADVERTISE);
        res = mii_nway_result(lpa|adv);
 
        if ((res & LPA_DUPLEX) == 0)
                mode &= ~AX88772_MEDIUM_FULL_DUPLEX;
        if ((res & LPA_100) == 0)
                mode &= ~AX88772_MEDIUM_100MB;
-       ax8817x_write_cmd(dev, AX_CMD_WRITE_MEDIUM_MODE, mode, 0, 0, NULL);
+       asix_write_cmd(dev, AX_CMD_WRITE_MEDIUM_MODE, mode, 0, 0, NULL);
 
        return 0;
 }
 
 static const struct driver_info ax8817x_info = {
        .description = "ASIX AX8817x USB 2.0 Ethernet",
-       .bind = ax8817x_bind,
-       .status = ax8817x_status,
+       .bind = ax88172_bind,
+       .status = asix_status,
        .link_reset = ax88172_link_reset,
        .reset = ax88172_link_reset,
        .flags =  FLAG_ETHER,
@@ -819,8 +819,8 @@ static const struct driver_info ax8817x_info = {
 
 static const struct driver_info dlink_dub_e100_info = {
        .description = "DLink DUB-E100 USB Ethernet",
-       .bind = ax8817x_bind,
-       .status = ax8817x_status,
+       .bind = ax88172_bind,
+       .status = asix_status,
        .link_reset = ax88172_link_reset,
        .reset = ax88172_link_reset,
        .flags =  FLAG_ETHER,
@@ -829,8 +829,8 @@ static const struct driver_info dlink_dub_e100_info = {
 
 static const struct driver_info netgear_fa120_info = {
        .description = "Netgear FA-120 USB Ethernet",
-       .bind = ax8817x_bind,
-       .status = ax8817x_status,
+       .bind = ax88172_bind,
+       .status = asix_status,
        .link_reset = ax88172_link_reset,
        .reset = ax88172_link_reset,
        .flags =  FLAG_ETHER,
@@ -839,8 +839,8 @@ static const struct driver_info netgear_fa120_info = {
 
 static const struct driver_info hawking_uf200_info = {
        .description = "Hawking UF200 USB Ethernet",
-       .bind = ax8817x_bind,
-       .status = ax8817x_status,
+       .bind = ax88172_bind,
+       .status = asix_status,
        .link_reset = ax88172_link_reset,
        .reset = ax88172_link_reset,
        .flags =  FLAG_ETHER,
@@ -850,13 +850,12 @@ static const struct driver_info hawking_uf200_info = {
 static const struct driver_info ax88772_info = {
        .description = "ASIX AX88772 USB 2.0 Ethernet",
        .bind = ax88772_bind,
-       .status = ax8817x_status,
+       .status = asix_status,
        .link_reset = ax88772_link_reset,
        .reset = ax88772_link_reset,
        .flags = FLAG_ETHER | FLAG_FRAMING_AX,
        .rx_fixup = ax88772_rx_fixup,
        .tx_fixup = ax88772_tx_fixup,
-       .data = 0x00130103,
 };
 
 static const struct usb_device_id      products [] = {
index 5b6675684567f883a8f462edd67f0f5efd5598ce..2deb4c01539e8466ef97766e408ff0b6689e71b5 100644 (file)
@@ -262,7 +262,7 @@ static int set_register(pegasus_t * pegasus, __u16 indx, __u8 data)
        usb_fill_control_urb(pegasus->ctrl_urb, pegasus->usb,
                             usb_sndctrlpipe(pegasus->usb, 0),
                             (char *) &pegasus->dr,
-                            &tmp, 1, ctrl_callback, pegasus);
+                            tmp, 1, ctrl_callback, pegasus);
 
        add_wait_queue(&pegasus->ctrl_wait, &wait);
        set_current_state(TASK_UNINTERRUPTIBLE);
index 49991ac1bf3b843420543013c14df70dea443526..94ddfe16fdda9237454525b745ba3f0b3e8c76ba 100644 (file)
  * RNDIS is NDIS remoted over USB.  It's a MSFT variant of CDC ACM ... of
  * course ACM was intended for modems, not Ethernet links!  USB's standard
  * for Ethernet links is "CDC Ethernet", which is significantly simpler.
+ *
+ * NOTE that Microsoft's "RNDIS 1.0" specification is incomplete.  Issues
+ * include:
+ *    - Power management in particular relies on information that's scattered
+ *     through other documentation, and which is incomplete or incorrect even
+ *     there.
+ *    - There are various undocumented protocol requirements, such as the
+ *     need to send unused garbage in control-OUT messages.
+ *    - In some cases, MS-Windows will emit undocumented requests; this
+ *     matters more to peripheral implementations than host ones.
+ *
+ * For these reasons and others, ** USE OF RNDIS IS STRONGLY DISCOURAGED ** in
+ * favor of such non-proprietary alternatives as CDC Ethernet or the newer (and
+ * currently rare) "Ethernet Emulation Model" (EEM).
  */
 
 /*
@@ -72,17 +86,17 @@ struct rndis_msg_hdr {
  */
 #define RNDIS_MSG_PACKET       ccpu2(0x00000001)       /* 1-N packets */
 #define RNDIS_MSG_INIT         ccpu2(0x00000002)
-#define RNDIS_MSG_INIT_C       (RNDIS_MSG_INIT|RNDIS_MSG_COMPLETION)
+#define RNDIS_MSG_INIT_C       (RNDIS_MSG_INIT|RNDIS_MSG_COMPLETION)
 #define RNDIS_MSG_HALT         ccpu2(0x00000003)
 #define RNDIS_MSG_QUERY                ccpu2(0x00000004)
-#define RNDIS_MSG_QUERY_C      (RNDIS_MSG_QUERY|RNDIS_MSG_COMPLETION)
+#define RNDIS_MSG_QUERY_C      (RNDIS_MSG_QUERY|RNDIS_MSG_COMPLETION)
 #define RNDIS_MSG_SET          ccpu2(0x00000005)
-#define RNDIS_MSG_SET_C        (RNDIS_MSG_SET|RNDIS_MSG_COMPLETION)
+#define RNDIS_MSG_SET_C                (RNDIS_MSG_SET|RNDIS_MSG_COMPLETION)
 #define RNDIS_MSG_RESET                ccpu2(0x00000006)
-#define RNDIS_MSG_RESET_C      (RNDIS_MSG_RESET|RNDIS_MSG_COMPLETION)
+#define RNDIS_MSG_RESET_C      (RNDIS_MSG_RESET|RNDIS_MSG_COMPLETION)
 #define RNDIS_MSG_INDICATE     ccpu2(0x00000007)
 #define RNDIS_MSG_KEEPALIVE    ccpu2(0x00000008)
-#define RNDIS_MSG_KEEPALIVE_C  (RNDIS_MSG_KEEPALIVE|RNDIS_MSG_COMPLETION)
+#define RNDIS_MSG_KEEPALIVE_C  (RNDIS_MSG_KEEPALIVE|RNDIS_MSG_COMPLETION)
 
 /* codes for "status" field of completion messages */
 #define        RNDIS_STATUS_SUCCESS            ccpu2(0x00000000)
@@ -596,13 +610,13 @@ static struct usb_driver rndis_driver = {
 
 static int __init rndis_init(void)
 {
-       return usb_register(&rndis_driver);
+       return usb_register(&rndis_driver);
 }
 module_init(rndis_init);
 
 static void __exit rndis_exit(void)
 {
-       usb_deregister(&rndis_driver);
+       usb_deregister(&rndis_driver);
 }
 module_exit(rndis_exit);
 
index 5a8a2c91c2b22347632b572f10f9980cae8266ce..f96b73f54bf1cdb7d4840d7b3c1c0600c8e4d6a0 100644 (file)
@@ -158,6 +158,15 @@ config USB_SERIAL_FTDI_SIO
          To compile this driver as a module, choose M here: the
          module will be called ftdi_sio.
 
+config USB_SERIAL_FUNSOFT
+       tristate "USB Fundamental Software Dongle Driver"
+       depends on USB_SERIAL
+       ---help---
+         Say Y here if you want to use the Fundamental Software dongle.
+
+         To compile this driver as a module, choose M here: the
+         module will be called funsoft.
+
 config USB_SERIAL_VISOR
        tristate "USB Handspring Visor / Palm m50x / Sony Clie Driver"
        depends on USB_SERIAL
index f7fe4172efedce723789253defddba0264286e27..93c21245b1af713d52974d7eec80097073f52ee1 100644 (file)
@@ -22,6 +22,7 @@ obj-$(CONFIG_USB_SERIAL_EDGEPORT)             += io_edgeport.o
 obj-$(CONFIG_USB_SERIAL_EDGEPORT_TI)           += io_ti.o
 obj-$(CONFIG_USB_SERIAL_EMPEG)                 += empeg.o
 obj-$(CONFIG_USB_SERIAL_FTDI_SIO)              += ftdi_sio.o
+obj-$(CONFIG_USB_SERIAL_FUNSOFT)               += funsoft.o
 obj-$(CONFIG_USB_SERIAL_GARMIN)                        += garmin_gps.o
 obj-$(CONFIG_USB_SERIAL_HP4X)                  += hp4x.o
 obj-$(CONFIG_USB_SERIAL_IPAQ)                  += ipaq.o
index 167f8ec561319cc11f03133a74beacf5775efae5..8023bb7279b123f52fbe400032a30d611dfe588e 100644 (file)
@@ -54,7 +54,7 @@ static struct console usbcons;
  * serial.c code, except that the specifier is "ttyUSB" instead
  * of "ttyS".
  */
-static int __init usb_console_setup(struct console *co, char *options)
+static int usb_console_setup(struct console *co, char *options)
 {
        struct usbcons_info *info = &usbcons_info;
        int baud = 9600;
index f3af81b4dd2966d39083baf2e009bfbc98aac5ba..f5851db67f5be87b2f37a69afd3feeb54fc93fbf 100644 (file)
@@ -489,10 +489,12 @@ static struct usb_device_id id_table_combined [] = {
        { USB_DEVICE(KOBIL_VID, KOBIL_CONV_KAAN_PID) },
        { USB_DEVICE(POSIFLEX_VID, POSIFLEX_PP7000_PID) },
        { USB_DEVICE(FTDI_VID, FTDI_TTUSB_PID) },
+       { USB_DEVICE(FTDI_VID, FTDI_ECLO_COM_1WIRE_PID) },
        { USB_DEVICE(FTDI_VID, FTDI_WESTREX_MODEL_777_PID) },
        { USB_DEVICE(FTDI_VID, FTDI_WESTREX_MODEL_8900F_PID) },
        { USB_DEVICE(FTDI_VID, FTDI_PCDJ_DAC2_PID) },
        { USB_DEVICE(ICOM_ID1_VID, ICOM_ID1_PID) },
+       { USB_DEVICE(PAPOUCH_VID, PAPOUCH_TMU_PID) },
        { },                                    /* Optional parameter entry */
        { }                                     /* Terminating entry */
 };
index 8da773c2744d01ddffe5bf11d33080992b747a7f..2155f0e4a378b29bd7dfab86e7044f4ef3d440e0 100644 (file)
 #define FTDI_WESTREX_MODEL_777_PID     0xDC00  /* Model 777 */
 #define FTDI_WESTREX_MODEL_8900F_PID   0xDC01  /* Model 8900F */
 
+/*
+ * Eclo (http://www.eclo.pt/) product IDs.
+ * PID 0xEA90 submitted by Martin Grill.
+ */
+#define FTDI_ECLO_COM_1WIRE_PID        0xEA90  /* COM to 1-Wire USB adaptor */
+
+/*
+ * Papouch products (http://www.papouch.com/)
+ * Submitted by Folkert van Heusden
+ */
+
+#define PAPOUCH_VID                    0x5050  /* Vendor ID */
+#define PAPOUCH_TMU_PID                        0x0400  /* TMU USB Thermometer */
+
+
 /* Commands */
 #define FTDI_SIO_RESET                 0 /* Reset the port */
 #define FTDI_SIO_MODEM_CTRL    1 /* Set the modem control register */
diff --git a/drivers/usb/serial/funsoft.c b/drivers/usb/serial/funsoft.c
new file mode 100644 (file)
index 0000000..803721b
--- /dev/null
@@ -0,0 +1,65 @@
+/*
+ * Funsoft Serial USB driver
+ *
+ * Copyright (C) 2006 Greg Kroah-Hartman <gregkh@suse.de>
+ *
+ *     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 <linux/kernel.h>
+#include <linux/init.h>
+#include <linux/tty.h>
+#include <linux/module.h>
+#include <linux/usb.h>
+#include "usb-serial.h"
+
+static struct usb_device_id id_table [] = {
+       { USB_DEVICE(0x1404, 0xcddc) },
+       { },
+};
+MODULE_DEVICE_TABLE(usb, id_table);
+
+static struct usb_driver funsoft_driver = {
+       .name =         "funsoft",
+       .probe =        usb_serial_probe,
+       .disconnect =   usb_serial_disconnect,
+       .id_table =     id_table,
+       .no_dynamic_id =        1,
+};
+
+static struct usb_serial_driver funsoft_device = {
+       .driver = {
+               .owner =        THIS_MODULE,
+               .name =         "funsoft",
+       },
+       .id_table =             id_table,
+       .num_interrupt_in =     NUM_DONT_CARE,
+       .num_bulk_in =          NUM_DONT_CARE,
+       .num_bulk_out =         NUM_DONT_CARE,
+       .num_ports =            1,
+};
+
+static int __init funsoft_init(void)
+{
+       int retval;
+
+       retval = usb_serial_register(&funsoft_device);
+       if (retval)
+               return retval;
+       retval = usb_register(&funsoft_driver);
+       if (retval)
+               usb_serial_deregister(&funsoft_device);
+       return retval;
+}
+
+static void __exit funsoft_exit(void)
+{
+       usb_deregister(&funsoft_driver);
+       usb_serial_deregister(&funsoft_device);
+}
+
+module_init(funsoft_init);
+module_exit(funsoft_exit);
+MODULE_LICENSE("GPL");
index 495db5755df9e3a1ea1ff7aae075d8853c8b1485..5cf2b80add7aa01ede3b1a588dc5c002d6dbccb8 100644 (file)
@@ -28,6 +28,7 @@
   2005-09-10  v0.4.3 added HUAWEI E600 card and Audiovox AirCard
   2005-09-20  v0.4.4 increased recv buffer size: the card sometimes
                      wants to send >2000 bytes.
+  2006-04-10  v0.4.2 fixed two array overrun errors :-/
 
   Work sponsored by: Sigos GmbH, Germany <info@sigos.de>
 
@@ -582,14 +583,14 @@ static void option_setup_urbs(struct usb_serial *serial)
        portdata = usb_get_serial_port_data(port);
 
        /* Do indat endpoints first */
-       for (j = 0; j <= N_IN_URB; ++j) {
+       for (j = 0; j < N_IN_URB; ++j) {
                portdata->in_urbs[j] = option_setup_urb (serial,
                   port->bulk_in_endpointAddress, USB_DIR_IN, port,
                   portdata->in_buffer[j], IN_BUFLEN, option_indat_callback);
        }
 
        /* outdat endpoints */
-       for (j = 0; j <= N_OUT_URB; ++j) {
+       for (j = 0; j < N_OUT_URB; ++j) {
                portdata->out_urbs[j] = option_setup_urb (serial,
                   port->bulk_out_endpointAddress, USB_DIR_OUT, port,
                   portdata->out_buffer[j], OUT_BUFLEN, option_outdat_callback);
index b3014fda645c2d1e5aae824e2a61c6a3b1511e7a..ccf746b27d4ea370758ad50fb2c3cbdf07eaaf92 100644 (file)
@@ -78,6 +78,7 @@ static struct usb_device_id id_table [] = {
        { USB_DEVICE(SAGEM_VENDOR_ID, SAGEM_PRODUCT_ID) },
        { USB_DEVICE(LEADTEK_VENDOR_ID, LEADTEK_9531_PRODUCT_ID) },
        { USB_DEVICE(SPEEDDRAGON_VENDOR_ID, SPEEDDRAGON_PRODUCT_ID) },
+       { USB_DEVICE(OTI_VENDOR_ID, OTI_PRODUCT_ID) },
        { }                                     /* Terminating entry */
 };
 
index 77901d14397940382d6ec98d6b1796a7242b6cc7..09f379b19e98517633e86ab4d85710a066f56b4d 100644 (file)
@@ -79,3 +79,7 @@
 /* USB GSM cable from Speed Dragon Multimedia, Ltd */
 #define SPEEDDRAGON_VENDOR_ID  0x0e55
 #define SPEEDDRAGON_PRODUCT_ID 0x110b
+
+/* Ours Technology Inc DKU-5 clone, chipset: Prolific Technology Inc */
+#define OTI_VENDOR_ID  0x0ea0
+#define OTI_PRODUCT_ID 0x6858
index 097f4e8488feb2788b42699e48a4010fc5ab8a3f..071f86a59c086222ecf89c8705080b064b4d8fdc 100644 (file)
 #include <linux/module.h>
 #include <linux/moduleparam.h>
 #include <linux/spinlock.h>
+#include <linux/mutex.h>
 #include <linux/list.h>
 #include <linux/smp_lock.h>
 #include <asm/uaccess.h>
-#include <asm/semaphore.h>
 #include <linux/usb.h>
 #include "usb-serial.h"
 #include "pl2303.h"
@@ -192,7 +192,7 @@ static int serial_open (struct tty_struct *tty, struct file * filp)
        if (!port)
                return -ENODEV;
 
-       if (down_interruptible(&port->sem))
+       if (mutex_lock_interruptible(&port->mutex))
                return -ERESTARTSYS;
         
        ++port->open_count;
@@ -219,7 +219,7 @@ static int serial_open (struct tty_struct *tty, struct file * filp)
                        goto bailout_module_put;
        }
 
-       up(&port->sem);
+       mutex_unlock(&port->mutex);
        return 0;
 
 bailout_module_put:
@@ -227,7 +227,7 @@ bailout_module_put:
 bailout_kref_put:
        kref_put(&serial->kref, destroy_serial);
        port->open_count = 0;
-       up(&port->sem);
+       mutex_unlock(&port->mutex);
        return retval;
 }
 
@@ -240,10 +240,10 @@ static void serial_close(struct tty_struct *tty, struct file * filp)
 
        dbg("%s - port %d", __FUNCTION__, port->number);
 
-       down(&port->sem);
+       mutex_lock(&port->mutex);
 
        if (port->open_count == 0) {
-               up(&port->sem);
+               mutex_unlock(&port->mutex);
                return;
        }
 
@@ -262,7 +262,7 @@ static void serial_close(struct tty_struct *tty, struct file * filp)
                module_put(port->serial->type->driver.owner);
        }
 
-       up(&port->sem);
+       mutex_unlock(&port->mutex);
        kref_put(&port->serial->kref, destroy_serial);
 }
 
@@ -783,7 +783,7 @@ int usb_serial_probe(struct usb_interface *interface,
                port->number = i + serial->minor;
                port->serial = serial;
                spin_lock_init(&port->lock);
-               sema_init(&port->sem, 1);
+               mutex_init(&port->mutex);
                INIT_WORK(&port->work, usb_serial_port_softint, port);
                serial->port[i] = port;
        }
index d7d27c3385b384ea090a033ebd6da14dc0512038..dc89d87104609524d6b3e07272153a6807459798 100644 (file)
@@ -16,7 +16,7 @@
 
 #include <linux/config.h>
 #include <linux/kref.h>
-#include <asm/semaphore.h>
+#include <linux/mutex.h>
 
 #define SERIAL_TTY_MAJOR       188     /* Nice legal number now */
 #define SERIAL_TTY_MINORS      255     /* loads of devices :) */
@@ -31,7 +31,7 @@
  * @serial: pointer back to the struct usb_serial owner of this port.
  * @tty: pointer to the corresponding tty for this port.
  * @lock: spinlock to grab when updating portions of this structure.
- * @sem: semaphore used to synchronize serial_open() and serial_close()
+ * @mutex: mutex used to synchronize serial_open() and serial_close()
  *     access for this port.
  * @number: the number of the port (the minor number).
  * @interrupt_in_buffer: pointer to the interrupt in buffer for this port.
@@ -63,7 +63,7 @@ struct usb_serial_port {
        struct usb_serial *     serial;
        struct tty_struct *     tty;
        spinlock_t              lock;
-       struct semaphore        sem;
+       struct mutex            mutex;
        unsigned char           number;
 
        unsigned char *         interrupt_in_buffer;
index 92be101feba70882baea621b27adde4df0f153b5..be9eec2257436c2152aecd9e0d20462f69902b2e 100644 (file)
@@ -48,7 +48,8 @@ config USB_STORAGE_FREECOM
 
 config USB_STORAGE_ISD200
        bool "ISD-200 USB/ATA Bridge support"
-       depends on USB_STORAGE && BLK_DEV_IDE
+       depends on USB_STORAGE
+       depends on BLK_DEV_IDE=y || BLK_DEV_IDE=USB_STORAGE
        ---help---
          Say Y here if you want to use USB Mass Store devices based
          on the In-Systems Design ISD-200 USB/ATA bridge.
index f87c0171f4eca2068c5fab79c11bbb11889452a7..9060e713744112e13a72e829e479f3fd51f770a3 100644 (file)
@@ -961,7 +961,7 @@ config FB_ATY128
 
 config FB_ATY
        tristate "ATI Mach64 display support" if PCI || ATARI
-       depends on FB
+       depends on FB && !SPARC32
        select FB_CFB_FILLRECT
        select FB_CFB_COPYAREA
        select FB_CFB_IMAGEBLIT
index b39e72d5413b60fb4845b7cf02991c557bcc49bf..d9d7d3c4cae2ed83b81b4b8db846d7fa8d826ed6 100644 (file)
@@ -3400,7 +3400,7 @@ static int __devinit atyfb_pci_probe(struct pci_dev *pdev, const struct pci_devi
        struct atyfb_par *par;
        int i, rc = -ENOMEM;
 
-       for (i = ARRAY_SIZE(aty_chips); i >= 0; i--)
+       for (i = ARRAY_SIZE(aty_chips) - 1; i >= 0; i--)
                if (pdev->device == aty_chips[i].pci_id)
                        break;
 
index 9a6b5b39b88ebed5807771037e7aeba34228258f..387a18a47ac24b533037368e0928f874500658af 100644 (file)
@@ -2265,7 +2265,7 @@ static struct bin_attribute edid2_attr = {
 };
 
 
-static int radeonfb_pci_register (struct pci_dev *pdev,
+static int __devinit radeonfb_pci_register (struct pci_dev *pdev,
                                  const struct pci_device_id *ent)
 {
        struct fb_info *info;
index 944855b3e4afe304aab2f25c43d24c6b5dbe82bf..372aa177682798bc2544ad3f04032ad6a36dc7c9 100644 (file)
@@ -435,6 +435,11 @@ int fb_prepare_logo(struct fb_info *info, int rotate)
                        depth = info->var.green.length;
        }
 
+       if (info->fix.visual == FB_VISUAL_STATIC_PSEUDOCOLOR) {
+               /* assume console colormap */
+               depth = 4;
+       }
+
        if (depth >= 8) {
                switch (info->fix.visual) {
                case FB_VISUAL_TRUECOLOR:
@@ -669,13 +674,19 @@ fb_write(struct file *file, const char __user *buf, size_t count, loff_t *ppos)
                total_size = info->fix.smem_len;
 
        if (p > total_size)
-               return 0;
+               return -EFBIG;
 
-       if (count >= total_size)
+       if (count > total_size) {
+               err = -EFBIG;
                count = total_size;
+       }
+
+       if (count + p > total_size) {
+               if (!err)
+                       err = -ENOSPC;
 
-       if (count + p > total_size)
                count = total_size - p;
+       }
 
        buffer = kmalloc((count > PAGE_SIZE) ? PAGE_SIZE : count,
                         GFP_KERNEL);
@@ -717,7 +728,7 @@ fb_write(struct file *file, const char __user *buf, size_t count, loff_t *ppos)
 
        kfree(buffer);
 
-       return (err) ? err : cnt;
+       return (cnt) ? cnt : err;
 }
 
 #ifdef CONFIG_KMOD
index 5fe197943deb4a1c1deea3fa3b71e716a93265b0..4e963930b50ae40ee358e19e999e12dc5b3db368 100644 (file)
@@ -73,8 +73,8 @@ static char *mode __devinitdata = NULL;
  * these flags allow the user to specify that requests for +ve sync
  * should be silently turned in -ve sync.
  */
-static int lowhsync __devinitdata = 0;
-static int lowvsync __devinitdata = 0;
+static int lowhsync;
+static int lowvsync;
 
 /*
  * The hardware state of the graphics card that isn't part of the
index 10e6b3aab9eaf18f7bd11824cfa63c12b88ba86e..0da624e6524f5e3be9c7c1406f5c9248613f7eaa 100644 (file)
@@ -73,7 +73,7 @@
 /* --------------------------------------------------------------------- */
 
 
-static char *mode_option __initdata = NULL;
+static char *mode_option __devinitdata = NULL;
 
 #ifdef MODULE
 
@@ -1545,7 +1545,7 @@ static int __devinit savage_map_mmio (struct fb_info *info)
        return 0;
 }
 
-static void __devinit savage_unmap_mmio (struct fb_info *info)
+static void savage_unmap_mmio (struct fb_info *info)
 {
        struct savagefb_par *par = info->par;
        DBG ("savage_unmap_mmio");
@@ -1597,7 +1597,7 @@ static int __devinit savage_map_video (struct fb_info *info,
        return 0;
 }
 
-static void __devinit savage_unmap_video (struct fb_info *info)
+static void savage_unmap_video (struct fb_info *info)
 {
        struct savagefb_par *par = info->par;
 
@@ -1614,7 +1614,7 @@ static void __devinit savage_unmap_video (struct fb_info *info)
        }
 }
 
-static int __devinit savage_init_hw (struct savagefb_par *par)
+static int savage_init_hw (struct savagefb_par *par)
 {
        unsigned char config1, m, n, n1, n2, sr8, cr3f, cr66 = 0, tmp;
 
index 8982e540214c56b2de7d0299ce8c15258d76fc83..b0b9acfdd430ec3a3d64eb0e4c082130d0ff55f7 100644 (file)
@@ -57,7 +57,7 @@ static unsigned short  *pmi_base  = NULL;
 static void            (*pmi_start)(void);
 static void            (*pmi_pal)(void);
 static int             depth;
-
+static int             vga_compat;
 /* --------------------------------------------------------------------- */
 
 static int vesafb_pan_display(struct fb_var_screeninfo *var,
@@ -83,9 +83,10 @@ static int vesafb_pan_display(struct fb_var_screeninfo *var,
 static void vesa_setpalette(int regno, unsigned red, unsigned green,
                            unsigned blue)
 {
+       int shift = 16 - depth;
+
 #ifdef __i386__
        struct { u_char blue, green, red, pad; } entry;
-       int shift = 16 - depth;
 
        if (pmi_setpal) {
                entry.red   = red   >> shift;
@@ -101,14 +102,20 @@ static void vesa_setpalette(int regno, unsigned red, unsigned green,
                   "d" (regno),          /* EDX */
                   "D" (&entry),         /* EDI */
                   "S" (&pmi_pal));      /* ESI */
-       } else {
-               /* without protected mode interface, try VGA registers... */
+               return;
+       }
+#endif
+
+/*
+ * without protected mode interface and if VGA compatible,
+ * try VGA registers...
+ */
+       if (vga_compat) {
                outb_p(regno,       dac_reg);
                outb_p(red   >> shift, dac_val);
                outb_p(green >> shift, dac_val);
                outb_p(blue  >> shift, dac_val);
        }
-#endif
 }
 
 static int vesafb_setcolreg(unsigned regno, unsigned red, unsigned green,
@@ -214,6 +221,7 @@ static int __init vesafb_probe(struct platform_device *dev)
        if (screen_info.orig_video_isVGA != VIDEO_TYPE_VLFB)
                return -ENODEV;
 
+       vga_compat = (screen_info.capabilities & 2) ? 0 : 1;
        vesafb_fix.smem_start = screen_info.lfb_base;
        vesafb_defined.bits_per_pixel = screen_info.lfb_depth;
        if (15 == vesafb_defined.bits_per_pixel)
@@ -318,6 +326,12 @@ static int __init vesafb_probe(struct platform_device *dev)
                }
        }
 
+       if (vesafb_defined.bits_per_pixel == 8 && !pmi_setpal && !vga_compat) {
+               printk(KERN_WARNING "vesafb: hardware palette is unchangeable,\n"
+                                   "        colors may be incorrect\n");
+               vesafb_fix.visual = FB_VISUAL_STATIC_PSEUDOCOLOR;
+       }
+
        vesafb_defined.xres_virtual = vesafb_defined.xres;
        vesafb_defined.yres_virtual = vesafb_fix.smem_len / vesafb_fix.line_length;
        if (ypan && vesafb_defined.yres_virtual > vesafb_defined.yres) {
@@ -354,7 +368,8 @@ static int __init vesafb_probe(struct platform_device *dev)
        printk(KERN_INFO "vesafb: %s: "
               "size=%d:%d:%d:%d, shift=%d:%d:%d:%d\n",
               (vesafb_defined.bits_per_pixel > 8) ?
-              "Truecolor" : "Pseudocolor",
+              "Truecolor" : (vga_compat || pmi_setpal) ?
+              "Pseudocolor" : "Static Pseudocolor",
               screen_info.rsvd_size,
               screen_info.red_size,
               screen_info.green_size,
index b0a0ae509c00524d27dd306541b0935321766514..61c599b4a1e32de2f7053408e64657067450d58e 100644 (file)
@@ -127,12 +127,13 @@ static struct super_block *v9fs_get_sb(struct file_system_type
 
        if ((newfid = v9fs_session_init(v9ses, dev_name, data)) < 0) {
                dprintk(DEBUG_ERROR, "problem initiating session\n");
-               kfree(v9ses);
-               return ERR_PTR(newfid);
+               sb = ERR_PTR(newfid);
+               goto out_free_session;
        }
 
        sb = sget(fs_type, NULL, v9fs_set_super, v9ses);
-
+       if (IS_ERR(sb))
+               goto out_close_session;
        v9fs_fill_super(sb, v9ses, flags);
 
        inode = v9fs_get_inode(sb, S_IFDIR | mode);
@@ -185,6 +186,12 @@ static struct super_block *v9fs_get_sb(struct file_system_type
 
        return sb;
 
+out_close_session:
+       v9fs_session_close(v9ses);
+out_free_session:
+       kfree(v9ses);
+       return sb;
+
 put_back_sb:
        /* deactivate_super calls v9fs_kill_super which will frees the rest */
        up_write(&sb->s_umount);
index 62ee097776f0cede02b98c3ff935b95109a66ae1..563a59e5e694db6b3fb2f217ba4dfe27df563cd1 100644 (file)
@@ -800,6 +800,7 @@ config PROC_KCORE
 config PROC_VMCORE
         bool "/proc/vmcore support (EXPERIMENTAL)"
         depends on PROC_FS && EXPERIMENTAL && CRASH_DUMP
+       default y
         help
         Exports the dump image of crashed kernel in ELF format.
 
@@ -842,6 +843,12 @@ config TMPFS
 config HUGETLBFS
        bool "HugeTLB file system support"
        depends X86 || IA64 || PPC64 || SPARC64 || SUPERH || BROKEN
+       help
+         hugetlbfs is a filesystem backing for HugeTLB pages, based on
+         ramfs. For architectures that support it, say Y here and read
+         <file:Documentation/vm/hugetlbpage.txt> for details.
+
+         If unsure, say N.
 
 config HUGETLB_PAGE
        def_bool HUGETLBFS
@@ -862,7 +869,7 @@ config RAMFS
 
 config CONFIGFS_FS
        tristate "Userspace-driven configuration filesystem (EXPERIMENTAL)"
-       depends on EXPERIMENTAL
+       depends on SYSFS && EXPERIMENTAL
        help
          configfs is a ram-based filesystem that provides the converse
          of sysfs's functionality. Where sysfs is a filesystem-based
index 8ed9b06a982834d91b70c9919d16f58f9149d1af..5638c8f9362f9222419e1cff3f80e50dca646abc 100644 (file)
@@ -504,7 +504,7 @@ static int populate_groups(struct config_group *group)
        int ret = 0;
        int i;
 
-       if (group && group->default_groups) {
+       if (group->default_groups) {
                /* FYI, we're faking mkdir here
                 * I'm not sure we need this semaphore, as we're called
                 * from our parent's mkdir.  That holds our parent's
index 242fe1a66ce5731690fc9e7dfe340307bc685448..1b4491cdd11581235564f6aaaf3a545f71df1f93 100644 (file)
@@ -599,7 +599,7 @@ sys_epoll_ctl(int epfd, int op, int fd, struct epoll_event __user *event)
        switch (op) {
        case EPOLL_CTL_ADD:
                if (!epi) {
-                       epds.events |= POLLERR | POLLHUP | POLLRDHUP;
+                       epds.events |= POLLERR | POLLHUP;
 
                        error = ep_insert(ep, &epds, tfile, fd);
                } else
@@ -613,7 +613,7 @@ sys_epoll_ctl(int epfd, int op, int fd, struct epoll_event __user *event)
                break;
        case EPOLL_CTL_MOD:
                if (epi) {
-                       epds.events |= POLLERR | POLLHUP | POLLRDHUP;
+                       epds.events |= POLLERR | POLLHUP;
                        error = ep_modify(ep, epi, &epds);
                } else
                        error = -ENOENT;
index 0291a68a36261ada2dca60e411af634b1373bc1c..3a79d97ac234422c353ad6c37ab973d3363471bd 100644 (file)
--- a/fs/exec.c
+++ b/fs/exec.c
@@ -665,9 +665,7 @@ static int de_thread(struct task_struct *tsk)
         * and to assume its PID:
         */
        if (!thread_group_leader(current)) {
-               struct task_struct *parent;
                struct dentry *proc_dentry1, *proc_dentry2;
-               unsigned long ptrace;
 
                /*
                 * Wait for the thread group leader to be a zombie.
@@ -678,6 +676,18 @@ static int de_thread(struct task_struct *tsk)
                while (leader->exit_state != EXIT_ZOMBIE)
                        yield();
 
+               /*
+                * The only record we have of the real-time age of a
+                * process, regardless of execs it's done, is start_time.
+                * All the past CPU time is accumulated in signal_struct
+                * from sister threads now dead.  But in this non-leader
+                * exec, nothing survives from the original leader thread,
+                * whose birth marks the true age of this process now.
+                * When we take on its identity by switching to its PID, we
+                * also take its birthdate (always earlier than our own).
+                */
+               current->start_time = leader->start_time;
+
                spin_lock(&leader->proc_lock);
                spin_lock(&current->proc_lock);
                proc_dentry1 = proc_pid_unhash(current);
@@ -692,22 +702,6 @@ static int de_thread(struct task_struct *tsk)
                 * two threads with a switched PID, and release
                 * the former thread group leader:
                 */
-               ptrace = leader->ptrace;
-               parent = leader->parent;
-               if (unlikely(ptrace) && unlikely(parent == current)) {
-                       /*
-                        * Joker was ptracing his own group leader,
-                        * and now he wants to be his own parent!
-                        * We can't have that.
-                        */
-                       ptrace = 0;
-               }
-
-               ptrace_unlink(current);
-               ptrace_unlink(leader);
-               remove_parent(current);
-               remove_parent(leader);
-
 
                /* Become a process group leader with the old leader's pid.
                 * Note: The old leader also uses thispid until release_task
@@ -718,19 +712,15 @@ static int de_thread(struct task_struct *tsk)
                attach_pid(current, PIDTYPE_PID,  current->pid);
                attach_pid(current, PIDTYPE_PGID, current->signal->pgrp);
                attach_pid(current, PIDTYPE_SID,  current->signal->session);
-               list_add_tail(&current->tasks, &init_task.tasks);
+               list_add_tail_rcu(&current->tasks, &init_task.tasks);
 
-               current->parent = current->real_parent = leader->real_parent;
-               leader->parent = leader->real_parent = child_reaper;
                current->group_leader = current;
-               leader->group_leader = leader;
+               leader->group_leader = current;
 
-               add_parent(current);
-               add_parent(leader);
-               if (ptrace) {
-                       current->ptrace = ptrace;
-                       __ptrace_link(current, parent);
-               }
+               /* Reduce leader to a thread */
+               detach_pid(leader, PIDTYPE_PGID);
+               detach_pid(leader, PIDTYPE_SID);
+               list_del_init(&leader->tasks);
 
                current->exit_signal = SIGCHLD;
 
index 1041dab6de2fd92bc1eff0b9abcae86973925017..c5ffa852396802d2f58cfae2474f500c4aeb002f 100644 (file)
@@ -767,6 +767,7 @@ int ext3_group_add(struct super_block *sb, struct ext3_new_group_data *input)
        if (input->group != sbi->s_groups_count) {
                ext3_warning(sb, __FUNCTION__,
                             "multiple resizers run on filesystem!");
+               unlock_super(sb);
                err = -EBUSY;
                goto exit_journal;
        }
@@ -974,6 +975,7 @@ int ext3_group_extend(struct super_block *sb, struct ext3_super_block *es,
        if (o_blocks_count != le32_to_cpu(es->s_blocks_count)) {
                ext3_warning(sb, __FUNCTION__,
                             "multiple resizers run on filesystem!");
+               unlock_super(sb);
                err = -EBUSY;
                goto exit_put;
        }
index 889f722ee36d638c5379634ebe2eb54c1055e58e..49035b174b48af51a20b319d133ead21736eefc0 100644 (file)
--- a/fs/fifo.c
+++ b/fs/fifo.c
 #include <linux/fs.h>
 #include <linux/pipe_fs_i.h>
 
-static void wait_for_partner(struct inode* inode, unsigned intcnt)
+static void wait_for_partner(struct inode* inode, unsigned int *cnt)
 {
        int cur = *cnt; 
-       while(cur == *cnt) {
-               pipe_wait(inode);
-               if(signal_pending(current))
+
+       while (cur == *cnt) {
+               pipe_wait(inode->i_pipe);
+               if (signal_pending(current))
                        break;
        }
 }
 
 static void wake_up_partner(struct inode* inode)
 {
-       wake_up_interruptible(PIPE_WAIT(*inode));
+       wake_up_interruptible(&inode->i_pipe->wait);
 }
 
 static int fifo_open(struct inode *inode, struct file *filp)
 {
+       struct pipe_inode_info *pipe;
        int ret;
 
-       mutex_lock(PIPE_MUTEX(*inode));
-       if (!inode->i_pipe) {
+       mutex_lock(&inode->i_mutex);
+       pipe = inode->i_pipe;
+       if (!pipe) {
                ret = -ENOMEM;
-               if(!pipe_new(inode))
+               pipe = alloc_pipe_info(inode);
+               if (!pipe)
                        goto err_nocleanup;
+               inode->i_pipe = pipe;
        }
        filp->f_version = 0;
 
@@ -53,18 +58,18 @@ static int fifo_open(struct inode *inode, struct file *filp)
         *  opened, even when there is no process writing the FIFO.
         */
                filp->f_op = &read_fifo_fops;
-               PIPE_RCOUNTER(*inode)++;
-               if (PIPE_READERS(*inode)++ == 0)
+               pipe->r_counter++;
+               if (pipe->readers++ == 0)
                        wake_up_partner(inode);
 
-               if (!PIPE_WRITERS(*inode)) {
+               if (!pipe->writers) {
                        if ((filp->f_flags & O_NONBLOCK)) {
                                /* suppress POLLHUP until we have
                                 * seen a writer */
-                               filp->f_version = PIPE_WCOUNTER(*inode);
+                               filp->f_version = pipe->w_counter;
                        } else 
                        {
-                               wait_for_partner(inode, &PIPE_WCOUNTER(*inode));
+                               wait_for_partner(inode, &pipe->w_counter);
                                if(signal_pending(current))
                                        goto err_rd;
                        }
@@ -78,16 +83,16 @@ static int fifo_open(struct inode *inode, struct file *filp)
         *  errno=ENXIO when there is no process reading the FIFO.
         */
                ret = -ENXIO;
-               if ((filp->f_flags & O_NONBLOCK) && !PIPE_READERS(*inode))
+               if ((filp->f_flags & O_NONBLOCK) && !pipe->readers)
                        goto err;
 
                filp->f_op = &write_fifo_fops;
-               PIPE_WCOUNTER(*inode)++;
-               if (!PIPE_WRITERS(*inode)++)
+               pipe->w_counter++;
+               if (!pipe->writers++)
                        wake_up_partner(inode);
 
-               if (!PIPE_READERS(*inode)) {
-                       wait_for_partner(inode, &PIPE_RCOUNTER(*inode));
+               if (!pipe->readers) {
+                       wait_for_partner(inode, &pipe->r_counter);
                        if (signal_pending(current))
                                goto err_wr;
                }
@@ -102,11 +107,11 @@ static int fifo_open(struct inode *inode, struct file *filp)
         */
                filp->f_op = &rdwr_fifo_fops;
 
-               PIPE_READERS(*inode)++;
-               PIPE_WRITERS(*inode)++;
-               PIPE_RCOUNTER(*inode)++;
-               PIPE_WCOUNTER(*inode)++;
-               if (PIPE_READERS(*inode) == 1 || PIPE_WRITERS(*inode) == 1)
+               pipe->readers++;
+               pipe->writers++;
+               pipe->r_counter++;
+               pipe->w_counter++;
+               if (pipe->readers == 1 || pipe->writers == 1)
                        wake_up_partner(inode);
                break;
 
@@ -116,27 +121,27 @@ static int fifo_open(struct inode *inode, struct file *filp)
        }
 
        /* Ok! */
-       mutex_unlock(PIPE_MUTEX(*inode));
+       mutex_unlock(&inode->i_mutex);
        return 0;
 
 err_rd:
-       if (!--PIPE_READERS(*inode))
-               wake_up_interruptible(PIPE_WAIT(*inode));
+       if (!--pipe->readers)
+               wake_up_interruptible(&pipe->wait);
        ret = -ERESTARTSYS;
        goto err;
 
 err_wr:
-       if (!--PIPE_WRITERS(*inode))
-               wake_up_interruptible(PIPE_WAIT(*inode));
+       if (!--pipe->writers)
+               wake_up_interruptible(&pipe->wait);
        ret = -ERESTARTSYS;
        goto err;
 
 err:
-       if (!PIPE_READERS(*inode) && !PIPE_WRITERS(*inode))
+       if (!pipe->readers && !pipe->writers)
                free_pipe_info(inode);
 
 err_nocleanup:
-       mutex_unlock(PIPE_MUTEX(*inode));
+       mutex_unlock(&inode->i_mutex);
        return ret;
 }
 
index 23d1f52eb1b8de693f86c96a8eccc2bb5909d750..cc750c68fe709b4d552bead603074564ecbb0c9b 100644 (file)
@@ -1,6 +1,6 @@
 /*
   FUSE: Filesystem in Userspace
-  Copyright (C) 2001-2005  Miklos Szeredi <miklos@szeredi.hu>
+  Copyright (C) 2001-2006  Miklos Szeredi <miklos@szeredi.hu>
 
   This program can be distributed under the terms of the GNU GPL.
   See the file COPYING.
@@ -23,13 +23,11 @@ static kmem_cache_t *fuse_req_cachep;
 
 static struct fuse_conn *fuse_get_conn(struct file *file)
 {
-       struct fuse_conn *fc;
-       spin_lock(&fuse_lock);
-       fc = file->private_data;
-       if (fc && !fc->connected)
-               fc = NULL;
-       spin_unlock(&fuse_lock);
-       return fc;
+       /*
+        * Lockless access is OK, because file->private data is set
+        * once during mount and is valid until the file is released.
+        */
+       return file->private_data;
 }
 
 static void fuse_request_init(struct fuse_req *req)
@@ -74,10 +72,8 @@ static void restore_sigs(sigset_t *oldset)
  */
 void fuse_reset_request(struct fuse_req *req)
 {
-       int preallocated = req->preallocated;
        BUG_ON(atomic_read(&req->count) != 1);
        fuse_request_init(req);
-       req->preallocated = preallocated;
 }
 
 static void __fuse_get_request(struct fuse_req *req)
@@ -92,80 +88,54 @@ static void __fuse_put_request(struct fuse_req *req)
        atomic_dec(&req->count);
 }
 
-static struct fuse_req *do_get_request(struct fuse_conn *fc)
+struct fuse_req *fuse_get_req(struct fuse_conn *fc)
 {
        struct fuse_req *req;
-
-       spin_lock(&fuse_lock);
-       BUG_ON(list_empty(&fc->unused_list));
-       req = list_entry(fc->unused_list.next, struct fuse_req, list);
-       list_del_init(&req->list);
-       spin_unlock(&fuse_lock);
-       fuse_request_init(req);
-       req->preallocated = 1;
-       req->in.h.uid = current->fsuid;
-       req->in.h.gid = current->fsgid;
-       req->in.h.pid = current->pid;
-       return req;
-}
-
-/* This can return NULL, but only in case it's interrupted by a SIGKILL */
-struct fuse_req *fuse_get_request(struct fuse_conn *fc)
-{
-       int intr;
        sigset_t oldset;
+       int intr;
+       int err;
 
        atomic_inc(&fc->num_waiting);
        block_sigs(&oldset);
-       intr = down_interruptible(&fc->outstanding_sem);
+       intr = wait_event_interruptible(fc->blocked_waitq, !fc->blocked);
        restore_sigs(&oldset);
-       if (intr) {
-               atomic_dec(&fc->num_waiting);
-               return NULL;
-       }
-       return do_get_request(fc);
-}
+       err = -EINTR;
+       if (intr)
+               goto out;
 
-/* Must be called with fuse_lock held */
-static void fuse_putback_request(struct fuse_conn *fc, struct fuse_req *req)
-{
-       if (req->preallocated) {
-               atomic_dec(&fc->num_waiting);
-               list_add(&req->list, &fc->unused_list);
-       } else
-               fuse_request_free(req);
+       req = fuse_request_alloc();
+       err = -ENOMEM;
+       if (!req)
+               goto out;
 
-       /* If we are in debt decrease that first */
-       if (fc->outstanding_debt)
-               fc->outstanding_debt--;
-       else
-               up(&fc->outstanding_sem);
+       req->in.h.uid = current->fsuid;
+       req->in.h.gid = current->fsgid;
+       req->in.h.pid = current->pid;
+       req->waiting = 1;
+       return req;
+
+ out:
+       atomic_dec(&fc->num_waiting);
+       return ERR_PTR(err);
 }
 
 void fuse_put_request(struct fuse_conn *fc, struct fuse_req *req)
 {
        if (atomic_dec_and_test(&req->count)) {
-               spin_lock(&fuse_lock);
-               fuse_putback_request(fc, req);
-               spin_unlock(&fuse_lock);
+               if (req->waiting)
+                       atomic_dec(&fc->num_waiting);
+               fuse_request_free(req);
        }
 }
 
-static void fuse_put_request_locked(struct fuse_conn *fc, struct fuse_req *req)
-{
-       if (atomic_dec_and_test(&req->count))
-               fuse_putback_request(fc, req);
-}
-
-void fuse_release_background(struct fuse_req *req)
+void fuse_remove_background(struct fuse_conn *fc, struct fuse_req *req)
 {
-       iput(req->inode);
-       iput(req->inode2);
-       if (req->file)
-               fput(req->file);
-       spin_lock(&fuse_lock);
-       list_del(&req->bg_entry);
-       spin_unlock(&fuse_lock);
+       list_del_init(&req->bg_entry);
+       if (fc->num_background == FUSE_MAX_BACKGROUND) {
+               fc->blocked = 0;
+               wake_up_all(&fc->blocked_waitq);
+       }
+       fc->num_background--;
 }
 
 /*
@@ -184,28 +154,38 @@ void fuse_release_background(struct fuse_req *req)
  * interrupted and put in the background, it will return with an error
  * and hence never be reset and reused.
  *
- * Called with fuse_lock, unlocks it
+ * Called with fc->lock, unlocks it
  */
 static void request_end(struct fuse_conn *fc, struct fuse_req *req)
 {
        list_del(&req->list);
        req->state = FUSE_REQ_FINISHED;
        if (!req->background) {
+               spin_unlock(&fc->lock);
                wake_up(&req->waitq);
-               fuse_put_request_locked(fc, req);
-               spin_unlock(&fuse_lock);
+               fuse_put_request(fc, req);
        } else {
+               struct inode *inode = req->inode;
+               struct inode *inode2 = req->inode2;
+               struct file *file = req->file;
                void (*end) (struct fuse_conn *, struct fuse_req *) = req->end;
                req->end = NULL;
-               spin_unlock(&fuse_lock);
-               down_read(&fc->sbput_sem);
-               if (fc->mounted)
-                       fuse_release_background(req);
-               up_read(&fc->sbput_sem);
+               req->inode = NULL;
+               req->inode2 = NULL;
+               req->file = NULL;
+               if (!list_empty(&req->bg_entry))
+                       fuse_remove_background(fc, req);
+               spin_unlock(&fc->lock);
+
                if (end)
                        end(fc, req);
                else
                        fuse_put_request(fc, req);
+
+               if (file)
+                       fput(file);
+               iput(inode);
+               iput(inode2);
        }
 }
 
@@ -242,6 +222,9 @@ static void background_request(struct fuse_conn *fc, struct fuse_req *req)
 {
        req->background = 1;
        list_add(&req->bg_entry, &fc->background);
+       fc->num_background++;
+       if (fc->num_background == FUSE_MAX_BACKGROUND)
+               fc->blocked = 1;
        if (req->inode)
                req->inode = igrab(req->inode);
        if (req->inode2)
@@ -250,16 +233,16 @@ static void background_request(struct fuse_conn *fc, struct fuse_req *req)
                get_file(req->file);
 }
 
-/* Called with fuse_lock held.  Releases, and then reacquires it. */
+/* Called with fc->lock held.  Releases, and then reacquires it. */
 static void request_wait_answer(struct fuse_conn *fc, struct fuse_req *req)
 {
        sigset_t oldset;
 
-       spin_unlock(&fuse_lock);
+       spin_unlock(&fc->lock);
        block_sigs(&oldset);
        wait_event_interruptible(req->waitq, req->state == FUSE_REQ_FINISHED);
        restore_sigs(&oldset);
-       spin_lock(&fuse_lock);
+       spin_lock(&fc->lock);
        if (req->state == FUSE_REQ_FINISHED && !req->interrupted)
                return;
 
@@ -273,9 +256,9 @@ static void request_wait_answer(struct fuse_conn *fc, struct fuse_req *req)
                   locked state, there mustn't be any filesystem
                   operation (e.g. page fault), since that could lead
                   to deadlock */
-               spin_unlock(&fuse_lock);
+               spin_unlock(&fc->lock);
                wait_event(req->waitq, !req->locked);
-               spin_lock(&fuse_lock);
+               spin_lock(&fc->lock);
        }
        if (req->state == FUSE_REQ_PENDING) {
                list_del(&req->list);
@@ -304,19 +287,14 @@ static void queue_request(struct fuse_conn *fc, struct fuse_req *req)
        req->in.h.unique = fc->reqctr;
        req->in.h.len = sizeof(struct fuse_in_header) +
                len_args(req->in.numargs, (struct fuse_arg *) req->in.args);
-       if (!req->preallocated) {
-               /* If request is not preallocated (either FORGET or
-                  RELEASE), then still decrease outstanding_sem, so
-                  user can't open infinite number of files while not
-                  processing the RELEASE requests.  However for
-                  efficiency do it without blocking, so if down()
-                  would block, just increase the debt instead */
-               if (down_trylock(&fc->outstanding_sem))
-                       fc->outstanding_debt++;
-       }
        list_add_tail(&req->list, &fc->pending);
        req->state = FUSE_REQ_PENDING;
+       if (!req->waiting) {
+               req->waiting = 1;
+               atomic_inc(&fc->num_waiting);
+       }
        wake_up(&fc->waitq);
+       kill_fasync(&fc->fasync, SIGIO, POLL_IN);
 }
 
 /*
@@ -325,7 +303,7 @@ static void queue_request(struct fuse_conn *fc, struct fuse_req *req)
 void request_send(struct fuse_conn *fc, struct fuse_req *req)
 {
        req->isreply = 1;
-       spin_lock(&fuse_lock);
+       spin_lock(&fc->lock);
        if (!fc->connected)
                req->out.h.error = -ENOTCONN;
        else if (fc->conn_error)
@@ -338,15 +316,16 @@ void request_send(struct fuse_conn *fc, struct fuse_req *req)
 
                request_wait_answer(fc, req);
        }
-       spin_unlock(&fuse_lock);
+       spin_unlock(&fc->lock);
 }
 
 static void request_send_nowait(struct fuse_conn *fc, struct fuse_req *req)
 {
-       spin_lock(&fuse_lock);
+       spin_lock(&fc->lock);
+       background_request(fc, req);
        if (fc->connected) {
                queue_request(fc, req);
-               spin_unlock(&fuse_lock);
+               spin_unlock(&fc->lock);
        } else {
                req->out.h.error = -ENOTCONN;
                request_end(fc, req);
@@ -362,9 +341,6 @@ void request_send_noreply(struct fuse_conn *fc, struct fuse_req *req)
 void request_send_background(struct fuse_conn *fc, struct fuse_req *req)
 {
        req->isreply = 1;
-       spin_lock(&fuse_lock);
-       background_request(fc, req);
-       spin_unlock(&fuse_lock);
        request_send_nowait(fc, req);
 }
 
@@ -373,16 +349,16 @@ void request_send_background(struct fuse_conn *fc, struct fuse_req *req)
  * anything that could cause a page-fault.  If the request was already
  * interrupted bail out.
  */
-static int lock_request(struct fuse_req *req)
+static int lock_request(struct fuse_conn *fc, struct fuse_req *req)
 {
        int err = 0;
        if (req) {
-               spin_lock(&fuse_lock);
+               spin_lock(&fc->lock);
                if (req->interrupted)
                        err = -ENOENT;
                else
                        req->locked = 1;
-               spin_unlock(&fuse_lock);
+               spin_unlock(&fc->lock);
        }
        return err;
 }
@@ -392,18 +368,19 @@ static int lock_request(struct fuse_req *req)
  * requester thread is currently waiting for it to be unlocked, so
  * wake it up.
  */
-static void unlock_request(struct fuse_req *req)
+static void unlock_request(struct fuse_conn *fc, struct fuse_req *req)
 {
        if (req) {
-               spin_lock(&fuse_lock);
+               spin_lock(&fc->lock);
                req->locked = 0;
                if (req->interrupted)
                        wake_up(&req->waitq);
-               spin_unlock(&fuse_lock);
+               spin_unlock(&fc->lock);
        }
 }
 
 struct fuse_copy_state {
+       struct fuse_conn *fc;
        int write;
        struct fuse_req *req;
        const struct iovec *iov;
@@ -416,11 +393,12 @@ struct fuse_copy_state {
        unsigned len;
 };
 
-static void fuse_copy_init(struct fuse_copy_state *cs, int write,
-                          struct fuse_req *req, const struct iovec *iov,
-                          unsigned long nr_segs)
+static void fuse_copy_init(struct fuse_copy_state *cs, struct fuse_conn *fc,
+                          int write, struct fuse_req *req,
+                          const struct iovec *iov, unsigned long nr_segs)
 {
        memset(cs, 0, sizeof(*cs));
+       cs->fc = fc;
        cs->write = write;
        cs->req = req;
        cs->iov = iov;
@@ -450,7 +428,7 @@ static int fuse_copy_fill(struct fuse_copy_state *cs)
        unsigned long offset;
        int err;
 
-       unlock_request(cs->req);
+       unlock_request(cs->fc, cs->req);
        fuse_copy_finish(cs);
        if (!cs->seglen) {
                BUG_ON(!cs->nr_segs);
@@ -473,7 +451,7 @@ static int fuse_copy_fill(struct fuse_copy_state *cs)
        cs->seglen -= cs->len;
        cs->addr += cs->len;
 
-       return lock_request(cs->req);
+       return lock_request(cs->fc, cs->req);
 }
 
 /* Do as much copy to/from userspace buffer as we can */
@@ -585,9 +563,9 @@ static void request_wait(struct fuse_conn *fc)
                if (signal_pending(current))
                        break;
 
-               spin_unlock(&fuse_lock);
+               spin_unlock(&fc->lock);
                schedule();
-               spin_lock(&fuse_lock);
+               spin_lock(&fc->lock);
        }
        set_current_state(TASK_RUNNING);
        remove_wait_queue(&fc->waitq, &wait);
@@ -606,18 +584,21 @@ static ssize_t fuse_dev_readv(struct file *file, const struct iovec *iov,
                              unsigned long nr_segs, loff_t *off)
 {
        int err;
-       struct fuse_conn *fc;
        struct fuse_req *req;
        struct fuse_in *in;
        struct fuse_copy_state cs;
        unsigned reqsize;
+       struct fuse_conn *fc = fuse_get_conn(file);
+       if (!fc)
+               return -EPERM;
 
  restart:
-       spin_lock(&fuse_lock);
-       fc = file->private_data;
-       err = -EPERM;
-       if (!fc)
+       spin_lock(&fc->lock);
+       err = -EAGAIN;
+       if ((file->f_flags & O_NONBLOCK) && fc->connected &&
+           list_empty(&fc->pending))
                goto err_unlock;
+
        request_wait(fc);
        err = -ENODEV;
        if (!fc->connected)
@@ -641,14 +622,14 @@ static ssize_t fuse_dev_readv(struct file *file, const struct iovec *iov,
                request_end(fc, req);
                goto restart;
        }
-       spin_unlock(&fuse_lock);
-       fuse_copy_init(&cs, 1, req, iov, nr_segs);
+       spin_unlock(&fc->lock);
+       fuse_copy_init(&cs, fc, 1, req, iov, nr_segs);
        err = fuse_copy_one(&cs, &in->h, sizeof(in->h));
        if (!err)
                err = fuse_copy_args(&cs, in->numargs, in->argpages,
                                     (struct fuse_arg *) in->args, 0);
        fuse_copy_finish(&cs);
-       spin_lock(&fuse_lock);
+       spin_lock(&fc->lock);
        req->locked = 0;
        if (!err && req->interrupted)
                err = -ENOENT;
@@ -663,12 +644,12 @@ static ssize_t fuse_dev_readv(struct file *file, const struct iovec *iov,
        else {
                req->state = FUSE_REQ_SENT;
                list_move_tail(&req->list, &fc->processing);
-               spin_unlock(&fuse_lock);
+               spin_unlock(&fc->lock);
        }
        return reqsize;
 
  err_unlock:
-       spin_unlock(&fuse_lock);
+       spin_unlock(&fc->lock);
        return err;
 }
 
@@ -735,9 +716,9 @@ static ssize_t fuse_dev_writev(struct file *file, const struct iovec *iov,
        struct fuse_copy_state cs;
        struct fuse_conn *fc = fuse_get_conn(file);
        if (!fc)
-               return -ENODEV;
+               return -EPERM;
 
-       fuse_copy_init(&cs, 0, NULL, iov, nr_segs);
+       fuse_copy_init(&cs, fc, 0, NULL, iov, nr_segs);
        if (nbytes < sizeof(struct fuse_out_header))
                return -EINVAL;
 
@@ -749,7 +730,7 @@ static ssize_t fuse_dev_writev(struct file *file, const struct iovec *iov,
            oh.len != nbytes)
                goto err_finish;
 
-       spin_lock(&fuse_lock);
+       spin_lock(&fc->lock);
        err = -ENOENT;
        if (!fc->connected)
                goto err_unlock;
@@ -760,9 +741,9 @@ static ssize_t fuse_dev_writev(struct file *file, const struct iovec *iov,
                goto err_unlock;
 
        if (req->interrupted) {
-               spin_unlock(&fuse_lock);
+               spin_unlock(&fc->lock);
                fuse_copy_finish(&cs);
-               spin_lock(&fuse_lock);
+               spin_lock(&fc->lock);
                request_end(fc, req);
                return -ENOENT;
        }
@@ -770,12 +751,12 @@ static ssize_t fuse_dev_writev(struct file *file, const struct iovec *iov,
        req->out.h = oh;
        req->locked = 1;
        cs.req = req;
-       spin_unlock(&fuse_lock);
+       spin_unlock(&fc->lock);
 
        err = copy_out_args(&cs, &req->out, nbytes);
        fuse_copy_finish(&cs);
 
-       spin_lock(&fuse_lock);
+       spin_lock(&fc->lock);
        req->locked = 0;
        if (!err) {
                if (req->interrupted)
@@ -787,7 +768,7 @@ static ssize_t fuse_dev_writev(struct file *file, const struct iovec *iov,
        return err ? err : nbytes;
 
  err_unlock:
-       spin_unlock(&fuse_lock);
+       spin_unlock(&fc->lock);
  err_finish:
        fuse_copy_finish(&cs);
        return err;
@@ -804,18 +785,19 @@ static ssize_t fuse_dev_write(struct file *file, const char __user *buf,
 
 static unsigned fuse_dev_poll(struct file *file, poll_table *wait)
 {
-       struct fuse_conn *fc = fuse_get_conn(file);
        unsigned mask = POLLOUT | POLLWRNORM;
-
+       struct fuse_conn *fc = fuse_get_conn(file);
        if (!fc)
-               return -ENODEV;
+               return POLLERR;
 
        poll_wait(file, &fc->waitq, wait);
 
-       spin_lock(&fuse_lock);
-       if (!list_empty(&fc->pending))
-                mask |= POLLIN | POLLRDNORM;
-       spin_unlock(&fuse_lock);
+       spin_lock(&fc->lock);
+       if (!fc->connected)
+               mask = POLLERR;
+       else if (!list_empty(&fc->pending))
+               mask |= POLLIN | POLLRDNORM;
+       spin_unlock(&fc->lock);
 
        return mask;
 }
@@ -823,7 +805,7 @@ static unsigned fuse_dev_poll(struct file *file, poll_table *wait)
 /*
  * Abort all requests on the given list (pending or processing)
  *
- * This function releases and reacquires fuse_lock
+ * This function releases and reacquires fc->lock
  */
 static void end_requests(struct fuse_conn *fc, struct list_head *head)
 {
@@ -832,7 +814,7 @@ static void end_requests(struct fuse_conn *fc, struct list_head *head)
                req = list_entry(head->next, struct fuse_req, list);
                req->out.h.error = -ECONNABORTED;
                request_end(fc, req);
-               spin_lock(&fuse_lock);
+               spin_lock(&fc->lock);
        }
 }
 
@@ -863,10 +845,10 @@ static void end_io_requests(struct fuse_conn *fc)
                        req->end = NULL;
                        /* The end function will consume this reference */
                        __fuse_get_request(req);
-                       spin_unlock(&fuse_lock);
+                       spin_unlock(&fc->lock);
                        wait_event(req->waitq, !req->locked);
                        end(fc, req);
-                       spin_lock(&fuse_lock);
+                       spin_lock(&fc->lock);
                }
        }
 }
@@ -893,35 +875,44 @@ static void end_io_requests(struct fuse_conn *fc)
  */
 void fuse_abort_conn(struct fuse_conn *fc)
 {
-       spin_lock(&fuse_lock);
+       spin_lock(&fc->lock);
        if (fc->connected) {
                fc->connected = 0;
                end_io_requests(fc);
                end_requests(fc, &fc->pending);
                end_requests(fc, &fc->processing);
                wake_up_all(&fc->waitq);
+               kill_fasync(&fc->fasync, SIGIO, POLL_IN);
        }
-       spin_unlock(&fuse_lock);
+       spin_unlock(&fc->lock);
 }
 
 static int fuse_dev_release(struct inode *inode, struct file *file)
 {
-       struct fuse_conn *fc;
-
-       spin_lock(&fuse_lock);
-       fc = file->private_data;
+       struct fuse_conn *fc = fuse_get_conn(file);
        if (fc) {
+               spin_lock(&fc->lock);
                fc->connected = 0;
                end_requests(fc, &fc->pending);
                end_requests(fc, &fc->processing);
-       }
-       spin_unlock(&fuse_lock);
-       if (fc)
+               spin_unlock(&fc->lock);
+               fasync_helper(-1, file, 0, &fc->fasync);
                kobject_put(&fc->kobj);
+       }
 
        return 0;
 }
 
+static int fuse_dev_fasync(int fd, struct file *file, int on)
+{
+       struct fuse_conn *fc = fuse_get_conn(file);
+       if (!fc)
+               return -EPERM;
+
+       /* No locking - fasync_helper does its own locking */
+       return fasync_helper(fd, file, on, &fc->fasync);
+}
+
 const struct file_operations fuse_dev_operations = {
        .owner          = THIS_MODULE,
        .llseek         = no_llseek,
@@ -931,6 +922,7 @@ const struct file_operations fuse_dev_operations = {
        .writev         = fuse_dev_writev,
        .poll           = fuse_dev_poll,
        .release        = fuse_dev_release,
+       .fasync         = fuse_dev_fasync,
 };
 
 static struct miscdevice fuse_miscdevice = {
index 256355b80256f4525272f84788c8561207942389..8d7546e832e89a28e770d09e8c6732577c41ea8f 100644 (file)
@@ -117,8 +117,8 @@ static int fuse_dentry_revalidate(struct dentry *entry, struct nameidata *nd)
                        return 0;
 
                fc = get_fuse_conn(inode);
-               req = fuse_get_request(fc);
-               if (!req)
+               req = fuse_get_req(fc);
+               if (IS_ERR(req))
                        return 0;
 
                fuse_lookup_init(req, entry->d_parent->d_inode, entry, &outarg);
@@ -188,9 +188,9 @@ static struct dentry *fuse_lookup(struct inode *dir, struct dentry *entry,
        if (entry->d_name.len > FUSE_NAME_MAX)
                return ERR_PTR(-ENAMETOOLONG);
 
-       req = fuse_get_request(fc);
-       if (!req)
-               return ERR_PTR(-EINTR);
+       req = fuse_get_req(fc);
+       if (IS_ERR(req))
+               return ERR_PTR(PTR_ERR(req));
 
        fuse_lookup_init(req, dir, entry, &outarg);
        request_send(fc, req);
@@ -244,15 +244,14 @@ static int fuse_create_open(struct inode *dir, struct dentry *entry, int mode,
        struct file *file;
        int flags = nd->intent.open.flags - 1;
 
-       err = -ENOSYS;
        if (fc->no_create)
-               goto out;
+               return -ENOSYS;
 
-       err = -EINTR;
-       req = fuse_get_request(fc);
-       if (!req)
-               goto out;
+       req = fuse_get_req(fc);
+       if (IS_ERR(req))
+               return PTR_ERR(req);
 
+       err = -ENOMEM;
        ff = fuse_file_alloc();
        if (!ff)
                goto out_put_request;
@@ -314,7 +313,6 @@ static int fuse_create_open(struct inode *dir, struct dentry *entry, int mode,
        fuse_file_free(ff);
  out_put_request:
        fuse_put_request(fc, req);
- out:
        return err;
 }
 
@@ -375,9 +373,9 @@ static int fuse_mknod(struct inode *dir, struct dentry *entry, int mode,
 {
        struct fuse_mknod_in inarg;
        struct fuse_conn *fc = get_fuse_conn(dir);
-       struct fuse_req *req = fuse_get_request(fc);
-       if (!req)
-               return -EINTR;
+       struct fuse_req *req = fuse_get_req(fc);
+       if (IS_ERR(req))
+               return PTR_ERR(req);
 
        memset(&inarg, 0, sizeof(inarg));
        inarg.mode = mode;
@@ -407,9 +405,9 @@ static int fuse_mkdir(struct inode *dir, struct dentry *entry, int mode)
 {
        struct fuse_mkdir_in inarg;
        struct fuse_conn *fc = get_fuse_conn(dir);
-       struct fuse_req *req = fuse_get_request(fc);
-       if (!req)
-               return -EINTR;
+       struct fuse_req *req = fuse_get_req(fc);
+       if (IS_ERR(req))
+               return PTR_ERR(req);
 
        memset(&inarg, 0, sizeof(inarg));
        inarg.mode = mode;
@@ -427,9 +425,9 @@ static int fuse_symlink(struct inode *dir, struct dentry *entry,
 {
        struct fuse_conn *fc = get_fuse_conn(dir);
        unsigned len = strlen(link) + 1;
-       struct fuse_req *req = fuse_get_request(fc);
-       if (!req)
-               return -EINTR;
+       struct fuse_req *req = fuse_get_req(fc);
+       if (IS_ERR(req))
+               return PTR_ERR(req);
 
        req->in.h.opcode = FUSE_SYMLINK;
        req->in.numargs = 2;
@@ -444,9 +442,9 @@ static int fuse_unlink(struct inode *dir, struct dentry *entry)
 {
        int err;
        struct fuse_conn *fc = get_fuse_conn(dir);
-       struct fuse_req *req = fuse_get_request(fc);
-       if (!req)
-               return -EINTR;
+       struct fuse_req *req = fuse_get_req(fc);
+       if (IS_ERR(req))
+               return PTR_ERR(req);
 
        req->in.h.opcode = FUSE_UNLINK;
        req->in.h.nodeid = get_node_id(dir);
@@ -476,9 +474,9 @@ static int fuse_rmdir(struct inode *dir, struct dentry *entry)
 {
        int err;
        struct fuse_conn *fc = get_fuse_conn(dir);
-       struct fuse_req *req = fuse_get_request(fc);
-       if (!req)
-               return -EINTR;
+       struct fuse_req *req = fuse_get_req(fc);
+       if (IS_ERR(req))
+               return PTR_ERR(req);
 
        req->in.h.opcode = FUSE_RMDIR;
        req->in.h.nodeid = get_node_id(dir);
@@ -504,9 +502,9 @@ static int fuse_rename(struct inode *olddir, struct dentry *oldent,
        int err;
        struct fuse_rename_in inarg;
        struct fuse_conn *fc = get_fuse_conn(olddir);
-       struct fuse_req *req = fuse_get_request(fc);
-       if (!req)
-               return -EINTR;
+       struct fuse_req *req = fuse_get_req(fc);
+       if (IS_ERR(req))
+               return PTR_ERR(req);
 
        memset(&inarg, 0, sizeof(inarg));
        inarg.newdir = get_node_id(newdir);
@@ -553,9 +551,9 @@ static int fuse_link(struct dentry *entry, struct inode *newdir,
        struct fuse_link_in inarg;
        struct inode *inode = entry->d_inode;
        struct fuse_conn *fc = get_fuse_conn(inode);
-       struct fuse_req *req = fuse_get_request(fc);
-       if (!req)
-               return -EINTR;
+       struct fuse_req *req = fuse_get_req(fc);
+       if (IS_ERR(req))
+               return PTR_ERR(req);
 
        memset(&inarg, 0, sizeof(inarg));
        inarg.oldnodeid = get_node_id(inode);
@@ -583,9 +581,9 @@ int fuse_do_getattr(struct inode *inode)
        int err;
        struct fuse_attr_out arg;
        struct fuse_conn *fc = get_fuse_conn(inode);
-       struct fuse_req *req = fuse_get_request(fc);
-       if (!req)
-               return -EINTR;
+       struct fuse_req *req = fuse_get_req(fc);
+       if (IS_ERR(req))
+               return PTR_ERR(req);
 
        req->in.h.opcode = FUSE_GETATTR;
        req->in.h.nodeid = get_node_id(inode);
@@ -673,9 +671,9 @@ static int fuse_access(struct inode *inode, int mask)
        if (fc->no_access)
                return 0;
 
-       req = fuse_get_request(fc);
-       if (!req)
-               return -EINTR;
+       req = fuse_get_req(fc);
+       if (IS_ERR(req))
+               return PTR_ERR(req);
 
        memset(&inarg, 0, sizeof(inarg));
        inarg.mask = mask;
@@ -780,9 +778,9 @@ static int fuse_readdir(struct file *file, void *dstbuf, filldir_t filldir)
        if (is_bad_inode(inode))
                return -EIO;
 
-       req = fuse_get_request(fc);
-       if (!req)
-               return -EINTR;
+       req = fuse_get_req(fc);
+       if (IS_ERR(req))
+               return PTR_ERR(req);
 
        page = alloc_page(GFP_KERNEL);
        if (!page) {
@@ -809,11 +807,11 @@ static char *read_link(struct dentry *dentry)
 {
        struct inode *inode = dentry->d_inode;
        struct fuse_conn *fc = get_fuse_conn(inode);
-       struct fuse_req *req = fuse_get_request(fc);
+       struct fuse_req *req = fuse_get_req(fc);
        char *link;
 
-       if (!req)
-               return ERR_PTR(-EINTR);
+       if (IS_ERR(req))
+               return ERR_PTR(PTR_ERR(req));
 
        link = (char *) __get_free_page(GFP_KERNEL);
        if (!link) {
@@ -933,9 +931,9 @@ static int fuse_setattr(struct dentry *entry, struct iattr *attr)
                }
        }
 
-       req = fuse_get_request(fc);
-       if (!req)
-               return -EINTR;
+       req = fuse_get_req(fc);
+       if (IS_ERR(req))
+               return PTR_ERR(req);
 
        memset(&inarg, 0, sizeof(inarg));
        iattr_to_fattr(attr, &inarg);
@@ -995,9 +993,9 @@ static int fuse_setxattr(struct dentry *entry, const char *name,
        if (fc->no_setxattr)
                return -EOPNOTSUPP;
 
-       req = fuse_get_request(fc);
-       if (!req)
-               return -EINTR;
+       req = fuse_get_req(fc);
+       if (IS_ERR(req))
+               return PTR_ERR(req);
 
        memset(&inarg, 0, sizeof(inarg));
        inarg.size = size;
@@ -1035,9 +1033,9 @@ static ssize_t fuse_getxattr(struct dentry *entry, const char *name,
        if (fc->no_getxattr)
                return -EOPNOTSUPP;
 
-       req = fuse_get_request(fc);
-       if (!req)
-               return -EINTR;
+       req = fuse_get_req(fc);
+       if (IS_ERR(req))
+               return PTR_ERR(req);
 
        memset(&inarg, 0, sizeof(inarg));
        inarg.size = size;
@@ -1085,9 +1083,9 @@ static ssize_t fuse_listxattr(struct dentry *entry, char *list, size_t size)
        if (fc->no_listxattr)
                return -EOPNOTSUPP;
 
-       req = fuse_get_request(fc);
-       if (!req)
-               return -EINTR;
+       req = fuse_get_req(fc);
+       if (IS_ERR(req))
+               return PTR_ERR(req);
 
        memset(&inarg, 0, sizeof(inarg));
        inarg.size = size;
@@ -1131,9 +1129,9 @@ static int fuse_removexattr(struct dentry *entry, const char *name)
        if (fc->no_removexattr)
                return -EOPNOTSUPP;
 
-       req = fuse_get_request(fc);
-       if (!req)
-               return -EINTR;
+       req = fuse_get_req(fc);
+       if (IS_ERR(req))
+               return PTR_ERR(req);
 
        req->in.h.opcode = FUSE_REMOVEXATTR;
        req->in.h.nodeid = get_node_id(inode);
index 975f2697e866388d5c9e5ad9f80fc75f6e0953a1..fc342cf7c2cc7881dbfafa09097d6de52b34bdca 100644 (file)
@@ -1,6 +1,6 @@
 /*
   FUSE: Filesystem in Userspace
-  Copyright (C) 2001-2005  Miklos Szeredi <miklos@szeredi.hu>
+  Copyright (C) 2001-2006  Miklos Szeredi <miklos@szeredi.hu>
 
   This program can be distributed under the terms of the GNU GPL.
   See the file COPYING.
@@ -22,9 +22,9 @@ static int fuse_send_open(struct inode *inode, struct file *file, int isdir,
        struct fuse_req *req;
        int err;
 
-       req = fuse_get_request(fc);
-       if (!req)
-               return -EINTR;
+       req = fuse_get_req(fc);
+       if (IS_ERR(req))
+               return PTR_ERR(req);
 
        memset(&inarg, 0, sizeof(inarg));
        inarg.flags = file->f_flags & ~(O_CREAT | O_EXCL | O_NOCTTY | O_TRUNC);
@@ -184,9 +184,9 @@ static int fuse_flush(struct file *file)
        if (fc->no_flush)
                return 0;
 
-       req = fuse_get_request(fc);
-       if (!req)
-               return -EINTR;
+       req = fuse_get_req(fc);
+       if (IS_ERR(req))
+               return PTR_ERR(req);
 
        memset(&inarg, 0, sizeof(inarg));
        inarg.fh = ff->fh;
@@ -223,9 +223,9 @@ int fuse_fsync_common(struct file *file, struct dentry *de, int datasync,
        if ((!isdir && fc->no_fsync) || (isdir && fc->no_fsyncdir))
                return 0;
 
-       req = fuse_get_request(fc);
-       if (!req)
-               return -EINTR;
+       req = fuse_get_req(fc);
+       if (IS_ERR(req))
+               return PTR_ERR(req);
 
        memset(&inarg, 0, sizeof(inarg));
        inarg.fh = ff->fh;
@@ -297,9 +297,9 @@ static int fuse_readpage(struct file *file, struct page *page)
        if (is_bad_inode(inode))
                goto out;
 
-       err = -EINTR;
-       req = fuse_get_request(fc);
-       if (!req)
+       req = fuse_get_req(fc);
+       err = PTR_ERR(req);
+       if (IS_ERR(req))
                goto out;
 
        req->out.page_zeroing = 1;
@@ -368,10 +368,10 @@ static int fuse_readpages_fill(void *_data, struct page *page)
             (req->num_pages + 1) * PAGE_CACHE_SIZE > fc->max_read ||
             req->pages[req->num_pages - 1]->index + 1 != page->index)) {
                fuse_send_readpages(req, data->file, inode);
-               data->req = req = fuse_get_request(fc);
-               if (!req) {
+               data->req = req = fuse_get_req(fc);
+               if (IS_ERR(req)) {
                        unlock_page(page);
-                       return -EINTR;
+                       return PTR_ERR(req);
                }
        }
        req->pages[req->num_pages] = page;
@@ -392,13 +392,17 @@ static int fuse_readpages(struct file *file, struct address_space *mapping,
 
        data.file = file;
        data.inode = inode;
-       data.req = fuse_get_request(fc);
-       if (!data.req)
-               return -EINTR;
+       data.req = fuse_get_req(fc);
+       if (IS_ERR(data.req))
+               return PTR_ERR(data.req);
 
        err = read_cache_pages(mapping, pages, fuse_readpages_fill, &data);
-       if (!err)
-               fuse_send_readpages(data.req, file, inode);
+       if (!err) {
+               if (data.req->num_pages)
+                       fuse_send_readpages(data.req, file, inode);
+               else
+                       fuse_put_request(fc, data.req);
+       }
        return err;
 }
 
@@ -451,9 +455,9 @@ static int fuse_commit_write(struct file *file, struct page *page,
        if (is_bad_inode(inode))
                return -EIO;
 
-       req = fuse_get_request(fc);
-       if (!req)
-               return -EINTR;
+       req = fuse_get_req(fc);
+       if (IS_ERR(req))
+               return PTR_ERR(req);
 
        req->num_pages = 1;
        req->pages[0] = page;
@@ -528,9 +532,9 @@ static ssize_t fuse_direct_io(struct file *file, const char __user *buf,
        if (is_bad_inode(inode))
                return -EIO;
 
-       req = fuse_get_request(fc);
-       if (!req)
-               return -EINTR;
+       req = fuse_get_req(fc);
+       if (IS_ERR(req))
+               return PTR_ERR(req);
 
        while (count) {
                size_t nres;
@@ -561,8 +565,12 @@ static ssize_t fuse_direct_io(struct file *file, const char __user *buf,
                buf += nres;
                if (nres != nbytes)
                        break;
-               if (count)
-                       fuse_reset_request(req);
+               if (count) {
+                       fuse_put_request(fc, req);
+                       req = fuse_get_req(fc);
+                       if (IS_ERR(req))
+                               break;
+               }
        }
        fuse_put_request(fc, req);
        if (res > 0) {
index a16a04fcf41eca2e37ac265a368a19eecf426dc3..59661c481d9d4fecb6286d2811cbebe649f3a992 100644 (file)
@@ -1,6 +1,6 @@
 /*
   FUSE: Filesystem in Userspace
-  Copyright (C) 2001-2005  Miklos Szeredi <miklos@szeredi.hu>
+  Copyright (C) 2001-2006  Miklos Szeredi <miklos@szeredi.hu>
 
   This program can be distributed under the terms of the GNU GPL.
   See the file COPYING.
@@ -18,8 +18,8 @@
 /** Max number of pages that can be used in a single read request */
 #define FUSE_MAX_PAGES_PER_REQ 32
 
-/** If more requests are outstanding, then the operation will block */
-#define FUSE_MAX_OUTSTANDING 10
+/** Maximum number of outstanding background requests */
+#define FUSE_MAX_BACKGROUND 10
 
 /** It could be as large as PATH_MAX, but would that have any uses? */
 #define FUSE_NAME_MAX 1024
@@ -131,8 +131,8 @@ struct fuse_conn;
  * A request to the client
  */
 struct fuse_req {
-       /** This can be on either unused_list, pending processing or
-           io lists in fuse_conn */
+       /** This can be on either pending processing or io lists in
+           fuse_conn */
        struct list_head list;
 
        /** Entry on the background list */
@@ -144,15 +144,12 @@ struct fuse_req {
        /*
         * The following bitfields are either set once before the
         * request is queued or setting/clearing them is protected by
-        * fuse_lock
+        * fuse_conn->lock
         */
 
        /** True if the request has reply */
        unsigned isreply:1;
 
-       /** The request is preallocated */
-       unsigned preallocated:1;
-
        /** The request was interrupted */
        unsigned interrupted:1;
 
@@ -162,6 +159,9 @@ struct fuse_req {
        /** Data is being copied to/from the request */
        unsigned locked:1;
 
+       /** Request is counted as "waiting" */
+       unsigned waiting:1;
+
        /** State of the request */
        enum fuse_req_state state;
 
@@ -213,6 +213,9 @@ struct fuse_req {
  * unmounted.
  */
 struct fuse_conn {
+       /** Lock protecting accessess to  members of this structure */
+       spinlock_t lock;
+
        /** The user id for this mount */
        uid_t user_id;
 
@@ -244,25 +247,20 @@ struct fuse_conn {
            interrupted request) */
        struct list_head background;
 
-       /** Controls the maximum number of outstanding requests */
-       struct semaphore outstanding_sem;
+       /** Number of requests currently in the background */
+       unsigned num_background;
 
-       /** This counts the number of outstanding requests if
-           outstanding_sem would go negative */
-       unsigned outstanding_debt;
+       /** Flag indicating if connection is blocked.  This will be
+           the case before the INIT reply is received, and if there
+           are too many outstading backgrounds requests */
+       int blocked;
 
-       /** RW semaphore for exclusion with fuse_put_super() */
-       struct rw_semaphore sbput_sem;
-
-       /** The list of unused requests */
-       struct list_head unused_list;
+       /** waitq for blocked connection */
+       wait_queue_head_t blocked_waitq;
 
        /** The next unique request id */
        u64 reqctr;
 
-       /** Mount is active */
-       unsigned mounted;
-
        /** Connection established, cleared on umount, connection
            abort and device release */
        unsigned connected;
@@ -318,6 +316,9 @@ struct fuse_conn {
 
        /** kobject */
        struct kobject kobj;
+
+       /** O_ASYNC requests */
+       struct fasync_struct *fasync;
 };
 
 static inline struct fuse_conn *get_fuse_conn_super(struct super_block *sb)
@@ -348,21 +349,6 @@ static inline u64 get_node_id(struct inode *inode)
 /** Device operations */
 extern const struct file_operations fuse_dev_operations;
 
-/**
- * This is the single global spinlock which protects FUSE's structures
- *
- * The following data is protected by this lock:
- *
- *  - the private_data field of the device file
- *  - the s_fs_info field of the super block
- *  - unused_list, pending, processing lists in fuse_conn
- *  - background list in fuse_conn
- *  - the unique request ID counter reqctr in fuse_conn
- *  - the sb (super_block) field in fuse_conn
- *  - the file (device file) field in fuse_conn
- */
-extern spinlock_t fuse_lock;
-
 /**
  * Get a filled in inode
  */
@@ -461,11 +447,11 @@ void fuse_reset_request(struct fuse_req *req);
 /**
  * Reserve a preallocated request
  */
-struct fuse_req *fuse_get_request(struct fuse_conn *fc);
+struct fuse_req *fuse_get_req(struct fuse_conn *fc);
 
 /**
- * Decrement reference count of a request.  If count goes to zero put
- * on unused list (preallocated) or free request (not preallocated).
+ * Decrement reference count of a request.  If count goes to zero free
+ * the request.
  */
 void fuse_put_request(struct fuse_conn *fc, struct fuse_req *req);
 
@@ -485,11 +471,11 @@ void request_send_noreply(struct fuse_conn *fc, struct fuse_req *req);
 void request_send_background(struct fuse_conn *fc, struct fuse_req *req);
 
 /**
- * Release inodes and file associated with background request
+ * Remove request from the the background list
  */
-void fuse_release_background(struct fuse_req *req);
+void fuse_remove_background(struct fuse_conn *fc, struct fuse_req *req);
 
-/* Abort all requests */
+/** Abort all requests */
 void fuse_abort_conn(struct fuse_conn *fc);
 
 /**
index 879e6fba94803eca6a1844d9d14d500116086ae7..43a6fc0db8a7ec981f73cd65a8c128a3fa68118a 100644 (file)
@@ -1,6 +1,6 @@
 /*
   FUSE: Filesystem in Userspace
-  Copyright (C) 2001-2005  Miklos Szeredi <miklos@szeredi.hu>
+  Copyright (C) 2001-2006  Miklos Szeredi <miklos@szeredi.hu>
 
   This program can be distributed under the terms of the GNU GPL.
   See the file COPYING.
@@ -22,7 +22,6 @@ MODULE_AUTHOR("Miklos Szeredi <miklos@szeredi.hu>");
 MODULE_DESCRIPTION("Filesystem in Userspace");
 MODULE_LICENSE("GPL");
 
-spinlock_t fuse_lock;
 static kmem_cache_t *fuse_inode_cachep;
 static struct subsystem connections_subsys;
 
@@ -205,17 +204,28 @@ static void fuse_put_super(struct super_block *sb)
 {
        struct fuse_conn *fc = get_fuse_conn_super(sb);
 
-       down_write(&fc->sbput_sem);
-       while (!list_empty(&fc->background))
-               fuse_release_background(list_entry(fc->background.next,
-                                                  struct fuse_req, bg_entry));
-
-       spin_lock(&fuse_lock);
-       fc->mounted = 0;
+       spin_lock(&fc->lock);
        fc->connected = 0;
-       spin_unlock(&fuse_lock);
-       up_write(&fc->sbput_sem);
+       while (!list_empty(&fc->background)) {
+               struct fuse_req *req = list_entry(fc->background.next,
+                                                 struct fuse_req, bg_entry);
+               struct inode *inode = req->inode;
+               struct inode *inode2 = req->inode2;
+
+               /* File would hold a reference to vfsmount */
+               BUG_ON(req->file);
+               req->inode = NULL;
+               req->inode2 = NULL;
+               fuse_remove_background(fc, req);
+
+               spin_unlock(&fc->lock);
+               iput(inode);
+               iput(inode2);
+               spin_lock(&fc->lock);
+       }
+       spin_unlock(&fc->lock);
        /* Flush all readers on this fs */
+       kill_fasync(&fc->fasync, SIGIO, POLL_IN);
        wake_up_all(&fc->waitq);
        kobject_del(&fc->kobj);
        kobject_put(&fc->kobj);
@@ -242,9 +252,9 @@ static int fuse_statfs(struct super_block *sb, struct kstatfs *buf)
        struct fuse_statfs_out outarg;
        int err;
 
-        req = fuse_get_request(fc);
-       if (!req)
-               return -EINTR;
+       req = fuse_get_req(fc);
+       if (IS_ERR(req))
+               return PTR_ERR(req);
 
        memset(&outarg, 0, sizeof(outarg));
        req->in.numargs = 0;
@@ -369,15 +379,7 @@ static int fuse_show_options(struct seq_file *m, struct vfsmount *mnt)
 
 static void fuse_conn_release(struct kobject *kobj)
 {
-       struct fuse_conn *fc = get_fuse_conn_kobj(kobj);
-
-       while (!list_empty(&fc->unused_list)) {
-               struct fuse_req *req;
-               req = list_entry(fc->unused_list.next, struct fuse_req, list);
-               list_del(&req->list);
-               fuse_request_free(req);
-       }
-       kfree(fc);
+       kfree(get_fuse_conn_kobj(kobj));
 }
 
 static struct fuse_conn *new_conn(void)
@@ -386,64 +388,24 @@ static struct fuse_conn *new_conn(void)
 
        fc = kzalloc(sizeof(*fc), GFP_KERNEL);
        if (fc) {
-               int i;
+               spin_lock_init(&fc->lock);
                init_waitqueue_head(&fc->waitq);
+               init_waitqueue_head(&fc->blocked_waitq);
                INIT_LIST_HEAD(&fc->pending);
                INIT_LIST_HEAD(&fc->processing);
                INIT_LIST_HEAD(&fc->io);
-               INIT_LIST_HEAD(&fc->unused_list);
                INIT_LIST_HEAD(&fc->background);
-               sema_init(&fc->outstanding_sem, 1); /* One for INIT */
-               init_rwsem(&fc->sbput_sem);
                kobj_set_kset_s(fc, connections_subsys);
                kobject_init(&fc->kobj);
                atomic_set(&fc->num_waiting, 0);
-               for (i = 0; i < FUSE_MAX_OUTSTANDING; i++) {
-                       struct fuse_req *req = fuse_request_alloc();
-                       if (!req) {
-                               kobject_put(&fc->kobj);
-                               return NULL;
-                       }
-                       list_add(&req->list, &fc->unused_list);
-               }
                fc->bdi.ra_pages = (VM_MAX_READAHEAD * 1024) / PAGE_CACHE_SIZE;
                fc->bdi.unplug_io_fn = default_unplug_io_fn;
                fc->reqctr = 0;
+               fc->blocked = 1;
        }
        return fc;
 }
 
-static struct fuse_conn *get_conn(struct file *file, struct super_block *sb)
-{
-       struct fuse_conn *fc;
-       int err;
-
-       err = -EINVAL;
-       if (file->f_op != &fuse_dev_operations)
-               goto out_err;
-
-       err = -ENOMEM;
-       fc = new_conn();
-       if (!fc)
-               goto out_err;
-
-       spin_lock(&fuse_lock);
-       err = -EINVAL;
-       if (file->private_data)
-               goto out_unlock;
-
-       kobject_get(&fc->kobj);
-       file->private_data = fc;
-       spin_unlock(&fuse_lock);
-       return fc;
-
- out_unlock:
-       spin_unlock(&fuse_lock);
-       kobject_put(&fc->kobj);
- out_err:
-       return ERR_PTR(err);
-}
-
 static struct inode *get_root_inode(struct super_block *sb, unsigned mode)
 {
        struct fuse_attr attr;
@@ -467,7 +429,6 @@ static struct super_operations fuse_super_operations = {
 
 static void process_init_reply(struct fuse_conn *fc, struct fuse_req *req)
 {
-       int i;
        struct fuse_init_out *arg = &req->misc.init_out;
 
        if (req->out.h.error || arg->major != FUSE_KERNEL_VERSION)
@@ -486,22 +447,13 @@ static void process_init_reply(struct fuse_conn *fc, struct fuse_req *req)
                fc->minor = arg->minor;
                fc->max_write = arg->minor < 5 ? 4096 : arg->max_write;
        }
-
-       /* After INIT reply is received other requests can go
-          out.  So do (FUSE_MAX_OUTSTANDING - 1) number of
-          up()s on outstanding_sem.  The last up() is done in
-          fuse_putback_request() */
-       for (i = 1; i < FUSE_MAX_OUTSTANDING; i++)
-               up(&fc->outstanding_sem);
-
        fuse_put_request(fc, req);
+       fc->blocked = 0;
+       wake_up_all(&fc->blocked_waitq);
 }
 
-static void fuse_send_init(struct fuse_conn *fc)
+static void fuse_send_init(struct fuse_conn *fc, struct fuse_req *req)
 {
-       /* This is called from fuse_read_super() so there's guaranteed
-          to be exactly one request available */
-       struct fuse_req *req = fuse_get_request(fc);
        struct fuse_init_in *arg = &req->misc.init_in;
 
        arg->major = FUSE_KERNEL_VERSION;
@@ -525,12 +477,9 @@ static void fuse_send_init(struct fuse_conn *fc)
 
 static unsigned long long conn_id(void)
 {
+       /* BKL is held for ->get_sb() */
        static unsigned long long ctr = 1;
-       unsigned long long val;
-       spin_lock(&fuse_lock);
-       val = ctr++;
-       spin_unlock(&fuse_lock);
-       return val;
+       return ctr++;
 }
 
 static int fuse_fill_super(struct super_block *sb, void *data, int silent)
@@ -540,6 +489,7 @@ static int fuse_fill_super(struct super_block *sb, void *data, int silent)
        struct fuse_mount_data d;
        struct file *file;
        struct dentry *root_dentry;
+       struct fuse_req *init_req;
        int err;
 
        if (!parse_fuse_opt((char *) data, &d))
@@ -555,10 +505,17 @@ static int fuse_fill_super(struct super_block *sb, void *data, int silent)
        if (!file)
                return -EINVAL;
 
-       fc = get_conn(file, sb);
-       fput(file);
-       if (IS_ERR(fc))
-               return PTR_ERR(fc);
+       if (file->f_op != &fuse_dev_operations)
+               return -EINVAL;
+
+       /* Setting file->private_data can't race with other mount()
+          instances, since BKL is held for ->get_sb() */
+       if (file->private_data)
+               return -EINVAL;
+
+       fc = new_conn();
+       if (!fc)
+               return -ENOMEM;
 
        fc->flags = d.flags;
        fc->user_id = d.user_id;
@@ -579,27 +536,39 @@ static int fuse_fill_super(struct super_block *sb, void *data, int silent)
                goto err;
        }
 
+       init_req = fuse_request_alloc();
+       if (!init_req)
+               goto err_put_root;
+
        err = kobject_set_name(&fc->kobj, "%llu", conn_id());
        if (err)
-               goto err_put_root;
+               goto err_free_req;
 
        err = kobject_add(&fc->kobj);
        if (err)
-               goto err_put_root;
+               goto err_free_req;
 
        sb->s_root = root_dentry;
-       spin_lock(&fuse_lock);
-       fc->mounted = 1;
        fc->connected = 1;
-       spin_unlock(&fuse_lock);
+       kobject_get(&fc->kobj);
+       file->private_data = fc;
+       /*
+        * atomic_dec_and_test() in fput() provides the necessary
+        * memory barrier for file->private_data to be visible on all
+        * CPUs after this
+        */
+       fput(file);
 
-       fuse_send_init(fc);
+       fuse_send_init(fc, init_req);
 
        return 0;
 
+ err_free_req:
+       fuse_request_free(init_req);
  err_put_root:
        dput(root_dentry);
  err:
+       fput(file);
        kobject_put(&fc->kobj);
        return err;
 }
@@ -753,7 +722,6 @@ static int __init fuse_init(void)
        printk("fuse init (API version %i.%i)\n",
               FUSE_KERNEL_VERSION, FUSE_KERNEL_MINOR_VERSION);
 
-       spin_lock_init(&fuse_lock);
        res = fuse_fs_init();
        if (res)
                goto err;
index 367c487c014b6f62db3c04811ad56e3bec4cc0df..1f50302849c53ce8c674fd71416777713de9009b 100644 (file)
@@ -538,7 +538,7 @@ void inotify_d_instantiate(struct dentry *entry, struct inode *inode)
        WARN_ON(entry->d_flags & DCACHE_INOTIFY_PARENT_WATCHED);
        spin_lock(&entry->d_lock);
        parent = entry->d_parent;
-       if (inotify_inode_watched(parent->d_inode))
+       if (parent->d_inode && inotify_inode_watched(parent->d_inode))
                entry->d_flags |= DCACHE_INOTIFY_PARENT_WATCHED;
        spin_unlock(&entry->d_lock);
 }
index d2b66bad7d50458a9725d9aa5eabb47b017932b0..3ef739120dff32b1a772514be25167e546b7d3af 100644 (file)
@@ -650,7 +650,7 @@ static void nlmsvc_grant_callback(struct rpc_task *task, void *data)
        svc_wake_up(block->b_daemon);
 }
 
-void nlmsvc_grant_release(void *data)
+static void nlmsvc_grant_release(void *data)
 {
        struct nlm_rqst         *call = data;
 
index dda83d6cd48b17934797de3f6c9f65c52662f859..efad798824dc19913b7aace09dbee47b8c6ca6a7 100644 (file)
@@ -2230,7 +2230,12 @@ void steal_locks(fl_owner_t from)
 
        lock_kernel();
        j = 0;
-       rcu_read_lock();
+
+       /*
+        * We are not taking a ref to the file structures, so
+        * we need to acquire ->file_lock.
+        */
+       spin_lock(&files->file_lock);
        fdt = files_fdtable(files);
        for (;;) {
                unsigned long set;
@@ -2248,7 +2253,7 @@ void steal_locks(fl_owner_t from)
                        set >>= 1;
                }
        }
-       rcu_read_unlock();
+       spin_unlock(&files->file_lock);
        unlock_kernel();
 }
 EXPORT_SYMBOL(steal_locks);
index bf478addb852b70c1ec036e33100f93031c5dc6b..2c5f1f80bdc28b868cb81aabecdae71bc9c6b480 100644 (file)
@@ -899,11 +899,13 @@ static int do_change_type(struct nameidata *nd, int flag)
 /*
  * do loopback mount.
  */
-static int do_loopback(struct nameidata *nd, char *old_name, int recurse)
+static int do_loopback(struct nameidata *nd, char *old_name, unsigned long flags, int mnt_flags)
 {
        struct nameidata old_nd;
        struct vfsmount *mnt = NULL;
+       int recurse = flags & MS_REC;
        int err = mount_is_safe(nd);
+
        if (err)
                return err;
        if (!old_name || !*old_name)
@@ -937,6 +939,7 @@ static int do_loopback(struct nameidata *nd, char *old_name, int recurse)
                spin_unlock(&vfsmount_lock);
                release_mounts(&umount_list);
        }
+       mnt->mnt_flags = mnt_flags;
 
 out:
        up_write(&namespace_sem);
@@ -1350,7 +1353,7 @@ long do_mount(char *dev_name, char *dir_name, char *type_page,
                retval = do_remount(&nd, flags & ~MS_REMOUNT, mnt_flags,
                                    data_page);
        else if (flags & MS_BIND)
-               retval = do_loopback(&nd, dev_name, flags & MS_REC);
+               retval = do_loopback(&nd, dev_name, flags, mnt_flags);
        else if (flags & (MS_SHARED | MS_PRIVATE | MS_SLAVE | MS_UNBINDABLE))
                retval = do_change_type(&nd, flags);
        else if (flags & MS_MOVE)
index a23f3489416709288655f80603337f91ea94e398..cae74dd4c7f51f6bd674c5e61bad36c415cb4460 100644 (file)
@@ -128,15 +128,14 @@ struct inode_operations nfs4_dir_inode_operations = {
 static int
 nfs_opendir(struct inode *inode, struct file *filp)
 {
-       int res = 0;
+       int res;
 
        dfprintk(VFS, "NFS: opendir(%s/%ld)\n",
                        inode->i_sb->s_id, inode->i_ino);
 
        lock_kernel();
        /* Call generic open code in order to cache credentials */
-       if (!res)
-               res = nfs_open(inode, filp);
+       res = nfs_open(inode, filp);
        unlock_kernel();
        return res;
 }
index 0f583cb16ddbc4bad0b48787a41160a6a5b8c148..3c72b0c072839383950c59955da28c6c098897bf 100644 (file)
@@ -112,10 +112,9 @@ static void nfs_direct_write_complete(struct nfs_direct_req *dreq, struct inode
  */
 ssize_t nfs_direct_IO(int rw, struct kiocb *iocb, const struct iovec *iov, loff_t pos, unsigned long nr_segs)
 {
-       struct dentry *dentry = iocb->ki_filp->f_dentry;
-
        dprintk("NFS: nfs_direct_IO (%s) off/no(%Ld/%lu) EINVAL\n",
-                       dentry->d_name.name, (long long) pos, nr_segs);
+                       iocb->ki_filp->f_dentry->d_name.name,
+                       (long long) pos, nr_segs);
 
        return -EINVAL;
 }
@@ -468,7 +467,6 @@ static const struct rpc_call_ops nfs_commit_direct_ops = {
 static void nfs_direct_commit_schedule(struct nfs_direct_req *dreq)
 {
        struct nfs_write_data *data = dreq->commit_data;
-       struct rpc_task *task = &data->task;
 
        data->inode = dreq->inode;
        data->cred = dreq->ctx->cred;
@@ -489,7 +487,7 @@ static void nfs_direct_commit_schedule(struct nfs_direct_req *dreq)
        /* Note: task.tk_ops->rpc_release will free dreq->commit_data */
        dreq->commit_data = NULL;
 
-       dprintk("NFS: %5u initiated commit call\n", task->tk_pid);
+       dprintk("NFS: %5u initiated commit call\n", data->task.tk_pid);
 
        lock_kernel();
        rpc_execute(&data->task);
index f1df2c8d92591e4fa1474d66ecda7f887868fd86..fade02c15e6ef11a8575e6381b6f10445a1de375 100644 (file)
@@ -534,10 +534,9 @@ static int nfs_lock(struct file *filp, int cmd, struct file_lock *fl)
  */
 static int nfs_flock(struct file *filp, int cmd, struct file_lock *fl)
 {
-       struct inode * inode = filp->f_mapping->host;
-
        dprintk("NFS: nfs_flock(f=%s/%ld, t=%x, fl=%x)\n",
-                       inode->i_sb->s_id, inode->i_ino,
+                       filp->f_dentry->d_inode->i_sb->s_id,
+                       filp->f_dentry->d_inode->i_ino,
                        fl->fl_type, fl->fl_flags);
 
        /*
index 2f7656b911b66df6f03a96561c2f03534ffa4241..d0b991a92327f32941a454865c6aed187523d52e 100644 (file)
@@ -700,12 +700,9 @@ static int nfs_show_stats(struct seq_file *m, struct vfsmount *mnt)
        /*
         * Display superblock I/O counters
         */
-       for (cpu = 0; cpu < NR_CPUS; cpu++) {
+       for_each_possible_cpu(cpu) {
                struct nfs_iostats *stats;
 
-               if (!cpu_possible(cpu))
-                       continue;
-
                preempt_disable();
                stats = per_cpu_ptr(nfss->io_stats, cpu);
 
index 47ece1dd3c6705fa12282b31354c5d1558228319..d86c0db7b1e82a03bd003bc54aca52385e2c1bb7 100644 (file)
@@ -1218,7 +1218,7 @@ out:
        return status;
 }
 
-static void nfs4_intent_set_file(struct nameidata *nd, struct dentry *dentry, struct nfs4_state *state)
+static int nfs4_intent_set_file(struct nameidata *nd, struct dentry *dentry, struct nfs4_state *state)
 {
        struct file *filp;
 
@@ -1227,8 +1227,10 @@ static void nfs4_intent_set_file(struct nameidata *nd, struct dentry *dentry, st
                struct nfs_open_context *ctx;
                ctx = (struct nfs_open_context *)filp->private_data;
                ctx->state = state;
-       } else
-               nfs4_close_state(state, nd->intent.open.flags);
+               return 0;
+       }
+       nfs4_close_state(state, nd->intent.open.flags);
+       return PTR_ERR(filp);
 }
 
 struct dentry *
@@ -1835,7 +1837,7 @@ nfs4_proc_create(struct inode *dir, struct dentry *dentry, struct iattr *sattr,
                        nfs_setattr_update_inode(state->inode, sattr);
        }
        if (status == 0 && nd != NULL && (nd->flags & LOOKUP_OPEN))
-               nfs4_intent_set_file(nd, dentry, state);
+               status = nfs4_intent_set_file(nd, dentry, state);
        else
                nfs4_close_state(state, flags);
 out:
index cfe9ce8816132373791a60e8be6e2ed1ed92f064..6e92b0fe5323483cd6ce3bd25fd6d5a211d9589b 100644 (file)
 
 int nfsd_setuser(struct svc_rqst *rqstp, struct svc_export *exp)
 {
-       struct svc_cred *cred = &rqstp->rq_cred;
+       struct svc_cred cred = rqstp->rq_cred;
        int i;
        int ret;
 
        if (exp->ex_flags & NFSEXP_ALLSQUASH) {
-               cred->cr_uid = exp->ex_anon_uid;
-               cred->cr_gid = exp->ex_anon_gid;
-               put_group_info(cred->cr_group_info);
-               cred->cr_group_info = groups_alloc(0);
+               cred.cr_uid = exp->ex_anon_uid;
+               cred.cr_gid = exp->ex_anon_gid;
+               cred.cr_group_info = groups_alloc(0);
        } else if (exp->ex_flags & NFSEXP_ROOTSQUASH) {
                struct group_info *gi;
-               if (!cred->cr_uid)
-                       cred->cr_uid = exp->ex_anon_uid;
-               if (!cred->cr_gid)
-                       cred->cr_gid = exp->ex_anon_gid;
-               gi = groups_alloc(cred->cr_group_info->ngroups);
+               if (!cred.cr_uid)
+                       cred.cr_uid = exp->ex_anon_uid;
+               if (!cred.cr_gid)
+                       cred.cr_gid = exp->ex_anon_gid;
+               gi = groups_alloc(cred.cr_group_info->ngroups);
                if (gi)
-                       for (i = 0; i < cred->cr_group_info->ngroups; i++) {
-                               if (!GROUP_AT(cred->cr_group_info, i))
+                       for (i = 0; i < cred.cr_group_info->ngroups; i++) {
+                               if (!GROUP_AT(cred.cr_group_info, i))
                                        GROUP_AT(gi, i) = exp->ex_anon_gid;
                                else
-                                       GROUP_AT(gi, i) = GROUP_AT(cred->cr_group_info, i);
+                                       GROUP_AT(gi, i) = GROUP_AT(cred.cr_group_info, i);
                        }
-               put_group_info(cred->cr_group_info);
-               cred->cr_group_info = gi;
-       }
+               cred.cr_group_info = gi;
+       } else
+               get_group_info(cred.cr_group_info);
 
-       if (cred->cr_uid != (uid_t) -1)
-               current->fsuid = cred->cr_uid;
+       if (cred.cr_uid != (uid_t) -1)
+               current->fsuid = cred.cr_uid;
        else
                current->fsuid = exp->ex_anon_uid;
-       if (cred->cr_gid != (gid_t) -1)
-               current->fsgid = cred->cr_gid;
+       if (cred.cr_gid != (gid_t) -1)
+               current->fsgid = cred.cr_gid;
        else
                current->fsgid = exp->ex_anon_gid;
 
-       if (!cred->cr_group_info)
+       if (!cred.cr_group_info)
                return -ENOMEM;
-       ret = set_current_groups(cred->cr_group_info);
-       if ((cred->cr_uid)) {
+       ret = set_current_groups(cred.cr_group_info);
+       put_group_info(cred.cr_group_info);
+       if ((cred.cr_uid)) {
                cap_t(current->cap_effective) &= ~CAP_NFSD_MASK;
        } else {
                cap_t(current->cap_effective) |= (CAP_NFSD_MASK &
index c340be0a3f59b1826ef724ac57176628d2812411..4e0578121d9a621f0d36737582140e4573c464db 100644 (file)
@@ -422,7 +422,7 @@ static int svc_export_parse(struct cache_detail *cd, char *mesg, int mlen)
        if ((len=qword_get(&mesg, buf, PAGE_SIZE)) <= 0)
                goto out;
        err = path_lookup(buf, 0, &nd);
-       if (err) goto out;
+       if (err) goto out_no_path;
 
        exp.h.flags = 0;
        exp.ex_client = dom;
@@ -475,6 +475,7 @@ static int svc_export_parse(struct cache_detail *cd, char *mesg, int mlen)
  out:
        if (nd.dentry)
                path_release(&nd);
+ out_no_path:
        if (dom)
                auth_domain_put(dom);
        kfree(buf);
index 6d2dfed1de087a7a9b53961698bf521a811a51ee..f61142afea4490f5ebe542fe7ff167bf15a9564b 100644 (file)
@@ -682,7 +682,7 @@ static struct svc_procedure         nfsd_procedures3[22] = {
   PROC(lookup,  dirop,         dirop,          fhandle2, RC_NOCACHE, ST+FH+pAT+pAT),
   PROC(access,  access,        access,         fhandle,  RC_NOCACHE, ST+pAT+1),
   PROC(readlink, readlink,     readlink,       fhandle,  RC_NOCACHE, ST+pAT+1+NFS3_MAXPATHLEN/4),
-  PROC(read,    read,          read,           fhandle,  RC_NOCACHE, ST+pAT+4+NFSSVC_MAXBLKSIZE),
+  PROC(read,    read,          read,           fhandle,  RC_NOCACHE, ST+pAT+4+NFSSVC_MAXBLKSIZE/4),
   PROC(write,   write,         write,          fhandle,  RC_REPLBUFF, ST+WC+4),
   PROC(create,  create,        create,         fhandle2, RC_REPLBUFF, ST+(1+FH+pAT)+WC),
   PROC(mkdir,   mkdir,         create,         fhandle2, RC_REPLBUFF, ST+(1+FH+pAT)+WC),
index 7391f4aabedb0bd07e78ef26e64689ef2503f97f..edb107e61b91d8583f18e1bc26fe8c63e066196a 100644 (file)
@@ -710,9 +710,9 @@ calculate_posix_ace_count(struct nfs4_acl *n4acl)
                /* Also, the remaining entries are for named users and
                 * groups, and come in threes (mask, allow, deny): */
                if (n4acl->naces < 7)
-                       return -1;
+                       return -EINVAL;
                if ((n4acl->naces - 7) % 3)
-                       return -1;
+                       return -EINVAL;
                return 4 + (n4acl->naces - 7)/3;
        }
 }
@@ -790,7 +790,7 @@ nfs4_acl_split(struct nfs4_acl *acl, struct nfs4_acl *dacl)
                        continue;
 
                error = nfs4_acl_add_ace(dacl, ace->type, ace->flag,
-                               ace->access_mask, ace->whotype, ace->who) == -1;
+                               ace->access_mask, ace->whotype, ace->who);
                if (error < 0)
                        goto out;
 
@@ -866,7 +866,7 @@ nfs4_acl_add_ace(struct nfs4_acl *acl, u32 type, u32 flag, u32 access_mask,
        struct nfs4_ace *ace;
 
        if ((ace = kmalloc(sizeof(*ace), GFP_KERNEL)) == NULL)
-               return -1;
+               return -ENOMEM;
 
        ace->type = type;
        ace->flag = flag;
index c872bd07fc105f976ec1fb7f97261864e1eafcc7..dbaf3f93f3283f45e431e788aa23733f5c34b8b3 100644 (file)
@@ -441,8 +441,9 @@ nfsd4_probe_callback(struct nfs4_client *clp)
                goto out_clnt;
        }
 
-       /* the task holds a reference to the nfs4_client struct */
        cb->cb_client = clnt;
+
+       /* the task holds a reference to the nfs4_client struct */
        atomic_inc(&clp->cl_count);
 
        msg.rpc_cred = nfsd4_lookupcred(clp,0);
@@ -460,13 +461,12 @@ nfsd4_probe_callback(struct nfs4_client *clp)
 out_rpciod:
        atomic_dec(&clp->cl_count);
        rpciod_down();
+       cb->cb_client = NULL;
 out_clnt:
        rpc_shutdown_client(clnt);
-       goto out_err;
 out_err:
        dprintk("NFSD: warning: no callback path to client %.*s\n",
                (int)clp->cl_name.len, clp->cl_name.data);
-       cb->cb_client = NULL;
 }
 
 static void
index 6d63f1d9e5f598bdf15f9f44173083622a53eea5..b0e095ea0c03c2111f331613b8749d5eebf8dc76 100644 (file)
@@ -288,8 +288,6 @@ nfsd4_putrootfh(struct svc_rqst *rqstp, struct svc_fh *current_fh)
        fh_put(current_fh);
        status = exp_pseudoroot(rqstp->rq_client, current_fh,
                              &rqstp->rq_chandle);
-       if (!status)
-               status = nfserrno(nfsd_setuser(rqstp, current_fh->fh_export));
        return status;
 }
 
@@ -975,7 +973,7 @@ struct nfsd4_voidargs { int dummy; };
  */
 static struct svc_procedure            nfsd_procedures4[2] = {
   PROC(null,    void,          void,           void,     RC_NOCACHE, 1),
-  PROC(compound, compound,     compound,       compound, RC_NOCACHE, NFSD_BUFSIZE)
+  PROC(compound, compound,     compound,       compound, RC_NOCACHE, NFSD_BUFSIZE/4)
 };
 
 struct svc_version     nfsd_version4 = {
index 47ec112b266cf7a7c819babd881eb5176b7b4364..96c7578cbe1e82c16d2b720ef4e25e91d546187f 100644 (file)
@@ -147,6 +147,42 @@ get_nfs4_file(struct nfs4_file *fi)
        kref_get(&fi->fi_ref);
 }
 
+static int num_delegations;
+
+/*
+ * Open owner state (share locks)
+ */
+
+/* hash tables for nfs4_stateowner */
+#define OWNER_HASH_BITS              8
+#define OWNER_HASH_SIZE             (1 << OWNER_HASH_BITS)
+#define OWNER_HASH_MASK             (OWNER_HASH_SIZE - 1)
+
+#define ownerid_hashval(id) \
+        ((id) & OWNER_HASH_MASK)
+#define ownerstr_hashval(clientid, ownername) \
+        (((clientid) + opaque_hashval((ownername.data), (ownername.len))) & OWNER_HASH_MASK)
+
+static struct list_head        ownerid_hashtbl[OWNER_HASH_SIZE];
+static struct list_head        ownerstr_hashtbl[OWNER_HASH_SIZE];
+
+/* hash table for nfs4_file */
+#define FILE_HASH_BITS                   8
+#define FILE_HASH_SIZE                  (1 << FILE_HASH_BITS)
+#define FILE_HASH_MASK                  (FILE_HASH_SIZE - 1)
+/* hash table for (open)nfs4_stateid */
+#define STATEID_HASH_BITS              10
+#define STATEID_HASH_SIZE              (1 << STATEID_HASH_BITS)
+#define STATEID_HASH_MASK              (STATEID_HASH_SIZE - 1)
+
+#define file_hashval(x) \
+        hash_ptr(x, FILE_HASH_BITS)
+#define stateid_hashval(owner_id, file_id)  \
+        (((owner_id) + (file_id)) & STATEID_HASH_MASK)
+
+static struct list_head file_hashtbl[FILE_HASH_SIZE];
+static struct list_head stateid_hashtbl[STATEID_HASH_SIZE];
+
 static struct nfs4_delegation *
 alloc_init_deleg(struct nfs4_client *clp, struct nfs4_stateid *stp, struct svc_fh *current_fh, u32 type)
 {
@@ -155,9 +191,12 @@ alloc_init_deleg(struct nfs4_client *clp, struct nfs4_stateid *stp, struct svc_f
        struct nfs4_callback *cb = &stp->st_stateowner->so_client->cl_callback;
 
        dprintk("NFSD alloc_init_deleg\n");
+       if (num_delegations > STATEID_HASH_SIZE * 4)
+               return NULL;
        dp = kmem_cache_alloc(deleg_slab, GFP_KERNEL);
        if (dp == NULL)
                return dp;
+       num_delegations++;
        INIT_LIST_HEAD(&dp->dl_perfile);
        INIT_LIST_HEAD(&dp->dl_perclnt);
        INIT_LIST_HEAD(&dp->dl_recall_lru);
@@ -192,6 +231,7 @@ nfs4_put_delegation(struct nfs4_delegation *dp)
                dprintk("NFSD: freeing dp %p\n",dp);
                put_nfs4_file(dp->dl_file);
                kmem_cache_free(deleg_slab, dp);
+               num_delegations--;
        }
 }
 
@@ -329,23 +369,30 @@ put_nfs4_client(struct nfs4_client *clp)
                free_client(clp);
 }
 
+static void
+shutdown_callback_client(struct nfs4_client *clp)
+{
+       struct rpc_clnt *clnt = clp->cl_callback.cb_client;
+
+       /* shutdown rpc client, ending any outstanding recall rpcs */
+       if (clnt) {
+               clp->cl_callback.cb_client = NULL;
+               rpc_shutdown_client(clnt);
+               rpciod_down();
+       }
+}
+
 static void
 expire_client(struct nfs4_client *clp)
 {
        struct nfs4_stateowner *sop;
        struct nfs4_delegation *dp;
-       struct nfs4_callback *cb = &clp->cl_callback;
-       struct rpc_clnt *clnt = clp->cl_callback.cb_client;
        struct list_head reaplist;
 
        dprintk("NFSD: expire_client cl_count %d\n",
                            atomic_read(&clp->cl_count));
 
-       /* shutdown rpc client, ending any outstanding recall rpcs */
-       if (atomic_read(&cb->cb_set) == 1 && clnt) {
-               rpc_shutdown_client(clnt);
-               clnt = clp->cl_callback.cb_client = NULL;
-       }
+       shutdown_callback_client(clp);
 
        INIT_LIST_HEAD(&reaplist);
        spin_lock(&recall_lock);
@@ -936,40 +983,6 @@ out:
        return status;
 }
 
-/* 
- * Open owner state (share locks)
- */
-
-/* hash tables for nfs4_stateowner */
-#define OWNER_HASH_BITS              8
-#define OWNER_HASH_SIZE             (1 << OWNER_HASH_BITS)
-#define OWNER_HASH_MASK             (OWNER_HASH_SIZE - 1)
-
-#define ownerid_hashval(id) \
-        ((id) & OWNER_HASH_MASK)
-#define ownerstr_hashval(clientid, ownername) \
-        (((clientid) + opaque_hashval((ownername.data), (ownername.len))) & OWNER_HASH_MASK)
-
-static struct list_head        ownerid_hashtbl[OWNER_HASH_SIZE];
-static struct list_head        ownerstr_hashtbl[OWNER_HASH_SIZE];
-
-/* hash table for nfs4_file */
-#define FILE_HASH_BITS                   8
-#define FILE_HASH_SIZE                  (1 << FILE_HASH_BITS)
-#define FILE_HASH_MASK                  (FILE_HASH_SIZE - 1)
-/* hash table for (open)nfs4_stateid */
-#define STATEID_HASH_BITS              10
-#define STATEID_HASH_SIZE              (1 << STATEID_HASH_BITS)
-#define STATEID_HASH_MASK              (STATEID_HASH_SIZE - 1)
-
-#define file_hashval(x) \
-        hash_ptr(x, FILE_HASH_BITS)
-#define stateid_hashval(owner_id, file_id)  \
-        (((owner_id) + (file_id)) & STATEID_HASH_MASK)
-
-static struct list_head file_hashtbl[FILE_HASH_SIZE];
-static struct list_head stateid_hashtbl[STATEID_HASH_SIZE];
-
 /* OPEN Share state helper functions */
 static inline struct nfs4_file *
 alloc_init_file(struct inode *ino)
@@ -1186,8 +1199,7 @@ move_to_close_lru(struct nfs4_stateowner *sop)
 {
        dprintk("NFSD: move_to_close_lru nfs4_stateowner %p\n", sop);
 
-       unhash_stateowner(sop);
-       list_add_tail(&sop->so_close_lru, &close_lru);
+       list_move_tail(&sop->so_close_lru, &close_lru);
        sop->so_time = get_seconds();
 }
 
@@ -1916,8 +1928,7 @@ nfs4_laundromat(void)
                }
                dprintk("NFSD: purging unused open stateowner (so_id %d)\n",
                        sop->so_id);
-               list_del(&sop->so_close_lru);
-               nfs4_put_stateowner(sop);
+               release_stateowner(sop);
        }
        if (clientid_val < NFSD_LAUNDROMAT_MINTIMEOUT)
                clientid_val = NFSD_LAUNDROMAT_MINTIMEOUT;
@@ -2495,36 +2506,27 @@ nfs4_transform_lock_offset(struct file_lock *lock)
                lock->fl_end = OFFSET_MAX;
 }
 
-static int
-nfs4_verify_lock_stateowner(struct nfs4_stateowner *sop, unsigned int hashval)
-{
-       struct nfs4_stateowner *local = NULL;
-       int status = 0;
-                               
-       if (hashval >= LOCK_HASH_SIZE)
-               goto out;
-       list_for_each_entry(local, &lock_ownerid_hashtbl[hashval], so_idhash) {
-               if (local == sop) {
-                       status = 1;
-                       goto out;
-               }
-       }
-out:
-       return status;
-}
-
+/* Hack!: For now, we're defining this just so we can use a pointer to it
+ * as a unique cookie to identify our (NFSv4's) posix locks. */
+static struct lock_manager_operations nfsd_posix_mng_ops  = {
+};
 
 static inline void
 nfs4_set_lock_denied(struct file_lock *fl, struct nfsd4_lock_denied *deny)
 {
-       struct nfs4_stateowner *sop = (struct nfs4_stateowner *) fl->fl_owner;
-       unsigned int hval = lockownerid_hashval(sop->so_id);
+       struct nfs4_stateowner *sop;
+       unsigned int hval;
 
-       deny->ld_sop = NULL;
-       if (nfs4_verify_lock_stateowner(sop, hval)) {
+       if (fl->fl_lmops == &nfsd_posix_mng_ops) {
+               sop = (struct nfs4_stateowner *) fl->fl_owner;
+               hval = lockownerid_hashval(sop->so_id);
                kref_get(&sop->so_ref);
                deny->ld_sop = sop;
                deny->ld_clientid = sop->so_client->cl_clientid;
+       } else {
+               deny->ld_sop = NULL;
+               deny->ld_clientid.cl_boot = 0;
+               deny->ld_clientid.cl_id = 0;
        }
        deny->ld_start = fl->fl_start;
        deny->ld_length = ~(u64)0;
@@ -2736,6 +2738,7 @@ nfsd4_lock(struct svc_rqst *rqstp, struct svc_fh *current_fh, struct nfsd4_lock
        file_lock.fl_pid = current->tgid;
        file_lock.fl_file = filp;
        file_lock.fl_flags = FL_POSIX;
+       file_lock.fl_lmops = &nfsd_posix_mng_ops;
 
        file_lock.fl_start = lock->lk_offset;
        if ((lock->lk_length == ~(u64)0) || 
@@ -2841,6 +2844,7 @@ nfsd4_lockt(struct svc_rqst *rqstp, struct svc_fh *current_fh, struct nfsd4_lock
                file_lock.fl_owner = (fl_owner_t)lockt->lt_stateowner;
        file_lock.fl_pid = current->tgid;
        file_lock.fl_flags = FL_POSIX;
+       file_lock.fl_lmops = &nfsd_posix_mng_ops;
 
        file_lock.fl_start = lockt->lt_offset;
        if ((lockt->lt_length == ~(u64)0) || LOFF_OVERFLOW(lockt->lt_offset, lockt->lt_length))
@@ -2900,6 +2904,7 @@ nfsd4_locku(struct svc_rqst *rqstp, struct svc_fh *current_fh, struct nfsd4_lock
        file_lock.fl_pid = current->tgid;
        file_lock.fl_file = filp;
        file_lock.fl_flags = FL_POSIX; 
+       file_lock.fl_lmops = &nfsd_posix_mng_ops;
        file_lock.fl_start = locku->lu_offset;
 
        if ((locku->lu_length == ~(u64)0) || LOFF_OVERFLOW(locku->lu_offset, locku->lu_length))
@@ -3211,15 +3216,8 @@ __nfs4_state_shutdown(void)
        int i;
        struct nfs4_client *clp = NULL;
        struct nfs4_delegation *dp = NULL;
-       struct nfs4_stateowner *sop = NULL;
        struct list_head *pos, *next, reaplist;
 
-       list_for_each_safe(pos, next, &close_lru) {
-               sop = list_entry(pos, struct nfs4_stateowner, so_close_lru);
-               list_del(&sop->so_close_lru);
-               nfs4_put_stateowner(sop);
-       }
-
        for (i = 0; i < CLIENT_HASH_SIZE; i++) {
                while (!list_empty(&conf_id_hashtbl[i])) {
                        clp = list_entry(conf_id_hashtbl[i].next, struct nfs4_client, cl_idhash);
@@ -3244,8 +3242,6 @@ __nfs4_state_shutdown(void)
        }
 
        cancel_delayed_work(&laundromat_work);
-       flush_workqueue(laundry_wq);
-       destroy_workqueue(laundry_wq);
        nfsd4_shutdown_recdir();
        nfs4_init = 0;
 }
@@ -3253,6 +3249,8 @@ __nfs4_state_shutdown(void)
 void
 nfs4_state_shutdown(void)
 {
+       cancel_rearming_delayed_workqueue(laundry_wq, &laundromat_work);
+       destroy_workqueue(laundry_wq);
        nfs4_lock_state();
        nfs4_release_reclaim();
        __nfs4_state_shutdown();
index 03857fd8112632a044ddab6d0a4ade576e762298..de3998f15f1017ea47c8976d474cf3afa03ed397 100644 (file)
@@ -299,11 +299,10 @@ nfsd4_decode_fattr(struct nfsd4_compoundargs *argp, u32 *bmval, struct iattr *ia
                                                buf, dummy32, &ace.who);
                        if (status)
                                goto out_nfserr;
-                       if (nfs4_acl_add_ace(*acl, ace.type, ace.flag,
-                                ace.access_mask, ace.whotype, ace.who) != 0) {
-                               status = -ENOMEM;
+                       status = nfs4_acl_add_ace(*acl, ace.type, ace.flag,
+                                ace.access_mask, ace.whotype, ace.who);
+                       if (status)
                                goto out_nfserr;
-                       }
                }
        } else
                *acl = NULL;
@@ -2085,27 +2084,20 @@ nfsd4_encode_read(struct nfsd4_compoundres *resp, int nfserr, struct nfsd4_read
        WRITE32(eof);
        WRITE32(maxcount);
        ADJUST_ARGS();
-       resp->xbuf->head[0].iov_len = ((char*)resp->p) - (char*)resp->xbuf->head[0].iov_base;
-
+       resp->xbuf->head[0].iov_len = (char*)p
+                                       - (char*)resp->xbuf->head[0].iov_base;
        resp->xbuf->page_len = maxcount;
 
-       /* read zero bytes -> don't set up tail */
-       if(!maxcount)
-               return 0;        
-
-       /* set up page for remaining responses */
-       svc_take_page(resp->rqstp);
-       resp->xbuf->tail[0].iov_base = 
-               page_address(resp->rqstp->rq_respages[resp->rqstp->rq_resused-1]);
-       resp->rqstp->rq_restailpage = resp->rqstp->rq_resused-1;
+       /* Use rest of head for padding and remaining ops: */
+       resp->rqstp->rq_restailpage = 0;
+       resp->xbuf->tail[0].iov_base = p;
        resp->xbuf->tail[0].iov_len = 0;
-       resp->p = resp->xbuf->tail[0].iov_base;
-       resp->end = resp->p + PAGE_SIZE/4;
-
        if (maxcount&3) {
-               *(resp->p)++ = 0;
+               RESERVE_SPACE(4);
+               WRITE32(0);
                resp->xbuf->tail[0].iov_base += maxcount&3;
                resp->xbuf->tail[0].iov_len = 4 - (maxcount&3);
+               ADJUST_ARGS();
        }
        return 0;
 }
@@ -2142,21 +2134,20 @@ nfsd4_encode_readlink(struct nfsd4_compoundres *resp, int nfserr, struct nfsd4_r
 
        WRITE32(maxcount);
        ADJUST_ARGS();
-       resp->xbuf->head[0].iov_len = ((char*)resp->p) - (char*)resp->xbuf->head[0].iov_base;
+       resp->xbuf->head[0].iov_len = (char*)p
+                               - (char*)resp->xbuf->head[0].iov_base;
+       resp->xbuf->page_len = maxcount;
 
-       svc_take_page(resp->rqstp);
-       resp->xbuf->tail[0].iov_base = 
-               page_address(resp->rqstp->rq_respages[resp->rqstp->rq_resused-1]);
-       resp->rqstp->rq_restailpage = resp->rqstp->rq_resused-1;
+       /* Use rest of head for padding and remaining ops: */
+       resp->rqstp->rq_restailpage = 0;
+       resp->xbuf->tail[0].iov_base = p;
        resp->xbuf->tail[0].iov_len = 0;
-       resp->p = resp->xbuf->tail[0].iov_base;
-       resp->end = resp->p + PAGE_SIZE/4;
-
-       resp->xbuf->page_len = maxcount;
        if (maxcount&3) {
-               *(resp->p)++ = 0;
+               RESERVE_SPACE(4);
+               WRITE32(0);
                resp->xbuf->tail[0].iov_base += maxcount&3;
                resp->xbuf->tail[0].iov_len = 4 - (maxcount&3);
+               ADJUST_ARGS();
        }
        return 0;
 }
@@ -2166,7 +2157,7 @@ nfsd4_encode_readdir(struct nfsd4_compoundres *resp, int nfserr, struct nfsd4_re
 {
        int maxcount;
        loff_t offset;
-       u32 *page, *savep;
+       u32 *page, *savep, *tailbase;
        ENCODE_HEAD;
 
        if (nfserr)
@@ -2182,6 +2173,7 @@ nfsd4_encode_readdir(struct nfsd4_compoundres *resp, int nfserr, struct nfsd4_re
        WRITE32(0);
        ADJUST_ARGS();
        resp->xbuf->head[0].iov_len = ((char*)resp->p) - (char*)resp->xbuf->head[0].iov_base;
+       tailbase = p;
 
        maxcount = PAGE_SIZE;
        if (maxcount > readdir->rd_maxcount)
@@ -2226,14 +2218,12 @@ nfsd4_encode_readdir(struct nfsd4_compoundres *resp, int nfserr, struct nfsd4_re
        *p++ = htonl(readdir->common.err == nfserr_eof);
        resp->xbuf->page_len = ((char*)p) - (char*)page_address(resp->rqstp->rq_respages[resp->rqstp->rq_resused-1]);
 
-       /* allocate a page for the tail */
-       svc_take_page(resp->rqstp);
-       resp->xbuf->tail[0].iov_base = 
-               page_address(resp->rqstp->rq_respages[resp->rqstp->rq_resused-1]);
-       resp->rqstp->rq_restailpage = resp->rqstp->rq_resused-1;
+       /* Use rest of head for padding and remaining ops: */
+       resp->rqstp->rq_restailpage = 0;
+       resp->xbuf->tail[0].iov_base = tailbase;
        resp->xbuf->tail[0].iov_len = 0;
        resp->p = resp->xbuf->tail[0].iov_base;
-       resp->end = resp->p + PAGE_SIZE/4;
+       resp->end = resp->p + (PAGE_SIZE - resp->xbuf->head[0].iov_len)/4;
 
        return 0;
 err_no_verf:
index 3e6b75cd90fd162093bceb4426f4f6bbdbf4e789..06cd0db0f32b306dd34dbf1462fdd74b63ecf38f 100644 (file)
@@ -553,7 +553,7 @@ static struct svc_procedure         nfsd_procedures2[18] = {
   PROC(none,    void,          void,           none,           RC_NOCACHE, ST),
   PROC(lookup,  diropargs,     diropres,       fhandle,        RC_NOCACHE, ST+FH+AT),
   PROC(readlink, readlinkargs, readlinkres,    none,           RC_NOCACHE, ST+1+NFS_MAXPATHLEN/4),
-  PROC(read,    readargs,      readres,        fhandle,        RC_NOCACHE, ST+AT+1+NFSSVC_MAXBLKSIZE),
+  PROC(read,    readargs,      readres,        fhandle,        RC_NOCACHE, ST+AT+1+NFSSVC_MAXBLKSIZE/4),
   PROC(none,    void,          void,           none,           RC_NOCACHE, ST),
   PROC(write,   writeargs,     attrstat,       fhandle,        RC_REPLBUFF, ST+AT),
   PROC(create,  createargs,    diropres,       fhandle,        RC_REPLBUFF, ST+FH+AT),
index 31018333dc383f58905f6348ac7a949de04849ca..6aa92d0e68764a7b4ef0ab7de0f34003570f71f8 100644 (file)
@@ -371,7 +371,6 @@ out_nfserr:
 static ssize_t nfsd_getxattr(struct dentry *dentry, char *key, void **buf)
 {
        ssize_t buflen;
-       int error;
 
        buflen = vfs_getxattr(dentry, key, NULL, 0);
        if (buflen <= 0)
@@ -381,10 +380,7 @@ static ssize_t nfsd_getxattr(struct dentry *dentry, char *key, void **buf)
        if (!*buf)
                return -ENOMEM;
 
-       error = vfs_getxattr(dentry, key, *buf, buflen);
-       if (error < 0)
-               return error;
-       return buflen;
+       return vfs_getxattr(dentry, key, *buf, buflen);
 }
 #endif
 
index bff0f0d06867f12c282111c948274a80bfc188c2..21f38accd0399dd26f6fa1da70af16209c01469e 100644 (file)
@@ -153,6 +153,7 @@ struct o2hb_region {
 struct o2hb_bio_wait_ctxt {
        atomic_t          wc_num_reqs;
        struct completion wc_io_complete;
+       int               wc_error;
 };
 
 static void o2hb_write_timeout(void *arg)
@@ -186,6 +187,7 @@ static inline void o2hb_bio_wait_init(struct o2hb_bio_wait_ctxt *wc,
 {
        atomic_set(&wc->wc_num_reqs, num_ios);
        init_completion(&wc->wc_io_complete);
+       wc->wc_error = 0;
 }
 
 /* Used in error paths too */
@@ -218,8 +220,10 @@ static int o2hb_bio_end_io(struct bio *bio,
 {
        struct o2hb_bio_wait_ctxt *wc = bio->bi_private;
 
-       if (error)
+       if (error) {
                mlog(ML_ERROR, "IO Error %d\n", error);
+               wc->wc_error = error;
+       }
 
        if (bio->bi_size)
                return 1;
@@ -390,6 +394,8 @@ static int o2hb_read_slots(struct o2hb_region *reg,
 
 bail_and_wait:
        o2hb_wait_on_io(reg, &wc);
+       if (wc.wc_error && !status)
+               status = wc.wc_error;
 
        if (bios) {
                for(i = 0; i < num_bios; i++)
@@ -790,20 +796,24 @@ static int o2hb_highest_node(unsigned long *nodes,
        return highest;
 }
 
-static void o2hb_do_disk_heartbeat(struct o2hb_region *reg)
+static int o2hb_do_disk_heartbeat(struct o2hb_region *reg)
 {
        int i, ret, highest_node, change = 0;
        unsigned long configured_nodes[BITS_TO_LONGS(O2NM_MAX_NODES)];
        struct bio *write_bio;
        struct o2hb_bio_wait_ctxt write_wc;
 
-       if (o2nm_configured_node_map(configured_nodes, sizeof(configured_nodes)))
-               return;
+       ret = o2nm_configured_node_map(configured_nodes,
+                                      sizeof(configured_nodes));
+       if (ret) {
+               mlog_errno(ret);
+               return ret;
+       }
 
        highest_node = o2hb_highest_node(configured_nodes, O2NM_MAX_NODES);
        if (highest_node >= O2NM_MAX_NODES) {
                mlog(ML_NOTICE, "ocfs2_heartbeat: no configured nodes found!\n");
-               return;
+               return -EINVAL;
        }
 
        /* No sense in reading the slots of nodes that don't exist
@@ -813,7 +823,7 @@ static void o2hb_do_disk_heartbeat(struct o2hb_region *reg)
        ret = o2hb_read_slots(reg, highest_node + 1);
        if (ret < 0) {
                mlog_errno(ret);
-               return;
+               return ret;
        }
 
        /* With an up to date view of the slots, we can check that no
@@ -831,7 +841,7 @@ static void o2hb_do_disk_heartbeat(struct o2hb_region *reg)
        ret = o2hb_issue_node_write(reg, &write_bio, &write_wc);
        if (ret < 0) {
                mlog_errno(ret);
-               return;
+               return ret;
        }
 
        i = -1;
@@ -847,6 +857,15 @@ static void o2hb_do_disk_heartbeat(struct o2hb_region *reg)
         */
        o2hb_wait_on_io(reg, &write_wc);
        bio_put(write_bio);
+       if (write_wc.wc_error) {
+               /* Do not re-arm the write timeout on I/O error - we
+                * can't be sure that the new block ever made it to
+                * disk */
+               mlog(ML_ERROR, "Write error %d on device \"%s\"\n",
+                    write_wc.wc_error, reg->hr_dev_name);
+               return write_wc.wc_error;
+       }
+
        o2hb_arm_write_timeout(reg);
 
        /* let the person who launched us know when things are steady */
@@ -854,6 +873,8 @@ static void o2hb_do_disk_heartbeat(struct o2hb_region *reg)
                if (atomic_dec_and_test(&reg->hr_steady_iterations))
                        wake_up(&o2hb_steady_queue);
        }
+
+       return 0;
 }
 
 /* Subtract b from a, storing the result in a. a *must* have a larger
@@ -913,7 +934,10 @@ static int o2hb_thread(void *data)
                 * likely to time itself out. */
                do_gettimeofday(&before_hb);
 
-               o2hb_do_disk_heartbeat(reg);
+               i = 0;
+               do {
+                       ret = o2hb_do_disk_heartbeat(reg);
+               } while (ret && ++i < 2);
 
                do_gettimeofday(&after_hb);
                elapsed_msec = o2hb_elapsed_msecs(&before_hb, &after_hb);
index c3764f4744ee60c9a7f6e6e2b11ff7c1fd9f48c4..74ca4e5f9765aba66cc342af3876731aba199428 100644 (file)
@@ -139,6 +139,10 @@ static void user_ast(void *opaque)
                return;
        }
 
+       mlog_bug_on_msg(lockres->l_requested == LKM_IVMODE,
+                       "Lockres %s, requested ivmode. flags 0x%x\n",
+                       lockres->l_name, lockres->l_flags);
+
        /* we're downconverting. */
        if (lockres->l_requested < lockres->l_level) {
                if (lockres->l_requested <=
@@ -229,23 +233,42 @@ static void user_unlock_ast(void *opaque, enum dlm_status status)
 
        mlog(0, "UNLOCK AST called on lock %s\n", lockres->l_name);
 
-       if (status != DLM_NORMAL)
+       if (status != DLM_NORMAL && status != DLM_CANCELGRANT)
                mlog(ML_ERROR, "Dlm returns status %d\n", status);
 
        spin_lock(&lockres->l_lock);
-       if (lockres->l_flags & USER_LOCK_IN_TEARDOWN)
+       /* The teardown flag gets set early during the unlock process,
+        * so test the cancel flag to make sure that this ast isn't
+        * for a concurrent cancel. */
+       if (lockres->l_flags & USER_LOCK_IN_TEARDOWN
+           && !(lockres->l_flags & USER_LOCK_IN_CANCEL)) {
                lockres->l_level = LKM_IVMODE;
-       else {
+       } else if (status == DLM_CANCELGRANT) {
+               mlog(0, "Lock %s, cancel fails, flags 0x%x\n",
+                    lockres->l_name, lockres->l_flags);
+               /* We tried to cancel a convert request, but it was
+                * already granted. Don't clear the busy flag - the
+                * ast should've done this already. */
+               BUG_ON(!(lockres->l_flags & USER_LOCK_IN_CANCEL));
+               lockres->l_flags &= ~USER_LOCK_IN_CANCEL;
+               goto out_noclear;
+       } else {
+               BUG_ON(!(lockres->l_flags & USER_LOCK_IN_CANCEL));
+               /* Cancel succeeded, we want to re-queue */
+               mlog(0, "Lock %s, cancel succeeds, flags 0x%x\n",
+                    lockres->l_name, lockres->l_flags);
                lockres->l_requested = LKM_IVMODE; /* cancel an
                                                    * upconvert
                                                    * request. */
                lockres->l_flags &= ~USER_LOCK_IN_CANCEL;
                /* we want the unblock thread to look at it again
                 * now. */
-               __user_dlm_queue_lockres(lockres);
+               if (lockres->l_flags & USER_LOCK_BLOCKED)
+                       __user_dlm_queue_lockres(lockres);
        }
 
        lockres->l_flags &= ~USER_LOCK_BUSY;
+out_noclear:
        spin_unlock(&lockres->l_lock);
 
        wake_up(&lockres->l_event);
@@ -268,13 +291,26 @@ static void user_dlm_unblock_lock(void *opaque)
 
        spin_lock(&lockres->l_lock);
 
-       BUG_ON(!(lockres->l_flags & USER_LOCK_BLOCKED));
-       BUG_ON(!(lockres->l_flags & USER_LOCK_QUEUED));
+       mlog_bug_on_msg(!(lockres->l_flags & USER_LOCK_QUEUED),
+                       "Lockres %s, flags 0x%x\n",
+                       lockres->l_name, lockres->l_flags);
 
-       /* notice that we don't clear USER_LOCK_BLOCKED here. That's
-        * for user_ast to do. */
+       /* notice that we don't clear USER_LOCK_BLOCKED here. If it's
+        * set, we want user_ast clear it. */
        lockres->l_flags &= ~USER_LOCK_QUEUED;
 
+       /* It's valid to get here and no longer be blocked - if we get
+        * several basts in a row, we might be queued by the first
+        * one, the unblock thread might run and clear the queued
+        * flag, and finally we might get another bast which re-queues
+        * us before our ast for the downconvert is called. */
+       if (!(lockres->l_flags & USER_LOCK_BLOCKED)) {
+               mlog(0, "Lockres %s, flags 0x%x: queued but not blocking\n",
+                       lockres->l_name, lockres->l_flags);
+               spin_unlock(&lockres->l_lock);
+               goto drop_ref;
+       }
+
        if (lockres->l_flags & USER_LOCK_IN_TEARDOWN) {
                mlog(0, "lock is in teardown so we do nothing\n");
                spin_unlock(&lockres->l_lock);
@@ -282,7 +318,9 @@ static void user_dlm_unblock_lock(void *opaque)
        }
 
        if (lockres->l_flags & USER_LOCK_BUSY) {
-               mlog(0, "BUSY flag detected...\n");
+               mlog(0, "Cancel lock %s, flags 0x%x\n",
+                    lockres->l_name, lockres->l_flags);
+
                if (lockres->l_flags & USER_LOCK_IN_CANCEL) {
                        spin_unlock(&lockres->l_lock);
                        goto drop_ref;
@@ -296,14 +334,7 @@ static void user_dlm_unblock_lock(void *opaque)
                                   LKM_CANCEL,
                                   user_unlock_ast,
                                   lockres);
-               if (status == DLM_CANCELGRANT) {
-                       /* If we got this, then the ast was fired
-                        * before we could cancel. We cleanup our
-                        * state, and restart the function. */
-                       spin_lock(&lockres->l_lock);
-                       lockres->l_flags &= ~USER_LOCK_IN_CANCEL;
-                       spin_unlock(&lockres->l_lock);
-               } else if (status != DLM_NORMAL)
+               if (status != DLM_NORMAL)
                        user_log_dlm_error("dlmunlock", status, lockres);
                goto drop_ref;
        }
@@ -581,6 +612,14 @@ int user_dlm_destroy_lock(struct user_lock_res *lockres)
        mlog(0, "asked to destroy %s\n", lockres->l_name);
 
        spin_lock(&lockres->l_lock);
+       if (lockres->l_flags & USER_LOCK_IN_TEARDOWN) {
+               mlog(0, "Lock is already torn down\n");
+               spin_unlock(&lockres->l_lock);
+               return 0;
+       }
+
+       lockres->l_flags |= USER_LOCK_IN_TEARDOWN;
+
        while (lockres->l_flags & USER_LOCK_BUSY) {
                spin_unlock(&lockres->l_lock);
 
@@ -606,7 +645,6 @@ int user_dlm_destroy_lock(struct user_lock_res *lockres)
 
        lockres->l_flags &= ~USER_LOCK_ATTACHED;
        lockres->l_flags |= USER_LOCK_BUSY;
-       lockres->l_flags |= USER_LOCK_IN_TEARDOWN;
        spin_unlock(&lockres->l_lock);
 
        mlog(0, "unlocking lockres %s\n", lockres->l_name);
index 34e903a6a46b22e42be625f060e28973b6d77801..581eb451a41a36796a2a2d55b7463028d4dae10e 100644 (file)
@@ -260,6 +260,17 @@ static int ocfs2_truncate_file(struct inode *inode,
        if (new_i_size == le64_to_cpu(fe->i_size))
                goto bail;
 
+       /* This forces other nodes to sync and drop their pages. Do
+        * this even if we have a truncate without allocation change -
+        * ocfs2 cluster sizes can be much greater than page size, so
+        * we have to truncate them anyway.  */
+       status = ocfs2_data_lock(inode, 1);
+       if (status < 0) {
+               mlog_errno(status);
+               goto bail;
+       }
+       ocfs2_data_unlock(inode, 1);
+
        if (le32_to_cpu(fe->i_clusters) ==
            ocfs2_clusters_for_bytes(osb->sb, new_i_size)) {
                mlog(0, "fe->i_clusters = %u, so we do a simple truncate\n",
@@ -272,14 +283,6 @@ static int ocfs2_truncate_file(struct inode *inode,
                goto bail;
        }
 
-       /* This forces other nodes to sync and drop their pages */
-       status = ocfs2_data_lock(inode, 1);
-       if (status < 0) {
-               mlog_errno(status);
-               goto bail;
-       }
-       ocfs2_data_unlock(inode, 1);
-
        /* alright, we're going to need to do a full blown alloc size
         * change. Orphan the inode so that recovery can complete the
         * truncate if necessary. This does the task of marking
index c32c89d6d8dbed71f831e94f8aa0c67eade8cfc1..53ec28c367770d5704ecdb24f7549470cb0ccf6a 100644 (file)
--- a/fs/open.c
+++ b/fs/open.c
@@ -331,7 +331,10 @@ out:
 
 asmlinkage long sys_ftruncate(unsigned int fd, unsigned long length)
 {
-       return do_sys_ftruncate(fd, length, 1);
+       long ret = do_sys_ftruncate(fd, length, 1);
+       /* avoid REGPARM breakage on x86: */
+       prevent_tail_call(ret);
+       return ret;
 }
 
 /* LFS versions of truncate are only needed on 32 bit machines */
@@ -343,7 +346,10 @@ asmlinkage long sys_truncate64(const char __user * path, loff_t length)
 
 asmlinkage long sys_ftruncate64(unsigned int fd, loff_t length)
 {
-       return do_sys_ftruncate(fd, length, 0);
+       long ret = do_sys_ftruncate(fd, length, 0);
+       /* avoid REGPARM breakage on x86: */
+       prevent_tail_call(ret);
+       return ret;
 }
 #endif
 
@@ -1093,20 +1099,30 @@ long do_sys_open(int dfd, const char __user *filename, int flags, int mode)
 
 asmlinkage long sys_open(const char __user *filename, int flags, int mode)
 {
+       long ret;
+
        if (force_o_largefile())
                flags |= O_LARGEFILE;
 
-       return do_sys_open(AT_FDCWD, filename, flags, mode);
+       ret = do_sys_open(AT_FDCWD, filename, flags, mode);
+       /* avoid REGPARM breakage on x86: */
+       prevent_tail_call(ret);
+       return ret;
 }
 EXPORT_SYMBOL_GPL(sys_open);
 
 asmlinkage long sys_openat(int dfd, const char __user *filename, int flags,
                           int mode)
 {
+       long ret;
+
        if (force_o_largefile())
                flags |= O_LARGEFILE;
 
-       return do_sys_open(dfd, filename, flags, mode);
+       ret = do_sys_open(dfd, filename, flags, mode);
+       /* avoid REGPARM breakage on x86: */
+       prevent_tail_call(ret);
+       return ret;
 }
 EXPORT_SYMBOL_GPL(sys_openat);
 
index af0cb4b9e784e21b5c0b38921728d8b1e0f069b5..45ae7dd3c650399baafe5c8d20cc3b6734181d7a 100644 (file)
@@ -331,7 +331,9 @@ void delete_partition(struct gendisk *disk, int part)
        devfs_remove("%s/part%d", disk->devfs_name, part);
        if (p->holder_dir)
                kobject_unregister(p->holder_dir);
-       kobject_unregister(&p->kobj);
+       kobject_uevent(&p->kobj, KOBJ_REMOVE);
+       kobject_del(&p->kobj);
+       kobject_put(&p->kobj);
 }
 
 void add_partition(struct gendisk *disk, int part, sector_t start, sector_t len)
@@ -357,7 +359,10 @@ void add_partition(struct gendisk *disk, int part, sector_t start, sector_t len)
                snprintf(p->kobj.name,KOBJ_NAME_LEN,"%s%d",disk->kobj.name,part);
        p->kobj.parent = &disk->kobj;
        p->kobj.ktype = &ktype_part;
-       kobject_register(&p->kobj);
+       kobject_init(&p->kobj);
+       kobject_add(&p->kobj);
+       if (!disk->part_uevent_suppress)
+               kobject_uevent(&p->kobj, KOBJ_ADD);
        partition_sysfs_add_subdir(p);
        disk->part[part-1] = p;
 }
@@ -367,6 +372,7 @@ static char *make_block_name(struct gendisk *disk)
        char *name;
        static char *block_str = "block:";
        int size;
+       char *s;
 
        size = strlen(block_str) + strlen(disk->disk_name) + 1;
        name = kmalloc(size, GFP_KERNEL);
@@ -374,6 +380,10 @@ static char *make_block_name(struct gendisk *disk)
                return NULL;
        strcpy(name, block_str);
        strcat(name, disk->disk_name);
+       /* ewww... some of these buggers have / in name... */
+       s = strchr(name, '/');
+       if (s)
+               *s = '!';
        return name;
 }
 
@@ -395,6 +405,8 @@ void register_disk(struct gendisk *disk)
 {
        struct block_device *bdev;
        char *s;
+       int i;
+       struct hd_struct *p;
        int err;
 
        strlcpy(disk->kobj.name,disk->disk_name,KOBJ_NAME_LEN);
@@ -406,13 +418,12 @@ void register_disk(struct gendisk *disk)
                return;
        disk_sysfs_symlinks(disk);
        disk_sysfs_add_subdirs(disk);
-       kobject_uevent(&disk->kobj, KOBJ_ADD);
 
        /* No minors to use for partitions */
        if (disk->minors == 1) {
                if (disk->devfs_name[0] != '\0')
                        devfs_add_disk(disk);
-               return;
+               goto exit;
        }
 
        /* always add handle for the whole disk */
@@ -420,16 +431,32 @@ void register_disk(struct gendisk *disk)
 
        /* No such device (e.g., media were just removed) */
        if (!get_capacity(disk))
-               return;
+               goto exit;
 
        bdev = bdget_disk(disk, 0);
        if (!bdev)
-               return;
+               goto exit;
 
+       /* scan partition table, but suppress uevents */
        bdev->bd_invalidated = 1;
-       if (blkdev_get(bdev, FMODE_READ, 0) < 0)
-               return;
+       disk->part_uevent_suppress = 1;
+       err = blkdev_get(bdev, FMODE_READ, 0);
+       disk->part_uevent_suppress = 0;
+       if (err < 0)
+               goto exit;
        blkdev_put(bdev);
+
+exit:
+       /* announce disk after possible partitions are already created */
+       kobject_uevent(&disk->kobj, KOBJ_ADD);
+
+       /* announce possible partitions */
+       for (i = 1; i < disk->minors; i++) {
+               p = disk->part[i-1];
+               if (!p || !p->nr_sects)
+                       continue;
+               kobject_uevent(&p->kobj, KOBJ_ADD);
+       }
 }
 
 int rescan_partitions(struct gendisk *disk, struct block_device *bdev)
index 795df987cd38bbbe773fcc029084c019c75e5d02..7fefb10db8d9d6ad2a187d3c352cd0557beb30f5 100644 (file)
--- a/fs/pipe.c
+++ b/fs/pipe.c
@@ -36,7 +36,7 @@
  */
 
 /* Drop the inode semaphore and wait for a pipe event, atomically */
-void pipe_wait(struct inode * inode)
+void pipe_wait(struct pipe_inode_info *pipe)
 {
        DEFINE_WAIT(wait);
 
@@ -44,11 +44,14 @@ void pipe_wait(struct inode * inode)
         * Pipes are system-local resources, so sleeping on them
         * is considered a noninteractive wait:
         */
-       prepare_to_wait(PIPE_WAIT(*inode), &wait, TASK_INTERRUPTIBLE|TASK_NONINTERACTIVE);
-       mutex_unlock(PIPE_MUTEX(*inode));
+       prepare_to_wait(&pipe->wait, &wait,
+                       TASK_INTERRUPTIBLE | TASK_NONINTERACTIVE);
+       if (pipe->inode)
+               mutex_unlock(&pipe->inode->i_mutex);
        schedule();
-       finish_wait(PIPE_WAIT(*inode), &wait);
-       mutex_lock(PIPE_MUTEX(*inode));
+       finish_wait(&pipe->wait, &wait);
+       if (pipe->inode)
+               mutex_lock(&pipe->inode->i_mutex);
 }
 
 static int
@@ -91,7 +94,8 @@ pipe_iov_copy_to_user(struct iovec *iov, const void *from, unsigned long len)
        return 0;
 }
 
-static void anon_pipe_buf_release(struct pipe_inode_info *info, struct pipe_buffer *buf)
+static void anon_pipe_buf_release(struct pipe_inode_info *pipe,
+                                 struct pipe_buffer *buf)
 {
        struct page *page = buf->page;
 
@@ -100,42 +104,46 @@ static void anon_pipe_buf_release(struct pipe_inode_info *info, struct pipe_buff
        /*
         * If nobody else uses this page, and we don't already have a
         * temporary page, let's keep track of it as a one-deep
-        * allocation cache
+        * allocation cache. (Otherwise just release our reference to it)
         */
-       if (page_count(page) == 1 && !info->tmp_page) {
-               info->tmp_page = page;
-               return;
-       }
-
-       /*
-        * Otherwise just release our reference to it
-        */
-       page_cache_release(page);
+       if (page_count(page) == 1 && !pipe->tmp_page)
+               pipe->tmp_page = page;
+       else
+               page_cache_release(page);
 }
 
-static void *anon_pipe_buf_map(struct file *file, struct pipe_inode_info *info, struct pipe_buffer *buf)
+static void * anon_pipe_buf_map(struct file *file, struct pipe_inode_info *pipe,
+                               struct pipe_buffer *buf)
 {
        return kmap(buf->page);
 }
 
-static void anon_pipe_buf_unmap(struct pipe_inode_info *info, struct pipe_buffer *buf)
+static void anon_pipe_buf_unmap(struct pipe_inode_info *pipe,
+                               struct pipe_buffer *buf)
 {
        kunmap(buf->page);
 }
 
-static int anon_pipe_buf_steal(struct pipe_inode_info *info,
+static int anon_pipe_buf_steal(struct pipe_inode_info *pipe,
                               struct pipe_buffer *buf)
 {
        buf->flags |= PIPE_BUF_FLAG_STOLEN;
        return 0;
 }
 
+static void anon_pipe_buf_get(struct pipe_inode_info *info,
+                             struct pipe_buffer *buf)
+{
+       page_cache_get(buf->page);
+}
+
 static struct pipe_buf_operations anon_pipe_buf_ops = {
        .can_merge = 1,
        .map = anon_pipe_buf_map,
        .unmap = anon_pipe_buf_unmap,
        .release = anon_pipe_buf_release,
        .steal = anon_pipe_buf_steal,
+       .get = anon_pipe_buf_get,
 };
 
 static ssize_t
@@ -143,7 +151,7 @@ pipe_readv(struct file *filp, const struct iovec *_iov,
           unsigned long nr_segs, loff_t *ppos)
 {
        struct inode *inode = filp->f_dentry->d_inode;
-       struct pipe_inode_info *info;
+       struct pipe_inode_info *pipe;
        int do_wakeup;
        ssize_t ret;
        struct iovec *iov = (struct iovec *)_iov;
@@ -156,13 +164,13 @@ pipe_readv(struct file *filp, const struct iovec *_iov,
 
        do_wakeup = 0;
        ret = 0;
-       mutex_lock(PIPE_MUTEX(*inode));
-       info = inode->i_pipe;
+       mutex_lock(&inode->i_mutex);
+       pipe = inode->i_pipe;
        for (;;) {
-               int bufs = info->nrbufs;
+               int bufs = pipe->nrbufs;
                if (bufs) {
-                       int curbuf = info->curbuf;
-                       struct pipe_buffer *buf = info->bufs + curbuf;
+                       int curbuf = pipe->curbuf;
+                       struct pipe_buffer *buf = pipe->bufs + curbuf;
                        struct pipe_buf_operations *ops = buf->ops;
                        void *addr;
                        size_t chars = buf->len;
@@ -171,16 +179,17 @@ pipe_readv(struct file *filp, const struct iovec *_iov,
                        if (chars > total_len)
                                chars = total_len;
 
-                       addr = ops->map(filp, info, buf);
+                       addr = ops->map(filp, pipe, buf);
                        if (IS_ERR(addr)) {
                                if (!ret)
                                        ret = PTR_ERR(addr);
                                break;
                        }
                        error = pipe_iov_copy_to_user(iov, addr + buf->offset, chars);
-                       ops->unmap(info, buf);
+                       ops->unmap(pipe, buf);
                        if (unlikely(error)) {
-                               if (!ret) ret = -EFAULT;
+                               if (!ret)
+                                       ret = -EFAULT;
                                break;
                        }
                        ret += chars;
@@ -188,10 +197,10 @@ pipe_readv(struct file *filp, const struct iovec *_iov,
                        buf->len -= chars;
                        if (!buf->len) {
                                buf->ops = NULL;
-                               ops->release(info, buf);
+                               ops->release(pipe, buf);
                                curbuf = (curbuf + 1) & (PIPE_BUFFERS-1);
-                               info->curbuf = curbuf;
-                               info->nrbufs = --bufs;
+                               pipe->curbuf = curbuf;
+                               pipe->nrbufs = --bufs;
                                do_wakeup = 1;
                        }
                        total_len -= chars;
@@ -200,9 +209,9 @@ pipe_readv(struct file *filp, const struct iovec *_iov,
                }
                if (bufs)       /* More to do? */
                        continue;
-               if (!PIPE_WRITERS(*inode))
+               if (!pipe->writers)
                        break;
-               if (!PIPE_WAITING_WRITERS(*inode)) {
+               if (!pipe->waiting_writers) {
                        /* syscall merging: Usually we must not sleep
                         * if O_NONBLOCK is set, or if we got some data.
                         * But if a writer sleeps in kernel space, then
@@ -216,20 +225,22 @@ pipe_readv(struct file *filp, const struct iovec *_iov,
                        }
                }
                if (signal_pending(current)) {
-                       if (!ret) ret = -ERESTARTSYS;
+                       if (!ret)
+                               ret = -ERESTARTSYS;
                        break;
                }
                if (do_wakeup) {
-                       wake_up_interruptible_sync(PIPE_WAIT(*inode));
-                       kill_fasync(PIPE_FASYNC_WRITERS(*inode), SIGIO, POLL_OUT);
+                       wake_up_interruptible_sync(&pipe->wait);
+                       kill_fasync(&pipe->fasync_writers, SIGIO, POLL_OUT);
                }
-               pipe_wait(inode);
+               pipe_wait(pipe);
        }
-       mutex_unlock(PIPE_MUTEX(*inode));
-       /* Signal writers asynchronously that there is more room.  */
+       mutex_unlock(&inode->i_mutex);
+
+       /* Signal writers asynchronously that there is more room. */
        if (do_wakeup) {
-               wake_up_interruptible(PIPE_WAIT(*inode));
-               kill_fasync(PIPE_FASYNC_WRITERS(*inode), SIGIO, POLL_OUT);
+               wake_up_interruptible(&pipe->wait);
+               kill_fasync(&pipe->fasync_writers, SIGIO, POLL_OUT);
        }
        if (ret > 0)
                file_accessed(filp);
@@ -240,6 +251,7 @@ static ssize_t
 pipe_read(struct file *filp, char __user *buf, size_t count, loff_t *ppos)
 {
        struct iovec iov = { .iov_base = buf, .iov_len = count };
+
        return pipe_readv(filp, &iov, 1, ppos);
 }
 
@@ -248,7 +260,7 @@ pipe_writev(struct file *filp, const struct iovec *_iov,
            unsigned long nr_segs, loff_t *ppos)
 {
        struct inode *inode = filp->f_dentry->d_inode;
-       struct pipe_inode_info *info;
+       struct pipe_inode_info *pipe;
        ssize_t ret;
        int do_wakeup;
        struct iovec *iov = (struct iovec *)_iov;
@@ -262,10 +274,10 @@ pipe_writev(struct file *filp, const struct iovec *_iov,
 
        do_wakeup = 0;
        ret = 0;
-       mutex_lock(PIPE_MUTEX(*inode));
-       info = inode->i_pipe;
+       mutex_lock(&inode->i_mutex);
+       pipe = inode->i_pipe;
 
-       if (!PIPE_READERS(*inode)) {
+       if (!pipe->readers) {
                send_sig(SIGPIPE, current, 0);
                ret = -EPIPE;
                goto out;
@@ -273,23 +285,25 @@ pipe_writev(struct file *filp, const struct iovec *_iov,
 
        /* We try to merge small writes */
        chars = total_len & (PAGE_SIZE-1); /* size of the last buffer */
-       if (info->nrbufs && chars != 0) {
-               int lastbuf = (info->curbuf + info->nrbufs - 1) & (PIPE_BUFFERS-1);
-               struct pipe_buffer *buf = info->bufs + lastbuf;
+       if (pipe->nrbufs && chars != 0) {
+               int lastbuf = (pipe->curbuf + pipe->nrbufs - 1) &
+                                                       (PIPE_BUFFERS-1);
+               struct pipe_buffer *buf = pipe->bufs + lastbuf;
                struct pipe_buf_operations *ops = buf->ops;
                int offset = buf->offset + buf->len;
+
                if (ops->can_merge && offset + chars <= PAGE_SIZE) {
                        void *addr;
                        int error;
 
-                       addr = ops->map(filp, info, buf);
+                       addr = ops->map(filp, pipe, buf);
                        if (IS_ERR(addr)) {
                                error = PTR_ERR(addr);
                                goto out;
                        }
                        error = pipe_iov_copy_from_user(offset + addr, iov,
                                                        chars);
-                       ops->unmap(info, buf);
+                       ops->unmap(pipe, buf);
                        ret = error;
                        do_wakeup = 1;
                        if (error)
@@ -304,16 +318,18 @@ pipe_writev(struct file *filp, const struct iovec *_iov,
 
        for (;;) {
                int bufs;
-               if (!PIPE_READERS(*inode)) {
+
+               if (!pipe->readers) {
                        send_sig(SIGPIPE, current, 0);
-                       if (!ret) ret = -EPIPE;
+                       if (!ret)
+                               ret = -EPIPE;
                        break;
                }
-               bufs = info->nrbufs;
+               bufs = pipe->nrbufs;
                if (bufs < PIPE_BUFFERS) {
-                       int newbuf = (info->curbuf + bufs) & (PIPE_BUFFERS-1);
-                       struct pipe_buffer *buf = info->bufs + newbuf;
-                       struct page *page = info->tmp_page;
+                       int newbuf = (pipe->curbuf + bufs) & (PIPE_BUFFERS-1);
+                       struct pipe_buffer *buf = pipe->bufs + newbuf;
+                       struct page *page = pipe->tmp_page;
                        int error;
 
                        if (!page) {
@@ -322,9 +338,9 @@ pipe_writev(struct file *filp, const struct iovec *_iov,
                                        ret = ret ? : -ENOMEM;
                                        break;
                                }
-                               info->tmp_page = page;
+                               pipe->tmp_page = page;
                        }
-                       /* Always wakeup, even if the copy fails. Otherwise
+                       /* Always wake up, even if the copy fails. Otherwise
                         * we lock up (O_NONBLOCK-)readers that sleep due to
                         * syscall merging.
                         * FIXME! Is this really true?
@@ -337,7 +353,8 @@ pipe_writev(struct file *filp, const struct iovec *_iov,
                        error = pipe_iov_copy_from_user(kmap(page), iov, chars);
                        kunmap(page);
                        if (unlikely(error)) {
-                               if (!ret) ret = -EFAULT;
+                               if (!ret)
+                                       ret = -EFAULT;
                                break;
                        }
                        ret += chars;
@@ -347,8 +364,8 @@ pipe_writev(struct file *filp, const struct iovec *_iov,
                        buf->ops = &anon_pipe_buf_ops;
                        buf->offset = 0;
                        buf->len = chars;
-                       info->nrbufs = ++bufs;
-                       info->tmp_page = NULL;
+                       pipe->nrbufs = ++bufs;
+                       pipe->tmp_page = NULL;
 
                        total_len -= chars;
                        if (!total_len)
@@ -357,27 +374,29 @@ pipe_writev(struct file *filp, const struct iovec *_iov,
                if (bufs < PIPE_BUFFERS)
                        continue;
                if (filp->f_flags & O_NONBLOCK) {
-                       if (!ret) ret = -EAGAIN;
+                       if (!ret)
+                               ret = -EAGAIN;
                        break;
                }
                if (signal_pending(current)) {
-                       if (!ret) ret = -ERESTARTSYS;
+                       if (!ret)
+                               ret = -ERESTARTSYS;
                        break;
                }
                if (do_wakeup) {
-                       wake_up_interruptible_sync(PIPE_WAIT(*inode));
-                       kill_fasync(PIPE_FASYNC_READERS(*inode), SIGIO, POLL_IN);
+                       wake_up_interruptible_sync(&pipe->wait);
+                       kill_fasync(&pipe->fasync_readers, SIGIO, POLL_IN);
                        do_wakeup = 0;
                }
-               PIPE_WAITING_WRITERS(*inode)++;
-               pipe_wait(inode);
-               PIPE_WAITING_WRITERS(*inode)--;
+               pipe->waiting_writers++;
+               pipe_wait(pipe);
+               pipe->waiting_writers--;
        }
 out:
-       mutex_unlock(PIPE_MUTEX(*inode));
+       mutex_unlock(&inode->i_mutex);
        if (do_wakeup) {
-               wake_up_interruptible(PIPE_WAIT(*inode));
-               kill_fasync(PIPE_FASYNC_READERS(*inode), SIGIO, POLL_IN);
+               wake_up_interruptible(&pipe->wait);
+               kill_fasync(&pipe->fasync_readers, SIGIO, POLL_IN);
        }
        if (ret > 0)
                file_update_time(filp);
@@ -389,6 +408,7 @@ pipe_write(struct file *filp, const char __user *buf,
           size_t count, loff_t *ppos)
 {
        struct iovec iov = { .iov_base = (void __user *)buf, .iov_len = count };
+
        return pipe_writev(filp, &iov, 1, ppos);
 }
 
@@ -399,7 +419,8 @@ bad_pipe_r(struct file *filp, char __user *buf, size_t count, loff_t *ppos)
 }
 
 static ssize_t
-bad_pipe_w(struct file *filp, const char __user *buf, size_t count, loff_t *ppos)
+bad_pipe_w(struct file *filp, const char __user *buf, size_t count,
+          loff_t *ppos)
 {
        return -EBADF;
 }
@@ -409,21 +430,22 @@ pipe_ioctl(struct inode *pino, struct file *filp,
           unsigned int cmd, unsigned long arg)
 {
        struct inode *inode = filp->f_dentry->d_inode;
-       struct pipe_inode_info *info;
+       struct pipe_inode_info *pipe;
        int count, buf, nrbufs;
 
        switch (cmd) {
                case FIONREAD:
-                       mutex_lock(PIPE_MUTEX(*inode));
-                       info =  inode->i_pipe;
+                       mutex_lock(&inode->i_mutex);
+                       pipe = inode->i_pipe;
                        count = 0;
-                       buf = info->curbuf;
-                       nrbufs = info->nrbufs;
+                       buf = pipe->curbuf;
+                       nrbufs = pipe->nrbufs;
                        while (--nrbufs >= 0) {
-                               count += info->bufs[buf].len;
+                               count += pipe->bufs[buf].len;
                                buf = (buf+1) & (PIPE_BUFFERS-1);
                        }
-                       mutex_unlock(PIPE_MUTEX(*inode));
+                       mutex_unlock(&inode->i_mutex);
+
                        return put_user(count, (int __user *)arg);
                default:
                        return -EINVAL;
@@ -436,17 +458,17 @@ pipe_poll(struct file *filp, poll_table *wait)
 {
        unsigned int mask;
        struct inode *inode = filp->f_dentry->d_inode;
-       struct pipe_inode_info *info = inode->i_pipe;
+       struct pipe_inode_info *pipe = inode->i_pipe;
        int nrbufs;
 
-       poll_wait(filp, PIPE_WAIT(*inode), wait);
+       poll_wait(filp, &pipe->wait, wait);
 
        /* Reading only -- no need for acquiring the semaphore.  */
-       nrbufs = info->nrbufs;
+       nrbufs = pipe->nrbufs;
        mask = 0;
        if (filp->f_mode & FMODE_READ) {
                mask = (nrbufs > 0) ? POLLIN | POLLRDNORM : 0;
-               if (!PIPE_WRITERS(*inode) && filp->f_version != PIPE_WCOUNTER(*inode))
+               if (!pipe->writers && filp->f_version != pipe->w_counter)
                        mask |= POLLHUP;
        }
 
@@ -456,7 +478,7 @@ pipe_poll(struct file *filp, poll_table *wait)
                 * Most Unices do not set POLLERR for FIFOs but on Linux they
                 * behave exactly like pipes for poll().
                 */
-               if (!PIPE_READERS(*inode))
+               if (!pipe->readers)
                        mask |= POLLERR;
        }
 
@@ -466,17 +488,21 @@ pipe_poll(struct file *filp, poll_table *wait)
 static int
 pipe_release(struct inode *inode, int decr, int decw)
 {
-       mutex_lock(PIPE_MUTEX(*inode));
-       PIPE_READERS(*inode) -= decr;
-       PIPE_WRITERS(*inode) -= decw;
-       if (!PIPE_READERS(*inode) && !PIPE_WRITERS(*inode)) {
+       struct pipe_inode_info *pipe;
+
+       mutex_lock(&inode->i_mutex);
+       pipe = inode->i_pipe;
+       pipe->readers -= decr;
+       pipe->writers -= decw;
+
+       if (!pipe->readers && !pipe->writers) {
                free_pipe_info(inode);
        } else {
-               wake_up_interruptible(PIPE_WAIT(*inode));
-               kill_fasync(PIPE_FASYNC_READERS(*inode), SIGIO, POLL_IN);
-               kill_fasync(PIPE_FASYNC_WRITERS(*inode), SIGIO, POLL_OUT);
+               wake_up_interruptible(&pipe->wait);
+               kill_fasync(&pipe->fasync_readers, SIGIO, POLL_IN);
+               kill_fasync(&pipe->fasync_writers, SIGIO, POLL_OUT);
        }
-       mutex_unlock(PIPE_MUTEX(*inode));
+       mutex_unlock(&inode->i_mutex);
 
        return 0;
 }
@@ -487,9 +513,9 @@ pipe_read_fasync(int fd, struct file *filp, int on)
        struct inode *inode = filp->f_dentry->d_inode;
        int retval;
 
-       mutex_lock(PIPE_MUTEX(*inode));
-       retval = fasync_helper(fd, filp, on, PIPE_FASYNC_READERS(*inode));
-       mutex_unlock(PIPE_MUTEX(*inode));
+       mutex_lock(&inode->i_mutex);
+       retval = fasync_helper(fd, filp, on, &inode->i_pipe->fasync_readers);
+       mutex_unlock(&inode->i_mutex);
 
        if (retval < 0)
                return retval;
@@ -504,9 +530,9 @@ pipe_write_fasync(int fd, struct file *filp, int on)
        struct inode *inode = filp->f_dentry->d_inode;
        int retval;
 
-       mutex_lock(PIPE_MUTEX(*inode));
-       retval = fasync_helper(fd, filp, on, PIPE_FASYNC_WRITERS(*inode));
-       mutex_unlock(PIPE_MUTEX(*inode));
+       mutex_lock(&inode->i_mutex);
+       retval = fasync_helper(fd, filp, on, &inode->i_pipe->fasync_writers);
+       mutex_unlock(&inode->i_mutex);
 
        if (retval < 0)
                return retval;
@@ -519,16 +545,17 @@ static int
 pipe_rdwr_fasync(int fd, struct file *filp, int on)
 {
        struct inode *inode = filp->f_dentry->d_inode;
+       struct pipe_inode_info *pipe = inode->i_pipe;
        int retval;
 
-       mutex_lock(PIPE_MUTEX(*inode));
+       mutex_lock(&inode->i_mutex);
 
-       retval = fasync_helper(fd, filp, on, PIPE_FASYNC_READERS(*inode));
+       retval = fasync_helper(fd, filp, on, &pipe->fasync_readers);
 
        if (retval >= 0)
-               retval = fasync_helper(fd, filp, on, PIPE_FASYNC_WRITERS(*inode));
+               retval = fasync_helper(fd, filp, on, &pipe->fasync_writers);
 
-       mutex_unlock(PIPE_MUTEX(*inode));
+       mutex_unlock(&inode->i_mutex);
 
        if (retval < 0)
                return retval;
@@ -567,9 +594,9 @@ pipe_read_open(struct inode *inode, struct file *filp)
 {
        /* We could have perhaps used atomic_t, but this and friends
           below are the only places.  So it doesn't seem worthwhile.  */
-       mutex_lock(PIPE_MUTEX(*inode));
-       PIPE_READERS(*inode)++;
-       mutex_unlock(PIPE_MUTEX(*inode));
+       mutex_lock(&inode->i_mutex);
+       inode->i_pipe->readers++;
+       mutex_unlock(&inode->i_mutex);
 
        return 0;
 }
@@ -577,9 +604,9 @@ pipe_read_open(struct inode *inode, struct file *filp)
 static int
 pipe_write_open(struct inode *inode, struct file *filp)
 {
-       mutex_lock(PIPE_MUTEX(*inode));
-       PIPE_WRITERS(*inode)++;
-       mutex_unlock(PIPE_MUTEX(*inode));
+       mutex_lock(&inode->i_mutex);
+       inode->i_pipe->writers++;
+       mutex_unlock(&inode->i_mutex);
 
        return 0;
 }
@@ -587,12 +614,12 @@ pipe_write_open(struct inode *inode, struct file *filp)
 static int
 pipe_rdwr_open(struct inode *inode, struct file *filp)
 {
-       mutex_lock(PIPE_MUTEX(*inode));
+       mutex_lock(&inode->i_mutex);
        if (filp->f_mode & FMODE_READ)
-               PIPE_READERS(*inode)++;
+               inode->i_pipe->readers++;
        if (filp->f_mode & FMODE_WRITE)
-               PIPE_WRITERS(*inode)++;
-       mutex_unlock(PIPE_MUTEX(*inode));
+               inode->i_pipe->writers++;
+       mutex_unlock(&inode->i_mutex);
 
        return 0;
 }
@@ -675,37 +702,38 @@ static struct file_operations rdwr_pipe_fops = {
        .fasync         = pipe_rdwr_fasync,
 };
 
-void free_pipe_info(struct inode *inode)
+struct pipe_inode_info * alloc_pipe_info(struct inode *inode)
+{
+       struct pipe_inode_info *pipe;
+
+       pipe = kzalloc(sizeof(struct pipe_inode_info), GFP_KERNEL);
+       if (pipe) {
+               init_waitqueue_head(&pipe->wait);
+               pipe->r_counter = pipe->w_counter = 1;
+               pipe->inode = inode;
+       }
+
+       return pipe;
+}
+
+void __free_pipe_info(struct pipe_inode_info *pipe)
 {
        int i;
-       struct pipe_inode_info *info = inode->i_pipe;
 
-       inode->i_pipe = NULL;
        for (i = 0; i < PIPE_BUFFERS; i++) {
-               struct pipe_buffer *buf = info->bufs + i;
+               struct pipe_buffer *buf = pipe->bufs + i;
                if (buf->ops)
-                       buf->ops->release(info, buf);
+                       buf->ops->release(pipe, buf);
        }
-       if (info->tmp_page)
-               __free_page(info->tmp_page);
-       kfree(info);
+       if (pipe->tmp_page)
+               __free_page(pipe->tmp_page);
+       kfree(pipe);
 }
 
-struct inode* pipe_new(struct inode* inode)
+void free_pipe_info(struct inode *inode)
 {
-       struct pipe_inode_info *info;
-
-       info = kzalloc(sizeof(struct pipe_inode_info), GFP_KERNEL);
-       if (!info)
-               goto fail_page;
-       inode->i_pipe = info;
-
-       init_waitqueue_head(PIPE_WAIT(*inode));
-       PIPE_RCOUNTER(*inode) = PIPE_WCOUNTER(*inode) = 1;
-
-       return inode;
-fail_page:
-       return NULL;
+       __free_pipe_info(inode->i_pipe);
+       inode->i_pipe = NULL;
 }
 
 static struct vfsmount *pipe_mnt __read_mostly;
@@ -713,6 +741,7 @@ static int pipefs_delete_dentry(struct dentry *dentry)
 {
        return 1;
 }
+
 static struct dentry_operations pipefs_dentry_operations = {
        .d_delete       = pipefs_delete_dentry,
 };
@@ -720,13 +749,17 @@ static struct dentry_operations pipefs_dentry_operations = {
 static struct inode * get_pipe_inode(void)
 {
        struct inode *inode = new_inode(pipe_mnt->mnt_sb);
+       struct pipe_inode_info *pipe;
 
        if (!inode)
                goto fail_inode;
 
-       if(!pipe_new(inode))
+       pipe = alloc_pipe_info(inode);
+       if (!pipe)
                goto fail_iput;
-       PIPE_READERS(*inode) = PIPE_WRITERS(*inode) = 1;
+       inode->i_pipe = pipe;
+
+       pipe->readers = pipe->writers = 1;
        inode->i_fop = &rdwr_pipe_fops;
 
        /*
@@ -741,10 +774,12 @@ static struct inode * get_pipe_inode(void)
        inode->i_gid = current->fsgid;
        inode->i_atime = inode->i_mtime = inode->i_ctime = CURRENT_TIME;
        inode->i_blksize = PAGE_SIZE;
+
        return inode;
 
 fail_iput:
        iput(inode);
+
 fail_inode:
        return NULL;
 }
@@ -757,7 +792,7 @@ int do_pipe(int *fd)
        struct inode * inode;
        struct file *f1, *f2;
        int error;
-       int i,j;
+       int i, j;
 
        error = -ENFILE;
        f1 = get_empty_filp();
@@ -790,6 +825,7 @@ int do_pipe(int *fd)
        dentry = d_alloc(pipe_mnt->mnt_sb->s_root, &this);
        if (!dentry)
                goto close_f12_inode_i_j;
+
        dentry->d_op = &pipefs_dentry_operations;
        d_add(dentry, inode);
        f1->f_vfsmnt = f2->f_vfsmnt = mntget(mntget(pipe_mnt));
@@ -813,6 +849,7 @@ int do_pipe(int *fd)
        fd_install(j, f2);
        fd[0] = i;
        fd[1] = j;
+
        return 0;
 
 close_f12_inode_i_j:
@@ -837,8 +874,9 @@ no_files:
  * d_name - pipe: will go nicely and kill the special-casing in procfs.
  */
 
-static struct super_block *pipefs_get_sb(struct file_system_type *fs_type,
-       int flags, const char *dev_name, void *data)
+static struct super_block *
+pipefs_get_sb(struct file_system_type *fs_type, int flags,
+             const char *dev_name, void *data)
 {
        return get_sb_pseudo(fs_type, "pipe:", NULL, PIPEFS_MAGIC);
 }
@@ -852,6 +890,7 @@ static struct file_system_type pipe_fs_type = {
 static int __init init_pipe_fs(void)
 {
        int err = register_filesystem(&pipe_fs_type);
+
        if (!err) {
                pipe_mnt = kern_mount(&pipe_fs_type);
                if (IS_ERR(pipe_mnt)) {
index a3a3eecef68946110f8f2641959af78eff7be428..6cc77dc3f3ff79c49fa7d4ce89360b595995d839 100644 (file)
@@ -297,16 +297,20 @@ static int proc_fd_link(struct inode *inode, struct dentry **dentry, struct vfsm
 
        files = get_files_struct(task);
        if (files) {
-               rcu_read_lock();
+               /*
+                * We are not taking a ref to the file structure, so we must
+                * hold ->file_lock.
+                */
+               spin_lock(&files->file_lock);
                file = fcheck_files(files, fd);
                if (file) {
                        *mnt = mntget(file->f_vfsmnt);
                        *dentry = dget(file->f_dentry);
-                       rcu_read_unlock();
+                       spin_unlock(&files->file_lock);
                        put_files_struct(files);
                        return 0;
                }
-               rcu_read_unlock();
+               spin_unlock(&files->file_lock);
                put_files_struct(files);
        }
        return -ENOENT;
@@ -1523,7 +1527,12 @@ static struct dentry *proc_lookupfd(struct inode * dir, struct dentry * dentry,
        if (!files)
                goto out_unlock;
        inode->i_mode = S_IFLNK;
-       rcu_read_lock();
+
+       /*
+        * We are not taking a ref to the file structure, so we must
+        * hold ->file_lock.
+        */
+       spin_lock(&files->file_lock);
        file = fcheck_files(files, fd);
        if (!file)
                goto out_unlock2;
@@ -1531,7 +1540,7 @@ static struct dentry *proc_lookupfd(struct inode * dir, struct dentry * dentry,
                inode->i_mode |= S_IRUSR | S_IXUSR;
        if (file->f_mode & 2)
                inode->i_mode |= S_IWUSR | S_IXUSR;
-       rcu_read_unlock();
+       spin_unlock(&files->file_lock);
        put_files_struct(files);
        inode->i_op = &proc_pid_link_inode_operations;
        inode->i_size = 64;
@@ -1541,7 +1550,7 @@ static struct dentry *proc_lookupfd(struct inode * dir, struct dentry * dentry,
        return NULL;
 
 out_unlock2:
-       rcu_read_unlock();
+       spin_unlock(&files->file_lock);
        put_files_struct(files);
 out_unlock:
        iput(inode);
index 7efa73d44c9a5b6f61a7ee3bb4aa02ff885eebb1..20d4b2237fcefd482112a3752669fe87004884bf 100644 (file)
@@ -103,8 +103,8 @@ static ssize_t read_vmcore(struct file *file, char __user *buffer,
                                size_t buflen, loff_t *fpos)
 {
        ssize_t acc = 0, tmp;
-       size_t tsz, nr_bytes;
-       u64 start;
+       size_t tsz;
+       u64 start, nr_bytes;
        struct vmcore *curr_m = NULL;
 
        if (buflen == 0 || *fpos >= vmcore_size)
index 6256ca81a718673694249aa2bcc3f9dff6895bcf..5bc0e9234f9d7c5dd21b1e244127fece7bfa905c 100644 (file)
@@ -202,7 +202,7 @@ int rw_verify_area(int read_write, struct file *file, loff_t *ppos, size_t count
                goto Einval;
 
        inode = file->f_dentry->d_inode;
-       if (inode->i_flock && MANDATORY_LOCK(inode)) {
+       if (unlikely(inode->i_flock && MANDATORY_LOCK(inode))) {
                int retval = locks_mandatory_area(
                        read_write == READ ? FLOCK_VERIFY_READ : FLOCK_VERIFY_WRITE,
                        inode, file, pos, count);
index 071660fa7b01e06d9717f6ac14ce2410414dbf91..a8109baa5e46429a894664eba4bfe1ce25f4b89b 100644 (file)
@@ -310,8 +310,9 @@ static int core_sys_select(int n, fd_set __user *inp, fd_set __user *outp,
                           fd_set __user *exp, s64 *timeout)
 {
        fd_set_bits fds;
-       char *bits;
-       int ret, size, max_fdset;
+       void *bits;
+       int ret, max_fdset;
+       unsigned int size;
        struct fdtable *fdt;
        /* Allocate small arguments on the stack to save memory and be faster */
        long stack_fds[SELECT_STACK_ALLOC/sizeof(long)];
@@ -333,20 +334,21 @@ static int core_sys_select(int n, fd_set __user *inp, fd_set __user *outp,
         * since we used fdset we need to allocate memory in units of
         * long-words. 
         */
-       ret = -ENOMEM;
        size = FDS_BYTES(n);
-       if (6*size < SELECT_STACK_ALLOC)
-               bits = stack_fds;
-       else
+       bits = stack_fds;
+       if (size > sizeof(stack_fds) / 6) {
+               /* Not enough space in on-stack array; must use kmalloc */
+               ret = -ENOMEM;
                bits = kmalloc(6 * size, GFP_KERNEL);
-       if (!bits)
-               goto out_nofds;
-       fds.in      = (unsigned long *)  bits;
-       fds.out     = (unsigned long *) (bits +   size);
-       fds.ex      = (unsigned long *) (bits + 2*size);
-       fds.res_in  = (unsigned long *) (bits + 3*size);
-       fds.res_out = (unsigned long *) (bits + 4*size);
-       fds.res_ex  = (unsigned long *) (bits + 5*size);
+               if (!bits)
+                       goto out_nofds;
+       }
+       fds.in      = bits;
+       fds.out     = bits +   size;
+       fds.ex      = bits + 2*size;
+       fds.res_in  = bits + 3*size;
+       fds.res_out = bits + 4*size;
+       fds.res_ex  = bits + 5*size;
 
        if ((ret = get_fd_set(n, inp, fds.in)) ||
            (ret = get_fd_set(n, outp, fds.out)) ||
index bfa42a277bb874ac94a34db4d3c7f593afc5410c..0559e7577a04164ececffdcdbd57089d980dd586 100644 (file)
@@ -9,11 +9,12 @@
  * that transfers data buffers to or from a pipe buffer.
  *
  * Named by Larry McVoy, original implementation from Linus, extended by
- * Jens to support splicing to files and fixing the initial implementation
- * bugs.
+ * Jens to support splicing to files, network, direct splicing, etc and
+ * fixing lots of bugs.
  *
- * Copyright (C) 2005 Jens Axboe <axboe@suse.de>
- * Copyright (C) 2005 Linus Torvalds <torvalds@osdl.org>
+ * Copyright (C) 2005-2006 Jens Axboe <axboe@suse.de>
+ * Copyright (C) 2005-2006 Linus Torvalds <torvalds@osdl.org>
+ * Copyright (C) 2006 Ingo Molnar <mingo@elte.hu>
  *
  */
 #include <linux/fs.h>
@@ -49,7 +50,8 @@ static int page_cache_pipe_buf_steal(struct pipe_inode_info *info,
        struct page *page = buf->page;
        struct address_space *mapping = page_mapping(page);
 
-       WARN_ON(!PageLocked(page));
+       lock_page(page);
+
        WARN_ON(!PageUptodate(page));
 
        /*
@@ -64,8 +66,10 @@ static int page_cache_pipe_buf_steal(struct pipe_inode_info *info,
        if (PagePrivate(page))
                try_to_release_page(page, mapping_gfp_mask(mapping));
 
-       if (!remove_mapping(mapping, page))
+       if (!remove_mapping(mapping, page)) {
+               unlock_page(page);
                return 1;
+       }
 
        buf->flags |= PIPE_BUF_FLAG_STOLEN | PIPE_BUF_FLAG_LRU;
        return 0;
@@ -84,69 +88,89 @@ static void *page_cache_pipe_buf_map(struct file *file,
                                     struct pipe_buffer *buf)
 {
        struct page *page = buf->page;
-
-       lock_page(page);
+       int err;
 
        if (!PageUptodate(page)) {
-               unlock_page(page);
-               return ERR_PTR(-EIO);
-       }
+               lock_page(page);
 
-       if (!page->mapping) {
+               /*
+                * Page got truncated/unhashed. This will cause a 0-byte
+                * splice, if this is the first page.
+                */
+               if (!page->mapping) {
+                       err = -ENODATA;
+                       goto error;
+               }
+
+               /*
+                * Uh oh, read-error from disk.
+                */
+               if (!PageUptodate(page)) {
+                       err = -EIO;
+                       goto error;
+               }
+
+               /*
+                * Page is ok afterall, fall through to mapping.
+                */
                unlock_page(page);
-               return ERR_PTR(-ENODATA);
        }
 
-       return kmap(buf->page);
+       return kmap(page);
+error:
+       unlock_page(page);
+       return ERR_PTR(err);
 }
 
 static void page_cache_pipe_buf_unmap(struct pipe_inode_info *info,
                                      struct pipe_buffer *buf)
 {
-       unlock_page(buf->page);
        kunmap(buf->page);
 }
 
+static void page_cache_pipe_buf_get(struct pipe_inode_info *info,
+                                   struct pipe_buffer *buf)
+{
+       page_cache_get(buf->page);
+}
+
 static struct pipe_buf_operations page_cache_pipe_buf_ops = {
        .can_merge = 0,
        .map = page_cache_pipe_buf_map,
        .unmap = page_cache_pipe_buf_unmap,
        .release = page_cache_pipe_buf_release,
        .steal = page_cache_pipe_buf_steal,
+       .get = page_cache_pipe_buf_get,
 };
 
 /*
  * Pipe output worker. This sets up our pipe format with the page cache
  * pipe buffer operations. Otherwise very similar to the regular pipe_writev().
  */
-static ssize_t move_to_pipe(struct inode *inode, struct page **pages,
-                           int nr_pages, unsigned long offset,
-                           unsigned long len, unsigned int flags)
+static ssize_t move_to_pipe(struct pipe_inode_info *pipe, struct page **pages,
+                           int nr_pages, unsigned long len,
+                           unsigned int offset, unsigned int flags)
 {
-       struct pipe_inode_info *info;
        int ret, do_wakeup, i;
 
        ret = 0;
        do_wakeup = 0;
        i = 0;
 
-       mutex_lock(PIPE_MUTEX(*inode));
+       if (pipe->inode)
+               mutex_lock(&pipe->inode->i_mutex);
 
-       info = inode->i_pipe;
        for (;;) {
-               int bufs;
-
-               if (!PIPE_READERS(*inode)) {
+               if (!pipe->readers) {
                        send_sig(SIGPIPE, current, 0);
                        if (!ret)
                                ret = -EPIPE;
                        break;
                }
 
-               bufs = info->nrbufs;
-               if (bufs < PIPE_BUFFERS) {
-                       int newbuf = (info->curbuf + bufs) & (PIPE_BUFFERS - 1);
-                       struct pipe_buffer *buf = info->bufs + newbuf;
+               if (pipe->nrbufs < PIPE_BUFFERS) {
+                       int newbuf = (pipe->curbuf + pipe->nrbufs) & (PIPE_BUFFERS - 1);
+                       struct pipe_buffer *buf = pipe->bufs + newbuf;
                        struct page *page = pages[i++];
                        unsigned long this_len;
 
@@ -158,8 +182,9 @@ static ssize_t move_to_pipe(struct inode *inode, struct page **pages,
                        buf->offset = offset;
                        buf->len = this_len;
                        buf->ops = &page_cache_pipe_buf_ops;
-                       info->nrbufs = ++bufs;
-                       do_wakeup = 1;
+                       pipe->nrbufs++;
+                       if (pipe->inode)
+                               do_wakeup = 1;
 
                        ret += this_len;
                        len -= this_len;
@@ -168,7 +193,7 @@ static ssize_t move_to_pipe(struct inode *inode, struct page **pages,
                                break;
                        if (!len)
                                break;
-                       if (bufs < PIPE_BUFFERS)
+                       if (pipe->nrbufs < PIPE_BUFFERS)
                                continue;
 
                        break;
@@ -187,22 +212,26 @@ static ssize_t move_to_pipe(struct inode *inode, struct page **pages,
                }
 
                if (do_wakeup) {
-                       wake_up_interruptible_sync(PIPE_WAIT(*inode));
-                       kill_fasync(PIPE_FASYNC_READERS(*inode), SIGIO,
-                                   POLL_IN);
+                       smp_mb();
+                       if (waitqueue_active(&pipe->wait))
+                               wake_up_interruptible_sync(&pipe->wait);
+                       kill_fasync(&pipe->fasync_readers, SIGIO, POLL_IN);
                        do_wakeup = 0;
                }
 
-               PIPE_WAITING_WRITERS(*inode)++;
-               pipe_wait(inode);
-               PIPE_WAITING_WRITERS(*inode)--;
+               pipe->waiting_writers++;
+               pipe_wait(pipe);
+               pipe->waiting_writers--;
        }
 
-       mutex_unlock(PIPE_MUTEX(*inode));
+       if (pipe->inode)
+               mutex_unlock(&pipe->inode->i_mutex);
 
        if (do_wakeup) {
-               wake_up_interruptible(PIPE_WAIT(*inode));
-               kill_fasync(PIPE_FASYNC_READERS(*inode), SIGIO, POLL_IN);
+               smp_mb();
+               if (waitqueue_active(&pipe->wait))
+                       wake_up_interruptible(&pipe->wait);
+               kill_fasync(&pipe->fasync_readers, SIGIO, POLL_IN);
        }
 
        while (i < nr_pages)
@@ -211,96 +240,155 @@ static ssize_t move_to_pipe(struct inode *inode, struct page **pages,
        return ret;
 }
 
-static int __generic_file_splice_read(struct file *in, struct inode *pipe,
-                                     size_t len, unsigned int flags)
+static int
+__generic_file_splice_read(struct file *in, loff_t *ppos,
+                          struct pipe_inode_info *pipe, size_t len,
+                          unsigned int flags)
 {
        struct address_space *mapping = in->f_mapping;
-       unsigned int offset, nr_pages;
-       struct page *pages[PIPE_BUFFERS], *shadow[PIPE_BUFFERS];
+       unsigned int loff, offset, nr_pages;
+       struct page *pages[PIPE_BUFFERS];
        struct page *page;
-       pgoff_t index, pidx;
-       int i, j;
+       pgoff_t index, end_index;
+       loff_t isize;
+       size_t bytes;
+       int i, error;
 
-       index = in->f_pos >> PAGE_CACHE_SHIFT;
-       offset = in->f_pos & ~PAGE_CACHE_MASK;
+       index = *ppos >> PAGE_CACHE_SHIFT;
+       loff = offset = *ppos & ~PAGE_CACHE_MASK;
        nr_pages = (len + offset + PAGE_CACHE_SIZE - 1) >> PAGE_CACHE_SHIFT;
 
        if (nr_pages > PIPE_BUFFERS)
                nr_pages = PIPE_BUFFERS;
 
        /*
-        * initiate read-ahead on this page range
+        * Initiate read-ahead on this page range. however, don't call into
+        * read-ahead if this is a non-zero offset (we are likely doing small
+        * chunk splice and the page is already there) for a single page.
         */
-       do_page_cache_readahead(mapping, in, index, nr_pages);
+       if (!offset || nr_pages > 1)
+               do_page_cache_readahead(mapping, in, index, nr_pages);
 
        /*
-        * Get as many pages from the page cache as possible..
-        * Start IO on the page cache entries we create (we
-        * can assume that any pre-existing ones we find have
-        * already had IO started on them).
+        * Now fill in the holes:
         */
-       i = find_get_pages(mapping, index, nr_pages, pages);
+       error = 0;
+       bytes = 0;
+       for (i = 0; i < nr_pages; i++, index++) {
+               unsigned int this_len;
 
-       /*
-        * common case - we found all pages and they are contiguous,
-        * kick them off
-        */
-       if (i && (pages[i - 1]->index == index + i - 1))
-               goto splice_them;
+               if (!len)
+                       break;
 
-       /*
-        * fill shadow[] with pages at the right locations, so we only
-        * have to fill holes
-        */
-       memset(shadow, 0, nr_pages * sizeof(struct page *));
-       for (j = 0; j < i; j++)
-               shadow[pages[j]->index - index] = pages[j];
+               /*
+                * this_len is the max we'll use from this page
+                */
+               this_len = min(len, PAGE_CACHE_SIZE - loff);
+find_page:
+               /*
+                * lookup the page for this index
+                */
+               page = find_get_page(mapping, index);
+               if (!page) {
+                       /*
+                        * page didn't exist, allocate one
+                        */
+                       page = page_cache_alloc_cold(mapping);
+                       if (!page)
+                               break;
 
-       /*
-        * now fill in the holes
-        */
-       for (i = 0, pidx = index; i < nr_pages; pidx++, i++) {
-               int error;
+                       error = add_to_page_cache_lru(page, mapping, index,
+                                               mapping_gfp_mask(mapping));
+                       if (unlikely(error)) {
+                               page_cache_release(page);
+                               break;
+                       }
 
-               if (shadow[i])
-                       continue;
+                       goto readpage;
+               }
 
                /*
-                * no page there, look one up / create it
+                * If the page isn't uptodate, we may need to start io on it
                 */
-               page = find_or_create_page(mapping, pidx,
-                                                  mapping_gfp_mask(mapping));
-               if (!page)
-                       break;
+               if (!PageUptodate(page)) {
+                       /*
+                        * If in nonblock mode then dont block on waiting
+                        * for an in-flight io page
+                        */
+                       if (flags & SPLICE_F_NONBLOCK)
+                               break;
+
+                       lock_page(page);
+
+                       /*
+                        * page was truncated, stop here. if this isn't the
+                        * first page, we'll just complete what we already
+                        * added
+                        */
+                       if (!page->mapping) {
+                               unlock_page(page);
+                               page_cache_release(page);
+                               break;
+                       }
+                       /*
+                        * page was already under io and is now done, great
+                        */
+                       if (PageUptodate(page)) {
+                               unlock_page(page);
+                               goto fill_it;
+                       }
 
-               if (PageUptodate(page))
-                       unlock_page(page);
-               else {
+readpage:
+                       /*
+                        * need to read in the page
+                        */
                        error = mapping->a_ops->readpage(in, page);
 
                        if (unlikely(error)) {
                                page_cache_release(page);
+                               if (error == AOP_TRUNCATED_PAGE)
+                                       goto find_page;
                                break;
                        }
-               }
-               shadow[i] = page;
-       }
 
-       if (!i) {
-               for (i = 0; i < nr_pages; i++) {
-                        if (shadow[i])
-                               page_cache_release(shadow[i]);
+                       /*
+                        * i_size must be checked after ->readpage().
+                        */
+                       isize = i_size_read(mapping->host);
+                       end_index = (isize - 1) >> PAGE_CACHE_SHIFT;
+                       if (unlikely(!isize || index > end_index)) {
+                               page_cache_release(page);
+                               break;
+                       }
+
+                       /*
+                        * if this is the last page, see if we need to shrink
+                        * the length and stop
+                        */
+                       if (end_index == index) {
+                               loff = PAGE_CACHE_SIZE - (isize & ~PAGE_CACHE_MASK);
+                               if (bytes + loff > isize) {
+                                       page_cache_release(page);
+                                       break;
+                               }
+                               /*
+                                * force quit after adding this page
+                                */
+                               nr_pages = i;
+                               this_len = min(this_len, loff);
+                       }
                }
-               return 0;
+fill_it:
+               pages[i] = page;
+               bytes += this_len;
+               len -= this_len;
+               loff = 0;
        }
 
-       memcpy(pages, shadow, i * sizeof(struct page *));
+       if (i)
+               return move_to_pipe(pipe, pages, i, bytes, offset, flags);
 
-       /*
-        * Now we splice them into the pipe..
-        */
-splice_them:
-       return move_to_pipe(pipe, pages, i, offset, len, flags);
+       return error;
 }
 
 /**
@@ -311,30 +399,34 @@ splice_them:
  * @flags:     splice modifier flags
  *
  * Will read pages from given file and fill them into a pipe.
- *
  */
-ssize_t generic_file_splice_read(struct file *in, struct inode *pipe,
-                                size_t len, unsigned int flags)
+ssize_t generic_file_splice_read(struct file *in, loff_t *ppos,
+                                struct pipe_inode_info *pipe, size_t len,
+                                unsigned int flags)
 {
        ssize_t spliced;
        int ret;
 
        ret = 0;
        spliced = 0;
+
        while (len) {
-               ret = __generic_file_splice_read(in, pipe, len, flags);
+               ret = __generic_file_splice_read(in, ppos, pipe, len, flags);
 
-               if (ret <= 0)
+               if (ret < 0)
                        break;
+               else if (!ret) {
+                       if (spliced)
+                               break;
+                       if (flags & SPLICE_F_NONBLOCK) {
+                               ret = -EAGAIN;
+                               break;
+                       }
+               }
 
-               in->f_pos += ret;
+               *ppos += ret;
                len -= ret;
                spliced += ret;
-
-               if (!(flags & SPLICE_F_NONBLOCK))
-                       continue;
-               ret = -EAGAIN;
-               break;
        }
 
        if (spliced)
@@ -360,10 +452,10 @@ static int pipe_to_sendpage(struct pipe_inode_info *info,
        int more;
 
        /*
-        * sub-optimal, but we are limited by the pipe ->map. we don't
+        * Sub-optimal, but we are limited by the pipe ->map. We don't
         * need a kmap'ed buffer here, we just want to make sure we
         * have the page pinned if the pipe page originates from the
-        * page cache
+        * page cache.
         */
        ptr = buf->ops->map(file, info, buf);
        if (IS_ERR(ptr))
@@ -414,7 +506,7 @@ static int pipe_to_file(struct pipe_inode_info *info, struct pipe_buffer *buf,
        int ret;
 
        /*
-        * after this, page will be locked and unmapped
+        * make sure the data in this buffer is uptodate
         */
        src = buf->ops->map(file, info, buf);
        if (IS_ERR(src))
@@ -424,12 +516,13 @@ static int pipe_to_file(struct pipe_inode_info *info, struct pipe_buffer *buf,
        offset = sd->pos & ~PAGE_CACHE_MASK;
 
        /*
-        * reuse buf page, if SPLICE_F_MOVE is set
+        * Reuse buf page, if SPLICE_F_MOVE is set.
         */
        if (sd->flags & SPLICE_F_MOVE) {
                /*
                 * If steal succeeds, buf->page is now pruned from the vm
-                * side (LRU and page cache) and we can reuse it.
+                * side (LRU and page cache) and we can reuse it. The page
+                * will also be looked on successful return.
                 */
                if (buf->ops->steal(info, buf))
                        goto find_page;
@@ -442,15 +535,27 @@ static int pipe_to_file(struct pipe_inode_info *info, struct pipe_buffer *buf,
                        lru_cache_add(page);
        } else {
 find_page:
-               ret = -ENOMEM;
-               page = find_or_create_page(mapping, index, gfp_mask);
-               if (!page)
-                       goto out;
+               page = find_lock_page(mapping, index);
+               if (!page) {
+                       ret = -ENOMEM;
+                       page = page_cache_alloc_cold(mapping);
+                       if (unlikely(!page))
+                               goto out_nomem;
+
+                       /*
+                        * This will also lock the page
+                        */
+                       ret = add_to_page_cache_lru(page, mapping, index,
+                                                   gfp_mask);
+                       if (unlikely(ret))
+                               goto out;
+               }
 
                /*
-                * If the page is uptodate, it is also locked. If it isn't
-                * uptodate, we can mark it uptodate if we are filling the
-                * full page. Otherwise we need to read it in first...
+                * We get here with the page locked. If the page is also
+                * uptodate, we don't need to do more. If it isn't, we
+                * may need to bring it in if we are not going to overwrite
+                * the full page.
                 */
                if (!PageUptodate(page)) {
                        if (sd->len < PAGE_CACHE_SIZE) {
@@ -462,7 +567,7 @@ find_page:
 
                                if (!PageUptodate(page)) {
                                        /*
-                                        * page got invalidated, repeat
+                                        * Page got invalidated, repeat.
                                         */
                                        if (!page->mapping) {
                                                unlock_page(page);
@@ -472,10 +577,8 @@ find_page:
                                        ret = -EIO;
                                        goto out;
                                }
-                       } else {
-                               WARN_ON(!PageLocked(page));
+                       } else
                                SetPageUptodate(page);
-                       }
                }
        }
 
@@ -501,12 +604,14 @@ find_page:
        } else if (ret)
                goto out;
 
+       mark_page_accessed(page);
        balance_dirty_pages_ratelimited(mapping);
 out:
-       if (!(buf->flags & PIPE_BUF_FLAG_STOLEN)) {
+       if (!(buf->flags & PIPE_BUF_FLAG_STOLEN))
                page_cache_release(page);
-               unlock_page(page);
-       }
+
+       unlock_page(page);
+out_nomem:
        buf->ops->unmap(info, buf);
        return ret;
 }
@@ -519,11 +624,10 @@ typedef int (splice_actor)(struct pipe_inode_info *, struct pipe_buffer *,
  * key here is the 'actor' worker passed in that actually moves the data
  * to the wanted destination. See pipe_to_file/pipe_to_sendpage above.
  */
-static ssize_t move_from_pipe(struct inode *inode, struct file *out,
-                             size_t len, unsigned int flags,
+static ssize_t move_from_pipe(struct pipe_inode_info *pipe, struct file *out,
+                             loff_t *ppos, size_t len, unsigned int flags,
                              splice_actor *actor)
 {
-       struct pipe_inode_info *info;
        int ret, do_wakeup, err;
        struct splice_desc sd;
 
@@ -533,24 +637,21 @@ static ssize_t move_from_pipe(struct inode *inode, struct file *out,
        sd.total_len = len;
        sd.flags = flags;
        sd.file = out;
-       sd.pos = out->f_pos;
+       sd.pos = *ppos;
 
-       mutex_lock(PIPE_MUTEX(*inode));
+       if (pipe->inode)
+               mutex_lock(&pipe->inode->i_mutex);
 
-       info = inode->i_pipe;
        for (;;) {
-               int bufs = info->nrbufs;
-
-               if (bufs) {
-                       int curbuf = info->curbuf;
-                       struct pipe_buffer *buf = info->bufs + curbuf;
+               if (pipe->nrbufs) {
+                       struct pipe_buffer *buf = pipe->bufs + pipe->curbuf;
                        struct pipe_buf_operations *ops = buf->ops;
 
                        sd.len = buf->len;
                        if (sd.len > sd.total_len)
                                sd.len = sd.total_len;
 
-                       err = actor(info, buf, &sd);
+                       err = actor(pipe, buf, &sd);
                        if (err) {
                                if (!ret && err != -ENODATA)
                                        ret = err;
@@ -561,13 +662,14 @@ static ssize_t move_from_pipe(struct inode *inode, struct file *out,
                        ret += sd.len;
                        buf->offset += sd.len;
                        buf->len -= sd.len;
+
                        if (!buf->len) {
                                buf->ops = NULL;
-                               ops->release(info, buf);
-                               curbuf = (curbuf + 1) & (PIPE_BUFFERS - 1);
-                               info->curbuf = curbuf;
-                               info->nrbufs = --bufs;
-                               do_wakeup = 1;
+                               ops->release(pipe, buf);
+                               pipe->curbuf = (pipe->curbuf + 1) & (PIPE_BUFFERS - 1);
+                               pipe->nrbufs--;
+                               if (pipe->inode)
+                                       do_wakeup = 1;
                        }
 
                        sd.pos += sd.len;
@@ -576,11 +678,11 @@ static ssize_t move_from_pipe(struct inode *inode, struct file *out,
                                break;
                }
 
-               if (bufs)
+               if (pipe->nrbufs)
                        continue;
-               if (!PIPE_WRITERS(*inode))
+               if (!pipe->writers)
                        break;
-               if (!PIPE_WAITING_WRITERS(*inode)) {
+               if (!pipe->waiting_writers) {
                        if (ret)
                                break;
                }
@@ -598,31 +700,32 @@ static ssize_t move_from_pipe(struct inode *inode, struct file *out,
                }
 
                if (do_wakeup) {
-                       wake_up_interruptible_sync(PIPE_WAIT(*inode));
-                       kill_fasync(PIPE_FASYNC_WRITERS(*inode),SIGIO,POLL_OUT);
+                       smp_mb();
+                       if (waitqueue_active(&pipe->wait))
+                               wake_up_interruptible_sync(&pipe->wait);
+                       kill_fasync(&pipe->fasync_writers, SIGIO, POLL_OUT);
                        do_wakeup = 0;
                }
 
-               pipe_wait(inode);
+               pipe_wait(pipe);
        }
 
-       mutex_unlock(PIPE_MUTEX(*inode));
+       if (pipe->inode)
+               mutex_unlock(&pipe->inode->i_mutex);
 
        if (do_wakeup) {
-               wake_up_interruptible(PIPE_WAIT(*inode));
-               kill_fasync(PIPE_FASYNC_WRITERS(*inode), SIGIO, POLL_OUT);
+               smp_mb();
+               if (waitqueue_active(&pipe->wait))
+                       wake_up_interruptible(&pipe->wait);
+               kill_fasync(&pipe->fasync_writers, SIGIO, POLL_OUT);
        }
 
-       mutex_lock(&out->f_mapping->host->i_mutex);
-       out->f_pos = sd.pos;
-       mutex_unlock(&out->f_mapping->host->i_mutex);
        return ret;
-
 }
 
 /**
  * generic_file_splice_write - splice data from a pipe to a file
- * @inode:     pipe inode
+ * @pipe:      pipe info
  * @out:       file to write to
  * @len:       number of bytes to splice
  * @flags:     splice modifier flags
@@ -631,27 +734,34 @@ static ssize_t move_from_pipe(struct inode *inode, struct file *out,
  * the given pipe inode to the given file.
  *
  */
-ssize_t generic_file_splice_write(struct inode *inode, struct file *out,
-                                 size_t len, unsigned int flags)
+ssize_t
+generic_file_splice_write(struct pipe_inode_info *pipe, struct file *out,
+                         loff_t *ppos, size_t len, unsigned int flags)
 {
        struct address_space *mapping = out->f_mapping;
-       ssize_t ret = move_from_pipe(inode, out, len, flags, pipe_to_file);
+       ssize_t ret;
 
-       /*
-        * if file or inode is SYNC and we actually wrote some data, sync it
-        */
-       if (unlikely((out->f_flags & O_SYNC) || IS_SYNC(mapping->host))
-           && ret > 0) {
+       ret = move_from_pipe(pipe, out, ppos, len, flags, pipe_to_file);
+       if (ret > 0) {
                struct inode *inode = mapping->host;
-               int err;
 
-               mutex_lock(&inode->i_mutex);
-               err = generic_osync_inode(mapping->host, mapping,
-                                               OSYNC_METADATA|OSYNC_DATA);
-               mutex_unlock(&inode->i_mutex);
+               *ppos += ret;
+
+               /*
+                * If file or inode is SYNC and we actually wrote some data,
+                * sync it.
+                */
+               if (unlikely((out->f_flags & O_SYNC) || IS_SYNC(inode))) {
+                       int err;
+
+                       mutex_lock(&inode->i_mutex);
+                       err = generic_osync_inode(inode, mapping,
+                                                 OSYNC_METADATA|OSYNC_DATA);
+                       mutex_unlock(&inode->i_mutex);
 
-               if (err)
-                       ret = err;
+                       if (err)
+                               ret = err;
+               }
        }
 
        return ret;
@@ -670,10 +780,10 @@ EXPORT_SYMBOL(generic_file_splice_write);
  * is involved.
  *
  */
-ssize_t generic_splice_sendpage(struct inode *inode, struct file *out,
-                               size_t len, unsigned int flags)
+ssize_t generic_splice_sendpage(struct pipe_inode_info *pipe, struct file *out,
+                               loff_t *ppos, size_t len, unsigned int flags)
 {
-       return move_from_pipe(inode, out, len, flags, pipe_to_sendpage);
+       return move_from_pipe(pipe, out, ppos, len, flags, pipe_to_sendpage);
 }
 
 EXPORT_SYMBOL(generic_splice_sendpage);
@@ -681,77 +791,228 @@ EXPORT_SYMBOL(generic_splice_sendpage);
 /*
  * Attempt to initiate a splice from pipe to file.
  */
-static long do_splice_from(struct inode *pipe, struct file *out, size_t len,
-                          unsigned int flags)
+static long do_splice_from(struct pipe_inode_info *pipe, struct file *out,
+                          loff_t *ppos, size_t len, unsigned int flags)
 {
-       loff_t pos;
        int ret;
 
-       if (!out->f_op || !out->f_op->splice_write)
+       if (unlikely(!out->f_op || !out->f_op->splice_write))
                return -EINVAL;
 
-       if (!(out->f_mode & FMODE_WRITE))
+       if (unlikely(!(out->f_mode & FMODE_WRITE)))
                return -EBADF;
 
-       pos = out->f_pos;
-       ret = rw_verify_area(WRITE, out, &pos, len);
+       ret = rw_verify_area(WRITE, out, ppos, len);
        if (unlikely(ret < 0))
                return ret;
 
-       return out->f_op->splice_write(pipe, out, len, flags);
+       return out->f_op->splice_write(pipe, out, ppos, len, flags);
 }
 
 /*
  * Attempt to initiate a splice from a file to a pipe.
  */
-static long do_splice_to(struct file *in, struct inode *pipe, size_t len,
+static long do_splice_to(struct file *in, loff_t *ppos,
+                        struct pipe_inode_info *pipe, size_t len,
                         unsigned int flags)
 {
-       loff_t pos, isize, left;
+       loff_t isize, left;
        int ret;
 
-       if (!in->f_op || !in->f_op->splice_read)
+       if (unlikely(!in->f_op || !in->f_op->splice_read))
                return -EINVAL;
 
-       if (!(in->f_mode & FMODE_READ))
+       if (unlikely(!(in->f_mode & FMODE_READ)))
                return -EBADF;
 
-       pos = in->f_pos;
-       ret = rw_verify_area(READ, in, &pos, len);
+       ret = rw_verify_area(READ, in, ppos, len);
        if (unlikely(ret < 0))
                return ret;
 
        isize = i_size_read(in->f_mapping->host);
-       if (unlikely(in->f_pos >= isize))
+       if (unlikely(*ppos >= isize))
                return 0;
        
-       left = isize - in->f_pos;
-       if (left < len)
+       left = isize - *ppos;
+       if (unlikely(left < len))
                len = left;
 
-       return in->f_op->splice_read(in, pipe, len, flags);
+       return in->f_op->splice_read(in, ppos, pipe, len, flags);
+}
+
+long do_splice_direct(struct file *in, loff_t *ppos, struct file *out,
+                     size_t len, unsigned int flags)
+{
+       struct pipe_inode_info *pipe;
+       long ret, bytes;
+       loff_t out_off;
+       umode_t i_mode;
+       int i;
+
+       /*
+        * We require the input being a regular file, as we don't want to
+        * randomly drop data for eg socket -> socket splicing. Use the
+        * piped splicing for that!
+        */
+       i_mode = in->f_dentry->d_inode->i_mode;
+       if (unlikely(!S_ISREG(i_mode) && !S_ISBLK(i_mode)))
+               return -EINVAL;
+
+       /*
+        * neither in nor out is a pipe, setup an internal pipe attached to
+        * 'out' and transfer the wanted data from 'in' to 'out' through that
+        */
+       pipe = current->splice_pipe;
+       if (unlikely(!pipe)) {
+               pipe = alloc_pipe_info(NULL);
+               if (!pipe)
+                       return -ENOMEM;
+
+               /*
+                * We don't have an immediate reader, but we'll read the stuff
+                * out of the pipe right after the move_to_pipe(). So set
+                * PIPE_READERS appropriately.
+                */
+               pipe->readers = 1;
+
+               current->splice_pipe = pipe;
+       }
+
+       /*
+        * Do the splice.
+        */
+       ret = 0;
+       bytes = 0;
+       out_off = 0;
+
+       while (len) {
+               size_t read_len, max_read_len;
+
+               /*
+                * Do at most PIPE_BUFFERS pages worth of transfer:
+                */
+               max_read_len = min(len, (size_t)(PIPE_BUFFERS*PAGE_SIZE));
+
+               ret = do_splice_to(in, ppos, pipe, max_read_len, flags);
+               if (unlikely(ret < 0))
+                       goto out_release;
+
+               read_len = ret;
+
+               /*
+                * NOTE: nonblocking mode only applies to the input. We
+                * must not do the output in nonblocking mode as then we
+                * could get stuck data in the internal pipe:
+                */
+               ret = do_splice_from(pipe, out, &out_off, read_len,
+                                    flags & ~SPLICE_F_NONBLOCK);
+               if (unlikely(ret < 0))
+                       goto out_release;
+
+               bytes += ret;
+               len -= ret;
+
+               /*
+                * In nonblocking mode, if we got back a short read then
+                * that was due to either an IO error or due to the
+                * pagecache entry not being there. In the IO error case
+                * the _next_ splice attempt will produce a clean IO error
+                * return value (not a short read), so in both cases it's
+                * correct to break out of the loop here:
+                */
+               if ((flags & SPLICE_F_NONBLOCK) && (read_len < max_read_len))
+                       break;
+       }
+
+       pipe->nrbufs = pipe->curbuf = 0;
+
+       return bytes;
+
+out_release:
+       /*
+        * If we did an incomplete transfer we must release
+        * the pipe buffers in question:
+        */
+       for (i = 0; i < PIPE_BUFFERS; i++) {
+               struct pipe_buffer *buf = pipe->bufs + i;
+
+               if (buf->ops) {
+                       buf->ops->release(pipe, buf);
+                       buf->ops = NULL;
+               }
+       }
+       pipe->nrbufs = pipe->curbuf = 0;
+
+       /*
+        * If we transferred some data, return the number of bytes:
+        */
+       if (bytes > 0)
+               return bytes;
+
+       return ret;
 }
 
+EXPORT_SYMBOL(do_splice_direct);
+
 /*
  * Determine where to splice to/from.
  */
-static long do_splice(struct file *in, struct file *out, size_t len,
-                     unsigned int flags)
+static long do_splice(struct file *in, loff_t __user *off_in,
+                     struct file *out, loff_t __user *off_out,
+                     size_t len, unsigned int flags)
 {
-       struct inode *pipe;
+       struct pipe_inode_info *pipe;
+       loff_t offset, *off;
+       long ret;
+
+       pipe = in->f_dentry->d_inode->i_pipe;
+       if (pipe) {
+               if (off_in)
+                       return -ESPIPE;
+               if (off_out) {
+                       if (out->f_op->llseek == no_llseek)
+                               return -EINVAL;
+                       if (copy_from_user(&offset, off_out, sizeof(loff_t)))
+                               return -EFAULT;
+                       off = &offset;
+               } else
+                       off = &out->f_pos;
+
+               ret = do_splice_from(pipe, out, off, len, flags);
+
+               if (off_out && copy_to_user(off_out, off, sizeof(loff_t)))
+                       ret = -EFAULT;
 
-       pipe = in->f_dentry->d_inode;
-       if (pipe->i_pipe)
-               return do_splice_from(pipe, out, len, flags);
+               return ret;
+       }
+
+       pipe = out->f_dentry->d_inode->i_pipe;
+       if (pipe) {
+               if (off_out)
+                       return -ESPIPE;
+               if (off_in) {
+                       if (in->f_op->llseek == no_llseek)
+                               return -EINVAL;
+                       if (copy_from_user(&offset, off_in, sizeof(loff_t)))
+                               return -EFAULT;
+                       off = &offset;
+               } else
+                       off = &in->f_pos;
 
-       pipe = out->f_dentry->d_inode;
-       if (pipe->i_pipe)
-               return do_splice_to(in, pipe, len, flags);
+               ret = do_splice_to(in, off, pipe, len, flags);
+
+               if (off_in && copy_to_user(off_in, off, sizeof(loff_t)))
+                       ret = -EFAULT;
+
+               return ret;
+       }
 
        return -EINVAL;
 }
 
-asmlinkage long sys_splice(int fdin, int fdout, size_t len, unsigned int flags)
+asmlinkage long sys_splice(int fd_in, loff_t __user *off_in,
+                          int fd_out, loff_t __user *off_out,
+                          size_t len, unsigned int flags)
 {
        long error;
        struct file *in, *out;
@@ -761,13 +1022,15 @@ asmlinkage long sys_splice(int fdin, int fdout, size_t len, unsigned int flags)
                return 0;
 
        error = -EBADF;
-       in = fget_light(fdin, &fput_in);
+       in = fget_light(fd_in, &fput_in);
        if (in) {
                if (in->f_mode & FMODE_READ) {
-                       out = fget_light(fdout, &fput_out);
+                       out = fget_light(fd_out, &fput_out);
                        if (out) {
                                if (out->f_mode & FMODE_WRITE)
-                                       error = do_splice(in, out, len, flags);
+                                       error = do_splice(in, off_in,
+                                                         out, off_out,
+                                                         len, flags);
                                fput_light(out, fput_out);
                        }
                }
@@ -777,3 +1040,192 @@ asmlinkage long sys_splice(int fdin, int fdout, size_t len, unsigned int flags)
 
        return error;
 }
+
+/*
+ * Link contents of ipipe to opipe.
+ */
+static int link_pipe(struct pipe_inode_info *ipipe,
+                    struct pipe_inode_info *opipe,
+                    size_t len, unsigned int flags)
+{
+       struct pipe_buffer *ibuf, *obuf;
+       int ret, do_wakeup, i, ipipe_first;
+
+       ret = do_wakeup = ipipe_first = 0;
+
+       /*
+        * Potential ABBA deadlock, work around it by ordering lock
+        * grabbing by inode address. Otherwise two different processes
+        * could deadlock (one doing tee from A -> B, the other from B -> A).
+        */
+       if (ipipe->inode < opipe->inode) {
+               ipipe_first = 1;
+               mutex_lock(&ipipe->inode->i_mutex);
+               mutex_lock(&opipe->inode->i_mutex);
+       } else {
+               mutex_lock(&opipe->inode->i_mutex);
+               mutex_lock(&ipipe->inode->i_mutex);
+       }
+
+       for (i = 0;; i++) {
+               if (!opipe->readers) {
+                       send_sig(SIGPIPE, current, 0);
+                       if (!ret)
+                               ret = -EPIPE;
+                       break;
+               }
+               if (ipipe->nrbufs - i) {
+                       ibuf = ipipe->bufs + ((ipipe->curbuf + i) & (PIPE_BUFFERS - 1));
+
+                       /*
+                        * If we have room, fill this buffer
+                        */
+                       if (opipe->nrbufs < PIPE_BUFFERS) {
+                               int nbuf = (opipe->curbuf + opipe->nrbufs) & (PIPE_BUFFERS - 1);
+
+                               /*
+                                * Get a reference to this pipe buffer,
+                                * so we can copy the contents over.
+                                */
+                               ibuf->ops->get(ipipe, ibuf);
+
+                               obuf = opipe->bufs + nbuf;
+                               *obuf = *ibuf;
+
+                               if (obuf->len > len)
+                                       obuf->len = len;
+
+                               opipe->nrbufs++;
+                               do_wakeup = 1;
+                               ret += obuf->len;
+                               len -= obuf->len;
+
+                               if (!len)
+                                       break;
+                               if (opipe->nrbufs < PIPE_BUFFERS)
+                                       continue;
+                       }
+
+                       /*
+                        * We have input available, but no output room.
+                        * If we already copied data, return that. If we
+                        * need to drop the opipe lock, it must be ordered
+                        * last to avoid deadlocks.
+                        */
+                       if ((flags & SPLICE_F_NONBLOCK) || !ipipe_first) {
+                               if (!ret)
+                                       ret = -EAGAIN;
+                               break;
+                       }
+                       if (signal_pending(current)) {
+                               if (!ret)
+                                       ret = -ERESTARTSYS;
+                               break;
+                       }
+                       if (do_wakeup) {
+                               smp_mb();
+                               if (waitqueue_active(&opipe->wait))
+                                       wake_up_interruptible(&opipe->wait);
+                               kill_fasync(&opipe->fasync_readers, SIGIO, POLL_IN);
+                               do_wakeup = 0;
+                       }
+
+                       opipe->waiting_writers++;
+                       pipe_wait(opipe);
+                       opipe->waiting_writers--;
+                       continue;
+               }
+
+               /*
+                * No input buffers, do the usual checks for available
+                * writers and blocking and wait if necessary
+                */
+               if (!ipipe->writers)
+                       break;
+               if (!ipipe->waiting_writers) {
+                       if (ret)
+                               break;
+               }
+               /*
+                * pipe_wait() drops the ipipe mutex. To avoid deadlocks
+                * with another process, we can only safely do that if
+                * the ipipe lock is ordered last.
+                */
+               if ((flags & SPLICE_F_NONBLOCK) || ipipe_first) {
+                       if (!ret)
+                               ret = -EAGAIN;
+                       break;
+               }
+               if (signal_pending(current)) {
+                       if (!ret)
+                               ret = -ERESTARTSYS;
+                       break;
+               }
+
+               if (waitqueue_active(&ipipe->wait))
+                       wake_up_interruptible_sync(&ipipe->wait);
+               kill_fasync(&ipipe->fasync_writers, SIGIO, POLL_OUT);
+
+               pipe_wait(ipipe);
+       }
+
+       mutex_unlock(&ipipe->inode->i_mutex);
+       mutex_unlock(&opipe->inode->i_mutex);
+
+       if (do_wakeup) {
+               smp_mb();
+               if (waitqueue_active(&opipe->wait))
+                       wake_up_interruptible(&opipe->wait);
+               kill_fasync(&opipe->fasync_readers, SIGIO, POLL_IN);
+       }
+
+       return ret;
+}
+
+/*
+ * This is a tee(1) implementation that works on pipes. It doesn't copy
+ * any data, it simply references the 'in' pages on the 'out' pipe.
+ * The 'flags' used are the SPLICE_F_* variants, currently the only
+ * applicable one is SPLICE_F_NONBLOCK.
+ */
+static long do_tee(struct file *in, struct file *out, size_t len,
+                  unsigned int flags)
+{
+       struct pipe_inode_info *ipipe = in->f_dentry->d_inode->i_pipe;
+       struct pipe_inode_info *opipe = out->f_dentry->d_inode->i_pipe;
+
+       /*
+        * Link ipipe to the two output pipes, consuming as we go along.
+        */
+       if (ipipe && opipe)
+               return link_pipe(ipipe, opipe, len, flags);
+
+       return -EINVAL;
+}
+
+asmlinkage long sys_tee(int fdin, int fdout, size_t len, unsigned int flags)
+{
+       struct file *in;
+       int error, fput_in;
+
+       if (unlikely(!len))
+               return 0;
+
+       error = -EBADF;
+       in = fget_light(fdin, &fput_in);
+       if (in) {
+               if (in->f_mode & FMODE_READ) {
+                       int fput_out;
+                       struct file *out = fget_light(fdout, &fput_out);
+
+                       if (out) {
+                               if (out->f_mode & FMODE_WRITE)
+                                       error = do_tee(in, out, len, flags);
+                               fput_light(out, fput_out);
+                       }
+               }
+               fput_light(in, fput_in);
+       }
+
+       return error;
+}
index 8616006d2094818b8796fe998dc72bc2627f8e96..aab5ffe77e9fd67e3ac9173a4cb9488fd393f074 100644 (file)
--- a/fs/sync.c
+++ b/fs/sync.c
@@ -61,7 +61,7 @@
  * will be available after a crash.
  */
 asmlinkage long sys_sync_file_range(int fd, loff_t offset, loff_t nbytes,
-                                       int flags)
+                                       unsigned int flags)
 {
        int ret;
        struct file *file;
@@ -126,7 +126,7 @@ out:
  * `endbyte' is inclusive
  */
 int do_sync_file_range(struct file *file, loff_t offset, loff_t endbyte,
-                       int flags)
+                       unsigned int flags)
 {
        int ret;
        struct address_space *mapping;
index 6cfdc9a87772b99e4a126c72d9ae6ab327f60adb..610b5bdbe75bc1a04c870a3def601b9b666a1772 100644 (file)
@@ -43,6 +43,7 @@ static struct sysfs_dirent * sysfs_new_dirent(struct sysfs_dirent * parent_sd,
 
        memset(sd, 0, sizeof(*sd));
        atomic_set(&sd->s_count, 1);
+       atomic_set(&sd->s_event, 0);
        INIT_LIST_HEAD(&sd->s_children);
        list_add(&sd->s_sibling, &parent_sd->s_children);
        sd->s_element = element;
index f1cb1ddde511d7db0978ebc9bb7c7e3feb453394..cf3786625bfade2ec42b0bcebcd6b0c72771ff21 100644 (file)
@@ -6,6 +6,7 @@
 #include <linux/fsnotify.h>
 #include <linux/kobject.h>
 #include <linux/namei.h>
+#include <linux/poll.h>
 #include <asm/uaccess.h>
 #include <asm/semaphore.h>
 
@@ -57,6 +58,7 @@ struct sysfs_buffer {
        struct sysfs_ops        * ops;
        struct semaphore        sem;
        int                     needs_read_fill;
+       int                     event;
 };
 
 
@@ -72,6 +74,7 @@ struct sysfs_buffer {
  */
 static int fill_read_buffer(struct dentry * dentry, struct sysfs_buffer * buffer)
 {
+       struct sysfs_dirent * sd = dentry->d_fsdata;
        struct attribute * attr = to_attr(dentry);
        struct kobject * kobj = to_kobj(dentry->d_parent);
        struct sysfs_ops * ops = buffer->ops;
@@ -83,6 +86,7 @@ static int fill_read_buffer(struct dentry * dentry, struct sysfs_buffer * buffer
        if (!buffer->page)
                return -ENOMEM;
 
+       buffer->event = atomic_read(&sd->s_event);
        count = ops->show(kobj,attr,buffer->page);
        buffer->needs_read_fill = 0;
        BUG_ON(count > (ssize_t)PAGE_SIZE);
@@ -348,12 +352,84 @@ static int sysfs_release(struct inode * inode, struct file * filp)
        return 0;
 }
 
+/* Sysfs attribute files are pollable.  The idea is that you read
+ * the content and then you use 'poll' or 'select' to wait for
+ * the content to change.  When the content changes (assuming the
+ * manager for the kobject supports notification), poll will
+ * return POLLERR|POLLPRI, and select will return the fd whether
+ * it is waiting for read, write, or exceptions.
+ * Once poll/select indicates that the value has changed, you
+ * need to close and re-open the file, as simply seeking and reading
+ * again will not get new data, or reset the state of 'poll'.
+ * Reminder: this only works for attributes which actively support
+ * it, and it is not possible to test an attribute from userspace
+ * to see if it supports poll (Nether 'poll' or 'select' return
+ * an appropriate error code).  When in doubt, set a suitable timeout value.
+ */
+static unsigned int sysfs_poll(struct file *filp, poll_table *wait)
+{
+       struct sysfs_buffer * buffer = filp->private_data;
+       struct kobject * kobj = to_kobj(filp->f_dentry->d_parent);
+       struct sysfs_dirent * sd = filp->f_dentry->d_fsdata;
+       int res = 0;
+
+       poll_wait(filp, &kobj->poll, wait);
+
+       if (buffer->event != atomic_read(&sd->s_event)) {
+               res = POLLERR|POLLPRI;
+               buffer->needs_read_fill = 1;
+       }
+
+       return res;
+}
+
+
+static struct dentry *step_down(struct dentry *dir, const char * name)
+{
+       struct dentry * de;
+
+       if (dir == NULL || dir->d_inode == NULL)
+               return NULL;
+
+       mutex_lock(&dir->d_inode->i_mutex);
+       de = lookup_one_len(name, dir, strlen(name));
+       mutex_unlock(&dir->d_inode->i_mutex);
+       dput(dir);
+       if (IS_ERR(de))
+               return NULL;
+       if (de->d_inode == NULL) {
+               dput(de);
+               return NULL;
+       }
+       return de;
+}
+
+void sysfs_notify(struct kobject * k, char *dir, char *attr)
+{
+       struct dentry *de = k->dentry;
+       if (de)
+               dget(de);
+       if (de && dir)
+               de = step_down(de, dir);
+       if (de && attr)
+               de = step_down(de, attr);
+       if (de) {
+               struct sysfs_dirent * sd = de->d_fsdata;
+               if (sd)
+                       atomic_inc(&sd->s_event);
+               wake_up_interruptible(&k->poll);
+               dput(de);
+       }
+}
+EXPORT_SYMBOL_GPL(sysfs_notify);
+
 const struct file_operations sysfs_file_operations = {
        .read           = sysfs_read_file,
        .write          = sysfs_write_file,
        .llseek         = generic_file_llseek,
        .open           = sysfs_open_file,
        .release        = sysfs_release,
+       .poll           = sysfs_poll,
 };
 
 
index 32958a7c50e95ce5ffe448a83507c654901fb349..3651ffb5ec091972f92f418dce997883feae6f40 100644 (file)
@@ -11,6 +11,7 @@ extern int sysfs_make_dirent(struct sysfs_dirent *, struct dentry *, void *,
 
 extern int sysfs_add_file(struct dentry *, const struct attribute *, int);
 extern void sysfs_hash_and_remove(struct dentry * dir, const char * name);
+extern struct sysfs_dirent *sysfs_find(struct sysfs_dirent *dir, const char * name);
 
 extern int sysfs_create_subdir(struct kobject *, const char *, struct dentry **);
 extern void sysfs_remove_subdir(struct dentry *);
index 6cbbd165c60db28815b79b18992f5a7433485067..4d191ef39b67a62abd3171ec5499f8868727b37f 100644 (file)
@@ -870,12 +870,14 @@ xfs_page_state_convert(
        pgoff_t                 end_index, last_index, tlast;
        ssize_t                 size, len;
        int                     flags, err, iomap_valid = 0, uptodate = 1;
-       int                     page_dirty, count = 0, trylock_flag = 0;
+       int                     page_dirty, count = 0;
+       int                     trylock = 0;
        int                     all_bh = unmapped;
 
-       /* wait for other IO threads? */
-       if (startio && (wbc->sync_mode == WB_SYNC_NONE && wbc->nonblocking))
-               trylock_flag |= BMAPI_TRYLOCK;
+       if (startio) {
+               if (wbc->sync_mode == WB_SYNC_NONE && wbc->nonblocking)
+                       trylock |= BMAPI_TRYLOCK;
+       }
 
        /* Is this page beyond the end of the file? */
        offset = i_size_read(inode);
@@ -956,15 +958,13 @@ xfs_page_state_convert(
 
                        if (buffer_unwritten(bh)) {
                                type = IOMAP_UNWRITTEN;
-                               flags = BMAPI_WRITE|BMAPI_IGNSTATE;
+                               flags = BMAPI_WRITE | BMAPI_IGNSTATE;
                        } else if (buffer_delay(bh)) {
                                type = IOMAP_DELAY;
-                               flags = BMAPI_ALLOCATE;
-                               if (!startio)
-                                       flags |= trylock_flag;
+                               flags = BMAPI_ALLOCATE | trylock;
                        } else {
                                type = IOMAP_NEW;
-                               flags = BMAPI_WRITE|BMAPI_MMAP;
+                               flags = BMAPI_WRITE | BMAPI_MMAP;
                        }
 
                        if (!iomap_valid) {
index 9fb0312665caacd41872527e101f8c19706ceaa1..26fed0756f0100b5c2e2aec31eb5e1f5853c9ed4 100644 (file)
@@ -182,7 +182,7 @@ free_address(
 {
        a_list_t        *aentry;
 
-       aentry = kmalloc(sizeof(a_list_t), GFP_ATOMIC & ~__GFP_HIGH);
+       aentry = kmalloc(sizeof(a_list_t), GFP_NOWAIT);
        if (likely(aentry)) {
                spin_lock(&as_lock);
                aentry->next = as_free_head;
index ae4c4754ed3185446023f8f25c0efd068104b19d..c847416f6d1010ac9ffea5ad764661662472632a 100644 (file)
@@ -252,56 +252,60 @@ xfs_file_sendfile_invis(
 STATIC ssize_t
 xfs_file_splice_read(
        struct file             *infilp,
-       struct inode            *pipe,
+       loff_t                  *ppos,
+       struct pipe_inode_info  *pipe,
        size_t                  len,
        unsigned int            flags)
 {
        vnode_t                 *vp = vn_from_inode(infilp->f_dentry->d_inode);
        ssize_t                 rval;
 
-       VOP_SPLICE_READ(vp, infilp, pipe, len, flags, 0, NULL, rval);
+       VOP_SPLICE_READ(vp, infilp, ppos, pipe, len, flags, 0, NULL, rval);
        return rval;
 }
 
 STATIC ssize_t
 xfs_file_splice_read_invis(
        struct file             *infilp,
-       struct inode            *pipe,
+       loff_t                  *ppos,
+       struct pipe_inode_info  *pipe,
        size_t                  len,
        unsigned int            flags)
 {
        vnode_t                 *vp = vn_from_inode(infilp->f_dentry->d_inode);
        ssize_t                 rval;
 
-       VOP_SPLICE_READ(vp, infilp, pipe, len, flags, IO_INVIS, NULL, rval);
+       VOP_SPLICE_READ(vp, infilp, ppos, pipe, len, flags, IO_INVIS, NULL, rval);
        return rval;
 }
 
 STATIC ssize_t
 xfs_file_splice_write(
-       struct inode            *pipe,
+       struct pipe_inode_info  *pipe,
        struct file             *outfilp,
+       loff_t                  *ppos,
        size_t                  len,
        unsigned int            flags)
 {
        vnode_t                 *vp = vn_from_inode(outfilp->f_dentry->d_inode);
        ssize_t                 rval;
 
-       VOP_SPLICE_WRITE(vp, pipe, outfilp, len, flags, 0, NULL, rval);
+       VOP_SPLICE_WRITE(vp, pipe, outfilp, ppos, len, flags, 0, NULL, rval);
        return rval;
 }
 
 STATIC ssize_t
 xfs_file_splice_write_invis(
-       struct inode            *pipe,
+       struct pipe_inode_info  *pipe,
        struct file             *outfilp,
+       loff_t                  *ppos,
        size_t                  len,
        unsigned int            flags)
 {
        vnode_t                 *vp = vn_from_inode(outfilp->f_dentry->d_inode);
        ssize_t                 rval;
 
-       VOP_SPLICE_WRITE(vp, pipe, outfilp, len, flags, IO_INVIS, NULL, rval);
+       VOP_SPLICE_WRITE(vp, pipe, outfilp, ppos, len, flags, IO_INVIS, NULL, rval);
        return rval;
 }
 
index 149237304fb6b59e457037e06ae2325ee17193ba..2e2e275c786f2e98f617ef7d720e1b0b617a4643 100644 (file)
@@ -673,8 +673,7 @@ xfs_vn_setattr(
        if (ia_valid & ATTR_ATIME) {
                vattr.va_mask |= XFS_AT_ATIME;
                vattr.va_atime = attr->ia_atime;
-               if (ia_valid & ATTR_ATIME_SET)
-                       inode->i_atime = attr->ia_atime;
+               inode->i_atime = attr->ia_atime;
        }
        if (ia_valid & ATTR_MTIME) {
                vattr.va_mask |= XFS_AT_MTIME;
index 90cd314acbaa7bc742af0509f263dd18053b5d74..67efe3308980a0110030b58cbfca276a230ee32e 100644 (file)
@@ -338,7 +338,8 @@ ssize_t
 xfs_splice_read(
        bhv_desc_t              *bdp,
        struct file             *infilp,
-       struct inode            *pipe,
+       loff_t                  *ppos,
+       struct pipe_inode_info  *pipe,
        size_t                  count,
        int                     flags,
        int                     ioflags,
@@ -360,7 +361,7 @@ xfs_splice_read(
                int error;
 
                error = XFS_SEND_DATA(mp, DM_EVENT_READ, BHV_TO_VNODE(bdp),
-                                       infilp->f_pos, count,
+                                       *ppos, count,
                                        FILP_DELAY_FLAG(infilp), &locktype);
                if (error) {
                        xfs_iunlock(ip, XFS_IOLOCK_SHARED);
@@ -368,8 +369,8 @@ xfs_splice_read(
                }
        }
        xfs_rw_enter_trace(XFS_SPLICE_READ_ENTER, &ip->i_iocore,
-                          pipe, count, infilp->f_pos, ioflags);
-       ret = generic_file_splice_read(infilp, pipe, count, flags);
+                          pipe, count, *ppos, ioflags);
+       ret = generic_file_splice_read(infilp, ppos, pipe, count, flags);
        if (ret > 0)
                XFS_STATS_ADD(xs_read_bytes, ret);
 
@@ -380,8 +381,9 @@ xfs_splice_read(
 ssize_t
 xfs_splice_write(
        bhv_desc_t              *bdp,
-       struct inode            *pipe,
+       struct pipe_inode_info  *pipe,
        struct file             *outfilp,
+       loff_t                  *ppos,
        size_t                  count,
        int                     flags,
        int                     ioflags,
@@ -403,7 +405,7 @@ xfs_splice_write(
                int error;
 
                error = XFS_SEND_DATA(mp, DM_EVENT_WRITE, BHV_TO_VNODE(bdp),
-                                       outfilp->f_pos, count,
+                                       *ppos, count,
                                        FILP_DELAY_FLAG(outfilp), &locktype);
                if (error) {
                        xfs_iunlock(ip, XFS_IOLOCK_EXCL);
@@ -411,8 +413,8 @@ xfs_splice_write(
                }
        }
        xfs_rw_enter_trace(XFS_SPLICE_WRITE_ENTER, &ip->i_iocore,
-                          pipe, count, outfilp->f_pos, ioflags);
-       ret = generic_file_splice_write(pipe, outfilp, count, flags);
+                          pipe, count, *ppos, ioflags);
+       ret = generic_file_splice_write(pipe, outfilp, ppos, count, flags);
        if (ret > 0)
                XFS_STATS_ADD(xs_write_bytes, ret);
 
index eaa5659713fb8d9535eb2c08bed9a7e621839d35..8f4539952350e235991e857cdf97548e230f7632 100644 (file)
@@ -93,11 +93,11 @@ extern ssize_t xfs_write(struct bhv_desc *, struct kiocb *,
 extern ssize_t xfs_sendfile(struct bhv_desc *, struct file *,
                                loff_t *, int, size_t, read_actor_t,
                                void *, struct cred *);
-extern ssize_t xfs_splice_read(struct bhv_desc *, struct file *,
-                               struct inode *, size_t, int, int,
+extern ssize_t xfs_splice_read(struct bhv_desc *, struct file *, loff_t *,
+                               struct pipe_inode_info *, size_t, int, int,
                                struct cred *);
-extern ssize_t xfs_splice_write(struct bhv_desc *, struct inode *,
-                               struct file *, size_t, int, int,
+extern ssize_t xfs_splice_write(struct bhv_desc *, struct pipe_inode_info *,
+                               struct file *, loff_t *, size_t, int, int,
                                struct cred *);
 
 #endif /* __XFS_LRW_H__ */
index 6f1c79a28f8bee1e1faac2a2ced7b5acce9bacca..2a8e16c22353c98f44a12bc462130a43c2646555 100644 (file)
@@ -173,11 +173,11 @@ typedef ssize_t (*vop_write_t)(bhv_desc_t *, struct kiocb *,
 typedef ssize_t (*vop_sendfile_t)(bhv_desc_t *, struct file *,
                                loff_t *, int, size_t, read_actor_t,
                                void *, struct cred *);
-typedef ssize_t (*vop_splice_read_t)(bhv_desc_t *, struct file *,
-                               struct inode *, size_t, int, int,
+typedef ssize_t (*vop_splice_read_t)(bhv_desc_t *, struct file *, loff_t *,
+                               struct pipe_inode_info *, size_t, int, int,
                                struct cred *);
-typedef ssize_t (*vop_splice_write_t)(bhv_desc_t *, struct inode *,
-                               struct file *, size_t, int, int,
+typedef ssize_t (*vop_splice_write_t)(bhv_desc_t *, struct pipe_inode_info *,
+                               struct file *, loff_t *, size_t, int, int,
                                struct cred *);
 typedef int    (*vop_ioctl_t)(bhv_desc_t *, struct inode *, struct file *,
                                int, unsigned int, void __user *);
@@ -284,10 +284,10 @@ typedef struct vnodeops {
        rv = _VOP_(vop_write, vp)((vp)->v_fbhv,file,iov,segs,offset,ioflags,cr)
 #define VOP_SENDFILE(vp,f,off,ioflags,cnt,act,targ,cr,rv)              \
        rv = _VOP_(vop_sendfile, vp)((vp)->v_fbhv,f,off,ioflags,cnt,act,targ,cr)
-#define VOP_SPLICE_READ(vp,f,pipe,cnt,fl,iofl,cr,rv)                   \
-       rv = _VOP_(vop_splice_read, vp)((vp)->v_fbhv,f,pipe,cnt,fl,iofl,cr)
-#define VOP_SPLICE_WRITE(vp,f,pipe,cnt,fl,iofl,cr,rv)                  \
-       rv = _VOP_(vop_splice_write, vp)((vp)->v_fbhv,f,pipe,cnt,fl,iofl,cr)
+#define VOP_SPLICE_READ(vp,f,o,pipe,cnt,fl,iofl,cr,rv)                 \
+       rv = _VOP_(vop_splice_read, vp)((vp)->v_fbhv,f,o,pipe,cnt,fl,iofl,cr)
+#define VOP_SPLICE_WRITE(vp,f,o,pipe,cnt,fl,iofl,cr,rv)                        \
+       rv = _VOP_(vop_splice_write, vp)((vp)->v_fbhv,f,o,pipe,cnt,fl,iofl,cr)
 #define VOP_BMAP(vp,of,sz,rw,b,n,rv)                                   \
        rv = _VOP_(vop_bmap, vp)((vp)->v_fbhv,of,sz,rw,b,n)
 #define VOP_OPEN(vp, cr, rv)                                           \
index 4eeb856183b1364ec0c3f6d2b7016a1b9a503ccb..deddbd03c1667e61b6f28e12e012e5c2bd1724e3 100644 (file)
@@ -158,9 +158,10 @@ xfs_ialloc_ag_alloc(
         */
        agi = XFS_BUF_TO_AGI(agbp);
        newino = be32_to_cpu(agi->agi_newino);
-       if(likely(newino != NULLAGINO)) {
-               args.agbno = XFS_AGINO_TO_AGBNO(args.mp, newino) +
-                               XFS_IALLOC_BLOCKS(args.mp);
+       args.agbno = XFS_AGINO_TO_AGBNO(args.mp, newino) +
+                       XFS_IALLOC_BLOCKS(args.mp);
+       if (likely(newino != NULLAGINO &&
+                 (args.agbno < be32_to_cpu(agi->agi_length)))) {
                args.fsbno = XFS_AGB_TO_FSB(args.mp,
                                be32_to_cpu(agi->agi_seqno), args.agbno);
                args.type = XFS_ALLOCTYPE_THIS_BNO;
@@ -182,8 +183,8 @@ xfs_ialloc_ag_alloc(
                 * Set the alignment for the allocation.
                 * If stripe alignment is turned on then align at stripe unit
                 * boundary.
-                * If the cluster size is smaller than a filesystem block 
-                * then we're doing I/O for inodes in filesystem block size 
+                * If the cluster size is smaller than a filesystem block
+                * then we're doing I/O for inodes in filesystem block size
                 * pieces, so don't need alignment anyway.
                 */
                isaligned = 0;
@@ -192,7 +193,7 @@ xfs_ialloc_ag_alloc(
                        args.alignment = args.mp->m_dalign;
                        isaligned = 1;
                } else if (XFS_SB_VERSION_HASALIGN(&args.mp->m_sb) &&
-                          args.mp->m_sb.sb_inoalignmt >= 
+                          args.mp->m_sb.sb_inoalignmt >=
                           XFS_B_TO_FSBT(args.mp,
                                XFS_INODE_CLUSTER_SIZE(args.mp)))
                                args.alignment = args.mp->m_sb.sb_inoalignmt;
@@ -220,7 +221,7 @@ xfs_ialloc_ag_alloc(
                if ((error = xfs_alloc_vextent(&args)))
                        return error;
        }
+
        /*
         * If stripe alignment is turned on, then try again with cluster
         * alignment.
index bb33113eef9f6be3f8b85107067ccedf5fa96003..b53854325266efb6e55f46cc26f0f6de0d481ce2 100644 (file)
@@ -421,7 +421,10 @@ finish_inode:
                        ip->i_chash = chlnew;
                        chlnew->chl_ip = ip;
                        chlnew->chl_blkno = ip->i_blkno;
+                       if (ch->ch_list)
+                               ch->ch_list->chl_prev = chlnew;
                        chlnew->chl_next = ch->ch_list;
+                       chlnew->chl_prev = NULL;
                        ch->ch_list = chlnew;
                        chlnew = NULL;
                }
@@ -723,23 +726,15 @@ xfs_iextract(
                ASSERT(ip->i_cnext == ip && ip->i_cprev == ip);
                ASSERT(ip->i_chash != NULL);
                chm=NULL;
-               for (chl = ch->ch_list; chl != NULL; chl = chl->chl_next) {
-                       if (chl->chl_blkno == ip->i_blkno) {
-                               if (chm == NULL) {
-                                       /* first item on the list */
-                                       ch->ch_list = chl->chl_next;
-                               } else {
-                                       chm->chl_next = chl->chl_next;
-                               }
-                               kmem_zone_free(xfs_chashlist_zone, chl);
-                               break;
-                       } else {
-                               ASSERT(chl->chl_ip != ip);
-                               chm = chl;
-                       }
-               }
-               ASSERT_ALWAYS(chl != NULL);
-       } else {
+               chl = ip->i_chash;
+               if (chl->chl_prev)
+                       chl->chl_prev->chl_next = chl->chl_next;
+               else
+                       ch->ch_list = chl->chl_next;
+               if (chl->chl_next)
+                       chl->chl_next->chl_prev = chl->chl_prev;
+               kmem_zone_free(xfs_chashlist_zone, chl);
+       } else {
                /* delete one inode from a non-empty list */
                iq = ip->i_cnext;
                iq->i_cprev = ip->i_cprev;
index 48146bdc6bdde8bff1a17533d2019d21cd0f535f..94b60dd03801ba4ef4638ab0ffe50219a0170338 100644 (file)
@@ -2732,16 +2732,29 @@ xfs_iunpin(
        ASSERT(atomic_read(&ip->i_pincount) > 0);
 
        if (atomic_dec_and_test(&ip->i_pincount)) {
-               vnode_t *vp = XFS_ITOV_NULL(ip);
+               /*
+                * If the inode is currently being reclaimed, the
+                * linux inode _and_ the xfs vnode may have been
+                * freed so we cannot reference either of them safely.
+                * Hence we should not try to do anything to them
+                * if the xfs inode is currently in the reclaim
+                * path.
+                *
+                * However, we still need to issue the unpin wakeup
+                * call as the inode reclaim may be blocked waiting for
+                * the inode to become unpinned.
+                */
+               if (!(ip->i_flags & (XFS_IRECLAIM|XFS_IRECLAIMABLE))) {
+                       vnode_t *vp = XFS_ITOV_NULL(ip);
 
-               /* make sync come back and flush this inode */
-               if (vp) {
-                       struct inode    *inode = vn_to_inode(vp);
+                       /* make sync come back and flush this inode */
+                       if (vp) {
+                               struct inode    *inode = vn_to_inode(vp);
 
-                       if (!(inode->i_state & I_NEW))
-                               mark_inode_dirty_sync(inode);
+                               if (!(inode->i_state & I_NEW))
+                                       mark_inode_dirty_sync(inode);
+                       }
                }
-
                wake_up(&ip->i_ipin_wait);
        }
 }
index 39ef9c36ea55802fbe4dbd3efa114acbccdbcea2..3b544db1790b1508d87e8db827d908fe8a7cd318 100644 (file)
@@ -189,6 +189,7 @@ typedef struct xfs_ihash {
  */
 typedef struct xfs_chashlist {
        struct xfs_chashlist    *chl_next;
+       struct xfs_chashlist    *chl_prev;
        struct xfs_inode        *chl_ip;
        xfs_daddr_t             chl_blkno;      /* starting block number of
                                                 * the cluster */
index 049fabb7f7e0b87652586e30d6224a0f847de2ce..c0b1c2906880da1b58bcb217c4c11c407ee539d0 100644 (file)
@@ -270,7 +270,7 @@ xfs_mount_validate_sb(
            (sbp->sb_blocklog - sbp->sb_inodelog != sbp->sb_inopblog)   ||
            (sbp->sb_rextsize * sbp->sb_blocksize > XFS_MAX_RTEXTSIZE)  ||
            (sbp->sb_rextsize * sbp->sb_blocksize < XFS_MIN_RTEXTSIZE)  ||
-           (sbp->sb_imax_pct > 100 || sbp->sb_imax_pct < 1))) {
+           (sbp->sb_imax_pct > 100 /* zero sb_imax_pct is valid */))) {
                xfs_fs_mount_cmn_err(flags, "SB sanity check 1 failed");
                return XFS_ERROR(EFSCORRUPTED);
        }
diff --git a/include/asm-alpha/numnodes.h b/include/asm-alpha/numnodes.h
deleted file mode 100644 (file)
index cd42582..0000000
+++ /dev/null
@@ -1,7 +0,0 @@
-#ifndef _ASM_MAX_NUMNODES_H
-#define _ASM_MAX_NUMNODES_H
-
-/* Max 128 Nodes - Marvel */
-#define NODES_SHIFT    7
-
-#endif /* _ASM_MAX_NUMNODES_H */
index 2339b764f69f611c949a9d22068a6e62f31136fa..1adfd18e6154ba116c1121bb76825afdb489cd53 100644 (file)
 #define SCREEN_END             0xdfc00000
 #define SCREEN_BASE            0xdf800000
 
-#define FLUSH_BASE             0xdf000000
-
 #define VIDC_BASE              (void __iomem *)0xe0400000
 #define IOMD_BASE              IOMEM(0xe0200000)
 #define IOC_BASE               IOMEM(0xe0200000)
 #define FLOPPYDMA_BASE         IOMEM(0xe002a000)
 #define PCIO_BASE              IOMEM(0xe0010000)
 
-#define FLUSH_BASE_PHYS                0x00000000      /* ROM */
-
 #define vidc_writel(val)       __raw_writel(val, VIDC_BASE)
 
 /* in/out bias for the ISA slot region */
index 34f40a6cec3042d065636750c6f5ca5d69ccf3da..3178140e24cae0b07e23ff01de8856962c006ffb 100644 (file)
 #define __virt_to_bus(x) __virt_to_phys(x)
 #define __bus_to_virt(x) __phys_to_virt(x)
 
+/*
+ * Cache flushing area - ROM
+ */
+#define FLUSH_BASE_PHYS                0x00000000
+#define FLUSH_BASE             0xdf000000
+
 #endif
index f61cadabe0ec60e3237308c83ad62069fdef4e40..9213bfe4831d6f2e716348d9d9d9976b404b9cd1 100644 (file)
@@ -18,4 +18,4 @@
 
 #define UART_SHIFT     2
 #define FLOW_CONTROL
-#include <asm/hardware/debug-8250.h>
+#include <asm/hardware/debug-8250.S>
index 4e41c2358f4eee850e91ec0c48e36275ae60e75b..3ce864def41efc2cd17c8b60aa1ff63e7e85b7ec 100644 (file)
@@ -57,9 +57,6 @@
 /*
  * RAM definitions
  */
-#define FLUSH_BASE_PHYS                0x40000000
-#define FLUSH_BASE             0xdf000000
-
 #define UNCACHEABLE_ADDR       0xff000000      /* IRQ_STAT */
 
 #endif
index 02f144520c10f647d16d79d6f8e01d994b2552d7..c7c500e176d0e3727414e5eb0084f8b24851d092 100644 (file)
 #define __virt_to_bus(x)       (x)
 #define __bus_to_virt(x)       (x)
 
+/*
+ * Cache flushing area - SRAM
+ */
+#define FLUSH_BASE_PHYS                0x40000000
+#define FLUSH_BASE             0xdf000000
+
 #endif
index 66b19c7fd908abd0158037891ea994849039d61c..ae5b775eb0b7517b4e57dae2bee61250d2f7b1c9 100644 (file)
@@ -10,7 +10,7 @@
 
 #include <linux/serial_reg.h>
 
-#define SERIAL_BASE    ((unsigned char *)0xfe000be0)
+#define SERIAL_BASE    ((unsigned char *)0xf0000be0)
 
 /*
  * This does not append a newline
index 2ef2200f108cd8f18ac9e5865c01683290582ac5..ec51fe92483b13e12485f7753a6db86b0293b613 100644 (file)
@@ -48,9 +48,6 @@
 #define PCICFG0_SIZE           0x01000000
 #define PCICFG0_BASE           0xfa000000
 
-#define FLUSH_SIZE             0x00100000
-#define FLUSH_BASE             0xf9000000
-
 #define PCIMEM_SIZE            0x01000000
 #define PCIMEM_BASE            0xf0000000
 
@@ -61,9 +58,6 @@
 #define PCIMEM_SIZE            0x80000000
 #define PCIMEM_BASE            0x80000000
 
-#define FLUSH_SIZE             0x00100000
-#define FLUSH_BASE             0x7e000000
-
 #define WFLUSH_SIZE            0x01000000
 #define WFLUSH_BASE            0x7d000000
 
@@ -94,7 +88,6 @@
 #define XBUS_SWITCH_J17_11     ((*XBUS_SWITCH) & (1 << 5))
 #define XBUS_SWITCH_J17_9      ((*XBUS_SWITCH) & (1 << 6))
 
-#define FLUSH_BASE_PHYS                0x50000000
 #define UNCACHEABLE_ADDR       (ARMCSR_BASE + 0x108)
 
 
index 09e335cd687d8623a3fb843f7d0f16442c28c58b..99181ffc7e27977899929aa65eed85501403bb36 100644 (file)
@@ -49,12 +49,22 @@ extern unsigned long __bus_to_virt(unsigned long);
 #define TASK_SIZE              UL(0xbf000000)
 #define PAGE_OFFSET            UL(0xc0000000)
 
+/*
+ * Cache flushing area.
+ */
+#define FLUSH_BASE             0xf9000000
+
 #elif defined(CONFIG_ARCH_CO285)
 
 /* Task size and page offset at 1.5GB */
 #define TASK_SIZE              UL(0x5f000000)
 #define PAGE_OFFSET            UL(0x60000000)
 
+/*
+ * Cache flushing area.
+ */
+#define FLUSH_BASE             0x7e000000
+
 #else
 
 #error "Undefined footbridge architecture"
@@ -72,4 +82,6 @@ extern unsigned long __bus_to_virt(unsigned long);
  */
 #define TASK_UNMAPPED_BASE ((TASK_SIZE + 0x01000000) / 3)
 
+#define FLUSH_BASE_PHYS                0x50000000
+
 #endif
index eb99fd69fd242aaa25f1e9b47460ec80bce49010..2b25e640247d14a55da35c28c3608178da98179d 100644 (file)
@@ -17,6 +17,9 @@
                tst     \rx, #1                         @ mmu enabled?
                ldreq   \rx, =IXP23XX_PERIPHERAL_PHYS   @ physical
                ldrne   \rx, =IXP23XX_PERIPHERAL_VIRT   @ virtual
+#ifdef __ARMEB__
+               orr     \rx, \rx, #0x00000003
+#endif
                .endm
 
 #define UART_SHIFT     2
index b755079befabb40d8d6ece8338a9bbc263dd23d0..2ab43f3a4a8deafee20d63b20f7da469214f4918 100644 (file)
@@ -52,9 +52,6 @@
 #define ISA_SIZE               0x20000000
 #define ISA_BASE               0xe0000000
 
-#define FLUSH_BASE_PHYS                0x40000000      /* ROM */
-#define FLUSH_BASE             0xdf000000
-
 #define PCIO_BASE              IO_BASE
 
 #endif
index 9e50a171f78ac5843eb5872255affaa53d3833dc..402df637e7403b1924a9e20a0bc432852d7307ad 100644 (file)
 #define __virt_to_bus(x) __virt_to_phys(x)
 #define __bus_to_virt(x) __phys_to_virt(x)
 
+/*
+ * Cache flushing area - ROM
+ */
+#define FLUSH_BASE_PHYS                0x40000000
+#define FLUSH_BASE             0xdf000000
+
 #endif
index c92bcb8376295912d2839a196311029243a3895c..9f1a58cbf407dfa1a3b37b8caac598bd0c5aa872 100644 (file)
@@ -31,8 +31,6 @@
 
 #ifdef CONFIG_DISCONTIGMEM
 
-#define NODES_SHIFT    4       /* Up to 16 nodes */
-
 /*
  * Given a kernel address, find the home node of the underlying memory.
  */
index 9d7f87375aa774b477485aa79eb422d00c9536ac..7480f4e8d9747e480e78bccd708d3ea7388800cb 100644 (file)
@@ -46,7 +46,6 @@
 #define SCREEN_END             0xdfc00000
 #define SCREEN_BASE            0xdf800000
 
-#define FLUSH_BASE             0xdf000000
 #define UNCACHEABLE_ADDR       0xdf010000
 
 /*
@@ -59,8 +58,6 @@
 #define PCIO_BASE              IOMEM(0xe0010000)
 #define FLOPPYDMA_BASE         IOMEM(0xe002a000)
 
-#define FLUSH_BASE_PHYS                0x00000000      /* ROM */
-
 #define vidc_writel(val)       __raw_writel(val, VIDC_BASE)
 
 #define IO_EC_EASI_BASE                0x81400000
index 0592cb3f0c7436c4856af1246430a2e0ff8fc0e3..303c424ce673e502d740c824afabb635ff2bb56d 100644 (file)
 #define __virt_to_bus(x) __virt_to_phys(x)
 #define __bus_to_virt(x) __phys_to_virt(x)
 
+/*
+ * Cache flushing area - ROM
+ */
+#define FLUSH_BASE_PHYS                0x00000000
+#define FLUSH_BASE             0xdf000000
+
 #endif
diff --git a/include/asm-arm/arch-s3c2410/leds-gpio.h b/include/asm-arm/arch-s3c2410/leds-gpio.h
new file mode 100644 (file)
index 0000000..f07ed04
--- /dev/null
@@ -0,0 +1,28 @@
+/* linux/include/asm-arm/arch-s3c2410/leds-gpio.h
+ *
+ * (c) 2006 Simtec Electronics
+ *     http://armlinux.simtec.co.uk/
+ *     Ben Dooks <ben@simtec.co.uk>
+ *
+ * S3C24XX - LEDs GPIO connector
+ *
+ * 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.
+*/
+
+#ifndef __ASM_ARCH_LEDSGPIO_H
+#define __ASM_ARCH_LEDSGPIO_H "leds-gpio.h"
+
+#define S3C24XX_LEDF_ACTLOW    (1<<0)          /* LED is on when GPIO low */
+#define S3C24XX_LEDF_TRISTATE  (1<<1)          /* tristate to turn off */
+
+struct s3c24xx_led_platdata {
+       unsigned int             gpio;
+       unsigned int             flags;
+
+       char                    *name;
+       char                    *def_trigger;
+};
+
+#endif /* __ASM_ARCH_LEDSGPIO_H */
index 28711aaa4968b5daa5882f905780ed120793fdee..ee008a5484f316a64afc59046985b9e48f0e1d66 100644 (file)
 
 #include <linux/config.h>
 
-/* Flushing areas */
-#define FLUSH_BASE_PHYS                0xe0000000      /* SA1100 zero bank */
-#define FLUSH_BASE             0xf5000000
-#define FLUSH_BASE_MINICACHE   0xf5800000
 #define UNCACHEABLE_ADDR       0xfa050000
 
 
index 018a9f0e3986d2d8f2c53f7f33b7ef17cfb86dc2..a29fac1387caf7324016a7d3607568924f71294f 100644 (file)
@@ -91,4 +91,11 @@ void sa1111_adjust_zones(int node, unsigned long *size, unsigned long *holes);
 
 #endif
 
+/*
+ * Cache flushing area - SA1100 zero bank
+ */
+#define FLUSH_BASE_PHYS                0xe0000000
+#define FLUSH_BASE             0xf5000000
+#define FLUSH_BASE_MINICACHE   0xf5100000
+
 #endif
index 4d35f8c154c308ec7abf0437eab8ab258a35633a..ecba45260898d029b0a28f26e269a63e1defb859 100644 (file)
  */
 #define IO_BASE                        0xe0000000
 
-/*
- * RAM definitions
- */
-#define FLUSH_BASE_PHYS                0x80000000
-
 #else
 
 #define IO_BASE                        0
@@ -33,7 +28,6 @@
 #define ROMCARD_SIZE           0x08000000
 #define ROMCARD_START          0x10000000
 
-#define FLUSH_BASE             0xdf000000
 #define PCIO_BASE              0xe0000000
 
 
index 95a29b4bc5d07d11306947ef0b3e241c150b57af..6968d6103ea00b8386163184e1b64a98c151e201 100644 (file)
@@ -39,4 +39,10 @@ static inline void __arch_adjust_zones(int node, unsigned long *zone_size, unsig
 #define __virt_to_bus(x)       __virt_to_phys(x)
 #define __bus_to_virt(x)       __phys_to_virt(x)
 
+/*
+ * Cache flushing area
+ */
+#define FLUSH_BASE_PHYS                0x80000000
+#define FLUSH_BASE             0xdf000000
+
 #endif
index 6246bf83627d3c7c5304cdc47d974daec61f8702..52bae088a185c04fb95186acde501e53e92e1817 100644 (file)
@@ -26,7 +26,9 @@
 
 struct vfp_hard_struct {
        __u64 fpregs[16];
+#if __LINUX_ARM_ARCH__ < 6
        __u32 fpmx_state;
+#endif
        __u32 fpexc;
        __u32 fpscr;
        /*
index 2b3cf69b3ed9eda46633c85beeb97eef81058da8..20928940759545f0caefc7ed142a9bd308b8802f 100644 (file)
@@ -172,10 +172,10 @@ static inline __deprecated void *bus_to_virt(unsigned long x)
  *  virt_addr_valid(k) indicates whether a virtual address is valid
  */
 #ifndef CONFIG_DISCONTIGMEM
-#define ARCH_PFN_OFFSET                (PHYS_PFN_OFFSET)
+#define ARCH_PFN_OFFSET                PHYS_PFN_OFFSET
 #define pfn_valid(pfn)         ((pfn) >= PHYS_PFN_OFFSET && (pfn) < (PHYS_PFN_OFFSET + max_mapnr))
 
-#define virt_to_page(kaddr)    (pfn_to_page(__pa(kaddr) >> PAGE_SHIFT))
+#define virt_to_page(kaddr)    pfn_to_page(__pa(kaddr) >> PAGE_SHIFT)
 #define virt_addr_valid(kaddr) ((unsigned long)(kaddr) >= PAGE_OFFSET && (unsigned long)(kaddr) < (unsigned long)high_memory)
 
 #define PHYS_TO_NID(addr)      (0)
@@ -187,8 +187,8 @@ static inline __deprecated void *bus_to_virt(unsigned long x)
  * around in memory.
  */
 #include <linux/numa.h>
-#define arch_pfn_to_nid(pfn)   (PFN_TO_NID(pfn))
-#define arch_local_page_offset(pfn, nid) (LOCAL_MAP_NR((pfn) << PAGE_OFFSET))
+#define arch_pfn_to_nid(pfn)   PFN_TO_NID(pfn)
+#define arch_local_page_offset(pfn, nid) LOCAL_MAP_NR((pfn) << PAGE_SHIFT)
 
 #define pfn_valid(pfn)                                         \
        ({                                                      \
diff --git a/include/asm-arm/numnodes.h b/include/asm-arm/numnodes.h
deleted file mode 100644 (file)
index 8df3681..0000000
+++ /dev/null
@@ -1,26 +0,0 @@
-/*
- *  linux/include/asm-arm/numnodes.h
- *
- *  Copyright (C) 2002 Russell King
- *
- * 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 declaration for the size of the NUMA (CONFIG_DISCONTIGMEM)
- * memory node table is the default.
- *
- * A good place to override this value is include/asm/arch/memory.h.
- */
-
-#ifndef __ASM_ARM_NUMNODES_H
-#define __ASM_ARM_NUMNODES_H
-
-#include <asm/memory.h>
-
-#ifndef NODES_SHIFT
-# define NODES_SHIFT   2       /* Normally, Max 4 Nodes */
-#endif
-
-#endif
index 65ac305c2d457fae139048b71093bc34972e8b4c..ee8dfea549bc324239b1e60f0cdd9ef984e75dfb 100644 (file)
 #define __ARM_NR_usr32                 (__ARM_NR_BASE+4)
 #define __ARM_NR_set_tls               (__ARM_NR_BASE+5)
 
+/*
+ * The following syscalls are obsolete and no longer available for EABI.
+ */
+#if defined(__ARM_EABI__)
+#undef __NR_time
+#undef __NR_umount
+#undef __NR_stime
+#undef __NR_alarm
+#undef __NR_utime
+#undef __NR_getrlimit
+#undef __NR_select
+#undef __NR_readdir
+#undef __NR_mmap
+#undef __NR_socketcall
+#undef __NR_syscall
+#undef __NR_ipc
+#endif
+
 #define __sys2(x) #x
 #define __sys1(x) __sys2(x)
 
index 15bd6e74c9cf44ec8c5d256985587f7ea4ad09f5..27fe028b4e72bbd05ff2ec64054e61e1e86a72c9 100644 (file)
 
        @ read all the working registers back into the VFP
        .macro  VFPFLDMIA, base
+#if __LINUX_ARM_ARCH__ < 6
        LDC     p11, cr0, [\base],#33*4             @ FLDMIAX \base!, {d0-d15}
+#else
+       LDC     p11, cr0, [\base],#32*4             @ FLDMIAD \base!, {d0-d15}
+#endif
        .endm
 
        @ write all the working registers out of the VFP
        .macro  VFPFSTMIA, base
+#if __LINUX_ARM_ARCH__ < 6
        STC     p11, cr0, [\base],#33*4             @ FSTMIAX \base!, {d0-d15}
+#else
+       STC     p11, cr0, [\base],#32*4             @ FSTMIAD \base!, {d0-d15}
+#endif
        .endm
index 1d63c2aa8ec2cf295245b97c44755f6fa4299c21..b1c593b6dbff163df5118bc6ba8c5841148fd43a 100644 (file)
@@ -8,7 +8,6 @@
  */
 
 extern struct task_struct *resume(struct task_struct *prev, struct task_struct *next, int);
-#define prepare_to_switch()     do { } while(0)
 #define switch_to(prev,next,last) last = resume(prev,next, \
                                         (int)&((struct task_struct *)0)->thread)
 
index 2627bbdf8a1144e78c5a85584f86a152640ddb43..bb2dfe480213571dbaf0776892c0516af6b76a9d 100644 (file)
 #define __NR_mq_timedreceive   (__NR_mq_open+3)
 #define __NR_mq_notify         (__NR_mq_open+4)
 #define __NR_mq_getsetattr     (__NR_mq_open+5)
-#define __NR_sys_kexec_load    283
+#define __NR_kexec_load                283
 #define __NR_waitid            284
 /* #define __NR_sys_setaltroot 285 */
 #define __NR_add_key           286
index f72ff0c4dc0b9050a580e0c4dba61b8a36b7b129..1734ed91bcdcdb7f0136f10bd9f14fc8e9d535b3 100644 (file)
@@ -18,8 +18,6 @@
 
 struct thread_struct;
 
-#define prepare_to_switch()    do { } while(0)
-
 /*
  * switch_to(prev, next) should switch from task `prev' to `next'
  * `prev' will never be the same as `next'.
index 322531caa484f7697bcb48bd3fe2b824d0e3ed8b..2662a3e12dc4157ff0d7ab408559bd84280ed7bc 100644 (file)
 #define __NR_mq_timedreceive   (__NR_mq_open+3)
 #define __NR_mq_notify         (__NR_mq_open+4)
 #define __NR_mq_getsetattr     (__NR_mq_open+5)
-#define __NR_sys_kexec_load    283
+#define __NR_kexec_load                283
 #define __NR_waitid            284
 /* #define __NR_sys_setaltroot 285 */
 #define __NR_add_key           286
index dfe96c7121cfe3ad6742fbb93ebea1bb6aea85be..8e81cf665e75ea3406b2d4a79f7a002671aa52f8 100644 (file)
@@ -4,8 +4,6 @@
 #include <linux/config.h> /* get configuration macros */
 #include <linux/linkage.h>
 
-#define prepare_to_switch()    do { } while(0)
-
 /*
  * switch_to(n) should switch tasks to task ptr, first checking that
  * ptr isn't the current task, in which case it does nothing.  This
index 56a4a5686c88197b0e6defc5d9b153944ad631ac..adb05159379b975dcf19c5c2005fd8e2dc0e7720 100644 (file)
 #define __NR_mq_timedreceive   (__NR_mq_open+3)
 #define __NR_mq_notify         (__NR_mq_open+4)
 #define __NR_mq_getsetattr     (__NR_mq_open+5)
-#define __NR_sys_kexec_load    283
+#define __NR_kexec_load                283
 #define __NR_waitid            284
 /* #define __NR_sys_setaltroot 285 */
 #define __NR_add_key           286
index ff9ac8d19eb2584565cb5d8f93b196dc929cbc2d..288233fd77d7b755b8c5962da5084d32a1558351 100644 (file)
@@ -139,6 +139,8 @@ void switch_ipi_to_APIC_timer(void *cpumask);
 
 extern int timer_over_8254;
 
+extern int modern_apic(void);
+
 #else /* !CONFIG_X86_LOCAL_APIC */
 static inline void lapic_shutdown(void) { }
 
index 22d80ece95cb48de54ed1dea6e0c9475d10935ba..4ddce5296a788a2b6442700f4126bb636cd14df9 100644 (file)
@@ -183,6 +183,7 @@ static __inline__ int atomic_add_return(int i, atomic_t *v)
 {
        int __i;
 #ifdef CONFIG_M386
+       unsigned long flags;
        if(unlikely(boot_cpu_data.x86==3))
                goto no_xadd;
 #endif
@@ -196,10 +197,10 @@ static __inline__ int atomic_add_return(int i, atomic_t *v)
 
 #ifdef CONFIG_M386
 no_xadd: /* Legacy 386 processor */
-       local_irq_disable();
+       local_irq_save(flags);
        __i = atomic_read(v);
        atomic_set(v, i + __i);
-       local_irq_enable();
+       local_irq_restore(flags);
        return i + __i;
 #endif
 }
index 5c0b5876b9318cf7e41af251c367597776330569..b44bfc6239cb51debea374b173e58b5469f8ff1c 100644 (file)
@@ -71,6 +71,7 @@
 #define X86_FEATURE_P4         (3*32+ 7) /* P4 */
 #define X86_FEATURE_CONSTANT_TSC (3*32+ 8) /* TSC ticks at a constant rate */
 #define X86_FEATURE_UP         (3*32+ 9) /* smp kernel running on up */
+#define X86_FEATURE_FXSAVE_LEAK (3*32+10) /* FXSAVE leaks FOP/FIP/FOP */
 
 /* Intel-defined CPU features, CPUID level 0x00000001 (ecx), word 4 */
 #define X86_FEATURE_XMM3       (4*32+ 0) /* Streaming SIMD Extensions-3 */
index edf65be21a9249a163e1fa187b6e79fa862cf054..ca82acb8cb1f7831d10bdc5fb135be8e85bf411a 100644 (file)
@@ -35,6 +35,10 @@ struct e820map {
 };
 
 extern struct e820map e820;
+
+extern int e820_all_mapped(unsigned long start, unsigned long end,
+                          unsigned type);
+
 #endif/*!__ASSEMBLY__*/
 
 #endif/*__E820_HEADER*/
index 16ef9f996e3f41606974816a6ac4a36851ad6e76..7f1a8a6ee32fa41dfcb86683f6f5aaae4f9d3d52 100644 (file)
@@ -89,6 +89,7 @@
  * then 32 bit HPET counter wrapsaround in less than 0.5 sec.
  */
 #define HPET_MIN_PERIOD (100000UL)
+#define HPET_TICK_RATE  (HZ * 100000UL)
 
 extern unsigned long hpet_tick;        /* hpet clks count per tick */
 extern unsigned long hpet_address;     /* hpet memory map physical address */
index 152d0baa576a675b39bfa408a6b69f670e8ad118..7b1f01191e7063df3ab056dfdb17e6de0bcd828f 100644 (file)
@@ -13,6 +13,7 @@
 
 #include <linux/sched.h>
 #include <linux/init.h>
+#include <linux/kernel_stat.h>
 #include <asm/processor.h>
 #include <asm/sigcontext.h>
 #include <asm/user.h>
@@ -38,17 +39,38 @@ extern void init_fpu(struct task_struct *);
 extern void kernel_fpu_begin(void);
 #define kernel_fpu_end() do { stts(); preempt_enable(); } while(0)
 
+/* We need a safe address that is cheap to find and that is already
+   in L1 during context switch. The best choices are unfortunately
+   different for UP and SMP */
+#ifdef CONFIG_SMP
+#define safe_address (__per_cpu_offset[0])
+#else
+#define safe_address (kstat_cpu(0).cpustat.user)
+#endif
+
 /*
  * These must be called with preempt disabled
  */
 static inline void __save_init_fpu( struct task_struct *tsk )
 {
+       /* Use more nops than strictly needed in case the compiler
+          varies code */
        alternative_input(
-               "fnsave %1 ; fwait ;" GENERIC_NOP2,
-               "fxsave %1 ; fnclex",
+               "fnsave %[fx] ;fwait;" GENERIC_NOP8 GENERIC_NOP4,
+               "fxsave %[fx]\n"
+               "bt $7,%[fsw] ; jc 1f ; fnclex\n1:",
                X86_FEATURE_FXSR,
-               "m" (tsk->thread.i387.fxsave)
-               :"memory");
+               [fx] "m" (tsk->thread.i387.fxsave),
+               [fsw] "m" (tsk->thread.i387.fxsave.swd) : "memory");
+       /* AMD K7/K8 CPUs don't save/restore FDP/FIP/FOP unless an exception
+          is pending.  Clear the x87 state here by setting it to fixed
+          values. __per_cpu_offset[0] is a random variable that should be in L1 */
+       alternative_input(
+               GENERIC_NOP8 GENERIC_NOP2,
+               "emms\n\t"              /* clear stack tags */
+               "fildl %[addr]",        /* set F?P to defined value */
+               X86_FEATURE_FXSAVE_LEAK,
+               [addr] "m" (safe_address));
        task_thread_info(tsk)->status &= ~TS_USEDFPU;
 }
 
index 62113d3bfdc21837c3c1d87a6457fb75a09a8a4c..770bf6da8c3dd019aca47ca2251195db8e057564 100644 (file)
@@ -18,7 +18,6 @@ extern void find_smp_config (void);
 extern void get_smp_config (void);
 extern int nr_ioapics;
 extern int apic_version [MAX_APICS];
-extern int mp_bus_id_to_type [MAX_MP_BUSSES];
 extern int mp_irq_entries;
 extern struct mpc_config_intsrc mp_irqs [MAX_IRQ_SOURCES];
 extern int mpc_default_type;
diff --git a/include/asm-i386/numnodes.h b/include/asm-i386/numnodes.h
deleted file mode 100644 (file)
index a61f38c..0000000
+++ /dev/null
@@ -1,18 +0,0 @@
-#ifndef _ASM_MAX_NUMNODES_H
-#define _ASM_MAX_NUMNODES_H
-
-#include <linux/config.h>
-
-#ifdef CONFIG_X86_NUMAQ
-
-/* Max 16 Nodes */
-#define NODES_SHIFT    4
-
-#elif defined(CONFIG_ACPI_SRAT)
-
-/* Max 8 Nodes */
-#define NODES_SHIFT    3
-
-#endif /* CONFIG_X86_NUMAQ */
-
-#endif /* _ASM_MAX_NUMNODES_H */
index 2e7f3e257fddf9cba326fab28d769db4bdfeb055..d81d6cfc1bb4a81f40b213cab6a14eed67f371c9 100644 (file)
 #define __NR_mq_timedreceive   (__NR_mq_open+3)
 #define __NR_mq_notify         (__NR_mq_open+4)
 #define __NR_mq_getsetattr     (__NR_mq_open+5)
-#define __NR_sys_kexec_load    283
+#define __NR_kexec_load                283
 #define __NR_waitid            284
 /* #define __NR_sys_setaltroot 285 */
 #define __NR_add_key           286
 #define __NR_unshare           310
 #define __NR_set_robust_list   311
 #define __NR_get_robust_list   312
-#define __NR_sys_splice                313
-#define __NR_sys_sync_file_range 314
+#define __NR_splice            313
+#define __NR_sync_file_range   314
+#define __NR_tee               315
 
-#define NR_syscalls 315
+#define NR_syscalls 316
 
 /*
  * user-visible error numbers are in the range -1 - -128: see
index 56d2ddc97b30cd9c236e8b173edeea52ae2fc0c0..734d137dda6ecb22f1f58c9cc09f6925fe605e03 100644 (file)
@@ -1,12 +1,15 @@
 /*
- * ia64/platform/hp/common/hp_acpi.h
+ * (c) Copyright 2003, 2006 Hewlett-Packard Development Company, L.P.
+ *     Alex Williamson <alex.williamson@hp.com>
+ *     Bjorn Helgaas <bjorn.helgaas@hp.com>
  *
- * Copyright (C) 2003 Hewlett-Packard
- * Copyright (C) Alex Williamson
- * Copyright (C) Bjorn Helgaas
+ * 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.
  *
  * Vendor specific extensions to ACPI.
  */
+
 #ifndef _ASM_IA64_ACPI_EXT_H
 #define _ASM_IA64_ACPI_EXT_H
 
index 218c458ab60c8ef34d69aa95942f8709f0f29eee..c195a9ad12551e88e28aedf02a15743f643dc35e 100644 (file)
@@ -58,6 +58,8 @@ enum die_val {
        DIE_MCA_RENDZVOUS_ENTER,
        DIE_MCA_RENDZVOUS_PROCESS,
        DIE_MCA_RENDZVOUS_LEAVE,
+       DIE_MCA_NEW_TIMEOUT,
+       DIE_INIT_ENTER,
        DIE_INIT_MONARCH_ENTER,
        DIE_INIT_MONARCH_PROCESS,
        DIE_INIT_MONARCH_LEAVE,
index bfbbb8da79c7b9e577bed354ce15145f0db34582..9c5389b7e62375aae8515c5d74720d378b8adf48 100644 (file)
@@ -148,6 +148,11 @@ extern int  ia64_reg_MCA_extension(int (*fn)(void *, struct ia64_sal_os_state *)
 extern void ia64_unreg_MCA_extension(void);
 extern u64 ia64_get_rnat(u64 *);
 
+struct ia64_mca_notify_die {
+       struct ia64_sal_os_state *sos;
+       int *monarch_cpu;
+};
+
 #else  /* __ASSEMBLY__ */
 
 #define IA64_MCA_CORRECTED     0x0     /* Error has been corrected by OS_MCA */
index 5a3224f6af380aaa89aeb71f081ff6909304d9de..bed73a643a56e3c0169a4fd43b705fcba491f5c8 100644 (file)
@@ -84,7 +84,7 @@ __mutex_fastpath_unlock(atomic_t *count, void (*fail_fn)(atomic_t *))
 static inline int
 __mutex_fastpath_trylock(atomic_t *count, int (*fail_fn)(atomic_t *))
 {
-       if (likely(cmpxchg_acq(count, 1, 0)) == 1)
+       if (cmpxchg_acq(count, 1, 0) == 1)
                return 1;
        return 0;
 }
diff --git a/include/asm-ia64/numnodes.h b/include/asm-ia64/numnodes.h
deleted file mode 100644 (file)
index e9d356f..0000000
+++ /dev/null
@@ -1,20 +0,0 @@
-#ifndef _ASM_MAX_NUMNODES_H
-#define _ASM_MAX_NUMNODES_H
-
-#ifdef CONFIG_IA64_DIG
-/* Max 8 Nodes */
-#  define NODES_SHIFT  3
-#elif defined(CONFIG_IA64_HP_ZX1) || defined(CONFIG_IA64_HP_ZX1_SWIOTLB)
-/* Max 32 Nodes */
-#  define NODES_SHIFT  5
-#elif defined(CONFIG_IA64_SGI_SN2) || defined(CONFIG_IA64_GENERIC)
-#  if CONFIG_IA64_NR_NODES == 256
-#    define NODES_SHIFT        8
-#  elif CONFIG_IA64_NR_NODES <= 512
-#    define NODES_SHIFT    9
-#  elif CONFIG_IA64_NR_NODES <= 1024
-#    define NODES_SHIFT    10
-#  endif
-#endif
-
-#endif /* _ASM_MAX_NUMNODES_H */
index 36070c1014d885397d92897cdfb97decf3c671a2..a40ebec6aeebe234a91dc84767e266177a9c058d 100644 (file)
 /* 1294, 1295 reserved for pselect/ppoll */
 #define __NR_unshare                   1296
 #define __NR_splice                    1297
+#define __NR_set_robust_list           1298
+#define __NR_get_robust_list           1299
+#define __NR_sync_file_range           1300
+#define __NR_tee                       1301
 
 #ifdef __KERNEL__
 
 #include <linux/config.h>
 
-#define NR_syscalls                    274 /* length of syscall table */
+#define NR_syscalls                    278 /* length of syscall table */
 
 #define __ARCH_WANT_SYS_RT_SIGACTION
 
index bc3349ffc5055e14fba1d60e7b3eef5ae65c88b3..091177cda223708f6c0a3560b58bfe775845f02a 100644 (file)
@@ -17,7 +17,7 @@
 extern unsigned long vga_console_iobase;
 extern unsigned long vga_console_membase;
 
-#define VGA_MAP_MEM(x) ((unsigned long) ioremap(vga_console_membase + (x), 0))
+#define VGA_MAP_MEM(x) ((unsigned long) ioremap_nocache(vga_console_membase + (x), 0))
 
 #define vga_readb(x)   (*(x))
 #define vga_writeb(x,y)        (*(y) = (x))
index b7f4d8aaeb469b0409103dd8057e3b6f80c2cc8f..1a1aa17edd33fe737d1035676d756421b93a1fe8 100644 (file)
        push    r13
        mvfachi r13
        push    r13
+       ldi     r13, #0
+       push    r13             ; dummy push acc1h
+       push    r13             ; dummy push acc1l
 #else
 #error unknown isa configuration
 #endif
        pop     r13
        mvtaclo r13, a1
 #elif defined(CONFIG_ISA_M32R2) || defined(CONFIG_ISA_M32R)
+       pop     r13             ; dummy pop acc1h
+       pop     r13             ; dummy pop acc1l
        pop     r13
        mvtachi r13
        pop     r13
index 1d3c25d61bcb2399e6f4def20b7ac16b2a911fd0..031369a7afc85ed732613f483906b826707afecb 100644 (file)
 /* Power Control of MMC and CF */
 #define PLD_CPCR               __reg16(PLD_BASE + 0x14000)
 
-
-/*==== ICU ====*/
-#define  M32R_IRQ_PC104        (5)   /* INT4(PC/104) */
-#define  M32R_IRQ_I2C          (28)  /* I2C-BUS     */
-#define  PLD_IRQ_CFIREQ       (6)  /* INT5 CFC Card Interrupt */
-#define  PLD_IRQ_CFC_INSERT   (7)  /* INT6 CFC Card Insert */
-#define  PLD_IRQ_IDEIREQ      (8)  /* INT7 IDE Interrupt   */
-#define  PLD_IRQ_MMCCARD      (43)  /* MMC Card Insert */
-#define  PLD_IRQ_MMCIRQ       (44)  /* MMC Transfer Done */
-
+/* ICU */
+#define M32R_IRQ_PC104         (5)     /* INT4(PC/104) */
+#define M32R_IRQ_I2C           (28)    /* I2C-BUS */
+#define PLD_IRQ_CFIREQ         (6)     /* INT5 CFC Card Interrupt */
+#define PLD_IRQ_CFC_INSERT     (7)     /* INT6 CFC Card Insert & Eject */
+#define PLD_IRQ_IDEIREQ                (8)     /* INT7 IDE Interrupt */
+#define PLD_IRQ_MMCCARD                (43)    /* MMC Card Insert */
+#define PLD_IRQ_MMCIRQ         (44)    /* MMC Transfer Done */
 
 #if 0
 /* LED Control
@@ -97,7 +95,6 @@
 #define PLD_CRC16ADATA         __reg16(PLD_BASE + 0x18008)
 #define PLD_CRC16AINDATA       __reg16(PLD_BASE + 0x1800a)
 
-
 #if 0
 /* RTC */
 #define PLD_RTCCR              __reg16(PLD_BASE + 0x1c000)
 
 #endif
 
+/* Reset Control */
+#define PLD_REBOOT             __reg16(PLD_BASE + 0x38000)
+
 #endif /* _MAPPI3_PLD.H */
diff --git a/include/asm-m32r/numnodes.h b/include/asm-m32r/numnodes.h
deleted file mode 100644 (file)
index 479a39d..0000000
+++ /dev/null
@@ -1,15 +0,0 @@
-#ifndef _ASM_NUMNODES_H_
-#define _ASM_NUMNODES_H_
-
-#include <linux/config.h>
-
-#ifdef CONFIG_DISCONTIGMEM
-
-#if defined(CONFIG_CHIP_M32700)
-#define        NODES_SHIFT     1       /* Max 2 Nodes */
-#endif /* CONFIG_CHIP_M32700 */
-
-#endif /* CONFIG_DISCONTIGMEM */
-
-#endif /* _ASM_NUMNODES_H_ */
-
index 0d058b2d844e468ac6d6ac448a553dfa1d752528..53c792452dfc0c036538230f69fce24406d119f9 100644 (file)
 #define PT_ACC1L       18
 #define PT_ACCH                PT_ACC0H
 #define PT_ACCL                PT_ACC0L
+#elif defined(CONFIG_ISA_M32R2) || defined(CONFIG_ISA_M32R)
+#define PT_ACCH                15
+#define PT_ACCL                16
+#define PT_DUMMY_ACC1H 17
+#define PT_DUMMY_ACC1L 18
+#else
+#error unknown isa conifiguration
+#endif
 #define PT_PSW         19
 #define PT_BPC         20
 #define PT_BBPSW       21
 #define PT_LR          25
 #define PT_SPI         26
 #define PT_ORIGR0      27
-#elif defined(CONFIG_ISA_M32R2) || defined(CONFIG_ISA_M32R)
-#define PT_ACCH                15
-#define PT_ACCL                16
-#define PT_PSW         17
-#define PT_BPC         18
-#define PT_BBPSW       19
-#define PT_BBPC                20
-#define PT_SPU         21
-#define PT_FP          22
-#define PT_LR          23
-#define PT_SPI         24
-#define PT_ORIGR0      25
-#else
-#error unknown isa conifiguration
-#endif
 
 /* virtual pt_reg entry for gdb */
 #define PT_PC          30
@@ -121,6 +114,8 @@ struct pt_regs {
 #elif defined(CONFIG_ISA_M32R2) || defined(CONFIG_ISA_M32R)
        unsigned long acch;
        unsigned long accl;
+       unsigned long dummy_acc1h;
+       unsigned long dummy_acc1l;
 #else
 #error unknown isa configuration
 #endif
index bf447c52a0a126c8a26719885d5e081f73c3c728..81750edc8916267e035dcf47484afe001910c74a 100644 (file)
@@ -9,7 +9,7 @@
  * SMP- and interrupt-safe semaphores..
  *
  * Copyright (C) 1996  Linus Torvalds
- * Copyright (C) 2004  Hirokazu Takata <takata at linux-m32r.org>
+ * Copyright (C) 2004, 2006  Hirokazu Takata <takata at linux-m32r.org>
  */
 
 #include <linux/config.h>
@@ -77,27 +77,8 @@ asmlinkage void __up(struct semaphore * sem);
  */
 static inline void down(struct semaphore * sem)
 {
-       unsigned long flags;
-       long count;
-
        might_sleep();
-       local_irq_save(flags);
-       __asm__ __volatile__ (
-               "# down                         \n\t"
-               DCACHE_CLEAR("%0", "r4", "%1")
-               M32R_LOCK" %0, @%1;             \n\t"
-               "addi   %0, #-1;                \n\t"
-               M32R_UNLOCK" %0, @%1;           \n\t"
-               : "=&r" (count)
-               : "r" (&sem->count)
-               : "memory"
-#ifdef CONFIG_CHIP_M32700_TS1
-               , "r4"
-#endif /* CONFIG_CHIP_M32700_TS1 */
-       );
-       local_irq_restore(flags);
-
-       if (unlikely(count < 0))
+       if (unlikely(atomic_dec_return(&sem->count) < 0))
                __down(sem);
 }
 
@@ -107,28 +88,10 @@ static inline void down(struct semaphore * sem)
  */
 static inline int down_interruptible(struct semaphore * sem)
 {
-       unsigned long flags;
-       long count;
        int result = 0;
 
        might_sleep();
-       local_irq_save(flags);
-       __asm__ __volatile__ (
-               "# down_interruptible           \n\t"
-               DCACHE_CLEAR("%0", "r4", "%1")
-               M32R_LOCK" %0, @%1;             \n\t"
-               "addi   %0, #-1;                \n\t"
-               M32R_UNLOCK" %0, @%1;           \n\t"
-               : "=&r" (count)
-               : "r" (&sem->count)
-               : "memory"
-#ifdef CONFIG_CHIP_M32700_TS1
-               , "r4"
-#endif /* CONFIG_CHIP_M32700_TS1 */
-       );
-       local_irq_restore(flags);
-
-       if (unlikely(count < 0))
+       if (unlikely(atomic_dec_return(&sem->count) < 0))
                result = __down_interruptible(sem);
 
        return result;
@@ -174,26 +137,7 @@ static inline int down_trylock(struct semaphore * sem)
  */
 static inline void up(struct semaphore * sem)
 {
-       unsigned long flags;
-       long count;
-
-       local_irq_save(flags);
-       __asm__ __volatile__ (
-               "# up                           \n\t"
-               DCACHE_CLEAR("%0", "r4", "%1")
-               M32R_LOCK" %0, @%1;             \n\t"
-               "addi   %0, #1;                 \n\t"
-               M32R_UNLOCK" %0, @%1;           \n\t"
-               : "=&r" (count)
-               : "r" (&sem->count)
-               : "memory"
-#ifdef CONFIG_CHIP_M32700_TS1
-               , "r4"
-#endif /* CONFIG_CHIP_M32700_TS1 */
-       );
-       local_irq_restore(flags);
-
-       if (unlikely(count <= 0))
+       if (unlikely(atomic_inc_return(&sem->count) <= 0))
                __up(sem);
 }
 
index c233e2def2a3d198fd881c7e5f2e153b8763a0a3..942b8a30937df79deb9ac1dc76bb8cd27862afd9 100644 (file)
@@ -32,6 +32,8 @@ struct sigcontext {
 #elif defined(CONFIG_ISA_M32R2) || defined(CONFIG_ISA_M32R)
        unsigned long sc_acch;
        unsigned long sc_accl;
+       unsigned long sc_dummy_acc1h;
+       unsigned long sc_dummy_acc1l;
 #else
 #error unknown isa configuration
 #endif
index 7885b7df84a2b5209d26bfd639f28082999f9728..1184293e57127c532b47477c2003e37f22749f45 100644 (file)
@@ -67,7 +67,8 @@ extern volatile int cpu_2_physid[NR_CPUS];
 #define raw_smp_processor_id() (current_thread_info()->cpu)
 
 extern cpumask_t cpu_callout_map;
-#define cpu_possible_map cpu_callout_map
+extern cpumask_t cpu_possible_map;
+extern cpumask_t cpu_present_map;
 
 static __inline__ int hard_smp_processor_id(void)
 {
index d6a2c613be68abff0d8a8d58de9bddbbf2800ac2..e55013f378e582357df670aee5638e62e8e5a2af 100644 (file)
@@ -6,8 +6,8 @@
  * License.  See the file "COPYING" in the main directory of this archive
  * for more details.
  *
- * Copyright (C) 2001  by Hiroyuki Kondo, Hirokazu Takata, and Hitoshi Yamamoto
- * Copyright (C) 2004  Hirokazu Takata <takata at linux-m32r.org>
+ * Copyright (C) 2001  Hiroyuki Kondo, Hirokazu Takata, and Hitoshi Yamamoto
+ * Copyright (C) 2004, 2006  Hirokazu Takata <takata at linux-m32r.org>
  */
 
 #include <linux/config.h>
  * switch_to(prev, next) should switch from task `prev' to `next'
  * `prev' will never be the same as `next'.
  *
- * `next' and `prev' should be struct task_struct, but it isn't always defined
+ * `next' and `prev' should be task_t, but it isn't always defined
  */
 
-#ifndef CONFIG_SMP
-#define prepare_to_switch()  do { } while(0)
-#endif /* not CONFIG_SMP */
-
 #define switch_to(prev, next, last)  do { \
-       register unsigned long  arg0 __asm__ ("r0") = (unsigned long)prev; \
-       register unsigned long  arg1 __asm__ ("r1") = (unsigned long)next; \
-       register unsigned long  *oldsp __asm__ ("r2") = &(prev->thread.sp); \
-       register unsigned long  *newsp __asm__ ("r3") = &(next->thread.sp); \
-       register unsigned long  *oldlr __asm__ ("r4") = &(prev->thread.lr); \
-       register unsigned long  *newlr __asm__ ("r5") = &(next->thread.lr); \
-       register struct task_struct  *__last __asm__ ("r6"); \
        __asm__ __volatile__ ( \
-               "st     r8, @-r15                                 \n\t" \
-               "st     r9, @-r15                                 \n\t" \
-               "st    r10, @-r15                                 \n\t" \
-               "st    r11, @-r15                                 \n\t" \
-               "st    r12, @-r15                                 \n\t" \
-               "st    r13, @-r15                                 \n\t" \
-               "st    r14, @-r15                                 \n\t" \
-               "seth  r14, #high(1f)                             \n\t" \
-               "or3   r14, r14, #low(1f)                         \n\t" \
-               "st    r14, @r4    ; store old LR                 \n\t" \
-               "st    r15, @r2    ; store old SP                 \n\t" \
-               "ld    r15, @r3    ; load new SP                  \n\t" \
-               "st     r0, @-r15  ; store 'prev' onto new stack  \n\t" \
-               "ld    r14, @r5    ; load new LR                  \n\t" \
-               "jmp   r14                                        \n\t" \
-               ".fillinsn                                        \n  " \
-               "1:                                               \n\t" \
-               "ld     r6, @r15+  ; load 'prev' from new stack   \n\t" \
-               "ld    r14, @r15+                                 \n\t" \
-               "ld    r13, @r15+                                 \n\t" \
-               "ld    r12, @r15+                                 \n\t" \
-               "ld    r11, @r15+                                 \n\t" \
-               "ld    r10, @r15+                                 \n\t" \
-               "ld     r9, @r15+                                 \n\t" \
-               "ld     r8, @r15+                                 \n\t" \
-               : "=&r" (__last) \
-               : "r" (arg0), "r" (arg1), "r" (oldsp), "r" (newsp), \
-                 "r" (oldlr), "r" (newlr) \
-               : "memory" \
+               "       seth    lr, #high(1f)                           \n" \
+               "       or3     lr, lr, #low(1f)                        \n" \
+               "       st      lr, @%4  ; store old LR                 \n" \
+               "       ld      lr, @%5  ; load new LR                  \n" \
+               "       st      sp, @%2  ; store old SP                 \n" \
+               "       ld      sp, @%3  ; load new SP                  \n" \
+               "       push    %1  ; store `prev' on new stack         \n" \
+               "       jmp     lr                                      \n" \
+               "       .fillinsn                                       \n" \
+               "1:                                                     \n" \
+               "       pop     %0  ; restore `__last' from new stack   \n" \
+               : "=r" (last) \
+               : "0" (prev), \
+                 "r" (&(prev->thread.sp)), "r" (&(next->thread.sp)), \
+                 "r" (&(prev->thread.lr)), "r" (&(next->thread.lr)) \
+               : "memory", "lr" \
        ); \
-       last = __last; \
 } while(0)
 
 /*
@@ -171,8 +146,8 @@ extern void  __xchg_called_with_bad_pointer(void);
 #define DCACHE_CLEAR(reg0, reg1, addr)
 #endif /* CONFIG_CHIP_M32700_TS1 */
 
-static __inline__ unsigned long __xchg(unsigned long x, volatile void * ptr,
-       int size)
+static inline unsigned long
+__xchg(unsigned long x, volatile void * ptr, int size)
 {
        unsigned long flags;
        unsigned long tmp = 0;
@@ -224,7 +199,7 @@ static __inline__ unsigned long __xchg(unsigned long x, volatile void * ptr,
 
 #define __HAVE_ARCH_CMPXCHG    1
 
-static __inline__ unsigned long
+static inline unsigned long
 __cmpxchg_u32(volatile unsigned int *p, unsigned int old, unsigned int new)
 {
        unsigned long flags;
@@ -258,7 +233,7 @@ __cmpxchg_u32(volatile unsigned int *p, unsigned int old, unsigned int new)
    if something tries to do an invalid cmpxchg().  */
 extern void __cmpxchg_called_with_bad_pointer(void);
 
-static __inline__ unsigned long
+static inline unsigned long
 __cmpxchg(volatile void *ptr, unsigned long old, unsigned long new, int size)
 {
        switch (size) {
index e8ae61956a5134fd3dab8d946fc152ffd6a22923..819cc28a94f7c430e977064ccd84f2052406795e 100644 (file)
@@ -5,17 +5,9 @@
  *  linux/include/asm-m32r/uaccess.h
  *
  *  M32R version.
- *    Copyright (C) 2004  Hirokazu Takata <takata at linux-m32r.org>
+ *    Copyright (C) 2004, 2006  Hirokazu Takata <takata at linux-m32r.org>
  */
 
-#undef UACCESS_DEBUG
-
-#ifdef UACCESS_DEBUG
-#define UAPRINTK(args...) printk(args)
-#else
-#define UAPRINTK(args...)
-#endif /* UACCESS_DEBUG */
-
 /*
  * User space memory access functions
  */
 #define MAKE_MM_SEG(s) ((mm_segment_t) { (s) })
 
 #ifdef CONFIG_MMU
+
 #define KERNEL_DS      MAKE_MM_SEG(0xFFFFFFFF)
 #define USER_DS                MAKE_MM_SEG(PAGE_OFFSET)
-#else
-#define KERNEL_DS      MAKE_MM_SEG(0xFFFFFFFF)
-#define USER_DS                MAKE_MM_SEG(0xFFFFFFFF)
-#endif /* CONFIG_MMU */
-
 #define get_ds()       (KERNEL_DS)
-#ifdef CONFIG_MMU
 #define get_fs()       (current_thread_info()->addr_limit)
 #define set_fs(x)      (current_thread_info()->addr_limit = (x))
-#else
+
+#else /* not CONFIG_MMU */
+
+#define KERNEL_DS      MAKE_MM_SEG(0xFFFFFFFF)
+#define USER_DS                MAKE_MM_SEG(0xFFFFFFFF)
+#define get_ds()       (KERNEL_DS)
+
 static inline mm_segment_t get_fs(void)
 {
-  return USER_DS;
+       return USER_DS;
 }
 
 static inline void set_fs(mm_segment_t s)
 {
 }
-#endif /* CONFIG_MMU */
+
+#endif /* not CONFIG_MMU */
 
 #define segment_eq(a,b)        ((a).seg == (b).seg)
 
@@ -83,9 +77,9 @@ static inline void set_fs(mm_segment_t s)
                "       subx    %0, %0\n"                               \
                "       cmpu    %4, %1\n"                               \
                "       subx    %0, %5\n"                               \
-               : "=&r"(flag), "=r"(sum)                                \
-               : "1"(addr), "r"((int)(size)),                          \
-                 "r"(current_thread_info()->addr_limit.seg), "r"(0)    \
+               : "=&r" (flag), "=r" (sum)                              \
+               : "1" (addr), "r" ((int)(size)),                        \
+                 "r" (current_thread_info()->addr_limit.seg), "r" (0)  \
                : "cbit" );                                             \
        flag; })
 
@@ -113,10 +107,10 @@ static inline void set_fs(mm_segment_t s)
 #else
 static inline int access_ok(int type, const void *addr, unsigned long size)
 {
-  extern unsigned long memory_start, memory_end;
-  unsigned long val = (unsigned long)addr;
+       extern unsigned long memory_start, memory_end;
+       unsigned long val = (unsigned long)addr;
 
-  return ((val >= memory_start) && ((val + size) < memory_end));
+       return ((val >= memory_start) && ((val + size) < memory_end));
 }
 #endif /* CONFIG_MMU */
 
@@ -155,39 +149,6 @@ extern int fixup_exception(struct pt_regs *regs);
  * accesses to the same area of user memory).
  */
 
-extern void __get_user_1(void);
-extern void __get_user_2(void);
-extern void __get_user_4(void);
-
-#ifndef MODULE
-#define __get_user_x(size,ret,x,ptr)                                   \
-       __asm__ __volatile__(                                           \
-               "       mv      r0, %0\n"                               \
-               "       mv      r1, %1\n"                               \
-               "       bl __get_user_" #size "\n"                      \
-               "       mv      %0, r0\n"                               \
-               "       mv      %1, r1\n"                               \
-               : "=r"(ret), "=r"(x)                                    \
-               : "0"(ptr)                                              \
-               : "r0", "r1", "r14" )
-#else /* MODULE */
-/*
- * Use "jl" instead of "bl" for MODULE
- */
-#define __get_user_x(size,ret,x,ptr)                                   \
-       __asm__ __volatile__(                                           \
-               "       mv      r0, %0\n"                               \
-               "       mv      r1, %1\n"                               \
-               "       seth    lr, #high(__get_user_" #size ")\n"      \
-               "       or3     lr, lr, #low(__get_user_" #size ")\n"   \
-               "       jl      lr\n"                                   \
-               "       mv      %0, r0\n"                               \
-               "       mv      %1, r1\n"                               \
-               : "=r"(ret), "=r"(x)                                    \
-               : "0"(ptr)                                              \
-               : "r0", "r1", "r14" )
-#endif
-
 /* Careful: we have to cast the result to the type of the pointer for sign
    reasons */
 /**
@@ -208,20 +169,7 @@ extern void __get_user_4(void);
  * On error, the variable @x is set to zero.
  */
 #define get_user(x,ptr)                                                        \
-({     int __ret_gu;                                                   \
-       unsigned long __val_gu;                                         \
-       __chk_user_ptr(ptr);                                            \
-       switch(sizeof (*(ptr))) {                                       \
-       case 1:  __get_user_x(1,__ret_gu,__val_gu,ptr); break;          \
-       case 2:  __get_user_x(2,__ret_gu,__val_gu,ptr); break;          \
-       case 4:  __get_user_x(4,__ret_gu,__val_gu,ptr); break;          \
-       default: __get_user_x(X,__ret_gu,__val_gu,ptr); break;          \
-       }                                                               \
-       (x) = (__typeof__(*(ptr)))__val_gu;                             \
-       __ret_gu;                                                       \
-})
-
-extern void __put_user_bad(void);
+       __get_user_check((x),(ptr),sizeof(*(ptr)))
 
 /**
  * put_user: - Write a simple value into user space.
@@ -240,8 +188,7 @@ extern void __put_user_bad(void);
  * Returns zero on success, or -EFAULT on error.
  */
 #define put_user(x,ptr)                                                        \
-  __put_user_check((__typeof__(*(ptr)))(x),(ptr),sizeof(*(ptr)))
-
+       __put_user_check((__typeof__(*(ptr)))(x),(ptr),sizeof(*(ptr)))
 
 /**
  * __get_user: - Get a simple variable from user space, with less checking.
@@ -264,8 +211,64 @@ extern void __put_user_bad(void);
  * On error, the variable @x is set to zero.
  */
 #define __get_user(x,ptr) \
-  __get_user_nocheck((x),(ptr),sizeof(*(ptr)))
+       __get_user_nocheck((x),(ptr),sizeof(*(ptr)))
 
+#define __get_user_nocheck(x,ptr,size)                                 \
+({                                                                     \
+       long __gu_err = 0;                                              \
+       unsigned long __gu_val;                                         \
+       might_sleep();                                                  \
+       __get_user_size(__gu_val,(ptr),(size),__gu_err);                \
+       (x) = (__typeof__(*(ptr)))__gu_val;                             \
+       __gu_err;                                                       \
+})
+
+#define __get_user_check(x,ptr,size)                                   \
+({                                                                     \
+       long __gu_err = -EFAULT;                                        \
+       unsigned long __gu_val = 0;                                     \
+       const __typeof__(*(ptr)) __user *__gu_addr = (ptr);             \
+       might_sleep();                                                  \
+       if (access_ok(VERIFY_READ,__gu_addr,size))                      \
+               __get_user_size(__gu_val,__gu_addr,(size),__gu_err);    \
+       (x) = (__typeof__(*(ptr)))__gu_val;                             \
+       __gu_err;                                                       \
+})
+
+extern long __get_user_bad(void);
+
+#define __get_user_size(x,ptr,size,retval)                             \
+do {                                                                   \
+       retval = 0;                                                     \
+       __chk_user_ptr(ptr);                                            \
+       switch (size) {                                                 \
+         case 1: __get_user_asm(x,ptr,retval,"ub"); break;             \
+         case 2: __get_user_asm(x,ptr,retval,"uh"); break;             \
+         case 4: __get_user_asm(x,ptr,retval,""); break;               \
+         default: (x) = __get_user_bad();                              \
+       }                                                               \
+} while (0)
+
+#define __get_user_asm(x, addr, err, itype)                            \
+       __asm__ __volatile__(                                           \
+               "       .fillinsn\n"                                    \
+               "1:     ld"itype" %1,@%2\n"                             \
+               "       .fillinsn\n"                                    \
+               "2:\n"                                                  \
+               ".section .fixup,\"ax\"\n"                              \
+               "       .balign 4\n"                                    \
+               "3:     ldi %0,%3\n"                                    \
+               "       seth r14,#high(2b)\n"                           \
+               "       or3 r14,r14,#low(2b)\n"                         \
+               "       jmp r14\n"                                      \
+               ".previous\n"                                           \
+               ".section __ex_table,\"a\"\n"                           \
+               "       .balign 4\n"                                    \
+               "       .long 1b,3b\n"                                  \
+               ".previous"                                             \
+               : "=&r" (err), "=&r" (x)                                \
+               : "r" (addr), "i" (-EFAULT), "0" (err)                  \
+               : "r14", "memory")
 
 /**
  * __put_user: - Write a simple value into user space, with less checking.
@@ -287,11 +290,13 @@ extern void __put_user_bad(void);
  * Returns zero on success, or -EFAULT on error.
  */
 #define __put_user(x,ptr) \
-  __put_user_nocheck((__typeof__(*(ptr)))(x),(ptr),sizeof(*(ptr)))
+       __put_user_nocheck((__typeof__(*(ptr)))(x),(ptr),sizeof(*(ptr)))
+
 
 #define __put_user_nocheck(x,ptr,size)                                 \
 ({                                                                     \
        long __pu_err;                                                  \
+       might_sleep();                                                  \
        __put_user_size((x),(ptr),(size),__pu_err);                     \
        __pu_err;                                                       \
 })
@@ -308,28 +313,28 @@ extern void __put_user_bad(void);
 })
 
 #if defined(__LITTLE_ENDIAN__)
-#define __put_user_u64(x, addr, err)                                    \
-        __asm__ __volatile__(                                           \
-                "       .fillinsn\n"                                    \
-                "1:     st %L1,@%2\n"                                    \
-                "       .fillinsn\n"                                    \
-                "2:     st %H1,@(4,%2)\n"                                \
-                "       .fillinsn\n"                                    \
-                "3:\n"                                                  \
-                ".section .fixup,\"ax\"\n"                              \
-                "       .balign 4\n"                                    \
-                "4:     ldi %0,%3\n"                                    \
-                "       seth r14,#high(3b)\n"                           \
-                "       or3 r14,r14,#low(3b)\n"                         \
-                "       jmp r14\n"                                      \
-                ".previous\n"                                           \
-                ".section __ex_table,\"a\"\n"                           \
-                "       .balign 4\n"                                    \
-                "       .long 1b,4b\n"                                  \
-                "       .long 2b,4b\n"                                  \
-                ".previous"                                             \
-                : "=&r"(err)                                             \
-                : "r"(x), "r"(addr), "i"(-EFAULT), "0"(err)            \
+#define __put_user_u64(x, addr, err)                                   \
+        __asm__ __volatile__(                                          \
+                "       .fillinsn\n"                                   \
+                "1:     st %L1,@%2\n"                                  \
+                "       .fillinsn\n"                                   \
+                "2:     st %H1,@(4,%2)\n"                              \
+                "       .fillinsn\n"                                   \
+                "3:\n"                                                 \
+                ".section .fixup,\"ax\"\n"                             \
+                "       .balign 4\n"                                   \
+                "4:     ldi %0,%3\n"                                   \
+                "       seth r14,#high(3b)\n"                          \
+                "       or3 r14,r14,#low(3b)\n"                                \
+                "       jmp r14\n"                                     \
+                ".previous\n"                                          \
+                ".section __ex_table,\"a\"\n"                          \
+                "       .balign 4\n"                                   \
+                "       .long 1b,4b\n"                                 \
+                "       .long 2b,4b\n"                                 \
+                ".previous"                                            \
+                : "=&r" (err)                                          \
+                : "r" (x), "r" (addr), "i" (-EFAULT), "0" (err)                \
                 : "r14", "memory")
 
 #elif defined(__BIG_ENDIAN__)
@@ -353,13 +358,15 @@ extern void __put_user_bad(void);
                "       .long 1b,4b\n"                                  \
                "       .long 2b,4b\n"                                  \
                ".previous"                                             \
-               : "=&r"(err)                                            \
-               : "r"(x), "r"(addr), "i"(-EFAULT), "0"(err)             \
+               : "=&r" (err)                                           \
+               : "r" (x), "r" (addr), "i" (-EFAULT), "0" (err)         \
                : "r14", "memory")
 #else
 #error no endian defined
 #endif
 
+extern void __put_user_bad(void);
+
 #define __put_user_size(x,ptr,size,retval)                             \
 do {                                                                   \
        retval = 0;                                                     \
@@ -398,52 +405,8 @@ struct __large_struct { unsigned long buf[100]; };
                "       .balign 4\n"                                    \
                "       .long 1b,3b\n"                                  \
                ".previous"                                             \
-               : "=&r"(err)                                            \
-               : "r"(x), "r"(addr), "i"(-EFAULT), "0"(err)             \
-               : "r14", "memory")
-
-#define __get_user_nocheck(x,ptr,size)                                 \
-({                                                                     \
-       long __gu_err;                                                  \
-       unsigned long __gu_val;                                         \
-       __get_user_size(__gu_val,(ptr),(size),__gu_err);                \
-       (x) = (__typeof__(*(ptr)))__gu_val;                             \
-       __gu_err;                                                       \
-})
-
-extern long __get_user_bad(void);
-
-#define __get_user_size(x,ptr,size,retval)                             \
-do {                                                                   \
-       retval = 0;                                                     \
-       __chk_user_ptr(ptr);                                            \
-       switch (size) {                                                 \
-         case 1: __get_user_asm(x,ptr,retval,"ub"); break;             \
-         case 2: __get_user_asm(x,ptr,retval,"uh"); break;             \
-         case 4: __get_user_asm(x,ptr,retval,""); break;               \
-         default: (x) = __get_user_bad();                              \
-       }                                                               \
-} while (0)
-
-#define __get_user_asm(x, addr, err, itype)                            \
-       __asm__ __volatile__(                                           \
-               "       .fillinsn\n"                                    \
-               "1:     ld"itype" %1,@%2\n"                             \
-               "       .fillinsn\n"                                    \
-               "2:\n"                                                  \
-               ".section .fixup,\"ax\"\n"                              \
-               "       .balign 4\n"                                    \
-               "3:     ldi %0,%3\n"                                    \
-               "       seth r14,#high(2b)\n"                           \
-               "       or3 r14,r14,#low(2b)\n"                         \
-               "       jmp r14\n"                                      \
-               ".previous\n"                                           \
-               ".section __ex_table,\"a\"\n"                           \
-               "       .balign 4\n"                                    \
-               "       .long 1b,3b\n"                                  \
-               ".previous"                                             \
-               : "=&r"(err), "=&r"(x)                                  \
-               : "r"(addr), "i"(-EFAULT), "0"(err)                     \
+               : "=&r" (err)                                           \
+               : "r" (x), "r" (addr), "i" (-EFAULT), "0" (err)         \
                : "r14", "memory")
 
 /*
@@ -453,7 +416,6 @@ do {                                                                        \
  * anything, so this is accurate.
  */
 
-
 /*
  * Copy To/From Userspace
  */
@@ -511,8 +473,9 @@ do {                                                                        \
                "       .long 2b,9b\n"                                  \
                "       .long 3b,9b\n"                                  \
                ".previous\n"                                           \
-               : "=&r"(__dst), "=&r"(__src), "=&r"(size), "=&r"(__c)   \
-               : "0"(to), "1"(from), "2"(size), "3"(size / 4)          \
+               : "=&r" (__dst), "=&r" (__src), "=&r" (size),           \
+                 "=&r" (__c)                                           \
+               : "0" (to), "1" (from), "2" (size), "3" (size / 4)      \
                : "r14", "memory");                                     \
 } while (0)
 
@@ -573,8 +536,9 @@ do {                                                                        \
                "       .long 2b,7b\n"                                  \
                "       .long 3b,7b\n"                                  \
                ".previous\n"                                           \
-               : "=&r"(__dst), "=&r"(__src), "=&r"(size), "=&r"(__c)   \
-               : "0"(to), "1"(from), "2"(size), "3"(size / 4)          \
+               : "=&r" (__dst), "=&r" (__src), "=&r" (size),           \
+                 "=&r" (__c)                                           \
+               : "0" (to), "1" (from), "2" (size), "3" (size / 4)      \
                : "r14", "memory");                                     \
 } while (0)
 
@@ -676,7 +640,7 @@ unsigned long __generic_copy_from_user(void *, const void __user *, unsigned lon
 #define copy_from_user(to,from,n)                      \
 ({                                                     \
        might_sleep();                                  \
-__generic_copy_from_user((to),(from),(n));     \
+       __generic_copy_from_user((to),(from),(n));      \
 })
 
 long __must_check strncpy_from_user(char *dst, const char __user *src,
index 39be87ca2a5a7cf7966621e11b9cf007ba6c388f..be0eb014c3b0c99b745e9de701fd660fc2849714 100644 (file)
 #define __NR_mq_timedreceive   (__NR_mq_open+3)
 #define __NR_mq_notify         (__NR_mq_open+4)
 #define __NR_mq_getsetattr     (__NR_mq_open+5)
-#define __NR_sys_kexec_load    283
+#define __NR_kexec_load                283
 #define __NR_waitid            284
 
 #define NR_syscalls 285
index 30b18ea6cb1116fd12e86094788c5917fe9f7e99..f54aa147ec19066ac6aa9f729f72e78f35958153 100644 (file)
 #ifdef CONFIG_64BIT
 #include <asm/asmmacro-64.h>
 #endif
+#ifdef CONFIG_MIPS_MT_SMTC
+#include <asm/mipsmtregs.h>
+#endif
 
+#ifdef CONFIG_MIPS_MT_SMTC
+       .macro  local_irq_enable reg=t0
+       mfc0    \reg, CP0_TCSTATUS
+       ori     \reg, \reg, TCSTATUS_IXMT
+       xori    \reg, \reg, TCSTATUS_IXMT
+       mtc0    \reg, CP0_TCSTATUS
+       ehb
+       .endm
+
+       .macro  local_irq_disable reg=t0
+       mfc0    \reg, CP0_TCSTATUS
+       ori     \reg, \reg, TCSTATUS_IXMT
+       mtc0    \reg, CP0_TCSTATUS
+       ehb
+       .endm
+#else
        .macro  local_irq_enable reg=t0
        mfc0    \reg, CP0_STATUS
        ori     \reg, \reg, 1
@@ -32,6 +51,7 @@
        mtc0    \reg, CP0_STATUS
        irq_disable_hazard
        .endm
+#endif /* CONFIG_MIPS_MT_SMTC */
 
 #ifdef CONFIG_CPU_SB1
        .macro  fpu_enable_hazard
        .endm
 #endif
 
+/*
+ * Temporary until all gas have MT ASE support
+ */
+       .macro  DMT     reg=0
+       .word   (0x41600bc1 | (\reg << 16))
+       .endm
+
+       .macro  EMT     reg=0
+       .word   (0x41600be1 | (\reg << 16))
+       .endm
+
+       .macro  DVPE    reg=0
+       .word   (0x41600001 | (\reg << 16))
+       .endm
+
+       .macro  EVPE    reg=0
+       .word   (0x41600021 | (\reg << 16))
+       .endm
+
+       .macro  MFTR    rt=0, rd=0, u=0, sel=0
+        .word  (0x41000000 | (\rt << 16) | (\rd << 11) | (\u << 5) | (\sel))
+       .endm
+
+       .macro  MTTR    rt=0, rd=0, u=0, sel=0
+        .word  (0x41800000 | (\rt << 16) | (\rd << 11) | (\u << 5) | (\sel))
+       .endm
+
 #endif /* _ASM_ASMMACRO_H */
index aeae9fabf4a9be581937ce767a2eb4af1c6c3979..47bc8f6c20d2e2795211335e37cbb4e01489e0c2 100644 (file)
@@ -74,6 +74,7 @@ static inline void copy_from_user_page(struct vm_area_struct *vma,
 
 extern void (*flush_cache_sigtramp)(unsigned long addr);
 extern void (*flush_icache_all)(void);
+extern void (*local_flush_data_cache_page)(void * addr);
 extern void (*flush_data_cache_page)(unsigned long addr);
 
 /*
index 3f2b6d9ac45e73a5a770f878eab547cc33641785..254e11ed247b04cc4085782a51bd067f21db9e1b 100644 (file)
@@ -40,7 +40,7 @@
 #define cpu_has_sb1_cache      (cpu_data[0].options & MIPS_CPU_SB1_CACHE)
 #endif
 #ifndef cpu_has_fpu
-#define cpu_has_fpu            (cpu_data[0].options & MIPS_CPU_FPU)
+#define cpu_has_fpu            (current_cpu_data.options & MIPS_CPU_FPU)
 #endif
 #ifndef cpu_has_32fpr
 #define cpu_has_32fpr          (cpu_data[0].options & MIPS_CPU_32FPR)
index 140be1c67da7c734d38471df1ebe0ebf80ad9e1c..6572ac703662068da6de5ad81c8b952aec4ee591 100644 (file)
@@ -73,6 +73,16 @@ struct cpuinfo_mips {
        struct cache_desc       dcache; /* Primary D or combined I/D cache */
        struct cache_desc       scache; /* Secondary cache */
        struct cache_desc       tcache; /* Tertiary/split secondary cache */
+#if defined(CONFIG_MIPS_MT_SMTC)
+       /*
+        * In the MIPS MT "SMTC" model, each TC is considered
+        * to be a "CPU" for the purposes of scheduling, but
+        * exception resources, ASID spaces, etc, are common
+        * to all TCs within the same VPE.
+        */
+       int                     vpe_id;  /* Virtual Processor number */
+       int                     tc_id;   /* Thread Context number */
+#endif /* CONFIG_MIPS_MT */
        void                    *data;  /* Additional data */
 } __attribute__((aligned(SMP_CACHE_BYTES)));
 
diff --git a/include/asm-mips/ds1742.h b/include/asm-mips/ds1742.h
new file mode 100644 (file)
index 0000000..c2f2c32
--- /dev/null
@@ -0,0 +1,13 @@
+/*
+ * This file is subject to the terms and conditions of the GNU General Public
+ * License.  See the file "COPYING" in the main directory of this archive
+ * for more details.
+ *
+ * Copyright (C) 2006 by Ralf Baechle (ralf@linux-mips.org)
+ */
+#ifndef _ASM_DS1742_H
+#define _ASM_DS1742_H
+
+#include <ds1742.h>
+
+#endif /* _ASM_DS1742_H */
index 851f013adad34a4541dad2cfce71f1823cfd15bb..bdc9de2df1ef28d52644252ab060de9969f6ab2c 100644 (file)
 #define SHT_MIPS_CONFLICT      0x70000002
 #define SHT_MIPS_GPTAB         0x70000003
 #define SHT_MIPS_UCODE         0x70000004
-
-#define SHF_MIPS_GPREL 0x10000000
+#define SHT_MIPS_DEBUG         0x70000005
+#define SHT_MIPS_REGINFO       0x70000006
+#define SHT_MIPS_PACKAGE       0x70000007
+#define SHT_MIPS_PACKSYM       0x70000008
+#define SHT_MIPS_RELD          0x70000009
+#define SHT_MIPS_IFACE         0x7000000b
+#define SHT_MIPS_CONTENT       0x7000000c
+#define SHT_MIPS_OPTIONS       0x7000000d
+#define SHT_MIPS_SHDR          0x70000010
+#define SHT_MIPS_FDESC         0x70000011
+#define SHT_MIPS_EXTSYM                0x70000012
+#define SHT_MIPS_DENSE         0x70000013
+#define SHT_MIPS_PDESC         0x70000014
+#define SHT_MIPS_LOCSYM                0x70000015
+#define SHT_MIPS_AUXSYM                0x70000016
+#define SHT_MIPS_OPTSYM                0x70000017
+#define SHT_MIPS_LOCSTR                0x70000018
+#define SHT_MIPS_LINE          0x70000019
+#define SHT_MIPS_RFDESC                0x7000001a
+#define SHT_MIPS_DELTASYM      0x7000001b
+#define SHT_MIPS_DELTAINST     0x7000001c
+#define SHT_MIPS_DELTACLASS    0x7000001d
+#define SHT_MIPS_DWARF         0x7000001e
+#define SHT_MIPS_DELTADECL     0x7000001f
+#define SHT_MIPS_SYMBOL_LIB    0x70000020
+#define SHT_MIPS_EVENTS                0x70000021
+#define SHT_MIPS_TRANSLATE     0x70000022
+#define SHT_MIPS_PIXIE         0x70000023
+#define SHT_MIPS_XLATE         0x70000024
+#define SHT_MIPS_XLATE_DEBUG   0x70000025
+#define SHT_MIPS_WHIRL         0x70000026
+#define SHT_MIPS_EH_REGION     0x70000027
+#define SHT_MIPS_XLATE_OLD     0x70000028
+#define SHT_MIPS_PDR_EXCEPTION 0x70000029
+
+#define SHF_MIPS_GPREL         0x10000000
+#define SHF_MIPS_MERGE         0x20000000
+#define SHF_MIPS_ADDR          0x40000000
+#define SHF_MIPS_STRING                0x80000000
+#define SHF_MIPS_NOSTRIP       0x08000000
+#define SHF_MIPS_LOCAL         0x04000000
+#define SHF_MIPS_NAMES         0x02000000
+#define SHF_MIPS_NODUPES       0x01000000
 
 #ifndef ELF_ARCH
 /* ELF register definitions */
index 9c828b1f821875e273bdd3da8f9a6b3fcf98e27b..b0f50015e25253688fd24e6154f48d70710d5fa3 100644 (file)
 #include <asm/processor.h>
 #include <asm/current.h>
 
+#ifdef CONFIG_MIPS_MT_FPAFF
+#include <asm/mips_mt.h>
+#endif
+
 struct sigcontext;
 struct sigcontext32;
 
index feb29a79388869199d0331fae77273a1d0473873..dadc05188db717c288ab9ecd6a86d483e4731119 100644 (file)
@@ -284,6 +284,8 @@ do {                                                                        \
 #define instruction_hazard() do { } while (0)
 #endif
 
+extern void mips_ihb(void);
+
 #endif /* __ASSEMBLY__ */
 
 #endif /* _ASM_HAZARDS_H */
index 774348734fa0b38a8fbe916972a966a59302be17..4bb9c06f44107006f4c6330df7f0aedb23bc96a2 100644 (file)
@@ -19,7 +19,12 @@ __asm__ (
        "       .set    push                                            \n"
        "       .set    reorder                                         \n"
        "       .set    noat                                            \n"
-#ifdef CONFIG_CPU_MIPSR2
+#ifdef CONFIG_MIPS_MT_SMTC
+       "       mfc0    $1, $2, 1       # SMTC - clear TCStatus.IXMT    \n"
+       "       ori     $1, 0x400                                       \n"
+       "       xori    $1, 0x400                                       \n"
+       "       mtc0    $1, $2, 1                                       \n"
+#elif defined(CONFIG_CPU_MIPSR2)
        "       ei                                                      \n"
 #else
        "       mfc0    $1,$12                                          \n"
@@ -62,7 +67,12 @@ __asm__ (
        "       .macro  local_irq_disable\n"
        "       .set    push                                            \n"
        "       .set    noat                                            \n"
-#ifdef CONFIG_CPU_MIPSR2
+#ifdef CONFIG_MIPS_MT_SMTC
+       "       mfc0    $1, $2, 1                                       \n"
+       "       ori     $1, 0x400                                       \n"
+       "       .set    noreorder                                       \n"
+       "       mtc0    $1, $2, 1                                       \n"
+#elif defined(CONFIG_CPU_MIPSR2)
        "       di                                                      \n"
 #else
        "       mfc0    $1,$12                                          \n"
@@ -88,7 +98,11 @@ __asm__ (
        "       .macro  local_save_flags flags                          \n"
        "       .set    push                                            \n"
        "       .set    reorder                                         \n"
+#ifdef CONFIG_MIPS_MT_SMTC
+       "       mfc0    \\flags, $2, 1                                  \n"
+#else
        "       mfc0    \\flags, $12                                    \n"
+#endif
        "       .set    pop                                             \n"
        "       .endm                                                   \n");
 
@@ -102,7 +116,13 @@ __asm__ (
        "       .set    push                                            \n"
        "       .set    reorder                                         \n"
        "       .set    noat                                            \n"
-#ifdef CONFIG_CPU_MIPSR2
+#ifdef CONFIG_MIPS_MT_SMTC
+       "       mfc0    \\result, $2, 1                                 \n"
+       "       ori     $1, \\result, 0x400                             \n"
+       "       .set    noreorder                                       \n"
+       "       mtc0    $1, $2, 1                                       \n"
+       "       andi    \\result, \\result, 0x400                       \n"
+#elif defined(CONFIG_CPU_MIPSR2)
        "       di      \\result                                        \n"
        "       andi    \\result, 1                                     \n"
 #else
@@ -128,7 +148,14 @@ __asm__ (
        "       .set    push                                            \n"
        "       .set    noreorder                                       \n"
        "       .set    noat                                            \n"
-#if defined(CONFIG_CPU_MIPSR2) && defined(CONFIG_IRQ_CPU)
+#ifdef CONFIG_MIPS_MT_SMTC
+       "mfc0   $1, $2, 1                                               \n"
+       "andi   \\flags, 0x400                                          \n"
+       "ori    $1, 0x400                                               \n"
+       "xori   $1, 0x400                                               \n"
+       "or     \\flags, $1                                             \n"
+       "mtc0   \\flags, $2, 1                                          \n"
+#elif defined(CONFIG_CPU_MIPSR2) && defined(CONFIG_IRQ_CPU)
        /*
         * Slow, but doesn't suffer from a relativly unlikely race
         * condition we're having since days 1.
@@ -167,11 +194,29 @@ do {                                                                      \
                : "memory");                                            \
 } while(0)
 
-#define irqs_disabled()                                                        \
-({                                                                     \
-       unsigned long flags;                                            \
-       local_save_flags(flags);                                        \
-       !(flags & 1);                                                   \
-})
+static inline int irqs_disabled(void)
+{
+#ifdef CONFIG_MIPS_MT_SMTC
+       /*
+        * SMTC model uses TCStatus.IXMT to disable interrupts for a thread/CPU
+        */
+       unsigned long __result;
+
+       __asm__ __volatile__(
+       "       .set    noreorder                                       \n"
+       "       mfc0    %0, $2, 1                                       \n"
+       "       andi    %0, 0x400                                       \n"
+       "       slt     %0, $0, %0                                      \n"
+       "       .set    reorder                                         \n"
+       : "=r" (__result));
+
+       return __result;
+#else
+       unsigned long flags;
+       local_save_flags(flags);
+
+       return !(flags & 1);
+#endif
+}
 
 #endif /* _ASM_INTERRUPT_H */
index 8a342ccb34a80e34c3c52835759d675744162142..dde677f02bc015e1129d3b30a550f707f3b8f61d 100644 (file)
@@ -11,6 +11,9 @@
 
 #include <linux/config.h>
 #include <linux/linkage.h>
+
+#include <asm/mipsmtregs.h>
+
 #include <irq.h>
 
 #ifdef CONFIG_I8259
@@ -26,6 +29,23 @@ struct pt_regs;
 
 extern asmlinkage unsigned int do_IRQ(unsigned int irq, struct pt_regs *regs);
 
+#ifdef CONFIG_MIPS_MT_SMTC
+/*
+ * Clear interrupt mask handling "backstop" if irq_hwmask
+ * entry so indicates. This implies that the ack() or end()
+ * functions will take over re-enabling the low-level mask.
+ * Otherwise it will be done on return from exception.
+ */
+#define __DO_IRQ_SMTC_HOOK()                                           \
+do {                                                                   \
+       if (irq_hwmask[irq] & 0x0000ff00)                               \
+               write_c0_tccontext(read_c0_tccontext() &                \
+                                  ~(irq_hwmask[irq] & 0x0000ff00));    \
+} while (0)
+#else
+#define __DO_IRQ_SMTC_HOOK() do { } while (0)
+#endif
+
 #ifdef CONFIG_PREEMPT
 
 /*
@@ -39,6 +59,7 @@ extern asmlinkage unsigned int do_IRQ(unsigned int irq, struct pt_regs *regs);
 #define do_IRQ(irq, regs)                                              \
 do {                                                                   \
        irq_enter();                                                    \
+       __DO_IRQ_SMTC_HOOK();                                           \
        __do_IRQ((irq), (regs));                                        \
        irq_exit();                                                     \
 } while (0)
@@ -46,5 +67,14 @@ do {                                                                 \
 #endif
 
 extern void arch_init_irq(void);
+extern void spurious_interrupt(struct pt_regs *regs);
+
+#ifdef CONFIG_MIPS_MT_SMTC
+struct irqaction;
+
+extern unsigned long irq_hwmask[];
+extern int setup_irq_smtc(unsigned int irq, struct irqaction * new,
+                          unsigned long hwmask);
+#endif /* CONFIG_MIPS_MT_SMTC */
 
 #endif /* _ASM_IRQ_H */
diff --git a/include/asm-mips/kspd.h b/include/asm-mips/kspd.h
new file mode 100644 (file)
index 0000000..4e9e724
--- /dev/null
@@ -0,0 +1,36 @@
+/*
+ * Copyright (C) 2005 MIPS Technologies, Inc.  All rights reserved.
+ *
+ *  This program is free software; you can distribute 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 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.,
+ *  59 Temple Place - Suite 330, Boston MA 02111-1307, USA.
+ *
+ */
+
+#ifndef _ASM_KSPD_H
+#define _ASM_KSPD_H
+
+struct kspd_notifications {
+       void (*kspd_sp_exit)(int sp_id);
+
+       struct list_head list;
+};
+
+#ifdef CONFIG_MIPS_APSP_KSPD
+extern void kspd_notify(struct kspd_notifications *notify);
+#else
+static inline void kspd_notify(struct kspd_notifications *notify)
+{
+}
+#endif
+
+#endif
index 550979a9ea9d21432fe0a8570f73d9cf294df4be..e3315359500abba1617bb13f4abd17be79dc2f66 100644 (file)
@@ -104,65 +104,107 @@ static __inline__ unsigned long ide_default_io_base(int index)
 #endif
 
 /* MIPS port and memory-mapped I/O string operations.  */
+static inline void __ide_flush_prologue(void)
+{
+#ifdef CONFIG_SMP
+       if (cpu_has_dc_aliases)
+               preempt_disable();
+#endif
+}
+
+static inline void __ide_flush_epilogue(void)
+{
+#ifdef CONFIG_SMP
+       if (cpu_has_dc_aliases)
+               preempt_enable();
+#endif
+}
 
 static inline void __ide_flush_dcache_range(unsigned long addr, unsigned long size)
 {
        if (cpu_has_dc_aliases) {
                unsigned long end = addr + size;
-               for (; addr < end; addr += PAGE_SIZE)
-                       flush_dcache_page(virt_to_page(addr));
+
+               while (addr < end) {
+                       local_flush_data_cache_page((void *)addr);
+                       addr += PAGE_SIZE;
+               }
        }
 }
 
+/*
+ * insw() and gang might be called with interrupts disabled, so we can't
+ * send IPIs for flushing due to the potencial of deadlocks, see the comment
+ * above smp_call_function() in arch/mips/kernel/smp.c.  We work around the
+ * problem by disabling preemption so we know we actually perform the flush
+ * on the processor that actually has the lines to be flushed which hopefully
+ * is even better for performance anyway.
+ */
 static inline void __ide_insw(unsigned long port, void *addr,
        unsigned int count)
 {
+       __ide_flush_prologue();
        insw(port, addr, count);
        __ide_flush_dcache_range((unsigned long)addr, count * 2);
+       __ide_flush_epilogue();
 }
 
 static inline void __ide_insl(unsigned long port, void *addr, unsigned int count)
 {
+       __ide_flush_prologue();
        insl(port, addr, count);
        __ide_flush_dcache_range((unsigned long)addr, count * 4);
+       __ide_flush_epilogue();
 }
 
 static inline void __ide_outsw(unsigned long port, const void *addr,
        unsigned long count)
 {
+       __ide_flush_prologue();
        outsw(port, addr, count);
        __ide_flush_dcache_range((unsigned long)addr, count * 2);
+       __ide_flush_epilogue();
 }
 
 static inline void __ide_outsl(unsigned long port, const void *addr,
        unsigned long count)
 {
+       __ide_flush_prologue();
        outsl(port, addr, count);
        __ide_flush_dcache_range((unsigned long)addr, count * 4);
+       __ide_flush_epilogue();
 }
 
 static inline void __ide_mm_insw(void __iomem *port, void *addr, u32 count)
 {
+       __ide_flush_prologue();
        readsw(port, addr, count);
        __ide_flush_dcache_range((unsigned long)addr, count * 2);
+       __ide_flush_epilogue();
 }
 
 static inline void __ide_mm_insl(void __iomem *port, void *addr, u32 count)
 {
+       __ide_flush_prologue();
        readsl(port, addr, count);
        __ide_flush_dcache_range((unsigned long)addr, count * 4);
+       __ide_flush_epilogue();
 }
 
 static inline void __ide_mm_outsw(void __iomem *port, void *addr, u32 count)
 {
+       __ide_flush_prologue();
        writesw(port, addr, count);
        __ide_flush_dcache_range((unsigned long)addr, count * 2);
+       __ide_flush_epilogue();
 }
 
 static inline void __ide_mm_outsl(void __iomem * port, void *addr, u32 count)
 {
+       __ide_flush_prologue();
        writesl(port, addr, count);
        __ide_flush_dcache_range((unsigned long)addr, count * 4);
+       __ide_flush_epilogue();
 }
 
 /* ide_insw calls insw, not __ide_insw.  Why? */
index cff6192d4bdbd820ab659c5cf8d449413ea7b697..8a8fef6d07fad7608a14404e496fd99bcba54861 100644 (file)
@@ -3,14 +3,14 @@
  * License.  See the file "COPYING" in the main directory of this archive
  * for more details.
  *
- * Copyright (C) 2003 by Ralf Baechle
+ * Copyright (C) 2003, 06 by Ralf Baechle
  */
 #ifndef __ASM_MACH_JMR3927_DS1742_H
 #define __ASM_MACH_JMR3927_DS1742_H
 
 #include <asm/jmr3927/jmr3927.h>
 
-#define rtc_read(reg)          (jmr3927_nvram_in(addr))
+#define rtc_read(reg)          (jmr3927_nvram_in(reg))
 #define rtc_write(data, reg)   (jmr3927_nvram_out((data),(reg)))
 
 #endif /* __ASM_MACH_JMR3927_DS1742_H */
diff --git a/include/asm-mips/mach-mips/param.h b/include/asm-mips/mach-mips/param.h
new file mode 100644 (file)
index 0000000..805ef6d
--- /dev/null
@@ -0,0 +1,13 @@
+/*
+ * This file is subject to the terms and conditions of the GNU General Public
+ * License.  See the file "COPYING" in the main directory of this archive
+ * for more details.
+ *
+ * Copyright (C) 2003 by Ralf Baechle
+ */
+#ifndef __ASM_MACH_MIPS_PARAM_H
+#define __ASM_MACH_MIPS_PARAM_H
+
+#define HZ             100             /* Internal kernel timer frequency */
+
+#endif /* __ASM_MACH_MIPS_PARAM_H */
index 9225b3397a4fb4d126cce26b4a37602696c0cd6d..6bb2125bb0538b1a8d148d4df9462ae3ab8e89c9 100644 (file)
@@ -53,4 +53,6 @@ struct mv_pci_controller {
        unsigned long   config_vreg;
 };
 
+extern void ll_mv64340_irq(struct pt_regs *regs);
+
 #endif /* __ASM_MIPS_MARVELL_H */
index 0998151fb3a12e68b28960082ff810cc5fd78c7c..a8ae12d120eecad17db01c7074d277e5919aa482 100644 (file)
 #define ATLAS_RTC_ADR_REG       0x1f000800
 #define ATLAS_RTC_DAT_REG       0x1f000808
 
-
 /*
  * Atlas interrupt controller register base.
  */
 #define ATLAS_ICTRL_REGS_BASE   0x1f000000
 
+/*
+ * Atlas registers are memory mapped on 64-bit aligned boundaries and
+ * only word access are allowed.
+ */
+struct atlas_ictrl_regs {
+       volatile unsigned int intraw;
+       int dummy1;
+       volatile unsigned int intseten;
+       int dummy2;
+       volatile unsigned int intrsten;
+       int dummy3;
+       volatile unsigned int intenable;
+       int dummy4;
+       volatile unsigned int intstatus;
+       int dummy5;
+};
+
 /*
  * Atlas UART register base.
  */
index bba35c183d087dd77747a4b1dfe527b2d8afc824..fd7ebc54fa901ff7384df77024dca98abf6e257e 100644 (file)
 #define ATLASINT_RES31         (ATLASINT_BASE+31)
 #define ATLASINT_END           (ATLASINT_BASE+31)
 
-/*
- * Atlas registers are memory mapped on 64-bit aligned boundaries and
- * only word access are allowed.
- */
-struct atlas_ictrl_regs {
-        volatile unsigned int intraw;
-        int dummy1;
-        volatile unsigned int intseten;
-        int dummy2;
-        volatile unsigned int intrsten;
-        int dummy3;
-        volatile unsigned int intenable;
-        int dummy4;
-        volatile unsigned int intstatus;
-        int dummy5;
-};
-
-extern void atlasint_init(void);
-
 #endif /* !(_MIPS_ATLASINT_H) */
diff --git a/include/asm-mips/mips_mt.h b/include/asm-mips/mips_mt.h
new file mode 100644 (file)
index 0000000..c31a312
--- /dev/null
@@ -0,0 +1,15 @@
+/*
+ * Definitions and decalrations for MIPS MT support
+ * that are common between SMTC, VSMP, and/or AP/SP
+ * kernel models.
+ */
+#ifndef __ASM_MIPS_MT_H
+#define __ASM_MIPS_MT_H
+
+extern cpumask_t mt_fpu_cpumask;
+extern unsigned long mt_fpemul_threshold;
+
+extern void mips_mt_regdump(unsigned long previous_mvpcontrol_value);
+extern void mips_mt_set_cpuoptions(void);
+
+#endif /* __ASM_MIPS_MT_H */
index a669c0702c66705fc7440b1056d9727ad03bc8b9..f637ce70758fb363b930f18615726c6205d060d7 100644 (file)
 
 #ifndef __ASSEMBLY__
 
-extern void mips_mt_regdump(void);
+extern void mips_mt_regdump(unsigned long previous_mvpcontrol_value);
 
 static inline unsigned int dvpe(void)
 {
@@ -234,7 +234,7 @@ static inline void __raw_emt(void)
        __asm__ __volatile__(
        "       .set    noreorder                                       \n"
        "       .set    mips32r2                                        \n"
-       "       emt                                                     \n"
+       "       .word   0x41600be1                      # emt           \n"
        "       ehb                                                     \n"
        "       .set    mips0                                           \n"
        "       .set    reorder");
@@ -282,8 +282,11 @@ static inline void ehb(void)
                                                                        \
        __asm__ __volatile__(                                           \
        "       .set    push                                    \n"     \
+       "       .set    noat                                    \n"     \
        "       .set    mips32r2                                \n"     \
-       "       mftgpr  %0," #rt "                              \n"     \
+       "       # mftgpr $1," #rt "                             \n"     \
+       "       .word   0x41000820 | (" #rt " << 16)            \n"     \
+       "       move    %0, $1                                  \n"     \
        "       .set    pop                                     \n"     \
        : "=r" (__res));                                                \
                                                                        \
@@ -295,9 +298,7 @@ static inline void ehb(void)
        unsigned long __res;                                            \
                                                                        \
        __asm__ __volatile__(                                           \
-       ".set noat\n\t"                                                 \
-       "mftr\t%0, " #rt ", " #u ", " #sel "\n\t"                       \
-       ".set at\n\t"                                                   \
+       "       mftr    %0, " #rt ", " #u ", " #sel "           \n"     \
        : "=r" (__res));                                                \
                                                                        \
        __res;                                                          \
@@ -364,6 +365,9 @@ do {                                                                        \
 #define read_vpe_c0_ebase()            mftc0(15,1)
 #define write_vpe_c0_ebase(val)                mttc0(15, 1, val)
 #define write_vpe_c0_compare(val)      mttc0(11, 0, val)
+#define read_vpe_c0_badvaddr()         mftc0(8, 0)
+#define read_vpe_c0_epc()              mftc0(14, 0)
+#define write_vpe_c0_epc(val)          mttc0(14, 0, val)
 
 
 /* TC */
index 035ba0a9b0dfe3c62d1f80a510246e82b6e5ce35..a2ef579f6b1a26d8e87d3b5c19b405629dfe0b29 100644 (file)
@@ -836,6 +836,9 @@ do {                                                                        \
 #define read_c0_cache()                __read_32bit_c0_register($7, 0) /* TX39xx */
 #define write_c0_cache(val)    __write_32bit_c0_register($7, 0, val)
 
+#define read_c0_badvaddr()     __read_ulong_c0_register($8, 0)
+#define write_c0_badvaddr(val) __write_ulong_c0_register($8, 0, val)
+
 #define read_c0_count()                __read_32bit_c0_register($9, 0)
 #define write_c0_count(val)    __write_32bit_c0_register($9, 0, val)
 
@@ -858,7 +861,19 @@ do {                                                                       \
 #define write_c0_compare3(val) __write_32bit_c0_register($11, 7, val)
 
 #define read_c0_status()       __read_32bit_c0_register($12, 0)
+#ifdef CONFIG_MIPS_MT_SMTC
+#define write_c0_status(val)                                           \
+do {                                                                   \
+       __write_32bit_c0_register($12, 0, val);                         \
+       __ehb();                                                        \
+} while (0)
+#else
+/*
+ * Legacy non-SMTC code, which may be hazardous
+ * but which might not support EHB
+ */
 #define write_c0_status(val)   __write_32bit_c0_register($12, 0, val)
+#endif /* CONFIG_MIPS_MT_SMTC */
 
 #define read_c0_cause()                __read_32bit_c0_register($13, 0)
 #define write_c0_cause(val)    __write_32bit_c0_register($13, 0, val)
@@ -1001,6 +1016,9 @@ do {                                                                      \
 #define read_c0_taglo()                __read_32bit_c0_register($28, 0)
 #define write_c0_taglo(val)    __write_32bit_c0_register($28, 0, val)
 
+#define read_c0_dtaglo()       __read_32bit_c0_register($28, 2)
+#define write_c0_dtaglo(val)   __write_32bit_c0_register($28, 2, val)
+
 #define read_c0_taghi()                __read_32bit_c0_register($29, 0)
 #define write_c0_taghi(val)    __write_32bit_c0_register($29, 0, val)
 
@@ -1354,15 +1372,119 @@ static inline void tlb_write_random(void)
 /*
  * Manipulate bits in a c0 register.
  */
+#ifndef CONFIG_MIPS_MT_SMTC
+/*
+ * SMTC Linux requires shutting-down microthread scheduling
+ * during CP0 register read-modify-write sequences.
+ */
+#define __BUILD_SET_C0(name)                                   \
+static inline unsigned int                                     \
+set_c0_##name(unsigned int set)                                        \
+{                                                              \
+       unsigned int res;                                       \
+                                                               \
+       res = read_c0_##name();                                 \
+       res |= set;                                             \
+       write_c0_##name(res);                                   \
+                                                               \
+       return res;                                             \
+}                                                              \
+                                                               \
+static inline unsigned int                                     \
+clear_c0_##name(unsigned int clear)                            \
+{                                                              \
+       unsigned int res;                                       \
+                                                               \
+       res = read_c0_##name();                                 \
+       res &= ~clear;                                          \
+       write_c0_##name(res);                                   \
+                                                               \
+       return res;                                             \
+}                                                              \
+                                                               \
+static inline unsigned int                                     \
+change_c0_##name(unsigned int change, unsigned int new)                \
+{                                                              \
+       unsigned int res;                                       \
+                                                               \
+       res = read_c0_##name();                                 \
+       res &= ~change;                                         \
+       res |= (new & change);                                  \
+       write_c0_##name(res);                                   \
+                                                               \
+       return res;                                             \
+}
+
+#else /* SMTC versions that manage MT scheduling */
+
+#include <asm/interrupt.h>
+
+/*
+ * This is a duplicate of dmt() in mipsmtregs.h to avoid problems with
+ * header file recursion.
+ */
+static inline unsigned int __dmt(void)
+{
+       int res;
+
+       __asm__ __volatile__(
+       "       .set    push                                            \n"
+       "       .set    mips32r2                                        \n"
+       "       .set    noat                                            \n"
+       "       .word   0x41610BC1                      # dmt $1        \n"
+       "       ehb                                                     \n"
+       "       move    %0, $1                                          \n"
+       "       .set    pop                                             \n"
+       : "=r" (res));
+
+       instruction_hazard();
+
+       return res;
+}
+
+#define __VPECONTROL_TE_SHIFT  15
+#define __VPECONTROL_TE                (1UL << __VPECONTROL_TE_SHIFT)
+
+#define __EMT_ENABLE           __VPECONTROL_TE
+
+static inline void __emt(unsigned int previous)
+{
+       if ((previous & __EMT_ENABLE))
+               __asm__ __volatile__(
+               "       .set    noreorder                               \n"
+               "       .set    mips32r2                                \n"
+               "       .word   0x41600be1              # emt           \n"
+               "       ehb                                             \n"
+               "       .set    mips0                                   \n"
+               "       .set    reorder                                 \n");
+}
+
+static inline void __ehb(void)
+{
+       __asm__ __volatile__(
+       "       ehb                                                     \n");
+}
+
+/*
+ * Note that local_irq_save/restore affect TC-specific IXMT state,
+ * not Status.IE as in non-SMTC kernel.
+ */
+
 #define __BUILD_SET_C0(name)                                   \
 static inline unsigned int                                     \
 set_c0_##name(unsigned int set)                                        \
 {                                                              \
        unsigned int res;                                       \
+       unsigned int omt;                                       \
+       unsigned int flags;                                     \
                                                                \
+       local_irq_save(flags);                                  \
+       omt = __dmt();                                          \
        res = read_c0_##name();                                 \
        res |= set;                                             \
        write_c0_##name(res);                                   \
+       __emt(omt);                                             \
+       local_irq_restore(flags);                               \
                                                                \
        return res;                                             \
 }                                                              \
@@ -1371,10 +1493,16 @@ static inline unsigned int                                      \
 clear_c0_##name(unsigned int clear)                            \
 {                                                              \
        unsigned int res;                                       \
+       unsigned int omt;                                       \
+       unsigned int flags;                                     \
                                                                \
+       local_irq_save(flags);                                  \
+       omt = __dmt();                                          \
        res = read_c0_##name();                                 \
        res &= ~clear;                                          \
        write_c0_##name(res);                                   \
+       __emt(omt);                                             \
+       local_irq_restore(flags);                               \
                                                                \
        return res;                                             \
 }                                                              \
@@ -1383,14 +1511,22 @@ static inline unsigned int                                      \
 change_c0_##name(unsigned int change, unsigned int new)                \
 {                                                              \
        unsigned int res;                                       \
+       unsigned int omt;                                       \
+       unsigned int flags;                                     \
                                                                \
+       local_irq_save(flags);                                  \
+                                                               \
+       omt = __dmt();                                          \
        res = read_c0_##name();                                 \
        res &= ~change;                                         \
        res |= (new & change);                                  \
        write_c0_##name(res);                                   \
+       __emt(omt);                                             \
+       local_irq_restore(flags);                               \
                                                                \
        return res;                                             \
 }
+#endif
 
 __BUILD_SET_C0(status)
 __BUILD_SET_C0(cause)
index 61cf22588137a3505c3d469c0da618734fbea190..6e09f4c87211017602fe9adba197855294e5dc77 100644 (file)
 #include <linux/slab.h>
 #include <asm/cacheflush.h>
 #include <asm/tlbflush.h>
+#ifdef CONFIG_MIPS_MT_SMTC
+#include <asm/mipsmtregs.h>
+#include <asm/smtc.h>
+#endif /* SMTC */
 
 /*
  * For the fast tlb miss handlers, we keep a per cpu array of pointers
@@ -54,6 +58,14 @@ extern unsigned long pgd_current[];
 #define ASID_INC       0x1
 #define ASID_MASK      0xfff
 
+/* SMTC/34K debug hack - but maybe we'll keep it */
+#elif defined(CONFIG_MIPS_MT_SMTC)
+
+#define ASID_INC       0x1
+extern unsigned long smtc_asid_mask;
+#define ASID_MASK      (smtc_asid_mask)
+#define        HW_ASID_MASK    0xff
+/* End SMTC/34K debug hack */
 #else /* FIXME: not correct for R6000 */
 
 #define ASID_INC       0x1
@@ -76,6 +88,8 @@ static inline void enter_lazy_tlb(struct mm_struct *mm, struct task_struct *tsk)
 #define ASID_VERSION_MASK  ((unsigned long)~(ASID_MASK|(ASID_MASK-1)))
 #define ASID_FIRST_VERSION ((unsigned long)(~ASID_VERSION_MASK) + 1)
 
+#ifndef CONFIG_MIPS_MT_SMTC
+/* Normal, classic MIPS get_new_mmu_context */
 static inline void
 get_new_mmu_context(struct mm_struct *mm, unsigned long cpu)
 {
@@ -91,6 +105,12 @@ get_new_mmu_context(struct mm_struct *mm, unsigned long cpu)
        cpu_context(cpu, mm) = asid_cache(cpu) = asid;
 }
 
+#else /* CONFIG_MIPS_MT_SMTC */
+
+#define get_new_mmu_context(mm,cpu) smtc_get_new_mmu_context((mm),(cpu))
+
+#endif /* CONFIG_MIPS_MT_SMTC */
+
 /*
  * Initialize the context related info for a new mm_struct
  * instance.
@@ -111,14 +131,46 @@ static inline void switch_mm(struct mm_struct *prev, struct mm_struct *next,
 {
        unsigned int cpu = smp_processor_id();
        unsigned long flags;
-
+#ifdef CONFIG_MIPS_MT_SMTC
+       unsigned long oldasid;
+       unsigned long mtflags;
+       int mytlb = (smtc_status & SMTC_TLB_SHARED) ? 0 : cpu_data[cpu].vpe_id;
        local_irq_save(flags);
+       mtflags = dvpe();
+#else /* Not SMTC */
+       local_irq_save(flags);
+#endif /* CONFIG_MIPS_MT_SMTC */
 
        /* Check if our ASID is of an older version and thus invalid */
        if ((cpu_context(cpu, next) ^ asid_cache(cpu)) & ASID_VERSION_MASK)
                get_new_mmu_context(next, cpu);
-
+#ifdef CONFIG_MIPS_MT_SMTC
+       /*
+        * If the EntryHi ASID being replaced happens to be
+        * the value flagged at ASID recycling time as having
+        * an extended life, clear the bit showing it being
+        * in use by this "CPU", and if that's the last bit,
+        * free up the ASID value for use and flush any old
+        * instances of it from the TLB.
+        */
+       oldasid = (read_c0_entryhi() & ASID_MASK);
+       if(smtc_live_asid[mytlb][oldasid]) {
+               smtc_live_asid[mytlb][oldasid] &= ~(0x1 << cpu);
+               if(smtc_live_asid[mytlb][oldasid] == 0)
+                       smtc_flush_tlb_asid(oldasid);
+       }
+       /*
+        * Tread softly on EntryHi, and so long as we support
+        * having ASID_MASK smaller than the hardware maximum,
+        * make sure no "soft" bits become "hard"...
+        */
+       write_c0_entryhi((read_c0_entryhi() & ~HW_ASID_MASK)
+                       | (cpu_context(cpu, next) & ASID_MASK));
+       ehb(); /* Make sure it propagates to TCStatus */
+       evpe(mtflags);
+#else
        write_c0_entryhi(cpu_context(cpu, next));
+#endif /* CONFIG_MIPS_MT_SMTC */
        TLBMISS_HANDLER_SETUP_PGD(next->pgd);
 
        /*
@@ -151,12 +203,34 @@ activate_mm(struct mm_struct *prev, struct mm_struct *next)
        unsigned long flags;
        unsigned int cpu = smp_processor_id();
 
+#ifdef CONFIG_MIPS_MT_SMTC
+       unsigned long oldasid;
+       unsigned long mtflags;
+       int mytlb = (smtc_status & SMTC_TLB_SHARED) ? 0 : cpu_data[cpu].vpe_id;
+#endif /* CONFIG_MIPS_MT_SMTC */
+
        local_irq_save(flags);
 
        /* Unconditionally get a new ASID.  */
        get_new_mmu_context(next, cpu);
 
+#ifdef CONFIG_MIPS_MT_SMTC
+       /* See comments for similar code above */
+       mtflags = dvpe();
+       oldasid = read_c0_entryhi() & ASID_MASK;
+       if(smtc_live_asid[mytlb][oldasid]) {
+               smtc_live_asid[mytlb][oldasid] &= ~(0x1 << cpu);
+                       if(smtc_live_asid[mytlb][oldasid] == 0)
+                                smtc_flush_tlb_asid(oldasid);
+       }
+       /* See comments for similar code above */
+       write_c0_entryhi((read_c0_entryhi() & ~HW_ASID_MASK) |
+                        (cpu_context(cpu, next) & ASID_MASK));
+       ehb(); /* Make sure it propagates to TCStatus */
+       evpe(mtflags);
+#else
        write_c0_entryhi(cpu_context(cpu, next));
+#endif /* CONFIG_MIPS_MT_SMTC */
        TLBMISS_HANDLER_SETUP_PGD(next->pgd);
 
        /* mark mmu ownership change */
@@ -174,17 +248,49 @@ static inline void
 drop_mmu_context(struct mm_struct *mm, unsigned cpu)
 {
        unsigned long flags;
+#ifdef CONFIG_MIPS_MT_SMTC
+       unsigned long oldasid;
+       /* Can't use spinlock because called from TLB flush within DVPE */
+       unsigned int prevvpe;
+       int mytlb = (smtc_status & SMTC_TLB_SHARED) ? 0 : cpu_data[cpu].vpe_id;
+#endif /* CONFIG_MIPS_MT_SMTC */
 
        local_irq_save(flags);
 
        if (cpu_isset(cpu, mm->cpu_vm_mask))  {
                get_new_mmu_context(mm, cpu);
+#ifdef CONFIG_MIPS_MT_SMTC
+               /* See comments for similar code above */
+               prevvpe = dvpe();
+               oldasid = (read_c0_entryhi() & ASID_MASK);
+               if(smtc_live_asid[mytlb][oldasid]) {
+                 smtc_live_asid[mytlb][oldasid] &= ~(0x1 << cpu);
+                 if(smtc_live_asid[mytlb][oldasid] == 0)
+                       smtc_flush_tlb_asid(oldasid);
+               }
+               /* See comments for similar code above */
+               write_c0_entryhi((read_c0_entryhi() & ~HW_ASID_MASK)
+                               | cpu_asid(cpu, mm));
+               ehb(); /* Make sure it propagates to TCStatus */
+               evpe(prevvpe);
+#else /* not CONFIG_MIPS_MT_SMTC */
                write_c0_entryhi(cpu_asid(cpu, mm));
+#endif /* CONFIG_MIPS_MT_SMTC */
        } else {
                /* will get a new context next time */
+#ifndef CONFIG_MIPS_MT_SMTC
                cpu_context(cpu, mm) = 0;
+#else /* SMTC */
+               int i;
+
+               /* SMTC shares the TLB (and ASIDs) across VPEs */
+               for (i = 0; i < num_online_cpus(); i++) {
+                   if((smtc_status & SMTC_TLB_SHARED)
+                   || (cpu_data[i].vpe_id == cpu_data[cpu].vpe_id))
+                       cpu_context(i, mm) = 0;
+               }
+#endif /* CONFIG_MIPS_MT_SMTC */
        }
-
        local_irq_restore(flags);
 }
 
diff --git a/include/asm-mips/numnodes.h b/include/asm-mips/numnodes.h
deleted file mode 100644 (file)
index 4f00c16..0000000
+++ /dev/null
@@ -1,7 +0,0 @@
-#ifndef _ASM_MAX_NUMNODES_H
-#define _ASM_MAX_NUMNODES_H
-
-/* Max 128 Nodes */
-#define NODES_SHIFT    6
-
-#endif /* _ASM_MAX_NUMNODES_H */
index 39d2bd50fecede26d52090657e08b5fe71e29f39..0fb75f0762e0b6934dbe03b18f3aace575ba5f96 100644 (file)
@@ -12,6 +12,7 @@
 #define _ASM_PROCESSOR_H
 
 #include <linux/config.h>
+#include <linux/cpumask.h>
 #include <linux/threads.h>
 
 #include <asm/cachectl.h>
@@ -107,6 +108,10 @@ struct mips_dsp_state {
 
 #define INIT_DSP {{0,},}
 
+#define INIT_CPUMASK { \
+       {0,} \
+}
+
 typedef struct {
        unsigned long seg;
 } mm_segment_t;
@@ -129,6 +134,12 @@ struct thread_struct {
 
        /* Saved fpu/fpu emulator stuff. */
        union mips_fpu_union fpu;
+#ifdef CONFIG_MIPS_MT_FPAFF
+       /* Emulated instruction count */
+       unsigned long emulated_fp;
+       /* Saved per-thread scheduler affinity mask */
+       cpumask_t user_cpus_allowed;
+#endif /* CONFIG_MIPS_MT_FPAFF */
 
        /* Saved state of the DSP ASE, if available. */
        struct mips_dsp_state dsp;
@@ -142,6 +153,7 @@ struct thread_struct {
 #define MF_LOGADE      2               /* Log address errors to syslog */
 #define MF_32BIT_REGS  4               /* also implies 16/32 fprs */
 #define MF_32BIT_ADDR  8               /* 32-bit address space (o32/n32) */
+#define MF_FPUBOUND    0x10            /* thread bound to FPU-full CPU set */
        unsigned long mflags;
        unsigned long irix_trampoline;  /* Wheee... */
        unsigned long irix_oldctx;
@@ -153,6 +165,12 @@ struct thread_struct {
 #define MF_N32         MF_32BIT_ADDR
 #define MF_N64         0
 
+#ifdef CONFIG_MIPS_MT_FPAFF
+#define FPAFF_INIT 0, INIT_CPUMASK,
+#else
+#define FPAFF_INIT
+#endif /* CONFIG_MIPS_MT_FPAFF */
+
 #define INIT_THREAD  { \
         /* \
          * saved main processor registers \
@@ -167,6 +185,10 @@ struct thread_struct {
         * saved fpu/fpu emulator stuff \
         */ \
        INIT_FPU, \
+       /* \
+        * fpu affinity state (null if not FPAFF) \
+        */ \
+       FPAFF_INIT \
        /* \
         * saved dsp/dsp emulator stuff \
         */ \
index 95c5839ac4657dac29ebc30c03d05774ea677c8b..fa9d8713c12a2615ac0e1c89ff3b22f9be683797 100644 (file)
@@ -45,6 +45,10 @@ struct pt_regs {
        unsigned long cp0_badvaddr;
        unsigned long cp0_cause;
        unsigned long cp0_epc;
+#ifdef CONFIG_MIPS_MT_SMTC
+       unsigned long cp0_tcstatus;
+       unsigned long smtc_pad;
+#endif /* CONFIG_MIPS_MT_SMTC */
 };
 
 /* Arbitrarily choose the same ptrace numbers as used by the Sparc code. */
index 90c374700977cc87091663ac5d9ac71012ce600d..3c8e3c8d1a9a5da1a3aab928ceb3bc92a4685cf8 100644 (file)
@@ -15,6 +15,7 @@
 #include <asm/asm.h>
 #include <asm/cacheops.h>
 #include <asm/cpu-features.h>
+#include <asm/mipsmtregs.h>
 
 /*
  * This macro return a properly sign-extended address suitable as base address
        "       cache   %0, %1                                  \n"     \
        "       .set    pop                                     \n"     \
        :                                                               \
-       : "i" (op), "m" (*(unsigned char *)(addr)))
+       : "i" (op), "R" (*(unsigned char *)(addr)))
+
+#ifdef CONFIG_MIPS_MT
+/*
+ * Temporary hacks for SMTC debug. Optionally force single-threaded
+ * execution during I-cache flushes.
+ */
+
+#define PROTECT_CACHE_FLUSHES 1
+
+#ifdef PROTECT_CACHE_FLUSHES
+
+extern int mt_protiflush;
+extern int mt_protdflush;
+extern void mt_cflush_lockdown(void);
+extern void mt_cflush_release(void);
+
+#define BEGIN_MT_IPROT \
+       unsigned long flags = 0;                        \
+       unsigned long mtflags = 0;                      \
+       if(mt_protiflush) {                             \
+               local_irq_save(flags);                  \
+               ehb();                                  \
+               mtflags = dvpe();                       \
+               mt_cflush_lockdown();                   \
+       }
+
+#define END_MT_IPROT \
+       if(mt_protiflush) {                             \
+               mt_cflush_release();                    \
+               evpe(mtflags);                          \
+               local_irq_restore(flags);               \
+       }
+
+#define BEGIN_MT_DPROT \
+       unsigned long flags = 0;                        \
+       unsigned long mtflags = 0;                      \
+       if(mt_protdflush) {                             \
+               local_irq_save(flags);                  \
+               ehb();                                  \
+               mtflags = dvpe();                       \
+               mt_cflush_lockdown();                   \
+       }
+
+#define END_MT_DPROT \
+       if(mt_protdflush) {                             \
+               mt_cflush_release();                    \
+               evpe(mtflags);                          \
+               local_irq_restore(flags);               \
+       }
+
+#else
+
+#define BEGIN_MT_IPROT
+#define BEGIN_MT_DPROT
+#define END_MT_IPROT
+#define END_MT_DPROT
+
+#endif /* PROTECT_CACHE_FLUSHES */
+
+#define __iflush_prologue                                              \
+       unsigned long redundance;                                       \
+       extern int mt_n_iflushes;                                       \
+       BEGIN_MT_IPROT                                                  \
+       for (redundance = 0; redundance < mt_n_iflushes; redundance++) {
+
+#define __iflush_epilogue                                              \
+       END_MT_IPROT                                                    \
+       }
+
+#define __dflush_prologue                                              \
+       unsigned long redundance;                                       \
+       extern int mt_n_dflushes;                                       \
+       BEGIN_MT_DPROT                                                  \
+       for (redundance = 0; redundance < mt_n_dflushes; redundance++) {
+
+#define __dflush_epilogue \
+       END_MT_DPROT     \
+       }
+
+#define __inv_dflush_prologue __dflush_prologue
+#define __inv_dflush_epilogue __dflush_epilogue
+#define __sflush_prologue {
+#define __sflush_epilogue }
+#define __inv_sflush_prologue __sflush_prologue
+#define __inv_sflush_epilogue __sflush_epilogue
+
+#else /* CONFIG_MIPS_MT */
+
+#define __iflush_prologue {
+#define __iflush_epilogue }
+#define __dflush_prologue {
+#define __dflush_epilogue }
+#define __inv_dflush_prologue {
+#define __inv_dflush_epilogue }
+#define __sflush_prologue {
+#define __sflush_epilogue }
+#define __inv_sflush_prologue {
+#define __inv_sflush_epilogue }
+
+#endif /* CONFIG_MIPS_MT */
 
 static inline void flush_icache_line_indexed(unsigned long addr)
 {
+       __iflush_prologue
        cache_op(Index_Invalidate_I, addr);
+       __iflush_epilogue
 }
 
 static inline void flush_dcache_line_indexed(unsigned long addr)
 {
+       __dflush_prologue
        cache_op(Index_Writeback_Inv_D, addr);
+       __dflush_epilogue
 }
 
 static inline void flush_scache_line_indexed(unsigned long addr)
@@ -56,17 +161,23 @@ static inline void flush_scache_line_indexed(unsigned long addr)
 
 static inline void flush_icache_line(unsigned long addr)
 {
+       __iflush_prologue
        cache_op(Hit_Invalidate_I, addr);
+       __iflush_epilogue
 }
 
 static inline void flush_dcache_line(unsigned long addr)
 {
+       __dflush_prologue
        cache_op(Hit_Writeback_Inv_D, addr);
+       __dflush_epilogue
 }
 
 static inline void invalidate_dcache_line(unsigned long addr)
 {
+       __dflush_prologue
        cache_op(Hit_Invalidate_D, addr);
+       __dflush_epilogue
 }
 
 static inline void invalidate_scache_line(unsigned long addr)
@@ -239,9 +350,13 @@ static inline void blast_##pfx##cache##lsize(void)                 \
                               current_cpu_data.desc.waybit;            \
        unsigned long ws, addr;                                         \
                                                                        \
+       __##pfx##flush_prologue                                         \
+                                                                       \
        for (ws = 0; ws < ws_end; ws += ws_inc)                         \
                for (addr = start; addr < end; addr += lsize * 32)      \
                        cache##lsize##_unroll32(addr|ws,indexop);       \
+                                                                       \
+       __##pfx##flush_epilogue                                         \
 }                                                                      \
                                                                        \
 static inline void blast_##pfx##cache##lsize##_page(unsigned long page)        \
@@ -249,10 +364,14 @@ static inline void blast_##pfx##cache##lsize##_page(unsigned long page)   \
        unsigned long start = page;                                     \
        unsigned long end = page + PAGE_SIZE;                           \
                                                                        \
+       __##pfx##flush_prologue                                         \
+                                                                       \
        do {                                                            \
                cache##lsize##_unroll32(start,hitop);                   \
                start += lsize * 32;                                    \
        } while (start < end);                                          \
+                                                                       \
+       __##pfx##flush_epilogue                                         \
 }                                                                      \
                                                                        \
 static inline void blast_##pfx##cache##lsize##_page_indexed(unsigned long page) \
@@ -265,9 +384,13 @@ static inline void blast_##pfx##cache##lsize##_page_indexed(unsigned long page)
                               current_cpu_data.desc.waybit;            \
        unsigned long ws, addr;                                         \
                                                                        \
+       __##pfx##flush_prologue                                         \
+                                                                       \
        for (ws = 0; ws < ws_end; ws += ws_inc)                         \
                for (addr = start; addr < end; addr += lsize * 32)      \
                        cache##lsize##_unroll32(addr|ws,indexop);       \
+                                                                       \
+       __##pfx##flush_epilogue                                         \
 }
 
 __BUILD_BLAST_CACHE(d, dcache, Index_Writeback_Inv_D, Hit_Writeback_Inv_D, 16)
@@ -288,12 +411,17 @@ static inline void prot##blast_##pfx##cache##_range(unsigned long start, \
        unsigned long lsize = cpu_##desc##_line_size();                 \
        unsigned long addr = start & ~(lsize - 1);                      \
        unsigned long aend = (end - 1) & ~(lsize - 1);                  \
+                                                                       \
+       __##pfx##flush_prologue                                         \
+                                                                       \
        while (1) {                                                     \
                prot##cache_op(hitop, addr);                            \
                if (addr == aend)                                       \
                        break;                                          \
                addr += lsize;                                          \
        }                                                               \
+                                                                       \
+       __##pfx##flush_epilogue                                         \
 }
 
 __BUILD_BLAST_CACHE_RANGE(d, dcache, Hit_Writeback_Inv_D, protected_)
index a2abc4572b638e5bf33cd59f3bdcb121c1d42865..82ad401c7dcae6839d5ea6b0e7181ce6fca84822 100644 (file)
@@ -32,7 +32,7 @@ static inline unsigned int get_rtc_time(struct rtc_time *time)
 {
        unsigned long nowtime;
 
-       nowtime = rtc_get_time();
+       nowtime = rtc_mips_get_time();
        to_tm(nowtime, time);
        time->tm_year -= 1900;
 
@@ -47,7 +47,7 @@ static inline int set_rtc_time(struct rtc_time *time)
        nowtime = mktime(time->tm_year+1900, time->tm_mon+1,
                        time->tm_mday, time->tm_hour, time->tm_min,
                        time->tm_sec);
-       ret = rtc_set_time(nowtime);
+       ret = rtc_mips_set_time(nowtime);
 
        return ret;
 }
index 1298c3fdf6c99b393dbaf118dd429d22672e4cb3..76cd51c6be397979beb615f70914b413f9ccfef1 100644 (file)
@@ -3,32 +3,46 @@
  *
  */
 
-#ifndef _RTLX_H
-#define _RTLX_H_
+#ifndef __ASM_RTLX_H
+#define __ASM_RTLX_H_
 
 #define LX_NODE_BASE 10
 
 #define MIPSCPU_INT_BASE       16
 #define MIPS_CPU_RTLX_IRQ 0
 
-#define RTLX_VERSION 1
+#define RTLX_VERSION 2
 #define RTLX_xID 0x12345600
 #define RTLX_ID (RTLX_xID | RTLX_VERSION)
 #define RTLX_CHANNELS 8
 
-#define RTLX_BUFFER_SIZE 1024
+#define RTLX_CHANNEL_STDIO     0
+#define RTLX_CHANNEL_DBG       1
+#define RTLX_CHANNEL_SYSIO     2
 
-/*
- * lx_state bits
- */
-#define RTLX_STATE_OPENED 1UL
+extern int rtlx_open(int index, int can_sleep);
+extern int rtlx_release(int index);
+extern ssize_t rtlx_read(int index, void *buff, size_t count, int user);
+extern ssize_t rtlx_write(int index, void *buffer, size_t count, int user);
+extern unsigned int rtlx_read_poll(int index, int can_sleep);
+extern unsigned int rtlx_write_poll(int index);
+
+enum rtlx_state {
+       RTLX_STATE_UNUSED,
+       RTLX_STATE_INITIALISED,
+       RTLX_STATE_REMOTE_READY,
+       RTLX_STATE_OPENED
+};
+
+#define RTLX_BUFFER_SIZE 1024
 
 /* each channel supports read and write.
    linux (vpe0) reads lx_buffer  and writes rt_buffer
    SP (vpe1) reads rt_buffer and writes lx_buffer
 */
 struct rtlx_channel {
-       unsigned long lx_state;
+       enum rtlx_state rt_state;
+       enum rtlx_state lx_state;
 
        int buffer_size;
 
@@ -38,15 +52,13 @@ struct rtlx_channel {
 
        int lx_write, lx_read;
        char *lx_buffer;
-
-       void *queues;
-
 };
 
 struct rtlx_info {
        unsigned long id;
+       enum rtlx_state state;
 
        struct rtlx_channel channel[RTLX_CHANNELS];
 };
 
-#endif /* _RTLX_H_ */
+#endif /* __ASM_RTLX_H_ */
index 7b236641220381122fe44c79385c3282b57d647e..7196ceb0e94821988a2bea67bff64e90568b5c32 100644 (file)
 #include <asm/it8712.h>
 #define ITE_SERIAL_PORT_DEFNS                                  \
     { .baud_base = BASE_BAUD, .port = (IT8172_PCI_IO_BASE + IT_UART_BASE), \
-      .irq = IT8172_UART_IRQ, .flags = STD_COM_FLAGS, .type = 0x3 }, \
+      .irq = IT8172_UART_IRQ, .flags = STD_COM_FLAGS, .port = PORT_16550 }, \
     { .baud_base = (24000000/(16*13)), .port = (IT8172_PCI_IO_BASE + IT8712_UART1_PORT), \
-      .irq = IT8172_SERIRQ_4, .flags = STD_COM_FLAGS, .type = 0x3 }, \
+      .irq = IT8172_SERIRQ_4, .flags = STD_COM_FLAGS, .port = PORT_16550 }, \
     /* Smart Card Reader 0 */ \
     { .baud_base = BASE_BAUD, .port = (IT8172_PCI_IO_BASE + IT_SCR0_BASE), \
-      .irq = IT8172_SCR0_IRQ, .flags = STD_COM_FLAGS, .type = 0x3 }, \
+      .irq = IT8172_SCR0_IRQ, .flags = STD_COM_FLAGS, .port = PORT_16550 }, \
     /* Smart Card Reader 1 */ \
     { .baud_base = BASE_BAUD, .port = (IT8172_PCI_IO_BASE + IT_SCR1_BASE), \
-      .irq = IT8172_SCR1_IRQ, .flags = STD_COM_FLAGS, .type = 0x3 },
+      .irq = IT8172_SCR1_IRQ, .flags = STD_COM_FLAGS, .port = PORT_16550 },
 #else
 #define ITE_SERIAL_PORT_DEFNS
 #endif
 #include <asm/it8172/it8172_int.h>
 #define IVR_SERIAL_PORT_DEFNS                                  \
     { .baud_base = BASE_BAUD, .port = (IT8172_PCI_IO_BASE + IT_UART_BASE), \
-      .irq = IT8172_UART_IRQ, .flags = STD_COM_FLAGS, .type = 0x3 },         \
+      .irq = IT8172_UART_IRQ, .flags = STD_COM_FLAGS, .port = PORT_16550 },         \
     /* Smart Card Reader 1 */ \
     { .baud_base = BASE_BAUD, .port = (IT8172_PCI_IO_BASE + IT_SCR1_BASE), \
-      .irq = IT8172_SCR1_IRQ, .flags = STD_COM_FLAGS, .type = 0x3 },
+      .irq = IT8172_SCR1_IRQ, .flags = STD_COM_FLAGS, .port = PORT_16550 },
 #else
 #define IVR_SERIAL_PORT_DEFNS
 #endif
diff --git a/include/asm-mips/smtc.h b/include/asm-mips/smtc.h
new file mode 100644 (file)
index 0000000..e1941d1
--- /dev/null
@@ -0,0 +1,55 @@
+#ifndef _ASM_SMTC_MT_H
+#define _ASM_SMTC_MT_H
+
+/*
+ * Definitions for SMTC multitasking on MIPS MT cores
+ */
+
+#include <asm/mips_mt.h>
+
+/*
+ * System-wide SMTC status information
+ */
+
+extern unsigned int smtc_status;
+
+#define SMTC_TLB_SHARED        0x00000001
+#define SMTC_MTC_ACTIVE        0x00000002
+
+/*
+ * TLB/ASID Management information
+ */
+
+#define MAX_SMTC_TLBS 2
+#define MAX_SMTC_ASIDS 256
+#if NR_CPUS <= 8
+typedef char asiduse;
+#else
+#if NR_CPUS <= 16
+typedef short asiduse;
+#else
+typedef long asiduse;
+#endif
+#endif
+
+extern asiduse smtc_live_asid[MAX_SMTC_TLBS][MAX_SMTC_ASIDS];
+
+void smtc_get_new_mmu_context(struct mm_struct *mm, unsigned long cpu);
+
+void smtc_flush_tlb_asid(unsigned long asid);
+extern int mipsmt_build_cpu_map(int startslot);
+extern void mipsmt_prepare_cpus(void);
+extern void smtc_smp_finish(void);
+extern void smtc_boot_secondary(int cpu, struct task_struct *t);
+
+/*
+ * Sharing the TLB between multiple VPEs means that the
+ * "random" index selection function is not allowed to
+ * select the current value of the Index register. To
+ * avoid additional TLB pressure, the Index registers
+ * are "parked" with an non-Valid value.
+ */
+
+#define PARKED_INDEX   ((unsigned int)0x80000000)
+
+#endif /*  _ASM_SMTC_MT_H */
diff --git a/include/asm-mips/smtc_ipi.h b/include/asm-mips/smtc_ipi.h
new file mode 100644 (file)
index 0000000..f22c3e2
--- /dev/null
@@ -0,0 +1,118 @@
+/*
+ * Definitions used in MIPS MT SMTC "Interprocessor Interrupt" code.
+ */
+#ifndef __ASM_SMTC_IPI_H
+#define __ASM_SMTC_IPI_H
+
+//#define SMTC_IPI_DEBUG
+
+#ifdef SMTC_IPI_DEBUG
+#include <asm/mipsregs.h>
+#include <asm/mipsmtregs.h>
+#endif /* SMTC_IPI_DEBUG */
+
+/*
+ * An IPI "message"
+ */
+
+struct smtc_ipi {
+       struct smtc_ipi *flink;
+       int type;
+       void *arg;
+       int dest;
+#ifdef SMTC_IPI_DEBUG
+       int sender;
+       long stamp;
+#endif /* SMTC_IPI_DEBUG */
+};
+
+/*
+ * Defined IPI Types
+ */
+
+#define LINUX_SMP_IPI 1
+#define SMTC_CLOCK_TICK 2
+
+/*
+ * A queue of IPI messages
+ */
+
+struct smtc_ipi_q {
+       struct smtc_ipi *head;
+       spinlock_t lock;
+       struct smtc_ipi *tail;
+       int depth;
+};
+
+extern struct smtc_ipi_q IPIQ[NR_CPUS];
+extern struct smtc_ipi_q freeIPIq;
+
+static inline void smtc_ipi_nq(struct smtc_ipi_q *q, struct smtc_ipi *p)
+{
+       long flags;
+
+       spin_lock_irqsave(&q->lock, flags);
+       if (q->head == NULL)
+               q->head = q->tail = p;
+       else
+               q->tail->flink = p;
+       p->flink = NULL;
+       q->tail = p;
+       q->depth++;
+#ifdef SMTC_IPI_DEBUG
+       p->sender = read_c0_tcbind();
+       p->stamp = read_c0_count();
+#endif /* SMTC_IPI_DEBUG */
+       spin_unlock_irqrestore(&q->lock, flags);
+}
+
+static inline struct smtc_ipi *smtc_ipi_dq(struct smtc_ipi_q *q)
+{
+       struct smtc_ipi *p;
+       long flags;
+
+       spin_lock_irqsave(&q->lock, flags);
+       if (q->head == NULL)
+               p = NULL;
+       else {
+               p = q->head;
+               q->head = q->head->flink;
+               q->depth--;
+               /* Arguably unnecessary, but leaves queue cleaner */
+               if (q->head == NULL)
+                       q->tail = NULL;
+       }
+       spin_unlock_irqrestore(&q->lock, flags);
+       return p;
+}
+
+static inline void smtc_ipi_req(struct smtc_ipi_q *q, struct smtc_ipi *p)
+{
+       long flags;
+
+       spin_lock_irqsave(&q->lock, flags);
+       if (q->head == NULL) {
+               q->head = q->tail = p;
+               p->flink = NULL;
+       } else {
+               p->flink = q->head;
+               q->head = p;
+       }
+       q->depth++;
+       spin_unlock_irqrestore(&q->lock, flags);
+}
+
+static inline int smtc_ipi_qdepth(struct smtc_ipi_q *q)
+{
+       long flags;
+       int retval;
+
+       spin_lock_irqsave(&q->lock, flags);
+       retval = q->depth;
+       spin_unlock_irqrestore(&q->lock, flags);
+       return retval;
+}
+
+extern void smtc_send_ipi(int cpu, int type, unsigned int action);
+
+#endif /* __ASM_SMTC_IPI_H */
diff --git a/include/asm-mips/smtc_proc.h b/include/asm-mips/smtc_proc.h
new file mode 100644 (file)
index 0000000..25da651
--- /dev/null
@@ -0,0 +1,23 @@
+/*
+ * Definitions for SMTC /proc entries
+ * Copyright(C) 2005 MIPS Technologies Inc.
+ */
+#ifndef __ASM_SMTC_PROC_H
+#define __ASM_SMTC_PROC_H
+
+/*
+ * per-"CPU" statistics
+ */
+
+struct smtc_cpu_proc {
+       unsigned long timerints;
+       unsigned long selfipis;
+};
+
+extern struct smtc_cpu_proc smtc_cpu_stats[NR_CPUS];
+
+/* Count of number of recoveries of "stolen" FPU access rights on 34K */
+
+extern atomic_t smtc_fpu_recoveries;
+
+#endif /* __ASM_SMTC_PROC_H */
index 2acf3e844f0001951dcad3ed848eccdde9cba824..c4856a874965f3ad851808c9ec7886fd45bcd2a7 100644 (file)
 #include <linux/threads.h>
 
 #include <asm/asm.h>
+#include <asm/asmmacro.h>
 #include <asm/mipsregs.h>
 #include <asm/asm-offsets.h>
 
+#ifdef CONFIG_MIPS_MT_SMTC
+#include <asm/mipsmtregs.h>
+#endif /* CONFIG_MIPS_MT_SMTC */
+
                .macro  SAVE_AT
                .set    push
                .set    noat
 #ifdef CONFIG_SMP
                .macro  get_saved_sp    /* SMP variation */
 #ifdef CONFIG_32BIT
+#ifdef CONFIG_MIPS_MT_SMTC
+               .set    mips32
+               mfc0    k0, CP0_TCBIND;
+               .set    mips0
+               lui     k1, %hi(kernelsp)
+               srl     k0, k0, 19
+               /* No need to shift down and up to clear bits 0-1 */
+#else
                mfc0    k0, CP0_CONTEXT
                lui     k1, %hi(kernelsp)
                srl     k0, k0, 23
+#endif
                addu    k1, k0
                LONG_L  k1, %lo(kernelsp)(k1)
 #endif
 #ifdef CONFIG_64BIT
+#ifdef CONFIG_MIPS_MT_SMTC
+               .set    mips64
+               mfc0    k0, CP0_TCBIND;
+               .set    mips0
+               lui     k0, %highest(kernelsp)
+               dsrl    k1, 19
+               /* No need to shift down and up to clear bits 0-2 */
+#else
                MFC0    k1, CP0_CONTEXT
                lui     k0, %highest(kernelsp)
                dsrl    k1, 23
                dsll    k0, k0, 16
                daddiu  k0, %hi(kernelsp)
                dsll    k0, k0, 16
+#endif /* CONFIG_MIPS_MT_SMTC */
                daddu   k1, k1, k0
                LONG_L  k1, %lo(kernelsp)(k1)
-#endif
+#endif /* CONFIG_64BIT */
                .endm
 
                .macro  set_saved_sp stackp temp temp2
 #ifdef CONFIG_32BIT
+#ifdef CONFIG_MIPS_MT_SMTC
+               mfc0    \temp, CP0_TCBIND
+               srl     \temp, 19
+#else
                mfc0    \temp, CP0_CONTEXT
                srl     \temp, 23
 #endif
+#endif
 #ifdef CONFIG_64BIT
+#ifdef CONFIG_MIPS_MT_SMTC
+               mfc0    \temp, CP0_TCBIND
+               dsrl    \temp, 19
+#else
                MFC0    \temp, CP0_CONTEXT
                dsrl    \temp, 23
+#endif
 #endif
                LONG_S  \stackp, kernelsp(\temp)
                .endm
                PTR_SUBU sp, k1, PT_SIZE
                LONG_S  k0, PT_R29(sp)
                LONG_S  $3, PT_R3(sp)
+               /*
+                * You might think that you don't need to save $0,
+                * but the FPU emulator and gdb remote debug stub
+                * need it to operate correctly
+                */
                LONG_S  $0, PT_R0(sp)
                mfc0    v1, CP0_STATUS
                LONG_S  $2, PT_R2(sp)
                LONG_S  v1, PT_STATUS(sp)
+#ifdef CONFIG_MIPS_MT_SMTC
+               /*
+                * Ideally, these instructions would be shuffled in
+                * to cover the pipeline delay.
+                */
+               .set    mips32
+               mfc0    v1, CP0_TCSTATUS
+               .set    mips0
+               LONG_S  v1, PT_TCSTATUS(sp)
+#endif /* CONFIG_MIPS_MT_SMTC */
                LONG_S  $4, PT_R4(sp)
                mfc0    v1, CP0_CAUSE
                LONG_S  $5, PT_R5(sp)
                .endm
 
 #else
+/*
+ * For SMTC kernel, global IE should be left set, and interrupts
+ * controlled exclusively via IXMT.
+ */
 
+#ifdef CONFIG_MIPS_MT_SMTC
+#define STATMASK 0x1e
+#else
+#define STATMASK 0x1f
+#endif
                .macro  RESTORE_SOME
                .set    push
                .set    reorder
                .set    noat
+#ifdef CONFIG_MIPS_MT_SMTC
+               .set    mips32r2
+               /*
+                * This may not really be necessary if ints are already
+                * inhibited here.
+                */
+               mfc0    v0, CP0_TCSTATUS
+               ori     v0, TCSTATUS_IXMT
+               mtc0    v0, CP0_TCSTATUS
+               ehb
+               DMT     5                               # dmt a1
+               jal     mips_ihb
+#endif /* CONFIG_MIPS_MT_SMTC */
                mfc0    a0, CP0_STATUS
-               ori     a0, 0x1f
-               xori    a0, 0x1f
+               ori     a0, STATMASK
+               xori    a0, STATMASK
                mtc0    a0, CP0_STATUS
                li      v1, 0xff00
                and     a0, v1
                and     v0, v1
                or      v0, a0
                mtc0    v0, CP0_STATUS
+#ifdef CONFIG_MIPS_MT_SMTC
+/*
+ * Only after EXL/ERL have been restored to status can we
+ * restore TCStatus.IXMT.
+ */
+               LONG_L  v1, PT_TCSTATUS(sp)
+               ehb
+               mfc0    v0, CP0_TCSTATUS
+               andi    v1, TCSTATUS_IXMT
+               /* We know that TCStatua.IXMT should be set from above */
+               xori    v0, v0, TCSTATUS_IXMT
+               or      v0, v0, v1
+               mtc0    v0, CP0_TCSTATUS
+               ehb
+               andi    a1, a1, VPECONTROL_TE
+               beqz    a1, 1f
+               emt
+1:
+               .set    mips0
+#endif /* CONFIG_MIPS_MT_SMTC */
                LONG_L  v1, PT_EPC(sp)
                MTC0    v1, CP0_EPC
                LONG_L  $31, PT_R31(sp)
  * Set cp0 enable bit as sign that we're running on the kernel stack
  */
                .macro  CLI
+#if !defined(CONFIG_MIPS_MT_SMTC)
                mfc0    t0, CP0_STATUS
                li      t1, ST0_CU0 | 0x1f
                or      t0, t1
                xori    t0, 0x1f
                mtc0    t0, CP0_STATUS
+#else /* CONFIG_MIPS_MT_SMTC */
+               /*
+                * For SMTC, we need to set privilege
+                * and disable interrupts only for the
+                * current TC, using the TCStatus register.
+                */
+               mfc0    t0,CP0_TCSTATUS
+               /* Fortunately CU 0 is in the same place in both registers */
+               /* Set TCU0, TMX, TKSU (for later inversion) and IXMT */
+               li      t1, ST0_CU0 | 0x08001c00
+               or      t0,t1
+               /* Clear TKSU, leave IXMT */
+               xori    t0, 0x00001800
+               mtc0    t0, CP0_TCSTATUS
+               ehb
+               /* We need to leave the global IE bit set, but clear EXL...*/
+               mfc0    t0, CP0_STATUS
+               ori     t0, ST0_EXL | ST0_ERL
+               xori    t0, ST0_EXL | ST0_ERL
+               mtc0    t0, CP0_STATUS
+#endif /* CONFIG_MIPS_MT_SMTC */
                irq_disable_hazard
                .endm
 
  * Set cp0 enable bit as sign that we're running on the kernel stack
  */
                .macro  STI
+#if !defined(CONFIG_MIPS_MT_SMTC)
                mfc0    t0, CP0_STATUS
                li      t1, ST0_CU0 | 0x1f
                or      t0, t1
                xori    t0, 0x1e
                mtc0    t0, CP0_STATUS
+#else /* CONFIG_MIPS_MT_SMTC */
+               /*
+                * For SMTC, we need to set privilege
+                * and enable interrupts only for the
+                * current TC, using the TCStatus register.
+                */
+               ehb
+               mfc0    t0,CP0_TCSTATUS
+               /* Fortunately CU 0 is in the same place in both registers */
+               /* Set TCU0, TKSU (for later inversion) and IXMT */
+               li      t1, ST0_CU0 | 0x08001c00
+               or      t0,t1
+               /* Clear TKSU *and* IXMT */
+               xori    t0, 0x00001c00
+               mtc0    t0, CP0_TCSTATUS
+               ehb
+               /* We need to leave the global IE bit set, but clear EXL...*/
+               mfc0    t0, CP0_STATUS
+               ori     t0, ST0_EXL
+               xori    t0, ST0_EXL
+               mtc0    t0, CP0_STATUS
+               /* irq_enable_hazard below should expand to EHB for 24K/34K cpus */
+#endif /* CONFIG_MIPS_MT_SMTC */
                irq_enable_hazard
                .endm
 
  * Set cp0 enable bit as sign that we're running on the kernel stack
  */
                .macro  KMODE
+#ifdef CONFIG_MIPS_MT_SMTC
+               /*
+                * This gets baroque in SMTC.  We want to
+                * protect the non-atomic clearing of EXL
+                * with DMT/EMT, but we don't want to take
+                * an interrupt while DMT is still in effect.
+                */
+
+               /* KMODE gets invoked from both reorder and noreorder code */
+               .set    push
+               .set    mips32r2
+               .set    noreorder
+               mfc0    v0, CP0_TCSTATUS
+               andi    v1, v0, TCSTATUS_IXMT
+               ori     v0, TCSTATUS_IXMT
+               mtc0    v0, CP0_TCSTATUS
+               ehb
+               DMT     2                               # dmt   v0
+               /*
+                * We don't know a priori if ra is "live"
+                */
+               move    t0, ra
+               jal     mips_ihb
+               nop     /* delay slot */
+               move    ra, t0
+#endif /* CONFIG_MIPS_MT_SMTC */
                mfc0    t0, CP0_STATUS
                li      t1, ST0_CU0 | 0x1e
                or      t0, t1
                xori    t0, 0x1e
                mtc0    t0, CP0_STATUS
+#ifdef CONFIG_MIPS_MT_SMTC
+               ehb
+               andi    v0, v0, VPECONTROL_TE
+               beqz    v0, 2f
+               nop     /* delay slot */
+               emt
+2:
+               mfc0    v0, CP0_TCSTATUS
+               /* Clear IXMT, then OR in previous value */
+               ori     v0, TCSTATUS_IXMT
+               xori    v0, TCSTATUS_IXMT
+               or      v0, v1, v0
+               mtc0    v0, CP0_TCSTATUS
+               /*
+                * irq_disable_hazard below should expand to EHB
+                * on 24K/34K CPUS
+                */
+               .set pop
+#endif /* CONFIG_MIPS_MT_SMTC */
                irq_disable_hazard
                .endm
 
index 4097fac5ac3cf66874a248b18ae0cba66adffe16..261f71d16a074f4dd4b3ab2fc2d42ba2c583d2e9 100644 (file)
@@ -155,6 +155,37 @@ extern asmlinkage void *resume(void *last, void *next, void *next_ti);
 
 struct task_struct;
 
+#ifdef CONFIG_MIPS_MT_FPAFF
+
+/*
+ * Handle the scheduler resume end of FPU affinity management.  We do this
+ * inline to try to keep the overhead down. If we have been forced to run on
+ * a "CPU" with an FPU because of a previous high level of FP computation,
+ * but did not actually use the FPU during the most recent time-slice (CU1
+ * isn't set), we undo the restriction on cpus_allowed.
+ *
+ * We're not calling set_cpus_allowed() here, because we have no need to
+ * force prompt migration - we're already switching the current CPU to a
+ * different thread.
+ */
+
+#define switch_to(prev,next,last)                                      \
+do {                                                                   \
+       if (cpu_has_fpu &&                                              \
+           (prev->thread.mflags & MF_FPUBOUND) &&                      \
+            (!(KSTK_STATUS(prev) & ST0_CU1))) {                        \
+               prev->thread.mflags &= ~MF_FPUBOUND;                    \
+               prev->cpus_allowed = prev->thread.user_cpus_allowed;    \
+       }                                                               \
+       if (cpu_has_dsp)                                                \
+               __save_dsp(prev);                                       \
+       next->thread.emulated_fp = 0;                                   \
+       (last) = resume(prev, next, next->thread_info);                 \
+       if (cpu_has_dsp)                                                \
+               __restore_dsp(current);                                 \
+} while(0)
+
+#else
 #define switch_to(prev,next,last)                                      \
 do {                                                                   \
        if (cpu_has_dsp)                                                \
@@ -163,6 +194,7 @@ do {                                                                        \
        if (cpu_has_dsp)                                                \
                __restore_dsp(current);                                 \
 } while(0)
+#endif
 
 /*
  * On SMP systems, when the scheduler does migration-cost autodetection,
@@ -440,8 +472,8 @@ static inline unsigned long __cmpxchg(volatile void * ptr, unsigned long old,
 extern void set_handler (unsigned long offset, void *addr, unsigned long len);
 extern void set_uncached_handler (unsigned long offset, void *addr, unsigned long len);
 extern void *set_vi_handler (int n, void *addr);
-extern void *set_vi_srs_handler (int n, void *addr, int regset);
 extern void *set_except_vector(int n, void *addr);
+extern unsigned long ebase;
 extern void per_cpu_trap_init(void);
 
 extern NORET_TYPE void die(const char *, struct pt_regs *);
index b5c78a4a019210cdfd9e140a2c74c3c3fd43158b..1068fe9a0a583cff6f272357733f1f664833a7f7 100644 (file)
 #define __NR_pselect6                  (__NR_Linux + 301)
 #define __NR_ppoll                     (__NR_Linux + 302)
 #define __NR_unshare                   (__NR_Linux + 303)
+#define __NR_splice                    (__NR_Linux + 304)
+#define __NR_sync_file_range           (__NR_Linux + 305)
 
 /*
  * Offset of the last Linux o32 flavoured syscall
  */
-#define __NR_Linux_syscalls            303
+#define __NR_Linux_syscalls            305
 
 #endif /* _MIPS_SIM == _MIPS_SIM_ABI32 */
 
 #define __NR_O32_Linux                 4000
-#define __NR_O32_Linux_syscalls                303
+#define __NR_O32_Linux_syscalls                305
 
 #if _MIPS_SIM == _MIPS_SIM_ABI64
 
 #define __NR_pselect6                  (__NR_Linux + 260)
 #define __NR_ppoll                     (__NR_Linux + 261)
 #define __NR_unshare                   (__NR_Linux + 262)
+#define __NR_splice                    (__NR_Linux + 263)
+#define __NR_sync_file_range           (__NR_Linux + 264)
 
 /*
  * Offset of the last Linux 64-bit flavoured syscall
  */
-#define __NR_Linux_syscalls            262
+#define __NR_Linux_syscalls            264
 
 #endif /* _MIPS_SIM == _MIPS_SIM_ABI64 */
 
 #define __NR_64_Linux                  5000
-#define __NR_64_Linux_syscalls         262
+#define __NR_64_Linux_syscalls         264
 
 #if _MIPS_SIM == _MIPS_SIM_NABI32
 
 #define __NR_pselect6                  (__NR_Linux + 264)
 #define __NR_ppoll                     (__NR_Linux + 265)
 #define __NR_unshare                   (__NR_Linux + 266)
+#define __NR_splice                    (__NR_Linux + 267)
+#define __NR_sync_file_range           (__NR_Linux + 268)
 
 /*
  * Offset of the last N32 flavoured syscall
  */
-#define __NR_Linux_syscalls            266
+#define __NR_Linux_syscalls            268
 
 #endif /* _MIPS_SIM == _MIPS_SIM_NABI32 */
 
 #define __NR_N32_Linux                 6000
-#define __NR_N32_Linux_syscalls                266
+#define __NR_N32_Linux_syscalls                268
 
 #ifndef __ASSEMBLY__
 
diff --git a/include/asm-mips/vpe.h b/include/asm-mips/vpe.h
new file mode 100644 (file)
index 0000000..c6e1b96
--- /dev/null
@@ -0,0 +1,37 @@
+/*
+ * Copyright (C) 2005 MIPS Technologies, Inc.  All rights reserved.
+ *
+ *  This program is free software; you can distribute 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 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.,
+ *  59 Temple Place - Suite 330, Boston MA 02111-1307, USA.
+ *
+ */
+
+#ifndef _ASM_VPE_H
+#define _ASM_VPE_H
+
+struct vpe_notifications {
+       void (*start)(int vpe);
+       void (*stop)(int vpe);
+
+       struct list_head list;
+};
+
+
+extern int vpe_notify(int index, struct vpe_notifications *notify);
+
+extern void *vpe_get_shared(int index);
+extern int vpe_getuid(int index);
+extern int vpe_getgid(int index);
+extern char *vpe_getcwd(int index);
+
+#endif /* _ASM_VPE_H */
diff --git a/include/asm-parisc/numnodes.h b/include/asm-parisc/numnodes.h
deleted file mode 100644 (file)
index 6c67651..0000000
+++ /dev/null
@@ -1,7 +0,0 @@
-#ifndef _ASM_MAX_NUMNODES_H
-#define _ASM_MAX_NUMNODES_H
-
-/* Max 8 Nodes */
-#define NODES_SHIFT    3
-
-#endif /* _ASM_MAX_NUMNODES_H */
index 51f87d9993b6d09e2833f2ff403a58783c61d7bf..7bc6d73b2823c5032852d3b1ae57b8db569795e8 100644 (file)
  */
 extern unsigned int virt_irq_to_real_map[NR_IRQS];
 
+/* The maximum virtual IRQ number that we support.  This
+ * can be set by the platform and will be reduced by the
+ * value of __irq_offset_value.  It defaults to and is
+ * capped by (NR_IRQS - 1).
+ */
+extern unsigned int virt_irq_max;
+
 /* Create a mapping for a real_irq if it doesn't already exist.
  * Return the virtual irq as a convenience.
  */
diff --git a/include/asm-powerpc/numnodes.h b/include/asm-powerpc/numnodes.h
deleted file mode 100644 (file)
index e138eda..0000000
+++ /dev/null
@@ -1,9 +0,0 @@
-#ifndef _ASM_POWERPC_MAX_NUMNODES_H
-#define _ASM_POWERPC_MAX_NUMNODES_H
-#ifdef __KERNEL__
-
-/* Max 16 Nodes */
-#define NODES_SHIFT    4
-
-#endif /* __KERNEL__ */
-#endif /* _ASM_POWERPC_MAX_NUMNODES_H */
index ffc7462d77ba752f1d803a73326a09a48531f026..88b553c6b26c9b461660b8de1f31c98c87c86a68 100644 (file)
@@ -37,6 +37,8 @@ struct thread_info {
        int             preempt_count;          /* 0 => preemptable,
                                                   <0 => BUG */
        struct restart_block restart_block;
+       unsigned long   local_flags;            /* private flags for thread */
+
        /* low level flags - has atomic operations done on it */
        unsigned long   flags ____cacheline_aligned_in_smp;
 };
@@ -143,6 +145,12 @@ static inline struct thread_info *current_thread_info(void)
                                 _TIF_NEED_RESCHED | _TIF_RESTORE_SIGMASK)
 #define _TIF_PERSYSCALL_MASK   (_TIF_RESTOREALL|_TIF_NOERROR)
 
+/* Bits in local_flags */
+/* Don't move TLF_NAPPING without adjusting the code in entry_32.S */
+#define TLF_NAPPING            0       /* idle thread enabled NAP mode */
+
+#define _TLF_NAPPING           (1 << TLF_NAPPING)
+
 #endif /* __KERNEL__ */
 
 #endif /* _ASM_POWERPC_THREAD_INFO_H */
index 536ba0873052c92be7e314446f69b1ae8b5b2e0c..c612f1a6277240edd9ae5526fe1678415fd2f48b 100644 (file)
 #define __NR_ppoll             281
 #define __NR_unshare           282
 #define __NR_splice            283
+#define __NR_tee               284
 
-#define __NR_syscalls          284
+#define __NR_syscalls          285
 
 #ifdef __KERNEL__
 #define __NR__exit __NR_exit
index de1d9926aa60386da7e464b59e45e4bb6784a1c1..399bf02894dd10cf5fc320557484eb0fcb27f7cd 100644 (file)
@@ -1,6 +1,8 @@
 #ifndef __ARCH_S390_ATOMIC__
 #define __ARCH_S390_ATOMIC__
 
+#include <linux/compiler.h>
+
 /*
  *  include/asm-s390/atomic.h
  *
index 4cbc336e4d60ad95a5aa956ccd385e16b702a7e2..15fd2eda6c90191913581024465d59fcfb694e88 100644 (file)
 #include <types.h>
 #endif
 
-extern __u8 _ascebc_500[];   /* ASCII -> EBCDIC 500 conversion table */
-extern __u8 _ebcasc_500[];   /* EBCDIC 500 -> ASCII conversion table */
-extern __u8 _ascebc[];   /* ASCII -> EBCDIC conversion table */
-extern __u8 _ebcasc[];   /* EBCDIC -> ASCII conversion table */
-extern __u8 _ebc_tolower[]; /* EBCDIC -> lowercase */
-extern __u8 _ebc_toupper[]; /* EBCDIC -> uppercase */
+extern __u8 _ascebc_500[256];   /* ASCII -> EBCDIC 500 conversion table */
+extern __u8 _ebcasc_500[256];   /* EBCDIC 500 -> ASCII conversion table */
+extern __u8 _ascebc[256];   /* ASCII -> EBCDIC conversion table */
+extern __u8 _ebcasc[256];   /* EBCDIC -> ASCII conversion table */
+extern __u8 _ebc_tolower[256]; /* EBCDIC -> lowercase */
+extern __u8 _ebc_toupper[256]; /* EBCDIC -> uppercase */
 
 static inline void
 codepage_convert(const __u8 *codepage, volatile __u8 * addr, unsigned long nr)
diff --git a/include/asm-sh/numnodes.h b/include/asm-sh/numnodes.h
deleted file mode 100644 (file)
index f73e85b..0000000
+++ /dev/null
@@ -1,7 +0,0 @@
-#ifndef _ASM_MAX_NUMNODES_H
-#define _ASM_MAX_NUMNODES_H
-
-/* Max 2 Nodes */
-#define NODES_SHIFT    1
-
-#endif /* _ASM_MAX_NUMNODES_H */
index f2c8e14d1fd9c31e65c7d1d9a28a4730c373b43c..05520cebda1289ae4b490342efe3c56cb8a8e2ad 100644 (file)
 #define __NR_mq_timedreceive    (__NR_mq_open+3)
 #define __NR_mq_notify          (__NR_mq_open+4)
 #define __NR_mq_getsetattr      (__NR_mq_open+5)
-#define __NR_sys_kexec_load    283
+#define __NR_kexec_load                283
 #define __NR_waitid            284
 #define __NR_add_key           285
 #define __NR_request_key       286
index 2a1cfa404ea4b1b432c41eef1395882e4aabf465..1f8f394ae37184dd2b2b931f97420d25c4de118d 100644 (file)
 #define __NR_mq_timedreceive    (__NR_mq_open+3)
 #define __NR_mq_notify          (__NR_mq_open+4)
 #define __NR_mq_getsetattr      (__NR_mq_open+5)
-#define __NR_sys_kexec_load    311
+#define __NR_kexec_load                311
 #define __NR_waitid            312
 #define __NR_add_key           313
 #define __NR_request_key       314
index 264f0ebeaedcefde264f9da35d04dc5ee6ad1c21..45feff893b8e0f9df1d5c60b6bd4ec423a150058 100644 (file)
 #define __NR_setfsgid           229 /* Linux Specific                              */
 #define __NR__newselect         230 /* Linux Specific                              */
 #define __NR_time               231 /* Linux Specific                              */
-#define __NR_sys_splice         232 /* Linux Specific                              */
+#define __NR_splice             232 /* Linux Specific                              */
 #define __NR_stime              233 /* Linux Specific                              */
 #define __NR_statfs64           234 /* Linux Specific                              */
 #define __NR_fstatfs64          235 /* Linux Specific                              */
 #define __NR_mq_notify         277
 #define __NR_mq_getsetattr     278
 #define __NR_waitid            279
-#define __NR_sys_setaltroot    280
+#define __NR_tee               280
 #define __NR_add_key           281
 #define __NR_request_key       282
 #define __NR_keyctl            283
diff --git a/include/asm-sparc/vga.h b/include/asm-sparc/vga.h
new file mode 100644 (file)
index 0000000..c69d5b2
--- /dev/null
@@ -0,0 +1,33 @@
+/*
+ *     Access to VGA videoram
+ *
+ *     (c) 1998 Martin Mares <mj@ucw.cz>
+ */
+
+#ifndef _LINUX_ASM_VGA_H_
+#define _LINUX_ASM_VGA_H_
+
+#include <asm/types.h>
+
+#define VT_BUF_HAVE_RW
+
+#undef scr_writew
+#undef scr_readw
+
+static inline void scr_writew(u16 val, u16 *addr)
+{
+       BUG_ON((long) addr >= 0);
+
+       *addr = val;
+}
+
+static inline u16 scr_readw(const u16 *addr)
+{
+       BUG_ON((long) addr >= 0);
+
+       return *addr;
+}
+
+#define VGA_MAP_MEM(x,s) (x)
+
+#endif
index 82032e159a76376040b8ac9084e788f75eeb4e1f..baef13b589525f7b7b9e21fe4dde913def2e40e4 100644 (file)
@@ -26,7 +26,7 @@ register unsigned long __local_per_cpu_offset asm("g5");
 #define percpu_modcopy(pcpudst, src, size)                     \
 do {                                                           \
        unsigned int __i;                                       \
-       for_each_cpu(__i)                                       \
+       for_each_possible_cpu(__i)                              \
                memcpy((pcpudst)+__per_cpu_offset(__i),         \
                       (src), (size));                          \
 } while (0)
index d0544b4f47b75d30744098f551f1374c745dadbb..597f6923a46eec7665cb887a0c2b7e9b51404f1c 100644 (file)
 #ifdef __KERNEL__
 #define __NR_time              231 /* Linux sparc32                               */
 #endif
-#define __NR_sys_splice         232 /* Linux Specific                              */
+#define __NR_splice             232 /* Linux Specific                              */
 #define __NR_stime              233 /* Linux Specific                              */
 #define __NR_statfs64           234 /* Linux Specific                              */
 #define __NR_fstatfs64          235 /* Linux Specific                              */
 #define __NR_mq_notify         277
 #define __NR_mq_getsetattr     278
 #define __NR_waitid            279
-/*#define __NR_sys_setaltroot  280 available (was setaltroot) */
+#define __NR_tee               280
 #define __NR_add_key           281
 #define __NR_request_key       282
 #define __NR_keyctl            283
index 30656c962d7428b889707856b5aad2a08e8fca5b..6e2528bb0083ee4039cc30a5f3ee5aae3bb67e79 100644 (file)
@@ -56,6 +56,9 @@ extern int do_get_thread_area_tt(struct user_desc *info);
 extern int arch_switch_tls_skas(struct task_struct *from, struct task_struct *to);
 extern int arch_switch_tls_tt(struct task_struct *from, struct task_struct *to);
 
+extern void arch_switch_to_tt(struct task_struct *from, struct task_struct *to);
+extern void arch_switch_to_skas(struct task_struct *from, struct task_struct *to);
+
 static inline int do_get_thread_area(struct user_desc *info)
 {
        return CHOOSE_MODE_PROC(do_get_thread_area_tt, do_get_thread_area_skas, info);
index 107decbd6e6cfc038a1729a77154f97ed5f65204..7091af4b786677ca176f08d01127cc6f69361185 100644 (file)
@@ -18,8 +18,6 @@
 #include <asm/ptrace.h>
 
 
-#define prepare_to_switch()    do { } while (0)
-
 /*
  * switch_to(n) should switch tasks to task ptr, first checking that
  * ptr isn't the current task, in which case it does nothing.
index c8043a16152e31fc52d3a48c32ae94ec2155eed9..f8dff1c67538b75381964b6c5c7b4dd3dcc9b37d 100644 (file)
@@ -20,8 +20,8 @@
        __attribute__((__section__(".data.page_aligned")))
 #endif
 
-#define __read_mostly __attribute__((__section__(".data.read_mostly")))
-
 #endif
 
+#define __read_mostly __attribute__((__section__(".data.read_mostly")))
+
 #endif
index 76bb6193ae9107a380ac6b754d5dd498869eef5f..662964b74e348f228fbb9c874567c574d6339175 100644 (file)
@@ -64,6 +64,7 @@
 #define X86_FEATURE_REP_GOOD   (3*32+ 4) /* rep microcode works well on this CPU */
 #define X86_FEATURE_CONSTANT_TSC (3*32+5) /* TSC runs at constant rate */
 #define X86_FEATURE_SYNC_RDTSC  (3*32+6)  /* RDTSC syncs CPU core */
+#define X86_FEATURE_FXSAVE_LEAK (3*32+7)  /* FIP/FOP/FDP leaks through FXSAVE */
 
 /* Intel-defined CPU features, CPUID level 0x00000001 (ecx), word 4 */
 #define X86_FEATURE_XMM3       (4*32+ 0) /* Streaming SIMD Extensions-3 */
index 8dcc32665240fbaa657029e34c65274f8e234fd4..93b51df5168770547bb0fa8393348af343a7e2a8 100644 (file)
@@ -47,7 +47,8 @@ extern void contig_e820_setup(void);
 extern unsigned long e820_end_of_ram(void);
 extern void e820_reserve_resources(void);
 extern void e820_print_map(char *who);
-extern int e820_mapped(unsigned long start, unsigned long end, unsigned type);
+extern int e820_any_mapped(unsigned long start, unsigned long end, unsigned type);
+extern int e820_all_mapped(unsigned long start, unsigned long end, unsigned type);
 
 extern void e820_bootmem_free(pg_data_t *pgdat, unsigned long start,unsigned long end);
 extern void e820_setup_gap(void);
index 08b75c15269ae1fcd01cb2457cddaca1477b239a..18ff7ee9e774c7506ce3fe596a2945ea425c91df 100644 (file)
@@ -51,6 +51,8 @@
 
 #define HPET_TN_ROUTE_SHIFT    9
 
+#define HPET_TICK_RATE (HZ * 100000UL)
+
 extern int is_hpet_enabled(void);
 extern int hpet_rtc_timer_init(void);
 extern int oem_force_hpet_timer(void);
index 876eb9a2fe7868a7c7ce01ef694403b3150f4601..cba8a3b0cded5a77191d9528710b04c85bc13c5b 100644 (file)
@@ -72,6 +72,23 @@ extern int set_fpregs(struct task_struct *tsk,
 #define set_fpu_swd(t,val) ((t)->thread.i387.fxsave.swd = (val))
 #define set_fpu_fxsr_twd(t,val) ((t)->thread.i387.fxsave.twd = (val))
 
+#define X87_FSW_ES (1 << 7)    /* Exception Summary */
+
+/* AMD CPUs don't save/restore FDP/FIP/FOP unless an exception
+   is pending. Clear the x87 state here by setting it to fixed
+   values. The kernel data segment can be sometimes 0 and sometimes
+   new user value. Both should be ok.
+   Use the PDA as safe address because it should be already in L1. */
+static inline void clear_fpu_state(struct i387_fxsave_struct *fx)
+{
+       if (unlikely(fx->swd & X87_FSW_ES))
+                asm volatile("fnclex");
+       alternative_input(ASM_NOP8 ASM_NOP2,
+                    "    emms\n"               /* clear stack tags */
+                    "    fildl %%gs:0",        /* load to clear state */
+                    X86_FEATURE_FXSAVE_LEAK);
+}
+
 static inline int restore_fpu_checking(struct i387_fxsave_struct *fx) 
 { 
        int err;
@@ -119,6 +136,7 @@ static inline int save_i387_checking(struct i387_fxsave_struct __user *fx)
 #endif
        if (unlikely(err))
                __clear_user(fx, sizeof(struct i387_fxsave_struct));
+       /* No need to clear here because the caller clears USED_MATH */
        return err;
 } 
 
@@ -149,7 +167,7 @@ static inline void __fxsave_clear(struct task_struct *tsk)
                                "i" (offsetof(__typeof__(*tsk),
                                              thread.i387.fxsave)));
 #endif
-       __asm__ __volatile__("fnclex");
+       clear_fpu_state(&tsk->thread.i387.fxsave);
 }
 
 static inline void kernel_fpu_begin(void)
index eeb2bcd635de610095baa83a210564777d72ad53..b4f4b172b15ad3908e78fc42c6e6a31041600f78 100644 (file)
 #define __NR_ia32_ppoll                        309
 #define __NR_ia32_unshare              310
 
-#define IA32_NR_syscalls 315   /* must be > than biggest syscall! */
-
 #endif /* _ASM_X86_64_IA32_UNISTD_H_ */
index cafdfb37f0d8a6db30c5ada019fe52747b880b8b..a05da8a50bfdf28a659df356a0d7a7fbf6342409 100644 (file)
@@ -177,7 +177,7 @@ static inline __u16 __readw(const volatile void __iomem *addr)
 {
        return *(__force volatile __u16 *)addr;
 }
-static inline __u32 __readl(const volatile void __iomem *addr)
+static __always_inline __u32 __readl(const volatile void __iomem *addr)
 {
        return *(__force volatile __u32 *)addr;
 }
index 5d298b799a9f5ff6c036efad1b8f6afc6d899820..7229785094e375ff3e8bba0629b787aa66f609f5 100644 (file)
@@ -70,6 +70,9 @@ struct mce_log {
 #define MCE_THRESHOLD_BASE      MCE_EXTENDED_BANK + 1 /* MCE_AMD */
 #define MCE_THRESHOLD_DRAM_ECC  MCE_THRESHOLD_BASE + 4
 
+#ifdef __KERNEL__
+#include <asm/atomic.h>
+
 void mce_log(struct mce *m);
 #ifdef CONFIG_X86_MCE_INTEL
 void mce_intel_feature_init(struct cpuinfo_x86 *c);
@@ -87,4 +90,8 @@ static inline void mce_amd_feature_init(struct cpuinfo_x86 *c)
 }
 #endif
 
+extern atomic_t mce_entry;
+
+#endif
+
 #endif
index 6b18cd8f293d731d4908e52799131e1ff3bcc645..6944e7122df5194c767217444a993a90db3d6ede 100644 (file)
@@ -12,7 +12,8 @@
 
 #include <asm/smp.h>
 
-#define NODEMAPSIZE 0xfff
+/* Should really switch to dynamic allocation at some point */
+#define NODEMAPSIZE 0x4fff
 
 /* Simple perfect hash to map physical addresses to node numbers */
 struct memnode {
index f6cbb4cbb5a3e9bd262c289473dcb3815b5ecf1d..1cc92fe02503d00abee3782364dfad767e19386f 100644 (file)
@@ -2,7 +2,6 @@
 #define _ASM_X8664_NUMA_H 1
 
 #include <linux/nodemask.h>
-#include <asm/numnodes.h>
 
 struct bootnode {
        u64 start,end; 
@@ -18,6 +17,8 @@ extern void numa_init_array(void);
 extern int numa_off;
 
 extern void numa_set_node(int cpu, int node);
+extern void srat_reserve_add_area(int nodeid);
+extern int hotadd_percent;
 
 extern unsigned char apicid_to_node[256];
 #ifdef CONFIG_NUMA
diff --git a/include/asm-x86_64/numnodes.h b/include/asm-x86_64/numnodes.h
deleted file mode 100644 (file)
index 32be16b..0000000
+++ /dev/null
@@ -1,12 +0,0 @@
-#ifndef _ASM_X8664_NUMNODES_H
-#define _ASM_X8664_NUMNODES_H 1
-
-#include <linux/config.h>
-
-#ifdef CONFIG_NUMA
-#define NODES_SHIFT    6
-#else
-#define NODES_SHIFT    0
-#endif
-
-#endif
index 4405b4adeabad5e09a0d014f578dd8f618433740..7f33aaf9f7b1870c1b58d9de974712c004809182 100644 (file)
@@ -26,7 +26,7 @@
 #define percpu_modcopy(pcpudst, src, size)                     \
 do {                                                           \
        unsigned int __i;                                       \
-       for_each_cpu(__i)                                       \
+       for_each_possible_cpu(__i)                              \
                memcpy((pcpudst)+__per_cpu_offset(__i),         \
                       (src), (size));                          \
 } while (0)
index f18443fcdf04c9a0570727e82b2f6d2d221d07f2..b9e5320b76252f06d86fac9f1ac36eeaaa41233b 100644 (file)
@@ -33,7 +33,7 @@ static __always_inline cycles_t get_cycles_sync(void)
        unsigned eax;
        /* Don't do an additional sync on CPUs where we know
           RDTSC is already synchronous. */
-       alternative_io(ASM_NOP2, "cpuid", X86_FEATURE_SYNC_RDTSC,
+       alternative_io("cpuid", ASM_NOP2, X86_FEATURE_SYNC_RDTSC,
                          "=a" (eax), "0" (1) : "ebx","ecx","edx","memory");
        rdtscll(ret);
        return ret;
index f21ff2c1e960bfcafeb735b058857c14f0529a2e..98c36eae567c0fc0d593d0af3974a71492f62b72 100644 (file)
@@ -611,8 +611,12 @@ __SYSCALL(__NR_set_robust_list, sys_set_robust_list)
 __SYSCALL(__NR_get_robust_list, sys_get_robust_list)
 #define __NR_splice            275
 __SYSCALL(__NR_splice, sys_splice)
+#define __NR_tee               276
+__SYSCALL(__NR_tee, sys_tee)
+#define __NR_sync_file_range   277
+__SYSCALL(__NR_sync_file_range, sys_sync_file_range)
 
-#define __NR_syscall_max __NR_splice
+#define __NR_syscall_max __NR_sync_file_range
 
 #ifndef __NO_STUBS
 
index 10c443435c117084abfbf10b204c7254eff26970..3b89a772d0a0b954e5cec7647cdf0890f0db68c5 100644 (file)
 #define TIOCSERSETMULTI _IOW('T', 91, struct serial_multiport_struct) /* Set multiport config */
 
 #define TIOCMIWAIT     _IO('T', 92) /* wait for a change on serial input line(s) */
-#define TIOCGICOUNT    _IOR('T', 93, struct async_icount) /* read serial port inline interrupt counts */
+#define TIOCGICOUNT    0x545D  /* read serial port inline interrupt counts */
 
 #endif /* _XTENSA_IOCTLS_H */
index 9284867f1cb90616cfba4af95b14f42f3059cdd5..b29f7ae6a08ae5a872be5ca443844a4f01dd7362 100644 (file)
@@ -111,8 +111,6 @@ extern void *_switch_to(void *last, void *next);
 
 #endif /* __ASSEMBLY__ */
 
-#define prepare_to_switch()    do { } while(0)
-
 #define switch_to(prev,next,last)              \
 do {                                           \
        clear_cpenable();                       \
index d0cac8b58de7e81b088bc5e85e80ae0587740092..59e1259b1c408ad22a68b25b4b0a2e1580513747 100644 (file)
@@ -17,6 +17,8 @@
 
 #include <asm/scatterlist.h>
 
+struct scsi_ioctl_command;
+
 struct request_queue;
 typedef struct request_queue request_queue_t;
 struct elevator_queue;
@@ -611,6 +613,8 @@ extern void blk_plug_device(request_queue_t *);
 extern int blk_remove_plug(request_queue_t *);
 extern void blk_recount_segments(request_queue_t *, struct bio *);
 extern int scsi_cmd_ioctl(struct file *, struct gendisk *, unsigned int, void __user *);
+extern int sg_scsi_ioctl(struct file *, struct request_queue *,
+               struct gendisk *, struct scsi_ioctl_command __user *);
 extern void blk_start_queue(request_queue_t *q);
 extern void blk_stop_queue(request_queue_t *q);
 extern void blk_sync_queue(struct request_queue *q);
index de3eb8d8ae26d28999e8a12b74c6ddb024749eb8..da2d107fe2cf302cb8aa9c6d14cdae04ee5a5d55 100644 (file)
@@ -45,6 +45,7 @@ extern unsigned long __init bootmem_bootmap_pages (unsigned long);
 extern unsigned long __init init_bootmem (unsigned long addr, unsigned long memend);
 extern void __init free_bootmem (unsigned long addr, unsigned long size);
 extern void * __init __alloc_bootmem (unsigned long size, unsigned long align, unsigned long goal);
+extern void * __init __alloc_bootmem_nopanic (unsigned long size, unsigned long align, unsigned long goal);
 extern void * __init __alloc_bootmem_low(unsigned long size,
                                         unsigned long align,
                                         unsigned long goal);
index 9b4751aecc238d7cbc5ab045ccd7d70cfbe26245..ff61817082fa80271a24f4b2ad70623c013dfc26 100644 (file)
@@ -21,7 +21,7 @@ enum dma_data_direction {
 #define DMA_30BIT_MASK 0x000000003fffffffULL
 #define DMA_29BIT_MASK 0x000000001fffffffULL
 #define DMA_28BIT_MASK 0x000000000fffffffULL
-#define DMA_24BIT_MASK 0x0000000000ffffffULL
+#define DMA_24BIT_MASK 0x0000000000ffffffULL
 
 #include <asm/dma-mapping.h>
 
index 16be62041bfec6a7984e8e2080f01d32f94d6e67..ff56c0bec43cdfe3dae236685d3f4e8b01e689d7 100644 (file)
@@ -762,7 +762,7 @@ extern int fcntl_getlease(struct file *filp);
 #define SYNC_FILE_RANGE_WRITE          2
 #define SYNC_FILE_RANGE_WAIT_AFTER     4
 extern int do_sync_file_range(struct file *file, loff_t offset, loff_t endbyte,
-                       int flags);
+                       unsigned int flags);
 
 /* fs/locks.c */
 extern void locks_init_lock(struct file_lock *);
@@ -1039,8 +1039,8 @@ struct file_operations {
        int (*check_flags)(int);
        int (*dir_notify)(struct file *filp, unsigned long arg);
        int (*flock) (struct file *, int, struct file_lock *);
-       ssize_t (*splice_write)(struct inode *, struct file *, size_t, unsigned int);
-       ssize_t (*splice_read)(struct file *, struct inode *, size_t, unsigned int);
+       ssize_t (*splice_write)(struct pipe_inode_info *, struct file *, loff_t *, size_t, unsigned int);
+       ssize_t (*splice_read)(struct file *, loff_t *, struct pipe_inode_info *, size_t, unsigned int);
 };
 
 struct inode_operations {
@@ -1614,8 +1614,17 @@ extern ssize_t generic_file_sendfile(struct file *, loff_t *, size_t, read_actor
 extern void do_generic_mapping_read(struct address_space *mapping,
                                    struct file_ra_state *, struct file *,
                                    loff_t *, read_descriptor_t *, read_actor_t);
-extern ssize_t generic_file_splice_read(struct file *, struct inode *, size_t, unsigned int);
-extern ssize_t generic_file_splice_write(struct inode *, struct file *, size_t, unsigned int);
+
+/* fs/splice.c */
+extern ssize_t generic_file_splice_read(struct file *, loff_t *,
+               struct pipe_inode_info *, size_t, unsigned int);
+extern ssize_t generic_file_splice_write(struct pipe_inode_info *,
+               struct file *, loff_t *, size_t, unsigned int);
+extern ssize_t generic_splice_sendpage(struct pipe_inode_info *pipe,
+               struct file *out, loff_t *, size_t len, unsigned int flags);
+extern long do_splice_direct(struct file *in, loff_t *ppos, struct file *out,
+               size_t len, unsigned int flags);
+
 extern void
 file_ra_state_init(struct file_ra_state *ra, struct address_space *mapping);
 extern ssize_t generic_file_readv(struct file *filp, const struct iovec *iov, 
index 10a27f29d6925514265aa39834642bb58dd4c493..2ef845b35175815b8823e35bf6c23723725c13d3 100644 (file)
@@ -105,6 +105,7 @@ struct gendisk {
                                          * disks that can't be partitioned. */
        char disk_name[32];             /* name of major driver */
        struct hd_struct **part;        /* [indexed by minor] */
+       int part_uevent_suppress;
        struct block_device_operations *fops;
        struct request_queue *queue;
        void *private_data;
index 7851e6b520cf013f4091cd4932f69cb4b00e76b5..3ac452945a7d58fdbe7c4e59fed4373f904798f7 100644 (file)
@@ -57,6 +57,8 @@ struct vm_area_struct;
                        __GFP_NOFAIL|__GFP_NORETRY|__GFP_NO_GROW|__GFP_COMP| \
                        __GFP_NOMEMALLOC|__GFP_HARDWALL)
 
+/* This equals 0, but use constants in case they ever change */
+#define GFP_NOWAIT     (GFP_ATOMIC & ~__GFP_HIGH)
 /* GFP_ATOMIC means both !wait (__GFP_WAIT not set) and use emergency pool */
 #define GFP_ATOMIC     (__GFP_HIGH)
 #define GFP_NOIO       (__GFP_WAIT)
index 8d2db412ba9ca2f46f9161642b70705d68f7fe03..a8bef1d1371cc999ce6882d355c7554ca7738173 100644 (file)
@@ -1220,7 +1220,6 @@ typedef struct ide_pci_enablebit_s {
 enum {
        /* Uses ISA control ports not PCI ones. */
        IDEPCI_FLAG_ISA_PORTS           = (1 << 0),
-       IDEPCI_FLAG_FORCE_PDC           = (1 << 1),
 };
 
 typedef struct ide_pci_device_s {
index ed0ac7c39fdc49bc83c9db2dc885d1ec63046873..93dcbe1abb4c83b65cc6af59fb84c3c5e16effbb 100644 (file)
@@ -245,7 +245,8 @@ void __init parse_early_param(void);
 #define __cpuexitdata  __exitdata
 #endif
 
-#ifdef CONFIG_MEMORY_HOTPLUG
+#if defined(CONFIG_MEMORY_HOTPLUG) || defined(CONFIG_ACPI_HOTPLUG_MEMORY) \
+       || defined(CONFIG_ACPI_HOTPLUG_MEMORY_MODULE)
 #define __meminit
 #define __meminitdata
 #define __memexit
index 99905e180532e094c2efb0fc8c3ce6c66c63d92b..043376920f51af0aaa317459a8172b00c814dab0 100644 (file)
@@ -36,6 +36,8 @@
 /* LATCH is used in the interval timer and ftape setup. */
 #define LATCH  ((CLOCK_TICK_RATE + HZ/2) / HZ) /* For divider */
 
+#define LATCH_HPET ((HPET_TICK_RATE + HZ/2) / HZ)
+
 /* Suppose we want to devide two numbers NOM and DEN: NOM/DEN, the we can
  * improve accuracy by shifting LSH bits, hence calculating:
  *     (NOM << LSH) / DEN
 /* HZ is the requested value. ACTHZ is actual HZ ("<< 8" is for accuracy) */
 #define ACTHZ (SH_DIV (CLOCK_TICK_RATE, LATCH, 8))
 
+#define ACTHZ_HPET (SH_DIV (HPET_TICK_RATE, LATCH_HPET, 8))
+
 /* TICK_NSEC is the time between ticks in nsec assuming real ACTHZ */
 #define TICK_NSEC (SH_DIV (1000000UL * 1000, ACTHZ, 8))
 
+#define TICK_NSEC_HPET (SH_DIV(1000000UL * 1000, ACTHZ_HPET, 8))
+
 /* TICK_USEC is the time between ticks in usec assuming fake USER_HZ */
 #define TICK_USEC ((1000000UL + USER_HZ/2) / USER_HZ)
 
index c73ed0b05591ab97ba07e61d7020e53a10dbee5f..2ae50277f581a030cd2f235c4c955baa9d4fb49f 100644 (file)
@@ -177,7 +177,7 @@ static inline void console_verbose(void)
 
 extern void bust_spinlocks(int yes);
 extern int oops_in_progress;           /* If set, an oops, panic(), BUG() or die() is in progress */
-extern __deprecated_for_modules int panic_timeout;
+extern int panic_timeout;
 extern int panic_on_oops;
 extern int tainted;
 extern const char *print_tainted(void);
index 4cb1214ec29091919215d5db84323f68b638590e..dcd0623be892fb522d82b698f51365f760f8a03d 100644 (file)
@@ -24,6 +24,7 @@
 #include <linux/rwsem.h>
 #include <linux/kref.h>
 #include <linux/kernel.h>
+#include <linux/wait.h>
 #include <asm/atomic.h>
 
 #define KOBJ_NAME_LEN                  20
@@ -56,6 +57,7 @@ struct kobject {
        struct kset             * kset;
        struct kobj_type        * ktype;
        struct dentry           * dentry;
+       wait_queue_head_t       poll;
 };
 
 extern int kobject_set_name(struct kobject *, const char *, ...)
index 4617e75903b007b411788f0e5fb61156cfd95535..dc23c7c639f321f9bbb857d2176130c3316c4489 100644 (file)
@@ -19,39 +19,38 @@ struct class_device;
  */
 
 enum led_brightness {
-       LED_OFF = 0,
-       LED_HALF = 127,
-       LED_FULL = 255,
+       LED_OFF         = 0,
+       LED_HALF        = 127,
+       LED_FULL        = 255,
 };
 
 struct led_classdev {
-       const char *name;
-       int brightness;
-       int flags;
-#define LED_SUSPENDED       (1 << 0)
+       const char              *name;
+       int                      brightness;
+       int                      flags;
 
-       /* A function to set the brightness of the led */
-       void (*brightness_set)(struct led_classdev *led_cdev,
-                               enum led_brightness brightness);
+#define LED_SUSPENDED          (1 << 0)
 
-       struct class_device *class_dev;
-       /* LED Device linked list */
-       struct list_head node;
+       /* Set LED brightness level */
+       void            (*brightness_set)(struct led_classdev *led_cdev,
+                                         enum led_brightness brightness);
+
+       struct class_device     *class_dev;
+       struct list_head         node;                  /* LED Device list */
+       char                    *default_trigger;       /* Trigger to use */
 
-       /* Trigger data */
-       char *default_trigger;
 #ifdef CONFIG_LEDS_TRIGGERS
-       rwlock_t trigger_lock;
        /* Protects the trigger data below */
+       rwlock_t                 trigger_lock;
 
-       struct led_trigger *trigger;
-       struct list_head trig_list;
-       void *trigger_data;
+       struct led_trigger      *trigger;
+       struct list_head         trig_list;
+       void                    *trigger_data;
 #endif
 };
 
 extern int led_classdev_register(struct device *parent,
-                               struct led_classdev *led_cdev);
+                                struct led_classdev *led_cdev);
 extern void led_classdev_unregister(struct led_classdev *led_cdev);
 extern void led_classdev_suspend(struct led_classdev *led_cdev);
 extern void led_classdev_resume(struct led_classdev *led_cdev);
@@ -65,16 +64,16 @@ extern void led_classdev_resume(struct led_classdev *led_cdev);
 
 struct led_trigger {
        /* Trigger Properties */
-       const char *name;
-       void (*activate)(struct led_classdev *led_cdev);
-       void (*deactivate)(struct led_classdev *led_cdev);
+       const char       *name;
+       void            (*activate)(struct led_classdev *led_cdev);
+       void            (*deactivate)(struct led_classdev *led_cdev);
 
        /* LEDs under control by this trigger (for simple triggers) */
-       rwlock_t leddev_list_lock;
-       struct list_head led_cdevs;
+       rwlock_t          leddev_list_lock;
+       struct list_head  led_cdevs;
 
        /* Link to next registered trigger */
-       struct list_head next_trig;
+       struct list_head  next_trig;
 };
 
 /* Registration functions for complex triggers */
index 0d61357604d5b24726c9dd2fd410b264a75182bb..b80d2e7fa6d25ba608c11d5bd0ca790c0653dfe1 100644 (file)
@@ -523,7 +523,6 @@ extern void ata_host_set_remove(struct ata_host_set *host_set);
 extern int ata_scsi_detect(struct scsi_host_template *sht);
 extern int ata_scsi_ioctl(struct scsi_device *dev, int cmd, void __user *arg);
 extern int ata_scsi_queuecmd(struct scsi_cmnd *cmd, void (*done)(struct scsi_cmnd *));
-extern int ata_scsi_error(struct Scsi_Host *host);
 extern void ata_eh_qc_complete(struct ata_queued_cmd *qc);
 extern void ata_eh_qc_retry(struct ata_queued_cmd *qc);
 extern int ata_scsi_release(struct Scsi_Host *host);
index 968b1aa3732cb1fe13f7f3ea81df13722375000d..911206386171ccedc51397d9e36a7c424de9642c 100644 (file)
@@ -58,8 +58,6 @@ extern int add_one_highpage(struct page *page, int pfn, int bad_ppro);
 /* need some defines for these for archs that don't support it */
 extern void online_page(struct page *page);
 /* VM interface that may be used by firmware interface */
-extern int add_memory(u64 start, u64 size);
-extern int remove_memory(u64 start, u64 size);
 extern int online_pages(unsigned long, unsigned long);
 
 /* reasonably generic interface to expand the physical pages in a zone  */
@@ -92,11 +90,6 @@ static inline int mhp_notimplemented(const char *func)
        return -ENOSYS;
 }
 
-static inline int __add_pages(struct zone *zone, unsigned long start_pfn,
-       unsigned long nr_pages)
-{
-       return mhp_notimplemented(__FUNCTION__);
-}
 #endif /* ! CONFIG_MEMORY_HOTPLUG */
 static inline int __remove_pages(struct zone *zone, unsigned long start_pfn,
        unsigned long nr_pages)
@@ -105,4 +98,8 @@ static inline int __remove_pages(struct zone *zone, unsigned long start_pfn,
        dump_stack();
        return -ENOSYS;
 }
+
+extern int add_memory(u64 start, u64 size);
+extern int remove_memory(u64 start, u64 size);
+
 #endif /* __LINUX_MEMORY_HOTPLUG_H */
index 6aa016f1d3ae05d4b29e2076431219283b4c689a..1154684209a4458d1507702e1c4a778d942eda94 100644 (file)
@@ -229,10 +229,9 @@ struct page {
                unsigned long private;          /* Mapping-private opaque data:
                                                 * usually used for buffer_heads
                                                 * if PagePrivate set; used for
-                                                * swp_entry_t if PageSwapCache.
-                                                * When page is free, this
+                                                * swp_entry_t if PageSwapCache;
                                                 * indicates order in the buddy
-                                                * system.
+                                                * system if PG_buddy is set.
                                                 */
                struct address_space *mapping;  /* If low bit clear, points to
                                                 * inode address_space, or NULL.
index 955d3069d7271dd0dfc65a26f9e122b7b7b502af..edfa012fad3a93dd1e25b0f84d9bf166a225221e 100644 (file)
@@ -13,7 +13,7 @@
 #ifndef __ASM_MV643XX_H
 #define __ASM_MV643XX_H
 
-#ifdef __MIPS__
+#ifdef __mips__
 #include <asm/addrspace.h>
 #include <asm/marvell.h>
 #endif
index 412e52ca9720c7d942948b904554cf6052a8ac16..b31a9bca9361307a6ce997c029634a58e2cd4939 100644 (file)
@@ -110,6 +110,8 @@ struct nf_info
 /* Function to register/unregister hook points. */
 int nf_register_hook(struct nf_hook_ops *reg);
 void nf_unregister_hook(struct nf_hook_ops *reg);
+int nf_register_hooks(struct nf_hook_ops *reg, unsigned int n);
+void nf_unregister_hooks(struct nf_hook_ops *reg, unsigned int n);
 
 /* Functions to register get/setsockopt ranges (non-inclusive).  You
    need to check permissions yourself! */
@@ -281,16 +283,42 @@ extern void nf_invalidate_cache(int pf);
    Returns true or false. */
 extern int skb_make_writable(struct sk_buff **pskb, unsigned int writable_len);
 
-struct nf_queue_rerouter {
-       void (*save)(const struct sk_buff *skb, struct nf_info *info);
-       int (*reroute)(struct sk_buff **skb, const struct nf_info *info);
-       int rer_size;
+struct nf_afinfo {
+       unsigned short  family;
+       unsigned int    (*checksum)(struct sk_buff *skb, unsigned int hook,
+                                   unsigned int dataoff, u_int8_t protocol);
+       void            (*saveroute)(const struct sk_buff *skb,
+                                    struct nf_info *info);
+       int             (*reroute)(struct sk_buff **skb,
+                                  const struct nf_info *info);
+       int             route_key_size;
 };
 
-#define nf_info_reroute(x) ((void *)x + sizeof(struct nf_info))
+extern struct nf_afinfo *nf_afinfo[];
+static inline struct nf_afinfo *nf_get_afinfo(unsigned short family)
+{
+       return rcu_dereference(nf_afinfo[family]);
+}
+
+static inline unsigned int
+nf_checksum(struct sk_buff *skb, unsigned int hook, unsigned int dataoff,
+           u_int8_t protocol, unsigned short family)
+{
+       struct nf_afinfo *afinfo;
+       unsigned int csum = 0;
+
+       rcu_read_lock();
+       afinfo = nf_get_afinfo(family);
+       if (afinfo)
+               csum = afinfo->checksum(skb, hook, dataoff, protocol);
+       rcu_read_unlock();
+       return csum;
+}
 
-extern int nf_register_queue_rerouter(int pf, struct nf_queue_rerouter *rer);
-extern int nf_unregister_queue_rerouter(int pf);
+extern int nf_register_afinfo(struct nf_afinfo *afinfo);
+extern void nf_unregister_afinfo(struct nf_afinfo *afinfo);
+
+#define nf_info_reroute(x) ((void *)x + sizeof(struct nf_info))
 
 #include <net/flow.h>
 extern void (*ip_nat_decode_session)(struct sk_buff *, struct flowi *);
index 43c09d790b838151aba69d891638801a57e1e9d0..85301c5e8d246b8093a0e2d788cc68153efa5cab 100644 (file)
@@ -80,6 +80,8 @@ enum nf_ip_hook_priorities {
 #ifdef __KERNEL__
 extern int ip_route_me_harder(struct sk_buff **pskb);
 extern int ip_xfrm_me_harder(struct sk_buff **pskb);
+extern unsigned int nf_ip_checksum(struct sk_buff *skb, unsigned int hook,
+                                  unsigned int dataoff, u_int8_t protocol);
 #endif /*__KERNEL__*/
 
 #endif /*__LINUX_IP_NETFILTER_H*/
index 0987cea538403cd8a31d54219e788a7e15fc3b40..eace86bd2adbe0462abe44d5c1d6b7d5fc2523b0 100644 (file)
@@ -3,6 +3,8 @@
 
 #ifdef __KERNEL__
 
+#include <linux/netfilter_ipv4/ip_conntrack_helper_h323_asn1.h>
+
 #define RAS_PORT 1719
 #define Q931_PORT 1720
 #define H323_RTP_CHANNEL_MAX 4 /* Audio, video, FAX and other */
@@ -25,6 +27,56 @@ struct ip_ct_h323_master {
        };
 };
 
+struct ip_conntrack_expect;
+
+extern int get_h225_addr(unsigned char *data, TransportAddress * addr,
+                        u_int32_t * ip, u_int16_t * port);
+extern void ip_conntrack_h245_expect(struct ip_conntrack *new,
+                                    struct ip_conntrack_expect *this);
+extern void ip_conntrack_q931_expect(struct ip_conntrack *new,
+                                    struct ip_conntrack_expect *this);
+extern int (*set_h245_addr_hook) (struct sk_buff ** pskb,
+                                 unsigned char **data, int dataoff,
+                                 H245_TransportAddress * addr,
+                                 u_int32_t ip, u_int16_t port);
+extern int (*set_h225_addr_hook) (struct sk_buff ** pskb,
+                                 unsigned char **data, int dataoff,
+                                 TransportAddress * addr,
+                                 u_int32_t ip, u_int16_t port);
+extern int (*set_sig_addr_hook) (struct sk_buff ** pskb,
+                                struct ip_conntrack * ct,
+                                enum ip_conntrack_info ctinfo,
+                                unsigned char **data,
+                                TransportAddress * addr, int count);
+extern int (*set_ras_addr_hook) (struct sk_buff ** pskb,
+                                struct ip_conntrack * ct,
+                                enum ip_conntrack_info ctinfo,
+                                unsigned char **data,
+                                TransportAddress * addr, int count);
+extern int (*nat_rtp_rtcp_hook) (struct sk_buff ** pskb,
+                                struct ip_conntrack * ct,
+                                enum ip_conntrack_info ctinfo,
+                                unsigned char **data, int dataoff,
+                                H245_TransportAddress * addr,
+                                u_int16_t port, u_int16_t rtp_port,
+                                struct ip_conntrack_expect * rtp_exp,
+                                struct ip_conntrack_expect * rtcp_exp);
+extern int (*nat_t120_hook) (struct sk_buff ** pskb, struct ip_conntrack * ct,
+                            enum ip_conntrack_info ctinfo,
+                            unsigned char **data, int dataoff,
+                            H245_TransportAddress * addr, u_int16_t port,
+                            struct ip_conntrack_expect * exp);
+extern int (*nat_h245_hook) (struct sk_buff ** pskb, struct ip_conntrack * ct,
+                            enum ip_conntrack_info ctinfo,
+                            unsigned char **data, int dataoff,
+                            TransportAddress * addr, u_int16_t port,
+                            struct ip_conntrack_expect * exp);
+extern int (*nat_q931_hook) (struct sk_buff ** pskb, struct ip_conntrack * ct,
+                            enum ip_conntrack_info ctinfo,
+                            unsigned char **data, TransportAddress * addr,
+                            int idx, u_int16_t port,
+                            struct ip_conntrack_expect * exp);
+
 #endif
 
 #endif
diff --git a/include/linux/netfilter_ipv4/ip_conntrack_helper_h323_asn1.h b/include/linux/netfilter_ipv4/ip_conntrack_helper_h323_asn1.h
new file mode 100644 (file)
index 0000000..0bd8280
--- /dev/null
@@ -0,0 +1,98 @@
+/****************************************************************************
+ * ip_conntrack_helper_h323_asn1.h - BER and PER decoding library for H.323
+ *                                  conntrack/NAT module.
+ *
+ * Copyright (c) 2006 by Jing Min Zhao <zhaojingmin@hotmail.com>
+ *
+ * This source code is licensed under General Public License version 2.
+ *
+ *
+ * This library is based on H.225 version 4, H.235 version 2 and H.245
+ * version 7. It is extremely optimized to decode only the absolutely
+ * necessary objects in a signal for Linux kernel NAT module use, so don't
+ * expect it to be a full ASN.1 library.
+ *
+ * Features:
+ *
+ * 1. Small. The total size of code plus data is less than 20 KB (IA32).
+ * 2. Fast. Decoding Netmeeting's Setup signal 1 million times on a PIII 866
+ *    takes only 3.9 seconds.
+ * 3. No memory allocation. It uses a static object. No need to initialize or
+ *    cleanup.
+ * 4. Thread safe.
+ * 5. Support embedded architectures that has no misaligned memory access
+ *    support.
+ *
+ * Limitations:
+ *
+ * 1. At most 30 faststart entries. Actually this is limited by ethernet's MTU.
+ *    If a Setup signal contains more than 30 faststart, the packet size will
+ *    very likely exceed the MTU size, then the TPKT will be fragmented. I
+ *    don't know how to handle this in a Netfilter module. Anybody can help?
+ *    Although I think 30 is enough for most of the cases.
+ * 2. IPv4 addresses only.
+ *
+ ****************************************************************************/
+
+#ifndef _IP_CONNTRACK_HELPER_H323_ASN1_H_
+#define _IP_CONNTRACK_HELPER_H323_ASN1_H_
+
+/*****************************************************************************
+ * H.323 Types
+ ****************************************************************************/
+#include "ip_conntrack_helper_h323_types.h"
+
+typedef struct {
+       enum {
+               Q931_NationalEscape = 0x00,
+               Q931_Alerting = 0x01,
+               Q931_CallProceeding = 0x02,
+               Q931_Connect = 0x07,
+               Q931_ConnectAck = 0x0F,
+               Q931_Progress = 0x03,
+               Q931_Setup = 0x05,
+               Q931_SetupAck = 0x0D,
+               Q931_Resume = 0x26,
+               Q931_ResumeAck = 0x2E,
+               Q931_ResumeReject = 0x22,
+               Q931_Suspend = 0x25,
+               Q931_SuspendAck = 0x2D,
+               Q931_SuspendReject = 0x21,
+               Q931_UserInformation = 0x20,
+               Q931_Disconnect = 0x45,
+               Q931_Release = 0x4D,
+               Q931_ReleaseComplete = 0x5A,
+               Q931_Restart = 0x46,
+               Q931_RestartAck = 0x4E,
+               Q931_Segment = 0x60,
+               Q931_CongestionCtrl = 0x79,
+               Q931_Information = 0x7B,
+               Q931_Notify = 0x6E,
+               Q931_Status = 0x7D,
+               Q931_StatusEnquiry = 0x75,
+               Q931_Facility = 0x62
+       } MessageType;
+       H323_UserInformation UUIE;
+} Q931;
+
+/*****************************************************************************
+ * Decode Functions Return Codes
+ ****************************************************************************/
+
+#define H323_ERROR_NONE 0      /* Decoded successfully */
+#define H323_ERROR_STOP 1      /* Decoding stopped, not really an error */
+#define H323_ERROR_BOUND -1
+#define H323_ERROR_RANGE -2
+
+
+/*****************************************************************************
+ * Decode Functions
+ ****************************************************************************/
+
+int DecodeRasMessage(unsigned char *buf, size_t sz, RasMessage * ras);
+int DecodeQ931(unsigned char *buf, size_t sz, Q931 * q931);
+int DecodeMultimediaSystemControlMessage(unsigned char *buf, size_t sz,
+                                        MultimediaSystemControlMessage *
+                                        mscm);
+
+#endif
diff --git a/include/linux/netfilter_ipv4/ip_conntrack_helper_h323_types.h b/include/linux/netfilter_ipv4/ip_conntrack_helper_h323_types.h
new file mode 100644 (file)
index 0000000..cc98f7a
--- /dev/null
@@ -0,0 +1,938 @@
+/* Generated by Jing Min Zhao's ASN.1 parser, Mar 15 2006
+ *
+ * Copyright (c) 2006 Jing Min Zhao <zhaojingmin@users.sourceforge.net>
+ *
+ * This source code is licensed under General Public License version 2.
+ */
+
+typedef struct TransportAddress_ipAddress {    /* SEQUENCE */
+       int options;            /* No use */
+       unsigned ip;
+} TransportAddress_ipAddress;
+
+typedef struct TransportAddress {      /* CHOICE */
+       enum {
+               eTransportAddress_ipAddress,
+               eTransportAddress_ipSourceRoute,
+               eTransportAddress_ipxAddress,
+               eTransportAddress_ip6Address,
+               eTransportAddress_netBios,
+               eTransportAddress_nsap,
+               eTransportAddress_nonStandardAddress,
+       } choice;
+       union {
+               TransportAddress_ipAddress ipAddress;
+       };
+} TransportAddress;
+
+typedef struct DataProtocolCapability {        /* CHOICE */
+       enum {
+               eDataProtocolCapability_nonStandard,
+               eDataProtocolCapability_v14buffered,
+               eDataProtocolCapability_v42lapm,
+               eDataProtocolCapability_hdlcFrameTunnelling,
+               eDataProtocolCapability_h310SeparateVCStack,
+               eDataProtocolCapability_h310SingleVCStack,
+               eDataProtocolCapability_transparent,
+               eDataProtocolCapability_segmentationAndReassembly,
+               eDataProtocolCapability_hdlcFrameTunnelingwSAR,
+               eDataProtocolCapability_v120,
+               eDataProtocolCapability_separateLANStack,
+               eDataProtocolCapability_v76wCompression,
+               eDataProtocolCapability_tcp,
+               eDataProtocolCapability_udp,
+       } choice;
+} DataProtocolCapability;
+
+typedef struct DataApplicationCapability_application { /* CHOICE */
+       enum {
+               eDataApplicationCapability_application_nonStandard,
+               eDataApplicationCapability_application_t120,
+               eDataApplicationCapability_application_dsm_cc,
+               eDataApplicationCapability_application_userData,
+               eDataApplicationCapability_application_t84,
+               eDataApplicationCapability_application_t434,
+               eDataApplicationCapability_application_h224,
+               eDataApplicationCapability_application_nlpid,
+               eDataApplicationCapability_application_dsvdControl,
+               eDataApplicationCapability_application_h222DataPartitioning,
+               eDataApplicationCapability_application_t30fax,
+               eDataApplicationCapability_application_t140,
+               eDataApplicationCapability_application_t38fax,
+               eDataApplicationCapability_application_genericDataCapability,
+       } choice;
+       union {
+               DataProtocolCapability t120;
+       };
+} DataApplicationCapability_application;
+
+typedef struct DataApplicationCapability {     /* SEQUENCE */
+       int options;            /* No use */
+       DataApplicationCapability_application application;
+} DataApplicationCapability;
+
+typedef struct DataType {      /* CHOICE */
+       enum {
+               eDataType_nonStandard,
+               eDataType_nullData,
+               eDataType_videoData,
+               eDataType_audioData,
+               eDataType_data,
+               eDataType_encryptionData,
+               eDataType_h235Control,
+               eDataType_h235Media,
+               eDataType_multiplexedStream,
+       } choice;
+       union {
+               DataApplicationCapability data;
+       };
+} DataType;
+
+typedef struct UnicastAddress_iPAddress {      /* SEQUENCE */
+       int options;            /* No use */
+       unsigned network;
+} UnicastAddress_iPAddress;
+
+typedef struct UnicastAddress {        /* CHOICE */
+       enum {
+               eUnicastAddress_iPAddress,
+               eUnicastAddress_iPXAddress,
+               eUnicastAddress_iP6Address,
+               eUnicastAddress_netBios,
+               eUnicastAddress_iPSourceRouteAddress,
+               eUnicastAddress_nsap,
+               eUnicastAddress_nonStandardAddress,
+       } choice;
+       union {
+               UnicastAddress_iPAddress iPAddress;
+       };
+} UnicastAddress;
+
+typedef struct H245_TransportAddress { /* CHOICE */
+       enum {
+               eH245_TransportAddress_unicastAddress,
+               eH245_TransportAddress_multicastAddress,
+       } choice;
+       union {
+               UnicastAddress unicastAddress;
+       };
+} H245_TransportAddress;
+
+typedef struct H2250LogicalChannelParameters { /* SEQUENCE */
+       enum {
+               eH2250LogicalChannelParameters_nonStandard = (1 << 31),
+               eH2250LogicalChannelParameters_associatedSessionID =
+                   (1 << 30),
+               eH2250LogicalChannelParameters_mediaChannel = (1 << 29),
+               eH2250LogicalChannelParameters_mediaGuaranteedDelivery =
+                   (1 << 28),
+               eH2250LogicalChannelParameters_mediaControlChannel =
+                   (1 << 27),
+               eH2250LogicalChannelParameters_mediaControlGuaranteedDelivery
+                   = (1 << 26),
+               eH2250LogicalChannelParameters_silenceSuppression = (1 << 25),
+               eH2250LogicalChannelParameters_destination = (1 << 24),
+               eH2250LogicalChannelParameters_dynamicRTPPayloadType =
+                   (1 << 23),
+               eH2250LogicalChannelParameters_mediaPacketization = (1 << 22),
+               eH2250LogicalChannelParameters_transportCapability =
+                   (1 << 21),
+               eH2250LogicalChannelParameters_redundancyEncoding = (1 << 20),
+               eH2250LogicalChannelParameters_source = (1 << 19),
+       } options;
+       H245_TransportAddress mediaChannel;
+       H245_TransportAddress mediaControlChannel;
+} H2250LogicalChannelParameters;
+
+typedef struct OpenLogicalChannel_forwardLogicalChannelParameters_multiplexParameters {        /* CHOICE */
+       enum {
+               eOpenLogicalChannel_forwardLogicalChannelParameters_multiplexParameters_h222LogicalChannelParameters,
+               eOpenLogicalChannel_forwardLogicalChannelParameters_multiplexParameters_h223LogicalChannelParameters,
+               eOpenLogicalChannel_forwardLogicalChannelParameters_multiplexParameters_v76LogicalChannelParameters,
+               eOpenLogicalChannel_forwardLogicalChannelParameters_multiplexParameters_h2250LogicalChannelParameters,
+               eOpenLogicalChannel_forwardLogicalChannelParameters_multiplexParameters_none,
+       } choice;
+       union {
+               H2250LogicalChannelParameters h2250LogicalChannelParameters;
+       };
+} OpenLogicalChannel_forwardLogicalChannelParameters_multiplexParameters;
+
+typedef struct OpenLogicalChannel_forwardLogicalChannelParameters {    /* SEQUENCE */
+       enum {
+               eOpenLogicalChannel_forwardLogicalChannelParameters_portNumber
+                   = (1 << 31),
+               eOpenLogicalChannel_forwardLogicalChannelParameters_forwardLogicalChannelDependency
+                   = (1 << 30),
+               eOpenLogicalChannel_forwardLogicalChannelParameters_replacementFor
+                   = (1 << 29),
+       } options;
+       DataType dataType;
+       OpenLogicalChannel_forwardLogicalChannelParameters_multiplexParameters
+           multiplexParameters;
+} OpenLogicalChannel_forwardLogicalChannelParameters;
+
+typedef struct OpenLogicalChannel_reverseLogicalChannelParameters_multiplexParameters {        /* CHOICE */
+       enum {
+               eOpenLogicalChannel_reverseLogicalChannelParameters_multiplexParameters_h223LogicalChannelParameters,
+               eOpenLogicalChannel_reverseLogicalChannelParameters_multiplexParameters_v76LogicalChannelParameters,
+               eOpenLogicalChannel_reverseLogicalChannelParameters_multiplexParameters_h2250LogicalChannelParameters,
+       } choice;
+       union {
+               H2250LogicalChannelParameters h2250LogicalChannelParameters;
+       };
+} OpenLogicalChannel_reverseLogicalChannelParameters_multiplexParameters;
+
+typedef struct OpenLogicalChannel_reverseLogicalChannelParameters {    /* SEQUENCE */
+       enum {
+               eOpenLogicalChannel_reverseLogicalChannelParameters_multiplexParameters
+                   = (1 << 31),
+               eOpenLogicalChannel_reverseLogicalChannelParameters_reverseLogicalChannelDependency
+                   = (1 << 30),
+               eOpenLogicalChannel_reverseLogicalChannelParameters_replacementFor
+                   = (1 << 29),
+       } options;
+       OpenLogicalChannel_reverseLogicalChannelParameters_multiplexParameters
+           multiplexParameters;
+} OpenLogicalChannel_reverseLogicalChannelParameters;
+
+typedef struct NetworkAccessParameters_networkAddress {        /* CHOICE */
+       enum {
+               eNetworkAccessParameters_networkAddress_q2931Address,
+               eNetworkAccessParameters_networkAddress_e164Address,
+               eNetworkAccessParameters_networkAddress_localAreaAddress,
+       } choice;
+       union {
+               H245_TransportAddress localAreaAddress;
+       };
+} NetworkAccessParameters_networkAddress;
+
+typedef struct NetworkAccessParameters {       /* SEQUENCE */
+       enum {
+               eNetworkAccessParameters_distribution = (1 << 31),
+               eNetworkAccessParameters_externalReference = (1 << 30),
+               eNetworkAccessParameters_t120SetupProcedure = (1 << 29),
+       } options;
+       NetworkAccessParameters_networkAddress networkAddress;
+} NetworkAccessParameters;
+
+typedef struct OpenLogicalChannel {    /* SEQUENCE */
+       enum {
+               eOpenLogicalChannel_reverseLogicalChannelParameters =
+                   (1 << 31),
+               eOpenLogicalChannel_separateStack = (1 << 30),
+               eOpenLogicalChannel_encryptionSync = (1 << 29),
+       } options;
+       OpenLogicalChannel_forwardLogicalChannelParameters
+           forwardLogicalChannelParameters;
+       OpenLogicalChannel_reverseLogicalChannelParameters
+           reverseLogicalChannelParameters;
+       NetworkAccessParameters separateStack;
+} OpenLogicalChannel;
+
+typedef struct Setup_UUIE_fastStart {  /* SEQUENCE OF */
+       int count;
+       OpenLogicalChannel item[30];
+} Setup_UUIE_fastStart;
+
+typedef struct Setup_UUIE {    /* SEQUENCE */
+       enum {
+               eSetup_UUIE_h245Address = (1 << 31),
+               eSetup_UUIE_sourceAddress = (1 << 30),
+               eSetup_UUIE_destinationAddress = (1 << 29),
+               eSetup_UUIE_destCallSignalAddress = (1 << 28),
+               eSetup_UUIE_destExtraCallInfo = (1 << 27),
+               eSetup_UUIE_destExtraCRV = (1 << 26),
+               eSetup_UUIE_callServices = (1 << 25),
+               eSetup_UUIE_sourceCallSignalAddress = (1 << 24),
+               eSetup_UUIE_remoteExtensionAddress = (1 << 23),
+               eSetup_UUIE_callIdentifier = (1 << 22),
+               eSetup_UUIE_h245SecurityCapability = (1 << 21),
+               eSetup_UUIE_tokens = (1 << 20),
+               eSetup_UUIE_cryptoTokens = (1 << 19),
+               eSetup_UUIE_fastStart = (1 << 18),
+               eSetup_UUIE_mediaWaitForConnect = (1 << 17),
+               eSetup_UUIE_canOverlapSend = (1 << 16),
+               eSetup_UUIE_endpointIdentifier = (1 << 15),
+               eSetup_UUIE_multipleCalls = (1 << 14),
+               eSetup_UUIE_maintainConnection = (1 << 13),
+               eSetup_UUIE_connectionParameters = (1 << 12),
+               eSetup_UUIE_language = (1 << 11),
+               eSetup_UUIE_presentationIndicator = (1 << 10),
+               eSetup_UUIE_screeningIndicator = (1 << 9),
+               eSetup_UUIE_serviceControl = (1 << 8),
+               eSetup_UUIE_symmetricOperationRequired = (1 << 7),
+               eSetup_UUIE_capacity = (1 << 6),
+               eSetup_UUIE_circuitInfo = (1 << 5),
+               eSetup_UUIE_desiredProtocols = (1 << 4),
+               eSetup_UUIE_neededFeatures = (1 << 3),
+               eSetup_UUIE_desiredFeatures = (1 << 2),
+               eSetup_UUIE_supportedFeatures = (1 << 1),
+               eSetup_UUIE_parallelH245Control = (1 << 0),
+       } options;
+       TransportAddress h245Address;
+       TransportAddress destCallSignalAddress;
+       TransportAddress sourceCallSignalAddress;
+       Setup_UUIE_fastStart fastStart;
+} Setup_UUIE;
+
+typedef struct CallProceeding_UUIE_fastStart { /* SEQUENCE OF */
+       int count;
+       OpenLogicalChannel item[30];
+} CallProceeding_UUIE_fastStart;
+
+typedef struct CallProceeding_UUIE {   /* SEQUENCE */
+       enum {
+               eCallProceeding_UUIE_h245Address = (1 << 31),
+               eCallProceeding_UUIE_callIdentifier = (1 << 30),
+               eCallProceeding_UUIE_h245SecurityMode = (1 << 29),
+               eCallProceeding_UUIE_tokens = (1 << 28),
+               eCallProceeding_UUIE_cryptoTokens = (1 << 27),
+               eCallProceeding_UUIE_fastStart = (1 << 26),
+               eCallProceeding_UUIE_multipleCalls = (1 << 25),
+               eCallProceeding_UUIE_maintainConnection = (1 << 24),
+               eCallProceeding_UUIE_fastConnectRefused = (1 << 23),
+               eCallProceeding_UUIE_featureSet = (1 << 22),
+       } options;
+       TransportAddress h245Address;
+       CallProceeding_UUIE_fastStart fastStart;
+} CallProceeding_UUIE;
+
+typedef struct Connect_UUIE_fastStart {        /* SEQUENCE OF */
+       int count;
+       OpenLogicalChannel item[30];
+} Connect_UUIE_fastStart;
+
+typedef struct Connect_UUIE {  /* SEQUENCE */
+       enum {
+               eConnect_UUIE_h245Address = (1 << 31),
+               eConnect_UUIE_callIdentifier = (1 << 30),
+               eConnect_UUIE_h245SecurityMode = (1 << 29),
+               eConnect_UUIE_tokens = (1 << 28),
+               eConnect_UUIE_cryptoTokens = (1 << 27),
+               eConnect_UUIE_fastStart = (1 << 26),
+               eConnect_UUIE_multipleCalls = (1 << 25),
+               eConnect_UUIE_maintainConnection = (1 << 24),
+               eConnect_UUIE_language = (1 << 23),
+               eConnect_UUIE_connectedAddress = (1 << 22),
+               eConnect_UUIE_presentationIndicator = (1 << 21),
+               eConnect_UUIE_screeningIndicator = (1 << 20),
+               eConnect_UUIE_fastConnectRefused = (1 << 19),
+               eConnect_UUIE_serviceControl = (1 << 18),
+               eConnect_UUIE_capacity = (1 << 17),
+               eConnect_UUIE_featureSet = (1 << 16),
+       } options;
+       TransportAddress h245Address;
+       Connect_UUIE_fastStart fastStart;
+} Connect_UUIE;
+
+typedef struct Alerting_UUIE_fastStart {       /* SEQUENCE OF */
+       int count;
+       OpenLogicalChannel item[30];
+} Alerting_UUIE_fastStart;
+
+typedef struct Alerting_UUIE { /* SEQUENCE */
+       enum {
+               eAlerting_UUIE_h245Address = (1 << 31),
+               eAlerting_UUIE_callIdentifier = (1 << 30),
+               eAlerting_UUIE_h245SecurityMode = (1 << 29),
+               eAlerting_UUIE_tokens = (1 << 28),
+               eAlerting_UUIE_cryptoTokens = (1 << 27),
+               eAlerting_UUIE_fastStart = (1 << 26),
+               eAlerting_UUIE_multipleCalls = (1 << 25),
+               eAlerting_UUIE_maintainConnection = (1 << 24),
+               eAlerting_UUIE_alertingAddress = (1 << 23),
+               eAlerting_UUIE_presentationIndicator = (1 << 22),
+               eAlerting_UUIE_screeningIndicator = (1 << 21),
+               eAlerting_UUIE_fastConnectRefused = (1 << 20),
+               eAlerting_UUIE_serviceControl = (1 << 19),
+               eAlerting_UUIE_capacity = (1 << 18),
+               eAlerting_UUIE_featureSet = (1 << 17),
+       } options;
+       TransportAddress h245Address;
+       Alerting_UUIE_fastStart fastStart;
+} Alerting_UUIE;
+
+typedef struct Information_UUIE_fastStart {    /* SEQUENCE OF */
+       int count;
+       OpenLogicalChannel item[30];
+} Information_UUIE_fastStart;
+
+typedef struct Information_UUIE {      /* SEQUENCE */
+       enum {
+               eInformation_UUIE_callIdentifier = (1 << 31),
+               eInformation_UUIE_tokens = (1 << 30),
+               eInformation_UUIE_cryptoTokens = (1 << 29),
+               eInformation_UUIE_fastStart = (1 << 28),
+               eInformation_UUIE_fastConnectRefused = (1 << 27),
+               eInformation_UUIE_circuitInfo = (1 << 26),
+       } options;
+       Information_UUIE_fastStart fastStart;
+} Information_UUIE;
+
+typedef struct FacilityReason {        /* CHOICE */
+       enum {
+               eFacilityReason_routeCallToGatekeeper,
+               eFacilityReason_callForwarded,
+               eFacilityReason_routeCallToMC,
+               eFacilityReason_undefinedReason,
+               eFacilityReason_conferenceListChoice,
+               eFacilityReason_startH245,
+               eFacilityReason_noH245,
+               eFacilityReason_newTokens,
+               eFacilityReason_featureSetUpdate,
+               eFacilityReason_forwardedElements,
+               eFacilityReason_transportedInformation,
+       } choice;
+} FacilityReason;
+
+typedef struct Facility_UUIE_fastStart {       /* SEQUENCE OF */
+       int count;
+       OpenLogicalChannel item[30];
+} Facility_UUIE_fastStart;
+
+typedef struct Facility_UUIE { /* SEQUENCE */
+       enum {
+               eFacility_UUIE_alternativeAddress = (1 << 31),
+               eFacility_UUIE_alternativeAliasAddress = (1 << 30),
+               eFacility_UUIE_conferenceID = (1 << 29),
+               eFacility_UUIE_callIdentifier = (1 << 28),
+               eFacility_UUIE_destExtraCallInfo = (1 << 27),
+               eFacility_UUIE_remoteExtensionAddress = (1 << 26),
+               eFacility_UUIE_tokens = (1 << 25),
+               eFacility_UUIE_cryptoTokens = (1 << 24),
+               eFacility_UUIE_conferences = (1 << 23),
+               eFacility_UUIE_h245Address = (1 << 22),
+               eFacility_UUIE_fastStart = (1 << 21),
+               eFacility_UUIE_multipleCalls = (1 << 20),
+               eFacility_UUIE_maintainConnection = (1 << 19),
+               eFacility_UUIE_fastConnectRefused = (1 << 18),
+               eFacility_UUIE_serviceControl = (1 << 17),
+               eFacility_UUIE_circuitInfo = (1 << 16),
+               eFacility_UUIE_featureSet = (1 << 15),
+               eFacility_UUIE_destinationInfo = (1 << 14),
+               eFacility_UUIE_h245SecurityMode = (1 << 13),
+       } options;
+       FacilityReason reason;
+       TransportAddress h245Address;
+       Facility_UUIE_fastStart fastStart;
+} Facility_UUIE;
+
+typedef struct Progress_UUIE_fastStart {       /* SEQUENCE OF */
+       int count;
+       OpenLogicalChannel item[30];
+} Progress_UUIE_fastStart;
+
+typedef struct Progress_UUIE { /* SEQUENCE */
+       enum {
+               eProgress_UUIE_h245Address = (1 << 31),
+               eProgress_UUIE_h245SecurityMode = (1 << 30),
+               eProgress_UUIE_tokens = (1 << 29),
+               eProgress_UUIE_cryptoTokens = (1 << 28),
+               eProgress_UUIE_fastStart = (1 << 27),
+               eProgress_UUIE_multipleCalls = (1 << 26),
+               eProgress_UUIE_maintainConnection = (1 << 25),
+               eProgress_UUIE_fastConnectRefused = (1 << 24),
+       } options;
+       TransportAddress h245Address;
+       Progress_UUIE_fastStart fastStart;
+} Progress_UUIE;
+
+typedef struct H323_UU_PDU_h323_message_body { /* CHOICE */
+       enum {
+               eH323_UU_PDU_h323_message_body_setup,
+               eH323_UU_PDU_h323_message_body_callProceeding,
+               eH323_UU_PDU_h323_message_body_connect,
+               eH323_UU_PDU_h323_message_body_alerting,
+               eH323_UU_PDU_h323_message_body_information,
+               eH323_UU_PDU_h323_message_body_releaseComplete,
+               eH323_UU_PDU_h323_message_body_facility,
+               eH323_UU_PDU_h323_message_body_progress,
+               eH323_UU_PDU_h323_message_body_empty,
+               eH323_UU_PDU_h323_message_body_status,
+               eH323_UU_PDU_h323_message_body_statusInquiry,
+               eH323_UU_PDU_h323_message_body_setupAcknowledge,
+               eH323_UU_PDU_h323_message_body_notify,
+       } choice;
+       union {
+               Setup_UUIE setup;
+               CallProceeding_UUIE callProceeding;
+               Connect_UUIE connect;
+               Alerting_UUIE alerting;
+               Information_UUIE information;
+               Facility_UUIE facility;
+               Progress_UUIE progress;
+       };
+} H323_UU_PDU_h323_message_body;
+
+typedef struct RequestMessage {        /* CHOICE */
+       enum {
+               eRequestMessage_nonStandard,
+               eRequestMessage_masterSlaveDetermination,
+               eRequestMessage_terminalCapabilitySet,
+               eRequestMessage_openLogicalChannel,
+               eRequestMessage_closeLogicalChannel,
+               eRequestMessage_requestChannelClose,
+               eRequestMessage_multiplexEntrySend,
+               eRequestMessage_requestMultiplexEntry,
+               eRequestMessage_requestMode,
+               eRequestMessage_roundTripDelayRequest,
+               eRequestMessage_maintenanceLoopRequest,
+               eRequestMessage_communicationModeRequest,
+               eRequestMessage_conferenceRequest,
+               eRequestMessage_multilinkRequest,
+               eRequestMessage_logicalChannelRateRequest,
+       } choice;
+       union {
+               OpenLogicalChannel openLogicalChannel;
+       };
+} RequestMessage;
+
+typedef struct OpenLogicalChannelAck_reverseLogicalChannelParameters_multiplexParameters {     /* CHOICE */
+       enum {
+               eOpenLogicalChannelAck_reverseLogicalChannelParameters_multiplexParameters_h222LogicalChannelParameters,
+               eOpenLogicalChannelAck_reverseLogicalChannelParameters_multiplexParameters_h2250LogicalChannelParameters,
+       } choice;
+       union {
+               H2250LogicalChannelParameters h2250LogicalChannelParameters;
+       };
+} OpenLogicalChannelAck_reverseLogicalChannelParameters_multiplexParameters;
+
+typedef struct OpenLogicalChannelAck_reverseLogicalChannelParameters { /* SEQUENCE */
+       enum {
+               eOpenLogicalChannelAck_reverseLogicalChannelParameters_portNumber
+                   = (1 << 31),
+               eOpenLogicalChannelAck_reverseLogicalChannelParameters_multiplexParameters
+                   = (1 << 30),
+               eOpenLogicalChannelAck_reverseLogicalChannelParameters_replacementFor
+                   = (1 << 29),
+       } options;
+       OpenLogicalChannelAck_reverseLogicalChannelParameters_multiplexParameters
+           multiplexParameters;
+} OpenLogicalChannelAck_reverseLogicalChannelParameters;
+
+typedef struct H2250LogicalChannelAckParameters {      /* SEQUENCE */
+       enum {
+               eH2250LogicalChannelAckParameters_nonStandard = (1 << 31),
+               eH2250LogicalChannelAckParameters_sessionID = (1 << 30),
+               eH2250LogicalChannelAckParameters_mediaChannel = (1 << 29),
+               eH2250LogicalChannelAckParameters_mediaControlChannel =
+                   (1 << 28),
+               eH2250LogicalChannelAckParameters_dynamicRTPPayloadType =
+                   (1 << 27),
+               eH2250LogicalChannelAckParameters_flowControlToZero =
+                   (1 << 26),
+               eH2250LogicalChannelAckParameters_portNumber = (1 << 25),
+       } options;
+       H245_TransportAddress mediaChannel;
+       H245_TransportAddress mediaControlChannel;
+} H2250LogicalChannelAckParameters;
+
+typedef struct OpenLogicalChannelAck_forwardMultiplexAckParameters {   /* CHOICE */
+       enum {
+               eOpenLogicalChannelAck_forwardMultiplexAckParameters_h2250LogicalChannelAckParameters,
+       } choice;
+       union {
+               H2250LogicalChannelAckParameters
+                   h2250LogicalChannelAckParameters;
+       };
+} OpenLogicalChannelAck_forwardMultiplexAckParameters;
+
+typedef struct OpenLogicalChannelAck { /* SEQUENCE */
+       enum {
+               eOpenLogicalChannelAck_reverseLogicalChannelParameters =
+                   (1 << 31),
+               eOpenLogicalChannelAck_separateStack = (1 << 30),
+               eOpenLogicalChannelAck_forwardMultiplexAckParameters =
+                   (1 << 29),
+               eOpenLogicalChannelAck_encryptionSync = (1 << 28),
+       } options;
+       OpenLogicalChannelAck_reverseLogicalChannelParameters
+           reverseLogicalChannelParameters;
+       OpenLogicalChannelAck_forwardMultiplexAckParameters
+           forwardMultiplexAckParameters;
+} OpenLogicalChannelAck;
+
+typedef struct ResponseMessage {       /* CHOICE */
+       enum {
+               eResponseMessage_nonStandard,
+               eResponseMessage_masterSlaveDeterminationAck,
+               eResponseMessage_masterSlaveDeterminationReject,
+               eResponseMessage_terminalCapabilitySetAck,
+               eResponseMessage_terminalCapabilitySetReject,
+               eResponseMessage_openLogicalChannelAck,
+               eResponseMessage_openLogicalChannelReject,
+               eResponseMessage_closeLogicalChannelAck,
+               eResponseMessage_requestChannelCloseAck,
+               eResponseMessage_requestChannelCloseReject,
+               eResponseMessage_multiplexEntrySendAck,
+               eResponseMessage_multiplexEntrySendReject,
+               eResponseMessage_requestMultiplexEntryAck,
+               eResponseMessage_requestMultiplexEntryReject,
+               eResponseMessage_requestModeAck,
+               eResponseMessage_requestModeReject,
+               eResponseMessage_roundTripDelayResponse,
+               eResponseMessage_maintenanceLoopAck,
+               eResponseMessage_maintenanceLoopReject,
+               eResponseMessage_communicationModeResponse,
+               eResponseMessage_conferenceResponse,
+               eResponseMessage_multilinkResponse,
+               eResponseMessage_logicalChannelRateAcknowledge,
+               eResponseMessage_logicalChannelRateReject,
+       } choice;
+       union {
+               OpenLogicalChannelAck openLogicalChannelAck;
+       };
+} ResponseMessage;
+
+typedef struct MultimediaSystemControlMessage {        /* CHOICE */
+       enum {
+               eMultimediaSystemControlMessage_request,
+               eMultimediaSystemControlMessage_response,
+               eMultimediaSystemControlMessage_command,
+               eMultimediaSystemControlMessage_indication,
+       } choice;
+       union {
+               RequestMessage request;
+               ResponseMessage response;
+       };
+} MultimediaSystemControlMessage;
+
+typedef struct H323_UU_PDU_h245Control {       /* SEQUENCE OF */
+       int count;
+       MultimediaSystemControlMessage item[4];
+} H323_UU_PDU_h245Control;
+
+typedef struct H323_UU_PDU {   /* SEQUENCE */
+       enum {
+               eH323_UU_PDU_nonStandardData = (1 << 31),
+               eH323_UU_PDU_h4501SupplementaryService = (1 << 30),
+               eH323_UU_PDU_h245Tunneling = (1 << 29),
+               eH323_UU_PDU_h245Control = (1 << 28),
+               eH323_UU_PDU_nonStandardControl = (1 << 27),
+               eH323_UU_PDU_callLinkage = (1 << 26),
+               eH323_UU_PDU_tunnelledSignallingMessage = (1 << 25),
+               eH323_UU_PDU_provisionalRespToH245Tunneling = (1 << 24),
+               eH323_UU_PDU_stimulusControl = (1 << 23),
+               eH323_UU_PDU_genericData = (1 << 22),
+       } options;
+       H323_UU_PDU_h323_message_body h323_message_body;
+       H323_UU_PDU_h245Control h245Control;
+} H323_UU_PDU;
+
+typedef struct H323_UserInformation {  /* SEQUENCE */
+       enum {
+               eH323_UserInformation_user_data = (1 << 31),
+       } options;
+       H323_UU_PDU h323_uu_pdu;
+} H323_UserInformation;
+
+typedef struct GatekeeperRequest {     /* SEQUENCE */
+       enum {
+               eGatekeeperRequest_nonStandardData = (1 << 31),
+               eGatekeeperRequest_gatekeeperIdentifier = (1 << 30),
+               eGatekeeperRequest_callServices = (1 << 29),
+               eGatekeeperRequest_endpointAlias = (1 << 28),
+               eGatekeeperRequest_alternateEndpoints = (1 << 27),
+               eGatekeeperRequest_tokens = (1 << 26),
+               eGatekeeperRequest_cryptoTokens = (1 << 25),
+               eGatekeeperRequest_authenticationCapability = (1 << 24),
+               eGatekeeperRequest_algorithmOIDs = (1 << 23),
+               eGatekeeperRequest_integrity = (1 << 22),
+               eGatekeeperRequest_integrityCheckValue = (1 << 21),
+               eGatekeeperRequest_supportsAltGK = (1 << 20),
+               eGatekeeperRequest_featureSet = (1 << 19),
+               eGatekeeperRequest_genericData = (1 << 18),
+       } options;
+       TransportAddress rasAddress;
+} GatekeeperRequest;
+
+typedef struct GatekeeperConfirm {     /* SEQUENCE */
+       enum {
+               eGatekeeperConfirm_nonStandardData = (1 << 31),
+               eGatekeeperConfirm_gatekeeperIdentifier = (1 << 30),
+               eGatekeeperConfirm_alternateGatekeeper = (1 << 29),
+               eGatekeeperConfirm_authenticationMode = (1 << 28),
+               eGatekeeperConfirm_tokens = (1 << 27),
+               eGatekeeperConfirm_cryptoTokens = (1 << 26),
+               eGatekeeperConfirm_algorithmOID = (1 << 25),
+               eGatekeeperConfirm_integrity = (1 << 24),
+               eGatekeeperConfirm_integrityCheckValue = (1 << 23),
+               eGatekeeperConfirm_featureSet = (1 << 22),
+               eGatekeeperConfirm_genericData = (1 << 21),
+       } options;
+       TransportAddress rasAddress;
+} GatekeeperConfirm;
+
+typedef struct RegistrationRequest_callSignalAddress { /* SEQUENCE OF */
+       int count;
+       TransportAddress item[10];
+} RegistrationRequest_callSignalAddress;
+
+typedef struct RegistrationRequest_rasAddress {        /* SEQUENCE OF */
+       int count;
+       TransportAddress item[10];
+} RegistrationRequest_rasAddress;
+
+typedef struct RegistrationRequest {   /* SEQUENCE */
+       enum {
+               eRegistrationRequest_nonStandardData = (1 << 31),
+               eRegistrationRequest_terminalAlias = (1 << 30),
+               eRegistrationRequest_gatekeeperIdentifier = (1 << 29),
+               eRegistrationRequest_alternateEndpoints = (1 << 28),
+               eRegistrationRequest_timeToLive = (1 << 27),
+               eRegistrationRequest_tokens = (1 << 26),
+               eRegistrationRequest_cryptoTokens = (1 << 25),
+               eRegistrationRequest_integrityCheckValue = (1 << 24),
+               eRegistrationRequest_keepAlive = (1 << 23),
+               eRegistrationRequest_endpointIdentifier = (1 << 22),
+               eRegistrationRequest_willSupplyUUIEs = (1 << 21),
+               eRegistrationRequest_maintainConnection = (1 << 20),
+               eRegistrationRequest_alternateTransportAddresses = (1 << 19),
+               eRegistrationRequest_additiveRegistration = (1 << 18),
+               eRegistrationRequest_terminalAliasPattern = (1 << 17),
+               eRegistrationRequest_supportsAltGK = (1 << 16),
+               eRegistrationRequest_usageReportingCapability = (1 << 15),
+               eRegistrationRequest_multipleCalls = (1 << 14),
+               eRegistrationRequest_supportedH248Packages = (1 << 13),
+               eRegistrationRequest_callCreditCapability = (1 << 12),
+               eRegistrationRequest_capacityReportingCapability = (1 << 11),
+               eRegistrationRequest_capacity = (1 << 10),
+               eRegistrationRequest_featureSet = (1 << 9),
+               eRegistrationRequest_genericData = (1 << 8),
+       } options;
+       RegistrationRequest_callSignalAddress callSignalAddress;
+       RegistrationRequest_rasAddress rasAddress;
+       unsigned timeToLive;
+} RegistrationRequest;
+
+typedef struct RegistrationConfirm_callSignalAddress { /* SEQUENCE OF */
+       int count;
+       TransportAddress item[10];
+} RegistrationConfirm_callSignalAddress;
+
+typedef struct RegistrationConfirm {   /* SEQUENCE */
+       enum {
+               eRegistrationConfirm_nonStandardData = (1 << 31),
+               eRegistrationConfirm_terminalAlias = (1 << 30),
+               eRegistrationConfirm_gatekeeperIdentifier = (1 << 29),
+               eRegistrationConfirm_alternateGatekeeper = (1 << 28),
+               eRegistrationConfirm_timeToLive = (1 << 27),
+               eRegistrationConfirm_tokens = (1 << 26),
+               eRegistrationConfirm_cryptoTokens = (1 << 25),
+               eRegistrationConfirm_integrityCheckValue = (1 << 24),
+               eRegistrationConfirm_willRespondToIRR = (1 << 23),
+               eRegistrationConfirm_preGrantedARQ = (1 << 22),
+               eRegistrationConfirm_maintainConnection = (1 << 21),
+               eRegistrationConfirm_serviceControl = (1 << 20),
+               eRegistrationConfirm_supportsAdditiveRegistration = (1 << 19),
+               eRegistrationConfirm_terminalAliasPattern = (1 << 18),
+               eRegistrationConfirm_supportedPrefixes = (1 << 17),
+               eRegistrationConfirm_usageSpec = (1 << 16),
+               eRegistrationConfirm_featureServerAlias = (1 << 15),
+               eRegistrationConfirm_capacityReportingSpec = (1 << 14),
+               eRegistrationConfirm_featureSet = (1 << 13),
+               eRegistrationConfirm_genericData = (1 << 12),
+       } options;
+       RegistrationConfirm_callSignalAddress callSignalAddress;
+       unsigned timeToLive;
+} RegistrationConfirm;
+
+typedef struct UnregistrationRequest_callSignalAddress {       /* SEQUENCE OF */
+       int count;
+       TransportAddress item[10];
+} UnregistrationRequest_callSignalAddress;
+
+typedef struct UnregistrationRequest { /* SEQUENCE */
+       enum {
+               eUnregistrationRequest_endpointAlias = (1 << 31),
+               eUnregistrationRequest_nonStandardData = (1 << 30),
+               eUnregistrationRequest_endpointIdentifier = (1 << 29),
+               eUnregistrationRequest_alternateEndpoints = (1 << 28),
+               eUnregistrationRequest_gatekeeperIdentifier = (1 << 27),
+               eUnregistrationRequest_tokens = (1 << 26),
+               eUnregistrationRequest_cryptoTokens = (1 << 25),
+               eUnregistrationRequest_integrityCheckValue = (1 << 24),
+               eUnregistrationRequest_reason = (1 << 23),
+               eUnregistrationRequest_endpointAliasPattern = (1 << 22),
+               eUnregistrationRequest_supportedPrefixes = (1 << 21),
+               eUnregistrationRequest_alternateGatekeeper = (1 << 20),
+               eUnregistrationRequest_genericData = (1 << 19),
+       } options;
+       UnregistrationRequest_callSignalAddress callSignalAddress;
+} UnregistrationRequest;
+
+typedef struct AdmissionRequest {      /* SEQUENCE */
+       enum {
+               eAdmissionRequest_callModel = (1 << 31),
+               eAdmissionRequest_destinationInfo = (1 << 30),
+               eAdmissionRequest_destCallSignalAddress = (1 << 29),
+               eAdmissionRequest_destExtraCallInfo = (1 << 28),
+               eAdmissionRequest_srcCallSignalAddress = (1 << 27),
+               eAdmissionRequest_nonStandardData = (1 << 26),
+               eAdmissionRequest_callServices = (1 << 25),
+               eAdmissionRequest_canMapAlias = (1 << 24),
+               eAdmissionRequest_callIdentifier = (1 << 23),
+               eAdmissionRequest_srcAlternatives = (1 << 22),
+               eAdmissionRequest_destAlternatives = (1 << 21),
+               eAdmissionRequest_gatekeeperIdentifier = (1 << 20),
+               eAdmissionRequest_tokens = (1 << 19),
+               eAdmissionRequest_cryptoTokens = (1 << 18),
+               eAdmissionRequest_integrityCheckValue = (1 << 17),
+               eAdmissionRequest_transportQOS = (1 << 16),
+               eAdmissionRequest_willSupplyUUIEs = (1 << 15),
+               eAdmissionRequest_callLinkage = (1 << 14),
+               eAdmissionRequest_gatewayDataRate = (1 << 13),
+               eAdmissionRequest_capacity = (1 << 12),
+               eAdmissionRequest_circuitInfo = (1 << 11),
+               eAdmissionRequest_desiredProtocols = (1 << 10),
+               eAdmissionRequest_desiredTunnelledProtocol = (1 << 9),
+               eAdmissionRequest_featureSet = (1 << 8),
+               eAdmissionRequest_genericData = (1 << 7),
+       } options;
+       TransportAddress destCallSignalAddress;
+       TransportAddress srcCallSignalAddress;
+} AdmissionRequest;
+
+typedef struct AdmissionConfirm {      /* SEQUENCE */
+       enum {
+               eAdmissionConfirm_irrFrequency = (1 << 31),
+               eAdmissionConfirm_nonStandardData = (1 << 30),
+               eAdmissionConfirm_destinationInfo = (1 << 29),
+               eAdmissionConfirm_destExtraCallInfo = (1 << 28),
+               eAdmissionConfirm_destinationType = (1 << 27),
+               eAdmissionConfirm_remoteExtensionAddress = (1 << 26),
+               eAdmissionConfirm_alternateEndpoints = (1 << 25),
+               eAdmissionConfirm_tokens = (1 << 24),
+               eAdmissionConfirm_cryptoTokens = (1 << 23),
+               eAdmissionConfirm_integrityCheckValue = (1 << 22),
+               eAdmissionConfirm_transportQOS = (1 << 21),
+               eAdmissionConfirm_willRespondToIRR = (1 << 20),
+               eAdmissionConfirm_uuiesRequested = (1 << 19),
+               eAdmissionConfirm_language = (1 << 18),
+               eAdmissionConfirm_alternateTransportAddresses = (1 << 17),
+               eAdmissionConfirm_useSpecifiedTransport = (1 << 16),
+               eAdmissionConfirm_circuitInfo = (1 << 15),
+               eAdmissionConfirm_usageSpec = (1 << 14),
+               eAdmissionConfirm_supportedProtocols = (1 << 13),
+               eAdmissionConfirm_serviceControl = (1 << 12),
+               eAdmissionConfirm_multipleCalls = (1 << 11),
+               eAdmissionConfirm_featureSet = (1 << 10),
+               eAdmissionConfirm_genericData = (1 << 9),
+       } options;
+       TransportAddress destCallSignalAddress;
+} AdmissionConfirm;
+
+typedef struct LocationRequest {       /* SEQUENCE */
+       enum {
+               eLocationRequest_endpointIdentifier = (1 << 31),
+               eLocationRequest_nonStandardData = (1 << 30),
+               eLocationRequest_sourceInfo = (1 << 29),
+               eLocationRequest_canMapAlias = (1 << 28),
+               eLocationRequest_gatekeeperIdentifier = (1 << 27),
+               eLocationRequest_tokens = (1 << 26),
+               eLocationRequest_cryptoTokens = (1 << 25),
+               eLocationRequest_integrityCheckValue = (1 << 24),
+               eLocationRequest_desiredProtocols = (1 << 23),
+               eLocationRequest_desiredTunnelledProtocol = (1 << 22),
+               eLocationRequest_featureSet = (1 << 21),
+               eLocationRequest_genericData = (1 << 20),
+               eLocationRequest_hopCount = (1 << 19),
+               eLocationRequest_circuitInfo = (1 << 18),
+       } options;
+       TransportAddress replyAddress;
+} LocationRequest;
+
+typedef struct LocationConfirm {       /* SEQUENCE */
+       enum {
+               eLocationConfirm_nonStandardData = (1 << 31),
+               eLocationConfirm_destinationInfo = (1 << 30),
+               eLocationConfirm_destExtraCallInfo = (1 << 29),
+               eLocationConfirm_destinationType = (1 << 28),
+               eLocationConfirm_remoteExtensionAddress = (1 << 27),
+               eLocationConfirm_alternateEndpoints = (1 << 26),
+               eLocationConfirm_tokens = (1 << 25),
+               eLocationConfirm_cryptoTokens = (1 << 24),
+               eLocationConfirm_integrityCheckValue = (1 << 23),
+               eLocationConfirm_alternateTransportAddresses = (1 << 22),
+               eLocationConfirm_supportedProtocols = (1 << 21),
+               eLocationConfirm_multipleCalls = (1 << 20),
+               eLocationConfirm_featureSet = (1 << 19),
+               eLocationConfirm_genericData = (1 << 18),
+               eLocationConfirm_circuitInfo = (1 << 17),
+               eLocationConfirm_serviceControl = (1 << 16),
+       } options;
+       TransportAddress callSignalAddress;
+       TransportAddress rasAddress;
+} LocationConfirm;
+
+typedef struct InfoRequestResponse_callSignalAddress { /* SEQUENCE OF */
+       int count;
+       TransportAddress item[10];
+} InfoRequestResponse_callSignalAddress;
+
+typedef struct InfoRequestResponse {   /* SEQUENCE */
+       enum {
+               eInfoRequestResponse_nonStandardData = (1 << 31),
+               eInfoRequestResponse_endpointAlias = (1 << 30),
+               eInfoRequestResponse_perCallInfo = (1 << 29),
+               eInfoRequestResponse_tokens = (1 << 28),
+               eInfoRequestResponse_cryptoTokens = (1 << 27),
+               eInfoRequestResponse_integrityCheckValue = (1 << 26),
+               eInfoRequestResponse_needResponse = (1 << 25),
+               eInfoRequestResponse_capacity = (1 << 24),
+               eInfoRequestResponse_irrStatus = (1 << 23),
+               eInfoRequestResponse_unsolicited = (1 << 22),
+               eInfoRequestResponse_genericData = (1 << 21),
+       } options;
+       TransportAddress rasAddress;
+       InfoRequestResponse_callSignalAddress callSignalAddress;
+} InfoRequestResponse;
+
+typedef struct RasMessage {    /* CHOICE */
+       enum {
+               eRasMessage_gatekeeperRequest,
+               eRasMessage_gatekeeperConfirm,
+               eRasMessage_gatekeeperReject,
+               eRasMessage_registrationRequest,
+               eRasMessage_registrationConfirm,
+               eRasMessage_registrationReject,
+               eRasMessage_unregistrationRequest,
+               eRasMessage_unregistrationConfirm,
+               eRasMessage_unregistrationReject,
+               eRasMessage_admissionRequest,
+               eRasMessage_admissionConfirm,
+               eRasMessage_admissionReject,
+               eRasMessage_bandwidthRequest,
+               eRasMessage_bandwidthConfirm,
+               eRasMessage_bandwidthReject,
+               eRasMessage_disengageRequest,
+               eRasMessage_disengageConfirm,
+               eRasMessage_disengageReject,
+               eRasMessage_locationRequest,
+               eRasMessage_locationConfirm,
+               eRasMessage_locationReject,
+               eRasMessage_infoRequest,
+               eRasMessage_infoRequestResponse,
+               eRasMessage_nonStandardMessage,
+               eRasMessage_unknownMessageResponse,
+               eRasMessage_requestInProgress,
+               eRasMessage_resourcesAvailableIndicate,
+               eRasMessage_resourcesAvailableConfirm,
+               eRasMessage_infoRequestAck,
+               eRasMessage_infoRequestNak,
+               eRasMessage_serviceControlIndication,
+               eRasMessage_serviceControlResponse,
+       } choice;
+       union {
+               GatekeeperRequest gatekeeperRequest;
+               GatekeeperConfirm gatekeeperConfirm;
+               RegistrationRequest registrationRequest;
+               RegistrationConfirm registrationConfirm;
+               UnregistrationRequest unregistrationRequest;
+               AdmissionRequest admissionRequest;
+               AdmissionConfirm admissionConfirm;
+               LocationRequest locationRequest;
+               LocationConfirm locationConfirm;
+               InfoRequestResponse infoRequestResponse;
+       };
+} RasMessage;
index 14f2bd010884de35e7d5d1ac223dfe9836c8a22c..52a7b9e76428c8a9ee359685b9b99dfd0c8809f1 100644 (file)
@@ -73,6 +73,9 @@ enum nf_ip6_hook_priorities {
 };
 
 #ifdef CONFIG_NETFILTER
+extern unsigned int nf_ip6_checksum(struct sk_buff *skb, unsigned int hook,
+                                   unsigned int dataoff, u_int8_t protocol);
+
 extern int ipv6_netfilter_init(void);
 extern void ipv6_netfilter_fini(void);
 #else /* CONFIG_NETFILTER */
index f0c539bd3cfc44e07eaafc26bcf358c29c0fc65f..e481feb1bfd81e061e3c2488ece336f936fdc9d6 100644 (file)
@@ -3,11 +3,9 @@
 
 #include <linux/config.h>
 
-#ifndef CONFIG_FLATMEM
-#include <asm/numnodes.h>
-#endif
-
-#ifndef NODES_SHIFT
+#ifdef CONFIG_NODES_SHIFT
+#define NODES_SHIFT     CONFIG_NODES_SHIFT
+#else
 #define NODES_SHIFT     0
 #endif
 
index 9ea629c02a4b98fc7cf06c71b9dd9c74b5a15bde..d276a4e2f825030593c89bef5cb216803b5d4a4e 100644 (file)
 
 /*
  * Don't use the *_dontuse flags.  Use the macros.  Otherwise you'll break
- * locked- and dirty-page accounting.  The top eight bits of page->flags are
- * used for page->zone, so putting flag bits there doesn't work.
+ * locked- and dirty-page accounting.
+ *
+ * The page flags field is split into two parts, the main flags area
+ * which extends from the low bits upwards, and the fields area which
+ * extends from the high bits downwards.
+ *
+ *  | FIELD | ... | FLAGS |
+ *  N-1     ^             0
+ *          (N-FLAGS_RESERVED)
+ *
+ * The fields area is reserved for fields mapping zone, node and SPARSEMEM
+ * section.  The boundry between these two areas is defined by
+ * FLAGS_RESERVED which defines the width of the fields section
+ * (see linux/mmzone.h).  New flags must _not_ overlap with this area.
  */
 #define PG_locked               0      /* Page is locked. Don't touch. */
 #define PG_error                1
@@ -74,7 +86,9 @@
 #define PG_mappedtodisk                16      /* Has blocks allocated on-disk */
 #define PG_reclaim             17      /* To be reclaimed asap */
 #define PG_nosave_free         18      /* Free, should not be written */
-#define PG_uncached            19      /* Page has been mapped as uncached */
+#define PG_buddy               19      /* Page is free, on buddy lists */
+
+#define PG_uncached            20      /* Page has been mapped as uncached */
 
 /*
  * Global page accounting.  One instance per CPU.  Only unsigned longs are
@@ -317,6 +331,10 @@ extern void __mod_page_state_offset(unsigned long offset, unsigned long delta);
 #define SetPageNosaveFree(page)        set_bit(PG_nosave_free, &(page)->flags)
 #define ClearPageNosaveFree(page)              clear_bit(PG_nosave_free, &(page)->flags)
 
+#define PageBuddy(page)                test_bit(PG_buddy, &(page)->flags)
+#define __SetPageBuddy(page)   __set_bit(PG_buddy, &(page)->flags)
+#define __ClearPageBuddy(page) __clear_bit(PG_buddy, &(page)->flags)
+
 #define PageMappedToDisk(page) test_bit(PG_mappedtodisk, &(page)->flags)
 #define SetPageMappedToDisk(page) set_bit(PG_mappedtodisk, &(page)->flags)
 #define ClearPageMappedToDisk(page) clear_bit(PG_mappedtodisk, &(page)->flags)
index 0aad5a378e950580e76d3bea81817fc069ca12aa..3a6a4e37a482f3a6d4e54cc044c1c438d87eb999 100644 (file)
@@ -97,7 +97,13 @@ enum pci_channel_state {
 
 typedef unsigned short __bitwise pci_bus_flags_t;
 enum pci_bus_flags {
-       PCI_BUS_FLAGS_NO_MSI = (pci_bus_flags_t) 1,
+       PCI_BUS_FLAGS_NO_MSI = (__force pci_bus_flags_t) 1,
+};
+
+struct pci_cap_saved_state {
+       struct hlist_node next;
+       char cap_nr;
+       u32 data[0];
 };
 
 /*
@@ -159,6 +165,7 @@ struct pci_dev {
        unsigned int    block_ucfg_access:1;    /* userspace config space access is blocked */
 
        u32             saved_config_space[16]; /* config space saved at suspend time */
+       struct hlist_head saved_cap_space;
        struct bin_attribute *rom_attr; /* attribute descriptor for sysfs ROM entry */
        int rom_attr_enabled;           /* has display of the rom attribute been enabled? */
        struct bin_attribute *res_attr[DEVICE_COUNT_RESOURCE]; /* sysfs file for resources */
@@ -169,6 +176,30 @@ struct pci_dev {
 #define        to_pci_dev(n) container_of(n, struct pci_dev, dev)
 #define for_each_pci_dev(d) while ((d = pci_get_device(PCI_ANY_ID, PCI_ANY_ID, d)) != NULL)
 
+static inline struct pci_cap_saved_state *pci_find_saved_cap(
+       struct pci_dev *pci_dev,char cap)
+{
+       struct pci_cap_saved_state *tmp;
+       struct hlist_node *pos;
+
+       hlist_for_each_entry(tmp, pos, &pci_dev->saved_cap_space, next) {
+               if (tmp->cap_nr == cap)
+                       return tmp;
+       }
+       return NULL;
+}
+
+static inline void pci_add_saved_cap(struct pci_dev *pci_dev,
+       struct pci_cap_saved_state *new_cap)
+{
+       hlist_add_head(&new_cap->next, &pci_dev->saved_cap_space);
+}
+
+static inline void pci_remove_saved_cap(struct pci_cap_saved_state *cap)
+{
+       hlist_del(&cap->next);
+}
+
 /*
  *  For PCI devices, the region numbers are assigned this way:
  *
index 870fe38378b1ab2f24befb308567b79b8f2e8a50..d6fe048376ab02010a1709b6dcce4e94f4b70601 100644 (file)
 #define PCI_DEVICE_ID_ATI_IXP300_SATA   0x436e
 #define PCI_DEVICE_ID_ATI_IXP400_IDE   0x4376
 #define PCI_DEVICE_ID_ATI_IXP400_SATA   0x4379
+#define PCI_DEVICE_ID_ATI_IXP400_SATA2 0x437a
+#define PCI_DEVICE_ID_ATI_IXP600_SATA  0x4380
+#define PCI_DEVICE_ID_ATI_IXP600_SRAID 0x4381
+#define PCI_DEVICE_ID_ATI_IXP600_IDE   0x438c
 
 #define PCI_VENDOR_ID_VLSI             0x1004
 #define PCI_DEVICE_ID_VLSI_82C592      0x0005
 #define PCI_DEVICE_ID_AMD_8111_SMBUS   0x746b
 #define PCI_DEVICE_ID_AMD_8111_AUDIO   0x746d
 #define PCI_DEVICE_ID_AMD_8151_0       0x7454
-#define PCI_DEVICE_ID_AMD_8131_APIC     0x7450
+#define PCI_DEVICE_ID_AMD_8131_BRIDGE  0x7450
+#define PCI_DEVICE_ID_AMD_8131_APIC    0x7451
 #define PCI_DEVICE_ID_AMD_CS5536_ISA    0x2090
 #define PCI_DEVICE_ID_AMD_CS5536_FLASH  0x2091
 #define PCI_DEVICE_ID_AMD_CS5536_AUDIO  0x2093
index ec384958d509690090aa1936b4624cb3da05b2d8..ef7f33c0be19190590cc205f5828ba1fc6ea9170 100644 (file)
@@ -21,6 +21,7 @@ struct pipe_buf_operations {
        void (*unmap)(struct pipe_inode_info *, struct pipe_buffer *);
        void (*release)(struct pipe_inode_info *, struct pipe_buffer *);
        int (*steal)(struct pipe_inode_info *, struct pipe_buffer *);
+       void (*get)(struct pipe_inode_info *, struct pipe_buffer *);
 };
 
 struct pipe_inode_info {
@@ -36,27 +37,19 @@ struct pipe_inode_info {
        unsigned int w_counter;
        struct fasync_struct *fasync_readers;
        struct fasync_struct *fasync_writers;
+       struct inode *inode;
 };
 
 /* Differs from PIPE_BUF in that PIPE_SIZE is the length of the actual
    memory allocation, whereas PIPE_BUF makes atomicity guarantees.  */
 #define PIPE_SIZE              PAGE_SIZE
 
-#define PIPE_MUTEX(inode)      (&(inode).i_mutex)
-#define PIPE_WAIT(inode)       (&(inode).i_pipe->wait)
-#define PIPE_READERS(inode)    ((inode).i_pipe->readers)
-#define PIPE_WRITERS(inode)    ((inode).i_pipe->writers)
-#define PIPE_WAITING_WRITERS(inode)    ((inode).i_pipe->waiting_writers)
-#define PIPE_RCOUNTER(inode)   ((inode).i_pipe->r_counter)
-#define PIPE_WCOUNTER(inode)   ((inode).i_pipe->w_counter)
-#define PIPE_FASYNC_READERS(inode)     (&((inode).i_pipe->fasync_readers))
-#define PIPE_FASYNC_WRITERS(inode)     (&((inode).i_pipe->fasync_writers))
-
 /* Drop the inode semaphore and wait for a pipe event, atomically */
-void pipe_wait(struct inode * inode);
+void pipe_wait(struct pipe_inode_info *pipe);
 
-struct inode* pipe_new(struct inode* inode);
-void free_pipe_info(struct inode* inode);
+struct pipe_inode_info * alloc_pipe_info(struct inode * inode);
+void free_pipe_info(struct inode * inode);
+void __free_pipe_info(struct pipe_inode_info *);
 
 /*
  * splice is tied to pipes as a transport (at least for now), so we'll just
index 6df2585c0169765def9648d35c5a0188ba8a3c53..66be58902b17c1f5a282c6fc5172a7fe61fcc56b 100644 (file)
@@ -199,6 +199,12 @@ extern int device_suspend(pm_message_t state);
 
 extern int dpm_runtime_suspend(struct device *, pm_message_t);
 extern void dpm_runtime_resume(struct device *);
+extern void __suspend_report_result(const char *function, void *fn, int ret);
+
+#define suspend_report_result(fn, ret)                                 \
+       do {                                                            \
+               __suspend_report_result(__FUNCTION__, fn, ret);         \
+       } while (0)
 
 #else /* !CONFIG_PM */
 
@@ -219,6 +225,8 @@ static inline void dpm_runtime_resume(struct device * dev)
 {
 }
 
+#define suspend_report_result(fn, ret) do { } while (0)
+
 #endif
 
 /* changes to device_may_wakeup take effect on the next pm state change.
index 1252b45face162d02b6d553429475786055503ab..008932d73c3564db945995b5cc1db52c8811c882 100644 (file)
@@ -15,11 +15,6 @@ extern int pm_active;
 struct pm_dev __deprecated *
 pm_register(pm_dev_t type, unsigned long id, pm_callback callback);
 
-/*
- * Unregister a device with power management
- */
-void __deprecated pm_unregister(struct pm_dev *dev);
-
 /*
  * Unregister all devices with matching callback
  */
@@ -41,8 +36,6 @@ static inline struct pm_dev *pm_register(pm_dev_t type,
        return NULL;
 }
 
-static inline void pm_unregister(struct pm_dev *dev) {}
-
 static inline void pm_unregister_all(pm_callback callback) {}
 
 static inline int pm_send_all(pm_request_t rqst, void *data)
index 135871df991103b661eb5e78e0c0c30084fc278d..4b47a0253425f9be28430757b1275d72a1245dae 100644 (file)
@@ -79,7 +79,7 @@ struct kcore_list {
 struct vmcore {
        struct list_head list;
        unsigned long long paddr;
-       unsigned long size;
+       unsigned long long size;
        loff_t offset;
 };
 
index 774e1acfb8c4bab01eb9a1291711d0a6948834a8..f1fbae7e390ec4f53d67fa54e244153768449061 100644 (file)
@@ -227,8 +227,8 @@ struct mdp_superblock_1 {
                                 */
 
        /* These are only valid with feature bit '4' */
-       __u64   reshape_position;       /* next address in array-space for reshape */
        __u32   new_level;      /* new level we are reshaping to                */
+       __u64   reshape_position;       /* next address in array-space for reshape */
        __u32   delta_disks;    /* change in number of raid_disks               */
        __u32   new_layout;     /* new layout                                   */
        __u32   new_chunk;      /* new chunk size (bytes)                       */
index 541f4828f5e760bc8808a154a38d5570e65f09a4..29b7d4f87d207a69a1b8a2c0167416f1332f030d 100644 (file)
@@ -684,6 +684,7 @@ static inline void prefetch_stack(struct task_struct *t) { }
 
 struct audit_context;          /* See audit.c */
 struct mempolicy;
+struct pipe_inode_info;
 
 enum sleep_type {
        SLEEP_NORMAL,
@@ -882,6 +883,11 @@ struct task_struct {
 
        atomic_t fs_excl;       /* holding fs exclusive resources */
        struct rcu_head rcu;
+
+       /*
+        * cache last used pipe for splice
+        */
+       struct pipe_inode_info *splice_pipe;
 };
 
 static inline pid_t process_group(struct task_struct *tsk)
@@ -905,7 +911,6 @@ static inline int pid_alive(struct task_struct *p)
 extern void free_task(struct task_struct *tsk);
 #define get_task_struct(tsk) do { atomic_inc(&(tsk)->usage); } while(0)
 
-extern void __put_task_struct_cb(struct rcu_head *rhp);
 extern void __put_task_struct(struct task_struct *t);
 
 static inline void put_task_struct(struct task_struct *t)
@@ -1187,8 +1192,7 @@ extern void wait_task_inactive(task_t * p);
 #define remove_parent(p)       list_del_init(&(p)->sibling)
 #define add_parent(p)          list_add_tail(&(p)->sibling,&(p)->parent->children)
 
-#define next_task(p)   list_entry((p)->tasks.next, struct task_struct, tasks)
-#define prev_task(p)   list_entry((p)->tasks.prev, struct task_struct, tasks)
+#define next_task(p)   list_entry(rcu_dereference((p)->tasks.next), struct task_struct, tasks)
 
 #define for_each_process(p) \
        for (p = &init_task ; (p = next_task(p)) != &init_task ; )
@@ -1203,9 +1207,10 @@ extern void wait_task_inactive(task_t * p);
 #define while_each_thread(g, t) \
        while ((t = next_thread(t)) != g)
 
-#define thread_group_leader(p) (p->pid == p->tgid)
+/* de_thread depends on thread_group_leader not being a pid based check */
+#define thread_group_leader(p) (p == p->group_leader)
 
-static inline task_t *next_thread(task_t *p)
+static inline task_t *next_thread(const task_t *p)
 {
        return list_entry(rcu_dereference(p->thread_group.next),
                                task_t, thread_group);
index 6336987dae6283806a531b6f7bf8d13efc0e9840..2925e66a6732937f1693e2e5fd1868ec6d86c3df 100644 (file)
@@ -41,7 +41,8 @@ struct screen_info {
        u16 vesapm_off;         /* 0x30 */
        u16 pages;              /* 0x32 */
        u16 vesa_attributes;    /* 0x34 */
-                               /* 0x36 -- 0x3f reserved for future expansion */
+       u32 capabilities;       /* 0x36 */
+                               /* 0x3a -- 0x3f reserved for future expansion */
 };
 
 extern struct screen_info screen_info;
diff --git a/include/linux/sdla_asy.h b/include/linux/sdla_asy.h
deleted file mode 100644 (file)
index f622425..0000000
+++ /dev/null
@@ -1,226 +0,0 @@
-/*****************************************************************************
-* sdla_asy.h   Header file for the Sangoma S508/S514 asynchronous code API     
-*
-* Author:      Gideon Hack     
-*
-* Copyright:   (c) 2000 Sangoma Technologies Inc.
-*
-*              This program is free software; you can redistribute it and/or
-*              modify it under the terms of the GNU General Public License
-*              as published by the Free Software Foundation; either version
-*              2 of the License, or (at your option) any later version.
-* ============================================================================
-*
-* Jan 28, 2000 Gideon Hack     Initial Version
-*
-*****************************************************************************/
-
-
-#ifndef _WANPIPE_ASYNC_H
-#define _WANPIPE_ASYNC_H
-
-/* ----------------------------------------------------------------------------
- *                        Interface commands
- * --------------------------------------------------------------------------*/
-
-#define SET_ASY_CONFIGURATION          0xE2    /* set the asychronous operational configuration */
-#define READ_ASY_CONFIGURATION         0xE3    /* read the current asychronous operational configuration */
-#define ENABLE_ASY_COMMUNICATIONS      0xE4    /* enable asychronous communications */
-#define DISABLE_ASY_COMMUNICATIONS     0xE5    /* disable asychronous communications */
-#define READ_ASY_OPERATIONAL_STATS     0xE7    /* retrieve the asychronous operational statistics */
-#define FLUSH_ASY_OPERATIONAL_STATS    0xE8    /* flush the asychronous operational statistics */
-#define TRANSMIT_ASY_BREAK_SIGNAL      0xEC    /* transmit an asychronous break signal */
-
-
-
-/* ----------------------------------------------------------------------------
- *                     Return codes from interface commands
- * --------------------------------------------------------------------------*/
-
-#define COMMAND_INVALID_FOR_PORT       0x50    /* the command is invalid for the selected port */
-#define DISABLE_ASY_COMMS_BEFORE_CFG   0xE1    /* communications must be disabled before setting the configuration */
-#define ASY_COMMS_ENABLED              0xE1    /* communications are currently enabled */
-#define ASY_COMMS_DISABLED             0xE1    /* communications are currently disabled */
-#define ASY_CFG_BEFORE_COMMS_ENABLED   0xE2    /* perform a SET_ASY_CONFIGURATION before enabling comms */
-#define LGTH_ASY_CFG_DATA_INVALID      0xE2    /* the length of the passed configuration data is invalid */
-#define INVALID_ASY_CFG_DATA           0xE3    /* the passed configuration data is invalid */
-#define ASY_BREAK_SIGNAL_BUSY          0xEC    /* a break signal is being transmitted */
-
-
-
-/* ----------------------------------------------------------------------------
- *   Constants for the SET_ASY_CONFIGURATION/READ_ASY_CONFIGURATION command
- * --------------------------------------------------------------------------*/
-
-/* the asynchronous configuration structure */
-typedef struct {
-       unsigned long baud_rate                 PACKED;                                                 /* the baud rate */     
-       unsigned short line_config_options      PACKED; /* line configuration options */
-       unsigned short modem_config_options     PACKED; /* modem configuration options */
-       unsigned short asy_API_options          PACKED; /* asynchronous API options */
-       unsigned short asy_protocol_options     PACKED; /* asynchronous protocol options */
-       unsigned short Tx_bits_per_char         PACKED; /* number of bits per tx character */
-       unsigned short Rx_bits_per_char         PACKED; /* number of bits per received character */
-       unsigned short stop_bits                PACKED; /* number of stop bits per character */
-       unsigned short parity                   PACKED; /* parity definition */
-       unsigned short break_timer              PACKED; /* the break signal timer */
-       unsigned short asy_Rx_inter_char_timer  PACKED; /* the receive inter-character timer */
-       unsigned short asy_Rx_complete_length   PACKED; /* the receive 'buffer complete' length */
-       unsigned short XON_char                 PACKED; /* the XON character */
-       unsigned short XOFF_char                PACKED; /* the XOFF character */
-       unsigned short asy_statistics_options   PACKED; /* async operational stat options */
-       unsigned long ptr_shared_mem_info_struct    PACKED;/* ptr to the shared memory area information structure */
-       unsigned long ptr_asy_Tx_stat_el_cfg_struct PACKED;/* ptr to the transmit status element configuration structure */
-       unsigned long ptr_asy_Rx_stat_el_cfg_struct PACKED;/* ptr to the receive status element configuration structure */
-} ASY_CONFIGURATION_STRUCT;
-
-/* permitted minimum and maximum values for setting the asynchronous configuration */
-#define MIN_ASY_BAUD_RATE              50      /* maximum baud rate */
-#define MAX_ASY_BAUD_RATE              250000  /* minimum baud rate */
-#define MIN_ASY_BITS_PER_CHAR          5       /* minimum number of bits per character */
-#define MAX_ASY_BITS_PER_CHAR          8       /* maximum number of bits per character */
-#define MIN_BREAK_TMR_VAL              0       /* minimum break signal timer */
-#define MAX_BREAK_TMR_VAL              5000    /* maximum break signal timer */
-#define MIN_ASY_RX_INTER_CHAR_TMR      0       /* minimum receive inter-character timer */
-#define MAX_ASY_RX_INTER_CHAR_TMR      30000   /* maximum receive inter-character timer */
-#define MIN_ASY_RX_CPLT_LENGTH         0       /* minimum receive 'length complete' value */
-#define MAX_ASY_RX_CPLT_LENGTH         2000    /* maximum receive 'length complete' value */
-
-/* bit settings for the 'asy_API_options' */
-#define ASY_RX_DATA_TRANSPARENT                0x0001  /* do not strip parity and unused bits from received characters */
-
-/* bit settings for the 'asy_protocol_options' */
-#define ASY_RTS_HS_FOR_RX              0x0001  /* RTS handshaking is used for reception control */
-#define ASY_XON_XOFF_HS_FOR_RX         0x0002  /* XON/XOFF handshaking is used for reception control */
-#define ASY_XON_XOFF_HS_FOR_TX         0x0004  /* XON/XOFF handshaking is used for transmission control */
-#define ASY_DCD_HS_FOR_TX              0x0008  /* DCD handshaking is used for transmission control */
-#define ASY_CTS_HS_FOR_TX              0x0020  /* CTS handshaking is used for transmission control */
-
-/* bit settings for the 'stop_bits' definition */
-#define ONE_STOP_BIT                   1                       /* representation for 1 stop bit */
-#define TWO_STOP_BITS                  2                       /* representation for 2 stop bits */
-#define ONE_AND_A_HALF_STOP_BITS       3                       /* representation for 1.5 stop bits */
-
-/* bit settings for the 'parity' definition */
-#define NO_PARITY                      0                       /* representation for no parity */
-#define ODD_PARITY                     1                       /* representation for odd parity */
-#define EVEN_PARITY                    2                       /* representation for even parity */
-
-
-
-/* ----------------------------------------------------------------------------
- *    Constants for the READ_COMMS_ERROR_STATS command (asynchronous mode)
- * --------------------------------------------------------------------------*/
-
-/* the communications error statistics structure */
-typedef struct {
-       unsigned short Rx_overrun_err_count     PACKED; /* receiver overrun error count */
-       unsigned short Rx_parity_err_count      PACKED; /* parity errors received count */
-       unsigned short Rx_framing_err_count     PACKED; /* framing errors received count */
-       unsigned short comms_err_stat_reserved_1 PACKED;/* reserved for later use */
-       unsigned short comms_err_stat_reserved_2 PACKED;/* reserved for later use */
-       unsigned short comms_err_stat_reserved_3 PACKED;/* reserved for later use */
-       unsigned short comms_err_stat_reserved_4 PACKED;/* reserved for later use */
-       unsigned short comms_err_stat_reserved_5 PACKED;/* reserved for later use */
-       unsigned short DCD_state_change_count   PACKED; /* DCD state change count */
-       unsigned short CTS_state_change_count   PACKED; /* CTS state change count */
-} ASY_COMMS_ERROR_STATS_STRUCT;
-
-
-
-/* ----------------------------------------------------------------------------
- *         Constants for the READ_ASY_OPERATIONAL_STATS command
- * --------------------------------------------------------------------------*/
-
-/* the asynchronous operational statistics structure */
-typedef struct {
-
-       /* Data transmission statistics */
-       unsigned long Data_blocks_Tx_count PACKED;/* number of blocks transmitted */
-       unsigned long Data_bytes_Tx_count  PACKED;/* number of bytes transmitted */
-       unsigned long Data_Tx_throughput   PACKED;/* transmit throughput */
-       unsigned long no_ms_for_Data_Tx_thruput_comp PACKED;/* millisecond time used for the Tx throughput computation */
-       unsigned long Tx_Data_discard_lgth_err_count PACKED;/* number of Data blocks discarded (length error) */
-       unsigned long reserved_Data_frm_Tx_stat1 PACKED;/* reserved for later use */
-       unsigned long reserved_Data_frm_Tx_stat2 PACKED;/* reserved for later use */
-       unsigned long reserved_Data_frm_Tx_stat3 PACKED;/* reserved for later use */
-
-       /* Data reception statistics */
-       unsigned long Data_blocks_Rx_count PACKED;/* number of blocks received */
-       unsigned long Data_bytes_Rx_count  PACKED;/* number of bytes received */
-       unsigned long Data_Rx_throughput   PACKED;/* receive throughput */
-       unsigned long no_ms_for_Data_Rx_thruput_comp PACKED;/* millisecond time used for the Rx throughput computation */
-       unsigned long Rx_Data_bytes_discard_count    PACKED;/* received Data bytes discarded */
-       unsigned long reserved_Data_frm_Rx_stat1     PACKED;/* reserved for later use */
-
-       /* handshaking protocol statistics */
-       unsigned short XON_chars_Tx_count       PACKED; /* number of XON characters transmitted */
-       unsigned short XOFF_chars_Tx_count      PACKED; /* number of XOFF characters transmitted */
-       unsigned short XON_chars_Rx_count       PACKED; /* number of XON characters received */
-       unsigned short XOFF_chars_Rx_count      PACKED; /* number of XOFF characters received */
-       unsigned short Tx_halt_modem_low_count  PACKED; /* number of times Tx halted (modem line low) */
-       unsigned short Rx_halt_RTS_low_count    PACKED; /* number of times Rx halted by setting RTS low */
-       unsigned long reserved_handshaking_stat1 PACKED;/* reserved for later use */
-
-       /* break statistics */
-       unsigned short break_Tx_count   PACKED; /* number of break sequences transmitted */
-       unsigned short break_Rx_count   PACKED; /* number of break sequences received */
-       unsigned long reserved_break_stat1 PACKED;/* reserved for later use */
-
-       /* miscellaneous statistics */
-       unsigned long reserved_misc_stat1       PACKED; /* reserved for later use */
-       unsigned long reserved_misc_stat2       PACKED; /* reserved for later use */
-
-} ASY_OPERATIONAL_STATS_STRUCT;
-
-
-
-/* ----------------------------------------------------------------------------
- *                      Constants for Data transmission
- * --------------------------------------------------------------------------*/
-
-/* the Data block transmit status element configuration structure */
-typedef struct {
-       unsigned short number_Tx_status_elements PACKED;                /* number of transmit status elements */
-       unsigned long base_addr_Tx_status_elements PACKED;      /* base address of the transmit element list */
-       unsigned long next_Tx_status_element_to_use PACKED;     /* pointer to the next transmit element to be used */
-} ASY_TX_STATUS_EL_CFG_STRUCT;
-
-
-/* the Data block transmit status element structure */
-typedef struct {
-       unsigned char opp_flag PACKED;                                                          /* opp flag */
-       unsigned short data_length PACKED;                                              /* length of the block to be transmitted */
-       unsigned char reserved_1 PACKED;                                                        /* reserved for internal use */
-       unsigned long reserved_2 PACKED;                                                        /* reserved for internal use */
-       unsigned long reserved_3 PACKED;                                                        /* reserved for internal use */
-       unsigned long ptr_data_bfr PACKED;                                              /* pointer to the data area */
-} ASY_DATA_TX_STATUS_EL_STRUCT;
-
-
-
-/* ----------------------------------------------------------------------------
- *                      Constants for Data reception
- * --------------------------------------------------------------------------*/
-
-/* the Data block receive status element configuration structure */
-typedef struct {
-       unsigned short number_Rx_status_elements    PACKED;/* number of receive status elements */
-       unsigned long base_addr_Rx_status_elements  PACKED;/* base address of the receive element list */
-       unsigned long next_Rx_status_element_to_use PACKED;/* pointer to the next receive element to be used */
-       unsigned long base_addr_Rx_buffer       PACKED;/* base address of the receive data buffer */
-       unsigned long end_addr_Rx_buffer        PACKED;/* end address of the receive data buffer */
-} ASY_RX_STATUS_EL_CFG_STRUCT;
-
-/* the Data block receive status element structure */
-typedef struct {
-       unsigned char opp_flag          PACKED; /* opp flag */
-       unsigned short data_length      PACKED; /* length of the received data block */
-       unsigned char reserved_1        PACKED; /* reserved for internal use */
-       unsigned short time_stamp       PACKED; /* receive time stamp (HDLC_STREAMING_MODE) */
-       unsigned short data_buffered    PACKED; /* the number of data bytes still buffered */
-       unsigned long reserved_2        PACKED; /* reserved for internal use */
-       unsigned long ptr_data_bfr      PACKED; /* pointer to the data area */
-} ASY_DATA_RX_STATUS_EL_STRUCT;
-
-#endif
diff --git a/include/linux/sdla_chdlc.h b/include/linux/sdla_chdlc.h
deleted file mode 100644 (file)
index d2e35a2..0000000
+++ /dev/null
@@ -1,813 +0,0 @@
-/*************************************************************************
- sdla_chdlc.h  Sangoma Cisco HDLC firmware API definitions
-
- Author:       Gideon Hack
-               Nenad Corbic <ncorbic@sangoma.com>      
-
- Copyright:    (c) 1995-2000 Sangoma Technologies Inc.
-
-               This program is free software; you can redistribute it and/or
-               modify it under the term of the GNU General Public License
-               as published by the Free Software Foundation; either version
-               2 of the License, or (at your option) any later version.
-
-===========================================================================
-  Oct 04, 1999  Nenad Corbic    Updated API support
-  Jun 02, 1999  Gideon Hack     Changes for S514 usage.
-  Oct 28, 1998 Jaspreet Singh  Made changes for Dual Port CHDLC.
-  Jun 11, 1998 David Fong      Initial version.
-===========================================================================
-
- Organization
-       - Compatibility notes
-       - Constants defining the shared memory control block (mailbox)
-       - Interface commands
-       - Return code from interface commands
-       - Constants for the commands (structures for casting data)
-       - UDP Management constants and structures
-
-*************************************************************************/
-
-#ifndef _SDLA_CHDLC_H
-#  define _SDLC_CHDLC_H
-
-/*------------------------------------------------------------------------
-   Notes:
-
-       All structres defined in this file are byte-aligned.  
-
-       Compiler        Platform
-       ------------------------
-       GNU C           Linux
-
-------------------------------------------------------------------------*/
-
-#ifndef        PACKED
-#define        PACKED __attribute__((packed))
-#endif /* PACKED */
-
-
-/* ----------------------------------------------------------------------------
- *        Constants defining the shared memory control block (mailbox)
- * --------------------------------------------------------------------------*/
-
-#define PRI_BASE_ADDR_MB_STRUCT        0xE000  /* the base address of the mailbox structure on the adapter */
-#define SEC_BASE_ADDR_MB_STRUCT        0xE800  /* the base address of the mailbox structure on the adapter */
-#define SIZEOF_MB_DATA_BFR             2032    /* the size of the actual mailbox data area */
-#define NUMBER_MB_RESERVED_BYTES       0x0B    /* the number of reserved bytes in the mailbox header area */
-
-
-#define MIN_LGTH_CHDLC_DATA_CFG        300     /* min length of the CHDLC data field (for configuration purposes) */
-#define PRI_MAX_NO_DATA_BYTES_IN_FRAME  15354 /* PRIMARY - max length of the CHDLC data field */
-
-typedef struct {
-       unsigned char opp_flag PACKED;                  /* the opp flag */
-       unsigned char command PACKED;                   /* the user command */
-       unsigned short buffer_length PACKED;            /* the data length */
-       unsigned char return_code PACKED;               /* the return code */
-       unsigned char MB_reserved[NUMBER_MB_RESERVED_BYTES] PACKED;     /* reserved for later */
-       unsigned char data[SIZEOF_MB_DATA_BFR] PACKED;  /* the data area */
-} CHDLC_MAILBOX_STRUCT;
-
-typedef struct {
-        pid_t                   pid_num PACKED;
-        CHDLC_MAILBOX_STRUCT     cmdarea PACKED;
-
-} CMDBLOCK_STRUCT;
-
-
-
-
-/* ----------------------------------------------------------------------------
- *                        Interface commands
- * --------------------------------------------------------------------------*/
-
-/* global interface commands */
-#define READ_GLOBAL_EXCEPTION_CONDITION        0x01
-#define SET_GLOBAL_CONFIGURATION       0x02
-#define READ_GLOBAL_CONFIGURATION      0x03
-#define READ_GLOBAL_STATISTICS         0x04
-#define FLUSH_GLOBAL_STATISTICS                0x05
-#define SET_MODEM_STATUS               0x06    /* set status of DTR or RTS */
-#define READ_MODEM_STATUS              0x07    /* read status of CTS and DCD */
-#define READ_COMMS_ERROR_STATS         0x08    
-#define FLUSH_COMMS_ERROR_STATS                0x09
-#define SET_TRACE_CONFIGURATION                0x0A    /* set the line trace config */
-#define READ_TRACE_CONFIGURATION       0x0B    /* read the line trace config */
-#define READ_TRACE_STATISTICS          0x0C    /* read the trace statistics */
-#define FLUSH_TRACE_STATISTICS         0x0D    /* flush the trace statistics */
-#define FT1_MONITOR_STATUS_CTRL                0x1C    /* set the status of the S508/FT1 monitoring */
-#define SET_FT1_CONFIGURATION          0x18    /* set the FT1 configuration */
-#define READ_FT1_CONFIGURATION         0x19    /* read the FT1 configuration */
-#define TRANSMIT_ASYNC_DATA_TO_FT1     0x1A    /* output asynchronous data to the FT1 */
-#define RECEIVE_ASYNC_DATA_FROM_FT1    0x1B    /* receive asynchronous data from the FT1 */
-#define FT1_MONITOR_STATUS_CTRL                0x1C    /* set the status of the FT1 monitoring */
-
-#define READ_FT1_OPERATIONAL_STATS     0x1D    /* read the S508/FT1 operational statistics */
-#define SET_FT1_MODE                   0x1E    /* set the operational mode of the S508/FT1 module */
-
-/* CHDLC-level interface commands */
-#define READ_CHDLC_CODE_VERSION                0x20    
-#define READ_CHDLC_EXCEPTION_CONDITION 0x21    /* read exception condition from the adapter */
-#define SET_CHDLC_CONFIGURATION                0x22
-#define READ_CHDLC_CONFIGURATION       0x23
-#define ENABLE_CHDLC_COMMUNICATIONS    0x24
-#define DISABLE_CHDLC_COMMUNICATIONS   0x25
-#define READ_CHDLC_LINK_STATUS         0x26
-#define READ_CHDLC_OPERATIONAL_STATS   0x27
-#define FLUSH_CHDLC_OPERATIONAL_STATS  0x28
-#define SET_CHDLC_INTERRUPT_TRIGGERS   0x30    /* set application interrupt triggers */
-#define READ_CHDLC_INTERRUPT_TRIGGERS  0x31    /* read application interrupt trigger configuration */
-
-/* Special UDP drivers management commands */
-#define CPIPE_ENABLE_TRACING                           0x50
-#define CPIPE_DISABLE_TRACING                          0x51
-#define CPIPE_GET_TRACE_INFO                           0x52
-#define CPIPE_GET_IBA_DATA                             0x53
-#define CPIPE_FT1_READ_STATUS                          0x54
-#define CPIPE_DRIVER_STAT_IFSEND                       0x55
-#define CPIPE_DRIVER_STAT_INTR                         0x56
-#define CPIPE_DRIVER_STAT_GEN                          0x57
-#define CPIPE_FLUSH_DRIVER_STATS                       0x58
-#define CPIPE_ROUTER_UP_TIME                           0x59
-
-/* Driver specific commands for API */
-#define        CHDLC_READ_TRACE_DATA           0xE4    /* read trace data */
-#define TRACE_ALL                       0x00
-#define TRACE_PROT                     0x01
-#define TRACE_DATA                     0x02
-
-#define DISCARD_RX_ERROR_FRAMES        0x0001
-
-/* ----------------------------------------------------------------------------
- *                     Return codes from interface commands
- * --------------------------------------------------------------------------*/
-
-#define COMMAND_OK                             0x00
-
-/* return codes from global interface commands */
-#define NO_GLOBAL_EXCEP_COND_TO_REPORT         0x01    /* there is no CHDLC exception condition to report */
-#define LGTH_GLOBAL_CFG_DATA_INVALID           0x01    /* the length of the passed global configuration data is invalid */
-#define LGTH_TRACE_CFG_DATA_INVALID            0x01    /* the length of the passed trace configuration data is invalid */
-#define IRQ_TIMEOUT_VALUE_INVALID              0x02    /* an invalid application IRQ timeout value was selected */
-#define TRACE_CONFIG_INVALID                   0x02    /* the passed line trace configuration is invalid */
-#define ADAPTER_OPERATING_FREQ_INVALID         0x03    /* an invalid adapter operating frequency was selected */
-#define TRC_DEAC_TMR_INVALID                   0x03    /* the trace deactivation timer is invalid */
-#define S508_FT1_ADPTR_NOT_PRESENT             0x0C    /* the S508/FT1 adapter is not present */
-#define INVALID_FT1_STATUS_SELECTION            0x0D    /* the S508/FT1 status selection is invalid */
-#define FT1_OP_STATS_NOT_ENABLED               0x0D    /* the FT1 operational statistics have not been enabled */
-#define FT1_OP_STATS_NOT_AVAILABLE             0x0E    /* the FT1 operational statistics are not currently available */
-#define S508_FT1_MODE_SELECTION_BUSY           0x0E    /* the S508/FT1 adapter is busy selecting the operational mode */
-
-/* return codes from command READ_GLOBAL_EXCEPTION_CONDITION */
-#define EXCEP_MODEM_STATUS_CHANGE              0x10            /* a modem status change occurred */
-#define EXCEP_TRC_DISABLED                     0x11            /* the trace has been disabled */
-#define EXCEP_IRQ_TIMEOUT                      0x12            /* IRQ timeout */
-
-/* return codes from CHDLC-level interface commands */
-#define NO_CHDLC_EXCEP_COND_TO_REPORT          0x21    /* there is no CHDLC exception condition to report */
-#define CHDLC_COMMS_DISABLED                   0x21    /* communications are not currently enabled */
-#define CHDLC_COMMS_ENABLED                    0x21    /* communications are currently enabled */
-#define DISABLE_CHDLC_COMMS_BEFORE_CFG         0x21    /* CHDLC communications must be disabled before setting the configuration */
-#define ENABLE_CHDLC_COMMS_BEFORE_CONN         0x21    /* communications must be enabled before using the CHDLC_CONNECT conmmand */
-#define CHDLC_CFG_BEFORE_COMMS_ENABLED         0x22    /* perform a SET_CHDLC_CONFIGURATION before enabling comms */
-#define LGTH_CHDLC_CFG_DATA_INVALID            0x22    /* the length of the passed CHDLC configuration data is invalid */
-#define LGTH_INT_TRIGGERS_DATA_INVALID         0x22    /* the length of the passed interrupt trigger data is invalid */
-#define INVALID_IRQ_SELECTED                   0x23    /* in invalid IRQ was selected in the SET_CHDLC_INTERRUPT_TRIGGERS */
-#define INVALID_CHDLC_CFG_DATA                 0x23    /* the passed CHDLC configuration data is invalid */
-#define IRQ_TMR_VALUE_INVALID                  0x24    /* an invalid application IRQ timer value was selected */
-#define LARGER_PERCENT_TX_BFR_REQUIRED         0x24    /* a larger Tx buffer percentage is required */
-#define LARGER_PERCENT_RX_BFR_REQUIRED         0x25    /* a larger Rx buffer percentage is required */
-#define S514_BOTH_PORTS_SAME_CLK_MODE          0x26    /* S514 - both ports must have same clock mode */
-#define INVALID_CMND_HDLC_STREAM_MODE           0x4E    /* the CHDLC interface command is invalid for HDLC streaming mode */
-#define INVALID_CHDLC_COMMAND                  0x4F    /* the defined CHDLC interface command is invalid */
-
-/* return codes from command READ_CHDLC_EXCEPTION_CONDITION */
-#define EXCEP_LINK_ACTIVE                      0x30    /* the CHDLC link has become active */
-#define EXCEP_LINK_INACTIVE_MODEM              0x31    /* the CHDLC link has become inactive (modem status) */
-#define EXCEP_LINK_INACTIVE_KPALV              0x32    /* the CHDLC link has become inactive (keepalive status) */
-#define EXCEP_IP_ADDRESS_DISCOVERED            0x33    /* the IP address has been discovered */
-#define EXCEP_LOOPBACK_CONDITION               0x34    /* a loopback condition has occurred */
-
-
-/* return code from command CHDLC_SEND_WAIT and CHDLC_SEND_NO_WAIT */
-#define LINK_DISCONNECTED                      0x21
-#define NO_TX_BFRS_AVAIL                       0x24
-
-
-/* ----------------------------------------------------------------------------
- * Constants for the SET_GLOBAL_CONFIGURATION/READ_GLOBAL_CONFIGURATION commands
- * --------------------------------------------------------------------------*/
-
-/* the global configuration structure */
-typedef struct {
-       unsigned short adapter_config_options PACKED;   /* adapter config options */
-       unsigned short app_IRQ_timeout PACKED;          /* application IRQ timeout */
-       unsigned long adapter_operating_frequency PACKED;       /* adapter operating frequency */
-} GLOBAL_CONFIGURATION_STRUCT;
-
-/* settings for the 'app_IRQ_timeout' */
-#define MAX_APP_IRQ_TIMEOUT_VALUE      5000    /* the maximum permitted IRQ timeout */
-
-
-
-/* ----------------------------------------------------------------------------
- *             Constants for the READ_GLOBAL_STATISTICS command
- * --------------------------------------------------------------------------*/
-
-/* the global statistics structure */
-typedef struct {
-       unsigned short app_IRQ_timeout_count PACKED;
-} GLOBAL_STATS_STRUCT;
-
-
-
-/* ----------------------------------------------------------------------------
- *             Constants for the READ_COMMS_ERROR_STATS command
- * --------------------------------------------------------------------------*/
-
-/* the communications error statistics structure */
-typedef struct {
-       unsigned short Rx_overrun_err_count PACKED;
-       unsigned short CRC_err_count PACKED;    /* receiver CRC error count */
-       unsigned short Rx_abort_count PACKED;   /* abort frames recvd count */
-       unsigned short Rx_dis_pri_bfrs_full_count PACKED;/* receiver disabled */
-       unsigned short comms_err_stat_reserved_1 PACKED;/* reserved for later */
-       unsigned short sec_Tx_abort_msd_Tx_int_count PACKED; /* secondary - abort frames transmitted count (missed Tx interrupt) */
-       unsigned short missed_Tx_und_int_count PACKED;  /* missed tx underrun interrupt count */
-        unsigned short sec_Tx_abort_count PACKED;   /*secondary-abort frames tx count */
-       unsigned short DCD_state_change_count PACKED; /* DCD state change */
-       unsigned short CTS_state_change_count PACKED; /* CTS state change */
-} COMMS_ERROR_STATS_STRUCT;
-
-
-
-/* ----------------------------------------------------------------------------
- *                  Constants used for line tracing
- * --------------------------------------------------------------------------*/
-
-/* the trace configuration structure (SET_TRACE_CONFIGURATION/READ_TRACE_CONFIGURATION commands) */
-typedef struct {
-       unsigned char trace_config PACKED;              /* trace configuration */
-       unsigned short trace_deactivation_timer PACKED; /* trace deactivation timer */
-       unsigned long ptr_trace_stat_el_cfg_struct PACKED;      /* a pointer to the line trace element configuration structure */
-} LINE_TRACE_CONFIG_STRUCT;
-
-/* 'trace_config' bit settings */
-#define TRACE_INACTIVE         0x00    /* trace is inactive */
-#define TRACE_ACTIVE           0x01    /* trace is active */
-#define TRACE_DELAY_MODE       0x04    /* operate the trace in delay mode */
-#define TRACE_DATA_FRAMES      0x08    /* trace Data frames */
-#define TRACE_SLARP_FRAMES     0x10    /* trace SLARP frames */
-#define TRACE_CDP_FRAMES       0x20    /* trace CDP frames */
-
-/* the line trace status element configuration structure */
-typedef struct {
-       unsigned short number_trace_status_elements PACKED;     /* number of line trace elements */
-       unsigned long base_addr_trace_status_elements PACKED;   /* base address of the trace element list */
-       unsigned long next_trace_element_to_use PACKED; /* pointer to the next trace element to be used */
-       unsigned long base_addr_trace_buffer PACKED;            /* base address of the trace data buffer */
-       unsigned long end_addr_trace_buffer PACKED;             /* end address of the trace data buffer */
-} TRACE_STATUS_EL_CFG_STRUCT;
-
-/* the line trace status element structure */
-typedef struct {
-       unsigned char opp_flag PACKED;                  /* opp flag */
-       unsigned short trace_length PACKED;             /* trace length */
-       unsigned char trace_type PACKED;                /* trace type */
-       unsigned short trace_time_stamp PACKED; /* time stamp */
-       unsigned short trace_reserved_1 PACKED; /* reserved for later use */
-       unsigned long trace_reserved_2 PACKED;          /* reserved for later use */
-       unsigned long ptr_data_bfr PACKED;              /* ptr to the trace data buffer */
-} TRACE_STATUS_ELEMENT_STRUCT;
-
-/* "trace_type" bit settings */
-#define TRACE_INCOMING                         0x00
-#define TRACE_OUTGOINGING              0x01
-#define TRACE_INCOMING_ABORTED                 0x10
-#define TRACE_INCOMING_CRC_ERROR       0x20
-#define TRACE_INCOMING_OVERRUN_ERROR   0x40
-
-
-
-/* the line trace statistics structure */
-typedef struct {
-       unsigned long frames_traced_count PACKED;       /* number of frames traced */
-       unsigned long trc_frms_not_recorded_count PACKED;       /* number of trace frames discarded */
-} LINE_TRACE_STATS_STRUCT;
-
-
-/* ----------------------------------------------------------------------------
- *               Constants for the FT1_MONITOR_STATUS_CTRL command
- * --------------------------------------------------------------------------*/
-
-#define DISABLE_FT1_STATUS_STATISTICS  0x00    /* disable the FT1 status and statistics monitoring */
-#define ENABLE_READ_FT1_STATUS         0x01    /* read the FT1 operational status */
-#define ENABLE_READ_FT1_OP_STATS       0x02    /* read the FT1 operational statistics */
-#define FLUSH_FT1_OP_STATS             0x04    /* flush the FT1 operational statistics */
-
-
-
-
-/* ----------------------------------------------------------------------------
- *               Constants for the SET_CHDLC_CONFIGURATION command
- * --------------------------------------------------------------------------*/
-
-/* the CHDLC configuration structure */
-typedef struct {
-       unsigned long baud_rate PACKED;         /* the baud rate */     
-       unsigned short line_config_options PACKED;      /* line configuration options */
-       unsigned short modem_config_options PACKED;     /* modem configration options */
-       unsigned short modem_status_timer PACKED;       /* timer for monitoring modem status changes */
-       unsigned short CHDLC_API_options PACKED;        /* CHDLC API options */
-       unsigned short CHDLC_protocol_options PACKED;   /* CHDLC protocol options */
-       unsigned short percent_data_buffer_for_Tx PACKED;       /* percentage data buffering used for Tx */
-       unsigned short CHDLC_statistics_options PACKED; /* CHDLC operational statistics options */
-       unsigned short max_CHDLC_data_field_length PACKED;      /* the maximum length of the CHDLC Data field */
-       unsigned short transmit_keepalive_timer PACKED;         /* the transmit keepalive timer */
-       unsigned short receive_keepalive_timer PACKED;          /* the receive keepalive timer */
-       unsigned short keepalive_error_tolerance PACKED;        /* the receive keepalive error tolerance */
-       unsigned short SLARP_request_timer PACKED;              /* the SLARP request timer */
-       unsigned long IP_address PACKED;                        /* the IP address */
-       unsigned long IP_netmask PACKED;                        /* the IP netmask */
-       unsigned long ptr_shared_mem_info_struct PACKED;        /* a pointer to the shared memory area information structure */
-       unsigned long ptr_CHDLC_Tx_stat_el_cfg_struct PACKED;   /* a pointer to the transmit status element configuration structure */
-       unsigned long ptr_CHDLC_Rx_stat_el_cfg_struct PACKED;   /* a pointer to the receive status element configuration structure */
-} CHDLC_CONFIGURATION_STRUCT;
-
-/* settings for the 'line_config_options' */
-#define INTERFACE_LEVEL_V35                                    0x0000 /* V.35 interface level */
-#define INTERFACE_LEVEL_RS232                                  0x0001 /* RS-232 interface level */
-
-/* settings for the 'modem_config_options' */
-
-#define DONT_RAISE_DTR_RTS_ON_EN_COMMS         0x0001
-/* don't automatically raise DTR and RTS when performing an
-   ENABLE_CHDLC_COMMUNICATIONS command */
-
-#define DONT_REPORT_CHG_IN_MODEM_STAT          0x0002
-/* don't report changes in modem status to the application */
-
-
-/* bit settings for the 'CHDLC_protocol_options' byte */
-
-#define IGNORE_DCD_FOR_LINK_STAT               0x0001
-/* ignore DCD in determining the CHDLC link status */
-
-#define IGNORE_CTS_FOR_LINK_STAT               0x0002
-/* ignore CTS in determining the CHDLC link status */
-
-#define IGNORE_KPALV_FOR_LINK_STAT             0x0004
-/* ignore keepalive frames in determining the CHDLC link status */ 
-
-#define SINGLE_TX_BUFFER                       0x4000 
-/* configure a single transmit buffer */
-
-#define HDLC_STREAMING_MODE                    0x8000
-
-/*   settings for the 'CHDLC_statistics_options' */
-
-#define CHDLC_TX_DATA_BYTE_COUNT_STAT          0x0001
-/* record the number of Data bytes transmitted */
-
-#define CHDLC_RX_DATA_BYTE_COUNT_STAT          0x0002
-/* record the number of Data bytes received */
-
-#define CHDLC_TX_THROUGHPUT_STAT               0x0004
-/* compute the Data frame transmit throughput */
-
-#define CHDLC_RX_THROUGHPUT_STAT               0x0008
-/* compute the Data frame receive throughput */
-
-
-/* permitted minimum and maximum values for setting the CHDLC configuration */
-#define PRI_MAX_BAUD_RATE_S508 2666666 /* PRIMARY   - maximum baud rate (S508) */
-#define SEC_MAX_BAUD_RATE_S508 258064  /* SECONDARY - maximum baud rate (S508) */
-#define PRI_MAX_BAUD_RATE_S514  2750000 /* PRIMARY   - maximum baud rate (S508) */
-#define SEC_MAX_BAUD_RATE_S514  515625  /* SECONDARY - maximum baud rate (S508) */
-#define MIN_MODEM_TIMER        0                       /* minimum modem status timer */
-#define MAX_MODEM_TIMER        5000                    /* maximum modem status timer */
-
-#define SEC_MAX_NO_DATA_BYTES_IN_FRAME  2048 /* SECONDARY - max length of the CHDLC data field */
-
-#define MIN_Tx_KPALV_TIMER     0         /* minimum transmit keepalive timer */
-#define MAX_Tx_KPALV_TIMER     60000     /* maximum transmit keepalive timer */
-#define DEFAULT_Tx_KPALV_TIMER 10000     /* default transmit keepalive timer */
-
-#define MIN_Rx_KPALV_TIMER     10        /* minimum receive keepalive timer */
-#define MAX_Rx_KPALV_TIMER     60000     /* maximum receive keepalive timer */
-#define DEFAULT_Rx_KPALV_TIMER 10000     /* default receive keepalive timer */
-
-#define MIN_KPALV_ERR_TOL      1         /* min kpalv error tolerance count */
-#define MAX_KPALV_ERR_TOL      20        /* max kpalv error tolerance count */
-#define DEFAULT_KPALV_ERR_TOL  3         /* default value */
-
-#define MIN_SLARP_REQ_TIMER    0         /* min transmit SLARP Request timer */
-#define MAX_SLARP_REQ_TIMER    60000     /* max transmit SLARP Request timer */
-#define DEFAULT_SLARP_REQ_TIMER        0         /* default value -- no SLARP */
-
-
-
-/* ----------------------------------------------------------------------------
- *             Constants for the READ_CHDLC_LINK_STATUS command
- * --------------------------------------------------------------------------*/
-
-/* the CHDLC status structure */
-typedef struct {
-       unsigned char CHDLC_link_status PACKED; /* CHDLC link status */
-       unsigned char no_Data_frms_for_app PACKED;      /* number of Data frames available for the application */
-       unsigned char receiver_status PACKED;   /* enabled/disabled */
-       unsigned char SLARP_state PACKED;       /* internal SLARP state */
-} CHDLC_LINK_STATUS_STRUCT;
-
-/* settings for the 'CHDLC_link_status' variable */
-#define CHDLC_LINK_INACTIVE            0x00    /* the CHDLC link is inactive */
-#define CHDLC_LINK_ACTIVE              0x01    /* the CHDLC link is active */
-
-
-
-/* ----------------------------------------------------------------------------
- *           Constants for the READ_CHDLC_OPERATIONAL_STATS command
- * --------------------------------------------------------------------------*/
-
-/* the CHDLC operational statistics structure */
-typedef struct {
-
-       /* Data frame transmission statistics */
-       unsigned long Data_frames_Tx_count PACKED;      /* # of frames transmitted */
-       unsigned long Data_bytes_Tx_count PACKED;       /* # of bytes transmitted */
-       unsigned long Data_Tx_throughput PACKED;        /* transmit throughput */
-       unsigned long no_ms_for_Data_Tx_thruput_comp PACKED;    /* millisecond time used for the Tx throughput computation */
-       unsigned long Tx_Data_discard_lgth_err_count PACKED;    /* number of Data frames discarded (length error) */
-       unsigned long reserved_Data_frm_Tx_stat1 PACKED;        /* reserved for later */
-       unsigned long reserved_Data_frm_Tx_stat2 PACKED;        /* reserved for later */
-       unsigned long reserved_Data_frm_Tx_stat3 PACKED;        /* reserved for later */
-
-       /* Data frame reception statistics */
-       unsigned long Data_frames_Rx_count PACKED;      /* number of frames received */
-       unsigned long Data_bytes_Rx_count PACKED;       /* number of bytes received */
-       unsigned long Data_Rx_throughput PACKED;        /* receive throughput */
-       unsigned long no_ms_for_Data_Rx_thruput_comp PACKED;    /* millisecond time used for the Rx throughput computation */
-       unsigned long Rx_Data_discard_short_count PACKED;       /* received Data frames discarded (too short) */
-       unsigned long Rx_Data_discard_long_count PACKED;        /* received Data frames discarded (too long) */
-       unsigned long Rx_Data_discard_inactive_count PACKED;    /* received Data frames discarded (link inactive) */
-       unsigned long reserved_Data_frm_Rx_stat1 PACKED;        /* reserved for later */
-
-       /* SLARP frame transmission/reception statistics */
-       unsigned long CHDLC_SLARP_REQ_Tx_count PACKED;          /* number of SLARP Request frames transmitted */
-       unsigned long CHDLC_SLARP_REQ_Rx_count PACKED;          /* number of SLARP Request frames received */
-       unsigned long CHDLC_SLARP_REPLY_Tx_count PACKED;        /* number of SLARP Reply frames transmitted */
-       unsigned long CHDLC_SLARP_REPLY_Rx_count PACKED;        /* number of SLARP Reply frames received */
-       unsigned long CHDLC_SLARP_KPALV_Tx_count PACKED;        /* number of SLARP keepalive frames transmitted */
-       unsigned long CHDLC_SLARP_KPALV_Rx_count PACKED;        /* number of SLARP keepalive frames received */
-       unsigned long reserved_SLARP_stat1 PACKED;              /* reserved for later */
-       unsigned long reserved_SLARP_stat2 PACKED;              /* reserved for later */
-
-       /* CDP frame transmission/reception statistics */
-       unsigned long CHDLC_CDP_Tx_count PACKED;                /* number of CDP frames transmitted */
-       unsigned long CHDLC_CDP_Rx_count PACKED;                /* number of CDP frames received */
-       unsigned long reserved_CDP_stat1 PACKED;                /* reserved for later */
-       unsigned long reserved_CDP_stat2 PACKED;                /* reserved for later */
-       unsigned long reserved_CDP_stat3 PACKED;                /* reserved for later */
-       unsigned long reserved_CDP_stat4 PACKED;                /* reserved for later */
-       unsigned long reserved_CDP_stat5 PACKED;                /* reserved for later */
-       unsigned long reserved_CDP_stat6 PACKED;                /* reserved for later */
-
-       /* Incoming frames with a format error statistics */
-       unsigned short Rx_frm_incomp_CHDLC_hdr_count PACKED;    /* frames received of with incomplete Cisco HDLC header */
-       unsigned short Rx_frms_too_long_count PACKED;           /* frames received of excessive length count */
-       unsigned short Rx_invalid_CHDLC_addr_count PACKED;      /* frames received with an invalid CHDLC address count */
-       unsigned short Rx_invalid_CHDLC_ctrl_count PACKED;      /* frames received with an invalid CHDLC control field count */
-       unsigned short Rx_invalid_CHDLC_type_count PACKED;      /* frames received of an invalid CHDLC frame type count */
-       unsigned short Rx_SLARP_invalid_code_count PACKED;      /* SLARP frame received with an invalid packet code */
-       unsigned short Rx_SLARP_Reply_bad_IP_addr PACKED;       /* SLARP Reply received - bad IP address */
-       unsigned short Rx_SLARP_Reply_bad_netmask PACKED;       /* SLARP Reply received - bad netmask */
-       unsigned long reserved_frm_format_err1 PACKED;          /* reserved for later */
-       unsigned long reserved_frm_format_err2 PACKED;          /* reserved for later */
-       unsigned long reserved_frm_format_err3 PACKED;          /* reserved for later */
-       unsigned long reserved_frm_format_err4 PACKED;          /* reserved for later */
-
-       /* CHDLC timeout/retry statistics */
-       unsigned short SLARP_Rx_keepalive_TO_count PACKED;      /* timeout count for incoming SLARP frames */
-       unsigned short SLARP_Request_TO_count PACKED;           /* timeout count for SLARP Request frames */
-       unsigned long To_retry_reserved_stat1 PACKED;           /* reserved for later */
-       unsigned long To_retry_reserved_stat2 PACKED;           /* reserved for later */
-       unsigned long To_retry_reserved_stat3 PACKED;           /* reserved for later */
-
-       /* CHDLC link active/inactive and loopback statistics */
-       unsigned short link_active_count PACKED;                /* number of times that the link went active */
-       unsigned short link_inactive_modem_count PACKED;        /* number of times that the link went inactive (modem failure) */
-       unsigned short link_inactive_keepalive_count PACKED;    /* number of times that the link went inactive (keepalive failure) */
-       unsigned short link_looped_count PACKED;                /* link looped count */
-       unsigned long link_status_reserved_stat1 PACKED;        /* reserved for later use */
-       unsigned long link_status_reserved_stat2 PACKED;        /* reserved for later use */
-
-       /* miscellaneous statistics */
-       unsigned long reserved_misc_stat1 PACKED;               /* reserved for later */
-       unsigned long reserved_misc_stat2 PACKED;               /* reserved for later */
-       unsigned long reserved_misc_stat3 PACKED;               /* reserved for later */
-       unsigned long reserved_misc_stat4 PACKED;               /* reserved for later */
-
-} CHDLC_OPERATIONAL_STATS_STRUCT;
-
-
-
-/* ----------------------------------------------------------------------------
- *                 Constants for using application interrupts
- * --------------------------------------------------------------------------*/
-
-/* the structure used for the SET_CHDLC_INTERRUPT_TRIGGERS/READ_CHDLC_INTERRUPT_TRIGGERS command */
-typedef struct {
-       unsigned char CHDLC_interrupt_triggers PACKED;  /* CHDLC interrupt trigger configuration */
-       unsigned char IRQ PACKED;                       /* IRQ to be used */
-       unsigned short interrupt_timer PACKED;          /* interrupt timer */
-       unsigned short misc_interrupt_bits PACKED;      /* miscellaneous bits */
-} CHDLC_INT_TRIGGERS_STRUCT;
-
-/* 'CHDLC_interrupt_triggers' bit settings */
-#define APP_INT_ON_RX_FRAME            0x01    /* interrupt on Data frame reception */
-#define APP_INT_ON_TX_FRAME            0x02    /* interrupt when an Data frame may be transmitted */
-#define APP_INT_ON_COMMAND_COMPLETE    0x04    /* interrupt when an interface command is complete */
-#define APP_INT_ON_TIMER               0x08    /* interrupt on a defined millisecond timeout */
-#define APP_INT_ON_GLOBAL_EXCEP_COND   0x10    /* interrupt on a global exception condition */
-#define APP_INT_ON_CHDLC_EXCEP_COND    0x20    /* interrupt on an CHDLC exception condition */
-#define APP_INT_ON_TRACE_DATA_AVAIL    0x80    /* interrupt when trace data is available */
-
-/* interrupt types indicated at 'interrupt_type' byte of the INTERRUPT_INFORMATION_STRUCT */
-#define NO_APP_INTS_PEND               0x00    /* no interrups are pending */
-#define RX_APP_INT_PEND                        0x01    /* a receive interrupt is pending */
-#define TX_APP_INT_PEND                        0x02    /* a transmit interrupt is pending */
-#define COMMAND_COMPLETE_APP_INT_PEND  0x04    /* a 'command complete' interrupt is pending */
-#define TIMER_APP_INT_PEND             0x08    /* a timer interrupt is pending */
-#define GLOBAL_EXCEP_COND_APP_INT_PEND         0x10    /* a global exception condition interrupt is pending */
-#define CHDLC_EXCEP_COND_APP_INT_PEND  0x20    /* an CHDLC exception condition interrupt is pending */
-#define TRACE_DATA_AVAIL_APP_INT_PEND  0x80    /* a trace data available interrupt is pending */
-
-
-/* modem status changes */
-#define DCD_HIGH                       0x08
-#define CTS_HIGH                       0x20
-
-
-/* ----------------------------------------------------------------------------
- *                   Constants for Data frame transmission
- * --------------------------------------------------------------------------*/
-
-/* the Data frame transmit status element configuration structure */
-typedef struct {
-       unsigned short number_Tx_status_elements PACKED;        /* number of transmit status elements */
-       unsigned long base_addr_Tx_status_elements PACKED;      /* base address of the transmit element list */
-       unsigned long next_Tx_status_element_to_use PACKED;     /* pointer to the next transmit element to be used */
-} CHDLC_TX_STATUS_EL_CFG_STRUCT;
-
-/* the Data frame transmit status element structure */
-typedef struct {
-       unsigned char opp_flag PACKED;          /* opp flag */
-       unsigned short frame_length PACKED;     /* length of the frame to be transmitted */
-       unsigned char reserved_1 PACKED;        /* reserved for internal use */
-       unsigned long reserved_2 PACKED;        /* reserved for internal use */
-       unsigned long reserved_3 PACKED;        /* reserved for internal use */
-       unsigned long ptr_data_bfr PACKED;      /* pointer to the data area */
-} CHDLC_DATA_TX_STATUS_EL_STRUCT;
-
-
-
-/* ----------------------------------------------------------------------------
- *                   Constants for Data frame reception
- * --------------------------------------------------------------------------*/
-
-/* the Data frame receive status element configuration structure */
-typedef struct {
-       unsigned short number_Rx_status_elements PACKED;        /* number of receive status elements */
-       unsigned long base_addr_Rx_status_elements PACKED;      /* base address of the receive element list */
-       unsigned long next_Rx_status_element_to_use PACKED;     /* pointer to the next receive element to be used */
-       unsigned long base_addr_Rx_buffer PACKED;               /* base address of the receive data buffer */
-       unsigned long end_addr_Rx_buffer PACKED;                /* end address of the receive data buffer */
-} CHDLC_RX_STATUS_EL_CFG_STRUCT;
-
-/* the Data frame receive status element structure */
-typedef struct {
-       unsigned char opp_flag PACKED;          /* opp flag */
-       unsigned short frame_length PACKED;   /* length of the received frame */
-        unsigned char error_flag PACKED; /* frame errors (HDLC_STREAMING_MODE)*/
-        unsigned short time_stamp PACKED; /* receive time stamp (HDLC_STREAMING_MODE) */
-        unsigned long reserved_1 PACKED;       /* reserved for internal use */
-        unsigned short reserved_2 PACKED;      /* reserved for internal use */
-        unsigned long ptr_data_bfr PACKED;     /* pointer to the data area */
-} CHDLC_DATA_RX_STATUS_EL_STRUCT;
-
-
-
-/* ----------------------------------------------------------------------------
- *         Constants defining the shared memory information area
- * --------------------------------------------------------------------------*/
-
-/* the global information structure */
-typedef struct {
-       unsigned char global_status PACKED;             /* global status */
-       unsigned char modem_status PACKED;              /* current modem status */
-       unsigned char global_excep_conditions PACKED;   /* global exception conditions */
-       unsigned char glob_info_reserved[5] PACKED;     /* reserved */
-       unsigned char codename[4] PACKED;               /* Firmware name */
-       unsigned char codeversion[4] PACKED;            /* Firmware version */
-} GLOBAL_INFORMATION_STRUCT;
-
-/* the CHDLC information structure */
-typedef struct {
-       unsigned char CHDLC_status PACKED;              /* CHDLC status */
-       unsigned char CHDLC_excep_conditions PACKED;    /* CHDLC exception conditions */
-       unsigned char CHDLC_info_reserved[14] PACKED;   /* reserved */
-} CHDLC_INFORMATION_STRUCT;
-
-/* the interrupt information structure */
-typedef struct {
-       unsigned char interrupt_type PACKED;            /* type of interrupt triggered */
-       unsigned char interrupt_permission PACKED;      /* interrupt permission mask */
-       unsigned char int_info_reserved[14] PACKED;     /* reserved */
-} INTERRUPT_INFORMATION_STRUCT;
-
-/* the S508/FT1 information structure */
-typedef struct {
-       unsigned char parallel_port_A_input PACKED;     /* input - parallel port A */
-       unsigned char parallel_port_B_input PACKED;     /* input - parallel port B */
-       unsigned char FT1_info_reserved[14] PACKED;     /* reserved */
-} FT1_INFORMATION_STRUCT;
-
-/* the shared memory area information structure */
-typedef struct {
-       GLOBAL_INFORMATION_STRUCT global_info_struct PACKED;            /* the global information structure */
-       CHDLC_INFORMATION_STRUCT CHDLC_info_struct PACKED;              /* the CHDLC information structure */
-       INTERRUPT_INFORMATION_STRUCT interrupt_info_struct PACKED;      /* the interrupt information structure */
-       FT1_INFORMATION_STRUCT FT1_info_struct PACKED;                  /* the S508/FT1 information structure */
-} SHARED_MEMORY_INFO_STRUCT;
-
-/* ----------------------------------------------------------------------------
- *        UDP Management constants and structures 
- * --------------------------------------------------------------------------*/
-
-/* The embedded control block for UDP mgmt 
-   This is essentially a mailbox structure, without the large data field */
-
-typedef struct {
-        unsigned char  opp_flag PACKED;                  /* the opp flag */
-        unsigned char  command PACKED;                   /* the user command */
-        unsigned short buffer_length PACKED;             /* the data length */
-        unsigned char  return_code PACKED;               /* the return code */
-       unsigned char  MB_reserved[NUMBER_MB_RESERVED_BYTES] PACKED;    /* reserved for later */
-} cblock_t;
-
-
-/* UDP management packet layout (data area of ip packet) */
-/*
-typedef struct {
-       unsigned char           signature[8]    PACKED;
-       unsigned char           request_reply   PACKED;
-       unsigned char           id              PACKED;
-       unsigned char           reserved[6]     PACKED;
-       cblock_t                cblock          PACKED;
-       unsigned char           num_frames      PACKED;
-       unsigned char           ismoredata      PACKED;
-       unsigned char           data[SIZEOF_MB_DATA_BFR]        PACKED;
-} udp_management_packet_t;
-
-*/
-
-typedef struct {
-       unsigned char           num_frames      PACKED;
-       unsigned char           ismoredata      PACKED;
-} trace_info_t;
-
-typedef struct {
-       ip_pkt_t                ip_pkt          PACKED;
-       udp_pkt_t               udp_pkt         PACKED;
-       wp_mgmt_t               wp_mgmt         PACKED;
-       cblock_t                cblock          PACKED;
-       trace_info_t            trace_info      PACKED;
-       unsigned char           data[SIZEOF_MB_DATA_BFR]      PACKED;
-} chdlc_udp_pkt_t;
-
-typedef struct ft1_exec_cmd{
-       unsigned char  command PACKED;                   /* the user command */
-        unsigned short buffer_length PACKED;             /* the data length */
-        unsigned char  return_code PACKED;               /* the return code */
-       unsigned char  MB_reserved[NUMBER_MB_RESERVED_BYTES] PACKED;
-} ft1_exec_cmd_t;
-
-typedef struct {
-       unsigned char  opp_flag                         PACKED;
-       ft1_exec_cmd_t cmd                              PACKED;
-       unsigned char  data[SIZEOF_MB_DATA_BFR]         PACKED;
-} ft1_exec_t;
-
-#define UDPMGMT_SIGNATURE      "CTPIPEAB"
-
-
-/* UDP/IP packet (for UDP management) layout */
-/*
-typedef struct {
-       unsigned char   reserved[2]     PACKED;
-       unsigned short  ip_length       PACKED;
-       unsigned char   reserved2[4]    PACKED;
-       unsigned char   ip_ttl          PACKED;
-       unsigned char   ip_protocol     PACKED;
-       unsigned short  ip_checksum     PACKED;
-       unsigned long   ip_src_address  PACKED;
-       unsigned long   ip_dst_address  PACKED;
-       unsigned short  udp_src_port    PACKED;
-       unsigned short  udp_dst_port    PACKED;
-       unsigned short  udp_length      PACKED;
-       unsigned short  udp_checksum    PACKED;
-       udp_management_packet_t um_packet PACKED;
-} ip_packet_t;
-*/
-
-/* valid ip_protocol for UDP management */
-#define UDPMGMT_UDP_PROTOCOL 0x11
-
-
-typedef struct {
-       unsigned char   status          PACKED;
-       unsigned char   data_avail      PACKED;
-       unsigned short  real_length     PACKED;
-       unsigned short  time_stamp      PACKED;
-       unsigned char   data[1]         PACKED;
-} trace_pkt_t;
-
-typedef struct {
-       unsigned char   error_flag      PACKED;
-       unsigned short  time_stamp      PACKED;
-       unsigned char   reserved[13]    PACKED;
-} api_rx_hdr_t;
-
-typedef struct {
-        api_rx_hdr_t   api_rx_hdr      PACKED;
-        void *         data            PACKED;
-} api_rx_element_t;
-
-typedef struct {
-       unsigned char   attr            PACKED;
-       unsigned char   reserved[15]    PACKED;
-} api_tx_hdr_t;
-
-typedef struct {
-       api_tx_hdr_t    api_tx_hdr      PACKED;
-       void *          data            PACKED;
-} api_tx_element_t;
-
-/* ----------------------------------------------------------------------------
- *   Constants for the SET_FT1_CONFIGURATION/READ_FT1_CONFIGURATION command
- * --------------------------------------------------------------------------*/
-
-/* the FT1 configuration structure */
-typedef struct {
-       unsigned short framing_mode;
-       unsigned short encoding_mode;
-       unsigned short line_build_out;
-       unsigned short channel_base;
-       unsigned short baud_rate_kbps;                                  /* the baud rate (in kbps) */   
-       unsigned short clock_mode;
-} ft1_config_t;
-
-/* settings for the 'framing_mode' */
-#define ESF_FRAMING    0x00    /* ESF framing */
-#define D4_FRAMING     0x01    /* D4 framing */
-
-/* settings for the 'encoding_mode' */
-#define B8ZS_ENCODING  0x00    /* B8ZS encoding */
-#define AMI_ENCODING   0x01    /* AMI encoding */
-
-/* settings for the 'line_build_out' */
-#define LN_BLD_CSU_0dB_DSX1_0_to_133   0x00    /* set build out to CSU (0db) or DSX-1 (0-133ft) */
-#define LN_BLD_DSX1_133_to_266         0x01    /* set build out DSX-1 (133-266ft) */
-#define LN_BLD_DSX1_266_to_399         0x02    /* set build out DSX-1 (266-399ft) */
-#define LN_BLD_DSX1_399_to_533         0x03    /* set build out DSX-1 (399-533ft) */
-#define LN_BLD_DSX1_533_to_655         0x04    /* set build out DSX-1 (533-655ft) */
-#define LN_BLD_CSU_NEG_7dB             0x05    /* set build out to CSU (-7.5db) */
-#define LN_BLD_CSU_NEG_15dB            0x06    /* set build out to CSU (-15db) */
-#define LN_BLD_CSU_NEG_22dB            0x07    /* set build out to CSU (-22.5db) */
-
-/* settings for the 'channel_base' */
-#define MIN_CHANNEL_BASE_VALUE         1               /* the minimum permitted channel base value */
-#define MAX_CHANNEL_BASE_VALUE         24              /* the maximum permitted channel base value */
-
-/* settings for the 'baud_rate_kbps' */
-#define MIN_BAUD_RATE_KBPS             0               /* the minimum permitted baud rate (kbps) */
-#define MAX_BAUD_RATE_KBPS             1536    /* the maximum permitted baud rate (kbps) */
-#define BAUD_RATE_FT1_AUTO_CONFIG      0xFFFF /* the baud rate used to trigger an automatic FT1 configuration */
-
-/* settings for the 'clock_mode' */
-#define CLOCK_MODE_NORMAL              0x00    /* clock mode set to normal (slave) */
-#define CLOCK_MODE_MASTER              0x01    /* clock mode set to master */
-
-
-#define BAUD_RATE_FT1_AUTO_CONFIG      0xFFFF
-#define AUTO_FT1_CONFIG_NOT_COMPLETE   0x08
-#define AUTO_FT1_CFG_FAIL_OP_MODE      0x0C
-#define AUTO_FT1_CFG_FAIL_INVALID_LINE         0x0D
-
-#ifdef         _MSC_
-#  pragma      pack()
-#endif
-#endif /* _SDLA_CHDLC_H */
diff --git a/include/linux/sdla_ppp.h b/include/linux/sdla_ppp.h
deleted file mode 100644 (file)
index 6f39231..0000000
+++ /dev/null
@@ -1,575 +0,0 @@
-/*****************************************************************************
-* sdla_ppp.h   Sangoma PPP firmware API definitions.
-*
-* Author:      Nenad Corbic    <ncorbic@sangoma.com>
-*
-* Copyright:   (c) 1995-1997 Sangoma Technologies Inc.
-*
-*              This program is free software; you can redistribute it and/or
-*              modify it under the terms of the GNU General Public License
-*              as published by the Free Software Foundation; either version
-*              2 of the License, or (at your option) any later version.
-* ============================================================================
-* Feb 24, 2000  Nenad Corbic    v2.1.2
-* Jan 06, 1997 Gene Kozin      v2.0
-* Apr 11, 1996 Gene Kozin      Initial version.
-*****************************************************************************/
-#ifndef        _SDLA_PPP_H
-#define        _SDLA_PPP_H
-
-/*----------------------------------------------------------------------------
- * Notes:
- * ------
- * 1. All structures defined in this file are byte-alined.  
- *
- *     Compiler        Platform
- *     --------        --------
- *     GNU C           Linux           
- */
-
-#ifndef        PACKED
-#    define    PACKED  __attribute__((packed))
-#endif /* PACKED */
-
-/* Adapter memory layout and important constants */
-#define        PPP508_MB_VECT  0xE000  /* mailbox window vector */
-#define        PPP508_MB_OFFS  0               /* mailbox offset */
-#define        PPP508_FLG_OFFS 0x1000  /* status flags offset */
-#define        PPP508_BUF_OFFS 0x1100  /* buffer info block offset */
-#define PPP514_MB_OFFS  0xE000  /* mailbox offset */
-#define PPP514_FLG_OFFS 0xF000  /* status flags offset */
-#define PPP514_BUF_OFFS 0xF100  /* buffer info block offset */
-
-#define PPP_MAX_DATA   1008    /* command block data buffer length */
-
-/****** Data Structures *****************************************************/
-
-/*----------------------------------------------------------------------------
- * PPP Command Block.
- */
-typedef struct ppp_cmd{
-       unsigned char  command  PACKED; /* command code */
-       unsigned short length   PACKED; /* length of data buffer */
-       unsigned char  result   PACKED; /* return code */
-       unsigned char  rsrv[11] PACKED; /* reserved for future use */
-} ppp_cmd_t;
-
-typedef struct cblock{
-       unsigned char  opp_flag PACKED;
-       unsigned char  command  PACKED; /* command code */
-       unsigned short length   PACKED; /* length of data buffer */
-       unsigned char  result   PACKED; /* return code */
-       unsigned char  rsrv[11] PACKED; /* reserved for future use */
-} cblock_t;
-
-typedef struct ppp_udp_pkt{
-       ip_pkt_t        ip_pkt  PACKED;
-       udp_pkt_t       udp_pkt PACKED;
-       wp_mgmt_t       wp_mgmt PACKED;
-       cblock_t        cblock  PACKED;
-       unsigned char   data[MAX_LGTH_UDP_MGNT_PKT] PACKED;
-} ppp_udp_pkt_t;       
-
-typedef struct {
-       unsigned char   status          PACKED;
-       unsigned char   data_avail      PACKED;
-       unsigned short  real_length     PACKED;
-       unsigned short  time_stamp      PACKED;
-       unsigned char   data[1]         PACKED;
-} trace_pkt_t;
-
-
-typedef struct {
-       unsigned char   opp_flag        PACKED;
-       unsigned char   trace_type      PACKED;
-       unsigned short  trace_length    PACKED;
-       unsigned short  trace_data_ptr  PACKED;
-       unsigned short  trace_time_stamp PACKED;
-} trace_element_t;
-
-/* 'command' field defines */
-#define PPP_READ_CODE_VERSION  0x10    /* configuration commands */
-#define PPP_SET_CONFIG         0x05
-#define PPP_READ_CONFIG                0x06
-#define        PPP_SET_INTR_FLAGS      0x20
-#define        PPP_READ_INTR_FLAGS     0x21
-#define        PPP_SET_INBOUND_AUTH    0x30
-#define        PPP_SET_OUTBOUND_AUTH   0x31
-#define        PPP_GET_CONNECTION_INFO 0x32
-
-#define PPP_COMM_ENABLE                0x03    /* operational commands */
-#define PPP_COMM_DISABLE       0x04
-#define        PPP_SEND_SIGN_FRAME     0x23
-#define        PPP_READ_SIGN_RESPONSE  0x24
-#define        PPP_DATALINE_MONITOR    0x33
-
-#define PPP_READ_STATISTICS    0x07    /* statistics commands */
-#define PPP_FLUSH_STATISTICS   0x08
-#define PPP_READ_ERROR_STATS   0x09
-#define PPP_FLUSH_ERROR_STATS  0x0A
-#define PPP_READ_PACKET_STATS  0x12
-#define PPP_FLUSH_PACKET_STATS 0x13
-#define PPP_READ_LCP_STATS     0x14
-#define PPP_FLUSH_LCP_STATS    0x15
-#define PPP_READ_LPBK_STATS    0x16
-#define PPP_FLUSH_LPBK_STATS   0x17
-#define PPP_READ_IPCP_STATS    0x18
-#define PPP_FLUSH_IPCP_STATS   0x19
-#define PPP_READ_IPXCP_STATS   0x1A
-#define PPP_FLUSH_IPXCP_STATS  0x1B
-#define PPP_READ_PAP_STATS     0x1C
-#define PPP_FLUSH_PAP_STATS    0x1D
-#define PPP_READ_CHAP_STATS    0x1E
-#define PPP_FLUSH_CHAP_STATS   0x1F
-
-/* 'result' field defines */
-#define PPPRES_OK              0x00    /* command executed successfully */
-#define        PPPRES_INVALID_STATE    0x09    /* invalid command in this context */
-
-/*----------------------------------------------------------------------------
- * PPP Mailbox.
- *     This structure is located at offset PPP???_MB_OFFS into PPP???_MB_VECT
- */
-typedef struct ppp_mbox
-{
-       unsigned char flag      PACKED; /* 00h: command execution flag */
-       ppp_cmd_t     cmd       PACKED; /* 01h: command block */
-       unsigned char data[1]   PACKED; /* 10h: variable length data buffer */
-} ppp_mbox_t;
-
-/*----------------------------------------------------------------------------
- * PPP Status Flags.
- *     This structure is located at offset PPP???_FLG_OFFS into
- *     PPP???_MB_VECT.
- */
-typedef struct ppp_flags
-{
-       unsigned char iflag             PACKED; /* 00: interrupt flag */
-       unsigned char imask             PACKED; /* 01: interrupt mask */
-       unsigned char resrv             PACKED;
-       unsigned char mstatus           PACKED; /* 03: modem status */
-       unsigned char lcp_state         PACKED; /* 04: LCP state */
-       unsigned char ppp_phase         PACKED; /* 05: PPP phase */
-       unsigned char ip_state          PACKED; /* 06: IPCP state */
-       unsigned char ipx_state         PACKED; /* 07: IPXCP state */
-       unsigned char pap_state         PACKED; /* 08: PAP state */
-       unsigned char chap_state        PACKED; /* 09: CHAP state */
-       unsigned short disc_cause       PACKED; /* 0A: disconnection cause */
-} ppp_flags_t;
-
-/* 'iflag' defines */
-#define        PPP_INTR_RXRDY          0x01    /* Rx ready */
-#define        PPP_INTR_TXRDY          0x02    /* Tx ready */
-#define        PPP_INTR_MODEM          0x04    /* modem status change (DCD, CTS) */
-#define        PPP_INTR_CMD            0x08    /* interface command completed */
-#define        PPP_INTR_DISC           0x10    /* data link disconnected */
-#define        PPP_INTR_OPEN           0x20    /* data link open */
-#define        PPP_INTR_DROP_DTR       0x40    /* DTR drop timeout expired */
-#define PPP_INTR_TIMER          0x80    /* timer interrupt */
-
-
-/* 'mstatus' defines */
-#define        PPP_MDM_DCD             0x08    /* mdm_status: DCD */
-#define        PPP_MDM_CTS             0x20    /* mdm_status: CTS */
-
-/* 'disc_cause' defines */
-#define PPP_LOCAL_TERMINATION   0x0001 /* Local Request by PPP termination phase */
-#define PPP_DCD_CTS_DROP        0x0002  /* DCD and/or CTS dropped. Link down */
-#define PPP_REMOTE_TERMINATION 0x0800  /* Remote Request by PPP termination phase */
-
-/* 'misc_config_bits' defines */
-#define DONT_RE_TX_ABORTED_I_FRAMES    0x01
-#define TX_FRM_BYTE_COUNT_STATS         0x02
-#define RX_FRM_BYTE_COUNT_STATS         0x04
-#define TIME_STAMP_IN_RX_FRAMES         0x08
-#define NON_STD_ADPTR_FREQ              0x10
-#define INTERFACE_LEVEL_RS232           0x20
-#define AUTO_LINK_RECOVERY              0x100
-#define DONT_TERMINATE_LNK_MAX_CONFIG   0x200                    
-
-/* 'authentication options' defines */
-#define NO_AUTHENTICATION      0x00
-#define INBOUND_AUTH           0x80
-#define PAP_AUTH               0x01
-#define CHAP_AUTH              0x02            
-
-/* 'ip options' defines */
-#define L_AND_R_IP_NO_ASSIG    0x00
-#define L_IP_LOCAL_ASSIG       0x01
-#define L_IP_REMOTE_ASSIG      0x02
-#define R_IP_LOCAL_ASSIG        0x04
-#define R_IP_REMOTE_ASSIG       0x08
-#define ENABLE_IP              0x80
-
-/* 'ipx options' defines */
-#define ROUTING_PROT_DEFAULT    0x20
-#define ENABLE_IPX             0x80
-#define DISABLE_IPX            0x00
-
-/*----------------------------------------------------------------------------
- * PPP Buffer Info.
- *     This structure is located at offset PPP508_BUF_OFFS into
- *     PPP508_MB_VECT.
- */
-typedef struct ppp508_buf_info
-{
-       unsigned short txb_num  PACKED; /* 00: number of transmit buffers */
-       unsigned long  txb_ptr  PACKED; /* 02: pointer to the buffer ctl. */
-       unsigned long  txb_nxt  PACKED;
-       unsigned char  rsrv1[22] PACKED;
-       unsigned short rxb_num  PACKED; /* 20: number of receive buffers */
-       unsigned long  rxb_ptr  PACKED; /* 22: pointer to the buffer ctl. */
-       unsigned long  rxb1_ptr PACKED; /* 26: pointer to the first buf.ctl. */
-       unsigned long  rxb_base PACKED; /* 2A: pointer to the buffer base */
-       unsigned char  rsrv2[2] PACKED;
-       unsigned long  rxb_end  PACKED; /* 30: pointer to the buffer end */
-} ppp508_buf_info_t;
-
-/*----------------------------------------------------------------------------
- * Transmit/Receive Buffer Control Block.
- */
-typedef struct ppp_buf_ctl
-{
-       unsigned char  flag             PACKED; /* 00: 'buffer ready' flag */
-       unsigned short length           PACKED; /* 01: length of data */
-       unsigned char  reserved1[1]     PACKED; /* 03: */
-       unsigned char  proto            PACKED; /* 04: protocol */
-       unsigned short timestamp        PACKED; /* 05: time stamp (Rx only) */
-       unsigned char  reserved2[5]     PACKED; /* 07: */
-       union
-       {
-               unsigned short o_p[2];  /* 1C: buffer offset & page (S502) */
-               unsigned long  ptr;     /* 1C: buffer pointer (S508) */
-       } buf                           PACKED;
-} ppp_buf_ctl_t;
-
-/*----------------------------------------------------------------------------
- * S508 Adapter Configuration Block (passed to the PPP_SET_CONFIG command).
- */
-typedef struct ppp508_conf
-{
-       unsigned long  line_speed       PACKED; /* 00: baud rate, bps */
-       unsigned short txbuf_percent    PACKED; /* 04: % of Tx buffer */
-       unsigned short conf_flags       PACKED; /* 06: configuration bits */
-       unsigned short mtu_local        PACKED; /* 08: local MTU */
-       unsigned short mtu_remote       PACKED; /* 0A: remote MTU */
-       unsigned short restart_tmr      PACKED; /* 0C: restart timer */
-       unsigned short auth_rsrt_tmr    PACKED; /* 0E: authentication timer */
-       unsigned short auth_wait_tmr    PACKED; /* 10: authentication timer */
-       unsigned short mdm_fail_tmr     PACKED; /* 12: modem failure timer */
-       unsigned short dtr_drop_tmr     PACKED; /* 14: DTR drop timer */
-       unsigned short connect_tmout    PACKED; /* 16: connection timeout */
-       unsigned short conf_retry       PACKED; /* 18: max. retry */
-       unsigned short term_retry       PACKED; /* 1A: max. retry */
-       unsigned short fail_retry       PACKED; /* 1C: max. retry */
-       unsigned short auth_retry       PACKED; /* 1E: max. retry */
-       unsigned char  auth_options     PACKED; /* 20: authentication opt. */
-       unsigned char  ip_options       PACKED; /* 21: IP options */
-       unsigned long  ip_local         PACKED; /* 22: local IP address */
-       unsigned long  ip_remote        PACKED; /* 26: remote IP address */
-       unsigned char  ipx_options      PACKED; /* 2A: IPX options */
-       unsigned char  ipx_netno[4]     PACKED; /* 2B: IPX net number */
-       unsigned char  ipx_local[6]     PACKED; /* 2F: local IPX node number*/
-       unsigned char  ipx_remote[6]    PACKED; /* 35: remote IPX node num.*/
-       unsigned char  ipx_router[48]   PACKED; /* 3B: IPX router name*/
-       unsigned long  alt_cpu_clock    PACKED; /* 6B:  */
-} ppp508_conf_t;
-
-/*----------------------------------------------------------------------------
- * S508 Adapter Read Connection Information Block 
- *    Returned by the PPP_GET_CONNECTION_INFO command
- */
-typedef struct ppp508_connect_info
-{
-       unsigned short  mru             PACKED; /* 00-01 Remote Max Rec' Unit */
-       unsigned char   ip_options      PACKED; /* 02: Negotiated ip options  */
-       unsigned long   ip_local        PACKED; /* 03-06: local IP address    */
-       unsigned long   ip_remote       PACKED; /* 07-0A: remote IP address   */
-       unsigned char   ipx_options     PACKED; /* 0B: Negotiated ipx options */
-       unsigned char   ipx_netno[4]    PACKED; /* 0C-0F: IPX net number      */
-       unsigned char   ipx_local[6]    PACKED; /* 10-1F: local IPX node #    */
-       unsigned char   ipx_remote[6]   PACKED; /* 16-1B: remote IPX node #   */
-       unsigned char   ipx_router[48]  PACKED; /* 1C-4B: IPX router name     */
-       unsigned char   auth_status     PACKED; /* 4C: Authentication Status  */
-       unsigned char   inbd_auth_peerID[1] PACKED; /* 4D: variable length inbound authenticated peer ID */
-} ppp508_connect_info_t;
-
-/* 'line_speed' field */
-#define        PPP_BITRATE_1200        0x01
-#define        PPP_BITRATE_2400        0x02
-#define        PPP_BITRATE_4800        0x03
-#define        PPP_BITRATE_9600        0x04
-#define        PPP_BITRATE_19200       0x05
-#define        PPP_BITRATE_38400       0x06
-#define        PPP_BITRATE_45000       0x07
-#define        PPP_BITRATE_56000       0x08
-#define        PPP_BITRATE_64000       0x09
-#define        PPP_BITRATE_74000       0x0A
-#define        PPP_BITRATE_112000      0x0B
-#define        PPP_BITRATE_128000      0x0C
-#define        PPP_BITRATE_156000      0x0D
-
-/* Defines for the 'conf_flags' field */
-#define        PPP_IGNORE_TX_ABORT     0x01    /* don't re-transmit aborted frames */
-#define        PPP_ENABLE_TX_STATS     0x02    /* enable Tx statistics */
-#define        PPP_ENABLE_RX_STATS     0x04    /* enable Rx statistics */
-#define        PPP_ENABLE_TIMESTAMP    0x08    /* enable timestamp */
-
-/* 'ip_options' defines */
-#define        PPP_LOCAL_IP_LOCAL      0x01
-#define        PPP_LOCAL_IP_REMOTE     0x02
-#define        PPP_REMOTE_IP_LOCAL     0x04
-#define        PPP_REMOTE_IP_REMOTE    0x08
-
-/* 'ipx_options' defines */
-#define        PPP_REMOTE_IPX_NETNO    0x01
-#define        PPP_REMOTE_IPX_LOCAL    0x02
-#define        PPP_REMOTE_IPX_REMOTE   0x04
-#define        PPP_IPX_ROUTE_RIP_SAP   0x08
-#define        PPP_IPX_ROUTE_NLSP      0x10
-#define        PPP_IPX_ROUTE_DEFAULT   0x20
-#define        PPP_IPX_CONF_COMPLETE   0x40
-#define        PPP_IPX_ENABLE          0x80
-
-/*----------------------------------------------------------------------------
- * S508 Adapter Configuration Block (returned by the PPP_READ_CONFIG command).
- */
-typedef struct ppp508_get_conf
-{
-       unsigned long  bps      PACKED; /* 00: baud rate, bps */
-       ppp508_conf_t  conf     PACKED; /* 04: requested config. */
-       unsigned short txb_num  PACKED; /* 6F: number of Tx buffers */
-       unsigned short rxb_num  PACKED; /* 71: number of Rx buffers */
-} ppp508_get_conf_t;
-
-/*----------------------------------------------------------------------------
- * S508 Operational Statistics (returned by the PPP_READ_STATISTIC command).
- */
-typedef struct ppp508_stats
-{
-       unsigned short reserved1        PACKED; /* 00: */
-       unsigned short rx_bad_len       PACKED; /* 02: */
-       unsigned short reserved2        PACKED; /* 04: */
-       unsigned long  tx_frames        PACKED; /* 06: */
-       unsigned long  tx_bytes PACKED; /* 0A: */
-       unsigned long  rx_frames        PACKED; /* 0E: */
-       unsigned long  rx_bytes PACKED; /* 12: */
-} ppp508_stats_t;
-
-/*----------------------------------------------------------------------------
- * Adapter Error Statistics (returned by the PPP_READ_ERROR_STATS command).
- */
-typedef struct ppp_err_stats
-{
-       unsigned char    rx_overrun     PACKED; /* 00: Rx overrun errors */
-       unsigned char    rx_bad_crc     PACKED; /* 01: Rx CRC errors */
-       unsigned char    rx_abort       PACKED; /* 02: Rx aborted frames */
-       unsigned char    rx_lost        PACKED; /* 03: Rx frames lost */
-       unsigned char    tx_abort       PACKED; /* 04: Tx aborted frames */
-       unsigned char    tx_underrun    PACKED; /* 05: Tx underrun errors */
-       unsigned char    tx_missed_intr PACKED; /* 06: Tx underruns missed */
-       unsigned char    reserved       PACKED; /* 07: Tx underruns missed */
-       unsigned char    dcd_trans      PACKED; /* 08: DCD transitions */
-       unsigned char    cts_trans      PACKED; /* 09: CTS transitions */
-} ppp_err_stats_t;
-
-/*----------------------------------------------------------------------------
- * Packet Statistics (returned by the PPP_READ_PACKET_STATS command).
- */
-typedef struct ppp_pkt_stats
-{
-       unsigned short rx_bad_header    PACKED; /* 00: */
-       unsigned short rx_prot_unknwn   PACKED; /* 02: */
-       unsigned short rx_too_large     PACKED; /* 04: */
-       unsigned short rx_lcp           PACKED; /* 06: */
-       unsigned short tx_lcp           PACKED; /* 08: */
-       unsigned short rx_ipcp          PACKED; /* 0A: */
-       unsigned short tx_ipcp          PACKED; /* 0C: */
-       unsigned short rx_ipxcp         PACKED; /* 0E: */
-       unsigned short tx_ipxcp         PACKED; /* 10: */
-       unsigned short rx_pap           PACKED; /* 12: */
-       unsigned short tx_pap           PACKED; /* 14: */
-       unsigned short rx_chap          PACKED; /* 16: */
-       unsigned short tx_chap          PACKED; /* 18: */
-       unsigned short rx_lqr           PACKED; /* 1A: */
-       unsigned short tx_lqr           PACKED; /* 1C: */
-       unsigned short rx_ip            PACKED; /* 1E: */
-       unsigned short tx_ip            PACKED; /* 20: */
-       unsigned short rx_ipx           PACKED; /* 22: */
-       unsigned short tx_ipx           PACKED; /* 24: */
-} ppp_pkt_stats_t;
-
-/*----------------------------------------------------------------------------
- * LCP Statistics (returned by the PPP_READ_LCP_STATS command).
- */
-typedef struct ppp_lcp_stats
-{
-       unsigned short rx_unknown       PACKED; /* 00: unknown LCP type */
-       unsigned short rx_conf_rqst     PACKED; /* 02: Configure-Request */
-       unsigned short rx_conf_ack      PACKED; /* 04: Configure-Ack */
-       unsigned short rx_conf_nak      PACKED; /* 06: Configure-Nak */
-       unsigned short rx_conf_rej      PACKED; /* 08: Configure-Reject */
-       unsigned short rx_term_rqst     PACKED; /* 0A: Terminate-Request */
-       unsigned short rx_term_ack      PACKED; /* 0C: Terminate-Ack */
-       unsigned short rx_code_rej      PACKED; /* 0E: Code-Reject */
-       unsigned short rx_proto_rej     PACKED; /* 10: Protocol-Reject */
-       unsigned short rx_echo_rqst     PACKED; /* 12: Echo-Request */
-       unsigned short rx_echo_reply    PACKED; /* 14: Echo-Reply */
-       unsigned short rx_disc_rqst     PACKED; /* 16: Discard-Request */
-       unsigned short tx_conf_rqst     PACKED; /* 18: Configure-Request */
-       unsigned short tx_conf_ack      PACKED; /* 1A: Configure-Ack */
-       unsigned short tx_conf_nak      PACKED; /* 1C: Configure-Nak */
-       unsigned short tx_conf_rej      PACKED; /* 1E: Configure-Reject */
-       unsigned short tx_term_rqst     PACKED; /* 20: Terminate-Request */
-       unsigned short tx_term_ack      PACKED; /* 22: Terminate-Ack */
-       unsigned short tx_code_rej      PACKED; /* 24: Code-Reject */
-       unsigned short tx_proto_rej     PACKED; /* 26: Protocol-Reject */
-       unsigned short tx_echo_rqst     PACKED; /* 28: Echo-Request */
-       unsigned short tx_echo_reply    PACKED; /* 2A: Echo-Reply */
-       unsigned short tx_disc_rqst     PACKED; /* 2E: Discard-Request */
-       unsigned short rx_too_large     PACKED; /* 30: packets too large */
-       unsigned short rx_ack_inval     PACKED; /* 32: invalid Conf-Ack */
-       unsigned short rx_rej_inval     PACKED; /* 34: invalid Conf-Reject */
-       unsigned short rx_rej_badid     PACKED; /* 36: Conf-Reject w/bad ID */
-} ppp_lcp_stats_t;
-
-/*----------------------------------------------------------------------------
- * Loopback Error Statistics (returned by the PPP_READ_LPBK_STATS command).
- */
-typedef struct ppp_lpbk_stats
-{
-       unsigned short conf_magic       PACKED; /* 00:  */
-       unsigned short loc_echo_rqst    PACKED; /* 02:  */
-       unsigned short rem_echo_rqst    PACKED; /* 04:  */
-       unsigned short loc_echo_reply   PACKED; /* 06:  */
-       unsigned short rem_echo_reply   PACKED; /* 08:  */
-       unsigned short loc_disc_rqst    PACKED; /* 0A:  */
-       unsigned short rem_disc_rqst    PACKED; /* 0C:  */
-       unsigned short echo_tx_collsn   PACKED; /* 0E:  */
-       unsigned short echo_rx_collsn   PACKED; /* 10:  */
-} ppp_lpbk_stats_t;
-
-/*----------------------------------------------------------------------------
- * Protocol Statistics (returned by the PPP_READ_IPCP_STATS and
- * PPP_READ_IPXCP_STATS commands).
- */
-typedef struct ppp_prot_stats
-{
-       unsigned short rx_unknown       PACKED; /* 00: unknown type */
-       unsigned short rx_conf_rqst     PACKED; /* 02: Configure-Request */
-       unsigned short rx_conf_ack      PACKED; /* 04: Configure-Ack */
-       unsigned short rx_conf_nak      PACKED; /* 06: Configure-Nak */
-       unsigned short rx_conf_rej      PACKED; /* 08: Configure-Reject */
-       unsigned short rx_term_rqst     PACKED; /* 0A: Terminate-Request */
-       unsigned short rx_term_ack      PACKED; /* 0C: Terminate-Ack */
-       unsigned short rx_code_rej      PACKED; /* 0E: Code-Reject */
-       unsigned short reserved         PACKED; /* 10: */
-       unsigned short tx_conf_rqst     PACKED; /* 12: Configure-Request */
-       unsigned short tx_conf_ack      PACKED; /* 14: Configure-Ack */
-       unsigned short tx_conf_nak      PACKED; /* 16: Configure-Nak */
-       unsigned short tx_conf_rej      PACKED; /* 18: Configure-Reject */
-       unsigned short tx_term_rqst     PACKED; /* 1A: Terminate-Request */
-       unsigned short tx_term_ack      PACKED; /* 1C: Terminate-Ack */
-       unsigned short tx_code_rej      PACKED; /* 1E: Code-Reject */
-       unsigned short rx_too_large     PACKED; /* 20: packets too large */
-       unsigned short rx_ack_inval     PACKED; /* 22: invalid Conf-Ack */
-       unsigned short rx_rej_inval     PACKED; /* 24: invalid Conf-Reject */
-       unsigned short rx_rej_badid     PACKED; /* 26: Conf-Reject w/bad ID */
-} ppp_prot_stats_t;
-
-/*----------------------------------------------------------------------------
- * PAP Statistics (returned by the PPP_READ_PAP_STATS command).
- */
-typedef struct ppp_pap_stats
-{
-       unsigned short rx_unknown       PACKED; /* 00: unknown type */
-       unsigned short rx_auth_rqst     PACKED; /* 02: Authenticate-Request */
-       unsigned short rx_auth_ack      PACKED; /* 04: Authenticate-Ack */
-       unsigned short rx_auth_nak      PACKED; /* 06: Authenticate-Nak */
-       unsigned short reserved         PACKED; /* 08: */
-       unsigned short tx_auth_rqst     PACKED; /* 0A: Authenticate-Request */
-       unsigned short tx_auth_ack      PACKED; /* 0C: Authenticate-Ack */
-       unsigned short tx_auth_nak      PACKED; /* 0E: Authenticate-Nak */
-       unsigned short rx_too_large     PACKED; /* 10: packets too large */
-       unsigned short rx_bad_peerid    PACKED; /* 12: invalid peer ID */
-       unsigned short rx_bad_passwd    PACKED; /* 14: invalid password */
-} ppp_pap_stats_t;
-
-/*----------------------------------------------------------------------------
- * CHAP Statistics (returned by the PPP_READ_CHAP_STATS command).
- */
-typedef struct ppp_chap_stats
-{
-       unsigned short rx_unknown       PACKED; /* 00: unknown type */
-       unsigned short rx_challenge     PACKED; /* 02: Authenticate-Request */
-       unsigned short rx_response      PACKED; /* 04: Authenticate-Ack */
-       unsigned short rx_success       PACKED; /* 06: Authenticate-Nak */
-       unsigned short rx_failure       PACKED; /* 08: Authenticate-Nak */
-       unsigned short reserved         PACKED; /* 0A: */
-       unsigned short tx_challenge     PACKED; /* 0C: Authenticate-Request */
-       unsigned short tx_response      PACKED; /* 0E: Authenticate-Ack */
-       unsigned short tx_success       PACKED; /* 10: Authenticate-Nak */
-       unsigned short tx_failure       PACKED; /* 12: Authenticate-Nak */
-       unsigned short rx_too_large     PACKED; /* 14: packets too large */
-       unsigned short rx_bad_peerid    PACKED; /* 16: invalid peer ID */
-       unsigned short rx_bad_passwd    PACKED; /* 18: invalid password */
-       unsigned short rx_bad_md5       PACKED; /* 1A: invalid MD5 format */
-       unsigned short rx_bad_resp      PACKED; /* 1C: invalid response */
-} ppp_chap_stats_t;
-
-/*----------------------------------------------------------------------------
- * Connection Information (returned by the PPP_GET_CONNECTION_INFO command).
- */
-typedef struct ppp_conn_info
-{
-       unsigned short remote_mru       PACKED; /* 00:  */
-       unsigned char  ip_options       PACKED; /* 02:  */
-       unsigned char  ip_local[4]      PACKED; /* 03:  */
-       unsigned char  ip_remote[4]     PACKED; /* 07:  */
-       unsigned char  ipx_options      PACKED; /* 0B:  */
-       unsigned char  ipx_network[4]   PACKED; /* 0C:  */
-       unsigned char  ipx_local[6]     PACKED; /* 10:  */
-       unsigned char  ipx_remote[6]    PACKED; /* 16:  */
-       unsigned char  ipx_router[48]   PACKED; /* 1C:  */
-       unsigned char  auth_status      PACKED; /* 4C:  */
-       unsigned char  peer_id[0]       PACKED; /* 4D:  */
-} ppp_conn_info_t;
-
-/* Data structure for SET_TRIGGER_INTR command
- */
-
-typedef struct ppp_intr_info{
-       unsigned char  i_enable         PACKED; /* 0 Interrupt enable bits */
-       unsigned char  irq              PACKED; /* 1 Irq number */
-       unsigned short timer_len        PACKED; /* 2 Timer delay */
-} ppp_intr_info_t;
-
-
-#define FT1_MONITOR_STATUS_CTRL                         0x80
-#define SET_FT1_MODE                                    0x81
-
-
-
-/* Special UDP drivers management commands */
-#define PPIPE_ENABLE_TRACING                            0x20
-#define PPIPE_DISABLE_TRACING                           0x21
-#define PPIPE_GET_TRACE_INFO                            0x22
-#define PPIPE_GET_IBA_DATA                              0x23
-#define PPIPE_KILL_BOARD                               0x24
-#define PPIPE_FT1_READ_STATUS                           0x25
-#define PPIPE_DRIVER_STAT_IFSEND                        0x26
-#define PPIPE_DRIVER_STAT_INTR                          0x27
-#define PPIPE_DRIVER_STAT_GEN                           0x28
-#define PPIPE_FLUSH_DRIVER_STATS                        0x29
-#define PPIPE_ROUTER_UP_TIME                            0x30
-
-#define DISABLE_TRACING                                0x00
-#define TRACE_SIGNALLING_FRAMES                                0x01
-#define TRACE_DATA_FRAMES                              0x02
-
-
-
-#ifdef         _MSC_
-#  pragma      pack()
-#endif
-#endif /* _SDLA_PPP_H */
diff --git a/include/linux/sdla_x25.h b/include/linux/sdla_x25.h
deleted file mode 100644 (file)
index 57db980..0000000
+++ /dev/null
@@ -1,772 +0,0 @@
-/*****************************************************************************
-* sdla_x25.h   Sangoma X.25 firmware API definitions.
-*
-* Author:      Nenad Corbic    <ncorbic@sangoma.com>
-*
-* Copyright:   (c) 1995-2000 Sangoma Technologies Inc.
-*
-*              This program is free software; you can redistribute it and/or
-*              modify it under the terms of the GNU General Public License
-*              as published by the Free Software Foundation; either version
-               2 of the License, or (at your option) any later version.
-* ============================================================================
-* Feb 28, 2000  Nenad Corbic    Updated for socket based x25api
-* Dec 13, 1996 Gene Kozin      Initial version
-*****************************************************************************/
-#ifndef        _SDLA_X25_H
-#define        _SDLA_X25_H
-
-/*----------------------------------------------------------------------------
- * Notes:
- * ------
- * 1. All structures defined in this file are byte-alined.  
- *     Compiler        Platform        
- *     --------        --------
- *     GNU C           Linux
- *
- */
-
-#ifndef        PACKED
-#      define  PACKED  __attribute__((packed))
-#endif /* PACKED */
-
-/******        CONSTANTS DEFINITIONS ***********************************************/
-
-#define        X25_MAX_CHAN    255     /* max number of open X.25 circuits */
-#define        X25_MAX_DATA    1024    /* max length of X.25 data buffer */
-/*
- * X.25 shared memory layout.
- */
-#define        X25_MBOX_OFFS   0x16B0  /* general mailbox block */
-#define        X25_RXMBOX_OFFS 0x1AD0  /* receive mailbox */
-#define        X25_STATUS_OFFS 0x1EF0  /* X.25 status structure */
-#define X25_MB_VECTOR  0xE000  /* S514 mailbox window vecotr */
-#define X25_MISC_HDLC_BITS 0x1F00 /*X.25 miscallaneous HDLC bits */
-
-/* code levels */
-#define HDLC_LEVEL 0x01
-#define X25_LEVEL  0x02
-#define X25_AND_HDLC_LEVEL 0x03
-#define DO_HDLC_LEVEL_ERROR_CHECKING 0x04
-
-/****** DATA STRUCTURES *****************************************************/
-
-/*----------------------------------------------------------------------------
- * X.25 Command Block.
- */
-typedef struct X25Cmd
-{
-       unsigned char command   PACKED; /* command code */
-       unsigned short length   PACKED; /* transfer data length */
-       unsigned char result    PACKED; /* return code */
-       unsigned char pf        PACKED; /* P/F bit */
-       unsigned short lcn      PACKED; /* logical channel */
-       unsigned char qdm       PACKED; /* Q/D/M bits */
-       unsigned char cause     PACKED; /* cause field */
-       unsigned char diagn     PACKED; /* diagnostics */
-       unsigned char pktType   PACKED; /* packet type */
-       unsigned char resrv[4]  PACKED; /* reserved */
-} TX25Cmd;
-
-/*
- * Defines for the 'command' field.
- */
-/*----- General commands --------------*/
-#define X25_SET_GLOBAL_VARS    0x0B    /* set global variables */ 
-#define X25_READ_MODEM_STATUS  0x0C    /* read modem status */
-#define X25_READ_CODE_VERSION  0x15    /* read firmware version number */
-#define X25_TRACE_CONFIGURE    0x14    /* configure trace facility */
-#define X25_READ_TRACE_DATA    0x16    /* read trace data */
-#define        X25_SET_INTERRUPT_MODE  0x17    /* set interrupt generation mode */
-#define        X25_READ_INTERRUPT_MODE 0x18    /* read interrupt generation mode */
-/*----- HDLC-level commands -----------*/
-#define X25_HDLC_LINK_CONFIGURE        0x01    /* configure HDLC link level */   
-#define X25_HDLC_LINK_OPEN     0x02    /* open HDLC link */            
-#define X25_HDLC_LINK_CLOSE    0x03    /* close HDLC link */
-#define X25_HDLC_LINK_SETUP    0x04    /* set up HDLC link */ 
-#define X25_HDLC_LINK_DISC     0x05    /* disconnect DHLC link */
-#define X25_HDLC_LINK_STATUS   0x06    /* read DHLC link status */
-#define X25_HDLC_READ_STATS    0x07    /* read operational statistics */
-#define X25_HDLC_FLUSH_STATS   0x08    /* flush operational statistics */
-#define X25_HDLC_READ_COMM_ERR 0x09    /* read error statistics */
-#define X25_HDLC_FLUSH_COMM_ERR        0x0A    /* flush error statistics */
-#define X25_HDLC_FLUSH_BUFFERS 0x0D    /* flush HDLC-level data buffers */
-#define X25_HDLC_SPRVS_CNT_STAT 0x0F   /* read surervisory count status */
-#define X25_HDLC_SEND_UI_FRAME 0x10    /* send unnumbered information frame */
-#define X25_HDLC_WRITE         0x11    /* send HDLC information frame */
-#define X25_HDLC_READ          0x21    /* read HDLC information frame */
-#define X25_HDLC_READ_CONFIG   0x12    /* read HDLC configuration */
-#define X25_HDLC_SET_CONFIG    0x13    /* set HDLC configuration */
-#define SET_PROTOCOL_LEVEL     0x1F    /* set protocol level */
-/*----- X.25-level commands -----------*/
-#define X25_READ               0x22    /* read X.25 packet */
-#define X25_WRITE              0x23    /* send X.25 packet */
-#define X25_PLACE_CALL         0x30    /* place a call on SVC */
-#define X25_ACCEPT_CALL                0x31    /* accept incomming call */
-#define X25_CLEAR_CALL         0x32    /* clear call */
-#define X25_CLEAR_CONFRM       0x33    /* send clear confirmation packet */
-#define X25_RESET              0x34    /* send reset request packet */
-#define X25_RESET_CONFRM       0x35    /* send reset confirmation packet */
-#define X25_RESTART            0x36    /* send restart request packet */
-#define X25_RESTART_CONFRM     0x37    /* send restart confirmation packet */
-#define X25_INTERRUPT          0x38    /* send interrupt request packet */
-#define X25_INTERRUPT_CONFRM   0x39    /* send interrupt confirmation pkt */
-#define X25_REGISTRATION_RQST  0x3A    /* send registration request packet */
-#define X25_REGISTRATION_CONFRM        0x3B    /* send registration confirmation */
-#define X25_IS_DATA_AVAILABLE  0x40    /* querry receive queue */
-#define X25_INCOMMING_CALL_CTL 0x41    /* select incomming call options */
-#define X25_CONFIGURE_PVC      0x42    /* configure PVC */
-#define X25_GET_ACTIVE_CHANNELS        0x43    /* get a list of active circuits */
-#define X25_READ_CHANNEL_CONFIG        0x44    /* read virt. circuit configuration */
-#define X25_FLUSH_DATA_BUFFERS 0x45    /* flush X.25-level data buffers */
-#define X25_READ_HISTORY_TABLE 0x46    /* read asynchronous event log */
-#define X25_HISTORY_TABLE_CTL  0x47    /* control asynchronous event log */
-#define        X25_GET_TX_D_BIT_STATUS 0x48    /* is packet with D-bit acknowleged */
-#define        X25_READ_STATISTICS     0x49    /* read X.25-level statistics */
-#define        X25_FLUSH_STATISTICS    0x4A    /* flush X.25-level statistics */
-#define        X25_READ_CONFIGURATION  0x50    /* read HDLC & X.25 configuration */
-#define        X25_SET_CONFIGURATION   0x51    /* set HDLC & X.25 configuration */
-
-/*
- * Defines for the 'result' field.
- */
-/*----- General results ---------------*/
-#define X25RES_OK              0x00
-#define X25RES_ERROR           0x01
-#define X25RES_LINK_NOT_IN_ABM 0x02    /* link is not in ABM mode */
-#define X25RES_LINK_CLOSED     0x03
-#define X25RES_INVAL_LENGTH    0x04
-#define X25RES_INVAL_CMD       0x05
-#define X25RES_UNNUMBERED_FRAME        0x06    /* unnunbered frame received */
-#define X25RES_FRM_REJECT_MODE 0x07    /* link is in Frame Reject mode */
-#define X25RES_MODEM_FAILURE   0x08    /* DCD and/or CTS dropped */
-#define X25RES_N2_RETRY_LIMIT  0x09    /* N2 retry limit has been exceeded */
-#define X25RES_INVAL_LCN       0x30    /* invalid logical channel number */
-#define X25RES_INVAL_STATE     0x31    /* channel is not in data xfer mode */
-#define X25RES_INVAL_DATA_LEN  0x32    /* invalid data length */
-#define X25RES_NOT_READY       0x33    /* no data available / buffers full */
-#define X25RES_NETWORK_DOWN    0x34
-#define X25RES_CHANNEL_IN_USE  0x35    /* there is data queued on this LCN */
-#define X25RES_REGST_NOT_SUPPRT        0x36    /* registration not supported */
-#define X25RES_INVAL_FORMAT    0x37    /* invalid packet format */
-#define X25RES_D_BIT_NOT_SUPPRT        0x38    /* D-bit pragmatics not supported */
-#define X25RES_FACIL_NOT_SUPPRT        0x39    /* Call facility not supported */
-#define X25RES_INVAL_CALL_ARG  0x3A    /* errorneous call arguments */
-#define X25RES_INVAL_CALL_DATA 0x3B    /* errorneous call user data */
-#define X25RES_ASYNC_PACKET    0x40    /* asynchronous packet received */
-#define X25RES_PROTO_VIOLATION 0x41    /* protocol violation occurred */
-#define X25RES_PKT_TIMEOUT     0x42    /* X.25 packet time out */
-#define X25RES_PKT_RETRY_LIMIT 0x43    /* X.25 packet retry limit exceeded */
-/*----- Command-dependent results -----*/
-#define X25RES_LINK_DISC       0x00    /* HDLC_LINK_STATUS */
-#define X25RES_LINK_IN_ABM     0x01    /* HDLC_LINK_STATUS */
-#define X25RES_NO_DATA         0x01    /* HDLC_READ/READ_TRACE_DATA*/
-#define X25RES_TRACE_INACTIVE  0x02    /* READ_TRACE_DATA */
-#define X25RES_LINK_IS_OPEN    0x01    /* HDLC_LINK_OPEN */
-#define X25RES_LINK_IS_DISC    0x02    /* HDLC_LINK_DISC */
-#define X25RES_LINK_IS_CLOSED  0x03    /* HDLC_LINK_CLOSE */
-#define X25RES_INVAL_PARAM     0x31    /* INCOMMING_CALL_CTL */
-#define X25RES_INVAL_CONFIG    0x35    /* REGISTR_RQST/CONFRM */
-
-/*
- * Defines for the 'qdm_bits' field.
- */
-#define X25CMD_Q_BIT_MASK      0x04
-#define X25CMD_D_BIT_MASK      0x02
-#define X25CMD_M_BIT_MASK      0x01
-
-/*
- * Defines for the 'pkt_type' field.
- */
-/*----- Asynchronous events ------*/
-#define ASE_CLEAR_RQST         0x02
-#define ASE_RESET_RQST         0x04
-#define ASE_RESTART_RQST       0x08
-#define ASE_INTERRUPT          0x10
-#define ASE_DTE_REGISTR_RQST   0x20
-#define ASE_CALL_RQST          0x30
-#define ASE_CALL_ACCEPTED      0x31
-#define ASE_CLEAR_CONFRM       0x32
-#define ASE_RESET_CONFRM       0x33
-#define ASE_RESTART_CONFRM     0x34
-#define ASE_INTERRUPT_CONFRM   0x35
-#define ASE_DCE_REGISTR_CONFRM 0x36
-#define ASE_DIAGNOSTIC         0x37
-#define ASE_CALL_AUTO_CLEAR    0x38
-#define AUTO_RESPONSE_FLAG     0x80
-/*----- Time-Out events ----------*/
-#define TOE_RESTART_RQST       0x03
-#define TOE_CALL_RQST          0x05
-#define TOE_CLEAR_RQST         0x08
-#define TOE_RESET_RQST         0x0A
-/*----- Protocol Violation events */
-#define PVE_CLEAR_RQST         0x32
-#define PVE_RESET_RQST         0x33
-#define PVE_RESTART_RQST       0x34
-#define PVE_DIAGNOSTIC         0x37
-
-#define INTR_ON_RX_FRAME            0x01
-#define INTR_ON_TX_FRAME            0x02
-#define INTR_ON_MODEM_STATUS_CHANGE 0x04
-#define INTR_ON_COMMAND_COMPLETE    0x08
-#define INTR_ON_X25_ASY_TRANSACTION 0x10
-#define INTR_ON_TIMER              0x40
-#define DIRECT_RX_INTR_USAGE        0x80
-
-#define NO_INTR_PENDING                0x00
-#define RX_INTR_PENDING                        0x01    
-#define TX_INTR_PENDING                        0x02
-#define MODEM_INTR_PENDING             0x04
-#define COMMAND_COMPLETE_INTR_PENDING  0x08
-#define X25_ASY_TRANS_INTR_PENDING     0x10
-#define TIMER_INTR_PENDING             0x40
-
-/*----------------------------------------------------------------------------
- * X.25 Mailbox.
- *     This structure is located at offsets X25_MBOX_OFFS and X25_RXMBOX_OFFS
- *     into shared memory window.
- */
-typedef struct X25Mbox
-{
-       unsigned char opflag    PACKED; /* 00h: execution flag */
-       TX25Cmd cmd             PACKED; /* 01h: command block */
-       unsigned char data[1]   PACKED; /* 10h: data buffer */
-} TX25Mbox;
-
-/*----------------------------------------------------------------------------
- * X.25 Time Stamp Structure.
- */
-typedef struct X25TimeStamp
-{
-       unsigned char month     PACKED;
-       unsigned char date      PACKED;
-       unsigned char sec       PACKED;
-       unsigned char min       PACKED;
-       unsigned char hour      PACKED;
-} TX25TimeStamp;
-
-/*----------------------------------------------------------------------------
- * X.25 Status Block.
- *     This structure is located at offset X25_STATUS_OFF into shared memory
- *     window.
- */
-typedef struct X25Status
-{
-       unsigned short pvc_map  PACKED; /* 00h: PVC map */
-       unsigned short icc_map  PACKED; /* 02h: Incomming Chan. map */
-       unsigned short twc_map  PACKED; /* 04h: Two-way Cnan. map */
-       unsigned short ogc_map  PACKED; /* 06h: Outgoing Chan. map */
-       TX25TimeStamp tstamp    PACKED; /* 08h: timestamp (BCD) */
-       unsigned char iflags    PACKED; /* 0Dh: interrupt flags */
-       unsigned char imask     PACKED; /* 0Eh: interrupt mask  */
-       unsigned char resrv     PACKED; /* 0Eh: */
-       unsigned char gflags    PACKED; /* 10h: misc. HDLC/X25 flags */
-       unsigned char cflags[X25_MAX_CHAN] PACKED; /* channel status bytes */
-} TX25Status;
-
-/*
- * Bitmasks for the 'iflags' field.
- */
-#define X25_RX_INTR    0x01    /* receive interrupt */
-#define X25_TX_INTR    0x02    /* transmit interrupt */
-#define X25_MODEM_INTR 0x04    /* modem status interrupt (CTS/DCD) */
-#define X25_EVENT_INTR 0x10    /* asyncronous event encountered */
-#define X25_CMD_INTR   0x08    /* interface command complete */
-
-/*
- * Bitmasks for the 'gflags' field.
- */
-#define X25_HDLC_ABM   0x01    /* HDLC is in ABM mode */
-#define X25_RX_READY   0x02    /* X.25 data available */
-#define X25_TRACE_READY        0x08    /* trace data available */
-#define X25_EVENT_IND  0x20    /* asynchronous event indicator */
-#define X25_TX_READY   0x40    /* space is available in Tx buf.*/
-
-/*
- * Bitmasks for the 'cflags' field.
- */
-#define X25_XFER_MODE  0x80    /* channel is in data transfer mode */
-#define X25_TXWIN_OPEN 0x40    /* transmit window open */
-#define X25_RXBUF_MASK 0x3F    /* number of data buffers available */
-
-/*****************************************************************************
- * Following definitions structurize contents of the TX25Mbox.data field for
- * different X.25 interface commands.
- ****************************************************************************/
-
-/* ---------------------------------------------------------------------------
- * X25_SET_GLOBAL_VARS Command.
- */
-typedef struct X25GlobalVars
-{
-       unsigned char resrv     PACKED; /* 00h: reserved */
-       unsigned char dtrCtl    PACKED; /* 01h: DTR control code */
-       unsigned char resErr    PACKED; /* 01h: '1' - reset modem error */
-} TX25GlobalVars;
-
-/*
- * Defines for the 'dtrCtl' field.
- */
-#define X25_RAISE_DTR  0x01
-#define X25_DROP_DTR   0x02
-
-/* ---------------------------------------------------------------------------
- * X25_READ_MODEM_STATUS Command.
- */
-typedef struct X25ModemStatus
-{
-       unsigned char   status  PACKED;         /* 00h: modem status */
-} TX25ModemStatus;
-
-/*
- * Defines for the 'status' field.
- */
-#define X25_CTS_MASK   0x20
-#define X25_DCD_MASK   0x08
-
-/* ---------------------------------------------------------------------------
- * X25_HDLC_LINK_STATUS Command.
- */
-typedef struct X25LinkStatus
-{
-       unsigned char txQueued  PACKED; /* 00h: queued Tx I-frames*/
-       unsigned char rxQueued  PACKED; /* 01h: queued Rx I-frames*/
-       unsigned char station   PACKED; /* 02h: DTE/DCE config. */
-       unsigned char reserved  PACKED; /* 03h: reserved */
-       unsigned char sfTally   PACKED; /* 04h: supervisory frame tally */
-} TX25LinkStatus;
-
-/*
- * Defines for the 'station' field.
- */
-#define        X25_STATION_DTE 0x01    /* station configured as DTE */
-#define X25_STATION_DCE        0x02    /* station configured as DCE */
-
-/* ---------------------------------------------------------------------------
- * X25_HDLC_READ_STATS Command.
- */
-typedef struct HdlcStats
-{                                              /*      a number of ... */
-       unsigned short rxIFrames        PACKED; /* 00h: ready Rx I-frames */
-       unsigned short rxNoseq          PACKED; /* 02h: frms out-of-sequence */
-       unsigned short rxNodata         PACKED; /* 04h: I-frms without data */
-       unsigned short rxDiscarded      PACKED; /* 06h: discarded frames */
-       unsigned short rxTooLong        PACKED; /* 08h: frames too long */
-       unsigned short rxBadAddr        PACKED; /* 0Ah: frms with inval.addr*/
-       unsigned short txAcked          PACKED; /* 0Ch: acknowledged I-frms */
-       unsigned short txRetransm       PACKED; /* 0Eh: re-transmit. I-frms */
-       unsigned short t1Timeout        PACKED; /* 10h: T1 timeouts */
-       unsigned short rxSABM           PACKED; /* 12h: received SABM frames */
-       unsigned short rxDISC           PACKED; /* 14h: received DISC frames */
-       unsigned short rxDM             PACKED; /* 16h: received DM frames */
-       unsigned short rxFRMR           PACKED; /* 18h: FRMR frames received */
-       unsigned short txSABM           PACKED; /* 1Ah: transm. SABM frames*/
-       unsigned short txDISC           PACKED; /* 1Ch: transm. DISC frames*/
-       unsigned short txDM             PACKED; /* 1Eh: transm. DM frames */
-       unsigned short txFRMR           PACKED; /* 20h: transm. FRMR frames*/
-} THdlcStats;
-
-/* ---------------------------------------------------------------------------
- * X25_HDLC_READ_COMM_ERR Command.
- */
-typedef struct HdlcCommErr
-{                                              /*      a number of ... */
-       unsigned char rxOverrun         PACKED; /* 00h: Rx overrun errors */
-       unsigned char rxBadCrc          PACKED; /* 01h: Rx CRC errors */
-       unsigned char rxAborted         PACKED; /* 02h: Rx aborted frames */
-       unsigned char rxDropped         PACKED; /* 03h: frames lost */
-       unsigned char txAborted         PACKED; /* 04h: Tx aborted frames */
-       unsigned char txUnderrun        PACKED; /* 05h: Tx underrun errors */
-       unsigned char txMissIntr        PACKED; /* 06h: missed underrun ints */
-       unsigned char reserved          PACKED; /* 07h: reserved */
-       unsigned char droppedDCD        PACKED; /* 08h: times DCD dropped */
-       unsigned char droppedCTS        PACKED; /* 09h: times CTS dropped */
-} THdlcCommErr;
-
-/* ---------------------------------------------------------------------------
- * X25_SET_CONFIGURATION & X25_READ_CONFIGURATION Commands.
- */
-typedef struct X25Config
-{
-unsigned char baudRate         PACKED; /* 00h:  */
-       unsigned char t1                PACKED; /* 01h:  */
-       unsigned char t2                PACKED; /* 02h:  */
-       unsigned char n2                PACKED; /* 03h:  */
-       unsigned short hdlcMTU          PACKED; /* 04h:  */
-       unsigned char hdlcWindow        PACKED; /* 06h:  */
-       unsigned char t4                PACKED; /* 07h:  */
-       unsigned char autoModem         PACKED; /* 08h:  */
-       unsigned char autoHdlc          PACKED; /* 09h:  */
-       unsigned char hdlcOptions       PACKED; /* 0Ah:  */
-       unsigned char station           PACKED; /* 0Bh:  */
-       unsigned char pktWindow         PACKED; /* 0Ch:  */
-       unsigned short defPktSize       PACKED; /* 0Dh:  */
-       unsigned short pktMTU           PACKED; /* 0Fh:  */
-       unsigned short loPVC            PACKED; /* 11h:  */
-       unsigned short hiPVC            PACKED; /* 13h:  */
-       unsigned short loIncommingSVC   PACKED; /* 15h:  */
-       unsigned short hiIncommingSVC   PACKED; /* 17h:  */
-       unsigned short loTwoWaySVC      PACKED; /* 19h:  */
-       unsigned short hiTwoWaySVC      PACKED; /* 1Bh:  */
-       unsigned short loOutgoingSVC    PACKED; /* 1Dh:  */
-       unsigned short hiOutgoingSVC    PACKED; /* 1Fh:  */
-       unsigned short options          PACKED; /* 21h:  */
-       unsigned char responseOpt       PACKED; /* 23h:  */
-       unsigned short facil1           PACKED; /* 24h:  */
-       unsigned short facil2           PACKED; /* 26h:  */
-       unsigned short ccittFacil       PACKED; /* 28h:  */
-       unsigned short otherFacil       PACKED; /* 2Ah:  */
-       unsigned short ccittCompat      PACKED; /* 2Ch:  */
-       unsigned char t10t20            PACKED; /* 2Eh:  */
-       unsigned char t11t21            PACKED; /* 2Fh:  */
-       unsigned char t12t22            PACKED; /* 30h:  */
-       unsigned char t13t23            PACKED; /* 31h:  */
-       unsigned char t16t26            PACKED; /* 32H:  */
-       unsigned char t28               PACKED; /* 33h:  */
-       unsigned char r10r20            PACKED; /* 34h:  */
-       unsigned char r12r22            PACKED; /* 35h:  */
-       unsigned char r13r23            PACKED; /* 36h:  */
-} TX25Config;
-
-/* ---------------------------------------------------------------------------
- * X25_READ_CHANNEL_CONFIG Command.
- */
-typedef struct X25ChanAlloc                    /*----- Channel allocation -*/
-{
-       unsigned short loPVC            PACKED; /* 00h: lowest PVC number */
-       unsigned short hiPVC            PACKED; /* 02h: highest PVC number */
-       unsigned short loIncommingSVC   PACKED; /* 04h: lowest incoming SVC */
-       unsigned short hiIncommingSVC   PACKED; /* 06h: highest incoming SVC */
-       unsigned short loTwoWaySVC      PACKED; /* 08h: lowest two-way SVC */
-       unsigned short hiTwoWaySVC      PACKED; /* 0Ah: highest two-way SVC */
-       unsigned short loOutgoingSVC    PACKED; /* 0Ch: lowest outgoing SVC */
-       unsigned short hiOutgoingSVC    PACKED; /* 0Eh: highest outgoing SVC */
-} TX25ChanAlloc;
-
-typedef struct X25ChanCfg              /*------ Channel configuration -----*/
-{
-       unsigned char type      PACKED; /* 00h: channel type */
-       unsigned char txConf    PACKED; /* 01h: Tx packet and window sizes */
-       unsigned char rxConf    PACKED; /* 01h: Rx packet and window sizes */
-} TX25ChanCfg;
-
-/*
- * Defines for the 'type' field.
- */
-#define        X25_PVC         0x01    /* PVC */
-#define        X25_SVC_IN      0x03    /* Incoming SVC */
-#define        X25_SVC_TWOWAY  0x07    /* Two-way SVC */
-#define        X25_SVC_OUT     0x0B    /* Outgoing SVC */
-
-/*----------------------------------------------------------------------------
- * X25_READ_STATISTICS Command.
- */
-typedef struct X25Stats
-{                                              /* number of packets Tx/Rx'ed */
-       unsigned short txRestartRqst    PACKED; /* 00h: Restart Request */
-       unsigned short rxRestartRqst    PACKED; /* 02h: Restart Request */
-       unsigned short txRestartConf    PACKED; /* 04h: Restart Confirmation */
-       unsigned short rxRestartConf    PACKED; /* 06h: Restart Confirmation */
-       unsigned short txResetRqst      PACKED; /* 08h: Reset Request */
-       unsigned short rxResetRqst      PACKED; /* 0Ah: Reset Request */
-       unsigned short txResetConf      PACKED; /* 0Ch: Reset Confirmation */
-       unsigned short rxResetConf      PACKED; /* 0Eh: Reset Confirmation */
-       unsigned short txCallRequest    PACKED; /* 10h: Call Request */
-       unsigned short rxCallRequest    PACKED; /* 12h: Call Request */
-       unsigned short txCallAccept     PACKED; /* 14h: Call Accept */
-       unsigned short rxCallAccept     PACKED; /* 16h: Call Accept */
-       unsigned short txClearRqst      PACKED; /* 18h: Clear Request */
-       unsigned short rxClearRqst      PACKED; /* 1Ah: Clear Request */
-       unsigned short txClearConf      PACKED; /* 1Ch: Clear Confirmation */
-       unsigned short rxClearConf      PACKED; /* 1Eh: Clear Confirmation */
-       unsigned short txDiagnostic     PACKED; /* 20h: Diagnostic */
-       unsigned short rxDiagnostic     PACKED; /* 22h: Diagnostic */
-       unsigned short txRegRqst        PACKED; /* 24h: Registration Request */
-       unsigned short rxRegRqst        PACKED; /* 26h: Registration Request */
-       unsigned short txRegConf        PACKED; /* 28h: Registration Confirm.*/
-       unsigned short rxRegConf        PACKED; /* 2Ah: Registration Confirm.*/
-       unsigned short txInterrupt      PACKED; /* 2Ch: Interrupt */
-       unsigned short rxInterrupt      PACKED; /* 2Eh: Interrupt */
-       unsigned short txIntrConf       PACKED; /* 30h: Interrupt Confirm. */
-       unsigned short rxIntrConf       PACKED; /* 32h: Interrupt Confirm. */
-       unsigned short txData           PACKED; /* 34h: Data */
-       unsigned short rxData           PACKED; /* 36h: Data */
-       unsigned short txRR             PACKED; /* 38h: RR */
-       unsigned short rxRR             PACKED; /* 3Ah: RR */
-       unsigned short txRNR            PACKED; /* 3Ch: RNR */
-       unsigned short rxRNR            PACKED; /* 3Eh: RNR */
-} TX25Stats;
-
-/*----------------------------------------------------------------------------
- * X25_READ_HISTORY_TABLE Command.
- */
-typedef struct X25EventLog
-{
-       unsigned char   type    PACKED; /* 00h: transaction type */
-       unsigned short  lcn     PACKED; /* 01h: logical channel num */
-       unsigned char   packet  PACKED; /* 03h: async packet type */
-       unsigned char   cause   PACKED; /* 04h: X.25 cause field */
-       unsigned char   diag    PACKED; /* 05h: X.25 diag field */
-       TX25TimeStamp   ts      PACKED; /* 06h: time stamp */
-} TX25EventLog;
-
-/*
- * Defines for the 'type' field.
- */
-#define X25LOG_INCOMMING       0x00
-#define X25LOG_APPLICATION     0x01
-#define X25LOG_AUTOMATIC       0x02
-#define X25LOG_ERROR           0x04
-#define X25LOG_TIMEOUT         0x08
-#define X25LOG_RECOVERY                0x10
-
-/*
- * Defines for the 'packet' field.
- */
-#define X25LOG_CALL_RQST       0x0B
-#define X25LOG_CALL_ACCEPTED   0x0F
-#define X25LOG_CLEAR_RQST      0x13
-#define X25LOG_CLEAR_CONFRM    0x17
-#define X25LOG_RESET_RQST      0x1B
-#define X25LOG_RESET_CONFRM    0x1F
-#define X25LOG_RESTART_RQST    0xFB
-#define X25LOG_RESTART_COMFRM  0xFF
-#define X25LOG_DIAGNOSTIC      0xF1
-#define X25LOG_DTE_REG_RQST    0xF3
-#define X25LOG_DTE_REG_COMFRM  0xF7
-
-/* ---------------------------------------------------------------------------
- * X25_TRACE_CONFIGURE Command.
- */
-typedef struct X25TraceCfg
-{
-       unsigned char flags     PACKED; /* 00h: trace configuration flags */
-       unsigned char timeout   PACKED; /* 01h: timeout for trace delay mode*/
-} TX25TraceCfg;
-
-/*
- * Defines for the 'flags' field.
- */
-#define X25_TRC_ENABLE         0x01    /* bit0: '1' - trace enabled */
-#define X25_TRC_TIMESTAMP      0x02    /* bit1: '1' - time stamping enabled*/
-#define X25_TRC_DELAY          0x04    /* bit2: '1' - trace delay enabled */
-#define X25_TRC_DATA           0x08    /* bit3: '1' - trace data packets */
-#define X25_TRC_SUPERVISORY    0x10    /* bit4: '1' - trace suprvisory pkts*/
-#define X25_TRC_ASYNCHRONOUS   0x20    /* bit5: '1' - trace asynch. packets*/
-#define X25_TRC_HDLC           0x40    /* bit6: '1' - trace all packets */
-#define X25_TRC_READ           0x80    /* bit7: '1' - get current config. */
-
-/* ---------------------------------------------------------------------------
- * X25_READ_TRACE_DATA Command.
- */
-typedef struct X25Trace                        /*----- Trace data structure -------*/
-{
-       unsigned short length   PACKED; /* 00h: trace data length */
-       unsigned char type      PACKED; /* 02h: trace type */
-       unsigned char lost_cnt  PACKED; /* 03h: N of traces lost */
-       TX25TimeStamp tstamp    PACKED; /* 04h: mon/date/sec/min/hour */
-       unsigned short millisec PACKED; /* 09h: ms time stamp */
-       unsigned char data[0]   PACKED; /* 0Bh: traced frame */
-} TX25Trace;
-
-/*
- * Defines for the 'type' field.
- */
-#define X25_TRC_TYPE_MASK      0x0F    /* bits 0..3: trace type */
-#define X25_TRC_TYPE_RX_FRAME  0x00    /* received frame trace */
-#define X25_TRC_TYPE_TX_FRAME  0x01    /* transmitted frame */
-#define X25_TRC_TYPE_ERR_FRAME 0x02    /* error frame */
-
-#define X25_TRC_ERROR_MASK     0xF0    /* bits 4..7: error code */
-#define X25_TRCERR_RX_ABORT    0x10    /* receive abort error */
-#define X25_TRCERR_RX_BADCRC   0x20    /* receive CRC error */
-#define X25_TRCERR_RX_OVERRUN  0x30    /* receiver overrun error */
-#define X25_TRCERR_RX_TOO_LONG 0x40    /* excessive frame length error */
-#define X25_TRCERR_TX_ABORT    0x70    /* aborted frame transmittion error */
-#define X25_TRCERR_TX_UNDERRUN 0x80    /* transmit underrun error */
-
-/*****************************************************************************
- * Following definitions describe HDLC frame and X.25 packet formats.
- ****************************************************************************/
-
-typedef struct HDLCFrame               /*----- DHLC Frame Format ----------*/
-{
-       unsigned char addr      PACKED; /* address field */
-       unsigned char cntl      PACKED; /* control field */
-       unsigned char data[0]   PACKED;
-} THDLCFrame;
-
-typedef struct X25Pkt                  /*----- X.25 Paket Format ----------*/
-{
-       unsigned char lcn_hi    PACKED; /* 4 MSB of Logical Channel Number */
-       unsigned char lcn_lo    PACKED; /* 8 LSB of Logical Channel Number */
-       unsigned char type      PACKED;
-       unsigned char data[0]   PACKED;
-} TX25Pkt;
-
-/*
- * Defines for the 'lcn_hi' field.
- */
-#define        X25_Q_BIT_MASK          0x80    /* Data Qualifier Bit mask */
-#define        X25_D_BIT_MASK          0x40    /* Delivery Confirmation Bit mask */
-#define        X25_M_BITS_MASK         0x30    /* Modulo Bits mask */
-#define        X25_LCN_MSB_MASK        0x0F    /* LCN most significant bits mask */
-
-/*
- * Defines for the 'type' field.
- */
-#define        X25PKT_DATA             0x01    /* Data packet mask */
-#define        X25PKT_SUPERVISORY      0x02    /* Supervisory packet mask */
-#define        X25PKT_CALL_RQST        0x0B    /* Call Request/Incoming */
-#define        X25PKT_CALL_ACCEPTED    0x0F    /* Call Accepted/Connected */
-#define        X25PKT_CLEAR_RQST       0x13    /* Clear Request/Indication */
-#define        X25PKT_CLEAR_CONFRM     0x17    /* Clear Confirmation */
-#define        X25PKT_RESET_RQST       0x1B    /* Reset Request/Indication */
-#define        X25PKT_RESET_CONFRM     0x1F    /* Reset Confirmation */
-#define        X25PKT_RESTART_RQST     0xFB    /* Restart Request/Indication */
-#define        X25PKT_RESTART_CONFRM   0xFF    /* Restart Confirmation */
-#define        X25PKT_INTERRUPT        0x23    /* Interrupt */
-#define        X25PKT_INTERRUPT_CONFRM 0x27    /* Interrupt Confirmation */
-#define        X25PKT_DIAGNOSTIC       0xF1    /* Diagnostic */
-#define        X25PKT_REGISTR_RQST     0xF3    /* Registration Request */
-#define        X25PKT_REGISTR_CONFRM   0xF7    /* Registration Confirmation */
-#define        X25PKT_RR_MASKED        0x01    /* Receive Ready packet after masking */
-#define        X25PKT_RNR_MASKED       0x05    /* Receive Not Ready after masking  */
-
-
-typedef struct {
-       TX25Cmd cmd             PACKED;
-       char data[X25_MAX_DATA] PACKED;
-} mbox_cmd_t;
-
-
-typedef struct {
-       unsigned char  qdm      PACKED; /* Q/D/M bits */
-       unsigned char  cause    PACKED; /* cause field */
-       unsigned char  diagn    PACKED; /* diagnostics */
-       unsigned char  pktType  PACKED;
-       unsigned short length   PACKED;
-       unsigned char  result   PACKED;
-       unsigned short lcn      PACKED;
-       char reserved[7]        PACKED;
-}x25api_hdr_t;
-
-
-typedef struct {
-       x25api_hdr_t hdr        PACKED;
-       char data[X25_MAX_DATA] PACKED;
-}x25api_t;
-
-
-/* 
- * XPIPEMON Definitions
- */
-
-/* valid ip_protocol for UDP management */
-#define UDPMGMT_UDP_PROTOCOL 0x11
-#define UDPMGMT_XPIPE_SIGNATURE         "XLINK8ND"
-#define UDPMGMT_DRVRSTATS_SIGNATURE     "DRVSTATS"
-
-/* values for request/reply byte */
-#define UDPMGMT_REQUEST        0x01
-#define UDPMGMT_REPLY  0x02
-#define UDP_OFFSET     12
-
-
-typedef struct {
-       unsigned char opp_flag  PACKED; /* the opp flag */
-       unsigned char command   PACKED; /* command code */
-       unsigned short length   PACKED; /* transfer data length */
-       unsigned char result    PACKED; /* return code */
-       unsigned char pf        PACKED; /* P/F bit */
-       unsigned short lcn      PACKED; /* logical channel */
-       unsigned char qdm       PACKED; /* Q/D/M bits */
-       unsigned char cause     PACKED; /* cause field */
-       unsigned char diagn     PACKED; /* diagnostics */
-       unsigned char pktType   PACKED; /* packet type */
-       unsigned char resrv[4]  PACKED; /* reserved */
-} cblock_t;
-
-typedef struct {
-       ip_pkt_t                ip_pkt          PACKED;
-       udp_pkt_t               udp_pkt         PACKED;
-       wp_mgmt_t               wp_mgmt         PACKED;
-        cblock_t                cblock          PACKED;
-        unsigned char           data[4080]      PACKED;
-} x25_udp_pkt_t;
-
-
-typedef struct read_hdlc_stat {
-       unsigned short inf_frames_rx_ok PACKED;
-        unsigned short inf_frames_rx_out_of_seq PACKED;
-       unsigned short inf_frames_rx_no_data PACKED;
-       unsigned short inf_frames_rx_dropped PACKED;
-       unsigned short inf_frames_rx_data_too_long PACKED;
-       unsigned short inf_frames_rx_invalid_addr PACKED;
-       unsigned short inf_frames_tx_ok PACKED;
-        unsigned short inf_frames_tx_retransmit PACKED;
-               unsigned short T1_timeouts PACKED;
-       unsigned short SABM_frames_rx PACKED;
-       unsigned short DISC_frames_rx PACKED;
-       unsigned short DM_frames_rx PACKED;
-       unsigned short FRMR_frames_rx PACKED;
-       unsigned short SABM_frames_tx PACKED;
-       unsigned short DISC_frames_tx PACKED;
-       unsigned short DM_frames_tx PACKED;
-       unsigned short FRMR_frames_tx PACKED;
-} read_hdlc_stat_t;
-
-typedef struct read_comms_err_stats{
-       unsigned char overrun_err_rx PACKED;
-       unsigned char CRC_err PACKED;
-       unsigned char abort_frames_rx PACKED;
-       unsigned char frames_dropped_buf_full PACKED;
-       unsigned char abort_frames_tx PACKED;
-       unsigned char transmit_underruns PACKED;
-       unsigned char missed_tx_underruns_intr PACKED;
-       unsigned char reserved PACKED;
-       unsigned char DCD_drop PACKED;
-       unsigned char CTS_drop PACKED;
-} read_comms_err_stats_t;
-
-typedef struct trace_data {
-       unsigned short length PACKED;
-       unsigned char  type PACKED;
-       unsigned char  trace_dropped PACKED;
-       unsigned char  reserved[5] PACKED;
-       unsigned short timestamp PACKED;
-        unsigned char  data PACKED;
-} trace_data_t;
-
-enum {UDP_XPIPE_TYPE};
-
-#define XPIPE_ENABLE_TRACING                    0x14
-#define XPIPE_DISABLE_TRACING                   0x14
-#define XPIPE_GET_TRACE_INFO                    0x16
-#define XPIPE_FT1_READ_STATUS                   0x74
-#define XPIPE_DRIVER_STAT_IFSEND                0x75
-#define XPIPE_DRIVER_STAT_INTR                  0x76
-#define XPIPE_DRIVER_STAT_GEN                   0x77
-#define XPIPE_FLUSH_DRIVER_STATS                0x78
-#define XPIPE_ROUTER_UP_TIME                    0x79        
-#define XPIPE_SET_FT1_MODE                     0x81
-#define XPIPE_FT1_STATUS_CTRL                  0x80
-
-
-/* error messages */
-#define NO_BUFFS_OR_CLOSED_WIN  0x33
-#define DATA_LENGTH_TOO_BIG     0x32
-#define NO_DATA_AVAILABLE       0x33
-#define Z80_TIMEOUT_ERROR       0x0a   
-#define        NO_BUFFS                0x08
-
-
-/* Trace options */
-#define TRACE_DEFAULT          0x03
-#define TRACE_SUPERVISOR_FRMS  0x10
-#define TRACE_ASYNC_FRMS       0x20
-#define TRACE_ALL_HDLC_FRMS    0x40
-#define TRACE_DATA_FRMS                0x08
-
-
-#endif /* _SDLA_X25_H */
diff --git a/include/linux/sdladrv.h b/include/linux/sdladrv.h
deleted file mode 100644 (file)
index c85e103..0000000
+++ /dev/null
@@ -1,66 +0,0 @@
-/*****************************************************************************
-* sdladrv.h    SDLA Support Module.  Kernel API Definitions.
-*
-* Author:      Gideon Hack     
-*
-* Copyright:   (c) 1995-2000 Sangoma Technologies Inc.
-*
-*              This program is free software; you can redistribute it and/or
-*              modify it under the terms of the GNU General Public License
-*              as published by the Free Software Foundation; either version
-*              2 of the License, or (at your option) any later version.
-* ============================================================================
-* Jun 02, 1999         Gideon Hack     Added support for the S514 PCI adapter.
-* Dec 11, 1996 Gene Kozin      Complete overhaul.
-* Oct 17, 1996 Gene Kozin      Minor bug fixes.
-* Jun 12, 1996 Gene Kozin      Added support for S503 card.
-* Dec 06, 1995 Gene Kozin      Initial version.
-*****************************************************************************/
-#ifndef        _SDLADRV_H
-#define        _SDLADRV_H
-
-
-#define        SDLA_MAXIORANGE 4       /* maximum I/O port range */
-#define        SDLA_WINDOWSIZE 0x2000  /* default dual-port memory window size */
-/****** Data Structures *****************************************************/
-
-/*----------------------------------------------------------------------------
- * Adapter hardware configuration. Pointer to this structure is passed to all
- * APIs.
- */
-typedef struct sdlahw
-{
-       unsigned type;                  /* adapter type */
-       unsigned fwid;                  /* firmware ID */
-       unsigned port;                  /* adapter I/O port base */
-       int irq;                        /* interrupt request level */
-       char S514_cpu_no[1];            /* PCI CPU Number */
-       unsigned char S514_slot_no;     /* PCI Slot Number */
-       char auto_pci_cfg;              /* Autodetect PCI Slot */
-       struct pci_dev *pci_dev;        /* PCI device */
-       void * dpmbase;                 /* dual-port memory base */
-       unsigned dpmsize;               /* dual-port memory size */
-       unsigned pclk;                  /* CPU clock rate, kHz */
-       unsigned long memory;           /* memory size */
-       unsigned long vector;           /* local offset of the DPM window */
-       unsigned io_range;              /* I/O port range */
-       unsigned char regs[SDLA_MAXIORANGE]; /* was written to registers */
-       unsigned reserved[5];
-} sdlahw_t;
-
-/****** Function Prototypes *************************************************/
-
-extern int sdla_setup  (sdlahw_t* hw, void* sfm, unsigned len);
-extern int sdla_down   (sdlahw_t* hw);
-extern void S514_intack  (sdlahw_t* hw, u32 int_status);
-extern void read_S514_int_stat (sdlahw_t* hw, u32* int_status);
-extern int sdla_mapmem (sdlahw_t* hw, unsigned long addr);
-extern int sdla_peek   (sdlahw_t* hw, unsigned long addr, void* buf,
-                        unsigned len);
-extern int sdla_poke   (sdlahw_t* hw, unsigned long addr, void* buf,
-                        unsigned len);
-extern int sdla_exec   (void* opflag);
-
-extern unsigned wanpipe_hw_probe(void);
-
-#endif /* _SDLADRV_H */
diff --git a/include/linux/sdlapci.h b/include/linux/sdlapci.h
deleted file mode 100644 (file)
index 6f7c904..0000000
+++ /dev/null
@@ -1,72 +0,0 @@
-/*****************************************************************************
-* sdlapci.h    WANPIPE(tm) Multiprotocol WAN Link Driver.
-*              Definitions for the SDLA PCI adapter.
-*
-* Author:      Gideon Hack     <ghack@sangoma.com>
-*
-* Copyright:   (c) 1999-2000 Sangoma Technologies Inc.
-*
-*              This program is free software; you can redistribute it and/or
-*              modify it under the terms of the GNU General Public License
-*              as published by the Free Software Foundation; either version
-*              2 of the License, or (at your option) any later version.
-* ============================================================================
-* Jun 02, 1999 Gideon Hack     Initial version.
-*****************************************************************************/
-#ifndef        _SDLAPCI_H
-#define        _SDLAPCI_H
-
-/****** Defines *************************************************************/
-
-/* Definitions for identifying and finding S514 PCI adapters */
-#define V3_VENDOR_ID           0x11B0          /* V3 vendor ID number */
-#define V3_DEVICE_ID           0x0002          /* V3 device ID number */
-#define SANGOMA_SUBSYS_VENDOR  0x4753          /* ID for Sangoma */
-#define PCI_DEV_SLOT_MASK      0x1F            /* mask for slot numbering */
-#define PCI_IRQ_NOT_ALLOCATED  0xFF            /* interrupt line for no IRQ */
-
-/* Local PCI register offsets */ 
-#define PCI_VENDOR_ID_WORD     0x00            /* vendor ID */
-#define PCI_IO_BASE_DWORD      0x10            /* IO base */   
-#define PCI_MEM_BASE0_DWORD    0x14            /* memory base - apperture 0 */
-#define PCI_MEM_BASE1_DWORD     0x18           /* memory base - apperture 1 */
-#define PCI_SUBSYS_VENDOR_WORD         0x2C            /* subsystem vendor ID */
-#define PCI_INT_LINE_BYTE      0x3C            /* interrupt line */
-#define PCI_INT_PIN_BYTE       0x3D            /* interrupt pin */
-#define PCI_MAP0_DWORD         0x40            /* PCI to local bus address 0 */
-#define PCI_MAP1_DWORD          0x44           /* PCI to local bus address 1 */
-#define PCI_INT_STATUS          0x48           /* interrupt status */
-#define PCI_INT_CONFIG         0x4C            /* interrupt configuration */
-  
-/* Local PCI register usage */
-#define PCI_MEMORY_ENABLE      0x00000003      /* enable PCI memory */
-#define PCI_CPU_A_MEM_DISABLE  0x00000002      /* disable CPU A memory */
-#define PCI_CPU_B_MEM_DISABLE          0x00100002      /* disable CPU B memory */
-#define PCI_ENABLE_IRQ_CPU_A   0x005A0004      /* enable IRQ for CPU A */
-#define PCI_ENABLE_IRQ_CPU_B    0x005A0008     /* enable IRQ for CPU B */
-#define PCI_DISABLE_IRQ_CPU_A   0x00000004     /* disable IRQ for CPU A */
-#define PCI_DISABLE_IRQ_CPU_B   0x00000008     /* disable IRQ for CPU B */
-/* Setting for the Interrupt Status register */  
-#define IRQ_CPU_A               0x04            /* IRQ for CPU A */
-#define IRQ_CPU_B               0x08           /* IRQ for CPU B */
-
-/* The maximum size of the S514 memory */
-#define MAX_SIZEOF_S514_MEMORY (256 * 1024)
-
-/* S514 control register offsets within the memory address space */
-#define S514_CTRL_REG_BYTE     0x80000
-/* S514 adapter control bytes */
-#define S514_CPU_HALT          0x00
-#define S514_CPU_START         0x01
-
-/* The maximum number of S514 adapters supported */
-#define MAX_S514_CARDS         20      
-
-#define PCI_CARD_TYPE          0x2E
-#define S514_DUAL_CPU          0x12
-#define S514_SINGLE_CPU                0x11
-
-#endif /* _SDLAPCI_H */
-
diff --git a/include/linux/sdlasfm.h b/include/linux/sdlasfm.h
deleted file mode 100644 (file)
index 94aaa8a..0000000
+++ /dev/null
@@ -1,104 +0,0 @@
-/*****************************************************************************
-* sdlasfm.h    WANPIPE(tm) Multiprotocol WAN Link Driver.
-*              Definitions for the SDLA Firmware Module (SFM).
-*
-* Author:      Gideon Hack     
-*
-* Copyright:   (c) 1995-1999 Sangoma Technologies Inc.
-*
-*              This program is free software; you can redistribute it and/or
-*              modify it under the terms of the GNU General Public License
-*              as published by the Free Software Foundation; either version
-*              2 of the License, or (at your option) any later version.
-* ============================================================================
-* Jun 02, 1999  Gideon Hack    Added support for the S514 adapter.
-* Dec 11, 1996 Gene Kozin      Cosmetic changes
-* Apr 16, 1996 Gene Kozin      Changed adapter & firmware IDs. Version 2
-* Dec 15, 1995 Gene Kozin      Structures chaned
-* Nov 09, 1995 Gene Kozin      Initial version.
-*****************************************************************************/
-#ifndef        _SDLASFM_H
-#define        _SDLASFM_H
-
-/****** Defines *************************************************************/
-
-#define        SFM_VERSION     2
-#define        SFM_SIGNATURE   "SFM - Sangoma SDLA Firmware Module"
-
-/* min/max */
-#define        SFM_IMAGE_SIZE  0x8000  /* max size of SDLA code image file */
-#define        SFM_DESCR_LEN   256     /* max length of description string */
-#define        SFM_MAX_SDLA    16      /* max number of compatible adapters */
-
-/* Adapter types */
-#define SDLA_S502A     5020
-#define SDLA_S502E     5021
-#define SDLA_S503      5030
-#define SDLA_S508      5080
-#define SDLA_S507      5070
-#define SDLA_S509      5090
-#define SDLA_S514      5140
-
-/* S514 PCI adapter CPU numbers */
-#define S514_CPU_A     'A'
-#define S514_CPU_B     'B'
-
-
-/* Firmware identification numbers:
- *    0  ..  999       Test & Diagnostics
- *  1000 .. 1999       Streaming HDLC
- *  2000 .. 2999       Bisync
- *  3000 .. 3999       SDLC
- *  4000 .. 4999       HDLC
- *  5000 .. 5999       X.25
- *  6000 .. 6999       Frame Relay
- *  7000 .. 7999       PPP
- *  8000 .. 8999        Cisco HDLC
- */
-#define        SFID_CALIB502    200
-#define        SFID_STRM502    1200
-#define        SFID_STRM508    1800
-#define        SFID_BSC502     2200
-#define        SFID_SDLC502    3200
-#define        SFID_HDLC502    4200
-#define        SFID_HDLC508    4800
-#define        SFID_X25_502    5200
-#define        SFID_X25_508    5800
-#define        SFID_FR502      6200
-#define        SFID_FR508      6800
-#define        SFID_PPP502     7200
-#define        SFID_PPP508     7800
-#define SFID_PPP514    7140
-#define        SFID_CHDLC508   8800
-#define SFID_CHDLC514  8140
-
-/****** Data Types **********************************************************/
-
-typedef struct sfm_info                /* firmware module information */
-{
-       unsigned short  codeid;         /* firmware ID */
-       unsigned short  version;        /* firmaware version number */
-       unsigned short  adapter[SFM_MAX_SDLA]; /* compatible adapter types */
-       unsigned long   memsize;        /* minimum memory size */
-       unsigned short  reserved[2];    /* reserved */
-       unsigned short  startoffs;      /* entry point offset */
-       unsigned short  winoffs;        /* dual-port memory window offset */
-       unsigned short  codeoffs;       /* code load offset */
-       unsigned short  codesize;       /* code size */
-       unsigned short  dataoffs;       /* configuration data load offset */
-       unsigned short  datasize;       /* configuration data size */
-} sfm_info_t;
-
-typedef struct sfm                     /* SDLA firmware file structire */
-{
-       char            signature[80];  /* SFM file signature */
-       unsigned short  version;        /* file format version */
-       unsigned short  checksum;       /* info + image */
-       unsigned short  reserved[6];    /* reserved */
-       char            descr[SFM_DESCR_LEN]; /* description string */
-       sfm_info_t      info;           /* firmware module info */
-       unsigned char   image[1];       /* code image (variable size) */
-} sfm_t;
-
-#endif /* _SDLASFM_H */
-
index fca9b0fb5b4eb2d8c15d0e3f263accba2b6eefb5..5a095572881d0757030522bbd5d7dd4467b547ae 100644 (file)
@@ -73,7 +73,7 @@ static inline int write_tryseqlock(seqlock_t *sl)
 }
 
 /* Start of read calculation -- fetch last complete writer token */
-static inline unsigned read_seqbegin(const seqlock_t *sl)
+static __always_inline unsigned read_seqbegin(const seqlock_t *sl)
 {
        unsigned ret = sl->sequence;
        smp_rmb();
@@ -88,7 +88,7 @@ static inline unsigned read_seqbegin(const seqlock_t *sl)
  *    
  * Using xor saves one conditional branch.
  */
-static inline int read_seqretry(const seqlock_t *sl, unsigned iv)
+static __always_inline int read_seqretry(const seqlock_t *sl, unsigned iv)
 {
        smp_rmb();
        return (iv & 1) | (sl->sequence ^ iv);
index c4619a428d9b11f86648e1971645c2d312a99a8b..f8f234708b984c58addf22edcef14a93d29b4df2 100644 (file)
@@ -344,6 +344,13 @@ extern void              skb_over_panic(struct sk_buff *skb, int len,
                                     void *here);
 extern void          skb_under_panic(struct sk_buff *skb, int len,
                                      void *here);
+extern void          skb_truesize_bug(struct sk_buff *skb);
+
+static inline void skb_truesize_check(struct sk_buff *skb)
+{
+       if (unlikely((int)skb->truesize < sizeof(struct sk_buff) + skb->len))
+               skb_truesize_bug(skb);
+}
 
 extern int skb_append_datato_frags(struct sock *sk, struct sk_buff *skb,
                        int getfrag(void *from, char *to, int offset,
index dee221429ad0b96c86bdd0035b2a42571d634ab1..c61306da8c5256971fb78443f7fa242d43730997 100644 (file)
 extern "C" {
 #endif
 
-extern char * strpbrk(const char *,const char *);
-extern char * strsep(char **,const char *);
-extern __kernel_size_t strspn(const char *,const char *);
-extern __kernel_size_t strcspn(const char *,const char *);
-
 extern char *strndup_user(const char __user *, long);
 
 /*
@@ -70,6 +65,18 @@ extern __kernel_size_t strlen(const char *);
 #ifndef __HAVE_ARCH_STRNLEN
 extern __kernel_size_t strnlen(const char *,__kernel_size_t);
 #endif
+#ifndef __HAVE_ARCH_STRPBRK
+extern char * strpbrk(const char *,const char *);
+#endif
+#ifndef __HAVE_ARCH_STRSEP
+extern char * strsep(char **,const char *);
+#endif
+#ifndef __HAVE_ARCH_STRSPN
+extern __kernel_size_t strspn(const char *,const char *);
+#endif
+#ifndef __HAVE_ARCH_STRCSPN
+extern __kernel_size_t strcspn(const char *,const char *);
+#endif
 
 #ifndef __HAVE_ARCH_MEMSET
 extern void * memset(void *,int,__kernel_size_t);
index 8f96e9dc369abebb5cbef5f8a8cfed63398efb65..77f78e56c4814606066669b2ba45104fafb45b91 100644 (file)
@@ -69,9 +69,21 @@ struct rpc_clnt;
 /*
  * EXPORTed functions for managing rpc_iostats structures
  */
+
+#ifdef CONFIG_PROC_FS
+
 struct rpc_iostats *   rpc_alloc_iostats(struct rpc_clnt *);
 void                   rpc_count_iostats(struct rpc_task *);
 void                   rpc_print_iostats(struct seq_file *, struct rpc_clnt *);
 void                   rpc_free_iostats(struct rpc_iostats *);
 
+#else  /*  CONFIG_PROC_FS  */
+
+static inline struct rpc_iostats *rpc_alloc_iostats(struct rpc_clnt *clnt) { return NULL; }
+static inline void rpc_count_iostats(struct rpc_task *task) {}
+static inline void rpc_print_iostats(struct seq_file *seq, struct rpc_clnt *clnt) {}
+static inline void rpc_free_iostats(struct rpc_iostats *stats) {}
+
+#endif  /*  CONFIG_PROC_FS  */
+
 #endif /* _LINUX_SUNRPC_METRICS_H */
index 50cab2a09f28caebad19282c2b8a6b610ef13175..50356438454525d46b951e3fde65058478bf8017 100644 (file)
@@ -197,15 +197,16 @@ svc_take_res_page(struct svc_rqst *rqstp)
        return rqstp->rq_respages[rqstp->rq_resused++];
 }
 
-static inline int svc_take_page(struct svc_rqst *rqstp)
+static inline void svc_take_page(struct svc_rqst *rqstp)
 {
-       if (rqstp->rq_arghi <= rqstp->rq_argused)
-               return -ENOMEM;
+       if (rqstp->rq_arghi <= rqstp->rq_argused) {
+               WARN_ON(1);
+               return;
+       }
        rqstp->rq_arghi--;
        rqstp->rq_respages[rqstp->rq_resused] =
                rqstp->rq_argpages[rqstp->rq_arghi];
        rqstp->rq_resused++;
-       return 0;
 }
 
 static inline void svc_pushback_allpages(struct svc_rqst *rqstp)
index 7eebbab7160bf1900b5bec67374c271e6a4d9539..e8bbe8118de8118dc6f5fd1b7e21cacafa8afef4 100644 (file)
@@ -53,6 +53,7 @@ struct rpc_timeout {
 
 struct rpc_task;
 struct rpc_xprt;
+struct seq_file;
 
 /*
  * This describes a complete RPC request
index 54eac8a39a4c11d8c760064a8f2fa987ce45d13a..5b1fdf1cff4f057a67eb1c81e487acad031a89b2 100644 (file)
@@ -155,6 +155,7 @@ extern void swapin_readahead(swp_entry_t, unsigned long, struct vm_area_struct *
 /* linux/mm/page_alloc.c */
 extern unsigned long totalram_pages;
 extern unsigned long totalhigh_pages;
+extern unsigned long totalreserve_pages;
 extern long nr_swap_pages;
 extern unsigned int nr_free_pages(void);
 extern unsigned int nr_free_pages_pgdat(pg_data_t *pgdat);
index 5717147596b6c0918829bd5e48b2ea23d783ff5d..d3ebc0e68b2b4cbc20d847cc86598a6e12bedaa0 100644 (file)
@@ -569,9 +569,14 @@ asmlinkage long compat_sys_newfstatat(unsigned int dfd, char __user * filename,
 asmlinkage long compat_sys_openat(unsigned int dfd, const char __user *filename,
                                   int flags, int mode);
 asmlinkage long sys_unshare(unsigned long unshare_flags);
-asmlinkage long sys_splice(int fdin, int fdout, size_t len,
-                               unsigned int flags);
+
+asmlinkage long sys_splice(int fd_in, loff_t __user *off_in,
+                          int fd_out, loff_t __user *off_out,
+                          size_t len, unsigned int flags);
+
+asmlinkage long sys_tee(int fdin, int fdout, size_t len, unsigned int flags);
+
 asmlinkage long sys_sync_file_range(int fd, loff_t offset, loff_t nbytes,
-                                       int flags);
+                                       unsigned int flags);
 
 #endif
index 392da5a6dacb79530c7dc9c0445b6b7d0f0350bb..1ea5d3cda6ae2374056769173d6bd56fa9fd4128 100644 (file)
@@ -74,6 +74,7 @@ struct sysfs_dirent {
        umode_t                 s_mode;
        struct dentry           * s_dentry;
        struct iattr            * s_iattr;
+       atomic_t                s_event;
 };
 
 #define SYSFS_ROOT             0x0001
@@ -117,6 +118,7 @@ int sysfs_remove_bin_file(struct kobject * kobj, struct bin_attribute * attr);
 
 int sysfs_create_group(struct kobject *, const struct attribute_group *);
 void sysfs_remove_group(struct kobject *, const struct attribute_group *);
+void sysfs_notify(struct kobject * k, char *dir, char *attr);
 
 #else /* CONFIG_SYSFS */
 
@@ -185,6 +187,10 @@ static inline void sysfs_remove_group(struct kobject * k, const struct attribute
        ;
 }
 
+static inline void sysfs_notify(struct kobject * k, char *dir, char *attr)
+{
+}
+
 #endif /* CONFIG_SYSFS */
 
 #endif /* _SYSFS_H_ */
index 0976a163b459b79715f97c86af4a0c892eaf19fe..31548303ee3767095f86efb47696ce433662450e 100644 (file)
@@ -6,9 +6,10 @@ extern int tty_insert_flip_string(struct tty_struct *tty, const unsigned char *c
 extern int tty_insert_flip_string_flags(struct tty_struct *tty, const unsigned char *chars, const char *flags, size_t size);
 extern int tty_prepare_flip_string(struct tty_struct *tty, unsigned char **chars, size_t size);
 extern int tty_prepare_flip_string_flags(struct tty_struct *tty, unsigned char **chars, char **flags, size_t size);
+void tty_schedule_flip(struct tty_struct *tty);
 
 static inline int tty_insert_flip_char(struct tty_struct *tty,
-                                      unsigned char ch, char flag)
+                                       unsigned char ch, char flag)
 {
        struct tty_buffer *tb = tty->buf.tail;
        if (tb && tb->active && tb->used < tb->size) {
@@ -19,26 +20,4 @@ static inline int tty_insert_flip_char(struct tty_struct *tty,
        return tty_insert_flip_string_flags(tty, &ch, &flag, 1);
 }
 
-static inline void tty_schedule_flip(struct tty_struct *tty)
-{
-       unsigned long flags;
-       spin_lock_irqsave(&tty->buf.lock, flags);
-       if (tty->buf.tail != NULL) {
-               tty->buf.tail->active = 0;
-               tty->buf.tail->commit = tty->buf.tail->used;
-       }
-       spin_unlock_irqrestore(&tty->buf.lock, flags);
-       schedule_delayed_work(&tty->buf.work, 1);
-}
-
-#undef _INLINE_
-
-
 #endif /* _LINUX_TTY_FLIP_H */
-
-
-
-
-
-
-
diff --git a/include/linux/usb/net2280.h b/include/linux/usb/net2280.h
new file mode 100644 (file)
index 0000000..c602f88
--- /dev/null
@@ -0,0 +1,444 @@
+/*
+ * NetChip 2280 high/full speed USB device controller.
+ * Unlike many such controllers, this one talks PCI.
+ */
+#ifndef __LINUX_USB_NET2280_H
+#define __LINUX_USB_NET2280_H
+
+/*
+ * Copyright (C) 2002 NetChip Technology, Inc. (http://www.netchip.com)
+ * Copyright (C) 2003 David Brownell
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * 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., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+ */
+
+/*-------------------------------------------------------------------------*/
+
+/* NET2280 MEMORY MAPPED REGISTERS
+ *
+ * The register layout came from the chip documentation, and the bit
+ * number definitions were extracted from chip specification.
+ *
+ * Use the shift operator ('<<') to build bit masks, with readl/writel
+ * to access the registers through PCI.
+ */
+
+/* main registers, BAR0 + 0x0000 */
+struct net2280_regs {
+       // offset 0x0000
+       u32             devinit;
+#define     LOCAL_CLOCK_FREQUENCY                               8
+#define     FORCE_PCI_RESET                                     7
+#define     PCI_ID                                              6
+#define     PCI_ENABLE                                          5
+#define     FIFO_SOFT_RESET                                     4
+#define     CFG_SOFT_RESET                                      3
+#define     PCI_SOFT_RESET                                      2
+#define     USB_SOFT_RESET                                      1
+#define     M8051_RESET                                         0
+       u32             eectl;
+#define     EEPROM_ADDRESS_WIDTH                                23
+#define     EEPROM_CHIP_SELECT_ACTIVE                           22
+#define     EEPROM_PRESENT                                      21
+#define     EEPROM_VALID                                        20
+#define     EEPROM_BUSY                                         19
+#define     EEPROM_CHIP_SELECT_ENABLE                           18
+#define     EEPROM_BYTE_READ_START                              17
+#define     EEPROM_BYTE_WRITE_START                             16
+#define     EEPROM_READ_DATA                                    8
+#define     EEPROM_WRITE_DATA                                   0
+       u32             eeclkfreq;
+       u32             _unused0;
+       // offset 0x0010
+
+       u32             pciirqenb0;             /* interrupt PCI master ... */
+#define     SETUP_PACKET_INTERRUPT_ENABLE                       7
+#define     ENDPOINT_F_INTERRUPT_ENABLE                         6
+#define     ENDPOINT_E_INTERRUPT_ENABLE                         5
+#define     ENDPOINT_D_INTERRUPT_ENABLE                         4
+#define     ENDPOINT_C_INTERRUPT_ENABLE                         3
+#define     ENDPOINT_B_INTERRUPT_ENABLE                         2
+#define     ENDPOINT_A_INTERRUPT_ENABLE                         1
+#define     ENDPOINT_0_INTERRUPT_ENABLE                         0
+       u32             pciirqenb1;
+#define     PCI_INTERRUPT_ENABLE                                31
+#define     POWER_STATE_CHANGE_INTERRUPT_ENABLE                 27
+#define     PCI_ARBITER_TIMEOUT_INTERRUPT_ENABLE                26
+#define     PCI_PARITY_ERROR_INTERRUPT_ENABLE                   25
+#define     PCI_MASTER_ABORT_RECEIVED_INTERRUPT_ENABLE          20
+#define     PCI_TARGET_ABORT_RECEIVED_INTERRUPT_ENABLE          19
+#define     PCI_TARGET_ABORT_ASSERTED_INTERRUPT_ENABLE          18
+#define     PCI_RETRY_ABORT_INTERRUPT_ENABLE                    17
+#define     PCI_MASTER_CYCLE_DONE_INTERRUPT_ENABLE              16
+#define     GPIO_INTERRUPT_ENABLE                               13
+#define     DMA_D_INTERRUPT_ENABLE                              12
+#define     DMA_C_INTERRUPT_ENABLE                              11
+#define     DMA_B_INTERRUPT_ENABLE                              10
+#define     DMA_A_INTERRUPT_ENABLE                              9
+#define     EEPROM_DONE_INTERRUPT_ENABLE                        8
+#define     VBUS_INTERRUPT_ENABLE                               7
+#define     CONTROL_STATUS_INTERRUPT_ENABLE                     6
+#define     ROOT_PORT_RESET_INTERRUPT_ENABLE                    4
+#define     SUSPEND_REQUEST_INTERRUPT_ENABLE                    3
+#define     SUSPEND_REQUEST_CHANGE_INTERRUPT_ENABLE             2
+#define     RESUME_INTERRUPT_ENABLE                             1
+#define     SOF_INTERRUPT_ENABLE                                0
+       u32             cpu_irqenb0;            /* ... or onboard 8051 */
+#define     SETUP_PACKET_INTERRUPT_ENABLE                       7
+#define     ENDPOINT_F_INTERRUPT_ENABLE                         6
+#define     ENDPOINT_E_INTERRUPT_ENABLE                         5
+#define     ENDPOINT_D_INTERRUPT_ENABLE                         4
+#define     ENDPOINT_C_INTERRUPT_ENABLE                         3
+#define     ENDPOINT_B_INTERRUPT_ENABLE                         2
+#define     ENDPOINT_A_INTERRUPT_ENABLE                         1
+#define     ENDPOINT_0_INTERRUPT_ENABLE                         0
+       u32             cpu_irqenb1;
+#define     CPU_INTERRUPT_ENABLE                                31
+#define     POWER_STATE_CHANGE_INTERRUPT_ENABLE                 27
+#define     PCI_ARBITER_TIMEOUT_INTERRUPT_ENABLE                26
+#define     PCI_PARITY_ERROR_INTERRUPT_ENABLE                   25
+#define     PCI_INTA_INTERRUPT_ENABLE                           24
+#define     PCI_PME_INTERRUPT_ENABLE                            23
+#define     PCI_SERR_INTERRUPT_ENABLE                           22
+#define     PCI_PERR_INTERRUPT_ENABLE                           21
+#define     PCI_MASTER_ABORT_RECEIVED_INTERRUPT_ENABLE          20
+#define     PCI_TARGET_ABORT_RECEIVED_INTERRUPT_ENABLE          19
+#define     PCI_RETRY_ABORT_INTERRUPT_ENABLE                    17
+#define     PCI_MASTER_CYCLE_DONE_INTERRUPT_ENABLE              16
+#define     GPIO_INTERRUPT_ENABLE                               13
+#define     DMA_D_INTERRUPT_ENABLE                              12
+#define     DMA_C_INTERRUPT_ENABLE                              11
+#define     DMA_B_INTERRUPT_ENABLE                              10
+#define     DMA_A_INTERRUPT_ENABLE                              9
+#define     EEPROM_DONE_INTERRUPT_ENABLE                        8
+#define     VBUS_INTERRUPT_ENABLE                               7
+#define     CONTROL_STATUS_INTERRUPT_ENABLE                     6
+#define     ROOT_PORT_RESET_INTERRUPT_ENABLE                    4
+#define     SUSPEND_REQUEST_INTERRUPT_ENABLE                    3
+#define     SUSPEND_REQUEST_CHANGE_INTERRUPT_ENABLE             2
+#define     RESUME_INTERRUPT_ENABLE                             1
+#define     SOF_INTERRUPT_ENABLE                                0
+
+       // offset 0x0020
+       u32             _unused1;
+       u32             usbirqenb1;
+#define     USB_INTERRUPT_ENABLE                                31
+#define     POWER_STATE_CHANGE_INTERRUPT_ENABLE                 27
+#define     PCI_ARBITER_TIMEOUT_INTERRUPT_ENABLE                26
+#define     PCI_PARITY_ERROR_INTERRUPT_ENABLE                   25
+#define     PCI_INTA_INTERRUPT_ENABLE                           24
+#define     PCI_PME_INTERRUPT_ENABLE                            23
+#define     PCI_SERR_INTERRUPT_ENABLE                           22
+#define     PCI_PERR_INTERRUPT_ENABLE                           21
+#define     PCI_MASTER_ABORT_RECEIVED_INTERRUPT_ENABLE          20
+#define     PCI_TARGET_ABORT_RECEIVED_INTERRUPT_ENABLE          19
+#define     PCI_RETRY_ABORT_INTERRUPT_ENABLE                    17
+#define     PCI_MASTER_CYCLE_DONE_INTERRUPT_ENABLE              16
+#define     GPIO_INTERRUPT_ENABLE                               13
+#define     DMA_D_INTERRUPT_ENABLE                              12
+#define     DMA_C_INTERRUPT_ENABLE                              11
+#define     DMA_B_INTERRUPT_ENABLE                              10
+#define     DMA_A_INTERRUPT_ENABLE                              9
+#define     EEPROM_DONE_INTERRUPT_ENABLE                        8
+#define     VBUS_INTERRUPT_ENABLE                               7
+#define     CONTROL_STATUS_INTERRUPT_ENABLE                     6
+#define     ROOT_PORT_RESET_INTERRUPT_ENABLE                    4
+#define     SUSPEND_REQUEST_INTERRUPT_ENABLE                    3
+#define     SUSPEND_REQUEST_CHANGE_INTERRUPT_ENABLE             2
+#define     RESUME_INTERRUPT_ENABLE                             1
+#define     SOF_INTERRUPT_ENABLE                                0
+       u32             irqstat0;
+#define     INTA_ASSERTED                                       12
+#define     SETUP_PACKET_INTERRUPT                              7
+#define     ENDPOINT_F_INTERRUPT                                6
+#define     ENDPOINT_E_INTERRUPT                                5
+#define     ENDPOINT_D_INTERRUPT                                4
+#define     ENDPOINT_C_INTERRUPT                                3
+#define     ENDPOINT_B_INTERRUPT                                2
+#define     ENDPOINT_A_INTERRUPT                                1
+#define     ENDPOINT_0_INTERRUPT                                0
+       u32             irqstat1;
+#define     POWER_STATE_CHANGE_INTERRUPT                        27
+#define     PCI_ARBITER_TIMEOUT_INTERRUPT                       26
+#define     PCI_PARITY_ERROR_INTERRUPT                          25
+#define     PCI_INTA_INTERRUPT                                  24
+#define     PCI_PME_INTERRUPT                                   23
+#define     PCI_SERR_INTERRUPT                                  22
+#define     PCI_PERR_INTERRUPT                                  21
+#define     PCI_MASTER_ABORT_RECEIVED_INTERRUPT                 20
+#define     PCI_TARGET_ABORT_RECEIVED_INTERRUPT                 19
+#define     PCI_RETRY_ABORT_INTERRUPT                           17
+#define     PCI_MASTER_CYCLE_DONE_INTERRUPT                     16
+#define     SOF_DOWN_INTERRUPT                                  14
+#define     GPIO_INTERRUPT                                      13
+#define     DMA_D_INTERRUPT                                     12
+#define     DMA_C_INTERRUPT                                     11
+#define     DMA_B_INTERRUPT                                     10
+#define     DMA_A_INTERRUPT                                     9
+#define     EEPROM_DONE_INTERRUPT                               8
+#define     VBUS_INTERRUPT                                      7
+#define     CONTROL_STATUS_INTERRUPT                            6
+#define     ROOT_PORT_RESET_INTERRUPT                           4
+#define     SUSPEND_REQUEST_INTERRUPT                           3
+#define     SUSPEND_REQUEST_CHANGE_INTERRUPT                    2
+#define     RESUME_INTERRUPT                                    1
+#define     SOF_INTERRUPT                                       0
+       // offset 0x0030
+       u32             idxaddr;
+       u32             idxdata;
+       u32             fifoctl;
+#define     PCI_BASE2_RANGE                                     16
+#define     IGNORE_FIFO_AVAILABILITY                            3
+#define     PCI_BASE2_SELECT                                    2
+#define     FIFO_CONFIGURATION_SELECT                           0
+       u32             _unused2;
+       // offset 0x0040
+       u32             memaddr;
+#define     START                                               28
+#define     DIRECTION                                           27
+#define     FIFO_DIAGNOSTIC_SELECT                              24
+#define     MEMORY_ADDRESS                                      0
+       u32             memdata0;
+       u32             memdata1;
+       u32             _unused3;
+       // offset 0x0050
+       u32             gpioctl;
+#define     GPIO3_LED_SELECT                                    12
+#define     GPIO3_INTERRUPT_ENABLE                              11
+#define     GPIO2_INTERRUPT_ENABLE                              10
+#define     GPIO1_INTERRUPT_ENABLE                              9
+#define     GPIO0_INTERRUPT_ENABLE                              8
+#define     GPIO3_OUTPUT_ENABLE                                 7
+#define     GPIO2_OUTPUT_ENABLE                                 6
+#define     GPIO1_OUTPUT_ENABLE                                 5
+#define     GPIO0_OUTPUT_ENABLE                                 4
+#define     GPIO3_DATA                                          3
+#define     GPIO2_DATA                                          2
+#define     GPIO1_DATA                                          1
+#define     GPIO0_DATA                                          0
+       u32             gpiostat;
+#define     GPIO3_INTERRUPT                                     3
+#define     GPIO2_INTERRUPT                                     2
+#define     GPIO1_INTERRUPT                                     1
+#define     GPIO0_INTERRUPT                                     0
+} __attribute__ ((packed));
+
+/* usb control, BAR0 + 0x0080 */
+struct net2280_usb_regs {
+       // offset 0x0080
+       u32             stdrsp;
+#define     STALL_UNSUPPORTED_REQUESTS                          31
+#define     SET_TEST_MODE                                       16
+#define     GET_OTHER_SPEED_CONFIGURATION                       15
+#define     GET_DEVICE_QUALIFIER                                14
+#define     SET_ADDRESS                                         13
+#define     ENDPOINT_SET_CLEAR_HALT                             12
+#define     DEVICE_SET_CLEAR_DEVICE_REMOTE_WAKEUP               11
+#define     GET_STRING_DESCRIPTOR_2                             10
+#define     GET_STRING_DESCRIPTOR_1                             9
+#define     GET_STRING_DESCRIPTOR_0                             8
+#define     GET_SET_INTERFACE                                   6
+#define     GET_SET_CONFIGURATION                               5
+#define     GET_CONFIGURATION_DESCRIPTOR                        4
+#define     GET_DEVICE_DESCRIPTOR                               3
+#define     GET_ENDPOINT_STATUS                                 2
+#define     GET_INTERFACE_STATUS                                1
+#define     GET_DEVICE_STATUS                                   0
+       u32             prodvendid;
+#define     PRODUCT_ID                                          16
+#define     VENDOR_ID                                           0
+       u32             relnum;
+       u32             usbctl;
+#define     SERIAL_NUMBER_INDEX                                 16
+#define     PRODUCT_ID_STRING_ENABLE                            13
+#define     VENDOR_ID_STRING_ENABLE                             12
+#define     USB_ROOT_PORT_WAKEUP_ENABLE                         11
+#define     VBUS_PIN                                            10
+#define     TIMED_DISCONNECT                                    9
+#define     SUSPEND_IMMEDIATELY                                 7
+#define     SELF_POWERED_USB_DEVICE                             6
+#define     REMOTE_WAKEUP_SUPPORT                               5
+#define     PME_POLARITY                                        4
+#define     USB_DETECT_ENABLE                                   3
+#define     PME_WAKEUP_ENABLE                                   2
+#define     DEVICE_REMOTE_WAKEUP_ENABLE                         1
+#define     SELF_POWERED_STATUS                                 0
+       // offset 0x0090
+       u32             usbstat;
+#define     HIGH_SPEED                                          7
+#define     FULL_SPEED                                          6
+#define     GENERATE_RESUME                                     5
+#define     GENERATE_DEVICE_REMOTE_WAKEUP                       4
+       u32             xcvrdiag;
+#define     FORCE_HIGH_SPEED_MODE                               31
+#define     FORCE_FULL_SPEED_MODE                               30
+#define     USB_TEST_MODE                                       24
+#define     LINE_STATE                                          16
+#define     TRANSCEIVER_OPERATION_MODE                          2
+#define     TRANSCEIVER_SELECT                                  1
+#define     TERMINATION_SELECT                                  0
+       u32             setup0123;
+       u32             setup4567;
+       // offset 0x0090
+       u32             _unused0;
+       u32             ouraddr;
+#define     FORCE_IMMEDIATE                                     7
+#define     OUR_USB_ADDRESS                                     0
+       u32             ourconfig;
+} __attribute__ ((packed));
+
+/* pci control, BAR0 + 0x0100 */
+struct net2280_pci_regs {
+       // offset 0x0100
+       u32              pcimstctl;
+#define     PCI_ARBITER_PARK_SELECT                             13
+#define     PCI_MULTI LEVEL_ARBITER                             12
+#define     PCI_RETRY_ABORT_ENABLE                              11
+#define     DMA_MEMORY_WRITE_AND_INVALIDATE_ENABLE              10
+#define     DMA_READ_MULTIPLE_ENABLE                            9
+#define     DMA_READ_LINE_ENABLE                                8
+#define     PCI_MASTER_COMMAND_SELECT                           6
+#define         MEM_READ_OR_WRITE                                   0
+#define         IO_READ_OR_WRITE                                    1
+#define         CFG_READ_OR_WRITE                                   2
+#define     PCI_MASTER_START                                    5
+#define     PCI_MASTER_READ_WRITE                               4
+#define         PCI_MASTER_WRITE                                    0
+#define         PCI_MASTER_READ                                     1
+#define     PCI_MASTER_BYTE_WRITE_ENABLES                       0
+       u32              pcimstaddr;
+       u32              pcimstdata;
+       u32              pcimststat;
+#define     PCI_ARBITER_CLEAR                                   2
+#define     PCI_EXTERNAL_ARBITER                                1
+#define     PCI_HOST_MODE                                       0
+} __attribute__ ((packed));
+
+/* dma control, BAR0 + 0x0180 ... array of four structs like this,
+ * for channels 0..3.  see also struct net2280_dma:  descriptor
+ * that can be loaded into some of these registers.
+ */
+struct net2280_dma_regs {      /* [11.7] */
+       // offset 0x0180, 0x01a0, 0x01c0, 0x01e0,
+       u32             dmactl;
+#define     DMA_SCATTER_GATHER_DONE_INTERRUPT_ENABLE            25
+#define     DMA_CLEAR_COUNT_ENABLE                              21
+#define     DESCRIPTOR_POLLING_RATE                             19
+#define         POLL_CONTINUOUS                                     0
+#define         POLL_1_USEC                                         1
+#define         POLL_100_USEC                                       2
+#define         POLL_1_MSEC                                         3
+#define     DMA_VALID_BIT_POLLING_ENABLE                        18
+#define     DMA_VALID_BIT_ENABLE                                17
+#define     DMA_SCATTER_GATHER_ENABLE                           16
+#define     DMA_OUT_AUTO_START_ENABLE                           4
+#define     DMA_PREEMPT_ENABLE                                  3
+#define     DMA_FIFO_VALIDATE                                   2
+#define     DMA_ENABLE                                          1
+#define     DMA_ADDRESS_HOLD                                    0
+       u32             dmastat;
+#define     DMA_ABORT_DONE_INTERRUPT                            27
+#define     DMA_SCATTER_GATHER_DONE_INTERRUPT                   25
+#define     DMA_TRANSACTION_DONE_INTERRUPT                      24
+#define     DMA_ABORT                                           1
+#define     DMA_START                                           0
+       u32             _unused0 [2];
+       // offset 0x0190, 0x01b0, 0x01d0, 0x01f0,
+       u32             dmacount;
+#define     VALID_BIT                                           31
+#define     DMA_DIRECTION                                       30
+#define     DMA_DONE_INTERRUPT_ENABLE                           29
+#define     END_OF_CHAIN                                        28
+#define         DMA_BYTE_COUNT_MASK                                 ((1<<24)-1)
+#define     DMA_BYTE_COUNT                                      0
+       u32             dmaaddr;
+       u32             dmadesc;
+       u32             _unused1;
+} __attribute__ ((packed));
+
+/* dedicated endpoint registers, BAR0 + 0x0200 */
+
+struct net2280_dep_regs {      /* [11.8] */
+       // offset 0x0200, 0x0210, 0x220, 0x230, 0x240
+       u32             dep_cfg;
+       // offset 0x0204, 0x0214, 0x224, 0x234, 0x244
+       u32             dep_rsp;
+       u32             _unused [2];
+} __attribute__ ((packed));
+
+/* configurable endpoint registers, BAR0 + 0x0300 ... array of seven structs
+ * like this, for ep0 then the configurable endpoints A..F
+ * ep0 reserved for control; E and F have only 64 bytes of fifo
+ */
+struct net2280_ep_regs {       /* [11.9] */
+       // offset 0x0300, 0x0320, 0x0340, 0x0360, 0x0380, 0x03a0, 0x03c0
+       u32             ep_cfg;
+#define     ENDPOINT_BYTE_COUNT                                 16
+#define     ENDPOINT_ENABLE                                     10
+#define     ENDPOINT_TYPE                                       8
+#define     ENDPOINT_DIRECTION                                  7
+#define     ENDPOINT_NUMBER                                     0
+       u32             ep_rsp;
+#define     SET_NAK_OUT_PACKETS                                 15
+#define     SET_EP_HIDE_STATUS_PHASE                            14
+#define     SET_EP_FORCE_CRC_ERROR                              13
+#define     SET_INTERRUPT_MODE                                  12
+#define     SET_CONTROL_STATUS_PHASE_HANDSHAKE                  11
+#define     SET_NAK_OUT_PACKETS_MODE                            10
+#define     SET_ENDPOINT_TOGGLE                                 9
+#define     SET_ENDPOINT_HALT                                   8
+#define     CLEAR_NAK_OUT_PACKETS                               7
+#define     CLEAR_EP_HIDE_STATUS_PHASE                          6
+#define     CLEAR_EP_FORCE_CRC_ERROR                            5
+#define     CLEAR_INTERRUPT_MODE                                4
+#define     CLEAR_CONTROL_STATUS_PHASE_HANDSHAKE                3
+#define     CLEAR_NAK_OUT_PACKETS_MODE                          2
+#define     CLEAR_ENDPOINT_TOGGLE                               1
+#define     CLEAR_ENDPOINT_HALT                                 0
+       u32             ep_irqenb;
+#define     SHORT_PACKET_OUT_DONE_INTERRUPT_ENABLE              6
+#define     SHORT_PACKET_TRANSFERRED_INTERRUPT_ENABLE           5
+#define     DATA_PACKET_RECEIVED_INTERRUPT_ENABLE               3
+#define     DATA_PACKET_TRANSMITTED_INTERRUPT_ENABLE            2
+#define     DATA_OUT_PING_TOKEN_INTERRUPT_ENABLE                1
+#define     DATA_IN_TOKEN_INTERRUPT_ENABLE                      0
+       u32             ep_stat;
+#define     FIFO_VALID_COUNT                                    24
+#define     HIGH_BANDWIDTH_OUT_TRANSACTION_PID                  22
+#define     TIMEOUT                                             21
+#define     USB_STALL_SENT                                      20
+#define     USB_IN_NAK_SENT                                     19
+#define     USB_IN_ACK_RCVD                                     18
+#define     USB_OUT_PING_NAK_SENT                               17
+#define     USB_OUT_ACK_SENT                                    16
+#define     FIFO_OVERFLOW                                       13
+#define     FIFO_UNDERFLOW                                      12
+#define     FIFO_FULL                                           11
+#define     FIFO_EMPTY                                          10
+#define     FIFO_FLUSH                                          9
+#define     SHORT_PACKET_OUT_DONE_INTERRUPT                     6
+#define     SHORT_PACKET_TRANSFERRED_INTERRUPT                  5
+#define     NAK_OUT_PACKETS                                     4
+#define     DATA_PACKET_RECEIVED_INTERRUPT                      3
+#define     DATA_PACKET_TRANSMITTED_INTERRUPT                   2
+#define     DATA_OUT_PING_TOKEN_INTERRUPT                       1
+#define     DATA_IN_TOKEN_INTERRUPT                             0
+       // offset 0x0310, 0x0330, 0x0350, 0x0370, 0x0390, 0x03b0, 0x03d0
+       u32             ep_avail;
+       u32             ep_data;
+       u32             _unused0 [2];
+} __attribute__ ((packed));
+
+#endif /* __LINUX_USB_NET2280_H */
index fadc535e29251c833ed14267923907fda85a2614..dc7c621e464714b6e6646b9abcf48b6519c1856a 100644 (file)
 #else
 #define MODULE_VERMAGIC_PREEMPT ""
 #endif
+#ifdef CONFIG_MODULE_UNLOAD
+#define MODULE_VERMAGIC_MODULE_UNLOAD "mod_unload "
+#else
+#define MODULE_VERMAGIC_MODULE_UNLOAD ""
+#endif
 #ifndef MODULE_ARCH_VERMAGIC
 #define MODULE_ARCH_VERMAGIC ""
 #endif
@@ -19,5 +24,5 @@
 #define VERMAGIC_STRING                                                \
        UTS_RELEASE " "                                                 \
        MODULE_VERMAGIC_SMP MODULE_VERMAGIC_PREEMPT                     \
-       MODULE_ARCH_VERMAGIC                                            \
+       MODULE_VERMAGIC_MODULE_UNLOAD MODULE_ARCH_VERMAGIC              \
        "gcc-" __stringify(__GNUC__) "." __stringify(__GNUC_MINOR__)
diff --git a/include/linux/wanpipe.h b/include/linux/wanpipe.h
deleted file mode 100644 (file)
index dae9860..0000000
+++ /dev/null
@@ -1,483 +0,0 @@
-/*****************************************************************************
-* wanpipe.h    WANPIPE(tm) Multiprotocol WAN Link Driver.
-*              User-level API definitions.
-*
-* Author:      Nenad Corbic <ncorbic@sangoma.com>
-*              Gideon Hack     
-*
-* Copyright:   (c) 1995-2000 Sangoma Technologies Inc.
-*
-*              This program is free software; you can redistribute it and/or
-*              modify it under the terms of the GNU General Public License
-*              as published by the Free Software Foundation; either version
-*              2 of the License, or (at your option) any later version.
-* ============================================================================
-* Nov 3,  2000  Nenad Corbic    Added config_id to sdla_t structure.
-*                               Used to determine the protocol running.
-* Jul 13, 2000  Nenad Corbic   Added SyncPPP Support
-* Feb 24, 2000  Nenad Corbic    Added support for x25api driver
-* Oct 04, 1999  Nenad Corbic    New CHDLC and FRAME RELAY code, SMP support
-* Jun 02, 1999  Gideon Hack    Added 'update_call_count' for Cisco HDLC 
-*                              support
-* Jun 26, 1998 David Fong      Added 'ip_mode' in sdla_t.u.p for dynamic IP
-*                              routing mode configuration
-* Jun 12, 1998 David Fong      Added Cisco HDLC union member in sdla_t
-* Dec 08, 1997 Jaspreet Singh  Added 'authenticator' in union of 'sdla_t' 
-* Nov 26, 1997 Jaspreet Singh  Added 'load_sharing' structure.  Also added 
-*                              'devs_struct','dev_to_devtint_next' to 'sdla_t' 
-* Nov 24, 1997 Jaspreet Singh  Added 'irq_dis_if_send_count', 
-*                              'irq_dis_poll_count' to 'sdla_t'.
-* Nov 06, 1997 Jaspreet Singh  Added a define called 'INTR_TEST_MODE'
-* Oct 20, 1997 Jaspreet Singh  Added 'buff_intr_mode_unbusy' and 
-*                              'dlci_intr_mode_unbusy' to 'sdla_t'
-* Oct 18, 1997 Jaspreet Singh  Added structure to maintain global driver
-*                              statistics.
-* Jan 15, 1997 Gene Kozin      Version 3.1.0
-*                               o added UDP management stuff
-* Jan 02, 1997 Gene Kozin      Version 3.0.0
-*****************************************************************************/
-#ifndef        _WANPIPE_H
-#define        _WANPIPE_H
-
-#include <linux/wanrouter.h>
-
-/* Defines */
-
-#ifndef        PACKED
-#define        PACKED  __attribute__((packed))
-#endif
-
-#define        WANPIPE_MAGIC   0x414C4453L     /* signature: 'SDLA' reversed */
-
-/* IOCTL numbers (up to 16) */
-#define        WANPIPE_DUMP    (ROUTER_USER+0) /* dump adapter's memory */
-#define        WANPIPE_EXEC    (ROUTER_USER+1) /* execute firmware command */
-
-#define TRACE_ALL                       0x00
-#define TRACE_PROT                     0x01
-#define TRACE_DATA                     0x02
-
-/* values for request/reply byte */
-#define UDPMGMT_REQUEST        0x01
-#define UDPMGMT_REPLY  0x02
-#define UDP_OFFSET     12
-
-#define MAX_CMD_BUFF   10
-#define MAX_X25_LCN    255     /* Maximum number of x25 channels */
-#define MAX_LCN_NUM    4095    /* Maximum lcn number */
-#define MAX_FT1_RETRY  100
-
-#ifndef AF_WANPIPE
-       #define AF_WANPIPE 25
-       #ifndef PF_WANPIPE
-               #define PF_WANPIPE AF_WANPIPE
-       #endif
-#endif
-
-
-#define TX_TIMEOUT 5*HZ
-
-/* General Critical Flags */
-#define SEND_CRIT      0x00
-#define PERI_CRIT      0x01
-
-/* Chdlc and PPP polling critical flag */
-#define POLL_CRIT      0x03
-
-/* Frame Relay Tx IRQ send critical flag */
-#define SEND_TXIRQ_CRIT 0x02
-
-/* Frame Relay ARP critical flag */
-#define ARP_CRIT       0x03
-
-/* Bit maps for dynamic interface configuration
- * DYN_OPT_ON : turns this option on/off 
- * DEV_DOWN   : device was shutdown by the driver not
- *              by user 
- */
-#define DYN_OPT_ON     0x00
-#define DEV_DOWN       0x01
-
-/*
- * Data structures for IOCTL calls.
- */
-
-typedef struct sdla_dump       /* WANPIPE_DUMP */
-{
-       unsigned long magic;    /* for verification */
-       unsigned long offset;   /* absolute adapter memory address */
-       unsigned long length;   /* block length */
-       void* ptr;              /* -> buffer */
-} sdla_dump_t;
-
-typedef struct sdla_exec       /* WANPIPE_EXEC */
-{
-       unsigned long magic;    /* for verification */
-       void* cmd;              /* -> command structure */
-       void* data;             /* -> data buffer */
-} sdla_exec_t;
-
-/* UDP management stuff */
-
-typedef struct wum_header
-{
-       unsigned char signature[8];     /* 00h: signature */
-       unsigned char type;             /* 08h: request/reply */
-       unsigned char command;          /* 09h: commnand */
-       unsigned char reserved[6];      /* 0Ah: reserved */
-} wum_header_t;
-
-/*************************************************************************
- Data Structure for global statistics
-*************************************************************************/
-
-typedef struct global_stats
-{
-       unsigned long isr_entry;
-       unsigned long isr_already_critical;             
-       unsigned long isr_rx;
-       unsigned long isr_tx;
-       unsigned long isr_intr_test;
-       unsigned long isr_spurious;
-       unsigned long isr_enable_tx_int;
-       unsigned long rx_intr_corrupt_rx_bfr;
-       unsigned long rx_intr_on_orphaned_DLCI;
-       unsigned long rx_intr_dev_not_started;
-       unsigned long tx_intr_dev_not_started;
-       unsigned long poll_entry;
-       unsigned long poll_already_critical;
-       unsigned long poll_processed;
-       unsigned long poll_tbusy_bad_status;
-       unsigned long poll_host_disable_irq;
-       unsigned long poll_host_enable_irq;
-
-} global_stats_t;
-
-
-typedef struct{
-       unsigned short  udp_src_port            PACKED;
-       unsigned short  udp_dst_port            PACKED;
-       unsigned short  udp_length              PACKED;
-       unsigned short  udp_checksum            PACKED;
-} udp_pkt_t;
-
-
-typedef struct {
-       unsigned char   ver_inet_hdr_length     PACKED;
-       unsigned char   service_type            PACKED;
-       unsigned short  total_length            PACKED;
-       unsigned short  identifier              PACKED;
-       unsigned short  flags_frag_offset       PACKED;
-       unsigned char   ttl                     PACKED;
-       unsigned char   protocol                PACKED;
-       unsigned short  hdr_checksum            PACKED;
-       unsigned long   ip_src_address          PACKED;
-       unsigned long   ip_dst_address          PACKED;
-} ip_pkt_t;
-
-
-typedef struct {
-        unsigned char           signature[8]    PACKED;
-        unsigned char           request_reply   PACKED;
-        unsigned char           id              PACKED;
-        unsigned char           reserved[6]     PACKED;
-} wp_mgmt_t;
-
-/*************************************************************************
- Data Structure for if_send  statistics
-*************************************************************************/  
-typedef struct if_send_stat{
-       unsigned long if_send_entry;
-       unsigned long if_send_skb_null;
-       unsigned long if_send_broadcast;
-       unsigned long if_send_multicast;
-       unsigned long if_send_critical_ISR;
-       unsigned long if_send_critical_non_ISR;
-       unsigned long if_send_tbusy;
-       unsigned long if_send_tbusy_timeout;
-       unsigned long if_send_PIPE_request;
-       unsigned long if_send_wan_disconnected;
-       unsigned long if_send_dlci_disconnected;
-       unsigned long if_send_no_bfrs;
-       unsigned long if_send_adptr_bfrs_full;
-       unsigned long if_send_bfr_passed_to_adptr;
-       unsigned long if_send_protocol_error;
-               unsigned long if_send_bfr_not_passed_to_adptr;
-               unsigned long if_send_tx_int_enabled;
-        unsigned long if_send_consec_send_fail; 
-} if_send_stat_t;
-
-typedef struct rx_intr_stat{
-       unsigned long rx_intr_no_socket;
-       unsigned long rx_intr_dev_not_started;
-       unsigned long rx_intr_PIPE_request;
-       unsigned long rx_intr_bfr_not_passed_to_stack;
-       unsigned long rx_intr_bfr_passed_to_stack;
-} rx_intr_stat_t;      
-
-typedef struct pipe_mgmt_stat{
-       unsigned long UDP_PIPE_mgmt_kmalloc_err;
-       unsigned long UDP_PIPE_mgmt_direction_err;
-       unsigned long UDP_PIPE_mgmt_adptr_type_err;
-       unsigned long UDP_PIPE_mgmt_adptr_cmnd_OK;
-       unsigned long UDP_PIPE_mgmt_adptr_cmnd_timeout;
-       unsigned long UDP_PIPE_mgmt_adptr_send_passed;
-       unsigned long UDP_PIPE_mgmt_adptr_send_failed;
-       unsigned long UDP_PIPE_mgmt_not_passed_to_stack;
-       unsigned long UDP_PIPE_mgmt_passed_to_stack;
-       unsigned long UDP_PIPE_mgmt_no_socket;
-        unsigned long UDP_PIPE_mgmt_passed_to_adptr;
-} pipe_mgmt_stat_t;
-
-
-typedef struct {
-       struct sk_buff *skb;
-} bh_data_t, cmd_data_t;
-
-#define MAX_LGTH_UDP_MGNT_PKT 2000
-
-/* This is used for interrupt testing */
-#define INTR_TEST_MODE 0x02
-
-#define        WUM_SIGNATURE_L 0x50495046
-#define        WUM_SIGNATURE_H 0x444E3845
-
-#define        WUM_KILL        0x50
-#define        WUM_EXEC        0x51
-
-#define WANPIPE                0x00
-#define API            0x01
-#define BRIDGE         0x02
-#define BRIDGE_NODE    0x03
-
-#ifdef __KERNEL__
-/****** Kernel Interface ****************************************************/
-
-#include <linux/sdladrv.h>     /* SDLA support module API definitions */
-#include <linux/sdlasfm.h>     /* SDLA firmware module definitions */
-#include <linux/workqueue.h>
-#include <linux/serial.h>
-#include <linux/serialP.h>
-#include <linux/serial_reg.h>
-#include <asm/serial.h>
-#include <linux/tty.h>
-#include <linux/tty_driver.h>
-#include <linux/tty_flip.h>
-
-/****** Data Structures *****************************************************/
-
-/* Adapter Data Space.
- * This structure is needed because we handle multiple cards, otherwise
- * static data would do it.
- */
-typedef struct sdla
-{
-       char devname[WAN_DRVNAME_SZ+1]; /* card name */
-       sdlahw_t hw;                    /* hardware configuration */
-       struct wan_device wandev;       /* WAN device data space */
-       
-       unsigned open_cnt;              /* number of open interfaces */
-       unsigned long state_tick;       /* link state timestamp */
-       unsigned intr_mode;             /* Type of Interrupt Mode */
-       char in_isr;                    /* interrupt-in-service flag */
-       char buff_int_mode_unbusy;      /* flag for carrying out dev_tint */  
-       char dlci_int_mode_unbusy;      /* flag for carrying out dev_tint */
-       long configured;                /* flag for previous configurations */
-       
-       unsigned short irq_dis_if_send_count; /* Disabling irqs in if_send*/
-       unsigned short irq_dis_poll_count;   /* Disabling irqs in poll routine*/
-       unsigned short force_enable_irq;
-       char TracingEnabled;            /* flag for enabling trace */
-       global_stats_t statistics;      /* global statistics */
-       void* mbox;                     /* -> mailbox */
-       void* rxmb;                     /* -> receive mailbox */
-       void* flags;                    /* -> adapter status flags */
-       void (*isr)(struct sdla* card); /* interrupt service routine */
-       void (*poll)(struct sdla* card); /* polling routine */
-       int (*exec)(struct sdla* card, void* u_cmd, void* u_data);
-                                       /* Used by the listen() system call */          
-       /* Wanpipe Socket Interface */
-       int   (*func) (struct sk_buff *, struct sock *);
-       struct sock *sk;
-
-       /* Shutdown function */
-       void (*disable_comm) (struct sdla *card);
-
-       /* Secondary Port Device: Piggibacking */
-       struct sdla *next;
-
-       /* TTY driver variables */
-       unsigned char tty_opt;
-       struct tty_struct *tty;
-       unsigned int tty_minor;
-       unsigned int tty_open;
-       unsigned char *tty_buf;
-       unsigned char *tty_rx;
-       struct work_struct tty_work;
-       
-       union
-       {
-               struct
-               {                       /****** X.25 specific data **********/
-                       u32 lo_pvc;
-                       u32 hi_pvc;
-                       u32 lo_svc;
-                       u32 hi_svc;
-                       struct net_device *svc_to_dev_map[MAX_X25_LCN];
-                       struct net_device *pvc_to_dev_map[MAX_X25_LCN];
-                       struct net_device *tx_dev;
-                       struct net_device *cmd_dev;
-                       u32 no_dev;
-                       volatile u8 *hdlc_buf_status;
-                       u32 tx_interrupts_pending;
-                        u16 timer_int_enabled;
-                       struct net_device *poll_device;
-                       atomic_t command_busy;
-
-                       u16 udp_pkt_lgth;
-                        u32 udp_type;
-                        u8  udp_pkt_src;
-                       u32 udp_lcn;
-                        struct net_device *udp_dev;
-                        s8 udp_pkt_data[MAX_LGTH_UDP_MGNT_PKT];
-
-                       u8 LAPB_hdlc;           /* Option to turn off X25 and run only LAPB */
-                       u8 logging;             /* Option to log call messages */
-                       u8 oob_on_modem;        /* Option to send modem status to the api */
-                       u16 num_of_ch;          /* Number of channels configured by the user */
-
-                       struct work_struct x25_poll_work;
-                       struct timer_list x25_timer;
-               } x;
-               struct
-               {                       /****** frame relay specific data ***/
-                       void* rxmb_base;        /* -> first Rx buffer */
-                       void* rxmb_last;        /* -> last Rx buffer */
-                       unsigned rx_base;       /* S508 receive buffer base */
-                       unsigned rx_top;        /* S508 receive buffer end */
-                       unsigned short node_dlci[100];
-                       unsigned short dlci_num;
-                        struct net_device *dlci_to_dev_map[991 + 1];
-                        unsigned tx_interrupts_pending;
-                        unsigned short timer_int_enabled;
-                        unsigned short udp_pkt_lgth;
-                        int udp_type;
-                        char udp_pkt_src;
-                        unsigned udp_dlci;
-                        char udp_pkt_data[MAX_LGTH_UDP_MGNT_PKT];
-                        void* trc_el_base;                     /* first trace element */
-                        void* trc_el_last;                     /* last trace element */
-                        void *curr_trc_el;                     /* current trace element */
-                        unsigned short trc_bfr_space;          /* trace buffer space */
-                       unsigned char  update_comms_stats;
-                       struct net_device *arp_dev;
-                       spinlock_t if_send_lock;
-               } f;
-               struct                  /****** PPP-specific data ***********/
-               {
-                       char if_name[WAN_IFNAME_SZ+1];  /* interface name */
-                       void* txbuf;            /* -> current Tx buffer */
-                       void* txbuf_base;       /* -> first Tx buffer */
-                       void* txbuf_last;       /* -> last Tx buffer */
-                       void* rxbuf_base;       /* -> first Rx buffer */
-                       void* rxbuf_last;       /* -> last Rx buffer */
-                       unsigned rx_base;       /* S508 receive buffer base */
-                       unsigned rx_top;        /* S508 receive buffer end */
-                       char ip_mode;           /* STATIC/HOST/PEER IP Mode */
-                       char authenticator;     /* Authenticator for PAP/CHAP */
-                       unsigned char comm_enabled; /* Is comm enabled or not */
-                       unsigned char peer_route;   /* Process Peer Route */    
-                       unsigned long *txbuf_next;  /* Next Tx buffer to use */ 
-                       unsigned long *rxbuf_next;  /* Next Rx buffer to use */
-               } p;
-               struct                  /* Cisco HDLC-specific data */
-               {
-                       char if_name[WAN_IFNAME_SZ+1];  /* interface name */
-                       unsigned char comm_port;/* Communication Port O or 1 */
-                       unsigned char usedby;  /* Used by WANPIPE or API */
-                       void* rxmb;             /* Receive mail box */
-                       void* flags;            /* flags */
-                       void* tx_status;        /* Tx status element */
-                       void* rx_status;        /* Rx status element */
-                       void* txbuf;            /* -> current Tx buffer */
-                       void* txbuf_base;       /* -> first Tx buffer */
-                       void* txbuf_last;       /* -> last Tx buffer */
-                       void* rxbuf_base;       /* -> first Rx buffer */
-                       void* rxbuf_last;       /* -> last Rx buffer */
-                       unsigned rx_base;       /* S508 receive buffer base */
-                       unsigned rx_top;        /* S508 receive buffer end */
-                       unsigned char receive_only; /* high speed receivers */
-                       unsigned short protocol_options;
-                       unsigned short kpalv_tx;        /* Tx kpalv timer */
-                       unsigned short kpalv_rx;        /* Rx kpalv timer */
-                       unsigned short kpalv_err;       /* Error tolerance */
-                       unsigned short slarp_timer;     /* SLARP req timer */
-                       unsigned state;                 /* state of the link */
-                       unsigned char api_status;
-                       unsigned char update_call_count;
-                       unsigned short api_options;     /* for async config */
-                       unsigned char  async_mode;
-                       unsigned short tx_bits_per_char;
-                       unsigned short rx_bits_per_char;
-                       unsigned short stop_bits;
-                       unsigned short parity;
-                       unsigned short break_timer;
-                       unsigned short inter_char_timer;
-                       unsigned short rx_complete_length;
-                       unsigned short xon_char;
-                       unsigned short xoff_char;
-                       unsigned char comm_enabled; /* Is comm enabled or not */
-                       unsigned char backup;
-               } c;
-               struct
-               {
-                       void* tx_status;        /* Tx status element */
-                       void* rx_status;        /* Rx status element */
-                       void* trace_status;     /* Trace status element */
-                       void* txbuf;            /* -> current Tx buffer */
-                       void* txbuf_base;       /* -> first Tx buffer */
-                       void* txbuf_last;       /* -> last Tx buffer */
-                       void* rxbuf_base;       /* -> first Rx buffer */
-                       void* rxbuf_last;       /* -> last Rx buffer */
-                       void* tracebuf;         /* -> current Trace buffer */
-                       void* tracebuf_base;    /* -> current Trace buffer */
-                       void* tracebuf_last;    /* -> current Trace buffer */
-                       unsigned rx_base;       /* receive buffer base */
-                       unsigned rx_end;        /* receive buffer end */
-                       unsigned trace_base;    /* trace buffer base */
-                       unsigned trace_end;     /* trace buffer end */
-
-               } h;
-       } u;
-} sdla_t;
-
-/****** Public Functions ****************************************************/
-
-void wanpipe_open      (sdla_t* card);                 /* wpmain.c */
-void wanpipe_close     (sdla_t* card);                 /* wpmain.c */
-void wanpipe_set_state (sdla_t* card, int state);      /* wpmain.c */
-
-int wpx_init (sdla_t* card, wandev_conf_t* conf);      /* wpx.c */
-int wpf_init (sdla_t* card, wandev_conf_t* conf);      /* wpf.c */
-int wpp_init (sdla_t* card, wandev_conf_t* conf);      /* wpp.c */
-int wpc_init (sdla_t* card, wandev_conf_t* conf); /* Cisco HDLC */
-int bsc_init (sdla_t* card, wandev_conf_t* conf);      /* BSC streaming */
-int hdlc_init(sdla_t* card, wandev_conf_t* conf);      /* HDLC support */
-int wpft1_init (sdla_t* card, wandev_conf_t* conf);     /* FT1 Config support */
-int wsppp_init (sdla_t* card, wandev_conf_t* conf);    /* Sync PPP on top of RAW CHDLC */
-
-extern sdla_t * wanpipe_find_card(char *);
-extern sdla_t * wanpipe_find_card_num (int);
-
-extern void wanpipe_queue_work (struct work_struct *);
-extern void wanpipe_mark_bh (void);
-extern void wakeup_sk_bh(struct net_device *dev);
-extern int change_dev_flags(struct net_device *dev, unsigned flags);
-extern unsigned long get_ip_address(struct net_device *dev, int option);
-extern void add_gateway(sdla_t *card, struct net_device *dev);
-
-
-#endif /* __KERNEL__ */
-#endif /* _WANPIPE_H */
-
index a13e30c35f4259e7ba835e7eda73b38995246437..643bded9f557b5556ea159515b7915cf9016484d 100644 (file)
@@ -10,8 +10,6 @@
 extern struct neigh_table arp_tbl;
 
 extern void    arp_init(void);
-extern int     arp_rcv(struct sk_buff *skb, struct net_device *dev,
-                       struct packet_type *pt, struct net_device *orig_dev);
 extern int     arp_find(unsigned char *haddr, struct sk_buff *skb);
 extern int     arp_ioctl(unsigned int cmd, void __user *arg);
 extern void     arp_send(int type, int ptype, u32 dest_ip, 
index b971d8c82bdd6fbd92fb65795766438fa6300fbb..6b3693f05ca05722660df48af1cb352a17a70c3e 100644 (file)
@@ -267,8 +267,9 @@ extern void ieee80211softmac_stop(struct net_device *dev);
 #define IEEE80211SOFTMAC_EVENT_AUTH_FAILED             5
 #define IEEE80211SOFTMAC_EVENT_AUTH_TIMEOUT            6
 #define IEEE80211SOFTMAC_EVENT_ASSOCIATE_NET_NOT_FOUND 7
+#define IEEE80211SOFTMAC_EVENT_DISASSOCIATED           8
 /* keep this updated! */
-#define IEEE80211SOFTMAC_EVENT_LAST                    7
+#define IEEE80211SOFTMAC_EVENT_LAST                    8
 /*
  * If you want to be notified of certain events, you can call
  * ieee80211softmac_notify[_atomic] with
index 25f708ff020e9b158e26fe95c56b2706774c8bdf..59f0c83d55a243913eec31fefe22433213a8d48b 100644 (file)
@@ -48,31 +48,7 @@ static inline int inet6_sk_ehashfn(const struct sock *sk)
        return inet6_ehashfn(laddr, lport, faddr, fport);
 }
 
-static inline void __inet6_hash(struct inet_hashinfo *hashinfo,
-                               struct sock *sk)
-{
-       struct hlist_head *list;
-       rwlock_t *lock;
-
-       BUG_TRAP(sk_unhashed(sk));
-
-       if (sk->sk_state == TCP_LISTEN) {
-               list = &hashinfo->listening_hash[inet_sk_listen_hashfn(sk)];
-               lock = &hashinfo->lhash_lock;
-               inet_listen_wlock(hashinfo);
-       } else {
-               unsigned int hash;
-               sk->sk_hash = hash = inet6_sk_ehashfn(sk);
-               hash &= (hashinfo->ehash_size - 1);
-               list = &hashinfo->ehash[hash].chain;
-               lock = &hashinfo->ehash[hash].lock;
-               write_lock(lock);
-       }
-
-       __sk_add_node(sk, list);
-       sock_prot_inc_use(sk->sk_prot);
-       write_unlock(lock);
-}
+extern void __inet6_hash(struct inet_hashinfo *hashinfo, struct sock *sk);
 
 /*
  * Sockets in TCP_CLOSE state are _always_ taken out of the hash, so
@@ -80,52 +56,12 @@ static inline void __inet6_hash(struct inet_hashinfo *hashinfo,
  *
  * The sockhash lock must be held as a reader here.
  */
-static inline struct sock *
-               __inet6_lookup_established(struct inet_hashinfo *hashinfo,
+extern struct sock *__inet6_lookup_established(struct inet_hashinfo *hashinfo,
                                           const struct in6_addr *saddr,
                                           const u16 sport,
                                           const struct in6_addr *daddr,
                                           const u16 hnum,
-                                          const int dif)
-{
-       struct sock *sk;
-       const struct hlist_node *node;
-       const __u32 ports = INET_COMBINED_PORTS(sport, hnum);
-       /* Optimize here for direct hit, only listening connections can
-        * have wildcards anyways.
-        */
-       unsigned int hash = inet6_ehashfn(daddr, hnum, saddr, sport);
-       struct inet_ehash_bucket *head = inet_ehash_bucket(hashinfo, hash);
-
-       prefetch(head->chain.first);
-       read_lock(&head->lock);
-       sk_for_each(sk, node, &head->chain) {
-               /* For IPV6 do the cheaper port and family tests first. */
-               if (INET6_MATCH(sk, hash, saddr, daddr, ports, dif))
-                       goto hit; /* You sunk my battleship! */
-       }
-       /* Must check for a TIME_WAIT'er before going to listener hash. */
-       sk_for_each(sk, node, &(head + hashinfo->ehash_size)->chain) {
-               const struct inet_timewait_sock *tw = inet_twsk(sk);
-
-               if(*((__u32 *)&(tw->tw_dport))  == ports        &&
-                  sk->sk_family                == PF_INET6) {
-                       const struct inet6_timewait_sock *tw6 = inet6_twsk(sk);
-
-                       if (ipv6_addr_equal(&tw6->tw_v6_daddr, saddr)   &&
-                           ipv6_addr_equal(&tw6->tw_v6_rcv_saddr, daddr)       &&
-                           (!sk->sk_bound_dev_if || sk->sk_bound_dev_if == dif))
-                               goto hit;
-               }
-       }
-       read_unlock(&head->lock);
-       return NULL;
-
-hit:
-       sock_hold(sk);
-       read_unlock(&head->lock);
-       return sk;
-}
+                                          const int dif);
 
 extern struct sock *inet6_lookup_listener(struct inet_hashinfo *hashinfo,
                                          const struct in6_addr *daddr,
index 8fe6156ca9b0807fc3cbb98d2c7aa0faf5741978..3d2e5ca62a5af1c8ba234523d9886380d7d90564 100644 (file)
@@ -95,6 +95,7 @@ extern int            ip_local_deliver(struct sk_buff *skb);
 extern int             ip_mr_input(struct sk_buff *skb);
 extern int             ip_output(struct sk_buff *skb);
 extern int             ip_mc_output(struct sk_buff *skb);
+extern int             ip_fragment(struct sk_buff *skb, int (*output)(struct sk_buff *));
 extern int             ip_do_nat(struct sk_buff *skb);
 extern void            ip_send_check(struct iphdr *ip);
 extern int             ip_queue_xmit(struct sk_buff *skb, int ipfragok);
index 6d6f0634ae41294299324005be723d0ac86a1bf0..4abedb8eaece67a43e4a091cca197477c025cc7a 100644 (file)
@@ -230,7 +230,7 @@ extern int                  ip6_ra_control(struct sock *sk, int sel,
                                               void (*destructor)(struct sock *));
 
 
-extern int                     ipv6_parse_hopopts(struct sk_buff *skb, int);
+extern int                     ipv6_parse_hopopts(struct sk_buff *skb);
 
 extern struct ipv6_txoptions *  ipv6_dup_options(struct sock *sk, struct ipv6_txoptions *opt);
 extern struct ipv6_txoptions * ipv6_renew_options(struct sock *sk, struct ipv6_txoptions *opt,
index af2b0544586e73ad6a0420f5a4bcaec527250ca4..ff8b0dad7b0fcb5831f0801e4489fce01944d8ab 100644 (file)
@@ -454,6 +454,7 @@ static inline void sk_stream_set_owner_r(struct sk_buff *skb, struct sock *sk)
 
 static inline void sk_stream_free_skb(struct sock *sk, struct sk_buff *skb)
 {
+       skb_truesize_check(skb);
        sock_set_flag(sk, SOCK_QUEUE_SHRUNK);
        sk->sk_wmem_queued   -= skb->truesize;
        sk->sk_forward_alloc += skb->truesize;
index 1a318374faefc42e853ab4692b9aeb046aebda46..1d10c879f7e241b8543e0f86cb51d45e56381982 100644 (file)
@@ -8,6 +8,7 @@
 static inline __be16 x25_type_trans(struct sk_buff *skb, struct net_device *dev)
 {
        skb->mac.raw = skb->data;
+       skb->dev = dev;
        skb->pkt_type = PACKET_HOST;
        
        return htons(ETH_P_X25);
index 0d5529c382e8ce5d66fceac90f12c3dba7e51440..afa508d92c93fdf6b3a4a96946a223c440514750 100644 (file)
@@ -143,6 +143,11 @@ struct xfrm_state
        /* Replay detection state at the time we sent the last notification */
        struct xfrm_replay_state preplay;
 
+       /* internal flag that only holds state for delayed aevent at the
+        * moment
+       */
+       u32                     xflags;
+
        /* Replay detection notification settings */
        u32                     replay_maxage;
        u32                     replay_maxdiff;
@@ -168,6 +173,9 @@ struct xfrm_state
        void                    *data;
 };
 
+/* xflags - make enum if more show up */
+#define XFRM_TIME_DEFER        1
+
 enum {
        XFRM_STATE_VOID,
        XFRM_STATE_ACQ,
index f404fe21cc2162eea489411627f90237bba52037..ad63c215efe5b68be3d555fccda212ff09a3358a 100644 (file)
@@ -91,34 +91,6 @@ enum ib_sa_selector {
        IB_SA_BEST = 3
 };
 
-enum ib_sa_rate {
-       IB_SA_RATE_2_5_GBPS = 2,
-       IB_SA_RATE_5_GBPS   = 5,
-       IB_SA_RATE_10_GBPS  = 3,
-       IB_SA_RATE_20_GBPS  = 6,
-       IB_SA_RATE_30_GBPS  = 4,
-       IB_SA_RATE_40_GBPS  = 7,
-       IB_SA_RATE_60_GBPS  = 8,
-       IB_SA_RATE_80_GBPS  = 9,
-       IB_SA_RATE_120_GBPS = 10
-};
-
-static inline int ib_sa_rate_enum_to_int(enum ib_sa_rate rate)
-{
-       switch (rate) {
-       case IB_SA_RATE_2_5_GBPS: return  1;
-       case IB_SA_RATE_5_GBPS:   return  2;
-       case IB_SA_RATE_10_GBPS:  return  4;
-       case IB_SA_RATE_20_GBPS:  return  8;
-       case IB_SA_RATE_30_GBPS:  return 12;
-       case IB_SA_RATE_40_GBPS:  return 16;
-       case IB_SA_RATE_60_GBPS:  return 24;
-       case IB_SA_RATE_80_GBPS:  return 32;
-       case IB_SA_RATE_120_GBPS: return 48;
-       default:                  return -1;
-       }
-}
-
 /*
  * Structures for SA records are named "struct ib_sa_xxx_rec."  No
  * attempt is made to pack structures to match the physical layout of
index c1ad6273ac6ca5f5fcb20d9dfd7f1bdcc08ccd6b..6bbf1b364400568b283215e37b6e9bec776dd84b 100644 (file)
@@ -314,6 +314,34 @@ enum ib_ah_flags {
        IB_AH_GRH       = 1
 };
 
+enum ib_rate {
+       IB_RATE_PORT_CURRENT = 0,
+       IB_RATE_2_5_GBPS = 2,
+       IB_RATE_5_GBPS   = 5,
+       IB_RATE_10_GBPS  = 3,
+       IB_RATE_20_GBPS  = 6,
+       IB_RATE_30_GBPS  = 4,
+       IB_RATE_40_GBPS  = 7,
+       IB_RATE_60_GBPS  = 8,
+       IB_RATE_80_GBPS  = 9,
+       IB_RATE_120_GBPS = 10
+};
+
+/**
+ * ib_rate_to_mult - Convert the IB rate enum to a multiple of the
+ * base rate of 2.5 Gbit/sec.  For example, IB_RATE_5_GBPS will be
+ * converted to 2, since 5 Gbit/sec is 2 * 2.5 Gbit/sec.
+ * @rate: rate to convert.
+ */
+int ib_rate_to_mult(enum ib_rate rate) __attribute_const__;
+
+/**
+ * mult_to_ib_rate - Convert a multiple of 2.5 Gbit/sec to an IB rate
+ * enum.
+ * @mult: multiple to convert.
+ */
+enum ib_rate mult_to_ib_rate(int mult) __attribute_const__;
+
 struct ib_ah_attr {
        struct ib_global_route  grh;
        u16                     dlid;
index 174101b2069bb086b8419ffab9635f0bd8c5cd78..d31b16d25a09f0c0980f7ce824a890a70c86f605 100644 (file)
@@ -28,4 +28,5 @@
 #define BLIST_NO_ULD_ATTACH    0x100000 /* device is actually for RAID config */
 #define BLIST_SELECT_NO_ATN    0x200000 /* select without ATN */
 #define BLIST_RETRY_HWERROR    0x400000 /* retry HARDWARE_ERROR */
+#define BLIST_MAX_512          0x800000 /* maximum 512 sector cdb length */
 #endif
index dc6862d09e535d630bbbaee2f2f00afbf3f4011d..de6ce541a046c551b065fa6737b949c4bee6fff2 100644 (file)
@@ -140,7 +140,6 @@ struct scsi_host_template {
         *
         * Status: REQUIRED     (at least one of them)
         */
-       int (* eh_strategy_handler)(struct Scsi_Host *);
        int (* eh_abort_handler)(struct scsi_cmnd *);
        int (* eh_device_reset_handler)(struct scsi_cmnd *);
        int (* eh_bus_reset_handler)(struct scsi_cmnd *);
index d4be4d92d5868d8e0f3d548c02571fe543ee2342..edb9525386dadc40b38788787d6c92586dcf5e82 100644 (file)
@@ -41,8 +41,6 @@ typedef struct scsi_fctargaddress {
 } Scsi_FCTargAddress;
 
 extern int scsi_ioctl(struct scsi_device *, int, void __user *);
-extern int scsi_ioctl_send_command(struct scsi_device *,
-                                  struct scsi_ioctl_command __user *);
 extern int scsi_nonblockable_ioctl(struct scsi_device *sdev, int cmd,
                                   void __user *arg, struct file *filp);
 
index b3657f111937a32d159ff1d99b48d0c19ed73604..cca1d4926d2aa47333749967577087df93b9ec52 100644 (file)
@@ -49,6 +49,11 @@ struct scsi_transport_template {
         */
        unsigned int create_work_queue : 1;
 
+       /*
+        * Allows a transport to override the default error handler.
+        */
+       void (* eh_strategy_handler)(struct Scsi_Host *);
+
        /*
         * This is an optional routine that allows the transport to become
         * involved when a scsi io timer fires. The return value tells the
index cf3fec8be1e358c6f3a95cef7d5eff5cf2dbc655..5626225bd3aec200d9a04728bc56af49a33ad002 100644 (file)
@@ -202,12 +202,19 @@ struct fc_rport { /* aka fc_starget_attrs */
        /* internal data */
        unsigned int channel;
        u32 number;
+       u8 flags;
        struct list_head peers;
        struct device dev;
        struct work_struct dev_loss_work;
        struct work_struct scan_work;
+       struct work_struct stgt_delete_work;
+       struct work_struct rport_delete_work;
 } __attribute__((aligned(sizeof(unsigned long))));
 
+/* bit field values for struct fc_rport "flags" field: */
+#define FC_RPORT_DEVLOSS_PENDING       0x01
+#define FC_RPORT_SCAN_PENDING          0x02
+
 #define        dev_to_rport(d)                         \
        container_of(d, struct fc_rport, dev)
 #define transport_class_to_rport(classdev)     \
@@ -327,13 +334,16 @@ struct fc_host_attrs {
        struct list_head rport_bindings;
        u32 next_rport_number;
        u32 next_target_id;
-       u8 flags;
-       struct work_struct rport_del_work;
-};
 
-/* values for struct fc_host_attrs "flags" field: */
-#define FC_SHOST_RPORT_DEL_SCHEDULED   0x01
+       /* work queues for rport state manipulation */
+       char work_q_name[KOBJ_NAME_LEN];
+       struct workqueue_struct *work_q;
+       char devloss_work_q_name[KOBJ_NAME_LEN];
+       struct workqueue_struct *devloss_work_q;
+};
 
+#define shost_to_fc_host(x) \
+       ((struct fc_host_attrs *)(x)->shost_data)
 
 #define fc_host_node_name(x) \
        (((struct fc_host_attrs *)(x)->shost_data)->node_name)
@@ -375,10 +385,14 @@ struct fc_host_attrs {
        (((struct fc_host_attrs *)(x)->shost_data)->next_rport_number)
 #define fc_host_next_target_id(x) \
        (((struct fc_host_attrs *)(x)->shost_data)->next_target_id)
-#define fc_host_flags(x) \
-       (((struct fc_host_attrs *)(x)->shost_data)->flags)
-#define fc_host_rport_del_work(x) \
-       (((struct fc_host_attrs *)(x)->shost_data)->rport_del_work)
+#define fc_host_work_q_name(x) \
+       (((struct fc_host_attrs *)(x)->shost_data)->work_q_name)
+#define fc_host_work_q(x) \
+       (((struct fc_host_attrs *)(x)->shost_data)->work_q)
+#define fc_host_devloss_work_q_name(x) \
+       (((struct fc_host_attrs *)(x)->shost_data)->devloss_work_q_name)
+#define fc_host_devloss_work_q(x) \
+       (((struct fc_host_attrs *)(x)->shost_data)->devloss_work_q)
 
 
 /* The functions by which the transport class and the driver communicate */
@@ -461,10 +475,15 @@ fc_remote_port_chkready(struct fc_rport *rport)
 
        switch (rport->port_state) {
        case FC_PORTSTATE_ONLINE:
-               result = 0;
+               if (rport->roles & FC_RPORT_ROLE_FCP_TARGET)
+                       result = 0;
+               else if (rport->flags & FC_RPORT_DEVLOSS_PENDING)
+                       result = DID_IMM_RETRY << 16;
+               else
+                       result = DID_NO_CONNECT << 16;
                break;
        case FC_PORTSTATE_BLOCKED:
-               result = DID_BUS_BUSY << 16;
+               result = DID_IMM_RETRY << 16;
                break;
        default:
                result = DID_NO_CONNECT << 16;
index 66b1f08b42b90a79921135a487474b10802d80ec..df70e7592ab5dace9547942beadb73a08b75887a 100644 (file)
@@ -367,7 +367,7 @@ struct snd_pcm_substream {
        struct snd_pcm_group self_group;        /* fake group for non linked substream (with substream lock inside) */
        struct snd_pcm_group *group;            /* pointer to current group */
        /* -- assigned files -- */
-       struct snd_pcm_file *file;
+       void *file;
        struct file *ffile;
        void (*pcm_release)(struct snd_pcm_substream *);
 #if defined(CONFIG_SND_PCM_OSS) || defined(CONFIG_SND_PCM_OSS_MODULE)
@@ -898,7 +898,6 @@ ssize_t snd_pcm_format_size(snd_pcm_format_t format, size_t samples);
 const unsigned char *snd_pcm_format_silence_64(snd_pcm_format_t format);
 int snd_pcm_format_set_silence(snd_pcm_format_t format, void *buf, unsigned int frames);
 snd_pcm_format_t snd_pcm_build_linear_format(int width, int unsignd, int big_endian);
-const char *snd_pcm_format_name(snd_pcm_format_t format);
 
 void snd_pcm_set_ops(struct snd_pcm * pcm, int direction, struct snd_pcm_ops *ops);
 void snd_pcm_set_sync(struct snd_pcm_substream *substream);
index 6b0c9af5bbf7c4a2569cf982ea4eba3821e9634b..1c2faf62bc7301a823b26cee9ae738069e93aaa6 100644 (file)
--- a/ipc/shm.c
+++ b/ipc/shm.c
@@ -162,6 +162,8 @@ static int shm_mmap(struct file * file, struct vm_area_struct * vma)
        ret = shmem_mmap(file, vma);
        if (ret == 0) {
                vma->vm_ops = &shm_vm_ops;
+               if (!(vma->vm_flags & VM_WRITE))
+                       vma->vm_flags &= ~VM_MAYWRITE;
                shm_inc(file->f_dentry->d_inode->i_ino);
        }
 
index 5e785a29e1e63349ff35f8a1b3282f468fd24277..b3dcfad3b4f72075b7c338dc182eeb0c2403d482 100644 (file)
@@ -183,8 +183,7 @@ static int grow_ary(struct ipc_ids* ids, int newsize)
        if(new == NULL)
                return size;
        new->size = newsize;
-       memcpy(new->p, ids->entries->p, sizeof(struct kern_ipc_perm *)*size +
-                                       sizeof(struct ipc_id_ary));
+       memcpy(new->p, ids->entries->p, sizeof(struct kern_ipc_perm *)*size);
        for(i=size;i<newsize;i++) {
                new->p[i] = NULL;
        }
index 6c2eeb8f6390c1ae1daeb3b12ecd3aa974b3c599..f86434d7b3d1811b689bfedcfc1bc40079950a34 100644 (file)
@@ -34,6 +34,7 @@
 #include <linux/mutex.h>
 #include <linux/futex.h>
 #include <linux/compat.h>
+#include <linux/pipe_fs_i.h>
 
 #include <asm/uaccess.h>
 #include <asm/unistd.h>
@@ -55,7 +56,7 @@ static void __unhash_process(struct task_struct *p)
                detach_pid(p, PIDTYPE_PGID);
                detach_pid(p, PIDTYPE_SID);
 
-               list_del_init(&p->tasks);
+               list_del_rcu(&p->tasks);
                __get_cpu_var(process_counts)--;
        }
        list_del_rcu(&p->thread_group);
@@ -941,6 +942,9 @@ fastcall NORET_TYPE void do_exit(long code)
        if (tsk->io_context)
                exit_io_context();
 
+       if (tsk->splice_pipe)
+               __free_pipe_info(tsk->splice_pipe);
+
        /* PF_DEAD causes final put_task_struct after we schedule. */
        preempt_disable();
        BUG_ON(tsk->flags & PF_DEAD);
index 3384eb89cb1c4ff25c5448ff91502bd4a79ee7db..d2fa57d480d4af9c868c2e7a5602f50b6e164795 100644 (file)
@@ -124,12 +124,6 @@ void __put_task_struct(struct task_struct *tsk)
                free_task(tsk);
 }
 
-void __put_task_struct_cb(struct rcu_head *rhp)
-{
-       struct task_struct *tsk = container_of(rhp, struct task_struct, rcu);
-       __put_task_struct(tsk);
-}
-
 void __init fork_init(unsigned long mempages)
 {
 #ifndef __HAVE_ARCH_TASK_STRUCT_ALLOCATOR
@@ -186,6 +180,7 @@ static struct task_struct *dup_task_struct(struct task_struct *orig)
        atomic_set(&tsk->usage,2);
        atomic_set(&tsk->fs_excl, 0);
        tsk->btrace_seq = 0;
+       tsk->splice_pipe = NULL;
        return tsk;
 }
 
@@ -1210,7 +1205,7 @@ static task_t *copy_process(unsigned long clone_flags,
                        attach_pid(p, PIDTYPE_PGID, process_group(p));
                        attach_pid(p, PIDTYPE_SID, p->signal->session);
 
-                       list_add_tail(&p->tasks, &init_task.tasks);
+                       list_add_tail_rcu(&p->tasks, &init_task.tasks);
                        __get_cpu_var(process_counts)++;
                }
                attach_pid(p, PIDTYPE_PID, p->pid);
index f181ff4dd32ec18221955508d515c3b8da81c6a6..d2a7296c8251979b67be6a98640025c0181462c5 100644 (file)
@@ -501,6 +501,7 @@ int hrtimer_cancel(struct hrtimer *timer)
 
                if (ret >= 0)
                        return ret;
+               cpu_relax();
        }
 }
 
index 2b33f852be3eaf123aa63d530f2d58c5126a19c2..9f77f50d814317409f1ed02ce73372bfb428c99f 100644 (file)
@@ -1,4 +1,5 @@
 
-obj-y := handle.o manage.o spurious.o migration.o
+obj-y := handle.o manage.o spurious.o
 obj-$(CONFIG_GENERIC_IRQ_PROBE) += autoprobe.o
 obj-$(CONFIG_PROC_FS) += proc.o
+obj-$(CONFIG_GENERIC_PENDING_IRQ) += migration.o
index 52a8655fa080047a64cf3dc39635d28c2183abb7..134f9f2e0e3962cabf8859d6bc5581f9dfdfea16 100644 (file)
@@ -1,6 +1,5 @@
-#include <linux/irq.h>
 
-#if defined(CONFIG_GENERIC_PENDING_IRQ)
+#include <linux/irq.h>
 
 void set_pending_irq(unsigned int irq, cpumask_t mask)
 {
@@ -61,5 +60,3 @@ void move_native_irq(int irq)
        }
        cpus_clear(pending_irq_cpumask[irq]);
 }
-
-#endif
index 1156eb0977d04db06b1daeb926d776e87c34a5b7..1fbf466a29aab6ca0dfe1cf6e5d6ac16fba546d8 100644 (file)
@@ -585,6 +585,9 @@ int __kprobes register_kretprobe(struct kretprobe *rp)
        int i;
 
        rp->kp.pre_handler = pre_handler_kretprobe;
+       rp->kp.post_handler = NULL;
+       rp->kp.fault_handler = NULL;
+       rp->kp.break_handler = NULL;
 
        /* Pre-allocate memory for max kretprobe instances */
        if (rp->maxactive <= 0) {
index f895c7c01d5b18b4140dae5e35b284589380e481..cc2a4c9c36ac231781a41fba4031a17bc3b1f7e7 100644 (file)
@@ -27,7 +27,6 @@ static int pause_on_oops_flag;
 static DEFINE_SPINLOCK(pause_on_oops_lock);
 
 int panic_timeout;
-EXPORT_SYMBOL(panic_timeout);
 
 ATOMIC_NOTIFIER_HEAD(panic_notifier_list);
 
index 0f6908cce1dd230ab4e0dfa423b2fae1e030f040..84063ac8fcfc95bd15d56dc6778ec45bb503aa43 100644 (file)
@@ -75,25 +75,6 @@ struct pm_dev *pm_register(pm_dev_t type,
        return dev;
 }
 
-/**
- *     pm_unregister -  unregister a device with power management
- *     @dev: device to unregister
- *
- *     Remove a device from the power management notification lists. The
- *     dev passed must be a handle previously returned by pm_register.
- */
-void pm_unregister(struct pm_dev *dev)
-{
-       if (dev) {
-               mutex_lock(&pm_devs_lock);
-               list_del(&dev->entry);
-               mutex_unlock(&pm_devs_lock);
-
-               kfree(dev);
-       }
-}
-
 static void __pm_unregister(struct pm_dev *dev)
 {
        if (dev) {
@@ -258,7 +239,6 @@ int pm_send_all(pm_request_t rqst, void *data)
 }
 
 EXPORT_SYMBOL(pm_register);
-EXPORT_SYMBOL(pm_unregister);
 EXPORT_SYMBOL(pm_unregister_all);
 EXPORT_SYMBOL(pm_send_all);
 EXPORT_SYMBOL(pm_active);
index c5863d02c89efc08ef430752bb062f0aafcb4bc7..3eeedbb13b7864d525c6740a99156b433e3b6a51 100644 (file)
@@ -240,14 +240,15 @@ static void copy_data_pages(struct pbe *pblist)
  *     free_pagedir - free pages allocated with alloc_pagedir()
  */
 
-static void free_pagedir(struct pbe *pblist)
+static void free_pagedir(struct pbe *pblist, int clear_nosave_free)
 {
        struct pbe *pbe;
 
        while (pblist) {
                pbe = (pblist + PB_PAGE_SKIP)->next;
                ClearPageNosave(virt_to_page(pblist));
-               ClearPageNosaveFree(virt_to_page(pblist));
+               if (clear_nosave_free)
+                       ClearPageNosaveFree(virt_to_page(pblist));
                free_page((unsigned long)pblist);
                pblist = pbe;
        }
@@ -389,7 +390,7 @@ struct pbe *alloc_pagedir(unsigned int nr_pages, gfp_t gfp_mask, int safe_needed
                pbe->next = alloc_image_page(gfp_mask, safe_needed);
        }
        if (!pbe) { /* get_zeroed_page() failed */
-               free_pagedir(pblist);
+               free_pagedir(pblist, 1);
                pblist = NULL;
         } else
                create_pbe_list(pblist, nr_pages);
@@ -736,7 +737,7 @@ static int create_image(struct snapshot_handle *handle)
                pblist = alloc_pagedir(nr_copy_pages, GFP_ATOMIC, 1);
                if (pblist)
                        copy_page_backup_list(pblist, p);
-               free_pagedir(p);
+               free_pagedir(p, 0);
                if (!pblist)
                        error = -ENOMEM;
        }
index 0eeb7e66722c899fa2f53ee7b451d981aa91f6a3..4e0f0ec003f751a0aa91e2d8388365f042f072d9 100644 (file)
@@ -56,10 +56,6 @@ void ptrace_untrace(task_t *child)
                        signal_wake_up(child, 1);
                }
        }
-       if (child->signal->flags & SIGNAL_GROUP_EXIT) {
-               sigaddset(&child->pending.signal, SIGKILL);
-               signal_wake_up(child, 1);
-       }
        spin_unlock(&child->sighand->siglock);
 }
 
@@ -81,7 +77,8 @@ void __ptrace_unlink(task_t *child)
                add_parent(child);
        }
 
-       ptrace_untrace(child);
+       if (child->state == TASK_TRACED)
+               ptrace_untrace(child);
 }
 
 /*
index dd153d6f8a04b7c2ba8c4954b8628ef70ad307ce..365f0b90b4de534b628acb871ace309491672690 100644 (file)
@@ -664,6 +664,48 @@ static int effective_prio(task_t *p)
        return prio;
 }
 
+/*
+ * We place interactive tasks back into the active array, if possible.
+ *
+ * To guarantee that this does not starve expired tasks we ignore the
+ * interactivity of a task if the first expired task had to wait more
+ * than a 'reasonable' amount of time. This deadline timeout is
+ * load-dependent, as the frequency of array switched decreases with
+ * increasing number of running tasks. We also ignore the interactivity
+ * if a better static_prio task has expired, and switch periodically
+ * regardless, to ensure that highly interactive tasks do not starve
+ * the less fortunate for unreasonably long periods.
+ */
+static inline int expired_starving(runqueue_t *rq)
+{
+       int limit;
+
+       /*
+        * Arrays were recently switched, all is well
+        */
+       if (!rq->expired_timestamp)
+               return 0;
+
+       limit = STARVATION_LIMIT * rq->nr_running;
+
+       /*
+        * It's time to switch arrays
+        */
+       if (jiffies - rq->expired_timestamp >= limit)
+               return 1;
+
+       /*
+        * There's a better selection in the expired array
+        */
+       if (rq->curr->static_prio > rq->best_expired_prio)
+               return 1;
+
+       /*
+        * All is well
+        */
+       return 0;
+}
+
 /*
  * __activate_task - move a task to the runqueue.
  */
@@ -671,7 +713,7 @@ static void __activate_task(task_t *p, runqueue_t *rq)
 {
        prio_array_t *target = rq->active;
 
-       if (batch_task(p))
+       if (unlikely(batch_task(p) || (expired_starving(rq) && !rt_task(p))))
                target = rq->expired;
        enqueue_task(p, target);
        rq->nr_running++;
@@ -2489,22 +2531,6 @@ unsigned long long current_sched_time(const task_t *tsk)
        return ns;
 }
 
-/*
- * We place interactive tasks back into the active array, if possible.
- *
- * To guarantee that this does not starve expired tasks we ignore the
- * interactivity of a task if the first expired task had to wait more
- * than a 'reasonable' amount of time. This deadline timeout is
- * load-dependent, as the frequency of array switched decreases with
- * increasing number of running tasks. We also ignore the interactivity
- * if a better static_prio task has expired:
- */
-#define EXPIRED_STARVING(rq) \
-       ((STARVATION_LIMIT && ((rq)->expired_timestamp && \
-               (jiffies - (rq)->expired_timestamp >= \
-                       STARVATION_LIMIT * ((rq)->nr_running) + 1))) || \
-                       ((rq)->curr->static_prio > (rq)->best_expired_prio))
-
 /*
  * Account user cpu time to a process.
  * @p: the process that the cpu time gets accounted to
@@ -2640,7 +2666,7 @@ void scheduler_tick(void)
 
                if (!rq->expired_timestamp)
                        rq->expired_timestamp = jiffies;
-               if (!TASK_INTERACTIVE(p) || EXPIRED_STARVING(rq)) {
+               if (!TASK_INTERACTIVE(p) || expired_starving(rq)) {
                        enqueue_task(p, rq->expired);
                        if (p->static_prio < rq->best_expired_prio)
                                rq->best_expired_prio = p->static_prio;
index 5ccaac505e8dabd792eab331cf4e80bfa9a5f4cf..e5f8aea78ffebd71a1322ca8279321aac3b077e6 100644 (file)
@@ -868,7 +868,6 @@ __group_complete_signal(int sig, struct task_struct *p)
                if (t == NULL)
                        /* restart balancing at this thread */
                        t = p->signal->curr_target = p;
-               BUG_ON(t->tgid != p->tgid);
 
                while (!wants_signal(sig, t)) {
                        t = next_thread(t);
@@ -1755,9 +1754,9 @@ relock:
                        /* Let the debugger run.  */
                        ptrace_stop(signr, signr, info);
 
-                       /* We're back.  Did the debugger cancel the sig or group_exit? */
+                       /* We're back.  Did the debugger cancel the sig */
                        signr = current->exit_code;
-                       if (signr == 0 || current->signal->flags & SIGNAL_GROUP_EXIT)
+                       if (signr == 0)
                                continue;
 
                        current->exit_code = 0;
index d82864c4a6178fd48716a0c642745b01794562d1..5433195040f195ea8ec71f83fd34c775346c1c68 100644 (file)
@@ -120,3 +120,15 @@ cond_syscall(sys32_sysctl);
 cond_syscall(ppc_rtas);
 cond_syscall(sys_spu_run);
 cond_syscall(sys_spu_create);
+
+/* mmu depending weak syscall entries */
+cond_syscall(sys_mprotect);
+cond_syscall(sys_msync);
+cond_syscall(sys_mlock);
+cond_syscall(sys_munlock);
+cond_syscall(sys_mlockall);
+cond_syscall(sys_munlockall);
+cond_syscall(sys_mincore);
+cond_syscall(sys_madvise);
+cond_syscall(sys_mremap);
+cond_syscall(sys_remap_file_pages);
index c3a874f1393cd95d859267ed783a9edde8a8ff71..8837737888361960307a2931177bd2a7d66631e7 100644 (file)
@@ -81,9 +81,10 @@ struct tvec_t_base_s {
 } ____cacheline_aligned_in_smp;
 
 typedef struct tvec_t_base_s tvec_base_t;
-static DEFINE_PER_CPU(tvec_base_t *, tvec_bases);
+
 tvec_base_t boot_tvec_bases;
 EXPORT_SYMBOL(boot_tvec_bases);
+static DEFINE_PER_CPU(tvec_base_t *, tvec_bases) = { &boot_tvec_bases };
 
 static inline void set_running_timer(tvec_base_t *base,
                                        struct timer_list *timer)
@@ -1224,28 +1225,36 @@ static int __devinit init_timers_cpu(int cpu)
 {
        int j;
        tvec_base_t *base;
+       static char __devinitdata tvec_base_done[NR_CPUS];
 
-       base = per_cpu(tvec_bases, cpu);
-       if (!base) {
+       if (!tvec_base_done[cpu]) {
                static char boot_done;
 
-               /*
-                * Cannot do allocation in init_timers as that runs before the
-                * allocator initializes (and would waste memory if there are
-                * more possible CPUs than will ever be installed/brought up).
-                */
                if (boot_done) {
+                       /*
+                        * The APs use this path later in boot
+                        */
                        base = kmalloc_node(sizeof(*base), GFP_KERNEL,
                                                cpu_to_node(cpu));
                        if (!base)
                                return -ENOMEM;
                        memset(base, 0, sizeof(*base));
+                       per_cpu(tvec_bases, cpu) = base;
                } else {
-                       base = &boot_tvec_bases;
+                       /*
+                        * This is for the boot CPU - we use compile-time
+                        * static initialisation because per-cpu memory isn't
+                        * ready yet and because the memory allocators are not
+                        * initialised either.
+                        */
                        boot_done = 1;
+                       base = &boot_tvec_bases;
                }
-               per_cpu(tvec_bases, cpu) = base;
+               tvec_base_done[cpu] = 1;
+       } else {
+               base = per_cpu(tvec_bases, cpu);
        }
+
        spin_lock_init(&base->lock);
        for (j = 0; j < TVN_SIZE; j++) {
                INIT_LIST_HEAD(base->tv5.vec + j);
@@ -1455,7 +1464,7 @@ static void time_interpolator_update(long delta_nsec)
         */
        if (jiffies % INTERPOLATOR_ADJUST == 0)
        {
-               if (time_interpolator->skips == 0 && time_interpolator->offset > TICK_NSEC)
+               if (time_interpolator->skips == 0 && time_interpolator->offset > tick_nsec)
                        time_interpolator->nsec_per_cyc--;
                if (time_interpolator->ns_skipped > INTERPOLATOR_MAX_SKIP && time_interpolator->offset == 0)
                        time_interpolator->nsec_per_cyc++;
index aa25605027c8eb19c682cd6efec17b0d79073451..187e2a423878229b53e7c5310946621274901bf7 100644 (file)
 
 asmlinkage long sys_chown16(const char __user * filename, old_uid_t user, old_gid_t group)
 {
-       return sys_chown(filename, low2highuid(user), low2highgid(group));
+       long ret = sys_chown(filename, low2highuid(user), low2highgid(group));
+       /* avoid REGPARM breakage on x86: */
+       prevent_tail_call(ret);
+       return ret;
 }
 
 asmlinkage long sys_lchown16(const char __user * filename, old_uid_t user, old_gid_t group)
 {
-       return sys_lchown(filename, low2highuid(user), low2highgid(group));
+       long ret = sys_lchown(filename, low2highuid(user), low2highgid(group));
+       /* avoid REGPARM breakage on x86: */
+       prevent_tail_call(ret);
+       return ret;
 }
 
 asmlinkage long sys_fchown16(unsigned int fd, old_uid_t user, old_gid_t group)
 {
-       return sys_fchown(fd, low2highuid(user), low2highgid(group));
+       long ret = sys_fchown(fd, low2highuid(user), low2highgid(group));
+       /* avoid REGPARM breakage on x86: */
+       prevent_tail_call(ret);
+       return ret;
 }
 
 asmlinkage long sys_setregid16(old_gid_t rgid, old_gid_t egid)
 {
-       return sys_setregid(low2highgid(rgid), low2highgid(egid));
+       long ret = sys_setregid(low2highgid(rgid), low2highgid(egid));
+       /* avoid REGPARM breakage on x86: */
+       prevent_tail_call(ret);
+       return ret;
 }
 
 asmlinkage long sys_setgid16(old_gid_t gid)
 {
-       return sys_setgid(low2highgid(gid));
+       long ret = sys_setgid(low2highgid(gid));
+       /* avoid REGPARM breakage on x86: */
+       prevent_tail_call(ret);
+       return ret;
 }
 
 asmlinkage long sys_setreuid16(old_uid_t ruid, old_uid_t euid)
 {
-       return sys_setreuid(low2highuid(ruid), low2highuid(euid));
+       long ret = sys_setreuid(low2highuid(ruid), low2highuid(euid));
+       /* avoid REGPARM breakage on x86: */
+       prevent_tail_call(ret);
+       return ret;
 }
 
 asmlinkage long sys_setuid16(old_uid_t uid)
 {
-       return sys_setuid(low2highuid(uid));
+       long ret = sys_setuid(low2highuid(uid));
+       /* avoid REGPARM breakage on x86: */
+       prevent_tail_call(ret);
+       return ret;
 }
 
 asmlinkage long sys_setresuid16(old_uid_t ruid, old_uid_t euid, old_uid_t suid)
 {
-       return sys_setresuid(low2highuid(ruid), low2highuid(euid),
-               low2highuid(suid));
+       long ret = sys_setresuid(low2highuid(ruid), low2highuid(euid),
+                                low2highuid(suid));
+       /* avoid REGPARM breakage on x86: */
+       prevent_tail_call(ret);
+       return ret;
 }
 
 asmlinkage long sys_getresuid16(old_uid_t __user *ruid, old_uid_t __user *euid, old_uid_t __user *suid)
@@ -72,8 +96,11 @@ asmlinkage long sys_getresuid16(old_uid_t __user *ruid, old_uid_t __user *euid,
 
 asmlinkage long sys_setresgid16(old_gid_t rgid, old_gid_t egid, old_gid_t sgid)
 {
-       return sys_setresgid(low2highgid(rgid), low2highgid(egid),
-               low2highgid(sgid));
+       long ret = sys_setresgid(low2highgid(rgid), low2highgid(egid),
+                                low2highgid(sgid));
+       /* avoid REGPARM breakage on x86: */
+       prevent_tail_call(ret);
+       return ret;
 }
 
 asmlinkage long sys_getresgid16(old_gid_t __user *rgid, old_gid_t __user *egid, old_gid_t __user *sgid)
@@ -89,12 +116,18 @@ asmlinkage long sys_getresgid16(old_gid_t __user *rgid, old_gid_t __user *egid,
 
 asmlinkage long sys_setfsuid16(old_uid_t uid)
 {
-       return sys_setfsuid(low2highuid(uid));
+       long ret = sys_setfsuid(low2highuid(uid));
+       /* avoid REGPARM breakage on x86: */
+       prevent_tail_call(ret);
+       return ret;
 }
 
 asmlinkage long sys_setfsgid16(old_gid_t gid)
 {
-       return sys_setfsgid(low2highgid(gid));
+       long ret = sys_setfsgid(low2highgid(gid));
+       /* avoid REGPARM breakage on x86: */
+       prevent_tail_call(ret);
+       return ret;
 }
 
 static int groups16_to_user(old_gid_t __user *grouplist,
index d57fd9181b187ed07856ae0bb845bcc6e93a006b..6ecc180beb7145c5c649f36bc2b7961eab7af13e 100644 (file)
@@ -101,7 +101,7 @@ config DEBUG_PREEMPT
 
 config DEBUG_MUTEXES
        bool "Mutex debugging, deadlock detection"
-       default y
+       default n
        depends on DEBUG_KERNEL
        help
         This allows mutex semantics violations and mutex related deadlocks
index 25204a41a9b01d5764ccdeffba064af81e584c05..01d9575139408bf2a697b4683bd2183ea7cd104c 100644 (file)
@@ -128,6 +128,7 @@ void kobject_init(struct kobject * kobj)
 {
        kref_init(&kobj->kref);
        INIT_LIST_HEAD(&kobj->entry);
+       init_waitqueue_head(&kobj->poll);
        kobj->kset = kset_get(kobj->kset);
 }
 
index b3c28a3f63322ff528a38df4895020c257b20050..064f6315b1c3e16c731117a7e1aa185a5b2bd405 100644 (file)
@@ -362,6 +362,7 @@ size_t strspn(const char *s, const char *accept)
 EXPORT_SYMBOL(strspn);
 #endif
 
+#ifndef __HAVE_ARCH_STRCSPN
 /**
  * strcspn - Calculate the length of the initial substring of @s which does
  *     not contain letters in @reject
@@ -384,6 +385,7 @@ size_t strcspn(const char *s, const char *reject)
        return count;
 }
 EXPORT_SYMBOL(strcspn);
+#endif
 
 #ifndef __HAVE_ARCH_STRPBRK
 /**
@@ -403,6 +405,7 @@ char *strpbrk(const char *cs, const char *ct)
        }
        return NULL;
 }
+EXPORT_SYMBOL(strpbrk);
 #endif
 
 #ifndef __HAVE_ARCH_STRSEP
@@ -467,7 +470,7 @@ EXPORT_SYMBOL(memset);
 void *memcpy(void *dest, const void *src, size_t count)
 {
        char *tmp = dest;
-       char *s = src;
+       const char *s = src;
 
        while (count--)
                *tmp++ = *s++;
index d3e3bd2ffceacc4adfaea34e40fc537fce762b04..d213feded10df30d04fedd2e744fc89ab3f6f934 100644 (file)
@@ -401,7 +401,7 @@ unsigned long __init free_all_bootmem (void)
        return(free_all_bootmem_core(NODE_DATA(0)));
 }
 
-void * __init __alloc_bootmem(unsigned long size, unsigned long align, unsigned long goal)
+void * __init __alloc_bootmem_nopanic(unsigned long size, unsigned long align, unsigned long goal)
 {
        bootmem_data_t *bdata;
        void *ptr;
@@ -409,7 +409,14 @@ void * __init __alloc_bootmem(unsigned long size, unsigned long align, unsigned
        list_for_each_entry(bdata, &bdata_list, list)
                if ((ptr = __alloc_bootmem_core(bdata, size, align, goal, 0)))
                        return(ptr);
+       return NULL;
+}
 
+void * __init __alloc_bootmem(unsigned long size, unsigned long align, unsigned long goal)
+{
+       void *mem = __alloc_bootmem_nopanic(size,align,goal);
+       if (mem)
+               return mem;
        /*
         * Whoops, we cannot satisfy the allocation request.
         */
index af3d573b014122f7fd2a99c3ee90c3826f70457f..4e196155a0c3635801bd0f8dcff0b18ce1bbcf37 100644 (file)
@@ -168,6 +168,9 @@ static long madvise_remove(struct vm_area_struct *vma,
                        return -EINVAL;
        }
 
+       if ((vma->vm_flags & (VM_SHARED|VM_WRITE)) != (VM_SHARED|VM_WRITE))
+               return -EACCES;
+
        mapping = vma->vm_file->f_mapping;
 
        offset = (loff_t)(start - vma->vm_start)
index dec8249e972de3cdae046203b16ef32d25d1cda9..8778f58880c41c55cab9a2de035e960379b0cfe4 100644 (file)
@@ -1761,7 +1761,6 @@ static void gather_stats(struct page *page, void *private, int pte_dirty)
                md->mapcount_max = count;
 
        md->node[page_to_nid(page)]++;
-       cond_resched();
 }
 
 #ifdef CONFIG_HUGETLB_PAGE
index 09f6e4aa87fc493f1c4c7accf27ab0280d2b7c01..d444229f2599245e1cb0d904e7cdfed11db88b7a 100644 (file)
@@ -16,8 +16,7 @@
 #include <linux/module.h>
 #include <linux/swap.h>
 #include <linux/pagemap.h>
-#include <linux/buffer_head.h> /* for try_to_release_page(),
-                                       buffer_heads_over_limit */
+#include <linux/buffer_head.h>
 #include <linux/mm_inline.h>
 #include <linux/pagevec.h>
 #include <linux/rmap.h>
@@ -28,8 +27,6 @@
 
 #include "internal.h"
 
-#include "internal.h"
-
 /* The maximum number of pages to take off the LRU for migration */
 #define MIGRATE_CHUNK_SIZE 256
 
@@ -176,7 +173,6 @@ unlock_retry:
 retry:
        return -EAGAIN;
 }
-EXPORT_SYMBOL(swap_page);
 
 /*
  * Remove references for a page and establish the new page with the correct
@@ -234,7 +230,7 @@ int migrate_page_remove_references(struct page *newpage,
        if (!page_mapping(page) || page_count(page) != nr_refs ||
                        *radix_pointer != page) {
                write_unlock_irq(&mapping->tree_lock);
-               return 1;
+               return -EAGAIN;
        }
 
        /*
index e780d19aa21447df1b48d92273276700cf2b56f4..e6ee12344b139274325a1db834da1de6cf334da1 100644 (file)
--- a/mm/mmap.c
+++ b/mm/mmap.c
@@ -121,14 +121,26 @@ int __vm_enough_memory(long pages, int cap_sys_admin)
                 * only call if we're about to fail.
                 */
                n = nr_free_pages();
+
+               /*
+                * Leave reserved pages. The pages are not for anonymous pages.
+                */
+               if (n <= totalreserve_pages)
+                       goto error;
+               else
+                       n -= totalreserve_pages;
+
+               /*
+                * Leave the last 3% for root
+                */
                if (!cap_sys_admin)
                        n -= n / 32;
                free += n;
 
                if (free > pages)
                        return 0;
-               vm_unacct_memory(pages);
-               return -ENOMEM;
+
+               goto error;
        }
 
        allowed = (totalram_pages - hugetlb_total_pages())
@@ -150,7 +162,7 @@ int __vm_enough_memory(long pages, int cap_sys_admin)
         */
        if (atomic_read(&vm_committed_space) < (long)allowed)
                return 0;
-
+error:
        vm_unacct_memory(pages);
 
        return -ENOMEM;
@@ -220,6 +232,17 @@ asmlinkage unsigned long sys_brk(unsigned long brk)
 
        if (brk < mm->end_code)
                goto out;
+
+       /*
+        * Check against rlimit here. If this check is done later after the test
+        * of oldbrk with newbrk then it can escape the test and let the data
+        * segment grow beyond its set limit the in case where the limit is
+        * not page aligned -Ram Gupta
+        */
+       rlim = current->signal->rlim[RLIMIT_DATA].rlim_cur;
+       if (rlim < RLIM_INFINITY && brk - mm->start_data > rlim)
+               goto out;
+
        newbrk = PAGE_ALIGN(brk);
        oldbrk = PAGE_ALIGN(mm->brk);
        if (oldbrk == newbrk)
@@ -232,11 +255,6 @@ asmlinkage unsigned long sys_brk(unsigned long brk)
                goto out;
        }
 
-       /* Check against rlimit.. */
-       rlim = current->signal->rlim[RLIMIT_DATA].rlim_cur;
-       if (rlim < RLIM_INFINITY && brk - mm->start_data > rlim)
-               goto out;
-
        /* Check against existing mmap mappings. */
        if (find_vma_intersection(mm, oldbrk, newbrk+PAGE_SIZE))
                goto out;
index db45efac17cc218e390dd4a8b6d8366219c546a3..029fadac0fb5d1d6f89f5ddbd216ccb4004e5804 100644 (file)
@@ -1147,14 +1147,26 @@ int __vm_enough_memory(long pages, int cap_sys_admin)
                 * only call if we're about to fail.
                 */
                n = nr_free_pages();
+
+               /*
+                * Leave reserved pages. The pages are not for anonymous pages.
+                */
+               if (n <= totalreserve_pages)
+                       goto error;
+               else
+                       n -= totalreserve_pages;
+
+               /*
+                * Leave the last 3% for root
+                */
                if (!cap_sys_admin)
                        n -= n / 32;
                free += n;
 
                if (free > pages)
                        return 0;
-               vm_unacct_memory(pages);
-               return -ENOMEM;
+
+               goto error;
        }
 
        allowed = totalram_pages * sysctl_overcommit_ratio / 100;
@@ -1175,7 +1187,7 @@ int __vm_enough_memory(long pages, int cap_sys_admin)
         */
        if (atomic_read(&vm_committed_space) < (long)allowed)
                return 0;
-
+error:
        vm_unacct_memory(pages);
 
        return -ENOMEM;
index 78747afad6b0d6e2b2a2e0c08075e9911c8b85c6..042e6436c3ee8db6548a687dc289a207f2c43fd6 100644 (file)
 unsigned long badness(struct task_struct *p, unsigned long uptime)
 {
        unsigned long points, cpu_time, run_time, s;
-       struct list_head *tsk;
+       struct mm_struct *mm;
+       struct task_struct *child;
 
-       if (!p->mm)
+       task_lock(p);
+       mm = p->mm;
+       if (!mm) {
+               task_unlock(p);
                return 0;
+       }
 
        /*
         * The memory size of the process is the basis for the badness.
         */
-       points = p->mm->total_vm;
+       points = mm->total_vm;
+
+       /*
+        * After this unlock we can no longer dereference local variable `mm'
+        */
+       task_unlock(p);
 
        /*
         * Processes which fork a lot of child processes are likely
@@ -64,11 +74,11 @@ unsigned long badness(struct task_struct *p, unsigned long uptime)
         * child is eating the vast majority of memory, adding only half
         * to the parents will make the child our kill candidate of choice.
         */
-       list_for_each(tsk, &p->children) {
-               struct task_struct *chld;
-               chld = list_entry(tsk, struct task_struct, sibling);
-               if (chld->mm != p->mm && chld->mm)
-                       points += chld->mm->total_vm/2 + 1;
+       list_for_each_entry(child, &p->children, sibling) {
+               task_lock(child);
+               if (child->mm != mm && child->mm)
+                       points += child->mm->total_vm/2 + 1;
+               task_unlock(child);
        }
 
        /*
@@ -244,17 +254,24 @@ static void __oom_kill_task(task_t *p, const char *message)
        force_sig(SIGKILL, p);
 }
 
-static struct mm_struct *oom_kill_task(task_t *p, const char *message)
+static int oom_kill_task(task_t *p, const char *message)
 {
-       struct mm_struct *mm = get_task_mm(p);
+       struct mm_struct *mm;
        task_t * g, * q;
 
-       if (!mm)
-               return NULL;
-       if (mm == &init_mm) {
-               mmput(mm);
-               return NULL;
-       }
+       mm = p->mm;
+
+       /* WARNING: mm may not be dereferenced since we did not obtain its
+        * value from get_task_mm(p).  This is OK since all we need to do is
+        * compare mm to q->mm below.
+        *
+        * Furthermore, even if mm contains a non-NULL value, p->mm may
+        * change to NULL at any time since we do not hold task_lock(p).
+        * However, this is of no concern to us.
+        */
+
+       if (mm == NULL || mm == &init_mm)
+               return 1;
 
        __oom_kill_task(p, message);
        /*
@@ -266,13 +283,12 @@ static struct mm_struct *oom_kill_task(task_t *p, const char *message)
                        __oom_kill_task(q, message);
        while_each_thread(g, q);
 
-       return mm;
+       return 0;
 }
 
-static struct mm_struct *oom_kill_process(struct task_struct *p,
-                               unsigned long points, const char *message)
+static int oom_kill_process(struct task_struct *p, unsigned long points,
+               const char *message)
 {
-       struct mm_struct *mm;
        struct task_struct *c;
        struct list_head *tsk;
 
@@ -283,9 +299,8 @@ static struct mm_struct *oom_kill_process(struct task_struct *p,
                c = list_entry(tsk, struct task_struct, sibling);
                if (c->mm == p->mm)
                        continue;
-               mm = oom_kill_task(c, message);
-               if (mm)
-                       return mm;
+               if (!oom_kill_task(c, message))
+                       return 0;
        }
        return oom_kill_task(p, message);
 }
@@ -300,7 +315,6 @@ static struct mm_struct *oom_kill_process(struct task_struct *p,
  */
 void out_of_memory(struct zonelist *zonelist, gfp_t gfp_mask, int order)
 {
-       struct mm_struct *mm = NULL;
        task_t *p;
        unsigned long points = 0;
 
@@ -320,12 +334,12 @@ void out_of_memory(struct zonelist *zonelist, gfp_t gfp_mask, int order)
         */
        switch (constrained_alloc(zonelist, gfp_mask)) {
        case CONSTRAINT_MEMORY_POLICY:
-               mm = oom_kill_process(current, points,
+               oom_kill_process(current, points,
                                "No available memory (MPOL_BIND)");
                break;
 
        case CONSTRAINT_CPUSET:
-               mm = oom_kill_process(current, points,
+               oom_kill_process(current, points,
                                "No available memory in cpuset");
                break;
 
@@ -347,8 +361,7 @@ retry:
                        panic("Out of memory and no killable processes...\n");
                }
 
-               mm = oom_kill_process(p, points, "Out of memory");
-               if (!mm)
+               if (oom_kill_process(p, points, "Out of memory"))
                        goto retry;
 
                break;
@@ -357,8 +370,6 @@ retry:
 out:
        read_unlock(&tasklist_lock);
        cpuset_unlock();
-       if (mm)
-               mmput(mm);
 
        /*
         * Give "p" a good chance of killing itself before we
index 6dcce3a4bbdc6eff21c99607c463bdb15cccd752..75d7f48b79bba537d522cbd709138d48196d6782 100644 (file)
@@ -72,13 +72,12 @@ int dirty_background_ratio = 10;
 int vm_dirty_ratio = 40;
 
 /*
- * The interval between `kupdate'-style writebacks, in centiseconds
- * (hundredths of a second)
+ * The interval between `kupdate'-style writebacks, in jiffies
  */
 int dirty_writeback_interval = 5 * HZ;
 
 /*
- * The longest number of centiseconds for which data is allowed to remain dirty
+ * The longest number of jiffies for which data is allowed to remain dirty
  */
 int dirty_expire_interval = 30 * HZ;
 
index dc523a1f270db11ad4930fa47548232c14e6e4ad..123c605867404ecfc00ef0d19a8a65d852ed0be0 100644 (file)
@@ -51,6 +51,7 @@ nodemask_t node_possible_map __read_mostly = NODE_MASK_ALL;
 EXPORT_SYMBOL(node_possible_map);
 unsigned long totalram_pages __read_mostly;
 unsigned long totalhigh_pages __read_mostly;
+unsigned long totalreserve_pages __read_mostly;
 long nr_swap_pages;
 int percpu_pagelist_fraction;
 
@@ -151,7 +152,8 @@ static void bad_page(struct page *page)
                        1 << PG_reclaim |
                        1 << PG_slab    |
                        1 << PG_swapcache |
-                       1 << PG_writeback );
+                       1 << PG_writeback |
+                       1 << PG_buddy );
        set_page_count(page, 0);
        reset_page_mapcount(page);
        page->mapping = NULL;
@@ -230,18 +232,20 @@ static inline void prep_zero_page(struct page *page, int order, gfp_t gfp_flags)
  * zone->lock is already acquired when we use these.
  * So, we don't need atomic page->flags operations here.
  */
-static inline unsigned long page_order(struct page *page) {
+static inline unsigned long page_order(struct page *page)
+{
        return page_private(page);
 }
 
-static inline void set_page_order(struct page *page, int order) {
+static inline void set_page_order(struct page *page, int order)
+{
        set_page_private(page, order);
-       __SetPagePrivate(page);
+       __SetPageBuddy(page);
 }
 
 static inline void rmv_page_order(struct page *page)
 {
-       __ClearPagePrivate(page);
+       __ClearPageBuddy(page);
        set_page_private(page, 0);
 }
 
@@ -280,11 +284,13 @@ __find_combined_index(unsigned long page_idx, unsigned int order)
  * This function checks whether a page is free && is the buddy
  * we can do coalesce a page and its buddy if
  * (a) the buddy is not in a hole &&
- * (b) the buddy is free &&
- * (c) the buddy is on the buddy system &&
- * (d) a page and its buddy have the same order.
- * for recording page's order, we use page_private(page) and PG_private.
+ * (b) the buddy is in the buddy system &&
+ * (c) a page and its buddy have the same order.
  *
+ * For recording whether a page is in the buddy system, we use PG_buddy.
+ * Setting, clearing, and testing PG_buddy is serialized by zone->lock.
+ *
+ * For recording page's order, we use page_private(page).
  */
 static inline int page_is_buddy(struct page *page, int order)
 {
@@ -293,11 +299,11 @@ static inline int page_is_buddy(struct page *page, int order)
                return 0;
 #endif
 
-       if (PagePrivate(page)           &&
-           (page_order(page) == order) &&
-            page_count(page) == 0)
-               return 1;
-       return 0;
+       if (PageBuddy(page) && page_order(page) == order) {
+               BUG_ON(page_count(page) != 0);
+               return 1;
+       }
+       return 0;
 }
 
 /*
@@ -313,7 +319,7 @@ static inline int page_is_buddy(struct page *page, int order)
  * as necessary, plus some accounting needed to play nicely with other
  * parts of the VM system.
  * At each level, we keep a list of pages, which are heads of continuous
- * free pages of length of (1 << order) and marked with PG_Private.Page's
+ * free pages of length of (1 << order) and marked with PG_buddy. Page's
  * order is recorded in page_private(page) field.
  * So when we are allocating or freeing one, we can derive the state of the
  * other.  That is, if we allocate a small block, and both were   
@@ -376,7 +382,8 @@ static inline int free_pages_check(struct page *page)
                        1 << PG_slab    |
                        1 << PG_swapcache |
                        1 << PG_writeback |
-                       1 << PG_reserved ))))
+                       1 << PG_reserved |
+                       1 << PG_buddy ))))
                bad_page(page);
        if (PageDirty(page))
                __ClearPageDirty(page);
@@ -524,7 +531,8 @@ static int prep_new_page(struct page *page, int order, gfp_t gfp_flags)
                        1 << PG_slab    |
                        1 << PG_swapcache |
                        1 << PG_writeback |
-                       1 << PG_reserved ))))
+                       1 << PG_reserved |
+                       1 << PG_buddy ))))
                bad_page(page);
 
        /*
@@ -2471,6 +2479,38 @@ void __init page_alloc_init(void)
        hotcpu_notifier(page_alloc_cpu_notify, 0);
 }
 
+/*
+ * calculate_totalreserve_pages - called when sysctl_lower_zone_reserve_ratio
+ *     or min_free_kbytes changes.
+ */
+static void calculate_totalreserve_pages(void)
+{
+       struct pglist_data *pgdat;
+       unsigned long reserve_pages = 0;
+       int i, j;
+
+       for_each_online_pgdat(pgdat) {
+               for (i = 0; i < MAX_NR_ZONES; i++) {
+                       struct zone *zone = pgdat->node_zones + i;
+                       unsigned long max = 0;
+
+                       /* Find valid and maximum lowmem_reserve in the zone */
+                       for (j = i; j < MAX_NR_ZONES; j++) {
+                               if (zone->lowmem_reserve[j] > max)
+                                       max = zone->lowmem_reserve[j];
+                       }
+
+                       /* we treat pages_high as reserved pages. */
+                       max += zone->pages_high;
+
+                       if (max > zone->present_pages)
+                               max = zone->present_pages;
+                       reserve_pages += max;
+               }
+       }
+       totalreserve_pages = reserve_pages;
+}
+
 /*
  * setup_per_zone_lowmem_reserve - called whenever
  *     sysctl_lower_zone_reserve_ratio changes.  Ensures that each zone
@@ -2502,6 +2542,9 @@ static void setup_per_zone_lowmem_reserve(void)
                        }
                }
        }
+
+       /* update totalreserve_pages */
+       calculate_totalreserve_pages();
 }
 
 /*
@@ -2556,6 +2599,9 @@ void setup_per_zone_pages_min(void)
                zone->pages_high  = zone->pages_min + tmp / 2;
                spin_unlock_irqrestore(&zone->lru_lock, flags);
        }
+
+       /* update totalreserve_pages */
+       calculate_totalreserve_pages();
 }
 
 /*
index f055c14202161a7b561599536cfb269240bbd1dc..e6ef9bd52335bac10026972cb177f5de97eee817 100644 (file)
--- a/mm/slab.c
+++ b/mm/slab.c
@@ -420,6 +420,7 @@ struct kmem_cache {
        unsigned long max_freeable;
        unsigned long node_allocs;
        unsigned long node_frees;
+       unsigned long node_overflow;
        atomic_t allochit;
        atomic_t allocmiss;
        atomic_t freehit;
@@ -465,6 +466,7 @@ struct kmem_cache {
 #define        STATS_INC_ERR(x)        ((x)->errors++)
 #define        STATS_INC_NODEALLOCS(x) ((x)->node_allocs++)
 #define        STATS_INC_NODEFREES(x)  ((x)->node_frees++)
+#define STATS_INC_ACOVERFLOW(x)   ((x)->node_overflow++)
 #define        STATS_SET_FREEABLE(x, i)                                        \
        do {                                                            \
                if ((x)->max_freeable < i)                              \
@@ -484,6 +486,7 @@ struct kmem_cache {
 #define        STATS_INC_ERR(x)        do { } while (0)
 #define        STATS_INC_NODEALLOCS(x) do { } while (0)
 #define        STATS_INC_NODEFREES(x)  do { } while (0)
+#define STATS_INC_ACOVERFLOW(x)   do { } while (0)
 #define        STATS_SET_FREEABLE(x, i) do { } while (0)
 #define STATS_INC_ALLOCHIT(x)  do { } while (0)
 #define STATS_INC_ALLOCMISS(x) do { } while (0)
@@ -1453,7 +1456,14 @@ static void *kmem_getpages(struct kmem_cache *cachep, gfp_t flags, int nodeid)
        int i;
 
        flags |= cachep->gfpflags;
+#ifndef CONFIG_MMU
+       /* nommu uses slab's for process anonymous memory allocations, so
+        * requires __GFP_COMP to properly refcount higher order allocations"
+        */
+       page = alloc_pages_node(nodeid, (flags | __GFP_COMP), cachep->gfporder);
+#else
        page = alloc_pages_node(nodeid, flags, cachep->gfporder);
+#endif
        if (!page)
                return NULL;
        addr = page_address(page);
@@ -2318,13 +2328,15 @@ EXPORT_SYMBOL(kmem_cache_destroy);
 
 /* Get the memory for a slab management obj. */
 static struct slab *alloc_slabmgmt(struct kmem_cache *cachep, void *objp,
-                                  int colour_off, gfp_t local_flags)
+                                  int colour_off, gfp_t local_flags,
+                                  int nodeid)
 {
        struct slab *slabp;
 
        if (OFF_SLAB(cachep)) {
                /* Slab management obj is off-slab. */
-               slabp = kmem_cache_alloc(cachep->slabp_cache, local_flags);
+               slabp = kmem_cache_alloc_node(cachep->slabp_cache,
+                                             local_flags, nodeid);
                if (!slabp)
                        return NULL;
        } else {
@@ -2334,6 +2346,7 @@ static struct slab *alloc_slabmgmt(struct kmem_cache *cachep, void *objp,
        slabp->inuse = 0;
        slabp->colouroff = colour_off;
        slabp->s_mem = objp + colour_off;
+       slabp->nodeid = nodeid;
        return slabp;
 }
 
@@ -2519,7 +2532,7 @@ static int cache_grow(struct kmem_cache *cachep, gfp_t flags, int nodeid)
                goto failed;
 
        /* Get slab management. */
-       slabp = alloc_slabmgmt(cachep, objp, offset, local_flags);
+       slabp = alloc_slabmgmt(cachep, objp, offset, local_flags, nodeid);
        if (!slabp)
                goto opps1;
 
@@ -3080,9 +3093,11 @@ static inline void __cache_free(struct kmem_cache *cachep, void *objp)
                        if (l3->alien && l3->alien[nodeid]) {
                                alien = l3->alien[nodeid];
                                spin_lock(&alien->lock);
-                               if (unlikely(alien->avail == alien->limit))
+                               if (unlikely(alien->avail == alien->limit)) {
+                                       STATS_INC_ACOVERFLOW(cachep);
                                        __drain_alien_cache(cachep,
                                                            alien, nodeid);
+                               }
                                alien->entry[alien->avail++] = objp;
                                spin_unlock(&alien->lock);
                        } else {
@@ -3760,7 +3775,7 @@ static void print_slabinfo_header(struct seq_file *m)
        seq_puts(m, " : slabdata <active_slabs> <num_slabs> <sharedavail>");
 #if STATS
        seq_puts(m, " : globalstat <listallocs> <maxobjs> <grown> <reaped> "
-                "<error> <maxfreeable> <nodeallocs> <remotefrees>");
+                "<error> <maxfreeable> <nodeallocs> <remotefrees> <alienoverflow>");
        seq_puts(m, " : cpustat <allochit> <allocmiss> <freehit> <freemiss>");
 #endif
        seq_putc(m, '\n');
@@ -3874,11 +3889,12 @@ static int s_show(struct seq_file *m, void *p)
                unsigned long max_freeable = cachep->max_freeable;
                unsigned long node_allocs = cachep->node_allocs;
                unsigned long node_frees = cachep->node_frees;
+               unsigned long overflows = cachep->node_overflow;
 
                seq_printf(m, " : globalstat %7lu %6lu %5lu %4lu \
-                               %4lu %4lu %4lu %4lu", allocs, high, grown,
+                               %4lu %4lu %4lu %4lu %4lu", allocs, high, grown,
                                reaped, errors, max_freeable, node_allocs,
-                               node_frees);
+                               node_frees, overflows);
        }
        /* cpu stats */
        {
index 9bcc7e2cabfd4d5b9147b8547a34e6dd0594a629..a68255ba4553770f7c4050857a11661160ea3942 100644 (file)
--- a/mm/slob.c
+++ b/mm/slob.c
@@ -354,9 +354,7 @@ void *__alloc_percpu(size_t size)
        if (!pdata)
                return NULL;
 
-       for (i = 0; i < NR_CPUS; i++) {
-               if (!cpu_possible(i))
-                       continue;
+       for_each_possible_cpu(i) {
                pdata->ptrs[i] = kmalloc(size, GFP_KERNEL);
                if (!pdata->ptrs[i])
                        goto unwind_oom;
@@ -383,11 +381,9 @@ free_percpu(const void *objp)
        int i;
        struct percpu_data *p = (struct percpu_data *) (~(unsigned long) objp);
 
-       for (i = 0; i < NR_CPUS; i++) {
-               if (!cpu_possible(i))
-                       continue;
+       for_each_possible_cpu(i)
                kfree(p->ptrs[i]);
-       }
+
        kfree(p);
 }
 EXPORT_SYMBOL(free_percpu);
index 3ab4e7947bab38435755b6cfad29cabf31c46701..1a786bfaa416c8d6972ef974dd31577caf14cc9e 100644 (file)
@@ -2,7 +2,6 @@
 
 /* Written 1995-2000 by Werner Almesberger, EPFL LRC/ICA */
 
-
 #include <linux/config.h>
 #include <linux/string.h>
 #include <linux/errno.h>
@@ -54,24 +53,24 @@ static struct net_device *clip_devs;
 static struct atm_vcc *atmarpd;
 static struct neigh_table clip_tbl;
 static struct timer_list idle_timer;
-static int start_timer = 1;
-
 
-static int to_atmarpd(enum atmarp_ctrl_type type,int itf,unsigned long ip)
+static int to_atmarpd(enum atmarp_ctrl_type type, int itf, unsigned long ip)
 {
        struct sock *sk;
        struct atmarp_ctrl *ctrl;
        struct sk_buff *skb;
 
-       DPRINTK("to_atmarpd(%d)\n",type);
-       if (!atmarpd) return -EUNATCH;
+       DPRINTK("to_atmarpd(%d)\n", type);
+       if (!atmarpd)
+               return -EUNATCH;
        skb = alloc_skb(sizeof(struct atmarp_ctrl),GFP_ATOMIC);
-       if (!skb) return -ENOMEM;
+       if (!skb)
+               return -ENOMEM;
        ctrl = (struct atmarp_ctrl *) skb_put(skb,sizeof(struct atmarp_ctrl));
        ctrl->type = type;
        ctrl->itf_num = itf;
        ctrl->ip = ip;
-       atm_force_charge(atmarpd,skb->truesize);
+       atm_force_charge(atmarpd, skb->truesize);
 
        sk = sk_atm(atmarpd);
        skb_queue_tail(&sk->sk_receive_queue, skb);
@@ -79,26 +78,24 @@ static int to_atmarpd(enum atmarp_ctrl_type type,int itf,unsigned long ip)
        return 0;
 }
 
-
-static void link_vcc(struct clip_vcc *clip_vcc,struct atmarp_entry *entry)
+static void link_vcc(struct clip_vcc *clip_vcc, struct atmarp_entry *entry)
 {
-       DPRINTK("link_vcc %p to entry %p (neigh %p)\n",clip_vcc,entry,
-           entry->neigh);
+       DPRINTK("link_vcc %p to entry %p (neigh %p)\n", clip_vcc, entry,
+               entry->neigh);
        clip_vcc->entry = entry;
-       clip_vcc->xoff = 0; /* @@@ may overrun buffer by one packet */
+       clip_vcc->xoff = 0;     /* @@@ may overrun buffer by one packet */
        clip_vcc->next = entry->vccs;
        entry->vccs = clip_vcc;
        entry->neigh->used = jiffies;
 }
 
-
 static void unlink_clip_vcc(struct clip_vcc *clip_vcc)
 {
        struct atmarp_entry *entry = clip_vcc->entry;
        struct clip_vcc **walk;
 
        if (!entry) {
-               printk(KERN_CRIT "!clip_vcc->entry (clip_vcc %p)\n",clip_vcc);
+               printk(KERN_CRIT "!clip_vcc->entry (clip_vcc %p)\n", clip_vcc);
                return;
        }
        spin_lock_bh(&entry->neigh->dev->xmit_lock);    /* block clip_start_xmit() */
@@ -107,24 +104,24 @@ static void unlink_clip_vcc(struct clip_vcc *clip_vcc)
                if (*walk == clip_vcc) {
                        int error;
 
-                       *walk = clip_vcc->next; /* atomic */
+                       *walk = clip_vcc->next; /* atomic */
                        clip_vcc->entry = NULL;
                        if (clip_vcc->xoff)
                                netif_wake_queue(entry->neigh->dev);
                        if (entry->vccs)
                                goto out;
-                       entry->expires = jiffies-1;
-                               /* force resolution or expiration */
+                       entry->expires = jiffies - 1;
+                       /* force resolution or expiration */
                        error = neigh_update(entry->neigh, NULL, NUD_NONE,
                                             NEIGH_UPDATE_F_ADMIN);
                        if (error)
                                printk(KERN_CRIT "unlink_clip_vcc: "
-                                   "neigh_update failed with %d\n",error);
+                                      "neigh_update failed with %d\n", error);
                        goto out;
                }
        printk(KERN_CRIT "ATMARP: unlink_clip_vcc failed (entry %p, vcc "
-         "0x%p)\n",entry,clip_vcc);
-out:
+              "0x%p)\n", entry, clip_vcc);
+      out:
        spin_unlock_bh(&entry->neigh->dev->xmit_lock);
 }
 
@@ -153,13 +150,13 @@ static int neigh_check_cb(struct neighbour *n)
                DPRINTK("destruction postponed with ref %d\n",
                        atomic_read(&n->refcnt));
 
-               while ((skb = skb_dequeue(&n->arp_queue)) != NULL) 
+               while ((skb = skb_dequeue(&n->arp_queue)) != NULL)
                        dev_kfree_skb(skb);
 
                return 0;
        }
 
-       DPRINTK("expired neigh %p\n",n);
+       DPRINTK("expired neigh %p\n", n);
        return 1;
 }
 
@@ -167,7 +164,7 @@ static void idle_timer_check(unsigned long dummy)
 {
        write_lock(&clip_tbl.lock);
        __neigh_for_each_release(&clip_tbl, neigh_check_cb);
-       mod_timer(&idle_timer, jiffies+CLIP_CHECK_INTERVAL*HZ);
+       mod_timer(&idle_timer, jiffies + CLIP_CHECK_INTERVAL * HZ);
        write_unlock(&clip_tbl.lock);
 }
 
@@ -177,13 +174,13 @@ static int clip_arp_rcv(struct sk_buff *skb)
 
        DPRINTK("clip_arp_rcv\n");
        vcc = ATM_SKB(skb)->vcc;
-       if (!vcc || !atm_charge(vcc,skb->truesize)) {
+       if (!vcc || !atm_charge(vcc, skb->truesize)) {
                dev_kfree_skb_any(skb);
                return 0;
        }
-       DPRINTK("pushing to %p\n",vcc);
-       DPRINTK("using %p\n",CLIP_VCC(vcc)->old_push);
-       CLIP_VCC(vcc)->old_push(vcc,skb);
+       DPRINTK("pushing to %p\n", vcc);
+       DPRINTK("using %p\n", CLIP_VCC(vcc)->old_push);
+       CLIP_VCC(vcc)->old_push(vcc, skb);
        return 0;
 }
 
@@ -193,34 +190,38 @@ static const unsigned char llc_oui[] = {
        0x03,   /* Ctrl: Unnumbered Information Command PDU */
        0x00,   /* OUI: EtherType */
        0x00,
-       0x00 };
+       0x00
+};
 
-static void clip_push(struct atm_vcc *vcc,struct sk_buff *skb)
+static void clip_push(struct atm_vcc *vcc, struct sk_buff *skb)
 {
        struct clip_vcc *clip_vcc = CLIP_VCC(vcc);
 
        DPRINTK("clip push\n");
        if (!skb) {
-               DPRINTK("removing VCC %p\n",clip_vcc);
-               if (clip_vcc->entry) unlink_clip_vcc(clip_vcc);
-               clip_vcc->old_push(vcc,NULL); /* pass on the bad news */
+               DPRINTK("removing VCC %p\n", clip_vcc);
+               if (clip_vcc->entry)
+                       unlink_clip_vcc(clip_vcc);
+               clip_vcc->old_push(vcc, NULL);  /* pass on the bad news */
                kfree(clip_vcc);
                return;
        }
-       atm_return(vcc,skb->truesize);
+       atm_return(vcc, skb->truesize);
        skb->dev = clip_vcc->entry ? clip_vcc->entry->neigh->dev : clip_devs;
-               /* clip_vcc->entry == NULL if we don't have an IP address yet */
+       /* clip_vcc->entry == NULL if we don't have an IP address yet */
        if (!skb->dev) {
                dev_kfree_skb_any(skb);
                return;
        }
        ATM_SKB(skb)->vcc = vcc;
        skb->mac.raw = skb->data;
-       if (!clip_vcc->encap || skb->len < RFC1483LLC_LEN || memcmp(skb->data,
-           llc_oui,sizeof(llc_oui))) skb->protocol = htons(ETH_P_IP);
+       if (!clip_vcc->encap
+           || skb->len < RFC1483LLC_LEN
+           || memcmp(skb->data, llc_oui, sizeof (llc_oui)))
+               skb->protocol = htons(ETH_P_IP);
        else {
                skb->protocol = ((u16 *) skb->data)[3];
-               skb_pull(skb,RFC1483LLC_LEN);
+               skb_pull(skb, RFC1483LLC_LEN);
                if (skb->protocol == htons(ETH_P_ARP)) {
                        PRIV(skb->dev)->stats.rx_packets++;
                        PRIV(skb->dev)->stats.rx_bytes += skb->len;
@@ -235,58 +236,54 @@ static void clip_push(struct atm_vcc *vcc,struct sk_buff *skb)
        netif_rx(skb);
 }
 
-
 /*
  * Note: these spinlocks _must_not_ block on non-SMP. The only goal is that
  * clip_pop is atomic with respect to the critical section in clip_start_xmit.
  */
 
-
-static void clip_pop(struct atm_vcc *vcc,struct sk_buff *skb)
+static void clip_pop(struct atm_vcc *vcc, struct sk_buff *skb)
 {
        struct clip_vcc *clip_vcc = CLIP_VCC(vcc);
        struct net_device *dev = skb->dev;
        int old;
        unsigned long flags;
 
-       DPRINTK("clip_pop(vcc %p)\n",vcc);
-       clip_vcc->old_pop(vcc,skb);
+       DPRINTK("clip_pop(vcc %p)\n", vcc);
+       clip_vcc->old_pop(vcc, skb);
        /* skb->dev == NULL in outbound ARP packets */
-       if (!dev) return;
-       spin_lock_irqsave(&PRIV(dev)->xoff_lock,flags);
-       if (atm_may_send(vcc,0)) {
-               old = xchg(&clip_vcc->xoff,0);
-               if (old) netif_wake_queue(dev);
+       if (!dev)
+               return;
+       spin_lock_irqsave(&PRIV(dev)->xoff_lock, flags);
+       if (atm_may_send(vcc, 0)) {
+               old = xchg(&clip_vcc->xoff, 0);
+               if (old)
+                       netif_wake_queue(dev);
        }
-       spin_unlock_irqrestore(&PRIV(dev)->xoff_lock,flags);
+       spin_unlock_irqrestore(&PRIV(dev)->xoff_lock, flags);
 }
 
-
 static void clip_neigh_destroy(struct neighbour *neigh)
 {
-       DPRINTK("clip_neigh_destroy (neigh %p)\n",neigh);
+       DPRINTK("clip_neigh_destroy (neigh %p)\n", neigh);
        if (NEIGH2ENTRY(neigh)->vccs)
                printk(KERN_CRIT "clip_neigh_destroy: vccs != NULL !!!\n");
        NEIGH2ENTRY(neigh)->vccs = (void *) 0xdeadbeef;
 }
 
-
-static void clip_neigh_solicit(struct neighbour *neigh,struct sk_buff *skb)
+static void clip_neigh_solicit(struct neighbour *neigh, struct sk_buff *skb)
 {
-       DPRINTK("clip_neigh_solicit (neigh %p, skb %p)\n",neigh,skb);
-       to_atmarpd(act_need,PRIV(neigh->dev)->number,NEIGH2ENTRY(neigh)->ip);
+       DPRINTK("clip_neigh_solicit (neigh %p, skb %p)\n", neigh, skb);
+       to_atmarpd(act_need, PRIV(neigh->dev)->number, NEIGH2ENTRY(neigh)->ip);
 }
 
-
-static void clip_neigh_error(struct neighbour *neigh,struct sk_buff *skb)
+static void clip_neigh_error(struct neighbour *neigh, struct sk_buff *skb)
 {
 #ifndef CONFIG_ATM_CLIP_NO_ICMP
-       icmp_send(skb,ICMP_DEST_UNREACH,ICMP_HOST_UNREACH,0);
+       icmp_send(skb, ICMP_DEST_UNREACH, ICMP_HOST_UNREACH, 0);
 #endif
        kfree_skb(skb);
 }
 
-
 static struct neigh_ops clip_neigh_ops = {
        .family =               AF_INET,
        .solicit =              clip_neigh_solicit,
@@ -297,7 +294,6 @@ static struct neigh_ops clip_neigh_ops = {
        .queue_xmit =           dev_queue_xmit,
 };
 
-
 static int clip_constructor(struct neighbour *neigh)
 {
        struct atmarp_entry *entry = NEIGH2ENTRY(neigh);
@@ -305,9 +301,10 @@ static int clip_constructor(struct neighbour *neigh)
        struct in_device *in_dev;
        struct neigh_parms *parms;
 
-       DPRINTK("clip_constructor (neigh %p, entry %p)\n",neigh,entry);
+       DPRINTK("clip_constructor (neigh %p, entry %p)\n", neigh, entry);
        neigh->type = inet_addr_type(entry->ip);
-       if (neigh->type != RTN_UNICAST) return -EINVAL;
+       if (neigh->type != RTN_UNICAST)
+               return -EINVAL;
 
        rcu_read_lock();
        in_dev = __in_dev_get_rcu(dev);
@@ -326,13 +323,13 @@ static int clip_constructor(struct neighbour *neigh)
            neigh->ops->connected_output : neigh->ops->output;
        entry->neigh = neigh;
        entry->vccs = NULL;
-       entry->expires = jiffies-1;
+       entry->expires = jiffies - 1;
        return 0;
 }
 
 static u32 clip_hash(const void *pkey, const struct net_device *dev)
 {
-       return jhash_2words(*(u32 *)pkey, dev->ifindex, clip_tbl.hash_rnd);
+       return jhash_2words(*(u32 *) pkey, dev->ifindex, clip_tbl.hash_rnd);
 }
 
 static struct neigh_table clip_tbl = {
@@ -366,7 +363,6 @@ static struct neigh_table clip_tbl = {
        .gc_thresh3     = 1024,
 };
 
-
 /* @@@ copy bh locking from arp.c -- need to bh-enable atm code before */
 
 /*
@@ -376,15 +372,13 @@ static struct neigh_table clip_tbl = {
  * clip_setentry.
  */
 
-
-static int clip_encap(struct atm_vcc *vcc,int mode)
+static int clip_encap(struct atm_vcc *vcc, int mode)
 {
        CLIP_VCC(vcc)->encap = mode;
        return 0;
 }
 
-
-static int clip_start_xmit(struct sk_buff *skb,struct net_device *dev)
+static int clip_start_xmit(struct sk_buff *skb, struct net_device *dev)
 {
        struct clip_priv *clip_priv = PRIV(dev);
        struct atmarp_entry *entry;
@@ -392,7 +386,7 @@ static int clip_start_xmit(struct sk_buff *skb,struct net_device *dev)
        int old;
        unsigned long flags;
 
-       DPRINTK("clip_start_xmit (skb %p)\n",skb);
+       DPRINTK("clip_start_xmit (skb %p)\n", skb);
        if (!skb->dst) {
                printk(KERN_ERR "clip_start_xmit: skb->dst == NULL\n");
                dev_kfree_skb(skb);
@@ -401,9 +395,9 @@ static int clip_start_xmit(struct sk_buff *skb,struct net_device *dev)
        }
        if (!skb->dst->neighbour) {
 #if 0
-               skb->dst->neighbour = clip_find_neighbour(skb->dst,1);
+               skb->dst->neighbour = clip_find_neighbour(skb->dst, 1);
                if (!skb->dst->neighbour) {
-                       dev_kfree_skb(skb); /* lost that one */
+                       dev_kfree_skb(skb);     /* lost that one */
                        clip_priv->stats.tx_dropped++;
                        return 0;
                }
@@ -417,73 +411,73 @@ static int clip_start_xmit(struct sk_buff *skb,struct net_device *dev)
        if (!entry->vccs) {
                if (time_after(jiffies, entry->expires)) {
                        /* should be resolved */
-                       entry->expires = jiffies+ATMARP_RETRY_DELAY*HZ;
-                       to_atmarpd(act_need,PRIV(dev)->number,entry->ip);
+                       entry->expires = jiffies + ATMARP_RETRY_DELAY * HZ;
+                       to_atmarpd(act_need, PRIV(dev)->number, entry->ip);
                }
                if (entry->neigh->arp_queue.qlen < ATMARP_MAX_UNRES_PACKETS)
-                       skb_queue_tail(&entry->neigh->arp_queue,skb);
+                       skb_queue_tail(&entry->neigh->arp_queue, skb);
                else {
                        dev_kfree_skb(skb);
                        clip_priv->stats.tx_dropped++;
                }
                return 0;
        }
-       DPRINTK("neigh %p, vccs %p\n",entry,entry->vccs);
+       DPRINTK("neigh %p, vccs %p\n", entry, entry->vccs);
        ATM_SKB(skb)->vcc = vcc = entry->vccs->vcc;
-       DPRINTK("using neighbour %p, vcc %p\n",skb->dst->neighbour,vcc);
+       DPRINTK("using neighbour %p, vcc %p\n", skb->dst->neighbour, vcc);
        if (entry->vccs->encap) {
                void *here;
 
-               here = skb_push(skb,RFC1483LLC_LEN);
-               memcpy(here,llc_oui,sizeof(llc_oui));
+               here = skb_push(skb, RFC1483LLC_LEN);
+               memcpy(here, llc_oui, sizeof(llc_oui));
                ((u16 *) here)[3] = skb->protocol;
        }
        atomic_add(skb->truesize, &sk_atm(vcc)->sk_wmem_alloc);
        ATM_SKB(skb)->atm_options = vcc->atm_options;
        entry->vccs->last_use = jiffies;
-       DPRINTK("atm_skb(%p)->vcc(%p)->dev(%p)\n",skb,vcc,vcc->dev);
-       old = xchg(&entry->vccs->xoff,1); /* assume XOFF ... */
+       DPRINTK("atm_skb(%p)->vcc(%p)->dev(%p)\n", skb, vcc, vcc->dev);
+       old = xchg(&entry->vccs->xoff, 1);      /* assume XOFF ... */
        if (old) {
                printk(KERN_WARNING "clip_start_xmit: XOFF->XOFF transition\n");
                return 0;
        }
        clip_priv->stats.tx_packets++;
        clip_priv->stats.tx_bytes += skb->len;
-       (void) vcc->send(vcc,skb);
-       if (atm_may_send(vcc,0)) {
+       vcc->send(vcc, skb);
+       if (atm_may_send(vcc, 0)) {
                entry->vccs->xoff = 0;
                return 0;
        }
-       spin_lock_irqsave(&clip_priv->xoff_lock,flags);
-       netif_stop_queue(dev); /* XOFF -> throttle immediately */
+       spin_lock_irqsave(&clip_priv->xoff_lock, flags);
+       netif_stop_queue(dev);  /* XOFF -> throttle immediately */
        barrier();
        if (!entry->vccs->xoff)
                netif_start_queue(dev);
-               /* Oh, we just raced with clip_pop. netif_start_queue should be
-                  good enough, because nothing should really be asleep because
-                  of the brief netif_stop_queue. If this isn't true or if it
-                  changes, use netif_wake_queue instead. */
-       spin_unlock_irqrestore(&clip_priv->xoff_lock,flags);
+       /* Oh, we just raced with clip_pop. netif_start_queue should be
+          good enough, because nothing should really be asleep because
+          of the brief netif_stop_queue. If this isn't true or if it
+          changes, use netif_wake_queue instead. */
+       spin_unlock_irqrestore(&clip_priv->xoff_lock, flags);
        return 0;
 }
 
-
 static struct net_device_stats *clip_get_stats(struct net_device *dev)
 {
        return &PRIV(dev)->stats;
 }
 
-
-static int clip_mkip(struct atm_vcc *vcc,int timeout)
+static int clip_mkip(struct atm_vcc *vcc, int timeout)
 {
        struct clip_vcc *clip_vcc;
        struct sk_buff_head copy;
        struct sk_buff *skb;
 
-       if (!vcc->push) return -EBADFD;
-       clip_vcc = kmalloc(sizeof(struct clip_vcc),GFP_KERNEL);
-       if (!clip_vcc) return -ENOMEM;
-       DPRINTK("mkip clip_vcc %p vcc %p\n",clip_vcc,vcc);
+       if (!vcc->push)
+               return -EBADFD;
+       clip_vcc = kmalloc(sizeof(struct clip_vcc), GFP_KERNEL);
+       if (!clip_vcc)
+               return -ENOMEM;
+       DPRINTK("mkip clip_vcc %p vcc %p\n", clip_vcc, vcc);
        clip_vcc->vcc = vcc;
        vcc->user_back = clip_vcc;
        set_bit(ATM_VF_IS_CLIP, &vcc->flags);
@@ -491,7 +485,7 @@ static int clip_mkip(struct atm_vcc *vcc,int timeout)
        clip_vcc->xoff = 0;
        clip_vcc->encap = 1;
        clip_vcc->last_use = jiffies;
-       clip_vcc->idle_timeout = timeout*HZ;
+       clip_vcc->idle_timeout = timeout * HZ;
        clip_vcc->old_push = vcc->push;
        clip_vcc->old_pop = vcc->pop;
        vcc->push = clip_push;
@@ -501,27 +495,25 @@ static int clip_mkip(struct atm_vcc *vcc,int timeout)
        /* re-process everything received between connection setup and MKIP */
        while ((skb = skb_dequeue(&copy)) != NULL)
                if (!clip_devs) {
-                       atm_return(vcc,skb->truesize);
+                       atm_return(vcc, skb->truesize);
                        kfree_skb(skb);
-               }
-               else {
+               } else {
                        unsigned int len = skb->len;
 
-                       clip_push(vcc,skb);
+                       clip_push(vcc, skb);
                        PRIV(skb->dev)->stats.rx_packets--;
                        PRIV(skb->dev)->stats.rx_bytes -= len;
                }
        return 0;
 }
 
-
-static int clip_setentry(struct atm_vcc *vcc,u32 ip)
+static int clip_setentry(struct atm_vcc *vcc, u32 ip)
 {
        struct neighbour *neigh;
        struct atmarp_entry *entry;
        int error;
        struct clip_vcc *clip_vcc;
-       struct flowi fl = { .nl_u = { .ip4_u = { .daddr = ip, .tos = 1 } } };
+       struct flowi fl = { .nl_u = { .ip4_u = { .daddr = ip, .tos = 1}} };
        struct rtable *rt;
 
        if (vcc->push != clip_push) {
@@ -538,28 +530,29 @@ static int clip_setentry(struct atm_vcc *vcc,u32 ip)
                unlink_clip_vcc(clip_vcc);
                return 0;
        }
-       error = ip_route_output_key(&rt,&fl);
-       if (error) return error;
-       neigh = __neigh_lookup(&clip_tbl,&ip,rt->u.dst.dev,1);
+       error = ip_route_output_key(&rt, &fl);
+       if (error)
+               return error;
+       neigh = __neigh_lookup(&clip_tbl, &ip, rt->u.dst.dev, 1);
        ip_rt_put(rt);
        if (!neigh)
                return -ENOMEM;
        entry = NEIGH2ENTRY(neigh);
        if (entry != clip_vcc->entry) {
-               if (!clip_vcc->entry) DPRINTK("setentry: add\n");
+               if (!clip_vcc->entry)
+                       DPRINTK("setentry: add\n");
                else {
                        DPRINTK("setentry: update\n");
                        unlink_clip_vcc(clip_vcc);
                }
-               link_vcc(clip_vcc,entry);
+               link_vcc(clip_vcc, entry);
        }
-       error = neigh_update(neigh, llc_oui, NUD_PERMANENT, 
-                            NEIGH_UPDATE_F_OVERRIDE|NEIGH_UPDATE_F_ADMIN);
+       error = neigh_update(neigh, llc_oui, NUD_PERMANENT,
+                            NEIGH_UPDATE_F_OVERRIDE | NEIGH_UPDATE_F_ADMIN);
        neigh_release(neigh);
        return error;
 }
 
-
 static void clip_setup(struct net_device *dev)
 {
        dev->hard_start_xmit = clip_start_xmit;
@@ -568,15 +561,14 @@ static void clip_setup(struct net_device *dev)
        dev->type = ARPHRD_ATM;
        dev->hard_header_len = RFC1483LLC_LEN;
        dev->mtu = RFC1626_MTU;
-       dev->tx_queue_len = 100; /* "normal" queue (packets) */
-           /* When using a "real" qdisc, the qdisc determines the queue */
-           /* length. tx_queue_len is only used for the default case, */
-           /* without any more elaborate queuing. 100 is a reasonable */
-           /* compromise between decent burst-tolerance and protection */
-           /* against memory hogs. */
+       dev->tx_queue_len = 100;        /* "normal" queue (packets) */
+       /* When using a "real" qdisc, the qdisc determines the queue */
+       /* length. tx_queue_len is only used for the default case, */
+       /* without any more elaborate queuing. 100 is a reasonable */
+       /* compromise between decent burst-tolerance and protection */
+       /* against memory hogs. */
 }
 
-
 static int clip_create(int number)
 {
        struct net_device *dev;
@@ -585,19 +577,19 @@ static int clip_create(int number)
 
        if (number != -1) {
                for (dev = clip_devs; dev; dev = PRIV(dev)->next)
-                       if (PRIV(dev)->number == number) return -EEXIST;
-       }
-       else {
+                       if (PRIV(dev)->number == number)
+                               return -EEXIST;
+       else {
                number = 0;
                for (dev = clip_devs; dev; dev = PRIV(dev)->next)
                        if (PRIV(dev)->number >= number)
-                               number = PRIV(dev)->number+1;
+                               number = PRIV(dev)->number + 1;
        }
        dev = alloc_netdev(sizeof(struct clip_priv), "", clip_setup);
        if (!dev)
                return -ENOMEM;
        clip_priv = PRIV(dev);
-       sprintf(dev->name,"atm%d",number);
+       sprintf(dev->name, "atm%d", number);
        spin_lock_init(&clip_priv->xoff_lock);
        clip_priv->number = number;
        error = register_netdev(dev);
@@ -607,53 +599,48 @@ static int clip_create(int number)
        }
        clip_priv->next = clip_devs;
        clip_devs = dev;
-       DPRINTK("registered (net:%s)\n",dev->name);
+       DPRINTK("registered (net:%s)\n", dev->name);
        return number;
 }
 
-
-static int clip_device_event(struct notifier_block *this,unsigned long event,
-    void *dev)
+static int clip_device_event(struct notifier_block *this, unsigned long event,
+                            void *arg)
 {
+       struct net_device *dev = arg;
+
+       if (event == NETDEV_UNREGISTER) {
+               neigh_ifdown(&clip_tbl, dev);
+               return NOTIFY_DONE;
+       }
+
        /* ignore non-CLIP devices */
-       if (((struct net_device *) dev)->type != ARPHRD_ATM ||
-           ((struct net_device *) dev)->hard_start_xmit != clip_start_xmit)
+       if (dev->type != ARPHRD_ATM || dev->hard_start_xmit != clip_start_xmit)
                return NOTIFY_DONE;
+
        switch (event) {
-               case NETDEV_UP:
-                       DPRINTK("clip_device_event NETDEV_UP\n");
-                       (void) to_atmarpd(act_up,PRIV(dev)->number,0);
-                       break;
-               case NETDEV_GOING_DOWN:
-                       DPRINTK("clip_device_event NETDEV_DOWN\n");
-                       (void) to_atmarpd(act_down,PRIV(dev)->number,0);
-                       break;
-               case NETDEV_CHANGE:
-               case NETDEV_CHANGEMTU:
-                       DPRINTK("clip_device_event NETDEV_CHANGE*\n");
-                       (void) to_atmarpd(act_change,PRIV(dev)->number,0);
-                       break;
-               case NETDEV_REBOOT:
-               case NETDEV_REGISTER:
-               case NETDEV_DOWN:
-                       DPRINTK("clip_device_event %ld\n",event);
-                       /* ignore */
-                       break;
-               default:
-                       printk(KERN_WARNING "clip_device_event: unknown event "
-                           "%ld\n",event);
-                       break;
+       case NETDEV_UP:
+               DPRINTK("clip_device_event NETDEV_UP\n");
+               to_atmarpd(act_up, PRIV(dev)->number, 0);
+               break;
+       case NETDEV_GOING_DOWN:
+               DPRINTK("clip_device_event NETDEV_DOWN\n");
+               to_atmarpd(act_down, PRIV(dev)->number, 0);
+               break;
+       case NETDEV_CHANGE:
+       case NETDEV_CHANGEMTU:
+               DPRINTK("clip_device_event NETDEV_CHANGE*\n");
+               to_atmarpd(act_change, PRIV(dev)->number, 0);
+               break;
        }
        return NOTIFY_DONE;
 }
 
-
-static int clip_inet_event(struct notifier_block *this,unsigned long event,
-    void *ifa)
+static int clip_inet_event(struct notifier_block *this, unsigned long event,
+                          void *ifa)
 {
        struct in_device *in_dev;
 
-       in_dev = ((struct in_ifaddr *) ifa)->ifa_dev;
+       in_dev = ((struct in_ifaddr *)ifa)->ifa_dev;
        if (!in_dev || !in_dev->dev) {
                printk(KERN_WARNING "clip_inet_event: no device\n");
                return NOTIFY_DONE;
@@ -662,23 +649,20 @@ static int clip_inet_event(struct notifier_block *this,unsigned long event,
         * Transitions are of the down-change-up type, so it's sufficient to
         * handle the change on up.
         */
-       if (event != NETDEV_UP) return NOTIFY_DONE;
-       return clip_device_event(this,NETDEV_CHANGE,in_dev->dev);
+       if (event != NETDEV_UP)
+               return NOTIFY_DONE;
+       return clip_device_event(this, NETDEV_CHANGE, in_dev->dev);
 }
 
 
 static struct notifier_block clip_dev_notifier = {
-       clip_device_event,
-       NULL,
-       0
+       .notifier_call = clip_device_event,
 };
 
 
 
 static struct notifier_block clip_inet_notifier = {
-       clip_inet_event,
-       NULL,
-       0
+       .notifier_call = clip_inet_event,
 };
 
 
@@ -686,14 +670,12 @@ static struct notifier_block clip_inet_notifier = {
 static void atmarpd_close(struct atm_vcc *vcc)
 {
        DPRINTK("atmarpd_close\n");
-       atmarpd = NULL; /* assumed to be atomic */
-       barrier();
-       unregister_inetaddr_notifier(&clip_inet_notifier);
-       unregister_netdevice_notifier(&clip_dev_notifier);
-       if (skb_peek(&sk_atm(vcc)->sk_receive_queue))
-               printk(KERN_ERR "atmarpd_close: closing with requests "
-                   "pending\n");
+
+       rtnl_lock();
+       atmarpd = NULL;
        skb_queue_purge(&sk_atm(vcc)->sk_receive_queue);
+       rtnl_unlock();
+
        DPRINTK("(done)\n");
        module_put(THIS_MODULE);
 }
@@ -714,14 +696,14 @@ static struct atm_dev atmarpd_dev = {
 
 static int atm_init_atmarp(struct atm_vcc *vcc)
 {
-       if (atmarpd) return -EADDRINUSE;
-       if (start_timer) {
-               start_timer = 0;
-               init_timer(&idle_timer);
-               idle_timer.expires = jiffies+CLIP_CHECK_INTERVAL*HZ;
-               idle_timer.function = idle_timer_check;
-               add_timer(&idle_timer);
+       rtnl_lock();
+       if (atmarpd) {
+               rtnl_unlock();
+               return -EADDRINUSE;
        }
+
+       mod_timer(&idle_timer, jiffies+CLIP_CHECK_INTERVAL*HZ);
+
        atmarpd = vcc;
        set_bit(ATM_VF_META,&vcc->flags);
        set_bit(ATM_VF_READY,&vcc->flags);
@@ -731,10 +713,7 @@ static int atm_init_atmarp(struct atm_vcc *vcc)
        vcc->push = NULL;
        vcc->pop = NULL; /* crash */
        vcc->push_oam = NULL; /* crash */
-       if (register_netdevice_notifier(&clip_dev_notifier))
-               printk(KERN_ERR "register_netdevice_notifier failed\n");
-       if (register_inetaddr_notifier(&clip_inet_notifier))
-               printk(KERN_ERR "register_inetaddr_notifier failed\n");
+       rtnl_unlock();
        return 0;
 }
 
@@ -744,53 +723,53 @@ static int clip_ioctl(struct socket *sock, unsigned int cmd, unsigned long arg)
        int err = 0;
 
        switch (cmd) {
-               case SIOCMKCLIP:
-               case ATMARPD_CTRL:
-               case ATMARP_MKIP:
-               case ATMARP_SETENTRY:
-               case ATMARP_ENCAP:
-                       if (!capable(CAP_NET_ADMIN))
-                               return -EPERM;
-                       break;
-               default:
-                       return -ENOIOCTLCMD;
+       case SIOCMKCLIP:
+       case ATMARPD_CTRL:
+       case ATMARP_MKIP:
+       case ATMARP_SETENTRY:
+       case ATMARP_ENCAP:
+               if (!capable(CAP_NET_ADMIN))
+                       return -EPERM;
+               break;
+       default:
+               return -ENOIOCTLCMD;
        }
 
        switch (cmd) {
-               case SIOCMKCLIP:
-                       err = clip_create(arg);
-                       break;
-               case ATMARPD_CTRL:
-                       err = atm_init_atmarp(vcc);
-                       if (!err) {
-                               sock->state = SS_CONNECTED;
-                               __module_get(THIS_MODULE);
-                       }
-                       break;
-               case ATMARP_MKIP:
-                       err = clip_mkip(vcc ,arg);
-                       break;
-               case ATMARP_SETENTRY:
-                       err = clip_setentry(vcc, arg);
-                       break;
-               case ATMARP_ENCAP:
-                       err = clip_encap(vcc, arg);
-                       break;
+       case SIOCMKCLIP:
+               err = clip_create(arg);
+               break;
+       case ATMARPD_CTRL:
+               err = atm_init_atmarp(vcc);
+               if (!err) {
+                       sock->state = SS_CONNECTED;
+                       __module_get(THIS_MODULE);
+               }
+               break;
+       case ATMARP_MKIP:
+               err = clip_mkip(vcc, arg);
+               break;
+       case ATMARP_SETENTRY:
+               err = clip_setentry(vcc, arg);
+               break;
+       case ATMARP_ENCAP:
+               err = clip_encap(vcc, arg);
+               break;
        }
        return err;
 }
 
 static struct atm_ioctl clip_ioctl_ops = {
-       .owner  = THIS_MODULE,
-       .ioctl  = clip_ioctl,
+       .owner = THIS_MODULE,
+       .ioctl = clip_ioctl,
 };
 
 #ifdef CONFIG_PROC_FS
 
 static void svc_addr(struct seq_file *seq, struct sockaddr_atmsvc *addr)
 {
-       static int code[] = { 1,2,10,6,1,0 };
-       static int e164[] = { 1,8,4,6,1,0 };
+       static int code[] = { 1, 2, 10, 6, 1, 0 };
+       static int e164[] = { 1, 8, 4, 6, 1, 0 };
 
        if (*addr->sas_addr.pub) {
                seq_printf(seq, "%s", addr->sas_addr.pub);
@@ -809,7 +788,7 @@ static void svc_addr(struct seq_file *seq, struct sockaddr_atmsvc *addr)
                for (i = 0; fields[i]; i++) {
                        for (j = fields[i]; j; j--)
                                seq_printf(seq, "%02X", *prv++);
-                       if (fields[i+1])
+                       if (fields[i + 1])
                                seq_putc(seq, '.');
                }
        }
@@ -828,8 +807,7 @@ static void atmarp_info(struct seq_file *seq, struct net_device *dev,
        svc = ((clip_vcc == SEQ_NO_VCC_TOKEN) ||
               (sk_atm(clip_vcc->vcc)->sk_family == AF_ATMSVC));
 
-       llc = ((clip_vcc == SEQ_NO_VCC_TOKEN) ||
-              clip_vcc->encap);
+       llc = ((clip_vcc == SEQ_NO_VCC_TOKEN) || clip_vcc->encap);
 
        if (clip_vcc == SEQ_NO_VCC_TOKEN)
                exp = entry->neigh->used;
@@ -839,10 +817,7 @@ static void atmarp_info(struct seq_file *seq, struct net_device *dev,
        exp = (jiffies - exp) / HZ;
 
        seq_printf(seq, "%-6s%-4s%-4s%5ld ",
-                  dev->name,
-                  svc ? "SVC" : "PVC",
-                  llc ? "LLC" : "NULL",
-                  exp);
+                  dev->name, svc ? "SVC" : "PVC", llc ? "LLC" : "NULL", exp);
 
        off = scnprintf(buf, sizeof(buf) - 1, "%d.%d.%d.%d",
                        NIPQUAD(entry->ip));
@@ -860,8 +835,7 @@ static void atmarp_info(struct seq_file *seq, struct net_device *dev,
        } else if (!svc) {
                seq_printf(seq, "%d.%d.%d\n",
                           clip_vcc->vcc->dev->number,
-                          clip_vcc->vcc->vpi,
-                          clip_vcc->vcc->vci);
+                          clip_vcc->vcc->vpi, clip_vcc->vcc->vci);
        } else {
                svc_addr(seq, &clip_vcc->vcc->remote);
                seq_putc(seq, '\n');
@@ -894,7 +868,7 @@ static struct clip_vcc *clip_seq_next_vcc(struct atmarp_entry *e,
 }
 
 static void *clip_seq_vcc_walk(struct clip_seq_state *state,
-                              struct atmarp_entry *e, loff_t *pos)
+                              struct atmarp_entry *e, loff_t * pos)
 {
        struct clip_vcc *vcc = state->vcc;
 
@@ -911,24 +885,24 @@ static void *clip_seq_vcc_walk(struct clip_seq_state *state,
 
        return vcc;
 }
-  
+
 static void *clip_seq_sub_iter(struct neigh_seq_state *_state,
-                              struct neighbour *n, loff_t *pos)
+                              struct neighbour *n, loff_t * pos)
 {
-       struct clip_seq_state *state = (struct clip_seq_state *) _state;
+       struct clip_seq_state *state = (struct clip_seq_state *)_state;
 
        return clip_seq_vcc_walk(state, NEIGH2ENTRY(n), pos);
 }
 
-static void *clip_seq_start(struct seq_file *seq, loff_t *pos)
+static void *clip_seq_start(struct seq_file *seq, loff_t * pos)
 {
        return neigh_seq_start(seq, pos, &clip_tbl, NEIGH_SEQ_NEIGH_ONLY);
 }
 
 static int clip_seq_show(struct seq_file *seq, void *v)
 {
-       static char atm_arp_banner[] = 
-               "IPitf TypeEncp Idle IP address      ATM address\n";
+       static char atm_arp_banner[] =
+           "IPitf TypeEncp Idle IP address      ATM address\n";
 
        if (v == SEQ_START_TOKEN) {
                seq_puts(seq, atm_arp_banner);
@@ -939,7 +913,7 @@ static int clip_seq_show(struct seq_file *seq, void *v)
 
                atmarp_info(seq, n->dev, NEIGH2ENTRY(n), vcc);
        }
-       return 0;
+       return 0;
 }
 
 static struct seq_operations arp_seq_ops = {
@@ -988,20 +962,19 @@ static struct file_operations arp_seq_fops = {
 
 static int __init atm_clip_init(void)
 {
+       struct proc_dir_entry *p;
        neigh_table_init(&clip_tbl);
 
        clip_tbl_hook = &clip_tbl;
        register_atm_ioctl(&clip_ioctl_ops);
+       register_netdevice_notifier(&clip_dev_notifier);
+       register_inetaddr_notifier(&clip_inet_notifier);
 
-#ifdef CONFIG_PROC_FS
-{
-       struct proc_dir_entry *p;
+       setup_timer(&idle_timer, idle_timer_check, 0);
 
        p = create_proc_entry("arp", S_IRUGO, atm_proc_root);
        if (p)
                p->proc_fops = &arp_seq_fops;
-}
-#endif
 
        return 0;
 }
@@ -1012,13 +985,15 @@ static void __exit atm_clip_exit(void)
 
        remove_proc_entry("arp", atm_proc_root);
 
+       unregister_inetaddr_notifier(&clip_inet_notifier);
+       unregister_netdevice_notifier(&clip_dev_notifier);
+
        deregister_atm_ioctl(&clip_ioctl_ops);
 
        /* First, stop the idle timer, so it stops banging
         * on the table.
         */
-       if (start_timer == 0)
-               del_timer(&idle_timer);
+       del_timer_sync(&idle_timer);
 
        /* Next, purge the table, so that the device
         * unregister loop below does not hang due to
@@ -1042,5 +1017,6 @@ static void __exit atm_clip_exit(void)
 
 module_init(atm_clip_init);
 module_exit(atm_clip_exit);
-
+MODULE_AUTHOR("Werner Almesberger");
+MODULE_DESCRIPTION("Classical/IP over ATM interface");
 MODULE_LICENSE("GPL");
index 6b61323ce23cad772371657cf18833027f56d0f9..0c2d13ad69bbf0c799f8bff6fbc2e78ffcc22763 100644 (file)
@@ -255,7 +255,7 @@ static inline int sco_send_frame(struct sock *sk, struct msghdr *msg, int len)
        }
 
        if ((err = hci_send_sco(conn->hcon, skb)) < 0)
-               goto fail;
+               return err;
 
        return count;
 
index b7766562d72c0aaaa7727d80e3db1cc31043406b..b0b7f55c1edd38f2901cfc450ac638ca6589dd80 100644 (file)
@@ -125,9 +125,6 @@ int br_handle_frame(struct net_bridge_port *p, struct sk_buff **pskb)
        struct sk_buff *skb = *pskb;
        const unsigned char *dest = eth_hdr(skb)->h_dest;
 
-       if (p->state == BR_STATE_DISABLED)
-               goto err;
-
        if (!is_valid_ether_addr(eth_hdr(skb)->h_source))
                goto err;
 
index f29450b788be166182999ed6f927a15f6fcb186a..3da9264449f79d6d517fce1391af3f663bdde3a8 100644 (file)
@@ -765,6 +765,15 @@ out:
        return NF_STOLEN;
 }
 
+static int br_nf_dev_queue_xmit(struct sk_buff *skb)
+{
+       if (skb->protocol == htons(ETH_P_IP) &&
+           skb->len > skb->dev->mtu &&
+           !(skb_shinfo(skb)->ufo_size || skb_shinfo(skb)->tso_size))
+               return ip_fragment(skb, br_dev_queue_push_xmit);
+       else
+               return br_dev_queue_push_xmit(skb);
+}
 
 /* PF_BRIDGE/POST_ROUTING ********************************************/
 static unsigned int br_nf_post_routing(unsigned int hook, struct sk_buff **pskb,
@@ -824,7 +833,7 @@ static unsigned int br_nf_post_routing(unsigned int hook, struct sk_buff **pskb,
                realoutdev = nf_bridge->netoutdev;
 #endif
        NF_HOOK(pf, NF_IP_POST_ROUTING, skb, NULL, realoutdev,
-               br_dev_queue_push_xmit);
+               br_nf_dev_queue_xmit);
 
        return NF_STOLEN;
 
@@ -869,7 +878,7 @@ static unsigned int ip_sabotage_out(unsigned int hook, struct sk_buff **pskb,
 
        if ((out->hard_start_xmit == br_dev_xmit &&
             okfn != br_nf_forward_finish &&
-            okfn != br_nf_local_out_finish && okfn != br_dev_queue_push_xmit)
+            okfn != br_nf_local_out_finish && okfn != br_nf_dev_queue_xmit)
 #if defined(CONFIG_VLAN_8021Q) || defined(CONFIG_VLAN_8021Q_MODULE)
            || ((out->priv_flags & IFF_802_1Q_VLAN) &&
                VLAN_DEV_INFO(out)->real_dev->hard_start_xmit == br_dev_xmit)
index 01eae97c53d9db212d1e52b8209a9067961dea67..3a13ed643459bc3d249d0b73b1c98a1d76e5a3c5 100644 (file)
@@ -824,14 +824,14 @@ static int translate_table(struct ebt_replace *repl,
        if (udc_cnt) {
                /* this will get free'd in do_replace()/ebt_register_table()
                   if an error occurs */
-               newinfo->chainstack = (struct ebt_chainstack **)
-                  vmalloc((highest_possible_processor_id()+1) 
-                                               * sizeof(struct ebt_chainstack));
+               newinfo->chainstack =
+                       vmalloc((highest_possible_processor_id()+1)
+                                       * sizeof(*(newinfo->chainstack)));
                if (!newinfo->chainstack)
                        return -ENOMEM;
-               for_each_cpu(i) {
+               for_each_possible_cpu(i) {
                        newinfo->chainstack[i] =
-                          vmalloc(udc_cnt * sizeof(struct ebt_chainstack));
+                         vmalloc(udc_cnt * sizeof(*(newinfo->chainstack[0])));
                        if (!newinfo->chainstack[i]) {
                                while (i)
                                        vfree(newinfo->chainstack[--i]);
@@ -841,8 +841,7 @@ static int translate_table(struct ebt_replace *repl,
                        }
                }
 
-               cl_s = (struct ebt_cl_stack *)
-                  vmalloc(udc_cnt * sizeof(struct ebt_cl_stack));
+               cl_s = vmalloc(udc_cnt * sizeof(*cl_s));
                if (!cl_s)
                        return -ENOMEM;
                i = 0; /* the i'th udc */
@@ -901,7 +900,7 @@ static void get_counters(struct ebt_counter *oldcounters,
               sizeof(struct ebt_counter) * nentries);
 
        /* add other counters to those of cpu 0 */
-       for_each_cpu(cpu) {
+       for_each_possible_cpu(cpu) {
                if (cpu == 0)
                        continue;
                counter_base = COUNTER_BASE(oldcounters, nentries, cpu);
@@ -944,8 +943,7 @@ static int do_replace(void __user *user, unsigned int len)
 
        countersize = COUNTER_OFFSET(tmp.nentries) * 
                                        (highest_possible_processor_id()+1);
-       newinfo = (struct ebt_table_info *)
-          vmalloc(sizeof(struct ebt_table_info) + countersize);
+       newinfo = vmalloc(sizeof(*newinfo) + countersize);
        if (!newinfo)
                return -ENOMEM;
 
@@ -967,8 +965,7 @@ static int do_replace(void __user *user, unsigned int len)
        /* the user wants counters back
           the check on the size is done later, when we have the lock */
        if (tmp.num_counters) {
-               counterstmp = (struct ebt_counter *)
-                  vmalloc(tmp.num_counters * sizeof(struct ebt_counter));
+               counterstmp = vmalloc(tmp.num_counters * sizeof(*counterstmp));
                if (!counterstmp) {
                        ret = -ENOMEM;
                        goto free_entries;
@@ -1036,7 +1033,7 @@ static int do_replace(void __user *user, unsigned int len)
 
        vfree(table->entries);
        if (table->chainstack) {
-               for_each_cpu(i)
+               for_each_possible_cpu(i)
                        vfree(table->chainstack[i]);
                vfree(table->chainstack);
        }
@@ -1054,7 +1051,7 @@ free_counterstmp:
        vfree(counterstmp);
        /* can be initialized in translate_table() */
        if (newinfo->chainstack) {
-               for_each_cpu(i)
+               for_each_possible_cpu(i)
                        vfree(newinfo->chainstack[i]);
                vfree(newinfo->chainstack);
        }
@@ -1148,8 +1145,7 @@ int ebt_register_table(struct ebt_table *table)
 
        countersize = COUNTER_OFFSET(table->table->nentries) *
                                        (highest_possible_processor_id()+1);
-       newinfo = (struct ebt_table_info *)
-          vmalloc(sizeof(struct ebt_table_info) + countersize);
+       newinfo = vmalloc(sizeof(*newinfo) + countersize);
        ret = -ENOMEM;
        if (!newinfo)
                return -ENOMEM;
@@ -1201,7 +1197,7 @@ free_unlock:
        mutex_unlock(&ebt_mutex);
 free_chainstack:
        if (newinfo->chainstack) {
-               for_each_cpu(i)
+               for_each_possible_cpu(i)
                        vfree(newinfo->chainstack[i]);
                vfree(newinfo->chainstack);
        }
@@ -1224,7 +1220,7 @@ void ebt_unregister_table(struct ebt_table *table)
        mutex_unlock(&ebt_mutex);
        vfree(table->private->entries);
        if (table->private->chainstack) {
-               for_each_cpu(i)
+               for_each_possible_cpu(i)
                        vfree(table->private->chainstack[i]);
                vfree(table->private->chainstack);
        }
@@ -1247,8 +1243,7 @@ static int update_counters(void __user *user, unsigned int len)
        if (hlp.num_counters == 0)
                return -EINVAL;
 
-       if ( !(tmp = (struct ebt_counter *)
-          vmalloc(hlp.num_counters * sizeof(struct ebt_counter))) ){
+       if (!(tmp = vmalloc(hlp.num_counters * sizeof(*tmp)))) {
                MEMPRINT("Update_counters && nomemory\n");
                return -ENOMEM;
        }
@@ -1377,8 +1372,7 @@ static int copy_everything_to_user(struct ebt_table *t, void __user *user,
                        BUGPRINT("Num_counters wrong\n");
                        return -EINVAL;
                }
-               counterstmp = (struct ebt_counter *)
-                  vmalloc(nentries * sizeof(struct ebt_counter));
+               counterstmp = vmalloc(nentries * sizeof(*counterstmp));
                if (!counterstmp) {
                        MEMPRINT("Couldn't copy counters, out of memory\n");
                        return -ENOMEM;
index 434220d093aae3f20c4da3bc3881911dd64c0c3c..3bad1afc89fa48b505c001a24da094de18f14cab 100644 (file)
@@ -2698,7 +2698,8 @@ int dev_ioctl(unsigned int cmd, void __user *arg)
                                /* If command is `set a parameter', or
                                 * `get the encoding parameters', check if
                                 * the user has the right to do it */
-                               if (IW_IS_SET(cmd) || cmd == SIOCGIWENCODE) {
+                               if (IW_IS_SET(cmd) || cmd == SIOCGIWENCODE
+                                   || cmd == SIOCGIWENCODEEXT) {
                                        if (!capable(CAP_NET_ADMIN))
                                                return -EPERM;
                                }
@@ -3042,11 +3043,11 @@ void netdev_run_todo(void)
 
                switch(dev->reg_state) {
                case NETREG_REGISTERING:
+                       dev->reg_state = NETREG_REGISTERED;
                        err = netdev_register_sysfs(dev);
                        if (err)
                                printk(KERN_ERR "%s: failed sysfs registration (%d)\n",
                                       dev->name, err);
-                       dev->reg_state = NETREG_REGISTERED;
                        break;
 
                case NETREG_UNREGISTERING:
@@ -3100,12 +3101,11 @@ struct net_device *alloc_netdev(int sizeof_priv, const char *name,
        alloc_size = (sizeof(*dev) + NETDEV_ALIGN_CONST) & ~NETDEV_ALIGN_CONST;
        alloc_size += sizeof_priv + NETDEV_ALIGN_CONST;
 
-       p = kmalloc(alloc_size, GFP_KERNEL);
+       p = kzalloc(alloc_size, GFP_KERNEL);
        if (!p) {
                printk(KERN_ERR "alloc_dev: Unable to allocate device.\n");
                return NULL;
        }
-       memset(p, 0, alloc_size);
 
        dev = (struct net_device *)
                (((long)p + NETDEV_ALIGN_CONST) & ~NETDEV_ALIGN_CONST);
@@ -3347,7 +3347,7 @@ static int __init net_dev_init(void)
         *      Initialise the packet receive queues.
         */
 
-       for_each_cpu(i) {
+       for_each_possible_cpu(i) {
                struct softnet_data *queue;
 
                queue = &per_cpu(softnet_data, i);
index cf581407538c4b160947548b0fa350840b959dd0..29ee77f15932465115d64f7f5d01d395e69af6d6 100644 (file)
@@ -55,15 +55,12 @@ int alloc_divert_blk(struct net_device *dev)
 
        dev->divert = NULL;
        if (dev->type == ARPHRD_ETHER) {
-               dev->divert = (struct divert_blk *)
-                       kmalloc(alloc_size, GFP_KERNEL);
+               dev->divert = kzalloc(alloc_size, GFP_KERNEL);
                if (dev->divert == NULL) {
                        printk(KERN_INFO "divert: unable to allocate divert_blk for %s\n",
                               dev->name);
                        return -ENOMEM;
                }
-
-               memset(dev->divert, 0, sizeof(struct divert_blk));
                dev_hold(dev);
        }
 
index 93fbd01d225952c66228d228a66340101448166a..5b4486a60cf6bca668bf4f5e7232d6df1a37dbb9 100644 (file)
@@ -34,6 +34,7 @@
 #include <linux/timer.h>
 #include <asm/system.h>
 #include <asm/uaccess.h>
+#include <asm/unaligned.h>
 #include <linux/filter.h>
 
 /* No hurry in this branch */
@@ -177,7 +178,7 @@ unsigned int sk_run_filter(struct sk_buff *skb, struct sock_filter *filter, int
 load_w:
                        ptr = load_pointer(skb, k, 4, &tmp);
                        if (ptr != NULL) {
-                               A = ntohl(*(u32 *)ptr);
+                               A = ntohl(get_unaligned((u32 *)ptr));
                                continue;
                        }
                        break;
@@ -186,7 +187,7 @@ load_w:
 load_h:
                        ptr = load_pointer(skb, k, 2, &tmp);
                        if (ptr != NULL) {
-                               A = ntohs(*(u16 *)ptr);
+                               A = ntohs(get_unaligned((u16 *)ptr));
                                continue;
                        }
                        break;
index 55789f832edadc23d41851f6009b3d01f6072148..2191af5f26acbfe61f6e1633de7d40cfbd83c27c 100644 (file)
@@ -79,7 +79,7 @@ static void flow_cache_new_hashrnd(unsigned long arg)
 {
        int i;
 
-       for_each_cpu(i)
+       for_each_possible_cpu(i)
                flow_hash_rnd_recalc(i) = 1;
 
        flow_hash_rnd_timer.expires = jiffies + FLOW_HASH_RND_PERIOD;
@@ -318,12 +318,10 @@ static void __devinit flow_cache_cpu_prepare(int cpu)
                /* NOTHING */;
 
        flow_table(cpu) = (struct flow_cache_entry **)
-               __get_free_pages(GFP_KERNEL, order);
+               __get_free_pages(GFP_KERNEL|__GFP_ZERO, order);
        if (!flow_table(cpu))
                panic("NET: failed to allocate flow cache order %lu\n", order);
 
-       memset(flow_table(cpu), 0, PAGE_SIZE << order);
-
        flow_hash_rnd_recalc(cpu) = 1;
        flow_count(cpu) = 0;
 
@@ -363,7 +361,7 @@ static int __init flow_cache_init(void)
        flow_hash_rnd_timer.expires = jiffies + FLOW_HASH_RND_PERIOD;
        add_timer(&flow_hash_rnd_timer);
 
-       for_each_cpu(i)
+       for_each_possible_cpu(i)
                flow_cache_cpu_prepare(i);
 
        hotcpu_notifier(flow_cache_cpu, 0);
index b07c029e8219e3fbe6493c28e560faf0de473612..3cad026764f0c9b94f9615ee22da0f9b4ed16833 100644 (file)
@@ -159,11 +159,10 @@ int gen_new_estimator(struct gnet_stats_basic *bstats,
        if (parm->interval < -2 || parm->interval > 3)
                return -EINVAL;
 
-       est = kmalloc(sizeof(*est), GFP_KERNEL);
+       est = kzalloc(sizeof(*est), GFP_KERNEL);
        if (est == NULL)
                return -ENOBUFS;
 
-       memset(est, 0, sizeof(*est));
        est->interval = parm->interval + 2;
        est->bstats = bstats;
        est->rate_est = rate_est;
index 0c8666872d10fdf0d90fea6b327952c6f6493051..4cf878efdb49eb9fc7d02b7b41f83601ab29d079 100644 (file)
@@ -284,14 +284,11 @@ static struct neighbour **neigh_hash_alloc(unsigned int entries)
        struct neighbour **ret;
 
        if (size <= PAGE_SIZE) {
-               ret = kmalloc(size, GFP_ATOMIC);
+               ret = kzalloc(size, GFP_ATOMIC);
        } else {
                ret = (struct neighbour **)
-                       __get_free_pages(GFP_ATOMIC, get_order(size));
+                     __get_free_pages(GFP_ATOMIC|__GFP_ZERO, get_order(size));
        }
-       if (ret)
-               memset(ret, 0, size);
-
        return ret;
 }
 
@@ -1089,8 +1086,7 @@ static void neigh_hh_init(struct neighbour *n, struct dst_entry *dst,
                if (hh->hh_type == protocol)
                        break;
 
-       if (!hh && (hh = kmalloc(sizeof(*hh), GFP_ATOMIC)) != NULL) {
-               memset(hh, 0, sizeof(struct hh_cache));
+       if (!hh && (hh = kzalloc(sizeof(*hh), GFP_ATOMIC)) != NULL) {
                rwlock_init(&hh->hh_lock);
                hh->hh_type = protocol;
                atomic_set(&hh->hh_refcnt, 0);
@@ -1366,13 +1362,11 @@ void neigh_table_init(struct neigh_table *tbl)
        tbl->hash_buckets = neigh_hash_alloc(tbl->hash_mask + 1);
 
        phsize = (PNEIGH_HASHMASK + 1) * sizeof(struct pneigh_entry *);
-       tbl->phash_buckets = kmalloc(phsize, GFP_KERNEL);
+       tbl->phash_buckets = kzalloc(phsize, GFP_KERNEL);
 
        if (!tbl->hash_buckets || !tbl->phash_buckets)
                panic("cannot allocate neighbour cache hashes");
 
-       memset(tbl->phash_buckets, 0, phsize);
-
        get_random_bytes(&tbl->hash_rnd, sizeof(tbl->hash_rnd));
 
        rwlock_init(&tbl->lock);
@@ -1633,7 +1627,7 @@ static int neightbl_fill_info(struct neigh_table *tbl, struct sk_buff *skb,
 
                memset(&ndst, 0, sizeof(ndst));
 
-               for_each_cpu(cpu) {
+               for_each_possible_cpu(cpu) {
                        struct neigh_statistics *st;
 
                        st = per_cpu_ptr(tbl->stats, cpu);
index 21b68464cabbd38530f14fee95dd875a71ad877e..c12990c9c603ebb0403ffaab710139409cde81de 100644 (file)
@@ -165,7 +165,7 @@ static ssize_t show_operstate(struct class_device *dev, char *buf)
                operstate = IF_OPER_DOWN;
        read_unlock(&dev_base_lock);
 
-       if (operstate >= sizeof(operstates))
+       if (operstate >= ARRAY_SIZE(operstates))
                return -EINVAL; /* should not happen */
 
        return sprintf(buf, "%s\n", operstates[operstate]);
index 1e44eda1fda9f028bb3e9d67c06a4d6dda30311e..79ebd75fbe4dec5c57ddd34c4501c5858b04d8fb 100644 (file)
@@ -38,13 +38,11 @@ int reqsk_queue_alloc(struct request_sock_queue *queue,
 {
        const int lopt_size = sizeof(struct listen_sock) +
                              nr_table_entries * sizeof(struct request_sock *);
-       struct listen_sock *lopt = kmalloc(lopt_size, GFP_KERNEL);
+       struct listen_sock *lopt = kzalloc(lopt_size, GFP_KERNEL);
 
        if (lopt == NULL)
                return -ENOMEM;
 
-       memset(lopt, 0, lopt_size);
-
        for (lopt->max_qlen_log = 6;
             (1 << lopt->max_qlen_log) < sysctl_max_syn_backlog;
             lopt->max_qlen_log++);
index 09464fa8d72f8b10c881b44678e8aa1084a3bcfb..fb3770f9c09405f3dce34e2b429e74d4a9761508 100644 (file)
@@ -112,6 +112,14 @@ void skb_under_panic(struct sk_buff *skb, int sz, void *here)
        BUG();
 }
 
+void skb_truesize_bug(struct sk_buff *skb)
+{
+       printk(KERN_ERR "SKB BUG: Invalid truesize (%u) "
+              "len=%u, sizeof(sk_buff)=%Zd\n",
+              skb->truesize, skb->len, sizeof(struct sk_buff));
+}
+EXPORT_SYMBOL(skb_truesize_bug);
+
 /*     Allocate a new skbuff. We do this ourselves so we can fill in a few
  *     'private' fields and also do memory statistics to find all the
  *     [BEEP] leaks.
index 35e25259fd95712a0145853eeea4f01493ad5599..e9489696f694540bfb90d12aba6e1cd3c5dd1d57 100644 (file)
@@ -176,6 +176,7 @@ void sk_stream_rfree(struct sk_buff *skb)
 {
        struct sock *sk = skb->sk;
 
+       skb_truesize_check(skb);
        atomic_sub(skb->truesize, &sk->sk_rmem_alloc);
        sk->sk_forward_alloc += skb->truesize;
 }
index fdc4f38bc46ccfbcc86c4a36698489cfcd0ba08b..4f96f389243d7d6322288609f6477c74eab5ac09 100644 (file)
@@ -121,7 +121,7 @@ void __init net_random_init(void)
 {
        int i;
 
-       for_each_cpu(i) {
+       for_each_possible_cpu(i) {
                struct nrnd_state *state = &per_cpu(net_rand_state,i);
                __net_srandom(state, i+jiffies);
        }
@@ -133,7 +133,7 @@ static int net_random_reseed(void)
        unsigned long seed[NR_CPUS];
 
        get_random_bytes(seed, sizeof(seed));
-       for_each_cpu(i) {
+       for_each_possible_cpu(i) {
                struct nrnd_state *state = &per_cpu(net_rand_state,i);
                __net_srandom(state, seed[i]);
        }
index 81d6995fcfdb30bd684b839626a0145fd079bd31..d2bc72d318f7bdb41dc4ab9c1ab3c08978c5af4e 100644 (file)
@@ -1726,6 +1726,14 @@ int wireless_rtnetlink_get(struct net_device *   dev,
        if(!IW_IS_GET(request->cmd))
                return -EOPNOTSUPP;
 
+       /* If command is `get the encoding parameters', check if
+        * the user has the right to do it */
+       if (request->cmd == SIOCGIWENCODE ||
+           request->cmd == SIOCGIWENCODEEXT) {
+               if (!capable(CAP_NET_ADMIN))
+                       return -EPERM;
+       }
+
        /* Special cases */
        if(request->cmd == SIOCGIWSTATS)
                /* Get Wireless Stats */
index 29047995c6957595bf40bdffbc8ad940291ba174..f2c011fd2ba128f92757aa816da604804d99394f 100644 (file)
@@ -498,7 +498,7 @@ int dccp_v4_conn_request(struct sock *sk, struct sk_buff *skb)
                goto drop;
 
        if (dccp_parse_options(sk, skb))
-               goto drop;
+               goto drop_and_free;
 
        dccp_openreq_init(req, &dp, skb);
 
index 6cd9f3427be6c029daa85340ae2a1bca69b1e20a..f2a27cc6ecb1fc653fa7643e543cd1e7dfb4a3f8 100644 (file)
@@ -1,6 +1,7 @@
 config IEEE80211_SOFTMAC
        tristate "Software MAC add-on to the IEEE 802.11 networking stack"
        depends on IEEE80211 && EXPERIMENTAL
+       select WIRELESS_EXT
        ---help---
        This option enables the hardware independent software MAC addon
        for the IEEE 802.11 networking stack.
index be61de78dfa4a6dc01f6a653e3b6efee89ceac54..4498023841dcc7d83e0e59d792a27b2f839256d4 100644 (file)
@@ -101,6 +101,7 @@ ieee80211softmac_disassoc(struct ieee80211softmac_device *mac, u16 reason)
        /* Do NOT clear bssvalid as that will break ieee80211softmac_assoc_work! */
        mac->associated = 0;
        mac->associnfo.associating = 0;
+       ieee80211softmac_call_events_locked(mac, IEEE80211SOFTMAC_EVENT_DISASSOCIATED, NULL);
        spin_unlock_irqrestore(&mac->lock, flags);
 }
 
@@ -373,6 +374,7 @@ ieee80211softmac_handle_disassoc(struct net_device * dev,
        spin_lock_irqsave(&mac->lock, flags);
        mac->associnfo.bssvalid = 0;
        mac->associated = 0;
+       ieee80211softmac_call_events_locked(mac, IEEE80211SOFTMAC_EVENT_DISASSOCIATED, NULL);
        schedule_work(&mac->associnfo.work);
        spin_unlock_irqrestore(&mac->lock, flags);
        
@@ -391,6 +393,7 @@ ieee80211softmac_handle_reassoc_req(struct net_device * dev,
                dprintkl(KERN_INFO PFX "reassoc request from unknown network\n");
                return 0;
        }
-       ieee80211softmac_assoc(mac, network);
+       schedule_work(&mac->associnfo.work);
+
        return 0;
 }
index 0a52bbda1e4c8c20e2862eb69d673a3c406def2b..8cc8f3f0f8e73d3809556a6cb30c3c8cf588c111 100644 (file)
@@ -67,6 +67,7 @@ static char *event_descriptions[IEEE80211SOFTMAC_EVENT_LAST+1] = {
        "authenticating failed",
        "authenticating timed out",
        "associating failed because no suitable network was found",
+       "disassociated",
 };
 
 
@@ -128,13 +129,42 @@ void
 ieee80211softmac_call_events_locked(struct ieee80211softmac_device *mac, int event, void *event_ctx)
 {
        struct ieee80211softmac_event *eventptr, *tmp;
-       union iwreq_data wrqu;
-       char *msg;
+       struct ieee80211softmac_network *network;
        
        if (event >= 0) {
-               msg = event_descriptions[event];
-               wrqu.data.length = strlen(msg);
-               wireless_send_event(mac->dev, IWEVCUSTOM, &wrqu, msg);
+               union iwreq_data wrqu;
+               int we_event;
+               char *msg = NULL;
+
+               switch(event) {
+               case IEEE80211SOFTMAC_EVENT_ASSOCIATED:
+                       network = (struct ieee80211softmac_network *)event_ctx;
+                       wrqu.data.length = 0;
+                       wrqu.data.flags = 0;
+                       memcpy(wrqu.ap_addr.sa_data, &network->bssid[0], ETH_ALEN);
+                       wrqu.ap_addr.sa_family = ARPHRD_ETHER;
+                       we_event = SIOCGIWAP;
+                       break;
+               case IEEE80211SOFTMAC_EVENT_DISASSOCIATED:
+                       wrqu.data.length = 0;
+                       wrqu.data.flags = 0;
+                       memset(&wrqu, '\0', sizeof (union iwreq_data));
+                       wrqu.ap_addr.sa_family = ARPHRD_ETHER;
+                       we_event = SIOCGIWAP;
+                       break;
+               case IEEE80211SOFTMAC_EVENT_SCAN_FINISHED:
+                       wrqu.data.length = 0;
+                       wrqu.data.flags = 0;
+                       memset(&wrqu, '\0', sizeof (union iwreq_data));
+                       we_event = SIOCGIWSCAN;
+                       break;
+               default:
+                       msg = event_descriptions[event];
+                       wrqu.data.length = strlen(msg);
+                       we_event = IWEVCUSTOM;
+                       break;
+               }
+               wireless_send_event(mac->dev, we_event, &wrqu, msg);
        }
 
        if (!list_empty(&mac->events))
index febc51dbb41247119f501625f6bd54f537dc0afc..cc6cd56c85b100af93a7216442c4a6d9ade20e36 100644 (file)
@@ -180,9 +180,21 @@ ieee80211softmac_assoc_req(struct ieee80211_assoc_request **pkt,
        ieee80211softmac_hdr_3addr(mac, &((*pkt)->header), IEEE80211_STYPE_ASSOC_REQ, net->bssid, net->bssid);
 
        /* Fill in capability Info */
-       (*pkt)->capability = (mac->ieee->iw_mode == IW_MODE_MASTER) || (mac->ieee->iw_mode == IW_MODE_INFRA) ?
-               cpu_to_le16(WLAN_CAPABILITY_ESS) :
-               cpu_to_le16(WLAN_CAPABILITY_IBSS);
+       switch (mac->ieee->iw_mode) {
+       case IW_MODE_INFRA:
+               (*pkt)->capability = cpu_to_le16(WLAN_CAPABILITY_ESS);
+               break;
+       case IW_MODE_ADHOC:
+               (*pkt)->capability = cpu_to_le16(WLAN_CAPABILITY_IBSS);
+               break;
+       case IW_MODE_AUTO:
+               (*pkt)->capability = net->capabilities & (WLAN_CAPABILITY_ESS|WLAN_CAPABILITY_IBSS);
+               break;
+       default:
+               /* bleh. we don't ever go to these modes */
+               printk(KERN_ERR PFX "invalid iw_mode!\n");
+               break;
+       }
        /* Need to add this
        (*pkt)->capability |= mac->ieee->short_slot ? 
                        cpu_to_le16(WLAN_CAPABILITY_SHORT_SLOT_TIME) : 0;
index bb9ab8b45d09fde0898f3e19ee2fbf9d6726152b..2b9e7edfa3ce4719d5783bd1b822bd825c763cce 100644 (file)
@@ -47,6 +47,7 @@ ieee80211softmac_start_scan(struct ieee80211softmac_device *sm)
        sm->scanning = 1;
        spin_unlock_irqrestore(&sm->lock, flags);
 
+       netif_tx_disable(sm->ieee->dev);
        ret = sm->start_scan(sm->dev);
        if (ret) {
                spin_lock_irqsave(&sm->lock, flags);
@@ -239,6 +240,7 @@ void ieee80211softmac_scan_finished(struct ieee80211softmac_device *sm)
                if (net)
                        sm->set_channel(sm->dev, net->channel);
        }
+       netif_wake_queue(sm->ieee->dev);
        ieee80211softmac_call_events(sm, IEEE80211SOFTMAC_EVENT_SCAN_FINISHED, NULL);
 }
 EXPORT_SYMBOL_GPL(ieee80211softmac_scan_finished);
index b559aa9b5507712acea32ca7b6e7c614e5e37773..00f0d4f71897aff525361f4c8ee9b7e76b284dcd 100644 (file)
@@ -41,13 +41,23 @@ ieee80211softmac_wx_trigger_scan(struct net_device *net_dev,
 EXPORT_SYMBOL_GPL(ieee80211softmac_wx_trigger_scan);
 
 
+/* if we're still scanning, return -EAGAIN so that userspace tools
+ * can get the complete scan results, otherwise return 0. */
 int
 ieee80211softmac_wx_get_scan_results(struct net_device *net_dev,
                                     struct iw_request_info *info,
                                     union iwreq_data *data,
                                     char *extra)
 {
+       unsigned long flags;
        struct ieee80211softmac_device *sm = ieee80211_priv(net_dev);
+
+       spin_lock_irqsave(&sm->lock, flags);
+       if (sm->scanning) {
+               spin_unlock_irqrestore(&sm->lock, flags);
+               return -EAGAIN;
+       }
+       spin_unlock_irqrestore(&sm->lock, flags);
        return ieee80211_wx_get_scan(sm->ieee, info, data, extra);
 }
 EXPORT_SYMBOL_GPL(ieee80211softmac_wx_get_scan_results);
index 041dadde31af74c23b482bb65905f2bba6822471..4749d504c6292188f921b8b296c0394834f2851f 100644 (file)
@@ -928,7 +928,8 @@ static void parp_redo(struct sk_buff *skb)
  *     Receive an arp request from the device layer.
  */
 
-int arp_rcv(struct sk_buff *skb, struct net_device *dev, struct packet_type *pt, struct net_device *orig_dev)
+static int arp_rcv(struct sk_buff *skb, struct net_device *dev,
+                  struct packet_type *pt, struct net_device *orig_dev)
 {
        struct arphdr *arp;
 
@@ -1417,7 +1418,6 @@ static int __init arp_proc_init(void)
 
 EXPORT_SYMBOL(arp_broken_ops);
 EXPORT_SYMBOL(arp_find);
-EXPORT_SYMBOL(arp_rcv);
 EXPORT_SYMBOL(arp_create);
 EXPORT_SYMBOL(arp_xmit);
 EXPORT_SYMBOL(arp_send);
index 81c2f788529242e63bbc3316cf64993da1ec3774..54419b27686f86f33e370c4241235ef5bc723034 100644 (file)
@@ -1556,7 +1556,6 @@ void __init devinet_init(void)
 #endif
 }
 
-EXPORT_SYMBOL(devinet_ioctl);
 EXPORT_SYMBOL(in_dev_finish_destroy);
 EXPORT_SYMBOL(inet_select_addr);
 EXPORT_SYMBOL(inetdev_by_index);
index 4e3d3811dea29f67c2cd701368ea3bb6a0c677a8..cdde963909603aae61b7398afb09112dde407e52 100644 (file)
@@ -666,4 +666,3 @@ void __init ip_fib_init(void)
 }
 
 EXPORT_SYMBOL(inet_addr_type);
-EXPORT_SYMBOL(ip_rt_ioctl);
index ccd3efc6a173bc45ad189a9bca84d76d594f9eff..95a639f2e3dbc654df393c3f985b20c4fa036560 100644 (file)
@@ -50,7 +50,7 @@
  *             Patrick McHardy <kaber@trash.net>
  */
 
-#define VERSION "0.406"
+#define VERSION "0.407"
 
 #include <linux/config.h>
 #include <asm/uaccess.h>
@@ -314,11 +314,6 @@ static void __leaf_free_rcu(struct rcu_head *head)
        kfree(container_of(head, struct leaf, rcu));
 }
 
-static inline void free_leaf(struct leaf *leaf)
-{
-       call_rcu(&leaf->rcu, __leaf_free_rcu);
-}
-
 static void __leaf_info_free_rcu(struct rcu_head *head)
 {
        kfree(container_of(head, struct leaf_info, rcu));
@@ -357,7 +352,12 @@ static void __tnode_free_rcu(struct rcu_head *head)
 
 static inline void tnode_free(struct tnode *tn)
 {
-       call_rcu(&tn->rcu, __tnode_free_rcu);
+       if(IS_LEAF(tn)) {
+               struct leaf *l = (struct leaf *) tn;
+               call_rcu_bh(&l->rcu, __leaf_free_rcu);
+       }
+        else
+               call_rcu(&tn->rcu, __tnode_free_rcu);
 }
 
 static struct leaf *leaf_new(void)
index 9831fd2c73a0a222290f504e44d413627c5fe216..2a0455911ee0a9c9119472c01d4d4717f58e190b 100644 (file)
@@ -1107,7 +1107,7 @@ void __init icmp_init(struct net_proto_family *ops)
        struct inet_sock *inet;
        int i;
 
-       for_each_cpu(i) {
+       for_each_possible_cpu(i) {
                int err;
 
                err = sock_create_kern(PF_INET, SOCK_RAW, IPPROTO_ICMP,
index ef7366fc132f6e7e6eab1c93fa3097749cbd9372..ee9b5515b9aea20fb28d61be5aedc04321f20676 100644 (file)
@@ -43,8 +43,6 @@ struct inet_bind_bucket *inet_bind_bucket_create(kmem_cache_t *cachep,
        return tb;
 }
 
-EXPORT_SYMBOL(inet_bind_bucket_create);
-
 /*
  * Caller must hold hashbucket lock for this tb with local BH disabled
  */
@@ -64,8 +62,6 @@ void inet_bind_hash(struct sock *sk, struct inet_bind_bucket *tb,
        inet_csk(sk)->icsk_bind_hash = tb;
 }
 
-EXPORT_SYMBOL(inet_bind_hash);
-
 /*
  * Get rid of any references to a local port held by the given sock.
  */
index 2a8adda15e1199c3d849d4e51ad899eabfeb43c3..da734c4391796e017ef55d5e3e4730bfe16a4490 100644 (file)
@@ -304,13 +304,17 @@ out:
 
 /* Creation primitives. */
 
-static struct ipq *ip_frag_intern(unsigned int hash, struct ipq *qp_in)
+static struct ipq *ip_frag_intern(struct ipq *qp_in)
 {
        struct ipq *qp;
 #ifdef CONFIG_SMP
        struct hlist_node *n;
 #endif
+       unsigned int hash;
+
        write_lock(&ipfrag_lock);
+       hash = ipqhashfn(qp_in->id, qp_in->saddr, qp_in->daddr,
+                        qp_in->protocol);
 #ifdef CONFIG_SMP
        /* With SMP race we have to recheck hash table, because
         * such entry could be created on other cpu, while we
@@ -345,7 +349,7 @@ static struct ipq *ip_frag_intern(unsigned int hash, struct ipq *qp_in)
 }
 
 /* Add an entry to the 'ipq' queue for a newly received IP datagram. */
-static struct ipq *ip_frag_create(unsigned hash, struct iphdr *iph, u32 user)
+static struct ipq *ip_frag_create(struct iphdr *iph, u32 user)
 {
        struct ipq *qp;
 
@@ -371,7 +375,7 @@ static struct ipq *ip_frag_create(unsigned hash, struct iphdr *iph, u32 user)
        spin_lock_init(&qp->lock);
        atomic_set(&qp->refcnt, 1);
 
-       return ip_frag_intern(hash, qp);
+       return ip_frag_intern(qp);
 
 out_nomem:
        LIMIT_NETDEBUG(KERN_ERR "ip_frag_create: no memory left !\n");
@@ -387,11 +391,12 @@ static inline struct ipq *ip_find(struct iphdr *iph, u32 user)
        __u32 saddr = iph->saddr;
        __u32 daddr = iph->daddr;
        __u8 protocol = iph->protocol;
-       unsigned int hash = ipqhashfn(id, saddr, daddr, protocol);
+       unsigned int hash;
        struct ipq *qp;
        struct hlist_node *n;
 
        read_lock(&ipfrag_lock);
+       hash = ipqhashfn(id, saddr, daddr, protocol);
        hlist_for_each_entry(qp, n, &ipq_hash[hash], list) {
                if(qp->id == id         &&
                   qp->saddr == saddr   &&
@@ -405,7 +410,7 @@ static inline struct ipq *ip_find(struct iphdr *iph, u32 user)
        }
        read_unlock(&ipfrag_lock);
 
-       return ip_frag_create(hash, iph, user);
+       return ip_frag_create(iph, user);
 }
 
 /* Is the fragment too far ahead to be part of ipq? */
index 9981dcd68f11e76dc5213832ac20323a6b6dd3d1..ab99bebdcdc89da781df9997c002f9d3a27c6693 100644 (file)
@@ -656,7 +656,7 @@ static int ipgre_rcv(struct sk_buff *skb)
                read_unlock(&ipgre_lock);
                return(0);
        }
-       icmp_send(skb, ICMP_DEST_UNREACH, ICMP_PROT_UNREACH, 0);
+       icmp_send(skb, ICMP_DEST_UNREACH, ICMP_PORT_UNREACH, 0);
 
 drop:
        read_unlock(&ipgre_lock);
index f75ff1d96551d1e03cbfba7153c1bedb9b6e36df..cff9c3a72daf254013b7ae80cb5761e04a733a2f 100644 (file)
@@ -86,8 +86,6 @@
 
 int sysctl_ip_default_ttl = IPDEFTTL;
 
-static int ip_fragment(struct sk_buff *skb, int (*output)(struct sk_buff*));
-
 /* Generate a checksum for an outgoing IP datagram. */
 __inline__ void ip_send_check(struct iphdr *iph)
 {
@@ -421,7 +419,7 @@ static void ip_copy_metadata(struct sk_buff *to, struct sk_buff *from)
  *     single device frame, and queue such a frame for sending.
  */
 
-static int ip_fragment(struct sk_buff *skb, int (*output)(struct sk_buff*))
+int ip_fragment(struct sk_buff *skb, int (*output)(struct sk_buff*))
 {
        struct iphdr *iph;
        int raw = 0;
@@ -673,6 +671,8 @@ fail:
        return err;
 }
 
+EXPORT_SYMBOL(ip_fragment);
+
 int
 ip_generic_getfrag(void *from, char *to, int offset, int len, int odd, struct sk_buff *skb)
 {
@@ -904,7 +904,7 @@ alloc_new_skb:
                         * because we have no idea what fragment will be
                         * the last.
                         */
-                       if (datalen == length)
+                       if (datalen == length + fraggap)
                                alloclen += rt->u.dst.trailer_len;
 
                        if (transhdrlen) {
index 0a1d86a0f63289844a7dafccf5a726644ae38f45..cd810f41af1a71db684a7787bde2bbc8e5d601f7 100644 (file)
@@ -290,11 +290,8 @@ static void ipcomp_free_scratches(void)
        if (!scratches)
                return;
 
-       for_each_cpu(i) {
-               void *scratch = *per_cpu_ptr(scratches, i);
-               if (scratch)
-                       vfree(scratch);
-       }
+       for_each_possible_cpu(i)
+               vfree(*per_cpu_ptr(scratches, i));
 
        free_percpu(scratches);
 }
@@ -313,7 +310,7 @@ static void **ipcomp_alloc_scratches(void)
 
        ipcomp_scratches = scratches;
 
-       for_each_cpu(i) {
+       for_each_possible_cpu(i) {
                void *scratch = vmalloc(IPCOMP_SCRATCH_SIZE);
                if (!scratch)
                        return NULL;
@@ -344,7 +341,7 @@ static void ipcomp_free_tfms(struct crypto_tfm **tfms)
        if (!tfms)
                return;
 
-       for_each_cpu(cpu) {
+       for_each_possible_cpu(cpu) {
                struct crypto_tfm *tfm = *per_cpu_ptr(tfms, cpu);
                crypto_free_tfm(tfm);
        }
@@ -384,7 +381,7 @@ static struct crypto_tfm **ipcomp_alloc_tfms(const char *alg_name)
        if (!tfms)
                goto error;
 
-       for_each_cpu(cpu) {
+       for_each_possible_cpu(cpu) {
                struct crypto_tfm *tfm = crypto_alloc_tfm(alg_name, 0);
                if (!tfm)
                        goto error;
index eef07b0916a3da9e875ef6652ec4e6c204ebdc4d..ea398ee43f28740d6b75eee0efe5ecdcd97c54ee 100644 (file)
@@ -474,9 +474,6 @@ static int ipip_rcv(struct sk_buff *skb)
        struct iphdr *iph;
        struct ip_tunnel *tunnel;
 
-       if (!pskb_may_pull(skb, sizeof(struct iphdr)))
-               goto out;
-
        iph = skb->nh.iph;
 
        read_lock(&ipip_lock);
@@ -508,7 +505,6 @@ static int ipip_rcv(struct sk_buff *skb)
        }
        read_unlock(&ipip_lock);
 
-out:
        return -1;
 }
 
index b5ad9ac2fbcc04b2c444df5a32d1ffe4c9646afe..6a9e34b794bc7d3c495566045ef2c38bad3a0c5d 100644 (file)
@@ -133,7 +133,7 @@ struct ip_rt_info {
        u_int8_t tos;
 };
 
-static void queue_save(const struct sk_buff *skb, struct nf_info *info)
+static void nf_ip_saveroute(const struct sk_buff *skb, struct nf_info *info)
 {
        struct ip_rt_info *rt_info = nf_info_reroute(info);
 
@@ -146,7 +146,7 @@ static void queue_save(const struct sk_buff *skb, struct nf_info *info)
        }
 }
 
-static int queue_reroute(struct sk_buff **pskb, const struct nf_info *info)
+static int nf_ip_reroute(struct sk_buff **pskb, const struct nf_info *info)
 {
        const struct ip_rt_info *rt_info = nf_info_reroute(info);
 
@@ -161,20 +161,54 @@ static int queue_reroute(struct sk_buff **pskb, const struct nf_info *info)
        return 0;
 }
 
-static struct nf_queue_rerouter ip_reroute = {
-       .rer_size       = sizeof(struct ip_rt_info),
-       .save           = queue_save,
-       .reroute        = queue_reroute,
+unsigned int nf_ip_checksum(struct sk_buff *skb, unsigned int hook,
+                           unsigned int dataoff, u_int8_t protocol)
+{
+       struct iphdr *iph = skb->nh.iph;
+       unsigned int csum = 0;
+
+       switch (skb->ip_summed) {
+       case CHECKSUM_HW:
+               if (hook != NF_IP_PRE_ROUTING && hook != NF_IP_LOCAL_IN)
+                       break;
+               if ((protocol == 0 && !(u16)csum_fold(skb->csum)) ||
+                   !csum_tcpudp_magic(iph->saddr, iph->daddr,
+                                      skb->len - dataoff, protocol,
+                                      skb->csum)) {
+                       skb->ip_summed = CHECKSUM_UNNECESSARY;
+                       break;
+               }
+               /* fall through */
+       case CHECKSUM_NONE:
+               if (protocol == 0)
+                       skb->csum = 0;
+               else
+                       skb->csum = csum_tcpudp_nofold(iph->saddr, iph->daddr,
+                                                      skb->len - dataoff,
+                                                      protocol, 0);
+               csum = __skb_checksum_complete(skb);
+       }
+       return csum;
+}
+
+EXPORT_SYMBOL(nf_ip_checksum);
+
+static struct nf_afinfo nf_ip_afinfo = {
+       .family         = AF_INET,
+       .checksum       = nf_ip_checksum,
+       .saveroute      = nf_ip_saveroute,
+       .reroute        = nf_ip_reroute,
+       .route_key_size = sizeof(struct ip_rt_info),
 };
 
 static int ipv4_netfilter_init(void)
 {
-       return nf_register_queue_rerouter(PF_INET, &ip_reroute);
+       return nf_register_afinfo(&nf_ip_afinfo);
 }
 
 static void ipv4_netfilter_fini(void)
 {
-       nf_unregister_queue_rerouter(PF_INET);
+       nf_unregister_afinfo(&nf_ip_afinfo);
 }
 
 module_init(ipv4_netfilter_init);
index 77855ccd6b4398cf4999eb4742aaf17a52983876..c60fd5c4ea1e531f71f57a2704da64b1c5985f3e 100644 (file)
@@ -69,6 +69,7 @@ config IP_NF_CONNTRACK_NETLINK
        tristate 'Connection tracking netlink interface (EXPERIMENTAL)'
        depends on EXPERIMENTAL && IP_NF_CONNTRACK && NETFILTER_NETLINK
        depends on IP_NF_CONNTRACK!=y || NETFILTER_NETLINK!=m
+       depends on IP_NF_NAT=n || IP_NF_NAT
        help
          This option enables support for a netlink-based userspace interface
 
index a44a5d73457da49a275d8c55a475a119e514db8f..c2d92f99a2b8b0b18bc1f17e1ec742a2c6051de5 100644 (file)
@@ -646,7 +646,7 @@ static int translate_table(const char *name,
        }
 
        /* And one copy for every other CPU */
-       for_each_cpu(i) {
+       for_each_possible_cpu(i) {
                if (newinfo->entries[i] && newinfo->entries[i] != entry0)
                        memcpy(newinfo->entries[i], entry0, newinfo->size);
        }
@@ -696,7 +696,7 @@ static void get_counters(const struct xt_table_info *t,
                           counters,
                           &i);
 
-       for_each_cpu(cpu) {
+       for_each_possible_cpu(cpu) {
                if (cpu == curcpu)
                        continue;
                i = 0;
index d0d379c7df9abdbbde9165b5fc11ec2e7f969b6b..d7c472faa53b9666449b66dda6629137b1ae1970 100644 (file)
@@ -181,33 +181,26 @@ static struct nf_hook_ops arpt_ops[] = {
 
 static int __init arptable_filter_init(void)
 {
-       int ret, i;
+       int ret;
 
        /* Register table */
        ret = arpt_register_table(&packet_filter, &initial_table.repl);
        if (ret < 0)
                return ret;
 
-       for (i = 0; i < ARRAY_SIZE(arpt_ops); i++)
-               if ((ret = nf_register_hook(&arpt_ops[i])) < 0)
-                       goto cleanup_hooks;
+       ret = nf_register_hooks(arpt_ops, ARRAY_SIZE(arpt_ops));
+       if (ret < 0)
+               goto cleanup_table;
        return ret;
 
-cleanup_hooks:
-       while (--i >= 0)
-               nf_unregister_hook(&arpt_ops[i]);
-
+cleanup_table:
        arpt_unregister_table(&packet_filter);
        return ret;
 }
 
 static void __exit arptable_filter_fini(void)
 {
-       unsigned int i;
-
-       for (i = 0; i < ARRAY_SIZE(arpt_ops); i++)
-               nf_unregister_hook(&arpt_ops[i]);
-
+       nf_unregister_hooks(arpt_ops, ARRAY_SIZE(arpt_ops));
        arpt_unregister_table(&packet_filter);
 }
 
index ceaabc18202b71e8b26c7bdbb23fa08fc0c9a780..979a2eac6f003101438ecd518b1c4d9c2c365bf8 100644 (file)
@@ -133,7 +133,7 @@ static void ip_ct_event_cache_flush(void)
        struct ip_conntrack_ecache *ecache;
        int cpu;
 
-       for_each_cpu(cpu) {
+       for_each_possible_cpu(cpu) {
                ecache = &per_cpu(ip_conntrack_ecache, cpu);
                if (ecache->ct)
                        ip_conntrack_put(ecache->ct);
index daeb1395faa4db85096a108489b70645d9c9955b..2c2fb700d835364e76f5f479bec02aacafa80074 100644 (file)
@@ -9,37 +9,6 @@
  * Jozsef Kadlecsik <kadlec@blackhole.kfki.hu>
  *
  * For more information, please see http://nath323.sourceforge.net/
- *
- * Changes:
- *     2006-02-01 - initial version 0.1
- *
- *     2006-02-20 - version 0.2
- *       1. Changed source format to follow kernel conventions
- *       2. Deleted some unnecessary structures
- *       3. Minor fixes
- *
- *     2006-03-10 - version 0.3
- *       1. Added support for multiple TPKTs in one packet (suggested by
- *          Patrick McHardy)
- *       2. Avoid excessive stack usage (based on Patrick McHardy's patch)
- *       3. Added support for non-linear skb (based on Patrick McHardy's patch)
- *       4. Fixed missing H.245 module owner (Patrick McHardy)
- *       5. Avoid long RAS expectation chains (Patrick McHardy)
- *       6. Fixed incorrect __exit attribute (Patrick McHardy)
- *       7. Eliminated unnecessary return code
- *       8. Fixed incorrect use of NAT data from conntrack code (suggested by
- *          Patrick McHardy)
- *       9. Fixed TTL calculation error in RCF
- *       10. Added TTL support in RRQ
- *       11. Better support for separate TPKT header and data
- *
- *     2006-03-15 - version 0.4
- *       1. Added support for T.120 channels
- *       2. Added parameter gkrouted_only (suggested by Patrick McHardy)
- *       3. Splitted ASN.1 code and data (suggested by Patrick McHardy)
- *       4. Sort ASN.1 data to avoid forwarding declarations (suggested by
- *          Patrick McHardy)
- *       5. Reset next TPKT data length in get_tpkt_data()
  */
 
 #include <linux/config.h>
@@ -54,8 +23,6 @@
 #include <linux/netfilter_ipv4/ip_conntrack_h323.h>
 #include <linux/moduleparam.h>
 
-#include "ip_conntrack_helper_h323_asn1.h"
-
 #if 0
 #define DEBUGP printk
 #else
 #endif
 
 /* Parameters */
+static unsigned int default_rrq_ttl = 300;
+module_param(default_rrq_ttl, uint, 0600);
+MODULE_PARM_DESC(default_rrq_ttl, "use this TTL if it's missing in RRQ");
+
 static int gkrouted_only = 1;
 module_param(gkrouted_only, int, 0600);
 MODULE_PARM_DESC(gkrouted_only, "only accept calls from gatekeeper");
@@ -222,8 +193,8 @@ static int get_tpkt_data(struct sk_buff **pskb, struct ip_conntrack *ct,
 }
 
 /****************************************************************************/
-int get_h245_addr(unsigned char *data, H245_TransportAddress * addr,
-                 u_int32_t * ip, u_int16_t * port)
+static int get_h245_addr(unsigned char *data, H245_TransportAddress * addr,
+                        u_int32_t * ip, u_int16_t * port)
 {
        unsigned char *p;
 
@@ -1302,7 +1273,7 @@ static int process_rrq(struct sk_buff **pskb, struct ip_conntrack *ct,
                DEBUGP("ip_ct_ras: RRQ TTL = %u seconds\n", rrq->timeToLive);
                info->timeout = rrq->timeToLive;
        } else
-               info->timeout = 0;
+               info->timeout = default_rrq_ttl;
 
        return 0;
 }
@@ -1713,18 +1684,17 @@ static int __init init(void)
 module_init(init);
 module_exit(fini);
 
-EXPORT_SYMBOL(get_h245_addr);
-EXPORT_SYMBOL(get_h225_addr);
-EXPORT_SYMBOL(ip_conntrack_h245_expect);
-EXPORT_SYMBOL(ip_conntrack_q931_expect);
-EXPORT_SYMBOL(set_h245_addr_hook);
-EXPORT_SYMBOL(set_h225_addr_hook);
-EXPORT_SYMBOL(set_sig_addr_hook);
-EXPORT_SYMBOL(set_ras_addr_hook);
-EXPORT_SYMBOL(nat_rtp_rtcp_hook);
-EXPORT_SYMBOL(nat_t120_hook);
-EXPORT_SYMBOL(nat_h245_hook);
-EXPORT_SYMBOL(nat_q931_hook);
+EXPORT_SYMBOL_GPL(get_h225_addr);
+EXPORT_SYMBOL_GPL(ip_conntrack_h245_expect);
+EXPORT_SYMBOL_GPL(ip_conntrack_q931_expect);
+EXPORT_SYMBOL_GPL(set_h245_addr_hook);
+EXPORT_SYMBOL_GPL(set_h225_addr_hook);
+EXPORT_SYMBOL_GPL(set_sig_addr_hook);
+EXPORT_SYMBOL_GPL(set_ras_addr_hook);
+EXPORT_SYMBOL_GPL(nat_rtp_rtcp_hook);
+EXPORT_SYMBOL_GPL(nat_t120_hook);
+EXPORT_SYMBOL_GPL(nat_h245_hook);
+EXPORT_SYMBOL_GPL(nat_q931_hook);
 
 MODULE_AUTHOR("Jing Min Zhao <zhaojingmin@users.sourceforge.net>");
 MODULE_DESCRIPTION("H.323 connection tracking helper");
index afa525129b51a8ac0a6a53109a3d2c00c692410b..48078002e45075292624ea748bc2386b8e841728 100644 (file)
@@ -15,7 +15,7 @@
 #else
 #include <stdio.h>
 #endif
-#include "ip_conntrack_helper_h323_asn1.h"
+#include <linux/netfilter_ipv4/ip_conntrack_helper_h323_asn1.h>
 
 /* Trace Flag */
 #ifndef H323_TRACE
diff --git a/net/ipv4/netfilter/ip_conntrack_helper_h323_asn1.h b/net/ipv4/netfilter/ip_conntrack_helper_h323_asn1.h
deleted file mode 100644 (file)
index 0bd8280..0000000
+++ /dev/null
@@ -1,98 +0,0 @@
-/****************************************************************************
- * ip_conntrack_helper_h323_asn1.h - BER and PER decoding library for H.323
- *                                  conntrack/NAT module.
- *
- * Copyright (c) 2006 by Jing Min Zhao <zhaojingmin@hotmail.com>
- *
- * This source code is licensed under General Public License version 2.
- *
- *
- * This library is based on H.225 version 4, H.235 version 2 and H.245
- * version 7. It is extremely optimized to decode only the absolutely
- * necessary objects in a signal for Linux kernel NAT module use, so don't
- * expect it to be a full ASN.1 library.
- *
- * Features:
- *
- * 1. Small. The total size of code plus data is less than 20 KB (IA32).
- * 2. Fast. Decoding Netmeeting's Setup signal 1 million times on a PIII 866
- *    takes only 3.9 seconds.
- * 3. No memory allocation. It uses a static object. No need to initialize or
- *    cleanup.
- * 4. Thread safe.
- * 5. Support embedded architectures that has no misaligned memory access
- *    support.
- *
- * Limitations:
- *
- * 1. At most 30 faststart entries. Actually this is limited by ethernet's MTU.
- *    If a Setup signal contains more than 30 faststart, the packet size will
- *    very likely exceed the MTU size, then the TPKT will be fragmented. I
- *    don't know how to handle this in a Netfilter module. Anybody can help?
- *    Although I think 30 is enough for most of the cases.
- * 2. IPv4 addresses only.
- *
- ****************************************************************************/
-
-#ifndef _IP_CONNTRACK_HELPER_H323_ASN1_H_
-#define _IP_CONNTRACK_HELPER_H323_ASN1_H_
-
-/*****************************************************************************
- * H.323 Types
- ****************************************************************************/
-#include "ip_conntrack_helper_h323_types.h"
-
-typedef struct {
-       enum {
-               Q931_NationalEscape = 0x00,
-               Q931_Alerting = 0x01,
-               Q931_CallProceeding = 0x02,
-               Q931_Connect = 0x07,
-               Q931_ConnectAck = 0x0F,
-               Q931_Progress = 0x03,
-               Q931_Setup = 0x05,
-               Q931_SetupAck = 0x0D,
-               Q931_Resume = 0x26,
-               Q931_ResumeAck = 0x2E,
-               Q931_ResumeReject = 0x22,
-               Q931_Suspend = 0x25,
-               Q931_SuspendAck = 0x2D,
-               Q931_SuspendReject = 0x21,
-               Q931_UserInformation = 0x20,
-               Q931_Disconnect = 0x45,
-               Q931_Release = 0x4D,
-               Q931_ReleaseComplete = 0x5A,
-               Q931_Restart = 0x46,
-               Q931_RestartAck = 0x4E,
-               Q931_Segment = 0x60,
-               Q931_CongestionCtrl = 0x79,
-               Q931_Information = 0x7B,
-               Q931_Notify = 0x6E,
-               Q931_Status = 0x7D,
-               Q931_StatusEnquiry = 0x75,
-               Q931_Facility = 0x62
-       } MessageType;
-       H323_UserInformation UUIE;
-} Q931;
-
-/*****************************************************************************
- * Decode Functions Return Codes
- ****************************************************************************/
-
-#define H323_ERROR_NONE 0      /* Decoded successfully */
-#define H323_ERROR_STOP 1      /* Decoding stopped, not really an error */
-#define H323_ERROR_BOUND -1
-#define H323_ERROR_RANGE -2
-
-
-/*****************************************************************************
- * Decode Functions
- ****************************************************************************/
-
-int DecodeRasMessage(unsigned char *buf, size_t sz, RasMessage * ras);
-int DecodeQ931(unsigned char *buf, size_t sz, Q931 * q931);
-int DecodeMultimediaSystemControlMessage(unsigned char *buf, size_t sz,
-                                        MultimediaSystemControlMessage *
-                                        mscm);
-
-#endif
diff --git a/net/ipv4/netfilter/ip_conntrack_helper_h323_types.h b/net/ipv4/netfilter/ip_conntrack_helper_h323_types.h
deleted file mode 100644 (file)
index cc98f7a..0000000
+++ /dev/null
@@ -1,938 +0,0 @@
-/* Generated by Jing Min Zhao's ASN.1 parser, Mar 15 2006
- *
- * Copyright (c) 2006 Jing Min Zhao <zhaojingmin@users.sourceforge.net>
- *
- * This source code is licensed under General Public License version 2.
- */
-
-typedef struct TransportAddress_ipAddress {    /* SEQUENCE */
-       int options;            /* No use */
-       unsigned ip;
-} TransportAddress_ipAddress;
-
-typedef struct TransportAddress {      /* CHOICE */
-       enum {
-               eTransportAddress_ipAddress,
-               eTransportAddress_ipSourceRoute,
-               eTransportAddress_ipxAddress,
-               eTransportAddress_ip6Address,
-               eTransportAddress_netBios,
-               eTransportAddress_nsap,
-               eTransportAddress_nonStandardAddress,
-       } choice;
-       union {
-               TransportAddress_ipAddress ipAddress;
-       };
-} TransportAddress;
-
-typedef struct DataProtocolCapability {        /* CHOICE */
-       enum {
-               eDataProtocolCapability_nonStandard,
-               eDataProtocolCapability_v14buffered,
-               eDataProtocolCapability_v42lapm,
-               eDataProtocolCapability_hdlcFrameTunnelling,
-               eDataProtocolCapability_h310SeparateVCStack,
-               eDataProtocolCapability_h310SingleVCStack,
-               eDataProtocolCapability_transparent,
-               eDataProtocolCapability_segmentationAndReassembly,
-               eDataProtocolCapability_hdlcFrameTunnelingwSAR,
-               eDataProtocolCapability_v120,
-               eDataProtocolCapability_separateLANStack,
-               eDataProtocolCapability_v76wCompression,
-               eDataProtocolCapability_tcp,
-               eDataProtocolCapability_udp,
-       } choice;
-} DataProtocolCapability;
-
-typedef struct DataApplicationCapability_application { /* CHOICE */
-       enum {
-               eDataApplicationCapability_application_nonStandard,
-               eDataApplicationCapability_application_t120,
-               eDataApplicationCapability_application_dsm_cc,
-               eDataApplicationCapability_application_userData,
-               eDataApplicationCapability_application_t84,
-               eDataApplicationCapability_application_t434,
-               eDataApplicationCapability_application_h224,
-               eDataApplicationCapability_application_nlpid,
-               eDataApplicationCapability_application_dsvdControl,
-               eDataApplicationCapability_application_h222DataPartitioning,
-               eDataApplicationCapability_application_t30fax,
-               eDataApplicationCapability_application_t140,
-               eDataApplicationCapability_application_t38fax,
-               eDataApplicationCapability_application_genericDataCapability,
-       } choice;
-       union {
-               DataProtocolCapability t120;
-       };
-} DataApplicationCapability_application;
-
-typedef struct DataApplicationCapability {     /* SEQUENCE */
-       int options;            /* No use */
-       DataApplicationCapability_application application;
-} DataApplicationCapability;
-
-typedef struct DataType {      /* CHOICE */
-       enum {
-               eDataType_nonStandard,
-               eDataType_nullData,
-               eDataType_videoData,
-               eDataType_audioData,
-               eDataType_data,
-               eDataType_encryptionData,
-               eDataType_h235Control,
-               eDataType_h235Media,
-               eDataType_multiplexedStream,
-       } choice;
-       union {
-               DataApplicationCapability data;
-       };
-} DataType;
-
-typedef struct UnicastAddress_iPAddress {      /* SEQUENCE */
-       int options;            /* No use */
-       unsigned network;
-} UnicastAddress_iPAddress;
-
-typedef struct UnicastAddress {        /* CHOICE */
-       enum {
-               eUnicastAddress_iPAddress,
-               eUnicastAddress_iPXAddress,
-               eUnicastAddress_iP6Address,
-               eUnicastAddress_netBios,
-               eUnicastAddress_iPSourceRouteAddress,
-               eUnicastAddress_nsap,
-               eUnicastAddress_nonStandardAddress,
-       } choice;
-       union {
-               UnicastAddress_iPAddress iPAddress;
-       };
-} UnicastAddress;
-
-typedef struct H245_TransportAddress { /* CHOICE */
-       enum {
-               eH245_TransportAddress_unicastAddress,
-               eH245_TransportAddress_multicastAddress,
-       } choice;
-       union {
-               UnicastAddress unicastAddress;
-       };
-} H245_TransportAddress;
-
-typedef struct H2250LogicalChannelParameters { /* SEQUENCE */
-       enum {
-               eH2250LogicalChannelParameters_nonStandard = (1 << 31),
-               eH2250LogicalChannelParameters_associatedSessionID =
-                   (1 << 30),
-               eH2250LogicalChannelParameters_mediaChannel = (1 << 29),
-               eH2250LogicalChannelParameters_mediaGuaranteedDelivery =
-                   (1 << 28),
-               eH2250LogicalChannelParameters_mediaControlChannel =
-                   (1 << 27),
-               eH2250LogicalChannelParameters_mediaControlGuaranteedDelivery
-                   = (1 << 26),
-               eH2250LogicalChannelParameters_silenceSuppression = (1 << 25),
-               eH2250LogicalChannelParameters_destination = (1 << 24),
-               eH2250LogicalChannelParameters_dynamicRTPPayloadType =
-                   (1 << 23),
-               eH2250LogicalChannelParameters_mediaPacketization = (1 << 22),
-               eH2250LogicalChannelParameters_transportCapability =
-                   (1 << 21),
-               eH2250LogicalChannelParameters_redundancyEncoding = (1 << 20),
-               eH2250LogicalChannelParameters_source = (1 << 19),
-       } options;
-       H245_TransportAddress mediaChannel;
-       H245_TransportAddress mediaControlChannel;
-} H2250LogicalChannelParameters;
-
-typedef struct OpenLogicalChannel_forwardLogicalChannelParameters_multiplexParameters {        /* CHOICE */
-       enum {
-               eOpenLogicalChannel_forwardLogicalChannelParameters_multiplexParameters_h222LogicalChannelParameters,
-               eOpenLogicalChannel_forwardLogicalChannelParameters_multiplexParameters_h223LogicalChannelParameters,
-               eOpenLogicalChannel_forwardLogicalChannelParameters_multiplexParameters_v76LogicalChannelParameters,
-               eOpenLogicalChannel_forwardLogicalChannelParameters_multiplexParameters_h2250LogicalChannelParameters,
-               eOpenLogicalChannel_forwardLogicalChannelParameters_multiplexParameters_none,
-       } choice;
-       union {
-               H2250LogicalChannelParameters h2250LogicalChannelParameters;
-       };
-} OpenLogicalChannel_forwardLogicalChannelParameters_multiplexParameters;
-
-typedef struct OpenLogicalChannel_forwardLogicalChannelParameters {    /* SEQUENCE */
-       enum {
-               eOpenLogicalChannel_forwardLogicalChannelParameters_portNumber
-                   = (1 << 31),
-               eOpenLogicalChannel_forwardLogicalChannelParameters_forwardLogicalChannelDependency
-                   = (1 << 30),
-               eOpenLogicalChannel_forwardLogicalChannelParameters_replacementFor
-                   = (1 << 29),
-       } options;
-       DataType dataType;
-       OpenLogicalChannel_forwardLogicalChannelParameters_multiplexParameters
-           multiplexParameters;
-} OpenLogicalChannel_forwardLogicalChannelParameters;
-
-typedef struct OpenLogicalChannel_reverseLogicalChannelParameters_multiplexParameters {        /* CHOICE */
-       enum {
-               eOpenLogicalChannel_reverseLogicalChannelParameters_multiplexParameters_h223LogicalChannelParameters,
-               eOpenLogicalChannel_reverseLogicalChannelParameters_multiplexParameters_v76LogicalChannelParameters,
-               eOpenLogicalChannel_reverseLogicalChannelParameters_multiplexParameters_h2250LogicalChannelParameters,
-       } choice;
-       union {
-               H2250LogicalChannelParameters h2250LogicalChannelParameters;
-       };
-} OpenLogicalChannel_reverseLogicalChannelParameters_multiplexParameters;
-
-typedef struct OpenLogicalChannel_reverseLogicalChannelParameters {    /* SEQUENCE */
-       enum {
-               eOpenLogicalChannel_reverseLogicalChannelParameters_multiplexParameters
-                   = (1 << 31),
-               eOpenLogicalChannel_reverseLogicalChannelParameters_reverseLogicalChannelDependency
-                   = (1 << 30),
-               eOpenLogicalChannel_reverseLogicalChannelParameters_replacementFor
-                   = (1 << 29),
-       } options;
-       OpenLogicalChannel_reverseLogicalChannelParameters_multiplexParameters
-           multiplexParameters;
-} OpenLogicalChannel_reverseLogicalChannelParameters;
-
-typedef struct NetworkAccessParameters_networkAddress {        /* CHOICE */
-       enum {
-               eNetworkAccessParameters_networkAddress_q2931Address,
-               eNetworkAccessParameters_networkAddress_e164Address,
-               eNetworkAccessParameters_networkAddress_localAreaAddress,
-       } choice;
-       union {
-               H245_TransportAddress localAreaAddress;
-       };
-} NetworkAccessParameters_networkAddress;
-
-typedef struct NetworkAccessParameters {       /* SEQUENCE */
-       enum {
-               eNetworkAccessParameters_distribution = (1 << 31),
-               eNetworkAccessParameters_externalReference = (1 << 30),
-               eNetworkAccessParameters_t120SetupProcedure = (1 << 29),
-       } options;
-       NetworkAccessParameters_networkAddress networkAddress;
-} NetworkAccessParameters;
-
-typedef struct OpenLogicalChannel {    /* SEQUENCE */
-       enum {
-               eOpenLogicalChannel_reverseLogicalChannelParameters =
-                   (1 << 31),
-               eOpenLogicalChannel_separateStack = (1 << 30),
-               eOpenLogicalChannel_encryptionSync = (1 << 29),
-       } options;
-       OpenLogicalChannel_forwardLogicalChannelParameters
-           forwardLogicalChannelParameters;
-       OpenLogicalChannel_reverseLogicalChannelParameters
-           reverseLogicalChannelParameters;
-       NetworkAccessParameters separateStack;
-} OpenLogicalChannel;
-
-typedef struct Setup_UUIE_fastStart {  /* SEQUENCE OF */
-       int count;
-       OpenLogicalChannel item[30];
-} Setup_UUIE_fastStart;
-
-typedef struct Setup_UUIE {    /* SEQUENCE */
-       enum {
-               eSetup_UUIE_h245Address = (1 << 31),
-               eSetup_UUIE_sourceAddress = (1 << 30),
-               eSetup_UUIE_destinationAddress = (1 << 29),
-               eSetup_UUIE_destCallSignalAddress = (1 << 28),
-               eSetup_UUIE_destExtraCallInfo = (1 << 27),
-               eSetup_UUIE_destExtraCRV = (1 << 26),
-               eSetup_UUIE_callServices = (1 << 25),
-               eSetup_UUIE_sourceCallSignalAddress = (1 << 24),
-               eSetup_UUIE_remoteExtensionAddress = (1 << 23),
-               eSetup_UUIE_callIdentifier = (1 << 22),
-               eSetup_UUIE_h245SecurityCapability = (1 << 21),
-               eSetup_UUIE_tokens = (1 << 20),
-               eSetup_UUIE_cryptoTokens = (1 << 19),
-               eSetup_UUIE_fastStart = (1 << 18),
-               eSetup_UUIE_mediaWaitForConnect = (1 << 17),
-               eSetup_UUIE_canOverlapSend = (1 << 16),
-               eSetup_UUIE_endpointIdentifier = (1 << 15),
-               eSetup_UUIE_multipleCalls = (1 << 14),
-               eSetup_UUIE_maintainConnection = (1 << 13),
-               eSetup_UUIE_connectionParameters = (1 << 12),
-               eSetup_UUIE_language = (1 << 11),
-               eSetup_UUIE_presentationIndicator = (1 << 10),
-               eSetup_UUIE_screeningIndicator = (1 << 9),
-               eSetup_UUIE_serviceControl = (1 << 8),
-               eSetup_UUIE_symmetricOperationRequired = (1 << 7),
-               eSetup_UUIE_capacity = (1 << 6),
-               eSetup_UUIE_circuitInfo = (1 << 5),
-               eSetup_UUIE_desiredProtocols = (1 << 4),
-               eSetup_UUIE_neededFeatures = (1 << 3),
-               eSetup_UUIE_desiredFeatures = (1 << 2),
-               eSetup_UUIE_supportedFeatures = (1 << 1),
-               eSetup_UUIE_parallelH245Control = (1 << 0),
-       } options;
-       TransportAddress h245Address;
-       TransportAddress destCallSignalAddress;
-       TransportAddress sourceCallSignalAddress;
-       Setup_UUIE_fastStart fastStart;
-} Setup_UUIE;
-
-typedef struct CallProceeding_UUIE_fastStart { /* SEQUENCE OF */
-       int count;
-       OpenLogicalChannel item[30];
-} CallProceeding_UUIE_fastStart;
-
-typedef struct CallProceeding_UUIE {   /* SEQUENCE */
-       enum {
-               eCallProceeding_UUIE_h245Address = (1 << 31),
-               eCallProceeding_UUIE_callIdentifier = (1 << 30),
-               eCallProceeding_UUIE_h245SecurityMode = (1 << 29),
-               eCallProceeding_UUIE_tokens = (1 << 28),
-               eCallProceeding_UUIE_cryptoTokens = (1 << 27),
-               eCallProceeding_UUIE_fastStart = (1 << 26),
-               eCallProceeding_UUIE_multipleCalls = (1 << 25),
-               eCallProceeding_UUIE_maintainConnection = (1 << 24),
-               eCallProceeding_UUIE_fastConnectRefused = (1 << 23),
-               eCallProceeding_UUIE_featureSet = (1 << 22),
-       } options;
-       TransportAddress h245Address;
-       CallProceeding_UUIE_fastStart fastStart;
-} CallProceeding_UUIE;
-
-typedef struct Connect_UUIE_fastStart {        /* SEQUENCE OF */
-       int count;
-       OpenLogicalChannel item[30];
-} Connect_UUIE_fastStart;
-
-typedef struct Connect_UUIE {  /* SEQUENCE */
-       enum {
-               eConnect_UUIE_h245Address = (1 << 31),
-               eConnect_UUIE_callIdentifier = (1 << 30),
-               eConnect_UUIE_h245SecurityMode = (1 << 29),
-               eConnect_UUIE_tokens = (1 << 28),
-               eConnect_UUIE_cryptoTokens = (1 << 27),
-               eConnect_UUIE_fastStart = (1 << 26),
-               eConnect_UUIE_multipleCalls = (1 << 25),
-               eConnect_UUIE_maintainConnection = (1 << 24),
-               eConnect_UUIE_language = (1 << 23),
-               eConnect_UUIE_connectedAddress = (1 << 22),
-               eConnect_UUIE_presentationIndicator = (1 << 21),
-               eConnect_UUIE_screeningIndicator = (1 << 20),
-               eConnect_UUIE_fastConnectRefused = (1 << 19),
-               eConnect_UUIE_serviceControl = (1 << 18),
-               eConnect_UUIE_capacity = (1 << 17),
-               eConnect_UUIE_featureSet = (1 << 16),
-       } options;
-       TransportAddress h245Address;
-       Connect_UUIE_fastStart fastStart;
-} Connect_UUIE;
-
-typedef struct Alerting_UUIE_fastStart {       /* SEQUENCE OF */
-       int count;
-       OpenLogicalChannel item[30];
-} Alerting_UUIE_fastStart;
-
-typedef struct Alerting_UUIE { /* SEQUENCE */
-       enum {
-               eAlerting_UUIE_h245Address = (1 << 31),
-               eAlerting_UUIE_callIdentifier = (1 << 30),
-               eAlerting_UUIE_h245SecurityMode = (1 << 29),
-               eAlerting_UUIE_tokens = (1 << 28),
-               eAlerting_UUIE_cryptoTokens = (1 << 27),
-               eAlerting_UUIE_fastStart = (1 << 26),
-               eAlerting_UUIE_multipleCalls = (1 << 25),
-               eAlerting_UUIE_maintainConnection = (1 << 24),
-               eAlerting_UUIE_alertingAddress = (1 << 23),
-               eAlerting_UUIE_presentationIndicator = (1 << 22),
-               eAlerting_UUIE_screeningIndicator = (1 << 21),
-               eAlerting_UUIE_fastConnectRefused = (1 << 20),
-               eAlerting_UUIE_serviceControl = (1 << 19),
-               eAlerting_UUIE_capacity = (1 << 18),
-               eAlerting_UUIE_featureSet = (1 << 17),
-       } options;
-       TransportAddress h245Address;
-       Alerting_UUIE_fastStart fastStart;
-} Alerting_UUIE;
-
-typedef struct Information_UUIE_fastStart {    /* SEQUENCE OF */
-       int count;
-       OpenLogicalChannel item[30];
-} Information_UUIE_fastStart;
-
-typedef struct Information_UUIE {      /* SEQUENCE */
-       enum {
-               eInformation_UUIE_callIdentifier = (1 << 31),
-               eInformation_UUIE_tokens = (1 << 30),
-               eInformation_UUIE_cryptoTokens = (1 << 29),
-               eInformation_UUIE_fastStart = (1 << 28),
-               eInformation_UUIE_fastConnectRefused = (1 << 27),
-               eInformation_UUIE_circuitInfo = (1 << 26),
-       } options;
-       Information_UUIE_fastStart fastStart;
-} Information_UUIE;
-
-typedef struct FacilityReason {        /* CHOICE */
-       enum {
-               eFacilityReason_routeCallToGatekeeper,
-               eFacilityReason_callForwarded,
-               eFacilityReason_routeCallToMC,
-               eFacilityReason_undefinedReason,
-               eFacilityReason_conferenceListChoice,
-               eFacilityReason_startH245,
-               eFacilityReason_noH245,
-               eFacilityReason_newTokens,
-               eFacilityReason_featureSetUpdate,
-               eFacilityReason_forwardedElements,
-               eFacilityReason_transportedInformation,
-       } choice;
-} FacilityReason;
-
-typedef struct Facility_UUIE_fastStart {       /* SEQUENCE OF */
-       int count;
-       OpenLogicalChannel item[30];
-} Facility_UUIE_fastStart;
-
-typedef struct Facility_UUIE { /* SEQUENCE */
-       enum {
-               eFacility_UUIE_alternativeAddress = (1 << 31),
-               eFacility_UUIE_alternativeAliasAddress = (1 << 30),
-               eFacility_UUIE_conferenceID = (1 << 29),
-               eFacility_UUIE_callIdentifier = (1 << 28),
-               eFacility_UUIE_destExtraCallInfo = (1 << 27),
-               eFacility_UUIE_remoteExtensionAddress = (1 << 26),
-               eFacility_UUIE_tokens = (1 << 25),
-               eFacility_UUIE_cryptoTokens = (1 << 24),
-               eFacility_UUIE_conferences = (1 << 23),
-               eFacility_UUIE_h245Address = (1 << 22),
-               eFacility_UUIE_fastStart = (1 << 21),
-               eFacility_UUIE_multipleCalls = (1 << 20),
-               eFacility_UUIE_maintainConnection = (1 << 19),
-               eFacility_UUIE_fastConnectRefused = (1 << 18),
-               eFacility_UUIE_serviceControl = (1 << 17),
-               eFacility_UUIE_circuitInfo = (1 << 16),
-               eFacility_UUIE_featureSet = (1 << 15),
-               eFacility_UUIE_destinationInfo = (1 << 14),
-               eFacility_UUIE_h245SecurityMode = (1 << 13),
-       } options;
-       FacilityReason reason;
-       TransportAddress h245Address;
-       Facility_UUIE_fastStart fastStart;
-} Facility_UUIE;
-
-typedef struct Progress_UUIE_fastStart {       /* SEQUENCE OF */
-       int count;
-       OpenLogicalChannel item[30];
-} Progress_UUIE_fastStart;
-
-typedef struct Progress_UUIE { /* SEQUENCE */
-       enum {
-               eProgress_UUIE_h245Address = (1 << 31),
-               eProgress_UUIE_h245SecurityMode = (1 << 30),
-               eProgress_UUIE_tokens = (1 << 29),
-               eProgress_UUIE_cryptoTokens = (1 << 28),
-               eProgress_UUIE_fastStart = (1 << 27),
-               eProgress_UUIE_multipleCalls = (1 << 26),
-               eProgress_UUIE_maintainConnection = (1 << 25),
-               eProgress_UUIE_fastConnectRefused = (1 << 24),
-       } options;
-       TransportAddress h245Address;
-       Progress_UUIE_fastStart fastStart;
-} Progress_UUIE;
-
-typedef struct H323_UU_PDU_h323_message_body { /* CHOICE */
-       enum {
-               eH323_UU_PDU_h323_message_body_setup,
-               eH323_UU_PDU_h323_message_body_callProceeding,
-               eH323_UU_PDU_h323_message_body_connect,
-               eH323_UU_PDU_h323_message_body_alerting,
-               eH323_UU_PDU_h323_message_body_information,
-               eH323_UU_PDU_h323_message_body_releaseComplete,
-               eH323_UU_PDU_h323_message_body_facility,
-               eH323_UU_PDU_h323_message_body_progress,
-               eH323_UU_PDU_h323_message_body_empty,
-               eH323_UU_PDU_h323_message_body_status,
-               eH323_UU_PDU_h323_message_body_statusInquiry,
-               eH323_UU_PDU_h323_message_body_setupAcknowledge,
-               eH323_UU_PDU_h323_message_body_notify,
-       } choice;
-       union {
-               Setup_UUIE setup;
-               CallProceeding_UUIE callProceeding;
-               Connect_UUIE connect;
-               Alerting_UUIE alerting;
-               Information_UUIE information;
-               Facility_UUIE facility;
-               Progress_UUIE progress;
-       };
-} H323_UU_PDU_h323_message_body;
-
-typedef struct RequestMessage {        /* CHOICE */
-       enum {
-               eRequestMessage_nonStandard,
-               eRequestMessage_masterSlaveDetermination,
-               eRequestMessage_terminalCapabilitySet,
-               eRequestMessage_openLogicalChannel,
-               eRequestMessage_closeLogicalChannel,
-               eRequestMessage_requestChannelClose,
-               eRequestMessage_multiplexEntrySend,
-               eRequestMessage_requestMultiplexEntry,
-               eRequestMessage_requestMode,
-               eRequestMessage_roundTripDelayRequest,
-               eRequestMessage_maintenanceLoopRequest,
-               eRequestMessage_communicationModeRequest,
-               eRequestMessage_conferenceRequest,
-               eRequestMessage_multilinkRequest,
-               eRequestMessage_logicalChannelRateRequest,
-       } choice;
-       union {
-               OpenLogicalChannel openLogicalChannel;
-       };
-} RequestMessage;
-
-typedef struct OpenLogicalChannelAck_reverseLogicalChannelParameters_multiplexParameters {     /* CHOICE */
-       enum {
-               eOpenLogicalChannelAck_reverseLogicalChannelParameters_multiplexParameters_h222LogicalChannelParameters,
-               eOpenLogicalChannelAck_reverseLogicalChannelParameters_multiplexParameters_h2250LogicalChannelParameters,
-       } choice;
-       union {
-               H2250LogicalChannelParameters h2250LogicalChannelParameters;
-       };
-} OpenLogicalChannelAck_reverseLogicalChannelParameters_multiplexParameters;
-
-typedef struct OpenLogicalChannelAck_reverseLogicalChannelParameters { /* SEQUENCE */
-       enum {
-               eOpenLogicalChannelAck_reverseLogicalChannelParameters_portNumber
-                   = (1 << 31),
-               eOpenLogicalChannelAck_reverseLogicalChannelParameters_multiplexParameters
-                   = (1 << 30),
-               eOpenLogicalChannelAck_reverseLogicalChannelParameters_replacementFor
-                   = (1 << 29),
-       } options;
-       OpenLogicalChannelAck_reverseLogicalChannelParameters_multiplexParameters
-           multiplexParameters;
-} OpenLogicalChannelAck_reverseLogicalChannelParameters;
-
-typedef struct H2250LogicalChannelAckParameters {      /* SEQUENCE */
-       enum {
-               eH2250LogicalChannelAckParameters_nonStandard = (1 << 31),
-               eH2250LogicalChannelAckParameters_sessionID = (1 << 30),
-               eH2250LogicalChannelAckParameters_mediaChannel = (1 << 29),
-               eH2250LogicalChannelAckParameters_mediaControlChannel =
-                   (1 << 28),
-               eH2250LogicalChannelAckParameters_dynamicRTPPayloadType =
-                   (1 << 27),
-               eH2250LogicalChannelAckParameters_flowControlToZero =
-                   (1 << 26),
-               eH2250LogicalChannelAckParameters_portNumber = (1 << 25),
-       } options;
-       H245_TransportAddress mediaChannel;
-       H245_TransportAddress mediaControlChannel;
-} H2250LogicalChannelAckParameters;
-
-typedef struct OpenLogicalChannelAck_forwardMultiplexAckParameters {   /* CHOICE */
-       enum {
-               eOpenLogicalChannelAck_forwardMultiplexAckParameters_h2250LogicalChannelAckParameters,
-       } choice;
-       union {
-               H2250LogicalChannelAckParameters
-                   h2250LogicalChannelAckParameters;
-       };
-} OpenLogicalChannelAck_forwardMultiplexAckParameters;
-
-typedef struct OpenLogicalChannelAck { /* SEQUENCE */
-       enum {
-               eOpenLogicalChannelAck_reverseLogicalChannelParameters =
-                   (1 << 31),
-               eOpenLogicalChannelAck_separateStack = (1 << 30),
-               eOpenLogicalChannelAck_forwardMultiplexAckParameters =
-                   (1 << 29),
-               eOpenLogicalChannelAck_encryptionSync = (1 << 28),
-       } options;
-       OpenLogicalChannelAck_reverseLogicalChannelParameters
-           reverseLogicalChannelParameters;
-       OpenLogicalChannelAck_forwardMultiplexAckParameters
-           forwardMultiplexAckParameters;
-} OpenLogicalChannelAck;
-
-typedef struct ResponseMessage {       /* CHOICE */
-       enum {
-               eResponseMessage_nonStandard,
-               eResponseMessage_masterSlaveDeterminationAck,
-               eResponseMessage_masterSlaveDeterminationReject,
-               eResponseMessage_terminalCapabilitySetAck,
-               eResponseMessage_terminalCapabilitySetReject,
-               eResponseMessage_openLogicalChannelAck,
-               eResponseMessage_openLogicalChannelReject,
-               eResponseMessage_closeLogicalChannelAck,
-               eResponseMessage_requestChannelCloseAck,
-               eResponseMessage_requestChannelCloseReject,
-               eResponseMessage_multiplexEntrySendAck,
-               eResponseMessage_multiplexEntrySendReject,
-               eResponseMessage_requestMultiplexEntryAck,
-               eResponseMessage_requestMultiplexEntryReject,
-               eResponseMessage_requestModeAck,
-               eResponseMessage_requestModeReject,
-               eResponseMessage_roundTripDelayResponse,
-               eResponseMessage_maintenanceLoopAck,
-               eResponseMessage_maintenanceLoopReject,
-               eResponseMessage_communicationModeResponse,
-               eResponseMessage_conferenceResponse,
-               eResponseMessage_multilinkResponse,
-               eResponseMessage_logicalChannelRateAcknowledge,
-               eResponseMessage_logicalChannelRateReject,
-       } choice;
-       union {
-               OpenLogicalChannelAck openLogicalChannelAck;
-       };
-} ResponseMessage;
-
-typedef struct MultimediaSystemControlMessage {        /* CHOICE */
-       enum {
-               eMultimediaSystemControlMessage_request,
-               eMultimediaSystemControlMessage_response,
-               eMultimediaSystemControlMessage_command,
-               eMultimediaSystemControlMessage_indication,
-       } choice;
-       union {
-               RequestMessage request;
-               ResponseMessage response;
-       };
-} MultimediaSystemControlMessage;
-
-typedef struct H323_UU_PDU_h245Control {       /* SEQUENCE OF */
-       int count;
-       MultimediaSystemControlMessage item[4];
-} H323_UU_PDU_h245Control;
-
-typedef struct H323_UU_PDU {   /* SEQUENCE */
-       enum {
-               eH323_UU_PDU_nonStandardData = (1 << 31),
-               eH323_UU_PDU_h4501SupplementaryService = (1 << 30),
-               eH323_UU_PDU_h245Tunneling = (1 << 29),
-               eH323_UU_PDU_h245Control = (1 << 28),
-               eH323_UU_PDU_nonStandardControl = (1 << 27),
-               eH323_UU_PDU_callLinkage = (1 << 26),
-               eH323_UU_PDU_tunnelledSignallingMessage = (1 << 25),
-               eH323_UU_PDU_provisionalRespToH245Tunneling = (1 << 24),
-               eH323_UU_PDU_stimulusControl = (1 << 23),
-               eH323_UU_PDU_genericData = (1 << 22),
-       } options;
-       H323_UU_PDU_h323_message_body h323_message_body;
-       H323_UU_PDU_h245Control h245Control;
-} H323_UU_PDU;
-
-typedef struct H323_UserInformation {  /* SEQUENCE */
-       enum {
-               eH323_UserInformation_user_data = (1 << 31),
-       } options;
-       H323_UU_PDU h323_uu_pdu;
-} H323_UserInformation;
-
-typedef struct GatekeeperRequest {     /* SEQUENCE */
-       enum {
-               eGatekeeperRequest_nonStandardData = (1 << 31),
-               eGatekeeperRequest_gatekeeperIdentifier = (1 << 30),
-               eGatekeeperRequest_callServices = (1 << 29),
-               eGatekeeperRequest_endpointAlias = (1 << 28),
-               eGatekeeperRequest_alternateEndpoints = (1 << 27),
-               eGatekeeperRequest_tokens = (1 << 26),
-               eGatekeeperRequest_cryptoTokens = (1 << 25),
-               eGatekeeperRequest_authenticationCapability = (1 << 24),
-               eGatekeeperRequest_algorithmOIDs = (1 << 23),
-               eGatekeeperRequest_integrity = (1 << 22),
-               eGatekeeperRequest_integrityCheckValue = (1 << 21),
-               eGatekeeperRequest_supportsAltGK = (1 << 20),
-               eGatekeeperRequest_featureSet = (1 << 19),
-               eGatekeeperRequest_genericData = (1 << 18),
-       } options;
-       TransportAddress rasAddress;
-} GatekeeperRequest;
-
-typedef struct GatekeeperConfirm {     /* SEQUENCE */
-       enum {
-               eGatekeeperConfirm_nonStandardData = (1 << 31),
-               eGatekeeperConfirm_gatekeeperIdentifier = (1 << 30),
-               eGatekeeperConfirm_alternateGatekeeper = (1 << 29),
-               eGatekeeperConfirm_authenticationMode = (1 << 28),
-               eGatekeeperConfirm_tokens = (1 << 27),
-               eGatekeeperConfirm_cryptoTokens = (1 << 26),
-               eGatekeeperConfirm_algorithmOID = (1 << 25),
-               eGatekeeperConfirm_integrity = (1 << 24),
-               eGatekeeperConfirm_integrityCheckValue = (1 << 23),
-               eGatekeeperConfirm_featureSet = (1 << 22),
-               eGatekeeperConfirm_genericData = (1 << 21),
-       } options;
-       TransportAddress rasAddress;
-} GatekeeperConfirm;
-
-typedef struct RegistrationRequest_callSignalAddress { /* SEQUENCE OF */
-       int count;
-       TransportAddress item[10];
-} RegistrationRequest_callSignalAddress;
-
-typedef struct RegistrationRequest_rasAddress {        /* SEQUENCE OF */
-       int count;
-       TransportAddress item[10];
-} RegistrationRequest_rasAddress;
-
-typedef struct RegistrationRequest {   /* SEQUENCE */
-       enum {
-               eRegistrationRequest_nonStandardData = (1 << 31),
-               eRegistrationRequest_terminalAlias = (1 << 30),
-               eRegistrationRequest_gatekeeperIdentifier = (1 << 29),
-               eRegistrationRequest_alternateEndpoints = (1 << 28),
-               eRegistrationRequest_timeToLive = (1 << 27),
-               eRegistrationRequest_tokens = (1 << 26),
-               eRegistrationRequest_cryptoTokens = (1 << 25),
-               eRegistrationRequest_integrityCheckValue = (1 << 24),
-               eRegistrationRequest_keepAlive = (1 << 23),
-               eRegistrationRequest_endpointIdentifier = (1 << 22),
-               eRegistrationRequest_willSupplyUUIEs = (1 << 21),
-               eRegistrationRequest_maintainConnection = (1 << 20),
-               eRegistrationRequest_alternateTransportAddresses = (1 << 19),
-               eRegistrationRequest_additiveRegistration = (1 << 18),
-               eRegistrationRequest_terminalAliasPattern = (1 << 17),
-               eRegistrationRequest_supportsAltGK = (1 << 16),
-               eRegistrationRequest_usageReportingCapability = (1 << 15),
-               eRegistrationRequest_multipleCalls = (1 << 14),
-               eRegistrationRequest_supportedH248Packages = (1 << 13),
-               eRegistrationRequest_callCreditCapability = (1 << 12),
-               eRegistrationRequest_capacityReportingCapability = (1 << 11),
-               eRegistrationRequest_capacity = (1 << 10),
-               eRegistrationRequest_featureSet = (1 << 9),
-               eRegistrationRequest_genericData = (1 << 8),
-       } options;
-       RegistrationRequest_callSignalAddress callSignalAddress;
-       RegistrationRequest_rasAddress rasAddress;
-       unsigned timeToLive;
-} RegistrationRequest;
-
-typedef struct RegistrationConfirm_callSignalAddress { /* SEQUENCE OF */
-       int count;
-       TransportAddress item[10];
-} RegistrationConfirm_callSignalAddress;
-
-typedef struct RegistrationConfirm {   /* SEQUENCE */
-       enum {
-               eRegistrationConfirm_nonStandardData = (1 << 31),
-               eRegistrationConfirm_terminalAlias = (1 << 30),
-               eRegistrationConfirm_gatekeeperIdentifier = (1 << 29),
-               eRegistrationConfirm_alternateGatekeeper = (1 << 28),
-               eRegistrationConfirm_timeToLive = (1 << 27),
-               eRegistrationConfirm_tokens = (1 << 26),
-               eRegistrationConfirm_cryptoTokens = (1 << 25),
-               eRegistrationConfirm_integrityCheckValue = (1 << 24),
-               eRegistrationConfirm_willRespondToIRR = (1 << 23),
-               eRegistrationConfirm_preGrantedARQ = (1 << 22),
-               eRegistrationConfirm_maintainConnection = (1 << 21),
-               eRegistrationConfirm_serviceControl = (1 << 20),
-               eRegistrationConfirm_supportsAdditiveRegistration = (1 << 19),
-               eRegistrationConfirm_terminalAliasPattern = (1 << 18),
-               eRegistrationConfirm_supportedPrefixes = (1 << 17),
-               eRegistrationConfirm_usageSpec = (1 << 16),
-               eRegistrationConfirm_featureServerAlias = (1 << 15),
-               eRegistrationConfirm_capacityReportingSpec = (1 << 14),
-               eRegistrationConfirm_featureSet = (1 << 13),
-               eRegistrationConfirm_genericData = (1 << 12),
-       } options;
-       RegistrationConfirm_callSignalAddress callSignalAddress;
-       unsigned timeToLive;
-} RegistrationConfirm;
-
-typedef struct UnregistrationRequest_callSignalAddress {       /* SEQUENCE OF */
-       int count;
-       TransportAddress item[10];
-} UnregistrationRequest_callSignalAddress;
-
-typedef struct UnregistrationRequest { /* SEQUENCE */
-       enum {
-               eUnregistrationRequest_endpointAlias = (1 << 31),
-               eUnregistrationRequest_nonStandardData = (1 << 30),
-               eUnregistrationRequest_endpointIdentifier = (1 << 29),
-               eUnregistrationRequest_alternateEndpoints = (1 << 28),
-               eUnregistrationRequest_gatekeeperIdentifier = (1 << 27),
-               eUnregistrationRequest_tokens = (1 << 26),
-               eUnregistrationRequest_cryptoTokens = (1 << 25),
-               eUnregistrationRequest_integrityCheckValue = (1 << 24),
-               eUnregistrationRequest_reason = (1 << 23),
-               eUnregistrationRequest_endpointAliasPattern = (1 << 22),
-               eUnregistrationRequest_supportedPrefixes = (1 << 21),
-               eUnregistrationRequest_alternateGatekeeper = (1 << 20),
-               eUnregistrationRequest_genericData = (1 << 19),
-       } options;
-       UnregistrationRequest_callSignalAddress callSignalAddress;
-} UnregistrationRequest;
-
-typedef struct AdmissionRequest {      /* SEQUENCE */
-       enum {
-               eAdmissionRequest_callModel = (1 << 31),
-               eAdmissionRequest_destinationInfo = (1 << 30),
-               eAdmissionRequest_destCallSignalAddress = (1 << 29),
-               eAdmissionRequest_destExtraCallInfo = (1 << 28),
-               eAdmissionRequest_srcCallSignalAddress = (1 << 27),
-               eAdmissionRequest_nonStandardData = (1 << 26),
-               eAdmissionRequest_callServices = (1 << 25),
-               eAdmissionRequest_canMapAlias = (1 << 24),
-               eAdmissionRequest_callIdentifier = (1 << 23),
-               eAdmissionRequest_srcAlternatives = (1 << 22),
-               eAdmissionRequest_destAlternatives = (1 << 21),
-               eAdmissionRequest_gatekeeperIdentifier = (1 << 20),
-               eAdmissionRequest_tokens = (1 << 19),
-               eAdmissionRequest_cryptoTokens = (1 << 18),
-               eAdmissionRequest_integrityCheckValue = (1 << 17),
-               eAdmissionRequest_transportQOS = (1 << 16),
-               eAdmissionRequest_willSupplyUUIEs = (1 << 15),
-               eAdmissionRequest_callLinkage = (1 << 14),
-               eAdmissionRequest_gatewayDataRate = (1 << 13),
-               eAdmissionRequest_capacity = (1 << 12),
-               eAdmissionRequest_circuitInfo = (1 << 11),
-               eAdmissionRequest_desiredProtocols = (1 << 10),
-               eAdmissionRequest_desiredTunnelledProtocol = (1 << 9),
-               eAdmissionRequest_featureSet = (1 << 8),
-               eAdmissionRequest_genericData = (1 << 7),
-       } options;
-       TransportAddress destCallSignalAddress;
-       TransportAddress srcCallSignalAddress;
-} AdmissionRequest;
-
-typedef struct AdmissionConfirm {      /* SEQUENCE */
-       enum {
-               eAdmissionConfirm_irrFrequency = (1 << 31),
-               eAdmissionConfirm_nonStandardData = (1 << 30),
-               eAdmissionConfirm_destinationInfo = (1 << 29),
-               eAdmissionConfirm_destExtraCallInfo = (1 << 28),
-               eAdmissionConfirm_destinationType = (1 << 27),
-               eAdmissionConfirm_remoteExtensionAddress = (1 << 26),
-               eAdmissionConfirm_alternateEndpoints = (1 << 25),
-               eAdmissionConfirm_tokens = (1 << 24),
-               eAdmissionConfirm_cryptoTokens = (1 << 23),
-               eAdmissionConfirm_integrityCheckValue = (1 << 22),
-               eAdmissionConfirm_transportQOS = (1 << 21),
-               eAdmissionConfirm_willRespondToIRR = (1 << 20),
-               eAdmissionConfirm_uuiesRequested = (1 << 19),
-               eAdmissionConfirm_language = (1 << 18),
-               eAdmissionConfirm_alternateTransportAddresses = (1 << 17),
-               eAdmissionConfirm_useSpecifiedTransport = (1 << 16),
-               eAdmissionConfirm_circuitInfo = (1 << 15),
-               eAdmissionConfirm_usageSpec = (1 << 14),
-               eAdmissionConfirm_supportedProtocols = (1 << 13),
-               eAdmissionConfirm_serviceControl = (1 << 12),
-               eAdmissionConfirm_multipleCalls = (1 << 11),
-               eAdmissionConfirm_featureSet = (1 << 10),
-               eAdmissionConfirm_genericData = (1 << 9),
-       } options;
-       TransportAddress destCallSignalAddress;
-} AdmissionConfirm;
-
-typedef struct LocationRequest {       /* SEQUENCE */
-       enum {
-               eLocationRequest_endpointIdentifier = (1 << 31),
-               eLocationRequest_nonStandardData = (1 << 30),
-               eLocationRequest_sourceInfo = (1 << 29),
-               eLocationRequest_canMapAlias = (1 << 28),
-               eLocationRequest_gatekeeperIdentifier = (1 << 27),
-               eLocationRequest_tokens = (1 << 26),
-               eLocationRequest_cryptoTokens = (1 << 25),
-               eLocationRequest_integrityCheckValue = (1 << 24),
-               eLocationRequest_desiredProtocols = (1 << 23),
-               eLocationRequest_desiredTunnelledProtocol = (1 << 22),
-               eLocationRequest_featureSet = (1 << 21),
-               eLocationRequest_genericData = (1 << 20),
-               eLocationRequest_hopCount = (1 << 19),
-               eLocationRequest_circuitInfo = (1 << 18),
-       } options;
-       TransportAddress replyAddress;
-} LocationRequest;
-
-typedef struct LocationConfirm {       /* SEQUENCE */
-       enum {
-               eLocationConfirm_nonStandardData = (1 << 31),
-               eLocationConfirm_destinationInfo = (1 << 30),
-               eLocationConfirm_destExtraCallInfo = (1 << 29),
-               eLocationConfirm_destinationType = (1 << 28),
-               eLocationConfirm_remoteExtensionAddress = (1 << 27),
-               eLocationConfirm_alternateEndpoints = (1 << 26),
-               eLocationConfirm_tokens = (1 << 25),
-               eLocationConfirm_cryptoTokens = (1 << 24),
-               eLocationConfirm_integrityCheckValue = (1 << 23),
-               eLocationConfirm_alternateTransportAddresses = (1 << 22),
-               eLocationConfirm_supportedProtocols = (1 << 21),
-               eLocationConfirm_multipleCalls = (1 << 20),
-               eLocationConfirm_featureSet = (1 << 19),
-               eLocationConfirm_genericData = (1 << 18),
-               eLocationConfirm_circuitInfo = (1 << 17),
-               eLocationConfirm_serviceControl = (1 << 16),
-       } options;
-       TransportAddress callSignalAddress;
-       TransportAddress rasAddress;
-} LocationConfirm;
-
-typedef struct InfoRequestResponse_callSignalAddress { /* SEQUENCE OF */
-       int count;
-       TransportAddress item[10];
-} InfoRequestResponse_callSignalAddress;
-
-typedef struct InfoRequestResponse {   /* SEQUENCE */
-       enum {
-               eInfoRequestResponse_nonStandardData = (1 << 31),
-               eInfoRequestResponse_endpointAlias = (1 << 30),
-               eInfoRequestResponse_perCallInfo = (1 << 29),
-               eInfoRequestResponse_tokens = (1 << 28),
-               eInfoRequestResponse_cryptoTokens = (1 << 27),
-               eInfoRequestResponse_integrityCheckValue = (1 << 26),
-               eInfoRequestResponse_needResponse = (1 << 25),
-               eInfoRequestResponse_capacity = (1 << 24),
-               eInfoRequestResponse_irrStatus = (1 << 23),
-               eInfoRequestResponse_unsolicited = (1 << 22),
-               eInfoRequestResponse_genericData = (1 << 21),
-       } options;
-       TransportAddress rasAddress;
-       InfoRequestResponse_callSignalAddress callSignalAddress;
-} InfoRequestResponse;
-
-typedef struct RasMessage {    /* CHOICE */
-       enum {
-               eRasMessage_gatekeeperRequest,
-               eRasMessage_gatekeeperConfirm,
-               eRasMessage_gatekeeperReject,
-               eRasMessage_registrationRequest,
-               eRasMessage_registrationConfirm,
-               eRasMessage_registrationReject,
-               eRasMessage_unregistrationRequest,
-               eRasMessage_unregistrationConfirm,
-               eRasMessage_unregistrationReject,
-               eRasMessage_admissionRequest,
-               eRasMessage_admissionConfirm,
-               eRasMessage_admissionReject,
-               eRasMessage_bandwidthRequest,
-               eRasMessage_bandwidthConfirm,
-               eRasMessage_bandwidthReject,
-               eRasMessage_disengageRequest,
-               eRasMessage_disengageConfirm,
-               eRasMessage_disengageReject,
-               eRasMessage_locationRequest,
-               eRasMessage_locationConfirm,
-               eRasMessage_locationReject,
-               eRasMessage_infoRequest,
-               eRasMessage_infoRequestResponse,
-               eRasMessage_nonStandardMessage,
-               eRasMessage_unknownMessageResponse,
-               eRasMessage_requestInProgress,
-               eRasMessage_resourcesAvailableIndicate,
-               eRasMessage_resourcesAvailableConfirm,
-               eRasMessage_infoRequestAck,
-               eRasMessage_infoRequestNak,
-               eRasMessage_serviceControlIndication,
-               eRasMessage_serviceControlResponse,
-       } choice;
-       union {
-               GatekeeperRequest gatekeeperRequest;
-               GatekeeperConfirm gatekeeperConfirm;
-               RegistrationRequest registrationRequest;
-               RegistrationConfirm registrationConfirm;
-               UnregistrationRequest unregistrationRequest;
-               AdmissionRequest admissionRequest;
-               AdmissionConfirm admissionConfirm;
-               LocationRequest locationRequest;
-               LocationConfirm locationConfirm;
-               InfoRequestResponse infoRequestResponse;
-       };
-} RasMessage;
index 3021af0910f1198c0760cdaccc3d9b0751f55e87..d8b14a9010a650c1805359afd40fc2d2e9732f55 100644 (file)
@@ -224,25 +224,14 @@ icmp_error(struct sk_buff *skb, enum ip_conntrack_info *ctinfo,
        }
 
        /* See ip_conntrack_proto_tcp.c */
-       if (hooknum != NF_IP_PRE_ROUTING)
-               goto checksum_skipped;
-
-       switch (skb->ip_summed) {
-       case CHECKSUM_HW:
-               if (!(u16)csum_fold(skb->csum)) 
-                       break;
-               /* fall through */
-       case CHECKSUM_NONE:
-               skb->csum = 0;
-               if (__skb_checksum_complete(skb)) {
-                       if (LOG_INVALID(IPPROTO_ICMP))
-                               nf_log_packet(PF_INET, 0, skb, NULL, NULL, NULL,
-                                             "ip_ct_icmp: bad ICMP checksum ");
-                       return -NF_ACCEPT;
-               }
+       if (hooknum == NF_IP_PRE_ROUTING &&
+           nf_ip_checksum(skb, hooknum, skb->nh.iph->ihl * 4, 0)) {
+               if (LOG_INVALID(IPPROTO_ICMP))
+                       nf_log_packet(PF_INET, 0, skb, NULL, NULL, NULL,
+                                     "ip_ct_icmp: bad ICMP checksum ");
+               return -NF_ACCEPT;
        }
 
-checksum_skipped:
        /*
         *      18 is the highest 'known' ICMP type. Anything else is a mystery
         *
index e0dc370635459a499ebfd725a5a87842830addac..062b252b58ad2f7e581cb61a350cbd39b23ecf06 100644 (file)
@@ -870,11 +870,8 @@ static int tcp_error(struct sk_buff *skb,
         * and moreover root might send raw packets.
         */
        /* FIXME: Source route IP option packets --RR */
-       if (hooknum == NF_IP_PRE_ROUTING
-           && skb->ip_summed != CHECKSUM_UNNECESSARY
-           && csum_tcpudp_magic(iph->saddr, iph->daddr, tcplen, IPPROTO_TCP,
-                                skb->ip_summed == CHECKSUM_HW ? skb->csum
-                                : skb_checksum(skb, iph->ihl*4, tcplen, 0))) {
+       if (hooknum == NF_IP_PRE_ROUTING &&
+           nf_ip_checksum(skb, hooknum, iph->ihl * 4, IPPROTO_TCP)) {
                if (LOG_INVALID(IPPROTO_TCP))
                        nf_log_packet(PF_INET, 0, skb, NULL, NULL, NULL,
                                  "ip_ct_tcp: bad TCP checksum ");
index 55b7d3210adf9e0e48ff3b7a10c4c78e6a91f985..70899868783bc1d7366037f3ff240dce8befb9b6 100644 (file)
@@ -120,11 +120,8 @@ static int udp_error(struct sk_buff *skb, enum ip_conntrack_info *ctinfo,
         * because the semantic of CHECKSUM_HW is different there 
         * and moreover root might send raw packets.
         * FIXME: Source route IP option packets --RR */
-       if (hooknum == NF_IP_PRE_ROUTING
-           && skb->ip_summed != CHECKSUM_UNNECESSARY
-           && csum_tcpudp_magic(iph->saddr, iph->daddr, udplen, IPPROTO_UDP,
-                                skb->ip_summed == CHECKSUM_HW ? skb->csum
-                                : skb_checksum(skb, iph->ihl*4, udplen, 0))) {
+       if (hooknum == NF_IP_PRE_ROUTING &&
+           nf_ip_checksum(skb, hooknum, iph->ihl * 4, IPPROTO_UDP)) {
                if (LOG_INVALID(IPPROTO_UDP))
                        nf_log_packet(PF_INET, 0, skb, NULL, NULL, NULL,
                                  "ip_ct_udp: bad UDP checksum ");
index 52076026db36804eb5c2331c770f97f50414d889..929d61f7be91589b6ce2022ffd01dfc68767dc31 100644 (file)
@@ -469,70 +469,63 @@ static unsigned int ip_conntrack_local(unsigned int hooknum,
 
 /* Connection tracking may drop packets, but never alters them, so
    make it the first hook. */
-static struct nf_hook_ops ip_conntrack_defrag_ops = {
-       .hook           = ip_conntrack_defrag,
-       .owner          = THIS_MODULE,
-       .pf             = PF_INET,
-       .hooknum        = NF_IP_PRE_ROUTING,
-       .priority       = NF_IP_PRI_CONNTRACK_DEFRAG,
-};
-
-static struct nf_hook_ops ip_conntrack_in_ops = {
-       .hook           = ip_conntrack_in,
-       .owner          = THIS_MODULE,
-       .pf             = PF_INET,
-       .hooknum        = NF_IP_PRE_ROUTING,
-       .priority       = NF_IP_PRI_CONNTRACK,
-};
-
-static struct nf_hook_ops ip_conntrack_defrag_local_out_ops = {
-       .hook           = ip_conntrack_defrag,
-       .owner          = THIS_MODULE,
-       .pf             = PF_INET,
-       .hooknum        = NF_IP_LOCAL_OUT,
-       .priority       = NF_IP_PRI_CONNTRACK_DEFRAG,
-};
-
-static struct nf_hook_ops ip_conntrack_local_out_ops = {
-       .hook           = ip_conntrack_local,
-       .owner          = THIS_MODULE,
-       .pf             = PF_INET,
-       .hooknum        = NF_IP_LOCAL_OUT,
-       .priority       = NF_IP_PRI_CONNTRACK,
-};
-
-/* helpers */
-static struct nf_hook_ops ip_conntrack_helper_out_ops = {
-       .hook           = ip_conntrack_help,
-       .owner          = THIS_MODULE,
-       .pf             = PF_INET,
-       .hooknum        = NF_IP_POST_ROUTING,
-       .priority       = NF_IP_PRI_CONNTRACK_HELPER,
-};
-
-static struct nf_hook_ops ip_conntrack_helper_in_ops = {
-       .hook           = ip_conntrack_help,
-       .owner          = THIS_MODULE,
-       .pf             = PF_INET,
-       .hooknum        = NF_IP_LOCAL_IN,
-       .priority       = NF_IP_PRI_CONNTRACK_HELPER,
-};
-
-/* Refragmenter; last chance. */
-static struct nf_hook_ops ip_conntrack_out_ops = {
-       .hook           = ip_confirm,
-       .owner          = THIS_MODULE,
-       .pf             = PF_INET,
-       .hooknum        = NF_IP_POST_ROUTING,
-       .priority       = NF_IP_PRI_CONNTRACK_CONFIRM,
-};
-
-static struct nf_hook_ops ip_conntrack_local_in_ops = {
-       .hook           = ip_confirm,
-       .owner          = THIS_MODULE,
-       .pf             = PF_INET,
-       .hooknum        = NF_IP_LOCAL_IN,
-       .priority       = NF_IP_PRI_CONNTRACK_CONFIRM,
+static struct nf_hook_ops ip_conntrack_ops[] = {
+       {
+               .hook           = ip_conntrack_defrag,
+               .owner          = THIS_MODULE,
+               .pf             = PF_INET,
+               .hooknum        = NF_IP_PRE_ROUTING,
+               .priority       = NF_IP_PRI_CONNTRACK_DEFRAG,
+       },
+       {
+               .hook           = ip_conntrack_in,
+               .owner          = THIS_MODULE,
+               .pf             = PF_INET,
+               .hooknum        = NF_IP_PRE_ROUTING,
+               .priority       = NF_IP_PRI_CONNTRACK,
+       },
+       {
+               .hook           = ip_conntrack_defrag,
+               .owner          = THIS_MODULE,
+               .pf             = PF_INET,
+               .hooknum        = NF_IP_LOCAL_OUT,
+               .priority       = NF_IP_PRI_CONNTRACK_DEFRAG,
+       },
+       {
+               .hook           = ip_conntrack_local,
+               .owner          = THIS_MODULE,
+               .pf             = PF_INET,
+               .hooknum        = NF_IP_LOCAL_OUT,
+               .priority       = NF_IP_PRI_CONNTRACK,
+       },
+       {
+               .hook           = ip_conntrack_help,
+               .owner          = THIS_MODULE,
+               .pf             = PF_INET,
+               .hooknum        = NF_IP_POST_ROUTING,
+               .priority       = NF_IP_PRI_CONNTRACK_HELPER,
+       },
+       {
+               .hook           = ip_conntrack_help,
+               .owner          = THIS_MODULE,
+               .pf             = PF_INET,
+               .hooknum        = NF_IP_LOCAL_IN,
+               .priority       = NF_IP_PRI_CONNTRACK_HELPER,
+       },
+       {
+               .hook           = ip_confirm,
+               .owner          = THIS_MODULE,
+               .pf             = PF_INET,
+               .hooknum        = NF_IP_POST_ROUTING,
+               .priority       = NF_IP_PRI_CONNTRACK_CONFIRM,
+       },
+       {
+               .hook           = ip_confirm,
+               .owner          = THIS_MODULE,
+               .pf             = PF_INET,
+               .hooknum        = NF_IP_LOCAL_IN,
+               .priority       = NF_IP_PRI_CONNTRACK_CONFIRM,
+       },
 };
 
 /* Sysctl support */
@@ -783,18 +776,46 @@ static ctl_table ip_ct_net_table[] = {
 EXPORT_SYMBOL(ip_ct_log_invalid);
 #endif /* CONFIG_SYSCTL */
 
-static int init_or_cleanup(int init)
+/* FIXME: Allow NULL functions and sub in pointers to generic for
+   them. --RR */
+int ip_conntrack_protocol_register(struct ip_conntrack_protocol *proto)
+{
+       int ret = 0;
+
+       write_lock_bh(&ip_conntrack_lock);
+       if (ip_ct_protos[proto->proto] != &ip_conntrack_generic_protocol) {
+               ret = -EBUSY;
+               goto out;
+       }
+       ip_ct_protos[proto->proto] = proto;
+ out:
+       write_unlock_bh(&ip_conntrack_lock);
+       return ret;
+}
+
+void ip_conntrack_protocol_unregister(struct ip_conntrack_protocol *proto)
+{
+       write_lock_bh(&ip_conntrack_lock);
+       ip_ct_protos[proto->proto] = &ip_conntrack_generic_protocol;
+       write_unlock_bh(&ip_conntrack_lock);
+
+       /* Somebody could be still looking at the proto in bh. */
+       synchronize_net();
+
+       /* Remove all contrack entries for this protocol */
+       ip_ct_iterate_cleanup(kill_proto, &proto->proto);
+}
+
+static int __init ip_conntrack_standalone_init(void)
 {
 #ifdef CONFIG_PROC_FS
        struct proc_dir_entry *proc, *proc_exp, *proc_stat;
 #endif
        int ret = 0;
 
-       if (!init) goto cleanup;
-
        ret = ip_conntrack_init();
        if (ret < 0)
-               goto cleanup_nothing;
+               return ret;
 
 #ifdef CONFIG_PROC_FS
        ret = -ENOMEM;
@@ -813,78 +834,25 @@ static int init_or_cleanup(int init)
        proc_stat->owner = THIS_MODULE;
 #endif
 
-       ret = nf_register_hook(&ip_conntrack_defrag_ops);
+       ret = nf_register_hooks(ip_conntrack_ops, ARRAY_SIZE(ip_conntrack_ops));
        if (ret < 0) {
-               printk("ip_conntrack: can't register pre-routing defrag hook.\n");
+               printk("ip_conntrack: can't register hooks.\n");
                goto cleanup_proc_stat;
        }
-       ret = nf_register_hook(&ip_conntrack_defrag_local_out_ops);
-       if (ret < 0) {
-               printk("ip_conntrack: can't register local_out defrag hook.\n");
-               goto cleanup_defragops;
-       }
-       ret = nf_register_hook(&ip_conntrack_in_ops);
-       if (ret < 0) {
-               printk("ip_conntrack: can't register pre-routing hook.\n");
-               goto cleanup_defraglocalops;
-       }
-       ret = nf_register_hook(&ip_conntrack_local_out_ops);
-       if (ret < 0) {
-               printk("ip_conntrack: can't register local out hook.\n");
-               goto cleanup_inops;
-       }
-       ret = nf_register_hook(&ip_conntrack_helper_in_ops);
-       if (ret < 0) {
-               printk("ip_conntrack: can't register local in helper hook.\n");
-               goto cleanup_inandlocalops;
-       }
-       ret = nf_register_hook(&ip_conntrack_helper_out_ops);
-       if (ret < 0) {
-               printk("ip_conntrack: can't register postrouting helper hook.\n");
-               goto cleanup_helperinops;
-       }
-       ret = nf_register_hook(&ip_conntrack_out_ops);
-       if (ret < 0) {
-               printk("ip_conntrack: can't register post-routing hook.\n");
-               goto cleanup_helperoutops;
-       }
-       ret = nf_register_hook(&ip_conntrack_local_in_ops);
-       if (ret < 0) {
-               printk("ip_conntrack: can't register local in hook.\n");
-               goto cleanup_inoutandlocalops;
-       }
 #ifdef CONFIG_SYSCTL
        ip_ct_sysctl_header = register_sysctl_table(ip_ct_net_table, 0);
        if (ip_ct_sysctl_header == NULL) {
                printk("ip_conntrack: can't register to sysctl.\n");
                ret = -ENOMEM;
-               goto cleanup_localinops;
+               goto cleanup_hooks;
        }
 #endif
-
        return ret;
 
- cleanup:
-       synchronize_net();
 #ifdef CONFIG_SYSCTL
-       unregister_sysctl_table(ip_ct_sysctl_header);
- cleanup_localinops:
+ cleanup_hooks:
+       nf_unregister_hooks(ip_conntrack_ops, ARRAY_SIZE(ip_conntrack_ops));
 #endif
-       nf_unregister_hook(&ip_conntrack_local_in_ops);
- cleanup_inoutandlocalops:
-       nf_unregister_hook(&ip_conntrack_out_ops);
- cleanup_helperoutops:
-       nf_unregister_hook(&ip_conntrack_helper_out_ops);
- cleanup_helperinops:
-       nf_unregister_hook(&ip_conntrack_helper_in_ops);
- cleanup_inandlocalops:
-       nf_unregister_hook(&ip_conntrack_local_out_ops);
- cleanup_inops:
-       nf_unregister_hook(&ip_conntrack_in_ops);
- cleanup_defraglocalops:
-       nf_unregister_hook(&ip_conntrack_defrag_local_out_ops);
- cleanup_defragops:
-       nf_unregister_hook(&ip_conntrack_defrag_ops);
  cleanup_proc_stat:
 #ifdef CONFIG_PROC_FS
        remove_proc_entry("ip_conntrack", proc_net_stat);
@@ -895,48 +863,22 @@ static int init_or_cleanup(int init)
  cleanup_init:
 #endif /* CONFIG_PROC_FS */
        ip_conntrack_cleanup();
- cleanup_nothing:
-       return ret;
-}
-
-/* FIXME: Allow NULL functions and sub in pointers to generic for
-   them. --RR */
-int ip_conntrack_protocol_register(struct ip_conntrack_protocol *proto)
-{
-       int ret = 0;
-
-       write_lock_bh(&ip_conntrack_lock);
-       if (ip_ct_protos[proto->proto] != &ip_conntrack_generic_protocol) {
-               ret = -EBUSY;
-               goto out;
-       }
-       ip_ct_protos[proto->proto] = proto;
- out:
-       write_unlock_bh(&ip_conntrack_lock);
        return ret;
 }
 
-void ip_conntrack_protocol_unregister(struct ip_conntrack_protocol *proto)
-{
-       write_lock_bh(&ip_conntrack_lock);
-       ip_ct_protos[proto->proto] = &ip_conntrack_generic_protocol;
-       write_unlock_bh(&ip_conntrack_lock);
-       
-       /* Somebody could be still looking at the proto in bh. */
-       synchronize_net();
-
-       /* Remove all contrack entries for this protocol */
-       ip_ct_iterate_cleanup(kill_proto, &proto->proto);
-}
-
-static int __init ip_conntrack_standalone_init(void)
-{
-       return init_or_cleanup(1);
-}
-
 static void __exit ip_conntrack_standalone_fini(void)
 {
-       init_or_cleanup(0);
+       synchronize_net();
+#ifdef CONFIG_SYSCTL
+       unregister_sysctl_table(ip_ct_sysctl_header);
+#endif
+       nf_unregister_hooks(ip_conntrack_ops, ARRAY_SIZE(ip_conntrack_ops));
+#ifdef CONFIG_PROC_FS
+       remove_proc_entry("ip_conntrack", proc_net_stat);
+       proc_net_remove("ip_conntrack_expect");
+       proc_net_remove("ip_conntrack");
+#endif /* CONFIG_PROC_FS */
+       ip_conntrack_cleanup();
 }
 
 module_init(ip_conntrack_standalone_init);
index a0bc883928c09d4b7a5531af474820ce12ead663..d45663d137a72b576e306dfe4cb1c671a057c307 100644 (file)
@@ -7,24 +7,6 @@
  *
  * Based on the 'brute force' H.323 NAT module by
  * Jozsef Kadlecsik <kadlec@blackhole.kfki.hu>
- *
- * Changes:
- *     2006-02-01 - initial version 0.1
- *
- *     2006-02-20 - version 0.2
- *       1. Changed source format to follow kernel conventions
- *       2. Deleted some unnecessary structures
- *       3. Minor fixes
- *
- *     2006-03-10 - version 0.3
- *       1. Added support for multiple TPKTs in one packet (suggested by
- *          Patrick McHardy)
- *       2. Added support for non-linear skb (based on Patrick McHardy's patch)
- *       3. Eliminated unnecessary return code
- *
- *     2006-03-15 - version 0.4
- *       1. Added support for T.120 channels
- *       2. Added parameter gkrouted_only (suggested by Patrick McHardy)
  */
 
 #include <linux/module.h>
 #include <linux/netfilter_ipv4/ip_conntrack_h323.h>
 #include <linux/netfilter_ipv4/ip_conntrack_helper.h>
 
-#include "ip_conntrack_helper_h323_asn1.h"
-
 #if 0
 #define DEBUGP printk
 #else
 #define DEBUGP(format, args...)
 #endif
 
-extern int get_h245_addr(unsigned char *data, H245_TransportAddress * addr,
-                        u_int32_t * ip, u_int16_t * port);
-extern int get_h225_addr(unsigned char *data, TransportAddress * addr,
-                        u_int32_t * ip, u_int16_t * port);
-extern void ip_conntrack_h245_expect(struct ip_conntrack *new,
-                                    struct ip_conntrack_expect *this);
-extern void ip_conntrack_q931_expect(struct ip_conntrack *new,
-                                    struct ip_conntrack_expect *this);
-extern int (*set_h245_addr_hook) (struct sk_buff ** pskb,
-                                 unsigned char **data, int dataoff,
-                                 H245_TransportAddress * addr,
-                                 u_int32_t ip, u_int16_t port);
-extern int (*set_h225_addr_hook) (struct sk_buff ** pskb,
-                                 unsigned char **data, int dataoff,
-                                 TransportAddress * addr,
-                                 u_int32_t ip, u_int16_t port);
-extern int (*set_sig_addr_hook) (struct sk_buff ** pskb,
-                                struct ip_conntrack * ct,
-                                enum ip_conntrack_info ctinfo,
-                                unsigned char **data,
-                                TransportAddress * addr, int count);
-extern int (*set_ras_addr_hook) (struct sk_buff ** pskb,
-                                struct ip_conntrack * ct,
-                                enum ip_conntrack_info ctinfo,
-                                unsigned char **data,
-                                TransportAddress * addr, int count);
-extern int (*nat_rtp_rtcp_hook) (struct sk_buff ** pskb,
-                                struct ip_conntrack * ct,
-                                enum ip_conntrack_info ctinfo,
-                                unsigned char **data, int dataoff,
-                                H245_TransportAddress * addr,
-                                u_int16_t port, u_int16_t rtp_port,
-                                struct ip_conntrack_expect * rtp_exp,
-                                struct ip_conntrack_expect * rtcp_exp);
-extern int (*nat_t120_hook) (struct sk_buff ** pskb, struct ip_conntrack * ct,
-                            enum ip_conntrack_info ctinfo,
-                            unsigned char **data, int dataoff,
-                            H245_TransportAddress * addr, u_int16_t port,
-                            struct ip_conntrack_expect * exp);
-extern int (*nat_h245_hook) (struct sk_buff ** pskb, struct ip_conntrack * ct,
-                            enum ip_conntrack_info ctinfo,
-                            unsigned char **data, int dataoff,
-                            TransportAddress * addr, u_int16_t port,
-                            struct ip_conntrack_expect * exp);
-extern int (*nat_q931_hook) (struct sk_buff ** pskb, struct ip_conntrack * ct,
-                            enum ip_conntrack_info ctinfo,
-                            unsigned char **data, TransportAddress * addr,
-                            int idx, u_int16_t port,
-                            struct ip_conntrack_expect * exp);
-
-
 /****************************************************************************/
 static int set_addr(struct sk_buff **pskb,
                    unsigned char **data, int dataoff,
index efba8c4e42e03e63cf166e9ad80acdf613a00aa6..1aba926c1cb05444d57dd9cc695fb9d999f5e824 100644 (file)
@@ -279,7 +279,7 @@ static struct ipt_target ipt_dnat_reg = {
        .target         = ipt_dnat_target,
        .targetsize     = sizeof(struct ip_nat_multi_range_compat),
        .table          = "nat",
-       .hooks          = 1 << NF_IP_PRE_ROUTING,
+       .hooks          = (1 << NF_IP_PRE_ROUTING) | (1 << NF_IP_LOCAL_OUT),
        .checkentry     = ipt_dnat_checkentry,
 };
 
index 3505b0de2e046c09c39a9466df5b939089f0a50a..8f760b28617e8c5b62f456c77e92f5032a264599 100644 (file)
@@ -299,69 +299,63 @@ ip_nat_adjust(unsigned int hooknum,
 
 /* We must be after connection tracking and before packet filtering. */
 
-/* Before packet filtering, change destination */
-static struct nf_hook_ops ip_nat_in_ops = {
-       .hook           = ip_nat_in,
-       .owner          = THIS_MODULE,
-       .pf             = PF_INET,
-       .hooknum        = NF_IP_PRE_ROUTING,
-       .priority       = NF_IP_PRI_NAT_DST,
+static struct nf_hook_ops ip_nat_ops[] = {
+       /* Before packet filtering, change destination */
+       {
+               .hook           = ip_nat_in,
+               .owner          = THIS_MODULE,
+               .pf             = PF_INET,
+               .hooknum        = NF_IP_PRE_ROUTING,
+               .priority       = NF_IP_PRI_NAT_DST,
+       },
+       /* After packet filtering, change source */
+       {
+               .hook           = ip_nat_out,
+               .owner          = THIS_MODULE,
+               .pf             = PF_INET,
+               .hooknum        = NF_IP_POST_ROUTING,
+               .priority       = NF_IP_PRI_NAT_SRC,
+       },
+       /* After conntrack, adjust sequence number */
+       {
+               .hook           = ip_nat_adjust,
+               .owner          = THIS_MODULE,
+               .pf             = PF_INET,
+               .hooknum        = NF_IP_POST_ROUTING,
+               .priority       = NF_IP_PRI_NAT_SEQ_ADJUST,
+       },
+       /* Before packet filtering, change destination */
+       {
+               .hook           = ip_nat_local_fn,
+               .owner          = THIS_MODULE,
+               .pf             = PF_INET,
+               .hooknum        = NF_IP_LOCAL_OUT,
+               .priority       = NF_IP_PRI_NAT_DST,
+       },
+       /* After packet filtering, change source */
+       {
+               .hook           = ip_nat_fn,
+               .owner          = THIS_MODULE,
+               .pf             = PF_INET,
+               .hooknum        = NF_IP_LOCAL_IN,
+               .priority       = NF_IP_PRI_NAT_SRC,
+       },
+       /* After conntrack, adjust sequence number */
+       {
+               .hook           = ip_nat_adjust,
+               .owner          = THIS_MODULE,
+               .pf             = PF_INET,
+               .hooknum        = NF_IP_LOCAL_IN,
+               .priority       = NF_IP_PRI_NAT_SEQ_ADJUST,
+       },
 };
 
-/* After packet filtering, change source */
-static struct nf_hook_ops ip_nat_out_ops = {
-       .hook           = ip_nat_out,
-       .owner          = THIS_MODULE,
-       .pf             = PF_INET,
-       .hooknum        = NF_IP_POST_ROUTING,
-       .priority       = NF_IP_PRI_NAT_SRC,
-};
-
-/* After conntrack, adjust sequence number */
-static struct nf_hook_ops ip_nat_adjust_out_ops = {
-       .hook           = ip_nat_adjust,
-       .owner          = THIS_MODULE,
-       .pf             = PF_INET,
-       .hooknum        = NF_IP_POST_ROUTING,
-       .priority       = NF_IP_PRI_NAT_SEQ_ADJUST,
-};
-
-/* Before packet filtering, change destination */
-static struct nf_hook_ops ip_nat_local_out_ops = {
-       .hook           = ip_nat_local_fn,
-       .owner          = THIS_MODULE,
-       .pf             = PF_INET,
-       .hooknum        = NF_IP_LOCAL_OUT,
-       .priority       = NF_IP_PRI_NAT_DST,
-};
-
-/* After packet filtering, change source for reply packets of LOCAL_OUT DNAT */
-static struct nf_hook_ops ip_nat_local_in_ops = {
-       .hook           = ip_nat_fn,
-       .owner          = THIS_MODULE,
-       .pf             = PF_INET,
-       .hooknum        = NF_IP_LOCAL_IN,
-       .priority       = NF_IP_PRI_NAT_SRC,
-};
-
-/* After conntrack, adjust sequence number */
-static struct nf_hook_ops ip_nat_adjust_in_ops = {
-       .hook           = ip_nat_adjust,
-       .owner          = THIS_MODULE,
-       .pf             = PF_INET,
-       .hooknum        = NF_IP_LOCAL_IN,
-       .priority       = NF_IP_PRI_NAT_SEQ_ADJUST,
-};
-
-
-static int init_or_cleanup(int init)
+static int __init ip_nat_standalone_init(void)
 {
        int ret = 0;
 
        need_conntrack();
 
-       if (!init) goto cleanup;
-
 #ifdef CONFIG_XFRM
        BUG_ON(ip_nat_decode_session != NULL);
        ip_nat_decode_session = nat_decode_session;
@@ -371,50 +365,13 @@ static int init_or_cleanup(int init)
                printk("ip_nat_init: can't setup rules.\n");
                goto cleanup_decode_session;
        }
-       ret = nf_register_hook(&ip_nat_in_ops);
+       ret = nf_register_hooks(ip_nat_ops, ARRAY_SIZE(ip_nat_ops));
        if (ret < 0) {
-               printk("ip_nat_init: can't register in hook.\n");
+               printk("ip_nat_init: can't register hooks.\n");
                goto cleanup_rule_init;
        }
-       ret = nf_register_hook(&ip_nat_out_ops);
-       if (ret < 0) {
-               printk("ip_nat_init: can't register out hook.\n");
-               goto cleanup_inops;
-       }
-       ret = nf_register_hook(&ip_nat_adjust_in_ops);
-       if (ret < 0) {
-               printk("ip_nat_init: can't register adjust in hook.\n");
-               goto cleanup_outops;
-       }
-       ret = nf_register_hook(&ip_nat_adjust_out_ops);
-       if (ret < 0) {
-               printk("ip_nat_init: can't register adjust out hook.\n");
-               goto cleanup_adjustin_ops;
-       }
-       ret = nf_register_hook(&ip_nat_local_out_ops);
-       if (ret < 0) {
-               printk("ip_nat_init: can't register local out hook.\n");
-               goto cleanup_adjustout_ops;
-       }
-       ret = nf_register_hook(&ip_nat_local_in_ops);
-       if (ret < 0) {
-               printk("ip_nat_init: can't register local in hook.\n");
-               goto cleanup_localoutops;
-       }
        return ret;
 
- cleanup:
-       nf_unregister_hook(&ip_nat_local_in_ops);
- cleanup_localoutops:
-       nf_unregister_hook(&ip_nat_local_out_ops);
- cleanup_adjustout_ops:
-       nf_unregister_hook(&ip_nat_adjust_out_ops);
- cleanup_adjustin_ops:
-       nf_unregister_hook(&ip_nat_adjust_in_ops);
- cleanup_outops:
-       nf_unregister_hook(&ip_nat_out_ops);
- cleanup_inops:
-       nf_unregister_hook(&ip_nat_in_ops);
  cleanup_rule_init:
        ip_nat_rule_cleanup();
  cleanup_decode_session:
@@ -425,14 +382,14 @@ static int init_or_cleanup(int init)
        return ret;
 }
 
-static int __init ip_nat_standalone_init(void)
-{
-       return init_or_cleanup(1);
-}
-
 static void __exit ip_nat_standalone_fini(void)
 {
-       init_or_cleanup(0);
+       nf_unregister_hooks(ip_nat_ops, ARRAY_SIZE(ip_nat_ops));
+       ip_nat_rule_cleanup();
+#ifdef CONFIG_XFRM
+       ip_nat_decode_session = NULL;
+       synchronize_net();
+#endif
 }
 
 module_init(ip_nat_standalone_init);
index 896a244f8f91c06a2a35410b091db3612a7e7208..b93f0494362f888785d2dd8af8524d86f67ccdc0 100644 (file)
@@ -662,15 +662,11 @@ static struct nf_queue_handler nfqh = {
        .outfn  = &ipq_enqueue_packet,
 };
 
-static int
-init_or_cleanup(int init)
+static int __init ip_queue_init(void)
 {
        int status = -ENOMEM;
        struct proc_dir_entry *proc;
        
-       if (!init)
-               goto cleanup;
-
        netlink_register_notifier(&ipq_nl_notifier);
        ipqnl = netlink_kernel_create(NETLINK_FIREWALL, 0, ipq_rcv_sk,
                                      THIS_MODULE);
@@ -697,11 +693,6 @@ init_or_cleanup(int init)
        }
        return status;
 
-cleanup:
-       nf_unregister_queue_handlers(&nfqh);
-       synchronize_net();
-       ipq_flush(NF_DROP);
-       
 cleanup_sysctl:
        unregister_sysctl_table(ipq_sysctl_header);
        unregister_netdevice_notifier(&ipq_dev_notifier);
@@ -717,15 +708,21 @@ cleanup_netlink_notifier:
        return status;
 }
 
-static int __init ip_queue_init(void)
-{
-       
-       return init_or_cleanup(1);
-}
-
 static void __exit ip_queue_fini(void)
 {
-       init_or_cleanup(0);
+       nf_unregister_queue_handlers(&nfqh);
+       synchronize_net();
+       ipq_flush(NF_DROP);
+
+       unregister_sysctl_table(ipq_sysctl_header);
+       unregister_netdevice_notifier(&ipq_dev_notifier);
+       proc_net_remove(IPQ_PROC_FS_NAME);
+
+       sock_release(ipqnl->sk_socket);
+       mutex_lock(&ipqnl_mutex);
+       mutex_unlock(&ipqnl_mutex);
+
+       netlink_unregister_notifier(&ipq_nl_notifier);
 }
 
 MODULE_DESCRIPTION("IPv4 packet queue handler");
index d5b8cdd361ce875bfe7c078f1f173db58153c85e..d25ac8ba6ebaedb0e0e1cbe658b80c94e0814b39 100644 (file)
@@ -735,7 +735,7 @@ translate_table(const char *name,
        }
 
        /* And one copy for every other CPU */
-       for_each_cpu(i) {
+       for_each_possible_cpu(i) {
                if (newinfo->entries[i] && newinfo->entries[i] != entry0)
                        memcpy(newinfo->entries[i], entry0, newinfo->size);
        }
@@ -788,7 +788,7 @@ get_counters(const struct xt_table_info *t,
                          counters,
                          &i);
 
-       for_each_cpu(cpu) {
+       for_each_possible_cpu(cpu) {
                if (cpu == curcpu)
                        continue;
                i = 0;
index e4768a31718b83e530121f3049e9ef320797dc90..aad9d28c8d7123dd2a5f8a043fa3658d9970185e 100644 (file)
@@ -725,22 +725,17 @@ static struct file_operations clusterip_proc_fops = {
 
 #endif /* CONFIG_PROC_FS */
 
-static int init_or_cleanup(int fini)
+static int __init ipt_clusterip_init(void)
 {
        int ret;
 
-       if (fini)
-               goto cleanup;
-
-       if (ipt_register_target(&clusterip_tgt)) {
-               ret = -EINVAL;
-               goto cleanup_none;
-       }
+       ret = ipt_register_target(&clusterip_tgt);
+       if (ret < 0)
+               return ret;
 
-       if (nf_register_hook(&cip_arp_ops) < 0) {
-               ret = -EINVAL;
+       ret = nf_register_hook(&cip_arp_ops);
+       if (ret < 0)
                goto cleanup_target;
-       }
 
 #ifdef CONFIG_PROC_FS
        clusterip_procdir = proc_mkdir("ipt_CLUSTERIP", proc_net);
@@ -753,31 +748,24 @@ static int init_or_cleanup(int fini)
 
        printk(KERN_NOTICE "ClusterIP Version %s loaded successfully\n",
                CLUSTERIP_VERSION);
-
        return 0;
 
-cleanup:
-       printk(KERN_NOTICE "ClusterIP Version %s unloading\n",
-               CLUSTERIP_VERSION);
-#ifdef CONFIG_PROC_FS
-       remove_proc_entry(clusterip_procdir->name, clusterip_procdir->parent);
-#endif
 cleanup_hook:
        nf_unregister_hook(&cip_arp_ops);
 cleanup_target:
        ipt_unregister_target(&clusterip_tgt);
-cleanup_none:
-       return -EINVAL;
-}
-
-static int __init ipt_clusterip_init(void)
-{
-       return init_or_cleanup(0);
+       return ret;
 }
 
 static void __exit ipt_clusterip_fini(void)
 {
-       init_or_cleanup(1);
+       printk(KERN_NOTICE "ClusterIP Version %s unloading\n",
+               CLUSTERIP_VERSION);
+#ifdef CONFIG_PROC_FS
+       remove_proc_entry(clusterip_procdir->name, clusterip_procdir->parent);
+#endif
+       nf_unregister_hook(&cip_arp_ops);
+       ipt_unregister_target(&clusterip_tgt);
 }
 
 module_init(ipt_clusterip_init);
index 4269a5440d43a5eaf3a497ab64f3240978073b05..0bba3c2bb786b831ae9c3bb68213181395ea266e 100644 (file)
@@ -106,7 +106,6 @@ static void send_reset(struct sk_buff *oldskb, int hook)
        struct rtable *rt;
        u_int16_t tmp_port;
        u_int32_t tmp_addr;
-       unsigned int tcplen;
        int needs_ack;
        int hh_len;
 
@@ -124,13 +123,7 @@ static void send_reset(struct sk_buff *oldskb, int hook)
                return;
 
        /* Check checksum */
-       tcplen = oldskb->len - iph->ihl * 4;
-       if (((hook != NF_IP_LOCAL_IN && oldskb->ip_summed != CHECKSUM_HW) ||
-            (hook == NF_IP_LOCAL_IN &&
-             oldskb->ip_summed != CHECKSUM_UNNECESSARY)) &&
-           csum_tcpudp_magic(iph->saddr, iph->daddr, tcplen, IPPROTO_TCP,
-                             oldskb->ip_summed == CHECKSUM_HW ? oldskb->csum :
-                             skb_checksum(oldskb, iph->ihl * 4, tcplen, 0)))
+       if (nf_ip_checksum(oldskb, hook, iph->ihl * 4, IPPROTO_TCP))
                return;
 
        if ((rt = route_reverse(oldskb, oth, hook)) == NULL)
index 3d80aefe9cfa72599b65ad0b215e569208928e69..7f417484bfbf3ee566359bd13d02199c1034b696 100644 (file)
@@ -157,37 +157,20 @@ static int __init iptable_filter_init(void)
                return ret;
 
        /* Register hooks */
-       ret = nf_register_hook(&ipt_ops[0]);
+       ret = nf_register_hooks(ipt_ops, ARRAY_SIZE(ipt_ops));
        if (ret < 0)
                goto cleanup_table;
 
-       ret = nf_register_hook(&ipt_ops[1]);
-       if (ret < 0)
-               goto cleanup_hook0;
-
-       ret = nf_register_hook(&ipt_ops[2]);
-       if (ret < 0)
-               goto cleanup_hook1;
-
        return ret;
 
- cleanup_hook1:
-       nf_unregister_hook(&ipt_ops[1]);
- cleanup_hook0:
-       nf_unregister_hook(&ipt_ops[0]);
  cleanup_table:
        ipt_unregister_table(&packet_filter);
-
        return ret;
 }
 
 static void __exit iptable_filter_fini(void)
 {
-       unsigned int i;
-
-       for (i = 0; i < sizeof(ipt_ops)/sizeof(struct nf_hook_ops); i++)
-               nf_unregister_hook(&ipt_ops[i]);
-
+       nf_unregister_hooks(ipt_ops, ARRAY_SIZE(ipt_ops));
        ipt_unregister_table(&packet_filter);
 }
 
index 412fc96cc8968c6f22d8d6576a65557f52e00a7a..397b95cc026ba9841f4414ca79cc9622318654e1 100644 (file)
@@ -211,49 +211,20 @@ static int __init iptable_mangle_init(void)
                return ret;
 
        /* Register hooks */
-       ret = nf_register_hook(&ipt_ops[0]);
+       ret = nf_register_hooks(ipt_ops, ARRAY_SIZE(ipt_ops));
        if (ret < 0)
                goto cleanup_table;
 
-       ret = nf_register_hook(&ipt_ops[1]);
-       if (ret < 0)
-               goto cleanup_hook0;
-
-       ret = nf_register_hook(&ipt_ops[2]);
-       if (ret < 0)
-               goto cleanup_hook1;
-
-       ret = nf_register_hook(&ipt_ops[3]);
-       if (ret < 0)
-               goto cleanup_hook2;
-
-       ret = nf_register_hook(&ipt_ops[4]);
-       if (ret < 0)
-               goto cleanup_hook3;
-
        return ret;
 
- cleanup_hook3:
-        nf_unregister_hook(&ipt_ops[3]);
- cleanup_hook2:
-        nf_unregister_hook(&ipt_ops[2]);
- cleanup_hook1:
-       nf_unregister_hook(&ipt_ops[1]);
- cleanup_hook0:
-       nf_unregister_hook(&ipt_ops[0]);
  cleanup_table:
        ipt_unregister_table(&packet_mangler);
-
        return ret;
 }
 
 static void __exit iptable_mangle_fini(void)
 {
-       unsigned int i;
-
-       for (i = 0; i < sizeof(ipt_ops)/sizeof(struct nf_hook_ops); i++)
-               nf_unregister_hook(&ipt_ops[i]);
-
+       nf_unregister_hooks(ipt_ops, ARRAY_SIZE(ipt_ops));
        ipt_unregister_table(&packet_mangler);
 }
 
index 03cc79a6160a68b89fbae369d06bf71dd95f5fde..7912cce1e1b8d2a0b1af3689354b8f590cd43fcd 100644 (file)
@@ -101,18 +101,18 @@ ipt_hook(unsigned int hook,
 /* 'raw' is the very first table. */
 static struct nf_hook_ops ipt_ops[] = {
        {
-         .hook = ipt_hook, 
-         .pf = PF_INET, 
-         .hooknum = NF_IP_PRE_ROUTING, 
-         .priority = NF_IP_PRI_RAW,
-         .owner = THIS_MODULE,
+               .hook = ipt_hook,
+               .pf = PF_INET,
+               .hooknum = NF_IP_PRE_ROUTING,
+               .priority = NF_IP_PRI_RAW,
+               .owner = THIS_MODULE,
        },
        {
-         .hook = ipt_hook, 
-         .pf = PF_INET, 
-         .hooknum = NF_IP_LOCAL_OUT, 
-         .priority = NF_IP_PRI_RAW,
-         .owner = THIS_MODULE,
+               .hook = ipt_hook,
+               .pf = PF_INET,
+               .hooknum = NF_IP_LOCAL_OUT,
+               .priority = NF_IP_PRI_RAW,
+               .owner = THIS_MODULE,
        },
 };
 
@@ -126,31 +126,20 @@ static int __init iptable_raw_init(void)
                return ret;
 
        /* Register hooks */
-       ret = nf_register_hook(&ipt_ops[0]);
+       ret = nf_register_hooks(ipt_ops, ARRAY_SIZE(ipt_ops));
        if (ret < 0)
                goto cleanup_table;
 
-       ret = nf_register_hook(&ipt_ops[1]);
-       if (ret < 0)
-               goto cleanup_hook0;
-
        return ret;
 
- cleanup_hook0:
-       nf_unregister_hook(&ipt_ops[0]);
  cleanup_table:
        ipt_unregister_table(&packet_raw);
-
        return ret;
 }
 
 static void __exit iptable_raw_fini(void)
 {
-       unsigned int i;
-
-       for (i = 0; i < sizeof(ipt_ops)/sizeof(struct nf_hook_ops); i++)
-               nf_unregister_hook(&ipt_ops[i]);
-
+       nf_unregister_hooks(ipt_ops, ARRAY_SIZE(ipt_ops));
        ipt_unregister_table(&packet_raw);
 }
 
index 4afbc699d3ba4ecedba1cbfca87d4be862cc57ec..5bc9f64d7b5b06f9bf1d5a2d8c3923f6fdaccfb9 100644 (file)
@@ -210,71 +210,63 @@ static unsigned int ipv4_conntrack_local(unsigned int hooknum,
 
 /* Connection tracking may drop packets, but never alters them, so
    make it the first hook. */
-static struct nf_hook_ops ipv4_conntrack_defrag_ops = {
-       .hook           = ipv4_conntrack_defrag,
-       .owner          = THIS_MODULE,
-       .pf             = PF_INET,
-       .hooknum        = NF_IP_PRE_ROUTING,
-       .priority       = NF_IP_PRI_CONNTRACK_DEFRAG,
-};
-
-static struct nf_hook_ops ipv4_conntrack_in_ops = {
-       .hook           = ipv4_conntrack_in,
-       .owner          = THIS_MODULE,
-       .pf             = PF_INET,
-       .hooknum        = NF_IP_PRE_ROUTING,
-       .priority       = NF_IP_PRI_CONNTRACK,
-};
-
-static struct nf_hook_ops ipv4_conntrack_defrag_local_out_ops = {
-       .hook           = ipv4_conntrack_defrag,
-       .owner          = THIS_MODULE,
-       .pf             = PF_INET,
-       .hooknum        = NF_IP_LOCAL_OUT,
-       .priority       = NF_IP_PRI_CONNTRACK_DEFRAG,
-};
-
-static struct nf_hook_ops ipv4_conntrack_local_out_ops = {
-       .hook           = ipv4_conntrack_local,
-       .owner          = THIS_MODULE,
-       .pf             = PF_INET,
-       .hooknum        = NF_IP_LOCAL_OUT,
-       .priority       = NF_IP_PRI_CONNTRACK,
-};
-
-/* helpers */
-static struct nf_hook_ops ipv4_conntrack_helper_out_ops = {
-       .hook           = ipv4_conntrack_help,
-       .owner          = THIS_MODULE,
-       .pf             = PF_INET,
-       .hooknum        = NF_IP_POST_ROUTING,
-       .priority       = NF_IP_PRI_CONNTRACK_HELPER,
-};
-
-static struct nf_hook_ops ipv4_conntrack_helper_in_ops = {
-       .hook           = ipv4_conntrack_help,
-       .owner          = THIS_MODULE,
-       .pf             = PF_INET,
-       .hooknum        = NF_IP_LOCAL_IN,
-       .priority       = NF_IP_PRI_CONNTRACK_HELPER,
-};
-
-
-/* Refragmenter; last chance. */
-static struct nf_hook_ops ipv4_conntrack_out_ops = {
-       .hook           = ipv4_confirm,
-       .owner          = THIS_MODULE,
-       .pf             = PF_INET,
-       .hooknum        = NF_IP_POST_ROUTING,
-       .priority       = NF_IP_PRI_CONNTRACK_CONFIRM,
-};
-
-static struct nf_hook_ops ipv4_conntrack_local_in_ops = {
-       .hook           = ipv4_confirm,
-       .owner          = THIS_MODULE,
-       .pf             = PF_INET,
-       .hooknum        = NF_IP_LOCAL_IN,
-       .priority       = NF_IP_PRI_CONNTRACK_CONFIRM,
+static struct nf_hook_ops ipv4_conntrack_ops[] = {
+       {
+               .hook           = ipv4_conntrack_defrag,
+               .owner          = THIS_MODULE,
+               .pf             = PF_INET,
+               .hooknum        = NF_IP_PRE_ROUTING,
+               .priority       = NF_IP_PRI_CONNTRACK_DEFRAG,
+       },
+       {
+               .hook           = ipv4_conntrack_in,
+               .owner          = THIS_MODULE,
+               .pf             = PF_INET,
+               .hooknum        = NF_IP_PRE_ROUTING,
+               .priority       = NF_IP_PRI_CONNTRACK,
+       },
+       {
+               .hook           = ipv4_conntrack_defrag,
+               .owner          = THIS_MODULE,
+               .pf             = PF_INET,
+               .hooknum        = NF_IP_LOCAL_OUT,
+               .priority       = NF_IP_PRI_CONNTRACK_DEFRAG,
+       },
+       {
+               .hook           = ipv4_conntrack_local,
+               .owner          = THIS_MODULE,
+               .pf             = PF_INET,
+               .hooknum        = NF_IP_LOCAL_OUT,
+               .priority       = NF_IP_PRI_CONNTRACK,
+       },
+       {
+               .hook           = ipv4_conntrack_help,
+               .owner          = THIS_MODULE,
+               .pf             = PF_INET,
+               .hooknum        = NF_IP_POST_ROUTING,
+               .priority       = NF_IP_PRI_CONNTRACK_HELPER,
+       },
+       {
+               .hook           = ipv4_conntrack_help,
+               .owner          = THIS_MODULE,
+               .pf             = PF_INET,
+               .hooknum        = NF_IP_LOCAL_IN,
+               .priority       = NF_IP_PRI_CONNTRACK_HELPER,
+       },
+       {
+               .hook           = ipv4_confirm,
+               .owner          = THIS_MODULE,
+               .pf             = PF_INET,
+               .hooknum        = NF_IP_POST_ROUTING,
+               .priority       = NF_IP_PRI_CONNTRACK_CONFIRM,
+       },
+       {
+               .hook           = ipv4_confirm,
+               .owner          = THIS_MODULE,
+               .pf             = PF_INET,
+               .hooknum        = NF_IP_LOCAL_IN,
+               .priority       = NF_IP_PRI_CONNTRACK_CONFIRM,
+       },
 };
 
 #ifdef CONFIG_SYSCTL
@@ -440,16 +432,20 @@ struct nf_conntrack_l3proto nf_conntrack_l3proto_ipv4 = {
 extern struct nf_conntrack_protocol nf_conntrack_protocol_tcp4;
 extern struct nf_conntrack_protocol nf_conntrack_protocol_udp4;
 extern struct nf_conntrack_protocol nf_conntrack_protocol_icmp;
-static int init_or_cleanup(int init)
+
+MODULE_ALIAS("nf_conntrack-" __stringify(AF_INET));
+MODULE_LICENSE("GPL");
+
+static int __init nf_conntrack_l3proto_ipv4_init(void)
 {
        int ret = 0;
 
-       if (!init) goto cleanup;
+       need_conntrack();
 
        ret = nf_register_sockopt(&so_getorigdst);
        if (ret < 0) {
                printk(KERN_ERR "Unable to register netfilter socket option\n");
-               goto cleanup_nothing;
+               return ret;
        }
 
        ret = nf_conntrack_protocol_register(&nf_conntrack_protocol_tcp4);
@@ -476,84 +472,26 @@ static int init_or_cleanup(int init)
                goto cleanup_icmp;
        }
 
-       ret = nf_register_hook(&ipv4_conntrack_defrag_ops);
+       ret = nf_register_hooks(ipv4_conntrack_ops,
+                               ARRAY_SIZE(ipv4_conntrack_ops));
        if (ret < 0) {
-               printk("nf_conntrack_ipv4: can't register pre-routing defrag hook.\n");
+               printk("nf_conntrack_ipv4: can't register hooks.\n");
                goto cleanup_ipv4;
        }
-       ret = nf_register_hook(&ipv4_conntrack_defrag_local_out_ops);
-       if (ret < 0) {
-               printk("nf_conntrack_ipv4: can't register local_out defrag hook.\n");
-               goto cleanup_defragops;
-       }
-
-       ret = nf_register_hook(&ipv4_conntrack_in_ops);
-       if (ret < 0) {
-               printk("nf_conntrack_ipv4: can't register pre-routing hook.\n");
-               goto cleanup_defraglocalops;
-       }
-
-       ret = nf_register_hook(&ipv4_conntrack_local_out_ops);
-       if (ret < 0) {
-               printk("nf_conntrack_ipv4: can't register local out hook.\n");
-               goto cleanup_inops;
-       }
-
-       ret = nf_register_hook(&ipv4_conntrack_helper_in_ops);
-       if (ret < 0) {
-               printk("nf_conntrack_ipv4: can't register local helper hook.\n");
-               goto cleanup_inandlocalops;
-       }
-
-       ret = nf_register_hook(&ipv4_conntrack_helper_out_ops);
-       if (ret < 0) {
-               printk("nf_conntrack_ipv4: can't register postrouting helper hook.\n");
-               goto cleanup_helperinops;
-       }
-
-       ret = nf_register_hook(&ipv4_conntrack_out_ops);
-       if (ret < 0) {
-               printk("nf_conntrack_ipv4: can't register post-routing hook.\n");
-               goto cleanup_helperoutops;
-       }
-
-       ret = nf_register_hook(&ipv4_conntrack_local_in_ops);
-       if (ret < 0) {
-               printk("nf_conntrack_ipv4: can't register local in hook.\n");
-               goto cleanup_inoutandlocalops;
-       }
-
 #ifdef CONFIG_SYSCTL
        nf_ct_ipv4_sysctl_header = register_sysctl_table(nf_ct_net_table, 0);
        if (nf_ct_ipv4_sysctl_header == NULL) {
                printk("nf_conntrack: can't register to sysctl.\n");
                ret = -ENOMEM;
-               goto cleanup_localinops;
+               goto cleanup_hooks;
        }
 #endif
        return ret;
 
- cleanup:
-       synchronize_net();
 #ifdef CONFIG_SYSCTL
-       unregister_sysctl_table(nf_ct_ipv4_sysctl_header);
- cleanup_localinops:
+ cleanup_hooks:
+       nf_unregister_hooks(ipv4_conntrack_ops, ARRAY_SIZE(ipv4_conntrack_ops));
 #endif
-       nf_unregister_hook(&ipv4_conntrack_local_in_ops);
- cleanup_inoutandlocalops:
-       nf_unregister_hook(&ipv4_conntrack_out_ops);
- cleanup_helperoutops:
-       nf_unregister_hook(&ipv4_conntrack_helper_out_ops);
- cleanup_helperinops:
-       nf_unregister_hook(&ipv4_conntrack_helper_in_ops);
- cleanup_inandlocalops:
-       nf_unregister_hook(&ipv4_conntrack_local_out_ops);
- cleanup_inops:
-       nf_unregister_hook(&ipv4_conntrack_in_ops);
- cleanup_defraglocalops:
-       nf_unregister_hook(&ipv4_conntrack_defrag_local_out_ops);
- cleanup_defragops:
-       nf_unregister_hook(&ipv4_conntrack_defrag_ops);
  cleanup_ipv4:
        nf_conntrack_l3proto_unregister(&nf_conntrack_l3proto_ipv4);
  cleanup_icmp:
@@ -564,22 +502,21 @@ static int init_or_cleanup(int init)
        nf_conntrack_protocol_unregister(&nf_conntrack_protocol_tcp4);
  cleanup_sockopt:
        nf_unregister_sockopt(&so_getorigdst);
- cleanup_nothing:
        return ret;
 }
 
-MODULE_ALIAS("nf_conntrack-" __stringify(AF_INET));
-MODULE_LICENSE("GPL");
-
-static int __init nf_conntrack_l3proto_ipv4_init(void)
-{
-       need_conntrack();
-       return init_or_cleanup(1);
-}
-
 static void __exit nf_conntrack_l3proto_ipv4_fini(void)
 {
-       init_or_cleanup(0);
+       synchronize_net();
+#ifdef CONFIG_SYSCTL
+       unregister_sysctl_table(nf_ct_ipv4_sysctl_header);
+#endif
+       nf_unregister_hooks(ipv4_conntrack_ops, ARRAY_SIZE(ipv4_conntrack_ops));
+       nf_conntrack_l3proto_unregister(&nf_conntrack_l3proto_ipv4);
+       nf_conntrack_protocol_unregister(&nf_conntrack_protocol_icmp);
+       nf_conntrack_protocol_unregister(&nf_conntrack_protocol_udp4);
+       nf_conntrack_protocol_unregister(&nf_conntrack_protocol_tcp4);
+       nf_unregister_sockopt(&so_getorigdst);
 }
 
 module_init(nf_conntrack_l3proto_ipv4_init);
index 52dc175be39a65701d6bb730abdd7238daaa0245..4b0d361cc6e69fbb178b8fc82f47631a86053527 100644 (file)
@@ -235,30 +235,14 @@ icmp_error(struct sk_buff *skb, unsigned int dataoff,
        }
 
        /* See ip_conntrack_proto_tcp.c */
-       if (hooknum != NF_IP_PRE_ROUTING)
-               goto checksum_skipped;
-
-       switch (skb->ip_summed) {
-       case CHECKSUM_HW:
-               if (!(u16)csum_fold(skb->csum))
-                       break;
+       if (hooknum == NF_IP_PRE_ROUTING &&
+           nf_ip_checksum(skb, hooknum, dataoff, 0)) {
                if (LOG_INVALID(IPPROTO_ICMP))
                        nf_log_packet(PF_INET, 0, skb, NULL, NULL, NULL,
                                      "nf_ct_icmp: bad HW ICMP checksum ");
                return -NF_ACCEPT;
-       case CHECKSUM_NONE:
-               if ((u16)csum_fold(skb_checksum(skb, 0, skb->len, 0))) {
-                       if (LOG_INVALID(IPPROTO_ICMP))
-                               nf_log_packet(PF_INET, 0, skb, NULL, NULL,
-                                             NULL,
-                                             "nf_ct_icmp: bad ICMP checksum ");
-                       return -NF_ACCEPT;
-               }
-       default:
-               break;
        }
 
-checksum_skipped:
        /*
         *      18 is the highest 'known' ICMP type. Anything else is a mystery
         *
index 1b167c4bb3beb0254f446a6ab21ca41fd87a0455..d61e2a9d394d24d22d282deabba9fafeb088affa 100644 (file)
@@ -49,7 +49,7 @@ static int fold_prot_inuse(struct proto *proto)
        int res = 0;
        int cpu;
 
-       for_each_cpu(cpu)
+       for_each_possible_cpu(cpu)
                res += proto->stats[cpu].inuse;
 
        return res;
@@ -91,7 +91,7 @@ fold_field(void *mib[], int offt)
        unsigned long res = 0;
        int i;
 
-       for_each_cpu(i) {
+       for_each_possible_cpu(i) {
                res += *(((unsigned long *) per_cpu_ptr(mib[0], i)) + offt);
                res += *(((unsigned long *) per_cpu_ptr(mib[1], i)) + offt);
        }
index 94fcbc5e5a1b62cfd696a6751dfcd17816a74f4a..cc9423de7311fcac8845b38a055b6ea008b22ec7 100644 (file)
@@ -2741,7 +2741,10 @@ int inet_rtm_getroute(struct sk_buff *in_skb, struct nlmsghdr* nlh, void *arg)
        /* Reserve room for dummy headers, this skb can pass
           through good chunk of routing engine.
         */
-       skb->mac.raw = skb->data;
+       skb->mac.raw = skb->nh.raw = skb->data;
+
+       /* Bugfix: need to give ip_route_input enough of an IP header to not gag. */
+       skb->nh.iph->protocol = IPPROTO_ICMP;
        skb_reserve(skb, MAX_HEADER + sizeof(struct iphdr));
 
        if (rta[RTA_SRC - 1])
@@ -3083,7 +3086,7 @@ static int ip_rt_acct_read(char *buffer, char **start, off_t offset,
                memcpy(dst, src, length);
 
                /* Add the other cpus in, one int at a time */
-               for_each_cpu(i) {
+               for_each_possible_cpu(i) {
                        unsigned int j;
 
                        src = ((u32 *) IP_RT_ACCT_CPU(i)) + offset;
index 195d8358455839cb77e8e48b1a99a60e74623fe9..9f0cca4c4fae2021e52ee5655f9b89b9ade7f753 100644 (file)
@@ -4559,7 +4559,6 @@ discard:
 
 EXPORT_SYMBOL(sysctl_tcp_ecn);
 EXPORT_SYMBOL(sysctl_tcp_reordering);
-EXPORT_SYMBOL(sysctl_tcp_abc);
 EXPORT_SYMBOL(tcp_parse_options);
 EXPORT_SYMBOL(tcp_rcv_established);
 EXPORT_SYMBOL(tcp_rcv_state_process);
index 9e85c04161090e7687024906e2d288f3132cb4c1..672950e54c498a2cddf1f86b3321363be991e3ef 100644 (file)
@@ -1859,5 +1859,4 @@ EXPORT_SYMBOL(tcp_proc_unregister);
 #endif
 EXPORT_SYMBOL(sysctl_local_port_range);
 EXPORT_SYMBOL(sysctl_tcp_low_latency);
-EXPORT_SYMBOL(sysctl_tcp_tw_reuse);
 
index 9d79546d384ef1ee49a45e1a29e5f78fbb36a214..a28ae593b97613d4d09a692e2363f24e2b59417b 100644 (file)
@@ -59,9 +59,6 @@ int sysctl_tcp_tso_win_divisor = 3;
 int sysctl_tcp_mtu_probing = 0;
 int sysctl_tcp_base_mss = 512;
 
-EXPORT_SYMBOL(sysctl_tcp_mtu_probing);
-EXPORT_SYMBOL(sysctl_tcp_base_mss);
-
 static void update_send_head(struct sock *sk, struct tcp_sock *tp,
                             struct sk_buff *skb)
 {
@@ -536,6 +533,7 @@ int tcp_fragment(struct sock *sk, struct sk_buff *skb, u32 len, unsigned int mss
        struct tcp_sock *tp = tcp_sk(sk);
        struct sk_buff *buff;
        int nsize, old_factor;
+       int nlen;
        u16 flags;
 
        BUG_ON(len > skb->len);
@@ -554,7 +552,11 @@ int tcp_fragment(struct sock *sk, struct sk_buff *skb, u32 len, unsigned int mss
        buff = sk_stream_alloc_skb(sk, nsize, GFP_ATOMIC);
        if (buff == NULL)
                return -ENOMEM; /* We'll just try again later. */
+
        sk_charge_skb(sk, buff);
+       nlen = skb->len - len - nsize;
+       buff->truesize += nlen;
+       skb->truesize -= nlen;
 
        /* Correct the sequence numbers. */
        TCP_SKB_CB(buff)->seq = TCP_SKB_CB(skb)->seq + len;
@@ -1040,7 +1042,8 @@ static int tso_fragment(struct sock *sk, struct sk_buff *skb, unsigned int len,
        if (unlikely(buff == NULL))
                return -ENOMEM;
 
-       buff->truesize = nlen;
+       sk_charge_skb(sk, buff);
+       buff->truesize += nlen;
        skb->truesize -= nlen;
 
        /* Correct the sequence numbers. */
index 0d7d386dac2287bbfb9ef42ec6bbf0d83bb5073f..8d30c48f090e59dd9ac96b40252b0ac4c9099246 100644 (file)
@@ -8,6 +8,8 @@
 #include <linux/mutex.h>
 #include <linux/netdevice.h>
 #include <linux/skbuff.h>
+#include <net/icmp.h>
+#include <net/ip.h>
 #include <net/protocol.h>
 #include <net/xfrm.h>
 
@@ -70,10 +72,16 @@ static int tunnel4_rcv(struct sk_buff *skb)
 {
        struct xfrm_tunnel *handler;
 
+       if (!pskb_may_pull(skb, sizeof(struct iphdr)))
+               goto drop;
+
        for (handler = tunnel4_handlers; handler; handler = handler->next)
                if (!handler->handler(skb))
                        return 0;
 
+       icmp_send(skb, ICMP_DEST_UNREACH, ICMP_PORT_UNREACH, 0);
+
+drop:
        kfree_skb(skb);
        return 0;
 }
index e1b8f4b90d802bf430fb8ddaff53699882bba5b8..3e174c83bfe7a805fe40d446d7114124453b0d9f 100644 (file)
@@ -37,8 +37,6 @@ static int xfrm4_parse_spi(struct sk_buff *skb, u8 nexthdr, u32 *spi, u32 *seq)
 {
        switch (nexthdr) {
        case IPPROTO_IPIP:
-               if (!pskb_may_pull(skb, sizeof(struct iphdr)))
-                       return -EINVAL;
                *spi = skb->nh.iph->saddr;
                *seq = 0;
                return 0;
@@ -90,7 +88,7 @@ int xfrm4_rcv_encap(struct sk_buff *skb, __u16 encap_type)
                if (unlikely(x->km.state != XFRM_STATE_VALID))
                        goto drop_unlock;
 
-               if (x->encap->encap_type != encap_type)
+               if ((x->encap ? x->encap->encap_type : 0) != encap_type)
                        goto drop_unlock;
 
                if (x->props.replay_window && xfrm_replay_check(x, seq))
index 2a1e7e45b890ff9eccb841c3271b3b09e52c8305..a18d4256372cf988e66d1feef51507b7163b8103 100644 (file)
@@ -485,15 +485,27 @@ static struct tlvtype_proc tlvprochopopt_lst[] = {
        { -1, }
 };
 
-int ipv6_parse_hopopts(struct sk_buff *skb, int nhoff)
+int ipv6_parse_hopopts(struct sk_buff *skb)
 {
        struct inet6_skb_parm *opt = IP6CB(skb);
 
+       /*
+        * skb->nh.raw is equal to skb->data, and
+        * skb->h.raw - skb->nh.raw is always equal to
+        * sizeof(struct ipv6hdr) by definition of
+        * hop-by-hop options.
+        */
+       if (!pskb_may_pull(skb, sizeof(struct ipv6hdr) + 8) ||
+           !pskb_may_pull(skb, sizeof(struct ipv6hdr) + ((skb->h.raw[1] + 1) << 3))) {
+               kfree_skb(skb);
+               return -1;
+       }
+
        opt->hop = sizeof(struct ipv6hdr);
        if (ip6_parse_tlv(tlvprochopopt_lst, skb)) {
                skb->h.raw += (skb->h.raw[1]+1)<<3;
                opt->nhoff = sizeof(struct ipv6hdr);
-               return sizeof(struct ipv6hdr);
+               return 1;
        }
        return -1;
 }
index 21eb725e885ffe85bfa72d1f35ad9993911cd68f..1044b6fce0d5d472b11b0eef3a2e261650869e5e 100644 (file)
@@ -717,7 +717,7 @@ int __init icmpv6_init(struct net_proto_family *ops)
        struct sock *sk;
        int err, i, j;
 
-       for_each_cpu(i) {
+       for_each_possible_cpu(i) {
                err = sock_create_kern(PF_INET6, SOCK_RAW, IPPROTO_ICMPV6,
                                       &per_cpu(__icmpv6_socket, i));
                if (err < 0) {
@@ -763,7 +763,7 @@ void icmpv6_cleanup(void)
 {
        int i;
 
-       for_each_cpu(i) {
+       for_each_possible_cpu(i) {
                sock_release(per_cpu(__icmpv6_socket, i));
        }
        inet6_del_protocol(&icmpv6_protocol, IPPROTO_ICMPV6);
index bb8ffb8a14c5d17ff7e22c3d18d9ffb4ad9f058e..2ae84c961678f17d258aaf1524a2d58a39f60835 100644 (file)
 #include <net/inet6_hashtables.h>
 #include <net/ip.h>
 
+void __inet6_hash(struct inet_hashinfo *hashinfo,
+                               struct sock *sk)
+{
+       struct hlist_head *list;
+       rwlock_t *lock;
+
+       BUG_TRAP(sk_unhashed(sk));
+
+       if (sk->sk_state == TCP_LISTEN) {
+               list = &hashinfo->listening_hash[inet_sk_listen_hashfn(sk)];
+               lock = &hashinfo->lhash_lock;
+               inet_listen_wlock(hashinfo);
+       } else {
+               unsigned int hash;
+               sk->sk_hash = hash = inet6_sk_ehashfn(sk);
+               hash &= (hashinfo->ehash_size - 1);
+               list = &hashinfo->ehash[hash].chain;
+               lock = &hashinfo->ehash[hash].lock;
+               write_lock(lock);
+       }
+
+       __sk_add_node(sk, list);
+       sock_prot_inc_use(sk->sk_prot);
+       write_unlock(lock);
+}
+EXPORT_SYMBOL(__inet6_hash);
+
+/*
+ * Sockets in TCP_CLOSE state are _always_ taken out of the hash, so
+ * we need not check it for TCP lookups anymore, thanks Alexey. -DaveM
+ *
+ * The sockhash lock must be held as a reader here.
+ */
+struct sock *__inet6_lookup_established(struct inet_hashinfo *hashinfo,
+                                          const struct in6_addr *saddr,
+                                          const u16 sport,
+                                          const struct in6_addr *daddr,
+                                          const u16 hnum,
+                                          const int dif)
+{
+       struct sock *sk;
+       const struct hlist_node *node;
+       const __u32 ports = INET_COMBINED_PORTS(sport, hnum);
+       /* Optimize here for direct hit, only listening connections can
+        * have wildcards anyways.
+        */
+       unsigned int hash = inet6_ehashfn(daddr, hnum, saddr, sport);
+       struct inet_ehash_bucket *head = inet_ehash_bucket(hashinfo, hash);
+
+       prefetch(head->chain.first);
+       read_lock(&head->lock);
+       sk_for_each(sk, node, &head->chain) {
+               /* For IPV6 do the cheaper port and family tests first. */
+               if (INET6_MATCH(sk, hash, saddr, daddr, ports, dif))
+                       goto hit; /* You sunk my battleship! */
+       }
+       /* Must check for a TIME_WAIT'er before going to listener hash. */
+       sk_for_each(sk, node, &(head + hashinfo->ehash_size)->chain) {
+               const struct inet_timewait_sock *tw = inet_twsk(sk);
+
+               if(*((__u32 *)&(tw->tw_dport))  == ports        &&
+                  sk->sk_family                == PF_INET6) {
+                       const struct inet6_timewait_sock *tw6 = inet6_twsk(sk);
+
+                       if (ipv6_addr_equal(&tw6->tw_v6_daddr, saddr)   &&
+                           ipv6_addr_equal(&tw6->tw_v6_rcv_saddr, daddr)       &&
+                           (!sk->sk_bound_dev_if || sk->sk_bound_dev_if == dif))
+                               goto hit;
+               }
+       }
+       read_unlock(&head->lock);
+       return NULL;
+
+hit:
+       sock_hold(sk);
+       read_unlock(&head->lock);
+       return sk;
+}
+EXPORT_SYMBOL(__inet6_lookup_established);
+
 struct sock *inet6_lookup_listener(struct inet_hashinfo *hashinfo,
                                   const struct in6_addr *daddr,
                                   const unsigned short hnum, const int dif)
index 29f73592e68e51304c7c6859c82eb44248e3a3ae..aceee252503dfe84f5ccb34b950949f284577d0a 100644 (file)
@@ -114,11 +114,10 @@ int ipv6_rcv(struct sk_buff *skb, struct net_device *dev, struct packet_type *pt
        }
 
        if (hdr->nexthdr == NEXTHDR_HOP) {
-               if (ipv6_parse_hopopts(skb, IP6CB(skb)->nhoff) < 0) {
+               if (ipv6_parse_hopopts(skb) < 0) {
                        IP6_INC_STATS_BH(IPSTATS_MIB_INHDRERRORS);
                        return 0;
                }
-               hdr = skb->nh.ipv6h;
        }
 
        return NF_HOOK(PF_INET6,NF_IP6_PRE_ROUTING, skb, dev, NULL, ip6_rcv_finish);
index ff9040c92556d20fb453b5ff815e402dc6c6ff60..a995796b5a577fb7b0f4a947d54a85897143a1ab 100644 (file)
@@ -519,9 +519,6 @@ ip6ip6_rcv(struct sk_buff *skb)
        struct ipv6hdr *ipv6h;
        struct ip6_tnl *t;
 
-       if (!pskb_may_pull(skb, sizeof (*ipv6h)))
-               goto discard;
-
        ipv6h = skb->nh.ipv6h;
 
        read_lock(&ip6ip6_lock);
@@ -529,8 +526,7 @@ ip6ip6_rcv(struct sk_buff *skb)
        if ((t = ip6ip6_tnl_lookup(&ipv6h->saddr, &ipv6h->daddr)) != NULL) {
                if (!xfrm6_policy_check(NULL, XFRM_POLICY_IN, skb)) {
                        read_unlock(&ip6ip6_lock);
-                       kfree_skb(skb);
-                       return 0;
+                       goto discard;
                }
 
                if (!(t->parms.flags & IP6_TNL_F_CAP_RCV)) {
@@ -557,9 +553,11 @@ ip6ip6_rcv(struct sk_buff *skb)
                return 0;
        }
        read_unlock(&ip6ip6_lock);
-       icmpv6_send(skb, ICMPV6_DEST_UNREACH, ICMPV6_ADDR_UNREACH, 0, skb->dev);
-discard:
        return 1;
+
+discard:
+       kfree_skb(skb);
+       return 0;
 }
 
 static inline struct ipv6_txoptions *create_tel(__u8 encap_limit)
index 00f3fadfcca7f4f736d1038d2919ba3e8d668296..05eb67def39f17e9c9b84d9270fdbe6fe1ee2a87 100644 (file)
@@ -290,7 +290,7 @@ static void ipcomp6_free_scratches(void)
        if (!scratches)
                return;
 
-       for_each_cpu(i) {
+       for_each_possible_cpu(i) {
                void *scratch = *per_cpu_ptr(scratches, i);
 
                vfree(scratch);
@@ -313,7 +313,7 @@ static void **ipcomp6_alloc_scratches(void)
 
        ipcomp6_scratches = scratches;
 
-       for_each_cpu(i) {
+       for_each_possible_cpu(i) {
                void *scratch = vmalloc(IPCOMP_SCRATCH_SIZE);
                if (!scratch)
                        return NULL;
@@ -344,7 +344,7 @@ static void ipcomp6_free_tfms(struct crypto_tfm **tfms)
        if (!tfms)
                return;
 
-       for_each_cpu(cpu) {
+       for_each_possible_cpu(cpu) {
                struct crypto_tfm *tfm = *per_cpu_ptr(tfms, cpu);
                crypto_free_tfm(tfm);
        }
@@ -384,7 +384,7 @@ static struct crypto_tfm **ipcomp6_alloc_tfms(const char *alg_name)
        if (!tfms)
                goto error;
 
-       for_each_cpu(cpu) {
+       for_each_possible_cpu(cpu) {
                struct crypto_tfm *tfm = crypto_alloc_tfm(alg_name, 0);
                if (!tfm)
                        goto error;
index d750cfc019dcabc7efa187266e0001e550d30fe5..395a417ba9554baaeb0d9678c543abe4e802b3eb 100644 (file)
@@ -7,6 +7,7 @@
 #include <net/ipv6.h>
 #include <net/ip6_route.h>
 #include <net/xfrm.h>
+#include <net/ip6_checksum.h>
 
 int ip6_route_me_harder(struct sk_buff *skb)
 {
@@ -54,7 +55,7 @@ struct ip6_rt_info {
        struct in6_addr saddr;
 };
 
-static void save(const struct sk_buff *skb, struct nf_info *info)
+static void nf_ip6_saveroute(const struct sk_buff *skb, struct nf_info *info)
 {
        struct ip6_rt_info *rt_info = nf_info_reroute(info);
 
@@ -66,7 +67,7 @@ static void save(const struct sk_buff *skb, struct nf_info *info)
        }
 }
 
-static int reroute(struct sk_buff **pskb, const struct nf_info *info)
+static int nf_ip6_reroute(struct sk_buff **pskb, const struct nf_info *info)
 {
        struct ip6_rt_info *rt_info = nf_info_reroute(info);
 
@@ -79,15 +80,50 @@ static int reroute(struct sk_buff **pskb, const struct nf_info *info)
        return 0;
 }
 
-static struct nf_queue_rerouter ip6_reroute = {
-       .rer_size       = sizeof(struct ip6_rt_info),
-       .save           = &save,
-       .reroute        = &reroute,
+unsigned int nf_ip6_checksum(struct sk_buff *skb, unsigned int hook,
+                            unsigned int dataoff, u_int8_t protocol)
+{
+       struct ipv6hdr *ip6h = skb->nh.ipv6h;
+       unsigned int csum = 0;
+
+       switch (skb->ip_summed) {
+       case CHECKSUM_HW:
+               if (hook != NF_IP6_PRE_ROUTING && hook != NF_IP6_LOCAL_IN)
+                       break;
+               if (!csum_ipv6_magic(&ip6h->saddr, &ip6h->daddr,
+                                    skb->len - dataoff, protocol,
+                                    csum_sub(skb->csum,
+                                             skb_checksum(skb, 0,
+                                                          dataoff, 0)))) {
+                       skb->ip_summed = CHECKSUM_UNNECESSARY;
+                       break;
+               }
+               /* fall through */
+       case CHECKSUM_NONE:
+               skb->csum = ~csum_ipv6_magic(&ip6h->saddr, &ip6h->daddr,
+                                            skb->len - dataoff,
+                                            protocol,
+                                            csum_sub(0,
+                                                     skb_checksum(skb, 0,
+                                                                  dataoff, 0)));
+               csum = __skb_checksum_complete(skb);
+       }
+       return csum;
+}
+
+EXPORT_SYMBOL(nf_ip6_checksum);
+
+static struct nf_afinfo nf_ip6_afinfo = {
+       .family         = AF_INET6,
+       .checksum       = nf_ip6_checksum,
+       .saveroute      = nf_ip6_saveroute,
+       .reroute        = nf_ip6_reroute,
+       .route_key_size = sizeof(struct ip6_rt_info),
 };
 
 int __init ipv6_netfilter_init(void)
 {
-       return nf_register_queue_rerouter(PF_INET6, &ip6_reroute);
+       return nf_register_afinfo(&nf_ip6_afinfo);
 }
 
 /* This can be called from inet6_init() on errors, so it cannot
@@ -95,5 +131,5 @@ int __init ipv6_netfilter_init(void)
  */
 void ipv6_netfilter_fini(void)
 {
-       nf_unregister_queue_rerouter(PF_INET6);
+       nf_unregister_afinfo(&nf_ip6_afinfo);
 }
index e81c6a9dab81d6c5e25add11ed68df89e4655b91..b4b7d441af25411f04af9e7a657cb21488f51370 100644 (file)
@@ -658,15 +658,11 @@ static struct nf_queue_handler nfqh = {
        .outfn  = &ipq_enqueue_packet,
 };
 
-static int
-init_or_cleanup(int init)
+static int __init ip6_queue_init(void)
 {
        int status = -ENOMEM;
        struct proc_dir_entry *proc;
        
-       if (!init)
-               goto cleanup;
-
        netlink_register_notifier(&ipq_nl_notifier);
        ipqnl = netlink_kernel_create(NETLINK_IP6_FW, 0, ipq_rcv_sk,
                                      THIS_MODULE);
@@ -693,11 +689,6 @@ init_or_cleanup(int init)
        }
        return status;
 
-cleanup:
-       nf_unregister_queue_handlers(&nfqh);
-       synchronize_net();
-       ipq_flush(NF_DROP);
-       
 cleanup_sysctl:
        unregister_sysctl_table(ipq_sysctl_header);
        unregister_netdevice_notifier(&ipq_dev_notifier);
@@ -713,15 +704,21 @@ cleanup_netlink_notifier:
        return status;
 }
 
-static int __init ip6_queue_init(void)
-{
-       
-       return init_or_cleanup(1);
-}
-
 static void __exit ip6_queue_fini(void)
 {
-       init_or_cleanup(0);
+       nf_unregister_queue_handlers(&nfqh);
+       synchronize_net();
+       ipq_flush(NF_DROP);
+
+       unregister_sysctl_table(ipq_sysctl_header);
+       unregister_netdevice_notifier(&ipq_dev_notifier);
+       proc_net_remove(IPQ_PROC_FS_NAME);
+
+       sock_release(ipqnl->sk_socket);
+       mutex_lock(&ipqnl_mutex);
+       mutex_unlock(&ipqnl_mutex);
+
+       netlink_unregister_notifier(&ipq_nl_notifier);
 }
 
 MODULE_DESCRIPTION("IPv6 packet queue handler");
index 3ecf2db841f80802f2971faa34e592729339ee96..642b4b11464f1594c28cc99550fccd809d96d4df 100644 (file)
@@ -788,7 +788,7 @@ translate_table(const char *name,
        }
 
        /* And one copy for every other CPU */
-       for_each_cpu(i) {
+       for_each_possible_cpu(i) {
                if (newinfo->entries[i] && newinfo->entries[i] != entry0)
                        memcpy(newinfo->entries[i], entry0, newinfo->size);
        }
@@ -841,7 +841,7 @@ get_counters(const struct xt_table_info *t,
                           counters,
                           &i);
 
-       for_each_cpu(cpu) {
+       for_each_possible_cpu(cpu) {
                if (cpu == curcpu)
                        continue;
                i = 0;
index e5e724d9ee60ed40d61e651955528b60354606b0..60976c0c58e81ecdf3320152415d5be0bc80812f 100644 (file)
@@ -177,37 +177,20 @@ static int __init ip6table_filter_init(void)
                return ret;
 
        /* Register hooks */
-       ret = nf_register_hook(&ip6t_ops[0]);
+       ret = nf_register_hooks(ip6t_ops, ARRAY_SIZE(ip6t_ops));
        if (ret < 0)
                goto cleanup_table;
 
-       ret = nf_register_hook(&ip6t_ops[1]);
-       if (ret < 0)
-               goto cleanup_hook0;
-
-       ret = nf_register_hook(&ip6t_ops[2]);
-       if (ret < 0)
-               goto cleanup_hook1;
-
        return ret;
 
- cleanup_hook1:
-       nf_unregister_hook(&ip6t_ops[1]);
- cleanup_hook0:
-       nf_unregister_hook(&ip6t_ops[0]);
  cleanup_table:
        ip6t_unregister_table(&packet_filter);
-
        return ret;
 }
 
 static void __exit ip6table_filter_fini(void)
 {
-       unsigned int i;
-
-       for (i = 0; i < sizeof(ip6t_ops)/sizeof(struct nf_hook_ops); i++)
-               nf_unregister_hook(&ip6t_ops[i]);
-
+       nf_unregister_hooks(ip6t_ops, ARRAY_SIZE(ip6t_ops));
        ip6t_unregister_table(&packet_filter);
 }
 
index e1f0f6ae9841ed646dcd0c4d3afd9c9e9c6a0f91..03a13eab1daef67a7766b328acb9886edbd64014 100644 (file)
@@ -238,49 +238,20 @@ static int __init ip6table_mangle_init(void)
                return ret;
 
        /* Register hooks */
-       ret = nf_register_hook(&ip6t_ops[0]);
+       ret = nf_register_hooks(ip6t_ops, ARRAY_SIZE(ip6t_ops));
        if (ret < 0)
                goto cleanup_table;
 
-       ret = nf_register_hook(&ip6t_ops[1]);
-       if (ret < 0)
-               goto cleanup_hook0;
-
-       ret = nf_register_hook(&ip6t_ops[2]);
-       if (ret < 0)
-               goto cleanup_hook1;
-
-       ret = nf_register_hook(&ip6t_ops[3]);
-       if (ret < 0)
-               goto cleanup_hook2;
-
-       ret = nf_register_hook(&ip6t_ops[4]);
-       if (ret < 0)
-               goto cleanup_hook3;
-
        return ret;
 
- cleanup_hook3:
-        nf_unregister_hook(&ip6t_ops[3]);
- cleanup_hook2:
-       nf_unregister_hook(&ip6t_ops[2]);
- cleanup_hook1:
-       nf_unregister_hook(&ip6t_ops[1]);
- cleanup_hook0:
-       nf_unregister_hook(&ip6t_ops[0]);
  cleanup_table:
        ip6t_unregister_table(&packet_mangler);
-
        return ret;
 }
 
 static void __exit ip6table_mangle_fini(void)
 {
-       unsigned int i;
-
-       for (i = 0; i < sizeof(ip6t_ops)/sizeof(struct nf_hook_ops); i++)
-               nf_unregister_hook(&ip6t_ops[i]);
-
+       nf_unregister_hooks(ip6t_ops, ARRAY_SIZE(ip6t_ops));
        ip6t_unregister_table(&packet_mangler);
 }
 
index 54d1fffd62bac61c354981c4ab992c49adfaff2f..61a7c58e99f88c72fe3dda967388820460da47e1 100644 (file)
@@ -152,31 +152,20 @@ static int __init ip6table_raw_init(void)
                return ret;
 
        /* Register hooks */
-       ret = nf_register_hook(&ip6t_ops[0]);
+       ret = nf_register_hooks(ip6t_ops, ARRAY_SIZE(ip6t_ops));
        if (ret < 0)
                goto cleanup_table;
 
-       ret = nf_register_hook(&ip6t_ops[1]);
-       if (ret < 0)
-               goto cleanup_hook0;
-
        return ret;
 
- cleanup_hook0:
-       nf_unregister_hook(&ip6t_ops[0]);
  cleanup_table:
        ip6t_unregister_table(&packet_raw);
-
        return ret;
 }
 
 static void __exit ip6table_raw_fini(void)
 {
-       unsigned int i;
-
-       for (i = 0; i < sizeof(ip6t_ops)/sizeof(struct nf_hook_ops); i++)
-               nf_unregister_hook(&ip6t_ops[i]);
-
+       nf_unregister_hooks(ip6t_ops, ARRAY_SIZE(ip6t_ops));
        ip6t_unregister_table(&packet_raw);
 }
 
index c8b5a96cbb0f563baa97c1b3708329bfcef4d37e..93bae36f2663e03370e8016da83ae4a43843e6ad 100644 (file)
@@ -286,55 +286,49 @@ static unsigned int ipv6_conntrack_local(unsigned int hooknum,
        return ipv6_conntrack_in(hooknum, pskb, in, out, okfn);
 }
 
-/* Connection tracking may drop packets, but never alters them, so
-   make it the first hook. */
-static struct nf_hook_ops ipv6_conntrack_defrag_ops = {
-       .hook           = ipv6_defrag,
-       .owner          = THIS_MODULE,
-       .pf             = PF_INET6,
-       .hooknum        = NF_IP6_PRE_ROUTING,
-       .priority       = NF_IP6_PRI_CONNTRACK_DEFRAG,
-};
-
-static struct nf_hook_ops ipv6_conntrack_in_ops = {
-       .hook           = ipv6_conntrack_in,
-       .owner          = THIS_MODULE,
-       .pf             = PF_INET6,
-       .hooknum        = NF_IP6_PRE_ROUTING,
-       .priority       = NF_IP6_PRI_CONNTRACK,
-};
-
-static struct nf_hook_ops ipv6_conntrack_local_out_ops = {
-       .hook           = ipv6_conntrack_local,
-       .owner          = THIS_MODULE,
-       .pf             = PF_INET6,
-       .hooknum        = NF_IP6_LOCAL_OUT,
-       .priority       = NF_IP6_PRI_CONNTRACK,
-};
-
-static struct nf_hook_ops ipv6_conntrack_defrag_local_out_ops = {
-       .hook           = ipv6_defrag,
-       .owner          = THIS_MODULE,
-       .pf             = PF_INET6,
-       .hooknum        = NF_IP6_LOCAL_OUT,
-       .priority       = NF_IP6_PRI_CONNTRACK_DEFRAG,
-};
-
-/* Refragmenter; last chance. */
-static struct nf_hook_ops ipv6_conntrack_out_ops = {
-       .hook           = ipv6_confirm,
-       .owner          = THIS_MODULE,
-       .pf             = PF_INET6,
-       .hooknum        = NF_IP6_POST_ROUTING,
-       .priority       = NF_IP6_PRI_LAST,
-};
-
-static struct nf_hook_ops ipv6_conntrack_local_in_ops = {
-       .hook           = ipv6_confirm,
-       .owner          = THIS_MODULE,
-       .pf             = PF_INET6,
-       .hooknum        = NF_IP6_LOCAL_IN,
-       .priority       = NF_IP6_PRI_LAST-1,
+static struct nf_hook_ops ipv6_conntrack_ops[] = {
+       {
+               .hook           = ipv6_defrag,
+               .owner          = THIS_MODULE,
+               .pf             = PF_INET6,
+               .hooknum        = NF_IP6_PRE_ROUTING,
+               .priority       = NF_IP6_PRI_CONNTRACK_DEFRAG,
+       },
+       {
+               .hook           = ipv6_conntrack_in,
+               .owner          = THIS_MODULE,
+               .pf             = PF_INET6,
+               .hooknum        = NF_IP6_PRE_ROUTING,
+               .priority       = NF_IP6_PRI_CONNTRACK,
+       },
+       {
+               .hook           = ipv6_conntrack_local,
+               .owner          = THIS_MODULE,
+               .pf             = PF_INET6,
+               .hooknum        = NF_IP6_LOCAL_OUT,
+               .priority       = NF_IP6_PRI_CONNTRACK,
+       },
+       {
+               .hook           = ipv6_defrag,
+               .owner          = THIS_MODULE,
+               .pf             = PF_INET6,
+               .hooknum        = NF_IP6_LOCAL_OUT,
+               .priority       = NF_IP6_PRI_CONNTRACK_DEFRAG,
+       },
+       {
+               .hook           = ipv6_confirm,
+               .owner          = THIS_MODULE,
+               .pf             = PF_INET6,
+               .hooknum        = NF_IP6_POST_ROUTING,
+               .priority       = NF_IP6_PRI_LAST,
+       },
+       {
+               .hook           = ipv6_confirm,
+               .owner          = THIS_MODULE,
+               .pf             = PF_INET6,
+               .hooknum        = NF_IP6_LOCAL_IN,
+               .priority       = NF_IP6_PRI_LAST-1,
+       },
 };
 
 #ifdef CONFIG_SYSCTL
@@ -470,16 +464,21 @@ extern struct nf_conntrack_protocol nf_conntrack_protocol_udp6;
 extern struct nf_conntrack_protocol nf_conntrack_protocol_icmpv6;
 extern int nf_ct_frag6_init(void);
 extern void nf_ct_frag6_cleanup(void);
-static int init_or_cleanup(int init)
+
+MODULE_ALIAS("nf_conntrack-" __stringify(AF_INET6));
+MODULE_LICENSE("GPL");
+MODULE_AUTHOR("Yasuyuki KOZAKAI @USAGI <yasuyuki.kozakai@toshiba.co.jp>");
+
+static int __init nf_conntrack_l3proto_ipv6_init(void)
 {
        int ret = 0;
 
-       if (!init) goto cleanup;
+       need_conntrack();
 
        ret = nf_ct_frag6_init();
        if (ret < 0) {
                printk("nf_conntrack_ipv6: can't initialize frag6.\n");
-               goto cleanup_nothing;
+               return ret;
        }
        ret = nf_conntrack_protocol_register(&nf_conntrack_protocol_tcp6);
        if (ret < 0) {
@@ -505,71 +504,27 @@ static int init_or_cleanup(int init)
                goto cleanup_icmpv6;
        }
 
-       ret = nf_register_hook(&ipv6_conntrack_defrag_ops);
+       ret = nf_register_hooks(ipv6_conntrack_ops,
+                               ARRAY_SIZE(ipv6_conntrack_ops));
        if (ret < 0) {
                printk("nf_conntrack_ipv6: can't register pre-routing defrag "
                       "hook.\n");
                goto cleanup_ipv6;
        }
-
-       ret = nf_register_hook(&ipv6_conntrack_defrag_local_out_ops);
-       if (ret < 0) {
-               printk("nf_conntrack_ipv6: can't register local_out defrag "
-                      "hook.\n");
-               goto cleanup_defragops;
-       }
-
-       ret = nf_register_hook(&ipv6_conntrack_in_ops);
-       if (ret < 0) {
-               printk("nf_conntrack_ipv6: can't register pre-routing hook.\n");
-               goto cleanup_defraglocalops;
-       }
-
-       ret = nf_register_hook(&ipv6_conntrack_local_out_ops);
-       if (ret < 0) {
-               printk("nf_conntrack_ipv6: can't register local out hook.\n");
-               goto cleanup_inops;
-       }
-
-       ret = nf_register_hook(&ipv6_conntrack_out_ops);
-       if (ret < 0) {
-               printk("nf_conntrack_ipv6: can't register post-routing hook.\n");
-               goto cleanup_inandlocalops;
-       }
-
-       ret = nf_register_hook(&ipv6_conntrack_local_in_ops);
-       if (ret < 0) {
-               printk("nf_conntrack_ipv6: can't register local in hook.\n");
-               goto cleanup_inoutandlocalops;
-       }
-
 #ifdef CONFIG_SYSCTL
        nf_ct_ipv6_sysctl_header = register_sysctl_table(nf_ct_net_table, 0);
        if (nf_ct_ipv6_sysctl_header == NULL) {
                printk("nf_conntrack: can't register to sysctl.\n");
                ret = -ENOMEM;
-               goto cleanup_localinops;
+               goto cleanup_hooks;
        }
 #endif
        return ret;
 
- cleanup:
-       synchronize_net();
 #ifdef CONFIG_SYSCTL
-       unregister_sysctl_table(nf_ct_ipv6_sysctl_header);
- cleanup_localinops:
+ cleanup_hooks:
+       nf_unregister_hooks(ipv6_conntrack_ops, ARRAY_SIZE(ipv6_conntrack_ops));
 #endif
-       nf_unregister_hook(&ipv6_conntrack_local_in_ops);
- cleanup_inoutandlocalops:
-       nf_unregister_hook(&ipv6_conntrack_out_ops);
- cleanup_inandlocalops:
-       nf_unregister_hook(&ipv6_conntrack_local_out_ops);
- cleanup_inops:
-       nf_unregister_hook(&ipv6_conntrack_in_ops);
- cleanup_defraglocalops:
-       nf_unregister_hook(&ipv6_conntrack_defrag_local_out_ops);
- cleanup_defragops:
-       nf_unregister_hook(&ipv6_conntrack_defrag_ops);
  cleanup_ipv6:
        nf_conntrack_l3proto_unregister(&nf_conntrack_l3proto_ipv6);
  cleanup_icmpv6:
@@ -580,23 +535,21 @@ static int init_or_cleanup(int init)
        nf_conntrack_protocol_unregister(&nf_conntrack_protocol_tcp6);
  cleanup_frag6:
        nf_ct_frag6_cleanup();
- cleanup_nothing:
        return ret;
 }
 
-MODULE_ALIAS("nf_conntrack-" __stringify(AF_INET6));
-MODULE_LICENSE("GPL");
-MODULE_AUTHOR("Yasuyuki KOZAKAI @USAGI <yasuyuki.kozakai@toshiba.co.jp>");
-
-static int __init nf_conntrack_l3proto_ipv6_init(void)
-{
-       need_conntrack();
-       return init_or_cleanup(1);
-}
-
 static void __exit nf_conntrack_l3proto_ipv6_fini(void)
 {
-       init_or_cleanup(0);
+       synchronize_net();
+#ifdef CONFIG_SYSCTL
+       unregister_sysctl_table(nf_ct_ipv6_sysctl_header);
+#endif
+       nf_unregister_hooks(ipv6_conntrack_ops, ARRAY_SIZE(ipv6_conntrack_ops));
+       nf_conntrack_l3proto_unregister(&nf_conntrack_l3proto_ipv6);
+       nf_conntrack_protocol_unregister(&nf_conntrack_protocol_icmpv6);
+       nf_conntrack_protocol_unregister(&nf_conntrack_protocol_udp6);
+       nf_conntrack_protocol_unregister(&nf_conntrack_protocol_tcp6);
+       nf_ct_frag6_cleanup();
 }
 
 module_init(nf_conntrack_l3proto_ipv6_init);
index 09945c333055291012340ba32fe6d19bb94bdef7..86c6703265d09b9cf976d95917e1ca2225a6274b 100644 (file)
@@ -233,21 +233,13 @@ icmpv6_error(struct sk_buff *skb, unsigned int dataoff,
                return -NF_ACCEPT;
        }
 
-       if (hooknum != NF_IP6_PRE_ROUTING)
-               goto skipped;
-
-       /* Ignore it if the checksum's bogus. */
-       if (csum_ipv6_magic(&skb->nh.ipv6h->saddr, &skb->nh.ipv6h->daddr,
-                           skb->len - dataoff, IPPROTO_ICMPV6,
-                           skb_checksum(skb, dataoff,
-                                        skb->len - dataoff, 0))) {
+       if (hooknum == NF_IP6_PRE_ROUTING &&
+           nf_ip6_checksum(skb, hooknum, dataoff, IPPROTO_ICMPV6)) {
                nf_log_packet(PF_INET6, 0, skb, NULL, NULL, NULL,
                              "nf_ct_icmpv6: ICMPv6 checksum failed\n");
                return -NF_ACCEPT;
        }
 
-skipped:
-
        /* is not error message ? */
        if (icmp6h->icmp6_type >= 128)
                return NF_ACCEPT;
index 4238b1ed886012a331b1c5dd16ddffa1ea2eaaae..779ddf77f4d41d0455d449ad2e4b4f8eeaf8f984 100644 (file)
@@ -38,7 +38,7 @@ static int fold_prot_inuse(struct proto *proto)
        int res = 0;
        int cpu;
 
-       for_each_cpu(cpu)
+       for_each_possible_cpu(cpu)
                res += proto->stats[cpu].inuse;
 
        return res;
@@ -140,7 +140,7 @@ fold_field(void *mib[], int offt)
         unsigned long res = 0;
         int i;
  
-        for_each_cpu(i) {
+        for_each_possible_cpu(i) {
                 res += *(((unsigned long *)per_cpu_ptr(mib[0], i)) + offt);
                 res += *(((unsigned long *)per_cpu_ptr(mib[1], i)) + offt);
         }
index b67a45fb93e9ddfa2f46fc460abb9974a55e6852..eef985e010ea7f85b06927d11fd181099825227f 100644 (file)
@@ -121,6 +121,10 @@ static __inline__ void fq_unlink(struct frag_queue *fq)
        write_unlock(&ip6_frag_lock);
 }
 
+/*
+ * callers should be careful not to use the hash value outside the ipfrag_lock
+ * as doing so could race with ipfrag_hash_rnd being recalculated.
+ */
 static unsigned int ip6qhashfn(u32 id, struct in6_addr *saddr,
                               struct in6_addr *daddr)
 {
@@ -324,15 +328,16 @@ out:
 /* Creation primitives. */
 
 
-static struct frag_queue *ip6_frag_intern(unsigned int hash,
-                                         struct frag_queue *fq_in)
+static struct frag_queue *ip6_frag_intern(struct frag_queue *fq_in)
 {
        struct frag_queue *fq;
+       unsigned int hash;
 #ifdef CONFIG_SMP
        struct hlist_node *n;
 #endif
 
        write_lock(&ip6_frag_lock);
+       hash = ip6qhashfn(fq_in->id, &fq_in->saddr, &fq_in->daddr);
 #ifdef CONFIG_SMP
        hlist_for_each_entry(fq, n, &ip6_frag_hash[hash], list) {
                if (fq->id == fq_in->id && 
@@ -362,7 +367,7 @@ static struct frag_queue *ip6_frag_intern(unsigned int hash,
 
 
 static struct frag_queue *
-ip6_frag_create(unsigned int hash, u32 id, struct in6_addr *src, struct in6_addr *dst)
+ip6_frag_create(u32 id, struct in6_addr *src, struct in6_addr *dst)
 {
        struct frag_queue *fq;
 
@@ -379,7 +384,7 @@ ip6_frag_create(unsigned int hash, u32 id, struct in6_addr *src, struct in6_addr
        spin_lock_init(&fq->lock);
        atomic_set(&fq->refcnt, 1);
 
-       return ip6_frag_intern(hash, fq);
+       return ip6_frag_intern(fq);
 
 oom:
        IP6_INC_STATS_BH(IPSTATS_MIB_REASMFAILS);
@@ -391,9 +396,10 @@ fq_find(u32 id, struct in6_addr *src, struct in6_addr *dst)
 {
        struct frag_queue *fq;
        struct hlist_node *n;
-       unsigned int hash = ip6qhashfn(id, src, dst);
+       unsigned int hash;
 
        read_lock(&ip6_frag_lock);
+       hash = ip6qhashfn(id, src, dst);
        hlist_for_each_entry(fq, n, &ip6_frag_hash[hash], list) {
                if (fq->id == id && 
                    ipv6_addr_equal(src, &fq->saddr) &&
@@ -405,7 +411,7 @@ fq_find(u32 id, struct in6_addr *src, struct in6_addr *dst)
        }
        read_unlock(&ip6_frag_lock);
 
-       return ip6_frag_create(hash, id, src, dst);
+       return ip6_frag_create(id, src, dst);
 }
 
 
index c2d3e17beae60cc1b2dcfdf4e4d46c7d57b12d05..6578c3080f47738fb1a2a4d35e4320c2c4d285a2 100644 (file)
@@ -397,7 +397,7 @@ static int ipip6_rcv(struct sk_buff *skb)
                return 0;
        }
 
-       icmp_send(skb, ICMP_DEST_UNREACH, ICMP_PROT_UNREACH, 0);
+       icmp_send(skb, ICMP_DEST_UNREACH, ICMP_PORT_UNREACH, 0);
        kfree_skb(skb);
        read_unlock(&ipip6_lock);
 out:
index 5659b52284bd55518960460d49a391a6f5ee8dac..0ef9a35798d13915eb158e54ee58800ca058168a 100644 (file)
  *             YOSHIFUJI Hideaki <yoshfuji@linux-ipv6.org>
  */
 
+#include <linux/icmpv6.h>
 #include <linux/init.h>
 #include <linux/module.h>
 #include <linux/mutex.h>
 #include <linux/netdevice.h>
 #include <linux/skbuff.h>
+#include <net/ipv6.h>
 #include <net/protocol.h>
 #include <net/xfrm.h>
 
@@ -87,10 +89,16 @@ static int tunnel6_rcv(struct sk_buff **pskb)
        struct sk_buff *skb = *pskb;
        struct xfrm6_tunnel *handler;
 
+       if (!pskb_may_pull(skb, sizeof(struct ipv6hdr)))
+               goto drop;
+
        for (handler = tunnel6_handlers; handler; handler = handler->next)
                if (!handler->handler(skb))
                        return 0;
 
+       icmpv6_send(skb, ICMPV6_DEST_UNREACH, ICMPV6_PORT_UNREACH, 0, skb->dev);
+
+drop:
        kfree_skb(skb);
        return 0;
 }
index 91cce8b2d7a5643b523c55b12758756a0d374aee..88c840f1beb678a373284799dc6f8a693fd89544 100644 (file)
@@ -191,16 +191,18 @@ error:
 static inline void
 _decode_session6(struct sk_buff *skb, struct flowi *fl)
 {
-       u16 offset = sizeof(struct ipv6hdr);
+       u16 offset = skb->h.raw - skb->nh.raw;
        struct ipv6hdr *hdr = skb->nh.ipv6h;
-       struct ipv6_opt_hdr *exthdr = (struct ipv6_opt_hdr*)(skb->nh.raw + offset);
-       u8 nexthdr = skb->nh.ipv6h->nexthdr;
+       struct ipv6_opt_hdr *exthdr;
+       u8 nexthdr = skb->nh.raw[IP6CB(skb)->nhoff];
 
        memset(fl, 0, sizeof(struct flowi));
        ipv6_addr_copy(&fl->fl6_dst, &hdr->daddr);
        ipv6_addr_copy(&fl->fl6_src, &hdr->saddr);
 
        while (pskb_may_pull(skb, skb->nh.raw + offset + 1 - skb->data)) {
+               exthdr = (struct ipv6_opt_hdr*)(skb->nh.raw + offset);
+
                switch (nexthdr) {
                case NEXTHDR_ROUTING:
                case NEXTHDR_HOP:
index 8f3addf0724c01658c8c46b96677f701c52197f8..d62e0f9b9da3edca21a8292bc321764aa1866187 100644 (file)
@@ -118,7 +118,8 @@ static inline int llc_fixup_skb(struct sk_buff *skb)
                u16 pdulen = eth_hdr(skb)->h_proto,
                    data_size = ntohs(pdulen) - llc_len;
 
-               skb_trim(skb, data_size);
+               if (unlikely(pskb_trim_rcsum(skb, data_size)))
+                       return 0;
        }
        return 1;
 }
index 1ceb1a6c254b81083ec7f50408b70ebbad017454..8455a32ea5c4df61e7cc8c78125f988e15b65cf3 100644 (file)
 
 #include "nf_internals.h"
 
+static DEFINE_SPINLOCK(afinfo_lock);
+
+struct nf_afinfo *nf_afinfo[NPROTO];
+EXPORT_SYMBOL(nf_afinfo);
+
+int nf_register_afinfo(struct nf_afinfo *afinfo)
+{
+       spin_lock(&afinfo_lock);
+       rcu_assign_pointer(nf_afinfo[afinfo->family], afinfo);
+       spin_unlock(&afinfo_lock);
+       return 0;
+}
+EXPORT_SYMBOL_GPL(nf_register_afinfo);
+
+void nf_unregister_afinfo(struct nf_afinfo *afinfo)
+{
+       spin_lock(&afinfo_lock);
+       rcu_assign_pointer(nf_afinfo[afinfo->family], NULL);
+       spin_unlock(&afinfo_lock);
+       synchronize_rcu();
+}
+EXPORT_SYMBOL_GPL(nf_unregister_afinfo);
+
 /* In this code, we can be waiting indefinitely for userspace to
  * service a packet if a hook returns NF_QUEUE.  We could keep a count
  * of skbuffs queued for userspace, and not deregister a hook unless
@@ -63,6 +86,34 @@ void nf_unregister_hook(struct nf_hook_ops *reg)
 }
 EXPORT_SYMBOL(nf_unregister_hook);
 
+int nf_register_hooks(struct nf_hook_ops *reg, unsigned int n)
+{
+       unsigned int i;
+       int err = 0;
+
+       for (i = 0; i < n; i++) {
+               err = nf_register_hook(&reg[i]);
+               if (err)
+                       goto err;
+       }
+       return err;
+
+err:
+       if (i > 0)
+               nf_unregister_hooks(reg, i);
+       return err;
+}
+EXPORT_SYMBOL(nf_register_hooks);
+
+void nf_unregister_hooks(struct nf_hook_ops *reg, unsigned int n)
+{
+       unsigned int i;
+
+       for (i = 0; i < n; i++)
+               nf_unregister_hook(&reg[i]);
+}
+EXPORT_SYMBOL(nf_unregister_hooks);
+
 unsigned int nf_iterate(struct list_head *head,
                        struct sk_buff **skb,
                        int hook,
index 56389c83557c6f791c0c01dfaa5f3088e489898c..e581190fb6c374ff691679e780dffeec6c213cd3 100644 (file)
@@ -146,7 +146,7 @@ static void nf_ct_event_cache_flush(void)
        struct nf_conntrack_ecache *ecache;
        int cpu;
 
-       for_each_cpu(cpu) {
+       for_each_possible_cpu(cpu) {
                ecache = &per_cpu(nf_conntrack_ecache, cpu);
                if (ecache->ct)
                        nf_ct_put(ecache->ct);
index 6492ed66fb3c6cb033d9db835cc0eac006ce8fa3..69899f27d26aad61b8eb09d5fd6d7a4118b0c10f 100644 (file)
@@ -799,8 +799,7 @@ static int tcp_error(struct sk_buff *skb,
                     unsigned int dataoff,
                     enum ip_conntrack_info *ctinfo,
                     int pf,
-                    unsigned int hooknum,
-                    int(*csum)(const struct sk_buff *,unsigned int))
+                    unsigned int hooknum)
 {
        struct tcphdr _tcph, *th;
        unsigned int tcplen = skb->len - dataoff;
@@ -830,9 +829,8 @@ static int tcp_error(struct sk_buff *skb,
         */
        /* FIXME: Source route IP option packets --RR */
        if (((pf == PF_INET && hooknum == NF_IP_PRE_ROUTING) ||
-            (pf == PF_INET6 && hooknum  == NF_IP6_PRE_ROUTING))
-           && skb->ip_summed != CHECKSUM_UNNECESSARY
-           && csum(skb, dataoff)) {
+            (pf == PF_INET6 && hooknum  == NF_IP6_PRE_ROUTING)) &&
+           nf_checksum(skb, hooknum, dataoff, IPPROTO_TCP, pf)) {
                if (LOG_INVALID(IPPROTO_TCP))
                        nf_log_packet(pf, 0, skb, NULL, NULL, NULL,
                                  "nf_ct_tcp: bad TCP checksum ");
@@ -851,44 +849,6 @@ static int tcp_error(struct sk_buff *skb,
        return NF_ACCEPT;
 }
 
-static int csum4(const struct sk_buff *skb, unsigned int dataoff)
-{
-       return csum_tcpudp_magic(skb->nh.iph->saddr, skb->nh.iph->daddr,
-                                skb->len - dataoff, IPPROTO_TCP,
-                                skb->ip_summed == CHECKSUM_HW ? skb->csum
-                                : skb_checksum(skb, dataoff,
-                                               skb->len - dataoff, 0));
-}
-
-static int csum6(const struct sk_buff *skb, unsigned int dataoff)
-{
-       return csum_ipv6_magic(&skb->nh.ipv6h->saddr, &skb->nh.ipv6h->daddr,
-                              skb->len - dataoff, IPPROTO_TCP,
-                              skb->ip_summed == CHECKSUM_HW
-                              ? csum_sub(skb->csum,
-                                         skb_checksum(skb, 0, dataoff, 0))
-                              : skb_checksum(skb, dataoff, skb->len - dataoff,
-                                             0));
-}
-
-static int tcp_error4(struct sk_buff *skb,
-                     unsigned int dataoff,
-                     enum ip_conntrack_info *ctinfo,
-                     int pf,
-                     unsigned int hooknum)
-{
-       return tcp_error(skb, dataoff, ctinfo, pf, hooknum, csum4);
-}
-
-static int tcp_error6(struct sk_buff *skb,
-                     unsigned int dataoff,
-                     enum ip_conntrack_info *ctinfo,
-                     int pf,
-                     unsigned int hooknum)
-{
-       return tcp_error(skb, dataoff, ctinfo, pf, hooknum, csum6);
-}
-
 /* Returns verdict for packet, or -1 for invalid. */
 static int tcp_packet(struct nf_conn *conntrack,
                      const struct sk_buff *skb,
@@ -1218,7 +1178,7 @@ struct nf_conntrack_protocol nf_conntrack_protocol_tcp4 =
        .print_conntrack        = tcp_print_conntrack,
        .packet                 = tcp_packet,
        .new                    = tcp_new,
-       .error                  = tcp_error4,
+       .error                  = tcp_error,
 #if defined(CONFIG_NF_CT_NETLINK) || \
     defined(CONFIG_NF_CT_NETLINK_MODULE)
        .to_nfattr              = tcp_to_nfattr,
@@ -1239,7 +1199,7 @@ struct nf_conntrack_protocol nf_conntrack_protocol_tcp6 =
        .print_conntrack        = tcp_print_conntrack,
        .packet                 = tcp_packet,
        .new                    = tcp_new,
-       .error                  = tcp_error6,
+       .error                  = tcp_error,
 #if defined(CONFIG_NF_CT_NETLINK) || \
     defined(CONFIG_NF_CT_NETLINK_MODULE)
        .to_nfattr              = tcp_to_nfattr,
index 831d206344e0176bf3987fc9d613cd8913dd4621..d93edbfde9e30a27c111fa0a540d4f82374f368b 100644 (file)
@@ -103,8 +103,7 @@ static int udp_new(struct nf_conn *conntrack, const struct sk_buff *skb,
 static int udp_error(struct sk_buff *skb, unsigned int dataoff,
                     enum ip_conntrack_info *ctinfo,
                     int pf,
-                    unsigned int hooknum,
-                    int (*csum)(const struct sk_buff *, unsigned int))
+                    unsigned int hooknum)
 {
        unsigned int udplen = skb->len - dataoff;
        struct udphdr _hdr, *hdr;
@@ -136,9 +135,8 @@ static int udp_error(struct sk_buff *skb, unsigned int dataoff,
         * and moreover root might send raw packets.
         * FIXME: Source route IP option packets --RR */
        if (((pf == PF_INET && hooknum == NF_IP_PRE_ROUTING) ||
-            (pf == PF_INET6 && hooknum == NF_IP6_PRE_ROUTING))
-           && skb->ip_summed != CHECKSUM_UNNECESSARY
-           && csum(skb, dataoff)) {
+            (pf == PF_INET6 && hooknum == NF_IP6_PRE_ROUTING)) &&
+           nf_checksum(skb, hooknum, dataoff, IPPROTO_UDP, pf)) {
                if (LOG_INVALID(IPPROTO_UDP))
                        nf_log_packet(pf, 0, skb, NULL, NULL, NULL,
                                "nf_ct_udp: bad UDP checksum ");
@@ -148,44 +146,6 @@ static int udp_error(struct sk_buff *skb, unsigned int dataoff,
        return NF_ACCEPT;
 }
 
-static int csum4(const struct sk_buff *skb, unsigned int dataoff)
-{
-       return csum_tcpudp_magic(skb->nh.iph->saddr, skb->nh.iph->daddr,
-                                skb->len - dataoff, IPPROTO_UDP,
-                                skb->ip_summed == CHECKSUM_HW ? skb->csum
-                                : skb_checksum(skb, dataoff,
-                                               skb->len - dataoff, 0));
-}
-
-static int csum6(const struct sk_buff *skb, unsigned int dataoff)
-{
-       return csum_ipv6_magic(&skb->nh.ipv6h->saddr, &skb->nh.ipv6h->daddr,
-                              skb->len - dataoff, IPPROTO_UDP,
-                              skb->ip_summed == CHECKSUM_HW
-                              ? csum_sub(skb->csum,
-                                         skb_checksum(skb, 0, dataoff, 0))
-                              : skb_checksum(skb, dataoff, skb->len - dataoff,
-                                             0));
-}
-
-static int udp_error4(struct sk_buff *skb,
-                     unsigned int dataoff,
-                     enum ip_conntrack_info *ctinfo,
-                     int pf,
-                     unsigned int hooknum)
-{
-       return udp_error(skb, dataoff, ctinfo, pf, hooknum, csum4);
-}
-
-static int udp_error6(struct sk_buff *skb,
-                     unsigned int dataoff,
-                     enum ip_conntrack_info *ctinfo,
-                     int pf,
-                     unsigned int hooknum)
-{
-       return udp_error(skb, dataoff, ctinfo, pf, hooknum, csum6);
-}
-
 struct nf_conntrack_protocol nf_conntrack_protocol_udp4 =
 {
        .l3proto                = PF_INET,
@@ -197,7 +157,7 @@ struct nf_conntrack_protocol nf_conntrack_protocol_udp4 =
        .print_conntrack        = udp_print_conntrack,
        .packet                 = udp_packet,
        .new                    = udp_new,
-       .error                  = udp_error4,
+       .error                  = udp_error,
 #if defined(CONFIG_NF_CT_NETLINK) || \
     defined(CONFIG_NF_CT_NETLINK_MODULE)
        .tuple_to_nfattr        = nf_ct_port_tuple_to_nfattr,
@@ -216,7 +176,7 @@ struct nf_conntrack_protocol nf_conntrack_protocol_udp6 =
        .print_conntrack        = udp_print_conntrack,
        .packet                 = udp_packet,
        .new                    = udp_new,
-       .error                  = udp_error6,
+       .error                  = udp_error,
 #if defined(CONFIG_NF_CT_NETLINK) || \
     defined(CONFIG_NF_CT_NETLINK_MODULE)
        .tuple_to_nfattr        = nf_ct_port_tuple_to_nfattr,
index c72aa3cd22e4a97b9880bd5b3e09bca594ceb9cb..408960c6a544489b2d269ed7a4809895b43fe440 100644 (file)
@@ -649,63 +649,6 @@ static ctl_table nf_ct_net_table[] = {
 EXPORT_SYMBOL(nf_ct_log_invalid);
 #endif /* CONFIG_SYSCTL */
 
-static int init_or_cleanup(int init)
-{
-#ifdef CONFIG_PROC_FS
-       struct proc_dir_entry *proc, *proc_exp, *proc_stat;
-#endif
-       int ret = 0;
-
-       if (!init) goto cleanup;
-
-       ret = nf_conntrack_init();
-       if (ret < 0)
-               goto cleanup_nothing;
-
-#ifdef CONFIG_PROC_FS
-       proc = proc_net_fops_create("nf_conntrack", 0440, &ct_file_ops);
-       if (!proc) goto cleanup_init;
-
-       proc_exp = proc_net_fops_create("nf_conntrack_expect", 0440,
-                                       &exp_file_ops);
-       if (!proc_exp) goto cleanup_proc;
-
-       proc_stat = create_proc_entry("nf_conntrack", S_IRUGO, proc_net_stat);
-       if (!proc_stat)
-               goto cleanup_proc_exp;
-
-       proc_stat->proc_fops = &ct_cpu_seq_fops;
-       proc_stat->owner = THIS_MODULE;
-#endif
-#ifdef CONFIG_SYSCTL
-       nf_ct_sysctl_header = register_sysctl_table(nf_ct_net_table, 0);
-       if (nf_ct_sysctl_header == NULL) {
-               printk("nf_conntrack: can't register to sysctl.\n");
-               ret = -ENOMEM;
-               goto cleanup_proc_stat;
-       }
-#endif
-
-       return ret;
-
- cleanup:
-#ifdef CONFIG_SYSCTL
-       unregister_sysctl_table(nf_ct_sysctl_header);
- cleanup_proc_stat:
-#endif
-#ifdef CONFIG_PROC_FS
-       remove_proc_entry("nf_conntrack", proc_net_stat);
- cleanup_proc_exp:
-       proc_net_remove("nf_conntrack_expect");
- cleanup_proc:
-       proc_net_remove("nf_conntrack");
- cleanup_init:
-#endif /* CNFIG_PROC_FS */
-       nf_conntrack_cleanup();
- cleanup_nothing:
-       return ret;
-}
-
 int nf_conntrack_l3proto_register(struct nf_conntrack_l3proto *proto)
 {
        int ret = 0;
@@ -808,12 +751,66 @@ void nf_conntrack_protocol_unregister(struct nf_conntrack_protocol *proto)
 
 static int __init nf_conntrack_standalone_init(void)
 {
-       return init_or_cleanup(1);
+#ifdef CONFIG_PROC_FS
+       struct proc_dir_entry *proc, *proc_exp, *proc_stat;
+#endif
+       int ret = 0;
+
+       ret = nf_conntrack_init();
+       if (ret < 0)
+               return ret;
+
+#ifdef CONFIG_PROC_FS
+       proc = proc_net_fops_create("nf_conntrack", 0440, &ct_file_ops);
+       if (!proc) goto cleanup_init;
+
+       proc_exp = proc_net_fops_create("nf_conntrack_expect", 0440,
+                                       &exp_file_ops);
+       if (!proc_exp) goto cleanup_proc;
+
+       proc_stat = create_proc_entry("nf_conntrack", S_IRUGO, proc_net_stat);
+       if (!proc_stat)
+               goto cleanup_proc_exp;
+
+       proc_stat->proc_fops = &ct_cpu_seq_fops;
+       proc_stat->owner = THIS_MODULE;
+#endif
+#ifdef CONFIG_SYSCTL
+       nf_ct_sysctl_header = register_sysctl_table(nf_ct_net_table, 0);
+       if (nf_ct_sysctl_header == NULL) {
+               printk("nf_conntrack: can't register to sysctl.\n");
+               ret = -ENOMEM;
+               goto cleanup_proc_stat;
+       }
+#endif
+       return ret;
+
+#ifdef CONFIG_SYSCTL
+ cleanup_proc_stat:
+#endif
+#ifdef CONFIG_PROC_FS
+       remove_proc_entry("nf_conntrack", proc_net_stat);
+ cleanup_proc_exp:
+       proc_net_remove("nf_conntrack_expect");
+ cleanup_proc:
+       proc_net_remove("nf_conntrack");
+ cleanup_init:
+#endif /* CNFIG_PROC_FS */
+       nf_conntrack_cleanup();
+       return ret;
 }
 
 static void __exit nf_conntrack_standalone_fini(void)
 {
-       init_or_cleanup(0);
+#ifdef CONFIG_SYSCTL
+       unregister_sysctl_table(nf_ct_sysctl_header);
+#endif
+#ifdef CONFIG_PROC_FS
+       remove_proc_entry("nf_conntrack", proc_net_stat);
+       proc_net_remove("nf_conntrack_expect");
+       proc_net_remove("nf_conntrack");
+#endif /* CNFIG_PROC_FS */
+       nf_conntrack_cleanup();
 }
 
 module_init(nf_conntrack_standalone_init);
index d9f0d7ef103b61f8209eaa9fd9aaa29306438309..ee8f70889f47d752b422b4eb01798c9e99266c7a 100644 (file)
@@ -17,7 +17,6 @@
  * for queueing and must reinject all packets it receives, no matter what.
  */
 static struct nf_queue_handler *queue_handler[NPROTO];
-static struct nf_queue_rerouter *queue_rerouter[NPROTO];
 
 static DEFINE_RWLOCK(queue_handler_lock);
 
@@ -59,32 +58,6 @@ int nf_unregister_queue_handler(int pf)
 }
 EXPORT_SYMBOL(nf_unregister_queue_handler);
 
-int nf_register_queue_rerouter(int pf, struct nf_queue_rerouter *rer)
-{
-       if (pf >= NPROTO)
-               return -EINVAL;
-
-       write_lock_bh(&queue_handler_lock);
-       rcu_assign_pointer(queue_rerouter[pf], rer);
-       write_unlock_bh(&queue_handler_lock);
-
-       return 0;
-}
-EXPORT_SYMBOL_GPL(nf_register_queue_rerouter);
-
-int nf_unregister_queue_rerouter(int pf)
-{
-       if (pf >= NPROTO)
-               return -EINVAL;
-
-       write_lock_bh(&queue_handler_lock);
-       rcu_assign_pointer(queue_rerouter[pf], NULL);
-       write_unlock_bh(&queue_handler_lock);
-       synchronize_rcu();
-       return 0;
-}
-EXPORT_SYMBOL_GPL(nf_unregister_queue_rerouter);
-
 void nf_unregister_queue_handlers(struct nf_queue_handler *qh)
 {
        int pf;
@@ -116,7 +89,7 @@ int nf_queue(struct sk_buff **skb,
        struct net_device *physindev = NULL;
        struct net_device *physoutdev = NULL;
 #endif
-       struct nf_queue_rerouter *rerouter;
+       struct nf_afinfo *afinfo;
 
        /* QUEUE == DROP if noone is waiting, to be safe. */
        read_lock(&queue_handler_lock);
@@ -126,7 +99,14 @@ int nf_queue(struct sk_buff **skb,
                return 1;
        }
 
-       info = kmalloc(sizeof(*info)+queue_rerouter[pf]->rer_size, GFP_ATOMIC);
+       afinfo = nf_get_afinfo(pf);
+       if (!afinfo) {
+               read_unlock(&queue_handler_lock);
+               kfree_skb(*skb);
+               return 1;
+       }
+
+       info = kmalloc(sizeof(*info) + afinfo->route_key_size, GFP_ATOMIC);
        if (!info) {
                if (net_ratelimit())
                        printk(KERN_ERR "OOM queueing packet %p\n",
@@ -158,10 +138,7 @@ int nf_queue(struct sk_buff **skb,
                if (physoutdev) dev_hold(physoutdev);
        }
 #endif
-       rerouter = rcu_dereference(queue_rerouter[pf]);
-       if (rerouter)
-               rerouter->save(*skb, info);
-
+       afinfo->saveroute(*skb, info);
        status = queue_handler[pf]->outfn(*skb, info, queuenum,
                                          queue_handler[pf]->data);
 
@@ -190,7 +167,7 @@ void nf_reinject(struct sk_buff *skb, struct nf_info *info,
 {
        struct list_head *elem = &info->elem->list;
        struct list_head *i;
-       struct nf_queue_rerouter *rerouter;
+       struct nf_afinfo *afinfo;
 
        rcu_read_lock();
 
@@ -228,8 +205,8 @@ void nf_reinject(struct sk_buff *skb, struct nf_info *info,
        }
 
        if (verdict == NF_ACCEPT) {
-               rerouter = rcu_dereference(queue_rerouter[info->pf]);
-               if (rerouter && rerouter->reroute(&skb, info) < 0)
+               afinfo = nf_get_afinfo(info->pf);
+               if (!afinfo || afinfo->reroute(&skb, info) < 0)
                        verdict = NF_DROP;
        }
 
index 3e3f5448bacb911437403b441d2df19e92ee8fb8..c60273cad778ed1c3cdc7eda166aafc6b21d9802 100644 (file)
@@ -1033,17 +1033,13 @@ static struct file_operations nful_file_ops = {
 
 #endif /* PROC_FS */
 
-static int
-init_or_cleanup(int init)
+static int __init nfnetlink_log_init(void)
 {
        int i, status = -ENOMEM;
 #ifdef CONFIG_PROC_FS
        struct proc_dir_entry *proc_nful;
 #endif
        
-       if (!init)
-               goto cleanup;
-
        for (i = 0; i < INSTANCE_BUCKETS; i++)
                INIT_HLIST_HEAD(&instance_table[i]);
        
@@ -1066,30 +1062,25 @@ init_or_cleanup(int init)
                goto cleanup_subsys;
        proc_nful->proc_fops = &nful_file_ops;
 #endif
-
        return status;
 
-cleanup:
-       nf_log_unregister_logger(&nfulnl_logger);
 #ifdef CONFIG_PROC_FS
-       remove_proc_entry("nfnetlink_log", proc_net_netfilter);
 cleanup_subsys:
-#endif
        nfnetlink_subsys_unregister(&nfulnl_subsys);
+#endif
 cleanup_netlink_notifier:
        netlink_unregister_notifier(&nfulnl_rtnl_notifier);
        return status;
 }
 
-static int __init nfnetlink_log_init(void)
-{
-       
-       return init_or_cleanup(1);
-}
-
 static void __exit nfnetlink_log_fini(void)
 {
-       init_or_cleanup(0);
+       nf_log_unregister_logger(&nfulnl_logger);
+#ifdef CONFIG_PROC_FS
+       remove_proc_entry("nfnetlink_log", proc_net_netfilter);
+#endif
+       nfnetlink_subsys_unregister(&nfulnl_subsys);
+       netlink_unregister_notifier(&nfulnl_rtnl_notifier);
 }
 
 MODULE_DESCRIPTION("netfilter userspace logging");
index d0e62f68139fefc3aa05b4086650645f9cff0b23..86a4ac33de3495791e5e465a5352afe79690c3cf 100644 (file)
@@ -1071,17 +1071,13 @@ static struct file_operations nfqnl_file_ops = {
 
 #endif /* PROC_FS */
 
-static int
-init_or_cleanup(int init)
+static int __init nfnetlink_queue_init(void)
 {
        int i, status = -ENOMEM;
 #ifdef CONFIG_PROC_FS
        struct proc_dir_entry *proc_nfqueue;
 #endif
        
-       if (!init)
-               goto cleanup;
-
        for (i = 0; i < INSTANCE_BUCKETS; i++)
                INIT_HLIST_HEAD(&instance_table[i]);
 
@@ -1101,31 +1097,26 @@ init_or_cleanup(int init)
 #endif
 
        register_netdevice_notifier(&nfqnl_dev_notifier);
-
        return status;
 
-cleanup:
-       nf_unregister_queue_handlers(&nfqh);
-       unregister_netdevice_notifier(&nfqnl_dev_notifier);
 #ifdef CONFIG_PROC_FS
-       remove_proc_entry("nfnetlink_queue", proc_net_netfilter);
 cleanup_subsys:
-#endif 
        nfnetlink_subsys_unregister(&nfqnl_subsys);
+#endif
 cleanup_netlink_notifier:
        netlink_unregister_notifier(&nfqnl_rtnl_notifier);
        return status;
 }
 
-static int __init nfnetlink_queue_init(void)
-{
-       
-       return init_or_cleanup(1);
-}
-
 static void __exit nfnetlink_queue_fini(void)
 {
-       init_or_cleanup(0);
+       nf_unregister_queue_handlers(&nfqh);
+       unregister_netdevice_notifier(&nfqnl_dev_notifier);
+#ifdef CONFIG_PROC_FS
+       remove_proc_entry("nfnetlink_queue", proc_net_netfilter);
+#endif
+       nfnetlink_subsys_unregister(&nfqnl_subsys);
+       netlink_unregister_notifier(&nfqnl_rtnl_notifier);
 }
 
 MODULE_DESCRIPTION("netfilter packet queue handler");
index feb8a9e066b08939f4988f23d3001b859ef31b3b..00cf0a4f4d92ab3a54ca6b503a83d7312efd74cb 100644 (file)
@@ -413,7 +413,7 @@ struct xt_table_info *xt_alloc_table_info(unsigned int size)
 
        newinfo->size = size;
 
-       for_each_cpu(cpu) {
+       for_each_possible_cpu(cpu) {
                if (size <= PAGE_SIZE)
                        newinfo->entries[cpu] = kmalloc_node(size,
                                                        GFP_KERNEL,
@@ -436,7 +436,7 @@ void xt_free_table_info(struct xt_table_info *info)
 {
        int cpu;
 
-       for_each_cpu(cpu) {
+       for_each_possible_cpu(cpu) {
                if (info->size <= PAGE_SIZE)
                        kfree(info->entries[cpu]);
                else
index fa877f8f652cb223bf907ffc4b55d99d98ebb75d..24c348fa89222b3c8d11d5b4db2938d82f3d7ad6 100644 (file)
@@ -66,7 +66,7 @@ static __inline__ struct tcf_police * tcf_police_lookup(u32 index)
 }
 
 #ifdef CONFIG_NET_CLS_ACT
-static int tcf_generic_walker(struct sk_buff *skb, struct netlink_callback *cb,
+static int tcf_act_police_walker(struct sk_buff *skb, struct netlink_callback *cb,
                               int type, struct tc_action *a)
 {
        struct tcf_police *p;
@@ -113,7 +113,7 @@ rtattr_failure:
 }
 
 static inline int
-tcf_hash_search(struct tc_action *a, u32 index)
+tcf_act_police_hash_search(struct tc_action *a, u32 index)
 {
        struct tcf_police *p = tcf_police_lookup(index);
 
@@ -387,9 +387,9 @@ static struct tc_action_ops act_police_ops = {
        .act            =       tcf_act_police,
        .dump           =       tcf_act_police_dump,
        .cleanup        =       tcf_act_police_cleanup,
-       .lookup         =       tcf_hash_search,
+       .lookup         =       tcf_act_police_hash_search,
        .init           =       tcf_act_police_locate,
-       .walk           =       tcf_generic_walker
+       .walk           =       tcf_act_police_walker
 };
 
 static int __init
index d47a52c303a81da44da5f8d8c478f77049e69483..5b3b0e0ae7e506391d22882ec0d7a91a1411800b 100644 (file)
@@ -69,7 +69,7 @@ fold_field(void *mib[], int nr)
        unsigned long res = 0;
        int i;
 
-       for_each_cpu(i) {
+       for_each_possible_cpu(i) {
                res +=
                    *((unsigned long *) (((void *) per_cpu_ptr(mib[0], i)) +
                                         sizeof (unsigned long) * nr));
index b807f360e02ccc336ad45f606feb92506b21af77..0ce12dfc7a71651cd1d3c49f8d7881da14a02020 100644 (file)
@@ -119,10 +119,6 @@ static ssize_t sock_writev(struct file *file, const struct iovec *vector,
 static ssize_t sock_sendpage(struct file *file, struct page *page,
                             int offset, size_t size, loff_t *ppos, int more);
 
-extern ssize_t generic_splice_sendpage(struct inode *inode, struct file *out,
-                               size_t len, unsigned int flags);
-
-
 /*
  *     Socket files have a set of 'special' operations as well as the generic file ones. These don't appear
  *     in the operation structures but are done directly via the socketcall() multiplexor.
@@ -494,6 +490,7 @@ static struct socket *sockfd_lookup_light(int fd, int *err, int *fput_needed)
        struct file *file;
        struct socket *sock;
 
+       *err = -EBADF;
        file = fget_light(fd, fput_needed);
        if (file) {
                sock = sock_from_file(file, err);
@@ -2136,7 +2133,7 @@ void socket_seq_show(struct seq_file *seq)
        int cpu;
        int counter = 0;
 
-       for_each_cpu(cpu)
+       for_each_possible_cpu(cpu)
                counter += per_cpu(sockets_in_use, cpu);
 
        /* It can be negative, by the way. 8) */
index 900ef31f5a0e601bd7f0a4cfc9fbfea06584c3c4..519ebc17c02845a762102c00b35efb6f01b73b46 100644 (file)
@@ -794,7 +794,6 @@ gss_create_cred(struct rpc_auth *auth, struct auth_cred *acred, int flags)
 
 out_err:
        dprintk("RPC:      gss_create_cred failed with error %d\n", err);
-       if (cred) gss_destroy_cred(&cred->gc_base);
        return ERR_PTR(err);
 }
 
index 97c981fa6b8ee4a48118cf46801e1fef60388b23..76b969e6904fdca3607845a050c331376845b180 100644 (file)
@@ -212,7 +212,6 @@ make_checksum(s32 cksumtype, char *header, int hdrlen, struct xdr_buf *body,
        char                            *cksumname;
        struct crypto_tfm               *tfm = NULL; /* XXX add to ctx? */
        struct scatterlist              sg[1];
-       u32                             code = GSS_S_FAILURE;
 
        switch (cksumtype) {
                case CKSUMTYPE_RSA_MD5:
@@ -221,13 +220,11 @@ make_checksum(s32 cksumtype, char *header, int hdrlen, struct xdr_buf *body,
                default:
                        dprintk("RPC:      krb5_make_checksum:"
                                " unsupported checksum %d", cksumtype);
-                       goto out;
+                       return GSS_S_FAILURE;
        }
        if (!(tfm = crypto_alloc_tfm(cksumname, CRYPTO_TFM_REQ_MAY_SLEEP)))
-               goto out;
+               return GSS_S_FAILURE;
        cksum->len = crypto_tfm_alg_digestsize(tfm);
-       if ((cksum->data = kmalloc(cksum->len, GFP_KERNEL)) == NULL)
-               goto out;
 
        crypto_digest_init(tfm);
        sg_set_buf(sg, header, hdrlen);
@@ -235,10 +232,8 @@ make_checksum(s32 cksumtype, char *header, int hdrlen, struct xdr_buf *body,
        process_xdr_buf(body, body_offset, body->len - body_offset,
                        checksummer, tfm);
        crypto_digest_final(tfm, cksum->data);
-       code = 0;
-out:
        crypto_free_tfm(tfm);
-       return code;
+       return 0;
 }
 
 EXPORT_SYMBOL(make_checksum);
index 4d7eb9e704da65be7b9146ed61ba6810991b78ae..d51e316c5821022690a88d93eadcf28b9ea31597 100644 (file)
@@ -1122,18 +1122,20 @@ svcauth_gss_release(struct svc_rqst *rqstp)
                                        integ_len))
                        BUG();
                if (resbuf->page_len == 0
-                       && resbuf->tail[0].iov_len + RPC_MAX_AUTH_SIZE
+                       && resbuf->head[0].iov_len + RPC_MAX_AUTH_SIZE
                                < PAGE_SIZE) {
                        BUG_ON(resbuf->tail[0].iov_len);
                        /* Use head for everything */
                        resv = &resbuf->head[0];
                } else if (resbuf->tail[0].iov_base == NULL) {
-                       /* copied from nfsd4_encode_read */
-                       svc_take_page(rqstp);
-                       resbuf->tail[0].iov_base = page_address(rqstp
-                                       ->rq_respages[rqstp->rq_resused-1]);
-                       rqstp->rq_restailpage = rqstp->rq_resused-1;
+                       if (resbuf->head[0].iov_len + RPC_MAX_AUTH_SIZE
+                                       > PAGE_SIZE)
+                               goto out_err;
+                       resbuf->tail[0].iov_base =
+                               resbuf->head[0].iov_base
+                               + resbuf->head[0].iov_len;
                        resbuf->tail[0].iov_len = 0;
+                       rqstp->rq_restailpage = 0;
                        resv = &resbuf->tail[0];
                } else {
                        resv = &resbuf->tail[0];
index dea529666d6991077aa69deaecad2818033def0c..15c2db26767bc5e5b6848d904078c9b0975dcfa4 100644 (file)
@@ -176,7 +176,8 @@ void rpc_count_iostats(struct rpc_task *task)
        op_metrics->om_execute += execute;
 }
 
-void _print_name(struct seq_file *seq, unsigned int op, struct rpc_procinfo *procs)
+static void _print_name(struct seq_file *seq, unsigned int op,
+                       struct rpc_procinfo *procs)
 {
        if (procs[op].p_name)
                seq_printf(seq, "\t%12s: ", procs[op].p_name);
index 953307a9df1d852c3eac546d9e1d97e728f0df3e..a3bbc891f95997bf7e186607214aedddc7c1d454 100644 (file)
@@ -229,8 +229,7 @@ static void node_is_down(struct publication *publ)
                                     publ->node, publ->ref, publ->key);
         assert(p == publ);
        write_unlock_bh(&tipc_nametbl_lock);
-       if (publ)
-               kfree(publ);
+       kfree(publ);
 }
 
 /**
index 8b9bf4a763b55408e3449aa6a0aa4c2a6d80be4d..b1265187b4a8f8cfe4c55ec5aa3f36742f30c917 100644 (file)
 #include <asm/uaccess.h>
 #include <linux/module.h>
 #include <linux/init.h>
-#include <linux/wanpipe.h>
 #include <linux/if_wanpipe.h>
 #include <linux/pkt_sched.h>
 #include <linux/tcp_states.h>
 #include <linux/if_wanpipe_common.h>
-#include <linux/sdla_x25.h>
 
 #ifdef CONFIG_INET
 #include <net/inet_common.h>
index a8e14dc1b04ee726e0ccb047dec04d30fa06756d..3dc3e1f3b7aae687346e4f9f8ff8926d658b65d0 100644 (file)
@@ -805,16 +805,22 @@ void xfrm_replay_notify(struct xfrm_state *x, int event)
        case XFRM_REPLAY_UPDATE:
                if (x->replay_maxdiff &&
                    (x->replay.seq - x->preplay.seq < x->replay_maxdiff) &&
-                   (x->replay.oseq - x->preplay.oseq < x->replay_maxdiff))
-                       return;
+                   (x->replay.oseq - x->preplay.oseq < x->replay_maxdiff)) {
+                       if (x->xflags & XFRM_TIME_DEFER)
+                               event = XFRM_REPLAY_TIMEOUT;
+                       else
+                               return;
+               }
 
                break;
 
        case XFRM_REPLAY_TIMEOUT:
                if ((x->replay.seq == x->preplay.seq) &&
                    (x->replay.bitmap == x->preplay.bitmap) &&
-                   (x->replay.oseq == x->preplay.oseq))
+                   (x->replay.oseq == x->preplay.oseq)) {
+                       x->xflags |= XFRM_TIME_DEFER;
                        return;
+               }
 
                break;
        }
@@ -825,8 +831,10 @@ void xfrm_replay_notify(struct xfrm_state *x, int event)
        km_state_notify(x, &c);
 
        if (x->replay_maxage &&
-           !mod_timer(&x->rtimer, jiffies + x->replay_maxage))
+           !mod_timer(&x->rtimer, jiffies + x->replay_maxage)) {
                xfrm_state_hold(x);
+               x->xflags &= ~XFRM_TIME_DEFER;
+       }
 }
 EXPORT_SYMBOL(xfrm_replay_notify);
 
@@ -836,10 +844,15 @@ static void xfrm_replay_timer_handler(unsigned long data)
 
        spin_lock(&x->lock);
 
-       if (xfrm_aevent_is_on() && x->km.state == XFRM_STATE_VALID)
-               xfrm_replay_notify(x, XFRM_REPLAY_TIMEOUT);
+       if (x->km.state == XFRM_STATE_VALID) {
+               if (xfrm_aevent_is_on())
+                       xfrm_replay_notify(x, XFRM_REPLAY_TIMEOUT);
+               else
+                       x->xflags |= XFRM_TIME_DEFER;
+       }
 
        spin_unlock(&x->lock);
+       xfrm_state_put(x);
 }
 
 int xfrm_replay_check(struct xfrm_state *x, u32 seq)
index 59620b1554e022a316daa7185a0cf17a02fe6e3d..b0d067be739056089fbb09a357bbacc5c0daf6b4 100644 (file)
@@ -87,6 +87,11 @@ cc-ifversion = $(shell if [ $(call cc-version, $(CC)) $(1) $(2) ]; then \
 # $(Q)$(MAKE) $(build)=dir
 build := -f $(if $(KBUILD_SRC),$(srctree)/)scripts/Makefile.build obj
 
+# Prefix -I with $(srctree) if it is not an absolute path
+addtree = $(if $(filter-out -I/%,$(1)),$(patsubst -I%,-I$(srctree)/%,$(1))) $(1)
+# Find all -I options and call addtree
+flags = $(foreach o,$($(1)),$(if $(filter -I%,$(o)),$(call addtree,$(o)),$(o)))
+
 # If quiet is set, only print short version of command
 cmd = @$(echo-cmd) $(cmd_$(1))
 
index 550798f57da5028401f05f67f9e483c6e6a2beda..2cb4935e85d1b0a8d3638783a8bd964489f984c1 100644 (file)
@@ -99,11 +99,6 @@ __a_flags    = $(_a_flags)
 __cpp_flags     = $(_cpp_flags)
 else
 
-# Prefix -I with $(srctree) if it is not an absolute path
-addtree = $(if $(filter-out -I/%,$(1)),$(patsubst -I%,-I$(srctree)/%,$(1))) $(1)
-# Find all -I options and call addtree
-flags = $(foreach o,$($(1)),$(if $(filter -I%,$(o)),$(call addtree,$(o)),$(o)))
-
 # -I$(obj) locates generated .h files
 # $(call addtree,-I$(obj)) locates .h files in srctree, from generated .c files
 #   and locates generated .h files
old mode 100644 (file)
new mode 100755 (executable)
old mode 100644 (file)
new mode 100755 (executable)
index 6d411169bfa62be23a244e2bf8f1a110c1936715..56b3bed1108f4132b297eee6dbc5255ce81d028c 100644 (file)
@@ -1,22 +1,55 @@
 #!/bin/bash
 # Copyright (C) Martin Schlemmer <azarah@nosferatu.za.org>
-# Released under the terms of the GNU GPL
-#
-# Generate a newline separated list of entries from the file/directory
-# supplied as an argument.
-#
-# If a file/directory is not supplied then generate a small dummy file.
+# Copyright (c) 2006           Sam Ravnborg <sam@ravnborg.org>
 #
-# The output is suitable for gen_init_cpio built from usr/gen_init_cpio.c.
+# Released under the terms of the GNU GPL
 #
+# Generate a cpio packed initramfs. It uses gen_init_cpio to generate
+# the cpio archive, and gzip to pack it.
+# The script may also be used to generate the inputfile used for gen_init_cpio
+# This script assumes that gen_init_cpio is located in usr/ directory
+
+# error out on errors
+set -e
+
+usage() {
+cat << EOF
+Usage:
+$0 [-o <file>] [-u <uid>] [-g <gid>] {-d | <cpio_source>} ...
+       -o <file>      Create gzipped initramfs file named <file> using
+                      gen_init_cpio and gzip
+       -u <uid>       User ID to map to user ID 0 (root).
+                      <uid> is only meaningful if <cpio_source>
+                      is a directory.
+       -g <gid>       Group ID to map to group ID 0 (root).
+                      <gid> is only meaningful if <cpio_source>
+                      is a directory.
+       <cpio_source>  File list or directory for cpio archive.
+                      If <cpio_source> is a .cpio file it will be used
+                      as direct input to initramfs.
+       -d             Output the default cpio list.
+
+All options except -o and -l may be repeated and are interpreted
+sequentially and immediately.  -u and -g states are preserved across
+<cpio_source> options so an explicit "-u 0 -g 0" is required
+to reset the root/group mapping.
+EOF
+}
+
+list_default_initramfs() {
+       # echo usr/kinit/kinit
+       :
+}
 
 default_initramfs() {
-       cat <<-EOF
+       cat <<-EOF >> ${output}
                # This is a very simple, default initramfs
 
                dir /dev 0755 0 0
                nod /dev/console 0600 0 0 c 5 1
                dir /root 0700 0 0
+               # file /kinit usr/kinit/kinit 0755 0 0
+               # slink /init kinit 0755 0 0
        EOF
 }
 
@@ -42,18 +75,28 @@ filetype() {
        return 0
 }
 
+list_print_mtime() {
+       :
+}
+
 print_mtime() {
-       local argv1="$1"
        local my_mtime="0"
 
-       if [ -e "${argv1}" ]; then
-               my_mtime=$(find "${argv1}" -printf "%T@\n" | sort -r | head -n 1)
+       if [ -e "$1" ]; then
+               my_mtime=$(find "$1" -printf "%T@\n" | sort -r | head -n 1)
        fi
-       
-       echo "# Last modified: ${my_mtime}"
-       echo
+
+       echo "# Last modified: ${my_mtime}" >> ${output}
+       echo "" >> ${output}
+}
+
+list_parse() {
+       echo "$1 \\"
 }
 
+# for each file print a line in following format
+# <filetype> <name> <path to file> <octal mode> <uid> <gid>
+# for links, devices etc the format differs. See gen_init_cpio for details
 parse() {
        local location="$1"
        local name="${location/${srcdir}//}"
@@ -99,80 +142,112 @@ parse() {
                        ;;
        esac
 
-       echo "${str}"
+       echo "${str}" >> ${output}
 
        return 0
 }
 
-usage() {
-       printf    "Usage:\n"
-       printf    "$0 [ [-u <root_uid>] [-g <root_gid>] [-d | <cpio_source>] ] . . .\n"
-       printf    "\n"
-       printf -- "-u <root_uid>  User ID to map to user ID 0 (root).\n"
-       printf    "               <root_uid> is only meaningful if <cpio_source>\n"
-       printf    "               is a directory.\n"
-       printf -- "-g <root_gid>  Group ID to map to group ID 0 (root).\n"
-       printf    "               <root_gid> is only meaningful if <cpio_source>\n"
-       printf    "               is a directory.\n"
-       printf    "<cpio_source>  File list or directory for cpio archive.\n"
-       printf    "               If <cpio_source> is not provided then a\n"
-       printf    "               a default list will be output.\n"
-       printf -- "-d             Output the default cpio list.  If no <cpio_source>\n"
-       printf    "               is given then the default cpio list will be output.\n"
-       printf    "\n"
-       printf    "All options may be repeated and are interpreted sequentially\n"
-       printf    "and immediately.  -u and -g states are preserved across\n"
-       printf    "<cpio_source> options so an explicit \"-u 0 -g 0\" is required\n"
-       printf    "to reset the root/group mapping.\n"
+unknown_option() {
+       printf "ERROR: unknown option \"$arg\"\n" >&2
+       printf "If the filename validly begins with '-', " >&2
+       printf "then it must be prefixed\n" >&2
+       printf "by './' so that it won't be interpreted as an option." >&2
+       printf "\n" >&2
+       usage >&2
+       exit 1
+}
+
+list_header() {
+       echo "deps_initramfs := \\"
+}
+
+header() {
+       printf "\n#####################\n# $1\n" >> ${output}
+}
+
+# process one directory (incl sub-directories)
+dir_filelist() {
+       ${dep_list}header "$1"
+
+       srcdir=$(echo "$1" | sed -e 's://*:/:g')
+       dirlist=$(find "${srcdir}" -printf "%p %m %U %G\n" 2>/dev/null)
+
+       # If $dirlist is only one line, then the directory is empty
+       if [  "$(echo "${dirlist}" | wc -l)" -gt 1 ]; then
+               ${dep_list}print_mtime "$1"
+
+               echo "${dirlist}" | \
+               while read x; do
+                       ${dep_list}parse ${x}
+               done
+       fi
 }
 
-build_list() {
-       printf "\n#####################\n# $cpio_source\n"
-
-       if [ -f "$cpio_source" ]; then
-               print_mtime "$cpio_source"
-               cat "$cpio_source"
-       elif [ -d "$cpio_source" ]; then
-               srcdir=$(echo "$cpio_source" | sed -e 's://*:/:g')
-               dirlist=$(find "${srcdir}" -printf "%p %m %U %G\n" 2>/dev/null)
-
-               # If $dirlist is only one line, then the directory is empty
-               if [  "$(echo "${dirlist}" | wc -l)" -gt 1 ]; then
-                       print_mtime "$cpio_source"
-               
-                       echo "${dirlist}" | \
-                       while read x; do
-                               parse ${x}
-                       done
+# if only one file is specified and it is .cpio file then use it direct as fs
+# if a directory is specified then add all files in given direcotry to fs
+# if a regular file is specified assume it is in gen_initramfs format
+input_file() {
+       source="$1"
+       if [ -f "$1" ]; then
+               ${dep_list}header "$1"
+               is_cpio="$(echo "$1" | sed 's/^.*\.cpio/cpio/')"
+               if [ $2 -eq 0 -a ${is_cpio} == "cpio" ]; then
+                       cpio_file=$1
+                       [ ! -z ${dep_list} ] && echo "$1"
+                       return 0
+               fi
+               if [ -z ${dep_list} ]; then
+                       print_mtime "$1" >> ${output}
+                       cat "$1"         >> ${output}
                else
-                       # Failsafe in case directory is empty
-                       default_initramfs
+                       grep ^file "$1" | cut -d ' ' -f 3
                fi
+       elif [ -d "$1" ]; then
+               dir_filelist "$1"
        else
-               echo "  $0: Cannot open '$cpio_source'" >&2
+               echo "  ${prog}: Cannot open '$1'" >&2
                exit 1
        fi
 }
 
-
+prog=$0
 root_uid=0
 root_gid=0
+dep_list=
+cpio_file=
+cpio_list=
+output="/dev/stdout"
+output_file=""
 
+arg="$1"
+case "$arg" in
+       "-l")   # files included in initramfs - used by kbuild
+               dep_list="list_"
+               shift
+               ;;
+       "-o")   # generate gzipped cpio image named $1
+               shift
+               output_file="$1"
+               cpio_list="$(mktemp ${TMPDIR:-/tmp}/cpiolist.XXXXXX)"
+               output=${cpio_list}
+               shift
+               ;;
+esac
 while [ $# -gt 0 ]; do
        arg="$1"
        shift
        case "$arg" in
-               "-u")
+               "-u")   # map $1 to uid=0 (root)
                        root_uid="$1"
                        shift
                        ;;
-               "-g")
+               "-g")   # map $1 to gid=0 (root)
                        root_gid="$1"
                        shift
                        ;;
-               "-d")
+               "-d")   # display default initramfs list
                        default_list="$arg"
-                       default_initramfs
+                       ${dep_list}default_initramfs
                        ;;
                "-h")
                        usage
@@ -181,23 +256,27 @@ while [ $# -gt 0 ]; do
                *)
                        case "$arg" in
                                "-"*)
-                                       printf "ERROR: unknown option \"$arg\"\n" >&2
-                                       printf "If the filename validly begins with '-', then it must be prefixed\n" >&2
-                                       printf "by './' so that it won't be interpreted as an option." >&2
-                                       printf "\n" >&2
-                                       usage >&2
-                                       exit 1
+                                       unknown_option
                                        ;;
-                               *)
-                                       cpio_source="$arg"
-                                       build_list
+                               *)      # input file/dir - process it
+                                       input_file "$arg" "$#"
                                        ;;
                        esac
                        ;;
        esac
 done
 
-# spit out the default cpio list if a source hasn't been specified
-[ -z "$cpio_source" -a -z "$default_list" ] && default_initramfs
-
+# If output_file is set we will generate cpio archive and gzip it
+# we are carefull to delete tmp files
+if [ ! -z ${output_file} ]; then
+       if [ -z ${cpio_file} ]; then
+               cpio_tfile="$(mktemp ${TMPDIR:-/tmp}/cpiofile.XXXXXX)"
+               usr/gen_init_cpio ${cpio_list} > ${cpio_tfile}
+       else
+               cpio_tfile=${cpio_file}
+       fi
+       rm ${cpio_list}
+       cat ${cpio_tfile} | gzip -f -9 - > ${output_file}
+       [ -z ${cpio_file} ] && rm ${cpio_tfile}
+fi
 exit 0
index 10eeae53d827f904a440c812af8febd13c891776..8012d1076876bb1f4ee9766a63720f0e53d9f829 100644 (file)
@@ -5,6 +5,7 @@
 
 #include <ctype.h>
 #include <stdlib.h>
+#include <stdio.h>
 #include <string.h>
 #include <unistd.h>
 #include <time.h>
@@ -63,20 +64,6 @@ static void check_stdin(void)
        }
 }
 
-static char *fgets_check_stream(char *s, int size, FILE *stream)
-{
-       char *ret = fgets(s, size, stream);
-
-       if (ret == NULL && feof(stream)) {
-               printf(_("aborted!\n\n"));
-               printf(_("Console input is closed. "));
-               printf(_("Run 'make oldconfig' to update configuration.\n\n"));
-               exit(1);
-       }
-
-       return ret;
-}
-
 static void conf_askvalue(struct symbol *sym, const char *def)
 {
        enum symbol_type type = sym_get_type(sym);
@@ -114,7 +101,7 @@ static void conf_askvalue(struct symbol *sym, const char *def)
                check_stdin();
        case ask_all:
                fflush(stdout);
-               fgets_check_stream(line, 128, stdin);
+               fgets(line, 128, stdin);
                return;
        case set_default:
                printf("%s\n", def);
@@ -328,8 +315,7 @@ static int conf_choice(struct menu *menu)
                printf("%*s%s\n", indent - 1, "", menu_get_prompt(menu));
                def_sym = sym_get_choice_value(sym);
                cnt = def = 0;
-               line[0] = '0';
-               line[1] = 0;
+               line[0] = 0;
                for (child = menu->list; child; child = child->next) {
                        if (!menu_is_visible(child))
                                continue;
@@ -370,7 +356,7 @@ static int conf_choice(struct menu *menu)
                        check_stdin();
                case ask_all:
                        fflush(stdout);
-                       fgets_check_stream(line, 128, stdin);
+                       fgets(line, 128, stdin);
                        strip(line);
                        if (line[0] == '?') {
                                printf("\n%s\n", menu->sym->help ?
@@ -546,7 +532,7 @@ int main(int ac, char **av)
                        break;
                case 'h':
                case '?':
-                       printf("%s [-o|-s] config\n", av[0]);
+                       fprintf(stderr, "See README for usage info\n");
                        exit(0);
                }
        }
index 1b8882ddbc74fed0fbed2c22f8dd317b6de0106b..1b5df589f3aecc12f3c0b8bde93526c84c0a60ec 100644 (file)
@@ -325,7 +325,7 @@ int conf_read(const char *name)
                                sym->flags |= e->right.sym->flags & SYMBOL_NEW;
        }
 
-       sym_change_count = conf_warnings && conf_unsaved;
+       sym_change_count = conf_warnings || conf_unsaved;
 
        return 0;
 }
index db07ae73e051f62a50421d10e1e2e0dc277136fc..be0200e9cdaf759ae9de72a1b2e5bec65bbaae9e 100644 (file)
@@ -196,8 +196,8 @@ int dialog_checklist(const char *title, const char *prompt, int height,
 
        print_buttons(dialog, height, width, 0);
 
-       wnoutrefresh(list);
        wnoutrefresh(dialog);
+       wnoutrefresh(list);
        doupdate();
 
        while (key != ESC) {
@@ -225,12 +225,11 @@ int dialog_checklist(const char *title, const char *prompt, int height,
                                        }
                                        scroll--;
                                        print_item(list, items[scroll * 3 + 1], status[scroll], 0, TRUE);
-                                       wnoutrefresh(list);
-
                                        print_arrows(dialog, choice, item_no,
                                                     scroll, box_y, box_x + check_x + 5, list_height);
 
-                                       wrefresh(dialog);
+                                       wnoutrefresh(dialog);
+                                       wrefresh(list);
 
                                        continue;       /* wait for another key press */
                                } else
@@ -252,12 +251,12 @@ int dialog_checklist(const char *title, const char *prompt, int height,
                                        scroll++;
                                        print_item(list, items[(scroll + max_choice - 1) * 3 + 1],
                                                   status[scroll + max_choice - 1], max_choice - 1, TRUE);
-                                       wnoutrefresh(list);
 
                                        print_arrows(dialog, choice, item_no,
                                                     scroll, box_y, box_x + check_x + 5, list_height);
 
-                                       wrefresh(dialog);
+                                       wnoutrefresh(dialog);
+                                       wrefresh(list);
 
                                        continue;       /* wait for another key press */
                                } else
@@ -271,8 +270,8 @@ int dialog_checklist(const char *title, const char *prompt, int height,
                                choice = i;
                                print_item(list, items[(scroll + choice) * 3 + 1],
                                           status[scroll + choice], choice, TRUE);
-                               wnoutrefresh(list);
-                               wrefresh(dialog);
+                               wnoutrefresh(dialog);
+                               wrefresh(list);
                        }
                        continue;       /* wait for another key press */
                }
@@ -306,8 +305,8 @@ int dialog_checklist(const char *title, const char *prompt, int height,
                                                print_item(list, items[(scroll + i) * 3 + 1],
                                                           status[scroll + i], i, i == choice);
                                }
-                               wnoutrefresh(list);
-                               wrefresh(dialog);
+                               wnoutrefresh(dialog);
+                               wrefresh(list);
 
                                for (i = 0; i < item_no; i++)
                                        if (status[i])
index 09512b54437594d4348f027f9a4b46743da99f47..bf8052f4fd4ab73c80cfd2040ed69d4562e456e0 100644 (file)
@@ -58,8 +58,7 @@
 
 #include "dialog.h"
 
-#define ITEM_IDENT 1   /* Indent of menu entries. Fixed for all menus */
-static int menu_width;
+static int menu_width, item_x;
 
 /*
  * Print menu item
@@ -70,7 +69,7 @@ static void do_print_item(WINDOW * win, const char *item, int choice,
        int j;
        char *menu_item = malloc(menu_width + 1);
 
-       strncpy(menu_item, item, menu_width - ITEM_IDENT);
+       strncpy(menu_item, item, menu_width - item_x);
        menu_item[menu_width] = 0;
        j = first_alpha(menu_item, "YyNnMmHh");
 
@@ -87,13 +86,13 @@ static void do_print_item(WINDOW * win, const char *item, int choice,
        wclrtoeol(win);
 #endif
        wattrset(win, selected ? item_selected_attr : item_attr);
-       mvwaddstr(win, choice, ITEM_IDENT, menu_item);
+       mvwaddstr(win, choice, item_x, menu_item);
        if (hotkey) {
                wattrset(win, selected ? tag_key_selected_attr : tag_key_attr);
-               mvwaddch(win, choice, ITEM_IDENT + j, menu_item[j]);
+               mvwaddch(win, choice, item_x + j, menu_item[j]);
        }
        if (selected) {
-               wmove(win, choice, ITEM_IDENT + 1);
+               wmove(win, choice, item_x + 1);
        }
        free(menu_item);
        wrefresh(win);
@@ -227,6 +226,8 @@ int dialog_menu(const char *title, const char *prompt, int height, int width,
        draw_box(dialog, box_y, box_x, menu_height + 2, menu_width + 2,
                 menubox_border_attr, menubox_attr);
 
+       item_x = (menu_width - 70) / 2;
+
        /* Set choice to default item */
        for (i = 0; i < item_no; i++)
                if (strcmp(current, items[i * 2]) == 0)
@@ -263,10 +264,10 @@ int dialog_menu(const char *title, const char *prompt, int height, int width,
        wnoutrefresh(menu);
 
        print_arrows(dialog, item_no, scroll,
-                    box_y, box_x + ITEM_IDENT + 1, menu_height);
+                    box_y, box_x + item_x + 1, menu_height);
 
        print_buttons(dialog, height, width, 0);
-       wmove(menu, choice, ITEM_IDENT + 1);
+       wmove(menu, choice, item_x + 1);
        wrefresh(menu);
 
        while (key != ESC) {
@@ -349,7 +350,7 @@ int dialog_menu(const char *title, const char *prompt, int height, int width,
                        print_item(scroll + choice, choice, TRUE);
 
                        print_arrows(dialog, item_no, scroll,
-                                    box_y, box_x + ITEM_IDENT + 1, menu_height);
+                                    box_y, box_x + item_x + 1, menu_height);
 
                        wnoutrefresh(dialog);
                        wrefresh(menu);
index 0b92ddff26fd146674834d5ff019d28413b97c1b..cd00e9f0758995e5d027ff9dc96835256b10860c 100644 (file)
@@ -492,17 +492,19 @@ static int strrcmp(const char *s, const char *sub)
  *   These functions may often be marked __init and we do not want to
  *   warn here.
  *   the pattern is identified by:
- *   tosec   = .init.text | .exit.text
+ *   tosec   = .init.text | .exit.text | .init.data
  *   fromsec = .data
- *   atsym = *_driver, *_ops, *_probe, *probe_one
+ *   atsym = *_driver, *_template, *_sht, *_ops, *_probe, *probe_one
  **/
 static int secref_whitelist(const char *tosec, const char *fromsec,
-                         const char *atsym)
+                           const char *atsym)
 {
        int f1 = 1, f2 = 1;
        const char **s;
        const char *pat2sym[] = {
                "_driver",
+               "_template", /* scsi uses *_template a lot */
+               "_sht",      /* scsi also used *_sht to some extent */
                "_ops",
                "_probe",
                "_probe_one",
@@ -522,7 +524,8 @@ static int secref_whitelist(const char *tosec, const char *fromsec,
 
        /* Check for pattern 2 */
        if ((strcmp(tosec, ".init.text") != 0) &&
-           (strcmp(tosec, ".exit.text") != 0))
+           (strcmp(tosec, ".exit.text") != 0) &&
+           (strcmp(tosec, ".init.data") != 0))
                f2 = 0;
        if (strcmp(fromsec, ".data") != 0)
                f2 = 0;
@@ -658,7 +661,7 @@ static void warn_sec_mismatch(const char *modname, const char *fromsec,
                warn("%s - Section mismatch: reference to %s:%s from %s "
                     "before '%s' (at offset -0x%llx)\n",
                     modname, secname, refsymname, fromsec,
-                    elf->strtab + before->st_name,
+                    elf->strtab + after->st_name,
                     (long long)r.r_offset);
        } else {
                warn("%s - Section mismatch: reference to %s:%s from %s "
@@ -820,6 +823,7 @@ static int exit_section(const char *name)
  * For our future {in}sanity, add a comment that this is the ppc .opd
  * section, not the ia64 .opd section.
  * ia64 .opd should not point to discarded sections.
+ * [.rodata] like for .init.text we ignore .rodata references -same reason
  **/
 static int exit_section_ref_ok(const char *name)
 {
@@ -829,6 +833,7 @@ static int exit_section_ref_ok(const char *name)
                ".exit.text",
                ".exit.data",
                ".init.text",
+               ".rodata",
                ".opd", /* See comment [OPD] */
                ".toc1",  /* used by ppc64 */
                ".altinstructions",
old mode 100644 (file)
new mode 100755 (executable)
old mode 100644 (file)
new mode 100755 (executable)
index beb43ef7f761fffaaa80393129e554922f92b544..84999f69773d6cc232ea6db365eac38e4e1b83ba 100755 (executable)
@@ -39,10 +39,10 @@ tune2fs 2>&1 | grep "^tune2fs" | sed 's/,//' |  awk \
 fsck.jfs -V 2>&1 | grep version | sed 's/,//' |  awk \
 'NR==1 {print "jfsutils              ", $3}'
 
-reiserfsck -V 2>&1 | grep reiserfsck | awk \
+reiserfsck -V 2>&1 | grep ^reiserfsck | awk \
 'NR==1{print "reiserfsprogs         ", $2}'
 
-fsck.reiser4 -V 2>&1 | grep fsck.reiser4 | awk \
+fsck.reiser4 -V 2>&1 | grep ^fsck.reiser4 | awk \
 'NR==1{print "reiser4progs          ", $2}'
 
 xfs_db -V 2>&1 | grep version | awk \
index a057e3311aad662f1ebcd8e79919fe76ea947e4b..b6061fa29da7fc7eb5278530ebb26769dc4ebcde 100644 (file)
@@ -785,6 +785,10 @@ key_ref_t key_create_or_update(key_ref_t keyring_ref,
 
        key_check(keyring);
 
+       key_ref = ERR_PTR(-ENOTDIR);
+       if (keyring->type != &key_type_keyring)
+               goto error_2;
+
        down_write(&keyring->sem);
 
        /* if we're going to allocate a new key, we're going to have
index d65a180f888d2475aeb444c04d4c1f9b5b42d23b..bffa924c1f88240b088e5c30ee7d9363849c45e2 100644 (file)
@@ -437,6 +437,7 @@ EXPORT_SYMBOL(keyring_search);
 /*
  * search the given keyring only (no recursion)
  * - keyring must be locked by caller
+ * - caller must guarantee that the keyring is a keyring
  */
 key_ref_t __keyring_search_one(key_ref_t keyring_ref,
                               const struct key_type *ktype,
index f6940618e345796a90ed32a30ec9a53024862090..217a0bef3c82b341db5c07d414b7385a8f4a00fb 100644 (file)
@@ -168,11 +168,12 @@ error:
  */
 int install_process_keyring(struct task_struct *tsk)
 {
-       unsigned long flags;
        struct key *keyring;
        char buf[20];
        int ret;
 
+       might_sleep();
+
        if (!tsk->signal->process_keyring) {
                sprintf(buf, "_pid.%u", tsk->tgid);
 
@@ -183,12 +184,12 @@ int install_process_keyring(struct task_struct *tsk)
                }
 
                /* attach keyring */
-               spin_lock_irqsave(&tsk->sighand->siglock, flags);
+               spin_lock_irq(&tsk->sighand->siglock);
                if (!tsk->signal->process_keyring) {
                        tsk->signal->process_keyring = keyring;
                        keyring = NULL;
                }
-               spin_unlock_irqrestore(&tsk->sighand->siglock, flags);
+               spin_unlock_irq(&tsk->sighand->siglock);
 
                key_put(keyring);
        }
@@ -207,38 +208,37 @@ error:
 static int install_session_keyring(struct task_struct *tsk,
                                   struct key *keyring)
 {
-       unsigned long flags;
        struct key *old;
        char buf[20];
-       int ret;
+
+       might_sleep();
 
        /* create an empty session keyring */
        if (!keyring) {
                sprintf(buf, "_ses.%u", tsk->tgid);
 
                keyring = keyring_alloc(buf, tsk->uid, tsk->gid, 1, NULL);
-               if (IS_ERR(keyring)) {
-                       ret = PTR_ERR(keyring);
-                       goto error;
-               }
+               if (IS_ERR(keyring))
+                       return PTR_ERR(keyring);
        }
        else {
                atomic_inc(&keyring->usage);
        }
 
        /* install the keyring */
-       spin_lock_irqsave(&tsk->sighand->siglock, flags);
-       old = rcu_dereference(tsk->signal->session_keyring);
+       spin_lock_irq(&tsk->sighand->siglock);
+       old = tsk->signal->session_keyring;
        rcu_assign_pointer(tsk->signal->session_keyring, keyring);
-       spin_unlock_irqrestore(&tsk->sighand->siglock, flags);
+       spin_unlock_irq(&tsk->sighand->siglock);
 
-       ret = 0;
+       /* we're using RCU on the pointer, but there's no point synchronising
+        * on it if it didn't previously point to anything */
+       if (old) {
+               synchronize_rcu();
+               key_put(old);
+       }
 
-       /* we're using RCU on the pointer */
-       synchronize_rcu();
-       key_put(old);
-error:
-       return ret;
+       return 0;
 
 } /* end install_session_keyring() */
 
@@ -311,7 +311,6 @@ void exit_keys(struct task_struct *tsk)
  */
 int exec_keys(struct task_struct *tsk)
 {
-       unsigned long flags;
        struct key *old;
 
        /* newly exec'd tasks don't get a thread keyring */
@@ -323,10 +322,10 @@ int exec_keys(struct task_struct *tsk)
        key_put(old);
 
        /* discard the process keyring from a newly exec'd task */
-       spin_lock_irqsave(&tsk->sighand->siglock, flags);
+       spin_lock_irq(&tsk->sighand->siglock);
        old = tsk->signal->process_keyring;
        tsk->signal->process_keyring = NULL;
-       spin_unlock_irqrestore(&tsk->sighand->siglock, flags);
+       spin_unlock_irq(&tsk->sighand->siglock);
 
        key_put(old);
 
index 640d0bfdbc6819e4ffa7845f1e10e92b5640e14a..84047f69f9c1b4d0bdfbbfe511457d6a62c18dad 100644 (file)
@@ -264,7 +264,7 @@ int mls_context_to_sid(char oldc,
 
        if (!selinux_mls_enabled) {
                if (def_sid != SECSID_NULL && oldc)
-                       *scontext += strlen(*scontext);
+                       *scontext += strlen(*scontext)+1;
                return 0;
        }
 
index dfab6c886698d97f6c7d278125fd878422e8b515..abe99d8813765a977405de8246d42f9597c34341 100644 (file)
@@ -281,7 +281,7 @@ u32 selinux_socket_getpeer_dgram(struct sk_buff *skb)
                int i;
 
                for (i = sp->len-1; i >= 0; i--) {
-                       struct xfrm_state *x = sp->x[i].xvec;
+                       struct xfrm_state *x = sp->xvec[i];
                        if (selinux_authorizable_xfrm(x)) {
                                struct xfrm_sec_ctx *ctx = x->security;
                                return ctx->ctx_sid;
@@ -314,7 +314,7 @@ int selinux_xfrm_sock_rcv_skb(u32 isec_sid, struct sk_buff *skb)
                 *  Only need to verify the existence of an authorizable sp.
                 */
                for (i = 0; i < sp->len; i++) {
-                       struct xfrm_state *x = sp->x[i].xvec;
+                       struct xfrm_state *x = sp->xvec[i];
 
                        if (x && selinux_authorizable_xfrm(x))
                                goto accept;
index 91114c7aeff5aa29c6c65375fda770f19425b381..c5978d6c6080777246d989293ad2ef1684833cbb 100644 (file)
@@ -1682,7 +1682,7 @@ static void snd_pcm_oss_init_substream(struct snd_pcm_substream *substream,
        substream->oss.setup = *setup;
        if (setup->nonblock)
                substream->ffile->f_flags |= O_NONBLOCK;
-       else
+       else if (setup->block)
                substream->ffile->f_flags &= ~O_NONBLOCK;
        runtime = substream->runtime;
        runtime->oss.params = 1;
@@ -1757,10 +1757,11 @@ static int snd_pcm_oss_open_file(struct file *file,
                }
 
                pcm_oss_file->streams[idx] = substream;
+               substream->file = pcm_oss_file;
                snd_pcm_oss_init_substream(substream, &setup[idx], minor);
        }
        
-       if (! pcm_oss_file->streams[0] && pcm_oss_file->streams[1]) {
+       if (!pcm_oss_file->streams[0] && !pcm_oss_file->streams[1]) {
                snd_pcm_oss_release_file(pcm_oss_file);
                return -EINVAL;
        }
@@ -1809,7 +1810,7 @@ static int snd_pcm_oss_open(struct inode *inode, struct file *file)
                err = -EFAULT;
                goto __error;
        }
-       memset(setup, 0, sizeof(*setup));
+       memset(setup, 0, sizeof(setup));
        if (file->f_mode & FMODE_WRITE)
                snd_pcm_oss_look_for_setup(pcm, SNDRV_PCM_STREAM_PLAYBACK,
                                           task_name, &setup[0]);
index 5d7eb123b99905df015d941b0a8b9aaca8f8ff6e..122e10a61ab9c7e788c68e8991965ec3dd8beb6e 100644 (file)
@@ -196,7 +196,7 @@ static char *snd_pcm_format_names[] = {
        FORMAT(U18_3BE),
 };
 
-const char *snd_pcm_format_name(snd_pcm_format_t format)
+static const char *snd_pcm_format_name(snd_pcm_format_t format)
 {
        return snd_pcm_format_names[format];
 }
index 964e4c47a7f1986a0cb031ab51375b5e0668fbf4..0860c5a84502f6f67451cdea60a566b639fdbf9b 100644 (file)
@@ -2007,14 +2007,16 @@ static void pcm_release_private(struct snd_pcm_substream *substream)
 void snd_pcm_release_substream(struct snd_pcm_substream *substream)
 {
        snd_pcm_drop(substream);
-       if (substream->pcm_release)
-               substream->pcm_release(substream);
        if (substream->hw_opened) {
                if (substream->ops->hw_free != NULL)
                        substream->ops->hw_free(substream);
                substream->ops->close(substream);
                substream->hw_opened = 0;
        }
+       if (substream->pcm_release) {
+               substream->pcm_release(substream);
+               substream->pcm_release = NULL;
+       }
        snd_pcm_detach_substream(substream);
 }
 
index 8687ae3c66b8c54bf156e2424c0a9ecf6d8e4c9a..b49a45cbf67a09aa9faf39ae75671dd0f7cad1bf 100644 (file)
@@ -183,7 +183,8 @@ static void snd_mpu401_uart_remove_timer (struct snd_mpu401 *mpu, int input)
 
  */
 
-static void snd_mpu401_uart_cmd(struct snd_mpu401 * mpu, unsigned char cmd, int ack)
+static int snd_mpu401_uart_cmd(struct snd_mpu401 * mpu, unsigned char cmd,
+               int ack)
 {
        unsigned long flags;
        int timeout, ok;
@@ -218,9 +219,11 @@ static void snd_mpu401_uart_cmd(struct snd_mpu401 * mpu, unsigned char cmd, int
                ok = 1;
        }
        spin_unlock_irqrestore(&mpu->input_lock, flags);
-       if (! ok)
+       if (!ok) {
                snd_printk("cmd: 0x%x failed at 0x%lx (status = 0x%x, data = 0x%x)\n", cmd, mpu->port, mpu->read(mpu, MPU401C(mpu)), mpu->read(mpu, MPU401D(mpu)));
-       // snd_printk("cmd: 0x%x at 0x%lx (status = 0x%x, data = 0x%x)\n", cmd, mpu->port, mpu->read(mpu, MPU401C(mpu)), mpu->read(mpu, MPU401D(mpu)));
+               return 1;
+       }
+       return 0;
 }
 
 /*
@@ -235,12 +238,19 @@ static int snd_mpu401_uart_input_open(struct snd_rawmidi_substream *substream)
        if (mpu->open_input && (err = mpu->open_input(mpu)) < 0)
                return err;
        if (! test_bit(MPU401_MODE_BIT_OUTPUT, &mpu->mode)) {
-               snd_mpu401_uart_cmd(mpu, MPU401_RESET, 1);
-               snd_mpu401_uart_cmd(mpu, MPU401_ENTER_UART, 1);
+               if (snd_mpu401_uart_cmd(mpu, MPU401_RESET, 1))
+                       goto error_out;
+               if (snd_mpu401_uart_cmd(mpu, MPU401_ENTER_UART, 1))
+                       goto error_out;
        }
        mpu->substream_input = substream;
        set_bit(MPU401_MODE_BIT_INPUT, &mpu->mode);
        return 0;
+
+error_out:
+       if (mpu->open_input && mpu->close_input)
+               mpu->close_input(mpu);
+       return -EIO;
 }
 
 static int snd_mpu401_uart_output_open(struct snd_rawmidi_substream *substream)
@@ -252,39 +262,52 @@ static int snd_mpu401_uart_output_open(struct snd_rawmidi_substream *substream)
        if (mpu->open_output && (err = mpu->open_output(mpu)) < 0)
                return err;
        if (! test_bit(MPU401_MODE_BIT_INPUT, &mpu->mode)) {
-               snd_mpu401_uart_cmd(mpu, MPU401_RESET, 1);
-               snd_mpu401_uart_cmd(mpu, MPU401_ENTER_UART, 1);
+               if (snd_mpu401_uart_cmd(mpu, MPU401_RESET, 1))
+                       goto error_out;
+               if (snd_mpu401_uart_cmd(mpu, MPU401_ENTER_UART, 1))
+                       goto error_out;
        }
        mpu->substream_output = substream;
        set_bit(MPU401_MODE_BIT_OUTPUT, &mpu->mode);
        return 0;
+
+error_out:
+       if (mpu->open_output && mpu->close_output)
+               mpu->close_output(mpu);
+       return -EIO;
 }
 
 static int snd_mpu401_uart_input_close(struct snd_rawmidi_substream *substream)
 {
        struct snd_mpu401 *mpu;
+       int err = 0;
 
        mpu = substream->rmidi->private_data;
        clear_bit(MPU401_MODE_BIT_INPUT, &mpu->mode);
        mpu->substream_input = NULL;
        if (! test_bit(MPU401_MODE_BIT_OUTPUT, &mpu->mode))
-               snd_mpu401_uart_cmd(mpu, MPU401_RESET, 0);
+               err = snd_mpu401_uart_cmd(mpu, MPU401_RESET, 0);
        if (mpu->close_input)
                mpu->close_input(mpu);
+       if (err)
+               return -EIO;
        return 0;
 }
 
 static int snd_mpu401_uart_output_close(struct snd_rawmidi_substream *substream)
 {
        struct snd_mpu401 *mpu;
+       int err = 0;
 
        mpu = substream->rmidi->private_data;
        clear_bit(MPU401_MODE_BIT_OUTPUT, &mpu->mode);
        mpu->substream_output = NULL;
        if (! test_bit(MPU401_MODE_BIT_INPUT, &mpu->mode))
-               snd_mpu401_uart_cmd(mpu, MPU401_RESET, 0);
+               err = snd_mpu401_uart_cmd(mpu, MPU401_RESET, 0);
        if (mpu->close_output)
                mpu->close_output(mpu);
+       if (err)
+               return -EIO;
        return 0;
 }
 
@@ -316,6 +339,7 @@ static void snd_mpu401_uart_input_trigger(struct snd_rawmidi_substream *substrea
                        snd_mpu401_uart_remove_timer(mpu, 1);
                clear_bit(MPU401_MODE_BIT_INPUT_TRIGGER, &mpu->mode);
        }
+
 }
 
 /*
index 326a057f752ff7c4d8dd2fcc8ba878e033d6608a..99908e44124da32593b6fa85ea87eafeb4cc1c6b 100644 (file)
@@ -193,9 +193,11 @@ static int __init alsa_card_ad1848_init(void)
                        continue;
                device = platform_device_register_simple(SND_AD1848_DRIVER,
                                                         i, NULL, 0);
-               if (IS_ERR(device)) {
-                       err = PTR_ERR(device);
-                       goto errout;
+               if (IS_ERR(device))
+                       continue;
+               if (!platform_get_drvdata(device)) {
+                       platform_device_unregister(device);
+                       continue;
                }
                devices[i] = device;
                cards++;
@@ -204,14 +206,10 @@ static int __init alsa_card_ad1848_init(void)
 #ifdef MODULE
                printk(KERN_ERR "AD1848 soundcard not found or device busy\n");
 #endif
-               err = -ENODEV;
-               goto errout;
+               snd_ad1848_unregister_all();
+               return -ENODEV;
        }
        return 0;
-
- errout:
-       snd_ad1848_unregister_all();
-       return err;
 }
 
 static void __exit alsa_card_ad1848_exit(void)
index a253a14e6a45be6ea18e8b982268c855337eefba..1124344ed948b38005041306e322d8107a7af4d1 100644 (file)
@@ -43,8 +43,7 @@ static int __devinit snd_adlib_probe(struct platform_device *device)
        struct snd_card *card;
        struct snd_opl3 *opl3;
 
-       int error;
-       int i = device->id;
+       int error, i = device->id;
 
        if (port[i] == SNDRV_AUTO_PORT) {
                snd_printk(KERN_ERR DRV_NAME ": please specify port\n");
@@ -95,8 +94,7 @@ static int __devinit snd_adlib_probe(struct platform_device *device)
        return 0;
 
 out1:  snd_card_free(card);
- out0: error = -EINVAL; /* FIXME: should be the original error code */
-       return error;
+out0:  return error;
 }
 
 static int __devexit snd_adlib_remove(struct platform_device *device)
@@ -134,6 +132,11 @@ static int __init alsa_card_adlib_init(void)
                if (IS_ERR(device))
                        continue;
 
+               if (!platform_get_drvdata(device)) {
+                       platform_device_unregister(device);
+                       continue;
+               }
+
                devices[i] = device;
                cards++;
        }
index bc0f5ebf5d3c835cb600a18565919b8729b03b57..3c1e9fd56fe00143e3c1a26ca81c5acc9affa4e8 100644 (file)
@@ -699,9 +699,11 @@ static int __init alsa_card_cmi8330_init(void)
                        continue;
                device = platform_device_register_simple(CMI8330_DRIVER,
                                                         i, NULL, 0);
-               if (IS_ERR(device)) {
-                       err = PTR_ERR(device);
-                       goto errout;
+               if (IS_ERR(device))
+                       continue;
+               if (!platform_get_drvdata(device)) {
+                       platform_device_unregister(device);
+                       continue;
                }
                platform_devices[i] = device;
                cards++;
@@ -719,14 +721,10 @@ static int __init alsa_card_cmi8330_init(void)
 #ifdef MODULE
                snd_printk(KERN_ERR "CMI8330 not found or device busy\n");
 #endif
-               err = -ENODEV;
-               goto errout;
+               snd_cmi8330_unregister_all();
+               return -ENODEV;
        }
        return 0;
-
- errout:
-       snd_cmi8330_unregister_all();
-       return err;
 }
 
 static void __exit alsa_card_cmi8330_exit(void)
index a30dcd96252525a11967c8aa2a879df5fb25b56e..397310f358b7c4ed1f0bfdefaebcb01bfc432442 100644 (file)
@@ -209,9 +209,11 @@ static int __init alsa_card_cs4231_init(void)
                        continue;
                device = platform_device_register_simple(SND_CS4231_DRIVER,
                                                         i, NULL, 0);
-               if (IS_ERR(device)) {
-                       err = PTR_ERR(device);
-                       goto errout;
+               if (IS_ERR(device))
+                       continue;
+               if (!platform_get_drvdata(device)) {
+                       platform_device_unregister(device);
+                       continue;
                }
                devices[i] = device;
                cards++;
@@ -220,14 +222,10 @@ static int __init alsa_card_cs4231_init(void)
 #ifdef MODULE
                printk(KERN_ERR "CS4231 soundcard not found or device busy\n");
 #endif
-               err = -ENODEV;
-               goto errout;
+               snd_cs4231_unregister_all();
+               return -ENODEV;
        }
        return 0;
-
- errout:
-       snd_cs4231_unregister_all();
-       return err;
 }
 
 static void __exit alsa_card_cs4231_exit(void)
index 382bb17ef49f08941fb88c76c037ff54caf02b57..f7fa779347ffea800b407a5a555b1cf37855137e 100644 (file)
@@ -780,9 +780,11 @@ static int __init alsa_card_cs423x_init(void)
                        continue;
                device = platform_device_register_simple(CS423X_DRIVER,
                                                         i, NULL, 0);
-               if (IS_ERR(device)) {
-                       err = PTR_ERR(device);
-                       goto errout;
+               if (IS_ERR(device))
+                       continue;
+               if (!platform_get_drvdata(device)) {
+                       platform_device_unregister(device);
+                       continue;
                }
                platform_devices[i] = device;
                snd_cs423x_devices++;
@@ -802,14 +804,10 @@ static int __init alsa_card_cs423x_init(void)
 #ifdef MODULE
                printk(KERN_ERR IDENT " soundcard not found or device busy\n");
 #endif
-               err = -ENODEV;
-               goto errout;
+               snd_cs423x_unregister_all();
+               return -ENODEV;
        }
        return 0;
-
- errout:
-       snd_cs423x_unregister_all();
-       return err;
 }
 
 static void __exit alsa_card_cs423x_exit(void)
index 2b69fc829265dfc87440f2e4c8c57ab384dd5db3..e90689ee162fac5174a3d4413cec954d6675fa40 100644 (file)
@@ -213,9 +213,11 @@ static int __init alsa_card_es1688_init(void)
                        continue;
                device = platform_device_register_simple(ES1688_DRIVER,
                                                         i, NULL, 0);
-               if (IS_ERR(device)) {
-                       err = PTR_ERR(device);
-                       goto errout;
+               if (IS_ERR(device))
+                       continue;
+               if (!platform_get_drvdata(device)) {
+                       platform_device_unregister(device);
+                       continue;
                }
                devices[i] = device;
                cards++;
@@ -224,14 +226,10 @@ static int __init alsa_card_es1688_init(void)
 #ifdef MODULE
                printk(KERN_ERR "ESS AudioDrive ES1688 soundcard not found or device busy\n");
 #endif
-               err = -ENODEV;
-               goto errout;
+               snd_es1688_unregister_all();
+               return -ENODEV;
        }
        return 0;
-
- errout:
-       snd_es1688_unregister_all();
-       return err;
 }
 
 static void __exit alsa_card_es1688_exit(void)
index 9fbc185b4cc24a734a1a19599eeed5d3738eb27f..a36ec1daa5cb9e24dcb5e3d887d5d56936c13f2b 100644 (file)
@@ -2391,9 +2391,11 @@ static int __init alsa_card_es18xx_init(void)
                        continue;
                device = platform_device_register_simple(ES18XX_DRIVER,
                                                         i, NULL, 0);
-               if (IS_ERR(device)) {
-                       err = PTR_ERR(device);
-                       goto errout;
+               if (IS_ERR(device))
+                       continue;
+               if (!platform_get_drvdata(device)) {
+                       platform_device_unregister(device);
+                       continue;
                }
                platform_devices[i] = device;
                cards++;
@@ -2411,14 +2413,10 @@ static int __init alsa_card_es18xx_init(void)
 #ifdef MODULE
                snd_printk(KERN_ERR "ESS AudioDrive ES18xx soundcard not found or device busy\n");
 #endif
-               err = -ENODEV;
-               goto errout;
+               snd_es18xx_unregister_all();
+               return -ENODEV;
        }
        return 0;
-
- errout:
-       snd_es18xx_unregister_all();
-       return err;
 }
 
 static void __exit alsa_card_es18xx_exit(void)
index 26dccfea243745634bafccddf0dca9c2cbe12158..37057a37dc30a870b611473113cd6b39425fa845 100644 (file)
@@ -253,9 +253,11 @@ static int __init alsa_card_gusclassic_init(void)
                        continue;
                device = platform_device_register_simple(GUSCLASSIC_DRIVER,
                                                         i, NULL, 0);
-               if (IS_ERR(device)) {
-                       err = PTR_ERR(device);
-                       goto errout;
+               if (IS_ERR(device))
+                       continue;
+               if (!platform_get_drvdata(device)) {
+                       platform_device_unregister(device);
+                       continue;
                }
                devices[i] = device;
                cards++;
@@ -264,14 +266,10 @@ static int __init alsa_card_gusclassic_init(void)
 #ifdef MODULE
                printk(KERN_ERR "GUS Classic soundcard not found or device busy\n");
 #endif
-               err = -ENODEV;
-               goto errout;
+               snd_gusclassic_unregister_all();
+               return -ENODEV;
        }
        return 0;
-
- errout:
-       snd_gusclassic_unregister_all();
-       return err;
 }
 
 static void __exit alsa_card_gusclassic_exit(void)
index 31dc20501d0c51937c4acae41d0fec1ab98282b3..05852fcc613bd32b54217af97f4ab850b8828916 100644 (file)
@@ -363,9 +363,11 @@ static int __init alsa_card_gusextreme_init(void)
                        continue;
                device = platform_device_register_simple(GUSEXTREME_DRIVER,
                                                         i, NULL, 0);
-               if (IS_ERR(device)) {
-                       err = PTR_ERR(device);
-                       goto errout;
+               if (IS_ERR(device))
+                       continue;
+               if (!platform_get_drvdata(device)) {
+                       platform_device_unregister(device);
+                       continue;
                }
                devices[i] = device;
                cards++;
@@ -374,14 +376,10 @@ static int __init alsa_card_gusextreme_init(void)
 #ifdef MODULE
                printk(KERN_ERR "GUS Extreme soundcard not found or device busy\n");
 #endif
-               err = -ENODEV;
-               goto errout;
+               snd_gusextreme_unregister_all();
+               return -ENODEV;
        }
        return 0;
-
- errout:
-       snd_gusextreme_unregister_all();
-       return err;
 }
 
 static void __exit alsa_card_gusextreme_exit(void)
index cafb9b67fa721d5bfd152121c30ce150ed2e85d2..fcf2c8fe6f94ba2b56dead0238e7b2816667a94f 100644 (file)
@@ -390,9 +390,11 @@ static int __init alsa_card_gusmax_init(void)
                        continue;
                device = platform_device_register_simple(GUSMAX_DRIVER,
                                                         i, NULL, 0);
-               if (IS_ERR(device)) {
-                       err = PTR_ERR(device);
-                       goto errout;
+               if (IS_ERR(device))
+                       continue;
+               if (!platform_get_drvdata(device)) {
+                       platform_device_unregister(device);
+                       continue;
                }
                devices[i] = device;
                cards++;
@@ -401,14 +403,10 @@ static int __init alsa_card_gusmax_init(void)
 #ifdef MODULE
                printk(KERN_ERR "GUS MAX soundcard not found or device busy\n");
 #endif
-               err = -ENODEV;
-               goto errout;
+               snd_gusmax_unregister_all();
+               return -ENODEV;
        }
        return 0;
-
- errout:
-       snd_gusmax_unregister_all();
-       return err;
 }
 
 static void __exit alsa_card_gusmax_exit(void)
index de71b7a99c83dd9f14c330605b28e9ca583dfd9b..4298d339e786fff55ccd1c090476b0bcf17d9441 100644 (file)
@@ -947,9 +947,11 @@ static int __init alsa_card_interwave_init(void)
 #endif
                device = platform_device_register_simple(INTERWAVE_DRIVER,
                                                         i, NULL, 0);
-               if (IS_ERR(device)) {
-                       err = PTR_ERR(device);
-                       goto errout;
+               if (IS_ERR(device))
+                       continue;
+               if (!platform_get_drvdata(device)) {
+                       platform_device_unregister(device);
+                       continue;
                }
                platform_devices[i] = device;
                cards++;
@@ -966,14 +968,10 @@ static int __init alsa_card_interwave_init(void)
 #ifdef MODULE
                printk(KERN_ERR "InterWave soundcard not found or device busy\n");
 #endif
-               err = -ENODEV;
-               goto errout;
+               snd_interwave_unregister_all();
+               return -ENODEV;
        }
        return 0;
-
- errout:
-       snd_interwave_unregister_all();
-       return err;
 }
 
 static void __exit alsa_card_interwave_exit(void)
index c906e205d7d52943be88e06aeb88301ddc9eeceb..6d889052c32c96932ed1484213f3f7382110786c 100644 (file)
@@ -962,9 +962,11 @@ static int __init alsa_card_opl3sa2_init(void)
 #endif
                device = platform_device_register_simple(OPL3SA2_DRIVER,
                                                         i, NULL, 0);
-               if (IS_ERR(device)) {
-                       err = PTR_ERR(device);
-                       goto errout;
+               if (IS_ERR(device))
+                       continue;
+               if (!platform_get_drvdata(device)) {
+                       platform_device_unregister(device);
+                       continue;
                }
                platform_devices[i] = device;
                snd_opl3sa2_devices++;
@@ -983,14 +985,10 @@ static int __init alsa_card_opl3sa2_init(void)
 #ifdef MODULE
                snd_printk(KERN_ERR "Yamaha OPL3-SA soundcard not found or device busy\n");
 #endif
-               err = -ENODEV;
-               goto errout;
+               snd_opl3sa2_unregister_all();
+               return -ENODEV;
        }
        return 0;
-
- errout:
-       snd_opl3sa2_unregister_all();
-       return err;
 }
 
 static void __exit alsa_card_opl3sa2_exit(void)
index 09384d03dc31f47e9b9a46e91254ba8ca6f70f2b..83d64bc07ff0f113fcf871d0d7e45f7b1ffffb48 100644 (file)
@@ -1436,8 +1436,11 @@ static int __init alsa_card_miro_init(void)
        if ((error = platform_driver_register(&snd_miro_driver)) < 0)
                return error;
        device = platform_device_register_simple(DRIVER_NAME, -1, NULL, 0);
-       if (! IS_ERR(device))
-               return 0;
+       if (! IS_ERR(device)) {
+               if (platform_get_drvdata(device))
+                       return 0;
+               platform_device_unregister(device);
+       }
 #ifdef MODULE
        printk(KERN_ERR "no miro soundcard found\n");
 #endif
index 65b28cbc0ebd75b5211e5cb3cb292e058e8e9239..8ee0d70536f9cc93998e37a26178004ed8768a89 100644 (file)
@@ -2099,8 +2099,11 @@ static int __init alsa_card_opti9xx_init(void)
                        return error;
                device = platform_device_register_simple(DRIVER_NAME, -1, NULL, 0);
                if (!IS_ERR(device)) {
-                       snd_opti9xx_platform_device = device;
-                       return 0;
+                       if (platform_get_drvdata(device)) {
+                               snd_opti9xx_platform_device = device;
+                               return 0;
+                       }
+                       platform_device_unregister(device);
                }
                platform_driver_unregister(&snd_opti9xx_driver);
        }
index 21ea65925a9eaf0b151450a069b1d69b76fecf2d..6333f900eaee63ec027d557d359dbea01e7fe8dc 100644 (file)
@@ -720,9 +720,11 @@ static int __init alsa_card_sb16_init(void)
                        continue;
                device = platform_device_register_simple(SND_SB16_DRIVER,
                                                         i, NULL, 0);
-               if (IS_ERR(device)) {
-                       err = PTR_ERR(device);
-                       goto errout;
+               if (IS_ERR(device))
+                       continue;
+               if (!platform_get_drvdata(device)) {
+                       platform_device_unregister(device);
+                       continue;
                }
                platform_devices[i] = device;
                cards++;
@@ -745,14 +747,10 @@ static int __init alsa_card_sb16_init(void)
                snd_printk(KERN_ERR "In case, if you have AWE card, try snd-sbawe module\n");
 #endif
 #endif
-               err = -ENODEV;
-               goto errout;
+               snd_sb16_unregister_all();
+               return -ENODEV;
        }
        return 0;
-
- errout:
-       snd_sb16_unregister_all();
-       return err;
 }
 
 static void __exit alsa_card_sb16_exit(void)
index 3efa23d303c3be07d96f16d60faefa79eba8c0ea..141400c014261aacffe3a42134ea34570c07a8fa 100644 (file)
@@ -264,9 +264,11 @@ static int __init alsa_card_sb8_init(void)
                        continue;
                device = platform_device_register_simple(SND_SB8_DRIVER,
                                                         i, NULL, 0);
-               if (IS_ERR(device)) {
-                       err = PTR_ERR(device);
-                       goto errout;
+               if (IS_ERR(device))
+                       continue;
+               if (!platform_get_drvdata(device)) {
+                       platform_device_unregister(device);
+                       continue;
                }
                devices[i] = device;
                cards++;
@@ -275,14 +277,10 @@ static int __init alsa_card_sb8_init(void)
 #ifdef MODULE
                snd_printk(KERN_ERR "Sound Blaster soundcard not found or device busy\n");
 #endif
-               err = -ENODEV;
-               goto errout;
+               snd_sb8_unregister_all();
+               return -ENODEV;
        }
        return 0;
-
- errout:
-       snd_sb8_unregister_all();
-       return err;
 }
 
 static void __exit alsa_card_sb8_exit(void)
index a60e66afbf90707c36f8cc56729cf3824beaa8b1..09c8e8c6b5e3cf8a548fdbec09660ca88eb70dfb 100644 (file)
@@ -366,9 +366,11 @@ static int __init alsa_card_sgalaxy_init(void)
                        continue;
                device = platform_device_register_simple(SND_SGALAXY_DRIVER,
                                                         i, NULL, 0);
-               if (IS_ERR(device)) {
-                       err = PTR_ERR(device);
-                       goto errout;
+               if (IS_ERR(device))
+                       continue;
+               if (!platform_get_drvdata(device)) {
+                       platform_device_unregister(device);
+                       continue;
                }
                devices[i] = device;
                cards++;
@@ -377,14 +379,10 @@ static int __init alsa_card_sgalaxy_init(void)
 #ifdef MODULE
                snd_printk(KERN_ERR "Sound Galaxy soundcard not found or device busy\n");
 #endif
-               err = -ENODEV;
-               goto errout;
+               snd_sgalaxy_unregister_all();
+               return -ENODEV;
        }
        return 0;
-
- errout:
-       snd_sgalaxy_unregister_all();
-       return err;
 }
 
 static void __exit alsa_card_sgalaxy_exit(void)
index 48e5552d34448bc562257a62613907469eedaac1..d2a856f0fde201d20e47da42d3960dea8d6537cd 100644 (file)
@@ -1427,8 +1427,8 @@ static int __init sscape_manual_probe(void)
                    dma[i] == SNDRV_AUTO_DMA) {
                        printk(KERN_INFO
                               "sscape: insufficient parameters, need IO, IRQ, MPU-IRQ and DMA\n");
-                       ret = -ENXIO;
-                       goto errout;
+                       sscape_unregister_all();
+                       return -ENXIO;
                }
 
                /*
@@ -1436,17 +1436,15 @@ static int __init sscape_manual_probe(void)
                 */
                device = platform_device_register_simple(SSCAPE_DRIVER,
                                                         i, NULL, 0);
-               if (IS_ERR(device)) {
-                       ret = PTR_ERR(device);
-                       goto errout;
+               if (IS_ERR(device))
+                       continue;
+               if (!platform_get_drvdata(device)) {
+                       platform_device_unregister(device);
+                       continue;
                }
                platform_devices[i] = device;
        }
        return 0;
-
- errout:
-       sscape_unregister_all();
-       return ret;
 }
 
 static void sscape_exit(void)
index 2f13cd5d4dcbc36bc152b3bf12308f0fd4a6bdb5..7ae86f82c3fa8b5852015c137950cedf93cf9322 100644 (file)
@@ -722,9 +722,11 @@ static int __init alsa_card_wavefront_init(void)
 #endif
                device = platform_device_register_simple(WAVEFRONT_DRIVER,
                                                         i, NULL, 0);
-               if (IS_ERR(device)) {
-                       err = PTR_ERR(device);
-                       goto errout;
+               if (IS_ERR(device))
+                       continue;
+               if (!platform_get_drvdata(device)) {
+                       platform_device_unregister(device);
+                       continue;
                }
                platform_devices[i] = device;
                cards++;
@@ -742,14 +744,10 @@ static int __init alsa_card_wavefront_init(void)
 #ifdef MODULE
                printk (KERN_ERR "No WaveFront cards found or devices busy\n");
 #endif
-               err = -ENODEV;
-               goto errout;
+               snd_wavefront_unregister_all();
+               return -ENODEV;
        }
        return 0;
-
- errout:
-       snd_wavefront_unregister_all();
-       return err;
 }
 
 static void __exit alsa_card_wavefront_exit(void)
index 88e52dc84c096b94514fd2e4ed76761edaceb42a..6275266dde2e754104badf084ce20003596a0d36 100644 (file)
@@ -5,23 +5,9 @@
 #
 # Prompt user for primary drivers.
 
-config OBSOLETE_OSS_DRIVER
-       bool "Obsolete OSS drivers"
-       depends on SOUND_PRIME
-       help
-         This option enables support for obsolete OSS drivers that
-         are scheduled for removal in the near future since there
-         are ALSA drivers for the same hardware.
-
-         Please contact Adrian Bunk <bunk@stusta.de> if you had to
-         say Y here because your soundcard is not properly supported
-         by ALSA.
-
-         If unsure, say N.
-
 config SOUND_BT878
        tristate "BT878 audio dma"
-       depends on SOUND_PRIME && PCI && OBSOLETE_OSS_DRIVER
+       depends on SOUND_PRIME && PCI
        ---help---
          Audio DMA support for bt878 based grabber boards.  As you might have
          already noticed, bt878 is listed with two functions in /proc/pci.
@@ -35,48 +21,9 @@ config SOUND_BT878
          To compile this driver as a module, choose M here: the module will
          be called btaudio.
 
-config SOUND_CMPCI
-       tristate "C-Media PCI (CMI8338/8738)"
-       depends on SOUND_PRIME && PCI && OBSOLETE_OSS_DRIVER
-       help
-         Say Y or M if you have a PCI sound card using the CMI8338
-         or the CMI8738 chipset.  Data on these chips are available at
-         <http://www.cmedia.com.tw/>.
-
-         A userspace utility to control some internal registers of these
-         chips is available at
-         <http://member.nifty.ne.jp/Breeze/softwares/unix/cmictl-e.html>.
-
-config SOUND_CMPCI_FM
-       bool "Enable legacy FM"
-       depends on SOUND_CMPCI && X86
-       help
-         Say Y here to enable the legacy FM (frequency-modulation) synthesizer
-         support on a card using the CMI8338 or CMI8378 chipset. Even it is
-         enabled, you need to set fmio as proper value to enable it.
-         Say N here if you don't need this.
-
-config SOUND_CMPCI_MIDI
-       bool "Enable legacy MPU-401"
-       depends on SOUND_CMPCI && X86
-       help
-         Say Y here to enable the legacy MPU401 MIDI synthesizer support on a
-         card using the CMI8338 or CMI8378 chipset. Even it is enabled,
-         you need to set mpuio as proper value to enable it.
-         Say N here if you don't need this.
-
-config SOUND_CMPCI_JOYSTICK
-       bool "Enable joystick"
-       depends on SOUND_CMPCI && X86 && (GAMEPORT=y || SOUND_CMPCI=GAMEPORT)
-       help
-         Say Y here in order to enable the joystick port on a sound card using
-         the CMI8338 or the CMI8738 chipset.  You need to config the
-         gameport support and set joystick parameter as 1 to use it.
-         Say N here if you don't need this.
-
 config SOUND_EMU10K1
        tristate "Creative SBLive! (EMU10K1)"
-       depends on SOUND_PRIME && PCI && OBSOLETE_OSS_DRIVER
+       depends on SOUND_PRIME && PCI
        ---help---
          Say Y or M if you have a PCI sound card using the EMU10K1 chipset,
          such as the Creative SBLive!, SB PCI512 or Emu-APS.
@@ -108,13 +55,6 @@ config SOUND_FUSION
          series) when wired as native sound drivers with AC97 codecs.  If
          this driver does not work try the CS4232 driver.
 
-config SOUND_CS4281
-       tristate "Crystal Sound CS4281"
-       depends on SOUND_PRIME && PCI && OBSOLETE_OSS_DRIVER
-       help
-         Picture and feature list at
-         <http://www.pcbroker.com/crystal4281.html>.
-
 config SOUND_BCM_CS4297A
        tristate "Crystal Sound CS4297a (for Swarm)"
        depends on SOUND_PRIME && SIBYTE_SWARM
@@ -125,22 +65,9 @@ config SOUND_BCM_CS4297A
          note that CONFIG_KGDB should not be enabled at the same
          time, since it also attempts to use this UART port.
 
-config SOUND_ES1370
-       tristate "Ensoniq AudioPCI (ES1370)"
-       depends on SOUND_PRIME && PCI && OBSOLETE_OSS_DRIVER
-       help
-         Say Y or M if you have a PCI sound card utilizing the Ensoniq
-         ES1370 chipset, such as Ensoniq's AudioPCI (non-97). To find
-         out if your sound card uses an ES1370 without removing your
-         computer's cover, use lspci -n and look for the PCI ID
-         1274:5000. Since Ensoniq was bought by Creative Labs,
-         Sound Blaster 64/PCI models are either ES1370 or ES1371 based.
-         This driver differs slightly from OSS/Free, so PLEASE READ
-         <file:Documentation/sound/oss/es1370>.
-
 config SOUND_ES1371
        tristate "Creative Ensoniq AudioPCI 97 (ES1371)"
-       depends on SOUND_PRIME && PCI && OBSOLETE_OSS_DRIVER
+       depends on SOUND_PRIME && PCI
        help
          Say Y or M if you have a PCI sound card utilizing the Ensoniq
          ES1371 chipset, such as Ensoniq's AudioPCI97. To find out if
@@ -151,33 +78,6 @@ config SOUND_ES1371
          slightly from OSS/Free, so PLEASE READ
          <file:Documentation/sound/oss/es1371>.
 
-config SOUND_ESSSOLO1
-       tristate "ESS Technology Solo1" 
-       depends on SOUND_PRIME && PCI && OBSOLETE_OSS_DRIVER
-       help
-         Say Y or M if you have a PCI sound card utilizing the ESS Technology
-         Solo1 chip. To find out if your sound card uses a
-         Solo1 chip without removing your computer's cover, use
-         lspci -n and look for the PCI ID 125D:1969. This driver
-         differs slightly from OSS/Free, so PLEASE READ
-         <file:Documentation/sound/oss/solo1>.
-
-config SOUND_MAESTRO
-       tristate "ESS Maestro, Maestro2, Maestro2E driver"
-       depends on SOUND_PRIME && PCI && OBSOLETE_OSS_DRIVER
-       help
-         Say Y or M if you have a sound system driven by ESS's Maestro line
-         of PCI sound chips.  These include the Maestro 1, Maestro 2, and
-         Maestro 2E.  See <file:Documentation/sound/oss/Maestro> for more
-         details.
-
-config SOUND_MAESTRO3
-       tristate "ESS Maestro3/Allegro driver (EXPERIMENTAL)"
-       depends on SOUND_PRIME && PCI && EXPERIMENTAL && OBSOLETE_OSS_DRIVER
-       help
-         Say Y or M if you have a sound system driven by ESS's Maestro 3
-         PCI sound chip.
-
 config SOUND_ICH
        tristate "Intel ICH (i8xx) audio support"
        depends on SOUND_PRIME && PCI
@@ -185,24 +85,6 @@ config SOUND_ICH
          Support for integral audio in Intel's I/O Controller Hub (ICH)
          chipset, as used on the 810/820/840 motherboards.
 
-config SOUND_HARMONY
-       tristate "PA Harmony audio driver"
-       depends on GSC_LASI && SOUND_PRIME && OBSOLETE_OSS_DRIVER
-       help
-         Say 'Y' or 'M' to include support for Harmony soundchip
-         on HP 712, 715/new and many other GSC based machines.
-
-config SOUND_SONICVIBES
-       tristate "S3 SonicVibes"
-       depends on SOUND_PRIME && PCI && OBSOLETE_OSS_DRIVER
-       help
-         Say Y or M if you have a PCI sound card utilizing the S3
-         SonicVibes chipset. To find out if your sound card uses a
-         SonicVibes chip without removing your computer's cover, use
-         lspci -n and look for the PCI ID 5333:CA00. This driver
-         differs slightly from OSS/Free, so PLEASE READ
-         <file:Documentation/sound/oss/sonicvibes>.
-
 config SOUND_VWSND
        tristate "SGI Visual Workstation Sound"
        depends on SOUND_PRIME && X86_VISWS
@@ -231,10 +113,6 @@ config SOUND_VRC5477
          integrated, multi-function controller chip for MIPS CPUs.  Works
          with the AC97 codec.
 
-config SOUND_AU1000
-       tristate "Au1000 Sound"
-       depends on SOUND_PRIME && (SOC_AU1000 || SOC_AU1100 || SOC_AU1500) && OBSOLETE_OSS_DRIVER
-
 config SOUND_AU1550_AC97
        tristate "Au1550 AC97 Sound"
        depends on SOUND_PRIME && SOC_AU1550
@@ -507,7 +385,7 @@ config MSND_FIFOSIZE
 
 config SOUND_VIA82CXXX
        tristate "VIA 82C686 Audio Codec"
-       depends on SOUND_PRIME && PCI && OBSOLETE_OSS_DRIVER
+       depends on SOUND_PRIME && PCI
        help
          Say Y here to include support for the audio codec found on VIA
          82Cxxx-based chips. Typically these are built into a motherboard.
@@ -576,18 +454,6 @@ config SOUND_AD1889
          Say M here if you have a sound card based on the Analog Devices
          AD1889 chip.
 
-config SOUND_SGALAXY
-       tristate "Aztech Sound Galaxy (non-PnP) cards"
-       depends on SOUND_OSS && OBSOLETE_OSS_DRIVER
-       help
-         This module initializes the older non Plug and Play sound galaxy
-         cards from Aztech. It supports the Waverider Pro 32 - 3D and the
-         Galaxy Washington 16.
-
-         If you compile the driver into the kernel, you have to add
-         "sgalaxy=<io>,<irq>,<dma>,<dma2>,<sgbase>" to the kernel command
-         line.
-
 config SOUND_ADLIB
        tristate "Adlib Cards"
        depends on SOUND_OSS
@@ -612,56 +478,6 @@ config SOUND_ACI_MIXER
 
          This driver is also available as a module and will be called aci.
 
-config SOUND_CS4232
-       tristate "Crystal CS4232 based (PnP) cards"
-       depends on SOUND_OSS && OBSOLETE_OSS_DRIVER
-       help
-         Say Y here if you have a card based on the Crystal CS4232 chip set,
-         which uses its own Plug and Play protocol.
-
-         If you compile the driver into the kernel, you have to add
-         "cs4232=<io>,<irq>,<dma>,<dma2>,<mpuio>,<mpuirq>" to the kernel
-         command line.
-
-         See <file:Documentation/sound/oss/CS4232> for more information on
-         configuring this card.
-
-config SOUND_SSCAPE
-       tristate "Ensoniq SoundScape support"
-       depends on SOUND_OSS && OBSOLETE_OSS_DRIVER
-       help
-         Answer Y if you have a sound card based on the Ensoniq SoundScape
-         chipset. Such cards are being manufactured at least by Ensoniq, Spea
-         and Reveal (Reveal makes also other cards).
-
-         If you compile the driver into the kernel, you have to add
-         "sscape=<io>,<irq>,<dma>,<mpuio>,<mpuirq>" to the kernel command
-         line.
-
-config SOUND_GUS
-       tristate "Gravis Ultrasound support"
-       depends on SOUND_OSS && OBSOLETE_OSS_DRIVER
-       help
-         Say Y here for any type of Gravis Ultrasound card, including the GUS
-         or GUS MAX.  See also <file:Documentation/sound/oss/ultrasound> for more
-         information on configuring this card with modules.
-
-         If you compile the driver into the kernel, you have to add
-         "gus=<io>,<irq>,<dma>,<dma2>" to the kernel command line.
-
-config SOUND_GUS16
-       bool "16 bit sampling option of GUS (_NOT_ GUS MAX)"
-       depends on SOUND_GUS
-       help
-         Support for Gravis Ulstrasound (GUS) cards (other than the GUS),
-         sampling at 16-bit width.
-
-config SOUND_GUSMAX
-       bool "GUS MAX support"
-       depends on SOUND_GUS
-       help
-         Support for Gravis Ulstrasound MAX.
-
 config SOUND_VMIDI
        tristate "Loopback MIDI device support"
        depends on SOUND_OSS
@@ -742,7 +558,7 @@ config SOUND_MPU401
 
 config SOUND_NM256
        tristate "NM256AV/NM256ZX audio support"
-       depends on SOUND_OSS && OBSOLETE_OSS_DRIVER
+       depends on SOUND_OSS
        help
          Say M here to include audio support for the NeoMagic 256AV/256ZX
          chipsets. These are the audio chipsets found in the Sony
@@ -752,35 +568,6 @@ config SOUND_NM256
 
          See <file:Documentation/sound/oss/NM256> for further information.
 
-config SOUND_MAD16
-       tristate "OPTi MAD16 and/or Mozart based cards"
-       depends on SOUND_OSS && OBSOLETE_OSS_DRIVER
-       ---help---
-         Answer Y if your card has a Mozart (OAK OTI-601) or MAD16 (OPTi
-         82C928 or 82C929 or 82C931) audio interface chip. These chips are
-         quite common so it's possible that many no-name cards have one of
-         them. In addition the MAD16 chip is used in some cards made by known
-         manufacturers such as Turtle Beach (Tropez), Reveal (some models)
-         and Diamond (latest ones). Note however that the Tropez sound cards
-         have their own driver; if you have one of those, say N here and Y or
-         M to "Full support for Turtle Beach WaveFront", below.
-
-         If you compile the driver into the kernel, you have to add
-         "mad16=<io>,<irq>,<dma>,<dma2>,<mpuio>,<mpuirq>" to the
-         kernel command line.
-
-         See also <file:Documentation/sound/oss/Opti> and
-         <file:Documentation/sound/oss/MAD16> for more information on setting
-         these cards up as modules.
-
-config MAD16_OLDCARD
-       bool "Support MIDI in older MAD16 based cards (requires SB)"
-       depends on SOUND_MAD16
-       help
-         Answer Y (or M) if you have an older card based on the C928 or
-         Mozart chipset and you want to have MIDI support. If you enable this
-         option you also need to enable support for Sound Blaster.
-
 config SOUND_PAS
        tristate "ProAudioSpectrum 16 support"
        depends on SOUND_OSS
@@ -873,53 +660,9 @@ config SOUND_SB
          You can say M here to compile this driver as a module; the module is
          called sb.
 
-config SOUND_AWE32_SYNTH
-       tristate "AWE32 synth"
-       depends on SOUND_OSS && OBSOLETE_OSS_DRIVER
-       help
-         Say Y here if you have a Sound Blaster SB32, AWE32-PnP, SB AWE64 or
-         similar sound card. See <file:Documentation/sound/oss/README.awe>,
-         <file:Documentation/sound/oss/AWE32> and the Soundblaster-AWE
-         mini-HOWTO, available from <http://www.tldp.org/docs.html#howto>
-         for more info.
-
-config SOUND_WAVEFRONT
-       tristate "Full support for Turtle Beach WaveFront (Tropez Plus, Tropez, Maui) synth/soundcards"
-       depends on SOUND_OSS && m && OBSOLETE_OSS_DRIVER
-       help
-         Answer Y or M if you have a Tropez Plus, Tropez or Maui sound card
-         and read the files <file:Documentation/sound/oss/Wavefront> and
-         <file:Documentation/sound/oss/Tropez+>.
-
-config SOUND_MAUI
-       tristate "Limited support for Turtle Beach Wave Front (Maui, Tropez) synthesizers"
-       depends on SOUND_OSS && OBSOLETE_OSS_DRIVER
-       help
-         Say Y here if you have a Turtle Beach Wave Front, Maui, or Tropez
-         sound card.
-
-         If you compile the driver into the kernel, you have to add
-         "maui=<io>,<irq>" to the kernel command line.
-
-config MAUI_HAVE_BOOT
-       bool "Have OSWF.MOT firmware file"
-       depends on SOUND_MAUI=y && !STANDALONE
-       help
-         Turtle Beach Maui and Tropez sound cards have a microcontroller
-         which needs to be initialized prior to use. OSWF.MOT is a file
-         distributed with the card's DOS/Windows drivers. Answer Y if you
-         have this file.
-
-config MAUI_BOOT_FILE
-       string "Full pathname of OSWF.MOT firmware file"
-       depends on MAUI_HAVE_BOOT
-       default "/etc/sound/oswf.mot"
-       help
-         Enter the full pathname of your OSWF.MOT file, starting from /.
-
 config SOUND_YM3812
        tristate "Yamaha FM synthesizer (YM3812/OPL-3) support"
-       depends on SOUND_OSS && OBSOLETE_OSS_DRIVER
+       depends on SOUND_OSS
        ---help---
          Answer Y if your card has a FM chip made by Yamaha (OPL2/OPL3/OPL4).
          Answering Y is usually a safe and recommended choice, however some
@@ -933,18 +676,6 @@ config SOUND_YM3812
 
          If unsure, say Y.
 
-config SOUND_OPL3SA1
-       tristate "Yamaha OPL3-SA1 audio controller"
-       depends on SOUND_OSS && OBSOLETE_OSS_DRIVER
-       help
-         Say Y or M if you have a Yamaha OPL3-SA1 sound chip, which is
-         usually built into motherboards. Read
-         <file:Documentation/sound/oss/OPL3-SA> for details.
-
-         If you compile the driver into the kernel, you have to add
-         "opl3sa=<io>,<irq>,<dma>,<dma2>,<mpuio>,<mpuirq>" to the kernel
-         command line.
-
 config SOUND_OPL3SA2
        tristate "Yamaha OPL3-SA2 and SA3 based PnP cards"
        depends on SOUND_OSS
@@ -959,19 +690,6 @@ config SOUND_OPL3SA2
          "opl3sa2=<io>,<irq>,<dma>,<dma2>,<mssio>,<mpuio>" to the kernel
          command line.
 
-config SOUND_YMFPCI
-       tristate "Yamaha YMF7xx PCI audio (native mode)"
-       depends on SOUND_OSS && PCI && OBSOLETE_OSS_DRIVER
-       help
-         Support for Yamaha cards including the YMF711, YMF715, YMF718,
-         YMF719, YMF724, Waveforce 192XG, and Waveforce 192 Digital.
-
-config SOUND_YMFPCI_LEGACY
-       bool "Yamaha PCI legacy ports support"
-       depends on SOUND_YMFPCI
-       help
-         Support for YMF7xx PCI cards emulating an MP401.
-
 config SOUND_UART6850
        tristate "6850 UART support"
        depends on SOUND_OSS
@@ -1101,30 +819,6 @@ config SOUND_KAHLUA
        tristate "XpressAudio Sound Blaster emulation"
        depends on SOUND_SB
 
-config SOUND_ALI5455
-       tristate "ALi5455 audio support"
-       depends on SOUND_PRIME && PCI && OBSOLETE_OSS_DRIVER
-
-config SOUND_FORTE
-       tristate "ForteMedia FM801 driver"
-       depends on SOUND_PRIME && PCI && OBSOLETE_OSS_DRIVER
-       help
-         Say Y or M if you want driver support for the ForteMedia FM801 PCI
-         audio controller (Abit AU10, Genius Sound Maker, HP Workstation
-         zx2000, and others).
-
-config SOUND_RME96XX
-       tristate "RME Hammerfall (RME96XX) support"
-       depends on SOUND_PRIME && PCI && OBSOLETE_OSS_DRIVER
-       help
-         Say Y or M if you have a Hammerfall or Hammerfall light
-         multichannel card from RME. If you want to access advanced
-         features of the card, read <file:Documentation/sound/oss/rme96xx>.
-
-config SOUND_AD1980
-       tristate "AD1980 front/back switch plugin"
-       depends on SOUND_PRIME && OBSOLETE_OSS_DRIVER
-
 config SOUND_SH_DAC_AUDIO
        tristate "SuperH DAC audio support"
        depends on SOUND_PRIME && CPU_SH3
index 0cd44a6f7ac069c9e3ba322f5a94c23526b3940d..3721c5857b9048eb76f655e01360e76d08580179 100644 (file)
@@ -94,6 +94,7 @@
 #include <linux/init.h>
 #include <linux/delay.h>
 #include <linux/proc_fs.h>
+#include <linux/dma-mapping.h>
 
 #include "hwaccess.h"
 #include "8010.h"
  
 
 /* the emu10k1 _seems_ to only supports 29 bit (512MiB) bit bus master */
-#define EMU10K1_DMA_MASK                0x1fffffff     /* DMA buffer mask for pci_alloc_consist */
+#define EMU10K1_DMA_MASK DMA_29BIT_MASK        /* DMA buffer mask for pci_alloc_consist */
 
 #ifndef PCI_VENDOR_ID_CREATIVE
 #define PCI_VENDOR_ID_CREATIVE 0x1102
index 278319bbdea19b0dceb94aa421ab102120dd0b87..d05200741ac3767538b0c91efe75829619f9ad73 100644 (file)
@@ -160,6 +160,7 @@ static const struct ac97_codec_id snd_ac97_codec_ids[] = {
 { 0x54584e20, 0xffffffff, "TLC320AD9xC",       NULL,           NULL },
 { 0x56494161, 0xffffffff, "VIA1612A",          NULL,           NULL }, // modified ICE1232 with S/PDIF
 { 0x56494170, 0xffffffff, "VIA1617A",          patch_vt1617a,  NULL }, // modified VT1616 with S/PDIF
+{ 0x56494182, 0xffffffff, "VIA1618",           NULL,           NULL },
 { 0x57454301, 0xffffffff, "W83971D",           NULL,           NULL },
 { 0x574d4c00, 0xffffffff, "WM9701A",           NULL,           NULL },
 { 0x574d4C03, 0xffffffff, "WM9703,WM9707,WM9708,WM9717", patch_wolfson03, NULL},
index 37b80570a5c6e471ca7265d505b4f0177ec32711..91899f87f0376ca7ffe95e66430e530da74d6aaa 100644 (file)
@@ -35,6 +35,7 @@
 #include <linux/init.h>
 #include <linux/moduleparam.h>
 #include <linux/pci.h>
+#include <linux/dma-mapping.h>
 #include <linux/interrupt.h>
 #include <linux/slab.h>
 
@@ -691,8 +692,8 @@ static int __devinit snd_als300_create(snd_card_t *card,
        if ((err = pci_enable_device(pci)) < 0)
                return err;
 
-       if (pci_set_dma_mask(pci, 0x0fffffff) < 0 ||
-               pci_set_consistent_dma_mask(pci, 0x0fffffff) < 0) {
+       if (pci_set_dma_mask(pci, DMA_28BIT_MASK) < 0 ||
+               pci_set_consistent_dma_mask(pci, DMA_28BIT_MASK) < 0) {
                printk(KERN_ERR "error setting 28bit DMA mask\n");
                pci_disable_device(pci);
                return -ENXIO;
index d65ccb1866a0204f5fd241816a4149edc6934a06..f078b716d2b05e2b06f7180437cf465ac7b2e80b 100644 (file)
@@ -19,7 +19,6 @@
 
 #ifdef __KERNEL__
 #include <sound/driver.h>
-#include <linux/init.h>
 #include <linux/pci.h>
 #include <asm/io.h>
 #include <sound/core.h>
@@ -277,14 +276,14 @@ static void vortex_Vort3D_InitializeSource(a3dsrc_t * a, int en);
 #endif
 
 /* Driver stuff. */
-static int __devinit vortex_gameport_register(vortex_t * card);
+static int vortex_gameport_register(vortex_t * card);
 static void vortex_gameport_unregister(vortex_t * card);
 #ifndef CHIP_AU8820
-static int __devinit vortex_eq_init(vortex_t * vortex);
-static int __devexit vortex_eq_free(vortex_t * vortex);
+static int vortex_eq_init(vortex_t * vortex);
+static int vortex_eq_free(vortex_t * vortex);
 #endif
 /* ALSA stuff. */
-static int __devinit snd_vortex_new_pcm(vortex_t * vortex, int idx, int nr);
-static int __devinit snd_vortex_mixer(vortex_t * vortex);
-static int __devinit snd_vortex_midi(vortex_t * vortex);
+static int snd_vortex_new_pcm(vortex_t * vortex, int idx, int nr);
+static int snd_vortex_mixer(vortex_t * vortex);
+static int snd_vortex_midi(vortex_t * vortex);
 #endif
index 9cac02e93b25611c60490deb0de769c3974830ec..4347e6abc1d5402765ebb6bf93b8243801efbfe0 100644 (file)
@@ -2658,7 +2658,7 @@ static void vortex_spdif_init(vortex_t * vortex, int spdif_sr, int spdif_mode)
 
 /* Initialization */
 
-static int vortex_core_init(vortex_t * vortex)
+static int __devinit vortex_core_init(vortex_t * vortex)
 {
 
        printk(KERN_INFO "Vortex: init.... ");
index 64fbfbbaf816f650bb9d8233de7b5ef38f510f00..0c86a31c43362c0fb5401c116c815de25cd87b00 100644 (file)
@@ -885,7 +885,7 @@ static char *EqBandLabels[10] __devinitdata = {
 };
 
 /* ALSA driver entry points. Init and exit. */
-static int vortex_eq_init(vortex_t * vortex)
+static int __devinit vortex_eq_init(vortex_t * vortex)
 {
        struct snd_kcontrol *kcontrol;
        int err, i;
index 6a13ca1d545e311980eddc0ba75be8c00b111fdf..7b5baa1738597b61e5785bcc270bb12b8ddae753 100644 (file)
@@ -506,7 +506,7 @@ static int __devinit snd_vortex_new_pcm(vortex_t * chip, int idx, int nr)
        int i;
        int err, nr_capt;
 
-       if ((chip == 0) || (idx < 0) || (idx > VORTEX_PCM_LAST))
+       if ((chip == 0) || (idx < 0) || (idx >= VORTEX_PCM_LAST))
                return -ENODEV;
 
        /* idx indicates which kind of PCM device. ADB, SPDIF, I2S and A3D share the 
index 31cb9b48bb593a5bcdccd2169ab610446e6ffa52..6bfa08436efa251b3c93aa77df2cdb539360b6e9 100644 (file)
@@ -843,8 +843,11 @@ static struct snd_emu_chip_details emu_chip_details[] = {
         .spdif_bug = 1,
         .ac97_chip = 1} ,
        /* Tested by shane-alsa@cm.nu 5th Nov 2005 */
+       /* The 0x20061102 does have SB0350 written on it
+        * Just like 0x20021102
+        */
        {.vendor = 0x1102, .device = 0x0004, .subsystem = 0x20061102,
-        .driver = "Audigy2", .name = "Audigy 2 [2006]", 
+        .driver = "Audigy2", .name = "Audigy 2 [SB0350b]", 
         .id = "Audigy2",
         .emu10k2_chip = 1,
         .ca0102_chip = 1,
index 2bfe37e8543cd75fad840821505fb57f2fd11498..bcfca159c6a2342f3071d6631cc3d24f8349c762 100644 (file)
@@ -801,6 +801,10 @@ static struct hda_board_config ad1986a_cfg_tbl[] = {
          .config = AD1986A_LAPTOP_EAPD }, /* Samsung R65-T2300 Charis */
        { .pci_subvendor = 0x1043, .pci_subdevice = 0x1213,
          .config = AD1986A_LAPTOP_EAPD }, /* ASUS A6J */
+       { .pci_subvendor = 0x1043, .pci_subdevice = 0x11f7,
+         .config = AD1986A_LAPTOP_EAPD }, /* ASUS U5A */
+       { .pci_subvendor = 0x103c, .pci_subdevice = 0x30af,
+         .config = AD1986A_LAPTOP_EAPD }, /* HP Compaq Presario B2800 */
        {}
 };
 
@@ -1330,6 +1334,8 @@ static struct hda_board_config ad1981_cfg_tbl[] = {
          .config = AD1981_HP }, /* HP nx6320 */
        { .pci_subvendor = 0x103c, .pci_subdevice = 0x309f,
          .config = AD1981_HP }, /* HP nx9420 AngelFire */
+       { .pci_subvendor = 0x103c, .pci_subdevice = 0x30a2,
+         .config = AD1981_HP }, /* HP nx9420 AngelFire */
        { .modelname = "basic", .config = AD1981_BASIC },
        {}
 };
index abe9493f0a2cac97246c026f48c7636043d25f12..7152607879539a8bf4be5e25060c810a82da5985 100644 (file)
@@ -310,6 +310,9 @@ static struct hda_board_config stac922x_cfg_tbl[] = {
          .pci_subdevice = 0x0b0b,
          .config = STAC_D945GTP3 },    /* Intel D945PSN - 3 Stack, 9221 A1 */
        { .pci_subvendor = PCI_VENDOR_ID_INTEL,
+         .pci_subdevice = 0x0707,
+         .config = STAC_D945GTP5 },    /* Intel D945PSV - 5 Stack */
+       { .pci_subvendor = PCI_VENDOR_ID_INTEL,
          .pci_subdevice = 0x0404,
          .config = STAC_D945GTP5 },    /* Intel D945GTP - 5 Stack */
        { .pci_subvendor = PCI_VENDOR_ID_INTEL,
index 1e7398de2865f94cf4f46f29581a654061dc494d..0f171dd1377b00bc3034b712f4f1d8f6f804b516 100644 (file)
@@ -2333,6 +2333,7 @@ static int __devinit check_dxs_list(struct pci_dev *pci)
                { .subvendor = 0x1019, .subdevice = 0x0a81, .action = VIA_DXS_NO_VRA }, /* ECS K7VTA3 v8.0 */
                { .subvendor = 0x1019, .subdevice = 0x0a85, .action = VIA_DXS_NO_VRA }, /* ECS L7VMM2 */
                { .subvendor = 0x1019, .subdevice = 0xa101, .action = VIA_DXS_SRC },
+               { .subvendor = 0x1019, .subdevice = 0xaa01, .action = VIA_DXS_SRC }, /* ECS K8T890-A */
                { .subvendor = 0x1025, .subdevice = 0x0033, .action = VIA_DXS_NO_VRA }, /* Acer Inspire 1353LM */
                { .subvendor = 0x1025, .subdevice = 0x0046, .action = VIA_DXS_SRC }, /* Acer Aspire 1524 WLMi */
                { .subvendor = 0x1043, .subdevice = 0x8095, .action = VIA_DXS_NO_VRA }, /* ASUS A7V8X (FIXME: possibly VIA_DXS_ENABLE?)*/
index e2129cb570bba89a6790afaa045e7aad65300f34..19d74e6f2685e11494d7dfdf66eb4c125d4d4c8d 100644 (file)
@@ -1,65 +1,48 @@
+#
+# kbuild file for usr/ - including initramfs image
+#
 
-obj-y := initramfs_data.o
-
-hostprogs-y  := gen_init_cpio
+klibcdirs:;
 
-clean-files := initramfs_data.cpio.gz initramfs_list
+# Generate builtin.o based on initramfs_data.o
+obj-y := initramfs_data.o
 
 # initramfs_data.o contains the initramfs_data.cpio.gz image.
 # The image is included using .incbin, a dependency which is not
 # tracked automatically.
 $(obj)/initramfs_data.o: $(obj)/initramfs_data.cpio.gz FORCE
 
-ifdef CONFIG_INITRAMFS_ROOT_UID
-gen_initramfs_args += -u $(CONFIG_INITRAMFS_ROOT_UID)
-endif
-
-ifdef CONFIG_INITRAMFS_ROOT_GID
-gen_initramfs_args += -g $(CONFIG_INITRAMFS_ROOT_GID)
-endif
-
-# The $(shell echo $(CONFIG_INITRAMFS_SOURCE)) is to remove the
-# gratuitous begin and end quotes from the Kconfig string type.
-# Internal, escaped quotes in the Kconfig string will loose the
-# escape and become active quotes.
-quotefixed_initramfs_source := $(shell echo $(CONFIG_INITRAMFS_SOURCE))
-
-filechk_initramfs_list = $(CONFIG_SHELL) \
- $(srctree)/scripts/gen_initramfs_list.sh $(gen_initramfs_args) $(quotefixed_initramfs_source)
-
-$(obj)/initramfs_list: $(obj)/Makefile FORCE
-       $(call filechk,initramfs_list)
-
-quiet_cmd_cpio = CPIO    $@
-      cmd_cpio = ./$< $(obj)/initramfs_list > $@
-
-
-# Check if the INITRAMFS_SOURCE is a cpio archive
-ifneq (,$(findstring .cpio,$(quotefixed_initramfs_source)))
-
-# INITRAMFS_SOURCE has a cpio archive - verify that it's a single file
-ifneq (1,$(words $(quotefixed_initramfs_source)))
-$(error Only a single file may be specified in CONFIG_INITRAMFS_SOURCE (="$(quotefixed_initramfs_source)") when a cpio archive is directly specified.)
-endif
-# Now use the cpio archive directly
-initramfs_data_cpio = $(quotefixed_initramfs_source)
-targets += $(quotefixed_initramfs_source)
-
-else
-
-# INITRAMFS_SOURCE is not a cpio archive - create one
-$(obj)/initramfs_data.cpio: $(obj)/gen_init_cpio \
-                            $(initramfs-y) $(obj)/initramfs_list FORCE
-       $(call if_changed,cpio)
-
-targets += initramfs_data.cpio
-initramfs_data_cpio = $(obj)/initramfs_data.cpio
-
+#####
+# Generate the initramfs cpio archive
+
+hostprogs-y := gen_init_cpio
+initramfs   := $(CONFIG_SHELL) $(srctree)/scripts/gen_initramfs_list.sh
+ramfs-input := $(if $(filter-out "",$(CONFIG_INITRAMFS_SOURCE)), \
+                    $(CONFIG_INITRAMFS_SOURCE),-d)
+ramfs-args  := \
+        $(if $(CONFIG_INITRAMFS_ROOT_UID), -u $(CONFIG_INITRAMFS_ROOT_UID)) \
+        $(if $(CONFIG_INITRAMFS_ROOT_GID), -g $(CONFIG_INITRAMFS_ROOT_GID)) \
+        $(ramfs-input)
+
+# .initramfs_data.cpio.gz.d is used to identify all files included
+# in initramfs and to detect if any files are added/removed.
+# Removed files are identified by directory timestamp being updated
+# The dependency list is generated by gen_initramfs.sh -l
+ifneq ($(wildcard $(obj)/.initramfs_data.cpio.gz.d),)
+       include $(obj)/.initramfs_data.cpio.gz.d
 endif
 
-
-$(obj)/initramfs_data.cpio.gz: $(initramfs_data_cpio) FORCE
-       $(call if_changed,gzip)
-
-targets += initramfs_data.cpio.gz
+quiet_cmd_initfs = GEN     $@
+      cmd_initfs = $(initramfs) -o $@ $(ramfs-args) $(ramfs-input)
+
+targets := initramfs_data.cpio.gz
+$(deps_initramfs): klibcdirs
+# We rebuild initramfs_data.cpio.gz if:
+# 1) Any included file is newer then initramfs_data.cpio.gz
+# 2) There are changes in which files are included (added or deleted)
+# 3) If gen_init_cpio are newer than initramfs_data.cpio.gz
+# 4) arguments to gen_initramfs.sh changes
+$(obj)/initramfs_data.cpio.gz: $(obj)/gen_init_cpio $(deps_initramfs) klibcdirs
+       $(Q)$(initramfs) -l $(ramfs-input) > $(obj)/.initramfs_data.cpio.gz.d
+       $(call if_changed,initfs)
 
index 33dbcbf77c5b0d5713d4c6774e5c7f863d4750fb..83acd6cc0b3cd70325ec383eb8fdc309918a0a98 100644 (file)
@@ -471,6 +471,7 @@ int main (int argc, char *argv[])
                                "ERROR: incorrect format, could not locate file type line %d: '%s'\n",
                                line_nr, line);
                        ec = -1;
+                       break;
                }
 
                if ('\n' == *type) {
@@ -506,7 +507,8 @@ int main (int argc, char *argv[])
                                line_nr, line);
                }
        }
-       cpio_trailer();
+       if (ec == 0)
+               cpio_trailer();
 
        exit(ec);
 }