2008-01-16 18:03:59

by Arnd Hannemann

[permalink] [raw]
Subject: 2.6.24-rc8 hangs at mfgpt-timer

#
# Automatically generated make config: don't edit
# Linux kernel version: 2.6.24-rc8
# Wed Jan 16 17:27:41 2008
#
# CONFIG_64BIT is not set
CONFIG_X86_32=y
# CONFIG_X86_64 is not set
CONFIG_X86=y
CONFIG_GENERIC_TIME=y
CONFIG_GENERIC_CMOS_UPDATE=y
CONFIG_CLOCKSOURCE_WATCHDOG=y
CONFIG_GENERIC_CLOCKEVENTS=y
CONFIG_LOCKDEP_SUPPORT=y
CONFIG_STACKTRACE_SUPPORT=y
CONFIG_SEMAPHORE_SLEEPERS=y
CONFIG_MMU=y
CONFIG_ZONE_DMA=y
CONFIG_QUICKLIST=y
CONFIG_GENERIC_ISA_DMA=y
CONFIG_GENERIC_IOMAP=y
CONFIG_GENERIC_BUG=y
CONFIG_GENERIC_HWEIGHT=y
CONFIG_ARCH_MAY_HAVE_PC_FDC=y
CONFIG_DMI=y
# CONFIG_RWSEM_GENERIC_SPINLOCK is not set
CONFIG_RWSEM_XCHGADD_ALGORITHM=y
# CONFIG_ARCH_HAS_ILOG2_U32 is not set
# CONFIG_ARCH_HAS_ILOG2_U64 is not set
CONFIG_GENERIC_CALIBRATE_DELAY=y
# CONFIG_GENERIC_TIME_VSYSCALL is not set
CONFIG_ARCH_SUPPORTS_OPROFILE=y
# CONFIG_ZONE_DMA32 is not set
CONFIG_ARCH_POPULATES_NODE_MAP=y
# CONFIG_AUDIT_ARCH is not set
CONFIG_GENERIC_HARDIRQS=y
CONFIG_GENERIC_IRQ_PROBE=y
CONFIG_X86_BIOS_REBOOT=y
CONFIG_KTIME_SCALAR=y
CONFIG_DEFCONFIG_LIST="/lib/modules/$UNAME_RELEASE/.config"

#
# General setup
#
CONFIG_EXPERIMENTAL=y
CONFIG_BROKEN_ON_SMP=y
CONFIG_INIT_ENV_ARG_LIMIT=32
CONFIG_LOCALVERSION=""
CONFIG_LOCALVERSION_AUTO=y
# CONFIG_SWAP is not set
CONFIG_SYSVIPC=y
CONFIG_SYSVIPC_SYSCTL=y
CONFIG_POSIX_MQUEUE=y
CONFIG_BSD_PROCESS_ACCT=y
# CONFIG_BSD_PROCESS_ACCT_V3 is not set
# CONFIG_TASKSTATS is not set
# CONFIG_USER_NS is not set
# CONFIG_PID_NS is not set
CONFIG_AUDIT=y
CONFIG_AUDITSYSCALL=y
CONFIG_AUDIT_TREE=y
# CONFIG_IKCONFIG is not set
CONFIG_LOG_BUF_SHIFT=14
# CONFIG_CGROUPS is not set
# CONFIG_FAIR_GROUP_SCHED is not set
CONFIG_SYSFS_DEPRECATED=y
# CONFIG_RELAY is not set
CONFIG_BLK_DEV_INITRD=y
CONFIG_INITRAMFS_SOURCE=""
# CONFIG_CC_OPTIMIZE_FOR_SIZE is not set
CONFIG_SYSCTL=y
# CONFIG_EMBEDDED is not set
CONFIG_UID16=y
CONFIG_SYSCTL_SYSCALL=y
CONFIG_KALLSYMS=y
# CONFIG_KALLSYMS_ALL is not set
# CONFIG_KALLSYMS_EXTRA_PASS is not set
CONFIG_HOTPLUG=y
CONFIG_PRINTK=y
CONFIG_BUG=y
CONFIG_ELF_CORE=y
CONFIG_BASE_FULL=y
CONFIG_FUTEX=y
CONFIG_ANON_INODES=y
CONFIG_EPOLL=y
CONFIG_SIGNALFD=y
CONFIG_EVENTFD=y
CONFIG_SHMEM=y
CONFIG_VM_EVENT_COUNTERS=y
CONFIG_SLAB=y
# CONFIG_SLUB is not set
# CONFIG_SLOB is not set
CONFIG_SLABINFO=y
CONFIG_RT_MUTEXES=y
# CONFIG_TINY_SHMEM is not set
CONFIG_BASE_SMALL=0
CONFIG_MODULES=y
CONFIG_MODULE_UNLOAD=y
CONFIG_MODULE_FORCE_UNLOAD=y
# CONFIG_MODVERSIONS is not set
# CONFIG_MODULE_SRCVERSION_ALL is not set
CONFIG_KMOD=y
CONFIG_BLOCK=y
# CONFIG_LBD is not set
# CONFIG_BLK_DEV_IO_TRACE is not set
# CONFIG_LSF is not set
# CONFIG_BLK_DEV_BSG 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"

#
# Processor type and features
#
CONFIG_TICK_ONESHOT=y
CONFIG_NO_HZ=y
CONFIG_HIGH_RES_TIMERS=y
CONFIG_GENERIC_CLOCKEVENTS_BUILD=y
# CONFIG_SMP is not set
CONFIG_X86_PC=y
# CONFIG_X86_ELAN is not set
# CONFIG_X86_VOYAGER is not set
# CONFIG_X86_NUMAQ is not set
# CONFIG_X86_SUMMIT is not set
# CONFIG_X86_BIGSMP is not set
# CONFIG_X86_VISWS is not set
# CONFIG_X86_GENERICARCH is not set
# CONFIG_X86_ES7000 is not set
# CONFIG_X86_VSMP is not set
CONFIG_SCHED_NO_NO_OMIT_FRAME_POINTER=y
# CONFIG_PARAVIRT_GUEST is not set
# CONFIG_M386 is not set
# CONFIG_M486 is not set
# CONFIG_M586 is not set
# CONFIG_M586TSC is not set
# CONFIG_M586MMX is not set
# CONFIG_M686 is not set
# CONFIG_MPENTIUMII is not set
# CONFIG_MPENTIUMIII is not set
# CONFIG_MPENTIUMM is not set
# CONFIG_MPENTIUM4 is not set
# CONFIG_MK6 is not set
# CONFIG_MK7 is not set
# CONFIG_MK8 is not set
# CONFIG_MCRUSOE is not set
# CONFIG_MEFFICEON is not set
# CONFIG_MWINCHIPC6 is not set
# CONFIG_MWINCHIP2 is not set
# CONFIG_MWINCHIP3D is not set
# CONFIG_MGEODEGX1 is not set
CONFIG_MGEODE_LX=y
# CONFIG_MCYRIXIII is not set
# CONFIG_MVIAC3_2 is not set
# CONFIG_MVIAC7 is not set
# CONFIG_MPSC is not set
# CONFIG_MCORE2 is not set
# CONFIG_GENERIC_CPU is not set
# CONFIG_X86_GENERIC is not set
CONFIG_X86_CMPXCHG=y
CONFIG_X86_L1_CACHE_SHIFT=5
CONFIG_X86_XADD=y
CONFIG_X86_WP_WORKS_OK=y
CONFIG_X86_INVLPG=y
CONFIG_X86_BSWAP=y
CONFIG_X86_POPAD_OK=y
CONFIG_X86_USE_PPRO_CHECKSUM=y
CONFIG_X86_USE_3DNOW=y
CONFIG_X86_TSC=y
CONFIG_X86_MINIMUM_CPU_FAMILY=4
CONFIG_HPET_TIMER=y
CONFIG_HPET_EMULATE_RTC=y
# CONFIG_PREEMPT_NONE is not set
CONFIG_PREEMPT_VOLUNTARY=y
# CONFIG_PREEMPT is not set
# CONFIG_X86_UP_APIC is not set
CONFIG_X86_MCE=y
CONFIG_X86_MCE_NONFATAL=y
CONFIG_VM86=y
# CONFIG_TOSHIBA is not set
# CONFIG_I8K is not set
# CONFIG_X86_REBOOTFIXUPS is not set
# CONFIG_MICROCODE is not set
# CONFIG_X86_MSR is not set
# CONFIG_X86_CPUID is not set
CONFIG_NOHIGHMEM=y
# CONFIG_HIGHMEM4G is not set
# CONFIG_HIGHMEM64G is not set
CONFIG_PAGE_OFFSET=0xC0000000
# CONFIG_X86_PAE is not set
CONFIG_ARCH_FLATMEM_ENABLE=y
CONFIG_ARCH_SPARSEMEM_ENABLE=y
CONFIG_ARCH_SELECT_MEMORY_MODEL=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=y
# CONFIG_SPARSEMEM_VMEMMAP_ENABLE is not set
CONFIG_SPLIT_PTLOCK_CPUS=4
# CONFIG_RESOURCES_64BIT is not set
CONFIG_ZONE_DMA_FLAG=1
CONFIG_BOUNCE=y
CONFIG_NR_QUICK=1
CONFIG_VIRT_TO_BUS=y
# CONFIG_MATH_EMULATION is not set
CONFIG_MTRR=y
CONFIG_SECCOMP=y
# CONFIG_HZ_100 is not set
CONFIG_HZ_250=y
# CONFIG_HZ_300 is not set
# CONFIG_HZ_1000 is not set
CONFIG_HZ=250
# CONFIG_KEXEC is not set
CONFIG_PHYSICAL_START=0x100000
# CONFIG_RELOCATABLE is not set
CONFIG_PHYSICAL_ALIGN=0x100000
CONFIG_COMPAT_VDSO=y

#
# Power management options
#
# CONFIG_PM is not set
CONFIG_SUSPEND_UP_POSSIBLE=y
CONFIG_HIBERNATION_UP_POSSIBLE=y

#
# CPU Frequency scaling
#
# CONFIG_CPU_FREQ is not set
# CONFIG_CPU_IDLE is not set

#
# Bus options (PCI etc.)
#
CONFIG_PCI=y
# CONFIG_PCI_GOBIOS is not set
# CONFIG_PCI_GOMMCONFIG is not set
# CONFIG_PCI_GODIRECT is not set
CONFIG_PCI_GOANY=y
CONFIG_PCI_BIOS=y
CONFIG_PCI_DIRECT=y
CONFIG_PCI_DOMAINS=y
# CONFIG_PCIEPORTBUS is not set
# CONFIG_ARCH_SUPPORTS_MSI is not set
CONFIG_PCI_LEGACY=y
# CONFIG_PCI_DEBUG is not set
CONFIG_ISA_DMA_API=y
CONFIG_ISA=y
# CONFIG_EISA is not set
# CONFIG_MCA is not set
# CONFIG_SCx200 is not set
CONFIG_GEODE_MFGPT_TIMER=y
# CONFIG_PCCARD is not set
# CONFIG_HOTPLUG_PCI is not set

#
# Executable file formats / Emulations
#
CONFIG_BINFMT_ELF=y
# CONFIG_BINFMT_AOUT is not set
# CONFIG_BINFMT_MISC is not set

#
# Networking
#
CONFIG_NET=y

#
# Networking options
#
CONFIG_PACKET=y
# CONFIG_PACKET_MMAP is not set
CONFIG_UNIX=y
CONFIG_XFRM=y
# CONFIG_XFRM_USER is not set
# CONFIG_XFRM_SUB_POLICY is not set
# CONFIG_XFRM_MIGRATE is not set
# 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_VERBOSE is not set
CONFIG_IP_PNP=y
CONFIG_IP_PNP_DHCP=y
CONFIG_IP_PNP_BOOTP=y
# CONFIG_IP_PNP_RARP is not set
CONFIG_NET_IPIP=y
CONFIG_NET_IPGRE=y
CONFIG_NET_IPGRE_BROADCAST=y
CONFIG_IP_MROUTE=y
# CONFIG_IP_PIMSM_V1 is not set
# CONFIG_IP_PIMSM_V2 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_XFRM_TUNNEL is not set
CONFIG_INET_TUNNEL=y
CONFIG_INET_XFRM_MODE_TRANSPORT=y
CONFIG_INET_XFRM_MODE_TUNNEL=y
CONFIG_INET_XFRM_MODE_BEET=y
# CONFIG_INET_LRO is not set
CONFIG_INET_DIAG=y
CONFIG_INET_TCP_DIAG=y
CONFIG_TCP_CONG_ADVANCED=y
CONFIG_TCP_CONG_BIC=y
CONFIG_TCP_CONG_CUBIC=y
CONFIG_TCP_CONG_WESTWOOD=y
CONFIG_TCP_CONG_HTCP=y
CONFIG_TCP_CONG_HSTCP=y
CONFIG_TCP_CONG_HYBLA=y
CONFIG_TCP_CONG_VEGAS=y
CONFIG_TCP_CONG_SCALABLE=y
CONFIG_TCP_CONG_LP=y
CONFIG_TCP_CONG_VENO=y
CONFIG_TCP_CONG_YEAH=y
CONFIG_TCP_CONG_ILLINOIS=y
# CONFIG_DEFAULT_BIC is not set
CONFIG_DEFAULT_CUBIC=y
# CONFIG_DEFAULT_HTCP is not set
# CONFIG_DEFAULT_VEGAS is not set
# CONFIG_DEFAULT_WESTWOOD is not set
# CONFIG_DEFAULT_RENO is not set
CONFIG_DEFAULT_TCP_CONG="cubic"
# CONFIG_TCP_MD5SIG is not set
# CONFIG_IP_VS is not set
CONFIG_IPV6=y
# CONFIG_IPV6_PRIVACY is not set
# CONFIG_IPV6_ROUTER_PREF is not set
# CONFIG_IPV6_OPTIMISTIC_DAD is not set
# CONFIG_INET6_AH is not set
# CONFIG_INET6_ESP is not set
# CONFIG_INET6_IPCOMP is not set
# CONFIG_IPV6_MIP6 is not set
# CONFIG_INET6_XFRM_TUNNEL is not set
# CONFIG_INET6_TUNNEL is not set
CONFIG_INET6_XFRM_MODE_TRANSPORT=y
CONFIG_INET6_XFRM_MODE_TUNNEL=y
CONFIG_INET6_XFRM_MODE_BEET=y
# CONFIG_INET6_XFRM_MODE_ROUTEOPTIMIZATION is not set
CONFIG_IPV6_SIT=y
# CONFIG_IPV6_TUNNEL is not set
# CONFIG_IPV6_MULTIPLE_TABLES is not set
# CONFIG_NETWORK_SECMARK is not set
CONFIG_NETFILTER=y
# CONFIG_NETFILTER_DEBUG is not set
CONFIG_BRIDGE_NETFILTER=y

#
# Core Netfilter Configuration
#
CONFIG_NETFILTER_NETLINK=y
# CONFIG_NETFILTER_NETLINK_QUEUE is not set
# CONFIG_NETFILTER_NETLINK_LOG is not set
# CONFIG_NF_CONNTRACK_ENABLED is not set
# CONFIG_NF_CONNTRACK is not set
CONFIG_NETFILTER_XTABLES=y
CONFIG_NETFILTER_XT_TARGET_CLASSIFY=y
# CONFIG_NETFILTER_XT_TARGET_DSCP is not set
CONFIG_NETFILTER_XT_TARGET_MARK=y
# CONFIG_NETFILTER_XT_TARGET_NFQUEUE is not set
# CONFIG_NETFILTER_XT_TARGET_NFLOG is not set
# CONFIG_NETFILTER_XT_TARGET_TRACE is not set
# CONFIG_NETFILTER_XT_TARGET_TCPMSS is not set
# CONFIG_NETFILTER_XT_MATCH_COMMENT is not set
# CONFIG_NETFILTER_XT_MATCH_DCCP is not set
# CONFIG_NETFILTER_XT_MATCH_DSCP is not set
# CONFIG_NETFILTER_XT_MATCH_ESP is not set
# CONFIG_NETFILTER_XT_MATCH_LENGTH is not set
CONFIG_NETFILTER_XT_MATCH_LIMIT=y
CONFIG_NETFILTER_XT_MATCH_MAC=y
CONFIG_NETFILTER_XT_MATCH_MARK=y
# CONFIG_NETFILTER_XT_MATCH_POLICY is not set
# CONFIG_NETFILTER_XT_MATCH_MULTIPORT is not set
# CONFIG_NETFILTER_XT_MATCH_PHYSDEV is not set
CONFIG_NETFILTER_XT_MATCH_PKTTYPE=y
# CONFIG_NETFILTER_XT_MATCH_QUOTA is not set
# CONFIG_NETFILTER_XT_MATCH_REALM is not set
# CONFIG_NETFILTER_XT_MATCH_SCTP is not set
# CONFIG_NETFILTER_XT_MATCH_STATISTIC is not set
# CONFIG_NETFILTER_XT_MATCH_STRING is not set
# CONFIG_NETFILTER_XT_MATCH_TCPMSS is not set
# CONFIG_NETFILTER_XT_MATCH_TIME is not set
# CONFIG_NETFILTER_XT_MATCH_U32 is not set
# CONFIG_NETFILTER_XT_MATCH_HASHLIMIT is not set

#
# IP: Netfilter Configuration
#
CONFIG_IP_NF_QUEUE=y
CONFIG_IP_NF_IPTABLES=y
CONFIG_IP_NF_MATCH_IPRANGE=y
CONFIG_IP_NF_MATCH_TOS=y
CONFIG_IP_NF_MATCH_RECENT=y
# CONFIG_IP_NF_MATCH_ECN is not set
# CONFIG_IP_NF_MATCH_AH is not set
# CONFIG_IP_NF_MATCH_TTL is not set
# CONFIG_IP_NF_MATCH_OWNER is not set
CONFIG_IP_NF_MATCH_ADDRTYPE=y
CONFIG_IP_NF_FILTER=y
CONFIG_IP_NF_TARGET_REJECT=y
# CONFIG_IP_NF_TARGET_LOG is not set
# CONFIG_IP_NF_TARGET_ULOG is not set
CONFIG_IP_NF_MANGLE=y
CONFIG_IP_NF_TARGET_TOS=y
# CONFIG_IP_NF_TARGET_ECN is not set
# CONFIG_IP_NF_TARGET_TTL is not set
# CONFIG_IP_NF_RAW is not set
CONFIG_IP_NF_ARPTABLES=y
CONFIG_IP_NF_ARPFILTER=y
CONFIG_IP_NF_ARP_MANGLE=y

#
# IPv6: Netfilter Configuration (EXPERIMENTAL)
#
# CONFIG_IP6_NF_QUEUE is not set
CONFIG_IP6_NF_IPTABLES=m
CONFIG_IP6_NF_MATCH_RT=m
CONFIG_IP6_NF_MATCH_OPTS=m
CONFIG_IP6_NF_MATCH_FRAG=m
CONFIG_IP6_NF_MATCH_HL=m
CONFIG_IP6_NF_MATCH_OWNER=m
CONFIG_IP6_NF_MATCH_IPV6HEADER=m
# CONFIG_IP6_NF_MATCH_AH is not set
# CONFIG_IP6_NF_MATCH_MH is not set
CONFIG_IP6_NF_MATCH_EUI64=m
CONFIG_IP6_NF_FILTER=m
CONFIG_IP6_NF_TARGET_LOG=m
CONFIG_IP6_NF_TARGET_REJECT=m
CONFIG_IP6_NF_MANGLE=m
CONFIG_IP6_NF_TARGET_HL=m
CONFIG_IP6_NF_RAW=m

#
# Bridge: Netfilter Configuration
#
# CONFIG_BRIDGE_NF_EBTABLES is not set
# CONFIG_IP_DCCP is not set
# CONFIG_IP_SCTP is not set
# CONFIG_TIPC is not set
# CONFIG_ATM is not set
CONFIG_BRIDGE=y
CONFIG_VLAN_8021Q=y
# CONFIG_DECNET is not set
CONFIG_LLC=y
# 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_ECONET is not set
# CONFIG_WAN_ROUTER is not set
CONFIG_NET_SCHED=y

#
# Queueing/Scheduling
#
CONFIG_NET_SCH_CBQ=y
CONFIG_NET_SCH_HTB=y
CONFIG_NET_SCH_HFSC=y
CONFIG_NET_SCH_PRIO=y
# CONFIG_NET_SCH_RR is not set
CONFIG_NET_SCH_RED=y
CONFIG_NET_SCH_SFQ=y
CONFIG_NET_SCH_TEQL=y
CONFIG_NET_SCH_TBF=y
CONFIG_NET_SCH_GRED=y
CONFIG_NET_SCH_DSMARK=y
CONFIG_NET_SCH_NETEM=y
CONFIG_NET_SCH_INGRESS=y

#
# Classification
#
CONFIG_NET_CLS=y
CONFIG_NET_CLS_BASIC=y
CONFIG_NET_CLS_TCINDEX=y
CONFIG_NET_CLS_ROUTE4=y
CONFIG_NET_CLS_ROUTE=y
CONFIG_NET_CLS_FW=y
CONFIG_NET_CLS_U32=y
CONFIG_CLS_U32_PERF=y
CONFIG_CLS_U32_MARK=y
# CONFIG_NET_CLS_RSVP is not set
# CONFIG_NET_CLS_RSVP6 is not set
# CONFIG_NET_EMATCH is not set
# CONFIG_NET_CLS_ACT is not set
# CONFIG_NET_CLS_POLICE is not set
CONFIG_NET_CLS_IND=y
CONFIG_NET_SCH_FIFO=y

#
# Network testing
#
CONFIG_NET_PKTGEN=m
# CONFIG_HAMRADIO is not set
# CONFIG_IRDA is not set
# CONFIG_BT is not set
# CONFIG_AF_RXRPC is not set
CONFIG_FIB_RULES=y

#
# Wireless
#
CONFIG_CFG80211=y
CONFIG_NL80211=y
CONFIG_WIRELESS_EXT=y
# CONFIG_MAC80211 is not set
# CONFIG_IEEE80211 is not set
# CONFIG_RFKILL is not set
# CONFIG_NET_9P is not set

#
# Device Drivers
#

#
# Generic Driver Options
#
CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug"
CONFIG_STANDALONE=y
CONFIG_PREVENT_FIRMWARE_BUILD=y
CONFIG_FW_LOADER=y
# CONFIG_DEBUG_DRIVER is not set
# CONFIG_DEBUG_DEVRES is not set
# CONFIG_SYS_HYPERVISOR is not set
# CONFIG_CONNECTOR is not set
# CONFIG_MTD is not set
# CONFIG_PARPORT is not set
CONFIG_PNP=y
# CONFIG_PNP_DEBUG is not set

#
# Protocols
#
# CONFIG_ISAPNP is not set
# CONFIG_PNPBIOS is not set
# CONFIG_PNPACPI is not set
CONFIG_BLK_DEV=y
# CONFIG_BLK_DEV_FD is not set
# CONFIG_BLK_DEV_XD is not set
# 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=y
# CONFIG_BLK_DEV_CRYPTOLOOP is not set
# CONFIG_BLK_DEV_NBD is not set
# 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_RAM_BLOCKSIZE=1024
# CONFIG_CDROM_PKTCDVD is not set
# CONFIG_ATA_OVER_ETH is not set
CONFIG_MISC_DEVICES=y
# CONFIG_IBM_ASM is not set
# CONFIG_PHANTOM is not set
# CONFIG_EEPROM_93CX6 is not set
# CONFIG_SGI_IOC4 is not set
# CONFIG_TIFM_CORE is not set
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_HD_IDE is not set
CONFIG_BLK_DEV_IDEDISK=y
CONFIG_IDEDISK_MULTI_MODE=y
# CONFIG_BLK_DEV_IDECD is not set
# CONFIG_BLK_DEV_IDETAPE is not set
# CONFIG_BLK_DEV_IDEFLOPPY is not set
# CONFIG_IDE_TASK_IOCTL is not set
CONFIG_IDE_PROC_FS=y

#
# IDE chipset support/bugfixes
#
CONFIG_IDE_GENERIC=y
# CONFIG_BLK_DEV_PLATFORM is not set
# CONFIG_BLK_DEV_CMD640 is not set
# CONFIG_BLK_DEV_IDEPNP is not set

#
# PCI IDE chipsets support
#
CONFIG_BLK_DEV_IDEPCI=y
CONFIG_IDEPCI_SHARE_IRQ=y
CONFIG_IDEPCI_PCIBUS_ORDER=y
# CONFIG_BLK_DEV_OFFBOARD is not set
CONFIG_BLK_DEV_GENERIC=y
# CONFIG_BLK_DEV_OPTI621 is not set
# CONFIG_BLK_DEV_RZ1000 is not set
CONFIG_BLK_DEV_IDEDMA_PCI=y
# CONFIG_BLK_DEV_AEC62XX is not set
# CONFIG_BLK_DEV_ALI15X3 is not set
# CONFIG_BLK_DEV_AMD74XX is not set
# CONFIG_BLK_DEV_ATIIXP 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_CS5535=y
# CONFIG_BLK_DEV_HPT34X is not set
# CONFIG_BLK_DEV_HPT366 is not set
# CONFIG_BLK_DEV_JMICRON is not set
CONFIG_BLK_DEV_SC1200=y
# CONFIG_BLK_DEV_PIIX is not set
# CONFIG_BLK_DEV_IT8213 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 is not set
# CONFIG_BLK_DEV_SIS5513 is not set
# CONFIG_BLK_DEV_SLC90E66 is not set
# CONFIG_BLK_DEV_TRM290 is not set
# CONFIG_BLK_DEV_VIA82CXXX is not set
# CONFIG_BLK_DEV_TC86C001 is not set
# CONFIG_IDE_ARM is not set

#
# Other IDE chipsets support
#

#
# Note: most of these also require special kernel boot parameters
#
# CONFIG_BLK_DEV_4DRIVES is not set
# CONFIG_BLK_DEV_ALI14XX is not set
# CONFIG_BLK_DEV_DTC2278 is not set
# CONFIG_BLK_DEV_HT6560B is not set
# CONFIG_BLK_DEV_QD65XX is not set
# CONFIG_BLK_DEV_UMC8672 is not set
CONFIG_BLK_DEV_IDEDMA=y
CONFIG_IDE_ARCH_OBSOLETE_INIT=y
# CONFIG_BLK_DEV_HD is not set

#
# SCSI device support
#
# CONFIG_RAID_ATTRS is not set
# CONFIG_SCSI is not set
# CONFIG_SCSI_DMA is not set
# CONFIG_SCSI_NETLINK is not set
# CONFIG_ATA is not set
# CONFIG_MD is not set
# CONFIG_FUSION is not set

#
# IEEE 1394 (FireWire) support
#
# CONFIG_FIREWIRE is not set
# CONFIG_IEEE1394 is not set
# CONFIG_I2O is not set
# CONFIG_MACINTOSH_DRIVERS is not set
CONFIG_NETDEVICES=y
# CONFIG_NETDEVICES_MULTIQUEUE is not set
CONFIG_DUMMY=m
# CONFIG_BONDING is not set
# CONFIG_MACVLAN is not set
# CONFIG_EQUALIZER is not set
CONFIG_TUN=y
# CONFIG_VETH is not set
# CONFIG_NET_SB1000 is not set
# CONFIG_ARCNET is not set
# CONFIG_PHYLIB is not set
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_LANCE is not set
# CONFIG_NET_VENDOR_SMC is not set
# CONFIG_NET_VENDOR_RACAL is not set
# CONFIG_NET_TULIP is not set
# CONFIG_AT1700 is not set
# CONFIG_DEPCA is not set
# CONFIG_HP100 is not set
# CONFIG_NET_ISA is not set
# CONFIG_IBM_NEW_EMAC_ZMII is not set
# CONFIG_IBM_NEW_EMAC_RGMII is not set
# CONFIG_IBM_NEW_EMAC_TAH is not set
# CONFIG_IBM_NEW_EMAC_EMAC4 is not set
CONFIG_NET_PCI=y
# CONFIG_PCNET32 is not set
# CONFIG_AMD8111_ETH is not set
# CONFIG_ADAPTEC_STARFIRE is not set
# CONFIG_AC3200 is not set
# CONFIG_APRICOT is not set
# CONFIG_B44 is not set
# CONFIG_FORCEDETH is not set
# CONFIG_CS89x0 is not set
# CONFIG_EEPRO100 is not set
# CONFIG_E100 is not set
# CONFIG_FEALNX is not set
CONFIG_NATSEMI=y
CONFIG_NE2K_PCI=y
# CONFIG_8139CP is not set
# CONFIG_8139TOO is not set
# CONFIG_SIS900 is not set
# CONFIG_EPIC100 is not set
# CONFIG_SUNDANCE is not set
# CONFIG_TLAN is not set
CONFIG_VIA_RHINE=y
CONFIG_VIA_RHINE_MMIO=y
# CONFIG_VIA_RHINE_NAPI is not set
# CONFIG_SC92031 is not set
# CONFIG_NETDEV_1000 is not set
# CONFIG_NETDEV_10000 is not set
# CONFIG_TR is not set

#
# Wireless LAN
#
# CONFIG_WLAN_PRE80211 is not set
# CONFIG_WLAN_80211 is not set

#
# 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_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_SHAPER is not set
CONFIG_NETCONSOLE=m
# CONFIG_NETCONSOLE_DYNAMIC is not set
CONFIG_NETPOLL=y
# CONFIG_NETPOLL_TRAP is not set
CONFIG_NET_POLL_CONTROLLER=y
# CONFIG_ISDN is not set
# CONFIG_PHONE is not set

#
# Input device support
#
CONFIG_INPUT=y
# CONFIG_INPUT_FF_MEMLESS is not set
# CONFIG_INPUT_POLLDEV is not set

#
# Userland interfaces
#
CONFIG_INPUT_MOUSEDEV=y
# CONFIG_INPUT_MOUSEDEV_PSAUX is not set
CONFIG_INPUT_MOUSEDEV_SCREEN_X=1024
CONFIG_INPUT_MOUSEDEV_SCREEN_Y=768
# CONFIG_INPUT_JOYDEV is not set
# CONFIG_INPUT_EVDEV is not set
# CONFIG_INPUT_EVBUG is not set

#
# Input Device Drivers
#
CONFIG_INPUT_KEYBOARD=y
CONFIG_KEYBOARD_ATKBD=y
# CONFIG_KEYBOARD_SUNKBD is not set
# CONFIG_KEYBOARD_LKKBD is not set
# CONFIG_KEYBOARD_XTKBD is not set
# CONFIG_KEYBOARD_NEWTON is not set
# CONFIG_KEYBOARD_STOWAWAY is not set
# CONFIG_INPUT_MOUSE is not set
# CONFIG_INPUT_JOYSTICK is not set
# CONFIG_INPUT_TABLET is not set
# CONFIG_INPUT_TOUCHSCREEN is not set
# CONFIG_INPUT_MISC is not set

#
# Hardware I/O ports
#
CONFIG_SERIO=y
CONFIG_SERIO_I8042=y
CONFIG_SERIO_SERPORT=y
# CONFIG_SERIO_CT82C710 is not set
# CONFIG_SERIO_PCIPS2 is not set
CONFIG_SERIO_LIBPS2=y
# CONFIG_SERIO_RAW is not set
# CONFIG_GAMEPORT is not set

#
# Character devices
#
CONFIG_VT=y
CONFIG_VT_CONSOLE=y
CONFIG_HW_CONSOLE=y
# CONFIG_VT_HW_CONSOLE_BINDING is not set
# CONFIG_SERIAL_NONSTANDARD is not set

#
# Serial drivers
#
CONFIG_SERIAL_8250=y
CONFIG_SERIAL_8250_CONSOLE=y
CONFIG_FIX_EARLYCON_MEM=y
CONFIG_SERIAL_8250_PCI=y
CONFIG_SERIAL_8250_PNP=y
CONFIG_SERIAL_8250_NR_UARTS=4
CONFIG_SERIAL_8250_RUNTIME_UARTS=4
# CONFIG_SERIAL_8250_EXTENDED is not set

#
# Non-8250 serial port support
#
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
# CONFIG_IPMI_HANDLER is not set
CONFIG_HW_RANDOM=y
# CONFIG_HW_RANDOM_INTEL is not set
# CONFIG_HW_RANDOM_AMD is not set
CONFIG_HW_RANDOM_GEODE=y
# CONFIG_HW_RANDOM_VIA is not set
CONFIG_NVRAM=y
CONFIG_RTC=y
# CONFIG_DTLK is not set
# CONFIG_R3964 is not set
# CONFIG_APPLICOM is not set
# CONFIG_SONYPI is not set
# CONFIG_MWAVE is not set
CONFIG_PC8736x_GPIO=y
CONFIG_NSC_GPIO=y
CONFIG_CS5535_GPIO=y
# CONFIG_RAW_DRIVER is not set
# CONFIG_HANGCHECK_TIMER is not set
# CONFIG_TCG_TPM is not set
# CONFIG_TELCLOCK is not set
CONFIG_DEVPORT=y
CONFIG_I2C=y
CONFIG_I2C_BOARDINFO=y
CONFIG_I2C_CHARDEV=m

#
# I2C Algorithms
#
CONFIG_I2C_ALGOBIT=m
# CONFIG_I2C_ALGOPCF is not set
# CONFIG_I2C_ALGOPCA is not set

#
# I2C Hardware Bus support
#
# CONFIG_I2C_ALI1535 is not set
# CONFIG_I2C_ALI1563 is not set
# CONFIG_I2C_ALI15X3 is not set
# CONFIG_I2C_AMD756 is not set
# CONFIG_I2C_AMD8111 is not set
# CONFIG_I2C_ELEKTOR is not set
# CONFIG_I2C_I801 is not set
# CONFIG_I2C_I810 is not set
# CONFIG_I2C_PIIX4 is not set
# CONFIG_I2C_NFORCE2 is not set
# CONFIG_I2C_OCORES is not set
# CONFIG_I2C_PARPORT_LIGHT is not set
# CONFIG_I2C_PROSAVAGE is not set
# CONFIG_I2C_SAVAGE4 is not set
# CONFIG_I2C_SIMTEC is not set
CONFIG_SCx200_ACB=m
# CONFIG_I2C_SIS5595 is not set
# CONFIG_I2C_SIS630 is not set
# CONFIG_I2C_SIS96X is not set
# CONFIG_I2C_TAOS_EVM is not set
# CONFIG_I2C_STUB is not set
# CONFIG_I2C_TINY_USB is not set
# CONFIG_I2C_VIA is not set
# CONFIG_I2C_VIAPRO is not set
# CONFIG_I2C_VOODOO3 is not set
# CONFIG_I2C_PCA_ISA is not set

#
# Miscellaneous I2C Chip support
#
# CONFIG_SENSORS_DS1337 is not set
# CONFIG_SENSORS_DS1374 is not set
# CONFIG_DS1682 is not set
# CONFIG_SENSORS_EEPROM is not set
# CONFIG_SENSORS_PCF8574 is not set
# CONFIG_SENSORS_PCA9539 is not set
# CONFIG_SENSORS_PCF8591 is not set
# CONFIG_SENSORS_MAX6875 is not set
# CONFIG_SENSORS_TSL2550 is not set
# CONFIG_I2C_DEBUG_CORE is not set
# CONFIG_I2C_DEBUG_ALGO is not set
# CONFIG_I2C_DEBUG_BUS is not set
# CONFIG_I2C_DEBUG_CHIP is not set

#
# SPI support
#
# CONFIG_SPI is not set
# CONFIG_SPI_MASTER is not set
# CONFIG_W1 is not set
CONFIG_POWER_SUPPLY=y
# CONFIG_POWER_SUPPLY_DEBUG is not set
# CONFIG_PDA_POWER is not set
# CONFIG_BATTERY_DS2760 is not set
CONFIG_HWMON=y
# CONFIG_HWMON_VID is not set
# CONFIG_SENSORS_ABITUGURU is not set
# CONFIG_SENSORS_ABITUGURU3 is not set
# CONFIG_SENSORS_AD7418 is not set
# CONFIG_SENSORS_ADM1021 is not set
# CONFIG_SENSORS_ADM1025 is not set
# CONFIG_SENSORS_ADM1026 is not set
# CONFIG_SENSORS_ADM1029 is not set
# CONFIG_SENSORS_ADM1031 is not set
# CONFIG_SENSORS_ADM9240 is not set
# CONFIG_SENSORS_ADT7470 is not set
# CONFIG_SENSORS_K8TEMP is not set
# CONFIG_SENSORS_ASB100 is not set
# CONFIG_SENSORS_ATXP1 is not set
# CONFIG_SENSORS_DS1621 is not set
# CONFIG_SENSORS_I5K_AMB is not set
# CONFIG_SENSORS_F71805F is not set
# CONFIG_SENSORS_F71882FG is not set
# CONFIG_SENSORS_F75375S is not set
# CONFIG_SENSORS_FSCHER is not set
# CONFIG_SENSORS_FSCPOS is not set
# CONFIG_SENSORS_FSCHMD is not set
# CONFIG_SENSORS_GL518SM is not set
# CONFIG_SENSORS_GL520SM is not set
# CONFIG_SENSORS_CORETEMP is not set
# CONFIG_SENSORS_IT87 is not set
# CONFIG_SENSORS_LM63 is not set
# CONFIG_SENSORS_LM75 is not set
CONFIG_SENSORS_LM77=m
# CONFIG_SENSORS_LM78 is not set
# CONFIG_SENSORS_LM80 is not set
# CONFIG_SENSORS_LM83 is not set
# CONFIG_SENSORS_LM85 is not set
# CONFIG_SENSORS_LM87 is not set
# CONFIG_SENSORS_LM90 is not set
# CONFIG_SENSORS_LM92 is not set
# CONFIG_SENSORS_LM93 is not set
# CONFIG_SENSORS_MAX1619 is not set
# CONFIG_SENSORS_MAX6650 is not set
# CONFIG_SENSORS_PC87360 is not set
# CONFIG_SENSORS_PC87427 is not set
# CONFIG_SENSORS_SIS5595 is not set
# CONFIG_SENSORS_DME1737 is not set
# CONFIG_SENSORS_SMSC47M1 is not set
# CONFIG_SENSORS_SMSC47M192 is not set
# CONFIG_SENSORS_SMSC47B397 is not set
# CONFIG_SENSORS_THMC50 is not set
# CONFIG_SENSORS_VIA686A is not set
# CONFIG_SENSORS_VT1211 is not set
# CONFIG_SENSORS_VT8231 is not set
# CONFIG_SENSORS_W83781D is not set
# CONFIG_SENSORS_W83791D is not set
# CONFIG_SENSORS_W83792D is not set
# CONFIG_SENSORS_W83793 is not set
# CONFIG_SENSORS_W83L785TS is not set
# CONFIG_SENSORS_W83627HF is not set
# CONFIG_SENSORS_W83627EHF is not set
# CONFIG_SENSORS_HDAPS is not set
# CONFIG_SENSORS_APPLESMC is not set
# CONFIG_HWMON_DEBUG_CHIP is not set
CONFIG_WATCHDOG=y
# CONFIG_WATCHDOG_NOWAYOUT is not set

#
# Watchdog Device Drivers
#
CONFIG_SOFT_WATCHDOG=m
# CONFIG_ACQUIRE_WDT is not set
# CONFIG_ADVANTECH_WDT is not set
# CONFIG_ALIM1535_WDT is not set
# CONFIG_ALIM7101_WDT is not set
# CONFIG_SC520_WDT is not set
# CONFIG_EUROTECH_WDT is not set
# CONFIG_IB700_WDT is not set
# CONFIG_IBMASR is not set
# CONFIG_WAFER_WDT is not set
# CONFIG_I6300ESB_WDT is not set
# CONFIG_ITCO_WDT is not set
# CONFIG_IT8712F_WDT is not set
# CONFIG_SC1200_WDT is not set
# CONFIG_PC87413_WDT is not set
# CONFIG_60XX_WDT is not set
# CONFIG_SBC8360_WDT is not set
# CONFIG_SBC7240_WDT is not set
# CONFIG_CPU5_WDT is not set
# CONFIG_SMSC37B787_WDT is not set
# CONFIG_W83627HF_WDT is not set
# CONFIG_W83697HF_WDT is not set
# CONFIG_W83877F_WDT is not set
# CONFIG_W83977F_WDT is not set
# CONFIG_MACHZ_WDT is not set
# CONFIG_SBC_EPX_C3_WATCHDOG is not set

#
# ISA-based Watchdog Cards
#
# CONFIG_PCWATCHDOG is not set
# CONFIG_MIXCOMWD is not set
# CONFIG_WDT is not set

#
# PCI-based Watchdog Cards
#
# CONFIG_PCIPCWATCHDOG is not set
# CONFIG_WDTPCI is not set

#
# USB-based Watchdog Cards
#
# CONFIG_USBPCWATCHDOG is not set

#
# Sonics Silicon Backplane
#
CONFIG_SSB_POSSIBLE=y
# CONFIG_SSB is not set

#
# Multifunction device drivers
#
# CONFIG_MFD_SM501 is not set

#
# Multimedia devices
#
# CONFIG_VIDEO_DEV is not set
# CONFIG_DVB_CORE is not set
# CONFIG_DAB is not set

#
# Graphics support
#
# CONFIG_AGP is not set
# CONFIG_DRM is not set
# CONFIG_VGASTATE is not set
# CONFIG_VIDEO_OUTPUT_CONTROL is not set
# CONFIG_FB is not set
# CONFIG_BACKLIGHT_LCD_SUPPORT is not set

#
# Display device support
#
# CONFIG_DISPLAY_SUPPORT is not set

#
# Console display driver support
#
CONFIG_VGA_CONSOLE=y
# CONFIG_VGACON_SOFT_SCROLLBACK is not set
# CONFIG_VIDEO_SELECT is not set
# CONFIG_MDA_CONSOLE is not set
CONFIG_DUMMY_CONSOLE=y

#
# Sound
#
# CONFIG_SOUND is not set
CONFIG_HID_SUPPORT=y
CONFIG_HID=y
CONFIG_HID_DEBUG=y
# CONFIG_HIDRAW is not set

#
# USB Input Devices
#
CONFIG_USB_HID=y
# CONFIG_USB_HIDINPUT_POWERBOOK is not set
# CONFIG_HID_FF is not set
# CONFIG_USB_HIDDEV is not set
CONFIG_USB_SUPPORT=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

#
# Miscellaneous USB options
#
CONFIG_USB_DEVICEFS=y
CONFIG_USB_DEVICE_CLASS=y
# CONFIG_USB_DYNAMIC_MINORS is not set
# CONFIG_USB_OTG is not set

#
# USB Host Controller Drivers
#
CONFIG_USB_EHCI_HCD=y
# CONFIG_USB_EHCI_SPLIT_ISO is not set
# CONFIG_USB_EHCI_ROOT_HUB_TT is not set
# CONFIG_USB_EHCI_TT_NEWSCHED is not set
# CONFIG_USB_ISP116X_HCD is not set
CONFIG_USB_OHCI_HCD=y
# CONFIG_USB_OHCI_BIG_ENDIAN_DESC is not set
# CONFIG_USB_OHCI_BIG_ENDIAN_MMIO is not set
CONFIG_USB_OHCI_LITTLE_ENDIAN=y
CONFIG_USB_UHCI_HCD=y
# CONFIG_USB_SL811_HCD is not set
# CONFIG_USB_R8A66597_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_LIBUSUAL is not set

#
# USB Imaging devices
#
# CONFIG_USB_MDC800 is not set
# CONFIG_USB_MON is not set

#
# 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_ADUTUX 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_BERRY_CHARGE is not set
# CONFIG_USB_LED is not set
# CONFIG_USB_CYPRESS_CY7C63 is not set
# CONFIG_USB_CYTHERM is not set
# CONFIG_USB_PHIDGET is not set
# CONFIG_USB_IDMOUSE is not set
# CONFIG_USB_FTDI_ELAN is not set
# CONFIG_USB_APPLEDISPLAY is not set
# CONFIG_USB_SISUSBVGA is not set
# CONFIG_USB_LD is not set
# CONFIG_USB_TRANCEVIBRATOR is not set
# CONFIG_USB_IOWARRIOR is not set
# CONFIG_USB_TEST is not set

#
# USB DSL modem support
#

#
# USB Gadget Support
#
# CONFIG_USB_GADGET is not set
# CONFIG_MMC is not set
# CONFIG_NEW_LEDS is not set
# CONFIG_INFINIBAND is not set
# CONFIG_EDAC is not set
# CONFIG_RTC_CLASS is not set
# CONFIG_DMADEVICES is not set
CONFIG_VIRTUALIZATION=y
# CONFIG_KVM is not set
# CONFIG_LGUEST is not set

#
# Userspace I/O
#
# CONFIG_UIO is not set

#
# Firmware Drivers
#
# CONFIG_EDD is not set
# CONFIG_DELL_RBU is not set
# CONFIG_DCDBAS is not set
CONFIG_DMIID=y

#
# 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_EXT4DEV_FS is not set
CONFIG_JBD=y
CONFIG_FS_MBCACHE=y
CONFIG_REISERFS_FS=y
# CONFIG_REISERFS_CHECK is not set
# CONFIG_REISERFS_PROC_INFO is not set
# CONFIG_REISERFS_FS_XATTR is not set
# CONFIG_JFS_FS is not set
# CONFIG_FS_POSIX_ACL is not set
# CONFIG_XFS_FS is not set
# CONFIG_GFS2_FS is not set
# CONFIG_OCFS2_FS is not set
# CONFIG_MINIX_FS is not set
# CONFIG_ROMFS_FS is not set
CONFIG_INOTIFY=y
CONFIG_INOTIFY_USER=y
# CONFIG_QUOTA is not set
CONFIG_DNOTIFY=y
# CONFIG_AUTOFS_FS is not set
CONFIG_AUTOFS4_FS=y
# CONFIG_FUSE_FS is not set

#
# CD-ROM/DVD Filesystems
#
CONFIG_ISO9660_FS=y
CONFIG_JOLIET=y
# CONFIG_ZISOFS is not set
CONFIG_UDF_FS=y
CONFIG_UDF_NLS=y

#
# DOS/FAT/NT Filesystems
#
CONFIG_FAT_FS=y
CONFIG_MSDOS_FS=y
CONFIG_VFAT_FS=y
CONFIG_FAT_DEFAULT_CODEPAGE=437
CONFIG_FAT_DEFAULT_IOCHARSET="iso8859-1"
# CONFIG_NTFS_FS is not set

#
# Pseudo filesystems
#
CONFIG_PROC_FS=y
CONFIG_PROC_KCORE=y
CONFIG_PROC_SYSCTL=y
CONFIG_SYSFS=y
CONFIG_TMPFS=y
# CONFIG_TMPFS_POSIX_ACL is not set
# CONFIG_HUGETLBFS is not set
# CONFIG_HUGETLB_PAGE 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 is not set
# 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
CONFIG_NETWORK_FILESYSTEMS=y
CONFIG_NFS_FS=y
CONFIG_NFS_V3=y
# CONFIG_NFS_V3_ACL is not set
CONFIG_NFS_V4=y
# 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_SUNRPC_GSS=y
# CONFIG_SUNRPC_BIND34 is not set
CONFIG_RPCSEC_GSS_KRB5=y
# 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

#
# Partition Types
#
# CONFIG_PARTITION_ADVANCED is not set
CONFIG_MSDOS_PARTITION=y
CONFIG_NLS=y
CONFIG_NLS_DEFAULT="iso8859-1"
CONFIG_NLS_CODEPAGE_437=y
# CONFIG_NLS_CODEPAGE_737 is not set
# CONFIG_NLS_CODEPAGE_775 is not set
# CONFIG_NLS_CODEPAGE_850 is not set
# CONFIG_NLS_CODEPAGE_852 is not set
# CONFIG_NLS_CODEPAGE_855 is not set
# CONFIG_NLS_CODEPAGE_857 is not set
# CONFIG_NLS_CODEPAGE_860 is not set
# CONFIG_NLS_CODEPAGE_861 is not set
# CONFIG_NLS_CODEPAGE_862 is not set
# CONFIG_NLS_CODEPAGE_863 is not set
# CONFIG_NLS_CODEPAGE_864 is not set
# CONFIG_NLS_CODEPAGE_865 is not set
# CONFIG_NLS_CODEPAGE_866 is not set
# CONFIG_NLS_CODEPAGE_869 is not set
# CONFIG_NLS_CODEPAGE_936 is not set
# CONFIG_NLS_CODEPAGE_950 is not set
# CONFIG_NLS_CODEPAGE_932 is not set
# CONFIG_NLS_CODEPAGE_949 is not set
# CONFIG_NLS_CODEPAGE_874 is not set
# CONFIG_NLS_ISO8859_8 is not set
# CONFIG_NLS_CODEPAGE_1250 is not set
# CONFIG_NLS_CODEPAGE_1251 is not set
# CONFIG_NLS_ASCII is not set
CONFIG_NLS_ISO8859_1=y
# CONFIG_NLS_ISO8859_2 is not set
# CONFIG_NLS_ISO8859_3 is not set
# CONFIG_NLS_ISO8859_4 is not set
# CONFIG_NLS_ISO8859_5 is not set
# CONFIG_NLS_ISO8859_6 is not set
# CONFIG_NLS_ISO8859_7 is not set
# CONFIG_NLS_ISO8859_9 is not set
# CONFIG_NLS_ISO8859_13 is not set
# CONFIG_NLS_ISO8859_14 is not set
# CONFIG_NLS_ISO8859_15 is not set
# CONFIG_NLS_KOI8_R is not set
# CONFIG_NLS_KOI8_U is not set
# CONFIG_NLS_UTF8 is not set
# CONFIG_DLM is not set
CONFIG_INSTRUMENTATION=y
# CONFIG_PROFILING is not set
# CONFIG_KPROBES is not set
# CONFIG_MARKERS is not set

#
# Kernel hacking
#
CONFIG_TRACE_IRQFLAGS_SUPPORT=y
CONFIG_PRINTK_TIME=y
CONFIG_ENABLE_WARN_DEPRECATED=y
CONFIG_ENABLE_MUST_CHECK=y
CONFIG_MAGIC_SYSRQ=y
CONFIG_UNUSED_SYMBOLS=y
# CONFIG_DEBUG_FS is not set
# CONFIG_HEADERS_CHECK is not set
CONFIG_DEBUG_KERNEL=y
# CONFIG_DEBUG_SHIRQ is not set
CONFIG_DETECT_SOFTLOCKUP=y
CONFIG_SCHED_DEBUG=y
# CONFIG_SCHEDSTATS is not set
# CONFIG_TIMER_STATS is not set
# CONFIG_DEBUG_SLAB is not set
# CONFIG_DEBUG_RT_MUTEXES is not set
# CONFIG_RT_MUTEX_TESTER is not set
# CONFIG_DEBUG_SPINLOCK is not set
CONFIG_DEBUG_MUTEXES=y
# CONFIG_DEBUG_LOCK_ALLOC is not set
# CONFIG_PROVE_LOCKING is not set
# CONFIG_LOCK_STAT is not set
# CONFIG_DEBUG_SPINLOCK_SLEEP is not set
# CONFIG_DEBUG_LOCKING_API_SELFTESTS is not set
# CONFIG_DEBUG_KOBJECT is not set
CONFIG_DEBUG_BUGVERBOSE=y
CONFIG_DEBUG_INFO=y
# CONFIG_DEBUG_VM is not set
# CONFIG_DEBUG_LIST is not set
# CONFIG_DEBUG_SG is not set
CONFIG_FRAME_POINTER=y
CONFIG_FORCED_INLINING=y
# CONFIG_BOOT_PRINTK_DELAY is not set
# CONFIG_RCU_TORTURE_TEST is not set
# CONFIG_FAULT_INJECTION is not set
# CONFIG_SAMPLES is not set
CONFIG_EARLY_PRINTK=y
CONFIG_DEBUG_STACKOVERFLOW=y
# CONFIG_DEBUG_STACK_USAGE is not set
# CONFIG_DEBUG_PAGEALLOC is not set
# CONFIG_DEBUG_RODATA is not set
CONFIG_4KSTACKS=y
CONFIG_DOUBLEFAULT=y

#
# Security options
#
# CONFIG_KEYS is not set
# CONFIG_SECURITY is not set
# CONFIG_SECURITY_FILE_CAPABILITIES is not set
CONFIG_CRYPTO=y
CONFIG_CRYPTO_ALGAPI=y
CONFIG_CRYPTO_BLKCIPHER=y
CONFIG_CRYPTO_MANAGER=y
# CONFIG_CRYPTO_HMAC is not set
# CONFIG_CRYPTO_XCBC is not set
# CONFIG_CRYPTO_NULL is not set
# CONFIG_CRYPTO_MD4 is not set
CONFIG_CRYPTO_MD5=y
# CONFIG_CRYPTO_SHA1 is not set
# CONFIG_CRYPTO_SHA256 is not set
# CONFIG_CRYPTO_SHA512 is not set
# CONFIG_CRYPTO_WP512 is not set
# CONFIG_CRYPTO_TGR192 is not set
# CONFIG_CRYPTO_GF128MUL is not set
# CONFIG_CRYPTO_ECB is not set
CONFIG_CRYPTO_CBC=y
# CONFIG_CRYPTO_PCBC is not set
# CONFIG_CRYPTO_LRW is not set
# CONFIG_CRYPTO_XTS is not set
# CONFIG_CRYPTO_CRYPTD is not set
CONFIG_CRYPTO_DES=y
# CONFIG_CRYPTO_FCRYPT is not set
# CONFIG_CRYPTO_BLOWFISH is not set
# CONFIG_CRYPTO_TWOFISH is not set
# CONFIG_CRYPTO_TWOFISH_586 is not set
# CONFIG_CRYPTO_SERPENT is not set
# CONFIG_CRYPTO_AES is not set
# CONFIG_CRYPTO_AES_586 is not set
# CONFIG_CRYPTO_CAST5 is not set
# CONFIG_CRYPTO_CAST6 is not set
# CONFIG_CRYPTO_TEA is not set
# CONFIG_CRYPTO_ARC4 is not set
# CONFIG_CRYPTO_KHAZAD is not set
# CONFIG_CRYPTO_ANUBIS is not set
# CONFIG_CRYPTO_SEED is not set
# CONFIG_CRYPTO_DEFLATE is not set
# CONFIG_CRYPTO_MICHAEL_MIC is not set
# CONFIG_CRYPTO_CRC32C is not set
# CONFIG_CRYPTO_CAMELLIA is not set
# CONFIG_CRYPTO_TEST is not set
# CONFIG_CRYPTO_AUTHENC is not set
CONFIG_CRYPTO_HW=y
# CONFIG_CRYPTO_DEV_PADLOCK is not set
CONFIG_CRYPTO_DEV_GEODE=y

#
# Library routines
#
CONFIG_BITREVERSE=y
# CONFIG_CRC_CCITT is not set
# CONFIG_CRC16 is not set
# CONFIG_CRC_ITU_T is not set
CONFIG_CRC32=y
# CONFIG_CRC7 is not set
CONFIG_LIBCRC32C=m
CONFIG_AUDIT_GENERIC=y
CONFIG_PLIST=y
CONFIG_HAS_IOMEM=y
CONFIG_HAS_IOPORT=y
CONFIG_HAS_DMA=y


Attachments:
dmesg_mfgpt_hang.txt (2.93 kB)
config-2.6.24-rc8 (35.87 kB)
Download all attachments

2008-01-16 21:19:16

by Andres Salomon

[permalink] [raw]
Subject: Re: 2.6.24-rc8 hangs at mfgpt-timer

On Wed, 16 Jan 2008 18:44:07 +0100
Arnd Hannemann <[email protected]> wrote:

> Hi,
>
> I'm trying to boot 2.6.24-rc8 on a GEODE LX board (ALIX.3),
> and it hangs during boot:
>
> [ 12.689971] NET: Registered protocol family 16
> [ 12.703329] geode-mfgpt: Registered timer 0
> [ 12.716149] mfgpt-timer: registering the MFGT timer as a clock event...
>


What BIOS are you using? It's possible that our detection code is
failing to detect in-use timers.

2008-01-16 21:56:06

by Andres Salomon

[permalink] [raw]
Subject: Re: 2.6.24-rc8 hangs at mfgpt-timer

On Wed, 16 Jan 2008 16:19:12 -0500
Andres Salomon <[email protected]> wrote:

> On Wed, 16 Jan 2008 18:44:07 +0100
> Arnd Hannemann <[email protected]> wrote:
>
> > Hi,
> >
> > I'm trying to boot 2.6.24-rc8 on a GEODE LX board (ALIX.3),
> > and it hangs during boot:
> >
> > [ 12.689971] NET: Registered protocol family 16
> > [ 12.703329] geode-mfgpt: Registered timer 0
> > [ 12.716149] mfgpt-timer: registering the MFGT timer as a clock event...
> >
>
>
> What BIOS are you using? It's possible that our detection code is
> failing to detect in-use timers.


