Subject: port-i386/6928: i386 SMP
To: None <gnats-bugs@gnats.netbsd.org>
From: Stefan Grefen <grefen@hprc.tandem.com>
List: netbsd-bugs
Date: 02/02/1999 15:45:14
>Number: 6928
>Category: port-i386
>Synopsis: AP processor bootstrap
>Confidential: no
>Severity: non-critical
>Priority: medium
>Responsible: port-i386-maintainer (NetBSD/i386 Portmaster)
>State: open
>Class: change-request
>Submitter-Id: net
>Arrival-Date: Tue Feb 2 06:35:00 1999
>Last-Modified:
>Originator: Stefan Grefen
>Organization:
Stefan Grefen Tandem Computers Europe Inc.
grefen@hprc.tandem.com High Performance Research Center
--- Hacking's just another word for nothing left to kludge. ---
>Release: NetBSD-current 01 Feb 1999
>Environment:
System: NetBSD hrriss 1.3H NetBSD 1.3H (HRRISS) #13: Wed Oct 28 13:35:10 CET 1998 grefen@hrriss:/old/usr/src/sup/src/sys/arch/i386/compile/HRRISS i386
>Description:
Bootstrap suuport for SMP system based on intel MP spec
>How-To-Repeat:
>Fix:
*** /usr/sup/src/sys/arch/i386/./conf/files.i386 Fri Jan 29 13:15:42 1999
--- ././conf/files.i386 Tue Feb 2 15:07:09 1999
***************
*** 56,61 ****
--- 56,62 ----
file arch/i386/i386/trap.c
file arch/i386/i386/vm_machdep.c
file dev/cons.c
+ file arch/i386/i386/multiprocessor.s xxmp
major {vnd = 14}
#
***************
*** 236,241 ****
--- 237,256 ----
attach apm at mainbus
file arch/i386/i386/apm.c apm needs-count
file arch/i386/i386/apmcall.s apm
+
+ # Intel SMP specification 1.4
+ device itlmps {id = -1}
+ attach itlmps at mainbus
+ file arch/i386/i386/mp_ispec.c itlmps
+
+ # CPUS
+ device cpu
+ attach cpu at itlmps
+ file arch/i386/i386/cpu.c cpu
+ #apics
+ device apic
+ attach apic at itlmps
+ file arch/i386/i386/apic.c apic
#
# Compatibility modules
*** /dev/null Sun Jan 31 22:45:35 1999
--- ././conf/PIIMP Tue Feb 2 14:32:57 1999
***************
*** 0 ****
--- 1,594 ----
+
+ #
+ # GENERIC -- everything that's currently supported
+ #
+
+ include "arch/i386/conf/std.i386"
+
+ maxusers 32 # estimated number of users
+
+ # CPU support. At least one is REQUIRED.
+ options I386_CPU
+ options I486_CPU
+ options I586_CPU
+ options I686_CPU
+ options XXMP
+
+ # CPU-related options.
+ options MATH_EMULATE # floating point emulation
+ #options VM86 # virtual 8086 emulation
+ options USER_LDT # user-settable LDT; used by WINE
+ # eliminate delay no-ops in I/O; recommended on all but very old machines
+ #options DUMMY_NOPS
+
+ # delay between "rebooting ..." message and hardware reset, in milliseconds
+ #options CPURESET_DELAY=2000
+
+ # Misc. i386-specific options
+ options XSERVER # X server support in console drivers
+ #options XSERVER_DDB # PF12 gets you into DDB when X is running
+
+ # This option allows you to force a serial console at the specified
+ # I/O address. see console(4) for details.
+ #options "CONSDEVNAME=\"com\"",CONADDR=0x2f8,CONSPEED=57600
+ # you don't want the option below ON iff you are using the
+ # serial console option of the new boot strap code.
+ #options CONS_OVERRIDE # Always use above! independent of boot info
+
+ # The following options override the memory sizes passed in from the boot
+ # block. Use them *only* if the boot block is unable to determine the correct
+ # values. Note that the BIOS may *correctly* report less than 640k of base
+ # memory if the extended BIOS data area is located at the top of base memory
+ # (as is the case on most recent systems).
+ #options REALBASEMEM=639 # size of base memory (in KB)
+ #options REALEXTMEM=15360 # size of extended memory (in KB)
+
+ # Standard system options
+
+ options UCONSOLE # users can use TIOCCONS (for xconsole)
+ options INSECURE # disable kernel security levels
+
+ options RTC_OFFSET=0 # hardware clock is this many mins. west of GMT
+ #options NTP # NTP phase/frequency locked loop
+
+ options KTRACE # system call tracing via ktrace(1)
+
+ options SYSVMSG # System V-like message queues
+ options SYSVSEM # System V-like semaphores
+ options SYSVSHM # System V-like memory sharing
+ #options SHMMAXPGS=1024 # 1024 pages is the default
+
+ options LKM # loadable kernel modules
+
+ # Diagnostic/debugging support options
+ options DIAGNOSTIC # cheap kernel consistency checks
+ #options DEBUG # expensive debugging checks/support
+ #options KMEMSTATS # kernel memory statistics (vmstat -m)
+ options DDB # in-kernel debugger
+ options DDB_HISTORY_SIZE=100 # enable history editing in DDB
+ #options KGDB # remote debugger
+ #options "KGDB_DEVNAME=\"com\"",KGDBADDR=0x3f8,KGDBRATE=9600
+ #makeoptions DEBUG="-g" # compile full symbol table
+
+ # Compatibility options
+ options COMPAT_NOMID # compatibility with 386BSD, BSDI, NetBSD 0.8,
+ options COMPAT_09 # NetBSD 0.9,
+ options COMPAT_10 # NetBSD 1.0,
+ options COMPAT_11 # NetBSD 1.1,
+ options COMPAT_12 # NetBSD 1.2,
+ options COMPAT_13 # NetBSD 1.3,
+ options COMPAT_43 # and 4.3BSD
+ options COMPAT_386BSD_MBRPART # recognize old partition ID
+
+ options COMPAT_SVR4 # binary compatibility with SVR4
+ options COMPAT_IBCS2 # binary compatibility with SCO and ISC
+ options COMPAT_LINUX # binary compatibility with Linux
+ options COMPAT_FREEBSD # binary compatibility with FreeBSD
+
+ # Executable format options
+ options EXEC_ELF32 # 32-bit ELF executables (SVR4, Linux)
+
+ # File systems
+ file-system FFS # UFS
+ #file-system EXT2FS # second extended file system (linux)
+ file-system LFS # log-structured file system
+ file-system MFS # memory file system
+ file-system NFS # Network File System client
+ file-system CD9660 # ISO 9660 + Rock Ridge file system
+ file-system MSDOSFS # MS-DOS file system
+ file-system FDESC # /dev/fd
+ file-system KERNFS # /kern
+ file-system NULLFS # loopback file system
+ file-system PORTAL # portal filesystem (still experimental)
+ file-system PROCFS # /proc
+ file-system UMAPFS # NULLFS + uid and gid remapping
+ file-system UNION # union file system
+ file-system CODA # Coda File System; also needs vcoda (below)
+
+ # File system options
+ options QUOTA # UFS quotas
+ #options FFS_EI # FFS Endian Independant support
+ options NFSSERVER # Network File System server
+ #options EXT2FS_SYSTEM_FLAGS # makes ext2fs file flags (append and
+ # immutable) behave as system flags.
+
+ # Networking options
+ #options GATEWAY # packet forwarding
+ options INET # IP + ICMP + TCP + UDP
+ #options MROUTING # IP multicast routing
+ #options NS # XNS
+ #options NSIP # XNS tunneling over IP
+ #options ISO,TPIP # OSI
+ #options EON # OSI tunneling over IP
+ #options CCITT,LLC,HDLC # X.25
+ #options NETATALK # AppleTalk networking protocols
+ #options PPP_BSDCOMP # BSD-Compress compression support for PPP
+ #options PPP_DEFLATE # Deflate compression support for PPP
+ #options PPP_FILTER # Active filter support for PPP (requires bpf)
+ #options PFIL_HOOKS # pfil(9) packet filter hooks
+ #options IPFILTER_LOG # ipmon(8) log support
+
+ # Compatibility with 4.2BSD implementation of TCP/IP. Not recommended.
+ #options TCP_COMPAT_42
+
+ # These options enable verbose messages for several subsystems.
+ # Warning, these may compile large string tables into the kernel!
+ options EISAVERBOSE # verbose EISA device autoconfig messages
+ options PCIVERBOSE # verbose PCI device autoconfig messages
+ #options PCMCIAVERBOSE # verbose PCMCIA configuration messages
+ options SCSIVERBOSE # human readable SCSI error messages
+ options USBVERBOSE # verbose USB device autoconfig messages
+
+ options NFS_BOOT_BOOTP,NFS_BOOT_BOOTPARAM
+
+ # Kernel root file system and dump configuration.
+ config netbsd root on ? type ?
+ #config netbsd root on sd0a type ffs
+ #config netbsd root on ? type nfs
+
+ #
+ # Device configuration
+ #
+
+ mainbus0 at root
+
+ itlmps0 at mainbus0
+ apm0 at mainbus0 # Advanced power management
+ #cpu* at mainbus0
+ cpu* at itlmps0 id ?
+ apic* at itlmps0 id ?
+
+ # Basic Bus Support
+
+ # PCI bus support
+ pci* at mainbus? bus ?
+ pci* at pchb? bus ?
+ pci* at ppb? bus ?
+
+ # PCI bridges
+ pchb* at pci? dev ? function ? # PCI-Host bridges
+ pceb* at pci? dev ? function ? # PCI-EISA bridges
+ pcib* at pci? dev ? function ? # PCI-ISA bridges
+ ppb* at pci? dev ? function ? # PCI-PCI bridges
+ # XXX 'puc's aren't really bridges, but there's no better place for them here
+ puc* at pci? dev ? function ? # PCI "universal" comm. cards
+
+ # EISA bus support
+ eisa* at mainbus?
+ eisa* at pceb?
+
+ # ISA bus support
+ isa* at mainbus?
+ isa* at pceb?
+ isa* at pcib?
+
+ # PCMCIA bus support
+ pcmcia* at pcic? controller ? socket ?
+
+ # ISA PCMCIA controllers
+ pcic0 at isa? port 0x3e0 iomem 0xd0000 iosiz 0x4000
+ pcic1 at isa? port 0x3e2 iomem 0xd4000 iosiz 0x4000
+
+ # PCI PCMCIA controllers
+ #pcic0 at pci? dev? function ?
+
+ # ISA Plug-and-Play bus support
+ isapnp0 at isa?
+
+ # ISA Plug-and-Play PCMCIA controllers
+ pcic* at isapnp?
+
+ # Coprocessor Support
+
+ # Math Coprocessor support
+ npx0 at isa? port 0xf0 irq 13 # x86 math coprocessor
+
+
+ # Console Devices
+
+ # ISA console. You can only configure one of these!
+ pc0 at isa? port 0x60 irq 1 # pccons generic PC console driver
+ #vt0 at isa? port 0x60 irq 1 # PCVT console driver
+
+ # Keyboard layout configuration for pccons
+ #options FRENCH_KBD
+ #options FINNISH_KBD
+ #options GERMAN_KBD
+ #options NORWEGIAN_KBD
+
+ pcppi0 at isa?
+ sysbeep0 at pcppi?
+
+ # Serial Devices
+
+ # PCI serial interfaces
+ #com* at puc? port ? # 16x450s on "universal" comm boards
+ #cy* at pci? dev ? function ? # Cyclades Cyclom-Y serial boards
+
+ # ISA Plug-and-Play serial interfaces
+ #com* at isapnp? # Modems and serial boards
+
+ # PCMCIA serial interfaces
+ com* at pcmcia? function ? # Modems and serial cards
+
+ pcmcom* at pcmcia? function ? # PCMCIA multi-port serial cards
+ com* at pcmcom? slave ? # ...and the slave devices
+
+ # ISA serial interfaces
+ #options COM_HAYESP # adds Hayes ESP serial board support
+ com0 at isa? port 0x3f8 irq 4 # Standard PC serial ports
+ com1 at isa? port 0x2f8 irq 3
+ com2 at isa? port 0x3e8 irq 5
+ #com3 at isa? port 0x2e8 irq 9
+ #ast0 at isa? port 0x1a0 irq 5 # AST 4-port serial cards
+ #com* at ast? slave ?
+ #boca0 at isa? port 0x100 irq 5 # BOCA 8-port serial cards
+ #com* at boca? slave ?
+ #tcom0 at isa? port 0x100 irq 7 # TC-800 8-port serial cards
+ #com* at tcom? slave ?
+ #rtfps0 at isa? port 0x1230 irq 10 # RT 4-port serial cards
+ #com* at rtfps? slave ?
+ #cy0 at isa? iomem 0xd4000 irq 12 # Cyclades serial cards
+
+
+ # Parallel Printer Interfaces
+
+ # PCI parallel printer interfaces
+ #lpt* at puc? port ? # || ports on "universal" comm boards
+
+ # ISA parallel printer interfaces
+ lpt0 at isa? port 0x378 irq 7 # standard PC parallel ports
+ lpt1 at isa? port 0x278
+ lpt2 at isa? port 0x3bc
+
+
+ # SCSI Controllers and Devices
+
+ # PCI SCSI controllers
+ #adv* at pci? dev ? function ? # AdvanSys 1200[A,B], 9xx[U,UA] SCSI
+ #adw* at pci? dev ? function ? # AdvanSys 9xxUW SCSI
+ #ahc* at pci? dev ? function ? # Adaptec [23]94x, aic78x0 SCSI
+ #bha* at pci? dev ? function ? # BusLogic 9xx SCSI
+ #isp* at pci? dev ? function ? # Qlogic ISP [12]0x0 SCSI/FibreChannel
+ ncr* at pci? dev ? function ? # NCR 53c8xx SCSI
+
+ # EISA SCSI controllers
+ #jahb* at eisa? slot ? # Adaptec 174[02] SCSI
+ #ajhc* at eisa? slot ? # Adaptec 274x, aic7770 SCSI
+ #bha* at eisa? slot ? # BusLogic 7xx SCSI
+ #uha* at eisa? slot ? # UltraStor 24f SCSI
+
+ # PCMCIA SCSI controllers
+ aic* at pcmcia? function ? # Adaptec APA-1460 SCSI
+
+ # ISA Plug-and-Play SCSI controllers
+ #aha* at isapnp? # Adaptec AHA-154[02
+ #aic* at isapnp? # Adaptec AHA-1520B
+
+ # ISA SCSI controllers
+ #aha0 at isa? port 0x330 irq ? drq ? # Adaptec 154[02] SCSI
+ #aha1 at isa? port 0x334 irq ? drq ?
+ #ahc0 at isa? port ? irq ? # Adaptec 284x SCSI
+ #aic0 at isa? port 0x340 irq 11 # Adaptec 152[02] SCSI
+ #bha0 at isa? port 0x330 irq ? drq ? # BusLogic [457]4X SCSI
+ #bha1 at isa? port 0x334 irq ? drq ?
+ #nca0 at isa? port 0x360 irq 15 # Port-mapped NCR 53C80 contoller
+ #nca1 at isa? iomem 0xd8000 irq 5 # Memory-mapped controller (T128, etc.)
+ #sea0 at isa? iomem 0xc8000 irq 5 # Seagate/Future Domain SCSI
+ #uha0 at isa? port 0x330 irq ? drq ? # UltraStor [13]4f SCSI
+ #uha1 at isa? port 0x340 irq ? drq ?
+ #wds0 at isa? port 0x350 irq 15 drq 6 # WD7000 and TMC-7000 controllers
+ #wds1 at isa? port 0x358 irq 11 drq 5
+
+ # SCSI bus support
+ #scsibus* at adv?
+ #scsibus* at adw?
+ #scsibus* at aha?
+ #scsibus* at ahb?
+ #scsibus* at ahc?
+ #scsibus* at aic?
+ #scsibus* at bha?
+ #scsibus* at isp?
+ #scsibus* at nca?
+ scsibus* at ncr?
+ #scsibus* at sea?
+ #scsibus* at uha?
+ #scsibus* at wds?
+
+ # SCSI devices
+ sd* at scsibus? target ? lun ? # SCSI disk drives
+ st* at scsibus? target ? lun ? # SCSI tape drives
+ cd* at scsibus? target ? lun ? # SCSI CD-ROM drives
+ ch* at scsibus? target ? lun ? # SCSI autochangers
+ ss* at scsibus? target ? lun ? # SCSI scanners
+ uk* at scsibus? target ? lun ? # SCSI unknown
+
+
+ # IDE and Related Devices
+ # PCI IDE controllers (CMD tech's PCI0640, Intel's PIIx, ...).
+ # The 0x0001 flag force the driver to use DMA, even if the driver doesn't know
+ # how to set up DMA modes for this chip. This may work, or may cause
+ # a machine hang with some controllers.
+ pciide* at pci ? dev ? function ? flags 0x0000
+
+ # ISA Plug-and-Play IDE controllers
+ wdc* at isapnp?
+
+ # PCMCIA IDE controllers
+ wdc* at pcmcia? function ?
+
+ # ISA ST506, ESDI, and IDE controllers
+ wdc0 at isa? port 0x1f0 irq 14
+ wdc1 at isa? port 0x170 irq 15
+
+ # IDE drives.
+ # Flags are used only with controlers that support DMA operations
+ # and mode settings (e.g. some pciide controllers)
+ # The first 4 bytes of the flags define the PIO mode to use, the
+ # second DMA mode and the third UltraDMA mode. For each group of 4 bytes,
+ # the 3 lower define the mode to use, and the last one must be 1 for the
+ # setting to be used. For DMA and UDMA, 0xf means 'disable'.
+ # 0x0fac means 'use PIO mode 4 DMA mode 2, disable UltraDMA'.
+ # 0x0000 means "use whatever the drive claims to support.
+ wd* at wdc? channel ? drive ? flags 0x0000
+ wd* at pciide? channel ? drive ? flags 0x0000
+
+ # ATAPI bus support
+ atapibus* at wdc? channel ?
+ atapibus* at pciide? channel ?
+
+ # ATAPI devices
+ # flags have the same meaning as for IDE drives.
+ cd* at atapibus? drive ? flags 0x0000 # ATAPI CD-ROM drives
+ sd* at atapibus? drive ? flags 0x0000 # ATAPI disk drives
+ uk* at atapibus? drive ? flags 0x0000 # ATAPI unknown
+
+
+ # Miscellaneous mass storage devices
+
+ # ISA floppy
+ fdc0 at isa? port 0x3f0 irq 6 drq 2 # standard PC floppy controllers
+ #fdc1 at isa? port 0x370 irq ? drq ?
+ fd* at fdc? drive ? # the drives themselves
+ # some machines need you to do this instead of fd*
+ #fd0 at fdc0 drive 0
+
+ # ISA CD-ROM devices
+ #mcd0 at isa? port 0x300 irq 10 # Mitsumi CD-ROM drives
+
+ # ISA tape devices
+ # note: the wt driver conflicts unpleasantly with SMC boards at the
+ # same I/O address. The probe reprograms their EEPROMs. Don't
+ # uncomment it unless you are actually using it.
+ #wt0 at isa? port 0x308 irq 5 drq 1 # Archive and Wangtek QIC tape drives
+
+
+ # Network Interfaces
+
+ # PCI network interfaces
+ de* at pci? dev ? function ? # DEC 21x4x-based Ethernet
+ #en* at pci? dev ? function ? # ENI/Adaptec ATM
+ #ep* at pci? dev ? function ? # 3Com 3c59x
+ #ex* at pci? dev ? function ? # 3Com 90x[B]
+ #epic* at pci? dev ? function ? # SMC EPIC/100 Ethernet
+ #esh* at pci? dev ? function ? # Essential HIPPI card
+ #fpa* at pci? dev ? function ? # DEC DEFPA FDDI
+ #fxp* at pci? dev ? function ? # Intel EtherExpress PRO 10+/100B
+ #le* at pci? dev ? function ? # PCnet-PCI Ethernet
+ #ne* at pci? dev ? function ? # NE2000-compatible Ethernet
+ #tl* at pci? dev ? function ? # ThunderLAN-based Ethernet
+
+ # EISA network interfaces
+ #ep* at eisa? slot ? # 3Com 3c579 Ethernet
+ #fea* at eisa? slot ? # DEC DEFEA FDDI
+
+ # ISA Plug-and-Play network interfaces
+ #ep* at isapnp? # 3Com 3c509 Ethernet
+ #ne* at isapnp? # NE2000-compatible Ethernet
+
+ # PCMCIA network interfaces
+ ep* at pcmcia? function ? # 3Com 3c589 and 3c562 Ethernet
+ #mbe* at pcmcia? function ? # MB8696x based Ethernet
+ ne* at pcmcia? function ? # NE2000-compatible Ethernet
+ #sm* at pcmcia? function ? # Megahertz Ethernet
+
+ # ISA network interfaces
+ #ate0 at isa? port 0x2a0 irq ? # AT1700
+ #cs0 at isa? port 0x300 iomem ? irq ? drq ? # CS8900 Ethernet
+ #ec0 at isa? port 0x250 iomem 0xd8000 irq 9 # 3Com 3c503 Ethernet
+ #eg0 at isa? port 0x280 irq 9 # 3C505 ethernet cards
+ #el0 at isa? port 0x300 irq 9 # 3C501 ethernet cards
+ #ep0 at isa? port ? irq ? # 3C509 ethernet cards
+ #ef0 at isa? port 0x360 iomem 0xd0000 irq 7 # 3C507
+ #ai0 at isa? port 0x360 iomem 0xd0000 irq 7 # StarLAN
+ #fmv0 at isa? port 0x2a0 irq ? # FMV-180 series
+ #ix0 at isa? port 0x300 irq 10 # EtherExpress/16
+ #iy0 at isa? port 0x360 irq ? # EtherExpress PRO 10 ISA
+ #lc0 at isa? port 0x320 iomem ? irq ? # DEC EtherWORKS III (LEMAC)
+ ##depca0 at isa? port 0x300 iomem 0xc8000 iosiz 0x8000 irq 5 # DEPCA
+ ##le* at depca?
+ #nele0 at isa? port 0x320 irq 9 drq 7 # NE2100
+ #le* at nele?
+ #bicc0 at isa? port 0x320 irq 10 drq 7 # BICC IsoLan
+ #le* at bicc?
+ #ne0 at isa? port 0x280 irq 9 # NE[12]000 ethernet cards
+ #ne1 at isa? port 0x300 irq 10
+ #sm0 at isa? port 0x300 irq 10 # SMC91C9x Ethernet
+ #we0 at isa? port 0x280 iomem 0xd0000 irq 9 # WD/SMC Ethernet
+ #we1 at isa? port 0x300 iomem 0xcc000 irq 10
+
+ # MII/PHY support
+ #exphy* at mii? phy ? # 3Com internal PHYs
+ #icsphy* at mii? phy ? # Integrated Circuit Systems ICS1890
+ #inphy* at mii? phy ? # Intel 82555 PHYs
+ #lxtphy* at mii? phy ? # Level One LXT-970 PHYs
+ #nsphy* at mii? phy ? # NS83840 PHYs
+ #qsphy* at mii? phy ? # Quality Semiconductor QS6612 PHYs
+ ##sqphy* at mii? phy ? # Seeq 80220/80221/80223 PHYs
+ #tlphy* at mii? phy ? # ThunderLAN PHYs
+ ukphy* at mii? phy ? # generic unknown PHYs
+
+ # USB Controller and Devices
+
+ # PCI USB controllers
+ uhci* at pci? # Universal Host Controller (Intel)
+ ohci* at pci? # Open Host Controller
+
+ # USB bus support
+ usb* at uhci?
+ usb* at ohci?
+
+ # USB Hubs
+ uhub* at usb?
+ uhub* at uhub? port ? configuration ? interface ?
+
+ # USB Mice
+ ums* at uhub? port ? configuration ? interface ?
+ wsmouse* at ums?
+
+ # USB Keyboards
+ ukbd* at uhub? port ? configuration ? interface ?
+ wskbd* at ukbd? console ?
+
+ # USB Generic HID devices
+ uhid* at uhub? port ? configuration ? interface ?
+
+ # USB Printer
+ ulpt* at uhub? port ? configuration ? interface ?
+
+ # USB Generic driver
+ ugen* at uhub? port ? configuration ? interface ?
+
+ # Audio Devices
+
+ # PCI audio devices
+ #eap* at pci? dev ? function ? # Ensoniq AudioPCI
+ #sv* at pci? dev ? function ? # S3 SonicVibes
+
+ # ISA Plug-and-Play audio devices
+ #ess* at isapnp? # ESS Tech ES1887, ES1888, ES888 audio
+ #guspnp* at isapnp? # Gravis Ultra Sound PnP audio
+ sb* at isapnp? # SoundBlaster-compatible audio
+ wss* at isapnp? # Windows Sound System
+ #ym* at isapnp? # Yamaha OPL3-SA3 audio
+
+ # ISA audio devices
+ #aria0 at isa? port 0x290 irq 10 # Aria
+ #gus0 at isa? port 0x220 irq 7 drq 1 drq2 6 # Gravis Ultra Sound
+ #pas0 at isa? port 0x220 irq 7 drq 1 # ProAudio Spectrum
+ #pss0 at isa? port 0x220 irq 7 drq 6 # Personal Sound System
+ #sp0 at pss0 port 0x530 irq 10 drq 0 # sound port driver
+ #sb0 at isa? port 0x220 irq 5 drq 1 drq2 5 # SoundBlaster
+ #wss0 at isa? port 0x530 irq 10 drq 0 drq2 1 # Windows Sound System
+
+ # OPL[23] FM syntheziers
+ #opl0 at isa? port 0x388 # use only if not attached to sound card
+ #opl* at ess?
+ opl* at sb?
+ #opl* at sv?
+
+ # USB Audio devices
+ #uaudio* at uhub? port ? configuration ? interface ?
+
+ # Audio support
+ #audio* at aria?
+ #audio* at eap?
+ #audio* at ess?
+ #audio* at gus?
+ #audio* at guspnp?
+ #audio* at pas?
+ audio* at sb?
+ #audio* at sp?
+ #audio* at sv?
+ #audio* at uaudio?
+ audio* at wss?
+ #audio* at ym?
+
+ # MIDI support
+ midi* at pcppi? # MIDI interface to the PC speaker
+ midi* at sb? # SB MPU401 port
+ midi* at opl? # OPL FM synth
+
+ # The spkr driver provides a simple tone interface to the built in speaker.
+ #spkr0 at pcppi? # PC speaker
+
+
+ # Mice
+
+ # ISA busmice
+ #lms0 at isa? port 0x23c irq 5 # Logitech bus mouse
+ #lms1 at isa? port 0x238 irq 5
+ #mms0 at isa? port 0x23c irq 5 # Microsoft InPort mouse
+ #mms1 at isa? port 0x238 irq 5
+ opms0 at pc? irq 12 # PS/2 auxiliary port mouse
+ #pms0 at vt? irq 12 # PS/2 auxiliary port mouse
+
+
+ # Joysticks
+
+ # ISA Plug-and-Play joysticks
+ joy* at isapnp? # Game ports (usually on audio cards)
+
+ # ISA joysticks. Probe is a little strange; add only if you have one.
+ #joy0 at isa? port 0x201
+
+
+ # Miscellaneous Devices
+
+ # Planetconnect Satellite receiver driver.
+ #satlink0 at isa? port 0x300 drq 1
+
+
+ # Pull in optional local configuration
+ include "arch/i386/conf/GENERIC.local"
+
+
+ # Pseudo-Devices
+
+ # disk/mass storage pseudo-devices
+ pseudo-device ccd 4 # concatenated/striped disk devices
+ #pseudo-device raid 4 # RAIDframe disk driver
+ pseudo-device md 1 # memory disk device (ramdisk)
+ pseudo-device vnd 4 # disk-like interface to files
+
+ # network pseudo-devices
+ pseudo-device bpfilter 8 # Berkeley packet filter
+ pseudo-device ipfilter # IP filter (firewall) and NAT
+ pseudo-device loop # network loopback
+ pseudo-device ppp 2 # Point-to-Point Protocol
+ pseudo-device sl 2 # Serial Line IP
+ #pseudo-device strip 2 # Starmode Radio IP (Metricom)
+ pseudo-device tun 2 # network tunneling over tty
+ pseudo-device gre 2 # generic L3 over IP tunnel
+
+ # miscellaneous pseudo-devices
+ pseudo-device pty 64 # pseudo-terminals
+ #pseudo-device tb 1 # tablet line discipline
+ pseudo-device sequencer 1 # MIDI sequencer
+
+ # rnd is EXPERIMENTAL at this point.
+ #pseudo-device rnd # /dev/random and in-kernel generator
+ #options RND_COM # use "com" randomness as well (BROKEN)
+
+ # a pseudo device needed for Coda # also needs CODA (above)
+ pseudo-device vcoda 4 # coda minicache <-> venus comm.
*** /usr/sup/src/sys/arch/i386/./conf/Makefile.i386 Fri Jan 29 13:15:42 1999
--- ././conf/Makefile.i386 Tue Feb 2 15:09:47 1999
***************
*** 191,198 ****
--- 191,205 ----
# depend on CPU configuration
locore.o machdep.o: Makefile
+ mp_tramp_values.h: ${I386}/i386/multiprocessor.s ${I386}/i386/mps2h
+ ${I386}/i386/mps2h ${CPPFLAGS} -D_LOCORE ${I386}/i386/multiprocessor.s >mp_tramp_values.h
locore.o: ${I386}/i386/locore.s assym.h
${NORMAL_S}
+
+ multiprocessor.o: ${I386}/i386/multiprocessor.s assym.h mp_tramp_values.h
+ ${NORMAL_S}
+
+
%RULES
*** /dev/null Sun Jan 31 22:45:35 1999
--- ././i386/mp_ispec.c Tue Feb 2 12:58:57 1999
***************
*** 0 ****
--- 1,923 ----
+ /*
+ * Copyright (c) 1999 Stefan Grefen
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ * must display the following acknowledgement:
+ * This product includes software developed by Stefan Grefen.
+ * 4. The name Stefan Grefen may not be used to endorse or promote
+ * products derived from this software without specific prior written
+ * permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY TERRENCE R. LAMBERT ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE TERRENCE R. LAMBERT BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+ /*
+ * Derived from FreeBSD's mp_machdep.c
+ */
+ /*
+ * Copyright (c) 1996, by Steve Passe
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. The name of the developer may NOT be used to endorse or promote products
+ * derived from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ * $Id:$
+ */
+
+ /*
+ * The Intel MP-stuff is just one way of x386 SMP systems
+ * so only Intel MP specific stuff is here.
+ */
+
+ #include <sys/param.h>
+ #include <sys/systm.h>
+ #include <sys/kernel.h>
+ #include <sys/device.h>
+ #include <sys/malloc.h>
+
+ #include <vm/vm.h>
+ #include <vm/vm_param.h>
+ #include <vm/pmap.h>
+ #include <vm/vm_kern.h>
+ #include <vm/vm_extern.h>
+ #include <machine/specialreg.h>
+ #include <machine/cputypes.h>
+ #include <machine/cpuvar.h>
+ #include <machine/bus.h>
+ #include <machine/multiprocessor.h>
+ #include <machine/apic.h>
+ #include <machine/apicvar.h>
+ #include <dev/isa/isareg.h>
+
+ #include "locators.h"
+
+ /*
+ * imho this is dead. IS there any board that needs it ??
+ */
+ #define WARMBOOT_TARGET 0
+ #define WARMBOOT_OFF (KERNBASE + 0x0467)
+ #define WARMBOOT_SEG (KERNBASE + 0x0469)
+
+ #define BIOS_BASE (0xf0000)
+ #define BIOS_SIZE (0x10000)
+ #define BIOS_COUNT (BIOS_SIZE)
+
+ #define CMOS_REG (0x70)
+ #define CMOS_DATA (0x71)
+ #define BIOS_RESET (0x0f)
+ #define BIOS_WARM (0x0a)
+
+ #define PROCENTRY_FLAG_EN 0x01
+ #define PROCENTRY_FLAG_BP 0x02
+ #define IOAPICENTRY_FLAG_EN 0x01
+
+ static int itlmpsmatch __P((struct device *, struct cfdata *, void *));
+ static void itlmpsattach __P((struct device *, struct device *, void *));
+
+
+ struct cfattach itlmps_ca = {
+ sizeof(struct device), itlmpsmatch, itlmpsattach
+ };
+
+
+ /* MP Floating Pointer Structure */
+ typedef struct MPFPS {
+ char signature[4];
+ void *pap;
+ u_char length;
+ u_char spec_rev;
+ u_char checksum;
+ u_char mpfb1;
+ u_char mpfb2;
+ u_char mpfb3;
+ u_char mpfb4;
+ u_char mpfb5;
+ } *mpfps_t;
+
+ /* MP Configuration Table Header */
+ typedef struct MPCTH {
+ char signature[4];
+ u_short base_table_length;
+ u_char spec_rev;
+ u_char checksum;
+ u_char oem_id[8];
+ u_char product_id[12];
+ void *oem_table_pointer;
+ u_short oem_table_size;
+ u_short entry_count;
+ void *apic_address;
+ u_short extended_table_length;
+ u_char extended_table_checksum;
+ u_char reserved;
+ } *mpcth_t;
+
+
+ typedef struct PROCENTRY {
+ u_char type;
+ u_char apic_id;
+ u_char apic_version;
+ u_char cpu_flags;
+ u_long cpu_signature;
+ u_long feature_flags;
+ u_long reserved1;
+ u_long reserved2;
+ } *proc_entry_ptr;
+
+ typedef struct BUSENTRY {
+ u_char type;
+ u_char bus_id;
+ char bus_type[6];
+ } *bus_entry_ptr;
+
+ typedef struct IOAPICENTRY {
+ u_char type;
+ u_char apic_id;
+ u_char apic_version;
+ u_char apic_flags;
+ void *apic_address;
+ } *io_apic_entry_ptr;
+
+ static struct IOAPICENTRY default_io_apic = {
+ 2,0,1,IOAPICENTRY_FLAG_EN,(caddr_t)DEFAULT_IO_APIC_BASE
+ };
+
+ typedef struct INTENTRY {
+ u_char type;
+ u_char int_type;
+ u_short int_flags;
+ u_char src_bus_id;
+ u_char src_bus_irq;
+ u_char dst_apic_id;
+ u_char dst_apic_int;
+ } *int_entry_ptr;
+
+ /* descriptions of MP basetable entries */
+ typedef struct BASETABLE_ENTRY {
+ u_char type;
+ u_char length;
+ char name[16];
+ } basetable_entry;
+
+ struct mp_float_loc {
+ paddr_t loc;
+ size_t len;
+ int scan;
+ mpfps_t mpfps;
+ mpcth_t cth;
+
+ };
+
+ static int search_for_sig(caddr_t target, int count, struct mp_float_loc *);
+ static int imp_chksum(void *p,int len);
+
+ static char *scan2name[] = {
+ "???", "EBDA","basemem","BIOS"
+ };
+
+ static struct mp_float_loc loc = { 0, 0, 0};
+
+ int itlmps_verbose = 0;
+
+ static struct mp_info _mpi, *mpi = &_mpi;
+
+ int mp_print __P((void *, const char *));
+ int mp_match __P((struct device *,struct cfdata *,void *));
+ int itlmpscpustart __P((struct cpu_softc *));
+
+ struct cpu_functions itlmpsf = { itlmpscpustart, NULL };
+
+
+ int mp_probe(void);
+ extern char *vmmap;
+ int i386_mem_add_mapping __P((bus_addr_t, bus_size_t,
+ int, bus_space_handle_t *));
+
+ struct mp_info * mptable_scan(struct mp_float_loc *loc, struct device *);
+
+ static int
+ itlmpsmatch(parent, match, aux)
+ struct device *parent;
+ struct cfdata *match;
+ void *aux;
+ {
+ const char **name = (const char **)aux;
+
+ if (strcmp(*name, "itlmps"))
+ return 0;
+ return mp_probe();
+ }
+
+ int
+ mp_print(aux, pnp)
+ void *aux;
+ const char *pnp;
+ {
+ struct mp_attach_arg * maa = (struct mp_attach_arg *) aux;
+ char *what;
+ switch (maa->type) {
+ case MP_CPU: what = "cpu"; break;
+ case MP_IO_APIC: what = "apic"; break;
+ default: what = "unkown"; break;
+ }
+ if (pnp)
+ printf("%s at %s:",what, pnp);
+ return (UNCONF);
+ }
+
+ int
+ mp_match(parent, cf, aux)
+ struct device *parent;
+ struct cfdata *cf;
+ void *aux;
+ {
+ struct mp_attach_arg * maa = (struct mp_attach_arg *) aux;
+
+ if (cf->cf_loc[ITLMPSCF_ID] != ITLMPSCF_ID_DEFAULT &&
+ cf->cf_loc[ITLMPSCF_ID] != maa->id )
+ return 0;
+ return ((*cf->cf_attach->ca_match)(parent, cf, aux));
+ }
+
+ int
+ itlmpscpustart(struct cpu_softc *csc) {
+ int error;
+
+ if (csc->bp) {
+ extern u_char cpu_spinup_trampoline[],cpu_spinup_trampoline_end[];
+
+
+ /*
+ * Copy boot code
+ */
+ #if defined(PMAP_NEW)
+ pmap_kenter_pa((vaddr_t)MP_TRAMPOLINE, /* virtual */
+ (paddr_t)MP_TRAMPOLINE, /* physical */
+ VM_PROT_ALL); /* protection */
+ #else
+ pmap_enter(pmap_kernel(),
+ (vaddr_t)MP_TRAMPOLINE, /* virtual */
+ (paddr_t)MP_TRAMPOLINE, /* physical */
+ VM_PROT_ALL, /* protection */
+ TRUE); /* wired down */
+ #endif
+ memcpy((caddr_t)MP_TRAMPOLINE,
+ cpu_spinup_trampoline,
+ cpu_spinup_trampoline_end-cpu_spinup_trampoline);
+
+ /*
+ * Map local apic
+ */
+ pmap_enter(pmap_kernel(),(vaddr_t)&local_apic,mpi->cpu_apic_address,
+ VM_PROT_ALL, 1);
+ return 0;
+ } else if (csc->ap) {
+ if ((error = i386_init(csc->sc_cpuid)) != 0)
+ return error;
+
+ if ((error = i386_ipi(MP_TRAMPOLINE/NBPG,csc->sc_cpuid,
+ APIC_DELMODE_STARTUP)) != 0)
+ return error;
+ } else {
+ return 0;
+ }
+
+ return 0;
+ }
+
+
+ static void
+ itlmpsattach (parent, self, aux)
+ struct device *parent, *self;
+ void *aux;
+ {
+ printf (": Intel SMP specification (Rev. %d.%d)\n found at 0x%x in %s[%d]\n Board OEMId [%8.8s] ProdId [%8.8s]\n"
+ , loc.mpfps->spec_rev
+ , loc.cth->spec_rev
+ , (unsigned int)loc.loc
+ , scan2name[loc.scan]
+ , loc.len
+ , loc.cth->oem_id
+ , loc.cth->product_id);
+ mptable_scan(&loc, self);
+ }
+
+ /*
+ * Look for an Intel MP spec table (ie, SMP capable hardware).
+ * vmmap is initialized, but not used yet (no need for locking) .
+ */
+ int
+ mp_probe(void)
+ {
+ caddr_t ebda,memtop;
+
+ if (loc.scan != 0 ) {
+ return 1;
+ }
+
+
+ /* see if EBDA exists */
+ pmap_kenter_pa((vaddr_t)vmmap, 0,VM_PROT_READ);
+
+ ebda = (caddr_t) ((* (u_short *) ((vaddr_t)vmmap + 0x40e))<<4);
+ memtop = (caddr_t) ((* (u_short *) ((vaddr_t)vmmap + 0x413))<<10);
+
+ pmap_kremove((vaddr_t)vmmap, NBPG);
+
+ loc.scan = 1;
+
+ if (ebda && ebda <(caddr_t)IOM_BEGIN ) {
+ if (search_for_sig(ebda, 1024, &loc )) {
+ goto found;
+ }
+ }
+
+ loc.scan = 2;
+
+ if (memtop && memtop < (caddr_t)IOM_BEGIN ) {
+ if (search_for_sig(memtop - 1024, 1024, &loc)) {
+ goto found;
+ }
+ }
+
+ loc.scan = 3;
+
+ /* search the BIOS */
+ if (search_for_sig((caddr_t)BIOS_BASE, BIOS_COUNT, &loc))
+ goto found;
+
+ /* nothing found */
+
+ loc.mpfps = (mpfps_t)0;
+ return 0;
+
+ found:
+ /*
+ * found a MP float structure
+ * now map it
+ */
+ if (i386_mem_add_mapping(loc.loc, loc.len,BUS_SPACE_MAP_CACHEABLE,
+ (bus_space_handle_t *)&loc.mpfps)) {
+ printf ("can't map MP float structure\n");
+ return 0;
+ }
+ if(itlmps_verbose)
+ printf("found floating structure at %lx[%d] -> %p\n",loc.loc,loc.len,loc.mpfps);
+ if (loc.mpfps->pap) {
+ mpcth_t cth = loc.mpfps->pap;
+ pmap_kenter_pa((vaddr_t)vmmap,
+ i386_trunc_page(&(cth->base_table_length)), VM_PROT_READ);
+ cth = (mpcth_t) ((caddr_t)vmmap) + (((int)cth) &PGOFSET);
+
+ if(itlmps_verbose)
+ printf("Config table at %p[%d] -> %p\n",loc.mpfps->pap,cth->base_table_length,cth);
+ if (imp_chksum(loc.mpfps->pap, cth->base_table_length)) {
+ printf ("Warning: Configuration Table checksum error\n");
+ }
+ if (i386_trunc_page(loc.loc) == i386_trunc_page(loc.mpfps->pap)
+ && i386_trunc_page(loc.loc) == i386_trunc_page(((caddr_t)loc.mpfps->pap)
+ + cth->base_table_length)) {
+ loc.cth = (mpcth_t)((caddr_t)loc.mpfps + (int)(((caddr_t)loc.mpfps->pap) - loc.loc));
+ } else {
+ if (i386_mem_add_mapping((paddr_t)loc.mpfps->pap, cth->base_table_length,
+ BUS_SPACE_MAP_CACHEABLE, (bus_space_handle_t *)&loc.cth)) {
+ printf ("can't map MP Configuration structure\n");
+ return 0;
+ }
+ }
+ pmap_kremove((vaddr_t)vmmap, NBPG);
+ }
+
+ return 10;
+ }
+
+
+ /*
+ * look for the MP spec signature
+ */
+ static int
+ imp_chksum(void *vp,int len) {
+ unsigned char res=0;
+ char *p = (char *)vp;
+ unsigned int map = i386_trunc_page(p);
+ while(len--) {
+ if (i386_trunc_page(p) != map) {
+ pmap_kenter_pa((vaddr_t)vmmap, (map = i386_trunc_page(p)),VM_PROT_READ);
+ }
+ res += *(((char *)vmmap) + ((unsigned)p & PGOFSET));
+ p++;
+ }
+ return res;
+ }
+
+
+ /* string defined by the Intel MP Spec as identifying the MP table */
+ #define MP_SIG 0x5f504d5f /* _MP_ */
+ static int
+ search_for_sig(caddr_t target, int count, struct mp_float_loc *loc)
+ {
+ unsigned int map = ~0;
+ int *p = (int *)target,*end = (int *)(target + count-12);
+
+ for (p = 0; p < end; p++) {
+ if (i386_trunc_page(p) != map) {
+ pmap_kenter_pa((vaddr_t)vmmap,
+ (map = i386_trunc_page(p)),VM_PROT_READ);
+ }
+ if (*((int *)(((caddr_t)vmmap) + ((unsigned)p & PGOFSET))) == MP_SIG) {
+ /*
+ * enough space?
+ */
+ if ((end - p) >=16 ){
+ /*
+ * checksum ??
+ */
+ mpfps_t m = (mpfps_t)(vmmap + ((unsigned)p & PGOFSET));
+ if (i386_trunc_page(&(m->length)) != i386_trunc_page(m)) {
+ /*
+ *grmblle
+ */
+ pmap_kenter_pa((vaddr_t)vmmap,
+ (map = i386_trunc_page(&(m->length))),VM_PROT_READ);
+ m = (mpfps_t)(((char *)m) - NBPG);
+ }
+ if (!imp_chksum(p,m->length*16)) {
+ loc->loc = (paddr_t)p;
+ loc->len = m->length*16;
+ pmap_kremove((vaddr_t)vmmap, NBPG);
+ return 1;
+ }
+ }
+ }
+ }
+ pmap_kremove((vaddr_t)vmmap, NBPG);
+
+ return 0;
+ }
+
+
+ static basetable_entry basetable_entry_types[] =
+ {
+ {0, 20, "Processor"},
+ {1, 8, "Bus"},
+ {2, 8, "I/O APIC"},
+ {3, 8, "I/O INT"},
+ {4, 8, "Local INT"}
+ };
+
+ enum busTypes {
+ UNKNOWN_BUSTYPE = 0 ,
+ ISA,
+ EISA,
+ PCI,
+ CBUS,
+ CBUSII,
+ XPRESS
+ };
+
+ typedef struct BUSDATA {
+ u_char bus_id;
+ enum busTypes bus_type;
+ } bus_datum;
+
+ typedef struct INTDATA {
+ u_char int_type;
+ u_short int_flags;
+ u_char src_bus_id;
+ u_char src_bus_irq;
+ u_char dst_apic_id;
+ u_char dst_apic_int;
+ u_char int_vector;
+ } io_int, local_int;
+
+ typedef struct BUSTYPENAME {
+ u_char type;
+ char name[7];
+ } bus_type_name;
+
+ static bus_type_name bus_type_table[] =
+ {
+ {CBUS, "CBUS"},
+ {CBUSII, "CBUSII"},
+ {EISA, "EISA"},
+ {UNKNOWN_BUSTYPE, "---"},
+ {UNKNOWN_BUSTYPE, "---"},
+ {ISA, "ISA"},
+ {UNKNOWN_BUSTYPE, "---"},
+ {UNKNOWN_BUSTYPE, "---"},
+ {UNKNOWN_BUSTYPE, "---"},
+ {UNKNOWN_BUSTYPE, "---"},
+ {UNKNOWN_BUSTYPE, "---"},
+ {UNKNOWN_BUSTYPE, "---"},
+ {PCI, "PCI"},
+ {UNKNOWN_BUSTYPE, "---"},
+ {UNKNOWN_BUSTYPE, "---"},
+ {UNKNOWN_BUSTYPE, "---"},
+ {UNKNOWN_BUSTYPE, "---"},
+ {XPRESS, "XPRESS"},
+ {UNKNOWN_BUSTYPE, "---"}
+ };
+
+ #define MAX_BUSTYPE (sizeof(bus_type_table)/sizeof(bus_type_table[0]))
+
+ static int processor_entry __P((struct mp_info *,proc_entry_ptr entry,struct device *));
+ static int bus_entry __P((struct mp_info *,bus_entry_ptr entry,struct device *));
+ static int io_apic_entry __P((struct mp_info *,io_apic_entry_ptr entry,struct device *));
+ static int int_entry __P((struct mp_info *,int_entry_ptr entry));
+ static int lookup_bus_type __P((char *name));
+
+
+ /*
+ * 1st pass on motherboard's Intel MP specification table.
+ *
+ * initializes:
+ * mp_ncpus = 1
+ *
+ * determines:
+ * cpu_apic_address (common to all CPUs)
+ * io_apic_address[N]
+ * mp_naps
+ * mp_nbusses
+ * mp_napics
+ * nintrs
+ */
+ struct mp_info *
+ mptable_scan(struct mp_float_loc *loc, struct device *self)
+ {
+ mpcth_t cth;
+ int totalSize;
+ void* position;
+ int count;
+ int type;
+ static int done = 0;
+
+ if (done) {
+ printf("DONE???\n");
+ return mpi;
+ }
+
+ /* init everything to empty */
+ mpi->ncpus = 0;
+ mpi->boot_cpu_id = 0; /* we don't ned it anyway ... */
+ mpi->cpu_apic_address = 0;
+
+ /* record whether PIC or virtual-wire mode */
+ mpi->flags = (loc->mpfps->mpfb2 & 0x80) ? MP_PICMODE : 0;
+ if (itlmps_verbose) {
+ printf("MP mode %s\n",mpi->flags?"picmode":"virtual wire");
+ }
+
+
+ /* check for use of 'default' configuration */
+ if (loc->mpfps->mpfb1 != 0) {
+ struct PROCENTRY pe;
+ extern int cpu_id, cpu_feature;
+ /* use default addresses */
+ mpi->cpu_apic_address = DEFAULT_APIC_BASE;
+
+ pe.apic_id = 0;
+ pe.cpu_flags = PROCENTRY_FLAG_EN|PROCENTRY_FLAG_BP;
+ pe.cpu_signature = cpu_id;
+ pe.feature_flags = cpu_feature;
+
+ processor_entry(mpi, &pe, self);
+
+ pe.apic_id = 1;
+ pe.cpu_flags = PROCENTRY_FLAG_EN;
+
+ processor_entry(mpi, &pe, self);
+
+
+ io_apic_entry(mpi, &default_io_apic,self);
+
+ return mpi;
+ } else {
+ if (loc->mpfps->pap == 0) {
+ printf("MP Configuration Table Header MISSING!");
+ return NULL ;
+ }
+ cth = loc->cth;
+
+ mpi->cpu_apic_address = (paddr_t)cth->apic_address;
+
+ /* walk the table, recording info of interest */
+ totalSize = cth->base_table_length - sizeof(struct MPCTH);
+ position = (u_char *) cth + sizeof(struct MPCTH);
+ count = cth->entry_count;
+
+ while (count--) {
+ switch (type = *(u_char *) position) {
+ case 0: /* processor_entry */
+ processor_entry(mpi, position,self);
+ break;
+ case 1: /* bus_entry */
+ bus_entry(mpi, position, self);
+ break;
+ case 2: /* io_apic_entry */
+ io_apic_entry(mpi, position, self);
+ break;
+ case 3: /* int_entry */
+ int_entry(mpi, position);
+ break;
+ case 4: /* int_entry */
+ break;
+ default:
+ printf("mpfps Base Table HOSED!");
+ /* NOTREACHED */
+ return NULL;
+ }
+
+ totalSize -= basetable_entry_types[type].length;
+ (u_char*)position += basetable_entry_types[type].length;
+ }
+ }
+
+ return mpi ;
+ }
+
+ static int
+ processor_entry(struct mp_info *mpi, proc_entry_ptr entry,struct device *self)
+ {
+ struct cpu_attach_args caa;
+ if(itlmps_verbose) {
+ printf("Found CPU %d flags [%x]%s\n",
+ entry->apic_id,
+ entry->cpu_flags,
+ entry->cpu_flags & PROCENTRY_FLAG_BP?"BP":"AP");
+ }
+ /* check for usability */
+ if (!(entry->cpu_flags & PROCENTRY_FLAG_EN))
+ return 0;
+
+ /* check for BSP flag */
+ if (entry->cpu_flags & PROCENTRY_FLAG_BP) {
+ mpi->boot_cpu_id = entry->apic_id;
+ caa.bp = 1 ;
+ } else {
+ caa.ap = 1;
+ }
+
+ caa.type = MP_CPU;
+ caa.cpu_id = entry->apic_id;
+ caa.cpu_func = &itlmpsf;
+ caa.cpu_signature = entry->cpu_signature;
+ caa.feature_flags = entry->feature_flags;
+
+ config_found_sm(self, &caa, mp_print, mp_match);
+
+ mpi->cpu_mask |= 1<<entry->apic_id;
+ mpi->ncpus++;
+ return 1;
+ }
+
+
+ #define TAB_UNIT 4
+ #define TAB_ROUND(a) _TAB_ROUND(a, TAB_UNIT)
+
+ #define _TAB_ROUND(a,u) (((a) + (u - 1)) & ~(u-1))
+ #define EXTEND_TAB(a,u) (!(_TAB_ROUND(a,u) == _TAB_ROUND((a+1),u)))
+ static int
+ bus_entry(struct mp_info *mpi, bus_entry_ptr entry,struct device *self)
+ {
+ int x;
+ char c, name[8];
+ #if 0
+ struct bus_info *bus;
+ union mainbus_attach_args {
+ const char *mba_busname; /* first elem of all */
+ struct pcibus_attach_args mba_pba;
+ struct eisabus_attach_args mba_eba;
+ struct isabus_attach_args mba_iba;
+ } maa;
+ #endif
+
+
+ if(itlmps_verbose) {
+ printf("Found BUS %d type [%6.6s]\n",
+ entry->bus_id,
+ entry->bus_type);
+ }
+ /* encode the name into an index */
+ for (x = 0; x < 6; ++x) {
+ if ((c = entry->bus_type[x]) == ' ')
+ break;
+ name[x] = c;
+ }
+ name[x] = '\0';
+
+ if ((x = lookup_bus_type(name)) == UNKNOWN_BUSTYPE) {
+ printf("unknown bus type: '%s'", name);
+ return 0; /* ignore */
+ }
+ #if 0
+ switch (x->type) {
+ case PCI: if (pci_mode_detect() != 0) {
+ extern int pci_seen;
+ mba.mba_pba.pba_busname = "pci";
+ mba.mba_pba.pba_iot = I386_BUS_SPACE_IO;
+ mba.mba_pba.pba_memt = I386_BUS_SPACE_MEM;
+ mba.mba_pba.pba_dmat = &pci_bus_dma_tag;
+ mba.mba_pba.pba_flags = pci_bus_flags();
+ mba.mba_pba.pba_bus = entry->bus_id ; /* TODO fix busid's for bad bioses */
+ config_found(self, &mba.mba_pba, mp_print);
+ pci_seen = 1;
+ }
+ break;
+ case EISA: {
+ extern int eisa_has_been_seen;
+ if (memcmp(ISA_HOLE_VADDR(EISA_ID_PADDR), EISA_ID, EISA_ID_LEN) == 0 &&
+ eisa_has_been_seen == 0) {
+ mba.mba_eba.eba_busname = "eisa";
+ mba.mba_eba.eba_iot = I386_BUS_SPACE_IO;
+ mba.mba_eba.eba_memt = I386_BUS_SPACE_MEM;
+ #if NEISA > 0
+ mba.mba_eba.eba_dmat = &eisa_bus_dma_tag;
+ #endif
+ config_found(self, &mba.mba_eba, mp_print);
+ }
+ }
+ break;
+ case ISA: {
+ extern int isa_has_been_seen;
+ if (isa_has_been_seen == 0) {
+ mba.mba_iba.iba_busname = "isa";
+ mba.mba_iba.iba_iot = I386_BUS_SPACE_IO;
+ mba.mba_iba.iba_memt = I386_BUS_SPACE_MEM;
+ #if NISA > 0
+ mba.mba_iba.iba_dmat = &isa_bus_dma_tag;
+ #endif
+ config_found(self, &mba.mba_iba, mp_print);
+ }
+ }
+ break;
+ }
+ #endif
+
+ return 1;
+ }
+
+
+ static int
+ io_apic_entry(struct mp_info *mpi, io_apic_entry_ptr entry,struct device *self)
+ {
+ struct apic_attach_args aaa;
+ if(itlmps_verbose) {
+ printf("Found IO-APIC %d vers. %d flags [%x] at %p\n",
+ entry->apic_id,
+ entry->apic_version,
+ entry->apic_flags,
+ entry->apic_address);
+ }
+ /* encode the name into an index */
+ if (!(entry->apic_flags & IOAPICENTRY_FLAG_EN))
+ return 0;
+ aaa.type = MP_IO_APIC;
+ aaa.apic_id = entry->apic_id;
+ aaa.apic_version = entry->apic_version;
+ aaa.apic_address = (paddr_t)entry->apic_address;
+
+ config_found_sm(self, &aaa, mp_print, mp_match);
+
+ return 1;
+ }
+
+
+
+ static int
+ lookup_bus_type(char *name)
+ {
+ int x;
+
+ for (x = 0; x < MAX_BUSTYPE; ++x)
+ if (strcmp(bus_type_table[x].name, name) == 0)
+ return bus_type_table[x].type;
+
+ return UNKNOWN_BUSTYPE;
+ }
+
+
+ static char f2pol[] = "DHRL";
+ static char f2trg[] = "DERL";
+ static char t2t2[] = "INSE";
+
+ static int
+ int_entry(struct mp_info *mpi, int_entry_ptr entry)
+ {
+ struct intr_info *inti;
+ if(itlmps_verbose) {
+ printf("Found INTR entry APIC %d.#%d Bus %d.#%d %c%c%c\n",
+ entry->dst_apic_id,
+ entry->dst_apic_int,
+ entry->src_bus_id,
+ entry->src_bus_irq,
+ f2pol[entry->int_flags&3],
+ f2trg[(entry->int_flags<<2)&3],
+ t2t2[entry->int_type&3]);
+ }
+
+ if (EXTEND_TAB(mpi->nints, 16) ) {
+ struct intr_info *tmp;
+
+ MALLOC(tmp, struct intr_info *,
+ _TAB_ROUND(mpi->nints + 1, 16) * sizeof(*tmp),
+ M_DEVBUF, M_NOWAIT);
+ if (tmp == NULL) {
+ printf("Can't alloc table space for a %s\n","intr");
+ return 0;
+ }
+ memset(&tmp[_TAB_ROUND(mpi->nints,16)],
+ 0,
+ 16 * sizeof(*tmp));
+ if (mpi->ints) {
+ memcpy(tmp, mpi->ints, _TAB_ROUND(mpi->nints ,16)
+ * sizeof(*tmp));
+ FREE(mpi->ints, M_DEVBUF);
+ }
+ mpi->ints = tmp;
+ }
+
+ inti = &mpi->ints[mpi->nints++];
+
+ inti->type = entry->int_type;
+ inti->flags = entry->int_flags;
+ inti->bus_irq = entry->src_bus_irq;
+ inti->apic_int = entry->dst_apic_int;
+
+
+ return 1;
+ }
+
+
+ int
+ i386_init(target)
+ int target;
+ {
+ unsigned j;
+ if((target&APIC_DEST_MASK)==0) {
+ local_apic.icr_hi=(target<<24);
+ }
+
+ local_apic.icr_lo= (local_apic.icr_lo&APIC_RESV2_MASK)|
+ (target&APIC_DEST_MASK)|APIC_TRIGMOD_LEVEL|
+ APIC_LEVEL_ASSERT|APIC_DELMODE_INIT;
+ j=100000;
+ while(j--&&(local_apic.icr_lo&APIC_DELSTAT_PEND));
+
+ local_apic.icr_lo= (local_apic.icr_lo&APIC_RESV2_MASK)|
+ (target&APIC_DEST_MASK)|APIC_TRIGMOD_LEVEL|
+ APIC_LEVEL_DEASSERT|APIC_DELMODE_INIT;
+ j=100000;
+ delay(10000);
+ while(j--&&(local_apic.icr_lo&APIC_DELSTAT_PEND));
+
+ return (local_apic.icr_lo&APIC_DELSTAT_PEND)?EBUSY:0;
+ }
+
+ int
+ i386_ipi(vec,target,dl)
+ int vec,target,dl;
+ {
+ unsigned j;
+ if((target&APIC_DEST_MASK)==0) {
+ local_apic.icr_hi=(target<<24);
+ }
+ local_apic.icr_lo=(target&APIC_DEST_MASK)|(vec|dl)|APIC_LEVEL_ASSERT;
+ j=100000;
+ while(j--&&(local_apic.icr_lo&APIC_DELSTAT_PEND));
+ return (local_apic.icr_lo&APIC_DELSTAT_PEND)?EBUSY:0;
+ }
+
+
*** /dev/null Sun Jan 31 22:45:35 1999
--- ././i386/multiprocessor.s Tue Feb 2 12:58:53 1999
***************
*** 0 ****
--- 1,181 ----
+ /*
+ * Copyright (c) 1999 Stefan Grefen
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ * must display the following acknowledgement:
+ * This product includes software developed by Stefan Grefen.
+ * 4. The name Stefan Grefen may not be used to endorse or promote
+ * products derived from this software without specific prior written
+ * permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY TERRENCE R. LAMBERT ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE TERRENCE R. LAMBERT BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+ /*
+ * MP startup ...
+ * the stuff from cpu_spinup_trampoline to mp_startup
+ * is copied into the first 640 KB
+ * the script mps2h defines GETVALUES and assembles the whole stuff
+ * and than uses the listing to define values for the _TRMP_LABELs
+ * These are included in the real assembly run
+ * What we would like todo is #define _TRMP_LABEL as a expression
+ * label = . - _C_LABEL(cpu_spinup_trampoline) + MP_TRAMPOLINE, but
+ * gas can't handle it ... :-((
+ * This would eliminate the mps2sh script ...
+ */
+ #include "assym.h"
+ #include <machine/param.h>
+ #include <machine/asm.h>
+ #include <machine/specialreg.h>
+ #include <machine/segments.h>
+ #include <machine/multiprocessor.h>
+ #ifndef GETVALUES
+ #include "mp_tramp_values.h"
+ #endif
+
+ #define GDTE(a,b) .byte 0xff,0xff,0x0,0x0,0x0,a,b,0x0
+ #define _RELOC(x) ((x) - KERNBASE)
+ #define RELOC(x) _RELOC(_C_LABEL(x))
+
+ #ifdef GETVALUES
+ #define _TRMP_LABEL(a) a :
+ #else
+ #define _TRMP_LABEL(a)
+ #endif
+
+ #if 0
+ /*
+ * What we would like todo, but gas can't handle it ...
+ *
+ #define _TRMP_LABEL(a) a = . - _C_LABEL(cpu_spinup_trampoline) + MP_TRAMPOLINE
+ */
+ #endif
+
+ /*
+ * Debug code to stop the 2'nd processor in various stages based on the
+ * value in cpu_trace
+ */
+ #ifdef MP_DEBUG
+ #define HALT(x) 1: movl (%edi),%ebx;cmpl $ x,%ebx ; jle 1b ; movl %edi,%ebx; addl $4,%ebx; movl $ x,(%ebx)
+ #else
+ #define HALT(x) /**/
+ #endif
+
+ .text
+ #ifdef GETVALUES
+ .org MP_TRAMPOLINE
+ #endif
+ .align 4,0x0
+ .global _C_LABEL(cpu_spinup_trampoline),_C_LABEL(cpu_spinup_trampoline_end)
+ .global _C_LABEL(init386_ap), _C_LABEL(cpu_hatch)
+ .global _C_LABEL(SPTD), _C_LABEL(SPST)
+ .global _C_LABEL(gdt)
+
+ _C_LABEL(cpu_spinup_trampoline):
+ cli
+ xorl %eax,%eax
+ movl %ax, %ds
+ movl %ax, %es
+ movl %ax, %ss
+ aword
+ word
+ lgdt (gdt_desc) # load flat descriptor table
+ movl %cr0,%eax # get cr0
+ word
+ orl $0x1, %eax # enable protected mode
+ movl %eax, %cr0 # doit
+ movl $0x10, %eax # data segment
+ movl %ax, %ds
+ movl %ax, %ss
+ movl %ax, %es
+ movl %ax, %fs
+ movl %ax, %gs
+ word
+ ljmp $0x8, $mp_startup
+ _TRMP_LABEL(mp_startup)
+ movl $ (MP_TRAMPOLINE+NBPG-4),%esp # bootstrap stack end location
+ #ifdef MP_DEBUG
+ leal RELOC(cpu_trace),%edi
+ #endif
+ HALT(0)
+ /* First, reset the PSL. */
+ pushl $PSL_MBO
+ popfl
+ movl RELOC(SPTD),%esi # get page directory
+
+ /* Load base of page directory and enable mapping. */
+ movl %esi,%eax # phys address of ptd
+ movl %eax,%cr3 # load ptd addr into mmu
+ movl %cr0,%eax # get control word
+ # enable paging & NPX emulation
+ orl $(CR0_PE|CR0_PG|CR0_NE|CR0_TS|CR0_EM|CR0_MP|CR0_WP),%eax
+ movl %eax,%cr0 # and let's page NOW!
+ #ifdef MP_DEBUG
+ leal _C_LABEL(cpu_trace),%edi # bootstrap stack end location
+ #endif
+ HALT(1)
+ movw $((NGDT*8) - 1), ngdt_table # prepare segment descriptor
+ movl _C_LABEL(gdt), %eax # for real gdt
+ movl %eax, ngdt_table+2
+ lgdt ngdt_table
+ jmp 1f
+ nop
+ 1:
+ HALT(2)
+ movl $GSEL(GDATA_SEL, SEL_KPL),%eax #switch to new segment
+ movl %ax,%ds
+ movl %ax,%es
+ movl %ax,%ss
+ HALT(3)
+ pushl $GSEL(GCODE_SEL, SEL_KPL)
+ pushl $mp_cont
+ HALT(4)
+ lret
+ .align 4,0x0
+ _TRMP_LABEL(gdt_table)
+ .word 0x0,0x0,0x0,0x0 # null GDTE
+ GDTE(0x9f,0xcf) # Kernel text
+ GDTE(0x93,0xcf) # Kernel data
+ _TRMP_LABEL(gdt_desc)
+ .word 0x17 # limit 3 entrys
+ .long gdt_table # where is is gdt
+ _TRMP_LABEL(ngdt_table)
+ .long 0 # filled in after paging in enabled
+ .long 0
+ .align 4,0x0
+ _C_LABEL(cpu_spinup_trampoline_end): #end of code copied to MP_TRAMPOLINE
+ mp_cont:
+ movl _C_LABEL(SPST),%esp
+ call _C_LABEL(init386_ap)
+ HALT(0x010)
+ call _C_LABEL(cpu_hatch) # cpu is running now should never return
+ mps:
+ hlt
+ jmp mps
+ .global _C_LABEL(spurious_intr)
+ _C_LABEL(spurious_intr): # for APIC
+ iret
+ #ifdef MP_DEBUG
+ .data
+ .global _C_LABEL(cpu_trace)
+ _C_LABEL(cpu_trace):
+ .long 0x40
+ .long 0
+ #endif
*** /dev/null Sun Jan 31 22:45:35 1999
--- ././i386/cpu.c Tue Feb 2 12:58:16 1999
***************
*** 0 ****
--- 1,398 ----
+ /*
+ * Copyright (c) 1999 Stefan Grefen
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ * must display the following acknowledgement:
+ * This product includes software developed by Stefan Grefen.
+ * 4. The name Stefan Grefen may not be used to endorse or promote
+ * products derived from this software without specific prior written
+ * permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY TERRENCE R. LAMBERT ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE TERRENCE R. LAMBERT BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+
+ #include "opt_ddb.h"
+ #include <sys/param.h>
+ #include <sys/systm.h>
+ #include <sys/device.h>
+
+ #include <vm/vm.h>
+ #include <vm/vm_kern.h>
+ #include <vm/vm_page.h>
+
+ #if defined(UVM)
+ #include <uvm/uvm_extern.h>
+ #endif
+
+
+ #include <machine/apic.h>
+ #include <machine/cpu.h>
+ #include <machine/cpufunc.h>
+ #include <machine/cpuvar.h>
+ #include <machine/pmap.new.h>
+ #include <machine/vmparam.h>
+ #include <machine/multiprocessor.h>
+
+
+ int cpu_match __P((struct device *, struct cfdata *, void *));
+ void cpu_attach __P((struct device *, struct device *, void *));
+
+ void init386_ap __P((void));
+ void cpu_hatch __P((void));
+ int enable_local_apic __P((void));
+ void cpu_start __P((struct cpu_softc *sc));
+ void ap_cpu_callback __P((struct device *self));
+
+
+ int cpu_verbose = 0;
+
+
+ struct cfattach cpu_ca = {
+ sizeof(struct cpu_softc), cpu_match, cpu_attach
+ };
+
+ struct cpu_softc *cpus[16] = { 0 };
+ void identifycpu1(struct cpu_softc * );
+ extern union descriptor *idt, *gdt, *ldt,*pentium_idt;
+ extern int spurious_intr(void);
+ int boot_cpu = -1;
+
+ /*
+ * Needed by the bootstrap code
+ */
+ unsigned long SPTD;
+ caddr_t SPST;
+
+ /*
+ * enable local apic
+ */
+ int
+ enable_local_apic(void) {
+ local_apic.svr = 64 | APIC_SVR_ENABLE;
+ return 0;
+ }
+
+ int
+ cpu_match(parent, match, aux)
+ struct device *parent;
+ struct cfdata *match;
+ void *aux;
+ {
+ struct mp_attach_arg * maa = (struct mp_attach_arg *) aux;
+
+ if (maa->type == MP_CPU)
+ return 1;
+ return 0;
+ }
+
+ /*
+ * start an application processor (AP)
+ */
+ void
+ cpu_start(sc)
+ struct cpu_softc *sc;
+ {
+ int i;
+ unsigned long *rec_mem =
+ (unsigned long *)uvm_km_alloc(kernel_map, NBPG);
+
+ for (i =0 ; i < 1024; i++) {
+ rec_mem[i] = (i << 12) | PG_V | PG_RW;
+ }
+
+ /*
+ * double map 0-4MB v === phys
+ */
+ sc->sc_ptd->pm_pdir[0] = vtophys(rec_mem)| PG_V | PG_RW;
+
+ /*
+ * pass PTF and stack to boot code
+ */
+ SPTD = sc->sc_ptd->pm_pdirpa;
+ SPST = sc->sc_stack;
+
+ /*
+ * now startup the CPU
+ */
+ printf("{");
+ CPU_STARTUP(sc);
+
+ /*
+ * wait for it to become ready
+ */
+ i = 100000;
+ for (i = 100000; !(sc->sc_flags & CPU_RUNNING) && i>0;i--) {
+ delay(10);
+ }
+ /* Debugger(); */
+ printf ("}");
+ #ifdef MP_DEBUG
+ if (cpu_verbose)
+ {
+ extern int cpu_trace;
+ printf ("[%d,%d]",cpu_trace,(&cpu_trace)[1]);
+ }
+ #endif
+ /*
+ * unmap boot code
+ */
+ sc->sc_ptd->pm_pdir[0] = 0;
+
+ /*
+ * free tmp page_table
+ */
+ uvm_km_free(kernel_map, (vaddr_t) rec_mem, NBPG);
+ }
+
+ /*
+ * AP can only be started after the boot processor (BP) has
+ * been initialized. We call config_defer until the BP
+ * is initialized and this is the callback that
+ * starts the defered AP's
+ */
+ void
+ ap_cpu_callback(self)
+ struct device *self;
+ {
+ struct cpu_softc *sc = (struct cpu_softc *) self;
+
+ printf("%s: defered startup (",sc->sc_dev.dv_xname);
+ cpu_start(sc);
+ printf(") %srunning\n",sc->sc_flags & CPU_RUNNING?"":"not ");
+ if (sc->sc_flags & CPU_RUNNING)
+ identifycpu1(sc);
+ }
+
+ void
+ cpu_attach(parent, self, aux)
+ struct device *parent, *self;
+ void *aux;
+ {
+ struct cpu_softc *sc = (struct cpu_softc *)self;
+ struct cpu_attach_args *caa = (struct cpu_attach_args *) aux;
+
+ if (cpus[caa->cpu_id] == NULL) {
+ cpus[caa->cpu_id] = sc;
+ sc->sc_cpuid = caa->cpu_id;
+ sc->sc_cpu_type = caa->cpu_signature;
+ sc->sc_func = caa->cpu_func;
+ sc->feature_flags = caa->feature_flags;
+
+ /*
+ * create copy of kernel PTD
+ */
+ sc->sc_ptd = pmap_create();
+
+ /*
+ * Allocate private page
+ */
+ sc->sc_stack = ((caddr_t)uvm_km_alloc(kernel_map, NBPG)) + NBPG-4;
+
+ printf(": (");
+
+ if (caa->ap && boot_cpu == -1) {
+ /*
+ * can't start AP yet ...
+ */
+ sc->ap = 1;
+ printf("startup defered");
+ config_defer(self, ap_cpu_callback);
+ return;
+ }
+
+ /*
+ * start an AP
+ */
+ if (caa->ap) {
+ sc->ap = 1;
+ cpu_start(sc);
+ } else if (caa->bp) {
+ printf("bootprocessor");
+ boot_cpu = sc->sc_cpuid;
+ sc->sc_flags |= CPU_RUNNING;
+ sc->bp = 1;
+ /*
+ * this initializes the BP (apic mapping)
+ */
+ CPU_STARTUP(sc);
+
+ /*
+ * Enable local apic
+ */
+ setgate(&idt[64].gd, spurious_intr, 0,SDT_SYS386IGT, SEL_KPL);
+ enable_local_apic();
+ } else {
+ /*
+ * Single processor (not used yet)
+ * this is for eliminating identifycpu from machdep
+ */
+ printf("single processor");
+ sc->sc_flags |= CPU_RUNNING;
+ sc->sp = 1;
+ }
+ printf(") %srunning\n",sc->sc_flags & CPU_RUNNING?"":"not ");
+ if (sc->sc_flags & CPU_RUNNING)
+ identifycpu1(sc);
+ }
+ }
+
+ /*
+ * initialize an AP
+ * GDT is done in the boot code
+ * IDT is done here
+ */
+ void
+ init386_ap(void)
+ {
+ struct region_descriptor region;
+ /*
+ * gdt is loaded already
+ */
+ setregion(®ion, pentium_idt, NIDT * sizeof(idt[0]) - 1);
+ lidt(®ion);
+
+ //enable_local_apic();
+ }
+
+ /*
+ * for now the CPU ends up here when its ready to run
+ * for now it jumps into an etenrnal loop
+ */
+ void
+ cpu_hatch(void)
+ {
+ struct cpu_softc *sc = cpus[cpuid()];
+
+ if (sc) {
+ printf("CPU %d reports for duty",cpuid());
+ sc->sc_flags |= CPU_RUNNING;
+ while(1);
+ }
+ }
+
+
+ extern const char *modifiers[] ;
+
+ static struct cpu_cpuid_nameclass i386_cpuid_cpus[] = {
+ {
+ "GenuineIntel",
+ CPUVENDOR_INTEL,
+ "Intel",
+ /* Family 4 */
+ { {
+ CPUCLASS_486,
+ {
+ "486DX", "486DX", "486SX", "486DX2", "486SL",
+ "486SX2", 0, "486DX2 W/B Enhanced",
+ "486DX4", 0, 0, 0, 0, 0, 0, 0,
+ "486" /* Default */
+ },
+ NULL
+ },
+ /* Family 5 */
+ {
+ CPUCLASS_586,
+ {
+ 0, "Pentium", "Pentium (P54C)",
+ "Pentium (P24T)", "Pentium/MMX", "Pentium", 0,
+ "Pentium (P54C)", 0, 0, 0, 0, 0, 0, 0, 0,
+ "Pentium" /* Default */
+ },
+ NULL
+ },
+ /* Family 6 */
+ {
+ CPUCLASS_686,
+ {
+ 0, "Pentium Pro", 0, "Pentium II",
+ "Pentium Pro", "Pentium II", 0,
+ 0, 0, 0, 0, 0, 0, 0, 0, 0,
+ "Pentium Pro" /* Default */
+ },
+ NULL
+ } }
+ }
+ };
+
+ extern char *classnames[] ;
+
+ void
+ identifycpu1(sc)
+ struct cpu_softc *sc;
+ {
+ extern char cpu_vendor[];
+ const char *name, *modifier, *vendorname;
+ int class = CPUCLASS_386, vendor, i, max;
+ int family, model, step, modif;
+ struct cpu_cpuid_nameclass *cpup = NULL;
+ char cpu_model[120];
+
+
+
+ max = sizeof (i386_cpuid_cpus) / sizeof (i386_cpuid_cpus[0]);
+ modif = (sc->sc_cpu_type >> 12) & 3;
+ family = (sc->sc_cpu_type >> 8) & 15;
+ if (family < CPU_MINFAMILY)
+ printf("identifycpu: strange family value");
+ model = (sc->sc_cpu_type >> 4) & 15;
+ step = sc->sc_cpu_type & 15;
+ printf("%s: family %x model %x step %x\n", sc->sc_dev.dv_xname,
+ family, model,step);
+
+ for (i = 0; i < max; i++) {
+ if (!strncmp(cpu_vendor,
+ i386_cpuid_cpus[i].cpu_id, 12)) {
+ cpup = &i386_cpuid_cpus[i];
+ break;
+ }
+ }
+
+ if (cpup == NULL) {
+ vendor = CPUVENDOR_UNKNOWN;
+ if (cpu_vendor[0] != '\0')
+ vendorname = &cpu_vendor[0];
+ else
+ vendorname = "Unknown";
+ if (family > CPU_MAXFAMILY)
+ family = CPU_MAXFAMILY;
+ class = family - 3;
+ modifier = "";
+ name = "";
+ } else {
+ vendor = cpup->cpu_vendor;
+ vendorname = cpup->cpu_vendorname;
+ modifier = modifiers[modif];
+ if (family > CPU_MAXFAMILY) {
+ family = CPU_MAXFAMILY;
+ model = CPU_DEFMODEL;
+ } else if (model > CPU_MAXMODEL)
+ model = CPU_DEFMODEL;
+ i = family - CPU_MINFAMILY;
+ name = cpup->cpu_family[i].cpu_models[model];
+ if (name == NULL)
+ name = cpup->cpu_family[i].cpu_models[CPU_DEFMODEL];
+ class = cpup->cpu_family[i].cpu_class;
+ }
+
+ sprintf(cpu_model, "%s %s%s (%s-class)", vendorname, modifier, name,
+ classnames[class]);
+ printf("%s: %s\n", sc->sc_dev.dv_xname, cpu_model);
+ }
*** /dev/null Sun Jan 31 22:45:35 1999
--- ././i386/mps2h Tue Feb 2 12:56:25 1999
***************
*** 0 ****
--- 1,25 ----
+ #!/bin/sh
+ # Copyright (c) 1999 Stefan Grefen
+ #
+ cpp -DGETVALUES $*| as -al -R | \
+ awk 'BEGIN{start=0;bc=0;label="";}
+ /^[ ]*[1-9][0-9]?[0-9]? (([0-9a-f][0-9a-f][0-9a-f][0-9a-f])|( )) [0-9A-F].*/{
+ val=$3
+ if(length(val)==0) {
+ if(start==0)
+ next
+ val=$2
+ } else {
+ start=1
+ }
+ if (label != "" ) {
+ printf("#define %s 0x%s\n",label,$2);
+ label = "";
+ }
+ }
+ /^[ ]*[1-9][0-9]?[0-9]?/ && /_TRMP_LABEL[(][-_A-Za-z0-9][-_A-Za-z0-9]+[)]/ {
+ sub("_TRMP_LABEL","",$2);
+ gsub("[()]","",$2);
+ label = $2;
+ }'
+ rm -f a.out
*** /dev/null Sun Jan 31 22:45:35 1999
--- ././i386/apic.c Tue Feb 2 14:32:05 1999
***************
*** 0 ****
--- 1,158 ----
+ /*
+ * Copyright (c) 1999 Stefan Grefen
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ * must display the following acknowledgement:
+ * This product includes software developed by Stefan Grefen.
+ * 4. The name Stefan Grefen may not be used to endorse or promote
+ * products derived from this software without specific prior written
+ * permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY TERRENCE R. LAMBERT ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE TERRENCE R. LAMBERT BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+ #include "opt_ddb.h"
+ #include <sys/param.h>
+ #include <sys/systm.h>
+ #include <sys/device.h>
+
+ #include <vm/vm.h>
+ #include <vm/vm_kern.h>
+ #include <vm/vm_page.h>
+
+ #include <machine/bus.h>
+
+ #if defined(UVM)
+ #include <uvm/uvm_extern.h>
+ #endif
+
+
+ #include <machine/apic.h>
+ #include <machine/apicvar.h>
+ #include <machine/pmap.new.h>
+ #include <machine/multiprocessor.h>
+
+ /*
+ * maps an IO-apic
+ * TODO locking, export of interrupt functions
+ * and mapping of interrupts.
+ */
+
+ int apic_match __P((struct device *, struct cfdata *, void *));
+ void apic_attach __P((struct device *, struct device *, void *));
+
+ int i386_mem_add_mapping __P((bus_addr_t, bus_size_t,
+ int, bus_space_handle_t *));
+
+ int apic_verbose = 0;
+
+ static __inline unsigned int
+ read_apic(struct apic_softc *sc,int regid) {
+ /*
+ * todo lock apic
+ */
+ sc->sc_register->ioregsel = regid;
+ return sc->sc_register->iowin;
+ }
+
+ static __inline void
+ write_apic(struct apic_softc *sc,int regid, int val) {
+ /*
+ * todo lock apic
+ */
+ sc->sc_register->ioregsel = regid;
+ sc->sc_register->iowin = val;
+ }
+
+
+
+
+
+ struct cfattach apic_ca = {
+ sizeof(struct apic_softc), apic_match, apic_attach
+ };
+
+ struct apic_softc *apics[16] = { 0 };
+
+ int
+ apic_match(parent, match, aux)
+ struct device *parent;
+ struct cfdata *match;
+ void *aux;
+ {
+ struct mp_attach_arg * maa = (struct mp_attach_arg *) aux;
+
+ if (maa->type == MP_IO_APIC)
+ return 1;
+ return 0;
+ }
+
+ /*
+ * can't use bus_space_xxx as we don't have a bus handle ...
+ */
+ void
+ apic_attach(parent, self, aux)
+ struct device *parent, *self;
+ void *aux;
+ {
+ struct apic_softc *sc = (struct apic_softc *)self;
+ struct apic_attach_args *aaa = (struct apic_attach_args *) aux;
+
+ if (apics[aaa->apic_id] == NULL) {
+ int apic_id;
+ apics[aaa->apic_id] = sc;
+ sc->sc_apicid = aaa->apic_id;
+
+ printf(" at 0x%lx\n", aaa->apic_address);
+ if (i386_mem_add_mapping(aaa->apic_address,
+ NBPG,0,(bus_space_handle_t *)&sc->sc_register)) {
+ printf("can't map io_apic\n");
+ }
+
+ apic_id = (read_apic(sc,IOAPIC_ID)&APIC_ID_MASK)>>24;
+ printf("%s: io-apic id %d, vers %x\n",
+ sc->sc_dev.dv_xname,
+ apic_id,
+ read_apic(sc,IOAPIC_VER)&0xff);
+ /*
+ * in case the APIC is not initialized to the correct ID
+ * do it now, maye we should record the original ID
+ * for interrupt mapping later ...
+ */
+ if (apic_id != sc->sc_apicid) {
+ write_apic(sc,IOAPIC_VER,
+ (read_apic(sc,IOAPIC_ID)&~APIC_ID_MASK)
+ |(sc->sc_apicid<<24));
+
+ apic_id = (read_apic(sc,IOAPIC_ID)&APIC_ID_MASK)>>24;
+
+ if (apic_id != sc->sc_apicid) {
+ printf("%s: can't remap io-apic id to %d\n",
+ sc->sc_dev.dv_xname,
+ sc->sc_apicid);
+ } else {
+ printf("%s: remaped io-apic id to %d\n",
+ sc->sc_dev.dv_xname,
+ sc->sc_apicid);
+ }
+ }
+ }
+ }
+
*** /usr/sup/src/sys/arch/i386/./i386/machdep.c Fri Jan 29 13:15:47 1999
--- ././i386/machdep.c Tue Feb 2 15:12:35 1999
***************
*** 1876,1887 ****
--- 1876,1893 ----
}
#endif
+ #ifdef XXMP
+ /* Assuming bioscall .... */
+ avail_start = 4*NBPG; /* save us a page for trampoline code and
+ one additional PT page! */
+ #else
#if NBIOSCALL > 0
avail_start = 3*NBPG; /* save us a page for trampoline code and
one additional PT page! */
#else
avail_start = NBPG; /* BIOS leaves data in low memory */
/* and VM system doesn't work with phys 0 */
+ #endif
#endif
avail_end = IOM_END + trunc_page(biosextmem * 1024);
*** /usr/sup/src/sys/arch/i386/./i386/locore.s Wed Jan 27 13:13:56 1999
--- ././i386/locore.s Sun Jan 31 23:27:35 1999
***************
*** 233,238 ****
--- 233,240 ----
#ifdef I586_CPU
.globl _C_LABEL(idt)
#endif
+ .global _C_LABEL(local_apic)
+ _C_LABEL(local_apic): .space NBPG
_C_LABEL(cpu): .long 0 # are we 386, 386sx, or 486,
# or Pentium, or..
_C_LABEL(cpu_id): .long 0 # saved from `cpuid' instruction
*** /usr/sup/src/sys/arch/i386/./i386/mainbus.c Wed Aug 5 13:09:31 1998
--- ././i386/mainbus.c Sat Jan 30 21:45:51 1999
***************
*** 84,89 ****
--- 84,94 ----
int eisa_has_been_seen;
/*
+ * Same as above, but for PCI.
+ */
+ int pci_has_been_seen;
+
+ /*
* Probe for the mainbus; always succeeds.
*/
int
***************
*** 108,113 ****
--- 113,125 ----
printf("\n");
+ #ifdef XXMP
+ /*
+ * First check for Intel MP-structure
+ */
+ mba.mba_busname = "itlmps";
+ config_found(self, &mba.mba_aaa, mainbus_print);
+ #endif
/*
* XXX Note also that the presence of a PCI bus should
* XXX _always_ be checked, and if present the bus should be
*** /dev/null Sun Jan 31 22:45:35 1999
--- ././include/cpuvar.h Tue Feb 2 13:00:51 1999
***************
*** 0 ****
--- 1,114 ----
+ /*
+ * Copyright (c) 1999 Stefan Grefen
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ * must display the following acknowledgement:
+ * This product includes software developed by Stefan Grefen.
+ * 4. The name Stefan Grefen may not be used to endorse or promote
+ * products derived from this software without specific prior written
+ * permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY TERRENCE R. LAMBERT ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE TERRENCE R. LAMBERT BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+ #define CPU_STARTUP(_sc) ((_sc)->sc_func->start(_sc))
+ #define CPU_STOP(_sc) ((_sc)->sc_func->stop(_sc))
+
+ struct cpu_softc {
+ struct device sc_dev; /* generic device glue */
+ u_long sc_cpuid; /* CPU ID */
+ int sc_cpu_type; /* CPU type */
+ int sc_apic_version; /* APIC version */
+ caddr_t sc_idle_stack; /* our idle stack */
+ u_long sc_flags; /* flags; see below */
+ struct cpu_functions *sc_func; /* basic functions */
+ TAILQ_ENTRY(cpu_softc) sc_q; /* processing queue */
+ int bp:1;
+ int ap:1;
+ int sp:1;
+ int xx:29;
+ struct pmap *sc_ptd;
+ caddr_t sc_stack;
+ int feature_flags;
+ };
+
+ struct cpu_functions {
+ int (*start)(struct cpu_softc *);
+ int (*stop)(struct cpu_softc *);
+ };
+
+ struct cpu_attach_args {
+ int type;
+ int cpu_id;
+ int bp:1;
+ int ap:1;
+ int sp:1;
+ int xx:29;
+ struct cpu_functions *cpu_func;
+ int cpu_signature;
+ int feature_flags;
+ };
+
+ struct bus_info {
+ int bus_id;
+ struct bus_info *parent;
+ struct bus_info *next,*child;
+ int bus_type;
+ };
+
+ struct intr_info {
+ int type;
+ int flags;
+ struct bus_info *bus;
+ struct apic_info *apic;
+ int bus_irq;
+ int apic_int;
+ int cpu_class;
+ };
+ #define CPU_CLASS_ALL 0 /* All, the default */
+ #define CPU_CLASS_BSP 1 /* only the boot processor */
+
+ struct mp_info {
+ int ncpus; /* # of CPUs, including BSP */
+ int cpu_mask; /* Bit mask of availale CPU's */
+ int boot_cpu_id; /* designated BSP */
+ int flags; /* various flags */
+ int nints;
+ paddr_t cpu_apic_address;
+ struct intr_info *ints;
+ };
+
+ #define CPUF_PRIMARY 0x00000001 /* CPU is primary CPU */
+ #define CPUF_APIC_CD 0x00000002 /* CPU has apic configured */
+
+ #define MP_PICMODE 0x00000001 /* System booted in picmode */
+
+ #define CPU_RUNNING 0x00001000
+
+
+ #ifdef _KERNEL
+ extern unsigned long cpus_running;
+ extern struct cpu_softc *cpus[];
+ extern struct cpu_softc *primary_cpu;
+
+ int i386_ipi __P((int,int,int));
+ int i386_init __P((int));
+ #endif
+
*** /dev/null Sun Jan 31 22:45:35 1999
--- ././include/apic.h Tue Feb 2 13:00:21 1999
***************
*** 0 ****
--- 1,484 ----
+ /*
+ * Copyright (c) 1999 Stefan Grefen
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ * must display the following acknowledgement:
+ * This product includes software developed by Stefan Grefen.
+ * 4. The name Stefan Grefen may not be used to endorse or promote
+ * products derived from this software without specific prior written
+ * permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY TERRENCE R. LAMBERT ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE TERRENCE R. LAMBERT BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+ /*
+ * Imported to NetBSD by Stefan Grefen 1999
+ */
+ /*
+ * Copyright (c) 1996, by Peter Wemm and Steve Passe
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. The name of the developer may NOT be used to endorse or promote products
+ * derived from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ * $Id: apic.h,v 1.12 1998/09/06 22:41:40 tegge Exp $
+ */
+
+ #ifndef _MACHINE_APIC_H_
+ #define _MACHINE_APIC_H_
+
+ /*
+ * Local && I/O APIC definitions.
+ */
+
+ /*
+ * Pentium P54C+ Build-in APIC
+ * (Advanced programmable Interrupt Controller)
+ *
+ * Base Address of Build-in APIC in memory location
+ * is 0xfee00000.
+ *
+ * Map of APIC REgisters:
+ *
+ * Offset (hex) Description Read/Write state
+ * 000 Reserved
+ * 010 Reserved
+ * 020 ID Local APIC ID R/W
+ * 030 VER Local APIC Version R
+ * 040 Reserved
+ * 050 Reserved
+ * 060 Reserved
+ * 070 Reserved
+ * 080 Task Priority Register R/W
+ * 090 Arbitration Priority Register R
+ * 0A0 Processor Priority Register R
+ * 0B0 EOI Register W
+ * 0C0 RRR Remote read R
+ * 0D0 Logical Destination R/W
+ * 0E0 Destination Format Register 0..27 R; 28..31 R/W
+ * 0F0 SVR Spurious Interrupt Vector Reg. 0..3 R; 4..9 R/W
+ * 100 ISR 000-031 R
+ * 110 ISR 032-063 R
+ * 120 ISR 064-095 R
+ * 130 ISR 095-128 R
+ * 140 ISR 128-159 R
+ * 150 ISR 160-191 R
+ * 160 ISR 192-223 R
+ * 170 ISR 224-255 R
+ * 180 TMR 000-031 R
+ * 190 TMR 032-063 R
+ * 1A0 TMR 064-095 R
+ * 1B0 TMR 095-128 R
+ * 1C0 TMR 128-159 R
+ * 1D0 TMR 160-191 R
+ * 1E0 TMR 192-223 R
+ * 1F0 TMR 224-255 R
+ * 200 IRR 000-031 R
+ * 210 IRR 032-063 R
+ * 220 IRR 064-095 R
+ * 230 IRR 095-128 R
+ * 240 IRR 128-159 R
+ * 250 IRR 160-191 R
+ * 260 IRR 192-223 R
+ * 270 IRR 224-255 R
+ * 280 Error Status Register R
+ * 290 Reserved
+ * 2A0 Reserved
+ * 2B0 Reserved
+ * 2C0 Reserved
+ * 2D0 Reserved
+ * 2E0 Reserved
+ * 2F0 Reserved
+ * 300 ICR_LOW Interrupt Command Reg. (0-31) R/W
+ * 310 ICR_HI Interrupt Command Reg. (32-63) R/W
+ * 320 Local Vector Table (Timer) R/W
+ * 330 Reserved
+ * 340 Reserved
+ * 350 LVT1 Local Vector Table (LINT0) R/W
+ * 360 LVT2 Local Vector Table (LINT1) R/W
+ * 370 LVT3 Local Vector Table (ERROR) R/W
+ * 380 Initial Count Reg. for Timer R/W
+ * 390 Current Count of Timer R
+ * 3A0 Reserved
+ * 3B0 Reserved
+ * 3C0 Reserved
+ * 3D0 Reserved
+ * 3E0 Timer Divide Configuration Reg. R/W
+ * 3F0 Reserved
+ */
+
+
+ /******************************************************************************
+ * global defines, etc.
+ */
+
+
+ /******************************************************************************
+ * LOCAL APIC structure
+ */
+
+ #ifndef _LOCORE
+
+
+ #define PAD3 int : 32; int : 32; int : 32
+ #define PAD4 int : 32; int : 32; int : 32; int : 32
+
+ struct local_apic {
+ /* reserved */ PAD4;
+ /* reserved */ PAD4;
+ unsigned int dummy:24;unsigned int id:8; PAD3;
+ unsigned int version; PAD3;
+ /* reserved */ PAD4;
+ /* reserved */ PAD4;
+ /* reserved */ PAD4;
+ /* reserved */ PAD4;
+ unsigned int tpr; PAD3;
+ unsigned int apr; PAD3;
+ unsigned int ppr; PAD3;
+ unsigned int eoi; PAD3;
+ /* reserved */ PAD4;
+ unsigned int ldr; PAD3;
+ unsigned int dfr; PAD3;
+ unsigned int svr; PAD3;
+ unsigned int isr0; PAD3;
+ unsigned int isr1; PAD3;
+ unsigned int isr2; PAD3;
+ unsigned int isr3; PAD3;
+ unsigned int isr4; PAD3;
+ unsigned int isr5; PAD3;
+ unsigned int isr6; PAD3;
+ unsigned int isr7; PAD3;
+ unsigned int tmr0; PAD3;
+ unsigned int tmr1; PAD3;
+ unsigned int tmr2; PAD3;
+ unsigned int tmr3; PAD3;
+ unsigned int tmr4; PAD3;
+ unsigned int tmr5; PAD3;
+ unsigned int tmr6; PAD3;
+ unsigned int tmr7; PAD3;
+ unsigned int irr0; PAD3;
+ unsigned int irr1; PAD3;
+ unsigned int irr2; PAD3;
+ unsigned int irr3; PAD3;
+ unsigned int irr4; PAD3;
+ unsigned int irr5; PAD3;
+ unsigned int irr6; PAD3;
+ unsigned int irr7; PAD3;
+ unsigned int esr; PAD3;
+ /* reserved */ PAD4;
+ /* reserved */ PAD4;
+ /* reserved */ PAD4;
+ /* reserved */ PAD4;
+ /* reserved */ PAD4;
+ /* reserved */ PAD4;
+ /* reserved */ PAD4;
+ unsigned int icr_lo; PAD3;
+ unsigned int icr_hi; PAD3;
+ unsigned int lvt_timer; PAD3;
+ /* reserved */ PAD4;
+ unsigned int lvt_pcint; PAD3;
+ unsigned int lvt_lint0; PAD3;
+ unsigned int lvt_lint1; PAD3;
+ unsigned int lvt_error; PAD3;
+ unsigned int icr_timer; PAD3;
+ unsigned int ccr_timer; PAD3;
+ /* reserved */ PAD4;
+ /* reserved */ PAD4;
+ /* reserved */ PAD4;
+ /* reserved */ PAD4;
+ unsigned int dcr_timer; PAD3;
+ /* reserved */ PAD4;
+ };
+
+ /******************************************************************************
+ * I/O APIC structure
+ */
+
+ struct io_apic {
+ unsigned int ioregsel; PAD3;
+ unsigned int iowin; PAD3;
+ };
+
+ #undef PAD4
+ #undef PAD3
+
+ #endif /* !LOCORE */
+
+
+ /******************************************************************************
+ * various code 'logical' values
+ */
+
+ /* default level for TPR */
+ #define LOPRIO_LEVEL 0x00000010 /* TPR of CPU accepting INTs */
+
+ #ifdef GRAB_LOPRIO
+ #define ALLHWI_LEVEL 0x00000000 /* TPR of CPU grabbing INTs */
+ #endif /** GRAB_LOPRIO */
+
+
+ /******************************************************************************
+ * LOCAL APIC defines
+ */
+
+ /* default physical locations of LOCAL (CPU) APICs */
+ #define DEFAULT_APIC_BASE 0xfee00000
+
+ /* fields in VER */
+ #define APIC_VER_VERSION 0x000000ff
+ #define APIC_VER_MAXLVT 0x00ff0000
+ #define MAXLVTSHIFT 16
+
+ /* fields in SVR */
+ #define APIC_SVR_VECTOR 0x000000ff
+ #define APIC_SVR_VEC_PROG 0x000000f0
+ #define APIC_SVR_VEC_FIX 0x0000000f
+ #define APIC_SVR_ENABLE 0x00000100
+ # define APIC_SVR_SWDIS 0x00000000
+ # define APIC_SVR_SWEN 0x00000100
+ #define APIC_SVR_FOCUS 0x00000200
+ # define APIC_SVR_FEN 0x00000000
+ # define APIC_SVR_FDIS 0x00000200
+
+ /* fields in TPR */
+ #define APIC_TPR_PRIO 0x000000ff
+ # define APIC_TPR_INT 0x000000f0
+ # define APIC_TPR_SUB 0x0000000f
+
+
+ /* fields in ICR_LOW */
+ #define APIC_VECTOR_MASK 0x000000ff
+
+ #define APIC_DELMODE_MASK 0x00000700
+ # define APIC_DELMODE_FIXED 0x00000000
+ # define APIC_DELMODE_LOWPRIO 0x00000100
+ # define APIC_DELMODE_SMI 0x00000200
+ # define APIC_DELMODE_RR 0x00000300
+ # define APIC_DELMODE_NMI 0x00000400
+ # define APIC_DELMODE_INIT 0x00000500
+ # define APIC_DELMODE_STARTUP 0x00000600
+ # define APIC_DELMODE_RESV 0x00000700
+
+ #define APIC_DESTMODE_MASK 0x00000800
+ # define APIC_DESTMODE_PHY 0x00000000
+ # define APIC_DESTMODE_LOG 0x00000800
+
+ #define APIC_DELSTAT_MASK 0x00001000
+ # define APIC_DELSTAT_IDLE 0x00000000
+ # define APIC_DELSTAT_PEND 0x00001000
+
+ /* #define APIC_RESV1_MASK 0x00002000 */
+ #define APIC_POLARITY_MASK 0x00002000
+ # define APIC_POLARITY_HIGH 0x00000000
+ # define APIC_POLARITY_LOW 0x00000000
+
+ #define APIC_LEVEL_MASK 0x00004000
+ # define APIC_LEVEL_DEASSERT 0x00000000
+ # define APIC_LEVEL_ASSERT 0x00004000
+
+ #define APIC_TRIGMOD_MASK 0x00008000
+ # define APIC_TRIGMOD_EDGE 0x00000000
+ # define APIC_TRIGMOD_LEVEL 0x00008000
+
+ #define APIC_RRSTAT_MASK 0x00030000
+ # define APIC_RRSTAT_INVALID 0x00000000
+ # define APIC_RRSTAT_INPROG 0x00010000
+ # define APIC_RRSTAT_VALID 0x00020000
+ # define APIC_RRSTAT_RESV 0x00030000
+
+ #define APIC_DEST_MASK 0x000c0000
+ # define APIC_DEST_DESTFLD 0x00000000
+ # define APIC_DEST_SELF 0x00040000
+ # define APIC_DEST_ALLISELF 0x00080000
+ # define APIC_DEST_ALLESELF 0x000c0000
+
+ #define APIC_RESV2_MASK 0xfff00000
+
+
+ /* fields in ICR_HIGH */
+ #define APIC_ID_MASK 0x0f000000
+ #define APIC_ID_SHIFT 24
+
+ /* fields in LVT1/2 */
+ #define APIC_LVT_VECTOR 0x000000ff
+ #define APIC_LVT_DM 0x00000700
+ # define APIC_LVT_DM_FIXED 0x00000000
+ # define APIC_LVT_DM_NMI 0x00000400
+ # define APIC_LVT_DM_EXTINT 0x00000700
+ #define APIC_LVT_DS 0x00001000
+ #define APIC_LVT_IIPP 0x00002000
+ #define APIC_LVT_IIPP_INTALO 0x00002000
+ #define APIC_LVT_IIPP_INTAHI 0x00000000
+ #define APIC_LVT_RIRR 0x00004000
+ #define APIC_LVT_TM 0x00008000
+ #define APIC_LVT_M 0x00010000
+
+
+ /* fields in LVT Timer */
+ #define APIC_LVTT_VECTOR 0x000000ff
+ #define APIC_LVTT_DS 0x00001000
+ #define APIC_LVTT_M 0x00010000
+ #define APIC_LVTT_TM 0x00020000
+
+
+ /* fields in TDCR */
+ #define APIC_TDCR_2 0x00
+ #define APIC_TDCR_4 0x01
+ #define APIC_TDCR_8 0x02
+ #define APIC_TDCR_16 0x03
+ #define APIC_TDCR_32 0x08
+ #define APIC_TDCR_64 0x09
+ #define APIC_TDCR_128 0x0a
+ #define APIC_TDCR_1 0x0b
+
+
+ /*
+ * fields in IRR
+ * ISA INTerrupts are in bits 16-31 of the 1st IRR register.
+ * these masks DON'T EQUAL the isa IRQs of the same name.
+ */
+ #define APIC_IRQ0 0x00000001
+ #define APIC_IRQ1 0x00000002
+ #define APIC_IRQ2 0x00000004
+ #define APIC_IRQ3 0x00000008
+ #define APIC_IRQ4 0x00000010
+ #define APIC_IRQ5 0x00000020
+ #define APIC_IRQ6 0x00000040
+ #define APIC_IRQ7 0x00000080
+ #define APIC_IRQ8 0x00000100
+ #define APIC_IRQ9 0x00000200
+ #define APIC_IRQ10 0x00000400
+ #define APIC_IRQ11 0x00000800
+ #define APIC_IRQ12 0x00001000
+ #define APIC_IRQ13 0x00002000
+ #define APIC_IRQ14 0x00004000
+ #define APIC_IRQ15 0x00008000
+ #define APIC_IRQ16 0x00010000
+ #define APIC_IRQ17 0x00020000
+ #define APIC_IRQ18 0x00040000
+ #define APIC_IRQ19 0x00080000
+ #define APIC_IRQ20 0x00100000
+ #define APIC_IRQ21 0x00200000
+ #define APIC_IRQ22 0x00400000
+ #define APIC_IRQ23 0x00800000
+
+
+ /******************************************************************************
+ * I/O APIC defines
+ */
+
+ /* default physical locations of an IO APIC */
+ #define DEFAULT_IO_APIC_BASE 0xfec00000
+
+ /* window register offset */
+ #define IOAPIC_WINDOW 0x10
+
+ /* indexes into IO APIC */
+ #define IOAPIC_ID 0x00
+ #define IOAPIC_VER 0x01
+ #define IOAPIC_ARB 0x02
+ #define IOAPIC_REDTBL 0x10
+ #define IOAPIC_REDTBL0 IOAPIC_REDTBL
+ #define IOAPIC_REDTBL1 (IOAPIC_REDTBL+0x02)
+ #define IOAPIC_REDTBL2 (IOAPIC_REDTBL+0x04)
+ #define IOAPIC_REDTBL3 (IOAPIC_REDTBL+0x06)
+ #define IOAPIC_REDTBL4 (IOAPIC_REDTBL+0x08)
+ #define IOAPIC_REDTBL5 (IOAPIC_REDTBL+0x0a)
+ #define IOAPIC_REDTBL6 (IOAPIC_REDTBL+0x0c)
+ #define IOAPIC_REDTBL7 (IOAPIC_REDTBL+0x0e)
+ #define IOAPIC_REDTBL8 (IOAPIC_REDTBL+0x10)
+ #define IOAPIC_REDTBL9 (IOAPIC_REDTBL+0x12)
+ #define IOAPIC_REDTBL10 (IOAPIC_REDTBL+0x14)
+ #define IOAPIC_REDTBL11 (IOAPIC_REDTBL+0x16)
+ #define IOAPIC_REDTBL12 (IOAPIC_REDTBL+0x18)
+ #define IOAPIC_REDTBL13 (IOAPIC_REDTBL+0x1a)
+ #define IOAPIC_REDTBL14 (IOAPIC_REDTBL+0x1c)
+ #define IOAPIC_REDTBL15 (IOAPIC_REDTBL+0x1e)
+ #define IOAPIC_REDTBL16 (IOAPIC_REDTBL+0x20)
+ #define IOAPIC_REDTBL17 (IOAPIC_REDTBL+0x22)
+ #define IOAPIC_REDTBL18 (IOAPIC_REDTBL+0x24)
+ #define IOAPIC_REDTBL19 (IOAPIC_REDTBL+0x26)
+ #define IOAPIC_REDTBL20 (IOAPIC_REDTBL+0x28)
+ #define IOAPIC_REDTBL21 (IOAPIC_REDTBL+0x2a)
+ #define IOAPIC_REDTBL22 (IOAPIC_REDTBL+0x2c)
+ #define IOAPIC_REDTBL23 (IOAPIC_REDTBL+0x2e)
+
+ /* fields in VER */
+ #define IOART_VER_VERSION 0x000000ff
+ #define IOART_VER_MAXREDIR 0x00ff0000
+ #define MAXREDIRSHIFT 16
+
+ /*
+ * fields in the IO APIC's redirection table entries
+ */
+ #define IOART_DEST APIC_ID_MASK /* broadcast addr: all APICs */
+
+ #define IOART_RESV 0x00fe0000 /* reserved */
+
+ #define IOART_INTMASK 0x00010000 /* R/W: INTerrupt mask */
+ # define IOART_INTMCLR 0x00000000 /* clear, allow INTs */
+ # define IOART_INTMSET 0x00010000 /* set, inhibit INTs */
+
+ #define IOART_TRGRMOD 0x00008000 /* R/W: trigger mode */
+ # define IOART_TRGREDG 0x00000000 /* edge */
+ # define IOART_TRGRLVL 0x00008000 /* level */
+
+ #define IOART_REM_IRR 0x00004000 /* RO: remote IRR */
+
+ #define IOART_INTPOL 0x00002000 /* R/W: INT input pin polarity */
+ # define IOART_INTAHI 0x00000000 /* active high */
+ # define IOART_INTALO 0x00002000 /* active low */
+
+ #define IOART_DELIVS 0x00001000 /* RO: delivery status */
+
+ #define IOART_DESTMOD 0x00000800 /* R/W: destination mode */
+ # define IOART_DESTPHY 0x00000000 /* physical */
+ # define IOART_DESTLOG 0x00000800 /* logical */
+
+ #define IOART_DELMOD 0x00000700 /* R/W: delivery mode */
+ # define IOART_DELFIXED 0x00000000 /* fixed */
+ # define IOART_DELLOPRI 0x00000100 /* lowest priority */
+ # define IOART_DELSMI 0x00000200 /* System Management INT */
+ # define IOART_DELRSV1 0x00000300 /* reserved */
+ # define IOART_DELNMI 0x00000400 /* NMI signal */
+ # define IOART_DELINIT 0x00000500 /* INIT signal */
+ # define IOART_DELRSV2 0x00000600 /* reserved */
+ # define IOART_DELEXINT 0x00000700 /* External INTerrupt */
+
+ #define IOART_INTVEC 0x000000ff /* R/W: INTerrupt vector field */
+
+ #endif /* _MACHINE_APIC_H_ */
*** /dev/null Sun Jan 31 22:45:35 1999
--- ././include/multiprocessor.h Tue Feb 2 13:01:00 1999
***************
*** 0 ****
--- 1,54 ----
+ /*
+ * Copyright (c) 1999 Stefan Grefen
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ * must display the following acknowledgement:
+ * This product includes software developed by Stefan Grefen.
+ * 4. The name Stefan Grefen may not be used to endorse or promote
+ * products derived from this software without specific prior written
+ * permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY TERRENCE R. LAMBERT ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE TERRENCE R. LAMBERT BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+ #ifndef _MULTIPROCESSOR_H_
+ #define _MULTIPROCESSOR_H_
+ #define MP_TRAMPOLINE (3 * NBPG)
+
+ #ifndef _LOCORE
+ #include <machine/apic.h>
+
+ struct mp_attach_arg {
+ int type;
+ int id;
+ };
+
+ #define MP_CPU 1
+ #define MP_IO_APIC 2
+
+
+ #ifdef _KERNEL
+ extern struct local_apic local_apic;
+ #define cpuid() (local_apic.id)
+ #endif
+
+ #endif
+ #endif
+
*** /dev/null Sun Jan 31 22:45:35 1999
--- ././include/apicvar.h Tue Feb 2 13:00:43 1999
***************
*** 0 ****
--- 1,45 ----
+ /*
+ * Copyright (c) 1999 Stefan Grefen
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ * must display the following acknowledgement:
+ * This product includes software developed by Stefan Grefen.
+ * 4. The name Stefan Grefen may not be used to endorse or promote
+ * products derived from this software without specific prior written
+ * permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY TERRENCE R. LAMBERT ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE TERRENCE R. LAMBERT BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+ struct apic_attach_args {
+ int type;
+ int apic_id;
+ int apic_version;
+ int flags;
+ paddr_t apic_address;
+ };
+
+ struct apic_softc {
+ struct device sc_dev; /* generic device glue */
+ int sc_apicid;
+
+ struct io_apic *sc_register;
+ };
+
>Audit-Trail:
>Unformatted: