More merge and update.

(1) deleted #if 0

    pc98/pc98/mse.c

(2) hold per-unit I/O ports in ed_softc

    pc98/pc98/if_ed.c
    pc98/pc98/if_ed98.h

(3) merge more files by segregating changes into headers.

  new file (moved from pc98/pc98):

    i386/isa/aic_98.h

  deleted:

    well, it's already in the commit message so I won't repeat the
    long list here ;)

Submitted by:	The FreeBSD(98) Development Team
This commit is contained in:
Satoshi Asami 1996-10-30 22:41:46 +00:00
parent 75680b05c6
commit e30f001135
Notes: svn2git 2020-12-20 02:59:44 +00:00
svn path=/head/; revision=19269
114 changed files with 1166 additions and 28780 deletions

View File

@ -23,7 +23,7 @@
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
* $Id: prof_machdep.c,v 1.2 1996/04/08 16:41:06 wollman Exp $
* $Id: prof_machdep.c,v 1.3 1996/10/17 19:32:10 bde Exp $
*/
#ifdef GUPROF
@ -40,7 +40,11 @@
#include <machine/profile.h>
#endif
#ifdef PC98
#include <pc98/pc98/pc98.h>
#else
#include <i386/isa/isa.h>
#endif
#include <i386/isa/timerreg.h>
#ifdef GUPROF

View File

@ -38,7 +38,7 @@
*
* from: @(#)vm_machdep.c 7.3 (Berkeley) 5/13/91
* Utah $Hdr: vm_machdep.c 1.16.1.1 89/06/23$
* $Id: vm_machdep.c,v 1.69 1996/09/28 22:37:43 dyson Exp $
* $Id: vm_machdep.c,v 1.70 1996/10/15 03:16:33 dyson Exp $
*/
#include "npx.h"
@ -66,7 +66,11 @@
#include <sys/user.h>
#ifdef PC98
#include <pc98/pc98/pc98.h>
#else
#include <i386/isa/isa.h>
#endif
#ifdef BOUNCE_BUFFERS
static vm_offset_t
@ -90,7 +94,11 @@ static int bounceallocarraysize;
static unsigned *bounceallocarray;
static int bouncefree;
#if defined(PC98) && defined (EPSON_BOUNCEDMA)
#define SIXTEENMEG (3840*4096) /* 15MB boundary */
#else
#define SIXTEENMEG (4096*4096)
#endif
#define MAXBKVA 1024
int maxbkva = MAXBKVA*PAGE_SIZE;
@ -748,7 +756,7 @@ cpu_reset() {
* to do the reset here would then end up in no man's land.
*/
#ifndef BROKEN_KEYBOARD_RESET
#if !defined(BROKEN_KEYBOARD_RESET) && !defined(PC98)
outb(IO_KBD + 4, 0xFE);
DELAY(500000); /* wait 0.5 sec to see if that did it */
printf("Keyboard reset did not work, attempting CPU shutdown\n");
@ -761,6 +769,12 @@ cpu_reset() {
/* "good night, sweet prince .... <THUNK!>" */
invltlb();
/* NOTREACHED */
#ifdef PC98
asm(" cli ");
outb(0x37, 0x0f); /* SHUT 0 = 0 */
outb(0x37, 0x0b); /* SHUT 1 = 0 */
outb(0xf0, 0x00); /* reset port */
#endif
while(1);
}

View File

@ -3,7 +3,7 @@
* Garrett Wollman, September 1994.
* This file is in the public domain.
*
* $Id: clock.h,v 1.19 1996/10/17 17:31:25 bde Exp $
* $Id: clock.h,v 1.20 1996/10/25 13:01:08 bde Exp $
*/
#ifndef _MACHINE_CLOCK_H_
@ -65,7 +65,11 @@ int sysbeep __P((int pitch, int period));
#ifdef CLOCK_HAIR
#ifdef PC98
#include <pc98/pc98/pc98.h> /* XXX */
#else
#include <i386/isa/isa.h> /* XXX */
#endif
#include <i386/isa/timerreg.h> /* XXX */
static __inline u_int

View File

@ -31,7 +31,7 @@
* SUCH DAMAGE.
*
* from: Header: timerreg.h,v 1.2 93/02/28 15:08:58 mccanne Exp
* $Id$
* $Id: timerreg.h,v 1.2 1993/10/16 13:46:26 rgrimes Exp $
*/
/*
@ -59,6 +59,7 @@
* in undefined behavior (but hopefully not fry the chip).
* Reading in this manner has no side effects.
*
* [IBM-PC]
* The outputs of the three timers are connected as follows:
*
* timer 0 -> irq 0
@ -67,15 +68,31 @@
*
* Timer 0 is used to call hardclock.
* Timer 2 is used to generate console beeps.
*
* [PC-9801]
* The outputs of the three timers are connected as follows:
*
* timer 0 -> irq 0
* timer 1 -> speaker (via keyboard controller)
* timer 2 -> RS232C
*
* Timer 0 is used to call hardclock.
* Timer 1 is used to generate console beeps.
*/
/*
* Macros for specifying values to be written into a mode register.
*/
#define TIMER_CNTR0 (IO_TIMER1 + 0) /* timer 0 counter port */
#ifdef PC98
#define TIMER_CNTR1 0x3fdb /* timer 1 counter port */
#define TIMER_CNTR2 (IO_TIMER1 + 4) /* timer 2 counter port */
#define TIMER_MODE (IO_TIMER1 + 6) /* timer mode port */
#else
#define TIMER_CNTR1 (IO_TIMER1 + 1) /* timer 1 counter port */
#define TIMER_CNTR2 (IO_TIMER1 + 2) /* timer 2 counter port */
#define TIMER_MODE (IO_TIMER1 + 3) /* timer mode port */
#endif
#define TIMER_SEL0 0x00 /* select counter 0 */
#define TIMER_SEL1 0x40 /* select counter 1 */
#define TIMER_SEL2 0x80 /* select counter 2 */

View File

@ -1,12 +1,26 @@
/*
* from: vector.s, 386BSD 0.1 unknown origin
* $Id: vector.s,v 1.19 1996/04/11 21:18:47 bde Exp $
* $Id: vector.s,v 1.20 1996/05/31 01:08:08 peter Exp $
*/
/*
* modified for PC98 by Kakefuda
*/
#include "opt_auto_eoi.h"
#include <i386/isa/icu.h>
#ifdef PC98
#include <pc98/pc98/pc98.h>
#else
#include <i386/isa/isa.h>
#endif
#ifdef PC98
#define ICU_IMR_OFFSET 2 /* IO_ICU{1,2} + 2 */
#else
#define ICU_IMR_OFFSET 1 /* IO_ICU{1,2} + 1 */
#endif
#define ICU_EOI 0x20 /* XXX - define elsewhere */
@ -168,7 +182,7 @@ IDTVEC(vec_name) ; \
movb _imen + IRQ_BYTE(irq_num),%al ; \
orb $IRQ_BIT(irq_num),%al ; \
movb %al,_imen + IRQ_BYTE(irq_num) ; \
outb %al,$icu+1 ; \
outb %al,$icu+ICU_IMR_OFFSET ; \
enable_icus ; \
incl _cnt+V_INTR ; /* tally interrupts */ \
movl _cpl,%eax ; \
@ -190,7 +204,7 @@ __CONCAT(Xresume,irq_num): ; \
movb _imen + IRQ_BYTE(irq_num),%al ; \
andb $~IRQ_BIT(irq_num),%al ; \
movb %al,_imen + IRQ_BYTE(irq_num) ; \
outb %al,$icu+1 ; \
outb %al,$icu+ICU_IMR_OFFSET ; \
sti ; /* XXX _doreti repeats the cli/sti */ \
MEXITCOUNT ; \
/* We could usually avoid the following jmp by inlining some of */ \

View File

@ -1,12 +1,26 @@
/*
* from: vector.s, 386BSD 0.1 unknown origin
* $Id: vector.s,v 1.19 1996/04/11 21:18:47 bde Exp $
* $Id: vector.s,v 1.20 1996/05/31 01:08:08 peter Exp $
*/
/*
* modified for PC98 by Kakefuda
*/
#include "opt_auto_eoi.h"
#include <i386/isa/icu.h>
#ifdef PC98
#include <pc98/pc98/pc98.h>
#else
#include <i386/isa/isa.h>
#endif
#ifdef PC98
#define ICU_IMR_OFFSET 2 /* IO_ICU{1,2} + 2 */
#else
#define ICU_IMR_OFFSET 1 /* IO_ICU{1,2} + 1 */
#endif
#define ICU_EOI 0x20 /* XXX - define elsewhere */
@ -168,7 +182,7 @@ IDTVEC(vec_name) ; \
movb _imen + IRQ_BYTE(irq_num),%al ; \
orb $IRQ_BIT(irq_num),%al ; \
movb %al,_imen + IRQ_BYTE(irq_num) ; \
outb %al,$icu+1 ; \
outb %al,$icu+ICU_IMR_OFFSET ; \
enable_icus ; \
incl _cnt+V_INTR ; /* tally interrupts */ \
movl _cpl,%eax ; \
@ -190,7 +204,7 @@ __CONCAT(Xresume,irq_num): ; \
movb _imen + IRQ_BYTE(irq_num),%al ; \
andb $~IRQ_BIT(irq_num),%al ; \
movb %al,_imen + IRQ_BYTE(irq_num) ; \
outb %al,$icu+1 ; \
outb %al,$icu+ICU_IMR_OFFSET ; \
sti ; /* XXX _doreti repeats the cli/sti */ \
MEXITCOUNT ; \
/* We could usually avoid the following jmp by inlining some of */ \

View File

@ -1,6 +1,6 @@
/**************************************************************************
**
** $Id: pcibus.c,v 1.25 1996/06/13 21:50:41 se Exp $
** $Id: pcibus.c,v 1.26 1996/06/18 01:22:28 bde Exp $
**
** pci bus subroutines for i386 architecture.
**
@ -151,7 +151,11 @@ DATA_SET (pcibus_set, i386pci);
#define CONF1_ENABLE_RES1 0x80000000ul
#define CONF2_ENABLE_PORT 0x0cf8
#ifdef PC98
#define CONF2_FORWARD_PORT 0x0cf9
#else
#define CONF2_FORWARD_PORT 0x0cfa
#endif
#define CONF2_ENABLE_CHK 0x0e
#define CONF2_ENABLE_RES 0x0e

View File

@ -1,6 +1,6 @@
/**************************************************************************
**
** $Id: pcibus.c,v 1.25 1996/06/13 21:50:41 se Exp $
** $Id: pcibus.c,v 1.26 1996/06/18 01:22:28 bde Exp $
**
** pci bus subroutines for i386 architecture.
**
@ -151,7 +151,11 @@ DATA_SET (pcibus_set, i386pci);
#define CONF1_ENABLE_RES1 0x80000000ul
#define CONF2_ENABLE_PORT 0x0cf8
#ifdef PC98
#define CONF2_FORWARD_PORT 0x0cf9
#else
#define CONF2_FORWARD_PORT 0x0cfa
#endif
#define CONF2_ENABLE_CHK 0x0e
#define CONF2_ENABLE_RES 0x0e

View File

@ -3,7 +3,7 @@
#
# modified for PC-9801
#
# $Id: files.pc98,v 1.7 1996/09/12 11:09:18 asami Exp $
# $Id: files.pc98,v 1.8 1996/10/23 07:24:49 asami Exp $
#
aic7xxx_asm optional ahc device-driver \
dependency "$S/dev/aic7xxx/aic7xxx_asm.c" \
@ -43,7 +43,7 @@ i386/i386/db_disasm.c optional ddb
i386/i386/db_interface.c optional ddb
i386/i386/db_trace.c optional ddb
i386/i386/i386-gdbstub.c optional ddb
pc98/i386/exception.s standard
i386/i386/exception.s standard
i386/i386/identcpu.c standard
i386/i386/in_cksum.c optional inet
# locore.s needs to be handled in Makefile to put it first. Otherwise it's
@ -62,7 +62,7 @@ i386/i386/swtch.s standard
i386/i386/sys_machdep.c standard
pc98/i386/trap.c standard
pc98/i386/userconfig.c optional userconfig
pc98/i386/vm_machdep.c standard
i386/i386/vm_machdep.c standard
i386/ibcs2/ibcs2_fcntl.c optional ibcs2
i386/ibcs2/ibcs2_stat.c optional ibcs2
i386/ibcs2/ibcs2_ipc.c optional ibcs2
@ -89,7 +89,7 @@ pc98/pc98/bs/bshw.c optional bs device-driver
pc98/pc98/bs/bsif.c optional bs device-driver
pc98/pc98/sbic55.c optional sbic device-driver
#i386/pc98/aha1542.c optional aha device-driver
pc98/pc98/aic6360.c optional aic device-driver
i386/isa/aic6360.c optional aic device-driver
pc98/pc98/b004.c optional bqu device-driver
i386/pc98/bt742a.c optional bt device-driver
i386/pc98/bt5xx-445.c optional bt device-driver
@ -130,8 +130,8 @@ pc98/pc98/mse.c optional mse device-driver
pc98/isa/ncr5380.c optional nca device-driver
pc98/pc98/npx.c optional npx device-driver
pc98/pc98/pcaudio.c optional pca device-driver
pc98/pc98/matcd/matcd.c optional matcd device-driver
pc98/pc98/pcibus.c optional pci device-driver
i386/isa/matcd/matcd.c optional matcd device-driver
i386/isa/pcibus.c optional pci device-driver
i386/isa/pcicx.c optional ze device-driver
i386/isa/pcicx.c optional zp device-driver
pc98/isa/pcvt/pcvt_drv.c optional vt device-driver
@ -140,11 +140,11 @@ pc98/isa/pcvt/pcvt_kbd.c optional vt device-driver
pc98/isa/pcvt/pcvt_out.c optional vt device-driver
pc98/isa/pcvt/pcvt_sup.c optional vt device-driver
pc98/isa/pcvt/pcvt_vtf.c optional vt device-driver
pc98/pc98/prof_machdep.c optional profiling-routine
i386/isa/prof_machdep.c optional profiling-routine
pc98/pc98/psm.c optional psm device-driver
pc98/isa/qcam.c optional qcam device-driver
pc98/isa/qcamio.c optional qcam device-driver
pc98/pc98/random_machdep.c standard
i386/isa/random_machdep.c standard
pc98/isa/rc.c optional rc device-driver
i386/isa/scd.c optional scd device-driver
pc98/isa/seagate.c optional sea device-driver
@ -152,51 +152,51 @@ pc98/isa/si.c optional si device-driver
pc98/isa/si_code.c optional si device-driver
pc98/pc98/sio.c optional sio device-driver
pc98/pc98/sound/pcm86.c optional pcm device-driver
pc98/pc98/sound/dev_table.c optional snd device-driver
i386/isa/sound/dev_table.c optional snd device-driver
pc98/pc98/sound/soundcard.c optional snd device-driver
pc98/pc98/sound/sound_switch.c optional snd device-driver
pc98/pc98/sound/audio.c optional snd device-driver
pc98/pc98/sound/dmabuf.c optional snd device-driver
pc98/pc98/sound/sys_timer.c optional snd device-driver
pc98/pc98/sound/sequencer.c optional snd device-driver
pc98/pc98/sound/patmgr.c optional snd device-driver
pc98/pc98/sound/adlib_card.c optional opl device-driver
i386/isa/sound/audio.c optional snd device-driver
i386/isa/sound/dmabuf.c optional snd device-driver
i386/isa/sound/sys_timer.c optional snd device-driver
i386/isa/sound/sequencer.c optional snd device-driver
i386/isa/sound/patmgr.c optional snd device-driver
i386/isa/sound/adlib_card.c optional opl device-driver
pc98/pc98/sound/opl3.c optional opl device-driver
pc98/pc98/sound/gus_card.c optional gus device-driver
pc98/pc98/sound/gus_midi.c optional gus device-driver
pc98/pc98/sound/gus_vol.c optional gus device-driver
pc98/pc98/sound/gus_wave.c optional gus device-driver
pc98/pc98/sound/ics2101.c optional gus device-driver
pc98/pc98/sound/sound_timer.c optional gus device-driver
pc98/pc98/sound/midi_synth.c optional gus device-driver
pc98/pc98/sound/midibuf.c optional gus device-driver
i386/isa/sound/gus_card.c optional gus device-driver
i386/isa/sound/gus_midi.c optional gus device-driver
i386/isa/sound/gus_vol.c optional gus device-driver
i386/isa/sound/gus_wave.c optional gus device-driver
i386/isa/sound/ics2101.c optional gus device-driver
i386/isa/sound/sound_timer.c optional gus device-driver
i386/isa/sound/midi_synth.c optional gus device-driver
i386/isa/sound/midibuf.c optional gus device-driver
pc98/pc98/sound/ad1848.c optional gusxvi device-driver
pc98/pc98/sound/ad1848.c optional gus device-driver
pc98/pc98/sound/ad1848.c optional mss device-driver
pc98/pc98/sound/midi_synth.c optional mss device-driver
pc98/pc98/sound/midibuf.c optional mss device-driver
pc98/pc98/sound/mpu401.c optional mpu device-driver
pc98/pc98/sound/midi_synth.c optional mpu device-driver
pc98/pc98/sound/midibuf.c optional mpu device-driver
pc98/pc98/sound/pas2_card.c optional pas device-driver
pc98/pc98/sound/pas2_midi.c optional pas device-driver
pc98/pc98/sound/pas2_mixer.c optional pas device-driver
i386/isa/sound/midi_synth.c optional mss device-driver
i386/isa/sound/midibuf.c optional mss device-driver
i386/isa/sound/mpu401.c optional mpu device-driver
i386/isa/sound/midi_synth.c optional mpu device-driver
i386/isa/sound/midibuf.c optional mpu device-driver
i386/isa/sound/pas2_card.c optional pas device-driver
i386/isa/sound/pas2_midi.c optional pas device-driver
i386/isa/sound/pas2_mixer.c optional pas device-driver
pc98/pc98/sound/pas2_pcm.c optional pas device-driver
pc98/pc98/sound/midi_synth.c optional pas device-driver
pc98/pc98/sound/midibuf.c optional pas device-driver
pc98/pc98/sound/sb_card.c optional sb device-driver
i386/isa/sound/midi_synth.c optional pas device-driver
i386/isa/sound/midibuf.c optional pas device-driver
i386/isa/sound/sb_card.c optional sb device-driver
pc98/pc98/sound/sb_dsp.c optional sb device-driver
pc98/pc98/sound/sb_midi.c optional sb device-driver
pc98/pc98/sound/sb_mixer.c optional sb device-driver
pc98/pc98/sound/midi_synth.c optional sb device-driver
pc98/pc98/sound/midibuf.c optional sb device-driver
i386/isa/sound/sb_midi.c optional sb device-driver
i386/isa/sound/sb_mixer.c optional sb device-driver
i386/isa/sound/midi_synth.c optional sb device-driver
i386/isa/sound/midibuf.c optional sb device-driver
pc98/pc98/sound/sb16_dsp.c optional sbxvi device-driver
pc98/pc98/sound/sb16_midi.c optional sbmidi device-driver
pc98/pc98/sound/uart6850.c optional uart device-driver
pc98/pc98/sound/midi_synth.c optional uart device-driver
pc98/pc98/sound/midibuf.c optional uart device-driver
pc98/pc98/sound/trix.c optional trix device-driver
pc98/pc98/sound/sscape.c optional sscape device-driver
i386/isa/sound/uart6850.c optional uart device-driver
i386/isa/sound/midi_synth.c optional uart device-driver
i386/isa/sound/midibuf.c optional uart device-driver
i386/isa/sound/trix.c optional trix device-driver
i386/isa/sound/sscape.c optional sscape device-driver
pc98/isa/spigot.c optional spigot device-driver
pc98/pc98/spkr.c optional speaker device-driver
pc98/isa/stallion.c optional stl device-driver
@ -205,7 +205,7 @@ pc98/isa/tw.c optional tw device-driver
pc98/isa/ultra14f.c optional uha device-driver
pc98/pc98/wd.c optional wdc device-driver
pc98/pc98/wd.c optional wd device-driver
pc98/pc98/atapi.c optional atapi device-driver
i386/isa/atapi.c optional atapi device-driver
pc98/pc98/wcd.c optional wcd device-driver
pc98/isa/wd7000.c optional wds device-driver
pc98/pc98/wt.c optional wt device-driver

View File

@ -1,4 +1,4 @@
# $Id: options.pc98,v 1.6 1996/10/23 07:24:55 asami Exp $
# $Id: options.pc98,v 1.7 1996/10/29 08:36:14 asami Exp $
BOUNCEPAGES opt_bounce.h
USER_LDT
MATH_EMULATE opt_math_emulate.h
@ -29,6 +29,8 @@ XSERVER opt_pcvt.h
AHC_TAGENABLE opt_aic7xxx.h
AHC_SCBPAGING_ENABLE opt_aic7xxx.h
AHC_FORCE_PIO opt_aic7xxx.h
AHC_SHARE_SCBS opt_aic7xxx.h
CLK_CALIBRATION_LOOP opt_clock.h
CLK_USE_I8254_CALIBRATION opt_clock.h

View File

@ -25,11 +25,150 @@
* (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: kbdtables.h,v 1.30 1995/12/10 13:38:53 phk Exp $
* $Id: kbdtables.h,v 1.31 1996/01/25 16:37:20 ache Exp $
*/
#define SET8 0x80 /* set eight bit on */
#ifdef PC98
/* PC-9801 keymap by kuribo@isl.melco.co.jp */
static keymap_t key_map = { 0x80, /* PC98 keymap */
/* alt
* scan cntrl alt alt cntrl
* code base shift cntrl shift alt shift cntrl shift spcl flgs
* ---------------------------------------------------------------------------
*/
/* sc=00 */ 0x1B, 0x1B, 0x1B, 0x1B, 0x1B, 0x1B, DBG, 0x1B, 0x02, 0x00,
/* sc=01 */ '1', '!', '!', '!', '1', '!', '!', '!', 0x00, 0x00,
/* sc=02 */ '2', '\"', 0x1A, 0x1A, '2', '@', 0x00, 0x00, 0x00, 0x00,
/* sc=03 */ '3', '#', 0x1B, 0x1B, '3', '#', 0x1B, 0x1B, 0x00, 0x00,
/* sc=04 */ '4', '$', 0x1C, 0x1C, '4', '$', 0x1C, 0x1C, 0x00, 0x00,
/* sc=05 */ '5', '%', 0x1D, 0x1D, '5', '%', 0x1D, 0x1D, 0x00, 0x00,
/* sc=06 */ '6', '&', 0x1E, 0x1E, '6', '^', 0x1E, 0x1E, 0x00, 0x00,
/* sc=07 */ '7', '\'', 0x1F, 0x1F, '7', '&', '&', '&', 0x00, 0x00,
/* sc=08 */ '8', '(', 0x7F, 0x7F, '8', '*', 0x08, 0x08, 0x00, 0x00,
/* sc=09 */ '9', ')', '9', '9', '9', '(', '(', '(', 0x00, 0x00,
/* sc=0a */ '0', NOP, '0', '0', '0', ')', ')', ')', 0x40, 0x00,
/* sc=0b */ '-', '=', '-', '-', '-', '_', 0x1F, 0x1F, 0x00, 0x00,
/* sc=0c */ '^', '`', 0x1E, 0x1E, '=', '+', '+', '+', 0x00, 0x00,
/* sc=0d */ '\\', '|', 0x1C, 0x1C, '\\', '|', 0x1C, 0x1C, 0x00, 0x00,
/* sc=0e */ 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x00, 0x00,
/* sc=0f */ '\t', '\t', '\t', '\t', '\t', '\t', '\t', '\t', 0x00, 0x00,
/* sc=10 */ 'q', 'Q', 0x11, 0x11, 'q', 'Q', 0x11, 0x11, 0x00, 0x01,
/* sc=11 */ 'w', 'W', 0x17, 0x17, 'w', 'W', 0x17, 0x17, 0x00, 0x01,
/* sc=12 */ 'e', 'E', 0x05, 0x05, 'e', 'E', 0x05, 0x05, 0x00, 0x01,
/* sc=13 */ 'r', 'R', 0x12, 0x12, 'r', 'R', 0x12, 0x12, 0x00, 0x01,
/* sc=14 */ 't', 'T', 0x14, 0x14, 't', 'T', 0x14, 0x14, 0x00, 0x01,
/* sc=15 */ 'y', 'Y', 0x19, 0x19, 'y', 'Y', 0x19, 0x19, 0x00, 0x01,
/* sc=16 */ 'u', 'U', 0x15, 0x15, 'u', 'U', 0x15, 0x15, 0x00, 0x01,
/* sc=17 */ 'i', 'I', 0x09, 0x09, 'i', 'I', 0x09, 0x09, 0x00, 0x01,
/* sc=18 */ 'o', 'O', 0x0F, 0x0F, 'o', 'O', 0x0F, 0x0F, 0x00, 0x01,
/* sc=19 */ 'p', 'P', 0x10, 0x10, 'p', 'P', 0x10, 0x10, 0x00, 0x01,
/* sc=1a */ '@', '~', 0x00, 0x00, '[', '{', 0x1B, 0x1B, 0x00, 0x00,
/* sc=1b */ '[', '{', 0x1B, 0x1B, ']', '}', 0x1D, 0x1D, 0x00, 0x00,
/* sc=1c */ '\r', '\r', '\n', '\n', '\r', '\r', '\n', '\n', 0x00, 0x00,
/* sc=1d */ 'a', 'A', 0x01, 0x01, 'a', 'A', 0x01, 0x01, 0x00, 0x01,
/* sc=1e */ 's', 'S', 0x13, 0x13, 's', 'S', 0x13, 0x13, 0x00, 0x01,
/* sc=1f */ 'd', 'D', 0x04, 0x04, 'd', 'D', 0x04, 0x04, 0x00, 0x01,
/* sc=20 */ 'f', 'F', 0x06, 0x06, 'f', 'F', 0x06, 0x06, 0x00, 0x01,
/* sc=21 */ 'g', 'G', 0x07, 0x07, 'g', 'G', 0x07, 0x07, 0x00, 0x01,
/* sc=22 */ 'h', 'H', 0x08, 0x08, 'h', 'H', 0x08, 0x08, 0x00, 0x01,
/* sc=23 */ 'j', 'J', '\n', '\n', 'j', 'J', '\n', '\n', 0x00, 0x01,
/* sc=24 */ 'k', 'K', 0x0B, 0x0B, 'k', 'K', 0x0B, 0x0B, 0x00, 0x01,
/* sc=25 */ 'l', 'L', 0x0C, 0x0C, 'l', 'L', 0x0C, 0x0C, 0x00, 0x01,
/* sc=26 */ ';', '+', ';', ';', ';', ':', ';', ';', 0x00, 0x00,
/* sc=27 */ ':', '*', ':', ':', '\'', '\"', '\'', '\'', 0x00, 0x00,
/* sc=28 */ ']', '}', 0x1D, 0x1D, '`', '~', '~', '~', 0x00, 0x00,
/* sc=29 */ 'z', 'Z', 0x1A, 0x1A, 'z', 'Z', 0x1A, 0x1A, 0x00, 0x01,
/* sc=2a */ 'x', 'X', 0x18, 0x18, 'x', 'X', 0x18, 0x18, 0x00, 0x01,
/* sc=2b */ 'c', 'C', 0x03, 0x03, 'c', 'C', 0x03, 0x03, 0x00, 0x01,
/* sc=2c */ 'v', 'V', 0x16, 0x16, 'v', 'V', 0x16, 0x16, 0x00, 0x01,
/* sc=2d */ 'b', 'B', 0x02, 0x02, 'b', 'B', 0x02, 0x02, 0x00, 0x01,
/* sc=2e */ 'n', 'N', 0x0E, 0x0E, 'n', 'N', 0x0E, 0x0E, 0x00, 0x01,
/* sc=2f */ 'm', 'M', '\r', '\r', 'm', 'M', '\r', '\r', 0x00, 0x01,
/* sc=30 */ ',', '<', '<', '<', ',', '<', '<', '<', 0x00, 0x00,
/* sc=31 */ '.', '>', '>', '>', '.', '>', '>', '>', 0x00, 0x00,
/* sc=32 */ '/', '?', 0x7F, 0x7F, '/', '?', 0x7F, 0x7F, 0x00, 0x00,
/* sc=33 */ NOP, '_', 0x1F, 0x1F, '\\', '|', 0x1C, 0x1C, 0x80, 0x00,
/* sc=34 */ ' ', ' ', 0x00, 0x00, ' ', ' ', 0x00, 0x00, 0x00, 0x00,
/* sc=35 */ 0x1B, 0x1B, 0x1B, 0x1B, 0x1B, 0x1B, 0x1B, 0x1B, 0x00, 0x00,
/* sc=36 */ F(51), F(51), F(51), F(51), F(51), F(51), F(51), F(51), 0xFF, 0x00,
/* sc=37 */ F(59), F(59), F(59), F(59), F(59), F(59), F(59), F(59), 0xFF, 0x00,
/* sc=38 */ F(60), F(60), F(60), F(60), F(60), F(60), F(60), F(60), 0xFF, 0x00,
/* sc=39 */ 0x7F, 0x7F, 0x7F, 0x7F, 0x7F, 0x7F, RBT, RBT, 0x03, 0x02,
/* sc=3a */ F(50), F(50), F(50), F(50), F(50), F(50), F(50), F(50), 0xFF, 0x00,
/* sc=3b */ F(53), F(53), F(53), F(53), F(53), F(53), F(53), F(53), 0xFF, 0x00,
/* sc=3c */ F(55), F(55), F(55), F(55), F(55), F(55), F(55), F(55), 0xFF, 0x00,
/* sc=3d */ F(58), F(58), F(58), F(58), F(58), F(58), F(58), F(58), 0xFF, 0x00,
/* sc=3e */ F(49), F(49), F(49), F(49), F(49), F(49), F(49), F(49), 0xFF, 0x00,
/* sc=3f */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=40 */ '-', '-', '-', '-', '-', '-', '-', '-', 0x00, 0x00,
/* sc=41 */ '/', '/', '/', '/', '/', '/', '/', '/', 0x00, 0x00,
/* sc=42 */ '7', '7', '7', '7', '7', '7', '7', '7', 0x00, 0x00,
/* sc=43 */ '8', '8', '8', '8', '8', '8', '8', '8', 0x00, 0x00,
/* sc=44 */ '9', '9', '9', '9', '9', '9', '9', '9', 0x00, 0x00,
/* sc=45 */ '*', '*', '*', '*', '*', '*', '*', '*', 0x00, 0x00,
/* sc=46 */ '4', '4', '4', '4', '4', '4', '4', '4', 0x00, 0x00,
/* sc=47 */ '5', '5', '5', '5', '5', '5', '5', '5', 0x00, 0x00,
/* sc=48 */ '6', '6', '6', '6', '6', '6', '6', '6', 0x00, 0x00,
/* sc=49 */ '+', '+', '+', '+', '+', '+', '+', '+', 0x00, 0x00,
/* sc=4a */ '1', '1', '1', '1', '1', '1', '1', '1', 0x00, 0x00,
/* sc=4b */ '2', '2', '2', '2', '2', '2', '2', '2', 0x00, 0x00,
/* sc=4c */ '3', '3', '3', '3', '3', '3', '3', '3', 0x00, 0x00,
/* sc=4d */ '=', '=', '=', '=', '=', '=', '=', '=', 0x00, 0x00,
/* sc=4e */ '0', '0', '0', '0', '0', '0', '0', '0', 0x00, 0x00,
/* sc=4f */ ',', ',', ',', ',', ',', ',', ',', ',', 0x00, 0x00,
/* sc=50 */ '.', '.', '.', '.', '.', '.', '.', '.', 0x00, 0x00,
/* sc=51 */ 0x1B, 0x1B, 0x1B, 0x1B, 0x1B, 0x1B, 0x1B, 0x1B, 0x00, 0x00,
/* sc=52 */ F(11), F(23), F(35), F(47), S(11), S(11), S(11), S(11), 0xFF, 0x00,
/* sc=53 */ F(12), F(24), F(36), F(48), S(12), S(12), S(12), S(12), 0xFF, 0x00,
/* sc=54 */ SLK, SLK, SLK, SLK, SLK, SLK, SLK, SLK, 0xFF, 0x00,
/* sc=55 */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=56 */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=57 */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=58 */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=59 */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=5a */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=5b */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=5c */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=5d */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=5e */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=5f */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=60 */ F(57), F(57), F(57), F(57), F(57), F(57), F(57), F(57), 0xFF, 0x00,
/* sc=61 */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=62 */ F( 1), F(13), F(25), F(37), S( 1), S( 1), S( 1), S( 1), 0xFF, 0x00,
/* sc=63 */ F( 2), F(14), F(26), F(38), S( 2), S( 2), S( 2), S( 2), 0xFF, 0x00,
/* sc=64 */ F( 3), F(15), F(27), F(39), S( 3), S( 3), S( 3), S( 3), 0xFF, 0x00,
/* sc=65 */ F( 4), F(16), F(28), F(40), S( 4), S( 4), S( 4), S( 4), 0xFF, 0x00,
/* sc=66 */ F( 5), F(17), F(29), F(41), S( 5), S( 5), S( 5), S( 5), 0xFF, 0x00,
/* sc=67 */ F( 6), F(18), F(30), F(42), S( 6), S( 6), S( 6), S( 6), 0xFF, 0x00,
/* sc=68 */ F( 7), F(19), F(31), F(43), S( 7), S( 7), S( 7), S( 7), 0xFF, 0x00,
/* sc=69 */ F( 8), F(20), F(32), F(44), S( 8), S( 8), S( 8), S( 8), 0xFF, 0x00,
/* sc=6a */ F( 9), F(21), F(33), F(45), S( 9), S( 9), S( 9), S( 9), 0xFF, 0x00,
/* sc=6b */ F(10), F(22), F(34), F(46), S(10), S(10), S(10), S(10), 0xFF, 0x00,
/* sc=6c */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=6d */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=6e */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=6f */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=70 */ LSH, LSH, LSH, LSH, LSH, LSH, LSH, LSH, 0xFF, 0x00,
/* sc=71 */ CLK, CLK, CLK, CLK, CLK, CLK, CLK, CLK, 0xFF, 0x00,
/* sc=72 */ LALT, LALT, LALT, LALT, LALT, LALT, LALT, LALT, 0xFF, 0x00,
/* sc=73 */ LALT, LALT, LALT, LALT, LALT, LALT, LALT, LALT, 0xFF, 0x00,
/* sc=74 */ LCTR, LCTR, LCTR, LCTR, LCTR, LCTR, LCTR, LCTR, 0xFF, 0x00,
/* sc=75 */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=76 */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=77 */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=78 */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=79 */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=7a */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=7b */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=7c */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=7d */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=7e */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=7f */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
};
#endif
#ifdef DKKEYMAP
static keymap_t key_map = { 0x6C, /* DK iso8859 keymap */
/* alt
@ -750,7 +889,7 @@ static keymap_t key_map = { 0xEC, /* keys number */
#endif
#if !defined(DKKEYMAP) && !defined(UKKEYMAP) && !defined(GRKEYMAP) && !defined(SWKEYMAP) && !defined(RUKEYMAP)
#if !defined(DKKEYMAP) && !defined(UKKEYMAP) && !defined(GRKEYMAP) && !defined(SWKEYMAP) && !defined(RUKEYMAP) && !defined(PC98)
static keymap_t key_map = { 0x6C, /* US iso8859 keymap */
/* alt
* scan cntrl alt alt cntrl

View File

@ -38,7 +38,7 @@
*
* from: @(#)vm_machdep.c 7.3 (Berkeley) 5/13/91
* Utah $Hdr: vm_machdep.c 1.16.1.1 89/06/23$
* $Id: vm_machdep.c,v 1.69 1996/09/28 22:37:43 dyson Exp $
* $Id: vm_machdep.c,v 1.70 1996/10/15 03:16:33 dyson Exp $
*/
#include "npx.h"
@ -66,7 +66,11 @@
#include <sys/user.h>
#ifdef PC98
#include <pc98/pc98/pc98.h>
#else
#include <i386/isa/isa.h>
#endif
#ifdef BOUNCE_BUFFERS
static vm_offset_t
@ -90,7 +94,11 @@ static int bounceallocarraysize;
static unsigned *bounceallocarray;
static int bouncefree;
#if defined(PC98) && defined (EPSON_BOUNCEDMA)
#define SIXTEENMEG (3840*4096) /* 15MB boundary */
#else
#define SIXTEENMEG (4096*4096)
#endif
#define MAXBKVA 1024
int maxbkva = MAXBKVA*PAGE_SIZE;
@ -748,7 +756,7 @@ cpu_reset() {
* to do the reset here would then end up in no man's land.
*/
#ifndef BROKEN_KEYBOARD_RESET
#if !defined(BROKEN_KEYBOARD_RESET) && !defined(PC98)
outb(IO_KBD + 4, 0xFE);
DELAY(500000); /* wait 0.5 sec to see if that did it */
printf("Keyboard reset did not work, attempting CPU shutdown\n");
@ -761,6 +769,12 @@ cpu_reset() {
/* "good night, sweet prince .... <THUNK!>" */
invltlb();
/* NOTREACHED */
#ifdef PC98
asm(" cli ");
outb(0x37, 0x0f); /* SHUT 0 = 0 */
outb(0x37, 0x0b); /* SHUT 1 = 0 */
outb(0xf0, 0x00); /* reset port */
#endif
while(1);
}

View File

@ -3,7 +3,7 @@
* Garrett Wollman, September 1994.
* This file is in the public domain.
*
* $Id: clock.h,v 1.19 1996/10/17 17:31:25 bde Exp $
* $Id: clock.h,v 1.20 1996/10/25 13:01:08 bde Exp $
*/
#ifndef _MACHINE_CLOCK_H_
@ -65,7 +65,11 @@ int sysbeep __P((int pitch, int period));
#ifdef CLOCK_HAIR
#ifdef PC98
#include <pc98/pc98/pc98.h> /* XXX */
#else
#include <i386/isa/isa.h> /* XXX */
#endif
#include <i386/isa/timerreg.h> /* XXX */
static __inline u_int

View File

@ -31,7 +31,7 @@
*/
/*
* $Id: aic6360.c,v 1.22 1996/09/06 23:07:07 phk Exp $
* $Id: aic6360.c,v 1.23 1996/10/15 19:22:04 bde Exp $
*
* Acknowledgements: Many of the algorithms used in this driver are
* inspired by the work of Julian Elischer (julian@tfs.com) and
@ -47,6 +47,10 @@
* 4) Rewrite it to use malloc for the acb structs instead of static alloc.?
*/
/*
* PC-9801-100/AHA-1030P support by URATA S.
*/
/*
* A few customizable items:
*/
@ -183,6 +187,9 @@
#define ST_MASK 0x3e /* bit 0,6,7 is reserved */
/* AIC6360 definitions */
#ifdef PC98
#include <i386/isa/aic_98.h>
#else
#define SCSISEQ (iobase + 0x00) /* SCSI sequence control */
#define SXFRCTL0 (iobase + 0x01) /* SCSI transfer control 0 */
#define SXFRCTL1 (iobase + 0x02) /* SCSI transfer control 1 */
@ -222,6 +229,7 @@
#define STACK (iobase + 0x1d) /* Stack */
#define TEST (iobase + 0x1e) /* Test register */
#define ID (iobase + 0x1f) /* ID register */
#endif
#define IDSTRING "(C)1991ADAPTECAIC6360 "
@ -609,6 +617,9 @@ static struct aic_data { /* One of these per adapter */
u_char imess[AIC_MAX_MSG_LEN + 1];
u_char *imp; /* Message pointer (for multibyte messages) */
u_char imlen;
#ifdef PC98
int *aicport; /* I/O port information */
#endif
} *aicdata[NAIC];
#define AIC_SHOWACBS 0x01
@ -723,6 +734,15 @@ aicprobe(dev)
bzero(aic, sizeof(struct aic_data));
aicdata[unit] = aic;
aic->iobase = dev->id_iobase;
#ifdef PC98
if (AIC_TYPE98(dev->id_flags) == AIC98_100) {
/* PC-9801-100 */
aic->aicport = aicport_100;
} else {
/* generic card */
aic->aicport = aicport_generic;
}
#endif
if (aic_find(aic) != 0) {
aicdata[unit] = NULL;
@ -730,6 +750,11 @@ aicprobe(dev)
return 0;
}
aicunit++;
#ifdef PC98
if (AIC_TYPE98(dev->id_flags) == AIC98_100)
return 0x40;
#endif
return 0x20;
}

View File

@ -358,7 +358,12 @@ static struct atapi_params *atapi_probe (int port, int unit)
{
struct atapi_params *ap;
char tb [DEV_BSIZE];
#ifdef PC98
int cnt;
outb(0x432,unit%2);
print(("unit = %d,select %d\n",unit,unit%2));
#endif
/* Wait for controller not busy. */
outb (port + AR_DRIVE, unit ? ARD_DRIVE1 : ARD_DRIVE0);
if (atapi_wait (port, 0) < 0) {
@ -368,8 +373,20 @@ static struct atapi_params *atapi_probe (int port, int unit)
}
/* Issue ATAPI IDENTIFY command. */
#ifdef PC98
outb (port + AR_DRIVE, unit/2 ? ARD_DRIVE1 : ARD_DRIVE0);
/* Wait for DRQ deassert. */
for (cnt=2000; cnt>0; --cnt)
if (! (inb (0x640 + AR_STATUS) & ARS_DRQ))
break;
outb (port + AR_COMMAND, ATAPIC_IDENTIFY);
DELAY(500);
#else
outb (port + AR_DRIVE, unit ? ARD_DRIVE1 : ARD_DRIVE0);
outb (port + AR_COMMAND, ATAPIC_IDENTIFY);
#endif
/* Check that device is present. */
if (inb (port + AR_STATUS) == 0xff) {
@ -550,7 +567,13 @@ int atapi_start_cmd (struct atapi *ata, struct atapicmd *ac)
ac->result.error = 0;
ac->result.status = 0;
#ifdef PC98
outb(0x432,(ac->unit)%2);
print(("(ac->unit) = %d,select %d (2) \n",(ac->unit),(ac->unit)%2));
outb (ata->port + AR_DRIVE, (ac->unit)/2 ? ARD_DRIVE1 : ARD_DRIVE0);
#else
outb (ata->port + AR_DRIVE, ac->unit ? ARD_DRIVE1 : ARD_DRIVE0);
#endif
if (atapi_wait (ata->port, 0) < 0) {
printf ("atapi%d.%d: controller not ready for cmd\n",
ata->ctrlr, ac->unit);
@ -632,6 +655,11 @@ int atapi_intr (int ctrlr)
struct atapi *ata = atapitab + ctrlr;
struct atapicmd *ac = ata->queue;
#ifdef PC98
outb(0x432,(ac->unit)%2);
print(("atapi_intr:(ac->unit)= %d,select %d\n",ac->unit,(ac->unit)%2));
#endif
if (! ac) {
printf ("atapi%d: stray interrupt\n", ata->ctrlr);
return (0);

View File

@ -17,6 +17,18 @@
/*
* Disk Controller ATAPI register definitions.
*/
#ifdef PC98
#define AR_DATA 0x0 /* RW - data register (16 bits) */
#define AR_ERROR 0x2 /* R - error register */
#define AR_FEATURES 0x2 /* W - features */
#define AR_IREASON 0x4 /* RW - interrupt reason */
#define AR_TAG 0x6 /* - reserved for SAM TAG byte */
#define AR_CNTLO 0x8 /* RW - byte count, low byte */
#define AR_CNTHI 0xa /* RW - byte count, high byte */
#define AR_DRIVE 0xc /* RW - drive select */
#define AR_COMMAND 0xe /* W - command register */
#define AR_STATUS 0xe /* R - immediate status */
#else
#define AR_DATA 0x0 /* RW - data register (16 bits) */
#define AR_ERROR 0x1 /* R - error register */
#define AR_FEATURES 0x1 /* W - features */
@ -27,6 +39,7 @@
#define AR_DRIVE 0x6 /* RW - drive select */
#define AR_COMMAND 0x7 /* W - command register */
#define AR_STATUS 0x7 /* R - immediate status */
#endif
/*
* Status register bits

View File

@ -36,7 +36,7 @@
*
* @(#)icu.s 7.2 (Berkeley) 5/21/91
*
* $Id: icu.s,v 1.24 1996/03/12 05:44:25 nate Exp $
* $Id: icu.s,v 1.25 1996/05/31 01:08:07 peter Exp $
*/
/*
@ -278,6 +278,7 @@ vec0:
MEXITCOUNT
jmp _Xintr0 /* XXX might need _Xfastintr0 */
#ifndef PC98
ALIGN_TEXT
vec8:
popl %eax
@ -287,6 +288,7 @@ vec8:
cli
MEXITCOUNT
jmp _Xintr8 /* XXX might need _Xfastintr8 */
#endif
#define BUILD_VEC(irq_num) \
ALIGN_TEXT ; \
@ -301,6 +303,9 @@ __CONCAT(vec,irq_num): ; \
BUILD_VEC(5)
BUILD_VEC(6)
BUILD_VEC(7)
#ifdef PC98
BUILD_VEC(8)
#endif
BUILD_VEC(9)
BUILD_VEC(10)
BUILD_VEC(11)

View File

@ -25,11 +25,150 @@
* (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: kbdtables.h,v 1.30 1995/12/10 13:38:53 phk Exp $
* $Id: kbdtables.h,v 1.31 1996/01/25 16:37:20 ache Exp $
*/
#define SET8 0x80 /* set eight bit on */
#ifdef PC98
/* PC-9801 keymap by kuribo@isl.melco.co.jp */
static keymap_t key_map = { 0x80, /* PC98 keymap */
/* alt
* scan cntrl alt alt cntrl
* code base shift cntrl shift alt shift cntrl shift spcl flgs
* ---------------------------------------------------------------------------
*/
/* sc=00 */ 0x1B, 0x1B, 0x1B, 0x1B, 0x1B, 0x1B, DBG, 0x1B, 0x02, 0x00,
/* sc=01 */ '1', '!', '!', '!', '1', '!', '!', '!', 0x00, 0x00,
/* sc=02 */ '2', '\"', 0x1A, 0x1A, '2', '@', 0x00, 0x00, 0x00, 0x00,
/* sc=03 */ '3', '#', 0x1B, 0x1B, '3', '#', 0x1B, 0x1B, 0x00, 0x00,
/* sc=04 */ '4', '$', 0x1C, 0x1C, '4', '$', 0x1C, 0x1C, 0x00, 0x00,
/* sc=05 */ '5', '%', 0x1D, 0x1D, '5', '%', 0x1D, 0x1D, 0x00, 0x00,
/* sc=06 */ '6', '&', 0x1E, 0x1E, '6', '^', 0x1E, 0x1E, 0x00, 0x00,
/* sc=07 */ '7', '\'', 0x1F, 0x1F, '7', '&', '&', '&', 0x00, 0x00,
/* sc=08 */ '8', '(', 0x7F, 0x7F, '8', '*', 0x08, 0x08, 0x00, 0x00,
/* sc=09 */ '9', ')', '9', '9', '9', '(', '(', '(', 0x00, 0x00,
/* sc=0a */ '0', NOP, '0', '0', '0', ')', ')', ')', 0x40, 0x00,
/* sc=0b */ '-', '=', '-', '-', '-', '_', 0x1F, 0x1F, 0x00, 0x00,
/* sc=0c */ '^', '`', 0x1E, 0x1E, '=', '+', '+', '+', 0x00, 0x00,
/* sc=0d */ '\\', '|', 0x1C, 0x1C, '\\', '|', 0x1C, 0x1C, 0x00, 0x00,
/* sc=0e */ 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x00, 0x00,
/* sc=0f */ '\t', '\t', '\t', '\t', '\t', '\t', '\t', '\t', 0x00, 0x00,
/* sc=10 */ 'q', 'Q', 0x11, 0x11, 'q', 'Q', 0x11, 0x11, 0x00, 0x01,
/* sc=11 */ 'w', 'W', 0x17, 0x17, 'w', 'W', 0x17, 0x17, 0x00, 0x01,
/* sc=12 */ 'e', 'E', 0x05, 0x05, 'e', 'E', 0x05, 0x05, 0x00, 0x01,
/* sc=13 */ 'r', 'R', 0x12, 0x12, 'r', 'R', 0x12, 0x12, 0x00, 0x01,
/* sc=14 */ 't', 'T', 0x14, 0x14, 't', 'T', 0x14, 0x14, 0x00, 0x01,
/* sc=15 */ 'y', 'Y', 0x19, 0x19, 'y', 'Y', 0x19, 0x19, 0x00, 0x01,
/* sc=16 */ 'u', 'U', 0x15, 0x15, 'u', 'U', 0x15, 0x15, 0x00, 0x01,
/* sc=17 */ 'i', 'I', 0x09, 0x09, 'i', 'I', 0x09, 0x09, 0x00, 0x01,
/* sc=18 */ 'o', 'O', 0x0F, 0x0F, 'o', 'O', 0x0F, 0x0F, 0x00, 0x01,
/* sc=19 */ 'p', 'P', 0x10, 0x10, 'p', 'P', 0x10, 0x10, 0x00, 0x01,
/* sc=1a */ '@', '~', 0x00, 0x00, '[', '{', 0x1B, 0x1B, 0x00, 0x00,
/* sc=1b */ '[', '{', 0x1B, 0x1B, ']', '}', 0x1D, 0x1D, 0x00, 0x00,
/* sc=1c */ '\r', '\r', '\n', '\n', '\r', '\r', '\n', '\n', 0x00, 0x00,
/* sc=1d */ 'a', 'A', 0x01, 0x01, 'a', 'A', 0x01, 0x01, 0x00, 0x01,
/* sc=1e */ 's', 'S', 0x13, 0x13, 's', 'S', 0x13, 0x13, 0x00, 0x01,
/* sc=1f */ 'd', 'D', 0x04, 0x04, 'd', 'D', 0x04, 0x04, 0x00, 0x01,
/* sc=20 */ 'f', 'F', 0x06, 0x06, 'f', 'F', 0x06, 0x06, 0x00, 0x01,
/* sc=21 */ 'g', 'G', 0x07, 0x07, 'g', 'G', 0x07, 0x07, 0x00, 0x01,
/* sc=22 */ 'h', 'H', 0x08, 0x08, 'h', 'H', 0x08, 0x08, 0x00, 0x01,
/* sc=23 */ 'j', 'J', '\n', '\n', 'j', 'J', '\n', '\n', 0x00, 0x01,
/* sc=24 */ 'k', 'K', 0x0B, 0x0B, 'k', 'K', 0x0B, 0x0B, 0x00, 0x01,
/* sc=25 */ 'l', 'L', 0x0C, 0x0C, 'l', 'L', 0x0C, 0x0C, 0x00, 0x01,
/* sc=26 */ ';', '+', ';', ';', ';', ':', ';', ';', 0x00, 0x00,
/* sc=27 */ ':', '*', ':', ':', '\'', '\"', '\'', '\'', 0x00, 0x00,
/* sc=28 */ ']', '}', 0x1D, 0x1D, '`', '~', '~', '~', 0x00, 0x00,
/* sc=29 */ 'z', 'Z', 0x1A, 0x1A, 'z', 'Z', 0x1A, 0x1A, 0x00, 0x01,
/* sc=2a */ 'x', 'X', 0x18, 0x18, 'x', 'X', 0x18, 0x18, 0x00, 0x01,
/* sc=2b */ 'c', 'C', 0x03, 0x03, 'c', 'C', 0x03, 0x03, 0x00, 0x01,
/* sc=2c */ 'v', 'V', 0x16, 0x16, 'v', 'V', 0x16, 0x16, 0x00, 0x01,
/* sc=2d */ 'b', 'B', 0x02, 0x02, 'b', 'B', 0x02, 0x02, 0x00, 0x01,
/* sc=2e */ 'n', 'N', 0x0E, 0x0E, 'n', 'N', 0x0E, 0x0E, 0x00, 0x01,
/* sc=2f */ 'm', 'M', '\r', '\r', 'm', 'M', '\r', '\r', 0x00, 0x01,
/* sc=30 */ ',', '<', '<', '<', ',', '<', '<', '<', 0x00, 0x00,
/* sc=31 */ '.', '>', '>', '>', '.', '>', '>', '>', 0x00, 0x00,
/* sc=32 */ '/', '?', 0x7F, 0x7F, '/', '?', 0x7F, 0x7F, 0x00, 0x00,
/* sc=33 */ NOP, '_', 0x1F, 0x1F, '\\', '|', 0x1C, 0x1C, 0x80, 0x00,
/* sc=34 */ ' ', ' ', 0x00, 0x00, ' ', ' ', 0x00, 0x00, 0x00, 0x00,
/* sc=35 */ 0x1B, 0x1B, 0x1B, 0x1B, 0x1B, 0x1B, 0x1B, 0x1B, 0x00, 0x00,
/* sc=36 */ F(51), F(51), F(51), F(51), F(51), F(51), F(51), F(51), 0xFF, 0x00,
/* sc=37 */ F(59), F(59), F(59), F(59), F(59), F(59), F(59), F(59), 0xFF, 0x00,
/* sc=38 */ F(60), F(60), F(60), F(60), F(60), F(60), F(60), F(60), 0xFF, 0x00,
/* sc=39 */ 0x7F, 0x7F, 0x7F, 0x7F, 0x7F, 0x7F, RBT, RBT, 0x03, 0x02,
/* sc=3a */ F(50), F(50), F(50), F(50), F(50), F(50), F(50), F(50), 0xFF, 0x00,
/* sc=3b */ F(53), F(53), F(53), F(53), F(53), F(53), F(53), F(53), 0xFF, 0x00,
/* sc=3c */ F(55), F(55), F(55), F(55), F(55), F(55), F(55), F(55), 0xFF, 0x00,
/* sc=3d */ F(58), F(58), F(58), F(58), F(58), F(58), F(58), F(58), 0xFF, 0x00,
/* sc=3e */ F(49), F(49), F(49), F(49), F(49), F(49), F(49), F(49), 0xFF, 0x00,
/* sc=3f */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=40 */ '-', '-', '-', '-', '-', '-', '-', '-', 0x00, 0x00,
/* sc=41 */ '/', '/', '/', '/', '/', '/', '/', '/', 0x00, 0x00,
/* sc=42 */ '7', '7', '7', '7', '7', '7', '7', '7', 0x00, 0x00,
/* sc=43 */ '8', '8', '8', '8', '8', '8', '8', '8', 0x00, 0x00,
/* sc=44 */ '9', '9', '9', '9', '9', '9', '9', '9', 0x00, 0x00,
/* sc=45 */ '*', '*', '*', '*', '*', '*', '*', '*', 0x00, 0x00,
/* sc=46 */ '4', '4', '4', '4', '4', '4', '4', '4', 0x00, 0x00,
/* sc=47 */ '5', '5', '5', '5', '5', '5', '5', '5', 0x00, 0x00,
/* sc=48 */ '6', '6', '6', '6', '6', '6', '6', '6', 0x00, 0x00,
/* sc=49 */ '+', '+', '+', '+', '+', '+', '+', '+', 0x00, 0x00,
/* sc=4a */ '1', '1', '1', '1', '1', '1', '1', '1', 0x00, 0x00,
/* sc=4b */ '2', '2', '2', '2', '2', '2', '2', '2', 0x00, 0x00,
/* sc=4c */ '3', '3', '3', '3', '3', '3', '3', '3', 0x00, 0x00,
/* sc=4d */ '=', '=', '=', '=', '=', '=', '=', '=', 0x00, 0x00,
/* sc=4e */ '0', '0', '0', '0', '0', '0', '0', '0', 0x00, 0x00,
/* sc=4f */ ',', ',', ',', ',', ',', ',', ',', ',', 0x00, 0x00,
/* sc=50 */ '.', '.', '.', '.', '.', '.', '.', '.', 0x00, 0x00,
/* sc=51 */ 0x1B, 0x1B, 0x1B, 0x1B, 0x1B, 0x1B, 0x1B, 0x1B, 0x00, 0x00,
/* sc=52 */ F(11), F(23), F(35), F(47), S(11), S(11), S(11), S(11), 0xFF, 0x00,
/* sc=53 */ F(12), F(24), F(36), F(48), S(12), S(12), S(12), S(12), 0xFF, 0x00,
/* sc=54 */ SLK, SLK, SLK, SLK, SLK, SLK, SLK, SLK, 0xFF, 0x00,
/* sc=55 */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=56 */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=57 */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=58 */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=59 */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=5a */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=5b */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=5c */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=5d */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=5e */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=5f */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=60 */ F(57), F(57), F(57), F(57), F(57), F(57), F(57), F(57), 0xFF, 0x00,
/* sc=61 */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=62 */ F( 1), F(13), F(25), F(37), S( 1), S( 1), S( 1), S( 1), 0xFF, 0x00,
/* sc=63 */ F( 2), F(14), F(26), F(38), S( 2), S( 2), S( 2), S( 2), 0xFF, 0x00,
/* sc=64 */ F( 3), F(15), F(27), F(39), S( 3), S( 3), S( 3), S( 3), 0xFF, 0x00,
/* sc=65 */ F( 4), F(16), F(28), F(40), S( 4), S( 4), S( 4), S( 4), 0xFF, 0x00,
/* sc=66 */ F( 5), F(17), F(29), F(41), S( 5), S( 5), S( 5), S( 5), 0xFF, 0x00,
/* sc=67 */ F( 6), F(18), F(30), F(42), S( 6), S( 6), S( 6), S( 6), 0xFF, 0x00,
/* sc=68 */ F( 7), F(19), F(31), F(43), S( 7), S( 7), S( 7), S( 7), 0xFF, 0x00,
/* sc=69 */ F( 8), F(20), F(32), F(44), S( 8), S( 8), S( 8), S( 8), 0xFF, 0x00,
/* sc=6a */ F( 9), F(21), F(33), F(45), S( 9), S( 9), S( 9), S( 9), 0xFF, 0x00,
/* sc=6b */ F(10), F(22), F(34), F(46), S(10), S(10), S(10), S(10), 0xFF, 0x00,
/* sc=6c */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=6d */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=6e */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=6f */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=70 */ LSH, LSH, LSH, LSH, LSH, LSH, LSH, LSH, 0xFF, 0x00,
/* sc=71 */ CLK, CLK, CLK, CLK, CLK, CLK, CLK, CLK, 0xFF, 0x00,
/* sc=72 */ LALT, LALT, LALT, LALT, LALT, LALT, LALT, LALT, 0xFF, 0x00,
/* sc=73 */ LALT, LALT, LALT, LALT, LALT, LALT, LALT, LALT, 0xFF, 0x00,
/* sc=74 */ LCTR, LCTR, LCTR, LCTR, LCTR, LCTR, LCTR, LCTR, 0xFF, 0x00,
/* sc=75 */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=76 */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=77 */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=78 */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=79 */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=7a */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=7b */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=7c */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=7d */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=7e */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=7f */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
};
#endif
#ifdef DKKEYMAP
static keymap_t key_map = { 0x6C, /* DK iso8859 keymap */
/* alt
@ -750,7 +889,7 @@ static keymap_t key_map = { 0xEC, /* keys number */
#endif
#if !defined(DKKEYMAP) && !defined(UKKEYMAP) && !defined(GRKEYMAP) && !defined(SWKEYMAP) && !defined(RUKEYMAP)
#if !defined(DKKEYMAP) && !defined(UKKEYMAP) && !defined(GRKEYMAP) && !defined(SWKEYMAP) && !defined(RUKEYMAP) && !defined(PC98)
static keymap_t key_map = { 0x6C, /* US iso8859 keymap */
/* alt
* scan cntrl alt alt cntrl

View File

@ -98,13 +98,20 @@ See matcd.c for Edit History
#define CMD 0 /*Write - commands*/
#define DATA 0 /*Read - data/status from drive*/
#ifdef PC98
#define PHASE 0x100 /*Write - switch between data/status*/
#define STATUS 0x100 /*Read - bus status */
#define RESET 0x200 /*Write - reset all attached drives*/
#define ALTDATA 0x200 /*<20>Read - data on non Creative bds.*/
#define SELECT 0x300 /*Write - drive select*/
#else /* !PC98 */
#define PHASE 1 /*Write - switch between data/status*/
#define STATUS 1 /*Read - bus status*/
#define RESET 2 /*Write - reset all attached drives*/
/*Any value written will reset*/
#define ALTDATA 2 /*<20>Read - data on non Creative bds.*/
#define SELECT 3 /*Write - drive select*/
#endif /*PC98*/
/* Creative PHASE port bit assignments
*/

View File

@ -184,6 +184,16 @@
#ifdef AUTOHUNT
static int port_hints[]={
#ifdef PC98
0x30d2,
0x30d0,
0x30d4,
0x30d6,
0x30d8,
0x30da,
0x30dc,
0x30de,
#else /* IBM-PC */
0x230, /*SB Pro & SB16*/
0x240, /*SB Pro & SB16*/
0x250, /*Creative omniCD standalone boards*/
@ -205,6 +215,7 @@ static int port_hints[]={
0x670, /*IBM*/
0x690, /*IBM*/
#endif /*0*/
#endif /* PC98 */
-1}; /*use. Table MUST end with -1*/
#endif /*AUTOHUNT*/

View File

@ -1,6 +1,6 @@
/**************************************************************************
**
** $Id: pcibus.c,v 1.25 1996/06/13 21:50:41 se Exp $
** $Id: pcibus.c,v 1.26 1996/06/18 01:22:28 bde Exp $
**
** pci bus subroutines for i386 architecture.
**
@ -151,7 +151,11 @@ DATA_SET (pcibus_set, i386pci);
#define CONF1_ENABLE_RES1 0x80000000ul
#define CONF2_ENABLE_PORT 0x0cf8
#ifdef PC98
#define CONF2_FORWARD_PORT 0x0cf9
#else
#define CONF2_FORWARD_PORT 0x0cfa
#endif
#define CONF2_ENABLE_CHK 0x0e
#define CONF2_ENABLE_RES 0x0e

View File

@ -23,7 +23,7 @@
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
* $Id: prof_machdep.c,v 1.2 1996/04/08 16:41:06 wollman Exp $
* $Id: prof_machdep.c,v 1.3 1996/10/17 19:32:10 bde Exp $
*/
#ifdef GUPROF
@ -40,7 +40,11 @@
#include <machine/profile.h>
#endif
#ifdef PC98
#include <pc98/pc98/pc98.h>
#else
#include <i386/isa/isa.h>
#endif
#include <i386/isa/timerreg.h>
#ifdef GUPROF

View File

@ -1,7 +1,7 @@
/*
* random_machdep.c -- A strong random number generator
*
* $Id: random_machdep.c,v 1.11 1996/09/27 13:25:13 peter Exp $
* $Id: random_machdep.c,v 1.12 1996/10/09 19:47:32 bde Exp $
*
* Version 0.95, last modified 18-Oct-95
*
@ -51,7 +51,11 @@
#include <machine/random.h>
#include <i386/isa/icu.h>
#ifdef PC98
#include <pc98/pc98/pc98.h>
#else
#include <i386/isa/isa.h>
#endif
#include <i386/isa/timerreg.h>
#define MAX_BLKDEV 4

View File

@ -301,6 +301,11 @@ struct sound_timer_operations {
{SNDCARD_TRXPRO, "MediaTriX AudioTriX Pro", attach_trix_wss, probe_trix_wss},
{SNDCARD_TRXPRO_SB, "AudioTriX (SB mode)", attach_trix_sb, probe_trix_sb},
{SNDCARD_TRXPRO_MPU, "AudioTriX MIDI", attach_trix_mpu, probe_trix_mpu},
#endif
#ifdef PC98
#ifndef EXCLUDE_PCM86
{SNDCARD_PCM86, "PC-9801-86/73", attach_pcm86, probe_pcm86},
#endif
#endif
{0, "*?*", NULL, NULL}
};
@ -383,6 +388,11 @@ struct sound_timer_operations {
#ifndef EXCLUDE_YM3812
{SNDCARD_ADLIB, {FM_MONO, 0, 0}, SND_DEFAULT_ENABLE},
#endif
#ifdef PC98
#ifndef EXCLUDE_PCM86
{SNDCARD_PCM86, {0, 0, 0}, SND_DEFAULT_ENABLE},
#endif
#endif
{0, {0}, 0}
};

View File

@ -92,6 +92,14 @@
#define EXCLUDE_UART6850
#endif
#ifdef PC98
#include "pcm.h"
#if NPCM == 0 && !defined(EXCLUDE_PCM86)
#define EXCLUDE_PCM86
#endif
#endif
/* nothing but a sequencer (Adlib/OPL) ? */
#if NGUS == 0 && NSB == 0 && NSBMIDI == 0 && NPAS == 0 && NMPU == 0 && \
NUART == 0 && NMSS == 0
@ -99,9 +107,11 @@
#define EXCLUDE_MIDI
#endif
#ifndef EXCLUDE_AUDIO
#if !defined(PC98) || defined(EXCLUDE_PCM86) && defined(EXCLUDE_MSS)
#define EXCLUDE_AUDIO
#endif
#endif
#endif
/* nothing but a Midi (MPU/UART) ? */
#if NGUS == 0 && NSB == 0 && NSBMIDI == 0 && NPAS == 0 && NOPL == 0 && \
@ -111,6 +121,8 @@
#define EXCLUDE_SEQUENCER
#endif
#ifndef EXCLUDE_AUDIO
#if !defined(PC98) || defined(EXCLUDE_PCM86) && defined(EXCLUDE_MSS)
#define EXCLUDE_AUDIO
#endif
#endif
#endif

View File

@ -249,6 +249,12 @@ int pss_ioctl (int dev, struct fileinfo *file,
int pss_lseek (int dev, struct fileinfo *file, off_t offset, int orig);
long pss_init(long mem_start);
#ifdef PC98
/* From pcm86.c */
int probe_pcm86(struct address_info *hw_config);
long attach_pcm86(long mem_start, struct address_info *hw_config);
#endif PC98
/* From aedsp16.c */
int InitAEDSP16_SBPRO(struct address_info *hw_config);
int InitAEDSP16_MSS(struct address_info *hw_config);

View File

@ -79,24 +79,44 @@ If your card has nonstandard I/O address or IRQ number, change defines
for the following settings in your kernel Makefile */
#ifndef SBC_BASE
#ifdef PC98
#define SBC_BASE 0x20d2 /* 0x20d2 is the factory default. */
#else
#define SBC_BASE 0x220 /* 0x220 is the factory default. */
#endif
#endif
#ifndef SBC_IRQ
#ifdef PC98
#define SBC_IRQ 10 /* IQR10 is not the factory default on PC9821. */
#else
#define SBC_IRQ 7 /* IQR7 is the factory default. */
#endif
#endif
#ifndef SBC_DMA
#ifdef PC98
#define SBC_DMA 3
#else
#define SBC_DMA 1
#endif
#endif
#ifndef SB16_DMA
#ifdef PC98
#define SB16_DMA 3
#else
#define SB16_DMA 6
#endif
#endif
#ifndef SB16MIDI_BASE
#ifdef PC98
#define SB16MIDI_BASE 0x80d2
#else
#define SB16MIDI_BASE 0x300
#endif
#endif
#ifndef PAS_BASE
#define PAS_BASE 0x388
@ -248,7 +268,11 @@ If your card has nonstandard I/O address or IRQ number, change defines
#define DMA_AUTOINIT 0x10
#ifdef PC98
#define FM_MONO 0x28d2 /* This is the I/O address used by AdLib */
#else
#define FM_MONO 0x388 /* This is the I/O address used by AdLib */
#endif
/* SEQ_MAX_QUEUE is the maximum number of sequencer events buffered by the
driver. (There is no need to alter this) */

View File

@ -31,7 +31,7 @@
* SUCH DAMAGE.
*
* from: Header: timerreg.h,v 1.2 93/02/28 15:08:58 mccanne Exp
* $Id$
* $Id: timerreg.h,v 1.2 1993/10/16 13:46:26 rgrimes Exp $
*/
/*
@ -59,6 +59,7 @@
* in undefined behavior (but hopefully not fry the chip).
* Reading in this manner has no side effects.
*
* [IBM-PC]
* The outputs of the three timers are connected as follows:
*
* timer 0 -> irq 0
@ -67,15 +68,31 @@
*
* Timer 0 is used to call hardclock.
* Timer 2 is used to generate console beeps.
*
* [PC-9801]
* The outputs of the three timers are connected as follows:
*
* timer 0 -> irq 0
* timer 1 -> speaker (via keyboard controller)
* timer 2 -> RS232C
*
* Timer 0 is used to call hardclock.
* Timer 1 is used to generate console beeps.
*/
/*
* Macros for specifying values to be written into a mode register.
*/
#define TIMER_CNTR0 (IO_TIMER1 + 0) /* timer 0 counter port */
#ifdef PC98
#define TIMER_CNTR1 0x3fdb /* timer 1 counter port */
#define TIMER_CNTR2 (IO_TIMER1 + 4) /* timer 2 counter port */
#define TIMER_MODE (IO_TIMER1 + 6) /* timer mode port */
#else
#define TIMER_CNTR1 (IO_TIMER1 + 1) /* timer 1 counter port */
#define TIMER_CNTR2 (IO_TIMER1 + 2) /* timer 2 counter port */
#define TIMER_MODE (IO_TIMER1 + 3) /* timer mode port */
#endif
#define TIMER_SEL0 0x00 /* select counter 0 */
#define TIMER_SEL1 0x40 /* select counter 1 */
#define TIMER_SEL2 0x80 /* select counter 2 */

View File

@ -1,12 +1,26 @@
/*
* from: vector.s, 386BSD 0.1 unknown origin
* $Id: vector.s,v 1.19 1996/04/11 21:18:47 bde Exp $
* $Id: vector.s,v 1.20 1996/05/31 01:08:08 peter Exp $
*/
/*
* modified for PC98 by Kakefuda
*/
#include "opt_auto_eoi.h"
#include <i386/isa/icu.h>
#ifdef PC98
#include <pc98/pc98/pc98.h>
#else
#include <i386/isa/isa.h>
#endif
#ifdef PC98
#define ICU_IMR_OFFSET 2 /* IO_ICU{1,2} + 2 */
#else
#define ICU_IMR_OFFSET 1 /* IO_ICU{1,2} + 1 */
#endif
#define ICU_EOI 0x20 /* XXX - define elsewhere */
@ -168,7 +182,7 @@ IDTVEC(vec_name) ; \
movb _imen + IRQ_BYTE(irq_num),%al ; \
orb $IRQ_BIT(irq_num),%al ; \
movb %al,_imen + IRQ_BYTE(irq_num) ; \
outb %al,$icu+1 ; \
outb %al,$icu+ICU_IMR_OFFSET ; \
enable_icus ; \
incl _cnt+V_INTR ; /* tally interrupts */ \
movl _cpl,%eax ; \
@ -190,7 +204,7 @@ __CONCAT(Xresume,irq_num): ; \
movb _imen + IRQ_BYTE(irq_num),%al ; \
andb $~IRQ_BIT(irq_num),%al ; \
movb %al,_imen + IRQ_BYTE(irq_num) ; \
outb %al,$icu+1 ; \
outb %al,$icu+ICU_IMR_OFFSET ; \
sti ; /* XXX _doreti repeats the cli/sti */ \
MEXITCOUNT ; \
/* We could usually avoid the following jmp by inlining some of */ \

View File

@ -1,6 +1,6 @@
/**************************************************************************
**
** $Id: pcibus.c,v 1.25 1996/06/13 21:50:41 se Exp $
** $Id: pcibus.c,v 1.26 1996/06/18 01:22:28 bde Exp $
**
** pci bus subroutines for i386 architecture.
**
@ -151,7 +151,11 @@ DATA_SET (pcibus_set, i386pci);
#define CONF1_ENABLE_RES1 0x80000000ul
#define CONF2_ENABLE_PORT 0x0cf8
#ifdef PC98
#define CONF2_FORWARD_PORT 0x0cf9
#else
#define CONF2_FORWARD_PORT 0x0cfa
#endif
#define CONF2_ENABLE_CHK 0x0e
#define CONF2_ENABLE_RES 0x0e

View File

@ -1,6 +1,6 @@
/**************************************************************************
**
** $Id: pcibus.c,v 1.25 1996/06/13 21:50:41 se Exp $
** $Id: pcibus.c,v 1.26 1996/06/18 01:22:28 bde Exp $
**
** pci bus subroutines for i386 architecture.
**
@ -151,7 +151,11 @@ DATA_SET (pcibus_set, i386pci);
#define CONF1_ENABLE_RES1 0x80000000ul
#define CONF2_ENABLE_PORT 0x0cf8
#ifdef PC98
#define CONF2_FORWARD_PORT 0x0cf9
#else
#define CONF2_FORWARD_PORT 0x0cfa
#endif
#define CONF2_ENABLE_CHK 0x0e
#define CONF2_ENABLE_RES 0x0e

View File

@ -1,6 +1,6 @@
/**************************************************************************
**
** $Id: pcibus.c,v 1.25 1996/06/13 21:50:41 se Exp $
** $Id: pcibus.c,v 1.26 1996/06/18 01:22:28 bde Exp $
**
** pci bus subroutines for i386 architecture.
**
@ -151,7 +151,11 @@ DATA_SET (pcibus_set, i386pci);
#define CONF1_ENABLE_RES1 0x80000000ul
#define CONF2_ENABLE_PORT 0x0cf8
#ifdef PC98
#define CONF2_FORWARD_PORT 0x0cf9
#else
#define CONF2_FORWARD_PORT 0x0cfa
#endif
#define CONF2_ENABLE_CHK 0x0e
#define CONF2_ENABLE_RES 0x0e

View File

@ -25,11 +25,150 @@
* (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: kbdtables.h,v 1.30 1995/12/10 13:38:53 phk Exp $
* $Id: kbdtables.h,v 1.31 1996/01/25 16:37:20 ache Exp $
*/
#define SET8 0x80 /* set eight bit on */
#ifdef PC98
/* PC-9801 keymap by kuribo@isl.melco.co.jp */
static keymap_t key_map = { 0x80, /* PC98 keymap */
/* alt
* scan cntrl alt alt cntrl
* code base shift cntrl shift alt shift cntrl shift spcl flgs
* ---------------------------------------------------------------------------
*/
/* sc=00 */ 0x1B, 0x1B, 0x1B, 0x1B, 0x1B, 0x1B, DBG, 0x1B, 0x02, 0x00,
/* sc=01 */ '1', '!', '!', '!', '1', '!', '!', '!', 0x00, 0x00,
/* sc=02 */ '2', '\"', 0x1A, 0x1A, '2', '@', 0x00, 0x00, 0x00, 0x00,
/* sc=03 */ '3', '#', 0x1B, 0x1B, '3', '#', 0x1B, 0x1B, 0x00, 0x00,
/* sc=04 */ '4', '$', 0x1C, 0x1C, '4', '$', 0x1C, 0x1C, 0x00, 0x00,
/* sc=05 */ '5', '%', 0x1D, 0x1D, '5', '%', 0x1D, 0x1D, 0x00, 0x00,
/* sc=06 */ '6', '&', 0x1E, 0x1E, '6', '^', 0x1E, 0x1E, 0x00, 0x00,
/* sc=07 */ '7', '\'', 0x1F, 0x1F, '7', '&', '&', '&', 0x00, 0x00,
/* sc=08 */ '8', '(', 0x7F, 0x7F, '8', '*', 0x08, 0x08, 0x00, 0x00,
/* sc=09 */ '9', ')', '9', '9', '9', '(', '(', '(', 0x00, 0x00,
/* sc=0a */ '0', NOP, '0', '0', '0', ')', ')', ')', 0x40, 0x00,
/* sc=0b */ '-', '=', '-', '-', '-', '_', 0x1F, 0x1F, 0x00, 0x00,
/* sc=0c */ '^', '`', 0x1E, 0x1E, '=', '+', '+', '+', 0x00, 0x00,
/* sc=0d */ '\\', '|', 0x1C, 0x1C, '\\', '|', 0x1C, 0x1C, 0x00, 0x00,
/* sc=0e */ 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x00, 0x00,
/* sc=0f */ '\t', '\t', '\t', '\t', '\t', '\t', '\t', '\t', 0x00, 0x00,
/* sc=10 */ 'q', 'Q', 0x11, 0x11, 'q', 'Q', 0x11, 0x11, 0x00, 0x01,
/* sc=11 */ 'w', 'W', 0x17, 0x17, 'w', 'W', 0x17, 0x17, 0x00, 0x01,
/* sc=12 */ 'e', 'E', 0x05, 0x05, 'e', 'E', 0x05, 0x05, 0x00, 0x01,
/* sc=13 */ 'r', 'R', 0x12, 0x12, 'r', 'R', 0x12, 0x12, 0x00, 0x01,
/* sc=14 */ 't', 'T', 0x14, 0x14, 't', 'T', 0x14, 0x14, 0x00, 0x01,
/* sc=15 */ 'y', 'Y', 0x19, 0x19, 'y', 'Y', 0x19, 0x19, 0x00, 0x01,
/* sc=16 */ 'u', 'U', 0x15, 0x15, 'u', 'U', 0x15, 0x15, 0x00, 0x01,
/* sc=17 */ 'i', 'I', 0x09, 0x09, 'i', 'I', 0x09, 0x09, 0x00, 0x01,
/* sc=18 */ 'o', 'O', 0x0F, 0x0F, 'o', 'O', 0x0F, 0x0F, 0x00, 0x01,
/* sc=19 */ 'p', 'P', 0x10, 0x10, 'p', 'P', 0x10, 0x10, 0x00, 0x01,
/* sc=1a */ '@', '~', 0x00, 0x00, '[', '{', 0x1B, 0x1B, 0x00, 0x00,
/* sc=1b */ '[', '{', 0x1B, 0x1B, ']', '}', 0x1D, 0x1D, 0x00, 0x00,
/* sc=1c */ '\r', '\r', '\n', '\n', '\r', '\r', '\n', '\n', 0x00, 0x00,
/* sc=1d */ 'a', 'A', 0x01, 0x01, 'a', 'A', 0x01, 0x01, 0x00, 0x01,
/* sc=1e */ 's', 'S', 0x13, 0x13, 's', 'S', 0x13, 0x13, 0x00, 0x01,
/* sc=1f */ 'd', 'D', 0x04, 0x04, 'd', 'D', 0x04, 0x04, 0x00, 0x01,
/* sc=20 */ 'f', 'F', 0x06, 0x06, 'f', 'F', 0x06, 0x06, 0x00, 0x01,
/* sc=21 */ 'g', 'G', 0x07, 0x07, 'g', 'G', 0x07, 0x07, 0x00, 0x01,
/* sc=22 */ 'h', 'H', 0x08, 0x08, 'h', 'H', 0x08, 0x08, 0x00, 0x01,
/* sc=23 */ 'j', 'J', '\n', '\n', 'j', 'J', '\n', '\n', 0x00, 0x01,
/* sc=24 */ 'k', 'K', 0x0B, 0x0B, 'k', 'K', 0x0B, 0x0B, 0x00, 0x01,
/* sc=25 */ 'l', 'L', 0x0C, 0x0C, 'l', 'L', 0x0C, 0x0C, 0x00, 0x01,
/* sc=26 */ ';', '+', ';', ';', ';', ':', ';', ';', 0x00, 0x00,
/* sc=27 */ ':', '*', ':', ':', '\'', '\"', '\'', '\'', 0x00, 0x00,
/* sc=28 */ ']', '}', 0x1D, 0x1D, '`', '~', '~', '~', 0x00, 0x00,
/* sc=29 */ 'z', 'Z', 0x1A, 0x1A, 'z', 'Z', 0x1A, 0x1A, 0x00, 0x01,
/* sc=2a */ 'x', 'X', 0x18, 0x18, 'x', 'X', 0x18, 0x18, 0x00, 0x01,
/* sc=2b */ 'c', 'C', 0x03, 0x03, 'c', 'C', 0x03, 0x03, 0x00, 0x01,
/* sc=2c */ 'v', 'V', 0x16, 0x16, 'v', 'V', 0x16, 0x16, 0x00, 0x01,
/* sc=2d */ 'b', 'B', 0x02, 0x02, 'b', 'B', 0x02, 0x02, 0x00, 0x01,
/* sc=2e */ 'n', 'N', 0x0E, 0x0E, 'n', 'N', 0x0E, 0x0E, 0x00, 0x01,
/* sc=2f */ 'm', 'M', '\r', '\r', 'm', 'M', '\r', '\r', 0x00, 0x01,
/* sc=30 */ ',', '<', '<', '<', ',', '<', '<', '<', 0x00, 0x00,
/* sc=31 */ '.', '>', '>', '>', '.', '>', '>', '>', 0x00, 0x00,
/* sc=32 */ '/', '?', 0x7F, 0x7F, '/', '?', 0x7F, 0x7F, 0x00, 0x00,
/* sc=33 */ NOP, '_', 0x1F, 0x1F, '\\', '|', 0x1C, 0x1C, 0x80, 0x00,
/* sc=34 */ ' ', ' ', 0x00, 0x00, ' ', ' ', 0x00, 0x00, 0x00, 0x00,
/* sc=35 */ 0x1B, 0x1B, 0x1B, 0x1B, 0x1B, 0x1B, 0x1B, 0x1B, 0x00, 0x00,
/* sc=36 */ F(51), F(51), F(51), F(51), F(51), F(51), F(51), F(51), 0xFF, 0x00,
/* sc=37 */ F(59), F(59), F(59), F(59), F(59), F(59), F(59), F(59), 0xFF, 0x00,
/* sc=38 */ F(60), F(60), F(60), F(60), F(60), F(60), F(60), F(60), 0xFF, 0x00,
/* sc=39 */ 0x7F, 0x7F, 0x7F, 0x7F, 0x7F, 0x7F, RBT, RBT, 0x03, 0x02,
/* sc=3a */ F(50), F(50), F(50), F(50), F(50), F(50), F(50), F(50), 0xFF, 0x00,
/* sc=3b */ F(53), F(53), F(53), F(53), F(53), F(53), F(53), F(53), 0xFF, 0x00,
/* sc=3c */ F(55), F(55), F(55), F(55), F(55), F(55), F(55), F(55), 0xFF, 0x00,
/* sc=3d */ F(58), F(58), F(58), F(58), F(58), F(58), F(58), F(58), 0xFF, 0x00,
/* sc=3e */ F(49), F(49), F(49), F(49), F(49), F(49), F(49), F(49), 0xFF, 0x00,
/* sc=3f */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=40 */ '-', '-', '-', '-', '-', '-', '-', '-', 0x00, 0x00,
/* sc=41 */ '/', '/', '/', '/', '/', '/', '/', '/', 0x00, 0x00,
/* sc=42 */ '7', '7', '7', '7', '7', '7', '7', '7', 0x00, 0x00,
/* sc=43 */ '8', '8', '8', '8', '8', '8', '8', '8', 0x00, 0x00,
/* sc=44 */ '9', '9', '9', '9', '9', '9', '9', '9', 0x00, 0x00,
/* sc=45 */ '*', '*', '*', '*', '*', '*', '*', '*', 0x00, 0x00,
/* sc=46 */ '4', '4', '4', '4', '4', '4', '4', '4', 0x00, 0x00,
/* sc=47 */ '5', '5', '5', '5', '5', '5', '5', '5', 0x00, 0x00,
/* sc=48 */ '6', '6', '6', '6', '6', '6', '6', '6', 0x00, 0x00,
/* sc=49 */ '+', '+', '+', '+', '+', '+', '+', '+', 0x00, 0x00,
/* sc=4a */ '1', '1', '1', '1', '1', '1', '1', '1', 0x00, 0x00,
/* sc=4b */ '2', '2', '2', '2', '2', '2', '2', '2', 0x00, 0x00,
/* sc=4c */ '3', '3', '3', '3', '3', '3', '3', '3', 0x00, 0x00,
/* sc=4d */ '=', '=', '=', '=', '=', '=', '=', '=', 0x00, 0x00,
/* sc=4e */ '0', '0', '0', '0', '0', '0', '0', '0', 0x00, 0x00,
/* sc=4f */ ',', ',', ',', ',', ',', ',', ',', ',', 0x00, 0x00,
/* sc=50 */ '.', '.', '.', '.', '.', '.', '.', '.', 0x00, 0x00,
/* sc=51 */ 0x1B, 0x1B, 0x1B, 0x1B, 0x1B, 0x1B, 0x1B, 0x1B, 0x00, 0x00,
/* sc=52 */ F(11), F(23), F(35), F(47), S(11), S(11), S(11), S(11), 0xFF, 0x00,
/* sc=53 */ F(12), F(24), F(36), F(48), S(12), S(12), S(12), S(12), 0xFF, 0x00,
/* sc=54 */ SLK, SLK, SLK, SLK, SLK, SLK, SLK, SLK, 0xFF, 0x00,
/* sc=55 */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=56 */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=57 */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=58 */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=59 */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=5a */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=5b */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=5c */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=5d */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=5e */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=5f */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=60 */ F(57), F(57), F(57), F(57), F(57), F(57), F(57), F(57), 0xFF, 0x00,
/* sc=61 */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=62 */ F( 1), F(13), F(25), F(37), S( 1), S( 1), S( 1), S( 1), 0xFF, 0x00,
/* sc=63 */ F( 2), F(14), F(26), F(38), S( 2), S( 2), S( 2), S( 2), 0xFF, 0x00,
/* sc=64 */ F( 3), F(15), F(27), F(39), S( 3), S( 3), S( 3), S( 3), 0xFF, 0x00,
/* sc=65 */ F( 4), F(16), F(28), F(40), S( 4), S( 4), S( 4), S( 4), 0xFF, 0x00,
/* sc=66 */ F( 5), F(17), F(29), F(41), S( 5), S( 5), S( 5), S( 5), 0xFF, 0x00,
/* sc=67 */ F( 6), F(18), F(30), F(42), S( 6), S( 6), S( 6), S( 6), 0xFF, 0x00,
/* sc=68 */ F( 7), F(19), F(31), F(43), S( 7), S( 7), S( 7), S( 7), 0xFF, 0x00,
/* sc=69 */ F( 8), F(20), F(32), F(44), S( 8), S( 8), S( 8), S( 8), 0xFF, 0x00,
/* sc=6a */ F( 9), F(21), F(33), F(45), S( 9), S( 9), S( 9), S( 9), 0xFF, 0x00,
/* sc=6b */ F(10), F(22), F(34), F(46), S(10), S(10), S(10), S(10), 0xFF, 0x00,
/* sc=6c */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=6d */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=6e */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=6f */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=70 */ LSH, LSH, LSH, LSH, LSH, LSH, LSH, LSH, 0xFF, 0x00,
/* sc=71 */ CLK, CLK, CLK, CLK, CLK, CLK, CLK, CLK, 0xFF, 0x00,
/* sc=72 */ LALT, LALT, LALT, LALT, LALT, LALT, LALT, LALT, 0xFF, 0x00,
/* sc=73 */ LALT, LALT, LALT, LALT, LALT, LALT, LALT, LALT, 0xFF, 0x00,
/* sc=74 */ LCTR, LCTR, LCTR, LCTR, LCTR, LCTR, LCTR, LCTR, 0xFF, 0x00,
/* sc=75 */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=76 */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=77 */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=78 */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=79 */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=7a */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=7b */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=7c */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=7d */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=7e */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
/* sc=7f */ NOP, NOP, NOP, NOP, NOP, NOP, NOP, NOP, 0xFF, 0x00,
};
#endif
#ifdef DKKEYMAP
static keymap_t key_map = { 0x6C, /* DK iso8859 keymap */
/* alt
@ -750,7 +889,7 @@ static keymap_t key_map = { 0xEC, /* keys number */
#endif
#if !defined(DKKEYMAP) && !defined(UKKEYMAP) && !defined(GRKEYMAP) && !defined(SWKEYMAP) && !defined(RUKEYMAP)
#if !defined(DKKEYMAP) && !defined(UKKEYMAP) && !defined(GRKEYMAP) && !defined(SWKEYMAP) && !defined(RUKEYMAP) && !defined(PC98)
static keymap_t key_map = { 0x6C, /* US iso8859 keymap */
/* alt
* scan cntrl alt alt cntrl

View File

@ -31,7 +31,7 @@
* SUCH DAMAGE.
*
* from: Header: timerreg.h,v 1.2 93/02/28 15:08:58 mccanne Exp
* $Id$
* $Id: timerreg.h,v 1.2 1993/10/16 13:46:26 rgrimes Exp $
*/
/*
@ -59,6 +59,7 @@
* in undefined behavior (but hopefully not fry the chip).
* Reading in this manner has no side effects.
*
* [IBM-PC]
* The outputs of the three timers are connected as follows:
*
* timer 0 -> irq 0
@ -67,15 +68,31 @@
*
* Timer 0 is used to call hardclock.
* Timer 2 is used to generate console beeps.
*
* [PC-9801]
* The outputs of the three timers are connected as follows:
*
* timer 0 -> irq 0
* timer 1 -> speaker (via keyboard controller)
* timer 2 -> RS232C
*
* Timer 0 is used to call hardclock.
* Timer 1 is used to generate console beeps.
*/
/*
* Macros for specifying values to be written into a mode register.
*/
#define TIMER_CNTR0 (IO_TIMER1 + 0) /* timer 0 counter port */
#ifdef PC98
#define TIMER_CNTR1 0x3fdb /* timer 1 counter port */
#define TIMER_CNTR2 (IO_TIMER1 + 4) /* timer 2 counter port */
#define TIMER_MODE (IO_TIMER1 + 6) /* timer mode port */
#else
#define TIMER_CNTR1 (IO_TIMER1 + 1) /* timer 1 counter port */
#define TIMER_CNTR2 (IO_TIMER1 + 2) /* timer 2 counter port */
#define TIMER_MODE (IO_TIMER1 + 3) /* timer mode port */
#endif
#define TIMER_SEL0 0x00 /* select counter 0 */
#define TIMER_SEL1 0x40 /* select counter 1 */
#define TIMER_SEL2 0x80 /* select counter 2 */

View File

@ -1,7 +1,7 @@
/*
* random_machdep.c -- A strong random number generator
*
* $Id: random_machdep.c,v 1.11 1996/09/27 13:25:13 peter Exp $
* $Id: random_machdep.c,v 1.12 1996/10/09 19:47:32 bde Exp $
*
* Version 0.95, last modified 18-Oct-95
*
@ -51,7 +51,11 @@
#include <machine/random.h>
#include <i386/isa/icu.h>
#ifdef PC98
#include <pc98/pc98/pc98.h>
#else
#include <i386/isa/isa.h>
#endif
#include <i386/isa/timerreg.h>
#define MAX_BLKDEV 4

View File

@ -34,7 +34,7 @@
* SUCH DAMAGE.
*
* from: @(#)isa.h 5.7 (Berkeley) 5/9/91
* $Id: pc98.h,v 1.5 1996/10/09 21:46:34 asami Exp $
* $Id: pc98.h,v 1.6 1996/10/23 07:25:22 asami Exp $
*/
#ifndef _PC98_PC98_PC98_H_
@ -73,7 +73,7 @@
#define IO_NMI 0x050 /* NMI Control */
#define IO_WAIT 0x05F /* WAIT 0.6 us */
#define IO_GDC1 0x060 /* 7220 GDC Text Control */
#define IO_TIMER 0x071 /* 8253C Timer */
#define IO_TIMER1 0x071 /* 8253C Timer */
#define IO_SASI 0x080 /* SASI Hard Disk Controller */
#define IO_FD1 0x090 /* 765A 1MB FDC */
#define IO_GDC2 0x0a0 /* 7220 GDC Graphic Control */

View File

@ -34,7 +34,11 @@
* SUCH DAMAGE.
*
* from: @(#)clock.c 7.2 (Berkeley) 5/12/91
* $Id: clock.c,v 1.8 1996/10/23 07:25:13 asami Exp $
* $Id: clock.c,v 1.9 1996/10/29 08:36:19 asami Exp $
*/
/*
* Routines to handle clock hardware.
*/
/*
@ -48,10 +52,6 @@
* modified for PC98 by Kakefuda
*/
/*
* Primitive clock interrupt routines.
*/
#include "opt_clock.h"
#include "opt_cpu.h"
@ -72,13 +72,12 @@
#ifdef PC98
#include <pc98/pc98/pc98.h>
#include <i386/isa/isa_device.h>
#include <pc98/pc98/timerreg.h>
#else
#include <i386/isa/isa.h>
#include <i386/isa/isa_device.h>
#include <i386/isa/rtc.h>
#include <i386/isa/timerreg.h>
#endif
#include <i386/isa/timerreg.h>
/*
* 32-bit time_t's can't reach leap years before 1904 or after 2036, so we
@ -109,52 +108,49 @@
int adjkerntz; /* local offset from GMT in seconds */
int disable_rtc_set; /* disable resettodr() if != 0 */
int wall_cmos_clock; /* wall CMOS clock assumed if != 0 */
u_int idelayed;
#if defined(I586_CPU) || defined(I686_CPU)
u_int i586_ctr_bias;
u_int i586_ctr_bias;
u_int i586_ctr_comultiplier;
u_int i586_ctr_freq;
u_int i586_ctr_multiplier;
long long i586_last_tick;
unsigned long i586_avg_tick;
#endif
int statclock_disable;
u_int stat_imask = SWI_CLOCK_MASK;
#ifdef TIMER_FREQ
static u_int timer_freq = TIMER_FREQ;
u_int timer_freq = TIMER_FREQ;
#else
#ifdef PC98
#ifndef AUTO_CLOCK
#ifndef PC98_8M
static u_int timer_freq = 2457600;
u_int timer_freq = 2457600;
#else /* !PC98_8M */
static u_int timer_freq = 1996800;
u_int timer_freq = 1996800;
#endif /* PC98_8M */
#else /* AUTO_CLOCK */
static u_int timer_freq = 2457600;
u_int timer_freq = 2457600;
#endif /* AUTO_CLOCK */
#else /* IBM-PC */
static u_int timer_freq = 1193182;
u_int timer_freq = 1193182;
#endif /* PC98 */
#endif
int timer0_max_count;
u_int timer0_overflow_threshold;
u_int timer0_prescaler_count;
int timer0_max_count;
u_int timer0_overflow_threshold;
u_int timer0_prescaler_count;
int wall_cmos_clock; /* wall CMOS clock assumed if != 0 */
static int beeping = 0;
static u_int clk_imask = HWI_MASK | SWI_MASK;
static const u_char daysinmonth[] = {31,28,31,30,31,30,31,31,30,31,30,31};
static u_int hardclock_max_count;
static u_int hardclock_max_count;
/*
* XXX new_function and timer_func should not handle clockframes, but
* timer_func currently needs to hold hardclock to handle the
* timer0_state == 0 case. We should use register_intr()/unregister_intr()
* to switch between clkintr() and a slightly different timerintr().
*/
static void (*new_function) __P((struct clockframe *frame));
static u_int new_rate;
static void (*new_function) __P((struct clockframe *frame));
static u_int new_rate;
#ifndef PC98
static u_char rtc_statusa = RTCSA_DIVIDER | RTCSA_NOPROF;
static u_char rtc_statusb = RTCSB_24HR | RTCSB_PINTR;
@ -171,7 +167,7 @@ static u_char timer0_state;
static u_char timer1_state;
#endif
static u_char timer2_state;
static void (*timer_func) __P((struct clockframe *frame)) = hardclock;
static void (*timer_func) __P((struct clockframe *frame)) = hardclock;
int rtc_inb __P((void));
#if defined(I586_CPU) || defined(I686_CPU)
@ -437,7 +433,7 @@ getit(void)
disable_intr();
/* Select timer0 and latch counter value. */
outb(TIMER_MODE, TIMER_SEL0);
outb(TIMER_MODE, TIMER_SEL0 | TIMER_LATCH);
low = inb(TIMER_CNTR0);
high = inb(TIMER_CNTR0);
@ -625,7 +621,7 @@ calibrate_clocks(void)
u_int count, prev_count, tot_count;
int sec, start_sec, timeout;
printf("Calibrating clock(s) relative to mc146818A clock...\n");
printf("Calibrating clock(s) relative to mc146818A clock ... ");
if (!(rtcin(RTC_STATUSD) & RTCSD_PWR))
goto fail;
timeout = 100000000;
@ -782,7 +778,7 @@ startrtclock()
if (delta < timer_freq / 100) {
#ifndef CLK_USE_I8254_CALIBRATION
if (bootverbose)
printf(
printf(
"CLK_USE_I8254_CALIBRATION not specified - using default frequency\n");
freq = timer_freq;
#endif
@ -802,7 +798,7 @@ startrtclock()
#ifndef CLK_USE_I586_CALIBRATION
if (i586_ctr_freq != 0) {
if (bootverbose)
printf(
printf(
"CLK_USE_I586_CALIBRATION not specified - using old calibration method\n");
i586_ctr_freq = 0;
}
@ -1114,10 +1110,8 @@ cpu_initclocks()
/*
* Finish setting up anti-jitter measures.
*/
if (i586_ctr_freq != 0) {
i586_last_tick = rdtsc();
i586_ctr_bias = i586_last_tick;
}
if (i586_ctr_freq != 0)
i586_ctr_bias = rdtsc();
#endif
#ifndef PC98

View File

@ -34,7 +34,11 @@
* SUCH DAMAGE.
*
* from: @(#)clock.c 7.2 (Berkeley) 5/12/91
* $Id: clock.c,v 1.8 1996/10/23 07:25:13 asami Exp $
* $Id: clock.c,v 1.9 1996/10/29 08:36:19 asami Exp $
*/
/*
* Routines to handle clock hardware.
*/
/*
@ -48,10 +52,6 @@
* modified for PC98 by Kakefuda
*/
/*
* Primitive clock interrupt routines.
*/
#include "opt_clock.h"
#include "opt_cpu.h"
@ -72,13 +72,12 @@
#ifdef PC98
#include <pc98/pc98/pc98.h>
#include <i386/isa/isa_device.h>
#include <pc98/pc98/timerreg.h>
#else
#include <i386/isa/isa.h>
#include <i386/isa/isa_device.h>
#include <i386/isa/rtc.h>
#include <i386/isa/timerreg.h>
#endif
#include <i386/isa/timerreg.h>
/*
* 32-bit time_t's can't reach leap years before 1904 or after 2036, so we
@ -109,52 +108,49 @@
int adjkerntz; /* local offset from GMT in seconds */
int disable_rtc_set; /* disable resettodr() if != 0 */
int wall_cmos_clock; /* wall CMOS clock assumed if != 0 */
u_int idelayed;
#if defined(I586_CPU) || defined(I686_CPU)
u_int i586_ctr_bias;
u_int i586_ctr_bias;
u_int i586_ctr_comultiplier;
u_int i586_ctr_freq;
u_int i586_ctr_multiplier;
long long i586_last_tick;
unsigned long i586_avg_tick;
#endif
int statclock_disable;
u_int stat_imask = SWI_CLOCK_MASK;
#ifdef TIMER_FREQ
static u_int timer_freq = TIMER_FREQ;
u_int timer_freq = TIMER_FREQ;
#else
#ifdef PC98
#ifndef AUTO_CLOCK
#ifndef PC98_8M
static u_int timer_freq = 2457600;
u_int timer_freq = 2457600;
#else /* !PC98_8M */
static u_int timer_freq = 1996800;
u_int timer_freq = 1996800;
#endif /* PC98_8M */
#else /* AUTO_CLOCK */
static u_int timer_freq = 2457600;
u_int timer_freq = 2457600;
#endif /* AUTO_CLOCK */
#else /* IBM-PC */
static u_int timer_freq = 1193182;
u_int timer_freq = 1193182;
#endif /* PC98 */
#endif
int timer0_max_count;
u_int timer0_overflow_threshold;
u_int timer0_prescaler_count;
int timer0_max_count;
u_int timer0_overflow_threshold;
u_int timer0_prescaler_count;
int wall_cmos_clock; /* wall CMOS clock assumed if != 0 */
static int beeping = 0;
static u_int clk_imask = HWI_MASK | SWI_MASK;
static const u_char daysinmonth[] = {31,28,31,30,31,30,31,31,30,31,30,31};
static u_int hardclock_max_count;
static u_int hardclock_max_count;
/*
* XXX new_function and timer_func should not handle clockframes, but
* timer_func currently needs to hold hardclock to handle the
* timer0_state == 0 case. We should use register_intr()/unregister_intr()
* to switch between clkintr() and a slightly different timerintr().
*/
static void (*new_function) __P((struct clockframe *frame));
static u_int new_rate;
static void (*new_function) __P((struct clockframe *frame));
static u_int new_rate;
#ifndef PC98
static u_char rtc_statusa = RTCSA_DIVIDER | RTCSA_NOPROF;
static u_char rtc_statusb = RTCSB_24HR | RTCSB_PINTR;
@ -171,7 +167,7 @@ static u_char timer0_state;
static u_char timer1_state;
#endif
static u_char timer2_state;
static void (*timer_func) __P((struct clockframe *frame)) = hardclock;
static void (*timer_func) __P((struct clockframe *frame)) = hardclock;
int rtc_inb __P((void));
#if defined(I586_CPU) || defined(I686_CPU)
@ -437,7 +433,7 @@ getit(void)
disable_intr();
/* Select timer0 and latch counter value. */
outb(TIMER_MODE, TIMER_SEL0);
outb(TIMER_MODE, TIMER_SEL0 | TIMER_LATCH);
low = inb(TIMER_CNTR0);
high = inb(TIMER_CNTR0);
@ -625,7 +621,7 @@ calibrate_clocks(void)
u_int count, prev_count, tot_count;
int sec, start_sec, timeout;
printf("Calibrating clock(s) relative to mc146818A clock...\n");
printf("Calibrating clock(s) relative to mc146818A clock ... ");
if (!(rtcin(RTC_STATUSD) & RTCSD_PWR))
goto fail;
timeout = 100000000;
@ -782,7 +778,7 @@ startrtclock()
if (delta < timer_freq / 100) {
#ifndef CLK_USE_I8254_CALIBRATION
if (bootverbose)
printf(
printf(
"CLK_USE_I8254_CALIBRATION not specified - using default frequency\n");
freq = timer_freq;
#endif
@ -802,7 +798,7 @@ startrtclock()
#ifndef CLK_USE_I586_CALIBRATION
if (i586_ctr_freq != 0) {
if (bootverbose)
printf(
printf(
"CLK_USE_I586_CALIBRATION not specified - using old calibration method\n");
i586_ctr_freq = 0;
}
@ -1114,10 +1110,8 @@ cpu_initclocks()
/*
* Finish setting up anti-jitter measures.
*/
if (i586_ctr_freq != 0) {
i586_last_tick = rdtsc();
i586_ctr_bias = i586_last_tick;
}
if (i586_ctr_freq != 0)
i586_ctr_bias = rdtsc();
#endif
#ifndef PC98

View File

@ -11,7 +11,7 @@
# device lines is present in the ./LINT configuration file. If you are
# in doubt as to the purpose or necessity of a line, check first in LINT.
#
# $Id: GENERIC98,v 1.6 1996/10/09 21:45:41 asami Exp $
# $Id: GENERIC98,v 1.7 1996/10/23 07:24:45 asami Exp $
# GENERIC98 -- Generic PC98 machine with WD/SBIC55 disks
@ -100,6 +100,9 @@ device wcd0 #IDE CD-ROM
# for any number of installed devices.
controller ncr0
controller ahc0
options "AHC_FORCE_PIO" # Some motherboards choke on MemI/O,
# so use PIO in the ahc driver in the
# generic kernel.
controller sbic0 at isa? port "IO_SCSI" bio irq 5 drq 3 vector sbicintr
# sbic55.c.new

View File

@ -11,7 +11,7 @@
# device lines is present in the ./LINT configuration file. If you are
# in doubt as to the purpose or necessity of a line, check first in LINT.
#
# $Id: GENERIC98,v 1.6 1996/10/09 21:45:41 asami Exp $
# $Id: GENERIC98,v 1.7 1996/10/23 07:24:45 asami Exp $
# GENERIC98 -- Generic PC98 machine with WD/SBIC55 disks
@ -100,6 +100,9 @@ device wcd0 #IDE CD-ROM
# for any number of installed devices.
controller ncr0
controller ahc0
options "AHC_FORCE_PIO" # Some motherboards choke on MemI/O,
# so use PIO in the ahc driver in the
# generic kernel.
controller sbic0 at isa? port "IO_SCSI" bio irq 5 drq 3 vector sbicintr
# sbic55.c.new

View File

@ -3,7 +3,7 @@
#
# modified for PC-9801
#
# $Id: files.pc98,v 1.7 1996/09/12 11:09:18 asami Exp $
# $Id: files.pc98,v 1.8 1996/10/23 07:24:49 asami Exp $
#
aic7xxx_asm optional ahc device-driver \
dependency "$S/dev/aic7xxx/aic7xxx_asm.c" \
@ -43,7 +43,7 @@ i386/i386/db_disasm.c optional ddb
i386/i386/db_interface.c optional ddb
i386/i386/db_trace.c optional ddb
i386/i386/i386-gdbstub.c optional ddb
pc98/i386/exception.s standard
i386/i386/exception.s standard
i386/i386/identcpu.c standard
i386/i386/in_cksum.c optional inet
# locore.s needs to be handled in Makefile to put it first. Otherwise it's
@ -62,7 +62,7 @@ i386/i386/swtch.s standard
i386/i386/sys_machdep.c standard
pc98/i386/trap.c standard
pc98/i386/userconfig.c optional userconfig
pc98/i386/vm_machdep.c standard
i386/i386/vm_machdep.c standard
i386/ibcs2/ibcs2_fcntl.c optional ibcs2
i386/ibcs2/ibcs2_stat.c optional ibcs2
i386/ibcs2/ibcs2_ipc.c optional ibcs2
@ -89,7 +89,7 @@ pc98/pc98/bs/bshw.c optional bs device-driver
pc98/pc98/bs/bsif.c optional bs device-driver
pc98/pc98/sbic55.c optional sbic device-driver
#i386/pc98/aha1542.c optional aha device-driver
pc98/pc98/aic6360.c optional aic device-driver
i386/isa/aic6360.c optional aic device-driver
pc98/pc98/b004.c optional bqu device-driver
i386/pc98/bt742a.c optional bt device-driver
i386/pc98/bt5xx-445.c optional bt device-driver
@ -130,8 +130,8 @@ pc98/pc98/mse.c optional mse device-driver
pc98/isa/ncr5380.c optional nca device-driver
pc98/pc98/npx.c optional npx device-driver
pc98/pc98/pcaudio.c optional pca device-driver
pc98/pc98/matcd/matcd.c optional matcd device-driver
pc98/pc98/pcibus.c optional pci device-driver
i386/isa/matcd/matcd.c optional matcd device-driver
i386/isa/pcibus.c optional pci device-driver
i386/isa/pcicx.c optional ze device-driver
i386/isa/pcicx.c optional zp device-driver
pc98/isa/pcvt/pcvt_drv.c optional vt device-driver
@ -140,11 +140,11 @@ pc98/isa/pcvt/pcvt_kbd.c optional vt device-driver
pc98/isa/pcvt/pcvt_out.c optional vt device-driver
pc98/isa/pcvt/pcvt_sup.c optional vt device-driver
pc98/isa/pcvt/pcvt_vtf.c optional vt device-driver
pc98/pc98/prof_machdep.c optional profiling-routine
i386/isa/prof_machdep.c optional profiling-routine
pc98/pc98/psm.c optional psm device-driver
pc98/isa/qcam.c optional qcam device-driver
pc98/isa/qcamio.c optional qcam device-driver
pc98/pc98/random_machdep.c standard
i386/isa/random_machdep.c standard
pc98/isa/rc.c optional rc device-driver
i386/isa/scd.c optional scd device-driver
pc98/isa/seagate.c optional sea device-driver
@ -152,51 +152,51 @@ pc98/isa/si.c optional si device-driver
pc98/isa/si_code.c optional si device-driver
pc98/pc98/sio.c optional sio device-driver
pc98/pc98/sound/pcm86.c optional pcm device-driver
pc98/pc98/sound/dev_table.c optional snd device-driver
i386/isa/sound/dev_table.c optional snd device-driver
pc98/pc98/sound/soundcard.c optional snd device-driver
pc98/pc98/sound/sound_switch.c optional snd device-driver
pc98/pc98/sound/audio.c optional snd device-driver
pc98/pc98/sound/dmabuf.c optional snd device-driver
pc98/pc98/sound/sys_timer.c optional snd device-driver
pc98/pc98/sound/sequencer.c optional snd device-driver
pc98/pc98/sound/patmgr.c optional snd device-driver
pc98/pc98/sound/adlib_card.c optional opl device-driver
i386/isa/sound/audio.c optional snd device-driver
i386/isa/sound/dmabuf.c optional snd device-driver
i386/isa/sound/sys_timer.c optional snd device-driver
i386/isa/sound/sequencer.c optional snd device-driver
i386/isa/sound/patmgr.c optional snd device-driver
i386/isa/sound/adlib_card.c optional opl device-driver
pc98/pc98/sound/opl3.c optional opl device-driver
pc98/pc98/sound/gus_card.c optional gus device-driver
pc98/pc98/sound/gus_midi.c optional gus device-driver
pc98/pc98/sound/gus_vol.c optional gus device-driver
pc98/pc98/sound/gus_wave.c optional gus device-driver
pc98/pc98/sound/ics2101.c optional gus device-driver
pc98/pc98/sound/sound_timer.c optional gus device-driver
pc98/pc98/sound/midi_synth.c optional gus device-driver
pc98/pc98/sound/midibuf.c optional gus device-driver
i386/isa/sound/gus_card.c optional gus device-driver
i386/isa/sound/gus_midi.c optional gus device-driver
i386/isa/sound/gus_vol.c optional gus device-driver
i386/isa/sound/gus_wave.c optional gus device-driver
i386/isa/sound/ics2101.c optional gus device-driver
i386/isa/sound/sound_timer.c optional gus device-driver
i386/isa/sound/midi_synth.c optional gus device-driver
i386/isa/sound/midibuf.c optional gus device-driver
pc98/pc98/sound/ad1848.c optional gusxvi device-driver
pc98/pc98/sound/ad1848.c optional gus device-driver
pc98/pc98/sound/ad1848.c optional mss device-driver
pc98/pc98/sound/midi_synth.c optional mss device-driver
pc98/pc98/sound/midibuf.c optional mss device-driver
pc98/pc98/sound/mpu401.c optional mpu device-driver
pc98/pc98/sound/midi_synth.c optional mpu device-driver
pc98/pc98/sound/midibuf.c optional mpu device-driver
pc98/pc98/sound/pas2_card.c optional pas device-driver
pc98/pc98/sound/pas2_midi.c optional pas device-driver
pc98/pc98/sound/pas2_mixer.c optional pas device-driver
i386/isa/sound/midi_synth.c optional mss device-driver
i386/isa/sound/midibuf.c optional mss device-driver
i386/isa/sound/mpu401.c optional mpu device-driver
i386/isa/sound/midi_synth.c optional mpu device-driver
i386/isa/sound/midibuf.c optional mpu device-driver
i386/isa/sound/pas2_card.c optional pas device-driver
i386/isa/sound/pas2_midi.c optional pas device-driver
i386/isa/sound/pas2_mixer.c optional pas device-driver
pc98/pc98/sound/pas2_pcm.c optional pas device-driver
pc98/pc98/sound/midi_synth.c optional pas device-driver
pc98/pc98/sound/midibuf.c optional pas device-driver
pc98/pc98/sound/sb_card.c optional sb device-driver
i386/isa/sound/midi_synth.c optional pas device-driver
i386/isa/sound/midibuf.c optional pas device-driver
i386/isa/sound/sb_card.c optional sb device-driver
pc98/pc98/sound/sb_dsp.c optional sb device-driver
pc98/pc98/sound/sb_midi.c optional sb device-driver
pc98/pc98/sound/sb_mixer.c optional sb device-driver
pc98/pc98/sound/midi_synth.c optional sb device-driver
pc98/pc98/sound/midibuf.c optional sb device-driver
i386/isa/sound/sb_midi.c optional sb device-driver
i386/isa/sound/sb_mixer.c optional sb device-driver
i386/isa/sound/midi_synth.c optional sb device-driver
i386/isa/sound/midibuf.c optional sb device-driver
pc98/pc98/sound/sb16_dsp.c optional sbxvi device-driver
pc98/pc98/sound/sb16_midi.c optional sbmidi device-driver
pc98/pc98/sound/uart6850.c optional uart device-driver
pc98/pc98/sound/midi_synth.c optional uart device-driver
pc98/pc98/sound/midibuf.c optional uart device-driver
pc98/pc98/sound/trix.c optional trix device-driver
pc98/pc98/sound/sscape.c optional sscape device-driver
i386/isa/sound/uart6850.c optional uart device-driver
i386/isa/sound/midi_synth.c optional uart device-driver
i386/isa/sound/midibuf.c optional uart device-driver
i386/isa/sound/trix.c optional trix device-driver
i386/isa/sound/sscape.c optional sscape device-driver
pc98/isa/spigot.c optional spigot device-driver
pc98/pc98/spkr.c optional speaker device-driver
pc98/isa/stallion.c optional stl device-driver
@ -205,7 +205,7 @@ pc98/isa/tw.c optional tw device-driver
pc98/isa/ultra14f.c optional uha device-driver
pc98/pc98/wd.c optional wdc device-driver
pc98/pc98/wd.c optional wd device-driver
pc98/pc98/atapi.c optional atapi device-driver
i386/isa/atapi.c optional atapi device-driver
pc98/pc98/wcd.c optional wcd device-driver
pc98/isa/wd7000.c optional wds device-driver
pc98/pc98/wt.c optional wt device-driver

View File

@ -1,4 +1,4 @@
# $Id: options.pc98,v 1.6 1996/10/23 07:24:55 asami Exp $
# $Id: options.pc98,v 1.7 1996/10/29 08:36:14 asami Exp $
BOUNCEPAGES opt_bounce.h
USER_LDT
MATH_EMULATE opt_math_emulate.h
@ -29,6 +29,8 @@ XSERVER opt_pcvt.h
AHC_TAGENABLE opt_aic7xxx.h
AHC_SCBPAGING_ENABLE opt_aic7xxx.h
AHC_FORCE_PIO opt_aic7xxx.h
AHC_SHARE_SCBS opt_aic7xxx.h
CLK_CALIBRATION_LOOP opt_clock.h
CLK_USE_I8254_CALIBRATION opt_clock.h

View File

@ -1,279 +0,0 @@
/*-
* Copyright (c) 1990 The Regents of the University of California.
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. All advertising materials mentioning features or use of this software
* must display the following acknowledgement:
* This product includes software developed by the University of
* California, Berkeley and its contributors.
* 4. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE REGENTS 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 REGENTS 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: exception.s,v 1.1.1.1 1996/06/14 10:04:41 asami Exp $
*/
#include "npx.h" /* NNPX */
#include "assym.s" /* system defines */
#include <sys/errno.h> /* error return codes */
#include <machine/spl.h> /* SWI_AST_MASK ... */
#include <machine/psl.h> /* PSL_I */
#include <machine/trap.h> /* trap codes */
#include <sys/syscall.h> /* syscall numbers */
#include <machine/asmacros.h> /* miscellaneous macros */
#include <sys/cdefs.h> /* CPP macros */
#define KDSEL 0x10 /* kernel data selector */
#define SEL_RPL_MASK 0x0003
#define TRAPF_CS_OFF (13 * 4)
.text
/*****************************************************************************/
/* Trap handling */
/*****************************************************************************/
/*
* Trap and fault vector routines
*/
#define IDTVEC(name) ALIGN_TEXT; .globl __CONCAT(_X,name); __CONCAT(_X,name):
#define TRAP(a) pushl $(a) ; jmp _alltraps
/*
* XXX - debugger traps are now interrupt gates so at least bdb doesn't lose
* control. The sti's give the standard losing behaviour for ddb and kgdb.
*/
#ifdef BDE_DEBUGGER
#define BDBTRAP(name) \
ss ; \
cmpb $0,_bdb_exists ; \
je 1f ; \
testb $SEL_RPL_MASK,4(%esp) ; \
jne 1f ; \
ss ; \
.globl __CONCAT(__CONCAT(bdb_,name),_ljmp); \
__CONCAT(__CONCAT(bdb_,name),_ljmp): \
ljmp $0,$0 ; \
1:
#else
#define BDBTRAP(name)
#endif
#define BPTTRAP(a) testl $PSL_I,4+8(%esp) ; je 1f ; sti ; 1: ; TRAP(a)
MCOUNT_LABEL(user)
MCOUNT_LABEL(btrap)
IDTVEC(div)
pushl $0; TRAP(T_DIVIDE)
IDTVEC(dbg)
BDBTRAP(dbg)
pushl $0; BPTTRAP(T_TRCTRAP)
IDTVEC(nmi)
pushl $0; TRAP(T_NMI)
IDTVEC(bpt)
BDBTRAP(bpt)
pushl $0; BPTTRAP(T_BPTFLT)
IDTVEC(ofl)
pushl $0; TRAP(T_OFLOW)
IDTVEC(bnd)
pushl $0; TRAP(T_BOUND)
IDTVEC(ill)
pushl $0; TRAP(T_PRIVINFLT)
IDTVEC(dna)
pushl $0; TRAP(T_DNA)
IDTVEC(fpusegm)
pushl $0; TRAP(T_FPOPFLT)
IDTVEC(tss)
TRAP(T_TSSFLT)
IDTVEC(missing)
TRAP(T_SEGNPFLT)
IDTVEC(stk)
TRAP(T_STKFLT)
IDTVEC(prot)
TRAP(T_PROTFLT)
IDTVEC(page)
TRAP(T_PAGEFLT)
IDTVEC(mchk)
pushl $0; TRAP(T_MCHK)
IDTVEC(rsvd)
pushl $0; TRAP(T_RESERVED)
IDTVEC(fpu)
#if NNPX > 0
/*
* Handle like an interrupt (except for accounting) so that we can
* call npxintr to clear the error. It would be better to handle
* npx interrupts as traps. This used to be difficult for nested
* interrupts, but now it is fairly easy - mask nested ones the
* same as SWI_AST's.
*/
pushl $0 /* dummy error code */
pushl $0 /* dummy trap type */
pushal
pushl %ds
pushl %es /* now the stack frame is a trap frame */
movl $KDSEL,%eax
movl %ax,%ds
movl %ax,%es
FAKE_MCOUNT(12*4(%esp))
movl _cpl,%eax
pushl %eax
pushl $0 /* dummy unit to finish building intr frame */
incl _cnt+V_TRAP
orl $SWI_AST_MASK,%eax
movl %eax,_cpl
call _npxintr
incb _intr_nesting_level
MEXITCOUNT
jmp _doreti
#else /* NNPX > 0 */
pushl $0; TRAP(T_ARITHTRAP)
#endif /* NNPX > 0 */
IDTVEC(align)
TRAP(T_ALIGNFLT)
SUPERALIGN_TEXT
.globl _alltraps
_alltraps:
pushal
pushl %ds
pushl %es
alltraps_with_regs_pushed:
movl $KDSEL,%eax
movl %ax,%ds
movl %ax,%es
FAKE_MCOUNT(12*4(%esp))
calltrap:
FAKE_MCOUNT(_btrap) /* init "from" _btrap -> calltrap */
incl _cnt+V_TRAP
orl $SWI_AST_MASK,_cpl
call _trap
/*
* There was no place to save the cpl so we have to recover it
* indirectly. For traps from user mode it was 0, and for traps
* from kernel mode Oring SWI_AST_MASK into it didn't change it.
*/
subl %eax,%eax
testb $SEL_RPL_MASK,TRAPF_CS_OFF(%esp)
jne 1f
movl _cpl,%eax
1:
/*
* Return via _doreti to handle ASTs. Have to change trap frame
* to interrupt frame.
*/
pushl %eax
subl $4,%esp
incb _intr_nesting_level
MEXITCOUNT
jmp _doreti
/*
* Call gate entry for syscall.
* The intersegment call has been set up to specify one dummy parameter.
* This leaves a place to put eflags so that the call frame can be
* converted to a trap frame. Note that the eflags is (semi-)bogusly
* pushed into (what will be) tf_err and then copied later into the
* final spot. It has to be done this way because esp can't be just
* temporarily altered for the pushfl - an interrupt might come in
* and clobber the saved cs/eip.
*/
SUPERALIGN_TEXT
IDTVEC(syscall)
pushfl /* save eflags in tf_err for now */
subl $4,%esp /* skip over tf_trapno */
pushal
pushl %ds
pushl %es
movl $KDSEL,%eax /* switch to kernel segments */
movl %ax,%ds
movl %ax,%es
movl TF_ERR(%esp),%eax /* copy saved eflags to final spot */
movl %eax,TF_EFLAGS(%esp)
movl $7,TF_ERR(%esp) /* sizeof "lcall 7,0" */
FAKE_MCOUNT(12*4(%esp))
incl _cnt+V_SYSCALL
movl $SWI_AST_MASK,_cpl
call _syscall
/*
* Return via _doreti to handle ASTs.
*/
pushl $0 /* cpl to restore */
subl $4,%esp
movb $1,_intr_nesting_level
MEXITCOUNT
jmp _doreti
/*
* Call gate entry for Linux/NetBSD syscall (int 0x80)
*/
SUPERALIGN_TEXT
IDTVEC(int0x80_syscall)
subl $8,%esp /* skip over tf_trapno and tf_err */
pushal
pushl %ds
pushl %es
movl $KDSEL,%eax /* switch to kernel segments */
movl %ax,%ds
movl %ax,%es
movl $2,TF_ERR(%esp) /* sizeof "int 0x80" */
FAKE_MCOUNT(12*4(%esp))
incl _cnt+V_SYSCALL
movl $SWI_AST_MASK,_cpl
call _syscall
/*
* Return via _doreti to handle ASTs.
*/
pushl $0 /* cpl to restore */
subl $4,%esp
movb $1,_intr_nesting_level
MEXITCOUNT
jmp _doreti
/*
* Include what was once config+isa-dependent code.
* XXX it should be in a stand-alone file. It's still icu-dependent and
* belongs in i386/isa.
*/
#ifdef PC98
#include "pc98/pc98/vector.s"
#else
#include "i386/isa/vector.s"
#endif
/*
* Include what was once icu-dependent code.
* XXX it should be merged into this file (also move the definition of
* imen to vector.s or isa.c).
* Before including it, set up a normal asm environment so that vector.s
* doesn't have to know that stuff is included after it.
*/
.data
ALIGN_DATA
.text
SUPERALIGN_TEXT
#ifdef PC98
#include "pc98/pc98/icu.s"
#else
#include "i386/isa/icu.s"
#endif

View File

@ -32,22 +32,20 @@
* SUCH DAMAGE.
*
* from: Steve McCanne's microtime code
* $Id: microtime.s,v 1.4 1996/09/07 02:13:34 asami Exp $
* $Id: microtime.s,v 1.5 1996/10/09 19:47:38 bde Exp $
*/
#include "opt_cpu.h"
#include <machine/asmacros.h>
#include <machine/clock.h>
#include <i386/isa/icu.h>
#ifdef PC98
#include <pc98/pc98/pc98.h>
#include <pc98/pc98/timerreg.h>
#else
#include <i386/isa/isa.h>
#include <i386/isa/timerreg.h>
#endif
#include <i386/isa/timerreg.h>
ENTRY(microtime)

View File

@ -46,7 +46,7 @@
** (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: userconfig.c,v 1.8 1996/10/23 07:25:04 asami Exp $
** $Id: userconfig.c,v 1.9 1996/10/29 08:36:17 asami Exp $
**/
/**
@ -244,7 +244,7 @@ static DEV_INFO device_info[] = {
{"aha", "Adaptec 154x SCSI controller", 0, CLS_STORAGE},
{"uha", "Ultrastor 14F/24F/34F SCSI controller",0, CLS_STORAGE},
{"aic", "Adaptec 152x SCSI and compatible sound cards", 0, CLS_STORAGE},
{"nca", "ProAudio Spectrum SCSI and comaptibles", 0, CLS_STORAGE},
{"nca", "ProAudio Spectrum SCSI and compatibles", 0, CLS_STORAGE},
{"sea", "Seagate ST01/ST02 SCSI and compatibles", 0, CLS_STORAGE},
{"wds", "Western Digitial WD7000 SCSI controller", 0, CLS_STORAGE},
{"ncr", "NCR 53C810 SCSI controller", FLG_FIXED, CLS_STORAGE},
@ -2247,7 +2247,7 @@ visuserconfig(void)
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
* $Id: userconfig.c,v 1.8 1996/10/23 07:25:04 asami Exp $
* $Id: userconfig.c,v 1.9 1996/10/29 08:36:17 asami Exp $
*/
#include "scbus.h"

View File

@ -1,864 +0,0 @@
/*-
* Copyright (c) 1982, 1986 The Regents of the University of California.
* Copyright (c) 1989, 1990 William Jolitz
* Copyright (c) 1994 John Dyson
* All rights reserved.
*
* This code is derived from software contributed to Berkeley by
* the Systems Programming Group of the University of Utah Computer
* Science Department, and William Jolitz.
*
* 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 the University of
* California, Berkeley and its contributors.
* 4. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE REGENTS 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 REGENTS 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.
*
* from: @(#)vm_machdep.c 7.3 (Berkeley) 5/13/91
* Utah $Hdr: vm_machdep.c 1.16.1.1 89/06/23$
* $Id: vm_machdep.c,v 1.5 1996/10/09 21:46:03 asami Exp $
*/
#include "npx.h"
#include "opt_bounce.h"
#include <sys/param.h>
#include <sys/systm.h>
#include <sys/proc.h>
#include <sys/malloc.h>
#include <sys/buf.h>
#include <sys/vnode.h>
#include <sys/vmmeter.h>
#include <machine/clock.h>
#include <machine/md_var.h>
#include <vm/vm.h>
#include <vm/vm_param.h>
#include <vm/vm_prot.h>
#include <vm/lock.h>
#include <vm/vm_kern.h>
#include <vm/vm_page.h>
#include <vm/vm_map.h>
#include <vm/vm_extern.h>
#include <sys/user.h>
#ifdef PC98
#include <pc98/pc98/pc98.h>
#include <pc98/pc98/epsonio.h>
#else
#include <i386/isa/isa.h>
#endif
#ifdef BOUNCE_BUFFERS
static vm_offset_t
vm_bounce_kva __P((int size, int waitok));
static void vm_bounce_kva_free __P((vm_offset_t addr, vm_offset_t size,
int now));
static vm_offset_t
vm_bounce_page_find __P((int count));
static void vm_bounce_page_free __P((vm_offset_t pa, int count));
static volatile int kvasfreecnt;
caddr_t bouncememory;
int bouncepages;
static int bpwait;
static vm_offset_t *bouncepa;
static int bmwait, bmfreeing;
#define BITS_IN_UNSIGNED (8*sizeof(unsigned))
static int bounceallocarraysize;
static unsigned *bounceallocarray;
static int bouncefree;
#if defined(PC98) && defined (EPSON_BOUNCEDMA)
#define SIXTEENMEG (3840*4096) /* 15MB boundary */
#else
#define SIXTEENMEG (4096*4096)
#endif
#define MAXBKVA 1024
int maxbkva = MAXBKVA*PAGE_SIZE;
/* special list that can be used at interrupt time for eventual kva free */
static struct kvasfree {
vm_offset_t addr;
vm_offset_t size;
} kvaf[MAXBKVA];
/*
* get bounce buffer pages (count physically contiguous)
* (only 1 inplemented now)
*/
static vm_offset_t
vm_bounce_page_find(count)
int count;
{
int bit;
int s,i;
if (count != 1)
panic("vm_bounce_page_find -- no support for > 1 page yet!!!");
s = splbio();
retry:
for (i = 0; i < bounceallocarraysize; i++) {
if (bounceallocarray[i] != 0xffffffff) {
bit = ffs(~bounceallocarray[i]);
if (bit) {
bounceallocarray[i] |= 1 << (bit - 1) ;
bouncefree -= count;
splx(s);
return bouncepa[(i * BITS_IN_UNSIGNED + (bit - 1))];
}
}
}
bpwait = 1;
tsleep((caddr_t) &bounceallocarray, PRIBIO, "bncwai", 0);
goto retry;
}
static void
vm_bounce_kva_free(addr, size, now)
vm_offset_t addr;
vm_offset_t size;
int now;
{
int s = splbio();
kvaf[kvasfreecnt].addr = addr;
kvaf[kvasfreecnt].size = size;
++kvasfreecnt;
if( now) {
/*
* this will do wakeups
*/
vm_bounce_kva(0,0);
} else {
if (bmwait) {
/*
* if anyone is waiting on the bounce-map, then wakeup
*/
wakeup((caddr_t) io_map);
bmwait = 0;
}
}
splx(s);
}
/*
* free count bounce buffer pages
*/
static void
vm_bounce_page_free(pa, count)
vm_offset_t pa;
int count;
{
int allocindex;
int index;
int bit;
if (count != 1)
panic("vm_bounce_page_free -- no support for > 1 page yet!!!");
for(index=0;index<bouncepages;index++) {
if( pa == bouncepa[index])
break;
}
if( index == bouncepages)
panic("vm_bounce_page_free: invalid bounce buffer");
allocindex = index / BITS_IN_UNSIGNED;
bit = index % BITS_IN_UNSIGNED;
bounceallocarray[allocindex] &= ~(1 << bit);
bouncefree += count;
if (bpwait) {
bpwait = 0;
wakeup((caddr_t) &bounceallocarray);
}
}
/*
* allocate count bounce buffer kva pages
*/
static vm_offset_t
vm_bounce_kva(size, waitok)
int size;
int waitok;
{
int i;
vm_offset_t kva = 0;
vm_offset_t off;
int s = splbio();
more:
if (!bmfreeing && kvasfreecnt) {
bmfreeing = 1;
for (i = 0; i < kvasfreecnt; i++) {
for(off=0;off<kvaf[i].size;off+=PAGE_SIZE) {
pmap_kremove( kvaf[i].addr + off);
}
kmem_free_wakeup(io_map, kvaf[i].addr,
kvaf[i].size);
}
kvasfreecnt = 0;
bmfreeing = 0;
if( bmwait) {
bmwait = 0;
wakeup( (caddr_t) io_map);
}
}
if( size == 0) {
splx(s);
return 0;
}
if ((kva = kmem_alloc_pageable(io_map, size)) == 0) {
if( !waitok) {
splx(s);
return 0;
}
bmwait = 1;
tsleep((caddr_t) io_map, PRIBIO, "bmwait", 0);
goto more;
}
splx(s);
return kva;
}
/*
* same as vm_bounce_kva -- but really allocate (but takes pages as arg)
*/
vm_offset_t
vm_bounce_kva_alloc(count)
int count;
{
int i;
vm_offset_t kva;
vm_offset_t pa;
if( bouncepages == 0) {
kva = (vm_offset_t) malloc(count*PAGE_SIZE, M_TEMP, M_WAITOK);
return kva;
}
kva = vm_bounce_kva(count*PAGE_SIZE, 1);
for(i=0;i<count;i++) {
pa = vm_bounce_page_find(1);
pmap_kenter(kva + i * PAGE_SIZE, pa);
}
return kva;
}
/*
* same as vm_bounce_kva_free -- but really free
*/
void
vm_bounce_kva_alloc_free(kva, count)
vm_offset_t kva;
int count;
{
int i;
vm_offset_t pa;
if( bouncepages == 0) {
free((caddr_t) kva, M_TEMP);
return;
}
for(i = 0; i < count; i++) {
pa = pmap_kextract(kva + i * PAGE_SIZE);
vm_bounce_page_free(pa, 1);
}
vm_bounce_kva_free(kva, count*PAGE_SIZE, 0);
}
/*
* do the things necessary to the struct buf to implement
* bounce buffers... inserted before the disk sort
*/
void
vm_bounce_alloc(bp)
struct buf *bp;
{
int countvmpg;
vm_offset_t vastart, vaend;
vm_offset_t vapstart, vapend;
vm_offset_t va, kva;
vm_offset_t pa;
int dobounceflag = 0;
int i;
if (bouncepages == 0)
return;
if (bp->b_flags & B_BOUNCE) {
printf("vm_bounce_alloc: called recursively???\n");
return;
}
if (bp->b_bufsize < bp->b_bcount) {
printf(
"vm_bounce_alloc: b_bufsize(0x%lx) < b_bcount(0x%lx) !!\n",
bp->b_bufsize, bp->b_bcount);
panic("vm_bounce_alloc");
}
/*
* This is not really necessary
* if( bp->b_bufsize != bp->b_bcount) {
* printf("size: %d, count: %d\n", bp->b_bufsize, bp->b_bcount);
* }
*/
vastart = (vm_offset_t) bp->b_data;
vaend = (vm_offset_t) bp->b_data + bp->b_bufsize;
vapstart = trunc_page(vastart);
vapend = round_page(vaend);
countvmpg = (vapend - vapstart) / PAGE_SIZE;
/*
* if any page is above 16MB, then go into bounce-buffer mode
*/
va = vapstart;
for (i = 0; i < countvmpg; i++) {
pa = pmap_kextract(va);
if (pa >= SIXTEENMEG)
++dobounceflag;
if( pa == 0)
panic("vm_bounce_alloc: Unmapped page");
va += PAGE_SIZE;
}
if (dobounceflag == 0)
return;
if (bouncepages < dobounceflag)
panic("Not enough bounce buffers!!!");
/*
* allocate a replacement kva for b_addr
*/
kva = vm_bounce_kva(countvmpg*PAGE_SIZE, 1);
#if 0
printf("%s: vapstart: %x, vapend: %x, countvmpg: %d, kva: %x ",
(bp->b_flags & B_READ) ? "read":"write",
vapstart, vapend, countvmpg, kva);
#endif
va = vapstart;
for (i = 0; i < countvmpg; i++) {
pa = pmap_kextract(va);
if (pa >= SIXTEENMEG) {
/*
* allocate a replacement page
*/
vm_offset_t bpa = vm_bounce_page_find(1);
pmap_kenter(kva + (PAGE_SIZE * i), bpa);
#if 0
printf("r(%d): (%x,%x,%x) ", i, va, pa, bpa);
#endif
/*
* if we are writing, the copy the data into the page
*/
if ((bp->b_flags & B_READ) == 0) {
bcopy((caddr_t) va, (caddr_t) kva + (PAGE_SIZE * i), PAGE_SIZE);
}
} else {
/*
* use original page
*/
pmap_kenter(kva + (PAGE_SIZE * i), pa);
}
va += PAGE_SIZE;
}
/*
* flag the buffer as being bounced
*/
bp->b_flags |= B_BOUNCE;
/*
* save the original buffer kva
*/
bp->b_savekva = bp->b_data;
/*
* put our new kva into the buffer (offset by original offset)
*/
bp->b_data = (caddr_t) (((vm_offset_t) kva) |
((vm_offset_t) bp->b_savekva & PAGE_MASK));
#if 0
printf("b_savekva: %x, newva: %x\n", bp->b_savekva, bp->b_data);
#endif
return;
}
/*
* hook into biodone to free bounce buffer
*/
void
vm_bounce_free(bp)
struct buf *bp;
{
int i;
vm_offset_t origkva, bouncekva, bouncekvaend;
/*
* if this isn't a bounced buffer, then just return
*/
if ((bp->b_flags & B_BOUNCE) == 0)
return;
/*
* This check is not necessary
* if (bp->b_bufsize != bp->b_bcount) {
* printf("vm_bounce_free: b_bufsize=%d, b_bcount=%d\n",
* bp->b_bufsize, bp->b_bcount);
* }
*/
origkva = (vm_offset_t) bp->b_savekva;
bouncekva = (vm_offset_t) bp->b_data;
/*
printf("free: %d ", bp->b_bufsize);
*/
/*
* check every page in the kva space for b_addr
*/
for (i = 0; i < bp->b_bufsize; ) {
vm_offset_t mybouncepa;
vm_offset_t copycount;
copycount = round_page(bouncekva + 1) - bouncekva;
mybouncepa = pmap_kextract(trunc_page(bouncekva));
/*
* if this is a bounced pa, then process as one
*/
if ( mybouncepa != pmap_kextract( trunc_page( origkva))) {
vm_offset_t tocopy = copycount;
if (i + tocopy > bp->b_bufsize)
tocopy = bp->b_bufsize - i;
/*
* if this is a read, then copy from bounce buffer into original buffer
*/
if (bp->b_flags & B_READ)
bcopy((caddr_t) bouncekva, (caddr_t) origkva, tocopy);
/*
* free the bounce allocation
*/
/*
printf("(kva: %x, pa: %x)", bouncekva, mybouncepa);
*/
vm_bounce_page_free(mybouncepa, 1);
}
origkva += copycount;
bouncekva += copycount;
i += copycount;
}
/*
printf("\n");
*/
/*
* add the old kva into the "to free" list
*/
bouncekva= trunc_page((vm_offset_t) bp->b_data);
bouncekvaend= round_page((vm_offset_t)bp->b_data + bp->b_bufsize);
/*
printf("freeva: %d\n", (bouncekvaend - bouncekva) / PAGE_SIZE);
*/
vm_bounce_kva_free( bouncekva, (bouncekvaend - bouncekva), 0);
bp->b_data = bp->b_savekva;
bp->b_savekva = 0;
bp->b_flags &= ~B_BOUNCE;
return;
}
/*
* init the bounce buffer system
*/
void
vm_bounce_init()
{
int i;
kvasfreecnt = 0;
if (bouncepages == 0)
return;
bounceallocarraysize = (bouncepages + BITS_IN_UNSIGNED - 1) / BITS_IN_UNSIGNED;
bounceallocarray = malloc(bounceallocarraysize * sizeof(unsigned), M_TEMP, M_NOWAIT);
if (!bounceallocarray)
panic("Cannot allocate bounce resource array");
bouncepa = malloc(bouncepages * sizeof(vm_offset_t), M_TEMP, M_NOWAIT);
if (!bouncepa)
panic("Cannot allocate physical memory array");
for(i=0;i<bounceallocarraysize;i++) {
bounceallocarray[i] = 0xffffffff;
}
for(i=0;i<bouncepages;i++) {
vm_offset_t pa;
if( (pa = pmap_kextract((vm_offset_t) bouncememory + i * PAGE_SIZE)) >= SIXTEENMEG)
panic("bounce memory out of range");
if( pa == 0)
panic("bounce memory not resident");
bouncepa[i] = pa;
bounceallocarray[i/(8*sizeof(int))] &= ~(1<<(i%(8*sizeof(int))));
}
bouncefree = bouncepages;
}
#endif /* BOUNCE_BUFFERS */
/*
* quick version of vm_fault
*/
void
vm_fault_quick(v, prot)
caddr_t v;
int prot;
{
if (prot & VM_PROT_WRITE)
subyte(v, fubyte(v));
else
fubyte(v);
}
/*
* Finish a fork operation, with process p2 nearly set up.
* Copy and update the kernel stack and pcb, making the child
* ready to run, and marking it so that it can return differently
* than the parent. Returns 1 in the child process, 0 in the parent.
* We currently double-map the user area so that the stack is at the same
* address in each process; in the future we will probably relocate
* the frame pointers on the stack after copying.
*/
int
cpu_fork(p1, p2)
register struct proc *p1, *p2;
{
struct pcb *pcb2 = &p2->p_addr->u_pcb;
int sp, offset;
volatile int retval;
/*
* Copy pcb and stack from proc p1 to p2.
* We do this as cheaply as possible, copying only the active
* part of the stack. The stack and pcb need to agree;
* this is tricky, as the final pcb is constructed by savectx,
* but its frame isn't yet on the stack when the stack is copied.
* This should be done differently, with a single call
* that copies and updates the pcb+stack,
* replacing the bcopy and savectx.
*/
__asm __volatile("movl %%esp,%0" : "=r" (sp));
offset = sp - (int)kstack;
retval = 1; /* return 1 in child */
bcopy((caddr_t)kstack + offset, (caddr_t)p2->p_addr + offset,
(unsigned) ctob(UPAGES) - offset);
p2->p_md.md_regs = p1->p_md.md_regs;
*pcb2 = p1->p_addr->u_pcb;
pcb2->pcb_cr3 = vtophys(p2->p_vmspace->vm_pmap.pm_pdir);
retval = 0; /* return 0 in parent */
savectx(pcb2);
return (retval);
}
void
cpu_exit(p)
register struct proc *p;
{
#ifdef USER_LDT
struct pcb *pcb;
#endif
#if NNPX > 0
npxexit(p);
#endif /* NNPX */
#ifdef USER_LDT
pcb = &p->p_addr->u_pcb;
if (pcb->pcb_ldt != 0) {
if (pcb == curpcb)
lldt(GSEL(GUSERLDT_SEL, SEL_KPL));
kmem_free(kernel_map, (vm_offset_t)pcb->pcb_ldt,
pcb->pcb_ldt_len * sizeof(union descriptor));
pcb->pcb_ldt_len = (int)pcb->pcb_ldt = 0;
}
#endif
cnt.v_swtch++;
cpu_switch(p);
panic("cpu_exit");
}
void
cpu_wait(p)
struct proc *p;
{
/* drop per-process resources */
pmap_dispose_proc(p);
vmspace_free(p->p_vmspace);
}
/*
* Dump the machine specific header information at the start of a core dump.
*/
int
cpu_coredump(p, vp, cred)
struct proc *p;
struct vnode *vp;
struct ucred *cred;
{
return (vn_rdwr(UIO_WRITE, vp, (caddr_t) p->p_addr, ctob(UPAGES),
(off_t)0, UIO_SYSSPACE, IO_NODELOCKED|IO_UNIT, cred, (int *)NULL,
p));
}
#ifdef notyet
static void
setredzone(pte, vaddr)
u_short *pte;
caddr_t vaddr;
{
/* eventually do this by setting up an expand-down stack segment
for ss0: selector, allowing stack access down to top of u.
this means though that protection violations need to be handled
thru a double fault exception that must do an integral task
switch to a known good context, within which a dump can be
taken. a sensible scheme might be to save the initial context
used by sched (that has physical memory mapped 1:1 at bottom)
and take the dump while still in mapped mode */
}
#endif
/*
* Convert kernel VA to physical address
*/
u_long
kvtop(void *addr)
{
vm_offset_t va;
va = pmap_kextract((vm_offset_t)addr);
if (va == 0)
panic("kvtop: zero page frame");
return((int)va);
}
/*
* Map an IO request into kernel virtual address space.
*
* All requests are (re)mapped into kernel VA space.
* Notice that we use b_bufsize for the size of the buffer
* to be mapped. b_bcount might be modified by the driver.
*/
void
vmapbuf(bp)
register struct buf *bp;
{
register caddr_t addr, v, kva;
vm_offset_t pa;
if ((bp->b_flags & B_PHYS) == 0)
panic("vmapbuf");
for (v = bp->b_saveaddr, addr = (caddr_t)trunc_page(bp->b_data);
addr < bp->b_data + bp->b_bufsize;
addr += PAGE_SIZE, v += PAGE_SIZE) {
/*
* Do the vm_fault if needed; do the copy-on-write thing
* when reading stuff off device into memory.
*/
vm_fault_quick(addr,
(bp->b_flags&B_READ)?(VM_PROT_READ|VM_PROT_WRITE):VM_PROT_READ);
pa = trunc_page(pmap_kextract((vm_offset_t) addr));
if (pa == 0)
panic("vmapbuf: page not present");
vm_page_hold(PHYS_TO_VM_PAGE(pa));
pmap_kenter((vm_offset_t) v, pa);
}
kva = bp->b_saveaddr;
bp->b_saveaddr = bp->b_data;
bp->b_data = kva + (((vm_offset_t) bp->b_data) & PAGE_MASK);
}
/*
* Free the io map PTEs associated with this IO operation.
* We also invalidate the TLB entries and restore the original b_addr.
*/
void
vunmapbuf(bp)
register struct buf *bp;
{
register caddr_t addr;
vm_offset_t pa;
if ((bp->b_flags & B_PHYS) == 0)
panic("vunmapbuf");
for (addr = (caddr_t)trunc_page(bp->b_data);
addr < bp->b_data + bp->b_bufsize;
addr += PAGE_SIZE) {
pa = trunc_page(pmap_kextract((vm_offset_t) addr));
pmap_kremove((vm_offset_t) addr);
vm_page_unhold(PHYS_TO_VM_PAGE(pa));
}
bp->b_data = bp->b_saveaddr;
}
/*
* Force reset the processor by invalidating the entire address space!
*/
void
cpu_reset() {
#ifdef PC98
asm(" cli ");
outb(0x37, 0x0f); /* SHUT 0 = 0 */
outb(0x37, 0x0b); /* SHUT 1 = 0 */
if ((pc98_machine_type & M_EPSON_PC98)
&& (epson_machine_id == 0x20 /*note A*/)) {
epson_outb(0xc17, epson_inb(0xc17) | 0x40);
/* reset port for NOTE_A */
}
outb(0xf0, 0x00); /* reset port */
#else /* IBM-PC */
/*
* Attempt to do a CPU reset via the keyboard controller,
* do not turn of the GateA20, as any machine that fails
* to do the reset here would then end up in no man's land.
*/
#ifndef BROKEN_KEYBOARD_RESET
outb(IO_KBD + 4, 0xFE);
DELAY(500000); /* wait 0.5 sec to see if that did it */
printf("Keyboard reset did not work, attempting CPU shutdown\n");
DELAY(1000000); /* wait 1 sec for printf to complete */
#endif
/* force a shutdown by unmapping entire address space ! */
bzero((caddr_t) PTD, PAGE_SIZE);
/* "good night, sweet prince .... <THUNK!>" */
invltlb();
#endif
/* NOTREACHED */
while(1);
}
/*
* Grow the user stack to allow for 'sp'. This version grows the stack in
* chunks of SGROWSIZ.
*/
int
grow(p, sp)
struct proc *p;
u_int sp;
{
unsigned int nss;
caddr_t v;
struct vmspace *vm = p->p_vmspace;
if ((caddr_t)sp <= vm->vm_maxsaddr || (unsigned)sp >= (unsigned)USRSTACK)
return (1);
nss = roundup(USRSTACK - (unsigned)sp, PAGE_SIZE);
if (nss > p->p_rlimit[RLIMIT_STACK].rlim_cur)
return (0);
if (vm->vm_ssize && roundup(vm->vm_ssize << PAGE_SHIFT,
SGROWSIZ) < nss) {
int grow_amount;
/*
* If necessary, grow the VM that the stack occupies
* to allow for the rlimit. This allows us to not have
* to allocate all of the VM up-front in execve (which
* is expensive).
* Grow the VM by the amount requested rounded up to
* the nearest SGROWSIZ to provide for some hysteresis.
*/
grow_amount = roundup((nss - (vm->vm_ssize << PAGE_SHIFT)), SGROWSIZ);
v = (char *)USRSTACK - roundup(vm->vm_ssize << PAGE_SHIFT,
SGROWSIZ) - grow_amount;
/*
* If there isn't enough room to extend by SGROWSIZ, then
* just extend to the maximum size
*/
if (v < vm->vm_maxsaddr) {
v = vm->vm_maxsaddr;
grow_amount = MAXSSIZ - (vm->vm_ssize << PAGE_SHIFT);
}
if ((grow_amount == 0) || (vm_map_find(&vm->vm_map, NULL, 0, (vm_offset_t *)&v,
grow_amount, FALSE, VM_PROT_ALL, VM_PROT_ALL, 0) != KERN_SUCCESS)) {
return (0);
}
vm->vm_ssize += grow_amount >> PAGE_SHIFT;
}
return (1);
}
/*
* prototype routine to implement the pre-zeroed page mechanism
* this routine is called from the idle loop.
*/
int
vm_page_zero_idle() {
vm_page_t m;
static int free_rover = 0;
if ((cnt.v_free_count > cnt.v_interrupt_free_min) &&
(m = vm_page_list_find(PQ_FREE, free_rover))) {
--(*vm_page_queues[m->queue].lcnt);
TAILQ_REMOVE(vm_page_queues[m->queue].pl, m, pageq);
enable_intr();
pmap_zero_page(VM_PAGE_TO_PHYS(m));
disable_intr();
m->queue = PQ_ZERO + m->pc;
++(*vm_page_queues[m->queue].lcnt);
TAILQ_INSERT_HEAD(vm_page_queues[m->queue].pl, m, pageq);
free_rover = (free_rover + PQ_PRIME3) & PQ_L2_MASK;
++vm_page_zero_count;
return 1;
}
return 0;
}

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

View File

@ -17,6 +17,18 @@
/*
* Disk Controller ATAPI register definitions.
*/
#ifdef PC98
#define AR_DATA 0x0 /* RW - data register (16 bits) */
#define AR_ERROR 0x2 /* R - error register */
#define AR_FEATURES 0x2 /* W - features */
#define AR_IREASON 0x4 /* RW - interrupt reason */
#define AR_TAG 0x6 /* - reserved for SAM TAG byte */
#define AR_CNTLO 0x8 /* RW - byte count, low byte */
#define AR_CNTHI 0xa /* RW - byte count, high byte */
#define AR_DRIVE 0xc /* RW - drive select */
#define AR_COMMAND 0xe /* W - command register */
#define AR_STATUS 0xe /* R - immediate status */
#else
#define AR_DATA 0x0 /* RW - data register (16 bits) */
#define AR_ERROR 0x1 /* R - error register */
#define AR_FEATURES 0x1 /* W - features */
@ -27,6 +39,7 @@
#define AR_DRIVE 0x6 /* RW - drive select */
#define AR_COMMAND 0x7 /* W - command register */
#define AR_STATUS 0x7 /* R - immediate status */
#endif
/*
* Status register bits

View File

@ -34,7 +34,11 @@
* SUCH DAMAGE.
*
* from: @(#)clock.c 7.2 (Berkeley) 5/12/91
* $Id: clock.c,v 1.8 1996/10/23 07:25:13 asami Exp $
* $Id: clock.c,v 1.9 1996/10/29 08:36:19 asami Exp $
*/
/*
* Routines to handle clock hardware.
*/
/*
@ -48,10 +52,6 @@
* modified for PC98 by Kakefuda
*/
/*
* Primitive clock interrupt routines.
*/
#include "opt_clock.h"
#include "opt_cpu.h"
@ -72,13 +72,12 @@
#ifdef PC98
#include <pc98/pc98/pc98.h>
#include <i386/isa/isa_device.h>
#include <pc98/pc98/timerreg.h>
#else
#include <i386/isa/isa.h>
#include <i386/isa/isa_device.h>
#include <i386/isa/rtc.h>
#include <i386/isa/timerreg.h>
#endif
#include <i386/isa/timerreg.h>
/*
* 32-bit time_t's can't reach leap years before 1904 or after 2036, so we
@ -109,52 +108,49 @@
int adjkerntz; /* local offset from GMT in seconds */
int disable_rtc_set; /* disable resettodr() if != 0 */
int wall_cmos_clock; /* wall CMOS clock assumed if != 0 */
u_int idelayed;
#if defined(I586_CPU) || defined(I686_CPU)
u_int i586_ctr_bias;
u_int i586_ctr_bias;
u_int i586_ctr_comultiplier;
u_int i586_ctr_freq;
u_int i586_ctr_multiplier;
long long i586_last_tick;
unsigned long i586_avg_tick;
#endif
int statclock_disable;
u_int stat_imask = SWI_CLOCK_MASK;
#ifdef TIMER_FREQ
static u_int timer_freq = TIMER_FREQ;
u_int timer_freq = TIMER_FREQ;
#else
#ifdef PC98
#ifndef AUTO_CLOCK
#ifndef PC98_8M
static u_int timer_freq = 2457600;
u_int timer_freq = 2457600;
#else /* !PC98_8M */
static u_int timer_freq = 1996800;
u_int timer_freq = 1996800;
#endif /* PC98_8M */
#else /* AUTO_CLOCK */
static u_int timer_freq = 2457600;
u_int timer_freq = 2457600;
#endif /* AUTO_CLOCK */
#else /* IBM-PC */
static u_int timer_freq = 1193182;
u_int timer_freq = 1193182;
#endif /* PC98 */
#endif
int timer0_max_count;
u_int timer0_overflow_threshold;
u_int timer0_prescaler_count;
int timer0_max_count;
u_int timer0_overflow_threshold;
u_int timer0_prescaler_count;
int wall_cmos_clock; /* wall CMOS clock assumed if != 0 */
static int beeping = 0;
static u_int clk_imask = HWI_MASK | SWI_MASK;
static const u_char daysinmonth[] = {31,28,31,30,31,30,31,31,30,31,30,31};
static u_int hardclock_max_count;
static u_int hardclock_max_count;
/*
* XXX new_function and timer_func should not handle clockframes, but
* timer_func currently needs to hold hardclock to handle the
* timer0_state == 0 case. We should use register_intr()/unregister_intr()
* to switch between clkintr() and a slightly different timerintr().
*/
static void (*new_function) __P((struct clockframe *frame));
static u_int new_rate;
static void (*new_function) __P((struct clockframe *frame));
static u_int new_rate;
#ifndef PC98
static u_char rtc_statusa = RTCSA_DIVIDER | RTCSA_NOPROF;
static u_char rtc_statusb = RTCSB_24HR | RTCSB_PINTR;
@ -171,7 +167,7 @@ static u_char timer0_state;
static u_char timer1_state;
#endif
static u_char timer2_state;
static void (*timer_func) __P((struct clockframe *frame)) = hardclock;
static void (*timer_func) __P((struct clockframe *frame)) = hardclock;
int rtc_inb __P((void));
#if defined(I586_CPU) || defined(I686_CPU)
@ -437,7 +433,7 @@ getit(void)
disable_intr();
/* Select timer0 and latch counter value. */
outb(TIMER_MODE, TIMER_SEL0);
outb(TIMER_MODE, TIMER_SEL0 | TIMER_LATCH);
low = inb(TIMER_CNTR0);
high = inb(TIMER_CNTR0);
@ -625,7 +621,7 @@ calibrate_clocks(void)
u_int count, prev_count, tot_count;
int sec, start_sec, timeout;
printf("Calibrating clock(s) relative to mc146818A clock...\n");
printf("Calibrating clock(s) relative to mc146818A clock ... ");
if (!(rtcin(RTC_STATUSD) & RTCSD_PWR))
goto fail;
timeout = 100000000;
@ -782,7 +778,7 @@ startrtclock()
if (delta < timer_freq / 100) {
#ifndef CLK_USE_I8254_CALIBRATION
if (bootverbose)
printf(
printf(
"CLK_USE_I8254_CALIBRATION not specified - using default frequency\n");
freq = timer_freq;
#endif
@ -802,7 +798,7 @@ startrtclock()
#ifndef CLK_USE_I586_CALIBRATION
if (i586_ctr_freq != 0) {
if (bootverbose)
printf(
printf(
"CLK_USE_I586_CALIBRATION not specified - using old calibration method\n");
i586_ctr_freq = 0;
}
@ -1114,10 +1110,8 @@ cpu_initclocks()
/*
* Finish setting up anti-jitter measures.
*/
if (i586_ctr_freq != 0) {
i586_last_tick = rdtsc();
i586_ctr_bias = i586_last_tick;
}
if (i586_ctr_freq != 0)
i586_ctr_bias = rdtsc();
#endif
#ifndef PC98

View File

@ -1,357 +0,0 @@
/*-
* Copyright (c) 1989, 1990 William F. Jolitz.
* Copyright (c) 1990 The Regents of the University of California.
* All rights reserved.
*
* This code is derived from software contributed to Berkeley by
* William Jolitz.
*
* 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 the University of
* California, Berkeley and its contributors.
* 4. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE REGENTS 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 REGENTS 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.
*
* @(#)icu.s 7.2 (Berkeley) 5/21/91
*
* $Id: icu.s,v 1.25 1996/05/31 01:08:07 peter Exp $
*/
/*
* AT/386
* Vector interrupt control section
*/
/*
* XXX this file should be named ipl.s. All spls are now soft and the
* only thing related to the hardware icu is that the h/w interrupt
* numbers are used without translation in the masks.
*/
.data
.globl _cpl
_cpl: .long HWI_MASK | SWI_MASK /* current priority (all off) */
.globl _imen
_imen: .long HWI_MASK /* interrupt mask enable (all h/w off) */
.globl _tty_imask
_tty_imask: .long 0
.globl _bio_imask
_bio_imask: .long 0
.globl _net_imask
_net_imask: .long 0
.globl _ipending
_ipending: .long 0
.globl _netisr
_netisr: .long 0 /* set with bits for which queue to service */
.globl _netisrs
_netisrs:
.long dummynetisr, dummynetisr, dummynetisr, dummynetisr
.long dummynetisr, dummynetisr, dummynetisr, dummynetisr
.long dummynetisr, dummynetisr, dummynetisr, dummynetisr
.long dummynetisr, dummynetisr, dummynetisr, dummynetisr
.long dummynetisr, dummynetisr, dummynetisr, dummynetisr
.long dummynetisr, dummynetisr, dummynetisr, dummynetisr
.long dummynetisr, dummynetisr, dummynetisr, dummynetisr
.long dummynetisr, dummynetisr, dummynetisr, dummynetisr
vec:
.long vec0, vec1, vec2, vec3, vec4, vec5, vec6, vec7
.long vec8, vec9, vec10, vec11, vec12, vec13, vec14, vec15
.text
/*
* Handle return from interrupts, traps and syscalls.
*/
SUPERALIGN_TEXT
_doreti:
FAKE_MCOUNT(_bintr) /* init "from" _bintr -> _doreti */
addl $4,%esp /* discard unit number */
popl %eax /* cpl to restore */
doreti_next:
/*
* Check for pending HWIs and SWIs atomically with restoring cpl
* and exiting. The check has to be atomic with exiting to stop
* (ipending & ~cpl) changing from zero to nonzero while we're
* looking at it (this wouldn't be fatal but it would increase
* interrupt latency). Restoring cpl has to be atomic with exiting
* so that the stack cannot pile up (the nesting level of interrupt
* handlers is limited by the number of bits in cpl).
*/
movl %eax,%ecx
notl %ecx
cli
andl _ipending,%ecx
jne doreti_unpend
doreti_exit:
movl %eax,_cpl
decb _intr_nesting_level
MEXITCOUNT
.globl doreti_popl_es
doreti_popl_es:
popl %es
.globl doreti_popl_ds
doreti_popl_ds:
popl %ds
popal
addl $8,%esp
.globl doreti_iret
doreti_iret:
iret
ALIGN_TEXT
.globl doreti_iret_fault
doreti_iret_fault:
subl $8,%esp
pushal
pushl %ds
.globl doreti_popl_ds_fault
doreti_popl_ds_fault:
pushl %es
.globl doreti_popl_es_fault
doreti_popl_es_fault:
movl $0,4+4+32+4(%esp) /* XXX should be the error code */
movl $T_PROTFLT,4+4+32+0(%esp)
jmp alltraps_with_regs_pushed
ALIGN_TEXT
doreti_unpend:
/*
* Enabling interrupts is safe because we haven't restored cpl yet.
* The locking from the "btrl" test is probably no longer necessary.
* We won't miss any new pending interrupts because we will check
* for them again.
*/
sti
bsfl %ecx,%ecx /* slow, but not worth optimizing */
btrl %ecx,_ipending
jnc doreti_next /* some intr cleared memory copy */
movl ihandlers(,%ecx,4),%edx
testl %edx,%edx
je doreti_next /* "can't happen" */
cmpl $NHWI,%ecx
jae doreti_swi
cli
movl %eax,_cpl
MEXITCOUNT
jmp %edx
ALIGN_TEXT
doreti_swi:
pushl %eax
/*
* The SWI_AST handler has to run at cpl = SWI_AST_MASK and the
* SWI_CLOCK handler at cpl = SWI_CLOCK_MASK, so we have to restore
* all the h/w bits in cpl now and have to worry about stack growth.
* The worst case is currently (30 Jan 1994) 2 SWI handlers nested
* in dying interrupt frames and about 12 HWIs nested in active
* interrupt frames. There are only 4 different SWIs and the HWI
* and SWI masks limit the nesting further.
*/
orl imasks(,%ecx,4),%eax
movl %eax,_cpl
call %edx
popl %eax
jmp doreti_next
ALIGN_TEXT
swi_ast:
addl $8,%esp /* discard raddr & cpl to get trap frame */
testb $SEL_RPL_MASK,TRAPF_CS_OFF(%esp)
je swi_ast_phantom
movl $T_ASTFLT,(2+8+0)*4(%esp)
call _trap
subl %eax,%eax /* recover cpl */
jmp doreti_next
ALIGN_TEXT
swi_ast_phantom:
/*
* These happen when there is an interrupt in a trap handler before
* ASTs can be masked or in an lcall handler before they can be
* masked or after they are unmasked. They could be avoided for
* trap entries by using interrupt gates, and for lcall exits by
* using by using cli, but they are unavoidable for lcall entries.
*/
cli
orl $SWI_AST_PENDING,_ipending
subl %eax,%eax
jmp doreti_exit /* SWI_AST is highest so we must be done */
/*
* Interrupt priority mechanism
* -- soft splXX masks with group mechanism (cpl)
* -- h/w masks for currently active or unused interrupts (imen)
* -- ipending = active interrupts currently masked by cpl
*/
ENTRY(splz)
/*
* The caller has restored cpl and checked that (ipending & ~cpl)
* is nonzero. We have to repeat the check since if there is an
* interrupt while we're looking, _doreti processing for the
* interrupt will handle all the unmasked pending interrupts
* because we restored early. We're repeating the calculation
* of (ipending & ~cpl) anyway so that the caller doesn't have
* to pass it, so this only costs one "jne". "bsfl %ecx,%ecx"
* is undefined when %ecx is 0 so we can't rely on the secondary
* btrl tests.
*/
movl _cpl,%eax
splz_next:
/*
* We don't need any locking here. (ipending & ~cpl) cannot grow
* while we're looking at it - any interrupt will shrink it to 0.
*/
movl %eax,%ecx
notl %ecx
andl _ipending,%ecx
jne splz_unpend
ret
ALIGN_TEXT
splz_unpend:
bsfl %ecx,%ecx
btrl %ecx,_ipending
jnc splz_next
movl ihandlers(,%ecx,4),%edx
testl %edx,%edx
je splz_next /* "can't happen" */
cmpl $NHWI,%ecx
jae splz_swi
/*
* We would prefer to call the intr handler directly here but that
* doesn't work for badly behaved handlers that want the interrupt
* frame. Also, there's a problem determining the unit number.
* We should change the interface so that the unit number is not
* determined at config time.
*/
jmp *vec(,%ecx,4)
ALIGN_TEXT
splz_swi:
cmpl $SWI_AST,%ecx
je splz_next /* "can't happen" */
pushl %eax
orl imasks(,%ecx,4),%eax
movl %eax,_cpl
call %edx
popl %eax
movl %eax,_cpl
jmp splz_next
/*
* Fake clock interrupt(s) so that they appear to come from our caller instead
* of from here, so that system profiling works.
* XXX do this more generally (for all vectors; look up the C entry point).
* XXX frame bogusness stops us from just jumping to the C entry point.
*/
ALIGN_TEXT
vec0:
popl %eax /* return address */
pushfl
#define KCSEL 8
pushl $KCSEL
pushl %eax
cli
MEXITCOUNT
jmp _Xintr0 /* XXX might need _Xfastintr0 */
#ifndef PC98
ALIGN_TEXT
vec8:
popl %eax
pushfl
pushl $KCSEL
pushl %eax
cli
MEXITCOUNT
jmp _Xintr8 /* XXX might need _Xfastintr8 */
#endif
#define BUILD_VEC(irq_num) \
ALIGN_TEXT ; \
__CONCAT(vec,irq_num): ; \
int $ICU_OFFSET + (irq_num) ; \
ret
BUILD_VEC(1)
BUILD_VEC(2)
BUILD_VEC(3)
BUILD_VEC(4)
BUILD_VEC(5)
BUILD_VEC(6)
BUILD_VEC(7)
#ifdef PC98
BUILD_VEC(8)
#endif
BUILD_VEC(9)
BUILD_VEC(10)
BUILD_VEC(11)
BUILD_VEC(12)
BUILD_VEC(13)
BUILD_VEC(14)
BUILD_VEC(15)
ALIGN_TEXT
swi_net:
MCOUNT
bsfl _netisr,%eax
je swi_net_done
swi_net_more:
btrl %eax,_netisr
jnc swi_net_next
call *_netisrs(,%eax,4)
swi_net_next:
bsfl _netisr,%eax
jne swi_net_more
swi_net_done:
ret
ALIGN_TEXT
dummynetisr:
MCOUNT
ret
/*
* XXX there should be a registration function to put the handler for the
* attached driver directly in ihandlers. Then this function will go away.
*/
ALIGN_TEXT
swi_tty:
MCOUNT
#include "cy.h"
#if NCY > 0
call _cypoll
#endif
#include "rc.h"
#if NRC > 0
call _rcpoll
#endif
#include "sio.h"
#if NSIO > 0
jmp _siopoll
#else
ret
#endif

View File

@ -24,7 +24,7 @@
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
* $Id: if_ed.c,v 1.9 1996/10/23 07:25:17 asami Exp $
* $Id: if_ed.c,v 1.10 1996/10/29 08:36:20 asami Exp $
*/
/*
@ -106,7 +106,17 @@
#include <i386/isa/if_edreg.h>
#ifdef PC98
#include <pc98/pc98/if_ed98.h>
/* register offsets */
struct pc98_edregister {
u_int *port;
u_int ioskip;
u_int nic_offset;
u_int asic_offset;
u_int data;
u_int reset;
u_int pc_misc;
u_int pc_reset;
};
#endif
/*
@ -160,12 +170,16 @@ struct ed_softc {
u_char next_packet; /* pointer to next unread RX packet */
struct ifmib_iso_8802_3 mibdata; /* stuff for network mgmt */
#ifdef PC98
int unit;
struct pc98_edregister edreg; /* I/O port register offset info */
#endif
};
static struct ed_softc ed_softc[NED];
#ifdef PC98
#include <pc98/pc98/if_ed98.h>
#endif
static int ed_attach __P((struct ed_softc *, int, int));
static int ed_attach_isa __P((struct isa_device *));
@ -421,10 +435,6 @@ ed_probe(isa_dev)
{
int nports;
#ifdef PC98
ed_softc[isa_dev->id_unit].unit = isa_dev->id_unit;
#endif
#if NCRD > 0
/*
* If PC-Card probe required, then register driver with
@ -443,7 +453,7 @@ ed_probe(isa_dev)
if ((ED_TYPE98(isa_dev->id_flags) == ED_TYPE98_GENERIC) ||
(ED_TYPE98(isa_dev->id_flags) == ED_TYPE98_LPC)) {
ed_softc[isa_dev->id_unit].type = ED_TYPE98_LPC;
pc98_set_register(isa_dev, isa_dev->id_unit, ED_TYPE98_LPC);
pc98_set_register(isa_dev, ED_TYPE98_LPC);
nports = ed_probe_Novell(isa_dev);
if (nports)
return (nports);
@ -454,7 +464,7 @@ ed_probe(isa_dev)
* Allied Telesis CenterCom LA-98-T
*/
ed_softc[isa_dev->id_unit].type = ED_TYPE98_GENERIC;
pc98_set_register(isa_dev, isa_dev->id_unit, ED_TYPE98_GENERIC);
pc98_set_register(isa_dev, ED_TYPE98_GENERIC);
if (ED_TYPE98(isa_dev->id_flags) == ED_TYPE98_GENERIC) {
#endif
@ -478,7 +488,7 @@ ed_probe(isa_dev)
if ((ED_TYPE98(isa_dev->id_flags) == ED_TYPE98_GENERIC) ||
(ED_TYPE98(isa_dev->id_flags) == ED_TYPE98_SIC)) {
ed_softc[isa_dev->id_unit].type = ED_TYPE98_SIC;
pc98_set_register(isa_dev, isa_dev->id_unit, ED_TYPE98_SIC);
pc98_set_register(isa_dev, ED_TYPE98_SIC);
nports = ed_probe_SIC98(isa_dev);
if (nports)
return (nports);
@ -492,7 +502,7 @@ ed_probe(isa_dev)
(ED_TYPE98(isa_dev->id_flags) == ED_TYPE98_BDN)) {
/* LD-BDN */
ed_softc[isa_dev->id_unit].type = ED_TYPE98_BDN;
pc98_set_register(isa_dev, isa_dev->id_unit, ED_TYPE98_BDN);
pc98_set_register(isa_dev, ED_TYPE98_BDN);
nports = ed_probe_Novell(isa_dev);
if (nports)
return (nports);
@ -506,7 +516,7 @@ ed_probe(isa_dev)
(ED_TYPE98(isa_dev->id_flags) == ED_TYPE98_LGY)) {
/* LGY-98 */
ed_softc[isa_dev->id_unit].type = ED_TYPE98_LGY;
pc98_set_register(isa_dev, isa_dev->id_unit, ED_TYPE98_LGY);
pc98_set_register(isa_dev, ED_TYPE98_LGY);
nports = ed_probe_Novell(isa_dev);
if (nports)
return (nports);
@ -520,7 +530,7 @@ ed_probe(isa_dev)
(ED_TYPE98(isa_dev->id_flags) == ED_TYPE98_ICM)) {
/* ICM */
ed_softc[isa_dev->id_unit].type = ED_TYPE98_ICM;
pc98_set_register(isa_dev, isa_dev->id_unit, ED_TYPE98_ICM);
pc98_set_register(isa_dev, ED_TYPE98_ICM);
nports = ed_probe_Novell(isa_dev);
if (nports)
return (nports);
@ -534,7 +544,7 @@ ed_probe(isa_dev)
(ED_TYPE98(isa_dev->id_flags) == ED_TYPE98_EGY)) {
/* EGY-98 */
ed_softc[isa_dev->id_unit].type = ED_TYPE98_EGY;
pc98_set_register(isa_dev, isa_dev->id_unit, ED_TYPE98_EGY);
pc98_set_register(isa_dev, ED_TYPE98_EGY);
nports = ed_probe_Novell(isa_dev);
if (nports)
return (nports);
@ -547,7 +557,7 @@ ed_probe(isa_dev)
(ED_TYPE98(isa_dev->id_flags) == ED_TYPE98_LA98)) {
/* LA-98 */
ed_softc[isa_dev->id_unit].type = ED_TYPE98_LA98;
pc98_set_register(isa_dev, isa_dev->id_unit, ED_TYPE98_LA98);
pc98_set_register(isa_dev, ED_TYPE98_LA98);
nports = ed_probe_Novell(isa_dev);
if (nports)
return (nports);
@ -560,7 +570,7 @@ ed_probe(isa_dev)
(ED_TYPE98(isa_dev->id_flags) == ED_TYPE98_108)) {
/* PC-9801-108 */
ed_softc[isa_dev->id_unit].type = ED_TYPE98_108;
pc98_set_register(isa_dev, isa_dev->id_unit, ED_TYPE98_108);
pc98_set_register(isa_dev, ED_TYPE98_108);
nports = ed_probe_Novell(isa_dev);
if (nports)
return (nports);
@ -573,7 +583,7 @@ ed_probe(isa_dev)
(ED_TYPE98(isa_dev->id_flags) == ED_TYPE98_CNET98EL)) {
/* C-NET(98)E/L */
ed_softc[isa_dev->id_unit].type = ED_TYPE98_CNET98EL;
pc98_set_register(isa_dev, isa_dev->id_unit, ED_TYPE98_CNET98EL);
pc98_set_register(isa_dev, ED_TYPE98_CNET98EL);
nports = ed_probe_CNET98EL(isa_dev);
if (nports)
return (nports);
@ -586,7 +596,7 @@ ed_probe(isa_dev)
(ED_TYPE98(isa_dev->id_flags) == ED_TYPE98_CNET98)) {
/* C-NET(98) */
ed_softc[isa_dev->id_unit].type = ED_TYPE98_CNET98;
pc98_set_register(isa_dev, isa_dev->id_unit, ED_TYPE98_CNET98);
pc98_set_register(isa_dev, ED_TYPE98_CNET98);
nports = ed_probe_CNET98(isa_dev);
if (nports)
return (nports);
@ -627,10 +637,6 @@ static int
ed_probe_generic8390(sc)
struct ed_softc *sc;
{
#ifdef PC98
int unit = sc->unit;
#endif
#ifdef PC98
if (sc->type == ED_TYPE98_LPC) {
if ((inb(sc->nic_addr + ED_P0_CR) &
@ -1036,9 +1042,6 @@ ed_probe_3Com(isa_dev)
int i;
u_int memsize;
u_char isa16bit;
#ifdef PC98
int unit = isa_dev->id_unit;
#endif
sc->asic_addr = isa_dev->id_iobase + ED_3COM_ASIC_OFFSET;
sc->nic_addr = isa_dev->id_iobase + ED_3COM_NIC_OFFSET;
@ -1359,7 +1362,6 @@ ed_probe_Novell_generic(sc, port, unit, flags)
if (sc->type == ED_TYPE98_LPC)
LPCT_1d0_OFF();
#endif
DELAY(5000);
/*
@ -1592,7 +1594,7 @@ ed_probe_Novell(isa_dev)
}
#if NCRD > 0
/*
* Probe framework for pccards. Replicates the standard framework,
* minus the pccard driver registration and ignores the ether address
@ -1653,9 +1655,7 @@ ed_probe_HP_pclanp(isa_dev)
u_char irq; /* board configured IRQ */
char test_pattern[ED_HPP_TEST_SIZE]; /* read/write areas for */
char test_buffer[ED_HPP_TEST_SIZE]; /* probing card */
#ifdef PC98
int unit = isa_dev->id_unit;
#endif
/* Fill in basic information */
sc->asic_addr = isa_dev->id_iobase + ED_HPP_ASIC_OFFSET;
@ -2503,9 +2503,6 @@ ed_stop(sc)
struct ed_softc *sc;
{
int n = 5000;
#ifdef PC98
int unit = sc->unit;
#endif
if (sc->gone)
return;
@ -2550,9 +2547,6 @@ ed_init(xsc)
struct ed_softc *sc = xsc;
struct ifnet *ifp = &sc->arpcom.ac_if;
int i, s;
#ifdef PC98
int unit = sc->unit;
#endif
if (sc->gone)
return;
@ -2655,7 +2649,7 @@ ed_init(xsc)
*/
#ifdef PC98
for (i = 0; i < ETHER_ADDR_LEN; ++i)
outb(sc->nic_addr + ED_P1_PAR0 + i * pc98_io_skip[unit],
outb(sc->nic_addr + ED_P1_PAR0 + i * sc->edreg.ioskip,
sc->arpcom.ac_enaddr[i]);
#else
for (i = 0; i < ETHER_ADDR_LEN; ++i)
@ -2713,9 +2707,6 @@ ed_xmit(sc)
{
struct ifnet *ifp = (struct ifnet *)sc;
unsigned short len;
#ifdef PC98
int unit = sc->unit;
#endif
if (sc->gone)
return;
@ -2930,9 +2921,6 @@ ed_rint(sc)
u_short len;
struct ed_ring packet_hdr;
char *packet_ptr;
#ifdef PC98
int unit = sc->unit;
#endif
if (sc->gone)
return;
@ -3056,9 +3044,6 @@ edintr_sc(sc)
{
struct ifnet *ifp = (struct ifnet *)sc;
u_char isr;
#ifdef PC98
int unit = sc->unit;
#endif
if (sc->gone)
return;
@ -3548,10 +3533,6 @@ ed_pio_readmem(sc, src, dst, amount)
unsigned char *dst;
unsigned short amount;
{
#ifdef PC98
int unit = sc->unit;
#endif
/* HP cards need special handling */
if (sc->vendor == ED_VENDOR_HP && sc->type == ED_TYPE_HP_PCLANPLUS) {
ed_hpp_readmem(sc, src, dst, amount);
@ -3603,9 +3584,6 @@ ed_pio_writemem(sc, src, dst, len)
unsigned short len;
{
int maxwait = 200; /* about 240us */
#ifdef PC98
int unit = sc->unit;
#endif
if (sc->vendor == ED_VENDOR_NOVELL) {
@ -3711,9 +3689,6 @@ ed_pio_write_mbufs(sc, m, dst)
unsigned short total_len, dma_len;
struct mbuf *mp;
int maxwait = 200; /* about 240us */
#ifdef PC98
int unit = sc->unit;
#endif
/* HP PC Lan+ cards need special handling */
if ((sc->vendor == ED_VENDOR_HP) &&
@ -3977,9 +3952,6 @@ ed_hpp_write_mbufs(struct ed_softc *sc, struct mbuf *m, int dst)
volatile u_short * const d =
(volatile u_short *) sc->hpp_mem_start;
int use_32bit_accesses = !(sc->hpp_id & ED_HPP_ID_16_BIT_ACCESS);
#ifdef PC98
int unit = sc->unit;
#endif
/* select page 0 registers */
outb(sc->nic_addr + ED_P0_CR, sc->cr_proto | ED_CR_STA);
@ -4095,9 +4067,6 @@ ed_setrcr(sc)
{
struct ifnet *ifp = (struct ifnet *)sc;
int i;
#ifdef PC98
int unit = sc->unit;
#endif
/* set page 1 registers */
outb(sc->nic_addr + ED_P0_CR, sc->cr_proto | ED_CR_PAGE_1 | ED_CR_STP);
@ -4109,7 +4078,7 @@ ed_setrcr(sc)
*/
#ifdef PC98
for (i = 0; i < 8; i++)
outb(sc->nic_addr + ED_P1_MAR0 + i * pc98_io_skip[unit], 0xff);
outb(sc->nic_addr + ED_P1_MAR0 + i * sc->edreg.ioskip, 0xff);
#else
for (i = 0; i < 8; i++)
outb(sc->nic_addr + ED_P1_MAR0 + i, 0xff);
@ -4139,7 +4108,7 @@ ed_setrcr(sc)
*/
#ifdef PC98
for (i = 0; i < 8; i++)
outb(sc->nic_addr + ED_P1_MAR0 + i * pc98_io_skip[unit],
outb(sc->nic_addr + ED_P1_MAR0 + i * sc->edreg.ioskip,
((u_char *) mcaf)[i]);
#else
for (i = 0; i < 8; i++)
@ -4155,12 +4124,12 @@ ed_setrcr(sc)
* Initialize multicast address hashing registers to
* not accept multicasts.
*/
#ifndef PC98
#ifdef PC98
for (i = 0; i < 8; ++i)
outb(sc->nic_addr + ED_P1_MAR0 + i, 0x00);
outb(sc->nic_addr + ED_P1_MAR0 + i * sc->edreg.ioskip, 0x00);
#else
for (i = 0; i < 8; ++i)
outb(sc->nic_addr + ED_P1_MAR0 + i * pc98_io_skip[unit], 0x00);
outb(sc->nic_addr + ED_P1_MAR0 + i, 0x00);
#endif
/* Set page 0 registers */

View File

@ -36,8 +36,7 @@
#error Why you include if_ed98.h?
#endif
static void pc98_set_register __P((struct isa_device *dev,
int unit, int type));
static void pc98_set_register __P((struct isa_device *dev, int type));
/*
* Vendor types
@ -50,11 +49,11 @@ static void pc98_set_register __P((struct isa_device *dev,
#ifdef ED_NOVELL_NIC_OFFSET
#undef ED_NOVELL_NIC_OFFSET
#endif
#define ED_NOVELL_NIC_OFFSET ed_novell_nic_offset[unit]
#define ED_NOVELL_NIC_OFFSET sc->edreg.nic_offset
#ifdef ED_NOVELL_ASIC_OFFSET
#undef ED_NOVELL_ASIC_OFFSET
#endif
#define ED_NOVELL_ASIC_OFFSET ed_novell_asic_offset[unit]
#define ED_NOVELL_ASIC_OFFSET sc->edreg.asic_offset
/*
* Remote DMA data register; for reading or writing to the NIC mem
@ -63,7 +62,7 @@ static void pc98_set_register __P((struct isa_device *dev,
#ifdef ED_NOVELL_DATA
#undef ED_NOVELL_DATA
#endif
#define ED_NOVELL_DATA ed_novell_data[unit]
#define ED_NOVELL_DATA sc->edreg.data
/*
* Reset register; reading from this register causes a board reset
@ -71,7 +70,7 @@ static void pc98_set_register __P((struct isa_device *dev,
#ifdef ED_NOVELL_RESET
#undef ED_NOVELL_RESET
#endif
#define ED_NOVELL_RESET ed_novell_reset[unit]
#define ED_NOVELL_RESET sc->edreg.reset
/*
* Card type
@ -113,152 +112,152 @@ static void pc98_set_register __P((struct isa_device *dev,
* Page 0 register offsets
*/
#undef ED_P0_CR
#define ED_P0_CR edp[unit][0x00]
#define ED_P0_CR sc->edreg.port[0x00]
#undef ED_P0_CLDA0
#define ED_P0_CLDA0 edp[unit][0x01]
#define ED_P0_CLDA0 sc->edreg.port[0x01]
#undef ED_P0_PSTART
#define ED_P0_PSTART edp[unit][0x01]
#define ED_P0_PSTART sc->edreg.port[0x01]
#undef ED_P0_CLDA1
#define ED_P0_CLDA1 edp[unit][0x02]
#define ED_P0_CLDA1 sc->edreg.port[0x02]
#undef ED_P0_PSTOP
#define ED_P0_PSTOP edp[unit][0x02]
#define ED_P0_PSTOP sc->edreg.port[0x02]
#undef ED_P0_BNRY
#define ED_P0_BNRY edp[unit][0x03]
#define ED_P0_BNRY sc->edreg.port[0x03]
#undef ED_P0_TSR
#define ED_P0_TSR edp[unit][0x04]
#define ED_P0_TSR sc->edreg.port[0x04]
#undef ED_P0_TPSR
#define ED_P0_TPSR edp[unit][0x04]
#define ED_P0_TPSR sc->edreg.port[0x04]
#undef ED_P0_NCR
#define ED_P0_NCR edp[unit][0x05]
#define ED_P0_NCR sc->edreg.port[0x05]
#undef ED_P0_TBCR0
#define ED_P0_TBCR0 edp[unit][0x05]
#define ED_P0_TBCR0 sc->edreg.port[0x05]
#undef ED_P0_FIFO
#define ED_P0_FIFO edp[unit][0x06]
#define ED_P0_FIFO sc->edreg.port[0x06]
#undef ED_P0_TBCR1
#define ED_P0_TBCR1 edp[unit][0x06]
#define ED_P0_TBCR1 sc->edreg.port[0x06]
#undef ED_P0_ISR
#define ED_P0_ISR edp[unit][0x07]
#define ED_P0_ISR sc->edreg.port[0x07]
#undef ED_P0_CRDA0
#define ED_P0_CRDA0 edp[unit][0x08]
#define ED_P0_CRDA0 sc->edreg.port[0x08]
#undef ED_P0_RSAR0
#define ED_P0_RSAR0 edp[unit][0x08]
#define ED_P0_RSAR0 sc->edreg.port[0x08]
#undef ED_P0_CRDA1
#define ED_P0_CRDA1 edp[unit][0x09]
#define ED_P0_CRDA1 sc->edreg.port[0x09]
#undef ED_P0_RSAR1
#define ED_P0_RSAR1 edp[unit][0x09]
#define ED_P0_RSAR1 sc->edreg.port[0x09]
#undef ED_P0_RBCR0
#define ED_P0_RBCR0 edp[unit][0x0a]
#define ED_P0_RBCR0 sc->edreg.port[0x0a]
#undef ED_P0_RBCR1
#define ED_P0_RBCR1 edp[unit][0x0b]
#define ED_P0_RBCR1 sc->edreg.port[0x0b]
#undef ED_P0_RSR
#define ED_P0_RSR edp[unit][0x0c]
#define ED_P0_RSR sc->edreg.port[0x0c]
#undef ED_P0_RCR
#define ED_P0_RCR edp[unit][0x0c]
#define ED_P0_RCR sc->edreg.port[0x0c]
#undef ED_P0_CNTR0
#define ED_P0_CNTR0 edp[unit][0x0d]
#define ED_P0_CNTR0 sc->edreg.port[0x0d]
#undef ED_P0_TCR
#define ED_P0_TCR edp[unit][0x0d]
#define ED_P0_TCR sc->edreg.port[0x0d]
#undef ED_P0_CNTR1
#define ED_P0_CNTR1 edp[unit][0x0e]
#define ED_P0_CNTR1 sc->edreg.port[0x0e]
#undef ED_P0_DCR
#define ED_P0_DCR edp[unit][0x0e]
#define ED_P0_DCR sc->edreg.port[0x0e]
#undef ED_P0_CNTR2
#define ED_P0_CNTR2 edp[unit][0x0f]
#define ED_P0_CNTR2 sc->edreg.port[0x0f]
#undef ED_P0_IMR
#define ED_P0_IMR edp[unit][0x0f]
#define ED_P0_IMR sc->edreg.port[0x0f]
/*
* Page 1 register offsets
*/
#undef ED_P1_CR
#define ED_P1_CR edp[unit][0x00]
#define ED_P1_CR sc->edreg.port[0x00]
#undef ED_P1_PAR0
#define ED_P1_PAR0 edp[unit][0x01]
#define ED_P1_PAR0 sc->edreg.port[0x01]
#undef ED_P1_PAR1
#define ED_P1_PAR1 edp[unit][0x02]
#define ED_P1_PAR1 sc->edreg.port[0x02]
#undef ED_P1_PAR2
#define ED_P1_PAR2 edp[unit][0x03]
#define ED_P1_PAR2 sc->edreg.port[0x03]
#undef ED_P1_PAR3
#define ED_P1_PAR3 edp[unit][0x04]
#define ED_P1_PAR3 sc->edreg.port[0x04]
#undef ED_P1_PAR4
#define ED_P1_PAR4 edp[unit][0x05]
#define ED_P1_PAR4 sc->edreg.port[0x05]
#undef ED_P1_PAR5
#define ED_P1_PAR5 edp[unit][0x06]
#define ED_P1_PAR5 sc->edreg.port[0x06]
#undef ED_P1_CURR
#define ED_P1_CURR edp[unit][0x07]
#define ED_P1_CURR sc->edreg.port[0x07]
#undef ED_P1_MAR0
#define ED_P1_MAR0 edp[unit][0x08]
#define ED_P1_MAR0 sc->edreg.port[0x08]
#undef ED_P1_MAR1
#define ED_P1_MAR1 edp[unit][0x09]
#define ED_P1_MAR1 sc->edreg.port[0x09]
#undef ED_P1_MAR2
#define ED_P1_MAR2 edp[unit][0x0a]
#define ED_P1_MAR2 sc->edreg.port[0x0a]
#undef ED_P1_MAR3
#define ED_P1_MAR3 edp[unit][0x0b]
#define ED_P1_MAR3 sc->edreg.port[0x0b]
#undef ED_P1_MAR4
#define ED_P1_MAR4 edp[unit][0x0c]
#define ED_P1_MAR4 sc->edreg.port[0x0c]
#undef ED_P1_MAR5
#define ED_P1_MAR5 edp[unit][0x0d]
#define ED_P1_MAR5 sc->edreg.port[0x0d]
#undef ED_P1_MAR6
#define ED_P1_MAR6 edp[unit][0x0e]
#define ED_P1_MAR6 sc->edreg.port[0x0e]
#undef ED_P1_MAR7
#define ED_P1_MAR7 edp[unit][0x0f]
#define ED_P1_MAR7 sc->edreg.port[0x0f]
/*
* Page 2 register offsets
*/
#undef ED_P2_CR
#define ED_P2_CR edp[unit][0x00]
#define ED_P2_CR sc->edreg.port[0x00]
#undef ED_P2_PSTART
#define ED_P2_PSTART edp[unit][0x01]
#define ED_P2_PSTART sc->edreg.port[0x01]
#undef ED_P2_CLDA0
#define ED_P2_CLDA0 edp[unit][0x01]
#define ED_P2_CLDA0 sc->edreg.port[0x01]
#undef ED_P2_PSTOP
#define ED_P2_PSTOP edp[unit][0x02]
#define ED_P2_PSTOP sc->edreg.port[0x02]
#undef ED_P2_CLDA1
#define ED_P2_CLDA1 edp[unit][0x02]
#define ED_P2_CLDA1 sc->edreg.port[0x02]
#undef ED_P2_RNPP
#define ED_P2_RNPP edp[unit][0x03]
#define ED_P2_RNPP sc->edreg.port[0x03]
#undef ED_P2_TPSR
#define ED_P2_TPSR edp[unit][0x04]
#define ED_P2_TPSR sc->edreg.port[0x04]
#undef ED_P2_LNPP
#define ED_P2_LNPP edp[unit][0x05]
#define ED_P2_LNPP sc->edreg.port[0x05]
#undef ED_P2_ACU
#define ED_P2_ACU edp[unit][0x06]
#define ED_P2_ACU sc->edreg.port[0x06]
#undef ED_P2_ACL
#define ED_P2_ACL edp[unit][0x07]
#define ED_P2_ACL sc->edreg.port[0x07]
#undef ED_P2_RCR
#define ED_P2_RCR edp[unit][0x0c]
#define ED_P2_RCR sc->edreg.port[0x0c]
#undef ED_P2_TCR
#define ED_P2_TCR edp[unit][0x0d]
#define ED_P2_TCR sc->edreg.port[0x0d]
#undef ED_P2_DCR
#define ED_P2_DCR edp[unit][0x0e]
#define ED_P2_DCR sc->edreg.port[0x0e]
#undef ED_P2_IMR
#define ED_P2_IMR edp[unit][0x0f]
#define ED_P2_IMR sc->edreg.port[0x0f]
/* PCCARD */
#ifdef ED_PC_MISC
#undef ED_PC_MISC
#endif
#define ED_PC_MISC ed_pc_misc[unit]
#define ED_PC_MISC sc->edreg.pc_misc
#ifdef ED_PC_RESET
#undef ED_PC_RESET
#endif
#define ED_PC_RESET ed_pc_reset[unit]
#define ED_PC_RESET sc->edreg.pc_reset
/* LPC-T support */
#define LPCT_1d0_ON() \
@ -336,19 +335,6 @@ static void pc98_set_register __P((struct isa_device *dev,
*/
#define ED_CNET98EL_ISR 0x05
/* register offsets */
static unsigned int *edp[NED];
static unsigned int pc98_io_skip[NED];
static int ed_novell_nic_offset[NED];
static int ed_novell_asic_offset[NED];
static int ed_novell_data[NED];
static int ed_novell_reset[NED];
static int ed_pc_misc[NED];
static int ed_pc_reset[NED];
/* NE2000, LGY-98, ICM, LPC-T, C-NET(98)E/L */
static unsigned int edp_generic[16] = {
0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15
@ -391,14 +377,15 @@ static unsigned int edp_cnet98[16] = {
};
static void pc98_set_register(struct isa_device *dev, int unit, int type)
static void pc98_set_register(struct isa_device *dev, int type)
{
struct ed_softc *sc = &ed_softc[dev->id_unit];
int adj;
switch (type) {
case ED_TYPE98_GENERIC:
edp[unit] = edp_generic;
pc98_io_skip[unit] = 1;
sc->edreg.port = edp_generic;
sc->edreg.ioskip = 1;
ED_NOVELL_NIC_OFFSET = 0x0000;
ED_NOVELL_ASIC_OFFSET = 0x0010;
ED_NOVELL_DATA = 0x0000;
@ -408,8 +395,8 @@ static void pc98_set_register(struct isa_device *dev, int unit, int type)
break;
case ED_TYPE98_LGY:
edp[unit] = edp_generic;
pc98_io_skip[unit] = 1;
sc->edreg.port = edp_generic;
sc->edreg.ioskip = 1;
ED_NOVELL_NIC_OFFSET = 0x0000;
ED_NOVELL_ASIC_OFFSET = 0x0200;
ED_NOVELL_DATA = 0x0000;
@ -419,8 +406,8 @@ static void pc98_set_register(struct isa_device *dev, int unit, int type)
break;
case ED_TYPE98_EGY:
edp[unit] = edp_egy98;
pc98_io_skip[unit] = 2;
sc->edreg.port = edp_egy98;
sc->edreg.ioskip = 2;
ED_NOVELL_NIC_OFFSET = 0;
ED_NOVELL_ASIC_OFFSET = 0x0200;
ED_NOVELL_DATA = 0x0000;
@ -430,8 +417,8 @@ static void pc98_set_register(struct isa_device *dev, int unit, int type)
break;
case ED_TYPE98_ICM:
edp[unit] = edp_generic;
pc98_io_skip[unit] = 1;
sc->edreg.port = edp_generic;
sc->edreg.ioskip = 1;
ED_NOVELL_NIC_OFFSET = 0;
ED_NOVELL_ASIC_OFFSET = 0x0100;
ED_NOVELL_DATA = 0x0000;
@ -441,8 +428,8 @@ static void pc98_set_register(struct isa_device *dev, int unit, int type)
break;
case ED_TYPE98_BDN:
edp[unit] = edp_bdn98;
pc98_io_skip[unit] = 0x1000;
sc->edreg.port = edp_bdn98;
sc->edreg.ioskip = 0x1000;
ED_NOVELL_NIC_OFFSET = 0x0000;
ED_NOVELL_ASIC_OFFSET = 0x0100;
ED_NOVELL_DATA = 0;
@ -452,8 +439,8 @@ static void pc98_set_register(struct isa_device *dev, int unit, int type)
break;
case ED_TYPE98_SIC:
edp[unit] = edp_sic98;
pc98_io_skip[unit] = 0x200;
sc->edreg.port = edp_sic98;
sc->edreg.ioskip = 0x200;
ED_NOVELL_NIC_OFFSET = 0x0000;
ED_NOVELL_ASIC_OFFSET = 0x2000;
ED_NOVELL_DATA = 0x00; /* dummy */
@ -463,8 +450,8 @@ static void pc98_set_register(struct isa_device *dev, int unit, int type)
break;
case ED_TYPE98_LPC:
edp[unit] = edp_generic;
pc98_io_skip[unit] = 0x1;
sc->edreg.port = edp_generic;
sc->edreg.ioskip = 0x1;
ED_NOVELL_NIC_OFFSET = 0x0000;
ED_NOVELL_ASIC_OFFSET = 0x0100;
ED_NOVELL_DATA = 0x0000;
@ -474,8 +461,8 @@ static void pc98_set_register(struct isa_device *dev, int unit, int type)
break;
case ED_TYPE98_108:
edp[unit] = edp_nec108;
pc98_io_skip[unit] = 2;
sc->edreg.port = edp_nec108;
sc->edreg.ioskip = 2;
adj = (dev->id_iobase & 0xf000) / 2;
ED_NOVELL_NIC_OFFSET = 0;
ED_NOVELL_ASIC_OFFSET = (0x888 | adj) - dev->id_iobase;
@ -486,8 +473,8 @@ static void pc98_set_register(struct isa_device *dev, int unit, int type)
break;
case ED_TYPE98_LA98:
edp[unit] = edp_la98;
pc98_io_skip[unit] = 0x1000;
sc->edreg.port = edp_la98;
sc->edreg.ioskip = 0x1000;
ED_NOVELL_NIC_OFFSET = 0;
ED_NOVELL_ASIC_OFFSET = 0x100;
ED_NOVELL_DATA = 0x0000;
@ -497,8 +484,8 @@ static void pc98_set_register(struct isa_device *dev, int unit, int type)
break;
case ED_TYPE98_CNET98EL:
edp[unit] = edp_generic;
pc98_io_skip[unit] = 1;
sc->edreg.port = edp_generic;
sc->edreg.ioskip = 1;
ED_NOVELL_NIC_OFFSET = 0;
ED_NOVELL_ASIC_OFFSET = 0x0400;
ED_NOVELL_DATA = 0x000e;
@ -507,8 +494,8 @@ static void pc98_set_register(struct isa_device *dev, int unit, int type)
break;
case ED_TYPE98_CNET98:
edp[unit] = edp_cnet98;
pc98_io_skip[unit] = 2;
sc->edreg.port = edp_cnet98;
sc->edreg.ioskip = 2;
ED_NOVELL_NIC_OFFSET = 0;
ED_NOVELL_ASIC_OFFSET = 0x0400;
ED_NOVELL_DATA = 0x000e;

View File

@ -21,7 +21,7 @@
*/
/*
* $Id: if_fe.c,v 1.8 1996/09/12 11:09:48 asami Exp $
* $Id: if_fe.c,v 1.9 1996/10/09 21:46:25 asami Exp $
*
* Device driver for Fujitsu MB86960A/MB86965A based Ethernet cards.
* To be used with FreeBSD 2.x
@ -242,8 +242,8 @@ static struct fe_softc {
#define sc_enaddr arpcom.ac_enaddr
/* Standard driver entry points. These can be static. */
static int fe_probe ( DEVICE * );
static int fe_attach ( DEVICE * );
static int fe_probe ( struct isa_device * );
static int fe_attach ( struct isa_device * );
static void fe_init ( int );
static int fe_ioctl ( struct ifnet *, int, caddr_t );
static void fe_start ( struct ifnet * );

View File

@ -1,9 +1,15 @@
/*
* Keyboard definitions
* from: unknown origin, 386BSD 0.1
* $Id: kbd.h,v 1.4 1995/05/30 08:02:38 rgrimes Exp $
*/
#ifndef _PC98_PC98_KBD_H_
#define _PC98_PC98_KBD_H_ 1
#ifndef _I386_ISA_KBD_H_
#define _I386_ISA_KBD_H_ 1
/* Reference: IBM AT Technical Reference Manual,
* pp. 1-38 to 1-43, 4-3 to 4-22
*/
/* commands and responses */
#define KBC_RESET 0xFF /* Reset the keyboard */
@ -12,4 +18,4 @@
#define KBR_RESEND 0xFE /* Keyboard needs resend of command */
#define KBR_ACK 0xFA /* Keyboard did receive command */
#define KBR_RSTDONE 0xAA /* Keyboard reset complete */
#endif /* _PC98_PC98_KBD_H_ */
#endif /* _I386_ISA_KBD_H_ */

File diff suppressed because it is too large Load Diff

View File

@ -1,42 +0,0 @@
Things to do for the matcd driver 4-Jul-95
1. Someone wants to switch all drivers from disklabel and
its assorted mechanisms over to disk slicing and its mechanisms,
but I was unable to find any useful documentation on how to
implement the changes for a read-only, single-partition,
removable (ie, partition can change size) device.
So this will have to wait until after 2.1.
2. Support for reading R-W subcodes while playing audio. This would be
useful if you have any CD+G or CD+MIDI discs, but the demand for this
is pretty low, unless you like Karaoke. Someone will also have to
write a CD+G viewer for X. The code for the driver to add this is
pretty minor but there aren't any precedents on how to handle the
data transfer to the application.
3. Support for reading the ISBN and UPC labels. The ioctl structures
for these appear to be defined but no other driver seems to do this.
4. Multi-session support. There are two forms of this; what
Philips defined and what Kodak uses. This will be quite
complicated and will probably require changes in the filesystem
layer. The drive support for Kodak multi-session is known to work.
5. Multiple data tracks. My vision here was to add an ioctl
that caused a track offset to be inserted into block requests,
effectively shifting the base to the specified track. Very
easy to add but not a big deal since I have only two discs
in my collection that have multiple data tracks and I mastered
one of them.
6. A curses-based CD-Player app (ie, not X). I will probably do this
mainly for its value as a debugging tool. It was pretty annoying
not finding a single application that actually issued all the
defined ioctls, let alone any new ones.
If you feel the urge to work on one or more of these remaining items,
please contact the author first at bsdmail@nemesis.lonestar.org
to make sure the work hasn't already been done or started.
Frank Durda IV

View File

@ -1,142 +0,0 @@
/*creative.h-------------------------------------------------------------------
Matsushita(Panasonic) / Creative CD-ROM Driver (matcd)
Authored by Frank Durda IV
Copyright 1994, 1995 Frank Durda IV. All rights reserved.
"FDIV" is a trademark of Frank Durda IV.
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 positioned at the very beginning of this file without
modification, all copyright strings, all related programming
codes that display the copyright strings, this list of
conditions and the following disclaimer.
2. Redistributions in binary form must contain all copyright strings
and related programming code that display the copyright strings.
3. 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.
4. All advertising materials mentioning features or use of this
software must display the following acknowledgement:
"The Matsushita/Panasonic CD-ROM driver was developed
by Frank Durda IV for use with "FreeBSD" and similar
operating systems."
"Similar operating systems" includes mainly non-profit oriented
systems for research and education, including but not restricted
to "NetBSD", "386BSD", and "Mach" (by CMU). The wording of the
acknowledgement (in electronic form or printed text) may not be
changed without permission from the author.
5. Absolutely no warranty of function, fitness or purpose is made
by the author Frank Durda IV.
6. Neither the name of the author nor the name "FreeBSD" may
be used to endorse or promote products derived from this software
without specific prior written permission.
(The author can be reached at bsdmail@nemesis.lonestar.org)
7. The product containing this software must meet all of these
conditions even if it is unsupported, not a complete system
and/or does not contain compiled code.
8. These conditions will be in force for the full life of the
copyright.
9. If all the above conditions are met, modifications to other
parts of this file may be freely made, although any person
or persons making changes do not receive the right to add their
name or names to the copyright strings and notices in this
software. Persons making changes are encouraged to insert edit
history in matcd.c and to put your name and details of the
change there.
10. You must have prior written permission from the author to
deviate from these terms.
Vendors who produce product(s) containing this code are encouraged
(but not required) to provide copies of the finished product(s) to
the author and to correspond with the author about development
activity relating to this code. Donations of development hardware
and/or software are also welcome. (This is one of the faster ways
to get a driver developed for a device.)
THIS SOFTWARE IS PROVIDED BY THE DEVELOPER(S) ``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 DEVELOPER(S) 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.
-----No changes are allowed above this line------------------------------------
See matcd.c for Edit History
These are the I/O port mapping offsets and bit assignments used
by Creative Labs in their implementation of the host interface for
the Matsushita CD-ROM drive. These may be different in the adapter
cards (including sound cards) made by other vendors.
It is unknown if the Creative interface is based on a reference design
provided by Matsushita (other interface vendors would similar or
identical if this was the case).
The drive is actually capable of some things that the Creative
interface doesn't implement, such as DMA and interrupts.
See matcd.h for defines related to the Matsushita drive itself.
*/
/* Creative Labs (and compatible) I/O port mapping offsets
*/
#define NUMPORTS 4 /*Four ports are decoded by the i/f*/
#define CMD 0 /*Write - commands*/
#define DATA 0 /*Read - data/status from drive*/
#ifdef PC98
#define PHASE 0x100 /*Write - switch between data/status*/
#define STATUS 0x100 /*Read - bus status */
#define RESET 0x200 /*Write - reset all attached drives*/
#define ALTDATA 0x200 /*<20>Read - data on non Creative bds.*/
#define SELECT 0x300 /*Write - drive select*/
#else /* !PC98 */
#define PHASE 1 /*Write - switch between data/status*/
#define STATUS 1 /*Read - bus status*/
#define RESET 2 /*Write - reset all attached drives*/
/*Any value written will reset*/
#define ALTDATA 2 /*<20>Read - data on non Creative bds.*/
#define SELECT 3 /*Write - drive select*/
#endif /*PC98*/
/* Creative PHASE port bit assignments
*/
#define PHASENA 1 /*Access data bytes instead of status*/
/* Creative STATUS port register bits
*/
#define DTEN 2 /*When low, in data xfer phase*/
#define STEN 4 /*When low, in status phase*/
#define TEST 1 /*Function is unknown*/
/* Creative drive SELECT port bit assignments
Note that in the Creative interface, DS0==Bit 1 and
DS1==Bit 0 (DS is Drive Select).
*/
#define CRDRIVE0 0x00
#define CRDRIVE1 0x02
#define CRDRIVE2 0x01
#define CRDRIVE3 0x03
/*End of creative.h*/

File diff suppressed because it is too large Load Diff

View File

@ -1,283 +0,0 @@
/*options.h--------------------------------------------------------------------
Matsushita(Panasonic) / Creative CD-ROM Driver (matcd)
Authored by Frank Durda IV
Copyright 1994, 1995 Frank Durda IV. All rights reserved.
"FDIV" is a trademark of Frank Durda IV.
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 positioned at the very beginning of this file without
modification, all copyright strings, all related programming
codes that display the copyright strings, this list of
conditions and the following disclaimer.
2. Redistributions in binary form must contain all copyright strings
and related programming code that display the copyright strings.
3. 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.
4. All advertising materials mentioning features or use of this
software must display the following acknowledgement:
"The Matsushita/Panasonic CD-ROM driver was developed
by Frank Durda IV for use with "FreeBSD" and similar
operating systems."
"Similar operating systems" includes mainly non-profit oriented
systems for research and education, including but not restricted
to "NetBSD", "386BSD", and "Mach" (by CMU). The wording of the
acknowledgement (in electronic form or printed text) may not be
changed without permission from the author.
5. Absolutely no warranty of function, fitness or purpose is made
by the author Frank Durda IV.
6. Neither the name of the author nor the name "FreeBSD" may
be used to endorse or promote products derived from this software
without specific prior written permission.
(The author can be reached at bsdmail@nemesis.lonestar.org)
7. The product containing this software must meet all of these
conditions even if it is unsupported, not a complete system
and/or does not contain compiled code.
8. These conditions will be in force for the full life of the
copyright.
9. If all the above conditions are met, modifications to other
parts of this file may be freely made, although any person
or persons making changes do not receive the right to add their
name or names to the copyright strings and notices in this
software. Persons making changes are encouraged to insert edit
history in matcd.c and to put your name and details of the
change there.
10. You must have prior written permission from the author to
deviate from these terms.
Vendors who produce product(s) containing this code are encouraged
(but not required) to provide copies of the finished product(s) to
the author and to correspond with the author about development
activity relating to this code. Donations of development hardware
and/or software are also welcome. (This is one of the faster ways
to get a driver developed for a device.)
THIS SOFTWARE IS PROVIDED BY THE DEVELOPER(S) ``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 DEVELOPER(S) 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.
-----No changes are allowed above this line------------------------------------
-----------------------------------------------------------------------------
Conditional compilation flags - change to suit your system
---------------------------------------------------------------------------*/
/* AUTOHUNT Adds extra code that allows the driver to search
for interface cards rather than having to hard-code
the locations in the kernel conf file.
Leaving AUTOHUNT enabled is the recommended setting.
*/
#define AUTOHUNT
/* NUMCTRLRS Configures support for between one and four
host interfaces, for up to 16 drives.
The number of entries in the kernel config
file is used by default, but this may be changed
to a specific value if desired.
Leaving NUMCTRLRS based on NMATCD is the
recommended setting.
*/
#if NMATCD >= 4
#define NUMCTRLRS 4 /*Limit driver to four host interfaces*/
#else /*NMATCD*/
#define NUMCTRLRS NMATCD
#endif /*NMATCD*/
/* FULLDRIVER If not set, the audio, non-data functions and
some error recovery functions are eliminated from
the compiled driver. The resulting driver will be
smaller and may help a kernel fit on a boot floppy.
Leaving FULLDRIVER enabled is the recommended setting.
*/
#ifndef BOOTMFS
#define FULLDRIVER
#endif /*BOOTMFS*/
/* RESETONBOOT causes the driver to reset the drive(s) to be
reset during probing. This causes any audio
playback to be aborted and the drives will close
their trays if they are open.
Leaving RESETONBOOT enabled is the recommended setting.
*/
#define RESETONBOOT
/*<15> LOCKDRIVE If enabled, when a drive is opened using a
<15> minor number greater than 127, the drive door is
<15> locked. The drive door remains locked until all
<23> partitions on the drive are closed. The EJECT,
<23> ALLOW and PREVENT ioctls are refused when this locking
<23> mechanism is active.
<15> The additional code size is small so enabling
<15> LOCKDRIVE is the recommended setting.
*/
#define LOCKDRIVE
/*<14> KRYTEN This enables a bug that someone might consider
<14> to be a feature. If KRYTEN is enabled and you are
<14> playing audio and you issue the resume-play ioctl,
<14> the audio will stutter, playing the same quarter
<14> of a second or so of audio several times before
<14> resuming normally. Resuming from a pause acts
<14> normally regardless of the setting of this flag.
<14> Leaving KRYTEN disabled is the recommended setting.
<14>*/
/*#define KRYTEN*/
/*---------------------------------------------------------------------------
This structure contains the hints for where we should look for the
host adapter. If you want to change where we search or reduce the
places we search to avoid confusing some other device, either
specify explicit addresses in the kernel config file (preferred)
or change this array.
If the kernel config file has multiple ? entries, the probe routines
will use this table multiple times and will eliminate each failed
entry that probe tries.
WARNING: The number of controller entries for this driver in config
must be less than or equal to the number of hints if hints are used.
If you add entries to the table, add them immediately before
the -1 end-of-table marker. The values already present are
the ones used by Creative Labs boards and those of a few
other vendors.
Each additional entry increases the boot time by four seconds,
and can increase the chance of accessing some other device.
Therefore, the list should be kept to a minimum. Once the
devices have been correctly located, the kernel should be
configured so that it looks only at the correct location from
that point on.
Be sure to search devices located below 0x3ff BEFORE scanning
higher locations. Some boards don't decode all I/O address lines,
so 0x230 and 0x630 appear identical.
---------------------------------------------------------------------------*/
#ifdef AUTOHUNT
static int port_hints[]={
#ifdef PC98
0x30d2,
0x30d0,
0x30d4,
0x30d6,
0x30d8,
0x30da,
0x30dc,
0x30de,
#else
0x230, /*SB Pro & SB16*/
0x240, /*SB Pro & SB16*/
0x250, /*Creative omniCD standalone boards*/
0x260, /*Creative omniCD standalone boards*/
0x340, /*Laser Mate*/
0x360, /*Laser Mate*/
0x630, /*IBM*/
#if 0
/* These locations are alternate settings for LaserMate and IBM
boards, but they usually conflict with network and SCSI cards.
I recommend against probing these randomly.
*/
0x310, /*Laser Mate*/
0x320, /*Laser Mate*/
0x330, /*Laser Mate*/
0x350, /*Laser Mate*/
0x370, /*Laser Mate*/
0x650, /*IBM*/
0x670, /*IBM*/
0x690, /*IBM*/
#endif /*0*/
#endif
-1}; /*use. Table MUST end with -1*/
#endif /*AUTOHUNT*/
/*---------------------------------------------------------------------------
Debugging flags - Turn these on only if you are looking at a
problem.
---------------------------------------------------------------------------*/
/* DEBUGOPEN If enabled, debug messages for open and close
operations.
*/
/*#define DEBUGOPEN*/
/* DEBUGIO If enabled, reports on calls to strategy, start
and other I/O related functions.
*/
/*#define DEBUGIO*/
/* DEBUGQUEUE If enabled, shows activity on disk request queues.
Warning - This debug is VERY VERY NOISY and will
loop endlessly if queues are not null terminated
as they should be.
*/
/*#define DEBUGQUEUE*/
/* DEBUGCMD If enabled, shows the actual commands being issued
to the CD-ROM drives.
*/
/*#define DEBUGCMD*/
/* DEBUGSLEEP If enabled, reports on timeouts, wakeups, dropped
threads, etc.
*/
/*#define DEBUGSLEEP*/
/* DEBUGIOCTL If enabled, reports on the various ioctl-related
calls and operations. You might have to enable
DEBUGCMD as well to get enough debugging information.
*/
/*#define DEBUGIOCTL*/
/* DEBUGPROBE If enabled, reports on the process of locating
adapters and drives. The debugging in matcdprobe()
and matcdattach() routines is enabled with this
flag.
*/
/*#define DEBUGPROBE*/
/*End of options.h*/

View File

@ -11,7 +11,7 @@
* this software for any purpose. It is provided "as is"
* without express or implied warranty.
*
* $Id: mse.c,v 1.4 1996/09/07 02:13:57 asami Exp $
* $Id: mse.c,v 1.5 1996/09/10 09:38:15 asami Exp $
*/
/*
* Driver for the Logitech and ATI Inport Bus mice for use with 386bsd and
@ -662,17 +662,7 @@ mse_probe98m(idp)
/* initialize */
outb(msport + INT, INT_DISABLE); /* INT disable */
outb(msport + HC, HC_NO_CLEAR); /* HC = 0 */
#if 0
if (inb(msport + PORT_C) & 0x80 != 0) {
return (0);
}
#endif
outb(msport + HC, HC_CLEAR); /* HC = 1 */
#if 0
if (inb(msport + PORT_C) & 0x80 == 0) {
return (0);
}
#endif
return (1);
}

View File

@ -34,7 +34,7 @@
* SUCH DAMAGE.
*
* from: @(#)isa.h 5.7 (Berkeley) 5/9/91
* $Id: pc98.h,v 1.5 1996/10/09 21:46:34 asami Exp $
* $Id: pc98.h,v 1.6 1996/10/23 07:25:22 asami Exp $
*/
#ifndef _PC98_PC98_PC98_H_
@ -73,7 +73,7 @@
#define IO_NMI 0x050 /* NMI Control */
#define IO_WAIT 0x05F /* WAIT 0.6 us */
#define IO_GDC1 0x060 /* 7220 GDC Text Control */
#define IO_TIMER 0x071 /* 8253C Timer */
#define IO_TIMER1 0x071 /* 8253C Timer */
#define IO_SASI 0x080 /* SASI Hard Disk Controller */
#define IO_FD1 0x090 /* 765A 1MB FDC */
#define IO_GDC2 0x0a0 /* 7220 GDC Graphic Control */

View File

@ -25,7 +25,7 @@
* (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: pcaudio.c,v 1.5 1996/09/10 09:38:24 asami Exp $
* $Id: pcaudio.c,v 1.6 1996/10/09 21:46:40 asami Exp $
*/
#include "pca.h"
@ -35,8 +35,7 @@
#include <sys/systm.h>
#include <sys/conf.h>
#include <sys/uio.h>
#include <sys/ioctl.h>
#include <sys/file.h>
#include <sys/fcntl.h>
#include <sys/proc.h>
#include <sys/kernel.h>
@ -45,18 +44,14 @@
#ifdef PC98
#include <pc98/pc98/pc98.h>
#include <i386/isa/isa_device.h>
#include <pc98/pc98/timerreg.h>
#include <pc98/pc98/sound/ulaw.h>
#else
#include <i386/isa/isa.h>
#endif
#include <i386/isa/isa_device.h>
#include <i386/isa/timerreg.h>
#define DSP_ULAW_NOT_WANTED
#include <i386/isa/sound/ulaw.h>
#endif
#ifdef DEVFS
#include <sys/devfsext.h>
@ -97,7 +92,7 @@ static void *pcac_devfs_token;
static int pca_sleep = 0;
static int pca_initialized = 0;
void pcaintr(struct clockframe *frame);
static void pcaintr(struct clockframe *frame);
static int pcaprobe(struct isa_device *dvp);
static int pcaattach(struct isa_device *dvp);
@ -121,7 +116,8 @@ static void pca_continue __P((void));
static void pca_init __P((void));
static void pca_pause __P((void));
static inline void conv(const void *table, void *buff, unsigned long n)
static inline void
conv(const void *table, void *buff, unsigned long n)
{
__asm__("1:\tmovb (%2), %3\n"
"\txlatb\n"
@ -152,7 +148,7 @@ pca_volume(int volume)
static void
pca_init()
pca_init(void)
{
pca_status.open = 0;
pca_status.queries = 0;
@ -233,7 +229,7 @@ pca_stop(void)
static void
pca_pause()
pca_pause(void)
{
int x = splhigh();
@ -249,7 +245,7 @@ pca_pause()
static void
pca_continue()
pca_continue(void)
{
int x = splhigh();
@ -313,7 +309,7 @@ pcaattach(struct isa_device *dvp)
}
static int
static int
pcaopen(dev_t dev, int flags, int fmt, struct proc *p)
{
/* audioctl device can always be opened */
@ -341,7 +337,7 @@ pcaopen(dev_t dev, int flags, int fmt, struct proc *p)
}
static int
static int
pcaclose(dev_t dev, int flags, int fmt, struct proc *p)
{
/* audioctl device can always be closed */
@ -357,7 +353,7 @@ pcaclose(dev_t dev, int flags, int fmt, struct proc *p)
}
static int
static int
pcawrite(dev_t dev, struct uio *uio, int flag)
{
int count, error, which, x;
@ -403,7 +399,7 @@ pcawrite(dev_t dev, struct uio *uio, int flag)
}
static int
static int
pcaioctl(dev_t dev, int cmd, caddr_t data, int flag, struct proc *p)
{
audio_info_t *auptr;
@ -467,7 +463,7 @@ pcaioctl(dev_t dev, int cmd, caddr_t data, int flag, struct proc *p)
}
void
static void
pcaintr(struct clockframe *frame)
{
if (pca_status.index < pca_status.in_use[pca_status.current]) {
@ -510,7 +506,7 @@ pcaintr(struct clockframe *frame)
}
int
static int
pcaselect(dev_t dev, int rw, struct proc *p)
{
int s = spltty();

View File

@ -1,526 +0,0 @@
/**************************************************************************
**
** $Id: pcibus.c,v 1.3 1996/09/03 10:23:51 asami Exp $
**
** pci bus subroutines for i386 architecture.
**
** FreeBSD
**
**-------------------------------------------------------------------------
**
** Copyright (c) 1994 Wolfgang Stanglmeier. All rights reserved.
**
** Redistribution and use in source and binary forms, with or without
** modification, are permitted provided that the following conditions
** are met:
** 1. Redistributions of source code must retain the above copyright
** notice, this list of conditions and the following disclaimer.
** 2. Redistributions in binary form must reproduce the above copyright
** notice, this list of conditions and the following disclaimer in the
** documentation and/or other materials provided with the distribution.
** 3. The name of the author may not be used to endorse or promote products
** derived from this software without specific prior written permission.
**
** THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
** IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
** OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
** IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
** INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
** NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
** THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
**
***************************************************************************
*/
#include "vector.h"
#include <sys/param.h>
#include <sys/systm.h>
#include <sys/kernel.h>
#include <i386/isa/icu.h>
#include <i386/isa/isa_device.h>
#include <pci/pcivar.h>
#include <pci/pcireg.h>
#include <pci/pcibus.h>
/*-----------------------------------------------------------------
**
** The following functions are provided by the pci bios.
** They are used only by the pci configuration.
**
** pcibus_setup():
** Probes for a pci system.
** Sets pci_maxdevice and pci_mechanism.
**
** pcibus_tag():
** Creates a handle for pci configuration space access.
** This handle is given to the read/write functions.
**
** pcibus_ftag():
** Creates a modified handle.
**
** pcibus_read():
** Read a long word from the pci configuration space.
** Requires a tag (from pcitag) and the register
** number (should be a long word alligned one).
**
** pcibus_write():
** Writes a long word to the pci configuration space.
** Requires a tag (from pcitag), the register number
** (should be a long word alligned one), and a value.
**
** pcibus_regirq():
** Register an interupt handler for a pci device.
** Requires a tag (from pcitag), the register number
** (should be a long word alligned one), and a value.
**
**-----------------------------------------------------------------
*/
static int
pcibus_check (void);
static void
pcibus_setup (void);
static pcici_t
pcibus_tag (u_char bus, u_char device, u_char func);
static pcici_t
pcibus_ftag (pcici_t tag, u_char func);
static u_long
pcibus_read (pcici_t tag, u_long reg);
static void
pcibus_write (pcici_t tag, u_long reg, u_long data);
static int
pcibus_ihandler_attach (int irq, inthand2_t *func, int arg, unsigned* maskptr);
static int
pcibus_ihandler_detach (int irq, inthand2_t *func);
static int
pcibus_imask_include (int irq, unsigned* maskptr);
static int
pcibus_imask_exclude (int irq, unsigned* maskptr);
static struct pcibus i386pci = {
"pci",
pcibus_setup,
pcibus_tag,
pcibus_ftag,
pcibus_read,
pcibus_write,
ICU_LEN,
pcibus_ihandler_attach,
pcibus_ihandler_detach,
pcibus_imask_include,
pcibus_imask_exclude,
};
/*
** Announce structure to generic driver
*/
DATA_SET (pcibus_set, i386pci);
/*--------------------------------------------------------------------
**
** Determine configuration mode
**
**--------------------------------------------------------------------
*/
#define CONF1_ADDR_PORT 0x0cf8
#define CONF1_DATA_PORT 0x0cfc
#define CONF1_ENABLE 0x80000000ul
#define CONF1_ENABLE_CHK 0x80000000ul
#define CONF1_ENABLE_MSK 0x7ff00000ul
#define CONF1_ENABLE_CHK1 0xff000001ul
#define CONF1_ENABLE_MSK1 0x80000001ul
#define CONF1_ENABLE_RES1 0x80000000ul
#define CONF2_ENABLE_PORT 0x0cf8
#ifdef PC98
#define CONF2_FORWARD_PORT 0x0cf9
#else
#define CONF2_FORWARD_PORT 0x0cfa
#endif
#define CONF2_ENABLE_CHK 0x0e
#define CONF2_ENABLE_RES 0x0e
static int
pcibus_check (void)
{
u_char device;
if (bootverbose) printf ("pcibus_check:\tdevice ");
for (device = 0; device < pci_maxdevice; device++) {
unsigned long id;
if (bootverbose)
printf ("%d ", device);
id = pcibus_read (pcibus_tag (0,device,0), 0);
if (id && id != 0xfffffffful) {
if (bootverbose) printf ("is there (id=%08lx)\n", id);
return 1;
}
}
if (bootverbose)
printf ("-- nothing found\n");
return 0;
}
static void
pcibus_setup (void)
{
unsigned long mode1res,oldval1;
unsigned char mode2res,oldval2;
oldval1 = inl (CONF1_ADDR_PORT);
if (bootverbose) {
printf ("pcibus_setup(1):\tmode 1 addr port (0x0cf8) is 0x%08lx\n", oldval1);
}
/*---------------------------------------
** Assume configuration mechanism 1 for now ...
**---------------------------------------
*/
if ((oldval1 & CONF1_ENABLE_MSK) == 0) {
pci_mechanism = 1;
pci_maxdevice = 32;
outl (CONF1_ADDR_PORT, CONF1_ENABLE_CHK);
outb (CONF1_ADDR_PORT +3, 0);
mode1res = inl (CONF1_ADDR_PORT);
outl (CONF1_ADDR_PORT, oldval1);
if (bootverbose)
printf ("pcibus_setup(1a):\tmode1res=0x%08lx (0x%08lx)\n",
mode1res, CONF1_ENABLE_CHK);
if (mode1res) {
if (pcibus_check())
return;
};
outl (CONF1_ADDR_PORT, CONF1_ENABLE_CHK1);
mode1res = inl(CONF1_ADDR_PORT);
outl (CONF1_ADDR_PORT, oldval1);
if (bootverbose)
printf ("pcibus_setup(1b):\tmode1res=0x%08lx (0x%08lx)\n",
mode1res, CONF1_ENABLE_CHK1);
if ((mode1res & CONF1_ENABLE_MSK1) == CONF1_ENABLE_RES1) {
if (pcibus_check())
return;
};
}
/*---------------------------------------
** Try configuration mechanism 2 ...
**---------------------------------------
*/
oldval2 = inb (CONF2_ENABLE_PORT);
if (bootverbose) {
printf ("pcibus_setup(2):\tmode 2 enable port (0x0cf8) is 0x%02x\n", oldval2);
}
if ((oldval2 & 0xf0) == 0) {
pci_mechanism = 2;
pci_maxdevice = 16;
outb (CONF2_ENABLE_PORT, CONF2_ENABLE_CHK);
mode2res = inb(CONF2_ENABLE_PORT);
outb (CONF2_ENABLE_PORT, oldval2);
if (bootverbose)
printf ("pcibus_setup(2a):\tmode2res=0x%02x (0x%02x)\n",
mode2res, CONF2_ENABLE_CHK);
if (mode2res == CONF2_ENABLE_RES) {
if (bootverbose)
printf ("pcibus_setup(2a):\tnow trying mechanism 2\n");
if (pcibus_check())
return;
}
}
/*---------------------------------------
** No PCI bus host bridge found
**---------------------------------------
*/
pci_mechanism = 0;
pci_maxdevice = 0;
}
/*--------------------------------------------------------------------
**
** Build a pcitag from bus, device and function number
**
**--------------------------------------------------------------------
*/
static pcici_t
pcibus_tag (unsigned char bus, unsigned char device, unsigned char func)
{
pcici_t tag;
tag.cfg1 = 0;
if (func >= 8) return tag;
switch (pci_mechanism) {
case 1:
if (device < 32) {
tag.cfg1 = CONF1_ENABLE
| (((u_long) bus ) << 16ul)
| (((u_long) device) << 11ul)
| (((u_long) func ) << 8ul);
}
break;
case 2:
if (device < 16) {
tag.cfg2.port = 0xc000 | (device << 8ul);
tag.cfg2.enable = 0xf0 | (func << 1ul);
tag.cfg2.forward = bus;
}
break;
};
return tag;
}
static pcici_t
pcibus_ftag (pcici_t tag, u_char func)
{
switch (pci_mechanism) {
case 1:
tag.cfg1 &= ~0x700ul;
tag.cfg1 |= (((u_long) func) << 8ul);
break;
case 2:
tag.cfg2.enable = 0xf0 | (func << 1ul);
break;
};
return tag;
}
/*--------------------------------------------------------------------
**
** Read register from configuration space.
**
**--------------------------------------------------------------------
*/
static u_long
pcibus_read (pcici_t tag, u_long reg)
{
u_long addr, data = 0;
if (!tag.cfg1) return (0xfffffffful);
switch (pci_mechanism) {
case 1:
addr = tag.cfg1 | (reg & 0xfc);
#ifdef PCI_DEBUG
printf ("pci_conf_read(1): addr=%x ", addr);
#endif
outl (CONF1_ADDR_PORT, addr);
data = inl (CONF1_DATA_PORT);
outl (CONF1_ADDR_PORT, 0 );
break;
case 2:
addr = tag.cfg2.port | (reg & 0xfc);
#ifdef PCI_DEBUG
printf ("pci_conf_read(2): addr=%x ", addr);
#endif
outb (CONF2_ENABLE_PORT , tag.cfg2.enable );
outb (CONF2_FORWARD_PORT, tag.cfg2.forward);
data = inl ((u_short) addr);
outb (CONF2_ENABLE_PORT, 0);
outb (CONF2_FORWARD_PORT, 0);
break;
};
#ifdef PCI_DEBUG
printf ("data=%x\n", data);
#endif
return (data);
}
/*--------------------------------------------------------------------
**
** Write register into configuration space.
**
**--------------------------------------------------------------------
*/
static void
pcibus_write (pcici_t tag, u_long reg, u_long data)
{
u_long addr;
if (!tag.cfg1) return;
switch (pci_mechanism) {
case 1:
addr = tag.cfg1 | (reg & 0xfc);
#ifdef PCI_DEBUG
printf ("pci_conf_write(1): addr=%x data=%x\n",
addr, data);
#endif
outl (CONF1_ADDR_PORT, addr);
outl (CONF1_DATA_PORT, data);
outl (CONF1_ADDR_PORT, 0 );
break;
case 2:
addr = tag.cfg2.port | (reg & 0xfc);
#ifdef PCI_DEBUG
printf ("pci_conf_write(2): addr=%x data=%x\n",
addr, data);
#endif
outb (CONF2_ENABLE_PORT, tag.cfg2.enable);
outb (CONF2_FORWARD_PORT, tag.cfg2.forward);
outl ((u_short) addr, data);
outb (CONF2_ENABLE_PORT, 0);
outb (CONF2_FORWARD_PORT, 0);
break;
};
}
/*-----------------------------------------------------------------------
**
** Register an interupt handler for a pci device.
**
**-----------------------------------------------------------------------
*/
static int
pcibus_ihandler_attach (int irq, inthand2_t *func, int arg, unsigned * maskptr)
{
char buf[16];
char *cp;
int free_id, id, result;
sprintf(buf, "pci irq%d", irq);
for (cp = intrnames, free_id = 0, id = 0; id < NR_DEVICES; id++) {
if (strcmp(cp, buf) == 0)
break;
if (free_id <= 0 && strcmp(cp, "pci irqnn") == 0)
free_id = id;
while (*cp++ != '\0')
;
}
if (id == NR_DEVICES) {
id = free_id;
if (id == 0) {
/*
* All pci irq counters are in use, perhaps because
* config is old so there aren't any. Abuse the
* clk0 counter.
*/
printf (
"pcibus_ihandler_attach: counting pci irq%d's as clk0 irqs\n",
irq);
}
}
result = register_intr(
irq, /* isa irq */
id, /* device id */
0, /* flags? */
func, /* handler */
maskptr, /* mask pointer */
arg); /* handler arg */
if (result) {
printf ("@@@ pcibus_ihandler_attach: result=%d\n", result);
return (result);
};
update_intr_masks();
INTREN ((1ul<<irq));
return (0);
}
static int
pcibus_ihandler_detach (int irq, inthand2_t *func)
{
int result;
INTRDIS ((1ul<<irq));
result = unregister_intr (irq, func);
if (result)
printf ("@@@ pcibus_ihandler_detach: result=%d\n", result);
update_intr_masks();
return (result);
}
static int
pcibus_imask_include (int irq, unsigned* maskptr)
{
unsigned mask;
if (!maskptr) return (0);
mask = 1ul << irq;
if (*maskptr & mask)
return (-1);
INTRMASK (*maskptr, mask);
update_intr_masks();
return (0);
}
static int
pcibus_imask_exclude (int irq, unsigned* maskptr)
{
unsigned mask;
if (!maskptr) return (0);
mask = 1ul << irq;
if (! (*maskptr & mask))
return (-1);
*maskptr &= ~mask;
update_intr_masks();
return (0);
}

View File

@ -1,163 +0,0 @@
/*
* NEED A COPYRIGHT NOPTICE HERE
*
* $Id: prof_machdep.c,v 1.2 1996/04/08 16:41:06 wollman Exp $
*/
#include <sys/param.h>
#include <sys/systm.h>
#include <machine/clock.h>
#ifdef PC98
#include <pc98/pc98/pc98.h>
#include <pc98/pc98/timerreg.h>
#else
#include <i386/isa/isa.h>
#include <i386/isa/timerreg.h>
#endif
#ifdef GUPROF
extern u_int cputime __P((void));
#endif
#ifdef __GNUC__
asm("
GM_STATE = 0
GMON_PROF_OFF = 3
.text
.align 4,0x90
.globl __mcount
__mcount:
#
# Check that we are profiling. Do it early for speed.
#
cmpl $GMON_PROF_OFF,__gmonparam+GM_STATE
je Lmcount_exit
#
# __mcount is the same as mcount except the caller hasn't changed
# the stack except to call here, so the caller's raddr is above
# our raddr.
#
movl 4(%esp),%edx
jmp Lgot_frompc
.align 4,0x90
.globl mcount
mcount:
cmpl $GMON_PROF_OFF,__gmonparam+GM_STATE
je Lmcount_exit
#
# The caller's stack frame has already been built, so %ebp is
# the caller's frame pointer. The caller's raddr is in the
# caller's frame following the caller's caller's frame pointer.
#
movl 4(%ebp),%edx
Lgot_frompc:
#
# Our raddr is the caller's pc.
#
movl (%esp),%eax
pushf
pushl %eax
pushl %edx
cli
call _mcount
addl $8,%esp
popf
Lmcount_exit:
ret
");
#else /* !__GNUC__ */
#error
#endif /* __GNUC__ */
#ifdef GUPROF
/*
* mexitcount saves the return register(s), loads selfpc and calls
* mexitcount(selfpc) to do the work. Someday it should be in a machine
* dependent file together with cputime(), __mcount and mcount. cputime()
* can't just be put in machdep.c because it has to be compiled without -pg.
*/
#ifdef __GNUC__
asm("
.text
#
# Dummy label to be seen when gprof -u hides mexitcount.
#
.align 4,0x90
.globl __mexitcount
__mexitcount:
nop
GMON_PROF_HIRES = 4
.align 4,0x90
.globl mexitcount
mexitcount:
cmpl $GMON_PROF_HIRES,__gmonparam+GM_STATE
jne Lmexitcount_exit
pushl %edx
pushl %eax
movl 8(%esp),%eax
pushf
pushl %eax
cli
call _mexitcount
addl $4,%esp
popf
popl %eax
popl %edx
Lmexitcount_exit:
ret
");
#else /* !__GNUC__ */
#error
#endif /* __GNUC__ */
/*
* Return the time elapsed since the last call. The units are machine-
* dependent.
*/
u_int
cputime()
{
u_int count;
u_int delta;
u_char low;
static u_int prev_count;
/*
* Read the current value of the 8254 timer counter 0.
*/
outb(TIMER_MODE, TIMER_SEL0 | TIMER_LATCH);
low = inb(TIMER_CNTR0);
count = low | (inb(TIMER_CNTR0) << 8);
/*
* The timer counts down from TIMER_CNTR0_MAX to 0 and then resets.
* While profiling is enabled, this routine is called at least twice
* per timer reset (for mcounting and mexitcounting hardclock()),
* so at most one reset has occurred since the last call, and one
* has occurred iff the current count is larger than the previous
* count. This allows counter underflow to be detected faster
* than in microtime().
*/
delta = prev_count - count;
prev_count = count;
if ((int) delta <= 0)
return (delta + timer0_max_count);
return (delta);
}
#else /* not GUPROF */
#ifdef __GNUC__
asm("
.text
.align 4,0x90
.globl mexitcount
mexitcount:
ret
");
#else /* !__GNUC__ */
#error
#endif /* __GNUC__ */
#endif /* GUPROF */

View File

@ -1,520 +0,0 @@
/*
* random_machdep.c -- A strong random number generator
*
* $Id: random_machdep.c,v 1.7 1996/10/09 21:46:41 asami Exp $
*
* Version 0.95, last modified 18-Oct-95
*
* Copyright Theodore Ts'o, 1994, 1995. 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, and the entire permission notice in its entirety,
* including the disclaimer of warranties.
* 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. The name of the author may not be used to endorse or promote
* products derived from this software without specific prior
* written permission.
*
* ALTERNATIVELY, this product may be distributed under the terms of
* the GNU Public License, in which case the provisions of the GPL are
* required INSTEAD OF the above restrictions. (This clause is
* necessary due to a potential bad interaction between the GPL and
* the restrictions contained in a BSD-style copyright.)
*
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESS OR IMPLIED
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
* DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT,
* INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
* (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
* SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
* STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
* OF THE POSSIBILITY OF SUCH DAMAGE.
*/
/*
* modified for PC-9801 by KATO T. of Nagoya University
*/
#include "opt_cpu.h"
#include <sys/param.h>
#include <sys/systm.h>
#include <sys/kernel.h>
#include <sys/select.h>
#include <sys/fcntl.h>
#include <machine/clock.h>
#include <machine/random.h>
#include <i386/isa/icu.h>
#ifdef PC98
#include <pc98/pc98/pc98.h>
#include <pc98/pc98/timerreg.h>
#else
#include <i386/isa/isa.h>
#include <i386/isa/timerreg.h>
#endif
#define MAX_BLKDEV 4
/*
* The pool is stirred with a primitive polynomial of degree 128
* over GF(2), namely x^128 + x^99 + x^59 + x^31 + x^9 + x^7 + 1.
* For a pool of size 64, try x^64+x^62+x^38+x^10+x^6+x+1.
*/
#define POOLWORDS 128 /* Power of 2 - note that this is 32-bit words */
#define POOLBITS (POOLWORDS*32)
#if POOLWORDS == 128
#define TAP1 99 /* The polynomial taps */
#define TAP2 59
#define TAP3 31
#define TAP4 9
#define TAP5 7
#elif POOLWORDS == 64
#define TAP1 62 /* The polynomial taps */
#define TAP2 38
#define TAP3 10
#define TAP4 6
#define TAP5 1
#else
#error No primitive polynomial available for chosen POOLWORDS
#endif
#define WRITEBUFFER 512 /* size in bytes */
/* There is actually only one of these, globally. */
struct random_bucket {
u_int add_ptr;
u_int entropy_count;
int input_rotate;
u_int32_t *pool;
struct selinfo rsel;
};
/* There is one of these per entropy source */
struct timer_rand_state {
u_long last_time;
int last_delta;
int nbits;
};
static struct random_bucket random_state;
static u_int32_t random_pool[POOLWORDS];
static struct timer_rand_state keyboard_timer_state;
static struct timer_rand_state extract_timer_state;
static struct timer_rand_state irq_timer_state[ICU_LEN];
#ifdef notyet
static struct timer_rand_state blkdev_timer_state[MAX_BLKDEV];
#endif
static struct wait_queue *random_wait;
inthand2_t *sec_intr_handler[ICU_LEN];
int sec_intr_unit[ICU_LEN];
#ifndef MIN
#define MIN(a,b) (((a) < (b)) ? (a) : (b))
#endif
void
rand_initialize(void)
{
random_state.add_ptr = 0;
random_state.entropy_count = 0;
random_state.pool = random_pool;
random_wait = NULL;
random_state.rsel.si_flags = 0;
random_state.rsel.si_pid = 0;
}
/*
* This function adds an int into the entropy "pool". It does not
* update the entropy estimate. The caller must do this if appropriate.
*
* The pool is stirred with a primitive polynomial of degree 128
* over GF(2), namely x^128 + x^99 + x^59 + x^31 + x^9 + x^7 + 1.
* For a pool of size 64, try x^64+x^62+x^38+x^10+x^6+x+1.
*
* We rotate the input word by a changing number of bits, to help
* assure that all bits in the entropy get toggled. Otherwise, if we
* consistently feed the entropy pool small numbers (like ticks and
* scancodes, for example), the upper bits of the entropy pool don't
* get affected. --- TYT, 10/11/95
*/
static inline void
add_entropy_word(struct random_bucket *r, const u_int32_t input)
{
u_int i;
u_int32_t w;
w = (input << r->input_rotate) | (input >> (32 - r->input_rotate));
i = r->add_ptr = (r->add_ptr - 1) & (POOLWORDS-1);
if (i)
r->input_rotate = (r->input_rotate + 7) & 31;
else
/*
* At the beginning of the pool, add an extra 7 bits
* rotation, so that successive passes spread the
* input bits across the pool evenly.
*/
r->input_rotate = (r->input_rotate + 14) & 31;
/* XOR in the various taps */
w ^= r->pool[(i+TAP1)&(POOLWORDS-1)];
w ^= r->pool[(i+TAP2)&(POOLWORDS-1)];
w ^= r->pool[(i+TAP3)&(POOLWORDS-1)];
w ^= r->pool[(i+TAP4)&(POOLWORDS-1)];
w ^= r->pool[(i+TAP5)&(POOLWORDS-1)];
w ^= r->pool[i];
/* Rotate w left 1 bit (stolen from SHA) and store */
r->pool[i] = (w << 1) | (w >> 31);
}
/*
* This function adds entropy to the entropy "pool" by using timing
* delays. It uses the timer_rand_state structure to make an estimate
* of how any bits of entropy this call has added to the pool.
*
* The number "num" is also added to the pool - it should somehow describe
* the type of event which just happened. This is currently 0-255 for
* keyboard scan codes, and 256 upwards for interrupts.
* On the i386, this is assumed to be at most 16 bits, and the high bits
* are used for a high-resolution timer.
*/
static void
add_timer_randomness(struct random_bucket *r, struct timer_rand_state *state,
u_int num)
{
int delta, delta2;
u_int nbits;
u_int32_t time;
#if defined(I586_CPU) || defined(I686_CPU)
if (i586_ctr_freq != 0) {
num ^= (u_int32_t) rdtsc() << 16;
r->entropy_count += 2;
} else {
#endif
disable_intr();
outb(TIMER_MODE, TIMER_SEL0 | TIMER_LATCH);
num ^= inb(TIMER_CNTR0) << 16;
num ^= inb(TIMER_CNTR0) << 24;
enable_intr();
r->entropy_count += 2;
#if defined(I586_CPU) || defined(I686_CPU)
}
#endif
time = ticks;
add_entropy_word(r, (u_int32_t) num);
add_entropy_word(r, time);
/*
* Calculate number of bits of randomness we probably
* added. We take into account the first and second order
* deltas in order to make our estimate.
*/
delta = time - state->last_time;
state->last_time = time;
delta2 = delta - state->last_delta;
state->last_delta = delta;
if (delta < 0) delta = -delta;
if (delta2 < 0) delta2 = -delta2;
delta = MIN(delta, delta2) >> 1;
for (nbits = 0; delta; nbits++)
delta >>= 1;
r->entropy_count += nbits;
/* Prevent overflow */
if (r->entropy_count > POOLBITS)
r->entropy_count = POOLBITS;
if (r->entropy_count >= 8)
selwakeup(&random_state.rsel);
}
void
add_keyboard_randomness(u_char scancode)
{
add_timer_randomness(&random_state, &keyboard_timer_state, scancode);
}
void
add_interrupt_randomness(int irq)
{
(sec_intr_handler[irq])(sec_intr_unit[irq]);
add_timer_randomness(&random_state, &irq_timer_state[irq], irq);
}
#ifdef notused
void
add_blkdev_randomness(int major)
{
if (major >= MAX_BLKDEV)
return;
add_timer_randomness(&random_state, &blkdev_timer_state[major],
0x200+major);
}
#endif /* notused */
/*
* MD5 transform algorithm, taken from code written by Colin Plumb,
* and put into the public domain
*
* QUESTION: Replace this with SHA, which as generally received better
* reviews from the cryptographic community?
*/
/* The four core functions - F1 is optimized somewhat */
/* #define F1(x, y, z) (x & y | ~x & z) */
#define F1(x, y, z) (z ^ (x & (y ^ z)))
#define F2(x, y, z) F1(z, x, y)
#define F3(x, y, z) (x ^ y ^ z)
#define F4(x, y, z) (y ^ (x | ~z))
/* This is the central step in the MD5 algorithm. */
#define MD5STEP(f, w, x, y, z, data, s) \
( w += f(x, y, z) + data, w = w<<s | w>>(32-s), w += x )
/*
* The core of the MD5 algorithm, this alters an existing MD5 hash to
* reflect the addition of 16 longwords of new data. MD5Update blocks
* the data and converts bytes into longwords for this routine.
*/
static void
MD5Transform(u_int32_t buf[4],
u_int32_t const in[16])
{
u_int32_t a, b, c, d;
a = buf[0];
b = buf[1];
c = buf[2];
d = buf[3];
MD5STEP(F1, a, b, c, d, in[ 0]+0xd76aa478, 7);
MD5STEP(F1, d, a, b, c, in[ 1]+0xe8c7b756, 12);
MD5STEP(F1, c, d, a, b, in[ 2]+0x242070db, 17);
MD5STEP(F1, b, c, d, a, in[ 3]+0xc1bdceee, 22);
MD5STEP(F1, a, b, c, d, in[ 4]+0xf57c0faf, 7);
MD5STEP(F1, d, a, b, c, in[ 5]+0x4787c62a, 12);
MD5STEP(F1, c, d, a, b, in[ 6]+0xa8304613, 17);
MD5STEP(F1, b, c, d, a, in[ 7]+0xfd469501, 22);
MD5STEP(F1, a, b, c, d, in[ 8]+0x698098d8, 7);
MD5STEP(F1, d, a, b, c, in[ 9]+0x8b44f7af, 12);
MD5STEP(F1, c, d, a, b, in[10]+0xffff5bb1, 17);
MD5STEP(F1, b, c, d, a, in[11]+0x895cd7be, 22);
MD5STEP(F1, a, b, c, d, in[12]+0x6b901122, 7);
MD5STEP(F1, d, a, b, c, in[13]+0xfd987193, 12);
MD5STEP(F1, c, d, a, b, in[14]+0xa679438e, 17);
MD5STEP(F1, b, c, d, a, in[15]+0x49b40821, 22);
MD5STEP(F2, a, b, c, d, in[ 1]+0xf61e2562, 5);
MD5STEP(F2, d, a, b, c, in[ 6]+0xc040b340, 9);
MD5STEP(F2, c, d, a, b, in[11]+0x265e5a51, 14);
MD5STEP(F2, b, c, d, a, in[ 0]+0xe9b6c7aa, 20);
MD5STEP(F2, a, b, c, d, in[ 5]+0xd62f105d, 5);
MD5STEP(F2, d, a, b, c, in[10]+0x02441453, 9);
MD5STEP(F2, c, d, a, b, in[15]+0xd8a1e681, 14);
MD5STEP(F2, b, c, d, a, in[ 4]+0xe7d3fbc8, 20);
MD5STEP(F2, a, b, c, d, in[ 9]+0x21e1cde6, 5);
MD5STEP(F2, d, a, b, c, in[14]+0xc33707d6, 9);
MD5STEP(F2, c, d, a, b, in[ 3]+0xf4d50d87, 14);
MD5STEP(F2, b, c, d, a, in[ 8]+0x455a14ed, 20);
MD5STEP(F2, a, b, c, d, in[13]+0xa9e3e905, 5);
MD5STEP(F2, d, a, b, c, in[ 2]+0xfcefa3f8, 9);
MD5STEP(F2, c, d, a, b, in[ 7]+0x676f02d9, 14);
MD5STEP(F2, b, c, d, a, in[12]+0x8d2a4c8a, 20);
MD5STEP(F3, a, b, c, d, in[ 5]+0xfffa3942, 4);
MD5STEP(F3, d, a, b, c, in[ 8]+0x8771f681, 11);
MD5STEP(F3, c, d, a, b, in[11]+0x6d9d6122, 16);
MD5STEP(F3, b, c, d, a, in[14]+0xfde5380c, 23);
MD5STEP(F3, a, b, c, d, in[ 1]+0xa4beea44, 4);
MD5STEP(F3, d, a, b, c, in[ 4]+0x4bdecfa9, 11);
MD5STEP(F3, c, d, a, b, in[ 7]+0xf6bb4b60, 16);
MD5STEP(F3, b, c, d, a, in[10]+0xbebfbc70, 23);
MD5STEP(F3, a, b, c, d, in[13]+0x289b7ec6, 4);
MD5STEP(F3, d, a, b, c, in[ 0]+0xeaa127fa, 11);
MD5STEP(F3, c, d, a, b, in[ 3]+0xd4ef3085, 16);
MD5STEP(F3, b, c, d, a, in[ 6]+0x04881d05, 23);
MD5STEP(F3, a, b, c, d, in[ 9]+0xd9d4d039, 4);
MD5STEP(F3, d, a, b, c, in[12]+0xe6db99e5, 11);
MD5STEP(F3, c, d, a, b, in[15]+0x1fa27cf8, 16);
MD5STEP(F3, b, c, d, a, in[ 2]+0xc4ac5665, 23);
MD5STEP(F4, a, b, c, d, in[ 0]+0xf4292244, 6);
MD5STEP(F4, d, a, b, c, in[ 7]+0x432aff97, 10);
MD5STEP(F4, c, d, a, b, in[14]+0xab9423a7, 15);
MD5STEP(F4, b, c, d, a, in[ 5]+0xfc93a039, 21);
MD5STEP(F4, a, b, c, d, in[12]+0x655b59c3, 6);
MD5STEP(F4, d, a, b, c, in[ 3]+0x8f0ccc92, 10);
MD5STEP(F4, c, d, a, b, in[10]+0xffeff47d, 15);
MD5STEP(F4, b, c, d, a, in[ 1]+0x85845dd1, 21);
MD5STEP(F4, a, b, c, d, in[ 8]+0x6fa87e4f, 6);
MD5STEP(F4, d, a, b, c, in[15]+0xfe2ce6e0, 10);
MD5STEP(F4, c, d, a, b, in[ 6]+0xa3014314, 15);
MD5STEP(F4, b, c, d, a, in[13]+0x4e0811a1, 21);
MD5STEP(F4, a, b, c, d, in[ 4]+0xf7537e82, 6);
MD5STEP(F4, d, a, b, c, in[11]+0xbd3af235, 10);
MD5STEP(F4, c, d, a, b, in[ 2]+0x2ad7d2bb, 15);
MD5STEP(F4, b, c, d, a, in[ 9]+0xeb86d391, 21);
buf[0] += a;
buf[1] += b;
buf[2] += c;
buf[3] += d;
}
#undef F1
#undef F2
#undef F3
#undef F4
#undef MD5STEP
#if POOLWORDS % 16
#error extract_entropy() assumes that POOLWORDS is a multiple of 16 words.
#endif
/*
* This function extracts randomness from the "entropy pool", and
* returns it in a buffer. This function computes how many remaining
* bits of entropy are left in the pool, but it does not restrict the
* number of bytes that are actually obtained.
*/
static inline int
extract_entropy(struct random_bucket *r, char *buf, int nbytes)
{
int ret, i;
u_int32_t tmp[4];
add_timer_randomness(r, &extract_timer_state, nbytes);
/* Redundant, but just in case... */
if (r->entropy_count > POOLBITS)
r->entropy_count = POOLBITS;
/* Why is this here? Left in from Ted Ts'o. Perhaps to limit time. */
if (nbytes > 32768)
nbytes = 32768;
ret = nbytes;
if (r->entropy_count / 8 >= nbytes)
r->entropy_count -= nbytes*8;
else
r->entropy_count = 0;
while (nbytes) {
/* Hash the pool to get the output */
tmp[0] = 0x67452301;
tmp[1] = 0xefcdab89;
tmp[2] = 0x98badcfe;
tmp[3] = 0x10325476;
for (i = 0; i < POOLWORDS; i += 16)
MD5Transform(tmp, r->pool+i);
/* Modify pool so next hash will produce different results */
add_entropy_word(r, tmp[0]);
add_entropy_word(r, tmp[1]);
add_entropy_word(r, tmp[2]);
add_entropy_word(r, tmp[3]);
/*
* Run the MD5 Transform one more time, since we want
* to add at least minimal obscuring of the inputs to
* add_entropy_word(). --- TYT
*/
MD5Transform(tmp, r->pool);
/* Copy data to destination buffer */
i = MIN(nbytes, 16);
bcopy(tmp, buf, i);
nbytes -= i;
buf += i;
}
/* Wipe data from memory */
bzero(tmp, sizeof(tmp));
return ret;
}
#ifdef notused /* XXX NOT the exported kernel interface */
/*
* This function is the exported kernel interface. It returns some
* number of good random numbers, suitable for seeding TCP sequence
* numbers, etc.
*/
void
get_random_bytes(void *buf, u_int nbytes)
{
extract_entropy(&random_state, (char *) buf, nbytes);
}
#endif /* notused */
u_int
read_random(char *buf, u_int nbytes)
{
if ((nbytes * 8) > random_state.entropy_count)
nbytes = random_state.entropy_count / 8;
return extract_entropy(&random_state, buf, nbytes);
}
u_int
read_random_unlimited(char *buf, u_int nbytes)
{
return extract_entropy(&random_state, buf, nbytes);
}
#ifdef notused
u_int
write_random(const char *buf, u_int nbytes)
{
u_int i;
u_int32_t word, *p;
for (i = nbytes, p = (u_int32_t *)buf;
i >= sizeof(u_int32_t);
i-= sizeof(u_int32_t), p++)
add_entropy_word(&random_state, *p);
if (i) {
word = 0;
bcopy(p, &word, i);
add_entropy_word(&random_state, word);
}
return nbytes;
}
#endif /* notused */
int
random_select(dev_t dev, int rw, struct proc *p)
{
int s, ret;
if (rw == FWRITE)
return 1; /* heh. */
s = splhigh();
if (random_state.entropy_count >= 8)
ret = 1;
else {
selrecord(p, &random_state.rsel);
ret = 0;
}
splx(s);
return ret;
}

View File

@ -1,122 +0,0 @@
Changelog for version 3.0-950506
------------------------------------
Since 3.0-94xxxx
- Too many changes
Since 3.0-940818
- Fixes for Linux 1.1.4x.
- Disables Disney Sound System with SG NX Pro 16 (less noise).
Since 2.90-2
- Fixes to soundcard.h
- Non blocking mode to /dev/sequencer
- Experimental detection code for Ensoniq Soundscape.
Since 2.90
- Minor and major bug fixes
Since pre-3.0-940712
- GUS MAX support
- Partially working MSS/WSS support (could work with some cards).
- Hardware u-Law and A-Law support with AD1848/CS4248 and CS4231 codecs
(GUS MAX, GUS16, WSS etc). Hardware ADPCM is possible with GUS16 and
GUS MAX, but it doesn't work yet.
Since pre-3.0-940426
- AD1848/CS4248/CS4231 codec support (MSS, GUS MAX, Aztec, Orchid etc).
This codec chip is used in various soundcards. This version is developed
for the 16 bit daughtercard of GUS. It should work with other cards also
if the following requirements are met:
- The I/O, IRQ and DMA settings are jumper selectable or
the card is initialized by booting DOS before booting Linux (etc.).
- You add the IO, IRQ and DMA settings manually to the local.h.
(Just define GUS16_BASE, GUS16_IRQ and GUS16_DMA). Note that
the base address bust be the base address of the codec chip not the
card itself. For the GUS16 these are the same but most MSS compatible
cards have the codec located at card_base+4.
- Some minor changes
Since 2.5 (******* MAJOR REWRITE ***********)
This version is based on v2.3. I have tried to maintain two versions
together so that this one should have the same features than v2.5.
Something may still be missing. If you notice such things, please let me
know.
The Readme.v30 contains more details.
- /dev/midi## devices.
- /dev/sequencer2
Since 2.5-beta2
- Some fine tuning to the GUS v3.7 mixer code.
- Fixed speed limits for the plain SB (1.0 to 2.0).
Since 2.5-beta
- Fixed OPL-3 detection with SB. Caused problems with PAS16.
- GUS v3.7 mixer support.
Since 2.4
- Mixer support for Sound Galaxy NX Pro (define __SGNXPRO__ on your local.h).
- Fixed truncated sound on /dev/dsp when the device is closed.
- Linear volume mode for GUS
- Pitch bends larger than +/- 2 octaves.
- MIDI recording for SB and SB Pro. (Untested).
- Some other fixes.
- SB16 MIDI and DSP drivers only initialized if SB16 actually installed.
- Implemented better detection for OPL-3. This should be useful if you
have an old SB Pro (the non-OPL-3 one) or a SB 2.0 clone which has a OPL-3.
- SVR4.2 support by Ian Hartas. Initial ALPHA TEST version (untested).
Since 2.3b
- Fixed bug which made it impossible to make long recordings to disk.
Recording was not restarted after a buffer overflow situation.
- Limited mixer support for GUS.
- Numerous improvements to the GUS driver by Andrew Robinson. Including
some click removal etc.
Since 2.3
- Fixed some minor bugs in the SB16 driver.
Since 2.2b
- Full SB16 DSP support. 8/16 bit, mono/stereo
- The SCO and FreeBSD versions should be in sync now. There are some
problems with SB16 and GUS in the freebsd versions.
The DMA buffer allocation of the SCO version has been polished but
there could still be some problems. At least it hogs memory.
The DMA channel
configuration method used in the sco/System is a hack.
- Support for the MPU emulation of the SB16.
- Some big arrays are now allocated boot time. This makes the bss segment
smaller which makes it possible to use the full driver with
NetBSD. These arrays are not allocated if no suitable soundcard is available.
- Fixed a bug in the compute_and_set_volume in gus_wave.c
- Fixed the too fast mono playback problem of SB Pro and PAS16.
Since 2.2
- Stereo recording for SB Pro. Somehow it was missing and nobody
had noticed it earlier.
- Minor polishing.
- Interpreting of boot time arguments (sound=) for Linux.
- Breakup of sb_dsp.c. Parts of the code has been moved to
sb_mixer.c and sb_midi.c
Since 2.1
- Preliminary support for SB16.
- The SB16 mixer is supported in it's native mode.
- Digitized voice capability up to 44.1 kHz/8 bit/mono
(16 bit and stereo support coming in the next release).
- Fixed some bugs in the digitized voice driver for PAS16.
- Proper initialization of the SB emulation of latest PAS16 models.
- Significantly improved /dev/dsp and /dev/audio support.
- Now supports half duplex mode. It's now possible to record and
playback without closing and reopening the device.
- It's possible to use smaller buffers than earlier. There is a new
ioctl(fd, SNDCTL_DSP_SUBDIVIDE, &n) where n should be 1, 2 or 4.
This call instructs the driver to use smaller buffers. The default
buffer size (0.5 to 1.0 seconds) is divided by n. Should be called
immediately after opening the device.
Since 2.0
Just cosmetic changes.

View File

@ -1,86 +0,0 @@
VoxWare v2.90 release notes
--------------------------
This version includes some hidden features which
are described in the file experimental.txt
Some of these features are not enabled by default. Look at
experimental.txt for more info.
I just decided to release this version with some
incompletely implemented features disabled since
there are some new features required by a popular
application. In addition there is also support
for the GUS MAX and the 16 bit sampling option of GUS.
The MSS/WSS support works now. At least with SG NX Pro 16.
********* IMPORTANT *****************************************
Linux 1.0 or later is required to by this driver version.
Don't distribute binaries which use /dev/sequencer and are
compiled with the soundcard.h of this version. They will
not work with version 2.x of the driver.
*************************************************************
You will need the snd-util-2.5.tar.gz and snd-data-0.1.tar.Z
packages to use this driver. They should be in the same
ftp site or BBS from where you got this driver. For
example at nic.funet.fi:pub/OS/Linux/*.
If you are looking for the installation instructions, please
look at linux/Readme.
Compatibility with the earlier versions
---------------------------------------
This version is backward compatible with the version 2.X. All programs
compiled with sys/soundcard.h of v2.X should work without problems.
PROGRAMS COMPILED WITH THE sys/soundcard.h OF THIS VERSION WILL NOT
WORK WITH v2.X DRIVER. BE CAREFUL WHEN DISTRIBUTING BINARIES COMPILED
FOR THIS VERSION.
Contributors
------------
This driver contains code by several contributors. In addition several other
persons have given useful suggestions. The following is a list of major
contributors. (I could have forgotten some names.)
Craig Metz 1/2 of the PAS16 Mixer and PCM support
Rob Hooft Volume computation algorithm for the FM synth.
Mika Liljeberg uLaw encoding and decoding routines
Greg Lee Volume computation algorithm for the GUS and
lot's of valuable suggestions.
Andy Warner ISC port
Jim Lowe FreeBSD port
Anders Baekgaard Bughunting and valuable suggestions.
Joerg Schubert SB16 DSP support.
Andrew Robinson Improvements to the GUS driver
Megens SA MIDI recording for SB and SB Pro.
Mikael Nordqvist Linear volume support for GUS.
Mikael Nordqvist Linear volume support for GUS.
Ian Hartas SVR4.2 port
Markus Aroharju and
Risto Kankkunen Major contributions to the mixer support
of GUS v3.7.
Hunyue Yau Mixer support for SG NX Pro.
Marc Hoffman PSS support.
Regards,
Hannu Savolainen
hannu@voxware.pp.fi
Snail mail: Hannu Savolainen
Hiekkalaiturintie 3 A 8
00980 Helsinki
Finland
FAX: +358 0 341 6272 (answers if I have my machine (mgetty) on).
NOTE! I probably don't answer to Snail mail or FAX messages. Sending answer
to each of them is simply too expensive and time consuming. However I
try to reply every email message I get (within a week). If you don't
get response, please check how your address is written in the message
header. I can't answer if I don't have a valid reply address.

View File

@ -1,6 +0,0 @@
Informations about Audio Excel DSP 16 can be found in the source
file aedsp16.c
Please, read the head of the source before using it. It contain useful
informations.
Riccardo

View File

@ -1,87 +0,0 @@
Linux sound-driver module
(c) Peter Trattler
License: GPL (Gnu Public License)
Idea:
I've modified the sources for the sound driver to allow simply insert and
remove the sound driver from the kernel by calling (only available for Linux)
insmod /usr/src/linux/modules/sound.o
and
rmmod sound
This may be useful if you are doing one of the following things:
1) Debugging the sound driver
2) Creating a new device within the sound-driver
3) You do not the sound driver all the time (as it wastes quite a lot of
memory for its buffers)
Compilation:
Go to /usr/src/linux and make the following steps:
a) configure the sound driver: To do that call "make config" and enable the
sound-driver -- you will be asked different questions about your
sound-hardware (remember not to use a too big DMA-Buffer size; you
should use 16kB, if you have 16Bit devices, otherwise you can use 32kB)
b) disable the sound driver in the kernel: call make config again but answer
'N' to "Sound card support"
c) run "make modules"; the sound-driver sound.o should end up in
/usr/src/linux/modules
If memory is tight:
I've allocated at about 70kB for the sound-drivers internal tables. If this
is too much, 'insmod sound.o' will generate the following warning
...
use 'insmod memsize=xxxx'
...
You can only use this command, if you have (I think) at least
modules-1.1.87 or up. You can also switch debugging on by running the command
insmod sound.o debugmem=1
Files I changed:
I've only changed the files soundcard.c(most changes) and some changes within
the Makefile, sound_config.h and the Makefile in /usr/src/linux/drivers
Bugs:
a) As the kmalloc (..., GFP_DMA) caused some unexpected errors (I don't know if
it is my fault), I created some code, which is (by default) enabled by
#define KMALLOC_DMA_BROKEN 1 (within soundcard.c).
It trys to allocate a large enough region, so that the complete dma-buffer
can be occupied in this space. If it does not fit within this region it
doubles the size of it. But this can cause problems, if the sound-buffer is
too big (as kmalloc can only handle regions at up to circa 100kB).
So take care to use for 8Bit devices a sound-DMA-buffer of 32kB (maximum)
and for 16Bit devices a maximum of 16kB. Otherwise the allocation scheme
might fail.
b) Buffers allocated by the different sound devices via calls to kmalloc are
not freed, if the sound driver is removed again (these buffers tend to be
quite small -- so it does not harm a lot)
c) If there is not enough (kernel-) memory available, the installation of
the sound-driver fails. (This happens quite often, if you did not install the
driver right after booting -- [PS: I've only got 5MB of Ram, so this might
be the source for this problem])
Author:
Peter Trattler (peter@sbox.tu-graz.ac.at)

View File

@ -1,142 +0,0 @@
VoxWare v3.0
------------
This is a late alpha/early beta of the VoxWare v3.0 to be relased May/June 95.
All features of v2.90-2 should work as earlier. There could be some
omissions but they are unintentional. I started this version thread
after v2.3 so all features implemented before it are there.
New features
============
There are now two new device interfaces. The /dev/midi## is a raw
tty like interface to MIDI ports. There is a device file for each MIDI
port on your system. They are named (/dev/midi00 to /dev/midiNN).
The second addition is the /dev/music which is higher level interface
than the old /dev/sequencer. It's intended for writing device independent
applications like sequencers.
/dev/midi##
-----------
This interface should be usefull for applications like MIDI sysex librarians.
There are (currently) no timing features so making music could be impossible.
There are as many /dev/midi## devices as there are MIDI ports in the system.
The /dev/midi00 is connected to the first one, /dev/midi01 to the second etc.
These devices work like tty devices in raw mode. Everything written to them is
sent out to the MIDI port. There is currently an extra delay of at most
1/100th of sec but it will be removed later.
The reading algorithm is little bit more complicated. There are two different
cases:
1) There is at least one byte in the input buffer.
The read returns as many bytes as it can without waiting for more bytes.
For example when a process reads 100 bytes and there are 10 bytes in the
buffer, the read returns just 10 bytes.
2) The input buffer is empty when the process calls read.
The read waits for the first byte and then continues as in case 1. By
default it waits infinitely but there is an ioctl for setting a timeout
for this. The ioctl(fd, SNDCTL_MIDI_PRETIME, &time) changes the timeout.
The time is given in 1/10th of seconds (10 means one second).
Other ioctl calls:
ioctl(fd, SNDCTL_MIDI_MPUMODE, &mode) is available for full MPU-401
compatible devices such as MPU-IPC-T, MQ PC Midi Card or MQX-32.
It's not available for the so called MPU UART ports of some soundcards
(PAS16, SB16 etc). By default the MIDI port is in UART mode after open.
If this ioctl is called with mode=1, the interface is put to the intelligent
(coprocessor) mode. NOTE! The MIDI port will be reset when this ioctl is called.
It could have some strange effects if not called immediately after open. This
vall returns EINVAL if the midi port doesn't support the MPU-401 intelligent
mode.
ioctl(fd, SNDCTL_MIDI_MPUCMD, &cmdstruct) is valid only if the MIDI port
is put to the coprocessor mode using ioctl(SNDCTL_MIDI_MPUMODE). It's used to
send commands to a MPU-401 compatible MIDI cards. Please refer to the
MPU-401 Technical Reference Manual (or Music Quest Technical Reference
Manual) for descriptions of the commands.
The argument of SNDCTL_MIDI_MPUCOMMAND is of type mpu_command_rec. It
has the following fields:
typedef struct {
unsigned char cmd;
char nr_args, nr_returns;
unsigned char data[30];
} mpu_command_rec;
where:
cmd Contains the command number.
nr_args Number of arguments of the command.
MUST BE INITIALIZED BEFORE CALL
nr_returns Number of bytes returned by the command.
MUST BE INITIALIZED BEFORE CALL
data Buffer for the command arguments and returned
data.
Be extremely carefull with the nr_args and nr_returns fields. They
must match the command. An incorrect value will put the card and
the driver out of sync. Refer to the MPU-401/MQX-32M documentation for further
datails.
/dev/music (/dev/sequencer2)
----------------------------
This device file works much like the /dev/sequencer which has been present
since the beginning. The main differences are the following:
- /dev/sequencer makes the MIDI ports to look like the synth devices. In fact
the result is somewhere between the MIDI specification and the synth devices of
/dev/sequencer. Both kind of devices are accessed using the SEQ_START_NOTE()
like macros. The voice number parameters of the API macros have been redefined
to denote MIDI channels. This means that the driver allocates voices for
the channels automaticly (this is a responsibility/right of an application
with /dev/sequencer). The result is that a SEQ_START_NOTE() macro has
similar effects for a synth channel than on a MIDI port. This kind of
solution provides better device independence than the /dev/sequencer. The
drawback is that the new interface doesn't permit so low level access to the
device as the /dev/sequencer does. An application developer must choose between
these two interfaces. I think the old /dev/sequencer is better for applications
like module players while the new one is better for making generic sequencer
programs.
- There are no separate MIDI devices with the /dev/sequencer2. The
ioctl(SNDCTL_SEQ_NRMIDIS) returns always zero. Instead the MIDI ports are
shown as synth devices. ioctl(SNDCTL_SEQ_NRSYNTHS) on /dev/sequencer2 will
return sum of internal synthesizers (GUS, OPL3) and MIDI ports in the systems.
- The new interface is used much like the ordinary /dev/sequencer. The
event format is new so you have to use the API macros defined in the
sys/soundcard.h. The interface is will propably change before the final 3.0
release but using the API macros should ensure compatibility in source level.
The new event format is not recognized by version 2.X so don't try to
distribute binaries compiled with soundcard.h of v3.X.
- The basic API useage is similar to the current one. There are some new
macros but the older ones should work as earlier. The most important
incompatibility is that the /dev/sequencer2 driver allocates voices itself.
The other one is that the application must send SEQ_START_TIMER() as it's
first event. Otherwise the timer is not started and the application waits
infinitely.
There are several new features but I don't document them here. There are
some info in the soundcard.h (near the end). I have also included some
sample code in the directory v30. Full documentation will
appear in the Hacker's Guide later.
Don't hesitate to contact me in case you have questions or comments.
Hannu Savolainen
hannu@voxware.pp.fi

View File

@ -1,55 +0,0 @@
/*
* sound/adlib_card.c
*
* Detection routine for the AdLib card.
*
* Copyright by Hannu Savolainen 1993
*
* 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.
*
* 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.
*
*/
#ifdef PC98
#include <pc98/pc98/sound/sound_config.h>
#else
#include <i386/isa/sound/sound_config.h>
#endif
#if defined(CONFIGURE_SOUNDCARD) && !defined(EXCLUDE_YM3812)
long
attach_adlib_card (long mem_start, struct address_info *hw_config)
{
if (opl3_detect (FM_MONO))
{
mem_start = opl3_init (mem_start);
}
return mem_start;
}
int
probe_adlib (struct address_info *hw_config)
{
return opl3_detect (FM_MONO);
}
#endif

View File

@ -1,587 +0,0 @@
/*
* sound/audio.c
*
* Device file manager for /dev/audio
*
* Copyright by Hannu Savolainen 1993
*
* 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.
*
* 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.
*
*/
#ifdef PC98
#include <pc98/pc98/sound/sound_config.h>
#else
#include <i386/isa/sound/sound_config.h>
#endif
#ifdef CONFIGURE_SOUNDCARD
#ifndef EXCLUDE_AUDIO
#include <i386/isa/sound/ulaw.h>
#include <i386/isa/sound/coproc.h>
#define ON 1
#define OFF 0
static int wr_buff_no[MAX_AUDIO_DEV]; /*
* != -1, if there is
* a incomplete output
* block in the queue.
*/
static int wr_buff_size[MAX_AUDIO_DEV], wr_buff_ptr[MAX_AUDIO_DEV];
static int audio_mode[MAX_AUDIO_DEV];
static int dev_nblock[MAX_AUDIO_DEV]; /* 1 if in noblocking mode */
#define AM_NONE 0
#define AM_WRITE 1
#define AM_READ 2
static char *wr_dma_buf[MAX_AUDIO_DEV];
static int audio_format[MAX_AUDIO_DEV];
static int local_conversion[MAX_AUDIO_DEV];
static int
set_format (int dev, int fmt)
{
if (fmt != AFMT_QUERY)
{
local_conversion[dev] = 0;
if (!(audio_devs[dev]->format_mask & fmt)) /* Not supported */
if (fmt == AFMT_MU_LAW)
{
fmt = AFMT_U8;
local_conversion[dev] = AFMT_MU_LAW;
}
else
fmt = AFMT_U8; /* This is always supported */
audio_format[dev] = DMAbuf_ioctl (dev, SNDCTL_DSP_SETFMT, fmt, 1);
}
if (local_conversion[dev]) /* This shadows the HW format */
return local_conversion[dev];
return audio_format[dev];
}
int
audio_open (int dev, struct fileinfo *file)
{
int ret;
int bits;
int dev_type = dev & 0x0f;
int mode = file->mode & O_ACCMODE;
dev = dev >> 4;
if (dev_type == SND_DEV_DSP16)
bits = 16;
else
bits = 8;
if ((ret = DMAbuf_open (dev, mode)) < 0)
return ret;
if (audio_devs[dev]->coproc)
if ((ret = audio_devs[dev]->coproc->
open (audio_devs[dev]->coproc->devc, COPR_PCM)) < 0)
{
audio_release (dev, file);
printk ("Sound: Can't access coprocessor device\n");
return ret;
}
local_conversion[dev] = 0;
if (DMAbuf_ioctl (dev, SNDCTL_DSP_SETFMT, bits, 1) != bits)
{
audio_release (dev, file);
return RET_ERROR (ENXIO);
}
if (dev_type == SND_DEV_AUDIO)
{
set_format (dev, AFMT_MU_LAW);
}
else
set_format (dev, bits);
wr_buff_no[dev] = -1;
audio_mode[dev] = AM_NONE;
wr_buff_size[dev] = wr_buff_ptr[dev] = 0;
dev_nblock[dev] = 0;
return ret;
}
void
audio_release (int dev, struct fileinfo *file)
{
int mode;
dev = dev >> 4;
mode = file->mode & O_ACCMODE;
if (wr_buff_no[dev] >= 0)
{
DMAbuf_start_output (dev, wr_buff_no[dev], wr_buff_ptr[dev]);
wr_buff_no[dev] = -1;
}
if (audio_devs[dev]->coproc)
audio_devs[dev]->coproc->close (audio_devs[dev]->coproc->devc, COPR_PCM);
DMAbuf_release (dev, mode);
}
#ifdef NO_INLINE_ASM
static void
translate_bytes (const unsigned char *table, unsigned char *buff, unsigned long n)
{
unsigned long i;
for (i = 0; i < n; ++i)
buff[i] = table[buff[i]];
}
#else
static inline void
translate_bytes (const void *table, void *buff, unsigned long n)
{
__asm__ ("cld\n"
"1:\tlodsb\n\t"
"xlatb\n\t"
"stosb\n\t"
"loop 1b\n\t":
: "b" ((long) table), "c" (n), "D" ((long) buff), "S" ((long) buff)
: "bx", "cx", "di", "si", "ax");
}
#endif
int
audio_write (int dev, struct fileinfo *file, snd_rw_buf * buf, int count)
{
int c, p, l;
int err;
dev = dev >> 4;
p = 0;
c = count;
if (audio_mode[dev] == AM_READ) /*
* Direction changed
*/
{
wr_buff_no[dev] = -1;
}
audio_mode[dev] = AM_WRITE;
if (!count) /*
* Flush output
*/
{
if (wr_buff_no[dev] >= 0)
{
DMAbuf_start_output (dev, wr_buff_no[dev], wr_buff_ptr[dev]);
wr_buff_no[dev] = -1;
}
return 0;
}
while (c)
{ /*
* Perform output blocking
*/
if (wr_buff_no[dev] < 0) /*
* There is no incomplete buffers
*/
{
if ((wr_buff_no[dev] = DMAbuf_getwrbuffer (dev, &wr_dma_buf[dev],
&wr_buff_size[dev],
dev_nblock[dev])) < 0)
{
/* Handle nonblocking mode */
#if defined(__FreeBSD__)
if (dev_nblock[dev] && wr_buff_no[dev] == RET_ERROR (EWOULDBLOCK))
return wr_buff_no[dev]; /*
* XXX Return error, write() will
* supply # of accepted bytes.
* In fact, in FreeBSD the check
* above should not be needed
*/
#else
if (dev_nblock[dev] && wr_buff_no[dev] == RET_ERROR (EAGAIN))
return p; /* No more space. Return # of accepted bytes */
#endif
return wr_buff_no[dev];
}
wr_buff_ptr[dev] = 0;
}
l = c;
if (l > (wr_buff_size[dev] - wr_buff_ptr[dev]))
l = (wr_buff_size[dev] - wr_buff_ptr[dev]);
if (!audio_devs[dev]->copy_from_user)
{ /*
* No device specific copy routine
*/
COPY_FROM_USER (&wr_dma_buf[dev][wr_buff_ptr[dev]], buf, p, l);
}
else
audio_devs[dev]->copy_from_user (dev,
wr_dma_buf[dev], wr_buff_ptr[dev], buf, p, l);
/*
* Insert local processing here
*/
if (local_conversion[dev] == AFMT_MU_LAW)
{
#ifdef linux
/*
* This just allows interrupts while the conversion is running
*/
__asm__ ("sti");
#endif
translate_bytes (ulaw_dsp, (unsigned char *) &wr_dma_buf[dev][wr_buff_ptr[dev]], l);
}
c -= l;
p += l;
wr_buff_ptr[dev] += l;
if (wr_buff_ptr[dev] >= wr_buff_size[dev])
{
if ((err = DMAbuf_start_output (dev, wr_buff_no[dev], wr_buff_ptr[dev])) < 0)
{
return err;
}
wr_buff_no[dev] = -1;
}
}
return count;
}
int
audio_read (int dev, struct fileinfo *file, snd_rw_buf * buf, int count)
{
int c, p, l;
char *dmabuf;
int buff_no;
dev = dev >> 4;
p = 0;
c = count;
if (audio_mode[dev] == AM_WRITE)
{
if (wr_buff_no[dev] >= 0)
{
DMAbuf_start_output (dev, wr_buff_no[dev], wr_buff_ptr[dev]);
wr_buff_no[dev] = -1;
}
}
audio_mode[dev] = AM_READ;
while (c)
{
if ((buff_no = DMAbuf_getrdbuffer (dev, &dmabuf, &l,
dev_nblock[dev])) < 0)
{
/* Nonblocking mode handling. Return current # of bytes */
#if defined(__FreeBSD__)
if (dev_nblock[dev] && buff_no == RET_ERROR (EWOULDBLOCK))
return buff_no; /*
* XXX Return error, read() will supply
* # of bytes actually read. In fact,
* in FreeBSD the check above should not
* be needed
*/
#else
if (dev_nblock[dev] && buff_no == RET_ERROR (EAGAIN))
return p;
#endif
return buff_no;
}
if (l > c)
l = c;
/*
* Insert any local processing here.
*/
if (local_conversion[dev] == AFMT_MU_LAW)
{
#ifdef linux
/*
* This just allows interrupts while the conversion is running
*/
__asm__ ("sti");
#endif
translate_bytes (dsp_ulaw, (unsigned char *) dmabuf, l);
}
COPY_TO_USER (buf, p, dmabuf, l);
DMAbuf_rmchars (dev, buff_no, l);
p += l;
c -= l;
}
return count - c;
}
int
audio_ioctl (int dev, struct fileinfo *file,
unsigned int cmd, unsigned int arg)
{
dev = dev >> 4;
if (((cmd >> 8) & 0xff) == 'C')
{
if (audio_devs[dev]->coproc) /* Coprocessor ioctl */
return audio_devs[dev]->coproc->ioctl (audio_devs[dev]->coproc->devc, cmd, arg, 0);
else
printk ("/dev/dsp%d: No coprocessor for this device\n", dev);
return RET_ERROR (EREMOTEIO);
}
else
switch (cmd)
{
case SNDCTL_DSP_SYNC:
if (wr_buff_no[dev] >= 0)
{
DMAbuf_start_output (dev, wr_buff_no[dev], wr_buff_ptr[dev]);
wr_buff_no[dev] = -1;
}
return DMAbuf_ioctl (dev, cmd, arg, 0);
break;
case SNDCTL_DSP_POST:
if (wr_buff_no[dev] >= 0)
{
DMAbuf_start_output (dev, wr_buff_no[dev], wr_buff_ptr[dev]);
wr_buff_no[dev] = -1;
}
return 0;
break;
case SNDCTL_DSP_RESET:
wr_buff_no[dev] = -1;
return DMAbuf_ioctl (dev, cmd, arg, 0);
break;
case SNDCTL_DSP_GETFMTS:
return IOCTL_OUT (arg, audio_devs[dev]->format_mask);
break;
case SNDCTL_DSP_SETFMT:
return IOCTL_OUT (arg, set_format (dev, IOCTL_IN (arg)));
case SNDCTL_DSP_GETISPACE:
if (audio_mode[dev] == AM_WRITE)
return RET_ERROR (EBUSY);
{
audio_buf_info info;
int err = DMAbuf_ioctl (dev, cmd, (unsigned long) &info, 1);
if (err < 0)
return err;
if (wr_buff_no[dev] != -1)
info.bytes += wr_buff_ptr[dev];
IOCTL_TO_USER ((char *) arg, 0, (char *) &info, sizeof (info));
return 0;
}
case SNDCTL_DSP_GETOSPACE:
if (audio_mode[dev] == AM_READ)
return RET_ERROR (EBUSY);
{
audio_buf_info info;
int err = DMAbuf_ioctl (dev, cmd, (unsigned long) &info, 1);
if (err < 0)
return err;
if (wr_buff_no[dev] != -1)
info.bytes += wr_buff_size[dev] - wr_buff_ptr[dev];
IOCTL_TO_USER ((char *) arg, 0, (char *) &info, sizeof (info));
return 0;
}
case SNDCTL_DSP_NONBLOCK:
dev_nblock[dev] = 1;
return 0;
break;
#ifdef __FreeBSD__
case FIONBIO: /* XXX Is this the same in Linux? */
if (*(int *)arg)
dev_nblock[dev] = 1;
else
dev_nblock[dev] = 0;
return 0;
break;
case FIOASYNC:
return 0; /* XXX Useful for ampling input notification? */
break;
#endif
default:
return DMAbuf_ioctl (dev, cmd, arg, 0);
}
}
long
audio_init (long mem_start)
{
/*
* NOTE! This routine could be called several times during boot.
*/
return mem_start;
}
#ifdef ALLOW_SELECT
int
audio_select (int dev, struct fileinfo *file, int sel_type, select_table * wait)
{
int l;
char *dmabuf;
dev = dev >> 4;
switch (sel_type)
{
case SEL_IN:
if (audio_mode[dev] != AM_READ && /* Wrong direction */
audio_mode[dev] != AM_NONE)
return 0;
if (DMAbuf_getrdbuffer (dev, &dmabuf, &l,
1 /* Don't block */ ) >= 0)
return 1; /* We have data */
return DMAbuf_select (dev, file, sel_type, wait);
break;
case SEL_OUT:
if (audio_mode[dev] != AM_WRITE && /* Wrong direction */
audio_mode[dev] != AM_NONE)
return 0;
if (wr_buff_no[dev] != -1)
return 1; /* There is space in the current buffer */
return DMAbuf_select (dev, file, sel_type, wait);
break;
case SEL_EX:
return 0;
}
return 0;
}
#endif /* ALLOW_SELECT */
#else /* EXCLUDE_AUDIO */
/*
* Stub versions
*/
int
audio_read (int dev, struct fileinfo *file, snd_rw_buf * buf, int count)
{
return RET_ERROR (EIO);
}
int
audio_write (int dev, struct fileinfo *file, snd_rw_buf * buf, int count)
{
return RET_ERROR (EIO);
}
int
audio_open (int dev, struct fileinfo *file)
{
return RET_ERROR (ENXIO);
}
void
audio_release (int dev, struct fileinfo *file)
{
};
int
audio_ioctl (int dev, struct fileinfo *file,
unsigned int cmd, unsigned int arg)
{
return RET_ERROR (EIO);
}
int
audio_lseek (int dev, struct fileinfo *file, off_t offset, int orig)
{
return RET_ERROR (EIO);
}
long
audio_init (long mem_start)
{
return mem_start;
}
#endif
#endif

View File

@ -1,186 +0,0 @@
/*
* sound/dev_table.c
*
* Device call tables.
*
* Copyright by Hannu Savolainen 1993
*
* 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.
*
* 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.
*
*/
#define _DEV_TABLE_C_
#ifdef PC98
#include <pc98/pc98/sound/sound_config.h>
#else
#include <i386/isa/sound/sound_config.h>
#endif
#ifdef CONFIGURE_SOUNDCARD
int
snd_find_driver (int type)
{
int i, n = sizeof (sound_drivers) / sizeof (struct driver_info);
for (i = 0; i < (n - 1); i++)
if (sound_drivers[i].card_type == type)
return i;
return -1; /*
* Not found
*/
}
static long
sndtable_init (long mem_start)
{
int i, n = sizeof (snd_installed_cards) / sizeof (struct card_info);
int drv;
printk ("Sound initialization started\n");
for (i = 0; i < (n - 1); i++)
if (snd_installed_cards[i].enabled)
if ((drv = snd_find_driver (snd_installed_cards[i].card_type)) == -1)
snd_installed_cards[i].enabled = 0; /*
* Mark as not detected
*/
else if (sound_drivers[drv].probe (&snd_installed_cards[i].config))
{
#ifndef SHORT_BANNERS
printk ("snd%d",
snd_installed_cards[i].card_type);
#endif
mem_start = sound_drivers[drv].attach (mem_start, &snd_installed_cards[i].config);
#ifndef SHORT_BANNERS
printk (" at 0x%x irq %d drq %d\n",
snd_installed_cards[i].config.io_base,
snd_installed_cards[i].config.irq,
snd_installed_cards[i].config.dma);
#endif
}
else
snd_installed_cards[i].enabled = 0; /*
* Mark as not detected
*/
printk ("Sound initialization complete\n");
return mem_start;
}
int
sndtable_probe (int unit, struct address_info *hw_config)
{
int i, n = sizeof (snd_installed_cards) / sizeof (struct card_info);
if (!unit)
return TRUE;
for (i = 0; i < (n - 1); i++)
if (snd_installed_cards[i].enabled)
if (snd_installed_cards[i].card_type == unit)
{
int drv;
snd_installed_cards[i].config.io_base = hw_config->io_base;
snd_installed_cards[i].config.irq = hw_config->irq;
snd_installed_cards[i].config.dma = hw_config->dma;
if ((drv = snd_find_driver (snd_installed_cards[i].card_type)) == -1)
snd_installed_cards[i].enabled = 0; /*
* Mark as not
* detected
*/
else if (sound_drivers[drv].probe (hw_config))
return 1;
snd_installed_cards[i].enabled = 0; /*
* Mark as not detected
*/
return 0;
}
return FALSE;
}
int
sndtable_init_card (int unit, struct address_info *hw_config)
{
int i, n = sizeof (snd_installed_cards) / sizeof (struct card_info);
if (!unit)
{
if (sndtable_init (0) != 0)
panic ("snd: Invalid memory allocation\n");
return TRUE;
}
for (i = 0; i < (n - 1); i++)
if (snd_installed_cards[i].card_type == unit)
{
int drv;
snd_installed_cards[i].config.io_base = hw_config->io_base;
snd_installed_cards[i].config.irq = hw_config->irq;
snd_installed_cards[i].config.dma = hw_config->dma;
if ((drv = snd_find_driver (snd_installed_cards[i].card_type)) == -1)
snd_installed_cards[i].enabled = 0; /*
* Mark as not detected
*/
else if (sound_drivers[drv].attach (0, hw_config) != 0)
panic ("snd#: Invalid memory allocation\n");
return TRUE;
}
return FALSE;
}
int
sndtable_get_cardcount (void)
{
return num_audiodevs + num_mixers + num_synths + num_midis;
}
struct address_info *
sound_getconf (int card_type)
{
int j, ptr;
int n = sizeof (snd_installed_cards) / sizeof (struct card_info);
ptr = -1;
for (j = 0; j < n && ptr == -1; j++)
if (snd_installed_cards[j].card_type == card_type)
ptr = j;
if (ptr == -1)
return (struct address_info *) NULL;
return &snd_installed_cards[ptr].config;
}
#else
void
sound_setup (char *str, int *ints)
{
}
#endif

View File

@ -1,429 +0,0 @@
/*
* dev_table.h
*
* Global definitions for device call tables
*
* Copyright by Hannu Savolainen 1993
*
* 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.
*
* 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.
*
*/
#ifndef _DEV_TABLE_H_
#define _DEV_TABLE_H_
/*
* NOTE! NOTE! NOTE! NOTE!
*
* If you modify this file, please check the dev_table.c also.
*
* NOTE! NOTE! NOTE! NOTE!
*/
struct driver_info {
int card_type; /* From soundcard.h */
char *name;
long (*attach) (long mem_start, struct address_info *hw_config);
int (*probe) (struct address_info *hw_config);
};
struct card_info {
int card_type; /* Link (search key) to the driver list */
struct address_info config;
int enabled;
};
/*
* Device specific parameters (used only by dmabuf.c)
*/
#define MAX_SUB_BUFFERS (32*MAX_REALTIME_FACTOR)
#define DMODE_NONE 0
#define DMODE_OUTPUT 1
#define DMODE_INPUT 2
struct dma_buffparms {
int dma_mode; /* DMODE_INPUT, DMODE_OUTPUT or DMODE_NONE */
/*
* Pointers to raw buffers
*/
char *raw_buf[DSP_BUFFCOUNT];
unsigned long raw_buf_phys[DSP_BUFFCOUNT];
int raw_count;
/*
* Device state tables
*/
unsigned long flags;
#define DMA_BUSY 0x00000001
#define DMA_RESTART 0x00000002
#define DMA_ACTIVE 0x00000004
#define DMA_STARTED 0x00000008
#define DMA_ALLOC_DONE 0x00000020
int open_mode;
/*
* Queue parameters.
*/
int qlen;
int qhead;
int qtail;
int nbufs;
int counts[MAX_SUB_BUFFERS];
int subdivision;
char *buf[MAX_SUB_BUFFERS];
unsigned long buf_phys[MAX_SUB_BUFFERS];
int fragment_size;
int max_fragments;
int bytes_in_use;
int underrun_count;
};
/*
* Structure for use with various microcontrollers and DSP processors
* in the recent soundcards.
*/
typedef struct coproc_operations {
char name[32];
int (*open) (void *devc, int sub_device);
void (*close) (void *devc, int sub_device);
int (*ioctl) (void *devc, unsigned int cmd, unsigned int arg, int local);
void (*reset) (void *devc);
void *devc; /* Driver specific info */
} coproc_operations;
struct audio_operations {
char name[32];
int flags;
#define NOTHING_SPECIAL 0
#define NEEDS_RESTART 1
#define DMA_AUTOMODE 2
int format_mask; /* Bitmask for supported audio formats */
void *devc; /* Driver specific info */
int (*open) (int dev, int mode);
void (*close) (int dev);
void (*output_block) (int dev, unsigned long buf,
int count, int intrflag, int dma_restart);
void (*start_input) (int dev, unsigned long buf,
int count, int intrflag, int dma_restart);
int (*ioctl) (int dev, unsigned int cmd, unsigned int arg, int local);
int (*prepare_for_input) (int dev, int bufsize, int nbufs);
int (*prepare_for_output) (int dev, int bufsize, int nbufs);
void (*reset) (int dev);
void (*halt_xfer) (int dev);
int (*local_qlen)(int dev);
void (*copy_from_user)(int dev, char *localbuf, int localoffs,
snd_rw_buf *userbuf, int useroffs, int len);
int buffcount;
long buffsize;
int dmachan;
struct dma_buffparms *dmap;
struct coproc_operations *coproc;
int mixer_dev;
};
struct mixer_operations {
char name[32];
int (*ioctl) (int dev, unsigned int cmd, unsigned int arg);
};
struct synth_operations {
struct synth_info *info;
int midi_dev;
int synth_type;
int synth_subtype;
int (*open) (int dev, int mode);
void (*close) (int dev);
int (*ioctl) (int dev, unsigned int cmd, unsigned int arg);
int (*kill_note) (int dev, int voice, int note, int velocity);
int (*start_note) (int dev, int voice, int note, int velocity);
int (*set_instr) (int dev, int voice, int instr);
void (*reset) (int dev);
void (*hw_control) (int dev, unsigned char *event);
int (*load_patch) (int dev, int format, snd_rw_buf *addr,
int offs, int count, int pmgr_flag);
void (*aftertouch) (int dev, int voice, int pressure);
void (*controller) (int dev, int voice, int ctrl_num, int value);
void (*panning) (int dev, int voice, int value);
void (*volume_method) (int dev, int mode);
int (*pmgr_interface) (int dev, struct patmgr_info *info);
void (*bender) (int dev, int chn, int value);
int (*alloc_voice) (int dev, int chn, int note, struct voice_alloc_info *alloc);
void (*setup_voice) (int dev, int voice, int chn);
struct voice_alloc_info alloc;
struct channel_info chn_info[16];
};
struct midi_input_info { /* MIDI input scanner variables */
#define MI_MAX 10
int m_busy;
unsigned char m_buf[MI_MAX];
unsigned char m_prev_status; /* For running status */
int m_ptr;
#define MST_INIT 0
#define MST_DATA 1
#define MST_SYSEX 2
int m_state;
int m_left;
};
struct midi_operations {
struct midi_info info;
struct synth_operations *converter;
struct midi_input_info in_info;
int (*open) (int dev, int mode,
void (*inputintr)(int dev, unsigned char data),
void (*outputintr)(int dev)
);
void (*close) (int dev);
int (*ioctl) (int dev, unsigned int cmd, unsigned int arg);
int (*putc) (int dev, unsigned char data);
int (*start_read) (int dev);
int (*end_read) (int dev);
void (*kick)(int dev);
int (*command) (int dev, unsigned char *data);
int (*buffer_status) (int dev);
int (*prefix_cmd) (int dev, unsigned char status);
struct coproc_operations *coproc;
};
struct sound_timer_operations {
struct sound_timer_info info;
int priority;
int devlink;
int (*open)(int dev, int mode);
void (*close)(int dev);
int (*event)(int dev, unsigned char *ev);
unsigned long (*get_time)(int dev);
int (*ioctl) (int dev, unsigned int cmd, unsigned int arg);
void (*arm_timer)(int dev, long time);
};
#ifdef _DEV_TABLE_C_
struct audio_operations *audio_devs[MAX_AUDIO_DEV] = {NULL}; int num_audiodevs = 0;
struct mixer_operations *mixer_devs[MAX_MIXER_DEV] = {NULL}; int num_mixers = 0;
struct synth_operations *synth_devs[MAX_SYNTH_DEV+MAX_MIDI_DEV] = {NULL}; int num_synths = 0;
struct midi_operations *midi_devs[MAX_MIDI_DEV] = {NULL}; int num_midis = 0;
#ifndef EXCLUDE_SEQUENCER
extern struct sound_timer_operations default_sound_timer;
struct sound_timer_operations *sound_timer_devs[MAX_TIMER_DEV] =
{&default_sound_timer, NULL};
int num_sound_timers = 1;
#else
struct sound_timer_operations *sound_timer_devs[MAX_TIMER_DEV] =
{NULL};
int num_sound_timers = 0;
#endif
/*
* List of low level drivers compiled into the kernel.
*/
struct driver_info sound_drivers[] = {
#ifndef EXCLUDE_PSS
{SNDCARD_PSS, "Echo Personal Sound System PSS (ESC614)", attach_pss, probe_pss},
# ifdef PSS_MPU_BASE
{SNDCARD_PSS_MPU, "PSS-MPU", attach_pss_mpu, probe_pss_mpu},
# endif
# ifdef PSS_MSS_BASE
{SNDCARD_PSS_MSS, "PSS-MSS", attach_pss_mss, probe_pss_mss},
# endif
#endif
#ifndef EXCLUDE_YM3812
{SNDCARD_ADLIB, "OPL-2/OPL-3 FM", attach_adlib_card, probe_adlib},
#endif
#ifndef EXCLUDE_PAS
{SNDCARD_PAS, "ProAudioSpectrum", attach_pas_card, probe_pas},
#endif
#if !defined(EXCLUDE_MPU401) && !defined(EXCLUDE_MIDI)
{SNDCARD_MPU401,"Roland MPU-401", attach_mpu401, probe_mpu401},
#endif
#if !defined(EXCLUDE_UART6850) && !defined(EXCLUDE_MIDI)
{SNDCARD_UART6850,"6860 UART Midi", attach_uart6850, probe_uart6850},
#endif
#ifndef EXCLUDE_SB
{SNDCARD_SB, "SoundBlaster", attach_sb_card, probe_sb},
#endif
#if !defined(EXCLUDE_SB) && !defined(EXCLUDE_SB16)
#ifndef EXCLUDE_AUDIO
{SNDCARD_SB16, "SoundBlaster16", sb16_dsp_init, sb16_dsp_detect},
#endif
#ifndef EXCLUDE_MIDI
{SNDCARD_SB16MIDI,"SB16 MIDI", attach_sb16midi, probe_sb16midi},
#endif
#endif
#ifndef EXCLUDE_GUS16
{SNDCARD_GUS16, "Ultrasound 16-bit opt.", attach_gus_db16, probe_gus_db16},
#endif
#ifndef EXCLUDE_MSS
{SNDCARD_MSS, "MS Sound System", attach_ms_sound, probe_ms_sound},
#endif
#ifndef EXCLUDE_GUS
{SNDCARD_GUS, "Gravis Ultrasound", attach_gus_card, probe_gus},
#endif
#ifndef EXCLUDE_SSCAPE
{SNDCARD_SSCAPE, "Ensoniq Soundscape", attach_sscape, probe_sscape},
{SNDCARD_SSCAPE_MSS, "MS Sound System (SoundScape)", attach_ss_ms_sound, probe_ss_ms_sound},
#endif
#ifndef EXCLUDE_TRIX
{SNDCARD_TRXPRO, "MediaTriX AudioTriX Pro", attach_trix_wss, probe_trix_wss},
{SNDCARD_TRXPRO_SB, "AudioTriX (SB mode)", attach_trix_sb, probe_trix_sb},
{SNDCARD_TRXPRO_MPU, "AudioTriX MIDI", attach_trix_mpu, probe_trix_mpu},
#endif
#ifdef PC98
#ifndef EXCLUDE_PCM86
{SNDCARD_PCM86, "PC-9801-86/73", attach_pcm86, probe_pcm86},
#endif
#endif
{0, "*?*", NULL, NULL}
};
#if defined(linux) || defined(__FreeBSD__)
/*
* List of devices actually configured in the system.
*
* Note! The detection order is significant. Don't change it.
*/
struct card_info snd_installed_cards[] = {
#ifndef EXCLUDE_PSS
{SNDCARD_PSS, {PSS_BASE, PSS_IRQ, PSS_DMA}, SND_DEFAULT_ENABLE},
# ifdef PSS_MPU_BASE
{SNDCARD_PSS_MPU, {PSS_MPU_BASE, PSS_MPU_IRQ, 0}, SND_DEFAULT_ENABLE},
# endif
# ifdef PSS_MSS_BASE
{SNDCARD_PSS_MSS, {PSS_MSS_BASE, PSS_MSS_IRQ, PSS_MSS_DMA}, SND_DEFAULT_ENABLE},
# endif
#endif
#ifndef EXCLUDE_TRIX
{SNDCARD_TRXPRO, {TRIX_BASE, TRIX_IRQ, TRIX_DMA}, SND_DEFAULT_ENABLE},
# ifdef TRIX_SB_BASE
{SNDCARD_TRXPRO_SB, {TRIX_SB_BASE, TRIX_SB_IRQ, TRIX_SB_DMA}, SND_DEFAULT_ENABLE},
# endif
# ifdef TRIX_MPU_BASE
{SNDCARD_TRXPRO_MPU, {TRIX_MPU_BASE, TRIX_MPU_IRQ, 0}, SND_DEFAULT_ENABLE},
# endif
#endif
#ifndef EXCLUDE_SSCAPE
{SNDCARD_SSCAPE, {SSCAPE_BASE, SSCAPE_IRQ, SSCAPE_DMA}, SND_DEFAULT_ENABLE},
{SNDCARD_SSCAPE_MSS, {SSCAPE_MSS_BASE, SSCAPE_MSS_IRQ, SSCAPE_MSS_DMA}, SND_DEFAULT_ENABLE},
#endif
#ifndef EXCLUDE_MSS
{SNDCARD_MSS, {MSS_BASE, MSS_IRQ, MSS_DMA}, SND_DEFAULT_ENABLE},
# ifdef MSS2_BASE
{SNDCARD_MSS, {MSS2_BASE, MSS2_IRQ, MSS2_DMA}, SND_DEFAULT_ENABLE},
# endif
#endif
#ifndef EXCLUDE_PAS
{SNDCARD_PAS, {PAS_BASE, PAS_IRQ, PAS_DMA}, SND_DEFAULT_ENABLE},
#endif
#ifndef EXCLUDE_SB
{SNDCARD_SB, {SBC_BASE, SBC_IRQ, SBC_DMA}, SND_DEFAULT_ENABLE},
#endif
#if !defined(EXCLUDE_MPU401) && !defined(EXCLUDE_MIDI)
{SNDCARD_MPU401, {MPU_BASE, MPU_IRQ, 0}, SND_DEFAULT_ENABLE},
#ifdef MPU2_BASE
{SNDCARD_MPU401, {MPU2_BASE, MPU2_IRQ, 0}, SND_DEFAULT_ENABLE},
#endif
#ifdef MPU3_BASE
{SNDCARD_MPU401, {MPU3_BASE, MPU2_IRQ, 0}, SND_DEFAULT_ENABLE},
#endif
#endif
#if !defined(EXCLUDE_UART6850) && !defined(EXCLUDE_MIDI)
{SNDCARD_UART6850, {U6850_BASE, U6850_IRQ, 0}, SND_DEFAULT_ENABLE},
#endif
#if !defined(EXCLUDE_SB) && !defined(EXCLUDE_SB16)
#ifndef EXCLUDE_AUDIO
{SNDCARD_SB16, {SBC_BASE, SBC_IRQ, SB16_DMA}, SND_DEFAULT_ENABLE},
#endif
#ifndef EXCLUDE_MIDI
{SNDCARD_SB16MIDI,{SB16MIDI_BASE, SBC_IRQ, 0}, SND_DEFAULT_ENABLE},
#endif
#endif
#ifndef EXCLUDE_GUS
#ifndef EXCLUDE_GUS16
{SNDCARD_GUS16, {GUS16_BASE, GUS16_IRQ, GUS16_DMA, GUS_DMA_READ}, SND_DEFAULT_ENABLE},
#endif
{SNDCARD_GUS, {GUS_BASE, GUS_IRQ, GUS_DMA, GUS_DMA_READ}, SND_DEFAULT_ENABLE},
#endif
#ifndef EXCLUDE_YM3812
{SNDCARD_ADLIB, {FM_MONO, 0, 0}, SND_DEFAULT_ENABLE},
#endif
#ifdef PC98
#ifndef EXCLUDE_PCM86
{SNDCARD_PCM86, {0, 0, 0}, SND_DEFAULT_ENABLE},
#endif
#endif
{0, {0}, 0}
};
int num_sound_cards =
sizeof(snd_installed_cards) / sizeof (struct card_info);
#else
int num_sound_cards = 0;
#endif /* linux */
int num_sound_drivers =
sizeof(sound_drivers) / sizeof (struct driver_info);
#else
extern struct audio_operations * audio_devs[MAX_AUDIO_DEV]; extern int num_audiodevs;
extern struct mixer_operations * mixer_devs[MAX_MIXER_DEV]; extern int num_mixers;
extern struct synth_operations * synth_devs[MAX_SYNTH_DEV+MAX_MIDI_DEV]; extern int num_synths;
extern struct midi_operations * midi_devs[MAX_MIDI_DEV]; extern int num_midis;
extern struct sound_timer_operations * sound_timer_devs[MAX_SYNTH_DEV+MAX_MIDI_DEV]; extern int num_sound_timers;
extern struct driver_info sound_drivers[];
extern int num_sound_drivers;
extern struct card_info snd_installed_cards[];
extern int num_sound_cards;
#endif /* _DEV_TABLE_C_ */
int sndtable_probe(int unit, struct address_info *hw_config);
int sndtable_init_card(int unit, struct address_info *hw_config);
int sndtable_get_cardcount (void);
struct address_info *sound_getconf(int card_type);
int snd_find_driver(int type);
#endif /* _DEV_TABLE_H_ */

File diff suppressed because it is too large Load Diff

View File

@ -1,197 +0,0 @@
/*
* sound/gus_card.c
*
* Detection routine for the Gravis Ultrasound.
*
* Copyright by Hannu Savolainen 1993
*
* 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.
*
* 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.
*
*/
#include <i386/isa/sound/sound_config.h>
#if defined(CONFIGURE_SOUNDCARD) && !defined(EXCLUDE_GUS)
#include <i386/isa/sound/gus_hw.h>
int gus_base, gus_irq, gus_dma;
extern int gus_wave_volume;
extern int gus_pcm_volume;
extern int have_gus_max;
long
attach_gus_card (long mem_start, struct address_info *hw_config)
{
int io_addr;
snd_set_irq_handler (hw_config->irq, gusintr, "Gravis Ultrasound");
if (gus_wave_detect (hw_config->io_base)) /*
* Try first the default
*/
{
mem_start = gus_wave_init (mem_start, hw_config->irq, hw_config->dma,
hw_config->dma_read);
#ifndef EXCLUDE_MIDI
mem_start = gus_midi_init (mem_start);
#endif
#ifndef EXCLUDE_SEQUENCER
sound_timer_init (hw_config->io_base + 8);
#endif
return mem_start;
}
#ifndef EXCLUDE_GUS_IODETECT
/*
* Look at the possible base addresses (0x2X0, X=1, 2, 3, 4, 5, 6)
*/
for (io_addr = 0x210; io_addr <= 0x260; io_addr += 0x10)
if (io_addr != hw_config->io_base) /*
* Already tested
*/
if (gus_wave_detect (io_addr))
{
printk (" WARNING! GUS found at %x, config was %x ", io_addr, hw_config->io_base);
mem_start = gus_wave_init (mem_start, hw_config->irq, hw_config->dma,
hw_config->dma_read);
#ifndef EXCLUDE_MIDI
mem_start = gus_midi_init (mem_start);
#endif
#ifndef EXCLUDE_SEQUENCER
sound_timer_init (io_addr + 8);
#endif
return mem_start;
}
#endif
return mem_start; /*
* Not detected
*/
}
int
probe_gus (struct address_info *hw_config)
{
int io_addr;
if (gus_wave_detect (hw_config->io_base))
return 1;
#ifndef EXCLUDE_GUS_IODETECT
/*
* Look at the possible base addresses (0x2X0, X=1, 2, 3, 4, 5, 6)
*/
for (io_addr = 0x210; io_addr <= 0x260; io_addr += 0x10)
if (io_addr != hw_config->io_base) /*
* Already tested
*/
if (gus_wave_detect (io_addr))
return 1;
#endif
return 0;
}
void
gusintr (INT_HANDLER_PARMS (irq, dummy))
{
unsigned char src;
#ifdef linux
sti ();
#endif
#ifndef EXCLUDE_GUSMAX
if (have_gus_max)
# if defined(__FreeBSD__)
ad1848_interrupt (INT_HANDLER_CALL (gus_irq));
# else
ad1848_interrupt (INT_HANDLER_CALL (irq));
# endif
#endif
while (1)
{
if (!(src = INB (u_IrqStatus)))
return;
if (src & DMA_TC_IRQ)
{
guswave_dma_irq ();
}
if (src & (MIDI_TX_IRQ | MIDI_RX_IRQ))
{
#ifndef EXCLUDE_MIDI
gus_midi_interrupt (0);
#endif
}
if (src & (GF1_TIMER1_IRQ | GF1_TIMER2_IRQ))
{
#ifndef EXCLUDE_SEQUENCER
sound_timer_interrupt ();
#else
gus_write8 (0x45, 0); /* Stop timers */
#endif
}
if (src & (WAVETABLE_IRQ | ENVELOPE_IRQ))
{
gus_voice_irq ();
}
}
}
#endif
/*
* Some extra code for the 16 bit sampling option
*/
#if defined(CONFIGURE_SOUNDCARD) && !defined(EXCLUDE_GUS16)
int
probe_gus_db16 (struct address_info *hw_config)
{
return ad1848_detect (hw_config->io_base);
}
long
attach_gus_db16 (long mem_start, struct address_info *hw_config)
{
gus_pcm_volume = 100;
gus_wave_volume = 90;
ad1848_init ("GUS 16 bit sampling", hw_config->io_base,
hw_config->irq,
hw_config->dma,
hw_config->dma);
return mem_start;
}
#endif

View File

@ -1,312 +0,0 @@
/*
* sound/gus2_midi.c
*
* The low level driver for the GUS Midi Interface.
*
* Copyright by Hannu Savolainen 1993
*
* 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.
*
* 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.
*
*/
#include <i386/isa/sound/sound_config.h>
#ifdef CONFIGURE_SOUNDCARD
#include <i386/isa/sound/gus_hw.h>
#if !defined(EXCLUDE_GUS) && !defined(EXCLUDE_MIDI)
static int midi_busy = 0, input_opened = 0;
static int my_dev;
static int output_used = 0;
static volatile unsigned char gus_midi_control;
static void (*midi_input_intr) (int dev, unsigned char data);
static unsigned char tmp_queue[256];
static volatile int qlen;
static volatile unsigned char qhead, qtail;
extern int gus_base, gus_irq, gus_dma;
#define GUS_MIDI_STATUS() INB(u_MidiStatus)
static int
gus_midi_open (int dev, int mode,
void (*input) (int dev, unsigned char data),
void (*output) (int dev)
)
{
if (midi_busy)
{
printk ("GUS: Midi busy\n");
return RET_ERROR (EBUSY);
}
OUTB (MIDI_RESET, u_MidiControl);
gus_delay ();
gus_midi_control = 0;
input_opened = 0;
if (mode == OPEN_READ || mode == OPEN_READWRITE)
{
gus_midi_control |= MIDI_ENABLE_RCV;
input_opened = 1;
}
if (mode == OPEN_WRITE || mode == OPEN_READWRITE)
{
gus_midi_control |= MIDI_ENABLE_XMIT;
}
OUTB (gus_midi_control, u_MidiControl); /*
* Enable
*/
midi_busy = 1;
qlen = qhead = qtail = output_used = 0;
midi_input_intr = input;
return 0;
}
static int
dump_to_midi (unsigned char midi_byte)
{
unsigned long flags;
int ok = 0;
output_used = 1;
DISABLE_INTR (flags);
if (GUS_MIDI_STATUS () & MIDI_XMIT_EMPTY)
{
ok = 1;
OUTB (midi_byte, u_MidiData);
}
else
{
/*
* Enable Midi xmit interrupts (again)
*/
gus_midi_control |= MIDI_ENABLE_XMIT;
OUTB (gus_midi_control, u_MidiControl);
}
RESTORE_INTR (flags);
return ok;
}
static void
gus_midi_close (int dev)
{
/*
* Reset FIFO pointers, disable intrs
*/
OUTB (MIDI_RESET, u_MidiControl);
midi_busy = 0;
}
static int
gus_midi_out (int dev, unsigned char midi_byte)
{
unsigned long flags;
/*
* Drain the local queue first
*/
DISABLE_INTR (flags);
while (qlen && dump_to_midi (tmp_queue[qhead]))
{
qlen--;
qhead++;
}
RESTORE_INTR (flags);
/*
* Output the byte if the local queue is empty.
*/
if (!qlen)
if (dump_to_midi (midi_byte))
return 1; /*
* OK
*/
/*
* Put to the local queue
*/
if (qlen >= 256)
return 0; /*
* Local queue full
*/
DISABLE_INTR (flags);
tmp_queue[qtail] = midi_byte;
qlen++;
qtail++;
RESTORE_INTR (flags);
return 1;
}
static int
gus_midi_start_read (int dev)
{
return 0;
}
static int
gus_midi_end_read (int dev)
{
return 0;
}
static int
gus_midi_ioctl (int dev, unsigned cmd, unsigned arg)
{
return RET_ERROR (EINVAL);
}
static void
gus_midi_kick (int dev)
{
}
static int
gus_midi_buffer_status (int dev)
{
unsigned long flags;
if (!output_used)
return 0;
DISABLE_INTR (flags);
if (qlen && dump_to_midi (tmp_queue[qhead]))
{
qlen--;
qhead++;
}
RESTORE_INTR (flags);
return (qlen > 0) | !(GUS_MIDI_STATUS () & MIDI_XMIT_EMPTY);
}
#define MIDI_SYNTH_NAME "Gravis Ultrasound Midi"
#define MIDI_SYNTH_CAPS SYNTH_CAP_INPUT
#include <i386/isa/sound/midi_synth.h>
static struct midi_operations gus_midi_operations =
{
{"Gravis UltraSound Midi", 0, 0, SNDCARD_GUS},
&std_midi_synth,
{0},
gus_midi_open,
gus_midi_close,
gus_midi_ioctl,
gus_midi_out,
gus_midi_start_read,
gus_midi_end_read,
gus_midi_kick,
NULL, /*
* command
*/
gus_midi_buffer_status,
NULL
};
long
gus_midi_init (long mem_start)
{
if (num_midis >= MAX_MIDI_DEV)
{
printk ("Sound: Too many midi devices detected\n");
return mem_start;
}
OUTB (MIDI_RESET, u_MidiControl);
std_midi_synth.midi_dev = my_dev = num_midis;
midi_devs[num_midis++] = &gus_midi_operations;
return mem_start;
}
void
gus_midi_interrupt (int dummy)
{
unsigned char stat, data;
unsigned long flags;
DISABLE_INTR (flags);
stat = GUS_MIDI_STATUS ();
if (stat & MIDI_RCV_FULL)
{
data = INB (u_MidiData);
if (input_opened)
midi_input_intr (my_dev, data);
}
if (stat & MIDI_XMIT_EMPTY)
{
while (qlen && dump_to_midi (tmp_queue[qhead]))
{
qlen--;
qhead++;
}
if (!qlen)
{
/*
* Disable Midi output interrupts, since no data in the buffer
*/
gus_midi_control &= ~MIDI_ENABLE_XMIT;
OUTB (gus_midi_control, u_MidiControl);
}
}
#if 0
if (stat & MIDI_FRAME_ERR)
printk ("GUS: Midi framing error\n");
if (stat & MIDI_OVERRUN && input_opened)
printk ("GUS: Midi input overrun\n");
#endif
RESTORE_INTR (flags);
}
#endif
#endif

View File

@ -1,150 +0,0 @@
/*
* gus_vol.c - Compute volume for GUS.
*
* Greg Lee 1993.
*/
#include <i386/isa/sound/sound_config.h>
#ifndef EXCLUDE_GUS
#include <i386/isa/sound/gus_linearvol.h>
extern unsigned short gus_adagio_vol (int vel, int mainv, int xpn, int voicev);
extern unsigned short gus_linear_vol (int vol, int mainvol);
#define GUS_VOLUME gus_wave_volume
extern int gus_wave_volume;
/*
* Calculate gus volume from note velocity, main volume, expression, and
* intrinsic patch volume given in patch library. Expression is multiplied
* in, so it emphasizes differences in note velocity, while main volume is
* added in -- I don't know whether this is right, but it seems reasonable to
* me. (In the previous stage, main volume controller messages were changed
* to expression controller messages, if they were found to be used for
* dynamic volume adjustments, so here, main volume can be assumed to be
* constant throughout a song.)
*
* Intrinsic patch volume is added in, but if over 64 is also multiplied in, so
* we can give a big boost to very weak voices like nylon guitar and the
* basses. The normal value is 64. Strings are assigned lower values.
*/
unsigned short
gus_adagio_vol (int vel, int mainv, int xpn, int voicev)
{
int i, m, n, x;
/*
* A voice volume of 64 is considered neutral, so adjust the main volume if
* something other than this neutral value was assigned in the patch
* library.
*/
x = 256 + 6 * (voicev - 64);
/*
* Boost expression by voice volume above neutral.
*/
if (voicev > 65)
xpn += voicev - 64;
xpn += (voicev - 64) / 2;
/*
* Combine multiplicative and level components.
*/
x = vel * xpn * 6 + (voicev / 4) * x;
#ifdef GUS_VOLUME
/*
* Further adjustment by installation-specific master volume control
* (default 60).
*/
x = (x * GUS_VOLUME * GUS_VOLUME) / 10000;
#endif
#ifdef GUS_USE_CHN_MAIN_VOLUME
/*
* Experimental support for the channel main volume
*/
mainv = (mainv / 2) + 64; /* Scale to 64 to 127 */
x = (x * mainv * mainv) / 16384;
#endif
if (x < 2)
return (0);
else if (x >= 65535)
return ((15 << 8) | 255);
/*
* Convert to gus's logarithmic form with 4 bit exponent i and 8 bit
* mantissa m.
*/
n = x;
i = 7;
if (n < 128)
{
while (i > 0 && n < (1 << i))
i--;
}
else
while (n > 255)
{
n >>= 1;
i++;
}
/*
* Mantissa is part of linear volume not expressed in exponent. (This is
* not quite like real logs -- I wonder if it's right.)
*/
m = x - (1 << i);
/*
* Adjust mantissa to 8 bits.
*/
if (m > 0)
{
if (i > 8)
m >>= i - 8;
else if (i < 8)
m <<= 8 - i;
}
return ((i << 8) + m);
}
/*
* Volume-values are interpreted as linear values. Volume is based on the
* value supplied with SEQ_START_NOTE(), channel main volume (if compiled in)
* and the volume set by the mixer-device (default 60%).
*/
unsigned short
gus_linear_vol (int vol, int mainvol)
{
int mixer_mainvol;
if (vol <= 0)
vol = 0;
else if (vol >= 127)
vol = 127;
#ifdef GUS_VOLUME
mixer_mainvol = GUS_VOLUME;
#else
mixer_mainvol = 100;
#endif
#ifdef GUS_USE_CHN_MAIN_VOLUME
if (mainvol <= 0)
mainvol = 0;
else if (mainvol >= 127)
mainvol = 127;
#else
mainvol = 128;
#endif
return gus_linearvol[(((vol * mainvol) / 128) * mixer_mainvol) / 100];
}
#endif

File diff suppressed because it is too large Load Diff

View File

@ -1,264 +0,0 @@
/*
* sound/ics2101.c
*
* Driver for the ICS2101 mixer of GUS v3.7.
*
* Copyright by Hannu Savolainen 1994
*
* 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.
*
* 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.
*
*/
#include <i386/isa/sound/sound_config.h>
#if defined(CONFIGURE_SOUNDCARD) && !defined(EXCLUDE_GUS)
#include <machine/ultrasound.h>
#include <i386/isa/sound/gus_hw.h>
#define MIX_DEVS (SOUND_MASK_MIC|SOUND_MASK_LINE| \
SOUND_MASK_SYNTH| \
SOUND_MASK_CD | SOUND_MASK_VOLUME)
extern int gus_base;
static int volumes[ICS_MIXDEVS];
static int left_fix[ICS_MIXDEVS] =
{1, 1, 1, 2, 1, 2};
static int right_fix[ICS_MIXDEVS] =
{2, 2, 2, 1, 2, 1};
static int
scale_vol (int vol)
{
#if 1
/*
* Experimental volume scaling by Risto Kankkunen.
* This should give smoother volume response than just
* a plain multiplication.
*/
int e;
if (vol < 0)
vol = 0;
if (vol > 100)
vol = 100;
vol = (31 * vol + 50) / 100;
e = 0;
if (vol)
{
while (vol < 16)
{
vol <<= 1;
e--;
}
vol -= 16;
e += 7;
}
return ((e << 4) + vol);
#else
return ((vol * 127) + 50) / 100;
#endif
}
static void
write_mix (int dev, int chn, int vol)
{
int *selector;
unsigned long flags;
int ctrl_addr = dev << 3;
int attn_addr = dev << 3;
vol = scale_vol (vol);
if (chn == CHN_LEFT)
{
selector = left_fix;
ctrl_addr |= 0x00;
attn_addr |= 0x02;
}
else
{
selector = right_fix;
ctrl_addr |= 0x01;
attn_addr |= 0x03;
}
DISABLE_INTR (flags);
OUTB (ctrl_addr, u_MixSelect);
OUTB (selector[dev], u_MixData);
OUTB (attn_addr, u_MixSelect);
OUTB ((unsigned char) vol, u_MixData);
RESTORE_INTR (flags);
}
static int
set_volumes (int dev, int vol)
{
int left = vol & 0x00ff;
int right = (vol >> 8) & 0x00ff;
if (left < 0)
left = 0;
if (left > 100)
left = 100;
if (right < 0)
right = 0;
if (right > 100)
right = 100;
write_mix (dev, CHN_LEFT, left);
write_mix (dev, CHN_RIGHT, right);
vol = left + (right << 8);
volumes[dev] = vol;
return vol;
}
static int
ics2101_mixer_ioctl (int dev, unsigned int cmd, unsigned int arg)
{
if (((cmd >> 8) & 0xff) == 'M')
{
if (cmd & IOC_IN)
switch (cmd & 0xff)
{
case SOUND_MIXER_RECSRC:
return gus_default_mixer_ioctl (dev, cmd, arg);
break;
case SOUND_MIXER_MIC:
return IOCTL_OUT (arg, set_volumes (DEV_MIC, IOCTL_IN (arg)));
break;
case SOUND_MIXER_CD:
return IOCTL_OUT (arg, set_volumes (DEV_CD, IOCTL_IN (arg)));
break;
case SOUND_MIXER_LINE:
return IOCTL_OUT (arg, set_volumes (DEV_LINE, IOCTL_IN (arg)));
break;
case SOUND_MIXER_SYNTH:
return IOCTL_OUT (arg, set_volumes (DEV_GF1, IOCTL_IN (arg)));
break;
case SOUND_MIXER_VOLUME:
return IOCTL_OUT (arg, set_volumes (DEV_VOL, IOCTL_IN (arg)));
break;
default:
return RET_ERROR (EINVAL);
}
else
switch (cmd & 0xff) /*
* Return parameters
*/
{
case SOUND_MIXER_RECSRC:
return gus_default_mixer_ioctl (dev, cmd, arg);
break;
case SOUND_MIXER_DEVMASK:
return IOCTL_OUT (arg, MIX_DEVS);
break;
case SOUND_MIXER_STEREODEVS:
return IOCTL_OUT (arg, SOUND_MASK_LINE | SOUND_MASK_CD |
SOUND_MASK_SYNTH | SOUND_MASK_VOLUME |
SOUND_MASK_MIC);
break;
case SOUND_MIXER_RECMASK:
return IOCTL_OUT (arg, SOUND_MASK_MIC | SOUND_MASK_LINE);
break;
case SOUND_MIXER_CAPS:
return IOCTL_OUT (arg, 0);
break;
case SOUND_MIXER_MIC:
return IOCTL_OUT (arg, volumes[DEV_MIC]);
break;
case SOUND_MIXER_LINE:
return IOCTL_OUT (arg, volumes[DEV_LINE]);
break;
case SOUND_MIXER_CD:
return IOCTL_OUT (arg, volumes[DEV_CD]);
break;
case SOUND_MIXER_VOLUME:
return IOCTL_OUT (arg, volumes[DEV_VOL]);
break;
case SOUND_MIXER_SYNTH:
return IOCTL_OUT (arg, volumes[DEV_GF1]);
break;
default:
return RET_ERROR (EINVAL);
}
}
return RET_ERROR (EINVAL);
}
static struct mixer_operations ics2101_mixer_operations =
{
"ICS2101 Multimedia Mixer",
ics2101_mixer_ioctl
};
long
ics2101_mixer_init (long mem_start)
{
int i;
if (num_mixers < MAX_MIXER_DEV)
{
mixer_devs[num_mixers++] = &ics2101_mixer_operations;
/*
* Some GUS v3.7 cards had some channels flipped. Disable
* the flipping feature if the model id is other than 5.
*/
if (INB (u_MixSelect) != 5)
{
for (i = 0; i < ICS_MIXDEVS; i++)
left_fix[i] = 1;
for (i = 0; i < ICS_MIXDEVS; i++)
right_fix[i] = 2;
}
set_volumes (DEV_GF1, 0x5a5a);
set_volumes (DEV_CD, 0x5a5a);
set_volumes (DEV_MIC, 0x0000);
set_volumes (DEV_LINE, 0x5a5a);
set_volumes (DEV_VOL, 0x5a5a);
set_volumes (DEV_UNUSED, 0x0000);
}
return mem_start;
}
#endif

View File

@ -1,128 +0,0 @@
/* for FreeBSD */
/*
* $Id: local.h,v 1.11 1994/11/01 17:26:50 ache Exp
*/
#define DSP_BUFFSIZE 65536
#define SELECTED_SOUND_OPTIONS 0xffffffff
#define SOUND_CONFIG_DATE "Sun Feb 5 14:38:12 EST 1995"
#define SOUND_CONFIG_BY "freebsd-hackers"
#define SOUND_CONFIG_HOST "freefall"
#define SOUND_CONFIG_DOMAIN "cdrom.com"
/* determine if sound code should be compiled */
#include "snd.h"
#if NSND > 0
#define KERNEL_SOUNDCARD
#endif
#define ALLOW_SELECT
/* PSS code does not work */
#ifndef EXCLUDE_PSS
#define EXCLUDE_PSS
#endif
#include "gus.h"
#if NGUS == 0 && !defined(EXCLUDE_GUS)
#define EXCLUDE_GUS
#endif
#include "gusxvi.h"
#if NGUSXVI == 0 && !defined(EXCLUDE_GUS16)
#define EXCLUDE_GUS16
#endif
#include "mss.h"
#if NMSS == 0 && !defined(EXCLUDE_MSS)
#define EXCLUDE_MSS
#endif
#include "trix.h"
#if NTRIX == 0 && !defined(EXCLUDE_TRIX)
#define EXCLUDE_TRIX
#endif
#include "sscape.h"
#if NSSCAPE == 0 && !defined(EXCLUDE_SSCAPE)
#define EXCLUDE_SSCAPE
#endif
#if NGUS == 0 && !defined(EXCLUDE_GUSMAX)
# define EXCLUDE_GUSMAX
# if defined(EXCLUDE_GUS16) && defined(EXCLUDE_MSS) && !defined(EXCLUDE_AD1848)
# define EXCLUDE_AD1848
# endif
#else
# define GUSMAX_MIXER
#endif
#include "sb.h"
#if NSB == 0 && !defined(EXCLUDE_SB)
#define EXCLUDE_SB
#endif
#include "sbxvi.h"
#if NSBXVI == 0 && !defined(EXCLUDE_SB16)
#define EXCLUDE_SB16
#endif
#include "sbmidi.h"
#if NSBMIDI == 0 && !defined(EXCLUDE_SB16MIDI)
#define EXCLUDE_SB16MIDI
#endif
#include "pas.h"
#if NPAS == 0 && !defined(EXCLUDE_PAS)
#define EXCLUDE_PAS
#endif
#include "mpu.h"
#if NMPU == 0 && !defined(EXCLUDE_MPU401)
#define EXCLUDE_MPU401
#endif
#include "opl.h"
#if NOPL == 0 && !defined(EXCLUDE_YM3812)
#define EXCLUDE_YM3812
#endif
#include "uart.h"
#if NUART == 0 && !defined(EXCLUDE_UART6850)
#define EXCLUDE_UART6850
#endif
#ifdef PC98
#include "pcm.h"
#if NPCM == 0 && !defined(EXCLUDE_PCM86)
#define EXCLUDE_PCM86
#endif
#endif
/* nothing but a sequencer (Adlib/OPL) ? */
#if NGUS == 0 && NSB == 0 && NSBMIDI == 0 && NPAS == 0 && NMPU == 0 && \
NUART == 0 && NMSS == 0
#ifndef EXCLUDE_MIDI
#define EXCLUDE_MIDI
#endif
#ifndef EXCLUDE_AUDIO
#if !defined(PC98) || defined(EXCLUDE_PCM86) && defined(EXCLUDE_MSS)
#define EXCLUDE_AUDIO
#endif
#endif
#endif
/* nothing but a Midi (MPU/UART) ? */
#if NGUS == 0 && NSB == 0 && NSBMIDI == 0 && NPAS == 0 && NOPL == 0 && \
NMSS == 0
/* MPU depends on sequencer timer */
#if NMPU == 0 && !defined(EXCLUDE_SEQUENCER)
#define EXCLUDE_SEQUENCER
#endif
#ifndef EXCLUDE_AUDIO
#if !defined(PC98) || defined(EXCLUDE_PCM86) && defined(EXCLUDE_MSS)
#define EXCLUDE_AUDIO
#endif
#endif
#endif

View File

@ -1,648 +0,0 @@
/*
* sound/midi_synth.c
*
* High level midi sequencer manager for dumb MIDI interfaces.
*
* Copyright by Hannu Savolainen 1993
*
* 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.
*
* 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.
*
*/
#define USE_SEQ_MACROS
#define USE_SIMPLE_MACROS
#ifdef PC98
#include <pc98/pc98/sound/sound_config.h>
#else
#include <i386/isa/sound/sound_config.h>
#endif
#if defined(CONFIGURE_SOUNDCARD) && !defined(EXCLUDE_MIDI)
#define _MIDI_SYNTH_C_
DEFINE_WAIT_QUEUE (sysex_sleeper, sysex_sleep_flag);
#include <i386/isa/sound/midi_synth.h>
static int midi2synth[MAX_MIDI_DEV];
static unsigned char prev_out_status[MAX_MIDI_DEV];
#define STORE(cmd) \
{ \
int len; \
unsigned char obuf[8]; \
cmd; \
seq_input_event(obuf, len); \
}
#define _seqbuf obuf
#define _seqbufptr 0
#define _SEQ_ADVBUF(x) len=x
void
do_midi_msg (int synthno, unsigned char *msg, int mlen)
{
switch (msg[0] & 0xf0)
{
case 0x90:
if (msg[2] != 0)
{
STORE (SEQ_START_NOTE (synthno, msg[0] & 0x0f, msg[1], msg[2]));
break;
}
msg[2] = 64;
case 0x80:
STORE (SEQ_STOP_NOTE (synthno, msg[0] & 0x0f, msg[1], msg[2]));
break;
case 0xA0:
STORE (SEQ_KEY_PRESSURE (synthno, msg[0] & 0x0f, msg[1], msg[2]));
break;
case 0xB0:
STORE (SEQ_CONTROL (synthno, msg[0] & 0x0f,
msg[1], msg[2]));
break;
case 0xC0:
STORE (SEQ_SET_PATCH (synthno, msg[0] & 0x0f, msg[1]));
break;
case 0xD0:
STORE (SEQ_CHN_PRESSURE (synthno, msg[0] & 0x0f, msg[1]));
break;
case 0xE0:
STORE (SEQ_BENDER (synthno, msg[0] & 0x0f,
(msg[1] % 0x7f) | ((msg[2] & 0x7f) << 7)));
break;
default:
printk ("MPU: Unknown midi channel message %02x\n", msg[0]);
}
}
static void
midi_outc (int midi_dev, int data)
{
int timeout;
for (timeout = 0; timeout < 32000; timeout++)
if (midi_devs[midi_dev]->putc (midi_dev, (unsigned char) (data & 0xff)))
{
if (data & 0x80) /*
* Status byte
*/
prev_out_status[midi_dev] =
(unsigned char) (data & 0xff); /*
* Store for running status
*/
return; /*
* Mission complete
*/
}
/*
* Sorry! No space on buffers.
*/
printk ("Midi send timed out\n");
}
static int
prefix_cmd (int midi_dev, unsigned char status)
{
if ((char *) midi_devs[midi_dev]->prefix_cmd == NULL)
return 1;
return midi_devs[midi_dev]->prefix_cmd (midi_dev, status);
}
static void
midi_synth_input (int dev, unsigned char data)
{
int orig_dev;
struct midi_input_info *inc;
static unsigned char len_tab[] = /* # of data bytes following a status
*/
{
2, /* 8x */
2, /* 9x */
2, /* Ax */
2, /* Bx */
1, /* Cx */
1, /* Dx */
2, /* Ex */
0 /* Fx */
};
if (dev < 0 || dev > num_synths)
return;
if (data == 0xfe) /* Ignore active sensing */
return;
orig_dev = midi2synth[dev];
inc = &midi_devs[orig_dev]->in_info;
switch (inc->m_state)
{
case MST_INIT:
if (data & 0x80) /* MIDI status byte */
{
if ((data & 0xf0) == 0xf0) /* Common message */
{
switch (data)
{
case 0xf0: /* Sysex */
inc->m_state = MST_SYSEX;
break; /* Sysex */
case 0xf1: /* MTC quarter frame */
case 0xf3: /* Song select */
inc->m_state = MST_DATA;
inc->m_ptr = 1;
inc->m_left = 1;
inc->m_buf[0] = data;
break;
case 0xf2: /* Song position pointer */
inc->m_state = MST_DATA;
inc->m_ptr = 1;
inc->m_left = 2;
inc->m_buf[0] = data;
break;
default:
inc->m_buf[0] = data;
inc->m_ptr = 1;
do_midi_msg (dev, inc->m_buf, inc->m_ptr);
inc->m_ptr = 0;
inc->m_left = 0;
}
}
else
{
inc->m_state = MST_DATA;
inc->m_ptr = 1;
inc->m_left = len_tab[(data >> 4) - 8];
inc->m_buf[0] = inc->m_prev_status = data;
}
}
else if (inc->m_prev_status & 0x80) /* Ignore if no previous status (yet) */
{ /* Data byte (use running status) */
inc->m_state = MST_DATA;
inc->m_ptr = 2;
inc->m_left = len_tab[(data >> 4) - 8] - 1;
inc->m_buf[0] = inc->m_prev_status;
inc->m_buf[1] = data;
}
break; /* MST_INIT */
case MST_DATA:
inc->m_buf[inc->m_ptr++] = data;
if (--inc->m_left <= 0)
{
inc->m_state = MST_INIT;
do_midi_msg (dev, inc->m_buf, inc->m_ptr);
inc->m_ptr = 0;
}
break; /* MST_DATA */
case MST_SYSEX:
if (data == 0xf7) /* Sysex end */
{
inc->m_state = MST_INIT;
inc->m_left = 0;
inc->m_ptr = 0;
}
break; /* MST_SYSEX */
default:
printk ("MIDI%d: Unexpected state %d (%02x)\n", orig_dev, inc->m_state,
(int) data);
inc->m_state = MST_INIT;
}
}
static void
midi_synth_output (int dev)
{
/*
* Currently NOP
*/
}
int
midi_synth_ioctl (int dev,
unsigned int cmd, unsigned int arg)
{
/*
* int orig_dev = synth_devs[dev]->midi_dev;
*/
switch (cmd)
{
case SNDCTL_SYNTH_INFO:
IOCTL_TO_USER ((char *) arg, 0, synth_devs[dev]->info,
sizeof (struct synth_info));
return 0;
break;
case SNDCTL_SYNTH_MEMAVL:
return 0x7fffffff;
break;
default:
return RET_ERROR (EINVAL);
}
}
int
midi_synth_kill_note (int dev, int channel, int note, int velocity)
{
int orig_dev = synth_devs[dev]->midi_dev;
int msg, chn;
if (note < 0 || note > 127)
return 0;
if (channel < 0 || channel > 15)
return 0;
if (velocity < 0)
velocity = 0;
if (velocity > 127)
velocity = 127;
msg = prev_out_status[orig_dev] & 0xf0;
chn = prev_out_status[orig_dev] & 0x0f;
if (chn == channel && ((msg == 0x90 && velocity == 64) || msg == 0x80))
{ /*
* Use running status
*/
if (!prefix_cmd (orig_dev, note))
return 0;
midi_outc (orig_dev, note);
if (msg == 0x90) /*
* Running status = Note on
*/
midi_outc (orig_dev, 0); /*
* Note on with velocity 0 == note
* off
*/
else
midi_outc (orig_dev, velocity);
}
else
{
if (velocity == 64)
{
if (!prefix_cmd (orig_dev, 0x90 | (channel & 0x0f)))
return 0;
midi_outc (orig_dev, 0x90 | (channel & 0x0f)); /*
* Note on
*/
midi_outc (orig_dev, note);
midi_outc (orig_dev, 0); /*
* Zero G
*/
}
else
{
if (!prefix_cmd (orig_dev, 0x80 | (channel & 0x0f)))
return 0;
midi_outc (orig_dev, 0x80 | (channel & 0x0f)); /*
* Note off
*/
midi_outc (orig_dev, note);
midi_outc (orig_dev, velocity);
}
}
return 0;
}
int
midi_synth_set_instr (int dev, int channel, int instr_no)
{
int orig_dev = synth_devs[dev]->midi_dev;
if (instr_no < 0 || instr_no > 127)
return 0;
if (channel < 0 || channel > 15)
return 0;
if (!prefix_cmd (orig_dev, 0xc0 | (channel & 0x0f)))
return 0;
midi_outc (orig_dev, 0xc0 | (channel & 0x0f)); /*
* Program change
*/
midi_outc (orig_dev, instr_no);
return 0;
}
int
midi_synth_start_note (int dev, int channel, int note, int velocity)
{
int orig_dev = synth_devs[dev]->midi_dev;
int msg, chn;
if (note < 0 || note > 127)
return 0;
if (channel < 0 || channel > 15)
return 0;
if (velocity < 0)
velocity = 0;
if (velocity > 127)
velocity = 127;
msg = prev_out_status[orig_dev] & 0xf0;
chn = prev_out_status[orig_dev] & 0x0f;
if (chn == channel && msg == 0x90)
{ /*
* Use running status
*/
if (!prefix_cmd (orig_dev, note))
return 0;
midi_outc (orig_dev, note);
midi_outc (orig_dev, velocity);
}
else
{
if (!prefix_cmd (orig_dev, 0x90 | (channel & 0x0f)))
return 0;
midi_outc (orig_dev, 0x90 | (channel & 0x0f)); /*
* Note on
*/
midi_outc (orig_dev, note);
midi_outc (orig_dev, velocity);
}
return 0;
}
void
midi_synth_reset (int dev)
{
}
int
midi_synth_open (int dev, int mode)
{
int orig_dev = synth_devs[dev]->midi_dev;
int err;
unsigned long flags;
struct midi_input_info *inc;
if (orig_dev < 0 || orig_dev > num_midis)
return RET_ERROR (ENXIO);
midi2synth[orig_dev] = dev;
prev_out_status[orig_dev] = 0;
if ((err = midi_devs[orig_dev]->open (orig_dev, mode,
midi_synth_input, midi_synth_output)) < 0)
return err;
inc = &midi_devs[orig_dev]->in_info;
DISABLE_INTR (flags);
inc->m_busy = 0;
inc->m_state = MST_INIT;
inc->m_ptr = 0;
inc->m_left = 0;
inc->m_prev_status = 0x00;
RESTORE_INTR (flags);
return 1;
}
void
midi_synth_close (int dev)
{
int orig_dev = synth_devs[dev]->midi_dev;
/*
* Shut up the synths by sending just single active sensing message.
*/
midi_devs[orig_dev]->putc (orig_dev, 0xfe);
midi_devs[orig_dev]->close (orig_dev);
}
void
midi_synth_hw_control (int dev, unsigned char *event)
{
}
int
midi_synth_load_patch (int dev, int format, snd_rw_buf * addr,
int offs, int count, int pmgr_flag)
{
int orig_dev = synth_devs[dev]->midi_dev;
struct sysex_info sysex;
int i;
unsigned long left, src_offs, eox_seen = 0;
int first_byte = 1;
int hdr_size = (unsigned long) &sysex.data[0] - (unsigned long) &sysex;
if (!prefix_cmd (orig_dev, 0xf0))
return 0;
if (format != SYSEX_PATCH)
{
printk ("MIDI Error: Invalid patch format (key) 0x%x\n", format);
return RET_ERROR (EINVAL);
}
if (count < hdr_size)
{
printk ("MIDI Error: Patch header too short\n");
return RET_ERROR (EINVAL);
}
count -= hdr_size;
/*
* Copy the header from user space but ignore the first bytes which have
* been transferred already.
*/
COPY_FROM_USER (&((char *) &sysex)[offs], addr, offs, hdr_size - offs);
if (count < sysex.len)
{
printk ("MIDI Warning: Sysex record too short (%d<%d)\n",
count, (int) sysex.len);
sysex.len = count;
}
left = sysex.len;
src_offs = 0;
RESET_WAIT_QUEUE (sysex_sleeper, sysex_sleep_flag);
for (i = 0; i < left && !PROCESS_ABORTING (sysex_sleeper, sysex_sleep_flag); i++)
{
unsigned char data;
GET_BYTE_FROM_USER (data, addr, hdr_size + i);
eox_seen = (i > 0 && data & 0x80); /* End of sysex */
if (eox_seen && data != 0xf7)
data = 0xf7;
if (i == 0)
{
if (data != 0xf0)
{
printk ("Error: Sysex start missing\n");
return RET_ERROR (EINVAL);
}
}
while (!midi_devs[orig_dev]->putc (orig_dev, (unsigned char) (data & 0xff)) &&
!PROCESS_ABORTING (sysex_sleeper, sysex_sleep_flag))
DO_SLEEP (sysex_sleeper, sysex_sleep_flag, 1); /* Wait for timeout */
if (!first_byte && data & 0x80)
return 0;
first_byte = 0;
}
if (!eox_seen)
midi_outc (orig_dev, 0xf7);
return 0;
}
void
midi_synth_panning (int dev, int channel, int pressure)
{
}
void
midi_synth_aftertouch (int dev, int channel, int pressure)
{
int orig_dev = synth_devs[dev]->midi_dev;
int msg, chn;
if (pressure < 0 || pressure > 127)
return;
if (channel < 0 || channel > 15)
return;
msg = prev_out_status[orig_dev] & 0xf0;
chn = prev_out_status[orig_dev] & 0x0f;
if (msg != 0xd0 || chn != channel) /*
* Test for running status
*/
{
if (!prefix_cmd (orig_dev, 0xd0 | (channel & 0x0f)))
return;
midi_outc (orig_dev, 0xd0 | (channel & 0x0f)); /*
* Channel pressure
*/
}
else if (!prefix_cmd (orig_dev, pressure))
return;
midi_outc (orig_dev, pressure);
}
void
midi_synth_controller (int dev, int channel, int ctrl_num, int value)
{
int orig_dev = synth_devs[dev]->midi_dev;
int chn, msg;
if (ctrl_num < 1 || ctrl_num > 127)
return; /* NOTE! Controller # 0 ignored */
if (channel < 0 || channel > 15)
return;
msg = prev_out_status[orig_dev] & 0xf0;
chn = prev_out_status[orig_dev] & 0x0f;
if (msg != 0xb0 || chn != channel)
{
if (!prefix_cmd (orig_dev, 0xb0 | (channel & 0x0f)))
return;
midi_outc (orig_dev, 0xb0 | (channel & 0x0f));
}
else if (!prefix_cmd (orig_dev, ctrl_num))
return;
midi_outc (orig_dev, ctrl_num);
midi_outc (orig_dev, value & 0x7f);
}
int
midi_synth_patchmgr (int dev, struct patmgr_info *rec)
{
return RET_ERROR (EINVAL);
}
void
midi_synth_bender (int dev, int channel, int value)
{
int orig_dev = synth_devs[dev]->midi_dev;
int msg, prev_chn;
if (channel < 0 || channel > 15)
return;
if (value < 0 || value > 16383)
return;
msg = prev_out_status[orig_dev] & 0xf0;
prev_chn = prev_out_status[orig_dev] & 0x0f;
if (msg != 0xd0 || prev_chn != channel) /*
* Test for running status
*/
{
if (!prefix_cmd (orig_dev, 0xe0 | (channel & 0x0f)))
return;
midi_outc (orig_dev, 0xe0 | (channel & 0x0f));
}
else if (!prefix_cmd (orig_dev, value & 0x7f))
return;
midi_outc (orig_dev, value & 0x7f);
midi_outc (orig_dev, (value >> 7) & 0x7f);
}
void
midi_synth_setup_voice (int dev, int voice, int channel)
{
}
#endif

View File

@ -1,474 +0,0 @@
/*
* sound/midibuf.c
*
* Device file manager for /dev/midi#
*
* Copyright by Hannu Savolainen 1993
*
* 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.
*
* 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.
*
*/
#ifdef PC98
#include <pc98/pc98/sound/sound_config.h>
#else
#include <i386/isa/sound/sound_config.h>
#endif
static void drain_midi_queue __P((int dev));
#if defined(CONFIGURE_SOUNDCARD) && !defined(EXCLUDE_MIDI)
/*
* Don't make MAX_QUEUE_SIZE larger than 4000
*/
#define MAX_QUEUE_SIZE 4000
DEFINE_WAIT_QUEUES (midi_sleeper[MAX_MIDI_DEV], midi_sleep_flag[MAX_MIDI_DEV]);
DEFINE_WAIT_QUEUES (input_sleeper[MAX_MIDI_DEV], input_sleep_flag[MAX_MIDI_DEV]);
struct midi_buf
{
int len, head, tail;
unsigned char queue[MAX_QUEUE_SIZE];
};
struct midi_parms
{
int prech_timeout; /*
* Timeout before the first ch
*/
};
static struct midi_buf *midi_out_buf[MAX_MIDI_DEV] =
{NULL};
static struct midi_buf *midi_in_buf[MAX_MIDI_DEV] =
{NULL};
static struct midi_parms parms[MAX_MIDI_DEV];
static void midi_poll (unsigned long dummy);
DEFINE_TIMER (poll_timer, midi_poll);
static volatile int open_devs = 0;
#define DATA_AVAIL(q) (q->len)
#define SPACE_AVAIL(q) (MAX_QUEUE_SIZE - q->len)
#define QUEUE_BYTE(q, data) \
if (SPACE_AVAIL(q)) \
{ \
unsigned long flags; \
DISABLE_INTR(flags); \
q->queue[q->tail] = (data); \
q->len++; q->tail = (q->tail+1) % MAX_QUEUE_SIZE; \
RESTORE_INTR(flags); \
}
#define REMOVE_BYTE(q, data) \
if (DATA_AVAIL(q)) \
{ \
unsigned long flags; \
DISABLE_INTR(flags); \
data = q->queue[q->head]; \
q->len--; q->head = (q->head+1) % MAX_QUEUE_SIZE; \
RESTORE_INTR(flags); \
}
static void
drain_midi_queue (int dev)
{
/*
* Give the Midi driver time to drain its output queues
*/
if (midi_devs[dev]->buffer_status != NULL)
while (!PROCESS_ABORTING (midi_sleeper[dev], midi_sleep_flag[dev]) &&
midi_devs[dev]->buffer_status (dev))
DO_SLEEP (midi_sleeper[dev], midi_sleep_flag[dev], HZ / 10);
}
static void
midi_input_intr (int dev, unsigned char data)
{
if (midi_in_buf[dev] == NULL)
return;
if (data == 0xfe) /*
* Active sensing
*/
return; /*
* Ignore
*/
if (SPACE_AVAIL (midi_in_buf[dev]))
{
QUEUE_BYTE (midi_in_buf[dev], data);
if (SOMEONE_WAITING (input_sleeper[dev], input_sleep_flag[dev]))
WAKE_UP (input_sleeper[dev], input_sleep_flag[dev]);
}
#if defined(__FreeBSD__)
if (selinfo[dev].si_pid)
selwakeup(&selinfo[dev]);
#endif
}
static void
midi_output_intr (int dev)
{
/*
* Currently NOP
*/
#if defined(__FreeBSD__)
if (selinfo[dev].si_pid)
selwakeup(&selinfo[dev]);
#endif
}
static void
midi_poll (unsigned long dummy)
{
unsigned long flags;
int dev;
DISABLE_INTR (flags);
if (open_devs)
{
for (dev = 0; dev < num_midis; dev++)
if (midi_out_buf[dev] != NULL)
{
while (DATA_AVAIL (midi_out_buf[dev]) &&
midi_devs[dev]->putc (dev,
midi_out_buf[dev]->queue[midi_out_buf[dev]->head]))
{
midi_out_buf[dev]->head = (midi_out_buf[dev]->head + 1) % MAX_QUEUE_SIZE;
midi_out_buf[dev]->len--;
}
if (DATA_AVAIL (midi_out_buf[dev]) < 100 &&
SOMEONE_WAITING (midi_sleeper[dev], midi_sleep_flag[dev]))
WAKE_UP (midi_sleeper[dev], midi_sleep_flag[dev]);
}
ACTIVATE_TIMER (poll_timer, midi_poll, 1); /*
* Come back later
*/
}
RESTORE_INTR (flags);
}
int
MIDIbuf_open (int dev, struct fileinfo *file)
{
int mode, err;
unsigned long flags;
dev = dev >> 4;
mode = file->mode & O_ACCMODE;
if (num_midis > MAX_MIDI_DEV)
{
printk ("Sound: FATAL ERROR: Too many midi interfaces\n");
num_midis = MAX_MIDI_DEV;
}
if (dev < 0 || dev >= num_midis)
{
printk ("Sound: Nonexistent MIDI interface %d\n", dev);
return RET_ERROR (ENXIO);
}
/*
* Interrupts disabled. Be careful
*/
DISABLE_INTR (flags);
if ((err = midi_devs[dev]->open (dev, mode,
midi_input_intr, midi_output_intr)) < 0)
{
RESTORE_INTR (flags);
return err;
}
parms[dev].prech_timeout = 0;
RESET_WAIT_QUEUE (midi_sleeper[dev], midi_sleep_flag[dev]);
RESET_WAIT_QUEUE (input_sleeper[dev], input_sleep_flag[dev]);
midi_in_buf[dev] = (struct midi_buf *) KERNEL_MALLOC (sizeof (struct midi_buf));
if (midi_in_buf[dev] == NULL)
{
printk ("midi: Can't allocate buffer\n");
midi_devs[dev]->close (dev);
RESTORE_INTR (flags);
return RET_ERROR (EIO);
}
midi_in_buf[dev]->len = midi_in_buf[dev]->head = midi_in_buf[dev]->tail = 0;
midi_out_buf[dev] = (struct midi_buf *) KERNEL_MALLOC (sizeof (struct midi_buf));
if (midi_out_buf[dev] == NULL)
{
printk ("midi: Can't allocate buffer\n");
midi_devs[dev]->close (dev);
KERNEL_FREE (midi_in_buf[dev]);
midi_in_buf[dev] = NULL;
RESTORE_INTR (flags);
return RET_ERROR (EIO);
}
midi_out_buf[dev]->len = midi_out_buf[dev]->head = midi_out_buf[dev]->tail = 0;
if (!open_devs)
ACTIVATE_TIMER (poll_timer, midi_poll, 1); /*
* Come back later
*/
open_devs++;
RESTORE_INTR (flags);
return err;
}
void
MIDIbuf_release (int dev, struct fileinfo *file)
{
int mode;
unsigned long flags;
dev = dev >> 4;
mode = file->mode & O_ACCMODE;
DISABLE_INTR (flags);
/*
* Wait until the queue is empty
*/
if (mode != OPEN_READ)
{
midi_devs[dev]->putc (dev, 0xfe); /*
* Active sensing to shut the
* devices
*/
while (!PROCESS_ABORTING (midi_sleeper[dev], midi_sleep_flag[dev]) &&
DATA_AVAIL (midi_out_buf[dev]))
DO_SLEEP (midi_sleeper[dev], midi_sleep_flag[dev], 0); /*
* Sync
*/
drain_midi_queue (dev); /*
* Ensure the output queues are empty
*/
}
midi_devs[dev]->close (dev);
KERNEL_FREE (midi_in_buf[dev]);
KERNEL_FREE (midi_out_buf[dev]);
midi_in_buf[dev] = NULL;
midi_out_buf[dev] = NULL;
open_devs--;
RESTORE_INTR (flags);
}
int
MIDIbuf_write (int dev, struct fileinfo *file, snd_rw_buf * buf, int count)
{
unsigned long flags;
int c, n, i;
unsigned char tmp_data;
dev = dev >> 4;
if (!count)
return 0;
DISABLE_INTR (flags);
c = 0;
while (c < count)
{
n = SPACE_AVAIL (midi_out_buf[dev]);
if (n == 0) /*
* No space just now. We have to sleep
*/
{
DO_SLEEP (midi_sleeper[dev], midi_sleep_flag[dev], 0);
if (PROCESS_ABORTING (midi_sleeper[dev], midi_sleep_flag[dev]))
{
RESTORE_INTR (flags);
return RET_ERROR (EINTR);
}
n = SPACE_AVAIL (midi_out_buf[dev]);
}
if (n > (count - c))
n = count - c;
for (i = 0; i < n; i++)
{
COPY_FROM_USER (&tmp_data, buf, c, 1);
QUEUE_BYTE (midi_out_buf[dev], tmp_data);
c++;
}
}
RESTORE_INTR (flags);
return c;
}
int
MIDIbuf_read (int dev, struct fileinfo *file, snd_rw_buf * buf, int count)
{
int n, c = 0;
unsigned long flags;
unsigned char tmp_data;
dev = dev >> 4;
DISABLE_INTR (flags);
if (!DATA_AVAIL (midi_in_buf[dev])) /*
* No data yet, wait
*/
{
DO_SLEEP (input_sleeper[dev], input_sleep_flag[dev],
parms[dev].prech_timeout);
if (PROCESS_ABORTING (input_sleeper[dev], input_sleep_flag[dev]))
c = RET_ERROR (EINTR); /*
* The user is getting restless
*/
}
if (c == 0 && DATA_AVAIL (midi_in_buf[dev])) /*
* Got some bytes
*/
{
n = DATA_AVAIL (midi_in_buf[dev]);
if (n > count)
n = count;
c = 0;
while (c < n)
{
REMOVE_BYTE (midi_in_buf[dev], tmp_data);
COPY_TO_USER (buf, c, &tmp_data, 1);
c++;
}
}
RESTORE_INTR (flags);
return c;
}
int
MIDIbuf_ioctl (int dev, struct fileinfo *file,
unsigned int cmd, unsigned int arg)
{
int val;
dev = dev >> 4;
if (((cmd >> 8) & 0xff) == 'C')
{
if (midi_devs[dev]->coproc) /* Coprocessor ioctl */
return midi_devs[dev]->coproc->ioctl (midi_devs[dev]->coproc->devc, cmd, arg, 0);
else
printk ("/dev/midi%d: No coprocessor for this device\n", dev);
return RET_ERROR (EREMOTEIO);
}
else
switch (cmd)
{
case SNDCTL_MIDI_PRETIME:
val = IOCTL_IN (arg);
if (val < 0)
val = 0;
val = (HZ * val) / 10;
parms[dev].prech_timeout = val;
return IOCTL_OUT (arg, val);
break;
default:
return midi_devs[dev]->ioctl (dev, cmd, arg);
}
}
#ifdef ALLOW_SELECT
int
MIDIbuf_select (int dev, struct fileinfo *file, int sel_type, select_table * wait)
{
dev = dev >> 4;
switch (sel_type)
{
case SEL_IN:
if (!DATA_AVAIL (midi_in_buf[dev]))
{
#if defined(__FreeBSD__)
selrecord(wait, &selinfo[dev]);
#else
input_sleep_flag[dev].mode = WK_SLEEP;
select_wait (&input_sleeper[dev], wait);
#endif
return 0;
}
return 1;
break;
case SEL_OUT:
if (SPACE_AVAIL (midi_out_buf[dev]))
{
#if defined(__FreeBSD__)
selrecord(wait, &selinfo[dev]);
#else
midi_sleep_flag[dev].mode = WK_SLEEP;
select_wait (&midi_sleeper[dev], wait);
#endif
return 0;
}
return 1;
break;
case SEL_EX:
return 0;
}
return 0;
}
#endif /* ALLOW_SELECT */
long
MIDIbuf_init (long mem_start)
{
return mem_start;
}
#endif

File diff suppressed because it is too large Load Diff

View File

@ -34,11 +34,7 @@
* hooft@chem.ruu.nl
*/
#ifdef PC98
#include <pc98/pc98/sound/sound_config.h>
#else
#include <i386/isa/sound/sound_config.h>
#endif
#if defined(CONFIGURE_SOUNDCARD) && !defined(EXCLUDE_YM3812)

View File

@ -1,420 +0,0 @@
#define _PAS2_CARD_C_
/*
* sound/pas2_card.c
*
* Detection routine for the Pro Audio Spectrum cards.
*
* Copyright by Hannu Savolainen 1993
*
* 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.
*
* 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.
*
*/
#include <i386/isa/sound/sound_config.h>
#if defined(CONFIGURE_SOUNDCARD) && !defined(EXCLUDE_PAS)
#define DEFINE_TRANSLATIONS
#include <i386/isa/sound/pas.h>
static int config_pas_hw __P((struct address_info *hw_config));
static int detect_pas_hw __P((struct address_info *hw_config));
static void pas2_msg __P((char *foo));
/*
* The Address Translation code is used to convert I/O register addresses to
* be relative to the given base -register
*/
int translat_code;
static int pas_intr_mask = 0;
static int pas_irq = 0;
char pas_model;
static char *pas_model_names[] =
{"", "Pro AudioSpectrum+", "CDPC", "Pro AudioSpectrum 16", "Pro AudioSpectrum 16D"};
extern void mix_write (unsigned char data, int ioaddr);
/*
* pas_read() and pas_write() are equivalents of INB() and OUTB()
*/
/*
* These routines perform the I/O address translation required
*/
/*
* to support other than the default base address
*/
unsigned char
pas_read (int ioaddr)
{
return INB (ioaddr ^ translat_code);
}
void
pas_write (unsigned char data, int ioaddr)
{
OUTB (data, ioaddr ^ translat_code);
}
static void
pas2_msg (char *foo)
{
printk (" PAS2: %s.\n", foo);
}
/******************* Begin of the Interrupt Handler ********************/
void
pasintr (INT_HANDLER_PARMS (irq, dummy))
{
int status;
status = pas_read (INTERRUPT_STATUS);
pas_write (status, INTERRUPT_STATUS); /*
* Clear interrupt
*/
if (status & I_S_PCM_SAMPLE_BUFFER_IRQ)
{
#ifndef EXCLUDE_AUDIO
pas_pcm_interrupt (status, 1);
#endif
status &= ~I_S_PCM_SAMPLE_BUFFER_IRQ;
}
if (status & I_S_MIDI_IRQ)
{
#ifndef EXCLUDE_MIDI
#ifdef EXCLUDE_PRO_MIDI
pas_midi_interrupt ();
#endif
#endif
status &= ~I_S_MIDI_IRQ;
}
}
int
pas_set_intr (int mask)
{
int err;
if (!mask)
return 0;
if (!pas_intr_mask)
{
if ((err = snd_set_irq_handler (pas_irq, pasintr, "PAS16")) < 0)
return err;
}
pas_intr_mask |= mask;
pas_write (pas_intr_mask, INTERRUPT_MASK);
return 0;
}
int
pas_remove_intr (int mask)
{
if (!mask)
return 0;
pas_intr_mask &= ~mask;
pas_write (pas_intr_mask, INTERRUPT_MASK);
if (!pas_intr_mask)
{
snd_release_irq (pas_irq);
}
return 0;
}
/******************* End of the Interrupt handler **********************/
/******************* Begin of the Initialization Code ******************/
static int
config_pas_hw (struct address_info *hw_config)
{
char ok = 1;
unsigned int_ptrs; /* scsi/sound interrupt pointers */
pas_irq = hw_config->irq;
pas_write (0x00, INTERRUPT_MASK);
pas_write (0x36, SAMPLE_COUNTER_CONTROL); /*
* Local timer control *
* register
*/
pas_write (0x36, SAMPLE_RATE_TIMER); /*
* Sample rate timer (16 bit)
*/
pas_write (0, SAMPLE_RATE_TIMER);
pas_write (0x74, SAMPLE_COUNTER_CONTROL); /*
* Local timer control *
* register
*/
pas_write (0x74, SAMPLE_BUFFER_COUNTER); /*
* Sample count register (16
* * bit)
*/
pas_write (0, SAMPLE_BUFFER_COUNTER);
pas_write (F_F_PCM_BUFFER_COUNTER | F_F_PCM_RATE_COUNTER | F_F_MIXER_UNMUTE | 1, FILTER_FREQUENCY);
pas_write (P_C_PCM_DMA_ENABLE | P_C_PCM_MONO | P_C_PCM_DAC_MODE | P_C_MIXER_CROSS_L_TO_L | P_C_MIXER_CROSS_R_TO_R, PCM_CONTROL);
pas_write (S_M_PCM_RESET | S_M_FM_RESET | S_M_SB_RESET | S_M_MIXER_RESET /*
* |
* S_M_OPL3_DUAL_MONO
*/ , SERIAL_MIXER);
pas_write (I_C_1_BOOT_RESET_ENABLE
#ifdef PAS_JOYSTICK_ENABLE
| I_C_1_JOYSTICK_ENABLE
#endif
,IO_CONFIGURATION_1);
if (pas_irq < 0 || pas_irq > 15)
{
printk ("PAS2: Invalid IRQ %d", pas_irq);
ok = 0;
}
else
{
int_ptrs = pas_read (IO_CONFIGURATION_3);
int_ptrs |= I_C_3_PCM_IRQ_translate[pas_irq] & 0xf;
pas_write (int_ptrs, IO_CONFIGURATION_3);
if (!I_C_3_PCM_IRQ_translate[pas_irq])
{
printk ("PAS2: Invalid IRQ %d", pas_irq);
ok = 0;
}
}
if (hw_config->dma < 0 || hw_config->dma > 7)
{
printk ("PAS2: Invalid DMA selection %d", hw_config->dma);
ok = 0;
}
else
{
pas_write (I_C_2_PCM_DMA_translate[hw_config->dma], IO_CONFIGURATION_2);
if (!I_C_2_PCM_DMA_translate[hw_config->dma])
{
printk ("PAS2: Invalid DMA selection %d", hw_config->dma);
ok = 0;
}
}
/*
* This fixes the timing problems of the PAS due to the Symphony chipset
* as per Media Vision. Only define this if your PAS doesn't work correctly.
*/
#ifdef SYMPHONY_PAS
OUTB (0x05, 0xa8);
OUTB (0x60, 0xa9);
#endif
#ifdef BROKEN_BUS_CLOCK
pas_write (S_C_1_PCS_ENABLE | S_C_1_PCS_STEREO | S_C_1_PCS_REALSOUND | S_C_1_FM_EMULATE_CLOCK, SYSTEM_CONFIGURATION_1);
#else
/*
* pas_write(S_C_1_PCS_ENABLE, SYSTEM_CONFIGURATION_1);
*/
pas_write (S_C_1_PCS_ENABLE | S_C_1_PCS_STEREO | S_C_1_PCS_REALSOUND, SYSTEM_CONFIGURATION_1);
#endif
pas_write (0x18, SYSTEM_CONFIGURATION_3); /*
* ???
*/
pas_write (F_F_MIXER_UNMUTE | 0x01, FILTER_FREQUENCY); /*
* Sets mute
* off and *
* selects
* filter
* rate * of
* 17.897 kHz
*/
if (pas_model == PAS_16 || pas_model == PAS_16D)
pas_write (8, PRESCALE_DIVIDER);
else
pas_write (0, PRESCALE_DIVIDER);
mix_write (P_M_MV508_ADDRESS | 5, PARALLEL_MIXER);
mix_write (5, PARALLEL_MIXER);
#if !defined(EXCLUDE_SB_EMULATION) || !defined(EXCLUDE_SB)
{
struct address_info *sb_config;
if ((sb_config = sound_getconf (SNDCARD_SB)))
{
unsigned char irq_dma;
/*
* Turn on Sound Blaster compatibility
*/
/*
* bit 1 = SB emulation
*/
/*
* bit 0 = MPU401 emulation (CDPC only :-( )
*/
pas_write (0x02, COMPATIBILITY_ENABLE);
/*
* "Emulation address"
*/
pas_write ((sb_config->io_base >> 4) & 0x0f, EMULATION_ADDRESS);
if (!E_C_SB_DMA_translate[sb_config->dma])
printk ("\n\nPAS16 Warning: Invalid SB DMA %d\n\n",
sb_config->dma);
if (!E_C_SB_IRQ_translate[sb_config->irq])
printk ("\n\nPAS16 Warning: Invalid SB IRQ %d\n\n",
sb_config->irq);
irq_dma = E_C_SB_DMA_translate[sb_config->dma] |
E_C_SB_IRQ_translate[sb_config->irq];
pas_write (irq_dma, EMULATION_CONFIGURATION);
}
}
#endif
if (!ok)
pas2_msg ("Driver not enabled");
return ok;
}
static int
detect_pas_hw (struct address_info *hw_config)
{
unsigned char board_id, foo;
/*
* WARNING: Setting an option like W:1 or so that disables warm boot reset
* of the card will screw up this detect code something fierce. Adding code
* to handle this means possibly interfering with other cards on the bus if
* you have something on base port 0x388. SO be forewarned.
*/
OUTB (0xBC, MASTER_DECODE); /*
* Talk to first board
*/
OUTB (hw_config->io_base >> 2, MASTER_DECODE); /*
* Set base address
*/
translat_code = PAS_DEFAULT_BASE ^ hw_config->io_base;
pas_write (1, WAIT_STATE); /*
* One wait-state
*/
board_id = pas_read (INTERRUPT_MASK);
if (board_id == 0xff)
return 0;
/*
* We probably have a PAS-series board, now check for a PAS2-series board
* by trying to change the board revision bits. PAS2-series hardware won't
* let you do this - the bits are read-only.
*/
foo = board_id ^ 0xe0;
pas_write (foo, INTERRUPT_MASK);
foo = INB (INTERRUPT_MASK);
pas_write (board_id, INTERRUPT_MASK);
if (board_id != foo) /*
* Not a PAS2
*/
return 0;
pas_model = pas_read (CHIP_REV);
return pas_model;
}
long
attach_pas_card (long mem_start, struct address_info *hw_config)
{
pas_irq = hw_config->irq;
if (detect_pas_hw (hw_config))
{
if (pas_model = pas_read (CHIP_REV))
{
#ifdef __FreeBSD__
printk ("pas0: <%s rev %d>", pas_model_names[(int) pas_model], pas_read (BOARD_REV_ID));
#else
printk (" <%s rev %d>", pas_model_names[(int) pas_model], pas_read (BOARD_REV_ID));
#endif
}
if (config_pas_hw (hw_config))
{
#ifndef EXCLUDE_AUDIO
mem_start = pas_pcm_init (mem_start, hw_config);
#endif
#if !defined(EXCLUDE_SB_EMULATION) && !defined(EXCLUDE_SB)
sb_dsp_disable_midi (); /*
* The SB emulation don't support *
* midi
*/
#endif
#ifndef EXCLUDE_YM3812
enable_opl3_mode (0x388, 0x38a, 0);
#endif
#ifndef EXCLUDE_MIDI
#ifdef EXCLUDE_PRO_MIDI
mem_start = pas_midi_init (mem_start);
#endif
#endif
pas_init_mixer ();
}
}
return mem_start;
}
int
probe_pas (struct address_info *hw_config)
{
return detect_pas_hw (hw_config);
}
#endif

View File

@ -1,341 +0,0 @@
/*
* sound/pas2_midi.c
*
* The low level driver for the PAS Midi Interface.
*
* Copyright by Hannu Savolainen 1993
*
* 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.
*
* 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.
*
*/
#include <i386/isa/sound/sound_config.h>
#ifdef CONFIGURE_SOUNDCARD
#include <i386/isa/sound/pas.h>
#if !defined(EXCLUDE_PAS) && !defined(EXCLUDE_MIDI) && defined(EXCLUDE_PRO_MIDI)
static int midi_busy = 0, input_opened = 0;
static int my_dev;
static volatile int ofifo_bytes = 0;
static unsigned char tmp_queue[256];
static volatile int qlen;
static volatile unsigned char qhead, qtail;
static void (*midi_input_intr) (int dev, unsigned char data);
static int
pas_midi_open (int dev, int mode,
void (*input) (int dev, unsigned char data),
void (*output) (int dev)
)
{
int err;
unsigned long flags;
unsigned char ctrl;
if (midi_busy)
{
printk ("PAS2: Midi busy\n");
return RET_ERROR (EBUSY);
}
/*
* Reset input and output FIFO pointers
*/
pas_write (M_C_RESET_INPUT_FIFO | M_C_RESET_OUTPUT_FIFO,
MIDI_CONTROL);
DISABLE_INTR (flags);
if ((err = pas_set_intr (I_M_MIDI_IRQ_ENABLE)) < 0)
return err;
/*
* Enable input available and output FIFO empty interrupts
*/
ctrl = 0;
input_opened = 0;
midi_input_intr = input;
if (mode == OPEN_READ || mode == OPEN_READWRITE)
{
ctrl |= M_C_ENA_INPUT_IRQ; /*
* Enable input
*/
input_opened = 1;
}
if (mode == OPEN_WRITE || mode == OPEN_READWRITE)
{
ctrl |= M_C_ENA_OUTPUT_IRQ | /*
* Enable output
*/
M_C_ENA_OUTPUT_HALF_IRQ;
}
pas_write (ctrl,
MIDI_CONTROL);
/*
* Acknowledge any pending interrupts
*/
pas_write (0xff, MIDI_STATUS);
ofifo_bytes = 0;
RESTORE_INTR (flags);
midi_busy = 1;
qlen = qhead = qtail = 0;
return 0;
}
static void
pas_midi_close (int dev)
{
/*
* Reset FIFO pointers, disable intrs
*/
pas_write (M_C_RESET_INPUT_FIFO | M_C_RESET_OUTPUT_FIFO, MIDI_CONTROL);
pas_remove_intr (I_M_MIDI_IRQ_ENABLE);
midi_busy = 0;
}
static int
dump_to_midi (unsigned char midi_byte)
{
int fifo_space, x;
fifo_space = ((x = pas_read (MIDI_FIFO_STATUS)) >> 4) & 0x0f;
if (fifo_space == 15 || (fifo_space < 2 && ofifo_bytes > 13)) /*
* Fifo
* full
*/
{
return 0; /*
* Upper layer will call again
*/
}
ofifo_bytes++;
pas_write (midi_byte, MIDI_DATA);
return 1;
}
static int
pas_midi_out (int dev, unsigned char midi_byte)
{
unsigned long flags;
/*
* Drain the local queue first
*/
DISABLE_INTR (flags);
while (qlen && dump_to_midi (tmp_queue[qhead]))
{
qlen--;
qhead++;
}
RESTORE_INTR (flags);
/*
* Output the byte if the local queue is empty.
*/
if (!qlen)
if (dump_to_midi (midi_byte))
return 1; /*
* OK
*/
/*
* Put to the local queue
*/
if (qlen >= 256)
return 0; /*
* Local queue full
*/
DISABLE_INTR (flags);
tmp_queue[qtail] = midi_byte;
qlen++;
qtail++;
RESTORE_INTR (flags);
return 1;
}
static int
pas_midi_start_read (int dev)
{
return 0;
}
static int
pas_midi_end_read (int dev)
{
return 0;
}
static int
pas_midi_ioctl (int dev, unsigned cmd, unsigned arg)
{
return RET_ERROR (EINVAL);
}
static void
pas_midi_kick (int dev)
{
ofifo_bytes = 0;
}
static int
pas_buffer_status (int dev)
{
return !qlen;
}
#define MIDI_SYNTH_NAME "Pro Audio Spectrum Midi"
#define MIDI_SYNTH_CAPS SYNTH_CAP_INPUT
#include <i386/isa/sound/midi_synth.h>
static struct midi_operations pas_midi_operations =
{
{"Pro Audio Spectrum", 0, 0, SNDCARD_PAS},
&std_midi_synth,
{0},
pas_midi_open,
pas_midi_close,
pas_midi_ioctl,
pas_midi_out,
pas_midi_start_read,
pas_midi_end_read,
pas_midi_kick,
NULL, /*
* command
*/
pas_buffer_status,
NULL
};
long
pas_midi_init (long mem_start)
{
if (num_midis >= MAX_MIDI_DEV)
{
printk ("Sound: Too many midi devices detected\n");
return mem_start;
}
std_midi_synth.midi_dev = my_dev = num_midis;
midi_devs[num_midis++] = &pas_midi_operations;
return mem_start;
}
void
pas_midi_interrupt (void)
{
unsigned char stat;
int i, incount;
unsigned long flags;
stat = pas_read (MIDI_STATUS);
if (stat & M_S_INPUT_AVAIL) /*
* Input byte available
*/
{
incount = pas_read (MIDI_FIFO_STATUS) & 0x0f; /*
* Input FIFO count
*/
if (!incount)
incount = 16;
for (i = 0; i < incount; i++)
if (input_opened)
{
midi_input_intr (my_dev, pas_read (MIDI_DATA));
}
else
pas_read (MIDI_DATA); /*
* Flush
*/
}
if (stat & (M_S_OUTPUT_EMPTY | M_S_OUTPUT_HALF_EMPTY))
{
if (!(stat & M_S_OUTPUT_EMPTY))
{
ofifo_bytes = 8;
}
else
{
ofifo_bytes = 0;
}
DISABLE_INTR (flags);
while (qlen && dump_to_midi (tmp_queue[qhead]))
{
qlen--;
qhead++;
}
RESTORE_INTR (flags);
}
#if 0
if (stat & M_S_FRAMING_ERROR)
printk ("MIDI framing error\n");
#endif
if (stat & M_S_OUTPUT_OVERRUN)
{
printk ("MIDI output overrun %x,%x,%d \n", pas_read (MIDI_FIFO_STATUS), stat, ofifo_bytes);
ofifo_bytes = 100;
}
pas_write (stat, MIDI_STATUS); /*
* Acknowledge interrupts
*/
}
#endif
#endif

View File

@ -1,340 +0,0 @@
#define _PAS2_MIXER_C_
/*
* sound/pas2_mixer.c
*
* Mixer routines for the Pro Audio Spectrum cards.
*
* Copyright by Hannu Savolainen 1993
*
* 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.
*
* 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.
*
*/
#include <i386/isa/sound/sound_config.h>
#if defined(CONFIGURE_SOUNDCARD) && !defined(EXCLUDE_PAS)
#include <i386/isa/sound/pas.h>
extern void mix_write __P((unsigned char data, int ioaddr));
static int pas_mixer_ioctl __P((int dev, unsigned int cmd, unsigned int arg));
static void set_mode __P((int new_mode));
#define TRACE(what) /* (what) */
extern int translat_code;
extern char pas_model;
static int rec_devices = (SOUND_MASK_MIC); /* Default recording source */
static int mode_control = 0;
#define POSSIBLE_RECORDING_DEVICES (SOUND_MASK_SYNTH | SOUND_MASK_SPEAKER | SOUND_MASK_LINE | SOUND_MASK_MIC | \
SOUND_MASK_CD | SOUND_MASK_ALTPCM)
#define SUPPORTED_MIXER_DEVICES (SOUND_MASK_SYNTH | SOUND_MASK_PCM | SOUND_MASK_SPEAKER | SOUND_MASK_LINE | SOUND_MASK_MIC | \
SOUND_MASK_CD | SOUND_MASK_ALTPCM | SOUND_MASK_IMIX | \
SOUND_MASK_VOLUME | SOUND_MASK_BASS | SOUND_MASK_TREBLE | SOUND_MASK_RECLEV | \
SOUND_MASK_MUTE | SOUND_MASK_ENHANCE | SOUND_MASK_LOUD)
static unsigned short levels[SOUND_MIXER_NRDEVICES] =
{
0x3232, /* Master Volume */
0x3232, /* Bass */
0x3232, /* Treble */
0x5050, /* FM */
0x4b4b, /* PCM */
0x3232, /* PC Speaker */
0x4b4b, /* Ext Line */
0x4b4b, /* Mic */
0x4b4b, /* CD */
0x6464, /* Recording monitor */
0x4b4b, /* SB PCM */
0x6464 /* Recording level */
};
void
mix_write (unsigned char data, int ioaddr)
{
/*
* The Revision D cards have a problem with their MVA508 interface. The
* kludge-o-rama fix is to make a 16-bit quantity with identical LSB and
* MSBs out of the output byte and to do a 16-bit out to the mixer port -
* 1. We need to do this because it isn't timing problem but chip access
* sequence problem.
*/
if (pas_model == PAS_16D)
{
OUTW (data | (data << 8), (ioaddr ^ translat_code) - 1);
OUTB (0x80, 0);
}
else
pas_write (data, ioaddr);
}
static int
mixer_output (int right_vol, int left_vol, int div, int bits,
int mixer) /* Input or output mixer */
{
int left = left_vol * div / 100;
int right = right_vol * div / 100;
if (bits & P_M_MV508_MIXER)
{ /*
* Select input or output mixer
*/
left |= mixer;
right |= mixer;
}
if (bits == P_M_MV508_BASS || bits == P_M_MV508_TREBLE)
{ /*
* Bass and treble are mono devices
*/
mix_write (P_M_MV508_ADDRESS | bits, PARALLEL_MIXER);
mix_write (left, PARALLEL_MIXER);
right_vol = left_vol;
}
else
{
mix_write (P_M_MV508_ADDRESS | P_M_MV508_LEFT | bits, PARALLEL_MIXER);
mix_write (left, PARALLEL_MIXER);
mix_write (P_M_MV508_ADDRESS | P_M_MV508_RIGHT | bits, PARALLEL_MIXER);
mix_write (right, PARALLEL_MIXER);
}
return (left_vol | (right_vol << 8));
}
static void
set_mode (int new_mode)
{
mix_write (P_M_MV508_ADDRESS | P_M_MV508_MODE, PARALLEL_MIXER);
mix_write (new_mode, PARALLEL_MIXER);
mode_control = new_mode;
}
static int
pas_mixer_set (int whichDev, unsigned int level)
{
int left, right, devmask, changed, i, mixer = 0;
TRACE (printk ("static int pas_mixer_set(int whichDev = %d, unsigned int level = %X)\n", whichDev, level));
left = level & 0x7f;
right = (level & 0x7f00) >> 8;
if (whichDev < SOUND_MIXER_NRDEVICES)
if ((1 << whichDev) & rec_devices)
mixer = P_M_MV508_INPUTMIX;
else
mixer = P_M_MV508_OUTPUTMIX;
switch (whichDev)
{
case SOUND_MIXER_VOLUME: /* Master volume (0-63) */
levels[whichDev] = mixer_output (right, left, 63, P_M_MV508_MASTER_A, 0);
break;
/*
* Note! Bass and Treble are mono devices. Will use just the left
* channel.
*/
case SOUND_MIXER_BASS: /* Bass (0-12) */
levels[whichDev] = mixer_output (right, left, 12, P_M_MV508_BASS, 0);
break;
case SOUND_MIXER_TREBLE: /* Treble (0-12) */
levels[whichDev] = mixer_output (right, left, 12, P_M_MV508_TREBLE, 0);
break;
case SOUND_MIXER_SYNTH: /* Internal synthesizer (0-31) */
levels[whichDev] = mixer_output (right, left, 31, P_M_MV508_MIXER | P_M_MV508_FM, mixer);
break;
case SOUND_MIXER_PCM: /* PAS PCM (0-31) */
levels[whichDev] = mixer_output (right, left, 31, P_M_MV508_MIXER | P_M_MV508_PCM, mixer);
break;
case SOUND_MIXER_ALTPCM: /* SB PCM (0-31) */
levels[whichDev] = mixer_output (right, left, 31, P_M_MV508_MIXER | P_M_MV508_SB, mixer);
break;
case SOUND_MIXER_SPEAKER: /* PC speaker (0-31) */
levels[whichDev] = mixer_output (right, left, 31, P_M_MV508_MIXER | P_M_MV508_SPEAKER, mixer);
break;
case SOUND_MIXER_LINE: /* External line (0-31) */
levels[whichDev] = mixer_output (right, left, 31, P_M_MV508_MIXER | P_M_MV508_LINE, mixer);
break;
case SOUND_MIXER_CD: /* CD (0-31) */
levels[whichDev] = mixer_output (right, left, 31, P_M_MV508_MIXER | P_M_MV508_CDROM, mixer);
break;
case SOUND_MIXER_MIC: /* External microphone (0-31) */
levels[whichDev] = mixer_output (right, left, 31, P_M_MV508_MIXER | P_M_MV508_MIC, mixer);
break;
case SOUND_MIXER_IMIX: /* Recording monitor (0-31) (Output mixer only) */
levels[whichDev] = mixer_output (right, left, 31, P_M_MV508_MIXER | P_M_MV508_IMIXER,
P_M_MV508_OUTPUTMIX);
break;
case SOUND_MIXER_RECLEV: /* Recording level (0-15) */
levels[whichDev] = mixer_output (right, left, 15, P_M_MV508_MASTER_B, 0);
break;
case SOUND_MIXER_MUTE:
return 0;
break;
case SOUND_MIXER_ENHANCE:
i = 0;
level &= 0x7f;
if (level)
i = (level / 20) - 1;
mode_control &= ~P_M_MV508_ENHANCE_BITS;
mode_control |= P_M_MV508_ENHANCE_BITS;
set_mode (mode_control);
if (i)
i = (i + 1) * 20;
return i;
break;
case SOUND_MIXER_LOUD:
mode_control &= ~P_M_MV508_LOUDNESS;
if (level)
mode_control |= P_M_MV508_LOUDNESS;
set_mode (mode_control);
return !!level; /* 0 or 1 */
break;
case SOUND_MIXER_RECSRC:
devmask = level & POSSIBLE_RECORDING_DEVICES;
changed = devmask ^ rec_devices;
rec_devices = devmask;
for (i = 0; i < SOUND_MIXER_NRDEVICES; i++)
if (changed & (1 << i))
{
pas_mixer_set (i, levels[i]);
}
return rec_devices;
break;
default:
return RET_ERROR (EINVAL);
}
return (levels[whichDev]);
}
/*****/
static void
pas_mixer_reset (void)
{
int foo;
TRACE (printk ("pas2_mixer.c: void pas_mixer_reset(void)\n"));
for (foo = 0; foo < SOUND_MIXER_NRDEVICES; foo++)
pas_mixer_set (foo, levels[foo]);
set_mode (P_M_MV508_LOUDNESS | P_M_MV508_ENHANCE_40);
}
int
pas_mixer_ioctl (int dev, unsigned int cmd, unsigned int arg)
{
TRACE (printk ("pas2_mixer.c: int pas_mixer_ioctl(unsigned int cmd = %X, unsigned int arg = %X)\n", cmd, arg));
if (((cmd >> 8) & 0xff) == 'M')
{
if (cmd & IOC_IN)
return IOCTL_OUT (arg, pas_mixer_set (cmd & 0xff, IOCTL_IN (arg)));
else
{ /*
* Read parameters
*/
switch (cmd & 0xff)
{
case SOUND_MIXER_RECSRC:
return IOCTL_OUT (arg, rec_devices);
break;
case SOUND_MIXER_STEREODEVS:
return IOCTL_OUT (arg, SUPPORTED_MIXER_DEVICES & ~(SOUND_MASK_BASS | SOUND_MASK_TREBLE));
break;
case SOUND_MIXER_DEVMASK:
return IOCTL_OUT (arg, SUPPORTED_MIXER_DEVICES);
break;
case SOUND_MIXER_RECMASK:
return IOCTL_OUT (arg, POSSIBLE_RECORDING_DEVICES & SUPPORTED_MIXER_DEVICES);
break;
case SOUND_MIXER_CAPS:
return IOCTL_OUT (arg, 0); /* No special capabilities */
break;
case SOUND_MIXER_MUTE:
return IOCTL_OUT (arg, 0); /* No mute yet */
break;
case SOUND_MIXER_ENHANCE:
if (!(mode_control & P_M_MV508_ENHANCE_BITS))
return IOCTL_OUT (arg, 0);
return IOCTL_OUT (arg, ((mode_control & P_M_MV508_ENHANCE_BITS) + 1) * 20);
break;
case SOUND_MIXER_LOUD:
if (mode_control & P_M_MV508_LOUDNESS)
return IOCTL_OUT (arg, 1);
return IOCTL_OUT (arg, 0);
break;
default:
return IOCTL_OUT (arg, levels[cmd & 0xff]);
}
}
}
return RET_ERROR (EINVAL);
}
static struct mixer_operations pas_mixer_operations =
{
"Pro Audio Spectrum 16",
pas_mixer_ioctl
};
int
pas_init_mixer (void)
{
pas_mixer_reset ();
if (num_mixers < MAX_MIXER_DEV)
mixer_devs[num_mixers++] = &pas_mixer_operations;
return 1;
}
#endif

View File

@ -1,272 +0,0 @@
/*
* sound/patmgr.c
*
* The patch maneger interface for the /dev/sequencer
*
* Copyright by Hannu Savolainen 1993
*
* 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.
*
* 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.
*
*/
#define PATMGR_C
#ifdef PC98
#include <pc98/pc98/sound/sound_config.h>
#else
#include <i386/isa/sound/sound_config.h>
#endif
#if defined(CONFIGURE_SOUNDCARD) && !defined(EXCLUDE_SEQUENCER)
DEFINE_WAIT_QUEUES (server_procs[MAX_SYNTH_DEV],
server_wait_flag[MAX_SYNTH_DEV]);
static struct patmgr_info *mbox[MAX_SYNTH_DEV] =
{NULL};
static volatile int msg_direction[MAX_SYNTH_DEV] =
{0};
static int pmgr_opened[MAX_SYNTH_DEV] =
{0};
#define A_TO_S 1
#define S_TO_A 2
DEFINE_WAIT_QUEUE (appl_proc, appl_wait_flag);
int
pmgr_open (int dev)
{
if (dev < 0 || dev >= num_synths)
return RET_ERROR (ENXIO);
if (pmgr_opened[dev])
return RET_ERROR (EBUSY);
pmgr_opened[dev] = 1;
RESET_WAIT_QUEUE (server_procs[dev], server_wait_flag[dev]);
return 0;
}
void
pmgr_release (int dev)
{
if (mbox[dev]) /*
* Killed in action. Inform the client
*/
{
mbox[dev]->key = PM_ERROR;
mbox[dev]->parm1 = RET_ERROR (EIO);
if (SOMEONE_WAITING (appl_proc, appl_wait_flag))
WAKE_UP (appl_proc, appl_wait_flag);
}
pmgr_opened[dev] = 0;
}
int
pmgr_read (int dev, struct fileinfo *file, snd_rw_buf * buf, int count)
{
unsigned long flags;
int ok = 0;
if (count != sizeof (struct patmgr_info))
{
printk ("PATMGR%d: Invalid read count\n", dev);
return RET_ERROR (EIO);
}
while (!ok && !PROCESS_ABORTING (server_procs[dev], server_wait_flag[dev]))
{
DISABLE_INTR (flags);
while (!(mbox[dev] && msg_direction[dev] == A_TO_S) &&
!PROCESS_ABORTING (server_procs[dev], server_wait_flag[dev]))
{
DO_SLEEP (server_procs[dev], server_wait_flag[dev], 0);
}
if (mbox[dev] && msg_direction[dev] == A_TO_S)
{
COPY_TO_USER (buf, 0, (char *) mbox[dev], count);
msg_direction[dev] = 0;
ok = 1;
}
RESTORE_INTR (flags);
}
if (!ok)
return RET_ERROR (EINTR);
return count;
}
int
pmgr_write (int dev, struct fileinfo *file, snd_rw_buf * buf, int count)
{
unsigned long flags;
if (count < 4)
{
printk ("PATMGR%d: Write count < 4\n", dev);
return RET_ERROR (EIO);
}
COPY_FROM_USER (mbox[dev], buf, 0, 4);
if (*(unsigned char *) mbox[dev] == SEQ_FULLSIZE)
{
int tmp_dev;
tmp_dev = ((unsigned short *) mbox[dev])[2];
if (tmp_dev != dev)
return RET_ERROR (ENXIO);
return synth_devs[dev]->load_patch (dev, *(unsigned short *) mbox[dev],
buf, 4, count, 1);
}
if (count != sizeof (struct patmgr_info))
{
printk ("PATMGR%d: Invalid write count\n", dev);
return RET_ERROR (EIO);
}
/*
* If everything went OK, there should be a preallocated buffer in the
* mailbox and a client waiting.
*/
DISABLE_INTR (flags);
if (mbox[dev] && !msg_direction[dev])
{
COPY_FROM_USER (&((char *) mbox[dev])[4], buf, 4, count - 4);
msg_direction[dev] = S_TO_A;
if (SOMEONE_WAITING (appl_proc, appl_wait_flag))
{
WAKE_UP (appl_proc, appl_wait_flag);
}
}
RESTORE_INTR (flags);
return count;
}
int
pmgr_access (int dev, struct patmgr_info *rec)
{
unsigned long flags;
int err = 0;
DISABLE_INTR (flags);
if (mbox[dev])
printk (" PATMGR: Server %d mbox full. Why?\n", dev);
else
{
rec->key = PM_K_COMMAND;
mbox[dev] = rec;
msg_direction[dev] = A_TO_S;
if (SOMEONE_WAITING (server_procs[dev], server_wait_flag[dev]))
{
WAKE_UP (server_procs[dev], server_wait_flag[dev]);
}
DO_SLEEP (appl_proc, appl_wait_flag, 0);
if (msg_direction[dev] != S_TO_A)
{
rec->key = PM_ERROR;
rec->parm1 = RET_ERROR (EIO);
}
else if (rec->key == PM_ERROR)
{
err = rec->parm1;
if (err > 0)
err = -err;
}
mbox[dev] = NULL;
msg_direction[dev] = 0;
}
RESTORE_INTR (flags);
return err;
}
int
pmgr_inform (int dev, int event, unsigned long p1, unsigned long p2,
unsigned long p3, unsigned long p4)
{
unsigned long flags;
int err = 0;
if (!pmgr_opened[dev])
return 0;
DISABLE_INTR (flags);
if (mbox[dev])
printk (" PATMGR: Server %d mbox full. Why?\n", dev);
else
{
if ((mbox[dev] =
(struct patmgr_info *) KERNEL_MALLOC (sizeof (struct patmgr_info))) == NULL)
{
printk ("pmgr: Couldn't allocate memory for a message\n");
return 0;
}
mbox[dev]->key = PM_K_EVENT;
mbox[dev]->command = event;
mbox[dev]->parm1 = p1;
mbox[dev]->parm2 = p2;
mbox[dev]->parm3 = p3;
msg_direction[dev] = A_TO_S;
if (SOMEONE_WAITING (server_procs[dev], server_wait_flag[dev]))
{
WAKE_UP (server_procs[dev], server_wait_flag[dev]);
}
DO_SLEEP (appl_proc, appl_wait_flag, 0);
if (mbox[dev])
KERNEL_FREE (mbox[dev]);
mbox[dev] = NULL;
msg_direction[dev] = 0;
}
RESTORE_INTR (flags);
return err;
}
#endif

View File

@ -25,7 +25,7 @@
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
* $Id: pcm86.c,v 2.4 1996/01/24 19:53:34 abtk Exp $
* $Id: pcm86.c,v 1.2 1996/09/12 11:11:16 asami Exp $
*/
/*
@ -36,7 +36,7 @@
*/
#include "sound_config.h"
#include <i386/isa/sound/sound_config.h>
#ifdef CONFIGURE_SOUNDCARD

View File

@ -34,11 +34,7 @@
/*
* #define DEB_DMARES
*/
#ifdef PC98
#include <pc98/pc98/sound/sound_config.h>
#else
#include <i386/isa/sound/sound_config.h>
#endif
#include <i386/isa/sound/sb.h>
#include <i386/isa/sound/sb_mixer.h>

View File

@ -27,11 +27,7 @@
*
*/
#ifdef PC98
#include <pc98/pc98/sound/sound_config.h>
#else
#include <i386/isa/sound/sound_config.h>
#endif
#ifdef CONFIGURE_SOUNDCARD

View File

@ -1,65 +0,0 @@
/*
* sound/sb_card.c
*
* Detection routine for the SoundBlaster cards.
*
* Copyright by Hannu Savolainen 1993
*
* 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.
*
* 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.
*
* Modified:
* Riccardo Facchetti 24 Mar 1995
* - Added the Audio Excel DSP 16 initialization routine.
*/
#ifdef PC98
#include <pc98/pc98/sound/sound_config.h>
#else
#include <i386/isa/sound/sound_config.h>
#endif
#if defined(CONFIGURE_SOUNDCARD) && !defined(EXCLUDE_SB)
long
attach_sb_card (long mem_start, struct address_info *hw_config)
{
#if !defined(EXCLUDE_AUDIO) || !defined(EXCLUDE_MIDI)
if (!sb_dsp_detect (hw_config))
return mem_start;
mem_start = sb_dsp_init (mem_start, hw_config);
#endif
return mem_start;
}
int
probe_sb (struct address_info *hw_config)
{
#if !defined(EXCLUDE_AEDSP16) && defined(AEDSP16_SBPRO)
/*
* Initialize Audio Excel DSP 16 to SBPRO.
*/
InitAEDSP16_SBPRO (hw_config);
#endif
return sb_dsp_detect (hw_config);
}
#endif

View File

@ -33,11 +33,7 @@
* Code added for MV ProSonic/Jazz 16 in 16 bit mode
*/
#ifdef PC98
#include <pc98/pc98/sound/sound_config.h>
#else
#include <i386/isa/sound/sound_config.h>
#endif
#if defined(CONFIGURE_SOUNDCARD) && !defined(EXCLUDE_SB)

View File

@ -1,257 +0,0 @@
/*
* sound/sb_dsp.c
*
* The low level driver for the SoundBlaster DS chips.
*
* Copyright by Hannu Savolainen 1993
*
* 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.
*
* 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.
*
*/
#ifdef PC98
#include <pc98/pc98/sound/sound_config.h>
#else
#include <i386/isa/sound/sound_config.h>
#endif
#if defined(CONFIGURE_SOUNDCARD) && !defined(EXCLUDE_SB) && !defined(EXCLUDE_MIDI)
#include <i386/isa/sound/sb.h>
#undef SB_TEST_IRQ
/*
* The DSP channel can be used either for input or output. Variable
* 'sb_irq_mode' will be set when the program calls read or write first time
* after open. Current version doesn't support mode changes without closing
* and reopening the device. Support for this feature may be implemented in a
* future version of this driver.
*/
extern int sb_dsp_ok; /* Set to 1 atfer successful initialization */
extern int sbc_base;
extern int sb_midi_mode;
extern int sb_midi_busy; /*
* * * * 1 if the process has output to MIDI
*
*/
extern int sb_dsp_busy;
extern int sb_dsp_highspeed;
extern volatile int sb_irq_mode;
extern int sb_duplex_midi;
extern int sb_intr_active;
static int input_opened = 0;
static int my_dev;
void (*midi_input_intr) (int dev, unsigned char data);
static int
sb_midi_open (int dev, int mode,
void (*input) (int dev, unsigned char data),
void (*output) (int dev)
)
{
int ret;
if (!sb_dsp_ok)
{
printk ("SB Error: MIDI hardware not installed\n");
return RET_ERROR (ENXIO);
}
if (sb_midi_busy)
return RET_ERROR (EBUSY);
if (mode != OPEN_WRITE && !sb_duplex_midi)
{
if (num_midis == 1)
printk ("SoundBlaster: Midi input not currently supported\n");
return RET_ERROR (EPERM);
}
sb_midi_mode = NORMAL_MIDI;
if (mode != OPEN_WRITE)
{
if (sb_dsp_busy || sb_intr_active)
return RET_ERROR (EBUSY);
sb_midi_mode = UART_MIDI;
}
if (sb_dsp_highspeed)
{
printk ("SB Error: Midi output not possible during stereo or high speed audio\n");
return RET_ERROR (EBUSY);
}
if (sb_midi_mode == UART_MIDI)
{
sb_irq_mode = IMODE_MIDI;
sb_reset_dsp ();
if (!sb_dsp_command (0x35))
return RET_ERROR (EIO); /*
* Enter the UART mode
*/
sb_intr_active = 1;
if ((ret = sb_get_irq ()) < 0)
{
sb_reset_dsp ();
return 0; /*
* IRQ not free
*/
}
input_opened = 1;
midi_input_intr = input;
}
sb_midi_busy = 1;
return 0;
}
static void
sb_midi_close (int dev)
{
if (sb_midi_mode == UART_MIDI)
{
sb_reset_dsp (); /*
* The only way to kill the UART mode
*/
sb_free_irq ();
}
sb_intr_active = 0;
sb_midi_busy = 0;
input_opened = 0;
}
static int
sb_midi_out (int dev, unsigned char midi_byte)
{
unsigned long flags;
if (sb_midi_mode == NORMAL_MIDI)
{
DISABLE_INTR (flags);
if (sb_dsp_command (0x38))
sb_dsp_command (midi_byte);
else
printk ("SB Error: Unable to send a MIDI byte\n");
RESTORE_INTR (flags);
}
else
sb_dsp_command (midi_byte); /*
* UART write
*/
return 1;
}
static int
sb_midi_start_read (int dev)
{
if (sb_midi_mode != UART_MIDI)
{
printk ("SoundBlaster: MIDI input not implemented.\n");
return RET_ERROR (EPERM);
}
return 0;
}
static int
sb_midi_end_read (int dev)
{
if (sb_midi_mode == UART_MIDI)
{
sb_reset_dsp ();
sb_intr_active = 0;
}
return 0;
}
static int
sb_midi_ioctl (int dev, unsigned cmd, unsigned arg)
{
return RET_ERROR (EPERM);
}
void
sb_midi_interrupt (int dummy)
{
unsigned long flags;
unsigned char data;
DISABLE_INTR (flags);
data = INB (DSP_READ);
if (input_opened)
midi_input_intr (my_dev, data);
RESTORE_INTR (flags);
}
#define MIDI_SYNTH_NAME "SoundBlaster Midi"
#define MIDI_SYNTH_CAPS 0
#include <i386/isa/sound/midi_synth.h>
static struct midi_operations sb_midi_operations =
{
{"SoundBlaster", 0, 0, SNDCARD_SB},
&std_midi_synth,
{0},
sb_midi_open,
sb_midi_close,
sb_midi_ioctl,
sb_midi_out,
sb_midi_start_read,
sb_midi_end_read,
NULL, /*
* Kick
*/
NULL, /*
* command
*/
NULL, /*
* buffer_status
*/
NULL
};
void
sb_midi_init (int model)
{
if (num_midis >= MAX_MIDI_DEV)
{
printk ("Sound: Too many midi devices detected\n");
return;
}
std_midi_synth.midi_dev = num_midis;
my_dev = num_midis;
midi_devs[num_midis++] = &sb_midi_operations;
}
#endif

View File

@ -1,591 +0,0 @@
/*
* sound/sb_mixer.c
*
* The low level mixer driver for the SoundBlaster Pro and SB16 cards.
*
* Copyright by Hannu Savolainen 1994
*
* 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.
*
* 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.
*
* Modified:
* Hunyue Yau Jan 6 1994
* Added code to support the Sound Galaxy NX Pro mixer.
*
*/
#ifdef PC98
#include <pc98/pc98/sound/sound_config.h>
#else
#include <i386/isa/sound/sound_config.h>
#endif
#if defined(CONFIGURE_SOUNDCARD) && !defined(EXCLUDE_SB) && !defined(EXCLUDE_SBPRO)
#define __SB_MIXER_C__
#include <i386/isa/sound/sb.h>
#include <i386/isa/sound/sb_mixer.h>
#undef SB_TEST_IRQ
extern int sbc_base;
extern int sbc_major;
extern int Jazz16_detected;
static int mixer_initialized = 0;
static int supported_rec_devices;
static int supported_devices;
static int recmask = 0;
static int mixer_model;
static int mixer_caps;
static mixer_tab *iomap;
void
sb_setmixer (unsigned int port, unsigned int value)
{
unsigned long flags;
DISABLE_INTR (flags);
OUTB ((unsigned char) (port & 0xff), MIXER_ADDR); /*
* Select register
*/
tenmicrosec ();
OUTB ((unsigned char) (value & 0xff), MIXER_DATA);
tenmicrosec ();
RESTORE_INTR (flags);
}
int
sb_getmixer (unsigned int port)
{
int val;
unsigned long flags;
DISABLE_INTR (flags);
OUTB ((unsigned char) (port & 0xff), MIXER_ADDR); /*
* Select register
*/
tenmicrosec ();
val = INB (MIXER_DATA);
tenmicrosec ();
RESTORE_INTR (flags);
return val;
}
void
sb_mixer_set_stereo (int mode)
{
if (!mixer_initialized)
return;
sb_setmixer (OUT_FILTER, ((sb_getmixer (OUT_FILTER) & ~STEREO_DAC)
| (mode ? STEREO_DAC : MONO_DAC)));
}
/*
* Returns:
* 0 No mixer detected.
* 1 Only a plain Sound Blaster Pro style mixer detected.
* 2 The Sound Galaxy NX Pro mixer detected.
*/
static int
detect_mixer (void)
{
#ifdef __SGNXPRO__
int oldbass, oldtreble;
#endif
int retcode = 1;
/*
* Detect the mixer by changing parameters of two volume channels. If the
* values read back match with the values written, the mixer is there (is
* it?)
*/
sb_setmixer (FM_VOL, 0xff);
sb_setmixer (VOC_VOL, 0x33);
if (sb_getmixer (FM_VOL) != 0xff)
return 0; /*
* No match
*/
if (sb_getmixer (VOC_VOL) != 0x33)
return 0;
#ifdef __SGNXPRO__
/* Attempt to detect the SG NX Pro by check for valid bass/treble
* registers.
*/
oldbass = sb_getmixer (BASS_LVL);
oldtreble = sb_getmixer (TREBLE_LVL);
sb_setmixer (BASS_LVL, 0xaa);
sb_setmixer (TREBLE_LVL, 0x55);
if ((sb_getmixer (BASS_LVL) != 0xaa) ||
(sb_getmixer (TREBLE_LVL) != 0x55))
{
retcode = 1; /* 1 == Only SB Pro detected */
}
else
retcode = 2; /* 2 == SG NX Pro detected */
/* Restore register in either case since SG NX Pro has EEPROM with
* 'preferred' values stored.
*/
sb_setmixer (BASS_LVL, oldbass);
sb_setmixer (TREBLE_LVL, oldtreble);
/*
* If the SB version is 3.X (SB Pro), assume we have a SG NX Pro 16.
* In this case it's good idea to disable the Disney Sound Source
* compatibility mode. It's useless and just causes noise every time the
* LPT-port is accessed.
*
* Also place the card into WSS mode.
*/
if (sbc_major == 3)
{
OUTB (0x01, sbc_base + 0x1c);
OUTB (0x00, sbc_base + 0x1a);
}
#endif
return retcode;
}
static void
change_bits (unsigned char *regval, int dev, int chn, int newval)
{
unsigned char mask;
int shift;
mask = (1 << (*iomap)[dev][chn].nbits) - 1;
newval = (int) ((newval * mask) + 50) / 100; /*
* Scale it
*/
shift = (*iomap)[dev][chn].bitoffs - (*iomap)[dev][LEFT_CHN].nbits + 1;
*regval &= ~(mask << shift); /*
* Filter out the previous value
*/
*regval |= (newval & mask) << shift; /*
* Set the new value
*/
}
static int
sb_mixer_get (int dev)
{
if (!((1 << dev) & supported_devices))
return RET_ERROR (EINVAL);
return levels[dev];
}
#ifdef JAZZ16
static char smw_mix_regs[] = /* Left mixer registers */
{
0x0b, /* SOUND_MIXER_VOLUME */
0x0d, /* SOUND_MIXER_BASS */
0x0d, /* SOUND_MIXER_TREBLE */
0x05, /* SOUND_MIXER_SYNTH */
0x09, /* SOUND_MIXER_PCM */
0x00, /* SOUND_MIXER_SPEAKER */
0x03, /* SOUND_MIXER_LINE */
0x01, /* SOUND_MIXER_MIC */
0x07, /* SOUND_MIXER_CD */
0x00, /* SOUND_MIXER_IMIX */
0x00, /* SOUND_MIXER_ALTPCM */
0x00, /* SOUND_MIXER_RECLEV */
0x00, /* SOUND_MIXER_IGAIN */
0x00, /* SOUND_MIXER_OGAIN */
0x00, /* SOUND_MIXER_LINE1 */
0x00, /* SOUND_MIXER_LINE2 */
0x00 /* SOUND_MIXER_LINE3 */
};
static void
smw_mixer_init (void)
{
int i;
sb_setmixer (0x00, 0x18); /* Mute unused (Telephone) line */
sb_setmixer (0x10, 0x38); /* Config register 2 */
supported_devices = 0;
for (i = 0; i < sizeof (smw_mix_regs); i++)
if (smw_mix_regs[i] != 0)
supported_devices |= (1 << i);
supported_rec_devices = supported_devices &
~(SOUND_MASK_BASS | SOUND_MASK_TREBLE | SOUND_MASK_PCM |
SOUND_MASK_VOLUME);
}
static int
smw_mixer_set (int dev, int value)
{
int left = value & 0x000000ff;
int right = (value & 0x0000ff00) >> 8;
int reg, val;
if (left > 100)
left = 100;
if (right > 100)
right = 100;
if (dev > 31)
return RET_ERROR (EINVAL);
if (!(supported_devices & (1 << dev))) /* Not supported */
return RET_ERROR (EINVAL);
switch (dev)
{
case SOUND_MIXER_VOLUME:
sb_setmixer (0x0b, 96 - (96 * left / 100)); /* 96=mute, 0=max */
sb_setmixer (0x0c, 96 - (96 * right / 100));
break;
case SOUND_MIXER_BASS:
case SOUND_MIXER_TREBLE:
levels[dev] = left | (right << 8);
/* Set left bass and treble values */
val = ((levels[SOUND_MIXER_TREBLE] & 0xff) * 16 / 100) << 4;
val |= ((levels[SOUND_MIXER_BASS] & 0xff) * 16 / 100) & 0x0f;
sb_setmixer (0x0d, val);
/* Set right bass and treble values */
val = (((levels[SOUND_MIXER_TREBLE] >> 8) & 0xff) * 16 / 100) << 4;
val |= (((levels[SOUND_MIXER_BASS] >> 8) & 0xff) * 16 / 100) & 0x0f;
sb_setmixer (0x0e, val);
break;
default:
reg = smw_mix_regs[dev];
if (reg == 0)
return RET_ERROR (EINVAL);
sb_setmixer (reg, (24 - (24 * left / 100)) | 0x20); /* 24=mute, 0=max */
sb_setmixer (reg + 1, (24 - (24 * right / 100)) | 0x40);
}
levels[dev] = left | (right << 8);
return left | (right << 8);
}
#endif
static int
sb_mixer_set (int dev, int value)
{
int left = value & 0x000000ff;
int right = (value & 0x0000ff00) >> 8;
int regoffs;
unsigned char val;
#ifdef JAZZ16
if (Jazz16_detected == 2)
return smw_mixer_set (dev, value);
#endif
if (left > 100)
left = 100;
if (right > 100)
right = 100;
if (dev > 31)
return RET_ERROR (EINVAL);
if (!(supported_devices & (1 << dev))) /*
* Not supported
*/
return RET_ERROR (EINVAL);
regoffs = (*iomap)[dev][LEFT_CHN].regno;
if (regoffs == 0)
return RET_ERROR (EINVAL);
val = sb_getmixer (regoffs);
change_bits (&val, dev, LEFT_CHN, left);
levels[dev] = left | (left << 8);
if ((*iomap)[dev][RIGHT_CHN].regno != regoffs) /*
* Change register
*/
{
sb_setmixer (regoffs, val); /*
* Save the old one
*/
regoffs = (*iomap)[dev][RIGHT_CHN].regno;
if (regoffs == 0)
return left | (left << 8); /*
* Just left channel present
*/
val = sb_getmixer (regoffs); /*
* Read the new one
*/
}
change_bits (&val, dev, RIGHT_CHN, right);
sb_setmixer (regoffs, val);
levels[dev] = left | (right << 8);
return left | (right << 8);
}
static void
set_recsrc (int src)
{
sb_setmixer (RECORD_SRC, (sb_getmixer (RECORD_SRC) & ~7) | (src & 0x7));
}
static int
set_recmask (int mask)
{
int devmask, i;
unsigned char regimageL, regimageR;
devmask = mask & supported_rec_devices;
switch (mixer_model)
{
case 3:
if (devmask != SOUND_MASK_MIC &&
devmask != SOUND_MASK_LINE &&
devmask != SOUND_MASK_CD)
{ /*
* More than one devices selected. Drop the *
* previous selection
*/
devmask &= ~recmask;
}
if (devmask != SOUND_MASK_MIC &&
devmask != SOUND_MASK_LINE &&
devmask != SOUND_MASK_CD)
{ /*
* More than one devices selected. Default to
* * mic
*/
devmask = SOUND_MASK_MIC;
}
if (devmask ^ recmask) /*
* Input source changed
*/
{
switch (devmask)
{
case SOUND_MASK_MIC:
set_recsrc (SRC_MIC);
break;
case SOUND_MASK_LINE:
set_recsrc (SRC_LINE);
break;
case SOUND_MASK_CD:
set_recsrc (SRC_CD);
break;
default:
set_recsrc (SRC_MIC);
}
}
break;
case 4:
if (!devmask)
devmask = SOUND_MASK_MIC;
regimageL = regimageR = 0;
for (i = 0; i < SOUND_MIXER_NRDEVICES; i++)
if ((1 << i) & devmask)
{
regimageL |= sb16_recmasks_L[i];
regimageR |= sb16_recmasks_R[i];
}
sb_setmixer (SB16_IMASK_L, regimageL);
sb_setmixer (SB16_IMASK_R, regimageR);
break;
}
recmask = devmask;
return recmask;
}
static int
sb_mixer_ioctl (int dev, unsigned int cmd, unsigned int arg)
{
if (((cmd >> 8) & 0xff) == 'M')
{
if (cmd & IOC_IN)
switch (cmd & 0xff)
{
case SOUND_MIXER_RECSRC:
return IOCTL_OUT (arg, set_recmask (IOCTL_IN (arg)));
break;
default:
return IOCTL_OUT (arg, sb_mixer_set (cmd & 0xff, IOCTL_IN (arg)));
}
else
switch (cmd & 0xff) /*
* Return parameters
*/
{
case SOUND_MIXER_RECSRC:
return IOCTL_OUT (arg, recmask);
break;
case SOUND_MIXER_DEVMASK:
return IOCTL_OUT (arg, supported_devices);
break;
case SOUND_MIXER_STEREODEVS:
if (Jazz16_detected)
return IOCTL_OUT (arg, supported_devices);
else
return IOCTL_OUT (arg, supported_devices &
~(SOUND_MASK_MIC | SOUND_MASK_SPEAKER));
break;
case SOUND_MIXER_RECMASK:
return IOCTL_OUT (arg, supported_rec_devices);
break;
case SOUND_MIXER_CAPS:
return IOCTL_OUT (arg, mixer_caps);
break;
default:
return IOCTL_OUT (arg, sb_mixer_get (cmd & 0xff));
}
}
else
return RET_ERROR (EINVAL);
}
static struct mixer_operations sb_mixer_operations =
{
"SoundBlaster",
sb_mixer_ioctl
};
static void
sb_mixer_reset (void)
{
int i;
for (i = 0; i < SOUND_MIXER_NRDEVICES; i++)
sb_mixer_set (i, levels[i]);
set_recmask (SOUND_MASK_MIC);
}
/*
* Returns a code depending on whether a SG NX Pro was detected.
* 1 == Plain SB Pro
* 2 == SG NX Pro detected.
* 3 == SB16
*
* Used to update message.
*/
int
sb_mixer_init (int major_model)
{
int mixer_type = 0;
sb_setmixer (0x00, 0); /* Reset mixer */
if (!(mixer_type = detect_mixer ()))
return 0; /* No mixer. Why? */
mixer_initialized = 1;
mixer_model = major_model;
switch (major_model)
{
case 3:
mixer_caps = SOUND_CAP_EXCL_INPUT;
#ifdef JAZZ16
if (Jazz16_detected == 2) /* SM Wave */
{
supported_devices = 0;
supported_rec_devices = 0;
iomap = &sbpro_mix;
smw_mixer_init ();
mixer_type = 1;
}
else
#endif
#ifdef __SGNXPRO__
if (mixer_type == 2) /* A SGNXPRO was detected */
{
supported_devices = SGNXPRO_MIXER_DEVICES;
supported_rec_devices = SGNXPRO_RECORDING_DEVICES;
iomap = &sgnxpro_mix;
}
else
#endif
{
supported_devices = SBPRO_MIXER_DEVICES;
supported_rec_devices = SBPRO_RECORDING_DEVICES;
iomap = &sbpro_mix;
mixer_type = 1;
}
break;
case 4:
mixer_caps = 0;
supported_devices = SB16_MIXER_DEVICES;
supported_rec_devices = SB16_RECORDING_DEVICES;
iomap = &sb16_mix;
mixer_type = 3;
break;
default:
printk ("SB Warning: Unsupported mixer type\n");
return 0;
}
if (num_mixers < MAX_MIXER_DEV)
mixer_devs[num_mixers++] = &sb_mixer_operations;
sb_mixer_reset ();
return mixer_type;
}
#endif

File diff suppressed because it is too large Load Diff

View File

@ -1,120 +0,0 @@
$Id: sound.doc,v 1.6 1996/04/11 15:34:22 smpatel Exp $
Instructions on using audio on a FreeBSD 2.1 (or 2.0-current) system.
See also /sys/i386/conf/LINT.
To enable sound driver support, the controller sound code must be included
in your config file:
# SB = SoundBlaster; PAS = ProAudioSpectrum; GUS = Gravis UltraSound
# Controls all sound devices
controller snd0
Uncomment one or more of these device entries, depending on what type of
sound card you have:
# ProAudioSpectrum PCM and Midi - for PAS
#device pas0 at isa? port 0x388 irq 10 drq 6 vector pasintr
# SoundBlaster DSP driver - for SB, SB Pro, SB16, PAS(emulating SB)
#device sb0 at isa? port 0x220 irq 7 drq 1 vector sbintr
# SoundBlaster 16 DSP driver - for SB16 - requires sb0 device
#device sbxvi0 at isa? drq 5
# SoundBlaster 16 MIDI - for SB16 - requires sb0 device
#device sbmidi0 at isa? port 0x300
# Gravis UltraSound - for GUS, GUS16, GUSMAX
# For cards that use 2 DMA Channels:
# drq = Write DMA Channel, flags = Read DMA Channel
#device gus0 at isa? port 0x220 irq 11 drq 1 flags 0x3 vector gusintr
# Gravis UltraSound 16 bit option - for GUS16 - requires gus0
#device gusxvi0 at isa? port 0x530 irq 7 drq 3 vector adintr
# MS Sound System (AD1848 Based Boards)
#device mss0 at isa? port 0x530 irq 10 drq 1 vector adintr
# Yamaha OPL-2/OPL-3 FM - for SB, SB Pro, SB16, PAS
#device opl0 at isa? port 0x388
# MPU-401 - for MPU-401 standalone card
#device mpu0 at isa? port 0x330 irq 6 drq 0
# 6850 UART Midi
#device uart0 at isa? port 0x330 irq 5 vector "m6850intr"
You may add one or more of the following depending on what you do and don't
want compiled into your kernel. Note: Excluding things with EXCLUDE_...
is NOT recommended unless you really know what you're doing.
#options EXCLUDE_AUDIO # NO digital audio support
#options EXCLUDE_SEQUENCER # NO sequencer support
#options EXCLUDE_MIDI # NO MIDI support whatsoever
#options EXCLUDE_SBPRO # EXCLUDE SB Pro support
#options EXCLUDE_SB_EMULATION # NO PAS SB emulation support
#options EXCLUDE_GUS_IODETECT # NO GUS io detection
#options EXCLUDE_PRO_MIDI # NO PAS MIDI support
Other Options:
#options SYMPHONY_PAS
Adds some code to make pas work with Symphony chipsets. Only use
this if your pas doesn't work and you have a Symphony chipset.
#options BROKEN_BUS_CLOCK
Some systems with the OPTI chipset and a PAS will require you to
use this option. Symptoms are that you will hear a lot of clicking and
popping sounds, like a geiger counter, coming out of the PAS even when
it is not playing anything.
#options MOZART_PORT
Adds support for Mozart (OAK OTI-601). (Part of the MSS driver)
#options OPTI_MAD16_PORT
Adds support for the OPTI MAD16 Chip. (Part of the MSS driver)
If your soundcard has a chip labeled "OPTi 82C929" then try this.
#options __SGNXPRO__
Adds support for the SG NX Pro mixer. (Part of the SB driver)
#options JAZZ16
Adds support for the MV Jazz16 (ProSonic etc). (Part of the SB Driver)
#options SM_WAVE
Adds support for the SoundMan Wave (Part of the SB Driver)
Note: You will need to do some work to get this to work.
See i386/isa/sound/configure.c
#options SM_GAMES
Adds support for the Logitech SoundMan Games (Part of the SB Driver)
#options PAS_JOYSTICK_ENABLE
Enables the gameport on the ProAudio Spectrum
NOTE: The MPU-401 driver may or may not work, and is unfortunately
unverifiable since no one I know has one. If you can test this,
please let me know! Also note that you will have to change these
settings if your soundcard is set for a non-standard address or IRQ.
Please check your documentation (or verify with any provided DOS utilities
that may have come with your card) and set the IRQ or address fields
accordingly.
Also: You can configure more then one card on a single DMA using
the conflicts keyword in your configuration file. This is useful for boards
with more then one type of emulation.
Probing problems: Since the SB16 uses the same IRQ and addresses for
the different drivers, some of the snd drivers will not be probed because
the kernel thinks there is a conflict. This can be worked-around by
using the "conflicts" keyword on the sb16's device line.
For further information, contact multimedia@freebsd.org
- Jordan Hubbard (jkh@freefall.cdrom.com)
- Steven Wallace (swallace@freefall.cdrom.com)
- Sujal Patel (smpatel@wam.umd.edu)

Some files were not shown because too many files have changed in this diff Show More