Also, could you provide a log with the following (untested) patch? I'm
curious how many MFGPTs we're actually detecting as being available, and
the existing code is backwards.



>From 0ea825fd564056ac653507517beb5cea9034e464 Mon Sep 17 00:00:00 2001
From: Andres Salomon <[email protected]>
Date: Wed, 16 Jan 2008 16:53:16 -0500
Subject: [PATCH] x86: geode: fix up ordering of messages during MFGPT detection

We're printing out informational messages in the wrong order while
probing for MFGPTs. This changes the order so that we first display
the number of available timers that were detected before displaying
messages about how we actually are using those timers.

Signed-off-by: Andres Salomon <[email protected]>
---
arch/x86/kernel/geode_32.c | 5 +----
arch/x86/kernel/mfgpt_32.c | 7 +++----
include/asm-x86/geode.h | 2 +-
3 files changed, 5 insertions(+), 9 deletions(-)

diff --git a/arch/x86/kernel/geode_32.c b/arch/x86/kernel/geode_32.c
index f12d8c5..00b45ae 100644
--- a/arch/x86/kernel/geode_32.c
+++ b/arch/x86/kernel/geode_32.c
@@ -145,14 +145,11 @@ EXPORT_SYMBOL_GPL(geode_gpio_setup_event);

static int __init geode_southbridge_init(void)
{
- int timers;
-
if (!is_geode())
return -ENODEV;

init_lbars();
- timers = geode_mfgpt_detect();
- printk(KERN_INFO "geode: %d MFGPT timers available.\n", timers);
+ geode_mfgpt_detect();
return 0;
}

diff --git a/arch/x86/kernel/mfgpt_32.c b/arch/x86/kernel/mfgpt_32.c
index 0ab680f..d11cba3 100644
--- a/arch/x86/kernel/mfgpt_32.c
+++ b/arch/x86/kernel/mfgpt_32.c
@@ -70,14 +70,14 @@ __setup("nomfgpt", mfgpt_disable);
* In other cases (such as with VSAless OpenFirmware), the system firmware
* leaves timers available for us to use.
*/
-int __init geode_mfgpt_detect(void)
+void __init geode_mfgpt_detect(void)
{
int count = 0, i;
u16 val;

if (disable) {
printk(KERN_INFO "geode-mfgpt: Skipping MFGPT setup\n");
- return 0;
+ return;
}

for (i = 0; i < MFGPT_MAX_TIMERS; i++) {
@@ -87,11 +87,10 @@ int __init geode_mfgpt_detect(void)
count++;
}
}
+ printk(KERN_INFO "geode-mfgpt: %d MFGPT timers available.\n", count);

/* set up clock event device, if desired */
i = mfgpt_timer_setup();
-
- return count;
}

int geode_mfgpt_toggle_event(int timer, int cmp, int event, int enable)
diff --git a/include/asm-x86/geode.h b/include/asm-x86/geode.h
index 771af33..1cb22cf 100644
--- a/include/asm-x86/geode.h
+++ b/include/asm-x86/geode.h
@@ -200,7 +200,7 @@ static inline u16 geode_mfgpt_read(int timer, u16 reg)
return inw(base + reg + (timer * 8));
}

-extern int __init geode_mfgpt_detect(void);
+extern void __init geode_mfgpt_detect(void);
extern int geode_mfgpt_toggle_event(int timer, int cmp, int event, int enable);
extern int geode_mfgpt_set_irq(int timer, int cmp, int irq, int enable);
extern int geode_mfgpt_alloc_timer(int timer, int domain, struct module *owner);
--
1.5.3.5

2008-01-17 09:54:13

by Arnd Hannemann

[permalink] [raw]
Subject: Re: 2.6.24-rc8 hangs at mfgpt-timer

Andres Salomon schrieb:
> On Wed, 16 Jan 2008 16:19:12 -0500
> Andres Salomon <[email protected]> wrote:
>
>> On Wed, 16 Jan 2008 18:44:07 +0100
>> Arnd Hannemann <[email protected]> wrote:
>>
>>> Hi,
>>>
>>> I'm trying to boot 2.6.24-rc8 on a GEODE LX board (ALIX.3),
>>> and it hangs during boot:
>>>
>>> [ 12.689971] NET: Registered protocol family 16
>>> [ 12.703329] geode-mfgpt: Registered timer 0
>>> [ 12.716149] mfgpt-timer: registering the MFGT timer as a clock event...
>>>
>>
>> What BIOS are you using? It's possible that our detection code is
>> failing to detect in-use timers.

I'm using v0.99 (latest available).
Also note when I do enable the mysterios "MFGPT workaround" option in
the bios the machine hangs directly after:
[ 36.780990] NET: Registered protocol family 16

>
>
> Also, could you provide a log with the following (untested) patch? I'm
> curious how many MFGPTs we're actually detecting as being available, and
> the existing code is backwards.

The relevant part would be:
[ 23.092507] NET: Registered protocol family 16
[ 23.105875] geode-mfgpt: 8 MFGPT timers available
[ 23.120247] geode-mfgpt: Registered timer 0
[ 23.133076] mfgpt-timer: registering the MFGT timer as a clock event.

Best regards,
Arnd Hannemann

2008-01-17 18:40:31

by Andres Salomon

[permalink] [raw]
Subject: Re: 2.6.24-rc8 hangs at mfgpt-timer

On Thu, 17 Jan 2008 10:54:30 +0100
Arnd Hannemann <[email protected]> wrote:

> Andres Salomon schrieb:
> > On Wed, 16 Jan 2008 16:19:12 -0500
> > Andres Salomon <[email protected]> wrote:
> >
> >> On Wed, 16 Jan 2008 18:44:07 +0100
> >> Arnd Hannemann <[email protected]> wrote:
> >>
> >>> Hi,
> >>>
> >>> I'm trying to boot 2.6.24-rc8 on a GEODE LX board (ALIX.3),
> >>> and it hangs during boot:
> >>>
> >>> [ 12.689971] NET: Registered protocol family 16
> >>> [ 12.703329] geode-mfgpt: Registered timer 0
> >>> [ 12.716149] mfgpt-timer: registering the MFGT timer as a clock event...
> >>>
> >>
> >> What BIOS are you using? It's possible that our detection code is
> >> failing to detect in-use timers.
>
> I'm using v0.99 (latest available).


v0.99 of what? Jordan seems to think it's an Award BIOS, but I'd like
to make sure.


> Also note when I do enable the mysterios "MFGPT workaround" option in
> the bios the machine hangs directly after:
> [ 36.780990] NET: Registered protocol family 16


"MFGPT workaround"? That sounds a bit frightening.

Presumably, the BIOS is using the MFGPTs, but we're not detecting them as
being in use.

I'm assuming that booting with 'nomfgpt' works for you?


>
> >
> >
> > Also, could you provide a log with the following (untested) patch? I'm
> > curious how many MFGPTs we're actually detecting as being available, and
> > the existing code is backwards.
>
> The relevant part would be:
> [ 23.092507] NET: Registered protocol family 16
> [ 23.105875] geode-mfgpt: 8 MFGPT timers available
> [ 23.120247] geode-mfgpt: Registered timer 0
> [ 23.133076] mfgpt-timer: registering the MFGT timer as a clock event.
>
> Best regards,
> Arnd Hannemann
>

2008-01-17 19:53:31

by Arnd Hannemann

[permalink] [raw]
Subject: Re: 2.6.24-rc8 hangs at mfgpt-timer

diff -uNr linux-2.6.16.56/arch/i386/kernel/geode-mfgpt.c linux-2.6.16.56.patched/arch/i386/kernel/geode-mfgpt.c
--- linux-2.6.16.56/arch/i386/kernel/geode-mfgpt.c 1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.16.56.patched/arch/i386/kernel/geode-mfgpt.c 2007-12-11 14:57:36.000000000 +0100
@@ -0,0 +1,312 @@
+/* Driver/API for AMD Geode Multi-Function General Purpose Timers (MFGPT)
+ *
+ * Copyright (C) 2006, Advanced Micro Devices, 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.
+ */
+
+#include <linux/module.h>
+#include <linux/kernel.h>
+#include <linux/pci.h>
+#include <linux/pci_ids.h>
+#include <linux/interrupt.h>
+#include <linux/cdev.h>
+#include <asm/geode-mfgpt.h>
+#include <asm/io.h>
+#include <asm/msr.h>
+
+#define WORKAROUND
+
+#define MFGPT_IRQ_MSR 0x51400028
+#define MFGPT_NR_MSR 0x51400029
+
+#define MFGPT_MAX_TIMERS 7
+#define MFGPT_PCI_BAR 2
+
+#define F_AVAIL 0x01
+#define F_RESERVED 0x02
+
+static void *mfgpt_iobase;
+static int reserved_mask = 0;
+static struct class *mfgpt_class;
+
+static struct mfgpt_timer_t {
+ int index;
+ int flags;
+ struct module *owner;
+ struct class_device *cdev;
+} mfgpt_timers[MFGPT_MAX_TIMERS];
+
+void
+geode_mfgpt_write(int i, u16 r, u16 v)
+{
+ iowrite16(v, mfgpt_iobase + (r + (i * 8)));
+}
+
+EXPORT_SYMBOL(geode_mfgpt_write);
+
+u16
+geode_mfgpt_read(int i, u16 r)
+{
+ return ioread16(mfgpt_iobase + (r + (i * 8)));
+}
+
+EXPORT_SYMBOL(geode_mfgpt_read);
+
+static ssize_t
+sys_print_register(struct class_device *dev, char *buf, int reg)
+{
+ struct mfgpt_timer_t *timer = class_get_devdata(dev);
+ u16 val = geode_mfgpt_read(timer->index, reg);
+
+ return sprintf(buf, "%4.4X\n", val);
+}
+
+static ssize_t
+sys_show_setup(struct class_device *dev, char *buf)
+{
+ return sys_print_register(dev, buf, MFGPT_REG_SETUP);
+}
+
+static ssize_t
+sys_show_counter(struct class_device *dev, char *buf)
+{
+ return sys_print_register(dev, buf, MFGPT_REG_COUNTER);
+}
+
+static ssize_t
+sys_show_cmp1(struct class_device *dev, char *buf)
+{
+ return sys_print_register(dev, buf, MFGPT_REG_CMP1);
+}
+
+static ssize_t
+sys_show_cmp2(struct class_device *dev, char *buf)
+{
+ return sys_print_register(dev, buf, MFGPT_REG_CMP2);
+}
+
+static struct class_device_attribute mfgpt_attrs[] = {
+ __ATTR(setup, S_IRUGO, sys_show_setup, NULL),
+ __ATTR(counter, S_IRUGO, sys_show_counter, NULL),
+ __ATTR(cmp1, S_IRUGO, sys_show_cmp1, NULL),
+ __ATTR(cmp2, S_IRUGO, sys_show_cmp2, NULL),
+};
+
+void
+geode_mfgpt_toggle_event(int timer, int cmp, int event, int setup)
+{
+ u32 msr, mask, value, dummy;
+ int shift = (cmp == MFGPT_CMP1) ? 0 : 8;
+
+ switch(event) {
+ case MFGPT_EVENT_RESET:
+ msr = MFGPT_NR_MSR;
+ mask = 1 << (timer + 24);
+ break;
+
+ case MFGPT_EVENT_NMI:
+ msr = MFGPT_NR_MSR;
+ mask = 1 << (timer + shift);
+ break;
+
+ case MFGPT_EVENT_IRQ:
+ msr = MFGPT_IRQ_MSR;
+ mask = 1 << (timer + shift);
+ break;
+
+ default:
+ return;
+ }
+
+ rdmsr(msr, value, dummy);
+
+ if (setup)
+ value |= mask;
+ else
+ value &= ~mask;
+
+ wrmsr(msr, value, dummy);
+}
+
+EXPORT_SYMBOL(geode_mfgpt_toggle_event);
+
+void
+geode_mfgpt_set_irq(int timer, int cmp, int irq, int setup)
+{
+ u32 val, dummy;
+ int offset;
+
+ geode_mfgpt_toggle_event(timer, cmp, MFGPT_EVENT_IRQ, setup);
+
+ rdmsr(0x51400022, val, dummy);
+
+ offset = (timer % 4) * 4;
+
+ val &= ~((0xF << offset) | (0xF << (offset + 16)));
+
+ if (setup) {
+ val |= (irq & 0x0F) << (offset);
+ val |= (irq & 0x0F) << (offset + 16);
+ }
+
+ wrmsr(0x51400022, val, dummy);
+}
+
+int
+geode_mfgpt_alloc_timer(int timer, int domain, struct module *owner)
+{
+ int i;
+
+ /* If they requested a specific timer, try to honor that */
+ if (mfgpt_iobase == NULL)
+ return -ENODEV;
+
+ if (timer != MFGPT_TIMER_ANY) {
+ if (mfgpt_timers[timer].flags & F_AVAIL) {
+ mfgpt_timers[timer].flags &= ~F_AVAIL;
+ mfgpt_timers[timer].owner = owner;
+
+ printk("geode-mfgpt: Registered timer %d\n", timer);
+ return timer;
+ }
+ else if (mfgpt_timers[timer].owner == owner)
+ return timer;
+
+ /* Request failed - somebody else owns it */
+ return -1;
+ }
+
+ /* Try to find an available timer */
+
+ for(i = 0; i < MFGPT_MAX_TIMERS; i++) {
+
+ if ((mfgpt_timers[i].flags & F_AVAIL) &&
+ !(mfgpt_timers[i].flags & F_RESERVED)) {
+ mfgpt_timers[i].flags &= ~F_AVAIL;
+ mfgpt_timers[i].owner = owner;
+
+ printk("geode-mfgpt: Registered timer %d\n", i);
+ return i;
+ }
+
+ if (i == 5 && domain == MFGPT_DOMAIN_WORKING)
+ break;
+ }
+
+ /* No timers available - too bad */
+ return -1;
+}
+
+EXPORT_SYMBOL(geode_mfgpt_alloc_timer);
+
+static int
+mfgpt_setup_timer(struct pci_dev *pdev, int timer)
+{
+ dev_t devid = MKDEV(0, 0);
+ u16 val = geode_mfgpt_read(timer, MFGPT_REG_SETUP);
+ mfgpt_timers[timer].index = timer;
+
+ if (reserved_mask & (1 << timer))
+ mfgpt_timers[timer].flags |= F_RESERVED;
+
+ if (!(val & MFGPT_SETUP_SETUP)) {
+ int v;
+
+ mfgpt_timers[timer].flags = F_AVAIL;
+
+ /* Add the class device */
+ mfgpt_timers[timer].cdev =
+ class_device_create(mfgpt_class, NULL, devid,
+ &pdev->dev, "mfgpt%d", timer);
+
+ class_set_devdata(mfgpt_timers[timer].cdev, &mfgpt_timers[timer]);
+
+ for(v = 0; v < ARRAY_SIZE(mfgpt_attrs); v++)
+ if (class_device_create_file(mfgpt_timers[timer].cdev,
+ &mfgpt_attrs[v]))
+ printk(KERN_ERR "geode-mfpgt: Couldn't create %s\n",
+ mfgpt_attrs[v].attr.name);
+
+ return 1;
+ }
+
+ return 0;
+}
+
+static struct pci_device_id geode_sbdevs[] = {
+ { PCI_DEVICE(PCI_VENDOR_ID_NS, PCI_DEVICE_ID_NS_CS5535_ISA) },
+ { PCI_DEVICE(PCI_VENDOR_ID_AMD, PCI_DEVICE_ID_AMD_CS5536_ISA) }
+};
+
+static int __init
+geode_mfgpt_init(void)
+{
+ struct pci_dev *pdev = NULL;
+ int i, ret, dev, count = 0;
+
+#ifdef WORKAROUND
+ u32 val, dummy;
+
+ /* The following udocumented bit resets the MFGPT timers */
+
+ val = 0xFF;
+ wrmsr(0x5140002B, val, dummy);
+#endif
+
+ for (dev = 0; dev < ARRAY_SIZE(geode_sbdevs); dev++) {
+ pdev = pci_get_device(geode_sbdevs[dev].vendor,
+ geode_sbdevs[dev].device, NULL);
+
+ if (pdev != NULL)
+ break;
+ }
+
+ if (pdev == NULL) {
+ printk(KERN_ERR "geode-mfgpt: No PCI devices found\n");
+ goto err;
+ }
+
+ if ((ret = pci_enable_device_bars(pdev, 1 << MFGPT_PCI_BAR)))
+ goto err;
+
+ if ((ret = pci_request_region(pdev, MFGPT_PCI_BAR, "geode-mfgpt")))
+ goto err;
+
+ mfgpt_iobase = pci_iomap(pdev, MFGPT_PCI_BAR, 64);
+
+ if (mfgpt_iobase == NULL)
+ goto ereq;
+
+ mfgpt_class = class_create(THIS_MODULE, "mfgpt");
+
+ if (IS_ERR(mfgpt_class)) {
+ printk(KERN_ERR "geode-mfgpt: Unable to allocate the class.\n");
+ goto eiobase;
+ }
+
+ for(i = 0; i < MFGPT_MAX_TIMERS; i++)
+ count += mfgpt_setup_timer(pdev, i);
+
+ printk("geode-mfgpt: %d timers available.\n", count);
+ return 0;
+
+ eiobase:
+ pci_iounmap(pdev, mfgpt_iobase);
+ mfgpt_iobase = NULL;
+
+ ereq:
+ pci_release_region(pdev, MFGPT_PCI_BAR);
+
+ err:
+ printk("geode-mfgpt: Error initalizing the timers\n");
+ return -1;
+}
+
+device_initcall(geode_mfgpt_init);
+MODULE_AUTHOR("Advanced Micro Devices, Inc");
+MODULE_DESCRIPTION("Geode GX/LX MFGPT Driver");
+MODULE_LICENSE("GPL");
diff -uNr linux-2.6.16.56/arch/i386/kernel/Makefile linux-2.6.16.56.patched/arch/i386/kernel/Makefile
--- linux-2.6.16.56/arch/i386/kernel/Makefile 2007-11-01 03:23:29.000000000 +0100
+++ linux-2.6.16.56.patched/arch/i386/kernel/Makefile 2007-12-12 15:18:48.000000000 +0100
@@ -37,6 +37,7 @@
obj-$(CONFIG_DOUBLEFAULT) += doublefault.o
obj-$(CONFIG_VM86) += vm86.o
obj-$(CONFIG_EARLY_PRINTK) += early_printk.o
+obj-m += geode-mfgpt.o

EXTRA_AFLAGS := -traditional

diff -uNr linux-2.6.16.56/drivers/char/watchdog/geodewdt.c linux-2.6.16.56.patched/drivers/char/watchdog/geodewdt.c
--- linux-2.6.16.56/drivers/char/watchdog/geodewdt.c 1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.16.56.patched/drivers/char/watchdog/geodewdt.c 2007-12-12 15:22:31.000000000 +0100
@@ -0,0 +1,247 @@
+/* Watchdog timer for the Geode GX/LX
+ *
+ * Copyright (C) 2006, Advanced Micro Devices, 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.
+ */
+
+
+#include <linux/module.h>
+#include <linux/types.h>
+#include <linux/miscdevice.h>
+#include <linux/watchdog.h>
+#include <linux/fs.h>
+#include <linux/notifier.h>
+#include <linux/reboot.h>
+
+#include <asm/uaccess.h>
+#include <asm/geode-mfgpt.h>
+
+#define GEODEWDT_HZ 500
+#define GEODEWDT_SCALE 6
+#define GEODEWDT_MAX_SECONDS 131
+
+#define WDT_FLAGS_OPEN 1
+#define WDT_FLAGS_ORPHAN 2
+
+/* The defaults for the other timers are 60, so we'll use that too */
+
+static int cur_interval = 60;
+static int wdt_timer;
+static unsigned long wdt_flags;
+static int safe_close;
+
+static void geodewdt_ping(void)
+{
+ printk("PING\n");
+ geode_mfgpt_write(wdt_timer, MFGPT_REG_SETUP, 0);
+ geode_mfgpt_write(wdt_timer, MFGPT_REG_COUNTER, 0);
+ geode_mfgpt_write(wdt_timer, MFGPT_REG_SETUP, MFGPT_SETUP_CNTEN);
+}
+
+static void geodewdt_stop(void)
+{
+ printk("STOP\n");
+ geode_mfgpt_write(wdt_timer, MFGPT_REG_SETUP, 0);
+ geode_mfgpt_write(wdt_timer, MFGPT_REG_COUNTER, 0);
+}
+
+static int geodewdt_set_heartbeat(int val)
+{
+ if (val < 1 || val > GEODEWDT_MAX_SECONDS)
+ return -EINVAL;
+
+ geode_mfgpt_write(wdt_timer, MFGPT_REG_SETUP, 0);
+ geode_mfgpt_write(wdt_timer, MFGPT_REG_CMP2, val * GEODEWDT_HZ);
+ geode_mfgpt_write(wdt_timer, MFGPT_REG_COUNTER, 0);
+ geode_mfgpt_write(wdt_timer, MFGPT_REG_SETUP, MFGPT_SETUP_CNTEN);
+
+ printk("HEARTBEAT %d\n", val);
+ cur_interval = val;
+ return 0;
+}
+
+static int
+geodewdt_open(struct inode *inode, struct file *file)
+{
+ if (test_and_set_bit(WDT_FLAGS_OPEN, &wdt_flags))
+ return -EBUSY;
+
+ if (!test_and_clear_bit(WDT_FLAGS_ORPHAN, &wdt_flags))
+ __module_get(THIS_MODULE);
+
+ geodewdt_ping();
+ return nonseekable_open(inode, file);
+}
+
+static int
+geodewdt_release(struct inode *inode, struct file *file)
+{
+ if (safe_close) {
+ geodewdt_stop();
+ module_put(THIS_MODULE);
+ }
+ else {
+ printk(KERN_CRIT "Unexpected close - watchdog is not stopping.\n");
+ geodewdt_ping();
+
+ set_bit(WDT_FLAGS_ORPHAN, &wdt_flags);
+ }
+
+ clear_bit(WDT_FLAGS_OPEN, &wdt_flags);
+ safe_close = 0;
+ return 0;
+}
+
+static ssize_t
+geodewdt_write(struct file *file, const char __user *data, size_t len,
+ loff_t *ppos)
+{
+ if(len) {
+ size_t i;
+ safe_close = 0;
+
+ for (i = 0; i != len; i++) {
+ char c;
+
+ if (get_user(c, data + i))
+ return -EFAULT;
+
+ if (c == 'V')
+ safe_close = 1;
+ }
+ }
+
+ geodewdt_ping();
+ return len;
+}
+
+static int
+geodewdt_ioctl(struct inode *inode, struct file *file, unsigned int cmd,
+ unsigned long arg)
+{
+ void __user *argp = (void __user *)arg;
+ int __user *p = argp;
+ int interval;
+
+ static struct watchdog_info ident = {
+ .options = WDIOF_SETTIMEOUT | WDIOF_KEEPALIVEPING
+ | WDIOF_MAGICCLOSE,
+ .firmware_version = 0,
+ .identity = "Geode Watchdog",
+ };
+
+ switch(cmd) {
+ case WDIOC_GETSUPPORT:
+ return copy_to_user(argp, &ident,
+ sizeof(ident)) ? -EFAULT : 0;
+ break;
+
+ case WDIOC_GETSTATUS:
+ case WDIOC_GETBOOTSTATUS:
+ return put_user(0, p);
+
+ case WDIOC_KEEPALIVE:
+ geodewdt_ping();
+ return 0;
+
+ case WDIOC_SETTIMEOUT:
+ if (get_user(interval, p))
+ return -EFAULT;
+
+ if (geodewdt_set_heartbeat(interval))
+ return -EINVAL;
+
+/* Fall through */
+
+ case WDIOC_GETTIMEOUT:
+ return put_user(cur_interval, p);
+ }
+
+ return -ENOTTY;
+}
+
+static int geodewdt_notify_sys(struct notifier_block *this,
+ unsigned long code, void *unused)
+{
+ if(code==SYS_DOWN || code==SYS_HALT)
+ geodewdt_stop();
+
+ return NOTIFY_DONE;
+}
+
+static const struct file_operations geodewdt_fops = {
+ .owner = THIS_MODULE,
+ .llseek = no_llseek,
+ .write = geodewdt_write,
+ .ioctl = geodewdt_ioctl,
+ .open = geodewdt_open,
+ .release = geodewdt_release,
+};
+
+static struct miscdevice geodewdt_miscdev = {
+ .minor = WATCHDOG_MINOR,
+ .name = "geode-watchdog",
+ .fops = &geodewdt_fops
+};
+
+static struct notifier_block geodewdt_notifier = {
+ .notifier_call = geodewdt_notify_sys
+};
+
+static int __init geodewdt_init(void)
+{
+ int ret, timer;
+
+ timer = geode_mfgpt_alloc_timer(MFGPT_TIMER_ANY,
+ MFGPT_DOMAIN_ANY, THIS_MODULE);
+
+ if (timer == -1) {
+ printk(KERN_ERR "geodewdt: No timers were available\n");
+ return -ENODEV;
+ }
+
+ wdt_timer = timer;
+
+ /* Set up the timer */
+
+ geode_mfgpt_write(wdt_timer, MFGPT_REG_SETUP,
+ GEODEWDT_SCALE | (3 << 8));
+
+ /* Set up comparator 2 to reset when the event fires */
+ geode_mfgpt_set_event(wdt_timer, MFGPT_CMP2, MFGPT_EVENT_RESET);
+
+ /* Set up the initial timeout */
+
+ geode_mfgpt_write(wdt_timer, MFGPT_REG_CMP2,
+ cur_interval * GEODEWDT_HZ);
+
+ ret = misc_register(&geodewdt_miscdev);
+ if (ret)
+ return ret;
+
+ ret = register_reboot_notifier(&geodewdt_notifier);
+
+ if (ret)
+ misc_deregister(&geodewdt_miscdev);
+
+ return ret;
+}
+
+static void __exit
+geodewdt_exit(void)
+{
+ misc_deregister(&geodewdt_miscdev);
+ unregister_reboot_notifier(&geodewdt_notifier);
+}
+
+module_init(geodewdt_init);
+module_exit(geodewdt_exit);
+
+MODULE_AUTHOR("Advanced Micro Devices, Inc");
+MODULE_DESCRIPTION("Geode GX/LX Watchdog Driver");
+MODULE_LICENSE("GPL");
+MODULE_ALIAS_MISCDEV(WATCHDOG_MINOR);
diff -uNr linux-2.6.16.56/drivers/char/watchdog/Kconfig linux-2.6.16.56.patched/drivers/char/watchdog/Kconfig
--- linux-2.6.16.56/drivers/char/watchdog/Kconfig 2007-11-01 03:23:29.000000000 +0100
+++ linux-2.6.16.56.patched/drivers/char/watchdog/Kconfig 2007-12-12 15:22:31.000000000 +0100
@@ -209,6 +209,14 @@
You can compile this driver directly into the kernel, or use
it as a module. The module will be called sc520_wdt.

+config GEODE_WDT
+ tristate "AMD Geode GX/LX Watchdog Timer"
+ depends on WATCHDOG && X86
+ help
+ Enable support for a hardware based watchdog timer running
+ on the MFGPT timers available on AMD Geode GX and LX based
+ platforms.
+
config EUROTECH_WDT
tristate "Eurotech CPU-1220/1410 Watchdog Timer"
depends on WATCHDOG && X86
diff -uNr linux-2.6.16.56/drivers/char/watchdog/Makefile linux-2.6.16.56.patched/drivers/char/watchdog/Makefile
--- linux-2.6.16.56/drivers/char/watchdog/Makefile 2007-11-01 03:23:29.000000000 +0100
+++ linux-2.6.16.56.patched/drivers/char/watchdog/Makefile 2007-12-12 15:22:31.000000000 +0100
@@ -38,6 +38,7 @@
obj-$(CONFIG_ALIM7101_WDT) += alim7101_wdt.o
obj-$(CONFIG_SC520_WDT) += sc520_wdt.o
obj-$(CONFIG_EUROTECH_WDT) += eurotechwdt.o
+obj-$(CONFIG_GEODE_WDT) += geodewdt.o
obj-$(CONFIG_IB700_WDT) += ib700wdt.o
obj-$(CONFIG_IBMASR) += ibmasr.o
obj-$(CONFIG_WAFER_WDT) += wafer5823wdt.o
diff -uNr linux-2.6.16.56/include/asm-i386/geode-mfgpt.h linux-2.6.16.56.patched/include/asm-i386/geode-mfgpt.h
--- linux-2.6.16.56/include/asm-i386/geode-mfgpt.h 1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.16.56.patched/include/asm-i386/geode-mfgpt.h 2007-12-11 14:57:37.000000000 +0100
@@ -0,0 +1,57 @@
+/* Driver/API for AMD Geode Multi-Function General Purpose Timers (MFGPT)
+ *
+ * Copyright (C) 2006, Advanced Micro Devices, 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.
+ *
+ */
+
+#ifndef MFGPT_GEODE_H_
+#define MFGPT_GEODE_H_
+
+#define MFGPT_TIMER_ANY -1
+
+#define MFGPT_DOMAIN_WORKING 1
+#define MFGPT_DOMAIN_STANDBY 2
+#define MFGPT_DOMAIN_ANY (MFGPT_DOMAIN_WORKING | MFGPT_DOMAIN_STANDBY)
+
+#define MFGPT_CMP1 0
+#define MFGPT_CMP2 1
+
+#define MFGPT_EVENT_IRQ 0
+#define MFGPT_EVENT_NMI 1
+#define MFGPT_EVENT_RESET 3
+
+#define MFGPT_REG_CMP1 0
+#define MFGPT_REG_CMP2 2
+#define MFGPT_REG_COUNTER 4
+#define MFGPT_REG_SETUP 6
+
+#define MFGPT_SETUP_CNTEN (1 << 15)
+#define MFGPT_SETUP_CMP2 (1 << 14)
+#define MFGPT_SETUP_CMP1 (1 << 13)
+#define MFGPT_SETUP_SETUP (1 << 12)
+#define MFGPT_SETUP_STOPEN (1 << 11)
+#define MFGPT_SETUP_EXTEN (1 << 10)
+#define MFGPT_SETUP_REVEN (1 << 5)
+#define MFGPT_SETUP_CLKSEL (1 << 4)
+
+extern void geode_mfgpt_toggle_event(int, int, int, int);
+
+#define geode_mfgpt_set_event(t,c,e) geode_mfgpt_toggle_event(t,c,e,1)
+#define geode_mfgpt_clear_event(t,c,e) geode_mfgpt_toggle_event(t,c,e,0)
+
+extern void geode_mfgpt_set_irq(int, int, int, int);
+
+#define geode_mfgpt_setup_irq(t, c, i) geode_mfgpt_set_irq(t,c,i,1)
+#define geode_mfgpt_release_irq(t, c, i) geode_mfgpt_set_irq(t,c,i,0)
+
+extern void geode_mfgpt_write(int, u16, u16);
+extern u16 geode_mfgpt_read(int, u16);
+
+extern int geode_mfgpt_alloc_timer(int, int, struct module *);
+
+#endif


Attachments:
patch_12_cs5535_gpt_wdt_alix_2.6.16 (17.00 kB)

2008-01-17 20:42:18

by Andres Salomon

[permalink] [raw]
Subject: Re: 2.6.24-rc8 hangs at mfgpt-timer

On Thu, 17 Jan 2008 20:53:57 +0100
Arnd Hannemann <[email protected]> wrote:

> Andres Salomon schrieb:
> > On Thu, 17 Jan 2008 10:54:30 +0100
> > Arnd Hannemann <[email protected]> wrote:
> >
> >> Andres Salomon schrieb:
> >>> On Wed, 16 Jan 2008 16:19:12 -0500
> >>> Andres Salomon <[email protected]> wrote:
> >>>
> >>>> On Wed, 16 Jan 2008 18:44:07 +0100
> >>>> Arnd Hannemann <[email protected]> wrote:
> >>>>
> >>>>> Hi,
> >>>>>
> >>>>> I'm trying to boot 2.6.24-rc8 on a GEODE LX board (ALIX.3),
> >>>>> and it hangs during boot:
> >>>>>
> >>>>> [ 12.689971] NET: Registered protocol family 16
> >>>>> [ 12.703329] geode-mfgpt: Registered timer 0
> >>>>> [ 12.716149] mfgpt-timer: registering the MFGT timer as a clock event...
> >>>>>
> >>>> What BIOS are you using? It's possible that our detection code is
> >>>> failing to detect in-use timers.
> >> I'm using v0.99 (latest available).
> >
> >
> > v0.99 of what? Jordan seems to think it's an Award BIOS, but I'd like
> > to make sure.
>
> Its an ALIX board from PCEngines, they have their own BIOS
> implementation (tinyBios).
> http://www.pcengines.ch/alix.htm
>

Ah, okay. I couldn't find anything about MFGPTs in the available
source, but I did find the following:

http://article.gmane.org/gmane.linux.distributions.voyage.general/1824

It would appear that something between 0.90 and 0.92 changed that
has broken things. There's also a changelog here:

http://forum.pfsense.org/index.php?topic=6729.15

Note two MFGPT-related entries in 0.92:

- disable CS5536 diverse device power management to avoid
MFGPT /
interrupt issues.

- MFGPT issues: please observe AMD CS5536 data book section
5.16.3,
incorrect initialization sequence can HANG the system.


I'm assuming the first is messing w/ DIVIL_GLD_MSR_PM...

2008-01-17 21:19:17

by Jordan Crouse

[permalink] [raw]
Subject: Re: 2.6.24-rc8 hangs at mfgpt-timer

On 17/01/08 20:53 +0100, Arnd Hannemann wrote:
> Andres Salomon schrieb:
> > On Thu, 17 Jan 2008 10:54:30 +0100
> > Arnd Hannemann <[email protected]> wrote:
> >
> >> Andres Salomon schrieb:
> >>> On Wed, 16 Jan 2008 16:19:12 -0500
> >>> Andres Salomon <[email protected]> wrote:
> >>>
> >>>> On Wed, 16 Jan 2008 18:44:07 +0100
> >>>> Arnd Hannemann <[email protected]> wrote:
> >>>>
> >>>>> Hi,
> >>>>>
> >>>>> I'm trying to boot 2.6.24-rc8 on a GEODE LX board (ALIX.3),
> >>>>> and it hangs during boot:
> >>>>>
> >>>>> [ 12.689971] NET: Registered protocol family 16
> >>>>> [ 12.703329] geode-mfgpt: Registered timer 0
> >>>>> [ 12.716149] mfgpt-timer: registering the MFGT timer as a clock event...
> >>>>>
> >>>> What BIOS are you using? It's possible that our detection code is
> >>>> failing to detect in-use timers.
> >> I'm using v0.99 (latest available).
> >
> >
> > v0.99 of what? Jordan seems to think it's an Award BIOS, but I'd like
> > to make sure.
>
> Its an ALIX board from PCEngines, they have their own BIOS
> implementation (tinyBios).
> http://www.pcengines.ch/alix.htm
>
> >
> >> Also note when I do enable the mysterios "MFGPT workaround" option in
> >> the bios the machine hangs directly after:
> >> [ 36.780990] NET: Registered protocol family 16
> >
> >
> > "MFGPT workaround"? That sounds a bit frightening.
> >
> > Presumably, the BIOS is using the MFGPTs, but we're not detecting them as
> > being in use.
> Yes I think so too, for the fun of it I compiled a 2.6.16.29 kernel with
> the attached patch from fi4l.

Okay - thats an MFPGT patch from pre-OLPC days. I am the guilty and
dubious party. We changed the API to work better with the timer tick,
and thats the version that ended up in the kernel.

I really wish I could take back this patch, because it keeps coming back
to torment me. We must, as a people, put it behind us and forgot it. :)

> relevant output is this:
> [ 31.015425] geode-mfgpt: 7 timers available.
> ...
> [ 31.245875] geode-mfgpt: Registered timer 0

> So the above kernel detects only 7 timers not 8, and it works. But note
> that timer 0 is not used as a clock event source but as a watchdog,
> which btw actually works fine :-)

It detects 7 timers because of a bug in the code - there really are 8
timers, which the current code correctly identifies.

> The funny thing is the #define workaround part of this dubious patch and
> its interaction with the bios:
>
> #ifdef WORKAROUND:
> I have to turn the "MFPGT workaround" option in the bios ON, to boot
> the kernel probably.
>
> #ifndef WORKAROUND:
> I have to turn the "MFPGT workaround" option in the bios OFF, to boot
> the kernel probably.

So the workaround works around the workaround. Fun. I think that Mitch
Bradley verified that if you write the magic MSR when all the clocks are
already clear that bad things happen. The workaround probably adds a
dummy clock in. Notice that the "magic MSR" no longer is in the vanilla
code, and thats the way it should be. If the BIOS doesn't allow use of
the clocks, then we have to live with that.

So, based on everything you are saying, I think its clear that our
problem isn't in the MFGPT, but rather in the timer tick (because, as
you said, the watchdog works). We try to use IRQ 7 for the tick, which
Andres and I totally plucked out of thin air based on what we had to work
with on OLPC. Its totally possible that the TinyBIOS had other ideas.
Please try to boot with nomfgpt, and see which interrupts are free, and
use mfgpt_irq= to change it to something else if 7 is in use. Based on
your findings above, you'll probably need to leave the MFGPT workaround
off from now on.

I'll port the watchdog timer to the new API, and we can use that instead
of the timer tick to just make sure that it isn't the timer that is broken.
Also, hopefully that will cease the stream of angry emails asking me why
the ancient patch doesn't work on a current kernel... :)

Jordan

2008-01-17 21:51:39

by Arnd Hannemann

[permalink] [raw]
Subject: Re: 2.6.24-rc8 hangs at mfgpt-timer

Jordan Crouse schrieb:
> On 17/01/08 20:53 +0100, Arnd Hannemann wrote:
>> Andres Salomon schrieb:
>>> On Thu, 17 Jan 2008 10:54:30 +0100
>>> Arnd Hannemann <[email protected]> wrote:
>>>
>>>> Andres Salomon schrieb:
>>>>> On Wed, 16 Jan 2008 16:19:12 -0500
>>>>> Andres Salomon <[email protected]> wrote:
>>>>>
>>>>>> On Wed, 16 Jan 2008 18:44:07 +0100
>>>>>> Arnd Hannemann <[email protected]> wrote:
>>>>>>
>>>>>>> Hi,
>>>>>>>
>>>>>>> I'm trying to boot 2.6.24-rc8 on a GEODE LX board (ALIX.3),
>>>>>>> and it hangs during boot:
>>>>>>>
>>>>>>> [ 12.689971] NET: Registered protocol family 16
>>>>>>> [ 12.703329] geode-mfgpt: Registered timer 0
>>>>>>> [ 12.716149] mfgpt-timer: registering the MFGT timer as a clock event...
>>>>>>>
>>>>>> What BIOS are you using? It's possible that our detection code is
>>>>>> failing to detect in-use timers.
>>>> I'm using v0.99 (latest available).
>>>
>>> v0.99 of what? Jordan seems to think it's an Award BIOS, but I'd like
>>> to make sure.
>> Its an ALIX board from PCEngines, they have their own BIOS
>> implementation (tinyBios).
>> http://www.pcengines.ch/alix.htm
>>
>>>> Also note when I do enable the mysterios "MFGPT workaround" option in
>>>> the bios the machine hangs directly after:
>>>> [ 36.780990] NET: Registered protocol family 16
>>>
>>> "MFGPT workaround"? That sounds a bit frightening.
>>>
>>> Presumably, the BIOS is using the MFGPTs, but we're not detecting them as
>>> being in use.
>> Yes I think so too, for the fun of it I compiled a 2.6.16.29 kernel with
>> the attached patch from fi4l.
>
> Okay - thats an MFPGT patch from pre-OLPC days. I am the guilty and
> dubious party. We changed the API to work better with the timer tick,
> and thats the version that ended up in the kernel.
>
> I really wish I could take back this patch, because it keeps coming back
> to torment me. We must, as a people, put it behind us and forgot it. :)
>
>> relevant output is this:
>> [ 31.015425] geode-mfgpt: 7 timers available.
>> ...
>> [ 31.245875] geode-mfgpt: Registered timer 0
>
>> So the above kernel detects only 7 timers not 8, and it works. But note
>> that timer 0 is not used as a clock event source but as a watchdog,
>> which btw actually works fine :-)
>
> It detects 7 timers because of a bug in the code - there really are 8
> timers, which the current code correctly identifies.
Yes I can confirm this, changed MFGPT_MAX_TIMERS from 7 to 8 in the old
kernel and it still works.

>> The funny thing is the #define workaround part of this dubious patch and
>> its interaction with the bios:
>>
>> #ifdef WORKAROUND:
>> I have to turn the "MFPGT workaround" option in the bios ON, to boot
>> the kernel probably.
>>
>> #ifndef WORKAROUND:
>> I have to turn the "MFPGT workaround" option in the bios OFF, to boot
>> the kernel probably.
>
> So the workaround works around the workaround. Fun. I think that Mitch
> Bradley verified that if you write the magic MSR when all the clocks are
> already clear that bad things happen. The workaround probably adds a
> dummy clock in. Notice that the "magic MSR" no longer is in the vanilla
> code, and thats the way it should be. If the BIOS doesn't allow use of
> the clocks, then we have to live with that.
>
> So, based on everything you are saying, I think its clear that our
> problem isn't in the MFGPT, but rather in the timer tick (because, as
> you said, the watchdog works). We try to use IRQ 7 for the tick, which
> Andres and I totally plucked out of thin air based on what we had to work
> with on OLPC. Its totally possible that the TinyBIOS had other ideas.
> Please try to boot with nomfgpt, and see which interrupts are free, and
> use mfgpt_irq= to change it to something else if 7 is in use. Based on
> your findings above, you'll probably need to leave the MFGPT workaround
> off from now on.
Great analysis! I think I can confirm this too. I tried the following:

First in mfgpt_timer_setup I commented out "clockevents_register_device"
result: the system still hangs with "registering the MFGT timer as a
clock event" !

Then I also commented out "ret = setup_irq(irq, &mfgptirq)".
result: system boots, voila!

However the vendor claims that 7 should be used (from the bios changelog):
"v0.90 (IRQ7 is no longer directed to the LPC bus, used as a default
interrupt for MFGPT high resolution timer."

There is also a interrupt map in the bios[0] readme:

IRQ0 timer
IRQ1 KBD (LPC)
IRQ2 cascade
IRQ3 COM1 serial (internal / LPC)
IRQ4 COM2 serial (LPC)
IRQ5 audio (CS5536)
IRQ6 FDC (LPC)
IRQ7 spare, used for MFGPT high resolution timer

IRQ8 RTC
IRQ9 PCI INTA
IRQ10 PCI INTB
IRQ11 PCI INTC
IRQ12 PCI INTD
IRQ13 floating point
IRQ14 IDE HDD
IRQ15 USB (CS5536)

/proc/interrupts on a running system looks like this:
CPU0
0: 12329 XT-PIC timer
2: 0 XT-PIC cascade
4: 240 XT-PIC serial
8: 3 XT-PIC rtc
9: 558 XT-PIC wifi0
10: 67591 XT-PIC eth0
11: 622 XT-PIC wifi1
NMI: 0
ERR: 0

> I'll port the watchdog timer to the new API, and we can use that instead
> of the timer tick to just make sure that it isn't the timer that is broken.
> Also, hopefully that will cease the stream of angry emails asking me why
> the ancient patch doesn't work on a current kernel... :)
Watchdog for the new API would be great :-)

> Jordan
Thanks for your effort!

[0] http://www.pcengines.ch/file/alixb099.zip

2008-01-17 22:39:29

by Jordan Crouse

[permalink] [raw]
Subject: Re: 2.6.24-rc8 hangs at mfgpt-timer

On 17/01/08 22:50 +0100, Arnd Hannemann wrote:
> Jordan Crouse schrieb:
> > On 17/01/08 20:53 +0100, Arnd Hannemann wrote:
> >> Andres Salomon schrieb:
> >>> On Thu, 17 Jan 2008 10:54:30 +0100
> >>> Arnd Hannemann <[email protected]> wrote:
> >>>
> >>>> Andres Salomon schrieb:
> >>>>> On Wed, 16 Jan 2008 16:19:12 -0500
> >>>>> Andres Salomon <[email protected]> wrote:
> >>>>>
> >>>>>> On Wed, 16 Jan 2008 18:44:07 +0100
> >>>>>> Arnd Hannemann <[email protected]> wrote:
> >>>>>>
> >>>>>>> Hi,
> >>>>>>>
> >>>>>>> I'm trying to boot 2.6.24-rc8 on a GEODE LX board (ALIX.3),
> >>>>>>> and it hangs during boot:
> >>>>>>>
> >>>>>>> [ 12.689971] NET: Registered protocol family 16
> >>>>>>> [ 12.703329] geode-mfgpt: Registered timer 0
> >>>>>>> [ 12.716149] mfgpt-timer: registering the MFGT timer as a clock event...
> >>>>>>>
> >>>>>> What BIOS are you using? It's possible that our detection code is
> >>>>>> failing to detect in-use timers.
> >>>> I'm using v0.99 (latest available).
> >>>
> >>> v0.99 of what? Jordan seems to think it's an Award BIOS, but I'd like
> >>> to make sure.
> >> Its an ALIX board from PCEngines, they have their own BIOS
> >> implementation (tinyBios).
> >> http://www.pcengines.ch/alix.htm
> >>
> >>>> Also note when I do enable the mysterios "MFGPT workaround" option in
> >>>> the bios the machine hangs directly after:
> >>>> [ 36.780990] NET: Registered protocol family 16
> >>>
> >>> "MFGPT workaround"? That sounds a bit frightening.
> >>>
> >>> Presumably, the BIOS is using the MFGPTs, but we're not detecting them as
> >>> being in use.
> >> Yes I think so too, for the fun of it I compiled a 2.6.16.29 kernel with
> >> the attached patch from fi4l.
> >
> > Okay - thats an MFPGT patch from pre-OLPC days. I am the guilty and
> > dubious party. We changed the API to work better with the timer tick,
> > and thats the version that ended up in the kernel.
> >
> > I really wish I could take back this patch, because it keeps coming back
> > to torment me. We must, as a people, put it behind us and forgot it. :)
> >
> >> relevant output is this:
> >> [ 31.015425] geode-mfgpt: 7 timers available.
> >> ...
> >> [ 31.245875] geode-mfgpt: Registered timer 0
> >
> >> So the above kernel detects only 7 timers not 8, and it works. But note
> >> that timer 0 is not used as a clock event source but as a watchdog,
> >> which btw actually works fine :-)
> >
> > It detects 7 timers because of a bug in the code - there really are 8
> > timers, which the current code correctly identifies.
> Yes I can confirm this, changed MFGPT_MAX_TIMERS from 7 to 8 in the old
> kernel and it still works.
>
> >> The funny thing is the #define workaround part of this dubious patch and
> >> its interaction with the bios:
> >>
> >> #ifdef WORKAROUND:
> >> I have to turn the "MFPGT workaround" option in the bios ON, to boot
> >> the kernel probably.
> >>
> >> #ifndef WORKAROUND:
> >> I have to turn the "MFPGT workaround" option in the bios OFF, to boot
> >> the kernel probably.
> >
> > So the workaround works around the workaround. Fun. I think that Mitch
> > Bradley verified that if you write the magic MSR when all the clocks are
> > already clear that bad things happen. The workaround probably adds a
> > dummy clock in. Notice that the "magic MSR" no longer is in the vanilla
> > code, and thats the way it should be. If the BIOS doesn't allow use of
> > the clocks, then we have to live with that.
> >
> > So, based on everything you are saying, I think its clear that our
> > problem isn't in the MFGPT, but rather in the timer tick (because, as
> > you said, the watchdog works). We try to use IRQ 7 for the tick, which
> > Andres and I totally plucked out of thin air based on what we had to work
> > with on OLPC. Its totally possible that the TinyBIOS had other ideas.
> > Please try to boot with nomfgpt, and see which interrupts are free, and
> > use mfgpt_irq= to change it to something else if 7 is in use. Based on
> > your findings above, you'll probably need to leave the MFGPT workaround
> > off from now on.
> Great analysis! I think I can confirm this too. I tried the following:
>
> First in mfgpt_timer_setup I commented out "clockevents_register_device"
> result: the system still hangs with "registering the MFGT timer as a
> clock event" !
>
> Then I also commented out "ret = setup_irq(irq, &mfgptirq)".
> result: system boots, voila!

Hmmm - not sure whats happening here. I wonder if we're stuck in an
interrupt storm of some sort as soon as you register the interrupt handler.
But I would think that whatever was causing the interrupt storm would be
running well before we hit setup_irq(), and you would be recording "nobody
cared" interrupts left and right.

The thing that scares me is that the TinyBIOS seems to know that we want
to use the MFGPT timers, and I wonder if they did anything behind the scenes
to "help us out" even though we didn't ask for it.

I don't know how easy it would be for you - but can you try reading
MSRs 0x51400020 - 0x51400023? If you need a command line app to do it,
you can use rdmsr from here:

http://wiki.laptop.org/go/Flashing_LinuxBIOS_on_A-Test_Boards

> Watchdog for the new API would be great :-)

Coming soon.

Jordan
--
Jordan Crouse
Systems Software Development Engineer
Advanced Micro Devices, Inc.

2008-01-17 22:55:30

by Arnd Hannemann

[permalink] [raw]
Subject: Re: 2.6.24-rc8 hangs at mfgpt-timer

Jordan Crouse wrote:
> On 17/01/08 22:50 +0100, Arnd Hannemann wrote:
>> Jordan Crouse schrieb:
>>> On 17/01/08 20:53 +0100, Arnd Hannemann wrote:
>>>> Andres Salomon schrieb:
>>>>> On Thu, 17 Jan 2008 10:54:30 +0100
>>>>> Arnd Hannemann <[email protected]> wrote:
>>>>>
>>>>>> Andres Salomon schrieb:
>>>>>>> On Wed, 16 Jan 2008 16:19:12 -0500
>>>>>>> Andres Salomon <[email protected]> wrote:
>>>>>>>
>>>>>>>> On Wed, 16 Jan 2008 18:44:07 +0100
>>>>>>>> Arnd Hannemann <[email protected]> wrote:
>>>>>>>>
>>>>>>>>> Hi,
>>>>>>>>>
>>>>>>>>> I'm trying to boot 2.6.24-rc8 on a GEODE LX board (ALIX.3),
>>>>>>>>> and it hangs during boot:
>>>>>>>>>
>>>>>>>>> [ 12.689971] NET: Registered protocol family 16
>>>>>>>>> [ 12.703329] geode-mfgpt: Registered timer 0
>>>>>>>>> [ 12.716149] mfgpt-timer: registering the MFGT timer as a clock event...
>>>>>>>>>
>>>>>>>> What BIOS are you using? It's possible that our detection code is
>>>>>>>> failing to detect in-use timers.
>>>>>> I'm using v0.99 (latest available).
>>>>> v0.99 of what? Jordan seems to think it's an Award BIOS, but I'd like
>>>>> to make sure.
>>>> Its an ALIX board from PCEngines, they have their own BIOS
>>>> implementation (tinyBios).
>>>> http://www.pcengines.ch/alix.htm
>>>>
>>>>>> Also note when I do enable the mysterios "MFGPT workaround" option in
>>>>>> the bios the machine hangs directly after:
>>>>>> [ 36.780990] NET: Registered protocol family 16
>>>>> "MFGPT workaround"? That sounds a bit frightening.
>>>>>
>>>>> Presumably, the BIOS is using the MFGPTs, but we're not detecting them as
>>>>> being in use.
>>>> Yes I think so too, for the fun of it I compiled a 2.6.16.29 kernel with
>>>> the attached patch from fi4l.
>>> Okay - thats an MFPGT patch from pre-OLPC days. I am the guilty and
>>> dubious party. We changed the API to work better with the timer tick,
>>> and thats the version that ended up in the kernel.
>>>
>>> I really wish I could take back this patch, because it keeps coming back
>>> to torment me. We must, as a people, put it behind us and forgot it. :)
>>>
>>>> relevant output is this:
>>>> [ 31.015425] geode-mfgpt: 7 timers available.
>>>> ...
>>>> [ 31.245875] geode-mfgpt: Registered timer 0
>>>> So the above kernel detects only 7 timers not 8, and it works. But note
>>>> that timer 0 is not used as a clock event source but as a watchdog,
>>>> which btw actually works fine :-)
>>> It detects 7 timers because of a bug in the code - there really are 8
>>> timers, which the current code correctly identifies.
>> Yes I can confirm this, changed MFGPT_MAX_TIMERS from 7 to 8 in the old
>> kernel and it still works.
>>
>>>> The funny thing is the #define workaround part of this dubious patch and
>>>> its interaction with the bios:
>>>>
>>>> #ifdef WORKAROUND:
>>>> I have to turn the "MFPGT workaround" option in the bios ON, to boot
>>>> the kernel probably.
>>>>
>>>> #ifndef WORKAROUND:
>>>> I have to turn the "MFPGT workaround" option in the bios OFF, to boot
>>>> the kernel probably.
>>> So the workaround works around the workaround. Fun. I think that Mitch
>>> Bradley verified that if you write the magic MSR when all the clocks are
>>> already clear that bad things happen. The workaround probably adds a
>>> dummy clock in. Notice that the "magic MSR" no longer is in the vanilla
>>> code, and thats the way it should be. If the BIOS doesn't allow use of
>>> the clocks, then we have to live with that.
>>>
>>> So, based on everything you are saying, I think its clear that our
>>> problem isn't in the MFGPT, but rather in the timer tick (because, as
>>> you said, the watchdog works). We try to use IRQ 7 for the tick, which
>>> Andres and I totally plucked out of thin air based on what we had to work
>>> with on OLPC. Its totally possible that the TinyBIOS had other ideas.
>>> Please try to boot with nomfgpt, and see which interrupts are free, and
>>> use mfgpt_irq= to change it to something else if 7 is in use. Based on
>>> your findings above, you'll probably need to leave the MFGPT workaround
>>> off from now on.
>> Great analysis! I think I can confirm this too. I tried the following:
>>
>> First in mfgpt_timer_setup I commented out "clockevents_register_device"
>> result: the system still hangs with "registering the MFGT timer as a
>> clock event" !
>>
>> Then I also commented out "ret = setup_irq(irq, &mfgptirq)".
>> result: system boots, voila!
>
> Hmmm - not sure whats happening here. I wonder if we're stuck in an
> interrupt storm of some sort as soon as you register the interrupt handler.
> But I would think that whatever was causing the interrupt storm would be
> running well before we hit setup_irq(), and you would be recording "nobody
> cared" interrupts left and right.

Interesting thing is that it hangs not in setup_irq() but later, right
after printing the newline of the printk.

> The thing that scares me is that the TinyBIOS seems to know that we want
> to use the MFGPT timers, and I wonder if they did anything behind the scenes
> to "help us out" even though we didn't ask for it.
>
> I don't know how easy it would be for you - but can you try reading
> MSRs 0x51400020 - 0x51400023? If you need a command line app to do it,
> you can use rdmsr from here:
>
> http://wiki.laptop.org/go/Flashing_LinuxBIOS_on_A-Test_Boards

MSR register 0x51400020 => b7:ef:5f:f4:bf:d1:95:68
MSR register 0x51400021 => b7:fd:1f:f4:bf:cf:5a:d8
MSR register 0x51400022 => b7:f3:bf:f4:bf:f5:fb:a8
MSR register 0x51400023 => b7:fb:9f:f4:bf:fd:d9:f8

>
>> Watchdog for the new API would be great :-)
>
> Coming soon.
>
> Jordan

Arnd

2008-01-17 22:59:27

by Jordan Crouse

[permalink] [raw]
Subject: Re: 2.6.24-rc8 hangs at mfgpt-timer

On 17/01/08 23:52 +0100, Arnd Hannemann wrote:

<snip>

> > Hmmm - not sure whats happening here. I wonder if we're stuck in an
> > interrupt storm of some sort as soon as you register the interrupt handler.
> > But I would think that whatever was causing the interrupt storm would be
> > running well before we hit setup_irq(), and you would be recording "nobody
> > cared" interrupts left and right.
>
> Interesting thing is that it hangs not in setup_irq() but later, right
> after printing the newline of the printk.

THat makes me think interrupt storm even more.

> > The thing that scares me is that the TinyBIOS seems to know that we want
> > to use the MFGPT timers, and I wonder if they did anything behind the scenes
> > to "help us out" even though we didn't ask for it.
> >
> > I don't know how easy it would be for you - but can you try reading
> > MSRs 0x51400020 - 0x51400023? If you need a command line app to do it,
> > you can use rdmsr from here:
> >
> > http://wiki.laptop.org/go/Flashing_LinuxBIOS_on_A-Test_Boards
>
> MSR register 0x51400020 => b7:ef:5f:f4:bf:d1:95:68
> MSR register 0x51400021 => b7:fd:1f:f4:bf:cf:5a:d8
> MSR register 0x51400022 => b7:f3:bf:f4:bf:f5:fb:a8
> MSR register 0x51400023 => b7:fb:9f:f4:bf:fd:d9:f8

Hmmm - those look wrong. Is /dev/cpu/0/msr there? The applet on the
wiki has a bug that doesn't check for it.

Jordan

--
Jordan Crouse
Systems Software Development Engineer
Advanced Micro Devices, Inc.

2008-01-17 23:39:09

by Arnd Hannemann

[permalink] [raw]
Subject: Re: 2.6.24-rc8 hangs at mfgpt-timer

Jordan Crouse schrieb:
> On 17/01/08 23:52 +0100, Arnd Hannemann wrote:
>
> <snip>
>
>>> Hmmm - not sure whats happening here. I wonder if we're stuck in an
>>> interrupt storm of some sort as soon as you register the interrupt handler.
>>> But I would think that whatever was causing the interrupt storm would be
>>> running well before we hit setup_irq(), and you would be recording "nobody
>>> cared" interrupts left and right.
>> Interesting thing is that it hangs not in setup_irq() but later, right
>> after printing the newline of the printk.
>
> THat makes me think interrupt storm even more.
>
>>> The thing that scares me is that the TinyBIOS seems to know that we want
>>> to use the MFGPT timers, and I wonder if they did anything behind the scenes
>>> to "help us out" even though we didn't ask for it.
>>>
>>> I don't know how easy it would be for you - but can you try reading
>>> MSRs 0x51400020 - 0x51400023? If you need a command line app to do it,
>>> you can use rdmsr from here:
>>>
>>> http://wiki.laptop.org/go/Flashing_LinuxBIOS_on_A-Test_Boards
>> MSR register 0x51400020 => b7:ef:5f:f4:bf:d1:95:68
>> MSR register 0x51400021 => b7:fd:1f:f4:bf:cf:5a:d8
>> MSR register 0x51400022 => b7:f3:bf:f4:bf:f5:fb:a8
>> MSR register 0x51400023 => b7:fb:9f:f4:bf:fd:d9:f8
>
> Hmmm - those look wrong. Is /dev/cpu/0/msr there? The applet on the
> wiki has a bug that doesn't check for it.
I'm sorry, I should have checked: I didn't execute rdmsr as root.
The correct ones:

MSR register 0x51400020 => 00:00:00:00:00:00:0f:00
MSR register 0x51400021 => 00:00:00:00:04:00:00:00
MSR register 0x51400022 => 00:00:00:00:00:00:00:00
MSR register 0x51400023 => 00:00:00:00:00:0c:ba:90

Arnd

2008-01-18 01:17:22

by Jordan Crouse

[permalink] [raw]
Subject: Re: 2.6.24-rc8 hangs at mfgpt-timer

On 18/01/08 00:39 +0100, Arnd Hannemann wrote:
> Jordan Crouse schrieb:
> > On 17/01/08 23:52 +0100, Arnd Hannemann wrote:
> >
> > <snip>
> >
> >>> Hmmm - not sure whats happening here. I wonder if we're stuck in an
> >>> interrupt storm of some sort as soon as you register the interrupt handler.
> >>> But I would think that whatever was causing the interrupt storm would be
> >>> running well before we hit setup_irq(), and you would be recording "nobody
> >>> cared" interrupts left and right.
> >> Interesting thing is that it hangs not in setup_irq() but later, right
> >> after printing the newline of the printk.
> >
> > THat makes me think interrupt storm even more.
> >
> >>> The thing that scares me is that the TinyBIOS seems to know that we want
> >>> to use the MFGPT timers, and I wonder if they did anything behind the scenes
> >>> to "help us out" even though we didn't ask for it.
> >>>
> >>> I don't know how easy it would be for you - but can you try reading
> >>> MSRs 0x51400020 - 0x51400023? If you need a command line app to do it,
> >>> you can use rdmsr from here:
> >>>
> >>> http://wiki.laptop.org/go/Flashing_LinuxBIOS_on_A-Test_Boards
> >> MSR register 0x51400020 => b7:ef:5f:f4:bf:d1:95:68
> >> MSR register 0x51400021 => b7:fd:1f:f4:bf:cf:5a:d8
> >> MSR register 0x51400022 => b7:f3:bf:f4:bf:f5:fb:a8
> >> MSR register 0x51400023 => b7:fb:9f:f4:bf:fd:d9:f8
> >
> > Hmmm - those look wrong. Is /dev/cpu/0/msr there? The applet on the
> > wiki has a bug that doesn't check for it.
> I'm sorry, I should have checked: I didn't execute rdmsr as root.
> The correct ones:
>
> MSR register 0x51400020 => 00:00:00:00:00:00:0f:00
> MSR register 0x51400021 => 00:00:00:00:04:00:00:00
> MSR register 0x51400022 => 00:00:00:00:00:00:00:00
> MSR register 0x51400023 => 00:00:00:00:00:0c:ba:90

Okay - those are sane. Those are the IRQ routing MSRs - each nibble is an
IRQ for something in the southbridge - since 7 doesn't appear, a rogue
interrupt isn't likely. Also, [0:31] in 0x51400022 are the MFGPT interrupts
specifically, and they are 0. The timer tick code would set the first nibble
to 7 (in a sane system).

So, everything _seems_ okay from the hardware side. The next step would be
to comment out the setup_irq() function and write a C app or something to
verify that all the MFGPT registers are set up like we expect them to be.
However, I think that maybe we can accomplish the same thing with the
forthcoming watchdog timer, since it will prove the MFGPT is behaving
well (though it doesn't use the interrupt wrapper, but one step at a time).

Jordan
--
Jordan Crouse
Systems Software Development Engineer
Advanced Micro Devices, Inc.

2008-01-19 01:15:31

by Jordan Crouse

[permalink] [raw]
Subject: [GEODE] Geode GX/LX watchdog timer (was 2.6.24-rc8 hangs at mfgpt-timer)

[GEODE] Add a watchdog driver based on the CS5535/CS5536 MFGPT timers

From: Jordan Crouse <[email protected]>

Add a watchdog timer based on the MFGPT timers in the CS5535/CS5536
companion chips to the AMD Geode GX and LX processors. Only caveat
is that the BIOS must provide at least a one free timer, and most
do not.

Signed-off-by: Jordan Crouse <[email protected]>
---

drivers/watchdog/Kconfig | 13 ++
drivers/watchdog/Makefile | 1
drivers/watchdog/geodewdt.c | 321 +++++++++++++++++++++++++++++++++++++++++++
3 files changed, 335 insertions(+), 0 deletions(-)

Index: git/drivers/watchdog/Kconfig
===================================================================
--- git.orig/drivers/watchdog/Kconfig 2008-01-18 15:06:44.000000000 -0700
+++ git/drivers/watchdog/Kconfig 2008-01-18 17:50:25.000000000 -0700
@@ -295,6 +295,20 @@

Most people will say N.

+config GEODE_WDT
+ tristate "AMD Geode CS5535/CS5536 Watchdog"
+ depends on MGEODE_LX
+ default n
+ help
+ This driver enables a watchdog capability built into the
+ CS5535/CS5536 companion chips for the AMD Geode GX and LX
+ processors. This watchdog watches your kernel to make sure
+ it doesn't freeze, and if it does, it reboots your computer after
+ a certain amount of time.
+
+ You can compile this driver directly into the kernel, or use
+ it as a module. The module will be called geodewdt.
+
config SC520_WDT
tristate "AMD Elan SC520 processor Watchdog"
depends on X86
Index: git/drivers/watchdog/Makefile
===================================================================
--- git.orig/drivers/watchdog/Makefile 2008-01-18 15:06:44.000000000 -0700
+++ git/drivers/watchdog/Makefile 2008-01-18 16:32:15.000000000 -0700
@@ -59,6 +59,7 @@
obj-$(CONFIG_ADVANTECH_WDT) += advantechwdt.o
obj-$(CONFIG_ALIM1535_WDT) += alim1535_wdt.o
obj-$(CONFIG_ALIM7101_WDT) += alim7101_wdt.o
+obj-$(CONFIG_GEODE_WDT) += geodewdt.o
obj-$(CONFIG_SC520_WDT) += sc520_wdt.o
obj-$(CONFIG_EUROTECH_WDT) += eurotechwdt.o
obj-$(CONFIG_IB700_WDT) += ib700wdt.o
Index: git/drivers/watchdog/geodewdt.c
===================================================================
--- /dev/null 1970-01-01 00:00:00.000000000 +0000
+++ git/drivers/watchdog/geodewdt.c 2008-01-18 17:47:39.000000000 -0700
@@ -0,0 +1,308 @@
+/* Watchdog timer for the Geode GX/LX with the CS5535/CS5536 companion chip
+ *
+ * Copyright (C) 2006-2007, Advanced Micro Devices, 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.
+ */
+
+
+#include <linux/module.h>
+#include <linux/moduleparam.h>
+#include <linux/types.h>
+#include <linux/miscdevice.h>
+#include <linux/watchdog.h>
+#include <linux/fs.h>
+#include <linux/platform_device.h>
+#include <linux/reboot.h>
+
+#include <asm/uaccess.h>
+#include <asm/geode.h>
+
+#define GEODEWDT_HZ 500
+#define GEODEWDT_SCALE 6
+#define GEODEWDT_MAX_SECONDS 131
+
+#define WDT_FLAGS_OPEN 1
+#define WDT_FLAGS_ORPHAN 2
+
+#define DRV_NAME "geodewdt"
+#define WATCHDOG_NAME "Geode GX/LX WDT"
+#define WATCHDOG_TIMEOUT 60
+
+static int timeout = WATCHDOG_TIMEOUT;
+module_param(timeout, int, 0);
+MODULE_PARM_DESC(timeout, "Watchdog timeout in seconds. 1<= timeout <=131, default=" __MODULE_STRING(WATCHDOG_TIMEOUT) ".");
+
+static int nowayout = WATCHDOG_NOWAYOUT;
+module_param(nowayout, int, 0);
+MODULE_PARM_DESC(nowayout, "Watchdog cannot be stopped once started (default=" __MODULE_STRING(WATCHDOG_NOWAYOUT) ")");
+
+static struct platform_device *geodewdt_platform_device;
+static unsigned long wdt_flags;
+static int wdt_timer;
+static int safe_close;
+
+static void geodewdt_ping(void)
+{
+ /* Stop the counter */
+ geode_mfgpt_write(wdt_timer, MFGPT_REG_SETUP, 0);
+
+ /* Reset the counter */
+ geode_mfgpt_write(wdt_timer, MFGPT_REG_COUNTER, 0);
+
+ /* Enable the counter */
+ geode_mfgpt_write(wdt_timer, MFGPT_REG_SETUP, MFGPT_SETUP_CNTEN);
+}
+
+static void geodewdt_disable(void)
+{
+ geode_mfgpt_write(wdt_timer, MFGPT_REG_SETUP, 0);
+ geode_mfgpt_write(wdt_timer, MFGPT_REG_COUNTER, 0);
+}
+
+static int geodewdt_set_heartbeat(int val)
+{
+ if (val < 1 || val > GEODEWDT_MAX_SECONDS)
+ return -EINVAL;
+
+ geode_mfgpt_write(wdt_timer, MFGPT_REG_SETUP, 0);
+ geode_mfgpt_write(wdt_timer, MFGPT_REG_CMP2, val * GEODEWDT_HZ);
+ geode_mfgpt_write(wdt_timer, MFGPT_REG_COUNTER, 0);
+ geode_mfgpt_write(wdt_timer, MFGPT_REG_SETUP, MFGPT_SETUP_CNTEN);
+
+ timeout = val;
+ return 0;
+}
+
+static int
+geodewdt_open(struct inode *inode, struct file *file)
+{
+ if (test_and_set_bit(WDT_FLAGS_OPEN, &wdt_flags))
+ return -EBUSY;
+
+ if (!test_and_clear_bit(WDT_FLAGS_ORPHAN, &wdt_flags))
+ __module_get(THIS_MODULE);
+
+ geodewdt_ping();
+ return nonseekable_open(inode, file);
+}
+
+static int
+geodewdt_release(struct inode *inode, struct file *file)
+{
+ if (safe_close) {
+ geodewdt_disable();
+ module_put(THIS_MODULE);
+ }
+ else {
+ printk(KERN_CRIT "Unexpected close - watchdog is not stopping.\n");
+ geodewdt_ping();
+
+ set_bit(WDT_FLAGS_ORPHAN, &wdt_flags);
+ }
+
+ clear_bit(WDT_FLAGS_OPEN, &wdt_flags);
+ safe_close = 0;
+ return 0;
+}
+
+static ssize_t
+geodewdt_write(struct file *file, const char __user *data, size_t len,
+ loff_t *ppos)
+{
+ if(len) {
+ if (!nowayout) {
+ size_t i;
+ safe_close = 0;
+
+ for (i = 0; i != len; i++) {
+ char c;
+
+ if (get_user(c, data + i))
+ return -EFAULT;
+
+ if (c == 'V')
+ safe_close = 1;
+ }
+ }
+
+ geodewdt_ping();
+ }
+ return len;
+}
+
+static int
+geodewdt_ioctl(struct inode *inode, struct file *file, unsigned int cmd,
+ unsigned long arg)
+{
+ void __user *argp = (void __user *)arg;
+ int __user *p = argp;
+ int interval;
+
+ static struct watchdog_info ident = {
+ .options = WDIOF_SETTIMEOUT | WDIOF_KEEPALIVEPING
+ | WDIOF_MAGICCLOSE,
+ .firmware_version = 1,
+ .identity = WATCHDOG_NAME,
+ };
+
+ switch(cmd) {
+ case WDIOC_GETSUPPORT:
+ return copy_to_user(argp, &ident,
+ sizeof(ident)) ? -EFAULT : 0;
+ break;
+
+ case WDIOC_GETSTATUS:
+ case WDIOC_GETBOOTSTATUS:
+ return put_user(0, p);
+
+ case WDIOC_KEEPALIVE:
+ geodewdt_ping();
+ return 0;
+
+ case WDIOC_SETTIMEOUT:
+ if (get_user(interval, p))
+ return -EFAULT;
+
+ if (geodewdt_set_heartbeat(interval))
+ return -EINVAL;
+
+/* Fall through */
+
+ case WDIOC_GETTIMEOUT:
+ return put_user(timeout, p);
+
+ case WDIOC_SETOPTIONS:
+ {
+ int options, ret = -EINVAL;
+
+ if (get_user(options, p))
+ return -EFAULT;
+
+ if (options & WDIOS_DISABLECARD) {
+ geodewdt_disable();
+ ret = 0;
+ }
+
+ if (options & WDIOS_ENABLECARD) {
+ geodewdt_ping();
+ ret = 0;
+ }
+
+ return ret;
+ }
+ default:
+ return -ENOTTY;
+ }
+
+ return 0;
+}
+
+static const struct file_operations geodewdt_fops = {
+ .owner = THIS_MODULE,
+ .llseek = no_llseek,
+ .write = geodewdt_write,
+ .ioctl = geodewdt_ioctl,
+ .open = geodewdt_open,
+ .release = geodewdt_release,
+};
+
+static struct miscdevice geodewdt_miscdev = {
+ .minor = WATCHDOG_MINOR,
+ .name = "geode-watchdog",
+ .fops = &geodewdt_fops
+};
+
+static int __devinit
+geodewdt_probe(struct platform_device *dev)
+{
+ int ret, timer;
+
+ timer = geode_mfgpt_alloc_timer(MFGPT_TIMER_ANY,
+ MFGPT_DOMAIN_WORKING, THIS_MODULE);
+
+ if (timer == -1) {
+ printk(KERN_ERR "geodewdt: No timers were available\n");
+ return -ENODEV;
+ }
+
+ wdt_timer = timer;
+
+ /* Set up the timer */
+
+ geode_mfgpt_write(wdt_timer, MFGPT_REG_SETUP,
+ GEODEWDT_SCALE | (3 << 8));
+
+ /* Set up comparator 2 to reset when the event fires */
+ geode_mfgpt_toggle_event(wdt_timer, MFGPT_CMP2, MFGPT_EVENT_RESET, 1);
+
+ /* Set up the initial timeout */
+
+ geode_mfgpt_write(wdt_timer, MFGPT_REG_CMP2,
+ timeout * GEODEWDT_HZ);
+
+ ret = misc_register(&geodewdt_miscdev);
+
+ return ret;
+}
+
+static int __devexit
+geodewdt_remove(struct platform_device *dev)
+{
+ misc_deregister(&geodewdt_miscdev);
+}
+
+static void
+geodewdt_shutdown(struct platform_device *dev)
+{
+ geodewdt_disable();
+}
+
+static struct platform_driver geodewdt_driver = {
+ .probe = geodewdt_probe,
+ .remove = __devexit_p(geodewdt_remove),
+ .shutdown = geodewdt_shutdown,
+ .driver = {
+ .owner = THIS_MODULE,
+ .name = DRV_NAME,
+ },
+};
+
+static int __init
+geodewdt_init(void)
+{
+ int ret;
+
+ ret = platform_driver_register(&geodewdt_driver);
+ if (ret)
+ return ret;
+
+ geodewdt_platform_device = platform_device_register_simple(DRV_NAME, -1, NULL, 0);
+ if (IS_ERR(geodewdt_platform_device)) {
+ ret = PTR_ERR(geodewdt_platform_device);
+ goto err;
+ }
+
+ return 0;
+err:
+ platform_driver_unregister(&geodewdt_driver);
+ return ret;
+}
+
+static void __exit
+geodewdt_exit(void)
+{
+ platform_device_unregister(geodewdt_platform_device);
+ platform_driver_unregister(&geodewdt_driver);
+}
+
+module_init(geodewdt_init);
+module_exit(geodewdt_exit);
+
+MODULE_AUTHOR("Advanced Micro Devices, Inc");
+MODULE_DESCRIPTION("Geode GX/LX Watchdog Driver");
+MODULE_LICENSE("GPL");
+MODULE_ALIAS_MISCDEV(WATCHDOG_MINOR);
Index: git/arch/x86/kernel/mfgpt_32.c
===================================================================
--- git.orig/arch/x86/kernel/mfgpt_32.c 2008-01-18 16:57:50.000000000 -0700
+++ git/arch/x86/kernel/mfgpt_32.c 2008-01-18 17:48:22.000000000 -0700
@@ -142,6 +142,8 @@
return 0;
}

+EXPORT_SYMBOL_GPL(geode_mfgpt_toggle_event);
+
int geode_mfgpt_set_irq(int timer, int cmp, int irq, int enable)
{
u32 val, dummy;
@@ -204,6 +206,7 @@
return -1;
}

+EXPORT_SYMBOL_GPL(geode_mfgpt_alloc_timer);

#ifdef CONFIG_GEODE_MFGPT_TIMER


Attachments:
(No filename) (1.63 kB)
geode-watchdog.patch (9.70 kB)
Download all attachments

2008-01-19 07:01:34

by Willy Tarreau

[permalink] [raw]
Subject: Re: [GEODE] Geode GX/LX watchdog timer (was 2.6.24-rc8 hangs at mfgpt-timer)

On Fri, Jan 18, 2008 at 06:06:24PM -0700, Jordan Crouse wrote:
> I don't know how much of a hassle it would be for Andres to get a 2.6.24
> kernel running on the OLPC to make sure that this isn't a regression
> in the timer tick code (I suspect it isn't a regression, but you never
> know). I also think that it would probably be in our best interest to
> default CONFIG_GEODE_MFGPT_TIMER to 'n' until we get this figured
> out. Since most BIOSen don't have timers available, that shouldn't affect
> too many people.

Well, I've successfully used earlier version of this code with 2.6.22
on a PCEngines ALIX motherboard equipped with LX800/CS5536. It boots
on a TinyBIOS.

I will try 2.6.24 + this patch on these boards when I have some time.

Willy

2008-01-20 13:22:25

by Arnd Hannemann

[permalink] [raw]
Subject: Re: [GEODE] Geode GX/LX watchdog timer (was 2.6.24-rc8 hangs at mfgpt-timer)

Hi,

Jordan Crouse wrote:
> On 17/01/08 23:52 +0100, Arnd Hannemann wrote:
>>>> Watchdog for the new API would be great :-)
>>> Coming soon.
>
> As promised, a watchdog driver for the Geode GX/LX processors is attached.
> I basically just ported the previous patch forward to 2.6.24.

Great work!

>
> I also have good news or bad news depending on your perspective. I wanted
> to test this against 2.6.24, and OLPC is stuck at an older kernel version,
> so I had to test this with coreboot (LinuxBIOS) on another Geode
> platform. Like all BIOSen execpt for the OLPC firmware, coreboot uses
> VSA (SMM handler) which consumes all the timers.
>
> So I used the magical MSR and surprise! - the timer tick hung.
> I compiled out the timer tick, and tested the watchdog timer instead,
> and it worked fine on timer 0. So I don't think the MFGPTs themselves
> have anything to do with this problem, but I do think it might be
> related to VSA and possibly interrupts too. I'm going to invoke the
> strong BIOS fu of our LinuxBIOS / BIOS expert Marc Jones, and see what
> he comes up with.
>
> I don't know how much of a hassle it would be for Andres to get a 2.6.24
> kernel running on the OLPC to make sure that this isn't a regression
> in the timer tick code (I suspect it isn't a regression, but you never
> know). I also think that it would probably be in our best interest to
> default CONFIG_GEODE_MFGPT_TIMER to 'n' until we get this figured
> out. Since most BIOSen don't have timers available, that shouldn't affect
> too many people.
>
> So, anyway, enjoy the watchdog timer - I hope it meets everybody's
> expectations for the 2.6.25 kernel.

Thanks a lot for this, it works great! (with CONFIG_GEODE_MFGPT_TIMER
not set).
However some minor issues:
Could the name of the /dev entry perhaps be changed from
"geode-watchdog" to "watchdog" instead?
I think all other watchdogs use "watchdog", and using two different
watchdogs in the same machine won't work anyway, because of the same
minor number, right?

As a second point my gcc (4.1.2) issues a warning:

drivers/watchdog/geodewdt.c: In function ‘geodewdt_remove’:
drivers/watchdog/geodewdt.c:256: warning: control reaches end of
non-void function

which I think is a valid one.

>
> Jordan
>
Best regards,
Arnd

2008-01-20 16:36:54

by Jordan Crouse

[permalink] [raw]
Subject: Re: Geode GX/LX watchdog timer (was 2.6.24-rc8 hangs at mfgpt-timer)

On 20/01/08 14:22 +0100, Arnd Hannemann wrote:
> Hi,
>
> Jordan Crouse wrote:
> > On 17/01/08 23:52 +0100, Arnd Hannemann wrote:
> >>>> Watchdog for the new API would be great :-)
> >>> Coming soon.
> >
> > As promised, a watchdog driver for the Geode GX/LX processors is attached.
> > I basically just ported the previous patch forward to 2.6.24.
>
> Great work!
>
> >
> > I also have good news or bad news depending on your perspective. I wanted
> > to test this against 2.6.24, and OLPC is stuck at an older kernel version,
> > so I had to test this with coreboot (LinuxBIOS) on another Geode
> > platform. Like all BIOSen execpt for the OLPC firmware, coreboot uses
> > VSA (SMM handler) which consumes all the timers.
> >
> > So I used the magical MSR and surprise! - the timer tick hung.
> > I compiled out the timer tick, and tested the watchdog timer instead,
> > and it worked fine on timer 0. So I don't think the MFGPTs themselves
> > have anything to do with this problem, but I do think it might be
> > related to VSA and possibly interrupts too. I'm going to invoke the
> > strong BIOS fu of our LinuxBIOS / BIOS expert Marc Jones, and see what
> > he comes up with.
> >
> > I don't know how much of a hassle it would be for Andres to get a 2.6.24
> > kernel running on the OLPC to make sure that this isn't a regression
> > in the timer tick code (I suspect it isn't a regression, but you never
> > know). I also think that it would probably be in our best interest to
> > default CONFIG_GEODE_MFGPT_TIMER to 'n' until we get this figured
> > out. Since most BIOSen don't have timers available, that shouldn't affect
> > too many people.
> >
> > So, anyway, enjoy the watchdog timer - I hope it meets everybody's
> > expectations for the 2.6.25 kernel.
>
> Thanks a lot for this, it works great! (with CONFIG_GEODE_MFGPT_TIMER
> not set).
> However some minor issues:
> Could the name of the /dev entry perhaps be changed from
> "geode-watchdog" to "watchdog" instead?
> I think all other watchdogs use "watchdog", and using two different
> watchdogs in the same machine won't work anyway, because of the same
> minor number, right?

Very much yes - complete oversight on my part.

> As a second point my gcc (4.1.2) issues a warning:
>
> drivers/watchdog/geodewdt.c: In function ‘geodewdt_remove’:
> drivers/watchdog/geodewdt.c:256: warning: control reaches end of
> non-void function
>
> which I think is a valid one.

Yes again. I'll refactor. Thanks for your comments.

Jordan
--
Jordan Crouse
Systems Software Development Engineer
Advanced Micro Devices, Inc.

2008-01-20 20:16:17

by Lennart Sorensen

[permalink] [raw]
Subject: Re: [GEODE] Geode GX/LX watchdog timer (was 2.6.24-rc8 hangs at mfgpt-timer)

On Fri, Jan 18, 2008 at 06:06:24PM -0700, Jordan Crouse wrote:
> As promised, a watchdog driver for the Geode GX/LX processors is attached.
> I basically just ported the previous patch forward to 2.6.24.
>
> I also have good news or bad news depending on your perspective. I wanted
> to test this against 2.6.24, and OLPC is stuck at an older kernel version,
> so I had to test this with coreboot (LinuxBIOS) on another Geode
> platform. Like all BIOSen execpt for the OLPC firmware, coreboot uses
> VSA (SMM handler) which consumes all the timers.

Hmm, the Geode LX platform I work with uses VSA/SMM and I have had no
problems using timer 2 for a watchdog. Some of the timers are certainly
already setup by something in the BIOS, but quite a few are not in use.
The board I am using is the compulab iGLX module. I did have to mangle
together a watchdog driver myself some time ago since there wasn't one
for the Geode LX at the time.

Of course I haven't gone past 2.6.18 kernel for now (I am tracking
Debian stable for the most part), so I have no idea if something in a
newer kernel breaks things.

> So I used the magical MSR and surprise! - the timer tick hung.
> I compiled out the timer tick, and tested the watchdog timer instead,
> and it worked fine on timer 0. So I don't think the MFGPTs themselves
> have anything to do with this problem, but I do think it might be
> related to VSA and possibly interrupts too. I'm going to invoke the
> strong BIOS fu of our LinuxBIOS / BIOS expert Marc Jones, and see what
> he comes up with.
>
> I don't know how much of a hassle it would be for Andres to get a 2.6.24
> kernel running on the OLPC to make sure that this isn't a regression
> in the timer tick code (I suspect it isn't a regression, but you never
> know). I also think that it would probably be in our best interest to
> default CONFIG_GEODE_MFGPT_TIMER to 'n' until we get this figured
> out. Since most BIOSen don't have timers available, that shouldn't affect
> too many people.
>
> So, anyway, enjoy the watchdog timer - I hope it meets everybody's
> expectations for the 2.6.25 kernel.

--
Len Sorensen

2008-01-21 17:51:11

by Jordan Crouse

[permalink] [raw]
Subject: Re: Geode GX/LX watchdog timer (RESEND)

[GEODE] Add a watchdog driver based on the CS5535/CS5536 MFGPT timers

From: Jordan Crouse <[email protected]>

Add a watchdog timer based on the MFGPT timers in the CS5535/CS5536
companion chips to the AMD Geode GX and LX processors. Only caveat
is that the BIOS must provide at least a one free timer, and most
do not.

Signed-off-by: Jordan Crouse <[email protected]>
---

drivers/watchdog/Kconfig | 13 ++
drivers/watchdog/Makefile | 1
drivers/watchdog/geodewdt.c | 309 +++++++++++++++++++++++++++++++++++++++++++
3 files changed, 323 insertions(+), 0 deletions(-)

diff --git a/drivers/watchdog/Kconfig b/drivers/watchdog/Kconfig
index 52dff40..15b4c29 100644
--- a/drivers/watchdog/Kconfig
+++ b/drivers/watchdog/Kconfig
@@ -295,6 +295,19 @@ config ALIM7101_WDT

Most people will say N.

+config GEODE_WDT
+ tristate "AMD Geode CS5535/CS5536 Watchdog"
+ depends on MGEODE_LX
+ help
+ This driver enables a watchdog capability built into the
+ CS5535/CS5536 companion chips for the AMD Geode GX and LX
+ processors. This watchdog watches your kernel to make sure
+ it doesn't freeze, and if it does, it reboots your computer after
+ a certain amount of time.
+
+ You can compile this driver directly into the kernel, or use
+ it as a module. The module will be called geodewdt.
+
config SC520_WDT
tristate "AMD Elan SC520 processor Watchdog"
depends on X86
diff --git a/drivers/watchdog/Makefile b/drivers/watchdog/Makefile
index 87483cc..830ce70 100644
--- a/drivers/watchdog/Makefile
+++ b/drivers/watchdog/Makefile
@@ -59,6 +59,7 @@ obj-$(CONFIG_ACQUIRE_WDT) += acquirewdt.o
obj-$(CONFIG_ADVANTECH_WDT) += advantechwdt.o
obj-$(CONFIG_ALIM1535_WDT) += alim1535_wdt.o
obj-$(CONFIG_ALIM7101_WDT) += alim7101_wdt.o
+obj-$(CONFIG_GEODE_WDT) += geodewdt.o
obj-$(CONFIG_SC520_WDT) += sc520_wdt.o
obj-$(CONFIG_EUROTECH_WDT) += eurotechwdt.o
obj-$(CONFIG_IB700_WDT) += ib700wdt.o
diff --git a/drivers/watchdog/geodewdt.c b/drivers/watchdog/geodewdt.c
new file mode 100644
index 0000000..f85b196
--- /dev/null
+++ b/drivers/watchdog/geodewdt.c
@@ -0,0 +1,309 @@
+/* Watchdog timer for the Geode GX/LX with the CS5535/CS5536 companion chip
+ *
+ * Copyright (C) 2006-2007, Advanced Micro Devices, 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.
+ */
+
+
+#include <linux/module.h>
+#include <linux/moduleparam.h>
+#include <linux/types.h>
+#include <linux/miscdevice.h>
+#include <linux/watchdog.h>
+#include <linux/fs.h>
+#include <linux/platform_device.h>
+#include <linux/reboot.h>
+
+#include <asm/uaccess.h>
+#include <asm/geode.h>
+
+#define GEODEWDT_HZ 500
+#define GEODEWDT_SCALE 6
+#define GEODEWDT_MAX_SECONDS 131
+
+#define WDT_FLAGS_OPEN 1
+#define WDT_FLAGS_ORPHAN 2
+
+#define DRV_NAME "geodewdt"
+#define WATCHDOG_NAME "Geode GX/LX WDT"
+#define WATCHDOG_TIMEOUT 60
+
+static int timeout = WATCHDOG_TIMEOUT;
+module_param(timeout, int, 0);
+MODULE_PARM_DESC(timeout, "Watchdog timeout in seconds. 1<= timeout <=131, default=" __MODULE_STRING(WATCHDOG_TIMEOUT) ".");
+
+static int nowayout = WATCHDOG_NOWAYOUT;
+module_param(nowayout, int, 0);
+MODULE_PARM_DESC(nowayout, "Watchdog cannot be stopped once started (default=" __MODULE_STRING(WATCHDOG_NOWAYOUT) ")");
+
+static struct platform_device *geodewdt_platform_device;
+static unsigned long wdt_flags;
+static int wdt_timer;
+static int safe_close;
+
+static void geodewdt_ping(void)
+{
+ /* Stop the counter */
+ geode_mfgpt_write(wdt_timer, MFGPT_REG_SETUP, 0);
+
+ /* Reset the counter */
+ geode_mfgpt_write(wdt_timer, MFGPT_REG_COUNTER, 0);
+
+ /* Enable the counter */
+ geode_mfgpt_write(wdt_timer, MFGPT_REG_SETUP, MFGPT_SETUP_CNTEN);
+}
+
+static void geodewdt_disable(void)
+{
+ geode_mfgpt_write(wdt_timer, MFGPT_REG_SETUP, 0);
+ geode_mfgpt_write(wdt_timer, MFGPT_REG_COUNTER, 0);
+}
+
+static int geodewdt_set_heartbeat(int val)
+{
+ if (val < 1 || val > GEODEWDT_MAX_SECONDS)
+ return -EINVAL;
+
+ geode_mfgpt_write(wdt_timer, MFGPT_REG_SETUP, 0);
+ geode_mfgpt_write(wdt_timer, MFGPT_REG_CMP2, val * GEODEWDT_HZ);
+ geode_mfgpt_write(wdt_timer, MFGPT_REG_COUNTER, 0);
+ geode_mfgpt_write(wdt_timer, MFGPT_REG_SETUP, MFGPT_SETUP_CNTEN);
+
+ timeout = val;
+ return 0;
+}
+
+static int
+geodewdt_open(struct inode *inode, struct file *file)
+{
+ if (test_and_set_bit(WDT_FLAGS_OPEN, &wdt_flags))
+ return -EBUSY;
+
+ if (!test_and_clear_bit(WDT_FLAGS_ORPHAN, &wdt_flags))
+ __module_get(THIS_MODULE);
+
+ geodewdt_ping();
+ return nonseekable_open(inode, file);
+}
+
+static int
+geodewdt_release(struct inode *inode, struct file *file)
+{
+ if (safe_close) {
+ geodewdt_disable();
+ module_put(THIS_MODULE);
+ }
+ else {
+ printk(KERN_CRIT "Unexpected close - watchdog is not stopping.\n");
+ geodewdt_ping();
+
+ set_bit(WDT_FLAGS_ORPHAN, &wdt_flags);
+ }
+
+ clear_bit(WDT_FLAGS_OPEN, &wdt_flags);
+ safe_close = 0;
+ return 0;
+}
+
+static ssize_t
+geodewdt_write(struct file *file, const char __user *data, size_t len,
+ loff_t *ppos)
+{
+ if(len) {
+ if (!nowayout) {
+ size_t i;
+ safe_close = 0;
+
+ for (i = 0; i != len; i++) {
+ char c;
+
+ if (get_user(c, data + i))
+ return -EFAULT;
+
+ if (c == 'V')
+ safe_close = 1;
+ }
+ }
+
+ geodewdt_ping();
+ }
+ return len;
+}
+
+static int
+geodewdt_ioctl(struct inode *inode, struct file *file, unsigned int cmd,
+ unsigned long arg)
+{
+ void __user *argp = (void __user *)arg;
+ int __user *p = argp;
+ int interval;
+
+ static struct watchdog_info ident = {
+ .options = WDIOF_SETTIMEOUT | WDIOF_KEEPALIVEPING
+ | WDIOF_MAGICCLOSE,
+ .firmware_version = 1,
+ .identity = WATCHDOG_NAME,
+ };
+
+ switch(cmd) {
+ case WDIOC_GETSUPPORT:
+ return copy_to_user(argp, &ident,
+ sizeof(ident)) ? -EFAULT : 0;
+ break;
+
+ case WDIOC_GETSTATUS:
+ case WDIOC_GETBOOTSTATUS:
+ return put_user(0, p);
+
+ case WDIOC_KEEPALIVE:
+ geodewdt_ping();
+ return 0;
+
+ case WDIOC_SETTIMEOUT:
+ if (get_user(interval, p))
+ return -EFAULT;
+
+ if (geodewdt_set_heartbeat(interval))
+ return -EINVAL;
+
+/* Fall through */
+
+ case WDIOC_GETTIMEOUT:
+ return put_user(timeout, p);
+
+ case WDIOC_SETOPTIONS:
+ {
+ int options, ret = -EINVAL;
+
+ if (get_user(options, p))
+ return -EFAULT;
+
+ if (options & WDIOS_DISABLECARD) {
+ geodewdt_disable();
+ ret = 0;
+ }
+
+ if (options & WDIOS_ENABLECARD) {
+ geodewdt_ping();
+ ret = 0;
+ }
+
+ return ret;
+ }
+ default:
+ return -ENOTTY;
+ }
+
+ return 0;
+}
+
+static const struct file_operations geodewdt_fops = {
+ .owner = THIS_MODULE,
+ .llseek = no_llseek,
+ .write = geodewdt_write,
+ .ioctl = geodewdt_ioctl,
+ .open = geodewdt_open,
+ .release = geodewdt_release,
+};
+
+static struct miscdevice geodewdt_miscdev = {
+ .minor = WATCHDOG_MINOR,
+ .name = "watchdog",
+ .fops = &geodewdt_fops
+};
+
+static int __devinit
+geodewdt_probe(struct platform_device *dev)
+{
+ int ret, timer;
+
+ timer = geode_mfgpt_alloc_timer(MFGPT_TIMER_ANY,
+ MFGPT_DOMAIN_WORKING, THIS_MODULE);
+
+ if (timer == -1) {
+ printk(KERN_ERR "geodewdt: No timers were available\n");
+ return -ENODEV;
+ }
+
+ wdt_timer = timer;
+
+ /* Set up the timer */
+
+ geode_mfgpt_write(wdt_timer, MFGPT_REG_SETUP,
+ GEODEWDT_SCALE | (3 << 8));
+
+ /* Set up comparator 2 to reset when the event fires */
+ geode_mfgpt_toggle_event(wdt_timer, MFGPT_CMP2, MFGPT_EVENT_RESET, 1);
+
+ /* Set up the initial timeout */
+
+ geode_mfgpt_write(wdt_timer, MFGPT_REG_CMP2,
+ timeout * GEODEWDT_HZ);
+
+ ret = misc_register(&geodewdt_miscdev);
+
+ return ret;
+}
+
+static int __devexit
+geodewdt_remove(struct platform_device *dev)
+{
+ misc_deregister(&geodewdt_miscdev);
+ return 0;
+}
+
+static void
+geodewdt_shutdown(struct platform_device *dev)
+{
+ geodewdt_disable();
+}
+
+static struct platform_driver geodewdt_driver = {
+ .probe = geodewdt_probe,
+ .remove = __devexit_p(geodewdt_remove),
+ .shutdown = geodewdt_shutdown,
+ .driver = {
+ .owner = THIS_MODULE,
+ .name = DRV_NAME,
+ },
+};
+
+static int __init
+geodewdt_init(void)
+{
+ int ret;
+
+ ret = platform_driver_register(&geodewdt_driver);
+ if (ret)
+ return ret;
+
+ geodewdt_platform_device = platform_device_register_simple(DRV_NAME, -1, NULL, 0);
+ if (IS_ERR(geodewdt_platform_device)) {
+ ret = PTR_ERR(geodewdt_platform_device);
+ goto err;
+ }
+
+ return 0;
+err:
+ platform_driver_unregister(&geodewdt_driver);
+ return ret;
+}
+
+static void __exit
+geodewdt_exit(void)
+{
+ platform_device_unregister(geodewdt_platform_device);
+ platform_driver_unregister(&geodewdt_driver);
+}
+
+module_init(geodewdt_init);
+module_exit(geodewdt_exit);
+
+MODULE_AUTHOR("Advanced Micro Devices, Inc");
+MODULE_DESCRIPTION("Geode GX/LX Watchdog Driver");
+MODULE_LICENSE("GPL");
+MODULE_ALIAS_MISCDEV(WATCHDOG_MINOR);


Attachments:
(No filename) (2.42 kB)
geode-watchdog.patch (8.98 kB)
Download all attachments

2008-01-21 18:36:51

by Arnd Hannemann

[permalink] [raw]
Subject: Re: Geode GX/LX watchdog timer (RESEND)

Jordan Crouse schrieb:
> On 20/01/08 14:22 +0100, Arnd Hannemann wrote:
>> Hi,
>>
>> Jordan Crouse wrote:
>>> On 17/01/08 23:52 +0100, Arnd Hannemann wrote:
>>>>>> Watchdog for the new API would be great :-)
>>>>> Coming soon.
>>> As promised, a watchdog driver for the Geode GX/LX processors is attached.
>>> I basically just ported the previous patch forward to 2.6.24.
>> Great work!
>>
>>> I also have good news or bad news depending on your perspective. I wanted
>>> to test this against 2.6.24, and OLPC is stuck at an older kernel version,
>>> so I had to test this with coreboot (LinuxBIOS) on another Geode
>>> platform. Like all BIOSen execpt for the OLPC firmware, coreboot uses
>>> VSA (SMM handler) which consumes all the timers.
>>>
>>> So I used the magical MSR and surprise! - the timer tick hung.
>>> I compiled out the timer tick, and tested the watchdog timer instead,
>>> and it worked fine on timer 0. So I don't think the MFGPTs themselves
>>> have anything to do with this problem, but I do think it might be
>>> related to VSA and possibly interrupts too. I'm going to invoke the
>>> strong BIOS fu of our LinuxBIOS / BIOS expert Marc Jones, and see what
>>> he comes up with.
>>>
>>> I don't know how much of a hassle it would be for Andres to get a 2.6.24
>>> kernel running on the OLPC to make sure that this isn't a regression
>>> in the timer tick code (I suspect it isn't a regression, but you never
>>> know). I also think that it would probably be in our best interest to
>>> default CONFIG_GEODE_MFGPT_TIMER to 'n' until we get this figured
>>> out. Since most BIOSen don't have timers available, that shouldn't affect
>>> too many people.
>>>
>>> So, anyway, enjoy the watchdog timer - I hope it meets everybody's
>>> expectations for the 2.6.25 kernel.
>> Thanks a lot for this, it works great! (with CONFIG_GEODE_MFGPT_TIMER
>> not set).
>> However some minor issues:
>> Could the name of the /dev entry perhaps be changed from
>> "geode-watchdog" to "watchdog" instead?
>> I think all other watchdogs use "watchdog", and using two different
>> watchdogs in the same machine won't work anyway, because of the same
>> minor number, right?
>>
>> As a second point my gcc (4.1.2) issues a warning:
>>
>> drivers/watchdog/geodewdt.c: In function ‘geodewdt_remove’:
>> drivers/watchdog/geodewdt.c:256: warning: control reaches end of
>> non-void function
>>
>> which I think is a valid one.
>
> Resending with Arnd's concern's addressed. Thanks.

I can confirm that it is still working fine :-)

>
> Jordan
>
Greetings,
Arnd

2008-01-21 23:28:07

by Jordan Crouse

[permalink] [raw]
Subject: Re: 2.6.24-rc8 hangs at mfgpt-timer

diff --git a/arch/x86/kernel/mfgpt_32.c b/arch/x86/kernel/mfgpt_32.c
index 0ab680f..5b4fa24 100644
--- a/arch/x86/kernel/mfgpt_32.c
+++ b/arch/x86/kernel/mfgpt_32.c
@@ -74,18 +74,31 @@ int __init geode_mfgpt_detect(void)
{
int count = 0, i;
u16 val;
+ u32 hi, lo;

if (disable) {
printk(KERN_INFO "geode-mfgpt: Skipping MFGPT setup\n");
return 0;
}

+ rdmsr(0x51400028, lo, hi);
+ printk(KERN_INFO "geode-mfgpt: IRQ MSR=%x:%x\n", hi, lo);
+
+ rdmsr(0x51400029, lo, hi);
+ printk(KERN_INFO "geode-mfgpt: NMI MSR=%x:%x\n", hi, lo);
+
+ rdmsr(0x51400022, lo, hi);
+ printk(KERN_INFO "geode-mfgpt: Unrestricted sources=%x\n", lo);
+
for (i = 0; i < MFGPT_MAX_TIMERS; i++) {
val = geode_mfgpt_read(i, MFGPT_REG_SETUP);
if (!(val & MFGPT_SETUP_SETUP)) {
mfgpt_timers[i].flags = F_AVAIL;
count++;
}
+ else {
+ printk(KERN_INFO "geode-mfgpt: [%d] is already setup=%x\n", i, val);
+ }
}

/* set up clock event device, if desired */


Attachments:
(No filename) (994.00 B)
mfgpt-debug-spew.patch (973.00 B)
Download all attachments

2008-01-22 00:00:44

by Willy Tarreau

[permalink] [raw]
Subject: Re: 2.6.24-rc8 hangs at mfgpt-timer

Hi Jordan,

On Mon, Jan 21, 2008 at 04:27:09PM -0700, Jordan Crouse wrote:
> Okay - I've been exploring a little bit more. I talked to the TinyBIOS
> developer, and he verified that TinyBIOS shouldn't use any MFGPT timers.
> He also told me that the mysterious "MFGPT workaround" was in fact the
> magic MFGPT erasing MSR that was in the old kernel driver.
>
> So with the "MFGPT workaround" turned off, TinyBIOS should be acting like
> the OLPC firmware with regards to timers, yet it is not. So that is
> curious. I think I might have identified a race condition in the code,
> but I'm not 100% sure thats the same problem that the ALIX platform is
> seeing.
>
> Anrd and others - will you please try the attached patch on your platform
> with the "MFGPT workaround" turned off and mfgpts enabled, and send out
> the dmesg?

Yes of course :

[ 44.013100] NET: Registered protocol family 16
[ 44.066308] geode-mfgpt: IRQ MSR=0:0
[ 44.110161] geode-mfgpt: NMI MSR=0:0
[ 44.154037] geode-mfgpt: Unrestricted sources=0

Then it hangs here.
In another mail I sent privately to Andres, I noticed that it was the
following line which hangs at first iteration (i == 0) :

val = geode_mfgpt_read(i, MFGPT_REG_SETUP);

I have a tinybios 0.98 with no workaround option configurable. I also
have CONFIG_GEODE_MFGPT_TIMER=n.

Hoping this helps,
Willy

2008-01-22 09:02:38

by Arnd Hannemann

[permalink] [raw]
Subject: Re: 2.6.24-rc8 hangs at mfgpt-timer

Jordan Crouse wrote:
> Okay - I've been exploring a little bit more. I talked to the TinyBIOS
> developer, and he verified that TinyBIOS shouldn't use any MFGPT timers.
> He also told me that the mysterious "MFGPT workaround" was in fact the
> magic MFGPT erasing MSR that was in the old kernel driver.
>
> So with the "MFGPT workaround" turned off, TinyBIOS should be acting like
> the OLPC firmware with regards to timers, yet it is not. So that is
> curious. I think I might have identified a race condition in the code,
> but I'm not 100% sure thats the same problem that the ALIX platform is
> seeing.
>
> Anrd and others - will you please try the attached patch on your platform
> with the "MFGPT workaround" turned off and mfgpts enabled, and send out
> the dmesg?

Of course, tinyBios version v0.99, "MFGPT workaround" turned off,
CONFIG_GEODE_MFGPT_TIMER=n:

[ 67.369697] NET: Registered protocol family 16
[ 67.383059] geode-mfgpt: IRQ MSR=0:0
[ 67.394058] geode-mfgpt: NMI MSR=0:0
[ 67.405049] geode-mfgpt: Unrestricted sources=0
[ 67.418909] geode: 8 MFGPT timers available.
[ 67.433211] PCI: PCI BIOS revision 2.10 entry at 0xfcd03, last bus=0

same with CONFIG_GEODE_MFGPT_TIMER=y (sorry, without move printk patch):

[ 22.289349] NET: Registered protocol family 16
[ 22.302716] geode-mfgpt: IRQ MSR=0:0
[ 22.313716] geode-mfgpt: NMI MSR=0:0
[ 22.324704] geode-mfgpt: Unrestricted sources=0
[ 22.338566] geode-mfgpt: Registered timer 0
[ 22.351393] mfgpt-timer: registering the MFGT timer as a clock event.
^^^^ Hangs here

>
> This will give us some debug information that I can use to ensure that
> the interrupts are set up correctly. You can leave the timer tick disabled
> if you want.

>
> Thanks,
> Jordan
>

Arnd

2008-01-22 10:33:55

by Lars Heete

[permalink] [raw]
Subject: Re: 2.6.24-rc8 hangs at mfgpt-timer

Hello,

On Tuesday 22 January 2008 10:03:08 am Arnd Hannemann wrote:
> Jordan Crouse wrote:
> > Okay - I've been exploring a little bit more. I talked to the TinyBIOS
> > developer, and he verified that TinyBIOS shouldn't use any MFGPT timers.
> > He also told me that the mysterious "MFGPT workaround" was in fact the
> > magic MFGPT erasing MSR that was in the old kernel driver.
> >
> > So with the "MFGPT workaround" turned off, TinyBIOS should be acting like
> > the OLPC firmware with regards to timers, yet it is not. So that is
> > curious. I think I might have identified a race condition in the code,
> > but I'm not 100% sure thats the same problem that the ALIX platform is
> > seeing.
> >
> > Anrd and others - will you please try the attached patch on your platform
> > with the "MFGPT workaround" turned off and mfgpts enabled, and send out
> > the dmesg?
>
> Of course, tinyBios version v0.99, "MFGPT workaround" turned off,
> CONFIG_GEODE_MFGPT_TIMER=n:
>
> [ 67.369697] NET: Registered protocol family 16
> [ 67.383059] geode-mfgpt: IRQ MSR=0:0
> [ 67.394058] geode-mfgpt: NMI MSR=0:0
> [ 67.405049] geode-mfgpt: Unrestricted sources=0
> [ 67.418909] geode: 8 MFGPT timers available.
> [ 67.433211] PCI: PCI BIOS revision 2.10 entry at 0xfcd03, last bus=0
>
> same with CONFIG_GEODE_MFGPT_TIMER=y (sorry, without move printk patch):
>
> [ 22.289349] NET: Registered protocol family 16
> [ 22.302716] geode-mfgpt: IRQ MSR=0:0
> [ 22.313716] geode-mfgpt: NMI MSR=0:0
> [ 22.324704] geode-mfgpt: Unrestricted sources=0
> [ 22.338566] geode-mfgpt: Registered timer 0
> [ 22.351393] mfgpt-timer: registering the MFGT timer as a clock event.
> ^^^^ Hangs here
I had the same problem with MFGPT Timers and alix (BIOS v0.99). I found that
if you use a different interrupt than the default 7 for MFGPT (just append
mfgpt_irq=8 to the kernel commandline), the timer seems to work.

CPU0
0: 33 XT-PIC-XT timer
2: 0 XT-PIC-XT cascade
4: 1662 XT-PIC-XT serial
8: 766 XT-PIC-XT mfgpt-timer
14: 473 XT-PIC-XT libata
NMI: 0
ERR: 0


> > This will give us some debug information that I can use to ensure that
> > the interrupts are set up correctly. You can leave the timer tick
> > disabled if you want.
> >
> >
> > Thanks,
> > Jordan
>
> Arnd

Lars

2008-01-22 11:18:18

by Arnd Hannemann

[permalink] [raw]
Subject: Re: 2.6.24-rc8 hangs at mfgpt-timer

Hi Lars,

Lars Heete schrieb:
> Hello,
>
> On Tuesday 22 January 2008 10:03:08 am Arnd Hannemann wrote:
>> Jordan Crouse wrote:
>>> Okay - I've been exploring a little bit more. I talked to the TinyBIOS
>>> developer, and he verified that TinyBIOS shouldn't use any MFGPT timers.
>>> He also told me that the mysterious "MFGPT workaround" was in fact the
>>> magic MFGPT erasing MSR that was in the old kernel driver.
>>>
>>> So with the "MFGPT workaround" turned off, TinyBIOS should be acting like
>>> the OLPC firmware with regards to timers, yet it is not. So that is
>>> curious. I think I might have identified a race condition in the code,
>>> but I'm not 100% sure thats the same problem that the ALIX platform is
>>> seeing.
>>>
>>> Anrd and others - will you please try the attached patch on your platform
>>> with the "MFGPT workaround" turned off and mfgpts enabled, and send out
>>> the dmesg?
>> Of course, tinyBios version v0.99, "MFGPT workaround" turned off,
>> CONFIG_GEODE_MFGPT_TIMER=n:
>>
>> [ 67.369697] NET: Registered protocol family 16
>> [ 67.383059] geode-mfgpt: IRQ MSR=0:0
>> [ 67.394058] geode-mfgpt: NMI MSR=0:0
>> [ 67.405049] geode-mfgpt: Unrestricted sources=0
>> [ 67.418909] geode: 8 MFGPT timers available.
>> [ 67.433211] PCI: PCI BIOS revision 2.10 entry at 0xfcd03, last bus=0
>>
>> same with CONFIG_GEODE_MFGPT_TIMER=y (sorry, without move printk patch):
>>
>> [ 22.289349] NET: Registered protocol family 16
>> [ 22.302716] geode-mfgpt: IRQ MSR=0:0
>> [ 22.313716] geode-mfgpt: NMI MSR=0:0
>> [ 22.324704] geode-mfgpt: Unrestricted sources=0
>> [ 22.338566] geode-mfgpt: Registered timer 0
>> [ 22.351393] mfgpt-timer: registering the MFGT timer as a clock event.
>> ^^^^ Hangs here
> I had the same problem with MFGPT Timers and alix (BIOS v0.99). I found that
> if you use a different interrupt than the default 7 for MFGPT (just append
> mfgpt_irq=8 to the kernel commandline), the timer seems to work.

Indeed.
Strange, it works at least with mfgpt_irq=8 (rtc) and mfgpt_irq=5 (audio):

[ 21.805129] geode-mfgpt: IRQ MSR=0:0
[ 21.816129] geode-mfgpt: NMI MSR=0:0
[ 21.827116] geode-mfgpt: Unrestricted sources=0
[ 21.840979] geode-mfgpt: Registered timer 0
[ 21.853806] mfgpt-timer: registering the MFGT timer as a clock event.
[ 21.873576] geode: 8 MFGPT timers available.
[ 21.887962] PCI: PCI BIOS revision 2.10 entry at 0xfcd03, last bus=0


/proc/interrupts with mfgpt_irq=5:
CPU0
0: 48 XT-PIC-XT timer
2: 0 XT-PIC-XT cascade
4: 674 XT-PIC-XT serial
5: 13706 XT-PIC-XT mfgpt-timer
8: 3 XT-PIC-XT rtc
10: 57137 XT-PIC-XT eth0
15: 1 XT-PIC-XT ehci_hcd:usb1, ohci_hcd:usb2
NMI: 0 Non-maskable interrupts
TRM: 0 Thermal event interrupts
SPU: 0 Spurious interrupts
ERR: 0

/proc/interrupts with mfgpt_irq=8:
CPU0
0: 48 XT-PIC-XT timer
2: 0 XT-PIC-XT cascade
4: 2511 XT-PIC-XT serial
8: 29061 XT-PIC-XT mfgpt-timer
10: 60701 XT-PIC-XT eth0
15: 1 XT-PIC-XT ehci_hcd:usb1, ohci_hcd:usb2
NMI: 0 Non-maskable interrupts
TRM: 0 Thermal event interrupts
SPU: 0 Spurious interrupts
ERR: 0

I noted that "rtc" disappeared, do I have any drawback of this?
I assume that the mfgpt-timer cannot be shared?

>
> CPU0
> 0: 33 XT-PIC-XT timer
> 2: 0 XT-PIC-XT cascade
> 4: 1662 XT-PIC-XT serial
> 8: 766 XT-PIC-XT mfgpt-timer
> 14: 473 XT-PIC-XT libata
> NMI: 0
> ERR: 0
>
>
>>> This will give us some debug information that I can use to ensure that
>>> the interrupts are set up correctly. You can leave the timer tick
>>> disabled if you want.
>>>
>>>
>>> Thanks,
>>> Jordan
>> Arnd
>
> Lars
>

Thanks for the hint!
Arnd

2008-01-22 18:16:55

by Jordan Crouse

[permalink] [raw]
Subject: Re: 2.6.24-rc8 hangs at mfgpt-timer

On 22/01/08 12:18 +0100, Arnd Hannemann wrote:
> Hi Lars,
>
> Lars Heete schrieb:
> > Hello,
> >
> > On Tuesday 22 January 2008 10:03:08 am Arnd Hannemann wrote:
> >> Jordan Crouse wrote:
> >>> Okay - I've been exploring a little bit more. I talked to the TinyBIOS
> >>> developer, and he verified that TinyBIOS shouldn't use any MFGPT timers.
> >>> He also told me that the mysterious "MFGPT workaround" was in fact the
> >>> magic MFGPT erasing MSR that was in the old kernel driver.
> >>>
> >>> So with the "MFGPT workaround" turned off, TinyBIOS should be acting like
> >>> the OLPC firmware with regards to timers, yet it is not. So that is
> >>> curious. I think I might have identified a race condition in the code,
> >>> but I'm not 100% sure thats the same problem that the ALIX platform is
> >>> seeing.
> >>>
> >>> Anrd and others - will you please try the attached patch on your platform
> >>> with the "MFGPT workaround" turned off and mfgpts enabled, and send out
> >>> the dmesg?
> >> Of course, tinyBios version v0.99, "MFGPT workaround" turned off,
> >> CONFIG_GEODE_MFGPT_TIMER=n:
> >>
> >> [ 67.369697] NET: Registered protocol family 16
> >> [ 67.383059] geode-mfgpt: IRQ MSR=0:0
> >> [ 67.394058] geode-mfgpt: NMI MSR=0:0
> >> [ 67.405049] geode-mfgpt: Unrestricted sources=0
> >> [ 67.418909] geode: 8 MFGPT timers available.
> >> [ 67.433211] PCI: PCI BIOS revision 2.10 entry at 0xfcd03, last bus=0
> >>
> >> same with CONFIG_GEODE_MFGPT_TIMER=y (sorry, without move printk patch):
> >>
> >> [ 22.289349] NET: Registered protocol family 16
> >> [ 22.302716] geode-mfgpt: IRQ MSR=0:0
> >> [ 22.313716] geode-mfgpt: NMI MSR=0:0
> >> [ 22.324704] geode-mfgpt: Unrestricted sources=0
> >> [ 22.338566] geode-mfgpt: Registered timer 0
> >> [ 22.351393] mfgpt-timer: registering the MFGT timer as a clock event.
> >> ^^^^ Hangs here
> > I had the same problem with MFGPT Timers and alix (BIOS v0.99). I found that
> > if you use a different interrupt than the default 7 for MFGPT (just append
> > mfgpt_irq=8 to the kernel commandline), the timer seems to work.
>
> Indeed.
> Strange, it works at least with mfgpt_irq=8 (rtc) and mfgpt_irq=5 (audio):

That is very unfortunate. We must continue to investigate.

> [ 21.805129] geode-mfgpt: IRQ MSR=0:0
> [ 21.816129] geode-mfgpt: NMI MSR=0:0
> [ 21.827116] geode-mfgpt: Unrestricted sources=0
> [ 21.840979] geode-mfgpt: Registered timer 0
> [ 21.853806] mfgpt-timer: registering the MFGT timer as a clock event.
> [ 21.873576] geode: 8 MFGPT timers available.
> [ 21.887962] PCI: PCI BIOS revision 2.10 entry at 0xfcd03, last bus=0
>
<snip>

> I noted that "rtc" disappeared, do I have any drawback of this?
> I assume that the mfgpt-timer cannot be shared?

No. We figured that was the best way to go. I don't know if there
are any technical reasons why it can't be shared, other then latency
problems.

But I would still prefer to figure out why 7 doesn't work - because there
is nothing in the hardware or kernel code that should prevent that.

Arnd - if you don't mind doing a little bit more debug work. You've already
given us the MSRs for 0x51400020 - 0x51400023. Can you now give us
0x51400024-0x51400027, as well as 5140004E? Our current working theory
is that IRQ7 (traditionally used by the LPT port) is still conflicting
somewhere.

Jordan
--
Jordan Crouse
Systems Software Development Engineer
Advanced Micro Devices, Inc.

2008-01-22 19:27:27

by Jordan Crouse

[permalink] [raw]
Subject: Re: 2.6.24-rc8 hangs at mfgpt-timer

[GEODE] fix a race condition in the MFGPT timer tick

From: Jordan Crouse <[email protected]>

When we set the MFGPT timer tick, there is a chance that we'll
immediately assert an event. If for some reason the IRQ routing
for this clock has been setup for some other purpose, then we
could end up firing an interrupt into the SMM handler or worse.

This rearranges the timer tick init function to initalize the handler
before we set up the MFGPT clock to make sure that even if we get
an event, it will go to the handler.

Furthermore, in the handler we need to make sure that we clear the
event, even if the timer isn't running.

Signed-off-by: Jordan Crouse <[email protected]>
---

arch/x86/kernel/mfgpt_32.c | 9 +++++----
1 files changed, 5 insertions(+), 4 deletions(-)

Index: git/arch/x86/kernel/mfgpt_32.c
===================================================================
--- git.orig/arch/x86/kernel/mfgpt_32.c 2008-01-21 17:09:54.000000000 -0700
+++ git/arch/x86/kernel/mfgpt_32.c 2008-01-22 12:21:21.000000000 -0700
@@ -278,12 +278,12 @@

static irqreturn_t mfgpt_tick(int irq, void *dev_id)
{
+ /* Turn off the clock (and clear the event) */
+ mfgpt_disable_timer(mfgpt_event_clock);
+
if (mfgpt_tick_mode == CLOCK_EVT_MODE_SHUTDOWN)
return IRQ_HANDLED;

- /* Turn off the clock */
- mfgpt_disable_timer(mfgpt_event_clock);
-
/* Clear the counter */
geode_mfgpt_write(mfgpt_event_clock, MFGPT_REG_COUNTER, 0);

@@ -319,10 +319,6 @@
}

mfgpt_event_clock = timer;
- /* Set the clock scale and enable the event mode for CMP2 */
- val = MFGPT_SCALE | (3 << 8);
-
- geode_mfgpt_write(mfgpt_event_clock, MFGPT_REG_SETUP, val);

/* Set up the IRQ on the MFGPT side */
if (geode_mfgpt_setup_irq(mfgpt_event_clock, MFGPT_CMP2, irq)) {
@@ -339,6 +335,11 @@
goto err;
}

+ /* Set the clock scale and enable the event mode for CMP2 */
+ val = MFGPT_SCALE | (3 << 8);
+
+ geode_mfgpt_write(mfgpt_event_clock, MFGPT_REG_SETUP, val);
+
/* Set up the clock event */
mfgpt_clockevent.mult = div_sc(MFGPT_HZ, NSEC_PER_SEC, 32);
mfgpt_clockevent.min_delta_ns = clockevent_delta2ns(0xF,


Attachments:
(No filename) (1.06 kB)
fix-mfgpt-race.patch (2.08 kB)
Download all attachments

2008-01-22 20:44:50

by Willy Tarreau

[permalink] [raw]
Subject: Re: 2.6.24-rc8 hangs at mfgpt-timer

Hi guys,

On Tue, Jan 22, 2008 at 12:32:26AM +0100, Willy Tarreau wrote:
> [ 44.013100] NET: Registered protocol family 16
> [ 44.066308] geode-mfgpt: IRQ MSR=0:0
> [ 44.110161] geode-mfgpt: NMI MSR=0:0
> [ 44.154037] geode-mfgpt: Unrestricted sources=0
>
> Then it hangs here.
> In another mail I sent privately to Andres, I noticed that it was the
> following line which hangs at first iteration (i == 0) :
>
> val = geode_mfgpt_read(i, MFGPT_REG_SETUP);
>
> I have a tinybios 0.98 with no workaround option configurable. I also
> have CONFIG_GEODE_MFGPT_TIMER=n.

Good news! I read the mfgpt patch for 2.6.22 and saw what the workaround
consisted in (writing 0xff at MSR 0x5140002B). So I tried adding the
following on top of 2.6.24-rc8 :

static int __init mfgpt_fix(char *s)
{
u32 val, dummy;

/* The following udocumented bit resets the MFGPT timers */
val = 0xFF;
wrmsr(0x5140002B, val, dummy);

return 1;
}
__setup("mfgptfix", mfgpt_fix);

and booted with the newly added option (mfgptfix). It worked like a charm :

[ 29.173796] NET: Registered protocol family 16
[ 29.226986] geode: lbars[0].base = 0x9d00
[ 29.275003] geode: lbars[1].base = 0x9c00
[ 29.323042] geode: lbars[2].base = 0x6100
[ 29.371082] geode: lbars[3].base = 0x6200
[ 29.419121] geode-mfgpt: IRQ MSR=0:0
[ 29.463000] geode-mfgpt: NMI MSR=0:0
[ 29.506881] geode-mfgpt: Unrestricted sources=0
[ 29.562202] geode_mfgpt: reading 0x6200 + 0x6 + (0x0 * 8) = 0x6206
[ 29.636237] geode_mfgpt: reading 0x6200 + 0x6 + (0x1 * 8) = 0x620e
[ 29.710270] geode_mfgpt: reading 0x6200 + 0x6 + (0x2 * 8) = 0x6216
[ 29.784305] geode_mfgpt: reading 0x6200 + 0x6 + (0x3 * 8) = 0x621e
[ 29.858338] geode_mfgpt: reading 0x6200 + 0x6 + (0x4 * 8) = 0x6226
[ 29.932376] geode_mfgpt: reading 0x6200 + 0x6 + (0x5 * 8) = 0x622e
[ 30.006409] geode_mfgpt: reading 0x6200 + 0x6 + (0x6 * 8) = 0x6236
[ 30.080444] geode_mfgpt: reading 0x6200 + 0x6 + (0x7 * 8) = 0x623e
[ 30.154475] geode: 8 MFGPT timers available.

So it seems like applying the workaround on top of TinyBIOS 0.98 undoes
this BIOS's workaround. I'm now wondering how we could detect whether
the workaround was applied or not :-/

Next, I retried with MFGPT_TIMER=y + latest fix you posted moving the
initialization race, and here's what I get now :

root@ALOHA-500:~# cat /proc/interrupts
CPU0
0: 77 XT-PIC-XT timer
2: 0 XT-PIC-XT cascade
4: 348 XT-PIC-XT serial
7: 12273 XT-PIC-XT mfgpt-timer
8: 0 XT-PIC-XT rtc
10: 80 XT-PIC-XT eth0
11: 0 XT-PIC-XT eth1
12: 1 XT-PIC-XT eth2
14: 13614 XT-PIC-XT ide0
NMI: 0 Non-maskable interrupts
TRM: 0 Thermal event interrupts
SPU: 0 Spurious interrupts
ERR: 0

Interestingly, during the boot, I got thousands of the following line :
geode_mfgpt: reading 0x6200 + 0x6 + (0x0 * 8) = 0x6206

It's a debug line I added in geode_mfgpt_read() which writes the timer and
reg being read. It slowed the boot down due to being written to a serial
console, but fortunately stopped when syslogd had changed the console log
level. Just checking...

# grep mfgpt /proc/interrupts;sleep 10;grep mfgpt /proc/interrupts
7: 82320 XT-PIC-XT mfgpt-timer
7: 84882 XT-PIC-XT mfgpt-timer

It delivers 256 IRQs/s. That makes me think about this comment in mfgpt_32.c :

* We are using the 32Khz input clock - its the only one that has the
* ranges we find desirable. The following table lists the suitable
* divisors and the associated hz, minimum interval
* and the maximum interval:
*
* Divisor Hz Min Delta (S) Max Delta (S)
* 1 32000 .0005 2.048
* 2 16000 .001 4.096
* 4 8000 .002 8.192
...

When you say a 32kHz clock, you mean 32000 Hz. Are you really sure ? Most
32 kHz clocks everywhere are really 32768 Hz (the watch quartz). BTW, I'm
seeing a 32.768 kHz xtal close to the CS5536, and the numbers above seem
to support this suggestion too.

So right now that I've found what caused old kernel to unexpectedly work,
I'm planning a BIOS upgrade. I'm still just wondering what we can do to
detect that the workaround should be needed. I suspect nothing, of course,
but just in case... Maybe we can detect the effects of the workaround ?

Best regards,
Willy

2008-01-22 20:53:52

by Arnd Hannemann

[permalink] [raw]
Subject: Re: 2.6.24-rc8 hangs at mfgpt-timer

Hi,

Jordan Crouse schrieb:
>> Indeed.
>> Strange, it works at least with mfgpt_irq=8 (rtc) and mfgpt_irq=5 (audio):
>
> I have most excellent news. I was able to get tinyBIOS booting on my
> development platform. I looked at the problem with the debugger and
> I think I might have found something. It looks like the interrupt is
> firing immediately before the clock is enabled. In the handler, we
> were returning immediately if the clock wasn't enabled (and not clearing
> the event), so we were caught in a classic interrupt storm.
>
> The attached patch rearranges the code so that the handler is installed
> before we setup the interrupt (so we have somebody to listen to the
> immediate interrupt), and it makes sure that we clear the event in the IRQ
> handler regardless of the state of the timer tick.

This patch indeed solves the problem. The board boots fine. Great work!

0: 48 XT-PIC-XT timer
2: 0 XT-PIC-XT cascade
4: 493 XT-PIC-XT serial
7: 25875 XT-PIC-XT mfgpt-timer
8: 3 XT-PIC-XT rtc
10: 56963 XT-PIC-XT eth0
15: 1 XT-PIC-XT ehci_hcd:usb1, ohci_hcd:usb2
NMI: 0 Non-maskable interrupts
TRM: 0 Thermal event interrupts
SPU: 0 Spurious interrupts
ERR: 0

>
> I'm not 100% sure why this happens on IRQ7 but not on 5 or 8, but it might
> have something to do with the interrupts already being enabled on the other
> vectors. Anyway, please try this test patch and let me know what happens.

Congratulations for this long but successful remote debugging ;-)

Greetings,
Arnd

2008-01-22 21:09:45

by Jordan Crouse

[permalink] [raw]
Subject: Re: 2.6.24-rc8 hangs at mfgpt-timer

On 22/01/08 21:15 +0100, Willy Tarreau wrote:
> Good news! I read the mfgpt patch for 2.6.22 and saw what the workaround
> consisted in (writing 0xff at MSR 0x5140002B). So I tried adding the
> following on top of 2.6.24-rc8 :
>
> static int __init mfgpt_fix(char *s)
> {
> u32 val, dummy;
>
> /* The following udocumented bit resets the MFGPT timers */
> val = 0xFF;
> wrmsr(0x5140002B, val, dummy);
>
> return 1;
> }
> __setup("mfgptfix", mfgpt_fix);
>
> and booted with the newly added option (mfgptfix). It worked like a charm :
>
<snip>

> So it seems like applying the workaround on top of TinyBIOS 0.98 undoes
> this BIOS's workaround. I'm now wondering how we could detect whether
> the workaround was applied or not :-/

Actually, the TinyBIOS "workaround" is the same thing.

Like I may have said before, there is a reason why this MSR is undocumented.
It works, but the behavior is unvalidated, and obviously erratic. When we
first developed this code, we were using the Geode GX on the OLPC with VSA,
so using the MSR was nessesary if we wanted to get our hands on any
timers at all. Mitch Bradley (author of OpenFirmware) determined through
testing that the MSR was erratic, especially when you ran it when all the
timers were already clear. I suspect thats the problem that we see here -
writing the MSR in TinyBIOS unstablizied the registers, and writing the
MSR again kicked it back. Of course, the unfortunate corollary is that
when the workaround isn't in v0.99, if you run the MSR in the kernel, then
you will end up destabilizing everything.

Furthermore, using the MSR is okay with TinyBIOS, but not okay with the
other Geode BIOSen (Insyde, General Software, and for the moment LinuxBIOS)
because VSA (the SMM handler) _does_ use some of the timers. So needless
to say, I'm concerned.

> Interestingly, during the boot, I got thousands of the following line :
> geode_mfgpt: reading 0x6200 + 0x6 + (0x0 * 8) = 0x6206
>
> It's a debug line I added in geode_mfgpt_read() which writes the timer and
> reg being read. It slowed the boot down due to being written to a serial
> console, but fortunately stopped when syslogd had changed the console log
> level. Just checking...

We control the timer and the status bits for the timer in the setup
register, which is what you are showing above. Thats fine.

> # grep mfgpt /proc/interrupts;sleep 10;grep mfgpt /proc/interrupts
> 7: 82320 XT-PIC-XT mfgpt-timer
> 7: 84882 XT-PIC-XT mfgpt-timer
>
> It delivers 256 IRQs/s. That makes me think about this comment in mfgpt_32.c :

Hmm - are you running with nohz? I ran the same thing on the OLPC
and I'm getting 81 IRQ/s which is okay, considering that sugar was running
in the background.

> * We are using the 32Khz input clock - its the only one that has the
> * ranges we find desirable. The following table lists the suitable
> * divisors and the associated hz, minimum interval
> * and the maximum interval:
> *
> * Divisor Hz Min Delta (S) Max Delta (S)
> * 1 32000 .0005 2.048
> * 2 16000 .001 4.096
> * 4 8000 .002 8.192
> ...
>
> When you say a 32kHz clock, you mean 32000 Hz. Are you really sure ? Most
> 32 kHz clocks everywhere are really 32768 Hz (the watch quartz). BTW, I'm
> seeing a 32.768 kHz xtal close to the CS5536, and the numbers above seem
> to support this suggestion too.

Hmm - yeah, my math is off there - it is a 32768 Hz clock. That
shouldn't affect things too negatively - if it does we can adjust the
divisor we use - currently we use 16.

> So right now that I've found what caused old kernel to unexpectedly work,
> I'm planning a BIOS upgrade. I'm still just wondering what we can do to
> detect that the workaround should be needed. I suspect nothing, of course,
> but just in case... Maybe we can detect the effects of the workaround ?

I'm not sure if we can - all we can tell is if the registers are zero or
not. Like I said, running the MSR is probably dangerous in 9 out of 10
situations, the one good use being the one you determined. I would
support adding the mfgptfix bit though - just as long as it isn't
automagic.

Thank you very much for your help!
Jordan

--
Jordan Crouse
Systems Software Development Engineer
Advanced Micro Devices, Inc.

2008-01-22 21:10:41

by Ingo Molnar

[permalink] [raw]
Subject: Re: 2.6.24-rc8 hangs at mfgpt-timer


* Arnd Hannemann <[email protected]> wrote:

> > The attached patch rearranges the code so that the handler is
> > installed before we setup the interrupt (so we have somebody to
> > listen to the immediate interrupt), and it makes sure that we clear
> > the event in the IRQ handler regardless of the state of the timer
> > tick.
>
> This patch indeed solves the problem. The board boots fine. Great
> work!

since this driver is new in 2.6.24, perhaps we should apply this fix to
v2.6.24?

Ingo

2008-01-22 21:45:10

by Willy Tarreau

[permalink] [raw]
Subject: Re: 2.6.24-rc8 hangs at mfgpt-timer

On Tue, Jan 22, 2008 at 02:08:58PM -0700, Jordan Crouse wrote:
> On 22/01/08 21:15 +0100, Willy Tarreau wrote:
> > So it seems like applying the workaround on top of TinyBIOS 0.98 undoes
> > this BIOS's workaround. I'm now wondering how we could detect whether
> > the workaround was applied or not :-/
>
> Actually, the TinyBIOS "workaround" is the same thing.
>
> Like I may have said before, there is a reason why this MSR is undocumented.
> It works, but the behavior is unvalidated, and obviously erratic. When we
> first developed this code, we were using the Geode GX on the OLPC with VSA,
> so using the MSR was nessesary if we wanted to get our hands on any
> timers at all. Mitch Bradley (author of OpenFirmware) determined through
> testing that the MSR was erratic, especially when you ran it when all the
> timers were already clear. I suspect thats the problem that we see here -
> writing the MSR in TinyBIOS unstablizied the registers, and writing the
> MSR again kicked it back. Of course, the unfortunate corollary is that
> when the workaround isn't in v0.99, if you run the MSR in the kernel, then
> you will end up destabilizing everything.

Indeed, that looks exactly like what's happening.

> Furthermore, using the MSR is okay with TinyBIOS, but not okay with the
> other Geode BIOSen (Insyde, General Software, and for the moment LinuxBIOS)
> because VSA (the SMM handler) _does_ use some of the timers. So needless
> to say, I'm concerned.

I certainly can understand.

> > Interestingly, during the boot, I got thousands of the following line :
> > geode_mfgpt: reading 0x6200 + 0x6 + (0x0 * 8) = 0x6206
> > It's a debug line I added in geode_mfgpt_read() which writes the timer and
> > reg being read. It slowed the boot down due to being written to a serial
> > console, but fortunately stopped when syslogd had changed the console log
> > level. Just checking...
>
> We control the timer and the status bits for the timer in the setup
> register, which is what you are showing above. Thats fine.

OK.

> > # grep mfgpt /proc/interrupts;sleep 10;grep mfgpt /proc/interrupts
> > 7: 82320 XT-PIC-XT mfgpt-timer
> > 7: 84882 XT-PIC-XT mfgpt-timer
> >
> > It delivers 256 IRQs/s. That makes me think about this comment in mfgpt_32.c :
>
> Hmm - are you running with nohz?

No but I have CONFIG_HZ=250. That makes sense then :

#define MFGPT_HZ (32000 / MFGPT_DIVISOR)
#define MFGPT_PERIODIC (MFGPT_HZ / HZ)

=> MFGPT_PERIODIC = (32000 / 16) / 250 = 8
Given that it's 32.768 kHz in fact, we get 32768/16/8 = 256 Hz

> > * We are using the 32Khz input clock - its the only one that has the
> > * ranges we find desirable. The following table lists the suitable
> > * divisors and the associated hz, minimum interval
> > * and the maximum interval:
> > *
> > * Divisor Hz Min Delta (S) Max Delta (S)
> > * 1 32000 .0005 2.048
> > * 2 16000 .001 4.096
> > * 4 8000 .002 8.192
> > ...
> >
> > When you say a 32kHz clock, you mean 32000 Hz. Are you really sure ? Most
> > 32 kHz clocks everywhere are really 32768 Hz (the watch quartz). BTW, I'm
> > seeing a 32.768 kHz xtal close to the CS5536, and the numbers above seem
> > to support this suggestion too.
>
> Hmm - yeah, my math is off there - it is a 32768 Hz clock. That
> shouldn't affect things too negatively - if it does we can adjust the
> divisor we use - currently we use 16.

Why not just ajust the constant in MFGPT_HZ since it's the only place (aside
the comments) where this is referenced ?

If you want I can send you a patch and adjust the comments at the same time.

> > So right now that I've found what caused old kernel to unexpectedly work,
> > I'm planning a BIOS upgrade. I'm still just wondering what we can do to
> > detect that the workaround should be needed. I suspect nothing, of course,
> > but just in case... Maybe we can detect the effects of the workaround ?
>
> I'm not sure if we can - all we can tell is if the registers are zero or
> not. Like I said, running the MSR is probably dangerous in 9 out of 10
> situations, the one good use being the one you determined. I would
> support adding the mfgptfix bit though - just as long as it isn't
> automagic.

OK I perfectly understand. While I see the current behaviour as a regression
compared to 2.6.22-mainline (since 2.6.24-rc8 does not boot off from this
board without nomfgpt), the first problem is in the BIOS and it requires an
upgrade. Maybe we should extend the scope of CONFIG_GEODE_MFGPT_TIMER to
allow it to completely disable the detection logic when it's off ? I certainly
can work a clean patch for "mfgptfix", but for users who will get caught with
this board not booting at all anymore, adding an option in their boot loaders
may be as problematic as upgrading the BIOS. I'm also thinking about the ones
preparing new software updates from a recent boards and deploying them miles
away without knowing they are running a 0.98 BIOS which will prevent their
new kernel from booting.

> Thank you very much for your help!

You're welcome, thanks to you too :-)
Willy

2008-01-22 21:50:44

by Willy Tarreau

[permalink] [raw]
Subject: Re: 2.6.24-rc8 hangs at mfgpt-timer

On Tue, Jan 22, 2008 at 10:10:14PM +0100, Ingo Molnar wrote:
>
> * Arnd Hannemann <[email protected]> wrote:
>
> > > The attached patch rearranges the code so that the handler is
> > > installed before we setup the interrupt (so we have somebody to
> > > listen to the immediate interrupt), and it makes sure that we clear
> > > the event in the IRQ handler regardless of the state of the timer
> > > tick.
> >
> > This patch indeed solves the problem. The board boots fine. Great
> > work!
>
> since this driver is new in 2.6.24, perhaps we should apply this fix to
> v2.6.24?

Yes, I do think so. You can add me too to the "Tested-by" lines if you want.

Willy

2008-01-22 21:53:57

by Thomas Gleixner

[permalink] [raw]
Subject: [git pull] was: Re: 2.6.24-rc8 hangs at mfgpt-timer

On Tue, 22 Jan 2008, Ingo Molnar wrote:
> * Arnd Hannemann <[email protected]> wrote:
>
> > > The attached patch rearranges the code so that the handler is
> > > installed before we setup the interrupt (so we have somebody to
> > > listen to the immediate interrupt), and it makes sure that we clear
> > > the event in the IRQ handler regardless of the state of the timer
> > > tick.
> >
> > This patch indeed solves the problem. The board boots fine. Great
> > work!
>
> since this driver is new in 2.6.24, perhaps we should apply this fix to
> v2.6.24?

Yes. It is definitely a safe change and makes otherwise broken systems
work. There is no impact to anything else than the GEODEs.

Linus,

if you agree, please pull the fix from:

ssh://master.kernel.org/pub/scm/linux/kernel/git/x86/linux-2.6-x86.git

Thanks,

tglx

2008-01-23 16:37:56

by Jordan Crouse

[permalink] [raw]
Subject: Re: 2.6.24-rc8 hangs at mfgpt-timer

On 22/01/08 22:15 +0100, Willy Tarreau wrote:
> On Tue, Jan 22, 2008 at 02:08:58PM -0700, Jordan Crouse wrote:
> > On 22/01/08 21:15 +0100, Willy Tarreau wrote:
> > > So it seems like applying the workaround on top of TinyBIOS 0.98 undoes
> > > this BIOS's workaround. I'm now wondering how we could detect whether
> > > the workaround was applied or not :-/
> >
> > Actually, the TinyBIOS "workaround" is the same thing.
> >
> > Like I may have said before, there is a reason why this MSR is undocumented.
> > It works, but the behavior is unvalidated, and obviously erratic. When we
> > first developed this code, we were using the Geode GX on the OLPC with VSA,
> > so using the MSR was nessesary if we wanted to get our hands on any
> > timers at all. Mitch Bradley (author of OpenFirmware) determined through
> > testing that the MSR was erratic, especially when you ran it when all the
> > timers were already clear. I suspect thats the problem that we see here -
> > writing the MSR in TinyBIOS unstablizied the registers, and writing the
> > MSR again kicked it back. Of course, the unfortunate corollary is that
> > when the workaround isn't in v0.99, if you run the MSR in the kernel, then
> > you will end up destabilizing everything.
>
> Indeed, that looks exactly like what's happening.
>
> > Furthermore, using the MSR is okay with TinyBIOS, but not okay with the
> > other Geode BIOSen (Insyde, General Software, and for the moment LinuxBIOS)
> > because VSA (the SMM handler) _does_ use some of the timers. So needless
> > to say, I'm concerned.
>
> I certainly can understand.
>
> > > Interestingly, during the boot, I got thousands of the following line :
> > > geode_mfgpt: reading 0x6200 + 0x6 + (0x0 * 8) = 0x6206
> > > It's a debug line I added in geode_mfgpt_read() which writes the timer and
> > > reg being read. It slowed the boot down due to being written to a serial
> > > console, but fortunately stopped when syslogd had changed the console log
> > > level. Just checking...
> >
> > We control the timer and the status bits for the timer in the setup
> > register, which is what you are showing above. Thats fine.
>
> OK.
>
> > > # grep mfgpt /proc/interrupts;sleep 10;grep mfgpt /proc/interrupts
> > > 7: 82320 XT-PIC-XT mfgpt-timer
> > > 7: 84882 XT-PIC-XT mfgpt-timer
> > >
> > > It delivers 256 IRQs/s. That makes me think about this comment in mfgpt_32.c :
> >
> > Hmm - are you running with nohz?
>
> No but I have CONFIG_HZ=250. That makes sense then :
>
> #define MFGPT_HZ (32000 / MFGPT_DIVISOR)
> #define MFGPT_PERIODIC (MFGPT_HZ / HZ)
>
> => MFGPT_PERIODIC = (32000 / 16) / 250 = 8
> Given that it's 32.768 kHz in fact, we get 32768/16/8 = 256 Hz
>
> > > * We are using the 32Khz input clock - its the only one that has the
> > > * ranges we find desirable. The following table lists the suitable
> > > * divisors and the associated hz, minimum interval
> > > * and the maximum interval:
> > > *
> > > * Divisor Hz Min Delta (S) Max Delta (S)
> > > * 1 32000 .0005 2.048
> > > * 2 16000 .001 4.096
> > > * 4 8000 .002 8.192
> > > ...
> > >
> > > When you say a 32kHz clock, you mean 32000 Hz. Are you really sure ? Most
> > > 32 kHz clocks everywhere are really 32768 Hz (the watch quartz). BTW, I'm
> > > seeing a 32.768 kHz xtal close to the CS5536, and the numbers above seem
> > > to support this suggestion too.
> >
> > Hmm - yeah, my math is off there - it is a 32768 Hz clock. That
> > shouldn't affect things too negatively - if it does we can adjust the
> > divisor we use - currently we use 16.
>
> Why not just ajust the constant in MFGPT_HZ since it's the only place (aside
> the comments) where this is referenced ?
>
> If you want I can send you a patch and adjust the comments at the same time.

That would be great.

> > > So right now that I've found what caused old kernel to unexpectedly work,
> > > I'm planning a BIOS upgrade. I'm still just wondering what we can do to
> > > detect that the workaround should be needed. I suspect nothing, of course,
> > > but just in case... Maybe we can detect the effects of the workaround ?
> >
> > I'm not sure if we can - all we can tell is if the registers are zero or
> > not. Like I said, running the MSR is probably dangerous in 9 out of 10
> > situations, the one good use being the one you determined. I would
> > support adding the mfgptfix bit though - just as long as it isn't
> > automagic.
>
> OK I perfectly understand. While I see the current behaviour as a regression
> compared to 2.6.22-mainline (since 2.6.24-rc8 does not boot off from this
> board without nomfgpt), the first problem is in the BIOS and it requires an
> upgrade. Maybe we should extend the scope of CONFIG_GEODE_MFGPT_TIMER to
> allow it to completely disable the detection logic when it's off ? I certainly
> can work a clean patch for "mfgptfix", but for users who will get caught with
> this board not booting at all anymore, adding an option in their boot loaders
> may be as problematic as upgrading the BIOS. I'm also thinking about the ones
> preparing new software updates from a recent boards and deploying them miles
> away without knowing they are running a 0.98 BIOS which will prevent their
> new kernel from booting.

I think not allowing MFGPT timers for broken BIOSen is the right way to go.
We can do just-in-time detection the first time one of the drivers (timer
tick or watchdog) asks for a timer, instead of the current way of probing
automatically.

That way, you can go merrily on your way if you don't try to use any of
the MFGPTs. TinyBIOS users can compile out CONFIG_GEODE_MFGPT_TIMER and
boot.

I'll write up a patch.

Thanks,
Jordan

--
Jordan Crouse
Systems Software Development Engineer
Advanced Micro Devices, Inc.

2008-01-23 16:41:16

by Willy Tarreau

[permalink] [raw]
Subject: Re: 2.6.24-rc8 hangs at mfgpt-timer

On Wed, Jan 23, 2008 at 09:36:46AM -0700, Jordan Crouse wrote:
> > Why not just ajust the constant in MFGPT_HZ since it's the only place (aside
> > the comments) where this is referenced ?
> >
> > If you want I can send you a patch and adjust the comments at the same time.
>
> That would be great.

OK will do ASAP.

> I think not allowing MFGPT timers for broken BIOSen is the right way to go.
> We can do just-in-time detection the first time one of the drivers (timer
> tick or watchdog) asks for a timer, instead of the current way of probing
> automatically.
>
> That way, you can go merrily on your way if you don't try to use any of
> the MFGPTs. TinyBIOS users can compile out CONFIG_GEODE_MFGPT_TIMER and
> boot.

I like this method a lot. At least, people with broken bioses would have
trouble only if they modprobe geodewdt or do such things. They will easily
find the relation between their action and the problem. Right now, we only
know that it hangs after "NET: ...".

> I'll write up a patch.

Fine.

Thanks,
Willy

2008-01-23 21:48:47

by Willy Tarreau

[permalink] [raw]
Subject: [PATCH 0/2] Was: 2.6.24-rc8 hangs at mfgpt-timer

On Tue, Jan 22, 2008 at 10:10:14PM +0100, Ingo Molnar wrote:
>
> * Arnd Hannemann <[email protected]> wrote:
>
> > > The attached patch rearranges the code so that the handler is
> > > installed before we setup the interrupt (so we have somebody to
> > > listen to the immediate interrupt), and it makes sure that we clear
> > > the event in the IRQ handler regardless of the state of the timer
> > > tick.
> >
> > This patch indeed solves the problem. The board boots fine. Great
> > work!
>
> since this driver is new in 2.6.24, perhaps we should apply this fix to
> v2.6.24?

Ingo, Jordan,

I have written the two minor patches we were talking about in previous
mail. The first one fixes the input clock from 32000 to 32768 Hz, and
the second one adds an "mfgptfix" boot parameter to enable the workaround
in order to fix a regression on motherboards with a broken BIOS on which
2.6.24-rc8 does not boot anymore whether mfgpt timers are enabled or not.

Jordan, if you think you'll push your changes for 2.6.24, feel free to
merge this patch with your work.

Both patches will be sent as a reply to this mail.

Regards,
Willy

2008-01-23 21:49:55

by Willy Tarreau

[permalink] [raw]
Subject: [PATCH 1/2] x86: GEODE fix MFGPT input clock value


The GEODE MFGPT code assumed that 32kHz was 32000 Hz while the boards
run on a 32.768 kHz digital watch crystal. In practise, it will not
change the timer's frequency as the skew was only 2.4%, but it
should provide more accurate intervals.

Signed-off-by: Willy Tarreau <[email protected]>
---
arch/x86/kernel/mfgpt_32.c | 24 ++++++++++++------------
1 files changed, 12 insertions(+), 12 deletions(-)

diff --git a/arch/x86/kernel/mfgpt_32.c b/arch/x86/kernel/mfgpt_32.c
index 3960ab7..5519091 100644
--- a/arch/x86/kernel/mfgpt_32.c
+++ b/arch/x86/kernel/mfgpt_32.c
@@ -12,21 +12,21 @@
*/

/*
- * We are using the 32Khz input clock - its the only one that has the
+ * We are using the 32.768Khz input clock - its the only one that has the
* ranges we find desirable. The following table lists the suitable
* divisors and the associated hz, minimum interval
* and the maximum interval:
*
- * Divisor Hz Min Delta (S) Max Delta (S)
- * 1 32000 .0005 2.048
- * 2 16000 .001 4.096
- * 4 8000 .002 8.192
- * 8 4000 .004 16.384
- * 16 2000 .008 32.768
- * 32 1000 .016 65.536
- * 64 500 .032 131.072
- * 128 250 .064 262.144
- * 256 125 .128 524.288
+ * Divisor Hz Min Delta (S) Max Delta (S)
+ * 1 32768 .00048828125 2.000
+ * 2 16384 .0009765625 4.000
+ * 4 8192 .001953125 8.000
+ * 8 4096 .00390625 16.000
+ * 16 2048 .0078125 32.000
+ * 32 1024 .015625 64.000
+ * 64 512 .03125 128.000
+ * 128 256 .0625 256.000
+ * 256 128 .125 512.000
*/

#include <linux/kernel.h>
@@ -45,7 +45,7 @@ static struct mfgpt_timer_t {

#define MFGPT_DIVISOR 16
#define MFGPT_SCALE 4 /* divisor = 2^(scale) */
-#define MFGPT_HZ (32000 / MFGPT_DIVISOR)
+#define MFGPT_HZ (32768 / MFGPT_DIVISOR)
#define MFGPT_PERIODIC (MFGPT_HZ / HZ)

#ifdef CONFIG_GEODE_MFGPT_TIMER
--
1.5.3.4

2008-01-23 21:51:47

by Willy Tarreau

[permalink] [raw]
Subject: [PATCH 2/2] x86: GEODE add the "mfgptfix" boot time option to fix MFGPT timers


The new "mfgptfix" boot command line option may be usd to fix MFGPT
timers on AMD Geode platforms when the BIOS has incorrectly applied
a workaround. TinyBIOS version 0.98 is known to be affected, 0.99
fixes the problem by letting the user disable the workaround.

Signed-off-by: Willy Tarreau <[email protected]>
---
Documentation/kernel-parameters.txt | 5 +++++
arch/x86/kernel/mfgpt_32.c | 15 +++++++++++++++
2 files changed, 20 insertions(+), 0 deletions(-)

diff --git a/Documentation/kernel-parameters.txt b/Documentation/kernel-parameters.txt
index c417877..83c6704 100644
--- a/Documentation/kernel-parameters.txt
+++ b/Documentation/kernel-parameters.txt
@@ -1051,6 +1051,11 @@ and is between 256 and 4096 characters. It is defined in the file
Multi-Function General Purpose Timers on AMD Geode
platforms.

+ mfgptfix [X86-32] Fix MFGPT timers on AMD Geode platforms when
+ the BIOS has incorrectly applied a workaround. TinyBIOS
+ version 0.98 is known to be affected, 0.99 fixes the
+ problem by letting the user disable the workaround.
+
mga= [HW,DRM]

mousedev.tap_time=
diff --git a/arch/x86/kernel/mfgpt_32.c b/arch/x86/kernel/mfgpt_32.c
index 5519091..f38d4a9 100644
--- a/arch/x86/kernel/mfgpt_32.c
+++ b/arch/x86/kernel/mfgpt_32.c
@@ -63,6 +63,21 @@ static int __init mfgpt_disable(char *s)
}
__setup("nomfgpt", mfgpt_disable);

+/* Reset the MFGPT timers. This is required by some broken BIOSes which already
+ * do the same and leave the system in an unstable state. TinyBIOS 0.98 is
+ * affected at least (0.99 is OK with MFGPT workaround left to off).
+ */
+static int __init mfgpt_fix(char *s)
+{
+ u32 val, dummy;
+
+ /* The following udocumented bit resets the MFGPT timers */
+ val = 0xFF; dummy = 0;
+ wrmsr(0x5140002B, val, dummy);
+ return 1;
+}
+__setup("mfgptfix", mfgpt_fix);
+
/*
* Check whether any MFGPTs are available for the kernel to use. In most
* cases, firmware that uses AMD's VSA code will claim all timers during
--
1.5.3.4

2008-01-23 22:00:29

by H. Peter Anvin

[permalink] [raw]
Subject: Re: [PATCH 1/2] x86: GEODE fix MFGPT input clock value

Willy Tarreau wrote:
> The GEODE MFGPT code assumed that 32kHz was 32000 Hz while the boards
> run on a 32.768 kHz digital watch crystal. In practise, it will not
> change the timer's frequency as the skew was only 2.4%, but it
> should provide more accurate intervals.
> - * Divisor Hz Min Delta (S) Max Delta (S)

Seconds are "s", not "S" (S = siemens.)

-hpa

2008-01-23 22:12:06

by Willy Tarreau

[permalink] [raw]
Subject: Re: [PATCH 1/2] x86: GEODE fix MFGPT input clock value

Hi Peter,

On Wed, Jan 23, 2008 at 01:59:32PM -0800, H. Peter Anvin wrote:
> Willy Tarreau wrote:
> >The GEODE MFGPT code assumed that 32kHz was 32000 Hz while the boards
> >run on a 32.768 kHz digital watch crystal. In practise, it will not
> >change the timer's frequency as the skew was only 2.4%, but it
> >should provide more accurate intervals.
> >- * Divisor Hz Min Delta (S) Max Delta (S)
>
> Seconds are "s", not "S" (S = siemens.)

You're quite right. Same as we should write kHz and not Khz. But I'm
used to change other people's work and particularly comments the least
possible. Do you want an update ?

Willy

2008-01-23 22:23:35

by H. Peter Anvin

[permalink] [raw]
Subject: Re: [PATCH 1/2] x86: GEODE fix MFGPT input clock value

Willy Tarreau wrote:
> Hi Peter,
>
> On Wed, Jan 23, 2008 at 01:59:32PM -0800, H. Peter Anvin wrote:
>> Willy Tarreau wrote:
>>> The GEODE MFGPT code assumed that 32kHz was 32000 Hz while the boards
>>> run on a 32.768 kHz digital watch crystal. In practise, it will not
>>> change the timer's frequency as the skew was only 2.4%, but it
>>> should provide more accurate intervals.
>>> - * Divisor Hz Min Delta (S) Max Delta (S)
>> Seconds are "s", not "S" (S = siemens.)
>
> You're quite right. Same as we should write kHz and not Khz. But I'm
> used to change other people's work and particularly comments the least
> possible. Do you want an update ?
>

I much prefer to see this done right. I have a pretty case-sensitive
brain, it seems.

-hpa

2008-01-23 22:37:41

by Jordan Crouse

[permalink] [raw]
Subject: Re: x86: GEODE fix MFGPT input clock value

On 23/01/08 23:11 +0100, Willy Tarreau wrote:
> Hi Peter,
>
> On Wed, Jan 23, 2008 at 01:59:32PM -0800, H. Peter Anvin wrote:
> > Willy Tarreau wrote:
> > >The GEODE MFGPT code assumed that 32kHz was 32000 Hz while the boards
> > >run on a 32.768 kHz digital watch crystal. In practise, it will not
> > >change the timer's frequency as the skew was only 2.4%, but it
> > >should provide more accurate intervals.
> > >- * Divisor Hz Min Delta (S) Max Delta (S)
> >
> > Seconds are "s", not "S" (S = siemens.)
>
> You're quite right. Same as we should write kHz and not Khz. But I'm
> used to change other people's work and particularly comments the least
> possible. Do you want an update ?

Please do - I don't mind if you change the comments - better that they
are right.

Jordan

--
Jordan Crouse
Systems Software Development Engineer
Advanced Micro Devices, Inc.

2008-01-23 22:42:13

by Willy Tarreau

[permalink] [raw]
Subject: Re: [PATCH 1/2] x86: GEODE fix MFGPT input clock value

On Wed, Jan 23, 2008 at 02:22:59PM -0800, H. Peter Anvin wrote:
> Willy Tarreau wrote:
> >Hi Peter,
> >
> >On Wed, Jan 23, 2008 at 01:59:32PM -0800, H. Peter Anvin wrote:
> >>Willy Tarreau wrote:
> >>>The GEODE MFGPT code assumed that 32kHz was 32000 Hz while the boards
> >>>run on a 32.768 kHz digital watch crystal. In practise, it will not
> >>>change the timer's frequency as the skew was only 2.4%, but it
> >>>should provide more accurate intervals.
> >>>- * Divisor Hz Min Delta (S) Max Delta (S)
> >>Seconds are "s", not "S" (S = siemens.)
> >
> >You're quite right. Same as we should write kHz and not Khz. But I'm
> >used to change other people's work and particularly comments the least
> >possible. Do you want an update ?
> >
>
> I much prefer to see this done right. I have a pretty case-sensitive
> brain, it seems.

Oh rest assured that you're not alone. I was smiling reading Andrew's
comments about people who "cnat tpye", and I must admit that I too am
often quite irritated by incorrect case and inverted letters, but I try
to refrain from whining, people say that I do it too much and for nothing :-)

OK, here it comes updated.

Willy


>From 3a314dd5c2a694f5b0a1c1b8b5690ee28f711b5e Mon Sep 17 00:00:00 2001
From: Willy Tarreau <[email protected]>
Date: Wed, 23 Jan 2008 23:05:50 +0100
Subject: [PATCH 1/2] x86: GEODE fix MFGPT input clock value

The GEODE MFGPT code assumed that 32kHz was 32000 Hz while the boards
run on a 32.768 kHz digital watch crystal. In practise, it will not
change the timer's frequency as the skew was only 2.4%, but it
should provide more accurate intervals.

Signed-off-by: Willy Tarreau <[email protected]>
---
arch/x86/kernel/mfgpt_32.c | 27 +++++++++++++--------------
1 files changed, 13 insertions(+), 14 deletions(-)

diff --git a/arch/x86/kernel/mfgpt_32.c b/arch/x86/kernel/mfgpt_32.c
index 3960ab7..f97e6e3 100644
--- a/arch/x86/kernel/mfgpt_32.c
+++ b/arch/x86/kernel/mfgpt_32.c
@@ -12,21 +12,20 @@
*/

/*
- * We are using the 32Khz input clock - its the only one that has the
+ * We are using the 32.768kHz input clock - its the only one that has the
* ranges we find desirable. The following table lists the suitable
- * divisors and the associated hz, minimum interval
- * and the maximum interval:
+ * divisors and the associated Hz, minimum interval and the maximum interval:
*
- * Divisor Hz Min Delta (S) Max Delta (S)
- * 1 32000 .0005 2.048
- * 2 16000 .001 4.096
- * 4 8000 .002 8.192
- * 8 4000 .004 16.384
- * 16 2000 .008 32.768
- * 32 1000 .016 65.536
- * 64 500 .032 131.072
- * 128 250 .064 262.144
- * 256 125 .128 524.288
+ * Divisor Hz Min Delta (s) Max Delta (s)
+ * 1 32768 .00048828125 2.000
+ * 2 16384 .0009765625 4.000
+ * 4 8192 .001953125 8.000
+ * 8 4096 .00390625 16.000
+ * 16 2048 .0078125 32.000
+ * 32 1024 .015625 64.000
+ * 64 512 .03125 128.000
+ * 128 256 .0625 256.000
+ * 256 128 .125 512.000
*/

#include <linux/kernel.h>
@@ -45,7 +44,7 @@ static struct mfgpt_timer_t {

#define MFGPT_DIVISOR 16
#define MFGPT_SCALE 4 /* divisor = 2^(scale) */
-#define MFGPT_HZ (32000 / MFGPT_DIVISOR)
+#define MFGPT_HZ (32768 / MFGPT_DIVISOR)
#define MFGPT_PERIODIC (MFGPT_HZ / HZ)

#ifdef CONFIG_GEODE_MFGPT_TIMER
--
1.5.3.3

2008-01-23 23:17:22

by Arnd Hannemann

[permalink] [raw]
Subject: Re: x86: GEODE fix MFGPT input clock value

Hi,

Jordan Crouse schrieb:
> On 23/01/08 23:11 +0100, Willy Tarreau wrote:
>> Hi Peter,
>>
>> On Wed, Jan 23, 2008 at 01:59:32PM -0800, H. Peter Anvin wrote:
>>> Willy Tarreau wrote:
>>>> The GEODE MFGPT code assumed that 32kHz was 32000 Hz while the boards
>>>> run on a 32.768 kHz digital watch crystal. In practise, it will not
>>>> change the timer's frequency as the skew was only 2.4%, but it
>>>> should provide more accurate intervals.
>>>> - * Divisor Hz Min Delta (S) Max Delta (S)
>>> Seconds are "s", not "S" (S = siemens.)
>> You're quite right. Same as we should write kHz and not Khz. But I'm
>> used to change other people's work and particularly comments the least
>> possible. Do you want an update ?
>
> Please do - I don't mind if you change the comments - better that they
> are right.

While you are on it, please include this one:

--- a/arch/x86/kernel/mfgpt_32.c 2008-01-24 00:08:20.000000000 +0100
+++ b/arch/x86/kernel/mfgpt_32.c 2008-01-24 00:05:17.000000000 +0100
@@ -361,7 +361,7 @@
&mfgpt_clockevent);

printk(KERN_INFO
- "mfgpt-timer: registering the MFGT timer as a clock event.\n");
+ "mfgpt-timer: registering the MFGPT timer as a clock event.\n");
clockevents_register_device(&mfgpt_clockevent);

return 0;


> Jordan
>

Arnd

2008-02-17 14:21:17

by Iain Paton

[permalink] [raw]
Subject: Re: Geode GX/LX watchdog timer (RESEND)

Arnd Hannemann wrote:

> I can confirm that it is still working fine :-)

Hi,

Has anyone managed to build this as a module against the full 2.6.24
release ?

I am seeing the following error:

CC [M] lib/zlib_inflate/infutil.o
CC [M] lib/zlib_inflate/inftrees.o
CC [M] lib/zlib_inflate/inflate_syms.o
LD [M] lib/zlib_inflate/zlib_inflate.o
Building modules, stage 2.
MODPOST 251 modules
ERROR: "geode_mfgpt_toggle_event" [drivers/watchdog/geodewdt.ko] undefined!
ERROR: "geode_mfgpt_alloc_timer" [drivers/watchdog/geodewdt.ko] undefined!
make[1]: *** [__modpost] Error 1
make: *** [modules] Error 2


arch/x86/kernel/mfgpt_32.c where these are defined seems to have been
built ok and they appear in System.map.

The only other thing I've done is to add "[PATCH] pata_cs5536 Fix
secondary port configuration" recently posted by Martin K. Petersen but
I don't believe that would cause this.

.config is available at http://pastebin.ca/907299

Iain

2008-02-17 14:46:19

by Arnd Hannemann

[permalink] [raw]
Subject: Re: Geode GX/LX watchdog timer (RESEND)

Hi,

Iain Paton wrote:
> Arnd Hannemann wrote:
>
>> I can confirm that it is still working fine :-)
>
> Hi,
>
> Has anyone managed to build this as a module against the full 2.6.24
> release ?
>
> I am seeing the following error:
>
> CC [M] lib/zlib_inflate/infutil.o
> CC [M] lib/zlib_inflate/inftrees.o
> CC [M] lib/zlib_inflate/inflate_syms.o
> LD [M] lib/zlib_inflate/zlib_inflate.o
> Building modules, stage 2.
> MODPOST 251 modules
> ERROR: "geode_mfgpt_toggle_event" [drivers/watchdog/geodewdt.ko] undefined!
> ERROR: "geode_mfgpt_alloc_timer" [drivers/watchdog/geodewdt.ko] undefined!
> make[1]: *** [__modpost] Error 1
> make: *** [modules] Error 2
>
>
> arch/x86/kernel/mfgpt_32.c where these are defined seems to have been
> built ok and they appear in System.map.
>
> The only other thing I've done is to add "[PATCH] pata_cs5536 Fix
> secondary port configuration" recently posted by Martin K. Petersen but
> I don't believe that would cause this.
>
> .config is available at http://pastebin.ca/907299

Never tried to built it as a module.
Probably there are issues with that. If I remember correctly I saw a patch in 2.6.25-rc which
mentioned that using mfgpt in modules won't work. Does this apply to 2.6.24 as well?

Best regards,
Arnd Hannemann



2008-02-17 14:55:28

by Adrian Bunk

[permalink] [raw]
Subject: Re: Geode GX/LX watchdog timer (RESEND)

On Sun, Feb 17, 2008 at 03:46:01PM +0100, Arnd Hannemann wrote:
> Hi,
>
> Iain Paton wrote:
> > Arnd Hannemann wrote:
> >
> >> I can confirm that it is still working fine :-)
> >
> > Hi,
> >
> > Has anyone managed to build this as a module against the full 2.6.24
> > release ?
> >
> > I am seeing the following error:
> >
> > CC [M] lib/zlib_inflate/infutil.o
> > CC [M] lib/zlib_inflate/inftrees.o
> > CC [M] lib/zlib_inflate/inflate_syms.o
> > LD [M] lib/zlib_inflate/zlib_inflate.o
> > Building modules, stage 2.
> > MODPOST 251 modules
> > ERROR: "geode_mfgpt_toggle_event" [drivers/watchdog/geodewdt.ko] undefined!
> > ERROR: "geode_mfgpt_alloc_timer" [drivers/watchdog/geodewdt.ko] undefined!
> > make[1]: *** [__modpost] Error 1
> > make: *** [modules] Error 2
> >
> >
> > arch/x86/kernel/mfgpt_32.c where these are defined seems to have been
> > built ok and they appear in System.map.
> >
> > The only other thing I've done is to add "[PATCH] pata_cs5536 Fix
> > secondary port configuration" recently posted by Martin K. Petersen but
> > I don't believe that would cause this.
> >
> > .config is available at http://pastebin.ca/907299
>
> Never tried to built it as a module.
> Probably there are issues with that. If I remember correctly I saw a patch in 2.6.25-rc which
> mentioned that using mfgpt in modules won't work. Does this apply to 2.6.24 as well?

For using code from modules it must be explicitely EXPORT_SYMBOL{,GPL}'ed.

Adding
EXPORT_SYMBOL_GPL(geode_mfgpt_toggle_event);
and
EXPORT_SYMBOL_GPL(geode_mfgpt_alloc_timer);
below the respective functions in mfgpt_32.c should fix this issue.

> Best regards,
> Arnd Hannemann

cu
Adrian

--

"Is there not promise of rain?" Ling Tan asked suddenly out
of the darkness. There had been need of rain for many days.
"Only a promise," Lao Er said.
Pearl S. Buck - Dragon Seed

2008-02-17 16:10:27

by Iain Paton

[permalink] [raw]
Subject: Re: Geode GX/LX watchdog timer (RESEND)

Adrian Bunk wrote:
> On Sun, Feb 17, 2008 at 03:46:01PM +0100, Arnd Hannemann wrote:
>> Never tried to built it as a module.
>> Probably there are issues with that. If I remember correctly I saw a patch in 2.6.25-rc which
>> mentioned that using mfgpt in modules won't work. Does this apply to 2.6.24 as well?
>
> For using code from modules it must be explicitely EXPORT_SYMBOL{,GPL}'ed.
>
> Adding
> EXPORT_SYMBOL_GPL(geode_mfgpt_toggle_event);
> and
> EXPORT_SYMBOL_GPL(geode_mfgpt_alloc_timer);
> below the respective functions in mfgpt_32.c should fix this issue.

I couldn't find the patch Arnd mentioned on lkml or in Linus git tree,
but adding the lines suggested by Adrian gets me a working module.

Hopefully the patch will arrive in the mainline tree at some point.

Thanks to both of you for the help!

Iain

2008-02-17 17:30:23

by Andres Salomon

[permalink] [raw]
Subject: Re: Geode GX/LX watchdog timer (RESEND)

On Sun, 17 Feb 2008 16:10:09 +0000
Iain Paton <[email protected]> wrote:

> Adrian Bunk wrote:
> > On Sun, Feb 17, 2008 at 03:46:01PM +0100, Arnd Hannemann wrote:
> >> Never tried to built it as a module.
> >> Probably there are issues with that. If I remember correctly I saw a patch in 2.6.25-rc which
> >> mentioned that using mfgpt in modules won't work. Does this apply to 2.6.24 as well?
> >
> > For using code from modules it must be explicitely EXPORT_SYMBOL{,GPL}'ed.
> >
> > Adding
> > EXPORT_SYMBOL_GPL(geode_mfgpt_toggle_event);
> > and
> > EXPORT_SYMBOL_GPL(geode_mfgpt_alloc_timer);
> > below the respective functions in mfgpt_32.c should fix this issue.
>
> I couldn't find the patch Arnd mentioned on lkml or in Linus git tree,
> but adding the lines suggested by Adrian gets me a working module.
>
> Hopefully the patch will arrive in the mainline tree at some point.
>

This was originally split out into two separate patches; one that exported
the proper symbols, and the other containing the watchdog timer. I merged
them in the geode tree. The patch is here:

http://git.infradead.org/?p=geode.git;a=commitdiff;h=5a840828ddb5bb7381435509a9460e0ba4aab550

That's also checkpatch.pl happy (or at least, it was when I committed it).

2008-02-17 19:47:22

by Arnd Hannemann

[permalink] [raw]
Subject: Re: Geode GX/LX watchdog timer (RESEND)

Iain Paton schrieb:
> Adrian Bunk wrote:
>> On Sun, Feb 17, 2008 at 03:46:01PM +0100, Arnd Hannemann wrote:
>>> Never tried to built it as a module.
>>> Probably there are issues with that. If I remember correctly I saw a
>>> patch in 2.6.25-rc which
>>> mentioned that using mfgpt in modules won't work. Does this apply to
>>> 2.6.24 as well?
>>
>> For using code from modules it must be explicitely
>> EXPORT_SYMBOL{,GPL}'ed.
>>
>> Adding
>> EXPORT_SYMBOL_GPL(geode_mfgpt_toggle_event);
>> and
>> EXPORT_SYMBOL_GPL(geode_mfgpt_alloc_timer);
>> below the respective functions in mfgpt_32.c should fix this issue.
>
> I couldn't find the patch Arnd mentioned on lkml or in Linus git tree,
> but adding the lines suggested by Adrian gets me a working module.


I meant commit fa28e067c3b8af96c79c060e163b1387c172ae75 in linus git, but seems
I misinterpreted it.

> x86: GEODE: MFGPT: drop module owner usage from MFGPT API
>
> We had planned to use the 'owner' field for allowing re-allocation of
> MFGPTs; however, doing it by module owner name isn't flexible enough. So,
> drop this for now. If it turns out that we need timers in modules, we'll
> need to come up with a scheme that matches the write-once fields of the
> MFGPTx_SETUP register, and drops ponies from the sky.
>
> Signed-off-by: Andres Salomon <[email protected]>
> Signed-off-by: Jordan Crouse <[email protected]>
> Signed-off-by: Ingo Molnar <[email protected]>
> Signed-off-by: Thomas Gleixner <[email protected]>

Best regards,
Arnd